How to monitor MQTT connection to see if it is dropped?

nickm2018 wrote on September 17, 2018:

What should I do in order to check if a mqtt connection has been dropped?

Lets say I successfully connected and subscribed and have been publishing messages over a period of time but then the AP goes down or the internet is dropped for a period of time. When the network is back, obviously the connection has been closed by the broker (guess this is dependent on the keep-alive value).

I can see that the publish will return a general failure or timeout error but is there a function that can return the status of the connection?

Should I assume if I get x number of timeout failures in a row that the connection is probably closed?

nickm2018 wrote on September 18, 2018:

The Ping timeout message is sent from the library to the agent and then dropped. My application never knows about the ping timeout.

In aws_mqtt_lib.c, function +MQTT_Periodic+
xEventCallbackParams.xEventType = eMQTTPingTimeout;
( void ) prvInvokeCallback( pxMQTTContext, &xEventCallbackParams );

This calls +prvMQTTEventCallback+ in aws_mqtt_agent.c where the event is dropped and not forwarded to my application through pxConnection->pxCallback.

Gaurav-Aggarwal-AWS wrote on September 18, 2018:

That is a good feedback and we can certainly improve by propagating the ping timeout event to the application. However, I think the application should still be informed in case of a disconnect. Which platform are you using so that I can try at my end?

Thanks.

nickm2018 wrote on September 19, 2018:

It is a custom platform using 1.4.0.

From what I can tell it should be transparent to the platform port. In the eventCallback, eMQTTPingTimeout is dropped under the default case that has a todo note.


static MQTTBool_t prvMQTTEventCallback( void * pvCallbackContext,
                                        const MQTTEventCallbackParams_t * const pxParams )
{
    MQTTBool_t xReturn = eMQTTFalse;
    MQTTBrokerConnection_t * pxConnection;
    UBaseType_t uxBrokerNumber = ( UBaseType_t ) pvCallbackContext; /*lint !e923 The cast is ok as we passed the index of the client before. */

    /* Broker number must be valid. */
    configASSERT( uxBrokerNumber < ( UBaseType_t ) mqttconfigMAX_BROKERS );

    /* Get the actual connection to the broker. */
    pxConnection = &( xMQTTConnections[ uxBrokerNumber ] );

    switch( pxParams->xEventType )
    {
        case eMQTTConnACK:
            prvProcessReceivedCONNACK( pxConnection, pxParams );
            break;

        case eMQTTSubACK:
            prvProcessReceivedSUBACK( pxConnection, pxParams );
            break;

        case eMQTTUnSubACK:
            prvProcessReceivedUNSUBACK( pxConnection, pxParams );
            break;

        case eMQTTPubACK:
            prvProcessReceivedPUBACK( pxConnection, pxParams );
            break;

        case eMQTTPublish:

            /* Inform the core library if the user wants to take
             * the ownership of the provided buffer. */
            if( prvProcessReceivedPublish( pxConnection, pxParams ) == pdTRUE )
            {
                xReturn = eMQTTTrue;
            }

            break;

        case eMQTTTimeout:
            prvProcessReceivedTimeout( pxConnection, pxParams );
            break;

        case eMQTTClientDisconnected:
            prvProcessReceivedDisconnect( pxConnection, pxParams );
            break;

        case eMQTTPacketDropped:
        	AWS_MQTT_ERROR( ( "[WARN] MQTT Agent dropped a packet. No buffer available.\r
" ) );
        	AWS_MQTT_ERROR( ( "Consider adjusting parameters in aws_bufferpool_config.h.\r
" ) );
            break;

        default:
           /* _TODO_ Handle the remaining events. */
            break;
    }

    return xReturn;
}

Gaurav-Aggarwal-AWS wrote on September 19, 2018:

Thank you for your feedback. We will work on forwarding the timeout event to the application.

However, what does +SOCKETS_Recv+ function return on your platform when the connection is dropped? It is expected that the +SOCKETS_Recv+ will return an error other than +SOCKETS_EWOULDBLOCK+ and then the agent is disconnected in which case application will get notified via +eMQTTAgentDisconnect+ event: https://github.com/aws/amazon-freertos/blob/master/lib/mqtt/aws_mqtt_agent.c#L1312

Thanks.

nickm2018 wrote on October 04, 2018:

Just to followup, when the network is disconnected, I receive wouldblock errors, which from what I can tell is normal behavior.

If running QoS of 1, what happens at the mqtt library level if the puback is not received? Any indication passed back to the application layer?

Edited by: nickm2018 on Oct 4, 2018 2:43 PM

hbouvier-AWS wrote on August 20, 2019:

This should behavior has been fixed with the latest release:
https://github.com/aws/amazon-freertos/tree/201906.00_Major