Rewrite k11ext mmu mapping func + linker script

This commit is contained in:
TuxSH 2018-05-25 23:27:50 +02:00
parent e64f267e4c
commit 35ad240018
6 changed files with 49 additions and 55 deletions

View File

@ -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++)
{ {

View File

@ -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)

View File

@ -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 ====

View File

@ -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;

View File

@ -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

View File

@ -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];