When given a type which can convert to any container-like type, the C(const C&) copy constructor and C(const C::_Base&) converting constructor are ambiguous. This change replaces the converting constructor's parameter with a reference_wrapper-like type so that calling that constructor requires an additional user-defined conversion. This gives it a lower rank than the copy constructor, avoiding the ambiguity.
While testing this change I discovered that __gnu_debug::forward_list doesn't have a convering constructor from the std::forward_list base, so this adds it. We should probably consider whether the converting constructors should be 'explicit' but I'm not changing that now. libstdc++-v3/ChangeLog: PR libstdc++/90102 * include/debug/deque (deque(const _Base&)): Replace parameter with a struct that wraps a const _Base&. * include/debug/forward_list (forward_list(_Base_ref)): New constructor. * include/debug/list (list(const _Base&)): Replace parameter with a struct that wraps a const _Base&. * include/debug/map.h (map(const _Base&)): Likewise. * include/debug/multimap.h (multimap(const _Base&)): Likewise. * include/debug/multiset.h (multiset(const _Base&)): Likewise. * include/debug/set.h (set(const _Base&)): Likewise. * include/debug/unordered_map (unordered_map(const _Base&)) (unordered_multimap(const _Base&)): Likewise. * include/debug/unordered_set (unordered_set(const _Base&)) (unordered_multiset(const _Base&)): Likewise. * testsuite/23_containers/vector/cons/destructible_debug_neg.cc: Adjust dg-error line number. * include/debug/vector (vector(const _Base&)): Likewise. * testsuite/23_containers/deque/debug/90102.cc: New test. * testsuite/23_containers/forward_list/debug/90102.cc: New test. * testsuite/23_containers/list/debug/90102.cc: New test. * testsuite/23_containers/map/debug/90102.cc: New test. * testsuite/23_containers/multimap/debug/90102.cc: New test. * testsuite/23_containers/multiset/debug/90102.cc: New test. * testsuite/23_containers/set/debug/90102.cc: New test. * testsuite/23_containers/unordered_map/debug/90102.cc: New test. * testsuite/23_containers/unordered_multimap/debug/90102.cc: New test. * testsuite/23_containers/unordered_multiset/debug/90102.cc: New test. * testsuite/23_containers/unordered_set/debug/90102.cc: New test. * testsuite/23_containers/vector/debug/90102.cc: New test. Tested powerpc64le-linux, committed to master.
commit eca833b81289438ec5ae3ed4c77ffb49cfb65f34 Author: Jonathan Wakely <jwak...@redhat.com> Date: Tue Jun 2 18:13:08 2020 +0100 libstdc++: Make debug containers prefer copy ctor to base ctor (PR 90102) When given a type which can convert to any container-like type, the C(const C&) copy constructor and C(const C::_Base&) converting constructor are ambiguous. This change replaces the converting constructor's parameter with a reference_wrapper-like type so that calling that constructor requires an additional user-defined conversion. This gives it a lower rank than the copy constructor, avoiding the ambiguity. While testing this change I discovered that __gnu_debug::forward_list doesn't have a convering constructor from the std::forward_list base, so this adds it. We should probably consider whether the converting constructors should be 'explicit' but I'm not changing that now. libstdc++-v3/ChangeLog: PR libstdc++/90102 * include/debug/deque (deque(const _Base&)): Replace parameter with a struct that wraps a const _Base&. * include/debug/forward_list (forward_list(_Base_ref)): New constructor. * include/debug/list (list(const _Base&)): Replace parameter with a struct that wraps a const _Base&. * include/debug/map.h (map(const _Base&)): Likewise. * include/debug/multimap.h (multimap(const _Base&)): Likewise. * include/debug/multiset.h (multiset(const _Base&)): Likewise. * include/debug/set.h (set(const _Base&)): Likewise. * include/debug/unordered_map (unordered_map(const _Base&)) (unordered_multimap(const _Base&)): Likewise. * include/debug/unordered_set (unordered_set(const _Base&)) (unordered_multiset(const _Base&)): Likewise. * testsuite/23_containers/vector/cons/destructible_debug_neg.cc: Adjust dg-error line number. * include/debug/vector (vector(const _Base&)): Likewise. * testsuite/23_containers/deque/debug/90102.cc: New test. * testsuite/23_containers/forward_list/debug/90102.cc: New test. * testsuite/23_containers/list/debug/90102.cc: New test. * testsuite/23_containers/map/debug/90102.cc: New test. * testsuite/23_containers/multimap/debug/90102.cc: New test. * testsuite/23_containers/multiset/debug/90102.cc: New test. * testsuite/23_containers/set/debug/90102.cc: New test. * testsuite/23_containers/unordered_map/debug/90102.cc: New test. * testsuite/23_containers/unordered_multimap/debug/90102.cc: New test. * testsuite/23_containers/unordered_multiset/debug/90102.cc: New test. * testsuite/23_containers/unordered_set/debug/90102.cc: New test. * testsuite/23_containers/vector/debug/90102.cc: New test. diff --git a/libstdc++-v3/include/debug/deque b/libstdc++-v3/include/debug/deque index 4d525bfc0aa..2bb99023870 100644 --- a/libstdc++-v3/include/debug/deque +++ b/libstdc++-v3/include/debug/deque @@ -64,6 +64,16 @@ namespace __debug template<typename _ItT, typename _SeqT, typename _CatT> friend class ::__gnu_debug::_Safe_iterator; + // Reference wrapper for base class. Disambiguates deque(const _Base&) + // from copy constructor by requiring a user-defined conversion. + // See PR libstdc++/90102. + struct _Base_ref + { + _Base_ref(const _Base& __r) : _M_ref(__r) { } + + const _Base& _M_ref; + }; + public: typedef typename _Base::reference reference; typedef typename _Base::const_reference const_reference; @@ -143,8 +153,8 @@ namespace __debug __gnu_debug::__base(__last), __a) { } - deque(const _Base& __x) - : _Base(__x) { } + deque(_Base_ref __x) + : _Base(__x._M_ref) { } #if __cplusplus < 201103L deque& diff --git a/libstdc++-v3/include/debug/forward_list b/libstdc++-v3/include/debug/forward_list index 2fd03e70499..fc6bf6359e9 100644 --- a/libstdc++-v3/include/debug/forward_list +++ b/libstdc++-v3/include/debug/forward_list @@ -201,6 +201,14 @@ namespace __debug template<typename _ItT, typename _SeqT, typename _CatT> friend class ::__gnu_debug::_Safe_iterator; + // Reference wrapper for base class. See PR libstdc++/90102. + struct _Base_ref + { + _Base_ref(const _Base& __r) : _M_ref(__r) { } + + const _Base& _M_ref; + }; + public: typedef typename _Base::reference reference; typedef typename _Base::const_reference const_reference; @@ -265,6 +273,8 @@ namespace __debug ~forward_list() = default; + forward_list(_Base_ref __x) : _Base(__x._M_ref) { } + forward_list& operator=(const forward_list&) = default; diff --git a/libstdc++-v3/include/debug/list b/libstdc++-v3/include/debug/list index 6dd85741f81..8f2a8cb0f01 100644 --- a/libstdc++-v3/include/debug/list +++ b/libstdc++-v3/include/debug/list @@ -65,6 +65,16 @@ namespace __debug template<typename _ItT, typename _SeqT, typename _CatT> friend class ::__gnu_debug::_Safe_iterator; + // Reference wrapper for base class. Disambiguates list(const _Base&) + // from copy constructor by requiring a user-defined conversion. + // See PR libstdc++/90102. + struct _Base_ref + { + _Base_ref(const _Base& __r) : _M_ref(__r) { } + + const _Base& _M_ref; + }; + public: typedef typename _Base::reference reference; typedef typename _Base::const_reference const_reference; @@ -144,8 +154,8 @@ namespace __debug __gnu_debug::__base(__last), __a) { } - list(const _Base& __x) - : _Base(__x) { } + list(_Base_ref __x) + : _Base(__x._M_ref) { } #if __cplusplus < 201103L list& diff --git a/libstdc++-v3/include/debug/map.h b/libstdc++-v3/include/debug/map.h index adbabf62915..03eb0cbe332 100644 --- a/libstdc++-v3/include/debug/map.h +++ b/libstdc++-v3/include/debug/map.h @@ -59,6 +59,16 @@ namespace __debug template<typename _ItT, typename _SeqT, typename _CatT> friend class ::__gnu_debug::_Safe_iterator; + // Reference wrapper for base class. Disambiguates map(const _Base&) + // from copy constructor by requiring a user-defined conversion. + // See PR libstdc++/90102. + struct _Base_ref + { + _Base_ref(const _Base& __r) : _M_ref(__r) { } + + const _Base& _M_ref; + }; + public: // types: typedef _Key key_type; @@ -126,8 +136,8 @@ namespace __debug ~map() = default; #endif - map(const _Base& __x) - : _Base(__x) { } + map(_Base_ref __x) + : _Base(__x._M_ref) { } explicit map(const _Compare& __comp, const _Allocator& __a = _Allocator()) diff --git a/libstdc++-v3/include/debug/multimap.h b/libstdc++-v3/include/debug/multimap.h index 6cba52d35dc..e8d420e2196 100644 --- a/libstdc++-v3/include/debug/multimap.h +++ b/libstdc++-v3/include/debug/multimap.h @@ -59,6 +59,16 @@ namespace __debug template<typename _ItT, typename _SeqT, typename _CatT> friend class ::__gnu_debug::_Safe_iterator; + // Reference wrapper for base class. Disambiguates multimap(const _Base&) + // from copy constructor by requiring a user-defined conversion. + // See PR libstdc++/90102. + struct _Base_ref + { + _Base_ref(const _Base& __r) : _M_ref(__r) { } + + const _Base& _M_ref; + }; + public: // types: typedef _Key key_type; @@ -138,8 +148,8 @@ namespace __debug __gnu_debug::__base(__last), __comp, __a) { } - multimap(const _Base& __x) - : _Base(__x) { } + multimap(_Base_ref __x) + : _Base(__x._M_ref) { } #if __cplusplus < 201103L multimap& diff --git a/libstdc++-v3/include/debug/multiset.h b/libstdc++-v3/include/debug/multiset.h index a2d5e717b34..152ebcd6870 100644 --- a/libstdc++-v3/include/debug/multiset.h +++ b/libstdc++-v3/include/debug/multiset.h @@ -58,6 +58,16 @@ namespace __debug template<typename _ItT, typename _SeqT, typename _CatT> friend class ::__gnu_debug::_Safe_iterator; + // Reference wrapper for base class. Disambiguates multiset(const _Base&) + // from copy constructor by requiring a user-defined conversion. + // See PR libstdc++/90102. + struct _Base_ref + { + _Base_ref(const _Base& __r) : _M_ref(__r) { } + + const _Base& _M_ref; + }; + public: // types: typedef _Key key_type; @@ -138,8 +148,8 @@ namespace __debug __gnu_debug::__base(__last), __comp, __a) { } - multiset(const _Base& __x) - : _Base(__x) { } + multiset(_Base_ref __x) + : _Base(__x._M_ref) { } #if __cplusplus < 201103L multiset& diff --git a/libstdc++-v3/include/debug/set.h b/libstdc++-v3/include/debug/set.h index 210186623df..85bc89e9915 100644 --- a/libstdc++-v3/include/debug/set.h +++ b/libstdc++-v3/include/debug/set.h @@ -58,6 +58,16 @@ namespace __debug template<typename _ItT, typename _SeqT, typename _CatT> friend class ::__gnu_debug::_Safe_iterator; + // Reference wrapper for base class. Disambiguates set(const _Base&) + // from copy constructor by requiring a user-defined conversion. + // See PR libstdc++/90102. + struct _Base_ref + { + _Base_ref(const _Base& __r) : _M_ref(__r) { } + + const _Base& _M_ref; + }; + public: // types: typedef _Key key_type; @@ -137,8 +147,8 @@ namespace __debug __gnu_debug::__base(__last), __comp, __a) { } - set(const _Base& __x) - : _Base(__x) { } + set(_Base_ref __x) + : _Base(__x._M_ref) { } #if __cplusplus < 201103L set& diff --git a/libstdc++-v3/include/debug/unordered_map b/libstdc++-v3/include/debug/unordered_map index 17fbba3aade..7d55174f63b 100644 --- a/libstdc++-v3/include/debug/unordered_map +++ b/libstdc++-v3/include/debug/unordered_map @@ -81,6 +81,14 @@ namespace __debug template<typename _ItT, typename _SeqT> friend class ::__gnu_debug::_Safe_local_iterator; + // Reference wrapper for base class. See PR libstdc++/90102. + struct _Base_ref + { + _Base_ref(const _Base& __r) : _M_ref(__r) { } + + const _Base& _M_ref; + }; + public: typedef typename _Base::size_type size_type; typedef typename _Base::hasher hasher; @@ -121,8 +129,8 @@ namespace __debug unordered_map(const unordered_map&) = default; - unordered_map(const _Base& __x) - : _Base(__x) { } + unordered_map(_Base_ref __x) + : _Base(__x._M_ref) { } unordered_map(unordered_map&&) = default; @@ -776,6 +784,14 @@ namespace __debug template<typename _ItT, typename _SeqT> friend class ::__gnu_debug::_Safe_local_iterator; + // Reference wrapper for base class. See PR libstdc++/90102. + struct _Base_ref + { + _Base_ref(const _Base& __r) : _M_ref(__r) { } + + const _Base& _M_ref; + }; + public: typedef typename _Base::size_type size_type; typedef typename _Base::hasher hasher; @@ -816,8 +832,8 @@ namespace __debug unordered_multimap(const unordered_multimap&) = default; - unordered_multimap(const _Base& __x) - : _Base(__x) { } + unordered_multimap(_Base_ref __x) + : _Base(__x._M_ref) { } unordered_multimap(unordered_multimap&&) = default; diff --git a/libstdc++-v3/include/debug/unordered_set b/libstdc++-v3/include/debug/unordered_set index 4d30852186c..37031da947e 100644 --- a/libstdc++-v3/include/debug/unordered_set +++ b/libstdc++-v3/include/debug/unordered_set @@ -78,6 +78,14 @@ namespace __debug template<typename _ItT, typename _SeqT> friend class ::__gnu_debug::_Safe_local_iterator; + // Reference wrapper for base class. See PR libstdc++/90102. + struct _Base_ref + { + _Base_ref(const _Base& __r) : _M_ref(__r) { } + + const _Base& _M_ref; + }; + public: typedef typename _Base::size_type size_type; typedef typename _Base::hasher hasher; @@ -118,8 +126,8 @@ namespace __debug unordered_set(const unordered_set&) = default; - unordered_set(const _Base& __x) - : _Base(__x) { } + unordered_set(_Base_ref __x) + : _Base(__x._M_ref) { } unordered_set(unordered_set&&) = default; @@ -646,6 +654,14 @@ namespace __debug template<typename _ItT, typename _SeqT> friend class ::__gnu_debug::_Safe_local_iterator; + // Reference wrapper for base class. See PR libstdc++/90102. + struct _Base_ref + { + _Base_ref(const _Base& __r) : _M_ref(__r) { } + + const _Base& _M_ref; + }; + public: typedef typename _Base::size_type size_type; typedef typename _Base::hasher hasher; @@ -686,8 +702,8 @@ namespace __debug unordered_multiset(const unordered_multiset&) = default; - unordered_multiset(const _Base& __x) - : _Base(__x) { } + unordered_multiset(_Base_ref __x) + : _Base(__x._M_ref) { } unordered_multiset(unordered_multiset&&) = default; diff --git a/libstdc++-v3/include/debug/vector b/libstdc++-v3/include/debug/vector index 4c08ab61ce8..47466169f8e 100644 --- a/libstdc++-v3/include/debug/vector +++ b/libstdc++-v3/include/debug/vector @@ -135,6 +135,16 @@ namespace __debug template<typename _ItT, typename _SeqT, typename _CatT> friend class ::__gnu_debug::_Safe_iterator; + // Reference wrapper for base class. Disambiguates vector(const _Base&) + // from copy constructor by requiring a user-defined conversion. + // See PR libstdc++/90102. + struct _Base_ref + { + _Base_ref(const _Base& __r) : _M_ref(__r) { } + + const _Base& _M_ref; + }; + public: typedef typename _Base::reference reference; typedef typename _Base::const_reference const_reference; @@ -207,8 +217,8 @@ namespace __debug : _Base(__x, __a) { } vector(vector&& __x, const allocator_type& __a) - noexcept( noexcept( - _Base(std::declval<_Base&&>()), std::declval<const allocator_type&>()) ) + noexcept(noexcept( + _Base(std::declval<_Base&&>()), std::declval<const allocator_type&>())) : _Safe(std::move(__x._M_safe()), __a), _Base(std::move(__x._M_base()), __a), _Safe_vector(std::move(__x)) { } @@ -221,8 +231,8 @@ namespace __debug #endif /// Construction from a normal-mode vector - vector(const _Base& __x) - : _Base(__x) { } + vector(_Base_ref __x) + : _Base(__x._M_ref) { } #if __cplusplus < 201103L vector& diff --git a/libstdc++-v3/testsuite/23_containers/deque/debug/90102.cc b/libstdc++-v3/testsuite/23_containers/deque/debug/90102.cc new file mode 100644 index 00000000000..80141a38ab8 --- /dev/null +++ b/libstdc++-v3/testsuite/23_containers/deque/debug/90102.cc @@ -0,0 +1,34 @@ +// Copyright (C) 2020 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-do compile { target c++11 } } + +#include <debug/deque> + +// PR libstdc++/90102 + +struct AnyCont +{ + template<class Cont, class Check = decltype(std::declval<Cont>().clear())> + operator Cont () const; +} a; + +// This should use copy constructor, not be ambiguous +__gnu_debug::deque<int> c(a); + +// Ensure construction from base container still works +__gnu_debug::deque<int> d(static_cast<std::deque<int>>(a)); diff --git a/libstdc++-v3/testsuite/23_containers/forward_list/debug/90102.cc b/libstdc++-v3/testsuite/23_containers/forward_list/debug/90102.cc new file mode 100644 index 00000000000..a382bde98a8 --- /dev/null +++ b/libstdc++-v3/testsuite/23_containers/forward_list/debug/90102.cc @@ -0,0 +1,34 @@ +// Copyright (C) 2020 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-do compile { target c++11 } } + +#include <debug/forward_list> + +// PR libstdc++/90102 + +struct AnyCont +{ + template<class Cont, class Check = decltype(std::declval<Cont>().clear())> + operator Cont () const; +} a; + +// This should use copy constructor, not be ambiguous +__gnu_debug::forward_list<int> c(a); + +// Ensure construction from base container still works +__gnu_debug::forward_list<int> d(static_cast<std::forward_list<int>>(a)); diff --git a/libstdc++-v3/testsuite/23_containers/list/debug/90102.cc b/libstdc++-v3/testsuite/23_containers/list/debug/90102.cc new file mode 100644 index 00000000000..49a23dc9d73 --- /dev/null +++ b/libstdc++-v3/testsuite/23_containers/list/debug/90102.cc @@ -0,0 +1,34 @@ +// Copyright (C) 2020 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-do compile { target c++11 } } + +#include <debug/list> + +// PR libstdc++/90102 + +struct AnyCont +{ + template<class Cont, class Check = decltype(std::declval<Cont>().clear())> + operator Cont () const; +} a; + +// This should use copy constructor, not be ambiguous +__gnu_debug::list<int> c(a); + +// Ensure construction from base container still works +__gnu_debug::list<int> d(static_cast<std::list<int>>(a)); diff --git a/libstdc++-v3/testsuite/23_containers/map/debug/90102.cc b/libstdc++-v3/testsuite/23_containers/map/debug/90102.cc new file mode 100644 index 00000000000..d50617f743a --- /dev/null +++ b/libstdc++-v3/testsuite/23_containers/map/debug/90102.cc @@ -0,0 +1,34 @@ +// Copyright (C) 2020 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-do compile { target c++11 } } + +#include <debug/map> + +// PR libstdc++/90102 + +struct AnyCont +{ + template<class Cont, class Check = decltype(std::declval<Cont>().clear())> + operator Cont () const; +} a; + +// This should use copy constructor, not be ambiguous +__gnu_debug::map<int, int> c(a); + +// Ensure construction from base container still works +__gnu_debug::map<int, int> d(static_cast<std::map<int, int>>(a)); diff --git a/libstdc++-v3/testsuite/23_containers/multimap/debug/90102.cc b/libstdc++-v3/testsuite/23_containers/multimap/debug/90102.cc new file mode 100644 index 00000000000..f11e3fe332b --- /dev/null +++ b/libstdc++-v3/testsuite/23_containers/multimap/debug/90102.cc @@ -0,0 +1,34 @@ +// Copyright (C) 2020 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-do compile { target c++11 } } + +#include <debug/map> + +// PR libstdc++/90102 + +struct AnyCont +{ + template<class Cont, class Check = decltype(std::declval<Cont>().clear())> + operator Cont () const; +} a; + +// This should use copy constructor, not be ambiguous +__gnu_debug::multimap<int, int> c(a); + +// Ensure construction from base container still works +__gnu_debug::multimap<int, int> d(static_cast<std::multimap<int, int>>(a)); diff --git a/libstdc++-v3/testsuite/23_containers/multiset/debug/90102.cc b/libstdc++-v3/testsuite/23_containers/multiset/debug/90102.cc new file mode 100644 index 00000000000..32ff73863c4 --- /dev/null +++ b/libstdc++-v3/testsuite/23_containers/multiset/debug/90102.cc @@ -0,0 +1,34 @@ +// Copyright (C) 2020 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-do compile { target c++11 } } + +#include <debug/set> + +// PR libstdc++/90102 + +struct AnyCont +{ + template<class Cont, class Check = decltype(std::declval<Cont>().clear())> + operator Cont () const; +} a; + +// This should use copy constructor, not be ambiguous +__gnu_debug::multiset<int> c(a); + +// Ensure construction from base container still works +__gnu_debug::multiset<int> d(static_cast<std::multiset<int>>(a)); diff --git a/libstdc++-v3/testsuite/23_containers/set/debug/90102.cc b/libstdc++-v3/testsuite/23_containers/set/debug/90102.cc new file mode 100644 index 00000000000..1da9f62bc81 --- /dev/null +++ b/libstdc++-v3/testsuite/23_containers/set/debug/90102.cc @@ -0,0 +1,34 @@ +// Copyright (C) 2020 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-do compile { target c++11 } } + +#include <debug/set> + +// PR libstdc++/90102 + +struct AnyCont +{ + template<class Cont, class Check = decltype(std::declval<Cont>().clear())> + operator Cont () const; +} a; + +// This should use copy constructor, not be ambiguous +__gnu_debug::set<int> c(a); + +// Ensure construction from base container still works +__gnu_debug::set<int> d(static_cast<std::set<int>>(a)); diff --git a/libstdc++-v3/testsuite/23_containers/unordered_map/debug/90102.cc b/libstdc++-v3/testsuite/23_containers/unordered_map/debug/90102.cc new file mode 100644 index 00000000000..da7f3901e8b --- /dev/null +++ b/libstdc++-v3/testsuite/23_containers/unordered_map/debug/90102.cc @@ -0,0 +1,34 @@ +// Copyright (C) 2020 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-do compile { target c++11 } } + +#include <debug/unordered_map> + +// PR libstdc++/90102 + +struct AnyCont +{ + template<class Cont, class Check = decltype(std::declval<Cont>().clear())> + operator Cont () const; +} a; + +// This should use copy constructor, not be ambiguous +__gnu_debug::unordered_map<int, int> c(a); + +// Ensure construction from base container still works +__gnu_debug::unordered_map<int, int> d(static_cast<std::unordered_map<int, int>>(a)); diff --git a/libstdc++-v3/testsuite/23_containers/unordered_multimap/debug/90102.cc b/libstdc++-v3/testsuite/23_containers/unordered_multimap/debug/90102.cc new file mode 100644 index 00000000000..398e7265491 --- /dev/null +++ b/libstdc++-v3/testsuite/23_containers/unordered_multimap/debug/90102.cc @@ -0,0 +1,34 @@ +// Copyright (C) 2020 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-do compile { target c++11 } } + +#include <debug/unordered_map> + +// PR libstdc++/90102 + +struct AnyCont +{ + template<class Cont, class Check = decltype(std::declval<Cont>().clear())> + operator Cont () const; +} a; + +// This should use copy constructor, not be ambiguous +__gnu_debug::unordered_multimap<int, int> c(a); + +// Ensure construction from base container still works +__gnu_debug::unordered_multimap<int, int> d(static_cast<std::unordered_multimap<int, int>>(a)); diff --git a/libstdc++-v3/testsuite/23_containers/unordered_multiset/debug/90102.cc b/libstdc++-v3/testsuite/23_containers/unordered_multiset/debug/90102.cc new file mode 100644 index 00000000000..a257acf7d9d --- /dev/null +++ b/libstdc++-v3/testsuite/23_containers/unordered_multiset/debug/90102.cc @@ -0,0 +1,34 @@ +// Copyright (C) 2020 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-do compile { target c++11 } } + +#include <debug/unordered_set> + +// PR libstdc++/90102 + +struct AnyCont +{ + template<class Cont, class Check = decltype(std::declval<Cont>().clear())> + operator Cont () const; +} a; + +// This should use copy constructor, not be ambiguous +__gnu_debug::unordered_multiset<int> c(a); + +// Ensure construction from base container still works +__gnu_debug::unordered_multiset<int> d(static_cast<std::unordered_multiset<int>>(a)); diff --git a/libstdc++-v3/testsuite/23_containers/unordered_set/debug/90102.cc b/libstdc++-v3/testsuite/23_containers/unordered_set/debug/90102.cc new file mode 100644 index 00000000000..49f352f55d7 --- /dev/null +++ b/libstdc++-v3/testsuite/23_containers/unordered_set/debug/90102.cc @@ -0,0 +1,34 @@ +// Copyright (C) 2020 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-do compile { target c++11 } } + +#include <debug/unordered_set> + +// PR libstdc++/90102 + +struct AnyCont +{ + template<class Cont, class Check = decltype(std::declval<Cont>().clear())> + operator Cont () const; +} a; + +// This should use copy constructor, not be ambiguous +__gnu_debug::unordered_set<int> c(a); + +// Ensure construction from base container still works +__gnu_debug::unordered_set<int> d(static_cast<std::unordered_set<int>>(a)); diff --git a/libstdc++-v3/testsuite/23_containers/vector/cons/destructible_debug_neg.cc b/libstdc++-v3/testsuite/23_containers/vector/cons/destructible_debug_neg.cc index 0eae8ee908c..9e58f0f4ddd 100644 --- a/libstdc++-v3/testsuite/23_containers/vector/cons/destructible_debug_neg.cc +++ b/libstdc++-v3/testsuite/23_containers/vector/cons/destructible_debug_neg.cc @@ -46,7 +46,7 @@ test02() // { dg-error "value type is destructible" "" { target *-*-* } 0 } // In Debug Mode the "required from here" errors come from <debug/vector> -// { dg-error "required from here" "" { target *-*-* } 163 } +// { dg-error "required from here" "" { target *-*-* } 173 } // Needed because of PR c++/92193 // { dg-prune-output "deleted function" } diff --git a/libstdc++-v3/testsuite/23_containers/vector/debug/90102.cc b/libstdc++-v3/testsuite/23_containers/vector/debug/90102.cc new file mode 100644 index 00000000000..19eb1fabafe --- /dev/null +++ b/libstdc++-v3/testsuite/23_containers/vector/debug/90102.cc @@ -0,0 +1,34 @@ +// Copyright (C) 2020 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-do compile { target c++11 } } + +#include <debug/vector> + +// PR libstdc++/90102 + +struct AnyCont +{ + template<class Cont, class Check = decltype(std::declval<Cont>().clear())> + operator Cont () const; +} a; + +// This should use copy constructor, not be ambiguous +__gnu_debug::vector<int> c(a); + +// Ensure construction from base container still works +__gnu_debug::vector<int> d(static_cast<std::vector<int>>(a));