diff options
Diffstat (limited to 'src/core/arm')
-rw-r--r-- | src/core/arm/dyncom/arm_dyncom_dec.cpp | 2 | ||||
-rw-r--r-- | src/core/arm/dyncom/arm_dyncom_interpreter.cpp | 29 | ||||
-rw-r--r-- | src/core/arm/skyeye_common/armemu.h | 2 | ||||
-rw-r--r-- | src/core/arm/skyeye_common/vfp/vfpdouble.cpp | 4 | ||||
-rw-r--r-- | src/core/arm/skyeye_common/vfp/vfpinstr.cpp | 8 |
5 files changed, 36 insertions, 9 deletions
diff --git a/src/core/arm/dyncom/arm_dyncom_dec.cpp b/src/core/arm/dyncom/arm_dyncom_dec.cpp index ffa627352..9f3b90fd0 100644 --- a/src/core/arm/dyncom/arm_dyncom_dec.cpp +++ b/src/core/arm/dyncom/arm_dyncom_dec.cpp @@ -42,7 +42,7 @@ const ISEITEM arm_instruction[] = { { "srs", 4, 6, 25, 31, 0x0000007c, 22, 22, 0x00000001, 16, 20, 0x0000000d, 8, 11, 0x00000005 }, { "rfe", 4, 6, 25, 31, 0x0000007c, 22, 22, 0x00000000, 20, 20, 0x00000001, 8, 11, 0x0000000a }, - { "bkpt", 2, 3, 20, 31, 0x00000e12, 4, 7, 0x00000007 }, + { "bkpt", 2, 3, 20, 27, 0x00000012, 4, 7, 0x00000007 }, { "blx", 1, 3, 25, 31, 0x0000007d }, { "cps", 3, 6, 20, 31, 0x00000f10, 16, 16, 0x00000000, 5, 5, 0x00000000 }, { "pld", 4, 4, 26, 31, 0x0000003d, 24, 24, 0x00000001, 20, 22, 0x00000005, 12, 15, 0x0000000f }, diff --git a/src/core/arm/dyncom/arm_dyncom_interpreter.cpp b/src/core/arm/dyncom/arm_dyncom_interpreter.cpp index f4b3c4734..b691ffbc3 100644 --- a/src/core/arm/dyncom/arm_dyncom_interpreter.cpp +++ b/src/core/arm/dyncom/arm_dyncom_interpreter.cpp @@ -792,6 +792,7 @@ typedef struct _stm_inst { } stm_inst; struct bkpt_inst { + u32 imm; }; struct blx1_inst { @@ -1371,7 +1372,22 @@ static ARM_INST_PTR INTERPRETER_TRANSLATE(bic)(unsigned int inst, int index) inst_base->br = INDIRECT_BRANCH; return inst_base; } -static ARM_INST_PTR INTERPRETER_TRANSLATE(bkpt)(unsigned int inst, int index) { UNIMPLEMENTED_INSTRUCTION("BKPT"); } + +static ARM_INST_PTR INTERPRETER_TRANSLATE(bkpt)(unsigned int inst, int index) +{ + arm_inst* const inst_base = (arm_inst*)AllocBuffer(sizeof(arm_inst) + sizeof(bkpt_inst)); + bkpt_inst* const inst_cream = (bkpt_inst*)inst_base->component; + + inst_base->cond = BITS(inst, 28, 31); + inst_base->idx = index; + inst_base->br = NON_BRANCH; + inst_base->load_r15 = 0; + + inst_cream->imm = BITS(inst, 8, 19) | BITS(inst, 0, 3); + + return inst_base; +} + static ARM_INST_PTR INTERPRETER_TRANSLATE(blx)(unsigned int inst, int index) { arm_inst *inst_base = (arm_inst *)AllocBuffer(sizeof(arm_inst) + sizeof(blx_inst)); @@ -3211,6 +3227,7 @@ static ARM_INST_PTR INTERPRETER_TRANSLATE(usada8)(unsigned int inst, int index) inst_cream->op1 = BITS(inst, 20, 24); inst_cream->op2 = BITS(inst, 5, 7); + inst_cream->Rd = BITS(inst, 16, 19); inst_cream->Rm = BITS(inst, 8, 11); inst_cream->Rn = BITS(inst, 0, 3); inst_cream->Ra = BITS(inst, 12, 15); @@ -4080,6 +4097,16 @@ unsigned InterpreterMainLoop(ARMul_State* state) { GOTO_NEXT_INST; } BKPT_INST: + { + if (inst_base->cond == 0xE || CondPassed(cpu, inst_base->cond)) { + bkpt_inst* const inst_cream = (bkpt_inst*)inst_base->component; + LOG_DEBUG(Core_ARM11, "Breakpoint instruction hit. Immediate: 0x%08X", inst_cream->imm); + } + cpu->Reg[15] += GET_INST_SIZE(cpu); + INC_PC(sizeof(bkpt_inst)); + FETCH_INST; + GOTO_NEXT_INST; + } BLX_INST: { blx_inst *inst_cream = (blx_inst *)inst_base->component; diff --git a/src/core/arm/skyeye_common/armemu.h b/src/core/arm/skyeye_common/armemu.h index 8bfd4e0f0..2a1c50779 100644 --- a/src/core/arm/skyeye_common/armemu.h +++ b/src/core/arm/skyeye_common/armemu.h @@ -35,7 +35,7 @@ enum : u32 { // Masks for groups of bits in the APSR. MODEBITS = 0x1F, - INTBITS = 0xC0, + INTBITS = 0x1C0, }; // Different ways to start the next instruction. diff --git a/src/core/arm/skyeye_common/vfp/vfpdouble.cpp b/src/core/arm/skyeye_common/vfp/vfpdouble.cpp index 17726b8bb..1a05ef8c1 100644 --- a/src/core/arm/skyeye_common/vfp/vfpdouble.cpp +++ b/src/core/arm/skyeye_common/vfp/vfpdouble.cpp @@ -381,7 +381,7 @@ static u32 vfp_compare(ARMul_State* state, int dd, int signal_on_qnan, int dm, u s64 d, m; u32 ret = 0; - LOG_TRACE(Core_ARM11, "In %s, state=0x%x, fpscr=0x%x\n", __FUNCTION__, state, fpscr); + LOG_TRACE(Core_ARM11, "In %s, state=0x%p, fpscr=0x%x\n", __FUNCTION__, state, fpscr); m = vfp_get_double(state, dm); if (vfp_double_packed_exponent(m) == 2047 && vfp_double_packed_mantissa(m)) { ret |= FPSCR_CFLAG | FPSCR_VFLAG; @@ -436,7 +436,7 @@ static u32 vfp_compare(ARMul_State* state, int dd, int signal_on_qnan, int dm, u ret |= FPSCR_CFLAG; } } - LOG_TRACE(Core_ARM11, "In %s, state=0x%x, ret=0x%x\n", __FUNCTION__, state, ret); + LOG_TRACE(Core_ARM11, "In %s, state=0x%p, ret=0x%x\n", __FUNCTION__, state, ret); return ret; } diff --git a/src/core/arm/skyeye_common/vfp/vfpinstr.cpp b/src/core/arm/skyeye_common/vfp/vfpinstr.cpp index 1f1b5b1c3..b9b96c388 100644 --- a/src/core/arm/skyeye_common/vfp/vfpinstr.cpp +++ b/src/core/arm/skyeye_common/vfp/vfpinstr.cpp @@ -1443,7 +1443,7 @@ VPUSH_INST: addr = cpu->Reg[R13] - inst_cream->imm32; - for (int i = 0; i < inst_cream->regs; i++) + for (unsigned int i = 0; i < inst_cream->regs; i++) { if (inst_cream->single) { @@ -1512,7 +1512,7 @@ VSTM_INST: /* encoding 1 */ addr = (inst_cream->add ? cpu->Reg[inst_cream->n] : cpu->Reg[inst_cream->n] - inst_cream->imm32); - for (int i = 0; i < inst_cream->regs; i++) + for (unsigned int i = 0; i < inst_cream->regs; i++) { if (inst_cream->single) { @@ -1581,7 +1581,7 @@ VPOP_INST: addr = cpu->Reg[R13]; - for (int i = 0; i < inst_cream->regs; i++) + for (unsigned int i = 0; i < inst_cream->regs; i++) { if (inst_cream->single) { @@ -1718,7 +1718,7 @@ VLDM_INST: addr = (inst_cream->add ? cpu->Reg[inst_cream->n] : cpu->Reg[inst_cream->n] - inst_cream->imm32); - for (int i = 0; i < inst_cream->regs; i++) + for (unsigned int i = 0; i < inst_cream->regs; i++) { if (inst_cream->single) { |