]> git.unchartedbackwaters.co.uk Git - francis/winuae.git/commitdiff
JIT LSL/LSR temporary shift count equals 32 fix.
authorToni Wilen <twilen@winuae.net>
Sat, 31 Oct 2020 17:35:03 +0000 (19:35 +0200)
committerToni Wilen <twilen@winuae.net>
Sat, 31 Oct 2020 17:35:03 +0000 (19:35 +0200)
jit/compemu_midfunc_x86.cpp
jit/compemu_midfunc_x86.h
jit/gencomp.cpp

index afb990340b050723baae196f29bd5561a3a0a245..b42955221b05746426aa9628f7973296765b3b6a 100644 (file)
@@ -116,7 +116,25 @@ MIDFUNC(0,duplicate_carry,(void))
        log_vwrite(FLAGX);
 }
 
-MIDFUNC(3,setcc_for_cntzero,(RR4 /* cnt */, RR4 data, int size))
+MIDFUNC(0,clear_overflow,(void))
+{
+       make_flags_live_internal();
+       raw_pushfl();
+
+       // clear OF flag
+       // and dword [esp],~0x0800
+       emit_byte(0x81);
+       emit_byte(0x24);
+       emit_byte(0x24);
+       emit_byte(0xff);
+       emit_byte(0xf7);
+       emit_byte(0xff);
+       emit_byte(0xff);
+
+       raw_popfl();
+}
+
+MIDFUNC(3,setcc_for_cntzero,(RR4 /* cnt */, RR4 data, int size, int ov))
 {
        uae_u8 *branchadd;
        uae_u8 *branchadd2;
@@ -125,6 +143,19 @@ MIDFUNC(3,setcc_for_cntzero,(RR4 /* cnt */, RR4 data, int size))
        make_flags_live_internal();
 
        raw_pushfl();
+
+       if (ov) {
+               // clear OF flag
+               // and dword [esp],~0x0800
+               emit_byte(0x81);
+               emit_byte(0x24);
+               emit_byte(0x24);
+               emit_byte(0xff);
+               emit_byte(0xf7);
+               emit_byte(0xff);
+               emit_byte(0xff);
+       }
+
        /*
         * shift count can only be in CL register; see shrl_b_rr
         */
index 82b75415b548dbbe12058c9f2aef73f7021e9aa3..a5b6df560184b6aaca4ccc84dd462c71a55d951e 100644 (file)
@@ -186,7 +186,8 @@ DECLARE_MIDFUNC(xor_b(RW1 d, RR1 s));
 DECLARE_MIDFUNC(live_flags(void));
 DECLARE_MIDFUNC(dont_care_flags(void));
 DECLARE_MIDFUNC(duplicate_carry(void));
-DECLARE_MIDFUNC(setcc_for_cntzero(RR4 d, RR4 data, int size));
+DECLARE_MIDFUNC(setcc_for_cntzero(RR4 d, RR4 data, int size, int ov));
+DECLARE_MIDFUNC(clear_overflow(void));
 DECLARE_MIDFUNC(restore_carry(void));
 DECLARE_MIDFUNC(start_needflags(void));
 DECLARE_MIDFUNC(end_needflags(void));
index dd7518fbfe1e958249fde4c6500235816bdcce02..7dfde616bb8d8d582ad3a80c58bbbf8df4e7e447 100644 (file)
@@ -2372,7 +2372,7 @@ gen_opcode(unsigned int opcode)
                        comprintf("\tlive_flags();\n");
                        comprintf("\tend_needflags();\n");
                        if (curi->smode != immi)
-                               comprintf("\tsetcc_for_cntzero(tmpcnt, data, %d);\n", curi->size == sz_byte ? 1 : curi->size == sz_word ? 2 : 4);
+                               comprintf("\tsetcc_for_cntzero(tmpcnt, data, %d, 0);\n", curi->size == sz_byte ? 1 : curi->size == sz_word ? 2 : 4);
                        else
                                comprintf("\tduplicate_carry();\n");
                        comprintf("if (!(needed_flags & FLAG_CZNV)) dont_care_flags();\n");
@@ -2453,7 +2453,7 @@ gen_opcode(unsigned int opcode)
                        comprintf("\tlive_flags();\n");
                        comprintf("\tend_needflags();\n");
                        if (curi->smode != immi)
-                               comprintf("\tsetcc_for_cntzero(tmpcnt, data, %d);\n", curi->size == sz_byte ? 1 : curi->size == sz_word ? 2 : 4);
+                               comprintf("\tsetcc_for_cntzero(tmpcnt, data, %d, 0);\n", curi->size == sz_byte ? 1 : curi->size == sz_word ? 2 : 4);
                        else
                                comprintf("\tduplicate_carry();\n");
                        comprintf("if (!(needed_flags & FLAG_CZNV)) dont_care_flags();\n");
@@ -2485,11 +2485,17 @@ gen_opcode(unsigned int opcode)
                if (curi->smode != immi) {
                        uses_cmov;
                        start_brace();
+                       comprintf("\tint cdata2 = scratchie++;\n");
                        comprintf("\tint cdata = scratchie++;\n");
                        comprintf("\tint tmpcnt=scratchie++;\n");
                        comprintf("\tmov_l_rr(tmpcnt,cnt);\n");
                        comprintf("\tand_l_ri(tmpcnt,63);\n");
                        comprintf("\tmov_l_ri(cdata, 0);\n");
+
+                       comprintf("\tmov_l_ri(cdata2, 32);\n");
+                       comprintf("\tcmp_l(tmpcnt, cdata2);\n");
+                       comprintf("\tcmov_l_rr(tmpcnt, cdata, NATIVE_CC_EQ);\n");
+
                        switch (curi->size) {
                        case sz_byte:
                                comprintf("\ttest_l_ri(tmpcnt, 0x38);\n");
@@ -2524,10 +2530,11 @@ gen_opcode(unsigned int opcode)
                if (!noflags) {
                        comprintf("\tlive_flags();\n");
                        comprintf("\tend_needflags();\n");
-                       if (curi->smode != immi)
-                               comprintf("\tsetcc_for_cntzero(tmpcnt, data, %d);\n", curi->size == sz_byte ? 1 : curi->size == sz_word ? 2 : 4);
-                       else
+                       if (curi->smode != immi) {
+                               comprintf("\tsetcc_for_cntzero(tmpcnt, data, %d, 0);\n", curi->size == sz_byte ? 1 : curi->size == sz_word ? 2 : 4);
+                       } else {
                                comprintf("\tduplicate_carry();\n");
+                       }
                        comprintf("if (!(needed_flags & FLAG_CZNV)) dont_care_flags();\n");
                }
                genastore("data", curi->dmode, "dstreg", curi->size, "data");
@@ -2557,11 +2564,17 @@ gen_opcode(unsigned int opcode)
                if (curi->smode != immi) {
                        uses_cmov;
                        start_brace();
+                       comprintf("\tint cdata2 = scratchie++;\n");
                        comprintf("\tint cdata = scratchie++;\n");
                        comprintf("\tint tmpcnt = scratchie++;\n");
                        comprintf("\tmov_l_rr(tmpcnt,cnt);\n");
                        comprintf("\tand_l_ri(tmpcnt,63);\n");
                        comprintf("\tmov_l_ri(cdata, 0);\n");
+
+                       comprintf("\tmov_l_ri(cdata2, 32);\n");
+                       comprintf("\tcmp_l(tmpcnt, cdata2);\n");
+                       comprintf("\tcmov_l_rr(tmpcnt, cdata, NATIVE_CC_EQ);\n");
+
                        switch (curi->size) {
                        case sz_byte:
                                comprintf("\ttest_l_ri(tmpcnt, 0x38);\n");
@@ -2596,10 +2609,12 @@ gen_opcode(unsigned int opcode)
                if (!noflags) {
                        comprintf("\tlive_flags();\n");
                        comprintf("\tend_needflags();\n");
-                       if (curi->smode != immi)
-                               comprintf("\tsetcc_for_cntzero(tmpcnt, data, %d);\n", curi->size == sz_byte ? 1 : curi->size == sz_word ? 2 : 4);
-                       else
+                       if (curi->smode != immi) {
+                               comprintf("\tsetcc_for_cntzero(tmpcnt, data, %d, 1);\n", curi->size == sz_byte ? 1 : curi->size == sz_word ? 2 : 4);
+                       } else {
+                               comprintf("\tclear_overflow();\n");
                                comprintf("\tduplicate_carry();\n");
+                       }
                        comprintf("if (!(needed_flags & FLAG_CZNV)) dont_care_flags();\n");
                }
                genastore("data", curi->dmode, "dstreg", curi->size, "data");