Rewrite k11ext mmu mapping func + linker script
This commit is contained in:
parent
e64f267e4c
commit
35ad240018
@ -107,7 +107,6 @@ u32 installK11Extension(u8 *pos, u32 size, bool needToInitSd, u32 baseK11VA, u32
|
|||||||
//Please keep that in sync with the definition in k11_extension/source/main.c
|
//Please keep that in sync with the definition in k11_extension/source/main.c
|
||||||
struct KExtParameters
|
struct KExtParameters
|
||||||
{
|
{
|
||||||
u32 __attribute__((aligned(0x400))) L2MMUTableFor0x40000000[256];
|
|
||||||
u32 basePA;
|
u32 basePA;
|
||||||
void *originalHandlers[4];
|
void *originalHandlers[4];
|
||||||
u32 L1MMUTableAddrs[4];
|
u32 L1MMUTableAddrs[4];
|
||||||
@ -136,7 +135,7 @@ u32 installK11Extension(u8 *pos, u32 size, bool needToInitSd, u32 baseK11VA, u32
|
|||||||
|
|
||||||
//Our kernel11 extension is initially loaded in VRAM
|
//Our kernel11 extension is initially loaded in VRAM
|
||||||
u32 kextTotalSize = *(u32 *)0x18000020 - 0x40000000;
|
u32 kextTotalSize = *(u32 *)0x18000020 - 0x40000000;
|
||||||
u32 dstKextPA = (ISN3DS ? 0x2E000000 : 0x26C00000) - kextTotalSize;
|
u32 dstKextPA = (ISN3DS ? 0x2E000000 : 0x26C00000) - (0x1000 + kextTotalSize);
|
||||||
|
|
||||||
u32 *hookVeneers = (u32 *)*freeK11Space;
|
u32 *hookVeneers = (u32 *)*freeK11Space;
|
||||||
u32 relocBase = 0xFFFF0000 + (*freeK11Space - (u8 *)arm11ExceptionsPage);
|
u32 relocBase = 0xFFFF0000 + (*freeK11Space - (u8 *)arm11ExceptionsPage);
|
||||||
@ -177,7 +176,7 @@ u32 installK11Extension(u8 *pos, u32 size, bool needToInitSd, u32 baseK11VA, u32
|
|||||||
*off = MAKE_BRANCH_LINK(baseK11VA + ((u8 *)off - pos), relocBase + 24);
|
*off = MAKE_BRANCH_LINK(baseK11VA + ((u8 *)off - pos), relocBase + 24);
|
||||||
|
|
||||||
struct KExtParameters *p = (struct KExtParameters *)(*(u32 *)0x18000024 - 0x40000000 + 0x18000000);
|
struct KExtParameters *p = (struct KExtParameters *)(*(u32 *)0x18000024 - 0x40000000 + 0x18000000);
|
||||||
p->basePA = dstKextPA;
|
p->basePA = dstKextPA + 0x1000;
|
||||||
|
|
||||||
for(u32 i = 0; i < 4; i++)
|
for(u32 i = 0; i < 4; i++)
|
||||||
{
|
{
|
||||||
|
@ -105,7 +105,7 @@ $(BUILD):
|
|||||||
#---------------------------------------------------------------------------------
|
#---------------------------------------------------------------------------------
|
||||||
clean:
|
clean:
|
||||||
@echo clean ...
|
@echo clean ...
|
||||||
@rm -fr $(BUILD) $(TARGET).bin $(TARGET).elf
|
@rm -fr $(BUILD) $(TARGET).elf
|
||||||
|
|
||||||
|
|
||||||
#---------------------------------------------------------------------------------
|
#---------------------------------------------------------------------------------
|
||||||
@ -117,11 +117,7 @@ DEPENDS := $(OFILES:.o=.d)
|
|||||||
#---------------------------------------------------------------------------------
|
#---------------------------------------------------------------------------------
|
||||||
# main targets
|
# main targets
|
||||||
#---------------------------------------------------------------------------------
|
#---------------------------------------------------------------------------------
|
||||||
all : $(OUTPUT).bin
|
all : $(OUTPUT).elf
|
||||||
|
|
||||||
$(OUTPUT).bin : $(OUTPUT).elf
|
|
||||||
$(OBJCOPY) -S -O binary $< $@
|
|
||||||
@echo built ... $(notdir $@)
|
|
||||||
|
|
||||||
$(OUTPUT).elf : $(OFILES)
|
$(OUTPUT).elf : $(OFILES)
|
||||||
|
|
||||||
|
@ -2,26 +2,26 @@ OUTPUT_FORMAT("elf32-littlearm", "elf32-bigarm", "elf32-littlearm")
|
|||||||
OUTPUT_ARCH(arm)
|
OUTPUT_ARCH(arm)
|
||||||
ENTRY(_start)
|
ENTRY(_start)
|
||||||
|
|
||||||
/* Mostly copied from https://github.com/devkitPro/buildscripts/blob/master/dkarm-eabi/crtls/3dsx.ld */
|
MEMORY
|
||||||
|
{
|
||||||
|
vram : ORIGIN = 0x18000000, LENGTH = 0x18180000 - 0x18000000 /* Up to the kernel builtins. */
|
||||||
|
main : ORIGIN = 0x40000000, LENGTH = 1M
|
||||||
|
}
|
||||||
|
|
||||||
|
PHDRS
|
||||||
|
{
|
||||||
|
main PT_LOAD;
|
||||||
|
}
|
||||||
|
|
||||||
SECTIONS
|
SECTIONS
|
||||||
{
|
{
|
||||||
PROVIDE(__start__ = 0x40000000);
|
PROVIDE(__start__ = 0x40000000);
|
||||||
|
. = ABSOLUTE(__start__);
|
||||||
. = __start__;
|
|
||||||
. = ALIGN(32);
|
|
||||||
|
|
||||||
.crt0 :
|
|
||||||
{
|
|
||||||
. = ALIGN(32);
|
|
||||||
KEEP( *(.text.start) )
|
|
||||||
KEEP( *(.init) )
|
|
||||||
. = ALIGN(4);
|
|
||||||
}
|
|
||||||
|
|
||||||
.text :
|
.text :
|
||||||
{
|
{
|
||||||
. = ALIGN(4);
|
KEEP( *(.text.start) )
|
||||||
|
KEEP( *(.init) )
|
||||||
|
|
||||||
/* .text */
|
/* .text */
|
||||||
*(.text)
|
*(.text)
|
||||||
@ -31,12 +31,11 @@ SECTIONS
|
|||||||
*(.stub)
|
*(.stub)
|
||||||
*(.gnu.warning)
|
*(.gnu.warning)
|
||||||
*(.gnu.linkonce.t*)
|
*(.gnu.linkonce.t*)
|
||||||
. = ALIGN(4);
|
|
||||||
|
|
||||||
/* .fini */
|
/* .fini */
|
||||||
KEEP( *(.fini) )
|
KEEP( *(.fini) )
|
||||||
. = ALIGN(4);
|
. = ALIGN(32);
|
||||||
}
|
} >main AT>vram :main
|
||||||
|
|
||||||
.rodata :
|
.rodata :
|
||||||
{
|
{
|
||||||
@ -46,64 +45,63 @@ SECTIONS
|
|||||||
*all.rodata*(*)
|
*all.rodata*(*)
|
||||||
*(.gnu.linkonce.r*)
|
*(.gnu.linkonce.r*)
|
||||||
SORT(CONSTRUCTORS)
|
SORT(CONSTRUCTORS)
|
||||||
. = ALIGN(4);
|
. = ALIGN(8);
|
||||||
}
|
} >main AT>vram
|
||||||
|
|
||||||
.preinit_array ALIGN(4) :
|
.preinit_array :
|
||||||
{
|
{
|
||||||
PROVIDE (__preinit_array_start = .);
|
PROVIDE (__preinit_array_start = .);
|
||||||
KEEP (*(.preinit_array))
|
KEEP (*(.preinit_array))
|
||||||
PROVIDE (__preinit_array_end = .);
|
PROVIDE (__preinit_array_end = .);
|
||||||
}
|
} >main AT>vram
|
||||||
|
|
||||||
.init_array ALIGN(4) :
|
.init_array :
|
||||||
{
|
{
|
||||||
PROVIDE (__init_array_start = .);
|
PROVIDE (__init_array_start = .);
|
||||||
KEEP (*(SORT(.init_array.*)))
|
KEEP (*(SORT(.init_array.*)))
|
||||||
KEEP (*(.init_array))
|
KEEP (*(.init_array))
|
||||||
PROVIDE (__init_array_end = .);
|
PROVIDE (__init_array_end = .);
|
||||||
}
|
} >main AT>vram
|
||||||
|
|
||||||
.fini_array ALIGN(4) :
|
.fini_array :
|
||||||
{
|
{
|
||||||
PROVIDE (__fini_array_start = .);
|
PROVIDE (__fini_array_start = .);
|
||||||
KEEP (*(.fini_array))
|
KEEP (*(.fini_array))
|
||||||
KEEP (*(SORT(.fini_array.*)))
|
KEEP (*(SORT(.fini_array.*)))
|
||||||
PROVIDE (__fini_array_end = .);
|
PROVIDE (__fini_array_end = .);
|
||||||
}
|
} >main AT>vram
|
||||||
|
|
||||||
.ctors ALIGN(4) :
|
.ctors :
|
||||||
{
|
{
|
||||||
KEEP (*crtbegin.o(.ctors)) /* MUST be first -- GCC requires it */
|
KEEP (*crtbegin.o(.ctors)) /* MUST be first -- GCC requires it */
|
||||||
KEEP (*(EXCLUDE_FILE (*crtend.o) .ctors))
|
KEEP (*(EXCLUDE_FILE (*crtend.o) .ctors))
|
||||||
KEEP (*(SORT(.ctors.*)))
|
KEEP (*(SORT(.ctors.*)))
|
||||||
KEEP (*(.ctors))
|
KEEP (*(.ctors))
|
||||||
}
|
. = ALIGN(4); /* REQUIRED. LD is flaky without it. */
|
||||||
|
} >main AT>vram
|
||||||
|
|
||||||
.dtors ALIGN(4) :
|
.dtors :
|
||||||
{
|
{
|
||||||
KEEP (*crtbegin.o(.dtors))
|
KEEP (*crtbegin.o(.dtors))
|
||||||
KEEP (*(EXCLUDE_FILE (*crtend.o) .dtors))
|
KEEP (*(EXCLUDE_FILE (*crtend.o) .dtors))
|
||||||
KEEP (*(SORT(.dtors.*)))
|
KEEP (*(SORT(.dtors.*)))
|
||||||
KEEP (*(.dtors))
|
KEEP (*(.dtors))
|
||||||
}
|
. = ALIGN(4); /* REQUIRED. LD is flaky without it. */
|
||||||
|
} >main AT>vram
|
||||||
|
|
||||||
.ARM.extab : { *(.ARM.extab* .gnu.linkonce.armextab.*) }
|
.ARM.extab : { *(.ARM.extab* .gnu.linkonce.armextab.*) __exidx_start = ABSOLUTE(.);} >main AT>vram
|
||||||
__exidx_start = .;
|
ARM.exidx : { *(.ARM.exidx* .gnu.linkonce.armexidx.*) __exidx_end = ABSOLUTE(.);} >main AT>vram
|
||||||
ARM.exidx : { *(.ARM.exidx* .gnu.linkonce.armexidx.*) }
|
|
||||||
__exidx_end = .;
|
|
||||||
|
|
||||||
.data :
|
.data :
|
||||||
{
|
{
|
||||||
*(.data)
|
*(.data)
|
||||||
*(.data.*)
|
*(.data.*)
|
||||||
KEEP (*(.large_patch*))
|
|
||||||
*(.gnu.linkonce.d*)
|
*(.gnu.linkonce.d*)
|
||||||
CONSTRUCTORS
|
CONSTRUCTORS
|
||||||
. = ALIGN(4);
|
. = ALIGN(32);
|
||||||
}
|
} >main AT>vram
|
||||||
|
|
||||||
.bss :
|
.bss (NOLOAD) :
|
||||||
{
|
{
|
||||||
. = ALIGN(32);
|
. = ALIGN(32);
|
||||||
PROVIDE (__bss_start__ = ABSOLUTE(.));
|
PROVIDE (__bss_start__ = ABSOLUTE(.));
|
||||||
@ -114,8 +112,8 @@ SECTIONS
|
|||||||
*(COMMON)
|
*(COMMON)
|
||||||
. = ALIGN(8);
|
. = ALIGN(8);
|
||||||
PROVIDE (__bss_end__ = ABSOLUTE(.));
|
PROVIDE (__bss_end__ = ABSOLUTE(.));
|
||||||
}
|
PROVIDE (__end__ = ABSOLUTE(.));
|
||||||
PROVIDE (__end__ = ABSOLUTE(.));
|
} >main :NONE
|
||||||
|
|
||||||
/* ==================
|
/* ==================
|
||||||
==== Metadata ====
|
==== Metadata ====
|
||||||
|
@ -34,7 +34,6 @@
|
|||||||
|
|
||||||
struct KExtParameters
|
struct KExtParameters
|
||||||
{
|
{
|
||||||
u32 ALIGN(0x400) L2MMUTableFor0x40000000[256];
|
|
||||||
u32 basePA;
|
u32 basePA;
|
||||||
void *originalHandlers[4];
|
void *originalHandlers[4];
|
||||||
u32 L1MMUTableAddrs[4];
|
u32 L1MMUTableAddrs[4];
|
||||||
@ -46,18 +45,20 @@ void relocateAndSetupMMU(u32 coreId, u32 *L1Table)
|
|||||||
{
|
{
|
||||||
struct KExtParameters *p0 = (struct KExtParameters *)((u32)&kExtParameters - 0x40000000 + 0x18000000);
|
struct KExtParameters *p0 = (struct KExtParameters *)((u32)&kExtParameters - 0x40000000 + 0x18000000);
|
||||||
struct KExtParameters *p = (struct KExtParameters *)((u32)&kExtParameters - 0x40000000 + p0->basePA);
|
struct KExtParameters *p = (struct KExtParameters *)((u32)&kExtParameters - 0x40000000 + p0->basePA);
|
||||||
|
u32 *L2Table = (u32 *)(p0->basePA - 0x1000);
|
||||||
|
|
||||||
if(coreId == 0)
|
if(coreId == 0)
|
||||||
{
|
{
|
||||||
// Relocate ourselves, and clear BSS
|
// Relocate ourselves, and clear BSS
|
||||||
// This is only OK because the jumps will be relative...
|
// This is only OK because the jumps will be relative & there's no mode switch...
|
||||||
memcpy((void *)p0->basePA, (const void *)0x18000000, __bss_start__ - __start__);
|
memcpy((void *)p0->basePA, (const void *)0x18000000, __bss_start__ - __start__);
|
||||||
memset((u32 *)(p0->basePA + (__bss_start__ - __start__)), 0, __bss_end__ - __bss_start__);
|
memset((u32 *)(p0->basePA + (__bss_start__ - __start__)), 0, __bss_end__ - __bss_start__);
|
||||||
|
|
||||||
// Map the kernel ext to 0x40000000
|
// Map the kernel ext to 0x40000000
|
||||||
// 4KB extended small pages: [SYS:RW USR:-- X TYP:NORMAL SHARED OUTER NOCACHE, INNER CACHED WB WA]
|
// 4KB extended small pages: [SYS:RW USR:-- X TYP:NORMAL SHARED OUTER NOCACHE, INNER CACHED WB WA]
|
||||||
|
memset(L2Table, 0, 4 * 256);
|
||||||
for(u32 offset = 0; offset < (u32)(__end__ - __start__); offset += 0x1000)
|
for(u32 offset = 0; offset < (u32)(__end__ - __start__); offset += 0x1000)
|
||||||
p->L2MMUTableFor0x40000000[offset >> 12] = (p0->basePA + offset) | 0x516;
|
L2Table[offset >> 12] = (p0->basePA + offset) | 0x516;
|
||||||
|
|
||||||
__asm__ __volatile__ ("sev");
|
__asm__ __volatile__ ("sev");
|
||||||
}
|
}
|
||||||
@ -74,7 +75,7 @@ void relocateAndSetupMMU(u32 coreId, u32 *L1Table)
|
|||||||
L1Table[i + (VA >> 20)] = PA | attribs;
|
L1Table[i + (VA >> 20)] = PA | attribs;
|
||||||
}
|
}
|
||||||
|
|
||||||
L1Table[0x40000000 >> 20] = (u32)p->L2MMUTableFor0x40000000 | 1;
|
L1Table[0x40000000 >> 20] = (u32)L2Table | 1;
|
||||||
|
|
||||||
p->L1MMUTableAddrs[coreId] = (u32)L1Table;
|
p->L1MMUTableAddrs[coreId] = (u32)L1Table;
|
||||||
}
|
}
|
||||||
@ -257,7 +258,7 @@ void main(FcramLayout *layout, KCoreContext *ctxs)
|
|||||||
u32 TTBCR_;
|
u32 TTBCR_;
|
||||||
s64 nb;
|
s64 nb;
|
||||||
|
|
||||||
layout->systemSize -= __end__ - __start__;
|
layout->systemSize -= 0x1000 + __end__ - __start__;
|
||||||
fcramLayout = *layout;
|
fcramLayout = *layout;
|
||||||
coreCtxs = ctxs;
|
coreCtxs = ctxs;
|
||||||
|
|
||||||
|
@ -23,7 +23,7 @@
|
|||||||
@ reasonable ways as different from the original version.
|
@ reasonable ways as different from the original version.
|
||||||
|
|
||||||
.section .text.start, "ax", %progbits
|
.section .text.start, "ax", %progbits
|
||||||
.balign 32
|
.balign 4
|
||||||
.global _start
|
.global _start
|
||||||
_start:
|
_start:
|
||||||
b start
|
b start
|
||||||
|
@ -100,7 +100,7 @@ void *svcHook(u8 *pageEnd)
|
|||||||
case 0x17:
|
case 0x17:
|
||||||
if(strcmp(codeSetOfProcess(currentProcess)->processName, "pm") == 0) // only called twice in pm, by the same function
|
if(strcmp(codeSetOfProcess(currentProcess)->processName, "pm") == 0) // only called twice in pm, by the same function
|
||||||
{
|
{
|
||||||
*(vu32 *)(configPage + 0x44) += __end__ - __start__;
|
*(vu32 *)(configPage + 0x44) += 0x1000 + __end__ - __start__;
|
||||||
doingVeryShittyPmResLimitWorkaround = true;
|
doingVeryShittyPmResLimitWorkaround = true;
|
||||||
}
|
}
|
||||||
return officialSVCs[0x17];
|
return officialSVCs[0x17];
|
||||||
@ -127,7 +127,7 @@ void *svcHook(u8 *pageEnd)
|
|||||||
case 0x79:
|
case 0x79:
|
||||||
if(doingVeryShittyPmResLimitWorkaround)
|
if(doingVeryShittyPmResLimitWorkaround)
|
||||||
{
|
{
|
||||||
*(vu32 *)(configPage + 0x44) -= __end__ - __start__;
|
*(vu32 *)(configPage + 0x44) -= 0x1000 + __end__ - __start__;
|
||||||
doingVeryShittyPmResLimitWorkaround = false;
|
doingVeryShittyPmResLimitWorkaround = false;
|
||||||
}
|
}
|
||||||
return officialSVCs[0x79];
|
return officialSVCs[0x79];
|
||||||
|
Reference in New Issue
Block a user