It has been a while since the last update. I have since received a number of questions regarding the status and development of the “Ryder” Blockstack hardware wallet prototype which I will try to address in this post.
Why a hardware device?
The current Blockstack authentication flows (Browser & Connect) store an encrypted version of the Master Private Key / BIP39 wallet seed in browser storage. Storing private keys on a computer that is connected to the internet in any form is dangerous and stories of people losing their crypto tokens due to private key theft are plentiful. Keeping private keys private is absolutely paramount in the Blockstack ecosystem, as they also form the basis of the user’s Decentralised Identities (DIDs). If private keys in the Blockstack authentication chain are stolen, it compromises the owner’s entire Decentralised ID keychain or a portion thereof. It means that all his or her private information stored on the associated Gaia Buckets is now accessible to the attacker forever. It has been shown before that it can be relatively effortless for attackers to steal private keys within many popular multi-user Blockstack dapps.
On top of that, the user experience design for the Connect authentication flow leads to bad security practices, as users are prompted to enter their “12 word secret key” when authenticating. Entering a seed on a website is never a good idea, and people with less experience may even leave text files with seeds lying around on their computer or USB devices. I invite you to read the article Private Keys + Websites = 💀 by MyCrypto, the creators of MyEtherWallet, and why they decided not not accept private key input on their platform anymore. And if you want to take the deep dive, take a look at the Cure53 pentest report for MyEtherWallet and their recommendation on page four.
Another big problem is that the current authentication flow makes it very difficult to bring your DIDs with you and set them up on other devices securely. It ties into the question of how to manage your seeds. Do you keep a note in your wallet or enter them into your smartphone? Even if the app you are using encrypts the data, the smartphone itself remains a huge attack vector. Perhaps one might argue that you should not bring your DIDs with you in the first place, but that would be a regression. A Trezor allows you bring your wallet with you and safely transact Bitcoin even when using a machine that is completely compromised. It should also be the case with DIDs.
The current Ryder prototype is a full implementation of the current Blockstack authentication algorithm that aims to address these issues and more. Along with a simple bridge service, the prototype already functions as a full, 100% compatible drop-in replacement for the Blockstack Browser. It currently features new wallet generation in hardware, recovery via seed input, identity selection, and more. To be compatible with the current authentication flow, it still exports the app private key, but this is merely a temporary measure to guarantee compatibility. The prototype is fully functional and can be used today.
However, the ultimate goal of the Ryder is to be more than just a key exporting hardware keychain and STX wallet. Instead, the device can be a total replacement for all crypto-related operations for Blockstack. The Ryder should also perform the cryptographic operations needed to store and read files. An upgraded Blockstack authentication system could communicate with the Ryder hardware directly, and stream file data to be encrypted or decrypted. The Ryder will, after confirmation by the user, stream the decrypted data back. The Blockstack dapp will then no longer hold any private key, and the user, by means of his or her Ryder, will be in ultimate control. The user is safe even if the dapp or his or her whole computer is compromised. Additionally, the user can safely bring his or her identities anywhere in the world, and use them securely on any computer.
It my strong conviction because of the aforementioned, that a hardware device is required for the continued success of the Blockstack ecosystem and to fulfil its promise of bringing about the decentralised internet.
What I have been focusing on since the last post are the user experience and the API layer. The programming of the hardware device itself has only seen slight modification. As mentioned previously, it is functional and the limitations seen in the videos that were released prior were purely due to the limited interface itself. I thus upgraded that interface, adding identity selection and profile & name resolution. The new authentication flow looks as follows, after clicking Sign In on any Blockstack app:
Identities are exported from the device instantly and the bridge resolves the username. The left-hand side shows which app you are attempting to sign in to and which permissions it is requesting — much like the Blockstack Browser does.
After selecting an identity from the list, the authentication request is sent to the device and you are presented with a confirmation screen on both sides. In the future, the selection interface could render a graphic of the device so that the user can see exactly what to expect.
If the identity numbers match and you are ready to sign in, simply press confirm and the sign-in process is completed.
The video above shows the whole process.
A low-level NodeJS API has been created to facilitate communication between the hardware and desktop applications. The API is completely asynchronous and can be used with the
async/await pattern. It allows developers to easily create applications without running the risk of blocking the thread and await user input or confirmation when necessary. Commands are queued and resolved in the order they come in. If a sequence of commands/responses with a guaranteed order is required, an exclusive lock can be requested. The locking mechanism is likewise asynchronous and can be awaited.
Once the low-level API is completed, a more straightforward higher-level API will be built on top of it so that developers that are uncomfortable dealing with bits and bytes can easily interface with the hardware as well.
An overview of the main capabilities of the prototype is as follows. The device can:
- Generate fresh wallets on-device. The process displays the BIP39 seed on screen much like other crypto hardware wallets out there;
- Restore from an existing BIP39 seed. The device prompts the user to enter the words in a random order as directed on screen;
- Factory reset itself. After a warning and user confirmation, it will clear the stored master key so that it can be initialised with a different wallet;
- Export identity public keys by number (path);
- Export app & identity private keys after receiving an app domain and user confirmation. A temporary measure to be compatible with the current authentication model.
The next iteration will generate the authentication response completely on the device. It is of course the aim to get rid of exporting the app private key to the app altogether; but as this requires a custom BlockstackJS library, it is reserved for a future iteration. Other security features like a PIN and lock timer will be added as time goes on. Another idea is to have an emergency PIN that clears the device when entered.
I am currently in talks with a few different entities to create the next iteration of the prototype. The cardboard will be replaced by a 3D printed enclosure soon. The dream of creating a wearable version may not be too far off either. However, everything from the name to its final form is still up in the air and I am very open to suggestions and feedback. I intend to propose this project to the newly formed Stacks Foundation as a possible recipient of a grant. It would help make the device a reality, make it open source, and get them out to everyone. If you like the project and would like to get your hands on one in the future, voicing your support is much appreciated. Together we can make this happen.
You can reach out to me on Twitter: @MarvinJanssen.