#malloc #heap-memory #cortex-m3 #newlib
#malloc #куча-память #cortex-m3 #newlib
Вопрос:
Я пытаюсь динамически выделить память, используя malloc от newlib, работающий на cortex-m3 («голый металл»), и я столкнулся с озадачивающей проблемой. Сразу после прошивки устройства malloc и free работают должным образом. Однако, как только я перезагружаю устройство, malloc возвращает только NULL. Все остальное работает, кроме malloc. Есть какие-либо подсказки о том, что может вызвать такое поведение?
Вот мой скрипт компоновщика:
MEMORY
{
FLASH (rx) : ORIGIN = 0x00000000, LENGTH = 512K
SRAM (rwx) : ORIGIN = 0x10000000, LENGTH = 32K
}
/* Section Definitions */
SECTIONS
{
.text :
{
KEEP(*(.isr_vector .isr_vector.*))
*(.text .text.*)
*(.gnu.linkonce.t.*)
*(.glue_7)
*(.glue_7t)
*(.gcc_except_table)
*(.rodata .rodata*)
*(.gnu.linkonce.r.*)
_etext = .;
} > FLASH
__exidx_start = .;
.ARM.exidx : { *(.ARM.exidx* .gnu.linkonce.armexidx.*) } > FLASH
__exidx_end = .;
/*.data : AT (_etext)*/
.data : AT (__exidx_end)
{
_data = .;
*(vtable vtable.*)
*(.data .data.*)
*(.gnu.linkonce.d*)
. = ALIGN(4);
_edata = . ;
} > SRAM
/* .bss section which is used for uninitialized data */
.bss (NOLOAD) :
{
_bss = . ;
*(.bss .bss.*)
*(.gnu.linkonce.b*)
*(COMMON)
. = ALIGN(4);
_ebss = . ;
} > SRAM
.stackarea (NOLOAD) :
{
. = ALIGN(8);
*(.stackarea .stackarea.*)
. = ALIGN(8);
} > SRAM
. = ALIGN(4);
_end = . ;
PROVIDE (end = .);
}
И это из моей карты памяти:
.stackarea 0x10000d3c 0x4
0x10000d40 . = ALIGN (0x8)
*fill* 0x10000d3c 0x4 00
*(.stackarea .stackarea.*)
0x10000d40 . = ALIGN (0x8)
0x10000d40 . = ALIGN (0x4)
0x10000d40 _end = .
0x10000d40 PROVIDE (end, .)
Когда malloc завершается успешно, он начинает выделение с 0x10000d48.
Комментарии:
1. что возвращает ‘mallinfo()’ после сброса?
Ответ №1:
Я не совсем уверен, как это работает на вашем Cortext-M3, но некоторое время назад у меня были некоторые проблемы с управлением памятью на RX62N. В конце концов, я решил заняться собственным управлением памятью, создав большую кучу, а затем выделить память с помощью моих собственных функций API. Я использовал простой связанный список для управления памятью. Таким образом, я могу гарантировать, что он будет работать каждый раз на моей плате и в коде 🙂
Надеюсь, это поможет 🙂 Приветствия!
Ответ №2:
Стек должен иметь более высокий адрес, чем куча.
Стек растет вниз, а куча вверх. Итак, поместите начало стека на последний адрес в SRAM. Куча начинается с метки «_end» и заканчивается в нижней части стека, поэтому попробуйте поместить метку «_end» сразу после метки «_ebss».
например.
/* .bss section which is used for uninitialized data */
.bss (NOLOAD) :
{
_bss = . ;
*(.bss .bss.*)
*(.gnu.linkonce.b*)
*(COMMON)
. = ALIGN(4);
_ebss = . ;
**_end = . ;**
} > SRAM