Commit e397ee3382a34c65b0fb93514c3eef5c31715d3c
1 parent
51789c41
Fix enough FPU/R2 support to get 24Kf going.
git-svn-id: svn://svn.savannah.nongnu.org/qemu/trunk@2528 c046a42c-6fe2-441c-8c8c-71466251a162
Showing
5 changed files
with
66 additions
and
26 deletions
target-mips/cpu.h
target-mips/exec.h
| ... | ... | @@ -152,6 +152,7 @@ void invalidate_tlb (CPUState *env, int idx, int use_extra); |
| 152 | 152 | void cpu_loop_exit(void); |
| 153 | 153 | void do_raise_exception_err (uint32_t exception, int error_code); |
| 154 | 154 | void do_raise_exception (uint32_t exception); |
| 155 | +void do_raise_exception_direct_err (uint32_t exception, int error_code); | |
| 155 | 156 | void do_raise_exception_direct (uint32_t exception); |
| 156 | 157 | |
| 157 | 158 | void cpu_dump_state(CPUState *env, FILE *f, | ... | ... |
target-mips/op.c
| ... | ... | @@ -1180,6 +1180,18 @@ void op_mfc0_config3 (void) |
| 1180 | 1180 | RETURN(); |
| 1181 | 1181 | } |
| 1182 | 1182 | |
| 1183 | +void op_mfc0_config6 (void) | |
| 1184 | +{ | |
| 1185 | + T0 = env->CP0_Config6; | |
| 1186 | + RETURN(); | |
| 1187 | +} | |
| 1188 | + | |
| 1189 | +void op_mfc0_config7 (void) | |
| 1190 | +{ | |
| 1191 | + T0 = env->CP0_Config7; | |
| 1192 | + RETURN(); | |
| 1193 | +} | |
| 1194 | + | |
| 1183 | 1195 | void op_mfc0_lladdr (void) |
| 1184 | 1196 | { |
| 1185 | 1197 | T0 = (int32_t)env->CP0_LLAddr >> 4; |
| ... | ... | @@ -1653,7 +1665,7 @@ void op_dmtc0_errorepc (void) |
| 1653 | 1665 | void op_cp1_enabled(void) |
| 1654 | 1666 | { |
| 1655 | 1667 | if (!(env->CP0_Status & (1 << CP0St_CU1))) { |
| 1656 | - CALL_FROM_TB2(do_raise_exception_err, EXCP_CpU, 1); | |
| 1668 | + CALL_FROM_TB2(do_raise_exception_direct_err, EXCP_CpU, 1); | |
| 1657 | 1669 | } |
| 1658 | 1670 | RETURN(); |
| 1659 | 1671 | } | ... | ... |
target-mips/op_helper.c
| ... | ... | @@ -56,10 +56,15 @@ void do_restore_state (void *pc_ptr) |
| 56 | 56 | cpu_restore_state (tb, env, pc, NULL); |
| 57 | 57 | } |
| 58 | 58 | |
| 59 | -void do_raise_exception_direct (uint32_t exception) | |
| 59 | +void do_raise_exception_direct_err (uint32_t exception, int error_code) | |
| 60 | 60 | { |
| 61 | 61 | do_restore_state (GETPC ()); |
| 62 | - do_raise_exception_err (exception, 0); | |
| 62 | + do_raise_exception_err (exception, error_code); | |
| 63 | +} | |
| 64 | + | |
| 65 | +void do_raise_exception_direct (uint32_t exception) | |
| 66 | +{ | |
| 67 | + do_raise_exception_direct_err (exception, 0); | |
| 63 | 68 | } |
| 64 | 69 | |
| 65 | 70 | #define MEMSUFFIX _raw | ... | ... |
target-mips/translate.c
| ... | ... | @@ -829,7 +829,7 @@ static void gen_flt_ldst (DisasContext *ctx, uint32_t opc, int ft, |
| 829 | 829 | break; |
| 830 | 830 | default: |
| 831 | 831 | MIPS_INVAL("float load/store"); |
| 832 | - generate_exception_err(ctx, EXCP_CpU, 1); | |
| 832 | + generate_exception(ctx, EXCP_RI); | |
| 833 | 833 | return; |
| 834 | 834 | } |
| 835 | 835 | MIPS_DEBUG("%s %s, %d(%s)", opn, fregnames[ft], offset, regnames[base]); |
| ... | ... | @@ -1932,22 +1932,31 @@ static void gen_mfc0 (DisasContext *ctx, int reg, int sel) |
| 1932 | 1932 | case 16: |
| 1933 | 1933 | switch (sel) { |
| 1934 | 1934 | case 0: |
| 1935 | - gen_op_mfc0_config0(); | |
| 1935 | + gen_op_mfc0_config0(); | |
| 1936 | 1936 | rn = "Config"; |
| 1937 | 1937 | break; |
| 1938 | 1938 | case 1: |
| 1939 | - gen_op_mfc0_config1(); | |
| 1939 | + gen_op_mfc0_config1(); | |
| 1940 | 1940 | rn = "Config1"; |
| 1941 | 1941 | break; |
| 1942 | 1942 | case 2: |
| 1943 | - gen_op_mfc0_config2(); | |
| 1943 | + gen_op_mfc0_config2(); | |
| 1944 | 1944 | rn = "Config2"; |
| 1945 | 1945 | break; |
| 1946 | 1946 | case 3: |
| 1947 | - gen_op_mfc0_config3(); | |
| 1947 | + gen_op_mfc0_config3(); | |
| 1948 | 1948 | rn = "Config3"; |
| 1949 | 1949 | break; |
| 1950 | - /* 6,7 are implementation dependent */ | |
| 1950 | + /* 4,5 are reserved */ | |
| 1951 | + /* 6,7 are implementation dependent */ | |
| 1952 | + case 6: | |
| 1953 | + gen_op_mfc0_config6(); | |
| 1954 | + rn = "Config6"; | |
| 1955 | + break; | |
| 1956 | + case 7: | |
| 1957 | + gen_op_mfc0_config7(); | |
| 1958 | + rn = "Config7"; | |
| 1959 | + break; | |
| 1951 | 1960 | default: |
| 1952 | 1961 | goto die; |
| 1953 | 1962 | } |
| ... | ... | @@ -2516,28 +2525,37 @@ static void gen_mtc0 (DisasContext *ctx, int reg, int sel) |
| 2516 | 2525 | case 16: |
| 2517 | 2526 | switch (sel) { |
| 2518 | 2527 | case 0: |
| 2519 | - gen_op_mtc0_config0(); | |
| 2528 | + gen_op_mtc0_config0(); | |
| 2520 | 2529 | rn = "Config"; |
| 2521 | 2530 | break; |
| 2522 | 2531 | case 1: |
| 2523 | - /* ignored */ | |
| 2532 | + /* ignored, read only */ | |
| 2524 | 2533 | rn = "Config1"; |
| 2525 | 2534 | break; |
| 2526 | 2535 | case 2: |
| 2527 | - gen_op_mtc0_config2(); | |
| 2536 | + gen_op_mtc0_config2(); | |
| 2528 | 2537 | rn = "Config2"; |
| 2529 | 2538 | break; |
| 2530 | 2539 | case 3: |
| 2531 | - /* ignored */ | |
| 2540 | + /* ignored, read only */ | |
| 2532 | 2541 | rn = "Config3"; |
| 2533 | 2542 | break; |
| 2534 | - /* 6,7 are implementation dependent */ | |
| 2543 | + /* 4,5 are reserved */ | |
| 2544 | + /* 6,7 are implementation dependent */ | |
| 2545 | + case 6: | |
| 2546 | + /* ignored */ | |
| 2547 | + rn = "Config6"; | |
| 2548 | + break; | |
| 2549 | + case 7: | |
| 2550 | + /* ignored */ | |
| 2551 | + rn = "Config7"; | |
| 2552 | + break; | |
| 2535 | 2553 | default: |
| 2536 | 2554 | rn = "Invalid config selector"; |
| 2537 | 2555 | goto die; |
| 2538 | 2556 | } |
| 2539 | - /* Stop translation as we may have switched the execution mode */ | |
| 2540 | - ctx->bstate = BS_STOP; | |
| 2557 | + /* Stop translation as we may have switched the execution mode */ | |
| 2558 | + ctx->bstate = BS_STOP; | |
| 2541 | 2559 | break; |
| 2542 | 2560 | case 17: |
| 2543 | 2561 | switch (sel) { |
| ... | ... | @@ -4140,7 +4158,7 @@ static void gen_compute_branch1 (DisasContext *ctx, uint32_t op, |
| 4140 | 4158 | break; |
| 4141 | 4159 | default: |
| 4142 | 4160 | MIPS_INVAL("cp1 branch/jump"); |
| 4143 | - generate_exception_err (ctx, EXCP_RI, 1); | |
| 4161 | + generate_exception (ctx, EXCP_RI); | |
| 4144 | 4162 | return; |
| 4145 | 4163 | } |
| 4146 | 4164 | gen_op_set_bcond(); |
| ... | ... | @@ -4173,7 +4191,7 @@ static void gen_cp1 (DisasContext *ctx, uint32_t opc, int rt, int fs) |
| 4173 | 4191 | case OPC_CFC1: |
| 4174 | 4192 | if (fs != 0 && fs != 31) { |
| 4175 | 4193 | MIPS_INVAL("cfc1 freg"); |
| 4176 | - generate_exception_err (ctx, EXCP_RI, 1); | |
| 4194 | + generate_exception (ctx, EXCP_RI); | |
| 4177 | 4195 | return; |
| 4178 | 4196 | } |
| 4179 | 4197 | GEN_LOAD_IMM_TN(T1, fs); |
| ... | ... | @@ -4184,7 +4202,7 @@ static void gen_cp1 (DisasContext *ctx, uint32_t opc, int rt, int fs) |
| 4184 | 4202 | case OPC_CTC1: |
| 4185 | 4203 | if (fs != 0 && fs != 31) { |
| 4186 | 4204 | MIPS_INVAL("ctc1 freg"); |
| 4187 | - generate_exception_err (ctx, EXCP_RI, 1); | |
| 4205 | + generate_exception (ctx, EXCP_RI); | |
| 4188 | 4206 | return; |
| 4189 | 4207 | } |
| 4190 | 4208 | GEN_LOAD_IMM_TN(T1, fs); |
| ... | ... | @@ -4201,7 +4219,7 @@ static void gen_cp1 (DisasContext *ctx, uint32_t opc, int rt, int fs) |
| 4201 | 4219 | ctx->opcode, ctx->opcode >> 26, ctx->opcode & 0x3F, |
| 4202 | 4220 | ((ctx->opcode >> 16) & 0x1F)); |
| 4203 | 4221 | } |
| 4204 | - generate_exception_err (ctx, EXCP_RI, 1); | |
| 4222 | + generate_exception (ctx, EXCP_RI); | |
| 4205 | 4223 | return; |
| 4206 | 4224 | } |
| 4207 | 4225 | MIPS_DEBUG("%s %s %s", opn, regnames[rt], fregnames[fs]); |
| ... | ... | @@ -4219,7 +4237,7 @@ static void gen_cp1 (DisasContext *ctx, uint32_t opc, int rt, int fs) |
| 4219 | 4237 | */ |
| 4220 | 4238 | #define CHECK_FR(ctx, freg) do { \ |
| 4221 | 4239 | if (!((ctx)->CP0_Status & (1<<CP0St_FR)) && ((freg) & 1)) { \ |
| 4222 | - generate_exception_err (ctx, EXCP_RI, 1); \ | |
| 4240 | + generate_exception (ctx, EXCP_RI); \ | |
| 4223 | 4241 | return; \ |
| 4224 | 4242 | } \ |
| 4225 | 4243 | } while(0) |
| ... | ... | @@ -4504,7 +4522,7 @@ static void gen_farith (DisasContext *ctx, uint32_t op1, int ft, int fs, int fd) |
| 4504 | 4522 | ctx->opcode, ctx->opcode >> 26, ctx->opcode & 0x3F, |
| 4505 | 4523 | ((ctx->opcode >> 16) & 0x1F)); |
| 4506 | 4524 | } |
| 4507 | - generate_exception_err (ctx, EXCP_RI, 1); | |
| 4525 | + generate_exception (ctx, EXCP_RI); | |
| 4508 | 4526 | return; |
| 4509 | 4527 | } |
| 4510 | 4528 | if (binary) |
| ... | ... | @@ -4627,11 +4645,12 @@ static void decode_opc (CPUState *env, DisasContext *ctx) |
| 4627 | 4645 | |
| 4628 | 4646 | case OPC_MOVCI: |
| 4629 | 4647 | if (env->CP0_Config1 & (1 << CP0C1_FP)) { |
| 4648 | + save_cpu_state(ctx, 1); | |
| 4630 | 4649 | gen_op_cp1_enabled(); |
| 4631 | 4650 | gen_movci(ctx, rd, rs, (ctx->opcode >> 18) & 0x7, |
| 4632 | 4651 | (ctx->opcode >> 16) & 1); |
| 4633 | 4652 | } else { |
| 4634 | - generate_exception(ctx, EXCP_RI); | |
| 4653 | + generate_exception_err(ctx, EXCP_CpU, 1); | |
| 4635 | 4654 | } |
| 4636 | 4655 | break; |
| 4637 | 4656 | |
| ... | ... | @@ -4905,7 +4924,7 @@ static void decode_opc (CPUState *env, DisasContext *ctx) |
| 4905 | 4924 | gen_farith(ctx, MASK_CP1_FUNC(ctx->opcode), rt, rd, sa); |
| 4906 | 4925 | break; |
| 4907 | 4926 | default: |
| 4908 | - generate_exception_err(ctx, EXCP_RI, 1); | |
| 4927 | + generate_exception (ctx, EXCP_RI); | |
| 4909 | 4928 | break; |
| 4910 | 4929 | } |
| 4911 | 4930 | } else { |
| ... | ... | @@ -4925,16 +4944,17 @@ static void decode_opc (CPUState *env, DisasContext *ctx) |
| 4925 | 4944 | |
| 4926 | 4945 | case OPC_CP3: |
| 4927 | 4946 | if (env->CP0_Config1 & (1 << CP0C1_FP)) { |
| 4947 | + save_cpu_state(ctx, 1); | |
| 4928 | 4948 | gen_op_cp1_enabled(); |
| 4929 | 4949 | op1 = MASK_CP3(ctx->opcode); |
| 4930 | 4950 | switch (op1) { |
| 4931 | 4951 | /* Not implemented */ |
| 4932 | 4952 | default: |
| 4933 | - generate_exception_err(ctx, EXCP_RI, 1); | |
| 4953 | + generate_exception (ctx, EXCP_RI); | |
| 4934 | 4954 | break; |
| 4935 | 4955 | } |
| 4936 | 4956 | } else { |
| 4937 | - generate_exception(ctx, EXCP_RI); | |
| 4957 | + generate_exception_err(ctx, EXCP_CpU, 1); | |
| 4938 | 4958 | } |
| 4939 | 4959 | break; |
| 4940 | 4960 | ... | ... |