Hi,
I am using RA6M4 mcu and freertos + tcp stack with freertos version 10.6.1.
Now, problem is in DHCP when state machine is in eWaitingAcknowledge state. So, if it receives NACK in the options from the server, it sets the client present dhcp state to eInitialWait.
switch( pxSet->ucOptionCode )
{
case dhcpIPv4_MESSAGE_TYPE_OPTION_CODE:
if( pxSet->pucByte[ pxSet->uxIndex ] == ( uint8_t ) xExpectedMessageType )
{
/* The message type is the message type the
* state machine is expecting. */
pxSet->ulProcessed++;
}
else
{
if( pxSet->pucByte[ pxSet->uxIndex ] == ( uint8_t ) dhcpMESSAGE_TYPE_NACK )
{
if( xExpectedMessageType == ( BaseType_t ) dhcpMESSAGE_TYPE_ACK )
{
/* Start again. */
EP_DHCPData.eDHCPState = eInitialWait;
}
}
/* Stop processing further options. */
pxSet->uxLength = 0;
}
break;
Now, if by any chance, it receives any dhcp packet at this instant and peeks the packet, then due to mismatch of present state and expected state, it will be stuck in the loop.
if( ( EP_DHCPData.eDHCPState != EP_DHCPData.eExpectedState ) && ( xReset == pdFALSE ) )
{
/* When the DHCP event was generated, the DHCP client was
* in a different state. Therefore, ignore this event. */
FreeRTOS_debug_printf( ( "vDHCPProcessEndPoint: wrong state: expect: %d got: %d : ignore\n",
EP_DHCPData.eExpectedState, EP_DHCPData.eDHCPState ) );
}
10.6.1 should be the version of FreeRTOS Kernel; can you share the version of FreeRTOS+TCP you are using?
Now, if by any chance, it receives any dhcp packet at this instant and peeks the packet, then due to mismatch of present state and expected state, it will be stuck in the loop
Can you try making the change below:
In vProcessHandleOption(), can you add “EP_DHCPData.eExpectedState = eInitialWait;” to see if the state mismatch doesn’t happen.
static void vProcessHandleOption( NetworkEndPoint_t * pxEndPoint,
ProcessSet_t * pxSet,
BaseType_t xExpectedMessageType )
{
/* Option-specific handling. */
switch( pxSet->ucOptionCode )
{
case dhcpIPv4_MESSAGE_TYPE_OPTION_CODE:
if( pxSet->pucByte[ pxSet->uxIndex ] == ( uint8_t ) xExpectedMessageType )
{
/* The message type is the message type the
* state machine is expecting. */
pxSet->ulProcessed++;
}
else
{
if( pxSet->pucByte[ pxSet->uxIndex ] == ( uint8_t ) dhcpMESSAGE_TYPE_NACK )
{
if( xExpectedMessageType == ( BaseType_t ) dhcpMESSAGE_TYPE_ACK )
{
/* Start again. */
EP_DHCPData.eDHCPState = eInitialWait;
/* ADD THIS LINE to fix the state mismatch */
EP_DHCPData.eExpectedState = eInitialWait;
}
}
/* Stop processing further options. */
pxSet->uxLength = 0;
}
break;
@NikhilKamath, Firstly, I have tried adding this line in the code. It does solve the problem of state mismatch but does not remove the real problem which i found while debugging.
The real problem was that when it receives a nak from a server another server happens to also send an offer to the mcu, due to this after handling the present NAK packet (and changing its state to eWaitingAcknowledge) when it peeks for a received packet, it receives the offer message and gets stuck in the loop.
It also results in other bugs like when we receive an ack but just after it, we receive an offer. There also it will be stuck.
So, to handle this, I am able to think of only releasing the packet when states mismatch.