【问题标题】:sigaction not initialized gcc 7sigaction未初始化gcc 7
【发布时间】:2019-10-14 13:50:04
【问题描述】:

假设是这个 C 文件:

#include <stdio.h>
#include <signal.h>

void handle(){
    return;
}

int main() {
    struct sigaction action;
    action.sa_handler = &handle;
    printf("%d\n", action.sa_flags);
    return 0;
}

用 gcc-7 (Ubuntu 7.4.0-1ubuntu1~18.04.1) 编译会抛出警告:

src/flags.c:14:2: warning: ‘action.sa_flags’ is used uninitialized in this function [-Wuninitialized]
  printf("%d\n", action.sa_flags);

但是,使用 gcc-5 (Ubuntu 5.4.0-6ubuntu1~16.04.11),没有警告。

使用 gcc-7,sa_flags 值确实没有初始化:

(gdb) x action.sa_flags
0x555545a0:    Cannot access memory at address 0x555545a0

在 gcc-5 中,它得到一个奇怪的值:

(gdb) x action.sa_flags
0x4004a0 <_start>:    0x8949ed31

我不明白为什么:

  • 使用 gcc-7,sa_flags 不会初始化为 0。
  • 对于 gcc-5,sa_flags_start 函数具有相同的地址。

【问题讨论】:

  • 较新版本的编译器给出更多/更好的警告是有道理的。
  • 函数中未初始化的变量/结构变量的元素具有垃圾值,在将它们设置为某些东西之前尝试使用它们是未定义的行为。
  • @Shawn 问题是手册(man sigaction)没有说明这种行为。
  • sa_flags and the _start function have the same address. - sa_flags 包含一个垃圾值,它恰好等于_start 的地址。哪种有意义,可能是 crt0 的剩余部分。
  • 呃……和sigaction()无关,和C语言和implicit initialization有关。

标签: c gcc structure sigaction


【解决方案1】:

struct sigaction action 未在任一编译器中初始化。您设置了action.sa_handler,但所有其他字段仍未初始化。从 gcc-7 开始,编译器足够聪明,可以注意到您只初始化了结构的某些字段,而其他字段未初始化。 Gcc-5 根本就没有那么聪明,但这并不意味着该结构曾经被初始化过。您在 action.sa_flags 中看到的只是调用 main 之前 crt0 代码在堆栈中留下的任何垃圾。

虽然结构中的指针在技术上是错误的,但一般的解决方案是将结构 memset() 设置为 0。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-03-03
    • 1970-01-01
    • 2023-03-12
    相关资源
    最近更新 更多