crypto: look up sender device for key bundles

Currently, when we receive a room key bundle to-device event, we don't look up
the sender device at all, meaning that the message is then marked as "from
missing device", which means that if you turn on "exclude insecure devices",
the message is dropped.

This patch changes the logic so that room key bundle to-device events are
treated the same way as most other to-device events (except room keys, which
continue to be special).

Fixes: https://github.com/matrix-org/matrix-rust-sdk/issues/5613, although the
integration test now fails because instead we hit https://github.com/matrix-org/matrix-rust-sdk/issues/5768.
This commit is contained in:
Richard van der Hoff
2025-10-09 00:52:05 +01:00
parent c45ede972e
commit 43e94bcfb4
2 changed files with 21 additions and 23 deletions
+2
View File
@@ -8,6 +8,8 @@ All notable changes to this project will be documented in this file.
### Bug Fixes
- Fix a bug which caused history shared on invite to be ignored when "exclude insecure devices" was enabled.
([#5763](https://github.com/matrix-org/matrix-rust-sdk/pull/5763))
- Fix a bug introduced in 0.14.0 which meant that the serialization of the value returned by `OtherUserIdentity::verification_request_content` did not include a `msgtype` field.
([#5642](https://github.com/matrix-org/matrix-rust-sdk/pull/5642))
+19 -23
View File
@@ -1558,38 +1558,34 @@ impl Account {
// valid. The processing of the historic room key bundle depends on this being
// here.
Self::check_sender_device_keys(event, sender_key)?;
let mut sender_device: Option<Device> = None;
if let AnyDecryptedOlmEvent::RoomKey(_) = event {
// If this event is an `m.room_key` event, defer the check for
// the Ed25519 key of the sender until we decrypt room events.
// This ensures that we receive the room key even if we don't
// have access to the device.
} else if let AnyDecryptedOlmEvent::RoomKeyBundle(_) = event {
// If this is a room key bundle we're requiring the device keys to be part of
// the `AnyDecryptedOlmEvent`. This ensures that we can skip the check for the
// Ed25519 key below since `Self::check_sender_device_keys` already did so.
//
// If the event didn't contain any sender device keys we'll throw an error
// refusing to decrypt the room key bundle.
return Ok(None);
}
// MSC4268 requires room key bundle events to have a `sender_device_keys` field.
// Enforce that now.
if let AnyDecryptedOlmEvent::RoomKeyBundle(_) = event {
event.sender_device_keys().ok_or(EventError::MissingSigningKey).inspect_err(|_| {
warn!("The room key bundle was missing the sender device keys in the event")
})?;
} else {
let device = store
.get_device_from_curve_key(event.sender(), sender_key)
.await?
.ok_or(EventError::MissingSigningKey)?;
let key = device.ed25519_key().ok_or(EventError::MissingSigningKey)?;
if key != event.keys().ed25519 {
return Err(
EventError::MismatchedKeys(key.into(), event.keys().ed25519.into()).into()
);
}
sender_device = Some(device);
}
Ok(sender_device)
let device = store
.get_device_from_curve_key(event.sender(), sender_key)
.await?
.ok_or(EventError::MissingSigningKey)?;
let key = device.ed25519_key().ok_or(EventError::MissingSigningKey)?;
if key != event.keys().ed25519 {
return Err(EventError::MismatchedKeys(key.into(), event.keys().ed25519.into()).into());
}
Ok(Some(device))
}
/// Return true if: