diff options
| -rw-r--r-- | include/linux/fs.h | 2 | ||||
| -rw-r--r-- | security/integrity/ima/ima_iint.c | 16 | ||||
| -rw-r--r-- | security/integrity/ima/ima_main.c | 1 |
3 files changed, 14 insertions, 5 deletions
diff --git a/include/linux/fs.h b/include/linux/fs.h index 01e3a0047fed..bb77843de9d6 100644 --- a/include/linux/fs.h +++ b/include/linux/fs.h | |||
| @@ -235,6 +235,7 @@ struct inodes_stat_t { | |||
| 235 | #define S_NOCMTIME 128 /* Do not update file c/mtime */ | 235 | #define S_NOCMTIME 128 /* Do not update file c/mtime */ |
| 236 | #define S_SWAPFILE 256 /* Do not truncate: swapon got its bmaps */ | 236 | #define S_SWAPFILE 256 /* Do not truncate: swapon got its bmaps */ |
| 237 | #define S_PRIVATE 512 /* Inode is fs-internal */ | 237 | #define S_PRIVATE 512 /* Inode is fs-internal */ |
| 238 | #define S_IMA 1024 /* Inode has an associated IMA struct */ | ||
| 238 | 239 | ||
| 239 | /* | 240 | /* |
| 240 | * Note that nosuid etc flags are inode-specific: setting some file-system | 241 | * Note that nosuid etc flags are inode-specific: setting some file-system |
| @@ -269,6 +270,7 @@ struct inodes_stat_t { | |||
| 269 | #define IS_NOCMTIME(inode) ((inode)->i_flags & S_NOCMTIME) | 270 | #define IS_NOCMTIME(inode) ((inode)->i_flags & S_NOCMTIME) |
| 270 | #define IS_SWAPFILE(inode) ((inode)->i_flags & S_SWAPFILE) | 271 | #define IS_SWAPFILE(inode) ((inode)->i_flags & S_SWAPFILE) |
| 271 | #define IS_PRIVATE(inode) ((inode)->i_flags & S_PRIVATE) | 272 | #define IS_PRIVATE(inode) ((inode)->i_flags & S_PRIVATE) |
| 273 | #define IS_IMA(inode) ((inode)->i_flags & S_IMA) | ||
| 272 | 274 | ||
| 273 | /* the read-only stuff doesn't really belong here, but any other place is | 275 | /* the read-only stuff doesn't really belong here, but any other place is |
| 274 | probably as bad and I don't want to create yet another include file. */ | 276 | probably as bad and I don't want to create yet another include file. */ |
diff --git a/security/integrity/ima/ima_iint.c b/security/integrity/ima/ima_iint.c index 969a1c1cb333..c442e47b6785 100644 --- a/security/integrity/ima/ima_iint.c +++ b/security/integrity/ima/ima_iint.c | |||
| @@ -59,6 +59,9 @@ struct ima_iint_cache *ima_iint_find(struct inode *inode) | |||
| 59 | { | 59 | { |
| 60 | struct ima_iint_cache *iint; | 60 | struct ima_iint_cache *iint; |
| 61 | 61 | ||
| 62 | if (!IS_IMA(inode)) | ||
| 63 | return NULL; | ||
| 64 | |||
| 62 | spin_lock(&ima_iint_lock); | 65 | spin_lock(&ima_iint_lock); |
| 63 | iint = __ima_iint_find(inode); | 66 | iint = __ima_iint_find(inode); |
| 64 | spin_unlock(&ima_iint_lock); | 67 | spin_unlock(&ima_iint_lock); |
| @@ -91,6 +94,7 @@ int ima_inode_alloc(struct inode *inode) | |||
| 91 | new_iint->inode = inode; | 94 | new_iint->inode = inode; |
| 92 | new_node = &new_iint->rb_node; | 95 | new_node = &new_iint->rb_node; |
| 93 | 96 | ||
| 97 | mutex_lock(&inode->i_mutex); /* i_flags */ | ||
| 94 | spin_lock(&ima_iint_lock); | 98 | spin_lock(&ima_iint_lock); |
| 95 | 99 | ||
| 96 | p = &ima_iint_tree.rb_node; | 100 | p = &ima_iint_tree.rb_node; |
| @@ -107,14 +111,17 @@ int ima_inode_alloc(struct inode *inode) | |||
| 107 | goto out_err; | 111 | goto out_err; |
| 108 | } | 112 | } |
| 109 | 113 | ||
| 114 | inode->i_flags |= S_IMA; | ||
| 110 | rb_link_node(new_node, parent, p); | 115 | rb_link_node(new_node, parent, p); |
| 111 | rb_insert_color(new_node, &ima_iint_tree); | 116 | rb_insert_color(new_node, &ima_iint_tree); |
| 112 | 117 | ||
| 113 | spin_unlock(&ima_iint_lock); | 118 | spin_unlock(&ima_iint_lock); |
| 119 | mutex_unlock(&inode->i_mutex); /* i_flags */ | ||
| 114 | 120 | ||
| 115 | return 0; | 121 | return 0; |
| 116 | out_err: | 122 | out_err: |
| 117 | spin_unlock(&ima_iint_lock); | 123 | spin_unlock(&ima_iint_lock); |
| 124 | mutex_unlock(&inode->i_mutex); /* i_flags */ | ||
| 118 | iint_free(new_iint); | 125 | iint_free(new_iint); |
| 119 | 126 | ||
| 120 | return rc; | 127 | return rc; |
| @@ -135,15 +142,14 @@ void ima_inode_free(struct inode *inode) | |||
| 135 | 142 | ||
| 136 | inode->i_readcount = 0; | 143 | inode->i_readcount = 0; |
| 137 | 144 | ||
| 145 | if (!IS_IMA(inode)) | ||
| 146 | return; | ||
| 147 | |||
| 138 | spin_lock(&ima_iint_lock); | 148 | spin_lock(&ima_iint_lock); |
| 139 | iint = __ima_iint_find(inode); | 149 | iint = __ima_iint_find(inode); |
| 140 | if (iint) | 150 | rb_erase(&iint->rb_node, &ima_iint_tree); |
| 141 | rb_erase(&iint->rb_node, &ima_iint_tree); | ||
| 142 | spin_unlock(&ima_iint_lock); | 151 | spin_unlock(&ima_iint_lock); |
| 143 | 152 | ||
| 144 | if (!iint) | ||
| 145 | return; | ||
| 146 | |||
| 147 | iint_free(iint); | 153 | iint_free(iint); |
| 148 | } | 154 | } |
| 149 | 155 | ||
diff --git a/security/integrity/ima/ima_main.c b/security/integrity/ima/ima_main.c index 1dccafef7494..60dd61527b1e 100644 --- a/security/integrity/ima/ima_main.c +++ b/security/integrity/ima/ima_main.c | |||
| @@ -211,6 +211,7 @@ void ima_file_free(struct file *file) | |||
| 211 | 211 | ||
| 212 | if (!iint_initialized || !S_ISREG(inode->i_mode)) | 212 | if (!iint_initialized || !S_ISREG(inode->i_mode)) |
| 213 | return; | 213 | return; |
| 214 | |||
| 214 | iint = ima_iint_find(inode); | 215 | iint = ima_iint_find(inode); |
| 215 | 216 | ||
| 216 | if (iint) | 217 | if (iint) |
