Index: xboing-2.4/audio/soundIt.c =================================================================== --- /dev/null 1970-01-01 00:00:00.000000000 +0000 +++ xboing-2.4/audio/soundIt.c 2006-05-30 12:53:03.000000000 +0200 @@ -0,0 +1,483 @@ +/* SoundIt library 0.021 + + Copyright 1994 Brad Pitzel pitzel@cs.sfu.ca + + Feel free to use/distribute/modify as long as proper credits + are included. +*/ + +#include "soundIt.h" +#include +#include /* PATH_MAX */ +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +/*==========================================================================*/ +/* the mix buff, where the channels are mixed into. The mix buffer is then + dumped to the sound device (/dev/dsp). Samples are mixed in + Vunclipbuf (buffer of ints), then the values in Vunclipbuf are clipped to + values between 0 and 255, and stored into Vclippedbuf (buffer of unsigned + chars). +*/ + +struct Mix + { + unsigned char *Vclippedbuf; + int *Vunclipbuf; + int Vsize; + }; +typedef struct Mix Mix; + +/*==========================================================================*/ +struct Channel + { + unsigned char *Vstart,*Vcurrent; /* ptr's into a playing sample */ + int Vlen; /* length of sample in bytes */ + int Vleft; /* bytes left of sample to play */ + }; +typedef struct Channel Channel; + +/*==========================================================================*/ + +/* variables prefixed with S_ are static */ +/* 0 if mixer isn't initialized or init failed, 1 if mixer is good */ +static int sampleMixerStatus = 0; + +static const Sample *S_sounds = NULL; /* ptr to array of samples */ +static int S_num_sounds = 0; /* size of 'sounds' array above */ +static int S_fd_snddev = -1; /* file # for sound device once open */ +static int S_fd_pipe[2] = { -1, -1 }; /* pipe to talk to child process */ +static int S_son_pid = -1; /* process ID for the forked sound mixer */ +static const char *S_snddev = NULL; /* char string for device, ie "/dev/dsp" */ +static int S_num_channels = 6; /* number of channels to mix */ +static int S_playback_freq = 0; /* playback frequency (in Hz) */ +/*==========================================================================*/ +/* non-public functions, used only within this file*/ + +int Snd_init_dev(); +int Snd_restore_dev(); + +void Chan_reset( Channel *chan ); /* init channel structure */ + + /* start a sample playing on a channel */ +void Chan_assign( Channel *chan, const Sample *snd ); + + /* mix all channels together into the 'mix' structure */ +int Chan_mixAll( Mix *mix, Channel *ch ); + + /* used by Chan_mixAll to mix the 1st channel */ +int Chan_copyIn( Channel *chan, Mix *mix ); + + /* used by Chan_mixAll to mix the middle channels */ +int Chan_mixIn( Channel *chan, Mix *mix ); + + /* used by Chan_mixAll to mix the last channel */ +int Chan_finalMixIn( Channel *chan, Mix *mix ); + + +/* alloc mem for mix buffer, and deallocate function */ +/* The sound channels are mixed together into the mix buffer */ +/* then the mix buffer data is sent directly to the sound device */ +void Mix_alloc( Mix *mix, int size ); +void Mix_dealloc( Mix *mix ); + +/*==========================================================================*/ +/* justing for testing, normally not called */ +void dump_snd_list() + { + int i=0; + + for(i=0; iVstart=NULL; + chan->Vcurrent=NULL; + chan->Vlen=0; + chan->Vleft=0; + } + +/*==========================================================================*/ +void Chan_assign( Channel *chan, const Sample *snd ) + { + chan->Vstart = snd->data; + chan->Vcurrent= chan->Vstart; + chan->Vlen = snd->len; + chan->Vleft = snd->len; + } + +/*==========================================================================*/ +int Chan_copyIn( Channel *chan, Mix *mix ) + { + int i,*p = mix->Vunclipbuf, result, min; + + result = (chan->Vleft>0) ? 1 : 0; + min = (chan->Vleft < mix->Vsize) ? chan->Vleft : mix->Vsize; + + for(i=0; iVcurrent++; + } + chan->Vleft -= i; + + /* fill the remaining (if any) part of the mix buffer with silence */ + while (iVsize) + { + *p++ = 128; + i++; + } + return result; + } + +/*==========================================================================*/ +int Chan_mixIn( Channel *chan, Mix *mix ) + { + int i,*p = mix->Vunclipbuf, result, min; + + result = (chan->Vleft>0) ? 1 : 0; + min = (chan->Vleft < mix->Vsize) ? chan->Vleft : mix->Vsize; + + for(i=0; iVcurrent++) - 128; + } + + chan->Vleft -= i; + return result; + } + +/*========================================================================*/ +/* clip an int to a value between 0 and 255 */ +static inline +unsigned char clip(int i) + { + return (i<0) ? 0 : ( (i>255) ? 255 : i ); + } + +/*==========================================================================*/ +int Chan_finalMixIn( Channel *chan, Mix *mix ) + { + register int i; + int *p = mix->Vunclipbuf, result, min; + unsigned char *final = mix->Vclippedbuf; + + result = (chan->Vleft>0) ? 1 : 0; + min = (chan->Vleft < mix->Vsize) ? chan->Vleft : mix->Vsize; + + for(i=0; iVcurrent++) - 128; + *final++ = clip(*p++); + } + chan->Vleft -= i; + + /* copy rest of Vunclipbuf over to Vclippedbuf */ + while (iVsize) + { + *final++ = clip(*p++); + i++; + } + + return result; + } + + +/*==========================================================================*/ +void Mix_alloc(Mix *mix, int size) + { + mix->Vclippedbuf = (unsigned char *)calloc( sizeof(char), size); + mix->Vunclipbuf = (int *)calloc( sizeof(int), size); + mix->Vsize = size; + + if ((mix->Vclippedbuf==NULL)||(mix->Vunclipbuf==NULL)) + { + fprintf(stderr,"Unable to allocate memory for mixer buffer\n"); + exit(-1); + } + } + +/*==========================================================================*/ +void Mix_dealloc( Mix *mix) + { + if (mix->Vclippedbuf) free(mix->Vclippedbuf); + if (mix->Vunclipbuf) free(mix->Vunclipbuf); + } + +/*==========================================================================*/ +/* Mixes together the channels into one sound. + Returns # of channels currently playing *any* sound + Therefore, return 0 means to channels have a sample, therefore no + sound is playing +*/ +int Chan_mixAll( Mix *mix, Channel *chan ) + { + int result = 0,i=0; + + result = Chan_copyIn( chan, mix); + + /* we want to loop for S_num_channels-2 */ + for(i=2;idata = NULL; + sample->len = 0; + + fp = fopen(file,"r"); + + if (fp==NULL) return -1; + + /* get length of the file */ + sample->len = lseek( fileno(fp), 0, SEEK_END ); + + /* go back to beginning of file */ + lseek( fileno(fp), 0, SEEK_SET ); + + /* alloc memory for sample */ + sample->data = (unsigned char *)malloc( sample->len ); + + if (sample->data==NULL) + { + fclose(fp); + return -2; + } + + fread( sample->data, 1, sample->len, fp ); + + fclose(fp); + + return 0; + } Index: xboing-2.4/audio/soundIt.h =================================================================== --- /dev/null 1970-01-01 00:00:00.000000000 +0000 +++ xboing-2.4/audio/soundIt.h 2006-05-30 12:53:03.000000000 +0200 @@ -0,0 +1,82 @@ +/* SoundIt library 0.03 + + Copyright 1994 Brad Pitzel pitzel@cs.sfu.ca + + Feel free to use/distribute/modify as long as proper credits + are included. +*/ + +/* Designed for digital sound effects in games. + + Will mix channels of mono 8-bit raw samples, & play back in "real-time". + Each channel can only play one sample at a time, but all + channels can play a different sample simultaneously. + + If you have sox, use the ' -t .ub ' option to make samples + that this library will play properly. + + I wrote this in C, instead of C++, so hopefully a few more people will + take a look and make it better :-) +*/ + +#ifndef SOUNDIT_VERS +#define SOUNDIT_VERS "0.03" + +#include +#include + +/* 00002 = 2 fragments */ +/* 00007 = means each fragment is 2^7 or 128 bytes */ +/* See voxware docs (in /usr/src/linux/drivers/sound) for more info */ +#define FRAG_SPEC 0x00020007 + +/*==========================================================================*/ +struct Sample + { + unsigned char *data; /* unsigned 8-bit raw samples */ + int len; /* length of sample in bytes */ + }; + +typedef struct Sample Sample; + +/* given the name of a .raw sound file, load it into the Sample struct */ +/* pointed to by 'sample' */ +int +Snd_loadRawSample( const char *file, Sample *sample ); + + +/*==========================================================================*/ +/* init sound device, etc.. */ +/* num_snd = the number of samples in the sample array *sa */ +/* sa = the sample array */ +/* freq = the rate (Hz) to play back the samples */ +/* channels = # of channels to mix */ +/* sound_device = a char string for the sound device, eg, "/dev/dsp" */ +/* returns: 0=success, -1=failure.*/ +int +Snd_init( int num_snd, const Sample *sa, int freq, + int channels, const char *sound_device ); + + +/* shutdown sample player, free mem, etc/etc..*/ +int +Snd_restore(); + + +/* play a sound effect in the given channel 1..n*/ +/* volume = integers from 0 (off) to 100 (full volume)*/ +int +Snd_effect( int nr, int channel ); + + +/* stop a channel (1..n) from playing*/ +/*void +Snd_reset(enum snd_channel channel);*/ + + +/* stop all channels from playing*/ +/*void +Snd_reset();*/ + + +#endif Index: xboing-2.4/Imakefile =================================================================== --- xboing-2.4.orig/Imakefile 2006-05-30 12:52:57.000000000 +0200 +++ xboing-2.4/Imakefile 2006-05-30 12:53:03.000000000 +0200 @@ -24,18 +24,24 @@ XCOMM This is the directory where the highscore, level & sound data will be XCOMM placed. Default will be the current directory. - XBOING_DIR = . + XBOING_DIR = /usr/lib/games/xboing + +XCOMM Added these to override defaults so make install installs into +XCOMM $PREFIX and /usr/games -- Joey Hess. + + BINDIR = $(PREFIX)/usr/games XCOMM These are some defines that must be set. Some may be overwritten in the XCOMM machine arch section. - XPMLIB = -L/usr/X11/lib -lXpm + XPMLIB = -lXpm XPMINCLUDE = -I/usr/X11/include/X11 XBOINGINCLUDE = -I./include LEVEL_INSTALL_DIR = $(XBOING_DIR)/levels SOUNDS_DIR = $(XBOING_DIR)/sounds BACKUP_DIR = $(XBOING_DIR)/../backups - HIGH_SCORE_FILE = $(XBOING_DIR)/.xboing.scr + HIGH_SCORE_DIR = /var/lib/games + HIGH_SCORE_FILE = $(HIGH_SCORE_DIR)/xboing.score AUDIO_AVAILABLE = False AUDIO_SRC = audio/NOaudio.c AUDIO_INCLUDE = @@ -44,6 +50,7 @@ XCOMM Uncomment this if you want to use ANY of the AUDIO sound systems #define COMPILE_IN_AUDIO +#define linux XCOMM Uncomment this if you want to use RPLAY sound system XCOMM #define USE_RPLAY @@ -62,9 +69,9 @@ #if defined(LinuxArchitecture) && defined(COMPILE_IN_AUDIO) AUDIO_AVAILABLE = True - AUDIO_SRC = audio/LINUXaudio.c + AUDIO_SRC = audio/LINUXaudio2.c AUDIO_INCLUDE = - AUDIO_LIB = + AUDIO_LIB = #endif /* linux */ #if defined(svr4) && defined(COMPILE_IN_AUDIO) @@ -81,7 +88,7 @@ AUDIO_LIB = -laudio #endif /* SGIArchitecture */ -#if defined(SparcArchitecture) && defined(COMPILE_IN_AUDIO) +#if defined(SparcArchitecture) && !defined(LinuxArchitecture) && defined(COMPILE_IN_AUDIO) AUDIO_AVAILABLE = True AUDIO_SRC = audio/SUNaudio.c @@ -132,7 +139,7 @@ -DLEVEL_INSTALL_DIR=\"$(LEVEL_INSTALL_DIR)\" \ -DAUDIO_AVAILABLE=\"$(AUDIO_AVAILABLE)\" \ -DSOUNDS_DIR=\"$(SOUNDS_DIR)\" \ - -DREADMEP_FILE=\"$(XBOING_DIR)/docs/problems.doc\" + -DREADMEP_FILE=\"/usr/share/doc/xboing/problems.doc.gz\" XCOMM -DUSE_FLOCK=\"True\" \ XCOMM -DNEED_USLEEP=\"True\" \ XCOMM -DNO_LOCKING=\"True\" @@ -159,7 +166,7 @@ highscore.o misc.o inst.o gun.o keys.o \ audio.o special.o presents.o demo.o file.o \ preview.o dialogue.o eyedude.o editor.o \ - keysedit.o + keysedit.o audio/soundIt.o PROGRAMS = xboing @@ -174,6 +181,10 @@ $(RM) $@ $(LN) $? $@ +audio/soundIt.c: + cd audio && \ + gcc -Wall -O2 -finline-functions -fomit-frame-pointer -ffast-math -I. -c soundIt.c -o soundIt.o + depend:: version.c audio.c ComplexProgramTarget_1($(PROGRAMS), $(LOCAL_LIBRARIES), ) @@ -182,30 +193,31 @@ @echo "XBoing directory is " $(XBOING_DIR) @: @echo "Creating directory " $(XBOING_DIR) - @if [ ! -d $(XBOING_DIR) ]; then mkdir $(XBOING_DIR); fi - $(INSTALL) -c $(INSTDATFLAGS) docs/problems.doc $(XBOING_DIR) + @if [ ! -d $(PREFIX)/$(XBOING_DIR) ]; then install -d $(PREFIX)/$(XBOING_DIR); fi + # $(INSTALL) -c $(INSTDATFLAGS) docs/problems.doc $(XBOING_DIR) @: @echo "Creating directory " $(LEVEL_INSTALL_DIR) - @if [ ! -d $(LEVEL_INSTALL_DIR) ]; then mkdir $(LEVEL_INSTALL_DIR); fi + @if [ ! -d $(PREFIX)/$(LEVEL_INSTALL_DIR) ]; then install -d $(PREFIX)/$(LEVEL_INSTALL_DIR); fi @: @echo "Copying level data into directory " $(LEVEL_INSTALL_DIR) @cd ./levels; set -x; for file in *.data; do \ - $(INSTALL) -c $(INSTDATFLAGS) $$file $(LEVEL_INSTALL_DIR);\ + $(INSTALL) -c $(INSTDATFLAGS) $$file $(PREFIX)/$(LEVEL_INSTALL_DIR);\ done @: @if [ "$(AUDIO_AVAILABLE)" = "True" ]; \ then \ echo "Creating directory " $(SOUNDS_DIR); \ - if [ ! -d $(SOUNDS_DIR) ]; then mkdir $(SOUNDS_DIR); fi;\ + if [ ! -d $(PREFIX)/$(SOUNDS_DIR) ]; then install -d $(PREFIX)/$(SOUNDS_DIR); fi;\ echo "Copying sound files into directory " $(SOUNDS_DIR);\ cd ./sounds; set -x; for file in *.au; do \ - $(INSTALL) -c $(INSTDATFLAGS) $$file $(SOUNDS_DIR); \ + $(INSTALL) -c $(INSTDATFLAGS) $$file $(PREFIX)/$(SOUNDS_DIR); \ done; \ fi @: @echo "Creating a highscore file " $(HIGH_SCORE_FILE) - @touch $(HIGH_SCORE_FILE); - @chmod a+rw $(HIGH_SCORE_FILE); + $(INSTALL) -d $(PREFIX)/$(HIGH_SCORE_DIR); +# @touch $(PREFIX)/$(HIGH_SCORE_FILE); +# @chmod 664 $(PREFIX)/$(HIGH_SCORE_FILE); XCOMM I use this for my daily backup of my code. Index: xboing-2.4/demo.c =================================================================== --- xboing-2.4.orig/demo.c 2006-05-30 12:52:57.000000000 +0200 +++ xboing-2.4/demo.c 2006-05-30 12:53:03.000000000 +0200 @@ -154,7 +154,7 @@ /* Construct the demo level filename */ if ((str = getenv("XBOING_LEVELS_DIR")) != NULL) - sprintf(levelPath, "%s/demo.data", str); + snprintf(levelPath, sizeof(levelPath),"%s/demo.data", str); else sprintf(levelPath, "%s/demo.data", LEVEL_INSTALL_DIR); Index: xboing-2.4/editor.c =================================================================== --- xboing-2.4.orig/editor.c 2006-05-30 12:52:57.000000000 +0200 +++ xboing-2.4/editor.c 2006-05-30 12:53:03.000000000 +0200 @@ -213,7 +213,7 @@ /* Construct the Edit level filename */ if ((str = getenv("XBOING_LEVELS_DIR")) != NULL) - sprintf(levelPath, "%s/editor.data", str); + snprintf(levelPath,sizeof(levelPath)-1, "%s/editor.data", str); else sprintf(levelPath, "%s/editor.data", LEVEL_INSTALL_DIR); @@ -958,8 +958,8 @@ if ((num > 0) && (num <= MAX_NUM_LEVELS)) { /* Construct the Edit level filename */ - if ((str2 = getenv("XBOING_LEVELS_DIR")) != NULL) - sprintf(levelPath, "%s/level%02ld.data", str2, (u_long) num); + if ((str2 = getenv("XBOING_LEVELS_DIR")) != NULL) + snprintf(levelPath, sizeof(levelPath)-1,"%s/level%02ld.data", str2, (u_long) num); else sprintf(levelPath, "%s/level%02ld.data", LEVEL_INSTALL_DIR, (u_long) num); @@ -1017,9 +1017,9 @@ num = atoi(str); if ((num > 0) && (num <= MAX_NUM_LEVELS)) { - /* Construct the Edit level filename */ - if ((str2 = getenv("XBOING_LEVELS_DIR")) != NULL) - sprintf(levelPath, "%s/level%02ld.data", str2, (u_long) num); + /* Construct the Edit level filename */ + if ((str2 = getenv("XBOING_LEVELS_DIR")) != NULL) + snprintf(levelPath, sizeof(levelPath)-1,"%s/level%02ld.data", str2, (u_long) num); else sprintf(levelPath, "%s/level%02ld.data", LEVEL_INSTALL_DIR, (u_long) num); Index: xboing-2.4/error.c =================================================================== --- xboing-2.4.orig/error.c 2006-05-30 12:52:58.000000000 +0200 +++ xboing-2.4/error.c 2006-05-30 12:53:03.000000000 +0200 @@ -87,8 +87,8 @@ #ifndef READMEP_FILE /* Repeated to generate a message when compiling */ -#define READMEP_FILE "README.problems" -#define READMEP_FILE "README.problems" +#define READMEP_FILE "README.problems.doc.gz" +#define READMEP_FILE "README.problems.doc.gz" #endif /* Print a standard error message to stdout and flush it */ fprintf(stdout, "XBoing - Error: %s\n", message); Index: xboing-2.4/file.c =================================================================== --- xboing-2.4.orig/file.c 2006-05-30 12:52:58.000000000 +0200 +++ xboing-2.4/file.c 2006-05-30 12:53:03.000000000 +0200 @@ -139,7 +139,7 @@ /* Construct the level filename */ if ((str = getenv("XBOING_LEVELS_DIR")) != NULL) - sprintf(levelPath, "%s/level%02ld.data", str, newLevel); + snprintf(levelPath,sizeof(levelPath), "%s/level%02ld.data", str, newLevel); else sprintf(levelPath, "%s/level%02ld.data", LEVEL_INSTALL_DIR, newLevel); @@ -177,7 +177,7 @@ static int bgrnd = 1; /* Save the file in home directory - construct path */ - sprintf(levelPath, "%s/.xboing-saveinfo", GetHomeDir()); + snprintf(levelPath, sizeof(levelPath)-1, "%s/.xboing-saveinfo", GetHomeDir()); /* Open the save file info for reading */ if ((saveFile = fopen(levelPath, "r+")) == NULL) @@ -239,7 +239,7 @@ DisplayLevelInfo(display, levelWindow, level); /* Load the saved file in home directory - construct path */ - sprintf(levelPath, "%s/.xboing-savelevel", GetHomeDir()); + snprintf(levelPath, sizeof(levelPath)-1, "%s/.xboing-savelevel", GetHomeDir()); /* Read in the saved level data */ if (ReadNextLevel(display, window, levelPath, True) == False) @@ -283,7 +283,7 @@ saveGame.numBullets = GetNumberBullets(); /* Save the file in home directory - construct path */ - sprintf(levelPath, "%s/.xboing-saveinfo", GetHomeDir()); + snprintf(levelPath, sizeof(levelPath)-1, "%s/.xboing-saveinfo", GetHomeDir()); /* Open the save file info for writing */ if ((saveFile = fopen(levelPath, "w+")) == NULL) @@ -309,7 +309,7 @@ WarningMessage("Cannot close save game info file."); /* Save the file in home directory - construct path */ - sprintf(levelPath, "%s/.xboing-savelevel", GetHomeDir()); + snprintf(levelPath, sizeof(levelPath)-1, "%s/.xboing-savelevel", GetHomeDir()); if (SaveLevelDataFile(display, levelPath) == True) { Index: xboing-2.4/highscore.c =================================================================== --- xboing-2.4.orig/highscore.c 2006-05-30 12:52:58.000000000 +0200 +++ xboing-2.4/highscore.c 2006-05-30 12:53:03.000000000 +0200 @@ -1023,7 +1023,7 @@ { /* Use the environment variable if it exists */ if ((str = getenv("XBOING_SCORE_FILE")) != NULL) - strcpy(filename, str); + strncpy(filename, str, sizeof(filename)-1); else strcpy(filename, HIGH_SCORE_FILE); } @@ -1095,7 +1095,7 @@ { /* Use the environment variable if it exists */ if ((str = getenv("XBOING_SCORE_FILE")) != NULL) - strcpy(filename, str); + strncpy(filename, str, sizeof(filename)-1); else strcpy(filename, HIGH_SCORE_FILE); } @@ -1218,7 +1218,7 @@ /* Use the environment variable if it exists */ if ((str = getenv("XBOING_SCORE_FILE")) != NULL) - strcpy(filename, str); + strncpy(filename, str, sizeof(filename)-1); else strcpy(filename, HIGH_SCORE_FILE); Index: xboing-2.4/init.c =================================================================== --- xboing-2.4.orig/init.c 2006-05-30 12:52:58.000000000 +0200 +++ xboing-2.4/init.c 2006-05-30 12:53:03.000000000 +0200 @@ -438,7 +438,7 @@ WarningMessage("Your X Window system display variable is not set."); else { - sprintf(string, "Cannot connect to display called <%s>.", displayName); + snprintf(string, sizeof(string) - 1, "Cannot connect to display called <%s>.", displayName); WarningMessage(string); } } Index: xboing-2.4/misc.c =================================================================== --- xboing-2.4.orig/misc.c 2006-05-30 12:52:58.000000000 +0200 +++ xboing-2.4/misc.c 2006-05-30 12:53:03.000000000 +0200 @@ -116,6 +116,10 @@ long SyncTime; static unsigned long accu; +#ifdef __alpha__ + ms *= 1000; /* convert from milliseconds to microseconds for usleep */ +#endif + gettimeofday(&st, NULL); XSync(display, False); gettimeofday(&et, NULL); @@ -427,7 +431,7 @@ */ if ((ptr = getenv("HOME")) != NULL) - (void) strcpy(dest, ptr); + (void) strncpy(dest, ptr,sizeof(dest)-1); else { /* HOME variable is not present so get USER var */ @@ -441,7 +445,7 @@ } if (pw) - (void) strcpy(dest, pw->pw_dir); + (void) strncpy(dest, pw->pw_dir, sizeof(dest)-1); else *dest = '\0'; } Index: xboing-2.4/preview.c =================================================================== --- xboing-2.4.orig/preview.c 2006-05-30 12:52:58.000000000 +0200 +++ xboing-2.4/preview.c 2006-05-30 12:53:03.000000000 +0200 @@ -139,7 +139,7 @@ /* Construct the Preview level filename */ if ((str = getenv("XBOING_LEVELS_DIR")) != NULL) - sprintf(levelPath, "%s/level%02d.data", str, lnum); + snprintf(levelPath, sizeof(levelPath)-1, "%s/level%02d.data", str, lnum); else sprintf(levelPath, "%s/level%02d.data", LEVEL_INSTALL_DIR, lnum);