From e87a0103cc90ffd8cc270a4acdf36c9b95d3b87f Mon Sep 17 00:00:00 2001 From: Jim Gustafson Date: Thu, 25 Jun 2020 14:42:32 -0700 Subject: [PATCH] Use message age to expire old incoming calls --- ts/services/calling.ts | 6 +----- ts/textsecure.d.ts | 1 + ts/textsecure/MessageReceiver.ts | 33 ++++++++++++++++++++++++++++++++ 3 files changed, 35 insertions(+), 5 deletions(-) diff --git a/ts/services/calling.ts b/ts/services/calling.ts index b5f1ff3c6fba..0c674c612714 100644 --- a/ts/services/calling.ts +++ b/ts/services/calling.ts @@ -165,11 +165,7 @@ export class CallingClass { return; } - const now = new Date(); - const serverTimestamp = envelope.serverTimestamp - ? envelope.serverTimestamp - : now.valueOf(); - const messageAgeSec = Math.floor((now.valueOf() - serverTimestamp) / 1000); + const messageAgeSec = envelope.messageAgeSec ? envelope.messageAgeSec : 0; RingRTC.handleCallingMessage( remoteUserId, diff --git a/ts/textsecure.d.ts b/ts/textsecure.d.ts index 0a9876b8160a..fc44d06765b4 100644 --- a/ts/textsecure.d.ts +++ b/ts/textsecure.d.ts @@ -372,6 +372,7 @@ export declare class EnvelopeClass { // Note: these additional properties are added in the course of processing id: string; unidentifiedDeliveryReceived?: boolean; + messageAgeSec?: number; } // Note: we need to use namespaces to express nested classes in Typescript diff --git a/ts/textsecure/MessageReceiver.ts b/ts/textsecure/MessageReceiver.ts index 88d2cb97db4d..2a1aff9b5165 100644 --- a/ts/textsecure/MessageReceiver.ts +++ b/ts/textsecure/MessageReceiver.ts @@ -369,6 +369,12 @@ class MessageReceiverInner extends EventTarget { ? envelope.serverTimestamp.toNumber() : null; + // Calculate the message age (time on server). + envelope.messageAgeSec = this.calculateMessageAge( + headers, + envelope.serverTimestamp + ); + this.cacheAndQueue(envelope, plaintext, request); } catch (e) { request.respond(500, 'Bad encrypted websocket message'); @@ -385,6 +391,33 @@ class MessageReceiverInner extends EventTarget { // tslint:disable-next-line no-floating-promises this.incomingQueue.add(job); } + calculateMessageAge( + headers: Array, + serverTimestamp?: number + ): number { + let messageAgeSec = 0; // Default to 0 in case of unreliable parameters. + + if (serverTimestamp) { + // The 'X-Signal-Timestamp' is usually the last item, so start there. + let it = headers.length; + while (--it >= 0) { + const match = headers[it].match(/^X-Signal-Timestamp:\s*(\d+)\s*$/); + if (match && match.length === 2) { + const timestamp = Number(match[1]); + + // One final sanity check, the timestamp when a message is pulled from + // the server should be later than when it was pushed. + if (timestamp > serverTimestamp) { + messageAgeSec = Math.floor((timestamp - serverTimestamp) / 1000); + } + + break; + } + } + } + + return messageAgeSec; + } async addToQueue(task: () => Promise) { this.count += 1;