GCC和Clang都不符合标准C++
Hacker News2026年7月19日 17:32
在C++中,函数类型与"语言链接"相联系:这可以是"C++"、"C"或其他某种实现定义的语言。标准非常明确地说明:具有不同语言链接的两个函数类型是不同的类型,即使它们在其他方面是相同的。这个想法是某些实现的C++函数与C函数可能具有不同的调用约定,因此它们不能混用。然而,GCC和Clang实际上并没有将语言链接信息与类型储存在一起。因此,具有不同语言链接的两个函数可以是相同的: #include <type_traits> extern "C" using c_func = void (); // 这个静态断言应该失败,但并没有失败 static_assert(std::is_same<c_func, void ()>::value); 这也可能在重载接收函数指针参数的函数时导致错误的编译失败: extern "C" using c_func = void (); void f(c_func *) {} void f(void (*)()) {} 上述代码应该可以编译,但是GCC和Clang都认为参数列表是相同的,因此这违反了一个定义原则。个人认为,这并不是GCC或Clang的问题;问题在于标准。也就是说,标准是错误的,应该更新为实现定义。GCC和Clang无法改变它们的行为,因为那将是一个破坏ABI的变化(在名字混淆中的extern "C"函数类型将以不同的方式编码)。而且它们没有理由进行这样的更改:据我所知,在几乎每个平台上,C和C++的调用约定是相同的。
本站免费、广告极少。如果觉得有帮助,可以请我们喝杯咖啡 —— 任何金额都对持续运营有实际帮助。
☕请我喝杯咖啡