You could use FreeRTOS+Trace to see what is happening. Start a trace recording using a circular buffer, then stop the trace when xQueueSend() returns pdFALSE so you can see what happens immediately before that.
You could also post the code for your receive function here. Without seeing the code there are too many possibilities to go through. For example, it could simply be that a task that has a higher priority is stopping the receive task from ever running so the queue becomes full.
Hi
I will try using the FreeRTOs+Trace next time it happens...
I don't think another task is stopping it from running.
The timeout on the xQueueReceive works fine, refreshing my watchdog. Also could debug the task, but pdTRUE never returned. Also configGENERATE_RUN_TIME_STATS say that no task a taking to much CPU time.
Receive code that stops receving
void ProtocolTXTask(void *pvParameters)
{
PROTOCOL_TX sTXData;
BYTE byRetries = 0;
BYTE byTXTaskID = 0;
// Create a queue for RX events...
g_xProtocolTXEvent = xQueueCreate( 5, sizeof(PROTOCOL_TX) );
if( g_xProtocolTXEvent == 0 )
{
return;
}
byTXTaskID = RegisterTaskToWatchdog(xProtocolTXHandle, 10);
while(TRUE)
{
if(pdTRUE == xQueueReceive (g_xProtocolTXEvent, &sTXData, 5000))
{
ProtocolGetLinkStates();
// Media connected?
if( bActiveConnection[sTXData.byMedia] )
{
// Send the data
if(pdTRUE == (*pTXdata[sTXData.byMedia])(sTXData.ulTXBuffer, sTXData.nSize, sTXData.xTimeout,
sTXData.bRAW)) // Normal
{
sTXData.byState = 1;
break;
}
else
{
sTXData.byState = 0;
}
}
}
NotifyWatchdog(byTXTaskID);
} // While(1)
}
Code that post to the g_xProtocolTXEvent queue (Called by different tasks)
BOOL ProtocolSendData(unsigned long ulTXData, int nTXSize, BYTE byMedia, portTickType xTimeOut, BOOL bRAW)
{
PROTOCOL_TX sTXData;
sTXData.nSize = nTXSize;
sTXData.ulTXBuffer = (unsigned long)ulTXData; // Address of the TX data
sTXData.xTimeout= xTimeOut;
sTXData.bRAW = bRAW;
sTXData.byMedia = byMedia;
if(xQueueSend(g_xProtocolTXEvent, (void*)&sTXData, ( portTickType ) 10))
{
return TRUE;
}
return FALSE;
}
if( g_xProtocolTXEvent == 0 )
{
return;
}
You must not exit a task like that. Use vTaskDelete(NULL) instead of return;
Does PROTOCOL_TX just contain the members shown being accessed in your ProtocolSendData() send function? If so then stack overflow is unlikely. You could set configCHECK_FOR_STACK_OVERFLOW to 2 to be a bit more secure, but I don't think that is your problem.
Is ProtocolSendData() ever called from an interrupt? If so then you will need to use xQueueSendFromISR() version.
Which compiler are you using? The state viewer plug in available for Eclipse and IAR will show you how many items are in the queue. If there are items in the queue then you can step through the xQueueReceive() function to see why it thinks its empty.
Have you checked all the http://www.freertos.org/FAQHelp.html items?
Yes, PROTOCOL_TX only contains the data shown...
I have configCHECK_FOR_STACK_OVERFLOW to 1 without anything. I know the configCHECK_FOR_STACK_OVERFLOW works. been there :-)
ProtocolSendData() is never send called from a ISR. It can be called from 3 different tasks.
I' usin KEIL MDK and I can see the the queue values. There are items in the queue.
I then step into the xQueueReceive(..) function, still with queue item at 5. The call stack also are correct.
Then after "taskENTER_CRITICAL" there was a task switch i guess. The call stack changed to a different part of my application (the call stack contained other functions that also uses xQueueReceive(..)) and the queue item was different as well.
I thin there was a contents switch during the debug steps. Maybe I can make the debugger disable all interrupts while stepping through code?
Thomas