@@ -297,6 +297,7 @@ erase_if(vector<T, Allocator>& c, Predicate pred); // C++20
297
297
#include < __utility/forward.h>
298
298
#include < __utility/move.h>
299
299
#include < __utility/swap.h>
300
+ #include < __utility/transaction.h>
300
301
#include < climits>
301
302
#include < cstdlib>
302
303
#include < cstring>
@@ -425,18 +426,27 @@ public:
425
426
value_type,
426
427
typename iterator_traits<_ForwardIterator>::reference>::value>::type* = 0 );
427
428
428
- _LIBCPP_CONSTEXPR_AFTER_CXX17 _LIBCPP_INLINE_VISIBILITY
429
- ~vector ()
430
- {
431
- __annotate_delete ();
432
- std::__debug_db_erase_c (this );
429
+ private:
430
+ class __destroy_vector {
431
+ public:
432
+ _LIBCPP_CONSTEXPR __destroy_vector (vector& __vec) : __vec_(__vec) {}
433
433
434
- if (this ->__begin_ != nullptr )
435
- {
436
- __clear ();
437
- __alloc_traits::deallocate (__alloc (), this ->__begin_ , capacity ());
434
+ _LIBCPP_CONSTEXPR_AFTER_CXX17 _LIBCPP_HIDE_FROM_ABI void operator ()() {
435
+ __vec_.__annotate_delete ();
436
+ std::__debug_db_erase_c (std::addressof (__vec_));
437
+
438
+ if (__vec_.__begin_ != nullptr ) {
439
+ __vec_.__clear ();
440
+ __alloc_traits::deallocate (__vec_.__alloc (), __vec_.__begin_ , __vec_.capacity ());
441
+ }
438
442
}
439
- }
443
+
444
+ private:
445
+ vector& __vec_;
446
+ };
447
+
448
+ public:
449
+ _LIBCPP_CONSTEXPR_AFTER_CXX17 _LIBCPP_HIDE_FROM_ABI ~vector () { __destroy_vector (*this )(); }
440
450
441
451
_LIBCPP_CONSTEXPR_AFTER_CXX17 vector (const vector& __x);
442
452
_LIBCPP_CONSTEXPR_AFTER_CXX17 vector (const vector& __x, const __type_identity_t <allocator_type>& __a);
@@ -1075,12 +1085,14 @@ template <class _Tp, class _Allocator>
1075
1085
_LIBCPP_CONSTEXPR_AFTER_CXX17
1076
1086
vector<_Tp, _Allocator>::vector(size_type __n)
1077
1087
{
1078
- _VSTD::__debug_db_insert_c (this );
1088
+ auto __guard = std::__make_transaction (__destroy_vector (*this ));
1089
+ std::__debug_db_insert_c (this );
1079
1090
if (__n > 0 )
1080
1091
{
1081
1092
__vallocate (__n);
1082
1093
__construct_at_end (__n);
1083
1094
}
1095
+ __guard.__complete ();
1084
1096
}
1085
1097
1086
1098
#if _LIBCPP_STD_VER > 11
@@ -1089,25 +1101,29 @@ _LIBCPP_CONSTEXPR_AFTER_CXX17
1089
1101
vector<_Tp, _Allocator>::vector(size_type __n, const allocator_type& __a)
1090
1102
: __end_cap_(nullptr , __a)
1091
1103
{
1092
- _VSTD::__debug_db_insert_c (this );
1104
+ auto __guard = std::__make_transaction (__destroy_vector (*this ));
1105
+ std::__debug_db_insert_c (this );
1093
1106
if (__n > 0 )
1094
1107
{
1095
1108
__vallocate (__n);
1096
1109
__construct_at_end (__n);
1097
1110
}
1111
+ __guard.__complete ();
1098
1112
}
1099
1113
#endif
1100
1114
1101
1115
template <class _Tp , class _Allocator >
1102
1116
_LIBCPP_CONSTEXPR_AFTER_CXX17
1103
1117
vector<_Tp, _Allocator>::vector(size_type __n, const value_type& __x)
1104
1118
{
1105
- _VSTD::__debug_db_insert_c (this );
1119
+ auto __guard = std::__make_transaction (__destroy_vector (*this ));
1120
+ std::__debug_db_insert_c (this );
1106
1121
if (__n > 0 )
1107
1122
{
1108
1123
__vallocate (__n);
1109
1124
__construct_at_end (__n, __x);
1110
1125
}
1126
+ __guard.__complete ();
1111
1127
}
1112
1128
1113
1129
template <class _Tp , class _Allocator >
@@ -1120,9 +1136,11 @@ vector<_Tp, _Allocator>::vector(_InputIterator __first,
1120
1136
typename iterator_traits<_InputIterator>::reference>::value,
1121
1137
_InputIterator>::type __last)
1122
1138
{
1123
- _VSTD::__debug_db_insert_c (this );
1139
+ auto __guard = std::__make_transaction (__destroy_vector (*this ));
1140
+ std::__debug_db_insert_c (this );
1124
1141
for (; __first != __last; ++__first)
1125
1142
emplace_back (*__first);
1143
+ __guard.__complete ();
1126
1144
}
1127
1145
1128
1146
template <class _Tp , class _Allocator >
@@ -1135,9 +1153,11 @@ vector<_Tp, _Allocator>::vector(_InputIterator __first, _InputIterator __last, c
1135
1153
typename iterator_traits<_InputIterator>::reference>::value>::type*)
1136
1154
: __end_cap_(nullptr , __a)
1137
1155
{
1138
- _VSTD::__debug_db_insert_c (this );
1156
+ auto __guard = std::__make_transaction (__destroy_vector (*this ));
1157
+ std::__debug_db_insert_c (this );
1139
1158
for (; __first != __last; ++__first)
1140
1159
emplace_back (*__first);
1160
+ __guard.__complete ();
1141
1161
}
1142
1162
1143
1163
template <class _Tp , class _Allocator >
@@ -1150,13 +1170,15 @@ vector<_Tp, _Allocator>::vector(_ForwardIterator __first,
1150
1170
typename iterator_traits<_ForwardIterator>::reference>::value,
1151
1171
_ForwardIterator>::type __last)
1152
1172
{
1153
- _VSTD::__debug_db_insert_c (this );
1154
- size_type __n = static_cast <size_type>(_VSTD::distance (__first, __last));
1173
+ auto __guard = std::__make_transaction (__destroy_vector (*this ));
1174
+ std::__debug_db_insert_c (this );
1175
+ size_type __n = static_cast <size_type>(std::distance (__first, __last));
1155
1176
if (__n > 0 )
1156
1177
{
1157
1178
__vallocate (__n);
1158
1179
__construct_at_end (__first, __last, __n);
1159
1180
}
1181
+ __guard.__complete ();
1160
1182
}
1161
1183
1162
1184
template <class _Tp , class _Allocator >
@@ -1169,41 +1191,47 @@ vector<_Tp, _Allocator>::vector(_ForwardIterator __first, _ForwardIterator __las
1169
1191
typename iterator_traits<_ForwardIterator>::reference>::value>::type*)
1170
1192
: __end_cap_(nullptr , __a)
1171
1193
{
1172
- _VSTD::__debug_db_insert_c (this );
1173
- size_type __n = static_cast <size_type>(_VSTD::distance (__first, __last));
1194
+ auto __guard = std::__make_transaction (__destroy_vector (*this ));
1195
+ std::__debug_db_insert_c (this );
1196
+ size_type __n = static_cast <size_type>(std::distance (__first, __last));
1174
1197
if (__n > 0 )
1175
1198
{
1176
1199
__vallocate (__n);
1177
1200
__construct_at_end (__first, __last, __n);
1178
1201
}
1202
+ __guard.__complete ();
1179
1203
}
1180
1204
1181
1205
template <class _Tp , class _Allocator >
1182
1206
_LIBCPP_CONSTEXPR_AFTER_CXX17
1183
1207
vector<_Tp, _Allocator>::vector(const vector& __x)
1184
1208
: __end_cap_(nullptr , __alloc_traits::select_on_container_copy_construction(__x.__alloc()))
1185
1209
{
1186
- _VSTD::__debug_db_insert_c (this );
1210
+ auto __guard = std::__make_transaction (__destroy_vector (*this ));
1211
+ std::__debug_db_insert_c (this );
1187
1212
size_type __n = __x.size ();
1188
1213
if (__n > 0 )
1189
1214
{
1190
1215
__vallocate (__n);
1191
1216
__construct_at_end (__x.__begin_ , __x.__end_ , __n);
1192
1217
}
1218
+ __guard.__complete ();
1193
1219
}
1194
1220
1195
1221
template <class _Tp , class _Allocator >
1196
1222
_LIBCPP_CONSTEXPR_AFTER_CXX17
1197
1223
vector<_Tp, _Allocator>::vector(const vector& __x, const __type_identity_t <allocator_type>& __a)
1198
1224
: __end_cap_(nullptr , __a)
1199
1225
{
1200
- _VSTD::__debug_db_insert_c (this );
1226
+ auto __guard = std::__make_transaction (__destroy_vector (*this ));
1227
+ std::__debug_db_insert_c (this );
1201
1228
size_type __n = __x.size ();
1202
1229
if (__n > 0 )
1203
1230
{
1204
1231
__vallocate (__n);
1205
1232
__construct_at_end (__x.__begin_ , __x.__end_ , __n);
1206
1233
}
1234
+ __guard.__complete ();
1207
1235
}
1208
1236
1209
1237
template <class _Tp , class _Allocator >
@@ -1243,7 +1271,9 @@ vector<_Tp, _Allocator>::vector(vector&& __x, const __type_identity_t<allocator_
1243
1271
else
1244
1272
{
1245
1273
typedef move_iterator<iterator> _Ip;
1274
+ auto __guard = std::__make_transaction (__destroy_vector (*this ));
1246
1275
assign (_Ip (__x.begin ()), _Ip (__x.end ()));
1276
+ __guard.__complete ();
1247
1277
}
1248
1278
}
1249
1279
@@ -1254,12 +1284,14 @@ _LIBCPP_CONSTEXPR_AFTER_CXX17
1254
1284
inline _LIBCPP_INLINE_VISIBILITY
1255
1285
vector<_Tp, _Allocator>::vector(initializer_list<value_type> __il)
1256
1286
{
1257
- _VSTD::__debug_db_insert_c (this );
1287
+ auto __guard = std::__make_transaction (__destroy_vector (*this ));
1288
+ std::__debug_db_insert_c (this );
1258
1289
if (__il.size () > 0 )
1259
1290
{
1260
1291
__vallocate (__il.size ());
1261
1292
__construct_at_end (__il.begin (), __il.end (), __il.size ());
1262
1293
}
1294
+ __guard.__complete ();
1263
1295
}
1264
1296
1265
1297
template <class _Tp , class _Allocator >
@@ -1268,12 +1300,14 @@ inline _LIBCPP_INLINE_VISIBILITY
1268
1300
vector<_Tp, _Allocator>::vector(initializer_list<value_type> __il, const allocator_type& __a)
1269
1301
: __end_cap_(nullptr , __a)
1270
1302
{
1271
- _VSTD::__debug_db_insert_c (this );
1303
+ auto __guard = std::__make_transaction (__destroy_vector (*this ));
1304
+ std::__debug_db_insert_c (this );
1272
1305
if (__il.size () > 0 )
1273
1306
{
1274
1307
__vallocate (__il.size ());
1275
1308
__construct_at_end (__il.begin (), __il.end (), __il.size ());
1276
1309
}
1310
+ __guard.__complete ();
1277
1311
}
1278
1312
1279
1313
#endif // _LIBCPP_CXX03_LANG
@@ -2111,8 +2145,26 @@ public:
2111
2145
#else
2112
2146
_NOEXCEPT;
2113
2147
#endif
2114
- _LIBCPP_CONSTEXPR_AFTER_CXX17 ~vector ();
2115
- _LIBCPP_CONSTEXPR_AFTER_CXX17 explicit vector (size_type __n);
2148
+
2149
+ private:
2150
+ class __destroy_vector {
2151
+ public:
2152
+ _LIBCPP_CONSTEXPR __destroy_vector (vector& __vec) : __vec_(__vec) {}
2153
+
2154
+ _LIBCPP_CONSTEXPR_AFTER_CXX17 _LIBCPP_HIDE_FROM_ABI void operator ()() {
2155
+ if (__vec_.__begin_ != nullptr )
2156
+ __storage_traits::deallocate (__vec_.__alloc (), __vec_.__begin_ , __vec_.__cap ());
2157
+ std::__debug_db_invalidate_all (this );
2158
+ }
2159
+
2160
+ private:
2161
+ vector& __vec_;
2162
+ };
2163
+
2164
+ public:
2165
+ _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_AFTER_CXX17 ~vector () { __destroy_vector (*this )(); }
2166
+
2167
+ _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_AFTER_CXX17 explicit vector (size_type __n);
2116
2168
#if _LIBCPP_STD_VER > 11
2117
2169
_LIBCPP_CONSTEXPR_AFTER_CXX17 explicit vector (size_type __n, const allocator_type& __a);
2118
2170
#endif
@@ -2647,12 +2699,14 @@ vector<bool, _Allocator>::vector(_ForwardIterator __first, _ForwardIterator __la
2647
2699
__size_ (0 ),
2648
2700
__cap_alloc_ (0 , __default_init_tag ())
2649
2701
{
2650
- size_type __n = static_cast <size_type>(_VSTD::distance (__first, __last));
2702
+ auto __guard = std::__make_transaction (__destroy_vector (*this ));
2703
+ size_type __n = static_cast <size_type>(std::distance (__first, __last));
2651
2704
if (__n > 0 )
2652
2705
{
2653
2706
__vallocate (__n);
2654
2707
__construct_at_end (__first, __last);
2655
2708
}
2709
+ __guard.__complete ();
2656
2710
}
2657
2711
2658
2712
template <class _Allocator >
@@ -2664,12 +2718,14 @@ vector<bool, _Allocator>::vector(_ForwardIterator __first, _ForwardIterator __la
2664
2718
__size_ (0 ),
2665
2719
__cap_alloc_ (0 , static_cast <__storage_allocator>(__a))
2666
2720
{
2667
- size_type __n = static_cast <size_type>(_VSTD::distance (__first, __last));
2721
+ auto __guard = std::__make_transaction (__destroy_vector (*this ));
2722
+ size_type __n = static_cast <size_type>(std::distance (__first, __last));
2668
2723
if (__n > 0 )
2669
2724
{
2670
2725
__vallocate (__n);
2671
2726
__construct_at_end (__first, __last);
2672
2727
}
2728
+ __guard.__complete ();
2673
2729
}
2674
2730
2675
2731
#ifndef _LIBCPP_CXX03_LANG
@@ -2706,15 +2762,6 @@ vector<bool, _Allocator>::vector(initializer_list<value_type> __il, const alloca
2706
2762
2707
2763
#endif // _LIBCPP_CXX03_LANG
2708
2764
2709
- template <class _Allocator >
2710
- _LIBCPP_CONSTEXPR_AFTER_CXX17
2711
- vector<bool , _Allocator>::~vector ()
2712
- {
2713
- if (__begin_ != nullptr )
2714
- __storage_traits::deallocate (__alloc (), __begin_, __cap ());
2715
- std::__debug_db_invalidate_all (this );
2716
- }
2717
-
2718
2765
template <class _Allocator >
2719
2766
_LIBCPP_CONSTEXPR_AFTER_CXX17
2720
2767
vector<bool , _Allocator>::vector (const vector& __v)
0 commit comments