From f14d3b157dcd28371cfec6ace87b8a98a73956c1 Mon Sep 17 00:00:00 2001 From: robojumper Date: Fri, 17 May 2024 12:03:34 +0200 Subject: [PATCH] One regswap and one thunk away --- config/SOUE01/symbols.txt | 6 +- include/egg/core/eggArchive.h | 2 +- include/egg/core/eggDvdRipper.h | 2 +- src/d/d_heap.cpp | 2 +- src/m/m_dvd.cpp | 146 +++++++++++++++++++++++++------- 5 files changed, 121 insertions(+), 37 deletions(-) diff --git a/config/SOUE01/symbols.txt b/config/SOUE01/symbols.txt index 1a34ef73..0a25394e 100644 --- a/config/SOUE01/symbols.txt +++ b/config/SOUE01/symbols.txt @@ -17734,7 +17734,7 @@ run__Q24mDvd10MyThread_cFP12mDvd_param_c = .text:0x802EEE10; // type:function si __ct__Q24mDvd10MyThread_cFiPQ23EGG4Heap = .text:0x802EEE40; // type:function size:0x4C run__Q24mDvd10MyThread_cFv = .text:0x802EEE90; // type:function size:0x8 create__4mDvdFiPQ23EGG4HeapPQ23EGG4HeapPQ23EGG4Heap = .text:0x802EEEA0; // type:function size:0x88 -loadToMainRAM__4mDvdFiPcPQ23EGG4HeapQ33EGG9DvdRipper15EAllocDirectionUlPUlPUlUl = .text:0x802EEF30; // type:function size:0x158 +loadToMainRAM__4mDvdFiPcPQ23EGG4HeapQ33EGG9DvdRipper15EAllocDirectionlPUlPUlUl = .text:0x802EEF30; // type:function size:0x158 ConvertPathToEntrynum__4mDvdFPCc = .text:0x802EF090; // type:function size:0x8 IsExistPath__4mDvdFPCc = .text:0x802EF0A0; // type:function size:0x30 __dt__14mDvd_command_cFv = .text:0x802EF0D0; // type:function size:0x60 @@ -17776,7 +17776,7 @@ __dt__21mDvd_toMainRam_base_cFv = .text:0x802EFC80; // type:function size:0x58 __dt__20mDvd_toMainRam_arc_cFv = .text:0x802EFCE0; // type:function size:0x58 __ct__20mDvd_toMainRam_arc_cFPQ23EGG7Archiveii = .text:0x802EFD40; // type:function size:0x60 makeRequest__20mDvd_toMainRam_arc_cFPQ23EGG7ArchiveiiPQ23EGG4Heap = .text:0x802EFDA0; // type:function size:0x80 -create__FPQ23EGG7ArchivePCciPQ23EGG4Heap = .text:0x802EFE20; // type:function size:0x64 +create__20mDvd_toMainRam_arc_cFPQ23EGG7ArchivePCciPQ23EGG4Heap = .text:0x802EFE20; // type:function size:0x64 fn_802EFE90 = .text:0x802EFE90; // type:function size:0x30 execute__20mDvd_toMainRam_arc_cFv = .text:0x802EFEC0; // type:function size:0x78 __ct__23mDvd_toMainRam_normal_cFi = .text:0x802EFF40; // type:function size:0x4C @@ -40269,7 +40269,7 @@ sThread__4mDvd = .sbss:0x80575C24; // type:object size:0x4 data:4byte sCommandHeap__4mDvd = .sbss:0x80575C28; // type:object size:0x4 data:4byte sArchiveHeap__4mDvd = .sbss:0x80575C2C; // type:object size:0x4 data:4byte isAutoStreamDecomp__4mDvd = .sbss:0x80575C30; // type:object size:0x1 data:byte -isRegistered__4mDvd = .sbss:0x80575C31; // type:object size:0x1 data:byte +@GUARD@loadToMainRAM__4mDvdFiPcPQ23EGG4HeapQ33EGG9DvdRipper15EAllocDirectionUlPUlPUlUl@DvdFile = .sbss:0x80575C31; // type:object size:0x1 data:byte mInstance__12mDvd_param_c = .sbss:0x80575C34; // type:object size:0x4 data:4byte s_SavedCurrentHeap__5mHeap = .sbss:0x80575C38; // type:object size:0x4 data:4byte g_archiveHeap__5mHeap = .sbss:0x80575C3C; // type:object size:0x4 data:4byte diff --git a/include/egg/core/eggArchive.h b/include/egg/core/eggArchive.h index 4600a3f8..72f2ec97 100644 --- a/include/egg/core/eggArchive.h +++ b/include/egg/core/eggArchive.h @@ -40,7 +40,7 @@ public: /* 80493760 */ static Archive *findArchive(NANDFileInfo *file); /* 804937f0 */ static void appendList(Archive *); // prob private /* 80493850 */ static void removeList(Archive *); - /* 80493860 */ static Archive *mount(void *data, Heap *heap, s32 align); + /* 80493860 */ static Archive *mount(void *data, Heap *heap, int align); /* 80493950 */ static Archive *mountFST(void *data, Heap *heap, s32 align); /* 80493a40 */ static Archive *mountNandFile(NANDFileInfo *, Heap *heap, s32 align); /* 80493ac0 */ static Archive *loadFST(const char *fileName, Heap *heap, s32 align); diff --git a/include/egg/core/eggDvdRipper.h b/include/egg/core/eggDvdRipper.h index 873508d6..fc2cc374 100644 --- a/include/egg/core/eggDvdRipper.h +++ b/include/egg/core/eggDvdRipper.h @@ -20,7 +20,7 @@ public: /* 804947e0 */ static u8 *loadToMainRAM(DvdFile *file, u8 *dst, Heap *heap, EAllocDirection allocDir, u32 offset, u32 *amountRead, u32 *fileSize); /* 804949b0 */ static void *loadToMainRAMDecomp(DvdFile *file, StreamDecomp *decompressor, u8 *dst, Heap *heap, - EAllocDirection allocDir, u32 offset, s32 size, u32 maxChunkSize, u32 *amountRead, u32 *fileSize); + EAllocDirection allocDir, s32 offset, u32 size, u32 maxChunkSize, u32 *amountRead, u32 *fileSize); public: /* 80574ed0 */ static bool sErrorRetry; diff --git a/src/d/d_heap.cpp b/src/d/d_heap.cpp index a29ba328..16ad0f70 100644 --- a/src/d/d_heap.cpp +++ b/src/d/d_heap.cpp @@ -18,7 +18,7 @@ extern "C" void fn_802DE710(); // TODO TU splits? void dHeapAllocator::onAlloc(EGG::HeapAllocArg *arg) { - if (arg->heap != nullptr) { + if (arg->ptr != nullptr) { return; } if (lbl_80571C58 == 0) { diff --git a/src/m/m_dvd.cpp b/src/m/m_dvd.cpp index 8c9b60b8..48718fe7 100644 --- a/src/m/m_dvd.cpp +++ b/src/m/m_dvd.cpp @@ -5,6 +5,11 @@ #include #include #include +#include +// clang-format off +// TODO a define in here stomps another header +#include +// clang-format on namespace mDvd { @@ -38,7 +43,6 @@ mDvd::MyThread_c *sThread; EGG::Heap *sCommandHeap; EGG::Heap *sArchiveHeap; bool isAutoStreamDecomp; -bool isRegistered; /** 802eece0 */ extern "C" void fn_802EECE0(TUncompressInfo_Base_c **ptr, TUncompressInfo_Base_c **last) { @@ -119,19 +123,40 @@ void create(int priority, EGG::Heap *commandHeap, EGG::Heap *archiveHeap, EGG::H } /** 802eef30 */ -void *loadToMainRAM(int entryNum, char *dst, EGG::Heap *heap, EGG::DvdRipper::EAllocDirection allocDir, u32 offset, +void *loadToMainRAM(int entryNum, char *dst, EGG::Heap *heap, EGG::DvdRipper::EAllocDirection allocDir, s32 offset, u32 *p6, u32 *p7, u32 decompressorType) { - // TODO + void *result; + u32 amountRead = 0; + u32 fileSize = 0; - if (decompressorType == 0) { - } else { - extern EGG::DvdFile DvdFile; - if (mDvd::isRegistered == false) { - static EGG::DvdFile DvdFile; + if (decompressorType != 0) { + EGG::StreamDecomp *decomp = newUncompressObj(decompressorType); + static EGG::DvdFile DvdFile; + DvdFile.open(entryNum); - isRegistered = true; + result = EGG::DvdRipper::loadToMainRAMDecomp(&DvdFile, decomp, (u8 *)dst, heap, allocDir, offset, 0, + maxChunkSize, nullptr, nullptr); + + deleteUncompressObj(decompressorType); + u32 size = DvdFile.mFileInfo.size; + DvdFile.close(); + if (result != nullptr) { + u32 b = EGG::ExpHeap::getSizeForMBlock(result); + DCStoreRangeNoSync(result, b); + fileSize = size; + amountRead = size; } + } else { + result = EGG::DvdRipper::loadToMainRAM(entryNum, (u8 *)dst, heap, allocDir, offset, &amountRead, &fileSize); } + + if (p6 != nullptr) { + *p6 = amountRead; + } + if (p7 != nullptr) { + *p7 = fileSize; + } + return result; } int ConvertPathToEntrynum(const char *path) { @@ -316,7 +341,11 @@ mDvdCommandReadCallback_c *mDvdCommandReadCallback_c::create(dvdReadCallback cb, } /** 802ef650 */ -extern "C" void fn_802EF650() {} +extern "C" mDvdCommandReadCallback_c *fn_802EF650(dvdReadCallback cb, void *cbData) { + mDvdCommandReadCallback_c *cmd = mDvdCommandReadCallback_c::create(cb, cbData); + while (!cmd) {} + return cmd; +} /** 802ef680 */ u32 mDvdCommandReadCallback_c::execute() { @@ -343,7 +372,54 @@ mDvd_mountMemArchive_c::mDvd_mountMemArchive_c(int mountDirection) { /** 802ef7c0 */ int findPathWithCompressedExtension(const char *name, u8 *outType) { - return 0; // TODO + // TODO regswap + int num; + u8 type; + char buf[256]; + mDvd::TUncompressInfo_Base_c **ptr; + + type = 0; + buf[255] = '\0'; + num = -1; + + strncpy(buf, name, sizeof(buf)); + if (buf[255] == '\0') { + char *end = buf + strlen(buf); + // Append the compressor extension and try to find a compressed version + for (ptr = mDvd::compressors_ptr; ptr != mDvd::compressors_last; ptr++) { + strncpy(end, (*ptr)->mExtension, sizeof(buf) - (end - buf)); + num = DVDConvertPathToEntrynum(buf); + if (num != -1) { + type = (*ptr)->mType; + goto end; + } + } + // No compressed version found + *end = '\0'; + end = strrchr(buf, '/'); + if (end == nullptr) { + end = buf; + } + end = strrchr(end, '.'); + if (end != nullptr) { + // Append the compressor extension and try to find a compressed version + for (ptr = mDvd::compressors_ptr; ptr != mDvd::compressors_last; ptr++) { + strncpy(end, (*ptr)->mExtension, sizeof(buf) - (end - buf)); + num = DVDConvertPathToEntrynum(buf); + if (num != -1) { + type = (*ptr)->mType; + goto end; + } + } + *end = '\0'; + } + } + +end: + if (num != -1 && outType != nullptr) { + *outType = type; + } + return num; } /** 802ef930 */ @@ -356,13 +432,20 @@ bool getAutoStreamDecomp() { return mDvd::isAutoStreamDecomp; } -// TODO maybe weak /** 802ef950 */ int ConvertPathToEntrynum(const char *path, u8 *outType) { - return 0; // TODO + int num = DVDConvertPathToEntrynum(path); + if (num != -1) { + if (outType != nullptr) { + *outType = 0; + } + } else if (getAutoStreamDecomp()) { + num = findPathWithCompressedExtension(path, outType); + } + return num; } -// TODO thunk +// TODO This thunk needs to not be inlined! /** 802ef950 */ int ConvertPathToEntrynum_Thunk(const char *path, u8 *outType) { return ConvertPathToEntrynum(path, outType); @@ -388,32 +471,27 @@ mDvd_mountMemArchive_c *mDvd_mountMemArchive_c::create(const char *path, u8 moun /** 802efa80 */ u32 mDvd_mountMemArchive_c::execute() { - void *data; - int align; EGG::DvdRipper::EAllocDirection allocDirection; EGG::Archive *archive; + void *data; EGG::Heap *heap; heap = mHeap != nullptr ? mHeap : mDvd::sArchiveHeap; archive = nullptr; allocDirection = mMountDirection == 1 ? EGG::DvdRipper::ALLOC_DIR_TOP : EGG::DvdRipper::ALLOC_DIR_BOTTOM; - data = mDvd::loadToMainRAM(mEntryNum, nullptr, heap, allocDirection, 0, (u32 *)field_0x18, 0, mCompressionType); + data = mDvd::loadToMainRAM(mEntryNum, nullptr, heap, allocDirection, 0, &field_0x18, 0, mCompressionType); if (data != nullptr) { - align = -4; - if (mMountDirection == 1) { - align = 4; - } - archive = EGG::Archive::mount(data, heap, align); + archive = EGG::Archive::mount(data, heap, mMountDirection == 1 ? 4 : -4); } - if (archive == nullptr) { + if (archive != nullptr) { + mDataPtr = archive; + } else { if (data != nullptr) { delete data; } field_0x18 = 0; - } else { - mDataPtr = archive; } waitDone(); return (bool)mDataPtr; @@ -476,7 +554,8 @@ mDvd_toMainRam_arc_c *mDvd_toMainRam_arc_c::makeRequest(EGG::Archive *arc, int e } /** 802efe20 */ -mDvd_toMainRam_arc_c *create(EGG::Archive *arc, const char *path, int mountDirection, EGG::Heap *heap) { +mDvd_toMainRam_arc_c *mDvd_toMainRam_arc_c::create(EGG::Archive *arc, const char *path, int mountDirection, + EGG::Heap *heap) { int entryNum = arc->convertPathToEntryID(path); mDvd_toMainRam_arc_c *cmd = nullptr; if (entryNum != -1) { @@ -486,8 +565,10 @@ mDvd_toMainRam_arc_c *create(EGG::Archive *arc, const char *path, int mountDirec } /** 802efe90 */ -extern "C" void fn_802EFE90() { - // TODO +extern "C" mDvd_toMainRam_arc_c *fn_802EFE90(EGG::Archive *arc, const char *path, int mountDirection, EGG::Heap *heap) { + mDvd_toMainRam_arc_c *cmd = mDvd_toMainRam_arc_c::create(arc, path, mountDirection, heap); + while (!cmd) {} + return cmd; } /** 802efec0 */ @@ -524,8 +605,10 @@ mDvd_toMainRam_normal_c *mDvd_toMainRam_normal_c::create(const char *path, int m } /** 802f0030 */ -extern "C" void fn_802F0030() { - // TODO +extern "C" mDvd_toMainRam_normal_c *fn_802F0030(const char *path, int mountDirection, EGG::Heap *heap) { + mDvd_toMainRam_normal_c *cmd = mDvd_toMainRam_normal_c::create(path, mountDirection, heap); + while (!cmd) {} + return cmd; } /** 802f0060 */ @@ -545,7 +628,8 @@ u32 mDvd_toMainRam_normal_c::execute() { u32 p6; u32 p7; EGG::Heap *heap = mHeap != nullptr ? mHeap : mDvd::sArchiveHeap; - EGG::DvdRipper::EAllocDirection allocDirection = mMountDirection == 1 ? EGG::DvdRipper::ALLOC_DIR_TOP : EGG::DvdRipper::ALLOC_DIR_BOTTOM; + EGG::DvdRipper::EAllocDirection allocDirection = + mMountDirection == 1 ? EGG::DvdRipper::ALLOC_DIR_TOP : EGG::DvdRipper::ALLOC_DIR_BOTTOM; mDataPtr = mDvd::loadToMainRAM(mEntryNum, 0, heap, allocDirection, 0, &p6, &p7, mCompressionType2); if (mDataPtr != nullptr) { field_0x10 = p6;