lkml.org 
[lkml]   [2021]   [Dec]   [8]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
 
Messages in this thread
    Patch in this message
    /
    From
    Subject[PATCH v5 05/16] ima: Move IMA's keys queue related variables into ima_namespace
    Date
    Move variables from keys queue into ima_namespace.

    Some variables have to be initialized before ima_init() runs, so statically
    initialize them for the init_ima_ns.

    Since only init_ima_ns uses the queued keys there's no need to free the
    list of queued keys when tearing down IMA namespaces.

    Signed-off-by: Stefan Berger <stefanb@linux.ibm.com>
    ---
    include/linux/ima.h | 11 ++++++
    security/integrity/ima/ima.h | 9 ++---
    security/integrity/ima/ima_asymmetric_keys.c | 5 +--
    security/integrity/ima/ima_init_ima_ns.c | 5 +++
    security/integrity/ima/ima_ns.c | 6 ++++
    security/integrity/ima/ima_queue_keys.c | 37 +++++++-------------
    6 files changed, 43 insertions(+), 30 deletions(-)

    diff --git a/include/linux/ima.h b/include/linux/ima.h
    index 529defe4d272..0ce58c17cb25 100644
    --- a/include/linux/ima.h
    +++ b/include/linux/ima.h
    @@ -219,6 +219,17 @@ struct ima_namespace {
    struct kmem_cache *ns_status_cache;

    #ifdef CONFIG_IMA_QUEUE_EARLY_BOOT_KEYS
    + /*
    + * Flag to indicate whether a key can be processed
    + * right away or should be queued for processing later.
    + */
    + bool ima_process_keys;
    +
    + /*
    + * To synchronize access to the list of keys that need to be measured
    + */
    + struct mutex ima_keys_lock;
    + struct list_head ima_keys;
    /*
    * If custom IMA policy is not loaded then keys queued up
    * for measurement should be freed. This worker is used
    diff --git a/security/integrity/ima/ima.h b/security/integrity/ima/ima.h
    index 9edab9050dc7..97eb03376855 100644
    --- a/security/integrity/ima/ima.h
    +++ b/security/integrity/ima/ima.h
    @@ -250,14 +250,15 @@ struct ima_key_entry {
    char *keyring_name;
    };
    void ima_init_key_queue(struct ima_namespace *ns);
    -bool ima_should_queue_key(void);
    -bool ima_queue_key(struct key *keyring, const void *payload,
    +bool ima_should_queue_key(struct ima_namespace *ns);
    +bool ima_queue_key(struct ima_namespace *ns, struct key *keyring, const void *payload,
    size_t payload_len);
    void ima_process_queued_keys(struct ima_namespace *ns);
    void ima_keys_handler(struct work_struct *work);
    #else
    -static inline bool ima_should_queue_key(void) { return false; }
    -static inline bool ima_queue_key(struct key *keyring,
    +static inline bool ima_should_queue_key(struct ima_namespace *ns) { return false; }
    +static inline bool ima_queue_key(struct ima_namespace *ns,
    + struct key *keyring,
    const void *payload,
    size_t payload_len) { return false; }
    static inline void ima_process_queued_keys(struct ima_namespace *ns) {}
    diff --git a/security/integrity/ima/ima_asymmetric_keys.c b/security/integrity/ima/ima_asymmetric_keys.c
    index f6aa0b47a772..b20e82eda8f4 100644
    --- a/security/integrity/ima/ima_asymmetric_keys.c
    +++ b/security/integrity/ima/ima_asymmetric_keys.c
    @@ -30,6 +30,7 @@ void ima_post_key_create_or_update(struct key *keyring, struct key *key,
    const void *payload, size_t payload_len,
    unsigned long flags, bool create)
    {
    + struct ima_namespace *ns = get_current_ns();
    bool queued = false;

    /* Only asymmetric keys are handled by this hook. */
    @@ -39,8 +40,8 @@ void ima_post_key_create_or_update(struct key *keyring, struct key *key,
    if (!payload || (payload_len == 0))
    return;

    - if (ima_should_queue_key())
    - queued = ima_queue_key(keyring, payload, payload_len);
    + if (ima_should_queue_key(ns))
    + queued = ima_queue_key(ns, keyring, payload, payload_len);

    if (queued)
    return;
    diff --git a/security/integrity/ima/ima_init_ima_ns.c b/security/integrity/ima/ima_init_ima_ns.c
    index 75ef17d52b5b..144b30ceefb0 100644
    --- a/security/integrity/ima/ima_init_ima_ns.c
    +++ b/security/integrity/ima/ima_init_ima_ns.c
    @@ -45,5 +45,10 @@ int __init ima_ns_init(void)
    struct ima_namespace init_ima_ns = {
    .kref = KREF_INIT(1),
    .user_ns = &init_user_ns,
    +#ifdef CONFIG_IMA_QUEUE_EARLY_BOOT_KEYS
    + .ima_process_keys = false,
    + .ima_keys_lock = __MUTEX_INITIALIZER(init_ima_ns.ima_keys_lock),
    + .ima_keys = LIST_HEAD_INIT(init_ima_ns.ima_keys),
    +#endif
    };
    EXPORT_SYMBOL(init_ima_ns);
    diff --git a/security/integrity/ima/ima_ns.c b/security/integrity/ima/ima_ns.c
    index 000dbde2f264..1ee724bab714 100644
    --- a/security/integrity/ima/ima_ns.c
    +++ b/security/integrity/ima/ima_ns.c
    @@ -38,6 +38,12 @@ int create_ima_ns(struct user_namespace *user_ns)
    if (err)
    goto fail_free;

    +#ifdef CONFIG_IMA_QUEUE_EARLY_BOOT_KEYS
    + ns->ima_process_keys = false;
    + mutex_init(&ns->ima_keys_lock);
    + INIT_LIST_HEAD(&ns->ima_keys);
    +#endif
    +
    user_ns->ima_ns = ns;

    return 0;
    diff --git a/security/integrity/ima/ima_queue_keys.c b/security/integrity/ima/ima_queue_keys.c
    index ed5923dfe71b..4c69178b1ffe 100644
    --- a/security/integrity/ima/ima_queue_keys.c
    +++ b/security/integrity/ima/ima_queue_keys.c
    @@ -14,17 +14,6 @@
    #include <keys/asymmetric-type.h>
    #include "ima.h"

    -/*
    - * Flag to indicate whether a key can be processed
    - * right away or should be queued for processing later.
    - */
    -static bool ima_process_keys;
    -
    -/*
    - * To synchronize access to the list of keys that need to be measured
    - */
    -static DEFINE_MUTEX(ima_keys_lock);
    -static LIST_HEAD(ima_keys);

    /*
    * This worker function frees keys that may still be
    @@ -100,7 +89,7 @@ static struct ima_key_entry *ima_alloc_key_entry(struct key *keyring,
    return entry;
    }

    -bool ima_queue_key(struct key *keyring, const void *payload,
    +bool ima_queue_key(struct ima_namespace *ns, struct key *keyring, const void *payload,
    size_t payload_len)
    {
    bool queued = false;
    @@ -110,12 +99,12 @@ bool ima_queue_key(struct key *keyring, const void *payload,
    if (!entry)
    return false;

    - mutex_lock(&ima_keys_lock);
    - if (!ima_process_keys) {
    - list_add_tail(&entry->list, &ima_keys);
    + mutex_lock(&ns->ima_keys_lock);
    + if (!ns->ima_process_keys) {
    + list_add_tail(&entry->list, &ns->ima_keys);
    queued = true;
    }
    - mutex_unlock(&ima_keys_lock);
    + mutex_unlock(&ns->ima_keys_lock);

    if (!queued)
    ima_free_key_entry(entry);
    @@ -134,7 +123,7 @@ void ima_process_queued_keys(struct ima_namespace *ns)
    struct ima_key_entry *entry, *tmp;
    bool process = false;

    - if (ima_process_keys)
    + if (ns->ima_process_keys)
    return;

    /*
    @@ -143,12 +132,12 @@ void ima_process_queued_keys(struct ima_namespace *ns)
    * First one setting the ima_process_keys flag to true will
    * process the queued keys.
    */
    - mutex_lock(&ima_keys_lock);
    - if (!ima_process_keys) {
    - ima_process_keys = true;
    + mutex_lock(&ns->ima_keys_lock);
    + if (!ns->ima_process_keys) {
    + ns->ima_process_keys = true;
    process = true;
    }
    - mutex_unlock(&ima_keys_lock);
    + mutex_unlock(&ns->ima_keys_lock);

    if (!process)
    return;
    @@ -159,7 +148,7 @@ void ima_process_queued_keys(struct ima_namespace *ns)
    put_user_ns(ns->user_ns);
    }

    - list_for_each_entry_safe(entry, tmp, &ima_keys, list) {
    + list_for_each_entry_safe(entry, tmp, &ns->ima_keys, list) {
    if (!ns->timer_expired)
    process_buffer_measurement(&init_user_ns, NULL,
    entry->payload,
    @@ -173,7 +162,7 @@ void ima_process_queued_keys(struct ima_namespace *ns)
    }
    }

    -inline bool ima_should_queue_key(void)
    +inline bool ima_should_queue_key(struct ima_namespace *ns)
    {
    - return !ima_process_keys;
    + return !ns->ima_process_keys;
    }
    --
    2.31.1
    \
     
     \ /
      Last update: 2021-12-08 23:19    [W:2.765 / U:0.008 seconds]
    ©2003-2020 Jasper Spaans|hosted at Digital Ocean and TransIP|Read the blog|Advertise on this site