keep only one handle of the NAND file around

This commit is contained in:
RSDuck 2021-01-17 19:56:02 +01:00
parent 53d5def919
commit 1d6cc3c6ef
5 changed files with 60 additions and 46 deletions

View File

@ -74,6 +74,9 @@ DSi_NDMA* NDMAs[8];
DSi_SDHost* SDMMC; DSi_SDHost* SDMMC;
DSi_SDHost* SDIO; DSi_SDHost* SDIO;
FILE* SDMMCFile;
FILE* SDIOFile;
u64 ConsoleID; u64 ConsoleID;
u8 eMMC_CID[16]; u8 eMMC_CID[16];
@ -122,6 +125,8 @@ void DeInit()
delete SDMMC; delete SDMMC;
delete SDIO; delete SDIO;
CloseDSiNAND();
} }
void Reset() void Reset()
@ -302,12 +307,11 @@ bool LoadNAND()
memset(NWRAMEnd, 0, sizeof(NWRAMEnd)); memset(NWRAMEnd, 0, sizeof(NWRAMEnd));
memset(NWRAMMask, 0, sizeof(NWRAMMask)); memset(NWRAMMask, 0, sizeof(NWRAMMask));
FILE* f = Platform::OpenLocalFile(Config::DSiNANDPath, "rb"); if (SDMMCFile)
if (f)
{ {
u32 bootparams[8]; u32 bootparams[8];
fseek(f, 0x220, SEEK_SET); fseek(SDMMCFile, 0x220, SEEK_SET);
fread(bootparams, 4, 8, f); fread(bootparams, 4, 8, SDMMCFile);
printf("ARM9: offset=%08X size=%08X RAM=%08X size_aligned=%08X\n", printf("ARM9: offset=%08X size=%08X RAM=%08X size_aligned=%08X\n",
bootparams[0], bootparams[1], bootparams[2], bootparams[3]); bootparams[0], bootparams[1], bootparams[2], bootparams[3]);
@ -320,8 +324,8 @@ bool LoadNAND()
MBK[1][8] = 0; MBK[1][8] = 0;
u32 mbk[12]; u32 mbk[12];
fseek(f, 0x380, SEEK_SET); fseek(SDMMCFile, 0x380, SEEK_SET);
fread(mbk, 4, 12, f); fread(mbk, 4, 12, SDMMCFile);
MapNWRAM_A(0, mbk[0] & 0xFF); MapNWRAM_A(0, mbk[0] & 0xFF);
MapNWRAM_A(1, (mbk[0] >> 8) & 0xFF); MapNWRAM_A(1, (mbk[0] >> 8) & 0xFF);
@ -375,12 +379,12 @@ bool LoadNAND()
AES_init_ctx_iv(&ctx, boot2key, boot2iv); AES_init_ctx_iv(&ctx, boot2key, boot2iv);
fseek(f, bootparams[0], SEEK_SET); fseek(SDMMCFile, bootparams[0], SEEK_SET);
dstaddr = bootparams[2]; dstaddr = bootparams[2];
for (u32 i = 0; i < bootparams[3]; i += 16) for (u32 i = 0; i < bootparams[3]; i += 16)
{ {
u8 data[16]; u8 data[16];
fread(data, 16, 1, f); fread(data, 16, 1, SDMMCFile);
for (int j = 0; j < 16; j++) tmp[j] = data[15-j]; for (int j = 0; j < 16; j++) tmp[j] = data[15-j];
AES_CTR_xcrypt_buffer(&ctx, tmp, 16); AES_CTR_xcrypt_buffer(&ctx, tmp, 16);
@ -400,12 +404,12 @@ bool LoadNAND()
AES_init_ctx_iv(&ctx, boot2key, boot2iv); AES_init_ctx_iv(&ctx, boot2key, boot2iv);
fseek(f, bootparams[4], SEEK_SET); fseek(SDMMCFile, bootparams[4], SEEK_SET);
dstaddr = bootparams[6]; dstaddr = bootparams[6];
for (u32 i = 0; i < bootparams[7]; i += 16) for (u32 i = 0; i < bootparams[7]; i += 16)
{ {
u8 data[16]; u8 data[16];
fread(data, 16, 1, f); fread(data, 16, 1, SDMMCFile);
for (int j = 0; j < 16; j++) tmp[j] = data[15-j]; for (int j = 0; j < 16; j++) tmp[j] = data[15-j];
AES_CTR_xcrypt_buffer(&ctx, tmp, 16); AES_CTR_xcrypt_buffer(&ctx, tmp, 16);
@ -427,25 +431,22 @@ bool LoadNAND()
// read the nocash footer // read the nocash footer
fseek(f, -0x40, SEEK_END); fseek(SDMMCFile, -0x40, SEEK_END);
char nand_footer[16]; char nand_footer[16];
const char* nand_footer_ref = "DSi eMMC CID/CPU"; const char* nand_footer_ref = "DSi eMMC CID/CPU";
fread(nand_footer, 1, 16, f); fread(nand_footer, 1, 16, SDMMCFile);
if (memcmp(nand_footer, nand_footer_ref, 16)) if (memcmp(nand_footer, nand_footer_ref, 16))
{ {
printf("ERROR: NAND missing nocash footer\n"); printf("ERROR: NAND missing nocash footer\n");
fclose(f);
return false; return false;
} }
fread(eMMC_CID, 1, 16, f); fread(eMMC_CID, 1, 16, SDMMCFile);
fread(&ConsoleID, 1, 8, f); fread(&ConsoleID, 1, 8, SDMMCFile);
printf("eMMC CID: "); printhex(eMMC_CID, 16); printf("eMMC CID: "); printhex(eMMC_CID, 16);
printf("Console ID: %016llX\n", ConsoleID); printf("Console ID: %016llX\n", ConsoleID);
fclose(f);
} }
memset(ITCMInit, 0, 0x8000); memset(ITCMInit, 0, 0x8000);
@ -463,6 +464,13 @@ bool LoadNAND()
return true; return true;
} }
void CloseDSiNAND()
{
if (DSi::SDMMCFile)
fclose(DSi::SDMMCFile);
if (DSi::SDIOFile)
fclose(DSi::SDIOFile);
}
void RunNDMAs(u32 cpu) void RunNDMAs(u32 cpu)
{ {

View File

@ -36,6 +36,9 @@ extern u64 ConsoleID;
extern DSi_SDHost* SDMMC; extern DSi_SDHost* SDMMC;
extern DSi_SDHost* SDIO; extern DSi_SDHost* SDIO;
extern FILE* SDMMCFile;
extern FILE* SDIOFile;
const u32 NWRAMSize = 0x40000; const u32 NWRAMSize = 0x40000;
extern u8* NWRAM_A; extern u8* NWRAM_A;
@ -59,6 +62,8 @@ void SoftReset();
bool LoadBIOS(); bool LoadBIOS();
bool LoadNAND(); bool LoadNAND();
void CloseDSiNAND();
void RunNDMAs(u32 cpu); void RunNDMAs(u32 cpu);
void StallNDMAs(); void StallNDMAs();
bool NDMAsInMode(u32 cpu, u32 mode); bool NDMAsInMode(u32 cpu, u32 mode);

View File

@ -114,14 +114,14 @@ void DSi_SDHost::Reset()
if (Config::DSiSDEnable) if (Config::DSiSDEnable)
{ {
sd = new DSi_MMCStorage(this, false, Config::DSiSDPath); sd = new DSi_MMCStorage(this, false, DSi::SDIOFile);
u8 sd_cid[16] = {0xBD, 0x12, 0x34, 0x56, 0x78, 0x03, 0x4D, 0x30, 0x30, 0x46, 0x50, 0x41, 0x00, 0x00, 0x15, 0x00}; u8 sd_cid[16] = {0xBD, 0x12, 0x34, 0x56, 0x78, 0x03, 0x4D, 0x30, 0x30, 0x46, 0x50, 0x41, 0x00, 0x00, 0x15, 0x00};
sd->SetCID(sd_cid); sd->SetCID(sd_cid);
} }
else else
sd = nullptr; sd = nullptr;
mmc = new DSi_MMCStorage(this, true, Config::DSiNANDPath); mmc = new DSi_MMCStorage(this, true, DSi::SDMMCFile);
mmc->SetCID(DSi::eMMC_CID); mmc->SetCID(DSi::eMMC_CID);
Ports[0] = sd; Ports[0] = sd;
@ -706,30 +706,14 @@ void DSi_SDHost::CheckSwapFIFO()
#define MMC_DESC (Internal?"NAND":"SDcard") #define MMC_DESC (Internal?"NAND":"SDcard")
DSi_MMCStorage::DSi_MMCStorage(DSi_SDHost* host, bool internal, const char* path) : DSi_SDDevice(host) DSi_MMCStorage::DSi_MMCStorage(DSi_SDHost* host, bool internal, FILE* file) : DSi_SDDevice(host)
{ {
Internal = internal; Internal = internal;
strncpy(FilePath, path, 1023); FilePath[1023] = '\0'; File = file;
File = Platform::OpenLocalFile(path, "r+b");
if (!File)
{
if (internal)
{
// TODO: proper failure
printf("!! MMC file %s does not exist\n", path);
}
else
{
File = Platform::OpenLocalFile(path, "w+b");
}
}
} }
DSi_MMCStorage::~DSi_MMCStorage() DSi_MMCStorage::~DSi_MMCStorage()
{ {}
if (File) fclose(File);
}
void DSi_MMCStorage::Reset() void DSi_MMCStorage::Reset()
{ {

View File

@ -120,7 +120,7 @@ protected:
class DSi_MMCStorage : public DSi_SDDevice class DSi_MMCStorage : public DSi_SDDevice
{ {
public: public:
DSi_MMCStorage(DSi_SDHost* host, bool internal, const char* path); DSi_MMCStorage(DSi_SDHost* host, bool internal, FILE* file);
~DSi_MMCStorage(); ~DSi_MMCStorage();
void Reset(); void Reset();
@ -134,7 +134,6 @@ public:
private: private:
bool Internal; bool Internal;
char FilePath[1024];
FILE* File; FILE* File;
u8 CID[16]; u8 CID[16];

View File

@ -25,6 +25,7 @@
#include "Platform.h" #include "Platform.h"
#include "NDS.h" #include "NDS.h"
#include "DSi.h"
#include "GBACart.h" #include "GBACart.h"
#include "AREngine.h" #include "AREngine.h"
@ -199,18 +200,27 @@ int VerifyDSiFirmware()
return Load_OK; return Load_OK;
} }
int VerifyDSiNAND() int SetupDSiNAND()
{ {
FILE* f; FILE* f;
long len; long len;
f = Platform::OpenLocalFile(Config::DSiNANDPath, "rb"); f = Platform::OpenLocalFile(Config::DSiNANDPath, "r+b");
if (!f) return Load_DSiNANDMissing; if (!f) return Load_DSiNANDMissing;
// TODO: some basic checks // TODO: some basic checks
// check that it has the nocash footer, and all // check that it has the nocash footer, and all
fclose(f); DSi::SDMMCFile = f;
if (Config::DSiSDEnable)
{
f = Platform::OpenLocalFile(Config::DSiSDPath, "r+b");
if (f)
DSi::SDIOFile = f;
else
DSi::SDIOFile = Platform::OpenLocalFile(Config::DSiSDPath, "w+b");
}
return Load_OK; return Load_OK;
} }
@ -243,6 +253,8 @@ void LoadCheats()
int LoadBIOS() int LoadBIOS()
{ {
DSi::CloseDSiNAND();
int res; int res;
res = VerifyDSBIOS(); res = VerifyDSBIOS();
@ -256,7 +268,7 @@ int LoadBIOS()
res = VerifyDSiFirmware(); res = VerifyDSiFirmware();
if (res != Load_OK) return res; if (res != Load_OK) return res;
res = VerifyDSiNAND(); res = SetupDSiNAND();
if (res != Load_OK) return res; if (res != Load_OK) return res;
} }
else else
@ -285,6 +297,8 @@ int LoadBIOS()
int LoadROM(const char* file, int slot) int LoadROM(const char* file, int slot)
{ {
DSi::CloseDSiNAND();
int res; int res;
bool directboot = Config::DirectBoot != 0; bool directboot = Config::DirectBoot != 0;
@ -305,7 +319,7 @@ int LoadROM(const char* file, int slot)
res = VerifyDSiFirmware(); res = VerifyDSiFirmware();
if (res != Load_OK) return res; if (res != Load_OK) return res;
res = VerifyDSiNAND(); res = SetupDSiNAND();
if (res != Load_OK) return res; if (res != Load_OK) return res;
GBACart::Eject(); GBACart::Eject();
@ -376,10 +390,14 @@ void UnloadROM(int slot)
} }
ROMPath[slot][0] = '\0'; ROMPath[slot][0] = '\0';
DSi::CloseDSiNAND();
} }
int Reset() int Reset()
{ {
DSi::CloseDSiNAND();
int res; int res;
bool directboot = Config::DirectBoot != 0; bool directboot = Config::DirectBoot != 0;
@ -394,7 +412,7 @@ int Reset()
res = VerifyDSiFirmware(); res = VerifyDSiFirmware();
if (res != Load_OK) return res; if (res != Load_OK) return res;
res = VerifyDSiNAND(); res = SetupDSiNAND();
if (res != Load_OK) return res; if (res != Load_OK) return res;
GBACart::Eject(); GBACart::Eject();