Hi Casey, On Fri, 2020-11-20 at 12:14 -0800, Casey Schaufler wrote: > diff --git a/security/security.c b/security/security.c > index 5da8b3643680..d01363cb0082 100644 > --- a/security/security.c > +++ b/security/security.c > > @@ -2510,7 +2526,24 @@ int security_key_getsecurity(struct key *key, char **_buffer) > > int security_audit_rule_init(u32 field, u32 op, char *rulestr, void **lsmrule) > { > - return call_int_hook(audit_rule_init, 0, field, op, rulestr, lsmrule); > + struct security_hook_list *hp; > + bool one_is_good = false; > + int rc = 0; > + int trc; > + > + hlist_for_each_entry(hp, &security_hook_heads.audit_rule_init, list) { > + if (WARN_ON(hp->lsmid->slot < 0 || hp->lsmid->slot >= lsm_slot)) > + continue; > + trc = hp->hook.audit_rule_init(field, op, rulestr, > + &lsmrule[hp->lsmid->slot]); > + if (trc == 0) > + one_is_good = true; > + else > + rc = trc; > + } > + if (one_is_good) > + return 0; > + return rc; > } So the same string may be defined by multiple LSMs. > > int security_audit_rule_known(struct audit_krule *krule) > @@ -2518,14 +2551,31 @@ int security_audit_rule_known(struct audit_krule *krule) > return call_int_hook(audit_rule_known, 0, krule); > } > > -void security_audit_rule_free(void *lsmrule) > +void security_audit_rule_free(void **lsmrule) > { > - call_void_hook(audit_rule_free, lsmrule); > + struct security_hook_list *hp; > + > + hlist_for_each_entry(hp, &security_hook_heads.audit_rule_free, list) { > + if (WARN_ON(hp->lsmid->slot < 0 || hp->lsmid->slot >= lsm_slot)) > + continue; > + hp->hook.audit_rule_free(lsmrule[hp->lsmid->slot]); > + } > } > If one LSM frees the string, then the string is deleted from all LSMs. I don't understand how this safe. > -int security_audit_rule_match(u32 secid, u32 field, u32 op, void *lsmrule) > +int security_audit_rule_match(u32 secid, u32 field, u32 op, void **lsmrule) > { > - return call_int_hook(audit_rule_match, 0, secid, field, op, lsmrule); > + struct security_hook_list *hp; > + int rc; > + > + hlist_for_each_entry(hp, &security_hook_heads.audit_rule_match, list) { > + if (WARN_ON(hp->lsmid->slot < 0 || hp->lsmid->slot >= lsm_slot)) > + continue; > + rc = hp->hook.audit_rule_match(secid, field, op, > + &lsmrule[hp->lsmid->slot]); > + if (rc) > + return rc; Suppose that there is an IMA dont_measure or dont_appraise rule, if one LSM matches, then this returns true, causing any measurement or integrity verification to be skipped. Sample policy rules: dont_measure obj_type=foo_log dont_appraise obj_type=foo_log Are there any plans to prevent label collisions or at least notify of a label collision? Mimi > + } > + return 0; > } > #endif /* CONFIG_AUDIT */