target/arm: Move the vfp decodetree calls next to the base isa

Have the calls adjacent as an intermediate step toward
actually merging the decodes.

Backports commit f0f6d5c81be47d593e5ece7f06df6fba4c15738b from qemu
This commit is contained in:
Richard Henderson 2020-03-21 23:54:54 -04:00 committed by Lioncash
parent f1ce64857c
commit 4ce91875e4

View File

@ -2728,32 +2728,6 @@ static void gen_neon_dup_high16(DisasContext *s, TCGv_i32 var)
tcg_temp_free_i32(tcg_ctx, tmp); tcg_temp_free_i32(tcg_ctx, tmp);
} }
/*
* Disassemble a VFP instruction. Returns nonzero if an error occurred
* (ie. an undefined instruction).
*/
static int disas_vfp_insn(DisasContext *s, uint32_t insn)
{
/*
* If the decodetree decoder handles this insn it will always
* emit code to either execute the insn or generate an appropriate
* exception; so we don't need to ever return non-zero to tell
* the calling code to emit an UNDEF exception.
*/
if (extract32(insn, 28, 4) == 0xf) {
if (disas_vfp_uncond(s, insn)) {
return 0;
}
} else {
if (disas_vfp(s, insn)) {
return 0;
}
}
/* If the decodetree decoder didn't handle this insn, it must be UNDEF */
return 1;
}
static inline bool use_goto_tb(DisasContext *s, target_ulong dest) static inline bool use_goto_tb(DisasContext *s, target_ulong dest)
{ {
#ifndef CONFIG_USER_ONLY #ifndef CONFIG_USER_ONLY
@ -11086,7 +11060,9 @@ static void disas_arm_insn(DisasContext *s, unsigned int insn)
ARCH(5); ARCH(5);
/* Unconditional instructions. */ /* Unconditional instructions. */
if (disas_a32_uncond(s, insn)) { /* TODO: Perhaps merge these into one decodetree output file. */
if (disas_a32_uncond(s, insn) ||
disas_vfp_uncond(s, insn)) {
return; return;
} }
/* fall back to legacy decoder */ /* fall back to legacy decoder */
@ -11113,13 +11089,6 @@ static void disas_arm_insn(DisasContext *s, unsigned int insn)
} }
return; return;
} }
if ((insn & 0x0f000e10) == 0x0e000a00) {
/* VFP. */
if (disas_vfp_insn(s, insn)) {
goto illegal_op;
}
return;
}
if ((insn & 0x0e000f00) == 0x0c000100) { if ((insn & 0x0e000f00) == 0x0c000100) {
if (arm_dc_feature(s, ARM_FEATURE_IWMMXT)) { if (arm_dc_feature(s, ARM_FEATURE_IWMMXT)) {
/* iWMMXt register transfer. */ /* iWMMXt register transfer. */
@ -11150,7 +11119,9 @@ static void disas_arm_insn(DisasContext *s, unsigned int insn)
arm_skip_unless(s, cond); arm_skip_unless(s, cond);
} }
if (disas_a32(s, insn)) { /* TODO: Perhaps merge these into one decodetree output file. */
if (disas_a32(s, insn) ||
disas_vfp(s, insn)) {
return; return;
} }
/* fall back to legacy decoder */ /* fall back to legacy decoder */
@ -11160,11 +11131,10 @@ static void disas_arm_insn(DisasContext *s, unsigned int insn)
case 0xd: case 0xd:
case 0xe: case 0xe:
if (((insn >> 8) & 0xe) == 10) { if (((insn >> 8) & 0xe) == 10) {
/* VFP. */ /* VFP, but failed disas_vfp. */
if (disas_vfp_insn(s, insn)) { goto illegal_op;
goto illegal_op; }
} if (disas_coproc_insn(s, insn)) {
} else if (disas_coproc_insn(s, insn)) {
/* Coprocessor. */ /* Coprocessor. */
goto illegal_op; goto illegal_op;
} }
@ -11253,7 +11223,14 @@ static void disas_thumb2_insn(DisasContext *s, uint32_t insn)
ARCH(6T2); ARCH(6T2);
} }
if (disas_t32(s, insn)) { /*
* TODO: Perhaps merge these into one decodetree output file.
* Note disas_vfp is written for a32 with cond field in the
* top nibble. The t32 encoding requires 0xe in the top nibble.
*/
if (disas_t32(s, insn) ||
disas_vfp_uncond(s, insn) ||
((insn >> 28) == 0xe && disas_vfp(s, insn))) {
return; return;
} }
/* fall back to legacy decoder */ /* fall back to legacy decoder */
@ -11270,17 +11247,15 @@ static void disas_thumb2_insn(DisasContext *s, uint32_t insn)
goto illegal_op; /* op0 = 0b11 : unallocated */ goto illegal_op; /* op0 = 0b11 : unallocated */
} }
if (disas_vfp_insn(s, insn)) { if (((insn >> 8) & 0xe) == 10 &&
if (((insn >> 8) & 0xe) == 10 && dc_isar_feature(aa32_fpsp_v2, s)) {
dc_isar_feature(aa32_fpsp_v2, s)) { /* FP, and the CPU supports it */
/* FP, and the CPU supports it */ goto illegal_op;
goto illegal_op; } else {
} else { /* All other insns: NOCP */
/* All other insns: NOCP */ gen_exception_insn(s, s->pc_curr, EXCP_NOCP,
gen_exception_insn(s, s->pc_curr, EXCP_NOCP, syn_uncategorized(),
syn_uncategorized(), default_exception_el(s));
default_exception_el(s));
}
} }
break; break;
} }
@ -11303,9 +11278,8 @@ static void disas_thumb2_insn(DisasContext *s, uint32_t insn)
goto illegal_op; goto illegal_op;
} }
} else if (((insn >> 8) & 0xe) == 10) { } else if (((insn >> 8) & 0xe) == 10) {
if (disas_vfp_insn(s, insn)) { /* VFP, but failed disas_vfp. */
goto illegal_op; goto illegal_op;
}
} else { } else {
if (insn & (1 << 28)) if (insn & (1 << 28))
goto illegal_op; goto illegal_op;