diff --git a/source/ngc/ngc.c b/source/ngc/ngc.c index bf936a0..ae95ae8 100644 --- a/source/ngc/ngc.c +++ b/source/ngc/ngc.c @@ -113,7 +113,6 @@ void reloadrom () audio_init(48000); /* Audio System initialization */ ClearGGCodes (); /* Clear Game Genie patches */ system_reset (); /* System Power ON */ - ogc_audio__reset(); /* reset audio buffers */ } /*************************************************************************** @@ -132,8 +131,6 @@ int main (int argc, char *argv[]) DI_Init(); #endif - u16 usBetweenFrames; - long long now, prev; int RenderedFrameCount = 0; int FrameCount = 0; @@ -189,59 +186,29 @@ int main (int argc, char *argv[]) MainMenu(); ConfigRequested = 0; - /* Initialize Frame timings */ - frameticker = 0; - prev = gettime(); - /* Emulation Loop */ while (1) { + /* audio DMA starting point */ ogc_audio__start(); - /* Frame synchronization */ - if (gc_pal != vdp_pal) + if (frameticker > 1) { - /* use timers */ - usBetweenFrames = vdp_pal ? 20000 : 16666; - now = gettime(); - if (diff_usec(prev, now) > usBetweenFrames) - { - /* Frame skipping */ - prev = now; - system_frame(1); - } - else - { - /* Delay */ - while (diff_usec(prev, now) < usBetweenFrames) now = gettime(); - - /* Render Frame */ - prev = now; - system_frame(0); - RenderedFrameCount++; - } - } - else - { - /* use VSync */ - if (frameticker > 1) - { /* Frame skipping */ frameticker--; system_frame (1); - } - else - { - /* Delay */ - while (!frameticker) usleep(10); - - /* Render Frame */ - system_frame (0); - RenderedFrameCount++; - } - - frameticker--; } + else + { + /* Delay */ + while (!frameticker) usleep(10); + + /* Render Frame */ + system_frame (0); + RenderedFrameCount++; + } + + frameticker--; /* update video & audio */ ogc_audio__update(); @@ -268,7 +235,6 @@ int main (int argc, char *argv[]) /* reset frame timings */ frameticker = 0; - prev = gettime(); FrameCount = 0; RenderedFrameCount = 0; } diff --git a/source/ngc/ogc_audio.c b/source/ngc/ogc_audio.c index 84be0e8..7dc0843 100644 --- a/source/ngc/ogc_audio.c +++ b/source/ngc/ogc_audio.c @@ -24,59 +24,55 @@ #include "shared.h" /* global datas */ -unsigned char soundbuffer[16][3840] ATTRIBUTE_ALIGN(32); -int mixbuffer = 0; +unsigned char soundbuffer[2][3840] ATTRIBUTE_ALIGN(32); +u8 mixbuffer = 0; -static int playbuffer = 0; -static int IsPlaying = 0; -static u32 dma_len = 3200; +static int IsPlaying = 0; +static int dma_len = 3200; -/*** AudioSwitchBuffers +/*** AudioDmaCallback Genesis Plus only provides sound data on completion of each frame. - To try to make the audio less choppy, this function is called from both the - DMA completion and update_audio. - Testing for data in the buffer ensures that there are no clashes. + To try to make the audio less choppy, we synchronize emulation with audio DMA + This ensure we only update audio framebuffer when DMA is finished ***/ -static void AudioSwitchBuffers() +static void AudioDmaCallback() { - /* increment soundbuffers index */ - playbuffer++; - playbuffer &= 0xf; - - /* reset audio DMA parameters */ - AUDIO_InitDMA((u32) soundbuffer[playbuffer], dma_len); + frameticker++; } void ogc_audio__init(void) { AUDIO_Init (NULL); AUDIO_SetDSPSampleRate (AI_SAMPLERATE_48KHZ); - // AUDIO_RegisterDMACallback (AudioSwitchBuffers); -} - -void ogc_audio__reset(void) -{ - IsPlaying = 0; + AUDIO_RegisterDMACallback (AudioDmaCallback); mixbuffer = 0; - playbuffer = 0; - memset(soundbuffer, 0, 16 * 3840); + memset(soundbuffer, 0, 2 * 3840); } void ogc_audio__update(void) { + /* buffer size */ + uint32 dma_len = vdp_pal ? 3840 : 3200; + + /* update DMA settings (this will only be taken in account when current DMA finishes) */ + AUDIO_InitDMA((u32) soundbuffer[mixbuffer], dma_len); + /* flush data from CPU cache */ DCFlushRange(soundbuffer[mixbuffer], dma_len); - AUDIO_InitDMA((u32) soundbuffer[mixbuffer], dma_len); + + /* switch buffer */ + mixbuffer ^= 1; } void ogc_audio__stop(void) { /* stop audio DMA */ AUDIO_StopDMA (); - AUDIO_InitDMA((u32) soundbuffer[0], dma_len); IsPlaying = 0; + + /* reset audio buffers */ mixbuffer = 0; - playbuffer = 0; + memset(soundbuffer, 0, 2 * 3840); } void ogc_audio__start(void) @@ -86,8 +82,8 @@ void ogc_audio__start(void) /* buffer size */ dma_len = vdp_pal ? 3840 : 3200; - /* set default DMA parameters */ - AUDIO_InitDMA((u32) soundbuffer[0], dma_len); + /* set first DMA parameters */ + AUDIO_InitDMA((u32) soundbuffer[1], dma_len); /* start audio DMA */ AUDIO_StartDMA(); diff --git a/source/ngc/ogc_audio.h b/source/ngc/ogc_audio.h index d75e421..2c7575f 100644 --- a/source/ngc/ogc_audio.h +++ b/source/ngc/ogc_audio.h @@ -24,11 +24,10 @@ #ifndef _GC_AUDIO_H_ #define _GC_AUDIO_H_ -extern u8 soundbuffer[16][3840]; -extern int mixbuffer; +extern u8 soundbuffer[2][3840]; +extern u8 mixbuffer; extern void ogc_audio__init(void); -extern void ogc_audio__reset(void); extern void ogc_audio__stop(void); extern void ogc_audio__start(void); extern void ogc_audio__update(void); diff --git a/source/ngc/ogc_video.c b/source/ngc/ogc_video.c index 2f1f957..7bc31be 100644 --- a/source/ngc/ogc_video.c +++ b/source/ngc/ogc_video.c @@ -346,13 +346,6 @@ static inline void draw_square (void) GX_End (); } -/* retrace handler */ -static void framestart(u32 retraceCnt) -{ - /* simply increment the tick counter */ - frameticker++; -} - /* Initialize GX */ static void gxStart(void) { @@ -725,9 +718,6 @@ void ogc_video__init(void) /* Set the framebuffer to be displayed at next VBlank */ VIDEO_SetNextFramebuffer (xfb[0]); - /* Register Video Retrace handlers */ - VIDEO_SetPreRetraceCallback(framestart); - /* Enable Video Interface */ VIDEO_SetBlack (FALSE); diff --git a/source/sound/sound.c b/source/sound/sound.c index b30ee36..56cca23 100644 --- a/source/sound/sound.c +++ b/source/sound/sound.c @@ -61,7 +61,7 @@ static inline uint32 psg_sample_cnt(uint8 is_z80) /* update FM samples */ static inline void fm_update() { - if(snd.fm.curStage - snd.fm.lastStage > 0) + if(snd.fm.curStage - snd.fm.lastStage > 1) { int *tempBuffer[2]; @@ -84,7 +84,7 @@ static inline void fm_update() /* update PSG samples */ static inline void psg_update() { - if(snd.psg.curStage - snd.psg.lastStage > 0) + if(snd.psg.curStage - snd.psg.lastStage > 1) { int16 *tempBuffer = snd.psg.buffer + snd.psg.lastStage; SN76489_Update (0, tempBuffer, snd.psg.curStage - snd.psg.lastStage); @@ -221,11 +221,8 @@ void fm_restore(void) /* write FM chip */ void fm_write(unsigned int cpu, unsigned int address, unsigned int data) { - if (address & 1) - { - snd.fm.curStage = fm_sample_cnt(cpu); - fm_update(); - } + snd.fm.curStage = fm_sample_cnt(cpu); + fm_update(); _YM2612_Write(address & 3, data); }