diff --git a/config/kuon.yaml b/config/kuon.yaml index efb39eb..1c53342 100644 --- a/config/kuon.yaml +++ b/config/kuon.yaml @@ -283,7 +283,7 @@ segments: - [0x059C60, asmtu, cs4/Seimei/src/Dss] - [0x05ACB0, asmtu, cs4/Seimei/src/Damage] - [0x05B3B0, asmtu, cs4/Seimei/src/Hmd] - - [0x05E360, asmtu, cs4/Seimei/src/Binder] + - [0x05E360, c, cs4/Seimei/src/Binder] - [0x05E980, asmtu, cs4/Seimei/src/Ene] - [0x060DF0, asmtu, cs4/Seimei/src/EneAct] - [0x062F40, asmtu, cs4/Seimei/src/EneThk] diff --git a/src/cs4/Seimei/src/Binder.c b/src/cs4/Seimei/src/Binder.c index a500b65..9f3de5d 100644 --- a/src/cs4/Seimei/src/Binder.c +++ b/src/cs4/Seimei/src/Binder.c @@ -1,15 +1,146 @@ +#include "Binder.h" +#include "Cdvd.h" +#include "File.h" +#include "Memory.h" #include "common.h" +#include "sce/libcdvd.h" -INCLUDE_ASM("config/asm/nonmatchings/cs4/Seimei/src/Binder", GetAllBindInfo); +// Belongs in CDVD.c +unsigned int GlobalLoadTimer; -INCLUDE_ASM("config/asm/nonmatchings/cs4/Seimei/src/Binder", SetAllBindInfo); +void GetAllBindInfo(char *fname /* r2 */, unsigned int *lsn /* r2 */, + unsigned int *size /* r2 */) { + // Range: 0x15E2E0 -> 0x15E440 + unsigned int hash = 0; // r7 + signed int i = 0; // r9 -INCLUDE_ASM("config/asm/nonmatchings/cs4/Seimei/src/Binder", GetBindNum); + hash = foo_fn(fname); -INCLUDE_ASM("config/asm/nonmatchings/cs4/Seimei/src/Binder", GetBindOffsetByName); + *lsn = 0x0; + *size = 0x0; + for (i = 0; i < AllBindDataNum; i++) { + if (hash == AllBindInfo[i].hash) { + *lsn = AllBindInfo[i].lsn; + *size = AllBindInfo[i].size; + break; + } + } +} -INCLUDE_ASM("config/asm/nonmatchings/cs4/Seimei/src/Binder", GetBindOffsetByIndex); +void SetAllBindInfo(void) { + signed int i; // r19 + LPBINDHEAD *lpBindHead; // s2 + LPOFFSET *lpOffset; // s1 + LPALLBINDINFO *lpAllBindInfo = (LPALLBINDINFO *)AllBindInfo; // s0 + sceCdRMode CdRMode = {0, 1, 0, 0}; -INCLUDE_ASM("config/asm/nonmatchings/cs4/Seimei/src/Binder", RemapBinderFile); + MakeCdvdReadPath(lpCdvd->fname, (char *)GetRootPath(), "All.bnd"); + MakeCdvdSearchPath(lpCdvd->sname, "All.bnd"); + StringCorrectPath4Disc(lpCdvd->fname, 1); + StringCorrectPath4Disc(lpCdvd->sname, 1); -INCLUDE_ASM("config/asm/nonmatchings/cs4/Seimei/src/Binder", ReadBinderFile); + lpCdvd->size = 0x18000; + + lpCdvd->sector = (lpCdvd->size + 0x7FF) / 2048; + lpCdvd->lpDmyData = MemAllocAlignReal(lpCdvd->sector << 0xB, 0x800U, + (char *)__FUNCTION__, ""); + if (lpCdvd->lpDmyData == NULL) { + while (1) + ; + } + + while (sceCdSearchFile((sceCdlFILE *)&lpCdvd->cdlfile, + (void *)&lpCdvd->sname) == 0) + ; + FlushCache(0); + while (sceCdRead(lpCdvd->cdlfile.lsn, lpCdvd->sector, lpCdvd->lpDmyData, + &CdRMode) == 0) + ; + sceCdSync(0); + memset(AllBindInfo, 0, sizeof(AllBindInfo)); + + lpBindHead = (void *)lpCdvd->lpDmyData; + lpOffset = (void *)(lpBindHead + 0x1); + if (lpBindHead->filenum > ARRAY_COUNT(AllBindInfo)) { + while (1) + ; + } + AllBindDataNum = lpBindHead->filenum; + + for (i = 0; i < lpBindHead->filenum; i++) { + lpOffset->nameoffset += (int)lpBindHead; + strcpy((char *)&lpAllBindInfo->filename, (char *)lpOffset->nameoffset); + lpAllBindInfo->lsn = (lpOffset->dataoffset >> 0xB) + lpCdvd->cdlfile.lsn; + lpAllBindInfo->size = lpOffset->filesize; + lpAllBindInfo->hash = foo_fn((char *)&lpAllBindInfo->filename); + lpOffset++; + lpAllBindInfo++; + } + MemFree(lpCdvd->lpDmyData); +} + +unsigned int GetBindNum(LPBINDHEAD *lpBindHead /* r2 */) { + + return lpBindHead->filenum; +} + +unsigned int GetBindOffsetByName(LPBINDHEAD *lpBindHead, char *fname) { + unsigned int i; // r17 + SHORT_OFFSET *lpOffset; // r16 + + if (lpBindHead == NULL) { + return 0; + } + + lpOffset = (SHORT_OFFSET *)(lpBindHead + 1); + + for (i = 0; i < lpBindHead->filenum; i++, lpOffset++) { + if (strcmp((char *)lpOffset->nameoffset, fname) == 0) { + return lpOffset->dataoffset; + } + } + + return 0; +} + +unsigned int GetBindOffsetByIndex(LPBINDHEAD *lpBindHead, u_short Index) { + unsigned int i; // r17 + SHORT_OFFSET *lpOffset; // r16 + + if (lpBindHead == NULL) { + return 0; + } + + lpOffset = (SHORT_OFFSET *)(lpBindHead + 1); + + for (i = 0; i < lpBindHead->filenum; i++, lpOffset++) { + if (lpOffset->fileID == Index) { + return lpOffset->dataoffset; + } + } + return 0; +} + +void RemapBinderFile(void *lpBuf /* r2 */) { + u_int i; // r6 + LPBINDHEAD *lpBindHead; // r2 + SHORT_OFFSET *lpOffset; // r5 + + if (lpBuf == NULL) { + return; + } + + lpBindHead = lpBuf; + lpOffset = (SHORT_OFFSET *)(lpBindHead + 1); + + for (i = 0; i < lpBindHead->filenum; i++) { + lpOffset[i].dataoffset += (u_int)lpBuf; + lpOffset[i].nameoffset += (u_int)lpBuf; + } +} + +void ReadBinderFile(char *filename /* r2 */, void **lplpBuf /* r5 */, + signed int dataindex /* r2 */, + signed int filetype /* r2 */) { + FileRead(filename, -1, (u_char **)lplpBuf, 0, dataindex, filetype, 0); +} diff --git a/src/cs4/Seimei/src/Binder.h b/src/cs4/Seimei/src/Binder.h new file mode 100644 index 0000000..43a4aa8 --- /dev/null +++ b/src/cs4/Seimei/src/Binder.h @@ -0,0 +1,92 @@ +#ifndef BINDER_H +#define BINDER_H + + +// Range: 0x15E440 -> 0x15E760 + // total size: 0x10 +typedef struct /* @anon0 */ { + char appname[4]; // offset 0x0, size 0x4 + unsigned int version; // offset 0x4, size 0x4 + unsigned int filesize; // offset 0x8, size 0x4 + unsigned int filenum; // offset 0xC, size 0x4 +} LPBINDHEAD; // r18 + +// total size: 0x10 +typedef struct /* @anon6 */ +{ + unsigned short fileID; // offset 0x0, size 0x2 + unsigned short groupID; // offset 0x2, size 0x2 + unsigned int dataoffset; // offset 0x4, size 0x4 + unsigned int filesize; // offset 0x8, size 0x4 + unsigned int nameoffset; // offset 0xC, size 0x4 +} LPOFFSET; // r17 + +// total size: 0x8C +typedef struct /* @anon5 */ +{ + char filename[128]; // offset 0x0, size 0x80 + unsigned int lsn; // offset 0x80, size 0x4 + unsigned int size; // offset 0x84, size 0x4 + unsigned int hash; // offset 0x88, size 0x4 +} LPALLBINDINFO; // r16 + +typedef struct { + // Members + unsigned short fileID; // offset 0x0, size 0x2 + unsigned short groupID; // offset 0x2, size 0x2 + unsigned int dataoffset; // offset 0x4, size 0x4 + unsigned int nameoffset; // offset 0x8, size 0x4 +} SHORT_OFFSET; // r16 + +typedef struct /* @anon5 */ { + // Members + char filename[128]; // offset 0x0, size 0x80 + unsigned int lsn; // offset 0x80, size 0x4 + unsigned int size; // offset 0x84, size 0x4 + unsigned int hash; // offset 0x88, size 0x4 +} BINDINFO; + +static unsigned int AllBindDataNum; // size: 0x4, address: 0x257964 + +static BINDINFO AllBindInfo[3200]; + +static inline unsigned int foo_fn(char* fname) { + unsigned int hash = 0; + int i = 0; + int foo[32] = { + 0x02, 0x03, 0x05, 0x07, + 0x0B, 0x0D, 0x11, 0x13, + 0x17, 0x1D, 0x1F, 0x25, + 0x29, 0x2B, 0x2F, 0x35, + 0x3B, 0x3D, 0x43, 0x47, + 0x49, 0x4F, 0x53, 0x59, + 0x61, 0x65, 0x67, 0x6B, + 0x6D, 0x71, 0x7F, 0x83 + }; + + int bar[32] = { + 0x007F, 0x0161, 0x025F, 0x036D, + 0x0481, 0x05AD, 0x06CD, 0x080F, + 0x0943, 0x0A81, 0x0BB9, 0x0D0F, + 0x0E4B, 0x0FA1, 0x10E7, 0x1237, + 0x1391, 0x1511, 0x1645, 0x17B3, + 0x18E5, 0x1A6B, 0x1BC5, 0x1D53, + 0x1EA1, 0x201D, 0x2197, 0x22E5, + 0x244D, 0x25AB, 0x2719, 0x2875 + }; + + for (; *fname != 0; fname++) { + + if (++i >= 32u) { + do { } while( 1 ); + } + hash += bar[i] * foo[i] * *fname; + } + return hash; +} + + + +void GetAllBindInfo(char * fname /* r2 */, unsigned int * lsn /* r2 */, unsigned int * size /* r2 */); + +#endif // BINDER_H \ No newline at end of file diff --git a/src/cs4/Seimei/src/Cdvd.h b/src/cs4/Seimei/src/Cdvd.h index 7d0a398..6ac765c 100644 --- a/src/cs4/Seimei/src/Cdvd.h +++ b/src/cs4/Seimei/src/Cdvd.h @@ -1,23 +1,25 @@ #ifndef CDVD_H #define CDVD_H + +typedef struct /* @anon4 */ { + // Members + unsigned int lsn; // offset 0x0, size 0x4 + unsigned int size; // offset 0x4, size 0x4 + char name[16]; // offset 0x8, size 0x10 + unsigned char date[8]; // offset 0x18, size 0x8 + unsigned int flag; // offset 0x20, size 0x4 +} CDLFILE; + /* Compile unit: C:\cs4\Seimei\src\Cdvd.c Producer: MW MIPS C Compiler Language: C */ -static // total size: 0x14C -struct /* @anon1 */ { +typedef struct /* @anon1 */ { // Members // total size: 0x24 - struct /* @anon0 */ { - // Members - unsigned int lsn; // offset 0x0, size 0x4 - unsigned int size; // offset 0x4, size 0x4 - char name[16]; // offset 0x8, size 0x10 - unsigned char date[8]; // offset 0x18, size 0x8 - unsigned int flag; // offset 0x20, size 0x4 - } cdlfile; // offset 0x0, size 0x24 + CDLFILE cdlfile; char fname[128]; // offset 0x24, size 0x80 char sname[128]; // offset 0xA4, size 0x80 signed int state; // offset 0x124, size 0x4 @@ -31,19 +33,10 @@ struct /* @anon1 */ { unsigned char unused[3]; // offset 0x141, size 0x3 unsigned char * * lplpAddr; // offset 0x144, size 0x4 unsigned char * lpDmyData; // offset 0x148, size 0x4 -} * lpSetCdvd; // size: 0x4, address: 0x257560 -static // total size: 0x14C -struct /* @anon1 */ { - // Members - // total size: 0x24 - struct /* @anon0 */ { - // Members - unsigned int lsn; // offset 0x0, size 0x4 - unsigned int size; // offset 0x4, size 0x4 - char name[16]; // offset 0x8, size 0x10 - unsigned char date[8]; // offset 0x18, size 0x8 - unsigned int flag; // offset 0x20, size 0x4 - } cdlfile; // offset 0x0, size 0x24 +} LPSETCDVD ; // size: 0x4, address: 0x257560 + +typedef struct /* @anon1 */ { + CDLFILE cdlfile; char fname[128]; // offset 0x24, size 0x80 char sname[128]; // offset 0xA4, size 0x80 signed int state; // offset 0x124, size 0x4 @@ -57,19 +50,12 @@ struct /* @anon1 */ { unsigned char unused[3]; // offset 0x141, size 0x3 unsigned char * * lplpAddr; // offset 0x144, size 0x4 unsigned char * lpDmyData; // offset 0x148, size 0x4 -} * lpLastCdvd; // size: 0x4, address: 0x257564 -static // total size: 0x14C -struct /* @anon1 */ { - // Members - // total size: 0x24 - struct /* @anon0 */ { - // Members - unsigned int lsn; // offset 0x0, size 0x4 - unsigned int size; // offset 0x4, size 0x4 - char name[16]; // offset 0x8, size 0x10 - unsigned char date[8]; // offset 0x18, size 0x8 - unsigned int flag; // offset 0x20, size 0x4 - } cdlfile; // offset 0x0, size 0x24 +} LPLASTCDVD; // size: 0x4, address: 0x257564 + +typedef struct /* @anon1 */ { + + CDLFILE cdlfile; + char fname[128]; // offset 0x24, size 0x80 char sname[128]; // offset 0xA4, size 0x80 signed int state; // offset 0x124, size 0x4 @@ -83,19 +69,12 @@ struct /* @anon1 */ { unsigned char unused[3]; // offset 0x141, size 0x3 unsigned char * * lplpAddr; // offset 0x144, size 0x4 unsigned char * lpDmyData; // offset 0x148, size 0x4 -} * lpCdvdRead; // size: 0x4, address: 0x257568 -// total size: 0x14C -struct /* @anon1 */ { +} LPCDVDREAD; // size: 0x4, address: 0x257568 + +typedef struct /* @anon1 */ { // Members // total size: 0x24 - struct /* @anon0 */ { - // Members - unsigned int lsn; // offset 0x0, size 0x4 - unsigned int size; // offset 0x4, size 0x4 - char name[16]; // offset 0x8, size 0x10 - unsigned char date[8]; // offset 0x18, size 0x8 - unsigned int flag; // offset 0x20, size 0x4 - } cdlfile; // offset 0x0, size 0x24 + CDLFILE cdlfile; char fname[128]; // offset 0x24, size 0x80 char sname[128]; // offset 0xA4, size 0x80 signed int state; // offset 0x124, size 0x4 @@ -109,7 +88,38 @@ struct /* @anon1 */ { unsigned char unused[3]; // offset 0x141, size 0x3 unsigned char * * lplpAddr; // offset 0x144, size 0x4 unsigned char * lpDmyData; // offset 0x148, size 0x4 -} CdvdReadSt[256]; // size: 0x14C00, address: 0xA01200 -unsigned int GlobalLoadTimer; // size: 0x4, address: 0x257894 +} CDVDREADST; // size: 0x14C00, address: 0xA01200 + +/* + Compile unit: C:\cs4\Seimei\src\Binder.c + Producer: MW MIPS C Compiler + Language: C +*/ +typedef struct /* @anon3 */ { + // Members + // total size: 0x24 +// offset 0x0, size 0x24 + CDLFILE cdlfile; + char fname[128]; // offset 0x24, size 0x80 + char sname[128]; // offset 0xA4, size 0x80 + signed int state; // offset 0x124, size 0x4 + signed int fileType; // offset 0x128, size 0x4 + signed int index; // offset 0x12C, size 0x4 + signed int fhd; // offset 0x130, size 0x4 + signed int size; // offset 0x134, size 0x4 + signed int sector; // offset 0x138, size 0x4 + unsigned int align; // offset 0x13C, size 0x4 + unsigned char retry; // offset 0x140, size 0x1 + unsigned char unused[3]; // offset 0x141, size 0x3 + unsigned char * * lplpAddr; // offset 0x144, size 0x4 + unsigned char * lpDmyData; // offset 0x148, size 0x4 +} LPCDVD; // size: 0x4, address: 0x257528 + +static LPCDVD *lpCdvd; +static LPSETCDVD *lpSetCdvd; +static LPLASTCDVD *lpLastCdvd; +static LPCDVDREAD *lpCdvdRead; +static CDVDREADST CdvdReadSt[256]; +extern unsigned int GlobalLoadTimer; // size: 0x4, address: 0x257894 #endif // CDVD_H diff --git a/src/cs4/Seimei/src/Memory.h b/src/cs4/Seimei/src/Memory.h index 5fec60c..4bce410 100644 --- a/src/cs4/Seimei/src/Memory.h +++ b/src/cs4/Seimei/src/Memory.h @@ -2,4 +2,6 @@ #define MEMORY_H void MemInit(); + +void * MemAllocAlignReal(unsigned int size /* r11 */, unsigned int align /* r2 */, char * lpFuncName /* r2 */, char * lpUseName /* r2 */); #endif