Compare commits

...

2 commits

Author SHA1 Message Date
Richard van der Hoff
06a1b66ea9 Update megolm.md
69+64 != 129
2022-11-30 13:06:04 +00:00
Richard van der Hoff
2ac6177f9c Simplify the ratchet 2022-11-30 12:26:48 +00:00

View file

@ -28,56 +28,18 @@ channels. Provided that peer-to-peer channel provides authenticity of the
messages to the participants and deniability of the messages to third parties, messages to the participants and deniability of the messages to third parties,
the Megolm session will inherit those properties. the Megolm session will inherit those properties.
## The Megolm ratchet algorithm ## The Megolm V2 ratchet algorithm
The Megolm ratchet $`R_i`$ consists of four parts, $`R_{i,j}`$ for The Megolm V2 ratchet $`R_i`$ is based on a single key whose length depends
$`j \in {0,1,2,3}`$. The length of each part depends on the hash function on the hash function in use (256 bits for this version of Megolm).
in use (256 bits for this version of Megolm).
The ratchet is initialised with cryptographically-secure random data, and The key is initialised with cryptographically-secure random data, and
advanced as follows: after each use is advanced by setting $`R_{i+1} = H(R_i)`$, where $`H`$ is
a hash function.
```math The ratchet value, $`R_{i}`$, is hashed to generate the keys used
\begin{aligned} to encrypt each message. This scheme allows a client
R_{i,0} &= to decrypt chat history onwards from the earliest value of the ratchet
\begin{cases}
H_0\left(R_{2^{24}(n-1),0}\right) &\text{if }\exists n | i = 2^{24}n\\
R_{i-1,0} &\text{otherwise}
\end{cases}\\
R_{i,1} &=
\begin{cases}
H_1\left(R_{2^{24}(n-1),0}\right) &\text{if }\exists n | i = 2^{24}n\\
H_1\left(R_{2^{16}(m-1),1}\right) &\text{if }\exists m | i = 2^{16}m\\
R_{i-1,1} &\text{otherwise}
\end{cases}\\
R_{i,2} &=
\begin{cases}
H_2\left(R_{2^{24}(n-1),0}\right) &\text{if }\exists n | i = 2^{24}n\\
H_2\left(R_{2^{16}(m-1),1}\right) &\text{if }\exists m | i = 2^{16}m\\
H_2\left(R_{2^8(p-1),2}\right) &\text{if }\exists p | i = 2^8p\\
R_{i-1,2} &\text{otherwise}
\end{cases}\\
R_{i,3} &=
\begin{cases}
H_3\left(R_{2^{24}(n-1),0}\right) &\text{if }\exists n | i = 2^{24}n\\
H_3\left(R_{2^{16}(m-1),1}\right) &\text{if }\exists m | i = 2^{16}m\\
H_3\left(R_{2^8(p-1),2}\right) &\text{if }\exists p | i = 2^8p\\
H_3\left(R_{i-1,3}\right) &\text{otherwise}
\end{cases}
\end{aligned}
```
where $`H_0`$, $`H_1`$, $`H_2`$, and $`H_3`$ are different hash
functions. In summary: every $`2^8`$ iterations, $`R_{i,3}`$ is
reseeded from $`R_{i,2}`$. Every $`2^{16}`$ iterations, $`R_{i,2}`$
and $`R_{i,3}`$ are reseeded from $`R_{i,1}`$. Every $`2^{24}`$
iterations, $`R_{i,1}`$, $`R_{i,2}`$ and $`R_{i,3}`$ are reseeded
from $`R_{i,0}`$.
The complete ratchet value, $`R_{i}`$, is hashed to generate the keys used
to encrypt each message. This scheme allows the ratchet to be advanced an
arbitrary amount forwards while needing at most 1020 hash computations. A
client can decrypt chat history onwards from the earliest value of the ratchet
it is aware of, but cannot decrypt history from before that point without it is aware of, but cannot decrypt history from before that point without
reversing the hash function. reversing the hash function.
@ -85,7 +47,6 @@ This allows a participant to share its ability to decrypt chat history with
another from a point in the conversation onwards by giving a copy of the another from a point in the conversation onwards by giving a copy of the
ratchet at that point in the conversation. ratchet at that point in the conversation.
## The Megolm protocol ## The Megolm protocol
### Session setup ### Session setup
@ -95,8 +56,7 @@ session consists of three parts:
* a 32 bit counter, $`i`$. * a 32 bit counter, $`i`$.
* an [Ed25519][] keypair, $`K`$. * an [Ed25519][] keypair, $`K`$.
* a ratchet, $`R_i`$, which consists of four 256-bit values, * a ratchet, $`R_i`$, consisting of a single 256-bit value.
$`R_{i,j}`$ for $`j \in {0,1,2,3}`$.
The counter $`i`$ is initialised to $`0`$. A new Ed25519 keypair is The counter $`i`$ is initialised to $`0`$. A new Ed25519 keypair is
generated for $`K`$. The ratchet is simply initialised with 1024 bits of generated for $`K`$. The ratchet is simply initialised with 1024 bits of
@ -157,18 +117,16 @@ received the session data.
### Advancing the ratchet ### Advancing the ratchet
After each message is encrypted, the ratchet is advanced. This is done as After each message is encrypted, the ratchet is advanced. This is done as
described in [The Megolm ratchet algorithm](#the-megolm-ratchet-algorithm), using the following definitions: described in [The Megolm V2 ratchet algorithm](#the-megolm-v2-ratchet-algorithm),
using the following definition for $`H`$:
```math ```math
\begin{aligned} \begin{aligned}
H_0(A) &\equiv \operatorname{HMAC}(A,\text{``\char`\\x00"}) \\ H(A) &\equiv \operatorname{HMAC}(A,\text{``\char`\\x00"}) \\
H_1(A) &\equiv \operatorname{HMAC}(A,\text{``\char`\\x01"}) \\
H_2(A) &\equiv \operatorname{HMAC}(A,\text{``\char`\\x02"}) \\
H_3(A) &\equiv \operatorname{HMAC}(A,\text{``\char`\\x03"}) \\
\end{aligned} \end{aligned}
``` ```
where $`\operatorname{HMAC}(A, T)`$ is the HMAC-SHA-256 of ``T``, using ``A`` as the where $`\operatorname{HMAC}(A, T)`$ is the HMAC-SHA-256 of $`T`$, using $`A`$ as the
key. key.
For outbound sessions, the updated ratchet and counter are stored in the For outbound sessions, the updated ratchet and counter are stored in the
@ -191,16 +149,16 @@ session.
The session sharing format is as follows: The session sharing format is as follows:
``` ```
+---+----+--------+--------+--------+--------+------+-----------+ +---+----+------+------+-----------+
| V | i | R(i,0) | R(i,1) | R(i,2) | R(i,3) | Kpub | Signature | | V | i | R(i) | Kpub | Signature |
+---+----+--------+--------+--------+--------+------+-----------+ +---+----+------+------+-----------+
0 1 5 37 69 101 133 165 229 bytes 0 1 5 37 69 133 bytes
``` ```
The version byte, ``V``, is ``"\x02"``. The version byte, ``V``, is ``"\x04"``.
This is followed by the ratchet index, $`i`$, which is encoded as a This is followed by the ratchet index, $`i`$, which is encoded as a
big-endian 32-bit integer; the ratchet values $`R_{i,j}`$; and the public big-endian 32-bit integer; the ratchet value $`R_{i}`$; and the public
part of the Ed25519 keypair $`K`$. part of the Ed25519 keypair $`K`$.
The data is then signed using the Ed25519 keypair, and the 64-byte signature is The data is then signed using the Ed25519 keypair, and the 64-byte signature is
@ -221,16 +179,16 @@ format](#session-sharing-format) except for dropping the signature.
The Megolm session export format is thus as follows: The Megolm session export format is thus as follows:
``` ```
+---+----+--------+--------+--------+--------+------+ +---+----+------+------+
| V | i | R(i,0) | R(i,1) | R(i,2) | R(i,3) | Kpub | | V | i | R(i) | Kpub |
+---+----+--------+--------+--------+--------+------+ +---+----+------+------+
0 1 5 37 69 101 133 165 bytes 0 1 5 37 69 bytes
``` ```
The version byte, ``V``, is ``"\x01"``. The version byte, ``V``, is ``"\x03"``.
This is followed by the ratchet index, $`i`$, which is encoded as a This is followed by the ratchet index, $`i`$, which is encoded as a
big-endian 32-bit integer; the ratchet values $`R_{i,j}`$; and the public big-endian 32-bit integer; the ratchet value $`R_{i}`$; and the public
part of the Ed25519 keypair $`K`$. part of the Ed25519 keypair $`K`$.
### Message format ### Message format