PR libstdc++/51333 Define recursive_init_error constructor non-inline
authorJonathan Wakely <jwakely@redhat.com>
Mon, 29 Jul 2019 14:27:19 +0000 (15:27 +0100)
committerJonathan Wakely <redi@gcc.gnu.org>
Mon, 29 Jul 2019 14:27:19 +0000 (15:27 +0100)
The recursive_init_error class is defined in a header, with an inline
constructor, but the definition of the vtable and destructor are not
exported from the shared library. With -fkeep-inline-functions the
constructor gets emitted in user code, and requires the (non-exported)
vtable. This fails to link.

As far as I can tell, the recursive_init_error class definition was
moved into <cxxabi.h> so it could be documented with Doxygen, not for
any technical reason. But now it's there (and documented), somebody
could be relying on it, by catching that type and possibly performing
derived-to-base conversions to the std::exception base class. So the
conservative fix is to leave the class definition in the header but make
the constructor non-inline. This still allows the type to be caught and
still defines its base class. User code can no longer construct objects
of that type, but that's not something we need to support.

PR libstdc++/51333
* libsupc++/cxxabi.h (__gnu_cxx::recursive_init_error): Do not define
constructor inline.
* libsupc++/guard_error.cc (__gnu_cxx::recursive_init_error): Define
constructor.
* testsuite/18_support/51333.cc: New test.

From-SVN: r273878

libstdc++-v3/ChangeLog
libstdc++-v3/libsupc++/cxxabi.h
libstdc++-v3/libsupc++/guard_error.cc
libstdc++-v3/testsuite/18_support/51333.cc [new file with mode: 0644]

index 11be89647b8a85755cce779643b82b558f11f82c..84fc03b048ba6ba78fe3090602cd8c8c94f1d15c 100644 (file)
@@ -1,3 +1,12 @@
+2019-07-29  Jonathan Wakely  <jwakely@redhat.com>
+
+       PR libstdc++/51333
+       * libsupc++/cxxabi.h (__gnu_cxx::recursive_init_error): Do not define
+       constructor inline.
+       * libsupc++/guard_error.cc (__gnu_cxx::recursive_init_error): Define
+       constructor.
+       * testsuite/18_support/51333.cc: New test.
+
 2019-07-28  Gerald Pfeifer  <gerald@pfeifer.com>
 
        * doc/xml/manual/documentation_hacking.xml: Fix broken reference
index 3562d4c227108bf6753f7f4b2f283df46bad4bb5..4d9f829ffed8625b32f6553a67a87c4f4a1e28c8 100644 (file)
@@ -684,8 +684,9 @@ namespace __gnu_cxx
    *  @brief Exception thrown by __cxa_guard_acquire.
    *  @ingroup exceptions
    *
-   *  6.7[stmt.dcl]/4: If control re-enters the declaration (recursively)
-   *  while the object is being initialized, the behavior is undefined.
+   *  C++ 2011 6.7 [stmt.dcl]/4: If control re-enters the declaration
+   *  recursively while the variable is being initialized, the behavior
+   *  is undefined.
    *
    *  Since we already have a library function to handle locking, we might
    *  as well check for this situation and throw an exception.
@@ -695,8 +696,8 @@ namespace __gnu_cxx
   class recursive_init_error: public std::exception
   {
   public:
-    recursive_init_error() throw() { }
-    virtual ~recursive_init_error() throw ();
+    recursive_init_error() _GLIBCXX_NOTHROW;
+    virtual ~recursive_init_error() _GLIBCXX_NOTHROW;
   };
 }
 #endif // __cplusplus
index 7595c67872ab2e809ffa785a5652aa057b1658b0..d7625af4d5456710388c58370fd4027f4b8bb1cd 100644 (file)
@@ -26,6 +26,6 @@
 
 namespace __gnu_cxx
 {
-  recursive_init_error::~recursive_init_error() throw() { }
+  recursive_init_error::recursive_init_error() noexcept { }
+  recursive_init_error::~recursive_init_error() noexcept { }
 }
-
diff --git a/libstdc++-v3/testsuite/18_support/51333.cc b/libstdc++-v3/testsuite/18_support/51333.cc
new file mode 100644 (file)
index 0000000..0fb7c33
--- /dev/null
@@ -0,0 +1,22 @@
+// Copyright (C) 2019 Free Software Foundation, Inc.
+//
+// This file is part of the GNU ISO C++ Library.  This library is free
+// software; you can redistribute it and/or modify it under the
+// terms of the GNU General Public License as published by the
+// Free Software Foundation; either version 3, or (at your option)
+// any later version.
+
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+// GNU General Public License for more details.
+
+// You should have received a copy of the GNU General Public License along
+// with this library; see the file COPYING3.  If not see
+// <http://www.gnu.org/licenses/>.
+
+// { dg-options "-fkeep-inline-functions" }
+// { dg-do link }
+
+#include <cxxabi.h>
+int main() { } // PR libstdc++/51333