Commit 390af821662c9d6af90b8914ec3efd0f8b255aef
1 parent
fa4da107
SH4: convert control/status register load/store to TCG
Signed-off-by: Aurelien Jarno <aurelien@aurel32.net> git-svn-id: svn://svn.savannah.nongnu.org/qemu/trunk@5118 c046a42c-6fe2-441c-8c8c-71466251a162
Showing
4 changed files
with
69 additions
and
82 deletions
target-sh4/helper.h
| ... | ... | @@ -16,3 +16,5 @@ DEF_HELPER(uint32_t, helper_subc, (uint32_t, uint32_t)) |
| 16 | 16 | DEF_HELPER(uint32_t, helper_negc, (uint32_t)) |
| 17 | 17 | DEF_HELPER(void, helper_macl, (uint32_t, uint32_t)) |
| 18 | 18 | DEF_HELPER(void, helper_macw, (uint32_t, uint32_t)) |
| 19 | + | |
| 20 | +DEF_HELPER(void, helper_ld_fpscr, (uint32_t)) | ... | ... |
target-sh4/op.c
| ... | ... | @@ -88,52 +88,6 @@ void OPPROTO op_shld_T0_T1(void) |
| 88 | 88 | RETURN(); |
| 89 | 89 | } |
| 90 | 90 | |
| 91 | -void OPPROTO op_ldc_T0_sr(void) | |
| 92 | -{ | |
| 93 | - env->sr = T0 & 0x700083f3; | |
| 94 | - RETURN(); | |
| 95 | -} | |
| 96 | - | |
| 97 | -void OPPROTO op_stc_sr_T0(void) | |
| 98 | -{ | |
| 99 | - T0 = env->sr; | |
| 100 | - RETURN(); | |
| 101 | -} | |
| 102 | - | |
| 103 | -#define LDSTOPS(target,load,store) \ | |
| 104 | -void OPPROTO op_##load##_T0_##target (void) \ | |
| 105 | -{ env ->target = T0; RETURN(); \ | |
| 106 | -} \ | |
| 107 | -void OPPROTO op_##store##_##target##_T0 (void) \ | |
| 108 | -{ T0 = env->target; RETURN(); \ | |
| 109 | -} \ | |
| 110 | - | |
| 111 | - LDSTOPS(gbr, ldc, stc) | |
| 112 | - LDSTOPS(vbr, ldc, stc) | |
| 113 | - LDSTOPS(ssr, ldc, stc) | |
| 114 | - LDSTOPS(spc, ldc, stc) | |
| 115 | - LDSTOPS(sgr, ldc, stc) | |
| 116 | - LDSTOPS(dbr, ldc, stc) | |
| 117 | - LDSTOPS(mach, lds, sts) | |
| 118 | - LDSTOPS(macl, lds, sts) | |
| 119 | - LDSTOPS(pr, lds, sts) | |
| 120 | - LDSTOPS(fpul, lds, sts) | |
| 121 | - | |
| 122 | -void OPPROTO op_lds_T0_fpscr(void) | |
| 123 | -{ | |
| 124 | - env->fpscr = T0 & 0x003fffff; | |
| 125 | - env->fp_status.float_rounding_mode = T0 & 0x01 ? | |
| 126 | - float_round_to_zero : float_round_nearest_even; | |
| 127 | - | |
| 128 | - RETURN(); | |
| 129 | -} | |
| 130 | - | |
| 131 | -void OPPROTO op_sts_fpscr_T0(void) | |
| 132 | -{ | |
| 133 | - T0 = env->fpscr & 0x003fffff; | |
| 134 | - RETURN(); | |
| 135 | -} | |
| 136 | - | |
| 137 | 91 | void OPPROTO op_rotcl_Rn(void) |
| 138 | 92 | { |
| 139 | 93 | helper_rotcl(&env->gregs[PARAM1]); | ... | ... |
target-sh4/op_helper.c
| ... | ... | @@ -388,3 +388,12 @@ void helper_rotcr(uint32_t * addr) |
| 388 | 388 | env->sr &= ~SR_T; |
| 389 | 389 | *addr = new; |
| 390 | 390 | } |
| 391 | + | |
| 392 | +void helper_ld_fpscr(uint32_t val) | |
| 393 | +{ | |
| 394 | + env->fpscr = val & 0x003fffff; | |
| 395 | + if (val & 0x01) | |
| 396 | + set_float_rounding_mode(float_round_to_zero, &env->fp_status); | |
| 397 | + else | |
| 398 | + set_float_rounding_mode(float_round_nearest_even, &env->fp_status); | |
| 399 | +} | ... | ... |
target-sh4/translate.c
| ... | ... | @@ -959,40 +959,34 @@ void _decode_opc(DisasContext * ctx) |
| 959 | 959 | gen_cmp_imm(TCG_COND_EQ, cpu_T[0], B7_0s); |
| 960 | 960 | return; |
| 961 | 961 | case 0xc400: /* mov.b @(disp,GBR),R0 */ |
| 962 | - gen_op_stc_gbr_T0(); | |
| 963 | - tcg_gen_addi_i32(cpu_T[0], cpu_T[0], B7_0); | |
| 962 | + tcg_gen_addi_i32(cpu_T[0], cpu_gbr, B7_0); | |
| 964 | 963 | tcg_gen_qemu_ld8s(cpu_T[0], cpu_T[0], ctx->memidx); |
| 965 | 964 | tcg_gen_mov_i32(cpu_gregs[REG(0)], cpu_T[0]); |
| 966 | 965 | return; |
| 967 | 966 | case 0xc500: /* mov.w @(disp,GBR),R0 */ |
| 968 | - gen_op_stc_gbr_T0(); | |
| 969 | - tcg_gen_addi_i32(cpu_T[0], cpu_T[0], B7_0 * 2); | |
| 967 | + tcg_gen_addi_i32(cpu_T[0], cpu_gbr, B7_0 * 2); | |
| 970 | 968 | tcg_gen_qemu_ld16s(cpu_T[0], cpu_T[0], ctx->memidx); |
| 971 | 969 | tcg_gen_mov_i32(cpu_gregs[REG(0)], cpu_T[0]); |
| 972 | 970 | return; |
| 973 | 971 | case 0xc600: /* mov.l @(disp,GBR),R0 */ |
| 974 | - gen_op_stc_gbr_T0(); | |
| 975 | - tcg_gen_addi_i32(cpu_T[0], cpu_T[0], B7_0 * 4); | |
| 972 | + tcg_gen_addi_i32(cpu_T[0], cpu_gbr, B7_0 * 4); | |
| 976 | 973 | tcg_gen_qemu_ld32s(cpu_T[0], cpu_T[0], ctx->memidx); |
| 977 | 974 | tcg_gen_mov_i32(cpu_gregs[REG(0)], cpu_T[0]); |
| 978 | 975 | return; |
| 979 | 976 | case 0xc000: /* mov.b R0,@(disp,GBR) */ |
| 980 | - gen_op_stc_gbr_T0(); | |
| 981 | - tcg_gen_addi_i32(cpu_T[0], cpu_T[0], B7_0); | |
| 977 | + tcg_gen_addi_i32(cpu_T[0], cpu_gbr, B7_0); | |
| 982 | 978 | tcg_gen_mov_i32(cpu_T[1], cpu_T[0]); |
| 983 | 979 | tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(0)]); |
| 984 | 980 | tcg_gen_qemu_st8(cpu_T[0], cpu_T[1], ctx->memidx); |
| 985 | 981 | return; |
| 986 | 982 | case 0xc100: /* mov.w R0,@(disp,GBR) */ |
| 987 | - gen_op_stc_gbr_T0(); | |
| 988 | - tcg_gen_addi_i32(cpu_T[0], cpu_T[0], B7_0 * 2); | |
| 983 | + tcg_gen_addi_i32(cpu_T[0], cpu_gbr, B7_0 * 2); | |
| 989 | 984 | tcg_gen_mov_i32(cpu_T[1], cpu_T[0]); |
| 990 | 985 | tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(0)]); |
| 991 | 986 | tcg_gen_qemu_st16(cpu_T[0], cpu_T[1], ctx->memidx); |
| 992 | 987 | return; |
| 993 | 988 | case 0xc200: /* mov.l R0,@(disp,GBR) */ |
| 994 | - gen_op_stc_gbr_T0(); | |
| 995 | - tcg_gen_addi_i32(cpu_T[0], cpu_T[0], B7_0 * 4); | |
| 989 | + tcg_gen_addi_i32(cpu_T[0], cpu_gbr, B7_0 * 4); | |
| 996 | 990 | tcg_gen_mov_i32(cpu_T[1], cpu_T[0]); |
| 997 | 991 | tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(0)]); |
| 998 | 992 | tcg_gen_qemu_st32(cpu_T[0], cpu_T[1], ctx->memidx); |
| ... | ... | @@ -1131,43 +1125,71 @@ void _decode_opc(DisasContext * ctx) |
| 1131 | 1125 | ctx->flags |= DELAY_SLOT; |
| 1132 | 1126 | ctx->delayed_pc = (uint32_t) - 1; |
| 1133 | 1127 | return; |
| 1134 | -#define LDST(reg,ldnum,ldpnum,ldop,stnum,stpnum,stop,extrald) \ | |
| 1128 | + case 0x400e: /* lds Rm,SR */ | |
| 1129 | + tcg_gen_andi_i32(cpu_sr, cpu_gregs[REG(B11_8)], 0x700083f3); | |
| 1130 | + ctx->bstate = BS_STOP; | |
| 1131 | + return; | |
| 1132 | + case 0x4007: /* lds.l @Rm+,SR */ | |
| 1133 | + tcg_gen_qemu_ld32s(cpu_T[0], cpu_gregs[REG(B11_8)], ctx->memidx); | |
| 1134 | + tcg_gen_addi_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 4); | |
| 1135 | + tcg_gen_andi_i32(cpu_sr, cpu_T[0], 0x700083f3); | |
| 1136 | + ctx->bstate = BS_STOP; | |
| 1137 | + return; | |
| 1138 | + case 0x0002: /* sts SR,Rn */ | |
| 1139 | + tcg_gen_mov_i32(cpu_gregs[REG(B11_8)], cpu_sr); | |
| 1140 | + return; | |
| 1141 | + case 0x4003: /* sts SR,@-Rn */ | |
| 1142 | + tcg_gen_subi_i32(cpu_T[0], cpu_gregs[REG(B11_8)], 4); | |
| 1143 | + tcg_gen_qemu_st32(cpu_sr, cpu_T[0], ctx->memidx); | |
| 1144 | + tcg_gen_subi_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 4); | |
| 1145 | + return; | |
| 1146 | +#define LDST(reg,ldnum,ldpnum,stnum,stpnum) \ | |
| 1135 | 1147 | case ldnum: \ |
| 1136 | - tcg_gen_mov_i32 (cpu_T[0], cpu_gregs[REG(B11_8)]); \ | |
| 1137 | - gen_op_##ldop##_T0_##reg (); \ | |
| 1138 | - extrald \ | |
| 1148 | + tcg_gen_mov_i32 (cpu_##reg, cpu_gregs[REG(B11_8)]); \ | |
| 1139 | 1149 | return; \ |
| 1140 | 1150 | case ldpnum: \ |
| 1141 | - tcg_gen_qemu_ld32s (cpu_T[0], cpu_gregs[REG(B11_8)], ctx->memidx); \ | |
| 1151 | + tcg_gen_qemu_ld32s (cpu_##reg, cpu_gregs[REG(B11_8)], ctx->memidx); \ | |
| 1142 | 1152 | tcg_gen_addi_i32(cpu_gregs[REG(B11_8)], \ |
| 1143 | 1153 | cpu_gregs[REG(B11_8)], 4); \ |
| 1144 | - gen_op_##ldop##_T0_##reg (); \ | |
| 1145 | - extrald \ | |
| 1146 | 1154 | return; \ |
| 1147 | 1155 | case stnum: \ |
| 1148 | - gen_op_##stop##_##reg##_T0 (); \ | |
| 1149 | - tcg_gen_mov_i32 (cpu_gregs[REG(B11_8)], cpu_T[0]); \ | |
| 1156 | + tcg_gen_mov_i32 (cpu_gregs[REG(B11_8)], cpu_##reg); \ | |
| 1150 | 1157 | return; \ |
| 1151 | 1158 | case stpnum: \ |
| 1152 | - gen_op_##stop##_##reg##_T0 (); \ | |
| 1153 | 1159 | tcg_gen_subi_i32(cpu_T[1], cpu_gregs[REG(B11_8)], 4); \ |
| 1154 | - tcg_gen_qemu_st32 (cpu_T[0], cpu_T[1], ctx->memidx); \ | |
| 1160 | + tcg_gen_qemu_st32 (cpu_##reg, cpu_T[1], ctx->memidx); \ | |
| 1155 | 1161 | tcg_gen_subi_i32(cpu_gregs[REG(B11_8)], \ |
| 1156 | 1162 | cpu_gregs[REG(B11_8)], 4); \ |
| 1157 | 1163 | return; |
| 1158 | - LDST(sr, 0x400e, 0x4007, ldc, 0x0002, 0x4003, stc, ctx->bstate = | |
| 1159 | - BS_STOP;) | |
| 1160 | - LDST(gbr, 0x401e, 0x4017, ldc, 0x0012, 0x4013, stc,) | |
| 1161 | - LDST(vbr, 0x402e, 0x4027, ldc, 0x0022, 0x4023, stc,) | |
| 1162 | - LDST(ssr, 0x403e, 0x4037, ldc, 0x0032, 0x4033, stc,) | |
| 1163 | - LDST(spc, 0x404e, 0x4047, ldc, 0x0042, 0x4043, stc,) | |
| 1164 | - LDST(dbr, 0x40fa, 0x40f6, ldc, 0x00fa, 0x40f2, stc,) | |
| 1165 | - LDST(mach, 0x400a, 0x4006, lds, 0x000a, 0x4002, sts,) | |
| 1166 | - LDST(macl, 0x401a, 0x4016, lds, 0x001a, 0x4012, sts,) | |
| 1167 | - LDST(pr, 0x402a, 0x4026, lds, 0x002a, 0x4022, sts,) | |
| 1168 | - LDST(fpul, 0x405a, 0x4056, lds, 0x005a, 0x4052, sts,) | |
| 1169 | - LDST(fpscr, 0x406a, 0x4066, lds, 0x006a, 0x4062, sts, ctx->bstate = | |
| 1170 | - BS_STOP;) | |
| 1164 | + LDST(gbr, 0x401e, 0x4017, 0x0012, 0x4013) | |
| 1165 | + LDST(vbr, 0x402e, 0x4027, 0x0022, 0x4023) | |
| 1166 | + LDST(ssr, 0x403e, 0x4037, 0x0032, 0x4033) | |
| 1167 | + LDST(spc, 0x404e, 0x4047, 0x0042, 0x4043) | |
| 1168 | + LDST(dbr, 0x40fa, 0x40f6, 0x00fa, 0x40f2) | |
| 1169 | + LDST(mach, 0x400a, 0x4006, 0x000a, 0x4002) | |
| 1170 | + LDST(macl, 0x401a, 0x4016, 0x001a, 0x4012) | |
| 1171 | + LDST(pr, 0x402a, 0x4026, 0x002a, 0x4022) | |
| 1172 | + LDST(fpul, 0x405a, 0x4056, 0x005a, 0x4052) | |
| 1173 | + case 0x406a: /* lds Rm,FPSCR */ | |
| 1174 | + tcg_gen_helper_0_1(helper_ld_fpscr, cpu_gregs[REG(B11_8)]); | |
| 1175 | + ctx->bstate = BS_STOP; | |
| 1176 | + return; | |
| 1177 | + case 0x4066: /* lds.l @Rm+,FPSCR */ | |
| 1178 | + tcg_gen_qemu_ld32s(cpu_T[0], cpu_gregs[REG(B11_8)], ctx->memidx); | |
| 1179 | + tcg_gen_addi_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 4); | |
| 1180 | + tcg_gen_helper_0_1(helper_ld_fpscr, cpu_T[0]); | |
| 1181 | + ctx->bstate = BS_STOP; | |
| 1182 | + return; | |
| 1183 | + case 0x006a: /* sts FPSCR,Rn */ | |
| 1184 | + tcg_gen_andi_i32(cpu_T[0], cpu_fpscr, 0x003fffff); | |
| 1185 | + tcg_gen_mov_i32(cpu_gregs[REG(B11_8)], cpu_T[0]); | |
| 1186 | + return; | |
| 1187 | + case 0x4062: /* sts FPSCR,@-Rn */ | |
| 1188 | + tcg_gen_andi_i32(cpu_T[0], cpu_fpscr, 0x003fffff); | |
| 1189 | + tcg_gen_subi_i32(cpu_T[1], cpu_gregs[REG(B11_8)], 4); | |
| 1190 | + tcg_gen_qemu_st32(cpu_T[0], cpu_T[1], ctx->memidx); | |
| 1191 | + tcg_gen_subi_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 4); | |
| 1192 | + return; | |
| 1171 | 1193 | case 0x00c3: /* movca.l R0,@Rm */ |
| 1172 | 1194 | tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(0)]); |
| 1173 | 1195 | tcg_gen_mov_i32(cpu_T[1], cpu_gregs[REG(B11_8)]); | ... | ... |