All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH v2 00/10] capstone + disassembler patches
@ 2020-09-14 23:02 Richard Henderson
  2020-09-14 23:02 ` [PATCH v2 01/10] capstone: Convert Makefile bits to meson bits Richard Henderson
                   ` (9 more replies)
  0 siblings, 10 replies; 29+ messages in thread
From: Richard Henderson @ 2020-09-14 23:02 UTC (permalink / raw)
  To: qemu-devel; +Cc: luoyonggang, alex.bennee, thuth

The primary change here is the update for capstone to meson.
This bypasses capstone's build system entirely.  There's more
commentary on that subject with the first patch.

Plus a collection of other fixes and cleanups in the area.

Changes for v2:
  * Several configury changes in patch 1, along the lines
    of that suggested by Paolo, but not exactly the same.
  * Drop sparc capstone enablement (I suddenly have a memory
    of doing the same thing last year).


r~


Richard Henderson (10):
  capstone: Convert Makefile bits to meson bits
  capstone: Update to upstream "next" branch
  disas: Move host asm annotations to tb_gen_code
  disas: Clean up CPUDebug initialization
  disas: Use qemu/bswap.h for bfd endian loads
  disas: Cleanup plugin_disas
  disas: Configure capstone for aarch64 host without libvixl
  disas: Split out capstone code to disas/capstone.c
  disas: Enable capstone disassembly for s390x
  disas/capstone: Add skipdata hook for s390x

 configure                 |  61 +---
 Makefile                  |  16 -
 include/disas/dis-asm.h   | 102 +++---
 include/disas/disas.h     |   2 +-
 include/exec/log.h        |   4 +-
 accel/tcg/translate-all.c |  24 +-
 disas.c                   | 703 +++++++++-----------------------------
 disas/capstone.c          | 326 ++++++++++++++++++
 target/s390x/cpu.c        |   4 +
 tcg/tcg.c                 |   4 +-
 capstone                  |   2 +-
 disas/meson.build         |   1 +
 meson.build               | 122 ++++++-
 meson_options.txt         |   4 +
 14 files changed, 676 insertions(+), 699 deletions(-)
 create mode 100644 disas/capstone.c

-- 
2.25.1



^ permalink raw reply	[flat|nested] 29+ messages in thread

* [PATCH v2 01/10] capstone: Convert Makefile bits to meson bits
  2020-09-14 23:02 [PATCH v2 00/10] capstone + disassembler patches Richard Henderson
@ 2020-09-14 23:02 ` Richard Henderson
  2020-09-14 23:06   ` Richard Henderson
  2020-09-15  6:10   ` Thomas Huth
  2020-09-14 23:02 ` [PATCH v2 02/10] capstone: Update to upstream "next" branch Richard Henderson
                   ` (8 subsequent siblings)
  9 siblings, 2 replies; 29+ messages in thread
From: Richard Henderson @ 2020-09-14 23:02 UTC (permalink / raw)
  To: qemu-devel; +Cc: Paolo Bonzini, luoyonggang, alex.bennee, thuth

There are better ways to do this, e.g. meson cmake subproject,
but that requires cmake 3.7 and some of our CI environments
only provide cmake 3.5.

Nor can we add a meson.build file to capstone/, because the git
submodule would then always report "untracked files".  Fixing that
would require creating our own branch on the qemu git mirror, at
which point we could just as easily create a native meson subproject.

Instead, build the library via the main meson.build.

This improves the current state of affairs in that we will re-link
the qemu executables against a changed libcapstone.a, which we wouldn't
do before-hand.  In addition, the use of the confuration header file
instead of command-line -DEFINES means that we will rebuild the
capstone objects with changes to meson.build.

Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
Cc: Paolo Bonzini <pbonzini@redhat.com>
v2: Further reduce probing in configure (paolo),
    Drop state 'internal' and use 'git' even when it isn't git.
    Move CONFIG_CAPSTONE to config_host_data.
---
 configure         |  61 +++-----------------------
 Makefile          |  16 -------
 meson.build       | 109 +++++++++++++++++++++++++++++++++++++++++++---
 meson_options.txt |   4 ++
 4 files changed, 113 insertions(+), 77 deletions(-)

diff --git a/configure b/configure
index ce27eafb0a..1fd80ed699 100755
--- a/configure
+++ b/configure
@@ -469,7 +469,7 @@ opengl=""
 opengl_dmabuf="no"
 cpuid_h="no"
 avx2_opt=""
-capstone=""
+capstone="auto"
 lzo=""
 snappy=""
 bzip2=""
@@ -1573,7 +1573,7 @@ for opt do
   ;;
   --enable-capstone) capstone="yes"
   ;;
-  --enable-capstone=git) capstone="git"
+  --enable-capstone=git) capstone="internal"
   ;;
   --enable-capstone=system) capstone="system"
   ;;
@@ -5124,51 +5124,11 @@ fi
 # capstone
 
 case "$capstone" in
-  "" | yes)
-    if $pkg_config capstone; then
-      capstone=system
-    elif test -e "${source_path}/.git" && test $git_update = 'yes' ; then
-      capstone=git
-    elif test -e "${source_path}/capstone/Makefile" ; then
-      capstone=internal
-    elif test -z "$capstone" ; then
-      capstone=no
-    else
-      feature_not_found "capstone" "Install capstone devel or git submodule"
-    fi
-    ;;
-
-  system)
-    if ! $pkg_config capstone; then
-      feature_not_found "capstone" "Install capstone devel"
-    fi
-    ;;
-esac
-
-case "$capstone" in
-  git | internal)
-    if test "$capstone" = git; then
+  auto | yes | internal)
+    # Simpler to always update submodule, even if not needed.
+    if test -e "${source_path}/.git" && test $git_update = 'yes' ; then
       git_submodules="${git_submodules} capstone"
     fi
-    mkdir -p capstone
-    if test "$mingw32" = "yes"; then
-      LIBCAPSTONE=capstone.lib
-    else
-      LIBCAPSTONE=libcapstone.a
-    fi
-    capstone_libs="-Lcapstone -lcapstone"
-    capstone_cflags="-I${source_path}/capstone/include"
-    ;;
-
-  system)
-    capstone_libs="$($pkg_config --libs capstone)"
-    capstone_cflags="$($pkg_config --cflags capstone)"
-    ;;
-
-  no)
-    ;;
-  *)
-    error_exit "Unknown state for capstone: $capstone"
     ;;
 esac
 
@@ -7288,11 +7248,6 @@ fi
 if test "$ivshmem" = "yes" ; then
   echo "CONFIG_IVSHMEM=y" >> $config_host_mak
 fi
-if test "$capstone" != "no" ; then
-  echo "CONFIG_CAPSTONE=y" >> $config_host_mak
-  echo "CAPSTONE_CFLAGS=$capstone_cflags" >> $config_host_mak
-  echo "CAPSTONE_LIBS=$capstone_libs" >> $config_host_mak
-fi
 if test "$debug_mutex" = "yes" ; then
   echo "CONFIG_DEBUG_MUTEX=y" >> $config_host_mak
 fi
@@ -7816,9 +7771,6 @@ done # for target in $targets
 if [ "$fdt" = "git" ]; then
   subdirs="$subdirs dtc"
 fi
-if [ "$capstone" = "git" -o "$capstone" = "internal" ]; then
-  subdirs="$subdirs capstone"
-fi
 echo "SUBDIRS=$subdirs" >> $config_host_mak
 if test -n "$LIBCAPSTONE"; then
   echo "LIBCAPSTONE=$LIBCAPSTONE" >> $config_host_mak
@@ -8005,7 +7957,8 @@ NINJA=${ninja:-$PWD/ninjatool} $meson setup \
         -Db_coverage=$(if test "$gcov" = yes; then echo true; else echo false; fi) \
 	-Dsdl=$sdl -Dsdl_image=$sdl_image \
 	-Dvnc=$vnc -Dvnc_sasl=$vnc_sasl -Dvnc_jpeg=$vnc_jpeg -Dvnc_png=$vnc_png \
-	-Dgettext=$gettext -Dxkbcommon=$xkbcommon -Du2f=$u2f\
+	-Dgettext=$gettext -Dxkbcommon=$xkbcommon -Du2f=$u2f \
+	-Dcapstone=$capstone \
         $cross_arg \
         "$PWD" "$source_path"
 
diff --git a/Makefile b/Makefile
index 7c60b9dcb8..f3da1760ad 100644
--- a/Makefile
+++ b/Makefile
@@ -156,22 +156,6 @@ dtc/all: .git-submodule-status dtc/libfdt
 dtc/%: .git-submodule-status
 	@mkdir -p $@
 
-# Overriding CFLAGS causes us to lose defines added in the sub-makefile.
-# Not overriding CFLAGS leads to mis-matches between compilation modes.
-# Therefore we replicate some of the logic in the sub-makefile.
-# Remove all the extra -Warning flags that QEMU uses that Capstone doesn't;
-# no need to annoy QEMU developers with such things.
-CAP_CFLAGS = $(patsubst -W%,,$(CFLAGS) $(QEMU_CFLAGS)) $(CAPSTONE_CFLAGS)
-CAP_CFLAGS += -DCAPSTONE_USE_SYS_DYN_MEM
-CAP_CFLAGS += -DCAPSTONE_HAS_ARM
-CAP_CFLAGS += -DCAPSTONE_HAS_ARM64
-CAP_CFLAGS += -DCAPSTONE_HAS_POWERPC
-CAP_CFLAGS += -DCAPSTONE_HAS_X86
-
-.PHONY: capstone/all
-capstone/all: .git-submodule-status
-	$(call quiet-command,$(MAKE) -C $(SRC_PATH)/capstone CAPSTONE_SHARED=no BUILDDIR="$(BUILD_DIR)/capstone" CC="$(CC)" AR="$(AR)" LD="$(LD)" RANLIB="$(RANLIB)" CFLAGS="$(CAP_CFLAGS)" $(SUBDIR_MAKEFLAGS) $(BUILD_DIR)/capstone/$(LIBCAPSTONE))
-
 .PHONY: slirp/all
 slirp/all: .git-submodule-status
 	$(call quiet-command,$(MAKE) -C $(SRC_PATH)/slirp		\
diff --git a/meson.build b/meson.build
index 690723b470..df7d2eb52f 100644
--- a/meson.build
+++ b/meson.build
@@ -10,6 +10,7 @@ else
   keyval = import('unstable-keyval')
 endif
 ss = import('sourceset')
+fs = import('fs')
 
 sh = find_program('sh')
 cc = meson.get_compiler('c')
@@ -415,11 +416,6 @@ if 'CONFIG_USB_LIBUSB' in config_host
   libusb = declare_dependency(compile_args: config_host['LIBUSB_CFLAGS'].split(),
                               link_args: config_host['LIBUSB_LIBS'].split())
 endif
-capstone = not_found
-if 'CONFIG_CAPSTONE' in config_host
-  capstone = declare_dependency(compile_args: config_host['CAPSTONE_CFLAGS'].split(),
-                                link_args: config_host['CAPSTONE_LIBS'].split())
-endif
 libpmem = not_found
 if 'CONFIG_LIBPMEM' in config_host
   libpmem = declare_dependency(compile_args: config_host['LIBPMEM_CFLAGS'].split(),
@@ -476,7 +472,6 @@ foreach k, v: config_host
     config_host_data.set(k, v == 'y' ? 1 : v)
   endif
 endforeach
-genh += configure_file(output: 'config-host.h', configuration: config_host_data)
 
 minikconf = find_program('scripts/minikconf.py')
 config_all_devices = {}
@@ -616,6 +611,106 @@ config_all += {
   'CONFIG_ALL': true,
 }
 
+capstone = not_found
+capstone_opt = get_option('capstone')
+if capstone_opt == 'no'
+  capstone_opt = false
+elif capstone_opt in ['yes', 'auto', 'system']
+  have_internal = fs.exists('capstone/Makefile')
+  capstone = dependency('capstone', static: enable_static,
+                        required: capstone_opt == 'system' or
+                                  capstone_opt == 'yes' and not have_internal)
+  if capstone.found()
+    capstone_opt = 'system'
+  elif have_internal
+    capstone_opt = 'internal'
+  else
+    capstone_opt = false
+  endif
+endif
+if capstone_opt == 'internal'
+  capstone_data = configuration_data()
+  capstone_data.set('CAPSTONE_USE_SYS_DYN_MEM', '1')
+
+  capstone_files = files(
+    'capstone/cs.c',
+    'capstone/MCInst.c',
+    'capstone/MCInstrDesc.c',
+    'capstone/MCRegisterInfo.c',
+    'capstone/SStream.c',
+    'capstone/utils.c'
+  )
+
+  if 'CONFIG_ARM_DIS' in config_all_disas
+    capstone_data.set('CAPSTONE_HAS_ARM', '1')
+    capstone_files += files(
+      'capstone/arch/ARM/ARMDisassembler.c',
+      'capstone/arch/ARM/ARMInstPrinter.c',
+      'capstone/arch/ARM/ARMMapping.c',
+      'capstone/arch/ARM/ARMModule.c'
+    )
+  endif
+
+  # FIXME: This config entry currently depends on a c++ compiler.
+  # Which is needed for building libvixl, but not for capstone.
+  if 'CONFIG_ARM_A64_DIS' in config_all_disas
+    capstone_data.set('CAPSTONE_HAS_ARM64', '1')
+    capstone_files += files(
+      'capstone/arch/AArch64/AArch64BaseInfo.c',
+      'capstone/arch/AArch64/AArch64Disassembler.c',
+      'capstone/arch/AArch64/AArch64InstPrinter.c',
+      'capstone/arch/AArch64/AArch64Mapping.c',
+      'capstone/arch/AArch64/AArch64Module.c'
+    )
+  endif
+
+  if 'CONFIG_PPC_DIS' in config_all_disas
+    capstone_data.set('CAPSTONE_HAS_POWERPC', '1')
+    capstone_files += files(
+      'capstone/arch/PowerPC/PPCDisassembler.c',
+      'capstone/arch/PowerPC/PPCInstPrinter.c',
+      'capstone/arch/PowerPC/PPCMapping.c',
+      'capstone/arch/PowerPC/PPCModule.c'
+    )
+  endif
+
+  if 'CONFIG_I386_DIS' in config_all_disas
+    capstone_data.set('CAPSTONE_HAS_X86', 1)
+    capstone_files += files(
+      'capstone/arch/X86/X86Disassembler.c',
+      'capstone/arch/X86/X86DisassemblerDecoder.c',
+      'capstone/arch/X86/X86ATTInstPrinter.c',
+      'capstone/arch/X86/X86IntelInstPrinter.c',
+      'capstone/arch/X86/X86Mapping.c',
+      'capstone/arch/X86/X86Module.c'
+    )
+  endif
+
+  configure_file(output: 'capstone-defs.h', configuration: capstone_data)
+
+  capstone_cargs = [
+    # FIXME: There does not seem to be a way to completely replace the c_args
+    # that come from add_project_arguments() -- we can only add to them.
+    # So: disable all warnings with a big hammer.
+    '-Wno-error', '-w',
+
+    # Include all configuration defines via a header file, which will wind up
+    # as a dependency on the object file, and thus changes here will result
+    # in a rebuild.
+    '-include', 'capstone-defs.h'
+  ]
+
+  libcapstone = static_library('capstone',
+                               sources: capstone_files,
+                               c_args: capstone_cargs,
+                               include_directories: 'capstone/include')
+  capstone = declare_dependency(link_with: libcapstone,
+                                include_directories: 'capstone/include')
+endif
+config_host_data.set('CONFIG_CAPSTONE', capstone.found())
+
+genh += configure_file(output: 'config-host.h', configuration: config_host_data)
+
 # Generators
 
 hxtool = find_program('scripts/hxtool')
@@ -1518,7 +1613,7 @@ summary_info += {'vvfat support':     config_host.has_key('CONFIG_VVFAT')}
 summary_info += {'qed support':       config_host.has_key('CONFIG_QED')}
 summary_info += {'parallels support': config_host.has_key('CONFIG_PARALLELS')}
 summary_info += {'sheepdog support':  config_host.has_key('CONFIG_SHEEPDOG')}
-summary_info += {'capstone':          config_host.has_key('CONFIG_CAPSTONE')}
+summary_info += {'capstone':          capstone_opt}
 summary_info += {'libpmem support':   config_host.has_key('CONFIG_LIBPMEM')}
 summary_info += {'libdaxctl support': config_host.has_key('CONFIG_LIBDAXCTL')}
 summary_info += {'libudev':           config_host.has_key('CONFIG_LIBUDEV')}
diff --git a/meson_options.txt b/meson_options.txt
index 543cf70043..f6a1b8ad21 100644
--- a/meson_options.txt
+++ b/meson_options.txt
@@ -22,3 +22,7 @@ option('vnc_sasl', type : 'feature', value : 'auto',
        description: 'SASL authentication for VNC server')
 option('xkbcommon', type : 'feature', value : 'auto',
        description: 'xkbcommon support')
+
+option('capstone', type: 'combo', value: 'no',
+       choices: ['no', 'yes', 'auto', 'system', 'internal'],
+       description: 'Whether and how to find the capstone library')
-- 
2.25.1



^ permalink raw reply related	[flat|nested] 29+ messages in thread

* [PATCH v2 02/10] capstone: Update to upstream "next" branch
  2020-09-14 23:02 [PATCH v2 00/10] capstone + disassembler patches Richard Henderson
  2020-09-14 23:02 ` [PATCH v2 01/10] capstone: Convert Makefile bits to meson bits Richard Henderson
