X-Git-Url: https://git.proxmox.com/?a=blobdiff_plain;f=disas.c;h=b801c8f51d4f1d8eae072ff18d6a26e37514cc83;hb=a63eb7a22731c4b0ec863582231f24c4b32b5969;hp=1334b8e0f369089a21c403fcde11a0a726b0aa0b;hpb=cd59dd8734bebe5bd06be8a3fa79a9f4facf6633;p=qemu.git diff --git a/disas.c b/disas.c index 1334b8e0f..b801c8f51 100644 --- a/disas.c +++ b/disas.c @@ -51,7 +51,7 @@ perror_memory (int status, bfd_vma memaddr, struct disassemble_info *info) "Address 0x%" PRIx64 " is out of bounds.\n", memaddr); } -/* This could be in a separate file, to save miniscule amounts of space +/* This could be in a separate file, to save minuscule amounts of space in statically linked executables. */ /* Just print the address is hex. This is included for completeness even @@ -64,6 +64,22 @@ generic_print_address (bfd_vma addr, struct disassemble_info *info) (*info->fprintf_func) (info->stream, "0x%" PRIx64, addr); } +/* Print address in hex, truncated to the width of a target virtual address. */ +static void +generic_print_target_address(bfd_vma addr, struct disassemble_info *info) +{ + uint64_t mask = ~0ULL >> (64 - TARGET_VIRT_ADDR_SPACE_BITS); + generic_print_address(addr & mask, info); +} + +/* Print address in hex, truncated to the width of a host virtual address. */ +static void +generic_print_host_address(bfd_vma addr, struct disassemble_info *info) +{ + uint64_t mask = ~0ULL >> (64 - (sizeof(void *) * 8)); + generic_print_address(addr & mask, info); +} + /* Just return the given address. */ int @@ -137,8 +153,8 @@ print_insn_thumb1(bfd_vma pc, disassemble_info *info) /* Disassemble this for me please... (debugging). 'flags' has the following values: - i386 - nonzero means 16 bit code - arm - nonzero means thumb code + i386 - 1 means 16 bit code, 2 means 64 bit code + arm - bit 0 = thumb, bit 1 = reverse endian ppc - nonzero means little endian other targets - unused */ @@ -154,6 +170,7 @@ void target_disas(FILE *out, target_ulong code, target_ulong size, int flags) disasm_info.read_memory_func = target_read_memory; disasm_info.buffer_vma = code; disasm_info.buffer_length = size; + disasm_info.print_address_func = generic_print_target_address; #ifdef TARGET_WORDS_BIGENDIAN disasm_info.endian = BFD_ENDIAN_BIG; @@ -169,10 +186,18 @@ void target_disas(FILE *out, target_ulong code, target_ulong size, int flags) disasm_info.mach = bfd_mach_i386_i386; print_insn = print_insn_i386; #elif defined(TARGET_ARM) - if (flags) - print_insn = print_insn_thumb1; - else - print_insn = print_insn_arm; + if (flags & 1) { + print_insn = print_insn_thumb1; + } else { + print_insn = print_insn_arm; + } + if (flags & 2) { +#ifdef TARGET_WORDS_BIGENDIAN + disasm_info.endian = BFD_ENDIAN_LITTLE; +#else + disasm_info.endian = BFD_ENDIAN_BIG; +#endif + } #elif defined(TARGET_SPARC) print_insn = print_insn_sparc; #ifdef TARGET_SPARC64 @@ -220,6 +245,9 @@ void target_disas(FILE *out, target_ulong code, target_ulong size, int flags) #elif defined(TARGET_MICROBLAZE) disasm_info.mach = bfd_arch_microblaze; print_insn = print_insn_microblaze; +#elif defined(TARGET_LM32) + disasm_info.mach = bfd_mach_lm32; + print_insn = print_insn_lm32; #else fprintf(out, "0x" TARGET_FMT_lx ": Asm output not supported on this arch\n", code); @@ -257,15 +285,16 @@ void target_disas(FILE *out, target_ulong code, target_ulong size, int flags) /* Disassemble this for me please... (debugging). */ void disas(FILE *out, void *code, unsigned long size) { - unsigned long pc; + uintptr_t pc; int count; struct disassemble_info disasm_info; int (*print_insn)(bfd_vma pc, disassemble_info *info); INIT_DISASSEMBLE_INFO(disasm_info, out, fprintf); + disasm_info.print_address_func = generic_print_host_address; disasm_info.buffer = code; - disasm_info.buffer_vma = (unsigned long)code; + disasm_info.buffer_vma = (uintptr_t)code; disasm_info.buffer_length = size; #ifdef HOST_WORDS_BIGENDIAN @@ -273,7 +302,9 @@ void disas(FILE *out, void *code, unsigned long size) #else disasm_info.endian = BFD_ENDIAN_LITTLE; #endif -#if defined(__i386__) +#if defined(CONFIG_TCG_INTERPRETER) + print_insn = print_insn_tci; +#elif defined(__i386__) disasm_info.mach = bfd_mach_i386_i386; print_insn = print_insn_i386; #elif defined(__x86_64__) @@ -285,9 +316,7 @@ void disas(FILE *out, void *code, unsigned long size) print_insn = print_insn_alpha; #elif defined(__sparc__) print_insn = print_insn_sparc; -#if defined(__sparc_v8plus__) || defined(__sparc_v8plusa__) || defined(__sparc_v9__) disasm_info.mach = bfd_mach_sparc_v9b; -#endif #elif defined(__arm__) print_insn = print_insn_arm; #elif defined(__MIPSEB__) @@ -307,8 +336,8 @@ void disas(FILE *out, void *code, unsigned long size) (long) code); return; #endif - for (pc = (unsigned long)code; size > 0; pc += count, size -= count) { - fprintf(out, "0x%08lx: ", pc); + for (pc = (uintptr_t)code; size > 0; pc += count, size -= count) { + fprintf(out, "0x%08" PRIxPTR ": ", pc); count = print_insn(pc, &disasm_info); fprintf(out, "\n"); if (count < 0) @@ -337,7 +366,7 @@ const char *lookup_symbol(target_ulong orig_addr) #include "monitor.h" static int monitor_disas_is_physical; -static CPUState *monitor_disas_env; +static CPUArchState *monitor_disas_env; static int monitor_read_memory (bfd_vma memaddr, bfd_byte *myaddr, int length, @@ -361,7 +390,7 @@ monitor_fprintf(FILE *stream, const char *fmt, ...) return 0; } -void monitor_disas(Monitor *mon, CPUState *env, +void monitor_disas(Monitor *mon, CPUArchState *env, target_ulong pc, int nb_insn, int is_physical, int flags) { int count, i; @@ -373,6 +402,7 @@ void monitor_disas(Monitor *mon, CPUState *env, monitor_disas_env = env; monitor_disas_is_physical = is_physical; disasm_info.read_memory_func = monitor_read_memory; + disasm_info.print_address_func = generic_print_target_address; disasm_info.buffer_vma = pc; @@ -419,6 +449,9 @@ void monitor_disas(Monitor *mon, CPUState *env, #elif defined(TARGET_S390X) disasm_info.mach = bfd_mach_s390_64; print_insn = print_insn_s390; +#elif defined(TARGET_LM32) + disasm_info.mach = bfd_mach_lm32; + print_insn = print_insn_lm32; #else monitor_printf(mon, "0x" TARGET_FMT_lx ": Asm output not supported on this arch\n", pc);