Index: include/memory =================================================================== --- include/memory +++ include/memory @@ -3702,11 +3702,25 @@ _Tp* get() _NOEXCEPT {return _VSTD::addressof(__data_.second());} }; +template +void +__shared_ptr_emplace__destroy(_Tp& t) +{ + t.~_Tp(); +} + +template +void +__shared_ptr_emplace__destroy(_Tp (&t)[__n]) +{ + for (auto i = __n; i > 0; i--) __shared_ptr_emplace__destroy(t[i]); +} + template void __shared_ptr_emplace<_Tp, _Alloc>::__on_zero_shared() _NOEXCEPT { - __data_.second().~_Tp(); + __shared_ptr_emplace__destroy(__data_.second()); } template @@ -4699,11 +4713,7 @@ template inline _LIBCPP_INLINE_VISIBILITY -typename enable_if -< - !is_array<_Tp>::value, - shared_ptr<_Tp> ->::type +shared_ptr<_Tp> make_shared(_Args&& ...__args) { return shared_ptr<_Tp>::make_shared(_VSTD::forward<_Args>(__args)...); Index: test/libcxx/memory/shared_ptr_array.pass.cpp =================================================================== --- test/libcxx/memory/shared_ptr_array.pass.cpp +++ test/libcxx/memory/shared_ptr_array.pass.cpp @@ -0,0 +1,83 @@ +//===----------------------------------------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// +// + +// +// UNSUPPORTED: c++98, c++03, c++11, c++14, c++17 + +#include +#include + +#include "test_macros.h" +#include "min_allocator.h" +#include "test_allocator.h" + +static int constructor_count = 0; +static int destructor_count = 0; + +struct test_onstructors +{ + test_onstructors() + { + constructor_count++; + } + + ~test_onstructors() + { + destructor_count++; + } + +}; + +template +void test_make_shared() +{ + std::shared_ptr foo = std::make_shared(); + std::shared_ptr bar(foo); + + typedef decltype(**foo) foo_element_type; + typedef decltype(**bar) bar_element_type; + + assert(typeid(foo_element_type) == typeid(T) && "Types do not match"); + assert(typeid(bar_element_type) == typeid(T) && "Types do not match"); + + /* XXX: Why doesnt this work? + int i[64]; + auto pi = &i; + ASSERT_SAME_TYPE(decltype(**pi), int); + */ +} + +void test_values() +{ + std::shared_ptr foo = std::make_shared(); + + for (int i = 0; i < 64; i++) + (*foo)[i] = i; + + for (int i = 0; i < 64; i++) + assert((*foo)[i] == i && "Incorrect retrieved from array value"); +} + +void test_constructor_count() +{ + std::shared_ptr foo = std::make_shared(); + assert(constructor_count == 64); +} + +int main() +{ + test_make_shared(); + test_make_shared(); + test_make_shared(); + + test_values(); + test_constructor_count(); + + assert(destructor_count == 64); +}