sound.c 22 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059
  1. /* -*- mode: c; tab-width: 4; c-basic-offset: 3; c-file-style: "linux" -*- */
  2. //
  3. // Copyright (c) 2009, Wei Mingzhi <whistler_wmz@users.sf.net>.
  4. // All rights reserved.
  5. //
  6. // This file is part of SDLPAL.
  7. //
  8. // SDLPAL is free software: you can redistribute it and/or modify
  9. // it under the terms of the GNU General Public License as published by
  10. // the Free Software Foundation, either version 3 of the License, or
  11. // (at your option) any later version.
  12. //
  13. // This program is distributed in the hope that it will be useful,
  14. // but WITHOUT ANY WARRANTY; without even the implied warranty of
  15. // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  16. // GNU General Public License for more details.
  17. //
  18. // You should have received a copy of the GNU General Public License
  19. // along with this program. If not, see <http://www.gnu.org/licenses/>.
  20. //
  21. #include "palcommon.h"
  22. #include "global.h"
  23. #include "palcfg.h"
  24. #include "sound.h"
  25. #include "players.h"
  26. #include "util.h"
  27. #include "resampler.h"
  28. #include "midi.h"
  29. #include <math.h>
  30. #if PAL_HAS_OGG
  31. #include <vorbis/codec.h>
  32. #endif
  33. static BOOL gSndOpened = FALSE;
  34. BOOL g_fNoSound = FALSE;
  35. BOOL g_fNoMusic = FALSE;
  36. #ifdef PAL_CLASSIC
  37. int g_iCurrChannel = 0;
  38. #endif
  39. #define PAL_CDTRACK_BASE 10000
  40. typedef LPCBYTE(*FNLoadSoundData)(LPCBYTE, DWORD, SDL_AudioSpec *);
  41. typedef struct tagSNDPLAYER
  42. {
  43. FILE *mkf;
  44. SDL_AudioSpec spec;
  45. SDL_mutex *mtx;
  46. LPBYTE buf[2], pos[2];
  47. INT audio_len[2];
  48. void *resampler;
  49. MUSICPLAYER *pMusPlayer;
  50. MUSICPLAYER *pCDPlayer;
  51. #if PAL_HAS_SDLCD
  52. SDL_CD *pCD;
  53. #endif
  54. FNLoadSoundData LoadSoundData;
  55. } SNDPLAYER;
  56. static SNDPLAYER gSndPlayer;
  57. typedef struct tagRIFFHEADER
  58. {
  59. DWORD riff_sig; /* 'RIFF' */
  60. DWORD data_length; /* Total length minus eight, little-endian */
  61. DWORD riff_type; /* 'WAVE' */
  62. } RIFFHEADER, *LPRIFFHEADER;
  63. typedef const RIFFHEADER *LPCRIFFHEADER;
  64. typedef struct tagRIFFCHUNK
  65. {
  66. DWORD chunk_type; /* 'fmt ' and so on */
  67. DWORD chunk_length; /* Total chunk length minus eight, little-endian */
  68. } RIFFCHUNK, *LPRIFFCHUNK;
  69. typedef const RIFFCHUNK *LPCRIFFCHUNK;
  70. typedef struct tagWAVEFORMATPCM
  71. {
  72. WORD wFormatTag; /* format type */
  73. WORD nChannels; /* number of channels (i.e. mono, stereo, etc.) */
  74. DWORD nSamplesPerSec; /* sample rate */
  75. DWORD nAvgBytesPerSec; /* for buffer estimation */
  76. WORD nBlockAlign; /* block size of data */
  77. WORD wBitsPerSample;
  78. } WAVEFORMATPCM, *LPWAVEFORMATPCM;
  79. typedef const WAVEFORMATPCM *LPCWAVEFORMATPCM;
  80. static LPCBYTE
  81. SOUND_LoadWAVEData(
  82. LPCBYTE lpData,
  83. DWORD dwLen,
  84. SDL_AudioSpec *lpSpec
  85. )
  86. /*++
  87. Purpose:
  88. Return the WAVE data pointer inside the input buffer.
  89. Parameters:
  90. [IN] lpData - pointer to the buffer of the WAVE file.
  91. [IN] dwLen - length of the buffer of the WAVE file.
  92. [OUT] lpSpec - pointer to the SDL_AudioSpec structure, which contains
  93. some basic information about the WAVE file.
  94. Return value:
  95. Pointer to the WAVE data inside the input buffer, NULL if failed.
  96. --*/
  97. {
  98. #if SDL_BYTEORDER == SDL_BIG_ENDIAN
  99. # define RIFF 'RIFF'
  100. # define WAVE 'WAVE'
  101. # define FMT 'fmt '
  102. # define DATA 'data'
  103. # define PCM 0x0100
  104. #else
  105. # define RIFF 'FFIR'
  106. # define WAVE 'EVAW'
  107. # define FMT ' tmf'
  108. # define DATA 'atad'
  109. # define PCM 0x0001
  110. #endif
  111. LPCRIFFHEADER lpRiff = (LPCRIFFHEADER)lpData;
  112. LPCRIFFCHUNK lpChunk;
  113. LPCWAVEFORMATPCM lpFormat = NULL;
  114. LPCBYTE lpWaveData = NULL;
  115. DWORD len;
  116. if (dwLen < sizeof(RIFFHEADER) || lpRiff->riff_sig != RIFF || lpRiff->riff_type != WAVE || dwLen < SDL_SwapLE32(lpRiff->data_length) + 8)
  117. {
  118. return NULL;
  119. }
  120. lpChunk = (LPCRIFFCHUNK)(lpRiff + 1); dwLen -= sizeof(RIFFHEADER);
  121. while (dwLen >= sizeof(RIFFCHUNK))
  122. {
  123. len = SDL_SwapLE32(lpChunk->chunk_length);
  124. if (dwLen >= sizeof(RIFFCHUNK) + len)
  125. dwLen -= sizeof(RIFFCHUNK) + len;
  126. else
  127. return NULL;
  128. switch (lpChunk->chunk_type)
  129. {
  130. case FMT:
  131. lpFormat = (LPCWAVEFORMATPCM)(lpChunk + 1);
  132. if (len != sizeof(WAVEFORMATPCM) || lpFormat->wFormatTag != PCM)
  133. {
  134. return NULL;
  135. }
  136. break;
  137. case DATA:
  138. lpWaveData = (LPCBYTE)(lpChunk + 1);
  139. dwLen = 0;
  140. break;
  141. }
  142. lpChunk = (LPCRIFFCHUNK)((LPCBYTE)(lpChunk + 1) + len);
  143. }
  144. if (lpFormat == NULL || lpWaveData == NULL)
  145. {
  146. return NULL;
  147. }
  148. lpSpec->channels = lpFormat->nChannels;
  149. lpSpec->format = (lpFormat->wBitsPerSample == 16) ? AUDIO_S16 : AUDIO_U8;
  150. lpSpec->freq = lpFormat->nSamplesPerSec;
  151. lpSpec->size = len;
  152. return lpWaveData;
  153. #undef RIFF
  154. #undef WAVE
  155. #undef FMT
  156. }
  157. typedef struct tagVOCHEADER
  158. {
  159. char signature[0x14]; /* "Creative Voice File\x1A" */
  160. WORD data_offset; /* little endian */
  161. WORD version;
  162. WORD version_checksum;
  163. } VOCHEADER, *LPVOCHEADER;
  164. typedef const VOCHEADER *LPCVOCHEADER;
  165. static LPCBYTE
  166. SOUND_LoadVOCData(
  167. LPCBYTE lpData,
  168. DWORD dwLen,
  169. SDL_AudioSpec *lpSpec
  170. )
  171. /*++
  172. Purpose:
  173. Return the VOC data pointer inside the input buffer. Currently supports type 01 block only.
  174. Parameters:
  175. [IN] lpData - pointer to the buffer of the VOC file.
  176. [IN] dwLen - length of the buffer of the VOC file.
  177. [OUT] lpSpec - pointer to the SDL_AudioSpec structure, which contains
  178. some basic information about the VOC file.
  179. Return value:
  180. Pointer to the WAVE data inside the input buffer, NULL if failed.
  181. Reference: http://sox.sourceforge.net/AudioFormats-11.html
  182. --*/
  183. {
  184. LPCVOCHEADER lpVOC = (LPCVOCHEADER)lpData;
  185. if (dwLen < sizeof(VOCHEADER) || memcmp(lpVOC->signature, "Creative Voice File\x1A", 0x14) || SDL_SwapLE16(lpVOC->data_offset) >= dwLen)
  186. {
  187. return NULL;
  188. }
  189. lpData += SDL_SwapLE16(lpVOC->data_offset);
  190. dwLen -= SDL_SwapLE16(lpVOC->data_offset);
  191. while (dwLen && *lpData)
  192. {
  193. DWORD len;
  194. if (dwLen >= 4)
  195. {
  196. len = lpData[1] | (lpData[2] << 8) | (lpData[3] << 16);
  197. if (dwLen >= len + 4)
  198. dwLen -= len + 4;
  199. else
  200. return NULL;
  201. }
  202. else
  203. {
  204. return NULL;
  205. }
  206. if (*lpData == 0x01)
  207. {
  208. if (lpData[5] != 0) return NULL; /* Only 8-bit is supported */
  209. lpSpec->format = AUDIO_U8;
  210. lpSpec->channels = 1;
  211. lpSpec->freq = ((1000000 / (256 - lpData[4]) + 99) / 100) * 100; /* Round to next 100Hz */
  212. lpSpec->size = len - 2;
  213. return lpData + 6;
  214. }
  215. else
  216. {
  217. lpData += len + 4;
  218. }
  219. }
  220. return NULL;
  221. }
  222. static void
  223. SOUND_ResampleU8(
  224. LPCBYTE lpData,
  225. const SDL_AudioSpec *lpSpec,
  226. LPBYTE lpBuffer,
  227. DWORD dwLen,
  228. void *resampler
  229. )
  230. /*++
  231. Purpose:
  232. Resample 8-bit unsigned PCM data into 16-bit signed (little-endian) PCM data.
  233. Parameters:
  234. [IN] lpData - pointer to the buffer of the input PCM data.
  235. [IN] lpSpec - pointer to the SDL_AudioSpec structure, which contains
  236. some basic information about the input PCM data.
  237. [IN] lpBuffer - pointer of the buffer of the output PCM data.
  238. [IN] dwLen - length of the buffer of the output PCM data, should be exactly
  239. the number of bytes needed of the resampled data.
  240. [IN] resampler - pointer of the resampler instance.
  241. Return value:
  242. None.
  243. --*/
  244. {
  245. int src_samples = lpSpec->size / lpSpec->channels, i;
  246. for (i = 0; i < lpSpec->channels; i++)
  247. {
  248. LPCBYTE src = lpData + i;
  249. short *dst = (short *)lpBuffer + i;
  250. int channel_len = dwLen / lpSpec->channels, total_bytes = 0;
  251. resampler_clear(resampler);
  252. while (total_bytes < channel_len && src_samples > 0)
  253. {
  254. int to_write, j;
  255. to_write = resampler_get_free_count(resampler);
  256. if (to_write > src_samples) to_write = src_samples;
  257. for (j = 0; j < to_write; j++)
  258. {
  259. resampler_write_sample(resampler, (*src ^ 0x80) << 8);
  260. src += lpSpec->channels;
  261. }
  262. src_samples -= to_write;
  263. while (total_bytes < channel_len && resampler_get_sample_count(resampler) > 0)
  264. {
  265. *dst = SDL_SwapLE16(resampler_get_and_remove_sample(resampler));
  266. dst += lpSpec->channels; total_bytes += (SDL_AUDIO_BITSIZE(AUDIO_S16) >> 3);
  267. }
  268. }
  269. /* Flush resampler's output buffer */
  270. while (total_bytes < channel_len)
  271. {
  272. int j, to_write = resampler_get_free_count(resampler);
  273. for (j = 0; j < to_write; j++)
  274. resampler_write_sample(resampler, (src[-lpSpec->channels] ^ 0x80) << 8);
  275. while (total_bytes < channel_len && resampler_get_sample_count(resampler) > 0)
  276. {
  277. *dst = SDL_SwapLE16(resampler_get_and_remove_sample(resampler));
  278. dst += lpSpec->channels; total_bytes += (SDL_AUDIO_BITSIZE(AUDIO_S16) >> 3);
  279. }
  280. }
  281. }
  282. }
  283. static void
  284. SOUND_ResampleS16(
  285. LPCBYTE lpData,
  286. const SDL_AudioSpec *lpSpec,
  287. LPBYTE lpBuffer,
  288. DWORD dwLen,
  289. void *resampler
  290. )
  291. /*++
  292. Purpose:
  293. Resample 16-bit signed (little-endian) PCM data into 16-bit signed (little-endian) PCM data.
  294. Parameters:
  295. [IN] lpData - pointer to the buffer of the input PCM data.
  296. [IN] lpSpec - pointer to the SDL_AudioSpec structure, which contains
  297. some basic information about the input PCM data.
  298. [IN] lpBuffer - pointer of the buffer of the output PCM data.
  299. [IN] dwLen - length of the buffer of the output PCM data, should be exactly
  300. the number of bytes needed of the resampled data.
  301. [IN] resampler - pointer of the resampler instance.
  302. Return value:
  303. None.
  304. --*/
  305. {
  306. int src_samples = lpSpec->size / lpSpec->channels / 2, i;
  307. for (i = 0; i < lpSpec->channels; i++)
  308. {
  309. const short *src = (short *)lpData + i;
  310. short *dst = (short *)lpBuffer + i;
  311. int channel_len = dwLen / lpSpec->channels, total_bytes = 0;
  312. resampler_clear(resampler);
  313. while (total_bytes < channel_len && src_samples > 0)
  314. {
  315. int to_write, j;
  316. to_write = resampler_get_free_count(resampler);
  317. if (to_write > src_samples) to_write = src_samples;
  318. for (j = 0; j < to_write; j++)
  319. {
  320. resampler_write_sample(resampler, SDL_SwapLE16(*src));
  321. src += lpSpec->channels;
  322. }
  323. src_samples -= to_write;
  324. while (total_bytes < channel_len && resampler_get_sample_count(resampler) > 0)
  325. {
  326. *dst = SDL_SwapLE16(resampler_get_and_remove_sample(resampler));
  327. dst += lpSpec->channels; total_bytes += (SDL_AUDIO_BITSIZE(AUDIO_S16) >> 3);
  328. }
  329. }
  330. /* Flush resampler's output buffer */
  331. while (total_bytes < channel_len)
  332. {
  333. int j, to_write = resampler_get_free_count(resampler);
  334. short val = SDL_SwapLE16(src[-lpSpec->channels]);
  335. for (j = 0; j < to_write; j++)
  336. resampler_write_sample(resampler, val);
  337. while (total_bytes < channel_len && resampler_get_sample_count(resampler) > 0)
  338. {
  339. *dst = SDL_SwapLE16(resampler_get_and_remove_sample(resampler));
  340. dst += lpSpec->channels; total_bytes += (SDL_AUDIO_BITSIZE(AUDIO_S16) >> 3);
  341. }
  342. }
  343. }
  344. }
  345. static VOID SDLCALL
  346. SOUND_FillAudio(
  347. LPVOID udata,
  348. LPBYTE stream,
  349. INT len
  350. )
  351. /*++
  352. Purpose:
  353. SDL sound callback function.
  354. Parameters:
  355. [IN] udata - pointer to user-defined parameters (Not used).
  356. [OUT] stream - pointer to the stream buffer.
  357. [IN] len - Length of the buffer.
  358. Return value:
  359. None.
  360. --*/
  361. {
  362. int i;
  363. #if SDL_VERSION_ATLEAST(2,0,0)
  364. memset(stream, 0, len);
  365. #endif
  366. //
  367. // Play music
  368. //
  369. if (!g_fNoMusic)
  370. {
  371. SDL_mutexP(gSndPlayer.mtx);
  372. if (gSndPlayer.pMusPlayer)
  373. {
  374. gSndPlayer.pMusPlayer->FillBuffer(gSndPlayer.pMusPlayer, stream, len);
  375. }
  376. if (gSndPlayer.pCDPlayer)
  377. {
  378. gSndPlayer.pCDPlayer->FillBuffer(gSndPlayer.pCDPlayer, stream, len);
  379. }
  380. SDL_mutexV(gSndPlayer.mtx);
  381. }
  382. //
  383. // No current playing sound
  384. //
  385. if (g_fNoSound)
  386. {
  387. return;
  388. }
  389. SDL_mutexP(gSndPlayer.mtx);
  390. for (i = 0; i < 2; i++)
  391. {
  392. //
  393. // Only play if we have data left
  394. //
  395. if (gSndPlayer.buf[i] == NULL)
  396. {
  397. continue;
  398. }
  399. if (gSndPlayer.audio_len[i] == 0)
  400. {
  401. //
  402. // Delete the audio buffer from memory
  403. //
  404. free(gSndPlayer.buf[i]);
  405. gSndPlayer.buf[i] = NULL;
  406. continue;
  407. }
  408. //
  409. // Mix as much data as possible
  410. //
  411. len = (len > gSndPlayer.audio_len[i]) ? gSndPlayer.audio_len[i] : len;
  412. SDL_MixAudio(stream, gSndPlayer.pos[i], len, gConfig.iVolume);
  413. gSndPlayer.pos[i] += len;
  414. gSndPlayer.audio_len[i] -= len;
  415. }
  416. SDL_mutexV(gSndPlayer.mtx);
  417. }
  418. static VOID
  419. SOUND_LoadMKF(
  420. VOID
  421. )
  422. /*++
  423. Purpose:
  424. Load MKF contents into memory.
  425. Parameters:
  426. None.
  427. Return value:
  428. None.
  429. --*/
  430. {
  431. char *mkfs[2];
  432. FNLoadSoundData func[2];
  433. int i;
  434. if (gConfig.fIsWIN95)
  435. {
  436. mkfs[0] = "sounds.mkf"; func[0] = SOUND_LoadWAVEData;
  437. mkfs[1] = "voc.mkf"; func[1] = SOUND_LoadVOCData;
  438. }
  439. else
  440. {
  441. mkfs[0] = "voc.mkf"; func[0] = SOUND_LoadVOCData;
  442. mkfs[1] = "sounds.mkf"; func[1] = SOUND_LoadWAVEData;
  443. }
  444. for (i = 0; i < 2; i++)
  445. {
  446. gSndPlayer.mkf = UTIL_OpenFile(mkfs[i]);
  447. if (gSndPlayer.mkf)
  448. {
  449. gSndPlayer.LoadSoundData = func[i];
  450. break;
  451. }
  452. }
  453. }
  454. INT
  455. SOUND_OpenAudio(
  456. VOID
  457. )
  458. /*++
  459. Purpose:
  460. Initialize the audio subsystem.
  461. Parameters:
  462. None.
  463. Return value:
  464. 0 if succeed, others if failed.
  465. --*/
  466. {
  467. SDL_AudioSpec spec;
  468. if (gSndOpened)
  469. {
  470. //
  471. // Already opened
  472. //
  473. return -1;
  474. }
  475. gSndOpened = FALSE;
  476. //
  477. // Load the MKF file.
  478. //
  479. SOUND_LoadMKF();
  480. if (gSndPlayer.mkf == NULL)
  481. {
  482. return -2;
  483. }
  484. //
  485. // Initialize the resampler
  486. //
  487. resampler_init();
  488. gSndPlayer.resampler = resampler_create();
  489. //
  490. // Open the sound subsystem.
  491. //
  492. gSndPlayer.spec.freq = gConfig.iSampleRate;
  493. gSndPlayer.spec.format = AUDIO_S16;
  494. gSndPlayer.spec.channels = gConfig.iAudioChannels;
  495. gSndPlayer.spec.samples = gConfig.wAudioBufferSize;
  496. gSndPlayer.spec.callback = SOUND_FillAudio;
  497. if (SDL_OpenAudio(&gSndPlayer.spec, &spec) < 0)
  498. {
  499. //
  500. // Failed
  501. //
  502. return -3;
  503. }
  504. memcpy(&gSndPlayer.spec, &spec, sizeof(SDL_AudioSpec));
  505. gSndPlayer.buf[0] = NULL;
  506. gSndPlayer.pos[0] = NULL;
  507. gSndPlayer.audio_len[0] = 0;
  508. gSndPlayer.buf[1] = NULL;
  509. gSndPlayer.pos[1] = NULL;
  510. gSndPlayer.audio_len[1] = 0;
  511. gSndPlayer.mtx = SDL_CreateMutex();
  512. gSndOpened = TRUE;
  513. //
  514. // Initialize the music subsystem.
  515. //
  516. switch (gConfig.eMusicType)
  517. {
  518. case MUSIC_RIX:
  519. if (!(gSndPlayer.pMusPlayer = RIX_Init(va("%s%s", gConfig.pszGamePath, "mus.mkf"))))
  520. {
  521. gSndPlayer.pMusPlayer = RIX_Init(va("%s%s", gConfig.pszGamePath, "MUS.MKF"));
  522. }
  523. break;
  524. case MUSIC_MP3:
  525. #if PAL_HAS_MP3
  526. gSndPlayer.pMusPlayer = MP3_Init(NULL);
  527. #else
  528. gSndPlayer.pMusPlayer = NULL;
  529. #endif
  530. break;
  531. case MUSIC_OGG:
  532. #if PAL_HAS_OGG
  533. gSndPlayer.pMusPlayer = OGG_Init(NULL);
  534. #else
  535. gSndPlayer.pMusPlayer = NULL;
  536. #endif
  537. break;
  538. case MUSIC_MIDI:
  539. gSndPlayer.pMusPlayer = NULL;
  540. break;
  541. }
  542. //
  543. // Initialize the CD audio.
  544. //
  545. switch (gConfig.eCDType)
  546. {
  547. case MUSIC_SDLCD:
  548. {
  549. #if PAL_HAS_SDLCD
  550. int i;
  551. gSndPlayer.pCD = NULL;
  552. for (i = 0; i < SDL_CDNumDrives(); i++)
  553. {
  554. gSndPlayer.pCD = SDL_CDOpen(i);
  555. if (gSndPlayer.pCD != NULL)
  556. {
  557. if (!CD_INDRIVE(SDL_CDStatus(gSndPlayer.pCD)))
  558. {
  559. SDL_CDClose(gSndPlayer.pCD);
  560. gSndPlayer.pCD = NULL;
  561. }
  562. else
  563. {
  564. break;
  565. }
  566. }
  567. }
  568. #endif
  569. gSndPlayer.pCDPlayer = NULL;
  570. break;
  571. }
  572. case MUSIC_MP3:
  573. #if PAL_HAS_MP3
  574. gSndPlayer.pCDPlayer = MP3_Init(NULL);
  575. #else
  576. gSndPlayer.pCDPlayer = NULL;
  577. #endif
  578. break;
  579. case MUSIC_OGG:
  580. #if PAL_HAS_OGG
  581. gSndPlayer.pCDPlayer = OGG_Init(NULL);
  582. #else
  583. gSndPlayer.pCDPlayer = NULL;
  584. #endif
  585. break;
  586. }
  587. //
  588. // Let the callback function run so that musics will be played.
  589. //
  590. SDL_PauseAudio(0);
  591. return 0;
  592. }
  593. VOID
  594. SOUND_CloseAudio(
  595. VOID
  596. )
  597. /*++
  598. Purpose:
  599. Close the audio subsystem.
  600. Parameters:
  601. None.
  602. Return value:
  603. None.
  604. --*/
  605. {
  606. SDL_CloseAudio();
  607. SDL_mutexP(gSndPlayer.mtx);
  608. if (gSndPlayer.buf[0] != NULL)
  609. {
  610. free(gSndPlayer.buf[0]);
  611. gSndPlayer.buf[0] = NULL;
  612. }
  613. if (gSndPlayer.buf[1] != NULL)
  614. {
  615. free(gSndPlayer.buf[1]);
  616. gSndPlayer.buf[1] = NULL;
  617. }
  618. if (gSndPlayer.mkf != NULL)
  619. {
  620. fclose(gSndPlayer.mkf);
  621. gSndPlayer.mkf = NULL;
  622. }
  623. if (gSndPlayer.pMusPlayer)
  624. {
  625. gSndPlayer.pMusPlayer->Shutdown(gSndPlayer.pMusPlayer);
  626. gSndPlayer.pMusPlayer = NULL;
  627. }
  628. if (gSndPlayer.pCDPlayer)
  629. {
  630. gSndPlayer.pCDPlayer->Shutdown(gSndPlayer.pCDPlayer);
  631. gSndPlayer.pCDPlayer = NULL;
  632. }
  633. #if PAL_HAS_SDLCD
  634. if (gSndPlayer.pCD != NULL)
  635. {
  636. SOUND_PlayCDA(-1);
  637. SDL_CDClose(gSndPlayer.pCD);
  638. }
  639. #endif
  640. if (gConfig.eMusicType == MUSIC_MIDI) MIDI_Play(0, FALSE);
  641. if (gSndPlayer.resampler)
  642. {
  643. resampler_delete(gSndPlayer.resampler);
  644. gSndPlayer.resampler = NULL;
  645. }
  646. SDL_mutexV(gSndPlayer.mtx);
  647. SDL_DestroyMutex(gSndPlayer.mtx);
  648. }
  649. SDL_AudioSpec*
  650. SOUND_GetAudioSpec(
  651. VOID
  652. )
  653. {
  654. return &gSndPlayer.spec;
  655. }
  656. VOID
  657. SOUND_AdjustVolume(
  658. INT iDirection
  659. )
  660. /*++
  661. Purpose:
  662. SDL sound volume adjust function.
  663. Parameters:
  664. [IN] iDirection - value, Increase (>0) or decrease (<=0) 3% volume.
  665. Return value:
  666. None.
  667. --*/
  668. {
  669. if (iDirection > 0)
  670. {
  671. gConfig.iVolume += SDL_MIX_MAXVOLUME * 0.03;
  672. if (gConfig.iVolume > SDL_MIX_MAXVOLUME)
  673. {
  674. gConfig.iVolume = SDL_MIX_MAXVOLUME;
  675. }
  676. }
  677. else
  678. {
  679. gConfig.iVolume -= SDL_MIX_MAXVOLUME * 0.03;
  680. if (gConfig.iVolume < 0)
  681. {
  682. gConfig.iVolume = 0;
  683. }
  684. }
  685. }
  686. VOID
  687. SOUND_PlayChannel(
  688. INT iSoundNum,
  689. INT iChannel
  690. )
  691. /*++
  692. Purpose:
  693. Play a sound in voc.mkf file.
  694. Parameters:
  695. [IN] iSoundNum - number of the sound.
  696. [IN] iChannel - the number of channel (0 or 1).
  697. Return value:
  698. None.
  699. --*/
  700. {
  701. SDL_AudioCVT wavecvt;
  702. SDL_AudioSpec wavespec;
  703. LPBYTE buf, bufdec;
  704. LPCBYTE bufsrc;
  705. int len;
  706. if (!gSndOpened || g_fNoSound)
  707. {
  708. return;
  709. }
  710. //
  711. // Stop playing current sound.
  712. //
  713. SDL_mutexP(gSndPlayer.mtx);
  714. if (gSndPlayer.buf[iChannel] != NULL)
  715. {
  716. free(gSndPlayer.buf[iChannel]);
  717. gSndPlayer.buf[iChannel] = NULL;
  718. }
  719. SDL_mutexV(gSndPlayer.mtx);
  720. if (iSoundNum < 0)
  721. {
  722. return;
  723. }
  724. //
  725. // Get the length of the sound file.
  726. //
  727. len = PAL_MKFGetChunkSize(iSoundNum, gSndPlayer.mkf);
  728. if (len <= 0)
  729. {
  730. return;
  731. }
  732. buf = (LPBYTE)malloc(len);
  733. if (buf == NULL)
  734. {
  735. return;
  736. }
  737. //
  738. // Read the sound file from the MKF archive.
  739. //
  740. PAL_MKFReadChunk(buf, len, iSoundNum, gSndPlayer.mkf);
  741. bufsrc = gSndPlayer.LoadSoundData(buf, len, &wavespec);
  742. if (bufsrc == NULL)
  743. {
  744. free(buf);
  745. return;
  746. }
  747. if (wavespec.freq != gSndPlayer.spec.freq)
  748. {
  749. /* Resampler is needed */
  750. resampler_set_quality(gSndPlayer.resampler, SOUND_IsIntegerConversion(wavespec.freq) ? RESAMPLER_QUALITY_MIN : gConfig.iResampleQuality);
  751. resampler_set_rate(gSndPlayer.resampler, (double)wavespec.freq / (double)gSndPlayer.spec.freq);
  752. len = (int)ceil(wavespec.size * (double)gSndPlayer.spec.freq / (double)wavespec.freq) * (SDL_AUDIO_BITSIZE(AUDIO_S16) / SDL_AUDIO_BITSIZE(wavespec.format));
  753. if (len >= wavespec.channels * 2 && (bufdec = malloc(len)))
  754. {
  755. if (wavespec.format == AUDIO_S16)
  756. SOUND_ResampleS16(bufsrc, &wavespec, bufdec, len, gSndPlayer.resampler);
  757. else
  758. SOUND_ResampleU8(bufsrc, &wavespec, bufdec, len, gSndPlayer.resampler);
  759. /* Free the original buffer and reset the pointer for simpler later operations */
  760. free(buf); buf = bufdec;
  761. wavespec.format = AUDIO_S16;
  762. wavespec.freq = gSndPlayer.spec.freq;
  763. }
  764. else
  765. {
  766. free(buf);
  767. return;
  768. }
  769. }
  770. else
  771. {
  772. bufdec = (LPBYTE)bufsrc;
  773. len = wavespec.size;
  774. }
  775. //
  776. // Build the audio converter and create conversion buffers
  777. //
  778. if (SDL_BuildAudioCVT(&wavecvt, wavespec.format, wavespec.channels, wavespec.freq,
  779. gSndPlayer.spec.format, gSndPlayer.spec.channels, gSndPlayer.spec.freq) < 0)
  780. {
  781. free(buf);
  782. return;
  783. }
  784. wavecvt.len = len & ~((SDL_AUDIO_BITSIZE(wavespec.format) >> 3) * wavespec.channels - 1);
  785. wavecvt.buf = (LPBYTE)malloc(wavecvt.len * wavecvt.len_mult);
  786. if (wavecvt.buf == NULL)
  787. {
  788. free(buf);
  789. return;
  790. }
  791. memcpy(wavecvt.buf, bufdec, len);
  792. free(buf);
  793. //
  794. // Run the audio converter
  795. //
  796. if (SDL_ConvertAudio(&wavecvt) < 0)
  797. {
  798. free(wavecvt.buf);
  799. return;
  800. }
  801. SDL_mutexP(gSndPlayer.mtx);
  802. if (gSndPlayer.buf[iChannel] != NULL)
  803. {
  804. free(gSndPlayer.buf[iChannel]);
  805. gSndPlayer.buf[iChannel] = NULL;
  806. }
  807. gSndPlayer.buf[iChannel] = wavecvt.buf;
  808. gSndPlayer.audio_len[iChannel] = wavecvt.len * wavecvt.len_mult;
  809. gSndPlayer.pos[iChannel] = wavecvt.buf;
  810. SDL_mutexV(gSndPlayer.mtx);
  811. }
  812. VOID
  813. SOUND_PlayMUS(
  814. INT iNumRIX,
  815. BOOL fLoop,
  816. FLOAT flFadeTime
  817. )
  818. {
  819. SDL_mutexP(gSndPlayer.mtx);
  820. if (gConfig.eMusicType == MUSIC_MIDI)
  821. {
  822. MIDI_Play(iNumRIX, fLoop);
  823. }
  824. else if (gSndPlayer.pMusPlayer)
  825. {
  826. gSndPlayer.pMusPlayer->Play(gSndPlayer.pMusPlayer, iNumRIX, fLoop, flFadeTime);
  827. }
  828. SDL_mutexV(gSndPlayer.mtx);
  829. }
  830. BOOL
  831. SOUND_PlayCDA(
  832. INT iNumTrack
  833. )
  834. /*++
  835. Purpose:
  836. Play a CD Audio Track.
  837. Parameters:
  838. [IN] iNumTrack - number of the CD Audio Track.
  839. Return value:
  840. TRUE if the track can be played, FALSE if not.
  841. --*/
  842. {
  843. BOOL ret = FALSE;
  844. #if PAL_HAS_SDLCD
  845. if (gSndPlayer.pCD != NULL)
  846. {
  847. if (CD_INDRIVE(SDL_CDStatus(gSndPlayer.pCD)))
  848. {
  849. SDL_CDStop(gSndPlayer.pCD);
  850. if (iNumTrack != -1)
  851. {
  852. SOUND_PlayMUS(-1, FALSE, 0);
  853. if (SDL_CDPlayTracks(gSndPlayer.pCD, iNumTrack - 1, 0, 1, 0) == 0)
  854. {
  855. return TRUE;
  856. }
  857. }
  858. }
  859. }
  860. #endif
  861. SDL_mutexP(gSndPlayer.mtx);
  862. if (gSndPlayer.pCDPlayer)
  863. {
  864. if (iNumTrack != -1)
  865. {
  866. SOUND_PlayMUS(-1, FALSE, 0);
  867. ret = gSndPlayer.pCDPlayer->Play(gSndPlayer.pCDPlayer, PAL_CDTRACK_BASE + iNumTrack, TRUE, 0);
  868. }
  869. else
  870. {
  871. ret = gSndPlayer.pCDPlayer->Play(gSndPlayer.pCDPlayer, -1, FALSE, 0);
  872. }
  873. }
  874. SDL_mutexV(gSndPlayer.mtx);
  875. return ret;
  876. }
  877. #ifdef PSP
  878. void
  879. SOUND_Reload(
  880. void
  881. )
  882. {
  883. fclose(gSndPlayer.mkf);
  884. SOUND_LoadMKF();
  885. }
  886. #endif