about summary refs log tree commit diff stats
path: root/src
diff options
context:
space:
mode:
authorYang Liu <liuyang22@iscas.ac.cn>2023-10-15 00:49:30 +0800
committerGitHub <noreply@github.com>2023-10-14 18:49:30 +0200
commit9191c993b15a9287cc2d00d20d609d1271886555 (patch)
tree2453f2a5002372d3a2d9c3ecd1d04c6fde8a0eac /src
parent1a2245043d36a22ebfd90f000901854dde170136 (diff)
downloadbox64-9191c993b15a9287cc2d00d20d609d1271886555.tar.gz
box64-9191c993b15a9287cc2d00d20d609d1271886555.zip
[DYNAREC] Fix x87cache issues (#1025)
* [DYNAREC][WIP] Fix x87cache issues

Co-authored-by fanwj@mail.ustc.edu.cn

* Check x87cache is full before push, is it working?

* Fixed a typo

* Update dynarec_arm64_helper.h

* Review

* Update test25
Diffstat (limited to 'src')
-rw-r--r--src/dynarec/arm64/dynarec_arm64_d8.c6
-rw-r--r--src/dynarec/arm64/dynarec_arm64_d9.c40
-rw-r--r--src/dynarec/arm64/dynarec_arm64_da.c8
-rw-r--r--src/dynarec/arm64/dynarec_arm64_db.c16
-rw-r--r--src/dynarec/arm64/dynarec_arm64_dc.c6
-rw-r--r--src/dynarec/arm64/dynarec_arm64_dd.c16
-rw-r--r--src/dynarec/arm64/dynarec_arm64_de.c22
-rw-r--r--src/dynarec/arm64/dynarec_arm64_df.c20
-rw-r--r--src/dynarec/arm64/dynarec_arm64_helper.c4
-rw-r--r--src/dynarec/arm64/dynarec_arm64_helper.h27
-rw-r--r--src/dynarec/rv64/dynarec_rv64_d8.c4
-rw-r--r--src/dynarec/rv64/dynarec_rv64_d9.c40
-rw-r--r--src/dynarec/rv64/dynarec_rv64_db.c12
-rw-r--r--src/dynarec/rv64/dynarec_rv64_dc.c2
-rw-r--r--src/dynarec/rv64/dynarec_rv64_dd.c8
-rw-r--r--src/dynarec/rv64/dynarec_rv64_de.c14
-rw-r--r--src/dynarec/rv64/dynarec_rv64_df.c12
-rw-r--r--src/dynarec/rv64/dynarec_rv64_functions.c6
-rw-r--r--src/dynarec/rv64/dynarec_rv64_helper.c4
-rw-r--r--src/dynarec/rv64/dynarec_rv64_helper.h22
20 files changed, 166 insertions, 123 deletions
diff --git a/src/dynarec/arm64/dynarec_arm64_d8.c b/src/dynarec/arm64/dynarec_arm64_d8.c
index a363945e..0fd7c7c4 100644
--- a/src/dynarec/arm64/dynarec_arm64_d8.c
+++ b/src/dynarec/arm64/dynarec_arm64_d8.c
@@ -108,7 +108,7 @@ uintptr_t dynarec64_D8(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
                 FCMPD(v1, v2);
             }
             FCOM(x1, x2, x3);
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
         case 0xE0:
         case 0xE1:
@@ -178,7 +178,7 @@ uintptr_t dynarec64_D8(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
                 FDIVD(v1, v2, v1);
             }
             break;
-      
+
         default:
             switch((nextop>>3)&7) {
                 case 0:
@@ -234,7 +234,7 @@ uintptr_t dynarec64_D8(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
                         FCMPD(v1, s0);
                     }
                     FCOM(x1, x2, x3);
-                    x87_do_pop(dyn, ninst, x3);
+                    X87_POP_OR_FAIL(dyn, ninst, x3);
                     break;
                 case 4:
                     INST_NAME("FSUB ST0, float[ED]");
diff --git a/src/dynarec/arm64/dynarec_arm64_d9.c b/src/dynarec/arm64/dynarec_arm64_d9.c
index fcb44d15..2a95b10a 100644
--- a/src/dynarec/arm64/dynarec_arm64_d9.c
+++ b/src/dynarec/arm64/dynarec_arm64_d9.c
@@ -51,7 +51,7 @@ uintptr_t dynarec64_D9(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
         case 0xC6:
         case 0xC7:
             INST_NAME("FLD STx");
-            v2 = x87_do_push(dyn, ninst, x1, X87_ST(nextop&7));
+            X87_PUSH_OR_FAIL(v2, dyn, ninst, x1, X87_ST(nextop&7));
             v1 = x87_get_st(dyn, ninst, x1, x2, (nextop&7)+1, X87_COMBINE(0, (nextop&7)+1));
             if(ST_IS_F(0)) {
                 FMOVS(v2, v1);
@@ -84,7 +84,7 @@ uintptr_t dynarec64_D9(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
 
         case 0xD8:
             INST_NAME("FSTPNCE ST0, ST0");
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
         case 0xD9:
         case 0xDA:
@@ -98,7 +98,7 @@ uintptr_t dynarec64_D9(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
             x87_get_st_empty(dyn, ninst, x1, x2, nextop&7, X87_ST(nextop&7));
             x87_get_st(dyn, ninst, x1, x2, 0, X87_ST0);
             x87_swapreg(dyn, ninst, x1, x2, 0, nextop&7);
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
         case 0xE0:
             INST_NAME("FCHS");
@@ -138,7 +138,7 @@ uintptr_t dynarec64_D9(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
 
         case 0xE8:
             INST_NAME("FLD1");
-            v1 = x87_do_push(dyn, ninst, x1, NEON_CACHE_ST_F);
+            X87_PUSH_OR_FAIL(v1, dyn, ninst, x1, NEON_CACHE_ST_F);
             if(ST_IS_F(0)) {
                 FMOVS_8(v1, 0b01110000);
             } else {
@@ -147,32 +147,32 @@ uintptr_t dynarec64_D9(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
             break;
         case 0xE9:
             INST_NAME("FLDL2T");
-            v1 = x87_do_push(dyn, ninst, x1, NEON_CACHE_ST_D);
+            X87_PUSH_OR_FAIL(v1, dyn, ninst, x1, NEON_CACHE_ST_D);
             FTABLE64(v1, L2T);
             break;
-        case 0xEA:     
+        case 0xEA:
             INST_NAME("FLDL2E");
-            v1 = x87_do_push(dyn, ninst, x1, NEON_CACHE_ST_D);
+            X87_PUSH_OR_FAIL(v1, dyn, ninst, x1, NEON_CACHE_ST_D);
             FTABLE64(v1, L2E);
             break;
         case 0xEB:
             INST_NAME("FLDPI");
-            v1 = x87_do_push(dyn, ninst, x1, NEON_CACHE_ST_D);
+            X87_PUSH_OR_FAIL(v1, dyn, ninst, x1, NEON_CACHE_ST_D);
             FTABLE64(v1, PI);
             break;
         case 0xEC:
             INST_NAME("FLDLG2");
-            v1 = x87_do_push(dyn, ninst, x1, NEON_CACHE_ST_D);
+            X87_PUSH_OR_FAIL(v1, dyn, ninst, x1, NEON_CACHE_ST_D);
             FTABLE64(v1, LG2);
             break;
         case 0xED:
             INST_NAME("FLDLN2");
-            v1 = x87_do_push(dyn, ninst, x1, NEON_CACHE_ST_D);
+            X87_PUSH_OR_FAIL(v1, dyn, ninst, x1, NEON_CACHE_ST_D);
             FTABLE64(v1, LN2);
             break;
         case 0xEE:
             INST_NAME("FLDZ");
-            v1 = x87_do_push(dyn, ninst, x1, NEON_CACHE_ST_F);
+            X87_PUSH_OR_FAIL(v1, dyn, ninst, x1, NEON_CACHE_ST_F);
             VEOR(v1, v1, v1);
             break;
 
@@ -188,14 +188,14 @@ uintptr_t dynarec64_D9(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
             x87_forget(dyn, ninst, x1, x2, 0);
             x87_forget(dyn, ninst, x1, x2, 1);
             CALL(native_fyl2x, -1);
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
         case 0xF2:
             INST_NAME("FPTAN");
             MESSAGE(LOG_DUMP, "Need Optimization\n");
             x87_forget(dyn, ninst, x1, x2, 0);
             CALL(native_ftan, -1);
-            v1 = x87_do_push(dyn, ninst, x1, NEON_CACHE_ST_F);
+            X87_PUSH_OR_FAIL(v1, dyn, ninst, x1, NEON_CACHE_ST_F);
             if(ST_IS_F(0)) {
                 FMOVS_8(v1, 0b01110000);
             } else {
@@ -208,12 +208,12 @@ uintptr_t dynarec64_D9(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
             x87_forget(dyn, ninst, x1, x2, 0);
             x87_forget(dyn, ninst, x1, x2, 1);
             CALL(native_fpatan, -1);
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
         case 0xF4:
             INST_NAME("FXTRACT");
             MESSAGE(LOG_DUMP, "Need Optimization\n");
-            x87_do_push_empty(dyn, ninst, 0);
+            X87_PUSH_EMPTY_OR_FAIL(dyn, ninst, 0);
             x87_forget(dyn, ninst, x1, x2, 1);
             CALL(native_fxtract, -1);
             break;
@@ -253,7 +253,7 @@ uintptr_t dynarec64_D9(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
             x87_forget(dyn, ninst, x1, x2, 0);
             x87_forget(dyn, ninst, x1, x2, 1);
             CALL(native_fyl2xp1, -1);
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
         case 0xFA:
             INST_NAME("FSQRT");
@@ -267,7 +267,7 @@ uintptr_t dynarec64_D9(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
         case 0xFB:
             INST_NAME("FSINCOS");
             MESSAGE(LOG_DUMP, "Need Optimization\n");
-            x87_do_push_empty(dyn, ninst, 0);
+            X87_PUSH_EMPTY_OR_FAIL(dyn, ninst, 0);
             x87_forget(dyn, ninst, x1, x2, 1);
             CALL(native_fsincos, -1);
             break;
@@ -322,12 +322,12 @@ uintptr_t dynarec64_D9(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
         case 0xEF:
             DEFAULT;
             break;
-             
+
         default:
             switch((nextop>>3)&7) {
                 case 0:
                     INST_NAME("FLD ST0, float[ED]");
-                    v1 = x87_do_push(dyn, ninst, x1, box64_dynarec_x87double?NEON_CACHE_ST_D:NEON_CACHE_ST_F);
+                    X87_PUSH_OR_FAIL(v1, dyn, ninst, x1, box64_dynarec_x87double?NEON_CACHE_ST_D:NEON_CACHE_ST_F);
                     addr = geted(dyn, addr, ninst, nextop, &ed, x2, &fixedaddress, &unscaled, 0xfff<<2, 3, rex, NULL, 0, 0);
                     VLD32(v1, ed, fixedaddress);
                     if(!ST_IS_F(0)) {
@@ -354,7 +354,7 @@ uintptr_t dynarec64_D9(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
                         FCVT_S_D(v1, v1);
                     }
                     VST32(v1, ed, fixedaddress);
-                    x87_do_pop(dyn, ninst, x3);
+                    X87_POP_OR_FAIL(dyn, ninst, x3);
                     break;
                 case 4:
                     INST_NAME("FLDENV Ed");
diff --git a/src/dynarec/arm64/dynarec_arm64_da.c b/src/dynarec/arm64/dynarec_arm64_da.c
index 101978e7..e1735b87 100644
--- a/src/dynarec/arm64/dynarec_arm64_da.c
+++ b/src/dynarec/arm64/dynarec_arm64_da.c
@@ -119,7 +119,7 @@ uintptr_t dynarec64_DA(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
             } else {
                 FCSELD(v1, v2, v1, cNE);        // F_PF==0
             }
-            break;       
+            break;
         case 0xE9:
             INST_NAME("FUCOMPP ST0, ST1");
             v1 = x87_get_st(dyn, ninst, x1, x2, 0, X87_COMBINE(0, nextop&7));
@@ -130,8 +130,8 @@ uintptr_t dynarec64_DA(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
                 FCMPD(v1, v2);
             }
             FCOM(x1, x2, x3);
-            x87_do_pop(dyn, ninst, x3);
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
 
         case 0xE4:
@@ -190,7 +190,7 @@ uintptr_t dynarec64_DA(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
                     SCVTFDD(v2, v2);    // i64 -> double
                     FCMPD(v1, v2);
                     FCOM(x1, x2, x3);
-                    x87_do_pop(dyn, ninst, x3);
+                    X87_POP_OR_FAIL(dyn, ninst, x3);
                     break;
                 case 4:
                     INST_NAME("FISUB ST0, Ed");
diff --git a/src/dynarec/arm64/dynarec_arm64_db.c b/src/dynarec/arm64/dynarec_arm64_db.c
index 89743516..f7cb9358 100644
--- a/src/dynarec/arm64/dynarec_arm64_db.c
+++ b/src/dynarec/arm64/dynarec_arm64_db.c
@@ -156,7 +156,7 @@ uintptr_t dynarec64_DB(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
             }
             FCOMI(x1, x2);
             break;
-        case 0xF0:  
+        case 0xF0:
         case 0xF1:
         case 0xF2:
         case 0xF3:
@@ -188,7 +188,7 @@ uintptr_t dynarec64_DB(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
             switch((nextop>>3)&7) {
                 case 0:
                     INST_NAME("FILD ST0, Ed");
-                    v1 = x87_do_push(dyn, ninst, x1, NEON_CACHE_ST_D);
+                    X87_PUSH_OR_FAIL(v1, dyn, ninst, x1, NEON_CACHE_ST_D);
                     addr = geted(dyn, addr, ninst, nextop, &ed, x2, &fixedaddress, &unscaled, 0xfff<<2, 3, rex, NULL, 0, 0);
                     VLD32(v1, ed, fixedaddress);
                     SXTL_32(v1, v1);    // i32 -> i64
@@ -218,7 +218,7 @@ uintptr_t dynarec64_DB(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
                     STW(x5, wback, fixedaddress);
                     MARK3;
                     #endif
-                    x87_do_pop(dyn, ninst, x3);
+                    X87_POP_OR_FAIL(dyn, ninst, x3);
                     break;
                 case 2:
                     INST_NAME("FIST Ed, ST0");
@@ -273,7 +273,7 @@ uintptr_t dynarec64_DB(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
                     MARK3;
                     #endif
                     x87_restoreround(dyn, ninst, u8);
-                    x87_do_pop(dyn, ninst, x3);
+                    X87_POP_OR_FAIL(dyn, ninst, x3);
                     break;
                 case 5:
                     INST_NAME("FLD tbyte");
@@ -296,13 +296,13 @@ uintptr_t dynarec64_DB(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
                         STRH_U12(x6, ed, 8);
                     } else {
                         if(box64_x87_no80bits) {
-                            v1 = x87_do_push(dyn, ninst, x1, NEON_CACHE_ST_D);
+                            X87_PUSH_OR_FAIL(v1, dyn, ninst, x1, NEON_CACHE_ST_D);
                             VLDR64_U12(v1, ed, fixedaddress);
                         } else {
                             if(ed!=x1) {
                                 MOVx_REG(x1, ed);
                             }
-                            x87_do_push_empty(dyn, ninst, x3);
+                            X87_PUSH_EMPTY_OR_FAIL(dyn, ninst, x3);
                             CALL(native_fld, -1);
                         }
                     }
@@ -344,7 +344,7 @@ uintptr_t dynarec64_DB(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
                         CMPSw_REG(x3, x4);
                         B_MARK2(cNE);
                         // NaN and Infinite
-                        ORRw_mask(x3, x5, 0, 0b1110);    //x3 = sign | 0x7fff 
+                        ORRw_mask(x3, x5, 0, 0b1110);    //x3 = sign | 0x7fff
                         TSTx_mask(x1, 1, 0, 0b110011); //0x000fffffffffffffL
                         ORRx_mask(x5, xZR, 1, 1, 0);    //0x8000000000000000
                         ORRx_mask(x4, xZR, 1, 0b10, 0b01); //0xc000000000000000
@@ -372,7 +372,7 @@ uintptr_t dynarec64_DB(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
                         STRH_U12(x3, wback, 8);
                         #endif
                     }
-                    x87_do_pop(dyn, ninst, x3);
+                    X87_POP_OR_FAIL(dyn, ninst, x3);
                     break;
                 default:
                     DEFAULT;
diff --git a/src/dynarec/arm64/dynarec_arm64_dc.c b/src/dynarec/arm64/dynarec_arm64_dc.c
index bd6c98d1..67be2c25 100644
--- a/src/dynarec/arm64/dynarec_arm64_dc.c
+++ b/src/dynarec/arm64/dynarec_arm64_dc.c
@@ -106,7 +106,7 @@ uintptr_t dynarec64_DC(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
                 FCMPD(v1, v2);
             }
             FCOM(x1, x2, x3);
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
         case 0xE0:
         case 0xE1:
@@ -158,7 +158,7 @@ uintptr_t dynarec64_DC(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
             } else {
                 FDIVD(v1, v2, v1);
             }
-            break;       
+            break;
         case 0xF8:
         case 0xF9:
         case 0xFA:
@@ -211,7 +211,7 @@ uintptr_t dynarec64_DC(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
                     VLD64(v2, wback, fixedaddress);
                     FCMPD(v1, v2);
                     FCOM(x1, x2, x3);
-                    x87_do_pop(dyn, ninst, x3);
+                    X87_POP_OR_FAIL(dyn, ninst, x3);
                     break;
                 case 4:
                     INST_NAME("FSUB ST0, double[ED]");
diff --git a/src/dynarec/arm64/dynarec_arm64_dd.c b/src/dynarec/arm64/dynarec_arm64_dd.c
index b2697912..7c689bbf 100644
--- a/src/dynarec/arm64/dynarec_arm64_dd.c
+++ b/src/dynarec/arm64/dynarec_arm64_dd.c
@@ -74,7 +74,7 @@ uintptr_t dynarec64_DD(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
             break;
         case 0xD8:
             INST_NAME("FSTP ST0, ST0");
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
         case 0xD9:
         case 0xDA:
@@ -88,7 +88,7 @@ uintptr_t dynarec64_DD(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
             x87_get_st_empty(dyn, ninst, x1, x2, nextop&7, X87_ST(nextop&7));
             x87_get_st(dyn, ninst, x1, x2, 0, X87_ST0);
             x87_swapreg(dyn, ninst, x1, x2, 0, nextop&7);
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
 
         case 0xE0:
@@ -126,7 +126,7 @@ uintptr_t dynarec64_DD(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
                 FCMPD(v1, v2);
             }
             FCOM(x1, x2, x3);
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
 
         case 0xC8:
@@ -160,7 +160,7 @@ uintptr_t dynarec64_DD(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
             switch((nextop>>3)&7) {
                 case 0:
                     INST_NAME("FLD double");
-                    v1 = x87_do_push(dyn, ninst, x3, NEON_CACHE_ST_D);
+                    X87_PUSH_OR_FAIL(v1, dyn, ninst, x3, NEON_CACHE_ST_D);
                     addr = geted(dyn, addr, ninst, nextop, &ed, x1, &fixedaddress, &unscaled, 0xfff<<3, 7, rex, NULL, 0, 0);
                     VLD64(v1, ed, fixedaddress);
                     break;
@@ -187,7 +187,7 @@ uintptr_t dynarec64_DD(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
                     STx(x5, ed, fixedaddress);
                     MARK3;
                     #endif
-                    x87_do_pop(dyn, ninst, x3);
+                    X87_POP_OR_FAIL(dyn, ninst, x3);
                     break;
                 case 2:
                     INST_NAME("FST double");
@@ -200,9 +200,9 @@ uintptr_t dynarec64_DD(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
                     v1 = x87_get_st(dyn, ninst, x1, x2, 0, NEON_CACHE_ST_D);
                     addr = geted(dyn, addr, ninst, nextop, &ed, x1, &fixedaddress, &unscaled, 0xfff<<3, 7, rex, NULL, 0, 0);
                     VST64(v1, ed, fixedaddress);
-                    x87_do_pop(dyn, ninst, x3);
+                    X87_POP_OR_FAIL(dyn, ninst, x3);
                     break;
-                case 4: 
+                case 4:
                     INST_NAME("FRSTOR m108byte");
                     MESSAGE(LOG_DUMP, "Need Optimization\n");
                     fpu_purgecache(dyn, ninst, 0, x1, x2, x3);
@@ -210,7 +210,7 @@ uintptr_t dynarec64_DD(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
                     if(ed!=x1) {MOVx_REG(x1, ed);}
                     CALL(native_frstor, -1);
                     break;
-                case 6: 
+                case 6:
                     INST_NAME("FSAVE m108byte");
                     MESSAGE(LOG_DUMP, "Need Optimization\n");
                     fpu_purgecache(dyn, ninst, 0, x1, x2, x3);
diff --git a/src/dynarec/arm64/dynarec_arm64_de.c b/src/dynarec/arm64/dynarec_arm64_de.c
index c045d23c..c46b0817 100644
--- a/src/dynarec/arm64/dynarec_arm64_de.c
+++ b/src/dynarec/arm64/dynarec_arm64_de.c
@@ -53,7 +53,7 @@ uintptr_t dynarec64_DE(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
             } else {
                 FADDD(v1, v1, v2);
             }
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
         case 0xC8:
         case 0xC9:
@@ -71,7 +71,7 @@ uintptr_t dynarec64_DE(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
             } else {
                 FMULD(v1, v1, v2);
             }
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
         case 0xD0:
         case 0xD1:
@@ -90,7 +90,7 @@ uintptr_t dynarec64_DE(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
                 FCMPD(v1, v2);
             }
             FCOM(x1, x2, x3);
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
         case 0xD9:
             INST_NAME("FCOMPP ST0, STx");
@@ -102,8 +102,8 @@ uintptr_t dynarec64_DE(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
                 FCMPD(v1, v2);
             }
             FCOM(x1, x2, x3);
-            x87_do_pop(dyn, ninst, x3);
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
         case 0xE0:
         case 0xE1:
@@ -121,7 +121,7 @@ uintptr_t dynarec64_DE(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
             } else {
                 FSUBD(v1, v2, v1);
             }
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
         case 0xE8:
         case 0xE9:
@@ -139,7 +139,7 @@ uintptr_t dynarec64_DE(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
             } else {
                 FSUBD(v1, v1, v2);
             }
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
         case 0xF0:
         case 0xF1:
@@ -157,8 +157,8 @@ uintptr_t dynarec64_DE(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
             } else {
                 FDIVD(v1, v2, v1);
             }
-            x87_do_pop(dyn, ninst, x3);
-            break;       
+            X87_POP_OR_FAIL(dyn, ninst, x3);
+            break;
         case 0xF8:
         case 0xF9:
         case 0xFA:
@@ -175,7 +175,7 @@ uintptr_t dynarec64_DE(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
             } else {
                 FDIVD(v1, v1, v2);
             }
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
         case 0xD8:
         case 0xDA:
@@ -233,7 +233,7 @@ uintptr_t dynarec64_DE(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
                     SCVTFDD(v2, v2);
                     FCMPD(v1, v2);
                     FCOM(x1, x2, x3);
-                    x87_do_pop(dyn, ninst, x3);
+                    X87_POP_OR_FAIL(dyn, ninst, x3);
                     break;
                 case 4:
                     INST_NAME("FISUB ST0, word[ED]");
diff --git a/src/dynarec/arm64/dynarec_arm64_df.c b/src/dynarec/arm64/dynarec_arm64_df.c
index c1ae66a3..40ad5066 100644
--- a/src/dynarec/arm64/dynarec_arm64_df.c
+++ b/src/dynarec/arm64/dynarec_arm64_df.c
@@ -51,7 +51,7 @@ uintptr_t dynarec64_DF(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
         case 0xC7:
             INST_NAME("FFREEP STx");
             // not handling Tag...
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
 
         case 0xE0:
@@ -81,7 +81,7 @@ uintptr_t dynarec64_DF(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
                 FCMPD(v1, v2);
             }
             FCOMI(x1, x2);
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
         case 0xF0:
         case 0xF1:
@@ -102,7 +102,7 @@ uintptr_t dynarec64_DF(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
                 FCMPD(v1, v2);
             }
             FCOMI(x1, x2);
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
 
         case 0xC8:
@@ -151,7 +151,7 @@ uintptr_t dynarec64_DF(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
             switch((nextop>>3)&7) {
                 case 0:
                     INST_NAME("FILD ST0, Ew");
-                    v1 = x87_do_push(dyn, ninst, x1, NEON_CACHE_ST_F);
+                    X87_PUSH_OR_FAIL(v1, dyn, ninst, x1, NEON_CACHE_ST_F);
                     addr = geted(dyn, addr, ninst, nextop, &wback, x3, &fixedaddress, &unscaled, 0xfff<<1, 1, rex, NULL, 0, 0);
                     LDSHw(x1, wback, fixedaddress);
                     if(ST_IS_F(0)) {
@@ -196,7 +196,7 @@ uintptr_t dynarec64_DF(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
                     MARK3;
                     STH(x3, wback, fixedaddress);
                     #endif
-                    x87_do_pop(dyn, ninst, x3);
+                    X87_POP_OR_FAIL(dyn, ninst, x3);
                     break;
                 case 2:
                     INST_NAME("FIST Ew, ST0");
@@ -275,19 +275,19 @@ uintptr_t dynarec64_DF(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
                     MARK3;
                     STH(x3, wback, fixedaddress);
                     #endif
-                    x87_do_pop(dyn, ninst, x3);
+                    X87_POP_OR_FAIL(dyn, ninst, x3);
                     x87_restoreround(dyn, ninst, u8);
                     break;
                 case 4:
                     INST_NAME("FBLD ST0, tbytes");
-                    x87_do_push_empty(dyn, ninst, x1);
+                    X87_PUSH_EMPTY_OR_FAIL(dyn, ninst, x1);
                     addr = geted(dyn, addr, ninst, nextop, &ed, x1, &fixedaddress, NULL, 0, 0, rex, NULL, 0, 0);
                     if(ed!=x1) {MOVx_REG(x1, ed);}
                     CALL(fpu_fbld, -1);
                     break;
                 case 5:
                     INST_NAME("FILD ST0, i64");
-                    v1 = x87_do_push(dyn, ninst, x1, NEON_CACHE_ST_I64);
+                    X87_PUSH_OR_FAIL(v1, dyn, ninst, x1, NEON_CACHE_ST_I64);
                     addr = geted(dyn, addr, ninst, nextop, &wback, x3, &fixedaddress, &unscaled, 0xfff<<3, 7, rex, NULL, 0, 0);
                     VLD64(v1, wback, fixedaddress);
                     if(!ST_IS_I64(0)) {
@@ -319,7 +319,7 @@ uintptr_t dynarec64_DF(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
                     addr = geted(dyn, addr, ninst, nextop, &ed, x1, &fixedaddress, NULL, 0, 0, rex, NULL, 0, 0);
                     if(ed!=x1) {MOVx_REG(x1, ed);}
                     CALL(fpu_fbst, -1);
-                    x87_do_pop(dyn, ninst, x3);
+                    X87_POP_OR_FAIL(dyn, ninst, x3);
                     break;
                 case 7:
                     INST_NAME("FISTP i64, ST0");
@@ -375,7 +375,7 @@ uintptr_t dynarec64_DF(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
                         #endif
                         x87_restoreround(dyn, ninst, u8);
                     }
-                    x87_do_pop(dyn, ninst, x3);
+                    X87_POP_OR_FAIL(dyn, ninst, x3);
                     break;
                 default:
                     DEFAULT;
diff --git a/src/dynarec/arm64/dynarec_arm64_helper.c b/src/dynarec/arm64/dynarec_arm64_helper.c
index d7474686..874c2ce7 100644
--- a/src/dynarec/arm64/dynarec_arm64_helper.c
+++ b/src/dynarec/arm64/dynarec_arm64_helper.c
@@ -256,7 +256,7 @@ static uintptr_t geted_32(dynarec_arm_t* dyn, uintptr_t addr, int ninst, uint8_t
         }
         if(nextop&0x80)
             i32 = F32S;
-        else 
+        else
             i32 = F8S;
         if(i32==0 || ((i32>=absmin) && (i32<=absmax)  && !(i32&mask)) || (unscaled && (i32>-256) && (i32<256))) {
             *fixaddress = i32;
@@ -2098,4 +2098,4 @@ void fpu_propagate_stack(dynarec_arm_t* dyn, int ninst)
     dyn->n.news = 0;
     dyn->n.stack_push = 0;
     dyn->n.swapped = 0;
-}
\ No newline at end of file
+}
diff --git a/src/dynarec/arm64/dynarec_arm64_helper.h b/src/dynarec/arm64/dynarec_arm64_helper.h
index dad782c5..8a8f9fb5 100644
--- a/src/dynarec/arm64/dynarec_arm64_helper.h
+++ b/src/dynarec/arm64/dynarec_arm64_helper.h
@@ -759,6 +759,27 @@
     LDP_REGS(R12, R13);     \
     LDP_REGS(R14, R15)
 
+#define X87_PUSH_OR_FAIL(var, dyn, ninst, scratch, t) \
+    if (dyn->n.stack == +8) {                         \
+        *ok = 0;                                      \
+        break;                                        \
+    }                                                 \
+    var = x87_do_push(dyn, ninst, scratch, t);
+
+#define X87_PUSH_EMPTY_OR_FAIL(dyn, ninst, scratch) \
+    if (dyn->n.stack == +8) {                       \
+        *ok = 0;                                    \
+        break;                                      \
+    }                                               \
+    x87_do_push_empty(dyn, ninst, scratch);
+
+#define X87_POP_OR_FAIL(dyn, ninst, scratch) \
+    if (dyn->n.stack == -8) {                \
+        *ok = 0;                             \
+        break;                               \
+    }                                        \
+    x87_do_pop(dyn, ninst, scratch);
+
 #define SET_DFNONE(S)    if(!dyn->f.dfnone) {STRw_U12(wZR, xEmu, offsetof(x64emu_t, df)); dyn->f.dfnone=1;}
 #define SET_DF(S, N)     if((N)!=d_none) {MOVZw(S, (N)); STRw_U12(S, xEmu, offsetof(x64emu_t, df)); dyn->f.dfnone=0;} else SET_DFNONE(S)
 #define SET_NODF()          dyn->f.dfnone = 0
@@ -989,9 +1010,9 @@ void* arm64_next(x64emu_t* emu, uintptr_t addr);
 
 #define emit_pf         STEPNAME(emit_pf)
 
-#define x87_do_push     STEPNAME(x87_do_push)
-#define x87_do_push_empty STEPNAME(x87_do_push_empty)
-#define x87_do_pop      STEPNAME(x87_do_pop)
+#define x87_do_push         STEPNAME(x87_do_push)
+#define x87_do_push_empty   STEPNAME(x87_do_push_empty)
+#define x87_do_pop          STEPNAME(x87_do_pop)
 #define x87_get_current_cache   STEPNAME(x87_get_current_cache)
 #define x87_get_cache   STEPNAME(x87_get_cache)
 #define x87_get_neoncache STEPNAME(x87_get_neoncache)
diff --git a/src/dynarec/rv64/dynarec_rv64_d8.c b/src/dynarec/rv64/dynarec_rv64_d8.c
index 7f14468b..e293236e 100644
--- a/src/dynarec/rv64/dynarec_rv64_d8.c
+++ b/src/dynarec/rv64/dynarec_rv64_d8.c
@@ -43,7 +43,7 @@ uintptr_t dynarec64_D8(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
 
     switch(nextop) {
         case 0xC0 ... 0xC7:
-        
+
         case 0xC8 ... 0xCF:
 
         case 0xD0 ... 0xD7:
@@ -92,7 +92,7 @@ uintptr_t dynarec64_D8(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
             }
             OR(x3, x3, x1);
             SH(x3, xEmu, offsetof(x64emu_t, sw));
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
         case 0xE0 ... 0xE7:
             INST_NAME("FSUB ST0, STx");
diff --git a/src/dynarec/rv64/dynarec_rv64_d9.c b/src/dynarec/rv64/dynarec_rv64_d9.c
index 4940d6b4..d5f2ad6d 100644
--- a/src/dynarec/rv64/dynarec_rv64_d9.c
+++ b/src/dynarec/rv64/dynarec_rv64_d9.c
@@ -54,7 +54,7 @@ uintptr_t dynarec64_D9(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
         case 0xC6:
         case 0xC7:
             INST_NAME("FLD STx");
-            v2 = x87_do_push(dyn, ninst, x1, X87_ST(nextop&7));
+            X87_PUSH_OR_FAIL(v2, dyn, ninst, x1, X87_ST(nextop&7));
             v1 = x87_get_st(dyn, ninst, x1, x2, (nextop&7)+1, X87_COMBINE(0, (nextop&7)+1));
             if(ST_IS_F(0)) {
                 FMVS(v2, v1);
@@ -87,7 +87,7 @@ uintptr_t dynarec64_D9(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
 
         case 0xD8:
             INST_NAME("FSTPNCE ST0, ST0");
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
         case 0xD9:
         case 0xDA:
@@ -101,7 +101,7 @@ uintptr_t dynarec64_D9(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
             x87_get_st_empty(dyn, ninst, x1, x2, nextop&7, X87_ST(nextop&7));
             x87_get_st(dyn, ninst, x1, x2, 0, X87_ST0);
             x87_swapreg(dyn, ninst, x1, x2, 0, nextop&7);
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
         case 0xE0:
             INST_NAME("FCHS");
@@ -135,7 +135,7 @@ uintptr_t dynarec64_D9(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
 
         case 0xE8:
             INST_NAME("FLD1");
-            v1 = x87_do_push(dyn, ninst, x1, EXT_CACHE_ST_F);
+            X87_PUSH_OR_FAIL(v1, dyn, ninst, x1, EXT_CACHE_ST_F);
             if(ST_IS_F(0)) {
                 MOV32w(x1, 0x3f800000);
                 FMVWX(v1, x1);
@@ -146,32 +146,32 @@ uintptr_t dynarec64_D9(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
             break;
         case 0xE9:
             INST_NAME("FLDL2T");
-            v1 = x87_do_push(dyn, ninst, x1, EXT_CACHE_ST_D);
+            X87_PUSH_OR_FAIL(v1, dyn, ninst, x1, EXT_CACHE_ST_D);
             FTABLE64(v1, L2T);
             break;
-        case 0xEA:     
+        case 0xEA:
             INST_NAME("FLDL2E");
-            v1 = x87_do_push(dyn, ninst, x1, EXT_CACHE_ST_D);
+            X87_PUSH_OR_FAIL(v1, dyn, ninst, x1, EXT_CACHE_ST_D);
             FTABLE64(v1, L2E);
             break;
         case 0xEB:
             INST_NAME("FLDPI");
-            v1 = x87_do_push(dyn, ninst, x1, EXT_CACHE_ST_D);
+            X87_PUSH_OR_FAIL(v1, dyn, ninst, x1, EXT_CACHE_ST_D);
             FTABLE64(v1, PI);
             break;
         case 0xEC:
             INST_NAME("FLDLG2");
-            v1 = x87_do_push(dyn, ninst, x1, EXT_CACHE_ST_D);
+            X87_PUSH_OR_FAIL(v1, dyn, ninst, x1, EXT_CACHE_ST_D);
             FTABLE64(v1, LG2);
             break;
         case 0xED:
             INST_NAME("FLDLN2");
-            v1 = x87_do_push(dyn, ninst, x1, EXT_CACHE_ST_D);
+            X87_PUSH_OR_FAIL(v1, dyn, ninst, x1, EXT_CACHE_ST_D);
             FTABLE64(v1, LN2);
             break;
         case 0xEE:
             INST_NAME("FLDZ");
-            v1 = x87_do_push(dyn, ninst, x1, EXT_CACHE_ST_F);
+            X87_PUSH_OR_FAIL(v1, dyn, ninst, x1, EXT_CACHE_ST_F);
             if(ST_IS_F(0)) {
                 FMVWX(v1, xZR);
             } else {
@@ -191,14 +191,14 @@ uintptr_t dynarec64_D9(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
             x87_forget(dyn, ninst, x1, x2, 0);
             x87_forget(dyn, ninst, x1, x2, 1);
             CALL(native_fyl2x, -1);
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
         case 0xF2:
             INST_NAME("FPTAN");
             MESSAGE(LOG_DUMP, "Need Optimization\n");
             x87_forget(dyn, ninst, x1, x2, 0);
             CALL(native_ftan, -1);
-            v1 = x87_do_push(dyn, ninst, x1, EXT_CACHE_ST_F);
+            X87_PUSH_OR_FAIL(v1, dyn, ninst, x1, EXT_CACHE_ST_F);
             if(ST_IS_F(0)) {
                 MOV32w(x1, 0x3f800000);
                 FMVWX(v1, x1);
@@ -213,12 +213,12 @@ uintptr_t dynarec64_D9(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
             x87_forget(dyn, ninst, x1, x2, 0);
             x87_forget(dyn, ninst, x1, x2, 1);
             CALL(native_fpatan, -1);
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
         case 0xF4:
             INST_NAME("FXTRACT");
             MESSAGE(LOG_DUMP, "Need Optimization\n");
-            x87_do_push_empty(dyn, ninst, 0);
+            X87_PUSH_EMPTY_OR_FAIL(dyn, ninst, 0);
             x87_forget(dyn, ninst, x1, x2, 1);
             CALL(native_fxtract, -1);
             break;
@@ -258,7 +258,7 @@ uintptr_t dynarec64_D9(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
             x87_forget(dyn, ninst, x1, x2, 0);
             x87_forget(dyn, ninst, x1, x2, 1);
             CALL(native_fyl2xp1, -1);
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
         case 0xFA:
             INST_NAME("FSQRT");
@@ -272,7 +272,7 @@ uintptr_t dynarec64_D9(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
         case 0xFB:
             INST_NAME("FSINCOS");
             MESSAGE(LOG_DUMP, "Need Optimization\n");
-            x87_do_push_empty(dyn, ninst, 0);
+            X87_PUSH_EMPTY_OR_FAIL(dyn, ninst, 0);
             x87_forget(dyn, ninst, x1, x2, 1);
             CALL(native_fsincos, -1);
             break;
@@ -349,12 +349,12 @@ uintptr_t dynarec64_D9(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
         case 0xEF:
             DEFAULT;
             break;
-             
+
         default:
             switch((nextop>>3)&7) {
                 case 0:
                     INST_NAME("FLD ST0, float[ED]");
-                    v1 = x87_do_push(dyn, ninst, x1, box64_dynarec_x87double?EXT_CACHE_ST_D:EXT_CACHE_ST_F);
+                    X87_PUSH_OR_FAIL(v1, dyn, ninst, x1, box64_dynarec_x87double?EXT_CACHE_ST_D:EXT_CACHE_ST_F);
                     addr = geted(dyn, addr, ninst, nextop, &ed, x2, x1, &fixedaddress, rex, NULL, 1, 0);
                     FLW(v1, ed, fixedaddress);
                     if(!ST_IS_F(0)) {
@@ -381,7 +381,7 @@ uintptr_t dynarec64_D9(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
                         FCVTSD(v1, v1);
                     }
                     FSW(v1, ed, fixedaddress);
-                    x87_do_pop(dyn, ninst, x3);
+                    X87_POP_OR_FAIL(dyn, ninst, x3);
                     break;
                 case 4:
                     INST_NAME("FLDENV Ed");
diff --git a/src/dynarec/rv64/dynarec_rv64_db.c b/src/dynarec/rv64/dynarec_rv64_db.c
index 7a5dddb0..36286197 100644
--- a/src/dynarec/rv64/dynarec_rv64_db.c
+++ b/src/dynarec/rv64/dynarec_rv64_db.c
@@ -189,7 +189,7 @@ uintptr_t dynarec64_DB(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
                 }
             }
             break;
-        case 0xF0:  
+        case 0xF0:
         case 0xF1:
         case 0xF2:
         case 0xF3:
@@ -213,7 +213,7 @@ uintptr_t dynarec64_DB(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
             switch((nextop>>3)&7) {
                 case 0:
                     INST_NAME("FILD ST0, Ed");
-                    v1 = x87_do_push(dyn, ninst, x1, EXT_CACHE_ST_D);
+                    X87_PUSH_OR_FAIL(v1, dyn, ninst, x1, EXT_CACHE_ST_D);
                     addr = geted(dyn, addr, ninst, nextop, &ed, x2, x1, &fixedaddress, rex, NULL, 1, 0);
                     LW(x1, ed, fixedaddress);
                     FCVTDW(v1, x1, RD_RNE);    // i32 -> double
@@ -245,7 +245,7 @@ uintptr_t dynarec64_DB(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
                     }
                     MARK2;
                     SW(x4, wback, fixedaddress);
-                    x87_do_pop(dyn, ninst, x3);
+                    X87_POP_OR_FAIL(dyn, ninst, x3);
                     break;
                 case 5:
                     INST_NAME("FLD tbyte");
@@ -268,13 +268,13 @@ uintptr_t dynarec64_DB(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
                         SH(x6, ed, fixedaddress+8);
                     } else {
                         if(box64_x87_no80bits) {
-                            v1 = x87_do_push(dyn, ninst, x1, EXT_CACHE_ST_D);
+                            X87_PUSH_OR_FAIL(v1, dyn, ninst, x1, EXT_CACHE_ST_D);
                             FLD(v1, ed, fixedaddress);
                         } else {
                             if(ed!=x1) {
                                 MV(x1, ed);
                             }
-                            x87_do_push_empty(dyn, ninst, x3);
+                            X87_PUSH_EMPTY_OR_FAIL(dyn, ninst, x3);
                             CALL(native_fld, -1);
                         }
                     }
@@ -293,7 +293,7 @@ uintptr_t dynarec64_DB(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
                         }
                         CALL(native_fstp, -1);
                     }
-                    x87_do_pop(dyn, ninst, x3);
+                    X87_POP_OR_FAIL(dyn, ninst, x3);
                     break;
                 default:
                     DEFAULT;
diff --git a/src/dynarec/rv64/dynarec_rv64_dc.c b/src/dynarec/rv64/dynarec_rv64_dc.c
index d802e2fb..6a84c603 100644
--- a/src/dynarec/rv64/dynarec_rv64_dc.c
+++ b/src/dynarec/rv64/dynarec_rv64_dc.c
@@ -101,7 +101,7 @@ uintptr_t dynarec64_DC(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
                     OR(x3, x3, x1);
                     SH(x3, xEmu, offsetof(x64emu_t, sw));
 
-                    x87_do_pop(dyn, ninst, x3);
+                    X87_POP_OR_FAIL(dyn, ninst, x3);
                     break;
                 case 6:
                     INST_NAME("FDIV ST0, double[ED]");
diff --git a/src/dynarec/rv64/dynarec_rv64_dd.c b/src/dynarec/rv64/dynarec_rv64_dd.c
index 044f9aab..b5a282e1 100644
--- a/src/dynarec/rv64/dynarec_rv64_dd.c
+++ b/src/dynarec/rv64/dynarec_rv64_dd.c
@@ -68,7 +68,7 @@ uintptr_t dynarec64_DD(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
             break;
         case 0xD8:
             INST_NAME("FSTP ST0, ST0");
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
         case 0xD9:
         case 0xDA:
@@ -82,7 +82,7 @@ uintptr_t dynarec64_DD(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
             x87_get_st_empty(dyn, ninst, x1, x2, nextop&7, X87_ST(nextop&7));
             x87_get_st(dyn, ninst, x1, x2, 0, X87_ST0);
             x87_swapreg(dyn, ninst, x1, x2, 0, nextop&7);
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
         case 0xE0:
         case 0xE1:
@@ -137,7 +137,7 @@ uintptr_t dynarec64_DD(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
             switch((nextop>>3)&7) {
                 case 0:
                     INST_NAME("FLD double");
-                    v1 = x87_do_push(dyn, ninst, x1, EXT_CACHE_ST_D);
+                    X87_PUSH_OR_FAIL(v1, dyn, ninst, x1, EXT_CACHE_ST_D);
                     addr = geted(dyn, addr, ninst, nextop, &wback, x2, x1, &fixedaddress, rex, NULL, 1, 0);
                     FLD(v1, wback, fixedaddress);
                     break;
@@ -152,7 +152,7 @@ uintptr_t dynarec64_DD(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
                     v1 = x87_get_st(dyn, ninst, x1, x2, 0, EXT_CACHE_ST_D);
                     addr = geted(dyn, addr, ninst, nextop, &wback, x2, x1, &fixedaddress, rex, NULL, 1, 0);
                     FSD(v1, wback, fixedaddress);
-                    x87_do_pop(dyn, ninst, x3);
+                    X87_POP_OR_FAIL(dyn, ninst, x3);
                     break;
                 case 7:
                     INST_NAME("FNSTSW m2byte");
diff --git a/src/dynarec/rv64/dynarec_rv64_de.c b/src/dynarec/rv64/dynarec_rv64_de.c
index a2341b40..6712a97c 100644
--- a/src/dynarec/rv64/dynarec_rv64_de.c
+++ b/src/dynarec/rv64/dynarec_rv64_de.c
@@ -52,7 +52,7 @@ uintptr_t dynarec64_DE(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
             } else {
                 FADDD(v1, v1, v2);
             }
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
         case 0xC8:
         case 0xC9:
@@ -70,7 +70,7 @@ uintptr_t dynarec64_DE(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
             } else {
                 FMULD(v1, v1, v2);
             }
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
         case 0xD0:
         case 0xD1:
@@ -103,7 +103,7 @@ uintptr_t dynarec64_DE(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
             } else {
                 FSUBD(v1, v2, v1);
             }
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
         case 0xE8:
         case 0xE9:
@@ -121,7 +121,7 @@ uintptr_t dynarec64_DE(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
             } else {
                 FSUBD(v1, v1, v2);
             }
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
         case 0xF0:
         case 0xF1:
@@ -139,8 +139,8 @@ uintptr_t dynarec64_DE(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
             } else {
                 FDIVD(v1, v2, v1);
             }
-            x87_do_pop(dyn, ninst, x3);
-            break;       
+            X87_POP_OR_FAIL(dyn, ninst, x3);
+            break;
         case 0xF8:
         case 0xF9:
         case 0xFA:
@@ -157,7 +157,7 @@ uintptr_t dynarec64_DE(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
             } else {
                 FDIVD(v1, v1, v2);
             }
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
         case 0xD8:
         case 0xDA:
diff --git a/src/dynarec/rv64/dynarec_rv64_df.c b/src/dynarec/rv64/dynarec_rv64_df.c
index de99b02a..01d7b67a 100644
--- a/src/dynarec/rv64/dynarec_rv64_df.c
+++ b/src/dynarec/rv64/dynarec_rv64_df.c
@@ -103,7 +103,7 @@ uintptr_t dynarec64_DF(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
                     // end
                 }
             }
-            x87_do_pop(dyn, ninst, x3);
+            X87_POP_OR_FAIL(dyn, ninst, x3);
             break;
         case 0xC8 ... 0xDF:
         case 0xE1 ... 0xE7:
@@ -115,7 +115,7 @@ uintptr_t dynarec64_DF(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
             switch((nextop>>3)&7) {
                 case 0:
                     INST_NAME("FILD ST0, Ew");
-                    v1 = x87_do_push(dyn, ninst, x1, EXT_CACHE_ST_F);
+                    X87_PUSH_OR_FAIL(v1, dyn, ninst, x1, EXT_CACHE_ST_F);
                     addr = geted(dyn, addr, ninst, nextop, &wback, x3, x4, &fixedaddress, rex, NULL, 1, 0);
                     LH(x1, wback, fixedaddress);
                     if(ST_IS_F(0)) {
@@ -144,7 +144,7 @@ uintptr_t dynarec64_DF(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
                     }
                     MARK2;
                     SH(x4, wback, fixedaddress);
-                    x87_do_pop(dyn, ninst, x3);
+                    X87_POP_OR_FAIL(dyn, ninst, x3);
                     break;
                 case 3:
                     INST_NAME("FISTP Ew, ST0");
@@ -168,11 +168,11 @@ uintptr_t dynarec64_DF(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
                     }
                     MARK2;
                     SH(x4, wback, fixedaddress);
-                    x87_do_pop(dyn, ninst, x3);
+                    X87_POP_OR_FAIL(dyn, ninst, x3);
                     break;
                 case 5:
                     INST_NAME("FILD ST0, i64");
-                    v1 = x87_do_push(dyn, ninst, x1, EXT_CACHE_ST_D);
+                    X87_PUSH_OR_FAIL(v1, dyn, ninst, x1, EXT_CACHE_ST_D);
                     addr = geted(dyn, addr, ninst, nextop, &wback, x2, x3, &fixedaddress, rex, NULL, 1, 0);
                     LD(x1, wback, fixedaddress);
                     if (rex.is32bits) {
@@ -233,7 +233,7 @@ uintptr_t dynarec64_DF(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
                     SD(x4, wback, fixedaddress);
                     MARK3;
                     x87_restoreround(dyn, ninst, u8);
-                    x87_do_pop(dyn, ninst, x3);
+                    X87_POP_OR_FAIL(dyn, ninst, x3);
                     break;
                 default:
                     DEFAULT;
diff --git a/src/dynarec/rv64/dynarec_rv64_functions.c b/src/dynarec/rv64/dynarec_rv64_functions.c
index 541ac45f..f01c638b 100644
--- a/src/dynarec/rv64/dynarec_rv64_functions.c
+++ b/src/dynarec/rv64/dynarec_rv64_functions.c
@@ -58,7 +58,7 @@ void fpu_free_reg(dynarec_rv64_t* dyn, int reg)
     int idx = EXTIDX(reg);
     // TODO: check upper limit?
     dyn->e.fpuused[idx] = 0;
-    if(dyn->e.extcache[reg].t!=EXT_CACHE_ST_F && dyn->e.extcache[reg].t!=EXT_CACHE_ST_D)
+    if(dyn->e.extcache[idx].t!=EXT_CACHE_ST_F && dyn->e.extcache[idx].t!=EXT_CACHE_ST_D)
         dyn->e.extcache[idx].v = 0;
 }
 // Get an MMX double reg
@@ -494,7 +494,7 @@ const char* getCacheName(int t, int n)
 void inst_name_pass3(dynarec_native_t* dyn, int ninst, const char* name, rex_t rex)
 {
     static const char* fnames[] = {
-        "ft0"," ft1", "ft2", "ft3", "ft4", "ft5", "ft6", "ft7",
+        "ft0", "ft1", "ft2", "ft3", "ft4", "ft5", "ft6", "ft7",
         "fs0", "fs1",
         "fa0", "fa1", "fa2", "fa3", "fa4", "fa5", "fa6", "fa7",
         "fs2", "fs3", "fs4", "fs5", "fs6", "fs7", "fs8", "fs9", "fs10", "fs11",
@@ -561,4 +561,4 @@ void print_newinst(dynarec_native_t* dyn, int ninst)
         ninst, dyn->block, dyn->native_size,
         (box64_dynarec_dump>1)?"\e[m":""
         );
-}
\ No newline at end of file
+}
diff --git a/src/dynarec/rv64/dynarec_rv64_helper.c b/src/dynarec/rv64/dynarec_rv64_helper.c
index 294db0ee..ecb1bf55 100644
--- a/src/dynarec/rv64/dynarec_rv64_helper.c
+++ b/src/dynarec/rv64/dynarec_rv64_helper.c
@@ -1675,9 +1675,9 @@ static void swapCache(dynarec_rv64_t* dyn, int ninst, int i, int j, extcache_t *
     // SWAP
     ext_cache_t tmp;
     MESSAGE(LOG_DUMP, "\t  - Swapping %d <-> %d\n", i, j);
-    // There is no VSWP in Arm64 NEON to swap 2 register contents!
+    // There is no swap instruction in RV64 to swap 2 float registers!
     // so use a scratch...
-    #define SCRATCH 0
+    #define SCRATCH 2
     if(i_single)
         FMVS(SCRATCH, reg_i);
     else
diff --git a/src/dynarec/rv64/dynarec_rv64_helper.h b/src/dynarec/rv64/dynarec_rv64_helper.h
index 02bc5211..78a9cece 100644
--- a/src/dynarec/rv64/dynarec_rv64_helper.h
+++ b/src/dynarec/rv64/dynarec_rv64_helper.h
@@ -864,6 +864,28 @@
     SLLI(dst, dst, 11 - 5);             \
     OR(dst, dst, s1)
 
+#define X87_PUSH_OR_FAIL(var, dyn, ninst, scratch, t) \
+    if (dyn->e.stack == +8) {                         \
+        *ok = 0;                                      \
+        break;                                        \
+    }                                                 \
+    var = x87_do_push(dyn, ninst, scratch, t);
+
+#define X87_PUSH_EMPTY_OR_FAIL(dyn, ninst, scratch) \
+    if (dyn->e.stack == +8) {                       \
+        *ok = 0;                                    \
+        break;                                      \
+    }                                               \
+    x87_do_push_empty(dyn, ninst, scratch);
+
+#define X87_POP_OR_FAIL(dyn, ninst, scratch) \
+    if (dyn->e.stack == -8) {                \
+        *ok = 0;                             \
+        break;                               \
+    }                                        \
+    x87_do_pop(dyn, ninst, scratch);
+
+
 #ifndef MAYSETFLAGS
 #define MAYSETFLAGS()
 #endif