@ 2020-09-14 23:02 ` Richard Henderson
  2020-09-14 23:02 ` [PATCH v2 03/10] disas: Move host asm annotations to tb_gen_code Richard Henderson
                   ` (7 subsequent siblings)
  9 siblings, 0 replies; 29+ messages in thread
From: Richard Henderson @ 2020-09-14 23:02 UTC (permalink / raw)
  To: qemu-devel; +Cc: luoyonggang, alex.bennee, thuth, Philippe Mathieu-Daudé

This branch contains a number of improvements over master,
including making all of the disassembler data constant.

We are skipping past the 4.0 branchpoint, which changed
the location of the includes within the source directory.

Tested-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
 capstone    | 2 +-
 meson.build | 3 ++-
 2 files changed, 3 insertions(+), 2 deletions(-)

diff --git a/capstone b/capstone
index 22ead3e0bf..f8b1b83301 160000
--- a/capstone
+++ b/capstone
@@ -1 +1 @@
-Subproject commit 22ead3e0bfdb87516656453336160e0a37b066bf
+Subproject commit f8b1b833015a4ae47110ed068e0deb7106ced66d
diff --git a/meson.build b/meson.build
index df7d2eb52f..cbb8257d6b 100644
--- a/meson.build
+++ b/meson.build
@@ -681,6 +681,7 @@ if capstone_opt == 'internal'
       'capstone/arch/X86/X86DisassemblerDecoder.c',
       'capstone/arch/X86/X86ATTInstPrinter.c',
       'capstone/arch/X86/X86IntelInstPrinter.c',
+      'capstone/arch/X86/X86InstPrinterCommon.c',
       'capstone/arch/X86/X86Mapping.c',
       'capstone/arch/X86/X86Module.c'
     )
@@ -705,7 +706,7 @@ if capstone_opt == 'internal'
                                c_args: capstone_cargs,
                                include_directories: 'capstone/include')
   capstone = declare_dependency(link_with: libcapstone,
-                                include_directories: 'capstone/include')
+                                include_directories: 'capstone/include/capstone')
 endif
 config_host_data.set('CONFIG_CAPSTONE', capstone.found())
 
-- 
2.25.1



^ permalink raw reply related	[flat|nested] 29+ messages in thread

* [PATCH v2 03/10] disas: Move host asm annotations to tb_gen_code
  2020-09-14 23:02 [PATCH v2 00/10] capstone + disassembler patches Richard Henderson
  2020-09-14 23:02 ` [PATCH v2 01/10] capstone: Convert Makefile bits to meson bits Richard Henderson
  2020-09-14 23:02 ` [PATCH v2 02/10] capstone: Update to upstream "next" branch Richard Henderson
@ 2020-09-14 23:02 ` Richard Henderson
  2020-09-15 16:36   ` Thomas Huth
  2020-09-14 23:02 ` [PATCH v2 04/10] disas: Clean up CPUDebug initialization Richard Henderson
                   ` (6 subsequent siblings)
  9 siblings, 1 reply; 29+ messages in thread
From: Richard Henderson @ 2020-09-14 23:02 UTC (permalink / raw)
  To: qemu-devel; +Cc: luoyonggang, alex.bennee, thuth

Instead of creating GStrings and passing them into log_disas,
just print the annotations directly in tb_gen_code.

Fix the annotations for the slow paths of the TB, after the
part implementing the final guest instruction.

Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
 include/disas/disas.h     |  2 +-
 include/exec/log.h        |  4 ++--
 accel/tcg/translate-all.c | 24 +++++++++++++++---------
 disas.c                   | 29 +++++++++--------------------
 tcg/tcg.c                 |  4 ++--
 5 files changed, 29 insertions(+), 34 deletions(-)

diff --git a/include/disas/disas.h b/include/disas/disas.h
index 1b6e035e32..36c33f6f19 100644
--- a/include/disas/disas.h
+++ b/include/disas/disas.h
@@ -7,7 +7,7 @@
 #include "cpu.h"
 
 /* Disassemble this for me please... (debugging). */
-void disas(FILE *out, void *code, unsigned long size, const char *note);
+void disas(FILE *out, void *code, unsigned long size);
 void target_disas(FILE *out, CPUState *cpu, target_ulong code,
                   target_ulong size);
 
diff --git a/include/exec/log.h b/include/exec/log.h
index 3ed797c1c8..fcc7b9e00b 100644
--- a/include/exec/log.h
+++ b/include/exec/log.h
@@ -56,13 +56,13 @@ static inline void log_target_disas(CPUState *cpu, target_ulong start,
     rcu_read_unlock();
 }
 
-static inline void log_disas(void *code, unsigned long size, const char *note)
+static inline void log_disas(void *code, unsigned long size)
 {
     QemuLogFile *logfile;
     rcu_read_lock();
     logfile = atomic_rcu_read(&qemu_logfile);
     if (logfile) {
-        disas(logfile->fd, code, size, note);
+        disas(logfile->fd, code, size);
     }
     rcu_read_unlock();
 }
diff --git a/accel/tcg/translate-all.c b/accel/tcg/translate-all.c
index 2d83013633..2874104a6a 100644
--- a/accel/tcg/translate-all.c
+++ b/accel/tcg/translate-all.c
@@ -1815,10 +1815,9 @@ TranslationBlock *tb_gen_code(CPUState *cpu,
         qemu_log_in_addr_range(tb->pc)) {
         FILE *logfile = qemu_log_lock();
         int code_size, data_size = 0;
-        g_autoptr(GString) note = g_string_new("[tb header & initial instruction]");
-        size_t chunk_start = 0;
+        size_t chunk_start;
         int insn = 0;
-        qemu_log("OUT: [size=%d]\n", gen_code_size);
+
         if (tcg_ctx->data_gen_ptr) {
             code_size = tcg_ctx->data_gen_ptr - tb->tc.ptr;
             data_size = gen_code_size - code_size;
@@ -1827,26 +1826,33 @@ TranslationBlock *tb_gen_code(CPUState *cpu,
         }
 
         /* Dump header and the first instruction */
+        qemu_log("OUT: [size=%d]\n", gen_code_size);
+        qemu_log("  -- guest addr 0x" TARGET_FMT_lx " + tb prologue\n",
+                 tcg_ctx->gen_insn_data[insn][0]);
         chunk_start = tcg_ctx->gen_insn_end_off[insn];
-        log_disas(tb->tc.ptr, chunk_start, note->str);
+        log_disas(tb->tc.ptr, chunk_start);
 
         /*
          * Dump each instruction chunk, wrapping up empty chunks into
          * the next instruction. The whole array is offset so the
          * first entry is the beginning of the 2nd instruction.
          */
-        while (insn <= tb->icount && chunk_start < code_size) {
+        while (insn < tb->icount) {
             size_t chunk_end = tcg_ctx->gen_insn_end_off[insn];
             if (chunk_end > chunk_start) {
-                g_string_printf(note, "[guest addr: " TARGET_FMT_lx "]",
-                                tcg_ctx->gen_insn_data[insn][0]);
-                log_disas(tb->tc.ptr + chunk_start, chunk_end - chunk_start,
-                          note->str);
+                qemu_log("  -- guest addr 0x" TARGET_FMT_lx "\n",
+                         tcg_ctx->gen_insn_data[insn][0]);
+                log_disas(tb->tc.ptr + chunk_start, chunk_end - chunk_start);
                 chunk_start = chunk_end;
             }
             insn++;
         }
 
+        if (chunk_start < code_size) {
+            qemu_log("  -- tb slow paths + alignment\n");
+            log_disas(tb->tc.ptr + chunk_start, code_size - chunk_start);
+        }
+
         /* Finally dump any data we may have after the block */
         if (data_size) {
             int i;
diff --git a/disas.c b/disas.c
index c1397d3933..a4304e8137 100644
--- a/disas.c
+++ b/disas.c
@@ -262,8 +262,7 @@ static void cap_dump_insn_units(disassemble_info *info, cs_insn *insn,
     }
 }
 
-static void cap_dump_insn(disassemble_info *info, cs_insn *insn,
-                          const char *note)
+static void cap_dump_insn(disassemble_info *info, cs_insn *insn)
 {
     fprintf_function print = info->fprintf_func;
     int i, n, split;
@@ -284,11 +283,7 @@ static void cap_dump_insn(disassemble_info *info, cs_insn *insn,
     }
 
     /* Print the actual instruction.  */
-    print(info->stream, "  %-8s %s", insn->mnemonic, insn->op_str);
-    if (note) {
-        print(info->stream, "\t\t%s", note);
-    }
-    print(info->stream, "\n");
+    print(info->stream, "  %-8s %s\n", insn->mnemonic, insn->op_str);
 
     /* Dump any remaining part of the insn on subsequent lines.  */
     for (i = split; i < n; i += split) {
@@ -320,7 +315,7 @@ static bool cap_disas_target(disassemble_info *info, uint64_t pc, size_t size)
         size -= tsize;
 
         while (cs_disasm_iter(handle, &cbuf, &csize, &pc, insn)) {
-            cap_dump_insn(info, insn, NULL);
+            cap_dump_insn(info, insn);
         }
 
         /* If the target memory is not consumed, go back for more... */
@@ -349,8 +344,7 @@ static bool cap_disas_target(disassemble_info *info, uint64_t pc, size_t size)
 }
 
 /* Disassemble SIZE bytes at CODE for the host.  */
-static bool cap_disas_host(disassemble_info *info, void *code, size_t size,
-                           const char *note)
+static bool cap_disas_host(disassemble_info *info, void *code, size_t size)
 {
     csh handle;
     const uint8_t *cbuf;
@@ -366,8 +360,7 @@ static bool cap_disas_host(disassemble_info *info, void *code, size_t size,
     pc = (uintptr_t)code;
 
     while (cs_disasm_iter(handle, &cbuf, &size, &pc, insn)) {
-        cap_dump_insn(info, insn, note);
-        note = NULL;
+        cap_dump_insn(info, insn);
     }
     if (size != 0) {
         (*info->fprintf_func)(info->stream,
@@ -411,7 +404,7 @@ static bool cap_disas_monitor(disassemble_info *info, uint64_t pc, int count)
         csize += tsize;
 
         if (cs_disasm_iter(handle, &cbuf, &csize, &pc, insn)) {
-            cap_dump_insn(info, insn, NULL);
+            cap_dump_insn(info, insn);
             if (--count <= 0) {
                 break;
             }
@@ -425,7 +418,7 @@ static bool cap_disas_monitor(disassemble_info *info, uint64_t pc, int count)
 #endif /* !CONFIG_USER_ONLY */
 #else
 # define cap_disas_target(i, p, s)  false
-# define cap_disas_host(i, p, s, n)  false
+# define cap_disas_host(i, p, s)  false
 # define cap_disas_monitor(i, p, c)  false
 # define cap_disas_plugin(i, p, c) false
 #endif /* CONFIG_CAPSTONE */
@@ -595,7 +588,7 @@ char *plugin_disas(CPUState *cpu, uint64_t addr, size_t size)
 }
 
 /* Disassemble this for me please... (debugging). */
-void disas(FILE *out, void *code, unsigned long size, const char *note)
+void disas(FILE *out, void *code, unsigned long size)
 {
     uintptr_t pc;
     int count;
@@ -673,7 +666,7 @@ void disas(FILE *out, void *code, unsigned long size, const char *note)
     print_insn = print_insn_hppa;
 #endif
 
-    if (s.info.cap_arch >= 0 && cap_disas_host(&s.info, code, size, note)) {
+    if (s.info.cap_arch >= 0 && cap_disas_host(&s.info, code, size)) {
         return;
     }
 
@@ -683,10 +676,6 @@ void disas(FILE *out, void *code, unsigned long size, const char *note)
     for (pc = (uintptr_t)code; size > 0; pc += count, size -= count) {
         fprintf(out, "0x%08" PRIxPTR ":  ", pc);
         count = print_insn(pc, &s.info);
-        if (note) {
-            fprintf(out, "\t\t%s", note);
-            note = NULL;
-        }
         fprintf(out, "\n");
         if (count < 0) {
             break;
diff --git a/tcg/tcg.c b/tcg/tcg.c
index 62f299e36e..9a111ce604 100644
--- a/tcg/tcg.c
+++ b/tcg/tcg.c
@@ -1101,7 +1101,7 @@ void tcg_prologue_init(TCGContext *s)
             size_t data_size = prologue_size - code_size;
             size_t i;
 
-            log_disas(buf0, code_size, NULL);
+            log_disas(buf0, code_size);
 
             for (i = 0; i < data_size; i += sizeof(tcg_target_ulong)) {
                 if (sizeof(tcg_target_ulong) == 8) {
@@ -1115,7 +1115,7 @@ void tcg_prologue_init(TCGContext *s)
                 }
             }
         } else {
-            log_disas(buf0, prologue_size, NULL);
+            log_disas(buf0, prologue_size);
         }
         qemu_log("\n");
         qemu_log_flush();
-- 
2.25.1



^ permalink raw reply related	[flat|nested] 29+ messages in thread

* [PATCH v2 04/10] disas: Clean up CPUDebug initialization
  2020-09-14 23:02 [PATCH v2 00/10] capstone + disassembler patches Richard Henderson
                   ` (2 preceding siblings ...)
  2020-09-14 23:02 ` [PATCH v2 03/10] disas: Move host asm annotations to tb_gen_code Richard Henderson
@ 2020-09-14 23:02 ` Richard Henderson
  2020-09-17 14:39   ` Thomas Huth
  2020-09-17 14:50   ` Thomas Huth
  2020-09-14 23:02 ` [PATCH v2 05/10] disas: Use qemu/bswap.h for bfd endian loads Richard Henderson
                   ` (5 subsequent siblings)
  9 siblings, 2 replies; 29+ messages in thread
From: Richard Henderson @ 2020-09-14 23:02 UTC (permalink / raw)
  To: qemu-devel; +Cc: luoyonggang, alex.bennee, thuth

Rename several functions, dropping "generic" and making "host"
vs "target" clearer.  Make a bunch of functions static that are
not used outside this file. Replace INIT_DISASSEMBLE_INFO with
a trio of functions.

Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
 include/disas/dis-asm.h |  60 --------
 disas.c                 | 326 ++++++++++++++++++----------------------
 2 files changed, 148 insertions(+), 238 deletions(-)

