src/gb/audio.c (view raw)
1/* Copyright (c) 2013-2016 Jeffrey Pfau
2 *
3 * This Source Code Form is subject to the terms of the Mozilla Public
4 * License, v. 2.0. If a copy of the MPL was not distributed with this
5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6#include "audio.h"
7
8#include "core/sync.h"
9#include "gb/gb.h"
10#include "gb/io.h"
11
12#define FRAME_CYCLES (DMG_LR35902_FREQUENCY >> 9)
13
14const uint32_t DMG_LR35902_FREQUENCY = 0x400000;
15static const int CLOCKS_PER_BLIP_FRAME = 0x1000;
16static const unsigned BLIP_BUFFER_SIZE = 0x4000;
17
18static void _writeDuty(struct GBAudioEnvelope* envelope, uint8_t value);
19static bool _writeSweep(struct GBAudioEnvelope* envelope, uint8_t value);
20static int32_t _updateSquareChannel(struct GBAudioSquareControl* envelope, int duty);
21static void _updateEnvelope(struct GBAudioEnvelope* envelope);
22static bool _updateSweep(struct GBAudioChannel1* ch, bool initial);
23static int32_t _updateChannel1(struct GBAudioChannel1* ch);
24static int32_t _updateChannel2(struct GBAudioChannel2* ch);
25static int32_t _updateChannel3(struct GBAudioChannel3* ch);
26static int32_t _updateChannel4(struct GBAudioChannel4* ch);
27static void _sample(struct GBAudio* audio, int32_t cycles);
28
29void GBAudioInit(struct GBAudio* audio, size_t samples) {
30 audio->samples = samples;
31 audio->left = blip_new(BLIP_BUFFER_SIZE);
32 audio->right = blip_new(BLIP_BUFFER_SIZE);
33 audio->clockRate = DMG_LR35902_FREQUENCY;
34 // Guess too large; we hang producing extra samples if we guess too low
35 blip_set_rates(audio->left, DMG_LR35902_FREQUENCY, 96000);
36 blip_set_rates(audio->right, DMG_LR35902_FREQUENCY, 96000);
37 audio->forceDisableCh[0] = false;
38 audio->forceDisableCh[1] = false;
39 audio->forceDisableCh[2] = false;
40 audio->forceDisableCh[3] = false;
41}
42
43void GBAudioDeinit(struct GBAudio* audio) {
44 blip_delete(audio->left);
45 blip_delete(audio->right);
46}
47
48void GBAudioReset(struct GBAudio* audio) {
49 audio->nextEvent = 0;
50 audio->nextCh1 = 0;
51 audio->nextCh2 = 0;
52 audio->nextCh3 = 0;
53 audio->nextCh4 = 0;
54 audio->ch1 = (struct GBAudioChannel1) { .envelope = { .dead = 2 } };
55 audio->ch2 = (struct GBAudioChannel2) { .envelope = { .dead = 2 } };
56 audio->ch3 = (struct GBAudioChannel3) { .bank = 0 };
57 audio->ch4 = (struct GBAudioChannel4) { .envelope = { .dead = 2 } };
58 audio->eventDiff = 0;
59 audio->nextFrame = 0;
60 audio->frame = 0;
61 audio->nextSample = 0;
62 audio->sampleInterval = 128;
63 audio->volumeRight = 0;
64 audio->volumeLeft = 0;
65 audio->ch1Right = false;
66 audio->ch2Right = false;
67 audio->ch3Right = false;
68 audio->ch4Right = false;
69 audio->ch1Left = false;
70 audio->ch2Left = false;
71 audio->ch3Left = false;
72 audio->ch4Left = false;
73 audio->playingCh1 = false;
74 audio->playingCh2 = false;
75 audio->playingCh3 = false;
76 audio->playingCh4 = false;
77}
78
79void GBAudioResizeBuffer(struct GBAudio* audio, size_t samples) {
80 mCoreSyncLockAudio(audio->p->sync);
81 audio->samples = samples;
82 blip_clear(audio->left);
83 blip_clear(audio->right);
84 audio->clock = 0;
85 mCoreSyncConsumeAudio(audio->p->sync);
86}
87
88void GBAudioWriteNR10(struct GBAudio* audio, uint8_t value) {
89 audio->ch1.shift = GBAudioRegisterSquareSweepGetShift(value);
90 audio->ch1.direction = GBAudioRegisterSquareSweepGetDirection(value);
91 audio->ch1.time = GBAudioRegisterSquareSweepGetTime(value);
92 audio->ch1.sweepStep = audio->ch1.time;
93}
94
95void GBAudioWriteNR11(struct GBAudio* audio, uint8_t value) {
96 _writeDuty(&audio->ch1.envelope, value);
97 audio->ch1.control.length = 64 - audio->ch1.envelope.length;
98}
99
100void GBAudioWriteNR12(struct GBAudio* audio, uint8_t value) {
101 if (!_writeSweep(&audio->ch1.envelope, value)) {
102 audio->playingCh1 = false;
103 // TODO: Don't need p
104 if (audio->p) {
105 audio->p->memory.io[REG_NR52] &= ~0x0001;
106 }
107 }
108}
109
110void GBAudioWriteNR13(struct GBAudio* audio, uint8_t value) {
111 audio->ch1.control.frequency &= 0x700;
112 audio->ch1.control.frequency |= GBAudioRegisterControlGetFrequency(value);
113}
114
115void GBAudioWriteNR14(struct GBAudio* audio, uint8_t value) {
116 audio->ch1.control.frequency &= 0xFF;
117 audio->ch1.control.frequency |= GBAudioRegisterControlGetFrequency(value << 8);
118 bool wasStop = audio->ch1.control.stop;
119 audio->ch1.control.stop = GBAudioRegisterControlGetStop(value << 8);
120 if (!wasStop && audio->ch1.control.stop && audio->ch1.control.length && !(audio->frame & 1)) {
121 --audio->ch1.control.length;
122 if (audio->ch1.control.length == 0) {
123 audio->playingCh1 = false;
124 }
125 }
126 if (GBAudioRegisterControlIsRestart(value << 8)) {
127 if (audio->nextEvent == INT_MAX) {
128 audio->eventDiff = 0;
129 }
130 if (!audio->playingCh1) {
131 audio->nextCh1 = audio->eventDiff;
132 }
133 audio->playingCh1 = audio->ch1.envelope.initialVolume || audio->ch1.envelope.direction;
134 audio->ch1.envelope.currentVolume = audio->ch1.envelope.initialVolume;
135 if (audio->ch1.envelope.currentVolume > 0 && audio->ch1.envelope.stepTime) {
136 audio->ch1.envelope.dead = 0;
137 }
138 audio->ch1.sweepStep = audio->ch1.time;
139 audio->ch1.sweepEnable = audio->ch1.sweepStep || audio->ch1.shift;
140 if (audio->playingCh1 && audio->ch1.shift) {
141 audio->playingCh1 = _updateSweep(&audio->ch1, true);
142 }
143 if (!audio->ch1.control.length) {
144 audio->ch1.control.length = 64;
145 if (audio->ch1.control.stop && !(audio->frame & 1)) {
146 --audio->ch1.control.length;
147 }
148 }
149 audio->nextEvent = audio->eventDiff;
150 if (audio->p) {
151 // TODO: Don't need
152 audio->p->cpu->nextEvent = audio->eventDiff;
153 }
154 }
155 // TODO: Don't need p
156 if (audio->p) {
157 audio->p->memory.io[REG_NR52] &= ~0x0001;
158 audio->p->memory.io[REG_NR52] |= audio->playingCh1;
159 }
160}
161
162void GBAudioWriteNR21(struct GBAudio* audio, uint8_t value) {
163 _writeDuty(&audio->ch2.envelope, value);
164 audio->ch2.control.length = 64 - audio->ch2.envelope.length;
165}
166
167void GBAudioWriteNR22(struct GBAudio* audio, uint8_t value) {
168 if (!_writeSweep(&audio->ch2.envelope, value)) {
169 audio->playingCh2 = false;
170 // TODO: Don't need p
171 if (audio->p) {
172 audio->p->memory.io[REG_NR52] &= ~0x0002;
173 }
174 }
175}
176
177void GBAudioWriteNR23(struct GBAudio* audio, uint8_t value) {
178 audio->ch2.control.frequency &= 0x700;
179 audio->ch2.control.frequency |= GBAudioRegisterControlGetFrequency(value);
180}
181
182void GBAudioWriteNR24(struct GBAudio* audio, uint8_t value) {
183 audio->ch2.control.frequency &= 0xFF;
184 audio->ch2.control.frequency |= GBAudioRegisterControlGetFrequency(value << 8);
185 bool wasStop = audio->ch2.control.stop;
186 audio->ch2.control.stop = GBAudioRegisterControlGetStop(value << 8);
187 if (!wasStop && audio->ch2.control.stop && audio->ch2.control.length && !(audio->frame & 1)) {
188 --audio->ch2.control.length;
189 if (audio->ch2.control.length == 0) {
190 audio->playingCh2 = false;
191 }
192 }
193 if (GBAudioRegisterControlIsRestart(value << 8)) {
194 audio->playingCh2 = audio->ch2.envelope.initialVolume || audio->ch2.envelope.direction;
195 audio->ch2.envelope.currentVolume = audio->ch2.envelope.initialVolume;
196 if (audio->ch2.envelope.currentVolume > 0 && audio->ch2.envelope.stepTime) {
197 audio->ch2.envelope.dead = 0;
198 }
199 if (audio->nextEvent == INT_MAX) {
200 audio->eventDiff = 0;
201 }
202 if (!audio->playingCh2) {
203 audio->nextCh2 = audio->eventDiff;
204 }
205 if (!audio->ch2.control.length) {
206 audio->ch2.control.length = 64;
207 if (audio->ch2.control.stop && !(audio->frame & 1)) {
208 --audio->ch2.control.length;
209 }
210 }
211 audio->nextEvent = audio->eventDiff;
212 if (audio->p) {
213 // TODO: Don't need p
214 audio->p->cpu->nextEvent = audio->eventDiff;
215 }
216 }
217 // TODO: Don't need p
218 if (audio->p) {
219 audio->p->memory.io[REG_NR52] &= ~0x0002;
220 audio->p->memory.io[REG_NR52] |= audio->playingCh2 << 1;
221 }
222}
223
224void GBAudioWriteNR30(struct GBAudio* audio, uint8_t value) {
225 audio->ch3.enable = GBAudioRegisterBankGetEnable(value);
226 if (!audio->ch3.enable) {
227 audio->playingCh3 = false;
228 // TODO: Don't need p
229 if (audio->p) {
230 audio->p->memory.io[REG_NR52] &= ~0x0004;
231 }
232 }
233}
234
235void GBAudioWriteNR31(struct GBAudio* audio, uint8_t value) {
236 audio->ch3.length = value;
237 audio->ch3.lengthShadow = 256 - value;
238}
239
240void GBAudioWriteNR32(struct GBAudio* audio, uint8_t value) {
241 audio->ch3.volume = GBAudioRegisterBankVolumeGetVolumeGB(value);
242}
243
244void GBAudioWriteNR33(struct GBAudio* audio, uint8_t value) {
245 audio->ch3.rate &= 0x700;
246 audio->ch3.rate |= GBAudioRegisterControlGetRate(value);
247}
248
249void GBAudioWriteNR34(struct GBAudio* audio, uint8_t value) {
250 audio->ch3.rate &= 0xFF;
251 audio->ch3.rate |= GBAudioRegisterControlGetRate(value << 8);
252 bool wasStop = audio->ch3.stop;
253 audio->ch3.stop = GBAudioRegisterControlGetStop(value << 8);
254 if (!wasStop && audio->ch3.stop && audio->ch3.lengthShadow && !(audio->frame & 1)) {
255 --audio->ch3.lengthShadow;
256 if (audio->ch3.lengthShadow == 0) {
257 audio->playingCh3 = false;
258 }
259 }
260 if (GBAudioRegisterControlIsRestart(value << 8)) {
261 audio->playingCh3 = audio->ch3.enable;
262 if (!audio->ch3.lengthShadow) {
263 audio->ch3.lengthShadow = 256;
264 if (audio->ch3.stop && !(audio->frame & 1)) {
265 --audio->ch3.lengthShadow;
266 }
267 }
268 }
269 if (audio->playingCh3) {
270 if (audio->nextEvent == INT_MAX) {
271 audio->eventDiff = 0;
272 }
273 audio->nextCh3 = audio->eventDiff;
274 audio->nextEvent = audio->eventDiff;
275 if (audio->p) {
276 // TODO: Don't need p
277 audio->p->cpu->nextEvent = audio->eventDiff;
278 }
279 }
280 // TODO: Don't need p
281 if (audio->p) {
282 audio->p->memory.io[REG_NR52] &= ~0x0004;
283 audio->p->memory.io[REG_NR52] |= audio->playingCh3 << 2;
284 }
285}
286
287void GBAudioWriteNR41(struct GBAudio* audio, uint8_t value) {
288 _writeDuty(&audio->ch4.envelope, value);
289 audio->ch4.length = 64 - audio->ch4.envelope.length;
290}
291
292void GBAudioWriteNR42(struct GBAudio* audio, uint8_t value) {
293 if (!_writeSweep(&audio->ch4.envelope, value)) {
294 audio->playingCh4 = false;
295 // TODO: Don't need p
296 if (audio->p) {
297 audio->p->memory.io[REG_NR52] &= ~0x0008;
298 }
299 }
300}
301
302void GBAudioWriteNR43(struct GBAudio* audio, uint8_t value) {
303 audio->ch4.ratio = GBAudioRegisterNoiseFeedbackGetRatio(value);
304 audio->ch4.frequency = GBAudioRegisterNoiseFeedbackGetFrequency(value);
305 audio->ch4.power = GBAudioRegisterNoiseFeedbackGetPower(value);
306}
307
308void GBAudioWriteNR44(struct GBAudio* audio, uint8_t value) {
309 bool wasStop = audio->ch4.stop;
310 audio->ch4.stop = GBAudioRegisterNoiseControlGetStop(value);
311 if (!wasStop && audio->ch4.stop && audio->ch4.length && !(audio->frame & 1)) {
312 --audio->ch4.length;
313 if (audio->ch4.length == 0) {
314 audio->playingCh4 = false;
315 }
316 }
317 if (GBAudioRegisterNoiseControlIsRestart(value)) {
318 audio->playingCh4 = audio->ch4.envelope.initialVolume || audio->ch4.envelope.direction;
319 audio->ch4.envelope.currentVolume = audio->ch4.envelope.initialVolume;
320 if (audio->ch4.envelope.currentVolume > 0 && audio->ch4.envelope.stepTime) {
321 audio->ch4.envelope.dead = 0;
322 }
323 if (audio->ch4.power) {
324 audio->ch4.lfsr = 0x40;
325 } else {
326 audio->ch4.lfsr = 0x4000;
327 }
328 if (audio->nextEvent == INT_MAX) {
329 audio->eventDiff = 0;
330 }
331 if (!audio->playingCh4) {
332 audio->nextCh4 = audio->eventDiff;
333 }
334 if (!audio->ch4.length) {
335 audio->ch4.length = 64;
336 if (audio->ch4.stop && !(audio->frame & 1)) {
337 --audio->ch4.length;
338 }
339 }
340 audio->nextEvent = audio->eventDiff;
341 if (audio->p) {
342 // TODO: Don't need p
343 audio->p->cpu->nextEvent = audio->eventDiff;
344 }
345 }
346 // TODO: Don't need p
347 if (audio->p) {
348 audio->p->memory.io[REG_NR52] &= ~0x0008;
349 audio->p->memory.io[REG_NR52] |= audio->playingCh4 << 3;
350 }
351}
352
353void GBAudioWriteNR50(struct GBAudio* audio, uint8_t value) {
354 audio->volumeRight = GBRegisterNR50GetVolumeRight(value);
355 audio->volumeLeft = GBRegisterNR50GetVolumeLeft(value);
356}
357
358void GBAudioWriteNR51(struct GBAudio* audio, uint8_t value) {
359 audio->ch1Right = GBRegisterNR51GetCh1Right(value);
360 audio->ch2Right = GBRegisterNR51GetCh2Right(value);
361 audio->ch3Right = GBRegisterNR51GetCh3Right(value);
362 audio->ch4Right = GBRegisterNR51GetCh4Right(value);
363 audio->ch1Left = GBRegisterNR51GetCh1Left(value);
364 audio->ch2Left = GBRegisterNR51GetCh2Left(value);
365 audio->ch3Left = GBRegisterNR51GetCh3Left(value);
366 audio->ch4Left = GBRegisterNR51GetCh4Left(value);
367}
368
369void GBAudioWriteNR52(struct GBAudio* audio, uint8_t value) {
370 audio->enable = GBAudioEnableGetEnable(value);
371 if (!audio->enable) {
372 audio->playingCh1 = 0;
373 audio->playingCh2 = 0;
374 audio->playingCh3 = 0;
375 audio->playingCh4 = 0;
376 GBAudioWriteNR10(audio, 0);
377 GBAudioWriteNR11(audio, 0);
378 GBAudioWriteNR12(audio, 0);
379 GBAudioWriteNR13(audio, 0);
380 GBAudioWriteNR14(audio, 0);
381 GBAudioWriteNR21(audio, 0);
382 GBAudioWriteNR22(audio, 0);
383 GBAudioWriteNR23(audio, 0);
384 GBAudioWriteNR24(audio, 0);
385 GBAudioWriteNR30(audio, 0);
386 GBAudioWriteNR31(audio, 0);
387 GBAudioWriteNR32(audio, 0);
388 GBAudioWriteNR33(audio, 0);
389 GBAudioWriteNR34(audio, 0);
390 GBAudioWriteNR41(audio, 0);
391 GBAudioWriteNR42(audio, 0);
392 GBAudioWriteNR43(audio, 0);
393 GBAudioWriteNR44(audio, 0);
394 GBAudioWriteNR50(audio, 0);
395 GBAudioWriteNR51(audio, 0);
396 if (audio->p) {
397 audio->p->memory.io[REG_NR10] = 0;
398 audio->p->memory.io[REG_NR11] = 0;
399 audio->p->memory.io[REG_NR12] = 0;
400 audio->p->memory.io[REG_NR13] = 0;
401 audio->p->memory.io[REG_NR14] = 0;
402 audio->p->memory.io[REG_NR21] = 0;
403 audio->p->memory.io[REG_NR22] = 0;
404 audio->p->memory.io[REG_NR23] = 0;
405 audio->p->memory.io[REG_NR24] = 0;
406 audio->p->memory.io[REG_NR30] = 0;
407 audio->p->memory.io[REG_NR31] = 0;
408 audio->p->memory.io[REG_NR32] = 0;
409 audio->p->memory.io[REG_NR33] = 0;
410 audio->p->memory.io[REG_NR34] = 0;
411 audio->p->memory.io[REG_NR41] = 0;
412 audio->p->memory.io[REG_NR42] = 0;
413 audio->p->memory.io[REG_NR43] = 0;
414 audio->p->memory.io[REG_NR44] = 0;
415 audio->p->memory.io[REG_NR50] = 0;
416 audio->p->memory.io[REG_NR51] = 0;
417 audio->p->memory.io[REG_NR52] &= ~0x000F;
418 }
419 } else {
420 audio->frame = 7;
421 }
422}
423
424int32_t GBAudioProcessEvents(struct GBAudio* audio, int32_t cycles) {
425 if (audio->nextEvent == INT_MAX) {
426 return INT_MAX;
427 }
428 audio->nextEvent -= cycles;
429 audio->eventDiff += cycles;
430 while (audio->nextEvent <= 0) {
431 audio->nextEvent = INT_MAX;
432 if (audio->enable) {
433 audio->nextFrame -= audio->eventDiff;
434 int frame = -1;
435 if (audio->nextFrame <= 0) {
436 frame = (audio->frame + 1) & 7;
437 audio->frame = frame;
438 audio->nextFrame += FRAME_CYCLES;
439 if (audio->nextFrame < audio->nextEvent) {
440 audio->nextEvent = audio->nextFrame;
441 }
442 }
443
444 if (audio->playingCh1) {
445 audio->nextCh1 -= audio->eventDiff;
446 if (!audio->ch1.envelope.dead && frame == 7) {
447 --audio->ch1.envelope.nextStep;
448 if (audio->ch1.envelope.nextStep == 0) {
449 int8_t sample = audio->ch1.control.hi * 0x10 - 0x8;
450 _updateEnvelope(&audio->ch1.envelope);
451 audio->ch1.sample = sample * audio->ch1.envelope.currentVolume;
452 }
453 }
454
455 if (audio->ch1.sweepEnable && (frame & 3) == 2) {
456 --audio->ch1.sweepStep;
457 if (audio->ch1.sweepStep == 0) {
458 audio->playingCh1 = _updateSweep(&audio->ch1, false);
459 }
460 }
461
462 if (audio->ch1.envelope.dead != 2) {
463 if (audio->nextCh1 <= 0) {
464 audio->nextCh1 += _updateChannel1(&audio->ch1);
465 }
466 if (audio->nextCh1 < audio->nextEvent) {
467 audio->nextEvent = audio->nextCh1;
468 }
469 }
470 }
471
472 if (audio->ch1.control.length && audio->ch1.control.stop && !(frame & 1)) {
473 --audio->ch1.control.length;
474 if (audio->ch1.control.length == 0) {
475 audio->playingCh1 = 0;
476 }
477 }
478
479 if (audio->playingCh2) {
480 audio->nextCh2 -= audio->eventDiff;
481 if (!audio->ch2.envelope.dead && frame == 7) {
482 --audio->ch2.envelope.nextStep;
483 if (audio->ch2.envelope.nextStep == 0) {
484 int8_t sample = audio->ch2.control.hi * 0x10 - 0x8;
485 _updateEnvelope(&audio->ch2.envelope);
486 audio->ch2.sample = sample * audio->ch2.envelope.currentVolume;
487 }
488 }
489
490 if (audio->ch2.envelope.dead != 2) {
491 if (audio->nextCh2 <= 0) {
492 audio->nextCh2 += _updateChannel2(&audio->ch2);
493 }
494 if (audio->nextCh2 < audio->nextEvent) {
495 audio->nextEvent = audio->nextCh2;
496 }
497 }
498 }
499
500 if (audio->ch2.control.length && audio->ch2.control.stop && !(frame & 1)) {
501 --audio->ch2.control.length;
502 if (audio->ch2.control.length == 0) {
503 audio->playingCh2 = 0;
504 }
505 }
506
507 if (audio->playingCh3) {
508 audio->nextCh3 -= audio->eventDiff;
509 if (audio->nextCh3 <= 0) {
510 audio->nextCh3 += _updateChannel3(&audio->ch3);
511 }
512 if (audio->nextCh3 < audio->nextEvent) {
513 audio->nextEvent = audio->nextCh3;
514 }
515 }
516
517 if (audio->ch3.lengthShadow && audio->ch3.stop && !(frame & 1)) {
518 --audio->ch3.lengthShadow;
519 if (audio->ch3.lengthShadow == 0) {
520 audio->playingCh3 = 0;
521 }
522 }
523
524 if (audio->playingCh4) {
525 audio->nextCh4 -= audio->eventDiff;
526 if (!audio->ch4.envelope.dead && frame == 7) {
527 --audio->ch4.envelope.nextStep;
528 if (audio->ch4.envelope.nextStep == 0) {
529 int8_t sample = (audio->ch4.sample >> 31) * 0x8;
530 _updateEnvelope(&audio->ch4.envelope);
531 audio->ch4.sample = sample * audio->ch4.envelope.currentVolume;
532 }
533 }
534
535 if (audio->ch4.envelope.dead != 2) {
536 if (audio->nextCh4 <= 0) {
537 int32_t timing = _updateChannel4(&audio->ch4);
538 if (audio->nextCh4 < -timing) {
539 int32_t bound = timing * 16;
540 // Perform negative modulo to cap to 16 iterations
541 audio->nextCh4 = bound - (audio->nextCh4 - 1) % bound - 1;
542 }
543 audio->nextCh4 += timing;
544 }
545 if (audio->nextCh4 < audio->nextEvent) {
546 audio->nextEvent = audio->nextCh4;
547 }
548 }
549 }
550
551 if (audio->ch4.length && audio->ch4.stop && !(frame & 1)) {
552 --audio->ch4.length;
553 if (audio->ch4.length == 0) {
554 audio->playingCh4 = 0;
555 }
556 }
557 }
558
559 if (audio->p) {
560 audio->p->memory.io[REG_NR52] &= ~0x000F;
561 audio->p->memory.io[REG_NR52] |= audio->playingCh1;
562 audio->p->memory.io[REG_NR52] |= audio->playingCh2 << 1;
563 audio->p->memory.io[REG_NR52] |= audio->playingCh3 << 2;
564 audio->p->memory.io[REG_NR52] |= audio->playingCh4 << 3;
565 audio->nextSample -= audio->eventDiff;
566 if (audio->nextSample <= 0) {
567 _sample(audio, audio->sampleInterval);
568 audio->nextSample += audio->sampleInterval;
569 }
570
571 if (audio->nextSample < audio->nextEvent) {
572 audio->nextEvent = audio->nextSample;
573 }
574 }
575 audio->eventDiff = 0;
576 }
577 return audio->nextEvent;
578}
579
580void GBAudioSamplePSG(struct GBAudio* audio, int16_t* left, int16_t* right) {
581 int sampleLeft = 0;
582 int sampleRight = 0;
583
584 if (audio->playingCh1 && !audio->forceDisableCh[0]) {
585 if (audio->ch1Left) {
586 sampleLeft += audio->ch1.sample;
587 }
588
589 if (audio->ch1Right) {
590 sampleRight += audio->ch1.sample;
591 }
592 }
593
594 if (audio->playingCh2 && !audio->forceDisableCh[1]) {
595 if (audio->ch2Left) {
596 sampleLeft += audio->ch2.sample;
597 }
598
599 if (audio->ch2Right) {
600 sampleRight += audio->ch2.sample;
601 }
602 }
603
604 if (audio->playingCh3 && !audio->forceDisableCh[2]) {
605 if (audio->ch3Left) {
606 sampleLeft += audio->ch3.sample;
607 }
608
609 if (audio->ch3Right) {
610 sampleRight += audio->ch3.sample;
611 }
612 }
613
614 if (audio->playingCh4 && !audio->forceDisableCh[3]) {
615 if (audio->ch4Left) {
616 sampleLeft += audio->ch4.sample;
617 }
618
619 if (audio->ch4Right) {
620 sampleRight += audio->ch4.sample;
621 }
622 }
623
624 *left = sampleLeft * (1 + audio->volumeLeft);
625 *right = sampleRight * (1 + audio->volumeRight);
626}
627
628void _sample(struct GBAudio* audio, int32_t cycles) {
629 int16_t sampleLeft = 0;
630 int16_t sampleRight = 0;
631 GBAudioSamplePSG(audio, &sampleLeft, &sampleRight);
632 sampleLeft <<= 1;
633 sampleRight <<= 1;
634
635 mCoreSyncLockAudio(audio->p->sync);
636 unsigned produced;
637 if ((size_t) blip_samples_avail(audio->left) < audio->samples) {
638 blip_add_delta(audio->left, audio->clock, sampleLeft - audio->lastLeft);
639 blip_add_delta(audio->right, audio->clock, sampleRight - audio->lastRight);
640 audio->lastLeft = sampleLeft;
641 audio->lastRight = sampleRight;
642 audio->clock += cycles;
643 if (audio->clock >= CLOCKS_PER_BLIP_FRAME) {
644 blip_end_frame(audio->left, audio->clock);
645 blip_end_frame(audio->right, audio->clock);
646 audio->clock -= CLOCKS_PER_BLIP_FRAME;
647 }
648 }
649 produced = blip_samples_avail(audio->left);
650 bool wait = produced >= audio->samples;
651 mCoreSyncProduceAudio(audio->p->sync, wait);
652 // TODO: Put AVStream back
653}
654
655void _writeDuty(struct GBAudioEnvelope* envelope, uint8_t value) {
656 envelope->length = GBAudioRegisterDutyGetLength(value);
657 envelope->duty = GBAudioRegisterDutyGetDuty(value);
658}
659
660bool _writeSweep(struct GBAudioEnvelope* envelope, uint8_t value) {
661 envelope->stepTime = GBAudioRegisterSweepGetStepTime(value);
662 envelope->direction = GBAudioRegisterSweepGetDirection(value);
663 envelope->initialVolume = GBAudioRegisterSweepGetInitialVolume(value);
664 if (envelope->stepTime == 0) {
665 envelope->dead = envelope->currentVolume ? 1 : 2;
666 } else if (!envelope->direction && !envelope->currentVolume) {
667 envelope->dead = 2;
668 } else if (envelope->direction && envelope->currentVolume == 0xF) {
669 envelope->dead = 1;
670 } else {
671 envelope->dead = 0;
672 }
673 envelope->nextStep = envelope->stepTime;
674 return envelope->initialVolume || envelope->direction;
675}
676
677static int32_t _updateSquareChannel(struct GBAudioSquareControl* control, int duty) {
678 control->hi = !control->hi;
679 int period = 4 * (2048 - control->frequency);
680 switch (duty) {
681 case 0:
682 return control->hi ? period : period * 7;
683 case 1:
684 return control->hi ? period * 2 : period * 6;
685 case 2:
686 return period * 4;
687 case 3:
688 return control->hi ? period * 6 : period * 2;
689 default:
690 // This should never be hit
691 return period * 4;
692 }
693}
694
695static void _updateEnvelope(struct GBAudioEnvelope* envelope) {
696 if (envelope->direction) {
697 ++envelope->currentVolume;
698 } else {
699 --envelope->currentVolume;
700 }
701 if (envelope->currentVolume >= 15) {
702 envelope->currentVolume = 15;
703 envelope->dead = 1;
704 } else if (envelope->currentVolume <= 0) {
705 envelope->currentVolume = 0;
706 envelope->dead = 2;
707 } else {
708 envelope->nextStep = envelope->stepTime;
709 }
710}
711
712static bool _updateSweep(struct GBAudioChannel1* ch, bool initial) {
713 if (ch->direction) {
714 int frequency = ch->control.frequency;
715 frequency -= frequency >> ch->shift;
716 if (frequency >= 0) {
717 ch->control.frequency = frequency;
718 }
719 } else {
720 int frequency = ch->control.frequency;
721 frequency += frequency >> ch->shift;
722 if (frequency < 2048) {
723 if (!initial && ch->shift) {
724 ch->control.frequency = frequency;
725 if (!_updateSweep(ch, true)) {
726 return false;
727 }
728 }
729 } else {
730 return false;
731 }
732 }
733 ch->sweepStep = ch->time;
734 return true;
735}
736
737static int32_t _updateChannel1(struct GBAudioChannel1* ch) {
738 int timing = _updateSquareChannel(&ch->control, ch->envelope.duty);
739 ch->sample = ch->control.hi * 0x10 - 0x8;
740 ch->sample *= ch->envelope.currentVolume;
741 return timing;
742}
743
744static int32_t _updateChannel2(struct GBAudioChannel2* ch) {
745 int timing = _updateSquareChannel(&ch->control, ch->envelope.duty);
746 ch->sample = ch->control.hi * 0x10 - 0x8;
747 ch->sample *= ch->envelope.currentVolume;
748 return timing;
749}
750
751static int32_t _updateChannel3(struct GBAudioChannel3* ch) {
752 int i;
753 int start;
754 int end;
755 int volume;
756 switch (ch->volume) {
757 case 0:
758 volume = 0;
759 break;
760 case 1:
761 volume = 4;
762 break;
763 case 2:
764 volume = 2;
765 break;
766 case 3:
767 volume = 1;
768 break;
769 default:
770 volume = 3;
771 break;
772 }
773 if (ch->size) {
774 start = 7;
775 end = 0;
776 } else if (ch->bank) {
777 start = 7;
778 end = 4;
779 } else {
780 start = 3;
781 end = 0;
782 }
783 uint32_t bitsCarry = ch->wavedata[end] & 0x000000F0;
784 uint32_t bits;
785 for (i = start; i >= end; --i) {
786 bits = ch->wavedata[i] & 0x000000F0;
787 ch->wavedata[i] = ((ch->wavedata[i] & 0x0F0F0F0F) << 4) | ((ch->wavedata[i] & 0xF0F0F000) >> 12);
788 ch->wavedata[i] |= bitsCarry << 20;
789 bitsCarry = bits;
790 }
791 ch->sample = bitsCarry >> 4;
792 ch->sample -= 8;
793 ch->sample *= volume * 4;
794 return 2 * (2048 - ch->rate);
795}
796
797static int32_t _updateChannel4(struct GBAudioChannel4* ch) {
798 int lsb = ch->lfsr & 1;
799 ch->sample = lsb * 0x10 - 0x8;
800 ch->sample *= ch->envelope.currentVolume;
801 ch->lfsr >>= 1;
802 ch->lfsr ^= (lsb * 0x60) << (ch->power ? 0 : 8);
803 int timing = ch->ratio ? 2 * ch->ratio : 1;
804 timing <<= ch->frequency;
805 timing *= 8;
806 return timing;
807}