
Using a Yubikey as smartcard for SSH public key authentication - sverige
http://www.undeadly.org/cgi?action=article;sid=20190302235509
======
ak217
I recently wrote a different application for YubiKeys - using the YKOATH
functionality to sign AWS API requests with HMAC-SHA256
([https://github.com/pyauth/exile](https://github.com/pyauth/exile)). What I
found is that Yubikey's protocol documentation is good, but their tools are
pretty bad, and none of them should be used. Instead, I recommend talking to
the smartcard interface through the lowest level library that's already
bundled with the major OSs - winscard/pcsclite/PCSC.framework (three
implementations all providing the same API).

The app I wrote includes Python ctypes bindings for all three implementations
([https://github.com/pyauth/exile/tree/master/exile/scard](https://github.com/pyauth/exile/tree/master/exile/scard),
and
[https://github.com/pyauth/exile/blob/master/exile/ykoath](https://github.com/pyauth/exile/blob/master/exile/ykoath)
contains an example of how to use them). Hopefully these will be useful to
others writing YubiKey-based applications.

I should add, there are other YubiKey modes (like U2F) that use the USB HID
protocol instead of the USB PCSC protocol. For those, someone at Google wrote
this library:
[https://github.com/google/pyu2f](https://github.com/google/pyu2f) which
provides similar capabilities for HID-based protocols. It similarly interfaces
directly with the system-provided HID API using ctypes.

~~~
ecesena
Can you use pyu2f with ssh? It’d be great to have a ssh binding to fido2, with
full support for new algos and resident keys, instead of gpg/pkcs11.

~~~
tialaramex
This can't work technically without a new SSH auth method.

The SSH public key auth method goes like this:

1\. Client "I want to do SSH public key auth. I can prove I know the
corresponding private key for key X" 2\. Server (typically checks
authorized_keys file to decide) may say "OK, yes, prove that" 3\. Client signs
per session data with key to prove possession [it may use the proxy technology
to have this done by a different client].

But a FIDO2 / CTAP key needs things to go the other way around

1\. Client "I want to try FIDO2" 2\. Server "OK, here is a Cookie. Can you
prove you know the associated private key?" 3\. Client uses CTAP protocol to
verify that the Yubikey recognises this cookie and gets back a proof, sends it
to server.

In the current world SSH clients know which keys they know, so they can begin
by telling the server, but in the FIDO world the Security Key is deliberately
too dumb to even know this, it has to be prompted with a cookie.

This is because of a correlation attack [edit: maybe that's the wrong word?
The attack is a bad guy figures out who you are based on seeing you connect
with this key in many places], which was not considered a big threat for SSH
but is clearly a problem on the Web. So FIDO SecurityKeys are engineered to
resist correlation by being so dumb that even they don't know if they know
your Facebook keys, until Facebook says "Hi, do you know the keys that go with
this cookie?" when you try to log in as you.

You can somewhat defend against correlation attack in SSH if it worries you by
the way, by explicitly configuring a particular public key for each connection
and forbidding the client from trying other keys (which it will by default)
using IdentitiesOnly and IdentityFile in OpenSSH.

~~~
ak217
SSH supports multiple methods of authentication, including challenge-response
authentication, which is specifically designed for the kind of exchange that
FIDO2/CTAP uses.

~~~
tialaramex
Blergh. RFC 4256, which I'd guess is what you're thinking about, aka keyboard-
interactive - is completely unsuitable for this purpose and certainly wasn't
"specifically designed" for it.

In fact RFC 4256 pretty much spells out what it's for, it lets you use PAM to
augment your authentication policies by changing what the remote user types
into their console. You can add a One Time Password check or whatever.

It is full of requirements like "A command line interface (CLI) client SHOULD
print the name and instruction (if non-empty), adding newlines" which have
nothing whatsoever to do with the actual problem for Security Keys.

Of course you could _add_ a new SSH authentication method, but the existing
RFC 4256 "challenge-response" approach is completely inappropriate.

~~~
ak217
Good to know, thanks, I didn't know challenge-response support in sshd was
specifically tied to RFC 4256.

With that said, I suspect it could be retrofitted for this purpose.

------
convolvatron
i bought a yubikey to do this. and after a while installing gpg and creating
master keys and subkeys, and dealing with the usual 'there are 4 different
verions of recipes to do this and none of them seem to work anymore', i gave
up.

this seems like such an overwhelmingly common use case I dont understand why
yubico doesnt make this as frictionless as possible. i understand that the
smart card spec is probably a hindrance, but still..

but its still on my (physical) keychain, looking forward to trying your non-
gpg workflow. thanks for posting.

~~~
naggie
I almost gave up too, but after (admittedly) a lot of battling I finally got
GPG to work well with my yuibkeys, allowing a portable SSH/GPG identity using
a single yubikey over several machines.

I also got GPG agent forwarding to work transparently and with improved
security by forwarding a dynamically created unix socket instead of a TCP
socket. It allows me to do remote code signing, as well as chain through a
bastion host.

Aside from jamming up with ansible occasionally, the setup is reliable.

I've documented the process for my own reference as much as I could here (yep,
a fifth guide):
[https://github.com/naggie/dotfiles/blob/master/etc/yubikey.m...](https://github.com/naggie/dotfiles/blob/master/etc/yubikey.md)
\-- see functions.sh in the same repository for some mechanisms to
automatically manage gpg-agent and the sockets without getting deadlocked.

I hope someone finds this useful. I'll certainly be trying the opensc method
here though, out of interest.

~~~
philsnow
You're talking about forwarding the GPG agent, so I was worried that you
hadn't found the touch-to-sign setting, but indeed you had.

Do you have a strong opinion on `on` vs `fixed` ? I tell myself that I should
use fixed but haven't bitten the bullet yet.

~~~
StreakyCobra
I set it to `on`. I read somewhere on internet an argument why `fixed` is not
really necessary: for setting it back to `off` you need the admin PIN, and you
have only 3 tries (by default) for the password. So I am not really worried
about someone managing to disable it. And that keep the possibility to change
my mind later on open, without having to reset the key.

~~~
naggie
I have it on -- if my Yubikey is locked out or lost, it's not a problem as I
have a backup of the master key in my safe. I could revoke the subkeys if the
yubikey is stolen, or trust that whoever finds the yubikey has only three
attempts on the pin.

Also I further mitigate the risk by having an explicit wrapper (gssh) to be
selective about when I forward GPG/SSH agent.

------
jwr
If you are OK with using PGP keys, there is an excellent guide at
[https://github.com/drduh/YubiKey-Guide](https://github.com/drduh/YubiKey-
Guide) — I've been using this kind of setup for almost a year now and it works
really, really well. Highly recommended.

Be sure to set the Yubikey to require touch.

As a side note, the author writes:

> GnuPG's user interface is a disaster

Well, I'd say the procedure described in the article is a strong contender,
too :-)

~~~
tanderson92
I used this too, it was great and works flawlessly. I found the author's
reasoning unconvincing (and not really argued at all).

------
nickray
As I'm currently working on possible options to expose on-device keys and
cryptography for our open source FIDO2 key (SoloKeys) beyond the FIDO use
case, I'd be curious about opinions on just exposing and using the PKCS#11 API
(Cryptoki) [0] directly.

Envisioned setup would entail: download (custom) `libsolo-pk11.so`, generate
RSA or ECDSA key on the USB key, get public key via `ssh-keygen -D libsolo-
pk11.so`, use via `ssh -I libsolo-pk11.so user@example.com`.

The equivalent thing can be done for TPMs with simple-tpm-pk11 [1] today.

Technically, I'd extend the FIDO2 CTAPHID transport with "vendor commands" [2]
mapping the basic Cryptoki API, and call that from the custom PKCS#11 shared
library, which is then just a simple shim/wrapper. No additional drivers
needed (everyone has HID).

Issues I can foresee: Users too attached to GPG workflow. Installation of
custom shared library. No SSH support (via PKCS#11) for Ed25519 yet. SSH
support for ECDSA only in about-to-be-released OpenSSH 8.0. Vanilla PuTTY on
Windows has no PKCS#11 support. Bad rap of PKCS#11 due to existing vendors
adding proprietary and closed source extensions. And the fact that SSH
(currently) presents _all_ keys to the host - I'd really like to be able to
specify which key to use.

Personally, I'm a bit allergic to the GPG/PCSC/PIV/CCID way of doing things...
My itch-to-scratch is just having a few keys off my computers (in particular,
portable), and perform (infrequent) signatures on the separate device. And do
this via a (comparatively) sane, open standard.

[0] [http://docs.oasis-
open.org/pkcs11/pkcs11-base/v2.40/os/pkcs1...](http://docs.oasis-
open.org/pkcs11/pkcs11-base/v2.40/os/pkcs11-base-v2.40-os.html)

[1] [https://github.com/ThomasHabets/simple-tpm-
pk11](https://github.com/ThomasHabets/simple-tpm-pk11)

[2] [https://fidoalliance.org/specs/fido-v2.0-rd-20180702/fido-
cl...](https://fidoalliance.org/specs/fido-v2.0-rd-20180702/fido-client-to-
authenticator-protocol-v2.0-rd-20180702.html#usb-vendor-specific-commands)

~~~
velosol
Personally I'd prefer as open a standard as possible usable across the
greatest swath possible (e.g. Chrome Windows/Mac, Chromium Linux, Firefox
W/M/L, Android Chrome/Firefox).

Someone else seems to second lower-level standards as the best way [1].

[1]:
[https://news.ycombinator.com/item?id=19567277](https://news.ycombinator.com/item?id=19567277)

------
megatraveller
I love using the Yubikey Neo with NFC, having my GPG Keys on it and using it
also for SSH connections, but mostly I love it for the OTP Feature.

Mostly using it on my Nexus 5. It is great, because using it by NFC with Open
Keychain and k9 I do not need to place my private key on the phone.
Additionaly that works also great to use the Yubikey to unlock the Phone and
also using it on the Yubico Authentificator for the OTPs.

That keys are really great. Love them.

The only other Tool I would recomend with similar features is the Nitrokey
([https://www.nitrokey.com/](https://www.nitrokey.com/)) but the Disadvantage
is, that they really lack on some features. But maybe a good alternative for
GPG and SSH.

The advantage of the Nitrokeys are, that in compare to Yubico products they
use open hardware.

Hope this helps out some people.

And, for everybody who is struggling on the usage, belive me, I spend over
four years making everything work and some really frustrating time reseting
stuff, building keys, fu*... up big and recover Accounts :D

~~~
Boulth
> Mostly using it on my Nexus 5. It is great, because using it by NFC with
> Open Keychain and k9 I do not need to place my private key on the phone.

And with TermBot you can use Yubikey to login via SSH. Can come in handy in
trouble.

------
amaccuish
I second using opensc over gpg.

GPG was a nightmare with it's own particular way of doing things and general
refusal to help other projects.

Their scdaemon takes exclusive use of the card and when this has been brought
up with the project, they said other projects should use their scdaemon to
inferface with cards rather than PKCS11 and opensc.

~~~
moreentropy
This was exactly my experience from two years ago. But to my surprise with
recent gpg2 versions most of those issues are gone (plus EC ssh key files are
supported, older gpg-agent could only do RSA)

scdaemon used to crash all the time, that doesn't happen anymore. GPG doesn't
lock the card so I have to stop scdaemon to use it w/ other apps.

So for the last half year I've happily used gpg-agent/scdaemon also as SSH
agent and it works really well without any issues.

But setting this up (w/ Ubuntu+Gnome) is still a ridiculous task:

\- Ensure gnupg2, scdaemon, pinentry-gnome3 are installed

\- cp /etc/xdg/autostart/gnome-keyring-ssh.desktop ~/.config/autostart/

\- edit ~/.config/autostart/gnome-keyring-ssh.desktop and add "X-GNOME-
Autostart-enabled=false"

\- edit ~/.gnupg/gpg-agent.conf and add "enable-ssh-support"

Gnome session startup will read both the "X-GNOME-Autostart-enabled=false" and
the "enable-ssh-support" and set up and start gpg-agent as ssh agent in the
session. There are other ways to disable a .desktop file, but the String
"X-GNOME-Autostart-enabled=false" has to be there for this to work.

When all this is set up usability is excellent. the system will even prompt to
plug in the right yubikey when you ssh into something. No need to add/remove
the card to/from the agent.

~~~
Tharre
And yet, scdaemon will still hang everytime you suspend on linux[0]. I've
written a udev rule to somewhat mitigate this[1], but it's still really
annoying that seemingly nobody cares enough to fix this issue.

[0]
[https://wiki.gnupg.org/SmartCard#Known_problem_of_Yubikey](https://wiki.gnupg.org/SmartCard#Known_problem_of_Yubikey)

[1] [https://github.com/Tharre/pkgbuilds/blob/master/arch-
system/...](https://github.com/Tharre/pkgbuilds/blob/master/arch-system/etc-
yubikey.rules)

------
bsder
I really loathe the fact that I can't just enroll 3 Yubikeys (or the
equivalent) for an employee (1 to be used, 1 for backup, and 1 extra in case
the backup fails) and be done with security for _everything_.

I'm not even requesting that I as the issuer be able to subordinate those
keys. Just make them work without making me want to shoot anyone who mentions
the word "security".

The security folks whine that nobody does security, but they sure don't make
it very easy to do so when someone wants to.

~~~
jrockway
We had a very good system at Google and I think there are papers floating
around about how it worked. You authenticated once per day per machine, and
occasionally privileged operations would require human presence detection by
pressing the security key. ssh, web... everything, all integrated. I wish we
had the same system at my current job, but alas, much programming would be
required.

I believe Google sells a product, the "identity aware proxy", that is very
much like what existed internally. I haven't used it, so am unsure. But it
sounds great.

~~~
cvwright
Sounds like you're talking about BeyondCorp?

[https://static.googleusercontent.com/media/research.google.c...](https://static.googleusercontent.com/media/research.google.com/en//pubs/archive/44860.pdf)

~~~
bduerst
AFAIK, it's part of the BeyondCorp initiative, which started as a way to give
trusted access to devices on untrusted IPs. GP here is talking about the
individual hardware dongles that are make the feat possible today:

[https://www.businessinsider.com/none-of-googles-employees-
ge...](https://www.businessinsider.com/none-of-googles-employees-get-phished-
because-of-yubikey-security-key-2018-7)

------
haberman
I'm amazed this is so complicated. I recently used
[https://github.com/sekey/sekey](https://github.com/sekey/sekey) to set up SSH
with TouchID on a mac, and was really surprised how simple it was.

~~~
pisipisipisi
As a 10+ year smart card crypto specialist I absolutely LOVE sekey

------
equalunique
This article was featured on BSD Now, a podcast that I would recommend to
anyone interested in using any of the BSDs:
[https://www.freebsdnews.com/2019/03/21/bsd-now-
episode-289-m...](https://www.freebsdnews.com/2019/03/21/bsd-now-
episode-289-microkernel-failure/)

~~~
sverige
Thanks for this! I used to listen to this regularly but fell out of the habit
a couple years ago.

------
codys
I've configured gpg to use keys from "smart cards" before, and didn't really
fall in love.

After the setup, things worked ok, but there were a few limitations that made
me more happy with just having the key on my computer.

The primary was that I had no way to validate that the key material was
encrypted at rest, and no documentation even appeared to make claims about how
the key material was stored. My setup used a fairly long PIN to replace what
would have been a fairly long password for decrypting the key material stored
on my computer. I wasn't really comfortable with using something simpler as a
PIN.

It may be the case that I could have leaned more on the hardware for security
and told myself that the limit to the number of password attempts should allow
for a shorter PIN to be used. But I was looking for something that I could add
as another layer to my existing process, rather than something that replaced
it.

At the end of the day, using a smart card to store key material just made it
harder for me to reason about the security of the key material itself due to
the increased number of unknowns. And it was more inconvenient.

------
jinnko
I was frustrated with the complexity and automated the process. Unfortunately
even automation doesn't protect you from the complexities of GPG, but it does
help. This is the tooling: [https://github.com/ixydo/gpg-smartcard-
automation](https://github.com/ixydo/gpg-smartcard-automation)

------
teamspirit
I have been doing this for a little over a year now. The most
difficult/frustrating thing was using it on my phone. Luckily, TermBot [0]
solved that, allowing me to choose an external agent for my key with
OpenKeyChain [1]. A Yubikey 5 with NFC and I feel real futuristic tapping my
phone to my pocket to gain access to remote computers. I get to do this with
my password manager too [2].

[0]
[https://f-droid.org/en/packages/org.sufficientlysecure.termb...](https://f-droid.org/en/packages/org.sufficientlysecure.termbot)

[1]
[https://f-droid.org/en/packages/org.sufficientlysecure.keych...](https://f-droid.org/en/packages/org.sufficientlysecure.keychain)

[2] [https://github.com/zeapo/Android-Password-
Store](https://github.com/zeapo/Android-Password-Store)

~~~
Steltek
I have been waiting for this for so long! Thank you so much for these links!

I have Pass working but SSH was always a glaring missing piece of the puzzle.
Now if only I can convince an SFTP client to do this, I'll be really sitting
pretty.

------
jandeboevrie
Remember to buy two devices and to swap usage every month. If one breaks you
loose access since the keys shouldn't leave the device. Use two and always
setup two keys .

Oh and the yubikeys nowdays are closed source. If you want actual open source
hardware and software, checkout the Nitrokey Start. It's cheaper and fully
open source, hard and software. Its an openpgp token:
[https://raymii.org/s/articles/Nitrokey_Start_Getting_started...](https://raymii.org/s/articles/Nitrokey_Start_Getting_started_guide.html)

If you want a smartcard, Nitrokey had Both the pro and the HSM. An openpgp
smartcard and and smartcard-hsm (just pkcs#11).

------
noliran
In addition to using YubiKey's U2F capabilities, I've been using its HMAC-SHA1
challenge-response mode as my password manager (more precisely a password
generator) for the past few months.

It uses these 3 to consistently generate a password for websites:

1\. A secret that I've pre-programmed in the YubiKey (+ 2 other backup
YubiKeys)

2\. A "pin code" (either provided by me, or in my case - protected by my
TouchID)

3\. The website's name

If you want to take a peek, I always appreciate feedback.
[https://github.com/noliran/ykpass](https://github.com/noliran/ykpass)

------
Boulth
> Since nobody can get at the ssh key thats in the Yubikey, a short pin will
> be fine - at least that's what the system promises.

Short pin is fine because after 3 tries the token is locked.

On the other hand there are no limits with software keys.

------
coldacid
I love my Yubikey for SSH auth, but it's a complete pain in the ass that gpg-
agent and OpenSSH won't play together on Windows. I and others have tried to
make broker apps that let them talk with each other but to no avail thanks to
libassuan's Windows "workaround" for AF_UNIX sockets.

In the end, I have to use gpg-agent's PuTTY support, which means no command-
line SSH, only a separate PuTTY window when I want to do SSH sessions, and
using plink for SSH auth for Git.

------
ejholmes
If you have a newer MacBook with TouchID, you can get similar benefits using
[https://github.com/sekey/sekey](https://github.com/sekey/sekey). Arguably
better, because access is backed by biometrics (TouchID) so it's "something
you are" (fingperint) + "something you have" (laptop) and quite a bit simpler
than setting up GPG backend SSH keys.

~~~
busterarm
Uh, what?

You're just combining "something you have" \+ "something you have". Unlike
with a Yubikey, your fingerprint will always be with you when you have your
laptop.

Biometric access is a terrible idea if you don't combine it with "something
you know". Access to your laptop can now be coerced or compelled at any time.

Every commercial biometrics system I've ever seen that's worth a damn at least
combines it with a pinpad.

~~~
ejholmes
Obviously, depends on your threat model. I'd argue that being physically
coerced ends up being a pretty low risk for most people. If you're just
looking for something better than storing private key material on a hard disc,
sekey is a pretty great alternative to using Yubikey + GPG.

------
atonse
There seems to be an opportunity here for someone to create the "Algo VPN"
version of Yubikey SSH.

Or maybe the Teleport people can just make this as painless as possible.

Or for keybase to make it painless. Don't try to support everything. Just
start with only supporting Yubikeys. Then you can expand.

~~~
xur17
Whoever does this -> I would love for the ability to backup my ssh and gpg
keys using backup words, similar to what cryptocurrency wallets use (24 words
that are used to define the entropy).

------
baud147258
Funny, that's exactly what we're doing at work right now: we're adapting our
JavaCard applet to use them with Yubikey, to be able to use the Yubikey like a
smartcard, including public key authentication.

------
everybodyknows
Earler discussion on HN:

[https://news.ycombinator.com/item?id=19340638](https://news.ycombinator.com/item?id=19340638)

------
1024core
Speaking of Yubikeys: I found a Yubikey lying somewhere. I asked around, no
takers. Is it safe to use such a Yubikey? It'd be a shame to waste it.

~~~
TylerE
You have what appears to be a Yubikey. Many devious attacks involve dropping a
device that LOOKS like a generic USB drive in a public location.

~~~
closeparen
If the device is U2F capable, you can check whether it is genuine [0]. Of
course, if it is not genuine, it can own your machine the moment you plug it
in.

[0] [https://www.yubico.com/genuine/](https://www.yubico.com/genuine/)

------
jamesholden
This is for OpenBSD. What about for us lowly Debian users? Anybody know how I
can do something similar? :)

------
jzig
After using one for over a year now all I can say is it shouldn't be this hard
:(

------
munchbunny
This is awesome. I've played with something similar and have been thinking
about automating some of this process to give small startups a really
lightweight way to on-board this kind of capability for physical + PIN multi-
factor SSH access.

------
platz
What happens when I loose the yubikey

~~~
opencl
You have a spare and revoke the ability to use the one you lost.

~~~
platz
Ah, makes sense.

I bet most people only buy 1 though

~~~
Faaak
You keep a backup of your master key in a secure way (paper key + locker +
passphrase)

