int ima_restore_measurement_list(loff_t bufsize, void *buf);
int ima_measurements_show(struct seq_file *m, void *v);
int __init ima_init_htable(void);
-unsigned long ima_get_binary_runtime_size(void);
+unsigned long ima_get_binary_runtime_size(enum binary_lists binary_list);
int ima_init_template(void);
void ima_init_template_list(void);
int __init ima_init_digests(void);
long len;
int n;
- buf_size = ima_get_binary_runtime_size();
+ buf_size = ima_get_binary_runtime_size(BINARY);
len = atomic_long_read(&ima_num_records[BINARY]);
n = scnprintf(ima_kexec_event, IMA_KEXEC_EVENT_LEN,
else
extra_memory = CONFIG_IMA_KEXEC_EXTRA_MEMORY_KB * 1024;
- binary_runtime_size = ima_get_binary_runtime_size() + extra_memory;
+ binary_runtime_size = ima_get_binary_runtime_size(BINARY) +
+ extra_memory;
if (binary_runtime_size >= ULONG_MAX - PAGE_SIZE)
kexec_segment_size = ULONG_MAX;
LIST_HEAD(ima_measurements); /* list of all measurements */
#ifdef CONFIG_IMA_KEXEC
-static unsigned long binary_runtime_size;
+static unsigned long binary_runtime_size[BINARY__LAST];
#else
-static unsigned long binary_runtime_size = ULONG_MAX;
+static unsigned long binary_runtime_size[BINARY__LAST] = {
+ [0 ... BINARY__LAST - 1] = ULONG_MAX
+};
#endif
atomic_long_t ima_num_records[BINARY__LAST] = {
return size;
}
+static void ima_update_binary_runtime_size(struct ima_template_entry *entry,
+ enum binary_lists binary_list)
+{
+ int size;
+
+ if (binary_runtime_size[binary_list] == ULONG_MAX)
+ return;
+
+ size = get_binary_runtime_size(entry);
+ binary_runtime_size[binary_list] =
+ (binary_runtime_size[binary_list] < ULONG_MAX - size) ?
+ binary_runtime_size[binary_list] + size : ULONG_MAX;
+}
+
/* ima_add_template_entry helper function:
* - Add template entry to the measurement list and hash table, for
* all entries except those carried across kexec.
hlist_add_head_rcu(&qe->hnext, &htable[key]);
}
- if (binary_runtime_size != ULONG_MAX) {
- int size;
-
- size = get_binary_runtime_size(entry);
- binary_runtime_size = (binary_runtime_size < ULONG_MAX - size) ?
- binary_runtime_size + size : ULONG_MAX;
- }
+ ima_update_binary_runtime_size(entry, BINARY);
return 0;
}
* entire binary_runtime_measurement list, including the ima_kexec_hdr
* structure.
*/
-unsigned long ima_get_binary_runtime_size(void)
+unsigned long ima_get_binary_runtime_size(enum binary_lists binary_list)
{
- if (binary_runtime_size >= (ULONG_MAX - sizeof(struct ima_kexec_hdr)))
+ unsigned long val;
+
+ mutex_lock(&ima_extend_list_mutex);
+ val = binary_runtime_size[binary_list];
+ mutex_unlock(&ima_extend_list_mutex);
+
+ if (val >= (ULONG_MAX - sizeof(struct ima_kexec_hdr)))
return ULONG_MAX;
else
- return binary_runtime_size + sizeof(struct ima_kexec_hdr);
+ return val + sizeof(struct ima_kexec_hdr);
}
static int ima_pcr_extend(struct tpm_digest *digests_arg, int pcr)