1 //===-- AppleObjCRuntimeV1.h ------------------------------------*- C++ -*-===//
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 #ifndef LLDB_SOURCE_PLUGINS_LANGUAGERUNTIME_OBJC_APPLEOBJCRUNTIME_APPLEOBJCRUNTIMEV1_H
10 #define LLDB_SOURCE_PLUGINS_LANGUAGERUNTIME_OBJC_APPLEOBJCRUNTIME_APPLEOBJCRUNTIMEV1_H
11 
12 #include "AppleObjCRuntime.h"
13 #include "lldb/lldb-private.h"
14 
15 #include "Plugins/LanguageRuntime/ObjC/ObjCLanguageRuntime.h"
16 
17 namespace lldb_private {
18 
19 class AppleObjCRuntimeV1 : public AppleObjCRuntime {
20 public:
21   ~AppleObjCRuntimeV1() override = default;
22 
23   // Static Functions
24   static void Initialize();
25 
26   static void Terminate();
27 
28   static lldb_private::LanguageRuntime *
29   CreateInstance(Process *process, lldb::LanguageType language);
30 
31   static lldb_private::ConstString GetPluginNameStatic();
32 
33   static char ID;
34 
isA(const void * ClassID)35   bool isA(const void *ClassID) const override {
36     return ClassID == &ID || AppleObjCRuntime::isA(ClassID);
37   }
38 
classof(const LanguageRuntime * runtime)39   static bool classof(const LanguageRuntime *runtime) {
40     return runtime->isA(&ID);
41   }
42 
43   lldb::addr_t GetTaggedPointerObfuscator();
44 
45   class ClassDescriptorV1 : public ObjCLanguageRuntime::ClassDescriptor {
46   public:
47     ClassDescriptorV1(ValueObject &isa_pointer);
48     ClassDescriptorV1(ObjCISA isa, lldb::ProcessSP process_sp);
49 
50     ~ClassDescriptorV1() override = default;
51 
GetClassName()52     ConstString GetClassName() override { return m_name; }
53 
54     ClassDescriptorSP GetSuperclass() override;
55 
56     ClassDescriptorSP GetMetaclass() const override;
57 
IsValid()58     bool IsValid() override { return m_valid; }
59 
60     // v1 does not support tagged pointers
61     bool GetTaggedPointerInfo(uint64_t *info_bits = nullptr,
62                               uint64_t *value_bits = nullptr,
63                               uint64_t *payload = nullptr) override {
64       return false;
65     }
66 
67     bool GetTaggedPointerInfoSigned(uint64_t *info_bits = nullptr,
68                                     int64_t *value_bits = nullptr,
69                                     uint64_t *payload = nullptr) override {
70       return false;
71     }
72 
GetInstanceSize()73     uint64_t GetInstanceSize() override { return m_instance_size; }
74 
GetISA()75     ObjCISA GetISA() override { return m_isa; }
76 
77     bool
78     Describe(std::function<void(ObjCLanguageRuntime::ObjCISA)> const
79                  &superclass_func,
80              std::function<bool(const char *, const char *)> const
81                  &instance_method_func,
82              std::function<bool(const char *, const char *)> const
83                  &class_method_func,
84              std::function<bool(const char *, const char *, lldb::addr_t,
85                                 uint64_t)> const &ivar_func) const override;
86 
87   protected:
88     void Initialize(ObjCISA isa, lldb::ProcessSP process_sp);
89 
90   private:
91     ConstString m_name;
92     ObjCISA m_isa;
93     ObjCISA m_parent_isa;
94     bool m_valid;
95     lldb::ProcessWP m_process_wp;
96     uint64_t m_instance_size;
97   };
98 
99   // These are generic runtime functions:
100   bool GetDynamicTypeAndAddress(ValueObject &in_value,
101                                 lldb::DynamicValueType use_dynamic,
102                                 TypeAndOrName &class_type_or_name,
103                                 Address &address,
104                                 Value::ValueType &value_type) override;
105 
106   llvm::Expected<std::unique_ptr<UtilityFunction>>
107   CreateObjectChecker(std::string, ExecutionContext &exe_ctx) override;
108 
109   // PluginInterface protocol
110   ConstString GetPluginName() override;
111 
112   uint32_t GetPluginVersion() override;
113 
GetRuntimeVersion()114   ObjCRuntimeVersions GetRuntimeVersion() const override {
115     return ObjCRuntimeVersions::eAppleObjC_V1;
116   }
117 
118   void UpdateISAToDescriptorMapIfNeeded() override;
119 
120   DeclVendor *GetDeclVendor() override;
121 
122 protected:
123   lldb::BreakpointResolverSP
124   CreateExceptionResolver(const lldb::BreakpointSP &bkpt,
125                           bool catch_bp, bool throw_bp) override;
126 
127   class HashTableSignature {
128   public:
129     HashTableSignature() = default;
130 
NeedsUpdate(uint32_t count,uint32_t num_buckets,lldb::addr_t buckets_ptr)131     bool NeedsUpdate(uint32_t count, uint32_t num_buckets,
132                      lldb::addr_t buckets_ptr) {
133       return m_count != count || m_num_buckets != num_buckets ||
134              m_buckets_ptr != buckets_ptr;
135     }
136 
UpdateSignature(uint32_t count,uint32_t num_buckets,lldb::addr_t buckets_ptr)137     void UpdateSignature(uint32_t count, uint32_t num_buckets,
138                          lldb::addr_t buckets_ptr) {
139       m_count = count;
140       m_num_buckets = num_buckets;
141       m_buckets_ptr = buckets_ptr;
142     }
143 
144   protected:
145     uint32_t m_count = 0;
146     uint32_t m_num_buckets = 0;
147     lldb::addr_t m_buckets_ptr = LLDB_INVALID_ADDRESS;
148   };
149 
150   lldb::addr_t GetISAHashTablePointer();
151 
152   HashTableSignature m_hash_signature;
153   lldb::addr_t m_isa_hash_table_ptr;
154   std::unique_ptr<DeclVendor> m_decl_vendor_up;
155 
156 private:
157   AppleObjCRuntimeV1(Process *process);
158 };
159 
160 } // namespace lldb_private
161 
162 #endif // LLDB_SOURCE_PLUGINS_LANGUAGERUNTIME_OBJC_APPLEOBJCRUNTIME_APPLEOBJCRUNTIMEV1_H
163