diff options
Diffstat (limited to 'opl/opl_sdl.c')
-rw-r--r-- | opl/opl_sdl.c | 31 |
1 files changed, 17 insertions, 14 deletions
diff --git a/opl/opl_sdl.c b/opl/opl_sdl.c index 3ed7f784..fa9f047a 100644 --- a/opl/opl_sdl.c +++ b/opl/opl_sdl.c @@ -39,7 +39,7 @@ typedef struct unsigned int rate; // Number of times the timer is advanced per sec. unsigned int enabled; // Non-zero if timer is enabled. unsigned int value; // Last value that was set. - unsigned int expire_time; // Calculated time that timer will expire. + uint64_t expire_time; // Calculated time that timer will expire. } opl_timer_t; // When the callback mutex is locked using OPL_Lock, callback functions @@ -55,18 +55,18 @@ static opl_callback_queue_t *callback_queue; static SDL_mutex *callback_queue_mutex = NULL; -// Current time, in number of samples since startup: +// Current time, in us since startup: -static int current_time; +static uint64_t current_time; // If non-zero, playback is currently paused. static int opl_sdl_paused; -// Time offset (in samples) due to the fact that callbacks +// Time offset (in us) due to the fact that callbacks // were previously paused. -static unsigned int pause_offset; +static uint64_t pause_offset; // OPL software emulator structure. @@ -106,20 +106,22 @@ static void AdvanceTime(unsigned int nsamples) { opl_callback_t callback; void *callback_data; + uint64_t us; SDL_LockMutex(callback_queue_mutex); // Advance time. - current_time += nsamples; + us = ((uint64_t) nsamples * OPL_SECOND) / mixing_freq; + current_time += us; if (opl_sdl_paused) { - pause_offset += nsamples; + pause_offset += us; } // Are there callbacks to invoke now? Keep invoking them - // until there are none more left. + // until there are no more left. while (!OPL_Queue_IsEmpty(callback_queue) && current_time >= OPL_Queue_Peek(callback_queue) + pause_offset) @@ -193,8 +195,8 @@ static void OPL_Mix_Callback(void *udata, while (filled < buffer_len) { - unsigned int next_callback_time; - unsigned int nsamples; + uint64_t next_callback_time; + uint64_t nsamples; SDL_LockMutex(callback_queue_mutex); @@ -210,7 +212,8 @@ static void OPL_Mix_Callback(void *udata, { next_callback_time = OPL_Queue_Peek(callback_queue) + pause_offset; - nsamples = next_callback_time - current_time; + nsamples = (next_callback_time - current_time) * mixing_freq; + nsamples = (nsamples + OPL_SECOND - 1) / OPL_SECOND; if (nsamples > buffer_len - filled) { @@ -395,7 +398,7 @@ static void OPLTimer_CalculateEndTime(opl_timer_t *timer) { tics = 0x100 - timer->value; timer->expire_time = current_time - + (tics * opl_sample_rate) / timer->rate; + + ((uint64_t) tics * OPL_SECOND) / timer->rate; } } @@ -454,13 +457,13 @@ static void OPL_SDL_PortWrite(opl_port_t port, unsigned int value) } } -static void OPL_SDL_SetCallback(unsigned int ms, +static void OPL_SDL_SetCallback(unsigned int us, opl_callback_t callback, void *data) { SDL_LockMutex(callback_queue_mutex); OPL_Queue_Push(callback_queue, callback, data, - current_time - pause_offset + (ms * mixing_freq) / 1000); + current_time - pause_offset + us); SDL_UnlockMutex(callback_queue_mutex); } |