Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

HSM instructions #31

Open
withinboredom opened this issue Feb 13, 2020 · 24 comments
Open

HSM instructions #31

withinboredom opened this issue Feb 13, 2020 · 24 comments

Comments

@withinboredom
Copy link

Not everyone keeps their SSH and PGP keys on their laptop. In the event that your key is not accessible by the signing tool, the signing tool can present you with the raw data needed to be signed.

I can't derive how to do this from any of the examples given or the instructions. Can someone explain how this is done?

@tedder
Copy link

tedder commented Feb 13, 2020

I think all that needs to be done is this:

  • from hsd:
    • run hsw or wallet
  • from hs-client:
    • bin/hsw-cli get, make sure it exists
    • bin/hsw-cli master, make sure it exists
    • generate subwallet: bin/hsw-cli account create initial
    • get the "faucet" address: bin/hsw-cli --account=initial address
  • from hs-airdrop:
    • bin/hs-airdrop ~/.ssh/your_private_ssh_key_registered_on_github faucet_address_from_last_step
  • can now stop hsw or wallet

I don't know why hsw/wallet keeps trying to reach hsd, when hsw and hsd can't both run as they create a LOCK file. But I think after these steps, once the chain progresses far enough, the HNS coins will appear.

@withinboredom
Copy link
Author

~/.ssh/your_private_ssh_key_registered_on_github

Yeah, that key doesn't exist because it's in an HSM and by the nature of an HSM, it can't be exported. I can only sign or encrypt data.

I was luckily able to find an old key in a backup that worked, but others will not be so lucky.

@xlc
Copy link

xlc commented Feb 17, 2020

I am using yubikey and how do I sign with it? How do I make the cli give me the data to sign?

@pinheadmz
Copy link
Member

pinheadmz commented Feb 17, 2020

This may not be possible because the nonce is discovered by hashing the private key, so you may need direct access to it. That's as far as I know, @chjj may have some more insight and this might be something we can enable in the future, just please be patient.

@withinboredom
Copy link
Author

Seems that we should be able to generate the nonce in the same way they were generated using our public key?

@pinheadmz
Copy link
Member

You're right, I think the bucket is determined by the first byte of the hash of the public key. Even if it wasn't, we could try to brute force the entire nonce space... I wonder how long that would take to find your own nonce that decrypts.

@kiwibrowser
Copy link

The first part is easy, in bin/hs-airdrop, change

-const {SSHPrivateKey} = ssh;
+const {SSHPrivateKey, SSHPublicKey} = ssh;
[...]
     default: {
       const str = data.toString('utf8');
-      const passphrase = await readPassphrase();
-      const key = SSHPrivateKey.fromString(str, passphrase);
+      const key = SSHPublicKey.fromString(str);

and it'll find the right bucket for the nonce.

However, you need to decrypt the nonce using your private key:

+      fs.writeFileSync('nonces/' + qqq + '.nonce', ct); // <--- this to get the nonce outside of the script
       out.push(key.decrypt(ct, priv));

and this I have no clue how to do, because eventually it goes into goo_* specific decrypt functions, but if someone is smarter than me I'm interested :)

My guess is that it was RSA-OAEP but I can't figure out the proper OpenSSL cli parameters.

If you manage to decrypt the nonce (there is 1500 files to try), then only the "signing-back" part from --bare has to be figured out (but that looks easy/easier)

@kiwibrowser
Copy link

It's my first airdrop btw, I just look into the project because it's fun to learn, and because it wasn't working as in the docs (otherwise crypto is not my cup of tea at all)

@pinheadmz
Copy link
Member

@kiwibrowser thank you for your patience and interest!
If you are able to complete an airdrop proof with secure hardware, it would be massively helpful to have a guide or gist or readme or blog post or something to help future users with the same issue.

Please let us know if you are able to figure it out, or have any other questions.

@metaspartan
Copy link

So does anyone have any instructions at all on how to actually sign the raw data for the hs-airdrop with a Yubikey? Trying just the exported secret key stub returns an "Unknown S2K Function"

@shankerwangmiao
Copy link

@carsenk For gpg keys, if your master key is stored in a hardware key, it seems that there is no way to claim currently. Otherwise, you can export the master key and use this tool normally.

@shankerwangmiao
Copy link

@pinheadmz I wonder if claiming the airdrop requires not only signing some data but also decrypting. If so, since for secure hardwares, the usage of a private key is limited, there would be no way to claim the airdrop using secure hardwares.

@metaspartan
Copy link

@shankerwangmiao It is stored on it, though I was able to export it, unless its just a stub of the secret key? I was looking at #44 and seemed to get a bit further without the Unknown S2K function but still getting an error....I feel this would pose a major problem for a majority of those trying to claim the airdrop as most use a smartcard for their GPG keys on Github for the best security.....Really hope something can be worked out here.

@shankerwangmiao
Copy link

@carsenk A stub won't work. It needs the private key itself.

@metaspartan
Copy link

@carsenk A stub won't work. It needs the private key itself.

So I exported the secret key (private GPG key) from my Yubikey, but from what I understand it will not accept it if it has subkeys except for one subkey with Signing permission?

@shankerwangmiao
Copy link

@carsenk Only the master private key is needed. So you need to verify which private key is on your Yubikey, a subkey or the master key. If your master key is on your Yubikey, there is no way to export it from your Yubikey and it seems that currently we have no method to claim the airdrop. If not, you can follow what is discussed in #44.

@cmars
Copy link

cmars commented Jan 6, 2021

From the main README:

In past weeks, it's become apparent that there are now various scams and phishing attempts targeting GitHub users. Handshake contributors will never ask you for your private keys, and revealing your private key to anyone is not necessary to redeem the airdrop.

Yet, that's exactly what's being asked for in order to receive the airdrop with this tool?

This seems like an interesting and well-intentioned project, but you have to expect some skepticism on matters of security. Private keys are kept on hardware devices for a good reason. Without carefully reading and completely understanding what the source code of hs-airdrop is doing, how can we distinguish it from a clever attempt to compromise supply-chains? Why would direct access be needed to the private key? I can only think of three reasons:

  1. The tool didn't bother to support it initially (hey, I get it, SC integration probably isn't easy!) but it's eventually possible, and the airdrop private key derivation algorithm could be published to allow us to do it ourselves.
  2. The airdrop used our public key in some novel "roll-your own crypto" kind of way, so standard decrypt/signing operations will not work -- but it's also more likely to be an insecure airdrop if this is the case.
  3. Run away, it's a trap!

