Commit 957de48d authored by David Reid's avatar David Reid

Another potential fix for some full-duplex glitching.

This change makes it so reading and writing is done on the smaller of
the period sizes between capture and playback devices.
parent 997d8a8d
...@@ -9216,8 +9216,9 @@ mal_result mal_device_map_next_playback_buffer__dsound(mal_device* pDevice) ...@@ -9216,8 +9216,9 @@ mal_result mal_device_map_next_playback_buffer__dsound(mal_device* pDevice)
{ {
DWORD periodSizeInBytes = (pDevice->playback.internalBufferSizeInFrames / pDevice->playback.internalPeriods) * mal_get_bytes_per_frame(pDevice->playback.internalFormat, pDevice->playback.internalChannels); DWORD periodSizeInBytes = (pDevice->playback.internalBufferSizeInFrames / pDevice->playback.internalPeriods) * mal_get_bytes_per_frame(pDevice->playback.internalFormat, pDevice->playback.internalChannels);
DWORD lockOffset = (pDevice->dsound.iNextPeriodPlayback * periodSizeInBytes); DWORD lockOffset = (pDevice->dsound.iNextPeriodPlayback * periodSizeInBytes);
DWORD lockSizeInBytes = periodSizeInBytes;
DWORD mappedSizeInBytes; DWORD mappedSizeInBytes;
HRESULT hr = mal_IDirectSoundBuffer_Lock((mal_IDirectSoundBuffer*)pDevice->dsound.pPlaybackBuffer, lockOffset, periodSizeInBytes, &pDevice->dsound.pMappedBufferPlayback, &mappedSizeInBytes, NULL, NULL, 0); HRESULT hr = mal_IDirectSoundBuffer_Lock((mal_IDirectSoundBuffer*)pDevice->dsound.pPlaybackBuffer, lockOffset, lockSizeInBytes, &pDevice->dsound.pMappedBufferPlayback, &mappedSizeInBytes, NULL, NULL, 0);
if (FAILED(hr)) { if (FAILED(hr)) {
return mal_post_error(pDevice, MAL_LOG_LEVEL_ERROR, "[DirectSound] Failed to map buffer from playback device in preparation for writing to the device.", MAL_FAILED_TO_MAP_DEVICE_BUFFER); return mal_post_error(pDevice, MAL_LOG_LEVEL_ERROR, "[DirectSound] Failed to map buffer from playback device in preparation for writing to the device.", MAL_FAILED_TO_MAP_DEVICE_BUFFER);
} }
...@@ -9225,6 +9226,8 @@ mal_result mal_device_map_next_playback_buffer__dsound(mal_device* pDevice) ...@@ -9225,6 +9226,8 @@ mal_result mal_device_map_next_playback_buffer__dsound(mal_device* pDevice)
pDevice->dsound.mappedBufferFramesCapacityPlayback = (mal_uint32)mappedSizeInBytes / mal_get_bytes_per_frame(pDevice->playback.internalFormat, pDevice->playback.internalChannels); pDevice->dsound.mappedBufferFramesCapacityPlayback = (mal_uint32)mappedSizeInBytes / mal_get_bytes_per_frame(pDevice->playback.internalFormat, pDevice->playback.internalChannels);
pDevice->dsound.mappedBufferFramesRemainingPlayback = (mal_uint32)mappedSizeInBytes / mal_get_bytes_per_frame(pDevice->playback.internalFormat, pDevice->playback.internalChannels); pDevice->dsound.mappedBufferFramesRemainingPlayback = (mal_uint32)mappedSizeInBytes / mal_get_bytes_per_frame(pDevice->playback.internalFormat, pDevice->playback.internalChannels);
//printf("TRACE 1: Playback: iNextPeriod=%d, internalBufferSizeInFrames=%d, periodSizeInBytes=%d, mappedSizeInBytes=%d\n", pDevice->dsound.iNextPeriodPlayback, pDevice->playback.internalBufferSizeInFrames, periodSizeInBytes, mappedSizeInBytes);
return MAL_SUCCESS; return MAL_SUCCESS;
} }
...@@ -9346,8 +9349,9 @@ mal_result mal_device_map_next_capture_buffer__dsound(mal_device* pDevice) ...@@ -9346,8 +9349,9 @@ mal_result mal_device_map_next_capture_buffer__dsound(mal_device* pDevice)
{ {
DWORD periodSizeInBytes = (pDevice->capture.internalBufferSizeInFrames / pDevice->capture.internalPeriods) * mal_get_bytes_per_frame(pDevice->capture.internalFormat, pDevice->capture.internalChannels); DWORD periodSizeInBytes = (pDevice->capture.internalBufferSizeInFrames / pDevice->capture.internalPeriods) * mal_get_bytes_per_frame(pDevice->capture.internalFormat, pDevice->capture.internalChannels);
DWORD lockOffset = (pDevice->dsound.iNextPeriodCapture * periodSizeInBytes); DWORD lockOffset = (pDevice->dsound.iNextPeriodCapture * periodSizeInBytes);
DWORD lockSizeInBytes = periodSizeInBytes;
DWORD mappedSizeInBytes; DWORD mappedSizeInBytes;
HRESULT hr = mal_IDirectSoundCaptureBuffer_Lock((mal_IDirectSoundCaptureBuffer*)pDevice->dsound.pCaptureBuffer, lockOffset, periodSizeInBytes, &pDevice->dsound.pMappedBufferCapture, &mappedSizeInBytes, NULL, NULL, 0); HRESULT hr = mal_IDirectSoundCaptureBuffer_Lock((mal_IDirectSoundCaptureBuffer*)pDevice->dsound.pCaptureBuffer, lockOffset, lockSizeInBytes, &pDevice->dsound.pMappedBufferCapture, &mappedSizeInBytes, NULL, NULL, 0);
if (FAILED(hr)) { if (FAILED(hr)) {
return mal_post_error(pDevice, MAL_LOG_LEVEL_ERROR, "[DirectSound] Failed to map buffer from capture device in preparation for writing to the device.", MAL_FAILED_TO_MAP_DEVICE_BUFFER); return mal_post_error(pDevice, MAL_LOG_LEVEL_ERROR, "[DirectSound] Failed to map buffer from capture device in preparation for writing to the device.", MAL_FAILED_TO_MAP_DEVICE_BUFFER);
} }
...@@ -9355,6 +9359,8 @@ mal_result mal_device_map_next_capture_buffer__dsound(mal_device* pDevice) ...@@ -9355,6 +9359,8 @@ mal_result mal_device_map_next_capture_buffer__dsound(mal_device* pDevice)
pDevice->dsound.mappedBufferFramesCapacityCapture = (mal_uint32)mappedSizeInBytes / mal_get_bytes_per_frame(pDevice->capture.internalFormat, pDevice->capture.internalChannels); pDevice->dsound.mappedBufferFramesCapacityCapture = (mal_uint32)mappedSizeInBytes / mal_get_bytes_per_frame(pDevice->capture.internalFormat, pDevice->capture.internalChannels);
pDevice->dsound.mappedBufferFramesRemainingCapture = (mal_uint32)mappedSizeInBytes / mal_get_bytes_per_frame(pDevice->capture.internalFormat, pDevice->capture.internalChannels); pDevice->dsound.mappedBufferFramesRemainingCapture = (mal_uint32)mappedSizeInBytes / mal_get_bytes_per_frame(pDevice->capture.internalFormat, pDevice->capture.internalChannels);
//printf("TRACE 1: Capture: internalBufferSizeInFrames=%d, periodSizeInBytes=%d, mappedSizeInBytes=%d\n", pDevice->capture.internalBufferSizeInFrames, periodSizeInBytes, mappedSizeInBytes);
return MAL_SUCCESS; return MAL_SUCCESS;
} }
...@@ -21805,12 +21811,19 @@ mal_thread_result MAL_THREADCALL mal_worker_thread(void* pData) ...@@ -21805,12 +21811,19 @@ mal_thread_result MAL_THREADCALL mal_worker_thread(void* pData)
); );
mal_uint32 periodSizeInFrames; mal_uint32 periodSizeInFrames;
if (pDevice->type == mal_device_type_capture || pDevice->type == mal_device_type_duplex) { if (pDevice->type == mal_device_type_capture) {
mal_assert(pDevice->capture.internalBufferSizeInFrames >= pDevice->capture.internalPeriods); mal_assert(pDevice->capture.internalBufferSizeInFrames >= pDevice->capture.internalPeriods);
periodSizeInFrames = pDevice->capture.internalBufferSizeInFrames / pDevice->capture.internalPeriods; periodSizeInFrames = pDevice->capture.internalBufferSizeInFrames / pDevice->capture.internalPeriods;
} else { } else if (pDevice->type == mal_device_type_playback) {
mal_assert(pDevice->playback.internalBufferSizeInFrames >= pDevice->playback.internalPeriods); mal_assert(pDevice->playback.internalBufferSizeInFrames >= pDevice->playback.internalPeriods);
periodSizeInFrames = pDevice->playback.internalBufferSizeInFrames / pDevice->playback.internalPeriods; periodSizeInFrames = pDevice->playback.internalBufferSizeInFrames / pDevice->playback.internalPeriods;
} else {
mal_assert(pDevice->capture.internalBufferSizeInFrames >= pDevice->capture.internalPeriods);
mal_assert(pDevice->playback.internalBufferSizeInFrames >= pDevice->playback.internalPeriods);
periodSizeInFrames = mal_min(
pDevice->capture.internalBufferSizeInFrames / pDevice->capture.internalPeriods,
pDevice->playback.internalBufferSizeInFrames / pDevice->playback.internalPeriods
);
} }
...@@ -31,7 +31,7 @@ void data_callback(mal_device* pDevice, void* pOutput, const void* pInput, mal_u ...@@ -31,7 +31,7 @@ void data_callback(mal_device* pDevice, void* pOutput, const void* pInput, mal_u
/* In this test the format and channel count are the same for both input and output which means we can just memcpy(). */ /* In this test the format and channel count are the same for both input and output which means we can just memcpy(). */
mal_copy_memory(pOutput, pInput, frameCount * mal_get_bytes_per_frame(pDevice->capture.format, pDevice->capture.channels)); mal_copy_memory(pOutput, pInput, frameCount * mal_get_bytes_per_frame(pDevice->capture.format, pDevice->capture.channels));
#if 0 #if 1
/* Also write to a wav file for debugging. */ /* Also write to a wav file for debugging. */
drwav* pWav = (drwav*)pDevice->pUserData; drwav* pWav = (drwav*)pDevice->pUserData;
mal_assert(pWav != NULL); mal_assert(pWav != NULL);
...@@ -44,7 +44,7 @@ int main(int argc, char** argv) ...@@ -44,7 +44,7 @@ int main(int argc, char** argv)
{ {
mal_result result; mal_result result;
#if 0 #if 1
drwav_data_format wavFormat; drwav_data_format wavFormat;
wavFormat.container = drwav_container_riff; wavFormat.container = drwav_container_riff;
wavFormat.format = DR_WAVE_FORMAT_PCM; wavFormat.format = DR_WAVE_FORMAT_PCM;
...@@ -60,7 +60,7 @@ int main(int argc, char** argv) ...@@ -60,7 +60,7 @@ int main(int argc, char** argv)
#endif #endif
mal_backend backend = mal_backend_wasapi; mal_backend backend = mal_backend_dsound;
mal_context_config contextConfig = mal_context_config_init(); mal_context_config contextConfig = mal_context_config_init();
contextConfig.logCallback = log_callback; contextConfig.logCallback = log_callback;
...@@ -81,11 +81,12 @@ int main(int argc, char** argv) ...@@ -81,11 +81,12 @@ int main(int argc, char** argv)
deviceConfig.playback.channels = 2; deviceConfig.playback.channels = 2;
deviceConfig.playback.shareMode = mal_share_mode_shared; deviceConfig.playback.shareMode = mal_share_mode_shared;
deviceConfig.sampleRate = 44100; deviceConfig.sampleRate = 44100;
deviceConfig.bufferSizeInMilliseconds = 100; //deviceConfig.bufferSizeInMilliseconds = 60;
deviceConfig.periods = 2; deviceConfig.bufferSizeInFrames = 4096;
//deviceConfig.periods = 3;
deviceConfig.dataCallback = data_callback; deviceConfig.dataCallback = data_callback;
deviceConfig.stopCallback = stop_callback; deviceConfig.stopCallback = stop_callback;
deviceConfig.pUserData = NULL/*&wav*/; deviceConfig.pUserData = &wav;
mal_device device; mal_device device;
result = mal_device_init(&context, &deviceConfig, &device); result = mal_device_init(&context, &deviceConfig, &device);
...@@ -107,7 +108,7 @@ int main(int argc, char** argv) ...@@ -107,7 +108,7 @@ int main(int argc, char** argv)
#endif #endif
mal_device_uninit(&device); mal_device_uninit(&device);
/*drwav_uninit(&wav);*/ drwav_uninit(&wav);
(void)argc; (void)argc;
(void)argv; (void)argv;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment