Weirdly large task priority

I have a hard fault on my Cortex-M0+. All my tasks have priority 1 (so far).
Using FreeRTOS commit c19b13cdf.

Examing the backtrace, the chip is stuck at tasks.c:4820:

                    /* Place the unblocked task into the appropriate ready
                     * list. */
                    prvAddTaskToReadyList( pxTCB );

Looking at the definition of the macro above:

#define prvAddTaskToReadyList( pxTCB )                                                                     \
    do {                                                                                                   \
        traceMOVED_TASK_TO_READY_STATE( pxTCB );                                                           \
        taskRECORD_READY_PRIORITY( ( pxTCB )->uxPriority );                                                \
        listINSERT_END( &( pxReadyTasksLists[ ( pxTCB )->uxPriority ] ), &( ( pxTCB )->xStateListItem ) ); \
        tracePOST_MOVED_TASK_TO_READY_STATE( pxTCB );                                                      \
    } while( 0 )

The priority value:

(gdb) p pxTCB
$4 = (TCB_t *) 0x20003f70
(gdb) p/x pxTCB->uxPriority
$5 = 0x30000001

This index is naturally out of bound for pxReadyTasksLists[]. Unfortunately, I could not make the debugger descend into that macro, so I am not sure where the debugger is stopped.

My questions are:

  • what could possibly be causing the 0x30 in the MSByte of the priority?
  • is it normal?
  • is the fault caused by the array index out of bound, or is that high value supposed to be cleaned inside the macro, before being used as an array index, e.g. by taskRECORD_READY_PRIORITY?
  • if not that, what could be causing the hard fault?

Seems like a memory corruption. Can you examine other fields in TCB and see if those look okay?

No.

Most likely, out of bounds access is causing the fault.

Here is the content of the TCB:

(gdb) p/x *pxTCB
$9 = {
  pxTopOfStack = 0x20003e70,
  xStateListItem = {
    xItemValue = 0x247a,
    pxNext = 0x0,
    pxPrevious = 0x35,
    pvOwner = 0x20003f70,
    pxContainer = 0x0
  },
  xEventListItem = {
    xItemValue = 0x4,
    pxNext = 0x0,
    pxPrevious = 0x0,
    pvOwner = 0x20003f70,
    pxContainer = 0x0
  },
  uxPriority = 0x30000001,
  pxStack = 0x20003768,
  pcTaskName = {0x74, 0x41, 0x0, 0x20, 0xb0, 0x3f, 0x0, 0x20, 0x43, 0xe0, 0x0, 0x10, 0xff, 0xff, 0xff, 
    0xff},
  uxBasePriority = 0x7,
  uxMutexesHeld = 0x20004150,
  pvThreadLocalStoragePointers = {0x30000000, 0x20003fc8, 0x1000e15d, 0xffffffff, 0x8},
  ulNotifiedValue = {0x20004150, 0x1000e015, 0x6},
  ucNotifyState = {0x1, 0x0, 0x0},
  ucDelayAborted = 0x0
}

Sadly, I cannot really make sense of most values in there. The task name seems to be “tA”, not a name I created, at least.

The pointers in the stack seem legit.

The first element of TreadLocalStoragePointers seems off.

The notifiedValues seem a bit crazy to me.

Does this look like memory corruption?

I am also confused by the value of pxTopOfStack in the call to pxPortInitialiseStack:

#6  0x10015bf4 in pxPortInitialiseStack (pxTopOfStack=0x80200012, pxCode=0x38bd8046, 
    pvParameters=0xbd46c060) at /projroot/vendor/FreeRTOS-Kernel/portable/GCC/ARM_CM0/port.c:172

But I am not sure what I should be expecting there.

At least, the memory corruption was consequent, so I could put a watchpoint on that priority value (yes, always the same address in the stack, I love deterministic bugs).

It turns out that a printf was corrupting the stack. The task running that code had too little memory allocated. This is not the first time this happens to me, I would need a better method to catch when my tasks write outside their allocated memory…

printf family of functions are known for consuming large amount of stack. Glad that you figured!