Message ID | 20200914000153.1725632-11-richard.henderson@linaro.org |
---|---|
State | Accepted |
Commit | c6d3da962f058bca09b25f99da35436816fb6de8 |
Headers | show |
Series | capstone + disassembler patches | expand |
On 9/14/20 2:01 AM, 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. > > Signed-off-by: Richard Henderson <richard.henderson@linaro.org> Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.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. */ >
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. */
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. Signed-off-by: Richard Henderson <richard.henderson@linaro.org> --- disas/capstone.c | 42 +++++++++++++++++++++++++++++++++++++++++- 1 file changed, 41 insertions(+), 1 deletion(-) -- 2.25.1