Hopefully it's (1). In that case, not claiming the drop yet should be no different from HODLing, so there's really no rush to claim the airdrop unless you're looking to ride a pump-and-dump wave at the launch or something. I would not expose my private keys for this.

@pinheadmz
Copy link
Member

@cmars it's actually closer to (2): https://fc20.ifca.ai/preproceedings/54.pdf

@natevw
Copy link

natevw commented May 10, 2021

@pinheadmz So what is meant by the "Fallback for HSMs" section still in the current README?

In the event that your key is not accessible by the signing tool, the signing tool can present you with the raw data needed to be signed. Your regular key is also included in the merkle tree (concatenated with a random nonce, seeded by the encrypted scalar to preserve privacy). Unfortunately, this will forgo the privacy preservation mechanism described above.

The OP here quotes that same thing but then all the discussion that follows gives the impression that:

  • the signing tool can't actually (or at least doesn't currently) present the raw data needed to be signed
  • there's not in practice an option to leverage the no-privacy version of "your regular key" either?? [does this have to do with the "bare goosig" change that led to the 5a6f57e documentation update?]

Basically just trying to get a handle on why the documentation still makes this sound easy when it seems to be a dead end?

@pinheadmz
Copy link
Member

@natevw Handshake is an experiment, a work-in-progress with no funding and a serious lack of contributors. I believe HSM signing can still happen it just takes work. There are a few good points brought up in this thread:

  • The airdrop starts by decrypting a nonce, there is nothing special about this but it works by brute-forcing a "bucket" of nonces and so integrating with an HSM will require a modified script (and I don't even know if all HSMs can decrypt as well as sign?)
  • The --bare option is what disables the tweak and reveals your raw public key on the blockchain. The tweak for ECDSA keys is the usual point-addition operation. For RSA keys, the goosig scheme was invented and is now disabled (the blockchain only allowed goosig for 13 months). So ECDSA key holders still have the option to blind their key, but RSA key holders MUST pass --bare to hs-airdrop when signing. So back to your comment: HSMs should be able to sign a raw proof if --bare is used, because then no weird operations are applied to the raw key.

@bert2002
Copy link

Just tried to use it with a key on a Yubikey through ssh agent, but no luck :(

@Anunayj
Copy link

Anunayj commented May 27, 2021

Okay I did some digging on how this could be done, and here's what I found:-

  1. If you use a PKCS11 token for ssh (For example yubikey), You should be able to hook pkcs11-tool to do decryption and signing for you.
  2. If you use a TPM 2.0 compatible TPM, look at tpm2-tools
  3. If you use a OpenPGP card, we're in bit of a pickle. OpenPGP specification computes signature a little differently, So you can't directly use gpg to do the signing. Someone will need to write a lower level tool that directly communicates with the device to do the signing.
    If you use a Ledger for your gpg keys, you can export and extract them. This could very well be the case with other JavaCards, so check with yours.

Ofcourse someone will need to write the code for doing this, and currently I don't think this would be on top of anyone's list (Most people don't have the financial incentive to figure this, and the number of people unable to claim their airdrop because of this don't seem to be very large). If you're affected, consider looking into this or offering up a bounty.
If your card comes with a tool that allows you to directly communicate with the device and access the RSA keys used (to decrypt/sign), implementing this should be relatively easy.

Though considering the complexity of supporting so many different devices and protocols. (or hacking around gnupg's source code) It is very unlikely someone will come up to implement this for cheap/free. It's honestly a shame that the founders did not take this in consideration when creating the airdrop, when OpenPGP standard exists exactly to address this problem.

@Anunayj
Copy link

Anunayj commented Jun 7, 2021

Also I just found OpenPGPpy which would make this process a lot easier for opengpg cards.

@roblabla
Copy link

roblabla commented Aug 23, 2021

I went deep into this, and I've come to the conclusion that people who store their RSA keys on an OpenPGP token will not be able to participate in this drop (Small edit: People using ECDSA keys may have better luck). Here's why: In order to participate in the drop, the user needs the ability to decrypt a nonce using OAEP padding. The OpenPGP Smartcard specification only supports the older PKCSv1.5 padding, not OAEP. As such, yubikey (and other HSM) users are SOL

This nonce is necessary as it changes the hash of the AirdropKey, which means despite the nonce not being used in the actual signature algorithm, we cannot find the subtree index in the merkle tree to generate our proof.

There is basically no way out of this problem. The OpenPGP Smartcard Specification is as low-level as you'll get. So to anyone in the same situation as I, using a yubikey in OpenPGP mode: Better luck next time.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests