Skip to content

Commit f5f32da

Browse files
author
Daniel Kroening
authored
Merge pull request diffblue#2364 from smowton/smowton/fix/autodetect-default-cxx-dialect
C/C++ frontends: select standard using the same rules as the compiler we emulate
2 parents d437f60 + 7210136 commit f5f32da

File tree

7 files changed

+168
-25
lines changed

7 files changed

+168
-25
lines changed

.travis.yml

+76-5
Original file line numberDiff line numberDiff line change
@@ -103,7 +103,9 @@ jobs:
103103
- parallel
104104
- libc6-dev-i386
105105
before_install:
106-
- mkdir bin ; ln -s /usr/bin/gcc-5 bin/gcc
106+
- mkdir bin
107+
- ln -s /usr/bin/gcc-5 bin/gcc
108+
- ln -s /usr/bin/g++-5 bin/g++
107109
# env: COMPILER=g++-5 SAN_FLAGS="-fsanitize=undefined -fno-sanitize-recover -fno-omit-frame-pointer"
108110
env:
109111
- COMPILER="ccache /usr/bin/g++-5"
@@ -136,7 +138,9 @@ jobs:
136138
- libubsan0
137139
- libc6-dev-i386
138140
before_install:
139-
- mkdir bin ; ln -s /usr/bin/gcc-5 bin/gcc
141+
- mkdir bin
142+
- ln -s /usr/bin/gcc-5 bin/gcc
143+
- ln -s /usr/bin/g++-5 bin/g++
140144
# env: COMPILER=g++-5 SAN_FLAGS="-fsanitize=undefined -fno-sanitize-recover -fno-omit-frame-pointer"
141145
env:
142146
- COMPILER="ccache /usr/bin/g++-5"
@@ -157,12 +161,15 @@ jobs:
157161
packages:
158162
- libwww-perl
159163
- clang-3.7
164+
- g++-5
160165
- libstdc++-5-dev
161166
- libubsan0
162167
- parallel
163168
- libc6-dev-i386
164169
before_install:
165-
- mkdir bin ; ln -s /usr/bin/gcc-5 bin/gcc
170+
- mkdir bin
171+
- ln -s /usr/bin/gcc-5 bin/gcc
172+
- ln -s /usr/bin/c++-5 bin/g++
166173
- export CCACHE_CPP2=yes
167174
# env: COMPILER=clang++-3.7 SAN_FLAGS="-fsanitize=undefined -fno-sanitize-recover=undefined,integer -fno-omit-frame-pointer"
168175
env:
@@ -184,11 +191,14 @@ jobs:
184191
packages:
185192
- libwww-perl
186193
- clang-3.7
194+
- g++-5
187195
- libstdc++-5-dev
188196
- libubsan0
189197
- libc6-dev-i386
190198
before_install:
191-
- mkdir bin ; ln -s /usr/bin/gcc-5 bin/gcc
199+
- mkdir bin
200+
- ln -s /usr/bin/gcc-5 bin/gcc
201+
- ln -s /usr/bin/g++-5 bin/g++
192202
- export CCACHE_CPP2=yes
193203
# env: COMPILER=clang++-3.7 SAN_FLAGS="-fsanitize=undefined -fno-sanitize-recover=undefined,integer -fno-omit-frame-pointer"
194204
env:
@@ -212,14 +222,75 @@ jobs:
212222
- g++-5
213223
- libc6-dev-i386
214224
before_install:
215-
- mkdir bin ; ln -s /usr/bin/gcc-5 bin/gcc
225+
- mkdir bin
226+
- ln -s /usr/bin/gcc-5 bin/gcc
227+
- ln -s /usr/bin/g++-5 bin/g++
216228
install:
217229
- ccache -z
218230
- ccache --max-size=1G
219231
- cmake -H. -Bbuild '-DCMAKE_BUILD_TYPE=Release' '-DCMAKE_CXX_COMPILER=/usr/bin/g++-5'
220232
- cmake --build build -- -j4
221233
script: (cd build; ctest -V -L CORE -j2)
222234

