Is there a standard definition for __cplusplus in c++14?

C++C++14

C++ Problem Overview


I'm looking to setup some preprocessor stuff, and I'd like a more exact number for what __cplusplus in C++14 should be defined as. Is there one mandated by the standard?

C++ Solutions


Solution 1 - C++

N3936* §16.8 [cpp.predefined]/p1:

> 1 The following macro names shall be defined by the implementation: > > __cplusplus > > The name __cplusplus is defined to the value 201402L when > compiling a C++ translation unit.

N3936 is the final working draft that became C++14, and the number 201402L is consistent with the meeting at which the C++14 standard is sent out for final balloting (February 2014).

*Those interested in obtaining a copy of the C++ standard should check out https://stackoverflow.com/questions/81656/where-do-i-find-the-current-c-or-c-standard-documents</sub>

Solution 2 - C++

cppreference has information on the standard values of the __cplusplus macro in the section "Predefined macros." Currently the standard values are:

199711L (C++98 or C++03)
201103L (C++11)
201402L (C++14)
201703L (C++17)
202002L (C++20)

The macro's value for any given version isn't firmly established until the final standard is published. Therefore, as of June 2019, there was no way to know what the macro value for C++2a would be (and as of Feb 2021 there's no way to know what the value will be for C++2b).

Library vendors typically gate their "C++2a" features on #if __cplusplus > 201703L, and their "C++2b" features on __cplusplus > 202002L, and so on.

Compiler vendors with a "C++2a" mode simply picked any arbitrary value for __cplusplus that made the library vendors' checks happy:

GCC (8.x thru 10.x) -std=c++2a mode uses __cplusplus == 201709L.
Clang (5.x thru 9.x) -std=c++2a mode uses __cplusplus == 201707L.
Microsoft Visual Studio (19.20 thru 19.28) /std:c++latest mode uses __cplusplus == 201705L if and only if you pass /Zc:__cplusplus! Otherwise it uses 199711L. So watch out for that!

How have transitions historically been handled?:

Clang 4.0.1 -std=c++1z set __cplusplus == 201406L. Clang 5.0.0 introduced -std=c++17 and -std=c++2a, made -std=c++1z a synonym for -std=c++17, and bumped the macro (no matter which of 17/1z you used) to the standard value 201703L. Clang 10.0 introduced -std=c++20, made -std=c++2a a synonym for -std=c++20, and bumped the macro to the standard value 202002L. As of Feb 2021, Clang has no formal "C++2b" mode.

GCC 5.1 introduced -std=c++1z and -std=c++17 as synonyms out of the gate, setting __cplusplus == 201500L. GCC 7.1 bumped the value (no matter which spelling you used) to the standard value of 201703L. GCC 8.1 introduced -std=c++2a with __cplusplus == 201709L. GCC 10.1 introduced -std=c++20 as a synonym for -std=c++2a (but left the macro at 201709L). As of Feb 2021, GCC trunk has introduced -std=c++2b with __cplusplus == 202100L.

Oddly, according to Godbolt Compiler Explorer, MSVC bumped the macro for -std:c++latest mode from 201704L to 201705L sometime between MSVC 19.16 and 19.20. As of Feb 2021, as far as I know, MSVC has no formal "C++20" mode.

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
QuestionMichael GazondaView Question on Stackoverflow
Solution 1 - C++T.C.View Answer on Stackoverflow
Solution 2 - C++QuuxplusoneView Answer on Stackoverflow