Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
26 changes: 26 additions & 0 deletions MatrixSDK.xcodeproj/project.pbxproj
Original file line number Diff line number Diff line change
Expand Up @@ -1767,6 +1767,12 @@
ED35652D281150310002BF6A /* MXOlmInboundGroupSessionUnitTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = ED35652B281150310002BF6A /* MXOlmInboundGroupSessionUnitTests.swift */; };
ED35652F281153480002BF6A /* MXMegolmSessionDataUnitTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = ED35652E281153480002BF6A /* MXMegolmSessionDataUnitTests.swift */; };
ED356530281153480002BF6A /* MXMegolmSessionDataUnitTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = ED35652E281153480002BF6A /* MXMegolmSessionDataUnitTests.swift */; };
ED44F01128180BCC00452A5D /* MXSharedHistoryKeyRequest.swift in Sources */ = {isa = PBXBuildFile; fileRef = ED44F01028180BCC00452A5D /* MXSharedHistoryKeyRequest.swift */; };
ED44F01228180BCC00452A5D /* MXSharedHistoryKeyRequest.swift in Sources */ = {isa = PBXBuildFile; fileRef = ED44F01028180BCC00452A5D /* MXSharedHistoryKeyRequest.swift */; };
ED44F01428180EAB00452A5D /* MXSharedHistoryKeyManager.swift in Sources */ = {isa = PBXBuildFile; fileRef = ED44F01328180EAB00452A5D /* MXSharedHistoryKeyManager.swift */; };
ED44F01528180EAB00452A5D /* MXSharedHistoryKeyManager.swift in Sources */ = {isa = PBXBuildFile; fileRef = ED44F01328180EAB00452A5D /* MXSharedHistoryKeyManager.swift */; };
ED44F01A28180F4000452A5D /* MXSharedHistoryKeyManagerUnitTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = ED44F01728180F1C00452A5D /* MXSharedHistoryKeyManagerUnitTests.swift */; };
ED44F01B28180F4000452A5D /* MXSharedHistoryKeyManagerUnitTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = ED44F01728180F1C00452A5D /* MXSharedHistoryKeyManagerUnitTests.swift */; };
ED5AE8C52816C8CF00105072 /* MXCoreDataRoomSummaryStore.xcdatamodeld in Sources */ = {isa = PBXBuildFile; fileRef = ED5AE8C22816C8CF00105072 /* MXCoreDataRoomSummaryStore.xcdatamodeld */; };
ED5AE8C62816C8CF00105072 /* MXCoreDataRoomSummaryStore.xcdatamodeld in Sources */ = {isa = PBXBuildFile; fileRef = ED5AE8C22816C8CF00105072 /* MXCoreDataRoomSummaryStore.xcdatamodeld */; };
ED88999127F2065D00718486 /* MXRoomAliasResolution.h in Headers */ = {isa = PBXBuildFile; fileRef = ED88998F27F2065C00718486 /* MXRoomAliasResolution.h */; settings = {ATTRIBUTES = (Public, ); }; };
Expand Down Expand Up @@ -2768,6 +2774,9 @@
ED2F344856EFFCA383E37B22 /* Pods-SDK-MatrixSDK.release.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-SDK-MatrixSDK.release.xcconfig"; path = "Target Support Files/Pods-SDK-MatrixSDK/Pods-SDK-MatrixSDK.release.xcconfig"; sourceTree = "<group>"; };
ED35652B281150310002BF6A /* MXOlmInboundGroupSessionUnitTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MXOlmInboundGroupSessionUnitTests.swift; sourceTree = "<group>"; };
ED35652E281153480002BF6A /* MXMegolmSessionDataUnitTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MXMegolmSessionDataUnitTests.swift; sourceTree = "<group>"; };
ED44F01028180BCC00452A5D /* MXSharedHistoryKeyRequest.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = MXSharedHistoryKeyRequest.swift; sourceTree = "<group>"; };
ED44F01328180EAB00452A5D /* MXSharedHistoryKeyManager.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = MXSharedHistoryKeyManager.swift; sourceTree = "<group>"; };
ED44F01728180F1C00452A5D /* MXSharedHistoryKeyManagerUnitTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MXSharedHistoryKeyManagerUnitTests.swift; sourceTree = "<group>"; };
ED5AE8C32816C8CF00105072 /* MXRoomSummaryCoreDataStore2.xcdatamodel */ = {isa = PBXFileReference; lastKnownFileType = wrapper.xcdatamodel; path = MXRoomSummaryCoreDataStore2.xcdatamodel; sourceTree = "<group>"; };
ED5AE8C42816C8CF00105072 /* MXRoomSummaryCoreDataStore.xcdatamodel */ = {isa = PBXFileReference; lastKnownFileType = wrapper.xcdatamodel; path = MXRoomSummaryCoreDataStore.xcdatamodel; sourceTree = "<group>"; };
ED88998F27F2065C00718486 /* MXRoomAliasResolution.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = MXRoomAliasResolution.h; sourceTree = "<group>"; };
Expand Down Expand Up @@ -4113,6 +4122,7 @@
32FA10C01FA1C9EE00E54233 /* MXOutgoingRoomKeyRequestManager.m */,
32A30B161FB4813400C8309E /* MXIncomingRoomKeyRequestManager.h */,
32A30B171FB4813400C8309E /* MXIncomingRoomKeyRequestManager.m */,
ED44F01328180EAB00452A5D /* MXSharedHistoryKeyManager.swift */,
);
path = KeySharing;
sourceTree = "<group>";
Expand All @@ -4126,6 +4136,7 @@
32F945F11FAB83D800622468 /* MXIncomingRoomKeyRequestCancellation.m */,
32FA10C81FA1C9F700E54233 /* MXOutgoingRoomKeyRequest.h */,
32FA10C91FA1C9F700E54233 /* MXOutgoingRoomKeyRequest.m */,
ED44F01028180BCC00452A5D /* MXSharedHistoryKeyRequest.swift */,
);
path = Data;
sourceTree = "<group>";
Expand Down Expand Up @@ -4873,6 +4884,7 @@
ED21F67A28104B9A002FF83D /* Crypto */ = {
isa = PBXGroup;
children = (
ED44F01628180F1300452A5D /* KeySharing */,
ED35652A281150230002BF6A /* Data */,
ED21F67B28104BA1002FF83D /* Algorithms */,
);
Expand Down Expand Up @@ -4904,6 +4916,14 @@
path = Data;
sourceTree = "<group>";
};
ED44F01628180F1300452A5D /* KeySharing */ = {
isa = PBXGroup;
children = (
ED44F01728180F1C00452A5D /* MXSharedHistoryKeyManagerUnitTests.swift */,
);
path = KeySharing;
sourceTree = "<group>";
};
ED8943D127E3474A000FC39C /* Store */ = {
isa = PBXGroup;
children = (
Expand Down Expand Up @@ -6031,7 +6051,9 @@
8EC511062568216B00EC4E5B /* MXTaggedEventInfo.m in Sources */,
3AC135DB2640335100EE1E74 /* MXDehydrationService.m in Sources */,
32792BDD2296B90A00F4FC9D /* MXAggregatedEditsUpdater.m in Sources */,
ED44F01428180EAB00452A5D /* MXSharedHistoryKeyManager.swift in Sources */,
3259CD541DF860C300186944 /* MXRealmCryptoStore.m in Sources */,
ED44F01128180BCC00452A5D /* MXSharedHistoryKeyRequest.swift in Sources */,
EC60EDAA265CFE3B00B39A4E /* MXRoomSyncTimeline.m in Sources */,
EC0B9438271DB0D600B4D440 /* MXMemoryRoomSummaryStore.m in Sources */,
EC8A53E225B1BCC6004E0802 /* MXThirdPartyUserInstance.m in Sources */,
Expand Down Expand Up @@ -6486,6 +6508,7 @@
32FCAB4D19E578860049C555 /* MXRestClientTests.m in Sources */,
32C78BA7256D227D008130B1 /* MXCryptoMigrationTests.m in Sources */,
ED21F68528104DA2002FF83D /* MXMegolmEncryptionTests.swift in Sources */,
ED44F01A28180F4000452A5D /* MXSharedHistoryKeyManagerUnitTests.swift in Sources */,
322985CB26FAF898001890BC /* MXSession.swift in Sources */,
EC131B192779D8D500712964 /* MXThreadEventTimelineUnitTests.swift in Sources */,
B135067427EB201E00BD3276 /* MXLocationServiceTests.swift in Sources */,
Expand Down Expand Up @@ -6574,7 +6597,9 @@
B14EF1E82397E90400758AF0 /* MXRoomPowerLevels.m in Sources */,
32EEA85E260401490041425B /* MXSummable.swift in Sources */,
B14EF1E92397E90400758AF0 /* MXRealmMediaScanMapper.m in Sources */,
ED44F01528180EAB00452A5D /* MXSharedHistoryKeyManager.swift in Sources */,
EC8A53E725B1BCC6004E0802 /* MXThirdPartyProtocol.m in Sources */,
ED44F01228180BCC00452A5D /* MXSharedHistoryKeyRequest.swift in Sources */,
B19A30D724042F2700FB6F35 /* MXSelfVerifyingMasterKeyNotTrustedQRCodeData.m in Sources */,
EC0B9439271DB0D600B4D440 /* MXMemoryRoomSummaryStore.m in Sources */,
B14EF1EA2397E90400758AF0 /* MXRealmMediaScan.m in Sources */,
Expand Down Expand Up @@ -7029,6 +7054,7 @@
EC116598270FCA8B0089FA56 /* MXBackgroundTaskUnitTests.swift in Sources */,
B1E09A322397FD750057C069 /* MXRoomTests.m in Sources */,
ED21F68628104DA2002FF83D /* MXMegolmEncryptionTests.swift in Sources */,
ED44F01B28180F4000452A5D /* MXSharedHistoryKeyManagerUnitTests.swift in Sources */,
322985CC26FAF898001890BC /* MXSession.swift in Sources */,
EC131B1A2779D8D500712964 /* MXThreadEventTimelineUnitTests.swift in Sources */,
B135067527EB201E00BD3276 /* MXLocationServiceTests.swift in Sources */,
Expand Down
4 changes: 3 additions & 1 deletion MatrixSDK/Crypto/Algorithms/Megolm/MXMegolmDecryption.h
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,9 @@

#import "MXDecrypting.h"

@interface MXMegolmDecryption : NSObject <MXDecrypting>
@protocol MXSharedHistoryKeyService;

@interface MXMegolmDecryption : NSObject <MXDecrypting, MXSharedHistoryKeyService>

@end

Expand Down
125 changes: 89 additions & 36 deletions MatrixSDK/Crypto/Algorithms/Megolm/MXMegolmDecryption.m
Original file line number Diff line number Diff line change
Expand Up @@ -328,50 +328,80 @@ - (MXHTTPOperation*)shareKeysWithDevice:(MXIncomingRoomKeyRequest*)keyRequest
NSString *deviceId = keyRequest.deviceId;
MXDeviceInfo *deviceInfo = [crypto.deviceList storedDevice:userId deviceId:deviceId];
NSDictionary *body = keyRequest.requestBody;
NSString *roomId, *senderKey, *sessionId;
MXJSONModelSetString(roomId, body[@"room_id"]);
MXJSONModelSetString(senderKey, body[@"sender_key"]);
MXJSONModelSetString(sessionId, body[@"session_id"]);

return [self shareKeysWitUserId:userId
devices:@[deviceInfo]
forceEnsureOlmSessions:NO
roomId:roomId
sessionId:sessionId
senderKey:senderKey
success:success
failure:failure];
}

#pragma mark - Private methods

- (MXHTTPOperation *)shareKeysWitUserId:(NSString *)userId
devices:(NSArray <MXDeviceInfo *> *)devices
forceEnsureOlmSessions:(BOOL)forceEnsureOlmSessions
roomId:(NSString *)roomId
sessionId:(NSString *)sessionId
senderKey:(NSString *)senderKey
success:(void (^)(void))success
failure:(void (^)(NSError *error))failure
{
MXHTTPOperation *operation;
MXWeakify(self);
operation = [crypto ensureOlmSessionsForDevices:@{
userId: @[deviceInfo]
userId: devices
}
force:NO
force:forceEnsureOlmSessions
success:^(MXUsersDevicesMap<MXOlmSessionResult *> *results)
{
MXStrongifyAndReturnIfNil(self);

MXOlmSessionResult *olmSessionResult = [results objectForDevice:deviceId forUser:userId];
if (!olmSessionResult.sessionId)
{
// no session with this device, probably because there
// were no one-time keys.
//
// ensureOlmSessionsForUsers has already done the logging,
// so just skip it.
if (success)
{
success();
}
return;
}

NSString *roomId, *senderKey, *sessionId;
MXJSONModelSetString(roomId, body[@"room_id"]);
MXJSONModelSetString(senderKey, body[@"sender_key"]);
MXJSONModelSetString(sessionId, body[@"session_id"]);

MXLogDebug(@"[MXMegolmDecryption] shareKeysWithDevice: sharing keys for session %@|%@ with device %@:%@", senderKey, sessionId, userId, deviceId);

NSDictionary *payload = [self->crypto buildMegolmKeyForwardingMessage:roomId senderKey:senderKey sessionId:sessionId chainIndex:nil];

MXDeviceInfo *deviceInfo = olmSessionResult.device;

MXUsersDevicesMap<NSDictionary*> *contentMap = [[MXUsersDevicesMap alloc] init];
[contentMap setObject:[self->crypto encryptMessage:payload forDevices:@[deviceInfo]]
forUser:userId andDevice:deviceId];

MXHTTPOperation *operation2 = [self->crypto.matrixRestClient sendToDevice:kMXEventTypeStringRoomEncrypted contentMap:contentMap txnId:nil success:success failure:failure];
[operation mutateTo:operation2];
MXStrongifyAndReturnIfNil(self);
NSDictionary *payload = [self->crypto buildMegolmKeyForwardingMessage:roomId
senderKey:senderKey
sessionId:sessionId
chainIndex:nil];

MXUsersDevicesMap<NSDictionary*> *contentMap = [[MXUsersDevicesMap alloc] init];
for (MXDeviceInfo *deviceInfo in devices)
{
MXOlmSessionResult *olmSessionResult = [results objectForDevice:deviceInfo.deviceId forUser:userId];
if (olmSessionResult.sessionId)
{
NSDictionary *message = [self->crypto encryptMessage:payload forDevices:@[deviceInfo]];
[contentMap setObject:message forUser:userId andDevice:deviceInfo.deviceId];
}
else
{
MXLogDebug(@"[MXMegolmDecryption] No session with device %@, cannot share keys", deviceInfo.deviceId);
}
}

if (contentMap.count == 0)
{
MXLogDebug(@"[MXMegolmDecryption] No devices available for user %@, cannot share keys", userId);
if (success)
{
success();
}
return;
}

MXLogDebug(@"[MXMegolmDecryption] shareKeysWithDevices: sharing keys for session %@|%@ with devices of user %@", senderKey, sessionId, userId);

MXHTTPOperation *operation2 = [self->crypto.matrixRestClient sendToDevice:kMXEventTypeStringRoomEncrypted
contentMap:contentMap
txnId:nil
success:success
failure:failure];
[operation mutateTo:operation2];

} failure:failure];

return operation;
Expand Down Expand Up @@ -498,6 +528,29 @@ - (void)requestKeysForEvent:(MXEvent*)event
}
}

