/sound.c

https://github.com/zodttd/gameboy4iphone · C · 483 lines · 410 code · 48 blank · 25 comment · 82 complexity · e323a1384883b7f5642399b39ea4241d MD5 · raw file

  1. #include "defs.h"
  2. #include "pcm.h"
  3. #include "sound.h"
  4. #include "cpu.h"
  5. #include "hw.h"
  6. #include "regs.h"
  7. #include "rc.h"
  8. #include "noise.h"
  9. const static byte dmgwave[16] =
  10. {
  11. 0xac, 0xdd, 0xda, 0x48,
  12. 0x36, 0x02, 0xcf, 0x16,
  13. 0x2c, 0x04, 0xe5, 0x2c,
  14. 0xac, 0xdd, 0xda, 0x48
  15. };
  16. const static byte cgbwave[16] =
  17. {
  18. 0x00, 0xff, 0x00, 0xff,
  19. 0x00, 0xff, 0x00, 0xff,
  20. 0x00, 0xff, 0x00, 0xff,
  21. 0x00, 0xff, 0x00, 0xff,
  22. };
  23. const static byte sqwave[4][8] =
  24. {
  25. { 0, 0,-1, 0, 0, 0, 0, 0 },
  26. { 0,-1,-1, 0, 0, 0, 0, 0 },
  27. { -1,-1,-1,-1, 0, 0, 0, 0 },
  28. { -1, 0, 0,-1,-1,-1,-1,-1 }
  29. };
  30. const static int freqtab[8] =
  31. {
  32. (1<<14)*2,
  33. (1<<14),
  34. (1<<14)/2,
  35. (1<<14)/3,
  36. (1<<14)/4,
  37. (1<<14)/5,
  38. (1<<14)/6,
  39. (1<<14)/7
  40. };
  41. struct snd snd;
  42. #define RATE (snd.rate)
  43. #define WAVE (snd.wave) /* ram.hi+0x30 */
  44. #define S1 (snd.ch[0])
  45. #define S2 (snd.ch[1])
  46. #define S3 (snd.ch[2])
  47. #define S4 (snd.ch[3])
  48. rcvar_t sound_exports[] =
  49. {
  50. RCV_END
  51. };
  52. static void s1_freq_d(int d)
  53. {
  54. if (RATE > (d<<4)) S1.freq = 0;
  55. else S1.freq = (RATE << 17)/d;
  56. }
  57. static void s1_freq()
  58. {
  59. s1_freq_d(2048 - (((R_NR14&7)<<8) + R_NR13));
  60. }
  61. static void s2_freq()
  62. {
  63. int d = 2048 - (((R_NR24&7)<<8) + R_NR23);
  64. if (RATE > (d<<4)) S2.freq = 0;
  65. else S2.freq = (RATE << 17)/d;
  66. }
  67. static void s3_freq()
  68. {
  69. int d = 2048 - (((R_NR34&7)<<8) + R_NR33);
  70. if (RATE > (d<<3)) S3.freq = 0;
  71. else S3.freq = (RATE << 21)/d;
  72. }
  73. static void s4_freq()
  74. {
  75. S4.freq = (freqtab[R_NR43&7] >> (R_NR43 >> 4)) * RATE;
  76. if (S4.freq >> 18) S4.freq = 1<<18;
  77. }
  78. void sound_dirty()
  79. {
  80. S1.swlen = ((R_NR10>>4) & 7) << 14;
  81. S1.len = (64-(R_NR11&63)) << 13;
  82. S1.envol = R_NR12 >> 4;
  83. S1.endir = (R_NR12>>3) & 1;
  84. S1.endir |= S1.endir - 1;
  85. S1.enlen = (R_NR12 & 7) << 15;
  86. s1_freq();
  87. S2.len = (64-(R_NR21&63)) << 13;
  88. S2.envol = R_NR22 >> 4;
  89. S2.endir = (R_NR22>>3) & 1;
  90. S2.endir |= S2.endir - 1;
  91. S2.enlen = (R_NR22 & 7) << 15;
  92. s2_freq();
  93. S3.len = (256-R_NR31) << 20;
  94. s3_freq();
  95. S4.len = (64-(R_NR41&63)) << 13;
  96. S4.envol = R_NR42 >> 4;
  97. S4.endir = (R_NR42>>3) & 1;
  98. S4.endir |= S4.endir - 1;
  99. S4.enlen = (R_NR42 & 7) << 15;
  100. s4_freq();
  101. }
  102. void sound_off()
  103. {
  104. memset(&S1, 0, sizeof S1);
  105. memset(&S2, 0, sizeof S2);
  106. memset(&S3, 0, sizeof S3);
  107. memset(&S4, 0, sizeof S4);
  108. R_NR10 = 0x80;
  109. R_NR11 = 0xBF;
  110. R_NR12 = 0xF3;
  111. R_NR14 = 0xBF;
  112. R_NR21 = 0x3F;
  113. R_NR22 = 0x00;
  114. R_NR24 = 0xBF;
  115. R_NR30 = 0x7F;
  116. R_NR31 = 0xFF;
  117. R_NR32 = 0x9F;
  118. R_NR33 = 0xBF;
  119. R_NR41 = 0xFF;
  120. R_NR42 = 0x00;
  121. R_NR43 = 0x00;
  122. R_NR44 = 0xBF;
  123. R_NR50 = 0x77;
  124. R_NR51 = 0xF3;
  125. R_NR52 = 0xF1;
  126. sound_dirty();
  127. }
  128. void sound_reset()
  129. {
  130. memset(&snd, 0, sizeof snd);
  131. if (pcm.hz) snd.rate = (1<<21) / pcm.hz;
  132. else snd.rate = 0;
  133. memcpy(WAVE, hw.cgb ? cgbwave : dmgwave, 16);
  134. memcpy(ram.hi+0x30, WAVE, 16);
  135. sound_off();
  136. }
  137. void sound_mix(short *sndbuf,int len)
  138. {
  139. int s, l, r, f, n;
  140. // if (!RATE || cpu.snd < RATE) return;
  141. // for (; cpu.snd >= RATE; cpu.snd -= RATE)
  142. while(len--)
  143. {
  144. l = r = 0;
  145. if (S1.on)
  146. {
  147. s = sqwave[R_NR11>>6][(S1.pos>>18)&7] & S1.envol;
  148. S1.pos += S1.freq;
  149. if ((R_NR14 & 64) && ((S1.cnt += RATE) >= S1.len))
  150. S1.on = 0;
  151. if (S1.enlen && (S1.encnt += RATE) >= S1.enlen)
  152. {
  153. S1.encnt -= S1.enlen;
  154. S1.envol += S1.endir;
  155. if (S1.envol < 0) S1.envol = 0;
  156. if (S1.envol > 15) S1.envol = 15;
  157. }
  158. if (S1.swlen && (S1.swcnt += RATE) >= S1.swlen)
  159. {
  160. S1.swcnt -= S1.swlen;
  161. f = S1.swfreq;
  162. n = (R_NR10 & 7);
  163. if (R_NR10 & 8) f -= (f >> n);
  164. else f += (f >> n);
  165. if (f > 2047)
  166. S1.on = 0;
  167. else
  168. {
  169. S1.swfreq = f;
  170. R_NR13 = f;
  171. R_NR14 = (R_NR14 & 0xF8) | (f>>8);
  172. s1_freq_d(2048 - f);
  173. }
  174. }
  175. s <<= 2;
  176. if (R_NR51 & 1) r += s;
  177. if (R_NR51 & 16) l += s;
  178. }
  179. if (S2.on)
  180. {
  181. s = sqwave[R_NR21>>6][(S2.pos>>18)&7] & S2.envol;
  182. S2.pos += S2.freq;
  183. if ((R_NR24 & 64) && ((S2.cnt += RATE) >= S2.len))
  184. S2.on = 0;
  185. if (S2.enlen && (S2.encnt += RATE) >= S2.enlen)
  186. {
  187. S2.encnt -= S2.enlen;
  188. S2.envol += S2.endir;
  189. if (S2.envol < 0) S2.envol = 0;
  190. if (S2.envol > 15) S2.envol = 15;
  191. }
  192. s <<= 2;
  193. if (R_NR51 & 2) r += s;
  194. if (R_NR51 & 32) l += s;
  195. }
  196. if (S3.on)
  197. {
  198. s = WAVE[(S3.pos>>22) & 15];
  199. if (S3.pos & (1<<21)) s &= 15;
  200. else s >>= 4;
  201. s -= 8;
  202. S3.pos += S3.freq;
  203. if ((R_NR34 & 64) && ((S3.cnt += RATE) >= S3.len))
  204. S3.on = 0;
  205. if (R_NR32 & 96) s <<= (3 - ((R_NR32>>5)&3));
  206. else s = 0;
  207. if (R_NR51 & 4) r += s;
  208. if (R_NR51 & 64) l += s;
  209. }
  210. if (S4.on)
  211. {
  212. if (R_NR43 & 8) s = 1 & (noise7[
  213. (S4.pos>>20)&15] >> (7-((S4.pos>>17)&7)));
  214. else s = 1 & (noise15[
  215. (S4.pos>>20)&4095] >> (7-((S4.pos>>17)&7)));
  216. s = (-s) & S4.envol;
  217. S4.pos += S4.freq;
  218. if ((R_NR44 & 64) && ((S4.cnt += RATE) >= S4.len))
  219. S4.on = 0;
  220. if (S4.enlen && (S4.encnt += RATE) >= S4.enlen)
  221. {
  222. S4.encnt -= S4.enlen;
  223. S4.envol += S4.endir;
  224. if (S4.envol < 0) S4.envol = 0;
  225. if (S4.envol > 15) S4.envol = 15;
  226. }
  227. s += s << 1;
  228. if (R_NR51 & 8) r += s;
  229. if (R_NR51 & 128) l += s;
  230. }
  231. l *= (R_NR50 & 0x07);
  232. r *= ((R_NR50 & 0x70)>>4);
  233. //l /= 16;
  234. //r /= 16;
  235. if (l > 511) l = 511;
  236. else if (l < -512) l = -512;
  237. if (r > 511) r = 511;
  238. else if (r < -512) r = -512;
  239. //l *= 128;
  240. //r *= 128;
  241. //if (l > 32767) l = 32767;
  242. //else if (l < -32768) l = -32768;
  243. //if (r > 32767) r = 32767;
  244. //else if (r < -32768) r = -32768;
  245. /* if (pcm.buf)
  246. {
  247. if (pcm.pos >= pcm.len)
  248. pcm_submit();
  249. if (pcm.stereo)
  250. {
  251. pcm.buf[pcm.pos++] = l+128;
  252. pcm.buf[pcm.pos++] = r+128;
  253. }
  254. else pcm.buf[pcm.pos++] = ((l+r)>>1)+128;
  255. }*/
  256. if (sndbuf)
  257. {
  258. if (pcm.stereo)
  259. {
  260. *sndbuf++ = l * 64; //+128;
  261. *sndbuf++ = r * 64; //+128;
  262. }
  263. else *sndbuf++ = ((l+r)/2) * 64; //+128;
  264. }
  265. }
  266. R_NR52 = (R_NR52&0xf0) | S1.on | (S2.on<<1) | (S3.on<<2) | (S4.on<<3);
  267. }
  268. byte sound_read(byte r)
  269. {
  270. // sound_mix(); //gp32
  271. /* printf("read %02X: %02X\n", r, REG(r)); */
  272. return REG(r);
  273. }
  274. void s1_init()
  275. {
  276. S1.swcnt = 0;
  277. S1.swfreq = ((R_NR14&7)<<8) + R_NR13;
  278. S1.envol = R_NR12 >> 4;
  279. S1.endir = (R_NR12>>3) & 1;
  280. S1.endir |= S1.endir - 1;
  281. S1.enlen = (R_NR12 & 7) << 15;
  282. if (!S1.on) S1.pos = 0;
  283. S1.on = 1;
  284. S1.cnt = 0;
  285. S1.encnt = 0;
  286. }
  287. void s2_init()
  288. {
  289. S2.envol = R_NR22 >> 4;
  290. S2.endir = (R_NR22>>3) & 1;
  291. S2.endir |= S2.endir - 1;
  292. S2.enlen = (R_NR22 & 7) << 15;
  293. if (!S2.on) S2.pos = 0;
  294. S2.on = 1;
  295. S2.cnt = 0;
  296. S2.encnt = 0;
  297. }
  298. void s3_init()
  299. {
  300. int i;
  301. if (!S3.on) S3.pos = 0;
  302. S3.cnt = 0;
  303. S3.on = R_NR30 >> 7;
  304. if (S3.on) for (i = 0; i < 16; i++)
  305. ram.hi[i+0x30] = 0x13 ^ ram.hi[i+0x31];
  306. }
  307. void s4_init()
  308. {
  309. S4.envol = R_NR42 >> 4;
  310. S4.endir = (R_NR42>>3) & 1;
  311. S4.endir |= S4.endir - 1;
  312. S4.enlen = (R_NR42 & 7) << 15;
  313. S4.on = 1;
  314. S4.pos = 0;
  315. S4.cnt = 0;
  316. S4.encnt = 0;
  317. }
  318. void sound_write(byte r, byte b)
  319. {
  320. #if 0
  321. static void *timer;
  322. if (!timer) timer = sys_timer();
  323. printf("write %02X: %02X @ %d\n", r, b, sys_elapsed(timer));
  324. #endif
  325. if (!(R_NR52 & 128) && r != RI_NR52) return;
  326. if ((r & 0xF0) == 0x30)
  327. {
  328. if (S3.on) ;//sound_mix(); //gp32
  329. if (!S3.on)
  330. WAVE[r-0x30] = ram.hi[r] = b;
  331. return;
  332. }
  333. //sound_mix(); //gp32
  334. switch (r)
  335. {
  336. case RI_NR10:
  337. R_NR10 = b;
  338. S1.swlen = ((R_NR10>>4) & 7) << 14;
  339. S1.swfreq = ((R_NR14&7)<<8) + R_NR13;
  340. break;
  341. case RI_NR11:
  342. R_NR11 = b;
  343. S1.len = (64-(R_NR11&63)) << 13;
  344. break;
  345. case RI_NR12:
  346. R_NR12 = b;
  347. S1.envol = R_NR12 >> 4;
  348. S1.endir = (R_NR12>>3) & 1;
  349. S1.endir |= S1.endir - 1;
  350. S1.enlen = (R_NR12 & 7) << 15;
  351. break;
  352. case RI_NR13:
  353. R_NR13 = b;
  354. s1_freq();
  355. break;
  356. case RI_NR14:
  357. R_NR14 = b;
  358. s1_freq();
  359. if (b & 128) s1_init();
  360. break;
  361. case RI_NR21:
  362. R_NR21 = b;
  363. S2.len = (64-(R_NR21&63)) << 13;
  364. break;
  365. case RI_NR22:
  366. R_NR22 = b;
  367. S2.envol = R_NR22 >> 4;
  368. S2.endir = (R_NR22>>3) & 1;
  369. S2.endir |= S2.endir - 1;
  370. S2.enlen = (R_NR22 & 7) << 15;
  371. break;
  372. case RI_NR23:
  373. R_NR23 = b;
  374. s2_freq();
  375. break;
  376. case RI_NR24:
  377. R_NR24 = b;
  378. s2_freq();
  379. if (b & 128) s2_init();
  380. break;
  381. case RI_NR30:
  382. R_NR30 = b;
  383. if (!(b & 128)) S3.on = 0;
  384. break;
  385. case RI_NR31:
  386. R_NR31 = b;
  387. S3.len = (256-R_NR31) << 13;
  388. break;
  389. case RI_NR32:
  390. R_NR32 = b;
  391. break;
  392. case RI_NR33:
  393. R_NR33 = b;
  394. s3_freq();
  395. break;
  396. case RI_NR34:
  397. R_NR34 = b;
  398. s3_freq();
  399. if (b & 128) s3_init();
  400. break;
  401. case RI_NR41:
  402. R_NR41 = b;
  403. S4.len = (64-(R_NR41&63)) << 13;
  404. break;
  405. case RI_NR42:
  406. R_NR42 = b;
  407. S4.envol = R_NR42 >> 4;
  408. S4.endir = (R_NR42>>3) & 1;
  409. S4.endir |= S4.endir - 1;
  410. S4.enlen = (R_NR42 & 7) << 15;
  411. break;
  412. case RI_NR43:
  413. R_NR43 = b;
  414. s4_freq();
  415. break;
  416. case RI_NR44:
  417. R_NR44 = b;
  418. if (b & 128) s4_init();
  419. break;
  420. case RI_NR50:
  421. R_NR50 = b;
  422. break;
  423. case RI_NR51:
  424. R_NR51 = b;
  425. break;
  426. case RI_NR52:
  427. R_NR52 = b;
  428. if (!(R_NR52 & 128))
  429. sound_off();
  430. break;
  431. default:
  432. return;
  433. }
  434. }