xref: /aosp_15_r20/external/deqp/framework/delibs/decpp/deUniquePtr.cpp (revision 35238bce31c2a825756842865a792f8cf7f89930)
1 /*-------------------------------------------------------------------------
2  * drawElements C++ Base Library
3  * -----------------------------
4  *
5  * Copyright 2014 The Android Open Source Project
6  *
7  * Licensed under the Apache License, Version 2.0 (the "License");
8  * you may not use this file except in compliance with the License.
9  * You may obtain a copy of the License at
10  *
11  *      http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing, software
14  * distributed under the License is distributed on an "AS IS" BASIS,
15  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16  * See the License for the specific language governing permissions and
17  * limitations under the License.
18  *
19  *//*!
20  * \file
21  * \brief Unique pointer.
22  *//*--------------------------------------------------------------------*/
23 
24 #include "deUniquePtr.hpp"
25 
26 #include <exception>
27 
28 namespace de
29 {
30 
31 namespace
32 {
33 
34 class Object
35 {
36 public:
Object(bool & exists)37     Object(bool &exists) : m_exists(exists)
38     {
39         m_exists = true;
40     }
41 
~Object(void)42     ~Object(void)
43     {
44         m_exists = false;
45     }
46 
47 private:
48     bool &m_exists;
49 };
50 
51 struct CustomDeleter
52 {
CustomDeleterde::__anon90d808610111::CustomDeleter53     CustomDeleter(bool *called) : m_called(called)
54     {
55     }
56 
operator ()de::__anon90d808610111::CustomDeleter57     void operator()(Object *ptr)
58     {
59         DE_TEST_ASSERT(!*m_called);
60         delete ptr;
61         *m_called = true;
62     }
63 
64     bool *m_called;
65 };
66 
createObject(bool & exists)67 MovePtr<Object> createObject(bool &exists)
68 {
69     UniquePtr<Object> objectPtr(new Object(exists));
70     return objectPtr.move();
71 }
72 
73 } // namespace
74 
UniquePtr_selfTest(void)75 void UniquePtr_selfTest(void)
76 {
77     // Basic test.
78     {
79         bool exists = false;
80         {
81             UniquePtr<Object> ptr(new Object(exists));
82             DE_TEST_ASSERT(exists);
83             DE_TEST_ASSERT(ptr.get() != DE_NULL);
84         }
85         DE_TEST_ASSERT(!exists);
86     }
87 
88     // Exception test.
89     {
90         bool exists = false;
91         try
92         {
93             UniquePtr<Object> ptr(new Object(exists));
94             DE_TEST_ASSERT(exists);
95             DE_TEST_ASSERT(ptr.get() != DE_NULL);
96             throw std::exception();
97         }
98         catch (const std::exception &)
99         {
100             DE_TEST_ASSERT(!exists);
101         }
102         DE_TEST_ASSERT(!exists);
103     }
104 
105     // Expression test.
106     {
107         bool exists = false;
108         bool test   = (UniquePtr<Object>(new Object(exists))).get() != DE_NULL && exists;
109         DE_TEST_ASSERT(!exists);
110         DE_TEST_ASSERT(test);
111     }
112 
113     // Custom deleter.
114     {
115         bool exists        = false;
116         bool deleterCalled = false;
117         {
118             UniquePtr<Object, CustomDeleter> ptr(new Object(exists), CustomDeleter(&deleterCalled));
119             DE_TEST_ASSERT(exists);
120             DE_TEST_ASSERT(!deleterCalled);
121             DE_TEST_ASSERT(ptr.get() != DE_NULL);
122         }
123         DE_TEST_ASSERT(!exists);
124         DE_TEST_ASSERT(deleterCalled);
125     }
126 
127     // MovePtr -> MovePtr moving
128     {
129         bool exists = false;
130         MovePtr<Object> ptr(new Object(exists));
131         DE_TEST_ASSERT(exists);
132         {
133             MovePtr<Object> ptr2 = ptr;
134             DE_TEST_ASSERT(exists);
135             // Ownership moved to ptr2, should be deleted when ptr2 goes out of scope.
136         }
137         DE_TEST_ASSERT(!exists);
138     }
139 
140     // UniquePtr -> MovePtr moving
141     {
142         bool exists = false;
143         UniquePtr<Object> ptr(new Object(exists));
144         DE_TEST_ASSERT(exists);
145         {
146             MovePtr<Object> ptr2 = ptr.move();
147             DE_TEST_ASSERT(exists);
148             // Ownership moved to ptr2, should be deleted when ptr2 goes out of scope.
149         }
150         DE_TEST_ASSERT(!exists);
151     }
152 
153     // MovePtr -> UniquePtr moving
154     {
155         bool exists = false;
156         {
157             UniquePtr<Object> ptr(createObject(exists));
158             DE_TEST_ASSERT(exists);
159         }
160         DE_TEST_ASSERT(!exists);
161     }
162 
163     // MovePtr assignment
164     {
165         bool exists1 = false;
166         bool exists2 = false;
167         MovePtr<Object> ptr1(new Object(exists1));
168         MovePtr<Object> ptr2(new Object(exists2));
169         ptr1 = ptr2;
170         DE_TEST_ASSERT(!exists1);
171         DE_TEST_ASSERT(exists2);
172     }
173 
174     // MovePtr stealing
175     {
176         bool exists = false;
177         Object *raw = DE_NULL;
178         {
179             MovePtr<Object> ptr1(new Object(exists));
180             raw = ptr1.release();
181             DE_TEST_ASSERT(raw != DE_NULL);
182             DE_TEST_ASSERT(ptr1.get() == DE_NULL);
183             DE_TEST_ASSERT(exists);
184         }
185         DE_TEST_ASSERT(exists);
186         delete raw;
187         DE_TEST_ASSERT(!exists);
188     }
189 
190     // Null MovePtr and assigning to it.
191     {
192         bool exists = false;
193         {
194             MovePtr<Object> ptr1;
195             DE_TEST_ASSERT(ptr1.get() == DE_NULL);
196             MovePtr<Object> ptr2(new Object(exists));
197             ptr1 = ptr2;
198             DE_TEST_ASSERT(exists);
199             DE_TEST_ASSERT(ptr1.get() != DE_NULL);
200             DE_TEST_ASSERT(ptr2.get() == DE_NULL);
201         }
202         DE_TEST_ASSERT(!exists);
203     }
204 
205 #if 0
206     // UniquePtr assignment or copy construction should not compile. This
207     // piece of code is intentionally commented out. To manually test that
208     // copying a UniquePtr is statically forbidden, uncomment and try to
209     // compile.
210     {
211         bool exists = false;
212         UniquePtr<Object> ptr(new Object(exists));
213         {
214             UniquePtr<Object> ptr2(ptr);
215             DE_TEST_ASSERT(exists);
216         }
217         DE_TEST_ASSERT(!exists);
218     }
219 #endif
220 }
221 
222 } // namespace de
223