Add copyright message to gles_video
[gpsp.git] / sound.c
1 /* gameplaySP
2  *
3  * Copyright (C) 2006 Exophase <exophase@gmail.com>
4  *
5  * This program is free software; you can redistribute it and/or
6  * modify it under the terms of the GNU General Public License as
7  * published by the Free Software Foundation; either version 2 of
8  * the License, or (at your option) any later version.
9  *
10  * This program is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13  * General Public License for more details.
14  *
15  * You should have received a copy of the GNU General Public License
16  * along with this program; if not, write to the Free Software
17  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
18  */
19
20
21 #include "common.h"
22 #include <SDL.h>
23 u32 global_enable_audio = 1;
24
25 direct_sound_struct direct_sound_channel[2];
26 gbc_sound_struct gbc_sound_channel[4];
27
28 #ifdef RPI_BUILD
29 u32 sound_frequency = 22050;
30 #else
31 u32 sound_frequency = 44100;
32 #endif
33
34 SDL_mutex *sound_mutex;
35 static SDL_cond *sound_cv;
36
37 #ifdef PSP_BUILD
38 u32 audio_buffer_size_number = 1;
39 #elif defined(POLLUX_BUILD)
40 u32 audio_buffer_size_number = 7;
41 #else
42 u32 audio_buffer_size_number = 8;
43 #endif
44
45 u32 sound_on;
46 static u32 audio_buffer_size;
47 static s16 sound_buffer[BUFFER_SIZE];
48 static u32 sound_buffer_base;
49
50 static u32 sound_last_cpu_ticks;
51 static fixed16_16 gbc_sound_tick_step;
52
53 static u32 sound_exit_flag;
54
55 // Queue 1, 2, or 4 samples to the top of the DS FIFO, wrap around circularly
56
57 #define sound_timer_queue(size, value)                                        \
58   *((s##size *)(ds->fifo + ds->fifo_top)) = value;                            \
59   ds->fifo_top = (ds->fifo_top + 1) % 32;                                     \
60
61 void sound_timer_queue8(u32 channel, u8 value)
62 {
63   direct_sound_struct *ds = direct_sound_channel + channel;
64   sound_timer_queue(8, value);
65 }
66
67 void sound_timer_queue16(u32 channel, u16 value)
68 {
69   direct_sound_struct *ds = direct_sound_channel + channel;
70   sound_timer_queue(8, value & 0xFF);
71   sound_timer_queue(8, value >> 8);
72 }
73
74 void sound_timer_queue32(u32 channel, u32 value)
75 {
76   direct_sound_struct *ds = direct_sound_channel + channel;
77
78   sound_timer_queue(8, value & 0xFF);
79   sound_timer_queue(8, (value >> 8) & 0xFF);
80   sound_timer_queue(8, (value >> 16) & 0xFF);
81   sound_timer_queue(8, value >> 24);
82 }
83
84 // Unqueue 1 sample from the base of the DS FIFO and place it on the audio
85 // buffer for as many samples as necessary. If the DS FIFO is 16 bytes or
86 // smaller and if DMA is enabled for the sound channel initiate a DMA transfer
87 // to the DS FIFO.
88
89 #define render_sample_null()                                                  \
90
91 #define render_sample_left()                                                  \
92   sound_buffer[buffer_index] += current_sample +                              \
93    fp16_16_to_u32((next_sample - current_sample) * (fifo_fractional >> 8))    \
94
95 #define render_sample_right()                                                 \
96   sound_buffer[buffer_index + 1] += current_sample +                          \
97    fp16_16_to_u32((next_sample - current_sample) * (fifo_fractional >> 8))    \
98
99 #define render_sample_both()                                                  \
100   dest_sample = current_sample +                                              \
101    fp16_16_to_u32((next_sample - current_sample) * (fifo_fractional >> 8));   \
102   sound_buffer[buffer_index] += dest_sample;                                  \
103   sound_buffer[buffer_index + 1] += dest_sample                               \
104
105 #define render_samples(type)                                                  \
106   while(fifo_fractional <= 0xFFFFFF)                                          \
107   {                                                                           \
108     render_sample_##type();                                                   \
109     fifo_fractional += frequency_step;                                        \
110     buffer_index = (buffer_index + 2) % BUFFER_SIZE;                          \
111   }                                                                           \
112
113 void sound_timer(fixed8_24 frequency_step, u32 channel)
114 {
115   direct_sound_struct *ds = direct_sound_channel + channel;
116
117   fixed8_24 fifo_fractional = ds->fifo_fractional;
118   u32 buffer_index = ds->buffer_index;
119   s16 current_sample, next_sample, dest_sample;
120
121   current_sample = ds->fifo[ds->fifo_base] << 4;
122   ds->fifo_base = (ds->fifo_base + 1) % 32;
123   next_sample = ds->fifo[ds->fifo_base] << 4;
124
125   if(sound_on == 1)
126   {
127     if(ds->volume == DIRECT_SOUND_VOLUME_50)
128     {
129       current_sample >>= 1;
130       next_sample >>= 1;
131     }
132
133     switch(ds->status)
134     {
135       case DIRECT_SOUND_INACTIVE:
136         render_samples(null);
137         break;
138
139       case DIRECT_SOUND_RIGHT:
140         render_samples(right);
141         break;
142
143       case DIRECT_SOUND_LEFT:
144         render_samples(left);
145         break;
146
147       case DIRECT_SOUND_LEFTRIGHT:
148         render_samples(both);
149         break;
150     }
151   }
152   else
153   {
154     render_samples(null);
155   }
156
157   ds->buffer_index = buffer_index;
158   ds->fifo_fractional = fp8_24_fractional_part(fifo_fractional);
159
160   if(((ds->fifo_top - ds->fifo_base) % 32) <= 16)
161   {
162     if(dma[1].direct_sound_channel == channel)
163       dma_transfer(dma + 1);
164
165     if(dma[2].direct_sound_channel == channel)
166       dma_transfer(dma + 2);
167   }
168 }
169
170 void sound_reset_fifo(u32 channel)
171 {
172   direct_sound_struct *ds = direct_sound_channel;
173
174   memset(ds->fifo, 0, 32);
175 }
176
177 // Initial pattern data = 4bits (signed)
178 // Channel volume = 12bits
179 // Envelope volume = 14bits
180 // Master volume = 2bits
181
182 // Recalculate left and right volume as volume changes.
183 // To calculate the current sample, use (sample * volume) >> 16
184
185 // Square waves range from -8 (low) to 7 (high)
186
187 s8 square_pattern_duty[4][8] =
188 {
189   { 0xF8, 0xF8, 0xF8, 0xF8, 0x07, 0xF8, 0xF8, 0xF8 },
190   { 0xF8, 0xF8, 0xF8, 0xF8, 0x07, 0x07, 0xF8, 0xF8 },
191   { 0xF8, 0xF8, 0x07, 0x07, 0x07, 0x07, 0xF8, 0xF8 },
192   { 0x07, 0x07, 0x07, 0x07, 0xF8, 0xF8, 0x07, 0x07 },
193 };
194
195 s8 wave_samples[64];
196
197 u32 noise_table15[1024];
198 u32 noise_table7[4];
199
200 u32 gbc_sound_master_volume_table[4] = { 1, 2, 4, 0 };
201
202 u32 gbc_sound_channel_volume_table[8] =
203 {
204   fixed_div(0, 7, 12),
205   fixed_div(1, 7, 12),
206   fixed_div(2, 7, 12),
207   fixed_div(3, 7, 12),
208   fixed_div(4, 7, 12),
209   fixed_div(5, 7, 12),
210   fixed_div(6, 7, 12),
211   fixed_div(7, 7, 12)
212 };
213
214 u32 gbc_sound_envelope_volume_table[16] =
215 {
216   fixed_div(0, 15, 14),
217   fixed_div(1, 15, 14),
218   fixed_div(2, 15, 14),
219   fixed_div(3, 15, 14),
220   fixed_div(4, 15, 14),
221   fixed_div(5, 15, 14),
222   fixed_div(6, 15, 14),
223   fixed_div(7, 15, 14),
224   fixed_div(8, 15, 14),
225   fixed_div(9, 15, 14),
226   fixed_div(10, 15, 14),
227   fixed_div(11, 15, 14),
228   fixed_div(12, 15, 14),
229   fixed_div(13, 15, 14),
230   fixed_div(14, 15, 14),
231   fixed_div(15, 15, 14)
232 };
233
234 u32 gbc_sound_buffer_index = 0;
235 u32 gbc_sound_last_cpu_ticks = 0;
236 u32 gbc_sound_partial_ticks = 0;
237
238 u32 gbc_sound_master_volume_left;
239 u32 gbc_sound_master_volume_right;
240 u32 gbc_sound_master_volume;
241
242 #define update_volume_channel_envelope(channel)                               \
243   volume_##channel = gbc_sound_envelope_volume_table[envelope_volume] *       \
244    gbc_sound_channel_volume_table[gbc_sound_master_volume_##channel] *        \
245    gbc_sound_master_volume_table[gbc_sound_master_volume]                     \
246
247 #define update_volume_channel_noenvelope(channel)                             \
248   volume_##channel = gs->wave_volume *                                        \
249    gbc_sound_channel_volume_table[gbc_sound_master_volume_##channel] *        \
250    gbc_sound_master_volume_table[gbc_sound_master_volume]                     \
251
252 #define update_volume(type)                                                   \
253   update_volume_channel_##type(left);                                         \
254   update_volume_channel_##type(right)                                         \
255
256 #define update_tone_sweep()                                                   \
257   if(gs->sweep_status)                                                        \
258   {                                                                           \
259     u32 sweep_ticks = gs->sweep_ticks - 1;                                    \
260                                                                               \
261     if(sweep_ticks == 0)                                                      \
262     {                                                                         \
263       u32 rate = gs->rate;                                                    \
264                                                                               \
265       if(gs->sweep_direction)                                                 \
266         rate = rate - (rate >> gs->sweep_shift);                              \
267       else                                                                    \
268         rate = rate + (rate >> gs->sweep_shift);                              \
269                                                                               \
270       if(rate > 2048)                                                         \
271         rate = 2048;                                                          \
272                                                                               \
273       frequency_step = float_to_fp16_16(((131072.0f / (2048 - rate)) * 8.0f)  \
274        / sound_frequency);                                                    \
275                                                                               \
276       gs->frequency_step = frequency_step;                                    \
277       gs->rate = rate;                                                        \
278                                                                               \
279       sweep_ticks = gs->sweep_initial_ticks;                                  \
280     }                                                                         \
281     gs->sweep_ticks = sweep_ticks;                                            \
282   }                                                                           \
283
284 #define update_tone_nosweep()                                                 \
285
286 #define update_tone_envelope()                                                \
287   if(gs->envelope_status)                                                     \
288   {                                                                           \
289     u32 envelope_ticks = gs->envelope_ticks - 1;                              \
290     envelope_volume = gs->envelope_volume;                                    \
291                                                                               \
292     if(envelope_ticks == 0)                                                   \
293     {                                                                         \
294       if(gs->envelope_direction)                                              \
295       {                                                                       \
296         if(envelope_volume != 15)                                             \
297           envelope_volume = gs->envelope_volume + 1;                          \
298       }                                                                       \
299       else                                                                    \
300       {                                                                       \
301         if(envelope_volume != 0)                                              \
302           envelope_volume = gs->envelope_volume - 1;                          \
303       }                                                                       \
304                                                                               \
305       update_volume(envelope);                                                \
306                                                                               \
307       gs->envelope_volume = envelope_volume;                                  \
308       gs->envelope_ticks = gs->envelope_initial_ticks;                        \
309     }                                                                         \
310     else                                                                      \
311     {                                                                         \
312       gs->envelope_ticks = envelope_ticks;                                    \
313     }                                                                         \
314   }                                                                           \
315
316 #define update_tone_noenvelope()                                              \
317
318 #define update_tone_counters(envelope_op, sweep_op)                           \
319   tick_counter += gbc_sound_tick_step;                                        \
320   if(tick_counter > 0xFFFF)                                                   \
321   {                                                                           \
322     if(gs->length_status)                                                     \
323     {                                                                         \
324       u32 length_ticks = gs->length_ticks - 1;                                \
325       gs->length_ticks = length_ticks;                                        \
326                                                                               \
327       if(length_ticks == 0)                                                   \
328       {                                                                       \
329         gs->active_flag = 0;                                                  \
330         break;                                                                \
331       }                                                                       \
332     }                                                                         \
333                                                                               \
334     update_tone_##envelope_op();                                              \
335     update_tone_##sweep_op();                                                 \
336                                                                               \
337     tick_counter &= 0xFFFF;                                                   \
338   }                                                                           \
339
340 #define gbc_sound_render_sample_right()                                       \
341   sound_buffer[buffer_index + 1] += (current_sample * volume_right) >> 22     \
342
343 #define gbc_sound_render_sample_left()                                        \
344   sound_buffer[buffer_index] += (current_sample * volume_left) >> 22          \
345
346 #define gbc_sound_render_sample_both()                                        \
347   gbc_sound_render_sample_right();                                            \
348   gbc_sound_render_sample_left()                                              \
349
350 #define gbc_sound_render_samples(type, sample_length, envelope_op, sweep_op)  \
351   for(i = 0; i < buffer_ticks; i++)                                           \
352   {                                                                           \
353     current_sample =                                                          \
354      sample_data[fp16_16_to_u32(sample_index) % sample_length];               \
355     gbc_sound_render_sample_##type();                                         \
356                                                                               \
357     sample_index += frequency_step;                                           \
358     buffer_index = (buffer_index + 2) % BUFFER_SIZE;                          \
359                                                                               \
360     update_tone_counters(envelope_op, sweep_op);                              \
361   }                                                                           \
362
363 #define gbc_noise_wrap_full 32767
364
365 #define gbc_noise_wrap_half 126
366
367 #define get_noise_sample_full()                                               \
368   current_sample =                                                            \
369    ((s32)(noise_table15[fp16_16_to_u32(sample_index) >> 5] <<                 \
370    (fp16_16_to_u32(sample_index) & 0x1F)) >> 31) & 0x0F                       \
371
372 #define get_noise_sample_half()                                               \
373   current_sample =                                                            \
374    ((s32)(noise_table7[fp16_16_to_u32(sample_index) >> 5] <<                  \
375    (fp16_16_to_u32(sample_index) & 0x1F)) >> 31) & 0x0F                       \
376
377 #define gbc_sound_render_noise(type, noise_type, envelope_op, sweep_op)       \
378   for(i = 0; i < buffer_ticks; i++)                                           \
379   {                                                                           \
380     get_noise_sample_##noise_type();                                          \
381     gbc_sound_render_sample_##type();                                         \
382                                                                               \
383     sample_index += frequency_step;                                           \
384                                                                               \
385     if(sample_index >= u32_to_fp16_16(gbc_noise_wrap_##noise_type))           \
386       sample_index -= u32_to_fp16_16(gbc_noise_wrap_##noise_type);            \
387                                                                               \
388     buffer_index = (buffer_index + 2) % BUFFER_SIZE;                          \
389     update_tone_counters(envelope_op, sweep_op);                              \
390   }                                                                           \
391
392 #define gbc_sound_render_channel(type, sample_length, envelope_op, sweep_op)  \
393   buffer_index = gbc_sound_buffer_index;                                      \
394   sample_index = gs->sample_index;                                            \
395   frequency_step = gs->frequency_step;                                        \
396   tick_counter = gs->tick_counter;                                            \
397                                                                               \
398   update_volume(envelope_op);                                                 \
399                                                                               \
400   switch(gs->status)                                                          \
401   {                                                                           \
402     case GBC_SOUND_INACTIVE:                                                  \
403       break;                                                                  \
404                                                                               \
405     case GBC_SOUND_LEFT:                                                      \
406       gbc_sound_render_##type(left, sample_length, envelope_op, sweep_op);    \
407       break;                                                                  \
408                                                                               \
409     case GBC_SOUND_RIGHT:                                                     \
410       gbc_sound_render_##type(right, sample_length, envelope_op, sweep_op);   \
411       break;                                                                  \
412                                                                               \
413     case GBC_SOUND_LEFTRIGHT:                                                 \
414       gbc_sound_render_##type(both, sample_length, envelope_op, sweep_op);    \
415       break;                                                                  \
416   }                                                                           \
417                                                                               \
418   gs->sample_index = sample_index;                                            \
419   gs->tick_counter = tick_counter;                                            \
420
421 #define gbc_sound_load_wave_ram(bank)                                         \
422   wave_bank = wave_samples + (bank * 32);                                     \
423   for(i = 0, i2 = 0; i < 16; i++, i2 += 2)                                    \
424   {                                                                           \
425     current_sample = wave_ram[i];                                             \
426     wave_bank[i2] = (((current_sample >> 4) & 0x0F) - 8);                     \
427     wave_bank[i2 + 1] = ((current_sample & 0x0F) - 8);                        \
428   }                                                                           \
429
430 void update_gbc_sound(u32 cpu_ticks)
431 {
432   fixed16_16 buffer_ticks = float_to_fp16_16((float)(cpu_ticks -
433    gbc_sound_last_cpu_ticks) * sound_frequency / GBC_BASE_RATE);
434   u32 i, i2;
435   gbc_sound_struct *gs = gbc_sound_channel;
436   fixed16_16 sample_index, frequency_step;
437   fixed16_16 tick_counter;
438   u32 buffer_index;
439   s32 volume_left, volume_right;
440   u32 envelope_volume;
441   s32 current_sample;
442   u32 sound_status = address16(io_registers, 0x84) & 0xFFF0;
443   s8 *sample_data;
444   s8 *wave_bank;
445   u8 *wave_ram = ((u8 *)io_registers) + 0x90;
446
447   gbc_sound_partial_ticks += fp16_16_fractional_part(buffer_ticks);
448   buffer_ticks = fp16_16_to_u32(buffer_ticks);
449
450   if(gbc_sound_partial_ticks > 0xFFFF)
451   {
452     buffer_ticks += 1;
453     gbc_sound_partial_ticks &= 0xFFFF;
454   }
455
456   SDL_LockMutex(sound_mutex);
457   if(synchronize_flag)
458   {
459     if(((gbc_sound_buffer_index - sound_buffer_base) % BUFFER_SIZE) >=
460      (audio_buffer_size * 2))
461     {
462       while(((gbc_sound_buffer_index - sound_buffer_base) % BUFFER_SIZE) >
463        (audio_buffer_size * 3 / 2))
464       {
465         SDL_CondWait(sound_cv, sound_mutex);
466       }
467
468 #ifdef PSP_BUILD
469       if(current_frameskip_type == auto_frameskip)
470       {
471         sceDisplayWaitVblankStart();
472         real_frame_count = 0;
473         virtual_frame_count = 0;
474       }
475 #else
476       if(current_frameskip_type == auto_frameskip)
477       {
478 /*
479         u64 current_ticks;
480         u64 next_ticks;
481         get_ticks_us(&current_ticks);
482
483         next_ticks = ((current_ticks + 16666) / 16667) * 16667;
484         delay_us(next_ticks - current_ticks);
485
486         get_ticks_us(&frame_count_initial_timestamp);
487 */
488         /* prevent frameskip, or it will cause more audio,
489          * then more waiting here, then frame skip again, ... */
490         num_skipped_frames = 100;
491       }
492 #endif
493
494     }
495   }
496   if(sound_on == 1)
497   {
498     gs = gbc_sound_channel + 0;
499     if(gs->active_flag)
500     {
501       sound_status |= 0x01;
502       sample_data = gs->sample_data;
503       envelope_volume = gs->envelope_volume;
504       gbc_sound_render_channel(samples, 8, envelope, sweep);
505     }
506
507     gs = gbc_sound_channel + 1;
508     if(gs->active_flag)
509     {
510       sound_status |= 0x02;
511       sample_data = gs->sample_data;
512       envelope_volume = gs->envelope_volume;
513       gbc_sound_render_channel(samples, 8, envelope, nosweep);
514     }
515
516     gs = gbc_sound_channel + 2;
517     if(gbc_sound_wave_update)
518     {
519       if(gs->wave_bank == 1)
520       {
521         gbc_sound_load_wave_ram(1);
522       }
523       else
524       {
525         gbc_sound_load_wave_ram(0);
526       }
527
528       gbc_sound_wave_update = 0;
529     }
530
531     if((gs->active_flag) && (gs->master_enable))
532     {
533       sound_status |= 0x04;
534       sample_data = wave_samples;
535       if(gs->wave_type == 0)
536       {
537         if(gs->wave_bank == 1)
538           sample_data += 32;
539
540         gbc_sound_render_channel(samples, 32, noenvelope, nosweep);
541       }
542       else
543       {
544         gbc_sound_render_channel(samples, 64, noenvelope, nosweep);
545       }
546     }
547
548     gs = gbc_sound_channel + 3;
549     if(gs->active_flag)
550     {
551       sound_status |= 0x08;
552       envelope_volume = gs->envelope_volume;
553
554       if(gs->noise_type == 1)
555       {
556         gbc_sound_render_channel(noise, half, envelope, nosweep);
557       }
558       else
559       {
560         gbc_sound_render_channel(noise, full, envelope, nosweep);
561       }
562     }
563   }
564
565   address16(io_registers, 0x84) = sound_status;
566
567   gbc_sound_last_cpu_ticks = cpu_ticks;
568   gbc_sound_buffer_index =
569    (gbc_sound_buffer_index + (buffer_ticks * 2)) % BUFFER_SIZE;
570
571   SDL_UnlockMutex(sound_mutex);
572
573   SDL_CondSignal(sound_cv);
574 }
575
576 #define sound_copy_normal()                                                   \
577   current_sample = source[i]                                                  \
578
579 #define sound_copy(source_offset, length, render_type)                        \
580   _length = (length) / 2;                                                     \
581   source = (s16 *)(sound_buffer + source_offset);                             \
582   for(i = 0; i < _length; i++)                                                \
583   {                                                                           \
584     sound_copy_##render_type();                                               \
585     if(current_sample > 2047)                                                 \
586       current_sample = 2047;                                                  \
587     if(current_sample < -2048)                                                \
588       current_sample = -2048;                                                 \
589                                                                               \
590     stream_base[i] = current_sample << 4;                                     \
591     source[i] = 0;                                                            \
592   }                                                                           \
593
594 #define sound_copy_null(source_offset, length)                                \
595   _length = (length) / 2;                                                     \
596   source = (s16 *)(sound_buffer + source_offset);                             \
597   for(i = 0; i < _length; i++)                                                \
598   {                                                                           \
599     stream_base[i] = 0;                                                       \
600     source[i] = 0;                                                            \
601   }                                                                           \
602
603
604 void sound_callback(void *userdata, Uint8 *stream, int length)
605 {
606   u32 sample_length = length / 2;
607   u32 _length;
608   u32 i;
609   s16 *stream_base = (s16 *)stream;
610   s16 *source;
611   s32 current_sample;
612
613   SDL_LockMutex(sound_mutex);
614
615   while(((gbc_sound_buffer_index - sound_buffer_base) % BUFFER_SIZE) <
616    length && !sound_exit_flag)
617   {
618     SDL_CondWait(sound_cv, sound_mutex);
619   }
620
621   if(global_enable_audio)
622   {
623     if((sound_buffer_base + sample_length) >= BUFFER_SIZE)
624     {
625       u32 partial_length = (BUFFER_SIZE - sound_buffer_base) * 2;
626       sound_copy(sound_buffer_base, partial_length, normal);
627       source = (s16 *)sound_buffer;
628       sound_copy(0, length - partial_length, normal);
629       sound_buffer_base = (length - partial_length) / 2;
630     }
631     else
632     {
633       sound_copy(sound_buffer_base, length, normal);
634       sound_buffer_base += sample_length;
635     }
636   }
637   else
638   {
639     if((sound_buffer_base + sample_length) >= BUFFER_SIZE)
640     {
641       u32 partial_length = (BUFFER_SIZE - sound_buffer_base) * 2;
642       sound_copy_null(sound_buffer_base, partial_length);
643       source = (s16 *)sound_buffer;
644       sound_copy(0, length - partial_length, normal);
645       sound_buffer_base = (length - partial_length) / 2;
646     }
647     else
648     {
649       sound_copy_null(sound_buffer_base, length);
650       sound_buffer_base += sample_length;
651     }
652   }
653
654   SDL_CondSignal(sound_cv);
655
656   SDL_UnlockMutex(sound_mutex);
657 }
658
659 // Special thanks to blarrg for the LSFR frequency used in Meridian, as posted
660 // on the forum at http://meridian.overclocked.org:
661 // http://meridian.overclocked.org/cgi-bin/wwwthreads/showpost.pl?Board=merid
662 // angeneraldiscussion&Number=2069&page=0&view=expanded&mode=threaded&sb=4
663 // Hope you don't mind me borrowing it ^_-
664
665 void init_noise_table(u32 *table, u32 period, u32 bit_length)
666 {
667   u32 shift_register = 0xFF;
668   u32 mask = ~(1 << bit_length);
669   s32 table_pos, bit_pos;
670   u32 current_entry;
671   u32 table_period = (period + 31) / 32;
672
673   // Bits are stored in reverse order so they can be more easily moved to
674   // bit 31, for sign extended shift down.
675
676   for(table_pos = 0; table_pos < table_period; table_pos++)
677   {
678     current_entry = 0;
679     for(bit_pos = 31; bit_pos >= 0; bit_pos--)
680     {
681       current_entry |= (shift_register & 0x01) << bit_pos;
682
683       shift_register =
684        ((1 & (shift_register ^ (shift_register >> 1))) << bit_length) |
685        ((shift_register >> 1) & mask);
686     }
687
688     table[table_pos] = current_entry;
689   }
690 }
691
692 void reset_sound()
693 {
694   direct_sound_struct *ds = direct_sound_channel;
695   gbc_sound_struct *gs = gbc_sound_channel;
696   u32 i;
697
698   SDL_LockMutex(sound_mutex);
699
700   sound_on = 0;
701   sound_buffer_base = 0;
702   sound_last_cpu_ticks = 0;
703   memset(sound_buffer, 0, sizeof(sound_buffer));
704
705   for(i = 0; i < 2; i++, ds++)
706   {
707     ds->buffer_index = 0;
708     ds->status = DIRECT_SOUND_INACTIVE;
709     ds->fifo_top = 0;
710     ds->fifo_base = 0;
711     ds->fifo_fractional = 0;
712     ds->last_cpu_ticks = 0;
713     memset(ds->fifo, 0, 32);
714   }
715
716   gbc_sound_buffer_index = 0;
717   gbc_sound_last_cpu_ticks = 0;
718   gbc_sound_partial_ticks = 0;
719
720   gbc_sound_master_volume_left = 0;
721   gbc_sound_master_volume_right = 0;
722   gbc_sound_master_volume = 0;
723   memset(wave_samples, 0, 64);
724
725   for(i = 0; i < 4; i++, gs++)
726   {
727     gs->status = GBC_SOUND_INACTIVE;
728     gs->sample_data = square_pattern_duty[2];
729     gs->active_flag = 0;
730   }
731
732   SDL_UnlockMutex(sound_mutex);
733 }
734
735 void sound_exit()
736 {
737   gbc_sound_buffer_index =
738    (sound_buffer_base + audio_buffer_size) % BUFFER_SIZE;
739   SDL_PauseAudio(1);
740   sound_exit_flag = 1;
741   SDL_CondSignal(sound_cv);
742   SDL_CloseAudio();
743   SDL_Delay(200);
744   SDL_DestroyMutex(sound_mutex);
745   sound_mutex = NULL;
746   SDL_DestroyCond(sound_cv);
747   sound_cv = NULL;
748 }
749
750 void init_sound(int need_reset)
751 {
752   SDL_AudioSpec sound_settings;
753
754   sound_exit_flag = 0;
755 #ifdef PSP_BUILD
756   audio_buffer_size = (audio_buffer_size_number * 1024) + 3072;
757 #else
758   audio_buffer_size = 16 << audio_buffer_size_number;
759 //  audio_buffer_size = 16384;
760 #endif
761
762   SDL_AudioSpec desired_spec =
763   {
764     sound_frequency,
765     AUDIO_S16,
766     2,
767     0,
768     audio_buffer_size / 4,
769     0,
770     0,
771     sound_callback,
772     NULL
773   };
774
775   sound_mutex = SDL_CreateMutex();
776   sound_cv = SDL_CreateCond();
777
778   SDL_OpenAudio(&desired_spec, &sound_settings);
779   sound_frequency = sound_settings.freq;
780   audio_buffer_size = sound_settings.size;
781   u32 i = audio_buffer_size / 16;
782   for (audio_buffer_size_number = 0; i && (i & 1) == 0; i >>= 1)
783     audio_buffer_size_number++;
784 #ifndef PSP_BUILD
785   printf("audio: freq %d, size %d\n", sound_frequency, audio_buffer_size);
786 #endif
787
788   gbc_sound_tick_step =
789    float_to_fp16_16(256.0f / sound_frequency);
790
791   init_noise_table(noise_table15, 32767, 14);
792   init_noise_table(noise_table7, 127, 6);
793
794   if (need_reset)
795     reset_sound();
796
797   SDL_PauseAudio(0);
798 }
799
800 #define sound_savestate_builder(type)                                       \
801 void sound_##type##_savestate(file_tag_type savestate_file)                 \
802 {                                                                           \
803   file_##type##_variable(savestate_file, sound_on);                         \
804   file_##type##_variable(savestate_file, sound_buffer_base);                \
805   file_##type##_variable(savestate_file, sound_last_cpu_ticks);             \
806   file_##type##_variable(savestate_file, gbc_sound_buffer_index);           \
807   file_##type##_variable(savestate_file, gbc_sound_last_cpu_ticks);         \
808   file_##type##_variable(savestate_file, gbc_sound_partial_ticks);          \
809   file_##type##_variable(savestate_file, gbc_sound_master_volume_left);     \
810   file_##type##_variable(savestate_file, gbc_sound_master_volume_right);    \
811   file_##type##_variable(savestate_file, gbc_sound_master_volume);          \
812   file_##type##_array(savestate_file, wave_samples);                        \
813   file_##type##_array(savestate_file, direct_sound_channel);                \
814   file_##type##_array(savestate_file, gbc_sound_channel);                   \
815 }                                                                           \
816
817 sound_savestate_builder(read);
818 sound_savestate_builder(write_mem);
819