为什么malloc()返回null,以及STM32F407上的堆需要或剩下多少?

为什么malloc()返回null,以及STM32F407上的堆需要或剩下多少?,c,embedded,malloc,heap,C,Embedded,Malloc,Heap,我刚刚发现我的解码器库无法初始化,因为malloc()无法分配内存,并返回给调用方“NULL” 我尝试了许多可能的场景,包括强制转换和不强制转换,并参考了许多关于malloc()的其他线程,但没有任何效果,直到我将堆大小更改为0x00001400,这显然解决了问题 现在的问题是,我怎样才能知道程序需要多少堆,或者剩下多少堆?数据表上说我的MCU有:“高达192+4 KB的SRAM,包括64 KB的CCM(核心耦合内存)数据RAM”,有人能给我解释一下这意味着什么吗?将其更改为0x00002000

我刚刚发现我的解码器库无法初始化,因为malloc()无法分配内存,并返回给调用方“NULL”

我尝试了许多可能的场景,包括强制转换和不强制转换,并参考了许多关于malloc()的其他线程,但没有任何效果,直到我将堆大小更改为0x00001400,这显然解决了问题

现在的问题是,我怎样才能知道程序需要多少堆,或者剩下多少堆?数据表上说我的MCU有:“高达192+4 KB的SRAM,包括64 KB的CCM(核心耦合内存)数据RAM”,有人能给我解释一下这意味着什么吗?将其更改为0x000020000(8192字节)将导致以下几十个错误:

错误:L6406E:具有任何选择器的执行区域中没有空间

8KB的内存不是该设备的一小部分吗?为什么我不能在0x00001800之外向堆添加更多

Keil在编译后报告的程序大小为:

程序大小:代码=103648 RO数据=45832 RW数据=580 ZI数据=129340


错误:L6406E,是因为您的目标上没有足够的RAM来支持链接器文件,没有神奇的方法来获得更多的RAM,堆栈和堆都使用RAM内存,但在您的情况下,它似乎有足够的内存,但编译器不知道这一点

我的建议是在KeilµVision IDE中使用链接器响应文件,并根据使用情况更新所需的内存部分

链接器命令(或响应)文件仅包含链接器指令。命令文件中未列出要链接的.OBJ文件和.LIB文件。这些由µVision自动从项目文件中获取

开始使用链接器命令文件的最佳方法是让µVision自动为您创建一个链接器命令文件,然后开始进行必要的更改

要从µVision生成命令文件

转到“项目”菜单并选择目标项的选项

单击L166 Misc或L51 Misc选项卡打开miscellaneous链接器选项

选中“使用链接器控制文件”复选框

点击创建。。。按钮这将创建一个链接器控制文件

点击编辑。。。按钮这将打开链接器控制文件进行编辑

编辑命令文件以包含所需的指令

创建链接器命令文件时,所创建的文件包括当前选定的指令

关于您面临的malloc()问题,

所需堆的大小取决于应用程序中所需的内存量,特别是使用malloc和calloc进行动态内存分配所需的内存。 请注意,一些类似C库的“printf”函数也在后台使用动态内存分配

如果您使用keilide编译源代码,那么可以通过修改启动文件来增加堆大小

;******************************************************************************
;
; <o> Heap Size (in Bytes) <0x0-0xFFFFFFFF:8>
;
;******************************************************************************
Heap    EQU     0x00000000
;******************************************************************************
;
; Allocate space for the heap.
;
;******************************************************************************
        AREA    HEAP, NOINIT, READWRITE, ALIGN=3
__heap_base
HeapMem
        SPACE   Heap
__heap_limit
;******************************************************************************
******************************************************************************
;
;  堆大小(字节)
;
;******************************************************************************
堆EQU 0x00000000
;******************************************************************************
;
; 为堆分配空间。
;
;******************************************************************************
面积堆,NOINIT,读写,对齐=3
__堆底
希普姆
空间堆
__堆极限
;******************************************************************************
如果您正在使用makeenviront构建应用程序,那么可以在线性文件中简单地更改堆大小

您可以直接从Keil官方网站获得有关该产品的详细信息,请查看以下链接


Jerry James。

错误:L6406E,是因为您的目标上没有足够的RAM来支持链接器文件,没有神奇的方法来获得更多的RAM,堆栈和堆都使用RAM内存,但在您的情况下,它似乎有足够的内存,但编译器没有意识到这一点

我的建议是在KeilµVision IDE中使用链接器响应文件,并根据使用情况更新所需的内存部分

链接器命令(或响应)文件仅包含链接器指令。命令文件中未列出要链接的.OBJ文件和.LIB文件。这些由µVision自动从项目文件中获取

开始使用链接器命令文件的最佳方法是让µVision自动为您创建一个链接器命令文件,然后开始进行必要的更改

要从µVision生成命令文件

转到“项目”菜单并选择目标项的选项

单击L166 Misc或L51 Misc选项卡打开miscellaneous链接器选项

选中“使用链接器控制文件”复选框

点击创建。。。按钮这将创建一个链接器控制文件

点击编辑。。。按钮这将打开链接器控制文件进行编辑

编辑命令文件以包含所需的指令

创建链接器命令文件时,所创建的文件包括当前选定的指令

关于您面临的malloc()问题,

所需堆的大小取决于应用程序中所需的内存量,特别是使用malloc和calloc进行动态内存分配所需的内存。 请注意,一些类似C库的“printf”函数也在后台使用动态内存分配

如果您使用keilide编译源代码,那么可以通过修改启动文件来增加堆大小

;******************************************************************************
;
; <o> Heap Size (in Bytes) <0x0-0xFFFFFFFF:8>
;
;******************************************************************************
Heap    EQU     0x00000000
;******************************************************************************
;
; Allocate space for the heap.
;
;******************************************************************************
        AREA    HEAP, NOINIT, READWRITE, ALIGN=3
__heap_base
HeapMem
        SPACE   Heap
__heap_limit
;******************************************************************************
******************************************************************************
;
;  堆大小(字节)
;
;******************************************************************************
void heapinfo()
{
    typedef int (*__heapprt)(void *, char const *, ...);
    __heapstats( (__heapprt)fprintf, stdout ) ;
}
mem = malloc( some_space ) ;
if( mem == NULL )
{
    heapinfo() ;
    for(;;) ; // wait for watchdog or debugger attach
}

// memory allocated successfully