Cleanup, fixed the second emuNAND patched FIRM still getting created, removed injector SOAP patch as it changes nothing without going to great lengths to change the region of a NNID, made L not needed to load payloads except for R and Select (Start is now default)
This commit is contained in:
parent
f7bbc4bfec
commit
0001f301f8
@ -176,42 +176,6 @@ void patchCode(u64 progid, u8 *code, u32 size)
|
||||
sizeof(skipEshopUpdateCheckPatch), 1
|
||||
);
|
||||
|
||||
if(R_SUCCEEDED(loadSecureinfo()))
|
||||
{
|
||||
static const char countryRespPattern[] = {
|
||||
0x01, 0x20, 0x01, 0x90, 0x22, 0x46, 0x06, 0x9B
|
||||
};
|
||||
static const char countryRespPatchModel[] = {
|
||||
0x06, 0x9A, 0x03, 0x20, 0x90, 0x47, 0x55, 0x21, 0x01, 0x70, 0x53, 0x21, 0x41, 0x70, 0x00, 0x21,
|
||||
0x81, 0x70, 0x60, 0x61, 0x00, 0x20
|
||||
};
|
||||
const char *country;
|
||||
char countryRespPatch[sizeof(countryRespPatchModel)];
|
||||
|
||||
switch(secureinfo[0x100])
|
||||
{
|
||||
case 1: country = "US"; break;
|
||||
case 2: country = "GB"; break; // sorry rest-of-Europe, you have to change this
|
||||
case 4: country = "CN"; break;
|
||||
case 5: country = "KR"; break;
|
||||
case 6: country = "TW"; break;
|
||||
default: case 0: country = "JP"; break;
|
||||
}
|
||||
//Patch XML response Country
|
||||
memcpy(countryRespPatch,
|
||||
countryRespPatchModel,
|
||||
sizeof(countryRespPatchModel)
|
||||
);
|
||||
countryRespPatch[6] = country[0];
|
||||
countryRespPatch[10] = country[1];
|
||||
patchMemory(code, size,
|
||||
countryRespPattern,
|
||||
sizeof(countryRespPattern), 0,
|
||||
countryRespPatch,
|
||||
sizeof(countryRespPatch), 1
|
||||
);
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
|
@ -5,8 +5,8 @@
|
||||
#define HID_PAD (*(vu32 *)0x10146000 ^ 0xFFF)
|
||||
#define BUTTON_X (1 << 10)
|
||||
#define BUTTON_Y (1 << 11)
|
||||
#define BUTTON_R1 (1 << 8)
|
||||
#define BUTTON_SELECT (1 << 2)
|
||||
#define BUTTON_START (1 << 3)
|
||||
#define BUTTON_RIGHT (1 << 4)
|
||||
#define BUTTON_LEFT (1 << 5)
|
||||
#define BUTTON_UP (1 << 6)
|
||||
|
@ -29,14 +29,14 @@ void main(void)
|
||||
//Get pressed buttons
|
||||
u32 pressed = HID_PAD;
|
||||
|
||||
if(((pressed & BUTTON_X) && loadPayload("/aurei/payloads/x.bin")) ||
|
||||
((pressed & BUTTON_Y) && loadPayload("/aurei/payloads/y.bin")) ||
|
||||
((pressed & BUTTON_SELECT) && loadPayload("/aurei/payloads/select.bin")) ||
|
||||
((pressed & BUTTON_START) && loadPayload("/aurei/payloads/start.bin")) ||
|
||||
((pressed & BUTTON_RIGHT) && loadPayload("/aurei/payloads/right.bin")) ||
|
||||
if(((pressed & BUTTON_RIGHT) && loadPayload("/aurei/payloads/right.bin")) ||
|
||||
((pressed & BUTTON_LEFT) && loadPayload("/aurei/payloads/left.bin")) ||
|
||||
((pressed & BUTTON_UP) && loadPayload("/aurei/payloads/up.bin")) ||
|
||||
((pressed & BUTTON_DOWN) && loadPayload("/aurei/payloads/down.bin")) ||
|
||||
((pressed & BUTTON_X) && loadPayload("/aurei/payloads/x.bin")) ||
|
||||
((pressed & BUTTON_Y) && loadPayload("/aurei/payloads/y.bin")) ||
|
||||
((pressed & BUTTON_SELECT) && loadPayload("/aurei/payloads/select.bin")) ||
|
||||
((pressed & BUTTON_R1) && loadPayload("/aurei/payloads/r.bin")) ||
|
||||
loadPayload("/aurei/payloads/default.bin"))
|
||||
((void (*)())PAYLOAD_ADDRESS)();
|
||||
}
|
@ -13,14 +13,17 @@
|
||||
#define BUTTON_L1 (1 << 9)
|
||||
#define BUTTON_A 1
|
||||
#define BUTTON_B (1 << 1)
|
||||
#define BUTTON_X (1 << 10)
|
||||
#define BUTTON_Y (1 << 11)
|
||||
#define BUTTON_SELECT (1 << 2)
|
||||
#define BUTTON_START (1 << 3)
|
||||
#define BUTTON_RIGHT (1 << 4)
|
||||
#define BUTTON_LEFT (1 << 5)
|
||||
#define BUTTON_UP (1 << 6)
|
||||
#define BUTTON_DOWN (1 << 7)
|
||||
#define BUTTON_L1R1 ((1 << 8) | (1 << 9))
|
||||
#define BUTTON_L1R1 (BUTTON_R1 | BUTTON_L1)
|
||||
#define SAFE_MODE (BUTTON_L1R1 | BUTTON_A | BUTTON_UP)
|
||||
#define OPTION_BUTTONS (BUTTON_L1R1 | BUTTON_A | BUTTON_SELECT)
|
||||
#define PAYLOAD_BUTTONS ((BUTTON_L1 | BUTTON_A | BUTTON_B) ^ 0xFFF)
|
||||
#define OVERRIDE_BUTTONS (BUTTON_B ^ 0xFFF)
|
||||
#define SINGLE_PAYLOAD_BUTTONS (BUTTON_LEFT | BUTTON_RIGHT | BUTTON_UP | BUTTON_DOWN | BUTTON_START | BUTTON_X | BUTTON_Y)
|
||||
#define L_PAYLOAD_BUTTONS (BUTTON_R1 | BUTTON_SELECT)
|
||||
#define MENU_BUTTONS (BUTTON_LEFT | BUTTON_RIGHT | BUTTON_UP | BUTTON_DOWN | BUTTON_A | BUTTON_START)
|
@ -8,7 +8,7 @@
|
||||
#include "memory.h"
|
||||
#include "fatfs/sdmmc/sdmmc.h"
|
||||
|
||||
void getEmunandSect(u32 *off, u32 *head, u32 *emuNAND)
|
||||
u32 getEmunandSect(u32 *off, u32 *head, u32 *emuNAND)
|
||||
{
|
||||
u8 *const temp = (u8 *)0x24300000;
|
||||
|
||||
@ -33,15 +33,16 @@ void getEmunandSect(u32 *off, u32 *head, u32 *emuNAND)
|
||||
*head = nandOffset + nandSize;
|
||||
}
|
||||
//Fallback to the first emuNAND if there's no second one
|
||||
else if(*emuNAND == 2)
|
||||
else
|
||||
{
|
||||
*emuNAND = 1;
|
||||
getEmunandSect(off, head, emuNAND);
|
||||
}
|
||||
else *emuNAND = 0;
|
||||
(*emuNAND)--;
|
||||
if(*emuNAND) getEmunandSect(off, head, emuNAND);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
||||
u32 getSDMMC(u8 *pos, u32 size)
|
||||
{
|
||||
|
@ -10,7 +10,7 @@
|
||||
|
||||
#define NCSD_MAGIC (0x4453434E)
|
||||
|
||||
void getEmunandSect(u32 *off, u32 *head, u32 *emuNAND);
|
||||
u32 getEmunandSect(u32 *off, u32 *head, u32 *emuNAND);
|
||||
u32 getSDMMC(u8 *pos, u32 size);
|
||||
void getEmuRW(u8 *pos, u32 size, u32 *readOff, u32 *writeOff);
|
||||
u32 *getMPU(u8 *pos, u32 size);
|
||||
|
@ -102,7 +102,7 @@ void setupCFW(void)
|
||||
}
|
||||
/* Else, force the last used boot options unless A/L/R/SELECT are pressed
|
||||
or the no-forcing flag is set */
|
||||
else if(!(pressed & OPTION_BUTTONS) && !((config >> 15) & 1))
|
||||
else if(!(pressed & OVERRIDE_BUTTONS) && !((config >> 15) & 1))
|
||||
{
|
||||
mode = (config >> 12) & 1;
|
||||
emuNAND = (config >> 13) & 3;
|
||||
@ -115,7 +115,8 @@ void setupCFW(void)
|
||||
{
|
||||
/* If L and one of the payload buttons are pressed, and if not using A9LH
|
||||
the Safe Mode combo is not pressed, chainload an external payload */
|
||||
if((pressed & BUTTON_L1) && (pressed & PAYLOAD_BUTTONS) && pressed != SAFE_MODE)
|
||||
if(((pressed & SINGLE_PAYLOAD_BUTTONS) || ((pressed & BUTTON_L1) && (pressed & L_PAYLOAD_BUTTONS)))
|
||||
&& pressed != SAFE_MODE)
|
||||
loadPayload();
|
||||
|
||||
//If no configuration file exists or SELECT is held, load configuration menu
|
||||
@ -134,7 +135,8 @@ void setupCFW(void)
|
||||
or R is pressed on a > 9.2 sysNAND, boot emuNAND */
|
||||
if((updatedSys && (!mode || (pressed & BUTTON_R1))) || (!updatedSys && mode && !(pressed & BUTTON_R1)))
|
||||
{
|
||||
//If not 9.0 FIRM and B is pressed, attempt booting the second emuNAND
|
||||
/* If not 9.0 FIRM and the second emuNAND is set as default and B isn't pressed, or vice-versa,
|
||||
attempt to boot it */
|
||||
emuNAND = (mode && ((!(pressed & BUTTON_B)) == ((config >> 4) & 1))) ? 2 : 1;
|
||||
}
|
||||
else emuNAND = 0;
|
||||
@ -158,18 +160,13 @@ void setupCFW(void)
|
||||
if(usePatchedFirmSet && fileExists(patchedFirms[selectedFirm - 1]))
|
||||
usePatchedFirm = 1;
|
||||
|
||||
else if(emuNAND)
|
||||
{
|
||||
//Detect EmuNAND
|
||||
getEmunandSect(&emuOffset, &emuHeader, &emuNAND);
|
||||
|
||||
//If none exists, force SysNAND + 9.6/10.x FIRM and re-detect patched FIRMs
|
||||
if(!emuNAND)
|
||||
/* If the user is booting EmuNAND but the chosen one is not found,
|
||||
force 9.6/10.x FIRM and re-detect the patched FIRMs */
|
||||
else if(emuNAND && !getEmunandSect(&emuOffset, &emuHeader, &emuNAND))
|
||||
{
|
||||
mode = 1;
|
||||
continue;
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
@ -205,7 +202,8 @@ void loadFirm(void)
|
||||
const char *path = usePatchedFirm ? patchedFirms[selectedFirm - 1] :
|
||||
(mode ? "/aurei/firmware.bin" : "/aurei/firmware90.bin");
|
||||
firmSize = fileSize(path);
|
||||
if(!firmSize) error("aurei/firmware(90).bin doesn't exist");
|
||||
if(!firmSize) error(mode ? "aurei/firmware.bin doesn't exist" :
|
||||
"aurei/firmware90.bin doesn't exist");
|
||||
fileRead(firm, path, firmSize);
|
||||
}
|
||||
|
||||
@ -213,18 +211,24 @@ void loadFirm(void)
|
||||
|
||||
//Check that the loaded FIRM matches the console
|
||||
if((((u32)section[2].address >> 8) & 0xFF) != (console ? 0x60 : 0x68))
|
||||
error("aurei/firmware(90).bin doesn't match this\nconsole, or it's encrypted");
|
||||
error(mode ? "aurei/firmware.bin doesn't match this console,\nor it's encrypted" :
|
||||
"aurei/firmware90.bin doesn't match this console,\nor it's encrypted");
|
||||
|
||||
arm9Section = (u8 *)firm + section[2].offset;
|
||||
|
||||
if(console && !usePatchedFirm) decryptArm9Bin(arm9Section, mode);
|
||||
//On N3DS, decrypt ARM9Bin and patch ARM9 entrypoint to skip arm9loader
|
||||
if(console && !usePatchedFirm)
|
||||
{
|
||||
decryptArm9Bin(arm9Section, mode);
|
||||
firm->arm9Entry = (u8 *)0x801B01C;
|
||||
}
|
||||
}
|
||||
|
||||
static inline void patchTwlAgb(u32 mode)
|
||||
static inline void patchTwlAgb(u32 whichFirm)
|
||||
{
|
||||
static firmHeader *const twlAgbFirm = (firmHeader *)0x25000000;
|
||||
|
||||
const char *path = mode ? "/aurei/firmware_agb.bin" : "/aurei/firmware_twl.bin";
|
||||
const char *path = whichFirm ? "/aurei/firmware_agb.bin" : "/aurei/firmware_twl.bin";
|
||||
u32 size = fileSize(path);
|
||||
|
||||
//Skip patching if the file doesn't exist
|
||||
@ -236,10 +240,15 @@ static inline void patchTwlAgb(u32 mode)
|
||||
|
||||
//Check that the loaded FIRM matches the console
|
||||
if((((u32)twlAgbSection[3].address >> 8) & 0xFF) != (console ? 0x60 : 0x68))
|
||||
error(mode ? "aurei/firmware_agb.bin doesn't match this\nconsole, or it's encrypted" :
|
||||
error(whichFirm ? "aurei/firmware_agb.bin doesn't match this\nconsole, or it's encrypted" :
|
||||
"aurei/firmware_twl.bin doesn't match this\nconsole, or it's encrypted");
|
||||
|
||||
if(console) decryptArm9Bin((u8 *)twlAgbFirm + twlAgbSection[3].offset, 0);
|
||||
//On N3DS, decrypt ARM9Bin and patch ARM9 entrypoint to skip arm9loader
|
||||
if(console)
|
||||
{
|
||||
decryptArm9Bin((u8 *)twlAgbFirm + twlAgbSection[3].offset, 0);
|
||||
twlAgbFirm->arm9Entry = (u8 *)0x801301C;
|
||||
}
|
||||
|
||||
struct patchData {
|
||||
u32 offset[2];
|
||||
@ -269,9 +278,9 @@ static inline void patchTwlAgb(u32 mode)
|
||||
|
||||
/* Calculate the amount of patches to apply. Only count the splash screen patch for AGB_FIRM
|
||||
if the matching option was enabled (keep it as last) */
|
||||
u32 numPatches = mode ? (sizeof(agbPatches) / sizeof(struct patchData)) - !((config >> 6) & 1) :
|
||||
u32 numPatches = whichFirm ? (sizeof(agbPatches) / sizeof(struct patchData)) - !((config >> 6) & 1) :
|
||||
(sizeof(twlPatches) / sizeof(struct patchData));
|
||||
const struct patchData *patches = mode ? agbPatches : twlPatches;
|
||||
const struct patchData *patches = whichFirm ? agbPatches : twlPatches;
|
||||
|
||||
//Patch
|
||||
for(u32 i = 0; i < numPatches; i++)
|
||||
@ -289,10 +298,7 @@ static inline void patchTwlAgb(u32 mode)
|
||||
}
|
||||
}
|
||||
|
||||
//Patch ARM9 entrypoint on N3DS to skip arm9loader
|
||||
if(console) twlAgbFirm->arm9Entry = (u8 *)0x801301C;
|
||||
|
||||
fileWrite(twlAgbFirm, mode ? patchedFirms[5] : patchedFirms[4], size);
|
||||
fileWrite(twlAgbFirm, whichFirm ? patchedFirms[5] : patchedFirms[4], size);
|
||||
}
|
||||
|
||||
//NAND redirection
|
||||
@ -379,10 +385,13 @@ static inline void injectLoader(void)
|
||||
|
||||
//Patches
|
||||
void patchFirm(void)
|
||||
{
|
||||
if(mode)
|
||||
{
|
||||
//Only patch AGB_FIRM/TWL_FIRM if the patched ones don't already exist
|
||||
if(!fileExists(patchedFirms[4])) patchTwlAgb(0);
|
||||
if(!fileExists(patchedFirms[5])) patchTwlAgb(1);
|
||||
}
|
||||
|
||||
//Skip patching
|
||||
if(usePatchedFirm) return;
|
||||
@ -419,9 +428,6 @@ void patchFirm(void)
|
||||
//Replace the FIRM loader with the injector
|
||||
injectLoader();
|
||||
|
||||
//Patch ARM9 entrypoint on N3DS to skip arm9loader
|
||||
if(console) firm->arm9Entry = (u8 *)0x801B01C;
|
||||
|
||||
//Write patched FIRM to SD if needed
|
||||
if(selectedFirm)
|
||||
if(!fileWrite(firm, patchedFirms[selectedFirm - 1], firmSize))
|
||||
|
Reference in New Issue
Block a user