在一个ARM7的问题实现与海湾合作委员会的malloc:malloc的返回NULL [英] Implementing malloc with gcc in an arm7 problems : malloc return NULL

查看:190
本文介绍了在一个ARM7的问题实现与海湾合作委员会的malloc:malloc的返回NULL的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我添加的malloc支持我的固件,我想我想的东西!

我用code的Sourcery G ++精简版库的ARM7TDMI处理器和我的code是根据这个链接中找到的例子:<一href=\"http://e2e.ti.com/support/microcontrollers/stellaris_arm_cortex-m3_microcontroller/f/473/t/44452.aspx#539503\" rel=\"nofollow\">http://e2e.ti.com/support/microcontrollers/stellaris_arm_cortex-m3_microcontroller/f/473/t/44452.aspx#539503

我说我的版本_sbrk的:

 的char * _sbrk(INT增量)
{
    //字符的extern _end; / *链接器定义* /
    静态字符* heap_end;
    字符* prev_heap_end;
    注册的char * stackPtr;    如果(heap_end == 0)
    {
        //第一次分配
        heap_end = HEAP_END;
    }    prev_heap_end = heap_end;    //获取当前堆栈指针
    ASM(MOV%0,SP \\ n \\ t的:= R(stackPtr));    如果(heap_end +增量&GT; stackPtr){
        返回NULL; //错误 - 没有更多的记忆
        //写(1,堆和栈碰撞\\ n,25);
        //中止();
    }
    heap_end + =增量;
    回报(字符*)prev_heap_end;
}

由SBRK使用的一些定义:

 的#define SDRAM_SIZE 16 * 1024 * 1024
#定义heap_base的_ebss
的#define HEAP_END((_stext + SDRAM_SIZE)-1)
#定义HEAP_SIZE HEAP_END - heap_base的

(_ EBSS和_stext来自我的连接文件)

下面是我的主,我做了一个简单的malloc /免费电话:

 无效C_main(无效)
{
  字符* testmalloc = 0;
  / *初始化堆描述符指针* /
  pHeapDesc​​riptor = __rt_embeddedalloc_init((无效*)heap_base的,HEAP_SIZE);
  testmalloc =的malloc(2048);
  免费(testmalloc);
}

我运行这个程序步模式。当我调用malloc,它最终叫我_sbrk执行,返回值(prev_heap_end)有一个期望值,但是当程序返回到主力,testmalloc值为NULL(某处GCC库中,prev_heap_end丢失)。

是否有人有一个想法是什么,我做错了?

不知道这是否会有所帮助,但这是我的gcc编译参数:

 臂无 -  EABI-GCC -march = ARMV4T -mcpu = ARM7TDMI -dp -c
-Wa,-adhlns =../../基地/库/ PA / main.o.lst-fmessage长度= 0
-fno零初始化功能于BSS -MMD -MP -MF../../基地/库/ PA / main.d
-MT../../基地/库/ PA / main.d-fpic -mlittle端-Wall -g3 -gdwarf-2
../../Base/Hardintrf/Mezzanine/main.c -o../../基地/库/ PA / main.o中

在此先感谢您的帮助!


解决方案

 如果(heap_end == 0)
{
    //第一次分配
    heap_end = HEAP_END;
}

这应该阅读:

 如果(heap_end == 0)
{
    //第一次分配
    heap_end = heap_base的;
}

所以你不要在你堆年底启动堆...你可能想要想出一个更好的名字为变量,然后heap_end避免在首位这种混乱。

此外,你不需要使用register修饰符正确地使你的内联汇编工作。编译器是足够聪明,为你做的。

I am adding malloc support in my firmware and I think I'm missing something!

I use code sourcery g++ lite library for an arm7tdmi processor and my code is based on the example found in this link : http://e2e.ti.com/support/microcontrollers/stellaris_arm_cortex-m3_microcontroller/f/473/t/44452.aspx#539503

I added my version of _sbrk :

char * _sbrk(int incr)
{
    //extern char _end; /* Defined by the linker */
    static char *heap_end;
    char *prev_heap_end;
    register char* stackPtr;

    if (heap_end == 0)
    {
        // first allocation
        heap_end =HEAP_END;
    }

    prev_heap_end = heap_end;

    // get current stack pointer
    asm ("mov %0, sp\n\t" : "=r" (stackPtr) );



    if (heap_end + incr > stackPtr) {
        return NULL;// error - no more memory
        //write (1, "Heap and stack collision\n", 25);
        //abort ();
    }
    heap_end += incr;
    return (char*) prev_heap_end;
}

Some defines used by sbrk :

#define SDRAM_SIZE 16*1024*1024        
#define HEAP_BASE  _ebss
#define HEAP_END ((_stext + SDRAM_SIZE) -1)
#define HEAP_SIZE HEAP_END - HEAP_BASE

(_ebss and _stext come from my linker file)

Here's my main where I did a simple malloc/free call :

void C_main ( void)
{
  char * testmalloc=0;
  /* Initialize "Heap Descriptor" pointer */
  pHeapDescriptor =  __rt_embeddedalloc_init ((void*)HEAP_BASE,HEAP_SIZE);
  testmalloc = malloc(2048);
  free(testmalloc);
}

I run this program in step mode. When I call malloc, it eventually call my _sbrk implementation, the return value (prev_heap_end) have an expected value, but when the program return to the main, the testmalloc value is NULL (somewhere in the gcc library, the prev_heap_end is lost).

Does someone have an idea of what I'm doing wrong?

Don't know if that will help, but this is my gcc compilation parameter :

arm-none-eabi-gcc  -march=armv4t -mcpu=arm7tdmi -dp -c 
-Wa,-adhlns="../../Base/Lib/Pa/main.o.lst" -fmessage-length=0 
-fno-zero-initialized-in-bss -MMD -MP -MF"../../Base/Lib/Pa/main.d" 
-MT"../../Base/Lib/Pa/main.d" -fpic -mlittle-endian -Wall -g3 -gdwarf-2  
../../Base/Hardintrf/Mezzanine/main.c -o"../../Base/Lib/Pa/main.o"

Thanks in advance for any help!

解决方案

if (heap_end == 0)
{
    // first allocation
    heap_end = HEAP_END;
}

This should read:

if (heap_end == 0)
{
    // first allocation
    heap_end = HEAP_BASE;
}

So you don't start your heap at the end of your heap... You might want to think up a better name for that variable then heap_end to avoid this confusion in the first place.

Also you don't need to use the register modifier to make your inline assembly work correctly. The compiler is smart enough to do that for you.

这篇关于在一个ARM7的问题实现与海湾合作委员会的malloc:malloc的返回NULL的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