diff options
Diffstat (limited to 'src/core')
| -rw-r--r-- | src/core/arm/skyeye_common/arm_regformat.h | 2 | ||||
| -rw-r--r-- | src/core/arm/skyeye_common/vfp/vfp.cpp | 16 | ||||
| -rw-r--r-- | src/core/arm/skyeye_common/vfp/vfp.h | 2 | ||||
| -rw-r--r-- | src/core/arm/skyeye_common/vfp/vfpinstr.cpp | 75 | 
4 files changed, 53 insertions, 42 deletions
diff --git a/src/core/arm/skyeye_common/arm_regformat.h b/src/core/arm/skyeye_common/arm_regformat.h index a92effbb4..d1c721809 100644 --- a/src/core/arm/skyeye_common/arm_regformat.h +++ b/src/core/arm/skyeye_common/arm_regformat.h @@ -59,6 +59,8 @@ enum {      VFP_FPSID,      VFP_FPSCR,      VFP_FPEXC, +    VFP_FPINST, +    VFP_FPINST2,      VFP_MVFR0,      VFP_MVFR1, diff --git a/src/core/arm/skyeye_common/vfp/vfp.cpp b/src/core/arm/skyeye_common/vfp/vfp.cpp index 571d6c2f2..f40cf5955 100644 --- a/src/core/arm/skyeye_common/vfp/vfp.cpp +++ b/src/core/arm/skyeye_common/vfp/vfp.cpp @@ -33,6 +33,10 @@ unsigned VFPInit(ARMul_State* state)      state->VFP[VFP_FPEXC] = 0;      state->VFP[VFP_FPSCR] = 0; +    // ARM11 MPCore instruction register reset values. +    state->VFP[VFP_FPINST]  = 0xEE000A00; +    state->VFP[VFP_FPINST2] = 0; +      // ARM11 MPCore feature register values.      state->VFP[VFP_MVFR0] = 0x11111111;      state->VFP[VFP_MVFR1] = 0; @@ -40,18 +44,6 @@ unsigned VFPInit(ARMul_State* state)      return 0;  } -void VMSR(ARMul_State* state, ARMword reg, ARMword Rt) -{ -    if (reg == 1) -    { -        state->VFP[VFP_FPSCR] = state->Reg[Rt]; -    } -    else if (reg == 8) -    { -        state->VFP[VFP_FPEXC] = state->Reg[Rt]; -    } -} -  void VMOVBRS(ARMul_State* state, ARMword to_arm, ARMword t, ARMword n, ARMword* value)  {      if (to_arm) diff --git a/src/core/arm/skyeye_common/vfp/vfp.h b/src/core/arm/skyeye_common/vfp/vfp.h index acefae9bb..eb376561a 100644 --- a/src/core/arm/skyeye_common/vfp/vfp.h +++ b/src/core/arm/skyeye_common/vfp/vfp.h @@ -36,10 +36,8 @@ void vfp_raise_exceptions(ARMul_State* state, u32 exceptions, u32 inst, u32 fpsc  u32 vfp_single_cpdo(ARMul_State* state, u32 inst, u32 fpscr);  u32 vfp_double_cpdo(ARMul_State* state, u32 inst, u32 fpscr); -void VMSR(ARMul_State* state, ARMword reg, ARMword Rt);  void VMOVBRS(ARMul_State* state, ARMword to_arm, ARMword t, ARMword n, ARMword* value);  void VMOVBRRD(ARMul_State* state, ARMword to_arm, ARMword t, ARMword t2, ARMword n, ARMword* value1, ARMword* value2);  void VMOVBRRSS(ARMul_State* state, ARMword to_arm, ARMword t, ARMword t2, ARMword n, ARMword* value1, ARMword* value2);  void VMOVI(ARMul_State* state, ARMword single, ARMword d, ARMword imm);  void VMOVR(ARMul_State* state, ARMword single, ARMword d, ARMword imm); - diff --git a/src/core/arm/skyeye_common/vfp/vfpinstr.cpp b/src/core/arm/skyeye_common/vfp/vfpinstr.cpp index 67fe63aa4..8efcbab1c 100644 --- a/src/core/arm/skyeye_common/vfp/vfpinstr.cpp +++ b/src/core/arm/skyeye_common/vfp/vfpinstr.cpp @@ -995,7 +995,7 @@ VMOVBRS_INST:  #ifdef VFP_INTERPRETER_STRUCT  struct vmsr_inst {      unsigned int reg; -    unsigned int Rd; +    unsigned int Rt;  };  #endif  #ifdef VFP_INTERPRETER_TRANS @@ -1009,7 +1009,7 @@ static ARM_INST_PTR INTERPRETER_TRANSLATE(vmsr)(unsigned int inst, int index)      inst_base->br   = NON_BRANCH;      inst_cream->reg = BITS(inst, 16, 19); -    inst_cream->Rd  = BITS(inst, 12, 15); +    inst_cream->Rt  = BITS(inst, 12, 15);      return inst_base;  } @@ -1017,15 +1017,30 @@ static ARM_INST_PTR INTERPRETER_TRANSLATE(vmsr)(unsigned int inst, int index)  #ifdef VFP_INTERPRETER_IMPL  VMSR_INST:  { -    if ((inst_base->cond == 0xe) || CondPassed(cpu, inst_base->cond)) { +    if (inst_base->cond == 0xE || CondPassed(cpu, inst_base->cond)) {          /* FIXME: special case for access to FPSID and FPEXC, VFP must be disabled ,             and in privileged mode */          /* Exceptions must be checked, according to v7 ref manual */          CHECK_VFP_ENABLED; -        vmsr_inst *inst_cream = (vmsr_inst *)inst_base->component; +        vmsr_inst* const inst_cream = (vmsr_inst*)inst_base->component; + +        unsigned int reg = inst_cream->reg; +        unsigned int rt  = inst_cream->Rt; -        VMSR(cpu, inst_cream->reg, inst_cream->Rd); +        if (reg == 1) +        { +            cpu->VFP[VFP_FPSCR] = cpu->Reg[rt]; +        } +        else if (InAPrivilegedMode(cpu)) +        { +            if (reg == 8) +                cpu->VFP[VFP_FPEXC] = cpu->Reg[rt]; +            else if (reg == 9) +                cpu->VFP[VFP_FPINST] = cpu->Reg[rt]; +            else if (reg == 10) +                cpu->VFP[VFP_FPINST2] = cpu->Reg[rt]; +        }      }      cpu->Reg[15] += GET_INST_SIZE(cpu);      INC_PC(sizeof(vmsr_inst)); @@ -1111,19 +1126,22 @@ static ARM_INST_PTR INTERPRETER_TRANSLATE(vmrs)(unsigned int inst, int index)  #ifdef VFP_INTERPRETER_IMPL  VMRS_INST:  { -    if ((inst_base->cond == 0xe) || CondPassed(cpu, inst_base->cond)) { +    if (inst_base->cond == 0xE || CondPassed(cpu, inst_base->cond)) {          /* FIXME: special case for access to FPSID and FPEXC, VFP must be disabled,             and in privileged mode */          /* Exceptions must be checked, according to v7 ref manual */          CHECK_VFP_ENABLED; -        vmrs_inst *inst_cream = (vmrs_inst *)inst_base->component; +        vmrs_inst* const inst_cream = (vmrs_inst*)inst_base->component; -        if (inst_cream->reg == 1) /* FPSCR */ +        unsigned int reg = inst_cream->reg; +        unsigned int rt  = inst_cream->Rt; + +        if (reg == 1) // FPSCR          { -            if (inst_cream->Rt != 15) +            if (rt != 15)              { -                cpu->Reg[inst_cream->Rt] = cpu->VFP[VFP_FPSCR]; +                cpu->Reg[rt] = cpu->VFP[VFP_FPSCR];              }              else              { @@ -1133,25 +1151,26 @@ VMRS_INST:                  cpu->VFlag = (cpu->VFP[VFP_FPSCR] >> 28) & 1;              }          } -        else +        else if (reg == 0)          { -            switch (inst_cream->reg) -            { -            case 0: -                cpu->Reg[inst_cream->Rt] = cpu->VFP[VFP_FPSID]; -                break; -            case 6: -                cpu->Reg[inst_cream->Rt] = cpu->VFP[VFP_MVFR1]; -                break; -            case 7: -                cpu->Reg[inst_cream->Rt] = cpu->VFP[VFP_MVFR0]; -                break; -            case 8: -                cpu->Reg[inst_cream->Rt] = cpu->VFP[VFP_FPEXC]; -                break; -            default: -                break; -            } +            cpu->Reg[rt] = cpu->VFP[VFP_FPSID]; +        } +        else if (reg == 6) +        { +            cpu->Reg[rt] = cpu->VFP[VFP_MVFR1]; +        } +        else if (reg == 7) +        { +            cpu->Reg[rt] = cpu->VFP[VFP_MVFR0]; +        } +        else if (InAPrivilegedMode(cpu)) +        { +            if (reg == 8) +                cpu->Reg[rt] = cpu->VFP[VFP_FPEXC]; +            else if (reg == 9) +                cpu->Reg[rt] = cpu->VFP[VFP_FPINST]; +            else if (reg == 10) +                cpu->Reg[rt] = cpu->VFP[VFP_FPINST2];          }      }      cpu->Reg[15] += GET_INST_SIZE(cpu);  | 
