mirror of
https://github.com/oxen-io/session-desktop.git
synced 2023-12-14 02:12:57 +01:00
Merge pull request #1337 from Bilb/fix-ssk
This commit is contained in:
commit
1545256cbe
10 changed files with 41 additions and 30 deletions
|
@ -11,5 +11,5 @@ module.exports = {
|
||||||
|
|
||||||
ENCRYPTED_MESSAGE_OVERHEAD: 53,
|
ENCRYPTED_MESSAGE_OVERHEAD: 53,
|
||||||
|
|
||||||
LOKI_FRIEND_REQUEST: 101,
|
FALLBACK_MESSAGE: 101,
|
||||||
};
|
};
|
||||||
|
|
|
@ -199,8 +199,8 @@ function _createUnidentifiedSenderMessageContentFromBuffer(serialized) {
|
||||||
case TypeEnum.PREKEY_MESSAGE:
|
case TypeEnum.PREKEY_MESSAGE:
|
||||||
type = CiphertextMessage.PREKEY_TYPE;
|
type = CiphertextMessage.PREKEY_TYPE;
|
||||||
break;
|
break;
|
||||||
case TypeEnum.LOKI_FRIEND_REQUEST:
|
case TypeEnum.FALLBACK_MESSAGE:
|
||||||
type = CiphertextMessage.LOKI_FRIEND_REQUEST;
|
type = CiphertextMessage.FALLBACK_MESSAGE;
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
throw new Error(`Unknown type: ${message.type}`);
|
throw new Error(`Unknown type: ${message.type}`);
|
||||||
|
@ -226,8 +226,8 @@ function _getProtoMessageType(type) {
|
||||||
return TypeEnum.MESSAGE;
|
return TypeEnum.MESSAGE;
|
||||||
case CiphertextMessage.PREKEY_TYPE:
|
case CiphertextMessage.PREKEY_TYPE:
|
||||||
return TypeEnum.PREKEY_MESSAGE;
|
return TypeEnum.PREKEY_MESSAGE;
|
||||||
case CiphertextMessage.LOKI_FRIEND_REQUEST:
|
case CiphertextMessage.FALLBACK_MESSAGE:
|
||||||
return TypeEnum.LOKI_FRIEND_REQUEST;
|
return TypeEnum.FALLBACK_MESSAGE;
|
||||||
default:
|
default:
|
||||||
throw new Error(`_getProtoMessageType: type '${type}' does not exist`);
|
throw new Error(`_getProtoMessageType: type '${type}' does not exist`);
|
||||||
}
|
}
|
||||||
|
@ -481,7 +481,7 @@ SecretSessionCipher.prototype = {
|
||||||
signalProtocolStore,
|
signalProtocolStore,
|
||||||
sender
|
sender
|
||||||
).decryptPreKeyWhisperMessage(message.content);
|
).decryptPreKeyWhisperMessage(message.content);
|
||||||
case CiphertextMessage.LOKI_FRIEND_REQUEST:
|
case CiphertextMessage.FALLBACK_MESSAGE:
|
||||||
return new libloki.crypto.FallBackSessionCipher(sender).decrypt(
|
return new libloki.crypto.FallBackSessionCipher(sender).decrypt(
|
||||||
message.content
|
message.content
|
||||||
);
|
);
|
||||||
|
|
|
@ -42,7 +42,7 @@ message Content {
|
||||||
|
|
||||||
message MediumGroupCiphertext {
|
message MediumGroupCiphertext {
|
||||||
optional bytes ciphertext = 1;
|
optional bytes ciphertext = 1;
|
||||||
optional string source = 2;
|
optional bytes source = 2;
|
||||||
optional uint32 keyIdx = 3;
|
optional uint32 keyIdx = 3;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -25,7 +25,7 @@ message UnidentifiedSenderMessage {
|
||||||
enum Type {
|
enum Type {
|
||||||
PREKEY_MESSAGE = 1;
|
PREKEY_MESSAGE = 1;
|
||||||
MESSAGE = 2;
|
MESSAGE = 2;
|
||||||
LOKI_FRIEND_REQUEST = 3;
|
FALLBACK_MESSAGE = 3;
|
||||||
}
|
}
|
||||||
|
|
||||||
optional Type type = 1;
|
optional Type type = 1;
|
||||||
|
|
|
@ -18,6 +18,7 @@ import ByteBuffer from 'bytebuffer';
|
||||||
import { BlockedNumberController } from '../util/blockedNumberController';
|
import { BlockedNumberController } from '../util/blockedNumberController';
|
||||||
import { decryptWithSenderKey } from '../session/medium_group/ratchet';
|
import { decryptWithSenderKey } from '../session/medium_group/ratchet';
|
||||||
import { StringUtils } from '../session/utils';
|
import { StringUtils } from '../session/utils';
|
||||||
|
import { UserUtil } from '../util';
|
||||||
|
|
||||||
export async function handleContentMessage(envelope: EnvelopePlus) {
|
export async function handleContentMessage(envelope: EnvelopePlus) {
|
||||||
const plaintext = await decrypt(envelope, envelope.content);
|
const plaintext = await decrypt(envelope, envelope.content);
|
||||||
|
@ -46,8 +47,6 @@ async function decryptForMediumGroup(
|
||||||
throw new Error(`Secret key is empty for group ${groupId}!`);
|
throw new Error(`Secret key is empty for group ${groupId}!`);
|
||||||
}
|
}
|
||||||
|
|
||||||
const { senderIdentity } = envelope;
|
|
||||||
|
|
||||||
const {
|
const {
|
||||||
ciphertext: outerCiphertext,
|
ciphertext: outerCiphertext,
|
||||||
ephemeralKey,
|
ephemeralKey,
|
||||||
|
@ -64,15 +63,27 @@ async function decryptForMediumGroup(
|
||||||
outerCiphertext
|
outerCiphertext
|
||||||
);
|
);
|
||||||
|
|
||||||
const { ciphertext, keyIdx } = SignalService.MediumGroupCiphertext.decode(
|
const {
|
||||||
|
source,
|
||||||
|
ciphertext,
|
||||||
|
keyIdx,
|
||||||
|
} = SignalService.MediumGroupCiphertext.decode(
|
||||||
new Uint8Array(mediumGroupCiphertext)
|
new Uint8Array(mediumGroupCiphertext)
|
||||||
);
|
);
|
||||||
|
const ourNumber = (await UserUtil.getCurrentDevicePubKey()) as string;
|
||||||
|
const sourceAsStr = StringUtils.decode(source, 'hex');
|
||||||
|
if (sourceAsStr === ourNumber) {
|
||||||
|
window.console.info(
|
||||||
|
'Dropping message from ourself after decryptForMediumGroup'
|
||||||
|
);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
const plaintext = await decryptWithSenderKey(
|
const plaintext = await decryptWithSenderKey(
|
||||||
ciphertext,
|
ciphertext,
|
||||||
keyIdx,
|
keyIdx,
|
||||||
groupId,
|
groupId,
|
||||||
senderIdentity
|
sourceAsStr
|
||||||
);
|
);
|
||||||
|
|
||||||
return plaintext;
|
return plaintext;
|
||||||
|
|
|
@ -4,6 +4,7 @@ import { UserUtil } from '../../util';
|
||||||
import { CipherTextObject } from '../../../libtextsecure/libsignal-protocol';
|
import { CipherTextObject } from '../../../libtextsecure/libsignal-protocol';
|
||||||
import { encryptWithSenderKey } from '../../session/medium_group/ratchet';
|
import { encryptWithSenderKey } from '../../session/medium_group/ratchet';
|
||||||
import { PubKey } from '../types';
|
import { PubKey } from '../types';
|
||||||
|
import { StringUtils } from '../utils';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Add padding to a message buffer
|
* Add padding to a message buffer
|
||||||
|
@ -90,7 +91,7 @@ export async function encryptForMediumGroup(
|
||||||
// We should include ciphertext idx in the message
|
// We should include ciphertext idx in the message
|
||||||
const content = SignalService.MediumGroupCiphertext.encode({
|
const content = SignalService.MediumGroupCiphertext.encode({
|
||||||
ciphertext,
|
ciphertext,
|
||||||
source: ourKey,
|
source: new Uint8Array(StringUtils.encode(ourKey, 'hex')),
|
||||||
keyIdx,
|
keyIdx,
|
||||||
}).finish();
|
}).finish();
|
||||||
|
|
||||||
|
|
|
@ -1,7 +1,6 @@
|
||||||
import { SignalService } from '../../../../../../protobuf';
|
|
||||||
import { ChatMessage } from '../ChatMessage';
|
import { ChatMessage } from '../ChatMessage';
|
||||||
import { PubKey } from '../../../../../types';
|
import { PubKey } from '../../../../../types';
|
||||||
import { MediumGroupMessage } from './MediumGroupMessage';
|
import { ClosedGroupChatMessage } from '../group/ClosedGroupChatMessage';
|
||||||
|
|
||||||
interface MediumGroupChatMessageParams {
|
interface MediumGroupChatMessageParams {
|
||||||
identifier?: string;
|
identifier?: string;
|
||||||
|
@ -9,21 +8,12 @@ interface MediumGroupChatMessageParams {
|
||||||
chatMessage: ChatMessage;
|
chatMessage: ChatMessage;
|
||||||
}
|
}
|
||||||
|
|
||||||
export class MediumGroupChatMessage extends MediumGroupMessage {
|
export class MediumGroupChatMessage extends ClosedGroupChatMessage {
|
||||||
private readonly chatMessage: ChatMessage;
|
|
||||||
|
|
||||||
constructor(params: MediumGroupChatMessageParams) {
|
constructor(params: MediumGroupChatMessageParams) {
|
||||||
super({
|
super({
|
||||||
timestamp: params.chatMessage.timestamp,
|
|
||||||
identifier: params.identifier ?? params.chatMessage.identifier,
|
identifier: params.identifier ?? params.chatMessage.identifier,
|
||||||
groupId: params.groupId,
|
groupId: params.groupId,
|
||||||
|
chatMessage: params.chatMessage,
|
||||||
});
|
});
|
||||||
this.chatMessage = params.chatMessage;
|
|
||||||
}
|
|
||||||
|
|
||||||
public dataProto(): SignalService.DataMessage {
|
|
||||||
const messageProto = this.chatMessage.dataProto();
|
|
||||||
|
|
||||||
return messageProto;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -39,7 +39,12 @@ export async function send(
|
||||||
plainTextBuffer,
|
plainTextBuffer,
|
||||||
encryption
|
encryption
|
||||||
);
|
);
|
||||||
const envelope = await buildEnvelope(envelopeType, timestamp, cipherText);
|
const envelope = await buildEnvelope(
|
||||||
|
envelopeType,
|
||||||
|
device.key,
|
||||||
|
timestamp,
|
||||||
|
cipherText
|
||||||
|
);
|
||||||
const data = wrapEnvelope(envelope);
|
const data = wrapEnvelope(envelope);
|
||||||
|
|
||||||
return pRetry(
|
return pRetry(
|
||||||
|
@ -54,11 +59,15 @@ export async function send(
|
||||||
|
|
||||||
async function buildEnvelope(
|
async function buildEnvelope(
|
||||||
type: SignalService.Envelope.Type,
|
type: SignalService.Envelope.Type,
|
||||||
|
sskSource: string | undefined,
|
||||||
timestamp: number,
|
timestamp: number,
|
||||||
content: Uint8Array
|
content: Uint8Array
|
||||||
): Promise<SignalService.Envelope> {
|
): Promise<SignalService.Envelope> {
|
||||||
let source: string | undefined;
|
let source: string | undefined;
|
||||||
if (type !== SignalService.Envelope.Type.UNIDENTIFIED_SENDER) {
|
|
||||||
|
if (type === SignalService.Envelope.Type.MEDIUM_GROUP_CIPHERTEXT) {
|
||||||
|
source = sskSource;
|
||||||
|
} else if (type !== SignalService.Envelope.Type.UNIDENTIFIED_SENDER) {
|
||||||
source = await UserUtil.getCurrentDevicePubKey();
|
source = await UserUtil.getCurrentDevicePubKey();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -12,7 +12,7 @@ import * as Ratchet from '../../../../session/medium_group/ratchet';
|
||||||
// tslint:disable-next-line: max-func-body-length
|
// tslint:disable-next-line: max-func-body-length
|
||||||
describe('MessageEncrypter', () => {
|
describe('MessageEncrypter', () => {
|
||||||
const sandbox = sinon.createSandbox();
|
const sandbox = sinon.createSandbox();
|
||||||
const ourNumber = 'ourNumber';
|
const ourNumber = '0123456789abcdef';
|
||||||
|
|
||||||
beforeEach(() => {
|
beforeEach(() => {
|
||||||
TestUtils.stubWindow('libsignal', {
|
TestUtils.stubWindow('libsignal', {
|
||||||
|
|
|
@ -36,7 +36,7 @@ describe('MessageSender', () => {
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('send', () => {
|
describe('send', () => {
|
||||||
const ourNumber = 'ourNumber';
|
const ourNumber = '0123456789abcdef';
|
||||||
let lokiMessageAPISendStub: sinon.SinonStub<
|
let lokiMessageAPISendStub: sinon.SinonStub<
|
||||||
[string, Uint8Array, number, number],
|
[string, Uint8Array, number, number],
|
||||||
Promise<void>
|
Promise<void>
|
||||||
|
|
Loading…
Reference in a new issue