- Micro is an STM32F407
- CH_DBG_ENABLE_CHECKS is TRUE
- CH_DBG_ENABLE_ASSERTS is TRUE
- CH_DBG_ENABLE_STACK_CHECK is TRUE
- PORT_ENABLE_GUARD_PAGES is TRUE
When trying to use the dynamic thread creation (chThdCreateFromHeap) in ChibiOS 17.6.x, the pointer returned by chHeapAllocAligned may not be aligned to a 32-byte boundary (which is the minimum memory guard size when using the MPU), even if the requested alignment is 32 bytes, it will alway return a pointer aligned to the size of stkalign_t (see macro H_BLOCK).
When the check API is enabled the following check fails in chThdCreateSuspendedI:
chDbgCheck(MEM_IS_ALIGNED(tdp->wbase, PORT_WORKING_AREA_ALIGN) &&
MEM_IS_ALIGNED(tdp->wend, PORT_STACK_ALIGN) &&
(tdp->wend > tdp->wbase) &&
(((size_t)tdp->wend - (size_t)tdp->wbase) >= THD_WORKING_AREA_SIZE(0)));
As tdp->wbase is not aligned to 32 bytes.
Now I am not using chThdCreateFromHeap since I don't want the thread to be started immediately. I have a custom function that realigns pointer returned by chHeapAllocAligned to a 32-byte boundary - only problem is that it may waste up to 32 bytes of RAM in the process:
void* wsp = chHeapAllocAligned(NULL, size + PORT_WORKING_AREA_ALIGN, PORT_WORKING_AREA_ALIGN);
ASSERT(wsp != NULL);
uint8_t* tmp = (uint8_t*)wsp;
tmp = (uint8_t*)(((uint32_t)tmp) & ~((uint32_t)PORT_WORKING_AREA_ALIGN - 1));
if (tmp != wsp) {
tmp += PORT_WORKING_AREA_ALIGN; // move to next 32-byte alignment
} else {
size += PORT_WORKING_AREA_ALIGN; // size of working area can be safely increased by 32 bytes
}
wsp = (void*)tmp;
I don't believe this affects any other release branch in ChibiOS since MPU guards were only implemented in 17.6.x release.