mirror of
https://github.com/yuzu-emu/unicorn.git
synced 2025-01-22 18:11:02 +00:00
target/arm: Convert MSR (immediate) and hints
Backports commit 6313059623dc512308681ba160ed862ac387e2fb from qemu
This commit is contained in:
parent
a011318794
commit
571d879c49
|
@ -22,6 +22,7 @@
|
|||
# All insns that have 0xf in insn[31:28] are in a32-uncond.decode.
|
||||
#
|
||||
|
||||
&empty
|
||||
&s_rrr_shi s rd rn rm shim shty
|
||||
&s_rrr_shr s rn rd rm rs shty
|
||||
&s_rri_rot s rn rd imm rot
|
||||
|
@ -152,3 +153,27 @@ SMULBB .... 0001 0110 .... 0000 .... 1000 .... @rd0mn
|
|||
SMULBT .... 0001 0110 .... 0000 .... 1100 .... @rd0mn
|
||||
SMULTB .... 0001 0110 .... 0000 .... 1010 .... @rd0mn
|
||||
SMULTT .... 0001 0110 .... 0000 .... 1110 .... @rd0mn
|
||||
|
||||
# MSR (immediate) and hints
|
||||
|
||||
&msr_i r mask rot imm
|
||||
@msr_i ---- .... .... mask:4 .... rot:4 imm:8 &msr_i
|
||||
|
||||
{
|
||||
{
|
||||
YIELD ---- 0011 0010 0000 1111 ---- 0000 0001
|
||||
WFE ---- 0011 0010 0000 1111 ---- 0000 0010
|
||||
WFI ---- 0011 0010 0000 1111 ---- 0000 0011
|
||||
|
||||
# TODO: Implement SEV, SEVL; may help SMP performance.
|
||||
# SEV ---- 0011 0010 0000 1111 ---- 0000 0100
|
||||
# SEVL ---- 0011 0010 0000 1111 ---- 0000 0101
|
||||
|
||||
# The canonical nop ends in 00000000, but the whole of the
|
||||
# rest of the space executes as nop if otherwise unsupported.
|
||||
NOP ---- 0011 0010 0000 1111 ---- ---- ----
|
||||
}
|
||||
# Note mask = 0 is covered by NOP
|
||||
MSR_imm .... 0011 0010 .... 1111 .... .... .... @msr_i r=0
|
||||
}
|
||||
MSR_imm .... 0011 0110 .... 1111 .... .... .... @msr_i r=1
|
||||
|
|
|
@ -19,6 +19,7 @@
|
|||
# This file is processed by scripts/decodetree.py
|
||||
#
|
||||
|
||||
&empty !extern
|
||||
&s_rrr_shi !extern s rd rn rm shim shty
|
||||
&s_rrr_shr !extern s rn rd rm rs shty
|
||||
&s_rri_rot !extern s rn rd imm rot
|
||||
|
@ -166,3 +167,19 @@ QADD 1111 1010 1000 .... 1111 .... 1000 .... @rndm
|
|||
QSUB 1111 1010 1000 .... 1111 .... 1010 .... @rndm
|
||||
QDADD 1111 1010 1000 .... 1111 .... 1001 .... @rndm
|
||||
QDSUB 1111 1010 1000 .... 1111 .... 1011 .... @rndm
|
||||
|
||||
# Branches and miscellaneous control
|
||||
|
||||
{
|
||||
YIELD 1111 0011 1010 1111 1000 0000 0000 0001
|
||||
WFE 1111 0011 1010 1111 1000 0000 0000 0010
|
||||
WFI 1111 0011 1010 1111 1000 0000 0000 0011
|
||||
|
||||
# TODO: Implement SEV, SEVL; may help SMP performance.
|
||||
# SEV 1111 0011 1010 1111 1000 0000 0000 0100
|
||||
# SEVL 1111 0011 1010 1111 1000 0000 0000 0101
|
||||
|
||||
# The canonical nop ends in 0000 0000, but the whole rest
|
||||
# of the space is "reserved hint, behaves as nop".
|
||||
NOP 1111 0011 1010 1111 1000 0000 ---- ----
|
||||
}
|
||||
|
|
|
@ -8504,6 +8504,44 @@ DO_SMLAWX(SMLAWT, 1, 1)
|
|||
|
||||
#undef DO_SMLAWX
|
||||
|
||||
/*
|
||||
* MSR (immediate) and hints
|
||||
*/
|
||||
|
||||
static bool trans_YIELD(DisasContext *s, arg_YIELD *a)
|
||||
{
|
||||
gen_nop_hint(s, 1);
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool trans_WFE(DisasContext *s, arg_WFE *a)
|
||||
{
|
||||
gen_nop_hint(s, 2);
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool trans_WFI(DisasContext *s, arg_WFI *a)
|
||||
{
|
||||
gen_nop_hint(s, 3);
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool trans_NOP(DisasContext *s, arg_NOP *a)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool trans_MSR_imm(DisasContext *s, arg_MSR_imm *a)
|
||||
{
|
||||
uint32_t val = ror32(a->imm, a->rot * 2);
|
||||
uint32_t mask = msr_mask(s, a->mask, a->r);
|
||||
|
||||
if (gen_set_psr_im(s, mask, a->r, val)) {
|
||||
unallocated_encoding(s);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
/*
|
||||
* Legacy decoder.
|
||||
*/
|
||||
|
@ -8786,21 +8824,9 @@ static void disas_arm_insn(DisasContext *s, unsigned int insn)
|
|||
}
|
||||
store_reg(s, rd, tmp);
|
||||
} else {
|
||||
if (((insn >> 12) & 0xf) != 0xf)
|
||||
goto illegal_op;
|
||||
if (((insn >> 16) & 0xf) == 0) {
|
||||
gen_nop_hint(s, insn & 0xff);
|
||||
} else {
|
||||
/* CPSR = immediate */
|
||||
val = insn & 0xff;
|
||||
shift = ((insn >> 8) & 0xf) * 2;
|
||||
val = ror32(val, shift);
|
||||
i = ((insn & (1 << 22)) != 0);
|
||||
if (gen_set_psr_im(s, msr_mask(s, (insn >> 16) & 0xf, i),
|
||||
i, val)) {
|
||||
goto illegal_op;
|
||||
}
|
||||
}
|
||||
/* MSR (immediate) and hints */
|
||||
/* All done in decodetree. Illegal ops already signalled. */
|
||||
g_assert_not_reached();
|
||||
}
|
||||
} else if ((insn & 0x0f900000) == 0x01000000
|
||||
&& (insn & 0x00000090) != 0x00000090) {
|
||||
|
@ -10751,9 +10777,7 @@ static void disas_thumb2_insn(DisasContext *s, uint32_t insn)
|
|||
goto illegal_op;
|
||||
break;
|
||||
case 2: /* cps, nop-hint. */
|
||||
if (((insn >> 8) & 7) == 0) {
|
||||
gen_nop_hint(s, insn & 0xff);
|
||||
}
|
||||
/* nop hints in decodetree */
|
||||
/* Implemented as NOP in user mode. */
|
||||
if (IS_USER(s))
|
||||
break;
|
||||
|
|
Loading…
Reference in a new issue