More musyx work

This commit is contained in:
Phillip Stephens 2022-12-24 14:54:58 -08:00
parent c1c2083bb4
commit 4919b49af6
12 changed files with 894 additions and 37 deletions

View File

@ -51,7 +51,9 @@
"dsp.h": "c",
"ar.h": "c",
"osrtcpriv.h": "c",
"osbootinfo.h": "c"
"osbootinfo.h": "c",
"assert.h": "c",
"math.h": "c"
},
"files.autoSave": "onFocusChange",
"files.insertFinalNewline": true,

View File

@ -545,8 +545,7 @@ lbl_803B6164:
/* 803B6254 003B31B4 38 21 00 30 */ addi r1, r1, 0x30
/* 803B6258 003B31B8 4E 80 00 20 */ blr
.global HandleReverb_0
HandleReverb_0:
.fn HandleReverb, local
/* 803B625C 003B31BC 94 21 FF 40 */ stwu r1, -0xc0(r1)
/* 803B6260 003B31C0 BD C1 00 08 */ stmw r14, 8(r1)
/* 803B6264 003B31C4 D9 C1 00 60 */ stfd f14, 0x60(r1)
@ -899,6 +898,7 @@ lbl_803B66C0:
/* 803B675C 003B36BC B9 C1 00 08 */ lmw r14, 8(r1)
/* 803B6760 003B36C0 38 21 00 C0 */ addi r1, r1, 0xc0
/* 803B6764 003B36C4 4E 80 00 20 */ blr
.endfn HandleReverb
.global ReverbHICallback
ReverbHICallback:
@ -941,19 +941,19 @@ lbl_803B67E8:
/* 803B67E8 003B3748 7F 63 DB 78 */ mr r3, r27
/* 803B67EC 003B374C 7F C4 F3 78 */ mr r4, r30
/* 803B67F0 003B3750 38 A0 00 00 */ li r5, 0
/* 803B67F4 003B3754 4B FF FA 69 */ bl HandleReverb_0
/* 803B67F4 003B3754 4B FF FA 69 */ bl HandleReverb
/* 803B67F8 003B3758 48 00 00 28 */ b lbl_803B6820
lbl_803B67FC:
/* 803B67FC 003B375C 7F 83 E3 78 */ mr r3, r28
/* 803B6800 003B3760 7F C4 F3 78 */ mr r4, r30
/* 803B6804 003B3764 38 A0 00 01 */ li r5, 1
/* 803B6808 003B3768 4B FF FA 55 */ bl HandleReverb_0
/* 803B6808 003B3768 4B FF FA 55 */ bl HandleReverb
/* 803B680C 003B376C 48 00 00 14 */ b lbl_803B6820
lbl_803B6810:
/* 803B6810 003B3770 7F A3 EB 78 */ mr r3, r29
/* 803B6814 003B3774 7F C4 F3 78 */ mr r4, r30
/* 803B6818 003B3778 38 A0 00 02 */ li r5, 2
/* 803B681C 003B377C 4B FF FA 41 */ bl HandleReverb_0
/* 803B681C 003B377C 4B FF FA 41 */ bl HandleReverb
lbl_803B6820:
/* 803B6820 003B3780 3B FF 00 01 */ addi r31, r31, 1
lbl_803B6824:

View File

