Skip to content

Commit 3574875

Browse files
committed
Fix race in creating calls
Second attempt, just put a mutex around the method that processes member state events. Also more logging. Supersedes #2662
1 parent 3e1e99f commit 3574875

File tree

1 file changed

+33
-4
lines changed

1 file changed

+33
-4
lines changed

src/webrtc/groupCall.ts

Lines changed: 33 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -185,6 +185,9 @@ export class GroupCall extends TypedEventEmitter<
185185
private resendMemberStateTimer: ReturnType<typeof setInterval> | null = null;
186186
private initWithAudioMuted = false;
187187
private initWithVideoMuted = false;
188+
// We use this as a set of mutexes, effectively, to make sure we only enter the function
189+
// to process a member state event once at any one time for each member
190+
private processingMemberStateEvent = new Map<string, boolean>();
188191

189192
constructor(
190193
private client: MatrixClient,
@@ -201,7 +204,8 @@ export class GroupCall extends TypedEventEmitter<
201204
this.groupCallId = groupCallId || genCallID();
202205

203206
for (const stateEvent of this.getMemberStateEvents()) {
204-
this.onMemberStateChanged(stateEvent);
207+
logger.debug("Processing member states on group call initialisation");
208+
this.processMemberStateEvent(stateEvent);
205209
}
206210
}
207211

@@ -332,7 +336,8 @@ export class GroupCall extends TypedEventEmitter<
332336
// Set up participants for the members currently in the room.
333337
// Other members will be picked up by the RoomState.members event.
334338
for (const stateEvent of this.getMemberStateEvents()) {
335-
this.onMemberStateChanged(stateEvent);
339+
logger.debug("Processing member states on call enter");
340+
this.processMemberStateEvent(stateEvent);
336341
}
337342

338343
this.retryCallLoopTimeout = setTimeout(this.onRetryCallLoop, this.retryCallInterval);
@@ -754,6 +759,25 @@ export class GroupCall extends TypedEventEmitter<
754759
}
755760

756761
public onMemberStateChanged = async (event: MatrixEvent) => {
762+
logger.debug("Processing member states on member state change");
763+
return this.processMemberStateEvent(event);
764+
};
765+
766+
private processMemberStateEvent = async (event: MatrixEvent) => {
767+
if (this.processingMemberStateEvent.has(event.getStateKey())) {
768+
logger.debug(`Already processing meber state event for ${event.getStateKey()}`);
769+
return;
770+
}
771+
772+
this.processingMemberStateEvent.set(event.getStateKey(), true);
773+
try {
774+
return this.processMemberStateEventInternal(event);
775+
} finally {
776+
this.processingMemberStateEvent.delete(event.getStateKey());
777+
}
778+
};
779+
780+
private processMemberStateEventInternal = async (event: MatrixEvent) => {
757781
// If we haven't entered the call yet, we don't care
758782
if (this.state !== GroupCallState.Entered) {
759783
return;
@@ -861,7 +885,9 @@ export class GroupCall extends TypedEventEmitter<
861885
const requestScreenshareFeed = opponentDevice.feeds.some(
862886
(feed) => feed.purpose === SDPStreamMetadataPurpose.Screenshare);
863887

864-
logger.log(`Placing call to ${member.userId}.`);
888+
logger.debug(
889+
`Placing call to ${member.userId}/${opponentDevice.device_id} session ID ${opponentDevice.session_id}.`,
890+
);
865891

866892
try {
867893
await newCall.placeCallWithCallFeeds(
@@ -889,8 +915,10 @@ export class GroupCall extends TypedEventEmitter<
889915
}
890916

891917
if (existingCall) {
918+
logger.debug(`Replacing call ${existingCall.callId} to ${member.userId} with ${newCall.callId}`);
892919
this.replaceCall(existingCall, newCall, CallErrorCode.NewSession);
893920
} else {
921+
logger.debug(`Adding call ${newCall.callId} to ${member.userId}`);
894922
this.addCall(newCall);
895923
}
896924
};
@@ -928,7 +956,8 @@ export class GroupCall extends TypedEventEmitter<
928956

929957
if (!existingCall && retryCallCount < 3) {
930958
this.retryCallCounts.set(memberId, retryCallCount + 1);
931-
this.onMemberStateChanged(event);
959+
logger.debug("Processing member states on call retry");
960+
this.processMemberStateEvent(event);
932961
}
933962
}
934963

0 commit comments

Comments
 (0)