Author: ericwf Date: Fri Oct 7 19:56:22 2016 New Revision: 283631 URL: http://llvm.org/viewvc/llvm-project?rev=283631&view=rev Log: [libc++] Fix stack_allocator
Summary: To quote STL the problems with stack allocator are" >"stack_allocator<T, N> is seriously nonconformant to N4582 17.6.3.5 >[allocator.requirements]. > First, it lacks a rebinding constructor. (The nested "struct rebind" isn't > sufficient.) > Second, it lacks templated equality/inequality. > Third, it completely ignores alignment. > Finally, and most severely, the Standard forbids its existence. Allocators > are forbidden from returning memory "inside themselves". This requirement is > implied by the Standard's requirements for rebinding and equality. It's > permitted to return memory from a separate buffer object on the stack, > though." This patch attempts to address all of those issues. First, instead of storing the buffer inside the allocator I've change `stack_allocator` to accept the buffer as an argument. Second, in order to fix rebinding I changed the parameter list from `<class T, size_t NumElements>` to `<class T, size_t NumBytes>`. This allows allocator rebinding between types that have different sizes. Third, I added copy and rebinding constructors and assignment operators. And finally I fixed the allocation logic to always return properly aligned storage. Reviewers: mclow.lists, howard.hinnant, STL_MSFT Subscribers: cfe-commits Differential Revision: https://reviews.llvm.org/D25154 Removed: libcxx/trunk/test/std/containers/stack_allocator.h Modified: libcxx/trunk/test/std/containers/container.adaptors/priority.queue/priqueue.cons/ctor_comp.pass.cpp libcxx/trunk/test/std/containers/container.adaptors/priority.queue/priqueue.cons/ctor_default.pass.cpp libcxx/trunk/test/std/containers/container.adaptors/queue/queue.cons/ctor_default.pass.cpp libcxx/trunk/test/std/containers/container.adaptors/stack/stack.cons/ctor_default.pass.cpp libcxx/trunk/test/std/containers/sequences/deque/deque.cons/default.pass.cpp libcxx/trunk/test/std/containers/sequences/deque/deque.cons/iter_iter.pass.cpp libcxx/trunk/test/std/containers/sequences/deque/deque.cons/size.pass.cpp libcxx/trunk/test/std/containers/sequences/deque/deque.cons/size_value.pass.cpp libcxx/trunk/test/std/containers/sequences/deque/deque.modifiers/insert_iter_iter.pass.cpp libcxx/trunk/test/std/containers/sequences/list/list.cons/default_stack_alloc.pass.cpp libcxx/trunk/test/std/containers/sequences/list/list.cons/input_iterator.pass.cpp libcxx/trunk/test/std/containers/sequences/list/list.cons/size_type.pass.cpp libcxx/trunk/test/std/containers/sequences/list/list.cons/size_value_alloc.pass.cpp libcxx/trunk/test/std/containers/sequences/vector/vector.capacity/reserve.pass.cpp libcxx/trunk/test/std/containers/sequences/vector/vector.capacity/resize_size.pass.cpp libcxx/trunk/test/std/containers/sequences/vector/vector.capacity/resize_size_value.pass.cpp libcxx/trunk/test/std/containers/sequences/vector/vector.capacity/shrink_to_fit.pass.cpp libcxx/trunk/test/std/containers/sequences/vector/vector.cons/construct_default.pass.cpp libcxx/trunk/test/std/containers/sequences/vector/vector.cons/construct_iter_iter.pass.cpp libcxx/trunk/test/std/containers/sequences/vector/vector.cons/construct_iter_iter_alloc.pass.cpp libcxx/trunk/test/std/containers/sequences/vector/vector.cons/construct_size_value.pass.cpp libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/emplace.pass.cpp libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/emplace_back.pass.cpp libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/insert_iter_iter_iter.pass.cpp libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/insert_iter_rvalue.pass.cpp libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/insert_iter_size_value.pass.cpp libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/insert_iter_value.pass.cpp libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/pop_back.pass.cpp libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/push_back.pass.cpp libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/push_back_rvalue.pass.cpp libcxx/trunk/test/support/test_allocator.h Modified: libcxx/trunk/test/std/containers/container.adaptors/priority.queue/priqueue.cons/ctor_comp.pass.cpp URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/std/containers/container.adaptors/priority.queue/priqueue.cons/ctor_comp.pass.cpp?rev=283631&r1=283630&r2=283631&view=diff ============================================================================== --- libcxx/trunk/test/std/containers/container.adaptors/priority.queue/priqueue.cons/ctor_comp.pass.cpp (original) +++ libcxx/trunk/test/std/containers/container.adaptors/priority.queue/priqueue.cons/ctor_comp.pass.cpp Fri Oct 7 19:56:22 2016 @@ -14,11 +14,11 @@ #include <queue> #include <cassert> -#include "../../../stack_allocator.h" +#include "test_allocator.h" int main() { - std::priority_queue<int, std::vector<int, stack_allocator<int, 10> > > q((std::less<int>())); + std::priority_queue<int, std::vector<int, limited_allocator<int, 10> > > q((std::less<int>())); assert(q.size() == 0); q.push(1); q.push(2); Modified: libcxx/trunk/test/std/containers/container.adaptors/priority.queue/priqueue.cons/ctor_default.pass.cpp URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/std/containers/container.adaptors/priority.queue/priqueue.cons/ctor_default.pass.cpp?rev=283631&r1=283630&r2=283631&view=diff ============================================================================== --- libcxx/trunk/test/std/containers/container.adaptors/priority.queue/priqueue.cons/ctor_default.pass.cpp (original) +++ libcxx/trunk/test/std/containers/container.adaptors/priority.queue/priqueue.cons/ctor_default.pass.cpp Fri Oct 7 19:56:22 2016 @@ -14,11 +14,11 @@ #include <queue> #include <cassert> -#include "../../../stack_allocator.h" +#include "test_allocator.h" int main() { - std::priority_queue<int, std::vector<int, stack_allocator<int, 10> > > q; + std::priority_queue<int, std::vector<int, limited_allocator<int, 10> > > q; assert(q.size() == 0); q.push(1); q.push(2); Modified: libcxx/trunk/test/std/containers/container.adaptors/queue/queue.cons/ctor_default.pass.cpp URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/std/containers/container.adaptors/queue/queue.cons/ctor_default.pass.cpp?rev=283631&r1=283630&r2=283631&view=diff ============================================================================== --- libcxx/trunk/test/std/containers/container.adaptors/queue/queue.cons/ctor_default.pass.cpp (original) +++ libcxx/trunk/test/std/containers/container.adaptors/queue/queue.cons/ctor_default.pass.cpp Fri Oct 7 19:56:22 2016 @@ -14,11 +14,11 @@ #include <queue> #include <cassert> -#include "../../../stack_allocator.h" +#include "test_allocator.h" int main() { - std::queue<int, std::vector<int, stack_allocator<int, 10> > > q; + std::queue<int, std::vector<int, limited_allocator<int, 10> > > q; assert(q.size() == 0); q.push(1); q.push(2); Modified: libcxx/trunk/test/std/containers/container.adaptors/stack/stack.cons/ctor_default.pass.cpp URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/std/containers/container.adaptors/stack/stack.cons/ctor_default.pass.cpp?rev=283631&r1=283630&r2=283631&view=diff ============================================================================== --- libcxx/trunk/test/std/containers/container.adaptors/stack/stack.cons/ctor_default.pass.cpp (original) +++ libcxx/trunk/test/std/containers/container.adaptors/stack/stack.cons/ctor_default.pass.cpp Fri Oct 7 19:56:22 2016 @@ -15,11 +15,11 @@ #include <vector> #include <cassert> -#include "../../../stack_allocator.h" +#include "test_allocator.h" int main() { - std::stack<int, std::vector<int, stack_allocator<int, 10> > > q; + std::stack<int, std::vector<int, limited_allocator<int, 10> > > q; assert(q.size() == 0); q.push(1); q.push(2); Modified: libcxx/trunk/test/std/containers/sequences/deque/deque.cons/default.pass.cpp URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/std/containers/sequences/deque/deque.cons/default.pass.cpp?rev=283631&r1=283630&r2=283631&view=diff ============================================================================== --- libcxx/trunk/test/std/containers/sequences/deque/deque.cons/default.pass.cpp (original) +++ libcxx/trunk/test/std/containers/sequences/deque/deque.cons/default.pass.cpp Fri Oct 7 19:56:22 2016 @@ -14,7 +14,7 @@ #include <deque> #include <cassert> -#include "../../../stack_allocator.h" +#include "test_allocator.h" #include "../../../NotConstructible.h" #include "min_allocator.h" @@ -33,7 +33,7 @@ test() int main() { test<int, std::allocator<int> >(); - test<NotConstructible, stack_allocator<NotConstructible, 1> >(); + test<NotConstructible, limited_allocator<NotConstructible, 1> >(); #if TEST_STD_VER >= 11 test<int, min_allocator<int> >(); test<NotConstructible, min_allocator<NotConstructible> >(); Modified: libcxx/trunk/test/std/containers/sequences/deque/deque.cons/iter_iter.pass.cpp URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/std/containers/sequences/deque/deque.cons/iter_iter.pass.cpp?rev=283631&r1=283630&r2=283631&view=diff ============================================================================== --- libcxx/trunk/test/std/containers/sequences/deque/deque.cons/iter_iter.pass.cpp (original) +++ libcxx/trunk/test/std/containers/sequences/deque/deque.cons/iter_iter.pass.cpp Fri Oct 7 19:56:22 2016 @@ -14,7 +14,7 @@ #include <deque> #include <cassert> -#include "../../../stack_allocator.h" +#include "test_allocator.h" #include "test_iterators.h" #include "min_allocator.h" @@ -55,7 +55,7 @@ int main() test(forward_iterator<const int*>(ab), forward_iterator<const int*>(an)); test(bidirectional_iterator<const int*>(ab), bidirectional_iterator<const int*>(an)); test(random_access_iterator<const int*>(ab), random_access_iterator<const int*>(an)); - test<stack_allocator<int, 4096> >(ab, an); + test<limited_allocator<int, 4096> >(ab, an); #if TEST_STD_VER >= 11 test<min_allocator<int> >(ab, an); #endif Modified: libcxx/trunk/test/std/containers/sequences/deque/deque.cons/size.pass.cpp URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/std/containers/sequences/deque/deque.cons/size.pass.cpp?rev=283631&r1=283630&r2=283631&view=diff ============================================================================== --- libcxx/trunk/test/std/containers/sequences/deque/deque.cons/size.pass.cpp (original) +++ libcxx/trunk/test/std/containers/sequences/deque/deque.cons/size.pass.cpp Fri Oct 7 19:56:22 2016 @@ -14,7 +14,7 @@ #include <deque> #include <cassert> -#include "../../../stack_allocator.h" +#include "test_allocator.h" #include "DefaultOnly.h" #include "min_allocator.h" @@ -98,7 +98,7 @@ int main() test<DefaultOnly, std::allocator<DefaultOnly> >(4096); test<DefaultOnly, std::allocator<DefaultOnly> >(4097); - test1<DefaultOnly, stack_allocator<DefaultOnly, 4096> >(4095); + test1<DefaultOnly, limited_allocator<DefaultOnly, 4096> >(4095); #if TEST_STD_VER >= 11 test<DefaultOnly, min_allocator<DefaultOnly> >(4095); Modified: libcxx/trunk/test/std/containers/sequences/deque/deque.cons/size_value.pass.cpp URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/std/containers/sequences/deque/deque.cons/size_value.pass.cpp?rev=283631&r1=283630&r2=283631&view=diff ============================================================================== --- libcxx/trunk/test/std/containers/sequences/deque/deque.cons/size_value.pass.cpp (original) +++ libcxx/trunk/test/std/containers/sequences/deque/deque.cons/size_value.pass.cpp Fri Oct 7 19:56:22 2016 @@ -14,7 +14,7 @@ #include <deque> #include <cassert> -#include "../../../stack_allocator.h" +#include "test_allocator.h" #include "min_allocator.h" template <class T, class Allocator> @@ -44,7 +44,7 @@ int main() test<int, std::allocator<int> >(4095, 78); test<int, std::allocator<int> >(4096, 1165); test<int, std::allocator<int> >(4097, 157); - test<int, stack_allocator<int, 4096> >(4095, 90); + test<int, limited_allocator<int, 4096> >(4095, 90); #if TEST_STD_VER >= 11 test<int, min_allocator<int> >(4095, 90); #endif Modified: libcxx/trunk/test/std/containers/sequences/deque/deque.modifiers/insert_iter_iter.pass.cpp URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/std/containers/sequences/deque/deque.modifiers/insert_iter_iter.pass.cpp?rev=283631&r1=283630&r2=283631&view=diff ============================================================================== --- libcxx/trunk/test/std/containers/sequences/deque/deque.modifiers/insert_iter_iter.pass.cpp (original) +++ libcxx/trunk/test/std/containers/sequences/deque/deque.modifiers/insert_iter_iter.pass.cpp Fri Oct 7 19:56:22 2016 @@ -20,7 +20,7 @@ #include "test_macros.h" #include "test_iterators.h" #include "MoveOnly.h" -#include "../../../stack_allocator.h" +#include "test_allocator.h" #include "min_allocator.h" template <class C> @@ -270,7 +270,7 @@ int main() testN<std::deque<int> >(rng[i], rng[j], rng[k]); testNI<std::deque<int> >(1500, 2000, 1000); #if TEST_STD_VER >= 11 - test_move<std::deque<MoveOnly, stack_allocator<MoveOnly, 2000> > >(); + test_move<std::deque<MoveOnly, limited_allocator<MoveOnly, 2000> > >(); #endif } #if TEST_STD_VER >= 11 Modified: libcxx/trunk/test/std/containers/sequences/list/list.cons/default_stack_alloc.pass.cpp URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/std/containers/sequences/list/list.cons/default_stack_alloc.pass.cpp?rev=283631&r1=283630&r2=283631&view=diff ============================================================================== --- libcxx/trunk/test/std/containers/sequences/list/list.cons/default_stack_alloc.pass.cpp (original) +++ libcxx/trunk/test/std/containers/sequences/list/list.cons/default_stack_alloc.pass.cpp Fri Oct 7 19:56:22 2016 @@ -13,7 +13,7 @@ #include <list> #include <cassert> -#include "../../../stack_allocator.h" +#include "test_allocator.h" #include "min_allocator.h" int main() @@ -29,7 +29,7 @@ int main() assert(std::distance(l.begin(), l.end()) == 0); } { - std::list<int, stack_allocator<int, 4> > l; + std::list<int, limited_allocator<int, 4> > l; assert(l.size() == 0); assert(std::distance(l.begin(), l.end()) == 0); } Modified: libcxx/trunk/test/std/containers/sequences/list/list.cons/input_iterator.pass.cpp URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/std/containers/sequences/list/list.cons/input_iterator.pass.cpp?rev=283631&r1=283630&r2=283631&view=diff ============================================================================== --- libcxx/trunk/test/std/containers/sequences/list/list.cons/input_iterator.pass.cpp (original) +++ libcxx/trunk/test/std/containers/sequences/list/list.cons/input_iterator.pass.cpp Fri Oct 7 19:56:22 2016 @@ -15,7 +15,7 @@ #include <list> #include <cassert> #include "test_iterators.h" -#include "../../../stack_allocator.h" +#include "test_allocator.h" #include "min_allocator.h" int main() @@ -43,7 +43,7 @@ int main() } { int a[] = {0, 1, 2, 3}; - std::list<int, stack_allocator<int, sizeof(a)/sizeof(a[0])> > l(input_iterator<const int*>(a), + std::list<int, limited_allocator<int, sizeof(a)/sizeof(a[0])> > l(input_iterator<const int*>(a), input_iterator<const int*>(a + sizeof(a)/sizeof(a[0]))); assert(l.size() == sizeof(a)/sizeof(a[0])); assert(std::distance(l.begin(), l.end()) == sizeof(a)/sizeof(a[0])); Modified: libcxx/trunk/test/std/containers/sequences/list/list.cons/size_type.pass.cpp URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/std/containers/sequences/list/list.cons/size_type.pass.cpp?rev=283631&r1=283630&r2=283631&view=diff ============================================================================== --- libcxx/trunk/test/std/containers/sequences/list/list.cons/size_type.pass.cpp (original) +++ libcxx/trunk/test/std/containers/sequences/list/list.cons/size_type.pass.cpp Fri Oct 7 19:56:22 2016 @@ -14,7 +14,7 @@ #include <list> #include <cassert> #include "DefaultOnly.h" -#include "../../../stack_allocator.h" +#include "test_allocator.h" #include "min_allocator.h" template <class T, class Allocator> @@ -48,7 +48,7 @@ int main() assert(*i == 0); } { - std::list<int, stack_allocator<int, 3> > l(3); + std::list<int, limited_allocator<int, 3> > l(3); assert(l.size() == 3); assert(std::distance(l.begin(), l.end()) == 3); std::list<int>::const_iterator i = l.begin(); Modified: libcxx/trunk/test/std/containers/sequences/list/list.cons/size_value_alloc.pass.cpp URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/std/containers/sequences/list/list.cons/size_value_alloc.pass.cpp?rev=283631&r1=283630&r2=283631&view=diff ============================================================================== --- libcxx/trunk/test/std/containers/sequences/list/list.cons/size_value_alloc.pass.cpp (original) +++ libcxx/trunk/test/std/containers/sequences/list/list.cons/size_value_alloc.pass.cpp Fri Oct 7 19:56:22 2016 @@ -14,7 +14,7 @@ #include <list> #include <cassert> #include "DefaultOnly.h" -#include "../../../stack_allocator.h" +#include "test_allocator.h" #include "min_allocator.h" int main() @@ -42,7 +42,7 @@ int main() assert(*i == 2); } { - std::list<int, stack_allocator<int, 3> > l(3, 2); + std::list<int, limited_allocator<int, 3> > l(3, 2); assert(l.size() == 3); assert(std::distance(l.begin(), l.end()) == 3); std::list<int>::const_iterator i = l.begin(); Modified: libcxx/trunk/test/std/containers/sequences/vector/vector.capacity/reserve.pass.cpp URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/std/containers/sequences/vector/vector.capacity/reserve.pass.cpp?rev=283631&r1=283630&r2=283631&view=diff ============================================================================== --- libcxx/trunk/test/std/containers/sequences/vector/vector.capacity/reserve.pass.cpp (original) +++ libcxx/trunk/test/std/containers/sequences/vector/vector.capacity/reserve.pass.cpp Fri Oct 7 19:56:22 2016 @@ -13,7 +13,7 @@ #include <vector> #include <cassert> -#include "../../../stack_allocator.h" +#include "test_allocator.h" #include "min_allocator.h" #include "asan_testing.h" @@ -37,7 +37,7 @@ int main() assert(is_contiguous_container_asan_correct(v)); } { - std::vector<int, stack_allocator<int, 250> > v(100); + std::vector<int, limited_allocator<int, 250> > v(100); assert(v.capacity() == 100); v.reserve(50); assert(v.size() == 100); Modified: libcxx/trunk/test/std/containers/sequences/vector/vector.capacity/resize_size.pass.cpp URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/std/containers/sequences/vector/vector.capacity/resize_size.pass.cpp?rev=283631&r1=283630&r2=283631&view=diff ============================================================================== --- libcxx/trunk/test/std/containers/sequences/vector/vector.capacity/resize_size.pass.cpp (original) +++ libcxx/trunk/test/std/containers/sequences/vector/vector.capacity/resize_size.pass.cpp Fri Oct 7 19:56:22 2016 @@ -13,7 +13,7 @@ #include <vector> #include <cassert> -#include "../../../stack_allocator.h" +#include "test_allocator.h" #include "MoveOnly.h" #include "min_allocator.h" #include "asan_testing.h" @@ -33,7 +33,7 @@ int main() assert(is_contiguous_container_asan_correct(v)); } { - std::vector<MoveOnly, stack_allocator<MoveOnly, 300> > v(100); + std::vector<MoveOnly, limited_allocator<MoveOnly, 300> > v(100); v.resize(50); assert(v.size() == 50); assert(v.capacity() == 100); @@ -56,7 +56,7 @@ int main() assert(is_contiguous_container_asan_correct(v)); } { - std::vector<int, stack_allocator<int, 300> > v(100); + std::vector<int, limited_allocator<int, 300> > v(100); v.resize(50); assert(v.size() == 50); assert(v.capacity() == 100); Modified: libcxx/trunk/test/std/containers/sequences/vector/vector.capacity/resize_size_value.pass.cpp URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/std/containers/sequences/vector/vector.capacity/resize_size_value.pass.cpp?rev=283631&r1=283630&r2=283631&view=diff ============================================================================== --- libcxx/trunk/test/std/containers/sequences/vector/vector.capacity/resize_size_value.pass.cpp (original) +++ libcxx/trunk/test/std/containers/sequences/vector/vector.capacity/resize_size_value.pass.cpp Fri Oct 7 19:56:22 2016 @@ -13,7 +13,7 @@ #include <vector> #include <cassert> -#include "../../../stack_allocator.h" +#include "test_allocator.h" #include "min_allocator.h" #include "asan_testing.h" @@ -35,7 +35,7 @@ int main() assert(v[i] == 1); } { - std::vector<int, stack_allocator<int, 300> > v(100); + std::vector<int, limited_allocator<int, 300> > v(100); v.resize(50, 1); assert(v.size() == 50); assert(v.capacity() == 100); Modified: libcxx/trunk/test/std/containers/sequences/vector/vector.capacity/shrink_to_fit.pass.cpp URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/std/containers/sequences/vector/vector.capacity/shrink_to_fit.pass.cpp?rev=283631&r1=283630&r2=283631&view=diff ============================================================================== --- libcxx/trunk/test/std/containers/sequences/vector/vector.capacity/shrink_to_fit.pass.cpp (original) +++ libcxx/trunk/test/std/containers/sequences/vector/vector.capacity/shrink_to_fit.pass.cpp Fri Oct 7 19:56:22 2016 @@ -13,7 +13,7 @@ #include <vector> #include <cassert> -#include "../../../stack_allocator.h" +#include "test_allocator.h" #include "min_allocator.h" #include "asan_testing.h" @@ -29,7 +29,7 @@ int main() assert(is_contiguous_container_asan_correct(v)); } { - std::vector<int, stack_allocator<int, 401> > v(100); + std::vector<int, limited_allocator<int, 401> > v(100); v.push_back(1); assert(is_contiguous_container_asan_correct(v)); v.shrink_to_fit(); @@ -39,7 +39,7 @@ int main() } #ifndef _LIBCPP_NO_EXCEPTIONS { - std::vector<int, stack_allocator<int, 400> > v(100); + std::vector<int, limited_allocator<int, 400> > v(100); v.push_back(1); assert(is_contiguous_container_asan_correct(v)); v.shrink_to_fit(); Modified: libcxx/trunk/test/std/containers/sequences/vector/vector.cons/construct_default.pass.cpp URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/std/containers/sequences/vector/vector.cons/construct_default.pass.cpp?rev=283631&r1=283630&r2=283631&view=diff ============================================================================== --- libcxx/trunk/test/std/containers/sequences/vector/vector.cons/construct_default.pass.cpp (original) +++ libcxx/trunk/test/std/containers/sequences/vector/vector.cons/construct_default.pass.cpp Fri Oct 7 19:56:22 2016 @@ -18,7 +18,7 @@ #include "test_macros.h" #include "test_allocator.h" #include "../../../NotConstructible.h" -#include "../../../stack_allocator.h" +#include "test_allocator.h" #include "min_allocator.h" #include "asan_testing.h" @@ -71,7 +71,7 @@ int main() (test_allocator<NotConstructible>(5)); } { - std::vector<int, stack_allocator<int, 10> > v; + std::vector<int, limited_allocator<int, 10> > v; assert(v.empty()); } #if TEST_STD_VER >= 11 Modified: libcxx/trunk/test/std/containers/sequences/vector/vector.cons/construct_iter_iter.pass.cpp URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/std/containers/sequences/vector/vector.cons/construct_iter_iter.pass.cpp?rev=283631&r1=283630&r2=283631&view=diff ============================================================================== --- libcxx/trunk/test/std/containers/sequences/vector/vector.cons/construct_iter_iter.pass.cpp (original) +++ libcxx/trunk/test/std/containers/sequences/vector/vector.cons/construct_iter_iter.pass.cpp Fri Oct 7 19:56:22 2016 @@ -16,7 +16,7 @@ #include "test_macros.h" #include "test_iterators.h" -#include "../../../stack_allocator.h" +#include "test_allocator.h" #include "min_allocator.h" #include "asan_testing.h" @@ -42,11 +42,11 @@ int main() test<std::vector<int> >(random_access_iterator<const int*>(a), random_access_iterator<const int*>(an)); test<std::vector<int> >(a, an); - test<std::vector<int, stack_allocator<int, 63> > >(input_iterator<const int*>(a), input_iterator<const int*>(an)); - test<std::vector<int, stack_allocator<int, 18> > >(forward_iterator<const int*>(a), forward_iterator<const int*>(an)); - test<std::vector<int, stack_allocator<int, 18> > >(bidirectional_iterator<const int*>(a), bidirectional_iterator<const int*>(an)); - test<std::vector<int, stack_allocator<int, 18> > >(random_access_iterator<const int*>(a), random_access_iterator<const int*>(an)); - test<std::vector<int, stack_allocator<int, 18> > >(a, an); + test<std::vector<int, limited_allocator<int, 63> > >(input_iterator<const int*>(a), input_iterator<const int*>(an)); + test<std::vector<int, limited_allocator<int, 18> > >(forward_iterator<const int*>(a), forward_iterator<const int*>(an)); + test<std::vector<int, limited_allocator<int, 18> > >(bidirectional_iterator<const int*>(a), bidirectional_iterator<const int*>(an)); + test<std::vector<int, limited_allocator<int, 18> > >(random_access_iterator<const int*>(a), random_access_iterator<const int*>(an)); + test<std::vector<int, limited_allocator<int, 18> > >(a, an); #if TEST_STD_VER >= 11 test<std::vector<int, min_allocator<int>> >(input_iterator<const int*>(a), input_iterator<const int*>(an)); test<std::vector<int, min_allocator<int>> >(forward_iterator<const int*>(a), forward_iterator<const int*>(an)); Modified: libcxx/trunk/test/std/containers/sequences/vector/vector.cons/construct_iter_iter_alloc.pass.cpp URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/std/containers/sequences/vector/vector.cons/construct_iter_iter_alloc.pass.cpp?rev=283631&r1=283630&r2=283631&view=diff ============================================================================== --- libcxx/trunk/test/std/containers/sequences/vector/vector.cons/construct_iter_iter_alloc.pass.cpp (original) +++ libcxx/trunk/test/std/containers/sequences/vector/vector.cons/construct_iter_iter_alloc.pass.cpp Fri Oct 7 19:56:22 2016 @@ -17,7 +17,7 @@ #include "test_macros.h" #include "test_iterators.h" -#include "../../../stack_allocator.h" +#include "test_allocator.h" #include "min_allocator.h" #include "asan_testing.h" Modified: libcxx/trunk/test/std/containers/sequences/vector/vector.cons/construct_size_value.pass.cpp URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/std/containers/sequences/vector/vector.cons/construct_size_value.pass.cpp?rev=283631&r1=283630&r2=283631&view=diff ============================================================================== --- libcxx/trunk/test/std/containers/sequences/vector/vector.cons/construct_size_value.pass.cpp (original) +++ libcxx/trunk/test/std/containers/sequences/vector/vector.cons/construct_size_value.pass.cpp Fri Oct 7 19:56:22 2016 @@ -15,7 +15,7 @@ #include <cassert> #include "test_macros.h" -#include "../../../stack_allocator.h" +#include "test_allocator.h" #include "min_allocator.h" #include "asan_testing.h" @@ -34,7 +34,7 @@ test(typename C::size_type n, const type int main() { test<std::vector<int> >(50, 3); - test<std::vector<int, stack_allocator<int, 50> > >(50, 5); + test<std::vector<int, limited_allocator<int, 50> > >(50, 5); #if TEST_STD_VER >= 11 test<std::vector<int, min_allocator<int>> >(50, 3); #endif Modified: libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/emplace.pass.cpp URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/emplace.pass.cpp?rev=283631&r1=283630&r2=283631&view=diff ============================================================================== --- libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/emplace.pass.cpp (original) +++ libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/emplace.pass.cpp Fri Oct 7 19:56:22 2016 @@ -17,7 +17,7 @@ #include <vector> #include <cassert> -#include "../../../stack_allocator.h" +#include "test_allocator.h" #include "min_allocator.h" #include "asan_testing.h" @@ -88,8 +88,8 @@ int main() assert(is_contiguous_container_asan_correct(c)); } { - std::vector<A, stack_allocator<A, 7> > c; - std::vector<A, stack_allocator<A, 7> >::iterator i = c.emplace(c.cbegin(), 2, 3.5); + std::vector<A, limited_allocator<A, 7> > c; + std::vector<A, limited_allocator<A, 7> >::iterator i = c.emplace(c.cbegin(), 2, 3.5); assert(i == c.begin()); assert(c.size() == 1); assert(c.front().geti() == 2); Modified: libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/emplace_back.pass.cpp URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/emplace_back.pass.cpp?rev=283631&r1=283630&r2=283631&view=diff ============================================================================== --- libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/emplace_back.pass.cpp (original) +++ libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/emplace_back.pass.cpp Fri Oct 7 19:56:22 2016 @@ -15,7 +15,7 @@ #include <vector> #include <cassert> -#include "../../../stack_allocator.h" +#include "test_allocator.h" #include "min_allocator.h" #include "test_allocator.h" #include "asan_testing.h" @@ -72,7 +72,7 @@ int main() assert(is_contiguous_container_asan_correct(c)); } { - std::vector<A, stack_allocator<A, 4> > c; + std::vector<A, limited_allocator<A, 4> > c; A& r1 = c.emplace_back(2, 3.5); assert(c.size() == 1); assert(&r1 == &c.back()); Modified: libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/insert_iter_iter_iter.pass.cpp URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/insert_iter_iter_iter.pass.cpp?rev=283631&r1=283630&r2=283631&view=diff ============================================================================== --- libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/insert_iter_iter_iter.pass.cpp (original) +++ libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/insert_iter_iter_iter.pass.cpp Fri Oct 7 19:56:22 2016 @@ -18,7 +18,7 @@ #include <vector> #include <cassert> -#include "../../../stack_allocator.h" +#include "test_allocator.h" #include "test_iterators.h" #include "min_allocator.h" #include "asan_testing.h" @@ -96,7 +96,7 @@ int main() assert(v[j] == 0); } { - std::vector<int, stack_allocator<int, 308> > v(100); + std::vector<int, limited_allocator<int, 308> > v(100); int a[] = {1, 2, 3, 4, 5}; const int N = sizeof(a)/sizeof(a[0]); std::vector<int>::iterator i = v.insert(v.cbegin() + 10, input_iterator<const int*>(a), @@ -113,7 +113,7 @@ int main() assert(v[j] == 0); } { - std::vector<int, stack_allocator<int, 300> > v(100); + std::vector<int, limited_allocator<int, 300> > v(100); int a[] = {1, 2, 3, 4, 5}; const int N = sizeof(a)/sizeof(a[0]); std::vector<int>::iterator i = v.insert(v.cbegin() + 10, forward_iterator<const int*>(a), Modified: libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/insert_iter_rvalue.pass.cpp URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/insert_iter_rvalue.pass.cpp?rev=283631&r1=283630&r2=283631&view=diff ============================================================================== --- libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/insert_iter_rvalue.pass.cpp (original) +++ libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/insert_iter_rvalue.pass.cpp Fri Oct 7 19:56:22 2016 @@ -17,7 +17,7 @@ #include <vector> #include <cassert> -#include "../../../stack_allocator.h" +#include "test_allocator.h" #include "MoveOnly.h" #include "min_allocator.h" #include "asan_testing.h" @@ -39,8 +39,8 @@ int main() assert(v[j] == MoveOnly()); } { - std::vector<MoveOnly, stack_allocator<MoveOnly, 300> > v(100); - std::vector<MoveOnly, stack_allocator<MoveOnly, 300> >::iterator i = v.insert(v.cbegin() + 10, MoveOnly(3)); + std::vector<MoveOnly, limited_allocator<MoveOnly, 300> > v(100); + std::vector<MoveOnly, limited_allocator<MoveOnly, 300> >::iterator i = v.insert(v.cbegin() + 10, MoveOnly(3)); assert(v.size() == 101); assert(is_contiguous_container_asan_correct(v)); assert(i == v.begin() + 10); Modified: libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/insert_iter_size_value.pass.cpp URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/insert_iter_size_value.pass.cpp?rev=283631&r1=283630&r2=283631&view=diff ============================================================================== --- libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/insert_iter_size_value.pass.cpp (original) +++ libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/insert_iter_size_value.pass.cpp Fri Oct 7 19:56:22 2016 @@ -17,7 +17,7 @@ #include <vector> #include <cassert> -#include "../../../stack_allocator.h" +#include "test_allocator.h" #include "min_allocator.h" #include "asan_testing.h" @@ -70,8 +70,8 @@ int main() assert(v[j] == 0); } { - std::vector<int, stack_allocator<int, 300> > v(100); - std::vector<int, stack_allocator<int, 300> >::iterator i = v.insert(v.cbegin() + 10, 5, 1); + std::vector<int, limited_allocator<int, 300> > v(100); + std::vector<int, limited_allocator<int, 300> >::iterator i = v.insert(v.cbegin() + 10, 5, 1); assert(v.size() == 105); assert(is_contiguous_container_asan_correct(v)); assert(i == v.begin() + 10); Modified: libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/insert_iter_value.pass.cpp URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/insert_iter_value.pass.cpp?rev=283631&r1=283630&r2=283631&view=diff ============================================================================== --- libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/insert_iter_value.pass.cpp (original) +++ libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/insert_iter_value.pass.cpp Fri Oct 7 19:56:22 2016 @@ -17,7 +17,7 @@ #include <vector> #include <cassert> -#include "../../../stack_allocator.h" +#include "test_allocator.h" #include "min_allocator.h" #include "asan_testing.h" @@ -68,8 +68,8 @@ int main() assert(v[j] == 0); } { - std::vector<int, stack_allocator<int, 300> > v(100); - std::vector<int, stack_allocator<int, 300> >::iterator i = v.insert(v.cbegin() + 10, 1); + std::vector<int, limited_allocator<int, 300> > v(100); + std::vector<int, limited_allocator<int, 300> >::iterator i = v.insert(v.cbegin() + 10, 1); assert(v.size() == 101); assert(is_contiguous_container_asan_correct(v)); assert(i == v.begin() + 10); Modified: libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/pop_back.pass.cpp URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/pop_back.pass.cpp?rev=283631&r1=283630&r2=283631&view=diff ============================================================================== --- libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/pop_back.pass.cpp (original) +++ libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/pop_back.pass.cpp Fri Oct 7 19:56:22 2016 @@ -17,7 +17,7 @@ #include <vector> #include <cassert> -#include "../../../stack_allocator.h" +#include "test_allocator.h" #include "min_allocator.h" #if _LIBCPP_DEBUG >= 1 Modified: libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/push_back.pass.cpp URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/push_back.pass.cpp?rev=283631&r1=283630&r2=283631&view=diff ============================================================================== --- libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/push_back.pass.cpp (original) +++ libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/push_back.pass.cpp Fri Oct 7 19:56:22 2016 @@ -13,7 +13,7 @@ #include <vector> #include <cassert> -#include "../../../stack_allocator.h" +#include "test_allocator.h" #include "min_allocator.h" #include "asan_testing.h" @@ -48,7 +48,7 @@ int main() assert(c[j] == j); } { - std::vector<int, stack_allocator<int, 15> > c; + std::vector<int, limited_allocator<int, 15> > c; c.push_back(0); assert(c.size() == 1); assert(is_contiguous_container_asan_correct(c)); Modified: libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/push_back_rvalue.pass.cpp URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/push_back_rvalue.pass.cpp?rev=283631&r1=283630&r2=283631&view=diff ============================================================================== --- libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/push_back_rvalue.pass.cpp (original) +++ libcxx/trunk/test/std/containers/sequences/vector/vector.modifiers/push_back_rvalue.pass.cpp Fri Oct 7 19:56:22 2016 @@ -14,7 +14,7 @@ #include <vector> #include <cassert> #include "MoveOnly.h" -#include "../../../stack_allocator.h" +#include "test_allocator.h" #include "min_allocator.h" #include "asan_testing.h" @@ -50,7 +50,7 @@ int main() assert(c[j] == MoveOnly(j)); } { - std::vector<MoveOnly, stack_allocator<MoveOnly, 15> > c; + std::vector<MoveOnly, limited_allocator<MoveOnly, 15> > c; c.push_back(MoveOnly(0)); assert(c.size() == 1); assert(is_contiguous_container_asan_correct(c)); Removed: libcxx/trunk/test/std/containers/stack_allocator.h URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/std/containers/stack_allocator.h?rev=283630&view=auto ============================================================================== --- libcxx/trunk/test/std/containers/stack_allocator.h (original) +++ libcxx/trunk/test/std/containers/stack_allocator.h (removed) @@ -1,66 +0,0 @@ -//===----------------------------------------------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#ifndef STACK_ALLOCATOR_H -#define STACK_ALLOCATOR_H - -#include <cstddef> -#include <new> - -template <class T, std::size_t N> -class stack_allocator -{ - char buf_[sizeof(T)*N]; - char* ptr_; -public: - typedef T value_type; - typedef value_type* pointer; - typedef const value_type* const_pointer; - typedef value_type& reference; - typedef const value_type& const_reference; - typedef std::size_t size_type; - typedef std::ptrdiff_t difference_type; - - template <class U> struct rebind {typedef stack_allocator<U, N> other;}; - - stack_allocator() : ptr_(buf_) {} - -private: - stack_allocator(const stack_allocator&);// = delete; - stack_allocator& operator=(const stack_allocator&);// = delete; - -public: - pointer allocate(size_type n, const void* = 0) - { - if (n > N - (ptr_ - buf_) / sizeof(value_type)) { -#ifndef _LIBCPP_NO_EXCEPTIONS - throw std::bad_alloc(); -#else - std::terminate(); -#endif - } - pointer r = (T*)ptr_; - ptr_ += n * sizeof(T); - return r; - } - void deallocate(pointer p, size_type n) - { - if ((char*)(p + n) == ptr_) - ptr_ = (char*)p; - } - - size_type max_size() const {return N;} -}; - -template <class T, std::size_t N> -inline -void -swap(stack_allocator<T, N>& x, stack_allocator<T, N>& y) {} - -#endif // STACK_ALLOCATOR_H Modified: libcxx/trunk/test/support/test_allocator.h URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/support/test_allocator.h?rev=283631&r1=283630&r2=283631&view=diff ============================================================================== --- libcxx/trunk/test/support/test_allocator.h (original) +++ libcxx/trunk/test/support/test_allocator.h Fri Oct 7 19:56:22 2016 @@ -302,5 +302,78 @@ operator!=(const TaggingAllocator<T>&, c { return false; } #endif +template <std::size_t MaxAllocs> +struct limited_alloc_handle { + std::size_t outstanding_; + void* last_alloc_; + + limited_alloc_handle() : outstanding_(0), last_alloc_(nullptr) {} + + template <class T> + T *allocate(std::size_t N) { + if (N + outstanding_ > MaxAllocs) + TEST_THROW(std::bad_alloc()); + last_alloc_ = ::operator new(N*sizeof(T)); + outstanding_ += N; + return static_cast<T*>(last_alloc_); + } + + void deallocate(void* ptr, std::size_t N) { + if (ptr == last_alloc_) { + last_alloc_ = nullptr; + assert(outstanding_ >= N); + outstanding_ -= N; + } + ::operator delete(ptr); + } +}; + +template <class T, std::size_t N> +class limited_allocator +{ + typedef limited_alloc_handle<N> BuffT; + std::shared_ptr<BuffT> handle_; +public: + typedef T value_type; + typedef value_type* pointer; + typedef const value_type* const_pointer; + typedef value_type& reference; + typedef const value_type& const_reference; + typedef std::size_t size_type; + typedef std::ptrdiff_t difference_type; + + template <class U> struct rebind { typedef limited_allocator<U, N> other; }; + + limited_allocator() : handle_(new BuffT) {} + + limited_allocator(limited_allocator const& other) : handle_(other.handle_) {} + + template <class U> + explicit limited_allocator(limited_allocator<U, N> const& other) + : handle_(other.handle_) {} + +private: + limited_allocator& operator=(const limited_allocator&);// = delete; + +public: + pointer allocate(size_type n) { return handle_->template allocate<T>(n); } + void deallocate(pointer p, size_type n) { handle_->deallocate(p, n); } + size_type max_size() const {return N;} + + BuffT* getHandle() const { return handle_.get(); } +}; + +template <class T, class U, std::size_t N> +inline bool operator==(limited_allocator<T, N> const& LHS, + limited_allocator<U, N> const& RHS) { + return LHS.getHandle() == RHS.getHandle(); +} + +template <class T, class U, std::size_t N> +inline bool operator!=(limited_allocator<T, N> const& LHS, + limited_allocator<U, N> const& RHS) { + return !(LHS == RHS); +} + #endif // TEST_ALLOCATOR_H _______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits