Public bug reported:
[What happened]
With SSSD smartcard authentication configured (YubiKey PIV, certmap rule mapping
the certificate to a local user), the GDM login screen does not automatically
fill in my username when the machine boots with the YubiKey already inserted.
I have to pick my user from the user list manually, after which smartcard PIN
auth proceeds normally.
[What I expected]
The greeter should begin smartcard verification with no username, let pam_sss
resolve the certificate to a user, and prefill it. This is the documented and
intended behaviour, and gnome-shell explicitly aims for it — gdm/util.js
`_initSmartcardManager()` carries the comment:
// We check for smartcards right away, since an inserted smartcard
// at startup should result in immediately initiating authentication.
[Steps to reproduce]
1. Configure SSSD smartcard auth for a local user (pam_cert_auth = true, a
[certmap/...] rule matching the PIV cert, trust anchor in
/etc/sssd/pki/sssd_auth_ca_db.pem).
2. Insert the smartcard and boot / restart gdm so the card is present *before*
the greeter starts.
3. Observe: the username is not prefilled.
4. Now unplug and re-insert the card at the greeter. The username IS prefilled.
Step 4 is the key signal: it only fails when the card is present during the
greeter's initial setup.
[This is not an SSSD misconfiguration]
I verified the whole SSSD path works:
- p11_child, run against the configured CA DB, returns the token and
certificate successfully:
`/usr/libexec/sssd/p11_child --pre --ca_db=/etc/sssd/pki/sssd_auth_ca_db.pem`
-> emits token name, module, key id, label and cert.
- The certmap rule loads (sssd_pam.log):
`p11_refresh_certmap_ctx: Trying to add rule
[user][-1][<SUBJECT>^CN=user$][(user)].`
- The cert -> user lookup succeeds:
`pam_forwarder_lookup_by_cert_done: Found [1] certificates and [1] related
users.`
- /etc/pam.d/gdm-smartcard has the correct
`pam_sss.so allow_missing_name try_cert_auth`.
Crucially, SSSD's PAM responder records *no* request at the time of the failed
attempt. gdm3 (with debug enabled) logs `starting conversation gdm-smartcard` at
22:55:46, but the first gdm-smartcard transaction to reach sssd_pam.log is 26
seconds later, and it already arrives with `user:` and `logon name:` set — i.e.
after I selected my name by hand. The username-less BeginVerification never
lands, so SSSD is never asked to map the certificate.
[Root cause]
gnome-shell aborts the username-less verification with an unhandled promise
rejection. Line numbers below are from the JS shipped in
gnome-shell 46.0-0ubuntu6~24.04.15 (extracted from
/usr/lib/gnome-shell/libshell-14.so). Full stack trace attached.
1. Card already inserted -> `_initSmartcardManager()` -> `_checkForSmartcard()`
-> emits `smartcard-status-changed`.
2. `_onSmartcardStatusChanged` (authPrompt.js:542) -> `reset()` -> `_onReset`
-> `_hideUserListAndBeginVerification` -> `begin()` -> `_getUserVerifier()`
-> `_beginVerification()`.
3. `_beginVerification()` (util.js:1044):
this._startService(foregroundService); // line 1053
this._startBackgroundServices();
this._generateMechanismsFromDiscreteServices(); // line 1055
`_startService` is `async` and is NOT awaited. It acquires the hold and then
suspends on `await this._userVerifier.call_begin_verification(...)` — the
very
call that would let pam_sss supply the username
(`foregroundServiceDeterminesUsername()` returns true for smartcard).
4. Line 1055 then runs synchronously and emits `mechanisms-list-changed` ->
`_onAuthMechanismsListChanged` (authPrompt.js:404) -> `_onMechanismsChanged`
(loginDialog.js:1047) -> `AuthMenuButton.setActiveItem`
(authMenuButton.js:202)
-> `active-item-changed` -> the handler at loginDialog.js:632 ->
`setForegroundMechanism` -> emits `foreground-mechanism-changed`.
5. `_onForegroundMechanismChanged` (authPrompt.js:545) calls `reset()`
**unconditionally**, which re-enters `_getUserVerifier()` ->
`_clearUserVerifier()` -> `this._userVerifier.run_dispose()`.
6. The suspended `_startService` from step 3 resumes against the freed proxy:
"Object Gdm.UserVerifierProxy (0x...), has been already disposed". The
promise rejects and nothing catches it, because line 1053 neither awaits nor
attaches a .catch().
Note the asymmetry: `_onSmartcardStatusChanged` (authPrompt.js:535-539) already
has a re-entrancy guard for exactly this hazard:
if (this._userVerifier.serviceIsDefault(GdmUtil.SMARTCARD_SERVICE_NAME) &&
(this.verificationStatus === AuthPromptStatus.VERIFYING ||
this.verificationStatus === AuthPromptStatus.VERIFICATION_IN_PROGRESS)
&&
this.smartcardDetected)
return;
`_onForegroundMechanismChanged` has no equivalent guard.
This only triggers on the first population of the mechanism list, because both
`AuthMenuButton.setActiveItem` and `ShellUserVerifier.setForegroundMechanism`
early-return when the mechanism is unchanged. That is exactly why it fails at
boot (card present during initial setup) but works on re-insertion.
[Suggested fix]
Either of:
- Guard `_onForegroundMechanismChanged` against re-entering reset while a
verification is already in flight, mirroring `_onSmartcardStatusChanged`; or
- Await (or at minimum `.catch()`) `_startService()` at util.js:1053, and don't
emit a mechanism-list change that can re-enter `reset()` from inside
`_beginVerification()`.
[Scope]
authMenuButton.js, `_generateMechanismsFromDiscreteServices` and
`setForegroundMechanism` are not in upstream GNOME 46; they arrive via the
Ubuntu authd patch set (d/changelog: "debian/patches/authd: Cleanup code and fix
mechanism switch handling"). So this looks Ubuntu-specific rather than upstream.
Note `com.ubuntu.login-screen enable-authd-authentication=false` does NOT avoid
it: `_generateMechanismsFromDiscreteServices` is not gated on that key (it
synthesizes mechanisms from the discrete gdm-smartcard/gdm-password services;
the key only gates the gdm-authd unified service at util.js:899).
[Workaround]
Unplug and re-insert the smartcard at the login screen.
[Possibly related]
LP#2161662 "smartcard auth breaks lockscreen" — different symptom and a much
newer gnome-shell (50.1 on 26.04), but same area of code.
[Versions]
Ubuntu 24.04.5 LTS, x11 session
gnome-shell 46.0-0ubuntu6~24.04.15
gdm3 46.2-1ubuntu1~24.04.9
sssd 2.9.4-1.1ubuntu6.8
libpam-sss 2.9.4-1.1ubuntu6.8
opensc 0.25.0~rc1-1ubuntu0.2
pcscd 2.0.3-1build1
kernel 7.0.0-38-generic
Hardware token: YubiKey (PIV), self-signed PIV certs, trust anchor installed in
/etc/sssd/pki/sssd_auth_ca_db.pem
** Affects: gnome-shell (Ubuntu)
Importance: Undecided
Status: New
** Attachment added: "Trace of the smartcard logic"
https://bugs.launchpad.net/bugs/2170508/+attachment/6008319/+files/gnome-shell-smartcard-trace.txt
--
You received this bug notification because you are a member of Ubuntu
Desktop Bugs, which is subscribed to gnome-shell in Ubuntu.
https://bugs.launchpad.net/bugs/2170508
Title:
GDM does not prefill the username from a smartcard when the card is
already inserted at greeter startup (re-entrant reset disposes the
UserVerifierProxy)
To manage notifications about this bug go to:
https://bugs.launchpad.net/ubuntu/+source/gnome-shell/+bug/2170508/+subscriptions
--
desktop-bugs mailing list
[email protected]
https://lists.ubuntu.com/mailman/listinfo/desktop-bugs