diff --git a/crates/matrix-sdk-crypto/src/session_manager/group_sessions/share_strategy.rs b/crates/matrix-sdk-crypto/src/session_manager/group_sessions/share_strategy.rs index c2bec06f962..1835dc64ef4 100644 --- a/crates/matrix-sdk-crypto/src/session_manager/group_sessions/share_strategy.rs +++ b/crates/matrix-sdk-crypto/src/session_manager/group_sessions/share_strategy.rs @@ -162,33 +162,7 @@ pub(crate) async fn collect_session_recipients( // of the devices in the session got deleted or blacklisted in the // meantime. If so, we should also rotate the session. if !should_rotate { - // Device IDs that should receive this session - let recipient_device_ids: BTreeSet<&DeviceId> = - recipients.iter().map(|d| d.device_id()).collect(); - - if let Some(shared) = outbound.shared_with_set.read().unwrap().get(user_id) { - // Devices that received this session - let shared: BTreeSet = shared.keys().cloned().collect(); - let shared: BTreeSet<&DeviceId> = shared.iter().map(|d| d.as_ref()).collect(); - - // The set difference between - // - // 1. Devices that had previously received the session, and - // 2. Devices that would now receive the session - // - // Represents newly deleted or blacklisted devices. If this - // set is non-empty, we must rotate. - let newly_deleted_or_blacklisted = - shared.difference(&recipient_device_ids).collect::>(); - - should_rotate = !newly_deleted_or_blacklisted.is_empty(); - if should_rotate { - debug!( - "Rotating a room key due to these devices being deleted/blacklisted {:?}", - newly_deleted_or_blacklisted, - ); - } - }; + should_rotate = is_session_overshared_for_user(outbound, user_id, &recipients) } devices.entry(user_id.to_owned()).or_default().extend(recipients); @@ -209,6 +183,45 @@ pub(crate) async fn collect_session_recipients( Ok(CollectRecipientsResult { should_rotate, devices, withheld_devices }) } +// Checks if the session has been shared with a device that is not anymore in the +// pool of devices that should participate in the discussion. +fn is_session_overshared_for_user( + outbound: &OutboundGroupSession, + user_id: &UserId, + recipients: &Vec, +) -> bool { + // Device IDs that should receive this session + let recipient_device_ids: BTreeSet<&DeviceId> = + recipients.iter().map(|d| d.device_id()).collect(); + + if let Some(shared) = outbound.shared_with_set.read().unwrap().get(user_id) { + // Devices that received this session + let shared: BTreeSet = shared.keys().cloned().collect(); + let shared: BTreeSet<&DeviceId> = shared.iter().map(|d| d.as_ref()).collect(); + + // The set difference between + // + // 1. Devices that had previously received the session, and + // 2. Devices that would now receive the session + // + // Represents newly deleted or blacklisted devices. If this + // set is non-empty, we must rotate. + let newly_deleted_or_blacklisted = + shared.difference(&recipient_device_ids).collect::>(); + + let should_rotate = !newly_deleted_or_blacklisted.is_empty(); + if should_rotate { + debug!( + "Rotating a room key due to these devices being deleted/blacklisted {:?}", + newly_deleted_or_blacklisted, + ); + } + should_rotate + } else { + false + } +} + struct RecipientDevices { allowed_devices: Vec, denied_devices_with_code: Vec<(DeviceData, WithheldCode)>,