5#ifndef RUNTIME_VM_DWARF_H_
6#define RUNTIME_VM_DWARF_H_
17#ifdef DART_PRECOMPILER
20class LineNumberProgramWriter;
22struct ScriptIndexPair {
24 typedef const Script*
Key;
25 typedef intptr_t
Value;
26 typedef ScriptIndexPair
Pair;
28 static Key KeyOf(
Pair kv) {
return kv.script_; }
30 static Value ValueOf(
Pair kv) {
return kv.index_; }
33 return String::Handle(
key->url()).Hash();
36 static inline bool IsKeyEqual(
Pair pair,
Key key) {
37 return pair.script_->ptr() ==
key->ptr();
40 ScriptIndexPair(
const Script*
s, intptr_t index) : script_(
s), index_(index) {
45 ScriptIndexPair() : script_(nullptr), index_(-1) {}
49 const Script* script_;
53typedef DirectChainedHashMap<ScriptIndexPair> ScriptIndexMap;
55struct FunctionIndexPair {
57 typedef const Function*
Key;
58 typedef intptr_t
Value;
59 typedef FunctionIndexPair
Pair;
61 static Key KeyOf(
Pair kv) {
return kv.function_; }
63 static Value ValueOf(
Pair kv) {
return kv.index_; }
65 static inline uword Hash(
Key key) {
return key->token_pos().Hash(); }
67 static inline bool IsKeyEqual(
Pair pair,
Key key) {
68 return pair.function_->ptr() ==
key->ptr();
71 FunctionIndexPair(
const Function* f, intptr_t index)
72 : function_(
f), index_(index) {
77 FunctionIndexPair() : function_(nullptr), index_(-1) {}
81 const Function* function_;
85typedef DirectChainedHashMap<FunctionIndexPair> FunctionIndexMap;
89struct DwarfCodeKeyValueTrait {
91 typedef const Code*
Key;
104 Pair& operator=(
const Pair& other) =
default;
110 static Key KeyOf(
Pair kv) {
return kv.code; }
112 static Value ValueOf(
Pair kv) {
return kv.value; }
116 return Utils::WordHash(
key->PayloadStart());
119 static inline bool IsKeyEqual(
Pair pair,
Key key) {
121 return pair.code->ptr() ==
key->ptr();
126using DwarfCodeMap = DirectChainedHashMap<DwarfCodeKeyValueTrait<T>>;
128class DwarfWriteStream :
public ValueObject {
130 DwarfWriteStream() {}
131 virtual ~DwarfWriteStream() {}
133 virtual void sleb128(intptr_t value) = 0;
134 virtual void uleb128(uintptr_t value) = 0;
135 virtual void u1(uint8_t value) = 0;
136 virtual void u2(uint16_t value) = 0;
137 virtual void u4(uint32_t value) = 0;
138 virtual void u8(uint64_t value) = 0;
139 virtual void string(
const char* cstr) = 0;
144 virtual void WritePrefixedLength(
const char* symbol_prefix,
145 std::function<
void()> body) = 0;
147 virtual void OffsetFromSymbol(intptr_t label, intptr_t
offset) = 0;
149 virtual void InitializeAbstractOrigins(intptr_t size) = 0;
150 virtual void RegisterAbstractOrigin(intptr_t index) = 0;
151 virtual void AbstractOrigin(intptr_t index) = 0;
156class Dwarf :
public ZoneAllocated {
158 explicit Dwarf(Zone* zone,
const Trie<const char>* deobfuscation_trie);
160 const ZoneGrowableArray<const Code*>& codes()
const {
return codes_; }
163 void AddCode(
const Code& code, intptr_t label);
165 intptr_t AddFunction(
const Function&
function);
166 intptr_t AddScript(
const Script& script);
167 intptr_t LookupFunction(
const Function&
function);
168 intptr_t LookupScript(
const Script& script);
170 void WriteAbbreviations(DwarfWriteStream* stream);
171 void WriteDebugInfo(DwarfWriteStream* stream);
172 void WriteLineNumberProgram(DwarfWriteStream* stream);
175 friend class LineNumberProgramWriter;
177 static constexpr intptr_t DW_TAG_compile_unit = 0x11;
178 static constexpr intptr_t DW_TAG_inlined_subroutine = 0x1d;
179 static constexpr intptr_t DW_TAG_subprogram = 0x2e;
181 static constexpr intptr_t DW_CHILDREN_no = 0x0;
182 static constexpr intptr_t DW_CHILDREN_yes = 0x1;
184 static constexpr intptr_t DW_AT_sibling = 0x1;
185 static constexpr intptr_t DW_AT_name = 0x3;
186 static constexpr intptr_t DW_AT_stmt_list = 0x10;
187 static constexpr intptr_t DW_AT_low_pc = 0x11;
188 static constexpr intptr_t DW_AT_high_pc = 0x12;
189 static constexpr intptr_t DW_AT_comp_dir = 0x1b;
190 static constexpr intptr_t DW_AT_inline = 0x20;
191 static constexpr intptr_t DW_AT_producer = 0x25;
192 static constexpr intptr_t DW_AT_abstract_origin = 0x31;
193 static constexpr intptr_t DW_AT_artificial = 0x34;
194 static constexpr intptr_t DW_AT_decl_column = 0x39;
195 static constexpr intptr_t DW_AT_decl_file = 0x3a;
196 static constexpr intptr_t DW_AT_decl_line = 0x3b;
197 static constexpr intptr_t DW_AT_call_column = 0x57;
198 static constexpr intptr_t DW_AT_call_file = 0x58;
199 static constexpr intptr_t DW_AT_call_line = 0x59;
201 static constexpr intptr_t DW_FORM_addr = 0x01;
202 static constexpr intptr_t DW_FORM_string = 0x08;
203 static constexpr intptr_t DW_FORM_flag = 0x0c;
204 static constexpr intptr_t DW_FORM_udata = 0x0f;
205 static constexpr intptr_t DW_FORM_ref4 = 0x13;
206 static constexpr intptr_t DW_FORM_ref_udata = 0x15;
207 static constexpr intptr_t DW_FORM_sec_offset = 0x17;
209 static constexpr intptr_t DW_INL_not_inlined = 0x0;
210 static constexpr intptr_t DW_INL_inlined = 0x1;
212 static constexpr intptr_t DW_LNS_copy = 0x1;
213 static constexpr intptr_t DW_LNS_advance_pc = 0x2;
214 static constexpr intptr_t DW_LNS_advance_line = 0x3;
215 static constexpr intptr_t DW_LNS_set_file = 0x4;
216 static constexpr intptr_t DW_LNS_set_column = 0x5;
218 static constexpr intptr_t DW_LNE_end_sequence = 0x01;
219 static constexpr intptr_t DW_LNE_set_address = 0x02;
223 static constexpr intptr_t DW_CFA_offset = 0x80;
224 static constexpr intptr_t DW_CFA_val_offset = 0x14;
225 static constexpr intptr_t DW_CFA_def_cfa = 0x0c;
229 kCompilationUnit = 1,
235 void WriteAbstractFunctions(DwarfWriteStream* stream);
236 void WriteConcreteFunctions(DwarfWriteStream* stream);
237 InliningNode* ExpandInliningTree(
const Code& code);
238 void WriteInliningNode(DwarfWriteStream* stream,
241 const Script& parent_script);
243 void WriteSyntheticLineNumberProgram(LineNumberProgramWriter* writer);
244 void WriteLineNumberProgramFromCodeSourceMaps(
245 LineNumberProgramWriter* writer);
248 const Trie<const char>*
const deobfuscation_trie_;
249 ZoneGrowableArray<const Code*> codes_;
250 DwarfCodeMap<intptr_t> code_to_label_;
251 ZoneGrowableArray<const Function*> functions_;
252 FunctionIndexMap function_to_index_;
253 ZoneGrowableArray<const Script*> scripts_;
254 ScriptIndexMap script_to_index_;
#define DEBUG_ASSERT(cond)
Dart_NativeFunction function