Commit | Line | Data |
---|---|---|
3666a048 | 1 | /* Copyright (C) 2006-2021 Free Software Foundation, Inc. |
f49ff000 YQ |
2 | |
3 | This file is part of GDB. | |
4 | ||
5 | This program is free software; you can redistribute it and/or modify | |
6 | it under the terms of the GNU General Public License as published by | |
7 | the Free Software Foundation; either version 3 of the License, or | |
8 | (at your option) any later version. | |
9 | ||
10 | This program is distributed in the hope that it will be useful, | |
11 | but WITHOUT ANY WARRANTY; without even the implied warranty of | |
12 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
13 | GNU General Public License for more details. | |
14 | ||
15 | You should have received a copy of the GNU General Public License | |
16 | along with this program. If not, see <http://www.gnu.org/licenses/>. */ | |
17 | ||
1a5c2598 TT |
18 | #ifndef COMMON_TDESC_H |
19 | #define COMMON_TDESC_H | |
f49ff000 YQ |
20 | |
21 | struct tdesc_feature; | |
22 | struct tdesc_type; | |
d4a0e8b5 SM |
23 | struct tdesc_type_builtin; |
24 | struct tdesc_type_vector; | |
25 | struct tdesc_type_with_fields; | |
f49ff000 YQ |
26 | struct tdesc_reg; |
27 | struct target_desc; | |
28 | ||
ea3e7d71 AH |
29 | /* The interface to visit different elements of target description. */ |
30 | ||
31 | class tdesc_element_visitor | |
32 | { | |
33 | public: | |
34 | virtual void visit_pre (const target_desc *e) | |
35 | {} | |
36 | ||
37 | virtual void visit_post (const target_desc *e) | |
38 | {} | |
39 | ||
40 | virtual void visit_pre (const tdesc_feature *e) | |
41 | {} | |
42 | ||
43 | virtual void visit_post (const tdesc_feature *e) | |
44 | {} | |
45 | ||
46 | virtual void visit (const tdesc_type_builtin *e) | |
47 | {} | |
48 | ||
49 | virtual void visit (const tdesc_type_vector *e) | |
50 | {} | |
51 | ||
52 | virtual void visit (const tdesc_type_with_fields *e) | |
53 | {} | |
54 | ||
55 | virtual void visit (const tdesc_reg *e) | |
56 | {} | |
57 | }; | |
58 | ||
59 | class tdesc_element | |
60 | { | |
61 | public: | |
62 | virtual void accept (tdesc_element_visitor &v) const = 0; | |
63 | }; | |
64 | ||
65 | /* An individual register from a target description. */ | |
66 | ||
67 | struct tdesc_reg : tdesc_element | |
68 | { | |
69 | tdesc_reg (struct tdesc_feature *feature, const std::string &name_, | |
70 | int regnum, int save_restore_, const char *group_, | |
71 | int bitsize_, const char *type_); | |
72 | ||
73 | virtual ~tdesc_reg () = default; | |
74 | ||
75 | DISABLE_COPY_AND_ASSIGN (tdesc_reg); | |
76 | ||
77 | /* The name of this register. In standard features, it may be | |
78 | recognized by the architecture support code, or it may be purely | |
79 | for the user. */ | |
80 | std::string name; | |
81 | ||
82 | /* The register number used by this target to refer to this | |
83 | register. This is used for remote p/P packets and to determine | |
84 | the ordering of registers in the remote g/G packets. */ | |
85 | long target_regnum; | |
86 | ||
87 | /* If this flag is set, GDB should save and restore this register | |
88 | around calls to an inferior function. */ | |
89 | int save_restore; | |
90 | ||
91 | /* The name of the register group containing this register, or empty | |
92 | if the group should be automatically determined from the | |
93 | register's type. If this is "general", "float", or "vector", the | |
94 | corresponding "info" command should display this register's | |
95 | value. It can be an arbitrary string, but should be limited to | |
96 | alphanumeric characters and internal hyphens. Currently other | |
97 | strings are ignored (treated as empty). */ | |
98 | std::string group; | |
99 | ||
100 | /* The size of the register, in bits. */ | |
101 | int bitsize; | |
102 | ||
103 | /* The type of the register. This string corresponds to either | |
104 | a named type from the target description or a predefined | |
105 | type from GDB. */ | |
106 | std::string type; | |
107 | ||
108 | /* The target-described type corresponding to TYPE, if found. */ | |
109 | struct tdesc_type *tdesc_type; | |
110 | ||
111 | void accept (tdesc_element_visitor &v) const override | |
112 | { | |
113 | v.visit (this); | |
114 | } | |
115 | ||
116 | bool operator== (const tdesc_reg &other) const | |
117 | { | |
118 | return (name == other.name | |
119 | && target_regnum == other.target_regnum | |
120 | && save_restore == other.save_restore | |
121 | && bitsize == other.bitsize | |
122 | && group == other.group | |
123 | && type == other.type); | |
124 | } | |
125 | ||
126 | bool operator!= (const tdesc_reg &other) const | |
127 | { | |
128 | return !(*this == other); | |
129 | } | |
130 | }; | |
131 | ||
132 | typedef std::unique_ptr<tdesc_reg> tdesc_reg_up; | |
133 | ||
fbf42f4e AB |
134 | /* Declaration of a structure that holds information about one |
135 | "compatibility" entry within a target description. */ | |
136 | ||
137 | struct tdesc_compatible_info; | |
138 | ||
139 | /* A pointer to a single piece of compatibility information. */ | |
140 | ||
141 | typedef std::unique_ptr<tdesc_compatible_info> tdesc_compatible_info_up; | |
142 | ||
143 | /* Return a vector of compatibility information pointers from the target | |
144 | description TARGET_DESC. */ | |
145 | ||
146 | const std::vector<tdesc_compatible_info_up> &tdesc_compatible_info_list | |
147 | (const target_desc *target_desc); | |
148 | ||
149 | /* Return the architecture name from a compatibility information | |
150 | COMPATIBLE. */ | |
151 | ||
152 | const char *tdesc_compatible_info_arch_name | |
153 | (const tdesc_compatible_info_up &compatible); | |
154 | ||
82ec9bc7 AH |
155 | enum tdesc_type_kind |
156 | { | |
157 | /* Predefined types. */ | |
158 | TDESC_TYPE_BOOL, | |
159 | TDESC_TYPE_INT8, | |
160 | TDESC_TYPE_INT16, | |
161 | TDESC_TYPE_INT32, | |
162 | TDESC_TYPE_INT64, | |
163 | TDESC_TYPE_INT128, | |
164 | TDESC_TYPE_UINT8, | |
165 | TDESC_TYPE_UINT16, | |
166 | TDESC_TYPE_UINT32, | |
167 | TDESC_TYPE_UINT64, | |
168 | TDESC_TYPE_UINT128, | |
169 | TDESC_TYPE_CODE_PTR, | |
170 | TDESC_TYPE_DATA_PTR, | |
a6d0f249 | 171 | TDESC_TYPE_IEEE_HALF, |
82ec9bc7 AH |
172 | TDESC_TYPE_IEEE_SINGLE, |
173 | TDESC_TYPE_IEEE_DOUBLE, | |
174 | TDESC_TYPE_ARM_FPA_EXT, | |
175 | TDESC_TYPE_I387_EXT, | |
2a67f09d | 176 | TDESC_TYPE_BFLOAT16, |
82ec9bc7 AH |
177 | |
178 | /* Types defined by a target feature. */ | |
179 | TDESC_TYPE_VECTOR, | |
180 | TDESC_TYPE_STRUCT, | |
181 | TDESC_TYPE_UNION, | |
182 | TDESC_TYPE_FLAGS, | |
183 | TDESC_TYPE_ENUM | |
184 | }; | |
185 | ||
186 | struct tdesc_type : tdesc_element | |
187 | { | |
188 | tdesc_type (const std::string &name_, enum tdesc_type_kind kind_) | |
189 | : name (name_), kind (kind_) | |
190 | {} | |
191 | ||
192 | virtual ~tdesc_type () = default; | |
193 | ||
194 | DISABLE_COPY_AND_ASSIGN (tdesc_type); | |
195 | ||
196 | /* The name of this type. */ | |
197 | std::string name; | |
198 | ||
199 | /* Identify the kind of this type. */ | |
200 | enum tdesc_type_kind kind; | |
201 | ||
202 | bool operator== (const tdesc_type &other) const | |
203 | { | |
204 | return name == other.name && kind == other.kind; | |
205 | } | |
206 | ||
207 | bool operator!= (const tdesc_type &other) const | |
208 | { | |
209 | return !(*this == other); | |
210 | } | |
211 | }; | |
212 | ||
213 | typedef std::unique_ptr<tdesc_type> tdesc_type_up; | |
214 | ||
eee8a18d AH |
215 | struct tdesc_type_builtin : tdesc_type |
216 | { | |
217 | tdesc_type_builtin (const std::string &name, enum tdesc_type_kind kind) | |
218 | : tdesc_type (name, kind) | |
219 | {} | |
220 | ||
221 | void accept (tdesc_element_visitor &v) const override | |
222 | { | |
223 | v.visit (this); | |
224 | } | |
225 | }; | |
226 | ||
227 | /* tdesc_type for vector types. */ | |
228 | ||
229 | struct tdesc_type_vector : tdesc_type | |
230 | { | |
231 | tdesc_type_vector (const std::string &name, tdesc_type *element_type_, | |
232 | int count_) | |
233 | : tdesc_type (name, TDESC_TYPE_VECTOR), | |
234 | element_type (element_type_), count (count_) | |
235 | {} | |
236 | ||
237 | void accept (tdesc_element_visitor &v) const override | |
238 | { | |
239 | v.visit (this); | |
240 | } | |
241 | ||
242 | struct tdesc_type *element_type; | |
243 | int count; | |
244 | }; | |
245 | ||
246 | /* A named type from a target description. */ | |
247 | ||
248 | struct tdesc_type_field | |
249 | { | |
250 | tdesc_type_field (const std::string &name_, tdesc_type *type_, | |
251 | int start_, int end_) | |
252 | : name (name_), type (type_), start (start_), end (end_) | |
253 | {} | |
254 | ||
255 | std::string name; | |
256 | struct tdesc_type *type; | |
257 | /* For non-enum-values, either both are -1 (non-bitfield), or both are | |
258 | not -1 (bitfield). For enum values, start is the value (which could be | |
259 | -1), end is -1. */ | |
260 | int start, end; | |
261 | }; | |
262 | ||
263 | /* tdesc_type for struct, union, flags, and enum types. */ | |
264 | ||
265 | struct tdesc_type_with_fields : tdesc_type | |
266 | { | |
267 | tdesc_type_with_fields (const std::string &name, tdesc_type_kind kind, | |
268 | int size_ = 0) | |
269 | : tdesc_type (name, kind), size (size_) | |
270 | {} | |
271 | ||
272 | void accept (tdesc_element_visitor &v) const override | |
273 | { | |
274 | v.visit (this); | |
275 | } | |
276 | ||
277 | std::vector<tdesc_type_field> fields; | |
278 | int size; | |
279 | }; | |
280 | ||
82ec9bc7 AH |
281 | /* A feature from a target description. Each feature is a collection |
282 | of other elements, e.g. registers and types. */ | |
283 | ||
284 | struct tdesc_feature : tdesc_element | |
285 | { | |
286 | tdesc_feature (const std::string &name_) | |
287 | : name (name_) | |
288 | {} | |
289 | ||
290 | virtual ~tdesc_feature () = default; | |
291 | ||
292 | DISABLE_COPY_AND_ASSIGN (tdesc_feature); | |
293 | ||
294 | /* The name of this feature. It may be recognized by the architecture | |
295 | support code. */ | |
296 | std::string name; | |
297 | ||
298 | /* The registers associated with this feature. */ | |
299 | std::vector<tdesc_reg_up> registers; | |
300 | ||
301 | /* The types associated with this feature. */ | |
302 | std::vector<tdesc_type_up> types; | |
303 | ||
304 | void accept (tdesc_element_visitor &v) const override; | |
305 | ||
306 | bool operator== (const tdesc_feature &other) const; | |
307 | ||
308 | bool operator!= (const tdesc_feature &other) const | |
309 | { | |
310 | return !(*this == other); | |
311 | } | |
312 | }; | |
313 | ||
314 | typedef std::unique_ptr<tdesc_feature> tdesc_feature_up; | |
315 | ||
0e267416 AB |
316 | /* A deleter adapter for a target_desc. There are different |
317 | implementations of this deleter class in gdb and gdbserver because even | |
318 | though the target_desc name is shared between the two projects, the | |
319 | actual implementations of target_desc are completely different. */ | |
320 | ||
321 | struct target_desc_deleter | |
322 | { | |
323 | void operator() (struct target_desc *desc) const; | |
324 | }; | |
325 | ||
326 | /* A unique pointer specialization that holds a target_desc. */ | |
327 | ||
328 | typedef std::unique_ptr<target_desc, target_desc_deleter> target_desc_up; | |
329 | ||
5f035c07 | 330 | /* Allocate a new target_desc. */ |
51a948fd | 331 | target_desc_up allocate_target_description (void); |
5f035c07 YQ |
332 | |
333 | /* Set TARGET_DESC's architecture by NAME. */ | |
334 | void set_tdesc_architecture (target_desc *target_desc, | |
335 | const char *name); | |
336 | ||
d278f585 AH |
337 | /* Return the architecture associated with this target description as a string, |
338 | or NULL if no architecture was specified. */ | |
339 | const char *tdesc_architecture_name (const struct target_desc *target_desc); | |
340 | ||
5f035c07 YQ |
341 | /* Set TARGET_DESC's osabi by NAME. */ |
342 | void set_tdesc_osabi (target_desc *target_desc, const char *name); | |
343 | ||
d278f585 AH |
344 | /* Return the osabi associated with this target description as a string, |
345 | or NULL if no osabi was specified. */ | |
346 | const char *tdesc_osabi_name (const struct target_desc *target_desc); | |
347 | ||
f49ff000 YQ |
348 | /* Return the type associated with ID in the context of FEATURE, or |
349 | NULL if none. */ | |
350 | struct tdesc_type *tdesc_named_type (const struct tdesc_feature *feature, | |
351 | const char *id); | |
352 | ||
353 | /* Return the created feature named NAME in target description TDESC. */ | |
354 | struct tdesc_feature *tdesc_create_feature (struct target_desc *tdesc, | |
3b74854b | 355 | const char *name); |
f49ff000 YQ |
356 | |
357 | /* Return the created vector tdesc_type named NAME in FEATURE. */ | |
358 | struct tdesc_type *tdesc_create_vector (struct tdesc_feature *feature, | |
359 | const char *name, | |
360 | struct tdesc_type *field_type, | |
361 | int count); | |
362 | ||
363 | /* Return the created struct tdesc_type named NAME in FEATURE. */ | |
d4a0e8b5 SM |
364 | tdesc_type_with_fields *tdesc_create_struct (struct tdesc_feature *feature, |
365 | const char *name); | |
f49ff000 YQ |
366 | |
367 | /* Return the created union tdesc_type named NAME in FEATURE. */ | |
d4a0e8b5 SM |
368 | tdesc_type_with_fields *tdesc_create_union (struct tdesc_feature *feature, |
369 | const char *name); | |
f49ff000 YQ |
370 | |
371 | /* Return the created flags tdesc_type named NAME in FEATURE. */ | |
d4a0e8b5 SM |
372 | tdesc_type_with_fields *tdesc_create_flags (struct tdesc_feature *feature, |
373 | const char *name, | |
374 | int size); | |
f49ff000 | 375 | |
eee8a18d AH |
376 | /* Return the created enum tdesc_type named NAME in FEATURE. */ |
377 | tdesc_type_with_fields *tdesc_create_enum (struct tdesc_feature *feature, | |
378 | const char *name, | |
379 | int size); | |
380 | ||
f49ff000 YQ |
381 | /* Add a new field to TYPE. FIELD_NAME is its name, and FIELD_TYPE is |
382 | its type. */ | |
d4a0e8b5 | 383 | void tdesc_add_field (tdesc_type_with_fields *type, const char *field_name, |
f49ff000 YQ |
384 | struct tdesc_type *field_type); |
385 | ||
eee8a18d AH |
386 | /* Add a new bitfield to TYPE, with range START to END. FIELD_NAME is its name, |
387 | and FIELD_TYPE is its type. */ | |
388 | void tdesc_add_typed_bitfield (tdesc_type_with_fields *type, | |
389 | const char *field_name, | |
390 | int start, int end, | |
391 | struct tdesc_type *field_type); | |
392 | ||
f49ff000 YQ |
393 | /* Set the total length of TYPE. Structs which contain bitfields may |
394 | omit the reserved bits, so the end of the last field may not | |
395 | suffice. */ | |
d4a0e8b5 | 396 | void tdesc_set_struct_size (tdesc_type_with_fields *type, int size); |
f49ff000 YQ |
397 | |
398 | /* Add a new untyped bitfield to TYPE. | |
399 | Untyped bitfields become either uint32 or uint64 depending on the size | |
400 | of the underlying type. */ | |
d4a0e8b5 | 401 | void tdesc_add_bitfield (tdesc_type_with_fields *type, const char *field_name, |
f49ff000 YQ |
402 | int start, int end); |
403 | ||
404 | /* A flag is just a typed(bool) single-bit bitfield. | |
405 | This function is kept to minimize changes in generated files. */ | |
d4a0e8b5 | 406 | void tdesc_add_flag (tdesc_type_with_fields *type, int start, |
f49ff000 YQ |
407 | const char *flag_name); |
408 | ||
eee8a18d AH |
409 | /* Add field with VALUE and NAME to the enum TYPE. */ |
410 | void tdesc_add_enum_value (tdesc_type_with_fields *type, int value, | |
411 | const char *name); | |
412 | ||
f49ff000 YQ |
413 | /* Create a register in feature FEATURE. */ |
414 | void tdesc_create_reg (struct tdesc_feature *feature, const char *name, | |
415 | int regnum, int save_restore, const char *group, | |
416 | int bitsize, const char *type); | |
417 | ||
e98577a9 AH |
418 | /* Return the tdesc in string XML format. */ |
419 | ||
420 | const char *tdesc_get_features_xml (const target_desc *tdesc); | |
421 | ||
422 | /* Print target description as xml. */ | |
423 | ||
424 | class print_xml_feature : public tdesc_element_visitor | |
425 | { | |
426 | public: | |
427 | print_xml_feature (std::string *buffer_) | |
caa7fd04 AB |
428 | : m_buffer (buffer_), |
429 | m_depth (0) | |
e98577a9 AH |
430 | {} |
431 | ||
432 | void visit_pre (const target_desc *e) override; | |
433 | void visit_post (const target_desc *e) override; | |
434 | void visit_pre (const tdesc_feature *e) override; | |
435 | void visit_post (const tdesc_feature *e) override; | |
436 | void visit (const tdesc_type_builtin *type) override; | |
437 | void visit (const tdesc_type_vector *type) override; | |
438 | void visit (const tdesc_type_with_fields *type) override; | |
439 | void visit (const tdesc_reg *reg) override; | |
440 | ||
441 | private: | |
caa7fd04 AB |
442 | |
443 | /* Called with a positive value of ADJUST when we move inside an element, | |
444 | for example inside <target>, and with a negative value when we leave | |
445 | the element. In this class this function does nothing, but a | |
446 | sub-class can override this to track the current level of nesting. */ | |
447 | void indent (int adjust) | |
448 | { | |
449 | m_depth += (adjust * 2); | |
450 | } | |
451 | ||
452 | /* Functions to add lines to the output buffer M_BUFFER. Each of these | |
453 | functions appends a newline, so don't include one in the strings being | |
454 | passed. */ | |
455 | void add_line (const std::string &str); | |
6db3031e | 456 | void add_line (const char *fmt, ...) ATTRIBUTE_PRINTF (2, 3); |
caa7fd04 AB |
457 | |
458 | /* The buffer we are writing too. */ | |
e98577a9 | 459 | std::string *m_buffer; |
caa7fd04 AB |
460 | |
461 | /* The current indentation depth. */ | |
462 | int m_depth; | |
e98577a9 AH |
463 | }; |
464 | ||
1a5c2598 | 465 | #endif /* COMMON_TDESC_H */ |