如何在C中检测变量未初始化/捕获SEGFULT

如何在C中检测变量未初始化/捕获SEGFULT,c,segmentation-fault,signals,C,Segmentation Fault,Signals,我目前有一个程序,需要测试作为参数传入的变量是否未初始化。到目前为止,这在C中似乎很难做到,所以我的下一个想法是调用一个信号处理程序来捕获SEGFULT。但是,我的代码在尝试访问未初始化变量时没有调用信号处理程序,如下所示: void segfault_sigaction(int signal, siginfo_t *si, void *arg) { printf("Caught segfault at address %p\n", si->si_addr); exit(0

我目前有一个程序,需要测试作为参数传入的变量是否未初始化。到目前为止,这在C中似乎很难做到,所以我的下一个想法是调用一个信号处理程序来捕获SEGFULT。但是,我的代码在尝试访问未初始化变量时没有调用信号处理程序,如下所示:

void segfault_sigaction(int signal, siginfo_t *si, void *arg)
{
    printf("Caught segfault at address %p\n", si->si_addr);
    exit(0);
}

void myfree(void*p, char * file, int line){

    struct sigaction sa;

    memset(&sa, 0, sizeof(sigaction));
    sigemptyset(&sa.sa_mask);
    sa.sa_sigaction = segfault_sigaction;
    sa.sa_flags   = SA_SIGINFO;

    sigaction(SIGSEGV, &sa, NULL);

    char up = *((char*)p); //Segfault

编辑:在Linux系统上

如果未初始化指针,则指针没有默认值。有时它是
NULL
(如果
p
NULL
,您可以捕获
SIGSEGV
),有时它指向一个有效内存,看起来一切正常。他们拥有的价值就是他们现在正在使用的内存中的垃圾。至于您的问题,我建议您编写自己版本的
malloc()
free()
,在分配内存的头上放一个神奇的数字,并测试释放时它是否仍然存在。

如果您没有初始化指针,指针就没有默认值。有时它是
NULL
(如果
p
NULL
,您可以捕获
SIGSEGV
),有时它指向一个有效内存,看起来一切正常。他们拥有的价值就是他们现在正在使用的内存中的垃圾。至于您的问题,我建议您编写自己版本的
malloc()
free()
,在分配内存的头上放一个神奇的数字,并测试释放时它是否仍然存在。

尝试使用memcheck工具。它可以检测未初始化的内存访问以及许多其他无效访问模式。可以找到一个教程。添加--track origins=yes参数(需要3.4.0版)可以更轻松地查找未初始化内存的使用情况。

尝试使用memcheck工具。它可以检测未初始化的内存访问以及许多其他无效访问模式。可以找到一个教程。添加--track origins=yes参数(需要3.4.0版)可以更容易地找到未初始化内存的使用情况。

这不是一个好主意。如果程序试图使用未初始化的变量,那么它总是一个bug。找到这个bug的正确方法是使用一个启用了所有警告的好编译器,或者更好的是使用一个静态分析工具。在开发程序时,应该发现并修复错误。不是在运行时

此外,通过良好的程序设计,调用方负责向函数传递正确的参数。函数本身根本不需要关心调用方。如果引用传递了不正确的参数,则所有下注都将关闭

访问未初始化指针指向的内存会导致未定义的行为,包括以下结果:

  • 存在分割错误
  • 程序崩溃了
  • 什么也没发生,但程序开始以奇怪的方式运行
  • 什么也没发生,程序似乎运行得很好

如果你这样做是因为你想要防御编程,那么你应该考虑对变量值进行某种明智的检查,最好是通过断言()或StasyAsjtAuthor()。p> 这不是个好主意。如果程序试图使用未初始化的变量,那么它总是一个bug。找到这个bug的正确方法是使用一个启用了所有警告的好编译器,或者更好的是使用一个静态分析工具。在开发程序时,应该发现并修复错误。不是在运行时

此外,通过良好的程序设计,调用方负责向函数传递正确的参数。函数本身根本不需要关心调用方。如果引用传递了不正确的参数,则所有下注都将关闭

访问未初始化指针指向的内存会导致未定义的行为,包括以下结果:

  • 存在分割错误
  • 程序崩溃了
  • 什么也没发生,但程序开始以奇怪的方式运行
  • 什么也没发生,程序似乎运行得很好

如果你这样做是因为你想要防御编程,那么你应该考虑对变量值进行某种明智的检查,最好是通过断言()或StasyAsjtAuthor()。p> 这与操作系统相关,是您在问题中未指定的重要信息。访问未初始化的变量不一定会导致segfault

sizeof(sigaction)
应该是
sizeof(struct sigaction)
sizeof sa
未初始化表示内容未定义。一般来说,您无法“检测”到这一点,但许多编译器都能够在使用潜在未赋值变量时发出警告。这与操作系统有关,是您在问题中未指定的重要信息。访问未初始化的变量不一定会导致segfault
sizeof(sigaction)
应该是
sizeof(struct sigaction)
sizeof sa
未初始化意味着内容未定义。一般来说,您无法“检测”这一点,但许多编译器能够在使用潜在未赋值变量时发出警告。要限定“有时”更多:这取决于编译器、操作系统和编译器标志。例如,在没有优化的情况下,某些编译器会用0初始化所有新分配的内存。在发行版中,这可能会被随机数据覆盖。最好使用LogicG8建议的工具,如valgrind。要限定“有时”更多:这取决于编译器、操作系统和编译器标志。例如,在未进行优化的情况下,某些编译器会使用0初始化所有新分配的内存。在发行版中,这可能会被随机数据覆盖。最好按照LogicG8的建议使用valgrind等工具。