Skip to content

Commit 0ca0cf9

Browse files
committed
Merge tag 'integrity-v6.14' of git://git.kernel.org/pub/scm/linux/kernel/git/zohar/linux-integrity
Pull integrity updates from Mimi Zohar: "There's just a couple of changes: two kernel messages addressed, a measurement policy collision addressed, and one policy cleanup. Please note that the contents of the IMA measurement list is potentially affected. The builtin tmpfs IMA policy rule change might introduce additional measurements, while detecting a reboot might eliminate some measurements" * tag 'integrity-v6.14' of git://git.kernel.org/pub/scm/linux/kernel/git/zohar/linux-integrity: ima: ignore suffixed policy rule comments ima: limit the builtin 'tcb' dont_measure tmpfs policy rule ima: kexec: silence RCU list traversal warning ima: Suspend PCR extends and log appends when rebooting
2 parents 7dd457a + 4785ed3 commit 0ca0cf9

File tree

5 files changed

+52
-3
lines changed

5 files changed

+52
-3
lines changed

security/integrity/ima/ima.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -278,6 +278,7 @@ unsigned long ima_get_binary_runtime_size(void);
278278
int ima_init_template(void);
279279
void ima_init_template_list(void);
280280
int __init ima_init_digests(void);
281+
void __init ima_init_reboot_notifier(void);
281282
int ima_lsm_policy_change(struct notifier_block *nb, unsigned long event,
282283
void *lsm_data);
283284

security/integrity/ima/ima_init.c

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -152,6 +152,8 @@ int __init ima_init(void)
152152

153153
ima_init_key_queue();
154154

155+
ima_init_reboot_notifier();
156+
155157
ima_measure_critical_data("kernel_info", "kernel_version",
156158
UTS_RELEASE, strlen(UTS_RELEASE), false,
157159
NULL, 0);

security/integrity/ima/ima_kexec.c

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -37,7 +37,8 @@ static int ima_dump_measurement_list(unsigned long *buffer_size, void **buffer,
3737

3838
memset(&khdr, 0, sizeof(khdr));
3939
khdr.version = 1;
40-
list_for_each_entry_rcu(qe, &ima_measurements, later) {
40+
/* This is an append-only list, no need to hold the RCU read lock */
41+
list_for_each_entry_rcu(qe, &ima_measurements, later, true) {
4142
if (file.count < file.size) {
4243
khdr.count++;
4344
ima_measurements_show(&file, qe);

security/integrity/ima/ima_policy.c

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -148,7 +148,8 @@ static struct ima_rule_entry dont_measure_rules[] __ro_after_init = {
148148
{.action = DONT_MEASURE, .fsmagic = PROC_SUPER_MAGIC, .flags = IMA_FSMAGIC},
149149
{.action = DONT_MEASURE, .fsmagic = SYSFS_MAGIC, .flags = IMA_FSMAGIC},
150150
{.action = DONT_MEASURE, .fsmagic = DEBUGFS_MAGIC, .flags = IMA_FSMAGIC},
151-
{.action = DONT_MEASURE, .fsmagic = TMPFS_MAGIC, .flags = IMA_FSMAGIC},
151+
{.action = DONT_MEASURE, .fsmagic = TMPFS_MAGIC, .func = FILE_CHECK,
152+
.flags = IMA_FSMAGIC | IMA_FUNC},
152153
{.action = DONT_MEASURE, .fsmagic = DEVPTS_SUPER_MAGIC, .flags = IMA_FSMAGIC},
153154
{.action = DONT_MEASURE, .fsmagic = BINFMTFS_MAGIC, .flags = IMA_FSMAGIC},
154155
{.action = DONT_MEASURE, .fsmagic = SECURITYFS_MAGIC, .flags = IMA_FSMAGIC},
@@ -1431,7 +1432,7 @@ static int ima_parse_rule(char *rule, struct ima_rule_entry *entry)
14311432
int token;
14321433
unsigned long lnum;
14331434

1434-
if (result < 0)
1435+
if (result < 0 || *p == '#') /* ignore suffixed comment */
14351436
break;
14361437
if ((*p == '\0') || (*p == ' ') || (*p == '\t'))
14371438
continue;

security/integrity/ima/ima_queue.c

Lines changed: 44 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@
1616
*/
1717

1818
#include <linux/rculist.h>
19+
#include <linux/reboot.h>
1920
#include <linux/slab.h>
2021
#include "ima.h"
2122

@@ -44,6 +45,12 @@ struct ima_h_table ima_htable = {
4445
*/
4546
static DEFINE_MUTEX(ima_extend_list_mutex);
4647

48+
/*
49+
* Used internally by the kernel to suspend measurements.
50+
* Protected by ima_extend_list_mutex.
51+
*/
52+
static bool ima_measurements_suspended;
53+
4754
/* lookup up the digest value in the hash table, and return the entry */
4855
static struct ima_queue_entry *ima_lookup_digest_entry(u8 *digest_value,
4956
int pcr)
@@ -168,6 +175,18 @@ int ima_add_template_entry(struct ima_template_entry *entry, int violation,
168175
int result = 0, tpmresult = 0;
169176

170177
mutex_lock(&ima_extend_list_mutex);
178+
179+
/*
180+
* Avoid appending to the measurement log when the TPM subsystem has
181+
* been shut down while preparing for system reboot.
182+
*/
183+
if (ima_measurements_suspended) {
184+
audit_cause = "measurements_suspended";
185+
audit_info = 0;
186+
result = -ENODEV;
187+
goto out;
188+
}
189+
171190
if (!violation && !IS_ENABLED(CONFIG_IMA_DISABLE_HTABLE)) {
172191
if (ima_lookup_digest_entry(digest, entry->pcr)) {
173192
audit_cause = "hash_exists";
@@ -211,6 +230,31 @@ int ima_restore_measurement_entry(struct ima_template_entry *entry)
211230
return result;
212231
}
213232

233+
static void ima_measurements_suspend(void)
234+
{
235+
mutex_lock(&ima_extend_list_mutex);
236+
ima_measurements_suspended = true;
237+
mutex_unlock(&ima_extend_list_mutex);
238+
}
239+
240+
static int ima_reboot_notifier(struct notifier_block *nb,
241+
unsigned long action,
242+
void *data)
243+
{
244+
ima_measurements_suspend();
245+
246+
return NOTIFY_DONE;
247+
}
248+
249+
static struct notifier_block ima_reboot_nb = {
250+
.notifier_call = ima_reboot_notifier,
251+
};
252+
253+
void __init ima_init_reboot_notifier(void)
254+
{
255+
register_reboot_notifier(&ima_reboot_nb);
256+
}
257+
214258
int __init ima_init_digests(void)
215259
{
216260
u16 digest_size;

0 commit comments

Comments
 (0)