Pushed the final changes that got audio working!
This commit is contained in:
@@ -35,11 +35,6 @@
|
|||||||
#define SAMPLES_TO_OVERPRODUCE 0x10
|
#define SAMPLES_TO_OVERPRODUCE 0x10
|
||||||
#define EXTRA_BUFFERED_AI_SAMPLES_TARGET 0x40
|
#define EXTRA_BUFFERED_AI_SAMPLES_TARGET 0x40
|
||||||
|
|
||||||
struct Sound {
|
|
||||||
s32 soundBits;
|
|
||||||
f32 *position;
|
|
||||||
}; // size = 0x8
|
|
||||||
|
|
||||||
struct ChannelVolumeScaleFade {
|
struct ChannelVolumeScaleFade {
|
||||||
f32 velocity;
|
f32 velocity;
|
||||||
u8 target;
|
u8 target;
|
||||||
@@ -413,7 +408,7 @@ extern void func_802ad74c(u32 bits, u32 arg);
|
|||||||
extern void func_802ad770(u32 bits, s8 arg);
|
extern void func_802ad770(u32 bits, s8 arg);
|
||||||
|
|
||||||
static void update_background_music_after_sound(u8 bank, u8 soundIndex);
|
static void update_background_music_after_sound(u8 bank, u8 soundIndex);
|
||||||
static void update_game_sound(void);
|
void update_game_sound(void);
|
||||||
static void fade_channel_volume_scale(u8 player, u8 channelId, u8 targetScale, u16 fadeTimer);
|
static void fade_channel_volume_scale(u8 player, u8 channelId, u8 targetScale, u16 fadeTimer);
|
||||||
void process_level_music_dynamics(void);
|
void process_level_music_dynamics(void);
|
||||||
static u8 begin_background_music_fade(u16 fadeDuration);
|
static u8 begin_background_music_fade(u16 fadeDuration);
|
||||||
@@ -663,7 +658,11 @@ extern void func_sh_802F64C8(void);
|
|||||||
* Called from threads: thread5_game_loop
|
* Called from threads: thread5_game_loop
|
||||||
*/
|
*/
|
||||||
void maybe_tick_game_sound(void) {
|
void maybe_tick_game_sound(void) {
|
||||||
|
DEBUG_PRINT("maybe_tick_game_sound()");
|
||||||
|
|
||||||
|
DEBUG_PRINT("- if game loop ticked is false...");
|
||||||
if (sGameLoopTicked != 0) {
|
if (sGameLoopTicked != 0) {
|
||||||
|
DEBUG_PRINT("- updating game sound");
|
||||||
update_game_sound();
|
update_game_sound();
|
||||||
sGameLoopTicked = 0;
|
sGameLoopTicked = 0;
|
||||||
}
|
}
|
||||||
@@ -794,14 +793,17 @@ struct SPTask *create_next_audio_frame_task(void) {
|
|||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
void create_next_audio_buffer(s16 *samples, u32 num_samples) {
|
void create_next_audio_buffer(s16 *samples, u32 num_samples) {
|
||||||
|
DEBUG_PRINT("create_next_audio_buffer()");
|
||||||
gAudioFrameCount++;
|
gAudioFrameCount++;
|
||||||
if (sGameLoopTicked != 0) {
|
if (sGameLoopTicked != 0) {
|
||||||
update_game_sound();
|
update_game_sound();
|
||||||
sGameLoopTicked = 0;
|
sGameLoopTicked = 0;
|
||||||
}
|
}
|
||||||
s32 writtenCmds;
|
s32 writtenCmds;
|
||||||
|
DEBUG_PRINT("- synthesis execute");
|
||||||
synthesis_execute(gAudioCmdBuffers[0], &writtenCmds, samples, num_samples);
|
synthesis_execute(gAudioCmdBuffers[0], &writtenCmds, samples, num_samples);
|
||||||
gAudioRandom = ((gAudioRandom + gAudioFrameCount) * gAudioFrameCount);
|
gAudioRandom = ((gAudioRandom + gAudioFrameCount) * gAudioFrameCount);
|
||||||
|
DEBUG_PRINT("- decrease sample dma ttls");
|
||||||
decrease_sample_dma_ttls();
|
decrease_sample_dma_ttls();
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
@@ -811,7 +813,7 @@ void create_next_audio_buffer(s16 *samples, u32 num_samples) {
|
|||||||
* Called from threads: thread4_sound, thread5_game_loop (EU only)
|
* Called from threads: thread4_sound, thread5_game_loop (EU only)
|
||||||
*/
|
*/
|
||||||
static void process_sound_request(u32 bits, f32 *pos) {
|
static void process_sound_request(u32 bits, f32 *pos) {
|
||||||
//DEBUG_PRINT("process_sound_request %d\n", bits);
|
DEBUG_PRINT("# process_sound_request %d\n", bits);
|
||||||
u8 bank;
|
u8 bank;
|
||||||
u8 soundIndex;
|
u8 soundIndex;
|
||||||
u8 counter = 0;
|
u8 counter = 0;
|
||||||
@@ -874,7 +876,7 @@ static void process_sound_request(u32 bits, f32 *pos) {
|
|||||||
|
|
||||||
// If free list has more than one element remaining
|
// If free list has more than one element remaining
|
||||||
if (sSoundBanks[bank][sSoundBankFreeListFront[bank]].next != 0xff && soundIndex != 0) {
|
if (sSoundBanks[bank][sSoundBankFreeListFront[bank]].next != 0xff && soundIndex != 0) {
|
||||||
//DEBUG_PRINT("process_sound_request2: soundIndex %d\n", soundIndex);
|
DEBUG_PRINT("process_sound_request2: soundIndex %d\n", soundIndex);
|
||||||
// Allocate from free list
|
// Allocate from free list
|
||||||
soundIndex = sSoundBankFreeListFront[bank];
|
soundIndex = sSoundBankFreeListFront[bank];
|
||||||
|
|
||||||
@@ -1333,7 +1335,7 @@ void audio_signal_game_loop_tick(void) {
|
|||||||
/**
|
/**
|
||||||
* Called from threads: thread4_sound, thread5_game_loop (EU and SH only)
|
* Called from threads: thread4_sound, thread5_game_loop (EU and SH only)
|
||||||
*/
|
*/
|
||||||
static void update_game_sound(void) {
|
void update_game_sound(void) {
|
||||||
u8 soundStatus;
|
u8 soundStatus;
|
||||||
u8 i;
|
u8 i;
|
||||||
u8 soundId;
|
u8 soundId;
|
||||||
@@ -2628,6 +2630,7 @@ void play_toads_jingle(void) {
|
|||||||
* Called from threads: thread5_game_loop
|
* Called from threads: thread5_game_loop
|
||||||
*/
|
*/
|
||||||
void sound_reset(u8 presetId) {
|
void sound_reset(u8 presetId) {
|
||||||
|
DEBUG_PRINT("sound_reset()");
|
||||||
#ifndef VERSION_JP
|
#ifndef VERSION_JP
|
||||||
if (presetId >= 8) {
|
if (presetId >= 8) {
|
||||||
presetId = 0;
|
presetId = 0;
|
||||||
@@ -2635,26 +2638,35 @@ void sound_reset(u8 presetId) {
|
|||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
sGameLoopTicked = 0;
|
sGameLoopTicked = 0;
|
||||||
|
DEBUG_PRINT("- disable all sequence players");
|
||||||
disable_all_sequence_players();
|
disable_all_sequence_players();
|
||||||
|
DEBUG_PRINT("- sound init");
|
||||||
sound_init();
|
sound_init();
|
||||||
#ifdef VERSION_SH
|
#ifdef VERSION_SH
|
||||||
func_802ad74c(0xF2000000, 0);
|
func_802ad74c(0xF2000000, 0);
|
||||||
#endif
|
#endif
|
||||||
#if defined(VERSION_JP) || defined(VERSION_US)
|
#if defined(VERSION_JP) || defined(VERSION_US)
|
||||||
|
DEBUG_PRINT("- audio reset session");
|
||||||
audio_reset_session(&gAudioSessionPresets[presetId]);
|
audio_reset_session(&gAudioSessionPresets[presetId]);
|
||||||
#else
|
#else
|
||||||
audio_reset_session_eu(presetId);
|
audio_reset_session_eu(presetId);
|
||||||
#endif
|
#endif
|
||||||
|
DEBUG_PRINT("- os write back dcache all");
|
||||||
osWritebackDCacheAll();
|
osWritebackDCacheAll();
|
||||||
if (presetId != 7) {
|
if (presetId != 7) {
|
||||||
|
DEBUG_PRINT("- preloading solve puzzle sequence");
|
||||||
preload_sequence(SEQ_EVENT_SOLVE_PUZZLE, PRELOAD_BANKS | PRELOAD_SEQUENCE);
|
preload_sequence(SEQ_EVENT_SOLVE_PUZZLE, PRELOAD_BANKS | PRELOAD_SEQUENCE);
|
||||||
|
DEBUG_PRINT("- preloading peach message");
|
||||||
preload_sequence(SEQ_EVENT_PEACH_MESSAGE, PRELOAD_BANKS | PRELOAD_SEQUENCE);
|
preload_sequence(SEQ_EVENT_PEACH_MESSAGE, PRELOAD_BANKS | PRELOAD_SEQUENCE);
|
||||||
|
DEBUG_PRINT("- preloading star spawn");
|
||||||
preload_sequence(SEQ_EVENT_CUTSCENE_STAR_SPAWN, PRELOAD_BANKS | PRELOAD_SEQUENCE);
|
preload_sequence(SEQ_EVENT_CUTSCENE_STAR_SPAWN, PRELOAD_BANKS | PRELOAD_SEQUENCE);
|
||||||
}
|
}
|
||||||
|
DEBUG_PRINT("- playing sfx sequence");
|
||||||
seq_player_play_sequence(SEQ_PLAYER_SFX, SEQ_SOUND_PLAYER, 0);
|
seq_player_play_sequence(SEQ_PLAYER_SFX, SEQ_SOUND_PLAYER, 0);
|
||||||
D_80332108 = (D_80332108 & 0xf0) + presetId;
|
D_80332108 = (D_80332108 & 0xf0) + presetId;
|
||||||
gSoundMode = D_80332108 >> 4;
|
gSoundMode = D_80332108 >> 4;
|
||||||
sHasStartedFadeOut = FALSE;
|
sHasStartedFadeOut = FALSE;
|
||||||
|
DEBUG_PRINT("- done resetting sound");
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
@@ -24,11 +24,20 @@ extern u32 gAudioRandom;
|
|||||||
extern f32 gAudioVolume;
|
extern f32 gAudioVolume;
|
||||||
extern u8 gAudioReverb;
|
extern u8 gAudioReverb;
|
||||||
|
|
||||||
|
struct Sound {
|
||||||
|
s32 soundBits;
|
||||||
|
f32 *position;
|
||||||
|
}; // size = 0x8
|
||||||
|
|
||||||
|
extern struct Sound sSoundRequests[0x100];
|
||||||
|
extern u8 sSoundRequestCount;
|
||||||
|
|
||||||
extern u8 gAudioSPTaskYieldBuffer[]; // ucode yield data ptr; only used in JP
|
extern u8 gAudioSPTaskYieldBuffer[]; // ucode yield data ptr; only used in JP
|
||||||
|
|
||||||
struct SPTask *create_next_audio_frame_task(void);
|
struct SPTask *create_next_audio_frame_task(void);
|
||||||
void create_next_audio_buffer(s16 *samples, u32 num_samples);
|
void create_next_audio_buffer(s16 *samples, u32 num_samples);
|
||||||
void audio_signal_game_loop_tick(void);
|
void audio_signal_game_loop_tick(void);
|
||||||
|
void update_game_sound(void);
|
||||||
void seq_player_fade_out(u8 player, u16 fadeDuration);
|
void seq_player_fade_out(u8 player, u16 fadeDuration);
|
||||||
void fade_volume_scale(u8 player, u8 targetScale, u16 fadeDuration);
|
void fade_volume_scale(u8 player, u8 targetScale, u16 fadeDuration);
|
||||||
void seq_player_lower_volume(u8 player, u16 fadeDuration, u8 percentage);
|
void seq_player_lower_volume(u8 player, u16 fadeDuration, u8 percentage);
|
||||||
@@ -41,7 +50,6 @@ void stop_sounds_from_source(f32 *pos);
|
|||||||
void stop_sounds_in_continuous_banks(void);
|
void stop_sounds_in_continuous_banks(void);
|
||||||
void sound_banks_disable(u8 player, u16 bankMask);
|
void sound_banks_disable(u8 player, u16 bankMask);
|
||||||
void sound_banks_enable(u8 player, u16 bankMask);
|
void sound_banks_enable(u8 player, u16 bankMask);
|
||||||
void func_80320A4C(u8 bankIndex, u8 arg1);
|
|
||||||
void set_sound_moving_speed(u8 bank, u8 speed);
|
void set_sound_moving_speed(u8 bank, u8 speed);
|
||||||
void play_dialog_sound(u8 dialogID);
|
void play_dialog_sound(u8 dialogID);
|
||||||
void play_music(u8 player, u16 seqArgs, u16 fadeTimer);
|
void play_music(u8 player, u16 seqArgs, u16 fadeTimer);
|
||||||
|
|||||||
+2
-21
@@ -1,5 +1,6 @@
|
|||||||
#include <ultra64.h>
|
#include <ultra64.h>
|
||||||
|
|
||||||
|
#include "../../debug_print.h"
|
||||||
#include "heap.h"
|
#include "heap.h"
|
||||||
#include "data.h"
|
#include "data.h"
|
||||||
#include "load.h"
|
#include "load.h"
|
||||||
@@ -252,26 +253,7 @@ void discard_sequence(s32 seqId) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void *soundAlloc(struct SoundAllocPool *pool, u32 size) {
|
void *soundAlloc(struct SoundAllocPool *pool, u32 size) {
|
||||||
#if defined(VERSION_EU) || defined(VERSION_SH)
|
DEBUG_PRINT("soundAlloc()");
|
||||||
u8 *start;
|
|
||||||
u8 *pos;
|
|
||||||
u32 alignedSize = ALIGN16(size);
|
|
||||||
|
|
||||||
start = pool->cur;
|
|
||||||
if (start + alignedSize <= pool->start + pool->size) {
|
|
||||||
pool->cur += alignedSize;
|
|
||||||
for (pos = start; pos < pool->cur; pos++) {
|
|
||||||
*pos = 0;
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
eu_stubbed_printf_1("Heap OverFlow : Not Allocate %d!\n", size);
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
#ifdef VERSION_SH
|
|
||||||
pool->numAllocatedEntries++;
|
|
||||||
#endif
|
|
||||||
return start;
|
|
||||||
#else
|
|
||||||
u8 *start;
|
u8 *start;
|
||||||
s32 last;
|
s32 last;
|
||||||
s32 i;
|
s32 i;
|
||||||
@@ -287,7 +269,6 @@ void *soundAlloc(struct SoundAllocPool *pool, u32 size) {
|
|||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
return start;
|
return start;
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef VERSION_SH
|
#ifdef VERSION_SH
|
||||||
|
|||||||
+53
-62
@@ -1,6 +1,7 @@
|
|||||||
#ifndef VERSION_SH
|
#ifndef VERSION_SH
|
||||||
#include <ultra64.h>
|
#include <ultra64.h>
|
||||||
|
|
||||||
|
#include "../../debug_print.h"
|
||||||
#include "data.h"
|
#include "data.h"
|
||||||
#include "external.h"
|
#include "external.h"
|
||||||
#include "heap.h"
|
#include "heap.h"
|
||||||
@@ -110,10 +111,17 @@ ALSeqFile *get_audio_file_header(s32 arg0);
|
|||||||
* Performs an immediate DMA copy
|
* Performs an immediate DMA copy
|
||||||
*/
|
*/
|
||||||
void audio_dma_copy_immediate(uintptr_t devAddr, void *vAddr, size_t nbytes) {
|
void audio_dma_copy_immediate(uintptr_t devAddr, void *vAddr, size_t nbytes) {
|
||||||
|
DEBUG_PRINT("audio_dma_copy_immediate()");
|
||||||
|
DEBUG_PRINT("- dev addr: %x", devAddr);
|
||||||
|
DEBUG_PRINT("- vAddr: %x", vAddr);
|
||||||
|
DEBUG_PRINT("- # bytes: %d", nbytes);
|
||||||
eu_stubbed_printf_3("Romcopy %x -> %x ,size %x\n", devAddr, vAddr, nbytes);
|
eu_stubbed_printf_3("Romcopy %x -> %x ,size %x\n", devAddr, vAddr, nbytes);
|
||||||
|
DEBUG_PRINT("- invalidate d cache");
|
||||||
osInvalDCache(vAddr, nbytes);
|
osInvalDCache(vAddr, nbytes);
|
||||||
|
DEBUG_PRINT("- start dma");
|
||||||
osPiStartDma(&gAudioDmaIoMesg, OS_MESG_PRI_HIGH, OS_READ, devAddr, vAddr, nbytes,
|
osPiStartDma(&gAudioDmaIoMesg, OS_MESG_PRI_HIGH, OS_READ, devAddr, vAddr, nbytes,
|
||||||
&gAudioDmaMesgQueue);
|
&gAudioDmaMesgQueue);
|
||||||
|
DEBUG_PRINT("- recv message");
|
||||||
osRecvMesg(&gAudioDmaMesgQueue, NULL, OS_MESG_BLOCK);
|
osRecvMesg(&gAudioDmaMesgQueue, NULL, OS_MESG_BLOCK);
|
||||||
eu_stubbed_printf_0("Romcopyend\n");
|
eu_stubbed_printf_0("Romcopyend\n");
|
||||||
}
|
}
|
||||||
@@ -580,6 +588,8 @@ l2:
|
|||||||
}
|
}
|
||||||
|
|
||||||
struct AudioBank *bank_load_immediate(s32 bankId, s32 arg1) {
|
struct AudioBank *bank_load_immediate(s32 bankId, s32 arg1) {
|
||||||
|
DEBUG_PRINT("bank_load_immediate()");
|
||||||
|
|
||||||
UNUSED u32 pad1[4];
|
UNUSED u32 pad1[4];
|
||||||
u32 buf[4];
|
u32 buf[4];
|
||||||
u32 numInstruments, numDrums;
|
u32 numInstruments, numDrums;
|
||||||
@@ -589,24 +599,35 @@ struct AudioBank *bank_load_immediate(s32 bankId, s32 arg1) {
|
|||||||
|
|
||||||
// (This is broken if the length is 1 (mod 16), but that never happens --
|
// (This is broken if the length is 1 (mod 16), but that never happens --
|
||||||
// it's always divisible by 4.)
|
// it's always divisible by 4.)
|
||||||
|
DEBUG_PRINT("- getting alloc");
|
||||||
alloc = gAlCtlHeader->seqArray[bankId].len + 0xf;
|
alloc = gAlCtlHeader->seqArray[bankId].len + 0xf;
|
||||||
|
DEBUG_PRINT("- aligning");
|
||||||
alloc = ALIGN16(alloc);
|
alloc = ALIGN16(alloc);
|
||||||
alloc -= 0x10;
|
alloc -= 0x10;
|
||||||
|
DEBUG_PRINT("- getting ctl data for bank %d", bankId);
|
||||||
ctlData = gAlCtlHeader->seqArray[bankId].offset;
|
ctlData = gAlCtlHeader->seqArray[bankId].offset;
|
||||||
|
DEBUG_PRINT("- alloc bank or seq");
|
||||||
ret = alloc_bank_or_seq(&gBankLoadedPool, 1, alloc, arg1, bankId);
|
ret = alloc_bank_or_seq(&gBankLoadedPool, 1, alloc, arg1, bankId);
|
||||||
if (ret == NULL) {
|
if (ret == NULL) {
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
DEBUG_PRINT("- copying dma immediate 1");
|
||||||
|
DEBUG_PRINT("- ctlData: %x", ctlData);
|
||||||
audio_dma_copy_immediate((uintptr_t) ctlData, buf, 0x10);
|
audio_dma_copy_immediate((uintptr_t) ctlData, buf, 0x10);
|
||||||
|
DEBUG_PRINT("- getting nums");
|
||||||
numInstruments = buf[0];
|
numInstruments = buf[0];
|
||||||
numDrums = buf[1];
|
numDrums = buf[1];
|
||||||
|
DEBUG_PRINT("- copying dma immediate 2");
|
||||||
audio_dma_copy_immediate((uintptr_t)(ctlData + 0x10), ret, alloc);
|
audio_dma_copy_immediate((uintptr_t)(ctlData + 0x10), ret, alloc);
|
||||||
|
DEBUG_PRINT("- patching bank");
|
||||||
patch_audio_bank(ret, gAlTbl->seqArray[bankId].offset, numInstruments, numDrums);
|
patch_audio_bank(ret, gAlTbl->seqArray[bankId].offset, numInstruments, numDrums);
|
||||||
|
DEBUG_PRINT("- setting ctl entries");
|
||||||
gCtlEntries[bankId].numInstruments = (u8) numInstruments;
|
gCtlEntries[bankId].numInstruments = (u8) numInstruments;
|
||||||
gCtlEntries[bankId].numDrums = (u8) numDrums;
|
gCtlEntries[bankId].numDrums = (u8) numDrums;
|
||||||
gCtlEntries[bankId].instruments = ret->instruments;
|
gCtlEntries[bankId].instruments = ret->instruments;
|
||||||
gCtlEntries[bankId].drums = ret->drums;
|
gCtlEntries[bankId].drums = ret->drums;
|
||||||
|
DEBUG_PRINT("- setting load status");
|
||||||
gBankLoadStatus[bankId] = SOUND_LOAD_STATUS_COMPLETE;
|
gBankLoadStatus[bankId] = SOUND_LOAD_STATUS_COMPLETE;
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
@@ -763,26 +784,32 @@ u8 get_missing_bank(u32 seqId, s32 *nonNullCount, s32 *nullCount) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
struct AudioBank *load_banks_immediate(s32 seqId, u8 *outDefaultBank) {
|
struct AudioBank *load_banks_immediate(s32 seqId, u8 *outDefaultBank) {
|
||||||
|
DEBUG_PRINT("load_banks_immediate()");
|
||||||
void *ret;
|
void *ret;
|
||||||
u32 bankId;
|
u32 bankId;
|
||||||
u16 offset;
|
u16 offset;
|
||||||
u8 i;
|
u8 i;
|
||||||
|
|
||||||
|
DEBUG_PRINT("- getting offset");
|
||||||
offset = ((u16 *) gAlBankSets)[seqId];
|
offset = ((u16 *) gAlBankSets)[seqId];
|
||||||
#ifdef VERSION_EU
|
#ifdef VERSION_EU
|
||||||
for (i = gAlBankSets[offset++]; i != 0; i--) {
|
for (i = gAlBankSets[offset++]; i != 0; i--) {
|
||||||
bankId = gAlBankSets[offset++];
|
bankId = gAlBankSets[offset++];
|
||||||
#else
|
#else
|
||||||
offset++;
|
offset++;
|
||||||
|
DEBUG_PRINT("- looping through bank sets");
|
||||||
for (i = gAlBankSets[offset - 1]; i != 0; i--) {
|
for (i = gAlBankSets[offset - 1]; i != 0; i--) {
|
||||||
offset++;
|
offset++;
|
||||||
|
DEBUG_PRINT("- getting bank id");
|
||||||
bankId = gAlBankSets[offset - 1];
|
bankId = gAlBankSets[offset - 1];
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
DEBUG_PRINT("- checking if bank load is complete");
|
||||||
if (IS_BANK_LOAD_COMPLETE(bankId) == TRUE) {
|
if (IS_BANK_LOAD_COMPLETE(bankId) == TRUE) {
|
||||||
#ifdef VERSION_EU
|
#ifdef VERSION_EU
|
||||||
ret = get_bank_or_seq(&gBankLoadedPool, 2, bankId);
|
ret = get_bank_or_seq(&gBankLoadedPool, 2, bankId);
|
||||||
#else
|
#else
|
||||||
|
DEBUG_PRINT("- getting bank or seq");
|
||||||
ret = get_bank_or_seq(&gBankLoadedPool, 2, gAlBankSets[offset - 1]);
|
ret = get_bank_or_seq(&gBankLoadedPool, 2, gAlBankSets[offset - 1]);
|
||||||
#endif
|
#endif
|
||||||
} else {
|
} else {
|
||||||
@@ -790,6 +817,7 @@ struct AudioBank *load_banks_immediate(s32 seqId, u8 *outDefaultBank) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (ret == NULL) {
|
if (ret == NULL) {
|
||||||
|
DEBUG_PRINT("- bank load immediate");
|
||||||
ret = bank_load_immediate(bankId, 2);
|
ret = bank_load_immediate(bankId, 2);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -798,6 +826,7 @@ struct AudioBank *load_banks_immediate(s32 seqId, u8 *outDefaultBank) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void preload_sequence(u32 seqId, u8 preloadMask) {
|
void preload_sequence(u32 seqId, u8 preloadMask) {
|
||||||
|
DEBUG_PRINT("preload_sequence()");
|
||||||
void *sequenceData;
|
void *sequenceData;
|
||||||
u8 temp;
|
u8 temp;
|
||||||
|
|
||||||
@@ -807,17 +836,21 @@ void preload_sequence(u32 seqId, u8 preloadMask) {
|
|||||||
|
|
||||||
gAudioLoadLock = AUDIO_LOCK_LOADING;
|
gAudioLoadLock = AUDIO_LOCK_LOADING;
|
||||||
if (preloadMask & PRELOAD_BANKS) {
|
if (preloadMask & PRELOAD_BANKS) {
|
||||||
|
DEBUG_PRINT("- load banks immediate");
|
||||||
load_banks_immediate(seqId, &temp);
|
load_banks_immediate(seqId, &temp);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (preloadMask & PRELOAD_SEQUENCE) {
|
if (preloadMask & PRELOAD_SEQUENCE) {
|
||||||
// @bug should be IS_SEQ_LOAD_COMPLETE
|
// @bug should be IS_SEQ_LOAD_COMPLETE
|
||||||
|
DEBUG_PRINT("- checking if bank load immediate");
|
||||||
if (IS_BANK_LOAD_COMPLETE(seqId) == TRUE) {
|
if (IS_BANK_LOAD_COMPLETE(seqId) == TRUE) {
|
||||||
eu_stubbed_printf_1("SEQ %d ALREADY CACHED\n", seqId);
|
eu_stubbed_printf_1("SEQ %d ALREADY CACHED\n", seqId);
|
||||||
|
DEBUG_PRINT("- getting bank or seq");
|
||||||
sequenceData = get_bank_or_seq(&gSeqLoadedPool, 2, seqId);
|
sequenceData = get_bank_or_seq(&gSeqLoadedPool, 2, seqId);
|
||||||
} else {
|
} else {
|
||||||
sequenceData = NULL;
|
sequenceData = NULL;
|
||||||
}
|
}
|
||||||
|
DEBUG_PRINT("- checking dma immediate");
|
||||||
if (sequenceData == NULL && sequence_dma_immediate(seqId, 2) == NULL) {
|
if (sequenceData == NULL && sequence_dma_immediate(seqId, 2) == NULL) {
|
||||||
gAudioLoadLock = AUDIO_LOCK_NOT_LOADING;
|
gAudioLoadLock = AUDIO_LOCK_NOT_LOADING;
|
||||||
return;
|
return;
|
||||||
@@ -905,22 +938,12 @@ void load_sequence_internal(u32 player, u32 seqId, s32 loadAsync) {
|
|||||||
|
|
||||||
// (void) must be omitted from parameters to fix stack with -framepointer
|
// (void) must be omitted from parameters to fix stack with -framepointer
|
||||||
void audio_init() {
|
void audio_init() {
|
||||||
#if defined(VERSION_EU)
|
DEBUG_PRINT("audio_init()");
|
||||||
UNUSED s8 pad[16];
|
|
||||||
#else
|
|
||||||
UNUSED s8 pad[32];
|
UNUSED s8 pad[32];
|
||||||
#endif
|
|
||||||
#if defined(VERSION_JP) || defined(VERSION_US)
|
|
||||||
u8 buf[0x10];
|
u8 buf[0x10];
|
||||||
#endif
|
|
||||||
s32 i, j, UNUSED k;
|
s32 i, j, UNUSED k;
|
||||||
UNUSED s32 lim1; // lim1 unused in EU
|
UNUSED s32 lim1; // lim1 unused in EU
|
||||||
#if defined(VERSION_EU)
|
|
||||||
UNUSED u8 buf[0x10];
|
|
||||||
s32 UNUSED lim2, lim3;
|
|
||||||
#else
|
|
||||||
s32 lim2, UNUSED lim3;
|
s32 lim2, UNUSED lim3;
|
||||||
#endif
|
|
||||||
UNUSED u32 size;
|
UNUSED u32 size;
|
||||||
UNUSED u64 *ptr64;
|
UNUSED u64 *ptr64;
|
||||||
void *data;
|
void *data;
|
||||||
@@ -928,57 +951,19 @@ void audio_init() {
|
|||||||
|
|
||||||
gAudioLoadLock = AUDIO_LOCK_UNINITIALIZED;
|
gAudioLoadLock = AUDIO_LOCK_UNINITIALIZED;
|
||||||
|
|
||||||
#if defined(VERSION_JP) || defined(VERSION_US)
|
DEBUG_PRINT("- setting values in unused");
|
||||||
lim1 = gUnusedCount80333EE8;
|
lim1 = gUnusedCount80333EE8;
|
||||||
for (i = 0; i < lim1; i++) {
|
for (i = 0; i < lim1; i++) {
|
||||||
gUnused80226E58[i] = 0;
|
gUnused80226E58[i] = 0;
|
||||||
gUnused80226E98[i] = 0;
|
gUnused80226E98[i] = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
DEBUG_PRINT("- clearing audio heap");
|
||||||
lim2 = gAudioHeapSize;
|
lim2 = gAudioHeapSize;
|
||||||
for (i = 0; i <= lim2 / 8 - 1; i++) {
|
for (i = 0; i <= lim2 / 8 - 1; i++) {
|
||||||
((u64 *) gAudioHeap)[i] = 0;
|
((u64 *) gAudioHeap)[i] = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef TARGET_N64
|
|
||||||
// It seems boot.s doesn't clear the .bss area for audio, so do it here.
|
|
||||||
i = 0;
|
|
||||||
lim3 = ((uintptr_t) &gAudioGlobalsEndMarker - (uintptr_t) &gAudioGlobalsStartMarker) / 8;
|
|
||||||
ptr64 = &gAudioGlobalsStartMarker - 1;
|
|
||||||
for (k = lim3; k >= 0; k--) {
|
|
||||||
i++;
|
|
||||||
ptr64[i] = 0;
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#else
|
|
||||||
for (i = 0; i < gAudioHeapSize / 8; i++) {
|
|
||||||
((u64 *) gAudioHeap)[i] = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
#ifdef TARGET_N64
|
|
||||||
// It seems boot.s doesn't clear the .bss area for audio, so do it here.
|
|
||||||
lim3 = ((uintptr_t) &gAudioGlobalsEndMarker - (uintptr_t) &gAudioGlobalsStartMarker) / 8;
|
|
||||||
ptr64 = &gAudioGlobalsStartMarker;
|
|
||||||
for (k = lim3; k >= 0; k--) {
|
|
||||||
*ptr64++ = 0;
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
D_EU_802298D0 = 20.03042f;
|
|
||||||
gRefreshRate = 50;
|
|
||||||
port_eu_init();
|
|
||||||
if (k) {
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifdef TARGET_N64
|
|
||||||
eu_stubbed_printf_3("Clear Workarea %x -%x size %x \n",
|
|
||||||
(uintptr_t) &gAudioGlobalsStartMarker,
|
|
||||||
(uintptr_t) &gAudioGlobalsEndMarker,
|
|
||||||
(uintptr_t) &gAudioGlobalsEndMarker - (uintptr_t) &gAudioGlobalsStartMarker
|
|
||||||
);
|
|
||||||
#endif
|
|
||||||
|
|
||||||
eu_stubbed_printf_1("AudioHeap is %x\n", gAudioHeapSize);
|
eu_stubbed_printf_1("AudioHeap is %x\n", gAudioHeapSize);
|
||||||
|
|
||||||
@@ -1009,13 +994,7 @@ void audio_init() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#if defined(VERSION_EU)
|
|
||||||
gAudioResetPresetIdToLoad = 0;
|
|
||||||
gAudioResetStatus = 1;
|
|
||||||
audio_shut_down_and_reset_step();
|
|
||||||
#else
|
|
||||||
audio_reset_session(&gAudioSessionPresets[0]);
|
audio_reset_session(&gAudioSessionPresets[0]);
|
||||||
#endif
|
|
||||||
|
|
||||||
// Not sure about these prints
|
// Not sure about these prints
|
||||||
eu_stubbed_printf_1("Heap reset.Synth Change %x \n", 0);
|
eu_stubbed_printf_1("Heap reset.Synth Change %x \n", 0);
|
||||||
@@ -1027,33 +1006,45 @@ void audio_init() {
|
|||||||
data = gMusicData;
|
data = gMusicData;
|
||||||
audio_dma_copy_immediate((uintptr_t) data, gSeqFileHeader, 0x10);
|
audio_dma_copy_immediate((uintptr_t) data, gSeqFileHeader, 0x10);
|
||||||
gSequenceCount = gSeqFileHeader->seqCount;
|
gSequenceCount = gSeqFileHeader->seqCount;
|
||||||
#if defined(VERSION_EU)
|
|
||||||
size = gSequenceCount * sizeof(ALSeqData) + 4;
|
|
||||||
size = ALIGN16(size);
|
|
||||||
#else
|
|
||||||
size = ALIGN16(gSequenceCount * sizeof(ALSeqData) + 4);
|
size = ALIGN16(gSequenceCount * sizeof(ALSeqData) + 4);
|
||||||
#endif
|
|
||||||
gSeqFileHeader = soundAlloc(&gAudioInitPool, size);
|
gSeqFileHeader = soundAlloc(&gAudioInitPool, size);
|
||||||
audio_dma_copy_immediate((uintptr_t) data, gSeqFileHeader, size);
|
audio_dma_copy_immediate((uintptr_t) data, gSeqFileHeader, size);
|
||||||
alSeqFileNew(gSeqFileHeader, data);
|
alSeqFileNew(gSeqFileHeader, data);
|
||||||
|
|
||||||
// Load header for CTL (instrument metadata)
|
// Load header for CTL (instrument metadata)
|
||||||
|
DEBUG_PRINT("- loading ctl header");
|
||||||
gAlCtlHeader = (ALSeqFile *) buf;
|
gAlCtlHeader = (ALSeqFile *) buf;
|
||||||
data = gSoundDataADSR;
|
data = gSoundDataADSR;
|
||||||
|
DEBUG_PRINT("- copying dma immediate");
|
||||||
audio_dma_copy_immediate((uintptr_t) data, gAlCtlHeader, 0x10);
|
audio_dma_copy_immediate((uintptr_t) data, gAlCtlHeader, 0x10);
|
||||||
size = gAlCtlHeader->seqCount * sizeof(ALSeqData) + 4;
|
size = gAlCtlHeader->seqCount * sizeof(ALSeqData) + 4;
|
||||||
|
DEBUG_PRINT("- seq count: %d", gAlCtlHeader->seqCount);
|
||||||
|
DEBUG_PRINT("- size after read: %d", size);
|
||||||
size = ALIGN16(size);
|
size = ALIGN16(size);
|
||||||
|
DEBUG_PRINT("- size after align: %d", size);
|
||||||
gCtlEntries = soundAlloc(&gAudioInitPool, gAlCtlHeader->seqCount * sizeof(struct CtlEntry));
|
gCtlEntries = soundAlloc(&gAudioInitPool, gAlCtlHeader->seqCount * sizeof(struct CtlEntry));
|
||||||
gAlCtlHeader = soundAlloc(&gAudioInitPool, size);
|
gAlCtlHeader = soundAlloc(&gAudioInitPool, size);
|
||||||
|
DEBUG_PRINT("@ copying data from sound data adsr to ctl header");
|
||||||
|
DEBUG_PRINT("- data: %x", data);
|
||||||
|
DEBUG_PRINT("- ctl header: %x", gAlCtlHeader);
|
||||||
|
DEBUG_PRINT("- size: %d", size);
|
||||||
audio_dma_copy_immediate((uintptr_t) data, gAlCtlHeader, size);
|
audio_dma_copy_immediate((uintptr_t) data, gAlCtlHeader, size);
|
||||||
|
DEBUG_PRINT("- creating new seq file for ctl");
|
||||||
alSeqFileNew(gAlCtlHeader, data);
|
alSeqFileNew(gAlCtlHeader, data);
|
||||||
|
|
||||||
// Load header for TBL (raw sound data)
|
// Load header for TBL (raw sound data)
|
||||||
|
DEBUG_PRINT("- loading tbl");
|
||||||
gAlTbl = (ALSeqFile *) buf;
|
gAlTbl = (ALSeqFile *) buf;
|
||||||
|
DEBUG_PRINT("- copying dma");
|
||||||
audio_dma_copy_immediate((uintptr_t) data, gAlTbl, 0x10);
|
audio_dma_copy_immediate((uintptr_t) data, gAlTbl, 0x10);
|
||||||
|
DEBUG_PRINT("- tbl seq count: %d", gAlTbl->seqCount);
|
||||||
size = gAlTbl->seqCount * sizeof(ALSeqData) + 4;
|
size = gAlTbl->seqCount * sizeof(ALSeqData) + 4;
|
||||||
|
DEBUG_PRINT("- size: %d", size);
|
||||||
size = ALIGN16(size);
|
size = ALIGN16(size);
|
||||||
|
DEBUG_PRINT("- size after align: %d", size);
|
||||||
gAlTbl = soundAlloc(&gAudioInitPool, size);
|
gAlTbl = soundAlloc(&gAudioInitPool, size);
|
||||||
|
DEBUG_PRINT("- tbl alloc at %x", gAlTbl);
|
||||||
|
DEBUG_PRINT("- gSoundDataRaw at %x", gSoundDataRaw);
|
||||||
audio_dma_copy_immediate((uintptr_t) gSoundDataRaw, gAlTbl, size);
|
audio_dma_copy_immediate((uintptr_t) gSoundDataRaw, gAlTbl, size);
|
||||||
alSeqFileNew(gAlTbl, gSoundDataRaw);
|
alSeqFileNew(gAlTbl, gSoundDataRaw);
|
||||||
|
|
||||||
|
|||||||
@@ -6,6 +6,7 @@
|
|||||||
#include "heap.h"
|
#include "heap.h"
|
||||||
#include "load.h"
|
#include "load.h"
|
||||||
#include "seqplayer.h"
|
#include "seqplayer.h"
|
||||||
|
#include "../../debug_print.h"
|
||||||
|
|
||||||
#define PORTAMENTO_IS_SPECIAL(x) ((x).mode & 0x80)
|
#define PORTAMENTO_IS_SPECIAL(x) ((x).mode & 0x80)
|
||||||
#define PORTAMENTO_MODE(x) ((x).mode & ~0x80)
|
#define PORTAMENTO_MODE(x) ((x).mode & ~0x80)
|
||||||
@@ -398,12 +399,11 @@ void init_layer_freelist(void) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
u8 m64_read_u8(struct M64ScriptState *state) {
|
u8 m64_read_u8(struct M64ScriptState *state) {
|
||||||
#if defined(VERSION_EU) || defined(VERSION_SH)
|
DEBUG_PRINT("m64_read_u8()");
|
||||||
return *(state->pc++);
|
DEBUG_PRINT("- state at %x", state);
|
||||||
#else
|
|
||||||
u8 *midiArg = state->pc++;
|
u8 *midiArg = state->pc++;
|
||||||
|
DEBUG_PRINT("- read u8 (%d) at (%x)", *midiArg, midiArg);
|
||||||
return *midiArg;
|
return *midiArg;
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
|
|
||||||
s16 m64_read_s16(struct M64ScriptState *state) {
|
s16 m64_read_s16(struct M64ScriptState *state) {
|
||||||
@@ -1109,7 +1109,11 @@ s32 seq_channel_layer_process_script_part2(struct SequenceChannelLayer *layer) {
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case 0xc6: // layer_setinstr
|
case 0xc6: // layer_setinstr
|
||||||
|
DEBUG_PRINT(" - cmd 0xc6, setinstr");
|
||||||
|
|
||||||
cmd = m64_read_u8(state);
|
cmd = m64_read_u8(state);
|
||||||
|
DEBUG_PRINT(" - read %d from state", cmd);
|
||||||
|
|
||||||
if (cmd >= 0x7f) {
|
if (cmd >= 0x7f) {
|
||||||
if (cmd == 0x7f) {
|
if (cmd == 0x7f) {
|
||||||
layer->instOrWave = 0;
|
layer->instOrWave = 0;
|
||||||
@@ -1401,6 +1405,9 @@ s32 seq_channel_layer_process_script_part3(struct SequenceChannelLayer *layer, s
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
u8 get_instrument(struct SequenceChannel *seqChannel, u8 instId, struct Instrument **instOut, struct AdsrSettings *adsr) {
|
u8 get_instrument(struct SequenceChannel *seqChannel, u8 instId, struct Instrument **instOut, struct AdsrSettings *adsr) {
|
||||||
|
DEBUG_PRINT("@ get_instrument()");
|
||||||
|
DEBUG_PRINT("- instrument id: %d", instId);
|
||||||
|
|
||||||
struct Instrument *inst;
|
struct Instrument *inst;
|
||||||
#if defined(VERSION_EU) || defined(VERSION_SH)
|
#if defined(VERSION_EU) || defined(VERSION_SH)
|
||||||
inst = get_instrument_inner(seqChannel->bankId, instId);
|
inst = get_instrument_inner(seqChannel->bankId, instId);
|
||||||
@@ -1458,6 +1465,10 @@ u8 get_instrument(struct SequenceChannel *seqChannel, u8 instId, struct Instrume
|
|||||||
}
|
}
|
||||||
|
|
||||||
void set_instrument(struct SequenceChannel *seqChannel, u8 instId) {
|
void set_instrument(struct SequenceChannel *seqChannel, u8 instId) {
|
||||||
|
DEBUG_PRINT("@ set_instrument()");
|
||||||
|
DEBUG_PRINT("- bank id: %d", seqChannel->bankId);
|
||||||
|
DEBUG_PRINT("- instrument id: %d", instId);
|
||||||
|
|
||||||
if (instId >= 0x80) {
|
if (instId >= 0x80) {
|
||||||
seqChannel->instOrWave = instId;
|
seqChannel->instOrWave = instId;
|
||||||
seqChannel->instrument = NULL;
|
seqChannel->instrument = NULL;
|
||||||
@@ -1486,6 +1497,8 @@ void sequence_channel_set_volume(struct SequenceChannel *seqChannel, u8 volume)
|
|||||||
}
|
}
|
||||||
|
|
||||||
void sequence_channel_process_script(struct SequenceChannel *seqChannel) {
|
void sequence_channel_process_script(struct SequenceChannel *seqChannel) {
|
||||||
|
DEBUG_PRINT("sequence_channel_process_script()");
|
||||||
|
|
||||||
struct M64ScriptState *state;
|
struct M64ScriptState *state;
|
||||||
struct SequencePlayer *seqPlayer;
|
struct SequencePlayer *seqPlayer;
|
||||||
u8 cmd;
|
u8 cmd;
|
||||||
@@ -1523,6 +1536,8 @@ void sequence_channel_process_script(struct SequenceChannel *seqChannel) {
|
|||||||
if (seqChannel->delay == 0) {
|
if (seqChannel->delay == 0) {
|
||||||
for (;;) {
|
for (;;) {
|
||||||
cmd = m64_read_u8(state);
|
cmd = m64_read_u8(state);
|
||||||
|
DEBUG_PRINT("- handling command: %x", cmd);
|
||||||
|
|
||||||
#if !defined(VERSION_EU) && !defined(VERSION_SH)
|
#if !defined(VERSION_EU) && !defined(VERSION_SH)
|
||||||
if (cmd == 0xff) // chan_end
|
if (cmd == 0xff) // chan_end
|
||||||
{
|
{
|
||||||
@@ -1703,7 +1718,12 @@ void sequence_channel_process_script(struct SequenceChannel *seqChannel) {
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
case 0xc1: // chan_setinstr ("set program"?)
|
case 0xc1: // chan_setinstr ("set program"?)
|
||||||
set_instrument(seqChannel, m64_read_u8(state));
|
DEBUG_PRINT(" - cmd 0xc1, setinstr");
|
||||||
|
|
||||||
|
u8 instrId = m64_read_u8(state);
|
||||||
|
DEBUG_PRINT(" - read %d from state", instrId);
|
||||||
|
|
||||||
|
set_instrument(seqChannel, instrId);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0xc3: // chan_largenotesoff
|
case 0xc3: // chan_largenotesoff
|
||||||
@@ -1832,25 +1852,21 @@ void sequence_channel_process_script(struct SequenceChannel *seqChannel) {
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case 0xc6: // chan_setbank; switch bank within set
|
case 0xc6: // chan_setbank; switch bank within set
|
||||||
|
DEBUG_PRINT(" - case 0xc6 - switch bank");
|
||||||
|
|
||||||
|
DEBUG_PRINT(" - seq id %d", seqPlayer->seqId);
|
||||||
|
|
||||||
cmd = m64_read_u8(state);
|
cmd = m64_read_u8(state);
|
||||||
|
DEBUG_PRINT(" - backwards bank id %d", cmd);
|
||||||
|
|
||||||
// Switch to the temp's (0-indexed) bank in this sequence's
|
// Switch to the temp's (0-indexed) bank in this sequence's
|
||||||
// bank set. Note that in the binary format (not in the JSON!)
|
// bank set. Note that in the binary format (not in the JSON!)
|
||||||
// the banks are listed backwards, so we counts from the back.
|
// the banks are listed backwards, so we counts from the back.
|
||||||
// (gAlBankSets[offset] is number of banks)
|
// (gAlBankSets[offset] is number of banks)
|
||||||
#if defined(VERSION_EU) || defined(VERSION_SH)
|
|
||||||
sp38 = ((u16 *) gAlBankSets)[seqPlayer->seqId];
|
|
||||||
loBits = *(sp38 + gAlBankSets);
|
|
||||||
cmd = gAlBankSets[(s32)sp38 + loBits - cmd];
|
|
||||||
#else
|
|
||||||
sp5A = ((u16 *) gAlBankSets)[seqPlayer->seqId];
|
sp5A = ((u16 *) gAlBankSets)[seqPlayer->seqId];
|
||||||
loBits = *(sp5A + gAlBankSets);
|
loBits = *(sp5A + gAlBankSets);
|
||||||
cmd = gAlBankSets[sp5A + loBits - cmd];
|
cmd = gAlBankSets[sp5A + loBits - cmd];
|
||||||
#endif
|
|
||||||
#ifdef VERSION_SH
|
|
||||||
if (get_bank_or_seq(1, 2, cmd) != NULL)
|
|
||||||
#else
|
|
||||||
if (get_bank_or_seq(&gBankLoadedPool, 2, cmd) != NULL)
|
if (get_bank_or_seq(&gBankLoadedPool, 2, cmd) != NULL)
|
||||||
#endif
|
|
||||||
{
|
{
|
||||||
seqChannel->bankId = cmd;
|
seqChannel->bankId = cmd;
|
||||||
} else {
|
} else {
|
||||||
@@ -2138,6 +2154,8 @@ void sequence_channel_process_script(struct SequenceChannel *seqChannel) {
|
|||||||
#else
|
#else
|
||||||
case 0x80: // chan_ioreadval; read data from audio lib
|
case 0x80: // chan_ioreadval; read data from audio lib
|
||||||
#endif
|
#endif
|
||||||
|
DEBUG_PRINT("- cmd 0x80, read data from audio lib");
|
||||||
|
DEBUG_PRINT(" - reading index: %d", loBits);
|
||||||
value = seqChannel->soundScriptIO[loBits];
|
value = seqChannel->soundScriptIO[loBits];
|
||||||
if (loBits < 4) {
|
if (loBits < 4) {
|
||||||
seqChannel->soundScriptIO[loBits] = -1;
|
seqChannel->soundScriptIO[loBits] = -1;
|
||||||
@@ -2229,6 +2247,8 @@ void sequence_channel_process_script(struct SequenceChannel *seqChannel) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void sequence_player_process_sequence(struct SequencePlayer *seqPlayer) {
|
void sequence_player_process_sequence(struct SequencePlayer *seqPlayer) {
|
||||||
|
DEBUG_PRINT("sequence_player_process_sequence()");
|
||||||
|
|
||||||
u8 cmd;
|
u8 cmd;
|
||||||
#ifdef VERSION_SH
|
#ifdef VERSION_SH
|
||||||
UNUSED u32 pad;
|
UNUSED u32 pad;
|
||||||
|
|||||||
+71
-208
@@ -1,6 +1,7 @@
|
|||||||
#ifndef VERSION_SH
|
#ifndef VERSION_SH
|
||||||
#include <ultra64.h>
|
#include <ultra64.h>
|
||||||
|
|
||||||
|
#include "../../debug_print.h"
|
||||||
#include "synthesis.h"
|
#include "synthesis.h"
|
||||||
#include "heap.h"
|
#include "heap.h"
|
||||||
#include "data.h"
|
#include "data.h"
|
||||||
@@ -27,9 +28,13 @@
|
|||||||
#define DMEM_ADDR_WET_RIGHT_CH 0x880
|
#define DMEM_ADDR_WET_RIGHT_CH 0x880
|
||||||
|
|
||||||
#define aSetLoadBufferPair(pkt, c, off) \
|
#define aSetLoadBufferPair(pkt, c, off) \
|
||||||
|
DEBUG_PRINT("- (in set load buffer pair, set buffer 1) "); \
|
||||||
aSetBuffer(pkt, 0, c + DMEM_ADDR_WET_LEFT_CH, 0, DEFAULT_LEN_1CH - c); \
|
aSetBuffer(pkt, 0, c + DMEM_ADDR_WET_LEFT_CH, 0, DEFAULT_LEN_1CH - c); \
|
||||||
|
DEBUG_PRINT("- (in set load buffer pair, load buffer 1) "); \
|
||||||
aLoadBuffer(pkt, VIRTUAL_TO_PHYSICAL2(gSynthesisReverb.ringBuffer.left + (off))); \
|
aLoadBuffer(pkt, VIRTUAL_TO_PHYSICAL2(gSynthesisReverb.ringBuffer.left + (off))); \
|
||||||
|
DEBUG_PRINT("- (in set load buffer pair, set buffer 2) "); \
|
||||||
aSetBuffer(pkt, 0, c + DMEM_ADDR_WET_RIGHT_CH, 0, DEFAULT_LEN_1CH - c); \
|
aSetBuffer(pkt, 0, c + DMEM_ADDR_WET_RIGHT_CH, 0, DEFAULT_LEN_1CH - c); \
|
||||||
|
DEBUG_PRINT("- (in set load buffer pair, load buffer 2) "); \
|
||||||
aLoadBuffer(pkt, VIRTUAL_TO_PHYSICAL2(gSynthesisReverb.ringBuffer.right + (off)))
|
aLoadBuffer(pkt, VIRTUAL_TO_PHYSICAL2(gSynthesisReverb.ringBuffer.right + (off)))
|
||||||
|
|
||||||
#define aSetSaveBufferPair(pkt, c, d, off) \
|
#define aSetSaveBufferPair(pkt, c, d, off) \
|
||||||
@@ -324,6 +329,7 @@ u64 *synthesis_execute(u64 *cmdBuf, s32 *writtenCmds, s16 *aiBuf, s32 bufLen) {
|
|||||||
#else
|
#else
|
||||||
// bufLen will be divisible by 16
|
// bufLen will be divisible by 16
|
||||||
u64 *synthesis_execute(u64 *cmdBuf, s32 *writtenCmds, s16 *aiBuf, s32 bufLen) {
|
u64 *synthesis_execute(u64 *cmdBuf, s32 *writtenCmds, s16 *aiBuf, s32 bufLen) {
|
||||||
|
DEBUG_PRINT("synthesis_execute()");
|
||||||
s32 chunkLen;
|
s32 chunkLen;
|
||||||
s32 i;
|
s32 i;
|
||||||
u32 *aiBufPtr = (u32 *) aiBuf;
|
u32 *aiBufPtr = (u32 *) aiBuf;
|
||||||
@@ -506,6 +512,8 @@ u64 *synthesis_do_one_audio_update(s16 *aiBuf, s32 bufLen, u64 *cmd, s32 updateI
|
|||||||
}
|
}
|
||||||
#else
|
#else
|
||||||
u64 *synthesis_do_one_audio_update(s16 *aiBuf, s32 bufLen, u64 *cmd, s32 updateIndex) {
|
u64 *synthesis_do_one_audio_update(s16 *aiBuf, s32 bufLen, u64 *cmd, s32 updateIndex) {
|
||||||
|
DEBUG_PRINT("synthesis_do_one_audio_update()");
|
||||||
|
|
||||||
UNUSED s32 pad1[1];
|
UNUSED s32 pad1[1];
|
||||||
s16 ra;
|
s16 ra;
|
||||||
s16 t4;
|
s16 t4;
|
||||||
@@ -514,35 +522,52 @@ u64 *synthesis_do_one_audio_update(s16 *aiBuf, s32 bufLen, u64 *cmd, s32 updateI
|
|||||||
UNUSED s32 pad2[1];
|
UNUSED s32 pad2[1];
|
||||||
s16 temp;
|
s16 temp;
|
||||||
|
|
||||||
|
DEBUG_PRINT("- curFrame: %d", gSynthesisReverb.curFrame);
|
||||||
|
DEBUG_PRINT("- updateIndex: %d", updateIndex);
|
||||||
|
|
||||||
v1 = &gSynthesisReverb.items[gSynthesisReverb.curFrame][updateIndex];
|
v1 = &gSynthesisReverb.items[gSynthesisReverb.curFrame][updateIndex];
|
||||||
|
DEBUG_PRINT("- v1: %x", v1);
|
||||||
|
|
||||||
if (gSynthesisReverb.useReverb == 0) {
|
if (gSynthesisReverb.useReverb == 0) {
|
||||||
|
DEBUG_PRINT("- w/o reverb");
|
||||||
aClearBuffer(cmd++, DMEM_ADDR_LEFT_CH, DEFAULT_LEN_2CH);
|
aClearBuffer(cmd++, DMEM_ADDR_LEFT_CH, DEFAULT_LEN_2CH);
|
||||||
cmd = synthesis_process_notes(aiBuf, bufLen, cmd);
|
cmd = synthesis_process_notes(aiBuf, bufLen, cmd);
|
||||||
} else {
|
} else {
|
||||||
|
DEBUG_PRINT("- w/ reverb");
|
||||||
if (gReverbDownsampleRate == 1) {
|
if (gReverbDownsampleRate == 1) {
|
||||||
|
DEBUG_PRINT("- w/ reverb downsample");
|
||||||
|
|
||||||
// Put the oldest samples in the ring buffer into the wet channels
|
// Put the oldest samples in the ring buffer into the wet channels
|
||||||
|
DEBUG_PRINT("- set load buffer pair 1");
|
||||||
|
DEBUG_PRINT("- startPos: %d", v1->startPos);
|
||||||
aSetLoadBufferPair(cmd++, 0, v1->startPos);
|
aSetLoadBufferPair(cmd++, 0, v1->startPos);
|
||||||
if (v1->lengthB != 0) {
|
if (v1->lengthB != 0) {
|
||||||
// Ring buffer wrapped
|
// Ring buffer wrapped
|
||||||
|
DEBUG_PRINT("- set load buffer pair 2");
|
||||||
aSetLoadBufferPair(cmd++, v1->lengthA, 0);
|
aSetLoadBufferPair(cmd++, v1->lengthA, 0);
|
||||||
temp = 0;
|
temp = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Use the reverb sound as initial sound for this audio update
|
// Use the reverb sound as initial sound for this audio update
|
||||||
|
DEBUG_PRINT("- dmem move");
|
||||||
aDMEMMove(cmd++, DMEM_ADDR_WET_LEFT_CH, DMEM_ADDR_LEFT_CH, DEFAULT_LEN_2CH);
|
aDMEMMove(cmd++, DMEM_ADDR_WET_LEFT_CH, DMEM_ADDR_LEFT_CH, DEFAULT_LEN_2CH);
|
||||||
|
|
||||||
// (Hopefully) lower the volume of the wet channels. New reverb will later be mixed into
|
// (Hopefully) lower the volume of the wet channels. New reverb will later be mixed into
|
||||||
// these channels.
|
// these channels.
|
||||||
|
DEBUG_PRINT("- set buffer");
|
||||||
aSetBuffer(cmd++, 0, 0, 0, DEFAULT_LEN_2CH);
|
aSetBuffer(cmd++, 0, 0, 0, DEFAULT_LEN_2CH);
|
||||||
// 0x8000 here is -100%
|
// 0x8000 here is -100%
|
||||||
|
DEBUG_PRINT("- mix");
|
||||||
aMix(cmd++, 0, /*gain*/ 0x8000 + gSynthesisReverb.reverbGain, /*in*/ DMEM_ADDR_WET_LEFT_CH,
|
aMix(cmd++, 0, /*gain*/ 0x8000 + gSynthesisReverb.reverbGain, /*in*/ DMEM_ADDR_WET_LEFT_CH,
|
||||||
/*out*/ DMEM_ADDR_WET_LEFT_CH);
|
/*out*/ DMEM_ADDR_WET_LEFT_CH);
|
||||||
} else {
|
} else {
|
||||||
|
DEBUG_PRINT("- w/o reverb downsample");
|
||||||
|
|
||||||
// Same as above but upsample the previously downsampled samples used for reverb first
|
// Same as above but upsample the previously downsampled samples used for reverb first
|
||||||
temp = 0; //! jesus christ
|
temp = 0; //! jesus christ
|
||||||
t4 = (v1->startPos & 7) * 2;
|
t4 = (v1->startPos & 7) * 2;
|
||||||
ra = ALIGN(v1->lengthA + t4, 4);
|
ra = ALIGN(v1->lengthA + t4, 4);
|
||||||
|
DEBUG_PRINT("- set load buffer pair");
|
||||||
aSetLoadBufferPair(cmd++, 0, v1->startPos - t4 / 2);
|
aSetLoadBufferPair(cmd++, 0, v1->startPos - t4 / 2);
|
||||||
if (v1->lengthB != 0) {
|
if (v1->lengthB != 0) {
|
||||||
// Ring buffer wrapped
|
// Ring buffer wrapped
|
||||||
@@ -553,12 +578,19 @@ u64 *synthesis_do_one_audio_update(s16 *aiBuf, s32 bufLen, u64 *cmd, s32 updateI
|
|||||||
//! useless assignment.
|
//! useless assignment.
|
||||||
ra = ra + temp;
|
ra = ra + temp;
|
||||||
}
|
}
|
||||||
|
DEBUG_PRINT("- set buffer 1");
|
||||||
aSetBuffer(cmd++, 0, t4 + DMEM_ADDR_WET_LEFT_CH, DMEM_ADDR_LEFT_CH, bufLen << 1);
|
aSetBuffer(cmd++, 0, t4 + DMEM_ADDR_WET_LEFT_CH, DMEM_ADDR_LEFT_CH, bufLen << 1);
|
||||||
|
DEBUG_PRINT("- resample 1");
|
||||||
aResample(cmd++, gSynthesisReverb.resampleFlags, (u16) gSynthesisReverb.resampleRate, VIRTUAL_TO_PHYSICAL2(gSynthesisReverb.resampleStateLeft));
|
aResample(cmd++, gSynthesisReverb.resampleFlags, (u16) gSynthesisReverb.resampleRate, VIRTUAL_TO_PHYSICAL2(gSynthesisReverb.resampleStateLeft));
|
||||||
|
DEBUG_PRINT("- set buffer 2");
|
||||||
aSetBuffer(cmd++, 0, t4 + DMEM_ADDR_WET_RIGHT_CH, DMEM_ADDR_RIGHT_CH, bufLen << 1);
|
aSetBuffer(cmd++, 0, t4 + DMEM_ADDR_WET_RIGHT_CH, DMEM_ADDR_RIGHT_CH, bufLen << 1);
|
||||||
|
DEBUG_PRINT("- resample 2");
|
||||||
aResample(cmd++, gSynthesisReverb.resampleFlags, (u16) gSynthesisReverb.resampleRate, VIRTUAL_TO_PHYSICAL2(gSynthesisReverb.resampleStateRight));
|
aResample(cmd++, gSynthesisReverb.resampleFlags, (u16) gSynthesisReverb.resampleRate, VIRTUAL_TO_PHYSICAL2(gSynthesisReverb.resampleStateRight));
|
||||||
|
DEBUG_PRINT("- set buffer 3");
|
||||||
aSetBuffer(cmd++, 0, 0, 0, DEFAULT_LEN_2CH);
|
aSetBuffer(cmd++, 0, 0, 0, DEFAULT_LEN_2CH);
|
||||||
|
DEBUG_PRINT("- mix");
|
||||||
aMix(cmd++, 0, /*gain*/ 0x8000 + gSynthesisReverb.reverbGain, /*in*/ DMEM_ADDR_LEFT_CH, /*out*/ DMEM_ADDR_LEFT_CH);
|
aMix(cmd++, 0, /*gain*/ 0x8000 + gSynthesisReverb.reverbGain, /*in*/ DMEM_ADDR_LEFT_CH, /*out*/ DMEM_ADDR_LEFT_CH);
|
||||||
|
DEBUG_PRINT("- dmem move");
|
||||||
aDMEMMove(cmd++, DMEM_ADDR_LEFT_CH, DMEM_ADDR_WET_LEFT_CH, DEFAULT_LEN_2CH);
|
aDMEMMove(cmd++, DMEM_ADDR_LEFT_CH, DMEM_ADDR_WET_LEFT_CH, DEFAULT_LEN_2CH);
|
||||||
}
|
}
|
||||||
cmd = synthesis_process_notes(aiBuf, bufLen, cmd);
|
cmd = synthesis_process_notes(aiBuf, bufLen, cmd);
|
||||||
@@ -586,6 +618,8 @@ u64 *synthesis_process_note(struct Note *note, struct NoteSubEu *noteSubEu, stru
|
|||||||
UNUSED s32 pad0[3];
|
UNUSED s32 pad0[3];
|
||||||
#else
|
#else
|
||||||
u64 *synthesis_process_notes(s16 *aiBuf, s32 bufLen, u64 *cmd) {
|
u64 *synthesis_process_notes(s16 *aiBuf, s32 bufLen, u64 *cmd) {
|
||||||
|
DEBUG_PRINT("synthesis_process_notes()");
|
||||||
|
|
||||||
s32 noteIndex; // sp174
|
s32 noteIndex; // sp174
|
||||||
struct Note *note; // s7
|
struct Note *note; // s7
|
||||||
UNUSED u8 pad0[0x08];
|
UNUSED u8 pad0[0x08];
|
||||||
@@ -669,49 +703,35 @@ u64 *synthesis_process_notes(s16 *aiBuf, s32 bufLen, u64 *cmd) {
|
|||||||
u16 noteSamplesDmemAddrBeforeResampling; // spD6, spAA
|
u16 noteSamplesDmemAddrBeforeResampling; // spD6, spAA
|
||||||
|
|
||||||
|
|
||||||
#ifndef VERSION_EU
|
|
||||||
for (noteIndex = 0; noteIndex < gMaxSimultaneousNotes; noteIndex++) {
|
for (noteIndex = 0; noteIndex < gMaxSimultaneousNotes; noteIndex++) {
|
||||||
|
DEBUG_PRINT("- for note index %d/%d", noteIndex, gMaxSimultaneousNotes);
|
||||||
|
|
||||||
|
DEBUG_PRINT("- getting note");
|
||||||
note = &gNotes[noteIndex];
|
note = &gNotes[noteIndex];
|
||||||
#ifdef VERSION_US
|
|
||||||
//! This function requires note->enabled to be volatile, but it breaks other functions like note_enable.
|
//! This function requires note->enabled to be volatile, but it breaks other functions like note_enable.
|
||||||
//! Casting to a struct with just the volatile bitfield works, but there may be a better way to match.
|
//! Casting to a struct with just the volatile bitfield works, but there may be a better way to match.
|
||||||
|
DEBUG_PRINT("- if note is enabled but not loaded");
|
||||||
if (((struct vNote *)note)->enabled && IS_BANK_LOAD_COMPLETE(note->bankId) == FALSE) {
|
if (((struct vNote *)note)->enabled && IS_BANK_LOAD_COMPLETE(note->bankId) == FALSE) {
|
||||||
#else
|
DEBUG_PRINT("- note is enabled but not loaded");
|
||||||
if (IS_BANK_LOAD_COMPLETE(note->bankId) == FALSE) {
|
|
||||||
#endif
|
|
||||||
gAudioErrorFlags = (note->bankId << 8) + noteIndex + 0x1000000;
|
gAudioErrorFlags = (note->bankId << 8) + noteIndex + 0x1000000;
|
||||||
} else if (((struct vNote *)note)->enabled) {
|
continue;
|
||||||
#else
|
|
||||||
if (note->noteSubEu.enabled == FALSE) {
|
|
||||||
return cmd;
|
|
||||||
} else {
|
|
||||||
#endif
|
|
||||||
flags = 0;
|
|
||||||
#ifdef VERSION_EU
|
|
||||||
tempBufLen = bufLen;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifdef VERSION_EU
|
|
||||||
if (noteSubEu->needsInit == TRUE) {
|
|
||||||
#else
|
|
||||||
if (note->needsInit == TRUE) {
|
|
||||||
#endif
|
|
||||||
flags = A_INIT;
|
|
||||||
#ifndef VERSION_EU
|
|
||||||
note->samplePosInt = 0;
|
|
||||||
note->samplePosFrac = 0;
|
|
||||||
#else
|
|
||||||
synthesisState->restart = FALSE;
|
|
||||||
synthesisState->samplePosInt = 0;
|
|
||||||
synthesisState->samplePosFrac = 0;
|
|
||||||
synthesisState->curVolLeft = 1;
|
|
||||||
synthesisState->curVolRight = 1;
|
|
||||||
synthesisState->prevHeadsetPanRight = 0;
|
|
||||||
synthesisState->prevHeadsetPanLeft = 0;
|
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifndef VERSION_EU
|
DEBUG_PRINT("- if note is enabled");
|
||||||
|
if (((struct vNote *)note)->enabled) {
|
||||||
|
DEBUG_PRINT("$ note is enabled!");
|
||||||
|
|
||||||
|
flags = 0;
|
||||||
|
|
||||||
|
DEBUG_PRINT("- if note needs to be init");
|
||||||
|
if (note->needsInit == TRUE) {
|
||||||
|
flags = A_INIT;
|
||||||
|
note->samplePosInt = 0;
|
||||||
|
note->samplePosFrac = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
DEBUG_PRINT("- if note frequency is less than 2");
|
||||||
if (note->frequency < US_FLOAT(2.0)) {
|
if (note->frequency < US_FLOAT(2.0)) {
|
||||||
nParts = 1;
|
nParts = 1;
|
||||||
if (note->frequency > US_FLOAT(1.99996)) {
|
if (note->frequency > US_FLOAT(1.99996)) {
|
||||||
@@ -730,43 +750,29 @@ u64 *synthesis_process_notes(s16 *aiBuf, s32 bufLen, u64 *cmd) {
|
|||||||
resamplingRateFixedPoint = (u16)(s32)(resamplingRate * 32768.0f);
|
resamplingRateFixedPoint = (u16)(s32)(resamplingRate * 32768.0f);
|
||||||
samplesLenFixedPoint = note->samplePosFrac + (resamplingRateFixedPoint * bufLen) * 2;
|
samplesLenFixedPoint = note->samplePosFrac + (resamplingRateFixedPoint * bufLen) * 2;
|
||||||
note->samplePosFrac = samplesLenFixedPoint & 0xFFFF; // 16-bit store, can't reuse
|
note->samplePosFrac = samplesLenFixedPoint & 0xFFFF; // 16-bit store, can't reuse
|
||||||
#else
|
|
||||||
resamplingRateFixedPoint = noteSubEu->resamplingRateFixedPoint;
|
|
||||||
nParts = noteSubEu->hasTwoAdpcmParts + 1;
|
|
||||||
samplesLenFixedPoint = (resamplingRateFixedPoint * tempBufLen * 2) + synthesisState->samplePosFrac;
|
|
||||||
synthesisState->samplePosFrac = samplesLenFixedPoint & 0xFFFF;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifdef VERSION_EU
|
DEBUG_PRINT("- if note sound is null");
|
||||||
if (noteSubEu->isSyntheticWave) {
|
|
||||||
cmd = load_wave_samples(cmd, noteSubEu, synthesisState, samplesLenFixedPoint >> 0x10);
|
|
||||||
noteSamplesDmemAddrBeforeResampling = (synthesisState->samplePosInt * 2) + DMEM_ADDR_UNCOMPRESSED_NOTE;
|
|
||||||
synthesisState->samplePosInt += samplesLenFixedPoint >> 0x10;
|
|
||||||
}
|
|
||||||
#else
|
|
||||||
if (note->sound == NULL) {
|
if (note->sound == NULL) {
|
||||||
// A wave synthesis note (not ADPCM)
|
// A wave synthesis note (not ADPCM)
|
||||||
|
|
||||||
|
DEBUG_PRINT("- note is null, do wave synthesis");
|
||||||
cmd = load_wave_samples(cmd, note, samplesLenFixedPoint >> 0x10);
|
cmd = load_wave_samples(cmd, note, samplesLenFixedPoint >> 0x10);
|
||||||
noteSamplesDmemAddrBeforeResampling = DMEM_ADDR_UNCOMPRESSED_NOTE + note->samplePosInt * 2;
|
noteSamplesDmemAddrBeforeResampling = DMEM_ADDR_UNCOMPRESSED_NOTE + note->samplePosInt * 2;
|
||||||
note->samplePosInt += (samplesLenFixedPoint >> 0x10);
|
note->samplePosInt += (samplesLenFixedPoint >> 0x10);
|
||||||
flags = 0;
|
flags = 0;
|
||||||
}
|
}
|
||||||
#endif
|
|
||||||
else {
|
else {
|
||||||
// ADPCM note
|
// ADPCM note
|
||||||
|
DEBUG_PRINT("- @ handle adpcm note");
|
||||||
|
|
||||||
#ifdef VERSION_EU
|
|
||||||
audioBookSample = noteSubEu->sound.audioBankSound->sample;
|
|
||||||
#else
|
|
||||||
audioBookSample = note->sound->sample;
|
audioBookSample = note->sound->sample;
|
||||||
#endif
|
|
||||||
|
|
||||||
loopInfo = audioBookSample->loop;
|
loopInfo = audioBookSample->loop;
|
||||||
endPos = loopInfo->end;
|
endPos = loopInfo->end;
|
||||||
sampleAddr = audioBookSample->sampleAddr;
|
sampleAddr = audioBookSample->sampleAddr;
|
||||||
resampledTempLen = 0;
|
resampledTempLen = 0;
|
||||||
for (curPart = 0; curPart < nParts; curPart++) {
|
for (curPart = 0; curPart < nParts; curPart++) {
|
||||||
|
DEBUG_PRINT("- for part %d", curPart);
|
||||||
nAdpcmSamplesProcessed = 0; // s8
|
nAdpcmSamplesProcessed = 0; // s8
|
||||||
s5 = 0; // s4
|
s5 = 0; // s4
|
||||||
|
|
||||||
@@ -782,21 +788,11 @@ u64 *synthesis_process_notes(s16 *aiBuf, s32 bufLen, u64 *cmd) {
|
|||||||
if (curLoadedBook != audioBookSample->book->book) {
|
if (curLoadedBook != audioBookSample->book->book) {
|
||||||
u32 nEntries; // v1
|
u32 nEntries; // v1
|
||||||
curLoadedBook = audioBookSample->book->book;
|
curLoadedBook = audioBookSample->book->book;
|
||||||
#ifdef VERSION_EU
|
|
||||||
nEntries = 16 * audioBookSample->book->order * audioBookSample->book->npredictors;
|
|
||||||
aLoadADPCM(cmd++, nEntries, VIRTUAL_TO_PHYSICAL2(curLoadedBook + noteSubEu->bookOffset));
|
|
||||||
#else
|
|
||||||
nEntries = audioBookSample->book->order * audioBookSample->book->npredictors;
|
nEntries = audioBookSample->book->order * audioBookSample->book->npredictors;
|
||||||
|
DEBUG_PRINT("- loading adpcm");
|
||||||
aLoadADPCM(cmd++, nEntries * 16, VIRTUAL_TO_PHYSICAL2(curLoadedBook));
|
aLoadADPCM(cmd++, nEntries * 16, VIRTUAL_TO_PHYSICAL2(curLoadedBook));
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef VERSION_EU
|
|
||||||
if (noteSubEu->bookOffset) {
|
|
||||||
curLoadedBook = euUnknownData_80301950; // what's this? never read
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
while (nAdpcmSamplesProcessed != samplesLenAdjusted) {
|
while (nAdpcmSamplesProcessed != samplesLenAdjusted) {
|
||||||
s32 samplesRemaining; // v1
|
s32 samplesRemaining; // v1
|
||||||
s32 s0;
|
s32 s0;
|
||||||
@@ -804,23 +800,12 @@ u64 *synthesis_process_notes(s16 *aiBuf, s32 bufLen, u64 *cmd) {
|
|||||||
noteFinished = FALSE;
|
noteFinished = FALSE;
|
||||||
restart = FALSE;
|
restart = FALSE;
|
||||||
nSamplesToProcess = samplesLenAdjusted - nAdpcmSamplesProcessed;
|
nSamplesToProcess = samplesLenAdjusted - nAdpcmSamplesProcessed;
|
||||||
#ifdef VERSION_EU
|
|
||||||
s2 = synthesisState->samplePosInt & 0xf;
|
|
||||||
samplesRemaining = endPos - synthesisState->samplePosInt;
|
|
||||||
#else
|
|
||||||
s2 = note->samplePosInt & 0xf;
|
s2 = note->samplePosInt & 0xf;
|
||||||
samplesRemaining = endPos - note->samplePosInt;
|
samplesRemaining = endPos - note->samplePosInt;
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifdef VERSION_EU
|
|
||||||
if (s2 == 0 && synthesisState->restart == FALSE) {
|
|
||||||
s2 = 16;
|
|
||||||
}
|
|
||||||
#else
|
|
||||||
if (s2 == 0 && note->restart == FALSE) {
|
if (s2 == 0 && note->restart == FALSE) {
|
||||||
s2 = 16;
|
s2 = 16;
|
||||||
}
|
}
|
||||||
#endif
|
|
||||||
s6 = 16 - s2; // a1
|
s6 = 16 - s2; // a1
|
||||||
|
|
||||||
if (nSamplesToProcess < samplesRemaining) {
|
if (nSamplesToProcess < samplesRemaining) {
|
||||||
@@ -828,11 +813,7 @@ u64 *synthesis_process_notes(s16 *aiBuf, s32 bufLen, u64 *cmd) {
|
|||||||
s0 = t0 * 16;
|
s0 = t0 * 16;
|
||||||
s3 = s6 + s0 - nSamplesToProcess;
|
s3 = s6 + s0 - nSamplesToProcess;
|
||||||
} else {
|
} else {
|
||||||
#ifndef VERSION_EU
|
|
||||||
s0 = samplesRemaining + s2 - 0x10;
|
s0 = samplesRemaining + s2 - 0x10;
|
||||||
#else
|
|
||||||
s0 = samplesRemaining - s6;
|
|
||||||
#endif
|
|
||||||
s3 = 0;
|
s3 = 0;
|
||||||
if (s0 <= 0) {
|
if (s0 <= 0) {
|
||||||
s0 = 0;
|
s0 = 0;
|
||||||
@@ -848,21 +829,10 @@ u64 *synthesis_process_notes(s16 *aiBuf, s32 bufLen, u64 *cmd) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (t0 != 0) {
|
if (t0 != 0) {
|
||||||
#ifdef VERSION_EU
|
|
||||||
temp = (synthesisState->samplePosInt - s2 + 0x10) / 16;
|
|
||||||
if (audioBookSample->loaded == 0x81) {
|
|
||||||
v0_2 = sampleAddr + temp * 9;
|
|
||||||
} else {
|
|
||||||
v0_2 = dma_sample_data(
|
|
||||||
(uintptr_t) (sampleAddr + temp * 9),
|
|
||||||
t0 * 9, flags, &synthesisState->sampleDmaIndex);
|
|
||||||
}
|
|
||||||
#else
|
|
||||||
temp = (note->samplePosInt - s2 + 0x10) / 16;
|
temp = (note->samplePosInt - s2 + 0x10) / 16;
|
||||||
v0_2 = dma_sample_data(
|
v0_2 = dma_sample_data(
|
||||||
(uintptr_t) (sampleAddr + temp * 9),
|
(uintptr_t) (sampleAddr + temp * 9),
|
||||||
t0 * 9, flags, ¬e->sampleDmaIndex);
|
t0 * 9, flags, ¬e->sampleDmaIndex);
|
||||||
#endif
|
|
||||||
a3 = (u32)((uintptr_t) v0_2 & 0xf);
|
a3 = (u32)((uintptr_t) v0_2 & 0xf);
|
||||||
aSetBuffer(cmd++, 0, DMEM_ADDR_COMPRESSED_ADPCM_DATA, 0, t0 * 9 + a3);
|
aSetBuffer(cmd++, 0, DMEM_ADDR_COMPRESSED_ADPCM_DATA, 0, t0 * 9 + a3);
|
||||||
aLoadBuffer(cmd++, VIRTUAL_TO_PHYSICAL2(v0_2 - a3));
|
aLoadBuffer(cmd++, VIRTUAL_TO_PHYSICAL2(v0_2 - a3));
|
||||||
@@ -871,38 +841,14 @@ u64 *synthesis_process_notes(s16 *aiBuf, s32 bufLen, u64 *cmd) {
|
|||||||
a3 = 0;
|
a3 = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef VERSION_EU
|
DEBUG_PRINT("- if not note restart");
|
||||||
if (synthesisState->restart != FALSE) {
|
|
||||||
aSetLoop(cmd++, VIRTUAL_TO_PHYSICAL2(audioBookSample->loop->state));
|
|
||||||
flags = A_LOOP; // = 2
|
|
||||||
synthesisState->restart = FALSE;
|
|
||||||
}
|
|
||||||
#else
|
|
||||||
if (note->restart != FALSE) {
|
if (note->restart != FALSE) {
|
||||||
aSetLoop(cmd++, VIRTUAL_TO_PHYSICAL2(audioBookSample->loop->state));
|
aSetLoop(cmd++, VIRTUAL_TO_PHYSICAL2(audioBookSample->loop->state));
|
||||||
flags = A_LOOP; // = 2
|
flags = A_LOOP; // = 2
|
||||||
note->restart = FALSE;
|
note->restart = FALSE;
|
||||||
}
|
}
|
||||||
#endif
|
|
||||||
|
|
||||||
nSamplesInThisIteration = s0 + s6 - s3;
|
nSamplesInThisIteration = s0 + s6 - s3;
|
||||||
#ifdef VERSION_EU
|
|
||||||
if (nAdpcmSamplesProcessed == 0) {
|
|
||||||
aSetBuffer(cmd++, 0, DMEM_ADDR_COMPRESSED_ADPCM_DATA + a3,
|
|
||||||
DMEM_ADDR_UNCOMPRESSED_NOTE, s0 * 2);
|
|
||||||
aADPCMdec(cmd++, flags,
|
|
||||||
VIRTUAL_TO_PHYSICAL2(synthesisState->synthesisBuffers->adpcmdecState));
|
|
||||||
sp130 = s2 * 2;
|
|
||||||
} else {
|
|
||||||
s5Aligned = ALIGN(s5, 5);
|
|
||||||
aSetBuffer(cmd++, 0, DMEM_ADDR_COMPRESSED_ADPCM_DATA + a3,
|
|
||||||
DMEM_ADDR_UNCOMPRESSED_NOTE + s5Aligned, s0 * 2);
|
|
||||||
aADPCMdec(cmd++, flags,
|
|
||||||
VIRTUAL_TO_PHYSICAL2(synthesisState->synthesisBuffers->adpcmdecState));
|
|
||||||
aDMEMMove(cmd++, DMEM_ADDR_UNCOMPRESSED_NOTE + s5Aligned + (s2 * 2),
|
|
||||||
DMEM_ADDR_UNCOMPRESSED_NOTE + s5, (nSamplesInThisIteration) * 2);
|
|
||||||
}
|
|
||||||
#else
|
|
||||||
if (nAdpcmSamplesProcessed == 0) {
|
if (nAdpcmSamplesProcessed == 0) {
|
||||||
aSetBuffer(cmd++, 0, DMEM_ADDR_COMPRESSED_ADPCM_DATA + a3, DMEM_ADDR_UNCOMPRESSED_NOTE, s0 * 2);
|
aSetBuffer(cmd++, 0, DMEM_ADDR_COMPRESSED_ADPCM_DATA + a3, DMEM_ADDR_UNCOMPRESSED_NOTE, s0 * 2);
|
||||||
aADPCMdec(cmd++, flags, VIRTUAL_TO_PHYSICAL2(note->synthesisBuffers->adpcmdecState));
|
aADPCMdec(cmd++, flags, VIRTUAL_TO_PHYSICAL2(note->synthesisBuffers->adpcmdecState));
|
||||||
@@ -912,7 +858,6 @@ u64 *synthesis_process_notes(s16 *aiBuf, s32 bufLen, u64 *cmd) {
|
|||||||
aADPCMdec(cmd++, flags, VIRTUAL_TO_PHYSICAL2(note->synthesisBuffers->adpcmdecState));
|
aADPCMdec(cmd++, flags, VIRTUAL_TO_PHYSICAL2(note->synthesisBuffers->adpcmdecState));
|
||||||
aDMEMMove(cmd++, DMEM_ADDR_UNCOMPRESSED_NOTE + ALIGN(s5, 5) + (s2 * 2), DMEM_ADDR_UNCOMPRESSED_NOTE + s5, (nSamplesInThisIteration) * 2);
|
aDMEMMove(cmd++, DMEM_ADDR_UNCOMPRESSED_NOTE + ALIGN(s5, 5) + (s2 * 2), DMEM_ADDR_UNCOMPRESSED_NOTE + s5, (nSamplesInThisIteration) * 2);
|
||||||
}
|
}
|
||||||
#endif
|
|
||||||
|
|
||||||
nAdpcmSamplesProcessed += nSamplesInThisIteration;
|
nAdpcmSamplesProcessed += nSamplesInThisIteration;
|
||||||
|
|
||||||
@@ -936,35 +881,23 @@ u64 *synthesis_process_notes(s16 *aiBuf, s32 bufLen, u64 *cmd) {
|
|||||||
}
|
}
|
||||||
flags = 0;
|
flags = 0;
|
||||||
|
|
||||||
|
DEBUG_PRINT("- if note finished");
|
||||||
if (noteFinished) {
|
if (noteFinished) {
|
||||||
aClearBuffer(cmd++, DMEM_ADDR_UNCOMPRESSED_NOTE + s5,
|
aClearBuffer(cmd++, DMEM_ADDR_UNCOMPRESSED_NOTE + s5,
|
||||||
(samplesLenAdjusted - nAdpcmSamplesProcessed) * 2);
|
(samplesLenAdjusted - nAdpcmSamplesProcessed) * 2);
|
||||||
#ifdef VERSION_EU
|
|
||||||
noteSubEu->finished = 1;
|
|
||||||
note->noteSubEu.finished = 1;
|
|
||||||
note->noteSubEu.enabled = 0;
|
|
||||||
#else
|
|
||||||
note->samplePosInt = 0;
|
note->samplePosInt = 0;
|
||||||
note->finished = 1;
|
note->finished = 1;
|
||||||
((struct vNote *)note)->enabled = 0;
|
((struct vNote *)note)->enabled = 0;
|
||||||
#endif
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
#ifdef VERSION_EU
|
|
||||||
if (restart) {
|
DEBUG_PRINT("- if restart");
|
||||||
synthesisState->restart = TRUE;
|
|
||||||
synthesisState->samplePosInt = loopInfo->start;
|
|
||||||
} else {
|
|
||||||
synthesisState->samplePosInt += nSamplesToProcess;
|
|
||||||
}
|
|
||||||
#else
|
|
||||||
if (restart) {
|
if (restart) {
|
||||||
note->restart = TRUE;
|
note->restart = TRUE;
|
||||||
note->samplePosInt = loopInfo->start;
|
note->samplePosInt = loopInfo->start;
|
||||||
} else {
|
} else {
|
||||||
note->samplePosInt += nSamplesToProcess;
|
note->samplePosInt += nSamplesToProcess;
|
||||||
}
|
}
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
|
|
||||||
switch (nParts) {
|
switch (nParts) {
|
||||||
@@ -976,18 +909,10 @@ u64 *synthesis_process_notes(s16 *aiBuf, s32 bufLen, u64 *cmd) {
|
|||||||
switch (curPart) {
|
switch (curPart) {
|
||||||
case 0:
|
case 0:
|
||||||
aSetBuffer(cmd++, 0, DMEM_ADDR_UNCOMPRESSED_NOTE + sp130, DMEM_ADDR_RESAMPLED, samplesLenAdjusted + 4);
|
aSetBuffer(cmd++, 0, DMEM_ADDR_UNCOMPRESSED_NOTE + sp130, DMEM_ADDR_RESAMPLED, samplesLenAdjusted + 4);
|
||||||
#ifdef VERSION_EU
|
|
||||||
aResample(cmd++, A_INIT, 0xff60, VIRTUAL_TO_PHYSICAL2(synthesisState->synthesisBuffers->dummyResampleState));
|
|
||||||
#else
|
|
||||||
aResample(cmd++, A_INIT, 0xff60, VIRTUAL_TO_PHYSICAL2(note->synthesisBuffers->dummyResampleState));
|
aResample(cmd++, A_INIT, 0xff60, VIRTUAL_TO_PHYSICAL2(note->synthesisBuffers->dummyResampleState));
|
||||||
#endif
|
|
||||||
resampledTempLen = samplesLenAdjusted + 4;
|
resampledTempLen = samplesLenAdjusted + 4;
|
||||||
noteSamplesDmemAddrBeforeResampling = DMEM_ADDR_RESAMPLED + 4;
|
noteSamplesDmemAddrBeforeResampling = DMEM_ADDR_RESAMPLED + 4;
|
||||||
#ifdef VERSION_EU
|
|
||||||
if (noteSubEu->finished != FALSE) {
|
|
||||||
#else
|
|
||||||
if (note->finished != FALSE) {
|
if (note->finished != FALSE) {
|
||||||
#endif
|
|
||||||
aClearBuffer(cmd++, DMEM_ADDR_RESAMPLED + resampledTempLen, samplesLenAdjusted + 0x10);
|
aClearBuffer(cmd++, DMEM_ADDR_RESAMPLED + resampledTempLen, samplesLenAdjusted + 0x10);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
@@ -996,15 +921,9 @@ u64 *synthesis_process_notes(s16 *aiBuf, s32 bufLen, u64 *cmd) {
|
|||||||
aSetBuffer(cmd++, 0, DMEM_ADDR_UNCOMPRESSED_NOTE + sp130,
|
aSetBuffer(cmd++, 0, DMEM_ADDR_UNCOMPRESSED_NOTE + sp130,
|
||||||
DMEM_ADDR_RESAMPLED2,
|
DMEM_ADDR_RESAMPLED2,
|
||||||
samplesLenAdjusted + 8);
|
samplesLenAdjusted + 8);
|
||||||
#ifdef VERSION_EU
|
|
||||||
aResample(cmd++, A_INIT, 0xff60,
|
|
||||||
VIRTUAL_TO_PHYSICAL2(
|
|
||||||
synthesisState->synthesisBuffers->dummyResampleState));
|
|
||||||
#else
|
|
||||||
aResample(cmd++, A_INIT, 0xff60,
|
aResample(cmd++, A_INIT, 0xff60,
|
||||||
VIRTUAL_TO_PHYSICAL2(
|
VIRTUAL_TO_PHYSICAL2(
|
||||||
note->synthesisBuffers->dummyResampleState));
|
note->synthesisBuffers->dummyResampleState));
|
||||||
#endif
|
|
||||||
aDMEMMove(cmd++, DMEM_ADDR_RESAMPLED2 + 4,
|
aDMEMMove(cmd++, DMEM_ADDR_RESAMPLED2 + 4,
|
||||||
DMEM_ADDR_RESAMPLED + resampledTempLen,
|
DMEM_ADDR_RESAMPLED + resampledTempLen,
|
||||||
samplesLenAdjusted + 4);
|
samplesLenAdjusted + 4);
|
||||||
@@ -1012,11 +931,7 @@ u64 *synthesis_process_notes(s16 *aiBuf, s32 bufLen, u64 *cmd) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef VERSION_EU
|
|
||||||
if (noteSubEu->finished != FALSE) {
|
|
||||||
#else
|
|
||||||
if (note->finished != FALSE) {
|
if (note->finished != FALSE) {
|
||||||
#endif
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -1024,15 +939,6 @@ u64 *synthesis_process_notes(s16 *aiBuf, s32 bufLen, u64 *cmd) {
|
|||||||
|
|
||||||
flags = 0;
|
flags = 0;
|
||||||
|
|
||||||
#ifdef VERSION_EU
|
|
||||||
if (noteSubEu->needsInit == TRUE) {
|
|
||||||
flags = A_INIT;
|
|
||||||
noteSubEu->needsInit = FALSE;
|
|
||||||
}
|
|
||||||
|
|
||||||
cmd = final_resample(cmd, synthesisState, bufLen * 2, resamplingRateFixedPoint,
|
|
||||||
noteSamplesDmemAddrBeforeResampling, flags);
|
|
||||||
#else
|
|
||||||
if (note->needsInit == TRUE) {
|
if (note->needsInit == TRUE) {
|
||||||
flags = A_INIT;
|
flags = A_INIT;
|
||||||
note->needsInit = FALSE;
|
note->needsInit = FALSE;
|
||||||
@@ -1040,75 +946,41 @@ u64 *synthesis_process_notes(s16 *aiBuf, s32 bufLen, u64 *cmd) {
|
|||||||
|
|
||||||
cmd = final_resample(cmd, note, bufLen * 2, resamplingRateFixedPoint,
|
cmd = final_resample(cmd, note, bufLen * 2, resamplingRateFixedPoint,
|
||||||
noteSamplesDmemAddrBeforeResampling, flags);
|
noteSamplesDmemAddrBeforeResampling, flags);
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifdef VERSION_EU
|
|
||||||
if (noteSubEu->headsetPanRight != 0 || synthesisState->prevHeadsetPanRight != 0) {
|
|
||||||
leftRight = 1;
|
|
||||||
} else if (noteSubEu->headsetPanLeft != 0 || synthesisState->prevHeadsetPanLeft != 0) {
|
|
||||||
leftRight = 2;
|
|
||||||
#else
|
|
||||||
if (note->headsetPanRight != 0 || note->prevHeadsetPanRight != 0) {
|
if (note->headsetPanRight != 0 || note->prevHeadsetPanRight != 0) {
|
||||||
leftRight = 1;
|
leftRight = 1;
|
||||||
} else if (note->headsetPanLeft != 0 || note->prevHeadsetPanLeft != 0) {
|
} else if (note->headsetPanLeft != 0 || note->prevHeadsetPanLeft != 0) {
|
||||||
leftRight = 2;
|
leftRight = 2;
|
||||||
#endif
|
|
||||||
} else {
|
} else {
|
||||||
leftRight = 0;
|
leftRight = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef VERSION_EU
|
|
||||||
cmd = process_envelope(cmd, noteSubEu, synthesisState, bufLen, 0, leftRight, flags);
|
|
||||||
#else
|
|
||||||
cmd = process_envelope(cmd, note, bufLen, 0, leftRight, flags);
|
cmd = process_envelope(cmd, note, bufLen, 0, leftRight, flags);
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifdef VERSION_EU
|
|
||||||
if (noteSubEu->usesHeadsetPanEffects) {
|
|
||||||
cmd = note_apply_headset_pan_effects(cmd, noteSubEu, synthesisState, bufLen * 2, flags, leftRight);
|
|
||||||
}
|
|
||||||
#else
|
|
||||||
if (note->usesHeadsetPanEffects) {
|
if (note->usesHeadsetPanEffects) {
|
||||||
cmd = note_apply_headset_pan_effects(cmd, note, bufLen * 2, flags, leftRight);
|
cmd = note_apply_headset_pan_effects(cmd, note, bufLen * 2, flags, leftRight);
|
||||||
}
|
}
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
#ifndef VERSION_EU
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
DEBUG_PRINT("- done handling notes");
|
||||||
|
|
||||||
|
DEBUG_PRINT("- setting buffer 1");
|
||||||
t9 = bufLen * 2;
|
t9 = bufLen * 2;
|
||||||
aSetBuffer(cmd++, 0, 0, DMEM_ADDR_TEMP, t9);
|
aSetBuffer(cmd++, 0, 0, DMEM_ADDR_TEMP, t9);
|
||||||
|
DEBUG_PRINT("- interleaving");
|
||||||
aInterleave(cmd++, DMEM_ADDR_LEFT_CH, DMEM_ADDR_RIGHT_CH);
|
aInterleave(cmd++, DMEM_ADDR_LEFT_CH, DMEM_ADDR_RIGHT_CH);
|
||||||
t9 *= 2;
|
t9 *= 2;
|
||||||
|
DEBUG_PRINT("- setting buffer 2");
|
||||||
aSetBuffer(cmd++, 0, 0, DMEM_ADDR_TEMP, t9);
|
aSetBuffer(cmd++, 0, 0, DMEM_ADDR_TEMP, t9);
|
||||||
|
DEBUG_PRINT("- saving buffer");
|
||||||
aSaveBuffer(cmd++, VIRTUAL_TO_PHYSICAL2(aiBuf));
|
aSaveBuffer(cmd++, VIRTUAL_TO_PHYSICAL2(aiBuf));
|
||||||
#endif
|
|
||||||
|
|
||||||
|
DEBUG_PRINT("- returning from process notes");
|
||||||
return cmd;
|
return cmd;
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef VERSION_EU
|
|
||||||
u64 *load_wave_samples(u64 *cmd, struct NoteSubEu *noteSubEu, struct NoteSynthesisState *synthesisState, s32 nSamplesToLoad) {
|
|
||||||
s32 a3;
|
|
||||||
s32 repeats;
|
|
||||||
s32 i;
|
|
||||||
aSetBuffer(cmd++, /*flags*/ 0, /*dmemin*/ DMEM_ADDR_UNCOMPRESSED_NOTE, /*dmemout*/ 0, /*count*/ 128);
|
|
||||||
aLoadBuffer(cmd++, VIRTUAL_TO_PHYSICAL2(noteSubEu->sound.samples));
|
|
||||||
|
|
||||||
synthesisState->samplePosInt &= 0x3f;
|
|
||||||
a3 = 64 - synthesisState->samplePosInt;
|
|
||||||
if (a3 < nSamplesToLoad) {
|
|
||||||
repeats = (nSamplesToLoad - a3 + 63) / 64;
|
|
||||||
for (i = 0; i < repeats; i++) {
|
|
||||||
aDMEMMove(cmd++,
|
|
||||||
/*dmemin*/ DMEM_ADDR_UNCOMPRESSED_NOTE,
|
|
||||||
/*dmemout*/ DMEM_ADDR_UNCOMPRESSED_NOTE + (1 + i) * 128,
|
|
||||||
/*count*/ 128);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return cmd;
|
|
||||||
}
|
|
||||||
#else
|
|
||||||
u64 *load_wave_samples(u64 *cmd, struct Note *note, s32 nSamplesToLoad) {
|
u64 *load_wave_samples(u64 *cmd, struct Note *note, s32 nSamplesToLoad) {
|
||||||
s32 a3;
|
s32 a3;
|
||||||
s32 i;
|
s32 i;
|
||||||
@@ -1124,21 +996,12 @@ u64 *load_wave_samples(u64 *cmd, struct Note *note, s32 nSamplesToLoad) {
|
|||||||
}
|
}
|
||||||
return cmd;
|
return cmd;
|
||||||
}
|
}
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifdef VERSION_EU
|
|
||||||
u64 *final_resample(u64 *cmd, struct NoteSynthesisState *synthesisState, s32 count, u16 pitch, u16 dmemIn, u32 flags) {
|
|
||||||
aSetBuffer(cmd++, /*flags*/ 0, dmemIn, /*dmemout*/ DMEM_ADDR_TEMP, count);
|
|
||||||
aResample(cmd++, flags, pitch, VIRTUAL_TO_PHYSICAL2(synthesisState->synthesisBuffers->finalResampleState));
|
|
||||||
return cmd;
|
|
||||||
}
|
|
||||||
#else
|
|
||||||
u64 *final_resample(u64 *cmd, struct Note *note, s32 count, u16 pitch, u16 dmemIn, u32 flags) {
|
u64 *final_resample(u64 *cmd, struct Note *note, s32 count, u16 pitch, u16 dmemIn, u32 flags) {
|
||||||
aSetBuffer(cmd++, /*flags*/ 0, dmemIn, /*dmemout*/ DMEM_ADDR_TEMP, count);
|
aSetBuffer(cmd++, /*flags*/ 0, dmemIn, /*dmemout*/ DMEM_ADDR_TEMP, count);
|
||||||
aResample(cmd++, flags, pitch, VIRTUAL_TO_PHYSICAL2(note->synthesisBuffers->finalResampleState));
|
aResample(cmd++, flags, pitch, VIRTUAL_TO_PHYSICAL2(note->synthesisBuffers->finalResampleState));
|
||||||
return cmd;
|
return cmd;
|
||||||
}
|
}
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifndef VERSION_EU
|
#ifndef VERSION_EU
|
||||||
u64 *process_envelope(u64 *cmd, struct Note *note, s32 nSamples, u16 inBuf, s32 headsetPanSettings,
|
u64 *process_envelope(u64 *cmd, struct Note *note, s32 nSamples, u16 inBuf, s32 headsetPanSettings,
|
||||||
|
|||||||
@@ -440,9 +440,13 @@ typedef short ENVMIX_STATE[40];
|
|||||||
*/
|
*/
|
||||||
#define aLoadBuffer(pkt, s) \
|
#define aLoadBuffer(pkt, s) \
|
||||||
{ \
|
{ \
|
||||||
|
DEBUG_PRINT("aLoadBuffer()"); \
|
||||||
|
DEBUG_PRINT("- getting pkt"); \
|
||||||
Acmd *_a = (Acmd *)pkt; \
|
Acmd *_a = (Acmd *)pkt; \
|
||||||
\
|
\
|
||||||
|
DEBUG_PRINT("- setting first word"); \
|
||||||
_a->words.w0 = _SHIFTL(A_LOADBUFF, 24, 8); \
|
_a->words.w0 = _SHIFTL(A_LOADBUFF, 24, 8); \
|
||||||
|
DEBUG_PRINT("- setting second word"); \
|
||||||
_a->words.w1 = (uintptr_t)(s); \
|
_a->words.w1 = (uintptr_t)(s); \
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -558,6 +562,8 @@ typedef short ENVMIX_STATE[40];
|
|||||||
*/
|
*/
|
||||||
#define aSetBuffer(pkt, f, i, o, c) \
|
#define aSetBuffer(pkt, f, i, o, c) \
|
||||||
{ \
|
{ \
|
||||||
|
DEBUG_PRINT("aSetBuffer()"); \
|
||||||
|
DEBUG_PRINT("- getting pkt"); \
|
||||||
Acmd *_a = (Acmd *)pkt; \
|
Acmd *_a = (Acmd *)pkt; \
|
||||||
\
|
\
|
||||||
_a->words.w0 = (_SHIFTL(A_SETBUFF, 24, 8) | _SHIFTL(f, 16, 8) | \
|
_a->words.w0 = (_SHIFTL(A_SETBUFF, 24, 8) | _SHIFTL(f, 16, 8) | \
|
||||||
|
|||||||
@@ -2,49 +2,21 @@
|
|||||||
#define _ULTRA64_LIBAUDIO_H_
|
#define _ULTRA64_LIBAUDIO_H_
|
||||||
|
|
||||||
#include "abi.h"
|
#include "abi.h"
|
||||||
|
#include <stdlib.h>
|
||||||
|
|
||||||
typedef struct
|
typedef struct
|
||||||
{
|
{
|
||||||
u8 *offset;
|
u8 *offset __attribute__((aligned (8)));
|
||||||
s32 len;
|
s32 len __attribute__((aligned (8)));
|
||||||
#ifdef VERSION_SH
|
|
||||||
s8 medium;
|
|
||||||
s8 magic; // tbl: 0x04, otherwise: 0x03
|
|
||||||
|
|
||||||
// for ctl (else zeros):
|
|
||||||
union {
|
|
||||||
// unused, just for clarification (big endian)
|
|
||||||
struct {
|
|
||||||
u8 bank;
|
|
||||||
u8 ff;
|
|
||||||
u8 numInstruments;
|
|
||||||
u8 numDrums;
|
|
||||||
} as_u8;
|
|
||||||
|
|
||||||
// used
|
|
||||||
struct {
|
|
||||||
s16 bankAndFf;
|
|
||||||
s16 numInstrumentsAndDrums;
|
|
||||||
} as_s16;
|
|
||||||
} ctl;
|
|
||||||
#endif
|
|
||||||
} ALSeqData;
|
} ALSeqData;
|
||||||
|
|
||||||
typedef struct
|
typedef struct
|
||||||
{
|
{
|
||||||
#ifndef VERSION_SH
|
unsigned short revision;
|
||||||
s16 revision;
|
unsigned short seqCount;
|
||||||
#endif
|
unsigned int pad;
|
||||||
s16 seqCount;
|
|
||||||
#ifdef VERSION_SH
|
|
||||||
s16 unk2;
|
|
||||||
u8 *data;
|
|
||||||
#if !IS_64_BIT
|
|
||||||
s32 pad[2];
|
|
||||||
#endif
|
|
||||||
#endif
|
|
||||||
ALSeqData seqArray[1];
|
ALSeqData seqArray[1];
|
||||||
} ALSeqFile;
|
} __attribute__((aligned (16))) ALSeqFile;
|
||||||
|
|
||||||
void alSeqFileNew(ALSeqFile *f, u8 *base);
|
void alSeqFileNew(ALSeqFile *f, u8 *base);
|
||||||
|
|
||||||
|
|||||||
@@ -10,6 +10,6 @@
|
|||||||
#define IS_BIG_ENDIAN (__BYTE_ORDER__ == __ORDER_BIG_ENDIAN__)
|
#define IS_BIG_ENDIAN (__BYTE_ORDER__ == __ORDER_BIG_ENDIAN__)
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#define DOUBLE_SIZE_ON_64_BIT(size) ((size) * (sizeof(void *) / 4))
|
#define DOUBLE_SIZE_ON_64_BIT(size) ((size) * 2)
|
||||||
|
|
||||||
#endif // PLATFORM_INFO_H
|
#endif // PLATFORM_INFO_H
|
||||||
|
|||||||
@@ -1,12 +1,19 @@
|
|||||||
#include "libultra_internal.h"
|
#include "libultra_internal.h"
|
||||||
#include "libaudio_internal.h"
|
#include "libaudio_internal.h"
|
||||||
|
|
||||||
|
#include "../../debug_print.h"
|
||||||
|
|
||||||
#define PATCH(SRC, BASE, TYPE) //SRC = (TYPE)((uintptr_t) SRC + (uintptr_t) BASE)
|
#define PATCH(SRC, BASE, TYPE) //SRC = (TYPE)((uintptr_t) SRC + (uintptr_t) BASE)
|
||||||
|
|
||||||
void alSeqFileNew(ALSeqFile *f, u8 *base) {
|
void alSeqFileNew(ALSeqFile *f, u8 *base) {
|
||||||
|
DEBUG_PRINT("alSeqFileNew()");
|
||||||
int i;
|
int i;
|
||||||
|
DEBUG_PRINT("- patching %d entries", f->seqCount);
|
||||||
for (i = 0; i < f->seqCount; i++) {
|
for (i = 0; i < f->seqCount; i++) {
|
||||||
|
DEBUG_PRINT("- handling entry %d", i);
|
||||||
|
DEBUG_PRINT("- patching offset (%x) with base (%x)", f->seqArray[i].offset, base);
|
||||||
PATCH(f->seqArray[i].offset, base, u8 *);
|
PATCH(f->seqArray[i].offset, base, u8 *);
|
||||||
|
DEBUG_PRINT("- result is (%x)", f->seqArray[i].offset);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -4,6 +4,7 @@
|
|||||||
#include <ultra64.h>
|
#include <ultra64.h>
|
||||||
|
|
||||||
#include "mixer.h"
|
#include "mixer.h"
|
||||||
|
#include "../../debug_print.h"
|
||||||
|
|
||||||
#ifdef __SSE4_1__
|
#ifdef __SSE4_1__
|
||||||
#include <immintrin.h>
|
#include <immintrin.h>
|
||||||
@@ -147,6 +148,8 @@ void aSaveBufferImpl(uint16_t source_addr, int16_t *dest_addr, uint16_t nbytes)
|
|||||||
}
|
}
|
||||||
#else
|
#else
|
||||||
void aLoadBufferImpl(const void *source_addr) {
|
void aLoadBufferImpl(const void *source_addr) {
|
||||||
|
DEBUG_PRINT("aLoadBufferImpl()");
|
||||||
|
DEBUG_PRINT("- source_addr: %x", source_addr);
|
||||||
memcpy(BUF_U8(rspa.in), source_addr, ROUND_UP_8(rspa.nbytes));
|
memcpy(BUF_U8(rspa.in), source_addr, ROUND_UP_8(rspa.nbytes));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
#include "convUtils.h"
|
#include "convUtils.h"
|
||||||
|
|
||||||
|
#include "../../debug_print.h"
|
||||||
#include "utils.h"
|
#include "utils.h"
|
||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
@@ -21,6 +22,8 @@
|
|||||||
unsigned char* gCtlSeqs;
|
unsigned char* gCtlSeqs;
|
||||||
|
|
||||||
struct seqFile* parse_seqfile(unsigned char* seq){ /* Read SeqFile data */
|
struct seqFile* parse_seqfile(unsigned char* seq){ /* Read SeqFile data */
|
||||||
|
DEBUG_PRINT("parse_seqfile()");
|
||||||
|
|
||||||
short revision = read_u16_be(seq);
|
short revision = read_u16_be(seq);
|
||||||
short bankCount = read_u16_be(seq + 2);
|
short bankCount = read_u16_be(seq + 2);
|
||||||
|
|
||||||
@@ -34,14 +37,20 @@ struct seqFile* parse_seqfile(unsigned char* seq){ /* Read SeqFile data */
|
|||||||
seqFile->seqArray[i].len = read_u32_be((seq + 4 + i * 8 + 4));
|
seqFile->seqArray[i].len = read_u32_be((seq + 4 + i * 8 + 4));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
DEBUG_PRINT("- revision: %d", revision);
|
||||||
if (revision == TYPE_CTL){
|
if (revision == TYPE_CTL){
|
||||||
|
DEBUG_PRINT("- ctl!");
|
||||||
// CTL file, contains instrument and drum data, this is really the only one that needs to be parsed, the rest only needs a header change
|
// CTL file, contains instrument and drum data, this is really the only one that needs to be parsed, the rest only needs a header change
|
||||||
gCtlSeqs = (unsigned char*)calloc(0x20B40, 1); // We only really need 0x20AD0 bytes but still
|
gCtlSeqs = (unsigned char*)calloc(0x20B40, 1); // We only really need 0x20AD0 bytes but still
|
||||||
uintptr_t pos = (uintptr_t)gCtlSeqs;
|
uintptr_t pos = (uintptr_t)gCtlSeqs;
|
||||||
|
DEBUG_PRINT("- bank count: %d", bankCount);
|
||||||
for (int i = 0; i < bankCount; i++){
|
for (int i = 0; i < bankCount; i++){
|
||||||
|
DEBUG_PRINT("- ctl bank index: %d", i);
|
||||||
uintptr_t start = pos;
|
uintptr_t start = pos;
|
||||||
struct CTL* ptr = parse_ctl_data(seq+(seqFile->seqArray[i].offset), &pos);
|
struct CTL* ptr = parse_ctl_data(seq+(seqFile->seqArray[i].offset), &pos);
|
||||||
|
DEBUG_PRINT("- read ptr: %x", ptr);
|
||||||
seqFile->seqArray[i].offset = ptr;
|
seqFile->seqArray[i].offset = ptr;
|
||||||
|
DEBUG_PRINT("- stored offset: %x", seqFile->seqArray[i].offset);
|
||||||
seqFile->seqArray[i].len = (unsigned int)(pos - start);
|
seqFile->seqArray[i].len = (unsigned int)(pos - start);
|
||||||
}
|
}
|
||||||
}else if (revision == TYPE_TBL){
|
}else if (revision == TYPE_TBL){
|
||||||
@@ -247,6 +256,9 @@ struct SEQ* parse_seq_data(unsigned char* seq){
|
|||||||
}
|
}
|
||||||
|
|
||||||
struct CTL* parse_ctl_data(unsigned char* ctlData, uintptr_t* pos){
|
struct CTL* parse_ctl_data(unsigned char* ctlData, uintptr_t* pos){
|
||||||
|
DEBUG_PRINT("parse_ctl_data()");
|
||||||
|
DEBUG_PRINT("- ctlData: %x", ctlData);
|
||||||
|
DEBUG_PRINT("- pos: %x", pos);
|
||||||
int instruments=read_u32_be(ctlData);
|
int instruments=read_u32_be(ctlData);
|
||||||
unsigned int size = sizeof(struct CTL) + sizeof(struct CInstrument*) * (instruments-1);
|
unsigned int size = sizeof(struct CTL) + sizeof(struct CInstrument*) * (instruments-1);
|
||||||
struct CTL* ctl = (struct CTL*)(*pos);
|
struct CTL* ctl = (struct CTL*)(*pos);
|
||||||
|
|||||||
+22
-2
@@ -10,6 +10,7 @@
|
|||||||
#include <string.h>
|
#include <string.h>
|
||||||
#include <math.h>
|
#include <math.h>
|
||||||
|
|
||||||
|
#include "decomp/audio/external.h"
|
||||||
#include "decomp/include/PR/os_cont.h"
|
#include "decomp/include/PR/os_cont.h"
|
||||||
#include "decomp/engine/math_util.h"
|
#include "decomp/engine/math_util.h"
|
||||||
#include "decomp/include/sm64.h"
|
#include "decomp/include/sm64.h"
|
||||||
@@ -135,8 +136,27 @@ SM64_LIB_FN void sm64_global_terminate( void )
|
|||||||
memory_terminate();
|
memory_terminate();
|
||||||
}
|
}
|
||||||
|
|
||||||
SM64_LIB_FN struct AudioBanks sm64_asset_load_audio_banks( uint8_t *rom ) {
|
SM64_LIB_FN void sm64_audio_init( uint8_t *rom ) {
|
||||||
return load_audio_banks( rom );
|
load_audio_banks( rom );
|
||||||
|
}
|
||||||
|
|
||||||
|
#define SAMPLES_HIGH 544
|
||||||
|
#define SAMPLES_LOW 528
|
||||||
|
|
||||||
|
extern SM64_LIB_FN uint32_t sm64_audio_tick( uint32_t numQueuedSamples, uint32_t numDesiredSamples, int16_t *audio_buffer ) {
|
||||||
|
DEBUG_PRINT("sm64_tick_audio()");
|
||||||
|
|
||||||
|
DEBUG_PRINT("- update game sound");
|
||||||
|
update_game_sound();
|
||||||
|
|
||||||
|
DEBUG_PRINT("- create next audio buffer");
|
||||||
|
u32 num_audio_samples = numQueuedSamples < numDesiredSamples ? SAMPLES_HIGH : SAMPLES_LOW;
|
||||||
|
for (int i = 0; i < 2; i++)
|
||||||
|
{
|
||||||
|
create_next_audio_buffer(audio_buffer + i * (2 * num_audio_samples), num_audio_samples);
|
||||||
|
}
|
||||||
|
|
||||||
|
return num_audio_samples;
|
||||||
}
|
}
|
||||||
|
|
||||||
SM64_LIB_FN void sm64_static_surfaces_load( const struct SM64Surface *surfaceArray, uint32_t numSurfaces )
|
SM64_LIB_FN void sm64_static_surfaces_load( const struct SM64Surface *surfaceArray, uint32_t numSurfaces )
|
||||||
|
|||||||
+2
-1
@@ -80,7 +80,8 @@ extern SM64_LIB_FN void sm64_register_play_sound_function( SM64PlaySoundFunction
|
|||||||
extern SM64_LIB_FN void sm64_global_init( uint8_t *rom, uint8_t *outTexture );
|
extern SM64_LIB_FN void sm64_global_init( uint8_t *rom, uint8_t *outTexture );
|
||||||
extern SM64_LIB_FN void sm64_global_terminate( void );
|
extern SM64_LIB_FN void sm64_global_terminate( void );
|
||||||
|
|
||||||
extern SM64_LIB_FN struct AudioBanks sm64_asset_load_audio_banks( uint8_t *rom );
|
extern SM64_LIB_FN void sm64_audio_init( uint8_t *rom );
|
||||||
|
extern SM64_LIB_FN uint32_t sm64_audio_tick( uint32_t numQueuedSamples, uint32_t numDesiredSamples, int16_t *audio_buffer );
|
||||||
|
|
||||||
extern SM64_LIB_FN void sm64_static_surfaces_load( const struct SM64Surface *surfaceArray, uint32_t numSurfaces );
|
extern SM64_LIB_FN void sm64_static_surfaces_load( const struct SM64Surface *surfaceArray, uint32_t numSurfaces );
|
||||||
|
|
||||||
|
|||||||
+16
-12
@@ -1,32 +1,36 @@
|
|||||||
#include "load_audio_data.h"
|
#include "load_audio_data.h"
|
||||||
|
|
||||||
|
#include "debug_print.h"
|
||||||
#include "decomp/tools/convUtils.h"
|
#include "decomp/tools/convUtils.h"
|
||||||
#include "decomp/audio/load.h"
|
#include "decomp/audio/load.h"
|
||||||
#include "decomp/audio/load_dat.h"
|
#include "decomp/audio/load_dat.h"
|
||||||
|
|
||||||
extern struct AudioBanks load_audio_banks( uint8_t *rom ) {
|
extern void load_audio_banks( uint8_t *rom ) {
|
||||||
|
DEBUG_PRINT("load_audio_banks()");
|
||||||
|
DEBUG_PRINT("- malloc");
|
||||||
uint8_t *rom2 = malloc(0x800000);
|
uint8_t *rom2 = malloc(0x800000);
|
||||||
|
|
||||||
|
DEBUG_PRINT("- memcpy");
|
||||||
memcpy(rom2, rom, 0x800000);
|
memcpy(rom2, rom, 0x800000);
|
||||||
rom = rom2;
|
rom = rom2;
|
||||||
|
DEBUG_PRINT("- parse ctl");
|
||||||
gSoundDataADSR = parse_seqfile(rom+0x57B720); //ctl
|
gSoundDataADSR = parse_seqfile(rom+0x57B720); //ctl
|
||||||
|
DEBUG_PRINT("- parse tbl");
|
||||||
gSoundDataRaw = parse_seqfile(rom+0x593560); //tbl
|
gSoundDataRaw = parse_seqfile(rom+0x593560); //tbl
|
||||||
|
DEBUG_PRINT("- parse music");
|
||||||
gMusicData = parse_seqfile(rom+0x7B0860);
|
gMusicData = parse_seqfile(rom+0x7B0860);
|
||||||
gBankSetsData = rom+0x7CC621;
|
gBankSetsData = rom+0x7CC621;
|
||||||
|
DEBUG_PRINT("- memmove");
|
||||||
memmove(gBankSetsData+0x45,gBankSetsData+0x45-1,0x5B);
|
memmove(gBankSetsData+0x45,gBankSetsData+0x45-1,0x5B);
|
||||||
gBankSetsData[0x45]=0x00;
|
gBankSetsData[0x45]=0x00;
|
||||||
|
DEBUG_PRINT("- ptrs to offsets");
|
||||||
ptrs_to_offsets(gSoundDataADSR);
|
ptrs_to_offsets(gSoundDataADSR);
|
||||||
|
|
||||||
|
DEBUG_PRINT("- audio init");
|
||||||
audio_init();
|
audio_init();
|
||||||
|
DEBUG_PRINT("- sound init");
|
||||||
int numBanks = 10;
|
sound_init();
|
||||||
for (int i = 0; i < 10; ++i) {
|
DEBUG_PRINT("- sound reset");
|
||||||
bank_load_immediate(i, 2);
|
sound_reset(0);
|
||||||
}
|
DEBUG_PRINT("- done with audio init!");
|
||||||
|
|
||||||
struct AudioBanks audioBanks;
|
|
||||||
audioBanks.numCtlEntries = numBanks;
|
|
||||||
audioBanks.ctlEntries = gCtlEntries;
|
|
||||||
|
|
||||||
return audioBanks;
|
|
||||||
}
|
}
|
||||||
@@ -2,9 +2,4 @@
|
|||||||
|
|
||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
|
|
||||||
struct AudioBanks {
|
extern void load_audio_banks( uint8_t *rom );
|
||||||
int numCtlEntries;
|
|
||||||
struct CtlEntry * ctlEntries;
|
|
||||||
};
|
|
||||||
|
|
||||||
extern struct AudioBanks load_audio_banks( uint8_t *rom );
|
|
||||||
@@ -1,8 +1,16 @@
|
|||||||
#include "play_sound.h"
|
#include "play_sound.h"
|
||||||
|
|
||||||
|
#include "decomp/audio/external.h"
|
||||||
|
#include "debug_print.h"
|
||||||
|
|
||||||
SM64PlaySoundFunctionPtr g_play_sound_func = NULL;
|
SM64PlaySoundFunctionPtr g_play_sound_func = NULL;
|
||||||
|
|
||||||
extern void play_sound( uint32_t soundBits, f32 *pos ) {
|
extern void play_sound( uint32_t soundBits, f32 *pos ) {
|
||||||
|
DEBUG_PRINT("$ play_sound(%d) request %d; pos %f %f %f\n", soundBits,sSoundRequestCount,pos[0],pos[1],pos[2]);
|
||||||
|
sSoundRequests[sSoundRequestCount].soundBits = soundBits;
|
||||||
|
sSoundRequests[sSoundRequestCount].position = pos;
|
||||||
|
sSoundRequestCount++;
|
||||||
|
|
||||||
if ( g_play_sound_func ) {
|
if ( g_play_sound_func ) {
|
||||||
g_play_sound_func(soundBits, pos);
|
g_play_sound_func(soundBits, pos);
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user