|
@@ -191,19 +191,37 @@ static int smk_set_access(struct smack_rule *srp, struct list_head *rule_list,
|
|
|
}
|
|
|
|
|
|
/**
|
|
|
- * smk_parse_rule - parse subject, object and access type
|
|
|
+ * smk_parse_rule - parse Smack rule from load string
|
|
|
* @data: string to be parsed whose size is SMK_LOADLEN
|
|
|
- * @rule: parsed entities are stored in here
|
|
|
+ * @rule: Smack rule
|
|
|
+ * @import: if non-zero, import labels
|
|
|
*/
|
|
|
-static int smk_parse_rule(const char *data, struct smack_rule *rule)
|
|
|
+static int smk_parse_rule(const char *data, struct smack_rule *rule, int import)
|
|
|
{
|
|
|
- rule->smk_subject = smk_import(data, 0);
|
|
|
- if (rule->smk_subject == NULL)
|
|
|
- return -1;
|
|
|
+ char smack[SMK_LABELLEN];
|
|
|
+ struct smack_known *skp;
|
|
|
|
|
|
- rule->smk_object = smk_import(data + SMK_LABELLEN, 0);
|
|
|
- if (rule->smk_object == NULL)
|
|
|
- return -1;
|
|
|
+ if (import) {
|
|
|
+ rule->smk_subject = smk_import(data, 0);
|
|
|
+ if (rule->smk_subject == NULL)
|
|
|
+ return -1;
|
|
|
+
|
|
|
+ rule->smk_object = smk_import(data + SMK_LABELLEN, 0);
|
|
|
+ if (rule->smk_object == NULL)
|
|
|
+ return -1;
|
|
|
+ } else {
|
|
|
+ smk_parse_smack(data, 0, smack);
|
|
|
+ skp = smk_find_entry(smack);
|
|
|
+ if (skp == NULL)
|
|
|
+ return -1;
|
|
|
+ rule->smk_subject = skp->smk_known;
|
|
|
+
|
|
|
+ smk_parse_smack(data + SMK_LABELLEN, 0, smack);
|
|
|
+ skp = smk_find_entry(smack);
|
|
|
+ if (skp == NULL)
|
|
|
+ return -1;
|
|
|
+ rule->smk_object = skp->smk_known;
|
|
|
+ }
|
|
|
|
|
|
rule->smk_access = 0;
|
|
|
|
|
@@ -327,7 +345,7 @@ static ssize_t smk_write_load_list(struct file *file, const char __user *buf,
|
|
|
goto out;
|
|
|
}
|
|
|
|
|
|
- if (smk_parse_rule(data, rule))
|
|
|
+ if (smk_parse_rule(data, rule, 1))
|
|
|
goto out_free_rule;
|
|
|
|
|
|
if (rule_list == NULL) {
|
|
@@ -1499,14 +1517,11 @@ static ssize_t smk_write_access(struct file *file, const char __user *buf,
|
|
|
char *data;
|
|
|
int res;
|
|
|
|
|
|
- if (!capable(CAP_MAC_ADMIN))
|
|
|
- return -EPERM;
|
|
|
-
|
|
|
data = simple_transaction_get(file, buf, count);
|
|
|
if (IS_ERR(data))
|
|
|
return PTR_ERR(data);
|
|
|
|
|
|
- if (count < SMK_LOADLEN || smk_parse_rule(data, &rule))
|
|
|
+ if (count < SMK_LOADLEN || smk_parse_rule(data, &rule, 0))
|
|
|
return -EINVAL;
|
|
|
|
|
|
res = smk_access(rule.smk_subject, rule.smk_object, rule.smk_access,
|
|
@@ -1560,7 +1575,7 @@ static int smk_fill_super(struct super_block *sb, void *data, int silent)
|
|
|
[SMK_LOAD_SELF] = {
|
|
|
"load-self", &smk_load_self_ops, S_IRUGO|S_IWUGO},
|
|
|
[SMK_ACCESSES] = {
|
|
|
- "access", &smk_access_ops, S_IRUGO|S_IWUSR},
|
|
|
+ "access", &smk_access_ops, S_IRUGO|S_IWUGO},
|
|
|
/* last one */
|
|
|
{""}
|
|
|
};
|