Type.h revision 263363
1//===-- Type.h --------------------------------------------------*- C++ -*-===//
2//
3//                     The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9
10#ifndef liblldb_Type_h_
11#define liblldb_Type_h_
12
13#include "lldb/lldb-private.h"
14#include "lldb/Core/ClangForward.h"
15#include "lldb/Core/ConstString.h"
16#include "lldb/Core/UserID.h"
17#include "lldb/Symbol/ClangASTType.h"
18#include "lldb/Symbol/Declaration.h"
19
20#include <set>
21
22namespace lldb_private {
23
24class SymbolFileType :
25    public std::enable_shared_from_this<SymbolFileType>,
26    public UserID
27    {
28    public:
29        SymbolFileType (SymbolFile &symbol_file, lldb::user_id_t uid) :
30            UserID (uid),
31            m_symbol_file (symbol_file)
32        {
33        }
34
35        ~SymbolFileType ()
36        {
37        }
38
39        Type *
40        operator->()
41        {
42            return GetType ();
43        }
44
45        Type *
46        GetType ();
47
48    protected:
49        SymbolFile &m_symbol_file;
50        lldb::TypeSP m_type_sp;
51    };
52
53class Type :
54    public std::enable_shared_from_this<Type>,
55    public UserID
56{
57public:
58    typedef enum EncodingDataTypeTag
59    {
60        eEncodingInvalid,
61        eEncodingIsUID,                 ///< This type is the type whose UID is m_encoding_uid
62        eEncodingIsConstUID,            ///< This type is the type whose UID is m_encoding_uid with the const qualifier added
63        eEncodingIsRestrictUID,         ///< This type is the type whose UID is m_encoding_uid with the restrict qualifier added
64        eEncodingIsVolatileUID,         ///< This type is the type whose UID is m_encoding_uid with the volatile qualifier added
65        eEncodingIsTypedefUID,          ///< This type is pointer to a type whose UID is m_encoding_uid
66        eEncodingIsPointerUID,          ///< This type is pointer to a type whose UID is m_encoding_uid
67        eEncodingIsLValueReferenceUID,  ///< This type is L value reference to a type whose UID is m_encoding_uid
68        eEncodingIsRValueReferenceUID,  ///< This type is R value reference to a type whose UID is m_encoding_uid
69        eEncodingIsSyntheticUID
70    } EncodingDataType;
71
72    typedef enum ResolveStateTag
73    {
74        eResolveStateUnresolved = 0,
75        eResolveStateForward    = 1,
76        eResolveStateLayout     = 2,
77        eResolveStateFull       = 3
78    } ResolveState;
79
80    Type (lldb::user_id_t uid,
81          SymbolFile* symbol_file,
82          const ConstString &name,
83          uint64_t byte_size,
84          SymbolContextScope *context,
85          lldb::user_id_t encoding_uid,
86          EncodingDataType encoding_uid_type,
87          const Declaration& decl,
88          const ClangASTType &clang_qual_type,
89          ResolveState clang_type_resolve_state);
90
91    // This makes an invalid type.  Used for functions that return a Type when they
92    // get an error.
93    Type();
94
95    Type (const Type &rhs);
96
97    const Type&
98    operator= (const Type& rhs);
99
100    void
101    Dump(Stream *s, bool show_context);
102
103    void
104    DumpTypeName(Stream *s);
105
106
107    void
108    GetDescription (Stream *s, lldb::DescriptionLevel level, bool show_name);
109
110    SymbolFile *
111    GetSymbolFile()
112    {
113        return m_symbol_file;
114    }
115    const SymbolFile *
116    GetSymbolFile() const
117    {
118        return m_symbol_file;
119    }
120
121    TypeList*
122    GetTypeList();
123
124    const ConstString&
125    GetName();
126
127    uint64_t
128    GetByteSize();
129
130    uint32_t
131    GetNumChildren (bool omit_empty_base_classes);
132
133    bool
134    IsAggregateType ();
135
136    bool
137    IsValidType ()
138    {
139        return m_encoding_uid_type != eEncodingInvalid;
140    }
141
142    bool
143    IsTypedef ()
144    {
145        return m_encoding_uid_type == eEncodingIsTypedefUID;
146    }
147
148    lldb::TypeSP
149    GetTypedefType();
150
151    const ConstString &
152    GetName () const
153    {
154        return m_name;
155    }
156
157    ConstString
158    GetQualifiedName ();
159
160    void
161    DumpValue(ExecutionContext *exe_ctx,
162              Stream *s,
163              const DataExtractor &data,
164              uint32_t data_offset,
165              bool show_type,
166              bool show_summary,
167              bool verbose,
168              lldb::Format format = lldb::eFormatDefault);
169
170    bool
171    DumpValueInMemory(ExecutionContext *exe_ctx,
172                      Stream *s,
173                      lldb::addr_t address,
174                      AddressType address_type,
175                      bool show_types,
176                      bool show_summary,
177                      bool verbose);
178
179    bool
180    ReadFromMemory (ExecutionContext *exe_ctx,
181                    lldb::addr_t address,
182                    AddressType address_type,
183                    DataExtractor &data);
184
185    bool
186    WriteToMemory (ExecutionContext *exe_ctx,
187                   lldb::addr_t address,
188                   AddressType address_type,
189                   DataExtractor &data);
190
191    bool
192    GetIsDeclaration() const;
193
194    void
195    SetIsDeclaration(bool b);
196
197    bool
198    GetIsExternal() const;
199
200    void
201    SetIsExternal(bool b);
202
203    lldb::Format
204    GetFormat ();
205
206    lldb::Encoding
207    GetEncoding (uint64_t &count);
208
209    SymbolContextScope *
210    GetSymbolContextScope()
211    {
212        return m_context;
213    }
214    const SymbolContextScope *
215    GetSymbolContextScope() const
216    {
217        return m_context;
218    }
219    void
220    SetSymbolContextScope(SymbolContextScope *context)
221    {
222        m_context = context;
223    }
224
225    const lldb_private::Declaration &
226    GetDeclaration () const;
227
228    // Get the clang type, and resolve definitions for any
229    // class/struct/union/enum types completely.
230    ClangASTType
231    GetClangFullType ();
232
233    // Get the clang type, and resolve definitions enough so that the type could
234    // have layout performed. This allows ptrs and refs to class/struct/union/enum
235    // types remain forward declarations.
236    ClangASTType
237    GetClangLayoutType ();
238
239    // Get the clang type and leave class/struct/union/enum types as forward
240    // declarations if they haven't already been fully defined.
241    ClangASTType
242    GetClangForwardType ();
243
244    ClangASTContext &
245    GetClangASTContext ();
246
247    static int
248    Compare(const Type &a, const Type &b);
249
250    // From a fully qualified typename, split the type into the type basename
251    // and the remaining type scope (namespaces/classes).
252    static bool
253    GetTypeScopeAndBasename (const char* &name_cstr,
254                             std::string &scope,
255                             std::string &basename,
256                             lldb::TypeClass &type_class);
257    void
258    SetEncodingType (Type *encoding_type)
259    {
260        m_encoding_type = encoding_type;
261    }
262
263    uint32_t
264    GetEncodingMask ();
265
266    ClangASTType
267    CreateClangTypedefType (Type *typedef_type, Type *base_type);
268
269    bool
270    IsRealObjCClass();
271
272    bool
273    IsCompleteObjCClass()
274    {
275        return m_flags.is_complete_objc_class;
276    }
277
278    void
279    SetIsCompleteObjCClass(bool is_complete_objc_class)
280    {
281        m_flags.is_complete_objc_class = is_complete_objc_class;
282    }
283
284protected:
285    ConstString m_name;
286    SymbolFile *m_symbol_file;
287    SymbolContextScope *m_context; // The symbol context in which this type is defined
288    Type *m_encoding_type;
289    lldb::user_id_t m_encoding_uid;
290    EncodingDataType m_encoding_uid_type;
291    uint64_t m_byte_size;
292    Declaration m_decl;
293    ClangASTType m_clang_type;
294
295    struct Flags {
296        ResolveState    clang_type_resolve_state : 2;
297        bool            is_complete_objc_class   : 1;
298    } m_flags;
299
300    Type *
301    GetEncodingType ();
302
303    bool
304    ResolveClangType (ResolveState clang_type_resolve_state);
305};
306
307// these classes are used to back the SBType* objects
308
309class TypePair {
310private:
311    ClangASTType clang_type;
312    lldb::TypeSP type_sp;
313
314public:
315    TypePair () : clang_type(), type_sp() {}
316    TypePair (ClangASTType type) :
317    clang_type(type),
318    type_sp()
319    {
320    }
321
322    TypePair (lldb::TypeSP type) :
323    clang_type(),
324    type_sp(type)
325    {
326        clang_type = type_sp->GetClangForwardType();
327    }
328
329    bool
330    IsValid () const
331    {
332        return clang_type.IsValid() || (type_sp.get() != nullptr);
333    }
334
335    explicit operator bool () const
336    {
337        return IsValid();
338    }
339
340    bool
341    operator == (const TypePair& rhs) const
342    {
343        return clang_type == rhs.clang_type &&
344        type_sp.get() == rhs.type_sp.get();
345    }
346
347    bool
348    operator != (const TypePair& rhs) const
349    {
350        return clang_type != rhs.clang_type ||
351        type_sp.get() != rhs.type_sp.get();
352    }
353
354    void
355    Clear ()
356    {
357        clang_type.Clear();
358        type_sp.reset();
359    }
360
361    ConstString
362    GetName () const
363    {
364        if (type_sp)
365            return type_sp->GetName();
366        if (clang_type)
367            return clang_type.GetTypeName();
368        return ConstString ();
369    }
370
371    void
372    SetType (ClangASTType type)
373    {
374        type_sp.reset();
375        clang_type = type;
376    }
377
378    void
379    SetType (lldb::TypeSP type)
380    {
381        type_sp = type;
382        clang_type = type_sp->GetClangForwardType();
383    }
384
385    lldb::TypeSP
386    GetTypeSP () const
387    {
388        return type_sp;
389    }
390
391    ClangASTType
392    GetClangASTType () const
393    {
394        return clang_type;
395    }
396
397    ClangASTType
398    GetPointerType () const
399    {
400        if (type_sp)
401            return type_sp->GetClangLayoutType().GetPointerType();
402        return clang_type.GetPointerType();
403    }
404
405    ClangASTType
406    GetPointeeType () const
407    {
408        if (type_sp)
409            return type_sp->GetClangFullType().GetPointeeType();
410        return clang_type.GetPointeeType();
411    }
412
413    ClangASTType
414    GetReferenceType () const
415    {
416        if (type_sp)
417            return type_sp->GetClangLayoutType().GetLValueReferenceType();
418        return clang_type.GetLValueReferenceType();
419    }
420
421    ClangASTType
422    GetDereferencedType () const
423    {
424        if (type_sp)
425            return type_sp->GetClangFullType().GetNonReferenceType();
426        return clang_type.GetNonReferenceType();
427    }
428
429    ClangASTType
430    GetUnqualifiedType () const
431    {
432        if (type_sp)
433            return type_sp->GetClangLayoutType().GetFullyUnqualifiedType();
434        return clang_type.GetFullyUnqualifiedType();
435    }
436
437    ClangASTType
438    GetCanonicalType () const
439    {
440        if (type_sp)
441            return type_sp->GetClangFullType().GetCanonicalType();
442        return clang_type.GetCanonicalType();
443    }
444
445    clang::ASTContext *
446    GetClangASTContext () const
447    {
448        return clang_type.GetASTContext();
449    }
450};
451
452class TypeImpl
453{
454public:
455
456    TypeImpl();
457
458    ~TypeImpl () {}
459
460    TypeImpl(const TypeImpl& rhs);
461
462    TypeImpl (lldb::TypeSP type_sp);
463
464    TypeImpl (ClangASTType clang_type);
465
466    TypeImpl (lldb::TypeSP type_sp, ClangASTType dynamic);
467
468    TypeImpl (ClangASTType clang_type, ClangASTType dynamic);
469
470    TypeImpl (TypePair pair, ClangASTType dynamic);
471
472    void
473    SetType (lldb::TypeSP type_sp);
474
475    void
476    SetType (ClangASTType clang_type);
477
478    void
479    SetType (lldb::TypeSP type_sp, ClangASTType dynamic);
480
481    void
482    SetType (ClangASTType clang_type, ClangASTType dynamic);
483
484    void
485    SetType (TypePair pair, ClangASTType dynamic);
486
487    TypeImpl&
488    operator = (const TypeImpl& rhs);
489
490    bool
491    operator == (const TypeImpl& rhs) const;
492
493    bool
494    operator != (const TypeImpl& rhs) const;
495
496    bool
497    IsValid() const;
498
499    explicit operator bool () const;
500
501    void Clear();
502
503    ConstString
504    GetName ()  const;
505
506    TypeImpl
507    GetPointerType () const;
508
509    TypeImpl
510    GetPointeeType () const;
511
512    TypeImpl
513    GetReferenceType () const;
514
515    TypeImpl
516    GetDereferencedType () const;
517
518    TypeImpl
519    GetUnqualifiedType() const;
520
521    TypeImpl
522    GetCanonicalType() const;
523
524    ClangASTType
525    GetClangASTType (bool prefer_dynamic);
526
527    clang::ASTContext *
528    GetClangASTContext (bool prefer_dynamic);
529
530    bool
531    GetDescription (lldb_private::Stream &strm,
532                    lldb::DescriptionLevel description_level);
533
534private:
535    TypePair m_static_type;
536    ClangASTType m_dynamic_type;
537};
538
539class TypeListImpl
540{
541public:
542    TypeListImpl() :
543        m_content()
544    {
545    }
546
547    void
548    Append (const lldb::TypeImplSP& type)
549    {
550        m_content.push_back(type);
551    }
552
553    class AppendVisitor
554    {
555    public:
556        AppendVisitor(TypeListImpl &type_list) :
557            m_type_list(type_list)
558        {
559        }
560
561        void
562        operator() (const lldb::TypeImplSP& type)
563        {
564            m_type_list.Append(type);
565        }
566
567    private:
568        TypeListImpl &m_type_list;
569    };
570
571    void
572    Append (const lldb_private::TypeList &type_list);
573
574    lldb::TypeImplSP
575    GetTypeAtIndex(size_t idx)
576    {
577        lldb::TypeImplSP type_sp;
578        if (idx < GetSize())
579            type_sp = m_content[idx];
580        return type_sp;
581    }
582
583    size_t
584    GetSize()
585    {
586        return m_content.size();
587    }
588
589private:
590    std::vector<lldb::TypeImplSP> m_content;
591};
592
593class TypeMemberImpl
594{
595public:
596    TypeMemberImpl () :
597        m_type_impl_sp (),
598        m_bit_offset (0),
599        m_name (),
600        m_bitfield_bit_size (0),
601        m_is_bitfield (false)
602
603    {
604    }
605
606    TypeMemberImpl (const lldb::TypeImplSP &type_impl_sp,
607                    uint64_t bit_offset,
608                    const ConstString &name,
609                    uint32_t bitfield_bit_size = 0,
610                    bool is_bitfield = false) :
611        m_type_impl_sp (type_impl_sp),
612        m_bit_offset (bit_offset),
613        m_name (name),
614        m_bitfield_bit_size (bitfield_bit_size),
615        m_is_bitfield (is_bitfield)
616    {
617    }
618
619    TypeMemberImpl (const lldb::TypeImplSP &type_impl_sp,
620                    uint64_t bit_offset):
621        m_type_impl_sp (type_impl_sp),
622        m_bit_offset (bit_offset),
623        m_name (),
624        m_bitfield_bit_size (0),
625        m_is_bitfield (false)
626    {
627        if (m_type_impl_sp)
628            m_name = m_type_impl_sp->GetName();
629    }
630
631    const lldb::TypeImplSP &
632    GetTypeImpl ()
633    {
634        return m_type_impl_sp;
635    }
636
637    const ConstString &
638    GetName () const
639    {
640        return m_name;
641    }
642
643    uint64_t
644    GetBitOffset () const
645    {
646        return m_bit_offset;
647    }
648
649    uint32_t
650    GetBitfieldBitSize () const
651    {
652        return m_bitfield_bit_size;
653    }
654
655    void
656    SetBitfieldBitSize (uint32_t bitfield_bit_size)
657    {
658        m_bitfield_bit_size = bitfield_bit_size;
659    }
660
661    bool
662    GetIsBitfield () const
663    {
664        return m_is_bitfield;
665    }
666
667    void
668    SetIsBitfield (bool is_bitfield)
669    {
670        m_is_bitfield = is_bitfield;
671    }
672
673protected:
674    lldb::TypeImplSP m_type_impl_sp;
675    uint64_t m_bit_offset;
676    ConstString m_name;
677    uint32_t m_bitfield_bit_size; // Bit size for bitfield members only
678    bool m_is_bitfield;
679};
680
681
682///
683/// Sometimes you can find the name of the type corresponding to an object, but we don't have debug
684/// information for it.  If that is the case, you can return one of these objects, and then if it
685/// has a full type, you can use that, but if not at least you can print the name for informational
686/// purposes.
687///
688
689class TypeAndOrName
690{
691public:
692    TypeAndOrName ();
693    TypeAndOrName (lldb::TypeSP &type_sp);
694    TypeAndOrName (const ClangASTType &clang_type);
695    TypeAndOrName (const char *type_str);
696    TypeAndOrName (const TypeAndOrName &rhs);
697    TypeAndOrName (ConstString &type_const_string);
698
699    TypeAndOrName &
700    operator= (const TypeAndOrName &rhs);
701
702    bool
703    operator==(const TypeAndOrName &other) const;
704
705    bool
706    operator!=(const TypeAndOrName &other) const;
707
708    ConstString GetName () const;
709
710    lldb::TypeSP
711    GetTypeSP () const
712    {
713        return m_type_pair.GetTypeSP();
714    }
715
716    ClangASTType
717    GetClangASTType () const
718    {
719        return m_type_pair.GetClangASTType();
720    }
721
722    void
723    SetName (const ConstString &type_name);
724
725    void
726    SetName (const char *type_name_cstr);
727
728    void
729    SetTypeSP (lldb::TypeSP type_sp);
730
731    void
732    SetClangASTType (ClangASTType clang_type);
733
734    bool
735    IsEmpty () const;
736
737    bool
738    HasName () const;
739
740    bool
741    HasTypeSP () const;
742
743    bool
744    HasClangASTType () const;
745
746    bool
747    HasType () const
748    {
749        return HasTypeSP() || HasClangASTType();
750    }
751
752    void
753    Clear ();
754
755    explicit operator bool ()
756    {
757        return !IsEmpty();
758    }
759
760private:
761    TypePair m_type_pair;
762    ConstString m_type_name;
763};
764
765} // namespace lldb_private
766
767#endif  // liblldb_Type_h_
768
769