• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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 #ifndef NASTY_CONTAINERS_H
10 #define NASTY_CONTAINERS_H
11 
12 #include <cassert>
13 #include <cstddef>
14 #include <vector>
15 #include <list>
16 #include <type_traits>
17 
18 #include "test_macros.h"
19 
20 template <class T>
21 class nasty_vector
22 {
23 public:
24     typedef typename std::vector<T>                           nested_container;
25     typedef typename nested_container::value_type             value_type;
26     typedef typename nested_container::reference              reference;
27     typedef typename nested_container::const_reference        const_reference;
28     typedef typename nested_container::iterator               iterator;
29     typedef typename nested_container::const_iterator         const_iterator;
30 
31     typedef typename nested_container::size_type              size_type;
32     typedef typename nested_container::difference_type        difference_type;
33     typedef typename nested_container::pointer                pointer;
34     typedef typename nested_container::const_pointer          const_pointer;
35 
36     typedef typename nested_container::reverse_iterator       reverse_iterator;
37     typedef typename nested_container::const_reverse_iterator const_reverse_iterator;
38 
nasty_vector()39     nasty_vector() : v_() {}
nasty_vector(size_type n)40     explicit nasty_vector(size_type n) : v_(n) {}
nasty_vector(size_type n,const value_type & value)41     nasty_vector(size_type n, const value_type& value) : v_(n, value) {}
nasty_vector(InputIterator first,InputIterator last)42     template <class InputIterator> nasty_vector(InputIterator first, InputIterator last) : v_(first, last) {}
43 #if TEST_STD_VER >= 11
nasty_vector(std::initializer_list<value_type> il)44     nasty_vector(std::initializer_list<value_type> il) : v_(il) {}
45 #endif
46     nasty_vector(const nasty_vector&) = default;
47     nasty_vector& operator=(const nasty_vector&) = default;
~nasty_vector()48     ~nasty_vector() {}
49 
50     template <class InputIterator>
assign(InputIterator first,InputIterator last)51         void assign(InputIterator first, InputIterator last) { v_.assign(first, last); }
assign(size_type n,const value_type & u)52     void assign(size_type n, const value_type& u) { v_.assign(n, u); }
53 #if TEST_STD_VER >= 11
assign(std::initializer_list<value_type> il)54     void assign(std::initializer_list<value_type> il)  { v_.assign(il); }
55 #endif
56 
begin()57     iterator               begin() TEST_NOEXCEPT         { return v_.begin(); }
begin()58     const_iterator         begin()   const TEST_NOEXCEPT { return v_.begin(); }
end()59     iterator               end() TEST_NOEXCEPT           { return v_.end(); }
end()60     const_iterator         end()     const TEST_NOEXCEPT { return v_.end(); }
61 
rbegin()62     reverse_iterator       rbegin() TEST_NOEXCEPT        { return v_.rbegin(); }
rbegin()63     const_reverse_iterator rbegin()  const TEST_NOEXCEPT { return v_.rbegin(); }
rend()64     reverse_iterator       rend() TEST_NOEXCEPT          { return v_.rend(); }
rend()65     const_reverse_iterator rend()    const TEST_NOEXCEPT { return v_.rend(); }
66 
cbegin()67     const_iterator         cbegin()  const TEST_NOEXCEPT { return v_.cbegin(); }
cend()68     const_iterator         cend()    const TEST_NOEXCEPT { return v_.cend(); }
crbegin()69     const_reverse_iterator crbegin() const TEST_NOEXCEPT { return v_.crbegin(); }
crend()70     const_reverse_iterator crend()   const TEST_NOEXCEPT { return v_.crend(); }
71 
size()72     size_type size() const TEST_NOEXCEPT      { return v_.size(); }
max_size()73     size_type max_size() const TEST_NOEXCEPT  { return v_.max_size(); }
capacity()74     size_type capacity() const TEST_NOEXCEPT  { return v_.capacity(); }
empty()75     bool empty() const TEST_NOEXCEPT          { return v_.empty(); }
reserve(size_type n)76     void reserve(size_type n)             { v_.reserve(n); };
shrink_to_fit()77     void shrink_to_fit() TEST_NOEXCEPT        { v_.shrink_to_fit(); }
78 
79     reference       operator[](size_type n)       { return v_[n]; }
80     const_reference operator[](size_type n) const { return v_[n]; }
at(size_type n)81     reference       at(size_type n)               { return v_.at(n); }
at(size_type n)82     const_reference at(size_type n) const         { return v_.at(n); }
83 
front()84     reference       front()       { return v_.front(); }
front()85     const_reference front() const { return v_.front(); }
back()86     reference       back()        { return v_.back(); }
back()87     const_reference back() const  { return v_.back(); }
88 
data()89     value_type*       data() TEST_NOEXCEPT       { return v_.data(); }
data()90     const value_type* data() const TEST_NOEXCEPT { return v_.data(); }
91 
push_back(const value_type & x)92     void push_back(const value_type& x)     { v_.push_back(x); }
93 #if TEST_STD_VER >= 11
push_back(value_type && x)94     void push_back(value_type&& x)          { v_.push_back(std::forward<value_type&&>(x)); }
95     template <class... Args>
emplace_back(Args &&...args)96         void emplace_back(Args&&... args)   { v_.emplace_back(std::forward<Args>(args)...); }
97 #endif
pop_back()98     void pop_back()                         { v_.pop_back(); }
99 
100 #if TEST_STD_VER >= 11
emplace(const_iterator pos,Args &&...args)101     template <class... Args> iterator emplace(const_iterator pos, Args&&... args)
102     { return v_.emplace(pos, std::forward<Args>(args)...); }
103 #endif
104 
insert(const_iterator pos,const value_type & x)105     iterator insert(const_iterator pos, const value_type& x) { return v_.insert(pos, x); }
106 #if TEST_STD_VER >= 11
insert(const_iterator pos,value_type && x)107     iterator insert(const_iterator pos, value_type&& x)      { return v_.insert(pos, std::forward<value_type>(x)); }
108 #endif
insert(const_iterator pos,size_type n,const value_type & x)109     iterator insert(const_iterator pos, size_type n, const value_type& x) { return v_.insert(pos, n, x); }
110     template <class InputIterator>
insert(const_iterator pos,InputIterator first,InputIterator last)111         iterator insert(const_iterator pos, InputIterator first, InputIterator last)
112     { return v_.insert(pos, first, last); }
113 
114 #if TEST_STD_VER >= 11
insert(const_iterator pos,std::initializer_list<value_type> il)115     iterator insert(const_iterator pos, std::initializer_list<value_type> il) { return v_.insert(pos, il); }
116 #endif
117 
erase(const_iterator pos)118     iterator erase(const_iterator pos)                        { return v_.erase(pos); }
erase(const_iterator first,const_iterator last)119     iterator erase(const_iterator first, const_iterator last) { return v_.erase(first, last); }
120 
clear()121     void clear() TEST_NOEXCEPT { v_.clear(); }
122 
resize(size_type sz)123     void resize(size_type sz)                      { v_.resize(sz); }
resize(size_type sz,const value_type & c)124     void resize(size_type sz, const value_type& c) { v_.resize(sz, c); }
125 
swap(nasty_vector & nv)126     void swap(nasty_vector &nv)
127 #if TEST_STD_VER > 14
128     noexcept(std::is_nothrow_swappable<nested_container>::value)
129 #elif defined(_LIBCPP_VERSION)
130     TEST_NOEXCEPT_COND(std::__is_nothrow_swappable<nested_container>::value)
131 #endif
132     { v_.swap(nv.v_); }
133 
134     nasty_vector *operator &()             { assert(false); return nullptr; }  // nasty
135     const nasty_vector *operator &() const { assert(false); return nullptr; }  // nasty
136 
137     nested_container v_;
138 };
139 
140 template <class T>
141 bool operator==(const nasty_vector<T>& x, const nasty_vector<T>& y) { return x.v_ == y.v_; }
142 
143 
144 #if TEST_STD_VER >= 20
145 
146 template <class T>
147 auto operator<=>(const nasty_vector<T>& x, const nasty_vector<T>& y) { return x.v_ <=> y.v_; }
148 
149 #endif
150 
151 template <class T>
152 class nasty_list
153 {
154 public:
155 
156     typedef typename std::list<T>                             nested_container;
157     typedef typename nested_container::value_type             value_type;
158     typedef typename nested_container::reference              reference;
159     typedef typename nested_container::const_reference        const_reference;
160     typedef typename nested_container::iterator               iterator;
161     typedef typename nested_container::const_iterator         const_iterator;
162 
163     typedef typename nested_container::size_type              size_type;
164     typedef typename nested_container::difference_type        difference_type;
165     typedef typename nested_container::pointer                pointer;
166     typedef typename nested_container::const_pointer          const_pointer;
167 
168     typedef typename nested_container::reverse_iterator       reverse_iterator;
169     typedef typename nested_container::const_reverse_iterator const_reverse_iterator;
170 
nasty_list()171     nasty_list() : l_() {}
nasty_list(size_type n)172     explicit nasty_list(size_type n)  : l_(n) {}
nasty_list(size_type n,const value_type & value)173     nasty_list(size_type n, const value_type& value)  : l_(n,value) {}
174     template <class Iter>
nasty_list(Iter first,Iter last)175         nasty_list(Iter first, Iter last)  : l_(first, last) {}
176 #if TEST_STD_VER >= 11
nasty_list(std::initializer_list<value_type> il)177     nasty_list(std::initializer_list<value_type> il) : l_(il) {}
178 #endif
179     nasty_list(const nasty_list&) = default;
180     nasty_list& operator=(const nasty_list&) = default;
~nasty_list()181     ~nasty_list() {}
182 
183 #if TEST_STD_VER >= 11
184     nasty_list& operator=(std::initializer_list<value_type> il) { l_ = il; return *this; }
185 #endif
186     template <class Iter>
assign(Iter first,Iter last)187         void assign(Iter first, Iter last) { l_.assign(first, last); }
assign(size_type n,const value_type & t)188     void assign(size_type n, const value_type& t) { l_.assign(n, t); }
189 #if TEST_STD_VER >= 11
assign(std::initializer_list<value_type> il)190     void assign(std::initializer_list<value_type> il) { l_.assign(il); }
191 #endif
192 
193 
begin()194     iterator               begin() TEST_NOEXCEPT         { return l_.begin(); }
begin()195     const_iterator         begin()   const TEST_NOEXCEPT { return l_.begin(); }
end()196     iterator               end() TEST_NOEXCEPT           { return l_.end(); }
end()197     const_iterator         end()     const TEST_NOEXCEPT { return l_.end(); }
198 
rbegin()199     reverse_iterator       rbegin() TEST_NOEXCEPT        { return l_.rbegin(); }
rbegin()200     const_reverse_iterator rbegin()  const TEST_NOEXCEPT { return l_.rbegin(); }
rend()201     reverse_iterator       rend() TEST_NOEXCEPT          { return l_.rend(); }
rend()202     const_reverse_iterator rend()    const TEST_NOEXCEPT { return l_.rend(); }
203 
cbegin()204     const_iterator         cbegin()  const TEST_NOEXCEPT { return l_.cbegin(); }
cend()205     const_iterator         cend()    const TEST_NOEXCEPT { return l_.cend(); }
crbegin()206     const_reverse_iterator crbegin() const TEST_NOEXCEPT { return l_.crbegin(); }
crend()207     const_reverse_iterator crend()   const TEST_NOEXCEPT { return l_.crend(); }
208 
front()209     reference       front()       { return l_.front(); }
front()210     const_reference front() const { return l_.front(); }
back()211     reference       back()        { return l_.back(); }
back()212     const_reference back() const  { return l_.back(); }
213 
size()214     size_type size() const TEST_NOEXCEPT      { return l_.size(); }
max_size()215     size_type max_size() const TEST_NOEXCEPT  { return l_.max_size(); }
empty()216     bool empty() const TEST_NOEXCEPT          { return l_.empty(); }
217 
push_front(const value_type & x)218     void push_front(const value_type& x)    { l_.push_front(x); }
push_back(const value_type & x)219     void push_back(const value_type& x)     { l_.push_back(x); }
220 #if TEST_STD_VER >= 11
push_back(value_type && x)221     void push_back(value_type&& x)          { l_.push_back(std::forward<value_type&&>(x)); }
push_front(value_type && x)222     void push_front(value_type&& x)         { l_.push_front(std::forward<value_type&&>(x)); }
223     template <class... Args>
emplace_back(Args &&...args)224         void emplace_back(Args&&... args)   { l_.emplace_back(std::forward<Args>(args)...); }
225     template <class... Args>
emplace_front(Args &&...args)226         void emplace_front(Args&&... args)  { l_.emplace_front(std::forward<Args>(args)...); }
227 #endif
pop_front()228     void pop_front()                        { l_.pop_front(); }
pop_back()229     void pop_back()                         { l_.pop_back(); }
230 
231 #if TEST_STD_VER >= 11
emplace(const_iterator pos,Args &&...args)232     template <class... Args> iterator emplace(const_iterator pos, Args&&... args)
233     { return l_.emplace(pos, std::forward<Args>(args)...); }
234 #endif
235 
insert(const_iterator pos,const value_type & x)236     iterator insert(const_iterator pos, const value_type& x) { return l_.insert(pos, x); }
237 #if TEST_STD_VER >= 11
insert(const_iterator pos,value_type && x)238     iterator insert(const_iterator pos, value_type&& x)      { return l_.insert(pos, std::forward<value_type>(x)); }
239 #endif
insert(const_iterator pos,size_type n,const value_type & x)240     iterator insert(const_iterator pos, size_type n, const value_type& x) { return l_.insert(pos, n, x); }
241     template <class InputIterator>
insert(const_iterator pos,InputIterator first,InputIterator last)242         iterator insert(const_iterator pos, InputIterator first, InputIterator last)
243     { return l_.insert(pos, first, last); }
244 
245 #if TEST_STD_VER >= 11
insert(const_iterator pos,std::initializer_list<value_type> il)246     iterator insert(const_iterator pos, std::initializer_list<value_type> il) { return l_.insert(pos, il); }
247 #endif
248 
erase(const_iterator pos)249     iterator erase(const_iterator pos)                      { return l_.erase(pos); }
erase(const_iterator first,const_iterator last)250     iterator erase(const_iterator first, const_iterator last) { return l_.erase(first, last); }
251 
resize(size_type n)252     void resize(size_type n)                      { l_.resize(n); }
resize(size_type n,const value_type & c)253     void resize(size_type n, const value_type& c) { l_.resize(n, c); }
254 
swap(nasty_list & nl)255     void swap(nasty_list &nl)
256 #if TEST_STD_VER > 14
257     noexcept(std::is_nothrow_swappable<nested_container>::value)
258 #elif defined(_LIBCPP_VERSION)
259     TEST_NOEXCEPT_COND(std::__is_nothrow_swappable<nested_container>::value)
260 #endif
261     { l_.swap(nl.l_); }
262 
clear()263     void clear() TEST_NOEXCEPT { l_.clear(); }
264 
265 //     void splice(const_iterator position, list& x);
266 //     void splice(const_iterator position, list&& x);
267 //     void splice(const_iterator position, list& x, const_iterator i);
268 //     void splice(const_iterator position, list&& x, const_iterator i);
269 //     void splice(const_iterator position, list& x, const_iterator first,
270 //                                                   const_iterator last);
271 //     void splice(const_iterator position, list&& x, const_iterator first,
272 //                                                   const_iterator last);
273 //
274 //     void remove(const value_type& value);
275 //     template <class Pred> void remove_if(Pred pred);
276 //     void unique();
277 //     template <class BinaryPredicate>
278 //         void unique(BinaryPredicate binary_pred);
279 //     void merge(list& x);
280 //     void merge(list&& x);
281 //     template <class Compare>
282 //         void merge(list& x, Compare comp);
283 //     template <class Compare>
284 //         void merge(list&& x, Compare comp);
285 //     void sort();
286 //     template <class Compare>
287 //         void sort(Compare comp);
288 //     void reverse() noexcept;
289 
290     nasty_list *operator &()             { assert(false); return nullptr; }  // nasty
291     const nasty_list *operator &() const { assert(false); return nullptr; }  // nasty
292 
293     nested_container l_;
294 };
295 
296 template <class T>
297 bool operator==(const nasty_list<T>& x, const nasty_list<T>& y) { return x.l_ == y.l_; }
298 
299 #if TEST_STD_VER >= 20
300 
301 template <class T>
302 auto operator<=>(const nasty_list<T>& x, const nasty_list<T>& y) { return x.l_ <=> y.l_; }
303 
304 #endif
305 
306 // Not really a mutex, but can play one in tests
307 class nasty_mutex
308 {
309 public:
nasty_mutex()310      nasty_mutex() TEST_NOEXCEPT {}
~nasty_mutex()311      ~nasty_mutex() {}
312 
313     nasty_mutex *operator& ()   { assert(false); return nullptr; }
314     template <typename T>
315     void operator, (const T &) { assert(false); }
316 
317 private:
nasty_mutex(const nasty_mutex &)318     nasty_mutex(const nasty_mutex&)            { assert(false); }
319     nasty_mutex& operator=(const nasty_mutex&) { assert(false); return *this; }
320 
321 public:
lock()322     void lock()               {}
try_lock()323     bool try_lock() TEST_NOEXCEPT { return true; }
unlock()324     void unlock() TEST_NOEXCEPT   {}
325 
326     // Shared ownership
lock_shared()327     void lock_shared()     {}
try_lock_shared()328     bool try_lock_shared() { return true; }
unlock_shared()329     void unlock_shared()   {}
330 };
331 
332 #endif
333