C 如何编写返回堆栈指针的函数

C 如何编写返回堆栈指针的函数,c,x86,powerpc,stack-frame,C,X86,Powerpc,Stack Frame,在阅读了以下内容后,我了解到不存在这样的东西(至少不是“便携的”) 然而,我在mono代码库中看到以下内容,返回指向堆栈的指针: static void * return_stack_ptr () { gpointer i; return &i; } 我很惊讶上面的代码甚至可以在诸如PowerPC之类的arch上工作,我本以为这只能在x86上工作(也许只有gcc) 这在PowerPC上可以使用吗?堆栈的目的是支持函数调用和局部变量。如果您的系统有一个堆栈,它将使用它,并

在阅读了以下内容后,我了解到不存在这样的东西(至少不是“便携的”)

然而,我在mono代码库中看到以下内容,返回指向堆栈的指针:

static void *
return_stack_ptr ()
{
    gpointer i;
    return &i;
}
我很惊讶上面的代码甚至可以在诸如PowerPC之类的arch上工作,我本以为这只能在x86上工作(也许只有gcc)


这在PowerPC上可以使用吗?

堆栈的目的是支持函数调用和局部变量。如果您的系统有一个堆栈,它将使用它,并在那里分配局部变量。因此,假设局部变量的地址指向堆栈中的某个地方是非常合理的。这并不特定于x86或gcc——这是一个相当普遍的想法

但是,使用指向不存在的变量的指针(即,在它超出范围后)是未定义的行为。所以这个函数不能保证做任何有意义的事情。事实上,“聪明”的编译器可以检测到您的程序使用了未定义的行为,并将您的代码替换为无操作(并称之为“性能优化”)

或者,“wise”编译器可以识别函数返回指向堆栈的指针,并使用硬件堆栈指针将其内联


这两个选项都不保证-此代码不可移植。

堆栈的目的是支持函数调用和局部变量。如果您的系统有一个堆栈,它将使用它,并在那里分配局部变量。因此,假设局部变量的地址指向堆栈中的某个地方是非常合理的。这并不特定于x86或gcc——这是一个相当普遍的想法

但是,使用指向不存在的变量的指针(即,在它超出范围后)是未定义的行为。所以这个函数不能保证做任何有意义的事情。事实上,“聪明”的编译器可以检测到您的程序使用了未定义的行为,并将您的代码替换为无操作(并称之为“性能优化”)

或者,“wise”编译器可以识别函数返回指向堆栈的指针,并使用硬件堆栈指针将其内联


这两个选项都不保证-此代码不可移植。

没有可移植函数可以返回指向C中堆栈的指针。只有不同程度的不可移植性。这种东西依赖于平台和编译器。PowerPC ABI确实有堆栈内存的概念,但是编译器可能会选择将变量
i
放入堆栈以外的另一个内存中。尽管如此,我还是认为它可以与任何主流的PowerPC配合使用compiler@atturri:如果您(正确)使用变量的地址,编译器必须将变量
i
放在内存中的某个位置。别无选择。@atturri:“堆栈”是一个非正式术语,表示“存储局部变量的内存区域”。根据定义,
&i
指向堆栈内部。但是,不能保证“堆栈”是一个连续的内存区域,或者
&i
位于任意一端,或者您可以在
&i
上执行指针算法。没有可移植函数可以在C中返回指向堆栈的指针。只有不同程度的不可移植性。这种东西依赖于平台和编译器。PowerPC ABI确实有堆栈内存的概念,但是编译器可能会选择将变量
i
放入堆栈以外的另一个内存中。尽管如此,我还是认为它可以与任何主流的PowerPC配合使用compiler@atturri:如果您(正确)使用变量的地址,编译器必须将变量
i
放在内存中的某个位置。别无选择。@atturri:“堆栈”是一个非正式术语,表示“存储局部变量的内存区域”。根据定义,
&i
指向堆栈内部。但是,不能保证“堆栈”是一个连续的内存区域,或者
&i
位于任一端,或者您可以对
&i
执行指针算术。请注意,仅仅拥有一个曾经有效的指针本身并不是唯一的行为。例如,这只是
free(ptr)
返回后的正常状态。请注意,仅仅拥有一个曾经有效的指针本身并不是正常的。例如,这只是
free(ptr)
返回后的正常状态。