The following snippet generates compilation errors on adding -pedantic
and -Werror
on compilers that are a bit old.
#include <cstdint>
#include <iostream>
int add(int a, int b){
return a + b;
}; // <-- stray semicolon
int main (){
return 0;
}
However this does not happen newer compiler versions. Please find a matrix of gcc
(10.x, 11.x) and clang
(5.x, 6.x) demonstrating the difference at https://godbolt.org/z/KWeb8WTxz.
I have two parts to my question:
- Why is this not triggered in recent compilers?
- Is it possible to enable the old behaviour in recent versions of
clang
orgcc
?
2
1 Answer
Starting in C++11, extra semicolons ;
(aka empty-declarations) at the global level are valid. I believe this is occasionally useful for writing macros.
As such, GCC 11 removed -pedantic
diagnostics for an extra ;
when -std=c++11
or later is used. See:
- [GCC Bug 96068] Extra semicolon outside of a function should be allowed after c++11?.
- [GCC Bugs Mailing list] -Wpedantic doesn’t warn about extra semicolons anymore
- [CWG 569] Spurious semicolons at namespace scope should be allowed
You can restore the old behavior by using a C++ standard older than C++11. Both GCC 11 and clang 6 will emit the old diagnostics if you pass -std=c++03
.
2
-
Thank you. My code uses cpp20, so
-std=c++03
is not viable. I am getting this on a CentOS compiler where I build python wheels. Any other static-analysis available that you know of that can help? Could you provide an example where this is useful for macros, as mentioned in this answer?– jerin10 hours ago
-
3
@jerin you could have something like an
IF_DEBUG
macro which removes code outside debug builds. Then,IF_DEBUG(int counter = 0);
to declare a debug-only global variable. You could of course put the semicolon inside the macro argument list, but this may mess up auto-formatting with clang-format, and having the semicolon after a function-style macro is preferred by most developers. On a non-debug build, this macro would expand to nothing and you would have an empty-declaration.– Jan Schultke10 hours ago
Because it's legal in all declaration contexts now. It wasn't before C++14 (in class scope) even though compiles allowed it.
1 hour ago
-Wextra-semi
catches those.1 hour ago