]> git.ipfire.org Git - thirdparty/systemd.git/commitdiff
cryptsetup: support keyfile-timeout for using a device as the key file
authorChih-Hsuan Yen <yan12125@gmail.com>
Thu, 4 Aug 2022 16:45:33 +0000 (00:45 +0800)
committerLuca Boccassi <luca.boccassi@gmail.com>
Mon, 8 Aug 2022 16:03:28 +0000 (17:03 +0100)
Closes https://github.com/systemd/systemd/issues/21993

man/crypttab.xml
src/cryptsetup/cryptsetup-generator.c

index 22411166a8dfe31b7b24a684ff944a38b1068dac..a296949595ec47fce822d02b7d697deb604248db 100644 (file)
         <term><option>keyfile-timeout=</option></term>
 
         <listitem><para> Specifies the timeout for the device on
-        which the key file resides and falls back to a password if
-        it could not be mounted. See
+        which the key file resides or the device used as the key file,
+        and falls back to a password if it could not be accessed. See
         <citerefentry><refentrytitle>systemd-cryptsetup-generator</refentrytitle><manvolnum>8</manvolnum></citerefentry>
         for key files on external devices.
         </para></listitem>
index 8f5ad67f48ee4b14ba4546ae84d112d6c91c5d18..07903f1044e7cb0524368c570ba639fa7f1f2c34 100644 (file)
@@ -227,9 +227,11 @@ static int generate_device_umount(const char *name,
         return 0;
 }
 
-static int print_dependencies(FILE *f, const char* device_path) {
+static int print_dependencies(FILE *f, const char* device_path, const char* timeout_value, bool canfail) {
         int r;
 
+        assert(!canfail || timeout_value);
+
         if (STR_IN_SET(device_path, "-", "none"))
                 /* None, nothing to do */
                 return 0;
@@ -259,9 +261,16 @@ static int print_dependencies(FILE *f, const char* device_path) {
                 if (r < 0)
                         return log_error_errno(r, "Failed to generate unit name: %m");
 
-                fprintf(f,
-                        "After=%1$s\n"
-                        "Requires=%1$s\n", unit);
+                fprintf(f, "After=%1$s\n", unit);
+                if (canfail) {
+                        fprintf(f, "Wants=%1$s\n", unit);
+                        r = write_drop_in_format(arg_dest, unit, 90, "device-timeout",
+                                "# Automatically generated by systemd-cryptsetup-generator \n\n"
+                                "[Unit]\nJobRunningTimeoutSec=%s", timeout_value);
+                        if (r < 0)
+                                return log_error_errno(r, "Failed to write device drop-in: %m");
+                } else
+                        fprintf(f, "Requires=%1$s\n", unit);
         } else {
                 /* Regular file, add mount dependency */
                 _cleanup_free_ char *escaped_path = specifier_escape(device_path);
@@ -463,14 +472,18 @@ static int create_disk(
                         netdev ? "remote-cryptsetup.target" : "cryptsetup.target");
 
         if (key_file && !keydev) {
-                r = print_dependencies(f, key_file);
+                r = print_dependencies(f, key_file,
+                        keyfile_timeout_value,
+                        /* canfail= */ keyfile_can_timeout > 0);
                 if (r < 0)
                         return r;
         }
 
         /* Check if a header option was specified */
         if (detached_header > 0 && !headerdev) {
-                r = print_dependencies(f, header_path);
+                r = print_dependencies(f, header_path,
+                        NULL,
+                        /* canfail= */ false); /* header is always necessary */
                 if (r < 0)
                         return r;
         }