headers/bsd: Add sys/queue.h.
[haiku.git] / src / kits / debugger / dwarf / AttributeClasses.cpp
blob47123d2b897778edac030fe87979e23b6420e0c6
1 /*
2 * Copyright 2009, Ingo Weinhold, ingo_weinhold@gmx.de.
3 * Copyright 2013-2014, Rene Gollent, rene@gollent.com.
4 * Distributed under the terms of the MIT License.
5 */
7 #include "AttributeClasses.h"
8 #include "Dwarf.h"
11 enum {
12 AC_ADDRESS = 1 << (ATTRIBUTE_CLASS_ADDRESS - 1),
13 AC_BLOCK = 1 << (ATTRIBUTE_CLASS_BLOCK - 1),
14 AC_CONSTANT = 1 << (ATTRIBUTE_CLASS_CONSTANT - 1),
15 AC_FLAG = 1 << (ATTRIBUTE_CLASS_FLAG - 1),
16 AC_LINEPTR = 1 << (ATTRIBUTE_CLASS_LINEPTR - 1),
17 AC_LOCLISTPTR = 1 << (ATTRIBUTE_CLASS_LOCLISTPTR - 1),
18 AC_MACPTR = 1 << (ATTRIBUTE_CLASS_MACPTR - 1),
19 AC_RANGELISTPTR = 1 << (ATTRIBUTE_CLASS_RANGELISTPTR - 1),
20 AC_REFERENCE = 1 << (ATTRIBUTE_CLASS_REFERENCE - 1),
21 AC_STRING = 1 << (ATTRIBUTE_CLASS_STRING - 1)
25 struct attribute_info_entry {
26 const char* name;
27 uint16 value;
28 uint16 classes;
31 struct attribute_name_info_entry {
32 const char* name;
33 DebugInfoEntrySetter setter;
34 uint16 value;
35 uint16 classes;
39 #undef ENTRY
40 #define ENTRY(name) "DW_AT_" #name, &DebugInfoEntry::AddAttribute_##name, \
41 DW_AT_##name
43 static const attribute_name_info_entry kAttributeNameInfos[] = {
44 { ENTRY(sibling), AC_REFERENCE },
45 { ENTRY(location), AC_BLOCK | AC_LOCLISTPTR },
46 { ENTRY(name), AC_STRING },
47 { ENTRY(ordering), AC_CONSTANT },
48 { ENTRY(byte_size), AC_BLOCK | AC_CONSTANT | AC_REFERENCE },
49 { ENTRY(bit_offset), AC_BLOCK | AC_CONSTANT | AC_REFERENCE },
50 { ENTRY(bit_size), AC_BLOCK | AC_CONSTANT | AC_REFERENCE },
51 { ENTRY(stmt_list), AC_LINEPTR },
52 { ENTRY(low_pc), AC_ADDRESS | AC_CONSTANT | AC_REFERENCE },
53 { ENTRY(high_pc), AC_ADDRESS | AC_CONSTANT | AC_REFERENCE },
54 { ENTRY(language), AC_CONSTANT },
55 { ENTRY(discr), AC_REFERENCE },
56 { ENTRY(discr_value), AC_CONSTANT },
57 { ENTRY(visibility), AC_CONSTANT },
58 { ENTRY(import), AC_REFERENCE },
59 { ENTRY(string_length), AC_BLOCK | AC_LOCLISTPTR },
60 { ENTRY(common_reference), AC_REFERENCE },
61 { ENTRY(comp_dir), AC_STRING },
62 { ENTRY(const_value), AC_BLOCK | AC_CONSTANT | AC_STRING },
63 { ENTRY(containing_type), AC_REFERENCE },
64 { ENTRY(default_value), AC_REFERENCE },
65 { ENTRY(inline), AC_CONSTANT },
66 { ENTRY(is_optional), AC_FLAG },
67 { ENTRY(lower_bound), AC_BLOCK | AC_CONSTANT | AC_REFERENCE },
68 { ENTRY(producer), AC_STRING },
69 { ENTRY(prototyped), AC_FLAG },
70 { ENTRY(return_addr), AC_BLOCK | AC_LOCLISTPTR },
71 { ENTRY(start_scope), AC_CONSTANT },
72 { ENTRY(bit_stride), AC_BLOCK | AC_CONSTANT | AC_REFERENCE },
73 { ENTRY(upper_bound), AC_BLOCK | AC_CONSTANT | AC_REFERENCE },
74 { ENTRY(abstract_origin), AC_REFERENCE },
75 { ENTRY(accessibility), AC_CONSTANT },
76 { ENTRY(address_class), AC_CONSTANT },
77 { ENTRY(artificial), AC_FLAG },
78 { ENTRY(base_types), AC_REFERENCE },
79 { ENTRY(calling_convention), AC_CONSTANT },
80 { ENTRY(count), AC_BLOCK | AC_CONSTANT | AC_REFERENCE },
81 { ENTRY(data_member_location), AC_BLOCK | AC_CONSTANT | AC_LOCLISTPTR },
82 { ENTRY(decl_column), AC_CONSTANT },
83 { ENTRY(decl_file), AC_CONSTANT },
84 { ENTRY(decl_line), AC_CONSTANT },
85 { ENTRY(declaration), AC_FLAG },
86 { ENTRY(discr_list), AC_BLOCK },
87 { ENTRY(encoding), AC_CONSTANT },
88 { ENTRY(external), AC_FLAG },
89 { ENTRY(frame_base), AC_BLOCK | AC_LOCLISTPTR },
90 { ENTRY(friend), AC_REFERENCE },
91 { ENTRY(identifier_case), AC_CONSTANT },
92 { ENTRY(macro_info), AC_MACPTR },
93 { ENTRY(namelist_item), AC_BLOCK | AC_REFERENCE },
94 { ENTRY(priority), AC_REFERENCE },
95 { ENTRY(segment), AC_BLOCK | AC_LOCLISTPTR },
96 { ENTRY(specification), AC_REFERENCE },
97 { ENTRY(static_link), AC_BLOCK | AC_LOCLISTPTR },
98 { ENTRY(type), AC_REFERENCE },
99 { ENTRY(use_location), AC_BLOCK | AC_LOCLISTPTR },
100 { ENTRY(variable_parameter), AC_FLAG },
101 { ENTRY(virtuality), AC_CONSTANT },
102 { ENTRY(vtable_elem_location), AC_BLOCK | AC_LOCLISTPTR },
103 { ENTRY(allocated), AC_BLOCK | AC_CONSTANT | AC_REFERENCE },
104 { ENTRY(associated), AC_BLOCK | AC_CONSTANT | AC_REFERENCE },
105 { ENTRY(data_location), AC_BLOCK },
106 { ENTRY(byte_stride), AC_BLOCK | AC_CONSTANT | AC_REFERENCE },
107 { ENTRY(entry_pc), AC_ADDRESS },
108 { ENTRY(use_UTF8), AC_FLAG },
109 { ENTRY(extension), AC_REFERENCE },
110 { ENTRY(ranges), AC_RANGELISTPTR },
111 { ENTRY(trampoline), AC_ADDRESS | AC_FLAG | AC_REFERENCE
112 | AC_STRING },
113 { ENTRY(call_column), AC_CONSTANT },
114 { ENTRY(call_file), AC_CONSTANT },
115 { ENTRY(call_line), AC_CONSTANT },
116 { ENTRY(description), AC_STRING },
117 { ENTRY(binary_scale), AC_CONSTANT },
118 { ENTRY(decimal_scale), AC_CONSTANT },
119 { ENTRY(small), AC_REFERENCE },
120 { ENTRY(decimal_sign), AC_CONSTANT },
121 { ENTRY(digit_count), AC_CONSTANT },
122 { ENTRY(picture_string), AC_STRING },
123 { ENTRY(mutable), AC_FLAG },
124 { ENTRY(threads_scaled), AC_FLAG },
125 { ENTRY(explicit), AC_FLAG },
126 { ENTRY(object_pointer), AC_REFERENCE },
127 { ENTRY(endianity), AC_CONSTANT },
128 { ENTRY(elemental), AC_FLAG },
129 { ENTRY(pure), AC_FLAG },
130 { ENTRY(recursive), AC_FLAG },
131 { ENTRY(signature), AC_REFERENCE },
132 { ENTRY(main_subprogram), AC_FLAG },
133 { ENTRY(data_bit_offset), AC_CONSTANT },
134 { ENTRY(const_expr), AC_FLAG },
135 { ENTRY(enum_class), AC_FLAG },
136 { ENTRY(linkage_name), AC_STRING },
137 { ENTRY(call_site_value), AC_BLOCK },
138 { ENTRY(call_site_data_value), AC_BLOCK },
139 { ENTRY(call_site_target), AC_BLOCK },
140 { ENTRY(call_site_target_clobbered),
141 AC_BLOCK },
142 { ENTRY(tail_call), AC_FLAG },
143 { ENTRY(all_tail_call_sites), AC_FLAG },
144 { ENTRY(all_call_sites), AC_FLAG },
145 { ENTRY(all_source_call_sites), AC_FLAG },
150 static const uint32 kAttributeNameInfoCount = DW_AT_linkage_name + 9;
151 static attribute_name_info_entry sAttributeNameInfos[kAttributeNameInfoCount];
154 #undef ENTRY
155 #define ENTRY(name) "DW_FORM_" #name, DW_FORM_##name
157 static const attribute_info_entry kAttributeFormInfos[] = {
158 { ENTRY(addr), AC_ADDRESS },
159 { ENTRY(block2), AC_BLOCK },
160 { ENTRY(block4), AC_BLOCK },
161 { ENTRY(data2), AC_CONSTANT },
162 { ENTRY(data4), AC_CONSTANT | AC_LINEPTR | AC_LOCLISTPTR
163 | AC_MACPTR | AC_RANGELISTPTR },
164 { ENTRY(data8), AC_CONSTANT | AC_LINEPTR | AC_LOCLISTPTR
165 | AC_MACPTR | AC_RANGELISTPTR },
166 { ENTRY(string), AC_STRING },
167 { ENTRY(block), AC_BLOCK },
168 { ENTRY(block1), AC_BLOCK },
169 { ENTRY(data1), AC_CONSTANT },
170 { ENTRY(flag), AC_FLAG },
171 { ENTRY(sdata), AC_CONSTANT },
172 { ENTRY(strp), AC_STRING },
173 { ENTRY(udata), AC_CONSTANT },
174 { ENTRY(ref_addr), AC_REFERENCE },
175 { ENTRY(ref1), AC_REFERENCE },
176 { ENTRY(ref2), AC_REFERENCE },
177 { ENTRY(ref4), AC_REFERENCE },
178 { ENTRY(ref8), AC_REFERENCE },
179 { ENTRY(ref_udata), AC_REFERENCE },
180 { ENTRY(indirect), AC_REFERENCE },
181 { ENTRY(sec_offset), AC_LINEPTR | AC_LOCLISTPTR | AC_MACPTR
182 | AC_RANGELISTPTR },
183 { ENTRY(exprloc), AC_BLOCK },
184 { ENTRY(flag_present), AC_FLAG },
185 { ENTRY(ref_sig8), AC_REFERENCE },
189 static const uint32 kAttributeFormInfoCount = DW_FORM_ref_sig8 + 1;
190 static attribute_info_entry sAttributeFormInfos[kAttributeFormInfoCount];
192 static struct InitAttributeInfos {
193 InitAttributeInfos()
195 for (uint32 i = 0; kAttributeNameInfos[i].name != NULL; i++) {
196 const attribute_name_info_entry& entry = kAttributeNameInfos[i];
197 if (entry.value <= DW_AT_linkage_name)
198 sAttributeNameInfos[entry.value] = entry;
199 else {
200 sAttributeNameInfos[DW_AT_linkage_name + 1
201 + (entry.value - DW_AT_call_site_value)] = entry;
205 for (uint32 i = 0; kAttributeFormInfos[i].name != NULL; i++) {
206 const attribute_info_entry& entry = kAttributeFormInfos[i];
207 sAttributeFormInfos[entry.value] = entry;
210 } sInitAttributeInfos;
213 uint16
214 get_attribute_name_classes(uint32 name)
216 if (name < DW_AT_linkage_name)
217 return sAttributeNameInfos[name].classes;
218 else if (name >= DW_AT_call_site_value
219 && name <= DW_AT_all_source_call_sites) {
220 return sAttributeNameInfos[DW_AT_linkage_name + 1
221 + (name - DW_AT_call_site_value)].classes;
224 return 0;
228 uint16
229 get_attribute_form_classes(uint32 form)
231 return form < kAttributeFormInfoCount
232 ? sAttributeFormInfos[form].classes : 0;
236 uint8
237 get_attribute_class(uint32 name, uint32 form)
239 uint16 classes = get_attribute_name_classes(name)
240 & get_attribute_form_classes(form);
242 int clazz = 0;
243 while (classes != 0) {
244 classes >>= 1;
245 clazz++;
248 return clazz;
252 const char*
253 get_attribute_name_name(uint32 name)
255 if (name < DW_AT_linkage_name)
256 return sAttributeNameInfos[name].name;
257 else if (name >= DW_AT_call_site_value
258 && name <= DW_AT_all_source_call_sites) {
259 return sAttributeNameInfos[DW_AT_linkage_name + 1 +
260 (name - DW_AT_call_site_value)].name;
263 return NULL;
267 const char*
268 get_attribute_form_name(uint32 form)
270 return form < kAttributeFormInfoCount
271 ? sAttributeFormInfos[form].name : NULL;
275 DebugInfoEntrySetter
276 get_attribute_name_setter(uint32 name)
278 return (name < kAttributeNameInfoCount)
279 ? sAttributeNameInfos[name].setter : NULL;