From cdbd2884df8ad026143bb482a96d38e616947b17 Mon Sep 17 00:00:00 2001 From: John Johansen Date: Thu, 16 Feb 2012 07:06:41 -0800 Subject: AppArmor: Add mising end of structure test to caps unpacking The unpacking of struct capsx is missing a check for the end of the caps structure. This can lead to unpack failures depending on what else is packed into the policy file being unpacked. Signed-off-by: John Johansen Acked-by: Kees Cook --- security/apparmor/policy_unpack.c | 2 ++ 1 file changed, 2 insertions(+) (limited to 'security/apparmor/policy_unpack.c') diff --git a/security/apparmor/policy_unpack.c b/security/apparmor/policy_unpack.c index 741dd13e089..5c46acf5aa6 100644 --- a/security/apparmor/policy_unpack.c +++ b/security/apparmor/policy_unpack.c @@ -554,6 +554,8 @@ static struct aa_profile *unpack_profile(struct aa_ext *e) goto fail; if (!unpack_u32(e, &(profile->caps.extended.cap[1]), NULL)) goto fail; + if (!unpack_nameX(e, AA_STRUCTEND, NULL)) + goto fail; } if (!unpack_rlimits(e, profile)) -- cgit v1.2.3-70-g09d2 From b1b4bc2ed94d157f3ed60c17a12b658ccb96a76f Mon Sep 17 00:00:00 2001 From: John Johansen Date: Sat, 10 Mar 2012 11:25:30 -0800 Subject: AppArmor: Fix oops in policy unpack auditing Post unpacking of policy a verification pass is made on x transition indexes. When this fails a call to audit_iface is made resulting in an oops, because audit_iface is expecting a valid buffer position but since the failure comes from post unpack verification there is none. Make the position argument optional so that audit_iface can be called from post unpack verification. Signed-off-by: John Johansen --- security/apparmor/policy_unpack.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) (limited to 'security/apparmor/policy_unpack.c') diff --git a/security/apparmor/policy_unpack.c b/security/apparmor/policy_unpack.c index 5c46acf5aa6..c50634b724b 100644 --- a/security/apparmor/policy_unpack.c +++ b/security/apparmor/policy_unpack.c @@ -84,7 +84,7 @@ static void audit_cb(struct audit_buffer *ab, void *va) * @new: profile if it has been allocated (MAYBE NULL) * @name: name of the profile being manipulated (MAYBE NULL) * @info: any extra info about the failure (MAYBE NULL) - * @e: buffer position info (NOT NULL) + * @e: buffer position info * @error: error code * * Returns: %0 or error @@ -95,7 +95,8 @@ static int audit_iface(struct aa_profile *new, const char *name, struct aa_profile *profile = __aa_current_profile(); struct common_audit_data sa; COMMON_AUDIT_DATA_INIT(&sa, NONE); - sa.aad.iface.pos = e->pos - e->start; + if (e) + sa.aad.iface.pos = e->pos - e->start; sa.aad.iface.target = new; sa.aad.name = name; sa.aad.info = info; -- cgit v1.2.3-70-g09d2 From ad5ff3db53c68c2f12936bc74ea5dfe0af943592 Mon Sep 17 00:00:00 2001 From: John Johansen Date: Thu, 16 Feb 2012 07:07:53 -0800 Subject: AppArmor: Add ability to load extended policy Add the base support for the new policy extensions. This does not bring any additional functionality, or change current semantics. Signed-off-by: John Johansen Acked-by: Kees Cook --- security/apparmor/include/apparmor.h | 13 +++++++++++++ security/apparmor/include/policy.h | 13 +++++++++++++ security/apparmor/policy.c | 1 + security/apparmor/policy_unpack.c | 24 +++++++++++++++++++++++- 4 files changed, 50 insertions(+), 1 deletion(-) (limited to 'security/apparmor/policy_unpack.c') diff --git a/security/apparmor/include/apparmor.h b/security/apparmor/include/apparmor.h index 248c408ddc1..40aedd9f73e 100644 --- a/security/apparmor/include/apparmor.h +++ b/security/apparmor/include/apparmor.h @@ -19,6 +19,19 @@ #include "match.h" +/* + * Class of mediation types in the AppArmor policy db + */ +#define AA_CLASS_ENTRY 0 +#define AA_CLASS_UNKNOWN 1 +#define AA_CLASS_FILE 2 +#define AA_CLASS_CAP 3 +#define AA_CLASS_NET 4 +#define AA_CLASS_RLIMITS 5 +#define AA_CLASS_DOMAIN 6 + +#define AA_CLASS_LAST AA_CLASS_DOMAIN + /* Control parameters settable through module/boot flags */ extern enum audit_mode aa_g_audit; extern bool aa_g_audit_header; diff --git a/security/apparmor/include/policy.h b/security/apparmor/include/policy.h index aeda5cf5690..9e18e9609e2 100644 --- a/security/apparmor/include/policy.h +++ b/security/apparmor/include/policy.h @@ -129,6 +129,17 @@ struct aa_namespace { struct list_head sub_ns; }; +/* struct aa_policydb - match engine for a policy + * dfa: dfa pattern match + * start: set of start states for the different classes of data + */ +struct aa_policydb { + /* Generic policy DFA specific rule types will be subsections of it */ + struct aa_dfa *dfa; + unsigned int start[AA_CLASS_LAST + 1]; + +}; + /* struct aa_profile - basic confinement data * @base - base components of the profile (name, refcount, lists, lock ...) * @parent: parent of profile @@ -143,6 +154,7 @@ struct aa_namespace { * @flags: flags controlling profile behavior * @path_flags: flags controlling path generation behavior * @size: the memory consumed by this profiles rules + * @policy: general match rules governing policy * @file: The set of rules governing basic file access and domain transitions * @caps: capabilities for the profile * @rlimits: rlimits for the profile @@ -179,6 +191,7 @@ struct aa_profile { u32 path_flags; int size; + struct aa_policydb policy; struct aa_file_rules file; struct aa_caps caps; struct aa_rlimit rlimits; diff --git a/security/apparmor/policy.c b/security/apparmor/policy.c index 4f0eadee78b..73288d0b541 100644 --- a/security/apparmor/policy.c +++ b/security/apparmor/policy.c @@ -749,6 +749,7 @@ static void free_profile(struct aa_profile *profile) aa_free_sid(profile->sid); aa_put_dfa(profile->xmatch); + aa_put_dfa(profile->policy.dfa); aa_put_profile(profile->replacedby); diff --git a/security/apparmor/policy_unpack.c b/security/apparmor/policy_unpack.c index c50634b724b..25fd51edc8d 100644 --- a/security/apparmor/policy_unpack.c +++ b/security/apparmor/policy_unpack.c @@ -469,7 +469,7 @@ static struct aa_profile *unpack_profile(struct aa_ext *e) { struct aa_profile *profile = NULL; const char *name = NULL; - int error = -EPROTO; + int i, error = -EPROTO; kernel_cap_t tmpcap; u32 tmp; @@ -562,6 +562,28 @@ static struct aa_profile *unpack_profile(struct aa_ext *e) if (!unpack_rlimits(e, profile)) goto fail; + if (unpack_nameX(e, AA_STRUCT, "policydb")) { + /* generic policy dfa - optional and may be NULL */ + profile->policy.dfa = unpack_dfa(e); + if (IS_ERR(profile->policy.dfa)) { + error = PTR_ERR(profile->policy.dfa); + profile->policy.dfa = NULL; + goto fail; + } + if (!unpack_u32(e, &profile->policy.start[0], "start")) + /* default start state */ + profile->policy.start[0] = DFA_START; + /* setup class index */ + for (i = AA_CLASS_FILE; i <= AA_CLASS_LAST; i++) { + profile->policy.start[i] = + aa_dfa_next(profile->policy.dfa, + profile->policy.start[0], + i); + } + if (!unpack_nameX(e, AA_STRUCTEND, NULL)) + goto fail; + } + /* get file rules */ profile->file.dfa = unpack_dfa(e); if (IS_ERR(profile->file.dfa)) { -- cgit v1.2.3-70-g09d2