Embedded Template Library 1.0
reference_counted_object.h
1
2//The MIT License(MIT)
3//
4//Embedded Template Library.
5//https://github.com/ETLCPP/etl
6//https://www.etlcpp.com
7//
8//Copyright(c) 2021 John Wellbelove
9//
10//Permission is hereby granted, free of charge, to any person obtaining a copy
11//of this software and associated documentation files(the "Software"), to deal
12//in the Software without restriction, including without limitation the rights
13//to use, copy, modify, merge, publish, distribute, sublicense, and / or sell
14//copies of the Software, and to permit persons to whom the Software is
15//furnished to do so, subject to the following conditions :
16//
17//The above copyright notice and this permission notice shall be included in all
18//copies or substantial portions of the Software.
19//
20//THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
21//IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
22//FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE
23//AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
24//LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
25//OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
26//SOFTWARE.
27//******************************************************************************/
28
29#ifndef ETL_REFERENCE_COUNTED_OBJECT_INCLUDED
30#define ETL_REFERENCE_COUNTED_OBJECT_INCLUDED
31
32#include "platform.h"
33#include "atomic.h"
34#include "exception.h"
35#include "error_handler.h"
36
37#include <stdint.h>
38
39namespace etl
40{
41
42 //***************************************************************************
45 //***************************************************************************
47 {
48 public:
49 reference_counting_exception(string_type reason_, string_type file_name_, numeric_type line_number_)
50 : exception(reason_, file_name_, line_number_)
51 {
52 }
53 };
54
55 //***************************************************************************
58 //***************************************************************************
60 {
61 public:
62 reference_count_overrun(string_type file_name_, numeric_type line_number_)
63 : etl::reference_counting_exception(ETL_ERROR_TEXT("reference_counting:overrun", ETL_REFERENCE_COUNTED_OBJECT_FILE_ID"A"), file_name_, line_number_)
64 {
65 }
66 };
67
68 //***************************************************************************
70 //***************************************************************************
72 {
73 public:
74
75 virtual ~ireference_counter() {};
76 virtual void set_reference_count(int32_t value) = 0;
77 virtual void increment_reference_count() = 0;
78 ETL_NODISCARD virtual int32_t decrement_reference_count() = 0;
79 ETL_NODISCARD virtual int32_t get_reference_count() const = 0;
80 };
81
82 //***************************************************************************
84 //***************************************************************************
85 template <typename TCounter>
87 {
88 public:
89
90 //***************************************************************************
92 //***************************************************************************
94 : reference_count(0)
95 {
96 }
97
98 //***************************************************************************
100 //***************************************************************************
101 virtual void set_reference_count(int32_t value) ETL_OVERRIDE
102 {
103 reference_count = value;
104 }
105
106 //***************************************************************************
108 //***************************************************************************
109 virtual void increment_reference_count() ETL_OVERRIDE
110 {
111 ++reference_count;
112 }
113
114 //***************************************************************************
116 //***************************************************************************
117 ETL_NODISCARD virtual int32_t decrement_reference_count() ETL_OVERRIDE
118 {
119 ETL_ASSERT(reference_count > 0, ETL_ERROR(reference_count_overrun));
120
121 return int32_t(--reference_count);
122 }
123
124 //***************************************************************************
126 //***************************************************************************
127 ETL_NODISCARD virtual int32_t get_reference_count() const ETL_OVERRIDE
128 {
129 return int32_t(reference_count);
130 }
131
132 private:
133
134 TCounter reference_count; // The reference count object.
135 };
136
137 //***************************************************************************
139 //***************************************************************************
140 template <>
142 {
143 public:
144
145 //***************************************************************************
147 //***************************************************************************
149 {
150 // Do nothing.
151 }
152
153 //***************************************************************************
155 //***************************************************************************
156 virtual void set_reference_count(int32_t /*value*/) ETL_OVERRIDE
157 {
158 // Do nothing.
159 }
160
161 //***************************************************************************
163 //***************************************************************************
164 virtual void increment_reference_count() ETL_OVERRIDE
165 {
166 // Do nothing.
167 }
168
169 //***************************************************************************
171 //***************************************************************************
172 ETL_NODISCARD virtual int32_t decrement_reference_count() ETL_OVERRIDE
173 {
174 return int32_t(1);
175 }
176
177 //***************************************************************************
179 //***************************************************************************
180 ETL_NODISCARD virtual int32_t get_reference_count() const ETL_OVERRIDE
181 {
182 return int32_t(1);
183 }
184 };
185
186 //***************************************************************************
188 //***************************************************************************
190 {
191 public:
192
193 virtual ~ireference_counted_object() {}
194 ETL_NODISCARD virtual ireference_counter& get_reference_counter() = 0;
195 ETL_NODISCARD virtual const ireference_counter& get_reference_counter() const = 0;
196 };
197
198 //***************************************************************************
202 //***************************************************************************
203 template <typename TObject, typename TCounter>
205 {
206 public:
207
208 typedef TObject value_type;
209 typedef TCounter counter_type;
210
211 //***************************************************************************
213 //***************************************************************************
215 {
216 }
217
218 //***************************************************************************
220 //***************************************************************************
221 reference_counted_object(const TObject& object_)
222 : object(object_)
223 {
224 }
225
226 //***************************************************************************
228 //***************************************************************************
229 ETL_NODISCARD value_type& get_object()
230 {
231 return object;
232 }
233
234
235 //***************************************************************************
237 //***************************************************************************
238 ETL_NODISCARD const value_type& get_object() const
239 {
240 return object;
241 }
242
243 //***************************************************************************
245 //***************************************************************************
246 ETL_NODISCARD virtual ireference_counter& get_reference_counter() ETL_OVERRIDE
247 {
248 return reference_counter;
249 }
250
251 //***************************************************************************
253 //***************************************************************************
254 ETL_NODISCARD virtual const ireference_counter& get_reference_counter() const ETL_OVERRIDE
255 {
256 return reference_counter;
257 }
258
259 private:
260
261 // This class must not be copy constructed or assigned.
263 reference_counted_object& operator =(const reference_counted_object&) ETL_DELETE;
264
265 TObject object;
267 };
268
269#if ETL_USING_CPP11 && ETL_HAS_ATOMIC
270 //***************************************************************************
273 //***************************************************************************
274 template <typename TObject>
276#endif
277}
278
279#endif
Base for all reference counted objects.
Definition: reference_counted_object.h:190
The base of all reference counters.
Definition: reference_counted_object.h:72
Definition: reference_counted_object.h:60
Definition: reference_counted_object.h:205
virtual ETL_NODISCARD ireference_counter & get_reference_counter() ETL_OVERRIDE
Get a reference to the reference counter.
Definition: reference_counted_object.h:246
reference_counted_object()
Constructor.
Definition: reference_counted_object.h:214
ETL_NODISCARD value_type & get_object()
Get a reference to the counted object.
Definition: reference_counted_object.h:229
reference_counted_object(const TObject &object_)
Constructor.
Definition: reference_counted_object.h:221
reference_counter()
Constructor.
Definition: reference_counted_object.h:148
virtual void set_reference_count(int32_t) ETL_OVERRIDE
Set the reference count.
Definition: reference_counted_object.h:156
virtual void increment_reference_count() ETL_OVERRIDE
Increment the reference count.
Definition: reference_counted_object.h:164
A specific type of reference counter.
Definition: reference_counted_object.h:87
virtual ETL_NODISCARD int32_t get_reference_count() const ETL_OVERRIDE
Get the current reference count.
Definition: reference_counted_object.h:127
virtual void increment_reference_count() ETL_OVERRIDE
Increment the reference count.
Definition: reference_counted_object.h:109
reference_counter()
Constructor.
Definition: reference_counted_object.h:93
virtual void set_reference_count(int32_t value) ETL_OVERRIDE
Set the reference count.
Definition: reference_counted_object.h:101
virtual ETL_NODISCARD int32_t decrement_reference_count() ETL_OVERRIDE
Decrement the reference count.
Definition: reference_counted_object.h:117
Definition: reference_counted_object.h:47
#define ETL_ASSERT(b, e)
Definition: error_handler.h:316
ETL_CONSTEXPR exception(string_type reason_, string_type, numeric_type line_)
Constructor.
Definition: exception.h:69
Definition: exception.h:47
bitset_ext
Definition: absolute.h:38