Handle multiple target events before commit resume
[deliverable/binutils-gdb.git] / gdb / amdgcn-rocm-tdep.c
CommitLineData
abeeff98
LM
1/* Target-dependent code for the ROCm amdgcn architecture.
2
ca9af5a1
LM
3 Copyright (C) 2019-2020 Free Software Foundation, Inc.
4 Copyright (C) 2019-2020 Advanced Micro Devices, Inc. All rights reserved.
abeeff98
LM
5
6 This file is part of GDB.
7
8 This program is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 3 of the License, or
11 (at your option) any later version.
12
13 This program is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
17
18 You should have received a copy of the GNU General Public License
19 along with this program. If not, see <http://www.gnu.org/licenses/>. */
20
21#include "defs.h"
22
23#include "amdgcn-rocm-tdep.h"
24#include "arch-utils.h"
25#include "dwarf2-frame.h"
26#include "frame-base.h"
27#include "frame-unwind.h"
28#include "gdbarch.h"
29#include "inferior.h"
30#include "osabi.h"
31#include "reggroups.h"
32#include "rocm-tdep.h"
33
34bool
35rocm_is_amdgcn_gdbarch (struct gdbarch *arch)
36{
37 return (gdbarch_bfd_arch_info (arch)->arch == bfd_arch_amdgcn);
38}
39
40/* Return the name of register REGNUM. */
41static const char *
42amdgcn_register_name (struct gdbarch *gdbarch, int regnum)
43{
44 amd_dbgapi_process_id_t process_id = get_amd_dbgapi_process_id ();
45 amd_dbgapi_wave_id_t wave_id = get_amd_dbgapi_wave_id (inferior_ptid);
46 struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
47
48 amd_dbgapi_size_t unused;
49 if (amd_dbgapi_wave_register_get_info (
50 process_id, wave_id, tdep->register_ids[regnum],
51 AMD_DBGAPI_REGISTER_INFO_SIZE, sizeof (unused), &unused)
52 != AMD_DBGAPI_STATUS_SUCCESS)
53 return "";
54
55 return tdep->register_names[regnum].c_str ();
56}
57
58static int
59amdgcn_dwarf_reg_to_regnum (struct gdbarch *gdbarch, int reg)
60{
61 amd_dbgapi_architecture_id_t architecture_id;
62 amd_dbgapi_register_id_t register_id;
63
64 if (amd_dbgapi_get_architecture (gdbarch_bfd_arch_info (gdbarch)->mach,
65 &architecture_id)
66 != AMD_DBGAPI_STATUS_SUCCESS)
67 return -1;
68
69 if (amd_dbgapi_dwarf_register_to_register (architecture_id, reg,
70 &register_id)
71 != AMD_DBGAPI_STATUS_SUCCESS)
72 return -1;
73
74 return gdbarch_tdep (gdbarch)->regnum_map[register_id];
75}
76
77static struct type *
78gdb_type_from_type_name (struct gdbarch *gdbarch, const std::string &type_name)
79{
80 size_t pos;
81
82 /* vector types. */
83 if ((pos = type_name.find_last_of ('[')) != std::string::npos)
84 {
85 struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
86
87 auto it = tdep->vector_type_map.find (type_name);
88 if (it != tdep->vector_type_map.end ())
89 return it->second;
90
91 struct type *vector_type = init_vector_type (
92 gdb_type_from_type_name (gdbarch, type_name.substr (0, pos)),
93 std::stoi (type_name.substr (pos + 1)));
94
2bcf29f7
LM
95 TYPE_NAME (vector_type)
96 = tdep->vector_type_map.emplace (type_name, vector_type)
97 .first->first.c_str ();
98
abeeff98
LM
99 return vector_type;
100 }
101 /* scalar types. */
102 else if (type_name == "int32_t")
103 return builtin_type (gdbarch)->builtin_int32;
104 else if (type_name == "uint32_t")
105 return builtin_type (gdbarch)->builtin_uint32;
106 else if (type_name == "int64_t")
107 return builtin_type (gdbarch)->builtin_int64;
108 else if (type_name == "uint64_t")
109 return builtin_type (gdbarch)->builtin_uint64;
110 else if (type_name == "float")
111 return builtin_type (gdbarch)->builtin_float;
112 else if (type_name == "double")
113 return builtin_type (gdbarch)->builtin_double;
114 else if (type_name == "void (*)()")
115 return builtin_type (gdbarch)->builtin_func_ptr;
116
117 return builtin_type (gdbarch)->builtin_void;
118}
119
120static struct type *
121amdgcn_register_type (struct gdbarch *gdbarch, int regnum)
122{
123 amd_dbgapi_process_id_t process_id = get_amd_dbgapi_process_id ();
124 amd_dbgapi_wave_id_t wave_id = get_amd_dbgapi_wave_id (inferior_ptid);
125 struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
126
127 char *bytes;
128 if (amd_dbgapi_wave_register_get_info (
129 process_id, wave_id, tdep->register_ids[regnum],
130 AMD_DBGAPI_REGISTER_INFO_TYPE, sizeof (bytes), &bytes)
131 == AMD_DBGAPI_STATUS_SUCCESS)
132 {
133 std::string type_name (bytes);
134 xfree (bytes);
135
136 return gdb_type_from_type_name (gdbarch, type_name);
137 }
138
139 return builtin_type (gdbarch)->builtin_void;
140}
141
142static int
143amdgcn_register_reggroup_p (struct gdbarch *gdbarch, int regnum,
144 struct reggroup *group)
145{
146 struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
147 const char *name = reggroup_name (group);
148
149 auto it = tdep->register_class_map.find (name);
150 if (it == tdep->register_class_map.end ())
151 return group == all_reggroup;
152
153 amd_dbgapi_architecture_id_t architecture_id;
154
155 if (amd_dbgapi_get_architecture (gdbarch_bfd_arch_info (gdbarch)->mach,
156 &architecture_id)
157 != AMD_DBGAPI_STATUS_SUCCESS)
158 return group == all_reggroup;
159
160 amd_dbgapi_register_class_state_t state;
161
162 if (amd_dbgapi_register_is_in_register_class (
163 architecture_id, tdep->register_ids[regnum], it->second, &state)
164 != AMD_DBGAPI_STATUS_SUCCESS)
165 return group == all_reggroup;
166
167 return state == AMD_DBGAPI_REGISTER_CLASS_STATE_MEMBER
168 || group == all_reggroup;
169}
170
171static int
172amdgcn_breakpoint_kind_from_pc (struct gdbarch *gdbarch, CORE_ADDR *)
173{
174 return gdbarch_tdep (gdbarch)->breakpoint_instruction_size;
175}
176
177static const gdb_byte *
178amdgcn_sw_breakpoint_from_kind (struct gdbarch *gdbarch, int kind, int *size)
179{
180 *size = kind;
181 return gdbarch_tdep (gdbarch)->breakpoint_instruction_bytes.get ();
182}
183
184struct amdgcn_frame_cache
185{
186 CORE_ADDR base;
187 CORE_ADDR pc;
188};
189
190static struct amdgcn_frame_cache *
191amdgcn_frame_cache (struct frame_info *this_frame, void **this_cache)
192{
193 if (*this_cache)
194 return (struct amdgcn_frame_cache *)*this_cache;
195
196 struct amdgcn_frame_cache *cache
197 = FRAME_OBSTACK_ZALLOC (struct amdgcn_frame_cache);
198 (*this_cache) = cache;
199
200 cache->pc = get_frame_func (this_frame);
201 cache->base = 0;
202
203 return cache;
204}
205
206static void
207amdgcn_frame_this_id (struct frame_info *this_frame, void **this_cache,
208 struct frame_id *this_id)
209{
210 struct amdgcn_frame_cache *cache
211 = amdgcn_frame_cache (this_frame, this_cache);
212
213 if (get_frame_type (this_frame) == INLINE_FRAME)
214 (*this_id) = frame_id_build (cache->base, cache->pc);
215 else
216 (*this_id) = outer_frame_id;
217
218 if (frame_debug)
219 {
220 fprintf_unfiltered (
221 gdb_stdlog, "{ amdgcn_frame_this_id (this_frame=%d) type=%d -> ",
222 frame_relative_level (this_frame), get_frame_type (this_frame));
223 fprint_frame_id (gdb_stdlog, *this_id);
224 fprintf_unfiltered (gdb_stdlog, "}\n");
225 }
226
227 return;
228}
229
230static struct frame_id
231amdgcn_dummy_id (struct gdbarch *gdbarch, struct frame_info *this_frame)
232{
233 return frame_id_build (0, get_frame_pc (this_frame));
234}
235
236static struct value *
237amdgcn_frame_prev_register (struct frame_info *this_frame, void **this_cache,
238 int regnum)
239{
240 return frame_unwind_got_register (this_frame, regnum, regnum);
241}
242
243static const struct frame_unwind amdgcn_frame_unwind = {
244 NORMAL_FRAME,
245 default_frame_unwind_stop_reason,
246 amdgcn_frame_this_id,
247 amdgcn_frame_prev_register,
248 NULL,
249 default_frame_sniffer,
250 NULL,
251 NULL,
252};
253
254struct rocm_displaced_step_closure : public displaced_step_closure
255{
256 amd_dbgapi_process_id_t process_id;
257 amd_dbgapi_wave_id_t wave_id;
258 amd_dbgapi_displaced_stepping_id_t displaced_stepping_id;
259};
260
261static CORE_ADDR
262amdgcn_rocm_displaced_step_location (struct gdbarch *gdbarch)
263{
264 size_t size = gdbarch_tdep (gdbarch)->breakpoint_instruction_size;
265 gdb::unique_xmalloc_ptr<gdb_byte> buffer (
266 static_cast<gdb_byte *> (xmalloc (size)));
267
268 /* Read the bytes that were overwritten by the breakpoint instruction. */
269 if (target_read_memory (regcache_read_pc (get_current_regcache ()),
270 buffer.get (), size))
271 return 0;
272
273 amd_dbgapi_displaced_stepping_id_t stepping_id;
274 if (amd_dbgapi_displaced_stepping_start (
275 get_amd_dbgapi_process_id (), get_amd_dbgapi_wave_id (inferior_ptid),
276 buffer.get (), &stepping_id)
277 != AMD_DBGAPI_STATUS_SUCCESS)
278 return 0;
279
280 return stepping_id.handle;
281}
282
283static struct displaced_step_closure *
284amdgcn_rocm_displaced_step_copy_insn (struct gdbarch *gdbarch, CORE_ADDR from,
285 CORE_ADDR to, struct regcache *regcache)
286{
287 rocm_displaced_step_closure *closure = new rocm_displaced_step_closure;
288
289 closure->process_id = get_amd_dbgapi_process_id ();
290 closure->wave_id = get_amd_dbgapi_wave_id (inferior_ptid);
291 closure->displaced_stepping_id = { to };
292
293 return closure;
294}
295
296static void
297amdgcn_rocm_displaced_step_fixup (struct gdbarch *gdbarch,
298 struct displaced_step_closure *closure_,
299 CORE_ADDR from, CORE_ADDR to,
300 struct regcache *regcache)
301{
302 rocm_displaced_step_closure *closure
303 = reinterpret_cast<rocm_displaced_step_closure *> (closure_);
304
305 amd_dbgapi_status_t status = amd_dbgapi_displaced_stepping_complete (
306 closure->process_id, closure->wave_id, closure->displaced_stepping_id);
307
308 if (status != AMD_DBGAPI_STATUS_SUCCESS)
45f0bbf1
LM
309 error (_ ("amd_dbgapi_displaced_stepping_complete failed (rc=%d)"),
310 status);
abeeff98
LM
311
312 /* We may have written some registers, so flush the register cache. */
313 registers_changed_ptid (regcache->ptid ());
314}
315
316static int
317print_insn_amdgcn (bfd_vma memaddr, struct disassemble_info *di)
318{
319 gdb_disassembler *self
320 = static_cast<gdb_disassembler *> (di->application_data);
321
322 /* Try to read at most instruction_size bytes. */
323
324 amd_dbgapi_size_t instruction_size = gdbarch_max_insn_length (self->arch ());
325 gdb::unique_xmalloc_ptr<gdb_byte> buffer (
326 (gdb_byte *)xmalloc (instruction_size));
327
328 instruction_size
45f0bbf1 329 = target_read (current_top_target (), TARGET_OBJECT_CODE_MEMORY, NULL,
abeeff98 330 buffer.get (), memaddr, instruction_size);
45f0bbf1 331 if (instruction_size == TARGET_XFER_E_IO || instruction_size == 0)
abeeff98
LM
332 {
333 (*di->memory_error_func) (-1, memaddr, di);
334 return -1;
335 }
336
337 amd_dbgapi_architecture_id_t architecture_id;
338 if (amd_dbgapi_get_architecture (gdbarch_bfd_arch_info (self->arch ())->mach,
339 &architecture_id)
340 != AMD_DBGAPI_STATUS_SUCCESS)
341 return -1;
342
343 char *instruction_text = nullptr;
79803eff
LM
344
345 auto symbolizer
346 = [] (amd_dbgapi_symbolizer_id_t id, amd_dbgapi_global_address_t address,
347 char **symbol_text) -> amd_dbgapi_status_t {
348 string_file string;
349 print_address (reinterpret_cast<struct gdbarch *> (id), address, &string);
350 *symbol_text = xstrdup (string.c_str ());
351 return AMD_DBGAPI_STATUS_SUCCESS;
352 };
abeeff98
LM
353
354 if (amd_dbgapi_disassemble_instruction (
355 architecture_id, static_cast<amd_dbgapi_global_address_t> (memaddr),
79803eff
LM
356 &instruction_size, buffer.get (), &instruction_text,
357 reinterpret_cast<amd_dbgapi_symbolizer_id_t> (self->arch ()),
358 symbolizer)
abeeff98
LM
359 != AMD_DBGAPI_STATUS_SUCCESS)
360 {
361 size_t alignment;
362 if (amd_dbgapi_architecture_get_info (
363 architecture_id,
364 AMD_DBGAPI_ARCHITECTURE_INFO_MINIMUM_INSTRUCTION_ALIGNMENT,
365 sizeof (alignment), &alignment)
366 != AMD_DBGAPI_STATUS_SUCCESS)
367 error (_ ("amd_dbgapi_architecture_get_info failed"));
368
369 (*di->fprintf_func) (di->stream, "<illegal instruction>");
370 /* Skip to the next valid instruction address. */
371 return align_up (memaddr + 1, alignment) - memaddr;
372 }
373
374 /* Print the instruction. */
375 (*di->fprintf_func) (di->stream, "%s", instruction_text);
376
abeeff98
LM
377 /* Free the memory allocated by the amd-dbgapi. */
378 xfree (instruction_text);
abeeff98
LM
379
380 return static_cast<int> (instruction_size);
381}
382
383static CORE_ADDR
384amdgcn_skip_prologue (struct gdbarch *gdbarch, CORE_ADDR start_pc)
385{
386 CORE_ADDR func_addr;
387
388 /* See if we can determine the end of the prologue via the symbol table.
389 If so, then return either PC, or the PC after the prologue, whichever
390 is greater. */
391 if (find_pc_partial_function (start_pc, NULL, &func_addr, NULL))
392 {
393 CORE_ADDR post_prologue_pc
394 = skip_prologue_using_sal (gdbarch, func_addr);
395 struct compunit_symtab *cust = find_pc_compunit_symtab (func_addr);
396
397 /* Clang always emits a line note before the prologue and another
398 one after. We trust clang to emit usable line notes. */
399 if (post_prologue_pc
400 && (cust != NULL && COMPUNIT_PRODUCER (cust) != NULL
401 && startswith (COMPUNIT_PRODUCER (cust), "clang ")))
402 return std::max (start_pc, post_prologue_pc);
403 }
404
405 /* Can't determine prologue from the symbol table, need to examine
406 instructions. */
407
408 return start_pc;
409}
410
411static struct gdbarch *
412amdgcn_gdbarch_init (struct gdbarch_info info, struct gdbarch_list *arches)
413{
414 /* If there is already a candidate, use it. */
415 arches = gdbarch_list_lookup_by_info (arches, &info);
416 if (arches != NULL)
417 return arches->gdbarch;
418
419 struct gdbarch_deleter
420 {
421 void
422 operator() (struct gdbarch *gdbarch) const
423 {
424 gdbarch_free (gdbarch);
425 }
426 };
427
428 /* Allocate space for the new architecture. */
429 std::unique_ptr<struct gdbarch_tdep> tdep (new struct gdbarch_tdep);
430 std::unique_ptr<struct gdbarch, gdbarch_deleter> gdbarch_u (
431 gdbarch_alloc (&info, tdep.get ()));
432
433 struct gdbarch *gdbarch = gdbarch_u.get ();
434
435 /* Data types. */
436 set_gdbarch_char_signed (gdbarch, 0);
437 set_gdbarch_ptr_bit (gdbarch, 64);
438 set_gdbarch_addr_bit (gdbarch, 64);
439 set_gdbarch_short_bit (gdbarch, 16);
440 set_gdbarch_int_bit (gdbarch, 32);
441 set_gdbarch_long_bit (gdbarch, 64);
442 set_gdbarch_long_long_bit (gdbarch, 64);
443 set_gdbarch_float_bit (gdbarch, 32);
444 set_gdbarch_double_bit (gdbarch, 64);
445 set_gdbarch_long_double_bit (gdbarch, 128);
446 set_gdbarch_float_format (gdbarch, floatformats_ieee_single);
447 set_gdbarch_double_format (gdbarch, floatformats_ieee_double);
448 set_gdbarch_long_double_format (gdbarch, floatformats_ieee_double);
449
450 /* Frame Interpretation. */
451 set_gdbarch_skip_prologue (gdbarch, amdgcn_skip_prologue);
452 set_gdbarch_inner_than (gdbarch, core_addr_lessthan);
453 dwarf2_append_unwinders (gdbarch);
454 frame_unwind_append_unwinder (gdbarch, &amdgcn_frame_unwind);
455 set_gdbarch_dummy_id (gdbarch, amdgcn_dummy_id);
456
457 /* Registers and Memory. */
458 amd_dbgapi_architecture_id_t architecture_id;
459 if (amd_dbgapi_get_architecture (gdbarch_bfd_arch_info (gdbarch)->mach,
460 &architecture_id)
461 != AMD_DBGAPI_STATUS_SUCCESS)
462 return nullptr;
463
464 size_t register_class_count;
465 amd_dbgapi_register_class_id_t *register_class_ids;
466
467 if (amd_dbgapi_architecture_register_class_list (
468 architecture_id, &register_class_count, &register_class_ids)
469 != AMD_DBGAPI_STATUS_SUCCESS)
470 return nullptr;
471
472 /* Add register groups. */
473 reggroup_add (gdbarch, all_reggroup);
474
475 for (size_t i = 0; i < register_class_count; ++i)
476 {
477 char *bytes;
478 if (amd_dbgapi_architecture_register_class_get_info (
479 architecture_id, register_class_ids[i],
480 AMD_DBGAPI_REGISTER_CLASS_INFO_NAME, sizeof (bytes), &bytes)
481 != AMD_DBGAPI_STATUS_SUCCESS)
482 continue;
483
484 gdb::unique_xmalloc_ptr<char> name (bytes);
485
486 auto inserted = tdep->register_class_map.emplace (name.get (),
487 register_class_ids[i]);
488
489 if (!inserted.second)
490 continue;
491
492 /* Allocate the reggroup in the gdbarch. */
493 auto *group = reggroup_gdbarch_new (gdbarch, name.get (), USER_REGGROUP);
494 if (!group)
495 {
496 tdep->register_class_map.erase (inserted.first);
497 continue;
498 }
499
500 reggroup_add (gdbarch, group);
501 }
502 xfree (register_class_ids);
503
504 /* Add registers. */
505 size_t register_count;
506 amd_dbgapi_register_id_t *register_ids;
507
508 if (amd_dbgapi_architecture_register_list (architecture_id, &register_count,
509 &register_ids)
510 != AMD_DBGAPI_STATUS_SUCCESS)
511 return nullptr;
512
513 tdep->register_ids.insert (tdep->register_ids.end (), &register_ids[0],
514 &register_ids[register_count]);
515
516 set_gdbarch_num_regs (gdbarch, register_count);
517 set_gdbarch_num_pseudo_regs (gdbarch, 0);
518 xfree (register_ids);
519
520 tdep->register_names.resize (register_count);
521 for (size_t i = 0; i < register_count; ++i)
522 {
523 if (!tdep->regnum_map.emplace (tdep->register_ids[i], i).second)
524 return nullptr;
525
526 char *bytes;
527 if (amd_dbgapi_architecture_register_get_info (
528 architecture_id, tdep->register_ids[i],
529 AMD_DBGAPI_REGISTER_INFO_NAME, sizeof (bytes), &bytes)
530 != AMD_DBGAPI_STATUS_SUCCESS)
531 continue;
532
533 tdep->register_names[i] = bytes;
534 xfree (bytes);
535 }
536
537 amd_dbgapi_register_id_t pc_register_id;
538 if (amd_dbgapi_architecture_get_info (
539 architecture_id, AMD_DBGAPI_ARCHITECTURE_INFO_PC_REGISTER,
540 sizeof (pc_register_id), &pc_register_id)
541 != AMD_DBGAPI_STATUS_SUCCESS)
542 return nullptr;
543
544 set_gdbarch_pc_regnum (gdbarch, tdep->regnum_map[pc_register_id]);
545 set_gdbarch_ps_regnum (gdbarch, -1);
546 set_gdbarch_sp_regnum (gdbarch, -1);
547 set_gdbarch_fp0_regnum (gdbarch, -1);
548
549 set_gdbarch_dwarf2_reg_to_regnum (gdbarch, amdgcn_dwarf_reg_to_regnum);
550
551 /* Register Representation. */
552 set_gdbarch_register_name (gdbarch, amdgcn_register_name);
553 set_gdbarch_register_type (gdbarch, amdgcn_register_type);
554 set_gdbarch_register_reggroup_p (gdbarch, amdgcn_register_reggroup_p);
555
556 /* Disassembly. */
557 set_gdbarch_print_insn (gdbarch, print_insn_amdgcn);
558
559 /* Displaced stepping. */
560 set_gdbarch_displaced_step_location (gdbarch,
561 amdgcn_rocm_displaced_step_location);
562
563 set_gdbarch_displaced_step_copy_insn (gdbarch,
564 amdgcn_rocm_displaced_step_copy_insn);
565 set_gdbarch_displaced_step_fixup (gdbarch, amdgcn_rocm_displaced_step_fixup);
566
567 /* Instructions. */
568 amd_dbgapi_size_t max_insn_length = 0;
569 if (amd_dbgapi_architecture_get_info (
570 architecture_id,
571 AMD_DBGAPI_ARCHITECTURE_INFO_LARGEST_INSTRUCTION_SIZE,
572 sizeof (max_insn_length), &max_insn_length)
573 != AMD_DBGAPI_STATUS_SUCCESS)
574 error (_ ("amd_dbgapi_architecture_get_info failed"));
575
576 set_gdbarch_max_insn_length (gdbarch, max_insn_length);
577
578 if (amd_dbgapi_architecture_get_info (
579 architecture_id,
580 AMD_DBGAPI_ARCHITECTURE_INFO_BREAKPOINT_INSTRUCTION_SIZE,
581 sizeof (tdep->breakpoint_instruction_size),
582 &tdep->breakpoint_instruction_size)
583 != AMD_DBGAPI_STATUS_SUCCESS)
584 error (_ ("amd_dbgapi_architecture_get_info failed"));
585
586 gdb_byte *breakpoint_instruction_bytes;
587 if (amd_dbgapi_architecture_get_info (
588 architecture_id, AMD_DBGAPI_ARCHITECTURE_INFO_BREAKPOINT_INSTRUCTION,
45f0bbf1 589 sizeof (breakpoint_instruction_bytes), &breakpoint_instruction_bytes)
abeeff98
LM
590 != AMD_DBGAPI_STATUS_SUCCESS)
591 error (_ ("amd_dbgapi_architecture_get_info failed"));
592
593 tdep->breakpoint_instruction_bytes.reset (breakpoint_instruction_bytes);
594
595 set_gdbarch_breakpoint_kind_from_pc (gdbarch,
596 amdgcn_breakpoint_kind_from_pc);
597 set_gdbarch_sw_breakpoint_from_kind (gdbarch,
598 amdgcn_sw_breakpoint_from_kind);
599
600 tdep.release ();
601 gdbarch_u.release ();
602
603 return gdbarch;
604}
605
606/* Provide a prototype to silence -Wmissing-prototypes. */
607extern initialize_file_ftype _initialize_amdgcn_rocm_tdep;
608
609void
610_initialize_amdgcn_rocm_tdep (void)
611{
612 gdbarch_register (bfd_arch_amdgcn, amdgcn_gdbarch_init, NULL);
613}
This page took 0.056083 seconds and 4 git commands to generate.