// Copyright 2020 Signal Messenger, LLC // SPDX-License-Identifier: AGPL-3.0-only import { PublicKey, Fingerprint } from '@signalapp/libsignal-client'; import type { ConversationType } from '../state/ducks/conversations'; import { UUID } from '../types/UUID'; import { assertDev } from './assert'; import * as log from '../logging/log'; export async function generateSecurityNumber( ourNumber: string, ourKey: Uint8Array, theirNumber: string, theirKey: Uint8Array ): Promise { const ourNumberBuf = Buffer.from(ourNumber); const ourKeyObj = PublicKey.deserialize(Buffer.from(ourKey)); const theirNumberBuf = Buffer.from(theirNumber); const theirKeyObj = PublicKey.deserialize(Buffer.from(theirKey)); const fingerprint = Fingerprint.new( 5200, 2, ourNumberBuf, ourKeyObj, theirNumberBuf, theirKeyObj ); const fingerprintString = fingerprint.displayableFingerprint().toString(); return Promise.resolve(fingerprintString); } export async function generateSecurityNumberBlock( contact: ConversationType ): Promise> { const { storage } = window.textsecure; const ourNumber = storage.user.getNumber(); const ourUuid = storage.user.getCheckedUuid(); const us = storage.protocol.getIdentityRecord(ourUuid); const ourKey = us ? us.publicKey : null; const theirUuid = UUID.lookup(contact.id); const them = theirUuid ? await storage.protocol.getOrMigrateIdentityRecord(theirUuid) : undefined; const theirKey = them?.publicKey; if (!ourKey) { throw new Error('Could not load our key'); } if (!theirKey) { throw new Error('Could not load their key'); } if (!contact.e164) { log.error( 'generateSecurityNumberBlock: Attempted to generate security number for contact with no e164' ); return []; } assertDev(ourNumber, 'Should have our number'); const securityNumber = await generateSecurityNumber( ourNumber, ourKey, contact.e164, theirKey ); const chunks = []; for (let i = 0; i < securityNumber.length; i += 5) { chunks.push(securityNumber.substring(i, i + 5)); } return chunks; }