From 5b6318ee3a2f17c2c5ac3815ffdbf421eb666785 Mon Sep 17 00:00:00 2001 From: Pablo Curiel Date: Tue, 6 Sep 2016 22:26:48 -0400 Subject: [PATCH 1/3] Support additional EmuNAND layouts. Fixes compatibility with a second EmuNAND placed after an EmuNAND created with either the 'default' or 'minimum' setup sizes with EmuNAND9 / 3DS Multi EmuNAND Creator. --- source/emunand.c | 68 ++++++++++++++++++++++++++++++++---------------- source/emunand.h | 1 + 2 files changed, 46 insertions(+), 23 deletions(-) diff --git a/source/emunand.c b/source/emunand.c index 9d31e40..ace1d29 100644 --- a/source/emunand.c +++ b/source/emunand.c @@ -25,37 +25,59 @@ #include "fatfs/sdmmc/sdmmc.h" #include "../build/emunandpatch.h" +#define O3DS_LEGACY_FAT 0x200000 +#define O3DS_DEFAULT_FAT 0x1DE000 +#define O3DS_MINIMUM_FAT 0x1D8000 + +#define N3DS_LEGACY_FAT 0x400000 +#define N3DS_DEFAULT_FAT 0x3B2000 +#define N3DS_MINIMUM_FAT 0x26E000 + void locateEmuNand(u32 *off, u32 *head, FirmwareSource *emuNand) { static u8 temp[0x200]; - + const u32 nandSize = getMMCDevice(0)->total_size; - u32 nandOffset = *emuNand == FIRMWARE_EMUNAND ? 0 : - (nandSize > 0x200000 ? 0x400000 : 0x200000); - - //Check for RedNAND - if(!sdmmc_sdcard_readsectors(nandOffset + 1, 1, temp) && - *(u32 *)(temp + 0x100) == NCSD_MAGIC) - { - *off = nandOffset + 1; - *head = nandOffset + 1; - } - - //Check for Gateway emuNAND - else if(!sdmmc_sdcard_readsectors(nandOffset + nandSize, 1, temp) && - *(u32 *)(temp + 0x100) == NCSD_MAGIC) - { - *off = nandOffset; - *head = nandOffset + nandSize; - } - + const u32 nandLayoutO3DS[3] = { O3DS_LEGACY_FAT, O3DS_DEFAULT_FAT, O3DS_MINIMUM_FAT }; // Legacy, Default, Minimum + const u32 nandLayoutN3DS[3] = { N3DS_LEGACY_FAT, N3DS_DEFAULT_FAT, N3DS_MINIMUM_FAT }; // Legacy, Default, Minimum + + u8 i; + u32 nandOffset; + bool found = false; + + for (i = 0; i < 3; i++) + { + if (i > 0 && *emuNand != FIRMWARE_EMUNAND2) break; + + // Check for 'Legacy', 'Default' and 'Minimum' partition layouts when checking for the 2nd EmuNAND + nandOffset = (*emuNand == FIRMWARE_EMUNAND ? 0 : (isN3DS ? nandLayoutN3DS[i] : nandLayoutO3DS[i])); + + //Check for RedNAND + if(!sdmmc_sdcard_readsectors(nandOffset + 1, 1, temp) && *(u32 *)(temp + 0x100) == NCSD_MAGIC) + { + *off = nandOffset + 1; + *head = nandOffset + 1; + found = true; + break; + } + + //Check for Gateway emuNAND + else if(!sdmmc_sdcard_readsectors(nandOffset + nandSize, 1, temp) && *(u32 *)(temp + 0x100) == NCSD_MAGIC) + { + *off = nandOffset; + *head = nandOffset + nandSize; + found = true; + break; + } + } + /* Fallback to the first emuNAND if there's no second one, or to SysNAND if there isn't any */ - else - { + if (!found) + { *emuNand = (*emuNand == FIRMWARE_EMUNAND2) ? FIRMWARE_EMUNAND : FIRMWARE_SYSNAND; if(*emuNand) locateEmuNand(off, head, emuNand); - } + } } static inline u8 *getFreeK9Space(u8 *pos, u32 size) diff --git a/source/emunand.h b/source/emunand.h index 543fbe0..8c8fd89 100644 --- a/source/emunand.h +++ b/source/emunand.h @@ -27,6 +27,7 @@ #define NCSD_MAGIC 0x4453434E extern u32 emuOffset; +extern bool isN3DS; void locateEmuNand(u32 *off, u32 *head, FirmwareSource *emuNand); void patchEmuNand(u8 *arm9Section, u32 arm9SectionSize, u8 *process9Offset, u32 process9Size, u32 emuHeader, u32 branchAdditive); \ No newline at end of file From 99654bd5b24adaf4d30057b7687038ded87aab65 Mon Sep 17 00:00:00 2001 From: Pablo Curiel Date: Wed, 7 Sep 2016 11:25:20 -0400 Subject: [PATCH 2/3] Fix compatibility with 2DS. Adds a check to determine if the NAND size is greater than the size of an Old 3DS Toshiba NAND. --- source/emunand.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/source/emunand.c b/source/emunand.c index ace1d29..c2db014 100644 --- a/source/emunand.c +++ b/source/emunand.c @@ -25,6 +25,8 @@ #include "fatfs/sdmmc/sdmmc.h" #include "../build/emunandpatch.h" +#define O3DS_TOSHIBA_NAND 0x1DD000 + #define O3DS_LEGACY_FAT 0x200000 #define O3DS_DEFAULT_FAT 0x1DE000 #define O3DS_MINIMUM_FAT 0x1D8000 @@ -50,7 +52,7 @@ void locateEmuNand(u32 *off, u32 *head, FirmwareSource *emuNand) if (i > 0 && *emuNand != FIRMWARE_EMUNAND2) break; // Check for 'Legacy', 'Default' and 'Minimum' partition layouts when checking for the 2nd EmuNAND - nandOffset = (*emuNand == FIRMWARE_EMUNAND ? 0 : (isN3DS ? nandLayoutN3DS[i] : nandLayoutO3DS[i])); + nandOffset = (*emuNand == FIRMWARE_EMUNAND ? 0 : ((isN3DS || nandSize > O3DS_TOSHIBA_NAND) ? nandLayoutN3DS[i] : nandLayoutO3DS[i])); //Check for RedNAND if(!sdmmc_sdcard_readsectors(nandOffset + 1, 1, temp) && *(u32 *)(temp + 0x100) == NCSD_MAGIC) From a331fcd8737abf5178bbd790f8f0229ae4473442 Mon Sep 17 00:00:00 2001 From: Pablo Curiel Date: Wed, 7 Sep 2016 11:33:05 -0400 Subject: [PATCH 3/3] Add minimum NAND size exception for 2DS. --- source/emunand.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/source/emunand.c b/source/emunand.c index c2db014..5fe88f9 100644 --- a/source/emunand.c +++ b/source/emunand.c @@ -54,6 +54,9 @@ void locateEmuNand(u32 *off, u32 *head, FirmwareSource *emuNand) // Check for 'Legacy', 'Default' and 'Minimum' partition layouts when checking for the 2nd EmuNAND nandOffset = (*emuNand == FIRMWARE_EMUNAND ? 0 : ((isN3DS || nandSize > O3DS_TOSHIBA_NAND) ? nandLayoutN3DS[i] : nandLayoutO3DS[i])); + // Exception for 2DS + if (i == 2 && !isN3DS && nandOffset == N3DS_MINIMUM_FAT) nandOffset = O3DS_MINIMUM_FAT; + //Check for RedNAND if(!sdmmc_sdcard_readsectors(nandOffset + 1, 1, temp) && *(u32 *)(temp + 0x100) == NCSD_MAGIC) {