每个libstdc++版本的`__GLIBCXX__`值

Value of `__GLIBCXX__` for each libstdc++ release

本文关键字:GLIBCXX libstdc++ 版本 每个      更新时间:2023-10-16

__GLIBCXX__包含libstdc++版本的时间戳,例如来自gcc文档(https://gcc.gnu.org/onlinedocs/libstdc++/manual/using_macros.html)

__GLIBCXX__当前版本的libstdc++,采用压缩的ISO日期格式,为无符号长。有关此特定宏在特定版本中的价值的详细信息,请参阅ABI政策和指南附录。

我正在寻找自4.9.0发布以来的所有版本的值(包括像4.8.x这样的较小版本的版本)

libstdc++的文档似乎没有提供这些信息(它只提供了gcc 4.7.0之前的日期)

在哪里可以找到__GLIBCXX__的值?有人有吗?

ABI政策和指南附录(https://gcc.gnu.org/onlinedocs/libstdc++/manual/abi.html)表示

库预定义宏的增量碰撞。对于3.4.0之前的版本,宏为GLIBCPP。对于以后的版本,它是GLIBCXX。(libstdc++项目在其整个源代码中从CPP大量更改为CXX,以允许"C"预处理器CPP宏命名空间。)这些宏被定义为库发布的日期,采用压缩的ISO日期格式,为无符号长。

但随后仅提供高达GCC 4.7.0的宏的值。这里仍然列出了特定GCC发布的日期:

https://gcc.gnu.org/releases.html

但例如,对于发布日期为"2014年7月16日"的GCC 4.9.1,ISO日期格式为20140716,__GLIBCXX__的值为20140617(请注意,7和6已切换)。

您想要的信息无论如何都是无用的,所以您应该用不同的方式解决问题。

GCC 4.9.3是在GCC 5.3之后发布的,所以它在该宏中的日期较晚,所以你不能只做这样的事情:

#if __GLIBCXX__ > 20150422 // GCC 5.1 release

因为4.9.3也是如此,但它并不具备5.1的所有功能。

大多数GNU/Linux发行版也没有发布正式的FSF版本,它们构建快照,其中会有快照的日期,而快照不会出现在任何发布日期列表中。在给定的一天,5.x分支的快照将与6.x分支的某一天的快照具有相同的日期,因此您无法区分它们。

为了回答最初的问题,您可以在shell中执行一个技巧性命令,以获取发布列表和每个发布的__GLIBCXX__值(从v4.1.0开始):

svn list "svn://gcc.gnu.org/svn/gcc/tags" | grep -o "gcc_([^34]_.*|4_[^0]_.*)_release" | xargs -n 1 -I {} sh -c "printf "{}: " && svn cat svn://gcc.gnu.org/svn/gcc/tags/{}/gcc/DATESTAMP"

结果是:

  • 4.1.0:20060228
  • 4.1.1:20060524
  • 4.1.2:20070214
  • 4.2.0:20070514
  • 4.2.1:20070719
  • 4.2.2:20071007
  • 4.2.3:20080201
  • 4.2.4:20080519
  • 4.3.0:20080305
  • 4.3.1:20080606
  • 4.3.2:20080827
  • 4.3.3:20090124
  • 4.3.4:20090804
  • 4.3.5:20100522
  • 4.3.6:20110627
  • 4.4.0:20090421
  • 4.4.1:20090722
  • 4.4.2:20091015
  • 4.4.3:20100121
  • 4.4.4:20100429
  • 4.4.5:20101001
  • 4.4.6:20110416
  • 4.4.7:20120313
  • 4.5.0:20100414
  • 4.5.1:20100731
  • 4.5.2:20101216
  • 4.5.3:20110428
  • 4.5.4:20120702
  • 4.6.0:20110325
  • 4.6.1:20110627
  • 4.6.2:20111026
  • 4.6.3:20120301
  • 4.6.4:20130412
  • 4.7.0:20120322
  • 4.7.1:20120614
  • 4.7.2:20120920
  • 4.7.3:20130411
  • 4.7.4:20140612
  • 4.8.0:20130322
  • 4.8.1:20130531
  • 4.8.2:20131016
  • 4.8.3:20140522
  • 4.8.4:20141219
  • 4.8.5:20150623
  • 4.9.0:20140422
  • 4.9.1:20140716
  • 4.9.2:20141030
  • 4.9.3:20150626
  • 5.1.0:20150422
  • 5.2.0:20150716
  • 5.3.0:20151204
  • 6.1.0:20160427
  • 6.2.0:20160822
  • 6.3.0:20161221
  • 6.4.0:20170704
  • 7.1.0:20170502
  • 7.2.0:20170814
  • 7.3.0:20180125

请注意,这些值来自GCC团队的官方发布。如果您使用的是非官方版本,则值可能略有不同。

您可以使用SVN发布列表作为源生成可能的__GLIBCXX__值列表:

svn list --xml 'https://gcc.gnu.org/svn/gcc/tags' 
    | grep '>gcc.*release' -A4 
    | grep 'name|date' 
    | sed -e 's/<[^>]+>//g' -e 's/T.*$//' -e 's/-//g' 
          -e 's/gcc_|_release//g'  
    | paste - -

GCC团队维护了一个类似的列表,但更自由,并使用分支ascii艺术进行注释:

https://gcc.gnu.org/develop.html#timeline

请注意,多个发布分支并行活动,例如4.8和4.9分支:

4_8_0   20130322
4_8_1   20130531
4_8_2   20131016
4_8_3   20140522
4_8_4   20141219
4_8_5   20150623
4_9_0   20140422
4_9_1   20140716
4_9_2   20141030
4_9_3   20150626
4_9_4   20160803

因此,不幸的是,您不能使用单个日期作为简单的截止值来确定某个发布。

当然,您可以从这个列表中自动生成一些辅助宏。比方说,你需要4.8 GLIBCXX版本的一些变通方法(GCC和不同的clang版本使用),然后你可以定义一个像这样的辅助宏(在包含一些STL头之后):

#if        __GLIBCXX__ == 20130322 
        || __GLIBCXX__ == 20130531 
        || __GLIBCXX__ == 20131016 
        || __GLIBCXX__ == 20140522 
        || __GLIBCXX__ == 20141219 
        || __GLIBCXX__ == 20150623
    #define HAVE_GLIBCXX_4_8     1
#else
    #define HAVE_GLIBCXX_4_8     0
#endif

如果您只是对主要版本感兴趣,并且只需要支持比GCC 7更新的版本,那么您也可以使用_GLIBCXX_RELEASE宏。