1 //===----------------------------------------------------------------------===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8
9 // UNSUPPORTED: c++03
10
11 // <scoped_allocator>
12
13 // template <class OuterAlloc, class... InnerAllocs>
14 // class scoped_allocator_adaptor
15
16 // template <class OuterA2>
17 // scoped_allocator_adaptor(OuterA2&& outerAlloc,
18 // const InnerAllocs& ...innerAllocs);
19
20 #include <scoped_allocator>
21 #include <cassert>
22
23 #include "test_macros.h"
24 #include "allocators.h"
25
main(int,char **)26 int main(int, char**) {
27 {
28 typedef std::scoped_allocator_adaptor<A1<int>> A;
29 A1<int> a3(3);
30 A a(a3);
31 assert(a.outer_allocator() == A1<int>(3));
32 assert(a.inner_allocator() == a);
33 assert(A1<int>::copy_called == true);
34 assert(A1<int>::move_called == false);
35 }
36 A1<int>::copy_called = false;
37 {
38 typedef std::scoped_allocator_adaptor<A1<int>> A;
39 A a(A1<int>(3));
40 assert(a.outer_allocator() == A1<int>(3));
41 assert(a.inner_allocator() == a);
42 assert(A1<int>::copy_called == false);
43 assert(A1<int>::move_called == true);
44 }
45 A1<int>::move_called = false;
46 {
47 typedef std::scoped_allocator_adaptor<A1<int>, A2<int>> A;
48 A1<int> a4(4);
49 A a(a4, A2<int>(5));
50 assert(A1<int>::copy_called == true);
51 assert(A1<int>::move_called == false);
52 assert(A2<int>::copy_called == true);
53 assert(A2<int>::move_called == false);
54 assert(a.outer_allocator() == A1<int>(4));
55 assert(a.inner_allocator() == std::scoped_allocator_adaptor<A2<int>>(A2<int>(5)));
56 }
57 A1<int>::copy_called = false;
58 A1<int>::move_called = false;
59 A2<int>::copy_called = false;
60 A2<int>::move_called = false;
61 {
62 typedef std::scoped_allocator_adaptor<A1<int>, A2<int>> A;
63 A a(A1<int>(4), A2<int>(5));
64 assert(A1<int>::copy_called == false);
65 assert(A1<int>::move_called == true);
66 assert(A2<int>::copy_called == true);
67 assert(A2<int>::move_called == false);
68 assert(a.outer_allocator() == A1<int>(4));
69 assert(a.inner_allocator() == std::scoped_allocator_adaptor<A2<int>>(A2<int>(5)));
70 }
71 A1<int>::copy_called = false;
72 A1<int>::move_called = false;
73 A2<int>::copy_called = false;
74 A2<int>::move_called = false;
75 A1<int>::move_called = false;
76 {
77 typedef std::scoped_allocator_adaptor<A1<int>, A2<int>, A3<int>> A;
78 A1<int> a4(4);
79 A a(a4, A2<int>(5), A3<int>(6));
80 assert(A1<int>::copy_called == true);
81 assert(A1<int>::move_called == false);
82 assert(A2<int>::copy_called == true);
83 assert(A2<int>::move_called == false);
84 assert(A3<int>::copy_called == true);
85 assert(A3<int>::move_called == false);
86 assert(a.outer_allocator() == A1<int>(4));
87 assert((a.inner_allocator() == std::scoped_allocator_adaptor<A2<int>, A3<int>>(A2<int>(5), A3<int>(6))));
88 }
89 A1<int>::copy_called = false;
90 A1<int>::move_called = false;
91 A2<int>::copy_called = false;
92 A2<int>::move_called = false;
93 A3<int>::copy_called = false;
94 A3<int>::move_called = false;
95 {
96 typedef std::scoped_allocator_adaptor<A1<int>, A2<int>, A3<int>> A;
97 A a(A1<int>(4), A2<int>(5), A3<int>(6));
98 assert(A1<int>::copy_called == false);
99 assert(A1<int>::move_called == true);
100 assert(A2<int>::copy_called == true);
101 assert(A2<int>::move_called == false);
102 assert(A3<int>::copy_called == true);
103 assert(A3<int>::move_called == false);
104 assert(a.outer_allocator() == A1<int>(4));
105 assert((a.inner_allocator() == std::scoped_allocator_adaptor<A2<int>, A3<int>>(A2<int>(5), A3<int>(6))));
106 }
107 {
108 // Test for LWG2782
109 static_assert(!std::is_convertible<A1<int>, A2<int>>::value, "");
110 static_assert(
111 !std::is_convertible< std::scoped_allocator_adaptor<A1<int>>, std::scoped_allocator_adaptor<A2<int>>>::value,
112 "");
113 }
114 {
115 // Test construction from convertible-to-allocator types (https://github.com/llvm/llvm-project/issues/78754)
116 typedef std::scoped_allocator_adaptor<A1<int>, A1<int>> A;
117 A a(A1<char>(4), A1<char>(5));
118 assert(a.outer_allocator() == A1<int>(4));
119 assert(a.inner_allocator() == A1<int>(5));
120 }
121
122 return 0;
123 }
124