]> git.ipfire.org Git - thirdparty/systemd.git/commitdiff
libfido2-util: accept cached pin in fido2_generate_hmac_hash()
authorMartin Wilck <mwilck@suse.com>
Mon, 17 Feb 2025 17:40:35 +0000 (18:40 +0100)
committerDaan De Meyer <daan.j.demeyer@gmail.com>
Tue, 4 Mar 2025 14:45:13 +0000 (15:45 +0100)
fido2_generate_hmac_hash() sets req->keyring to "fido2-pin" when
calling ask_password_auto(), suggesting that a key by this name
can be read from the kernel keyring. But the keyring is never
opened because the ASK_PASSWORD_ACCEPT_CACHED flag is not set.

Set ASK_PASSWORD_ACCEPT_CACHED to allow automated / scripted
setup of encrypted volumes with FIDO2. If the PIN turns out to
be invalid, clear ASK_PASSWORD_ACCEPT_CACHED to avoid retrying
and possible lockout.

(cherry picked from commit 505c2f21377019c058de16aa9e2d8db005e97e6f)

src/shared/libfido2-util.c

index ec5235860c2347e90724d0543b4d9e57d9d23627..309712bef67b5286e3459bd147e3907ed096d1e0 100644 (file)
@@ -853,6 +853,8 @@ int fido2_generate_hmac_hash(
                         return log_error_errno(SYNTHETIC_ERRNO(EINVAL),
                                                "Token asks for PIN but doesn't advertise 'clientPin' feature.");
 
+                AskPasswordFlags askpw_flags = ASK_PASSWORD_ACCEPT_CACHED;
+
                 for (;;) {
                         _cleanup_strv_free_erase_ char **pin = NULL;
                         AskPasswordRequest req = {
@@ -862,10 +864,12 @@ int fido2_generate_hmac_hash(
                                 .credential = askpw_credential,
                         };
 
-                        r = ask_password_auto(&req, USEC_INFINITY, /* flags= */ 0, &pin);
+                        r = ask_password_auto(&req, USEC_INFINITY, askpw_flags, &pin);
                         if (r < 0)
                                 return log_error_errno(r, "Failed to acquire user PIN: %m");
 
+                        askpw_flags &= ~ASK_PASSWORD_ACCEPT_CACHED;
+
                         r = FIDO_ERR_PIN_INVALID;
                         STRV_FOREACH(i, pin) {
                                 if (isempty(*i)) {