26/WAKU2-PAYLOAD defines how message payloads can be encrypted using supported symmetric/asymmetric primitives but it does not specify how users can possibly exchange encryption keys.
This post proposes to integrate multiple Noise handshakes in Waku2 to address the current lack of key-exchange protocols. This will provide a native way to instantiate end-to-end (E2E) encrypted communication channels among Waku2 users.
Furthermore, different handshakes can be combined and executed one after each other to define so called Noise pipes: these can be particularly useful to authenticate multiple static keys employed by different applications (e.g., Ethereum public static keys and E2E encrypted chats static keys), but also ease key revocation and reduce possible leakages in case of key compromises.
A Noise handshakes consists of multiple messages exchanged between two parties: an
Initiator and a
Responder, or, simply, Alice and Bob.
At the end of a Noise handshake, Alice and Bob will share some cryptographic material used to protect later exchanged messages.
The shared key material is derived from one or multiple Diffie-Hellman operations between parties’ temporary ephemeral keys
e and/or long-term static keys
s. Using a Key Derivation Function (KDF), encryption and decryption keys are derived similarly as in Double Ratchet but with different processing rules.
Depending on the handshake pattern executed, different security guarantees are provided on after-handshake exchanged messages.
All handshakes we propose in this post provide the following security properties:
Strong forward secrecy: messages cannot be decrypted even if the recipient’s static key is later compromised (unless an active attacker was impersonating the recipient since the beginning of the handshake).
Integrity: guaranteed by recommended encryption primitives, e.g. AEAD block ciphers like
Authentication resistant to key-compromise impersonation: authenticating data attached to exchanged messages cannot be forged even in the case either sender’s or recipient’s static key is compromised.
Identity-hiding: a passive attacker who reads exchanged handshake messages is not able to retrieve or guess parties’ static keys. Weaker guarantees can be granted instead in case of active attackers: these are briefly reported in each handshake description.
The Noise handshakes we suggest address four typical scenarios occurring when an encrypted communication channel between Alice and Bob is going to be created:
- Alice and Bob know each others’ static key.
- Alice knows Bob’s static key;
- Alice and Bob share no key material and they don’t know each others’ static key.
- Alice and Bob share some key material, but they don’t know each others’ static key.
The handshakes we propose for integration are named
XXpsk0, respectively, and would provide a key-exchange mechanism for most Waku2 use-cases.
An active attacker who compromised one party’s static key may lower the identity-hiding security guarantees provided by some handshakes. In our security model we exclude such adversary, but for completeness we report a summary of possible de-anonymization attacks that can be performed by an active attacker.
If Alice and Bob know each others’ static key (e.g., these are public or were already exchanged in a previous handshake) , they can execute a
K1K1 handshake. Using Noise notation (Alice is on the left) this can be sketched as:
K1K1: -> s <- s ... -> e <- e, ee, es -> se
We note that here only ephemeral keys are exchanged. This handshake is useful in case Alice needs to instantiate a new separate encrypted communication channel with Bob, e.g. opening multiple parallel connections, file transfers, etc.
Security considerations on identity-hiding (active attacker): no static key is transmitted, but an active attacker impersonating Alice can check candidates for Bob’s static key.
Here, Alice knows how to initiate a communication with Bob and she knows his public static key: such discovery can be achieved, for example, through a publicly accessible register of users’ static keys, smart contracts, or through a previous public/private advertisement of Bob’s static key.
A Noise handshake pattern that suits this scenario is
XK1: <- s ... -> e <- e, ee, es -> s, se
Within this handshake, Alice and Bob reciprocally authenticate their static keys
s using ephemeral keys
e. We note that while Bob’s static key is assumed to be known to Alice (and hence is not transmitted), Alice’s static key is sent to Bob encrypted with a key derived from both parties ephemeral keys and Bob’s static key.
Security considerations on identity-hiding (active attacker): Alice’s static key is encrypted with forward secrecy to an authenticated party. An active attacker who impersonates Alice can check candidates for Bob’s static key against recorded/accepted exchanged handshake messages.
If Alice is not aware of any static key belonging to Bob (and neither Bob knows anything about Alice), she can execute an
XX handshake, where each party tranXmits to the other its own static key.
The handshake goes as follows:
XX: -> e <- e, ee, s, es -> s, se
We note that the main difference with
XK1 is that in second step Bob sends to Alice his own static key encrypted with a key obtained from an ephemeral-ephemeral Diffie-Hellman exchange.
This handshake can be slightly changed in case both Alice and Bob pre-shares some secret
psk which can be used to strengthen their mutual authentication during the handshake execution. One of the resulting protocol, called
XXpsk0, goes as follow:
XXpsk0: -> psk, e <- e, ee, s, es -> s, se
The main difference with
XX is that Alice’s and Bob’s static keys, when transmitted, would be encrypted with a key derived from
psk as well.
Security considerations on identity-hiding (active attacker): Alice’s static key is encrypted with forward secrecy to an authenticated party for both
XXpsk0 handshakes. In
XX, Bob’s static key is encrypted with forward secrecy but is transmitted to a non-authenticated user which can then be an active attacker. In
XXpsk0, instead, Bob’s secret key is protected by forward secrecy to a partially authenticated party (through the pre-shared secret
psk but not through any static key), provided that
psk was not previously compromised (in such case identity-hiding properties provided by the
XX handshake applies).
We propose to implement and integrate in Waku2 the suggested Noise handshakes in the following order:
This is motivated by the following facts:
XXpsk0can be transformed to an
XXhandshake using an empty
XXcan be transformed to an
XK1handshake if Bob doesn’t transmit to Alice his static key;
XK1can be transformed to
K1K1if Alice doesn’t transmit to Bob her static key.
(we note, however, that the logic used to derive the shared key material will slightly differ among these handshakes).
In other words, a working implementation for a
K1K1 handshake can be easily extended to an implementation for
XK1, which in turn can be further extended to an implementation for the
XXpsk0 handshakes. In this way, each new added handshake implementation can be tested backwards with minor modifications.
Different trade-offs exist when adopting the suggested handshakes:
- Encrypted messages satisfy all the required security guarantees only after the first 2 handshake steps are complete, i.e. after 1 round trip time communication or 1-RTT.
K1K1, Alice can immediately encrypt messages (0-RTT) under Bob’s static key exceptionally using ECIES encryption, but such messages will not be protected by perfect forward secrecy. After-handshake messages must be encrypted instead according to Noise Protocol processing rules specifications.
- Parties not necessarily need to be online at the same time to execute an handshake, but they then should rely on 11/WAKU2-RELAY and 13/WAKU2-STORE to complete it.
- If a symmetric encryption key is compromised, all messages encrypted under that key (or under a publicly computable key derived from it), can be decrypted. To reduce the number of plaintext leaked, parties should execute after each exchanged encrypted message an ephemeral-ephemeral Diffie-Hellman to update their encryption/decryption keys.
- Users are required to locally store a cryptographic state (i.e., different symmetric and asymmetric keys) for each party with whom they have executed and handshake. If any of such state is lost or corrupted, it cannot be recovered and messages cannot be properly encrypted/decrypted.
- Previous trade-offs applies to each handshake executed within a Noise pipe. Hence, the latter have an increased complexity in terms of keys management.
In light of internal discussions, we believe that the proposed handshakes would be able to address most of the current top use-cases for Waku2, providing high security guarantees in just 1 Round Trip Time communication.
Once processing rules are fully implemented, support to more handshakes can be easily added by just specifying their respective handshake pattern, thus making Waku2 flexible enough to easily address many different application scenarios where a secure communication channel is needed.
Furthermore, Noise handshakes modularity allows instantiation of a secure communication channel based on parties’ reciprocal knowledge, removing the need to exchange any redundant authentication key material.
- Noise Explorer: formal verification of fundamental and custom Noise protocols:
Related PR and issues: