From 04c89959f817436b6fd983f9db88b45e28776003 Mon Sep 17 00:00:00 2001 From: linear cannon Date: Sat, 29 Jan 2022 07:27:45 -0800 Subject: [PATCH] adjust CLOCK_CYCLES and related macros to handle fpu/iu concurrency add CLOCK_CYCLES_FPU, which does exactly what CLOCK_CYCLES already did. add CONCURRENCY_CYCLES, which sets fpu_cycles, which is the number of available concurrent execution cycles that the integer unit can do "free" work in while the fpu is executing. adjust CLOCK_CYCLES so that if there are fpu_cycles, the cycle count is subtracted from fpu_cycles instead of cycles, emulating the behavior of these concurrent cycles being "free" as on real hardware. --- src/cpu/386.c | 15 ++++++++++++++- src/cpu/386_dynarec.c | 15 ++++++++++++++- src/cpu/386_dynarec_ops.c | 2 ++ src/cpu/808x.c | 23 ++++++++++++++++++++++- 4 files changed, 52 insertions(+), 3 deletions(-) diff --git a/src/cpu/386.c b/src/cpu/386.c index 298cc66fc..2358fd646 100644 --- a/src/cpu/386.c +++ b/src/cpu/386.c @@ -81,7 +81,20 @@ x386_log(const char *fmt, ...) #define OP_TABLE(name) ops_ ## name -#define CLOCK_CYCLES(c) cycles -= (c) +#define CLOCK_CYCLES(c) \ + {\ + if (fpu_cycles > 0) {\ + fpu_cycles -= (c);\ + if (fpu_cycles < 0) {\ + cycles += fpu_cycles;\ + }\ + } else {\ + cycles -= (c);\ + }\ + } + +#define CLOCK_CYCLES_FPU(c) cycles -= (c) +#define CONCURRENCY_CYCLES(c) fpu_cycles = (c) #define CLOCK_CYCLES_ALWAYS(c) cycles -= (c) #include "x86_ops.h" diff --git a/src/cpu/386_dynarec.c b/src/cpu/386_dynarec.c index d11be000e..88a95637c 100644 --- a/src/cpu/386_dynarec.c +++ b/src/cpu/386_dynarec.c @@ -267,9 +267,22 @@ static void prefetch_flush() #define OP_TABLE(name) ops_ ## name -#define CLOCK_CYCLES(c) cycles -= (c) +#define CLOCK_CYCLES(c) \ + {\ + if (fpu_cycles > 0) {\ + fpu_cycles -= (c);\ + if (fpu_cycles < 0) {\ + cycles += fpu_cycles;\ + }\ + } else {\ + cycles -= (c);\ + }\ + } +#define CLOCK_CYCLES_FPU(c) cycles -= (c) +#define CONCURRENCY_CYCLES(c) fpu_cycles = (c) #define CLOCK_CYCLES_ALWAYS(c) cycles -= (c) + #include "386_ops.h" diff --git a/src/cpu/386_dynarec_ops.c b/src/cpu/386_dynarec_ops.c index ef18c2558..40aa2db80 100644 --- a/src/cpu/386_dynarec_ops.c +++ b/src/cpu/386_dynarec_ops.c @@ -65,6 +65,8 @@ static __inline void fetch_ea_16_long(uint32_t rmdat) #define OP_TABLE(name) dynarec_ops_ ## name #define CLOCK_CYCLES(c) +#define CLOCK_CYCLES_FPU(c) +#define CONCURRENCY_CYCLES(c) fpu_cycles = (c) #define CLOCK_CYCLES_ALWAYS(c) cycles -= (c) #include "386_ops.h" diff --git a/src/cpu/808x.c b/src/cpu/808x.c index 750335b60..827ec5b1c 100644 --- a/src/cpu/808x.c +++ b/src/cpu/808x.c @@ -89,11 +89,32 @@ static int refresh = 0, cycdiff; wait(val, 0); \ } -#define CLOCK_CYCLES(val) \ +#define CLOCK_CYCLES_ALWAYS(val) \ { \ wait(val, 0); \ } +#define CLOCK_CYCLES_FPU(val) \ + { \ + wait(val, 0); \ + } + + +#define CLOCK_CYCLES(val) \ + { \ + if (fpu_cycles > 0) { \ + fpu_cycles -= (val); \ + if (fpu_cycles < 0) { \ + wait(val, 0); \ + } \ + } else { \ + wait(val, 0); \ + } \ + } + +#define CONCURRENCY_CYCLES(c) fpu_cycles = (c) + + typedef int (*OpFn)(uint32_t fetchdat);