[SDL] SDL sound under Mac OS X and Linux

Darrell Walisser walisser at mac.com
Sat Nov 23 06:24:01 PST 2002


On Saturday, November 23, 2002, at 06:03  AM, Fredrick Meunier wrote:

> Hi Darell,
>
> Darrell Walisser wrote:
>> On Thursday, November 21, 2002, at 04:06  PM, Fredrick Meunier wrote:
>>> 1) I write unsigned 8 bit samples to my sound card (padded to 16bit 
>>> if that's all that is available). Using OSS to output the samples 
>>> sounds fine, but using SDL under Linux or OS X sounds clipped when I 
>>> am outputting maximum volume (maximum value=128 +- 124). Is this a 
>>> known problem with SDL sound output, should I be reducing the max 
>>> amplitude of my samples?
>> I've also noticed this in the past. I'm not sure what the cause is. 
>> It might be a bug in mixing of 8 bit samples, or conversion of 8 bit 
>> to 16 bit samples. Does initializing SDL with 16 bit samples and 
>> converting your samples to 16 bit yourself fix the problem?
>
> No, converting the samples to 16 bit myself still leaves the (loudest) 
> samples sounding distorted (Linux and Mac OS X), and sounding perfect 
> on Linux using OSS.
>
>> This is pure speculation, but I think it's possible that after SDL 
>> hands off the samples they are processed again by the sound daemon 
>> (or entity that controls the system sound volume) and at that point 
>> there might be some distortion. In this case, using a sound format 
>> that mirrors the hardware/OS setting might solve the problem.
>
> I'll try a few different combinations and see if it helps.
>
>>> 2) I generate 1/50th of a second of audio at a time and write it to 
>>> a ring buffer, the SDL callback then reads the data writes it to the 
>>> sound card. Under Linux this works well, CPU usage is low and there 
>>> are practically no sound glitches. The same code on Mac OS X mostly 
>>> works, but if there is any movement in other windows the sound from 
>>> my app glitches. If I minimise my app or go fullscreen the glitches 
>>> dissapear. Is anyone else seeing this and are there any suggestions 
>>> about fixing the problem?
>
>> I've heard of this before. It might be because when you drag the 
>> application window (I presume dragging other application windows 
>> doesn't have this problem), the main thread is blocked temporarily (I 
>> don't really know why it would be, though). If you are using 
>> SDL_LockAudio() and copying to the ring buffer in the main thread, 
>> you might have breakups if your audio buffers are too small. See if 
>> using a larger audio buffer decreases this effect.
>
> Dragging any window or having the dock pop up will cause glitching.
> I think the main thread is not so much blocked from running as starved 
> of CPU as the demands of the window system or other programs 
> increases. I guess there are two fixes:
> 1) Make my program less CPU-hungry
> 2) Make the emulator run with real-time priority? Is there a real-time 
> scheduling priority available on Mac OS X?
>
> I get much higher CPU load than I would get on Linux (Linux 6% CPU, 
> Mac OS X 25-50% CPU as reported by top).
>
> I think that the remaining glitching is mostly caused by my graphics 
> routines not being as fast as they could be.
>
> I create my video mode attempting to match the users display like this:
>
> vidinfo = SDL_GetVideoInfo();
> gc = SDL_SetVideoMode( width, height, vidinfo->vfmt->BitsPerPixel, 
> SDL_HWSURFACE|SDL_ANYFORMAT|SDL_RESIZABLE );
>
> I have an offscreen surface that I create with:
>
> image = SDL_CreateRGBSurface( SDL_SWSURFACE, width, height, 
> gc->format->BitsPerPixel, gc->format->Rmask, gc->format->Gmask, 
> gc->format->Bmask, gc->format->Amask );
>
> That I draw to on a pixel basis every frame. I blit the relevant 
> changed areas from this image to the screen with:
>
> SDL_BlitSurface( image, &updated_rects[num_rects], gc, 
> &updated_rects[num_rects] );
>
> (as I am emulating the sweep of the video beam over the screen of the 
> emulated hardware there are changes in the image that should not show 
> up on screen until the next frame). I keep track of the areas dirtied 
> and then do a single call to SDL_UpdateRects every frame. This seems 
> plenty fast on Linux, but is there a better way to do it on Mac OS X?

There is a better way. Don't use SDL_HWSURFACE, and don't create an 
additional software buffer of the same size as the screen. Mac OS X 
doesn't support a hardware screen surface in windowed mode, and windows 
in Mac OS X are already double-buffered (note: this doesn't mean you 
should use SDL_Flip(), that's why SDL_DOUBLEBUF isn't set on the 
surface).

In fullscreen mode Mac OS X uses a hardware, single-buffered surface. 
But you would be better off to use a software surface, as it will 
likely be faster.





More information about the SDL mailing list