#pragma mark - MXSharedHistoryKeyStore

- (BOOL)hasSharedHistoryWithSessionId:(NSString *)sessionId senderKey:(NSString *)senderKey
{
MXOlmInboundGroupSession *session = [crypto.store inboundGroupSessionWithId:sessionId
andSenderKey:senderKey];
return session.sharedHistory;
}

- (void)shareKeysWithRequest:(MXSharedHistoryKeyRequest *)request
success:(void (^)(void))success
failure:(void (^)(NSError *error))failure
{
[self shareKeysWitUserId:request.userId
devices:request.devices
forceEnsureOlmSessions:YES
roomId:request.roomId
sessionId:request.sessionId
senderKey:request.senderKey
success:success
failure:failure];
}

@end

#endif
40 changes: 40 additions & 0 deletions MatrixSDK/Crypto/KeySharing/Data/MXSharedHistoryKeyRequest.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
//
// Copyright 2022 The Matrix.org Foundation C.I.C
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
//

/// Request to share the key for a given `sessionId` and `senderKey`
/// with selected user and all of their devices
@objcMembers
public class MXSharedHistoryKeyRequest: NSObject {
public let userId: String
public let devices: [MXDeviceInfo]
public let roomId: String
public let sessionId: String
public let senderKey: String

public init(
userId: String,
devices: [MXDeviceInfo],
roomId: String,
sessionId: String,
senderKey: String
) {
self.userId = userId
self.devices = devices
self.roomId = roomId
self.sessionId = sessionId
self.senderKey = senderKey
}
}
Loading