diff options
| author | John "Lameguy" Wilbert Villamor <lameguy64@gmail.com> | 2022-09-26 16:49:56 +0800 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2022-09-26 16:49:56 +0800 |
| commit | c4a2533d21dfd05cde841ea48c67b05e0e6a853f (patch) | |
| tree | c7ef61653b157b69fb0956709366996ddbc4ecfa /libpsn00b/include | |
| parent | a8b404b3400c3ebd8e0b923dcaefcc49ea563e36 (diff) | |
| parent | 86f0064afb8200e60dd80827535cac30d0eab028 (diff) | |
| download | psn00bsdk-c4a2533d21dfd05cde841ea48c67b05e0e6a853f.tar.gz | |
Merge pull request #55 from spicyjpeg/psxmdec
Full MDEC support, C library refactors, cleanups and bugfixes (v0.20)
Diffstat (limited to 'libpsn00b/include')
| -rw-r--r-- | libpsn00b/include/ctype.h | 23 | ||||
| -rw-r--r-- | libpsn00b/include/gtereg.inc (renamed from libpsn00b/include/gtereg.h) | 0 | ||||
| -rw-r--r-- | libpsn00b/include/hwregs_a.inc (renamed from libpsn00b/include/hwregs_a.h) | 11 | ||||
| -rw-r--r-- | libpsn00b/include/hwregs_c.h | 143 | ||||
| -rw-r--r-- | libpsn00b/include/inline_c.h | 1393 | ||||
| -rw-r--r-- | libpsn00b/include/inline_s.inc (renamed from libpsn00b/include/inline_s.h) | 0 | ||||
| -rw-r--r-- | libpsn00b/include/lzp/lzp.h | 20 | ||||
| -rw-r--r-- | libpsn00b/include/lzp/lzqlp.h | 12 | ||||
| -rw-r--r-- | libpsn00b/include/psxapi.h | 161 | ||||
| -rw-r--r-- | libpsn00b/include/psxcd.h | 95 | ||||
| -rw-r--r-- | libpsn00b/include/psxetc.h | 22 | ||||
| -rw-r--r-- | libpsn00b/include/psxgpu.h | 906 | ||||
| -rw-r--r-- | libpsn00b/include/psxgte.h | 54 | ||||
| -rw-r--r-- | libpsn00b/include/psxpress.h | 260 | ||||
| -rw-r--r-- | libpsn00b/include/psxspu.h | 228 | ||||
| -rw-r--r-- | libpsn00b/include/stdlib.h | 47 | ||||
| -rw-r--r-- | libpsn00b/include/string.h | 20 | ||||
| -rw-r--r-- | libpsn00b/include/strings.h | 23 |
18 files changed, 2252 insertions, 1166 deletions
diff --git a/libpsn00b/include/ctype.h b/libpsn00b/include/ctype.h index b79498a..24ee9d9 100644 --- a/libpsn00b/include/ctype.h +++ b/libpsn00b/include/ctype.h @@ -1,7 +1,20 @@ -#ifndef _CTYPE_H -#define _CTYPE_H +/* + * PSn00bSDK standard library + * (C) 2019-2022 PSXSDK authors, Lameguy64, spicyjpeg - MPL licensed + */ -extern int tolower(int chr); -extern int toupper(int chr); +#ifndef __CTYPE_H +#define __CTYPE_H -#endif
\ No newline at end of file +#ifdef __cplusplus +extern "C" { +#endif + +int tolower(int chr); +int toupper(int chr); + +#ifdef __cplusplus +} +#endif + +#endif diff --git a/libpsn00b/include/gtereg.h b/libpsn00b/include/gtereg.inc index 0d051fc..0d051fc 100644 --- a/libpsn00b/include/gtereg.h +++ b/libpsn00b/include/gtereg.inc diff --git a/libpsn00b/include/hwregs_a.h b/libpsn00b/include/hwregs_a.inc index 8a504f5..c78b41a 100644 --- a/libpsn00b/include/hwregs_a.h +++ b/libpsn00b/include/hwregs_a.inc @@ -1,10 +1,11 @@ -# Hardware register definitions for GNU assembler (as) -# -# Part of the PSn00bSDK Project by Lameguy64 -# 2019 Meido-Tek Productions +# PSn00bSDK hardware registers definitions +# (C) 2019-2022 Lameguy64, spicyjpeg - MPL licensed +## Constants -.set IOBASE, 0x1f80 # IO segment base +.set IOBASE, 0x1f80 +.set F_CPU, 33868800 +.set F_GPU, 53222400 ## GPU diff --git a/libpsn00b/include/hwregs_c.h b/libpsn00b/include/hwregs_c.h index e533c56..b205b87 100644 --- a/libpsn00b/include/hwregs_c.h +++ b/libpsn00b/include/hwregs_c.h @@ -14,116 +14,117 @@ /* Constants */ +#define IOBASE 0xbf800000 #define F_CPU 33868800UL #define F_GPU 53222400UL /* GPU */ -#define GPU_GP0 _MMIO32(0x1f801810) -#define GPU_GP1 _MMIO32(0x1f801814) +#define GPU_GP0 _MMIO32(IOBASE | 0x1810) +#define GPU_GP1 _MMIO32(IOBASE | 0x1814) /* CD drive */ -#define CD_STAT _MMIO8(0x1f801800) -#define CD_CMD _MMIO8(0x1f801801) -#define CD_DATA _MMIO8(0x1f801802) -#define CD_IRQ _MMIO8(0x1f801803) +#define CD_STAT _MMIO8(IOBASE | 0x1800) +#define CD_CMD _MMIO8(IOBASE | 0x1801) +#define CD_DATA _MMIO8(IOBASE | 0x1802) +#define CD_IRQ _MMIO8(IOBASE | 0x1803) -#define CD_REG(N) _MMIO8(0x1f801800 + (N)) +#define CD_REG(N) _MMIO8(IOBASE | 0x1800 + (N)) /* SPU */ -#define SPU_MASTER_VOL_L _MMIO16(0x1f801d80) -#define SPU_MASTER_VOL_R _MMIO16(0x1f801d82) -#define SPU_REVERB_VOL_L _MMIO16(0x1f801d84) -#define SPU_REVERB_VOL_R _MMIO16(0x1f801d86) -#define SPU_KEY_ON _MMIO32(0x1f801d88) -#define SPU_KEY_OFF _MMIO32(0x1f801d8c) -#define SPU_FM_MODE _MMIO32(0x1f801d90) -#define SPU_NOISE_MODE _MMIO32(0x1f801d94) -#define SPU_REVERB_ON _MMIO32(0x1f801d98) -#define SPU_CHAN_STATUS _MMIO32(0x1f801d9c) - -#define SPU_REVERB_ADDR _MMIO16(0x1f801da2) -#define SPU_IRQ_ADDR _MMIO16(0x1f801da4) -#define SPU_ADDR _MMIO16(0x1f801da6) -#define SPU_DATA _MMIO16(0x1f801da8) - -#define SPU_CTRL _MMIO16(0x1f801daa) -#define SPU_DMA_CTRL _MMIO16(0x1f801dac) -#define SPU_STAT _MMIO16(0x1f801dae) - -#define SPU_CD_VOL_L _MMIO16(0x1f801db0) -#define SPU_CD_VOL_R _MMIO16(0x1f801db2) -#define SPU_EXT_VOL_L _MMIO16(0x1f801db4) -#define SPU_EXT_VOL_R _MMIO16(0x1f801db6) -#define SPU_CURRENT_VOL_L _MMIO16(0x1f801db8) -#define SPU_CURRENT_VOL_R _MMIO16(0x1f801dba) +#define SPU_MASTER_VOL_L _MMIO16(IOBASE | 0x1d80) +#define SPU_MASTER_VOL_R _MMIO16(IOBASE | 0x1d82) +#define SPU_REVERB_VOL_L _MMIO16(IOBASE | 0x1d84) +#define SPU_REVERB_VOL_R _MMIO16(IOBASE | 0x1d86) +#define SPU_KEY_ON _MMIO32(IOBASE | 0x1d88) +#define SPU_KEY_OFF _MMIO32(IOBASE | 0x1d8c) +#define SPU_FM_MODE _MMIO32(IOBASE | 0x1d90) +#define SPU_NOISE_MODE _MMIO32(IOBASE | 0x1d94) +#define SPU_REVERB_ON _MMIO32(IOBASE | 0x1d98) +#define SPU_CHAN_STATUS _MMIO32(IOBASE | 0x1d9c) + +#define SPU_REVERB_ADDR _MMIO16(IOBASE | 0x1da2) +#define SPU_IRQ_ADDR _MMIO16(IOBASE | 0x1da4) +#define SPU_ADDR _MMIO16(IOBASE | 0x1da6) +#define SPU_DATA _MMIO16(IOBASE | 0x1da8) + +#define SPU_CTRL _MMIO16(IOBASE | 0x1daa) +#define SPU_DMA_CTRL _MMIO16(IOBASE | 0x1dac) +#define SPU_STAT _MMIO16(IOBASE | 0x1dae) + +#define SPU_CD_VOL_L _MMIO16(IOBASE | 0x1db0) +#define SPU_CD_VOL_R _MMIO16(IOBASE | 0x1db2) +#define SPU_EXT_VOL_L _MMIO16(IOBASE | 0x1db4) +#define SPU_EXT_VOL_R _MMIO16(IOBASE | 0x1db6) +#define SPU_CURRENT_VOL_L _MMIO16(IOBASE | 0x1db8) +#define SPU_CURRENT_VOL_R _MMIO16(IOBASE | 0x1dba) // These are not named SPU_VOICE_* to avoid name clashes with SPU attribute // flags defined in psxspu.h. -#define SPU_CH_VOL_L(N) _MMIO16(0x1f801c00 + 16 * (N)) -#define SPU_CH_VOL_R(N) _MMIO16(0x1f801c02 + 16 * (N)) -#define SPU_CH_FREQ(N) _MMIO16(0x1f801c04 + 16 * (N)) -#define SPU_CH_ADDR(N) _MMIO16(0x1f801c06 + 16 * (N)) -#define SPU_CH_ADSR(N) _MMIO32(0x1f801c08 + 16 * (N)) -#define SPU_CH_LOOP_ADDR(N) _MMIO16(0x1f801c0e + 16 * (N)) +#define SPU_CH_VOL_L(N) _MMIO16(IOBASE | 0x1c00 + 16 * (N)) +#define SPU_CH_VOL_R(N) _MMIO16(IOBASE | 0x1c02 + 16 * (N)) +#define SPU_CH_FREQ(N) _MMIO16(IOBASE | 0x1c04 + 16 * (N)) +#define SPU_CH_ADDR(N) _MMIO16(IOBASE | 0x1c06 + 16 * (N)) +#define SPU_CH_ADSR(N) _MMIO32(IOBASE | 0x1c08 + 16 * (N)) +#define SPU_CH_LOOP_ADDR(N) _MMIO16(IOBASE | 0x1c0e + 16 * (N)) /* MDEC */ -#define MDEC0 _MMIO32(0x1f801820) -#define MDEC1 _MMIO32(0x1f801824) +#define MDEC0 _MMIO32(IOBASE | 0x1820) +#define MDEC1 _MMIO32(IOBASE | 0x1824) /* SPI controller port */ // IMPORTANT: even though JOY_TXRX is a 32-bit register, it should only be // accessed as 8-bit. Reading it as 16 or 32-bit works fine on real hardware, // but leads to problems in some emulators. -#define JOY_TXRX _MMIO8(0x1f801040) -#define JOY_STAT _MMIO16(0x1f801044) -#define JOY_MODE _MMIO16(0x1f801048) -#define JOY_CTRL _MMIO16(0x1f80104a) -#define JOY_BAUD _MMIO16(0x1f80104e) +#define JOY_TXRX _MMIO8 (IOBASE | 0x1040) +#define JOY_STAT _MMIO16(IOBASE | 0x1044) +#define JOY_MODE _MMIO16(IOBASE | 0x1048) +#define JOY_CTRL _MMIO16(IOBASE | 0x104a) +#define JOY_BAUD _MMIO16(IOBASE | 0x104e) /* Serial port */ -#define SIO_TXRX _MMIO8(0x1f801050) -#define SIO_STAT _MMIO16(0x1f801054) -#define SIO_MODE _MMIO16(0x1f801058) -#define SIO_CTRL _MMIO16(0x1f80105a) -#define SIO_BAUD _MMIO16(0x1f80105e) +#define SIO_TXRX _MMIO8 (IOBASE | 0x1050) +#define SIO_STAT _MMIO16(IOBASE | 0x1054) +#define SIO_MODE _MMIO16(IOBASE | 0x1058) +#define SIO_CTRL _MMIO16(IOBASE | 0x105a) +#define SIO_BAUD _MMIO16(IOBASE | 0x105e) /* IRQ controller */ -#define IRQ_STAT _MMIO32(0x1f801070) -#define IRQ_MASK _MMIO32(0x1f801074) +#define IRQ_STAT _MMIO16(IOBASE | 0x1070) +#define IRQ_MASK _MMIO16(IOBASE | 0x1074) /* DMA */ -#define DMA_DPCR _MMIO32(0x1f8010f0) -#define DMA_DICR _MMIO32(0x1f8010f4) +#define DMA_DPCR _MMIO32(IOBASE | 0x10f0) +#define DMA_DICR _MMIO32(IOBASE | 0x10f4) -#define DMA_MADR(N) _MMIO32(0x1f801080 + 16 * (N)) -#define DMA_BCR(N) _MMIO32(0x1f801084 + 16 * (N)) -#define DMA_CHCR(N) _MMIO32(0x1f801088 + 16 * (N)) +#define DMA_MADR(N) _MMIO32(IOBASE | 0x1080 + 16 * (N)) +#define DMA_BCR(N) _MMIO32(IOBASE | 0x1084 + 16 * (N)) +#define DMA_CHCR(N) _MMIO32(IOBASE | 0x1088 + 16 * (N)) /* Timers */ -#define TIMER_VALUE(N) _MMIO32(0x1f801100 + 16 * (N)) -#define TIMER_CTRL(N) _MMIO32(0x1f801104 + 16 * (N)) -#define TIMER_RELOAD(N) _MMIO32(0x1f801108 + 16 * (N)) +#define TIMER_VALUE(N) _MMIO32(IOBASE | 0x1100 + 16 * (N)) +#define TIMER_CTRL(N) _MMIO32(IOBASE | 0x1104 + 16 * (N)) +#define TIMER_RELOAD(N) _MMIO32(IOBASE | 0x1108 + 16 * (N)) /* Memory control */ -#define EXP1_ADDR _MMIO32(0x1f801000) -#define EXP2_ADDR _MMIO32(0x1f801004) -#define EXP1_DELAY_SIZE _MMIO32(0x1f801008) -#define EXP3_DELAY_SIZE _MMIO32(0x1f80100c) -#define BIOS_DELAY_SIZE _MMIO32(0x1f801010) -#define SPU_DELAY_SIZE _MMIO32(0x1f801014) -#define CD_DELAY_SIZE _MMIO32(0x1f801018) -#define EXP2_DELAY_SIZE _MMIO32(0x1f80101c) -#define COM_DELAY_CFG _MMIO32(0x1f801020) -#define RAM_SIZE_CFG _MMIO32(0x1f801060) +#define EXP1_ADDR _MMIO32(IOBASE | 0x1000) +#define EXP2_ADDR _MMIO32(IOBASE | 0x1004) +#define EXP1_DELAY_SIZE _MMIO32(IOBASE | 0x1008) +#define EXP3_DELAY_SIZE _MMIO32(IOBASE | 0x100c) +#define BIOS_DELAY_SIZE _MMIO32(IOBASE | 0x1010) +#define SPU_DELAY_SIZE _MMIO32(IOBASE | 0x1014) +#define CD_DELAY_SIZE _MMIO32(IOBASE | 0x1018) +#define EXP2_DELAY_SIZE _MMIO32(IOBASE | 0x101c) +#define COM_DELAY_CFG _MMIO32(IOBASE | 0x1020) +#define RAM_SIZE_CFG _MMIO32(IOBASE | 0x1060) #endif diff --git a/libpsn00b/include/inline_c.h b/libpsn00b/include/inline_c.h index 177faf1..c5eaa59 100644 --- a/libpsn00b/include/inline_c.h +++ b/libpsn00b/include/inline_c.h @@ -1,32 +1,23 @@ -/* Inline GTE macros for the GNU C compiler. - * - * Part of the PSn00bSDK Project by Lameguy64. - * 2019 Meido-Tek Production - * - * All GTE commands can be used without having to pass your object file - * through some stupid tool such as DMPSX. Perhaps it was Sony's attempt - * to prevent people from quickly discovering the GTE commands from the - * official SDK easily? Though people could just extract the cop2 opcodes - * of an object file after it has been passed through DMPSX. - * - * Todo: A couple of GTE operation macros are still missing such as - * gte_rtv*() though they appear to be just variants of gte_mvmva more or - * less (gte_rtv0() is actually gte_mvmva(1, 0, 0, 3, 0) for example). +/* + * PSn00bSDK GTE macros + * (C) 2019 Lameguy64 + * (C) 2021-2022 Soapy (tweaked by spicyjpeg) * + * This header is basically identical to Nugget's inline_n.h. All GTE commands + * can be used right away without having to run DMPSX or any other tool on + * object files. */ #ifndef _INLINE_C_H #define _INLINE_C_H -/* - * GTE load macros - */ +/* GTE load macros */ /* Load a SVECTOR (passed as a pointer) to GTE V0 */ #define gte_ldv0( r0 ) __asm__ volatile ( \ - "lwc2 $0 , 0( %0 );" \ - "lwc2 $1 , 4( %0 );" \ + "lwc2 $0, 0( %0 );" \ + "lwc2 $1, 4( %0 );" \ : \ : "r"( r0 ) \ : "$t0" ) @@ -34,8 +25,8 @@ /* Load a SVECTOR (passed as a pointer) to GTE V1 */ #define gte_ldv1( r0 ) __asm__ volatile ( \ - "lwc2 $2 , 0( %0 );" \ - "lwc2 $3 , 4( %0 );" \ + "lwc2 $2, 0( %0 );" \ + "lwc2 $3, 4( %0 );" \ : \ : "r"( r0 ) \ : "$t0" ) @@ -43,8 +34,8 @@ /* Load a SVECTOR (passed as a pointer) to GTE V2 */ #define gte_ldv2( r0 ) __asm__ volatile ( \ - "lwc2 $4 , 0( %0 );" \ - "lwc2 $5 , 4( %0 );" \ + "lwc2 $4, 0( %0 );" \ + "lwc2 $5, 4( %0 );" \ : \ : "r"( r0 ) \ : "$t0" ) @@ -52,20 +43,187 @@ /* Load three SVECTORs (passed as a pointer) to the GTE at once */ #define gte_ldv3( r0, r1, r2 ) __asm__ volatile ( \ - "lwc2 $0 , 0( %0 );" \ - "lwc2 $1 , 4( %0 );" \ - "lwc2 $2 , 0( %1 );" \ - "lwc2 $3 , 4( %1 );" \ - "lwc2 $4 , 0( %2 );" \ - "lwc2 $5 , 4( %2 );" \ + "lwc2 $0, 0( %0 );" \ + "lwc2 $1, 4( %0 );" \ + "lwc2 $2, 0( %1 );" \ + "lwc2 $3, 4( %1 );" \ + "lwc2 $4, 0( %2 );" \ + "lwc2 $5, 4( %2 );" \ : \ : "r"( r0 ), "r"( r1 ), "r"( r2 ) ) - + +#define gte_ldv3c( r0 ) __asm__ volatile ( \ + "lwc2 $0, 0( %0 );" \ + "lwc2 $1, 4( %0 );" \ + "lwc2 $2, 8( %0 );" \ + "lwc2 $3, 12( %0 );" \ + "lwc2 $4, 16( %0 );" \ + "lwc2 $5, 20( %0 );" \ + : \ + : "r"( r0 ) ) + +#define gte_ldv3c_vertc( r0 ) __asm__ volatile ( \ + "lwc2 $0, 0( %0 );" \ + "lwc2 $1, 4( %0 );" \ + "lwc2 $2, 12( %0 );" \ + "lwc2 $3, 16( %0 );" \ + "lwc2 $4, 24( %0 );" \ + "lwc2 $5, 28( %0 );" \ + : \ + : "r"( r0 ) ) + +#define gte_ldv01( r0, r1 ) __asm__ volatile ( \ + "lwc2 $0, 0( %0 );" \ + "lwc2 $1, 4( %0 );" \ + "lwc2 $2, 0( %1 );" \ + "lwc2 $3, 4( %1 );" \ + : \ + : "r"( r0 ), "r"( r1 ) ) + +#define gte_ldv01c( r0 ) __asm__ volatile ( \ + "lwc2 $0, 0( %0 );" \ + "lwc2 $1, 4( %0 );" \ + "lwc2 $2, 8( %0 );" \ + "lwc2 $3, 12( %0 );" \ + : \ + : "r"( r0 ) ) + #define gte_ldrgb( r0 ) __asm__ volatile ( \ "lwc2 $6 , 0( %0 );" \ : \ : "r"( r0 ) ) - + +#define gte_ldrgb3( r0, r1, r2 ) __asm__ volatile ( \ + "lwc2 $20, 0( %0 );" \ + "lwc2 $21, 0( %1 );" \ + "lwc2 $22, 0( %2 );" \ + "lwc2 $6, 0( %2 );" \ + : \ + : "r"( r0 ), "r"( r1 ), "r"( r2 ) ) + +#define gte_ldrgb3c( r0 ) __asm__ volatile ( \ + "lwc2 $20, 0( %0 );" \ + "lwc2 $21, 4( %0 );" \ + "lwc2 $22, 8( %0 );" \ + "lwc2 $6, 8( %0 );" \ + : \ + : "r"( r0 ) ) + +#define gte_ldlv0( r0 ) __asm__ volatile ( \ + "lhu $13, 4( %0 );" \ + "lhu $12, 0( %0 );" \ + "sll $13, $13, 16;" \ + "or $12, $12, $13;" \ + "mtc2 $12, $0;" \ + "lwc2 $1, 8( %0 );" \ + : \ + : "r"( r0 ) \ + : "$12", "$13" ) + +#define gte_ldlvl( r0 ) __asm__ volatile ( \ + "lwc2 $9, 0( %0 );" \ + "lwc2 $10, 4( %0 );" \ + "lwc2 $11, 8( %0 );" \ + : \ + : "r"( r0 ) ) + +#define gte_ldsv( r0 ) __asm__ volatile ( \ + "lhu $12, 0( %0 );" \ + "lhu $13, 2( %0 );" \ + "lhu $14, 4( %0 );" \ + "mtc2 $12, $9;" \ + "mtc2 $13, $10;" \ + "mtc2 $14, $11;" \ + : \ + : "r"( r0 ) \ + : "$12", "$13", "$14" ) + +#define gte_ldbv( r0 ) __asm__ volatile ( \ + "lbu $12, 0( %0 );" \ + "lbu $13, 1( %0 );" \ + "mtc2 $12, $9;" \ + "mtc2 $13, $10;" \ + : \ + : "r"( r0 ) \ + : "$12", "$13" ) + +#define gte_ldcv( r0 ) __asm__ volatile ( \ + "lbu $12, 0( %0 );" \ + "lbu $13, 1( %0 );" \ + "lbu $14, 2( %0 );" \ + "mtc2 $12, $9;" \ + "mtc2 $13, $10;" \ + "mtc2 $14, $11;" \ + : \ + : "r"( r0 ) \ + : "$12", "$13", "$14" ) + +#define gte_ldclmv( r0 ) __asm__ volatile ( \ + "lhu $12, 0( %0 );" \ + "lhu $13, 6( %0 );" \ + "lhu $14, 12( %0 );" \ + "mtc2 $12, $9;" \ + "mtc2 $13, $10;" \ + "mtc2 $14, $11;" \ + : \ + : "r"( r0 ) \ + : "$12", "$13", "$14" ) + +#define gte_ldsxy0( r0 ) __asm__ volatile ( \ + "mtc2 %0, $12;" \ + : \ + : "r"( r0 ) ) + +#define gte_ldsxy1( r0 ) __asm__ volatile ( \ + "mtc2 %0, $13;" \ + : \ + : "r"( r0 ) ) + +#define gte_ldsxy2( r0 ) __asm__ volatile ( \ + "mtc2 %0, $14;" \ + : \ + : "r"( r0 ) ) + +#define gte_ldsxy3( r0, r1, r2 ) __asm__ volatile ( \ + "mtc2 %0, $12;" \ + "mtc2 %2, $14;" \ + "mtc2 %1, $13;" \ + : \ + : "r"( r0 ), "r"( r1 ), "r"( r2 ) ) + +#define gte_ldsxy3c( r0 ) __asm__ volatile ( \ + "lwc2 $12, 0( %0 );" \ + "lwc2 $13, 4( %0 );" \ + "lwc2 $14, 8( %0 );" \ + : \ + : "r"( r0 ) ) + +#define gte_ldsz3( r0, r1, r2 ) __asm__ volatile ( \ + "mtc2 %0, $17;" \ + "mtc2 %1, $18;" \ + "mtc2 %2, $19;" \ + : \ + : "r"( r0 ), "r"( r1 ), "r"( r2 ) ) + +#define gte_ldsz4( r0, r1, r2, r3 ) __asm__ volatile ( \ + "mtc2 %0, $16;" \ + "mtc2 %1, $17;" \ + "mtc2 %2, $18;" \ + "mtc2 %3, $19;" \ + : \ + : "r"( r0 ), "r"( r1 ), "r"( r2 ), "r"( r3 ) ) + +#define gte_ldopv1( r0 ) __asm__ volatile ( \ + "lw $12, 0( %0 );" \ + "lw $13, 4( %0 );" \ + "ctc2 $12, $0;" \ + "lw $14, 8( %0 );" \ + "ctc2 $13, $2;" \ + "ctc2 $14, $4;" \ + : \ + : "r"( r0 ) \ + : "$12", "$13", "$14" ) + #define gte_ldopv2( r0 ) __asm__ volatile ( \ "lwc2 $11, 8( %0 );" \ "lwc2 $9 , 0( %0 );" \ @@ -77,9 +235,53 @@ "mtc2 %0, $8;" \ : \ : "r"( r0 ) ) - -/* Sets the GTE offset - */ + +#define gte_ldlzc( r0 ) __asm__ volatile ( \ + "mtc2 %0, $30;" \ + : \ + : "r"( r0 ) ) + +#define gte_SetRGBcd( r0 ) __asm__ volatile ( \ + "lwc2 $6, 0( %0 );" \ + : \ + : "r"( r0 ) ) + +#define gte_ldbkdir( r0, r1, r2 ) __asm__ volatile ( \ + "ctc2 %0, $13;" \ + "ctc2 %1, $14;" \ + "ctc2 %2, $15;" \ + : \ + : "r"( r0 ), "r"( r1 ), "r"( r2 ) ) + +#define gte_SetBackColor( r0, r1, r2 ) __asm__ volatile ( \ + "sll $t0, %0, 4;" \ + "sll $t1, %1, 4;" \ + "sll $t2, %2, 4;" \ + "ctc2 $t0, $13;" \ + "ctc2 $t1, $14;" \ + "ctc2 $t2, $15;" \ + : \ + : "r"( r0 ), "r"( r1 ), "r"( r2 ) \ + : "$t0", "$t1", "$t2" ) + +#define gte_ldfcdir( r0, r1, r2 ) __asm__ volatile ( \ + "ctc2 %0, $21;" \ + "ctc2 %1, $22;" \ + "ctc2 %2, $23;" \ + : \ + : "r"( r0 ), "r"( r1 ), "r"( r2 ) ) + +#define gte_SetFarColor( r0, r1, r2 ) __asm__ volatile ( \ + "sll $12, %0, 4;" \ + "sll $13, %1, 4;" \ + "sll $14, %2, 4;" \ + "ctc2 $12, $21;" \ + "ctc2 $13, $22;" \ + "ctc2 $14, $23;" \ + : \ + : "r"( r0 ), "r"( r1 ), "r"( r2 ) \ + : "$12", "$13", "$14" ) + #define gte_SetGeomOffset( r0, r1 ) __asm__ volatile ( \ "sll $t0, %0, 16;" \ "sll $t1, %1, 16;" \ @@ -88,23 +290,21 @@ : \ : "r"( r0 ), "r"( r1 ) \ : "$t0", "$t1" ) - + #define gte_SetGeomScreen( r0 ) __asm__ volatile ( \ "ctc2 %0, $26;" \ : \ : "r"( r0 ) ) -#define gte_SetTransMatrix( r0 ) __asm__ volatile ( \ - "lw $t0, 20( %0 );" \ - "lw $t1, 24( %0 );" \ - "ctc2 $t0, $5;" \ - "lw $t2, 28( %0 );" \ - "ctc2 $t1, $6;" \ - "ctc2 $t2, $7;" \ +#define gte_ldsvrtrow0( r0 ) __asm__ volatile ( \ + "lw $12, 0( %0 );" \ + "lw $13, 4( %0 );" \ + "ctc2 $12, $0;" \ + "ctc2 $13, $1;" \ : \ : "r"( r0 ) \ - : "$t2" ) - + : "$12", "$13" ) + #define gte_SetRotMatrix( r0 ) __asm__ volatile ( \ "lw $t0, 0( %0 );" \ "lw $t1, 4( %0 );" \ @@ -120,6 +320,15 @@ : "r"( r0 ) \ : "$t2" ) +#define gte_ldsvllrow0( r0 ) __asm__ volatile ( \ + "lw $12, 0( %0 );" \ + "lw $13, 4( %0 );" \ + "ctc2 $12, $8;" \ + "ctc2 $13, $9;" \ + : \ + : "r"( r0 ) \ + : "$12", "$13" ) + #define gte_SetLightMatrix( r0 ) __asm__ volatile ( \ "lw $t0, 0( %0 );" \ "lw $t1, 4( %0 );" \ @@ -134,7 +343,16 @@ : \ : "r"( r0 ) \ : "$t2" ) - + +#define gte_ldsvlcrow0( r0 ) __asm__ volatile ( \ + "lw $12, 0( %0 );" \ + "lw $13, 4( %0 );" \ + "ctc2 $12, $16;" \ + "ctc2 $13, $17;" \ + : \ + : "r"( r0 ) \ + : "$12", "$13" ) + #define gte_SetColorMatrix( r0 ) __asm__ volatile ( \ "lw $t0, 0( %0 );" \ "lw $t1, 4( %0 );" \ @@ -149,44 +367,153 @@ : \ : "r"( r0 ) \ : "$t2" ) - -#define gte_SetBackColor( r0, r1, r2 ) __asm__ volatile ( \ - "sll $t0, %0, 4;" \ - "sll $t1, %1, 4;" \ - "sll $t2, %2, 4;" \ - "ctc2 $t0, $13;" \ - "ctc2 $t1, $14;" \ - "ctc2 $t2, $15;" \ + +#define gte_SetTransMatrix( r0 ) __asm__ volatile ( \ + "lw $t0, 20( %0 );" \ + "lw $t1, 24( %0 );" \ + "ctc2 $t0, $5;" \ + "lw $t2, 28( %0 );" \ + "ctc2 $t1, $6;" \ + "ctc2 $t2, $7;" \ : \ - : "r"( r0 ), "r"( r1 ), "r"( r2 ) \ - : "$t0", "$t1", "$t2" ) - -/* - * GTE store macros - */ - -#define gte_otz( r0 ) __asm__ volatile ( \ - "swc2 $7, 0( %0 );" \ + : "r"( r0 ) \ + : "$t2" ) + +#define gte_ldtr( r0, r1, r2 ) __asm__ volatile ( \ + "ctc2 %0, $5;" \ + "ctc2 %1, $6;" \ + "ctc2 %2, $7;" \ + : \ + : "r"( r0 ), "r"( r1 ), "r"( r2 ) ) + +#define gte_SetTransVector( r0 ) __asm__ volatile ( \ + "lw $12, 0( %0 );" \ + "lw $13, 4( %0 );" \ + "lw $14, 8( %0 );" \ + "ctc2 $12, $5;" \ + "ctc2 $13, $6;" \ + "ctc2 $14, $7;" \ : \ : "r"( r0 ) \ - : "memory" ) - -#define gte_stflg( r0 ) __asm__ volatile ( \ - "cfc2 $t0, $31;" \ - "nop;" \ - "sw $t0, 0( %0 );" \ + : "$12", "$13", "$14" ) + +#define gte_ld_intpol_uv0( r0 ) __asm__ volatile ( \ + "lbu $12, 0( %0 );" \ + "lbu $13, 1( %0 );" \ + "ctc2 $12, $21;" \ + "ctc2 $13, $22;" \ : \ : "r"( r0 ) \ - : "memory" ) - + : "$12", "$13" ) + +#define gte_ld_intpol_uv1( r0 ) __asm__ volatile ( \ + "lbu $12, 0( %0 );" \ + "lbu $13, 1( %0 );" \ + "mtc2 $12, $9;" \ + "mtc2 $13, $10;" \ + : \ + : "r"( r0 ) \ + : "$12", "$13" ) + +#define gte_ld_intpol_bv0( r0 ) __asm__ volatile ( \ + "lbu $12, 0( %0 );" \ + "lbu $13, 1( %0 );" \ + "ctc2 $12, $21;" \ + "ctc2 $13, $22;" \ + : \ + : "r"( r0 ) \ + : "$12", "$13" ) + +#define gte_ld_intpol_bv1( r0 ) __asm__ volatile ( \ + "lbu $12, 0( %0 );" \ + "lbu $13, 1( %0 );" \ + "mtc2 $12, $9;" \ + "mtc2 $13, $10;" \ + : \ + : "r"( r0 ) \ + : "$12", "$13" ) + +#define gte_ld_intpol_sv0( r0 ) __asm__ volatile ( \ + "lh $12, 0( %0 );" \ + "lh $13, 2( %0 );" \ + "lh $14, 4( %0 );" \ + "ctc2 $12, $21;" \ + "ctc2 $13, $22;" \ + "ctc2 $14, $23;" \ + : \ + : "r"( r0 ) \ + : "$12", "$13", "$14" ) + +#define gte_ld_intpol_sv1( r0 ) __asm__ volatile ( \ + "lh $12, 0( %0 );" \ + "lh $13, 2( %0 );" \ + "lh $14, 4( %0 );" \ + "mtc2 $12, $9;" \ + "mtc2 $13, $10;" \ + "mtc2 $14, $11;" \ + : \ + : "r"( r0 ) \ + : "$12", "$13", "$14" ) + +#define gte_ldfc( r0 ) __asm__ volatile ( \ + "lw $12, 0( %0 );" \ + "lw $13, 4( %0 );" \ + "lw $14, 8( %0 );" \ + "ctc2 $12, $21;" \ + "ctc2 $13, $22;" \ + "ctc2 $14, $23;" \ + : \ + : "r"( r0 ) \ + : "$12", "$13", "$14" ) + +#define gte_ldopv2SV( r0 ) __asm__ volatile ( \ + "lh $12, 0( %0 );" \ + "lh $13, 2( %0 );" \ + "lh $14, 4( %0 );" \ + "mtc2 $12, $9;" \ + "mtc2 $13, $10;" \ + "mtc2 $14, $11;" \ + : \ + : "r"( r0 ) \ + : "$12", "$13", "$14" ) + +#define gte_ldopv1SV( r0 ) __asm__ volatile ( \ + "lh $12, 0( %0 );" \ + "lh $13, 2( %0 );" \ + "ctc2 $12, $0;" \ + "lh $14, 4( %0 );" \ + "ctc2 $13, $2;" \ + "ctc2 $14, $4;" \ + : \ + : "r"( r0 ) \ + : "$12", "$13", "$14" ) + +/* GTE store macros */ + #define gte_stsxy( r0 ) __asm__ volatile ( \ "swc2 $14, 0( %0 );" \ : \ : "r"( r0 ) \ : "memory" ) - -#define gte_stsxy0( r0 ) __asm__ volatile ( \ + +#define gte_stsxy3( r0, r1, r2 ) __asm__ volatile ( \ "swc2 $12, 0( %0 );" \ + "swc2 $13, 0( %1 );" \ + "swc2 $14, 0( %2 );" \ + : \ + : "r"( r0 ), "r"( r1 ), "r"( r2 ) \ + : "memory" ) + +#define gte_stsxy3c( r0 ) __asm__ volatile ( \ + "swc2 $12, 0( %0 );" \ + "swc2 $13, 4( %0 );" \ + "swc2 $14, 8( %0 );" \ + : \ + : "r"( r0 ) \ + : "memory" ) + +#define gte_stsxy2( r0 ) __asm__ volatile ( \ + "swc2 $14, 0( %0 );" \ : \ : "r"( r0 ) \ : "memory" ) @@ -197,140 +524,526 @@ : "r"( r0 ) \ : "memory" ) -#define gte_stsxy2( r0 ) __asm__ volatile ( \ - "swc2 $14, 0( %0 );" \ +#define gte_stsxy0( r0 ) __asm__ volatile ( \ + "swc2 $12, 0( %0 );" \ : \ : "r"( r0 ) \ : "memory" ) -#define gte_stsxy3( r0, r1, r2 ) __asm__ volatile ( \ +#define gte_stsxy01( r0, r1 ) __asm__ volatile ( \ "swc2 $12, 0( %0 );" \ "swc2 $13, 0( %1 );" \ - "swc2 $14, 0( %2 );" \ : \ - : "r"( r0 ), "r"( r1 ), "r"( r2 ) \ + : "r"( r0 ), "r"( r1 ) \ + : "memory" ) + +#define gte_stsxy01c( r0 ) __asm__ volatile ( \ + "swc2 $12, 0( %0 );" \ + "swc2 $13, 4( %0 );" \ + : \ + : "r"( r0 ) \ : "memory" ) -#define gte_stsxy3_f3( r0 ) __asm__ volatile ( \ +#define gte_stsxy3_f3( r0 ) __asm__ volatile ( \ "swc2 $12, 8( %0 );" \ "swc2 $13, 12( %0 );" \ - "swc2 $14, 16( %0 )" \ + "swc2 $14, 16( %0 );" \ : \ - : "r"( r0 ) \ + : "r"( r0 ) \ : "memory" ) -#define gte_stsxy3_g3( r0 ) __asm__ volatile ( \ +#define gte_stsxy3_g3( r0 ) __asm__ volatile ( \ "swc2 $12, 8( %0 );" \ "swc2 $13, 16( %0 );" \ - "swc2 $14, 24( %0 )" \ + "swc2 $14, 24( %0 );" \ : \ - : "r"( r0 ) \ + : "r"( r0 ) \ : "memory" ) -#define gte_stsxy3_ft3( r0 ) __asm__ volatile ( \ +#define gte_stsxy3_ft3( r0 ) __asm__ volatile ( \ "swc2 $12, 8( %0 );" \ "swc2 $13, 16( %0 );" \ - "swc2 $14, 24( %0 )" \ + "swc2 $14, 24( %0 );" \ : \ - : "r"( r0 ) \ + : "r"( r0 ) \ : "memory" ) -#define gte_stsxy3_gt3( r0 ) __asm__ volatile ( \ +#define gte_stsxy3_gt3( r0 ) __asm__ volatile ( \ "swc2 $12, 8( %0 );" \ "swc2 $13, 20( %0 );" \ - "swc2 $14, 32( %0 )" \ + "swc2 $14, 32( %0 );" \ : \ - : "r"( r0 ) \ + : "r"( r0 ) \ : "memory" ) -#define gte_stsxy3_f4( r0 ) __asm__ volatile ( \ +#define gte_stsxy3_f4( r0 ) __asm__ volatile ( \ "swc2 $12, 8( %0 );" \ "swc2 $13, 12( %0 );" \ - "swc2 $14, 16( %0 )" \ + "swc2 $14, 16( %0 );" \ : \ - : "r"( r0 ) \ + : "r"( r0 ) \ : "memory" ) -#define gte_stsxy3_g4( r0 ) __asm__ volatile ( \ +#define gte_stsxy3_g4( r0 ) __asm__ volatile ( \ "swc2 $12, 8( %0 );" \ "swc2 $13, 16( %0 );" \ - "swc2 $14, 24( %0 )" \ + "swc2 $14, 24( %0 );" \ : \ - : "r"( r0 ) \ + : "r"( r0 ) \ : "memory" ) -#define gte_stsxy3_ft4( r0 ) __asm__ volatile ( \ +#define gte_stsxy3_ft4( r0 ) __asm__ volatile ( \ "swc2 $12, 8( %0 );" \ "swc2 $13, 16( %0 );" \ - "swc2 $14, 24( %0 )" \ + "swc2 $14, 24( %0 );" \ : \ - : "r"( r0 ) \ + : "r"( r0 ) \ : "memory" ) -#define gte_stsxy3_gt4( r0 ) __asm__ volatile ( \ +#define gte_stsxy3_gt4( r0 ) __asm__ volatile ( \ "swc2 $12, 8( %0 );" \ "swc2 $13, 20( %0 );" \ - "swc2 $14, 32( %0 )" \ + "swc2 $14, 32( %0 );" \ : \ - : "r"( r0 ) \ + : "r"( r0 ) \ : "memory" ) +#define gte_stdp( r0 ) __asm__ volatile ( \ + "swc2 $8, 0( %0 );" \ + : \ + : "r"( r0 ) \ + : "memory" ) + +#define gte_stflg( r0 ) __asm__ volatile ( \ + "cfc2 $12, $31;" \ + "nop;" \ + "sw $12, 0( %0 );" \ + : \ + : "r"( r0 ) \ + : "$12", "memory" ) + +#define gte_stflg_4( r0 ) __asm__ volatile ( \ + "cfc2 $12, $31;" \ + "addi $13, $0, 4;" \ + "sll $13, $13, 16;" \ + "and $12, $12, $13;" \ + "sw $12, 0( %0 );" \ + : \ + : "r"( r0 ) \ + : "$12", "$13", "memory" ) + #define gte_stsz( r0 ) __asm__ volatile ( \ "swc2 $19, 0( %0 );" \ : \ : "r"( r0 ) \ : "memory" ) - + +#define gte_stsz3( r0, r1, r2 ) __asm__ volatile ( \ + "swc2 $17, 0( %0 );" \ + "swc2 $18, 0( %1 );" \ + "swc2 $19, 0( %2 );" \ + : \ + : "r"( r0 ), "r"( r1 ), "r"( r2 ) \ + : "memory" ) + +#define gte_stsz4( r0, r1, r2, r3 ) __asm__ volatile ( \ + "swc2 $16, 0( %0 );" \ + "swc2 $17, 0( %1 );" \ + "swc2 $18, 0( %2 );" \ + "swc2 $19, 0( %3 );" \ + : \ + : "r"( r0 ), "r"( r1 ), "r"( r2 ), "r"( r3 ) \ + : "memory" ) + +#define gte_stsz3c( r0 ) __asm__ volatile ( \ + "swc2 $17, 0( %0 );" \ + "swc2 $18, 4( %0 );" \ + "swc2 $19, 8( %0 );" \ + : \ + : "r"( r0 ) \ + : "memory" ) + +#define gte_stsz4c( r0 ) __asm__ volatile ( \ + "swc2 $16, 0( %0 );" \ + "swc2 $17, 4( %0 );" \ + "swc2 $18, 8( %0 );" \ + "swc2 $19, 12( %0 );" \ + : \ + : "r"( r0 ) \ + : "memory" ) + +#define gte_stszotz( r0 ) __asm__ volatile ( \ + "mfc2 $12, $19;" \ + "nop;" \ + "sra $12, $12, 2;" \ + "sw $12, 0( %0 );" \ + : \ + : "r"( r0 ) \ + : "$12", "memory" ) + #define gte_stotz( r0 ) __asm__ volatile ( \ "swc2 $7, 0( %0 );" \ : \ - : "r"( r0 ) \ + : "r"( r0 ) \ : "memory" ) - + #define gte_stopz( r0 ) __asm__ volatile ( \ "swc2 $24, 0( %0 );" \ : \ : "r"( r0 ) \ : "memory" ) - + +#define gte_stlvl( r0 ) __asm__ volatile ( \ + "swc2 $9, 0( %0 );" \ + "swc2 $10, 4( %0 );" \ + "swc2 $11, 8( %0 );" \ + : \ + : "r"( r0 ) \ + : "memory" ) + +#define gte_stlvnl( r0 ) __asm__ volatile ( \ + "swc2 $25, 0( %0 );" \ + "swc2 $26, 4( %0 );" \ + "swc2 $27, 8( %0 );" \ + : \ + : "r"( r0 ) \ + : "memory" ) + +#define gte_stlvnl0( r0 ) __asm__ volatile ( \ + "swc2 $25, 0( %0 );" \ + : \ + : "r"( r0 ) \ + : "memory" ) + +#define gte_stlvnl1( r0 ) __asm__ volatile ( \ + "swc2 $26, 0( %0 );" \ + : \ + : "r"( r0 ) \ + : "memory" ) + +#define gte_stlvnl2( r0 ) __asm__ volatile ( \ + "swc2 $27, 0( %0 );" \ + : \ + : "r"( r0 ) \ + : "memory" ) + +#define gte_stsv( r0 ) __asm__ volatile ( \ + "mfc2 $12, $9;" \ + "mfc2 $13, $10;" \ + "mfc2 $14, $11;" \ + "sh $12, 0( %0 );" \ + "sh $13, 2( %0 );" \ + "sh $14, 4( %0 );" \ + : \ + : "r"( r0 ) \ + : "$12", "$13", "$14", "memory" ) + +#define gte_stclmv( r0 ) __asm__ volatile ( \ + "mfc2 $12, $9;" \ + "mfc2 $13, $10;" \ + "mfc2 $14, $11;" \ + "sh $12, 0( %0 );" \ + "sh $13, 6( %0 );" \ + "sh $14, 12( %0 );" \ + : \ + : "r"( r0 ) \ + : "$12", "$13", "$14", "memory" ) + +#define gte_stbv( r0 ) __asm__ volatile ( \ + "mfc2 $12, $9;" \ + "mfc2 $13, $10;" \ + "sb $12, 0( %0 );" \ + "sb $13, 1( %0 );" \ + : \ + : "r"( r0 ) \ + : "$12", "$13", "memory" ) + +#define gte_stcv( r0 ) __asm__ volatile ( \ + "mfc2 $12, $9;" \ + "mfc2 $13, $10;" \ + "mfc2 $14, $11;" \ + "sb $12, 0( %0 );" \ + "sb $13, 1( %0 );" \ + "sb $14, 2( %0 );" \ + : \ + : "r"( r0 ) \ + : "$12", "$13", "$14", "memory" ) + #define gte_strgb( r0 ) __asm__ volatile ( \ "swc2 $22, 0( %0 );" \ : \ : "r"( r0 ) \ : "memory" ) - + #define gte_strgb3( r0, r1, r2 ) __asm__ volatile ( \ "swc2 $20, 0( %0 );" \ "swc2 $21, 0( %1 );" \ "swc2 $22, 0( %2 );" \ : \ - : "r"( r0 ), "r"( r1 ), "r" ( r2 ) \ + : "r"( r0 ), "r"( r1 ), "r"( r2 ) \ : "memory" ) -#define gte_stsv( r0 ) __asm__ volatile ( \ - "mfc2 $t0, $9;" \ - "mfc2 $t1, $10;" \ - "mfc2 $t2, $11;" \ - "sh $t0, 0( %0 );" \ - "sh $t1, 2( %0 );" \ - "sh $t2, 4( %0 );" \ +#define gte_strgb3_g3( r0 ) __asm__ volatile ( \ + "swc2 $20, 4( %0 );" \ + "swc2 $21, 12( %0 );" \ + "swc2 $22, 20( %0 );" \ : \ : "r"( r0 ) \ : "memory" ) - -#define gte_stlvnl( r0 ) __asm__ volatile ( \ - "swc2 $25, 0( %0 );" \ - "swc2 $26, 4( %0 );" \ - "swc2 $27, 8( %0 );" \ + +#define gte_strgb3_gt3( r0 ) __asm__ volatile ( \ + "swc2 $20, 4( %0 );" \ + "swc2 $21, 16( %0 );" \ + "swc2 $22, 28( %0 );" \ : \ : "r"( r0 ) \ : "memory" ) - - -/* - * GTE operation macros (does not need a stupid tool such as dmpsx!) - */ - + +#define gte_strgb3_g4( r0 ) __asm__ volatile ( \ + "swc2 $20, 4( %0 );" \ + "swc2 $21, 12( %0 );" \ + "swc2 $22, 20( %0 );" \ + : \ + : "r"( r0 ) \ + : "memory" ) + +#define gte_strgb3_gt4( r0 ) __asm__ volatile ( \ + "swc2 $20, 4( %0 );" \ + "swc2 $21, 16( %0 );" \ + "swc2 $22, 28( %0 );" \ + : \ + : "r"( r0 ) \ + : "memory" ) + +#define gte_ReadGeomOffset( r0, r1 ) __asm__ volatile ( \ + "cfc2 $12, $24;" \ + "cfc2 $13, $25;" \ + "sra $12, $12, 16;" \ + "sra $13, $13, 16;" \ + "sw $12, 0( %0 );" \ + "sw $13, 0( %1 );" \ + : \ + : "r"( r0 ), "r"( r1 ) \ + : "$12", "$13", "memory" ) + +#define gte_ReadGeomScreen( r0 ) __asm__ volatile ( \ + "cfc2 $12, $26;" \ + "nop;" \ + "sw $12, 0( %0 );" \ + : \ + : "r"( r0 ) \ + : "$12", "memory" ) + +#define gte_ReadRotMatrix( r0 ) __asm__ volatile ( \ + "cfc2 $12, $0;" \ + "cfc2 $13, $1;" \ + "sw $12, 0( %0 );" \ + "sw $13, 4( %0 );" \ + "cfc2 $12, $2;" \ + "cfc2 $13, $3;" \ + "cfc2 $14, $4;" \ + "sw $12, 8( %0 );" \ + "sw $13, 12( %0 );" \ + "sw $14, 16( %0 );" \ + "cfc2 $12, $5;" \ + "cfc2 $13, $6;" \ + "cfc2 $14, $7;" \ + "sw $12, 20( %0 );" \ + "sw $13, 24( %0 );" \ + "sw $14, 28( %0 );" \ + : \ + : "r"( r0 ) \ + : "$12", "$13", "$14", "memory" ) + +#define gte_sttr( r0 ) __asm__ volatile ( \ + "cfc2 $12, $5;" \ + "cfc2 $13, $6;" \ + "cfc2 $14, $7;" \ + "sw $12, 0( %0 );" \ + "sw $13, 4( %0 );" \ + "sw $14, 8( %0 );" \ + : \ + : "r"( r0 ) \ + : "$12", "$13", "$14", "memory" ) + +#define gte_ReadLightMatrix( r0 ) __asm__ volatile ( \ + "cfc2 $12, $8;" \ + "cfc2 $13, $9;" \ + "sw $12, 0( %0 );" \ + "sw $13, 4( %0 );" \ + "cfc2 $12, $10;" \ + "cfc2 $13, $11;" \ + "cfc2 $14, $12;" \ + "sw $12, 8( %0 );" \ + "sw $13, 12( %0 );" \ + "sw $14, 16( %0 );" \ + "cfc2 $12, $13;" \ + "cfc2 $13, $14;" \ + "cfc2 $14, $15;" \ + "sw $12, 20( %0 );" \ + "sw $13, 24( %0 );" \ + "sw $14, 28( %0 );" \ + : \ + : "r"( r0 ) \ + : "$12", "$13", "$14", "memory" ) + +#define gte_ReadColorMatrix( r0 ) __asm__ volatile ( \ + "cfc2 $12, $16;" \ + "cfc2 $13, $17;" \ + "sw $12, 0( %0 );" \ + "sw $13, 4( %0 );" \ + "cfc2 $12, $18;" \ + "cfc2 $13, $19;" \ + "cfc2 $14, $20;" \ + "sw $12, 8( %0 );" \ + "sw $13, 12( %0 );" \ + "sw $14, 16( %0 );" \ + "cfc2 $12, $21;" \ + "cfc2 $13, $22;" \ + "cfc2 $14, $23;" \ + "sw $12, 20( %0 );" \ + "sw $13, 24( %0 );" \ + "sw $14, 28( %0 );" \ + : \ + : "r"( r0 ) \ + : "$12", "$13", "$14", "memory" ) + +#define gte_stlzc( r0 ) __asm__ volatile ( \ + "swc2 $31, 0( %0 );" \ + : \ + : "r"( r0 ) \ + : "memory" ) + +#define gte_stfc( r0 ) __asm__ volatile ( \ + "cfc2 $12, $21;" \ + "cfc2 $13, $22;" \ + "cfc2 $14, $23;" \ + "sw $12, 0( %0 );" \ + "sw $13, 4( %0 );" \ + "sw $14, 8( %0 );" \ + : \ + : "r"( r0 ) \ + : "$12", "$13", "$14", "memory" ) + +#define gte_mvlvtr() __asm__ volatile ( \ + "mfc2 $12, $25;" \ + "mfc2 $13, $26;" \ + "mfc2 $14, $27;" \ + "ctc2 $12, $5;" \ + "ctc2 $13, $6;" \ + "ctc2 $14, $7;" \ + : \ + : \ + : "$12", "$13", "$14" ) + +/*#define gte_nop() __asm__ volatile ( \ + "nop;" )*/ + +#define gte_subdvl( r0, r1, r2 ) __asm__ volatile ( \ + "lw $12, 0( %0 );" \ + "lw $13, 0( %1 );" \ + "mtc2 $12, $9;" \ + "mtc2 $13, $10;" \ + "sra $12, $12, 16;" \ + "sra $13, $13, 16;" \ + "subu $15, $12, $13;" \ + "mfc2 $12, $9;" \ + "mfc2 $13, $10;" \ + "sw $15, 4( %2 );" \ + "subu $12, $12, $13;" \ + "sw $12, 0( %2 );" \ + : \ + : "r"( r0 ), "r"( r1 ), "r"( r2 ) \ + : "$12", "$13", "$14", "$15", "memory" ) + +#define gte_subdvd( r0, r1, r2 ) __asm__ volatile ( \ + "lw $12, 0( %0 );" \ + "lw $13, 0( %1 );" \ + "mtc2 $12, $9;" \ + "mtc2 $13, $10;" \ + "sra $12, $12, 16;" \ + "sra $13, $13, 16;" \ + "subu $15, $12, $13;" \ + "mfc2 $12, $9;" \ + "mfc2 $13, $10;" \ + "sh $15, 2( %2 );" \ + "subu $12, $12, $13;" \ + "sh $12, 0( %2 );" \ + : \ + : "r"( r0 ), "r"( r1 ), "r"( r2 ) \ + : "$12", "$13", "$14", "$15", "memory" ) + +#define gte_adddvl( r0, r1, r2 ) __asm__ volatile ( \ + "lw $12, 0( %0 );" \ + "lw $13, 0( %1 );" \ + "mtc2 $12, $9;" \ + "mtc2 $13, $10;" \ + "sra $12, $12, 16;" \ + "sra $13, $13, 16;" \ + "addu $15, $12, $13;" \ + "mfc2 $12, $9;" \ + "mfc2 $13, $10;" \ + "sw $15, 4( %2 );" \ + "addu $12, $12, $13;" \ + "sw $12, 0( %2 );" \ + : \ + : "r"( r0 ), "r"( r1 ), "r"( r2 ) \ + : "$12", "$13", "$14", "$15", "memory" ) + +#define gte_adddvd( r0, r1, r2 ) __asm__ volatile ( \ + "lw $12, 0( %0 );" \ + "lw $13, 0( %1 );" \ + "mtc2 $12, $9;" \ + "mtc2 $13, $10;" \ + "sra $12, $12, 16;" \ + "sra $13, $13, 16;" \ + "addu $15, $12, $13;" \ + "mfc2 $12, $9;" \ + "mfc2 $13, $10;" \ + "sh $15, 2( %2 );" \ + "addu $12, $12, $13;" \ + "sh $12, 0( %2 );" \ + : \ + : "r"( r0 ), "r"( r1 ), "r"( r2 ) \ + : "$12", "$13", "$14", "$15", "memory" ) + +#define gte_FlipRotMatrixX() __asm__ volatile ( \ + "cfc2 $12, $0;" \ + "cfc2 $13, $1;" \ + "sll $14, $12, 16;" \ + "sra $14, $14, 16;" \ + "subu $14, $0, $14;" \ + "sra $15, $12, 16;" \ + "subu $15, $0, $15;" \ + "sll $15, $15, 16;" \ + "sll $14, $14, 16;" \ + "srl $14, $14, 16;" \ + "or $14, $14, $15;" \ + "ctc2 $14, $0;" \ + "sll $14, $13, 16;" \ + "sra $14, $14, 16;" \ + "subu $14, $0, $14;" \ + "sra $15, $13, 16;" \ + "sll $15, $15, 16;" \ + "sll $14, $14, 16;" \ + "srl $14, $14, 16;" \ + "or $14, $14, $15;" \ + "ctc2 $14, $1;" \ + : \ + : \ + : "$12", "$13", "$14", "$15" ) + +#define gte_FlipTRX() __asm__ volatile ( \ + "cfc2 $12, $5;" \ + "nop;" \ + "subu $12, $0, $12;" \ + "ctc2 $12, $5;" \ + : \ + : \ + : "$12" ) + +/* GTE operation macros */ + #define gte_rtps() __asm__ volatile ( \ "nop;" \ "nop;" \ @@ -340,169 +1053,405 @@ "nop;" \ "nop;" \ "cop2 0x0280030;" ) - -#define gte_nclip() __asm__ volatile ( \ + +#define gte_rt() __asm__ volatile ( \ "nop;" \ "nop;" \ - "cop2 0x1400006;" ) - -#define gte_avsz3() __asm__ volatile ( \ + "cop2 0x0480012;" ) + +#define gte_rtv0() __asm__ volatile ( \ "nop;" \ "nop;" \ - "cop2 0x158002D;" ) - -#define gte_avsz4() __asm__ volatile ( \ + "cop2 0x0486012;" ) + +#define gte_rtv1() __asm__ volatile ( \ "nop;" \ "nop;" \ - "cop2 0x168002E;" ) - -#define gte_sqr0() __asm__ volatile ( \ + "cop2 0x048E012;" ) + +#define gte_rtv2() __asm__ volatile ( \ "nop;" \ "nop;" \ - "cop2 0x0A00428;" ) - -#define gte_sqr12() __asm__ volatile ( \ + "cop2 0x0496012;" ) + +#define gte_rtir() __asm__ volatile ( \ "nop;" \ "nop;" \ - "cop2 0x0A80428;" ) - -#define gte_op0() __asm__ volatile ( \ + "cop2 0x049E012;" ) + +#define gte_rtir_sf0() __asm__ volatile ( \ "nop;" \ "nop;" \ - "cop2 0x170000C;" ) + "cop2 0x041E012;" ) -#define gte_op12() __asm__ volatile ( \ +#define gte_rtv0tr() __asm__ volatile ( \ "nop;" \ "nop;" \ - "cop2 0x178000C;" ) - -#define gte_ncs() __asm__ volatile ( \ + "cop2 0x0480012;" ) + +#define gte_rtv1tr() __asm__ volatile ( \ "nop;" \ "nop;" \ - "cop2 0x0C8041E;" ) - -#define gte_nct() __asm__ volatile ( \ + "cop2 0x0488012;" ) + +#define gte_rtv2tr() __asm__ volatile ( \ "nop;" \ "nop;" \ - "cop2 0x0D80420;" ) - -#define gte_nccs() __asm__ volatile ( \ + "cop2 0x0490012;" ) + +#define gte_rtirtr() __asm__ volatile ( \ "nop;" \ "nop;" \ - "cop2 0x108041B;" ) \ - -#define gte_ncct() __asm__ volatile ( \ + "cop2 0x0498012;" ) + +#define gte_rtv0bk() __asm__ volatile ( \ "nop;" \ "nop;" \ - "cop2 0x118043F;" ) - -#define gte_ncds() __asm__ volatile ( \ + "cop2 0x0482012;" ) + +#define gte_rtv1bk() __asm__ volatile ( \ "nop;" \ "nop;" \ - "cop2 0x0E80413;" ) - -#define gte_ncdt() __asm__ volatile ( \ + "cop2 0x048A012;" ) + +#define gte_rtv2bk() __asm__ volatile ( \ "nop;" \ "nop;" \ - "cop2 0x0F80416;" ) - -#define gte_cc() __asm__ volatile ( \ + "cop2 0x0492012;" ) + +#define gte_rtirbk() __asm__ volatile ( \ "nop;" \ "nop;" \ - "cop2 0x138041C;" ) - -#define gte_cdp() __asm__ volatile ( \ + "cop2 0x049A012;" ) + +#define gte_ll() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x04A6412;" ) + +#define gte_llv0() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x04A6012;" ) + +#define gte_llv1() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x04AE012;" ) + +#define gte_llv2() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x04B6012;" ) + +#define gte_llir() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x04BE012;" ) + +#define gte_llv0tr() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x04A0012;" ) + +#define gte_llv1tr() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x04A8012;" ) + +#define gte_llv2tr() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x04B0012;" ) + +#define gte_llirtr() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x04B8012;" ) + +#define gte_llv0bk() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x04A2012;" ) + +#define gte_llv1bk() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x04AA012;" ) + +#define gte_llv2bk() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x04B2012;" ) + +#define gte_llirbk() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x04BA012;" ) + + +#define gte_lc() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x04DA412;" ) + +#define gte_lcv0() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x04C6012;" ) + +#define gte_lcv1() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x04CE012;" ) + +#define gte_lcv2() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x04D6012;" ) + +#define gte_lcir() __asm__ volatile ( \ "nop;" \ "nop;" \ - "cop2 0x1280414;" ) - -#define gte_dcpl() __asm__ volatile ( \ + "cop2 0x04DE012;" ) + +#define gte_lcv0tr() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x04C0012;" ) + +#define gte_lcv1tr() __asm__ volatile ( \ + "nop;" \ "nop;" \ + "cop2 0x04C8012;" ) + +#define gte_lcv2tr() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x04D0012;" ) + +#define gte_lcirtr() __asm__ volatile ( \ "nop;" \ - "cop2 0x0680029;" ) - + "nop;" \ + "cop2 0x04D8012;" ) + +#define gte_lcv0bk() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x04C2012;" ) + +#define gte_lcv1bk() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x04CA012;" ) + +#define gte_lcv2bk() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x04D2012;" ) + +#define gte_lcirbk() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x04DA012;" ) + +#define gte_dpcl() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x0680029;" ) + #define gte_dpcs() __asm__ volatile ( \ "nop;" \ "nop;" \ - "cop2 0x0780010;" ) - + "cop2 0x0780010;" ) + #define gte_dpct() __asm__ volatile ( \ "nop;" \ "nop;" \ - "cop2 0x0180001;" ) + "cop2 0x0F8002A;" ) #define gte_intpl() __asm__ volatile ( \ "nop;" \ "nop;" \ - "cop2 0x0980011;" ) + "cop2 0x0980011;" ) -#define gte_gpf0() __asm__ volatile ( \ +#define gte_sqr12() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x0A80428;" ) + +#define gte_sqr0() __asm__ volatile ( \ "nop;" \ "nop;" \ - "cop2 0x190003D;" ) + "cop2 0x0A00428;" ) + +#define gte_ncs() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x0C8041E;" ) + +#define gte_nct() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x0D80420;" ) + +#define gte_ncds() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x0E80413;" ) + +#define gte_ncdt() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x0F80416;" ) + +#define gte_nccs() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x0108041B;" ) + +#define gte_ncct() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x0118043F;" ) + +#define gte_cdp() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x01280414;" ) + +#define gte_cc() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x0138041C;" ) + +#define gte_nclip() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x01400006;" ) + +#define gte_avsz3() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x0158002D;" ) + +#define gte_avsz4() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x0168002E;" ) + +#define gte_op12() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x0178000C;" ) + +#define gte_op0() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x0170000C;" ) #define gte_gpf12() __asm__ volatile ( \ "nop;" \ "nop;" \ - "cop2 0x198003D;" ) - -#define gte_gpl0() __asm__ volatile ( \ + "cop2 0x0198003D;" ) + +#define gte_gpf0() __asm__ volatile ( \ "nop;" \ "nop;" \ - "cop2 0x1A0003E;" ) + "cop2 0x0190003D;" ) #define gte_gpl12() __asm__ volatile ( \ "nop;" \ "nop;" \ - "cop2 0x1A8003E;" ) + "cop2 0x01A8003E;" ) + +#define gte_gpl0() __asm__ volatile ( \ + "nop;" \ + "nop;" \ + "cop2 0x01A0003E;" ) #define gte_mvmva_core( r0 ) __asm__ volatile ( \ "nop;" \ "nop;" \ - "cop2 %0" \ + "cop2 %0;" \ : \ : "g"( r0 ) ) - + #define gte_mvmva(sf, mx, v, cv, lm) gte_mvmva_core( 0x0400012 | \ ((sf)<<19) | ((mx)<<17) | ((v)<<15) | ((cv)<<13) | ((lm)<<10) ) - - -/* - * GTE operation macros without leading nops - * - * Checking assembler output when using these is advised. - */ + +/* GTE operation macros without leading nops */ -#define gte_rtps_b() __asm__ volatile ( "cop2 0x0180001;" ) -#define gte_rtpt_b() __asm__ volatile ( "cop2 0x0280030;" ) -#define gte_nclip_b() __asm__ volatile ( "cop2 0x1400006;" ) -#define gte_avsz3_b() __asm__ volatile ( "cop2 0x158002D;" ) -#define gte_avsz4_b() __asm__ volatile ( "cop2 0x168002E;" ) -#define gte_sqr0_b() __asm__ volatile ( "cop2 0x0A00428;" ) -#define gte_sqr12_b() __asm__ volatile ( "cop2 0x0A80428;" ) -#define gte_op0_b() __asm__ volatile ( "cop2 0x170000C;" ) -#define gte_op12_b() __asm__ volatile ( "cop2 0x178000C;" ) -#define gte_ncs_b() __asm__ volatile ( "cop2 0x0C8041E;" ) -#define gte_nct_b() __asm__ volatile ( "cop2 0x0D80420;" ) -#define gte_nccs_b() __asm__ volatile ( "cop2 0x108041B;" ) -#define gte_ncct_b() __asm__ volatile ( "cop2 0x118043F;" ) -#define gte_ncds_b() __asm__ volatile ( "cop2 0x0E80413;" ) -#define gte_ncdt_b() __asm__ volatile ( "cop2 0x0F80416;" ) -#define gte_cc_b() __asm__ volatile ( "cop2 0x138041C;" ) -#define gte_cdp_b() __asm__ volatile ( "cop2 0x1280414;" ) -#define gte_dcpl_b() __asm__ volatile ( "cop2 0x0680029;" ) -#define gte_dpcs_b() __asm__ volatile ( "cop2 0x0780010;" ) -#define gte_dpct_b() __asm__ volatile ( "cop2 0x0180001;" ) -#define gte_intpl_b() __asm__ volatile ( "cop2 0x0980011;" ) -#define gte_gpf0_b() __asm__ volatile ( "cop2 0x190003D;" ) -#define gte_gpf12_b() __asm__ volatile ( "cop2 0x198003D;" ) -#define gte_gpl0_b() __asm__ volatile ( "cop2 0x1A0003E;" ) -#define gte_gpl12_b() __asm__ volatile ( "cop2 0x1A8003E;" ) +#define gte_rtps_b() __asm__ volatile ( "cop2 0x0180001;" ) +#define gte_rtpt_b() __asm__ volatile ( "cop2 0x0280030;" ) +#define gte_rt_b() __asm__ volatile ( "cop2 0x0480012;" ) +#define gte_rtv0_b() __asm__ volatile ( "cop2 0x0486012;" ) +#define gte_rtv1_b() __asm__ volatile ( "cop2 0x048E012;" ) +#define gte_rtv2_b() __asm__ volatile ( "cop2 0x0496012;" ) +#define gte_rtir_b() __asm__ volatile ( "cop2 0x049E012;" ) +#define gte_rtir_sf0_b() __asm__ volatile ( "cop2 0x041E012;" ) +#define gte_rtv0tr_b() __asm__ volatile ( "cop2 0x0480012;" ) +#define gte_rtv1tr_b() __asm__ volatile ( "cop2 0x0488012;" ) +#define gte_rtv2tr_b() __asm__ volatile ( "cop2 0x0490012;" ) +#define gte_rtirtr_b() __asm__ volatile ( "cop2 0x0498012;" ) +#define gte_rtv0bk_b() __asm__ volatile ( "cop2 0x0482012;" ) +#define gte_rtv1bk_b() __asm__ volatile ( "cop2 0x048A012;" ) +#define gte_rtv2bk_b() __asm__ volatile ( "cop2 0x0492012;" ) +#define gte_rtirbk_b() __asm__ volatile ( "cop2 0x049A012;" ) +#define gte_ll_b() __asm__ volatile ( "cop2 0x04A6412;" ) +#define gte_llv0_b() __asm__ volatile ( "cop2 0x04A6012;" ) +#define gte_llv1_b() __asm__ volatile ( "cop2 0x04AE012;" ) +#define gte_llv2_b() __asm__ volatile ( "cop2 0x04B6012;" ) +#define gte_llir_b() __asm__ volatile ( "cop2 0x04BE012;" ) +#define gte_llv0tr_b() __asm__ volatile ( "cop2 0x04A0012;" ) +#define gte_llv1tr_b() __asm__ volatile ( "cop2 0x04A8012;" ) +#define gte_llv2tr_b() __asm__ volatile ( "cop2 0x04B0012;" ) +#define gte_llirtr_b() __asm__ volatile ( "cop2 0x04B8012;" ) +#define gte_llv0bk_b() __asm__ volatile ( "cop2 0x04A2012;" ) +#define gte_llv1bk_b() __asm__ volatile ( "cop2 0x04AA012;" ) +#define gte_llv2bk_b() __asm__ volatile ( "cop2 0x04B2012;" ) +#define gte_llirbk_b() __asm__ volatile ( "cop2 0x04BA012;" ) +#define gte_lc_b() __asm__ volatile ( "cop2 0x04DA412;" ) +#define gte_lcv0_b() __asm__ volatile ( "cop2 0x04C6012;" ) +#define gte_lcv1_b() __asm__ volatile ( "cop2 0x04CE012;" ) +#define gte_lcv2_b() __asm__ volatile ( "cop2 0x04D6012;" ) +#define gte_lcir_b() __asm__ volatile ( "cop2 0x04DE012;" ) +#define gte_lcv0tr_b() __asm__ volatile ( "cop2 0x04C0012;" ) +#define gte_lcv1tr_b() __asm__ volatile ( "cop2 0x04C8012;" ) +#define gte_lcv2tr_b() __asm__ volatile ( "cop2 0x04D0012;" ) +#define gte_lcirtr_b() __asm__ volatile ( "cop2 0x04D8012;" ) +#define gte_lcv0bk_b() __asm__ volatile ( "cop2 0x04C2012;" ) +#define gte_lcv1bk_b() __asm__ volatile ( "cop2 0x04CA012;" ) +#define gte_lcv2bk_b() __asm__ volatile ( "cop2 0x04D2012;" ) +#define gte_lcirbk_b() __asm__ volatile ( "cop2 0x04DA012;" ) +#define gte_dpcl_b() __asm__ volatile ( "cop2 0x0680029;" ) +#define gte_dpcs_b() __asm__ volatile ( "cop2 0x0780010;" ) +#define gte_dpct_b() __asm__ volatile ( "cop2 0x0F8002A;" ) +#define gte_intpl_b() __asm__ volatile ( "cop2 0x0980011;" ) +#define gte_sqr12_b() __asm__ volatile ( "cop2 0x0A80428;" ) +#define gte_sqr0_b() __asm__ volatile ( "cop2 0x0A00428;" ) +#define gte_ncs_b() __asm__ volatile ( "cop2 0x0C8041E;" ) +#define gte_nct_b() __asm__ volatile ( "cop2 0x0D80420;" ) +#define gte_ncds_b() __asm__ volatile ( "cop2 0x0E80413;" ) +#define gte_ncdt_b() __asm__ volatile ( "cop2 0x0F80416;" ) +#define gte_nccs_b() __asm__ volatile ( "cop2 0x0108041B;" ) +#define gte_ncct_b() __asm__ volatile ( "cop2 0x0118043F;" ) +#define gte_cdp_b() __asm__ volatile ( "cop2 0x01280414;" ) +#define gte_cc_b() __asm__ volatile ( "cop2 0x0138041C;" ) +#define gte_nclip_b() __asm__ volatile ( "cop2 0x01400006;" ) +#define gte_avsz3_b() __asm__ volatile ( "cop2 0x0158002D;" ) +#define gte_avsz4_b() __asm__ volatile ( "cop2 0x0168002E;" ) +#define gte_op12_b() __asm__ volatile ( "cop2 0x0178000C;" ) +#define gte_op0_b() __asm__ volatile ( "cop2 0x0170000C;" ) +#define gte_gpf12_b() __asm__ volatile ( "cop2 0x0198003D;" ) +#define gte_gpf0_b() __asm__ volatile ( "cop2 0x0190003D;" ) +#define gte_gpl12_b() __asm__ volatile ( "cop2 0x01A8003E;" ) +#define gte_gpl0_b() __asm__ volatile ( "cop2 0x01A0003E;" ) #define gte_mvmva_core_b( r0 ) __asm__ volatile ( \ - "cop2 %0" \ + "cop2 %0;" \ : \ - : "g"( r0 ) ) + : "g"( r0 ) ) #define gte_mvmva_b(sf, mx, v, cv, lm) gte_mvmva_core_b( 0x0400012 | \ ((sf)<<19) | ((mx)<<17) | ((v)<<15) | ((cv)<<13) | ((lm)<<10) ) - -#endif // _INLINE_C_H
\ No newline at end of file + +#endif // _INLINE_C_H diff --git a/libpsn00b/include/inline_s.h b/libpsn00b/include/inline_s.inc index 68e0d07..68e0d07 100644 --- a/libpsn00b/include/inline_s.h +++ b/libpsn00b/include/inline_s.inc diff --git a/libpsn00b/include/lzp/lzp.h b/libpsn00b/include/lzp/lzp.h index cfeeb72..456de02 100644 --- a/libpsn00b/include/lzp/lzp.h +++ b/libpsn00b/include/lzp/lzp.h @@ -16,7 +16,7 @@ #ifndef _LZPACK_H #define _LZPACK_H -#include <sys/types.h> +#include <stdint.h> #ifdef _WIN32 #include <windows.h> #endif @@ -64,9 +64,9 @@ typedef struct { //! File ID (must always be 'LZP') - char id[3]; + char id[3]; //! File count - u_char numFiles; + uint8_t numFiles; } LZP_HEAD; @@ -74,15 +74,15 @@ typedef struct { typedef struct { //! File name - char fileName[16]; + char fileName[16]; //! CRC32 checksum of file - u_int crc; + uint32_t crc; //! Original size of file in bytes - u_int fileSize; + uint32_t fileSize; //! Compressed size of file - u_int packedSize; + uint32_t packedSize; //! File data offset - u_int offset; + uint32_t offset; } LZP_FILE; @@ -162,7 +162,7 @@ void lzResetHashSizes(); * * \returns CRC16 hash of specified buffer. */ -unsigned short lzCRC16(const void* buff, int bytes, unsigned short crc); +uint16_t lzCRC16(const void* buff, int bytes, uint16_t crc); /*! Calculates a CRC32 hash of the specified buffer. * @@ -172,7 +172,7 @@ unsigned short lzCRC16(const void* buff, int bytes, unsigned short crc); * * \returns CRC32 hash of specified buffer. */ -unsigned int lzCRC32(const void* buff, int bytes, unsigned int crc); +uint32_t lzCRC32(const void* buff, int bytes, uint32_t crc); /*! @} */ diff --git a/libpsn00b/include/lzp/lzqlp.h b/libpsn00b/include/lzp/lzqlp.h index 5b70b40..32ce0d7 100644 --- a/libpsn00b/include/lzp/lzqlp.h +++ b/libpsn00b/include/lzp/lzqlp.h @@ -1,7 +1,7 @@ #ifndef _QLP_H #define _QLP_H -#include <sys/types.h> +#include <stdint.h> #ifdef _WIN32 #include <windows.h> #endif @@ -13,14 +13,14 @@ #define PACK_ERR_READ_FAULT -4 typedef struct { - char id[3]; - u_char numfiles; + char id[3]; + uint8_t numfiles; } QLP_HEAD; typedef struct { - char name[16]; - u_int size; - u_int offs; + char name[16]; + uint32_t size; + uint32_t offs; } QLP_FILE; int qlpFileCount(const QLP_HEAD* qlpfile); diff --git a/libpsn00b/include/psxapi.h b/libpsn00b/include/psxapi.h index 1298d29..5d1097e 100644 --- a/libpsn00b/include/psxapi.h +++ b/libpsn00b/include/psxapi.h @@ -1,5 +1,15 @@ -#ifndef __PSXAPI__ -#define __PSXAPI__ +/* + * PSn00bSDK kernel API library + * (C) 2019-2022 Lameguy64, spicyjpeg - MPL licensed + */ + +#ifndef __PSXAPI_H +#define __PSXAPI_H + +#include <stdint.h> +#include <stddef.h> + +/* Definitions */ #define DescHW 0xf0000000 #define DescSW 0xf4000000 @@ -32,29 +42,31 @@ #define RCntMdFR 0x0000 #define RCntMdGATE 0x0010 +/* Structure definitions */ + typedef struct { // Thread control block - int status; - int mode; + int status; + int mode; union { - unsigned int reg[37]; + uint32_t reg[37]; struct { - unsigned int zero, at; - unsigned int v0, v1; - unsigned int a0, a1, a2, a3; - unsigned int t0, t1, t2, t3, t4, t5, t6, t7; - unsigned int s0, s1, s2, s3, s4, s5, s6, s7; - unsigned int t8, t9; - unsigned int k0, k1; - unsigned int gp, sp, fp, ra; - - unsigned int cop0r14; - unsigned int hi; - unsigned int lo; - unsigned int cop0r12; - unsigned int cop0r13; + uint32_t zero, at; + uint32_t v0, v1; + uint32_t a0, a1, a2, a3; + uint32_t t0, t1, t2, t3, t4, t5, t6, t7; + uint32_t s0, s1, s2, s3, s4, s5, s6, s7; + uint32_t t8, t9; + uint32_t k0, k1; + uint32_t gp, sp, fp, ra; + + uint32_t cop0r14; + uint32_t hi; + uint32_t lo; + uint32_t cop0r12; + uint32_t cop0r13; }; }; - int _reserved[9]; + int _reserved[9]; } TCB; typedef struct { // Process control block @@ -85,17 +97,17 @@ typedef struct { // Device control block } DCB; typedef struct { // File control block - int status; - unsigned int diskid; - void *trns_addr; - unsigned int trns_len; - unsigned int filepos; - unsigned int flags; - unsigned int lasterr; - DCB *dcb; - unsigned int filesize; - unsigned int lba; - unsigned int fcbnum; + int status; + uint32_t diskid; + void *trns_addr; + uint32_t trns_len; + uint32_t filepos; + uint32_t flags; + uint32_t lasterr; + DCB *dcb; + uint32_t filesize; + uint32_t lba; + uint32_t fcbnum; } FCB; struct DIRENTRY { // Directory entry @@ -108,34 +120,31 @@ struct DIRENTRY { // Directory entry }; struct EXEC { - unsigned int pc0; - unsigned int gp0; - unsigned int t_addr; - unsigned int t_size; - unsigned int d_addr; - unsigned int d_size; - unsigned int b_addr; - unsigned int b_size; - unsigned int s_addr; - unsigned int s_size; - unsigned int sp,fp,rp,ret,base; + uint32_t pc0, gp0; + uint32_t t_addr, t_size; + uint32_t d_addr, d_size; + uint32_t b_addr, b_size; + uint32_t s_addr, s_size; + uint32_t sp, fp, rp, ret, base; }; struct JMP_BUF { - unsigned int ra, sp, fp; - unsigned int s0, s1, s2, s3, s4, s5, s6, s7; - unsigned int gp; + uint32_t ra, sp, fp; + uint32_t s0, s1, s2, s3, s4, s5, s6, s7; + uint32_t gp; }; // Not recommended to use these functions to install IRQ handlers typedef struct { - unsigned int* next; - unsigned int* func2; - unsigned int* func1; - unsigned int pad; + uint32_t *next; + uint32_t *func2; + uint32_t *func1; + int _reserved; } INT_RP; +/* API */ + #ifdef __cplusplus extern "C" { #endif @@ -143,30 +152,27 @@ extern "C" { void SysEnqIntRP(int pri, INT_RP *rp); void SysDeqIntRP(int pri, INT_RP *rp); -// Event handler stuff - -int OpenEvent(unsigned int cl, int spec, int mode, void (*func)()); -int CloseEvent(int ev_desc); -int EnableEvent(int ev_desc); -int DisableEvent(int ev_desc); - -// BIOS file functions +int OpenEvent(uint32_t cl, uint32_t spec, int mode, void (*func)()); +int CloseEvent(int event); +int WaitEvent(int event); +int TestEvent(int event); +int EnableEvent(int event); +int DisableEvent(int event); +void DeliverEvent(uint32_t cl, uint32_t spec); +void UnDeliverEvent(uint32_t cl, uint32_t spec); int open(const char *name, int mode); int close(int fd); -int seek(int fd, unsigned int offset, int mode); -int read(int fd, char *buff, unsigned int len); -int write(int fd, const char *buff, unsigned int len); +int seek(int fd, uint32_t offset, int mode); +int read(int fd, uint8_t *buff, size_t len); +int write(int fd, const uint8_t *buff, size_t len); int ioctl(int fd, int cmd, int arg); struct DIRENTRY *firstfile(const char *wildcard, struct DIRENTRY *entry); struct DIRENTRY *nextfile(struct DIRENTRY *entry); int erase(const char *name); int chdir(const char *path); -//#define delete( p ) erase( p ) // May conflict with delete operator in C++ -#define cd( p ) chdir( p ) // For compatibility - -// BIOS device functions +//#define cd(p) chdir(p) int AddDev(DCB *dcb); int DelDev(const char *name); @@ -175,18 +181,17 @@ void AddDummyTty(void); void EnterCriticalSection(void); void ExitCriticalSection(void); +void SwEnterCriticalSection(void); +void SwExitCriticalSection(void); -// BIOS CD functions void _InitCd(void); void _96_init(void); void _96_remove(void); -// BIOS pad functions -void InitPAD(char *buff1, int len1, char *buff2, int len2); +void InitPAD(uint8_t *buff1, int len1, uint8_t *buff2, int len2); void StartPAD(void); void StopPAD(void); -// BIOS memory card functions void InitCARD(int pad_enable); void StartCARD(void); void StopCARD(void); @@ -198,32 +203,32 @@ int _card_status(int chan); int _card_wait(int chan); int _card_clear(int chan); int _card_chan(void); -int _card_read(int chan, int sector, unsigned char *buf); -int _card_write(int chan, int sector, unsigned char *buf); +int _card_read(int chan, int sector, uint8_t *buf); +int _card_write(int chan, int sector, uint8_t *buf); void _new_card(void); -// Timers -int SetRCnt(int spec, unsigned short target, int mode); +int SetRCnt(int spec, uint16_t target, int mode); int GetRCnt(int spec); int StartRCnt(int spec); int StopRCnt(int spec); int ResetRCnt(int spec); -// BIOS IRQ acknowledge control void ChangeClearPAD(int mode); void ChangeClearRCnt(int t, int m); -// Executable functions +uint32_t OpenTh(uint32_t (*func)(), uint32_t sp, uint32_t gp); +int CloseTh(uint32_t thread); +int ChangeTh(uint32_t thread); + int Exec(struct EXEC *exec, int argc, char **argv); void FlushCache(void); -// BIOS setjmp functions void b_setjmp(struct JMP_BUF *buf); -void b_longjmp(struct JMP_BUF *buf, int param); +void b_longjmp(const struct JMP_BUF *buf, int param); void SetDefaultExitFromException(void); -void SetCustomExitFromException(struct JMP_BUF *buf); +void SetCustomExitFromException(const struct JMP_BUF *buf); +void ReturnFromException(void); -// Misc functions int GetSystemInfo(int index); void *GetB0Table(void); void *GetC0Table(void); diff --git a/libpsn00b/include/psxcd.h b/libpsn00b/include/psxcd.h index 3336963..03ee792 100644 --- a/libpsn00b/include/psxcd.h +++ b/libpsn00b/include/psxcd.h @@ -1,7 +1,12 @@ -#ifndef _LIBPSXCD_H -#define _LIBPSXCD_H +/* + * PSn00bSDK CD-ROM drive library + * (C) 2019-2022 Lameguy64, spicyjpeg - MPL licensed + */ -#include <sys/types.h> +#ifndef __PSXCD_H +#define __PSXCD_H + +#include <stdint.h> /* * CD-ROM control commands @@ -74,18 +79,18 @@ #define CdlIsoInvalidFs 0x03 #define CdlIsoLidOpen 0x04 -#define btoi(b) ((b)/16*10+(b)%16) /* Convert BCD value to integer */ -#define itob(i) ((i)/10*16+(i)%10) /* Convert integer to BCD value */ +#define btoi(b) ((b)/16*10+(b)%16) /* Convert BCD value to integer */ +#define itob(i) ((i)/10*16+(i)%10) /* Convert integer to BCD value */ /* * CD-ROM disc location struct */ typedef struct _CdlLOC { - u_char minute; - u_char second; - u_char sector; - u_char track; + uint8_t minute; + uint8_t second; + uint8_t sector; + uint8_t track; } CdlLOC; /* @@ -93,10 +98,10 @@ typedef struct _CdlLOC */ typedef struct _CdlATV { - u_char val0; /* L -> SPU L */ - u_char val1; /* L -> SPU R */ - u_char val2; /* R -> SPU R */ - u_char val3; /* R -> SPU L */ + uint8_t val0; /* L -> SPU L */ + uint8_t val1; /* L -> SPU R */ + uint8_t val2; /* R -> SPU R */ + uint8_t val3; /* R -> SPU L */ } CdlATV; /* @@ -104,68 +109,68 @@ typedef struct _CdlATV */ typedef struct _CdlFILE { - CdlLOC pos; - u_long size; - char name[16]; + CdlLOC pos; + uint32_t size; + char name[16]; } CdlFILE; typedef struct _CdlFILTER { - u_char file; - u_char chan; - u_short pad; + uint8_t file; + uint8_t chan; + uint16_t pad; } CdlFILTER; /* Directory query context */ typedef void* CdlDIR; /* Data callback */ -typedef void (*CdlCB)(int, u_char *); +typedef void (*CdlCB)(int, uint8_t *); #ifdef __cplusplus extern "C" { #endif -int CdInit(void); +int CdInit(void); -CdlLOC* CdIntToPos(int i, CdlLOC *p); -int CdPosToInt(CdlLOC *p); -int CdGetToc(CdlLOC *toc); +CdlLOC* CdIntToPos(int i, CdlLOC *p); +int CdPosToInt(CdlLOC *p); +int CdGetToc(CdlLOC *toc); -int CdControl(u_char com, const void *param, u_char *result); -int CdControlB(u_char com, const void *param, u_char *result); -int CdControlF(u_char com, const void *param); -int CdSync(int mode, u_char *result); -u_long CdSyncCallback(CdlCB func); +int CdControl(uint8_t com, const void *param, uint8_t *result); +int CdControlB(uint8_t com, const void *param, uint8_t *result); +int CdControlF(uint8_t com, const void *param); +int CdSync(int mode, uint8_t *result); +uint32_t CdSyncCallback(CdlCB func); -long CdReadyCallback(CdlCB func); -int CdGetSector(void *madr, int size); +long CdReadyCallback(CdlCB func); +int CdGetSector(void *madr, int size); CdlFILE* CdSearchFile(CdlFILE *loc, const char *filename); -int CdRead(int sectors, u_long *buf, int mode); -int CdReadSync(int mode, u_char *result); -u_long CdReadCallback(CdlCB func); +int CdRead(int sectors, uint32_t *buf, int mode); +int CdReadSync(int mode, uint8_t *result); +uint32_t CdReadCallback(CdlCB func); -int CdStatus(void); -int CdMode(void); +int CdStatus(void); +int CdMode(void); -int CdMix(CdlATV *vol); +int CdMix(CdlATV *vol); /* ORIGINAL CODE */ -CdlDIR* CdOpenDir(const char* path); -int CdReadDir(CdlDIR* dir, CdlFILE* file); -void CdCloseDir(CdlDIR* dir); +CdlDIR* CdOpenDir(const char* path); +int CdReadDir(CdlDIR* dir, CdlFILE* file); +void CdCloseDir(CdlDIR* dir); -int CdGetVolumeLabel(char* label); +int CdGetVolumeLabel(char* label); -long* CdAutoPauseCallback(void(*func)()); -int CdIsoError(); +long* CdAutoPauseCallback(void(*func)()); +int CdIsoError(); -int CdLoadSession(int session); +int CdLoadSession(int session); #ifdef __cplusplus } #endif -#endif /* _LIBPSXCD_H */ +#endif diff --git a/libpsn00b/include/psxetc.h b/libpsn00b/include/psxetc.h index a55e593..24485d9 100644 --- a/libpsn00b/include/psxetc.h +++ b/libpsn00b/include/psxetc.h @@ -1,15 +1,25 @@ -#ifndef _PSXETC_H -#define _PSXETC_H +/* + * PSn00bSDK interrupt management library + * (C) 2019-2022 Lameguy64, spicyjpeg - MPL licensed + */ + +#ifndef __PSXETC_H +#define __PSXETC_H + +/* Public API */ #ifdef __cplusplus extern "C" { #endif -// Interrupt callback functions -void *DMACallback(int dma, void (*func)(void)); void *InterruptCallback(int irq, void (*func)(void)); -void *GetInterruptCallback(int irq); // Original -void RestartCallback(); +void *GetInterruptCallback(int irq); +void *DMACallback(int dma, void (*func)(void)); +void *GetDMACallback(int dma); + +int ResetCallback(void); +void RestartCallback(void); +void StopCallback(void); #ifdef __cplusplus } diff --git a/libpsn00b/include/psxgpu.h b/libpsn00b/include/psxgpu.h index f061219..0e7ec00 100644 --- a/libpsn00b/include/psxgpu.h +++ b/libpsn00b/include/psxgpu.h @@ -1,623 +1,519 @@ +/* + * PSn00bSDK GPU library + * (C) 2019-2022 Lameguy64, spicyjpeg - MPL licensed + */ + #ifndef __PSXGPU_H #define __PSXGPU_H -#include <sys/types.h> - -// Low-level display parameters for DISPENV_RAW. A leftover from prototyping -#define DISP_WIDTH_256 0 -#define DISP_WIDTH_320 1 -#define DISP_WIDTH_384 64 -#define DISP_WIDTH_512 2 -#define DISP_WIDTH_640 3 - -#define DISP_HEIGHT_LOW 0 // Could be 240 for NTSC, 256 for PAL -#define DISP_HEIGHT_HIGH 4 // Could be 480 for NTSC, 512 for PAL -#define DISP_INTERLACE 32 -#define DISP_24BIT_COLOR 16 -#define DISP_MODE_NTSC 0 -#define DISP_MODE_PAL 8 +#include <stdint.h> +#include <stddef.h> +/* Definitions */ -#define MODE_NTSC 0 -#define MODE_PAL 1 +typedef enum _GPU_DispFlags { + DISP_WIDTH_256 = 0, + DISP_WIDTH_320 = 1, + DISP_WIDTH_512 = 2, + DISP_WIDTH_640 = 3, + DISP_HEIGHT_HIGH = 1 << 2, + DISP_MODE_PAL = 1 << 3, + DISP_24BIT_COLOR = 1 << 4, + DISP_INTERLACE = 1 << 5, + DISP_WIDTH_384 = 1 << 6 +} GPU_DispFlags; +typedef enum _GPU_VideoMode { + MODE_NTSC = 0, + MODE_PAL = 1 +} GPU_VideoMode; -// Vector macros +/* Structure macros */ -#define setVector( v, _x, _y, _z ) \ +#define setVector(v, _x, _y, _z) \ (v)->vx = _x, (v)->vy = _y, (v)->vz = _z -#define setRECT( v, _x, _y, _w, _h ) \ +#define setRECT(v, _x, _y, _w, _h) \ (v)->x = _x, (v)->y = _y, (v)->w = _w, (v)->h = _h +#define setTPage(p, tp, abr, x, y) ((p)->tpage = getTPage(tp, abr, x, y)) +#define setClut(p, x, y) ((p)->clut = getClut(x, y)) -// Primitive macros - -#define setDrawTPage( p, dfe, dtd, tpage ) \ - ( (p)->code[0] = tpage|(dfe<<10)|(dtd<<9), \ - setlen( p, 1 ), setcode( p, 0xe1 ) ) - -/*#define setVram2Vram( p ) ( setlen( p, 8 ), setcode( p, 0x80 ), \ - (p)->nop[0] = 0, (p)->nop[1] = 0, (p)->nop[2] = 0, (p)->nop[3] = 0 )*/ - -/* - -#define setTPagePri2( p, dth, tp, abr, x, y ) \ - ( (p)->code[0] = getTPage( tp, abr, x, y )|(dth<<9), \ - setlen( p, 1 ), setcode( p, 0xe1 ) )*/ - -/* - * Set primitive attributes - */ -#define setTPage( p, tp, abr, x, y ) \ - ( (p)->tpage = getTPage( tp, abr, x, y ) ) - -#define setClut( p, x, y ) \ - ( (p)->clut = getClut(x, y) ) - - -/* - * Set primitive colors - */ -#define setRGB0( p, r, g, b ) ( (p)->r0 = r, (p)->g0 = g, (p)->b0 = b ) -#define setRGB1( p, r, g, b ) ( (p)->r1 = r, (p)->g1 = g, (p)->b1 = b ) -#define setRGB2( p, r, g, b ) ( (p)->r2 = r, (p)->g2 = g, (p)->b2 = b ) -#define setRGB3( p, r, g, b ) ( (p)->r3 = r, (p)->g3 = g, (p)->b3 = b ) - +#define setRGB0(p, r, g, b) ((p)->r0 = r, (p)->g0 = g, (p)->b0 = b) +#define setRGB1(p, r, g, b) ((p)->r1 = r, (p)->g1 = g, (p)->b1 = b) +#define setRGB2(p, r, g, b) ((p)->r2 = r, (p)->g2 = g, (p)->b2 = b) +#define setRGB3(p, r, g, b) ((p)->r3 = r, (p)->g3 = g, (p)->b3 = b) -/* - * Set primitive screen coordinates - */ -#define setXY0( p, _x0, _y0 ) \ +#define setXY0(p, _x0, _y0) \ (p)->x0 = _x0, (p)->y0 = _y0 -#define setXY2( p, _x0, _y0, _x1, _y1 ) \ +#define setXY2(p, _x0, _y0, _x1, _y1) \ (p)->x0 = _x0, (p)->y0 = _y0, \ (p)->x1 = _x1, (p)->y1 = _y1 - -#define setXY3( p, _x0, _y0, _x1, _y1, _x2, _y2 ) \ + +#define setXY3(p, _x0, _y0, _x1, _y1, _x2, _y2) \ (p)->x0 = _x0, (p)->y0 = _y0, \ (p)->x1 = _x1, (p)->y1 = _y1, \ (p)->x2 = _x2, (p)->y2 = _y2 -#define setXY4( p, _x0, _y0, _x1, _y1, _x2, _y2, _x3, _y3 ) \ +#define setXY4(p, _x0, _y0, _x1, _y1, _x2, _y2, _x3, _y3) \ (p)->x0 = _x0, (p)->y0 = _y0, \ (p)->x1 = _x1, (p)->y1 = _y1, \ (p)->x2 = _x2, (p)->y2 = _y2, \ (p)->x3 = _x3, (p)->y3 = _y3 -#define setWH( p, _w, _h ) \ +#define setWH(p, _w, _h) \ (p)->w = _w, (p)->h = _h -/* - * Set texture coordinates - */ -#define setUV0( p, _u0, _v0 ) \ +#define setXYWH(p, _x0, _y0, _w, _h) \ + (p)->x0 = _x0, (p)->y0 = _y0, \ + (p)->x1 = (_x0 + (_w)), (p)->y1 = _y0, \ + (p)->x2 = _x0, (p)->y2 = (_y0 + (_h)), \ + (p)->x3 = (_x0 + (_w)), (p)->y3 = (_y0 + (_h)) + +#define setUV0(p, _u0, _v0) \ (p)->u0 = _u0, (p)->v0 = _v0 -#define setUV3( p, _u0, _v0, _u1, _v1, _u2, _v2 ) \ - (p)->u0 = _u0, (p)->v0 = _v0, \ - (p)->u1 = _u1, (p)->v1 = _v1, \ +#define setUV3(p, _u0, _v0, _u1, _v1, _u2, _v2) \ + (p)->u0 = _u0, (p)->v0 = _v0, \ + (p)->u1 = _u1, (p)->v1 = _v1, \ (p)->u2 = _u2, (p)->v2 = _v2 -#define setUV4( p, _u0, _v0, _u1, _v1, _u2, _v2, _u3, _v3 ) \ - (p)->u0 = _u0, (p)->v0 = _v0, \ - (p)->u1 = _u1, (p)->v1 = _v1, \ - (p)->u2 = _u2, (p)->v2 = _v2, \ +#define setUV4(p, _u0, _v0, _u1, _v1, _u2, _v2, _u3, _v3) \ + (p)->u0 = _u0, (p)->v0 = _v0, \ + (p)->u1 = _u1, (p)->v1 = _v1, \ + (p)->u2 = _u2, (p)->v2 = _v2, \ (p)->u3 = _u3, (p)->v3 = _v3 -#define setUVWH( p, _u0, _v0, _w, _h ) \ - (p)->u0 = _u0, (p)->v0 = _v0, \ - (p)->u1 = _u0+(_w), (p)->v1 = _v0, \ - (p)->u2 = _u0, (p)->v2 = _v0+(_h), \ - (p)->u3 = _u0+(_w), (p)->v3 = _v0+(_h) - - -/* - * Primitive handling macros - */ -#define setlen( p, _len ) ( ((P_TAG*)(p))->len = (unsigned char)(_len) ) -#define setaddr( p, _addr ) ( ((P_TAG*)(p))->addr = (unsigned int)(_addr) ) -#define setcode( p, _code ) ( ((P_TAG*)(p))->code = (unsigned char)(_code) ) - -#define getlen( p ) ( ((P_TAG*)(p))->len ) -#define getaddr( p ) ( ((P_TAG*)(p))->addr ) -#define getcode( p ) ( ((P_TAG*)(p))->code ) - -#define nextPrim( p ) (void*)((((P_TAG*)(p))->addr)|0x80000000) -#define isendprim( p ) ((((P_TAG*)(p))->addr)==0xffffff) - -#define addPrim( ot, p ) setaddr( p, getaddr( ot ) ), setaddr( ot, p ) -#define addPrims( ot, p0, p1 ) setaddr( p1, getaddr( ot ) ), setaddr( ot, p0 ) - -#define catPrim( p0, p1 ) setaddr( p0, p1 ) -#define termPrim( p ) setaddr( p, 0xffffff ) - -#define setSemiTrans( p, abe ) \ - ( (abe)?setcode( p, getcode( p )|0x2 ):setcode( p, getcode( p )&~0x2 ) ) - -#define setShadeTex( p, tge ) \ - ( (tge)?setcode( p, getcode( p )|0x1 ):setcode( p, getcode( p )&~0x1 ) ) - - -/* ORIGINAl CODE */ -#define setDrawMask( p, sb, mt ) \ - setlen( p, 1 ), (p)->code[0] = sb|(mt<<1), \ - setcode( p, 0xe6 ) - - -#define getTPage( tp, abr, x, y ) \ - ( (((x)&0x3ff)>>6) | (((y)>>8)<<4) | (((abr)&0x3)<<5) | (((tp)&0x3)<<7) ) - -#define getClut( x, y ) \ - ( ((y)<<6)|(((x)>>4)&0x3f) ) - - -/* - * Primitive initializers - */ -#define setPolyF3( p ) setlen( p, 4 ), setcode( p, 0x20 ) -#define setPolyFT3( p ) setlen( p, 7 ), setcode( p, 0x24 ) -#define setPolyG3( p ) setlen( p, 6 ), setcode( p, 0x30 ) -#define setPolyGT3( p ) setlen( p, 9 ), setcode( p, 0x34 ) - -#define setPolyF4( p ) setlen( p, 5 ), setcode( p, 0x28 ) -#define setPolyFT4( p ) setlen( p, 9 ), setcode( p, 0x2c ) -#define setPolyG4( p ) setlen( p, 8 ), setcode( p, 0x38 ) -#define setPolyGT4( p ) setlen( p, 12 ), setcode( p, 0x3c ) - -#define setSprt8( p ) setlen( p, 3 ), setcode( p, 0x74 ) -#define setSprt16( p ) setlen( p, 3 ), setcode( p, 0x7c ) -#define setSprt( p ) setlen( p, 4 ), setcode( p, 0x64 ) - -#define setTile1( p ) setlen( p, 2 ), setcode( p, 0x68 ) -#define setTile8( p ) setlen( p, 2 ), setcode( p, 0x70 ) -#define setTile16( p ) setlen( p, 2 ), setcode( p, 0x78 ) -#define setTile( p ) setlen( p, 3 ), setcode( p, 0x60 ) - -#define setLineF2( p ) setlen( p, 3 ), setcode( p, 0x40 ) -#define setLineG2( p ) setlen( p, 4 ), setcode( p, 0x50 ) - -#define setLineF3( p ) setlen( p, 5 ), setcode( p, 0x48 ), (p)->pad = 0x55555555 -#define setLineG3( p ) setlen( p, 7 ), setcode( p, 0x58 ), (p)->pad = 0x55555555, \ - (p)->p1 = 0, (p)->p2 = 0 - -#define setLineF4( p ) setlen( p, 6 ), setcode( p, 0x4c ), (p)->pad = 0x55555555 -#define setLineG4( p ) setlen( p, 9 ), setcode( p, 0x5c ), (p)->pad = 0x55555555, \ - (p)->p1 = 0, (p)->p2 = 0, (p)->p3 = 0 - -#define setFill( p ) setlen( p, 3 ), setcode( p, 0x02 ) - -#define setDrawOffset( p, _x, _y ) \ - setlen( p, 1 ), \ - (p)->code[0] = (_x&0x3FF)|((_y&0x3FF)<<11), \ - ((char*)(p)->code)[3] = 0xE5 - -#define setDrawArea( p, r ) \ - setlen( p, 2 ), \ - (p)->code[0] = ((r)->x&0x3FF)|(((r)->y&0x1FF)<<10), \ - (p)->code[1] = (((r)->x+(r)->w-1)&0x3FF)|((((r)->y+(r)->h-1)&0x1FF)<<10), \ - ((char*)&(p)->code[0])[3] = 0xE3, \ - ((char*)&(p)->code[1])[3] = 0xE4 - -#define setTexWindow( p, r ) \ - setlen( p, 1 ), \ - (p)->code[0] = ((r)->w&0x1F)|(((r)->h&0x1F)<<5)|(((r)->x&0x1F)<<10)|(((r)->y&0x1F)<<15), \ - ((char*)&(p)->code[0])[3] = 0xE2 - -/* - * Primitive definitions - */ -typedef struct _P_TAG -{ - unsigned addr:24; - unsigned len:8; - u_char r,g,b,code; +#define setUVWH(p, _u0, _v0, _w, _h) \ + (p)->u0 = _u0, (p)->v0 = _v0, \ + (p)->u1 = (_u0 + (_w)), (p)->v1 = _v0, \ + (p)->u2 = _u0, (p)->v2 = (_v0 + (_h)), \ + (p)->u3 = (_u0 + (_w)), (p)->v3 = (_v0 + (_h)) + +/* Primitive handling macros */ + +#define setlen(p, _len) (((P_TAG *) (p))->len = (uint8_t) (_len)) +#define setaddr(p, _addr) (((P_TAG *) (p))->addr = (uint32_t) (_addr)) +#define setcode(p, _code) (((P_TAG *) (p))->code = (uint8_t) (_code)) +#define getlen(p) (((P_TAG *) (p))->len) +#define getaddr(p) (((P_TAG *) (p))->addr) +#define getcode(p) (((P_TAG *) (p))->code) + +#define nextPrim(p) (void *) (0x80000000 | (((P_TAG *) (p))->addr)) +#define isendprim(p) ((((P_TAG *) (p))->addr) == 0xffffff) +#define addPrim(ot, p) setaddr(p, getaddr(ot)), setaddr(ot, p) +#define addPrims(ot, a, b) setaddr(b, getaddr(ot)), setaddr(ot, a) +#define catPrim(a, b) setaddr(a, b) +#define termPrim(p) setaddr(p, 0xffffff) + +#define setSemiTrans(p, abe) \ + ((abe) ? (getcode(p) |= 2) : (getcode(p) &= ~2)) + +#define setShadeTex(p, tge) \ + ((tge) ? (getcode(p) |= 1) : (getcode(p) &= ~1)) + +#define getTPage(tp, abr, x, y) \ + ((((x) & 0x3ff) >> 6) | (((y) >> 8) << 4) | (((abr) & 3) << 5) | (((tp) & 3) << 7)) + +#define getClut(x, y) (((y) << 6) | (((x) >> 4) & 0x3f)) + +/* Primitive initializer macros */ + +#define setPolyF3(p) setlen(p, 4), setcode(p, 0x20) +#define setPolyFT3(p) setlen(p, 7), setcode(p, 0x24) +#define setPolyG3(p) setlen(p, 6), setcode(p, 0x30) +#define setPolyGT3(p) setlen(p, 9), setcode(p, 0x34) +#define setPolyF4(p) setlen(p, 5), setcode(p, 0x28) +#define setPolyFT4(p) setlen(p, 9), setcode(p, 0x2c) +#define setPolyG4(p) setlen(p, 8), setcode(p, 0x38) +#define setPolyGT4(p) setlen(p, 12), setcode(p, 0x3c) +#define setSprt8(p) setlen(p, 3), setcode(p, 0x74) +#define setSprt16(p) setlen(p, 3), setcode(p, 0x7c) +#define setSprt(p) setlen(p, 4), setcode(p, 0x64) +#define setTile1(p) setlen(p, 2), setcode(p, 0x68) +#define setTile8(p) setlen(p, 2), setcode(p, 0x70) +#define setTile16(p) setlen(p, 2), setcode(p, 0x78) +#define setTile(p) setlen(p, 3), setcode(p, 0x60) +#define setLineF2(p) setlen(p, 3), setcode(p, 0x40) +#define setLineG2(p) setlen(p, 4), setcode(p, 0x50) +#define setLineF3(p) setlen(p, 5), setcode(p, 0x48), \ + (p)->pad = 0x55555555 +#define setLineG3(p) setlen(p, 7), setcode(p, 0x58), \ + (p)->pad = 0x55555555, (p)->p1 = 0, (p)->p2 = 0 +#define setLineF4(p) setlen(p, 6), setcode(p, 0x4c), \ + (p)->pad = 0x55555555 +#define setLineG4(p) setlen(p, 9), setcode(p, 0x5c), \ + (p)->pad = 0x55555555, (p)->p1 = 0, (p)->p2 = 0, (p)->p3 = 0 +#define setFill(p) setlen(p, 3), setcode(p, 0x02) +#define setVram2Vram(p) setlen(p, 8), setcode(p, 0x80), \ + (p)->pad[0] = 0, (p)->pad[1] = 0, (p)->pad[2] = 0, (p)->pad[3] = 0 + +#define setDrawTPage(p, dfe, dtd, tpage) \ + setlen(p, 1), \ + (p)->code[0] = 0xe1000000 | tpage | (dfe << 10) | (dtd << 9) + +#define setDrawOffset(p, _x, _y) \ + setlen(p, 1), \ + (p)->code[0] = 0xe5000000 | (_x & 0x3ff) | ((_y & 0x3ff) << 11) + +#define setDrawMask(p, sb, mt) \ + setlen(p, 1), \ + (p)->code[0] = 0xe6000000 | sb | (mt << 1) + +#define setDrawArea(p, r) \ + setlen(p, 2), \ + (p)->code[0] = 0xe3000000 | ((r)->x & 0x3ff) | (((r)->y & 0x1ff) << 10), \ + (p)->code[1] = 0xe4000000 | (((r)->x + (r)->w - 1) & 0x3ff) | ((((r)->y + (r)->h - 1) & 0x1ff) << 10) + +#define setTexWindow(p, r) \ + setlen(p, 1), \ + (p)->code[0] = 0xe2000000 | ((r)->w & 0x1f) | (((r)->h & 0x1f) << 5) | (((r)->x & 0x1f) << 10) | (((r)->y & 0x1f) << 15) + +/* Primitive structure definitions */ + +typedef struct _P_TAG { + uint32_t addr:24; + uint32_t len:8; + uint8_t r, g, b, code; } P_TAG; -/* - * Polygon primitive definitions - */ -typedef struct _POLY_F3 -{ - u_long tag; - u_char r0,g0,b0,code; - short x0,y0; - short x1,y1; - short x2,y2; +typedef struct _POLY_F3 { + uint32_t tag; + uint8_t r0, g0, b0, code; + int16_t x0, y0; + int16_t x1, y1; + int16_t x2, y2; } POLY_F3; -typedef struct _POLY_F4 -{ - u_long tag; - u_char r0,g0,b0,code; - short x0,y0; - short x1,y1; - short x2,y2; - short x3,y3; +typedef struct _POLY_F4 { + uint32_t tag; + uint8_t r0, g0, b0, code; + int16_t x0, y0; + int16_t x1, y1; + int16_t x2, y2; + int16_t x3, y3; } POLY_F4; -typedef struct _POLY_FT3 -{ - u_long tag; - u_char r0,g0,b0,code; - short x0,y0; - u_char u0,v0; - u_short clut; - short x1,y1; - u_char u1,v1; - u_short tpage; - short x2,y2; - u_char u2,v2; - u_short pad; +typedef struct _POLY_FT3 { + uint32_t tag; + uint8_t r0, g0, b0, code; + int16_t x0, y0; + uint8_t u0, v0; + uint16_t clut; + int16_t x1, y1; + uint8_t u1, v1; + uint16_t tpage; + int16_t x2, y2; + uint8_t u2, v2; + uint16_t pad; } POLY_FT3; -typedef struct _POLY_FT4 -{ - u_long tag; - u_char r0,g0,b0,code; - u_short x0,y0; - u_char u0,v0; - u_short clut; - short x1,y1; - u_char u1,v1; - u_short tpage; - short x2,y2; - u_char u2,v2; - u_short pad0; - short x3,y3; - u_char u3,v3; - u_short pad1; +typedef struct _POLY_FT4 { + uint32_t tag; + uint8_t r0, g0, b0, code; + uint16_t x0, y0; + uint8_t u0, v0; + uint16_t clut; + int16_t x1, y1; + uint8_t u1, v1; + uint16_t tpage; + int16_t x2, y2; + uint8_t u2, v2; + uint16_t pad0; + int16_t x3, y3; + uint8_t u3, v3; + uint16_t pad1; } POLY_FT4; -typedef struct _POLY_G3 -{ - u_long tag; - u_char r0,g0,b0,code; - short x0,y0; - u_char r1,g1,b1,pad0; - short x1,y1; - u_char r2,g2,b2,pad1; - short x2,y2; +typedef struct _POLY_G3 { + uint32_t tag; + uint8_t r0, g0, b0, code; + int16_t x0, y0; + uint8_t r1, g1, b1, pad0; + int16_t x1, y1; + uint8_t r2, g2, b2, pad1; + int16_t x2, y2; } POLY_G3; -typedef struct _POLY_G4 -{ - u_long tag; - u_char r0,g0,b0,code; - short x0,y0; - u_char r1,g1,b1,pad0; - short x1,y1; - u_char r2,g2,b2,pad1; - short x2,y2; - u_char r3,g3,b3,pad2; - short x3,y3; +typedef struct _POLY_G4 { + uint32_t tag; + uint8_t r0, g0, b0, code; + int16_t x0, y0; + uint8_t r1, g1, b1, pad0; + int16_t x1, y1; + uint8_t r2, g2, b2, pad1; + int16_t x2, y2; + uint8_t r3, g3, b3, pad2; + int16_t x3, y3; } POLY_G4; -typedef struct _POLY_GT3 -{ - u_long tag; - u_char r0,g0,b0,code; - short x0,y0; - u_char u0,v0; - u_short clut; - u_char r1,g1,b1,pad0; - short x1,y1; - u_char u1,v1; - u_short tpage; - u_char r2,g2,b2,pad1; - short x2,y2; - u_char u2,v2; - u_short pad2; +typedef struct _POLY_GT3 { + uint32_t tag; + uint8_t r0, g0, b0, code; + int16_t x0, y0; + uint8_t u0, v0; + uint16_t clut; + uint8_t r1, g1, b1, pad0; + int16_t x1, y1; + uint8_t u1, v1; + uint16_t tpage; + uint8_t r2, g2, b2, pad1; + int16_t x2, y2; + uint8_t u2, v2; + uint16_t pad2; } POLY_GT3; -typedef struct _POLY_GT4 -{ - u_long tag; - u_char r0,g0,b0,code; - short x0,y0; - u_char u0,v0; - u_short clut; - u_char r1,g1,b1,pad0; - short x1,y1; - u_char u1,v1; - u_short tpage; - u_char r2,g2,b2,pad1; - short x2,y2; - u_char u2,v2; - u_short pad2; - u_char r3,g3,b3,pad3; - short x3,y3; - u_char u3,v3; - u_short pad4; +typedef struct _POLY_GT4 { + uint32_t tag; + uint8_t r0, g0, b0, code; + int16_t x0, y0; + uint8_t u0, v0; + uint16_t clut; + uint8_t r1, g1, b1, pad0; + int16_t x1, y1; + uint8_t u1, v1; + uint16_t tpage; + uint8_t r2, g2, b2, pad1; + int16_t x2, y2; + uint8_t u2, v2; + uint16_t pad2; + uint8_t r3, g3, b3, pad3; + int16_t x3, y3; + uint8_t u3, v3; + uint16_t pad4; } POLY_GT4; -/* - * Line primitive definitions - */ -typedef struct _LINE_F2 -{ - u_long tag; - u_char r0,g0,b0,code; - short x0,y0; - short x1,y1; +typedef struct _LINE_F2 { + uint32_t tag; + uint8_t r0, g0, b0, code; + int16_t x0, y0; + int16_t x1, y1; } LINE_F2; -typedef struct _LINE_G2 -{ - u_long tag; - u_char r0,g0,b0,code; - short x0,y0; - u_char r1,g1,b1,p1; - short x1,y1; +typedef struct _LINE_G2 { + uint32_t tag; + uint8_t r0, g0, b0, code; + int16_t x0, y0; + uint8_t r1, g1, b1, p1; + int16_t x1, y1; } LINE_G2; -typedef struct _LINE_F3 -{ - u_long tag; - u_char r0,g0,b0,code; - short x0,y0; - short x1,y1; - short x2,y2; - u_long pad; /* actually a terminator for line loops */ +typedef struct _LINE_F3 { + uint32_t tag; + uint8_t r0, g0, b0, code; + int16_t x0, y0; + int16_t x1, y1; + int16_t x2, y2; + uint32_t pad; } LINE_F3; -typedef struct _LINE_G3 -{ - u_long tag; - u_char r0,g0,b0,code; - short x0,y0; - u_char r1,g1,b1,p1; - short x1,y1; - u_char r2,g2,b2,p2; - short x2,y2; - u_long pad; /* actually a terminator for line loops */ +typedef struct _LINE_G3 { + uint32_t tag; + uint8_t r0, g0, b0, code; + int16_t x0, y0; + uint8_t r1, g1, b1, p1; + int16_t x1, y1; + uint8_t r2, g2, b2, p2; + int16_t x2, y2; + uint32_t pad; } LINE_G3; -typedef struct _LINE_F4 -{ - u_long tag; - u_char r0,g0,b0,code; - short x0,y0; - short x1,y1; - short x2,y2; - short x3,y3; - u_long pad; +typedef struct _LINE_F4 { + uint32_t tag; + uint8_t r0, g0, b0, code; + int16_t x0, y0; + int16_t x1, y1; + int16_t x2, y2; + int16_t x3, y3; + uint32_t pad; } LINE_F4; -typedef struct _LINE_G4 -{ - u_long tag; - u_char r0,g0,b0,code; - short x0,y0; - u_char r1,g1,b1,p1; - short x1,y1; - u_char r2,g2,b2,p2; - short x2,y2; - u_char r3,g3,b3,p3; - short x3,y3; - u_long pad; +typedef struct _LINE_G4 { + uint32_t tag; + uint8_t r0, g0, b0, code; + int16_t x0, y0; + uint8_t r1, g1, b1, p1; + int16_t x1, y1; + uint8_t r2, g2, b2, p2; + int16_t x2, y2; + uint8_t r3, g3, b3, p3; + int16_t x3, y3; + uint32_t pad; } LINE_G4; -/* - * Tile and sprite primitive definitions - */ -typedef struct _TILE -{ - u_long tag; - u_char r0,g0,b0,code; - short x0,y0; - short w,h; +typedef struct _TILE { + uint32_t tag; + uint8_t r0, g0, b0, code; + int16_t x0, y0; + int16_t w, h; } TILE; -typedef struct _TILE_1 -{ - u_long tag; - u_char r0,g0,b0,code; - short x0,y0; -} TILE_1; - -typedef struct _TILE_8 -{ - u_long tag; - u_char r0,g0,b0,code; - short x0,y0; -} TILE_8; - -typedef struct _TILE_16 -{ - u_long tag; - u_char r0,g0,b0,code; - short x0,y0; -} TILE_16; - -/* - * Sprite primitive definitions - */ -typedef struct _SPRT -{ - u_long tag; - u_char r0,g0,b0,code; - short x0,y0; - u_char u0,v0; - u_short clut; - u_short w,h; +struct _TILE_FIXED { + uint32_t tag; + uint8_t r0, g0, b0, code; + int16_t x0, y0; +}; +typedef struct _TILE_FIXED TILE_1; +typedef struct _TILE_FIXED TILE_8; +typedef struct _TILE_FIXED TILE_16; + +typedef struct _SPRT { + uint32_t tag; + uint8_t r0, g0, b0, code; + int16_t x0, y0; + uint8_t u0, v0; + uint16_t clut; + uint16_t w, h; } SPRT; -typedef struct _SPRT_8 -{ - u_long tag; - u_char r0,g0,b0,code; - short x0,y0; - u_char u0,v0; - u_short clut; -} SPRT_8; - -typedef struct _SPRT_16 -{ - u_long tag; - u_char r0,g0,b0,code; - short x0,y0; - u_char u0,v0; - u_short clut; -} SPRT_16; - -/* - * VRAM fill and transfer primitive definitions - */ - -typedef struct _DR_ENV -{ - u_long tag; - u_long code[15]; +struct _SPRT_FIXED { + uint32_t tag; + uint8_t r0, g0, b0, code; + int16_t x0, y0; + uint8_t u0, v0; + uint16_t clut; +}; +typedef struct _SPRT_FIXED SPRT_8; +typedef struct _SPRT_FIXED SPRT_16; + +typedef struct _DR_ENV { + uint32_t tag; + uint32_t code[15]; } DR_ENV; -typedef struct _DR_AREA -{ - u_long tag; - u_long code[2]; +typedef struct _DR_AREA { + uint32_t tag; + uint32_t code[2]; } DR_AREA; -typedef struct _DR_OFFSET -{ - u_long tag; - u_long code[1]; +typedef struct _DR_OFFSET { + uint32_t tag; + uint32_t code[1]; } DR_OFFSET; -typedef struct _DR_TWIN -{ - u_long tag; - u_long code[2]; +typedef struct _DR_TWIN { + uint32_t tag; + uint32_t code[2]; } DR_TWIN; -typedef struct _DR_TPAGE -{ - u_long tag; - u_long code[1]; +typedef struct _DR_TPAGE { + uint32_t tag; + uint32_t code[1]; } DR_TPAGE; -typedef struct _DR_MASK /* ORIGINAL */ -{ - u_long tag; - u_long code[1]; +typedef struct _DR_MASK { + uint32_t tag; + uint32_t code[1]; } DR_MASK; -typedef struct _FILL /* ORIGINAL */ -{ - u_long tag; - u_char r0,g0,b0,code; - u_short x0,y0; // Note: coordinates must be in 16 pixel steps - u_short w,h; +typedef struct _FILL { + uint32_t tag; + uint8_t r0, g0, b0, code; + uint16_t x0, y0; // Note: coordinates must be in 16 pixel steps + uint16_t w, h; } FILL; -typedef struct _VRAM2VRAM /* ORIGINAL */ -{ - u_long tag; - u_char p0,p1,p2,code; - u_short x0,y0; - u_short x1,y1; - u_short w,h; - u_long nop[4]; +typedef struct _VRAM2VRAM { + uint32_t tag; + uint8_t p0, p1, p2, code; + uint16_t x0, y0; + uint16_t x1, y1; + uint16_t w, h; + uint32_t pad[4]; } VRAM2VRAM; -/* - * General structs - */ +/* Structure definitions */ -typedef struct _RECT -{ - short x,y; - short w,h; +typedef struct _RECT { + int16_t x, y, w, h; } RECT; -typedef struct _DISPENV_RAW /* obsolete */ -{ - unsigned int vid_mode; // Video mode - short vid_xpos,vid_ypos; // Video position (not framebuffer) - short fb_x,fb_y; // Framebuffer display position +typedef struct _DISPENV_RAW { + uint32_t vid_mode; + int16_t vid_xpos, vid_ypos; + int16_t fb_x, fb_y; } DISPENV_RAW; -typedef struct _DISPENV -{ - RECT disp; - RECT screen; - char isinter; - char isrgb24; - char reverse; - char pad; +typedef struct _DISPENV { + RECT disp, screen; + uint8_t isinter, isrgb24, reverse; + uint8_t _reserved; } DISPENV; -typedef struct _DRAWENV -{ - RECT clip; // Drawing area - short ofs[2]; // GPU draw offset (relative to draw area) - RECT tw; // Texture window (doesn't do anything atm) - u_short tpage; // Initial tpage value - u_char dtd; // Dither processing flag (simply OR'ed to tpage) - u_char dfe; // Drawing to display area blocked/allowed (simply OR'ed to tpage) - u_char isbg; // Clear draw area if non-zero - u_char r0,g0,b0; // Draw area clear color (if isbg iz nonzero) - DR_ENV dr_env; // Draw mode packet area (used by PutDrawEnv) +typedef struct _DRAWENV { + RECT clip; // Drawing area + int16_t ofs[2]; // GPU draw offset (relative to draw area) + RECT tw; // Texture window (doesn't do anything atm) + uint16_t tpage; // Initial tpage value + uint8_t dtd; // Dither processing flag (simply OR'ed to tpage) + uint8_t dfe; // Drawing to display area blocked/allowed (simply OR'ed to tpage) + uint8_t isbg; // Clear draw area if non-zero + uint8_t r0, g0, b0; // Draw area clear color (if isbg iz nonzero) + DR_ENV dr_env; // Draw mode packet area (used by PutDrawEnv) } DRAWENV; -typedef struct _TIM_IMAGE -{ - u_long mode; - RECT *crect; - u_long *caddr; - RECT *prect; - u_long *paddr; +typedef struct _TIM_IMAGE { + uint32_t mode; + RECT *crect; + uint32_t *caddr; + RECT *prect; + uint32_t *paddr; } TIM_IMAGE; +typedef struct _GsIMAGE { + uint32_t pmode; + int16_t px, py, pw, ph; + uint32_t *pixel; + int16_t cx, cy, cw, ch; + uint32_t *clut; +} GsIMAGE; + +/* Public API */ #ifdef __cplusplus extern "C" { #endif -// Function definitions (asm) - void ResetGraph(int mode); -int GetVideoMode(void); -void SetVideoMode(int mode); - -int GetODE(void); - -void PutDispEnvRaw(DISPENV_RAW *disp); /* obsolete */ -void PutDispEnv(DISPENV *disp); -void PutDrawEnv(DRAWENV *draw); - +GPU_VideoMode GetVideoMode(void); +void SetVideoMode(GPU_VideoMode mode); void SetDispMask(int mask); -int VSync(int m); -int DrawSync(int m); -void WaitGPUcmd(void); -void WaitGPUdma(void); +//void PutDispEnvRaw(const DISPENV_RAW *env); +void PutDispEnv(const DISPENV *env); +void PutDrawEnv(DRAWENV *env); +void PutDrawEnvFast(DRAWENV *env); -// Callback hook functions +int GetODE(void); +int VSync(int mode); +int DrawSync(int mode); + +void *VSyncHaltFunction(void (*func)(void)); void *VSyncCallback(void (*func)(void)); void *DrawSyncCallback(void (*func)(void)); -void LoadImage(RECT *rect, u_long *data); -void StoreImage(RECT *rect, u_long *data); - -void ClearOTagR(u_long* ot, int n); -void DrawOTag(u_long* ot); -void DrawPrim(void *pri); - -void AddPrim(u_long* ot, void* pri); +void LoadImage(const RECT *rect, const uint32_t *data); +void StoreImage(const RECT *rect, uint32_t *data); -// Function definitions (C) +void ClearOTagR(uint32_t *ot, size_t length); +void ClearOTag(uint32_t *ot, size_t length); +void DrawOTag(const uint32_t *ot); +void DrawOTag2(const uint32_t *ot); +void DrawOTagEnv(const uint32_t *ot, DRAWENV *env); +void DrawPrim(const uint32_t *pri); -int GetTimInfo(const u_long *tim, TIM_IMAGE *timimg); /* ORIGINAL */ +void AddPrim(uint32_t *ot, const void *pri); -DISPENV *SetDefDispEnv(DISPENV *disp, int x, int y, int w, int h); -DRAWENV *SetDefDrawEnv(DRAWENV *draw, int x, int y, int w, int h); +int GsGetTimInfo(const uint32_t *tim, GsIMAGE *info); +int GetTimInfo(const uint32_t *tim, TIM_IMAGE *info); -// Debug font functions +DISPENV *SetDefDispEnv(DISPENV *env, int x, int y, int w, int h); +DRAWENV *SetDefDrawEnv(DRAWENV *env, int x, int y, int w, int h); void FntLoad(int x, int y); -char *FntSort(u_long *ot, char *pri, int x, int y, const char *text); +char *FntSort(uint32_t *ot, char *pri, int x, int y, const char *text); int FntOpen(int x, int y, int w, int h, int isbg, int n); int FntPrint(int id, const char *fmt, ...); char *FntFlush(int id); diff --git a/libpsn00b/include/psxgte.h b/libpsn00b/include/psxgte.h index 7c10533..ddc988d 100644 --- a/libpsn00b/include/psxgte.h +++ b/libpsn00b/include/psxgte.h @@ -1,44 +1,45 @@ -#ifndef _PSXGTE_H -#define _PSXGTE_H +/* + * PSn00bSDK GTE library + * (C) 2019-2022 Lameguy64 - MPL licensed + */ +#ifndef __PSXGTE_H +#define __PSXGTE_H -#define ONE 4096 +#include <stdint.h> +#define ONE (1 << 12) -// For compatibility with official library syntax -#define csin(a) isin(a) -#define ccos(a) icos(a) -#define rsin(a) isin(a) -#define rcos(a) icos(a) - +/* Structure definitions */ -typedef struct MATRIX { - short m[3][3]; - int t[3]; +typedef struct _MATRIX { + int16_t m[3][3]; + int32_t t[3]; } MATRIX; -typedef struct VECTOR { - int vx, vy, vz; +typedef struct _VECTOR { + int32_t vx, vy, vz; } VECTOR; -typedef struct SVECTOR { - short vx, vy, vz, pad; +typedef struct _SVECTOR { + int16_t vx, vy, vz, pad; } SVECTOR; -typedef struct CVECTOR { - unsigned char r, g, b, cd; +typedef struct _CVECTOR { + uint8_t r, g, b, cd; } CVECTOR; -typedef struct DVECTOR { - short vx, vy; +typedef struct _DVECTOR { + int16_t vx, vy; } DVECTOR; +/* Public API */ #ifdef __cplusplus extern "C" { #endif -void InitGeom(); +void InitGeom(void); // Integer SIN/COS functions (4096 = 360 degrees) // Does not use tables! @@ -70,11 +71,16 @@ void VectorNormalS(VECTOR *v0, SVECTOR *v1); void Square0(VECTOR *v0, VECTOR *v1); -int SquareRoot12( int v ); -int SquareRoot0( int v ); +int SquareRoot12(int v); +int SquareRoot0(int v); + +#define csin(a) isin(a) +#define ccos(a) icos(a) +#define rsin(a) isin(a) +#define rcos(a) icos(a) #ifdef __cplusplus } #endif -#endif // _PSXGTE_H +#endif diff --git a/libpsn00b/include/psxpress.h b/libpsn00b/include/psxpress.h index b060170..2106a53 100644 --- a/libpsn00b/include/psxpress.h +++ b/libpsn00b/include/psxpress.h @@ -17,6 +17,28 @@ typedef struct _DECDCTENV { int16_t dct[64]; // Inverse DCT matrix (2.14 fixed-point) } DECDCTENV; +// This is the "small" lookup table used by DecDCTvlc(). It can be copied to +// the scratchpad. +typedef struct _DECDCTTAB { + uint16_t lut0[2]; + uint32_t lut2[8]; + uint32_t lut3[64]; + uint16_t lut4[8]; + uint16_t lut5[8]; + uint16_t lut7[16]; + uint16_t lut8[32]; + uint16_t lut9[32]; + uint16_t lut10[32]; + uint16_t lut11[32]; + uint16_t lut12[32]; +} DECDCTTAB; + +// This is the "large" table used by DecDCTvlc2(). +typedef struct _DECDCTTAB2 { + uint32_t lut[8192]; + uint32_t lut00[512]; +} DECDCTTAB2; + typedef enum _DECDCTMODE { DECDCT_MODE_24BPP = 1, DECDCT_MODE_16BPP = 0, @@ -24,6 +46,23 @@ typedef enum _DECDCTMODE { DECDCT_MODE_RAW = -1 } DECDCTMODE; +typedef struct _VLC_Context { + const uint32_t *input; + uint32_t window, next_window, remaining; + uint16_t quant_scale; + int8_t is_v3, bit_offset, block_index, coeff_index; +} VLC_Context; + +// Despite what some docs claim, the "number of 32-byte blocks" and "always +// 0x3800" fields are actually a single 32-bit field which is copied over to +// the output buffer, then parsed by DecDCTin() and written to the MDEC0 +// register. +typedef struct { + uint32_t mdec0_header; + uint16_t quant_scale; + uint16_t version; +} BS_Header; + /* Public API */ #ifdef __cplusplus @@ -40,7 +79,7 @@ extern "C" { * * @param mode */ -void DecDCTReset(int32_t mode); +void DecDCTReset(int mode); /** * @brief Uploads the specified decoding environment's quantization tables and @@ -61,15 +100,15 @@ void DecDCTReset(int32_t mode); * @param env Pointer to DECDCTENV or 0 for default tables * @param mono 0 for color (normal), 1 for monochrome */ -void DecDCTPutEnv(const DECDCTENV *env, int32_t mono); +void DecDCTPutEnv(const DECDCTENV *env, int mono); /** - * @brief Sets up the MDEC to start fetching and decoding a stream from the - * given address in main RAM. The first 32-bit word is initially copied to the - * MDEC0 register, then all subsequent data is read in 128-byte (32-word) - * chunks. The length of the stream (in 32-bit units, minus the first word) - * must be encoded in the lower 16 bits of the first word, as expected by the - * MDEC. + * @brief Sets up the MDEC to start fetching and decoding the given buffer. + * This function is meant to be used with buffers generated by DecDCTvlc(): the + * first 32-bit word of the buffer is initially copied to the MDEC0 register, + * then all subsequent data is read in 128-byte (32-word) chunks. The length of + * the stream (in 32-bit units, minus the first word) is encoded by DecDCTvlc() + * in the lower 16 bits of the first word. * * The mode argument optionally specifies the output color depth (0 for 16bpp, * 1 for 24bpp) if not already set in the first word. Passing -1 will result in @@ -79,7 +118,7 @@ void DecDCTPutEnv(const DECDCTENV *env, int32_t mono); * @param data * @param mode DECDCT_MODE_* or -1 */ -void DecDCTin(const uint32_t *data, int32_t mode); +void DecDCTin(const uint32_t *data, int mode); /** * @brief Configures the MDEC to automatically fetch data (the input stream, @@ -111,9 +150,9 @@ void DecDCTinRaw(const uint32_t *data, size_t length); * stream (usually a whole frame) is being written to main RAM. * * @param mode - * @return 0 or -1 in case of a timeout (mode = 0) / MDEC busy flag (mode = 1) + * @return 0 or -1 in case of a timeout (mode = 0), MDEC busy flag (mode = 1) */ -int32_t DecDCTinSync(int32_t mode); +int DecDCTinSync(int mode); /** * @brief Configures the MDEC to automatically transfer decoded image data in @@ -142,9 +181,204 @@ void DecDCTout(uint32_t *data, size_t length); * to register a callback that calls DecDCTin() to feed the MDEC. * * @param mode - * @return 0 or -1 in case of a timeout (mode = 0) / DMA busy flag (mode = 1) + * @return 0 or -1 in case of a timeout (mode = 0), DMA busy flag (mode = 1) + */ +int DecDCToutSync(int mode); + +/** + * @brief Begins decompressing the contents of a .BS file (or of a single .STR + * frame) into a buffer that can be passed to DecDCTin(). This function uses a + * small (<1 KB) lookup table combined with the GTE to accelerate the process; + * performance is roughly on par with DecDCTvlcStart2() if the lookup table + * is copied to the scratchpad beforehand by calling DecDCTvlcCopyTable(). The + * contents of the GTE's LZCR register, if any, will be destroyed. + * + * A VLC_Context object must be created and passed to this function, which will + * then proceed to initialize its fields. The max_size argument sets the + * maximum number of words that will be written to the output buffer; if more + * data needs to be written, this function will return 1. To continue decoding + * call DecDCTvlcContinue() with the same VLC_Context object (the output buffer + * can be different). If max_size = 0, the entire frame will always be decoded + * in one shot. + * + * Only bitstream version 2 is currently supported. + * + * WARNING: InitGeom() must be called prior to using DecDCTvlcStart() for the + * first time. Attempting to call this function with the GTE disabled will + * result in a crash. + * + * @param ctx Pointer to VLC_Context structure (which will be initialized) + * @param buf + * @param max_size Maximum number of 32-bit words to output + * @param bs + * @return 0, 1 if more data needs to be output or -1 in case of failure + */ +int DecDCTvlcStart(VLC_Context *ctx, uint32_t *buf, size_t max_size, const uint32_t *bs); + +/** + * @brief Resumes the decompression process started by DecDCTvlcStart(). The + * state of the decompressor is contained entirely in the VLC_Context structure + * so an arbitrary number of bitstreams can be decoded concurrently (although + * the limited CPU power makes it impractical to do so) by keeping a separate + * context for each bitstream. + * + * This function behaves like DecDCTvlcStart(), returning 1 if more data has to + * be written or 0 otherwise. DecDCTvlcContinue() shall not be called after a + * previous call to DecDCTvlcStart() or DecDCTvlcContinue() with the same + * context returned 0; in that case the context shall be discarded or reused to + * decode another bitstream. + * + * The contents of the GTE's LZCR register, if any, will be destroyed. + * + * See DecDCTvlcStart() for more details. + * + * @param ctx Pointer to already initialized VLC_Context structure + * @param buf + * @param max_size Maximum number of 32-bit words to output + * @return 0, 1 if more data needs to be output or -1 in case of failure + */ +int DecDCTvlcContinue(VLC_Context *ctx, uint32_t *buf, size_t max_size); + +/** + * A wrapper around DecDCTvlcStart() and DecDCTvlcContinue() for compatibility + * with the official SDK. This function uses an internal context; additionally, + * the maximum output buffer size is not passed as an argument but is instead + * set by calling DecDCTvlcSize(). + * + * This function behaves identically to DecDCTvlcContinue() if bs = 0 and + * DecDCTvlcStart() otherwise. + * + * See DecDCTvlcStart() for more details. + * + * WARNING: InitGeom() must be called prior to using DecDCTvlc() for the first + * time. Attempting to call this function with the GTE disabled will result in + * a crash. + * + * @param bs Pointer to bitstream data or 0 to resume decoding + * @param buf + * @return 0, 1 if more data needs to be output or -1 in case of failure + */ +int DecDCTvlc(const uint32_t *bs, uint32_t *buf); + +/** + * @brief Sets the maximum number of 32-bit words that a single call to + * DecDCTvlc() will output. If size = 0, the entire frame will always be + * decoded in one shot. + * + * @param size Maximum number of 32-bit words to output + * @return Previously set value + */ +size_t DecDCTvlcSize(size_t size); + +/** + * @brief Copies the small (<1 KB) lookup table used by DecDCTvlcContinue(), + * DecDCTvlcStart() and DecDCTvlc() (a DECDCTTAB structure) to the specified + * address. A copy of this table is always present in main RAM, however this + * function can be used to copy it to the scratchpad region to boost + * decompression performance. + * + * The address passed to this function is saved. Calls to DecDCTvlcStart(), + * DecDCTvlcContinue() and DecDCTvlc() will automatically use the last table + * copied. Call DecDCTvlcCopyTable(0) to revert to using the library's internal + * table in main RAM. + * + * @param addr Pointer to free area in scratchpad region or 0 to reset + */ +void DecDCTvlcCopyTable(DECDCTTAB *addr); + +/** + * @brief Begins decompressing the contents of a .BS file (or of a single .STR + * frame) into a buffer that can be passed to DecDCTin(). This function uses a + * large (34 KB) lookup table that must be loaded into main RAM beforehand by + * calling DecDCTvlcBuild(), but does not use the GTE nor the scratchpad. + * Depending on the specific bitstream being decoded DecDCTvlcStart2() might be + * slightly faster or slower than DecDCTvlcStart() with its lookup table copied + * to the scratchpad (see DecDCTvlcCopyTable()). DecDCTvlcStart() with the + * table in main RAM tends to be much slower. + * + * A VLC_Context object must be created and passed to this function, which will + * then proceed to initialize its fields. The max_size argument sets the + * maximum number of words that will be written to the output buffer; if more + * data needs to be written, this function will return 1. To continue decoding + * call DecDCTvlcContinue2() with the same VLC_Context object (the output + * buffer can be different). If max_size = 0, the entire frame will always be + * decoded in one shot. + * + * Only bitstream version 2 is currently supported. + * + * @param ctx Pointer to VLC_Context structure (which will be initialized) + * @param buf + * @param max_size Maximum number of 32-bit words to output + * @param bs + * @return 0, 1 if more data needs to be output or -1 in case of failure + */ +int DecDCTvlcStart2(VLC_Context *ctx, uint32_t *buf, size_t max_size, const uint32_t *bs); + +/** + * @brief Resumes the decompression process started by DecDCTvlcStart2(). The + * state of the decompressor is contained entirely in the VLC_Context structure + * so an arbitrary number of bitstreams can be decoded concurrently (although + * the limited CPU power makes it impractical to do so) by keeping a separate + * context for each bitstream. + * + * This function behaves like DecDCTvlcStart2(), returning 1 if more data has + * to be written or 0 otherwise. DecDCTvlcContinue2() shall not be called after + * a previous call to DecDCTvlcStart2() or DecDCTvlcContinue2() with the same + * context returned 0; in that case the context shall be discarded or reused to + * decode another bitstream. + * + * See DecDCTvlcStart2() for more details. + * + * @param ctx Pointer to already initialized VLC_Context structure + * @param buf + * @param max_size Maximum number of 32-bit words to output + * @return 0, 1 if more data needs to be output or -1 in case of failure + */ +int DecDCTvlcContinue2(VLC_Context *ctx, uint32_t *buf, size_t max_size); + +/** + * A wrapper around DecDCTvlcStart2() and DecDCTvlcContinue2() for + * compatibility with the official SDK. This function uses an internal context; + * additionally, the maximum output buffer size is not passed as an argument + * but is instead set by calling DecDCTvlcSize2(). + * + * This function behaves identically to DecDCTvlcContinue() if bs = 0 and + * DecDCTvlcStart() otherwise. The table argument can optionally be passed to + * use a custom lookup table. If zero, the last pointer passed to + * DecDCTvlcBuild() will be used. + * + * See DecDCTvlcStart2() for more details. + * + * @param bs Pointer to bitstream data or 0 to resume decoding + * @param buf + * @param table Pointer to decompressed table or 0 to use last table used + * @return 0, 1 if more data needs to be output or -1 in case of failure + */ +int DecDCTvlc2(const uint32_t *bs, uint32_t *buf, DECDCTTAB2 *table); + +/** + * @brief Sets the maximum number of 32-bit words that a single call to + * DecDCTvlc2() will output. If size = 0, the entire frame will always be + * decoded in one shot. + * + * @param size Maximum number of 32-bit words to output + * @return Previously set value + */ +size_t DecDCTvlcSize2(size_t size); + +/** + * @brief Generates the lookup table required by DecDCTvlcStart2(), + * DecDCTvlcContinue2() and DecDCTvlc2() (a DECDCTTAB2 structure) into the + * specified buffer. Since the table is relatively large (34 KB), it is + * recommended to only generate it in a dynamically-allocated buffer when + * needed and deallocate the buffer afterwards. + * + * The address passed to this function is saved. Calls to DecDCTvlcStart2() and + * DecDCTvlcContinue2() will automatically use the last table decompressed. + * + * @param table */ -int32_t DecDCToutSync(int32_t mode); +void DecDCTvlcBuild(DECDCTTAB2 *table); #ifdef __cplusplus } diff --git a/libpsn00b/include/psxspu.h b/libpsn00b/include/psxspu.h index da000e3..cf78e3d 100644 --- a/libpsn00b/include/psxspu.h +++ b/libpsn00b/include/psxspu.h @@ -1,138 +1,124 @@ +/* + * PSn00bSDK SPU library + * (C) 2019-2022 Lameguy64, spicyjpeg - MPL licensed + */ + #ifndef __PSXSPU_H #define __PSXSPU_H -#include <sys/types.h> - -// Mask settings bits for specifying voice channels - -#define SPU_00CH (1<<0) -#define SPU_01CH (1<<1) -#define SPU_02CH (1<<2) -#define SPU_03CH (1<<3) -#define SPU_04CH (1<<4) -#define SPU_05CH (1<<5) -#define SPU_06CH (1<<6) -#define SPU_07CH (1<<7) -#define SPU_08CH (1<<8) -#define SPU_09CH (1<<9) -#define SPU_10CH (1<<10) -#define SPU_11CH (1<<11) -#define SPU_12CH (1<<12) -#define SPU_13CH (1<<13) -#define SPU_14CH (1<<14) -#define SPU_15CH (1<<15) -#define SPU_16CH (1<<16) -#define SPU_17CH (1<<17) -#define SPU_18CH (1<<18) -#define SPU_19CH (1<<19) -#define SPU_20CH (1<<20) -#define SPU_21CH (1<<21) -#define SPU_22CH (1<<22) -#define SPU_23CH (1<<23) - -#define SPU_0CH SPU_00CH -#define SPU_1CH SPU_01CH -#define SPU_2CH SPU_02CH -#define SPU_3CH SPU_03CH -#define SPU_4CH SPU_04CH -#define SPU_5CH SPU_05CH -#define SPU_6CH SPU_06CH -#define SPU_7CH SPU_07CH -#define SPU_8CH SPU_08CH -#define SPU_9CH SPU_09CH - -#define SPU_KEYCH(x) (1<<(x)) -#define SPU_VOICECH(x) SPU_KEYCH(x) - - -// Mask setting bits for SpuVoiceAttr.mask - -#define SPU_VOICE_VOLL (1<<0) // Left volume -#define SPU_VOICE_VOLR (1<<1) // Right volume -#define SPU_VOICE_VOLMODEL (1<<2) // Left volume mode -#define SPU_VOICE_VOLMODER (1<<3) // Right volume mode -#define SPU_VOICE_PITCH (1<<4) // Pitch tone -#define SPU_VOICE_NOTE (1<<5) // Pitch note -#define SPU_VOICE_SAMPLE_NOTE (1<<6) // Sample base frequency? -#define SPU_VOICE_WDSA (1<<7) // Sample start address (in SPU RAM) -#define SPU_VOICE_ADSR_AMODE (1<<8) // ADSR attack mode -#define SPU_VOICE_ADSR_SMODE (1<<9) // ADSR sustain mode -#define SPU_VOICE_ADSR_RMODE (1<<10) // ADSR release mode -#define SPU_VOICE_ADSR_AR (1<<11) // ADSR attack rate -#define SPU_VOICE_ADSR_DR (1<<12) // ADSR decay rate -#define SPU_VOICE_ADSR_SR (1<<13) // ADSR sustain rate -#define SPU_VOICE_ADSR_RR (1<<14) // ADSR release rate -#define SPU_VOICE_ADSR_SL (1<<15) // ADSR sustain level -#define SPU_VOICE_LSAX (1<<16) // Loop start address (in SPU RAM) -#define SPU_VOICE_ADSR_ADSR1 (1<<17) // adsr1 for VagAtr (?) -#define SPU_VOICE_ADSR_ADSR2 (1<<18) // adsr2 for VagAtr (?) - - -#define SPU_TRANSFER_BY_DMA 0 - - -typedef struct { - short left; - short right; +#include <stdint.h> +#include <stddef.h> +#include <hwregs_c.h> + +/* Definitions */ + +typedef enum _SPU_AttrMask { + SPU_VOICE_VOLL = 1 << 0, // Left volume + SPU_VOICE_VOLR = 1 << 1, // Right volume + SPU_VOICE_VOLMODEL = 1 << 2, // Left volume mode + SPU_VOICE_VOLMODER = 1 << 3, // Right volume mode + SPU_VOICE_PITCH = 1 << 4, // Pitch tone + SPU_VOICE_NOTE = 1 << 5, // Pitch note + SPU_VOICE_SAMPLE_NOTE = 1 << 6, // Sample base frequency? + SPU_VOICE_WDSA = 1 << 7, // Sample start address (in SPU RAM) + SPU_VOICE_ADSR_AMODE = 1 << 8, // ADSR attack mode + SPU_VOICE_ADSR_SMODE = 1 << 9, // ADSR sustain mode + SPU_VOICE_ADSR_RMODE = 1 << 10, // ADSR release mode + SPU_VOICE_ADSR_AR = 1 << 11, // ADSR attack rate + SPU_VOICE_ADSR_DR = 1 << 12, // ADSR decay rate + SPU_VOICE_ADSR_SR = 1 << 13, // ADSR sustain rate + SPU_VOICE_ADSR_RR = 1 << 14, // ADSR release rate + SPU_VOICE_ADSR_SL = 1 << 15, // ADSR sustain level + SPU_VOICE_LSAX = 1 << 16, // Loop start address (in SPU RAM) + SPU_VOICE_ADSR_ADSR1 = 1 << 17, + SPU_VOICE_ADSR_ADSR2 = 1 << 18 +} SPU_AttrMask; + +typedef enum _SPU_TransferMode { + SPU_TRANSFER_BY_DMA = 0, + SPU_TRANSFER_BY_IO = 1 +} SPU_TransferMode; + +typedef enum _SPU_WaitMode { + SPU_TRANSFER_PEEK = 0, + SPU_TRANSFER_WAIT = 1 +} SPU_WaitMode; + +/* Structure definitions */ + +typedef struct _SpuVolume { + int16_t left, right; } SpuVolume; -typedef struct { - SpuVolume vol; // 0 - unsigned short freq; // 4 - unsigned short addr; // 6 - unsigned short loop_addr; // 8 - unsigned short res; // 10 - unsigned int adsr_param; // 12 -} SpuVoiceRaw; - -typedef struct { - u_int voice; - u_int mask; - SpuVolume volume; - SpuVolume volmode; - SpuVolume volumex; - u_short pitch; - u_short note; - u_short sample_note; - short envx; - u_int addr; - u_int loop_addr; - int a_mode; - int s_mode; - int r_mode; - u_short ar; - u_short dr; - u_short sr; - u_short rr; - u_short sl; - u_short adsr1; - u_short adsr2; +typedef struct _SpuVoiceAttr { + uint32_t voice; + uint32_t mask; + SpuVolume volume, volmode, volumex; + uint16_t pitch, note, sample_note; + int16_t envx; + uint32_t addr, loop_addr; + int a_mode, s_mode, r_mode; + uint16_t ar, dr, sr, rr, sl; + uint16_t adsr1, adsr2; } SpuVoiceAttr; +typedef struct _SpuExtAttr { + SpuVolume volume; + int reverb, mix; +} SpuExtAttr; + +typedef struct _SpuCommonAttr { + uint32_t mask; + SpuVolume mvol, mvolmode, mvolx; + SpuExtAttr cd, ext; +} SpuCommonAttr; + +/* "Useless" macros for official SDK compatibility */ + +#define SpuSetCommonMasterVolume(left, right) \ + (SPU_MASTER_VOL_L = (left), SPU_MASTER_VOL_R = (right)) +#define SpuSetCommonCDVolume(left, right) \ + (SPU_CD_VOL_L = (left), SPU_CD_VOL_R = (right)) +#define SpuSetCommonCDReverb(enable) \ + ((enable) ? (SPU_CTRL |= 0x0004) : (SPU_CTRL &= 0xfffb)) +#define SpuSetCommonExtVolume(left, right) \ + (SPU_EXT_VOL_L = (left), SPU_EXT_VOL_R = (right)) +#define SpuSetCommonExtReverb(enable) \ + ((enable) ? (SPU_CTRL |= 0x0002) : (SPU_CTRL &= 0xfffd)) + +#define SpuSetReverbAddr(addr) \ + (SPU_REVERB_ADDR = ((addr) + 7) / 8) +#define SpuSetIRQAddr(addr) \ + (SPU_IRQ_ADDR = ((addr) + 7) / 8) + +#define SpuSetVoiceVolume(ch, left, right) \ + (SPU_CH_VOL_L(ch) = (left), SPU_CH_VOL_R(ch) = (right)) +#define SpuSetVoicePitch(ch, pitch) \ + (SPU_CH_FREQ(ch) = (pitch)) +#define SpuSetVoiceStartAddr(ch, addr) \ + (SPU_CH_ADDR(ch) = ((addr) + 7) / 8) +#define SpuSetVoiceADSR(ch, ar, dr, sr, rr, sl) \ + (SPU_CH_ADSR(ch) = ((sl)) | ((dr) << 4) | ((ar) << 8) | ((rr) << 16) | ((sr) << 22) | (1 << 30)) + +#define SpuSetKey(enable, voice_bit) \ + ((enable) ? (SPU_KEY_ON = (voice_bit)) : (SPU_KEY_OFF = (voice_bit))) + +/* Public API */ + #ifdef __cplusplus extern "C" { #endif -void SpuInit(); - -void SpuSetVoiceRaw( int voice, const SpuVoiceRaw* param ); -void SpuReverbOn( int voice ); -void SpuSetReverb(); - -void SpuSetReverbAddr( int addr ); -void SpuSetReverbVolume( int left, int right ); +void SpuInit(void); - -void SpuSetKey(int on_off, u_int voice_bit); - -// SPU transfer functions -int SpuSetTransferMode(int mode); -int SpuSetTransferStartAddr(int addr); -int SpuWrite(const unsigned char* addr, int size); -void SpuWait(); +void SpuRead(uint32_t *data, size_t size); +void SpuWrite(const uint32_t *data, size_t size); +SPU_TransferMode SpuSetTransferMode(SPU_TransferMode mode); +uint32_t SpuSetTransferStartAddr(uint32_t addr); +int SpuIsTransferCompleted(int mode); #ifdef __cplusplus } #endif -#endif
\ No newline at end of file +#endif diff --git a/libpsn00b/include/stdlib.h b/libpsn00b/include/stdlib.h index 4c4fcd3..1888c69 100644 --- a/libpsn00b/include/stdlib.h +++ b/libpsn00b/include/stdlib.h @@ -1,36 +1,27 @@ /* - * stdlib.h - * - * Standard library functions - * - * Inherited from PSXSDK + * PSn00bSDK standard library + * (C) 2019-2022 PSXSDK authors, Lameguy64, spicyjpeg - MPL licensed */ -#ifndef _STDLIB_H -#define _STDLIB_H +#ifndef __STDLIB_H +#define __STDLIB_H -#define RAND_MAX 0x7fff +#include <stddef.h> -/* Conversion functions (not yet implemented) */ +/* Definitions */ -/* -extern int atoi(char *s); -extern long atol(char *s); -extern char atob(char *s); // Is this right? -*/ - -// Quick sort (not yet implemented) +#define RAND_MAX 0x7fff -//void qsort(void *base , int nel , int width , int (*cmp)(const void *,const void *)); +/* API */ #ifdef __cplusplus extern "C" { #endif -extern int __argc; -extern const char **__argv; +extern int __argc; +extern const char **__argv; -int rand(); +int rand(void); void srand(unsigned long seed); int abs(int j); @@ -39,16 +30,17 @@ long long strtoll(const char *nptr, char **endptr, int base); long strtol(const char *nptr, char **endptr, int base); long double strtold(const char *nptr, char **endptr); -// Note: these use floats internally! double strtod(const char *nptr, char **endptr); float strtof(const char *nptr, char **endptr); -// Memory allocation functions -void _mem_init(int ram_size, int stack_max_size); -void InitHeap(unsigned int *addr, int size); -int SetHeapSize(int size); -void *malloc(int size); -void *calloc(int number, int size); +void _mem_init(size_t ram_size, size_t stack_max_size); +void InitHeap(void *addr, size_t size); +//int SetHeapSize(size_t size); +void *sbrk(ptrdiff_t incr); + +void *malloc(size_t size); +void *calloc(size_t num, size_t size); +void *realloc(void *ptr, size_t size); void free(void *ptr); #ifdef __cplusplus @@ -56,4 +48,3 @@ void free(void *ptr); #endif #endif - diff --git a/libpsn00b/include/string.h b/libpsn00b/include/string.h index 365d238..ceee066 100644 --- a/libpsn00b/include/string.h +++ b/libpsn00b/include/string.h @@ -1,13 +1,10 @@ /* - * string.h - * - * Prototypes for string functions of the C library - * - * PSXSDK + * PSn00bSDK standard library + * (C) 2019-2022 PSXSDK authors, Lameguy64, spicyjpeg - MPL licensed */ -#ifndef _STRING_H -#define _STRING_H +#ifndef __STRING_H +#define __STRING_H #ifdef __cplusplus extern "C" { @@ -19,11 +16,6 @@ char *strpbrk(const char *dst , const char *src); char *strtok(char *s , char *set); char *strstr(const char *big , const char *little); -//int strspn(char *s , char *set); -//int strcspn(char *s , char *set); -//int index(char *s , int c); -//int rindex(char *s , int c); - char *strcat(char *s , const char *append); char *strncat(char *s , const char *append, int n); char *strcpy(char *dst , const char *src); @@ -34,9 +26,6 @@ char *strrchr(const char *s , int c); void *memmove(void *dst , const void *src , int n); void *memchr(void *s , int c , int n); - -// Functions converted to ASM - void *memcpy(void *dst , const void *src , int n); void *memset(void *dst , char c , int n); int memcmp(const void *b1 , const void *b2 , int n); @@ -46,4 +35,3 @@ int memcmp(const void *b1 , const void *b2 , int n); #endif #endif - diff --git a/libpsn00b/include/strings.h b/libpsn00b/include/strings.h index e5e88d4..7223ab9 100644 --- a/libpsn00b/include/strings.h +++ b/libpsn00b/include/strings.h @@ -1,18 +1,19 @@ -/* - * strings.h - * - * PSXSDK +/* + * PSn00bSDK standard library + * (C) 2019-2022 PSXSDK authors, Lameguy64, spicyjpeg - MPL licensed */ -#ifndef _STRINGS_H -#define _STRINGS_H +#ifndef __STRINGS_H +#define __STRINGS_H #include <string.h> -#define bcopy(src,dst,len) memmove(dst,src,len) -#define bzero(ptr, len) memset(ptr, 0, len) -#define bcmp(b1,b2,len) memcmp(b1,b2,len) -#define index(s, c) strchr(s, c) -#define rindex(s, c) strrchr(s, c) +/* Compatibility macros (this header is useless) */ + +#define bcopy(src, dst, len) memmove(dst, src, len) +#define bzero(ptr, len) memset(ptr, 0, len) +#define bcmp(b1, b2, len) memcmp(b1, b2, len) +#define index(s, c) strchr(s, c) +#define rindex(s, c) strrchr(s, c) #endif |
