add safeguards to ringtone playing twice

This commit is contained in:
Daniel Gultsch 2024-03-25 08:50:44 +01:00
parent e7edc2ce82
commit 21732237d4
No known key found for this signature in database
GPG key ID: F43D18AD2A0982C2
3 changed files with 17 additions and 4 deletions

View file

@ -502,11 +502,9 @@ public class NotificationService {
public synchronized void startRinging( public synchronized void startRinging(
final AbstractJingleConnection.Id id, final Set<Media> media) { final AbstractJingleConnection.Id id, final Set<Media> media) {
showIncomingCallNotification(id, media); showIncomingCallNotification(id, media);
final NotificationManager notificationManager = final NotificationManager notificationManager = mXmppConnectionService.getSystemService(NotificationManager.class);
(NotificationManager)
mXmppConnectionService.getSystemService(Context.NOTIFICATION_SERVICE);
final int currentInterruptionFilter; final int currentInterruptionFilter;
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M && notificationManager != null) { if (notificationManager != null) {
currentInterruptionFilter = notificationManager.getCurrentInterruptionFilter(); currentInterruptionFilter = notificationManager.getCurrentInterruptionFilter();
} else { } else {
currentInterruptionFilter = 1; // INTERRUPTION_FILTER_ALL currentInterruptionFilter = 1; // INTERRUPTION_FILTER_ALL
@ -525,6 +523,10 @@ public class NotificationService {
if (currentVibrationFuture != null) { if (currentVibrationFuture != null) {
currentVibrationFuture.cancel(true); currentVibrationFuture.cancel(true);
} }
final var preexistingRingtone = this.currentlyPlayingRingtone;
if (preexistingRingtone != null) {
preexistingRingtone.stop();
}
final SharedPreferences preferences = final SharedPreferences preferences =
PreferenceManager.getDefaultSharedPreferences(mXmppConnectionService); PreferenceManager.getDefaultSharedPreferences(mXmppConnectionService);
final Resources resources = mXmppConnectionService.getResources(); final Resources resources = mXmppConnectionService.getResources();

View file

@ -504,6 +504,7 @@ public class JingleConnectionManager extends AbstractConnectionManager {
final RtpSessionProposal proposal = final RtpSessionProposal proposal =
getRtpSessionProposal(account, from.asBareJid(), sessionId); getRtpSessionProposal(account, from.asBareJid(), sessionId);
synchronized (rtpSessionProposals) { synchronized (rtpSessionProposals) {
// TODO remove the remove()!= null check to ensure we always call busy()
if (proposal != null && rtpSessionProposals.remove(proposal) != null) { if (proposal != null && rtpSessionProposals.remove(proposal) != null) {
proposal.callIntegration.busy(); proposal.callIntegration.busy();
writeLogMissedOutgoing( writeLogMissedOutgoing(
@ -763,6 +764,7 @@ public class JingleConnectionManager extends AbstractConnectionManager {
final RtpSessionProposal proposal = final RtpSessionProposal proposal =
RtpSessionProposal.of(account, with.asBareJid(), media, callIntegration); RtpSessionProposal.of(account, with.asBareJid(), media, callIntegration);
callIntegration.setCallback(new ProposalStateCallback(proposal)); callIntegration.setCallback(new ProposalStateCallback(proposal));
// TODO ensure that there is no previous proposal?!
this.rtpSessionProposals.put(proposal, DeviceDiscoveryState.SEARCHING); this.rtpSessionProposals.put(proposal, DeviceDiscoveryState.SEARCHING);
mXmppConnectionService.notifyJingleRtpConnectionUpdate( mXmppConnectionService.notifyJingleRtpConnectionUpdate(
account, proposal.with, proposal.sessionId, RtpEndUserState.FINDING_DEVICE); account, proposal.with, proposal.sessionId, RtpEndUserState.FINDING_DEVICE);

View file

@ -2691,6 +2691,15 @@ public class JingleRtpConnection extends AbstractJingleConnection
@Override @Override
public void onCallIntegrationShowIncomingCallUi() { public void onCallIntegrationShowIncomingCallUi() {
if (isTerminated()) {
// there might be race conditions with the call integration service invoking this
// callback when the rtp session has already ended. It should be enough to just return
// instead of throwing an exception. however throwing an exception gives us a sense of
// if and how frequently this happens
throw new IllegalStateException(
"CallIntegration requested incoming call UI but session was already terminated");
}
// TODO apparently this can be called too early as well?
xmppConnectionService.getNotificationService().startRinging(id, getMedia()); xmppConnectionService.getNotificationService().startRinging(id, getMedia());
} }