235+
# cmake build using g++-7
236+
- stage: Test different OS/CXX/Flags
237+
os: linux
238+
compiler: gcc
239+
cache: ccache
240+
env:
241+
- BUILD_SYSTEM=cmake
242+
addons:
243+
apt:
244+
sources:
245+
- ubuntu-toolchain-r-test
246+
packages:
247+
- g++-7
248+
- libc6-dev-i386
249+
before_install:
250+
- mkdir bin
251+
- ln -s /usr/bin/gcc-7 bin/gcc
252+
- ln -s /usr/bin/g++-7 bin/g++
253+
install:
254+
- ccache -z
255+
- ccache --max-size=1G
256+
- cmake -H. -Bbuild '-DCMAKE_BUILD_TYPE=Release' '-DCMAKE_CXX_COMPILER=/usr/bin/g++-7'
257+
- cmake --build build -- -j4
258+
script: (cd build; ctest -V -L CORE -j2)
259+
260+
# cmake build using clang++-6
261+
- stage: Test different OS/CXX/Flags
262+
os: linux
263+
compiler: clang
264+
cache: ccache
265+
env:
266+
- BUILD_SYSTEM=cmake
267+
addons:
268+
apt:
269+
sources:
270+
- ubuntu-toolchain-r-test
271+
- llvm-toolchain-trusty-6.0
272+
packages:
273+
- libwww-perl
274+
- g++-5
275+
- clang-6.0
276+
- libstdc++-5-dev
277+
- libubsan0
278+
- parallel
279+
- libc6-dev-i386
280+
before_install:
281+
- mkdir bin
282+
# Use gcc/g++ 5 for tests, as Clang doesn't work yet
283+
# See https://github.com/diffblue/cbmc/issues/2370 for details.
284+
- ln -s /usr/bin/gcc-5 bin/gcc-5
285+
- ln -s /usr/bin/g++-5 bin/g++-5
286+
install:
287+
- ccache -z
288+
- ccache --max-size=1G
289+
- cmake -H. -Bbuild '-DCMAKE_BUILD_TYPE=Release' '-DCMAKE_CXX_COMPILER=/usr/bin/clang++-6.0' '-DCMAKE_CXX_FLAGS=-Qunused-arguments'
290+
- cmake --build build -- -j4
291+
script: (cd build; ctest -V -L CORE -j2)
292+
293+
# cmake build on OSX, using default clang
223294
- stage: Test different OS/CXX/Flags
224295
os: osx
225296
compiler: clang

regression/cpp/auto2/test.desc

+1-1
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
CORE
22
main.cpp
3-
3+
-std=c++98
44
^EXIT=0$
55
^SIGNAL=0$
66
--

regression/cpp/auto3/test.desc

+1-1
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
CORE
22
main.cpp
3-
3+
-std=c++98
44
^EXIT=(64|1)$
55
^SIGNAL=0$
66
parse error

src/goto-cc/gcc_mode.cpp

+5
Original file line numberDiff line numberDiff line change
@@ -597,6 +597,11 @@ int gcc_modet::doit()
597597
if(std_string=="gnu++14" || std_string=="c++14")
598598
config.cpp.set_cpp14();
599599
}
600+
else
601+
{
602+
config.ansi_c.c_standard = gcc_version.default_c_standard;
603+
config.cpp.cpp_standard = gcc_version.default_cxx_standard;
604+
}
600605

601606
// gcc's default is 32 bits for wchar_t
602607
if(cmdline.isset("short-wchar"))

src/goto-cc/gcc_version.cpp

+72-16
Original file line numberDiff line numberDiff line change
@@ -31,7 +31,8 @@ void gcc_versiont::get(const std::string &executable)
3131
"bcc 0 0 0\n"
3232
"#else\n"
3333
"gcc __GNUC__ __GNUC_MINOR__ __GNUC_PATCHLEVEL__\n"
34-
"#endif\n";
34+
"#endif\n"
35+
"default_c_standard __STDC_VERSION__\n";
3536
}
3637

3738
// some variants output stuff on stderr, say Apple LLVM,
@@ -52,23 +53,78 @@ void gcc_versiont::get(const std::string &executable)
5253
std::string line;
5354

