1 /****************************************************************/
2 /* code copyright 1995-1996 Andrew Johnson - ALL RIGHTS RESERVED*/
3 /*                          ajohnson@eecs.uic.edu               */
4 /*                                                              */
5 /*                      Electronic Visualization Lab (M/C 154)  */
6 /*                      University of Illinois at Chicago       */
7 /*                      851 South Morgan St. Room 1120 SEO      */
8 /*                      Chicago, IL 60607-7053                  */
9 /*                                                              */
10 /*                      (312) 996-3002     (312) 413-7585 FAX   */
11 /***********************************************************************/
12 /* audio.c  v 1.4                                                      */
13 /* audio routines for battalion                                        */
14 /* since audio is so machine dependant there is separate code for the  */
15 /*    various implementations ...                                      */
16 /***********************************************************************/
17 
18 #include "battalion.h"
19 #include <sys/stat.h>
20 
21 extern int noSound;
22 int soundOn;
23 int musicOn;
24 extern int showframes;
25 extern struct monsterInfo Googelon;
26 
27 /***************/
28 /* music stuff */
29 /***************/
30 
31 int playingTankFire, playingHeloRocket, playingTankMaser;
32 int playingExplosion, playingSlag, playingTech;
33 
34 int musicCount, deadCount;
35 
36 #ifdef SGIAUDIO
37 
38     struct sound * allSounds;
39     struct aSound oneSound[MAXSOUNDS];
40 
41 #endif
42 #ifdef SUNAUDIO
43 
44     char	*audio_buffer[MAXSOUNDS];
45     int		buffer_counter[MAXSOUNDS];
46     char	*audio_dev = "/dev/audio";
47     int		audiofd;
48     Audio_hdr   file_hdr;
49 
50     int playingBeam, playingMusic;
51 
52 #endif
53 
54 #ifdef MACVERSION
55 
56     int playingBeam, playingCrash, playingMusic, maserOn;
57 
58 Boolean idleFlag;
59 
60 		Handle  beamSound, boomSound, crashSound, monsterbeamSound,
61 				rocketSound, slagSound, tankSound, techSound, musicSound;
62 
63 long musicRefNum, monsterbeamRefNum, maserbeamRefNum;
64 SndChannelPtr musicChan, monsterbeamChan, maserbeamChan;
65 
66 #endif
67 
68 #ifdef LINUXAUDIO
69 
70 #include "soundIt.h"
71 #define	 NUM_SAMPLES	12
72 #define	 SAMPLE_RATE	11000
73 #define	 NUM_CHANNELS	8
74 
75     Sample	snd[NUM_SAMPLES];
76     char	*audio_dev = "/dev/dsp";
77     int		audiofd;
78     int playingBeam, playingMusic;
79 
80 #endif
81 
82 /*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/
83 /* small sound routines to avoid having to use external variables*/
84 
85 #ifdef LINUXAUDIO
86 
killSounds(void)87 void killSounds( void )
88 {
89     Snd_restore();
90 }
91 
92 #endif
93 
94 #ifdef MACVERSION
setSoundVolume(long vol)95 void setSoundVolume(long vol)
96 	{
97 	SetDefaultOutputVolume(vol);
98 	}
99 #endif
100 
turnSoundOff()101 void turnSoundOff()
102     {
103     soundOn = 0;
104     }
105 
turnSoundOn()106 void turnSoundOn()
107     {
108     soundOn = 1;
109     }
110 
toggleSound()111 void toggleSound()
112     {
113     soundOn = !soundOn;
114     }
115 
getSoundOn()116 int getSoundOn()
117     {
118     return(soundOn);
119     }
120 
turnMusicOff()121 void turnMusicOff()
122     {
123     musicOn = 0;
124     }
125 
turnMusicOn()126 void turnMusicOn()
127     {
128     musicOn = 1;
129     }
130 
toggleMusic()131 void toggleMusic()
132     {
133     musicOn = !musicOn;
134     }
135 
getMusicOn()136 int getMusicOn()
137     {
138     return(musicOn);
139     }
140 
141 /*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/
142 
checkSound(char * dataPath)143 void checkSound(char * dataPath)
144     {
145     char * garbage;
146 
147 #ifdef SGIAUDIO
148     long pvbuf[4];
149 
150     ALseterrorhandler(0);
151 
152     pvbuf[0] = AL_OUTPUT_COUNT;
153     pvbuf[2] = AL_MONITOR_CTL;
154 
155     if (ALgetparams(AL_DEFAULT_DEVICE, pvbuf, 4) < 0)
156 	{
157 	noSound = 1;
158 	soundOn = 0;
159 	musicOn = 0;
160 	}
161 
162     if (!noSound)
163 	{
164 	/******************************************/
165 	/* load all the sound effects into memory */
166 	/******************************************/
167 
168 	InitAudio("SOUNDS/beam.aiff",        dataPath,  0);
169 	InitAudio("SOUNDS/boom.aiff",        dataPath,  1);
170 	InitAudio("SOUNDS/crash.aiff",       dataPath,  2);
171 	InitAudio("SOUNDS/monsterbeam.aiff", dataPath,  3);
172 	InitAudio("SOUNDS/rocket.aiff",      dataPath,  4);
173 	InitAudio("SOUNDS/slag.aiff",        dataPath,  5);
174 	InitAudio("SOUNDS/tank.aiff",        dataPath,  6);
175 	InitAudio("SOUNDS/tech.aiff",        dataPath,  7);
176 
177 	/*********************************************/
178 	/* load all the background music into memory */
179 	/*********************************************/
180 
181 	InitAudio("MUSIC/1.aiff",        dataPath,  10);
182 	InitAudio("MUSIC/2.aiff",        dataPath,  11);
183 	InitAudio("MUSIC/3.aiff",        dataPath,  12);
184 	InitAudio("MUSIC/4.aiff",        dataPath,  13);
185 	InitAudio("MUSIC/5.aiff",        dataPath,  14);
186 
187 	InitAudio("MUSIC/d1.aiff",       dataPath,  15);
188 	InitAudio("MUSIC/d2.aiff",       dataPath,  16);
189 	InitAudio("MUSIC/d3.aiff",       dataPath,  17);
190 	InitAudio("MUSIC/d4.aiff",       dataPath,  18);
191 	InitAudio("MUSIC/d5.aiff",       dataPath,  19);
192 
193 	}
194 #else
195 # ifdef SUNAUDIO
196     /* Solaris audio support */
197 
198     noSound = 1;
199     soundOn = 0;
200     musicOn = 0;
201     {
202 	/* Check if audio device is available and writable */
203 	struct stat st;
204 
205 	if (stat(audio_dev, &st) >= 0) {
206 	    audiofd = open(audio_dev, O_WRONLY);
207 	    if (audiofd >= 0) {
208 		noSound = 0;
209 		close(audiofd);
210 	    }
211 	}
212     }
213 
214     if (!noSound) {
215 	/* Load all sound effects into memory */
216 	InitAudio("SOUNDS/beam.au",	    dataPath,  0);
217 	InitAudio("SOUNDS/boom.au",         dataPath,  1);
218 	InitAudio("SOUNDS/crash.au",        dataPath,  2);
219 	InitAudio("SOUNDS/monsterbeam.au",  dataPath,  3);
220 	InitAudio("SOUNDS/rocket.au",       dataPath,  4);
221 	InitAudio("SOUNDS/slag.au",         dataPath,  5);
222 	InitAudio("SOUNDS/tank.au",         dataPath,  6);
223 	InitAudio("SOUNDS/tech.au",         dataPath,  7);
224 
225 	/* Load all background music into memory */
226 	InitAudio("MUSIC/1.au",        	    dataPath,  10);
227 	InitAudio("MUSIC/2.au",		    dataPath,  11);
228 	InitAudio("MUSIC/3.au",		    dataPath,  12);
229 	InitAudio("MUSIC/4.au",		    dataPath,  13);
230 	InitAudio("MUSIC/5.au",		    dataPath,  14);
231 
232 	InitAudio("MUSIC/d1.au",	    dataPath,  15);
233 	InitAudio("MUSIC/d2.au",	    dataPath,  16);
234 	InitAudio("MUSIC/d3.au",	    dataPath,  17);
235 	InitAudio("MUSIC/d4.au",	    dataPath,  18);
236 	InitAudio("MUSIC/d5.au",	    dataPath,  19);
237     }
238 #else
239 #ifdef MACVERSION
240 
241 SndCommand testCommand;
242 
243 	beamSound	= GetResource( 'snd ', 1000 );
244 	boomSound	= GetResource( 'snd ', 1001 );
245 	crashSound	= GetResource( 'snd ', 1002 );
246 	monsterbeamSound = GetResource( 'snd ', 1003 );
247 	rocketSound	= GetResource( 'snd ', 1004 );
248 	slagSound	= GetResource( 'snd ', 1005 );
249 	tankSound	= GetResource( 'snd ', 1006 );
250 	techSound	= GetResource( 'snd ', 1007 );
251 	musicSound	= GetResource( 'snd ', 1010 );
252 
253     noSound = 0;
254     soundOn = 0;
255     musicOn = 0;
256 
257     /* using the SoundHelper code to do asynch audio */
258 
259     SHInitSoundHelper(&idleFlag, 8);
260 
261 SHPlayByHandle(musicSound, -1, &musicRefNum);
262 SHPlayPause(musicRefNum);
263 SHPlayByHandle(beamSound, -1, &maserbeamRefNum);
264 SHPlayPause(maserbeamRefNum);
265 SHPlayByHandle(monsterbeamSound, -1, &monsterbeamRefNum);
266 SHPlayPause(monsterbeamRefNum);
267 
268 
269 # else
270 #ifdef LINUXAUDIO
271     /* Linux audio support */
272 
273     noSound = 1;
274     soundOn = 0;
275     musicOn = 0;
276     {
277 	/* Check if audio device is available and writable */
278 	struct stat st;
279 
280 	if (stat(audio_dev, &st) >= 0) {
281 	    audiofd = open(audio_dev, O_WRONLY);
282 	    if (audiofd >= 0) {
283 		noSound = 0;
284 		close(audiofd);
285 	    }
286 	}
287     }
288 
289     if (!noSound) {
290 	/* Load all sound effects into memory */
291 	Snd_loadRawSample("SOUNDS/beam.raw", &snd[0]);
292 	Snd_loadRawSample("SOUNDS/boom.raw", &snd[1]);
293 	Snd_loadRawSample("SOUNDS/crash.raw",&snd[2]);
294 	Snd_loadRawSample("SOUNDS/monsterbeam.raw",&snd[3]);
295 	Snd_loadRawSample("SOUNDS/rocket.raw",&snd[4]);
296 	Snd_loadRawSample("SOUNDS/slag.raw",&snd[5]);
297 	Snd_loadRawSample("SOUNDS/tank.raw",&snd[6]);
298 	Snd_loadRawSample("SOUNDS/tech.raw",&snd[7]);
299 
300 	/* Load all background music into memory */
301 
302 	Snd_loadRawSample("MUSIC/1.raw",&snd[10]);
303 	Snd_loadRawSample("MUSIC/2.raw",&snd[11]);
304 /*	Snd_loadRawSample("MUSIC/3.au",&snd[12]);
305 	Snd_loadRawSample("MUSIC/4.au",&snd[13]);
306 	Snd_loadRawSample("MUSIC/5.au",&snd[14]);
307 
308 	Snd_loadRawSample("MUSIC/d1.au",&snd[15]);
309 	Snd_loadRawSample("MUSIC/d2.au",&snd[16]);
310 	Snd_loadRawSample("MUSIC/d3.au",&snd[17]);
311 	Snd_loadRawSample("MUSIC/d4.au",&snd[18]);
312 	Snd_loadRawSample("MUSIC/d5.au",&snd[19]);
313 */
314         if (Snd_init( NUM_SAMPLES, snd, SAMPLE_RATE, NUM_CHANNELS, audio_dev )==EXIT_FAILURE){
315    	    printf("Can't init soundIt library. yech..\n");
316    	    exit(0);
317 	}
318     }
319 #else
320 
321     /*  Other than SGI or Solaris or Macintosh*/
322     noSound = 1;
323     soundOn = 0;
324     musicOn = 0;
325 
326 #endif
327 #endif
328 #endif
329 #endif
330 
331 	garbage = dataPath; /* to avoid compiler warning */
332     }
333 
334 /*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/
335 
336 #ifdef MACVERSION
337 
processIdleAppSounds(void)338 void processIdleAppSounds(void)
339 {
340 	if (idleFlag)
341 	{
342 	SHIdle();
343 	}
344 }
345 #endif
346 
347 /*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/
348 /*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/
349 /* initialize sound list to empty                                */
350 /*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/
351 
initSounds()352 void initSounds()
353     {
354 #ifdef SGIAUDIO
355 
356     register int i;
357 
358     allSounds = NULL;
359     allSounds = (struct sound *) calloc(1, sizeof(struct sound));
360     allSounds->next = NULL;
361 
362     musicCount		= 0;
363     deadCount		= 0;
364 
365     playingTankFire = playingHeloRocket = playingTankMaser = 0;
366     playingExplosion = playingSlag = playingTech = 0;
367 
368     for (i=0; i<MAXSOUNDS; i++)
369 	{
370 	oneSound[i].samplesPerFrame	= 0;
371 	oneSound[i].numberSamples	= 0;
372 	oneSound[i].samplesPerBuffer	= 0;
373 	oneSound[i].audioRate		= 0;
374 	oneSound[i].sampleBuffer	= NULL;
375 	}
376 
377 #endif
378 # ifdef SUNAUDIO
379 
380     int n;
381 
382     musicCount		= 0;
383     deadCount		= 0;
384 
385     playingTankFire = playingHeloRocket = playingTankMaser = 0;
386     playingExplosion = playingSlag = playingTech = 0;
387     playingBeam = playingMusic = 0;
388 
389     /* Mark audio buffers as empty */
390 
391     for (n = 0; n < MAXSOUNDS; n++)
392 	audio_buffer[n] = NULL;
393 
394 # endif
395 
396 #ifdef MACVERSION
397 
398     musicCount		= 0;
399     deadCount		= 0;
400 
401     playingTankFire = playingHeloRocket = playingTankMaser = 0;
402     playingExplosion = playingSlag = playingTech = 0;
403     playingBeam = playingMusic = maserOn = 0;
404 	playingCrash = 0;
405 
406 
407 #endif
408 #ifdef LINUXAUDIO
409 
410     int n;
411 
412     musicCount		= 0;
413     deadCount		= 0;
414 
415     playingTankFire = playingHeloRocket = playingTankMaser = 0;
416     playingExplosion = playingSlag = playingTech = 0;
417     playingBeam = playingMusic = 0;
418 
419     /* Mark audio buffers as empty */
420 
421 //    for (n = 0; n < MAXSOUNDS; n++)
422 //	audio_buffer[n] = NULL;
423 
424 #endif
425 
426     }
427 
428 /*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/
429 /*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/
430 /* clear all completed sounds from the sound list                */
431 /*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/
432 
flushSounds()433 void flushSounds()
434     {
435 #ifdef SGIAUDIO
436 
437     struct sound *s, *t;
438 
439     playingHeloRocket = playingTech = playingTankMaser = playingSlag = 0;
440 
441     playingExplosion--;
442     if (playingExplosion < 0)
443 	playingExplosion = 0;
444 
445     playingTankFire--;
446     if (playingTankFire < 0)
447 	playingTankFire =  0;
448 
449     s = allSounds;
450     while(s->next != NULL)
451 	{
452 	if(ALgetfilled(s->next->audio_port) <= 0)
453 	    {
454 	    ALcloseport(s->next->audio_port);
455 	    t = s->next;
456 	    s->next = s->next->next;
457 	    free(t);
458 	    }
459 	else
460 	    s = s->next;
461 	}
462 #endif
463 # ifdef SUNAUDIO
464 
465     playingHeloRocket = playingTech = playingTankMaser = playingSlag = 0;
466 
467     playingExplosion--;
468     if (playingExplosion < 0)
469 	playingExplosion = 0;
470 
471     playingTankFire--;
472     if (playingTankFire < 0)
473 	playingTankFire = 0;
474 
475     playingBeam--;
476     if (playingBeam < 0)
477 	playingBeam = 0;
478 
479     playingMusic--;
480     if (playingMusic < 0)
481 	playingMusic = 0;
482 
483 # endif
484 
485 #ifdef MACVERSION
486 
487 	processIdleAppSounds();
488 
489     playingTankMaser = playingSlag = 0;
490 
491     playingHeloRocket--;
492     if (playingHeloRocket < 0)
493 	playingHeloRocket = 0;
494 
495     playingCrash--;
496     if (playingCrash < 0)
497 	playingCrash = 0;
498 
499     playingExplosion--;
500     if (playingExplosion < 0)
501 	playingExplosion = 0;
502 
503     playingTech--;
504     if (playingTech < 0)
505 	playingTech = 0;
506 
507     playingTankFire--;
508     if (playingTankFire < 0)
509 	playingTankFire =  0;
510 #endif
511 
512 #ifdef LINUXAUDIO
513 
514     playingHeloRocket = playingTech = playingTankMaser = playingSlag = 0;
515 
516     playingExplosion--;
517     if (playingExplosion < 0)
518 	playingExplosion = 0;
519 
520     playingTankFire--;
521     if (playingTankFire < 0)
522 	playingTankFire = 0;
523 
524     playingBeam--;
525     if (playingBeam < 0)
526 	playingBeam = 0;
527 
528     playingMusic--;
529     if (playingMusic < 0)
530 	playingMusic = 0;
531 
532 #endif
533 
534     }
535 
536 
537 
538 /*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/
539 /*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/
540 /* clear all sounds of a given type from the sound list          */
541 /*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/
542 
soundKiller(int soundType)543 void soundKiller(int soundType)
544     {
545     int garbage;
546 
547 #ifdef SGIAUDIO
548 
549     struct sound * s, *t;
550 
551     s = allSounds;
552 
553     while(s->next != NULL)
554 	{
555 	if (s->next->type == soundType)
556 	    {
557 	    ALcloseport(s->next->audio_port);
558 	    t = s->next;
559 	    s->next = s->next->next;
560 	    free(t);
561 	    }
562 	else
563 	    s = s->next;
564 	}
565 #endif
566 
567 #ifdef MACVERSION
568 
569 	/* stop the sound */
570 
571 	switch (soundType) {
572 		case MUSIC:
573 			/*if (playingMusic)*/
574 				{
575 				/* SHPlayStop(musicRefNum);*/
576 				SHPlayPause(musicRefNum);
577 				playingMusic = 0;
578 				}
579 			break;
580 		case MONSTERBEAM:
581 			/*if (playingBeam)*/
582 				{
583 				/*SHPlayStop(monsterbeamRefNum);*/
584 				SHPlayPause(monsterbeamRefNum);
585 				playingBeam = 0;
586 				}
587 			break;
588 
589 		case TANKMASER:
590 		/*	if (maserOn)*/
591 				{
592 				/*SHPlayStop(maserbeamRefNum);*/
593 				SHPlayPause(maserbeamRefNum);
594 				maserOn = 0;
595 				}
596 			break;
597 
598 }
599 #endif
600 
601 #ifdef LINUXAUDIO
602 /*
603 printf("callkill %d... ", soundType);
604     if (soundType == MUSIC) {
605 	Snd_effect( 10, -1 );
606 	Snd_effect( 11, -1 );
607     }
608 */
609 #endif
610 
611     garbage = soundType; /* to avoid compiler warning */
612     }
613 
614 /*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/
615 /*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/
616 /* process a request for a specific sound                        */
617 /*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/
618 
doSound(int theSound)619 void doSound(int theSound)
620     {
621     int garbage;
622 
623 #ifdef SGIAUDIO
624 
625 static int deadMusic[MAXDEADMUSIC] = {15, 16, 17, 18, 19};
626 
627 static int theMusic[MAXMUSIC] = {10, 11, 12, 13, 14};
628 
629 
630     struct sound * s, *t;
631     int soundDelay;
632 
633     if (!noSound)
634 	{
635 	soundDelay = showframes;
636 
637 	if (soundDelay <= 1)
638 	    soundDelay = 1;
639 
640 	if (soundDelay > 30)
641 	    soundDelay = 30;
642 
643 	if (((theSound == MUSIC) && musicOn) || ((theSound != MUSIC) && soundOn))
644 	    {
645 	    t = NULL;
646 
647 	    switch (theSound){
648 	    case MUSIC:		s = allSounds->next;
649 				while ((s != NULL) && (t == NULL))
650 				    if (s->type == MUSIC)
651 					t = s;
652 				    else
653 					s = s->next;
654 
655 				if (Googelon.monsterIsDead)
656 				    {
657 				    musicCount = 0;
658 				    if ((t != NULL) && (deadCount < MAXDEADMUSIC))
659 					{
660 					if ((ALgetfilled(t->audio_port)+oneSound[deadMusic[deadCount]].numberSamples < 2*oneSound[10].samplesPerBuffer) && (deadCount < 3))
661 					    {
662 					    ALwritesamps(t->audio_port,
663 							oneSound[deadMusic[deadCount]].sampleBuffer,
664 							oneSound[deadMusic[deadCount]].numberSamples);
665 					    deadCount = deadCount+1;
666 					    }
667 					}
668 				    else if (deadCount < MAXDEADMUSIC)
669 					{
670 					OutAudio(deadMusic[deadCount]);
671 					deadCount = deadCount+1;
672 					}
673 				    }
674 				else
675 				    {
676 				    deadCount = 0;
677 				    if (t != NULL)
678 					{
679 					if(ALgetfilled(t->audio_port)+oneSound[theMusic[musicCount]].numberSamples < 2*oneSound[10].samplesPerBuffer)
680 					    {
681 					    ALwritesamps(t->audio_port,
682 							oneSound[theMusic[musicCount]].sampleBuffer,
683 							oneSound[theMusic[musicCount]].numberSamples);
684 					    musicCount = (musicCount+1) % MAXMUSIC;
685 					    }
686 					}
687 				    else
688 					{
689 					OutAudio(theMusic[musicCount]);
690 					musicCount = (musicCount+1) % MAXMUSIC;
691 					}
692 
693 				    }
694 				break;
695 
696 	    case TANKFIRE:	if (!playingTankFire)
697 				    {
698 				    OutAudio(6);
699 				    playingTankFire = soundDelay / 5;
700 				    if (playingTankFire < 2)
701 					playingTankFire = 2;
702 				    }
703 				break;
704 
705 	    case HELOROCKET:    if (!playingHeloRocket)
706 				    {
707 				    OutAudio(4);
708 				    playingHeloRocket = 1;
709 				    }
710 				break;
711 
712 	    case TANKMASER:	s = allSounds->next;
713 				while ((s != NULL) && (t == NULL))
714 				    if (s->type == TANKMASER)
715 					t = s;
716 				    else
717 					s = s->next;
718 				if (t != NULL)
719 				    {
720 				    if(ALgetfilled(t->audio_port) <= oneSound[0].samplesPerBuffer)
721 					ALwritesamps(t->audio_port,
722 						    oneSound[0].sampleBuffer,
723 						    oneSound[0].numberSamples);
724 				    }
725 				else
726 				    OutAudio(0);
727 				break;
728 
729 	    case EXPLOSION:	if (!playingExplosion)
730 				    {
731 				    OutAudio(1);
732 				    playingExplosion = soundDelay / 5;
733 				    if (playingExplosion < 2)
734 					playingExplosion = 2;
735 				    }
736 				break;
737 
738 	    case MONSTERBEAM:	s = allSounds->next;
739 				while ((s != NULL) && (t == NULL))
740 				    if (s->type == MONSTERBEAM)
741 					t = s;
742 				    else
743 					s = s->next;
744 				if (t != NULL)
745 				    {
746 				    if(ALgetfilled(t->audio_port) <= oneSound[3].samplesPerBuffer)
747 					ALwritesamps(t->audio_port,
748 						    oneSound[3].sampleBuffer,
749 						    oneSound[3].numberSamples);
750 				    }
751 				else
752 				    OutAudio(3);
753 				break;
754 
755 	    case SLAG:		if (!playingSlag)
756 				    {
757 				    OutAudio(5);
758 				    playingSlag = 1;
759 				    }
760 				break;
761 
762 	    case CRASH:		OutAudio(2);
763 				break;
764 
765 	    case TECHSHOOT:    if (!playingTech)
766 				    {
767 				    OutAudio(7);
768 				    playingTech = 1;
769 				    }
770 				break;
771 	    }
772 	}
773     }
774 
775 #endif
776 # ifdef SUNAUDIO
777 
778 static int deadMusic[MAXDEADMUSIC] = {15, 16, 17, 18, 19};
779 
780 static int theMusic[MAXMUSIC] = {10, 11, 12, 13, 14};
781 
782     int soundDelay;
783 
784     if (!noSound) {
785 	soundDelay = showframes;
786 
787 	if (soundDelay <= 1)
788 	    soundDelay = 1;
789 
790 	if (soundDelay > 30)
791 	    soundDelay = 30;
792 
793 	if (((theSound == MUSIC) && musicOn) ||
794 	    ((theSound != MUSIC) && soundOn)) {
795 
796 	    switch (theSound) {
797 	    case MUSIC:
798 		if (!playingMusic) {
799 		    OutAudio(theMusic[musicCount]);
800 		    musicCount = (musicCount+1) % MAXMUSIC;
801 
802 		    /* each music sample is 5 secs long */
803 		    playingMusic =  soundDelay * 5; ;
804 		}
805 		break;
806 
807 	    case TANKFIRE:
808 		if (!playingTankFire) {
809 		    OutAudio(6);
810 		    playingTankFire = soundDelay / 5;
811 		    if (playingTankFire < 2)
812 			playingTankFire = 2;
813 		}
814 		break;
815 
816 	    case HELOROCKET:
817 		if (!playingHeloRocket) {
818 		    OutAudio(4);
819 		    playingHeloRocket = 1;
820 		}
821 		break;
822 
823 	    case TANKMASER:
824 		    OutAudio(0);
825 		break;
826 
827 	    case EXPLOSION:
828 		if (!playingExplosion) {
829 		    OutAudio(1);
830 		    playingExplosion = soundDelay / 5;
831 		    if (playingExplosion < 2)
832 			playingExplosion = 2;
833 		}
834 		break;
835 
836 	    case MONSTERBEAM:
837 		if (!playingBeam) {
838 		    OutAudio(3);
839 		    playingBeam = 5 /*soundDelay / 5*/;
840 		}
841 		break;
842 
843 	    case SLAG:
844 		if (!playingSlag) {
845 		    OutAudio(5);
846 		    playingSlag = 1;
847 		}
848 		break;
849 
850 	    case CRASH:
851 		OutAudio(2);
852 		break;
853 
854 	    case TECHSHOOT:
855 		if (!playingTech) {
856 		    OutAudio(7);
857 		    playingTech = 1;
858 		}
859 		break;
860 	    }
861 	}
862     }
863 
864 #endif
865 #ifdef LINUXAUDIO
866 
867 static int deadMusic[MAXDEADMUSIC] = {15, 16};
868 
869 static int theMusic[MAXMUSIC] = {10, 11};
870 
871     int soundDelay;
872 
873 //    printf("doSound -> %d\n", theSound);
874 
875     if (!noSound) {
876 	soundDelay = showframes;
877 
878 	if (soundDelay <= 1)
879 	    soundDelay = 1;
880 
881 	if (soundDelay > 30)
882 	    soundDelay = 30;
883 
884 	if (((theSound == MUSIC) && musicOn) ||
885 	    ((theSound != MUSIC) && soundOn)) {
886 
887 	    switch (theSound) {
888 	    case MUSIC:
889 		if (!playingMusic) {
890 		    OutAudio(theMusic[musicCount]);
891 		    musicCount = (musicCount+1) % MAXMUSIC;
892 //printf("Music start\n");
893 		    /* each music sample is 5 secs long */
894 		    playingMusic =  soundDelay * 20; ;
895 		}
896 		break;
897 
898 	    case TANKFIRE:
899 		if (!playingTankFire) {
900 		    OutAudio(6);
901 		    playingTankFire = soundDelay / 5;
902 		    if (playingTankFire < 2)
903 			playingTankFire = 2;
904 		}
905 		break;
906 
907 	    case HELOROCKET:
908 		if (!playingHeloRocket) {
909 		    OutAudio(4);
910 		    playingHeloRocket = 1;
911 		}
912 		break;
913 
914 	    case TANKMASER:
915 		    OutAudio(0);
916 		break;
917 
918 	    case EXPLOSION:
919 		if (!playingExplosion) {
920 		    OutAudio(1);
921 		    playingExplosion = soundDelay / 5;
922 		    if (playingExplosion < 2)
923 			playingExplosion = 2;
924 		}
925 		break;
926 
927 	    case MONSTERBEAM:
928 		if (!playingBeam) {
929 		    OutAudio(3);
930 		    playingBeam = 5 /*soundDelay / 5*/;
931 		}
932 		break;
933 
934 	    case SLAG:
935 		if (!playingSlag) {
936 		    OutAudio(5);
937 		    playingSlag = 1;
938 		}
939 		break;
940 
941 	    case CRASH:
942 		OutAudio(2);
943 		break;
944 
945 	    case TECHSHOOT:
946 		if (!playingTech) {
947 		    OutAudio(7);
948 		    playingTech = 1;
949 		}
950 		break;
951 	    }
952 	}
953     }
954 
955 #endif
956 
957 /*------------------------ Mac Specific code --------------------*/
958 
959 #ifdef MACVERSION
960     int soundDelay;
961 
962     if (!noSound)
963 	{
964 	soundDelay = showframes;
965 
966 	if (soundDelay <= 1)
967 	    soundDelay = 1;
968 
969 	if (soundDelay > 30)
970 	    soundDelay = 30;
971 
972 	if (((theSound == MUSIC) && musicOn) || ((theSound != MUSIC) && soundOn))
973 	    {
974 	    switch (theSound){
975 	    case MUSIC: if (!playingMusic)
976 	    				{
977 	    				/*SHPlayByHandle(musicSound, &musicRefNum);*/
978 	    				SHPlayContinue(musicRefNum);
979 	    				playingMusic = 1;
980 	    				}
981 				break;
982 
983 	    case TANKFIRE:if (!playingTankFire)
984 					    { /* different from sun version */
985 					    SHPlayByHandle(tankSound, 1, nil);
986 
987 					    playingTankFire = soundDelay / 5;
988 					    if (playingTankFire < 3)
989 						playingTankFire = 3;
990 					    }
991 				break;
992 
993 	    case HELOROCKET:
994 			if (!playingHeloRocket)
995 				{ /* different from sun version */
996 			    SHPlayByHandle(rocketSound, 1, nil);
997 
998 			    playingHeloRocket = soundDelay / 5;
999 			    if (playingHeloRocket < 3)
1000 					playingHeloRocket = 3;
1001 
1002 				}
1003 			break;
1004 
1005 
1006 	    case TANKMASER:
1007 	    			if (!maserOn)
1008 	    		 		{
1009 	    		 		/*SHPlayByHandle(beamSound, &maserbeamRefNum);*/
1010 	    		 		SHPlayContinue(maserbeamRefNum);
1011 
1012 	    		 		maserOn = 1;
1013 	    		 		}
1014 				break;
1015 
1016 	    case EXPLOSION:
1017 				if (!playingExplosion)
1018 					{ /* different from sun version */
1019 				     SHPlayByHandle(boomSound, 1, nil);
1020 
1021 				    playingExplosion = soundDelay / 5;
1022 				    if (playingExplosion < 3)
1023 					playingExplosion = 3;
1024 					}
1025 				break;
1026 
1027 	    case MONSTERBEAM:
1028 	    		if (!playingBeam)
1029 	    			{
1030 	    			/*SHPlayByHandle(monsterbeamSound, &monsterbeamRefNum);*/
1031 	    			SHPlayContinue(monsterbeamRefNum);
1032 
1033 	    			playingBeam = 1;
1034 	    			}
1035 				break;
1036 
1037 	    case SLAG:
1038 				if (!playingSlag) {
1039 				    SHPlayByHandle(slagSound, 1, nil);
1040 
1041 				    playingSlag = 1;
1042 				}
1043 				break;
1044 
1045 	    case CRASH:
1046 	    		if (!playingCrash)
1047 	    			{
1048 	    			SHPlayByHandle(crashSound, 1, nil);
1049 
1050 				    playingCrash = 2;
1051 				    }
1052 				break;
1053 
1054 	    case TECHSHOOT:
1055 				if (!playingTech)
1056 					{ /* different from sun version */
1057 				    SHPlayByHandle(techSound, 1, nil);
1058 
1059 				    playingTech = 2;
1060 					}
1061 				break;
1062 	    }
1063 	}
1064     }
1065 #endif
1066     garbage = theSound;
1067 }
1068 
1069 
1070 
1071 /*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/
1072 /*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/
1073 /* output a particular sound                                     */
1074 /*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/
1075 
1076 
OutAudio(int sCounter)1077 void OutAudio(int sCounter)
1078     {
1079     int garbage;
1080 
1081 #ifdef SGIAUDIO
1082 
1083     ALconfig audioPortConfig;
1084     long pvbuf[4];
1085     long outputRate;
1086     struct sound * s;
1087 
1088     pvbuf[0] = AL_OUTPUT_RATE;
1089     ALgetparams(AL_DEFAULT_DEVICE, pvbuf, 2);
1090 
1091     if (pvbuf[1] > 0)
1092 	outputRate = pvbuf[1];
1093     else
1094 	outputRate = AL_RATE_UNDEFINED;
1095 
1096     pvbuf[0] = AL_OUTPUT_COUNT;
1097     pvbuf[2] = AL_MONITOR_CTL;
1098     ALgetparams(AL_DEFAULT_DEVICE, pvbuf, 4);
1099 
1100     if ((outputRate != oneSound[sCounter].audioRate) || ((pvbuf[1] == 0) && (pvbuf[3] == AL_MONITOR_OFF)))
1101 	{
1102 	outputRate = oneSound[sCounter].audioRate;
1103 	pvbuf[0] = AL_OUTPUT_RATE;
1104 	pvbuf[1] = outputRate;
1105 	ALsetparams(AL_DEFAULT_DEVICE, pvbuf, 2);
1106 	}
1107 
1108     audioPortConfig = ALnewconfig();
1109     ALsetwidth(audioPortConfig, AL_SAMPLE_16);
1110     ALsetchannels(audioPortConfig, oneSound[sCounter].samplesPerFrame);
1111 
1112      switch(sCounter){
1113 	case 1:
1114 	case 2:
1115 	case 4:
1116 	case 5:
1117 	case 6:
1118 	case 7:	    ALsetqueuesize(audioPortConfig, oneSound[sCounter].samplesPerBuffer);
1119 		    break;
1120 	case 0:
1121 	case 3:	    ALsetqueuesize(audioPortConfig, 2*oneSound[sCounter].samplesPerBuffer);
1122 		    break;
1123 	default:    ALsetqueuesize(audioPortConfig, 3*oneSound[sCounter].samplesPerBuffer);
1124 		    break;
1125     }
1126 
1127     s = (struct sound *) calloc(1, sizeof(struct sound));
1128 
1129     if (s != NULL)
1130 	{
1131         if (sCounter == 3)
1132 	    s->type = MONSTERBEAM;
1133 	else if (sCounter == 0)
1134 	    s->type = TANKMASER;
1135 	else if (sCounter >= 10)
1136 	    s->type = MUSIC;
1137 	else
1138 	    s->type = -1;
1139 
1140 	s->next = allSounds->next;
1141 	allSounds->next = s;
1142 
1143 	s->audio_port = ALopenport("battalion", "w", audioPortConfig);
1144 	if (s->audio_port == 0)
1145 	    {
1146 	    showError("too many simultaneous sounds");
1147 	    allSounds->next = s->next;
1148 	    free(s);
1149 	    }
1150 	else
1151 	    ALwritesamps(s->audio_port, oneSound[sCounter].sampleBuffer, oneSound[sCounter].numberSamples);
1152 	}
1153 
1154 #endif
1155 # ifdef SUNAUDIO
1156 
1157     static int first = 1;
1158 
1159     /* Check if a valid buffer and buffer contains a sample */
1160 
1161     if (sCounter < 0 || sCounter >= MAXSOUNDS ||
1162 		audio_buffer[sCounter] == NULL)
1163 	return;
1164 
1165     if (first) {
1166 	first = 0;
1167 
1168 	/* Open audio device */
1169 
1170 	audiofd = open(audio_dev, O_WRONLY /*| O_NDELAY | O_NONBLOCK*/);
1171 	if (audiofd < 0)
1172 	    return;
1173     }
1174 
1175     audio_flush_play(audiofd);
1176 
1177     if (write(audiofd, audio_buffer[sCounter], buffer_counter[sCounter]) < 0)
1178 	fprintf(stderr, "audio_play: buffer %d failed\n", sCounter);
1179 
1180 
1181 # endif
1182 #ifdef LINUXAUDIO
1183 
1184     static int first = 1;
1185 
1186     /* Check if a valid buffer and buffer contains a sample */
1187 
1188 //    printf("Sound N --> %d \n", sCounter);
1189 
1190     if (sCounter < 0 || sCounter >= NUM_SAMPLES) return;
1191 
1192 
1193     Snd_effect( sCounter, sCounter );
1194 
1195 # endif
1196 
1197     garbage = sCounter; /* to avoid compiler warning */
1198     }
1199 
1200 /*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/
1201 /*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/
1202 /* load a particular sound into memory                           */
1203 /*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/
1204 
1205 
InitAudio(char * fileName,char * dataPath,int sCounter)1206 void InitAudio(char * fileName,  char * dataPath, int sCounter)
1207     {
1208     char * garbName,  * garbPath;
1209     int garbCount;
1210 
1211 #ifdef SGIAUDIO
1212 
1213     /* IRIX 6 compilers want these next two to be integers
1214      * while IRIS 5 compilers want them to be long ... sheesh */
1215 
1216     int bitsPerSample;
1217     int garbage;
1218 
1219     long framesPerBuffer;
1220     long framesRead;
1221     FILE * sndtest;
1222     AFfilehandle audioFile;
1223     char textBuffer[80];
1224     char fullPath[MAXPATH];
1225 
1226 
1227     bitsPerSample   = 0;
1228     framesPerBuffer = 0;
1229     garbage	    = 0;
1230     framesRead	    = 0;
1231 
1232     strcpy(fullPath, dataPath);
1233     strcat(fullPath, fileName);
1234 
1235     sndtest = fopen(fullPath, "rb");
1236     if (sndtest == NULL)
1237 	{
1238 	sprintf(textBuffer, "Could not load %s", fullPath);
1239 	showError(textBuffer);
1240 	}
1241     else
1242 	{
1243 	fclose(sndtest);
1244 
1245 	audioFile = AFopenfile(fullPath, "r", AF_NULL_FILESETUP);
1246 
1247 	oneSound[sCounter].samplesPerFrame = AFgetchannels(audioFile, AF_DEFAULT_TRACK);
1248 
1249 	AFgetsampfmt(audioFile, AF_DEFAULT_TRACK, &garbage, &bitsPerSample);
1250 
1251 	oneSound[sCounter].audioRate  = (long) (AFgetrate(audioFile, AF_DEFAULT_TRACK));
1252 
1253 	if (bitsPerSample != 16)
1254 	    {
1255 	    sprintf(textBuffer, "incorrect sound format for %s - should be 16-bits", fileName);
1256 	    showError(textBuffer);
1257 	    }
1258 
1259 	framesPerBuffer = AFgetframecnt(audioFile, AF_DEFAULT_TRACK);
1260 
1261 	oneSound[sCounter].samplesPerBuffer = framesPerBuffer * oneSound[sCounter].samplesPerFrame;
1262 
1263 	oneSound[sCounter].sampleBuffer = (short *) calloc((unsigned) oneSound[sCounter].samplesPerBuffer, sizeof(short));
1264 
1265 	AFseekframe(audioFile, AF_DEFAULT_TRACK, 0);
1266 
1267 	framesRead = AFreadframes(audioFile, AF_DEFAULT_TRACK, oneSound[sCounter].sampleBuffer, framesPerBuffer);
1268 
1269 	AFclosefile(audioFile);
1270 
1271 	oneSound[sCounter].numberSamples = framesRead * oneSound[sCounter].samplesPerFrame;
1272 	}
1273 
1274 #endif
1275 # ifdef SUNAUDIO
1276 
1277     int	    error;
1278     int	    count;
1279     char    audioFile[MAXPATH];
1280 
1281     strcpy(audioFile, dataPath);
1282     strcat(audioFile, fileName);
1283 
1284     if ((audiofd = open(audioFile, O_RDONLY, 0)) < 0) {
1285 	fprintf(stderr, "audio_load: cannot open %s\n", audioFile);
1286 	exit(1);
1287     }
1288 
1289     error = audio_read_filehdr(audiofd, &file_hdr, (char *)NULL, 0);
1290 
1291     if (error != AUDIO_SUCCESS) {
1292 	fprintf(stderr, "audio_load: %s is not a valid audio file\n",
1293 		audioFile);
1294 	exit(-1);
1295     }
1296 
1297     if (audio_buffer[sCounter]) {
1298 	free(audio_buffer[sCounter]);
1299 	audio_buffer[sCounter] = NULL;
1300     }
1301 
1302     audio_buffer[sCounter] = (char *)malloc(file_hdr.data_size);
1303 
1304     if ((count = read(audiofd, audio_buffer[sCounter],
1305 			  file_hdr.data_size)) < 0) {
1306 	fprintf(stderr, "audio_load: error reading\n");
1307 	close(audiofd);
1308     }
1309 
1310     buffer_counter[sCounter] = count;
1311     close(audiofd);
1312 
1313 # endif
1314 
1315 #ifdef LINUXAUDIO
1316 
1317 #endif
1318 
1319     garbName  = fileName;
1320     garbPath  = dataPath;
1321     garbCount = sCounter;
1322 
1323     }
1324