Skip to content

Instantly share code, notes, and snippets.

@Aob1987
Forked from axic/HandshakeKeys.md
Created February 3, 2020 20:05
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save Aob1987/fa428c931904e86f0a9a5e16f05b3b44 to your computer and use it in GitHub Desktop.
Save Aob1987/fa428c931904e86f0a9a5e16f05b3b44 to your computer and use it in GitHub Desktop.
Handshake - Keys and Addresses

Handshake - Keys and Addresses

DISCLAIMER: There is no warranty for any of the below be correct, up to date, or valid in any form. This is not a specification, only the braindump of some code digging. In fact it is very likely all of this is incorrect and useless. DO NOT PUT TOKENS INTO ADDRESSES GENERATED USING THE INFORMATION BELOW.

From their website:

Decentralized certificate authority and naming

An experimental peer-to-peer root DNS.

Handshake aims to "airdrop" a large quantity of the tokens to developers (backed by Github and Freenode profiles) or well known people (backed by PGP WoT).

In Q3/Q4 2018 the airdrop verification was done through their website and offered two options to generate an address: a web wallet or an offline tool. In 2019 this changed into including a large set of developers in a merkle tree and letting them prove their credentials after launch.

I was wondering what cryptography it is using and how it encodes addresses. The whitepaper doesn't include in depth detail about this and couldn't find any significant documentation. Only way to know is by digging through the source. Examined both the old faucet tool and the new airdrop tool.

Note: this document only focuses on the minimum needed to generate valid keys for the airdrop. There is a lot more needed to interact with the network.

Keys

Handshake currently follows the mainstream by using ECC with the secp256k1 curve. The official tools create HD wallets using BIP32 derivation, BIP44 derivation paths and BIP39 mnemonics. Nothing new under the sun, pretty standard practice.

The important piece of information is the coin type it uses: 5353. This is documented in the official registry, SLIP-44.

The official tools always generate a single key:

  • purpose: 44
  • coin: 5353
  • account: 0
  • change: 0
  • account_index: 0

or m/44'/5353'/0'/0/0 in short.

Address encoding

We can split address encoding into two parts:

  • creating an address out of a public key
  • encoding such address into a user-readable and safe form

Public key to addresses

Handshake uses compressed public keys and hashes them using Blake2b without an optional key and a desired output hash length of 20 bytes.

Readable Addresses

Addresses are encoded using Bech32. Bech32 was created to encode SegWit addresses in Bitcoin.

Depending on the network, it has four different "HRPs" (HRP stands for "Human-Readable Part" of the Bech32 otuput):

  • Mainnet: hs
  • Testnet: ts
  • Regtest: rs
  • Simtest: ss

The payload for Bech32 has a version number and data. The single case we are interested in is version 0 which stores the 20-byte long hashed address: uint8(0) .. address_hash, where .. means concatenation.

Note: it seems there is code in the faucet to support SegWit-style programs and potentially other features, hence the version number.

Summary

A user readable address (of a mainnet account) is the output of Bech32('hs', uint8(0) .. blake2b(compressed_pub_key, output_size = 20)), where .. means concatenation.

@Aob1987
Copy link
Author

Aob1987 commented Feb 24, 2020

Handshake - Keys and Addresses

DISCLAIMER: There is no warranty for any of the below be correct, up to date, or valid in any form. This is not a specification, only the braindump of some code digging. In fact it is very likely all of this is incorrect and useless. DO NOT PUT TOKENS INTO ADDRESSES GENERATED USING THE INFORMATION BELOW.

From their website:

Decentralized certificate authority and naming

An experimental peer-to-peer root DNS.

Handshake aims to "airdrop" a large quantity of the tokens to developers (backed by Github and Freenode profiles) or well known people (backed by PGP WoT).

In Q3/Q4 2018 the airdrop verification was done through their website and offered two options to generate an address: a web wallet or an offline tool. In 2019 this changed into including a large set of developers in a merkle tree and letting them prove their credentials after launch.

I was wondering what cryptography it is using and how it encodes addresses. The whitepaper doesn't include in depth detail about this and couldn't find any significant documentation. Only way to know is by digging through the source. Examined both the old faucet tool and the new airdrop tool.

Note: this document only focuses on the minimum needed to generate valid keys for the airdrop. There is a lot more needed to interact with the network.

Keys

Handshake currently follows the mainstream by using ECC with the secp256k1 curve. The official tools create HD wallets using BIP32 derivation, BIP44 derivation paths and BIP39 mnemonics. Nothing new under the sun, pretty standard practice.

The important piece of information is the coin type it uses: 5353. This is documented in the official registry, SLIP-44.

The official tools always generate a single key:

  • purpose: 44
  • coin: 5353
  • account: 0
  • change: 0
  • account_index: 0

or m/44'/5353'/0'/0/0 in short.

Address encoding

We can split address encoding into two parts:

  • creating an address out of a public key
  • encoding such address into a user-readable and safe form

Public key to addresses

Handshake uses compressed public keys and hashes them using Blake2b without an optional key and a desired output hash length of 20 bytes.

Readable Addresses

Addresses are encoded using Bech32. Bech32 was created to encode SegWit addresses in Bitcoin.

Depending on the network, it has four different "HRPs" (HRP stands for "Human-Readable Part" of the Bech32 otuput):

  • Mainnet: hs
  • Testnet: ts
  • Regtest: rs
  • Simtest: ss

The payload for Bech32 has a version number and data. The single case we are interested in is version 0 which stores the 20-byte long hashed address: uint8(0) .. address_hash, where .. means concatenation.

Note: it seems there is code in the faucet to support SegWit-style programs and potentially other features, hence the version number.

Summary

A user readable address (of a mainnet account) is the output of Bech32('hs', uint8(0) .. blake2b(compressed_pub_key, output_size = 20)), where .. means [concatenation.](hs1q7ad0a3lsdg8jcsxu9z9jmcf7lnetck4szx64kk)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment