Faye Duxovni 1 month ago committed by GitHub
commit 0c6fee1cab
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194

@ -0,0 +1,144 @@
# MSC3834: Opportunistic user key pinning (TOFU)
In the Matrix spec at present, there are no real provisions for
properly authenticating devices belonging to other users, aside from
the fairly rare cases where users actually take the time to verify
each other out-of-band. Most clients encourage users to cross-sign
their own devices, but this has little practical value for most users
in the ecosystem at present, unless you're willing to verify all of
your contacts or trust the user keys reported by homeservers.
The goal of this proposal is to establish a TOFU-style mechanism where
users' signing keys are pinned when they're first encountered;
internally, this will look similar to user verification, but will
require no action on either user's part, and correspondingly will not
be considered as high a level of trust. Nevertheless, this at least
raises the bar for Mallory-in-the-middle attacks by malicious
homeservers, as they can no longer quietly falsify signing keys for
users who are already in contact with each other.
## Proposal
This proposal adds a fourth ed25519 keypair to a user's set of
cross-signing keys: the TOFU Signing Key (TSK), identified by
`m.cross_signing.tofu_signing`. This key will be uploaded and stored
alongside the MSK, SSK, and USK; it will be published to the
`keys/device_signing/upload` using the new optional field
`tofu_signing_key`.
Whenever a user Alice and a user Bob are in a room together for the
first time, Alice's device will automatically and silently cross-sign
Bob's MSK using her TSK. This effectively pins Bob's MSK; in future
interactions, Alice will be able to check that any device of Bob's is
signed by Bob's SSK which is signed by the pinned MSK, confirming that
the device really does belong to Bob as long as that very first
interaction wasn't tampered with. If Alice's device later observes an
MSK for Bob that differs from the one signed by her TSK, the device
may warn Alice that Bob's key has changed, and could potentially
refuse to share keys with devices that aren't signed under the
original SSK/MSK until Alice chooses to accept the new key.
After a device signs one or several new MSKs with the TSK (on joining
a new room, or observing a new member join a room), it should upload
these new signatures to the homeserver via the
`keys/signatures/upload` API endpoint. However, it is important to
ensure that the homeserver cannot perform a denial-of-service attack
on key pinning by simply dropping TOFU signatures. For this reason, a
user's devices should periodically ask each other to confirm a hash of
the complete set of all cross-signing signatures created by that
user. At any point, a device may send any or all of the user's other
devices an encrypted to-device message, with event type
`m.signatures_hash_request` and no fields. When the device receives
the message, it should reply with an encrypted to-device message with
event type `m.signatures_hash` and one field `sha256`. This field
contains a SHA256 hash of the canonical JSON encoding of the complete
set of cross-signing signatures known to that device, in the format
for uploading to `keys/signatures/upload`, excluding any unsigned
fields - that is, a map from user ID, to key ID, to a signed JSON
object for that key.
## Potential issues
If a client does choose to warn users every time a pinned MSK changes,
users in many large rooms could be overwhelmed with warnings from
random people losing their devices and performing key resets. There
are several things clients can do to alleviate this. First, rather
than popping up a warning immediately in a toast or dialog as soon as
a key changes, clients should only warn the user when they actually
open one of the rooms where the changed key is present. In addition,
users should be given the option to automatically accept all future
key changes in a particular room, and the option to accept all key
changes globally if that's in line with the user's threat
model. Clients could still display a small state-event-like message in
room timelines notifying the user of a key change, or could simply
accept all key changes silently.
## Security considerations
In the malicious homeserver scenario that this proposal aims to
mitigate, the homeserver could attempt to simply exclude TSK
signatures from its responses to key queries, preventing the
propagation of pinned keys between devices, and possibly even causing
a device to lose track of pinned keys over time. To prevent this,
it's important that clients maintain a persistent record of TSK
signatures without relying on the homeserver to store that
information. Signatures must never be removed from this record, even
if they aren't present in homeserver responses. However, if multiple
valid signatures for the same key from the same TSK have been created
due to race conditions, only the signature whose base64 representation
comes first lexicographically should be kept.
When devices ask each other to confirm the hash of the set of
cross-signing signatures, they may not receive a response; this could
be because the other device is offline, it could be because the device
is using an older version of the spec and doesn't understand the
request, or it could be because the homeserver is performing a
denial-of-service attack. If a device doesn't get a response, and does
see other activity from the other device, it could possibly eventually
display a warning encouraging the user to upgrade their other
device. If the device observes too many missing key indices in its
to-device Olm session, however, that may be a sign that the homeserver
is dropping messages.
In this threat model, another thing the homeserver can do is falsely
claim that the user's cross-signing keys have been reset by another
device. For the most part, this simply amounts to a denial-of-service
attack on cross-signing, which is difficult to prevent in
general. However, it's important to note that if a formerly-verified
device is told by the server that there's been a key reset, it must
still hold onto its record of signatures created with the old TSK, and
re-sign those with the new TSK once it has been able to confirm the
new MSK as part of becoming re-verified.
## Unstable prefix
This proposal does not add any new API endpoints, but does add some
new fields and message types to existing data structures. These field
names and message types will be prefixed with `org.matrix.msc3834.v1`.
Test implementations can identify the TSK as
`org.matrix.msc3834.v1.cross_signing.tofu_signing`, use the optional
field `org.matrix.msc3834.v1.tofu_signing_key` for the
`keys/device_signing/upload` endpoint, and use the message types
`org.matrix.msc3834.v1.signatures_hash_request` and
`org.matrix.msc3834.v1.signatures_hash` for exchanging hashes of the
set of cross-signing signatures.
## Migration notes
When a device with this functionality first comes online, if the user
doesn't already have a TSK and if the device possesses the private
MSK, it should create a new TSK, sign it with the MSK, and publish it
to `keys/device_signing/upload`. This endpoint requires
authentication, and therefore the user may need to be prompted for a
password when they open their upgraded client. If the user already has
server-side secret storage set up, the device should also store the
private TSK encrypted in secret storage.
If the user does already have a TSK, devices should obtain the private
key either from secret storage or by requesting the secret from other
devices. In the event of a race condition where multiple devices have
upgraded and created TSKs, the TSK whose base64 representation comes
first lexicographically will take precedence. Once other devices have
received the private key for the winning TSK, they should use it to
re-sign and re-submit any TOFU signatures they've already created, and
replace any signatures by the old TSK in their persistent records.
Loading…
Cancel
Save