From: Zhang Tianxing zhangtianxing3@huawei.com
hulk inclusion category: bugfix bugzilla: https://gitee.com/openeuler/kernel/issues/I4O25G CVE: NA
--------------------------------
This reverts commit eecf0d8324b4fd931349e6528f82fc115dca5928.
Signed-off-by: Zhang Tianxing zhangtianxing3@huawei.com Acked-by: Xie XiuQi xiexiuqi@huawei.com Acked-by: Xiu Jianfengxiujianfeng@huawei.com Signed-off-by: Zheng Zengkai zhengzengkai@huawei.com --- include/linux/integrity.h | 31 -------- security/integrity/iint.c | 126 +++++++-------------------------- security/integrity/integrity.h | 11 --- 3 files changed, 24 insertions(+), 144 deletions(-)
diff --git a/include/linux/integrity.h b/include/linux/integrity.h index 4a38310e6e7e..2ea0f2f65ab6 100644 --- a/include/linux/integrity.h +++ b/include/linux/integrity.h @@ -8,10 +8,6 @@ #define _LINUX_INTEGRITY_H
#include <linux/fs.h> -#include <linux/rwlock_types.h> - -struct rb_root; -struct integrity_iint_tree;
enum integrity_status { INTEGRITY_PASS = 0, @@ -26,15 +22,8 @@ enum integrity_status { /* List of EVM protected security xattrs */ #ifdef CONFIG_INTEGRITY extern struct integrity_iint_cache *integrity_inode_get(struct inode *inode); -extern struct integrity_iint_cache *integrity_inode_rb_get(struct - integrity_iint_tree - *iint_tree, - struct inode *inode); extern void integrity_inode_free(struct inode *inode); -extern void integrity_inode_rb_free(struct integrity_iint_tree *iint_tree, - struct inode *inode); extern void __init integrity_load_keys(void); -extern void integrity_iint_tree_free(struct integrity_iint_tree *iint_tree);
#else static inline struct integrity_iint_cache * @@ -43,34 +32,14 @@ static inline struct integrity_iint_cache * return NULL; }
-static inline struct integrity_iint_cache * - integrity_inode_rb_get(struct - integrity_iint_tree - *iint_tree, - struct inode *inode) -{ - return NULL; -} - static inline void integrity_inode_free(struct inode *inode) { return; }
-static inline void integrity_inode_rb_free(struct integrity_iint_tree - *iint_tree, - struct inode *inode) -{ -} - static inline void integrity_load_keys(void) { } - -static inline void integrity_iint_tree_free(struct integrity_iint_tree - *iint_tree) -{ -} #endif /* CONFIG_INTEGRITY */
#ifdef CONFIG_INTEGRITY_ASYMMETRIC_KEYS diff --git a/security/integrity/iint.c b/security/integrity/iint.c index 48716d058ed1..8953ac6412c3 100644 --- a/security/integrity/iint.c +++ b/security/integrity/iint.c @@ -21,29 +21,19 @@ #include <linux/lsm_hooks.h> #include "integrity.h"
-struct integrity_iint_tree init_iint_tree = { - .lock = __RW_LOCK_UNLOCKED(init_iint_tree.lock), - .root = RB_ROOT -}; - +static struct rb_root integrity_iint_tree = RB_ROOT; +static DEFINE_RWLOCK(integrity_iint_lock); static struct kmem_cache *iint_cache __read_mostly;
struct dentry *integrity_dir;
/* - * __integrity_iint_rb_find - return the iint associated with an inode - * @iint_rb_root: pointer to the root of the iint tree - * @inode: pointer to the inode - * @return: pointer to the iint if found, NULL otherwise + * __integrity_iint_find - return the iint associated with an inode */ -static struct integrity_iint_cache * - __integrity_iint_rb_find(const struct rb_root - *iint_rb_root, - const struct inode - *inode) +static struct integrity_iint_cache *__integrity_iint_find(struct inode *inode) { struct integrity_iint_cache *iint; - struct rb_node *n = iint_rb_root->rb_node; + struct rb_node *n = integrity_iint_tree.rb_node;
while (n) { iint = rb_entry(n, struct integrity_iint_cache, rb_node); @@ -62,37 +52,22 @@ static struct integrity_iint_cache * }
/* - * integrity_iint_rb_find - return the iint associated with an inode - * @iint_tree: pointer to the iint tree root node and the associated lock - * @inode: pointer to the inode - * @return: pointer to the iint if found, NULL otherwise + * integrity_iint_find - return the iint associated with an inode */ -struct integrity_iint_cache *integrity_iint_rb_find(struct integrity_iint_tree - *iint_tree, - const struct inode *inode) +struct integrity_iint_cache *integrity_iint_find(struct inode *inode) { struct integrity_iint_cache *iint;
if (!IS_IMA(inode)) return NULL;
- read_lock(&iint_tree->lock); - iint = __integrity_iint_rb_find(&iint_tree->root, inode); - read_unlock(&iint_tree->lock); + read_lock(&integrity_iint_lock); + iint = __integrity_iint_find(inode); + read_unlock(&integrity_iint_lock);
return iint; }
-/* - * integrity_iint_find - return the iint associated with an inode - * @inode: pointer to the inode - * @return: pointer to the iint if found, NULL otherwise - */ -struct integrity_iint_cache *integrity_iint_find(struct inode *inode) -{ - return integrity_iint_rb_find(&init_iint_tree, inode); -} - static void iint_free(struct integrity_iint_cache *iint) { kfree(iint->ima_hash); @@ -111,36 +86,13 @@ static void iint_free(struct integrity_iint_cache *iint) }
/** - * integrity_iint_tree_free - traverse the tree and free all nodes - * @iint_tree: pointer to the iint tree root node and the associated lock - * - * The tree cannot be in use. This function should be called only from the - * destructor when no locks are required. - */ -void integrity_iint_tree_free(struct integrity_iint_tree *iint_tree) -{ - struct rb_root *root = &iint_tree->root; - struct integrity_iint_cache *iint, *tmp; - - rbtree_postorder_for_each_entry_safe(iint, tmp, root, rb_node) { - iint_free(iint); - } - - iint_tree->root = RB_ROOT; -} - -/** - * integrity_inode_rb_get - find or allocate an iint associated with an inode - * @iint_tree: pointer to the iint tree root node and the associated lock + * integrity_inode_get - find or allocate an iint associated with an inode * @inode: pointer to the inode - * @return: pointer to the existing iint if found, pointer to the allocated iint - * if it didn't exist, NULL in case of error + * @return: allocated iint * * Caller must lock i_mutex */ -struct integrity_iint_cache *integrity_inode_rb_get(struct integrity_iint_tree - *iint_tree, - struct inode *inode) +struct integrity_iint_cache *integrity_inode_get(struct inode *inode) { struct rb_node **p; struct rb_node *node, *parent = NULL; @@ -154,7 +106,7 @@ struct integrity_iint_cache *integrity_inode_rb_get(struct integrity_iint_tree if (!iint_cache) panic("%s: lsm=integrity required.\n", __func__);
- iint = integrity_iint_rb_find(iint_tree, inode); + iint = integrity_iint_find(inode); if (iint) return iint;
@@ -162,9 +114,9 @@ struct integrity_iint_cache *integrity_inode_rb_get(struct integrity_iint_tree if (!iint) return NULL;
- write_lock(&iint_tree->lock); + write_lock(&integrity_iint_lock);
- p = &iint_tree->root.rb_node; + p = &integrity_iint_tree.rb_node; while (*p) { parent = *p; test_iint = rb_entry(parent, struct integrity_iint_cache, @@ -179,63 +131,33 @@ struct integrity_iint_cache *integrity_inode_rb_get(struct integrity_iint_tree node = &iint->rb_node; inode->i_flags |= S_IMA; rb_link_node(node, parent, p); - rb_insert_color(node, &iint_tree->root); + rb_insert_color(node, &integrity_iint_tree);
- write_unlock(&iint_tree->lock); + write_unlock(&integrity_iint_lock); return iint; }
/** - * integrity_inode_get - find or allocate an iint associated with an inode - * @inode: pointer to the inode - * @return: pointer to the existing iint if found, pointer to the allocated iint - * if it didn't exist, NULL in case of error - * - * Caller must lock i_mutex - */ -struct integrity_iint_cache *integrity_inode_get(struct inode *inode) -{ - return integrity_inode_rb_get(&init_iint_tree, inode); -} - -/** - * integrity_inode_rb_free - called on security_inode_free - * @iint_tree: pointer to the iint tree root node and the associated lock + * integrity_inode_free - called on security_inode_free * @inode: pointer to the inode * * Free the integrity information(iint) associated with an inode. */ -void integrity_inode_rb_free(struct integrity_iint_tree *iint_tree, - struct inode *inode) +void integrity_inode_free(struct inode *inode) { struct integrity_iint_cache *iint;
if (!IS_IMA(inode)) return;
- write_lock(&iint_tree->lock); - iint = __integrity_iint_rb_find(&iint_tree->root, inode); - if (!iint) { - write_unlock(&iint_tree->lock); - return; - } - rb_erase(&iint->rb_node, &iint_tree->root); - write_unlock(&iint_tree->lock); + write_lock(&integrity_iint_lock); + iint = __integrity_iint_find(inode); + rb_erase(&iint->rb_node, &integrity_iint_tree); + write_unlock(&integrity_iint_lock);
iint_free(iint); }
-/** - * integrity_inode_free - called on security_inode_free - * @inode: pointer to the inode - * - * Free the integrity information(iint) associated with an inode. - */ -void integrity_inode_free(struct inode *inode) -{ - integrity_inode_rb_free(&init_iint_tree, inode); -} - static void init_once(void *foo) { struct integrity_iint_cache *iint = foo; diff --git a/security/integrity/integrity.h b/security/integrity/integrity.h index 05f6eabef9fe..77e6819e8db8 100644 --- a/security/integrity/integrity.h +++ b/security/integrity/integrity.h @@ -184,20 +184,11 @@ static inline void ima_load_digest_lists(void) } #endif
-struct integrity_iint_tree { - rwlock_t lock; - struct rb_root root; -}; - /* rbtree tree calls to lookup, insert, delete * integrity data associated with an inode. */ struct integrity_iint_cache *integrity_iint_find(struct inode *inode);
-struct integrity_iint_cache *integrity_iint_rb_find(struct integrity_iint_tree - *iint_tree, - const struct inode *inode); - int integrity_kernel_read(struct file *file, loff_t offset, void *addr, unsigned long count);
@@ -208,8 +199,6 @@ int integrity_kernel_read(struct file *file, loff_t offset,
extern struct dentry *integrity_dir;
-extern struct integrity_iint_tree init_iint_tree; - struct modsig;
#ifdef CONFIG_INTEGRITY_SIGNATURE