xref: /freebsd/contrib/llvm-project/lldb/source/Symbol/CompilerType.cpp (revision 700637cbb5e582861067a11aaca4d053546871d2)
1 //===-- CompilerType.cpp --------------------------------------------------===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 
9 #include "lldb/Symbol/CompilerType.h"
10 
11 #include "lldb/Core/Debugger.h"
12 #include "lldb/Symbol/Type.h"
13 #include "lldb/Target/ExecutionContext.h"
14 #include "lldb/Target/Process.h"
15 #include "lldb/Utility/ConstString.h"
16 #include "lldb/Utility/DataBufferHeap.h"
17 #include "lldb/Utility/DataExtractor.h"
18 #include "lldb/Utility/LLDBLog.h"
19 #include "lldb/Utility/Log.h"
20 #include "lldb/Utility/Scalar.h"
21 #include "lldb/Utility/Stream.h"
22 #include "lldb/Utility/StreamString.h"
23 
24 #include <iterator>
25 #include <mutex>
26 #include <optional>
27 
28 using namespace lldb;
29 using namespace lldb_private;
30 
31 // Tests
32 
IsAggregateType() const33 bool CompilerType::IsAggregateType() const {
34   if (IsValid())
35     if (auto type_system_sp = GetTypeSystem())
36       return type_system_sp->IsAggregateType(m_type);
37   return false;
38 }
39 
IsAnonymousType() const40 bool CompilerType::IsAnonymousType() const {
41   if (IsValid())
42     if (auto type_system_sp = GetTypeSystem())
43       return type_system_sp->IsAnonymousType(m_type);
44   return false;
45 }
46 
IsScopedEnumerationType() const47 bool CompilerType::IsScopedEnumerationType() const {
48   if (IsValid())
49     if (auto type_system_sp = GetTypeSystem())
50       return type_system_sp->IsScopedEnumerationType(m_type);
51   return false;
52 }
53 
IsArrayType(CompilerType * element_type_ptr,uint64_t * size,bool * is_incomplete) const54 bool CompilerType::IsArrayType(CompilerType *element_type_ptr, uint64_t *size,
55                                bool *is_incomplete) const {
56   if (IsValid())
57     if (auto type_system_sp = GetTypeSystem())
58       return type_system_sp->IsArrayType(m_type, element_type_ptr, size,
59                                       is_incomplete);
60 
61   if (element_type_ptr)
62     element_type_ptr->Clear();
63   if (size)
64     *size = 0;
65   if (is_incomplete)
66     *is_incomplete = false;
67   return false;
68 }
69 
IsVectorType(CompilerType * element_type,uint64_t * size) const70 bool CompilerType::IsVectorType(CompilerType *element_type,
71                                 uint64_t *size) const {
72   if (IsValid())
73     if (auto type_system_sp = GetTypeSystem())
74       return type_system_sp->IsVectorType(m_type, element_type, size);
75   return false;
76 }
77 
IsRuntimeGeneratedType() const78 bool CompilerType::IsRuntimeGeneratedType() const {
79   if (IsValid())
80     if (auto type_system_sp = GetTypeSystem())
81       return type_system_sp->IsRuntimeGeneratedType(m_type);
82   return false;
83 }
84 
IsCharType() const85 bool CompilerType::IsCharType() const {
86   if (IsValid())
87     if (auto type_system_sp = GetTypeSystem())
88       return type_system_sp->IsCharType(m_type);
89   return false;
90 }
91 
IsCompleteType() const92 bool CompilerType::IsCompleteType() const {
93   if (IsValid())
94     if (auto type_system_sp = GetTypeSystem())
95       return type_system_sp->IsCompleteType(m_type);
96   return false;
97 }
98 
IsForcefullyCompleted() const99 bool CompilerType::IsForcefullyCompleted() const {
100   if (IsValid())
101     if (auto type_system_sp = GetTypeSystem())
102       return type_system_sp->IsForcefullyCompleted(m_type);
103   return false;
104 }
105 
IsConst() const106 bool CompilerType::IsConst() const {
107   if (IsValid())
108     if (auto type_system_sp = GetTypeSystem())
109       return type_system_sp->IsConst(m_type);
110   return false;
111 }
112 
GetPtrAuthKey() const113 unsigned CompilerType::GetPtrAuthKey() const {
114   if (IsValid())
115     if (auto type_system_sp = GetTypeSystem())
116       return type_system_sp->GetPtrAuthKey(m_type);
117   return 0;
118 }
119 
GetPtrAuthDiscriminator() const120 unsigned CompilerType::GetPtrAuthDiscriminator() const {
121   if (IsValid())
122     if (auto type_system_sp = GetTypeSystem())
123       return type_system_sp->GetPtrAuthDiscriminator(m_type);
124   return 0;
125 }
126 
GetPtrAuthAddressDiversity() const127 bool CompilerType::GetPtrAuthAddressDiversity() const {
128   if (IsValid())
129     if (auto type_system_sp = GetTypeSystem())
130       return type_system_sp->GetPtrAuthAddressDiversity(m_type);
131   return false;
132 }
133 
IsFunctionType() const134 bool CompilerType::IsFunctionType() const {
135   if (IsValid())
136     if (auto type_system_sp = GetTypeSystem())
137       return type_system_sp->IsFunctionType(m_type);
138   return false;
139 }
140 
141 // Used to detect "Homogeneous Floating-point Aggregates"
142 uint32_t
IsHomogeneousAggregate(CompilerType * base_type_ptr) const143 CompilerType::IsHomogeneousAggregate(CompilerType *base_type_ptr) const {
144   if (IsValid())
145     if (auto type_system_sp = GetTypeSystem())
146       return type_system_sp->IsHomogeneousAggregate(m_type, base_type_ptr);
147   return 0;
148 }
149 
GetNumberOfFunctionArguments() const150 size_t CompilerType::GetNumberOfFunctionArguments() const {
151   if (IsValid())
152     if (auto type_system_sp = GetTypeSystem())
153       return type_system_sp->GetNumberOfFunctionArguments(m_type);
154   return 0;
155 }
156 
157 CompilerType
GetFunctionArgumentAtIndex(const size_t index) const158 CompilerType::GetFunctionArgumentAtIndex(const size_t index) const {
159   if (IsValid())
160     if (auto type_system_sp = GetTypeSystem())
161       return type_system_sp->GetFunctionArgumentAtIndex(m_type, index);
162   return CompilerType();
163 }
164 
IsFunctionPointerType() const165 bool CompilerType::IsFunctionPointerType() const {
166   if (IsValid())
167     if (auto type_system_sp = GetTypeSystem())
168       return type_system_sp->IsFunctionPointerType(m_type);
169   return false;
170 }
171 
IsMemberFunctionPointerType() const172 bool CompilerType::IsMemberFunctionPointerType() const {
173   if (IsValid())
174     if (auto type_system_sp = GetTypeSystem())
175       return type_system_sp->IsMemberFunctionPointerType(m_type);
176   return false;
177 }
178 
IsBlockPointerType(CompilerType * function_pointer_type_ptr) const179 bool CompilerType::IsBlockPointerType(
180     CompilerType *function_pointer_type_ptr) const {
181   if (IsValid())
182     if (auto type_system_sp = GetTypeSystem())
183       return type_system_sp->IsBlockPointerType(m_type, function_pointer_type_ptr);
184   return false;
185 }
186 
IsIntegerType(bool & is_signed) const187 bool CompilerType::IsIntegerType(bool &is_signed) const {
188   if (IsValid())
189     if (auto type_system_sp = GetTypeSystem())
190       return type_system_sp->IsIntegerType(m_type, is_signed);
191   return false;
192 }
193 
IsEnumerationType(bool & is_signed) const194 bool CompilerType::IsEnumerationType(bool &is_signed) const {
195   if (IsValid())
196     if (auto type_system_sp = GetTypeSystem())
197       return type_system_sp->IsEnumerationType(m_type, is_signed);
198   return false;
199 }
200 
IsIntegerOrEnumerationType(bool & is_signed) const201 bool CompilerType::IsIntegerOrEnumerationType(bool &is_signed) const {
202   return IsIntegerType(is_signed) || IsEnumerationType(is_signed);
203 }
204 
IsPointerType(CompilerType * pointee_type) const205 bool CompilerType::IsPointerType(CompilerType *pointee_type) const {
206   if (IsValid()) {
207     if (auto type_system_sp = GetTypeSystem())
208       return type_system_sp->IsPointerType(m_type, pointee_type);
209   }
210   if (pointee_type)
211     pointee_type->Clear();
212   return false;
213 }
214 
IsPointerOrReferenceType(CompilerType * pointee_type) const215 bool CompilerType::IsPointerOrReferenceType(CompilerType *pointee_type) const {
216   if (IsValid()) {
217     if (auto type_system_sp = GetTypeSystem())
218       return type_system_sp->IsPointerOrReferenceType(m_type, pointee_type);
219   }
220   if (pointee_type)
221     pointee_type->Clear();
222   return false;
223 }
224 
IsReferenceType(CompilerType * pointee_type,bool * is_rvalue) const225 bool CompilerType::IsReferenceType(CompilerType *pointee_type,
226                                    bool *is_rvalue) const {
227   if (IsValid()) {
228     if (auto type_system_sp = GetTypeSystem())
229       return type_system_sp->IsReferenceType(m_type, pointee_type, is_rvalue);
230   }
231   if (pointee_type)
232     pointee_type->Clear();
233   return false;
234 }
235 
ShouldTreatScalarValueAsAddress() const236 bool CompilerType::ShouldTreatScalarValueAsAddress() const {
237   if (IsValid())
238     if (auto type_system_sp = GetTypeSystem())
239       return type_system_sp->ShouldTreatScalarValueAsAddress(m_type);
240   return false;
241 }
242 
IsFloatingPointType(uint32_t & count,bool & is_complex) const243 bool CompilerType::IsFloatingPointType(uint32_t &count,
244                                        bool &is_complex) const {
245   if (IsValid()) {
246     if (auto type_system_sp = GetTypeSystem())
247       return type_system_sp->IsFloatingPointType(m_type, count, is_complex);
248   }
249   count = 0;
250   is_complex = false;
251   return false;
252 }
253 
IsDefined() const254 bool CompilerType::IsDefined() const {
255   if (IsValid())
256     if (auto type_system_sp = GetTypeSystem())
257       return type_system_sp->IsDefined(m_type);
258   return true;
259 }
260 
IsPolymorphicClass() const261 bool CompilerType::IsPolymorphicClass() const {
262   if (IsValid()) {
263     if (auto type_system_sp = GetTypeSystem())
264       return type_system_sp->IsPolymorphicClass(m_type);
265   }
266   return false;
267 }
268 
IsPossibleDynamicType(CompilerType * dynamic_pointee_type,bool check_cplusplus,bool check_objc) const269 bool CompilerType::IsPossibleDynamicType(CompilerType *dynamic_pointee_type,
270                                          bool check_cplusplus,
271                                          bool check_objc) const {
272   if (IsValid())
273     if (auto type_system_sp = GetTypeSystem())
274       return type_system_sp->IsPossibleDynamicType(m_type, dynamic_pointee_type,
275                                                 check_cplusplus, check_objc);
276   return false;
277 }
278 
IsScalarType() const279 bool CompilerType::IsScalarType() const {
280   if (IsValid())
281     if (auto type_system_sp = GetTypeSystem())
282       return type_system_sp->IsScalarType(m_type);
283   return false;
284 }
285 
IsTemplateType() const286 bool CompilerType::IsTemplateType() const {
287   if (IsValid())
288     if (auto type_system_sp = GetTypeSystem())
289       return type_system_sp->IsTemplateType(m_type);
290   return false;
291 }
292 
IsTypedefType() const293 bool CompilerType::IsTypedefType() const {
294   if (IsValid())
295     if (auto type_system_sp = GetTypeSystem())
296       return type_system_sp->IsTypedefType(m_type);
297   return false;
298 }
299 
IsVoidType() const300 bool CompilerType::IsVoidType() const {
301   if (IsValid())
302     if (auto type_system_sp = GetTypeSystem())
303       return type_system_sp->IsVoidType(m_type);
304   return false;
305 }
306 
IsPointerToScalarType() const307 bool CompilerType::IsPointerToScalarType() const {
308   if (!IsValid())
309     return false;
310 
311   return IsPointerType() && GetPointeeType().IsScalarType();
312 }
313 
IsArrayOfScalarType() const314 bool CompilerType::IsArrayOfScalarType() const {
315   CompilerType element_type;
316   if (IsArrayType(&element_type))
317     return element_type.IsScalarType();
318   return false;
319 }
320 
IsBeingDefined() const321 bool CompilerType::IsBeingDefined() const {
322   if (IsValid())
323     if (auto type_system_sp = GetTypeSystem())
324       return type_system_sp->IsBeingDefined(m_type);
325   return false;
326 }
327 
IsInteger() const328 bool CompilerType::IsInteger() const {
329   bool is_signed = false; // May be reset by the call below.
330   return IsIntegerType(is_signed);
331 }
332 
IsFloat() const333 bool CompilerType::IsFloat() const {
334   uint32_t count = 0;
335   bool is_complex = false;
336   return IsFloatingPointType(count, is_complex);
337 }
338 
IsEnumerationType() const339 bool CompilerType::IsEnumerationType() const {
340   bool is_signed = false; // May be reset by the call below.
341   return IsEnumerationType(is_signed);
342 }
343 
IsUnscopedEnumerationType() const344 bool CompilerType::IsUnscopedEnumerationType() const {
345   return IsEnumerationType() && !IsScopedEnumerationType();
346 }
347 
IsIntegerOrUnscopedEnumerationType() const348 bool CompilerType::IsIntegerOrUnscopedEnumerationType() const {
349   return IsInteger() || IsUnscopedEnumerationType();
350 }
351 
IsSigned() const352 bool CompilerType::IsSigned() const {
353   return GetTypeInfo() & lldb::eTypeIsSigned;
354 }
355 
IsNullPtrType() const356 bool CompilerType::IsNullPtrType() const {
357   return GetCanonicalType().GetBasicTypeEnumeration() ==
358          lldb::eBasicTypeNullPtr;
359 }
360 
IsBoolean() const361 bool CompilerType::IsBoolean() const {
362   return GetCanonicalType().GetBasicTypeEnumeration() == lldb::eBasicTypeBool;
363 }
364 
IsEnumerationIntegerTypeSigned() const365 bool CompilerType::IsEnumerationIntegerTypeSigned() const {
366   if (IsValid())
367     return GetEnumerationIntegerType().GetTypeInfo() & lldb::eTypeIsSigned;
368 
369   return false;
370 }
371 
IsScalarOrUnscopedEnumerationType() const372 bool CompilerType::IsScalarOrUnscopedEnumerationType() const {
373   return IsScalarType() || IsUnscopedEnumerationType();
374 }
375 
IsPromotableIntegerType() const376 bool CompilerType::IsPromotableIntegerType() const {
377   // Unscoped enums are always considered as promotable, even if their
378   // underlying type does not need to be promoted (e.g. "int").
379   if (IsUnscopedEnumerationType())
380     return true;
381 
382   switch (GetCanonicalType().GetBasicTypeEnumeration()) {
383   case lldb::eBasicTypeBool:
384   case lldb::eBasicTypeChar:
385   case lldb::eBasicTypeSignedChar:
386   case lldb::eBasicTypeUnsignedChar:
387   case lldb::eBasicTypeShort:
388   case lldb::eBasicTypeUnsignedShort:
389   case lldb::eBasicTypeWChar:
390   case lldb::eBasicTypeSignedWChar:
391   case lldb::eBasicTypeUnsignedWChar:
392   case lldb::eBasicTypeChar16:
393   case lldb::eBasicTypeChar32:
394     return true;
395 
396   default:
397     return false;
398   }
399 
400   llvm_unreachable("All cases handled above.");
401 }
402 
IsPointerToVoid() const403 bool CompilerType::IsPointerToVoid() const {
404   if (!IsValid())
405     return false;
406 
407   return IsPointerType() &&
408          GetPointeeType().GetBasicTypeEnumeration() == lldb::eBasicTypeVoid;
409 }
410 
IsRecordType() const411 bool CompilerType::IsRecordType() const {
412   if (!IsValid())
413     return false;
414 
415   return GetCanonicalType().GetTypeClass() &
416          (lldb::eTypeClassClass | lldb::eTypeClassStruct |
417           lldb::eTypeClassUnion);
418 }
419 
IsVirtualBase(CompilerType target_base,CompilerType * virtual_base,bool carry_virtual) const420 bool CompilerType::IsVirtualBase(CompilerType target_base,
421                                  CompilerType *virtual_base,
422                                  bool carry_virtual) const {
423   if (CompareTypes(target_base))
424     return carry_virtual;
425 
426   if (!carry_virtual) {
427     uint32_t num_virtual_bases = GetNumVirtualBaseClasses();
428     for (uint32_t i = 0; i < num_virtual_bases; ++i) {
429       uint32_t bit_offset;
430       auto base = GetVirtualBaseClassAtIndex(i, &bit_offset);
431       if (base.IsVirtualBase(target_base, virtual_base,
432                              /*carry_virtual*/ true)) {
433         if (virtual_base)
434           *virtual_base = base;
435 
436         return true;
437       }
438     }
439   }
440 
441   uint32_t num_direct_bases = GetNumDirectBaseClasses();
442   for (uint32_t i = 0; i < num_direct_bases; ++i) {
443     uint32_t bit_offset;
444     auto base = GetDirectBaseClassAtIndex(i, &bit_offset);
445     if (base.IsVirtualBase(target_base, virtual_base, carry_virtual))
446       return true;
447   }
448 
449   return false;
450 }
451 
IsContextuallyConvertibleToBool() const452 bool CompilerType::IsContextuallyConvertibleToBool() const {
453   return IsScalarType() || IsUnscopedEnumerationType() || IsPointerType() ||
454          IsNullPtrType() || IsArrayType();
455 }
456 
IsBasicType() const457 bool CompilerType::IsBasicType() const {
458   return GetCanonicalType().GetBasicTypeEnumeration() !=
459          lldb::eBasicTypeInvalid;
460 }
461 
TypeDescription()462 std::string CompilerType::TypeDescription() {
463   auto name = GetTypeName();
464   auto canonical_name = GetCanonicalType().GetTypeName();
465   if (name.IsEmpty() || canonical_name.IsEmpty())
466     return "''"; // Should not happen, unless the input is broken somehow.
467 
468   if (name == canonical_name)
469     return llvm::formatv("'{0}'", name);
470 
471   return llvm::formatv("'{0}' (canonically referred to as '{1}')", name,
472                        canonical_name);
473 }
474 
CompareTypes(CompilerType rhs) const475 bool CompilerType::CompareTypes(CompilerType rhs) const {
476   if (*this == rhs)
477     return true;
478 
479   const ConstString name = GetFullyUnqualifiedType().GetTypeName();
480   const ConstString rhs_name = rhs.GetFullyUnqualifiedType().GetTypeName();
481   return name == rhs_name;
482 }
483 
GetTypeTag()484 const char *CompilerType::GetTypeTag() {
485   switch (GetTypeClass()) {
486   case lldb::eTypeClassClass:
487     return "class";
488   case lldb::eTypeClassEnumeration:
489     return "enum";
490   case lldb::eTypeClassStruct:
491     return "struct";
492   case lldb::eTypeClassUnion:
493     return "union";
494   default:
495     return "unknown";
496   }
497   llvm_unreachable("All cases are covered by code above.");
498 }
499 
GetNumberOfNonEmptyBaseClasses()500 uint32_t CompilerType::GetNumberOfNonEmptyBaseClasses() {
501   uint32_t ret = 0;
502   uint32_t num_direct_bases = GetNumDirectBaseClasses();
503 
504   for (uint32_t i = 0; i < num_direct_bases; ++i) {
505     uint32_t bit_offset;
506     CompilerType base_type = GetDirectBaseClassAtIndex(i, &bit_offset);
507     if (base_type.GetNumFields() > 0 ||
508         base_type.GetNumberOfNonEmptyBaseClasses() > 0)
509       ret += 1;
510   }
511   return ret;
512 }
513 
514 // Type Completion
515 
GetCompleteType() const516 bool CompilerType::GetCompleteType() const {
517   if (IsValid())
518     if (auto type_system_sp = GetTypeSystem())
519       return type_system_sp->GetCompleteType(m_type);
520   return false;
521 }
522 
523 // AST related queries
GetPointerByteSize() const524 size_t CompilerType::GetPointerByteSize() const {
525   if (auto type_system_sp = GetTypeSystem())
526     return type_system_sp->GetPointerByteSize();
527   return 0;
528 }
529 
GetTypeName(bool BaseOnly) const530 ConstString CompilerType::GetTypeName(bool BaseOnly) const {
531   if (IsValid()) {
532     if (auto type_system_sp = GetTypeSystem())
533       return type_system_sp->GetTypeName(m_type, BaseOnly);
534   }
535   return ConstString("<invalid>");
536 }
537 
GetDisplayTypeName() const538 ConstString CompilerType::GetDisplayTypeName() const {
539   if (IsValid())
540     if (auto type_system_sp = GetTypeSystem())
541       return type_system_sp->GetDisplayTypeName(m_type);
542   return ConstString("<invalid>");
543 }
544 
GetMangledTypeName() const545 ConstString CompilerType::GetMangledTypeName() const {
546   if (IsValid()) {
547     if (auto type_system_sp = GetTypeSystem())
548       return type_system_sp->GetMangledTypeName(m_type);
549   }
550   return ConstString("<invalid>");
551 }
552 
GetTypeInfo(CompilerType * pointee_or_element_compiler_type) const553 uint32_t CompilerType::GetTypeInfo(
554     CompilerType *pointee_or_element_compiler_type) const {
555   if (IsValid())
556   if (auto type_system_sp = GetTypeSystem())
557     return type_system_sp->GetTypeInfo(m_type,
558                                        pointee_or_element_compiler_type);
559   return 0;
560 }
561 
GetMinimumLanguage()562 lldb::LanguageType CompilerType::GetMinimumLanguage() {
563   if (IsValid())
564     if (auto type_system_sp = GetTypeSystem())
565       return type_system_sp->GetMinimumLanguage(m_type);
566   return lldb::eLanguageTypeC;
567 }
568 
GetTypeClass() const569 lldb::TypeClass CompilerType::GetTypeClass() const {
570   if (IsValid())
571     if (auto type_system_sp = GetTypeSystem())
572       return type_system_sp->GetTypeClass(m_type);
573   return lldb::eTypeClassInvalid;
574 }
575 
SetCompilerType(lldb::TypeSystemWP type_system,lldb::opaque_compiler_type_t type)576 void CompilerType::SetCompilerType(lldb::TypeSystemWP type_system,
577                                    lldb::opaque_compiler_type_t type) {
578   m_type_system = type_system;
579   m_type = type;
580 }
581 
SetCompilerType(CompilerType::TypeSystemSPWrapper type_system,lldb::opaque_compiler_type_t type)582 void CompilerType::SetCompilerType(CompilerType::TypeSystemSPWrapper type_system,
583                                    lldb::opaque_compiler_type_t type) {
584   m_type_system = type_system.GetSharedPointer();
585   m_type = type;
586 }
587 
GetTypeQualifiers() const588 unsigned CompilerType::GetTypeQualifiers() const {
589   if (IsValid())
590     if (auto type_system_sp = GetTypeSystem())
591       return type_system_sp->GetTypeQualifiers(m_type);
592   return 0;
593 }
594 
595 // Creating related types
596 
597 CompilerType
GetArrayElementType(ExecutionContextScope * exe_scope) const598 CompilerType::GetArrayElementType(ExecutionContextScope *exe_scope) const {
599   if (IsValid()) {
600     if (auto type_system_sp = GetTypeSystem())
601       return type_system_sp->GetArrayElementType(m_type, exe_scope);
602   }
603   return CompilerType();
604 }
605 
GetArrayType(uint64_t size) const606 CompilerType CompilerType::GetArrayType(uint64_t size) const {
607   if (IsValid()) {
608     if (auto type_system_sp = GetTypeSystem())
609       return type_system_sp->GetArrayType(m_type, size);
610   }
611   return CompilerType();
612 }
613 
GetCanonicalType() const614 CompilerType CompilerType::GetCanonicalType() const {
615   if (IsValid())
616     if (auto type_system_sp = GetTypeSystem())
617       return type_system_sp->GetCanonicalType(m_type);
618   return CompilerType();
619 }
620 
GetFullyUnqualifiedType() const621 CompilerType CompilerType::GetFullyUnqualifiedType() const {
622   if (IsValid())
623     if (auto type_system_sp = GetTypeSystem())
624       return type_system_sp->GetFullyUnqualifiedType(m_type);
625   return CompilerType();
626 }
627 
GetEnumerationIntegerType() const628 CompilerType CompilerType::GetEnumerationIntegerType() const {
629   if (IsValid())
630     if (auto type_system_sp = GetTypeSystem())
631       return type_system_sp->GetEnumerationIntegerType(m_type);
632   return CompilerType();
633 }
634 
GetFunctionArgumentCount() const635 int CompilerType::GetFunctionArgumentCount() const {
636   if (IsValid()) {
637     if (auto type_system_sp = GetTypeSystem())
638       return type_system_sp->GetFunctionArgumentCount(m_type);
639   }
640   return -1;
641 }
642 
GetFunctionArgumentTypeAtIndex(size_t idx) const643 CompilerType CompilerType::GetFunctionArgumentTypeAtIndex(size_t idx) const {
644   if (IsValid()) {
645     if (auto type_system_sp = GetTypeSystem())
646       return type_system_sp->GetFunctionArgumentTypeAtIndex(m_type, idx);
647   }
648   return CompilerType();
649 }
650 
GetFunctionReturnType() const651 CompilerType CompilerType::GetFunctionReturnType() const {
652   if (IsValid()) {
653     if (auto type_system_sp = GetTypeSystem())
654       return type_system_sp->GetFunctionReturnType(m_type);
655   }
656   return CompilerType();
657 }
658 
GetNumMemberFunctions() const659 size_t CompilerType::GetNumMemberFunctions() const {
660   if (IsValid()) {
661     if (auto type_system_sp = GetTypeSystem())
662       return type_system_sp->GetNumMemberFunctions(m_type);
663   }
664   return 0;
665 }
666 
GetMemberFunctionAtIndex(size_t idx)667 TypeMemberFunctionImpl CompilerType::GetMemberFunctionAtIndex(size_t idx) {
668   if (IsValid()) {
669     if (auto type_system_sp = GetTypeSystem())
670       return type_system_sp->GetMemberFunctionAtIndex(m_type, idx);
671   }
672   return TypeMemberFunctionImpl();
673 }
674 
GetNonReferenceType() const675 CompilerType CompilerType::GetNonReferenceType() const {
676   if (IsValid())
677     if (auto type_system_sp = GetTypeSystem())
678       return type_system_sp->GetNonReferenceType(m_type);
679   return CompilerType();
680 }
681 
GetPointeeType() const682 CompilerType CompilerType::GetPointeeType() const {
683   if (IsValid()) {
684     if (auto type_system_sp = GetTypeSystem())
685       return type_system_sp->GetPointeeType(m_type);
686   }
687   return CompilerType();
688 }
689 
GetPointerType() const690 CompilerType CompilerType::GetPointerType() const {
691   if (IsValid()) {
692     if (auto type_system_sp = GetTypeSystem())
693       return type_system_sp->GetPointerType(m_type);
694   }
695   return CompilerType();
696 }
697 
AddPtrAuthModifier(uint32_t payload) const698 CompilerType CompilerType::AddPtrAuthModifier(uint32_t payload) const {
699   if (IsValid())
700     if (auto type_system_sp = GetTypeSystem())
701       return type_system_sp->AddPtrAuthModifier(m_type, payload);
702   return CompilerType();
703 }
704 
GetLValueReferenceType() const705 CompilerType CompilerType::GetLValueReferenceType() const {
706   if (IsValid())
707     if (auto type_system_sp = GetTypeSystem())
708       return type_system_sp->GetLValueReferenceType(m_type);
709   return CompilerType();
710 }
711 
GetRValueReferenceType() const712 CompilerType CompilerType::GetRValueReferenceType() const {
713   if (IsValid())
714     if (auto type_system_sp = GetTypeSystem())
715       return type_system_sp->GetRValueReferenceType(m_type);
716   return CompilerType();
717 }
718 
GetAtomicType() const719 CompilerType CompilerType::GetAtomicType() const {
720   if (IsValid())
721     if (auto type_system_sp = GetTypeSystem())
722       return type_system_sp->GetAtomicType(m_type);
723   return CompilerType();
724 }
725 
AddConstModifier() const726 CompilerType CompilerType::AddConstModifier() const {
727   if (IsValid())
728     if (auto type_system_sp = GetTypeSystem())
729       return type_system_sp->AddConstModifier(m_type);
730   return CompilerType();
731 }
732 
AddVolatileModifier() const733 CompilerType CompilerType::AddVolatileModifier() const {
734   if (IsValid())
735     if (auto type_system_sp = GetTypeSystem())
736       return type_system_sp->AddVolatileModifier(m_type);
737   return CompilerType();
738 }
739 
AddRestrictModifier() const740 CompilerType CompilerType::AddRestrictModifier() const {
741   if (IsValid())
742     if (auto type_system_sp = GetTypeSystem())
743       return type_system_sp->AddRestrictModifier(m_type);
744   return CompilerType();
745 }
746 
CreateTypedef(const char * name,const CompilerDeclContext & decl_ctx,uint32_t payload) const747 CompilerType CompilerType::CreateTypedef(const char *name,
748                                          const CompilerDeclContext &decl_ctx,
749                                          uint32_t payload) const {
750   if (IsValid())
751     if (auto type_system_sp = GetTypeSystem())
752       return type_system_sp->CreateTypedef(m_type, name, decl_ctx, payload);
753   return CompilerType();
754 }
755 
GetTypedefedType() const756 CompilerType CompilerType::GetTypedefedType() const {
757   if (IsValid())
758     if (auto type_system_sp = GetTypeSystem())
759       return type_system_sp->GetTypedefedType(m_type);
760   return CompilerType();
761 }
762 
763 // Create related types using the current type's AST
764 
765 CompilerType
GetBasicTypeFromAST(lldb::BasicType basic_type) const766 CompilerType::GetBasicTypeFromAST(lldb::BasicType basic_type) const {
767   if (IsValid())
768     if (auto type_system_sp = GetTypeSystem())
769       return type_system_sp->GetBasicTypeFromAST(basic_type);
770   return CompilerType();
771 }
772 // Exploring the type
773 
774 llvm::Expected<uint64_t>
GetBitSize(ExecutionContextScope * exe_scope) const775 CompilerType::GetBitSize(ExecutionContextScope *exe_scope) const {
776   if (IsValid())
777     if (auto type_system_sp = GetTypeSystem())
778       return type_system_sp->GetBitSize(m_type, exe_scope);
779   return llvm::createStringError("Invalid type: Cannot determine size");
780 }
781 
782 llvm::Expected<uint64_t>
GetByteSize(ExecutionContextScope * exe_scope) const783 CompilerType::GetByteSize(ExecutionContextScope *exe_scope) const {
784   auto bit_size_or_err = GetBitSize(exe_scope);
785   if (!bit_size_or_err)
786     return bit_size_or_err.takeError();
787   return (*bit_size_or_err + 7) / 8;
788 }
789 
790 std::optional<size_t>
GetTypeBitAlign(ExecutionContextScope * exe_scope) const791 CompilerType::GetTypeBitAlign(ExecutionContextScope *exe_scope) const {
792   if (IsValid())
793     if (auto type_system_sp = GetTypeSystem())
794       return type_system_sp->GetTypeBitAlign(m_type, exe_scope);
795   return {};
796 }
797 
GetEncoding(uint64_t & count) const798 lldb::Encoding CompilerType::GetEncoding(uint64_t &count) const {
799   if (IsValid())
800     if (auto type_system_sp = GetTypeSystem())
801       return type_system_sp->GetEncoding(m_type, count);
802   return lldb::eEncodingInvalid;
803 }
804 
GetFormat() const805 lldb::Format CompilerType::GetFormat() const {
806   if (IsValid())
807     if (auto type_system_sp = GetTypeSystem())
808       return type_system_sp->GetFormat(m_type);
809   return lldb::eFormatDefault;
810 }
811 
812 llvm::Expected<uint32_t>
GetNumChildren(bool omit_empty_base_classes,const ExecutionContext * exe_ctx) const813 CompilerType::GetNumChildren(bool omit_empty_base_classes,
814                              const ExecutionContext *exe_ctx) const {
815   if (IsValid())
816     if (auto type_system_sp = GetTypeSystem())
817       return type_system_sp->GetNumChildren(m_type, omit_empty_base_classes,
818                                        exe_ctx);
819   return llvm::createStringError("invalid type");
820 }
821 
GetBasicTypeEnumeration() const822 lldb::BasicType CompilerType::GetBasicTypeEnumeration() const {
823   if (IsValid())
824     if (auto type_system_sp = GetTypeSystem())
825       return type_system_sp->GetBasicTypeEnumeration(m_type);
826   return eBasicTypeInvalid;
827 }
828 
ForEachEnumerator(std::function<bool (const CompilerType & integer_type,ConstString name,const llvm::APSInt & value)> const & callback) const829 void CompilerType::ForEachEnumerator(
830     std::function<bool(const CompilerType &integer_type,
831                        ConstString name,
832                        const llvm::APSInt &value)> const &callback) const {
833   if (IsValid())
834     if (auto type_system_sp = GetTypeSystem())
835       return type_system_sp->ForEachEnumerator(m_type, callback);
836 }
837 
GetNumFields() const838 uint32_t CompilerType::GetNumFields() const {
839   if (IsValid())
840     if (auto type_system_sp = GetTypeSystem())
841       return type_system_sp->GetNumFields(m_type);
842   return 0;
843 }
844 
GetFieldAtIndex(size_t idx,std::string & name,uint64_t * bit_offset_ptr,uint32_t * bitfield_bit_size_ptr,bool * is_bitfield_ptr) const845 CompilerType CompilerType::GetFieldAtIndex(size_t idx, std::string &name,
846                                            uint64_t *bit_offset_ptr,
847                                            uint32_t *bitfield_bit_size_ptr,
848                                            bool *is_bitfield_ptr) const {
849   if (IsValid())
850     if (auto type_system_sp = GetTypeSystem())
851       return type_system_sp->GetFieldAtIndex(m_type, idx, name, bit_offset_ptr,
852                                         bitfield_bit_size_ptr, is_bitfield_ptr);
853   return CompilerType();
854 }
855 
GetNumDirectBaseClasses() const856 uint32_t CompilerType::GetNumDirectBaseClasses() const {
857   if (IsValid())
858     if (auto type_system_sp = GetTypeSystem())
859       return type_system_sp->GetNumDirectBaseClasses(m_type);
860   return 0;
861 }
862 
GetNumVirtualBaseClasses() const863 uint32_t CompilerType::GetNumVirtualBaseClasses() const {
864   if (IsValid())
865     if (auto type_system_sp = GetTypeSystem())
866       return type_system_sp->GetNumVirtualBaseClasses(m_type);
867   return 0;
868 }
869 
870 CompilerType
GetDirectBaseClassAtIndex(size_t idx,uint32_t * bit_offset_ptr) const871 CompilerType::GetDirectBaseClassAtIndex(size_t idx,
872                                         uint32_t *bit_offset_ptr) const {
873   if (IsValid())
874     if (auto type_system_sp = GetTypeSystem())
875       return type_system_sp->GetDirectBaseClassAtIndex(m_type, idx,
876                                                     bit_offset_ptr);
877   return CompilerType();
878 }
879 
880 CompilerType
GetVirtualBaseClassAtIndex(size_t idx,uint32_t * bit_offset_ptr) const881 CompilerType::GetVirtualBaseClassAtIndex(size_t idx,
882                                          uint32_t *bit_offset_ptr) const {
883   if (IsValid())
884     if (auto type_system_sp = GetTypeSystem())
885       return type_system_sp->GetVirtualBaseClassAtIndex(m_type, idx,
886                                                      bit_offset_ptr);
887   return CompilerType();
888 }
889 
GetStaticFieldWithName(llvm::StringRef name) const890 CompilerDecl CompilerType::GetStaticFieldWithName(llvm::StringRef name) const {
891   if (IsValid())
892     return GetTypeSystem()->GetStaticFieldWithName(m_type, name);
893   return CompilerDecl();
894 }
895 
GetDereferencedType(ExecutionContext * exe_ctx,std::string & deref_name,uint32_t & deref_byte_size,int32_t & deref_byte_offset,ValueObject * valobj,uint64_t & language_flags) const896 llvm::Expected<CompilerType> CompilerType::GetDereferencedType(
897     ExecutionContext *exe_ctx, std::string &deref_name,
898     uint32_t &deref_byte_size, int32_t &deref_byte_offset, ValueObject *valobj,
899     uint64_t &language_flags) const {
900   if (IsValid())
901     if (auto type_system_sp = GetTypeSystem())
902       return type_system_sp->GetDereferencedType(
903           m_type, exe_ctx, deref_name, deref_byte_size, deref_byte_offset,
904           valobj, language_flags);
905   return CompilerType();
906 }
907 
GetChildCompilerTypeAtIndex(ExecutionContext * exe_ctx,size_t idx,bool transparent_pointers,bool omit_empty_base_classes,bool ignore_array_bounds,std::string & child_name,uint32_t & child_byte_size,int32_t & child_byte_offset,uint32_t & child_bitfield_bit_size,uint32_t & child_bitfield_bit_offset,bool & child_is_base_class,bool & child_is_deref_of_parent,ValueObject * valobj,uint64_t & language_flags) const908 llvm::Expected<CompilerType> CompilerType::GetChildCompilerTypeAtIndex(
909     ExecutionContext *exe_ctx, size_t idx, bool transparent_pointers,
910     bool omit_empty_base_classes, bool ignore_array_bounds,
911     std::string &child_name, uint32_t &child_byte_size,
912     int32_t &child_byte_offset, uint32_t &child_bitfield_bit_size,
913     uint32_t &child_bitfield_bit_offset, bool &child_is_base_class,
914     bool &child_is_deref_of_parent, ValueObject *valobj,
915     uint64_t &language_flags) const {
916   if (IsValid())
917     if (auto type_system_sp = GetTypeSystem())
918       return type_system_sp->GetChildCompilerTypeAtIndex(
919           m_type, exe_ctx, idx, transparent_pointers, omit_empty_base_classes,
920           ignore_array_bounds, child_name, child_byte_size, child_byte_offset,
921           child_bitfield_bit_size, child_bitfield_bit_offset,
922           child_is_base_class, child_is_deref_of_parent, valobj,
923           language_flags);
924   return CompilerType();
925 }
926 
927 // Look for a child member (doesn't include base classes, but it does include
928 // their members) in the type hierarchy. Returns an index path into
929 // "clang_type" on how to reach the appropriate member.
930 //
931 //    class A
932 //    {
933 //    public:
934 //        int m_a;
935 //        int m_b;
936 //    };
937 //
938 //    class B
939 //    {
940 //    };
941 //
942 //    class C :
943 //        public B,
944 //        public A
945 //    {
946 //    };
947 //
948 // If we have a clang type that describes "class C", and we wanted to looked
949 // "m_b" in it:
950 //
951 // With omit_empty_base_classes == false we would get an integer array back
952 // with: { 1,  1 } The first index 1 is the child index for "class A" within
953 // class C The second index 1 is the child index for "m_b" within class A
954 //
955 // With omit_empty_base_classes == true we would get an integer array back
956 // with: { 0,  1 } The first index 0 is the child index for "class A" within
957 // class C (since class B doesn't have any members it doesn't count) The second
958 // index 1 is the child index for "m_b" within class A
959 
GetIndexOfChildMemberWithName(llvm::StringRef name,bool omit_empty_base_classes,std::vector<uint32_t> & child_indexes) const960 size_t CompilerType::GetIndexOfChildMemberWithName(
961     llvm::StringRef name, bool omit_empty_base_classes,
962     std::vector<uint32_t> &child_indexes) const {
963   if (IsValid() && !name.empty()) {
964     if (auto type_system_sp = GetTypeSystem())
965       return type_system_sp->GetIndexOfChildMemberWithName(
966         m_type, name, omit_empty_base_classes, child_indexes);
967   }
968   return 0;
969 }
970 
971 CompilerType
GetDirectNestedTypeWithName(llvm::StringRef name) const972 CompilerType::GetDirectNestedTypeWithName(llvm::StringRef name) const {
973   if (IsValid() && !name.empty()) {
974     if (auto type_system_sp = GetTypeSystem())
975       return type_system_sp->GetDirectNestedTypeWithName(m_type, name);
976   }
977   return CompilerType();
978 }
979 
GetNumTemplateArguments(bool expand_pack) const980 size_t CompilerType::GetNumTemplateArguments(bool expand_pack) const {
981   if (IsValid()) {
982     if (auto type_system_sp = GetTypeSystem())
983       return type_system_sp->GetNumTemplateArguments(m_type, expand_pack);
984   }
985   return 0;
986 }
987 
988 TemplateArgumentKind
GetTemplateArgumentKind(size_t idx,bool expand_pack) const989 CompilerType::GetTemplateArgumentKind(size_t idx, bool expand_pack) const {
990   if (IsValid())
991     if (auto type_system_sp = GetTypeSystem())
992       return type_system_sp->GetTemplateArgumentKind(m_type, idx, expand_pack);
993   return eTemplateArgumentKindNull;
994 }
995 
GetTypeTemplateArgument(size_t idx,bool expand_pack) const996 CompilerType CompilerType::GetTypeTemplateArgument(size_t idx,
997                                                    bool expand_pack) const {
998   if (IsValid()) {
999     if (auto type_system_sp = GetTypeSystem())
1000       return type_system_sp->GetTypeTemplateArgument(m_type, idx, expand_pack);
1001   }
1002   return CompilerType();
1003 }
1004 
1005 std::optional<CompilerType::IntegralTemplateArgument>
GetIntegralTemplateArgument(size_t idx,bool expand_pack) const1006 CompilerType::GetIntegralTemplateArgument(size_t idx, bool expand_pack) const {
1007   if (IsValid())
1008     if (auto type_system_sp = GetTypeSystem())
1009       return type_system_sp->GetIntegralTemplateArgument(m_type, idx, expand_pack);
1010   return std::nullopt;
1011 }
1012 
GetTypeForFormatters() const1013 CompilerType CompilerType::GetTypeForFormatters() const {
1014   if (IsValid())
1015     if (auto type_system_sp = GetTypeSystem())
1016       return type_system_sp->GetTypeForFormatters(m_type);
1017   return CompilerType();
1018 }
1019 
ShouldPrintAsOneLiner(ValueObject * valobj) const1020 LazyBool CompilerType::ShouldPrintAsOneLiner(ValueObject *valobj) const {
1021   if (IsValid())
1022     if (auto type_system_sp = GetTypeSystem())
1023       return type_system_sp->ShouldPrintAsOneLiner(m_type, valobj);
1024   return eLazyBoolCalculate;
1025 }
1026 
IsMeaninglessWithoutDynamicResolution() const1027 bool CompilerType::IsMeaninglessWithoutDynamicResolution() const {
1028   if (IsValid())
1029     if (auto type_system_sp = GetTypeSystem())
1030       return type_system_sp->IsMeaninglessWithoutDynamicResolution(m_type);
1031   return false;
1032 }
1033 
1034 // Get the index of the child of "clang_type" whose name matches. This function
1035 // doesn't descend into the children, but only looks one level deep and name
1036 // matches can include base class names.
1037 
1038 llvm::Expected<uint32_t>
GetIndexOfChildWithName(llvm::StringRef name,bool omit_empty_base_classes) const1039 CompilerType::GetIndexOfChildWithName(llvm::StringRef name,
1040                                       bool omit_empty_base_classes) const {
1041   if (IsValid() && !name.empty()) {
1042     if (auto type_system_sp = GetTypeSystem())
1043       return type_system_sp->GetIndexOfChildWithName(m_type, name,
1044                                                      omit_empty_base_classes);
1045   }
1046   return llvm::createStringError("Type has no child named '%s'",
1047                                  name.str().c_str());
1048 }
1049 
1050 // Dumping types
1051 
DumpTypeValue(Stream * s,lldb::Format format,const DataExtractor & data,lldb::offset_t byte_offset,size_t byte_size,uint32_t bitfield_bit_size,uint32_t bitfield_bit_offset,ExecutionContextScope * exe_scope)1052 bool CompilerType::DumpTypeValue(Stream *s, lldb::Format format,
1053                                  const DataExtractor &data,
1054                                  lldb::offset_t byte_offset, size_t byte_size,
1055                                  uint32_t bitfield_bit_size,
1056                                  uint32_t bitfield_bit_offset,
1057                                  ExecutionContextScope *exe_scope) {
1058   if (IsValid())
1059     if (auto type_system_sp = GetTypeSystem())
1060       return type_system_sp->DumpTypeValue(
1061           m_type, *s, format, data, byte_offset, byte_size, bitfield_bit_size,
1062           bitfield_bit_offset, exe_scope);
1063   return false;
1064 }
1065 
DumpTypeDescription(lldb::DescriptionLevel level) const1066 void CompilerType::DumpTypeDescription(lldb::DescriptionLevel level) const {
1067   if (IsValid())
1068     if (auto type_system_sp = GetTypeSystem())
1069       type_system_sp->DumpTypeDescription(m_type, level);
1070 }
1071 
DumpTypeDescription(Stream * s,lldb::DescriptionLevel level) const1072 void CompilerType::DumpTypeDescription(Stream *s,
1073                                        lldb::DescriptionLevel level) const {
1074   if (IsValid())
1075     if (auto type_system_sp = GetTypeSystem())
1076       type_system_sp->DumpTypeDescription(m_type, *s, level);
1077 }
1078 
1079 #ifndef NDEBUG
dump() const1080 LLVM_DUMP_METHOD void CompilerType::dump() const {
1081   if (IsValid())
1082     if (auto type_system_sp = GetTypeSystem())
1083       return type_system_sp->dump(m_type);
1084   llvm::errs() << "<invalid>\n";
1085 }
1086 #endif
1087 
GetValueAsScalar(const lldb_private::DataExtractor & data,lldb::offset_t data_byte_offset,size_t data_byte_size,Scalar & value,ExecutionContextScope * exe_scope) const1088 bool CompilerType::GetValueAsScalar(const lldb_private::DataExtractor &data,
1089                                     lldb::offset_t data_byte_offset,
1090                                     size_t data_byte_size, Scalar &value,
1091                                     ExecutionContextScope *exe_scope) const {
1092   if (!IsValid())
1093     return false;
1094 
1095   if (IsAggregateType()) {
1096     return false; // Aggregate types don't have scalar values
1097   } else {
1098     uint64_t count = 0;
1099     lldb::Encoding encoding = GetEncoding(count);
1100 
1101     if (encoding == lldb::eEncodingInvalid || count != 1)
1102       return false;
1103 
1104     auto byte_size_or_err = GetByteSize(exe_scope);
1105     if (!byte_size_or_err) {
1106       LLDB_LOG_ERRORV(
1107           GetLog(LLDBLog::Types), byte_size_or_err.takeError(),
1108           "Cannot get value as scalar: Cannot determine type size: {0}");
1109       return false;
1110     }
1111     uint64_t byte_size = *byte_size_or_err;
1112 
1113     // A bit or byte size of 0 is not a bug, but it doesn't make sense to read a
1114     // scalar of zero size.
1115     if (byte_size == 0)
1116       return false;
1117 
1118     lldb::offset_t offset = data_byte_offset;
1119     switch (encoding) {
1120     case lldb::eEncodingInvalid:
1121       break;
1122     case lldb::eEncodingVector:
1123       break;
1124     case lldb::eEncodingUint:
1125       if (byte_size <= sizeof(unsigned long long)) {
1126         uint64_t uval64 = data.GetMaxU64(&offset, byte_size);
1127         if (byte_size <= sizeof(unsigned int)) {
1128           value = (unsigned int)uval64;
1129           return true;
1130         } else if (byte_size <= sizeof(unsigned long)) {
1131           value = (unsigned long)uval64;
1132           return true;
1133         } else if (byte_size <= sizeof(unsigned long long)) {
1134           value = (unsigned long long)uval64;
1135           return true;
1136         } else
1137           value.Clear();
1138       }
1139       break;
1140 
1141     case lldb::eEncodingSint:
1142       if (byte_size <= sizeof(long long)) {
1143         int64_t sval64 = data.GetMaxS64(&offset, byte_size);
1144         if (byte_size <= sizeof(int)) {
1145           value = (int)sval64;
1146           return true;
1147         } else if (byte_size <= sizeof(long)) {
1148           value = (long)sval64;
1149           return true;
1150         } else if (byte_size <= sizeof(long long)) {
1151           value = (long long)sval64;
1152           return true;
1153         } else
1154           value.Clear();
1155       }
1156       break;
1157 
1158     case lldb::eEncodingIEEE754:
1159       if (byte_size <= sizeof(long double)) {
1160         uint32_t u32;
1161         uint64_t u64;
1162         if (byte_size == sizeof(float)) {
1163           if (sizeof(float) == sizeof(uint32_t)) {
1164             u32 = data.GetU32(&offset);
1165             value = *((float *)&u32);
1166             return true;
1167           } else if (sizeof(float) == sizeof(uint64_t)) {
1168             u64 = data.GetU64(&offset);
1169             value = *((float *)&u64);
1170             return true;
1171           }
1172         } else if (byte_size == sizeof(double)) {
1173           if (sizeof(double) == sizeof(uint32_t)) {
1174             u32 = data.GetU32(&offset);
1175             value = *((double *)&u32);
1176             return true;
1177           } else if (sizeof(double) == sizeof(uint64_t)) {
1178             u64 = data.GetU64(&offset);
1179             value = *((double *)&u64);
1180             return true;
1181           }
1182         } else if (byte_size == sizeof(long double)) {
1183           if (sizeof(long double) == sizeof(uint32_t)) {
1184             u32 = data.GetU32(&offset);
1185             value = *((long double *)&u32);
1186             return true;
1187           } else if (sizeof(long double) == sizeof(uint64_t)) {
1188             u64 = data.GetU64(&offset);
1189             value = *((long double *)&u64);
1190             return true;
1191           }
1192         }
1193       }
1194       break;
1195     }
1196   }
1197   return false;
1198 }
1199 
CompilerType(CompilerType::TypeSystemSPWrapper type_system,lldb::opaque_compiler_type_t type)1200 CompilerType::CompilerType(CompilerType::TypeSystemSPWrapper type_system,
1201                            lldb::opaque_compiler_type_t type)
1202     : m_type_system(type_system.GetSharedPointer()), m_type(type) {
1203   assert(Verify() && "verification failed");
1204 }
1205 
CompilerType(lldb::TypeSystemWP type_system,lldb::opaque_compiler_type_t type)1206 CompilerType::CompilerType(lldb::TypeSystemWP type_system,
1207                            lldb::opaque_compiler_type_t type)
1208     : m_type_system(type_system), m_type(type) {
1209   assert(Verify() && "verification failed");
1210 }
1211 
1212 #ifndef NDEBUG
Verify() const1213 bool CompilerType::Verify() const {
1214   if (!IsValid())
1215     return true;
1216   if (auto type_system_sp = GetTypeSystem())
1217     return type_system_sp->Verify(m_type);
1218   return true;
1219 }
1220 #endif
1221 
GetTypeSystem() const1222 CompilerType::TypeSystemSPWrapper CompilerType::GetTypeSystem() const {
1223   return {m_type_system.lock()};
1224 }
1225 
operator ==(const CompilerType::TypeSystemSPWrapper & other) const1226 bool CompilerType::TypeSystemSPWrapper::operator==(
1227     const CompilerType::TypeSystemSPWrapper &other) const {
1228   if (!m_typesystem_sp && !other.m_typesystem_sp)
1229     return true;
1230   if (m_typesystem_sp && other.m_typesystem_sp)
1231     return m_typesystem_sp.get() == other.m_typesystem_sp.get();
1232   return false;
1233 }
1234 
operator ->() const1235 TypeSystem *CompilerType::TypeSystemSPWrapper::operator->() const {
1236   assert(m_typesystem_sp);
1237   return m_typesystem_sp.get();
1238 }
1239 
operator ==(const lldb_private::CompilerType & lhs,const lldb_private::CompilerType & rhs)1240 bool lldb_private::operator==(const lldb_private::CompilerType &lhs,
1241                               const lldb_private::CompilerType &rhs) {
1242   return lhs.GetTypeSystem() == rhs.GetTypeSystem() &&
1243          lhs.GetOpaqueQualType() == rhs.GetOpaqueQualType();
1244 }
1245 
operator !=(const lldb_private::CompilerType & lhs,const lldb_private::CompilerType & rhs)1246 bool lldb_private::operator!=(const lldb_private::CompilerType &lhs,
1247                               const lldb_private::CompilerType &rhs) {
1248   return !(lhs == rhs);
1249 }
1250