]> git.unchartedbackwaters.co.uk Git - francis/winuae.git/commitdiff
CHK2/CMP2 undefined N and V flags emulated.
authorToni Wilen <twilen@winuae.net>
Mon, 2 Sep 2019 17:04:15 +0000 (20:04 +0300)
committerToni Wilen <twilen@winuae.net>
Mon, 2 Sep 2019 17:04:15 +0000 (20:04 +0300)
gencpu.cpp
include/newcpu.h
newcpu_common.cpp

index 4b68b632c88d19731ed6417ebf806e8a81828e6a..d1770636ac1153c19fa851a860088ea209612f7d 100644 (file)
@@ -5017,7 +5017,7 @@ bccl_not68020:
                genamode (curi, curi->smode, "srcreg", curi->size, "extra", 1, 0, 0);
                genamode (curi, curi->dmode, "dstreg", curi->size, "dst", 2, 0, 0);
                fill_prefetch_0 ();
-               printf ("\t{uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15];\n");
+               printf ("\t{uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15];\n");
                switch (curi->size) {
                case sz_byte:
                        printf ("\tlower = (uae_s32)(uae_s8)%s (dsta); upper = (uae_s32)(uae_s8)%s (dsta + 1);\n", srcb, srcb);
@@ -5033,12 +5033,16 @@ bccl_not68020:
                default:
                        term ();
                }
-               printf("\tsetchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? %d : 2);\n", curi->size);
-               printf("\tupper -= lower;\n");
-               printf("\treg -= lower;\n");
-               printf("\tSET_ZFLG (upper == reg || 0 == reg);\n");
-               printf("\tSET_CFLG_ALWAYS (reg > upper);\n");
-               printf("\tif ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); goto %s; }\n}\n", endlabelstr);
+               printf("\tSET_CFLG(0);\n");
+               printf("\tSET_ZFLG(0);\n");
+               printf("\tsetchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 2 : %d);\n", curi->size);
+               printf("\tif(upper == reg || lower == reg) {\n");
+               printf("\t\tSET_ZFLG(1);\n");
+               printf("\t}else{\n");
+               printf("\t\tif (lower <= upper && (reg < lower || reg > upper)) SET_CFLG(1);\n");
+               printf("\t\tif (lower > upper && reg > upper && reg < lower) SET_CFLG(1);\n");
+               printf("\t}\n");
+               printf("\tif ((extra & 0x800) && GET_CFLG()) { Exception_cpu(6); goto %s; }\n}\n", endlabelstr);
                need_endlabel = 1;
                break;
 
index 83d823c55fdeb137f102aa6841efcb359404359a..b672e3c17a7d77a5b5126234711c7907957b8e6e 100644 (file)
@@ -682,7 +682,7 @@ extern void divbyzero_special(bool issigned, uae_s32 dst);
 extern void setdivuflags(bool overflow, uae_u32 dividend, uae_u16 divisor);
 extern void setdivsflags(bool overflow, uae_s32 dividend, uae_s16 divisor);
 extern void setchkundefinedflags(uae_s32 src, uae_s32 dst, int size);
-extern void setchk2undefinedflags(uae_u32 lower, uae_u32 upper, uae_u32 val, int size);
+extern void setchk2undefinedflags(uae_s32 lower, uae_s32 upper, uae_s32 val, int size);
 extern void protect_roms (bool);
 extern void unprotect_maprom (void);
 extern bool is_hardreset(void);
index 02753998a92b237d158fdb04bb6608eda20b9a06..7561d5f15ce91088aead3ed9a1ab94c5df73daa4 100644 (file)
@@ -924,25 +924,98 @@ void setchkundefinedflags(uae_s32 src, uae_s32 dst, int size)
        }
 }
 
-void setchk2undefinedflags(uae_u32 lower, uae_u32 upper, uae_u32 val, int size)
-{
-       uae_u32 nmask;
-       if (size == sz_byte)
-               nmask = 0x80;
-       else if (size == sz_word)
-               nmask = 0x8000;
-       else
-               nmask = 0x80000000;
+/*
+ * CHK2/CMP2 undefined flags
+ *
+ * 68020-68030: See below..
+ * 68040: N: val<0 V=0
+ *
+ */
 
+// This is the complex one.
+// Someone else can attempt to simplify this..
+void setchk2undefinedflags(uae_s32 lower, uae_s32 upper, uae_s32 val, int size)
+{
        SET_NFLG(0);
-       if ((upper & nmask) && val > upper) {
-               SET_NFLG(1);
-       } else if (!(upper & nmask) && val > upper && val < nmask) {
-               SET_NFLG(1);
-       } else if (val < lower) {
-               SET_NFLG(1);
-       }
        SET_VFLG(0);
+
+       if (currprefs.cpu_model >= 68040) {
+               SET_NFLG(val < 0);
+               return;
+       }
+
+       if (val == lower || val == upper)
+               return;
+
+       if (lower < 0 && upper >= 0) {
+               if (val < lower) {
+                       SET_NFLG(1);
+               }
+               if (val >= 0 && val < upper) {
+                       SET_NFLG(1);
+               }
+               if (val >= 0 && lower - val >= 0) {
+                       SET_VFLG(1);
+                       SET_NFLG(0);
+                       if (val > upper) {
+                               SET_NFLG(1);
+                       }
+               }
+       } else if (lower >= 0 && upper < 0) {
+               if (val >= 0) {
+                       SET_NFLG(1);
+               }
+               if (val > upper) {
+                       SET_NFLG(1);
+               }
+               if (val > lower && upper - val >= 0) {
+                       SET_VFLG(1);
+                       SET_NFLG(0);
+               }
+       } else if (lower >= 0 && upper >= 0 && lower > upper) {
+               if (val > upper && val < lower) {
+                       SET_NFLG(1);
+               }
+               if (val < 0 && lower - val < 0) {
+                       SET_VFLG(1);
+               }
+               if (val < 0 && lower - val >= 0) {
+                       SET_NFLG(1);
+               }
+       } else if (lower >= 0 && upper >= 0 && lower <= upper) {
+               if (val >= 0 && val < lower) {
+                       SET_NFLG(1);
+               }
+               if (val > upper) {
+                       SET_NFLG(1);
+               }
+               if (val < 0 && upper - val < 0) {
+                       SET_VFLG(1);
+                       SET_NFLG(1);
+               }
+       } else if (lower < 0 && upper < 0 && lower > upper) {
+               if (val >= 0) {
+                       SET_NFLG(1);
+               }
+               if (val > upper && val < lower) {
+                       SET_NFLG(1);
+               }
+               if (val >= 0 && val - lower < 0) {
+                       SET_NFLG(0);
+                       SET_VFLG(1);
+               }
+       } else if (lower < 0 && upper < 0 && lower <= upper) {
+               if (val < lower) {
+                       SET_NFLG(1);
+               }
+               if (val < 0 && val > upper) {
+                       SET_NFLG(1);
+               }
+               if (val >= 0 && val - lower < 0) {
+                       SET_NFLG(1);
+                       SET_VFLG(1);
+               }
+       }
 }
 
 #ifndef CPUEMU_68000_ONLY