From d04e01159d1686f90ecf99bf74a40978df4fe810 Mon Sep 17 00:00:00 2001 From: ABelliqueux Date: Thu, 28 Oct 2021 20:29:05 +0200 Subject: [PATCH] Add Hello_mod example --- common.mk | 5 + hello_mod/HIT/STAR.HIT | Bin 0 -> 157036 bytes hello_mod/Makefile | 8 + hello_mod/README.md | 6 + hello_mod/hello_mod.c | 229 +++++++++++ hello_mod/src/mod.c | 66 ++++ hello_mod/src/mod.h | 22 ++ hello_mod/src/modplayer.c | 806 ++++++++++++++++++++++++++++++++++++++ hello_mod/src/modplayer.h | 150 +++++++ 9 files changed, 1292 insertions(+) create mode 100644 hello_mod/HIT/STAR.HIT create mode 100644 hello_mod/Makefile create mode 100644 hello_mod/README.md create mode 100644 hello_mod/hello_mod.c create mode 100644 hello_mod/src/mod.c create mode 100644 hello_mod/src/mod.h create mode 100644 hello_mod/src/modplayer.c create mode 100644 hello_mod/src/modplayer.h diff --git a/common.mk b/common.mk index f7e4701..7a9aead 100644 --- a/common.mk +++ b/common.mk @@ -4,6 +4,7 @@ TYPE = ps-exe THISDIR := $(dir $(abspath $(lastword $(MAKEFILE_LIST)))) SRCS += $(THISDIR)thirdparty/nugget/common/crt0/crt0.s +SRCS += $(THISDIR)thirdparty/nugget/common/syscalls/printf.s CPPFLAGS += -I$(THISDIR)thirdparty/nugget/psyq/include -I$(THISDIR)psyq-4_7-converted/include -I$(THISDIR)psyq-4.7-converted-full/include -I$(THISDIR)psyq/include LDFLAGS += -L$(THISDIR)thirdparty/nugget/psyq/lib -L$(THISDIR)psyq-4_7-converted/lib -L$(THISDIR)psyq-4.7-converted-full/lib -L$(THISDIR)psyq/lib @@ -49,3 +50,7 @@ endef # convert VAG files to bin %.o: %.vag $(call OBJCOPYME) + +# convert HIT to bin +%.o: %.HIT + $(call OBJCOPYME) \ No newline at end of file diff --git a/hello_mod/HIT/STAR.HIT b/hello_mod/HIT/STAR.HIT new file mode 100644 index 0000000000000000000000000000000000000000..891dca8db3240e177426e875b3525aa30fb2873e GIT binary patch literal 157036 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Ð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 literal 0 HcmV?d00001 diff --git a/hello_mod/Makefile b/hello_mod/Makefile new file mode 100644 index 0000000..602b988 --- /dev/null +++ b/hello_mod/Makefile @@ -0,0 +1,8 @@ +TARGET = hello_mod + +SRCS = hello_mod.c \ +src/mod.c \ +src/modplayer.c \ +HIT/STAR.HIT \ + +include ../common.mk diff --git a/hello_mod/README.md b/hello_mod/README.md new file mode 100644 index 0000000..e76c499 --- /dev/null +++ b/hello_mod/README.md @@ -0,0 +1,6 @@ +See the **wiki** for more details on MOD usage : [https://github.com/ABelliqueux/nolibgs_hello_worlds/wiki/MOD](https://github.com/ABelliqueux/nolibgs_hello_worlds/wiki/MOD). + +## Credits + +MOD : stardust memories by Jester : https://modarchive.org/index.php?request=view_by_moduleid&query=59344 +Modplayer port by @NicolasNoble : https://github.com/grumpycoders/pcsx-redux/tree/main/src/mips/modplayer \ No newline at end of file diff --git a/hello_mod/hello_mod.c b/hello_mod/hello_mod.c new file mode 100644 index 0000000..84bc300 --- /dev/null +++ b/hello_mod/hello_mod.c @@ -0,0 +1,229 @@ +// Play a MOD file converted to HIT +// MOD Wiki page : https://github.com/ABelliqueux/nolibgs_hello_worlds/wiki/MOD +#include +#include +#include +#include +#include +#include +// Mod playback +#include "src/mod.h" + +#define VMODE 0 // Video Mode : 0 : NTSC, 1: PAL +#define SCREENXRES 320 // Screen width +#define SCREENYRES 240 // Screen height : If VMODE is 0 = 240, if VMODE is 1 = 256 +#define CENTERX SCREENXRES/2 // Center of screen on x +#define CENTERY SCREENYRES/2 // Center of screen on y +#define FONTX 960 +#define FONTY 0 +#define OTLEN 8 +DISPENV disp[2]; // Double buffered DISPENV and DRAWENV +DRAWENV draw[2]; +short db = 1; // index of which buffer is used, values 0, 1 + +// Font color +CVECTOR fntColor = { 128, 255, 0 }; +CVECTOR fntColorBG = { 0, 0, 0 }; + +// Playback state +enum PLAYBACK { + STOP = 0, + PLAY = 1, + PAUSE = 2, +}; + +enum PLAYBACK state = PLAY; + +void init(void); +void FntColor(CVECTOR fgcol, CVECTOR bgcol ); +void display(void); +void drawBG(void); +void checkPad(void); + +void FntColor(CVECTOR fgcol, CVECTOR bgcol ) +{ + // The debug font clut is at tx, ty + 128 + // tx = bg color + // tx + 1 = fg color + // We can override the color by drawing a rect at these coordinates + // + RECT fg = { FONTX+1, FONTY + 128, 1, 1 }; + RECT bg = { FONTX, FONTY + 128, 1, 1 }; + ClearImage(&fg, fgcol.r, fgcol.g, fgcol.b); + ClearImage(&bg, bgcol.r, bgcol.g, bgcol.b); +} + +void init(void) +{ + ResetCallback(); + ResetGraph(0); // Initialize drawing engine with a complete reset (0) + InitGeom(); + SetGeomOffset(CENTERX,CENTERY); + SetGeomScreen(CENTERX); + SetDefDispEnv(&disp[0], 0, 0 , SCREENXRES, SCREENYRES); // Set display area for both &disp[0] and &disp[1] + SetDefDispEnv(&disp[1], 0, SCREENYRES, SCREENXRES, SCREENYRES); // &disp[0] is on top of &disp[1] + SetDefDrawEnv(&draw[0], 0, SCREENYRES, SCREENXRES, SCREENYRES); // Set draw for both &draw[0] and &draw[1] + SetDefDrawEnv(&draw[1], 0, 0 , SCREENXRES, SCREENYRES); // &draw[0] is below &draw[1] + // Set video mode + #if VMODE + SetVideoMode(MODE_PAL); + disp[0].disp.y = 8; + disp[1].disp.y = 8; + #endif + SetDispMask(1); // Display on screen + setRGB0(&draw[0], 40, 40, 40); // set color for first draw area + setRGB0(&draw[1], 40, 40, 40); // set color for second draw area + draw[0].isbg = 1; // set mask for draw areas. 1 means repainting the area with the RGB color each frame + draw[1].isbg = 1; + PutDispEnv(&disp[db]); // set the disp and draw environnments + PutDrawEnv(&draw[db]); + FntLoad(FONTX, FONTY); // Load font to vram at 960,0(+128) + FntOpen(32, 64, 260, 120, 0, 120 ); // FntOpen(x, y, width, height, black_bg, max. nbr. chars + FntColor(fntColor, fntColorBG); +} +void display(void) +{ + DrawSync(0); // Wait for all drawing to terminate + VSync(0); // Wait for the next vertical blank + PutDispEnv(&disp[db]); // set alternate disp and draw environnments + PutDrawEnv(&draw[db]); + db = !db; +} + +void checkPad(void) +{ + u_short pad = 0; + static u_short oldPad; + pad = PadRead(0); + + // Up + if ( pad & PADLup && !(oldPad & PADLup) ) + { + MOD_PlayNote(11, 25, 15, 63); + oldPad = pad; + } + if ( !(pad & PADLup) && oldPad & PADLup ) + { + oldPad = pad; + } + // Down + if ( pad & PADLdown && !(oldPad & PADLdown) ) + { + MOD_PlayNote(12, 26, 15, 63); + oldPad = pad; + } + if ( !(pad & PADLdown) && oldPad & PADLdown ) + { + oldPad = pad; + } + // Left + if ( pad & PADLleft && !(oldPad & PADLleft) ) + { + MOD_PlayNote(13, 27, 15, 63); + oldPad = pad; + } + if ( !(pad & PADLleft) && oldPad & PADLleft ) + { + oldPad = pad; + } + // Right + if ( pad & PADLright && !(oldPad & PADLright) ) + { + // Channel 1 is transition anim, only take input when !transition + MOD_PlayNote(6, 21, 15, 63); + oldPad = pad; + } + if ( !(pad & PADLright) && oldPad & PADLright ) + { + oldPad = pad; + } + // Cross button + if ( pad & PADRdown && !(oldPad & PADRdown) ) + { + // Select sound + MOD_PlayNote(7, 22, 15, 63); + oldPad = pad; + } + if ( !(pad & PADRdown) && oldPad & PADRdown ) + { + oldPad = pad; + } + // Square button + if ( pad & PADRleft && !(oldPad & PADRleft) ) + { + // Select sound + MOD_PlayNote(8, 23, 15, 63); + oldPad = pad; + } + if ( !(pad & PADRleft) && oldPad & PADRleft ) + { + oldPad = pad; + } + // Circle button + if ( pad & PADRright && !(oldPad & PADRright) ) + { + // Select sound + MOD_PlayNote(9, 28, 15, 63); + oldPad = pad; + } + if ( !(pad & PADRright) && oldPad & PADRright ) + { + oldPad = pad; + } + // Circle button + if ( pad & PADRup && !(oldPad & PADRup) ) + { + // Select sound + MOD_PlayNote(9, 24, 15, 63); + oldPad = pad; + } + if ( !(pad & PADRup) && oldPad & PADRup ) + { + oldPad = pad; + } + // Select button + if ( pad & PADselect && !(oldPad & PADselect) ) + { + if ( state == PLAY ) { stopMusic(); state = STOP; } + else if ( state == STOP ) { startMusic(); state = PLAY; } + oldPad = pad; + } + if ( !(pad & PADselect) && oldPad & PADselect ) + { + oldPad = pad; + } + // Start button + if ( pad & PADstart && !(oldPad & PADstart) ) + { + if ( state == PLAY ) { pauseMusic(); state = PAUSE; } + else if ( state == PAUSE ) { resumeMusic(); state = PLAY; } + oldPad = pad; + } + if ( !(pad & PADstart) && oldPad & PADstart ) + { + oldPad = pad; + } + +} +int main() { + u_int t = 0; + init(); + PadInit(0); + VSyncCallback(checkPad); + // Mod Playback + loadMod(); + startMusic(); + // Main loop + while (1) + { + // TODO: change volume, restart playback + t++; + FntPrint("Hello mod ! %d\nUse pad buttons to play sounds.\n", t); + FntPrint("State: %d\n", state); + FntPrint("Start : play/pause music.\n"); + FntFlush(-1); + display(); + } + return 0; +} + diff --git a/hello_mod/src/mod.c b/hello_mod/src/mod.c new file mode 100644 index 0000000..9ace81a --- /dev/null +++ b/hello_mod/src/mod.c @@ -0,0 +1,66 @@ +#include "mod.h" + +long musicEvent; +typedef struct SpuVoiceVolume { + short volL, volR; +} SpuVoiceVolume; + +SpuVoiceVolume volumeState[24] = {0}; + +void muteSPUvoices() { + for (unsigned i = 0; i < 24; i++) { + // Store current volume + SpuGetVoiceVolume(i, &(volumeState[i].volL), &(volumeState[i].volR) ); + // Mute + SpuSetVoiceVolume(i, 0, 0); + } +} + +void restoreSPUvoices() { + for (unsigned i = 0; i < 24; i++) { + // Restore volume + SpuSetVoiceVolume(i, volumeState[i].volL, volumeState[i].volR ); + } +} + +// Playing a sound effect (aka mod note): https://discord.com/channels/642647820683444236/642848592754901033/898249196174458900 +// Code by NicolasNoble : https://discord.com/channels/642647820683444236/663664210525290507/902624952715452436 +void loadMod() { + printf("Loading MOD:\'%s\'\n", HITFILE); + MOD_Load((struct MODFileFormat*)HITFILE); + printf("%02d Channels, %02d Orders\n", MOD_Channels, MOD_SongLength); +} + +void startMusic() { + ResetRCnt(RCntCNT1); + SetRCnt(RCntCNT1, MOD_hblanks, RCntMdINTR); + StartRCnt(RCntCNT1); + musicEvent = OpenEvent(RCntCNT1, EvSpINT, EvMdINTR, processMusic); + EnableEvent(musicEvent); + restoreSPUvoices(); +} + +long processMusic() { + uint32_t old_hblanks = MOD_hblanks; + MOD_Poll(); + uint32_t new_hblanks = MOD_hblanks; + if (old_hblanks != new_hblanks) SetRCnt(RCntCNT1, new_hblanks, RCntMdINTR); + return MOD_hblanks; +} + +void pauseMusic() { + muteSPUvoices(); + DisableEvent(musicEvent); +} + +void resumeMusic() { + restoreSPUvoices(); + EnableEvent(musicEvent); +} + +void stopMusic() { + MOD_Silence(); + StopRCnt(RCntCNT1); + DisableEvent(musicEvent); + CloseEvent(musicEvent); +} diff --git a/hello_mod/src/mod.h b/hello_mod/src/mod.h new file mode 100644 index 0000000..e614f00 --- /dev/null +++ b/hello_mod/src/mod.h @@ -0,0 +1,22 @@ +#pragma once +#include +#include +#include "../../thirdparty/nugget/common/hardware/hwregs.h" +#include "../../thirdparty/nugget/common/hardware/irq.h" +#include "../../thirdparty/nugget/common/syscalls/syscalls.h" +#define printf ramsyscall_printf + +// Mod Playback +#include "modplayer.h" +extern const uint8_t _binary_HIT_STAR_HIT_start[]; +#define HITFILE _binary_HIT_STAR_HIT_start +extern long musicEvent; + +void muteSPUvoices(); +void restoreSPUvoices(); +void loadMod(); +long processMusic(); +void startMusic(); +void pauseMusic(); +void resumeMusic(); +void stopMusic(); \ No newline at end of file diff --git a/hello_mod/src/modplayer.c b/hello_mod/src/modplayer.c new file mode 100644 index 0000000..c30efed --- /dev/null +++ b/hello_mod/src/modplayer.c @@ -0,0 +1,806 @@ +/* + +MIT License + +Copyright (c) 2021 PCSX-Redux authors + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. + +*/ + +#include "modplayer.h" + +#include +#include + +#include "../../thirdparty/nugget/common/hardware/dma.h" +#include "../../thirdparty/nugget/common/hardware/spu.h" +#include "../../thirdparty/nugget/common/syscalls/syscalls.h" + +/* This code is a reverse engineering of the file MODPLAY.BIN, located in the zip file + "Asm-Mod" from http://hitmen.c02.at/html/psx_tools.html, that has the CRC32 bb91769f. */ + +struct MODSampleData { + char name[22]; + union { + uint16_t length; + uint8_t lenarr[2]; + }; + uint8_t finetune; + uint8_t volume; + uint16_t repeatLocation; + uint16_t repeatLength; +}; + +struct MODFileFormat { + char title[20]; + struct MODSampleData samples[31]; + uint8_t songLength; + uint8_t padding; + uint8_t patternTable[128]; + uint8_t signature[4]; +}; + +struct SPUChannelData { + uint16_t note; + int16_t period; + uint16_t slideTo; + uint8_t slideSpeed; + uint8_t volume; + uint8_t sampleID; + int8_t vibrato; + uint8_t fx[4]; + uint16_t samplePos; +}; + +struct SpuInstrumentData { + uint16_t baseAddress; + uint8_t finetune; + uint8_t volume; +}; + +static struct SpuInstrumentData s_spuInstrumentData[31]; + +static void SPUInit() { + DPCR |= 0x000b0000; + SPU_VOL_MAIN_LEFT = 0x3800; + SPU_VOL_MAIN_RIGHT = 0x3800; + SPU_CTRL = 0; + SPU_KEY_ON_LOW = 0; + SPU_KEY_ON_HIGH = 0; + SPU_KEY_OFF_LOW = 0xffff; + SPU_KEY_OFF_HIGH = 0xffff; + SPU_RAM_DTC = 4; + SPU_VOL_CD_LEFT = 0; + SPU_VOL_CD_RIGHT = 0; + SPU_PITCH_MOD_LOW = 0; + SPU_PITCH_MOD_HIGH = 0; + SPU_NOISE_EN_LOW = 0; + SPU_NOISE_EN_HIGH = 0; + SPU_REVERB_EN_LOW = 0; + SPU_REVERB_EN_HIGH = 0; + SPU_VOL_EXT_LEFT = 0; + SPU_VOL_EXT_RIGHT = 0; + SPU_CTRL = 0x8000; +} + +static void SPUResetVoice(int voiceID) { + SPU_VOICES[voiceID].volumeLeft = 0; + SPU_VOICES[voiceID].volumeRight = 0; + SPU_VOICES[voiceID].sampleRate = 0; + SPU_VOICES[voiceID].sampleStartAddr = 0; + SPU_VOICES[voiceID].ad = 0x000f; + SPU_VOICES[voiceID].currentVolume = 0; + SPU_VOICES[voiceID].sampleRepeatAddr = 0; + SPU_VOICES[voiceID].sr = 0x0000; +} + +static void SPUUploadInstruments(uint32_t SpuAddr, const uint8_t* data, uint32_t size) { + uint32_t bcr = size >> 6; + if (size & 0x3f) bcr++; + bcr <<= 16; + bcr |= 0x10; + + SPU_RAM_DTA = SpuAddr >> 3; + SPU_CTRL = (SPU_CTRL & ~0x0030) | 0x0020; + while ((SPU_CTRL & 0x0030) != 0x0020) + ; + // original code erroneously was doing SBUS_DEV4_CTRL = SBUS_DEV4_CTRL; + SBUS_DEV4_CTRL &= ~0x0f000000; + DMA_CTRL[DMA_SPU].MADR = (uint32_t)data; + DMA_CTRL[DMA_SPU].BCR = bcr; + DMA_CTRL[DMA_SPU].CHCR = 0x01000201; + + while ((DMA_CTRL[DMA_SPU].CHCR & 0x01000000) != 0) + ; +} + +static void SPUUnMute() { SPU_CTRL = 0xc000; } + +static void SPUSetVoiceVolume(int voiceID, uint16_t left, uint16_t right) { + SPU_VOICES[voiceID].volumeLeft = left >> 2; + SPU_VOICES[voiceID].volumeRight = right >> 2; +} + +static void SPUSetStartAddress(int voiceID, uint32_t spuAddr) { SPU_VOICES[voiceID].sampleStartAddr = spuAddr >> 3; } + +static void SPUWaitIdle() { + do { + for (unsigned c = 0; c < 2045; c++) __asm__ volatile(""); + } while ((SPU_STATUS & 0x07ff) != 0); +} + +static void SPUKeyOn(uint32_t voiceBits) { + SPU_KEY_ON_LOW = voiceBits; + SPU_KEY_ON_HIGH = voiceBits >> 16; +} + +static void SPUSetVoiceSampleRate(int voiceID, uint16_t sampleRate) { SPU_VOICES[voiceID].sampleRate = sampleRate; } + +unsigned MOD_Check(const struct MODFileFormat* module) { + if (syscall_strncmp(module->signature, "HIT", 3) == 0) { + return module->signature[3] - '0'; + } else if (syscall_strncmp(module->signature, "HM", 2) == 0) { + return ((module->signature[2] - '0') * 10) + module->signature[3] - '0'; + } + return 0; +} + +unsigned MOD_Channels = 0; +unsigned MOD_SongLength = 0; +// original code keeps this one to the very beginning of the file, +// while this code keeps the pointer to the beginning of the order table +static const uint8_t* MOD_ModuleData = NULL; +unsigned MOD_CurrentOrder = 0; +unsigned MOD_CurrentPattern = 0; +unsigned MOD_CurrentRow = 0; +unsigned MOD_Speed = 0; +unsigned MOD_Tick = 0; +// this never seems to be updated in the original code, which is a +// mistake; the F command handler was all wrong +unsigned MOD_BPM = 0; +// original code keeps this one to the NEXT row, +// while this code keeps the pointer to the CURRENT row +const uint8_t* MOD_RowPointer = NULL; +int MOD_ChangeRowNextTick = 0; +unsigned MOD_NextRow = 0; +int MOD_ChangeOrderNextTick = 0; +unsigned MOD_NextOrder = 0; +uint8_t MOD_PatternDelay = 0; +unsigned MOD_LoopStart = 0; +unsigned MOD_LoopCount = 0; +int MOD_Stereo = 0; +uint32_t MOD_hblanks; + +// This function is now more of a helper to calculate the number of hsync +// values to wait until the next call to MOD_Poll. If the user wants to use +// another method, they will have to inspect MOD_BPM manually and make their +// own math based on their own timer. +static void MOD_SetBPM(unsigned bpm) { + MOD_BPM = bpm; + // The original code only uses 39000 here but the reality is a bit more + // complex than that, as not all clocks are exactly the same, depending + // on the machine's region, and the video mode selected. + + uint32_t status = GPU_STATUS; + int isPalConsole = *((const char*)0xbfc7ff52) == 'E'; + int isPal = (status & 0x00100000) != 0; + uint32_t base; + if (isPal && isPalConsole) { // PAL video on PAL console + base = 39062; // 312.5 * 125 * 50.000 / 50 or 314 * 125 * 49.761 / 50 + } else if (isPal && !isPalConsole) { // PAL video on NTSC console + base = 39422; // 312.5 * 125 * 50.460 / 50 or 314 * 125 * 50.219 / 50 + } else if (!isPal && isPalConsole) { // NTSC video on PAL console + base = 38977; // 262.5 * 125 * 59.393 / 50 or 263 * 125 * 59.280 / 50 + } else { // NTSC video on NTSC console + base = 39336; // 262.5 * 125 * 59.940 / 50 or 263 * 125 * 59.826 / 50 + } + MOD_hblanks = base / bpm; +} + +static struct SPUChannelData s_channelData[24]; + +uint32_t MOD_Load(const struct MODFileFormat* module) { + SPUInit(); + MOD_Channels = MOD_Check(module); + + if (MOD_Channels == 0) return 0; + + uint32_t currentSpuAddress = 0x1010; + for (unsigned i = 0; i < 31; i++) { + s_spuInstrumentData[i].baseAddress = currentSpuAddress >> 4; + s_spuInstrumentData[i].finetune = module->samples[i].finetune; + s_spuInstrumentData[i].volume = module->samples[i].volume; + currentSpuAddress += module->samples[i].lenarr[0] * 0x100 + module->samples[i].lenarr[1]; + } + + MOD_SongLength = module->songLength; + + unsigned maxPatternID = 0; + for (unsigned i = 0; i < 128; i++) { + if (maxPatternID < module->patternTable[i]) maxPatternID = module->patternTable[i]; + } + + MOD_ModuleData = (const uint8_t*)&module->patternTable[0]; + + SPUUploadInstruments(0x1010, MOD_ModuleData + 4 + 128 + MOD_Channels * 0x100 * (maxPatternID + 1), + currentSpuAddress - 0x1010); + + MOD_CurrentOrder = 0; + MOD_CurrentPattern = module->patternTable[0]; + MOD_CurrentRow = 0; + MOD_Speed = 6; + MOD_Tick = 6; + MOD_RowPointer = MOD_ModuleData + 4 + 128 + MOD_CurrentPattern * MOD_Channels * 0x100; + // original code goes only up to MOD_Channels; let's reset all 24 + for (unsigned i = 0; i < 24; i++) SPUResetVoice(i); + MOD_ChangeRowNextTick = 0; + MOD_ChangeOrderNextTick = 0; + MOD_LoopStart = 0; + MOD_LoopCount = 0; + + // these two are erroneously missing from the original code, at + // least for being able to play more than one music + MOD_PatternDelay = 0; + syscall_memset(s_channelData, 0, sizeof(s_channelData)); + + SPUUnMute(); + + // this one is also missing, and is necessary, for being able to call MOD_Load + // after another song that changed the tempo previously + MOD_SetBPM(125); + + // the original code would do: + // return MOD_Channels; + // but we are returning the size for the MOD_Relocate call + return 4 + 128 + MOD_Channels * 0x100 * (maxPatternID + 1); +} + +void MOD_Silence() { + SPUInit(); + for (unsigned i = 0; i < 24; i++) { + SPUResetVoice(i); + } +} + +void MOD_Relocate(uint8_t* s1) { + if (MOD_ModuleData == s1) return; + unsigned maxPatternID = 0; + for (unsigned i = 0; i < 128; i++) { + if (maxPatternID < MOD_ModuleData[i]) maxPatternID = MOD_ModuleData[i]; + } + + size_t n = 4 + 128 + MOD_Channels * 0x100 * (maxPatternID + 1); + + const uint8_t* s2 = MOD_ModuleData; + size_t i; + + if (s1 < s2) { + for (i = 0; i < n; i++) *s1++ = *s2++; + } else if (s1 > s2) { + s1 += n; + s2 += n; + for (i = 0; i < n; i++) *--s1 = *--s2; + } + + MOD_ModuleData = s1; +} + +static const uint8_t MOD_SineTable[32] = { + 0x00, 0x18, 0x31, 0x4a, 0x61, 0x78, 0x8d, 0xa1, 0xb4, 0xc5, 0xd4, 0xe0, 0xeb, 0xf4, 0xfa, 0xfd, + 0xff, 0xfd, 0xfa, 0xf4, 0xeb, 0xe0, 0xd4, 0xc5, 0xb4, 0xa1, 0x8d, 0x78, 0x61, 0x4a, 0x31, 0x18, +}; + +// C C# D D# E F F# G G# A A# B +const uint16_t MOD_PeriodTable[36 * 16] = { + 856, 808, 762, 720, 678, 640, 604, 570, 538, 508, 480, 453, // octave 1 tune 0 + 428, 404, 381, 360, 339, 320, 302, 285, 269, 254, 240, 226, // octave 2 tune 0 + 214, 202, 190, 180, 170, 160, 151, 143, 135, 127, 120, 113, // octave 3 tune 0 + 850, 802, 757, 715, 674, 637, 601, 567, 535, 505, 477, 450, // octave 1 tune 1 + 425, 401, 379, 357, 337, 318, 300, 284, 268, 253, 239, 225, // octave 2 tune 1 + 213, 201, 189, 179, 169, 159, 150, 142, 134, 126, 119, 113, // octave 3 tune 1 + 844, 796, 752, 709, 670, 632, 597, 563, 532, 502, 474, 447, // octave 1 tune 2 + 422, 398, 376, 355, 335, 316, 298, 282, 266, 251, 237, 224, // octave 2 tune 2 + 211, 199, 188, 177, 167, 158, 149, 141, 133, 125, 118, 112, // octave 3 tune 2 + 838, 791, 746, 704, 665, 628, 592, 559, 528, 498, 470, 444, // octave 1 tune 3 + 419, 395, 373, 352, 332, 314, 296, 280, 264, 249, 235, 222, // octave 2 tune 3 + 209, 198, 187, 176, 166, 157, 148, 140, 132, 125, 118, 111, // octave 3 tune 3 + 832, 785, 741, 699, 660, 623, 588, 555, 524, 495, 467, 441, // octave 1 tune 4 + 416, 392, 370, 350, 330, 312, 294, 278, 262, 247, 233, 220, // octave 2 tune 4 + 208, 196, 185, 175, 165, 156, 147, 139, 131, 124, 117, 110, // octave 3 tune 4 + 826, 779, 736, 694, 655, 619, 584, 551, 520, 491, 463, 437, // octave 1 tune 5 + 413, 390, 368, 347, 328, 309, 292, 276, 260, 245, 232, 219, // octave 2 tune 5 + 206, 195, 184, 174, 164, 155, 146, 138, 130, 123, 116, 109, // octave 3 tune 5 + 820, 774, 730, 689, 651, 614, 580, 547, 516, 487, 460, 434, // octave 1 tune 6 + 410, 387, 365, 345, 325, 307, 290, 274, 258, 244, 230, 217, // octave 2 tune 6 + 205, 193, 183, 172, 163, 154, 145, 137, 129, 122, 115, 109, // octave 3 tune 6 + 814, 768, 725, 684, 646, 610, 575, 543, 513, 484, 457, 431, // octave 1 tune 7 + 407, 384, 363, 342, 323, 305, 288, 272, 256, 242, 228, 216, // octave 2 tune 7 + 204, 192, 181, 171, 161, 152, 144, 136, 128, 121, 114, 108, // octave 3 tune 7 + 907, 856, 808, 762, 720, 678, 640, 604, 570, 538, 508, 480, // octave 1 tune -8 + 453, 428, 404, 381, 360, 339, 320, 302, 285, 269, 254, 240, // octave 2 tune -8 + 226, 214, 202, 190, 180, 170, 160, 151, 143, 135, 127, 120, // octave 3 tune -8 + 900, 850, 802, 757, 715, 675, 636, 601, 567, 535, 505, 477, // octave 1 tune -7 + 450, 425, 401, 379, 357, 337, 318, 300, 284, 268, 253, 238, // octave 2 tune -7 + 225, 212, 200, 189, 179, 169, 159, 150, 142, 134, 126, 119, // octave 3 tune -7 + 894, 844, 796, 752, 709, 670, 632, 597, 563, 532, 502, 474, // octave 1 tune -6 + 447, 422, 398, 376, 355, 335, 316, 298, 282, 266, 251, 237, // octave 2 tune -6 + 223, 211, 199, 188, 177, 167, 158, 149, 141, 133, 125, 118, // octave 3 tune -6 + 887, 838, 791, 746, 704, 665, 628, 592, 559, 528, 498, 470, // octave 1 tune -5 + 444, 419, 395, 373, 352, 332, 314, 296, 280, 264, 249, 235, // octave 2 tune -5 + 222, 209, 198, 187, 176, 166, 157, 148, 140, 132, 125, 118, // octave 3 tune -5 + 881, 832, 785, 741, 699, 660, 623, 588, 555, 524, 494, 467, // octave 1 tune -4 + 441, 416, 392, 370, 350, 330, 312, 294, 278, 262, 247, 233, // octave 2 tune -4 + 220, 208, 196, 185, 175, 165, 156, 147, 139, 131, 123, 117, // octave 3 tune -4 + 875, 826, 779, 736, 694, 655, 619, 584, 551, 520, 491, 463, // octave 1 tune -3 + 437, 413, 390, 368, 347, 328, 309, 292, 276, 260, 245, 232, // octave 2 tune -3 + 219, 206, 195, 184, 174, 164, 155, 146, 138, 130, 123, 116, // octave 3 tune -3 + 868, 820, 774, 730, 689, 651, 614, 580, 547, 516, 487, 460, // octave 1 tune -2 + 434, 410, 387, 365, 345, 325, 307, 290, 274, 258, 244, 230, // octave 2 tune -2 + 217, 205, 193, 183, 172, 163, 154, 145, 137, 129, 122, 115, // octave 3 tune -2 + 862, 814, 768, 725, 684, 646, 610, 575, 543, 513, 484, 457, // octave 1 tune -1 + 431, 407, 384, 363, 342, 323, 305, 288, 272, 256, 242, 228, // octave 2 tune -1 + 216, 203, 192, 181, 171, 161, 152, 144, 136, 128, 121, 114, // octave 3 tune -1 +}; + +#define SETVOICESAMPLERATE(channel, newPeriod) \ + SPUSetVoiceSampleRate(channel, ((7093789 / (newPeriod * 2)) << 12) / 44100) +#define SETVOICEVOLUME(channel, volume) \ + volume <<= 8; \ + if (MOD_Stereo) { \ + int pan = (channel & 1) ^ (channel >> 1); \ + int16_t left = pan == 0 ? volume : 0; \ + int16_t right = pan == 0 ? 0 : volume; \ + SPUSetVoiceVolume(channel, left, right); \ + } else { \ + SPUSetVoiceVolume(channel, volume, volume); \ + } + +static void MOD_UpdateEffect() { + const uint8_t* rowPointer = MOD_RowPointer; + const unsigned channels = MOD_Channels; + for (unsigned channel = 0; channel < channels; channel++) { + uint8_t effectNibble23 = rowPointer[3]; + uint8_t effectNibble1 = rowPointer[2] & 0x0f; + uint8_t effectNibble2 = effectNibble23 & 0x0f; + uint8_t effectNibble3 = effectNibble23 >> 4; + + uint8_t arpeggioTick; + int32_t newPeriod; + int16_t volume; + uint16_t slideTo; + uint8_t fx; + uint32_t mutation; + int8_t newValue; + + struct SPUChannelData* const channelData = &s_channelData[channel]; + + switch (effectNibble1) { + case 0: // arpeggio + if (effectNibble23 == 0) break; + arpeggioTick = MOD_Tick; + arpeggioTick %= 3; + switch (arpeggioTick) { + case 0: + newPeriod = channelData->period; + break; + case 1: + newPeriod = MOD_PeriodTable[channelData->note + effectNibble3]; + break; + case 2: + newPeriod = MOD_PeriodTable[channelData->note + effectNibble2]; + break; + } + SETVOICESAMPLERATE(channel, newPeriod); + break; + case 1: // portamento up + newPeriod = channelData->period; + newPeriod -= effectNibble23; + if (newPeriod < 108) newPeriod = 108; + channelData->period = newPeriod; + SETVOICESAMPLERATE(channel, newPeriod); + break; + case 2: // portamento down + newPeriod = channelData->period; + newPeriod += effectNibble23; + if (newPeriod > 907) newPeriod = 907; + channelData->period = newPeriod; + SETVOICESAMPLERATE(channel, newPeriod); + break; + case 5: + volume = channelData->volume; + if (effectNibble23 <= 0x10) { + volume -= effectNibble23; + if (volume < 0) volume = 0; + } else { + volume += effectNibble3; + if (volume > 63) volume = 63; + } + channelData->volume = volume; + SETVOICEVOLUME(channel, volume); + /* fall through */ + case 3: // glissando + newPeriod = channelData->period; + slideTo = channelData->slideTo; + if (newPeriod < slideTo) { + newPeriod += channelData->slideSpeed; + if (newPeriod > slideTo) newPeriod = slideTo; + } else if (newPeriod > slideTo) { + newPeriod -= channelData->slideSpeed; + if (newPeriod < slideTo) newPeriod = slideTo; + } + channelData->period = newPeriod; + SETVOICESAMPLERATE(channel, newPeriod); + break; + case 6: + volume = channelData->volume; + if (effectNibble23 <= 0x10) { + volume -= effectNibble23; + if (volume < 0) volume = 0; + } else { + volume += effectNibble3; + if (volume > 63) volume = 63; + } + channelData->volume = volume; + SETVOICEVOLUME(channel, volume); + /* fall through */ + case 4: // vibrato + mutation = channelData->vibrato & 0x1f; + switch (channelData->fx[3] & 3) { + case 0: + case 3: // 3 is technically random + mutation = MOD_SineTable[mutation]; + break; + case 1: + if (channelData->vibrato < 0) { + mutation *= -8; + mutation += 0xff; + } else { + mutation *= 8; + } + break; + case 2: + mutation = 0xff; + break; + } + mutation *= channelData->fx[1] >> 4; + mutation >>= 7; + newPeriod = channelData->period; + if (channelData->vibrato < 0) { + newPeriod -= mutation; + } else { + newPeriod += mutation; + } + newValue = channelData->vibrato; + newValue += channelData->fx[1] & 0x0f; + if (newValue >= 32) newValue -= 64; + channelData->vibrato = newValue; + SETVOICESAMPLERATE(channel, newPeriod); + break; + case 7: // tremolo + mutation = s_channelData[0].fx[0] & 0x1f; + switch (s_channelData[0].fx[3] & 3) { + case 0: + case 3: // 3 is technically random + mutation = MOD_SineTable[mutation]; + break; + case 1: + if (channelData->fx[0] & 0x80) { + mutation *= -8; + mutation += 0xff; + } else { + mutation *= 8; + } + break; + case 2: + mutation = 0xff; + break; + } + mutation *= channelData->fx[3] >> 4; + mutation >>= 6; + volume = channelData->volume; + if (channelData->fx[0] & 0x80) { + volume -= mutation; + } else { + volume += mutation; + } + newValue = channelData->fx[0] + (channelData->fx[2] & 0x0f); + if (newValue >= 32) newValue -= 64; + channelData->fx[0] = newValue; + if (volume > 63) volume = 63; + SETVOICEVOLUME(channel, volume); + break; + case 10: // volume slide + volume = channelData->volume; + if (effectNibble23 <= 0x10) { + volume -= effectNibble23; + if (volume < 0) volume = 0; + } else { + volume += effectNibble3; + if (volume > 63) volume = 63; + } + channelData->volume = volume; + SETVOICEVOLUME(channel, volume); + break; + case 14: // extended + switch (effectNibble3) { + case 9: // retrigger sample + // this doesn't look right, we probably want to reset the sample location + if ((MOD_Tick % effectNibble2) == 0) SPUKeyOn(1 << channel); + break; + case 12: // cut sample + if (MOD_Tick != effectNibble2) break; + channelData->volume = 0; + SPUSetVoiceVolume(channel, 0, 0); + } + break; + } + + rowPointer += 4; + } +} + +static void MOD_UpdateRow() { + const unsigned channels = MOD_Channels; + if (MOD_ChangeOrderNextTick) { + unsigned newOrder = MOD_NextOrder; + if (newOrder >= MOD_SongLength) newOrder = 0; + MOD_CurrentRow = 0; + MOD_CurrentOrder = newOrder; + MOD_CurrentPattern = MOD_ModuleData[newOrder]; + } + if (MOD_ChangeRowNextTick) { + unsigned newRow = (MOD_NextRow >> 4) * 10 + (MOD_NextRow & 0x0f); + if (newRow >= 64) newRow = 0; + MOD_CurrentRow = newRow; + if (MOD_ChangeOrderNextTick) { + if (++MOD_CurrentOrder >= MOD_SongLength) MOD_CurrentOrder = 0; + MOD_CurrentPattern = MOD_ModuleData[MOD_CurrentOrder]; + } + } + MOD_ChangeRowNextTick = 0; + MOD_ChangeOrderNextTick = 0; + MOD_RowPointer = + MOD_ModuleData + 128 + 4 + MOD_CurrentPattern * MOD_Channels * 0x100 + MOD_CurrentRow * channels * 4; + const uint8_t* rowPointer = MOD_RowPointer; + + for (unsigned channel = 0; channel < channels; channel++) { + int16_t volume; + struct SPUChannelData* const channelData = &s_channelData[channel]; + + uint8_t effectNibble1 = rowPointer[2]; + uint8_t effectNibble23 = rowPointer[3]; + uint16_t nibble0 = rowPointer[0]; + unsigned sampleID = (nibble0 & 0xf0) | (effectNibble1 >> 4); + uint8_t effectNibble2 = effectNibble23 & 0x0f; + uint8_t effectNibble3 = effectNibble23 >> 4; + unsigned period = ((nibble0 & 0x0f) << 8) | rowPointer[1]; + int32_t newPeriod; + uint8_t fx; + effectNibble1 &= 0x0f; + + if (effectNibble1 != 9) channelData->samplePos = 0; + if (sampleID != 0) { + channelData->sampleID = --sampleID; + volume = s_spuInstrumentData[sampleID].volume; + if (volume > 63) volume = 63; + channelData->volume = volume; + if (effectNibble1 != 7) { + SETVOICEVOLUME(channel, volume); + } + SPUSetStartAddress(channel, s_spuInstrumentData[sampleID].baseAddress << 4 + channelData->samplePos); + } + + if (period != 0) { + int periodIndex; + // original code erroneously does >= 0 + for (periodIndex = 35; periodIndex--; periodIndex > 0) { + if (MOD_PeriodTable[periodIndex] == period) break; + } + channelData->note = periodIndex + s_spuInstrumentData[channelData->sampleID].finetune * 36; + fx = channelData->fx[3]; + if ((fx & 0x0f) < 4) { + channelData->vibrato = 0; + } + if ((fx >> 4) < 4) { + channelData->fx[0] = 0; + } + if ((effectNibble1 != 3) && (effectNibble1 != 5)) { + SPUWaitIdle(); + SPUKeyOn(1 << channel); + channelData->period = MOD_PeriodTable[channelData->note]; + } + newPeriod = channelData->period; + SETVOICESAMPLERATE(channel, newPeriod); + } + + switch (effectNibble1) { + case 3: // glissando + if (effectNibble23 != 0) { + channelData->slideSpeed = effectNibble23; + } + if (period != 0) { + channelData->slideTo = MOD_PeriodTable[channelData->note]; + } + break; + case 4: // vibrato + if (effectNibble3 != 0) { + fx = channelData->fx[1]; + fx &= ~0x0f; + fx |= effectNibble3; + channelData->fx[1] = fx; + } + if (effectNibble2 != 0) { + fx = channelData->fx[1]; + fx &= ~0xf0; + fx |= effectNibble3 << 4; + channelData->fx[1] = fx; + } + break; + case 7: // tremolo + if (effectNibble3 != 0) { + fx = channelData->fx[2]; + fx &= ~0x0f; + fx |= effectNibble3; + channelData->fx[2] = fx; + } + if (effectNibble2 != 0) { + fx = channelData->fx[2]; + fx &= ~0xf0; + fx |= effectNibble2 << 4; + channelData->fx[2] = fx; + } + break; + case 9: // sample jump + if (effectNibble23 != 0) { + uint16_t newSamplePos = effectNibble23; + channelData->samplePos = newSamplePos << 7; + } + break; + case 11: // order jump + if (!MOD_ChangeOrderNextTick) { + MOD_ChangeOrderNextTick = 1; + MOD_NextOrder = effectNibble23; + } + break; + case 12: // set volume + volume = effectNibble23; + if (volume > 64) volume = 63; + channelData->volume = volume; + SETVOICEVOLUME(channel, volume); + break; + case 13: // pattern break + if (!MOD_ChangeRowNextTick) { + MOD_ChangeRowNextTick = 1; + MOD_NextRow = effectNibble23; + } + break; + case 14: // extended + switch (effectNibble3) { + case 1: // fineslide up + newPeriod = channelData->period; + newPeriod -= effectNibble2; + channelData->period = newPeriod; + SETVOICESAMPLERATE(channel, newPeriod); + break; + case 2: // fineslide down + newPeriod = channelData->period; + newPeriod += effectNibble2; + channelData->period = newPeriod; + SETVOICESAMPLERATE(channel, newPeriod); + break; + case 4: // set vibrato waveform + fx = channelData->fx[3]; + fx &= ~0x0f; + fx |= effectNibble2; + channelData->fx[3] = fx; + break; + case 5: // set finetune value + s_spuInstrumentData[sampleID].finetune = effectNibble2; + break; + case 6: // loop pattern + if (MOD_LoopCount-- == 0) { + MOD_LoopCount = effectNibble2; + } + if (MOD_LoopCount != 0) { + MOD_CurrentRow = MOD_LoopStart; + } + break; + case 7: // set tremolo waveform + fx = channelData->fx[3]; + fx &= ~0xf0; + fx |= effectNibble2 << 4; + channelData->fx[3] = fx; + break; + case 10: // fine volume up + volume = channelData->volume; + volume += effectNibble2; + if (volume > 63) volume = 63; + channelData->volume = volume; + SETVOICEVOLUME(channel, volume); + break; + case 11: // fine volume down + volume = channelData->volume; + volume -= effectNibble2; + if (volume < 0) volume = 0; + channelData->volume = volume; + SETVOICEVOLUME(channel, volume); + break; + case 14: // delay pattern + MOD_PatternDelay = effectNibble2; + break; + } + break; + case 15: // set speed + // the original code here is very wrong with regards to + // how to interpret the command; also it was very opinionated + // about using timer1 for its clock source + if (effectNibble23 == 0) break; + if (effectNibble23 < 32) { + MOD_Speed = effectNibble23; + } else { + MOD_SetBPM(effectNibble23); + } + break; + } + + rowPointer += 4; + } +} + +void MOD_Poll() { + // the original code is getting the delay pattern wrong here, and + // isn't processing them as actual line delays, rather as a sort + // of ticks delay, and was basically going too fast + uint8_t newPatternDelay = MOD_PatternDelay; + if (++MOD_Tick < MOD_Speed) { + MOD_UpdateEffect(); + } else { + MOD_Tick = 0; + if (newPatternDelay-- == 0) { + MOD_UpdateRow(); + newPatternDelay = MOD_PatternDelay; + // I don't think the original code was handling this properly... + if (++MOD_CurrentRow >= 64 || MOD_ChangeRowNextTick) { + MOD_CurrentRow = 0; + if (++MOD_CurrentOrder >= MOD_SongLength) { + MOD_CurrentOrder = 0; + } + MOD_CurrentPattern = MOD_ModuleData[MOD_CurrentOrder]; + } + } else { + MOD_UpdateEffect(); + } + } + MOD_PatternDelay = newPatternDelay; +} + +void MOD_PlayNote(unsigned channel, unsigned sampleID, unsigned note, int16_t volume) { + if (volume < 0) volume = 0; + if (volume > 63) volume = 63; + struct SPUChannelData* const channelData = &s_channelData[channel]; + channelData->samplePos = 0; + SPUSetVoiceVolume(channel, volume << 8, volume << 8); + SPUSetStartAddress(channel, s_spuInstrumentData[sampleID].baseAddress << 4 + channelData->samplePos); + SPUWaitIdle(); + SPUKeyOn(1 << channel); + channelData->note = note = note + s_spuInstrumentData[sampleID].finetune * 36; + int32_t newPeriod = channelData->period = MOD_PeriodTable[note]; + SETVOICESAMPLERATE(channel, newPeriod); +} diff --git a/hello_mod/src/modplayer.h b/hello_mod/src/modplayer.h new file mode 100644 index 0000000..8a27a66 --- /dev/null +++ b/hello_mod/src/modplayer.h @@ -0,0 +1,150 @@ +/* + +MIT License + +Copyright (c) 2021 PCSX-Redux authors + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. + +*/ + +#pragma once + +#include + +// Once MOD_Load returns, these values will be valid. +// Unless specified, consider them read only, but +// modifying them might be doable if you know what you are doing. +extern unsigned MOD_Channels; +extern unsigned MOD_SongLength; +extern unsigned MOD_CurrentOrder; +extern unsigned MOD_CurrentPattern; +extern unsigned MOD_CurrentRow; +extern unsigned MOD_Speed; +extern unsigned MOD_Tick; +extern unsigned MOD_BPM; +extern unsigned MOD_LoopStart; +extern unsigned MOD_LoopCount; +extern uint8_t MOD_PatternDelay; + +// This is a pointer to the current row that's +// being played. Used for decoding. The number +// of relevant bytes for a row is 4 * MOD_Channels. +extern const uint8_t* MOD_RowPointer; + +// These four are fine to change outside of MOD_Poll. +// The first two are booleans, and the next two are the values +// you need them to be set at when MOD_Poll is called next. +// If you need immediate row / pattern change, also set +// MOD_Tick to MOD_Speed. +extern int MOD_ChangeRowNextTick; +extern int MOD_ChangeOrderNextTick; +extern unsigned MOD_NextRow; +extern unsigned MOD_NextOrder; + +// This can be used to decode MOD_RowPointer. +extern const uint16_t MOD_PeriodTable[]; + +// Internal HIT file structure, but conformant to +// http://www.aes.id.au/modformat.html +struct MODFileFormat; + +// Returns the number of channel from this module, +// or 0 if the module is invalid. +unsigned MOD_Check(const struct MODFileFormat* module); + +// Loads the specified module and gets it ready for +// playback. Returns the number of bytes needed if +// relocation is desired. The pointer has to be +// aligned to a 4-bytes boundary. Will also setup +// the SPU. +uint32_t MOD_Load(const struct MODFileFormat* module); + +// Call this function periodically to play sound. The +// frequency at which this is called will determine the +// actual playback speed of the module. Most modules will +// not change the default tempo, which requires calling +// MOD_Poll 50 times per second, or exactly the vertical +// refresh rate in PAL. Preferably call this from timer1's +// IRQ however, and look up MOD_hblanks to decide of the +// next target value to use. +// To pause or stop playback, simply stop calling this +// function. The internal player doesn't need any +// sort of cleanup, and switching to another song simply +// requires calling MOD_Load with a new file. +void MOD_Poll(); + +// New APIs from the original code from there on. + +// Defaults to 0. This is a boolean indicating if we +// want the volume settings to be monaural or the same +// as the original Amiga's Paula chip. +extern int MOD_Stereo; + +// Indicates the number of hblank ticks to wait before +// calling MOD_Poll. This value may or may not change +// after a call to MOD_Poll, if the track requested a +// tempo change. +extern uint32_t MOD_hblanks; + +// It is possible to reclaim memory from the initial call +// to MOD_Load, in case the module was loaded from an +// external source. The number of bytes needed for the +// player will be returned by MOD_Load. Call MOD_Relocate +// with a new memory buffer that has at least this many bytes. +// Caller is responsible for managing the memory. +// It is fine to reuse the same buffer as the original input, +// if you wish to simply realloc it after relocating it, +// provided your realloc implementation guarantees that the +// shrunk buffer will remain at the same location. +// +// For example, this pseudo-code is valid: +// bool load_mod_file(File mod_file) { +// void * buffer = malloc(file_size(mod_file)); +// readfile(mod_file, buffer); +// uint32_t size = MOD_Load(buffer); +// if (size == 0) { +// free(buffer); +// return false; +// } +// MOD_Relocate(buffer); +// void * newbuffer = realloc(buffer, size); +// if (newbuffer != buffer) { +// free(newbuffer); +// return false; +// } +// return true; +// } +void MOD_Relocate(uint8_t* buffer); + +// Plays an arbitrary note from the MOD's samples bank. +// The volume will always be centered, so the sample will +// be monaural. The voiceID ideally should be set to a +// value that is less than MOD_Channels. Remember the PS1 +// has 24 channels total, so voiceID can be between 0 and 23. +// The note is a value between 0 and 35. The exact note played +// is on the normal 12-notes, C, C#, D, ... scale, and there +// are three octaves available, which gives the 12*3=36 +// interval value of the note argument. The volume argument +// is between 0 and 63. You can simulate KeyOff by simply +// setting the volume of the voice to 0. +void MOD_PlayNote(unsigned voiceID, unsigned sampleID, unsigned note, int16_t volume); + +// Added API to reset the SPU and silence everything. +void MOD_Silence();