Skip to content

Commit a58ae62

Browse files
authored
exposed -std to define mapping in interface / add support for more -std values / added setting of __STDC_VERSION__ (#242)
1 parent 47bc464 commit a58ae62

3 files changed

Lines changed: 83 additions & 11 deletions

File tree

simplecpp.cpp

Lines changed: 54 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -1254,11 +1254,11 @@ unsigned int simplecpp::TokenList::fileIndex(const std::string &filename)
12541254

12551255

12561256
namespace simplecpp {
1257-
class Macro;
1257+
class Macro;
12581258
#if __cplusplus >= 201103L
1259-
using MacroMap = std::unordered_map<TokenString,Macro>;
1259+
using MacroMap = std::unordered_map<TokenString,Macro>;
12601260
#else
1261-
typedef std::map<TokenString,Macro> MacroMap;
1261+
typedef std::map<TokenString,Macro> MacroMap;
12621262
#endif
12631263

12641264
class Macro {
@@ -2937,14 +2937,16 @@ void simplecpp::preprocess(simplecpp::TokenList &output, const simplecpp::TokenL
29372937
macros.insert(std::make_pair("__DATE__", Macro("__DATE__", getDateDefine(&ltime), files)));
29382938
macros.insert(std::make_pair("__TIME__", Macro("__TIME__", getTimeDefine(&ltime), files)));
29392939

2940-
if (dui.std == "c++11")
2941-
macros.insert(std::make_pair("__cplusplus", Macro("__cplusplus", "201103L", files)));
2942-
else if (dui.std == "c++14")
2943-
macros.insert(std::make_pair("__cplusplus", Macro("__cplusplus", "201402L", files)));
2944-
else if (dui.std == "c++17")
2945-
macros.insert(std::make_pair("__cplusplus", Macro("__cplusplus", "201703L", files)));
2946-
else if (dui.std == "c++20")
2947-
macros.insert(std::make_pair("__cplusplus", Macro("__cplusplus", "202002L", files)));
2940+
if (!dui.std.empty()) {
2941+
std::string std_def = simplecpp::getCStdString(dui.std);
2942+
if (!std_def.empty()) {
2943+
macros.insert(std::make_pair("__STDC_VERSION__", Macro("__STDC_VERSION__", std_def, files)));
2944+
} else {
2945+
std_def = simplecpp::getCppStdString(dui.std);
2946+
if (!std_def.empty())
2947+
macros.insert(std::make_pair("__cplusplus", Macro("__cplusplus", std_def, files)));
2948+
}
2949+
}
29482950

29492951
// TRUE => code in current #if block should be kept
29502952
// ELSE_IS_TRUE => code in current #if block should be dropped. the code in the #else should be kept.
@@ -3336,6 +3338,47 @@ void simplecpp::cleanup(std::map<std::string, TokenList*> &filedata)
33363338
filedata.clear();
33373339
}
33383340

3341+
std::string simplecpp::getCStdString(const std::string &std)
3342+
{
3343+
if (std == "c90" || std == "c89" || std == "iso9899:1990" || std == "iso9899:199409" || std == "gnu90" || std == "gnu89") {
3344+
// __STDC_VERSION__ is not set for C90 although the macro was added in the 1994 amendments
3345+
return "";
3346+
}
3347+
if (std == "c99" || std == "c9x" || std == "iso9899:1999" || std == "iso9899:199x" || std == "gnu99"|| std == "gnu9x")
3348+
return "199901L";
3349+
if (std == "c11" || std == "c1x" || std == "iso9899:2011" || std == "gnu11" || std == "gnu1x")
3350+
return "201112L";
3351+
if (std == "c17" || std == "c18" || std == "iso9899:2017" || std == "iso9899:2018" || std == "gnu17"|| std == "gnu18")
3352+
return "201710L";
3353+
if (std == "c2x" || std == "gnu2x") {
3354+
// Clang 11 returns "201710L"
3355+
return "202000L";
3356+
}
3357+
return "";
3358+
}
3359+
3360+
std::string simplecpp::getCppStdString(const std::string &std)
3361+
{
3362+
if (std == "c++98" || std == "c++03" || std == "gnu++98" || std == "gnu++03")
3363+
return "199711L";
3364+
if (std == "c++11" || std == "gnu++11" || std == "c++0x" || std == "gnu++0x")
3365+
return "201103L";
3366+
if (std == "c++14" || std == "c++1y" || std == "gnu++14" || std == "gnu++1y")
3367+
return "201402L";
3368+
if (std == "c++17" || std == "c++1z" || std == "gnu++17" || std == "gnu++1z")
3369+
return "201703L";
3370+
if (std == "c++20" || std == "c++2a" || std == "gnu++20" || std == "gnu++2a") {
3371+
// GCC 10 returns "201703L"
3372+
return "202002L";
3373+
}
3374+
/*
3375+
if (std == "c++23" || std == "c++2b" || std == "gnu++23" || std == "gnu++2b") {
3376+
// supported by GCC 11+
3377+
return "";
3378+
} */
3379+
return "";
3380+
}
3381+
33393382
#if (__cplusplus < 201103L) && !defined(__APPLE__)
33403383
#undef nullptr
33413384
#endif

simplecpp.h

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -351,6 +351,12 @@ namespace simplecpp {
351351

352352
/** Convert Cygwin path to Windows path */
353353
SIMPLECPP_LIB std::string convertCygwinToWindowsPath(const std::string &cygwinPath);
354+
355+
/** Returns the __STDC_VERSION__ value for a given standard */
356+
SIMPLECPP_LIB static std::string getCStdString(const std::string &std);
357+
358+
/** Returns the __cplusplus value for a given standard */
359+
SIMPLECPP_LIB static std::string getCppStdString(const std::string &std);
354360
}
355361

356362
#if (__cplusplus < 201103L) && !defined(__APPLE__)

test.cpp

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2202,6 +2202,26 @@ static void dateDefine()
22022202
ASSERT_EQUALS('"', dt[12]);
22032203
}
22042204

2205+
static void stdcVersionDefine()
2206+
{
2207+
const char code[] = "#if defined(__STDC_VERSION__)\n"
2208+
" __STDC_VERSION__\n"
2209+
"#endif\n";
2210+
simplecpp::DUI dui;
2211+
dui.std = "c11";
2212+
ASSERT_EQUALS("\n201112L", preprocess(code, dui));
2213+
}
2214+
2215+
static void cpluscplusDefine()
2216+
{
2217+
const char code[] = "#if defined(__cplusplus)\n"
2218+
" __cplusplus\n"
2219+
"#endif\n";
2220+
simplecpp::DUI dui;
2221+
dui.std = "c++11";
2222+
ASSERT_EQUALS("\n201103L", preprocess(code, dui));
2223+
}
2224+
22052225
int main(int argc, char **argv)
22062226
{
22072227
TEST_CASE(backslash);
@@ -2386,5 +2406,8 @@ int main(int argc, char **argv)
23862406
TEST_CASE(timeDefine);
23872407
TEST_CASE(dateDefine);
23882408

2409+
TEST_CASE(stdcVersionDefine);
2410+
TEST_CASE(cpluscplusDefine);
2411+
23892412
return numberOfFailedAssertions > 0 ? EXIT_FAILURE : EXIT_SUCCESS;
23902413
}

0 commit comments

Comments
 (0)