]> git.ipfire.org Git - thirdparty/systemd.git/commitdiff
veritysetup: optionally measure Verity once we activated it
authorLennart Poettering <lennart@amutable.com>
Wed, 11 Feb 2026 12:13:21 +0000 (13:13 +0100)
committerLennart Poettering <lennart@amutable.com>
Tue, 17 Feb 2026 21:00:14 +0000 (22:00 +0100)
As in the previous commit, also enable the measurement logic when
activating Verity via veritsetup rather than the dissection logic.

The logic stays close to the interface of cryptsetup for measuring the
volume key.

man/veritytab.xml
src/veritysetup/veritysetup.c

index 9b131e350c46c6f147613f8ac8973c3d0af53681..913acad9a2db4022f9bdeb9b8a1c1427f8a9b3b9 100644 (file)
@@ -298,6 +298,18 @@ This is based on crypttab(5).
         </listitem>
       </varlistentry>
 
+      <varlistentry>
+        <term><option>tpm2-measure-nvpcr=</option></term>
+
+        <listitem><para>Takes a boolean argument, or an NvPCR name as argument. May be used to enable
+        automatic measurement of the volume name and Verity root hash, as well as the serials and issuers of
+        the certificates used to generate the provided signatures (if any) will be measured. Passing false
+        disables the mechanism. Passing true enables measurement into the <literal>verity</literal> NvPCR. If
+        any other string is specified this selects the NvPCR to measure into by name.</para>
+
+        <xi:include href="version-info.xml" xpointer="v260"/></listitem>
+      </varlistentry>
+
     </variablelist>
 
     <para>At early boot and when the system manager configuration is
index 91b5bcaaa28d3f26826c5560e46c811361a4f327..e2135562c1f126dfb70a85df5b7ecac6d000a72e 100644 (file)
 #include "main-func.h"
 #include "parse-util.h"
 #include "path-util.h"
+#include "pcrextend-util.h"
 #include "pretty-print.h"
 #include "string-util.h"
 #include "strv.h"
+#include "tpm2-util.h"
 #include "verbs.h"
 
 static char *arg_hash = NULL; /* the hash algorithm */
@@ -38,12 +40,14 @@ static uint64_t arg_fec_roots = 2;
 static void *arg_root_hash_signature = NULL;
 static size_t arg_root_hash_signature_size = 0;
 static bool arg_root_hash_signature_auto = false;
+static char *arg_tpm2_measure_nvpcr = NULL;
 
 STATIC_DESTRUCTOR_REGISTER(arg_hash, freep);
 STATIC_DESTRUCTOR_REGISTER(arg_salt, freep);
 STATIC_DESTRUCTOR_REGISTER(arg_uuid, freep);
 STATIC_DESTRUCTOR_REGISTER(arg_fec_what, freep);
 STATIC_DESTRUCTOR_REGISTER(arg_root_hash_signature, freep);
+STATIC_DESTRUCTOR_REGISTER(arg_tpm2_measure_nvpcr, freep);
 
 static int help(void) {
         _cleanup_free_ char *link = NULL;
@@ -142,7 +146,7 @@ static int parse_options(const char *options) {
 
         for (;;) {
                 _cleanup_free_ char *word = NULL;
-                char *val;
+                const char *val;
 
                 r = extract_first_word(&options, &word, ",", EXTRACT_DONT_COALESCE_SEPARATORS | EXTRACT_UNESCAPE_SEPARATORS);
                 if (r < 0)
@@ -290,6 +294,21 @@ static int parse_options(const char *options) {
                         if (r < 0)
                                 return r;
 
+                } else if ((val = startswith(word, "tpm2-measure-nvpcr="))) {
+                        r = isempty(val) ? 0 : parse_boolean(val);
+                        if (r == 0) {
+                                arg_tpm2_measure_nvpcr = mfree(arg_tpm2_measure_nvpcr);
+                                return 0;
+                        }
+                        if (r > 0)
+                                val = "verity";
+                        else if (!tpm2_nvpcr_name_is_valid(val)) {
+                                log_warning("Invalid NvPCR name, ignoring: %s", word);
+                                return 0;
+                        }
+
+                        if (free_and_strdup(&arg_tpm2_measure_nvpcr, val) < 0)
+                                return log_oom();
                 } else
                         log_warning("Encountered unknown option '%s', ignoring.", word);
         }
@@ -423,6 +442,11 @@ static int verb_attach(int argc, char *argv[], void *userdata) {
         if (r < 0)
                 return log_error_errno(r, "Failed to set up verity device '%s': %m", volume);
 
+        (void) pcrextend_verity_now(
+                        volume,
+                        &IOVEC_MAKE(rh, rh_size),
+                        &IOVEC_MAKE(arg_root_hash_signature, arg_root_hash_signature_size));
+
         return 0;
 }