IMA: Measure kernel version in early boot
diff mbox series

Message ID
State New, archived
Headers show
  • IMA: Measure kernel version in early boot
Related show

Commit Message

Raphael Gianotti Oct. 23, 2020, 10:59 p.m. UTC
The digital integrity of a kernel can be verified by the boot loader on
cold boot, and during kexec, by the current running kernel, before it is
loaded. However, it is still possible that the new kernel being loaded is
older then the current kernel, and/or has known vulnerabilities.
Therefore, it is imperative that an attestation service be able to verify
the version of the kernel being loaded on the client, from cold boot and
subsequent kexec system calls, ensuring that only kernels with versions
known to be good are loaded.

Measure the kernel version using ima_measure_critical_data() early on in
the boot sequence, reducing the chances of known kernel vulnerabilities
being exploited. With IMA being part of the kernel, this overall approach
makes the measurement itself more trustworthy. ima_measure_critical_data()
also makes use of queuing, thus the version string stored in linux_banner
can queued for measuring in ima_init, with the actual measurement taking
place as soon as the IMA subsystem is ready.

Adding the following line to the ima policy file (/etc/ima/ima-policy)
will enable this measurement:

        measure func=CRITICAL_DATA data_sources=kernel_version template=ima-buf

To extract the measured data after boot, the following command can be used:

        grep -m 1 "kernel_version" \

Sample output from the command above:

        10 355335b64c90d5810cf0d869d84a4076ebcabd89 ima-buf sha256:05260b2
        kernel_version 4c696e75782076657273696f6e20352e392e302d7263322d313

The above corresponds to the following (decoded) version string:

        Linux version 5.9.0-rc2-16267-gc8b3d5ae4b1a-dirty (rapha@rapha
        -Virtual-Machine) (aarch64-linux-gnu-gcc (Ubuntu/Linaro 7.5.0-
        3ubuntu1~18.04) 7.5.0, GNU ld (GNU Binutils for Ubuntu) 2.30)
        #16 SMP Wed Oct 14 15:51:39 PDT 2020

Signed-off-by: Raphael Gianotti <>
 security/integrity/ima/Kconfig          | 10 ++++++++++
 security/integrity/ima/ima.h            |  1 +
 security/integrity/ima/ima_main.c       |  5 ++++-
 security/integrity/ima/ima_queue_data.c |  5 +++--
 4 files changed, 18 insertions(+), 3 deletions(-)

diff mbox series

diff --git a/security/integrity/ima/Kconfig b/security/integrity/ima/Kconfig
index fec7e74978ed..7ad3ddb83c06 100644
--- a/security/integrity/ima/Kconfig
+++ b/security/integrity/ima/Kconfig
@@ -328,3 +328,13 @@  config IMA_SECURE_AND_OR_TRUSTED_BOOT
           This option is selected by architectures to enable secure and/or
           trusted boot based on IMA runtime policies.
+       bool
+       depends on IMA
+       default y
+       help
+	  This option enables measuring the kernel version and causes it to
+	  be measured during kernel boot.
+	  This option requires the following IMA rule to be set:
+	  measure func=CRITICAL_DATA data_sources=kernel_version template=ima-buf
diff --git a/security/integrity/ima/ima.h b/security/integrity/ima/ima.h
index e99e5e0db720..9d4b4a6027db 100644
--- a/security/integrity/ima/ima.h
+++ b/security/integrity/ima/ima.h
@@ -230,6 +230,7 @@  struct modsig;
 #define __ima_supported_kernel_data_sources(source)	\
 	source(MIN_SOURCE, min_source)			\
+	source(KERNEL_VERSION, kernel_version)		\
 	source(MAX_SOURCE, max_source)
 #define __ima_enum_stringify(ENUM, str) (#str),
diff --git a/security/integrity/ima/ima_main.c b/security/integrity/ima/ima_main.c
index 5162917e6bf2..e128b27776e2 100644
--- a/security/integrity/ima/ima_main.c
+++ b/security/integrity/ima/ima_main.c
@@ -948,8 +948,11 @@  static int __init init_ima(void)
 	if (error)
 		pr_warn("Couldn't register LSM notifier, error %d\n", error);
-	if (!error)
+	if (!error) {
+		ima_measure_critical_data("kernel_version", "kernel_version",
+					  linux_banner, strlen(linux_banner), false);
+	}
 	return error;
diff --git a/security/integrity/ima/ima_queue_data.c b/security/integrity/ima/ima_queue_data.c
index 4871ed3af436..fbd0a7bf668e 100644
--- a/security/integrity/ima/ima_queue_data.c
+++ b/security/integrity/ima/ima_queue_data.c
@@ -35,8 +35,9 @@  static bool timer_expired;
 static inline bool ima_queuing_enabled(void)