We are currently migrating Bugzilla to GitHub issues.
Any changes made to the bug tracker now will be lost, so please do not post new bugs or make changes to them.
When we're done, all bug URLs will redirect to their equivalent location on the new bug tracker.

Bug 3073 - SDL_OpenAudioDevice with NULL obtained variable behaves as though requested samples changes
Summary: SDL_OpenAudioDevice with NULL obtained variable behaves as though requested s...
Status: RESOLVED INVALID
Alias: None
Product: SDL
Classification: Unclassified
Component: audio (show other bugs)
Version: 2.0.3
Hardware: x86_64 Linux
: P2 normal
Assignee: Ryan C. Gordon
QA Contact: Sam Lantinga
URL:
Keywords:
Depends on:
Blocks:
 
Reported: 2015-07-25 03:29 UTC by Gabriel Marcano
Modified: 2015-07-28 04:29 UTC (History)
1 user (show)

See Also:


Attachments
main.c, Sample file showcasing issue (1012 bytes, text/x-c)
2015-07-25 03:29 UTC, Gabriel Marcano
Details

Note You need to log in before you can comment on or make changes to this bug.
Description Gabriel Marcano 2015-07-25 03:29:34 UTC
Created attachment 2228 [details]
main.c, Sample file showcasing issue

I am using libSDL2-2.0.3 on Gentoo Linux. While trying to play a simple square wave with SDL, I realized that for some reason the number of samples I was requesting in the wanted SDL_AudioSpec struct for SDL_OpenAudioDevice() was being cut in half without telling me, since the obtained pointer was set to NULL (the documentation states that SDL should convert things on its own in the background if conversion is needed).

Some more things I've noticed:

When the callback function was called by SDL, the length variable passed to it still stated the original buffer size I asked for, but when the sound plays back I did not hear a clean square wave. It was only when I modified my generation algorithm to only work on the first half of the buffer that the clean square wave worked.

I compiled SDL with debugging symbols and stepped though. I found that for opening a pulseaudio device (which is what I have), the samples get halved (in src/audio/pulseaudio/SDL_pulseaudio.c:413). Maybe this is related somehow? I tried commenting this out and recompiling SDL, but then the callback function was getting a length size of double my requested sample size, so there may be more code doing more doubling/halving elsewhere.

I'm attaching a simple program that exhibits the issue. The function generate_samples just generates the given number of samples for a 16 bit native byte ordering PCM square wave, and stores the samples in a global array. The function keeps track of the current position in the wave period, so that it can begin, when called again, where it left off. The function fill_audio is the callback registered with SDL. There are two generate_samples lines (one should be commented out). The one with just len shows the default SDL behavior, and the one with len/2 shows my workaround. The default behavior should cause for the square wave to sound, well, like crap. With my workaround (by only using the first half of the buffer), causes a nice square wave to sound.

I compiled the program using GCC-5.1 using C99. I can provide more information if necessary.
Comment 1 Gabriel Marcano 2015-07-28 04:29:33 UTC
It seems I misread the documentation. I assumed the length from the callback was the number of samples requested by SDL, but in reality it is the number of bytes in the buffer. In my case, each mono sample is actually of two bytes. After fixing my code to take this difference into account, sound works as it should. It still seems that the PulseAudio code cuts samples in half internally, but SDL behaves consistent with its documentation (again, the callback receives the number of bytes in the buffer instead of the number of samples).

I apologize for the noise. Keep up the good work!