Dear @Kuzco
I dis some additional investigations, and basically found 3 issues around the malloc
problem:
- M4 reset sequence
- M4 cache
- Scatter file
M4 Reset Sequence
The reset sequence used in the RpmsgLib V2.2 does only reset the M4 core, but not the whole M4 platform. This leaves the LMEM memory controller and M4 caches in an undefined state.
For a restart, the A7 updated code and data, but this does not update the M4 cache content. Therefore, after an M4 reset, I suspect that the M4 is reading instructions and data partially from the outdated cache, not from the actual RAM which was modified by the A7 before.
The next release V2.3 of the RpMsgLib will do a proper M4 platform reset.
M4 cache
Not all debug solutions take cache memory into account. Therefore it can happen that variables or memory dumps shown in the debugger don’t reflect the actual values.
To make sure to get consistent information, you might want to disable the M4 instruction / data caches by clearing the ENCACHE
bit in the LMEM_PCCCR
and LMEM_PSCCR
registers.
Unfortunately this has an impact on the software performance.
Scatter file
There were 2 issues in the scatter files:
- The reset vector and stack pointer is placed at 0x1fff8000 instead of 0x00000000. This requires the loader on the A7 core to copy the vectors into the correct location, before starting the M4 core. As far as I could see, this is properly handled by the RpMsgLib, so not really an issue.
- Too much space is allocated for global variables. if >30kB of variables are declared, they overlap with the heap and the stack
The correct scatterfile for using the TCM memories looks as follows (initial comments stripped):
#define m_interrupts_start 0x00000000
#define m_interrupts_size 0x00000240
#define m_text_start 0x1FFF8240
#define m_text_size 0x00007DC0
/* m_data_size includes stack and heap */
#define m_data_start 0x20000000
#define m_data_size 0x8000
/* Sizes */
#if (defined(__stack_size__))
#define Stack_Size __stack_size__
#else
#define Stack_Size 0x0400
#endif
#if (defined(__heap_size__))
#define Heap_Size __heap_size__
#else
#define Heap_Size 0x0400
#endif
LR_m_text m_text_start m_text_size { ; load region size_region
ER_m_text m_text_start m_text_size { ; load address = execution address
* (InRoot$$Sections)
.ANY (+RO)
}
RW_m_data m_data_start m_data_size - Stack_Size - Heap_Size { ; RW data
.ANY (+RW +ZI)
}
ARM_LIB_HEAP m_data_start + m_data_size - Stack_Size - Heap_Size EMPTY Heap_Size { ; Heap region growing up
}
ARM_LIB_STACK m_data_start + m_data_size EMPTY -Stack_Size { ; Stack region growing down
}
}
LR_m_interrupts m_interrupts_start m_interrupts_size {
VECTOR_ROM m_interrupts_start m_interrupts_size { ; load address = execution address
* (RESET,+FIRST)
}
}
Best Regards,
Andy