mac_partition.c revision 165469
1105828Srwatson/*-
2126097Srwatson * Copyright (c) 1999-2002 Robert N. M. Watson
3126097Srwatson * Copyright (c) 2001-2002 Networks Associates Technology, Inc.
4105828Srwatson * All rights reserved.
5105828Srwatson *
6105828Srwatson * This software was developed by Robert Watson for the TrustedBSD Project.
7105828Srwatson *
8106393Srwatson * This software was developed for the FreeBSD Project in part by Network
9106393Srwatson * Associates Laboratories, the Security Research Division of Network
10106393Srwatson * Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 ("CBOSS"),
11106393Srwatson * as part of the DARPA CHATS research program.
12105828Srwatson *
13105828Srwatson * Redistribution and use in source and binary forms, with or without
14105828Srwatson * modification, are permitted provided that the following conditions
15105828Srwatson * are met:
16105828Srwatson * 1. Redistributions of source code must retain the above copyright
17105828Srwatson *    notice, this list of conditions and the following disclaimer.
18105828Srwatson * 2. Redistributions in binary form must reproduce the above copyright
19105828Srwatson *    notice, this list of conditions and the following disclaimer in the
20105828Srwatson *    documentation and/or other materials provided with the distribution.
21105828Srwatson *
22105828Srwatson * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
23105828Srwatson * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
24105828Srwatson * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
25105828Srwatson * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
26105828Srwatson * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
27105828Srwatson * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
28105828Srwatson * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
29105828Srwatson * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
30105828Srwatson * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
31105828Srwatson * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
32105828Srwatson * SUCH DAMAGE.
33105828Srwatson *
34105828Srwatson * $FreeBSD: head/sys/security/mac_partition/mac_partition.c 165469 2006-12-22 23:34:47Z rwatson $
35105828Srwatson */
36105828Srwatson
37105828Srwatson/*
38105828Srwatson * Developed by the TrustedBSD Project.
39105828Srwatson * Experiment with a partition-like model.
40105828Srwatson */
41105828Srwatson
42105828Srwatson#include <sys/types.h>
43105828Srwatson#include <sys/param.h>
44105828Srwatson#include <sys/conf.h>
45105828Srwatson#include <sys/kernel.h>
46105828Srwatson#include <sys/mac.h>
47105828Srwatson#include <sys/mount.h>
48164033Srwatson#include <sys/priv.h>
49105828Srwatson#include <sys/proc.h>
50116701Srwatson#include <sys/sbuf.h>
51105828Srwatson#include <sys/systm.h>
52105828Srwatson#include <sys/sysproto.h>
53105828Srwatson#include <sys/sysent.h>
54105828Srwatson#include <sys/vnode.h>
55105828Srwatson#include <sys/file.h>
56105828Srwatson#include <sys/socket.h>
57105828Srwatson#include <sys/socketvar.h>
58150340Sphk#include <sys/sx.h>
59105828Srwatson#include <sys/sysctl.h>
60105828Srwatson
61105828Srwatson#include <fs/devfs/devfs.h>
62105828Srwatson
63105828Srwatson#include <net/bpfdesc.h>
64105828Srwatson#include <net/if.h>
65105828Srwatson#include <net/if_types.h>
66105828Srwatson#include <net/if_var.h>
67105828Srwatson
68105828Srwatson#include <vm/vm.h>
69105828Srwatson
70165469Srwatson#include <security/mac/mac_policy.h>
71105828Srwatson#include <security/mac_partition/mac_partition.h>
72105828Srwatson
73105828SrwatsonSYSCTL_DECL(_security_mac);
74105828Srwatson
75105828SrwatsonSYSCTL_NODE(_security_mac, OID_AUTO, partition, CTLFLAG_RW, 0,
76105828Srwatson    "TrustedBSD mac_partition policy controls");
77105828Srwatson
78105828Srwatsonstatic int	mac_partition_enabled = 1;
79105828SrwatsonSYSCTL_INT(_security_mac_partition, OID_AUTO, enabled, CTLFLAG_RW,
80105828Srwatson    &mac_partition_enabled, 0, "Enforce partition policy");
81105828Srwatson
82105828Srwatsonstatic int	partition_slot;
83105828Srwatson#define	SLOT(l)	(LABEL_TO_SLOT((l), partition_slot).l_long)
84105828Srwatson
85105828Srwatsonstatic void
86105828Srwatsonmac_partition_init(struct mac_policy_conf *conf)
87105828Srwatson{
88105828Srwatson
89105828Srwatson}
90105828Srwatson
91105828Srwatsonstatic void
92105828Srwatsonmac_partition_init_label(struct label *label)
93105828Srwatson{
94105828Srwatson
95105828Srwatson	SLOT(label) = 0;
96105828Srwatson}
97105828Srwatson
98105828Srwatsonstatic void
99105828Srwatsonmac_partition_destroy_label(struct label *label)
100105828Srwatson{
101105828Srwatson
102105828Srwatson	SLOT(label) = 0;
103105828Srwatson}
104105828Srwatson
105123173Srwatsonstatic void
106123173Srwatsonmac_partition_copy_label(struct label *src, struct label *dest)
107123173Srwatson{
108123173Srwatson
109123173Srwatson	SLOT(dest) = SLOT(src);
110123173Srwatson}
111123173Srwatson
112105828Srwatsonstatic int
113105828Srwatsonmac_partition_externalize_label(struct label *label, char *element_name,
114116701Srwatson    struct sbuf *sb, int *claimed)
115105828Srwatson{
116105828Srwatson
117105828Srwatson	if (strcmp(MAC_PARTITION_LABEL_NAME, element_name) != 0)
118105828Srwatson		return (0);
119105828Srwatson
120105828Srwatson	(*claimed)++;
121116701Srwatson
122116701Srwatson	if (sbuf_printf(sb, "%ld", SLOT(label)) == -1)
123116701Srwatson		return (EINVAL);
124116701Srwatson	else
125116701Srwatson		return (0);
126105828Srwatson}
127105828Srwatson
128105828Srwatsonstatic int
129105828Srwatsonmac_partition_internalize_label(struct label *label, char *element_name,
130105828Srwatson    char *element_data, int *claimed)
131105828Srwatson{
132105828Srwatson
133105828Srwatson	if (strcmp(MAC_PARTITION_LABEL_NAME, element_name) != 0)
134105828Srwatson		return (0);
135105828Srwatson
136105828Srwatson	(*claimed)++;
137105828Srwatson	SLOT(label) = strtol(element_data, NULL, 10);
138105828Srwatson	return (0);
139105828Srwatson}
140105828Srwatson
141105828Srwatsonstatic void
142105828Srwatsonmac_partition_create_proc0(struct ucred *cred)
143105828Srwatson{
144105828Srwatson
145122524Srwatson	SLOT(cred->cr_label) = 0;
146105828Srwatson}
147105828Srwatson
148105828Srwatsonstatic void
149105828Srwatsonmac_partition_create_proc1(struct ucred *cred)
150105828Srwatson{
151105828Srwatson
152122524Srwatson	SLOT(cred->cr_label) = 0;
153105828Srwatson}
154105828Srwatson
155105828Srwatsonstatic void
156105828Srwatsonmac_partition_relabel_cred(struct ucred *cred, struct label *newlabel)
157105828Srwatson{
158105828Srwatson
159105828Srwatson	if (SLOT(newlabel) != 0)
160122524Srwatson		SLOT(cred->cr_label) = SLOT(newlabel);
161105828Srwatson}
162105828Srwatson
163105828Srwatsonstatic int
164105828Srwatsonlabel_on_label(struct label *subject, struct label *object)
165105828Srwatson{
166105828Srwatson
167105828Srwatson	if (mac_partition_enabled == 0)
168105828Srwatson		return (0);
169105828Srwatson
170105828Srwatson	if (SLOT(subject) == 0)
171105828Srwatson		return (0);
172105828Srwatson
173105828Srwatson	if (SLOT(subject) == SLOT(object))
174105828Srwatson		return (0);
175105828Srwatson
176105828Srwatson	return (EPERM);
177105828Srwatson}
178105828Srwatson
179105828Srwatsonstatic int
180105828Srwatsonmac_partition_check_cred_relabel(struct ucred *cred, struct label *newlabel)
181105828Srwatson{
182105828Srwatson	int error;
183105828Srwatson
184105828Srwatson	error = 0;
185105828Srwatson
186105828Srwatson	/* Treat "0" as a no-op request. */
187105828Srwatson	if (SLOT(newlabel) != 0) {
188105828Srwatson		/*
189106367Srwatson		 * Require BSD privilege in order to change the partition.
190106367Srwatson		 * Originally we also required that the process not be
191106367Srwatson		 * in a partition in the first place, but this didn't
192106367Srwatson		 * interact well with sendmail.
193105828Srwatson		 */
194164033Srwatson		error = priv_check_cred(cred, PRIV_MAC_PARTITION, 0);
195105828Srwatson	}
196105828Srwatson
197105828Srwatson	return (error);
198105828Srwatson}
199105828Srwatson
200105828Srwatsonstatic int
201105828Srwatsonmac_partition_check_cred_visible(struct ucred *u1, struct ucred *u2)
202105828Srwatson{
203105828Srwatson	int error;
204105828Srwatson
205122524Srwatson	error = label_on_label(u1->cr_label, u2->cr_label);
206105828Srwatson
207105828Srwatson	return (error == 0 ? 0 : ESRCH);
208105828Srwatson}
209105828Srwatson
210105828Srwatsonstatic int
211105828Srwatsonmac_partition_check_proc_debug(struct ucred *cred, struct proc *proc)
212105828Srwatson{
213105828Srwatson	int error;
214105828Srwatson
215122524Srwatson	error = label_on_label(cred->cr_label, proc->p_ucred->cr_label);
216105828Srwatson
217105828Srwatson	return (error ? ESRCH : 0);
218105828Srwatson}
219105828Srwatson
220105828Srwatsonstatic int
221105828Srwatsonmac_partition_check_proc_sched(struct ucred *cred, struct proc *proc)
222105828Srwatson{
223105828Srwatson	int error;
224105828Srwatson
225122524Srwatson	error = label_on_label(cred->cr_label, proc->p_ucred->cr_label);
226105828Srwatson
227105828Srwatson	return (error ? ESRCH : 0);
228105828Srwatson}
229105828Srwatson
230105828Srwatsonstatic int
231105828Srwatsonmac_partition_check_proc_signal(struct ucred *cred, struct proc *proc,
232105828Srwatson    int signum)
233105828Srwatson{
234105828Srwatson	int error;
235105828Srwatson
236122524Srwatson	error = label_on_label(cred->cr_label, proc->p_ucred->cr_label);
237105828Srwatson
238105828Srwatson	return (error ? ESRCH : 0);
239105828Srwatson}
240105828Srwatson
241105828Srwatsonstatic int
242105828Srwatsonmac_partition_check_socket_visible(struct ucred *cred, struct socket *socket,
243105828Srwatson    struct label *socketlabel)
244105828Srwatson{
245105828Srwatson	int error;
246105828Srwatson
247122524Srwatson	error = label_on_label(cred->cr_label, socketlabel);
248105828Srwatson
249105828Srwatson	return (error ? ENOENT : 0);
250105828Srwatson}
251105828Srwatson
252106648Srwatsonstatic int
253106648Srwatsonmac_partition_check_vnode_exec(struct ucred *cred, struct vnode *vp,
254106648Srwatson    struct label *label, struct image_params *imgp, struct label *execlabel)
255106648Srwatson{
256106648Srwatson
257106648Srwatson	if (execlabel != NULL) {
258106648Srwatson		/*
259106648Srwatson		 * We currently don't permit labels to be changed at
260106648Srwatson		 * exec-time as part of the partition model, so disallow
261106648Srwatson		 * non-NULL partition label changes in execlabel.
262106648Srwatson		 */
263106648Srwatson		if (SLOT(execlabel) != 0)
264106648Srwatson			return (EINVAL);
265106648Srwatson	}
266106648Srwatson
267106648Srwatson	return (0);
268106648Srwatson}
269106648Srwatson
270106217Srwatsonstatic struct mac_policy_ops mac_partition_ops =
271105828Srwatson{
272106217Srwatson	.mpo_init = mac_partition_init,
273106217Srwatson	.mpo_init_cred_label = mac_partition_init_label,
274106217Srwatson	.mpo_destroy_cred_label = mac_partition_destroy_label,
275123173Srwatson	.mpo_copy_cred_label = mac_partition_copy_label,
276106217Srwatson	.mpo_externalize_cred_label = mac_partition_externalize_label,
277106217Srwatson	.mpo_internalize_cred_label = mac_partition_internalize_label,
278106217Srwatson	.mpo_create_proc0 = mac_partition_create_proc0,
279106217Srwatson	.mpo_create_proc1 = mac_partition_create_proc1,
280106217Srwatson	.mpo_relabel_cred = mac_partition_relabel_cred,
281106217Srwatson	.mpo_check_cred_relabel = mac_partition_check_cred_relabel,
282106217Srwatson	.mpo_check_cred_visible = mac_partition_check_cred_visible,
283106217Srwatson	.mpo_check_proc_debug = mac_partition_check_proc_debug,
284106217Srwatson	.mpo_check_proc_sched = mac_partition_check_proc_sched,
285106217Srwatson	.mpo_check_proc_signal = mac_partition_check_proc_signal,
286106217Srwatson	.mpo_check_socket_visible = mac_partition_check_socket_visible,
287106648Srwatson	.mpo_check_vnode_exec = mac_partition_check_vnode_exec,
288105828Srwatson};
289105828Srwatson
290112717SrwatsonMAC_POLICY_SET(&mac_partition_ops, mac_partition, "TrustedBSD MAC/Partition",
291112717Srwatson    MPC_LOADTIME_FLAG_UNLOADOK, &partition_slot);
292