[Pcsclite-muscle] Directly using RSA key of a smartcard

David Woodhouse dwmw2 at infradead.org
Thu Jun 22 03:10:24 PDT 2023


On Wed, 2023-06-21 at 13:08 -0400, Michael Conrad wrote:
> Hello, I'm new to smartcards and curious if it is possible to ask the
> card "what is your public RSA key", encrypt something with that public 
> key, and then ask the card to decrypt it back to the original value.  In 
> other words, I want to get at the raw encryption API without the hassle 
> of the gpg infrastructure that is normally used for this.  (and yes I
> understand that the things directly encrypted with RSA need to be small 
> values like raw AES keys, used for further encryption and decryption 
> using CBC or similar)
> 
> If so, could you provide some pointers on convenient ways I might access 
> this API from a script?  (but I can write C if I need to)
> 
> Thanks, and if you want some stackexchange credit I have the question at
> 
> https://unix.stackexchange.com/questions/749431/is-there-a-tool-that-can-perform-direct-rsa-decryption-with-a-yubikey

Assuming you are running on a modern Linux or similar system, this
should be fairly simple.

Setup:

Make sure your Yubikey has enabled 'PIV' mode, and you've installed the
OpenSC PKCS#11 module as others have said. Also install the OpenSSL
PKCS#11 'engine'.

Use the yubico-piv-tool¹ or any other method you like to install an RSA
(or EC, which will be a lot faster if you'd care to join us in the 21st
century) key into the slot² of your choice, let's say the 'Card
Authentication slot 9e for example. You can either import an existing
key, or create one that's never existed outside the Yubikey.

Now it's simple. Any software that can use an RSA key from a file
*ought* to accept a standard PKCS#11 URI³ identifying the key in the
Yubikey instead.

The URI for the key in the Card Authentication slot will be something
like 'pkcs11:manufacturer=piv_II;id=%01'.

So you can do something like

 echo "test payload" | openssl dgst -sha256 -sign 'pkcs11:manufacturer=piv_II;id=%04' -hex

... except OpenSSL doesn't *quite* get this right yet, so you have to add 

 -engine pkcs11 -keyform engine

to the above command line because all crypto software authors hate
their users and it doesn't bother to *infer* those obvious things from
the fact that you gave it a PKCS#11 URI. This is also *slightly* out of
date because newer OpenSSL uses "providers" instead of engines, and I
think it *still* doesn't just get things right  for itself so you need
a slightly *different* pointless arcane incantation to make it do so.

Decent software *won't* need those extra hints, and will just take the
URI in place of a filename and do the right thing. File bugs if not.

Example:
 $ yubico-piv-tool -s9e -ARSA2048 -agenerate | tee pubkey.pem
-----BEGIN PUBLIC KEY-----
MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAr9LrzjNbRABqhDQrGi3l
VcQhmUu0lls8k4XnO8c/U0oS6IvH4H7HuqXFfwThYofxIgA2eIXuRXf+V/CSWtXN
40Bb10QKcTXVATm05+KFNWg1GCVg2yrvsUOQSd6MOxAa5goUUi2xOjeLFZRvXuvt
YmLytwY77YqE0WOHYfYuk9kolueZHhq4BSOVRmQpZxKd6/MkWlT46SPc3Bwbyx41
t2U42vlnHYuma3NF6qI+a+LaMyvkFVBkRM6A1WB2u5jjl/ZQmyYsuqg2e8xu7P8m
5/GUH9HjD074+ea1NEdMncPhKjO+pL24BSebtIPUmzEJIh6kCaweJYiMKYuLx15H
HQIDAQAB
-----END PUBLIC KEY-----
Successfully generated a new private key.
 $ echo Test | openssl dgst -sha256 -sign 'pkcs11:manufacturer=piv_II;id=%04' -engine pkcs11 -keyform engine  > signature.bin
 $ echo Test openssl dgst -sha256 -verify pubkey.pem -signature signature.bin
Verified OK



¹ https://developers.yubico.com/yubico-piv-tool/
² https://developers.yubico.com/PIV/Introduction/Certificate_slots.html
³ https://datatracker.ietf.org/doc/html/rfc7512
-------------- next part --------------
A non-text attachment was scrubbed...
Name: smime.p7s
Type: application/pkcs7-signature
Size: 5965 bytes
Desc: not available
URL: <http://lists.infradead.org/pipermail/pcsclite-muscle/attachments/20230622/e34215bb/attachment-0001.p7s>


More information about the pcsclite-muscle mailing list