@ -940,8 +940,8 @@ LIBS = [
"musyx/hw_volconv",
["musyx/snd3d", False],
["musyx/snd_init", True],
["musyx/snd_math", False],
"musyx/snd_midictrl",
["musyx/snd_math", True],
["musyx/snd_midictrl", False],
["musyx/snd_service", True],
["musyx/hardware", False],
"musyx/hw_aramdma",
@ -953,7 +953,7 @@ LIBS = [
["musyx/reverb_fx", True],
["musyx/reverb", False],
["musyx/delay_fx", True],
"musyx/chorus_fx",
["musyx/chorus_fx", True],
],
},
{
@ -1133,7 +1133,10 @@ if __name__ == "__main__":
n.variable("devkitppc", "/opt/devkitpro/devkitPPC")
cflags_base = "-proc gekko -nodefaults -Cpp_exceptions off -RTTI off -fp hard -fp_contract on -O4,p -maxerrors 1 -enum int -inline auto -str reuse -nosyspath -MMD -DPRIME1 -DVERSION=$version_num -DNONMATCHING=0 -i include/ -i libc/"
if args.debug:
cflags_base += " -sym on"
cflags_base += " -sym on -D_DEBUG"
else:
cflags_base += " -DNDEBUG"
n.variable("cflags_base", cflags_base)
n.variable(
"cflags_retro",
@ -1143,7 +1146,7 @@ if __name__ == "__main__":
"cflags_runtime",
"$cflags_base -use_lmw_stmw on -str reuse,pool,readonly -gccinc -inline deferred,auto",
)
n.variable("cflags_musyx", "$cflags_base -str reuse,pool,readonly")
n.variable("cflags_musyx", "$cflags_base -str reuse,pool,readonly -fp_contract off")
asflags = "-mgekko -I include/ --defsym version=$version_num -W --strip-local-absolute -gdwarf-2"
n.variable("asflags", asflags)
ldflags = "-fp fmadd -nodefaults -lcf ldscript.lcf"

32
include/musyx/assert.h Normal file
View File

@ -0,0 +1,32 @@
#ifndef _MUSYX_ASSERT
#define _MUSYX_ASSERT
extern void OSPanic(const char* file, int line, const char* msg, ...);
#ifndef ASSERT
#ifdef _DEBUG
#define ASSERT(cond) \
do { \
if (!cond) { \
OSPanic(__FILE__, __LINE__, "Failed assertion " #cond); \
} \
} while(0)
#else
#define ASSERT(cond)
#endif
#endif
#ifndef ASSERT_MSG
#ifdef _DEBUG
#define ASSERT_MSG(cond, msg) \
do { \
if (!cond) { \
OSPanic(__FILE__, __LINE__, msg); \
} \
} while(0)
#else
#define ASSERT_MSG(cond, msg)
#endif
#endif
#endif // _MUSYX_ASSERT

View File

@ -236,7 +236,49 @@ SND_VOICEID sndFXCheck(SND_VOICEID vid);
bool sndFXKeyOff(SND_VOICEID vid);
bool sndFXCtrl(SND_VOICEID vid, u8 ctrl, u8 value);
bool sndFXCtrl14(SND_VOICEID vid, u8 ctrl, u16 value);
#define _SND_CHORUS_NUM_BLOCKS 3
typedef struct _SND_CHORUS_SRCINFO {
s32* dest;
s32* smpBase;
s32* old;
u32 posLo;
u32 posHi;
u32 pitchLo;
u32 pitchHi;
u32 trigger;
u32 target;
} _SND_CHORUS_SRCINFO;
typedef struct _SND_CHORUS_WORK {
s32* lastLeft[_SND_CHORUS_NUM_BLOCKS];
s32* lastRight[_SND_CHORUS_NUM_BLOCKS];
s32* lastSur[_SND_CHORUS_NUM_BLOCKS];
u8 currentLast;
s32 oldLeft[4];
s32 oldRight[4];
s32 oldSur[4];
u32 currentPosLo;
u32 currentPosHi;
s32 pitchOffset;
u32 pitchOffsetPeriodCount;
u32 pitchOffsetPeriod;
_SND_CHORUS_SRCINFO src;
} _SND_CHORUS_WORK;
typedef struct SND_AUX_CHORUS {
_SND_CHORUS_WORK work;
u32 baseDelay;
u32 variation;
u32 period;
} SND_AUX_CHORUS;
void sndAuxCallbackChorus(u8 reason, SND_AUX_INFO* info, void* user);
bool sndAuxCallbackPrepareChorus(SND_AUX_CHORUS* ch);
bool sndAuxCallbackShutdownChorus(SND_AUX_CHORUS* ch);
bool sndAuxCallbackUpdateSettingsChorus(SND_AUX_CHORUS* ch);
#ifdef __cplusplus
}
#endif

View File

@ -89,6 +89,7 @@ double copysign(double x, double y);
double floor(double x);
double fabs(double x);
double pow(double x, double y);
#ifdef __MWERKS__
#pragma cplusplus on

540
src/musyx/chorus_fx.c Normal file
View File

@ -0,0 +1,540 @@
#include "musyx/musyx_priv.h"
#include "musyx/assert.h"
static float rsmpTab12khz[512] = {
0.097503662109f, 0.802215576172f, 0.101593017578f, -0.000976562500f, 0.093505859375f,
0.802032470703f, 0.105804443359f, -0.001037597656f, 0.089599609375f, 0.801696777344f,
0.110107421875f, -0.001159667969f, 0.085784912109f, 0.801177978516f, 0.114471435547f,
-0.001281738281f, 0.082031250000f, 0.800476074219f, 0.118927001953f, -0.001403808594f,
0.078369140625f, 0.799621582031f, 0.123474121094f, -0.001525878906f, 0.074798583984f,
0.798614501953f, 0.128143310547f, -0.001647949219f, 0.071350097656f, 0.797424316406f,
0.132873535156f, -0.001770019531f, 0.067962646484f, 0.796051025391f, 0.137695312500f,
-0.001922607422f, 0.064697265625f, 0.794525146484f, 0.142608642578f, -0.002044677734f,
0.061492919922f, 0.792846679688f, 0.147613525391f, -0.002197265625f, 0.058349609375f,
0.790985107422f, 0.152709960938f, -0.002319335938f, 0.055328369141f, 0.788940429688f,
0.157897949219f, -0.002471923828f, 0.052368164062f, 0.786743164062f, 0.163177490234f,
-0.002655029297f, 0.049499511719f, 0.784423828125f, 0.168518066406f, -0.002807617188f,
0.046722412109f, 0.781890869141f, 0.173980712891f, -0.002990722656f, 0.044006347656f,
0.779205322266f, 0.179504394531f, -0.003143310547f, 0.041412353516f, 0.776367187500f,
0.185119628906f, -0.003326416016f, 0.038879394531f, 0.773376464844f, 0.190826416016f,
-0.003509521484f, 0.036407470703f, 0.770233154297f, 0.196594238281f, -0.003692626953f,
0.034027099609f, 0.766937255859f, 0.202484130859f, -0.003875732422f, 0.031738281250f,
0.763488769531f, 0.208435058594f, -0.004058837891f, 0.029510498047f, 0.759857177734f,
0.214447021484f, -0.004272460938f, 0.027374267578f, 0.756103515625f, 0.220550537109f,
-0.004455566406f, 0.025299072266f, 0.752197265625f, 0.226745605469f, -0.004669189453f,
0.023315429688f, 0.748168945312f, 0.233001708984f, -0.004852294922f, 0.021392822266f,
0.743988037109f, 0.239318847656f, -0.005065917969f, 0.019561767578f, 0.739654541016f,
0.245727539062f, -0.005310058594f, 0.017791748047f, 0.735198974609f, 0.252197265625f,
-0.005523681641f, 0.016052246094f, 0.730590820312f, 0.258728027344f, -0.005706787109f,
0.014404296875f, 0.725860595703f, 0.265350341797f, -0.005920410156f, 0.012817382812f,
0.721008300781f, 0.272033691406f, -0.006164550781f, 0.011322021484f, 0.716003417969f,
0.278778076172f, -0.006378173828f, 0.009887695312f, 0.710906982422f, 0.285583496094f,
-0.006561279297f, 0.008514404297f, 0.705657958984f, 0.292449951172f, -0.006774902344f,
0.007202148438f, 0.700317382812f, 0.299346923828f, -0.007019042969f, 0.005920410156f,
0.694854736328f, 0.306335449219f, -0.007232666016f, 0.004699707031f, 0.689270019531f,
0.313385009766f, -0.007415771484f, 0.003570556641f, 0.683563232422f, 0.320465087891f,
-0.007629394531f, 0.002471923828f, 0.677734375000f, 0.327606201172f, -0.007873535156f,
0.001434326172f, 0.671844482422f, 0.334777832031f, -0.008087158203f, 0.000457763672f,
0.665832519531f, 0.341979980469f, -0.008270263672f, -0.000488281250f, 0.659729003906f,
0.349243164062f, -0.008453369141f, -0.001342773438f, 0.653533935547f, 0.356567382812f,
-0.008636474609f, -0.002166748047f, 0.647216796875f, 0.363891601562f, -0.008850097656f,
-0.002960205078f, 0.640838623047f, 0.371276855469f, -0.009033203125f, -0.003692626953f,
0.634338378906f, 0.378692626953f, -0.009216308594f, -0.004364013672f, 0.627777099609f,
0.386138916016f, -0.009338378906f, -0.004974365234f, 0.621154785156f, 0.393615722656f,
-0.009490966797f, -0.005584716797f, 0.614440917969f, 0.401092529297f, -0.009643554688f,
-0.006134033203f, 0.607635498047f, 0.408599853516f, -0.009796142578f, -0.006652832031f,
0.600769042969f, 0.416107177734f, -0.009918212891f, -0.007141113281f, 0.593841552734f,
0.423645019531f, -0.010009765625f, -0.007568359375f, 0.586853027344f, 0.431213378906f,
-0.010131835938f, -0.007965087891f, 0.579772949219f, 0.438751220703f, -0.010223388672f,
-0.008331298828f, 0.572662353516f, 0.446319580078f, -0.010284423828f, -0.008666992188f,
0.565521240234f, 0.453887939453f, -0.010345458984f, -0.008972167969f, 0.558319091797f,
0.461456298828f, -0.010406494141f, -0.009216308594f, 0.551055908203f, 0.469024658203f,
-0.010406494141f, -0.009460449219f, 0.543731689453f, 0.476593017578f, -0.010406494141f,
-0.009674072266f, 0.536407470703f, 0.484130859375f, -0.010375976562f, -0.009857177734f,
0.529022216797f, 0.491668701172f, -0.010375976562f, -0.010009765625f, 0.521606445312f,
0.499176025391f, -0.010314941406f, -0.010131835938f, 0.514160156250f, 0.506683349609f,
-0.010253906250f, -0.010253906250f, 0.506683349609f, 0.514160156250f, -0.010131835938f,
-0.010314941406f, 0.499176025391f, 0.521606445312f, -0.010009765625f, -0.010375976562f,
0.491668701172f, 0.529022216797f, -0.009857177734f, -0.010375976562f, 0.484130859375f,
0.536407470703f, -0.009674072266f, -0.010406494141f, 0.476593017578f, 0.543731689453f,
-0.009460449219f, -0.010406494141f, 0.469024658203f, 0.551055908203f, -0.009216308594f,
-0.010406494141f, 0.461456298828f, 0.558319091797f, -0.008972167969f, -0.010345458984f,
0.453887939453f, 0.565521240234f, -0.008666992188f, -0.010284423828f, 0.446319580078f,
0.572662353516f, -0.008331298828f, -0.010223388672f, 0.438751220703f, 0.579772949219f,
-0.007965087891f, -0.010131835938f, 0.431213378906f, 0.586853027344f, -0.007568359375f,
-0.010009765625f, 0.423645019531f, 0.593841552734f, -0.007141113281f, -0.009918212891f,
0.416107177734f, 0.600769042969f, -0.006652832031f, -0.009796142578f, 0.408599853516f,
0.607635498047f, -0.006134033203f, -0.009643554688f, 0.401092529297f, 0.614440917969f,
-0.005584716797f, -0.009490966797f, 0.393615722656f, 0.621154785156f, -0.004974365234f,
-0.009338378906f, 0.386138916016f, 0.627777099609f, -0.004364013672f, -0.009216308594f,
0.378692626953f, 0.634338378906f, -0.003692626953f, -0.009033203125f, 0.371276855469f,
0.640838623047f, -0.002960205078f, -0.008850097656f, 0.363891601562f, 0.647216796875f,
-0.002166748047f, -0.008636474609f, 0.356567382812f, 0.653533935547f, -0.001342773438f,
-0.008453369141f, 0.349243164062f, 0.659729003906f, -0.000488281250f, -0.008270263672f,
0.341979980469f, 0.665832519531f, 0.000457763672f, -0.008087158203f, 0.334777832031f,
0.671844482422f, 0.001434326172f, -0.007873535156f, 0.327606201172f, 0.677734375000f,
0.002471923828f, -0.007629394531f, 0.320465087891f, 0.683563232422f, 0.003570556641f,
-0.007415771484f, 0.313385009766f, 0.689270019531f, 0.004699707031f, -0.007232666016f,
0.306335449219f, 0.694854736328f, 0.005920410156f, -0.007019042969f, 0.299346923828f,
0.700317382812f, 0.007202148438f, -0.006774902344f, 0.292449951172f, 0.705657958984f,
0.008514404297f, -0.006561279297f, 0.285583496094f, 0.710906982422f, 0.009887695312f,
-0.006378173828f, 0.278778076172f, 0.716003417969f, 0.011322021484f, -0.006164550781f,
0.272033691406f, 0.721008300781f, 0.012817382812f, -0.005920410156f, 0.265350341797f,
0.725860595703f, 0.014404296875f, -0.005706787109f, 0.258728027344f, 0.730590820312f,
0.016052246094f, -0.005523681641f, 0.252197265625f, 0.735198974609f, 0.017791748047f,
-0.005310058594f, 0.245727539062f, 0.739654541016f, 0.019561767578f, -0.005065917969f,
0.239318847656f, 0.743988037109f, 0.021392822266f, -0.004852294922f, 0.233001708984f,
0.748168945312f, 0.023315429688f, -0.004669189453f, 0.226745605469f, 0.752197265625f,
0.025299072266f, -0.004455566406f, 0.220550537109f, 0.756103515625f, 0.027374267578f,
-0.004272460938f, 0.214447021484f, 0.759857177734f, 0.029510498047f, -0.004058837891f,
0.208435058594f, 0.763488769531f, 0.031738281250f, -0.003875732422f, 0.202484130859f,
0.766937255859f, 0.034027099609f, -0.003692626953f, 0.196594238281f, 0.770233154297f,
0.036407470703f, -0.003509521484f, 0.190826416016f, 0.773376464844f, 0.038879394531f,
-0.003326416016f, 0.185119628906f, 0.776367187500f, 0.041412353516f, -0.003143310547f,
0.179504394531f, 0.779205322266f, 0.044006347656f, -0.002990722656f, 0.173980712891f,
0.781890869141f, 0.046722412109f, -0.002807617188f, 0.168518066406f, 0.784423828125f,
0.049499511719f, -0.002655029297f, 0.163177490234f, 0.786743164062f, 0.052368164062f,
-0.002471923828f, 0.157897949219f, 0.788940429688f, 0.055328369141f, -0.002319335938f,
0.152709960938f, 0.790985107422f, 0.058349609375f, -0.002197265625f, 0.147613525391f,
0.792846679688f, 0.061492919922f, -0.002044677734f, 0.142608642578f, 0.794525146484f,
0.064697265625f, -0.001922607422f, 0.137695312500f, 0.796051025391f, 0.067962646484f,
-0.001770019531f, 0.132873535156f, 0.797424316406f, 0.071350097656f, -0.001647949219f,
0.128143310547f, 0.798614501953f, 0.074798583984f, -0.001525878906f, 0.123474121094f,
0.799621582031f, 0.078369140625f, -0.001403808594f, 0.118927001953f, 0.800476074219f,
0.082031250000f, -0.001281738281f, 0.114471435547f, 0.801177978516f, 0.085784912109f,
-0.001159667969f, 0.110107421875f, 0.801696777344f, 0.089599609375f, -0.001037597656f,
0.105804443359f, 0.802032470703f, 0.093505859375f, -0.000976562500f, 0.101593017578f,
0.802215576172f, 0.097503662109f,
};
const double i2fMagic = 4.503601774854144E15;
#if NONMATCHING
void do_src1(_SND_CHORUS_SRCINFO* src) {
// TODO: Match this
}
#else
/* clang-format off */
#pragma push
#pragma optimization_level 0
#pragma optimizewithasm off
asm void do_src1(_SND_CHORUS_SRCINFO* src) {
nofralloc
stwu r1, -0x40(r1)
stmw r26, 0x28(r1)
lwz r4, 0xc(r3)
lwz r5, 0x10(r3)
lwz r6, 0x14(r3)
lwz r8, 0x1c(r3)
lwz r7, 0x20(r3)
lwz r31, 4(r3)
lwz r30, 0(r3)
lwz r9, 8(r3)
lis r10, 0x4330
stw r10, 8(r1)
stw r10, 0x10(r1)
stw r10, 0x18(r1)
stw r10, 0x20(r1)
lis r10, i2fMagic@ha
lfd f9, i2fMagic@l(r10)
slwi r10, r5, 2
lwz r11, 0(r9)
lwz r29, 4(r9)
lwz r28, 8(r9)
lwzx r27, r31, r10
xoris r11, r11, 0x8000
xoris r29, r29, 0x8000
stw r11, 0xc(r1)
xoris r28, r28, 0x8000
stw r29, 0x14(r1)
xoris r27, r27, 0x8000
stw r28, 0x1c(r1)
lfd f1, 8(r1)
stw r27, 0x24(r1)
lfd f2, 0x10(r1)
fsubs f1, f1, f9
lfd f3, 0x18(r1)
fsubs f2, f2, f9
lfd f4, 0x20(r1)
fsubs f3, f3, f9
fsubs f4, f4, f9
li r26, -4
lis r12, rsmpTab12khz@ha
addi r12, r12, rsmpTab12khz@l
li r9, 0xa0
mtctr r9
lbl_803B6D5C:
rlwinm r10, r4, 7, 0x15, 0x1b
addc r4, r4, r6
add r10, r10, r12
mcrxr cr0
lfs f5, 0(r10)
beq lbl_803B6DA4
lfs f6, 4(r10)
fmuls f10, f1, f5
lfs f7, 8(r10)
fmadds f10, f2, f6, f10
lfs f8, 0xc(r10)
fmadds f10, f3, f7, f10
addi r30, r30, 4
fmadds f10, f4, f8, f10
fctiwz f10, f10
stfiwx f10, r26, r30
bdnz lbl_803B6D5C
b lbl_803B6E10
lbl_803B6DA4:
addi r5, r5, 1
lfs f6, 4(r10)
fmuls f10, f1, f5
cmpw r5, r8
fmr f1, f2
lfs f7, 8(r10)
fmadds f10, f2, f6, f10
fmr f2, f3
lfs f8, 0xc(r10)
fmadds f10, f3, f7, f10
addi r30, r30, 4
fmr f3, f4
bne+ lbl_803B6DDC
mr r5, r7
lbl_803B6DDC:
fmadds f10, f4, f8, f10
slwi r9, r5, 2
bdz lbl_803B6E08
lwzx r10, r9, r31
fctiwz f10, f10
xoris r10, r10, 0x8000
stw r10, 0xc(r1)
stfiwx f10, r26, r30
lfd f4, 8(r1)
fsubs f4, f4, f9
b lbl_803B6D5C
lbl_803B6E08:
fctiwz f10, f10
stfiwx f10, r26, r30
lbl_803B6E10:
lwz r9, 8(r3)
fctiwz f1, f1
fctiwz f2, f2
fctiwz f3, f3
stfiwx f1, r0, r9
addi r10, r9, 4
stfiwx f2, r0, r10
addi r10, r9, 8
stfiwx f3, r0, r10
stw r4, 0xc(r3)
stw r5, 0x10(r3)
lmw r26, 0x28(r1)
addi r1, r1, 0x40
blr
}
#pragma pop
/* clang-format on */
#endif
#if NONMATCHING
void do_src2(_SND_CHORUS_SRCINFO* src) {
// TODO: Match this
}
#else
/* clang-format off */
#pragma push
#pragma optimization_level 0
#pragma optimizewithasm off
asm void do_src2(_SND_CHORUS_SRCINFO* src) {
nofralloc
stwu r1, -0x40(r1)
stmw r26, 0x28(r1)
lwz r4, 0xc(r3)
lwz r5, 0x10(r3)
lwz r6, 0x14(r3)
lwz r8, 0x1c(r3)
lwz r7, 0x20(r3)
lwz r31, 4(r3)
lwz r30, 0(r3)
lwz r9, 8(r3)
lis r10, 0x4330
stw r10, 8(r1)
stw r10, 0x10(r1)
stw r10, 0x18(r1)
stw r10, 0x20(r1)
lis r10, i2fMagic@ha
lfd f9, i2fMagic@l(r10)
slwi r10, r5, 2
lwz r11, 0(r9)
lwz r29, 4(r9)
lwz r28, 8(r9)
lwzx r27, r31, r10
xoris r11, r11, 0x8000
xoris r29, r29, 0x8000
stw r11, 0xc(r1)
xoris r28, r28, 0x8000
stw r29, 0x14(r1)
xoris r27, r27, 0x8000
stw r28, 0x1c(r1)
lfd f1, 8(r1)
stw r27, 0x24(r1)
lfd f2, 0x10(r1)
fsubs f1, f1, f9
lfd f3, 0x18(r1)
fsubs f2, f2, f9
lfd f4, 0x20(r1)
fsubs f3, f3, f9
fsubs f4, f4, f9
li r26, -4
lis r12, rsmpTab12khz@ha
addi r12, r12, rsmpTab12khz@l
li r9, 0xa0
mtctr r9
lbl_803B6EF4:
rlwinm r10, r4, 7, 0x15, 0x1b
addc r4, r4, r6
add r10, r10, r12
mcrxr cr0
addi r5, r5, 1
lfs f5, 0(r10)
beq lbl_803B6F70
lfs f6, 4(r10)
fmuls f10, f1, f5
cmpw r5, r8
fmr f1, f2
lfs f7, 8(r10)
fmadds f10, f2, f6, f10
fmr f2, f3
lfs f8, 0xc(r10)
fmadds f10, f3, f7, f10
addi r30, r30, 4
fmr f3, f4
bne+ lbl_803B6F44
mr r5, r7
lbl_803B6F44:
fmadds f10, f4, f8, f10
slwi r9, r5, 2
bdz lbl_803B6FF4
lwzx r10, r9, r31
fctiwz f10, f10
xoris r10, r10, 0x8000
stw r10, 0xc(r1)
stfiwx f10, r26, r30
lfd f4, 8(r1)
fsubs f4, f4, f9
b lbl_803B6EF4
lbl_803B6F70:
cmpw r5, r8
lfs f6, 4(r10)
bne+ lbl_803B6F80
mr r5, r7
lbl_803B6F80:
slwi r11, r5, 2
addi r5, r5, 1
lwzx r29, r11, r31
fmuls f10, f1, f5
cmpw r5, r8
xoris r29, r29, 0x8000
fmr f1, f3
lfs f7, 8(r10)
stw r29, 0xc(r1)
fmadds f10, f2, f6, f10
lfs f8, 0xc(r10)
fmadds f10, f3, f7, f10
lfd f3, 8(r1)
fmr f2, f4
addi r30, r30, 4
fsubs f3, f3, f9
bne+ lbl_803B6FC8
mr r5, r7
lbl_803B6FC8:
fmadds f10, f4, f8, f10
slwi r9, r5, 2
bdz lbl_803B6FF4
lwzx r10, r9, r31
fctiwz f10, f10
xoris r10, r10, 0x8000
stw r10, 0xc(r1)
stfiwx f10, r26, r30
lfd f4, 8(r1)
fsubs f4, f4, f9
b lbl_803B6EF4
lbl_803B6FF4:
fctiwz f10, f10
stfiwx f10, r26, r30
lwz r9, 8(r3)
fctiwz f1, f1
fctiwz f2, f2
fctiwz f3, f3
stfiwx f1, r0, r9
addi r10, r9, 4
stfiwx f2, r0, r10
addi r10, r9, 8
stfiwx f3, r0, r10
stw r4, 0xc(r3)
stw r5, 0x10(r3)
lmw r26, 0x28(r1)
addi r1, r1, 0x40
blr
}
#pragma pop
/* clang-format on */
#endif
void sndAuxCallbackChorus(u8 reason, SND_AUX_INFO* info, void* user) {
SND_AUX_CHORUS* chorus;
u8 currLast;
s32* lastLeft;
s32* lastRight;
s32* lastSur;
s32* left;
s32* right;
s32* sur;
u32 i;
s32 tmp;
switch (reason) {
case SND_AUX_REASON_BUFFERUPDATE:
chorus = (SND_AUX_CHORUS*)user;
currLast = (chorus->work.currentLast + 1) % 3;
lastLeft = chorus->work.lastLeft[currLast];
lastRight = chorus->work.lastRight[currLast];
lastSur = chorus->work.lastSur[currLast];
left = info->data.bufferUpdate.left;
right = info->data.bufferUpdate.right;
sur = info->data.bufferUpdate.surround;
for (i = 0; i < 160; ++i) {
int tmp = *left;
++left;
*lastLeft = tmp;
++lastLeft;
tmp = *right;
++right;
*lastRight = tmp;
++lastRight;
tmp = *sur;
++sur;
*lastSur = tmp;
++lastSur;
}
chorus->work.src.pitchHi = (chorus->work.pitchOffset >> 0x10) + 1;
chorus->work.src.pitchLo = (chorus->work.pitchOffset << 0x10);
tmp = chorus->work.pitchOffsetPeriodCount - 1;
chorus->work.pitchOffsetPeriodCount = tmp;
if (tmp == 0) {
chorus->work.pitchOffsetPeriodCount = chorus->work.pitchOffsetPeriod;
chorus->work.pitchOffset = -chorus->work.pitchOffset;
}
for (i = 0; i < 3; ++i) {
chorus->work.src.posHi = chorus->work.currentPosHi;
chorus->work.src.posLo = chorus->work.currentPosLo;
switch (i) {
case 0:
chorus->work.src.smpBase = chorus->work.lastLeft[0];
chorus->work.src.dest = info->data.bufferUpdate.left;
chorus->work.src.old = chorus->work.oldLeft;
break;
case 1:
chorus->work.src.smpBase = chorus->work.lastRight[0];
chorus->work.src.dest = info->data.bufferUpdate.right;
chorus->work.src.old = chorus->work.oldRight;
break;
case 2:
chorus->work.src.smpBase = chorus->work.lastSur[0];
chorus->work.src.dest = info->data.bufferUpdate.surround;
chorus->work.src.old = chorus->work.oldSur;
break;
}
switch (chorus->work.src.pitchHi) {
case 0:
do_src1(&chorus->work.src);
break;
case 1:
do_src2(&chorus->work.src);
break;
}
}
chorus->work.currentPosHi = chorus->work.src.posHi % 480;
chorus->work.currentPosLo = chorus->work.src.posLo;
chorus->work.currentLast = currLast;
break;
case SND_AUX_REASON_PARAMETERUPDATE:
break;
default:
ASSERT(FALSE);
break;
}
}
bool sndAuxCallbackUpdateSettingsChorus(SND_AUX_CHORUS* ch) {
ch->work.currentPosHi = 0x140 - ((ch->baseDelay - 5) << 5);
ch->work.currentPosLo = 0;
ch->work.currentPosHi = (ch->work.currentPosHi + (ch->work.currentLast - 1) * 0xa0) % 0x1e0;
ch->work.pitchOffsetPeriod = (ch->period / 5) + 1 & ~1;
ch->work.pitchOffsetPeriodCount = (u32)ch->work.pitchOffsetPeriod >> 1;
ch->work.pitchOffset = (ch->variation << 16) / (ch->work.pitchOffsetPeriod * 5);
return TRUE;
}
bool sndAuxCallbackPrepareChorus(SND_AUX_CHORUS* chorus) {
u32 i;
bool ret;
s32* lastLeft;
s32* lastRight;
s32* lastSur;
chorus->work.lastLeft[0] = (s32*)salMalloc(0x1680);
if (chorus->work.lastLeft[0] != NULL) {
chorus->work.lastRight[0] = chorus->work.lastLeft[0] + 0x1e0;
chorus->work.lastSur[0] = chorus->work.lastRight[0] + 0x1e0;
for (i = 0; i < 3; ++i) {
chorus->work.lastLeft[i] = chorus->work.lastLeft[0] + i * 0xa0;
chorus->work.lastRight[i] = chorus->work.lastRight[0] + i * 0xa0;
chorus->work.lastSur[i] = chorus->work.lastSur[0] + i * 0xa0;
}
lastLeft = chorus->work.lastLeft[0];
lastRight = chorus->work.lastRight[0];
lastSur = chorus->work.lastSur[0];
for (i = 0; i < 0x140; i += 1) {
*lastLeft = 0;
++lastLeft;
*lastRight = 0;
++lastRight;
*lastSur = 0;
++lastSur;
}
chorus->work.currentLast = 1;
chorus->work.oldLeft[3] = 0;
chorus->work.oldLeft[2] = 0;
chorus->work.oldLeft[1] = 0;
chorus->work.oldLeft[0] = 0;
chorus->work.oldRight[3] = 0;
chorus->work.oldRight[2] = 0;
chorus->work.oldRight[1] = 0;
chorus->work.oldRight[0] = 0;
chorus->work.oldSur[3] = 0;
chorus->work.oldSur[2] = 0;
chorus->work.oldSur[1] = 0;
chorus->work.oldSur[0] = 0;
chorus->work.src.trigger = 480;
chorus->work.src.target = 0;
ret = sndAuxCallbackUpdateSettingsChorus(chorus);
} else {
ret = FALSE;
}
return ret;
}
bool sndAuxCallbackShutdownChorus(SND_AUX_CHORUS* ch) {
salFree(ch->work.lastLeft[0]);
return TRUE;
}

View File

@ -34,17 +34,17 @@ bool ReverbHICreate(_SND_REVHI_WORK* rev, f32 coloration, f32 time, f32 mix, f32
for (i = 0; i < 3; ++i) {
for (j = 0; j < 3; ++j) {
DLcreate(&rev->C[i], lens[j] + 2);
DLsetdelay(&rev->C[i], lens[j]);
DLcreate(&rev->C[j + i], lens[j] + 2);
DLsetdelay(&rev->C[j + i], lens[j]);
rev->combCoef[j + i * 3] = pow(10.f, (lens[j] * -3) / (32000.f * time));
}
for (j = 0; j < 2; ++j) {
DLcreate(&rev->AP[i], lens[j + 3] + 2);
DLsetdelay(&rev->AP[i], lens[j + 3]);
DLcreate(&rev->AP[j + i], lens[j + 3] + 2);
DLsetdelay(&rev->AP[j + i], lens[j + 3]);
}
DLcreate(&rev->AP[i], lens[i + 5] + 2);
DLsetdelay(&rev->AP[i], lens[i + 5]);
DLcreate(&rev->AP[i + 2], lens[i + 5] + 2);
DLsetdelay(&rev->AP[i + 2], lens[i + 5]);
rev->lpLastout[i] = 0.f;
}
@ -74,11 +74,32 @@ bool ReverbHICreate(_SND_REVHI_WORK* rev, f32 coloration, f32 time, f32 mix, f32
return TRUE;
}
void DoCrossTalk() {}
void HandleReverb_0() {}
static void DoCrossTalk(s32* a, s32* b, f32 start, f32 end) {}
void ReverbHICallback() {}
static void HandleReverb(s32*, SND_AUX_REVERBHI* rev, s32) {}
#pragma dont_inline on
void ReverbHICallback(s32* left, s32* right, s32* surround, SND_AUX_REVERBHI* rev) {
u8 i;
for (i = 0; i < 3; ++i) {
switch (i) {
case 0:
if (rev->rv.crosstalk != 0.f) {
DoCrossTalk(left, right, 0.5f * rev->rv.crosstalk, 1.f - (0.5f * rev->rv.crosstalk));
}
HandleReverb(left, rev, 0);
break;
case 1:
HandleReverb(right, rev, 1);
break;
case 2:
HandleReverb(surround, rev, 2);
break;
}
}
}
#pragma dont_inline reset
void ReverbHIFree(_SND_REVHI_WORK* rv) {
u8 i;

View File

@ -15,13 +15,16 @@
extern bool ReverbHICreate(_SND_REVHI_WORK* rev, f32 coloration, f32 time, f32 mix, f32 damping,
f32 preDelay, f32 crosstalk);
extern void ReverbHIFree(_SND_REVHI_WORK* rev);
extern void ReverbHIModify(_SND_REVHI_WORK* rev, f32 coloration, f32 time, f32 mix, f32 damping,
f32 preDelay, f32 crosstalk);
extern void ReverbHICallback(s32* left, s32* right, s32* surround, SND_AUX_REVERBHI* rev);
void sndAuxCallbackReverbHI(u8 reason, SND_AUX_INFO* info, void* user) {
switch (reason) {
case SND_AUX_REASON_BUFFERUPDATE:
if (((SND_AUX_REVERBHI*)user)->tempDisableFX == 0) {
ReverbHICallback(info->data.bufferUpdate.left, info->data.bufferUpdate.right,
info->data.bufferUpdate.surround, user);
info->data.bufferUpdate.surround, (SND_AUX_REVERBHI*)user);
}
case SND_AUX_REASON_PARAMETERUPDATE:
break;
@ -31,8 +34,16 @@ void sndAuxCallbackReverbHI(u8 reason, SND_AUX_INFO* info, void* user) {
}
}
bool sndAuxCallbackUpdateSettingsReverbHI(SND_AUX_REVERBHI* rev) {
rev->tempDisableFX = TRUE;
ReverbHIModify(&rev->rv, rev->coloration, rev->time, rev->mix, rev->damping, rev->preDelay,
rev->crosstalk);
rev->tempDisableFX = FALSE;
return TRUE;
}
bool sndAuxCallbackPrepareReverbHI(SND_AUX_REVERBHI* rev) {
rev->tempDisableFX = 0;
rev->tempDisableFX = FALSE;
return ReverbHICreate(&rev->rv, rev->coloration, rev->time, rev->mix, rev->damping, rev->preDelay,
rev->crosstalk);
}
@ -41,8 +52,3 @@ bool sndAuxCallbackShutdownReverbHI(SND_AUX_REVERBHI* rev) {
ReverbHIFree(&rev->rv);
return TRUE;
}
bool sndAuxCallbackUpdateSettingsReverbHI(SND_AUX_REVERBHI* rev) {
/* not in MP */
return FALSE;
}

View File

@ -1,11 +1,6 @@
#include "musyx/musyx_priv.h"
#ifdef __cplusplus
extern "C" {
#endif
/* TODO: Move these to a more approprate location */
//#define _DEBUG
#include "musyx/assert.h"
s32 DoInit(u32 rate, u32 aramSize, u8 voices, u32 flags) {
dataInitStack();
@ -54,6 +49,9 @@ void sndQuit() {
sndActive = 0;
}
#ifdef __cplusplus
void sndSetMaxVoices(u8 music, u8 sfx) {
ASSERT_MSG(music > synthInfo.voices, "Music voices are above maximum voice number.");
ASSERT_MSG(sfx > synthInfo.voices, "Sfx voices are above maximum voice number.");
synthInfo.music = music;
synthInfo.sfx = sfx;
}
#endif

View File

@ -21,4 +21,166 @@ void salCrossProduct(SND_FVECTOR* out, const SND_FVECTOR* a, const SND_FVECTOR*
out->z = (a->x * b->y) - (a->y * b->x);
}
void salInvertMatrix(SND_FMATRIX* out, const SND_FMATRIX* in) { out->t[0] = 1.f; }
#if NONMATCHING
void salInvertMatrix(SND_FMATRIX* out, const SND_FMATRIX* in) {
float fVar1;
float fVar2;
float fVar3;
float fVar4;
fVar1 = in->m[1][1] * in->m[2][2] - in->m[2][1] * in->m[1][2];
fVar4 = -(in->m[1][0] * in->m[2][2] - in->m[2][0] * in->m[1][2]);
fVar2 = in->m[1][0] * in->m[2][1] - in->m[2][0] * in->m[1][1];
fVar3 = 1.f / (in->m[0][2] * fVar2 + in->m[0][0] * fVar1 + in->m[0][1] * fVar4);
out->m[0][0] = fVar3 * fVar1;
out->m[1][0] = fVar3 * fVar4;
out->m[2][0] = fVar3 * fVar2;
out->m[0][1] = -fVar3 * (in->m[0][1] * in->m[2][2] - in->m[2][1] * in->m[0][2]);
out->m[1][1] = fVar3 * (in->m[0][0] * in->m[2][2] - in->m[2][0] * in->m[0][2]);
out->m[2][1] = -fVar3 * (in->m[0][0] * in->m[2][1] - in->m[2][0] * in->m[0][1]);
out->m[0][2] = fVar3 * (in->m[0][1] * in->m[1][2] - in->m[1][1] * in->m[0][2]);
out->m[1][2] = -fVar3 * (in->m[0][0] * in->m[1][2] - in->m[1][0] * in->m[0][2]);
out->m[2][2] = fVar3 * (in->m[0][0] * in->m[1][1] - in->m[1][0] * in->m[0][1]);
out->t[0] = (-in->t[0] * out->m[0][0] - in->t[1] * out->m[0][1]) - in->t[2] * out->m[0][2];
out->t[1] = (-in->t[0] * out->m[1][0] - in->t[1] * out->m[1][1]) - in->t[2] * out->m[1][2];
out->t[2] = (-in->t[0] * out->m[2][0] - in->t[1] * out->m[2][1]) - in->t[2] * out->m[2][2];
}
#else
/* clang-format off */
#pragma push
#pragma optimization_level 0
#pragma optimizewithasm off
const float one = 1.f;
asm void salInvertMatrix(SND_FMATRIX* out, const SND_FMATRIX* in) {
nofralloc
lfs f5, 0x20(r4)
lfs f10, 0xc(r4)
lfs f0, 0x14(r4)
lfs f6, 0x1c(r4)
fmuls f3, f10, f5
lfs f9, 0x18(r4)
lfs f8, 0x10(r4)
fmuls f4, f6, f0
fmuls f2, f9, f0
lfs f1, 0(r4)
fmuls f7, f8, f5
lfs f0, 4(r4)
fmuls f5, f10, f6
fsubs f6, f3, f2
fsubs f7, f7, f4
lfs f2, 8(r4)
fmuls f4, f9, f8
lfs f3, one
fneg f6, f6
fmuls f1, f1, f7
fsubs f4, f5, f4
fmuls f0, f0, f6
fmuls f2, f2, f4
fadds f0, f1, f0
fadds f0, f2, f0
fdivs f1, f3, f0
fmuls f0, f1, f7
fmuls f3, f1, f6
fmuls f2, f1, f4
stfs f0, 0(r3)
fneg f0, f1
stfs f3, 0xc(r3)
stfs f2, 0x18(r3)
lfs f5, 4(r4)
lfs f4, 0x20(r4)
lfs f3, 0x1c(r4)
lfs f2, 8(r4)
fmuls f4, f5, f4
fmuls f2, f3, f2
fsubs f2, f4, f2
fmuls f2, f0, f2
stfs f2, 4(r3)
lfs f5, 0(r4)
lfs f4, 0x20(r4)
lfs f3, 0x18(r4)
lfs f2, 8(r4)
fmuls f4, f5, f4
fmuls f2, f3, f2
fsubs f2, f4, f2
fmuls f2, f1, f2
stfs f2, 0x10(r3)
lfs f5, 0(r4)
lfs f4, 0x1c(r4)
lfs f3, 0x18(r4)
lfs f2, 4(r4)
fmuls f4, f5, f4
fmuls f2, f3, f2
fsubs f2, f4, f2
fmuls f2, f0, f2
stfs f2, 0x1c(r3)
lfs f5, 4(r4)
lfs f4, 0x14(r4)
lfs f3, 0x10(r4)
lfs f2, 8(r4)
fmuls f4, f5, f4
fmuls f2, f3, f2
fsubs f2, f4, f2
fmuls f2, f1, f2
stfs f2, 8(r3)
lfs f5, 0(r4)
lfs f4, 0x14(r4)
lfs f3, 0xc(r4)
lfs f2, 8(r4)
fmuls f4, f5, f4
fmuls f2, f3, f2
fsubs f2, f4, f2
fmuls f0, f0, f2
stfs f0, 0x14(r3)
lfs f4, 0(r4)
lfs f3, 0x10(r4)
lfs f2, 0xc(r4)
lfs f0, 4(r4)
fmuls f3, f4, f3
fmuls f0, f2, f0
fsubs f0, f3, f0
fmuls f0, f1, f0
stfs f0, 0x20(r3)
lfs f0, 0x24(r4)
lfs f4, 0(r3)
fneg f5, f0
lfs f3, 0x28(r4)
lfs f2, 4(r3)
lfs f1, 0x2c(r4)
lfs f0, 8(r3)
fmuls f4, f5, f4
fmuls f2, f3, f2
fmuls f0, f1, f0
fsubs f1, f4, f2
fsubs f0, f1, f0
stfs f0, 0x24(r3)
lfs f0, 0x24(r4)
lfs f4, 0xc(r3)
fneg f5, f0
lfs f3, 0x28(r4)
lfs f2, 0x10(r3)
lfs f1, 0x2c(r4)
lfs f0, 0x14(r3)
fmuls f4, f5, f4
fmuls f2, f3, f2
fmuls f0, f1, f0
fsubs f1, f4, f2
fsubs f0, f1, f0
stfs f0, 0x28(r3)
lfs f1, 0x24(r4)
lfs f0, 0x18(r3)
fneg f4, f1
lfs f3, 0x28(r4)
lfs f2, 0x1c(r3)
lfs f1, 0x2c(r4)
fmuls f4, f4, f0
lfs f0, 0x20(r3)
fmuls f2, f3, f2
fmuls f0, f1, f0
fsubs f1, f4, f2
fsubs f0, f1, f0
stfs f0, 0x2c(r3)
blr
}
#pragma pop
/* clang-format on */
#endif

50
src/musyx/snd_midictrl.c Normal file
View File

@ -0,0 +1,50 @@
#include "musyx/assert.h"
#include "musyx/musyx_priv.h"
#define SYNTH_FX_MIDISET 0xFF
u32 inpGlobalMIDIDirtyFlags[8][16];
s32 midi_ctrl;
inline bool GetGlobalFlagSet(u8 chan, u8 midiSet, s32 flag) {
return (flag & inpGlobalMIDIDirtyFlags[midiSet][chan]) != 0;
}
void inpResetGlobalMIDIDirtyFlags() {
u32 i, j;
for (i = 0; i < 8; ++i) {
for (j = 0; j < 16; ++j) {
inpGlobalMIDIDirtyFlags[i][j] = 0xFF;
}
}
}
bool inpResetGlobalMIDIDirtyFlag(u8 chan, u8 midiSet, s32 flag) {
// ASSERT(midiSet!=SYNTH_FX_MIDISET);
bool ret = GetGlobalFlagSet(chan, midiSet, flag);
if (ret) {
inpGlobalMIDIDirtyFlags[midiSet][chan] &= ~flag;
}
return ret;
}
void inpSetGlobalMIDIDirtyFlag(u8 chan, u8 midiSet, s32 flag) {
// ASSERT(midiSet!=SYNTH_FX_MIDISET);
inpGlobalMIDIDirtyFlags[midiSet][chan] |= flag;
}
void inpSetRPNHi(u8 a, u8 b, u8 c) {
}
void inpSetRPNLo(u8 a, u8 b, u8 c) {
}
void inpSetRPNDec(u8 a, u8 b) {
}
void inpSetRPNInc(u8 a, u8 b) {
}