2 * Functions related to disassembly from the monitor
4 * SPDX-License-Identifier: GPL-2.0-or-later
7 #include "qemu/osdep.h"
8 #include "disas-internal.h"
9 #include "disas/disas.h"
10 #include "exec/memory.h"
11 #include "hw/core/cpu.h"
12 #include "monitor/monitor.h"
15 * Get LENGTH bytes from info's buffer, at target address memaddr.
16 * Transfer them to myaddr.
19 virtual_read_memory(bfd_vma memaddr
, bfd_byte
*myaddr
, int length
,
20 struct disassemble_info
*info
)
22 CPUDebug
*s
= container_of(info
, CPUDebug
, info
);
23 int r
= cpu_memory_rw_debug(s
->cpu
, memaddr
, myaddr
, length
, 0);
28 physical_read_memory(bfd_vma memaddr
, bfd_byte
*myaddr
, int length
,
29 struct disassemble_info
*info
)
31 CPUDebug
*s
= container_of(info
, CPUDebug
, info
);
34 res
= address_space_read(s
->cpu
->as
, memaddr
, MEMTXATTRS_UNSPECIFIED
,
36 return res
== MEMTX_OK
? 0 : EIO
;
39 /* Disassembler for the monitor. */
40 void monitor_disas(Monitor
*mon
, CPUState
*cpu
, uint64_t pc
,
41 int nb_insn
, bool is_physical
)
45 g_autoptr(GString
) ds
= g_string_new("");
47 disas_initialize_debug_target(&s
, cpu
);
48 s
.info
.fprintf_func
= disas_gstring_printf
;
49 s
.info
.stream
= (FILE *)ds
; /* abuse this slot */
50 s
.info
.show_opcodes
= true;
53 s
.info
.read_memory_func
= physical_read_memory
;
55 s
.info
.read_memory_func
= virtual_read_memory
;
57 s
.info
.buffer_vma
= pc
;
59 if (s
.info
.cap_arch
>= 0 && cap_disas_monitor(&s
.info
, pc
, nb_insn
)) {
60 monitor_puts(mon
, ds
->str
);
64 if (!s
.info
.print_insn
) {
65 monitor_printf(mon
, "0x%08" PRIx64
66 ": Asm output not supported on this arch\n", pc
);
70 for (i
= 0; i
< nb_insn
; i
++) {
71 g_string_append_printf(ds
, "0x%08" PRIx64
": ", pc
);
72 count
= s
.info
.print_insn(pc
, &s
.info
);
73 g_string_append_c(ds
, '\n');
80 monitor_puts(mon
, ds
->str
);