]> icculus.org git repositories - btb/d2x.git/blob - arch/dos/allg_snd/sound/sound.c
This commit was generated by cvs2svn to compensate for changes in r2,
[btb/d2x.git] / arch / dos / allg_snd / sound / sound.c
1 /*         ______   ___    ___ 
2  *        /\  _  \ /\_ \  /\_ \ 
3  *        \ \ \L\ \\//\ \ \//\ \      __     __   _ __   ___ 
4  *         \ \  __ \ \ \ \  \ \ \   /'__`\ /'_ `\/\`'__\/ __`\
5  *          \ \ \/\ \ \_\ \_ \_\ \_/\  __//\ \L\ \ \ \//\ \L\ \
6  *           \ \_\ \_\/\____\/\____\ \____\ \____ \ \_\\ \____/
7  *            \/_/\/_/\/____/\/____/\/____/\/___L\ \/_/ \/___/
8  *                                           /\____/
9  *                                           \_/__/
10  *      By Shawn Hargreaves,
11  *      1 Salisbury Road,
12  *      Market Drayton,
13  *      Shropshire,
14  *      England, TF9 1AJ.
15  *
16  *      Sound setup routines and API framework functions.
17  *
18  *      See readme.txt for copyright information.
19  */
20
21
22 #include <stdlib.h>
23 #include <stdio.h>
24 #include <string.h>
25 #include <errno.h>
26 #include <limits.h>
27 #include <dir.h>
28
29 #ifdef DJGPP
30 #include <go32.h>
31 #include <sys/farptr.h>
32 #endif
33
34 #include "allegro.h"
35 #include "internal.h"
36
37
38
39 /* dummy functions for the nosound drivers */
40 int  _dummy_detect() { return TRUE; }
41 int  _dummy_init(int voices) { return 0; }
42 void _dummy_exit() { }
43 int  _dummy_mixer_volume(int volume) { return 0; }
44 void _dummy_init_voice(int voice, SAMPLE *sample) { }
45 void _dummy_noop1(int p) { }
46 void _dummy_noop2(int p1, int p2) { }
47 void _dummy_noop3(int p1, int p2, int p3) { }
48 int  _dummy_get_position(int voice) { return -1; }
49 int  _dummy_get(int voice) { return 0; }
50 void _dummy_raw_midi(unsigned char data) { }
51 int  _dummy_load_patches(char *patches, char *drums) { return 0; }
52 void _dummy_adjust_patches(char *patches, char *drums) { }
53 void _dummy_key_on(int inst, int note, int bend, int vol, int pan) { }
54
55 /* put this after all the dummy functions, so they will all get locked */
56 END_OF_FUNCTION(_dummy_detect); 
57
58
59
60 DIGI_DRIVER digi_none =
61 {
62    "No sound", "The sound of silence",
63    0, 0, 0xFFFF, 0,
64    _dummy_detect,
65    _dummy_init,
66    _dummy_exit,
67    _dummy_mixer_volume,
68    _dummy_init_voice,
69    _dummy_noop1,
70    _dummy_noop1,
71    _dummy_noop1,
72    _dummy_noop2,
73    _dummy_get_position,
74    _dummy_noop2,
75    _dummy_get,
76    _dummy_noop2,
77    _dummy_noop3,
78    _dummy_noop1,
79    _dummy_get,
80    _dummy_noop2,
81    _dummy_noop3,
82    _dummy_noop1,
83    _dummy_get,
84    _dummy_noop2,
85    _dummy_noop3,
86    _dummy_noop1,
87    _dummy_noop3,
88    _dummy_noop3,
89    _dummy_noop3
90 };
91
92
93 MIDI_DRIVER midi_none =
94 {
95    "No sound", "The sound of silence",
96    0, 0, 0xFFFF, 0, -1, -1,
97    _dummy_detect,
98    _dummy_init,
99    _dummy_exit,
100    _dummy_mixer_volume,
101    _dummy_raw_midi,
102    _dummy_load_patches,
103    _dummy_adjust_patches,
104    _dummy_key_on,
105    _dummy_noop1,
106    _dummy_noop2,
107    _dummy_noop3,
108    _dummy_noop2,
109    _dummy_noop2
110 };
111
112
113 int digi_card = DIGI_AUTODETECT;          /* current driver ID numbers */
114 int midi_card = MIDI_AUTODETECT;
115
116 DIGI_DRIVER *digi_driver = &digi_none;    /* these things do all the work */
117 MIDI_DRIVER *midi_driver = &midi_none;
118
119 static int sound_installed = FALSE;       /* are we installed? */
120
121 static int digi_reserve = -1;             /* how many voices to reserve */
122 static int midi_reserve = -1;
123
124 VOICE _voice[VIRTUAL_VOICES];             /* list of active samples */
125
126 PHYS_VOICE _phys_voice[DIGI_VOICES];      /* physical -> virtual voice map */
127
128 int _digi_volume = -1;                    /* current volume settings */
129 int _midi_volume = -1;
130
131 int _flip_pan = FALSE;                    /* reverse l/r sample panning? */
132
133 int _sb_freq = -1;                        /* hardware parameters */
134 int _sb_port = -1;
135 int _sb_dma = -1;
136 int _sb_irq = -1;
137 int _fm_port = -1;
138 int _mpu_port = -1;
139
140 #define SWEEP_FREQ   50
141
142 static void update_sweeps();
143 static void sound_lock_mem();
144
145 int (*_midi_init)() = NULL;
146 void (*_midi_exit)() = NULL;
147
148
149
150 /* read_sound_config:
151  *  Helper for reading the sound hardware configuration data.
152  */
153 static void read_sound_config()
154 {
155    _flip_pan = get_config_int("sound", "flip_pan", FALSE);
156    _sb_port = get_config_hex("sound", "sb_port", -1);
157    _sb_dma = get_config_int("sound", "sb_dma", -1);
158    _sb_irq = get_config_int("sound", "sb_irq", -1);
159    _sb_freq = get_config_int("sound", "sb_freq", -1);
160    _fm_port = get_config_hex("sound", "fm_port", -1);
161    _mpu_port = get_config_hex("sound", "mpu_port", -1);
162    _digi_volume = get_config_int("sound", "digi_volume", -1);
163    _midi_volume = get_config_int("sound", "midi_volume", -1);
164 }
165
166
167
168 /* detect_digi_driver:
169  *  Detects whether the specified digital sound driver is available,
170  *  returning the maximum number of voices that it can provide, or
171  *  zero if the device is not present. This function must be called
172  *  _before_ install_sound().
173  */
174 int detect_digi_driver(int driver_id)
175 {
176    int i;
177
178    if (sound_installed)
179       return 0;
180
181    read_sound_config();
182
183    for (i=0; _digi_driver_list[i].driver_id; i++) {
184       if (_digi_driver_list[i].driver_id == driver_id) {
185          digi_card = driver_id;
186          midi_card = MIDI_AUTODETECT;
187          if (_digi_driver_list[i].driver->detect())
188             return _digi_driver_list[i].driver->max_voices;
189          else
190             return 0;
191       }
192    }
193
194    return digi_none.max_voices;
195 }
196
197
198
199 /* detect_midi_driver:
200  *  Detects whether the specified midi sound driver is available,
201  *  returning the maximum number of voices that it can provide, or
202  *  zero if the device is not present. If this routine returns -1,
203  *  it is a note-stealing MIDI driver, which shares voices with the
204  *  current digital driver. In this situation you can use the 
205  *  reserve_voices() function to specify how the available voices are
206  *  divided between the digital and MIDI playback routines. This function
207  *  must be called _before_ install_sound().
208  */
209 int detect_midi_driver(int driver_id)
210 {
211    int i;
212
213    if (sound_installed)
214       return 0;
215
216    read_sound_config();
217
218    for (i=0; _midi_driver_list[i].driver_id; i++) {
219       if (_midi_driver_list[i].driver_id == driver_id) {
220          digi_card = DIGI_AUTODETECT;
221          midi_card = driver_id;
222          if (_midi_driver_list[i].driver->detect())
223             return _midi_driver_list[i].driver->max_voices;
224          else
225             return 0;
226       }
227    }
228
229    return midi_none.max_voices;
230 }
231
232
233
234 /* reserve_voices:
235  *  Reserves a number of voices for the digital and MIDI sound drivers
236  *  respectively. This must be called _before_ install_sound(). If you 
237  *  attempt to reserve too many voices, subsequent calls to install_sound()
238  *  will fail. Note that depending on the driver you may actually get 
239  *  more voices than you reserve: these values just specify the minimum
240  *  that is appropriate for your application. Pass a negative reserve value 
241  *  to use the default settings.
242  */
243 void reserve_voices(int digi_voices, int midi_voices)
244 {
245    digi_reserve = digi_voices;
246    midi_reserve = midi_voices;
247 }
248
249
250
251 /* install_sound:
252  *  Initialises the sound module, returning zero on success. The two card 
253  *  parameters should use the DIGI_* and MIDI_* constants defined in 
254  *  allegro.h. Pass DIGI_AUTODETECT and MIDI_AUTODETECT if you don't know 
255  *  what the soundcard is.
256  */
257 int install_sound(int digi, int midi, char *cfg_path)
258 {
259    int digi_voices, midi_voices;
260    int c;
261
262    if (sound_installed)
263       return 0;
264
265    for (c=0; c<VIRTUAL_VOICES; c++) {
266       _voice[c].sample = NULL;
267       _voice[c].num = -1;
268    }
269
270    for (c=0; c<DIGI_VOICES; c++)
271       _phys_voice[c].num = -1;
272
273    /* initialise the midi file player */
274    if (_midi_init)
275       if (_midi_init() != 0)
276          return -1;
277
278 /*       register_datafile_object(DAT_SAMPLE, NULL, (void (*)(void *))destroy_sample);*/
279
280    digi_card = digi;
281    midi_card = midi;
282
283    /* read config information */
284    if (digi_card == DIGI_AUTODETECT)
285       digi_card = get_config_int("sound", "digi_card", DIGI_AUTODETECT);
286
287    if (midi_card == MIDI_AUTODETECT)
288       midi_card = get_config_int("sound", "midi_card", MIDI_AUTODETECT);
289
290    if (digi_reserve < 0)
291       digi_reserve = get_config_int("sound", "digi_voices", -1);
292
293    if (midi_reserve < 0)
294       midi_reserve = get_config_int("sound", "midi_voices", -1);
295
296    read_sound_config();
297
298    sound_lock_mem();
299    _dma_lock_mem();
300
301    digi_driver = NULL;
302
303    /* search table for a specific digital driver */
304    for (c=0; _digi_driver_list[c].driver; c++) { 
305       if (_digi_driver_list[c].driver_id == digi_card) {
306          digi_driver = _digi_driver_list[c].driver;
307          if (!digi_driver->detect()) {
308             digi_driver = &digi_none; 
309             if (_midi_exit)
310                _midi_exit();
311             return -1;
312          }
313          break;
314       }
315    }
316
317    /* autodetect digital driver */
318    if (!digi_driver) {
319       for (c=0; _digi_driver_list[c].driver; c++) {
320          digi_card = _digi_driver_list[c].driver_id;
321          if ((_digi_driver_list[c].autodetect) &&
322              (_digi_driver_list[c].driver->detect())) {
323             digi_driver = _digi_driver_list[c].driver;
324             break;
325          }
326       }
327    }
328
329    midi_driver = NULL;
330
331    /* search table for a specific MIDI driver */
332    for (c=0; _midi_driver_list[c].driver; c++) { 
333       if (_midi_driver_list[c].driver_id == midi_card) {
334          midi_driver = _midi_driver_list[c].driver;
335          if (!midi_driver->detect()) {
336             digi_driver = &digi_none; 
337             midi_driver = &midi_none; 
338             if (_midi_exit)
339                _midi_exit();
340             return -1;
341          }
342          break;
343       }
344    }
345
346    /* autodetect MIDI driver */
347    if (!midi_driver) {
348       for (c=0; _midi_driver_list[c].driver; c++) {
349          midi_card = _midi_driver_list[c].driver_id;
350          if ((_midi_driver_list[c].autodetect) &&
351              (_midi_driver_list[c].driver->detect())) {
352             midi_driver = _midi_driver_list[c].driver;
353             break;
354          }
355       }
356    }
357
358    /* work out how many voices to allocate for each driver */
359    if (digi_reserve >= 0)
360       digi_voices = digi_reserve;
361    else
362       digi_voices = digi_driver->def_voices;
363
364    if (midi_driver->max_voices < 0) {
365       /* MIDI driver steals voices from the digital player */
366       if (midi_reserve >= 0)
367          midi_voices = midi_reserve;
368       else
369          midi_voices = MID(0, digi_driver->max_voices - digi_voices, midi_driver->def_voices);
370
371       digi_voices += midi_voices;
372    }
373    else {
374       /* MIDI driver has voices of its own */
375       if (midi_reserve >= 0)
376          midi_voices = midi_reserve;
377       else
378          midi_voices = midi_driver->def_voices;
379    }
380
381    /* make sure this is a reasonable number of voices to use */
382    if ((digi_voices > DIGI_VOICES) || (midi_voices > MIDI_VOICES)) {
383       sprintf(allegro_error, "Insufficient %s voices available", 
384                   (digi_voices > DIGI_VOICES) ? "digital" : "MIDI");
385       digi_driver = &digi_none; 
386       midi_driver = &midi_none; 
387       if (_midi_exit)
388          _midi_exit();
389       return -1;
390    }
391
392    /* initialise the digital sound driver */
393    if (digi_driver->init(digi_voices) != 0) {
394       digi_driver = &digi_none; 
395       midi_driver = &midi_none; 
396       if (_midi_exit)
397          _midi_exit();
398       return -1;
399    }
400
401    /* initialise the midi driver */
402    if (midi_driver->init(midi_voices) != 0) {
403       digi_driver->exit();
404       digi_driver = &digi_none; 
405       midi_driver = &midi_none; 
406       if (_midi_exit)
407          _midi_exit();
408       return -1;
409    }
410
411    digi_driver->voices = MIN(digi_driver->voices, DIGI_VOICES);
412    midi_driver->voices = MIN(midi_driver->voices, MIDI_VOICES);
413
414    /* check that we actually got enough voices */
415    if ((digi_driver->voices < digi_voices) ||
416        ((midi_driver->voices < midi_voices) && (!midi_driver->raw_midi))) {
417       sprintf(allegro_error, "Insufficient %s voices available", 
418                   (digi_driver->voices < digi_voices) ? "digital" : "MIDI");
419       midi_driver->exit();
420       digi_driver->exit();
421       digi_driver = &digi_none; 
422       midi_driver = &midi_none; 
423       if (_midi_exit)
424          _midi_exit();
425       return -1;
426    }
427
428    /* adjust for note-stealing MIDI drivers */
429    if (midi_driver->max_voices < 0) {
430       midi_voices += (digi_driver->voices - digi_voices) * 3/4;
431       digi_driver->voices -= midi_voices;
432       midi_driver->basevoice = VIRTUAL_VOICES - midi_voices;
433       midi_driver->voices = midi_voices;
434
435       for (c=0; c<midi_voices; c++) {
436          _voice[midi_driver->basevoice+c].num = digi_driver->voices+c;
437          _phys_voice[digi_driver->voices+c].num = midi_driver->basevoice+c;
438       }
439    }
440
441    /* simulate ramp/sweep effects for drivers that don't do it directly */
442    if ((!digi_driver->ramp_volume) ||
443        (!digi_driver->sweep_frequency) ||
444        (!digi_driver->sweep_pan))
445       install_int_ex(update_sweeps, BPS_TO_TIMER(SWEEP_FREQ));
446
447    /* set the global sound volume */
448    if ((_digi_volume >= 0) || (_midi_volume >= 0))
449       set_volume(_digi_volume, _midi_volume);
450
451    _add_exit_func(remove_sound);
452    sound_installed = TRUE;
453    return 0;
454 }
455
456
457
458 /* remove_sound:
459  *  Sound module cleanup routine.
460  */
461 void remove_sound()
462 {
463    int c;
464
465    if (sound_installed) {
466       remove_int(update_sweeps);
467
468       for (c=0; c<VIRTUAL_VOICES; c++)
469          if (_voice[c].sample)
470             deallocate_voice(c);
471
472       if (_midi_exit)
473          _midi_exit();
474
475       midi_driver->exit();
476       midi_driver = &midi_none; 
477
478       digi_driver->exit();
479       digi_driver = &digi_none; 
480
481       _remove_exit_func(remove_sound);
482       sound_installed = FALSE;
483    }
484 }
485
486
487
488 /* set_volume:
489  *  Alters the global sound output volume. Specify volumes for both digital
490  *  samples and MIDI playback, as integers from 0 to 255. If possible this
491  *  routine will use a hardware mixer to control the volume, otherwise it
492  *  will tell the sample mixer and MIDI player to simulate a mixer in
493  *  software.
494  */
495 void set_volume(int digi_volume, int midi_volume)
496 {
497    if (digi_volume >= 0) {
498       digi_volume = MID(0, digi_volume, 255);
499
500       if ((digi_driver->mixer_volume) && 
501           (digi_driver->mixer_volume(digi_volume) == 0))
502          _digi_volume = -1;
503       else
504          _digi_volume = digi_volume;
505    }
506
507    if (midi_volume >= 0) {
508       midi_volume = MID(0, midi_volume, 255);
509
510       if ((midi_driver->mixer_volume) && 
511           (midi_driver->mixer_volume(midi_volume) == 0))
512          _midi_volume = -1;
513       else
514          _midi_volume = midi_volume;
515    }
516 }
517
518
519
520 /* lock_sample:
521  *  Locks a SAMPLE struct into physical memory. Pretty important, since 
522  *  they are mostly accessed inside interrupt handlers.
523  */
524 void lock_sample(SAMPLE *spl)
525 {
526    #ifdef DJGPP
527       _go32_dpmi_lock_data(spl, sizeof(SAMPLE));
528       _go32_dpmi_lock_data(spl->data, spl->len*spl->bits/8);
529    #endif
530 }
531
532
533
534 /* load_sample:
535  *  Loads a sample from disk.
536  */
537 SAMPLE *load_sample(char *filename)
538 {
539    if (stricmp(get_extension(filename), "wav") == 0)
540       return load_wav(filename);
541    else if (stricmp(get_extension(filename), "voc") == 0)
542       return load_voc(filename);
543    else
544       return NULL;
545 }
546
547
548
549 /* load_voc:
550  *  Reads a mono 8 bit VOC format sample file, returning a SAMPLE structure, 
551  *  or NULL on error.
552  */
553 SAMPLE *load_voc(char *filename)
554 {
555    PACKFILE *f;
556    char buffer[30];
557    int freq = 22050;
558    int bits = 8;
559    SAMPLE *spl = NULL;
560    int len;
561    int x;
562
563    f = pack_fopen(filename, F_READ);
564    if (!f) 
565       return NULL;
566
567    pack_fread(buffer, 0x16, f);
568
569    if (memcmp(buffer, "Creative Voice File", 0x13))
570       goto getout;
571
572    if (pack_igetw(f) != 0x010A)        /* version: should be 0x010A */
573       goto getout;
574
575    if (pack_igetw(f) != 0x1129)        /* subversion: should be 0x1129 */
576       goto getout;
577
578    if (pack_getc(f) != 0x01)           /* sound data: should be 0x01 */
579       goto getout;
580
581    len = pack_igetw(f);                /* length is three bytes long: two */
582    x = pack_getc(f);                   /* .. and one byte */
583    x <<= 16;
584    len += x-2;
585
586    x = pack_getc(f);                   /* one byte of frequency */
587    freq = 1000000 / (256-x);
588
589    x = pack_getc(f);                   /* skip one byte */
590
591    spl = malloc(sizeof(SAMPLE));
592
593    if (spl) {
594       spl->bits = bits;
595       spl->freq = freq;
596       spl->len = len;
597       spl->priority = 255;
598       spl->loop_start = 0;
599       spl->loop_end = len;
600       spl->param = -1;
601
602       spl->data = malloc(len);
603       if (!spl->data) {
604          free(spl);
605          spl = NULL;
606       }
607       else {
608          pack_fread(spl->data, len, f);
609          if (errno) {
610             free(spl->data);
611             free(spl);
612             spl = NULL;
613          }
614       }
615    }
616
617    getout: 
618
619    pack_fclose(f);
620
621    if (spl)
622       lock_sample(spl);
623
624    return spl;
625 }
626
627
628
629 /* load_wav:
630  *  Reads a mono RIFF WAV format sample file, returning a SAMPLE structure, 
631  *  or NULL on error.
632  */
633 SAMPLE *load_wav(char *filename)
634 {
635    int trashtmp;
636    PACKFILE *f;
637    char buffer[25];
638    int i;
639    int length, len;
640    int freq = 22050;
641    int bits = 8;
642    signed short s;
643    SAMPLE *spl = NULL;
644
645    f = pack_fopen(filename, F_READ);
646    if (!f)
647       return NULL;
648
649    pack_fread(buffer, 12, f);          /* check RIFF header */
650    if (memcmp(buffer, "RIFF", 4) || memcmp(buffer+8, "WAVE", 4))
651       goto getout;
652
653    while (!pack_feof(f)) {
654       if (pack_fread(buffer, 4, f) != 4)
655          break;
656
657       length = pack_igetl(f);          /* read chunk length */
658
659       if (memcmp(buffer, "fmt ", 4) == 0) {
660          i = pack_igetw(f);            /* should be 1 for PCM data */
661          length -= 2;
662          if (i != 1) 
663             goto getout;
664
665          i = pack_igetw(f);            /* should be 1 for mono data */
666          length -= 2;
667          if (i != 1)
668             goto getout;
669
670          freq = pack_igetl(f);         /* sample frequency */
671          length -= 4;
672
673          trashtmp=pack_igetl(f);                /* skip six bytes */
674          trashtmp=pack_igetw(f);
675          length -= 6;
676
677          bits = pack_igetw(f);         /* 8 or 16 bit data? */
678          length -= 2;
679          if ((bits != 8) && (bits != 16))
680             goto getout;
681       }
682       else if (memcmp(buffer, "data", 4) == 0) {
683          len = length;
684          if (bits == 16)
685             len /= 2;
686
687          spl = malloc(sizeof(SAMPLE)); 
688
689          if (spl) {                    /* initialise the sample struct */
690             spl->bits = bits;
691             spl->freq = freq;
692             spl->len = len;
693             spl->priority = 255;
694             spl->loop_start = 0;
695             spl->loop_end = len;
696             spl->param = -1;
697
698             spl->data = malloc(length);
699
700             if (!spl->data) {
701                free(spl);
702                spl = NULL;
703             }
704             else {                     /* read the actual sample data */
705                if (bits == 8) {
706                   pack_fread(spl->data, length, f);
707                }
708                else {
709                   for (i=0; i<len; i++) {
710                      s = pack_igetw(f);
711                      ((signed short *)spl->data)[i] = s^0x8000;
712                   }
713                }
714
715                length -= len;
716
717                if (errno) {
718                   free(spl->data);
719                   free(spl);
720                   spl = NULL;
721                }
722             }
723          }
724       }
725
726       while (length > 0) {             /* skip the remainder of the chunk */
727          if (pack_getc(f) == EOF)
728             break;
729
730          length--;
731       }
732    }
733
734    getout:
735
736    pack_fclose(f);
737
738    if (spl)
739       lock_sample(spl);
740
741    return spl;
742 }
743
744
745
746 /* destroy_sample:
747  *  Frees a SAMPLE struct, checking whether the sample is currently playing, 
748  *  and stopping it if it is.
749  */
750 void destroy_sample(SAMPLE *spl)
751 {
752    if (spl) {
753       stop_sample(spl);
754
755       if (spl->data) {
756          _unlock_dpmi_data(spl->data, spl->len*spl->bits/8);
757          free(spl->data);
758       }
759
760       _unlock_dpmi_data(spl, sizeof(SAMPLE));
761       free(spl);
762    }
763 }
764
765
766
767 /* absolute_freq:
768  *  Converts a pitch from the relative 1000 = original format to an absolute
769  *  value in hz.
770  */
771 static inline int absolute_freq(int freq, SAMPLE *spl)
772 {
773    if (freq == 1000)
774       return spl->freq;
775    else
776       return (spl->freq * freq) / 1000;
777 }
778
779
780
781 /* play_sample:
782  *  Triggers a sample at the specified volume, pan position, and frequency.
783  *  The volume and pan range from 0 (min/left) to 255 (max/right), although
784  *  the resolution actually used by the playback routines is likely to be
785  *  less than this. Frequency is relative rather than absolute: 1000 
786  *  represents the frequency that the sample was recorded at, 2000 is 
787  *  twice this, etc. If loop is true the sample will repeat until you call 
788  *  stop_sample(), and can be manipulated while it is playing by calling
789  *  adjust_sample().
790  */
791 int play_sample(SAMPLE *spl, int vol, int pan, int freq, int loop)
792 {
793    int voice = allocate_voice(spl);
794
795    if (voice >= 0) {
796       voice_set_volume(voice, vol);
797       voice_set_pan(voice, pan);
798       voice_set_frequency(voice, absolute_freq(freq, spl));
799       voice_set_playmode(voice, (loop ? PLAYMODE_LOOP : PLAYMODE_PLAY));
800       voice_start(voice);
801       release_voice(voice);
802    }
803
804    return voice;
805 }
806
807 END_OF_FUNCTION(play_sample);
808
809
810
811 /* adjust_sample:
812  *  Alters the parameters of a sample while it is playing, useful for
813  *  manipulating looped sounds. You can alter the volume, pan, and
814  *  frequency, and can also remove the looping flag, which will stop
815  *  the sample when it next reaches the end of its loop. If there are
816  *  several copies of the same sample playing, this will adjust the
817  *  first one it comes across. If the sample is not playing it has no
818  *  effect.
819  */
820 void adjust_sample(SAMPLE *spl, int vol, int pan, int freq, int loop)
821 {
822    int c;
823
824    for (c=0; c<VIRTUAL_VOICES; c++) { 
825       if (_voice[c].sample == spl) {
826          voice_set_volume(c, vol);
827          voice_set_pan(c, pan);
828          voice_set_frequency(c, absolute_freq(freq, spl));
829          voice_set_playmode(c, (loop ? PLAYMODE_LOOP : PLAYMODE_PLAY));
830          return;
831       }
832    }
833 }
834
835 END_OF_FUNCTION(adjust_sample);
836
837
838
839 /* stop_sample:
840  *  Kills off a sample, which is required if you have set a sample going 
841  *  in looped mode. If there are several copies of the sample playing,
842  *  it will stop them all.
843  */
844 void stop_sample(SAMPLE *spl)
845 {
846    int c;
847
848    for (c=0; c<VIRTUAL_VOICES; c++)
849       if (_voice[c].sample == spl)
850          deallocate_voice(c);
851 }
852
853 END_OF_FUNCTION(stop_sample);
854
855
856
857 /* allocate_physical_voice:
858  *  Allocates a physical voice, killing off others as required in order
859  *  to make room for it.
860  */
861 static inline int allocate_physical_voice(int priority)
862 {
863    VOICE *voice;
864    int best = -1;
865    int best_score = 0;
866    int score;
867    int c;
868
869    /* look for a free voice */
870    for (c=0; c<digi_driver->voices; c++)
871       if (_phys_voice[c].num < 0)
872          return c;
873
874    /* look for an autokill voice that has stopped */
875    for (c=0; c<digi_driver->voices; c++) {
876       voice = _voice + _phys_voice[c].num;
877       if ((voice->autokill) && (digi_driver->get_position(c) < 0)) {
878          digi_driver->release_voice(c);
879          voice->sample = NULL;
880          voice->num = -1;
881          _phys_voice[c].num = -1;
882          return c;
883       }
884    }
885
886    /* ok, we're going to have to get rid of something to make room... */
887    for (c=0; c<digi_driver->voices; c++) {
888       voice = _voice + _phys_voice[c].num;
889
890       /* sort by voice priorities */
891       if (voice->priority <= priority) {
892          score = 65536 - voice->priority * 256;
893
894          /* bias with a least-recently-used counter */
895          score += MID(0, retrace_count - voice->time, 32768);
896
897          /* bias according to whether the voice is looping or not */
898          if (!(_phys_voice[c].playmode & PLAYMODE_LOOP))
899             score += 32768;
900
901          if (score > best_score) {
902             best = c;
903             best_score = score;
904          }
905       }
906    }
907
908    if (best >= 0) {
909       /* kill off the old voice */
910       digi_driver->stop_voice(best);
911       digi_driver->release_voice(best);
912       _voice[_phys_voice[best].num].num = -1;
913       _phys_voice[best].num = -1;
914       return best;
915    }
916
917    return -1;
918 }
919
920
921
922 /* allocate_virtual_voice:
923  *  Allocates a virtual voice. This doesn't need to worry about killing off 
924  *  others to make room, as we allow up to 256 virtual voices to be used
925  *  simultaneously.
926  */
927 static inline int allocate_virtual_voice()
928 {
929    int virt_voices, c;
930
931    virt_voices = VIRTUAL_VOICES;
932    if (midi_driver->max_voices < 0)
933       virt_voices -= midi_driver->voices;
934
935    /* look for a free voice */
936    for (c=0; c<virt_voices; c++)
937       if (!_voice[c].sample)
938          return c;
939
940    /* look for a stopped autokill voice */
941    for (c=0; c<virt_voices; c++) {
942       if (_voice[c].autokill) {
943          if (_voice[c].num < 0) {
944             _voice[c].sample = NULL;
945             return c;
946          }
947          else {
948             if (digi_driver->get_position(_voice[c].num) < 0) {
949                digi_driver->release_voice(_voice[c].num);
950                _phys_voice[_voice[c].num].num = -1;
951                _voice[c].sample = NULL;
952                _voice[c].num = -1;
953                return c;
954             }
955          }
956       }
957    }
958
959    return -1;
960 }
961
962
963
964 /* allocate_voice:
965  *  Allocates a voice ready for playing the specified sample, returning
966  *  the voice number (note this is not the same as the physical voice
967  *  number used by the sound drivers, and must only be used with the other
968  *  voice functions, _not_ passed directly to the driver routines).
969  *  Returns -1 if there is no voice available (this should never happen,
970  *  since there are 256 virtual voices and anyone who needs more than that
971  *  needs some urgent repairs to their brain :-)
972  */
973 int allocate_voice(SAMPLE *spl)
974 {
975    int phys = allocate_physical_voice(spl->priority);
976    int virt = allocate_virtual_voice();
977
978    if (virt >= 0) {
979       _voice[virt].sample = spl;
980       _voice[virt].num = phys;
981       _voice[virt].autokill = FALSE;
982       _voice[virt].time = retrace_count;
983       _voice[virt].priority = spl->priority;
984
985       if (phys >= 0) {
986          _phys_voice[phys].num = virt;
987          _phys_voice[phys].playmode = 0;
988          _phys_voice[phys].vol = ((_digi_volume >= 0) ? _digi_volume : 255) << 12;
989          _phys_voice[phys].pan = 128 << 12;
990          _phys_voice[phys].freq = spl->freq << 12;
991          _phys_voice[phys].dvol = 0;
992          _phys_voice[phys].dpan = 0;
993          _phys_voice[phys].dfreq = 0;
994
995          digi_driver->init_voice(phys, spl);
996       }
997    }
998
999    return virt;
1000 }
1001
1002 END_OF_FUNCTION(allocate_voice);
1003
1004
1005
1006 /* deallocate_voice:
1007  *  Releases a voice that was previously returned by allocate_voice().
1008  */
1009 void deallocate_voice(int voice)
1010 {
1011    if (_voice[voice].num >= 0) {
1012       digi_driver->stop_voice(_voice[voice].num);
1013       digi_driver->release_voice(_voice[voice].num);
1014       _phys_voice[_voice[voice].num].num = -1;
1015       _voice[voice].num = -1;
1016    }
1017
1018    _voice[voice].sample = NULL;
1019 }
1020
1021 END_OF_FUNCTION(deallocate_voice);
1022
1023
1024
1025 /* reallocate_voice:
1026  *  Switches an already-allocated voice to use a different sample.
1027  */
1028 void reallocate_voice(int voice, SAMPLE *spl)
1029 {
1030    int phys = _voice[voice].num;
1031
1032    if (phys >= 0) {
1033       digi_driver->stop_voice(phys);
1034       digi_driver->release_voice(phys);
1035    }
1036
1037    _voice[voice].sample = spl;
1038    _voice[voice].autokill = FALSE;
1039    _voice[voice].time = retrace_count;
1040    _voice[voice].priority = spl->priority;
1041
1042    if (phys >= 0) {
1043       _phys_voice[phys].playmode = 0;
1044       _phys_voice[phys].vol = ((_digi_volume >= 0) ? _digi_volume : 255) << 12;
1045       _phys_voice[phys].pan = 128 << 12;
1046       _phys_voice[phys].freq = spl->freq << 12;
1047       _phys_voice[phys].dvol = 0;
1048       _phys_voice[phys].dpan = 0;
1049       _phys_voice[phys].dfreq = 0;
1050
1051       digi_driver->init_voice(phys, spl);
1052    }
1053 }
1054
1055 END_OF_FUNCTION(reallocate_voice);
1056
1057
1058
1059 /* release_voice:
1060  *  Flags that a voice is no longer going to be updated, so it can 
1061  *  automatically be freed as soon as the sample finishes playing.
1062  */
1063 void release_voice(int voice)
1064 {
1065    _voice[voice].autokill = TRUE;
1066 }
1067
1068 END_OF_FUNCTION(release_voice);
1069
1070
1071
1072 /* voice_start:
1073  *  Starts a voice playing.
1074  */
1075 void voice_start(int voice)
1076 {
1077    if (_voice[voice].num >= 0)
1078       digi_driver->start_voice(_voice[voice].num);
1079
1080    _voice[voice].time = retrace_count;
1081 }
1082
1083 END_OF_FUNCTION(voice_start);
1084
1085
1086
1087 /* voice_stop:
1088  *  Stops a voice from playing.
1089  */
1090 void voice_stop(int voice)
1091 {
1092    if (_voice[voice].num >= 0)
1093       digi_driver->stop_voice(_voice[voice].num);
1094 }
1095
1096 END_OF_FUNCTION(voice_stop);
1097
1098
1099
1100 /* voice_set_priority:
1101  *  Adjusts the priority of a voice (0-255).
1102  */
1103 void voice_set_priority(int voice, int priority)
1104 {
1105    _voice[voice].priority = priority;
1106 }
1107
1108 END_OF_FUNCTION(voice_set_priority);
1109
1110
1111
1112 /* voice_check:
1113  *  Checks whether a voice is playing, returning the sample if it is,
1114  *  or NULL if it has finished or been preempted by a different sound.
1115  */
1116 SAMPLE *voice_check(int voice)
1117 {
1118    if (_voice[voice].sample) {
1119       if (_voice[voice].num < 0)
1120          return NULL;
1121
1122       if (_voice[voice].autokill)
1123          if (voice_get_position(voice) < 0)
1124             return NULL;
1125
1126       return _voice[voice].sample;
1127    }
1128    else
1129       return NULL;
1130 }
1131
1132 END_OF_FUNCTION(voice_check);
1133
1134
1135
1136 /* voice_get_position:
1137  *  Returns the current play position of a voice, or -1 if that cannot
1138  *  be determined (because it has finished or been preempted by a
1139  *  different sound).
1140  */
1141 int voice_get_position(int voice)
1142 {
1143    if (_voice[voice].num >= 0)
1144       return digi_driver->get_position(_voice[voice].num);
1145    else
1146       return -1;
1147 }
1148
1149 END_OF_FUNCTION(voice_get_position);
1150
1151
1152
1153 /* voice_set_position:
1154  *  Sets the play position of a voice.
1155  */
1156 void voice_set_position(int voice, int position)
1157 {
1158    if (_voice[voice].num >= 0)
1159       digi_driver->set_position(_voice[voice].num, position);
1160 }
1161
1162 END_OF_FUNCTION(voice_set_position);
1163
1164
1165
1166 /* voice_set_playmode:
1167  *  Sets the loopmode of a voice.
1168  */
1169 void voice_set_playmode(int voice, int playmode)
1170 {
1171    if (_voice[voice].num >= 0) {
1172       _phys_voice[_voice[voice].num].playmode = playmode;
1173       digi_driver->loop_voice(_voice[voice].num, playmode);
1174
1175       if (playmode & PLAYMODE_BACKWARD)
1176          digi_driver->set_position(_voice[voice].num, _voice[voice].sample->len-1);
1177    }
1178 }
1179
1180 END_OF_FUNCTION(voice_set_playmode);
1181
1182
1183
1184 /* voice_get_volume:
1185  *  Returns the current volume of a voice, or -1 if that cannot
1186  *  be determined (because it has finished or been preempted by a
1187  *  different sound).
1188  */
1189 int voice_get_volume(int voice)
1190 {
1191    int vol;
1192
1193    if (_voice[voice].num >= 0)
1194       vol = digi_driver->get_volume(_voice[voice].num);
1195    else
1196       vol = -1;
1197
1198    if ((vol >= 0) && (_digi_volume >= 0)) {
1199       if (_digi_volume > 0)
1200          vol = MID(0, (vol * 255) / _digi_volume, 255);
1201       else
1202          vol = 0;
1203    }
1204
1205    return vol;
1206 }
1207
1208 END_OF_FUNCTION(voice_get_volume);
1209
1210
1211
1212 /* voice_set_volume:
1213  *  Sets the current volume of a voice.
1214  */
1215 void voice_set_volume(int voice, int volume)
1216 {
1217    if (_digi_volume >= 0)
1218       volume = (volume * _digi_volume) / 255;
1219
1220    if (_voice[voice].num >= 0) {
1221       _phys_voice[_voice[voice].num].vol = volume << 12;
1222       _phys_voice[_voice[voice].num].dvol = 0;
1223
1224       digi_driver->set_volume(_voice[voice].num, volume);
1225    }
1226 }
1227
1228 END_OF_FUNCTION(voice_set_volume);
1229
1230
1231
1232 /* voice_ramp_volume:
1233  *  Begins a volume ramp operation.
1234  */
1235 void voice_ramp_volume(int voice, int time, int endvol)
1236 {
1237    if (_digi_volume >= 0)
1238       endvol = (endvol * _digi_volume) / 255;
1239
1240    if (_voice[voice].num >= 0) {
1241       if (digi_driver->ramp_volume) {
1242          digi_driver->ramp_volume(_voice[voice].num, time, endvol);
1243       }
1244       else {
1245          int d = (endvol << 12) - _phys_voice[_voice[voice].num].vol;
1246          time = MAX(time * SWEEP_FREQ / 1000, 1);
1247          _phys_voice[_voice[voice].num].target_vol = endvol << 12;
1248          _phys_voice[_voice[voice].num].dvol = d / time;
1249       }
1250    }
1251 }
1252
1253 END_OF_FUNCTION(voice_ramp_volume);
1254
1255
1256
1257 /* voice_stop_volumeramp:
1258  *  Ends a volume ramp operation.
1259  */
1260 void voice_stop_volumeramp(int voice)
1261 {
1262    if (_voice[voice].num >= 0) {
1263       _phys_voice[_voice[voice].num].dvol = 0;
1264
1265       if (digi_driver->stop_volume_ramp)
1266          digi_driver->stop_volume_ramp(_voice[voice].num);
1267    }
1268 }
1269
1270 END_OF_FUNCTION(voice_stop_volumeramp);
1271
1272
1273
1274 /* voice_get_frequency:
1275  *  Returns the current frequency of a voice, or -1 if that cannot
1276  *  be determined (because it has finished or been preempted by a
1277  *  different sound).
1278  */
1279 int voice_get_frequency(int voice)
1280 {
1281    if (_voice[voice].num >= 0)
1282       return digi_driver->get_frequency(_voice[voice].num);
1283    else
1284       return -1;
1285 }
1286
1287 END_OF_FUNCTION(voice_get_frequency);
1288
1289
1290
1291 /* voice_set_frequency:
1292  *  Sets the pitch of a voice.
1293  */
1294 void voice_set_frequency(int voice, int frequency)
1295 {
1296    if (_voice[voice].num >= 0) {
1297       _phys_voice[_voice[voice].num].freq = frequency << 12;
1298       _phys_voice[_voice[voice].num].dfreq = 0;
1299
1300       digi_driver->set_frequency(_voice[voice].num, frequency);
1301    }
1302 }
1303
1304 END_OF_FUNCTION(voice_set_frequency);
1305
1306
1307
1308 /* voice_sweep_frequency:
1309  *  Begins a frequency sweep (glissando) operation.
1310  */
1311 void voice_sweep_frequency(int voice, int time, int endfreq)
1312 {
1313    if (_voice[voice].num >= 0) {
1314       if (digi_driver->sweep_frequency) {
1315          digi_driver->sweep_frequency(_voice[voice].num, time, endfreq);
1316       }
1317       else {
1318          int d = (endfreq << 12) - _phys_voice[_voice[voice].num].freq;
1319          time = MAX(time * SWEEP_FREQ / 1000, 1);
1320          _phys_voice[_voice[voice].num].target_freq = endfreq << 12;
1321          _phys_voice[_voice[voice].num].dfreq = d / time;
1322       }
1323    }
1324 }
1325
1326 END_OF_FUNCTION(voice_sweep_frequency);
1327
1328
1329
1330 /* voice_stop_frequency_sweep:
1331  *  Ends a frequency sweep.
1332  */
1333 void voice_stop_frequency_sweep(int voice)
1334 {
1335    if (_voice[voice].num >= 0) {
1336       _phys_voice[_voice[voice].num].dfreq = 0;
1337
1338       if (digi_driver->stop_frequency_sweep)
1339          digi_driver->stop_frequency_sweep(_voice[voice].num);
1340    }
1341 }
1342
1343 END_OF_FUNCTION(voice_stop_frequency_sweep);
1344
1345
1346
1347 /* voice_get_pan:
1348  *  Returns the current pan position of a voice, or -1 if that cannot
1349  *  be determined (because it has finished or been preempted by a
1350  *  different sound).
1351  */
1352 int voice_get_pan(int voice)
1353 {
1354    int pan;
1355
1356    if (_voice[voice].num >= 0)
1357       pan = digi_driver->get_pan(_voice[voice].num);
1358    else
1359       pan = -1;
1360
1361    if ((pan >= 0) && (_flip_pan))
1362       pan = 255 - pan;
1363
1364    return pan;
1365 }
1366
1367 END_OF_FUNCTION(voice_get_pan);
1368
1369
1370
1371 /* voice_set_pan:
1372  *  Sets the pan position of a voice.
1373  */
1374 void voice_set_pan(int voice, int pan)
1375 {
1376    if (_flip_pan)
1377       pan = 255 - pan;
1378
1379    if (_voice[voice].num >= 0) {
1380       _phys_voice[_voice[voice].num].pan = pan << 12;
1381       _phys_voice[_voice[voice].num].dpan = 0;
1382
1383       digi_driver->set_pan(_voice[voice].num, pan);
1384    }
1385 }
1386
1387 END_OF_FUNCTION(voice_set_pan);
1388
1389
1390
1391 /* voice_sweep_pan:
1392  *  Begins a pan sweep (left <-> right movement) operation.
1393  */
1394 void voice_sweep_pan(int voice, int time, int endpan)
1395 {
1396    if (_flip_pan)
1397       endpan = 255 - endpan;
1398
1399    if (_voice[voice].num >= 0) {
1400       if (digi_driver->sweep_pan) {
1401          digi_driver->sweep_pan(_voice[voice].num, time, endpan);
1402       }
1403       else {
1404          int d = (endpan << 12) - _phys_voice[_voice[voice].num].pan;
1405          time = MAX(time * SWEEP_FREQ / 1000, 1);
1406          _phys_voice[_voice[voice].num].target_pan = endpan << 12;
1407          _phys_voice[_voice[voice].num].dpan = d / time;
1408       }
1409    }
1410 }
1411
1412 END_OF_FUNCTION(voice_sweep_pan);
1413
1414
1415
1416 /* voice_stop_pan_sweep:
1417  *  Ends a pan sweep.
1418  */
1419 void voice_stop_pan_sweep(int voice)
1420 {
1421    if (_voice[voice].num >= 0) {
1422       _phys_voice[_voice[voice].num].dpan = 0;
1423
1424       if (digi_driver->stop_pan_sweep)
1425          digi_driver->stop_pan_sweep(_voice[voice].num);
1426    }
1427 }
1428
1429 END_OF_FUNCTION(voice_stop_pan_sweep);
1430
1431
1432
1433 /* voice_set_echo:
1434  *  Sets the echo parameters of a voice.
1435  */
1436 void voice_set_echo(int voice, int strength, int delay)
1437 {
1438    if ((_voice[voice].num >= 0) && (digi_driver->set_echo))
1439       digi_driver->set_echo(_voice[voice].num, strength, delay);
1440 }
1441
1442 END_OF_FUNCTION(voice_set_echo);
1443
1444
1445
1446 /* voice_set_tremolo:
1447  *  Sets the tremolo parameters of a voice.
1448  */
1449 void voice_set_tremolo(int voice, int rate, int depth)
1450 {
1451    if ((_voice[voice].num >= 0) && (digi_driver->set_tremolo))
1452       digi_driver->set_tremolo(_voice[voice].num, rate, depth);
1453 }
1454
1455 END_OF_FUNCTION(voice_set_tremolo);
1456
1457
1458
1459 /* voice_set_vibrato:
1460  *  Sets the vibrato parameters of a voice.
1461  */
1462 void voice_set_vibrato(int voice, int rate, int depth)
1463 {
1464    if ((_voice[voice].num >= 0) && (digi_driver->set_vibrato))
1465       digi_driver->set_vibrato(_voice[voice].num, rate, depth);
1466 }
1467
1468 END_OF_FUNCTION(voice_set_vibrato);
1469
1470
1471
1472 /* update_sweeps:
1473  *  Timer callback routine used to implement volume/frequency/pan sweep 
1474  *  effects, for those drivers that can't do them directly.
1475  */
1476 static void update_sweeps()
1477 {
1478    int phys_voices, i;
1479
1480    phys_voices = digi_driver->voices;
1481    if (midi_driver->max_voices < 0)
1482       phys_voices += midi_driver->voices;
1483
1484    for (i=0; i<phys_voices; i++) {
1485       if (_phys_voice[i].num >= 0) {
1486          /* update volume ramp */
1487          if ((!digi_driver->ramp_volume) && (_phys_voice[i].dvol)) {
1488             _phys_voice[i].vol += _phys_voice[i].dvol;
1489
1490             if (((_phys_voice[i].dvol > 0) && (_phys_voice[i].vol >= _phys_voice[i].target_vol)) ||
1491                 ((_phys_voice[i].dvol < 0) && (_phys_voice[i].vol <= _phys_voice[i].target_vol))) {
1492                _phys_voice[i].vol = _phys_voice[i].target_vol;
1493                _phys_voice[i].dvol = 0;
1494             }
1495
1496             digi_driver->set_volume(i, _phys_voice[i].vol >> 12);
1497          }
1498
1499          /* update frequency sweep */
1500          if ((!digi_driver->sweep_frequency) && (_phys_voice[i].dfreq)) {
1501             _phys_voice[i].freq += _phys_voice[i].dfreq;
1502
1503             if (((_phys_voice[i].dfreq > 0) && (_phys_voice[i].freq >= _phys_voice[i].target_freq)) ||
1504                 ((_phys_voice[i].dfreq < 0) && (_phys_voice[i].freq <= _phys_voice[i].target_freq))) {
1505                _phys_voice[i].freq = _phys_voice[i].target_freq;
1506                _phys_voice[i].dfreq = 0;
1507             }
1508
1509             digi_driver->set_frequency(i, _phys_voice[i].freq >> 12);
1510          }
1511
1512          /* update pan sweep */
1513          if ((!digi_driver->sweep_pan) && (_phys_voice[i].dpan)) {
1514             _phys_voice[i].pan += _phys_voice[i].dpan;
1515
1516             if (((_phys_voice[i].dpan > 0) && (_phys_voice[i].pan >= _phys_voice[i].target_pan)) ||
1517                 ((_phys_voice[i].dpan < 0) && (_phys_voice[i].pan <= _phys_voice[i].target_pan))) {
1518                _phys_voice[i].pan = _phys_voice[i].target_pan;
1519                _phys_voice[i].dpan = 0;
1520             }
1521
1522             digi_driver->set_pan(i, _phys_voice[i].pan >> 12);
1523          }
1524       }
1525    }
1526 }
1527
1528 static END_OF_FUNCTION(update_sweeps);
1529
1530
1531
1532 /* sound_lock_mem:
1533  *  Locks memory used by the functions in this file.
1534  */
1535 static void sound_lock_mem()
1536 {
1537    LOCK_VARIABLE(digi_none);
1538    LOCK_VARIABLE(midi_none);
1539    LOCK_VARIABLE(digi_card);
1540    LOCK_VARIABLE(midi_card);
1541    LOCK_VARIABLE(digi_driver);
1542    LOCK_VARIABLE(midi_driver);
1543    LOCK_VARIABLE(_voice);
1544    LOCK_VARIABLE(_phys_voice);
1545    LOCK_VARIABLE(_digi_volume);
1546    LOCK_VARIABLE(_midi_volume);
1547    LOCK_VARIABLE(_flip_pan);
1548    LOCK_FUNCTION(_dummy_detect);
1549    LOCK_FUNCTION(play_sample);
1550    LOCK_FUNCTION(adjust_sample);
1551    LOCK_FUNCTION(stop_sample);
1552    LOCK_FUNCTION(allocate_voice);
1553    LOCK_FUNCTION(deallocate_voice);
1554    LOCK_FUNCTION(reallocate_voice);
1555    LOCK_FUNCTION(voice_start);
1556    LOCK_FUNCTION(voice_stop);
1557    LOCK_FUNCTION(voice_set_priority);
1558    LOCK_FUNCTION(voice_check);
1559    LOCK_FUNCTION(voice_get_position);
1560    LOCK_FUNCTION(voice_set_position);
1561    LOCK_FUNCTION(voice_set_playmode);
1562    LOCK_FUNCTION(voice_get_volume);
1563    LOCK_FUNCTION(voice_set_volume);
1564    LOCK_FUNCTION(voice_ramp_volume);
1565    LOCK_FUNCTION(voice_stop_volumeramp);
1566    LOCK_FUNCTION(voice_get_frequency);
1567    LOCK_FUNCTION(voice_set_frequency);
1568    LOCK_FUNCTION(voice_sweep_frequency);
1569    LOCK_FUNCTION(voice_stop_frequency_sweep);
1570    LOCK_FUNCTION(voice_get_pan);
1571    LOCK_FUNCTION(voice_set_pan);
1572    LOCK_FUNCTION(voice_sweep_pan);
1573    LOCK_FUNCTION(voice_stop_pan_sweep);
1574    LOCK_FUNCTION(voice_set_echo);
1575    LOCK_FUNCTION(voice_set_tremolo);
1576    LOCK_FUNCTION(voice_set_vibrato);
1577    LOCK_FUNCTION(update_sweeps);
1578 }
1579