• Home
  • History
  • Annotate
  • Line#
  • Navigate
  • Raw
  • Download
  • only in /netgear-R7000-V1.0.7.12_1.2.5/components/opensource/linux/linux-2.6.36/security/selinux/
1/* Updated: Karl MacMillan <kmacmillan@tresys.com>
2 *
3 *	Added conditional policy language extensions
4 *
5 *  Updated: Hewlett-Packard <paul.moore@hp.com>
6 *
7 *	Added support for the policy capability bitmap
8 *
9 * Copyright (C) 2007 Hewlett-Packard Development Company, L.P.
10 * Copyright (C) 2003 - 2004 Tresys Technology, LLC
11 * Copyright (C) 2004 Red Hat, Inc., James Morris <jmorris@redhat.com>
12 *	This program is free software; you can redistribute it and/or modify
13 *	it under the terms of the GNU General Public License as published by
14 *	the Free Software Foundation, version 2.
15 */
16
17#include <linux/kernel.h>
18#include <linux/pagemap.h>
19#include <linux/slab.h>
20#include <linux/vmalloc.h>
21#include <linux/fs.h>
22#include <linux/mutex.h>
23#include <linux/init.h>
24#include <linux/string.h>
25#include <linux/security.h>
26#include <linux/major.h>
27#include <linux/seq_file.h>
28#include <linux/percpu.h>
29#include <linux/audit.h>
30#include <linux/uaccess.h>
31
32/* selinuxfs pseudo filesystem for exporting the security policy API.
33   Based on the proc code and the fs/nfsd/nfsctl.c code. */
34
35#include "flask.h"
36#include "avc.h"
37#include "avc_ss.h"
38#include "security.h"
39#include "objsec.h"
40#include "conditional.h"
41
42/* Policy capability filenames */
43static char *policycap_names[] = {
44	"network_peer_controls",
45	"open_perms"
46};
47
48unsigned int selinux_checkreqprot = CONFIG_SECURITY_SELINUX_CHECKREQPROT_VALUE;
49
50static int __init checkreqprot_setup(char *str)
51{
52	unsigned long checkreqprot;
53	if (!strict_strtoul(str, 0, &checkreqprot))
54		selinux_checkreqprot = checkreqprot ? 1 : 0;
55	return 1;
56}
57__setup("checkreqprot=", checkreqprot_setup);
58
59static DEFINE_MUTEX(sel_mutex);
60
61/* global data for booleans */
62static struct dentry *bool_dir;
63static int bool_num;
64static char **bool_pending_names;
65static int *bool_pending_values;
66
67/* global data for classes */
68static struct dentry *class_dir;
69static unsigned long last_class_ino;
70
71/* global data for policy capabilities */
72static struct dentry *policycap_dir;
73
74extern void selnl_notify_setenforce(int val);
75
76/* Check whether a task is allowed to use a security operation. */
77static int task_has_security(struct task_struct *tsk,
78			     u32 perms)
79{
80	const struct task_security_struct *tsec;
81	u32 sid = 0;
82
83	rcu_read_lock();
84	tsec = __task_cred(tsk)->security;
85	if (tsec)
86		sid = tsec->sid;
87	rcu_read_unlock();
88	if (!tsec)
89		return -EACCES;
90
91	return avc_has_perm(sid, SECINITSID_SECURITY,
92			    SECCLASS_SECURITY, perms, NULL);
93}
94
95enum sel_inos {
96	SEL_ROOT_INO = 2,
97	SEL_LOAD,	/* load policy */
98	SEL_ENFORCE,	/* get or set enforcing status */
99	SEL_CONTEXT,	/* validate context */
100	SEL_ACCESS,	/* compute access decision */
101	SEL_CREATE,	/* compute create labeling decision */
102	SEL_RELABEL,	/* compute relabeling decision */
103	SEL_USER,	/* compute reachable user contexts */
104	SEL_POLICYVERS,	/* return policy version for this kernel */
105	SEL_COMMIT_BOOLS, /* commit new boolean values */
106	SEL_MLS,	/* return if MLS policy is enabled */
107	SEL_DISABLE,	/* disable SELinux until next reboot */
108	SEL_MEMBER,	/* compute polyinstantiation membership decision */
109	SEL_CHECKREQPROT, /* check requested protection, not kernel-applied one */
110	SEL_COMPAT_NET,	/* whether to use old compat network packet controls */
111	SEL_REJECT_UNKNOWN, /* export unknown reject handling to userspace */
112	SEL_DENY_UNKNOWN, /* export unknown deny handling to userspace */
113	SEL_INO_NEXT,	/* The next inode number to use */
114};
115
116static unsigned long sel_last_ino = SEL_INO_NEXT - 1;
117
118#define SEL_INITCON_INO_OFFSET		0x01000000
119#define SEL_BOOL_INO_OFFSET		0x02000000
120#define SEL_CLASS_INO_OFFSET		0x04000000
121#define SEL_POLICYCAP_INO_OFFSET	0x08000000
122#define SEL_INO_MASK			0x00ffffff
123
124#define TMPBUFLEN	12
125static ssize_t sel_read_enforce(struct file *filp, char __user *buf,
126				size_t count, loff_t *ppos)
127{
128	char tmpbuf[TMPBUFLEN];
129	ssize_t length;
130
131	length = scnprintf(tmpbuf, TMPBUFLEN, "%d", selinux_enforcing);
132	return simple_read_from_buffer(buf, count, ppos, tmpbuf, length);
133}
134
135#ifdef CONFIG_SECURITY_SELINUX_DEVELOP
136static ssize_t sel_write_enforce(struct file *file, const char __user *buf,
137				 size_t count, loff_t *ppos)
138
139{
140	char *page;
141	ssize_t length;
142	int new_value;
143
144	if (count >= PAGE_SIZE)
145		return -ENOMEM;
146	if (*ppos != 0) {
147		/* No partial writes. */
148		return -EINVAL;
149	}
150	page = (char *)get_zeroed_page(GFP_KERNEL);
151	if (!page)
152		return -ENOMEM;
153	length = -EFAULT;
154	if (copy_from_user(page, buf, count))
155		goto out;
156
157	length = -EINVAL;
158	if (sscanf(page, "%d", &new_value) != 1)
159		goto out;
160
161	if (new_value != selinux_enforcing) {
162		length = task_has_security(current, SECURITY__SETENFORCE);
163		if (length)
164			goto out;
165		audit_log(current->audit_context, GFP_KERNEL, AUDIT_MAC_STATUS,
166			"enforcing=%d old_enforcing=%d auid=%u ses=%u",
167			new_value, selinux_enforcing,
168			audit_get_loginuid(current),
169			audit_get_sessionid(current));
170		selinux_enforcing = new_value;
171		if (selinux_enforcing)
172			avc_ss_reset(0);
173		selnl_notify_setenforce(selinux_enforcing);
174	}
175	length = count;
176out:
177	free_page((unsigned long) page);
178	return length;
179}
180#else
181#define sel_write_enforce NULL
182#endif
183
184static const struct file_operations sel_enforce_ops = {
185	.read		= sel_read_enforce,
186	.write		= sel_write_enforce,
187	.llseek		= generic_file_llseek,
188};
189
190static ssize_t sel_read_handle_unknown(struct file *filp, char __user *buf,
191					size_t count, loff_t *ppos)
192{
193	char tmpbuf[TMPBUFLEN];
194	ssize_t length;
195	ino_t ino = filp->f_path.dentry->d_inode->i_ino;
196	int handle_unknown = (ino == SEL_REJECT_UNKNOWN) ?
197		security_get_reject_unknown() : !security_get_allow_unknown();
198
199	length = scnprintf(tmpbuf, TMPBUFLEN, "%d", handle_unknown);
200	return simple_read_from_buffer(buf, count, ppos, tmpbuf, length);
201}
202
203static const struct file_operations sel_handle_unknown_ops = {
204	.read		= sel_read_handle_unknown,
205	.llseek		= generic_file_llseek,
206};
207
208#ifdef CONFIG_SECURITY_SELINUX_DISABLE
209static ssize_t sel_write_disable(struct file *file, const char __user *buf,
210				 size_t count, loff_t *ppos)
211
212{
213	char *page;
214	ssize_t length;
215	int new_value;
216	extern int selinux_disable(void);
217
218	if (count >= PAGE_SIZE)
219		return -ENOMEM;
220	if (*ppos != 0) {
221		/* No partial writes. */
222		return -EINVAL;
223	}
224	page = (char *)get_zeroed_page(GFP_KERNEL);
225	if (!page)
226		return -ENOMEM;
227	length = -EFAULT;
228	if (copy_from_user(page, buf, count))
229		goto out;
230
231	length = -EINVAL;
232	if (sscanf(page, "%d", &new_value) != 1)
233		goto out;
234
235	if (new_value) {
236		length = selinux_disable();
237		if (length < 0)
238			goto out;
239		audit_log(current->audit_context, GFP_KERNEL, AUDIT_MAC_STATUS,
240			"selinux=0 auid=%u ses=%u",
241			audit_get_loginuid(current),
242			audit_get_sessionid(current));
243	}
244
245	length = count;
246out:
247	free_page((unsigned long) page);
248	return length;
249}
250#else
251#define sel_write_disable NULL
252#endif
253
254static const struct file_operations sel_disable_ops = {
255	.write		= sel_write_disable,
256	.llseek		= generic_file_llseek,
257};
258
259static ssize_t sel_read_policyvers(struct file *filp, char __user *buf,
260				   size_t count, loff_t *ppos)
261{
262	char tmpbuf[TMPBUFLEN];
263	ssize_t length;
264
265	length = scnprintf(tmpbuf, TMPBUFLEN, "%u", POLICYDB_VERSION_MAX);
266	return simple_read_from_buffer(buf, count, ppos, tmpbuf, length);
267}
268
269static const struct file_operations sel_policyvers_ops = {
270	.read		= sel_read_policyvers,
271	.llseek		= generic_file_llseek,
272};
273
274/* declaration for sel_write_load */
275static int sel_make_bools(void);
276static int sel_make_classes(void);
277static int sel_make_policycap(void);
278
279/* declaration for sel_make_class_dirs */
280static int sel_make_dir(struct inode *dir, struct dentry *dentry,
281			unsigned long *ino);
282
283static ssize_t sel_read_mls(struct file *filp, char __user *buf,
284				size_t count, loff_t *ppos)
285{
286	char tmpbuf[TMPBUFLEN];
287	ssize_t length;
288
289	length = scnprintf(tmpbuf, TMPBUFLEN, "%d",
290			   security_mls_enabled());
291	return simple_read_from_buffer(buf, count, ppos, tmpbuf, length);
292}
293
294static const struct file_operations sel_mls_ops = {
295	.read		= sel_read_mls,
296	.llseek		= generic_file_llseek,
297};
298
299static ssize_t sel_write_load(struct file *file, const char __user *buf,
300			      size_t count, loff_t *ppos)
301
302{
303	int ret;
304	ssize_t length;
305	void *data = NULL;
306
307	mutex_lock(&sel_mutex);
308
309	length = task_has_security(current, SECURITY__LOAD_POLICY);
310	if (length)
311		goto out;
312
313	if (*ppos != 0) {
314		/* No partial writes. */
315		length = -EINVAL;
316		goto out;
317	}
318
319	if ((count > 64 * 1024 * 1024)
320	    || (data = vmalloc(count)) == NULL) {
321		length = -ENOMEM;
322		goto out;
323	}
324
325	length = -EFAULT;
326	if (copy_from_user(data, buf, count) != 0)
327		goto out;
328
329	length = security_load_policy(data, count);
330	if (length)
331		goto out;
332
333	ret = sel_make_bools();
334	if (ret) {
335		length = ret;
336		goto out1;
337	}
338
339	ret = sel_make_classes();
340	if (ret) {
341		length = ret;
342		goto out1;
343	}
344
345	ret = sel_make_policycap();
346	if (ret)
347		length = ret;
348	else
349		length = count;
350
351out1:
352	audit_log(current->audit_context, GFP_KERNEL, AUDIT_MAC_POLICY_LOAD,
353		"policy loaded auid=%u ses=%u",
354		audit_get_loginuid(current),
355		audit_get_sessionid(current));
356out:
357	mutex_unlock(&sel_mutex);
358	vfree(data);
359	return length;
360}
361
362static const struct file_operations sel_load_ops = {
363	.write		= sel_write_load,
364	.llseek		= generic_file_llseek,
365};
366
367static ssize_t sel_write_context(struct file *file, char *buf, size_t size)
368{
369	char *canon;
370	u32 sid, len;
371	ssize_t length;
372
373	length = task_has_security(current, SECURITY__CHECK_CONTEXT);
374	if (length)
375		return length;
376
377	length = security_context_to_sid(buf, size, &sid);
378	if (length < 0)
379		return length;
380
381	length = security_sid_to_context(sid, &canon, &len);
382	if (length < 0)
383		return length;
384
385	if (len > SIMPLE_TRANSACTION_LIMIT) {
386		printk(KERN_ERR "SELinux: %s:  context size (%u) exceeds "
387			"payload max\n", __func__, len);
388		length = -ERANGE;
389		goto out;
390	}
391
392	memcpy(buf, canon, len);
393	length = len;
394out:
395	kfree(canon);
396	return length;
397}
398
399static ssize_t sel_read_checkreqprot(struct file *filp, char __user *buf,
400				     size_t count, loff_t *ppos)
401{
402	char tmpbuf[TMPBUFLEN];
403	ssize_t length;
404
405	length = scnprintf(tmpbuf, TMPBUFLEN, "%u", selinux_checkreqprot);
406	return simple_read_from_buffer(buf, count, ppos, tmpbuf, length);
407}
408
409static ssize_t sel_write_checkreqprot(struct file *file, const char __user *buf,
410				      size_t count, loff_t *ppos)
411{
412	char *page;
413	ssize_t length;
414	unsigned int new_value;
415
416	length = task_has_security(current, SECURITY__SETCHECKREQPROT);
417	if (length)
418		return length;
419
420	if (count >= PAGE_SIZE)
421		return -ENOMEM;
422	if (*ppos != 0) {
423		/* No partial writes. */
424		return -EINVAL;
425	}
426	page = (char *)get_zeroed_page(GFP_KERNEL);
427	if (!page)
428		return -ENOMEM;
429	length = -EFAULT;
430	if (copy_from_user(page, buf, count))
431		goto out;
432
433	length = -EINVAL;
434	if (sscanf(page, "%u", &new_value) != 1)
435		goto out;
436
437	selinux_checkreqprot = new_value ? 1 : 0;
438	length = count;
439out:
440	free_page((unsigned long) page);
441	return length;
442}
443static const struct file_operations sel_checkreqprot_ops = {
444	.read		= sel_read_checkreqprot,
445	.write		= sel_write_checkreqprot,
446	.llseek		= generic_file_llseek,
447};
448
449/*
450 * Remaining nodes use transaction based IO methods like nfsd/nfsctl.c
451 */
452static ssize_t sel_write_access(struct file *file, char *buf, size_t size);
453static ssize_t sel_write_create(struct file *file, char *buf, size_t size);
454static ssize_t sel_write_relabel(struct file *file, char *buf, size_t size);
455static ssize_t sel_write_user(struct file *file, char *buf, size_t size);
456static ssize_t sel_write_member(struct file *file, char *buf, size_t size);
457
458static ssize_t (*write_op[])(struct file *, char *, size_t) = {
459	[SEL_ACCESS] = sel_write_access,
460	[SEL_CREATE] = sel_write_create,
461	[SEL_RELABEL] = sel_write_relabel,
462	[SEL_USER] = sel_write_user,
463	[SEL_MEMBER] = sel_write_member,
464	[SEL_CONTEXT] = sel_write_context,
465};
466
467static ssize_t selinux_transaction_write(struct file *file, const char __user *buf, size_t size, loff_t *pos)
468{
469	ino_t ino = file->f_path.dentry->d_inode->i_ino;
470	char *data;
471	ssize_t rv;
472
473	if (ino >= ARRAY_SIZE(write_op) || !write_op[ino])
474		return -EINVAL;
475
476	data = simple_transaction_get(file, buf, size);
477	if (IS_ERR(data))
478		return PTR_ERR(data);
479
480	rv = write_op[ino](file, data, size);
481	if (rv > 0) {
482		simple_transaction_set(file, rv);
483		rv = size;
484	}
485	return rv;
486}
487
488static const struct file_operations transaction_ops = {
489	.write		= selinux_transaction_write,
490	.read		= simple_transaction_read,
491	.release	= simple_transaction_release,
492	.llseek		= generic_file_llseek,
493};
494
495/*
496 * payload - write methods
497 * If the method has a response, the response should be put in buf,
498 * and the length returned.  Otherwise return 0 or and -error.
499 */
500
501static ssize_t sel_write_access(struct file *file, char *buf, size_t size)
502{
503	char *scon, *tcon;
504	u32 ssid, tsid;
505	u16 tclass;
506	struct av_decision avd;
507	ssize_t length;
508
509	length = task_has_security(current, SECURITY__COMPUTE_AV);
510	if (length)
511		return length;
512
513	length = -ENOMEM;
514	scon = kzalloc(size + 1, GFP_KERNEL);
515	if (!scon)
516		return length;
517
518	tcon = kzalloc(size + 1, GFP_KERNEL);
519	if (!tcon)
520		goto out;
521
522	length = -EINVAL;
523	if (sscanf(buf, "%s %s %hu", scon, tcon, &tclass) != 3)
524		goto out2;
525
526	length = security_context_to_sid(scon, strlen(scon) + 1, &ssid);
527	if (length < 0)
528		goto out2;
529	length = security_context_to_sid(tcon, strlen(tcon) + 1, &tsid);
530	if (length < 0)
531		goto out2;
532
533	security_compute_av_user(ssid, tsid, tclass, &avd);
534
535	length = scnprintf(buf, SIMPLE_TRANSACTION_LIMIT,
536			  "%x %x %x %x %u %x",
537			  avd.allowed, 0xffffffff,
538			  avd.auditallow, avd.auditdeny,
539			  avd.seqno, avd.flags);
540out2:
541	kfree(tcon);
542out:
543	kfree(scon);
544	return length;
545}
546
547static ssize_t sel_write_create(struct file *file, char *buf, size_t size)
548{
549	char *scon, *tcon;
550	u32 ssid, tsid, newsid;
551	u16 tclass;
552	ssize_t length;
553	char *newcon;
554	u32 len;
555
556	length = task_has_security(current, SECURITY__COMPUTE_CREATE);
557	if (length)
558		return length;
559
560	length = -ENOMEM;
561	scon = kzalloc(size + 1, GFP_KERNEL);
562	if (!scon)
563		return length;
564
565	tcon = kzalloc(size + 1, GFP_KERNEL);
566	if (!tcon)
567		goto out;
568
569	length = -EINVAL;
570	if (sscanf(buf, "%s %s %hu", scon, tcon, &tclass) != 3)
571		goto out2;
572
573	length = security_context_to_sid(scon, strlen(scon) + 1, &ssid);
574	if (length < 0)
575		goto out2;
576	length = security_context_to_sid(tcon, strlen(tcon) + 1, &tsid);
577	if (length < 0)
578		goto out2;
579
580	length = security_transition_sid_user(ssid, tsid, tclass, &newsid);
581	if (length < 0)
582		goto out2;
583
584	length = security_sid_to_context(newsid, &newcon, &len);
585	if (length < 0)
586		goto out2;
587
588	if (len > SIMPLE_TRANSACTION_LIMIT) {
589		printk(KERN_ERR "SELinux: %s:  context size (%u) exceeds "
590			"payload max\n", __func__, len);
591		length = -ERANGE;
592		goto out3;
593	}
594
595	memcpy(buf, newcon, len);
596	length = len;
597out3:
598	kfree(newcon);
599out2:
600	kfree(tcon);
601out:
602	kfree(scon);
603	return length;
604}
605
606static ssize_t sel_write_relabel(struct file *file, char *buf, size_t size)
607{
608	char *scon, *tcon;
609	u32 ssid, tsid, newsid;
610	u16 tclass;
611	ssize_t length;
612	char *newcon;
613	u32 len;
614
615	length = task_has_security(current, SECURITY__COMPUTE_RELABEL);
616	if (length)
617		return length;
618
619	length = -ENOMEM;
620	scon = kzalloc(size + 1, GFP_KERNEL);
621	if (!scon)
622		return length;
623
624	tcon = kzalloc(size + 1, GFP_KERNEL);
625	if (!tcon)
626		goto out;
627
628	length = -EINVAL;
629	if (sscanf(buf, "%s %s %hu", scon, tcon, &tclass) != 3)
630		goto out2;
631
632	length = security_context_to_sid(scon, strlen(scon) + 1, &ssid);
633	if (length < 0)
634		goto out2;
635	length = security_context_to_sid(tcon, strlen(tcon) + 1, &tsid);
636	if (length < 0)
637		goto out2;
638
639	length = security_change_sid(ssid, tsid, tclass, &newsid);
640	if (length < 0)
641		goto out2;
642
643	length = security_sid_to_context(newsid, &newcon, &len);
644	if (length < 0)
645		goto out2;
646
647	if (len > SIMPLE_TRANSACTION_LIMIT) {
648		length = -ERANGE;
649		goto out3;
650	}
651
652	memcpy(buf, newcon, len);
653	length = len;
654out3:
655	kfree(newcon);
656out2:
657	kfree(tcon);
658out:
659	kfree(scon);
660	return length;
661}
662
663static ssize_t sel_write_user(struct file *file, char *buf, size_t size)
664{
665	char *con, *user, *ptr;
666	u32 sid, *sids;
667	ssize_t length;
668	char *newcon;
669	int i, rc;
670	u32 len, nsids;
671
672	length = task_has_security(current, SECURITY__COMPUTE_USER);
673	if (length)
674		return length;
675
676	length = -ENOMEM;
677	con = kzalloc(size + 1, GFP_KERNEL);
678	if (!con)
679		return length;
680
681	user = kzalloc(size + 1, GFP_KERNEL);
682	if (!user)
683		goto out;
684
685	length = -EINVAL;
686	if (sscanf(buf, "%s %s", con, user) != 2)
687		goto out2;
688
689	length = security_context_to_sid(con, strlen(con) + 1, &sid);
690	if (length < 0)
691		goto out2;
692
693	length = security_get_user_sids(sid, user, &sids, &nsids);
694	if (length < 0)
695		goto out2;
696
697	length = sprintf(buf, "%u", nsids) + 1;
698	ptr = buf + length;
699	for (i = 0; i < nsids; i++) {
700		rc = security_sid_to_context(sids[i], &newcon, &len);
701		if (rc) {
702			length = rc;
703			goto out3;
704		}
705		if ((length + len) >= SIMPLE_TRANSACTION_LIMIT) {
706			kfree(newcon);
707			length = -ERANGE;
708			goto out3;
709		}
710		memcpy(ptr, newcon, len);
711		kfree(newcon);
712		ptr += len;
713		length += len;
714	}
715out3:
716	kfree(sids);
717out2:
718	kfree(user);
719out:
720	kfree(con);
721	return length;
722}
723
724static ssize_t sel_write_member(struct file *file, char *buf, size_t size)
725{
726	char *scon, *tcon;
727	u32 ssid, tsid, newsid;
728	u16 tclass;
729	ssize_t length;
730	char *newcon;
731	u32 len;
732
733	length = task_has_security(current, SECURITY__COMPUTE_MEMBER);
734	if (length)
735		return length;
736
737	length = -ENOMEM;
738	scon = kzalloc(size + 1, GFP_KERNEL);
739	if (!scon)
740		return length;
741
742	tcon = kzalloc(size + 1, GFP_KERNEL);
743	if (!tcon)
744		goto out;
745
746	length = -EINVAL;
747	if (sscanf(buf, "%s %s %hu", scon, tcon, &tclass) != 3)
748		goto out2;
749
750	length = security_context_to_sid(scon, strlen(scon) + 1, &ssid);
751	if (length < 0)
752		goto out2;
753	length = security_context_to_sid(tcon, strlen(tcon) + 1, &tsid);
754	if (length < 0)
755		goto out2;
756
757	length = security_member_sid(ssid, tsid, tclass, &newsid);
758	if (length < 0)
759		goto out2;
760
761	length = security_sid_to_context(newsid, &newcon, &len);
762	if (length < 0)
763		goto out2;
764
765	if (len > SIMPLE_TRANSACTION_LIMIT) {
766		printk(KERN_ERR "SELinux: %s:  context size (%u) exceeds "
767			"payload max\n", __func__, len);
768		length = -ERANGE;
769		goto out3;
770	}
771
772	memcpy(buf, newcon, len);
773	length = len;
774out3:
775	kfree(newcon);
776out2:
777	kfree(tcon);
778out:
779	kfree(scon);
780	return length;
781}
782
783static struct inode *sel_make_inode(struct super_block *sb, int mode)
784{
785	struct inode *ret = new_inode(sb);
786
787	if (ret) {
788		ret->i_mode = mode;
789		ret->i_atime = ret->i_mtime = ret->i_ctime = CURRENT_TIME;
790	}
791	return ret;
792}
793
794static ssize_t sel_read_bool(struct file *filep, char __user *buf,
795			     size_t count, loff_t *ppos)
796{
797	char *page = NULL;
798	ssize_t length;
799	ssize_t ret;
800	int cur_enforcing;
801	struct inode *inode = filep->f_path.dentry->d_inode;
802	unsigned index = inode->i_ino & SEL_INO_MASK;
803	const char *name = filep->f_path.dentry->d_name.name;
804
805	mutex_lock(&sel_mutex);
806
807	if (index >= bool_num || strcmp(name, bool_pending_names[index])) {
808		ret = -EINVAL;
809		goto out;
810	}
811
812	page = (char *)get_zeroed_page(GFP_KERNEL);
813	if (!page) {
814		ret = -ENOMEM;
815		goto out;
816	}
817
818	cur_enforcing = security_get_bool_value(index);
819	if (cur_enforcing < 0) {
820		ret = cur_enforcing;
821		goto out;
822	}
823	length = scnprintf(page, PAGE_SIZE, "%d %d", cur_enforcing,
824			  bool_pending_values[index]);
825	ret = simple_read_from_buffer(buf, count, ppos, page, length);
826out:
827	mutex_unlock(&sel_mutex);
828	if (page)
829		free_page((unsigned long)page);
830	return ret;
831}
832
833static ssize_t sel_write_bool(struct file *filep, const char __user *buf,
834			      size_t count, loff_t *ppos)
835{
836	char *page = NULL;
837	ssize_t length;
838	int new_value;
839	struct inode *inode = filep->f_path.dentry->d_inode;
840	unsigned index = inode->i_ino & SEL_INO_MASK;
841	const char *name = filep->f_path.dentry->d_name.name;
842
843	mutex_lock(&sel_mutex);
844
845	length = task_has_security(current, SECURITY__SETBOOL);
846	if (length)
847		goto out;
848
849	if (index >= bool_num || strcmp(name, bool_pending_names[index])) {
850		length = -EINVAL;
851		goto out;
852	}
853
854	if (count >= PAGE_SIZE) {
855		length = -ENOMEM;
856		goto out;
857	}
858
859	if (*ppos != 0) {
860		/* No partial writes. */
861		length = -EINVAL;
862		goto out;
863	}
864	page = (char *)get_zeroed_page(GFP_KERNEL);
865	if (!page) {
866		length = -ENOMEM;
867		goto out;
868	}
869
870	length = -EFAULT;
871	if (copy_from_user(page, buf, count))
872		goto out;
873
874	length = -EINVAL;
875	if (sscanf(page, "%d", &new_value) != 1)
876		goto out;
877
878	if (new_value)
879		new_value = 1;
880
881	bool_pending_values[index] = new_value;
882	length = count;
883
884out:
885	mutex_unlock(&sel_mutex);
886	if (page)
887		free_page((unsigned long) page);
888	return length;
889}
890
891static const struct file_operations sel_bool_ops = {
892	.read		= sel_read_bool,
893	.write		= sel_write_bool,
894	.llseek		= generic_file_llseek,
895};
896
897static ssize_t sel_commit_bools_write(struct file *filep,
898				      const char __user *buf,
899				      size_t count, loff_t *ppos)
900{
901	char *page = NULL;
902	ssize_t length;
903	int new_value;
904
905	mutex_lock(&sel_mutex);
906
907	length = task_has_security(current, SECURITY__SETBOOL);
908	if (length)
909		goto out;
910
911	if (count >= PAGE_SIZE) {
912		length = -ENOMEM;
913		goto out;
914	}
915	if (*ppos != 0) {
916		/* No partial writes. */
917		goto out;
918	}
919	page = (char *)get_zeroed_page(GFP_KERNEL);
920	if (!page) {
921		length = -ENOMEM;
922		goto out;
923	}
924
925	length = -EFAULT;
926	if (copy_from_user(page, buf, count))
927		goto out;
928
929	length = -EINVAL;
930	if (sscanf(page, "%d", &new_value) != 1)
931		goto out;
932
933	if (new_value && bool_pending_values)
934		security_set_bools(bool_num, bool_pending_values);
935
936	length = count;
937
938out:
939	mutex_unlock(&sel_mutex);
940	if (page)
941		free_page((unsigned long) page);
942	return length;
943}
944
945static const struct file_operations sel_commit_bools_ops = {
946	.write		= sel_commit_bools_write,
947	.llseek		= generic_file_llseek,
948};
949
950static void sel_remove_entries(struct dentry *de)
951{
952	struct list_head *node;
953
954	spin_lock(&dcache_lock);
955	node = de->d_subdirs.next;
956	while (node != &de->d_subdirs) {
957		struct dentry *d = list_entry(node, struct dentry, d_u.d_child);
958		list_del_init(node);
959
960		if (d->d_inode) {
961			d = dget_locked(d);
962			spin_unlock(&dcache_lock);
963			d_delete(d);
964			simple_unlink(de->d_inode, d);
965			dput(d);
966			spin_lock(&dcache_lock);
967		}
968		node = de->d_subdirs.next;
969	}
970
971	spin_unlock(&dcache_lock);
972}
973
974#define BOOL_DIR_NAME "booleans"
975
976static int sel_make_bools(void)
977{
978	int i, ret = 0;
979	ssize_t len;
980	struct dentry *dentry = NULL;
981	struct dentry *dir = bool_dir;
982	struct inode *inode = NULL;
983	struct inode_security_struct *isec;
984	char **names = NULL, *page;
985	int num;
986	int *values = NULL;
987	u32 sid;
988
989	/* remove any existing files */
990	for (i = 0; i < bool_num; i++)
991		kfree(bool_pending_names[i]);
992	kfree(bool_pending_names);
993	kfree(bool_pending_values);
994	bool_pending_names = NULL;
995	bool_pending_values = NULL;
996
997	sel_remove_entries(dir);
998
999	page = (char *)get_zeroed_page(GFP_KERNEL);
1000	if (!page)
1001		return -ENOMEM;
1002
1003	ret = security_get_bools(&num, &names, &values);
1004	if (ret != 0)
1005		goto out;
1006
1007	for (i = 0; i < num; i++) {
1008		dentry = d_alloc_name(dir, names[i]);
1009		if (!dentry) {
1010			ret = -ENOMEM;
1011			goto err;
1012		}
1013		inode = sel_make_inode(dir->d_sb, S_IFREG | S_IRUGO | S_IWUSR);
1014		if (!inode) {
1015			ret = -ENOMEM;
1016			goto err;
1017		}
1018
1019		len = snprintf(page, PAGE_SIZE, "/%s/%s", BOOL_DIR_NAME, names[i]);
1020		if (len < 0) {
1021			ret = -EINVAL;
1022			goto err;
1023		} else if (len >= PAGE_SIZE) {
1024			ret = -ENAMETOOLONG;
1025			goto err;
1026		}
1027		isec = (struct inode_security_struct *)inode->i_security;
1028		ret = security_genfs_sid("selinuxfs", page, SECCLASS_FILE, &sid);
1029		if (ret)
1030			goto err;
1031		isec->sid = sid;
1032		isec->initialized = 1;
1033		inode->i_fop = &sel_bool_ops;
1034		inode->i_ino = i|SEL_BOOL_INO_OFFSET;
1035		d_add(dentry, inode);
1036	}
1037	bool_num = num;
1038	bool_pending_names = names;
1039	bool_pending_values = values;
1040out:
1041	free_page((unsigned long)page);
1042	return ret;
1043err:
1044	if (names) {
1045		for (i = 0; i < num; i++)
1046			kfree(names[i]);
1047		kfree(names);
1048	}
1049	kfree(values);
1050	sel_remove_entries(dir);
1051	ret = -ENOMEM;
1052	goto out;
1053}
1054
1055#define NULL_FILE_NAME "null"
1056
1057struct dentry *selinux_null;
1058
1059static ssize_t sel_read_avc_cache_threshold(struct file *filp, char __user *buf,
1060					    size_t count, loff_t *ppos)
1061{
1062	char tmpbuf[TMPBUFLEN];
1063	ssize_t length;
1064
1065	length = scnprintf(tmpbuf, TMPBUFLEN, "%u", avc_cache_threshold);
1066	return simple_read_from_buffer(buf, count, ppos, tmpbuf, length);
1067}
1068
1069static ssize_t sel_write_avc_cache_threshold(struct file *file,
1070					     const char __user *buf,
1071					     size_t count, loff_t *ppos)
1072
1073{
1074	char *page;
1075	ssize_t ret;
1076	int new_value;
1077
1078	if (count >= PAGE_SIZE) {
1079		ret = -ENOMEM;
1080		goto out;
1081	}
1082
1083	if (*ppos != 0) {
1084		/* No partial writes. */
1085		ret = -EINVAL;
1086		goto out;
1087	}
1088
1089	page = (char *)get_zeroed_page(GFP_KERNEL);
1090	if (!page) {
1091		ret = -ENOMEM;
1092		goto out;
1093	}
1094
1095	if (copy_from_user(page, buf, count)) {
1096		ret = -EFAULT;
1097		goto out_free;
1098	}
1099
1100	if (sscanf(page, "%u", &new_value) != 1) {
1101		ret = -EINVAL;
1102		goto out;
1103	}
1104
1105	if (new_value != avc_cache_threshold) {
1106		ret = task_has_security(current, SECURITY__SETSECPARAM);
1107		if (ret)
1108			goto out_free;
1109		avc_cache_threshold = new_value;
1110	}
1111	ret = count;
1112out_free:
1113	free_page((unsigned long)page);
1114out:
1115	return ret;
1116}
1117
1118static ssize_t sel_read_avc_hash_stats(struct file *filp, char __user *buf,
1119				       size_t count, loff_t *ppos)
1120{
1121	char *page;
1122	ssize_t ret = 0;
1123
1124	page = (char *)__get_free_page(GFP_KERNEL);
1125	if (!page) {
1126		ret = -ENOMEM;
1127		goto out;
1128	}
1129	ret = avc_get_hash_stats(page);
1130	if (ret >= 0)
1131		ret = simple_read_from_buffer(buf, count, ppos, page, ret);
1132	free_page((unsigned long)page);
1133out:
1134	return ret;
1135}
1136
1137static const struct file_operations sel_avc_cache_threshold_ops = {
1138	.read		= sel_read_avc_cache_threshold,
1139	.write		= sel_write_avc_cache_threshold,
1140	.llseek		= generic_file_llseek,
1141};
1142
1143static const struct file_operations sel_avc_hash_stats_ops = {
1144	.read		= sel_read_avc_hash_stats,
1145	.llseek		= generic_file_llseek,
1146};
1147
1148#ifdef CONFIG_SECURITY_SELINUX_AVC_STATS
1149static struct avc_cache_stats *sel_avc_get_stat_idx(loff_t *idx)
1150{
1151	int cpu;
1152
1153	for (cpu = *idx; cpu < nr_cpu_ids; ++cpu) {
1154		if (!cpu_possible(cpu))
1155			continue;
1156		*idx = cpu + 1;
1157		return &per_cpu(avc_cache_stats, cpu);
1158	}
1159	return NULL;
1160}
1161
1162static void *sel_avc_stats_seq_start(struct seq_file *seq, loff_t *pos)
1163{
1164	loff_t n = *pos - 1;
1165
1166	if (*pos == 0)
1167		return SEQ_START_TOKEN;
1168
1169	return sel_avc_get_stat_idx(&n);
1170}
1171
1172static void *sel_avc_stats_seq_next(struct seq_file *seq, void *v, loff_t *pos)
1173{
1174	return sel_avc_get_stat_idx(pos);
1175}
1176
1177static int sel_avc_stats_seq_show(struct seq_file *seq, void *v)
1178{
1179	struct avc_cache_stats *st = v;
1180
1181	if (v == SEQ_START_TOKEN)
1182		seq_printf(seq, "lookups hits misses allocations reclaims "
1183			   "frees\n");
1184	else
1185		seq_printf(seq, "%u %u %u %u %u %u\n", st->lookups,
1186			   st->hits, st->misses, st->allocations,
1187			   st->reclaims, st->frees);
1188	return 0;
1189}
1190
1191static void sel_avc_stats_seq_stop(struct seq_file *seq, void *v)
1192{ }
1193
1194static const struct seq_operations sel_avc_cache_stats_seq_ops = {
1195	.start		= sel_avc_stats_seq_start,
1196	.next		= sel_avc_stats_seq_next,
1197	.show		= sel_avc_stats_seq_show,
1198	.stop		= sel_avc_stats_seq_stop,
1199};
1200
1201static int sel_open_avc_cache_stats(struct inode *inode, struct file *file)
1202{
1203	return seq_open(file, &sel_avc_cache_stats_seq_ops);
1204}
1205
1206static const struct file_operations sel_avc_cache_stats_ops = {
1207	.open		= sel_open_avc_cache_stats,
1208	.read		= seq_read,
1209	.llseek		= seq_lseek,
1210	.release	= seq_release,
1211};
1212#endif
1213
1214static int sel_make_avc_files(struct dentry *dir)
1215{
1216	int i, ret = 0;
1217	static struct tree_descr files[] = {
1218		{ "cache_threshold",
1219		  &sel_avc_cache_threshold_ops, S_IRUGO|S_IWUSR },
1220		{ "hash_stats", &sel_avc_hash_stats_ops, S_IRUGO },
1221#ifdef CONFIG_SECURITY_SELINUX_AVC_STATS
1222		{ "cache_stats", &sel_avc_cache_stats_ops, S_IRUGO },
1223#endif
1224	};
1225
1226	for (i = 0; i < ARRAY_SIZE(files); i++) {
1227		struct inode *inode;
1228		struct dentry *dentry;
1229
1230		dentry = d_alloc_name(dir, files[i].name);
1231		if (!dentry) {
1232			ret = -ENOMEM;
1233			goto out;
1234		}
1235
1236		inode = sel_make_inode(dir->d_sb, S_IFREG|files[i].mode);
1237		if (!inode) {
1238			ret = -ENOMEM;
1239			goto out;
1240		}
1241		inode->i_fop = files[i].ops;
1242		inode->i_ino = ++sel_last_ino;
1243		d_add(dentry, inode);
1244	}
1245out:
1246	return ret;
1247}
1248
1249static ssize_t sel_read_initcon(struct file *file, char __user *buf,
1250				size_t count, loff_t *ppos)
1251{
1252	struct inode *inode;
1253	char *con;
1254	u32 sid, len;
1255	ssize_t ret;
1256
1257	inode = file->f_path.dentry->d_inode;
1258	sid = inode->i_ino&SEL_INO_MASK;
1259	ret = security_sid_to_context(sid, &con, &len);
1260	if (ret < 0)
1261		return ret;
1262
1263	ret = simple_read_from_buffer(buf, count, ppos, con, len);
1264	kfree(con);
1265	return ret;
1266}
1267
1268static const struct file_operations sel_initcon_ops = {
1269	.read		= sel_read_initcon,
1270	.llseek		= generic_file_llseek,
1271};
1272
1273static int sel_make_initcon_files(struct dentry *dir)
1274{
1275	int i, ret = 0;
1276
1277	for (i = 1; i <= SECINITSID_NUM; i++) {
1278		struct inode *inode;
1279		struct dentry *dentry;
1280		dentry = d_alloc_name(dir, security_get_initial_sid_context(i));
1281		if (!dentry) {
1282			ret = -ENOMEM;
1283			goto out;
1284		}
1285
1286		inode = sel_make_inode(dir->d_sb, S_IFREG|S_IRUGO);
1287		if (!inode) {
1288			ret = -ENOMEM;
1289			goto out;
1290		}
1291		inode->i_fop = &sel_initcon_ops;
1292		inode->i_ino = i|SEL_INITCON_INO_OFFSET;
1293		d_add(dentry, inode);
1294	}
1295out:
1296	return ret;
1297}
1298
1299static inline unsigned int sel_div(unsigned long a, unsigned long b)
1300{
1301	return a / b - (a % b < 0);
1302}
1303
1304static inline unsigned long sel_class_to_ino(u16 class)
1305{
1306	return (class * (SEL_VEC_MAX + 1)) | SEL_CLASS_INO_OFFSET;
1307}
1308
1309static inline u16 sel_ino_to_class(unsigned long ino)
1310{
1311	return sel_div(ino & SEL_INO_MASK, SEL_VEC_MAX + 1);
1312}
1313
1314static inline unsigned long sel_perm_to_ino(u16 class, u32 perm)
1315{
1316	return (class * (SEL_VEC_MAX + 1) + perm) | SEL_CLASS_INO_OFFSET;
1317}
1318
1319static inline u32 sel_ino_to_perm(unsigned long ino)
1320{
1321	return (ino & SEL_INO_MASK) % (SEL_VEC_MAX + 1);
1322}
1323
1324static ssize_t sel_read_class(struct file *file, char __user *buf,
1325				size_t count, loff_t *ppos)
1326{
1327	ssize_t rc, len;
1328	char *page;
1329	unsigned long ino = file->f_path.dentry->d_inode->i_ino;
1330
1331	page = (char *)__get_free_page(GFP_KERNEL);
1332	if (!page) {
1333		rc = -ENOMEM;
1334		goto out;
1335	}
1336
1337	len = snprintf(page, PAGE_SIZE, "%d", sel_ino_to_class(ino));
1338	rc = simple_read_from_buffer(buf, count, ppos, page, len);
1339	free_page((unsigned long)page);
1340out:
1341	return rc;
1342}
1343
1344static const struct file_operations sel_class_ops = {
1345	.read		= sel_read_class,
1346	.llseek		= generic_file_llseek,
1347};
1348
1349static ssize_t sel_read_perm(struct file *file, char __user *buf,
1350				size_t count, loff_t *ppos)
1351{
1352	ssize_t rc, len;
1353	char *page;
1354	unsigned long ino = file->f_path.dentry->d_inode->i_ino;
1355
1356	page = (char *)__get_free_page(GFP_KERNEL);
1357	if (!page) {
1358		rc = -ENOMEM;
1359		goto out;
1360	}
1361
1362	len = snprintf(page, PAGE_SIZE, "%d", sel_ino_to_perm(ino));
1363	rc = simple_read_from_buffer(buf, count, ppos, page, len);
1364	free_page((unsigned long)page);
1365out:
1366	return rc;
1367}
1368
1369static const struct file_operations sel_perm_ops = {
1370	.read		= sel_read_perm,
1371	.llseek		= generic_file_llseek,
1372};
1373
1374static ssize_t sel_read_policycap(struct file *file, char __user *buf,
1375				  size_t count, loff_t *ppos)
1376{
1377	int value;
1378	char tmpbuf[TMPBUFLEN];
1379	ssize_t length;
1380	unsigned long i_ino = file->f_path.dentry->d_inode->i_ino;
1381
1382	value = security_policycap_supported(i_ino & SEL_INO_MASK);
1383	length = scnprintf(tmpbuf, TMPBUFLEN, "%d", value);
1384
1385	return simple_read_from_buffer(buf, count, ppos, tmpbuf, length);
1386}
1387
1388static const struct file_operations sel_policycap_ops = {
1389	.read		= sel_read_policycap,
1390	.llseek		= generic_file_llseek,
1391};
1392
1393static int sel_make_perm_files(char *objclass, int classvalue,
1394				struct dentry *dir)
1395{
1396	int i, rc = 0, nperms;
1397	char **perms;
1398
1399	rc = security_get_permissions(objclass, &perms, &nperms);
1400	if (rc)
1401		goto out;
1402
1403	for (i = 0; i < nperms; i++) {
1404		struct inode *inode;
1405		struct dentry *dentry;
1406
1407		dentry = d_alloc_name(dir, perms[i]);
1408		if (!dentry) {
1409			rc = -ENOMEM;
1410			goto out1;
1411		}
1412
1413		inode = sel_make_inode(dir->d_sb, S_IFREG|S_IRUGO);
1414		if (!inode) {
1415			rc = -ENOMEM;
1416			goto out1;
1417		}
1418		inode->i_fop = &sel_perm_ops;
1419		/* i+1 since perm values are 1-indexed */
1420		inode->i_ino = sel_perm_to_ino(classvalue, i + 1);
1421		d_add(dentry, inode);
1422	}
1423
1424out1:
1425	for (i = 0; i < nperms; i++)
1426		kfree(perms[i]);
1427	kfree(perms);
1428out:
1429	return rc;
1430}
1431
1432static int sel_make_class_dir_entries(char *classname, int index,
1433					struct dentry *dir)
1434{
1435	struct dentry *dentry = NULL;
1436	struct inode *inode = NULL;
1437	int rc;
1438
1439	dentry = d_alloc_name(dir, "index");
1440	if (!dentry) {
1441		rc = -ENOMEM;
1442		goto out;
1443	}
1444
1445	inode = sel_make_inode(dir->d_sb, S_IFREG|S_IRUGO);
1446	if (!inode) {
1447		rc = -ENOMEM;
1448		goto out;
1449	}
1450
1451	inode->i_fop = &sel_class_ops;
1452	inode->i_ino = sel_class_to_ino(index);
1453	d_add(dentry, inode);
1454
1455	dentry = d_alloc_name(dir, "perms");
1456	if (!dentry) {
1457		rc = -ENOMEM;
1458		goto out;
1459	}
1460
1461	rc = sel_make_dir(dir->d_inode, dentry, &last_class_ino);
1462	if (rc)
1463		goto out;
1464
1465	rc = sel_make_perm_files(classname, index, dentry);
1466
1467out:
1468	return rc;
1469}
1470
1471static void sel_remove_classes(void)
1472{
1473	struct list_head *class_node;
1474
1475	list_for_each(class_node, &class_dir->d_subdirs) {
1476		struct dentry *class_subdir = list_entry(class_node,
1477					struct dentry, d_u.d_child);
1478		struct list_head *class_subdir_node;
1479
1480		list_for_each(class_subdir_node, &class_subdir->d_subdirs) {
1481			struct dentry *d = list_entry(class_subdir_node,
1482						struct dentry, d_u.d_child);
1483
1484			if (d->d_inode)
1485				if (d->d_inode->i_mode & S_IFDIR)
1486					sel_remove_entries(d);
1487		}
1488
1489		sel_remove_entries(class_subdir);
1490	}
1491
1492	sel_remove_entries(class_dir);
1493}
1494
1495static int sel_make_classes(void)
1496{
1497	int rc = 0, nclasses, i;
1498	char **classes;
1499
1500	/* delete any existing entries */
1501	sel_remove_classes();
1502
1503	rc = security_get_classes(&classes, &nclasses);
1504	if (rc < 0)
1505		goto out;
1506
1507	/* +2 since classes are 1-indexed */
1508	last_class_ino = sel_class_to_ino(nclasses + 2);
1509
1510	for (i = 0; i < nclasses; i++) {
1511		struct dentry *class_name_dir;
1512
1513		class_name_dir = d_alloc_name(class_dir, classes[i]);
1514		if (!class_name_dir) {
1515			rc = -ENOMEM;
1516			goto out1;
1517		}
1518
1519		rc = sel_make_dir(class_dir->d_inode, class_name_dir,
1520				&last_class_ino);
1521		if (rc)
1522			goto out1;
1523
1524		/* i+1 since class values are 1-indexed */
1525		rc = sel_make_class_dir_entries(classes[i], i + 1,
1526				class_name_dir);
1527		if (rc)
1528			goto out1;
1529	}
1530
1531out1:
1532	for (i = 0; i < nclasses; i++)
1533		kfree(classes[i]);
1534	kfree(classes);
1535out:
1536	return rc;
1537}
1538
1539static int sel_make_policycap(void)
1540{
1541	unsigned int iter;
1542	struct dentry *dentry = NULL;
1543	struct inode *inode = NULL;
1544
1545	sel_remove_entries(policycap_dir);
1546
1547	for (iter = 0; iter <= POLICYDB_CAPABILITY_MAX; iter++) {
1548		if (iter < ARRAY_SIZE(policycap_names))
1549			dentry = d_alloc_name(policycap_dir,
1550					      policycap_names[iter]);
1551		else
1552			dentry = d_alloc_name(policycap_dir, "unknown");
1553
1554		if (dentry == NULL)
1555			return -ENOMEM;
1556
1557		inode = sel_make_inode(policycap_dir->d_sb, S_IFREG | S_IRUGO);
1558		if (inode == NULL)
1559			return -ENOMEM;
1560
1561		inode->i_fop = &sel_policycap_ops;
1562		inode->i_ino = iter | SEL_POLICYCAP_INO_OFFSET;
1563		d_add(dentry, inode);
1564	}
1565
1566	return 0;
1567}
1568
1569static int sel_make_dir(struct inode *dir, struct dentry *dentry,
1570			unsigned long *ino)
1571{
1572	int ret = 0;
1573	struct inode *inode;
1574
1575	inode = sel_make_inode(dir->i_sb, S_IFDIR | S_IRUGO | S_IXUGO);
1576	if (!inode) {
1577		ret = -ENOMEM;
1578		goto out;
1579	}
1580	inode->i_op = &simple_dir_inode_operations;
1581	inode->i_fop = &simple_dir_operations;
1582	inode->i_ino = ++(*ino);
1583	/* directory inodes start off with i_nlink == 2 (for "." entry) */
1584	inc_nlink(inode);
1585	d_add(dentry, inode);
1586	/* bump link count on parent directory, too */
1587	inc_nlink(dir);
1588out:
1589	return ret;
1590}
1591
1592static int sel_fill_super(struct super_block *sb, void *data, int silent)
1593{
1594	int ret;
1595	struct dentry *dentry;
1596	struct inode *inode, *root_inode;
1597	struct inode_security_struct *isec;
1598
1599	static struct tree_descr selinux_files[] = {
1600		[SEL_LOAD] = {"load", &sel_load_ops, S_IRUSR|S_IWUSR},
1601		[SEL_ENFORCE] = {"enforce", &sel_enforce_ops, S_IRUGO|S_IWUSR},
1602		[SEL_CONTEXT] = {"context", &transaction_ops, S_IRUGO|S_IWUGO},
1603		[SEL_ACCESS] = {"access", &transaction_ops, S_IRUGO|S_IWUGO},
1604		[SEL_CREATE] = {"create", &transaction_ops, S_IRUGO|S_IWUGO},
1605		[SEL_RELABEL] = {"relabel", &transaction_ops, S_IRUGO|S_IWUGO},
1606		[SEL_USER] = {"user", &transaction_ops, S_IRUGO|S_IWUGO},
1607		[SEL_POLICYVERS] = {"policyvers", &sel_policyvers_ops, S_IRUGO},
1608		[SEL_COMMIT_BOOLS] = {"commit_pending_bools", &sel_commit_bools_ops, S_IWUSR},
1609		[SEL_MLS] = {"mls", &sel_mls_ops, S_IRUGO},
1610		[SEL_DISABLE] = {"disable", &sel_disable_ops, S_IWUSR},
1611		[SEL_MEMBER] = {"member", &transaction_ops, S_IRUGO|S_IWUGO},
1612		[SEL_CHECKREQPROT] = {"checkreqprot", &sel_checkreqprot_ops, S_IRUGO|S_IWUSR},
1613		[SEL_REJECT_UNKNOWN] = {"reject_unknown", &sel_handle_unknown_ops, S_IRUGO},
1614		[SEL_DENY_UNKNOWN] = {"deny_unknown", &sel_handle_unknown_ops, S_IRUGO},
1615		/* last one */ {""}
1616	};
1617	ret = simple_fill_super(sb, SELINUX_MAGIC, selinux_files);
1618	if (ret)
1619		goto err;
1620
1621	root_inode = sb->s_root->d_inode;
1622
1623	dentry = d_alloc_name(sb->s_root, BOOL_DIR_NAME);
1624	if (!dentry) {
1625		ret = -ENOMEM;
1626		goto err;
1627	}
1628
1629	ret = sel_make_dir(root_inode, dentry, &sel_last_ino);
1630	if (ret)
1631		goto err;
1632
1633	bool_dir = dentry;
1634
1635	dentry = d_alloc_name(sb->s_root, NULL_FILE_NAME);
1636	if (!dentry) {
1637		ret = -ENOMEM;
1638		goto err;
1639	}
1640
1641	inode = sel_make_inode(sb, S_IFCHR | S_IRUGO | S_IWUGO);
1642	if (!inode) {
1643		ret = -ENOMEM;
1644		goto err;
1645	}
1646	inode->i_ino = ++sel_last_ino;
1647	isec = (struct inode_security_struct *)inode->i_security;
1648	isec->sid = SECINITSID_DEVNULL;
1649	isec->sclass = SECCLASS_CHR_FILE;
1650	isec->initialized = 1;
1651
1652	init_special_inode(inode, S_IFCHR | S_IRUGO | S_IWUGO, MKDEV(MEM_MAJOR, 3));
1653	d_add(dentry, inode);
1654	selinux_null = dentry;
1655
1656	dentry = d_alloc_name(sb->s_root, "avc");
1657	if (!dentry) {
1658		ret = -ENOMEM;
1659		goto err;
1660	}
1661
1662	ret = sel_make_dir(root_inode, dentry, &sel_last_ino);
1663	if (ret)
1664		goto err;
1665
1666	ret = sel_make_avc_files(dentry);
1667	if (ret)
1668		goto err;
1669
1670	dentry = d_alloc_name(sb->s_root, "initial_contexts");
1671	if (!dentry) {
1672		ret = -ENOMEM;
1673		goto err;
1674	}
1675
1676	ret = sel_make_dir(root_inode, dentry, &sel_last_ino);
1677	if (ret)
1678		goto err;
1679
1680	ret = sel_make_initcon_files(dentry);
1681	if (ret)
1682		goto err;
1683
1684	dentry = d_alloc_name(sb->s_root, "class");
1685	if (!dentry) {
1686		ret = -ENOMEM;
1687		goto err;
1688	}
1689
1690	ret = sel_make_dir(root_inode, dentry, &sel_last_ino);
1691	if (ret)
1692		goto err;
1693
1694	class_dir = dentry;
1695
1696	dentry = d_alloc_name(sb->s_root, "policy_capabilities");
1697	if (!dentry) {
1698		ret = -ENOMEM;
1699		goto err;
1700	}
1701
1702	ret = sel_make_dir(root_inode, dentry, &sel_last_ino);
1703	if (ret)
1704		goto err;
1705
1706	policycap_dir = dentry;
1707
1708out:
1709	return ret;
1710err:
1711	printk(KERN_ERR "SELinux: %s:  failed while creating inodes\n",
1712		__func__);
1713	goto out;
1714}
1715
1716static int sel_get_sb(struct file_system_type *fs_type,
1717		      int flags, const char *dev_name, void *data,
1718		      struct vfsmount *mnt)
1719{
1720	return get_sb_single(fs_type, flags, data, sel_fill_super, mnt);
1721}
1722
1723static struct file_system_type sel_fs_type = {
1724	.name		= "selinuxfs",
1725	.get_sb		= sel_get_sb,
1726	.kill_sb	= kill_litter_super,
1727};
1728
1729struct vfsmount *selinuxfs_mount;
1730
1731static int __init init_sel_fs(void)
1732{
1733	int err;
1734
1735	if (!selinux_enabled)
1736		return 0;
1737	err = register_filesystem(&sel_fs_type);
1738	if (!err) {
1739		selinuxfs_mount = kern_mount(&sel_fs_type);
1740		if (IS_ERR(selinuxfs_mount)) {
1741			printk(KERN_ERR "selinuxfs:  could not mount!\n");
1742			err = PTR_ERR(selinuxfs_mount);
1743			selinuxfs_mount = NULL;
1744		}
1745	}
1746	return err;
1747}
1748
1749__initcall(init_sel_fs);
1750
1751#ifdef CONFIG_SECURITY_SELINUX_DISABLE
1752void exit_sel_fs(void)
1753{
1754	unregister_filesystem(&sel_fs_type);
1755}
1756#endif
1757