5455
while(!in.fail() && std::getline(in, line))
55-
if(!line.empty() && line[0] != '#')
56-
break;
57-
58-
auto split = split_string(line, ' ');
56+
{
57+
if(line.empty() || line[0] == '#')
58+
continue;
59+
60+
auto split = split_string(line, ' ');
61+
62+
if(split.size() >= 4)
63+
{
64+
if(split[0] == "gcc")
65+
flavor = flavort::GCC;
66+
else if(split[0] == "bcc")
67+
flavor = flavort::BCC;
68+
else if(split[0] == "clang")
69+
flavor = flavort::CLANG;
70+
71+
v_major = unsafe_string2unsigned(split[1]);
72+
v_minor = unsafe_string2unsigned(split[2]);
73+
v_patchlevel = unsafe_string2unsigned(split[3]);
74+
}
75+
else if(split.size() == 2 && split[0] == "default_c_standard")
76+
{
77+
if(split[1] == "199901L")
78+
default_c_standard = configt::ansi_ct::c_standardt::C99;
79+
else if(split[1] == "201112L")
80+
default_c_standard = configt::ansi_ct::c_standardt::C11;
81+
}
82+
}
5983

60-
if(split.size() >= 4)
84+
if(flavor == flavort::GCC || flavor == flavort::CLANG)
6185
{
62-
if(split[0] == "gcc")
63-
flavor = flavort::GCC;
64-
else if(split[0] == "bcc")
65-
flavor = flavort::BCC;
66-
else if(split[0] == "clang")
67-
flavor = flavort::CLANG;
68-
69-
v_major = unsafe_string2unsigned(split[1]);
70-
v_minor = unsafe_string2unsigned(split[2]);
71-
v_patchlevel = unsafe_string2unsigned(split[3]);
86+
// Grab the default C++ standard. Unfortunately this requires another
87+
// run, as the compiler can't preprocess two files in one go.
88+
89+
temporary_filet cpp_in("goto-gcc.", ".cpp");
90+
temporary_filet cpp_out("goto-gcc.", ".out");
91+
temporary_filet cpp_err("goto-gcc.", ".err");
92+
93+
{
94+
std::ofstream out(cpp_in());
95+
out << "default_cxx_standard __cplusplus\n";
96+
}
97+
98+
int result = run(
99+
executable,
100+
{executable, "-E", "-x", "c++", "-", "-o", "-"},
101+
cpp_in(),
102+
cpp_out(),
103+
cpp_err());
104+
105+
if(result >= 0)
106+
{
107+
std::ifstream in(cpp_out());
108+
std::string line;
109+
110+
while(!in.fail() && std::getline(in, line))
111+
{
112+
if(line.empty() || line[0] == '#')
113+
continue;
114+
115+
auto split = split_string(line, ' ');
116+
117+
if(split.size() == 2 && split[0] == "default_cxx_standard")
118+
{
119+
if(split[1] == "199711L")
120+
default_cxx_standard = configt::cppt::cpp_standardt::CPP98;
121+
else if(split[1] == "201103L")
122+
default_cxx_standard = configt::cppt::cpp_standardt::CPP11;
123+
else if(split[1] == "201402L")
124+
default_cxx_standard = configt::cppt::cpp_standardt::CPP14;
125+
}
126+
}
127+
}
72128
}
73129
}
74130
}

src/goto-cc/gcc_version.h

+12-1
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,8 @@ Date: May 2018
1414
#include <iosfwd>
1515
#include <string>
1616

17+
#include <util/config.h>
18+
1719
class gcc_versiont
1820
{
1921
public:
@@ -34,8 +36,17 @@ class gcc_versiont
3436
BCC
3537
} flavor;
3638

39+
configt::ansi_ct::c_standardt default_c_standard;
40+
configt::cppt::cpp_standardt default_cxx_standard;
41+
3742
gcc_versiont()
38-
: v_major(0), v_minor(0), v_patchlevel(0), flavor(flavort::UNKNOWN)
43+
:
44+
v_major(0),
45+
v_minor(0),
46+
v_patchlevel(0),
47+
flavor(flavort::UNKNOWN),
48+
default_c_standard(configt::ansi_ct::c_standardt::C89),
49+
default_cxx_standard(configt::cppt::cpp_standardt::CPP98)
3950
{
4051
}
4152
};

src/util/irep_ids.def

+1-1
Original file line numberDiff line numberDiff line change
@@ -41,7 +41,7 @@ IREP_ID_ONE(member_name)
4141
IREP_ID_TWO(C_member_name, #member_name)
4242
IREP_ID_TWO(equal, =)
4343
IREP_ID_TWO(implies, =>)
44-
IREP_ID_TWO(iff, <=>)
44+
IREP_ID_TWO(iff, "<=>")
4545
IREP_ID_ONE(and)
4646
IREP_ID_ONE(nand)
4747
IREP_ID_ONE(or)

0 commit comments

Comments
 (0)