Options for providing a pin =========================== The obvious ways to provide user and security officer pin are to write a secret into p11nethsm.conf, pass it on command line to frontend tools interactively, or pass it as command line argument like pkcs11-tool --pin. In automation scenarios this may not be flexible or secure enough. A better option can be to include the pin-source attribute in a PKCS#11 URI as defined in RFC 7512 [1]. For example, pkcs11:token=NetHSM;object=mykey;type=private&pin-source=/secure/place/.pin is understood by both pkcs11-provider and the libp11 engine which will read the secret from a text file that was previously prepared in a secure context. [1] https://www.rfc-editor.org/rfc/rfc7512.html Testing with Nitrokey's public online demo instance =================================================== nethsm-pkcs11 can be tested with Nitrokey's online demo instance at nethsmdemo.nitrokey.com. This example shows how to use it to sign a text message through PKCS#11 using openssl as frontend. First copy the demo instance example configuration in place mkdir -p $HOME/.config/nitrokey cp /usr/share/doc/nethsm-pkcs11/examples/p11nethsm.demoinstance.conf \ $HOME/.config/nitrokey/p11nethsm.conf Since the demo instance is periodically reset, we must provision it first to get a key and user known to us. Provisioning can be done with the pynitrokey tool, or through REST API with plain curl as shown further on. # unlock - may fail if already unlocked curl -H "Content-Type: application/json" --data '{ "passphrase": "unlockunlock" }' \ https://admin:adminadmin@nethsmdemo.nitrokey.com/api/v1/unlock # provision - may fail if already provisioned curl -H "Content-Type: application/json" --data '{ "unlockPassphrase": "unlockunlock", "adminPassphrase": "adminadmin", "systemTime": "'$(date -u +%Y-%m-%dT%H:%M:%SZ)'" }' \ https://admin:adminadmin@nethsmdemo.nitrokey.com/api/v1/provision # create operator user curl -X "PUT" -H "Content-Type: application/json" --data '{ "realName": "Debian User", "role": "Operator", "passphrase": "operatoroperator" }' \ https://admin:adminadmin@nethsmdemo.nitrokey.com/api/v1/users/operator # generate signign key curl -H "Content-Type: application/json" --data '{ "mechanisms": [ "RSA_Signature_PKCS1" ], "type": "RSA", "length": 2048, "id": "myFirstKey" }' \ https://admin:adminadmin@nethsmdemo.nitrokey.com/api/v1/keys/generate Install pkcs11-provider and p11-kit to let openssl find the nethsm-pkcs11 module. Then verify the connection. sudo apt install nethsm-pkcs11 pkcs11-provider p11-kit-modules p11-kit list-modules The output should contain following lines (excerpt) module: nethsm_pkcs11 token: NetHSMdemo uri: pkcs11:model=NetHSM;manufacturer=Nitrokey%20GmbH;serial=0000000000;token=NetHSMdemo For CMS signign, we'll also need a signer certificate along with the key. It can be created and uploaded as follows. openssl req -provider pkcs11 -provider default \ -x509 -new -batch -subj /CN=myFirstKey -text -days 365 \ -key "pkcs11:token=NetHSMdemo;object=myFirstKey;type=private" \ -outform PEM \ -out /tmp/cert.pem curl -v -H "Content-Type: application/octet-stream" \ --upload-file /tmp/cert.pem \ https://admin:adminadmin@nethsmdemo.nitrokey.com/api/v1/keys/myFirstKey/cert Finally, we can sign our message and create a detached CMS signature: echo "my message" > /tmp/message.txt openssl cms -provider pkcs11 -provider default -sign \ -inkey "pkcs11:token=NetHSMdemo;object=myFirstKey;type=private" \ -signer "pkcs11:token=NetHSMdemo;object=myFirstKey;type=cert" \ -md SHA256 -outform DER -binary \ -in /tmp/message.txt \ -out /tmp/message.txt.sig