1#include <climits>
2#include <memory>
3#include <type_traits>
4
5#if REVISION == 0
6// Pre-c3d0205ee771 layout.
7#define SUBCLASS_PADDING
8#endif
9#if REVISION <= 1
10// Pre-D123580 layout.
11#define BITMASKS
12#endif
13#if REVISION <= 2
14// Pre-D125496 layout.
15#define SHORT_UNION
16#endif
17#if REVISION == 3
18// Pre-D128285 layout.
19#define PACKED_ANON_STRUCT
20#endif
21// REVISION == 4: current layout
22
23#ifdef PACKED_ANON_STRUCT
24#define BEGIN_PACKED_ANON_STRUCT struct __attribute__((packed)) {
25#define END_PACKED_ANON_STRUCT };
26#else
27#define BEGIN_PACKED_ANON_STRUCT
28#define END_PACKED_ANON_STRUCT
29#endif
30
31
32namespace std {
33namespace __lldb {
34
35template <class _Tp, int _Idx,
36 bool _CanBeEmptyBase =
37 std::is_empty<_Tp>::value && !std::is_final<_Tp>::value>
38struct __compressed_pair_elem {
39 explicit __compressed_pair_elem(_Tp __t) : __value_(__t) {}
40
41 _Tp &__get() { return __value_; }
42
43private:
44 _Tp __value_;
45};
46
47template <class _Tp, int _Idx>
48struct __compressed_pair_elem<_Tp, _Idx, true> : private _Tp {
49 explicit __compressed_pair_elem(_Tp __t) : _Tp(__t) {}
50
51 _Tp &__get() { return *this; }
52};
53
54template <class _T1, class _T2>
55class __compressed_pair : private __compressed_pair_elem<_T1, 0>,
56 private __compressed_pair_elem<_T2, 1> {
57public:
58 using _Base1 = __compressed_pair_elem<_T1, 0>;
59 using _Base2 = __compressed_pair_elem<_T2, 1>;
60
61 explicit __compressed_pair(_T1 __t1, _T2 __t2) : _Base1(__t1), _Base2(__t2) {}
62
63 _T1 &first() { return static_cast<_Base1 &>(*this).__get(); }
64};
65
66#if defined(ALTERNATE_LAYOUT) && defined(SUBCLASS_PADDING)
67template <class _CharT, size_t = sizeof(_CharT)> struct __padding {
68 unsigned char __xx[sizeof(_CharT) - 1];
69};
70
71template <class _CharT> struct __padding<_CharT, 1> {};
72#endif
73
74template <class _CharT, class _Traits, class _Allocator> class basic_string {
75public:
76 typedef _CharT value_type;
77 typedef _Allocator allocator_type;
78 typedef allocator_traits<allocator_type> __alloc_traits;
79 typedef typename __alloc_traits::size_type size_type;
80 typedef typename __alloc_traits::pointer pointer;
81
82#ifdef ALTERNATE_LAYOUT
83
84 struct __long {
85 pointer __data_;
86 size_type __size_;
87#ifdef BITMASKS
88 size_type __cap_;
89#else
90 size_type __cap_ : sizeof(size_type) * CHAR_BIT - 1;
91 size_type __is_long_ : 1;
92#endif
93 };
94
95 enum {
96 __min_cap = (sizeof(__long) - 1) / sizeof(value_type) > 2
97 ? (sizeof(__long) - 1) / sizeof(value_type)
98 : 2
99 };
100
101 struct __short {
102 value_type __data_[__min_cap];
103#ifdef BITMASKS
104#ifdef SUBCLASS_PADDING
105 struct : __padding<value_type> {
106 unsigned char __size_;
107 };
108#else
109 unsigned char __padding[sizeof(value_type) - 1];
110 unsigned char __size_;
111#endif
112#else // !BITMASKS
113 unsigned char __size_ : 7;
114 unsigned char __is_long_ : 1;
115#endif
116 };
117
118#ifdef BITMASKS
119#if __BYTE_ORDER__ == __ORDER_BIG_ENDIAN__
120 static const size_type __short_shift = 1;
121 static const size_type __long_mask = 0x1ul;
122#else
123 static const size_type __short_shift = 0;
124 static const size_type __long_mask = ~(size_type(~0) >> 1);
125#endif
126#else // !BITMASKS
127#if __BYTE_ORDER__ == __ORDER_BIG_ENDIAN__
128 static const size_type __endian_factor = 2;
129#else
130 static const size_type __endian_factor = 1;
131#endif
132#endif // BITMASKS
133
134#else // !ALTERNATE_LAYOUT
135
136 struct __long {
137#ifdef BITMASKS
138 size_type __cap_;
139#else
140 BEGIN_PACKED_ANON_STRUCT
141 size_type __is_long_ : 1;
142 size_type __cap_ : sizeof(size_type) * CHAR_BIT - 1;
143 END_PACKED_ANON_STRUCT
144#endif
145 size_type __size_;
146 pointer __data_;
147 };
148
149 enum {
150 __min_cap = (sizeof(__long) - 1) / sizeof(value_type) > 2
151 ? (sizeof(__long) - 1) / sizeof(value_type)
152 : 2
153 };
154
155 struct __short {
156#ifdef SHORT_UNION
157 union {
158#ifdef BITMASKS
159 unsigned char __size_;
160#else
161 struct {
162 unsigned char __is_long_ : 1;
163 unsigned char __size_ : 7;
164 };
165#endif
166 value_type __lx;
167 };
168#else
169 BEGIN_PACKED_ANON_STRUCT
170 unsigned char __is_long_ : 1;
171 unsigned char __size_ : 7;
172 END_PACKED_ANON_STRUCT
173 char __padding_[sizeof(value_type) - 1];
174#endif
175 value_type __data_[__min_cap];
176 };
177
178#ifdef BITMASKS
179#if __BYTE_ORDER__ == __ORDER_BIG_ENDIAN__
180 static const size_type __short_shift = 0;
181 static const size_type __long_mask = ~(size_type(~0) >> 1);
182#else
183 static const size_type __short_shift = 1;
184 static const size_type __long_mask = 0x1ul;
185#endif
186#else // !BITMASKS
187#if __BYTE_ORDER__ == __ORDER_BIG_ENDIAN__
188 static const size_type __endian_factor = 1;
189#else
190 static const size_type __endian_factor = 2;
191#endif
192#endif
193
194#endif // ALTERNATE_LAYOUT
195
196 union __ulx {
197 __long __lx;
198 __short __lxx;
199 };
200
201 enum { __n_words = sizeof(__ulx) / sizeof(size_type) };
202
203 struct __raw {
204 size_type __words[__n_words];
205 };
206
207 struct __rep {
208 union {
209 __long __l;
210 __short __s;
211 __raw __r;
212 };
213 };
214
215 __compressed_pair<__rep, allocator_type> __r_;
216
217public:
218 template <size_t __N>
219 basic_string(unsigned char __size, const value_type (&__data)[__N])
220 : __r_({}, {}) {
221 static_assert(__N < __min_cap, "");
222#ifdef BITMASKS
223 __r_.first().__s.__size_ = __size << __short_shift;
224#else
225 __r_.first().__s.__size_ = __size;
226 __r_.first().__s.__is_long_ = false;
227#endif
228 for (size_t __i = 0; __i < __N; ++__i)
229 __r_.first().__s.__data_[__i] = __data[__i];
230 }
231 basic_string(size_t __cap, size_type __size, pointer __data) : __r_({}, {}) {
232#ifdef BITMASKS
233 __r_.first().__l.__cap_ = __cap | __long_mask;
234#else
235 __r_.first().__l.__cap_ = __cap / __endian_factor;
236 __r_.first().__l.__is_long_ = true;
237#endif
238 __r_.first().__l.__size_ = __size;
239 __r_.first().__l.__data_ = __data;
240 }
241};
242
243using string = basic_string<char, std::char_traits<char>, std::allocator<char>>;
244
245} // namespace __lldb
246} // namespace std
247
248int main() {
249 char longdata[] = "I am a very long string";
250 std::__lldb::string longstring(sizeof(longdata), sizeof(longdata) - 1,
251 longdata);
252 std::__lldb::string shortstring(5, "short");
253 return 0; // Break here
254}
255

source code of lldb/test/API/functionalities/data-formatter/data-formatter-stl/libcxx/string/simulator/main.cpp