summaryrefslogtreecommitdiff
path: root/indra
diff options
context:
space:
mode:
authorRoxie Linden <roxie@lindenlab.com>2024-05-16 12:00:45 -0700
committerRoxie Linden <roxie@lindenlab.com>2024-05-16 12:00:45 -0700
commitc6e147ff224e1adc9a498d4a06ad54fff710d704 (patch)
treecb97291843f7784b33d2b3e369a91bd8b09f6e29 /indra
parent57b99aec74783c323738bd5a130c82c8dbf379c2 (diff)
Race condition resulted in close causing removal of peer connection while other jobs might be using it.
Diffstat (limited to 'indra')
-rw-r--r--indra/llwebrtc/llwebrtc.cpp23
-rw-r--r--indra/llwebrtc/llwebrtc.h3
-rw-r--r--indra/newview/llvoicewebrtc.cpp20
-rw-r--r--indra/newview/llvoicewebrtc.h7
4 files changed, 38 insertions, 15 deletions
diff --git a/indra/llwebrtc/llwebrtc.cpp b/indra/llwebrtc/llwebrtc.cpp
index 97c04ae446..5c71831c65 100644
--- a/indra/llwebrtc/llwebrtc.cpp
+++ b/indra/llwebrtc/llwebrtc.cpp
@@ -670,24 +670,23 @@ void LLWebRTCPeerConnectionImpl::init(LLWebRTCImpl * webrtc_impl)
}
void LLWebRTCPeerConnectionImpl::terminate()
{
- rtc::scoped_refptr<webrtc::PeerConnectionInterface> connection;
- mPeerConnection.swap(connection);
- rtc::scoped_refptr<webrtc::DataChannelInterface> dataChannel;
- mDataChannel.swap(dataChannel);
- rtc::scoped_refptr<webrtc::MediaStreamInterface> localStream;
- mLocalStream.swap(localStream);
-
mWebRTCImpl->PostSignalingTask(
[=]()
{
- if (connection)
+ if (mDataChannel)
{
- connection->Close();
+ mDataChannel->UnregisterObserver();
+ mDataChannel->Close();
+ mDataChannel = nullptr;
}
- if (dataChannel)
+ if (mPeerConnection)
+ {
+ mPeerConnection->Close();
+ mPeerConnection = nullptr;
+ }
+ for (auto &observer : mSignalingObserverList)
{
- dataChannel->UnregisterObserver();
- dataChannel->Close();
+ observer->OnPeerConnectionClosed();
}
});
}
diff --git a/indra/llwebrtc/llwebrtc.h b/indra/llwebrtc/llwebrtc.h
index ac71e0c744..ecbab81538 100644
--- a/indra/llwebrtc/llwebrtc.h
+++ b/indra/llwebrtc/llwebrtc.h
@@ -212,6 +212,9 @@ class LLWebRTCSignalingObserver
// Called when a connection enters a failure state and renegotiation is needed.
virtual void OnRenegotiationNeeded() = 0;
+ // Called when a peer connection has shut down
+ virtual void OnPeerConnectionClosed() = 0;
+
// Called when the audio channel has been established and audio
// can begin.
virtual void OnAudioEstablished(LLWebRTCAudioInterface *audio_interface) = 0;
diff --git a/indra/newview/llvoicewebrtc.cpp b/indra/newview/llvoicewebrtc.cpp
index e72d5e6066..2ab4ae2edf 100644
--- a/indra/newview/llvoicewebrtc.cpp
+++ b/indra/newview/llvoicewebrtc.cpp
@@ -2344,6 +2344,19 @@ void LLVoiceWebRTCConnection::OnRenegotiationNeeded()
});
}
+// callback from llwebrtc
+void LLVoiceWebRTCConnection::OnPeerConnectionClosed()
+{
+ LL::WorkQueue::postMaybe(mMainQueue,
+ [=] {
+ LL_DEBUGS("Voice") << "Peer connection has closed." << LL_ENDL;
+ if (mVoiceConnectionState == VOICE_STATE_WAIT_FOR_CLOSE)
+ {
+ setVoiceConnectionState(VOICE_STATE_CLOSED);
+ mOutstandingRequests--;
+ }
+ });
+}
void LLVoiceWebRTCConnection::setMuteMic(bool muted)
{
@@ -2741,8 +2754,13 @@ bool LLVoiceWebRTCConnection::connectionStateMachine()
case VOICE_STATE_SESSION_EXIT:
{
+ setVoiceConnectionState(VOICE_STATE_WAIT_FOR_CLOSE);
+ mOutstandingRequests++;
mWebRTCPeerConnectionInterface->shutdownConnection();
-
+ break;
+ case VOICE_STATE_WAIT_FOR_CLOSE:
+ break;
+ case VOICE_STATE_CLOSED:
if (!mShutDown)
{
mVoiceConnectionState = VOICE_STATE_START_SESSION;
diff --git a/indra/newview/llvoicewebrtc.h b/indra/newview/llvoicewebrtc.h
index c417dfe329..fcd4c04e98 100644
--- a/indra/newview/llvoicewebrtc.h
+++ b/indra/newview/llvoicewebrtc.h
@@ -585,6 +585,7 @@ class LLVoiceWebRTCConnection :
void OnIceCandidate(const llwebrtc::LLWebRTCIceCandidate &candidate) override;
void OnOfferAvailable(const std::string &sdp) override;
void OnRenegotiationNeeded() override;
+ void OnPeerConnectionClosed() override;
void OnAudioEstablished(llwebrtc::LLWebRTCAudioInterface *audio_interface) override;
//@}
@@ -640,13 +641,15 @@ class LLVoiceWebRTCConnection :
VOICE_STATE_DISCONNECT = 0x100,
VOICE_STATE_WAIT_FOR_EXIT = 0x200,
VOICE_STATE_SESSION_EXIT = 0x400,
- VOICE_STATE_SESSION_STOPPING = 0x780
+ VOICE_STATE_WAIT_FOR_CLOSE = 0x800,
+ VOICE_STATE_CLOSED = 0x1000,
+ VOICE_STATE_SESSION_STOPPING = 0x1F80
} EVoiceConnectionState;
EVoiceConnectionState mVoiceConnectionState;
LL::WorkQueue::weak_t mMainQueue;
- void setVoiceConnectionState(EVoiceConnectionState new_voice_connection_state)
+ void setVoiceConnectionState(EVoiceConnectionState new_voice_connection_state)
{
if (new_voice_connection_state & VOICE_STATE_SESSION_STOPPING)
{