【问题标题】:Why is _LARGEFILE_SOURCE defined in stdio.h when compiling with g++ but not gcc?为什么在使用 g++ 而不是 gcc 编译时在 stdio.h 中定义了 _LARGEFILE_SOURCE?
【发布时间】:2016-06-14 22:58:21
【问题描述】:

如果下面的代码是用 gcc lfs.c -o lfs 编译的,它什么也不打印。但是,如果使用 g++ lfs.c -o lfs 编译,则会打印“_LARGEFILE_SOURCE defined by stdio.h!”。

#ifdef _LARGEFILE_SOURCE
int largefile_defined_at_start = 1;
#else
int largefile_defined_at_start = 0;
#endif

// This defines _LARGEFILE_SOURCE, but only in C++!
#include <stdio.h>

int main(void) {
#ifdef _LARGEFILE_SOURCE
  if (!largefile_defined_at_start)
    printf("_LARGEFILE_SOURCE defined by stdio.h!");
#endif
  return 0;
}

在任何一种情况下,_LARGEFILE_SOURCE 都不是由编译器定义的:

gcc -dM -E - < /dev/null |grep _LARGEFILE_SOURCE |wc -l
0
g++ -dM -E - < /dev/null |grep _LARGEFILE_SOURCE |wc -l
0

当通过 g++ 前端调用 GCC 时,为什么 stdio.h 会定义 _LARGEFILE_SOURCE?

【问题讨论】:

  • 你在什么平台上编程?你是在针对 glibc 编程吗?
  • _LARGEFILE_SOURCE 反正已经过时了,你为什么认为你需要它?遗留代码?
  • @BaummitAugen 它没有过时。如果你在 i386 Linux 上编译一个 C 程序,你会得到一个 32 位的off_t 默认情况下。 _LARGEFILE_SOURCE 有点需要。
  • @FUZxxl 如果您只使用 #define _FILE_OFFSET_BITS 64 代替,它已经过时了。
  • @FUZxxl _FILE_OFFSET_BITS 64 是标准的 POSIX afaik,就像 _LARGEFILE_SOURCE。虽然后者被称为历史和“新程序不应该使用这个宏;定义 _XOPEN_SOURCE 就像刚刚描述的那样或定义 _FILE_OFFSET_BITS 的值为 64 是实现相同结果的首选机制。” man7.org/linux/man-pages/man7/feature_test_macros.7.html

标签: c++ c gcc large-files large-file-support


【解决方案1】:

因为g++定义了_GNU_SOURCE,它基本上暗示了所有其他的特性宏,比如_LARGEFILE_SOURCE。这些附加宏是在包含&lt;features.h&gt; 标头时定义的,并且大多数系统头文件在文件的早期都包含&lt;features.h&gt;_GNU_SOURCE 是预定义的这一事实对于想要编写可移植 C++ 代码的人来说是一个持续的挫败感。

我相信你可以简单地:

#undef _GNU_SOURCE

但是,这会破坏 libstdc++。哎哟!多么痛苦!这一切都源于 C++ 中最大的设计缺陷之一,即#include 基本上是文本包含。由于大部分 libstdc++ 是在头文件中定义(不仅仅是声明!),这意味着它们会用_GNU_SOURCE 污染您的程序。

如果您需要访问被_GNU_SOURCE 隐藏的接口(例如strerror_r,它完全被_GNU_SOURCE 破坏),那么您只能从不使用任何libstdc++ 的文件中访问这些接口标题。

据我所知,这只是 libstdc++ 的一个问题,所以我认为你也可以通过使用 libc++ 或其他类似的东西来避免这个问题。

【讨论】:

  • 这是一个非常奇怪的设计决定。
  • @FUZxxl:我可能会使用“病态”这个词,但“奇怪”有效。
  • 残酷的选择!我刚刚验证是这种情况,然后接受了您的回答。
猜你喜欢
  • 2011-10-01
  • 1970-01-01
  • 1970-01-01
  • 2015-03-29
  • 2014-04-25
  • 1970-01-01
  • 2015-10-13
  • 1970-01-01
  • 2019-11-15
相关资源
最近更新 更多