diff --git a/SignalServiceKit/src/Loki/Crypto/SessionCipher+Loki.m b/SignalServiceKit/src/Loki/Crypto/SessionCipher+Loki.m index be36b6684..467fe63a2 100644 --- a/SignalServiceKit/src/Loki/Crypto/SessionCipher+Loki.m +++ b/SignalServiceKit/src/Loki/Crypto/SessionCipher+Loki.m @@ -27,9 +27,9 @@ NSString *const kNSNotificationKey_ContactPubKey = @"kNSNotificationKey_ContactP // Our state before we decrypt the message SessionState *_Nullable state = [self getCurrentState:protocolContext]; - // Loki: Verify incoming friend request messages + // Verify incoming friend request messages if (!state) { - [self throws_verifyFriendRequestAcceptPreKeyForMessage:whisperMessage protocolContext:protocolContext]; + [self throws_validatePreKeysForFriendRequestAcceptance:whisperMessage protocolContext:protocolContext]; } // While decrypting our state may change internally @@ -132,16 +132,16 @@ NSString *const kNSNotificationKey_ContactPubKey = @"kNSNotificationKey_ContactP [self.sessionStore storeSession:self.recipientId deviceId:self.deviceId session:record protocolContext:protocolContext]; } -/// Check that we have matching prekeys in the case of a `PreKeyWhisperMessage` -/// This is so that we don't trigger a false friend request accept on unknown contacts -- (void)throws_verifyFriendRequestAcceptPreKeyForMessage:(id)whisperMessage protocolContext:(nullable id)protocolContext { +/// Check that we have matching pre keys in the case of a `PreKeyWhisperMessage`. +/// This is so that we don't trigger a false friend request accept on unknown contacts. +- (void)throws_validatePreKeysForFriendRequestAcceptance:(id)whisperMessage protocolContext:(nullable id)protocolContext { OWSAssertDebug([protocolContext isKindOfClass:[YapDatabaseReadTransaction class]]); YapDatabaseReadTransaction *transaction = protocolContext; - // We only want to look at `PreKeyWhisperMessage` + // Ignore anything that isn't a `PreKeyWhisperMessage` if (![whisperMessage isKindOfClass:[PreKeyWhisperMessage class]]) { return; } - // We need the primary storage to access contact prekeys + // Check the pre key store if (![self.prekeyStore isKindOfClass:[OWSPrimaryStorage class]]) { return; } PreKeyWhisperMessage *preKeyMessage = whisperMessage; @@ -149,11 +149,11 @@ NSString *const kNSNotificationKey_ContactPubKey = @"kNSNotificationKey_ContactP PreKeyRecord *_Nullable storedPreKey = [primaryStorage getPreKeyForContact:self.recipientId transaction:transaction]; if (!storedPreKey) { - OWSRaiseException(@"LokiInvalidPreKey", @"Received a friend request from a public key for which no prekey bundle was created."); + OWSRaiseException(@"Loki", @"Received a friend request from a public key for which no pre key bundle was created."); } if (storedPreKey.Id != preKeyMessage.prekeyID) { - OWSRaiseException(@"LokiPreKeyIdsDontMatch", @"Received a PreKeyWhisperMessage (friend request accept) from an unknown source."); + OWSRaiseException(@"Loki", @"Received a PreKeyWhisperMessage (friend request accept) from an unknown source."); } } diff --git a/SignalServiceKit/src/Messages/OWSBatchMessageProcessor.m b/SignalServiceKit/src/Messages/OWSBatchMessageProcessor.m index 8e7735407..117d2fdc9 100644 --- a/SignalServiceKit/src/Messages/OWSBatchMessageProcessor.m +++ b/SignalServiceKit/src/Messages/OWSBatchMessageProcessor.m @@ -365,20 +365,12 @@ NSString *const OWSMessageContentJobFinderExtensionGroup = @"OWSMessageContentJo { OWSAssertDebug(AppReadiness.isAppReady); - // Don't process incoming messages in app extensions. - if (!CurrentAppContext().isMainApp) { - return; - } - if (!self.tsAccountManager.isRegisteredAndReady) { - return; - } + if (!CurrentAppContext().isMainApp) { return; } + if (!self.tsAccountManager.isRegisteredAndReady) { return; } dispatch_async(self.serialQueue, ^{ - if (self.isDrainingQueue) { - return; - } + if (self.isDrainingQueue) { return; } self.isDrainingQueue = YES; - [self drainQueueWorkStep]; }); } @@ -387,7 +379,7 @@ NSString *const OWSMessageContentJobFinderExtensionGroup = @"OWSMessageContentJo { AssertOnDispatchQueue(self.serialQueue); - // We want a value that is just high enough to yield perf benefits. + // We want a value that is just high enough to yield performance benefits const NSUInteger kIncomingMessageBatchSize = 32; NSArray *batchJobs = [self.finder nextJobsForBatchSize:kIncomingMessageBatchSize]; @@ -525,7 +517,7 @@ NSString *const OWSMessageContentJobFinderExtensionGroup = @"OWSMessageContentJo transaction:(YapDatabaseReadWriteTransaction *)transaction { if (envelopeData.length < 1) { - OWSFailDebug(@"Empty envelope."); + OWSFailDebug(@"Received an empty envelope."); return; } OWSAssert(transaction); diff --git a/SignalServiceKit/src/Messages/OWSMessageDecrypter.m b/SignalServiceKit/src/Messages/OWSMessageDecrypter.m index 4d04d68b6..600ceadd2 100644 --- a/SignalServiceKit/src/Messages/OWSMessageDecrypter.m +++ b/SignalServiceKit/src/Messages/OWSMessageDecrypter.m @@ -177,7 +177,7 @@ NSError *EnsureDecryptError(NSError *_Nullable error, NSString *fallbackErrorDes OWSMessageDecryptResult *result, YapDatabaseReadWriteTransaction *transaction) { // Ensure all blocked messages are discarded. if ([self isEnvelopeSenderBlocked:envelope]) { - OWSLogInfo(@"Ignoring blocked envelope: %@", envelope.source); + OWSLogInfo(@"Ignoring blocked envelope from: %@.", envelope.source); return failureBlock(); } @@ -195,21 +195,21 @@ NSError *EnsureDecryptError(NSError *_Nullable error, NSString *fallbackErrorDes }; @try { - OWSLogInfo(@"decrypting envelope: %@", [self descriptionForEnvelope:envelope]); + OWSLogInfo(@"Decrypting envelope: %@.", [self descriptionForEnvelope:envelope]); if (envelope.type != SSKProtoEnvelopeTypeUnidentifiedSender) { if (!envelope.hasSource || envelope.source.length < 1 || ![ECKeyPair isValidHexEncodedPublicKeyWithCandidate:envelope.source]) { - OWSFailDebug(@"incoming envelope has invalid source"); + OWSFailDebug(@"Incoming envelope with invalid source."); return failureBlock(); } if (!envelope.hasSourceDevice || envelope.sourceDevice < 1) { - OWSFailDebug(@"incoming envelope has invalid source device"); + OWSFailDebug(@"Incoming envelope with invalid source device."); return failureBlock(); } // We block UD messages later, after they are decrypted. if ([self isEnvelopeSenderBlocked:envelope]) { - OWSLogInfo(@"ignoring blocked envelope: %@", envelope.source); + OWSLogInfo(@"Ignoring blocked envelope from: %@.", envelope.source); return failureBlock(); } } @@ -224,7 +224,7 @@ NSError *EnsureDecryptError(NSError *_Nullable error, NSString *fallbackErrorDes successBlock(result, transaction); } failureBlock:^(NSError * _Nullable error) { - OWSLogError(@"Decrypting friend request message from address: %@ failed with error: %@.", + OWSLogError(@"Decrypting friend request message from: %@ failed with error: %@.", envelopeAddress(envelope), error); failureBlock(); @@ -237,11 +237,11 @@ NSError *EnsureDecryptError(NSError *_Nullable error, NSString *fallbackErrorDes [self throws_decryptSecureMessage:envelope envelopeData:envelopeData successBlock:^(OWSMessageDecryptResult *result, YapDatabaseReadWriteTransaction *transaction) { - OWSLogDebug(@"decrypted secure message."); + OWSLogDebug(@"Decrypted secure message."); successBlock(result, transaction); } failureBlock:^(NSError *_Nullable error) { - OWSLogError(@"decrypting secure message from address: %@ failed with error: %@", + OWSLogError(@"Decrypting secure message from: %@ failed with error: %@.", envelopeAddress(envelope), error); OWSProdError([OWSAnalyticsEvents messageManagerErrorCouldNotHandleSecureMessage]); @@ -254,12 +254,11 @@ NSError *EnsureDecryptError(NSError *_Nullable error, NSString *fallbackErrorDes [self throws_decryptPreKeyBundle:envelope envelopeData:envelopeData successBlock:^(OWSMessageDecryptResult *result, YapDatabaseReadWriteTransaction *transaction) { - OWSLogDebug(@"decrypted pre-key whisper message"); + OWSLogDebug(@"Decrypted pre key bundle message."); successBlock(result, transaction); } failureBlock:^(NSError *_Nullable error) { - OWSLogError(@"decrypting pre-key whisper message from address: %@ failed " - @"with error: %@", + OWSLogError(@"Decrypting pre key bundle message from: %@ failed with error: %@.", envelopeAddress(envelope), error); OWSProdError([OWSAnalyticsEvents messageManagerErrorCouldNotHandlePrekeyBundle]); @@ -287,12 +286,11 @@ NSError *EnsureDecryptError(NSError *_Nullable error, NSString *fallbackErrorDes case SSKProtoEnvelopeTypeUnidentifiedSender: { [self decryptUnidentifiedSender:envelope successBlock:^(OWSMessageDecryptResult *result, YapDatabaseReadWriteTransaction *transaction) { - OWSLogDebug(@"decrypted unidentified sender message"); + OWSLogDebug(@"Decrypted unidentified sender message."); successBlock(result, transaction); } failureBlock:^(NSError *_Nullable error) { - OWSLogError(@"decrypting unidentified sender message from address: %@ failed " - @"with error: %@", + OWSLogError(@"Decrypting unidentified sender message from: %@ failed with error: %@.", envelopeAddress(envelope), error); OWSProdError([OWSAnalyticsEvents messageManagerErrorCouldNotHandleUnidentifiedSenderMessage]); @@ -302,11 +300,11 @@ NSError *EnsureDecryptError(NSError *_Nullable error, NSString *fallbackErrorDes return; } default: - OWSLogWarn(@"Received unhandled envelope type: %d", (int)envelope.type); + OWSLogWarn(@"Received unhandled envelope type: %d.", (int)envelope.type); break; } } @catch (NSException *exception) { - OWSFailDebug(@"Received an invalid envelope: %@", exception.debugDescription); + OWSFailDebug(@"Received an invalid envelope: %@.", exception.debugDescription); OWSProdFail([OWSAnalyticsEvents messageManagerErrorInvalidProtocolMessage]); [[self.primaryStorage newDatabaseConnection] @@ -342,7 +340,7 @@ NSError *EnsureDecryptError(NSError *_Nullable error, NSString *fallbackErrorDes NSData *_Nullable plaintextData = [[cipher decryptWithMessage:encryptedData] removePadding]; if (!plaintextData) { - NSString *errorString = [NSString stringWithFormat:@"Failed to decrypt friend request message for: %@.", recipientId]; + NSString *errorString = [NSString stringWithFormat:@"Failed to decrypt friend request message from: %@.", recipientId]; NSError *error = OWSErrorWithCodeDescription(OWSErrorCodeFailedToDecryptMessage, errorString); return failureBlock(error); } @@ -419,7 +417,7 @@ NSError *EnsureDecryptError(NSError *_Nullable error, NSString *fallbackErrorDes NSData *encryptedData = envelope.content ?: envelope.legacyMessage; if (!encryptedData) { OWSProdFail([OWSAnalyticsEvents messageManagerErrorMessageEnvelopeHasNoContent]); - NSError *error = OWSErrorWithCodeDescription(OWSErrorCodeFailedToDecryptMessage, @"Envelope has no content"); + NSError *error = OWSErrorWithCodeDescription(OWSErrorCodeFailedToDecryptMessage, @"Envelope has no content."); return failureBlock(error); } @@ -435,15 +433,8 @@ NSError *EnsureDecryptError(NSError *_Nullable error, NSString *fallbackErrorDes deviceId:deviceId]; // plaintextData may be nil for some envelope types. - NSData *_Nullable plaintextData = - [[cipher throws_lokiDecrypt:cipherMessage protocolContext:transaction] removePadding]; - - /* Loki: Original code - * ================ - NSData *_Nullable plaintextData = - [[cipher throws_decrypt:cipherMessage protocolContext:transaction] removePadding]; - * ================ - */ + NSData *_Nullable plaintextData = [[cipher throws_lokiDecrypt:cipherMessage protocolContext:transaction] removePadding]; + OWSMessageDecryptResult *result = [OWSMessageDecryptResult resultWithEnvelopeData:envelopeData plaintextData:plaintextData source:envelope.source @@ -454,7 +445,7 @@ NSError *EnsureDecryptError(NSError *_Nullable error, NSString *fallbackErrorDes dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{ [self processException:exception envelope:envelope]; NSString *errorDescription = [NSString - stringWithFormat:@"Exception while decrypting %@: %@", cipherTypeName, exception.description]; + stringWithFormat:@"Exception while decrypting %@: %@.", cipherTypeName, exception.description]; OWSLogError(@"%@", errorDescription); NSError *error = OWSErrorWithCodeDescription(OWSErrorCodeFailedToDecryptMessage, errorDescription); failureBlock(error); @@ -497,8 +488,8 @@ NSError *EnsureDecryptError(NSError *_Nullable error, NSString *fallbackErrorDes identityStore:self.identityManager error:&cipherError]; if (cipherError || !cipher) { - OWSFailDebug(@"Could not create secret session cipher: %@", cipherError); - cipherError = EnsureDecryptError(cipherError, @"Could not create secret session cipher"); + OWSFailDebug(@"Could not create secret session cipher: %@.", cipherError); + cipherError = EnsureDecryptError(cipherError, @"Could not create secret session cipher."); return failureBlock(cipherError); } @@ -514,9 +505,9 @@ NSError *EnsureDecryptError(NSError *_Nullable error, NSString *fallbackErrorDes if (!decryptResult) { if (!decryptError) { - OWSFailDebug(@"Caller should provide specific error"); + OWSFailDebug(@"Caller should provide specific error."); NSError *error = OWSErrorWithCodeDescription( - OWSErrorCodeFailedToDecryptUDMessage, @"Could not decrypt UD message"); + OWSErrorCodeFailedToDecryptUDMessage, @"Could not decrypt UD message."); return failureBlock(error); } @@ -565,7 +556,7 @@ NSError *EnsureDecryptError(NSError *_Nullable error, NSString *fallbackErrorDes dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{ [self processException:underlyingException envelope:identifiedEnvelope]; NSString *errorDescription = [NSString - stringWithFormat:@"Exception while decrypting ud message: %@", underlyingException.description]; + stringWithFormat:@"Exception while decrypting UD message: %@.", underlyingException.description]; OWSLogError(@"%@", errorDescription); NSError *error = OWSErrorWithCodeDescription(OWSErrorCodeFailedToDecryptMessage, errorDescription); failureBlock(error); @@ -580,7 +571,7 @@ NSError *EnsureDecryptError(NSError *_Nullable error, NSString *fallbackErrorDes return; } - OWSFailDebug(@"Could not decrypt UD message: %@", underlyingError); + OWSFailDebug(@"Could not decrypt UD message: %@.", underlyingError); failureBlock(underlyingError); return; } diff --git a/SignalServiceKit/src/Messages/OWSMessageManager.m b/SignalServiceKit/src/Messages/OWSMessageManager.m index 360ff7655..78b860e80 100644 --- a/SignalServiceKit/src/Messages/OWSMessageManager.m +++ b/SignalServiceKit/src/Messages/OWSMessageManager.m @@ -260,26 +260,27 @@ NS_ASSUME_NONNULL_BEGIN return; } if (!CurrentAppContext().isMainApp) { - OWSFail(@"Not main app."); + OWSFail(@"Not the main app."); return; } - OWSLogInfo(@"handling decrypted envelope: %@", [self descriptionForEnvelope:envelope]); + OWSLogInfo(@"Handling decrypted envelope: %@.", [self descriptionForEnvelope:envelope]); if (!wasReceivedByUD) { if (!envelope.hasSource || envelope.source.length < 1) { - OWSFailDebug(@"incoming envelope has invalid source"); + OWSFailDebug(@"Incoming envelope with invalid source."); return; } if (!envelope.hasSourceDevice || envelope.sourceDevice < 1) { - OWSFailDebug(@"incoming envelope has invalid source device"); + OWSFailDebug(@"Incoming envelope with invalid source device."); return; } } OWSAssertDebug(![self isEnvelopeSenderBlocked:envelope]); - // Loki: Ignore any friend requests that we got before restoration + // Loki: Ignore any friend requests from before restoration + // The envelope type is set during UD decryption. uint64_t restorationTime = [NSNumber numberWithDouble:[OWSPrimaryStorage.sharedManager getRestorationTime]].unsignedLongLongValue; if (envelope.type == SSKProtoEnvelopeTypeFriendRequest && envelope.timestamp < restorationTime * 1000) { [LKLogger print:@"[Loki] Ignoring friend request received before restoration."]; @@ -417,7 +418,7 @@ NS_ASSUME_NONNULL_BEGIN return; } if (envelope.sourceDevice < 1) { - OWSFailDebug(@"Invaid source device."); + OWSFailDebug(@"Invalid source device."); return; } @@ -426,23 +427,24 @@ NS_ASSUME_NONNULL_BEGIN sourceDeviceId:envelope.sourceDevice transaction:transaction]; if (duplicateEnvelope) { - OWSLogInfo(@"Ignoring previously received envelope from %@ with timestamp: %llu", + OWSLogInfo(@"Ignoring previously received envelope from: %@ with timestamp: %llu.", envelopeAddress(envelope), envelope.timestamp); return; } // Loki: Handle friend request acceptance if needed + // The envelope type is set during UD decryption. [self handleFriendRequestAcceptanceIfNeededWithEnvelope:envelope transaction:transaction]; if (envelope.content != nil) { NSError *error; SSKProtoContent *_Nullable contentProto = [SSKProtoContent parseData:plaintextData error:&error]; if (error || !contentProto) { - OWSFailDebug(@"could not parse proto: %@", error); + OWSFailDebug(@"Could not parse proto due to error: %@.", error); return; } - OWSLogInfo(@"handling content: ", [self descriptionForContent:contentProto]); + OWSLogInfo(@"Handling content: .", [self descriptionForContent:contentProto]); // Loki: Workaround for duplicate sync transcript issue if (contentProto.syncMessage != nil && contentProto.syncMessage.sent != nil) { @@ -460,7 +462,8 @@ NS_ASSUME_NONNULL_BEGIN } [self.primaryStorage setPreKeyBundle:bundle forContact:envelope.source transaction:transaction]; - // Loki: If we received a friend request, but we were already friends with this user, then reset the session + // Loki: If we received a friend request, but we were already friends with this user, reset the session + // The envelope type is set during UD decryption. if (envelope.type == SSKProtoEnvelopeTypeFriendRequest) { TSContactThread *thread = [TSContactThread getThreadWithContactId:envelope.source transaction:transaction]; if (thread && thread.isContactFriend) { @@ -558,13 +561,13 @@ NS_ASSUME_NONNULL_BEGIN return; } - // Loki: Don't process session request messages + // Loki: Don't process session request messages any further if ((dataMessage.flags & SSKProtoDataMessageFlagsSessionRequest) != 0) { return; } - // Loki: Don't process session restore messages + // Loki: Don't process session restore messages any further if ((dataMessage.flags & SSKProtoDataMessageFlagsSessionRestore) != 0) { return; } if ([self isDataMessageBlocked:dataMessage envelope:envelope]) { - NSString *logMessage = [NSString stringWithFormat:@"Ignoring blocked message from sender: %@", envelope.source]; + NSString *logMessage = [NSString stringWithFormat:@"Ignoring blocked message from sender: %@.", envelope.source]; if (dataMessage.group) { logMessage = [logMessage stringByAppendingFormat:@" in group: %@", dataMessage.group.id]; } @@ -574,14 +577,12 @@ NS_ASSUME_NONNULL_BEGIN if (dataMessage.hasTimestamp) { if (dataMessage.timestamp <= 0) { - OWSFailDebug(@"Ignoring message with invalid data message timestamp: %@", envelope.source); - // TODO: Add analytics. + OWSFailDebug(@"Ignoring data message with invalid timestamp: %@.", envelope.source); return; } // This prevents replay attacks by the service. if (dataMessage.timestamp != envelope.timestamp) { - OWSFailDebug(@"Ignoring message with non-matching data message timestamp: %@", envelope.source); - // TODO: Add analytics. + OWSFailDebug(@"Ignoring data message with non-matching timestamp: %@.", envelope.source); return; } } @@ -607,7 +608,7 @@ NS_ASSUME_NONNULL_BEGIN [self sendGroupInfoRequest:dataMessage.group.id envelope:envelope transaction:transaction]; return; } else { - OWSLogInfo(@"Ignoring group message for unknown group from: %@", envelope.source); + OWSLogInfo(@"Ignoring group message for unknown group from: %@.", envelope.source); return; } } @@ -890,7 +891,7 @@ NS_ASSUME_NONNULL_BEGIN TSThread *_Nullable thread = [self threadForEnvelope:envelope dataMessage:dataMessage transaction:transaction]; if (!thread) { - OWSFailDebug(@"ignoring media message for unknown group."); + OWSFailDebug(@"Ignoring media message for unknown group."); return; } @@ -905,17 +906,17 @@ NS_ASSUME_NONNULL_BEGIN [message saveWithTransaction:transaction]; - OWSLogDebug(@"incoming attachment message: %@", message.debugDescription); + OWSLogDebug(@"Incoming attachment message: %@.", message.debugDescription); [self.attachmentDownloads downloadAttachmentsForMessage:message transaction:transaction success:^(NSArray *attachmentStreams) { - OWSLogDebug(@"successfully fetched attachments: %lu for message: %@", + OWSLogDebug(@"Successfully fetched attachments: %lu for message: %@.", (unsigned long)attachmentStreams.count, message); } failure:^(NSError *error) { - OWSLogError(@"failed to fetch attachments for message: %@ with error: %@", message, error); + OWSLogError(@"Failed to fetch attachments for message: %@ with error: %@.", message, error); }]; } @@ -1402,7 +1403,9 @@ NS_ASSUME_NONNULL_BEGIN dispatch_queue_t messageProcessingQueue = SSKEnvironment.shared.batchMessageProcessor.processingQueue.serialQueue; AssertOnDispatchQueue(messageProcessingQueue); - + + // The envelope source is set during UD decryption. + if ([ECKeyPair isValidHexEncodedPublicKeyWithCandidate:envelope.source]) { dispatch_semaphore_t semaphore = dispatch_semaphore_create(0); [[LKAPI getDestinationsFor:envelope.source inTransaction:transaction].ensureOn(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^() { @@ -1432,7 +1435,7 @@ NS_ASSUME_NONNULL_BEGIN // We distinguish between the old group state (if any) and the new group state. TSGroupThread *_Nullable oldGroupThread = [TSGroupThread threadWithGroupId:groupId transaction:transaction]; if (oldGroupThread) { - // Loki: Try to figure out removed members + // Loki: Determine removed members removedMemberIds = [NSMutableSet setWithArray:oldGroupThread.groupModel.groupMemberIds]; [removedMemberIds minusSet:newMemberIds]; [removedMemberIds removeObject:hexEncodedPublicKey]; @@ -1562,7 +1565,7 @@ NS_ASSUME_NONNULL_BEGIN // Loki: Don't process friend requests in group chats if (body.length == 0 && attachmentPointers.count < 1 && !contact) { - OWSLogWarn(@"ignoring empty incoming message from: %@ for group: %@ with timestamp: %lu", + OWSLogWarn(@"Ignoring empty incoming message from: %@ for group: %@ with timestamp: %lu.", hexEncodedPublicKey, groupId, (unsigned long)timestamp); @@ -1591,14 +1594,14 @@ NS_ASSUME_NONNULL_BEGIN return incomingMessage; } default: { - OWSLogWarn(@"Ignoring unknown group message type: %d", (int)dataMessage.group.type); + OWSLogWarn(@"Ignoring unknown group message type: %d.", (int)dataMessage.group.type); return nil; } } } else { - // Loki: A message from a secondary device should appear as if it came from the primary device; the underlying - // friend request logic, however, should still be specific to the secondary device. + // Loki: A message from a slave device should appear as if it came from the master device; the underlying + // friend request logic, however, should still be specific to the slave device. // Loki: Get the master hex encoded public key and thread NSString *hexEncodedPublicKey = envelope.source; @@ -1606,7 +1609,7 @@ NS_ASSUME_NONNULL_BEGIN TSContactThread *thread = [TSContactThread getOrCreateThreadWithContactId:hexEncodedPublicKey transaction:transaction]; TSContactThread *masterThread = [TSContactThread getOrCreateThreadWithContactId:masterHexEncodedPublicKey transaction:transaction]; - OWSLogDebug(@"incoming message from: %@ with timestamp: %lu", hexEncodedPublicKey, (unsigned long)timestamp); + OWSLogDebug(@"Incoming message from: %@ with timestamp: %lu.", hexEncodedPublicKey, (unsigned long)timestamp); [[OWSDisappearingMessagesJob sharedJob] becomeConsistentWithDisappearingDuration:dataMessage.expireTimer thread:masterThread @@ -1665,7 +1668,7 @@ NS_ASSUME_NONNULL_BEGIN [self handleFriendRequestMessageIfNeededWithEnvelope:envelope data:dataMessage message:incomingMessage thread:thread transaction:transaction]; if (body.length == 0 && attachmentPointers.count < 1 && !contact) { - OWSLogWarn(@"ignoring empty incoming message from: %@ with timestamp: %lu", + OWSLogWarn(@"Ignoring empty incoming message from: %@ with timestamp: %lu.", hexEncodedPublicKey, (unsigned long)timestamp); return nil; @@ -1703,13 +1706,11 @@ NS_ASSUME_NONNULL_BEGIN if (profileKey.length == kAES256_KeyByteLength) { [self.profileManager setProfileKeyData:profileKey forRecipientId:recipientId avatarURL:url]; } else { - OWSFailDebug( - @"Unexpected profile key length:%lu on message from:%@", (unsigned long)profileKey.length, recipientId); + OWSFailDebug(@"Unexpected profile key length:%lu on message from:%@", (unsigned long)profileKey.length, recipientId); } } } -// Loki: Establish a session if there is no session between the memebers of a group - (void)establishSessionsWithMembersIfNeeded:(NSArray *)members forThread:(TSGroupThread *)thread transaction:(YapDatabaseReadWriteTransaction *)transaction { NSString *userHexEncodedPublicKey = OWSIdentityManager.sharedManager.identityKeyPair.hexEncodedPublicKey; @@ -1759,6 +1760,7 @@ NS_ASSUME_NONNULL_BEGIN if (envelope.isGroupChatMessage) { return NSLog(@"[Loki] Ignoring friend request in group chat.", @""); } + // The envelope type is set during UD decryption. if (envelope.type != SSKProtoEnvelopeTypeFriendRequest) { return NSLog(@"[Loki] Ignoring friend request logic for non friend request type envelope."); } @@ -1804,6 +1806,7 @@ NS_ASSUME_NONNULL_BEGIN - (void)handleFriendRequestAcceptanceIfNeededWithEnvelope:(SSKProtoEnvelope *)envelope transaction:(YapDatabaseReadWriteTransaction *)transaction { // If we get an envelope that isn't a friend request, then we can infer that we had to use // Signal cipher decryption and thus that we have a session with the other person. + // The envelope type is set during UD decryption. if (envelope.isGroupChatMessage || envelope.type == SSKProtoEnvelopeTypeFriendRequest) return; // Currently this uses `envelope.source` but with sync messages we'll need to use the message sender ID TSContactThread *thread = [TSContactThread getOrCreateThreadWithContactId:envelope.source transaction:transaction]; @@ -1896,7 +1899,7 @@ NS_ASSUME_NONNULL_BEGIN }]; } failure:^(NSError *error) { - OWSLogWarn(@"failed to download attachment for message: %lu with error: %@", + OWSLogWarn(@"Failed to download attachment for message: %lu with error: %@.", (unsigned long)incomingMessage.timestamp, error); }]; @@ -2017,7 +2020,7 @@ NS_ASSUME_NONNULL_BEGIN } } -# pragma mark - Loki Session +# pragma mark - Loki Session Handling - (void)handleNewSessionAdopted:(NSNotification *)notification { NSString *hexEncodedPublicKey = notification.userInfo[kNSNotificationKey_ContactPubKey]; diff --git a/SignalServiceKit/src/Messages/OWSMessageReceiver.m b/SignalServiceKit/src/Messages/OWSMessageReceiver.m index cd23ecf8e..adb2aa990 100644 --- a/SignalServiceKit/src/Messages/OWSMessageReceiver.m +++ b/SignalServiceKit/src/Messages/OWSMessageReceiver.m @@ -323,20 +323,12 @@ NSString *const OWSMessageDecryptJobFinderExtensionGroup = @"OWSMessageProcessin { OWSAssertDebug(AppReadiness.isAppReady); - // Don't decrypt messages in app extensions. - if (!CurrentAppContext().isMainApp) { - return; - } - if (!self.tsAccountManager.isRegisteredAndReady) { - return; - } + if (!CurrentAppContext().isMainApp) { return; } + if (!self.tsAccountManager.isRegisteredAndReady) { return; } dispatch_async(self.serialQueue, ^{ - if (self.isDrainingQueue) { - return; - } + if (self.isDrainingQueue) { return; } self.isDrainingQueue = YES; - [self drainQueueWorkStep]; }); } @@ -346,6 +338,7 @@ NSString *const OWSMessageDecryptJobFinderExtensionGroup = @"OWSMessageProcessin AssertOnDispatchQueue(self.serialQueue); OWSMessageDecryptJob *_Nullable job = [self.finder nextJob]; + if (!job) { self.isDrainingQueue = NO; OWSLogVerbose(@"Queue is drained."); @@ -369,8 +362,7 @@ NSString *const OWSMessageDecryptJobFinderExtensionGroup = @"OWSMessageProcessin - (BOOL)wasReceivedByUD:(SSKProtoEnvelope *)envelope { - return ( - envelope.type == SSKProtoEnvelopeTypeUnidentifiedSender && (!envelope.hasSource || envelope.source.length < 1)); + return (envelope.type == SSKProtoEnvelopeTypeUnidentifiedSender && (!envelope.hasSource || envelope.source.length < 1)); } - (void)processJob:(OWSMessageDecryptJob *)job completion:(void (^)(BOOL))completion @@ -379,9 +371,9 @@ NSString *const OWSMessageDecryptJobFinderExtensionGroup = @"OWSMessageProcessin OWSAssertDebug(job); SSKProtoEnvelope *_Nullable envelope = job.envelopeProto; + if (!envelope) { - OWSFailDebug(@"Could not parse proto."); - // TODO: Add analytics. + OWSFailDebug(@"Couldn't parse proto."); [self.dbConnection readWriteWithBlock:^(YapDatabaseReadWriteTransaction *transaction) { TSErrorMessage *errorMessage = [TSErrorMessage corruptedMessageInUnknownThread]; @@ -392,25 +384,7 @@ NSString *const OWSMessageDecryptJobFinderExtensionGroup = @"OWSMessageProcessin dispatch_async(self.serialQueue, ^{ completion(NO); }); - return; - } - - // Loki: Don't process any messages from ourself - ECKeyPair *_Nullable keyPair = OWSIdentityManager.sharedManager.identityKeyPair; - if (keyPair && [envelope.source isEqualToString:keyPair.hexEncodedPublicKey]) { - dispatch_async(self.serialQueue, ^{ - completion(YES); - }); - return; - } - - // Loki: Ignore any friend requests that we got before restoration - uint64_t restorationTime = [NSNumber numberWithDouble:[OWSPrimaryStorage.sharedManager getRestorationTime]].unsignedLongLongValue; - if (envelope.type == SSKProtoEnvelopeTypeFriendRequest && envelope.timestamp < restorationTime * 1000) { - [LKLogger print:@"[Loki] Ignoring friend request received before restoration."]; - dispatch_async(self.serialQueue, ^{ - completion(YES); - }); + return; } @@ -481,8 +455,7 @@ NSString *const OWSMessageDecryptJobFinderExtensionGroup = @"OWSMessageProcessin // For coherency we use the same dbConnection to persist and read the unprocessed envelopes YapDatabaseConnection *dbConnection = [primaryStorage newDatabaseConnection]; OWSMessageDecryptJobFinder *finder = [[OWSMessageDecryptJobFinder alloc] initWithDBConnection:dbConnection]; - OWSMessageDecryptQueue *processingQueue = - [[OWSMessageDecryptQueue alloc] initWithDBConnection:dbConnection finder:finder]; + OWSMessageDecryptQueue *processingQueue = [[OWSMessageDecryptQueue alloc] initWithDBConnection:dbConnection finder:finder]; _processingQueue = processingQueue; @@ -512,7 +485,7 @@ NSString *const OWSMessageDecryptJobFinderExtensionGroup = @"OWSMessageProcessin - (void)handleReceivedEnvelopeData:(NSData *)envelopeData { if (envelopeData.length < 1) { - OWSFailDebug(@"Empty envelope."); + OWSFailDebug(@"Received an empty envelope."); return; } @@ -520,7 +493,7 @@ NSString *const OWSMessageDecryptJobFinderExtensionGroup = @"OWSMessageProcessin NSUInteger kMaxEnvelopeByteCount = 250 * 1024; if (envelopeData.length > kMaxEnvelopeByteCount) { OWSProdError([OWSAnalyticsEvents messageReceiverErrorOversizeMessage]); - OWSFailDebug(@"Oversize message."); + OWSFailDebug(@"Received an oversized message."); return; } @@ -529,7 +502,7 @@ NSString *const OWSMessageDecryptJobFinderExtensionGroup = @"OWSMessageProcessin NSUInteger kLargeEnvelopeWarningByteCount = 25 * 1024; if (envelopeData.length > kLargeEnvelopeWarningByteCount) { OWSProdError([OWSAnalyticsEvents messageReceiverErrorLargeMessage]); - OWSFailDebug(@"Unexpectedly large message."); + OWSFailDebug(@"Received an unexpectedly large message."); } [self.processingQueue enqueueEnvelopeData:envelopeData];