mirror of
https://github.com/xemu-project/xemu.git
synced 2024-11-24 03:59:52 +00:00
target-tilegx: Support iret instruction and related special registers
EX_CONTEXT_0_0 is used for jumping address, and EX_CONTEXT_0_1 is for INTERRUPT_CRITICAL_SECTION, which should only be 0 or 1 in user mode, or it will cause target SIGILL (and the patch doesn't support system mode). Signed-off-by: Chen Gang <gang.chen.5i5j@gmail.com> Signed-off-by: Richard Henderson <rth@twiddle.net>
This commit is contained in:
parent
77b3adc001
commit
fec7daab3d
@ -53,6 +53,8 @@ enum {
|
||||
TILEGX_SPR_CMPEXCH = 0,
|
||||
TILEGX_SPR_CRITICAL_SEC = 1,
|
||||
TILEGX_SPR_SIM_CONTROL = 2,
|
||||
TILEGX_SPR_EX_CONTEXT_0_0 = 3,
|
||||
TILEGX_SPR_EX_CONTEXT_0_1 = 4,
|
||||
TILEGX_SPR_COUNT
|
||||
};
|
||||
|
||||
|
@ -22,6 +22,7 @@
|
||||
#include "qemu-common.h"
|
||||
#include "exec/helper-proto.h"
|
||||
#include <zlib.h> /* For crc32 */
|
||||
#include "syscall_defs.h"
|
||||
|
||||
void helper_exception(CPUTLGState *env, uint32_t excp)
|
||||
{
|
||||
@ -31,6 +32,27 @@ void helper_exception(CPUTLGState *env, uint32_t excp)
|
||||
cpu_loop_exit(cs);
|
||||
}
|
||||
|
||||
void helper_ext01_ics(CPUTLGState *env)
|
||||
{
|
||||
uint64_t val = env->spregs[TILEGX_SPR_EX_CONTEXT_0_1];
|
||||
|
||||
switch (val) {
|
||||
case 0:
|
||||
case 1:
|
||||
env->spregs[TILEGX_SPR_CRITICAL_SEC] = val;
|
||||
break;
|
||||
default:
|
||||
#if defined(CONFIG_USER_ONLY)
|
||||
env->signo = TARGET_SIGILL;
|
||||
env->sigcode = TARGET_ILL_ILLOPC;
|
||||
helper_exception(env, TILEGX_EXCP_SIGNAL);
|
||||
#else
|
||||
helper_exception(env, TILEGX_EXCP_OPCODE_UNIMPLEMENTED);
|
||||
#endif
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
uint64_t helper_cntlz(uint64_t arg)
|
||||
{
|
||||
return clz64(arg);
|
||||
|
@ -1,4 +1,5 @@
|
||||
DEF_HELPER_2(exception, noreturn, env, i32)
|
||||
DEF_HELPER_1(ext01_ics, void, env)
|
||||
DEF_HELPER_FLAGS_1(cntlz, TCG_CALL_NO_RWG_SE, i64, i64)
|
||||
DEF_HELPER_FLAGS_1(cnttz, TCG_CALL_NO_RWG_SE, i64, i64)
|
||||
DEF_HELPER_FLAGS_1(pcnt, TCG_CALL_NO_RWG_SE, i64, i64)
|
||||
|
@ -529,6 +529,15 @@ static TileExcp gen_rr_opcode(DisasContext *dc, unsigned opext,
|
||||
/* ??? This should yield, especially in system mode. */
|
||||
mnemonic = "nap";
|
||||
goto done0;
|
||||
case OE_RR_X1(IRET):
|
||||
gen_helper_ext01_ics(cpu_env);
|
||||
dc->jmp.cond = TCG_COND_ALWAYS;
|
||||
dc->jmp.dest = tcg_temp_new();
|
||||
tcg_gen_ld_tl(dc->jmp.dest, cpu_env,
|
||||
offsetof(CPUTLGState, spregs[TILEGX_SPR_EX_CONTEXT_0_0]));
|
||||
tcg_gen_andi_tl(dc->jmp.dest, dc->jmp.dest, ~7);
|
||||
mnemonic = "iret";
|
||||
goto done0;
|
||||
case OE_RR_X1(SWINT0):
|
||||
case OE_RR_X1(SWINT2):
|
||||
case OE_RR_X1(SWINT3):
|
||||
@ -606,7 +615,6 @@ static TileExcp gen_rr_opcode(DisasContext *dc, unsigned opext,
|
||||
break;
|
||||
case OE_RR_X0(FSINGLE_PACK1):
|
||||
case OE_RR_Y0(FSINGLE_PACK1):
|
||||
case OE_RR_X1(IRET):
|
||||
return TILEGX_EXCP_OPCODE_UNIMPLEMENTED;
|
||||
case OE_RR_X1(LD1S):
|
||||
memop = MO_SB;
|
||||
@ -1947,6 +1955,10 @@ static const TileSPR *find_spr(unsigned spr)
|
||||
offsetof(CPUTLGState, spregs[TILEGX_SPR_CRITICAL_SEC]), 0, 0)
|
||||
D(SIM_CONTROL,
|
||||
offsetof(CPUTLGState, spregs[TILEGX_SPR_SIM_CONTROL]), 0, 0)
|
||||
D(EX_CONTEXT_0_0,
|
||||
offsetof(CPUTLGState, spregs[TILEGX_SPR_EX_CONTEXT_0_0]), 0, 0)
|
||||
D(EX_CONTEXT_0_1,
|
||||
offsetof(CPUTLGState, spregs[TILEGX_SPR_EX_CONTEXT_0_1]), 0, 0)
|
||||
}
|
||||
|
||||
#undef D
|
||||
|
Loading…
Reference in New Issue
Block a user