diff --git a/source/crypto.c b/source/crypto.c index f837cb5..b5d7072 100755 --- a/source/crypto.c +++ b/source/crypto.c @@ -498,7 +498,7 @@ void kernel9Loader(Arm9Bin *arm9Section) aes_use_keyslot(arm9BinSlot); aes(startOfArm9Bin, startOfArm9Bin, arm9BinSize / AES_BLOCK_SIZE, arm9BinCtr, AES_CTR_MODE, AES_INPUT_BE | AES_INPUT_NORMAL); - if(*startOfArm9Bin != 0x47704770 && *startOfArm9Bin != 0xB0862000) error("Error decrypting New 3DS ARM9 Binary."); + if(*startOfArm9Bin != 0x47704770 && *startOfArm9Bin != 0xB0862000) error("Error decrypting the ARM9 binary."); } //Set >=9.6 KeyXs diff --git a/source/exceptions.h b/source/exceptions.h index 8be0806..ed0b584 100644 --- a/source/exceptions.h +++ b/source/exceptions.h @@ -27,21 +27,6 @@ #define MAKE_BRANCH(src,dst) (0xEA000000 | ((u32)((((u8 *)(dst) - (u8 *)(src)) >> 2) - 2) & 0xFFFFFF)) #define MAKE_BRANCH_LINK(src,dst) (0xEB000000 | ((u32)((((u8 *)(dst) - (u8 *)(src)) >> 2) - 2) & 0xFFFFFF)) -typedef struct __attribute__((packed)) -{ - u32 magic[2]; - u16 versionMinor, versionMajor; - - u16 processor, core; - u32 type; - - u32 totalSize; - u32 registerDumpSize; - u32 codeDumpSize; - u32 stackDumpSize; - u32 additionalDataSize; -} ExceptionDumpHeader; - void installArm9Handlers(void); u32 installArm11Handlers(u32 *exceptionsPage, u32 stackAddress, u32 codeSetOffset); void detectAndProcessExceptionDumps(void); \ No newline at end of file diff --git a/source/firm.c b/source/firm.c index 66f3da4..b8af875 100755 --- a/source/firm.c +++ b/source/firm.c @@ -155,10 +155,10 @@ u32 patchNativeFirm(u32 firmVersion, FirmwareSource nandType, u32 emuHeader, u32 ret += patchTitleInstallMinVersionChecks(process9Offset, process9Size, firmVersion); //Restore svcBackdoor - reimplementSvcBackdoor(arm11Section1, arm11SvcTable, baseK11VA, &freeK11Space); + ret += reimplementSvcBackdoor(arm11Section1, arm11SvcTable, baseK11VA, &freeK11Space); } - implementSvcGetCFWInfo(arm11Section1, arm11SvcTable, baseK11VA, &freeK11Space); + ret += implementSvcGetCFWInfo(arm11Section1, arm11SvcTable, baseK11VA, &freeK11Space); //Apply UNITINFO patch if(devMode == 2) ret += patchUnitInfoValueSet(arm9Section, firm->section[2].size); diff --git a/source/patches.c b/source/patches.c index 66e55b1..15ebf75 100644 --- a/source/patches.c +++ b/source/patches.c @@ -203,55 +203,85 @@ u32 patchOldFirmWrites(u8 *pos, u32 size) return ret; } -void reimplementSvcBackdoor(u8 *pos, u32 *arm11SvcTable, u32 baseK11VA, u8 **freeK11Space) +u32 reimplementSvcBackdoor(u8 *pos, u32 *arm11SvcTable, u32 baseK11VA, u8 **freeK11Space) { + u32 ret = 0; + //Official implementation of svcBackdoor - const u8 svcBackdoor[40] = {0xFF, 0x10, 0xCD, 0xE3, //bic r1, sp, #0xff - 0x0F, 0x1C, 0x81, 0xE3, //orr r1, r1, #0xf00 - 0x28, 0x10, 0x81, 0xE2, //add r1, r1, #0x28 - 0x00, 0x20, 0x91, 0xE5, //ldr r2, [r1] - 0x00, 0x60, 0x22, 0xE9, //stmdb r2!, {sp, lr} - 0x02, 0xD0, 0xA0, 0xE1, //mov sp, r2 - 0x30, 0xFF, 0x2F, 0xE1, //blx r0 - 0x03, 0x00, 0xBD, 0xE8, //pop {r0, r1} - 0x00, 0xD0, 0xA0, 0xE1, //mov sp, r0 - 0x11, 0xFF, 0x2F, 0xE1}; //bx r1 + const u8 svcBackdoor[] = {0xFF, 0x10, 0xCD, 0xE3, //bic r1, sp, #0xff + 0x0F, 0x1C, 0x81, 0xE3, //orr r1, r1, #0xf00 + 0x28, 0x10, 0x81, 0xE2, //add r1, r1, #0x28 + 0x00, 0x20, 0x91, 0xE5, //ldr r2, [r1] + 0x00, 0x60, 0x22, 0xE9, //stmdb r2!, {sp, lr} + 0x02, 0xD0, 0xA0, 0xE1, //mov sp, r2 + 0x30, 0xFF, 0x2F, 0xE1, //blx r0 + 0x03, 0x00, 0xBD, 0xE8, //pop {r0, r1} + 0x00, 0xD0, 0xA0, 0xE1, //mov sp, r0 + 0x11, 0xFF, 0x2F, 0xE1}; //bx r1 if(!arm11SvcTable[0x7B]) { - memcpy(*freeK11Space, svcBackdoor, 40); + if(*(u32 *)(*freeK11Space + sizeof(svcBackdoor) - 4) != 0xFFFFFFFF) ret = 1; + else + { + memcpy(*freeK11Space, svcBackdoor, sizeof(svcBackdoor)); - arm11SvcTable[0x7B] = baseK11VA + *freeK11Space - pos; - *freeK11Space += 40; + arm11SvcTable[0x7B] = baseK11VA + *freeK11Space - pos; + *freeK11Space += 40; + } } + + return ret; } -void implementSvcGetCFWInfo(u8 *pos, u32 *arm11SvcTable, u32 baseK11VA, u8 **freeK11Space) +u32 implementSvcGetCFWInfo(u8 *pos, u32 *arm11SvcTable, u32 baseK11VA, u8 **freeK11Space) { - memcpy(*freeK11Space, svcGetCFWInfo_bin, svcGetCFWInfo_bin_size); + u32 ret; - CFWInfo *info = (CFWInfo *)memsearch(*freeK11Space, "LUMA", svcGetCFWInfo_bin_size, 4); - - const char *rev = REVISION; - - info->commitHash = COMMIT_HASH; - info->config = configData.config; - info->versionMajor = (u8)(rev[1] - '0'); - info->versionMinor = (u8)(rev[3] - '0'); - - bool isRelease; - - if(rev[4] == '.') + if(*(u32 *)(*freeK11Space + svcGetCFWInfo_bin_size - 4) != 0xFFFFFFFF) ret = 1; + else { - info->versionBuild = (u8)(rev[5] - '0'); - isRelease = rev[6] == 0; + memcpy(*freeK11Space, svcGetCFWInfo_bin, svcGetCFWInfo_bin_size); + + struct CfwInfo + { + char magic[4]; + + u8 versionMajor; + u8 versionMinor; + u8 versionBuild; + u8 flags; + + u32 commitHash; + + u32 config; + } __attribute__((packed)) *info = (struct CfwInfo *)memsearch(*freeK11Space, "LUMA", svcGetCFWInfo_bin_size, 4); + + const char *rev = REVISION; + + info->commitHash = COMMIT_HASH; + info->config = configData.config; + info->versionMajor = (u8)(rev[1] - '0'); + info->versionMinor = (u8)(rev[3] - '0'); + + bool isRelease; + + if(rev[4] == '.') + { + info->versionBuild = (u8)(rev[5] - '0'); + isRelease = rev[6] == 0; + } + else isRelease = rev[4] == 0; + + info->flags = isRelease ? 1 : 0; + + arm11SvcTable[0x2E] = baseK11VA + *freeK11Space - pos; //Stubbed svc + *freeK11Space += svcGetCFWInfo_bin_size; + + ret = 0; } - else isRelease = rev[4] == 0; - info->flags = isRelease ? 1 : 0; - - arm11SvcTable[0x2E] = baseK11VA + *freeK11Space - pos; //Stubbed svc - *freeK11Space += svcGetCFWInfo_bin_size; + return ret; } u32 patchTitleInstallMinVersionChecks(u8 *pos, u32 size, u32 firmVersion) diff --git a/source/patches.h b/source/patches.h index dfa6c65..e762346 100644 --- a/source/patches.h +++ b/source/patches.h @@ -28,20 +28,6 @@ #include "types.h" -typedef struct __attribute__((packed)) -{ - char magic[4]; - - u8 versionMajor; - u8 versionMinor; - u8 versionBuild; - u8 flags; - - u32 commitHash; - - u32 config; -} CFWInfo; - extern CfgData configData; u8 *getProcess9Info(u8 *pos, u32 size, u32 *process9Size, u32 *process9MemAddr); @@ -51,8 +37,8 @@ u32 patchTitleInstallMinVersionChecks(u8 *pos, u32 size, u32 firmVersion); u32 patchFirmlaunches(u8 *pos, u32 size, u32 process9MemAddr); u32 patchFirmWrites(u8 *pos, u32 size); u32 patchOldFirmWrites(u8 *pos, u32 size); -void reimplementSvcBackdoor(u8 *pos, u32 *arm11SvcTable, u32 baseK11VA, u8 **freeK11Space); -void implementSvcGetCFWInfo(u8 *pos, u32 *arm11SvcTable, u32 baseK11VA, u8 **freeK11Space); +u32 reimplementSvcBackdoor(u8 *pos, u32 *arm11SvcTable, u32 baseK11VA, u8 **freeK11Space); +u32 implementSvcGetCFWInfo(u8 *pos, u32 *arm11SvcTable, u32 baseK11VA, u8 **freeK11Space); u32 patchArm9ExceptionHandlersInstall(u8 *pos, u32 size); u32 getInfoForArm11ExceptionHandlers(u8 *pos, u32 size, u32 *codeSetOffset); u32 patchSvcBreak9(u8 *pos, u32 size, u32 kernel9Address); diff --git a/source/types.h b/source/types.h index 3992341..9238d14 100644 --- a/source/types.h +++ b/source/types.h @@ -67,6 +67,21 @@ typedef struct __attribute__((packed)) u8 hash[32]; } PinData; +typedef struct __attribute__((packed)) +{ + u32 magic[2]; + u16 versionMinor, versionMajor; + + u16 processor, core; + u32 type; + + u32 totalSize; + u32 registerDumpSize; + u32 codeDumpSize; + u32 stackDumpSize; + u32 additionalDataSize; +} ExceptionDumpHeader; + typedef enum FirmwareSource { FIRMWARE_SYSNAND = 0,