在WSL2中使用智能卡进行SSH

发布于 2024-02-15  500 次阅读


起因

最近需要在WSL中进行一些SSH操作来远程连接服务器,考虑到自己平时使用智能卡(Yubikey)进行各种验证,所以有了在WSL中使用智能卡的需求。写出这篇文章简单介绍一下配置方法,方便自已以后配置。

创建WSL环境

这个不多说了,在Microsoft Store中直接下载Linux发行版就行。我用的是Ubuntu 22.04 LTS。注意需要使用WSL 2版本。

安装USB附加开源项目

USBIPD可以做到附加USB设备到WSL环境中,我们管理员打开PowerShell进行以下指令操作:

usbipd list

# Find your smartcard driver
usbipd bind --busid 2-1

usbipd attach --wsl --busid 2-1

经过这番操作,我们在WSL 2环境中就应该可以查询到智能卡设备了:

lsusb

Bus 002 Device 001: ID 1d6b:0003 Linux Foundation 3.0 root hub
Bus 001 Device 002: ID 1050:0407 Yubico.com Yubikey 4/5 OTP+U2F+CCID
Bus 001 Device 001: ID 1d6b:0002 Linux Foundation 2.0 root hub

在SSH中使用智能卡

安装智能卡模块:

sudo apt install opensc-pkcs11 pcscd sssd libpam-sss

注意:下半部分对Yubikey无效,请参考下一段

剩下的步骤可以参考这篇文章。为了防止文章失效,简略陈述一下文章。

我们需要安装OpenSC,来让SSH支持智能卡登录。

sudo apt-get install opensc

可以在ssh-agent中添加对应的智能卡:

ssh-add -s /usr/lib/x86_64-linux-gnu/opensc-pkcs11.so

然后在SSH config里对应的Host添加以下这句话:

PKCS11Provider /usr/lib/x86_64-linux-gnu/opensc-pkcs11.so

最后在远端机器添加对应的SSH公钥。

ssh-keygen -D /usr/lib/x86_64-linux-gnu/opensc-pkcs11.so -e

诡异的是,尽管可以触发SSH验证,但是登陆不上去(packet 51)。与Windows中相同操作对比后,观察到Linux会跳过触摸验证流程。现在需要研究如何进行该流程。

Yubikey特定模块

安装前置软件包

sudo apt-get install libpcsclite-dev

安装Yubikey Manager

sudo apt install yubikey-manager

研究了一圈,发现原因很可能是Yubikey需要特定的YKCS11支持。文章

sudo apt update && sudo apt install ykcs11

官网给出了在Ubuntu 22.04 LTS错误的安装地址,正确的如下:

PKCS11Provider /usr/lib/x86_64-linux-gnu/libykcs11.so

随后进行SSH验证,依旧不成功。弹出新错误:

C_Sign failed: 48
sign_and_send_pubkey: signing failed for RSA "Public key for PIV Attestation": error in libcrypto

更换密钥政策

四处找解决方案,找到了一个方法:

sudo apt install crypto-policies

sudo update-crypto-policies --set legacy

允许老的加密方法继续执行。

随后继续失败。调试后发现了根本问题:使用OpenSC来进行密钥导出会导出错误的认证密钥,而不是关键性的登录密钥。

重新使用YKCS11进行密钥导出:

ssh-keygen -D /usr/lib/x86_64-linux-gnu/libykcs11.so -e

选择Auth的公钥。使用Github添加后再次进行测试:

ssh github
Enter PIN for 'YubiKey PIV #12345678': 
PTY allocation request failed on channel 0
Hi init-new-world! You've successfully authenticated, but GitHub does not provide shell access.
Connection to github.com closed.

登陆完全成功,而且似乎不需要触摸智能卡。尝试登录本地WSL

ssh localhost

Enter PIN for 'YubiKey PIV #12345678': 
Welcome to Ubuntu 22.04.3 LTS (GNU/Linux 5.15.133.1-microsoft-standard-WSL2 x86_64)

完全成功。

一些彩蛋

那么那个所谓的“错误”的认证密钥是啥呢?经过测试,这个是智能卡上OpenPGP的认证密钥而非PIV的认证密钥。当然也不是不能用,只是由于Windows下的gpg-agent支持起来较为繁琐(需要WinGPGAgent支持,而该工具已经停止维护),从而仅使用GPG密钥来进行SSH登录变得不再靠谱。所以后续我将会把各种服务器切换回PIV登陆支持。

同时,我发现了一个有意思的仓库。这个小工具看上去很有意思,似乎和某公司的内部支持很像。后续可以对其进行研究。

在WSL中移除智能卡

物理拔出或使用如下命令:

usbipd detach --busid 2-1
It is my final heart.
最后更新于 2024-02-16