Bump libsignal to v0.96.2
Co-authored-by: Cody Henthorne <cody@signal.org>
This commit is contained in:
parent
7fdaf6f706
commit
9dac02fa1c
@ -4,6 +4,7 @@ import androidx.annotation.NonNull;
|
||||
import androidx.annotation.Nullable;
|
||||
|
||||
import org.signal.core.util.logging.Log;
|
||||
import org.signal.libsignal.protocol.NoSessionException;
|
||||
import org.thoughtcrime.securesms.crypto.SealedSenderAccessUtil;
|
||||
import org.thoughtcrime.securesms.database.MessageTable;
|
||||
import org.thoughtcrime.securesms.database.RecipientTable.RegisteredState;
|
||||
@ -144,6 +145,8 @@ public class AutomaticSessionResetJob extends BaseJob {
|
||||
messageSender.sendNullMessage(address, SealedSenderAccessUtil.getSealedSenderAccessFor(recipient));
|
||||
} catch (UntrustedIdentityException e) {
|
||||
Log.w(TAG, "Unable to send null message.");
|
||||
} catch (NoSessionException e) {
|
||||
Log.w(TAG, "Unable to send null message; no session to send over.", e);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -4,8 +4,8 @@ import androidx.annotation.NonNull;
|
||||
import androidx.annotation.Nullable;
|
||||
import androidx.annotation.WorkerThread;
|
||||
|
||||
|
||||
import org.signal.core.util.logging.Log;
|
||||
import org.signal.libsignal.protocol.NoSessionException;
|
||||
import org.thoughtcrime.securesms.database.GroupTable;
|
||||
import org.thoughtcrime.securesms.database.SignalDatabase;
|
||||
import org.thoughtcrime.securesms.database.model.RecipientRecord;
|
||||
@ -169,7 +169,7 @@ public class GroupCallUpdateSendJob extends BaseJob {
|
||||
}
|
||||
|
||||
private @NonNull List<Recipient> deliver(@NonNull GroupId groupId, @NonNull List<Recipient> destinations)
|
||||
throws IOException, UntrustedIdentityException
|
||||
throws IOException, UntrustedIdentityException, NoSessionException
|
||||
{
|
||||
SignalServiceDataMessage.Builder dataMessageBuilder = SignalServiceDataMessage.newBuilder()
|
||||
.withTimestamp(System.currentTimeMillis())
|
||||
|
||||
@ -5,6 +5,7 @@ import androidx.annotation.WorkerThread
|
||||
import okio.utf8Size
|
||||
import org.signal.core.util.UuidUtil.parseOrThrow
|
||||
import org.signal.core.util.logging.Log
|
||||
import org.signal.libsignal.protocol.NoSessionException
|
||||
import org.thoughtcrime.securesms.crypto.SealedSenderAccessUtil
|
||||
import org.thoughtcrime.securesms.database.NoSuchMessageException
|
||||
import org.thoughtcrime.securesms.database.RecipientTable.SealedSenderAccessMode
|
||||
@ -163,7 +164,17 @@ class IndividualSendJob private constructor(parameters: Parameters, private val
|
||||
val profileKey = recipient.profileKey
|
||||
val accessMode = recipient.sealedSenderAccessMode
|
||||
|
||||
val unidentified = deliver(message, originalEditedMessage)
|
||||
val unidentified = try {
|
||||
deliver(message, originalEditedMessage)
|
||||
} catch (e: NoSessionException) {
|
||||
warn(TAG, message.sentTimeMillis.toString(), "Failed to send message, likely due to a missing or corrupt session. Archiving sessions and retrying.", e)
|
||||
|
||||
val recipientId = message.threadRecipient.id
|
||||
AppDependencies.protocolStore.aci().sessions().archiveSessions(recipientId)
|
||||
AppDependencies.protocolStore.pni().sessions().archiveSessions(recipientId)
|
||||
|
||||
throw RetryLaterException()
|
||||
}
|
||||
|
||||
SignalDatabase.messages.markAsSent(messageId)
|
||||
markAttachmentsUploaded(messageId, message)
|
||||
|
||||
@ -5,6 +5,8 @@ import androidx.annotation.NonNull;
|
||||
import androidx.annotation.Nullable;
|
||||
|
||||
import org.signal.core.util.logging.Log;
|
||||
import org.signal.libsignal.protocol.NoSessionException;
|
||||
import org.signal.network.exceptions.PushNetworkException;
|
||||
import org.thoughtcrime.securesms.dependencies.AppDependencies;
|
||||
import org.thoughtcrime.securesms.jobmanager.Job;
|
||||
import org.thoughtcrime.securesms.jobmanager.JsonJobData;
|
||||
@ -13,12 +15,10 @@ import org.thoughtcrime.securesms.jobmanager.impl.SealedSenderConstraint;
|
||||
import org.thoughtcrime.securesms.keyvalue.SignalStore;
|
||||
import org.thoughtcrime.securesms.net.NotPushRegisteredException;
|
||||
import org.thoughtcrime.securesms.recipients.Recipient;
|
||||
import org.thoughtcrime.securesms.util.TextSecurePreferences;
|
||||
import org.whispersystems.signalservice.api.SignalServiceMessageSender;
|
||||
import org.whispersystems.signalservice.api.crypto.UntrustedIdentityException;
|
||||
import org.whispersystems.signalservice.api.messages.multidevice.ConfigurationMessage;
|
||||
import org.whispersystems.signalservice.api.messages.multidevice.SignalServiceSyncMessage;
|
||||
import org.signal.network.exceptions.PushNetworkException;
|
||||
import org.whispersystems.signalservice.api.push.exceptions.ServerRejectedException;
|
||||
|
||||
import java.io.IOException;
|
||||
@ -88,7 +88,7 @@ public class MultiDeviceConfigurationUpdateJob extends BaseJob {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onRun() throws IOException, UntrustedIdentityException {
|
||||
public void onRun() throws IOException, UntrustedIdentityException, NoSessionException {
|
||||
if (!Recipient.self().isRegistered()) {
|
||||
throw new NotPushRegisteredException();
|
||||
}
|
||||
|
||||
@ -14,6 +14,9 @@ import org.signal.core.ui.permissions.Permissions;
|
||||
import org.signal.core.util.AppForegroundObserver;
|
||||
import org.signal.core.util.logging.Log;
|
||||
import org.signal.libsignal.protocol.IdentityKey;
|
||||
import org.signal.libsignal.protocol.NoSessionException;
|
||||
import org.signal.network.exceptions.PushNetworkException;
|
||||
import org.signal.network.service.CdnService;
|
||||
import org.signal.network.exceptions.PushNetworkException;
|
||||
import org.signal.network.service.CdnService;
|
||||
import org.thoughtcrime.securesms.database.RecipientTable;
|
||||
@ -118,7 +121,7 @@ public class MultiDeviceContactUpdateJob extends BaseJob {
|
||||
|
||||
@Override
|
||||
public void onRun()
|
||||
throws IOException, UntrustedIdentityException, NetworkException
|
||||
throws IOException, UntrustedIdentityException, NetworkException, NoSessionException
|
||||
{
|
||||
if (!Recipient.self().isRegistered()) {
|
||||
throw new NotPushRegisteredException();
|
||||
@ -139,7 +142,7 @@ public class MultiDeviceContactUpdateJob extends BaseJob {
|
||||
}
|
||||
|
||||
private void generateSingleContactUpdate(@NonNull RecipientId recipientId)
|
||||
throws IOException, UntrustedIdentityException, NetworkException
|
||||
throws IOException, UntrustedIdentityException, NetworkException, NoSessionException
|
||||
{
|
||||
WriteDetails writeDetails = createTempFile();
|
||||
|
||||
@ -190,7 +193,7 @@ public class MultiDeviceContactUpdateJob extends BaseJob {
|
||||
}
|
||||
|
||||
private void generateFullContactUpdate()
|
||||
throws IOException, UntrustedIdentityException, NetworkException
|
||||
throws IOException, UntrustedIdentityException, NetworkException, NoSessionException
|
||||
{
|
||||
boolean isAppVisible = AppForegroundObserver.isForegrounded();
|
||||
long timeSinceLastSync = System.currentTimeMillis() - TextSecurePreferences.getLastFullContactSyncTime(context);
|
||||
@ -277,7 +280,7 @@ public class MultiDeviceContactUpdateJob extends BaseJob {
|
||||
}
|
||||
|
||||
private void sendUpdate(SignalServiceMessageSender messageSender, InputStream stream, long length, boolean complete)
|
||||
throws UntrustedIdentityException, NetworkException
|
||||
throws UntrustedIdentityException, NetworkException, NoSessionException
|
||||
{
|
||||
if (length > 0) {
|
||||
try {
|
||||
|
||||
@ -5,6 +5,8 @@ import androidx.annotation.NonNull;
|
||||
import androidx.annotation.Nullable;
|
||||
|
||||
import org.signal.core.util.logging.Log;
|
||||
import org.signal.libsignal.protocol.NoSessionException;
|
||||
import org.signal.network.exceptions.PushNetworkException;
|
||||
import org.thoughtcrime.securesms.database.RecipientTable.RegisteredState;
|
||||
import org.thoughtcrime.securesms.database.SignalDatabase;
|
||||
import org.thoughtcrime.securesms.database.model.RecipientRecord;
|
||||
@ -17,12 +19,10 @@ import org.thoughtcrime.securesms.keyvalue.SignalStore;
|
||||
import org.thoughtcrime.securesms.net.NotPushRegisteredException;
|
||||
import org.thoughtcrime.securesms.recipients.Recipient;
|
||||
import org.thoughtcrime.securesms.recipients.RecipientId;
|
||||
import org.thoughtcrime.securesms.util.TextSecurePreferences;
|
||||
import org.whispersystems.signalservice.api.SignalServiceMessageSender;
|
||||
import org.whispersystems.signalservice.api.crypto.UntrustedIdentityException;
|
||||
import org.whispersystems.signalservice.api.messages.multidevice.MessageRequestResponseMessage;
|
||||
import org.whispersystems.signalservice.api.messages.multidevice.SignalServiceSyncMessage;
|
||||
import org.signal.network.exceptions.PushNetworkException;
|
||||
import org.whispersystems.signalservice.api.push.exceptions.ServerRejectedException;
|
||||
|
||||
import java.io.IOException;
|
||||
@ -97,7 +97,7 @@ public class MultiDeviceMessageRequestResponseJob extends BaseJob {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onRun() throws IOException, UntrustedIdentityException {
|
||||
public void onRun() throws IOException, UntrustedIdentityException, NoSessionException {
|
||||
if (!Recipient.self().isRegistered()) {
|
||||
throw new NotPushRegisteredException();
|
||||
}
|
||||
|
||||
@ -5,9 +5,9 @@ import androidx.annotation.NonNull;
|
||||
import androidx.annotation.Nullable;
|
||||
|
||||
import org.signal.core.util.logging.Log;
|
||||
import org.signal.libsignal.zkgroup.profiles.ProfileKey;
|
||||
import org.signal.libsignal.protocol.NoSessionException;
|
||||
import org.signal.network.exceptions.PushNetworkException;
|
||||
import org.signal.network.service.CdnService;
|
||||
import org.thoughtcrime.securesms.crypto.ProfileKeyUtil;
|
||||
import org.thoughtcrime.securesms.dependencies.AppDependencies;
|
||||
import org.thoughtcrime.securesms.jobmanager.Job;
|
||||
import org.thoughtcrime.securesms.jobmanager.impl.NetworkConstraint;
|
||||
@ -18,15 +18,14 @@ import org.thoughtcrime.securesms.recipients.Recipient;
|
||||
import org.whispersystems.signalservice.api.SignalServiceMessageSender;
|
||||
import org.whispersystems.signalservice.api.crypto.AttachmentCipherStreamUtil;
|
||||
import org.whispersystems.signalservice.api.crypto.UntrustedIdentityException;
|
||||
import org.whispersystems.signalservice.internal.crypto.PaddingInputStream;
|
||||
import org.whispersystems.signalservice.api.messages.SignalServiceAttachment;
|
||||
import org.whispersystems.signalservice.api.messages.SignalServiceAttachmentStream;
|
||||
import org.whispersystems.signalservice.api.messages.multidevice.ContactsMessage;
|
||||
import org.whispersystems.signalservice.api.messages.multidevice.DeviceContact;
|
||||
import org.whispersystems.signalservice.api.messages.multidevice.DeviceContactsOutputStream;
|
||||
import org.whispersystems.signalservice.api.messages.multidevice.SignalServiceSyncMessage;
|
||||
import org.signal.network.exceptions.PushNetworkException;
|
||||
import org.whispersystems.signalservice.api.push.exceptions.ServerRejectedException;
|
||||
import org.whispersystems.signalservice.internal.crypto.PaddingInputStream;
|
||||
import org.whispersystems.signalservice.internal.push.http.ResumableUploadSpec;
|
||||
|
||||
import java.io.ByteArrayInputStream;
|
||||
@ -66,7 +65,7 @@ public class MultiDeviceProfileKeyUpdateJob extends BaseJob {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onRun() throws IOException, UntrustedIdentityException {
|
||||
public void onRun() throws IOException, UntrustedIdentityException, NoSessionException {
|
||||
if (!Recipient.self().isRegistered()) {
|
||||
throw new NotPushRegisteredException();
|
||||
}
|
||||
|
||||
@ -3,12 +3,14 @@ package org.thoughtcrime.securesms.jobs;
|
||||
import androidx.annotation.NonNull;
|
||||
import androidx.annotation.Nullable;
|
||||
|
||||
import java.util.stream.Collectors;
|
||||
import java.util.stream.Stream;
|
||||
import com.fasterxml.jackson.annotation.JsonProperty;
|
||||
|
||||
import org.signal.core.models.ServiceId;
|
||||
import org.signal.core.util.JsonUtils;
|
||||
import org.signal.core.util.ListUtil;
|
||||
import org.signal.core.util.logging.Log;
|
||||
import org.signal.libsignal.protocol.NoSessionException;
|
||||
import org.signal.network.exceptions.PushNetworkException;
|
||||
import org.thoughtcrime.securesms.database.MessageTable.SyncMessageId;
|
||||
import org.thoughtcrime.securesms.database.RecipientTable.RegisteredState;
|
||||
import org.thoughtcrime.securesms.database.SignalDatabase;
|
||||
@ -23,13 +25,10 @@ import org.thoughtcrime.securesms.keyvalue.SignalStore;
|
||||
import org.thoughtcrime.securesms.net.NotPushRegisteredException;
|
||||
import org.thoughtcrime.securesms.recipients.Recipient;
|
||||
import org.thoughtcrime.securesms.recipients.RecipientId;
|
||||
import org.signal.core.util.JsonUtils;
|
||||
import org.whispersystems.signalservice.api.SignalServiceMessageSender;
|
||||
import org.whispersystems.signalservice.api.crypto.UntrustedIdentityException;
|
||||
import org.whispersystems.signalservice.api.messages.multidevice.ReadMessage;
|
||||
import org.whispersystems.signalservice.api.messages.multidevice.SignalServiceSyncMessage;
|
||||
import org.signal.core.models.ServiceId;
|
||||
import org.signal.network.exceptions.PushNetworkException;
|
||||
import org.whispersystems.signalservice.api.push.exceptions.ServerRejectedException;
|
||||
|
||||
import java.io.IOException;
|
||||
@ -37,6 +36,8 @@ import java.io.Serializable;
|
||||
import java.util.LinkedList;
|
||||
import java.util.List;
|
||||
import java.util.concurrent.TimeUnit;
|
||||
import java.util.stream.Collectors;
|
||||
import java.util.stream.Stream;
|
||||
|
||||
public class MultiDeviceReadUpdateJob extends BaseJob {
|
||||
|
||||
@ -106,7 +107,7 @@ public class MultiDeviceReadUpdateJob extends BaseJob {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onRun() throws IOException, UntrustedIdentityException {
|
||||
public void onRun() throws IOException, UntrustedIdentityException, NoSessionException {
|
||||
if (!Recipient.self().isRegistered()) {
|
||||
throw new NotPushRegisteredException();
|
||||
}
|
||||
|
||||
@ -8,6 +8,8 @@ import org.signal.core.util.Base64;
|
||||
import org.signal.core.util.logging.Log;
|
||||
import org.signal.libsignal.protocol.IdentityKey;
|
||||
import org.signal.libsignal.protocol.InvalidKeyException;
|
||||
import org.signal.libsignal.protocol.NoSessionException;
|
||||
import org.signal.network.exceptions.PushNetworkException;
|
||||
import org.thoughtcrime.securesms.database.IdentityTable.VerifiedStatus;
|
||||
import org.thoughtcrime.securesms.dependencies.AppDependencies;
|
||||
import org.thoughtcrime.securesms.jobmanager.Job;
|
||||
@ -19,13 +21,11 @@ import org.thoughtcrime.securesms.net.NotPushRegisteredException;
|
||||
import org.thoughtcrime.securesms.recipients.Recipient;
|
||||
import org.thoughtcrime.securesms.recipients.RecipientId;
|
||||
import org.thoughtcrime.securesms.recipients.RecipientUtil;
|
||||
import org.thoughtcrime.securesms.util.TextSecurePreferences;
|
||||
import org.whispersystems.signalservice.api.SignalServiceMessageSender;
|
||||
import org.whispersystems.signalservice.api.crypto.UntrustedIdentityException;
|
||||
import org.whispersystems.signalservice.api.messages.multidevice.SignalServiceSyncMessage;
|
||||
import org.whispersystems.signalservice.api.messages.multidevice.VerifiedMessage;
|
||||
import org.whispersystems.signalservice.api.push.SignalServiceAddress;
|
||||
import org.signal.network.exceptions.PushNetworkException;
|
||||
import org.whispersystems.signalservice.api.push.exceptions.ServerRejectedException;
|
||||
|
||||
import java.io.IOException;
|
||||
@ -90,7 +90,7 @@ public class MultiDeviceVerifiedUpdateJob extends BaseJob {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onRun() throws IOException, UntrustedIdentityException {
|
||||
public void onRun() throws IOException, UntrustedIdentityException, NoSessionException {
|
||||
if (!Recipient.self().isRegistered()) {
|
||||
throw new NotPushRegisteredException();
|
||||
}
|
||||
|
||||
@ -5,7 +5,10 @@ import androidx.annotation.Nullable;
|
||||
|
||||
import com.fasterxml.jackson.annotation.JsonProperty;
|
||||
|
||||
import org.signal.core.util.JsonUtils;
|
||||
import org.signal.core.util.logging.Log;
|
||||
import org.signal.libsignal.protocol.NoSessionException;
|
||||
import org.signal.network.exceptions.PushNetworkException;
|
||||
import org.thoughtcrime.securesms.database.MessageTable.SyncMessageId;
|
||||
import org.thoughtcrime.securesms.database.RecipientTable.RegisteredState;
|
||||
import org.thoughtcrime.securesms.database.SignalDatabase;
|
||||
@ -19,13 +22,10 @@ import org.thoughtcrime.securesms.keyvalue.SignalStore;
|
||||
import org.thoughtcrime.securesms.net.NotPushRegisteredException;
|
||||
import org.thoughtcrime.securesms.recipients.Recipient;
|
||||
import org.thoughtcrime.securesms.recipients.RecipientId;
|
||||
import org.signal.core.util.JsonUtils;
|
||||
import org.thoughtcrime.securesms.util.TextSecurePreferences;
|
||||
import org.whispersystems.signalservice.api.SignalServiceMessageSender;
|
||||
import org.whispersystems.signalservice.api.crypto.UntrustedIdentityException;
|
||||
import org.whispersystems.signalservice.api.messages.multidevice.SignalServiceSyncMessage;
|
||||
import org.whispersystems.signalservice.api.messages.multidevice.ViewOnceOpenMessage;
|
||||
import org.signal.network.exceptions.PushNetworkException;
|
||||
import org.whispersystems.signalservice.api.push.exceptions.ServerRejectedException;
|
||||
|
||||
import java.io.IOException;
|
||||
@ -76,7 +76,7 @@ public class MultiDeviceViewOnceOpenJob extends BaseJob {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onRun() throws IOException, UntrustedIdentityException {
|
||||
public void onRun() throws IOException, UntrustedIdentityException, NoSessionException {
|
||||
if (!Recipient.self().isRegistered()) {
|
||||
throw new NotPushRegisteredException();
|
||||
}
|
||||
|
||||
@ -3,12 +3,13 @@ package org.thoughtcrime.securesms.jobs;
|
||||
import androidx.annotation.NonNull;
|
||||
import androidx.annotation.Nullable;
|
||||
|
||||
import java.util.stream.Collectors;
|
||||
import java.util.stream.Stream;
|
||||
import com.fasterxml.jackson.annotation.JsonProperty;
|
||||
|
||||
import org.signal.core.util.JsonUtils;
|
||||
import org.signal.core.util.ListUtil;
|
||||
import org.signal.core.util.logging.Log;
|
||||
import org.signal.libsignal.protocol.NoSessionException;
|
||||
import org.signal.network.exceptions.PushNetworkException;
|
||||
import org.thoughtcrime.securesms.database.MessageTable.SyncMessageId;
|
||||
import org.thoughtcrime.securesms.database.RecipientTable.RegisteredState;
|
||||
import org.thoughtcrime.securesms.database.SignalDatabase;
|
||||
@ -23,13 +24,10 @@ import org.thoughtcrime.securesms.keyvalue.SignalStore;
|
||||
import org.thoughtcrime.securesms.net.NotPushRegisteredException;
|
||||
import org.thoughtcrime.securesms.recipients.Recipient;
|
||||
import org.thoughtcrime.securesms.recipients.RecipientId;
|
||||
import org.signal.core.util.JsonUtils;
|
||||
import org.thoughtcrime.securesms.util.TextSecurePreferences;
|
||||
import org.whispersystems.signalservice.api.SignalServiceMessageSender;
|
||||
import org.whispersystems.signalservice.api.crypto.UntrustedIdentityException;
|
||||
import org.whispersystems.signalservice.api.messages.multidevice.SignalServiceSyncMessage;
|
||||
import org.whispersystems.signalservice.api.messages.multidevice.ViewedMessage;
|
||||
import org.signal.network.exceptions.PushNetworkException;
|
||||
import org.whispersystems.signalservice.api.push.exceptions.ServerRejectedException;
|
||||
|
||||
import java.io.IOException;
|
||||
@ -37,6 +35,8 @@ import java.io.Serializable;
|
||||
import java.util.LinkedList;
|
||||
import java.util.List;
|
||||
import java.util.concurrent.TimeUnit;
|
||||
import java.util.stream.Collectors;
|
||||
import java.util.stream.Stream;
|
||||
|
||||
public class MultiDeviceViewedUpdateJob extends BaseJob {
|
||||
|
||||
@ -106,7 +106,7 @@ public class MultiDeviceViewedUpdateJob extends BaseJob {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onRun() throws IOException, UntrustedIdentityException {
|
||||
public void onRun() throws IOException, UntrustedIdentityException, NoSessionException {
|
||||
if (!Recipient.self().isRegistered()) {
|
||||
throw new NotPushRegisteredException();
|
||||
}
|
||||
|
||||
@ -5,6 +5,7 @@ import androidx.annotation.Nullable;
|
||||
import androidx.annotation.WorkerThread;
|
||||
|
||||
import org.signal.core.util.logging.Log;
|
||||
import org.signal.libsignal.protocol.NoSessionException;
|
||||
import org.thoughtcrime.securesms.database.GroupTable;
|
||||
import org.thoughtcrime.securesms.database.SignalDatabase;
|
||||
import org.thoughtcrime.securesms.database.model.RecipientRecord;
|
||||
@ -188,7 +189,7 @@ public class ProfileKeySendJob extends BaseJob {
|
||||
|
||||
}
|
||||
|
||||
private List<Recipient> deliver(@NonNull List<Recipient> destinations) throws IOException, UntrustedIdentityException {
|
||||
private List<Recipient> deliver(@NonNull List<Recipient> destinations) throws IOException, UntrustedIdentityException, NoSessionException {
|
||||
SignalServiceDataMessage.Builder dataMessage = SignalServiceDataMessage.newBuilder()
|
||||
.asProfileKeyUpdate(true)
|
||||
.withTimestamp(System.currentTimeMillis())
|
||||
|
||||
@ -6,8 +6,9 @@ import androidx.annotation.NonNull;
|
||||
import androidx.annotation.Nullable;
|
||||
import androidx.annotation.WorkerThread;
|
||||
|
||||
|
||||
import org.signal.core.util.Util;
|
||||
import org.signal.core.util.logging.Log;
|
||||
import org.signal.libsignal.protocol.NoSessionException;
|
||||
import org.thoughtcrime.securesms.attachments.Attachment;
|
||||
import org.thoughtcrime.securesms.attachments.DatabaseAttachment;
|
||||
import org.thoughtcrime.securesms.database.GroupReceiptTable;
|
||||
@ -33,7 +34,6 @@ import org.thoughtcrime.securesms.recipients.RecipientId;
|
||||
import org.thoughtcrime.securesms.stories.Stories;
|
||||
import org.thoughtcrime.securesms.transport.RetryLaterException;
|
||||
import org.thoughtcrime.securesms.transport.UndeliverableMessageException;
|
||||
import org.signal.core.util.Util;
|
||||
import org.whispersystems.signalservice.api.crypto.UntrustedIdentityException;
|
||||
import org.whispersystems.signalservice.api.messages.SendMessageResult;
|
||||
import org.whispersystems.signalservice.api.messages.SignalServiceAttachment;
|
||||
@ -189,7 +189,7 @@ public final class PushDistributionListSendJob extends PushSendJob {
|
||||
|
||||
PushGroupSendJob.processGroupMessageResults(context, messageId, -1, null, message, results, targets, skipped, existingNetworkFailures, existingIdentityMismatches);
|
||||
|
||||
} catch (UntrustedIdentityException | UndeliverableMessageException e) {
|
||||
} catch (UntrustedIdentityException | UndeliverableMessageException | NoSessionException e) {
|
||||
warn(TAG, String.valueOf(message.getSentTimeMillis()), e);
|
||||
database.markAsSentFailed(messageId);
|
||||
notifyMediaMessageDeliveryFailed(context, messageId);
|
||||
@ -202,7 +202,7 @@ public final class PushDistributionListSendJob extends PushSendJob {
|
||||
}
|
||||
|
||||
private List<SendMessageResult> deliver(@NonNull OutgoingMessage message, @NonNull List<Recipient> destinations)
|
||||
throws IOException, UntrustedIdentityException, UndeliverableMessageException
|
||||
throws IOException, UntrustedIdentityException, UndeliverableMessageException, NoSessionException
|
||||
{
|
||||
try {
|
||||
List<Attachment> attachments = message.getAttachments().stream().filter(attachment -> !attachment.isSticker()).collect(Collectors.toList());
|
||||
|
||||
@ -6,10 +6,11 @@ import androidx.annotation.NonNull;
|
||||
import androidx.annotation.Nullable;
|
||||
import androidx.annotation.WorkerThread;
|
||||
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
import org.signal.core.util.ByteUnit;
|
||||
import org.signal.core.util.SetUtil;
|
||||
import org.signal.core.util.Util;
|
||||
import org.signal.core.util.logging.Log;
|
||||
import org.signal.libsignal.protocol.NoSessionException;
|
||||
import org.thoughtcrime.securesms.attachments.Attachment;
|
||||
import org.thoughtcrime.securesms.database.GroupReceiptTable;
|
||||
import org.thoughtcrime.securesms.database.GroupReceiptTable.GroupReceiptInfo;
|
||||
@ -44,12 +45,10 @@ import org.thoughtcrime.securesms.recipients.RecipientId;
|
||||
import org.thoughtcrime.securesms.recipients.RecipientUtil;
|
||||
import org.thoughtcrime.securesms.transport.RetryLaterException;
|
||||
import org.thoughtcrime.securesms.transport.UndeliverableMessageException;
|
||||
import org.signal.core.util.ByteUnit;
|
||||
import org.thoughtcrime.securesms.util.GroupUtil;
|
||||
import org.thoughtcrime.securesms.util.MessageUtil;
|
||||
import org.thoughtcrime.securesms.util.RecipientAccessList;
|
||||
import org.thoughtcrime.securesms.util.SignalLocalMetrics;
|
||||
import org.signal.core.util.Util;
|
||||
import org.whispersystems.signalservice.api.crypto.ContentHint;
|
||||
import org.whispersystems.signalservice.api.crypto.UntrustedIdentityException;
|
||||
import org.whispersystems.signalservice.api.messages.SendMessageResult;
|
||||
@ -74,9 +73,9 @@ import java.util.Locale;
|
||||
import java.util.Optional;
|
||||
import java.util.Set;
|
||||
import java.util.concurrent.TimeUnit;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
import kotlin.Pair;
|
||||
|
||||
import okio.ByteString;
|
||||
import okio.Utf8;
|
||||
|
||||
@ -250,7 +249,7 @@ public final class PushGroupSendJob extends PushSendJob {
|
||||
ConversationShortcutRankingUpdateJob.enqueueForOutgoingIfNecessary(groupRecipient);
|
||||
Log.i(TAG, JobLogger.format(this, "Finished send."));
|
||||
|
||||
} catch (UntrustedIdentityException | UndeliverableMessageException e) {
|
||||
} catch (UntrustedIdentityException | UndeliverableMessageException | NoSessionException e) {
|
||||
warn(TAG, String.valueOf(message.getSentTimeMillis()), e);
|
||||
database.markAsSentFailed(messageId);
|
||||
notifyMediaMessageDeliveryFailed(context, messageId);
|
||||
@ -271,7 +270,7 @@ public final class PushGroupSendJob extends PushSendJob {
|
||||
}
|
||||
|
||||
private List<SendMessageResult> deliver(OutgoingMessage message, @Nullable MessageRecord originalEditedMessage, @NonNull Recipient groupRecipient, @NonNull List<Recipient> destinations)
|
||||
throws IOException, UntrustedIdentityException, UndeliverableMessageException
|
||||
throws IOException, UntrustedIdentityException, UndeliverableMessageException, NoSessionException
|
||||
{
|
||||
if (Utf8.size(message.getBody()) > MessageUtil.MAX_INLINE_BODY_SIZE_BYTES) {
|
||||
throw new UndeliverableMessageException("The total body size was greater than our limit of " + MessageUtil.MAX_INLINE_BODY_SIZE_BYTES + " bytes.");
|
||||
|
||||
@ -10,6 +10,7 @@ import org.signal.core.models.ServiceId;
|
||||
import org.signal.core.models.ServiceId.ACI;
|
||||
import org.signal.core.util.Base64;
|
||||
import org.signal.core.util.logging.Log;
|
||||
import org.signal.libsignal.protocol.NoSessionException;
|
||||
import org.signal.storageservice.storage.protos.groups.local.DecryptedGroup;
|
||||
import org.thoughtcrime.securesms.database.RecipientTable;
|
||||
import org.thoughtcrime.securesms.database.SignalDatabase;
|
||||
@ -178,7 +179,7 @@ public final class PushGroupSilentUpdateSendJob extends BaseJob {
|
||||
}
|
||||
|
||||
private @NonNull List<Recipient> deliver(@NonNull List<Recipient> destinations, @NonNull GroupId.V2 groupId)
|
||||
throws IOException, UntrustedIdentityException
|
||||
throws IOException, UntrustedIdentityException, NoSessionException
|
||||
{
|
||||
SignalServiceGroupV2 group = SignalServiceGroupV2.fromProtobuf(groupContextV2);
|
||||
SignalServiceDataMessage groupDataMessage = SignalServiceDataMessage.newBuilder()
|
||||
|
||||
@ -7,6 +7,7 @@ import androidx.annotation.Nullable;
|
||||
import androidx.annotation.WorkerThread;
|
||||
|
||||
import org.signal.core.util.logging.Log;
|
||||
import org.signal.libsignal.protocol.NoSessionException;
|
||||
import org.thoughtcrime.securesms.database.GroupTable;
|
||||
import org.thoughtcrime.securesms.database.NoSuchMessageException;
|
||||
import org.thoughtcrime.securesms.database.ReactionTable;
|
||||
@ -229,7 +230,7 @@ public class ReactionSendJob extends BaseJob {
|
||||
}
|
||||
|
||||
private @NonNull List<Recipient> deliver(@NonNull RecipientRecord conversationRecipient, @NonNull List<Recipient> destinations, @NonNull Recipient targetAuthor, long targetSentTimestamp)
|
||||
throws IOException, UntrustedIdentityException
|
||||
throws IOException, UntrustedIdentityException, NoSessionException
|
||||
{
|
||||
SignalServiceDataMessage.Builder dataMessageBuilder = SignalServiceDataMessage.newBuilder()
|
||||
.withTimestamp(System.currentTimeMillis())
|
||||
|
||||
@ -1,6 +1,7 @@
|
||||
package org.thoughtcrime.securesms.jobs
|
||||
|
||||
import org.signal.core.util.logging.Log
|
||||
import org.signal.libsignal.protocol.NoSessionException
|
||||
import org.thoughtcrime.securesms.dependencies.AppDependencies
|
||||
import org.thoughtcrime.securesms.recipients.RecipientId
|
||||
import org.whispersystems.signalservice.api.crypto.UntrustedIdentityException
|
||||
@ -23,15 +24,15 @@ object ReceiptSender {
|
||||
fun sendWithSessionRepair(recipientId: RecipientId, operation: ReceiptSendOperation): SendMessageResult? {
|
||||
return try {
|
||||
operation.send()
|
||||
} catch (e: IllegalStateException) {
|
||||
Log.w(TAG, "Failed to send receipt, likely due to a missing or corrupt session. Archiving sessions and retrying.", e)
|
||||
} catch (e: NoSessionException) {
|
||||
Log.w(TAG, "Failed to send receipt due to a missing session. Archiving sessions and retrying.", e)
|
||||
|
||||
AppDependencies.protocolStore.aci().sessions().archiveSessions(recipientId)
|
||||
AppDependencies.protocolStore.pni().sessions().archiveSessions(recipientId)
|
||||
|
||||
try {
|
||||
operation.send()
|
||||
} catch (retryError: IllegalStateException) {
|
||||
} catch (retryError: NoSessionException) {
|
||||
Log.w(TAG, "Failed to send receipt even after archiving sessions. Dropping.", retryError)
|
||||
null
|
||||
}
|
||||
@ -39,7 +40,7 @@ object ReceiptSender {
|
||||
}
|
||||
|
||||
fun interface ReceiptSendOperation {
|
||||
@Throws(IOException::class, UntrustedIdentityException::class)
|
||||
@Throws(IOException::class, UntrustedIdentityException::class, NoSessionException::class)
|
||||
fun send(): SendMessageResult
|
||||
}
|
||||
}
|
||||
|
||||
@ -7,6 +7,7 @@ import androidx.annotation.WorkerThread;
|
||||
import org.signal.core.util.SetUtil;
|
||||
import org.signal.core.util.Util;
|
||||
import org.signal.core.util.logging.Log;
|
||||
import org.signal.libsignal.protocol.NoSessionException;
|
||||
import org.thoughtcrime.securesms.database.GroupTable;
|
||||
import org.thoughtcrime.securesms.database.MessageTable;
|
||||
import org.thoughtcrime.securesms.database.NoSuchMessageException;
|
||||
@ -228,7 +229,7 @@ public class RemoteDeleteSendJob extends BaseJob {
|
||||
long targetSentTimestamp,
|
||||
boolean isForStory,
|
||||
@Nullable DistributionListId distributionListId)
|
||||
throws IOException, UntrustedIdentityException
|
||||
throws IOException, UntrustedIdentityException, NoSessionException
|
||||
{
|
||||
SignalServiceDataMessage.Builder dataMessageBuilder = SignalServiceDataMessage.newBuilder()
|
||||
.withTimestamp(System.currentTimeMillis())
|
||||
|
||||
@ -5,6 +5,7 @@ import androidx.annotation.Nullable;
|
||||
|
||||
import org.signal.core.util.ThreadUtil;
|
||||
import org.signal.core.util.logging.Log;
|
||||
import org.signal.libsignal.protocol.NoSessionException;
|
||||
import org.signal.libsignal.protocol.SignalProtocolAddress;
|
||||
import org.signal.libsignal.protocol.message.SenderKeyDistributionMessage;
|
||||
import org.thoughtcrime.securesms.crypto.SealedSenderAccessUtil;
|
||||
@ -187,8 +188,8 @@ public class ResendMessageJob extends BaseJob {
|
||||
|
||||
try {
|
||||
result = messageSender.resendContent(address, access, sentTimestamp, contentToSend, contentHint, Optional.ofNullable(groupId).map(GroupId::getDecodedId), urgent);
|
||||
} catch (IllegalStateException e) {
|
||||
Log.w(TAG, "Failed to resend content. Archiving session and trying again.", e);
|
||||
} catch (NoSessionException e) {
|
||||
Log.w(TAG, "Failed to resend content due to a missing session. Archiving session and trying again.", e);
|
||||
AppDependencies.getProtocolStore().aci().sessions().archiveSessions(recipientId, SignalServiceAddress.DEFAULT_DEVICE_ID);
|
||||
AppDependencies.getProtocolStore().aci().sessions().archiveSiblingSessions(recipient.getServiceId().toProtocolAddress(SignalServiceAddress.DEFAULT_DEVICE_ID));
|
||||
AppDependencies.getProtocolStore().pni().sessions().archiveSessions(recipientId, SignalServiceAddress.DEFAULT_DEVICE_ID);
|
||||
|
||||
@ -6,6 +6,8 @@ import androidx.annotation.NonNull;
|
||||
import androidx.annotation.Nullable;
|
||||
import androidx.annotation.WorkerThread;
|
||||
|
||||
import org.signal.core.models.ServiceId;
|
||||
import org.signal.core.util.Util;
|
||||
import org.signal.core.util.logging.Log;
|
||||
import org.signal.libsignal.metadata.certificate.SenderCertificate;
|
||||
import org.signal.libsignal.protocol.InvalidKeyException;
|
||||
@ -14,6 +16,7 @@ import org.signal.libsignal.protocol.NoSessionException;
|
||||
import org.signal.libsignal.zkgroup.groups.GroupSecretParams;
|
||||
import org.signal.libsignal.zkgroup.groupsend.GroupSendEndorsement;
|
||||
import org.signal.libsignal.zkgroup.groupsend.GroupSendFullToken;
|
||||
import org.signal.network.util.Preconditions;
|
||||
import org.thoughtcrime.securesms.crypto.SealedSenderAccessUtil;
|
||||
import org.thoughtcrime.securesms.crypto.SenderKeyUtil;
|
||||
import org.thoughtcrime.securesms.database.MessageSendLogTables;
|
||||
@ -34,7 +37,6 @@ import org.thoughtcrime.securesms.recipients.RecipientUtil;
|
||||
import org.thoughtcrime.securesms.util.RecipientAccessList;
|
||||
import org.thoughtcrime.securesms.util.RemoteConfig;
|
||||
import org.thoughtcrime.securesms.util.SignalLocalMetrics;
|
||||
import org.signal.core.util.Util;
|
||||
import org.whispersystems.signalservice.api.SignalServiceMessageSender;
|
||||
import org.whispersystems.signalservice.api.SignalServiceMessageSender.LegacyGroupEvents;
|
||||
import org.whispersystems.signalservice.api.SignalServiceMessageSender.SenderKeyGroupEvents;
|
||||
@ -51,10 +53,8 @@ import org.whispersystems.signalservice.api.messages.SignalServiceStoryMessageRe
|
||||
import org.whispersystems.signalservice.api.messages.SignalServiceTypingMessage;
|
||||
import org.whispersystems.signalservice.api.messages.calls.SignalServiceCallMessage;
|
||||
import org.whispersystems.signalservice.api.push.DistributionId;
|
||||
import org.signal.core.models.ServiceId;
|
||||
import org.whispersystems.signalservice.api.push.SignalServiceAddress;
|
||||
import org.whispersystems.signalservice.api.push.exceptions.NotFoundException;
|
||||
import org.signal.network.util.Preconditions;
|
||||
import org.whispersystems.signalservice.internal.push.exceptions.InvalidUnidentifiedAccessHeaderException;
|
||||
import org.whispersystems.signalservice.internal.push.http.CancelationSignal;
|
||||
import org.whispersystems.signalservice.internal.push.http.PartialSendBatchCompleteListener;
|
||||
@ -108,7 +108,7 @@ public final class GroupSendUtil {
|
||||
boolean isForStory,
|
||||
@Nullable SignalServiceEditMessage editMessage,
|
||||
@Nullable CancelationSignal cancelationSignal)
|
||||
throws IOException, UntrustedIdentityException
|
||||
throws IOException, UntrustedIdentityException, NoSessionException
|
||||
{
|
||||
Preconditions.checkArgument(groupId == null || distributionListId == null, "Cannot supply both a groupId and a distributionListId!");
|
||||
|
||||
@ -135,7 +135,7 @@ public final class GroupSendUtil {
|
||||
@NonNull SignalServiceDataMessage message,
|
||||
boolean urgent,
|
||||
CancelationSignal cancelationSignal)
|
||||
throws IOException, UntrustedIdentityException
|
||||
throws IOException, UntrustedIdentityException, NoSessionException
|
||||
{
|
||||
return sendMessage(context, groupId, getDistributionId(groupId), null, allTargets, isRecipientUpdate, false, DataSendOperation.unresendable(message, contentHint, urgent), cancelationSignal);
|
||||
}
|
||||
@ -152,7 +152,7 @@ public final class GroupSendUtil {
|
||||
@NonNull List<Recipient> allTargets,
|
||||
@NonNull SignalServiceTypingMessage message,
|
||||
@Nullable CancelationSignal cancelationSignal)
|
||||
throws IOException, UntrustedIdentityException
|
||||
throws IOException, UntrustedIdentityException, NoSessionException
|
||||
{
|
||||
return sendMessage(context, groupId, getDistributionId(groupId), null, allTargets, false, false, new TypingSendOperation(message), cancelationSignal);
|
||||
}
|
||||
@ -168,7 +168,7 @@ public final class GroupSendUtil {
|
||||
@NonNull GroupId.V2 groupId,
|
||||
@NonNull List<Recipient> allTargets,
|
||||
@NonNull SignalServiceCallMessage message)
|
||||
throws IOException, UntrustedIdentityException
|
||||
throws IOException, UntrustedIdentityException, NoSessionException
|
||||
{
|
||||
return sendMessage(context, groupId, getDistributionId(groupId), null, allTargets, false, false, new CallSendOperation(message), null);
|
||||
}
|
||||
@ -187,7 +187,7 @@ public final class GroupSendUtil {
|
||||
long sentTimestamp,
|
||||
@NonNull SignalServiceStoryMessage message,
|
||||
@NonNull Set<SignalServiceStoryMessageRecipient> manifest)
|
||||
throws IOException, UntrustedIdentityException
|
||||
throws IOException, UntrustedIdentityException, NoSessionException
|
||||
{
|
||||
return sendMessage(
|
||||
context,
|
||||
@ -214,7 +214,7 @@ public final class GroupSendUtil {
|
||||
@NonNull MessageId messageId,
|
||||
long sentTimestamp,
|
||||
@NonNull SignalServiceStoryMessage message)
|
||||
throws IOException, UntrustedIdentityException
|
||||
throws IOException, UntrustedIdentityException, NoSessionException
|
||||
{
|
||||
return sendMessage(
|
||||
context,
|
||||
@ -253,7 +253,7 @@ public final class GroupSendUtil {
|
||||
boolean isStorySend,
|
||||
@NonNull SendOperation sendOperation,
|
||||
@Nullable CancelationSignal cancelationSignal)
|
||||
throws IOException, UntrustedIdentityException
|
||||
throws IOException, UntrustedIdentityException, NoSessionException
|
||||
{
|
||||
Log.i(TAG, "Starting group send. GroupId: " + (groupId != null ? groupId.toString() : "none") + ", DistributionId: " + (distributionId != null ? distributionId.toString() : "none") + " RelatedMessageId: " + (relatedMessageId != null ? relatedMessageId.toString() : "none") + ", Targets: " + allTargets.size() + ", RecipientUpdate: " + isRecipientUpdate + ", Operation: " + sendOperation.getClass().getSimpleName());
|
||||
|
||||
@ -577,7 +577,7 @@ public final class GroupSendUtil {
|
||||
boolean isRecipientUpdate,
|
||||
@Nullable PartialSendCompleteListener partialListener,
|
||||
@Nullable CancelationSignal cancelationSignal)
|
||||
throws IOException, UntrustedIdentityException;
|
||||
throws IOException, UntrustedIdentityException, NoSessionException;
|
||||
|
||||
@NonNull ContentHint getContentHint();
|
||||
long getSentTimestamp();
|
||||
@ -639,7 +639,7 @@ public final class GroupSendUtil {
|
||||
boolean isRecipientUpdate,
|
||||
@Nullable PartialSendCompleteListener partialListener,
|
||||
@Nullable CancelationSignal cancelationSignal)
|
||||
throws IOException, UntrustedIdentityException
|
||||
throws IOException, UntrustedIdentityException, NoSessionException
|
||||
{
|
||||
// PniSignatures are only needed for 1:1 messages, but some message jobs use the GroupSendUtil methods to send 1:1
|
||||
if (targets.size() == 1 && relatedMessageId == null) {
|
||||
@ -877,7 +877,7 @@ public final class GroupSendUtil {
|
||||
boolean isRecipientUpdate,
|
||||
@Nullable PartialSendCompleteListener partialListener,
|
||||
@Nullable CancelationSignal cancelationSignal)
|
||||
throws IOException, UntrustedIdentityException
|
||||
throws IOException, UntrustedIdentityException, NoSessionException
|
||||
{
|
||||
// We only allow legacy sends if you're sending to an empty group and just need to send a sync message.
|
||||
if (targets.isEmpty()) {
|
||||
|
||||
@ -13,16 +13,19 @@ import androidx.annotation.Nullable;
|
||||
|
||||
import org.greenrobot.eventbus.EventBus;
|
||||
import org.signal.core.models.ServiceId.ACI;
|
||||
import org.signal.core.util.AppForegroundObserver;
|
||||
import org.signal.core.util.Util;
|
||||
import org.signal.core.util.concurrent.KeyedSerialMonoLifoExecutor;
|
||||
import org.signal.core.util.concurrent.SignalExecutors;
|
||||
import org.signal.core.util.logging.Log;
|
||||
import org.signal.libsignal.protocol.NoSessionException;
|
||||
import org.signal.libsignal.zkgroup.GenericServerPublicParams;
|
||||
import org.signal.libsignal.zkgroup.InvalidInputException;
|
||||
import org.signal.libsignal.zkgroup.VerificationFailedException;
|
||||
import org.signal.libsignal.zkgroup.calllinks.CallLinkAuthCredentialPresentation;
|
||||
import org.signal.libsignal.zkgroup.calllinks.CallLinkSecretParams;
|
||||
import org.signal.libsignal.zkgroup.groups.GroupIdentifier;
|
||||
import org.signal.network.NetworkResult;
|
||||
import org.signal.ringrtc.CallException;
|
||||
import org.signal.ringrtc.CallId;
|
||||
import org.signal.ringrtc.CallLinkRootKey;
|
||||
@ -68,7 +71,6 @@ import org.thoughtcrime.securesms.service.webrtc.links.CallLinkRoomId;
|
||||
import org.thoughtcrime.securesms.service.webrtc.links.SignalCallLinkManager;
|
||||
import org.thoughtcrime.securesms.service.webrtc.state.WebRtcEphemeralState;
|
||||
import org.thoughtcrime.securesms.service.webrtc.state.WebRtcServiceState;
|
||||
import org.signal.core.util.AppForegroundObserver;
|
||||
import org.thoughtcrime.securesms.util.RecipientAccessList;
|
||||
import org.thoughtcrime.securesms.util.TextSecurePreferences;
|
||||
import org.thoughtcrime.securesms.util.rx.RxStore;
|
||||
@ -76,7 +78,6 @@ import org.thoughtcrime.securesms.webrtc.CallNotificationBuilder;
|
||||
import org.thoughtcrime.securesms.webrtc.audio.SignalAudioManager;
|
||||
import org.thoughtcrime.securesms.webrtc.locks.LockManager;
|
||||
import org.webrtc.PeerConnection;
|
||||
import org.signal.network.NetworkResult;
|
||||
import org.whispersystems.signalservice.api.NetworkResultUtil;
|
||||
import org.whispersystems.signalservice.api.crypto.SealedSenderAccess;
|
||||
import org.whispersystems.signalservice.api.crypto.UntrustedIdentityException;
|
||||
@ -902,6 +903,10 @@ public final class SignalCallManager implements CallManager.Observer, GroupCall.
|
||||
} catch (IOException e) {
|
||||
Log.i(TAG, "onSendCallMessage onFailure: ", e);
|
||||
process((s, p) -> p.handleGroupMessageSentError(s, Collections.singletonList(recipient.getId()), NETWORK_FAILURE));
|
||||
} catch (NoSessionException e) {
|
||||
Log.w(TAG, "onSendCallMessage onFailure: missing or corrupt session. Archiving sessions so the next send rebuilds.", e);
|
||||
archiveSessions(recipient.getId());
|
||||
process((s, p) -> p.handleGroupMessageSentError(s, Collections.singletonList(recipient.getId()), NETWORK_FAILURE));
|
||||
}
|
||||
});
|
||||
}
|
||||
@ -947,7 +952,7 @@ public final class SignalCallManager implements CallManager.Observer, GroupCall.
|
||||
|
||||
RetrieveProfileJob.enqueue(identifyFailureRecipientIds, true);
|
||||
}
|
||||
} catch (UntrustedIdentityException | IOException | InvalidInputException e) {
|
||||
} catch (UntrustedIdentityException | IOException | InvalidInputException | NoSessionException e) {
|
||||
Log.w(TAG, "onSendCallMessageToGroup failed", e);
|
||||
}
|
||||
});
|
||||
@ -1323,10 +1328,23 @@ public final class SignalCallManager implements CallManager.Observer, GroupCall.
|
||||
remotePeer.getCallId(),
|
||||
e instanceof UnregisteredUserException ? NO_SUCH_USER : NETWORK_FAILURE,
|
||||
Optional.empty()));
|
||||
} catch (NoSessionException e) {
|
||||
Log.w(TAG, "sendCallMessage: missing or corrupt session. Archiving sessions so the next send rebuilds.", e);
|
||||
archiveSessions(recipient.getId());
|
||||
processSendMessageFailureWithChangeDetection(remotePeer,
|
||||
(s, p) -> p.handleMessageSentError(s,
|
||||
remotePeer.getCallId(),
|
||||
NETWORK_FAILURE,
|
||||
Optional.empty()));
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private void archiveSessions(@NonNull RecipientId recipientId) {
|
||||
AppDependencies.getProtocolStore().aci().sessions().archiveSessions(recipientId);
|
||||
AppDependencies.getProtocolStore().pni().sessions().archiveSessions(recipientId);
|
||||
}
|
||||
|
||||
public void sendAcceptedCallEventSyncMessage(@NonNull RemotePeer remotePeer, boolean isOutgoing, boolean isVideoCall) {
|
||||
SignalDatabase
|
||||
.calls()
|
||||
@ -1337,7 +1355,7 @@ public final class SignalCallManager implements CallManager.Observer, GroupCall.
|
||||
try {
|
||||
SyncMessage.CallEvent callEvent = CallEventSyncMessageUtil.createAcceptedSyncMessage(remotePeer, System.currentTimeMillis(), isOutgoing, isVideoCall);
|
||||
AppDependencies.getSignalServiceMessageSender().sendSyncMessage(SignalServiceSyncMessage.forCallEvent(callEvent));
|
||||
} catch (IOException | UntrustedIdentityException e) {
|
||||
} catch (IOException | UntrustedIdentityException | NoSessionException e) {
|
||||
Log.w(TAG, "Unable to send call event sync message for " + remotePeer.getCallId().longValue(), e);
|
||||
}
|
||||
});
|
||||
@ -1354,7 +1372,7 @@ public final class SignalCallManager implements CallManager.Observer, GroupCall.
|
||||
try {
|
||||
SyncMessage.CallEvent callEvent = CallEventSyncMessageUtil.createNotAcceptedSyncMessage(remotePeer, System.currentTimeMillis(), isOutgoing, isVideoCall);
|
||||
AppDependencies.getSignalServiceMessageSender().sendSyncMessage(SignalServiceSyncMessage.forCallEvent(callEvent));
|
||||
} catch (IOException | UntrustedIdentityException e) {
|
||||
} catch (IOException | UntrustedIdentityException | NoSessionException e) {
|
||||
Log.w(TAG, "Unable to send call event sync message for " + remotePeer.getCallId().longValue(), e);
|
||||
}
|
||||
});
|
||||
@ -1367,7 +1385,7 @@ public final class SignalCallManager implements CallManager.Observer, GroupCall.
|
||||
try {
|
||||
SyncMessage.CallEvent callEvent = CallEventSyncMessageUtil.createNotAcceptedSyncMessage(remotePeer, System.currentTimeMillis(), isOutgoing, true);
|
||||
AppDependencies.getSignalServiceMessageSender().sendSyncMessage(SignalServiceSyncMessage.forCallEvent(callEvent));
|
||||
} catch (IOException | UntrustedIdentityException e) {
|
||||
} catch (IOException | UntrustedIdentityException | NoSessionException e) {
|
||||
Log.w(TAG, "Unable to send call event sync message for " + remotePeer.getCallId().longValue(), e);
|
||||
}
|
||||
});
|
||||
|
||||
@ -27,7 +27,7 @@ androidx-navigation3-core = "1.0.0"
|
||||
androidx-core-telecom = "1.1.0-alpha04"
|
||||
androidx-window = "1.3.0"
|
||||
glide = "4.15.1"
|
||||
libsignal-client = "0.94.5"
|
||||
libsignal-client = "0.96.2"
|
||||
mp4parser = "1.9.39"
|
||||
accompanist = "0.28.0"
|
||||
nanohttpd = "2.3.1"
|
||||
|
||||
@ -21596,20 +21596,20 @@ https://docs.gradle.org/current/userguide/dependency_verification.html
|
||||
<sha256 value="57b3cf8f247f1990211110734a7d1af413db145c8f17eb1b2cdc9b9321188c2b" origin="Generated by Gradle"/>
|
||||
</artifact>
|
||||
</component>
|
||||
<component group="org.signal" name="libsignal-android" version="0.94.5">
|
||||
<artifact name="libsignal-android-0.94.5.aar">
|
||||
<sha256 value="ec333b33aa9acc58d5e6dd9b0492497d4ceb978cd99658b9147be64cca2c61dd" origin="Generated by Gradle"/>
|
||||
<component group="org.signal" name="libsignal-android" version="0.96.2">
|
||||
<artifact name="libsignal-android-0.96.2.aar">
|
||||
<sha256 value="ea4d9e881537325ea9b8ed222664e5c47514f3c0d5ffe8ec7f4d43fda56a352c" origin="Generated by Gradle"/>
|
||||
</artifact>
|
||||
<artifact name="libsignal-android-0.94.5.module">
|
||||
<sha256 value="a2880e5eb149d57b383bd0a00d98b187370b9b61a6857326578a3f4b661fbf17" origin="Generated by Gradle"/>
|
||||
<artifact name="libsignal-android-0.96.2.module">
|
||||
<sha256 value="45cab6585d6acc231b81b53628dc5097118eddc50c75b2955c42d4ed8f0edb97" origin="Generated by Gradle"/>
|
||||
</artifact>
|
||||
</component>
|
||||
<component group="org.signal" name="libsignal-client" version="0.94.5">
|
||||
<artifact name="libsignal-client-0.94.5.jar">
|
||||
<sha256 value="33fcf541fe94dcf770f4934552e87e7280bf2d2c22b372159ee1d80accfdb09b" origin="Generated by Gradle"/>
|
||||
<component group="org.signal" name="libsignal-client" version="0.96.2">
|
||||
<artifact name="libsignal-client-0.96.2.jar">
|
||||
<sha256 value="0e3cb1c5a5cdd7d8fe696de7d82ad42785a9fef51b014c6bedd2f9ce0d5471af" origin="Generated by Gradle"/>
|
||||
</artifact>
|
||||
<artifact name="libsignal-client-0.94.5.module">
|
||||
<sha256 value="752f2d2ec20d7f56eb4503a58ce6786bdfd946dce7557134900855b042957c3e" origin="Generated by Gradle"/>
|
||||
<artifact name="libsignal-client-0.96.2.module">
|
||||
<sha256 value="d6742b8d7f365639abe694773fc154dee4868b0fb0b202fa2dbfbeb9b8985e6f" origin="Generated by Gradle"/>
|
||||
</artifact>
|
||||
</component>
|
||||
<component group="org.signal" name="ringrtc-android" version="2.69.3">
|
||||
|
||||
@ -5,13 +5,14 @@
|
||||
*/
|
||||
package org.whispersystems.signalservice.api;
|
||||
|
||||
import org.signal.network.NetworkResult;
|
||||
|
||||
import org.signal.core.models.ServiceId;
|
||||
import org.signal.core.models.ServiceId.PNI;
|
||||
import org.signal.core.util.Base64;
|
||||
import org.signal.core.util.ProtoUtil;
|
||||
import org.signal.core.util.Uint64RangeException;
|
||||
import org.signal.core.util.Uint64Util;
|
||||
import org.signal.core.util.UuidUtil;
|
||||
import org.signal.core.util.logging.Log;
|
||||
import org.signal.libsignal.metadata.certificate.SenderCertificate;
|
||||
import org.signal.libsignal.net.MismatchedDeviceException;
|
||||
import org.signal.libsignal.net.MultiRecipientMessageResponse;
|
||||
@ -28,13 +29,16 @@ import org.signal.libsignal.protocol.NoSessionException;
|
||||
import org.signal.libsignal.protocol.SessionBuilder;
|
||||
import org.signal.libsignal.protocol.SignalProtocolAddress;
|
||||
import org.signal.libsignal.protocol.groups.GroupSessionBuilder;
|
||||
import org.signal.core.util.logging.Log;
|
||||
import org.signal.libsignal.protocol.message.DecryptionErrorMessage;
|
||||
import org.signal.libsignal.protocol.message.PlaintextContent;
|
||||
import org.signal.libsignal.protocol.message.SenderKeyDistributionMessage;
|
||||
import org.signal.libsignal.protocol.state.PreKeyBundle;
|
||||
import org.signal.libsignal.protocol.state.SessionRecord;
|
||||
import org.signal.libsignal.zkgroup.groupsend.GroupSendFullToken;
|
||||
import org.signal.network.NetworkResult;
|
||||
import org.signal.network.exceptions.NonSuccessfulResponseCodeException;
|
||||
import org.signal.network.exceptions.PushNetworkException;
|
||||
import org.signal.network.util.Preconditions;
|
||||
import org.whispersystems.signalservice.api.crypto.AttachmentCipherStreamUtil;
|
||||
import org.whispersystems.signalservice.api.crypto.ContentHint;
|
||||
import org.whispersystems.signalservice.api.crypto.EnvelopeContent;
|
||||
@ -84,9 +88,7 @@ import org.whispersystems.signalservice.api.messages.shared.SharedContact;
|
||||
import org.whispersystems.signalservice.api.push.DistributionId;
|
||||
import org.whispersystems.signalservice.api.push.SignalServiceAddress;
|
||||
import org.whispersystems.signalservice.api.push.exceptions.AuthorizationFailedException;
|
||||
import org.signal.network.exceptions.NonSuccessfulResponseCodeException;
|
||||
import org.whispersystems.signalservice.api.push.exceptions.ProofRequiredException;
|
||||
import org.signal.network.exceptions.PushNetworkException;
|
||||
import org.whispersystems.signalservice.api.push.exceptions.RateLimitException;
|
||||
import org.whispersystems.signalservice.api.push.exceptions.RetryNetworkException;
|
||||
import org.whispersystems.signalservice.api.push.exceptions.ServerRejectedException;
|
||||
@ -94,9 +96,6 @@ import org.whispersystems.signalservice.api.push.exceptions.UnknownGroupSendExce
|
||||
import org.whispersystems.signalservice.api.push.exceptions.UnregisteredUserException;
|
||||
import org.whispersystems.signalservice.api.util.AttachmentPointerUtil;
|
||||
import org.whispersystems.signalservice.api.util.CredentialsProvider;
|
||||
import org.signal.network.util.Preconditions;
|
||||
import org.signal.core.util.Uint64RangeException;
|
||||
import org.signal.core.util.Uint64Util;
|
||||
import org.whispersystems.signalservice.api.websocket.WebSocketUnavailableException;
|
||||
import org.whispersystems.signalservice.internal.crypto.AttachmentDigest;
|
||||
import org.whispersystems.signalservice.internal.crypto.PaddingInputStream;
|
||||
@ -234,7 +233,7 @@ public class SignalServiceMessageSender {
|
||||
@Nullable SealedSenderAccess sealedSenderAccess,
|
||||
SignalServiceReceiptMessage message,
|
||||
boolean includePniSignature)
|
||||
throws IOException, UntrustedIdentityException
|
||||
throws IOException, UntrustedIdentityException, NoSessionException
|
||||
{
|
||||
Log.d(TAG, "[" + message.getWhen() + "] Sending a receipt.");
|
||||
|
||||
@ -258,7 +257,7 @@ public class SignalServiceMessageSender {
|
||||
@Nullable SealedSenderAccess sealedSenderAccess,
|
||||
Optional<byte[]> groupId,
|
||||
DecryptionErrorMessage errorMessage)
|
||||
throws IOException, UntrustedIdentityException
|
||||
throws IOException, UntrustedIdentityException, NoSessionException
|
||||
|
||||
{
|
||||
long timestamp = System.currentTimeMillis();
|
||||
@ -312,7 +311,7 @@ public class SignalServiceMessageSender {
|
||||
long timestamp,
|
||||
boolean isRecipientUpdate,
|
||||
Set<SignalServiceStoryMessageRecipient> manifest)
|
||||
throws IOException, UntrustedIdentityException
|
||||
throws IOException, UntrustedIdentityException, NoSessionException
|
||||
{
|
||||
Log.d(TAG, "[" + timestamp + "] Sending a story sync message.");
|
||||
|
||||
@ -368,7 +367,7 @@ public class SignalServiceMessageSender {
|
||||
public void sendCallMessage(SignalServiceAddress recipient,
|
||||
@Nullable SealedSenderAccess sealedSenderAccess,
|
||||
SignalServiceCallMessage message)
|
||||
throws IOException, UntrustedIdentityException
|
||||
throws IOException, UntrustedIdentityException, NoSessionException
|
||||
{
|
||||
long timestamp = System.currentTimeMillis();
|
||||
Log.d(TAG, "[" + timestamp + "] Sending a call message (single recipient).");
|
||||
@ -429,7 +428,7 @@ public class SignalServiceMessageSender {
|
||||
IndividualSendEvents sendEvents,
|
||||
boolean urgent,
|
||||
boolean includePniSignature)
|
||||
throws UntrustedIdentityException, IOException
|
||||
throws UntrustedIdentityException, IOException, NoSessionException
|
||||
{
|
||||
Log.d(TAG, "[" + message.getTimestamp() + "] Sending a data message.");
|
||||
|
||||
@ -448,7 +447,7 @@ public class SignalServiceMessageSender {
|
||||
IndividualSendEvents sendEvents,
|
||||
boolean urgent,
|
||||
long targetSentTimestamp)
|
||||
throws UntrustedIdentityException, IOException
|
||||
throws UntrustedIdentityException, IOException, NoSessionException
|
||||
{
|
||||
Log.d(TAG, "[" + message.getTimestamp() + "] Sending an edit message for " + targetSentTimestamp + ".");
|
||||
|
||||
@ -468,7 +467,7 @@ public class SignalServiceMessageSender {
|
||||
boolean urgent,
|
||||
boolean includePniSignature,
|
||||
Content content)
|
||||
throws UntrustedIdentityException, IOException
|
||||
throws UntrustedIdentityException, IOException, NoSessionException
|
||||
{
|
||||
if (includePniSignature) {
|
||||
Log.d(TAG, "[" + message.getTimestamp() + "] Including PNI signature.");
|
||||
@ -537,7 +536,7 @@ public class SignalServiceMessageSender {
|
||||
ContentHint contentHint,
|
||||
Optional<byte[]> groupId,
|
||||
boolean urgent)
|
||||
throws UntrustedIdentityException, IOException
|
||||
throws UntrustedIdentityException, IOException, NoSessionException
|
||||
{
|
||||
Log.d(TAG, "[" + timestamp + "] Resending content.");
|
||||
|
||||
@ -613,7 +612,7 @@ public class SignalServiceMessageSender {
|
||||
PartialSendCompleteListener partialListener,
|
||||
CancelationSignal cancelationSignal,
|
||||
boolean urgent)
|
||||
throws IOException, UntrustedIdentityException
|
||||
throws IOException, UntrustedIdentityException, NoSessionException
|
||||
{
|
||||
Log.d(TAG, "[" + message.getTimestamp() + "] Sending a data message to " + recipients.size() + " recipients.");
|
||||
|
||||
@ -665,7 +664,7 @@ public class SignalServiceMessageSender {
|
||||
CancelationSignal cancelationSignal,
|
||||
boolean urgent,
|
||||
long targetSentTimestamp)
|
||||
throws IOException, UntrustedIdentityException
|
||||
throws IOException, UntrustedIdentityException, NoSessionException
|
||||
{
|
||||
Log.d(TAG, "[" + message.getTimestamp() + "] Sending a edit message to " + recipients.size() + " recipients.");
|
||||
|
||||
@ -702,21 +701,21 @@ public class SignalServiceMessageSender {
|
||||
}
|
||||
|
||||
public SendMessageResult sendSyncMessage(SignalServiceDataMessage dataMessage)
|
||||
throws IOException, UntrustedIdentityException
|
||||
throws IOException, UntrustedIdentityException, NoSessionException
|
||||
{
|
||||
Log.d(TAG, "[" + dataMessage.getTimestamp() + "] Sending self-sync message.");
|
||||
return sendSyncMessage(createSelfSendSyncMessage(dataMessage));
|
||||
}
|
||||
|
||||
public SendMessageResult sendSelfSyncEditMessage(SignalServiceEditMessage editMessage)
|
||||
throws IOException, UntrustedIdentityException
|
||||
throws IOException, UntrustedIdentityException, NoSessionException
|
||||
{
|
||||
Log.d(TAG, "[" + editMessage.getDataMessage().getTimestamp() + "] Sending self-sync edit message for " + editMessage.getTargetSentTimestamp() + ".");
|
||||
return sendSyncMessage(createSelfSendSyncEditMessage(editMessage));
|
||||
}
|
||||
|
||||
public SendMessageResult sendSyncMessage(SignalServiceSyncMessage message)
|
||||
throws IOException, UntrustedIdentityException
|
||||
throws IOException, UntrustedIdentityException, NoSessionException
|
||||
{
|
||||
Content content;
|
||||
boolean urgent = false;
|
||||
@ -779,7 +778,7 @@ public class SignalServiceMessageSender {
|
||||
}
|
||||
|
||||
public @Nonnull SendMessageResult sendSyncMessage(Content content, boolean urgent, Optional<Long> sent)
|
||||
throws IOException, UntrustedIdentityException
|
||||
throws IOException, UntrustedIdentityException, NoSessionException
|
||||
{
|
||||
long timestamp = sent.orElseGet(System::currentTimeMillis);
|
||||
|
||||
@ -797,7 +796,7 @@ public class SignalServiceMessageSender {
|
||||
* @return Encrypted {@link OutgoingPushMessage} to be included in the change number request sent to the server
|
||||
*/
|
||||
public @Nonnull OutgoingPushMessage getEncryptedSyncPniInitializeDeviceMessage(int deviceId, @Nonnull SyncMessage.PniChangeNumber pniChangeNumber)
|
||||
throws UntrustedIdentityException, IOException, InvalidKeyException
|
||||
throws UntrustedIdentityException, IOException, InvalidKeyException, NoSessionException
|
||||
{
|
||||
SyncMessage.Builder syncMessage = createSyncMessageBuilder().pniChangeNumber(pniChangeNumber);
|
||||
Content.Builder content = new Content.Builder().syncMessage(syncMessage.build());
|
||||
@ -856,7 +855,7 @@ public class SignalServiceMessageSender {
|
||||
}
|
||||
|
||||
private SendMessageResult sendVerifiedSyncMessage(VerifiedMessage message)
|
||||
throws IOException, UntrustedIdentityException
|
||||
throws IOException, UntrustedIdentityException, NoSessionException
|
||||
{
|
||||
byte[] nullMessageBody = new DataMessage.Builder()
|
||||
.body(Base64.encodeWithPadding(Util.getRandomLengthSecretBytes(140)))
|
||||
@ -886,7 +885,7 @@ public class SignalServiceMessageSender {
|
||||
}
|
||||
|
||||
public SendMessageResult sendNullMessage(SignalServiceAddress address, @Nullable SealedSenderAccess sealedSenderAccess)
|
||||
throws UntrustedIdentityException, IOException
|
||||
throws UntrustedIdentityException, IOException, NoSessionException
|
||||
{
|
||||
byte[] nullMessageBody = new DataMessage.Builder()
|
||||
.body(Base64.encodeWithPadding(Util.getRandomLengthSecretBytes(140)))
|
||||
@ -1968,7 +1967,7 @@ public class SignalServiceMessageSender {
|
||||
SendEvents sendEvents,
|
||||
boolean urgent,
|
||||
boolean story)
|
||||
throws UntrustedIdentityException, IOException
|
||||
throws UntrustedIdentityException, IOException, NoSessionException
|
||||
{
|
||||
enforceMaxEnvelopeContentSize(content);
|
||||
|
||||
@ -2827,7 +2826,7 @@ public class SignalServiceMessageSender {
|
||||
boolean online,
|
||||
boolean urgent,
|
||||
boolean story)
|
||||
throws IOException, InvalidKeyException, UntrustedIdentityException
|
||||
throws IOException, InvalidKeyException, UntrustedIdentityException, NoSessionException
|
||||
{
|
||||
List<OutgoingPushMessage> messages = new LinkedList<>();
|
||||
List<Integer> subDevices = aciStore.getSubDeviceSessions(recipient.getIdentifier());
|
||||
@ -2858,7 +2857,7 @@ public class SignalServiceMessageSender {
|
||||
int deviceId,
|
||||
EnvelopeContent plaintext,
|
||||
boolean story)
|
||||
throws IOException, InvalidKeyException, UntrustedIdentityException
|
||||
throws IOException, InvalidKeyException, UntrustedIdentityException, NoSessionException
|
||||
{
|
||||
SignalProtocolAddress signalProtocolAddress = new SignalProtocolAddress(recipient.getIdentifier(), deviceId);
|
||||
SignalServiceCipher cipher = new SignalServiceCipher(localAddress, localDeviceId, aciStore, sessionLock, null);
|
||||
|
||||
@ -138,7 +138,7 @@ public interface EnvelopeContent {
|
||||
SignalSealedSessionCipher sealedSessionCipher,
|
||||
SignalProtocolAddress destination,
|
||||
SenderCertificate senderCertificate)
|
||||
throws UntrustedIdentityException, InvalidKeyException
|
||||
throws UntrustedIdentityException, InvalidKeyException, NoSessionException
|
||||
{
|
||||
UnidentifiedSenderMessageContent messageContent = new UnidentifiedSenderMessageContent(plaintextContent,
|
||||
senderCertificate,
|
||||
|
||||
@ -20,12 +20,10 @@ import org.signal.libsignal.protocol.NoSessionException;
|
||||
import org.signal.libsignal.protocol.SignalProtocolAddress;
|
||||
import org.signal.libsignal.protocol.UntrustedIdentityException;
|
||||
import org.signal.libsignal.protocol.state.SessionRecord;
|
||||
import org.signal.libsignal.protocol.state.SignalProtocolStore;
|
||||
import org.whispersystems.signalservice.api.SignalSessionLock;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Objects;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
/**
|
||||
@ -59,7 +57,13 @@ public class SignalSealedSessionCipher {
|
||||
throw new NoSessionException("No session for some recipients");
|
||||
}
|
||||
|
||||
return cipher.multiRecipientEncrypt(recipients, recipientSessions, content);
|
||||
try {
|
||||
return cipher.multiRecipientEncrypt(recipients, recipientSessions, content);
|
||||
} catch (IllegalStateException e) {
|
||||
NoSessionException nse = new NoSessionException(e.getMessage());
|
||||
nse.initCause(e);
|
||||
throw nse;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -69,13 +73,13 @@ public class SignalSealedSessionCipher {
|
||||
}
|
||||
}
|
||||
|
||||
public int getSessionVersion(SignalProtocolAddress remoteAddress) {
|
||||
public int getSessionVersion(SignalProtocolAddress remoteAddress) throws NoSessionException {
|
||||
try (SignalSessionLock.Lock unused = lock.acquire()) {
|
||||
return cipher.getSessionVersion(remoteAddress);
|
||||
}
|
||||
}
|
||||
|
||||
public int getRemoteRegistrationId(SignalProtocolAddress remoteAddress) {
|
||||
public int getRemoteRegistrationId(SignalProtocolAddress remoteAddress) throws NoSessionException {
|
||||
try (SignalSessionLock.Lock unused = lock.acquire()) {
|
||||
return cipher.getRemoteRegistrationId(remoteAddress);
|
||||
}
|
||||
|
||||
@ -6,6 +6,10 @@
|
||||
|
||||
package org.whispersystems.signalservice.api.crypto;
|
||||
|
||||
import org.signal.core.models.ServiceId;
|
||||
import org.signal.core.models.ServiceId.ACI;
|
||||
import org.signal.core.util.UuidUtil;
|
||||
import org.signal.core.util.logging.Log;
|
||||
import org.signal.libsignal.metadata.InvalidMetadataMessageException;
|
||||
import org.signal.libsignal.metadata.InvalidMetadataVersionException;
|
||||
import org.signal.libsignal.metadata.ProtocolDuplicateMessageException;
|
||||
@ -27,7 +31,6 @@ import org.signal.libsignal.protocol.InvalidKeyException;
|
||||
import org.signal.libsignal.protocol.InvalidKeyIdException;
|
||||
import org.signal.libsignal.protocol.InvalidMessageException;
|
||||
import org.signal.libsignal.protocol.InvalidRegistrationIdException;
|
||||
import org.signal.libsignal.protocol.InvalidSessionException;
|
||||
import org.signal.libsignal.protocol.InvalidVersionException;
|
||||
import org.signal.libsignal.protocol.LegacyMessageException;
|
||||
import org.signal.libsignal.protocol.NoSessionException;
|
||||
@ -35,7 +38,6 @@ import org.signal.libsignal.protocol.SessionCipher;
|
||||
import org.signal.libsignal.protocol.SignalProtocolAddress;
|
||||
import org.signal.libsignal.protocol.UntrustedIdentityException;
|
||||
import org.signal.libsignal.protocol.groups.GroupCipher;
|
||||
import org.signal.core.util.logging.Log;
|
||||
import org.signal.libsignal.protocol.message.CiphertextMessage;
|
||||
import org.signal.libsignal.protocol.message.PlaintextContent;
|
||||
import org.signal.libsignal.protocol.message.PreKeySignalMessage;
|
||||
@ -46,10 +48,7 @@ import org.whispersystems.signalservice.api.SignalServiceAccountDataStore;
|
||||
import org.whispersystems.signalservice.api.SignalSessionLock;
|
||||
import org.whispersystems.signalservice.api.messages.SignalServiceMetadata;
|
||||
import org.whispersystems.signalservice.api.push.DistributionId;
|
||||
import org.signal.core.models.ServiceId;
|
||||
import org.signal.core.models.ServiceId.ACI;
|
||||
import org.whispersystems.signalservice.api.push.SignalServiceAddress;
|
||||
import org.signal.core.util.UuidUtil;
|
||||
import org.whispersystems.signalservice.internal.push.Content;
|
||||
import org.whispersystems.signalservice.internal.push.Envelope;
|
||||
import org.whispersystems.signalservice.internal.push.OutgoingPushMessage;
|
||||
@ -115,21 +114,17 @@ public class SignalServiceCipher {
|
||||
public OutgoingPushMessage encrypt(SignalProtocolAddress destination,
|
||||
@Nullable SealedSenderAccess sealedSenderAccess,
|
||||
EnvelopeContent content)
|
||||
throws UntrustedIdentityException, InvalidKeyException
|
||||
throws UntrustedIdentityException, InvalidKeyException, NoSessionException
|
||||
{
|
||||
try {
|
||||
SignalProtocolAddress localProtocolAddress = new SignalProtocolAddress(localAddress.getIdentifier(), localDeviceId);
|
||||
SignalSessionCipher sessionCipher = new SignalSessionCipher(sessionLock, new SessionCipher(signalProtocolStore, localProtocolAddress, destination));
|
||||
if (sealedSenderAccess != null) {
|
||||
SignalSealedSessionCipher sealedSessionCipher = new SignalSealedSessionCipher(sessionLock, new SealedSessionCipher(signalProtocolStore, localAddress.getServiceId().getRawUuid(), localAddress.getNumber()
|
||||
.orElse(null), localDeviceId));
|
||||
SignalProtocolAddress localProtocolAddress = new SignalProtocolAddress(localAddress.getIdentifier(), localDeviceId);
|
||||
SignalSessionCipher sessionCipher = new SignalSessionCipher(sessionLock, new SessionCipher(signalProtocolStore, localProtocolAddress, destination));
|
||||
if (sealedSenderAccess != null) {
|
||||
SignalSealedSessionCipher sealedSessionCipher = new SignalSealedSessionCipher(sessionLock, new SealedSessionCipher(signalProtocolStore, localAddress.getServiceId().getRawUuid(), localAddress.getNumber()
|
||||
.orElse(null), localDeviceId));
|
||||
|
||||
return content.processSealedSender(sessionCipher, sealedSessionCipher, destination, sealedSenderAccess.getSenderCertificate());
|
||||
} else {
|
||||
return content.processUnsealedSender(sessionCipher, destination);
|
||||
}
|
||||
} catch (NoSessionException e) {
|
||||
throw new InvalidSessionException("Session not found: " + destination);
|
||||
return content.processSealedSender(sessionCipher, sealedSessionCipher, destination, sealedSenderAccess.getSenderCertificate());
|
||||
} else {
|
||||
return content.processUnsealedSender(sessionCipher, destination);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -55,7 +55,7 @@ public class SignalSessionCipher {
|
||||
}
|
||||
}
|
||||
|
||||
public int getSessionVersion() {
|
||||
public int getSessionVersion() throws NoSessionException {
|
||||
try (SignalSessionLock.Lock unused = lock.acquire()) {
|
||||
return cipher.getSessionVersion();
|
||||
}
|
||||
|
||||
@ -29,6 +29,7 @@ import org.signal.libsignal.net.UserBasedAuthorization
|
||||
import org.signal.libsignal.net.UserBasedSendAuthorization
|
||||
import org.signal.libsignal.protocol.IdentityKey
|
||||
import org.signal.libsignal.protocol.InvalidKeyException
|
||||
import org.signal.libsignal.protocol.NoSessionException
|
||||
import org.signal.libsignal.protocol.SessionBuilder
|
||||
import org.signal.libsignal.protocol.SignalProtocolAddress
|
||||
import org.signal.libsignal.protocol.UntrustedIdentityException
|
||||
@ -388,6 +389,10 @@ open class MessageService(
|
||||
raise(SendError.IdentityMismatch(serviceId, e))
|
||||
} catch (e: InvalidKeyException) {
|
||||
raise(SendError.ApplicationError(e))
|
||||
} catch (e: NoSessionException) {
|
||||
Log.w(TAG, "Missing or corrupt session for $address. Archiving so the next attempt rebuilds it.", e)
|
||||
protocolStore.archiveSession(address)
|
||||
raise(SendError.ApplicationError(e))
|
||||
}
|
||||
|
||||
private fun OutgoingPushMessage.toUnsealedMessage(): SingleOutboundUnsealedMessage {
|
||||
|
||||
@ -28,6 +28,7 @@ import org.signal.libsignal.net.ServiceIdNotFoundException
|
||||
import org.signal.libsignal.net.UserBasedAuthorization
|
||||
import org.signal.libsignal.net.UserBasedSendAuthorization
|
||||
import org.signal.libsignal.protocol.IdentityKeyPair
|
||||
import org.signal.libsignal.protocol.NoSessionException
|
||||
import org.signal.libsignal.protocol.SessionBuilder
|
||||
import org.signal.libsignal.protocol.SessionCipher
|
||||
import org.signal.libsignal.protocol.SignalProtocolAddress
|
||||
@ -440,6 +441,21 @@ class MessageServiceTest {
|
||||
assertThat(mismatch.exception).isEqualTo(untrusted)
|
||||
}
|
||||
|
||||
@Test
|
||||
fun `NoSessionException during encryption archives the session and surfaces a retryable error`() = runTest {
|
||||
val service = newService()
|
||||
every { protocolStore.getSubDeviceSessions(recipientAci.toString()) } returns emptyList()
|
||||
val noSession = NoSessionException("missing session")
|
||||
every { cipher.encrypt(any(), any(), any()) } throws noSession
|
||||
|
||||
val result = service.sendMessage(recipientAci, envelopeContent, timestamp, sealedSenderAccess = null, story = true, isOnline = false)
|
||||
|
||||
verify { protocolStore.archiveSession(SignalProtocolAddress(recipientAci.libSignalServiceId, SignalServiceAddress.DEFAULT_DEVICE_ID)) }
|
||||
val app = (result as Either.Left).value as MessageService.SendError.ApplicationError
|
||||
assertThat(app.exception).isEqualTo(noSession)
|
||||
coVerify(exactly = 0) { messageApi.sendSealedSenderMessage(any(), any(), any(), any(), any(), any()) }
|
||||
}
|
||||
|
||||
@Test
|
||||
fun `content larger than max returns ContentTooLarge before encryption`() = runTest {
|
||||
val largeContent: EnvelopeContent = mockk {
|
||||
|
||||
Loading…
Reference in New Issue
Block a user