sparc64: fix wrpstate and wrtl on delay slot
authorBlue Swirl <blauwirbel@gmail.com>
Tue, 26 Apr 2011 18:44:20 +0000 (18:44 +0000)
committerBlue Swirl <blauwirbel@gmail.com>
Sat, 14 May 2011 07:30:28 +0000 (07:30 +0000)
Use TCG local to work around TCG register flush due to a branch.

Thanks to Artyom Tarasenko, Igor Kovalenko and Aurelien Jarno.

Signed-off-by: Blue Swirl <blauwirbel@gmail.com>
target-sparc/translate.c

index 3c958b2..9222cde 100644 (file)
@@ -3505,16 +3505,28 @@ static void disas_sparc_insn(DisasContext * dc)
                                 tcg_gen_mov_tl(cpu_tbr, cpu_tmp0);
                                 break;
                             case 6: // pstate
-                                save_state(dc, cpu_cond);
-                                gen_helper_wrpstate(cpu_tmp0);
-                                dc->npc = DYNAMIC_PC;
+                                {
+                                    TCGv r_tmp = tcg_temp_local_new();
+
+                                    tcg_gen_mov_tl(r_tmp, cpu_tmp0);
+                                    save_state(dc, cpu_cond);
+                                    gen_helper_wrpstate(r_tmp);
+                                    tcg_temp_free(r_tmp);
+                                    dc->npc = DYNAMIC_PC;
+                                }
                                 break;
                             case 7: // tl
-                                save_state(dc, cpu_cond);
-                                tcg_gen_trunc_tl_i32(cpu_tmp32, cpu_tmp0);
-                                tcg_gen_st_i32(cpu_tmp32, cpu_env,
-                                               offsetof(CPUSPARCState, tl));
-                                dc->npc = DYNAMIC_PC;
+                                {
+                                    TCGv r_tmp = tcg_temp_local_new();
+
+                                    tcg_gen_mov_tl(r_tmp, cpu_tmp0);
+                                    save_state(dc, cpu_cond);
+                                    tcg_gen_trunc_tl_i32(cpu_tmp32, r_tmp);
+                                    tcg_temp_free(r_tmp);
+                                    tcg_gen_st_i32(cpu_tmp32, cpu_env,
+                                                   offsetof(CPUSPARCState, tl));
+                                    dc->npc = DYNAMIC_PC;
+                                }
                                 break;
                             case 8: // pil
                                 gen_helper_wrpil(cpu_tmp0);