shimunn / ctap Goto Github PK
View Code? Open in Web Editor NEWThis project forked from ardaxi/ctap
A Rust implementation of the FIDO2 CTAP protocol
This project forked from ardaxi/ctap
A Rust implementation of the FIDO2 CTAP protocol
I should be possible to specify a pin to use for the device being evaluated with the hmac
example. I would suggest adding conditional pin use querying an environmental variable. I would be willing to try my hand at this change with a pull request.
When attempting to test ctap using the hmac example, it can be observed that Yubico Yubikey devices with firmware 5.4.3 result in an error when trying to communicate with them. This compared compare to older firmware versions (eg. 5.2.4) is new and different. This issue was actually first observed when trying to use the fido2luks
project with such a device. As this tool relies on this library, it is unable to communicate with the device. The output from hmac
shows the error:
user@host:~$ sudo ./hmac
** usage_page_hex: 0007 , 0003
** usage_page_hex: f1d0 , 0021
Error: FidoError(FidoError(UnexpectedType { datatype: Array, info: 1 }
Error while decoding CBOR from device.)
Error while decoding CBOR from device.)
user@host:~$ (export RUST_BACKTRACE=1; sudo -E fido2luks connected)
user@host:~$ (export RUST_BACKTRACE=1; sudo -E ./hmac)
** usage_page_hex: 0007 , 0003
** usage_page_hex: f1d0 , 0021
Error: FidoError(FidoError(UnexpectedType { datatype: Array, info: 1 }
0: failure::backtrace::internal::InternalBacktrace::new
at /usr/local/cargo/registry/src/github.com-1ecc6299db9ec823/failure-0.1.8/src/backtrace/internal.rs:46:44
1: failure::backtrace::Backtrace::new
at /usr/local/cargo/registry/src/github.com-1ecc6299db9ec823/failure-0.1.8/src/backtrace/mod.rs:121:35
2: <failure::error::error_impl::ErrorImpl as core::convert::From<F>>::from
at /usr/local/cargo/registry/src/github.com-1ecc6299db9ec823/failure-0.1.8/src/error/error_impl.rs:19:17
3: <failure::error::Error as core::convert::From<F>>::from
at /usr/local/cargo/registry/src/github.com-1ecc6299db9ec823/failure-0.1.8/src/error/mod.rs:36:18
4: <T as core::convert::Into<U>>::into
at /usr/local/rustup/toolchains/1.53.0-x86_64-unknown-linux-gnu/lib/rustlib/src/rust/library/core/src/convert/mod.rs:538:9
5: failure::context::Context<D>::with_err
at /usr/local/cargo/registry/src/github.com-1ecc6299db9ec823/failure-0.1.8/src/context.rs:105:40
6: failure::Fail::context
at /usr/local/cargo/registry/src/github.com-1ecc6299db9ec823/failure-0.1.8/src/lib.rs:160:9
7: <ctap_hmac::error::FidoError as core::convert::From<cbor::decoder::DecodeError>>::from
at /home/vscode/code/src/error.rs:133:19
ctap_hmac::cbor::GetInfoResponse::decode
at /home/vscode/code/src/cbor.rs:288:31
8: ctap_hmac::cbor::Request::decode
at /home/vscode/code/src/cbor.rs:49:51
9: ctap_hmac::FidoDevice::cbor
at /home/vscode/code/src/lib.rs:556:9
10: ctap_hmac::FidoDevice::init
at /home/vscode/code/src/lib.rs:290:30
11: ctap_hmac::FidoDevice::new
at /home/vscode/code/src/lib.rs:274:9
12: hmac::main
at /home/vscode/code/examples/hmac.rs:18:22
13: core::ops::function::FnOnce::call_once
at /usr/local/rustup/toolchains/1.53.0-x86_64-unknown-linux-gnu/lib/rustlib/src/rust/library/core/src/ops/function.rs:227:5
14: std::sys_common::backtrace::__rust_begin_short_backtrace
at /usr/local/rustup/toolchains/1.53.0-x86_64-unknown-linux-gnu/lib/rustlib/src/rust/library/std/src/sys_common/backtrace.rs:125:18
15: std::rt::lang_start::{{closure}}
at /usr/local/rustup/toolchains/1.53.0-x86_64-unknown-linux-gnu/lib/rustlib/src/rust/library/std/src/rt.rs:49:18
16: core::ops::function::impls::<impl core::ops::function::FnOnce<A> for &F>::call_once
at /rustc/53cb7b09b00cbea8754ffb78e7e3cb521cb8af4b/library/core/src/ops/function.rs:259:13
std::panicking::try::do_call
at /rustc/53cb7b09b00cbea8754ffb78e7e3cb521cb8af4b/library/std/src/panicking.rs:379:40
std::panicking::try
at /rustc/53cb7b09b00cbea8754ffb78e7e3cb521cb8af4b/library/std/src/panicking.rs:343:19
std::panic::catch_unwind
at /rustc/53cb7b09b00cbea8754ffb78e7e3cb521cb8af4b/library/std/src/panic.rs:431:14
std::rt::lang_start_internal
at /rustc/53cb7b09b00cbea8754ffb78e7e3cb521cb8af4b/library/std/src/rt.rs:34:21
17: std::rt::lang_start
at /usr/local/rustup/toolchains/1.53.0-x86_64-unknown-linux-gnu/lib/rustlib/src/rust/library/std/src/rt.rs:48:5
18: main
19: __libc_start_main
20: <unknown>
Error while decoding CBOR from device.)
Error while decoding CBOR from device.)
Please note that some debugging output was added to this build (one line), but that was all.
After adding some additional debugging messages, the issue became more clear:
user@host:~$ (export RUST_BACKTRACE=1; sudo -E ./hmac)
** usage_page_hex: 0007 , 0003
** usage_page_hex: f1d0 , 0021
**** CBOR decoding start
** CBOR decoding 1
** CBOR decoding 2
** CBOR decoding 3
** CBOR decoding 4
** CBOR decoding 5
** CBOR decoding 6
** CBOR skipping 7
** CBOR skipping 8
** CBOR skipping 8
** CBOR skipping 128
** CBOR skipping 9
Error: FidoError(FidoError(UnexpectedType { datatype: Array, info: 1 }
0: failure::backtrace::internal::InternalBacktrace::new
at /usr/local/cargo/registry/src/github.com-1ecc6299db9ec823/failure-0.1.8/src/backtrace/internal.rs:46:44
1: failure::backtrace::Backtrace::new
at /usr/local/cargo/registry/src/github.com-1ecc6299db9ec823/failure-0.1.8/src/backtrace/mod.rs:121:35
2: <failure::error::error_impl::ErrorImpl as core::convert::From<F>>::from
at /usr/local/cargo/registry/src/github.com-1ecc6299db9ec823/failure-0.1.8/src/error/error_impl.rs:19:17
3: <failure::error::Error as core::convert::From<F>>::from
at /usr/local/cargo/registry/src/github.com-1ecc6299db9ec823/failure-0.1.8/src/error/mod.rs:36:18
4: <T as core::convert::Into<U>>::into
at /usr/local/rustup/toolchains/1.53.0-x86_64-unknown-linux-gnu/lib/rustlib/src/rust/library/core/src/convert/mod.rs:538:9
5: failure::context::Context<D>::with_err
at /usr/local/cargo/registry/src/github.com-1ecc6299db9ec823/failure-0.1.8/src/context.rs:105:40
6: failure::Fail::context
at /usr/local/cargo/registry/src/github.com-1ecc6299db9ec823/failure-0.1.8/src/lib.rs:160:9
7: <ctap_hmac::error::FidoError as core::convert::From<cbor::decoder::DecodeError>>::from
at /home/vscode/code/src/error.rs:133:19
ctap_hmac::cbor::GetInfoResponse::decode
at /home/vscode/code/src/cbor.rs:289:31
8: ctap_hmac::cbor::Request::decode
at /home/vscode/code/src/cbor.rs:49:51
9: ctap_hmac::FidoDevice::cbor
at /home/vscode/code/src/lib.rs:556:9
10: ctap_hmac::FidoDevice::init
at /home/vscode/code/src/lib.rs:290:30
11: ctap_hmac::FidoDevice::new
at /home/vscode/code/src/lib.rs:274:9
12: hmac::main
at /home/vscode/code/examples/hmac.rs:18:22
13: core::ops::function::FnOnce::call_once
at /usr/local/rustup/toolchains/1.53.0-x86_64-unknown-linux-gnu/lib/rustlib/src/rust/library/core/src/ops/function.rs:227:5
14: std::sys_common::backtrace::__rust_begin_short_backtrace
at /usr/local/rustup/toolchains/1.53.0-x86_64-unknown-linux-gnu/lib/rustlib/src/rust/library/std/src/sys_common/backtrace.rs:125:18
15: std::rt::lang_start::{{closure}}
at /usr/local/rustup/toolchains/1.53.0-x86_64-unknown-linux-gnu/lib/rustlib/src/rust/library/std/src/rt.rs:49:18
16: core::ops::function::impls::<impl core::ops::function::FnOnce<A> for &F>::call_once
at /rustc/53cb7b09b00cbea8754ffb78e7e3cb521cb8af4b/library/core/src/ops/function.rs:259:13
std::panicking::try::do_call
at /rustc/53cb7b09b00cbea8754ffb78e7e3cb521cb8af4b/library/std/src/panicking.rs:379:40
std::panicking::try
at /rustc/53cb7b09b00cbea8754ffb78e7e3cb521cb8af4b/library/std/src/panicking.rs:343:19
std::panic::catch_unwind
at /rustc/53cb7b09b00cbea8754ffb78e7e3cb521cb8af4b/library/std/src/panic.rs:431:14
std::rt::lang_start_internal
at /rustc/53cb7b09b00cbea8754ffb78e7e3cb521cb8af4b/library/std/src/rt.rs:34:21
17: std::rt::lang_start
at /usr/local/rustup/toolchains/1.53.0-x86_64-unknown-linux-gnu/lib/rustlib/src/rust/library/std/src/rt.rs:48:5
18: main
19: __libc_start_main
20: <unknown>
Error while decoding CBOR from device.)
Error while decoding CBOR from device.)
The yman diagnose output for the device is as follows:
user@host:~$ sudo ykman --diagnose
ykman: 4.0.5
Python: 3.8.5 (default, Jul 28 2020, 12:59:40)
[GCC 9.3.0]
Platform: linux
Arch: aarch64
Running as admin: True
Detected PC/SC readers:
Yubico YubiKey OTP+FIDO+CCID 00 00 (connect: Success)
Detected YubiKeys over PC/SC:
ScardYubiKeyDevice(pid=0407, fingerprint='Yubico YubiKey OTP+FIDO+CCID 00 00')
RawInfo: 260102033f0302033f020400c8c1de04010205030504030602000007010f0801000a01000f0100
DeviceInfo(config=DeviceConfig(enabled_capabilities={<TRANSPORT.USB: 'usb'>: <CAPABILITY.FIDO2|HSMAUTH|OATH|PIV|OPENPGP|4|U2F|OTP: 831>}, auto_eject_timeout=0, challenge_response_timeout=15, device_flags=<DEVICE_FLAG.0: 0>), serial=13156830, version=Version(major=5, minor=4, patch=3), form_factor=<FORM_FACTOR.USB_A_NANO: 2>, supported_capabilities={<TRANSPORT.USB: 'usb'>: <CAPABILITY.FIDO2|HSMAUTH|OATH|PIV|OPENPGP|4|U2F|OTP: 831>}, is_locked=False, is_fips=False)
Device name: YubiKey 5 Nano
PIV
PIV version: 5.4.3
WARNING: Using default PIN!
PIN tries remaining: 3/3
WARNING: Using default Management key!
Management key algorithm: TDES
CHUID: No data available.
CCC: No data available.
OATH
Oath version: 5.4.3
Password protected: False
OpenPGP
OpenPGP version: 3.4
Application version: 5.4.3
PIN tries remaining: 3
Reset code tries remaining: 0
Admin PIN tries remaining: 3
Touch policies
Signature key Off
Encryption key Off
Authentication key Off
Attestation key Off
Detected YubiKeys over HID OTP:
OtpYubiKeyDevice(pid=0407, fingerprint='/dev/hidraw0')
RawInfo: 260102033f0302033f020400c8c1de04010205030504030602000007010f0801000a01000f0100
DeviceInfo(config=DeviceConfig(enabled_capabilities={<TRANSPORT.USB: 'usb'>: <CAPABILITY.FIDO2|HSMAUTH|OATH|PIV|OPENPGP|4|U2F|OTP: 831>}, auto_eject_timeout=0, challenge_response_timeout=15, device_flags=<DEVICE_FLAG.0: 0>), serial=13156830, version=Version(major=5, minor=4, patch=3), form_factor=<FORM_FACTOR.USB_A_NANO: 2>, supported_capabilities={<TRANSPORT.USB: 'usb'>: <CAPABILITY.FIDO2|HSMAUTH|OATH|PIV|OPENPGP|4|U2F|OTP: 831>}, is_locked=False, is_fips=False)
Device name: YubiKey 5 Nano
OTP: ConfigState(configured: (True, False), touch_triggered: (True, False), led_inverted: False)
Detected YubiKeys over HID FIDO:
CtapYubiKeyDevice(pid=0407, fingerprint='/dev/hidraw1')
CTAP device version: 5.4.3
CTAPHID protocol version: 2
Capabilities: 5
RawInfo: 260102033f0302033f020400c8c1de04010205030504030602000007010f0801000a01000f0100
DeviceInfo(config=DeviceConfig(enabled_capabilities={<TRANSPORT.USB: 'usb'>: <CAPABILITY.FIDO2|HSMAUTH|OATH|PIV|OPENPGP|4|U2F|OTP: 831>}, auto_eject_timeout=0, challenge_response_timeout=15, device_flags=<DEVICE_FLAG.0: 0>), serial=13156830, version=Version(major=5, minor=4, patch=3), form_factor=<FORM_FACTOR.USB_A_NANO: 2>, supported_capabilities={<TRANSPORT.USB: 'usb'>: <CAPABILITY.FIDO2|HSMAUTH|OATH|PIV|OPENPGP|4|U2F|OTP: 831>}, is_locked=False, is_fips=False)
Device name: YubiKey 5 Nano
Ctap2Info: {<VERSIONS: 0x01>: ['U2F_V2', 'FIDO_2_0', 'FIDO_2_1_PRE'], <EXTENSIONS: 0x02>: ['credProtect', 'hmac-secret'], <AAGUID: 0x03>: b'\xee\x88(yr\x1cI\x13\x97u=\xfc\xce\x97\x07*', <OPTIONS: 0x04>: {'rk': True, 'up': True, 'plat': False, 'clientPin': True, 'credentialMgmtPreview': True}, <MAX_MSG_SIZE: 0x05>: 1200, <PIN_UV_PROTOCOLS: 0x06>: [2, 1], <MAX_CREDS_IN_LIST: 0x07>: 8, <MAX_CRED_ID_LENGTH: 0x08>: 128, <TRANSPORTS: 0x09>: ['usb'], <ALGORITHMS: 0x0A>: [{'alg': -7, 'type': 'public-key'}, {'alg': -8, 'type': 'public-key'}], <MIN_PIN_LENGTH: 0x0D>: 4, <FIRMWARE_VERSION: 0x0E>: 328707}
PIN retries: (8, None)
End of diagnostics
It seems as though some complex data is being returned by the device and not getting parse properly due to unknown/unsupported fields. These fields will need to be parsed properly in order for devices with this firmware to function with ctap_hmac
.
It seems the new fields are following the draft spec of fido 2.1. The latest version of the draft is here:
https://fidoalliance.org/specs/fido-v2.1-ps-20210615/fido-client-to-authenticator-protocol-v2.1-ps-20210615.html
It would be great to have a cross-platform library. I'm going to use this issue to lay out the state of the problem and to get a sense of how to best solve it.
Currently, there is a HID library, hidapi, that works for Mac OS and Windows. The way it is implemented now is that it calls out to libusb
C functions. The ctap-hid-fido2 crate uses hidapi
to communicate with FIDO2 devices, but of course does not support Linux.
Because the HID communication functions in the hidapi
crate rely on C code, the struct representation of the HID device (equivalent to ctap_hmac::FidoDevice
) in the ctap-hid-fido2
library retains the C representation of the device. That would cause a problem here, since we would have two ways of representing the device.
My proposal would be to abstract the functions in FidoDevice
out into a Trait, and then to implement that trait for a separate struct that would represent a Fido Device on MacOs or Windows. What are your thoughts on that way of solving the problem? I'm not 100% sold that this is the way forward, and I defer to your judgment here. Thanks in advance for entertaining my suggestsions!
A declarative, efficient, and flexible JavaScript library for building user interfaces.
๐ Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. ๐๐๐
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google โค๏ธ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.