diff --git a/include/disas/dis-asm.h b/include/disas/dis-asm.h
index 9856bf7921..d2418c977e 100644
--- a/include/disas/dis-asm.h
+++ b/include/disas/dis-asm.h
@@ -461,67 +461,7 @@ int print_insn_riscv32          (bfd_vma, disassemble_info*);
 int print_insn_riscv64          (bfd_vma, disassemble_info*);
 int print_insn_rx(bfd_vma, disassemble_info *);
 
-#if 0
-/* Fetch the disassembler for a given BFD, if that support is available.  */
-disassembler_ftype disassembler(bfd *);
-#endif
-
 \f
-/* This block of definitions is for particular callers who read instructions
-   into a buffer before calling the instruction decoder.  */
-
-/* Here is a function which callers may wish to use for read_memory_func.
-   It gets bytes from a buffer.  */
-int buffer_read_memory(bfd_vma, bfd_byte *, int, struct disassemble_info *);
-
-/* This function goes with buffer_read_memory.
-   It prints a message using info->fprintf_func and info->stream.  */
-void perror_memory(int, bfd_vma, struct disassemble_info *);
-
-
-/* Just print the address in hex.  This is included for completeness even
-   though both GDB and objdump provide their own (to print symbolic
-   addresses).  */
-void generic_print_address(bfd_vma, struct disassemble_info *);
-
-/* Always true.  */
-int generic_symbol_at_address(bfd_vma, struct disassemble_info *);
-
-/* Macro to initialize a disassemble_info struct.  This should be called
-   by all applications creating such a struct.  */
-#define INIT_DISASSEMBLE_INFO(INFO, STREAM, FPRINTF_FUNC) \
-  (INFO).flavour = bfd_target_unknown_flavour, \
-  (INFO).arch = bfd_arch_unknown, \
-  (INFO).mach = 0, \
-  (INFO).endian = BFD_ENDIAN_UNKNOWN, \
-  INIT_DISASSEMBLE_INFO_NO_ARCH(INFO, STREAM, FPRINTF_FUNC)
-
-/* Call this macro to initialize only the internal variables for the
-   disassembler.  Architecture dependent things such as byte order, or machine
-   variant are not touched by this macro.  This makes things much easier for
-   GDB which must initialize these things separately.  */
-
-#define INIT_DISASSEMBLE_INFO_NO_ARCH(INFO, STREAM, FPRINTF_FUNC) \
-  (INFO).fprintf_func = (FPRINTF_FUNC), \
-  (INFO).stream = (STREAM), \
-  (INFO).symbols = NULL, \
-  (INFO).num_symbols = 0, \
-  (INFO).private_data = NULL, \
-  (INFO).buffer = NULL, \
-  (INFO).buffer_vma = 0, \
-  (INFO).buffer_length = 0, \
-  (INFO).read_memory_func = buffer_read_memory, \
-  (INFO).memory_error_func = perror_memory, \
-  (INFO).print_address_func = generic_print_address, \
-  (INFO).print_insn = NULL, \
-  (INFO).symbol_at_address_func = generic_symbol_at_address, \
-  (INFO).flags = 0, \
-  (INFO).bytes_per_line = 0, \
-  (INFO).bytes_per_chunk = 0, \
-  (INFO).display_endian = BFD_ENDIAN_UNKNOWN, \
-  (INFO).disassembler_options = NULL, \
-  (INFO).insn_info_valid = 0
-
 #ifndef ATTRIBUTE_UNUSED
 #define ATTRIBUTE_UNUSED __attribute__((unused))
 #endif
diff --git a/disas.c b/disas.c
index a4304e8137..7bc8e9a037 100644
--- a/disas.c
+++ b/disas.c
@@ -16,78 +16,66 @@ typedef struct CPUDebug {
 /* Filled in by elfload.c.  Simplistic, but will do for now. */
 struct syminfo *syminfos = NULL;
 
-/* Get LENGTH bytes from info's buffer, at target address memaddr.
-   Transfer them to myaddr.  */
-int
-buffer_read_memory(bfd_vma memaddr, bfd_byte *myaddr, int length,
-                   struct disassemble_info *info)
+/*
+ * Get LENGTH bytes from info's buffer, at host address memaddr.
+ * Transfer them to myaddr.
+ */
+static int host_read_memory(bfd_vma memaddr, bfd_byte *myaddr, int length,
+                            struct disassemble_info *info)
 {
     if (memaddr < info->buffer_vma
-        || memaddr + length > info->buffer_vma + info->buffer_length)
+        || memaddr + length > info->buffer_vma + info->buffer_length) {
         /* Out of bounds.  Use EIO because GDB uses it.  */
         return EIO;
+    }
     memcpy (myaddr, info->buffer + (memaddr - info->buffer_vma), length);
     return 0;
 }
 
-/* Get LENGTH bytes from info's buffer, at target address memaddr.
-   Transfer them to myaddr.  */
-static int
-target_read_memory (bfd_vma memaddr,
-                    bfd_byte *myaddr,
-                    int length,
-                    struct disassemble_info *info)
+/*
+ * Get LENGTH bytes from info's buffer, at target address memaddr.
+ * Transfer them to myaddr.
+ */
+static int target_read_memory(bfd_vma memaddr, bfd_byte *myaddr, int length,
+                              struct disassemble_info *info)
 {
     CPUDebug *s = container_of(info, CPUDebug, info);
-    int r;
-
-    r = cpu_memory_rw_debug(s->cpu, memaddr, myaddr, length, 0);
-
+    int r = cpu_memory_rw_debug(s->cpu, memaddr, myaddr, length, 0);
     return r ? EIO : 0;
 }
 
 /* Print an error message.  We can assume that this is in response to
-   an error return from buffer_read_memory.  */
-void
-perror_memory (int status, bfd_vma memaddr, struct disassemble_info *info)
+   an error return from {host,target}_read_memory.  */
+static void perror_memory(int status, bfd_vma memaddr,
+                          struct disassemble_info *info)
 {
-  if (status != EIO)
-    /* Can't happen.  */
-    (*info->fprintf_func) (info->stream, "Unknown error %d\n", status);
-  else
-    /* Actually, address between memaddr and memaddr + len was
-       out of bounds.  */
-    (*info->fprintf_func) (info->stream,
-			   "Address 0x%" PRIx64 " is out of bounds.\n", memaddr);
+    if (status != EIO) {
+        /* Can't happen.  */
+        info->fprintf_func(info->stream, "Unknown error %d\n", status);
+    } else {
+        /* Address between memaddr and memaddr + len was out of bounds.  */
+        info->fprintf_func(info->stream,
+			   "Address 0x%" PRIx64 " is out of bounds.\n",
+                           memaddr);
+    }
 }
 
-/* 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
-   though both GDB and objdump provide their own (to print symbolic
-   addresses).  */
-
-void
-generic_print_address (bfd_vma addr, struct disassemble_info *info)
+/* Print address in hex. */
+static void print_address(bfd_vma addr, struct disassemble_info *info)
 {
-    (*info->fprintf_func) (info->stream, "0x%" PRIx64, addr);
+    info->fprintf_func(info->stream, "0x%" PRIx64, addr);
 }
 
 /* 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)
+static void host_print_address(bfd_vma addr, struct disassemble_info *info)
 {
-    uint64_t mask = ~0ULL >> (64 - (sizeof(void *) * 8));
-    generic_print_address(addr & mask, info);
+    print_address((uintptr_t)addr, info);
 }
 
-/* Just return the given address.  */
-
-int
-generic_symbol_at_address (bfd_vma addr, struct disassemble_info *info)
+/* Stub prevents some fruitless earching in optabs disassemblers. */
+static int symbol_at_address(bfd_vma addr, struct disassemble_info *info)
 {
-  return 1;
+    return 1;
 }
 
 bfd_vma bfd_getl64 (const bfd_byte *addr)
@@ -423,36 +411,116 @@ static bool cap_disas_monitor(disassemble_info *info, uint64_t pc, int count)
 # define cap_disas_plugin(i, p, c) false
 #endif /* CONFIG_CAPSTONE */
 
