/contrib/sdk/sources/SDL-1.2.2_newlib/src/audio/SDL_kolibri_audio.c |
---|
0,0 → 1,297 |
#include "SDL_audio.h" |
#include <menuet/os.h> |
#include <stdlib.h> |
#include <string.h> |
#include <sound.h> |
#include <stdio.h> |
static void GetNotify(__u32* event) |
{ |
__asm__("int $0x40" :: "a"(68),"b"(14),"c"(event)); |
} |
static int CreateThread(void* fn, char* p_stack) |
{ |
int res; |
__asm__("int $0x40" : "=a"(res) : "a"(51),"b"(1),"c"(fn),"d"(p_stack)); |
return res; |
} |
static char pinfo[1024]; |
static int GetProcessInfo(int slot) |
{ |
int res; |
__asm__("int $0x40" : "=a"(res) : "a"(9),"b"(pinfo),"c"(slot)); |
return res; |
} |
static void ActivateWnd(int slot) |
{ |
__asm__("int $0x40" :: "a"(18),"b"(3),"c"(slot)); |
} |
static void Yield(void) |
{ |
__asm__("int $0x40" :: "a"(68),"b"(1)); |
} |
static int bInitialized=0; |
static SNDBUF hBuff=0; |
static char* data=NULL; |
static int audio_tid=0; |
static int main_slot; |
static __u32 main_tid; |
static char audio_thread_stack[40960]; |
static __u32 used_format=0; |
static volatile int mix_size=0; |
static void (*callback)(void* userdata, Uint8* stream, int len); |
static void* userdata; |
int SDL_AudioInit(const char* driver_name) |
{ |
if (bInitialized) |
{ |
SDL_SetError("audio already initialized"); |
return -1; |
} |
int ver; |
if (InitSound(&ver)) |
{ |
SDL_printf("Warning: cannot load drivers, sound output will be disabled\n"); |
return 0; |
} |
bInitialized = 1; |
return 0; |
} |
void SDL_AudioQuit(void) |
{ |
} |
char* SDL_AudioDriverName(char* namebuf, int maxlen) |
{ |
if (!bInitialized) |
return NULL; |
strncpy(namebuf,"KolibriAudio",maxlen); |
return namebuf; |
} |
#define AUDIO_SUSPEND 1 |
#define AUDIO_RESUME 2 |
#define AUDIO_DIE 3 |
static volatile int audio_command=0,audio_response=0,bLocked=0,bInCallback=0; |
static void audio_thread(void) |
{ |
SDL_printf("audio_thread created\n"); |
int bPaused; |
__u32 event[6]; |
// initialize |
if (CreateBuffer(used_format|PCM_RING, 0, &hBuff)) |
{ |
audio_response=1; |
__menuet__sys_exit(); |
} |
GetBufferSize(hBuff, &mix_size); |
SDL_printf("buffer created, size is %d\n",mix_size); |
mix_size >>= 1; |
data = malloc(mix_size); |
audio_response=1; |
if (!data) __menuet__sys_exit(); |
// wait for resume |
while (audio_command!=AUDIO_RESUME) |
Yield(); |
// initialize |
/* bInCallback=1; |
callback(userdata,data,mix_size); |
SetBuffer(hBuff,data,0,mix_size); |
callback(userdata,data,mix_size); |
SetBuffer(hBuff,data,mix_size,mix_size); |
bInCallback=0;*/ |
audio_command=0; |
bPaused=0; |
audio_response=1; |
PlayBuffer(hBuff,0); |
// main loop |
for (;;) |
{ |
if (audio_command==AUDIO_RESUME) |
{ |
PlayBuffer(hBuff,0); |
audio_command = 0; |
bPaused = 0; |
audio_response = 1; |
} |
else if (audio_command==AUDIO_SUSPEND) |
{ |
StopBuffer(hBuff); |
audio_command = 0; |
bPaused = 1; |
audio_response = 1; |
} |
else if (audio_command==AUDIO_DIE) |
{ |
audio_response = 1; |
StopBuffer(hBuff); |
DestroyBuffer(hBuff); |
__menuet__sys_exit(); |
} |
else |
{ |
GetProcessInfo(main_slot); |
if (pinfo[0x32]==9 || *(__u32*)(pinfo+0x1E)!=main_tid) |
{ |
audio_command = AUDIO_DIE; |
continue; |
} |
} |
if (bPaused) |
__menuet__delay100(5); |
else |
{ |
GetNotify(event); |
if (event[0] != 0xFF000001) |
continue; |
while (bLocked) |
Yield(); |
bInCallback=1; |
callback(userdata,data,mix_size); |
bInCallback=0; |
SetBuffer(hBuff,data,event[3],mix_size); |
} |
} |
} |
int SDL_OpenAudio(SDL_AudioSpec* desired, SDL_AudioSpec* obtained) |
{ |
if (!bInitialized) |
{ |
SDL_SetError("Audio device was not initialized"); |
return -1; |
} |
if (!obtained) |
{ |
SDL_SetError("Audio format: software emulation is not supported"); |
return -1; |
} |
if (used_format) |
{ |
SDL_SetError("Audio device was already opened"); |
return -1; |
} |
memcpy(obtained,desired,sizeof(SDL_AudioSpec)); |
switch (desired->freq) |
{ |
#define HANDLE_FREQ(freq,symb) \ |
case freq: \ |
switch (desired->channels) \ |
{ \ |
case 1: \ |
switch (desired->format) \ |
{ \ |
case AUDIO_U8: \ |
case AUDIO_S8: \ |
used_format = PCM_1_8_##symb; \ |
break; \ |
case AUDIO_U16SYS: \ |
case AUDIO_S16SYS: \ |
used_format = PCM_1_16_##symb; \ |
break; \ |
} \ |
break; \ |
case 2: \ |
switch (desired->format) \ |
{ \ |
case AUDIO_U8: \ |
case AUDIO_S8: \ |
used_format = PCM_2_8_##symb; \ |
break; \ |
case AUDIO_U16SYS: \ |
case AUDIO_S16SYS: \ |
used_format = PCM_2_16_##symb; \ |
break; \ |
} \ |
break; \ |
} \ |
break; |
HANDLE_FREQ(48000,48); |
HANDLE_FREQ(44100,44); |
HANDLE_FREQ(32000,32); |
HANDLE_FREQ(24000,24); |
HANDLE_FREQ(22050,22); |
HANDLE_FREQ(16000,16); |
HANDLE_FREQ(12000,12); |
HANDLE_FREQ(11025,11); |
HANDLE_FREQ(8000,8); |
} |
if (!used_format) |
{ |
SDL_SetError("Unknown audio format"); |
return -1; |
} |
callback=desired->callback; |
userdata=desired->userdata; |
GetProcessInfo(-1); |
main_tid = *(__u32*)(pinfo+0x1E); |
for (main_slot=0;;main_slot++) |
{ |
GetProcessInfo(main_slot); |
if (pinfo[0x32]!=9 && *(__u32*)(pinfo+0x1E)==main_tid) |
break; |
} |
audio_tid=CreateThread(audio_thread,audio_thread_stack+40960); |
if (audio_tid<0) |
{ |
SDL_SetError("Cannot create audio thread"); |
return -1; |
} |
ActivateWnd(main_slot); |
while (!audio_response) |
Yield(); |
if (!hBuff) |
{ |
SDL_SetError("Cannot create audio buffer"); |
return -1; |
} |
if (!data) |
{ |
SDL_SetError("Cannot allocate audio buffer"); |
return -1; |
} |
obtained->silence = (desired->format == AUDIO_U8 ? 0x80 : 0); |
obtained->size = mix_size; |
obtained->samples = obtained->size / obtained->channels; |
if (desired->format == AUDIO_U16SYS || desired->format == AUDIO_S16SYS) |
obtained->samples /= 2; |
SDL_printf("obtained size is %d, samples %d\n",obtained->size, |
obtained->samples); |
return 0; |
} |
void SDL_CloseAudio(void) |
{ |
if (!audio_tid) return; |
audio_response = 0; |
audio_command = AUDIO_DIE; |
while (!audio_response) |
Yield(); |
free(data); |
used_format = 0; |
} |
void SDL_PauseAudio(int pause_on) |
{ |
if (!audio_tid) return; |
audio_response = 0; |
audio_command = pause_on?AUDIO_SUSPEND:AUDIO_RESUME; |
while (!audio_response) |
Yield(); |
} |
void SDL_LockAudio(void) |
{ |
if (!audio_tid) return; |
bLocked = 1; |
while (bInCallback) |
Yield(); |
} |
void SDL_UnlockAudio(void) |
{ |
bLocked = 0; |
} |
Property changes: |
Added: svn:executable |
+* |
\ No newline at end of property |
/contrib/sdk/sources/SDL-1.2.2_newlib/src/endian/SDL_endian.c |
---|
0,0 → 1,105 |
/* |
SDL - Simple DirectMedia Layer |
Copyright (C) 1997, 1998, 1999, 2000, 2001 Sam Lantinga |
This library is free software; you can redistribute it and/or |
modify it under the terms of the GNU Library General Public |
License as published by the Free Software Foundation; either |
version 2 of the License, or (at your option) any later version. |
This library is distributed in the hope that it will be useful, |
but WITHOUT ANY WARRANTY; without even the implied warranty of |
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU |
Library General Public License for more details. |
You should have received a copy of the GNU Library General Public |
License along with this library; if not, write to the Free |
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA |
Sam Lantinga |
slouken@devolution.com |
*/ |
/* Functions for dynamically reading and writing endian-specific values */ |
#include "SDL_endian.h" |
Uint16 SDL_ReadLE16 (SDL_RWops *src) |
{ |
Uint16 value; |
SDL_RWread(src, &value, (sizeof value), 1); |
return(SDL_SwapLE16(value)); |
} |
Uint16 SDL_ReadBE16 (SDL_RWops *src) |
{ |
Uint16 value; |
SDL_RWread(src, &value, (sizeof value), 1); |
return(SDL_SwapBE16(value)); |
} |
Uint32 SDL_ReadLE32 (SDL_RWops *src) |
{ |
Uint32 value; |
SDL_RWread(src, &value, (sizeof value), 1); |
return(SDL_SwapLE32(value)); |
} |
Uint32 SDL_ReadBE32 (SDL_RWops *src) |
{ |
Uint32 value; |
SDL_RWread(src, &value, (sizeof value), 1); |
return(SDL_SwapBE32(value)); |
} |
Uint64 SDL_ReadLE64 (SDL_RWops *src) |
{ |
Uint64 value; |
SDL_RWread(src, &value, (sizeof value), 1); |
return(SDL_SwapLE64(value)); |
} |
Uint64 SDL_ReadBE64 (SDL_RWops *src) |
{ |
Uint64 value; |
SDL_RWread(src, &value, (sizeof value), 1); |
return(SDL_SwapBE64(value)); |
} |
int SDL_WriteLE16 (SDL_RWops *dst, Uint16 value) |
{ |
value = SDL_SwapLE16(value); |
return(SDL_RWwrite(dst, &value, (sizeof value), 1)); |
} |
int SDL_WriteBE16 (SDL_RWops *dst, Uint16 value) |
{ |
value = SDL_SwapBE16(value); |
return(SDL_RWwrite(dst, &value, (sizeof value), 1)); |
} |
int SDL_WriteLE32 (SDL_RWops *dst, Uint32 value) |
{ |
value = SDL_SwapLE32(value); |
return(SDL_RWwrite(dst, &value, (sizeof value), 1)); |
} |
int SDL_WriteBE32 (SDL_RWops *dst, Uint32 value) |
{ |
value = SDL_SwapBE32(value); |
return(SDL_RWwrite(dst, &value, (sizeof value), 1)); |
} |
int SDL_WriteLE64 (SDL_RWops *dst, Uint64 value) |
{ |
value = SDL_SwapLE64(value); |
return(SDL_RWwrite(dst, &value, (sizeof value), 1)); |
} |
int SDL_WriteBE64 (SDL_RWops *dst, Uint64 value) |
{ |
value = SDL_SwapBE64(value); |
return(SDL_RWwrite(dst, &value, (sizeof value), 1)); |
} |
Property changes: |
Added: svn:executable |
+* |
\ No newline at end of property |
/contrib/sdk/sources/SDL-1.2.2_newlib/src/events/SDL_active.c |
---|
0,0 → 1,91 |
/* |
SDL - Simple DirectMedia Layer |
Copyright (C) 1997, 1998, 1999, 2000, 2001 Sam Lantinga |
This library is free software; you can redistribute it and/or |
modify it under the terms of the GNU Library General Public |
License as published by the Free Software Foundation; either |
version 2 of the License, or (at your option) any later version. |
This library is distributed in the hope that it will be useful, |
but WITHOUT ANY WARRANTY; without even the implied warranty of |
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU |
Library General Public License for more details. |
You should have received a copy of the GNU Library General Public |
License along with this library; if not, write to the Free |
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA |
Sam Lantinga |
slouken@devolution.com |
*/ |
/* Application focus/iconification handling code for SDL */ |
#include <stdio.h> |
#include <string.h> |
#include "SDL_events.h" |
#include "SDL_events_c.h" |
/* These are static for our active event handling code */ |
static Uint8 SDL_appstate = 0; |
/* Public functions */ |
int SDL_AppActiveInit(void) |
{ |
/* Start completely active */ |
SDL_appstate = (SDL_APPACTIVE|SDL_APPINPUTFOCUS|SDL_APPMOUSEFOCUS); |
/* That's it! */ |
return(0); |
} |
Uint8 SDL_GetAppState(void) |
{ |
return(SDL_appstate); |
} |
/* This is global for SDL_eventloop.c */ |
int SDL_PrivateAppActive(Uint8 gain, Uint8 state) |
{ |
int posted; |
Uint8 new_state; |
/* Modify the current state with the given mask */ |
if ( gain ) { |
new_state = (SDL_appstate | state); |
} else { |
new_state = (SDL_appstate & ~state); |
} |
/* Drop events that don't change state */ |
if ( new_state == SDL_appstate ) { |
return(0); |
} |
/* Update internal active state */ |
SDL_appstate = new_state; |
/* Post the event, if desired */ |
posted = 0; |
if ( SDL_ProcessEvents[SDL_ACTIVEEVENT] == SDL_ENABLE ) { |
SDL_Event event; |
memset(&event, 0, sizeof(event)); |
event.type = SDL_ACTIVEEVENT; |
event.active.gain = gain; |
event.active.state = state; |
if ( (SDL_EventOK == NULL) || (*SDL_EventOK)(&event) ) { |
posted = 1; |
SDL_PushEvent(&event); |
} |
} |
/* If we lost keyboard focus, post key-up events */ |
if ( (state & SDL_APPINPUTFOCUS) && !gain ) { |
SDL_ResetKeyboard(); |
} |
return(posted); |
} |
Property changes: |
Added: svn:executable |
+* |
\ No newline at end of property |
/contrib/sdk/sources/SDL-1.2.2_newlib/src/events/SDL_events.c |
---|
0,0 → 1,471 |
/* |
SDL - Simple DirectMedia Layer |
Copyright (C) 1997, 1998, 1999, 2000, 2001 Sam Lantinga |
This library is free software; you can redistribute it and/or |
modify it under the terms of the GNU Library General Public |
License as published by the Free Software Foundation; either |
version 2 of the License, or (at your option) any later version. |
This library is distributed in the hope that it will be useful, |
but WITHOUT ANY WARRANTY; without even the implied warranty of |
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU |
Library General Public License for more details. |
You should have received a copy of the GNU Library General Public |
License along with this library; if not, write to the Free |
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA |
Sam Lantinga |
slouken@devolution.com |
*/ |
/* General event handling code for SDL */ |
#include <stdio.h> |
#include <string.h> |
#include "SDL.h" |
#include "SDL_thread.h" |
#include "SDL_mutex.h" |
#include "SDL_events.h" |
#include "SDL_events_c.h" |
#include "SDL_timer_c.h" |
#ifndef DISABLE_JOYSTICK |
#include "SDL_joystick_c.h" |
#endif |
#ifndef ENABLE_X11 |
#define DISABLE_X11 |
#endif |
#include "SDL_syswm.h" |
#include "SDL_sysevents.h" |
/* Public data -- the event filter */ |
SDL_EventFilter SDL_EventOK = NULL; |
Uint8 SDL_ProcessEvents[SDL_NUMEVENTS]; |
static Uint32 SDL_eventstate = 0; |
/* Private data -- event queue */ |
#define MAXEVENTS 128 |
static struct { |
SDL_mutex *lock; |
int active; |
int head; |
int tail; |
SDL_Event event[MAXEVENTS]; |
int wmmsg_next; |
struct SDL_SysWMmsg wmmsg[MAXEVENTS]; |
} SDL_EventQ; |
/* Private data -- event locking structure */ |
static struct { |
SDL_mutex *lock; |
int safe; |
} SDL_EventLock; |
/* Thread functions */ |
static SDL_Thread *SDL_EventThread = NULL; /* Thread handle */ |
static Uint32 event_thread; /* The event thread id */ |
void SDL_Lock_EventThread(void) |
{ |
if ( SDL_EventThread && (SDL_ThreadID() != event_thread) ) { |
/* Grab lock and spin until we're sure event thread stopped */ |
SDL_mutexP(SDL_EventLock.lock); |
while ( ! SDL_EventLock.safe ) { |
SDL_Delay(1); |
} |
} |
} |
void SDL_Unlock_EventThread(void) |
{ |
if ( SDL_EventThread && (SDL_ThreadID() != event_thread) ) { |
SDL_mutexV(SDL_EventLock.lock); |
} |
} |
static int SDL_GobbleEvents(void *unused) |
{ |
SDL_SetTimerThreaded(2); |
event_thread = SDL_ThreadID(); |
while ( SDL_EventQ.active ) { |
SDL_VideoDevice *video = current_video; |
SDL_VideoDevice *this = current_video; |
/* Get events from the video subsystem */ |
if ( video ) { |
video->PumpEvents(this); |
} |
/* Queue pending key-repeat events */ |
SDL_CheckKeyRepeat(); |
#ifndef DISABLE_JOYSTICK |
/* Check for joystick state change */ |
if ( SDL_numjoysticks && (SDL_eventstate & SDL_JOYEVENTMASK) ) { |
SDL_JoystickUpdate(); |
} |
#endif |
/* Give up the CPU for the rest of our timeslice */ |
SDL_EventLock.safe = 1; |
if( SDL_timer_running ) { |
SDL_ThreadedTimerCheck(); |
} |
SDL_Delay(1); |
/* Check for event locking. |
On the P of the lock mutex, if the lock is held, this thread |
will wait until the lock is released before continuing. The |
safe flag will be set, meaning that the other thread can go |
about it's business. The safe flag is reset before the V, |
so as soon as the mutex is free, other threads can see that |
it's not safe to interfere with the event thread. |
*/ |
SDL_mutexP(SDL_EventLock.lock); |
SDL_EventLock.safe = 0; |
SDL_mutexV(SDL_EventLock.lock); |
} |
SDL_SetTimerThreaded(0); |
event_thread = 0; |
return(0); |
} |
static int SDL_StartEventThread(Uint32 flags) |
{ |
/* Reset everything to zero */ |
SDL_EventThread = NULL; |
memset(&SDL_EventLock, 0, sizeof(SDL_EventLock)); |
/* Create the lock and set ourselves active */ |
#ifndef DISABLE_THREADS |
SDL_EventQ.lock = SDL_CreateMutex(); |
if ( SDL_EventQ.lock == NULL ) { |
#ifdef macintosh /* On MacOS 7/8, you can't multithread, so no lock needed */ |
; |
#else |
return(-1); |
#endif |
} |
#endif /* !DISABLE_THREADS */ |
SDL_EventQ.active = 1; |
if ( (flags&SDL_INIT_EVENTTHREAD) == SDL_INIT_EVENTTHREAD ) { |
SDL_EventLock.lock = SDL_CreateMutex(); |
if ( SDL_EventLock.lock == NULL ) { |
return(-1); |
} |
SDL_EventLock.safe = 0; |
SDL_EventThread = SDL_CreateThread(SDL_GobbleEvents, NULL); |
if ( SDL_EventThread == NULL ) { |
return(-1); |
} |
} else { |
event_thread = 0; |
} |
return(0); |
} |
static void SDL_StopEventThread(void) |
{ |
SDL_EventQ.active = 0; |
if ( SDL_EventThread ) { |
SDL_WaitThread(SDL_EventThread, NULL); |
SDL_EventThread = NULL; |
SDL_DestroyMutex(SDL_EventLock.lock); |
} |
SDL_DestroyMutex(SDL_EventQ.lock); |
} |
Uint32 SDL_EventThreadID(void) |
{ |
return(event_thread); |
} |
/* Public functions */ |
void SDL_StopEventLoop(void) |
{ |
/* Halt the event thread, if running */ |
SDL_StopEventThread(); |
/* Clean out EventQ */ |
SDL_EventQ.head = 0; |
SDL_EventQ.tail = 0; |
SDL_EventQ.wmmsg_next = 0; |
} |
/* This function (and associated calls) may be called more than once */ |
int SDL_StartEventLoop(Uint32 flags) |
{ |
int retcode; |
/* Clean out the event queue */ |
SDL_EventThread = NULL; |
SDL_EventQ.lock = NULL; |
SDL_StopEventLoop(); |
/* No filter to start with, process most event types */ |
SDL_EventOK = NULL; |
memset(SDL_ProcessEvents,SDL_ENABLE,sizeof(SDL_ProcessEvents)); |
SDL_eventstate = ~0; |
/* It's not save to call SDL_EventState() yet */ |
SDL_eventstate &= ~(0x00000001 << SDL_SYSWMEVENT); |
SDL_ProcessEvents[SDL_SYSWMEVENT] = SDL_IGNORE; |
/* Initialize event handlers */ |
retcode = 0; |
retcode += SDL_AppActiveInit(); |
retcode += SDL_KeyboardInit(); |
retcode += SDL_MouseInit(); |
retcode += SDL_QuitInit(); |
if ( retcode < 0 ) { |