Opened 3 years ago

Closed 3 years ago

Last modified 3 years ago

#2871 closed defect (fixed)

lib/iostream/mm.cpp:Fails to build with GCC 6: declaration of ... has a different exception specifier

Reported by: Bas Couwenberg Owned by: grass-dev@…
Priority: blocker Milestone: 7.2.0
Component: Compiling Version: svn-releasebranch70
Keywords: iostream, gcc, -fexceptions, throw, noexcept Cc:
CPU: All Platform: Linux

Description

As reported by Martin Michlmayr in Debian Bug #811886:

This package fails to build with GCC 6. GCC 6 has not been released yet, but it's expected that GCC 6 will become the default compiler for stretch.

Note that only the first error is reported; there might be more. You can find a snapshot of GCC 6 in experimental. To build with GCC 6, you can set CC=gcc-6 CXX=g++-6 explicitly.

You may be able to find out more about this issue at https://gcc.gnu.org/gcc-6/changes.html

sbuild (Debian sbuild) 0.67.0 (26 Dec 2015) on dl580gen9-02.hlinux
...
c++ -Wdate-time -D_FORTIFY_SOURCE=2 -g -O2 -fstack-protector-strong -Wformat -Werror=format-security -fPIC  -I/<<PKGBUILDDIR>>/dist.x86_64-pc-linux-gnu/include -I/<<PKGBUILDDIR>>/dist.x86_64-pc-linux-gnu/include    -DPACKAGE=\""grasslibs"\"   -I/<<PKGBUILDDIR>>/dist.x86_64-pc-linux-gnu/include -I/<<PKGBUILDDIR>>/dist.x86_64-pc-linux-gnu/include -DRELDIR=\"lib/iostream\" -o OBJ.x86_64-pc-linux-gnu/rtimer.o -c rtimer.cpp
mm.cpp: In function 'void* operator new [](size_t)':
mm.cpp:279:7: error: declaration of 'void* operator new [](size_t) throw (std::bad_alloc)' has a different exception specifier
 void* operator new[] (size_t sz) throw(std::bad_alloc) {
       ^~~~~~~~

In file included from mm.cpp:49:0:
/<<PKGBUILDDIR>>/dist.x86_64-pc-linux-gnu/include/grass/iostream/mm.h:132:17: note: from previous declaration 'void* operator new [](std::size_t)'
   friend void * operator new[](size_t) throw(std::bad_alloc);
                 ^~~~~~~~

mm.cpp: In function 'void* operator new(size_t)':
mm.cpp:330:7: error: declaration of 'void* operator new(size_t) throw (std::bad_alloc)' has a different exception specifier
 void* operator new (size_t sz) throw(std::bad_alloc) {
       ^~~~~~~~

In file included from mm.cpp:49:0:
/<<PKGBUILDDIR>>/dist.x86_64-pc-linux-gnu/include/grass/iostream/mm.h:131:17: note: from previous declaration 'void* operator new(std::size_t)'
   friend void * operator new(size_t) throw(std::bad_alloc);
                 ^~~~~~~~

../../include/Make/Compile.make:35: recipe for target 'OBJ.x86_64-pc-linux-gnu/mm.o' failed

Change History (25)

comment:1 Changed 3 years ago by neteler

See also #2956

comment:2 Changed 3 years ago by neteler

I don't know much about C++ but is the suggestion given here of any use?

http://stackoverflow.com/questions/32760563/operator-new-overloading-c-handling-failure-without-exception

comment:3 Changed 3 years ago by Bas Couwenberg

My understanding of C++ is not sufficient to judge that either. It does seem like a good suggestion.

comment:4 Changed 3 years ago by neteler

CPU: UnspecifiedAll
Keywords: iostream added
Priority: normalblocker
Summary: Fails to build with GCC 6: declaration of ... has a different exception specifierlib/iostream/mm.cpp:Fails to build with GCC 6: declaration of ... has a different exception specifier
Version: 7.0.2svn-releasebranch70

(copied over from duplicate ticket 2956)

I'm trying to build GRASS GIS 7.0.3 for various Fedora/EPEL versions using Fedora's COPR (chroot based compile environment).

The following error appears:

make[5]: Leaving directory '/builddir/build/BUILD/grass-7.0.3/lib/python/imaging'
make[4]: Leaving directory '/builddir/build/BUILD/grass-7.0.3/lib/python'
make[3]: Leaving directory '/builddir/build/BUILD/grass-7.0.3/lib/python'
make[3]: Entering directory '/builddir/build/BUILD/grass-7.0.3/lib/iostream'
test -d OBJ.x86_64-redhat-linux-gnu || mkdir -p OBJ.x86_64-redhat-linux-gnu
c++  -O2 -g -pipe -Wall -Werror=format-security -Wp,-D_FORTIFY_SOURCE=2 -fexceptions -fstack-protector-strong --param=ssp-buffer-size=4 -grecord-gcc-switches -specs=/usr/lib/rpm/redhat/redhat-hardened-cc1 -m64 -mtune=generic -fPIC  -I/builddir/build/BUILD/grass-7.0.3/dist.x86_64-redhat-linux-gnu/include -I/builddir/build/BUILD/grass-7.0.3/dist.x86_64-redhat-linux-gnu/include    -DPACKAGE=\""grasslibs"\"   -I/builddir/build/BUILD/grass-7.0.3/dist.x86_64-redhat-linux-gnu/include -I/builddir/build/BUILD/grass-7.0.3/dist.x86_64-redhat-linux-gnu/include -DRELDIR=\"lib/iostream\" -o OBJ.x86_64-redhat-linux-gnu/mm_utils.o -c mm_utils.cpp
c++  -O2 -g -pipe -Wall -Werror=format-security -Wp,-D_FORTIFY_SOURCE=2 -fexceptions -fstack-protector-strong --param=ssp-buffer-size=4 -grecord-gcc-switches -specs=/usr/lib/rpm/redhat/redhat-hardened-cc1 -m64 -mtune=generic -fPIC  -I/builddir/build/BUILD/grass-7.0.3/dist.x86_64-redhat-linux-gnu/include -I/builddir/build/BUILD/grass-7.0.3/dist.x86_64-redhat-linux-gnu/include    -DPACKAGE=\""grasslibs"\"   -I/builddir/build/BUILD/grass-7.0.3/dist.x86_64-redhat-linux-gnu/include -I/builddir/build/BUILD/grass-7.0.3/dist.x86_64-redhat-linux-gnu/include -DRELDIR=\"lib/iostream\" -o OBJ.x86_64-redhat-linux-gnu/ami_stream.o -c ami_stream.cpp
c++  -O2 -g -pipe -Wall -Werror=format-security -Wp,-D_FORTIFY_SOURCE=2 -fexceptions -fstack-protector-strong --param=ssp-buffer-size=4 -grecord-gcc-switches -specs=/usr/lib/rpm/redhat/redhat-hardened-cc1 -m64 -mtune=generic -fPIC  -I/builddir/build/BUILD/grass-7.0.3/dist.x86_64-redhat-linux-gnu/include -I/builddir/build/BUILD/grass-7.0.3/dist.x86_64-redhat-linux-gnu/include    -DPACKAGE=\""grasslibs"\"   -I/builddir/build/BUILD/grass-7.0.3/dist.x86_64-redhat-linux-gnu/include -I/builddir/build/BUILD/grass-7.0.3/dist.x86_64-redhat-linux-gnu/include -DRELDIR=\"lib/iostream\" -o OBJ.x86_64-redhat-linux-gnu/mm.o -c mm.cpp
c++  -O2 -g -pipe -Wall -Werror=format-security -Wp,-D_FORTIFY_SOURCE=2 -fexceptions -fstack-protector-strong --param=ssp-buffer-size=4 -grecord-gcc-switches -specs=/usr/lib/rpm/redhat/redhat-hardened-cc1 -m64 -mtune=generic -fPIC  -I/builddir/build/BUILD/grass-7.0.3/dist.x86_64-redhat-linux-gnu/include -I/builddir/build/BUILD/grass-7.0.3/dist.x86_64-redhat-linux-gnu/include    -DPACKAGE=\""grasslibs"\"   -I/builddir/build/BUILD/grass-7.0.3/dist.x86_64-redhat-linux-gnu/include -I/builddir/build/BUILD/grass-7.0.3/dist.x86_64-redhat-linux-gnu/include -DRELDIR=\"lib/iostream\" -o OBJ.x86_64-redhat-linux-gnu/rtimer.o -c rtimer.cpp
mm.cpp: In function 'void* operator new [](size_t)':
mm.cpp:279:7: error: declaration of 'void* operator new [](size_t) throw (std::bad_alloc)' has a different exception specifier
 void* operator new[] (size_t sz) throw(std::bad_alloc) {
       ^~~~~~~~
In file included from mm.cpp:49:0:
/builddir/build/BUILD/grass-7.0.3/dist.x86_64-redhat-linux-gnu/include/grass/iostream/mm.h:132:17: note: from previous declaration 'void* operator new [](std::size_t)'
   friend void * operator new[](size_t) throw(std::bad_alloc);
                 ^~~~~~~~
mm.cpp: In function 'void* operator new(size_t)':
mm.cpp:330:7: error: declaration of 'void* operator new(size_t) throw (std::bad_alloc)' has a different exception specifier
 void* operator new (size_t sz) throw(std::bad_alloc) {
       ^~~~~~~~
In file included from mm.cpp:49:0:
/builddir/build/BUILD/grass-7.0.3/dist.x86_64-redhat-linux-gnu/include/grass/iostream/mm.h:131:17: note: from previous declaration 'void* operator new(std::size_t)'
   friend void * operator new(size_t) throw(std::bad_alloc);
                 ^~~~~~~~
../../include/Make/Compile.make:35: recipe for target 'OBJ.x86_64-redhat-linux-gnu/mm.o' failed
make[3]: *** [OBJ.x86_64-redhat-linux-gnu/mm.o] Error 1
make[3]: Leaving directory '/builddir/build/BUILD/grass-7.0.3/lib/iostream'

It happens both on i386/i686 and x86_64.

comment:5 in reply to:  2 ; Changed 3 years ago by glynn

Replying to neteler:

I don't know much about C++ but is the suggestion given here of any use?

http://stackoverflow.com/questions/32760563/operator-new-overloading-c-handling-failure-without-exception

That isn't relevant here.

Note that the exception specification was added in r50130 in response to #1533 specifically because omitting it resulted in compilation failures.

comment:6 in reply to:  5 ; Changed 3 years ago by neteler

Replying to glynn:

Note that the exception specification was added in r50130 in response to #1533 specifically because omitting it resulted in compilation failures.

I see (somehow).. but how to solve the new compilation error? Or is it "only" related to the compiler flags used by default?

comment:7 in reply to:  6 Changed 3 years ago by glynn

Replying to neteler:

I see (somehow).. but how to solve the new compilation error? Or is it "only" related to the compiler flags used by default?

It seems to be related to either the compiler version or the language version or some combination of those.

In the worst case, we may need to use preprocessor tests to either include or omit the exception specification depending on various macros. But I really have no idea what it should be testing for.

This has been reported as gcc bug 57632, but there's no resolution so far.

If it turns out only to be an issue with an "experimental" gcc release, I think it can be ignored.

comment:8 Changed 3 years ago by martinl

Priority: blockermajor

Downgrading the priority, GCC 6 is experimental version...

comment:9 Changed 3 years ago by martinl

Milestone: 7.0.47.1.0

comment:10 Changed 3 years ago by neteler

Milestone: 7.1.07.2.0

Milestone renamed

comment:11 in reply to:  8 ; Changed 3 years ago by Bas Couwenberg

Replying to martinl:

Downgrading the priority, GCC 6 is experimental version...

The severity of the bugreport in Debian has been raised to Release Critical because the GCC maintainers intend to switch to GCC 6 for the upcoming stretch release.

GRASS will be removed from testing (and upcoming stretch release) if this build failure with GCC 6 remains unfixed.

comment:12 Changed 3 years ago by martinl

Priority: majorblocker

comment:13 in reply to:  11 Changed 3 years ago by neteler

Replying to sebastic:

GRASS will be removed from testing (and upcoming stretch release) if this build failure with GCC 6 remains unfixed.

That decision sounds a bit harsh given that 1% ? of the functionality is affected. There is not too much which depends on lib/iostream/.

comment:14 Changed 3 years ago by Bas Couwenberg

Removing GRASS is not my choice, that's enforced by the Release Team in Debian. Packages with Release Critical bugs get removed from testing after a month without a fix for the RC bugs.

If we can disable the problematic functionality, that would be a perfectly acceptable sort term solution.

comment:15 Changed 3 years ago by wenzeslaus

In 68818:

use exception specifiers only for C++ versions older than C++11

Tested using GCC 5.2.1.

No exception specifiers (throw(...)) fail with -std=c++98 -fexceptions.
Omitting noexcept (or throw()) fails with -std=c++11 and -std=c++14.

Using cplusplus to get C++ standard version which defines
how the definitions in the standard library look like
and using GRASS_MM_USE_EXCEPTION_SPECIFIER we then use the right ones.

This contains old fix for -fexceptions with GCC 4.7 (see #1533, r50130)
and new fix for GCC 6 where -std=gnu++14 is by default (see #2871
and Debian Bug 811886).

Works also with clang++ -std=c++14.

comment:16 Changed 3 years ago by wenzeslaus

Keywords: gcc -fexceptions throw noexcept added

The GCC message is pretty confusing because it points to two places with the same specification claiming that the specification is different and showing previous declaration coming from library I suppose. Anyway, it seems that it all depends on the version of the standard used. C++11 and higher wants no specifiers (they are depreciated in C++) while C++98 standard with GCC option -fexceptions requires them. I don't know how to explain that the standard drafts around C++ don't specify noexcept for delete operator but there is no difference when using GCC 5.2 with -std=c++11 or -std=c++14; perhaps the library version is the same. I used __cplusplus to figure out the C++ standard in use, it seems that it is good enough (for g++ and clang).

The graph in the Debian bug report says 7.0.4, so this means that we need to eventually backport it to 70 unless they switch to 72. Can somebody conveniently test it with GCC 6?

Here are my references:

comment:17 Changed 3 years ago by Bas Couwenberg

I've added a patch with the changes from r68818 to the GRASS 7.0.4 Debian package, and built it successfully with GCC 6 (6.1.1) in Debian unstable.

I'll upload the package shortly to close the RC bug and keep GRASS in testing and the next stable release.

We'll update to GRASS 7.2 in Debian as soon as possible after it's released. If the release is before January 5th 2017 (Soft freeze) we should be able to include it in the stretch release. Otherwise it'll find its way into testing for the subsequent buster release.

Backporting the changes to the 7.0 branch is very welcome, but I don't mind carrying the patch in the Debian package either.

Last edited 3 years ago by Bas Couwenberg (previous) (diff)

comment:18 in reply to:  17 Changed 3 years ago by wenzeslaus

Replying to sebastic:

built it successfully with GCC 6 (6.1.1) in Debian unstable... I'll upload the package shortly

Great, thanks!

We'll update to GRASS 7.2 in Debian... If the release is before January 5th 2017

Good to know.

Backporting the changes to the 7.0 branch is very welcome, but I don't mind carrying the patch in the Debian package either.

It seems that Fedora/EPEL needs it too (see #2956), so I think we'll backport. One apparently never knows with these changes. Let's wait till the next commit which will trigger OSX build on Travis (which was broken while ago).

comment:19 Changed 3 years ago by martinl

What is status of this ticket? Backports still needed? Time to close?

comment:20 Changed 3 years ago by Bas Couwenberg

For Debian the backport to 7.0 is not really required, the Debian package includes the required changes as a patch, and the 7.2 release should happen soon enough.

comment:21 Changed 3 years ago by wenzeslaus

I need to backport it to 7.2.

comment:22 Changed 3 years ago by wenzeslaus

In 68911:

use exception specifiers only for C++ versions older than C++11 (backport r68818, see #2871)

comment:23 Changed 3 years ago by wenzeslaus

Resolution: fixed
Status: newclosed

In 68912:

use exception specifiers only for C++ versions older than C++11 (backport r68818, closes #2871, see #2956)

comment:24 Changed 3 years ago by wenzeslaus

#2956 (duplicate of this specific to Fedora/EPEL) was blocker with milestone 7.0.4, so I did backport to 7.0 branch as well.

comment:25 Changed 3 years ago by neteler

Backported to 6.4.svn in r68988 (for the upcoming 6.4.6 release)

Note: See TracTickets for help on using tickets.