调试C中的堆栈溢出?

时间:2014-05-09 06:02:58

标签: c debugging gdb stack-overflow

我有这个示例程序,当使用fstack-protector-all编译时会产生堆栈粉碎。

#include <stdio.h>
#include <stdint.h>


int func(int* value)
{
    uint8_t port = 1;

    *value = port; //Canary value changes at this point when seen in GDB

    return 1;
}

int main()
{
    uint16_t index = 0;

    int ret = func((int*)&index);

}

我不明白这条线有什么问题。是否需要进行类型转换?

2 个答案:

答案 0 :(得分:6)

这是因为int的大小和int16_t的大小不同。 int的大小(通常)是32位(四个字节),而int16_t是16位(两个字节)。

因此,当您将int写入int16_t变量时,您会写两个字节太多,并导致undefined behavior(在这种情况下,&#34;粉碎&#34;堆栈)。

问题更具体是因为您使用指向index的指针调用该函数,该指针是一个16位变量,但该函数需要(并使用其参数)作为32位变量。你不应该在通话中进行演员,因为隐藏了问题但没有解决它。您只需将8位值写入函数内的解除引用指针并不重要,目标仍然是32位变量,编译器将之前将8位值转换为32位值写给记忆。

答案 1 :(得分:2)

由于index的类型为uint16_t,因此只为其分配了16位。通过将index的地址转换为int*,您假装在大多数情况下可以访问超过16位--32位。

*value = port;

您正尝试在尚未分配的位中设置值。由于在该行中使用了未经授权的内存,因此任何事情都可能发生。

相关问题