Encrypted rooms in Matrix use Olm and Megolm, two related ratchet protocols. The effect is that even the homeserver operator (us — Meldry) can only see ciphertext for encrypted rooms. Decryption happens in your client, using keys that never leave your devices.
This page explains the moving parts so you understand what happens when Element asks you to verify a device or save a recovery key.
Why the split? Double Ratchet gives perfect forward secrecy per pair of devices, but doesn't scale to a group — you'd need O(n²) ratchets. Megolm gives one-way forward secrecy per room (past messages are safe if a current key leaks, but not the other way around) while keeping the cost O(n) per membership event.
Rotation looks like a tiny pause in message flow — you'll occasionally see "Unable to decrypt" for a split second while the new session propagates, then it self-heals.
Every device you sign in on generates its own set of long-lived identity keys (a Curve25519 + Ed25519 pair) on first launch. These are uploaded to your homeserver so other people can encrypt to you, but the private halves never leave the device.
When Alice starts talking in an encrypted room, her client:
None of this is visible to the user — it all happens in the client automatically. What the user sees is the verification step.
Because keys are per device, the first time you sign in from a new phone your laptop sees an "unverified device" warning. Verification is how you confirm "yes, that new device is really me (or really the friend I'm talking to)":
Cross-signing is the mechanism that makes per-device verification scale. It introduces three long-lived keys per account:
End result: you verify once per person (not once per device), and verification persists across reinstalls and new devices.
Your cross-signing secret keys, Megolm backup key and other long-lived secrets are encrypted with a passphrase you choose, then stored on the homeserver in an opaque blob called SSSS (Secure Secret Storage and Sharing). You unlock it on a new device by entering the passphrase (or pasting the recovery key), and only you can unlock it — the server can't read it.
This is how a fresh device bootstraps itself into an existing encrypted account without a second device being present. Without SSSS you'd need either your old device to cross-sign the new one manually, or you'd have to start a fresh cross-signing identity (and re-verify everyone).
SSSS uses PBKDF2-HMAC-SHA512 to derive the key from your passphrase. A well-chosen passphrase (or a random recovery key) is the only thing protecting your secrets at rest on the server.
Individual Megolm sessions are separately backed up to the homeserver, encrypted with a key that's itself stored in SSSS. This lets you decrypt old history on a new device: sign in, unlock SSSS with your passphrase, fetch the backup, decrypt the old Megolm sessions, decrypt the old messages.
Without key backup, signing in fresh and having lost your only other device means losing your encrypted history — by design. The server never had the keys, and we can't reconstruct them.
Practical implication for Meldry users: when you first set up encryption, Element prompts you to save a recovery key. Save it. A lost phone + no other device + no recovery key = lost encrypted history. There is no "reset password" that recovers the messages.
Encrypted (E2EE):
Not encrypted:
If a room was public first and encryption was turned on later, messages after the enable are encrypted but messages from before are not. Turning encryption on is a one-way switch — you can't turn it off once enabled.
"Unable to decrypt" errors. Usually means you don't have the Megolm session for that message. Happens when:
"Verify this device" prompts on every restart. You haven't set up cross-signing. Do it from Element's Settings → Security & Privacy → Cross-signing → Set up.
"Session expired / not found" on the server. Very rare — usually a homeserver-side bug. Restart the client; if it persists, file a support ticket.