xref: /openbmc/linux/security/apparmor/net.c (revision b78412b8)
1 /*
2  * AppArmor security module
3  *
4  * This file contains AppArmor network mediation
5  *
6  * Copyright (C) 1998-2008 Novell/SUSE
7  * Copyright 2009-2017 Canonical Ltd.
8  *
9  * This program is free software; you can redistribute it and/or
10  * modify it under the terms of the GNU General Public License as
11  * published by the Free Software Foundation, version 2 of the
12  * License.
13  */
14 
15 #include "include/apparmor.h"
16 #include "include/audit.h"
17 #include "include/context.h"
18 #include "include/label.h"
19 #include "include/net.h"
20 #include "include/policy.h"
21 
22 #include "net_names.h"
23 
24 
25 struct aa_sfs_entry aa_sfs_entry_network[] = {
26 	AA_SFS_FILE_STRING("af_mask",	AA_SFS_AF_MASK),
27 	{ }
28 };
29 
30 static const char * const net_mask_names[] = {
31 	"unknown",
32 	"send",
33 	"receive",
34 	"unknown",
35 
36 	"create",
37 	"shutdown",
38 	"connect",
39 	"unknown",
40 
41 	"setattr",
42 	"getattr",
43 	"setcred",
44 	"getcred",
45 
46 	"chmod",
47 	"chown",
48 	"chgrp",
49 	"lock",
50 
51 	"mmap",
52 	"mprot",
53 	"unknown",
54 	"unknown",
55 
56 	"accept",
57 	"bind",
58 	"listen",
59 	"unknown",
60 
61 	"setopt",
62 	"getopt",
63 	"unknown",
64 	"unknown",
65 
66 	"unknown",
67 	"unknown",
68 	"unknown",
69 	"unknown",
70 };
71 
72 
73 /* audit callback for net specific fields */
74 void audit_net_cb(struct audit_buffer *ab, void *va)
75 {
76 	struct common_audit_data *sa = va;
77 
78 	audit_log_format(ab, " family=");
79 	if (address_family_names[sa->u.net->family])
80 		audit_log_string(ab, address_family_names[sa->u.net->family]);
81 	else
82 		audit_log_format(ab, "\"unknown(%d)\"", sa->u.net->family);
83 	audit_log_format(ab, " sock_type=");
84 	if (sock_type_names[aad(sa)->net.type])
85 		audit_log_string(ab, sock_type_names[aad(sa)->net.type]);
86 	else
87 		audit_log_format(ab, "\"unknown(%d)\"", aad(sa)->net.type);
88 	audit_log_format(ab, " protocol=%d", aad(sa)->net.protocol);
89 
90 	if (aad(sa)->request & NET_PERMS_MASK) {
91 		audit_log_format(ab, " requested_mask=");
92 		aa_audit_perm_mask(ab, aad(sa)->request, NULL, 0,
93 				   net_mask_names, NET_PERMS_MASK);
94 
95 		if (aad(sa)->denied & NET_PERMS_MASK) {
96 			audit_log_format(ab, " denied_mask=");
97 			aa_audit_perm_mask(ab, aad(sa)->denied, NULL, 0,
98 					   net_mask_names, NET_PERMS_MASK);
99 		}
100 	}
101 	if (aad(sa)->peer) {
102 		audit_log_format(ab, " peer=");
103 		aa_label_xaudit(ab, labels_ns(aad(sa)->label), aad(sa)->peer,
104 				FLAGS_NONE, GFP_ATOMIC);
105 	}
106 }
107 
108 
109 /* Generic af perm */
110 int aa_profile_af_perm(struct aa_profile *profile, struct common_audit_data *sa,
111 		       u32 request, u16 family, int type)
112 {
113 	struct aa_perms perms = { };
114 
115 	AA_BUG(family >= AF_MAX);
116 	AA_BUG(type < 0 || type >= SOCK_MAX);
117 
118 	if (profile_unconfined(profile))
119 		return 0;
120 
121 	perms.allow = (profile->net.allow[family] & (1 << type)) ?
122 		ALL_PERMS_MASK : 0;
123 	perms.audit = (profile->net.audit[family] & (1 << type)) ?
124 		ALL_PERMS_MASK : 0;
125 	perms.quiet = (profile->net.quiet[family] & (1 << type)) ?
126 		ALL_PERMS_MASK : 0;
127 	aa_apply_modes_to_perms(profile, &perms);
128 
129 	return aa_check_perms(profile, &perms, request, sa, audit_net_cb);
130 }
131 
132 int aa_af_perm(struct aa_label *label, const char *op, u32 request, u16 family,
133 	       int type, int protocol)
134 {
135 	struct aa_profile *profile;
136 	DEFINE_AUDIT_NET(sa, op, NULL, family, type, protocol);
137 
138 	return fn_for_each_confined(label, profile,
139 			aa_profile_af_perm(profile, &sa, request, family,
140 					   type));
141 }
142 
143 static int aa_label_sk_perm(struct aa_label *label, const char *op, u32 request,
144 			    struct sock *sk)
145 {
146 	struct aa_profile *profile;
147 	DEFINE_AUDIT_SK(sa, op, sk);
148 
149 	AA_BUG(!label);
150 	AA_BUG(!sk);
151 
152 	if (unconfined(label))
153 		return 0;
154 
155 	return fn_for_each_confined(label, profile,
156 			aa_profile_af_sk_perm(profile, &sa, request, sk));
157 }
158 
159 int aa_sk_perm(const char *op, u32 request, struct sock *sk)
160 {
161 	struct aa_label *label;
162 	int error;
163 
164 	AA_BUG(!sk);
165 	AA_BUG(in_interrupt());
166 
167 	/* TODO: switch to begin_current_label ???? */
168 	label = begin_current_label_crit_section();
169 	error = aa_label_sk_perm(label, op, request, sk);
170 	end_current_label_crit_section(label);
171 
172 	return error;
173 }
174 
175 
176 int aa_sock_file_perm(struct aa_label *label, const char *op, u32 request,
177 		      struct socket *sock)
178 {
179 	AA_BUG(!label);
180 	AA_BUG(!sock);
181 	AA_BUG(!sock->sk);
182 
183 	return aa_label_sk_perm(label, op, request, sock->sk);
184 }
185