@@ -85,6 +85,12 @@ extern void semanage_set_disable_dontaudit(semanage_handle_t * handle, int disab
/* Set whether or not to execute setfiles to check file contexts upon commit */
extern void semanage_set_check_contexts(semanage_handle_t * sh, int do_check_contexts);
+/* Get the kernel policy version. */
+extern unsigned semanage_get_policyvers(semanage_handle_t *sh);
+
+/* Set the kernel policy version. */
+extern int semanage_set_policyvers(semanage_handle_t *sh, unsigned policyvers);
+
/* Get the default priority. */
extern uint16_t semanage_get_default_priority(semanage_handle_t *sh);
@@ -1204,6 +1204,7 @@ static int semanage_direct_commit(semanage_handle_t * sh)
size_t fc_buffer_len = 0;
const char *ofilename = NULL;
const char *path;
+ char kernel_path[PATH_MAX];
int retval = -1, num_modinfos = 0, i;
sepol_policydb_t *out = NULL;
struct cil_db *cildb = NULL;
@@ -1593,9 +1594,13 @@ rebuild:
if (retval < 0)
goto cleanup;
+ if (semanage_get_full_kernel_path(sh, SEMANAGE_FINAL_TMP, kernel_path)) {
+ ERR(sh, "Unable to build path to kernel policy.");
+ goto cleanup;
+ }
+
retval = semanage_copy_file(semanage_path(SEMANAGE_TMP, SEMANAGE_STORE_KERNEL),
- semanage_final_path(SEMANAGE_FINAL_TMP, SEMANAGE_KERNEL),
- sh->conf->file_mode);
+ kernel_path, sh->conf->file_mode);
if (retval < 0) {
goto cleanup;
}
@@ -81,6 +81,9 @@ semanage_handle_t *semanage_handle_create(void)
goto err;
sepol_msg_set_callback(sh->sepolh, semanage_msg_relay_handler, sh);
+ /* Default policy version is taken from config */
+ sh->policyvers = sh->conf->policyvers;
+
/* Default priority is 400 */
sh->priority = 400;
@@ -246,6 +249,27 @@ void semanage_set_check_contexts(semanage_handle_t * sh, int do_check_contexts)
return;
}
+unsigned semanage_get_policyvers(semanage_handle_t *sh)
+{
+ assert(sh != NULL);
+ return sh->policyvers;
+}
+
+int semanage_set_policyvers(semanage_handle_t *sh, unsigned policyvers)
+{
+ assert(sh != NULL);
+
+ /* Verify policy version */
+ if ( policyvers < POLICYDB_VERSION_MIN
+ || policyvers > POLICYDB_VERSION_MAX) {
+ ERR(sh, "Policy version %u is invalid.", policyvers);
+ return -1;
+ }
+
+ sh->policyvers = policyvers;
+ return 0;
+}
+
uint16_t semanage_get_default_priority(semanage_handle_t *sh)
{
assert(sh != NULL);
@@ -57,6 +57,7 @@ struct semanage_handle {
semanage_conf_t *conf;
+ unsigned policyvers;
uint16_t priority;
int is_connected;
int is_in_transaction;
@@ -63,3 +63,9 @@ LIBSEMANAGE_1.1 {
semanage_module_remove_key;
semanage_set_store_root;
} LIBSEMANAGE_1.0;
+
+LIBSEMANAGE_1.2 {
+ global:
+ semanage_get_policyvers;
+ semanage_set_policyvers;
+} LIBSEMANAGE_1.1;
@@ -277,9 +277,7 @@ cleanup:
static int semanage_init_final_suffix(semanage_handle_t *sh)
{
- int ret = 0;
int status = 0;
- char path[PATH_MAX];
size_t offset = strlen(selinux_policy_root());
semanage_final_suffix[SEMANAGE_FINAL_TOPLEVEL] = strdup("");
@@ -350,19 +348,9 @@ static int semanage_init_final_suffix(semanage_handle_t *sh)
goto cleanup;
}
- ret = snprintf(path,
- sizeof(path),
- "%s.%d",
- selinux_binary_policy_path() + offset,
- sh->conf->policyvers);
- if (ret < 0 || ret >= (int)sizeof(path)) {
- ERR(sh, "Unable to compose policy binary path.");
- status = -1;
- goto cleanup;
- }
-
- semanage_final_suffix[SEMANAGE_KERNEL] = strdup(path);
- if (semanage_final_suffix[SEMANAGE_KERNEL] == NULL) {
+ semanage_final_suffix[SEMANAGE_KERNEL_PREFIX] =
+ strdup(selinux_binary_policy_path() + offset);
+ if (semanage_final_suffix[SEMANAGE_KERNEL_PREFIX] == NULL) {
ERR(sh, "Unable to allocate space for policy binary path.");
status = -1;
goto cleanup;
@@ -503,6 +491,20 @@ const char *semanage_final_path(enum semanage_final_defs store,
return semanage_final_paths[store][path_name];
}
+/* Return a fully-qualified path + filename to kernel policy for the given
+ * semanage store.
+ */
+int semanage_get_full_kernel_path(semanage_handle_t * sh,
+ enum semanage_final_defs root,
+ char out[PATH_MAX])
+{
+ int ret = snprintf(out, PATH_MAX, "%s.%u",
+ semanage_final_path(root, SEMANAGE_KERNEL_PREFIX),
+ sh->policyvers);
+
+ return ret < 0 || ret >= PATH_MAX ? -1 : 0;
+}
+
/* Return a fully-qualified path + filename to the semanage
* configuration file. If semanage.conf file in the semanage
* root is cannot be read, use the default semanage.conf as a
@@ -1568,12 +1570,16 @@ static int semanage_validate_and_compile_fcontexts(semanage_handle_t * sh)
int status = -1;
if (sh->do_check_contexts) {
+ char path[PATH_MAX];
int ret;
+
+ if (semanage_get_full_kernel_path(sh, SEMANAGE_FINAL_TMP, path)) {
+ ERR(sh, "Unable to build path to kernel policy.");
+ goto cleanup;
+ }
+
ret = semanage_exec_prog(
- sh,
- sh->conf->setfiles,
- semanage_final_path(SEMANAGE_FINAL_TMP,
- SEMANAGE_KERNEL),
+ sh, sh->conf->setfiles, path,
semanage_final_path(SEMANAGE_FINAL_TMP,
SEMANAGE_FC));
if (ret != 0) {
@@ -2233,15 +2239,19 @@ int semanage_verify_linked(semanage_handle_t * sh)
int semanage_verify_kernel(semanage_handle_t * sh)
{
int retval = -1;
- const char *kernel_filename =
- semanage_final_path(SEMANAGE_FINAL_TMP, SEMANAGE_KERNEL);
+ char path[PATH_MAX];
semanage_conf_t *conf = sh->conf;
external_prog_t *e;
+
if (conf->kernel_prog == NULL) {
return 0;
}
+ if (semanage_get_full_kernel_path(sh, SEMANAGE_FINAL_TMP, path)) {
+ ERR(sh, "Unable to build path to kernel policy.");
+ goto cleanup;
+ }
for (e = conf->kernel_prog; e != NULL; e = e->next) {
- if (semanage_exec_prog(sh, e, kernel_filename, "$<") != 0) {
+ if (semanage_exec_prog(sh, e, path, "$<") != 0) {
goto cleanup;
}
}
@@ -81,7 +81,7 @@ enum semanage_final_path_defs {
SEMANAGE_FC_HOMEDIRS_BIN,
SEMANAGE_FC_LOCAL,
SEMANAGE_FC_LOCAL_BIN,
- SEMANAGE_KERNEL,
+ SEMANAGE_KERNEL_PREFIX,
SEMANAGE_NC,
SEMANAGE_SEUSERS,
SEMANAGE_FINAL_PATH_NUM
@@ -102,6 +102,10 @@ extern const char *semanage_path(enum semanage_store_defs store,
extern const char *semanage_final_path(enum semanage_final_defs root,
enum semanage_final_path_defs suffix);
+int semanage_get_full_kernel_path(semanage_handle_t * sh,
+ enum semanage_final_defs root,
+ char out[PATH_MAX]);
+
int semanage_create_store(semanage_handle_t * sh, int create);
int semanage_store_access_check(void);
This change will be needed to support explicly specifying the policy version in semodule (in a subsequent patch). Signed-off-by: Ondrej Mosnacek <omosnace@redhat.com> --- libsemanage/include/semanage/handle.h | 6 +++ libsemanage/src/direct_api.c | 9 ++++- libsemanage/src/handle.c | 24 ++++++++++++ libsemanage/src/handle.h | 1 + libsemanage/src/libsemanage.map | 6 +++ libsemanage/src/semanage_store.c | 54 ++++++++++++++++----------- libsemanage/src/semanage_store.h | 6 ++- 7 files changed, 81 insertions(+), 25 deletions(-)