我读过一些关于堆栈、堆以及它们在程序执行中如何使用的文章。这是其中之一。人们总是说,在调用函数时,它的参数以及局部变量都被放置到堆栈中(严格来说这是不正确的,正如 Eric Lippert 在他的文章中所描述的那样,但这不是我现在的问题)。
我的问题是函数的返回值存储在哪里以及如何传递给调用者?没有人说它被放在堆栈上,但仍然没有人说它不是。有人能澄清一下吗?
例如,考虑以下函数:
public DateTime GetTomorrowDate()
{
return DateTime.Now.AddDays(1).Date;
}
Run Code Online (Sandbox Code Playgroud)
我的理解是它将声明一个局部变量作为返回值是否正确?如果是这样,为什么当函数返回并且堆栈帧被破坏时它没有被破坏?它是否在调用者的堆栈帧中声明(即使调用者没有使用它)?或者它可能存储在寄存器中的某个位置(我不相信这一点,因为对于某些自定义结构可能没有合适大小的寄存器)。
有几种策略(我已经使用过)。
可能还有其他的,但这些是一个好的开始。
我的回答是基于将问题阅读为想要总结常用技术。在 C# 上下文中,它适用于 JIT 生成的代码,但不适用于 CIL 本身。
典型的面向堆栈的 VM 语言(包括 CIL)主要通过在函数返回时将值保留在堆栈上来从函数返回值。参数位于其下方,因此函数返回后需要进行一些堆栈清理。
正如 @eric 所说,很难看出这些信息何时有用。显然,从函数返回大值类型可能会对性能产生影响,但这只是预期的。
CIL 有很好的文档记录,但 JIT 编译和可能的其他机制却没有,这将进一步降低任何此类见解的有用性。