Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
27 changes: 25 additions & 2 deletions kernel/selinux/rules.c
Original file line number Diff line number Diff line change
Expand Up @@ -255,6 +255,8 @@ static int sepol_expected_argc(u32 cmd)
return 4;
case KSU_SEPOLICY_CMD_GENFSCON:
return 3;
case KSU_SEPOLICY_CMD_CLONE_TYPE:
return 2;
default:
return -EINVAL;
}
Expand Down Expand Up @@ -423,6 +425,20 @@ static int apply_one_sepolicy_cmd(struct policydb *db, const struct sepol_data *
}
return 0;

case KSU_SEPOLICY_CMD_CLONE_TYPE:
ret = sepol_require_not_all(args[0], "src");
if (ret < 0)
return ret;
ret = sepol_require_not_all(args[1], "dst");
if (ret < 0)
return ret;

if (!ksu_clone_type(db, args[0], args[1])) {
pr_err("sepol: clone_type failed.\n");
return -EINVAL;
}
return 0;

default:
pr_err("sepol: unknown cmd: %d\n", header->cmd);
return -EINVAL;
Expand Down Expand Up @@ -463,13 +479,14 @@ int handle_sepolicy(void __user *user_data, u64 data_len)

mutex_lock(&selinux_state.policy_mutex);

old_pol = selinux_state.policy;
pol = ksu_dup_sepolicy(rcu_dereference_protected(old_pol, lockdep_is_held(&selinux_state.policy_mutex)));
old_pol = rcu_dereference_protected(selinux_state.policy, lockdep_is_held(&selinux_state.policy_mutex));
pol = ksu_dup_sepolicy(old_pol);
if (IS_ERR(pol)) {
ret = PTR_ERR(pol);
pr_err("ksu_dup_sepolicy err: %d\n", ret);
goto out_unlock;
}
pr_info("sepol: duplicated policy ready, payload_len=%llu\n", data_len);
db = &pol->policydb;

cursor.cur = payload;
Expand Down Expand Up @@ -505,20 +522,26 @@ int handle_sepolicy(void __user *user_data, u64 data_len)
}
}

pr_debug("sepol: begin cmd #%u cmd=%u subcmd=%u\n", cmd_index, header.cmd, header.subcmd);
ret = apply_one_sepolicy_cmd(db, &header, args);
if (ret < 0) {
pr_err("sepol: cmd #%u failed, cmd=%u subcmd=%u.\n", cmd_index, header.cmd, header.subcmd);
if (header.cmd == KSU_SEPOLICY_CMD_CLONE_TYPE)
goto out_drop_new_policy;
} else {
success_cmd_count++;
pr_debug("sepol: end cmd #%u cmd=%u subcmd=%u\n", cmd_index, header.cmd, header.subcmd);
}
cmd_index++;
}

rcu_assign_pointer(selinux_state.policy, pol);
pr_info("sepol: publishing new policy\n");
synchronize_rcu();
ksu_destroy_sepolicy(old_pol);

reset_avc_cache();
pr_info("sepol: policy publish complete, success_cmd_count=%d\n", success_cmd_count);
ret = success_cmd_count;
goto out_unlock;

Expand Down
Loading