Currently, Trussed on the NitroKey 3 and SoloKeys Solo 2 returns "success" FIDO applet selection, but then returns 0x6985 (conditions of use not satisfied) to every command sent thereafter:
SELECT a0000006472f0001
>>> 00a4040008a0000006472f000100
OK "U2F_V2"
<<< 5532465f56329000
CTAP2 getInfo
>>> 80100000010400
ERROR: Conditions of use not satisfied
<<< 6985
By comparison, YubiKey's USB CCID implementation explicitly rejects the SELECT command with 0x6a82 (File or application not found):
SELECT a0000006472f0001
>>> 00a4040008a0000006472f000100
ERROR: File or application not found
<<< 6a82
I believe that YubiKey's behaviour follows the intent of the public parts of the FIDO specification[^1]. CTAP 2.1 § 11.3.2 Protocol states that "Authenticator replies with success if the applet is present", which while the applet is technically present, it's not actually usable over non-contactless interfaces. There is no consideration given in the specification to a potential distinction – so I don't think that Trussed is following the intent of the specification.
[^1]: There is apparently some secret FIDO documentation which says that one should disable the FIDO applet over USB CCID (to avoid a security issue on ChromeOS), but there's no further details on how an implementation should do this.
Trussed could error out here on contact interfaces instead:
CTAP implementations which support smart-card interfaces cannot treat presence of the FIDO applet as usability of the FIDO applet, which makes set-up more complicated and enumeration slower.
They may also need to blocklist Trussed security key vendors by their USB CCID device name to avoid touching a useless interface, but this is not a particularly scalable solution for firmware which is intended to be adopted by multiple vendors, especially if that vendor has switched firmware implementation in the past (where the USB CCID interface may actually work) or the vendor also manufactures smart card interfaces.
Alternatively, they may need to allowlist "real" contact/contactless interfaces, which is even less scalable... 🙃
Currently, Trussed on the NitroKey 3 and SoloKeys Solo 2 returns "success" FIDO applet selection, but then returns
0x6985
(conditions of use not satisfied) to every command sent thereafter:This appears to come from here:
https://github.com/trussed-dev/fido-authenticator/blob/7bd0c3bc5105a122fa11d9b354457746f391c4fb/src/dispatch/apdu.rs#L44-L48
By comparison, YubiKey's USB CCID implementation explicitly rejects the SELECT command with
0x6a82
(File or application not found):I believe that YubiKey's behaviour follows the intent of the public parts of the FIDO specification[^1]. CTAP 2.1 § 11.3.2 Protocol states that "Authenticator replies with success if the applet is present", which while the applet is technically present, it's not actually usable over non-contactless interfaces. There is no consideration given in the specification to a potential distinction – so I don't think that Trussed is following the intent of the specification.
[^1]: There is apparently some secret FIDO documentation which says that one should disable the FIDO applet over USB CCID (to avoid a security issue on ChromeOS), but there's no further details on how an implementation should do this.
Trussed could error out here on contact interfaces instead:
https://github.com/trussed-dev/fido-authenticator/blob/7bd0c3bc5105a122fa11d9b354457746f391c4fb/src/dispatch/apdu.rs#L31-L34
Impact of this issue
CTAP implementations which support smart-card interfaces cannot treat presence of the FIDO applet as usability of the FIDO applet, which makes set-up more complicated and enumeration slower.
They may also need to blocklist Trussed security key vendors by their USB CCID device name to avoid touching a useless interface, but this is not a particularly scalable solution for firmware which is intended to be adopted by multiple vendors, especially if that vendor has switched firmware implementation in the past (where the USB CCID interface may actually work) or the vendor also manufactures smart card interfaces.
Alternatively, they may need to allowlist "real" contact/contactless interfaces, which is even less scalable... 🙃