c - 返回未初始化的、最终未使用的结构是否是未定义的行为?

标签 c language-lawyer c11

如果唯一的后续使用是在如下所示的初始化语句中,那么 UB 是否会返回一个结构而不对其进行初始化:

typedef struct { int x; } s;

s callee(void) {
  s ret;
  return ret;
}

void caller() {
  s dummy = callee();
}

最佳答案

首先考虑这个类似的代码:

s ret;
s dummy = ret;

结构不能有陷阱表示 (C11 6.2.6.1/6)。但是,由于 Itanium 子句 (C11 6.3.2.1/2),此代码会导致未定义的行为,该子句表示使用从未被获取其地址的未初始化自动对象的值会导致 UB。

所以这段代码是明确定义的:

s ret;
&ret;
s dummy = ret;

有关该条款的进一步阅读,请参阅:Is a^a or a-a undefined behaviour if a is not initialized? .

<小时/>

对于带有函数返回值的版本:标准中没有说明返回值是否算作安腾子句中的自动对象。我倾向于说它不是,因为返回值没有被标准描述为对象。但如果熟悉 Itanium ABI 的人能够评论通过返回值传递未初始化的结构是否会触发 NaT 异常,那就太好了。

取而代之的是,我的立场是函数调用版本与上面讨论的赋值版本具有相同的语义,即发布的代码是 UB 但添加 &ret; 使其定义良好。

关于c - 返回未初始化的、最终未使用的结构是否是未定义的行为?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/50751665/

相关文章:

如果在c99中编译时不知道数组的长度,是否可以静态分配数组?

c - 这个程序到底是什么意思? (Shellcoder的手册)

c++ - 在 C++ 中存储局部变量和临时变量的存储术语是什么?

c - 如何在 C 中实现 Go 的 defer() 以便允许声明变量?

c++ - 使用数组地址获取尾后指针

c++ - 为什么新的 VS2013 项目的功能在文件是.cpp 的链接中未解决,但如果文件是.c 则可以

c - memcmp 比较数组的段(删除重复项)

c++ - C++ 中嵌套模板声明的限制

c - 强制读取 volatile 变量

未找到 C11 GCC threads.h?