dotnet / MQTTnet

MQTTnet is a high performance .NET library for MQTT based communication. It provides a MQTT client and a MQTT server (broker). The implementation is based on the documentation from http://mqtt.org/.
MIT License
4.48k stars 1.07k forks source link

MQTT communication exception while receiving packets #158

Closed liuhongbo closed 3 years ago

liuhongbo commented 6 years ago

I use the MQTTnet client to connect to aws iot through a presigned url, it works, however, every about 100 seconds (it is pretty accurate every time) it will get disconnected. i am not sure why. here is the log i got:

>> [2018-01-19T15:59:07.0172770-05:00] [10] [MqttClient] [Verbose]: Trying to connect with server.
>> [2018-01-19T15:59:07.0202781-05:00] [10] [MqttChannelAdapter] [Verbose]: Connecting [Timeout=00:00:30]
>> [2018-01-19T15:59:07.1783819-05:00] [11] [MqttClient] [Verbose]: Connection with server established.
>> [2018-01-19T15:59:07.1853863-05:00] [7] [MqttClient] [Info]: Start receiving packets.
>> [2018-01-19T15:59:07.3435203-05:00] [5] [MqttChannelAdapter] [Verbose]: TX >>> Connect: [ClientId=360d99a6fe41b3c1c6a095993b7ae9b6d2ca979c9b9cc690de1d03a7fe2f8e51] [Username=] [Password=] [KeepAlivePeriod=10] [CleanSession=True] [Timeout=00:00:30]
>> [2018-01-19T15:59:07.4546491-05:00] [7] [MqttChannelAdapter] [Verbose]: RX <<< ConnAck: [ConnectReturnCode=ConnectionAccepted] [IsSessionPresent=False]
>> [2018-01-19T15:59:07.4696600-05:00] [5] [MqttClient] [Info]: Received <<< ConnAck: [ConnectReturnCode=ConnectionAccepted] [IsSessionPresent=False]
>> [2018-01-19T15:59:07.4726629-05:00] [5] [MqttClient] [Verbose]: MQTT connection with server established.
>> [2018-01-19T15:59:07.4886676-05:00] [9] [MqttClient] [Info]: Start sending keep alive packets.
>> [2018-01-19T15:59:07.4896734-05:00] [9] [MqttChannelAdapter] [Verbose]: TX >>> PingReq [Timeout=00:00:30]
>> [2018-01-19T15:59:07.4966735-05:00] [5] [MqttChannelAdapter] [Verbose]: TX >>> Subscribe: [PacketIdentifier=1] [TopicFilters=57e581b25854ac000ff6f3ef@AtLeastOnce,59272c7e80e5cf82a30d39fb@AtLeastOnce,57fcd4575730e4000f9ba85f@AtLeastOnce] [Timeout=00:00:30]
>> [2018-01-19T15:59:07.5086791-05:00] [7] [MqttChannelAdapter] [Verbose]: RX <<< PingResp
>> [2018-01-19T15:59:07.5096801-05:00] [9] [MqttClient] [Info]: Received <<< PingResp
>> [2018-01-19T15:59:07.5527116-05:00] [7] [MqttChannelAdapter] [Verbose]: RX <<< SubAck: [PacketIdentifier=1] [SubscribeReturnCodes=SuccessMaximumQoS1,SuccessMaximumQoS1,SuccessMaximumQoS1]
>> [2018-01-19T15:59:07.5527116-05:00] [12] [MqttClient] [Info]: Received <<< SubAck: [PacketIdentifier=1] [SubscribeReturnCodes=SuccessMaximumQoS1,SuccessMaximumQoS1,SuccessMaximumQoS1]
>> [2018-01-19T15:59:17.5244169-05:00] [5] [MqttChannelAdapter] [Verbose]: TX >>> PingReq [Timeout=00:00:30]
>> [2018-01-19T15:59:17.5444309-05:00] [7] [MqttChannelAdapter] [Verbose]: RX <<< PingResp
>> [2018-01-19T15:59:17.5454313-05:00] [5] [MqttClient] [Info]: Received <<< PingResp
>> [2018-01-19T15:59:27.5646272-05:00] [5] [MqttChannelAdapter] [Verbose]: TX >>> PingReq [Timeout=00:00:30]
>> [2018-01-19T15:59:27.5836342-05:00] [7] [MqttChannelAdapter] [Verbose]: RX <<< PingResp
>> [2018-01-19T15:59:27.5836342-05:00] [5] [MqttClient] [Info]: Received <<< PingResp
>> [2018-01-19T15:59:37.5868786-05:00] [9] [MqttChannelAdapter] [Verbose]: TX >>> PingReq [Timeout=00:00:30]
>> [2018-01-19T15:59:37.6078826-05:00] [7] [MqttChannelAdapter] [Verbose]: RX <<< PingResp
>> [2018-01-19T15:59:37.6078826-05:00] [12] [MqttClient] [Info]: Received <<< PingResp
>> [2018-01-19T15:59:40.6239881-05:00] [7] [MqttChannelAdapter] [Verbose]: RX <<< Publish: [Topic=57fcd4575730e4000f9ba85f] [Payload.Length=512] [QoSLevel=AtLeastOnce] [Dup=False] [Retain=False] [PacketIdentifier=1]
>> [2018-01-19T15:59:40.6239881-05:00] [9] [MqttClient] [Info]: Received <<< Publish: [Topic=57fcd4575730e4000f9ba85f] [Payload.Length=512] [QoSLevel=AtLeastOnce] [Dup=False] [Retain=False] [PacketIdentifier=1]
>> [2018-01-19T15:59:40.9493656-05:00] [9] [MqttChannelAdapter] [Verbose]: TX >>> PubAck [Timeout=00:00:30]
>> [2018-01-19T15:59:47.6221570-05:00] [9] [MqttChannelAdapter] [Verbose]: TX >>> PingReq [Timeout=00:00:30]
>> [2018-01-19T15:59:47.6482058-05:00] [7] [MqttChannelAdapter] [Verbose]: RX <<< PingResp
>> [2018-01-19T15:59:47.6491995-05:00] [9] [MqttClient] [Info]: Received <<< PingResp
>> [2018-01-19T15:59:57.6662408-05:00] [9] [MqttChannelAdapter] [Verbose]: TX >>> PingReq [Timeout=00:00:30]
>> [2018-01-19T15:59:57.6872503-05:00] [7] [MqttChannelAdapter] [Verbose]: RX <<< PingResp
>> [2018-01-19T15:59:57.6892564-05:00] [9] [MqttClient] [Info]: Received <<< PingResp
>> [2018-01-19T16:00:07.7111522-05:00] [9] [MqttChannelAdapter] [Verbose]: TX >>> PingReq [Timeout=00:00:30]
>> [2018-01-19T16:00:07.7321702-05:00] [7] [MqttChannelAdapter] [Verbose]: RX <<< PingResp
>> [2018-01-19T16:00:07.7331669-05:00] [9] [MqttClient] [Info]: Received <<< PingResp
>> [2018-01-19T16:00:17.7528845-05:00] [12] [MqttChannelAdapter] [Verbose]: TX >>> PingReq [Timeout=00:00:30]
>> [2018-01-19T16:00:17.7728972-05:00] [7] [MqttChannelAdapter] [Verbose]: RX <<< PingResp
>> [2018-01-19T16:00:17.7748992-05:00] [9] [MqttClient] [Info]: Received <<< PingResp
>> [2018-01-19T16:00:27.7791319-05:00] [9] [MqttChannelAdapter] [Verbose]: TX >>> PingReq [Timeout=00:00:30]
>> [2018-01-19T16:00:27.8011393-05:00] [7] [MqttChannelAdapter] [Verbose]: RX <<< PingResp
>> [2018-01-19T16:00:27.8021397-05:00] [9] [MqttClient] [Info]: Received <<< PingResp
>> [2018-01-19T16:00:37.8198474-05:00] [12] [MqttChannelAdapter] [Verbose]: TX >>> PingReq [Timeout=00:00:30]
>> [2018-01-19T16:00:37.8388580-05:00] [7] [MqttChannelAdapter] [Verbose]: RX <<< PingResp
>> [2018-01-19T16:00:37.8388580-05:00] [11] [MqttClient] [Info]: Received <<< PingResp
>> [2018-01-19T16:00:47.4215941-05:00] [7] [MqttClient] [Warning]: MQTT communication exception while receiving packets.
MQTTnet.Exceptions.MqttCommunicationException: The remote party closed the WebSocket connection without completing the close handshake. ---> System.Net.WebSockets.WebSocketException: The remote party closed the WebSocket connection without completing the close handshake. ---> System.ObjectDisposedException: Cannot access a disposed object.
Object name: 'SslStream'.
   at System.Net.Security.SslState.CheckThrow(Boolean authSuccessCheck, Boolean shutdownCheck)
   at System.Net.Security.SslState.get_SecureStream()
   at System.Net.TlsStream.EndRead(IAsyncResult asyncResult)
   at System.Net.PooledStream.EndRead(IAsyncResult asyncResult)
   at System.IO.Stream.<>c.<BeginEndReadAsync>b__43_1(Stream stream, IAsyncResult asyncResult)
   at System.Threading.Tasks.TaskFactory`1.FromAsyncTrimPromise`1.Complete(TInstance thisRef, Func`3 endMethod, IAsyncResult asyncResult, Boolean requiresSynchronization)
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at System.Net.WebSockets.WebSocketConnectionStream.<ReadAsync>d__21.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at System.Runtime.CompilerServices.TaskAwaiter.ValidateEnd(Task task)
   at System.Net.WebSockets.WebSocketBase.WebSocketOperation.<Process>d__19.MoveNext()
   --- End of inner exception stack trace ---
   at System.Net.WebSockets.WebSocketBase.WebSocketOperation.<Process>d__19.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at System.Net.WebSockets.WebSocketBase.<ReceiveAsyncCore>d__45.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Implementations.WebSocketStream.<FetchChunkAsync>d__23.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Implementations.WebSocketStream.<ReadAsync>d__18.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Implementations.WebSocketStream.Read(Byte[] buffer, Int32 offset, Int32 count)
   at System.IO.Stream.ReadByte()
   at MQTTnet.Serializer.MqttPacketReader.ReadHeaderFromSource(Stream stream, CancellationToken cancellationToken)
   at MQTTnet.Adapter.MqttChannelAdapter.<ReceiveAsync>d__13.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Adapter.MqttChannelAdapter.<>c__DisplayClass12_0.<<ReceivePacketAsync>b__0>d.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Adapter.MqttChannelAdapter.<ExecuteAndWrapExceptionAsync>d__14.MoveNext()
   --- End of inner exception stack trace ---
   at MQTTnet.Adapter.MqttChannelAdapter.<ExecuteAndWrapExceptionAsync>d__14.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Adapter.MqttChannelAdapter.<ReceivePacketAsync>d__12.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Client.MqttClient.<ReceivePacketsAsync>d__40.MoveNext()
>> [2018-01-19T16:00:47.4676255-05:00] [7] [MqttClient] [Info]: Stopped sending keep alive packets.
>> [2018-01-19T16:00:47.4686240-05:00] [7] [MqttChannelAdapter] [Verbose]: Disconnecting [Timeout=00:00:30]
>> [2018-01-19T16:00:47.4716251-05:00] [7] [MqttClient] [Info]: Disconnected from adapter.
>> [2018-01-19T16:00:47.4716251-05:00] [7] [MqttClient] [Info]: Disconnected.
>> [2018-01-19T16:00:47.4776303-05:00] [7] [MqttClient] [Info]: Stopped receiving packets.

I am not sure if this is a issue with aws or not, but just can not find the cause.

chkr1011 commented 6 years ago

Hi @liuhongbo, which Version are you using? And what broker do you use?

Best regards Christian

liuhongbo commented 6 years ago

I am on version 2.6.0 the broker is aws iot message broker. (if i understood it correctly)

thank you.

liuhongbo commented 6 years ago

i fixed the issue, even though the fix is not perfect. the issue is described in this post

the only fix i found is like this:

var defaultMaxServicePointIdleTime = System.Net.ServicePointManager.MaxServicePointIdleTime;
System.Net.ServicePointManager.MaxServicePointIdleTime = Timeout.Infinite;                
await client.ConnectAsync(options);
System.Net.ServicePointManager.MaxServicePointIdleTime = defaultMaxServicePointIdleTime;

in theory this fix is not good enough to be accepted as a fix, but this is the only fix that works for me so far.

schenckg commented 6 years ago

I see the same issue connecting to an AWS IOT over WebSockets. Specifically the "The remote party closed the WebSocket connection without completing the close handshake" error. Like @liuhongbo, setting the ServicePointManager to Infinite timeout seemed to address the issue. I'd like to understand better why this occurs and the best practice for avoiding it.

liuhongbo commented 6 years ago

@schenckg my understand is that (but not quite sure).

  1. websocket works like this: it starts with a regular http connection, then use this http connection to start the WebSocket handshake, after the handshake, this same http connection is upgraded to a web socket connection.
  2. even though both regular http connection (http(s)) and web socket connection (ws(s)) are based on a regular TCP/IP connection, but seems in System.Net.ServicePointManager, they are treated and managed in different ServicePoints
  3. MaxServicePointIdleTime controls maximum idle time of a ServicePoint object which default is 100 seconds
  4. after upgrade to web sockets connections, the http connection will have no communications anymore, so after MaxServicePointIdleTime seconds, the ServicePoint will kill the http connection which in turn will kill the TCP/IP connection, which in turn the web socket connection is killed at the end.
biapar commented 6 years ago

@liuhongbo @chkr1011 @schenckg @JTrotta I've the same error connectiong a MQTT client to ASP.NET Core 2 Broker MQTT. How to solve? See: https://github.com/chkr1011/MQTTnet/issues/260

chkr1011 commented 5 years ago

The SSL stream disposed exception is fixed in latest dev branch. Please reopen this ticket if this still fails.

johan-lindqvist commented 5 years ago

I'm getting the exact same issue as described in the original post in 3.0.4. I'm also talking to an AWS IoT Message Broker.

The workaround that @liuhongbo mentioned (ServicePointManager.MaxServicePointIdleTime = Timeout.Infinite) worked, but it doesn't feel like a good solution.

SeppPenner commented 5 years ago

The SSL stream disposed exception is fixed in latest dev branch. Please reopen this ticket if this still fails.

@chkr1011 You need to check this again...

chkr1011 commented 5 years ago

@jltjohanlindqvist So your transport is also WebSocket + TLS and you send NO messages? Just Pin/Pong? Or is keep alive disabled?

johan-lindqvist commented 5 years ago

@chkr1011 correct, I configure with proxy, client id and a wss url as the websocketserver.

edit: I get this in the log when doing connect:

[2019-06-27T13:46:53.5499382Z] [6] [MqttClient.MqttChannelAdapter] [Verbose]: TX (56 bytes) >>> Connect: [ClientId=redacted] [Username=] [Password=] [KeepAlivePeriod=15] [CleanSession=True]
johan-lindqvist commented 5 years ago

The strange thing is, we have two addresses to our proxy at work. If I add the workaround it works with one of the proxy addresses, but not with the other proxy address, then I get the same issue of The remote party closed the WebSocket connection without completing the close handshake.

edit: So the workaround only works if I'm using the same proxy address that I've configured in the windows proxy settings. But I assume it should work without the workaround.

chkr1011 commented 5 years ago

Do you maybe use an UWP app?

johan-lindqvist commented 5 years ago

It's a WPF app.

johan-lindqvist commented 5 years ago

I'm pretty sure it has to do with the problem described in this comment https://github.com/dotnet/corefx/issues/31880#issuecomment-419269635 and the mentioned stackoverflow question.

johan-lindqvist commented 5 years ago

It is as I suspected, which is described in the comment previously mentioned, I get Content-Length: 0 in the upgrade response, using Fiddler I got this:

HTTP/1.1 101 Switching Protocols
content-length: 0
upgrade: websocket
connection: upgrade
sec-websocket-accept: cNjHkkVKpVoJEXu3fl86XPs5u8M=
sec-websocket-protocol: mqtt
EndTime: 13:26:15.363
ReceivedBytes: 45
SentBytes: 179

Which if I understand the corefx issue correctly is not handled well in .NET Framework.

I'm gonna test and see if I have the same issue using a .NET Core-project.

johan-lindqvist commented 5 years ago

Tested using a simple project for both .NET Core 2.2 and .NET Framework 4.8, and I can only reproduce the issue in .NET Framework 4.8. So it seems like it's a bug in the .NET Framework that they've fixed in .NET Core.

Guess there's not a lot to do in this project to fix this issue.

johan-lindqvist commented 5 years ago

I created an issue on the .NET Framework issue tracker, https://developercommunity.visualstudio.com/content/problem/629916/websocket-times-out-after-100-seconds.html

johan-lindqvist commented 5 years ago

@chkr1011 got this error tonight when running an MQTT WebSocket, as far as I understand this exception shouldn't happen in the TryRecievePacketsAsync method.

Unhandled task exception branches-MQTT-0554, System.AggregateException: A Task's exception(s) were not observed either by Waiting on the Task or accessing its Exception property. As a result, the unobserved exception was rethrown by the finalizer thread. ---> MQTTnet.Exceptions.MqttCommunicationException: The remote party closed the WebSocket connection without completing the close handshake. ---> System.Net.WebSockets.WebSocketException: The remote party closed the WebSocket connection without completing the close handshake. ---> System.ObjectDisposedException: Cannot access a disposed object.
Object name: 'SslStream'.
   at System.Net.Security.SslState.CheckThrow(Boolean authSuccessCheck, Boolean shutdownCheck)
   at System.Net.Security.SslState.get_SecureStream()
   at System.Net.TlsStream.EndRead(IAsyncResult asyncResult)
   at System.Threading.Tasks.TaskFactory`1.FromAsyncTrimPromise`1.Complete(TInstance thisRef, Func`3 endMethod, IAsyncResult asyncResult, Boolean requiresSynchronization)
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at System.Net.WebSockets.WebSocketConnectionStream.<ReadAsync>d__21.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at System.Net.WebSockets.WebSocketBase.WebSocketOperation.<Process>d__19.MoveNext()
   --- End of inner exception stack trace ---
   at System.Net.WebSockets.WebSocketBase.WebSocketOperation.<Process>d__19.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at System.Net.WebSockets.WebSocketBase.<ReceiveAsyncCore>d__45.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Implementations.MqttWebSocketChannel.<ReadAsync>d__18.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Formatter.MqttPacketReader.<ReadFixedHeaderAsync>d__3.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Adapter.MqttChannelAdapter.<ReceiveAsync>d__37.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Adapter.MqttChannelAdapter.<ReceivePacketAsync>d__35.MoveNext()
   --- End of inner exception stack trace ---
   at MQTTnet.Adapter.MqttChannelAdapter.WrapException(Exception exception)
   at MQTTnet.Adapter.MqttChannelAdapter.<ReceivePacketAsync>d__35.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Client.MqttClient.<TryReceivePacketsAsync>d__48.MoveNext()
   --- End of inner exception stack trace ---
