2013-07-19 214 views
0

我一直在研究有关缓冲数组缓冲区溢出

#include <iostream> 

using namespace std; 

int main() 
    { 
char input[3]; 
for(int i=0;i<100;i++){ 
    cin>>input[i]; 
    } 
return 0; 
} 

程序推移和不停止,并没有溢出的迹象(2 Linux系统测试)

发生,如果相同的I交换:

cin>>input[i]; 

有:

input[i]='a'; 
+3

这不会溢出堆栈,即写入超过数组的末尾。很明显,你没有很努力地学习......顺便说一句,把环路大小改为4100,尽管仍然没有保证,但你更有可能得到一个崩溃或某事 –

+0

是啊对不起,我没有读你回答完全。然而,在很多教程中,他们使用这样的代码来编辑函数的ret地址。 – user2455103

+0

它不是堆栈溢出,而是缓冲区溢出。 – syam

回答

2

这是一个缓冲区溢出,而不是堆栈溢出。该代码会垃圾堆栈,但如果幸运的话,您可能会看到访问冲突崩溃。它不会触发堆栈溢出,只有在调用过多的函数时才会发生 - 通常是通过递归。

void f() 
{ 
    f(); // <-- stack overflow sure to happen 
} 

如果您正在寻找可能发生的事情,我们无法保证它会发生。写入数组末尾是未定义的行为。如果系统检测到你正在做什么,它几乎肯定会让你崩溃,但是如果你只是覆盖了实际上属于你的进程的内存,那么直到你写完结束才会发生。

+0

“堆栈溢出肯定会发生”,除非优化器优化出来... –

+0

啊现在呢,是的,我无法区分两者,直到现在。对不起你的时间。 – user2455103

+0

haha​​ ok true - 因此,在未优化的调试版本上运行该程序,您可能会遇到堆栈溢出问题。 – Joel

1

参见What and where are the stack and heap?

如果您产生一个无休止地调用自己的函数,您将很快得到堆栈溢出。每个函数调用都会占用堆栈空间,并且很快就会耗尽堆栈空间!

void f() 
{ 
    f(); 
} 

在Visual Studio 2012,该代码甚至还制作了警告

warning C4717: 'f' : recursive on all control paths, function will cause runtime stack overflow 

的功能并没有得到上的Visual Studio 2012优化掉了,但尽管如此,作为@MooingDuck指出,编译器可相当聪明地发现代码中的优化和潜在的错误。

当您的程序崩溃时,堆栈溢出的告示符号会在程序的调用堆栈中反复出现相同的函数!可能更好地看看它现在看起来如何,所以你现在如何在将来如何识别它...

+0

空功能可以优化出 –

+0

@ Mooing哈哈!谢谢,我会投资。我通常很迂腐,避免这样的优化... – TooTone