C ++程序中非常奇怪的堆栈溢出 [英] VERY strange stack overflow in C++ program

查看:161
本文介绍了C ++程序中非常奇怪的堆栈溢出的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

前段时间,我编写了一个程序(Mac OS X,C ++,SDL,FMOD),并且效果不错.但是最近我想扩展它的功能并添加更多代码.现在,当我运行它并尝试测试新功能时,该程序会因SIGABRT而崩溃.

I wrote a program some time ago (Mac OS X, C++, SDL, FMOD) and it perfomed rather good. But lately I wanted to extend its functionality and added some more code to it. And now, when I run it and try to test the new functionality, the program crashes with SIGABRT.

查看调试器,在函数堆栈上,我看到:

Looking into debugger, on function stack I see:

  • _kill
  • kill $ UNIX2003
  • 提高
  • __ abort
  • __ stack_chk_fail
  • odtworz<-我的功能已被修改

据我所知,"__ stack_chk_fail"表示堆栈溢出.但这不是最奇怪的事情.在此功能"odtworz"中,我有一些类似这样的代码:

As far as I know, "__stack_chk_fail" indicates a stack overflow. But that's not the weirdest thing about it. In this function "odtworz", I have some code like this:

...

koniec = 0;
while ( koniec == 0 ) {
    ...
    if (mode == 1) {
        ...
    }
    else if (mode == 2) {
        ...
    }
    else if (mode == 3) {
       piesniOrkiestrowe[0] = '\0'; 
       while ( piesniOrkiestrowe[0] == '\0' ) { 
           losowaPiesn(); 
           char * piesnOrkiestrowa = szukajPiesniOrkiestrowej(); 
           if ( piesnOrkiestrowa != NULL ) 
              strcpy(piesniOrkiestrowe, piesnOrkiestrowa); 
       } 
       char nowyPiesnPlik[25]; 
       sprintf(nowyPiesnPlik, "%sorch/%s", PIESNI_DIR.c_str(), piesniOrkiestrowe);
    }
}

mode是全局变量,之前在函数中设置为值"2".现在想象一下-如果删除第三个if语句(模式== 3),该语句永远不会在此模式下执行,则程序不会崩溃!删除甚至无法执行的代码有助于解决问题!

mode is a global variable and is set to value "2" in a function before. And now imagine - if I delete the third if statement (mode == 3) which never gets executed in this mode, the program doesn't crash! Deleting code that doesn't even get to be executed helps the situation!

现在,我不想删除此代码,因为它用于我程序的其他模式.它在那里工作正常.那么有什么提示我可以搜索的吗?这可能是什么问题?

Now, I don't want to delete this code because it's for other mode of my program. And it works fine there. So any hints where I can search? What could be possibly wrong with this?

推荐答案

不是堆栈溢出错误.当检测到堆栈帧损坏时,将调用__stack_chk_fail.粉碎堆栈的传统方法是缓冲区溢出.导致它的代码不在您的代码段中,而是在点中.

It is not a stack overflow error. __stack_chk_fail is called when stack frame corruption is detected. The traditional way to smash the stack is a buffer overflow. The code that causes it is not in your snippet, it is in the dots.

使用注释中的代码更新问题之后:strcpy和sprintf调用都是堆栈损坏的理想选择.我在原始答案中提到的缓冲区溢出问题.猜一猜:nowyPiesnPlik看起来很小. sprintf()函数将过多的字符写入缓冲区并覆盖"canary".当金丝雀踩踏时,运行时将鸣叫鸡:)

After updating the question with code from a comment: both the strcpy and the sprintf calls are excellent candidates for stack corruption. The buffer overflow problem I mentioned in my original answer. Taking a guess: nowyPiesnPlik looks very small. The sprintf() function will write too many characters to the buffer and overwrite the "canary". When the canary gets stomped on, the runtime will whistle fowl :)

您可以使数组更大.这不是真正的解决方案,请对这些功能使用安全的替代方法,例如snprintf().我将避免提及strncpy().

You could make the array bigger. Not a real solution, use safe alternatives for these functions, like snprintf(). I'll avoid mentioning strncpy().

这篇关于C ++程序中非常奇怪的堆栈溢出的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