fixed ninjhax boot code
This commit is contained in:
@@ -96,7 +96,7 @@ wait_arm11_loop:
|
||||
BX R1
|
||||
|
||||
pa_hijack_arm9_dst: .long 0x1FFFFC00
|
||||
pa_arm11_code: .long 0x1FFFFFF8
|
||||
pa_arm11_code: .long 0x1FFFFFFC
|
||||
pa_pxi_regs: .long 0x10163000
|
||||
some_pxi_cmd: .long 0x44846
|
||||
pa_firm_header: .long 0x24000000
|
||||
|
||||
@@ -1,24 +0,0 @@
|
||||
.arm
|
||||
.align 4
|
||||
.code 32
|
||||
.text
|
||||
|
||||
@ default ARM9 payload, simply launches FIRM (reboots without clearing mem)
|
||||
.global arm9_start
|
||||
arm9_start:
|
||||
B skipvars
|
||||
|
||||
@ offs 4, will contain backup copy of FIRM ARM9
|
||||
@ entry point so execution can be returned to FIRM
|
||||
pa_arm9_entrypoint_backup: .long 0xFFFF0000
|
||||
|
||||
skipvars:
|
||||
STMFD SP!, {R0-R12,LR}
|
||||
|
||||
@ insert your funky stuff here
|
||||
LDMFD SP!, {R0-R12,LR}
|
||||
|
||||
LDR PC, pa_arm9_entrypoint_backup
|
||||
|
||||
.global arm9_end
|
||||
arm9_end:
|
||||
@@ -10,7 +10,9 @@
|
||||
#include <arpa/inet.h>
|
||||
#include "brahma.h"
|
||||
#include "exploitdata.h"
|
||||
#include "utils.h"
|
||||
|
||||
GSP_FramebufferInfo topFramebufferInfo, bottomFramebufferInfo;
|
||||
|
||||
/* should be the very first call. allocates heap buffer
|
||||
for ARM9 payload */
|
||||
@@ -318,9 +320,7 @@ s32 map_arm9_payload (void) {
|
||||
dst = (void *)(g_expdata.va_fcram_base + OFFS_FCRAM_ARM9_PAYLOAD);
|
||||
|
||||
if (!g_ext_arm9_loaded) {
|
||||
// defaul ARM9 payload
|
||||
src = &arm9_start;
|
||||
size = (u8 *)&arm9_end - (u8 *)&arm9_start;
|
||||
return 0;
|
||||
}
|
||||
else {
|
||||
// external ARM9 payload
|
||||
@@ -426,6 +426,18 @@ priv_firm_reboot (void) {
|
||||
asm volatile ("add sp, sp, #8\t\n");
|
||||
|
||||
repair_svcCreateThread();
|
||||
|
||||
// Save the framebuffers for arm9,
|
||||
u32 *save = (u32 *)(g_expdata.va_fcram_base + 0x3FFFE00);
|
||||
save[0] = topFramebufferInfo.framebuf0_vaddr;
|
||||
save[1] = topFramebufferInfo.framebuf1_vaddr;
|
||||
save[2] = bottomFramebufferInfo.framebuf0_vaddr;
|
||||
|
||||
// Working around a GCC bug to translate the va address to pa...
|
||||
save[0] += 0xC000000; // (pa FCRAM address - va FCRAM address)
|
||||
save[1] += 0xC000000;
|
||||
save[2] += 0xC000000;
|
||||
|
||||
exploit_arm9_race_condition();
|
||||
|
||||
asm volatile ("movs r0, #0\t\n"
|
||||
|
||||
@@ -1,19 +1,7 @@
|
||||
#include <3ds.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <malloc.h>
|
||||
#include "brahma.h"
|
||||
#include "hid.h"
|
||||
#include "menus.h"
|
||||
#include "sochlp.h"
|
||||
#include "payload_bin.h"
|
||||
|
||||
s32 quick_boot_firm (s32 load_from_disk) {
|
||||
if (load_from_disk)
|
||||
load_arm9_payload_from_mem(payload_bin, payload_bin_size);
|
||||
firm_reboot();
|
||||
}
|
||||
|
||||
s32 main (void) {
|
||||
// Initialize services
|
||||
@@ -25,27 +13,27 @@ s32 main (void) {
|
||||
sdmcInit();
|
||||
hbInit();
|
||||
qtmInit();
|
||||
|
||||
Handle fileHandle;
|
||||
u32 bytesRead;
|
||||
FS_archive sdmcArchive=(FS_archive){ARCH_SDMC, (FS_path){PATH_EMPTY, 1, (u8*)""}};
|
||||
FS_path filePath=FS_makePath(PATH_CHAR, "/reiNand.dat");
|
||||
Result ret=FSUSER_OpenFileDirectly(NULL, &fileHandle, sdmcArchive, filePath, FS_OPEN_READ, FS_ATTRIBUTE_NONE);
|
||||
if(ret) goto EXIT;
|
||||
FSFILE_Read(fileHandle, &bytesRead, 0x20000, 0x14400000, 320*1024);
|
||||
FSFILE_Close(fileHandle);
|
||||
|
||||
consoleInit(GFX_BOTTOM, NULL);
|
||||
if (brahma_init()) {
|
||||
quick_boot_firm(1);
|
||||
printf("[!] Quickload failed\n");
|
||||
brahma_exit();
|
||||
|
||||
gfxSwapBuffers();
|
||||
|
||||
u32 payload_size = 0x10000;
|
||||
void *payload = malloc(payload_size);
|
||||
|
||||
FILE *fp = fopen("/reiNand.dat", "r");
|
||||
if (!fp) goto exit;
|
||||
fseek(fp, 0x20000, SEEK_SET);
|
||||
fread(payload, payload_size, 1, fp);
|
||||
fclose(fp);
|
||||
|
||||
if (brahma_init()) {
|
||||
load_arm9_payload_from_mem(payload, payload_size);
|
||||
firm_reboot();
|
||||
brahma_exit();
|
||||
}
|
||||
|
||||
exit:
|
||||
if (payload) free(payload);
|
||||
|
||||
} else {
|
||||
printf("* BRAHMA *\n\n[!]Not enough memory\n");
|
||||
wait_any_key();
|
||||
}
|
||||
EXIT:
|
||||
hbExit();
|
||||
sdmcExit();
|
||||
fsExit();
|
||||
@@ -53,6 +41,5 @@ s32 main (void) {
|
||||
hidExit();
|
||||
aptExit();
|
||||
srvExit();
|
||||
// Return to hbmenu
|
||||
return 0;
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -1,171 +0,0 @@
|
||||
#include <dirent.h>
|
||||
#include <3ds.h>
|
||||
#include "menus.h"
|
||||
|
||||
s32 print_menu (s32 idx, struct menu_t *menu) {
|
||||
s32 i;
|
||||
s32 newidx;
|
||||
s32 count = menu_get_element_count(menu);
|
||||
|
||||
newidx = menu_update_index(idx, menu);
|
||||
for (i=0; i<count; i++) {
|
||||
if (newidx == i)
|
||||
printf("[ %s ]\n", menu_get_element_name(i, menu));
|
||||
else
|
||||
printf(" %s \n", menu_get_element_name(i, menu));
|
||||
}
|
||||
return newidx;
|
||||
}
|
||||
|
||||
s32 print_file_list (s32 idx, struct menu_t *menu) {
|
||||
s32 i = 0;
|
||||
s32 newidx;
|
||||
DIR *dp;
|
||||
struct dirent *entry;
|
||||
char *filename = 0;
|
||||
s32 totalfiles = 0;
|
||||
s32 num_printed = 0;
|
||||
|
||||
consoleClear();
|
||||
|
||||
printf("ARM9 payload (%s):\n\n\n", BRAHMADIR);
|
||||
printf("===========================\n");
|
||||
|
||||
s32 count = menu_get_element_count(menu);
|
||||
|
||||
newidx = menu_update_index(idx, menu);
|
||||
if((dp = opendir(BRAHMADIR))) {
|
||||
for (i=0; i<count; i++) {
|
||||
if ((entry = readdir(dp)) != 0) {
|
||||
filename = entry->d_name;
|
||||
}
|
||||
else {
|
||||
filename = "---";
|
||||
}
|
||||
if (newidx == i)
|
||||
printf("[ %s ] %s\n", menu_get_element_name(i, menu), filename);
|
||||
else
|
||||
printf(" %s %s\n", menu_get_element_name(i, menu), filename);
|
||||
}
|
||||
closedir(dp);
|
||||
}
|
||||
else {
|
||||
printf("[!] Could not open '%s'\n", BRAHMADIR);
|
||||
}
|
||||
|
||||
printf("===========================\n\n");
|
||||
printf("A: Confirm\n");
|
||||
printf("B: Back\n");
|
||||
|
||||
return newidx;
|
||||
}
|
||||
|
||||
s32 print_main_menu (s32 idx, struct menu_t *menu) {
|
||||
s32 newidx = 0;
|
||||
consoleClear();
|
||||
|
||||
printf("\n* BRAHMA *\n\n\n");
|
||||
printf("===========================\n");
|
||||
newidx = print_menu(idx, menu);
|
||||
printf("===========================\n\n");
|
||||
printf("A: Confirm\n");
|
||||
printf("B: Exit\n");
|
||||
|
||||
return newidx;
|
||||
}
|
||||
|
||||
s32 get_filename (s32 idx, char *buf, u32 size) {
|
||||
DIR *dp;
|
||||
struct dirent *entry;
|
||||
s32 result = 0;
|
||||
s32 numfiles = 0;
|
||||
|
||||
if((dp = opendir(BRAHMADIR)) && buf && size) {
|
||||
while((entry = readdir(dp)) != NULL) {
|
||||
if (numfiles == idx) {
|
||||
snprintf(buf, size-1, "%s%s", BRAHMADIR, entry->d_name);
|
||||
result = 1;
|
||||
break;
|
||||
}
|
||||
numfiles++;
|
||||
}
|
||||
closedir(dp);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
s32 menu_cb_recv (s32 idx, void *param) {
|
||||
return recv_arm9_payload();
|
||||
}
|
||||
|
||||
s32 menu_cb_load(s32 idx, void *param) {
|
||||
char filename[256];
|
||||
s32 result = 0;
|
||||
|
||||
if (param) {
|
||||
if (get_filename(*(u32 *)param, &filename, sizeof(filename))) {
|
||||
printf("[+] Loading %s\n", filename);
|
||||
result = load_arm9_payload(filename);
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
s32 menu_cb_choose_file (s32 idx, void *param) {
|
||||
s32 curidx = idx;
|
||||
s32 loaded = 0;
|
||||
|
||||
while (aptMainLoop()) {
|
||||
gspWaitForVBlank();
|
||||
|
||||
curidx = print_file_list(curidx, &g_file_list);
|
||||
u32 kDown = wait_key();
|
||||
|
||||
if (kDown & KEY_B) {
|
||||
break;
|
||||
}
|
||||
else if (kDown & KEY_A) {
|
||||
consoleClear();
|
||||
loaded = menu_execute_function(curidx, &g_file_list, &curidx);
|
||||
printf("%s\n", loaded? "[+] Success":"[!] Failure");
|
||||
wait_any_key();
|
||||
if (loaded)
|
||||
break;
|
||||
}
|
||||
else if (kDown & KEY_UP) {
|
||||
curidx--;
|
||||
}
|
||||
else if (kDown & KEY_DOWN) {
|
||||
curidx++;
|
||||
}
|
||||
gfxFlushBuffers();
|
||||
gfxSwapBuffers();
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
s32 menu_cb_run (s32 idx, void *param) {
|
||||
s32 fail_stage;
|
||||
|
||||
/* we're kinda screwed if the exploit fails
|
||||
and soc has been deinitialized. not sure
|
||||
whether cleaning up here improves existing
|
||||
problems with using sockets either */
|
||||
soc_exit();
|
||||
printf("[+] Running ARM9 payload\n");
|
||||
fail_stage = firm_reboot();
|
||||
|
||||
char *msg;
|
||||
switch (fail_stage) {
|
||||
case 1:
|
||||
msg = "[!] ARM11 exploit failed";
|
||||
break;
|
||||
case 2:
|
||||
msg = "[!] ARM9 exploit failed";
|
||||
break;
|
||||
default:
|
||||
msg = "[!] Unexpected error";
|
||||
}
|
||||
printf("%s\n", msg);
|
||||
return 1;
|
||||
}
|
||||
@@ -1,27 +0,0 @@
|
||||
#include <3ds.h>
|
||||
#include "sochlp.h"
|
||||
|
||||
u32 soc_init (void) {
|
||||
Result ret;
|
||||
u32 result = 0;
|
||||
|
||||
SOC_buffer = (u32*)memalign(SOC_ALIGN, SOC_BUFFERSIZE);
|
||||
if (SOC_buffer != 0) {
|
||||
ret = SOC_Initialize(SOC_buffer, SOC_BUFFERSIZE);
|
||||
if (ret == 0) {
|
||||
result = 1;
|
||||
} else {
|
||||
free(SOC_buffer);
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
u32 soc_exit (void) {
|
||||
if (SOC_buffer) {
|
||||
SOC_Shutdown();
|
||||
free(SOC_buffer);
|
||||
SOC_buffer = 0;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
@@ -1,45 +0,0 @@
|
||||
#include <3ds.h>
|
||||
#include "textmenu.h"
|
||||
|
||||
s32 menu_get_element_count (struct menu_t *menu) {
|
||||
s32 i = 0;
|
||||
|
||||
if (menu) {
|
||||
i = menu->element_count;
|
||||
}
|
||||
return i;
|
||||
}
|
||||
|
||||
s32 menu_is_valid_index (s32 idx, struct menu_t *menu) {
|
||||
return (menu != 0 && (idx >= 0 && idx < menu_get_element_count(menu)));
|
||||
}
|
||||
|
||||
s32 menu_update_index (s32 idx, struct menu_t *menu) {
|
||||
s32 newidx = 0;
|
||||
s32 count = menu_get_element_count(menu);
|
||||
|
||||
newidx = idx < 0 ? count - 1 : idx >= count ? 0 : idx;
|
||||
|
||||
return newidx;
|
||||
}
|
||||
|
||||
const char *menu_get_element_name (s32 idx, struct menu_t *menu) {
|
||||
return menu_is_valid_index(idx, menu) ? menu->element[idx].name : 0;
|
||||
}
|
||||
|
||||
menu_func_t *menu_get_element_function (s32 idx, struct menu_t *menu) {
|
||||
return menu_is_valid_index(idx, menu) ? menu->element[idx].func : 0;
|
||||
}
|
||||
|
||||
s32 menu_execute_function (s32 idx, struct menu_t *menu, void *param) {
|
||||
s32 result = 0;
|
||||
menu_func_t *f;
|
||||
|
||||
if (menu_is_valid_index(idx, menu)) {
|
||||
f = menu_get_element_function(idx, menu);
|
||||
if (f)
|
||||
result = f(idx, param);
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
Reference in New Issue
Block a user