From f5c022a8e4905a5fb8947f807d42eaeed6ad6f72 Mon Sep 17 00:00:00 2001 From: kub Date: Sat, 22 Jun 2024 23:12:31 +0200 Subject: [PATCH] core, revisit ym2612 busy flag implementation --- pico/memory.c | 13 ++++++++----- pico/pico_int.h | 11 +++++++---- pico/sound/ym2612.c | 8 +++++--- pico/sound/ym2612.h | 4 ++-- platform/gp2x/code940/940.c | 4 ++-- 5 files changed, 24 insertions(+), 16 deletions(-) diff --git a/pico/memory.c b/pico/memory.c index de5e3e5e..b1c917a1 100644 --- a/pico/memory.c +++ b/pico/memory.c @@ -1174,7 +1174,7 @@ static int ym2612_write_local(u32 a, u32 d, int is_from_z80) // the busy flag in the YM2612 status is actually a 32 cycle timer // (89.6 Z80 cycles), triggered by any write to the data port. - Pico.t.ym2612_busy = (cycles + 90) << 8; // Q8 for convenience + Pico.t.ym2612_busy = (cycles << 8) + YMBUSY_ZCYCLES; // Q8 for convenience switch (addr) { @@ -1284,9 +1284,11 @@ static u32 ym2612_read_local_68k(void) void ym2612_pack_state(void) { // timers are saved as tick counts, in 16.16 int format - int tac, tat = 0, tbc, tbt = 0; + int tac, tat = 0, tbc, tbt = 0, busy = 0; tac = 1024 - ym2612.OPN.ST.TA; tbc = 256 - ym2612.OPN.ST.TB; + if (Pico.t.ym2612_busy > 0) + busy = cycles_z80_to_68k(Pico.t.ym2612_busy); if (Pico.t.timer_a_next_oflow != TIMER_NO_OFLOW) tat = (int)((double)(Pico.t.timer_a_step - Pico.t.timer_a_next_oflow) / (double)Pico.t.timer_a_step * tac * 65536); @@ -1301,12 +1303,12 @@ void ym2612_pack_state(void) YM2612PicoStateSave2_940(tat, tbt); else #endif - YM2612PicoStateSave2(tat, tbt); + YM2612PicoStateSave2(tat, tbt, busy); } void ym2612_unpack_state(void) { - int i, ret, tac, tat, tbc, tbt; + int i, ret, tac, tat, tbc, tbt, busy = 0; YM2612PicoStateLoad(); // feed all the registers and update internal state @@ -1336,12 +1338,13 @@ void ym2612_unpack_state(void) ret = YM2612PicoStateLoad2_940(&tat, &tbt); else #endif - ret = YM2612PicoStateLoad2(&tat, &tbt); + ret = YM2612PicoStateLoad2(&tat, &tbt, &busy); if (ret != 0) { elprintf(EL_STATUS, "old ym2612 state"); return; // no saved timers } + Pico.t.ym2612_busy = cycles_68k_to_z80(busy); tac = (1024 - ym2612.OPN.ST.TA) << 16; tbc = (256 - ym2612.OPN.ST.TB) << 16; if (ym2612.OPN.ST.mode & 1) diff --git a/pico/pico_int.h b/pico/pico_int.h index 06f00c2f..79997d9b 100644 --- a/pico/pico_int.h +++ b/pico/pico_int.h @@ -209,6 +209,7 @@ extern struct DrZ80 drZ80; // 68k clock = OSC/7, z80 clock = OSC/15, 68k:z80 ratio = 7/15 = 3822.9/8192 #define cycles_68k_to_z80(x) ((x) * 3823 >> 13) +#define cycles_z80_to_68k(x) ((x) * 8777 >> 12) // ----------------------- SH2 CPU ----------------------- @@ -898,10 +899,12 @@ void ym2612_unpack_state(void); #define TIMER_NO_OFLOW 0x70000000 -// tA = 72 * (1024 - TA) / M, with M = mclock/2 -#define TIMER_A_TICK_ZCYCLES cycles_68k_to_z80(256LL* 72*2) // Q8 -// tB = 16*72 * ( 256 - TB) / M -#define TIMER_B_TICK_ZCYCLES cycles_68k_to_z80(256LL*16*72*2) // Q8 +// tA = 24*3 * (1024 - TA) / M, with M = mclock/2 +#define TIMER_A_TICK_ZCYCLES cycles_68k_to_z80(256LL* 24*3*2) // Q8 +// tB = 16*24*3 * ( 256 - TB) / M +#define TIMER_B_TICK_ZCYCLES cycles_68k_to_z80(256LL*16*24*3*2) // Q8 +// busy = 32*3 / M +#define YMBUSY_ZCYCLES cycles_68k_to_z80(256LL* 32*3*2) // Q8 #define timers_cycle(ticks) \ if (Pico.t.ym2612_busy > 0) \ diff --git a/pico/sound/ym2612.c b/pico/sound/ym2612.c index f0e60b42..ee84da23 100644 --- a/pico/sound/ym2612.c +++ b/pico/sound/ym2612.c @@ -2049,7 +2049,7 @@ typedef struct UINT32 eg_timer; UINT32 lfo_cnt; UINT16 lfo_ampm; - UINT16 unused2; + INT16 busy_timer; UINT32 keyon_field; // 20 UINT32 kcode_fc_sl3_3; UINT32 reserved[2]; @@ -2063,7 +2063,7 @@ typedef struct } ym_save_addon2; -void YM2612PicoStateSave2(int tat, int tbt) +void YM2612PicoStateSave2(int tat, int tbt, int busy) { ym_save_addon_slot ss; ym_save_addon2 sa2; @@ -2121,10 +2121,11 @@ void YM2612PicoStateSave2(int tat, int tbt) sa.eg_timer = ym2612.OPN.eg_timer; sa.lfo_cnt = ym2612.OPN.lfo_cnt; sa.lfo_ampm = g_lfo_ampm; + sa.busy_timer = busy; memcpy(ptr, &sa, sizeof(sa)); // 0x30 max } -int YM2612PicoStateLoad2(int *tat, int *tbt) +int YM2612PicoStateLoad2(int *tat, int *tbt, int *busy) { ym_save_addon_slot ss; ym_save_addon2 sa2; @@ -2150,6 +2151,7 @@ int YM2612PicoStateLoad2(int *tat, int *tbt) g_lfo_ampm = sa.lfo_ampm; if (tat != NULL) *tat = sa.TAT; if (tbt != NULL) *tbt = sa.TBT; + if (busy != NULL) *busy = sa.busy_timer; // chans 1,2,3 ptr = &ym2612.REGS[0x0b8]; diff --git a/pico/sound/ym2612.h b/pico/sound/ym2612.h index b981a428..56ec5ef9 100644 --- a/pico/sound/ym2612.h +++ b/pico/sound/ym2612.h @@ -177,8 +177,8 @@ int YM2612PicoTick_(int n); void YM2612PicoStateLoad_(void); void *YM2612GetRegs(void); -void YM2612PicoStateSave2(int tat, int tbt); -int YM2612PicoStateLoad2(int *tat, int *tbt); +void YM2612PicoStateSave2(int tat, int tbt, int busy); +int YM2612PicoStateLoad2(int *tat, int *tbt, int *busy); /* NB must be macros for compiling GP2X 940 code */ #ifndef __GP2X__ diff --git a/platform/gp2x/code940/940.c b/platform/gp2x/code940/940.c index 4ab8bad1..60be15c3 100644 --- a/platform/gp2x/code940/940.c +++ b/platform/gp2x/code940/940.c @@ -187,7 +187,7 @@ void Main940(void) break; case JOB940_PICOSTATESAVE2: - YM2612PicoStateSave2(0, 0); + YM2612PicoStateSave2(0, 0, 0); memcpy(shared_ctl->writebuff0, ym2612_940->REGS, 0x200); break; @@ -197,7 +197,7 @@ void Main940(void) case JOB940_PICOSTATELOAD2: memcpy(ym2612_940->REGS, shared_ctl->writebuff0, 0x200); - YM2612PicoStateLoad2(0, 0); + YM2612PicoStateLoad2(0, 0, 0); break; case JOB940_YM2612UPDATEONE: -- 2.39.5