---> (Inner Exception #0) MQTTnet.Exceptions.MqttCommunicationException: The remote party closed the WebSocket connection without completing the close handshake. ---> System.Net.WebSockets.WebSocketException: The remote party closed the WebSocket connection without completing the close handshake. ---> System.ObjectDisposedException: Cannot access a disposed object.
Object name: 'SslStream'.
   at System.Net.Security.SslState.CheckThrow(Boolean authSuccessCheck, Boolean shutdownCheck)
   at System.Net.Security.SslState.get_SecureStream()
   at System.Net.TlsStream.EndRead(IAsyncResult asyncResult)
   at System.Threading.Tasks.TaskFactory`1.FromAsyncTrimPromise`1.Complete(TInstance thisRef, Func`3 endMethod, IAsyncResult asyncResult, Boolean requiresSynchronization)
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at System.Net.WebSockets.WebSocketConnectionStream.<ReadAsync>d__21.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at System.Net.WebSockets.WebSocketBase.WebSocketOperation.<Process>d__19.MoveNext()
   --- End of inner exception stack trace ---
   at System.Net.WebSockets.WebSocketBase.WebSocketOperation.<Process>d__19.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at System.Net.WebSockets.WebSocketBase.<ReceiveAsyncCore>d__45.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Implementations.MqttWebSocketChannel.<ReadAsync>d__18.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Formatter.MqttPacketReader.<ReadFixedHeaderAsync>d__3.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Adapter.MqttChannelAdapter.<ReceiveAsync>d__37.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Adapter.MqttChannelAdapter.<ReceivePacketAsync>d__35.MoveNext()
   --- End of inner exception stack trace ---
   at MQTTnet.Adapter.MqttChannelAdapter.WrapException(Exception exception)
   at MQTTnet.Adapter.MqttChannelAdapter.<ReceivePacketAsync>d__35.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Client.MqttClient.<TryReceivePacketsAsync>d__48.MoveNext()<---

I still have the 100 second timeout issue, but we're bypassing that issue by just reconnecting every 100 seconds, which is not optimal, but until Microsoft or Amazon fixes their issues there's not a lot more we can do about it.

So this happened randomly while running a WebSocket during the night, with us using one MqttClient where we're reconnecting and subscribing each time we get the 100 second timeout.

Glad to provide more information if you feel there's any missing. I unfortunately don't have any logs from the MQTTnet lib.

chkr1011 commented 5 years ago

@jltjohanlindqvist In order to avouid the disconnects you can try to download and use the WebSocket4Net extensions. Then the WebSocket layer is a different one and may not disconnect. Or is the issue caused by the server (wasn't following all the time)?

Which version are you using? In theory this should be already fixed.

johan-lindqvist commented 5 years ago

We're using 3.0.5, and I saw that the WebSocket4Net doesn't support proxies which is why I'm not using it. We're not using the server at all, only the client parts of the MQTTnet lib.

A colleague and I looked at the source yesterday and we think the reason is that when we get to line 420 in MqttClient.cs the adapter has been disposed and thus we get an object disposed exception. This is probably because we weren't re-initializing our MqttClient object every time we got a disconnect (which in my opinion shouldn't be needed), we do that now and I'll see if we get the crash again.

johan-lindqvist commented 5 years ago

Still get the same crash even though we're always creating a new MqttClient every time we disconnect. So my idea that recreating the MqttClient would help was obviously wrong and now I'm at a bit of a loss what to do from my side?

Unhandled task exception master-0535, System.AggregateException: A Task's exception(s) were not observed either by Waiting on the Task or accessing its Exception property. As a result, the unobserved exception was rethrown by the finalizer thread. ---> MQTTnet.Exceptions.MqttCommunicationException: The remote party closed the WebSocket connection without completing the close handshake. ---> System.Net.WebSockets.WebSocketException: The remote party closed the WebSocket connection without completing the close handshake. ---> System.ObjectDisposedException: Cannot access a disposed object.
Object name: 'SslStream'.
   at System.Net.Security.SslState.CheckThrow(Boolean authSuccessCheck, Boolean shutdownCheck)
   at System.Net.Security.SslState.get_SecureStream()
   at System.Net.TlsStream.EndRead(IAsyncResult asyncResult)
   at System.Threading.Tasks.TaskFactory`1.FromAsyncTrimPromise`1.Complete(TInstance thisRef, Func`3 endMethod, IAsyncResult asyncResult, Boolean requiresSynchronization)
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at System.Net.WebSockets.WebSocketConnectionStream.<ReadAsync>d__21.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at System.Net.WebSockets.WebSocketBase.WebSocketOperation.<Process>d__19.MoveNext()
   --- End of inner exception stack trace ---
   at System.Net.WebSockets.WebSocketBase.WebSocketOperation.<Process>d__19.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at System.Net.WebSockets.WebSocketBase.<ReceiveAsyncCore>d__45.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Implementations.MqttWebSocketChannel.<ReadAsync>d__18.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Formatter.MqttPacketReader.<ReadFixedHeaderAsync>d__3.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Adapter.MqttChannelAdapter.<ReceiveAsync>d__37.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Adapter.MqttChannelAdapter.<ReceivePacketAsync>d__35.MoveNext()
   --- End of inner exception stack trace ---
   at MQTTnet.Adapter.MqttChannelAdapter.WrapException(Exception exception)
   at MQTTnet.Adapter.MqttChannelAdapter.<ReceivePacketAsync>d__35.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Client.MqttClient.<TryReceivePacketsAsync>d__48.MoveNext()
   --- End of inner exception stack trace ---
---> (Inner Exception #0) MQTTnet.Exceptions.MqttCommunicationException: The remote party closed the WebSocket connection without completing the close handshake. ---> System.Net.WebSockets.WebSocketException: The remote party closed the WebSocket connection without completing the close handshake. ---> System.ObjectDisposedException: Cannot access a disposed object.
Object name: 'SslStream'.
   at System.Net.Security.SslState.CheckThrow(Boolean authSuccessCheck, Boolean shutdownCheck)
   at System.Net.Security.SslState.get_SecureStream()
   at System.Net.TlsStream.EndRead(IAsyncResult asyncResult)
   at System.Threading.Tasks.TaskFactory`1.FromAsyncTrimPromise`1.Complete(TInstance thisRef, Func`3 endMethod, IAsyncResult asyncResult, Boolean requiresSynchronization)
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at System.Net.WebSockets.WebSocketConnectionStream.<ReadAsync>d__21.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at System.Net.WebSockets.WebSocketBase.WebSocketOperation.<Process>d__19.MoveNext()
   --- End of inner exception stack trace ---
   at System.Net.WebSockets.WebSocketBase.WebSocketOperation.<Process>d__19.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at System.Net.WebSockets.WebSocketBase.<ReceiveAsyncCore>d__45.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Implementations.MqttWebSocketChannel.<ReadAsync>d__18.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Formatter.MqttPacketReader.<ReadFixedHeaderAsync>d__3.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Adapter.MqttChannelAdapter.<ReceiveAsync>d__37.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Adapter.MqttChannelAdapter.<ReceivePacketAsync>d__35.MoveNext()
   --- End of inner exception stack trace ---
   at MQTTnet.Adapter.MqttChannelAdapter.WrapException(Exception exception)
   at MQTTnet.Adapter.MqttChannelAdapter.<ReceivePacketAsync>d__35.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Client.MqttClient.<TryReceivePacketsAsync>d__48.MoveNext()<---
johan-lindqvist commented 5 years ago

@chkr1011 any idea why this would be happening even after the changes to ReceivePacketsAsync -> TryReceivePacketsAsync?

chkr1011 commented 5 years ago

The main thing I am wondering is why this is not covered in a try-catch block. I am searching for it but have to clue. Do you have any idea?

johan-lindqvist commented 5 years ago

Could it be because the task is started in a Task.Run(), which means the exception is caught but since the task is not awaited the exception is not handled until the finalizer is disposing of the object and rethrows the exception causing the crash? https://github.com/chkr1011/MQTTnet/blob/7a642802ed7c217f53a865b4dc16e2f14b9634f1/Source/MQTTnet/Client/MqttClient.cs#L86

johan-lindqvist commented 5 years ago

Or it could be something that goes wrong in the catch block in TryReceivePacketsAsync, maybe?

ArsenijK commented 5 years ago

I have the same problem. Still can't find a workaround, same as @jltjohanlindqvist After first disconnect, I always get object disposed, and I'm very surprised, because I can't find a reason yet. The exception even gets wrapped to Mqtt Exception, but the point is, it's impossible to reconnect even with new Mqtt client. Maybe it's something with the Socket class? Maybe it has some kind of cache?

It looks like the last thing lib does is in MqttTcpChannel.ConnectAsync, and something fires: Object name: 'System.Net.Sockets.Socket'. ---> System.ObjectDisposedException: Cannot access a disposed object. And I am not passing any CancellationToken, so looking at source it seems it should be CancellationToken.None... But how does the socket gets disposed, if it's just been created? And it looks like it happens in Task.Factory.FromAsyncCoreLogic(), while calling EndConnect. I can't understand, how to fix it yet :(

I'm using WPF application targeting 4.7.2 Framework. Btw., can you tell me how #if NET452 || NET461 constants work?

   at System.Net.Sockets.Socket.InternalEndConnect(IAsyncResult asyncResult)
   at System.Net.Sockets.Socket.EndConnect(IAsyncResult asyncResult)
   at System.Threading.Tasks.TaskFactory`1.FromAsyncCoreLogic(IAsyncResult iar, Func`2 endFunction, Action`1 endAction, Task`1 promise, Boolean requiresSynchronization)
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at System.Runtime.CompilerServices.TaskAwaiter.ValidateEnd(Task task)
   at MQTTnet.Implementations.MqttTcpChannel.<ConnectAsync>d__15.MoveNext()
ArsenijK commented 5 years ago

It appears problem was on our side, if it helps @jltjohanlindqvist :

To test disconnect, I was changing my internet connection, and waiting for ping timeout. But my other internet had other IP and couldn't connect to MQTT server (it wasn't whitelisted). It's just very strange, that I got this kind of exception with this kind of stack trace. But since we opened MQTT server to the other IP as well, it managed to reconnect succesfully :) It's still a mystery to me, why was it Socket disposed exception though.

chkr1011 commented 5 years ago

@jltjohanlindqvist Do you have some disconnected handler attached?

From the StackTrace it looks like that it comes from WebSockets. So nothing we can fix.

The Task.Run is calling code which is wrapped in TryCatch only.

johan-lindqvist commented 5 years ago

Yeah, I'm using the UseDisconnectedHandler

johan-lindqvist commented 5 years ago

Why do you ask, @chkr1011 ?

johan-lindqvist commented 5 years ago

New stack trace where we also crash because of an unhandled exception.

Unhandled task exception master-0539, System.AggregateException: A Task's exception(s) were not observed either by Waiting on the Task or accessing its Exception property. As a result, the unobserved exception was rethrown by the finalizer thread. ---> MQTTnet.Exceptions.MqttCommunicationException: The remote party closed the WebSocket connection without completing the close handshake. ---> System.Net.WebSockets.WebSocketException: The remote party closed the WebSocket connection without completing the close handshake. ---> System.ObjectDisposedException: Cannot access a disposed object.
Object name: 'SslStream'.
   at System.Net.Security.SslState.ValidateCreateContext(Boolean isServer, String targetHost, SslProtocols enabledSslProtocols, X509Certificate serverCertificate, X509CertificateCollection clientCertificates, Boolean remoteCertRequired, Boolean checkCertRevocationStatus, Boolean checkCertName)
   at System.Net.TlsStream.ProcessAuthentication(LazyAsyncResult result)
   at System.Net.TlsStream.BeginWrite(Byte[] buffer, Int32 offset, Int32 size, AsyncCallback asyncCallback, Object asyncState)
   at System.IO.Stream.<>c.<BeginEndWriteAsync>b__53_0(Stream stream, ReadWriteParameters args, AsyncCallback callback, Object state)
   at System.Threading.Tasks.TaskFactory`1.FromAsyncTrim[TInstance,TArgs](TInstance thisRef, TArgs args, Func`5 beginMethod, Func`3 endMethod)
   at System.IO.Stream.BeginEndWriteAsync(Byte[] buffer, Int32 offset, Int32 count)
   at System.IO.Stream.WriteAsync(Byte[] buffer, Int32 offset, Int32 count, CancellationToken cancellationToken)
   at System.Net.DelegatedStream.WriteAsync(Byte[] buffer, Int32 offset, Int32 count, CancellationToken cancellationToken)
   at System.Net.WebSockets.WebSocketConnectionStream.WebSocketConnection.WriteAsync(Byte[] buffer, Int32 offset, Int32 count, CancellationToken cancellationToken)
   at System.Net.DelegatedStream.WriteAsync(Byte[] buffer, Int32 offset, Int32 count, CancellationToken cancellationToken)
   at System.Net.WebSockets.WebSocketConnectionStream.<>n__1(Byte[] buffer, Int32 offset, Int32 count, CancellationToken cancellationToken)
   at System.Net.WebSockets.WebSocketConnectionStream.<WriteAsync>d__22.MoveNext()
   --- End of inner exception stack trace ---
   at System.Net.WebSockets.WebSocketBase.WebSocketOperation.<Process>d__19.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at System.Net.WebSockets.WebSocketBase.<ReceiveAsyncCore>d__45.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Implementations.MqttWebSocketChannel.<ReadAsync>d__18.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at MQTTnet.Formatter.MqttPacketReader.<ReadFixedHeaderAsync>d__3.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Adapter.MqttChannelAdapter.<ReceiveAsync>d__37.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Adapter.MqttChannelAdapter.<ReceivePacketAsync>d__35.MoveNext()
   --- End of inner exception stack trace ---
   at MQTTnet.Adapter.MqttChannelAdapter.WrapException(Exception exception)
   at MQTTnet.Adapter.MqttChannelAdapter.<ReceivePacketAsync>d__35.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at MQTTnet.Client.MqttClient.<TryReceivePacketsAsync>d__48.MoveNext()
   --- End of inner exception stack trace ---
---> (Inner Exception #0) MQTTnet.Exceptions.MqttCommunicationException: The remote party closed the WebSocket connection without completing the close handshake. ---> System.Net.WebSockets.WebSocketException: The remote party closed the WebSocket connection without completing the close handshake. ---> System.ObjectDisposedException: Cannot access a disposed object.
Object name: 'SslStream'.
   at System.Net.Security.SslState.ValidateCreateContext(Boolean isServer, String targetHost, SslProtocols enabledSslProtocols, X509Certificate serverCertificate, X509CertificateCollection clientCertificates, Boolean remoteCertRequired, Boolean checkCertRevocationStatus, Boolean checkCertName)
   at System.Net.TlsStream.ProcessAuthentication(LazyAsyncResult result)
   at System.Net.TlsStream.BeginWrite(Byte[] buffer, Int32 offset, Int32 size, AsyncCallback asyncCallback, Object asyncState)
   at System.IO.Stream.<>c.<BeginEndWriteAsync>b__53_0(Stream stream, ReadWriteParameters args, AsyncCallback callback, Object state)
   at System.Threading.Tasks.TaskFactory`1.FromAsyncTrim[TInstance,TArgs](TInstance thisRef, TArgs args, Func`5 beginMethod, Func`3 endMethod)
   at System.IO.Stream.BeginEndWriteAsync(Byte[] buffer, Int32 offset, Int32 count)
   at System.IO.Stream.WriteAsync(Byte[] buffer, Int32 offset, Int32 count, CancellationToken cancellationToken)
   at System.Net.DelegatedStream.WriteAsync(Byte[] buffer, Int32 offset, Int32 count, CancellationToken cancellationToken)
   at System.Net.WebSockets.WebSocketConnectionStream.WebSocketConnection.WriteAsync(Byte[] buffer, Int32 offset, Int32 count, CancellationToken cancellationToken)
   at System.Net.DelegatedStream.WriteAsync(Byte[] buffer, Int32 offset, Int32 count, CancellationToken cancellationToken)
   at System.Net.WebSockets.WebSocketConnectionStream.<>n__1(Byte[] buffer, Int32 offset, Int32 count, CancellationToken cancellationToken)
   at System.Net.WebSockets.WebSocketConnectionStream.<WriteAsync>d__22.MoveNext()
   --- End of inner exception stack trace ---
   at System.Net.WebSockets.WebSocketBase.WebSocketOperation.<Process>d__19.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at System.Net.WebSockets.WebSocketBase.<ReceiveAsyncCore>d__45.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Implementations.MqttWebSocketChannel.<ReadAsync>d__18.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at MQTTnet.Formatter.MqttPacketReader.<ReadFixedHeaderAsync>d__3.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Adapter.MqttChannelAdapter.<ReceiveAsync>d__37.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at MQTTnet.Adapter.MqttChannelAdapter.<ReceivePacketAsync>d__35.MoveNext()
   --- End of inner exception stack trace ---
   at MQTTnet.Adapter.MqttChannelAdapter.WrapException(Exception exception)
   at MQTTnet.Adapter.MqttChannelAdapter.<ReceivePacketAsync>d__35.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at MQTTnet.Client.MqttClient.<TryReceivePacketsAsync>d__48.MoveNext()<---
johan-lindqvist commented 5 years ago

@chkr1011 we're still getting this crash, and after looking at the MQTTnet code we've found something we think might be the cause of the issue.

https://github.com/chkr1011/MQTTnet/blob/f54598c201b67abefaa0adc4c74e443617136371/Source/MQTTnet/Client/MqttClient.cs#L629-L648

What happens if one of the tasks that are run in a Task.Run ( _packetReceiverTask and _keepAlivePacketsSenderTask) get an exception that is not caught? This would mean we get to the WaitForTaskAsync method and on this line if (task.IsCanceled || task.IsCompleted || task.IsFaulted) we will check task.IsFaulted and then return without handling the exception, thus leaving us with an UnhandledTaskException. Also the

Is that if-case really needed? Why don't just remove the checking of canceled, completed and faulted and just always await the task? That way there wont be unhandled tasks, and if the task is completed or canceled the await will just return right away.

Or is there a reason for the if-case that we're not seeing?

edit: added a pull request with the changes I suggested here

edit 2: also, what's the idea behind the first if-clause in the WaitForTaskAsync method? There could be an issue where we return without awaiting the task in that case as well, maybe there should be a check at the top that makes sure task.IsFaulted == false?

chkr1011 commented 5 years ago

The reason was that be found a dead lock when using await. @JanEggers and I spent a lot of time to fix this.

But I am eager to try your solution because the current solution is only a workaround.

Let me try your pull request...

johan-lindqvist commented 5 years ago

Ah, I see. If you need any help don't hesitate to ask.

johan-lindqvist commented 5 years ago

@chkr1011 you asked earlier if I was using a DisconnectedHandler, was there any specific reason why you asked this?

Also, we've still not been able to fix the issue, still investigating.

chkr1011 commented 4 years ago

Please try 3.0.9-rc2. We again addressed some connection management issues.

chkr1011 commented 3 years ago

I close this ticket because I assume it is fixed.