Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Initial MSC for encrypting recovery keys for online megolm backups #1686

Closed
wants to merge 2 commits into from

Conversation

ara4n
Copy link
Member

@ara4n ara4n commented Sep 26, 2018


[MSC1219](https://github.com/matrix-org/matrix-doc/issues/1219) proposes an API for optionally storing encrypted megolm keys on your homeserver, so if a user loses all their devices, they can still recover their history. The megolm keys are public-key encrypted using a private Curve25519 key that only the end-user has.

However, there are usability concerns about users having to store their Curve25519 recovery private key in a secure manner. Casual users are likely to be scared away by having to file away a relatively long (e.g. 10 word) generated recovery key.
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I presume, if you are taking inspiration from FileVault, the system should also ask you to file away the generated key anyway? IIRC FileVault both encrypts your key with your UNIX password and has you write down the seed for the unencrypted key somewhere, just in case you forget your password.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yup. I will clarify, but the idea is that backing up your megolm keys, and backing up the recovery key is optional too. You can always keep a copy of the recovery key too offline.

We propose storing it using the /account_data API:

```json
PUT /_matrix/client/r0/user/{userId}/account_data/m.recovery_key
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The recovery key will be different for different backup versions, so maybe we should have a different name for each version. Also, we should probably put it in the m.megolm_backup namespace, for consistency with the backup spec. Maybe something like m.megolm_backup.v1.<backupversion>?


{
"algorithm": "m.recovery_key.v1.curve25519.pbkdf2",
"data": <base64>,
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

will also need to store a salt. Could also store other PBKDF2 parameters, such as number of rounds, so that people can be more paranoid if they want to.

* the `m.hidden` event field to indicate to the server that such events should not be included in /sync responses to clients.
* a `GET /_matrix/client/r0/user/{userId}/account_data/m.recovery_key` accessor, symmetrical to the existing PUT method, to access the data when needed.

We deliberately encrypt the Curve25519 private key rather than deriving it from the passphrase so that if the user chooses not to store their encrypted recovery key on the server, they can benefit from a Curve25519 key generated from a high entropy source of random rather than being needlessly derived from a passphrase of some kind. (TODO: Is this accurate)?
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think this is accurate, as users who want high entropy can just use a randomly generated base64 string or something similar as their passphrase. I think the main benefit of encrypting the private key is that you change the passphrase without re-encrypting everything.


In practice, this means:
* Mandating that clients use a high complexity passphrase to encrypt the recovery key - either by enforcing complexity requirements or by generating it for them (similar to 1Password's password creation UX).
* Symmetrically encrypting the Curve25519 key by N rounds of PBKDF2(key, passphrase) where N=100,000 - similarly to how we encrypt [offline megolm key backups](https://github.com/matrix-org/matrix-doc/issues/1211) today. (TODO: This needs to be fleshed out).
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

...and then presumably we need to hit the private key with AES to actually encrypt it with the key/iv from the PBKDF2?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@uhoreg if you can suggest how we should actually do this bit of it, it'd be much appreciated

@turt2live
Copy link
Member

Closing in favour of #1703 (which is what I'm told is supposed to happen)

@turt2live turt2live closed this Dec 17, 2018
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants