Qt
Internal/Contributor docs for the Qt SDK. Note: These are NOT official API docs; those are found at https://doc.qt.io/
Toggle main menu visibility
Loading...
Searching...
No Matches
qarraydata.h
Go to the documentation of this file.
1
// Copyright (C) 2020 The Qt Company Ltd.
2
// Copyright (C) 2019 Intel Corporation.
3
// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR LGPL-3.0-only OR GPL-2.0-only OR GPL-3.0-only
4
// Qt-Security score:significant reason:default
5
6
#
ifndef
QARRAYDATA_H
7
#
define
QARRAYDATA_H
8
9
#
include
<
QtCore
/
qpair
.
h
>
10
#
include
<
QtCore
/
qatomic
.
h
>
11
#
include
<
QtCore
/
qflags
.
h
>
12
#
include
<
QtCore
/
qcontainerfwd
.
h
>
13
#
include
<
string
.
h
>
14
15
QT_BEGIN_NAMESPACE
16
17
#
if
__has_cpp_attribute
(
gnu
::
malloc
)
18
#
define
Q_DECL_MALLOCLIKE
[
[
nodiscard
,
gnu
::
malloc
]
]
19
#
elif
Q_CC_MSVC_ONLY
20
#
define
Q_DECL_MALLOCLIKE
[
[
nodiscard
]
]
__declspec
(
allocator
)
__declspec
(
restrict
)
21
#
else
22
#
define
Q_DECL_MALLOCLIKE
[
[
nodiscard
]
]
23
#
endif
24
25
template
<
class
T>
struct
QTypedArrayData;
26
27
template
<
class
T>
28
struct
QTypedArrayAllocationResult
29
{
30
QTypedArrayData
<
T
> *
header
;
31
T *
ptr
;
32
33
[[
deprecated
]]
34
operator
std
::
pair
<
QTypedArrayData
<
T
>*,
T
*>()
const
noexcept
{
return
{
header
,
ptr
}; }
35
};
36
37
struct
QArrayData
38
{
39
enum
AllocationOption
{
40
Grow
,
41
KeepSize
42
};
43
44
enum
GrowthPosition
{
45
GrowsAtEnd
,
46
GrowsAtBeginning
47
};
48
49
enum
ArrayOption
{
50
ArrayOptionDefault
= 0,
51
CapacityReserved
= 0x1
//!< the capacity was reserved by the user, try to keep it
52
};
53
Q_DECLARE_FLAGS(ArrayOptions,
ArrayOption
)
54
55
QBasicAtomicInt
ref_
;
56
ArrayOptions
flags
;
57
qsizetype
alloc
;
58
59
qsizetype
allocatedCapacity
()
noexcept
60
{
61
qsizetype a = alloc;
62
Q_PRESUME(a > 0);
63
return
a;
64
}
65
66
qsizetype
constAllocatedCapacity
()
const
noexcept
67
{
68
qsizetype a = alloc;
69
Q_PRESUME(a > 0);
70
return
a;
71
}
72
73
/// Returns true if sharing took place
74
bool
ref
()
noexcept
75
{
76
ref_.refRelaxed();
// suffices for ref-counting
77
return
true
;
78
}
79
80
/// Returns false if deallocation is necessary
81
bool
deref
()
noexcept
82
{
83
return
ref_.deref();
84
}
85
86
bool
isShared
()
const
noexcept
87
{
88
return
ref_.loadRelaxed() != 1;
89
}
90
91
// Returns true if a detach is necessary before modifying the data
92
// This method is intentionally not const: if you want to know whether
93
// detaching is necessary, you should be in a non-const function already
94
bool
needsDetach
()
noexcept
95
{
96
return
ref_.loadRelaxed() > 1;
97
}
98
99
qsizetype
detachCapacity
(qsizetype newSize)
const
noexcept
100
{
101
if
(flags & CapacityReserved && newSize < constAllocatedCapacity())
102
return
constAllocatedCapacity();
103
return
newSize;
104
}
105
106
Q_DECL_MALLOCLIKE
107
static
Q_CORE_EXPORT
void
*
allocate
(
QArrayData
**pdata, qsizetype objectSize, qsizetype alignment,
108
qsizetype capacity,
AllocationOption
option =
QArrayData
::
KeepSize
)
noexcept
;
109
Q_DECL_MALLOCLIKE
110
static
Q_CORE_EXPORT
void
*
allocate1
(
QArrayData
**pdata, qsizetype capacity,
111
AllocationOption
option =
QArrayData
::
KeepSize
)
noexcept
;
112
Q_DECL_MALLOCLIKE
113
static
Q_CORE_EXPORT
void
*
allocate2
(
QArrayData
**pdata, qsizetype capacity,
114
AllocationOption
option =
QArrayData
::
KeepSize
)
noexcept
;
115
116
[[
nodiscard
]]
static
Q_CORE_EXPORT
std
::
pair
<
QArrayData
*,
void
*>
reallocateUnaligned
(
QArrayData
*
data
,
void
*
dataPointer
,
117
qsizetype
objectSize
,
qsizetype
newCapacity
,
AllocationOption
option
)
noexcept
;
118
static
Q_CORE_EXPORT
void
deallocate
(
QArrayData
*data, qsizetype objectSize,
119
qsizetype alignment)
noexcept
;
120
};
121
122
Q_DECLARE_OPERATORS_FOR_FLAGS(
QArrayData
::ArrayOptions)
123
124
namespace
QtPrivate
{
125
// QArrayData with strictest alignment requirements supported by malloc()
126
#
if
defined
(
Q_PROCESSOR_X86_32
)
&&
defined
(
Q_CC_GNU
)
127
// GCC's definition is incorrect since GCC 8 (commit r240248 in SVN; commit
128
// 63012d9a57edc950c5f30242d1e19318b5708060 in Git). This is applied to all
129
// GCC-like compilers in case they decide to follow GCC's lead in being wrong.
130
constexpr
size_t
MaxPrimitiveAlignment
= 2 *
sizeof
(
void
*);
131
#
else
132
constexpr
size_t
MaxPrimitiveAlignment
=
alignof
(
std
::
max_align_t
);
133
#
endif
134
135
struct
alignas
(
MaxPrimitiveAlignment
)
AlignedQArrayData
:
QArrayData
136
{
137
};
138
}
139
140
template
<
class
T>
141
struct
QTypedArrayData
142
:
QArrayData
143
{
144
struct
AlignmentDummy
{
QtPrivate
::
AlignedQArrayData
header
; T
data
; };
145
146
[[nodiscard]]
static
QTypedArrayAllocationResult
<T>
147
allocate
(qsizetype capacity,
AllocationOption
option =
QArrayData
::
KeepSize
)
148
{
149
static_assert
(
sizeof
(QTypedArrayData) ==
sizeof
(
QArrayData
));
150
Q_DECL_UNINITIALIZED
151
QArrayData *d;
152
void
*result;
153
if
constexpr
(
sizeof
(T) == 1) {
154
// necessarily, alignof(T) == 1
155
result = allocate1(&d, capacity, option);
156
}
else
if
constexpr
(
sizeof
(T) == 2) {
157
// alignof(T) may be 1, but that makes no difference
158
result = allocate2(&d, capacity, option);
159
}
else
{
160
result = QArrayData::allocate(&d,
sizeof
(T),
alignof
(
AlignmentDummy
), capacity, option);
161
}
162
#
if
__has_builtin
(
__builtin_assume_aligned
)
163
// and yet we do offer results that have stricter alignment
164
result = __builtin_assume_aligned(result, Q_ALIGNOF(AlignmentDummy));
165
#
endif
166
return
{
static_cast
<QTypedArrayData *>(d),
static_cast
<T *>(result)};
167
}
168
169
static
QTypedArrayAllocationResult
<T>
170
reallocateUnaligned
(QTypedArrayData *data, T *dataPointer, qsizetype capacity,
AllocationOption
option)
171
{
172
static_assert
(
sizeof
(QTypedArrayData) ==
sizeof
(
QArrayData
));
173
std::pair<QArrayData *,
void
*> pair =
174
QArrayData::reallocateUnaligned(data, dataPointer,
sizeof
(T), capacity, option);
175
return
{
static_cast
<QTypedArrayData *>(pair.first),
static_cast
<T *>(pair.second)};
176
}
177
178
static
void
deallocate
(
QArrayData
*data)
noexcept
179
{
180
static_assert
(
sizeof
(QTypedArrayData) ==
sizeof
(
QArrayData
));
181
QArrayData::deallocate(data,
sizeof
(T),
alignof
(
AlignmentDummy
));
182
}
183
184
static
T *
dataStart
(
QArrayData
*data, qsizetype alignment)
noexcept
185
{
186
// Alignment is a power of two
187
Q_ASSERT(alignment >= qsizetype(
alignof
(
QArrayData
)) && !(alignment & (alignment - 1)));
188
void
*start =
reinterpret_cast
<
void
*>((quintptr(data) +
sizeof
(
QArrayData
) + alignment - 1)
189
& ~quintptr(alignment - 1));
190
return
static_cast
<T *>(start);
191
}
192
193
constexpr
static
qsizetype
maxSize
()
noexcept
194
{
195
// -1 to deal with the pointer one-past-the-end
196
return
(QtPrivate::MaxAllocSize -
sizeof
(QtPrivate::AlignedQArrayData) - 1) /
sizeof
(T);
197
}
198
constexpr
static
qsizetype
max_size
()
noexcept
199
{
200
return
maxSize();
201
}
202
};
203
204
namespace
QtPrivate
{
205
struct
Q_CORE_EXPORT
QContainerImplHelper
206
{
207
enum
CutResult
{
Null
,
Empty
,
Full
,
Subset
};
208
static
constexpr
CutResult
mid
(
qsizetype
originalLength
,
qsizetype
*
_position
,
qsizetype
*
_length
)
209
{
210
qsizetype
&
position
= *
_position
;
211
qsizetype
&
length
= *
_length
;
212
if
(
position
>
originalLength
) {
213
position
= 0;
214
length
= 0;
215
return
Null
;
216
}
217
218
if
(
position
< 0) {
219
if
(
length
< 0 ||
length
+
position
>=
originalLength
) {
220
position
= 0;
221
length
=
originalLength
;
222
return
Full
;
223
}
224
if
(
length
+
position
<= 0) {
225
position
=
length
= 0;
226
return
Null
;
227
}
228
length
+=
position
;
229
position
= 0;
230
}
else
if
(
size_t
(
length
) >
size_t
(
originalLength
-
position
)) {
231
length
=
originalLength
-
position
;
232
}
233
234
if
(
position
== 0 &&
length
==
originalLength
)
235
return
Full
;
236
237
return
length
> 0 ?
Subset
:
Empty
;
238
}
239
};
240
}
241
242
#
undef
Q_DECL_MALLOCLIKE
243
244
QT_END_NAMESPACE
245
246
#
endif
// include guard
QtPrivate
Definition
qalloc.h:29
QtPrivate::MaxPrimitiveAlignment
constexpr size_t MaxPrimitiveAlignment
Definition
qarraydata.h:132
Q_DECL_MALLOCLIKE
#define Q_DECL_MALLOCLIKE
Definition
qarraydata.h:22
__has_builtin
#define __has_builtin(x)
Definition
qcompilerdetection.h:444
__has_cpp_attribute
#define __has_cpp_attribute(x)
Definition
qcompilerdetection.h:456
QArrayData
Definition
qarraydata.h:38
QArrayData::detachCapacity
qsizetype detachCapacity(qsizetype newSize) const noexcept
Definition
qarraydata.h:99
QArrayData::ArrayOption
ArrayOption
Definition
qarraydata.h:49
QArrayData::CapacityReserved
@ CapacityReserved
the capacity was reserved by the user, try to keep it
Definition
qarraydata.h:51
QArrayData::ArrayOptionDefault
@ ArrayOptionDefault
Definition
qarraydata.h:50
QArrayData::deref
bool deref() noexcept
Returns false if deallocation is necessary.
Definition
qarraydata.h:81
QArrayData::flags
ArrayOptions flags
Definition
qarraydata.h:56
QArrayData::isShared
bool isShared() const noexcept
Definition
qarraydata.h:86
QArrayData::alloc
qsizetype alloc
Definition
qarraydata.h:57
QArrayData::constAllocatedCapacity
qsizetype constAllocatedCapacity() const noexcept
Definition
qarraydata.h:66
QArrayData::allocate
static Q_DECL_MALLOCLIKE Q_CORE_EXPORT void * allocate(QArrayData **pdata, qsizetype objectSize, qsizetype alignment, qsizetype capacity, AllocationOption option=QArrayData::KeepSize) noexcept
Definition
qarraydata.cpp:190
QArrayData::deallocate
static Q_CORE_EXPORT void deallocate(QArrayData *data, qsizetype objectSize, qsizetype alignment) noexcept
Definition
qarraydata.cpp:249
QArrayData::needsDetach
bool needsDetach() noexcept
Definition
qarraydata.h:94
QArrayData::allocate2
static Q_DECL_MALLOCLIKE Q_CORE_EXPORT void * allocate2(QArrayData **pdata, qsizetype capacity, AllocationOption option=QArrayData::KeepSize) noexcept
Definition
qarraydata.cpp:209
QArrayData::allocatedCapacity
qsizetype allocatedCapacity() noexcept
Definition
qarraydata.h:59
QArrayData::GrowthPosition
GrowthPosition
Definition
qarraydata.h:44
QArrayData::GrowsAtEnd
@ GrowsAtEnd
Definition
qarraydata.h:45
QArrayData::GrowsAtBeginning
@ GrowsAtBeginning
Definition
qarraydata.h:46
QArrayData::ref
bool ref() noexcept
Returns true if sharing took place.
Definition
qarraydata.h:74
QArrayData::AllocationOption
AllocationOption
Definition
qarraydata.h:39
QArrayData::Grow
@ Grow
Definition
qarraydata.h:40
QArrayData::KeepSize
@ KeepSize
Definition
qarraydata.h:41
QArrayData::allocate1
static Q_DECL_MALLOCLIKE Q_CORE_EXPORT void * allocate1(QArrayData **pdata, qsizetype capacity, AllocationOption option=QArrayData::KeepSize) noexcept
Definition
qarraydata.cpp:202
QTypedArrayAllocationResult
Definition
qarraydata.h:29
QTypedArrayAllocationResult::header
QTypedArrayData< T > * header
Definition
qarraydata.h:30
QTypedArrayAllocationResult::ptr
T * ptr
Definition
qarraydata.h:31
QTypedArrayData::AlignmentDummy
Definition
qarraydata.h:144
QTypedArrayData::AlignmentDummy::header
QtPrivate::AlignedQArrayData header
Definition
qarraydata.h:144
QTypedArrayData::AlignmentDummy::data
T data
Definition
qarraydata.h:144
QTypedArrayData::maxSize
static constexpr qsizetype maxSize() noexcept
Definition
qarraydata.h:193
QTypedArrayData::max_size
static constexpr qsizetype max_size() noexcept
Definition
qarraydata.h:198
QTypedArrayData::deallocate
static void deallocate(QArrayData *data) noexcept
Definition
qarraydata.h:178
QTypedArrayData::dataStart
static T * dataStart(QArrayData *data, qsizetype alignment) noexcept
Definition
qarraydata.h:184
QTypedArrayData::allocate
static QTypedArrayAllocationResult< T > allocate(qsizetype capacity, AllocationOption option=QArrayData::KeepSize)
Definition
qarraydata.h:147
QTypedArrayData::reallocateUnaligned
static QTypedArrayAllocationResult< T > reallocateUnaligned(QTypedArrayData *data, T *dataPointer, qsizetype capacity, AllocationOption option)
Definition
qarraydata.h:170
QtPrivate::AlignedQArrayData
Definition
qarraydata.h:136
QtPrivate::QContainerImplHelper
Definition
qarraydata.h:206
qtbase
src
corelib
tools
qarraydata.h
Generated on
for Qt by
1.18.0