Remove path name from test case
[binutils-gdb.git] / gdb / amdgpu-tdep.c
1 /* Target-dependent code for the AMDGPU architectures.
2
3 Copyright (C) 2019-2023 Free Software Foundation, Inc.
4
5 This file is part of GDB.
6
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 3 of the License, or
10 (at your option) any later version.
11
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
16
17 You should have received a copy of the GNU General Public License
18 along with this program. If not, see <http://www.gnu.org/licenses/>. */
19
20 #include "defs.h"
21
22 #include "amd-dbgapi-target.h"
23 #include "amdgpu-tdep.h"
24 #include "arch-utils.h"
25 #include "disasm.h"
26 #include "dwarf2/frame.h"
27 #include "frame-unwind.h"
28 #include "gdbarch.h"
29 #include "gdbsupport/selftest.h"
30 #include "gdbtypes.h"
31 #include "inferior.h"
32 #include "objfiles.h"
33 #include "observable.h"
34 #include "producer.h"
35 #include "reggroups.h"
36
37 /* See amdgpu-tdep.h. */
38
39 bool
40 is_amdgpu_arch (struct gdbarch *arch)
41 {
42 gdb_assert (arch != nullptr);
43 return gdbarch_bfd_arch_info (arch)->arch == bfd_arch_amdgcn;
44 }
45
46 /* See amdgpu-tdep.h. */
47
48 amdgpu_gdbarch_tdep *
49 get_amdgpu_gdbarch_tdep (gdbarch *arch)
50 {
51 return gdbarch_tdep<amdgpu_gdbarch_tdep> (arch);
52 }
53
54 /* Dummy implementation of gdbarch_return_value_as_value. */
55
56 static return_value_convention
57 amdgpu_return_value_as_value (gdbarch *arch, value *function, type *valtype,
58 regcache *regcache, value **read_value,
59 const gdb_byte *writebuf)
60 {
61 gdb_assert_not_reached ("not implemented");
62 }
63
64 /* Return the name of register REGNUM. */
65
66 static const char *
67 amdgpu_register_name (struct gdbarch *gdbarch, int regnum)
68 {
69 /* The list of registers reported by amd-dbgapi for a given architecture
70 contains some duplicate names. For instance, there is an "exec" register
71 for waves in the wave32 mode and one for the waves in the wave64 mode.
72 However, at most one register with a given name is actually allocated for
73 a specific wave. If INFERIOR_PTID represents a GPU wave, we query
74 amd-dbgapi to know whether the requested register actually exists for the
75 current wave, so there won't be duplicates in the the register names we
76 report for that wave.
77
78 But there are two known cases where INFERIOR_PTID doesn't represent a GPU
79 wave:
80
81 - The user does "set arch amdgcn:gfxNNN" followed with "maint print
82 registers"
83 - The "register_name" selftest
84
85 In these cases, we can't query amd-dbgapi to know whether we should hide
86 the register or not. The "register_name" selftest checks that there aren't
87 duplicates in the register names returned by the gdbarch, so if we simply
88 return all register names, that test will fail. The other simple option is
89 to never return a register name, which is what we do here. */
90 if (!ptid_is_gpu (inferior_ptid))
91 return "";
92
93 amd_dbgapi_wave_id_t wave_id = get_amd_dbgapi_wave_id (inferior_ptid);
94 amdgpu_gdbarch_tdep *tdep = get_amdgpu_gdbarch_tdep (gdbarch);
95
96 amd_dbgapi_register_exists_t register_exists;
97 if (amd_dbgapi_wave_register_exists (wave_id, tdep->register_ids[regnum],
98 &register_exists)
99 != AMD_DBGAPI_STATUS_SUCCESS
100 || register_exists != AMD_DBGAPI_REGISTER_PRESENT)
101 return "";
102
103 return tdep->register_names[regnum].c_str ();
104 }
105
106 /* Return the internal register number for the DWARF register number DWARF_REG.
107
108 Return -1 if there's no internal register mapping to DWARF_REG. */
109
110 static int
111 amdgpu_dwarf_reg_to_regnum (struct gdbarch *gdbarch, int dwarf_reg)
112 {
113 amdgpu_gdbarch_tdep *tdep = get_amdgpu_gdbarch_tdep (gdbarch);
114
115 if (dwarf_reg < tdep->dwarf_regnum_to_gdb_regnum.size ())
116 return tdep->dwarf_regnum_to_gdb_regnum[dwarf_reg];
117
118 return -1;
119 }
120
121 /* A hierarchy of classes to represent an amd-dbgapi register type. */
122
123 struct amd_dbgapi_register_type
124 {
125 enum class kind
126 {
127 INTEGER,
128 FLOAT,
129 DOUBLE,
130 VECTOR,
131 CODE_PTR,
132 FLAGS,
133 ENUM,
134 };
135
136 amd_dbgapi_register_type (kind kind, std::string lookup_name)
137 : m_kind (kind), m_lookup_name (std::move (lookup_name))
138 {}
139
140 virtual ~amd_dbgapi_register_type () = default;
141
142 /* Return the type's kind. */
143 kind kind () const
144 { return m_kind; }
145
146 /* Name to use for this type in the existing type map. */
147 const std::string &lookup_name () const
148 { return m_lookup_name; }
149
150 private:
151 enum kind m_kind;
152 std::string m_lookup_name;
153 };
154
155 using amd_dbgapi_register_type_up = std::unique_ptr<amd_dbgapi_register_type>;
156
157 struct amd_dbgapi_register_type_integer : public amd_dbgapi_register_type
158 {
159 amd_dbgapi_register_type_integer (bool is_unsigned, unsigned int bit_size)
160 : amd_dbgapi_register_type
161 (kind::INTEGER,
162 string_printf ("%sint%d", is_unsigned ? "u" : "", bit_size)),
163 m_is_unsigned (is_unsigned),
164 m_bit_size (bit_size)
165 {}
166
167 bool is_unsigned () const
168 { return m_is_unsigned; }
169
170 unsigned int bit_size () const
171 { return m_bit_size; }
172
173 private:
174 bool m_is_unsigned;
175 unsigned int m_bit_size;
176 };
177
178 struct amd_dbgapi_register_type_float : public amd_dbgapi_register_type
179 {
180 amd_dbgapi_register_type_float ()
181 : amd_dbgapi_register_type (kind::FLOAT, "float")
182 {}
183 };
184
185 struct amd_dbgapi_register_type_double : public amd_dbgapi_register_type
186 {
187 amd_dbgapi_register_type_double ()
188 : amd_dbgapi_register_type (kind::DOUBLE, "double")
189 {}
190 };
191
192 struct amd_dbgapi_register_type_vector : public amd_dbgapi_register_type
193 {
194 amd_dbgapi_register_type_vector (const amd_dbgapi_register_type &element_type,
195 unsigned int count)
196 : amd_dbgapi_register_type (kind::VECTOR,
197 make_lookup_name (element_type, count)),
198 m_element_type (element_type),
199 m_count (count)
200 {}
201
202 const amd_dbgapi_register_type &element_type () const
203 { return m_element_type; }
204
205 unsigned int count () const
206 { return m_count; }
207
208 static std::string make_lookup_name
209 (const amd_dbgapi_register_type &element_type, unsigned int count)
210 {
211 return string_printf ("%s[%d]", element_type.lookup_name ().c_str (),
212 count);
213 }
214
215 private:
216 const amd_dbgapi_register_type &m_element_type;
217 unsigned int m_count;
218 };
219
220 struct amd_dbgapi_register_type_code_ptr : public amd_dbgapi_register_type
221 {
222 amd_dbgapi_register_type_code_ptr ()
223 : amd_dbgapi_register_type (kind::CODE_PTR, "void (*)()")
224 {}
225 };
226
227 struct amd_dbgapi_register_type_flags : public amd_dbgapi_register_type
228 {
229 struct field
230 {
231 std::string name;
232 unsigned int bit_pos_start;
233 unsigned int bit_pos_end;
234 const amd_dbgapi_register_type *type;
235 };
236
237 using container_type = std::vector<field>;
238 using const_iterator_type = container_type::const_iterator;
239
240 amd_dbgapi_register_type_flags (unsigned int bit_size, gdb::string_view name)
241 : amd_dbgapi_register_type (kind::FLAGS,
242 make_lookup_name (bit_size, name)),
243 m_bit_size (bit_size),
244 m_name (std::move (name))
245 {}
246
247 unsigned int bit_size () const
248 { return m_bit_size; }
249
250 void add_field (std::string name, unsigned int bit_pos_start,
251 unsigned int bit_pos_end,
252 const amd_dbgapi_register_type *type)
253 {
254 m_fields.push_back (field {std::move (name), bit_pos_start,
255 bit_pos_end, type});
256 }
257
258 container_type::size_type size () const
259 { return m_fields.size (); }
260
261 const field &operator[] (container_type::size_type pos) const
262 { return m_fields[pos]; }
263
264 const_iterator_type begin () const
265 { return m_fields.begin (); }
266
267 const_iterator_type end () const
268 { return m_fields.end (); }
269
270 const std::string &name () const
271 { return m_name; }
272
273 static std::string make_lookup_name (int bits, gdb::string_view name)
274 {
275 std::string res = string_printf ("flags%d_t ", bits);
276 res.append (name.data (), name.size ());
277 return res;
278 }
279
280 private:
281 unsigned int m_bit_size;
282 container_type m_fields;
283 std::string m_name;
284 };
285
286 using amd_dbgapi_register_type_flags_up
287 = std::unique_ptr<amd_dbgapi_register_type_flags>;
288
289 struct amd_dbgapi_register_type_enum : public amd_dbgapi_register_type
290 {
291 struct enumerator
292 {
293 std::string name;
294 ULONGEST value;
295 };
296
297 using container_type = std::vector<enumerator>;
298 using const_iterator_type = container_type::const_iterator;
299
300 amd_dbgapi_register_type_enum (gdb::string_view name)
301 : amd_dbgapi_register_type (kind::ENUM, make_lookup_name (name)),
302 m_name (name.data (), name.length ())
303 {}
304
305 void set_bit_size (int bit_size)
306 { m_bit_size = bit_size; }
307
308 unsigned int bit_size () const
309 { return m_bit_size; }
310
311 void add_enumerator (std::string name, ULONGEST value)
312 { m_enumerators.push_back (enumerator {std::move (name), value}); }
313
314 container_type::size_type size () const
315 { return m_enumerators.size (); }
316
317 const enumerator &operator[] (container_type::size_type pos) const
318 { return m_enumerators[pos]; }
319
320 const_iterator_type begin () const
321 { return m_enumerators.begin (); }
322
323 const_iterator_type end () const
324 { return m_enumerators.end (); }
325
326 const std::string &name () const
327 { return m_name; }
328
329 static std::string make_lookup_name (gdb::string_view name)
330 {
331 std::string res = "enum ";
332 res.append (name.data (), name.length ());
333 return res;
334 }
335
336 private:
337 unsigned int m_bit_size = 32;
338 container_type m_enumerators;
339 std::string m_name;
340 };
341
342 using amd_dbgapi_register_type_enum_up
343 = std::unique_ptr<amd_dbgapi_register_type_enum>;
344
345 /* Map type lookup names to types. */
346 using amd_dbgapi_register_type_map
347 = std::unordered_map<std::string, amd_dbgapi_register_type_up>;
348
349 /* Parse S as a ULONGEST, raise an error on overflow. */
350
351 static ULONGEST
352 try_strtoulst (gdb::string_view s)
353 {
354 errno = 0;
355 ULONGEST value = strtoulst (s.data (), nullptr, 0);
356 if (errno != 0)
357 error (_("Failed to parse integer."));
358
359 return value;
360 };
361
362 /* Shared regex bits. */
363 #define IDENTIFIER "[A-Za-z0-9_.]+"
364 #define WS "[ \t]+"
365 #define WSOPT "[ \t]*"
366
367 static const amd_dbgapi_register_type &
368 parse_amd_dbgapi_register_type (gdb::string_view type_name,
369 amd_dbgapi_register_type_map &type_map);
370
371
372 /* parse_amd_dbgapi_register_type helper for enum types. */
373
374 static void
375 parse_amd_dbgapi_register_type_enum_fields
376 (amd_dbgapi_register_type_enum &enum_type, gdb::string_view fields)
377 {
378 compiled_regex regex (/* name */
379 "^(" IDENTIFIER ")"
380 WSOPT "=" WSOPT
381 /* value */
382 "([0-9]+)"
383 WSOPT "(," WSOPT ")?",
384 REG_EXTENDED,
385 _("Error in AMDGPU enum register type regex"));
386 regmatch_t matches[4];
387
388 while (!fields.empty ())
389 {
390 int res = regex.exec (fields.data (), ARRAY_SIZE (matches), matches, 0);
391 if (res == REG_NOMATCH)
392 error (_("Failed to parse enum fields"));
393
394 auto sv_from_match = [fields] (const regmatch_t &m)
395 { return fields.substr (m.rm_so, m.rm_eo - m.rm_so); };
396
397 gdb::string_view name = sv_from_match (matches[1]);
398 gdb::string_view value_str = sv_from_match (matches[2]);
399 ULONGEST value = try_strtoulst (value_str);
400
401 if (value > std::numeric_limits<uint32_t>::max ())
402 enum_type.set_bit_size (64);
403
404 enum_type.add_enumerator (gdb::to_string (name), value);
405
406 fields = fields.substr (matches[0].rm_eo);
407 }
408 }
409
410 /* parse_amd_dbgapi_register_type helper for flags types. */
411
412 static void
413 parse_amd_dbgapi_register_type_flags_fields
414 (amd_dbgapi_register_type_flags &flags_type,
415 int bits, gdb::string_view name, gdb::string_view fields,
416 amd_dbgapi_register_type_map &type_map)
417 {
418 gdb_assert (bits == 32 || bits == 64);
419
420 std::string regex_str
421 = string_printf (/* type */
422 "^(bool|uint%d_t|enum" WS IDENTIFIER WSOPT "(\\{[^}]*})?)"
423 WS
424 /* name */
425 "(" IDENTIFIER ")" WSOPT
426 /* bit position */
427 "@([0-9]+)(-[0-9]+)?" WSOPT ";" WSOPT,
428 bits);
429 compiled_regex regex (regex_str.c_str (), REG_EXTENDED,
430 _("Error in AMDGPU register type flags fields regex"));
431 regmatch_t matches[6];
432
433 while (!fields.empty ())
434 {
435 int res = regex.exec (fields.data (), ARRAY_SIZE (matches), matches, 0);
436 if (res == REG_NOMATCH)
437 error (_("Failed to parse flags type fields string"));
438
439 auto sv_from_match = [fields] (const regmatch_t &m)
440 { return fields.substr (m.rm_so, m.rm_eo - m.rm_so); };
441
442 gdb::string_view field_type_str = sv_from_match (matches[1]);
443 gdb::string_view field_name = sv_from_match (matches[3]);
444 gdb::string_view pos_begin_str = sv_from_match (matches[4]);
445 ULONGEST pos_begin = try_strtoulst (pos_begin_str);
446
447 if (field_type_str == "bool")
448 flags_type.add_field (gdb::to_string (field_name), pos_begin, pos_begin,
449 nullptr);
450 else
451 {
452 if (matches[5].rm_so == -1)
453 error (_("Missing end bit position"));
454
455 gdb::string_view pos_end_str = sv_from_match (matches[5]);
456 ULONGEST pos_end = try_strtoulst (pos_end_str.substr (1));
457 const amd_dbgapi_register_type &field_type
458 = parse_amd_dbgapi_register_type (field_type_str, type_map);
459 flags_type.add_field (gdb::to_string (field_name), pos_begin, pos_end,
460 &field_type);
461 }
462
463 fields = fields.substr (matches[0].rm_eo);
464 }
465 }
466
467 /* parse_amd_dbgapi_register_type helper for scalars. */
468
469 static const amd_dbgapi_register_type &
470 parse_amd_dbgapi_register_type_scalar (gdb::string_view name,
471 amd_dbgapi_register_type_map &type_map)
472 {
473 std::string name_str = gdb::to_string (name);
474 auto it = type_map.find (name_str);
475 if (it != type_map.end ())
476 {
477 enum amd_dbgapi_register_type::kind kind = it->second->kind ();
478 if (kind != amd_dbgapi_register_type::kind::INTEGER
479 && kind != amd_dbgapi_register_type::kind::FLOAT
480 && kind != amd_dbgapi_register_type::kind::DOUBLE
481 && kind != amd_dbgapi_register_type::kind::CODE_PTR)
482 error (_("type mismatch"));
483
484 return *it->second;
485 }
486
487 amd_dbgapi_register_type_up type;
488 if (name == "int32_t")
489 type.reset (new amd_dbgapi_register_type_integer (false, 32));
490 else if (name == "uint32_t")
491 type.reset (new amd_dbgapi_register_type_integer (true, 32));
492 else if (name == "int64_t")
493 type.reset (new amd_dbgapi_register_type_integer (false, 64));
494 else if (name == "uint64_t")
495 type.reset (new amd_dbgapi_register_type_integer (true, 64));
496 else if (name == "float")
497 type.reset (new amd_dbgapi_register_type_float ());
498 else if (name == "double")
499 type.reset (new amd_dbgapi_register_type_double ());
500 else if (name == "void (*)()")
501 type.reset (new amd_dbgapi_register_type_code_ptr ());
502 else
503 error (_("unknown type %s"), name_str.c_str ());
504
505 auto insertion_pair = type_map.emplace (name, std::move (type));
506 return *insertion_pair.first->second;
507 }
508
509 /* Parse an amd-dbgapi register type string into an amd_dbgapi_register_type
510 object.
511
512 See the documentation of AMD_DBGAPI_REGISTER_INFO_TYPE in amd-dbgapi.h for
513 details about the format. */
514
515 static const amd_dbgapi_register_type &
516 parse_amd_dbgapi_register_type (gdb::string_view type_str,
517 amd_dbgapi_register_type_map &type_map)
518 {
519 size_t pos_open_bracket = type_str.find_last_of ('[');
520 auto sv_from_match = [type_str] (const regmatch_t &m)
521 { return type_str.substr (m.rm_so, m.rm_eo - m.rm_so); };
522
523 if (pos_open_bracket != gdb::string_view::npos)
524 {
525 /* Vector types. */
526 gdb::string_view element_type_str
527 = type_str.substr (0, pos_open_bracket);
528 const amd_dbgapi_register_type &element_type
529 = parse_amd_dbgapi_register_type (element_type_str, type_map);
530
531 size_t pos_close_bracket = type_str.find_last_of (']');
532 gdb_assert (pos_close_bracket != gdb::string_view::npos);
533 gdb::string_view count_str_view
534 = type_str.substr (pos_open_bracket + 1,
535 pos_close_bracket - pos_open_bracket);
536 std::string count_str = gdb::to_string (count_str_view);
537 unsigned int count = std::stoul (count_str);
538
539 std::string lookup_name
540 = amd_dbgapi_register_type_vector::make_lookup_name (element_type, count);
541 auto existing_type_it = type_map.find (lookup_name);
542 if (existing_type_it != type_map.end ())
543 {
544 gdb_assert (existing_type_it->second->kind ()
545 == amd_dbgapi_register_type::kind::VECTOR);
546 return *existing_type_it->second;
547 }
548
549 amd_dbgapi_register_type_up type
550 (new amd_dbgapi_register_type_vector (element_type, count));
551 auto insertion_pair
552 = type_map.emplace (type->lookup_name (), std::move (type));
553 return *insertion_pair.first->second;
554 }
555
556 if (type_str.find ("flags32_t") == 0 || type_str.find ("flags64_t") == 0)
557 {
558 /* Split 'type_str' into 4 tokens: "(type) (name) ({ (fields) })". */
559 compiled_regex regex ("^(flags32_t|flags64_t)"
560 WS "(" IDENTIFIER ")" WSOPT
561 "(\\{" WSOPT "(.*)})?",
562 REG_EXTENDED,
563 _("Error in AMDGPU register type regex"));
564
565 regmatch_t matches[5];
566 int res = regex.exec (type_str.data (), ARRAY_SIZE (matches), matches, 0);
567 if (res == REG_NOMATCH)
568 error (_("Failed to parse flags type string"));
569
570 gdb::string_view flags_keyword = sv_from_match (matches[1]);
571 unsigned int bit_size = flags_keyword == "flags32_t" ? 32 : 64;
572 gdb::string_view name = sv_from_match (matches[2]);
573 std::string lookup_name
574 = amd_dbgapi_register_type_flags::make_lookup_name (bit_size, name);
575 auto existing_type_it = type_map.find (lookup_name);
576
577 if (matches[3].rm_so == -1)
578 {
579 /* No braces, lookup existing type. */
580 if (existing_type_it == type_map.end ())
581 error (_("reference to unknown type %s."),
582 gdb::to_string (name).c_str ());
583
584 if (existing_type_it->second->kind ()
585 != amd_dbgapi_register_type::kind::FLAGS)
586 error (_("type mismatch"));
587
588 return *existing_type_it->second;
589 }
590 else
591 {
592 /* With braces, it's a definition. */
593 if (existing_type_it != type_map.end ())
594 error (_("re-definition of type %s."),
595 gdb::to_string (name).c_str ());
596
597 amd_dbgapi_register_type_flags_up flags_type
598 (new amd_dbgapi_register_type_flags (bit_size, name));
599 gdb::string_view fields_without_braces = sv_from_match (matches[4]);
600
601 parse_amd_dbgapi_register_type_flags_fields
602 (*flags_type, bit_size, name, fields_without_braces, type_map);
603
604 auto insertion_pair
605 = type_map.emplace (flags_type->lookup_name (),
606 std::move (flags_type));
607 return *insertion_pair.first->second;
608 }
609 }
610
611 if (type_str.find ("enum") == 0)
612 {
613 compiled_regex regex ("^enum" WS "(" IDENTIFIER ")" WSOPT "(\\{" WSOPT "([^}]*)})?",
614 REG_EXTENDED,
615 _("Error in AMDGPU register type enum regex"));
616
617 /* Split 'type_name' into 3 tokens: "(name) ( { (fields) } )". */
618 regmatch_t matches[4];
619 int res = regex.exec (type_str.data (), ARRAY_SIZE (matches), matches, 0);
620 if (res == REG_NOMATCH)
621 error (_("Failed to parse flags type string"));
622
623 gdb::string_view name = sv_from_match (matches[1]);
624
625 std::string lookup_name
626 = amd_dbgapi_register_type_enum::make_lookup_name (name);
627 auto existing_type_it = type_map.find (lookup_name);
628
629 if (matches[2].rm_so == -1)
630 {
631 /* No braces, lookup existing type. */
632 if (existing_type_it == type_map.end ())
633 error (_("reference to unknown type %s"),
634 gdb::to_string (name).c_str ());
635
636 if (existing_type_it->second->kind ()
637 != amd_dbgapi_register_type::kind::ENUM)
638 error (_("type mismatch"));
639
640 return *existing_type_it->second;
641 }
642 else
643 {
644 /* With braces, it's a definition. */
645 if (existing_type_it != type_map.end ())
646 error (_("re-definition of type %s"),
647 gdb::to_string (name).c_str ());
648
649 amd_dbgapi_register_type_enum_up enum_type
650 (new amd_dbgapi_register_type_enum (name));
651 gdb::string_view fields_without_braces = sv_from_match (matches[3]);
652
653 parse_amd_dbgapi_register_type_enum_fields
654 (*enum_type, fields_without_braces);
655
656 auto insertion_pair
657 = type_map.emplace (enum_type->lookup_name (),
658 std::move (enum_type));
659 return *insertion_pair.first->second;
660 }
661 }
662
663 return parse_amd_dbgapi_register_type_scalar (type_str, type_map);
664 }
665
666 /* Convert an amd_dbgapi_register_type object to a GDB type. */
667
668 static type *
669 amd_dbgapi_register_type_to_gdb_type (const amd_dbgapi_register_type &type,
670 struct gdbarch *gdbarch)
671 {
672 switch (type.kind ())
673 {
674 case amd_dbgapi_register_type::kind::INTEGER:
675 {
676 const auto &integer_type
677 = gdb::checked_static_cast<const amd_dbgapi_register_type_integer &>
678 (type);
679 switch (integer_type.bit_size ())
680 {
681 case 32:
682 if (integer_type.is_unsigned ())
683 return builtin_type (gdbarch)->builtin_uint32;
684 else
685 return builtin_type (gdbarch)->builtin_int32;
686
687 case 64:
688 if (integer_type.is_unsigned ())
689 return builtin_type (gdbarch)->builtin_uint64;
690 else
691 return builtin_type (gdbarch)->builtin_int64;
692
693 default:
694 gdb_assert_not_reached ("invalid bit size");
695 }
696 }
697
698 case amd_dbgapi_register_type::kind::VECTOR:
699 {
700 const auto &vector_type
701 = gdb::checked_static_cast<const amd_dbgapi_register_type_vector &>
702 (type);
703 struct type *element_type
704 = amd_dbgapi_register_type_to_gdb_type (vector_type.element_type (),
705 gdbarch);
706 return init_vector_type (element_type, vector_type.count ());
707 }
708
709 case amd_dbgapi_register_type::kind::FLOAT:
710 return builtin_type (gdbarch)->builtin_float;
711
712 case amd_dbgapi_register_type::kind::DOUBLE:
713 return builtin_type (gdbarch)->builtin_double;
714
715 case amd_dbgapi_register_type::kind::CODE_PTR:
716 return builtin_type (gdbarch)->builtin_func_ptr;
717
718 case amd_dbgapi_register_type::kind::FLAGS:
719 {
720 const auto &flags_type
721 = gdb::checked_static_cast<const amd_dbgapi_register_type_flags &>
722 (type);
723 struct type *gdb_type
724 = arch_flags_type (gdbarch, flags_type.name ().c_str (),
725 flags_type.bit_size ());
726
727 for (const auto &field : flags_type)
728 {
729 if (field.type == nullptr)
730 {
731 gdb_assert (field.bit_pos_start == field.bit_pos_end);
732 append_flags_type_flag (gdb_type, field.bit_pos_start,
733 field.name.c_str ());
734 }
735 else
736 {
737 struct type *field_type
738 = amd_dbgapi_register_type_to_gdb_type (*field.type, gdbarch);
739 gdb_assert (field_type != nullptr);
740 append_flags_type_field
741 (gdb_type, field.bit_pos_start,
742 field.bit_pos_end - field.bit_pos_start + 1,
743 field_type, field.name.c_str ());
744 }
745 }
746
747 return gdb_type;
748 }
749
750 case amd_dbgapi_register_type::kind::ENUM:
751 {
752 const auto &enum_type
753 = gdb::checked_static_cast<const amd_dbgapi_register_type_enum &>
754 (type);
755 struct type *gdb_type
756 = (type_allocator (gdbarch)
757 .new_type (TYPE_CODE_ENUM, enum_type.bit_size (),
758 enum_type.name ().c_str ()));
759
760 gdb_type->alloc_fields (enum_type.size ());
761 gdb_type->set_is_unsigned (true);
762
763 for (size_t i = 0; i < enum_type.size (); ++i)
764 {
765 const auto &field = enum_type[i];
766 gdb_type->field (i).set_name (xstrdup (field.name.c_str ()));
767 gdb_type->field (i).set_loc_enumval (field.value);
768 }
769
770 return gdb_type;
771 }
772
773 default:
774 gdb_assert_not_reached ("unhandled amd_dbgapi_register_type kind");
775 }
776 }
777
778 static type *
779 amdgpu_register_type (struct gdbarch *gdbarch, int regnum)
780 {
781 amdgpu_gdbarch_tdep *tdep = get_amdgpu_gdbarch_tdep (gdbarch);
782
783 if (tdep->register_types[regnum] == nullptr)
784 {
785 /* This is done lazily (not at gdbarch initialization time), because it
786 requires access to builtin_type, which can't be used while the gdbarch
787 is not fully initialized. */
788 char *bytes;
789 amd_dbgapi_status_t status
790 = amd_dbgapi_register_get_info (tdep->register_ids[regnum],
791 AMD_DBGAPI_REGISTER_INFO_TYPE,
792 sizeof (bytes), &bytes);
793 if (status != AMD_DBGAPI_STATUS_SUCCESS)
794 error (_("Failed to get register type from amd-dbgapi"));
795
796 gdb::unique_xmalloc_ptr<char> bytes_holder (bytes);
797 amd_dbgapi_register_type_map type_map;
798 const amd_dbgapi_register_type &register_type
799 = parse_amd_dbgapi_register_type (bytes, type_map);
800 tdep->register_types[regnum]
801 = amd_dbgapi_register_type_to_gdb_type (register_type, gdbarch);
802 gdb_assert (tdep->register_types[regnum] != nullptr);
803 }
804
805 return tdep->register_types[regnum];
806 }
807
808 static int
809 amdgpu_register_reggroup_p (struct gdbarch *gdbarch, int regnum,
810 const reggroup *group)
811 {
812 amdgpu_gdbarch_tdep *tdep = get_amdgpu_gdbarch_tdep (gdbarch);
813
814 auto it = tdep->register_class_map.find (group->name ());
815 if (it == tdep->register_class_map.end ())
816 return group == all_reggroup;
817
818 amd_dbgapi_register_class_state_t state;
819 if (amd_dbgapi_register_is_in_register_class (it->second,
820 tdep->register_ids[regnum],
821 &state)
822 != AMD_DBGAPI_STATUS_SUCCESS)
823 return group == all_reggroup;
824
825 return (state == AMD_DBGAPI_REGISTER_CLASS_STATE_MEMBER
826 || group == all_reggroup);
827 }
828
829 static int
830 amdgpu_breakpoint_kind_from_pc (struct gdbarch *gdbarch, CORE_ADDR *)
831 {
832 return get_amdgpu_gdbarch_tdep (gdbarch)->breakpoint_instruction_size;
833 }
834
835 static const gdb_byte *
836 amdgpu_sw_breakpoint_from_kind (struct gdbarch *gdbarch, int kind, int *size)
837 {
838 *size = kind;
839 return get_amdgpu_gdbarch_tdep (gdbarch)->breakpoint_instruction_bytes.get ();
840 }
841
842 struct amdgpu_frame_cache
843 {
844 CORE_ADDR base;
845 CORE_ADDR pc;
846 };
847
848 static amdgpu_frame_cache *
849 amdgpu_frame_cache (frame_info_ptr this_frame, void **this_cache)
850 {
851 if (*this_cache != nullptr)
852 return (struct amdgpu_frame_cache *) *this_cache;
853
854 struct amdgpu_frame_cache *cache
855 = FRAME_OBSTACK_ZALLOC (struct amdgpu_frame_cache);
856 (*this_cache) = cache;
857
858 cache->pc = get_frame_func (this_frame);
859 cache->base = 0;
860
861 return cache;
862 }
863
864 static void
865 amdgpu_frame_this_id (frame_info_ptr this_frame, void **this_cache,
866 frame_id *this_id)
867 {
868 struct amdgpu_frame_cache *cache
869 = amdgpu_frame_cache (this_frame, this_cache);
870
871 if (get_frame_type (this_frame) == INLINE_FRAME)
872 (*this_id) = frame_id_build (cache->base, cache->pc);
873 else
874 (*this_id) = outer_frame_id;
875
876 frame_debug_printf ("this_frame=%d, type=%d, this_id=%s",
877 frame_relative_level (this_frame),
878 get_frame_type (this_frame),
879 this_id->to_string ().c_str ());
880 }
881
882 static frame_id
883 amdgpu_dummy_id (struct gdbarch *gdbarch, frame_info_ptr this_frame)
884 {
885 return frame_id_build (0, get_frame_pc (this_frame));
886 }
887
888 static struct value *
889 amdgpu_frame_prev_register (frame_info_ptr this_frame, void **this_cache,
890 int regnum)
891 {
892 return frame_unwind_got_register (this_frame, regnum, regnum);
893 }
894
895 static const frame_unwind amdgpu_frame_unwind = {
896 "amdgpu",
897 NORMAL_FRAME,
898 default_frame_unwind_stop_reason,
899 amdgpu_frame_this_id,
900 amdgpu_frame_prev_register,
901 nullptr,
902 default_frame_sniffer,
903 nullptr,
904 nullptr,
905 };
906
907 static int
908 print_insn_amdgpu (bfd_vma memaddr, struct disassemble_info *info)
909 {
910 gdb_disassemble_info *di
911 = static_cast<gdb_disassemble_info *> (info->application_data);
912
913 /* Try to read at most INSTRUCTION_SIZE bytes. */
914
915 amd_dbgapi_size_t instruction_size = gdbarch_max_insn_length (di->arch ());
916 gdb::byte_vector buffer (instruction_size);
917
918 /* read_memory_func doesn't support partial reads, so if the read
919 fails, try one byte less, on and on until we manage to read
920 something. A case where this would happen is if we're trying to
921 read the last instruction at the end of a file section and that
922 instruction is smaller than the largest instruction. */
923 while (instruction_size > 0)
924 {
925 int ret = info->read_memory_func (memaddr, buffer.data (),
926 instruction_size, info);
927 if (ret == 0)
928 break;
929
930 --instruction_size;
931 }
932
933 if (instruction_size == 0)
934 {
935 info->memory_error_func (-1, memaddr, info);
936 return -1;
937 }
938
939 amd_dbgapi_architecture_id_t architecture_id;
940 amd_dbgapi_status_t status
941 = amd_dbgapi_get_architecture (gdbarch_bfd_arch_info (di->arch ())->mach,
942 &architecture_id);
943 if (status != AMD_DBGAPI_STATUS_SUCCESS)
944 return -1;
945
946 auto symbolizer = [] (amd_dbgapi_symbolizer_id_t symbolizer_id,
947 amd_dbgapi_global_address_t address,
948 char **symbol_text) -> amd_dbgapi_status_t
949 {
950 gdb_disassemble_info *disasm_info
951 = reinterpret_cast<gdb_disassemble_info *> (symbolizer_id);
952 gdb_printing_disassembler *disasm
953 = dynamic_cast<gdb_printing_disassembler *> (disasm_info);
954 gdb_assert (disasm != nullptr);
955
956 string_file string (disasm->stream ()->can_emit_style_escape ());
957 print_address (disasm->arch (), address, &string);
958 *symbol_text = xstrdup (string.c_str ());
959
960 return AMD_DBGAPI_STATUS_SUCCESS;
961 };
962 auto symbolizer_id = reinterpret_cast<amd_dbgapi_symbolizer_id_t> (di);
963 char *instruction_text = nullptr;
964 status = amd_dbgapi_disassemble_instruction (architecture_id, memaddr,
965 &instruction_size,
966 buffer.data (),
967 &instruction_text,
968 symbolizer_id,
969 symbolizer);
970 if (status != AMD_DBGAPI_STATUS_SUCCESS)
971 {
972 size_t alignment;
973 status = amd_dbgapi_architecture_get_info
974 (architecture_id,
975 AMD_DBGAPI_ARCHITECTURE_INFO_MINIMUM_INSTRUCTION_ALIGNMENT,
976 sizeof (alignment), &alignment);
977 if (status != AMD_DBGAPI_STATUS_SUCCESS)
978 error (_("amd_dbgapi_architecture_get_info failed"));
979
980 info->fprintf_func (di, "<illegal instruction>");
981
982 /* Skip to the next valid instruction address. */
983 return align_up (memaddr + 1, alignment) - memaddr;
984 }
985
986 /* Print the instruction. */
987 info->fprintf_func (di, "%s", instruction_text);
988
989 /* Free the memory allocated by the amd-dbgapi. */
990 xfree (instruction_text);
991
992 return static_cast<int> (instruction_size);
993 }
994
995 static CORE_ADDR
996 amdgpu_skip_prologue (struct gdbarch *gdbarch, CORE_ADDR start_pc)
997 {
998 CORE_ADDR func_addr;
999
1000 /* See if we can determine the end of the prologue via the symbol table.
1001 If so, then return either PC, or the PC after the prologue, whichever
1002 is greater. */
1003 if (find_pc_partial_function (start_pc, nullptr, &func_addr, nullptr))
1004 {
1005 CORE_ADDR post_prologue_pc
1006 = skip_prologue_using_sal (gdbarch, func_addr);
1007 struct compunit_symtab *cust = find_pc_compunit_symtab (func_addr);
1008
1009 /* Clang always emits a line note before the prologue and another
1010 one after. We trust clang to emit usable line notes. */
1011 if (post_prologue_pc != 0
1012 && cust != nullptr
1013 && cust->producer () != nullptr
1014 && producer_is_llvm (cust->producer ()))
1015 return std::max (start_pc, post_prologue_pc);
1016 }
1017
1018 return start_pc;
1019 }
1020
1021 static bool
1022 amdgpu_supports_arch_info (const struct bfd_arch_info *info)
1023 {
1024 amd_dbgapi_architecture_id_t architecture_id;
1025 amd_dbgapi_status_t status
1026 = amd_dbgapi_get_architecture (info->mach, &architecture_id);
1027
1028 gdb_assert (status != AMD_DBGAPI_STATUS_ERROR_NOT_INITIALIZED);
1029 return status == AMD_DBGAPI_STATUS_SUCCESS;
1030 }
1031
1032 static struct gdbarch *
1033 amdgpu_gdbarch_init (struct gdbarch_info info, struct gdbarch_list *arches)
1034 {
1035 /* If there is already a candidate, use it. */
1036 arches = gdbarch_list_lookup_by_info (arches, &info);
1037 if (arches != nullptr)
1038 return arches->gdbarch;
1039
1040 /* Allocate space for the new architecture. */
1041 gdbarch_up gdbarch_u
1042 (gdbarch_alloc (&info, gdbarch_tdep_up (new amdgpu_gdbarch_tdep)));
1043 gdbarch *gdbarch = gdbarch_u.get ();
1044 amdgpu_gdbarch_tdep *tdep = gdbarch_tdep<amdgpu_gdbarch_tdep> (gdbarch);
1045
1046 /* Data types. */
1047 set_gdbarch_char_signed (gdbarch, 0);
1048 set_gdbarch_ptr_bit (gdbarch, 64);
1049 set_gdbarch_addr_bit (gdbarch, 64);
1050 set_gdbarch_short_bit (gdbarch, 16);
1051 set_gdbarch_int_bit (gdbarch, 32);
1052 set_gdbarch_long_bit (gdbarch, 64);
1053 set_gdbarch_long_long_bit (gdbarch, 64);
1054 set_gdbarch_float_bit (gdbarch, 32);
1055 set_gdbarch_double_bit (gdbarch, 64);
1056 set_gdbarch_long_double_bit (gdbarch, 128);
1057 set_gdbarch_half_format (gdbarch, floatformats_ieee_half);
1058 set_gdbarch_float_format (gdbarch, floatformats_ieee_single);
1059 set_gdbarch_double_format (gdbarch, floatformats_ieee_double);
1060 set_gdbarch_long_double_format (gdbarch, floatformats_ieee_double);
1061
1062 /* Frame interpretation. */
1063 set_gdbarch_skip_prologue (gdbarch, amdgpu_skip_prologue);
1064 set_gdbarch_inner_than (gdbarch, core_addr_greaterthan);
1065 dwarf2_append_unwinders (gdbarch);
1066 frame_unwind_append_unwinder (gdbarch, &amdgpu_frame_unwind);
1067 set_gdbarch_dummy_id (gdbarch, amdgpu_dummy_id);
1068
1069 /* Registers and memory. */
1070 amd_dbgapi_architecture_id_t architecture_id;
1071 amd_dbgapi_status_t status
1072 = amd_dbgapi_get_architecture (gdbarch_bfd_arch_info (gdbarch)->mach,
1073 &architecture_id);
1074 if (status != AMD_DBGAPI_STATUS_SUCCESS)
1075 {
1076 warning (_("Failed to get architecture from amd-dbgapi"));
1077 return nullptr;
1078 }
1079
1080
1081 /* Add register groups. */
1082 size_t register_class_count;
1083 amd_dbgapi_register_class_id_t *register_class_ids;
1084 status = amd_dbgapi_architecture_register_class_list (architecture_id,
1085 &register_class_count,
1086 &register_class_ids);
1087 if (status != AMD_DBGAPI_STATUS_SUCCESS)
1088 {
1089 warning (_("Failed to get register class list from amd-dbgapi"));
1090 return nullptr;
1091 }
1092
1093 gdb::unique_xmalloc_ptr<amd_dbgapi_register_class_id_t>
1094 register_class_ids_holder (register_class_ids);
1095
1096 for (size_t i = 0; i < register_class_count; ++i)
1097 {
1098 char *bytes;
1099 status = amd_dbgapi_architecture_register_class_get_info
1100 (register_class_ids[i], AMD_DBGAPI_REGISTER_CLASS_INFO_NAME,
1101 sizeof (bytes), &bytes);
1102 if (status != AMD_DBGAPI_STATUS_SUCCESS)
1103 {
1104 warning (_("Failed to get register class name from amd-dbgapi"));
1105 return nullptr;
1106 }
1107
1108 gdb::unique_xmalloc_ptr<char> name (bytes);
1109
1110 auto inserted = tdep->register_class_map.emplace (name.get (),
1111 register_class_ids[i]);
1112 gdb_assert (inserted.second);
1113
1114 /* Avoid creating a user reggroup with the same name as some built-in
1115 reggroup, such as "general", "system", "vector", etc. */
1116 if (reggroup_find (gdbarch, name.get ()) != nullptr)
1117 continue;
1118
1119 /* Allocate the reggroup in the gdbarch. */
1120 reggroup_add
1121 (gdbarch, reggroup_gdbarch_new (gdbarch, name.get (), USER_REGGROUP));
1122 }
1123
1124 /* Add registers. */
1125 size_t register_count;
1126 amd_dbgapi_register_id_t *register_ids;
1127 status = amd_dbgapi_architecture_register_list (architecture_id,
1128 &register_count,
1129 &register_ids);
1130 if (status != AMD_DBGAPI_STATUS_SUCCESS)
1131 {
1132 warning (_("Failed to get register list from amd-dbgapi"));
1133 return nullptr;
1134 }
1135
1136 gdb::unique_xmalloc_ptr<amd_dbgapi_register_id_t> register_ids_holder
1137 (register_ids);
1138
1139 tdep->register_ids.insert (tdep->register_ids.end (), &register_ids[0],
1140 &register_ids[register_count]);
1141
1142 tdep->register_properties.resize (register_count,
1143 AMD_DBGAPI_REGISTER_PROPERTY_NONE);
1144 for (size_t regnum = 0; regnum < register_count; ++regnum)
1145 {
1146 auto &register_properties = tdep->register_properties[regnum];
1147 if (amd_dbgapi_register_get_info (register_ids[regnum],
1148 AMD_DBGAPI_REGISTER_INFO_PROPERTIES,
1149 sizeof (register_properties),
1150 &register_properties)
1151 != AMD_DBGAPI_STATUS_SUCCESS)
1152 {
1153 warning (_("Failed to get register properties from amd-dbgapi"));
1154 return nullptr;
1155 }
1156 }
1157
1158 set_gdbarch_num_regs (gdbarch, register_count);
1159 set_gdbarch_num_pseudo_regs (gdbarch, 0);
1160
1161 tdep->register_names.resize (register_count);
1162 tdep->register_types.resize (register_count);
1163 for (size_t i = 0; i < register_count; ++i)
1164 {
1165 /* Set amd-dbgapi register id -> gdb regnum mapping. */
1166 tdep->regnum_map.emplace (tdep->register_ids[i], i);
1167
1168 /* Get register name. */
1169 char *bytes;
1170 status = amd_dbgapi_register_get_info (tdep->register_ids[i],
1171 AMD_DBGAPI_REGISTER_INFO_NAME,
1172 sizeof (bytes), &bytes);
1173 if (status == AMD_DBGAPI_STATUS_SUCCESS)
1174 {
1175 tdep->register_names[i] = bytes;
1176 xfree (bytes);
1177 }
1178
1179 /* Get register DWARF number. */
1180 uint64_t dwarf_num;
1181 status = amd_dbgapi_register_get_info (tdep->register_ids[i],
1182 AMD_DBGAPI_REGISTER_INFO_DWARF,
1183 sizeof (dwarf_num), &dwarf_num);
1184 if (status == AMD_DBGAPI_STATUS_SUCCESS)
1185 {
1186 if (dwarf_num >= tdep->dwarf_regnum_to_gdb_regnum.size ())
1187 tdep->dwarf_regnum_to_gdb_regnum.resize (dwarf_num + 1, -1);
1188
1189 tdep->dwarf_regnum_to_gdb_regnum[dwarf_num] = i;
1190 }
1191 }
1192
1193 amd_dbgapi_register_id_t pc_register_id;
1194 status = amd_dbgapi_architecture_get_info
1195 (architecture_id, AMD_DBGAPI_ARCHITECTURE_INFO_PC_REGISTER,
1196 sizeof (pc_register_id), &pc_register_id);
1197 if (status != AMD_DBGAPI_STATUS_SUCCESS)
1198 {
1199 warning (_("Failed to get PC register from amd-dbgapi"));
1200 return nullptr;
1201 }
1202
1203 set_gdbarch_pc_regnum (gdbarch, tdep->regnum_map[pc_register_id]);
1204 set_gdbarch_ps_regnum (gdbarch, -1);
1205 set_gdbarch_sp_regnum (gdbarch, -1);
1206 set_gdbarch_fp0_regnum (gdbarch, -1);
1207
1208 set_gdbarch_dwarf2_reg_to_regnum (gdbarch, amdgpu_dwarf_reg_to_regnum);
1209
1210 set_gdbarch_return_value_as_value (gdbarch, amdgpu_return_value_as_value);
1211
1212 /* Register representation. */
1213 set_gdbarch_register_name (gdbarch, amdgpu_register_name);
1214 set_gdbarch_register_type (gdbarch, amdgpu_register_type);
1215 set_gdbarch_register_reggroup_p (gdbarch, amdgpu_register_reggroup_p);
1216
1217 /* Disassembly. */
1218 set_gdbarch_print_insn (gdbarch, print_insn_amdgpu);
1219
1220 /* Instructions. */
1221 amd_dbgapi_size_t max_insn_length = 0;
1222 status = amd_dbgapi_architecture_get_info
1223 (architecture_id, AMD_DBGAPI_ARCHITECTURE_INFO_LARGEST_INSTRUCTION_SIZE,
1224 sizeof (max_insn_length), &max_insn_length);
1225 if (status != AMD_DBGAPI_STATUS_SUCCESS)
1226 error (_("amd_dbgapi_architecture_get_info failed"));
1227
1228 set_gdbarch_max_insn_length (gdbarch, max_insn_length);
1229
1230 status = amd_dbgapi_architecture_get_info
1231 (architecture_id, AMD_DBGAPI_ARCHITECTURE_INFO_BREAKPOINT_INSTRUCTION_SIZE,
1232 sizeof (tdep->breakpoint_instruction_size),
1233 &tdep->breakpoint_instruction_size);
1234 if (status != AMD_DBGAPI_STATUS_SUCCESS)
1235 error (_("amd_dbgapi_architecture_get_info failed"));
1236
1237 gdb_byte *breakpoint_instruction_bytes;
1238 status = amd_dbgapi_architecture_get_info
1239 (architecture_id, AMD_DBGAPI_ARCHITECTURE_INFO_BREAKPOINT_INSTRUCTION,
1240 sizeof (breakpoint_instruction_bytes), &breakpoint_instruction_bytes);
1241 if (status != AMD_DBGAPI_STATUS_SUCCESS)
1242 error (_("amd_dbgapi_architecture_get_info failed"));
1243
1244 tdep->breakpoint_instruction_bytes.reset (breakpoint_instruction_bytes);
1245
1246 set_gdbarch_breakpoint_kind_from_pc (gdbarch,
1247 amdgpu_breakpoint_kind_from_pc);
1248 set_gdbarch_sw_breakpoint_from_kind (gdbarch,
1249 amdgpu_sw_breakpoint_from_kind);
1250
1251 amd_dbgapi_size_t pc_adjust;
1252 status = amd_dbgapi_architecture_get_info
1253 (architecture_id,
1254 AMD_DBGAPI_ARCHITECTURE_INFO_BREAKPOINT_INSTRUCTION_PC_ADJUST,
1255 sizeof (pc_adjust), &pc_adjust);
1256 if (status != AMD_DBGAPI_STATUS_SUCCESS)
1257 error (_("amd_dbgapi_architecture_get_info failed"));
1258
1259 set_gdbarch_decr_pc_after_break (gdbarch, pc_adjust);
1260
1261 return gdbarch_u.release ();
1262 }
1263
1264 #if defined GDB_SELF_TEST
1265
1266 static void
1267 amdgpu_register_type_parse_test ()
1268 {
1269 {
1270 /* A type that exercises flags and enums, in particular looking up an
1271 existing enum type by name. */
1272 const char *flags_type_str =
1273 "flags32_t mode { \
1274 enum fp_round { \
1275 NEAREST_EVEN = 0, \
1276 PLUS_INF = 1, \
1277 MINUS_INF = 2, \
1278 ZERO = 3 \
1279 } FP_ROUND.32 @0-1; \
1280 enum fp_round FP_ROUND.64_16 @2-3; \
1281 enum fp_denorm { \
1282 FLUSH_SRC_DST = 0, \
1283 FLUSH_DST = 1, \
1284 FLUSH_SRC = 2, \
1285 FLUSH_NONE = 3 \
1286 } FP_DENORM.32 @4-5; \
1287 enum fp_denorm FP_DENORM.64_16 @6-7; \
1288 bool DX10_CLAMP @8; \
1289 bool IEEE @9; \
1290 bool LOD_CLAMPED @10; \
1291 bool DEBUG_EN @11; \
1292 bool EXCP_EN.INVALID @12; \
1293 bool EXCP_EN.DENORM @13; \
1294 bool EXCP_EN.DIV0 @14; \
1295 bool EXCP_EN.OVERFLOW @15; \
1296 bool EXCP_EN.UNDERFLOW @16; \
1297 bool EXCP_EN.INEXACT @17; \
1298 bool EXCP_EN.INT_DIV0 @18; \
1299 bool EXCP_EN.ADDR_WATCH @19; \
1300 bool FP16_OVFL @23; \
1301 bool POPS_PACKER0 @24; \
1302 bool POPS_PACKER1 @25; \
1303 bool DISABLE_PERF @26; \
1304 bool GPR_IDX_EN @27; \
1305 bool VSKIP @28; \
1306 uint32_t CSP @29-31; \
1307 }";
1308 amd_dbgapi_register_type_map type_map;
1309 const amd_dbgapi_register_type &type
1310 = parse_amd_dbgapi_register_type (flags_type_str, type_map);
1311
1312 gdb_assert (type.kind () == amd_dbgapi_register_type::kind::FLAGS);
1313
1314 const auto &f
1315 = gdb::checked_static_cast<const amd_dbgapi_register_type_flags &> (type);
1316 gdb_assert (f.size () == 23);
1317
1318 /* Check the two "FP_ROUND" fields. */
1319 auto check_fp_round_field
1320 = [] (const char *name, const amd_dbgapi_register_type_flags::field &field)
1321 {
1322 gdb_assert (field.name == name);
1323 gdb_assert (field.type->kind ()
1324 == amd_dbgapi_register_type::kind::ENUM);
1325
1326 const auto &e
1327 = gdb::checked_static_cast<const amd_dbgapi_register_type_enum &>
1328 (*field.type);
1329 gdb_assert (e.size () == 4);
1330 gdb_assert (e[0].name == "NEAREST_EVEN");
1331 gdb_assert (e[0].value == 0);
1332 gdb_assert (e[3].name == "ZERO");
1333 gdb_assert (e[3].value == 3);
1334 };
1335
1336 check_fp_round_field ("FP_ROUND.32", f[0]);
1337 check_fp_round_field ("FP_ROUND.64_16", f[1]);
1338
1339 /* Check the "CSP" field. */
1340 gdb_assert (f[22].name == "CSP");
1341 gdb_assert (f[22].type->kind () == amd_dbgapi_register_type::kind::INTEGER);
1342
1343 const auto &i
1344 = gdb::checked_static_cast<const amd_dbgapi_register_type_integer &>
1345 (*f[22].type);
1346 gdb_assert (i.bit_size () == 32);
1347 gdb_assert (i.is_unsigned ());
1348 }
1349
1350 {
1351 /* Test the vector type. */
1352 const char *vector_type_str = "int32_t[64]";
1353 amd_dbgapi_register_type_map type_map;
1354 const amd_dbgapi_register_type &type
1355 = parse_amd_dbgapi_register_type (vector_type_str, type_map);
1356
1357 gdb_assert (type.kind () == amd_dbgapi_register_type::kind::VECTOR);
1358
1359 const auto &v
1360 = gdb::checked_static_cast<const amd_dbgapi_register_type_vector &>
1361 (type);
1362 gdb_assert (v.count () == 64);
1363
1364 const auto &et = v.element_type ();
1365 gdb_assert (et.kind () == amd_dbgapi_register_type::kind::INTEGER);
1366
1367 const auto &i
1368 = gdb::checked_static_cast<const amd_dbgapi_register_type_integer &> (et);
1369 gdb_assert (i.bit_size () == 32);
1370 gdb_assert (!i.is_unsigned ());
1371 }
1372 }
1373
1374 #endif
1375
1376 void _initialize_amdgpu_tdep ();
1377
1378 void
1379 _initialize_amdgpu_tdep ()
1380 {
1381 gdbarch_register (bfd_arch_amdgcn, amdgpu_gdbarch_init, NULL,
1382 amdgpu_supports_arch_info);
1383 #if defined GDB_SELF_TEST
1384 selftests::register_test ("amdgpu-register-type-parse-flags-fields",
1385 amdgpu_register_type_parse_test);
1386 #endif
1387 }