此代码是否返回对堆栈上分配的变量的无效引用?或者:
void *f(size_t sz) {
return alloca(sz);
}
或者它是由f(alloca(size), alloca(size))
之类的alloca实现/编译器支持处理的特殊情况吗?
答案 0 :(得分:5)
alloca
在f
的堆栈帧中分配空间。一旦函数返回(它不再是“保留”),你就无法用它做任何有用的事情。
alloca()函数在堆栈帧中分配空间的大小字节 来电者。此临时空间自动释放 调用alloca()的函数返回其调用者。
答案 1 :(得分:2)
这样:
void *f() {
char* pc4 = alloca(4);
...
}
就是这样:
void *f() {
char pc4[4];
...
}
在第二种情况下你也不能在功能之外返回/使用pc4,也不能在第一种情况下做同样的事情。
答案 2 :(得分:1)
是的,代码返回一个无效指针。 alloca
调用无法包含在函数中。如果需要包装alloca
,则仅限于宏包装器。
答案 3 :(得分:0)
alloca()
函数在堆栈框架中分配空间 调用者,并返回指向已分配块的指针。这暂时alloca()
函数从f()
自动释放空间 被称为回报。
这意味着,尝试访问f()
返回的内存将导致未定义的行为,因为{{1}}返回时会释放它。
答案 4 :(得分:0)
正如其他人所说,它会被释放,我真的不知道你怎么能改变这种行为。如果你看一下alloca
如何在amd-64上编译:
pushq %rbp
movq %rsp, %rbp
subq $144, %rsp
movq %rsp, %rax
addq $15, %rax
shrq $4, %rax
salq $4, %rax
leave
ret
你看
1)Alloca实际上并不是函数调用(因为正如你所说,它必须以不同的方式处理堆栈!)
2)当rbp
覆盖rsp
所以可以你得到你所询问的行为(没有编写程序集)?这是一个棘手的问题,我不知道,但似乎可能不是。
答案 5 :(得分:0)
我自己从未使用过alloca,但我在这里读到了“内联问题”: Why is the use of alloca() not considered good practice?
答案“最令人难忘的错误之一......”非常有趣。
因此,当函数超出范围时,内存肯定会被释放。