调用函数后确定ARM堆栈上使用的绝对字节数?

时间:2012-10-31 22:55:33

标签: assembly stack arm depth raspberry-pi

我正在努力使我的C代码免受我的Raspberry Pi上的堆栈溢出的影响。我是这个的初学者所以请耐心等待一下。有人告诉我,确定调用函数所使用的字节数的一种方法是通过填充知道值(例如0xff)来初始化堆栈上的空间。然后运行该函数,然后向后搜索以查看已知值中已更改了多少堆栈。通过将原始堆栈深度和堆栈深度置于第一个未更改的值之前,我可以确定该函数使用的堆栈数量。对我来说听起来很合理。

我的问题是这个装配对我来说真的很混乱。我一直在阅读我可以使用asm()在我的c代码中嵌入ARM汇编代码,但我不确定如何初始化堆栈内存然后返回并检查它。有没有我可以看到的资源会有所帮助?我对汇编知之甚少,甚至不知道如何形成一个非常好的搜索词。

感谢。

2 个答案:

答案 0 :(得分:2)

这应该很容易在asm中做,只要你知道你可以安全地去多深(你甚至可以把它作为一个参数传递)

.globl fill_stack
fill_stack:
  mov r2,sp
  mvn r3,#0
fsloop:
  stmdb r2!,{r3}
  subs r0,r0,#1
  bne fsloop
  bx lr

以上的C原型是

void fill_stack ( unsigned int );

其中参数是您要填充的32位字的数量。

将asm放在某个文件中说fill_stack.s并将该文件添加到您的c程序的编译器命令行中(或者如果您不使用c编译器那么将其单独组装到对象和链接)。内联汇编更难,不值得努力。

答案 1 :(得分:0)

我认为您不需要在汇编中执行此操作:您可以在C

中执行此操作
void stack_init(unsigned int size)
{
        int i;
        unsigned char mem[size];

        for (i = 0; i < size; i++)
                mem[i] = 0xAA; /* Best not to use 0 or all ones */
}

unsigned int stack_check(unsigned int max)
{
        int i;
        unsigned char mem[max];

        for (i = max - 1; i >= 0; --i) {
                if (mem[i] != 0xAA)
                        break;
        }
        return i + sizeof(int);
}