diff options
author | Lioncash <mathew1800@gmail.com> | 2015-07-28 05:45:24 +0200 |
---|---|---|
committer | Lioncash <mathew1800@gmail.com> | 2015-07-28 08:27:57 +0200 |
commit | 89540ea7618fbaca1c9cd332b24aff7f2865d324 (patch) | |
tree | d5e25da76e20be36e3016beb363b2c25071d9c36 | |
parent | dyncom: Remove code duplication regarding thumb instructions (diff) | |
download | yuzu-89540ea7618fbaca1c9cd332b24aff7f2865d324.tar yuzu-89540ea7618fbaca1c9cd332b24aff7f2865d324.tar.gz yuzu-89540ea7618fbaca1c9cd332b24aff7f2865d324.tar.bz2 yuzu-89540ea7618fbaca1c9cd332b24aff7f2865d324.tar.lz yuzu-89540ea7618fbaca1c9cd332b24aff7f2865d324.tar.xz yuzu-89540ea7618fbaca1c9cd332b24aff7f2865d324.tar.zst yuzu-89540ea7618fbaca1c9cd332b24aff7f2865d324.zip |
-rw-r--r-- | src/core/arm/dyncom/arm_dyncom_dec.cpp | 19 | ||||
-rw-r--r-- | src/core/arm/dyncom/arm_dyncom_dec.h | 10 | ||||
-rw-r--r-- | src/core/arm/dyncom/arm_dyncom_interpreter.cpp | 19 | ||||
-rw-r--r-- | src/core/arm/dyncom/arm_dyncom_thumb.cpp | 20 | ||||
-rw-r--r-- | src/core/arm/dyncom/arm_dyncom_thumb.h | 13 |
5 files changed, 40 insertions, 41 deletions
diff --git a/src/core/arm/dyncom/arm_dyncom_dec.cpp b/src/core/arm/dyncom/arm_dyncom_dec.cpp index 3ab9f2c17..48fc1c683 100644 --- a/src/core/arm/dyncom/arm_dyncom_dec.cpp +++ b/src/core/arm/dyncom/arm_dyncom_dec.cpp @@ -414,14 +414,13 @@ const ISEITEM arm_exclusion_code[] = { { "invalid", 0, INVALID, { 0 }} }; -int decode_arm_instr(u32 instr, s32* idx) { +ARMDecodeStatus DecodeARMInstruction(u32 instr, s32* idx) { int n = 0; int base = 0; - int ret = DECODE_FAILURE; - int i = 0; int instr_slots = sizeof(arm_instruction) / sizeof(ISEITEM); + ARMDecodeStatus ret = ARMDecodeStatus::FAILURE; - for (i = 0; i < instr_slots; i++) { + for (int i = 0; i < instr_slots; i++) { n = arm_instruction[i].attribute_value; base = 0; @@ -438,11 +437,11 @@ int decode_arm_instr(u32 instr, s32* idx) { n--; } - // All conditions is satisfied. + // All conditions are satisfied. if (n == 0) - ret = DECODE_SUCCESS; + ret = ARMDecodeStatus::SUCCESS; - if (ret == DECODE_SUCCESS) { + if (ret == ARMDecodeStatus::SUCCESS) { n = arm_exclusion_code[i].attribute_value; if (n != 0) { base = 0; @@ -454,13 +453,13 @@ int decode_arm_instr(u32 instr, s32* idx) { n--; } - // All conditions is satisfied. + // All conditions are satisfied. if (n == 0) - ret = DECODE_FAILURE; + ret = ARMDecodeStatus::FAILURE; } } - if (ret == DECODE_SUCCESS) { + if (ret == ARMDecodeStatus::SUCCESS) { *idx = i; return ret; } diff --git a/src/core/arm/dyncom/arm_dyncom_dec.h b/src/core/arm/dyncom/arm_dyncom_dec.h index 5f6279627..80d910218 100644 --- a/src/core/arm/dyncom/arm_dyncom_dec.h +++ b/src/core/arm/dyncom/arm_dyncom_dec.h @@ -6,13 +6,13 @@ #include "common/common_types.h" -int decode_arm_instr(u32 instr, s32* idx); - -enum DECODE_STATUS { - DECODE_SUCCESS, - DECODE_FAILURE +enum class ARMDecodeStatus { + SUCCESS, + FAILURE }; +ARMDecodeStatus DecodeARMInstruction(u32 instr, s32* idx); + struct instruction_set_encoding_item { const char *name; int attribute_value; diff --git a/src/core/arm/dyncom/arm_dyncom_interpreter.cpp b/src/core/arm/dyncom/arm_dyncom_interpreter.cpp index cdef72be6..d022546ed 100644 --- a/src/core/arm/dyncom/arm_dyncom_interpreter.cpp +++ b/src/core/arm/dyncom/arm_dyncom_interpreter.cpp @@ -3468,10 +3468,10 @@ enum { FETCH_FAILURE }; -static tdstate decode_thumb_instr(u32 inst, u32 addr, u32* arm_inst, u32* inst_size, ARM_INST_PTR* ptr_inst_base) { +static ThumbDecodeStatus DecodeThumbInstruction(u32 inst, u32 addr, u32* arm_inst, u32* inst_size, ARM_INST_PTR* ptr_inst_base) { // Check if in Thumb mode - tdstate ret = thumb_translate (addr, inst, arm_inst, inst_size); - if (ret == t_branch) { + ThumbDecodeStatus ret = TranslateThumbInstruction (addr, inst, arm_inst, inst_size); + if (ret == ThumbDecodeStatus::BRANCH) { int inst_index; int table_length = sizeof(arm_instruction_trans) / sizeof(transop_fp_t); u32 tinstr = GetThumbInstruction(inst, addr); @@ -3509,7 +3509,7 @@ static tdstate decode_thumb_instr(u32 inst, u32 addr, u32* arm_inst, u32* inst_s *ptr_inst_base = arm_instruction_trans[inst_index](tinstr, inst_index); break; default: - ret = t_undefined; + ret = ThumbDecodeStatus::UNDEFINED; break; } } @@ -3542,20 +3542,19 @@ static int InterpreterTranslate(ARMul_State* cpu, int& bb_start, u32 addr) { inst = Memory::Read32(phys_addr & 0xFFFFFFFC); size++; - // If we are in thumb instruction, we will translate one thumb to one corresponding arm instruction + // If we are in Thumb mode, we'll translate one Thumb instruction to the corresponding ARM instruction if (cpu->TFlag) { uint32_t arm_inst; - tdstate state = decode_thumb_instr(inst, phys_addr, &arm_inst, &inst_size, &inst_base); + ThumbDecodeStatus state = DecodeThumbInstruction(inst, phys_addr, &arm_inst, &inst_size, &inst_base); - // We have translated the branch instruction of thumb in thumb decoder - if(state == t_branch){ + // We have translated the Thumb branch instruction in the Thumb decoder + if (state == ThumbDecodeStatus::BRANCH) { goto translated; } inst = arm_inst; } - ret = decode_arm_instr(inst, &idx); - if (ret == DECODE_FAILURE) { + if (DecodeARMInstruction(inst, &idx) == ARMDecodeStatus::FAILURE) { std::string disasm = ARM_Disasm::Disassemble(phys_addr, inst); LOG_ERROR(Core_ARM11, "Decode failure.\tPC : [0x%x]\tInstruction : %s [%x]", phys_addr, disasm.c_str(), inst); LOG_ERROR(Core_ARM11, "cpsr=0x%x, cpu->TFlag=%d, r15=0x%x", cpu->Cpsr, cpu->TFlag, cpu->Reg[15]); diff --git a/src/core/arm/dyncom/arm_dyncom_thumb.cpp b/src/core/arm/dyncom/arm_dyncom_thumb.cpp index 6eb03fb5a..29272fd5d 100644 --- a/src/core/arm/dyncom/arm_dyncom_thumb.cpp +++ b/src/core/arm/dyncom/arm_dyncom_thumb.cpp @@ -12,8 +12,8 @@ // with the following Thumb instruction held in the high 16-bits. Passing in two Thumb instructions // allows easier simulation of the special dual BL instruction. -tdstate thumb_translate(u32 addr, u32 instr, u32* ainstr, u32* inst_size) { - tdstate valid = t_uninitialized; +ThumbDecodeStatus TranslateThumbInstruction(u32 addr, u32 instr, u32* ainstr, u32* inst_size) { + ThumbDecodeStatus valid = ThumbDecodeStatus::UNINITIALIZED; u32 tinstr = GetThumbInstruction(instr, addr); *ainstr = 0xDEADC0DE; // Debugging to catch non updates @@ -351,21 +351,21 @@ tdstate thumb_translate(u32 addr, u32 instr, u32* ainstr, u32* inst_size) { else *ainstr |= (tinstr & 0x00FF); } else if ((tinstr & 0x0F00) != 0x0E00) - valid = t_branch; + valid = ThumbDecodeStatus::BRANCH; else // UNDEFINED : cc=1110(AL) uses different format - valid = t_undefined; + valid = ThumbDecodeStatus::UNDEFINED; break; case 28: // B - valid = t_branch; + valid = ThumbDecodeStatus::BRANCH; break; case 29: - if(tinstr & 0x1) - valid = t_undefined; + if (tinstr & 0x1) + valid = ThumbDecodeStatus::UNDEFINED; else - valid = t_branch; + valid = ThumbDecodeStatus::BRANCH; break; case 30: // BL instruction 1 @@ -374,7 +374,7 @@ tdstate thumb_translate(u32 addr, u32 instr, u32* ainstr, u32* inst_size) { // simulation simple (from the user perspective) we check if the following instruction is // the second half of this BL, and if it is we simulate it immediately - valid = t_branch; + valid = ThumbDecodeStatus::BRANCH; break; case 31: // BL instruction 2 @@ -383,7 +383,7 @@ tdstate thumb_translate(u32 addr, u32 instr, u32* ainstr, u32* inst_size) { // ever be matched with the fmt19 "BL instruction 1" instruction. However, we do allow the // simulation of it on its own, with undefined results if r14 is not suitably initialised. - valid = t_branch; + valid = ThumbDecodeStatus::BRANCH; break; } diff --git a/src/core/arm/dyncom/arm_dyncom_thumb.h b/src/core/arm/dyncom/arm_dyncom_thumb.h index 74e69e13a..447974363 100644 --- a/src/core/arm/dyncom/arm_dyncom_thumb.h +++ b/src/core/arm/dyncom/arm_dyncom_thumb.h @@ -28,14 +28,15 @@ #include "common/common_types.h" -enum tdstate { - t_undefined, // Undefined Thumb instruction - t_decoded, // Instruction decoded to ARM equivalent - t_branch, // Thumb branch (already processed) - t_uninitialized, +enum class ThumbDecodeStatus { + UNDEFINED, // Undefined Thumb instruction + DECODED, // Instruction decoded to ARM equivalent + BRANCH, // Thumb branch (already processed) + UNINITIALIZED, }; -tdstate thumb_translate(u32 addr, u32 instr, u32* ainstr, u32* inst_size); +// Translates a Thumb mode instruction into its ARM equivalent. +ThumbDecodeStatus TranslateThumbInstruction(u32 addr, u32 instr, u32* ainstr, u32* inst_size); static inline u32 GetThumbInstruction(u32 instr, u32 address) { // Normally you would need to handle instruction endianness, |