From: Roberto Sassu roberto.sassu@huawei.com
euleros inclusion category: feature bugzilla: https://gitee.com/openeuler/kernel/issues/I7QZ2M CVE: NA
-------------------------------------------------
This patch adds the new policy keyword 'parser' to measure and appraise any file opened by the user space parser, while the parser opened digest_list_data_add or digest_list_data_del securityfs interfaces.
This ensures that all files processed by the user space parser are processed without including the FILE_CHECK hook in the policy. With this keyword it would be possible to have a policy to measure/appraise only executable code and digest lists.
Signed-off-by: Roberto Sassu roberto.sassu@huawei.com Signed-off-by: Tianxing Zhang zhangtianxing3@huawei.com Reviewed-by: Jason Yan yanaijie@huawei.com Signed-off-by: Zheng Zengkai zhengzengkai@huawei.com Signed-off-by: zhoushuiqing zhoushuiqing2@huawei.com --- security/integrity/ima/ima_policy.c | 33 +++++++++++++++++++++++++++-- 1 file changed, 31 insertions(+), 2 deletions(-)
diff --git a/security/integrity/ima/ima_policy.c b/security/integrity/ima/ima_policy.c index 88cd1778680a..582d81f8bfde 100644 --- a/security/integrity/ima/ima_policy.c +++ b/security/integrity/ima/ima_policy.c @@ -20,6 +20,7 @@ #include <linux/ima.h>
#include "ima.h" +#include "ima_digest_list.h"
/* flags definitions */ #define IMA_FUNC 0x0001 @@ -34,6 +35,7 @@ #define IMA_FSNAME 0x0200 #define IMA_KEYRINGS 0x0400 #define IMA_LABEL 0x0800 +#define IMA_PARSER 0x10000 #define IMA_VALIDATE_ALGOS 0x1000 #define IMA_GID 0x2000 #define IMA_EGID 0x4000 @@ -191,6 +193,10 @@ static struct ima_rule_entry default_measurement_rules[] __ro_after_init = { {.action = MEASURE, .func = DIGEST_LIST_CHECK, .flags = IMA_FUNC}, };
+static struct ima_rule_entry ima_parser_measure_rule __ro_after_init = { + .action = MEASURE, .flags = IMA_PARSER +}; + static struct ima_rule_entry default_appraise_rules[] __ro_after_init = { {.action = DONT_APPRAISE, .fsmagic = PROC_SUPER_MAGIC, .flags = IMA_FSMAGIC}, {.action = DONT_APPRAISE, .fsmagic = SYSFS_MAGIC, .flags = IMA_FSMAGIC}, @@ -259,6 +265,11 @@ static struct ima_rule_entry secure_boot_rules[] __ro_after_init = { .flags = IMA_FUNC | IMA_DIGSIG_REQUIRED}, };
+static struct ima_rule_entry ima_parser_appraise_rule __ro_after_init = { + .action = APPRAISE, + .flags = IMA_PARSER | IMA_DIGSIG_REQUIRED +}; + static struct ima_rule_entry critical_data_rules[] __ro_after_init = { {.action = MEASURE, .func = CRITICAL_DATA, .flags = IMA_FUNC}, }; @@ -645,6 +656,9 @@ static bool ima_match_rules(struct ima_rule_entry *rule, !rule->fowner_op(i_uid_into_vfsuid(idmap, inode), rule->fowner)) return false; + if ((rule->flags & IMA_PARSER) && + !ima_current_is_parser()) + return false; if ((rule->flags & IMA_FGROUP) && !rule->fgroup_op(i_gid_into_vfsgid(idmap, inode), rule->fgroup)) @@ -1010,6 +1024,9 @@ void __init ima_init_policy(void) break; }
+ if (ima_policy) + add_rules(&ima_parser_measure_rule, 1, IMA_DEFAULT_POLICY); + /* * Based on runtime secure boot flags, insert arch specific measurement * and appraise rules requiring file signatures for both the initial @@ -1064,6 +1081,10 @@ void __init ima_init_policy(void)
atomic_set(&ima_setxattr_allowed_hash_algorithms, 0);
+ if (ima_use_secure_boot || ima_use_appraise_tcb || + ima_use_appraise_exec_tcb) + add_rules(&ima_parser_appraise_rule, 1, IMA_DEFAULT_POLICY); + ima_update_policy_flags(); }
@@ -1127,7 +1148,7 @@ enum policy_opt { Opt_digest_type, Opt_appraise_type, Opt_appraise_flag, Opt_appraise_algos, Opt_permit_directio, Opt_pcr, Opt_template, Opt_keyrings, - Opt_label, Opt_err + Opt_label, Opt_parser, Opt_err };
static const match_table_t policy_tokens = { @@ -1176,6 +1197,7 @@ static const match_table_t policy_tokens = { {Opt_template, "template=%s"}, {Opt_keyrings, "keyrings=%s"}, {Opt_label, "label=%s"}, + {Opt_parser, "parser"}, {Opt_err, NULL} };
@@ -1302,7 +1324,7 @@ static bool ima_validate_rule(struct ima_rule_entry *entry) if (entry->action != APPRAISE && entry->flags & (IMA_DIGSIG_REQUIRED | IMA_MODSIG_ALLOWED | IMA_CHECK_BLACKLIST | IMA_VALIDATE_ALGOS | - IMA_META_IMMUTABLE_REQUIRED)) + IMA_META_IMMUTABLE_REQUIRED | IMA_PARSER)) return false;
/* @@ -1945,6 +1967,10 @@ static int ima_parse_rule(char *rule, struct ima_rule_entry *entry) &(template_desc->num_fields)); entry->template = template_desc; break; + case Opt_parser: + audit_log_format(ab, "parser "); + entry->flags |= IMA_PARSER; + break; case Opt_err: ima_log_string(ab, "UNKNOWN", p); result = -EINVAL; @@ -2290,6 +2316,9 @@ int ima_policy_show(struct seq_file *m, void *v) seq_puts(m, " "); }
+ if (entry->flags & IMA_PARSER) + seq_puts(m, "parser "); + for (i = 0; i < MAX_LSM_RULES; i++) { if (entry->lsm[i].rule) { switch (i) {