Skip to content

Deadlock #95

@dsparkplug

Description

@dsparkplug

I've found an circular locking issue with the IStanzaEventListener methods in the XmppStream class .

Basically the IStanzaEventListener.StanzaReceived which acquires a [MethodImpl(MethodImplOptions.Synchronized)] lock can call IStanzaEventListener.BytesWritten which also needs to acquire a [MethodImpl(MethodImplOptions.Synchronized)] lock and therefore deadlocks.

The chain of calls is as follows:

XmppStream.StanzaReceived acquires a MethodImpl(MethodImplOptions.Synchronized) lock
--> calls XmppStream.OnElement
if (State is not ServerFeaturesState.Instance or SASLState.Instance or StartTLSState.Instance or CompressionState.Instance or SASLAuthedState.Instance)
--> invokes XmppStream.OnProtocol event
In IQTracker OnProtocol event is set to OnIQ
--> calls IQTracker.Call which calls the 'cb' callback which is set to JabberClient.GotSession in JabberClient.GotResource
--> sets JabberClient.IsAuthenticated
--> calls JabberClient.Presence
--> calls JabberClient.Write
--> calls SocketStanzaStream.JabberClient.Write
--> calls AsyncSocket.Write
--> calls Stream.BeginWrite with callback WroteData
--> WroteData calls SocketStanzaStream.OnWrite
--> calls XmppStream.BytesWritten which waits for a MethodImpl(MethodImplOptions.Synchronized) lock

Any ideas how to go about fixing this? The way this code uses callbacks is so convoluted its hard to know where to start without breaking something else.

The chain of events and subsequent deadlock is reproducible when sending a large number of XMPP messages.

Metadata

Metadata

Assignees

No one assigned

    Labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions