libstdc++: fix compile error when converting std::weak_ptr<T[]>
A std::weak_ptr<T[]> can be converted to a compatible std::weak_ptr<U[]>. This is implemented by having suitable converting constructors to std::weak_ptr which dispatch to the __weak_ptr base class (implementation detail). In __weak_ptr<T[]>, lock() is supposed to return a __shared_ptr<T[]>, not a __shared_ptr<element_type> (that is, __shared_ptr<T>). Unfortunately the return type of lock() and the type of the returned __shared_ptr were mismatching and that was causing a compile error: when converting a __weak_ptr<T[]> to a __weak_ptr<U[]> through __weak_ptr's converting constructor, the code calls lock(), and that simply fails to build. Fix it by removing the usage of element_type inside lock(), and using _Tp instead. Note that std::weak_ptr::lock() itself was already correct; the one in __weak_ptr was faulty (and that is the one called by __weak_ptr's converting constructors). libstdc++-v3/ChangeLog: * include/bits/shared_ptr_base.h (lock): Fixed a compile error when calling lock() on a weak_ptr<T[]>, by removing an erroneous usage of element_type from within lock(). * testsuite/20_util/shared_ptr/requirements/explicit_instantiation/1.cc: Add more tests for array types. * testsuite/20_util/weak_ptr/requirements/explicit_instantiation/1.cc: Likewise. * testsuite/20_util/shared_ptr/requirements/1.cc: New test. * testsuite/20_util/weak_ptr/requirements/1.cc: New test.
This commit is contained in:
parent
adb14c7625
commit
df0e6509bf
5 changed files with 91 additions and 1 deletions
|
@ -2075,7 +2075,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
|
|||
|
||||
__shared_ptr<_Tp, _Lp>
|
||||
lock() const noexcept
|
||||
{ return __shared_ptr<element_type, _Lp>(*this, std::nothrow); }
|
||||
{ return __shared_ptr<_Tp, _Lp>(*this, std::nothrow); }
|
||||
|
||||
long
|
||||
use_count() const noexcept
|
||||
|
|
33
libstdc++-v3/testsuite/20_util/shared_ptr/requirements/1.cc
Normal file
33
libstdc++-v3/testsuite/20_util/shared_ptr/requirements/1.cc
Normal file
|
@ -0,0 +1,33 @@
|
|||
// { dg-do compile { target c++11 } }
|
||||
// { dg-require-effective-target hosted }
|
||||
|
||||
#include <memory>
|
||||
#include <testsuite_tr1.h>
|
||||
|
||||
using namespace __gnu_test;
|
||||
|
||||
void
|
||||
test01()
|
||||
{
|
||||
std::shared_ptr<ClassType> ptr;
|
||||
std::shared_ptr<const ClassType> ptr2 = ptr;
|
||||
|
||||
#if __cpp_lib_shared_ptr_arrays >= 201611L
|
||||
std::shared_ptr<ClassType[10]> ptr_array;
|
||||
std::shared_ptr<ClassType[]> ptr_array2 = ptr_array;
|
||||
std::shared_ptr<ClassType const []> ptr_array3 = ptr_array;
|
||||
#endif
|
||||
}
|
||||
|
||||
void
|
||||
test02()
|
||||
{
|
||||
std::shared_ptr<IncompleteClass> ptr;
|
||||
std::shared_ptr<const IncompleteClass> ptr2 = ptr;
|
||||
|
||||
#if __cpp_lib_shared_ptr_arrays >= 201611L
|
||||
std::shared_ptr<IncompleteClass[10]> ptr_array;
|
||||
std::shared_ptr<IncompleteClass[]> ptr_array2 = ptr_array;
|
||||
std::shared_ptr<IncompleteClass const []> ptr_array3 = ptr_array;
|
||||
#endif
|
||||
}
|
|
@ -28,3 +28,15 @@ template class std::shared_ptr<int>;
|
|||
template class std::shared_ptr<void>;
|
||||
template class std::shared_ptr<ClassType>;
|
||||
template class std::shared_ptr<IncompleteClass>;
|
||||
|
||||
#if __cpp_lib_shared_ptr_arrays >= 201611L
|
||||
template class std::shared_ptr<ClassType []>;
|
||||
template class std::shared_ptr<ClassType [42]>;
|
||||
template class std::shared_ptr<ClassType const []>;
|
||||
template class std::shared_ptr<ClassType const [42]>;
|
||||
|
||||
template class std::shared_ptr<IncompleteClass []>;
|
||||
template class std::shared_ptr<IncompleteClass [42]>;
|
||||
template class std::shared_ptr<IncompleteClass const []>;
|
||||
template class std::shared_ptr<IncompleteClass const [42]>;
|
||||
#endif
|
||||
|
|
33
libstdc++-v3/testsuite/20_util/weak_ptr/requirements/1.cc
Normal file
33
libstdc++-v3/testsuite/20_util/weak_ptr/requirements/1.cc
Normal file
|
@ -0,0 +1,33 @@
|
|||
// { dg-do compile { target c++11 } }
|
||||
// { dg-require-effective-target hosted }
|
||||
|
||||
#include <memory>
|
||||
#include <testsuite_tr1.h>
|
||||
|
||||
using namespace __gnu_test;
|
||||
|
||||
void
|
||||
test01()
|
||||
{
|
||||
std::weak_ptr<ClassType> ptr;
|
||||
std::weak_ptr<const ClassType> ptr2 = ptr;
|
||||
|
||||
#if __cpp_lib_shared_ptr_arrays >= 201611L
|
||||
std::weak_ptr<ClassType[10]> ptr_array;
|
||||
std::weak_ptr<ClassType[]> ptr_array2 = ptr_array;
|
||||
std::weak_ptr<ClassType const []> ptr_array3 = ptr_array;
|
||||
#endif
|
||||
}
|
||||
|
||||
void
|
||||
test02()
|
||||
{
|
||||
std::weak_ptr<IncompleteClass> ptr;
|
||||
std::weak_ptr<const IncompleteClass> ptr2 = ptr;
|
||||
|
||||
#if __cpp_lib_shared_ptr_arrays >= 201611L
|
||||
std::weak_ptr<IncompleteClass[10]> ptr_array;
|
||||
std::weak_ptr<IncompleteClass[]> ptr_array2 = ptr_array;
|
||||
std::weak_ptr<IncompleteClass const []> ptr_array3 = ptr_array;
|
||||
#endif
|
||||
}
|
|
@ -28,3 +28,15 @@ template class std::weak_ptr<int>;
|
|||
template class std::weak_ptr<void>;
|
||||
template class std::weak_ptr<ClassType>;
|
||||
template class std::weak_ptr<IncompleteClass>;
|
||||
|
||||
#if __cpp_lib_shared_ptr_arrays >= 201611L
|
||||
template class std::weak_ptr<ClassType []>;
|
||||
template class std::weak_ptr<ClassType [42]>;
|
||||
template class std::weak_ptr<ClassType const []>;
|
||||
template class std::weak_ptr<ClassType const [42]>;
|
||||
|
||||
template class std::weak_ptr<IncompleteClass []>;
|
||||
template class std::weak_ptr<IncompleteClass [42]>;
|
||||
template class std::weak_ptr<IncompleteClass const []>;
|
||||
template class std::weak_ptr<IncompleteClass const [42]>;
|
||||
#endif
|
||||
|
|
Loading…
Add table
Reference in a new issue