为什么setjmp不保存堆栈?
考虑以下代码:
#include <iostream>
jmp_buf Buf;
jmp_buf Buf2;
void MyFunction()
{
for(int i = 0; i < 5; i++)
{
std::cout << i << std::endl;
if(!setjmp(Buf))
longjmp(Buf2, 1);
}
}
int main (int argc, const char * argv[])
{
while(true)
{
if(!setjmp(Buf2))
{
MyFunction();
break;
}
longjmp(Buf, 1);
}
return 0;
}我所不同的是,代码会在main和函数之间来回跳转,并且每次返回打印递增的数字。
实际发生的情况是,它先打印0,然后再打印1无数次。这就好像当它跳回函数时,堆栈被重置为默认值。它为什么要这么做?有什么方法可以让它也保存堆栈吗?
我知道在编码风格和可读代码方面,setjmp和longjmp甚至比goto更差,但我现在正在试验,这些代码可能永远不会出现可用的应用程序。
发布于 2011-08-29 06:31:29
因为不幸的是setjmp不是这样工作的。setjmp将当前指令指针和寄存器集复制到跳转缓冲区,但不复制堆栈(显然是因为堆栈很大)。看起来你想使用一些基于协程的技术。如果你想自己做到这一点,请查看ucontext过程(ucontext.h) http://compute.cnr.berkeley.edu/cgi-bin/man-cgi?ucontext.h+3,它们将帮助你分配和管理额外的线程堆栈。
或者,您可以使用Russ Cox的libtask (http://swtch.com/libtask/),它将帮助您完成此任务。或者,如果你想自己做这件事,你应该看一看libtask代码(也可以通过该链接获得)。它非常容易阅读,所以它是一个很好的资源。
https://stackoverflow.com/questions/7224358
复制相似问题