https://gcc.gnu.org/bugzilla/show_bug.cgi?id=57632

Jonathan Wakely <redi at gcc dot gnu.org> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
           Keywords|                            |diagnostic
         Resolution|INVALID                     |---
     Ever confirmed|0                           |1
   Last reconfirmed|                            |2022-01-07
             Status|RESOLVED                    |NEW

--- Comment #5 from Jonathan Wakely <redi at gcc dot gnu.org> ---
I agree with comment 3 that the current diagnostic is poor:

#include <new>
void* operator new(std::size_t mem) throw(std::bad_alloc);
void* operator new(std::size_t mem) throw(std::bad_alloc);


g++ -std=c++11  -c new.cc -Wno-deprecated
new.cc:3:7: error: declaration of ‘void* operator new(std::size_t) throw
(std::bad_alloc)’ has a different exception specifier
    3 | void* operator new(std::size_t mem) throw(std::bad_alloc);
      |       ^~~~~~~~
new.cc:2:7: note: from previous declaration ‘void* operator new(std::size_t)’
    2 | void* operator new(std::size_t mem) throw(std::bad_alloc);
      |       ^~~~~~~~


Why does it accept the incorrect exception specification on line 2, but then
give an error for an identical one on line 3? Why do we refer to line 2 in the
note and say it's different, when it's not?

Paolo's explanation in comment 1 doesn't make the behaviour correct, it just
explains why we behave like that. Either both redeclarations should be valid or
neither should be valid.

So I think either we should either:

- accept both redeclarations (as Clang does), or

- give a diagnostic (maybe a pedwarn) for the first redeclaration because it
doesn't match the one in <new> (and the implicit one predefined by the
compiler), and fix the diagnostic to refer to the previous declaration in <new>
instead of the one on line 2.

Reply via email to