+static void initialize_debug(CPUDebug *s)
+{
+    memset(s, 0, sizeof(*s));
+    s->info.arch = bfd_arch_unknown;
+    s->info.cap_arch = -1;
+    s->info.cap_insn_unit = 4;
+    s->info.cap_insn_split = 4;
+    s->info.memory_error_func = perror_memory;
+    s->info.symbol_at_address_func = symbol_at_address;
+}
+
+static void initialize_debug_target(CPUDebug *s, CPUState *cpu)
+{
+    initialize_debug(s);
+
+    s->cpu = cpu;
+    s->info.read_memory_func = target_read_memory;
+    s->info.print_address_func = print_address;
+#ifdef TARGET_WORDS_BIGENDIAN
+    s->info.endian = BFD_ENDIAN_BIG;
+#else
+    s->info.endian = BFD_ENDIAN_LITTLE;
+#endif
+
+    CPUClass *cc = CPU_GET_CLASS(cpu);
+    if (cc->disas_set_info) {
+        cc->disas_set_info(cpu, &s->info);
+    }
+}
+
+static void initialize_debug_host(CPUDebug *s)
+{
+    initialize_debug(s);
+
+    s->info.read_memory_func = host_read_memory;
+    s->info.print_address_func = host_print_address;
+#ifdef HOST_WORDS_BIGENDIAN
+    s->info.endian = BFD_ENDIAN_BIG;
+#else
+    s->info.endian = BFD_ENDIAN_LITTLE;
+#endif
+#if defined(CONFIG_TCG_INTERPRETER)
+    s->info.print_insn = print_insn_tci;
+#elif defined(__i386__)
+    s->info.mach = bfd_mach_i386_i386;
+    s->info.print_insn = print_insn_i386;
+    s->info.cap_arch = CS_ARCH_X86;
+    s->info.cap_mode = CS_MODE_32;
+    s->info.cap_insn_unit = 1;
+    s->info.cap_insn_split = 8;
+#elif defined(__x86_64__)
+    s->info.mach = bfd_mach_x86_64;
+    s->info.print_insn = print_insn_i386;
+    s->info.cap_arch = CS_ARCH_X86;
+    s->info.cap_mode = CS_MODE_64;
+    s->info.cap_insn_unit = 1;
+    s->info.cap_insn_split = 8;
+#elif defined(_ARCH_PPC)
+    s->info.disassembler_options = (char *)"any";
+    s->info.print_insn = print_insn_ppc;
+    s->info.cap_arch = CS_ARCH_PPC;
+# ifdef _ARCH_PPC64
+    s->info.cap_mode = CS_MODE_64;
+# endif
+#elif defined(__riscv) && defined(CONFIG_RISCV_DIS)
+#if defined(_ILP32) || (__riscv_xlen == 32)
+    s->info.print_insn = print_insn_riscv32;
+#elif defined(_LP64)
+    s->info.print_insn = print_insn_riscv64;
+#else
+#error unsupported RISC-V ABI
+#endif
+#elif defined(__aarch64__) && defined(CONFIG_ARM_A64_DIS)
+    s->info.print_insn = print_insn_arm_a64;
+    s->info.cap_arch = CS_ARCH_ARM64;
+#elif defined(__alpha__)
+    s->info.print_insn = print_insn_alpha;
+#elif defined(__sparc__)
+    s->info.print_insn = print_insn_sparc;
+    s->info.mach = bfd_mach_sparc_v9b;
+#elif defined(__arm__)
+    /* TCG only generates code for arm mode.  */
+    s->info.print_insn = print_insn_arm;
+    s->info.cap_arch = CS_ARCH_ARM;
+#elif defined(__MIPSEB__)
+    s->info.print_insn = print_insn_big_mips;
+#elif defined(__MIPSEL__)
+    s->info.print_insn = print_insn_little_mips;
+#elif defined(__m68k__)
+    s->info.print_insn = print_insn_m68k;
+#elif defined(__s390__)
+    s->info.print_insn = print_insn_s390;
+#elif defined(__hppa__)
+    s->info.print_insn = print_insn_hppa;
+#endif
+}
+
 /* Disassemble this for me please... (debugging).  */
 void target_disas(FILE *out, CPUState *cpu, target_ulong code,
                   target_ulong size)
 {
-    CPUClass *cc = CPU_GET_CLASS(cpu);
     target_ulong pc;
     int count;
     CPUDebug s;
 
-    INIT_DISASSEMBLE_INFO(s.info, out, fprintf);
-
-    s.cpu = cpu;
-    s.info.read_memory_func = target_read_memory;
+    initialize_debug_target(&s, cpu);
+    s.info.fprintf_func = fprintf;
+    s.info.stream = out;
     s.info.buffer_vma = code;
     s.info.buffer_length = size;
-    s.info.print_address_func = generic_print_address;
-    s.info.cap_arch = -1;
-    s.info.cap_mode = 0;
-    s.info.cap_insn_unit = 4;
-    s.info.cap_insn_split = 4;
-
-#ifdef TARGET_WORDS_BIGENDIAN
-    s.info.endian = BFD_ENDIAN_BIG;
-#else
-    s.info.endian = BFD_ENDIAN_LITTLE;
-#endif
-
-    if (cc->disas_set_info) {
-        cc->disas_set_info(cpu, &s.info);
-    }
 
     if (s.info.cap_arch >= 0 && cap_disas_target(&s.info, code, size)) {
         return;
@@ -540,34 +608,17 @@ bool cap_disas_plugin(disassemble_info *info, uint64_t pc, size_t size)
  */
 char *plugin_disas(CPUState *cpu, uint64_t addr, size_t size)
 {
-    CPUClass *cc = CPU_GET_CLASS(cpu);
     int count;
     CPUDebug s;
     GString *ds = g_string_set_size(&plugin_disas_output, 0);
 
     g_assert(ds == &plugin_disas_output);
 
-    INIT_DISASSEMBLE_INFO(s.info, NULL, plugin_printf);
-
-    s.cpu = cpu;
-    s.info.read_memory_func = target_read_memory;
+    initialize_debug_target(&s, cpu);
+    s.info.fprintf_func = plugin_printf;
     s.info.buffer_vma = addr;
     s.info.buffer_length = size;
     s.info.print_address_func = plugin_print_address;
-    s.info.cap_arch = -1;
-    s.info.cap_mode = 0;
-    s.info.cap_insn_unit = 4;
-    s.info.cap_insn_split = 4;
-
-#ifdef TARGET_WORDS_BIGENDIAN
-    s.info.endian = BFD_ENDIAN_BIG;
-#else
-    s.info.endian = BFD_ENDIAN_LITTLE;
-#endif
-
-    if (cc->disas_set_info) {
-        cc->disas_set_info(cpu, &s.info);
-    }
 
     if (s.info.cap_arch >= 0 && cap_disas_plugin(&s.info, addr, size)) {
         return g_strdup(ds->str);
@@ -593,89 +644,24 @@ void disas(FILE *out, void *code, unsigned long size)
     uintptr_t pc;
     int count;
     CPUDebug s;
-    int (*print_insn)(bfd_vma pc, disassemble_info *info) = NULL;
-
-    INIT_DISASSEMBLE_INFO(s.info, out, fprintf);
-    s.info.print_address_func = generic_print_host_address;
 
+    initialize_debug_host(&s);
+    s.info.fprintf_func = fprintf;
+    s.info.stream = out;
     s.info.buffer = code;
     s.info.buffer_vma = (uintptr_t)code;
     s.info.buffer_length = size;
-    s.info.cap_arch = -1;
-    s.info.cap_mode = 0;
-    s.info.cap_insn_unit = 4;
-    s.info.cap_insn_split = 4;
-
-#ifdef HOST_WORDS_BIGENDIAN
-    s.info.endian = BFD_ENDIAN_BIG;
-#else
-    s.info.endian = BFD_ENDIAN_LITTLE;
-#endif
-#if defined(CONFIG_TCG_INTERPRETER)
-    print_insn = print_insn_tci;
-#elif defined(__i386__)
-    s.info.mach = bfd_mach_i386_i386;
-    print_insn = print_insn_i386;
-    s.info.cap_arch = CS_ARCH_X86;
-    s.info.cap_mode = CS_MODE_32;
-    s.info.cap_insn_unit = 1;
-    s.info.cap_insn_split = 8;
-#elif defined(__x86_64__)
-    s.info.mach = bfd_mach_x86_64;
-    print_insn = print_insn_i386;
-    s.info.cap_arch = CS_ARCH_X86;
-    s.info.cap_mode = CS_MODE_64;
-    s.info.cap_insn_unit = 1;
-    s.info.cap_insn_split = 8;
-#elif defined(_ARCH_PPC)
-    s.info.disassembler_options = (char *)"any";
-    print_insn = print_insn_ppc;
-    s.info.cap_arch = CS_ARCH_PPC;
-# ifdef _ARCH_PPC64
-    s.info.cap_mode = CS_MODE_64;
-# endif
-#elif defined(__riscv) && defined(CONFIG_RISCV_DIS)
-#if defined(_ILP32) || (__riscv_xlen == 32)
-    print_insn = print_insn_riscv32;
-#elif defined(_LP64)
-    print_insn = print_insn_riscv64;
-#else
-#error unsupported RISC-V ABI
-#endif
-#elif defined(__aarch64__) && defined(CONFIG_ARM_A64_DIS)
-    print_insn = print_insn_arm_a64;
-    s.info.cap_arch = CS_ARCH_ARM64;
-#elif defined(__alpha__)
-    print_insn = print_insn_alpha;
-#elif defined(__sparc__)
-    print_insn = print_insn_sparc;
-    s.info.mach = bfd_mach_sparc_v9b;
-#elif defined(__arm__)
-    print_insn = print_insn_arm;
-    s.info.cap_arch = CS_ARCH_ARM;
-    /* TCG only generates code for arm mode.  */
-#elif defined(__MIPSEB__)
-    print_insn = print_insn_big_mips;
-#elif defined(__MIPSEL__)
-    print_insn = print_insn_little_mips;
-#elif defined(__m68k__)
-    print_insn = print_insn_m68k;
-#elif defined(__s390__)
-    print_insn = print_insn_s390;
-#elif defined(__hppa__)
-    print_insn = print_insn_hppa;
-#endif
 
     if (s.info.cap_arch >= 0 && cap_disas_host(&s.info, code, size)) {
         return;
     }
 
-    if (print_insn == NULL) {
-        print_insn = print_insn_od_host;
+    if (s.info.print_insn == NULL) {
+        s.info.print_insn = print_insn_od_host;
     }
     for (pc = (uintptr_t)code; size > 0; pc += count, size -= count) {
         fprintf(out, "0x%08" PRIxPTR ":  ", pc);
-        count = print_insn(pc, &s.info);
+        count = s.info.print_insn(pc, &s.info);
         fprintf(out, "\n");
         if (count < 0) {
             break;
@@ -720,31 +706,15 @@ physical_read_memory(bfd_vma memaddr, bfd_byte *myaddr, int length,
 void monitor_disas(Monitor *mon, CPUState *cpu,
                    target_ulong pc, int nb_insn, int is_physical)
 {
-    CPUClass *cc = CPU_GET_CLASS(cpu);
     int count, i;
     CPUDebug s;
 
-    INIT_DISASSEMBLE_INFO(s.info, NULL, qemu_fprintf);
-
-    s.cpu = cpu;
-    s.info.read_memory_func
-        = (is_physical ? physical_read_memory : target_read_memory);
-    s.info.print_address_func = generic_print_address;
-    s.info.buffer_vma = pc;
-    s.info.cap_arch = -1;
-    s.info.cap_mode = 0;
-    s.info.cap_insn_unit = 4;
-    s.info.cap_insn_split = 4;
-
-#ifdef TARGET_WORDS_BIGENDIAN
-    s.info.endian = BFD_ENDIAN_BIG;
-#else
-    s.info.endian = BFD_ENDIAN_LITTLE;
-#endif
-
-    if (cc->disas_set_info) {
-        cc->disas_set_info(cpu, &s.info);
+    initialize_debug_target(&s, cpu);
+    s.info.fprintf_func = qemu_fprintf;
+    if (is_physical) {
+        s.info.read_memory_func = physical_read_memory;
     }
+    s.info.buffer_vma = pc;
 
     if (s.info.cap_arch >= 0 && cap_disas_monitor(&s.info, pc, nb_insn)) {
         return;
-- 
2.25.1



^ permalink raw reply related	[flat|nested] 29+ messages in thread

* [PATCH v2 05/10] disas: Use qemu/bswap.h for bfd endian loads
  2020-09-14 23:02 [PATCH v2 00/10] capstone + disassembler patches Richard Henderson
                   ` (3 preceding siblings ...)
  2020-09-14 23:02 ` [PATCH v2 04/10] disas: Clean up CPUDebug initialization Richard Henderson
@ 2020-09-14 23:02 ` Richard Henderson
  2020-09-14 23:02 ` [PATCH v2 06/10] disas: Cleanup plugin_disas Richard Henderson
                   ` (4 subsequent siblings)
  9 siblings, 0 replies; 29+ messages in thread
From: Richard Henderson @ 2020-09-14 23:02 UTC (permalink / raw)
  To: qemu-devel; +Cc: luoyonggang, alex.bennee, thuth, Philippe Mathieu-Daudé

Use the routines we have already instead of open-coding.

Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
 include/disas/dis-asm.h | 32 ++++++++++++++++++++----
 disas.c                 | 55 -----------------------------------------
 2 files changed, 27 insertions(+), 60 deletions(-)

diff --git a/include/disas/dis-asm.h b/include/disas/dis-asm.h
index d2418c977e..8a216ac495 100644
--- a/include/disas/dis-asm.h
+++ b/include/disas/dis-asm.h
@@ -468,11 +468,33 @@ int print_insn_rx(bfd_vma, disassemble_info *);
 
 /* from libbfd */
 
-bfd_vma bfd_getl64 (const bfd_byte *addr);
-bfd_vma bfd_getl32 (const bfd_byte *addr);
-bfd_vma bfd_getb32 (const bfd_byte *addr);
-bfd_vma bfd_getl16 (const bfd_byte *addr);
-bfd_vma bfd_getb16 (const bfd_byte *addr);
+#include "qemu/bswap.h"
+
+static inline bfd_vma bfd_getl64(const bfd_byte *addr)
+{
+    return ldq_le_p(addr);
+}
+
+static inline bfd_vma bfd_getl32(const bfd_byte *addr)
+{
+    return (uint32_t)ldl_le_p(addr);
+}
+
+static inline bfd_vma bfd_getl16(const bfd_byte *addr)
+{
+    return lduw_le_p(addr);
+}
+
+static inline bfd_vma bfd_getb32(const bfd_byte *addr)
+{
+    return (uint32_t)ldl_be_p(addr);
+}
+
+static inline bfd_vma bfd_getb16(const bfd_byte *addr)
+{
+    return lduw_be_p(addr);
+}
+
 typedef bool bfd_boolean;
 
 #endif /* DISAS_DIS_ASM_H */
diff --git a/disas.c b/disas.c
index 7bc8e9a037..bf19b1b0bf 100644
--- a/disas.c
+++ b/disas.c
@@ -78,61 +78,6 @@ static int symbol_at_address(bfd_vma addr, struct disassemble_info *info)
     return 1;
 }
 
-bfd_vma bfd_getl64 (const bfd_byte *addr)
-{
-  unsigned long long v;
-
-  v = (unsigned long long) addr[0];
-  v |= (unsigned long long) addr[1] << 8;
-  v |= (unsigned long long) addr[2] << 16;
-  v |= (unsigned long long) addr[3] << 24;
-  v |= (unsigned long long) addr[4] << 32;
-  v |= (unsigned long long) addr[5] << 40;
-  v |= (unsigned long long) addr[6] << 48;
-  v |= (unsigned long long) addr[7] << 56;
-  return (bfd_vma) v;
-}
-
-bfd_vma bfd_getl32 (const bfd_byte *addr)
-{
-  unsigned long v;
-
-  v = (unsigned long) addr[0];
-  v |= (unsigned long) addr[1] << 8;
-  v |= (unsigned long) addr[2] << 16;
-  v |= (unsigned long) addr[3] << 24;
-  return (bfd_vma) v;
-}
-
-bfd_vma bfd_getb32 (const bfd_byte *addr)
-{
-  unsigned long v;
-
-  v = (unsigned long) addr[0] << 24;
-  v |= (unsigned long) addr[1] << 16;
-  v |= (unsigned long) addr[2] << 8;
-  v |= (unsigned long) addr[3];
-  return (bfd_vma) v;
-}
-
-bfd_vma bfd_getl16 (const bfd_byte *addr)
-{
-  unsigned long v;
-
-  v = (unsigned long) addr[0];
-  v |= (unsigned long) addr[1] << 8;
-  return (bfd_vma) v;
-}
-
-bfd_vma bfd_getb16 (const bfd_byte *addr)
-{
-  unsigned long v;
-
-  v = (unsigned long) addr[0] << 24;
-  v |= (unsigned long) addr[1] << 16;
-  return (bfd_vma) v;
-}
-
 static int print_insn_objdump(bfd_vma pc, disassemble_info *info,
                               const char *prefix)
 {
-- 
2.25.1



^ permalink raw reply related	[flat|nested] 29+ messages in thread

* [PATCH v2 06/10] disas: Cleanup plugin_disas
  2020-09-14 23:02 [PATCH v2 00/10] capstone + disassembler patches Richard Henderson
                   ` (4 preceding siblings ...)
  2020-09-14 23:02 ` [PATCH v2 05/10] disas: Use qemu/bswap.h for bfd endian loads Richard Henderson
@ 2020-09-14 23:02 ` Richard Henderson
  2020-09-14 23:02 ` [PATCH v2 07/10] disas: Configure capstone for aarch64 host without libvixl Richard Henderson
                   ` (3 subsequent siblings)
  9 siblings, 0 replies; 29+ messages in thread
From: Richard Henderson @ 2020-09-14 23:02 UTC (permalink / raw)
  To: qemu-devel; +Cc: luoyonggang, alex.bennee, thuth

Do not retain a GString in thread-local storage.  Allocate a
new one and free it on every invocation.  Do not g_strdup the
result; return the buffer from the GString.  Do not use
warn_report.

Using cs_disasm allocated memory via the &insn parameter, but
that was never freed.  Use cs_disasm_iter so that we use the
memory that we've already allocated, and so that we only try
to disassemble one insn, as desired.  Do not allocate 1k to
hold the bytes for a single instruction.

Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
 disas.c | 55 +++++++++++++++++++------------------------------------
 1 file changed, 19 insertions(+), 36 deletions(-)

diff --git a/disas.c b/disas.c
index bf19b1b0bf..d0ccd4b727 100644
--- a/disas.c
+++ b/disas.c
@@ -491,13 +491,12 @@ void target_disas(FILE *out, CPUState *cpu, target_ulong code,
     }
 }
 
-static __thread GString plugin_disas_output;
-
 static int plugin_printf(FILE *stream, const char *fmt, ...)
 {
-    va_list va;
-    GString *s = &plugin_disas_output;
+    /* We abuse the FILE parameter to pass a GString. */
+    GString *s = (GString *)stream;
     int initial_len = s->len;
+    va_list va;
 
     va_start(va, fmt);
     g_string_append_vprintf(s, fmt, va);
@@ -517,28 +516,20 @@ static void plugin_print_address(bfd_vma addr, struct disassemble_info *info)
 static
 bool cap_disas_plugin(disassemble_info *info, uint64_t pc, size_t size)
 {
-    uint8_t cap_buf[1024];
+    uint8_t cap_buf[64];
+    const uint8_t *cbuf = cap_buf;
     csh handle;
-    cs_insn *insn;
-    size_t csize = 0;
-    int count;
-    GString *s = &plugin_disas_output;
 
     if (cap_disas_start(info, &handle) != CS_ERR_OK) {
         return false;
     }
-    insn = cap_insn;
 
-    size_t tsize = MIN(sizeof(cap_buf) - csize, size);
-    const uint8_t *cbuf = cap_buf;
-    target_read_memory(pc, cap_buf, tsize, info);
+    assert(size < sizeof(cap_buf));
+    target_read_memory(pc, cap_buf, size, info);
 
-    count = cs_disasm(handle, cbuf, size, 0, 1, &insn);
-
-    if (count) {
-        g_string_printf(s, "%s %s", insn->mnemonic, insn->op_str);
-    } else {
-        g_string_printf(s, "cs_disasm failed");
+    if (cs_disasm_iter(handle, &cbuf, &size, &pc, cap_insn)) {
+        GString *s = (GString *)info->stream;
+        g_string_printf(s, "%s %s", cap_insn->mnemonic, cap_insn->op_str);
     }
 
     cs_close(&handle);
@@ -553,34 +544,26 @@ bool cap_disas_plugin(disassemble_info *info, uint64_t pc, size_t size)
  */
 char *plugin_disas(CPUState *cpu, uint64_t addr, size_t size)
 {
-    int count;
     CPUDebug s;
-    GString *ds = g_string_set_size(&plugin_disas_output, 0);
-
-    g_assert(ds == &plugin_disas_output);
+    GString *ds = g_string_new(NULL);
 
     initialize_debug_target(&s, cpu);
     s.info.fprintf_func = plugin_printf;
+    s.info.stream = (FILE *)ds;  /* abuse this slot */
     s.info.buffer_vma = addr;
     s.info.buffer_length = size;
     s.info.print_address_func = plugin_print_address;
 
     if (s.info.cap_arch >= 0 && cap_disas_plugin(&s.info, addr, size)) {
-        return g_strdup(ds->str);
+        ; /* done */
+    } else if (s.info.print_insn) {
+        s.info.print_insn(addr, &s.info);
+    } else {
+        ; /* cannot disassemble -- return empty string */
     }
 
-    if (s.info.print_insn == NULL) {
-        s.info.print_insn = print_insn_od_target;
-    }
-
-    count = s.info.print_insn(addr, &s.info);
-
-    /* The decoder probably read more than it needed it's not critical */
-    if (count < size) {
-        warn_report("%s: %zu bytes left over", __func__, size - count);
-    }
-
-    return g_strdup(ds->str);
+    /* Return the buffer, freeing the GString container.  */
+    return g_string_free(ds, false);
 }
 
 /* Disassemble this for me please... (debugging). */
-- 
2.25.1



^ permalink raw reply related	[flat|nested] 29+ messages in thread

* [PATCH v2 07/10] disas: Configure capstone for aarch64 host without libvixl
  2020-09-14 23:02 [PATCH v2 00/10] capstone + disassembler patches Richard Henderson
                   ` (5 preceding siblings ...)
  2020-09-14 23:02 ` [PATCH v2 06/10] disas: Cleanup plugin_disas Richard Henderson
@ 2020-09-14 23:02 ` Richard Henderson
  2020-09-17 14:44   ` Thomas Huth
  2020-09-14 23:02 ` [PATCH v2 08/10] disas: Split out capstone code to disas/capstone.c Richard Henderson
                   ` (2 subsequent siblings)
  9 siblings, 1 reply; 29+ messages in thread
From: Richard Henderson @ 2020-09-14 23:02 UTC (permalink / raw)
  To: qemu-devel; +Cc: luoyonggang, alex.bennee, thuth

The ifdef tangle failed to set cap_arch if libvixl itself
was not configured (e.g. due to lack of c++ compiler).

Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
 disas.c | 6 ++++--
 1 file changed, 4 insertions(+), 2 deletions(-)

diff --git a/disas.c b/disas.c
index d0ccd4b727..01c8bc6c9e 100644
--- a/disas.c
+++ b/disas.c
@@ -428,9 +428,11 @@ static void initialize_debug_host(CPUDebug *s)
 #else
 #error unsupported RISC-V ABI
 #endif
-#elif defined(__aarch64__) && defined(CONFIG_ARM_A64_DIS)
-    s->info.print_insn = print_insn_arm_a64;
+#elif defined(__aarch64__)
     s->info.cap_arch = CS_ARCH_ARM64;
+# ifdef CONFIG_ARM_A64_DIS
+    s->info.print_insn = print_insn_arm_a64;
+# endif
 #elif defined(__alpha__)
     s->info.print_insn = print_insn_alpha;
 #elif defined(__sparc__)
-- 
2.25.1



^ permalink raw reply related	[flat|nested] 29+ messages in thread

* [PATCH v2 08/10] disas: Split out capstone code to disas/capstone.c
  2020-09-14 23:02 [PATCH v2 00/10] capstone + disassembler patches Richard Henderson
                   ` (6 preceding siblings ...)
  2020-09-14 23:02 ` [PATCH v2 07/10] disas: Configure capstone for aarch64 host without libvixl Richard Henderson
@ 2020-09-14 23:02 ` Richard Henderson
  2020-09-14 23:02 ` [PATCH v2 09/10] disas: Enable capstone disassembly for s390x Richard Henderson
  2020-09-14 23:02 ` [PATCH v2 10/10] disas/capstone: Add skipdata hook " Richard Henderson
  9 siblings, 0 replies; 29+ messages in thread
From: Richard Henderson @ 2020-09-14 23:02 UTC (permalink / raw)
  To: qemu-devel; +Cc: luoyonggang, alex.bennee, thuth

There is nothing target-specific about this code, so it
can be added to common_ss.  This also requires that the
base capstone dependency be added to common_ss, so that
we get the correct include paths added to CFLAGS.

Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
 include/disas/dis-asm.h |  12 ++
 disas.c                 | 275 --------------------------------------
 disas/capstone.c        | 286 ++++++++++++++++++++++++++++++++++++++++
 disas/meson.build       |   1 +
 meson.build             |   1 +
 5 files changed, 300 insertions(+), 275 deletions(-)
 create mode 100644 disas/capstone.c

diff --git a/include/disas/dis-asm.h b/include/disas/dis-asm.h
index 8a216ac495..a34837e4db 100644
--- a/include/disas/dis-asm.h
+++ b/include/disas/dis-asm.h
@@ -461,6 +461,18 @@ int print_insn_riscv32          (bfd_vma, disassemble_info*);
 int print_insn_riscv64          (bfd_vma, disassemble_info*);
 int print_insn_rx(bfd_vma, disassemble_info *);
 
+#ifdef CONFIG_CAPSTONE
+bool cap_disas_target(disassemble_info *info, uint64_t pc, size_t size);
+bool cap_disas_host(disassemble_info *info, void *code, size_t size);
+bool cap_disas_monitor(disassemble_info *info, uint64_t pc, int count);
+bool cap_disas_plugin(disassemble_info *info, uint64_t pc, size_t size);
+#else
+# define cap_disas_target(i, p, s)  false
+# define cap_disas_host(i, p, s)    false
+# define cap_disas_monitor(i, p, c) false
+# define cap_disas_plugin(i, p, c)  false
+#endif /* CONFIG_CAPSTONE */
+
 \f
 #ifndef ATTRIBUTE_UNUSED
 #define ATTRIBUTE_UNUSED __attribute__((unused))
diff --git a/disas.c b/disas.c
index 01c8bc6c9e..e27dea2c19 100644
--- a/disas.c
+++ b/disas.c
@@ -107,255 +107,6 @@ static int print_insn_od_target(bfd_vma pc, disassemble_info *info)
     return print_insn_objdump(pc, info, "OBJD-T");
 }
 
-#ifdef CONFIG_CAPSTONE
-/* Temporary storage for the capstone library.  This will be alloced via
-   malloc with a size private to the library; thus there's no reason not
-   to share this across calls and across host vs target disassembly.  */
-static __thread cs_insn *cap_insn;
-
-/* Initialize the Capstone library.  */
-/* ??? It would be nice to cache this.  We would need one handle for the
-   host and one for the target.  For most targets we can reset specific
-   parameters via cs_option(CS_OPT_MODE, new_mode), but we cannot change
-   CS_ARCH_* in this way.  Thus we would need to be able to close and
-   re-open the target handle with a different arch for the target in order
-   to handle AArch64 vs AArch32 mode switching.  */
-static cs_err cap_disas_start(disassemble_info *info, csh *handle)
-{
-    cs_mode cap_mode = info->cap_mode;
-    cs_err err;
-
-    cap_mode += (info->endian == BFD_ENDIAN_BIG ? CS_MODE_BIG_ENDIAN
-                 : CS_MODE_LITTLE_ENDIAN);
-
-    err = cs_open(info->cap_arch, cap_mode, handle);
-    if (err != CS_ERR_OK) {
-        return err;
-    }
-
-    /* ??? There probably ought to be a better place to put this.  */
-    if (info->cap_arch == CS_ARCH_X86) {
-        /* We don't care about errors (if for some reason the library
-           is compiled without AT&T syntax); the user will just have
-           to deal with the Intel syntax.  */
-        cs_option(*handle, CS_OPT_SYNTAX, CS_OPT_SYNTAX_ATT);
-    }
-
-    /* "Disassemble" unknown insns as ".byte W,X,Y,Z".  */
-    cs_option(*handle, CS_OPT_SKIPDATA, CS_OPT_ON);
-
-    /* Allocate temp space for cs_disasm_iter.  */
-    if (cap_insn == NULL) {
-        cap_insn = cs_malloc(*handle);
-        if (cap_insn == NULL) {
-            cs_close(handle);
-            return CS_ERR_MEM;
-        }
-    }
-    return CS_ERR_OK;
-}
-
-static void cap_dump_insn_units(disassemble_info *info, cs_insn *insn,
-                                int i, int n)
-{
-    fprintf_function print = info->fprintf_func;
-    FILE *stream = info->stream;
-
-    switch (info->cap_insn_unit) {
-    case 4:
-        if (info->endian == BFD_ENDIAN_BIG) {
-            for (; i < n; i += 4) {
-                print(stream, " %08x", ldl_be_p(insn->bytes + i));
-
-            }
-        } else {
-            for (; i < n; i += 4) {
-                print(stream, " %08x", ldl_le_p(insn->bytes + i));
-            }
-        }
-        break;
-
-    case 2:
-        if (info->endian == BFD_ENDIAN_BIG) {
-            for (; i < n; i += 2) {
-                print(stream, " %04x", lduw_be_p(insn->bytes + i));
-            }
-        } else {
-            for (; i < n; i += 2) {
-                print(stream, " %04x", lduw_le_p(insn->bytes + i));
-            }
-        }
-        break;
-
-    default:
-        for (; i < n; i++) {
-            print(stream, " %02x", insn->bytes[i]);
-        }
-        break;
-    }
-}
-
-static void cap_dump_insn(disassemble_info *info, cs_insn *insn)
-{
-    fprintf_function print = info->fprintf_func;
-    int i, n, split;
-
-    print(info->stream, "0x%08" PRIx64 ": ", insn->address);
-
-    n = insn->size;
-    split = info->cap_insn_split;
-
-    /* Dump the first SPLIT bytes of the instruction.  */
-    cap_dump_insn_units(info, insn, 0, MIN(n, split));
-
-    /* Add padding up to SPLIT so that mnemonics line up.  */
-    if (n < split) {
-        int width = (split - n) / info->cap_insn_unit;
-        width *= (2 * info->cap_insn_unit + 1);
-        print(info->stream, "%*s", width, "");
-    }
-
-    /* Print the actual instruction.  */
-    print(info->stream, "  %-8s %s\n", insn->mnemonic, insn->op_str);
-
-    /* Dump any remaining part of the insn on subsequent lines.  */
-    for (i = split; i < n; i += split) {
-        print(info->stream, "0x%08" PRIx64 ": ", insn->address + i);
-        cap_dump_insn_units(info, insn, i, MIN(n, i + split));
-        print(info->stream, "\n");
-    }
-}
-
-/* Disassemble SIZE bytes at PC for the target.  */
-static bool cap_disas_target(disassemble_info *info, uint64_t pc, size_t size)
-{
-    uint8_t cap_buf[1024];
-    csh handle;
-    cs_insn *insn;
-    size_t csize = 0;
-
-    if (cap_disas_start(info, &handle) != CS_ERR_OK) {
-        return false;
-    }
-    insn = cap_insn;
-
-    while (1) {
-        size_t tsize = MIN(sizeof(cap_buf) - csize, size);
-        const uint8_t *cbuf = cap_buf;
-
-        target_read_memory(pc + csize, cap_buf + csize, tsize, info);
-        csize += tsize;
-        size -= tsize;
-
-        while (cs_disasm_iter(handle, &cbuf, &csize, &pc, insn)) {
-            cap_dump_insn(info, insn);
-        }
-
-        /* If the target memory is not consumed, go back for more... */
-        if (size != 0) {
-            /* ... taking care to move any remaining fractional insn
-               to the beginning of the buffer.  */
-            if (csize != 0) {
-                memmove(cap_buf, cbuf, csize);
-            }
-            continue;
-        }
-
-        /* Since the target memory is consumed, we should not have
-           a remaining fractional insn.  */
-        if (csize != 0) {
-            (*info->fprintf_func)(info->stream,
-                "Disassembler disagrees with translator "
-                "over instruction decoding\n"
-                "Please report this to qemu-devel@nongnu.org\n");
-        }
-        break;
-    }
-
-    cs_close(&handle);
-    return true;
-}
-
-/* Disassemble SIZE bytes at CODE for the host.  */
-static bool cap_disas_host(disassemble_info *info, void *code, size_t size)
-{
-    csh handle;
-    const uint8_t *cbuf;
-    cs_insn *insn;
-    uint64_t pc;
-
-    if (cap_disas_start(info, &handle) != CS_ERR_OK) {
-        return false;
-    }
-    insn = cap_insn;
-
-    cbuf = code;
-    pc = (uintptr_t)code;
-
-    while (cs_disasm_iter(handle, &cbuf, &size, &pc, insn)) {
-        cap_dump_insn(info, insn);
-    }
-    if (size != 0) {
-        (*info->fprintf_func)(info->stream,
-            "Disassembler disagrees with TCG over instruction encoding\n"
-            "Please report this to qemu-devel@nongnu.org\n");
-    }
-
-    cs_close(&handle);
-    return true;
-}
-
-#if !defined(CONFIG_USER_ONLY)
-/* Disassemble COUNT insns at PC for the target.  */
-static bool cap_disas_monitor(disassemble_info *info, uint64_t pc, int count)
-{
-    uint8_t cap_buf[32];
-    csh handle;
-    cs_insn *insn;
-    size_t csize = 0;
-
-    if (cap_disas_start(info, &handle) != CS_ERR_OK) {
-        return false;
-    }
-    insn = cap_insn;
-
-    while (1) {
-        /* We want to read memory for one insn, but generically we do not
-           know how much memory that is.  We have a small buffer which is
-           known to be sufficient for all supported targets.  Try to not
-           read beyond the page, Just In Case.  For even more simplicity,
-           ignore the actual target page size and use a 1k boundary.  If
-           that turns out to be insufficient, we'll come back around the
-           loop and read more.  */
-        uint64_t epc = QEMU_ALIGN_UP(pc + csize + 1, 1024);
-        size_t tsize = MIN(sizeof(cap_buf) - csize, epc - pc);
-        const uint8_t *cbuf = cap_buf;
-
-        /* Make certain that we can make progress.  */
-        assert(tsize != 0);
-        info->read_memory_func(pc, cap_buf + csize, tsize, info);
-        csize += tsize;
-
-        if (cs_disasm_iter(handle, &cbuf, &csize, &pc, insn)) {
-            cap_dump_insn(info, insn);
-            if (--count <= 0) {
-                break;
-            }
-        }
-        memmove(cap_buf, cbuf, csize);
-    }
-
-    cs_close(&handle);
-    return true;
-}
-#endif /* !CONFIG_USER_ONLY */
-#else
-# define cap_disas_target(i, p, s)  false
-# define cap_disas_host(i, p, s)  false
-# define cap_disas_monitor(i, p, c)  false
-# define cap_disas_plugin(i, p, c) false
-#endif /* CONFIG_CAPSTONE */
-
 static void initialize_debug(CPUDebug *s)
 {
     memset(s, 0, sizeof(*s));
@@ -513,32 +264,6 @@ static void plugin_print_address(bfd_vma addr, struct disassemble_info *info)
 }
 
 
-#ifdef CONFIG_CAPSTONE
-/* Disassemble a single instruction directly into plugin output */
-static
-bool cap_disas_plugin(disassemble_info *info, uint64_t pc, size_t size)
-{
-    uint8_t cap_buf[64];
-    const uint8_t *cbuf = cap_buf;
-    csh handle;
-
-    if (cap_disas_start(info, &handle) != CS_ERR_OK) {
-        return false;
-    }
-
-    assert(size < sizeof(cap_buf));
-    target_read_memory(pc, cap_buf, size, info);
-
-    if (cs_disasm_iter(handle, &cbuf, &size, &pc, cap_insn)) {
-        GString *s = (GString *)info->stream;
-        g_string_printf(s, "%s %s", cap_insn->mnemonic, cap_insn->op_str);
-    }
-
-    cs_close(&handle);
-    return true;
-}
-#endif
-
 /*
  * We should only be dissembling one instruction at a time here. If
  * there is left over it usually indicates the front end has read more
diff --git a/disas/capstone.c b/disas/capstone.c
new file mode 100644
index 0000000000..b48f83958d
--- /dev/null
+++ b/disas/capstone.c
@@ -0,0 +1,286 @@
+/*
+ * Interface to the capstone disassembler.
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ */
+
+#include "qemu/osdep.h"
+#include "qemu/bswap.h"
+#include "disas/dis-asm.h"
+#include "disas/capstone.h"
+
+
+/*
+ * Temporary storage for the capstone library.  This will be alloced via
+ * malloc with a size private to the library; thus there's no reason not
+ * to share this across calls and across host vs target disassembly.
+ */
+static __thread cs_insn *cap_insn;
+
+/*
+ * Initialize the Capstone library.
+ *
+ * ??? It would be nice to cache this.  We would need one handle for the
+ * host and one for the target.  For most targets we can reset specific
+ * parameters via cs_option(CS_OPT_MODE, new_mode), but we cannot change
+ * CS_ARCH_* in this way.  Thus we would need to be able to close and
+ * re-open the target handle with a different arch for the target in order
+ * to handle AArch64 vs AArch32 mode switching.
+ */
+static cs_err cap_disas_start(disassemble_info *info, csh *handle)
+{
+    cs_mode cap_mode = info->cap_mode;
+    cs_err err;
+
+    cap_mode += (info->endian == BFD_ENDIAN_BIG ? CS_MODE_BIG_ENDIAN
+                 : CS_MODE_LITTLE_ENDIAN);
+
+    err = cs_open(info->cap_arch, cap_mode, handle);
+    if (err != CS_ERR_OK) {
+        return err;
+    }
+
+    /* "Disassemble" unknown insns as ".byte W,X,Y,Z".  */
+    cs_option(*handle, CS_OPT_SKIPDATA, CS_OPT_ON);
+
+    if (info->cap_arch == CS_ARCH_X86) {
+        /*
+         * We don't care about errors (if for some reason the library
+         * is compiled without AT&T syntax); the user will just have
+         * to deal with the Intel syntax.
+         */
+        cs_option(*handle, CS_OPT_SYNTAX, CS_OPT_SYNTAX_ATT);
+    }
+
+    /* Allocate temp space for cs_disasm_iter.  */
+    if (cap_insn == NULL) {
+        cap_insn = cs_malloc(*handle);
+        if (cap_insn == NULL) {
+            cs_close(handle);
+            return CS_ERR_MEM;
+        }
+    }
+    return CS_ERR_OK;
+}
+
+static void cap_dump_insn_units(disassemble_info *info, cs_insn *insn,
+                                int i, int n)
+{
+    fprintf_function print = info->fprintf_func;
+    FILE *stream = info->stream;
+
+    switch (info->cap_insn_unit) {
+    case 4:
+        if (info->endian == BFD_ENDIAN_BIG) {
+            for (; i < n; i += 4) {
+                print(stream, " %08x", ldl_be_p(insn->bytes + i));
+
+            }
+        } else {
+            for (; i < n; i += 4) {
+                print(stream, " %08x", ldl_le_p(insn->bytes + i));
+            }
+        }
+        break;
+
+    case 2:
+        if (info->endian == BFD_ENDIAN_BIG) {
+            for (; i < n; i += 2) {
+                print(stream, " %04x", lduw_be_p(insn->bytes + i));
+            }
+        } else {
+            for (; i < n; i += 2) {
+                print(stream, " %04x", lduw_le_p(insn->bytes + i));
+            }
+        }
+        break;
+
+    default:
+        for (; i < n; i++) {
+            print(stream, " %02x", insn->bytes[i]);
+        }
+        break;
+    }
+}
+
+static void cap_dump_insn(disassemble_info *info, cs_insn *insn)
+{
+    fprintf_function print = info->fprintf_func;
+    FILE *stream = info->stream;
+    int i, n, split;
+
+    print(stream, "0x%08" PRIx64 ": ", insn->address);
+
+    n = insn->size;
+    split = info->cap_insn_split;
+
+    /* Dump the first SPLIT bytes of the instruction.  */
+    cap_dump_insn_units(info, insn, 0, MIN(n, split));
+
+    /* Add padding up to SPLIT so that mnemonics line up.  */
+    if (n < split) {
+        int width = (split - n) / info->cap_insn_unit;
+        width *= (2 * info->cap_insn_unit + 1);
+        print(stream, "%*s", width, "");
+    }
+
+    /* Print the actual instruction.  */
+    print(stream, "  %-8s %s\n", insn->mnemonic, insn->op_str);
+
+    /* Dump any remaining part of the insn on subsequent lines.  */
+    for (i = split; i < n; i += split) {
+        print(stream, "0x%08" PRIx64 ": ", insn->address + i);
+        cap_dump_insn_units(info, insn, i, MIN(n, i + split));
+        print(stream, "\n");
+    }
+}
+
+/* Disassemble SIZE bytes at PC for the target.  */
+bool cap_disas_target(disassemble_info *info, uint64_t pc, size_t size)
+{
+    uint8_t cap_buf[1024];
+    csh handle;
+    cs_insn *insn;
+    size_t csize = 0;
+
+    if (cap_disas_start(info, &handle) != CS_ERR_OK) {
+        return false;
+    }
+    insn = cap_insn;
+
+    while (1) {
+        size_t tsize = MIN(sizeof(cap_buf) - csize, size);
+        const uint8_t *cbuf = cap_buf;
+
+        info->read_memory_func(pc + csize, cap_buf + csize, tsize, info);
+        csize += tsize;
+        size -= tsize;
+
+        while (cs_disasm_iter(handle, &cbuf, &csize, &pc, insn)) {
+            cap_dump_insn(info, insn);
+        }
+
+        /* If the target memory is not consumed, go back for more... */
+        if (size != 0) {
+            /*
+             * ... taking care to move any remaining fractional insn
+             * to the beginning of the buffer.
+             */
+            if (csize != 0) {
+                memmove(cap_buf, cbuf, csize);
+            }
+            continue;
+        }
+
+        /*
+         * Since the target memory is consumed, we should not have
+         * a remaining fractional insn.
+         */
+        if (csize != 0) {
+            info->fprintf_func(info->stream,
+                "Disassembler disagrees with translator "
+                "over instruction decoding\n"
+                "Please report this to qemu-devel@nongnu.org\n");
+        }
+        break;
+    }
+
+    cs_close(&handle);
+    return true;
+}
+
+/* Disassemble SIZE bytes at CODE for the host.  */
+bool cap_disas_host(disassemble_info *info, void *code, size_t size)
+{
+    csh handle;
+    const uint8_t *cbuf;
+    cs_insn *insn;
+    uint64_t pc;
+
+    if (cap_disas_start(info, &handle) != CS_ERR_OK) {
+        return false;
+    }
+    insn = cap_insn;
+
+    cbuf = code;
+    pc = (uintptr_t)code;
+
+    while (cs_disasm_iter(handle, &cbuf, &size, &pc, insn)) {
+        cap_dump_insn(info, insn);
+    }
+    if (size != 0) {
+        info->fprintf_func(info->stream,
+            "Disassembler disagrees with TCG over instruction encoding\n"
+            "Please report this to qemu-devel@nongnu.org\n");
+    }
+
+    cs_close(&handle);
+    return true;
+}
+
+/* Disassemble COUNT insns at PC for the target.  */
+bool cap_disas_monitor(disassemble_info *info, uint64_t pc, int count)
+{
+    uint8_t cap_buf[32];
+    csh handle;
+    cs_insn *insn;
+    size_t csize = 0;
+
+    if (cap_disas_start(info, &handle) != CS_ERR_OK) {
+        return false;
+    }
+    insn = cap_insn;
+
+    while (1) {
+        /*
+         * We want to read memory for one insn, but generically we do not
+         * know how much memory that is.  We have a small buffer which is
+         * known to be sufficient for all supported targets.  Try to not
+         * read beyond the page, Just In Case.  For even more simplicity,
+         * ignore the actual target page size and use a 1k boundary.  If
+         * that turns out to be insufficient, we'll come back around the
+         * loop and read more.
+         */
+        uint64_t epc = QEMU_ALIGN_UP(pc + csize + 1, 1024);
+        size_t tsize = MIN(sizeof(cap_buf) - csize, epc - pc);
+        const uint8_t *cbuf = cap_buf;
+
+        /* Make certain that we can make progress.  */
+        assert(tsize != 0);
+        info->read_memory_func(pc, cap_buf + csize, tsize, info);
+        csize += tsize;
+
+        if (cs_disasm_iter(handle, &cbuf, &csize, &pc, insn)) {
+            cap_dump_insn(info, insn);
+            if (--count <= 0) {
+                break;
+            }
+        }
+        memmove(cap_buf, cbuf, csize);
+    }
+
+    cs_close(&handle);
+    return true;
+}
+
+/* Disassemble a single instruction directly into plugin output */
+bool cap_disas_plugin(disassemble_info *info, uint64_t pc, size_t size)
+{
+    uint8_t cap_buf[32];
+    const uint8_t *cbuf = cap_buf;
+    csh handle;
+
+    if (cap_disas_start(info, &handle) != CS_ERR_OK) {
+        return false;
+    }
+
+    assert(size < sizeof(cap_buf));
+    info->read_memory_func(pc, cap_buf, size, info);
+
+    if (cs_disasm_iter(handle, &cbuf, &size, &pc, cap_insn)) {
+        info->fprintf_func(info->stream, "%s %s",
+                           cap_insn->mnemonic, cap_insn->op_str);
+    }
+
+    cs_close(&handle);
+    return true;
+}
diff --git a/disas/meson.build b/disas/meson.build
index bde8280c73..09a852742e 100644
--- a/disas/meson.build
+++ b/disas/meson.build
@@ -21,5 +21,6 @@ common_ss.add(when: 'CONFIG_S390_DIS', if_true: files('s390.c'))
 common_ss.add(when: 'CONFIG_SH4_DIS', if_true: files('sh4.c'))
 common_ss.add(when: 'CONFIG_SPARC_DIS', if_true: files('sparc.c'))
 common_ss.add(when: 'CONFIG_XTENSA_DIS', if_true: files('xtensa.c'))
+common_ss.add(when: capstone, if_true: files('capstone.c'))
 
 specific_ss.add(when: 'CONFIG_TCG_INTERPRETER', if_true: files('tci.c'))
diff --git a/meson.build b/meson.build
index cbb8257d6b..2f3da5d8c6 100644
--- a/meson.build
+++ b/meson.build
@@ -969,6 +969,7 @@ common_ss.add(files('cpus-common.c'))
 
 subdir('softmmu')
 
+common_ss.add(capstone)
 specific_ss.add(files('disas.c', 'exec.c', 'gdbstub.c'), capstone, libpmem, libdaxctl)
 specific_ss.add(files('exec-vary.c'))
 specific_ss.add(when: 'CONFIG_TCG', if_true: files(
-- 
2.25.1



^ permalink raw reply related	[flat|nested] 29+ messages in thread

* [PATCH v2 09/10] disas: Enable capstone disassembly for s390x
  2020-09-14 23:02 [PATCH v2 00/10] capstone + disassembler patches Richard Henderson
                   ` (7 preceding siblings ...)
  2020-09-14 23:02 ` [PATCH v2 08/10] disas: Split out capstone code to disas/capstone.c Richard Henderson
@ 2020-09-14 23:02 ` Richard Henderson
  2020-09-17 16:30   ` Thomas Huth
  2020-09-14 23:02 ` [PATCH v2 10/10] disas/capstone: Add skipdata hook " Richard Henderson
  9 siblings, 1 reply; 29+ messages in thread
From: Richard Henderson @ 2020-09-14 23:02 UTC (permalink / raw)
  To: qemu-devel; +Cc: luoyonggang, alex.bennee, thuth

Enable s390x, aka SYSZ, in the git submodule build.
Set the capstone parameters for both s390x host and guest.

Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
 disas.c            |  3 +++
 target/s390x/cpu.c |  4 ++++
 meson.build        | 11 +++++++++++
 3 files changed, 18 insertions(+)

diff --git a/disas.c b/disas.c
index e27dea2c19..c4cd305190 100644
--- a/disas.c
+++ b/disas.c
@@ -201,6 +201,9 @@ static void initialize_debug_host(CPUDebug *s)
     s->info.print_insn = print_insn_m68k;
 #elif defined(__s390__)
     s->info.print_insn = print_insn_s390;
+    s->info.cap_arch = CS_ARCH_SYSZ;
+    s->info.cap_insn_unit = 2;
+    s->info.cap_insn_split = 6;
 #elif defined(__hppa__)
     s->info.print_insn = print_insn_hppa;
 #endif
diff --git a/target/s390x/cpu.c b/target/s390x/cpu.c
index 749cd548f0..2a96692691 100644
--- a/target/s390x/cpu.c
+++ b/target/s390x/cpu.c
@@ -44,6 +44,7 @@
 #include "sysemu/tcg.h"
 #endif
 #include "fpu/softfloat-helpers.h"
+#include "disas/capstone.h"
 
 #define CR0_RESET       0xE0UL
 #define CR14_RESET      0xC2000000UL;
@@ -182,6 +183,9 @@ static void s390_cpu_disas_set_info(CPUState *cpu, disassemble_info *info)
 {
     info->mach = bfd_mach_s390_64;
     info->print_insn = print_insn_s390;
+    info->cap_arch = CS_ARCH_SYSZ;
+    info->cap_insn_unit = 2;
+    info->cap_insn_split = 6;
 }
 
 static void s390_cpu_realizefn(DeviceState *dev, Error **errp)
diff --git a/meson.build b/meson.build
index 2f3da5d8c6..448c87f645 100644
--- a/meson.build
+++ b/meson.build
@@ -674,6 +674,17 @@ if capstone_opt == 'internal'
     )
   endif
 
+  if 'CONFIG_S390_DIS' in config_all_disas
+    capstone_data.set('CAPSTONE_HAS_SYSZ', '1')
+    capstone_files += files(
+      'capstone/arch/SystemZ/SystemZDisassembler.c',
+      'capstone/arch/SystemZ/SystemZInstPrinter.c',
+      'capstone/arch/SystemZ/SystemZMapping.c',
+      'capstone/arch/SystemZ/SystemZModule.c',
+      'capstone/arch/SystemZ/SystemZMCTargetDesc.c'
+    )
+  endif
+
   if 'CONFIG_I386_DIS' in config_all_disas
     capstone_data.set('CAPSTONE_HAS_X86', 1)
     capstone_files += files(
-- 
2.25.1



^ permalink raw reply related	[flat|nested] 29+ messages in thread

* [PATCH v2 10/10] disas/capstone: Add skipdata hook for s390x
  2020-09-14 23:02 [PATCH v2 00/10] capstone + disassembler patches Richard Henderson
                   ` (8 preceding siblings ...)
  2020-09-14 23:02 ` [PATCH v2 09/10] disas: Enable capstone disassembly for s390x Richard Henderson
@ 2020-09-14 23:02 ` Richard Henderson
  2020-09-17 16:32   ` Thomas Huth
  9 siblings, 1 reply; 29+ messages in thread
From: Richard Henderson @ 2020-09-14 23:02 UTC (permalink / raw)
  To: qemu-devel; +Cc: luoyonggang, alex.bennee, thuth, Philippe Mathieu-Daudé

It is always possible to tell the length of an insn, even if the
actual insn is unknown.  Skip the correct number of bytes, so that
we stay in sync with the instruction stream.

Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
 disas/capstone.c | 42 +++++++++++++++++++++++++++++++++++++++++-
 1 file changed, 41 insertions(+), 1 deletion(-)

diff --git a/disas/capstone.c b/disas/capstone.c
index b48f83958d..0a9ef9c892 100644
--- a/disas/capstone.c
+++ b/disas/capstone.c
@@ -16,6 +16,39 @@
  */
 static __thread cs_insn *cap_insn;
 
+/*
+ * The capstone library always skips 2 bytes for S390X.
+ * This is less than ideal, since we can tell from the first two bits
+ * the size of the insn and thus stay in sync with the insn stream.
+ */
+static size_t CAPSTONE_API
+cap_skipdata_s390x_cb(const uint8_t *code, size_t code_size,
+                      size_t offset, void *user_data)
+{
+    size_t ilen;
+
+    /* See get_ilen() in target/s390x/internal.h.  */
+    switch (code[offset] >> 6) {
+    case 0:
+        ilen = 2;
+        break;
+    case 1:
+    case 2:
+        ilen = 4;
+        break;
+    default:
+        ilen = 6;
+        break;
+    }
+
+    return ilen;
+}
+
+static const cs_opt_skipdata cap_skipdata_s390x = {
+    .mnemonic = ".byte",
+    .callback = cap_skipdata_s390x_cb
+};
+
 /*
  * Initialize the Capstone library.
  *
@@ -42,13 +75,20 @@ static cs_err cap_disas_start(disassemble_info *info, csh *handle)
     /* "Disassemble" unknown insns as ".byte W,X,Y,Z".  */
     cs_option(*handle, CS_OPT_SKIPDATA, CS_OPT_ON);
 
-    if (info->cap_arch == CS_ARCH_X86) {
+    switch (info->cap_arch) {
+    case CS_ARCH_SYSZ:
+        cs_option(*handle, CS_OPT_SKIPDATA_SETUP,
+                  (uintptr_t)&cap_skipdata_s390x);
+        break;
+
+    case CS_ARCH_X86:
         /*
          * We don't care about errors (if for some reason the library
          * is compiled without AT&T syntax); the user will just have
          * to deal with the Intel syntax.
          */
         cs_option(*handle, CS_OPT_SYNTAX, CS_OPT_SYNTAX_ATT);
+        break;
     }
 
     /* Allocate temp space for cs_disasm_iter.  */
-- 
2.25.1



^ permalink raw reply related	[flat|nested] 29+ messages in thread

* Re: [PATCH v2 01/10] capstone: Convert Makefile bits to meson bits
  2020-09-14 23:02 ` [PATCH v2 01/10] capstone: Convert Makefile bits to meson bits Richard Henderson
@ 2020-09-14 23:06   ` Richard Henderson
  2020-09-15  6:27     ` Paolo Bonzini
  2020-09-15  6:10   ` Thomas Huth
  1 sibling, 1 reply; 29+ messages in thread
From: Richard Henderson @ 2020-09-14 23:06 UTC (permalink / raw)
  To: qemu-devel; +Cc: Paolo Bonzini, luoyonggang, alex.bennee, thuth

On 9/14/20 4:02 PM, Richard Henderson wrote:
> +option('capstone', type: 'combo', value: 'no',
> +       choices: ['no', 'yes', 'auto', 'system', 'internal'],
> +       description: 'Whether and how to find the capstone library')

Dangit, meant to change value: back to 'auto'.


r~


^ permalink raw reply	[flat|nested] 29+ messages in thread

* Re: [PATCH v2 01/10] capstone: Convert Makefile bits to meson bits
  2020-09-14 23:02 ` [PATCH v2 01/10] capstone: Convert Makefile bits to meson bits Richard Henderson
  2020-09-14 23:06   ` Richard Henderson
@ 2020-09-15  6:10   ` Thomas Huth
  1 sibling, 0 replies; 29+ messages in thread
From: Thomas Huth @ 2020-09-15  6:10 UTC (permalink / raw)
  To: Richard Henderson; +Cc: qemu-devel

On 15/09/2020 01.02, Richard Henderson wrote:
> There are better ways to do this, e.g. meson cmake subproject,
> but that requires cmake 3.7 and some of our CI environments
> only provide cmake 3.5.
> 
> Nor can we add a meson.build file to capstone/, because the git
> submodule would then always report "untracked files".  Fixing that
> would require creating our own branch on the qemu git mirror, at
> which point we could just as easily create a native meson subproject.
> 
> Instead, build the library via the main meson.build.
> 
> This improves the current state of affairs in that we will re-link
> the qemu executables against a changed libcapstone.a, which we wouldn't
> do before-hand.  In addition, the use of the confuration header file

s/confuration/configuration/

 Thomas



^ permalink raw reply	[flat|nested] 29+ messages in thread

* Re: [PATCH v2 01/10] capstone: Convert Makefile bits to meson bits
  2020-09-14 23:06   ` Richard Henderson
@ 2020-09-15  6:27     ` Paolo Bonzini
  2020-09-15 14:27       ` Richard Henderson
  0 siblings, 1 reply; 29+ messages in thread
From: Paolo Bonzini @ 2020-09-15  6:27 UTC (permalink / raw)
  To: Richard Henderson; +Cc: thuth, luoyonggang, Alex Bennée, qemu-devel

[-- Attachment #1: Type: text/plain, Size: 621 bytes --]

Looks good. Can you just add a "# Submodules" heading above the test?

I would also like to remove the "yes" value (that is, the default fails if
the internal copy is not there) but it can be done later for all submodules.

Paolo

Il mar 15 set 2020, 01:06 Richard Henderson <richard.henderson@linaro.org>
ha scritto:

> On 9/14/20 4:02 PM, Richard Henderson wrote:
> > +option('capstone', type: 'combo', value: 'no',
> > +       choices: ['no', 'yes', 'auto', 'system', 'internal'],
> > +       description: 'Whether and how to find the capstone library')
>
> Dangit, meant to change value: back to 'auto'.
>
>
> r~
>
>

[-- Attachment #2: Type: text/html, Size: 1132 bytes --]

^ permalink raw reply	[flat|nested] 29+ messages in thread

* Re: [PATCH v2 01/10] capstone: Convert Makefile bits to meson bits
  2020-09-15  6:27     ` Paolo Bonzini
@ 2020-09-15 14:27       ` Richard Henderson
  2020-09-15 16:12         ` 罗勇刚(Yonggang Luo)
  2020-09-15 16:58         ` Paolo Bonzini
  0 siblings, 2 replies; 29+ messages in thread
From: Richard Henderson @ 2020-09-15 14:27 UTC (permalink / raw)
  To: Paolo Bonzini; +Cc: thuth, luoyonggang, Alex Bennée, qemu-devel

On 9/14/20 11:27 PM, Paolo Bonzini wrote:
> Looks good. Can you just add a "# Submodules" heading above the test?
> 
> I would also like to remove the "yes" value (that is, the default fails if the
> internal copy is not there) but it can be done later for all submodules.

Unless you simply plan to rename {no, yes} to {disabled, enabled}, as for the
Feature objects, why?

That seems to be the only sensible value for --enable-foo, without the =system
or =git specifiers.  We *should* fail if no system library nor internal copy is
present.


r~


^ permalink raw reply	[flat|nested] 29+ messages in thread

* Re: [PATCH v2 01/10] capstone: Convert Makefile bits to meson bits
  2020-09-15 14:27       ` Richard Henderson
@ 2020-09-15 16:12         ` 罗勇刚(Yonggang Luo)
  2020-09-15 16:59           ` Paolo Bonzini
  2020-09-15 16:58         ` Paolo Bonzini
  1 sibling, 1 reply; 29+ messages in thread
From: 罗勇刚(Yonggang Luo) @ 2020-09-15 16:12 UTC (permalink / raw)
  To: Richard Henderson
  Cc: Paolo Bonzini, Thomas Huth, Alex Bennée, qemu-devel

[-- Attachment #1: Type: text/plain, Size: 1031 bytes --]

On Tue, Sep 15, 2020 at 10:27 PM Richard Henderson <
richard.henderson@linaro.org> wrote:

> On 9/14/20 11:27 PM, Paolo Bonzini wrote:
> > Looks good. Can you just add a "# Submodules" heading above the test?
> >
> > I would also like to remove the "yes" value (that is, the default fails
> if the
> > internal copy is not there) but it can be done later for all submodules.
>
> Unless you simply plan to rename {no, yes} to {disabled, enabled}, as for
> the
> Feature objects, why?
>
> That seems to be the only sensible value for --enable-foo, without the
> =system
> or =git specifiers.  We *should* fail if no system library nor internal
> copy is
> present.
>
I suggest remove the capstone=system option cause the system library may
not satisfy the requirements of qemu
and create in-consistence expereince when bug or error happens about
capstone. We either have git submodule capstone
or nothing at all

>
>
> r~
>


-- 
         此致
礼
罗勇刚
Yours
    sincerely,
Yonggang Luo

[-- Attachment #2: Type: text/html, Size: 1650 bytes --]

^ permalink raw reply	[flat|nested] 29+ messages in thread

* Re: [PATCH v2 03/10] disas: Move host asm annotations to tb_gen_code
  2020-09-14 23:02 ` [PATCH v2 03/10] disas: Move host asm annotations to tb_gen_code Richard Henderson
@ 2020-09-15 16:36   ` Thomas Huth
  0 siblings, 0 replies; 29+ messages in thread
From: Thomas Huth @ 2020-09-15 16:36 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel; +Cc: luoyonggang, alex.bennee

On 15/09/2020 01.02, Richard Henderson wrote:
> Instead of creating GStrings and passing them into log_disas,
> just print the annotations directly in tb_gen_code.
> 
> Fix the annotations for the slow paths of the TB, after the
> part implementing the final guest instruction.
> 
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
> ---
>  include/disas/disas.h     |  2 +-
>  include/exec/log.h        |  4 ++--
>  accel/tcg/translate-all.c | 24 +++++++++++++++---------
>  disas.c                   | 29 +++++++++--------------------
>  tcg/tcg.c                 |  4 ++--
>  5 files changed, 29 insertions(+), 34 deletions(-)

Reviewed-by: Thomas Huth <thuth@redhat.com>



^ permalink raw reply	[flat|nested] 29+ messages in thread

* Re: [PATCH v2 01/10] capstone: Convert Makefile bits to meson bits
  2020-09-15 14:27       ` Richard Henderson
  2020-09-15 16:12         ` 罗勇刚(Yonggang Luo)
@ 2020-09-15 16:58         ` Paolo Bonzini
  1 sibling, 0 replies; 29+ messages in thread
From: Paolo Bonzini @ 2020-09-15 16:58 UTC (permalink / raw)
  To: Richard Henderson; +Cc: thuth, luoyonggang, Alex Bennée, qemu-devel

On 15/09/20 16:27, Richard Henderson wrote:
> On 9/14/20 11:27 PM, Paolo Bonzini wrote:
>> Looks good. Can you just add a "# Submodules" heading above the test?
>>
>> I would also like to remove the "yes" value (that is, the default fails if the
>> internal copy is not there) but it can be done later for all submodules.
> 
> Unless you simply plan to rename {no, yes} to {disabled, enabled}, as for the
> Feature objects, why?
> 
> That seems to be the only sensible value for --enable-foo, without the =system
> or =git specifiers.  We *should* fail if no system library nor internal copy is
> present.

Yes, that was a bit concise.  I would like "auto" to take the meaning
that "yes" currently as.  Right now we have

no -> Easy :)
system -> System capstone if found, fail otherwise
internal/git -> Compile capstone if found, fail otherwise
auto -> System capstone, then internal, then disable
yes -> System capstone, then internal, then fail

I'm not sure of the usefulness of disabling a dependency because we
don't have it checked out, since we have the machinery to do the
checkout automatically.  So that would become:

no -> Easy :)
system -> System capstone if found, fail otherwise
internal/git -> Compile capstone if found, fail otherwise
auto -> System capstone, then internal, then fail

The disadvantage is that it would be different from other "auto"
symbols, which never fail.  But then those other "auto" symbols do not
have a built-in fallback, so the question is whether the combination of

1) building from a fresh git checkout
2) --disable-git-update
3) not having a system capstone/libfdt/slirp
4) not having --disable-{capstone,libfdt,slirp} on the command line

is more likely to be intentional or operator error.

Paolo



^ permalink raw reply	[flat|nested] 29+ messages in thread

* Re: [PATCH v2 01/10] capstone: Convert Makefile bits to meson bits
  2020-09-15 16:12         ` 罗勇刚(Yonggang Luo)
@ 2020-09-15 16:59           ` Paolo Bonzini
  2020-09-15 17:07             ` 罗勇刚(Yonggang Luo)
  0 siblings, 1 reply; 29+ messages in thread
From: Paolo Bonzini @ 2020-09-15 16:59 UTC (permalink / raw)
  To: luoyonggang, Richard Henderson; +Cc: Thomas Huth, Alex Bennée, qemu-devel

On 15/09/20 18:12, 罗勇刚(Yonggang Luo) wrote:
> 
> I suggest remove the capstone=system option cause the system library
> may not satisfy the requirements of qemu and create in-consistence
> expereince when bug or error happens about capstone. We either have
> git submodule capstone or nothing at all

Linux distributions generally do not want to have bundled libraries, so
the fallback to the system library is the default.  We single out
capstone, libfdt and slirp because they are slightly less common
dependencies and are missing on some distros; however, in general we
strive to _only_ use system libraries and not package any of QEMU's
dependencies.

Paolo



^ permalink raw reply	[flat|nested] 29+ messages in thread

* Re: [PATCH v2 01/10] capstone: Convert Makefile bits to meson bits
  2020-09-15 16:59           ` Paolo Bonzini
@ 2020-09-15 17:07             ` 罗勇刚(Yonggang Luo)
  2020-09-15 17:14               ` Paolo Bonzini
  0 siblings, 1 reply; 29+ messages in thread
From: 罗勇刚(Yonggang Luo) @ 2020-09-15 17:07 UTC (permalink / raw)
  To: Paolo Bonzini
  Cc: Alex Bennée, Thomas Huth, Richard Henderson, qemu-devel

[-- Attachment #1: Type: text/plain, Size: 1109 bytes --]

On Wed, Sep 16, 2020 at 1:00 AM Paolo Bonzini <pbonzini@redhat.com> wrote:

> On 15/09/20 18:12, 罗勇刚(Yonggang Luo) wrote:
> >
> > I suggest remove the capstone=system option cause the system library
> > may not satisfy the requirements of qemu and create in-consistence
> > expereince when bug or error happens about capstone. We either have
> > git submodule capstone or nothing at all
>
> Linux distributions generally do not want to have bundled libraries, so
>
Yes, bundled libraries is a bad idea, but static linked library is another
case, that won't affect
the Linux distributions.

> the fallback to the system library is the default.  We single out
> capstone, libfdt and slirp because they are slightly less common
>
Ineed, I would like suggest these three libraries always to be static
linked or not use it at all.

> dependencies and are missing on some distros; however, in general we
> strive to _only_ use system libraries and not package any of QEMU's
> dependencies.
>
> Paolo
>
>

-- 
         此致
礼
罗勇刚
Yours
    sincerely,
Yonggang Luo

[-- Attachment #2: Type: text/html, Size: 1858 bytes --]

^ permalink raw reply	[flat|nested] 29+ messages in thread

* Re: [PATCH v2 01/10] capstone: Convert Makefile bits to meson bits
  2020-09-15 17:07             ` 罗勇刚(Yonggang Luo)
@ 2020-09-15 17:14               ` Paolo Bonzini
  2020-09-15 17:20                 ` 罗勇刚(Yonggang Luo)
  0 siblings, 1 reply; 29+ messages in thread
From: Paolo Bonzini @ 2020-09-15 17:14 UTC (permalink / raw)
  To: luoyonggang; +Cc: Alex Bennée, Thomas Huth, Richard Henderson, qemu-devel

On 15/09/20 19:07, 罗勇刚(Yonggang Luo) wrote:
> 
>     Linux distributions generally do not want to have bundled libraries, so
> 
> Yes, bundled libraries is a bad idea, but static linked library is
> another case, that won't affect
> the Linux distributions. 

As far as Linux distributions are concerned, static linking is a case of
bundling.  Bundling means that, for example, any security issue will
require rebuilding the package that does the bundling (this applies
especially to slirp among the three that QEMU we bundles).

Paolo



^ permalink raw reply	[flat|nested] 29+ messages in thread

* Re: [PATCH v2 01/10] capstone: Convert Makefile bits to meson bits
  2020-09-15 17:14               ` Paolo Bonzini
@ 2020-09-15 17:20                 ` 罗勇刚(Yonggang Luo)
  0 siblings, 0 replies; 29+ messages in thread
From: 罗勇刚(Yonggang Luo) @ 2020-09-15 17:20 UTC (permalink / raw)
  To: Paolo Bonzini
  Cc: Alex Bennée, Thomas Huth, Richard Henderson, qemu-devel

[-- Attachment #1: Type: text/plain, Size: 819 bytes --]

On Wed, Sep 16, 2020 at 1:14 AM Paolo Bonzini <pbonzini@redhat.com> wrote:
>
> On 15/09/20 19:07, 罗勇刚(Yonggang Luo) wrote:
> >
> >     Linux distributions generally do not want to have bundled
libraries, so
> >
> > Yes, bundled libraries is a bad idea, but static linked library is
> > another case, that won't affect
> > the Linux distributions.
>
> As far as Linux distributions are concerned, static linking is a case of
> bundling.  Bundling means that, for example, any security issue will
> require rebuilding the package that does the bundling (this applies
> especially to slirp among the three that QEMU we bundles).

Oh, see that, so capstone and  libfdt doesn't have the security concern?
>
>
> Paolo
>


--
         此致
礼
罗勇刚
Yours
    sincerely,
Yonggang Luo

[-- Attachment #2: Type: text/html, Size: 1039 bytes --]

^ permalink raw reply	[flat|nested] 29+ messages in thread

* Re: [PATCH v2 04/10] disas: Clean up CPUDebug initialization
  2020-09-14 23:02 ` [PATCH v2 04/10] disas: Clean up CPUDebug initialization Richard Henderson
@ 2020-09-17 14:39   ` Thomas Huth
  2020-09-17 14:50   ` Thomas Huth
  1 sibling, 0 replies; 29+ messages in thread
From: Thomas Huth @ 2020-09-17 14:39 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel; +Cc: luoyonggang, alex.bennee

On 15/09/2020 01.02, Richard Henderson wrote:
> Rename several functions, dropping "generic" and making "host"
> vs "target" clearer.  Make a bunch of functions static that are
> not used outside this file. Replace INIT_DISASSEMBLE_INFO with
> a trio of functions.
> 
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
> ---
>  include/disas/dis-asm.h |  60 --------
>  disas.c                 | 326 ++++++++++++++++++----------------------
>  2 files changed, 148 insertions(+), 238 deletions(-)

I only did a quick review... looks fine to me, so:
Acked-by: Thomas Huth <thuth@redhat.com>



^ permalink raw reply	[flat|nested] 29+ messages in thread

* Re: [PATCH v2 07/10] disas: Configure capstone for aarch64 host without libvixl
  2020-09-14 23:02 ` [PATCH v2 07/10] disas: Configure capstone for aarch64 host without libvixl Richard Henderson
@ 2020-09-17 14:44   ` Thomas Huth
  0 siblings, 0 replies; 29+ messages in thread
From: Thomas Huth @ 2020-09-17 14:44 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel; +Cc: Peter Maydell, luoyonggang, alex.bennee

On 15/09/2020 01.02, Richard Henderson wrote:
> The ifdef tangle failed to set cap_arch if libvixl itself
> was not configured (e.g. due to lack of c++ compiler).
> 
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
> ---
>  disas.c | 6 ++++--
>  1 file changed, 4 insertions(+), 2 deletions(-)
> 
> diff --git a/disas.c b/disas.c
> index d0ccd4b727..01c8bc6c9e 100644
> --- a/disas.c
> +++ b/disas.c
> @@ -428,9 +428,11 @@ static void initialize_debug_host(CPUDebug *s)
>  #else
>  #error unsupported RISC-V ABI
>  #endif
> -#elif defined(__aarch64__) && defined(CONFIG_ARM_A64_DIS)
> -    s->info.print_insn = print_insn_arm_a64;
> +#elif defined(__aarch64__)
>      s->info.cap_arch = CS_ARCH_ARM64;
> +# ifdef CONFIG_ARM_A64_DIS
> +    s->info.print_insn = print_insn_arm_a64;
> +# endif
>  #elif defined(__alpha__)
>      s->info.print_insn = print_insn_alpha;
>  #elif defined(__sparc__)
> 

Reviewed-by: Thomas Huth <thuth@redhat.com>



^ permalink raw reply	[flat|nested] 29+ messages in thread

* Re: [PATCH v2 04/10] disas: Clean up CPUDebug initialization
  2020-09-14 23:02 ` [PATCH v2 04/10] disas: Clean up CPUDebug initialization Richard Henderson
  2020-09-17 14:39   ` Thomas Huth
@ 2020-09-17 14:50   ` Thomas Huth
  2020-09-17 17:06     ` Alex Bennée
  1 sibling, 1 reply; 29+ messages in thread
From: Thomas Huth @ 2020-09-17 14:50 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel; +Cc: luoyonggang, alex.bennee

On 15/09/2020 01.02, Richard Henderson wrote:
> Rename several functions, dropping "generic" and making "host"
> vs "target" clearer.  Make a bunch of functions static that are
> not used outside this file. Replace INIT_DISASSEMBLE_INFO with
> a trio of functions.
> 
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
> ---
>  include/disas/dis-asm.h |  60 --------
>  disas.c                 | 326 ++++++++++++++++++----------------------
>  2 files changed, 148 insertions(+), 238 deletions(-)
> 
> diff --git a/include/disas/dis-asm.h b/include/disas/dis-asm.h
> index 9856bf7921..d2418c977e 100644
> --- a/include/disas/dis-asm.h
> +++ b/include/disas/dis-asm.h
> @@ -461,67 +461,7 @@ int print_insn_riscv32          (bfd_vma, disassemble_info*);
>  int print_insn_riscv64          (bfd_vma, disassemble_info*);
>  int print_insn_rx(bfd_vma, disassemble_info *);
>  
> -#if 0
> -/* Fetch the disassembler for a given BFD, if that support is available.  */
> -disassembler_ftype disassembler(bfd *);
> -#endif
> -
>  \f

By the way, while you're at it, could you please also remove the form
feed character in this file here? ... that looks really confusing in my
e-mail client otherwise.

 Thanks,
  Thomas



^ permalink raw reply	[flat|nested] 29+ messages in thread

* Re: [PATCH v2 09/10] disas: Enable capstone disassembly for s390x
  2020-09-14 23:02 ` [PATCH v2 09/10] disas: Enable capstone disassembly for s390x Richard Henderson
@ 2020-09-17 16:30   ` Thomas Huth
  0 siblings, 0 replies; 29+ messages in thread
From: Thomas Huth @ 2020-09-17 16:30 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel; +Cc: luoyonggang, alex.bennee, qemu-s390x

On 15/09/2020 01.02, Richard Henderson wrote:
> Enable s390x, aka SYSZ, in the git submodule build.
> Set the capstone parameters for both s390x host and guest.
> 
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
> ---
>  disas.c            |  3 +++
>  target/s390x/cpu.c |  4 ++++
>  meson.build        | 11 +++++++++++
>  3 files changed, 18 insertions(+)
> 
> diff --git a/disas.c b/disas.c
> index e27dea2c19..c4cd305190 100644
> --- a/disas.c
> +++ b/disas.c
> @@ -201,6 +201,9 @@ static void initialize_debug_host(CPUDebug *s)
>      s->info.print_insn = print_insn_m68k;
>  #elif defined(__s390__)
>      s->info.print_insn = print_insn_s390;
> +    s->info.cap_arch = CS_ARCH_SYSZ;
> +    s->info.cap_insn_unit = 2;
> +    s->info.cap_insn_split = 6;
>  #elif defined(__hppa__)
>      s->info.print_insn = print_insn_hppa;
>  #endif
> diff --git a/target/s390x/cpu.c b/target/s390x/cpu.c
> index 749cd548f0..2a96692691 100644
> --- a/target/s390x/cpu.c
> +++ b/target/s390x/cpu.c
> @@ -44,6 +44,7 @@
>  #include "sysemu/tcg.h"
>  #endif
>  #include "fpu/softfloat-helpers.h"
> +#include "disas/capstone.h"
>  
>  #define CR0_RESET       0xE0UL
>  #define CR14_RESET      0xC2000000UL;
> @@ -182,6 +183,9 @@ static void s390_cpu_disas_set_info(CPUState *cpu, disassemble_info *info)
>  {
>      info->mach = bfd_mach_s390_64;
>      info->print_insn = print_insn_s390;
> +    info->cap_arch = CS_ARCH_SYSZ;
> +    info->cap_insn_unit = 2;
> +    info->cap_insn_split = 6;
>  }
>  
>  static void s390_cpu_realizefn(DeviceState *dev, Error **errp)
> diff --git a/meson.build b/meson.build
> index 2f3da5d8c6..448c87f645 100644
> --- a/meson.build
> +++ b/meson.build
> @@ -674,6 +674,17 @@ if capstone_opt == 'internal'
>      )
>    endif
>  
> +  if 'CONFIG_S390_DIS' in config_all_disas
> +    capstone_data.set('CAPSTONE_HAS_SYSZ', '1')
> +    capstone_files += files(
> +      'capstone/arch/SystemZ/SystemZDisassembler.c',
> +      'capstone/arch/SystemZ/SystemZInstPrinter.c',
> +      'capstone/arch/SystemZ/SystemZMapping.c',
> +      'capstone/arch/SystemZ/SystemZModule.c',
> +      'capstone/arch/SystemZ/SystemZMCTargetDesc.c'
> +    )
> +  endif
> +
>    if 'CONFIG_I386_DIS' in config_all_disas
>      capstone_data.set('CAPSTONE_HAS_X86', 1)
>      capstone_files += files(
> 

Acked-by: Thomas Huth <thuth@redhat.com>



^ permalink raw reply	[flat|nested] 29+ messages in thread

* Re: [PATCH v2 10/10] disas/capstone: Add skipdata hook for s390x
  2020-09-14 23:02 ` [PATCH v2 10/10] disas/capstone: Add skipdata hook " Richard Henderson
@ 2020-09-17 16:32   ` Thomas Huth
  0 siblings, 0 replies; 29+ messages in thread
From: Thomas Huth @ 2020-09-17 16:32 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel
  Cc: qemu-s390x, luoyonggang, alex.bennee, Philippe Mathieu-Daudé

On 15/09/2020 01.02, Richard Henderson wrote:
> It is always possible to tell the length of an insn, even if the
> actual insn is unknown.  Skip the correct number of bytes, so that
> we stay in sync with the instruction stream.
> 
> Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
> ---
>  disas/capstone.c | 42 +++++++++++++++++++++++++++++++++++++++++-
>  1 file changed, 41 insertions(+), 1 deletion(-)
> 
> diff --git a/disas/capstone.c b/disas/capstone.c
> index b48f83958d..0a9ef9c892 100644
> --- a/disas/capstone.c
> +++ b/disas/capstone.c
> @@ -16,6 +16,39 @@
>   */
>  static __thread cs_insn *cap_insn;
>  
> +/*
> + * The capstone library always skips 2 bytes for S390X.
> + * This is less than ideal, since we can tell from the first two bits
> + * the size of the insn and thus stay in sync with the insn stream.
> + */
> +static size_t CAPSTONE_API
> +cap_skipdata_s390x_cb(const uint8_t *code, size_t code_size,
> +                      size_t offset, void *user_data)
> +{
> +    size_t ilen;
> +
> +    /* See get_ilen() in target/s390x/internal.h.  */
> +    switch (code[offset] >> 6) {
> +    case 0:
> +        ilen = 2;
> +        break;
> +    case 1:
> +    case 2:
> +        ilen = 4;
> +        break;
> +    default:
> +        ilen = 6;
> +        break;
> +    }
> +
> +    return ilen;
> +}
> +
> +static const cs_opt_skipdata cap_skipdata_s390x = {
> +    .mnemonic = ".byte",
> +    .callback = cap_skipdata_s390x_cb
> +};
> +
>  /*
>   * Initialize the Capstone library.
>   *
> @@ -42,13 +75,20 @@ static cs_err cap_disas_start(disassemble_info *info, csh *handle)
>      /* "Disassemble" unknown insns as ".byte W,X,Y,Z".  */
>      cs_option(*handle, CS_OPT_SKIPDATA, CS_OPT_ON);
>  
> -    if (info->cap_arch == CS_ARCH_X86) {
> +    switch (info->cap_arch) {
> +    case CS_ARCH_SYSZ:
> +        cs_option(*handle, CS_OPT_SKIPDATA_SETUP,
> +                  (uintptr_t)&cap_skipdata_s390x);
> +        break;
> +
> +    case CS_ARCH_X86:
>          /*
>           * We don't care about errors (if for some reason the library
>           * is compiled without AT&T syntax); the user will just have
>           * to deal with the Intel syntax.
>           */
>          cs_option(*handle, CS_OPT_SYNTAX, CS_OPT_SYNTAX_ATT);
> +        break;
>      }
>  
>      /* Allocate temp space for cs_disasm_iter.  */
> 

Acked-by: Thomas Huth <thuth@redhat.com>



^ permalink raw reply	[flat|nested] 29+ messages in thread

* Re: [PATCH v2 04/10] disas: Clean up CPUDebug initialization
  2020-09-17 14:50   ` Thomas Huth
@ 2020-09-17 17:06     ` Alex Bennée
  2020-09-17 20:20       ` Richard Henderson
  0 siblings, 1 reply; 29+ messages in thread
From: Alex Bennée @ 2020-09-17 17:06 UTC (permalink / raw)
  To: Thomas Huth; +Cc: luoyonggang, Richard Henderson, qemu-devel


Thomas Huth <thuth@redhat.com> writes:

> On 15/09/2020 01.02, Richard Henderson wrote:
>> Rename several functions, dropping "generic" and making "host"
>> vs "target" clearer.  Make a bunch of functions static that are
>> not used outside this file. Replace INIT_DISASSEMBLE_INFO with
>> a trio of functions.
>> 
>> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
>> ---
>>  include/disas/dis-asm.h |  60 --------
>>  disas.c                 | 326 ++++++++++++++++++----------------------
>>  2 files changed, 148 insertions(+), 238 deletions(-)
>> 
>> diff --git a/include/disas/dis-asm.h b/include/disas/dis-asm.h
>> index 9856bf7921..d2418c977e 100644
>> --- a/include/disas/dis-asm.h
>> +++ b/include/disas/dis-asm.h
>> @@ -461,67 +461,7 @@ int print_insn_riscv32          (bfd_vma, disassemble_info*);
>>  int print_insn_riscv64          (bfd_vma, disassemble_info*);
>>  int print_insn_rx(bfd_vma, disassemble_info *);
>>  
>> -#if 0
>> -/* Fetch the disassembler for a given BFD, if that support is available.  */
>> -disassembler_ftype disassembler(bfd *);
>> -#endif
>> -
>>  \f
>
> By the way, while you're at it, could you please also remove the form
> feed character in this file here? ... that looks really confusing in my
> e-mail client otherwise.

I'm not entirely convinced that is from Richard. I've been seeing rouge
^L and ^M's from all sorts of normally unix clean contributors. I smell
mailing list shenanigans.

-- 
Alex Bennée


^ permalink raw reply	[flat|nested] 29+ messages in thread

* Re: [PATCH v2 04/10] disas: Clean up CPUDebug initialization
  2020-09-17 17:06     ` Alex Bennée
@ 2020-09-17 20:20       ` Richard Henderson
  0 siblings, 0 replies; 29+ messages in thread
From: Richard Henderson @ 2020-09-17 20:20 UTC (permalink / raw)
  To: Alex Bennée, Thomas Huth; +Cc: luoyonggang, qemu-devel

On 9/17/20 10:06 AM, Alex Bennée wrote:
>> By the way, while you're at it, could you please also remove the form
>> feed character in this file here? ... that looks really confusing in my
>> e-mail client otherwise.

I guess, sure.

> I'm not entirely convinced that is from Richard. I've been seeing rouge
> ^L and ^M's from all sorts of normally unix clean contributors. I smell
> mailing list shenanigans.

No, form-feed is an old gnu coding style; we got this via import.  It's some
emacs next-page thing, I think.


r~


^ permalink raw reply	[flat|nested] 29+ messages in thread

end of thread, other threads:[~2020-09-17 20:22 UTC | newest]

Thread overview: 29+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2020-09-14 23:02 [PATCH v2 00/10] capstone + disassembler patches Richard Henderson
2020-09-14 23:02 ` [PATCH v2 01/10] capstone: Convert Makefile bits to meson bits Richard Henderson
2020-09-14 23:06   ` Richard Henderson
2020-09-15  6:27     ` Paolo Bonzini
2020-09-15 14:27       ` Richard Henderson
2020-09-15 16:12         ` 罗勇刚(Yonggang Luo)
2020-09-15 16:59           ` Paolo Bonzini
2020-09-15 17:07             ` 罗勇刚(Yonggang Luo)
2020-09-15 17:14               ` Paolo Bonzini
2020-09-15 17:20                 ` 罗勇刚(Yonggang Luo)
2020-09-15 16:58         ` Paolo Bonzini
2020-09-15  6:10   ` Thomas Huth
2020-09-14 23:02 ` [PATCH v2 02/10] capstone: Update to upstream "next" branch Richard Henderson
2020-09-14 23:02 ` [PATCH v2 03/10] disas: Move host asm annotations to tb_gen_code Richard Henderson
2020-09-15 16:36   ` Thomas Huth
2020-09-14 23:02 ` [PATCH v2 04/10] disas: Clean up CPUDebug initialization Richard Henderson
2020-09-17 14:39   ` Thomas Huth
2020-09-17 14:50   ` Thomas Huth
2020-09-17 17:06     ` Alex Bennée
2020-09-17 20:20       ` Richard Henderson
2020-09-14 23:02 ` [PATCH v2 05/10] disas: Use qemu/bswap.h for bfd endian loads Richard Henderson
2020-09-14 23:02 ` [PATCH v2 06/10] disas: Cleanup plugin_disas Richard Henderson
2020-09-14 23:02 ` [PATCH v2 07/10] disas: Configure capstone for aarch64 host without libvixl Richard Henderson
2020-09-17 14:44   ` Thomas Huth
2020-09-14 23:02 ` [PATCH v2 08/10] disas: Split out capstone code to disas/capstone.c Richard Henderson
2020-09-14 23:02 ` [PATCH v2 09/10] disas: Enable capstone disassembly for s390x Richard Henderson
2020-09-17 16:30   ` Thomas Huth
2020-09-14 23:02 ` [PATCH v2 10/10] disas/capstone: Add skipdata hook " Richard Henderson
2020-09-17 16:32   ` Thomas Huth

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.