diff options
| author | Rozelette <Rozelette@users.noreply.github.com> | 2021-03-16 20:49:27 -0500 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2021-03-16 21:49:27 -0400 |
| commit | 8342329538eb75d01604328fec29e6bbfe6d9c1a (patch) | |
| tree | 604c173f5687d44ad47a724803de8c28beba244c /src/boot_O2_g3 | |
| parent | a53626049f6374382bf72076ab429b33d73b95a2 (diff) | |
yaz0.c OK (#71)
Diffstat (limited to 'src/boot_O2_g3')
| -rw-r--r-- | src/boot_O2_g3/yaz0.c | 150 | ||||
| -rw-r--r-- | src/boot_O2_g3/z_std_dma.c | 2 |
2 files changed, 151 insertions, 1 deletions
diff --git a/src/boot_O2_g3/yaz0.c b/src/boot_O2_g3/yaz0.c new file mode 100644 index 000000000..e583a086f --- /dev/null +++ b/src/boot_O2_g3/yaz0.c @@ -0,0 +1,150 @@ +#include <ultra64.h> +#include <global.h> + +u8 sYaz0DataBuffer[0x400]; +u8* sYaz0CurDataEnd; +u32 sYaz0CurRomStart; +u32 sYaz0CurSize; +u8* sYaz0MaxPtr; +u8* D_8009BE20; + +void* Yaz0_FirstDMA() { + u32 pad0; + u32 dmaSize; + u32 curSize; + + sYaz0MaxPtr = sYaz0CurDataEnd - 0x19; + + curSize = (u32)sYaz0CurDataEnd - (u32)sYaz0DataBuffer; + dmaSize = (curSize > sYaz0CurSize) ? sYaz0CurSize : curSize; + + DmaMgr_DMARomToRam(sYaz0CurRomStart, sYaz0DataBuffer, dmaSize); + sYaz0CurRomStart += dmaSize; + sYaz0CurSize -= dmaSize; + return sYaz0DataBuffer; +} + +void* Yaz0_NextDMA(void* curSrcPos) { + u8* dst; + u32 restSize; + u32 dmaSize; + OSPri oldPri; + + restSize = (u32)sYaz0CurDataEnd - (u32)curSrcPos; + + dst = (restSize & 7) ? (sYaz0DataBuffer - (restSize & 7)) + 8 : sYaz0DataBuffer; + + bcopy(curSrcPos, dst, restSize); + dmaSize = ((u32)sYaz0CurDataEnd - (u32)dst) - restSize; + if (sYaz0CurSize < dmaSize) { + dmaSize = sYaz0CurSize; + } + + if (dmaSize != 0) { + DmaMgr_DMARomToRam(sYaz0CurRomStart, dst + restSize, dmaSize); + sYaz0CurRomStart += dmaSize; + sYaz0CurSize -= dmaSize; + if (!sYaz0CurSize) { + sYaz0MaxPtr = dst + restSize + dmaSize; + } + } else { + oldPri = osGetThreadPri(NULL); + osSetThreadPri(NULL, 0x7F); + Fault_Log("圧縮展開異常\n"); + osSetThreadPri(NULL, oldPri); + } + + return dst; +} + +typedef struct { + /* 0x00 */ u32 magic; // Yaz0 + /* 0x04 */ u32 decSize; + /* 0x08 */ u32 compInfoOffset; // only used in mio0 + /* 0x0C */ u32 uncompDataOffset; // only used in mio0 +} Yaz0Header; // size = 0x10 + +#define YAZ0_MAGIC 0x59617A30 // "Yaz0" + +s32 Yaz0_DecompressImpl(u8* src, u8* dst) { + u32 bitIdx = 0; + u8* dstEnd; + u32 chunkHeader = 0; + u32 nibble; + u8* backPtr; + s32 chunkSize; + u32 off; + u32 magic; + + magic = ((Yaz0Header*)src)->magic; + + if (magic != YAZ0_MAGIC) { + return -1; + } + + dstEnd = dst + ((Yaz0Header*)src)->decSize; + src = src + sizeof(Yaz0Header); + + do { + if (bitIdx == 0) { + if ((sYaz0MaxPtr < src) && (sYaz0CurSize != 0)) { + src = Yaz0_NextDMA(src); + } + + chunkHeader = *src++; + bitIdx = 8; + } + + if (chunkHeader & (1 << 7)) { // uncompressed + *dst = *src; + dst++; + src++; + } else { // compressed + off = ((*src & 0xF) << 8 | *(src + 1)); + nibble = *src >> 4; + backPtr = dst - off; + src += 2; + + chunkSize = (nibble == 0) // N = chunkSize; B = back offset + ? *src++ + 0x12 // 3 bytes 0B BB NN + : nibble + 2; // 2 bytes NB BB + + do { + *dst++ = *(backPtr++ - 1); + chunkSize--; + } while (chunkSize != 0); + } + chunkHeader <<= 1; + bitIdx--; + } while (dst != dstEnd); + + D_8009BE20 = dstEnd; + + return 0; +} + +void Yaz0_Decompress(u32 romStart, void* dst, u32 size) { + s32 status; + u32 pad; + u8 sp80[0x50]; + u8 sp30[0x50]; + + if (sYaz0CurDataEnd != NULL) { + while (sYaz0CurDataEnd != NULL) { + func_80087A1C(10); + } + } + + sYaz0CurDataEnd = sYaz0DataBuffer + sizeof(sYaz0DataBuffer); + sYaz0CurRomStart = romStart; + sYaz0CurSize = size; + status = Yaz0_DecompressImpl(Yaz0_FirstDMA(), dst); + + if (status != 0) { + sprintf(sp80, "slidma slidstart_szs ret=%d", status); + sprintf(sp30, "src:%08lx dst:%08lx siz:%08lx", romStart, dst, size); + Fault_AddHungupAndCrashImpl(sp80, sp30); + } + + sYaz0CurDataEnd = NULL; +} diff --git a/src/boot_O2_g3/z_std_dma.c b/src/boot_O2_g3/z_std_dma.c index 6b7043396..2f617eb03 100644 --- a/src/boot_O2_g3/z_std_dma.c +++ b/src/boot_O2_g3/z_std_dma.c @@ -134,7 +134,7 @@ void DmaMgr_ProcessMsg(DmaRequest* a0) { } osSetThreadPri(NULL, 10); - Yaz0_LoadAndDecompressFile(sp28, sp30, sp24); + Yaz0_Decompress(sp28, sp30, sp24); osSetThreadPri(NULL, 17); } else { Fault_AddHungupAndCrash(dmamgrString800981F4, 558); |
