Compare commits

..

48 Commits

Author SHA1 Message Date
Aurora
1182d3a627 Fix #1050 2018-03-23 02:49:16 +01:00
TuxSH
938cb6492f Revert "Revert "Switched from mapping target process memory to svcReadProcessMemory & svcWriteProcessMemory functions.""
This reverts commit 1fd689f5da.
2018-03-20 01:11:49 +01:00
TuxSH
fed62855cb Merge pull request #1000 from duckbill007/master
Gateshark cheats support
2018-03-20 01:00:25 +01:00
Mikaela Szekely
4f54596658 Implement #940 (#1043)
Thanks @Qyriad ^^
2018-03-04 00:45:47 +01:00
Aurora Wright
0b41ed04d5 Simplify loadNintendoFirm after the previous commit 2018-02-09 05:09:43 +01:00
Aurora Wright
9509a86998 Force using the external FIRM if CTRNAND couldn't be mounted or the CTRNAND FIRM has issues 2018-02-05 03:47:43 +01:00
Duckbill
6d4d80a798 Merge remote-tracking branch 'upstream/master' 2018-01-19 17:38:57 +03:00
TuxSH
76d274cfe2 getmemregions: userland never exceeds 0x40000000 2018-01-19 01:42:53 +01:00
TuxSH
ccf13be964 Merge pull request #1010 from Nanquitas/input-redirection-sockupdate
InputRedirection: check service existence instead of using OpenProcessByName
2018-01-19 01:30:15 +01:00
TuxSH
e36b27ccf0 Merge pull request #1012 from Nanquitas/rosalina-freeze-fix
Rosalina: fix freeze when attempting to open Rosalina before the syst…
2018-01-19 01:29:58 +01:00
TuxSH
34c80ad476 Merge pull request #1009 from Nanquitas/gdb-list-memregion
gdb: new getmemregions command
2018-01-19 01:28:53 +01:00
TuxSH
97ae106d8e Merge pull request #1011 from Nanquitas/patch-2
sock_util: remove unneeded check
2018-01-19 01:28:08 +01:00
Nanquitas
7cb74b74d7 Rosalina: fix freeze when attempting to open Rosalina before the system finished to boot 2018-01-18 23:39:47 +01:00
Nanquitas
337205eb08 sock_util: remove unneeded check
We loop while (server_sockfd == -1) so it's safe to assume that (server_sockfd != -1) once out of the loop.
2018-01-18 22:57:46 +01:00
Nanquitas
f36977017b InputRedirection: check service existence instead of using OpenProcessByName 2018-01-18 20:44:54 +01:00
Nanquitas
e40b547bb6 gdb: new getmemregions command 2018-01-18 17:23:43 +01:00
Duckbill
1fd689f5da Revert "Switched from mapping target process memory to svcReadProcessMemory & svcWriteProcessMemory functions."
This reverts commit c5c8dca14c.
2018-01-16 09:54:55 +03:00
Duckbill
c5c8dca14c Switched from mapping target process memory to svcReadProcessMemory & svcWriteProcessMemory functions. 2018-01-15 21:29:05 +03:00
TuxSH
11f820efa7 Check service existence before GetServiceHandle 2018-01-15 02:52:50 +01:00
TuxSH
9074688491 Make srvGetServiceHandle non-blocking if service port is full in all cases 2018-01-15 02:27:07 +01:00
Duckbill
1de27c54f1 Fix range checks 2018-01-13 16:02:54 +03:00
Duckbill
3e67e64faa Fixes after review on github 2018-01-13 13:51:28 +03:00
TuxSH
553f8d2533 Remove lto for sysmodules 2018-01-12 11:20:17 +01:00
Duckbill
ec7ae35da1 Fixes for masked 16-bit cheat opcodes, based on existing cheats. 2018-01-12 10:46:50 +03:00
Duckbill
7e8da0d236 Possible out of bounds fix 2018-01-10 09:53:36 +03:00
Duckbill
b3e6561072 Merge remote-tracking branch 'upstream/master' 2018-01-06 12:29:08 +03:00
Aurora Wright
41f32ed983 Remove the need for hardcoding the horizontal positions for the "x"s in multiple choice options 2018-01-05 19:38:58 +01:00
TuxSH
bbadf840ef struct fb shouldn't be packed 2018-01-04 22:12:31 +01:00
TuxSH
acc50aae46 Merge branch 'master' of github.com:AuroraWright/Luma3DS 2018-01-04 18:41:14 +01:00
TuxSH
6a68a77973 Rewrite the ARM9 exception handlers, ...
- Fix patchArm9ExceptionHandlersInstall for older versions

- Fix some bugs in the ARM11 exception handlers

- Other, minor, changes
2018-01-04 18:40:11 +01:00
Duckbill
0f4d66dd61 Try to load cheats if there aren't any on every open of cheats menu. 2018-01-03 11:48:10 +03:00
Duckbill
d28642d2c3 More range checks and separate code and heap allocation 2018-01-03 00:27:44 +03:00
Duckbill
ca4685cc42 Range checks added 2018-01-02 14:23:45 +03:00
Aurora
522f10582d Merge pull request #995 from joel16/master
Update MCU::HWC functions with latest changes from ctrulib
2018-01-01 18:07:32 +01:00
Joel16
239d113177 Update mcu functions with changes from ctrulib 2018-01-01 11:05:22 -06:00
Duckbill
fd80294bf2 Fix buffer overflow in case of very long cheats.txt file 2017-12-31 11:26:18 +03:00
Duckbill
b379d83469 Merge remote-tracking branch 'upstream/master' 2017-12-31 11:16:44 +03:00
Aurora
27f352fdf1 Merge pull request #991 from Qyriad/master
Implement #989: Add configurable splash duration
2017-12-29 05:08:22 +01:00
Mikaela RJ Szekely
bfec874a7c Add colon in option that I forgot 2017-12-28 22:02:06 -05:00
Mikaela RJ Szekely
93561003e8 Implement #989: Add configurable splash duration 2017-12-28 21:50:06 -05:00
TuxSH
1572bfd989 [sm] Fix process unregistering logic bug (fixes #984)
In this case pm+sm were supposed to automatically unregister ro's services (the kernel can close a dying process's handle automatically). Not doing this apparently induced a reference leak of DevMenu's as a process, preventing it to be destroyed and the memory allocation reslimit counter to be updated by KProcess's destructor accordingly.
2017-12-27 19:30:57 +01:00
Duckbill
cb945612a3 Remove ast empty cheat from list 2017-12-25 14:16:57 +03:00
Duckbill
1b440f7f3b Skip empty cheats 2017-12-25 13:57:20 +03:00
Duckbill
78791f7b66 Paging fixes 2017-12-25 13:45:09 +03:00
Duckbill
5def0c18e2 Cheat file format changed from binary to plaintext 2017-12-22 14:46:46 +03:00
Duckbill
0e67b0f026 Moved key combo calculation to loading cheat phase 2017-12-22 12:39:09 +03:00
Duckbill
8052946517 Cheats array repleced by continous buffer 2017-12-22 12:17:45 +03:00
Duckbill
b6d6cc9750 Cheat implementations 2017-12-21 20:14:04 +03:00
40 changed files with 1744 additions and 235 deletions

6
.gitignore vendored
View File

@@ -13,4 +13,8 @@ exceptions/arm11/build
*.d
*.elf
*.cxi
.DS_Store
.DS_Store
*.dmp
.project
.cproject
.settings

View File

@@ -50,7 +50,7 @@ struct fb {
u8 *top_left;
u8 *top_right;
u8 *bottom;
} __attribute__((packed));
};
typedef enum
{

View File

@@ -42,4 +42,4 @@ struct fb {
u8 *top_left;
u8 *top_right;
u8 *bottom;
} __attribute__((packed));
};

View File

@@ -13,8 +13,8 @@ dir_build := build
dir_out := ../../$(dir_build)
ASFLAGS := -mcpu=arm946e-s
CFLAGS := -Wall -Wextra -mthumb $(ASFLAGS) -fno-builtin -std=c11 -Wno-main -O2 -flto -ffast-math
LDFLAGS := -nostdlib
CFLAGS := -Wall -Wextra -marm $(ASFLAGS) -fno-builtin -std=c11 -Wno-main -Os -ffast-math
LDFLAGS := -nostartfiles -Wl,--nmagic
objects = $(patsubst $(dir_source)/%.s, $(dir_build)/%.o, \
$(patsubst $(dir_source)/%.c, $(dir_build)/%.o, \

View File

@@ -4,7 +4,7 @@ OUTPUT_ARCH(arm)
ENTRY(_start)
SECTIONS
{
. = 0x01FF7FE0;
. = 0x01FF8000;
.text : ALIGN(4) { *(.text.start) *(.text*); . = ALIGN(4); }
.rodata : ALIGN(4) { *(.rodata*); . = ALIGN(4); }

View File

@@ -43,8 +43,9 @@ typedef struct __attribute__((packed))
u32 additionalDataSize;
} ExceptionDumpHeader;
u32 readMPUConfig(u32 *regionSettings);
void FIQHandler(void);
void undefinedInstructionHandler(void);
void dataAbortHandler(void);
void prefetchAbortHandler(void);
u32 safecpy(void *dst, const void *src, u32 len);

View File

@@ -22,92 +22,131 @@
@ or requiring that modified versions of such material be marked in
@ reasonable ways as different from the original version.
.macro GEN_HANDLER name
.global \name
.type \name, %function
\name:
ldr sp, =#0x02000000 @ We make the (full descending) stack point to the end of ITCM for our exception handlers.
@ It doesn't matter if we're overwriting stuff here, since we're going to reboot.
.macro GEN_USUAL_HANDLER name, index
\name\()Handler:
ldr sp, =_regs
stmia sp, {r0-r7}
stmfd sp!, {r0-r7} @ FIQ has its own r8-r14 regs
ldr r1, =\@ @ macro expansion counter
mov r0, #\index
b _commonHandler
.size \name, . - \name
.endm
.text
.arm
.align 4
.balign 4
.global _commonHandler
.type _commonHandler, %function
_commonHandler:
mov r1, r0
mov r0, sp
mrs r2, spsr
mov r6, sp
mrs r3, cpsr
add r6, r0, #(8 * 4)
orr r3, #0x1c0 @ disable Imprecise Aborts, IRQ and FIQ (equivalent to "cpsid aif" on arm11)
orr r3, #0xc0 @ mask interrupts
msr cpsr_cx, r3
tst r2, #0x20
bne noSvcBreak
cmp r1, #2
bne noSvcBreak
sub r0, lr, #4 @ calling cannotAccessAddress cause more problems that it actually solves... (I've to save a lot of regs and that's a pain tbh)
lsr r0, #20 @ we'll just do some address checks (to see if it's in ARM9 internal memory)
cmp r0, #0x80
bne noSvcBreak
ldr r4, [lr, #-4]
ldr r5, =#0xe12fff7f
cmp r4, r5
bne noSvcBreak
bic r5, r3, #0xf
orr r5, #0x3
msr cpsr_c, r5 @ switch to supervisor mode
ldmfd sp, {r8-r11}^
ldr r2, [sp, #0x1c] @ implementation details of the official svc handler
ldr r4, [sp, #0x18]
msr cpsr_c, r3 @ restore processor mode
tst r2, #0x20
addne lr, r4, #2 @ adjust address for later
moveq lr, r4
noSvcBreak:
ands r4, r2, #0xf @ get the mode that triggered the exception
moveq r4, #0xf @ usr => sys
bic r5, r3, #0xf
orr r5, r4
msr cpsr_c, r5 @ change processor mode
stmfd r6!, {r8-lr}
stmia r6!, {r8-lr}
msr cpsr_c, r3 @ restore processor mode
mov sp, r6
stmfd sp!, {r2,lr} @ it's a bit of a mess, but we will fix that later
@ order of saved regs now: cpsr, pc + (2/4/8), r8-r14, r0-r7
mov r0, sp
str lr, [r6], #4
str r2, [r6]
msr cpsr_cxsf, #0xdf @ finally, switch to system mode, mask interrupts and clear flags (in case of double faults)
ldr sp, =0x02000000
b mainHandler
GEN_HANDLER FIQHandler
GEN_HANDLER undefinedInstructionHandler
GEN_HANDLER prefetchAbortHandler
GEN_HANDLER dataAbortHandler
.global readMPUConfig
.type readMPUConfig, %function
readMPUConfig:
stmfd sp!, {r4-r8, lr}
mrc p15,0,r1,c6,c0,0
mrc p15,0,r2,c6,c1,0
mrc p15,0,r3,c6,c2,0
mrc p15,0,r4,c6,c3,0
mrc p15,0,r5,c6,c4,0
mrc p15,0,r6,c6,c5,0
mrc p15,0,r7,c6,c6,0
mrc p15,0,r8,c6,c7,0
stmia r0, {r1-r8}
mrc p15,0,r0,c5,c0,2 @ read data access permission bits
ldmfd sp!, {r4-r8, pc}
.global FIQHandler
.type FIQHandler, %function
GEN_USUAL_HANDLER FIQ, 0
.global undefinedInstructionHandler
.type undefinedInstructionHandler, %function
GEN_USUAL_HANDLER undefinedInstruction, 1
.global prefetchAbortHandler
.type prefetchAbortHandler, %function
prefetchAbortHandler:
msr cpsr_cx, #0xd7 @ mask interrupts (abort mode)
mrs sp, spsr
and sp, #0x3f
cmp sp, #0x13
bne _prefetchAbortNormalHandler
ldr sp, =BreakPtr
ldr sp, [sp]
cmp sp, #0
beq _prefetchAbortNormalHandler
add sp, #(1*4 + 4)
cmp lr, sp
bne _prefetchAbortNormalHandler
mov sp, r8
pop {r8-r11}
ldr lr, [sp, #8]!
ldr sp, [sp, #4]
msr spsr_cxsf, sp
tst sp, #0x20
addne lr, #2 @ adjust address for later
GEN_USUAL_HANDLER _prefetchAbortNormal, 2
.global dataAbortHandler
.type dataAbortHandler, %function
dataAbortHandler:
msr cpsr_cx, #0xd7 @ mask interrupts (abort mode)
mrs sp, spsr
and sp, #0x3f
cmp sp, #0x1f
bne _dataAbortNormalHandler
sub lr, #8
adr sp, safecpy
cmp lr, sp
blo _j_dataAbortNormalHandler
adr sp, _safecpy_end
cmp lr, sp
bhs _j_dataAbortNormalHandler
msr spsr_f, #(1 << 30)
mov r12, #0
adds pc, lr, #4
_j_dataAbortNormalHandler:
add lr, #8
GEN_USUAL_HANDLER _dataAbortNormal, 3
.global safecpy
.type safecpy, %function
safecpy:
push {r4, lr}
mov r3, #0
movs r12, #1
_safecpy_loop:
ldrb r4, [r1, r3]
cmp r12, #0
beq _safecpy_loop_end
strb r4, [r0, r3]
add r3, #1
cmp r3, r2
blo _safecpy_loop
_safecpy_loop_end:
mov r0, r3
pop {r4, pc}
_safecpy_end:
.bss
.balign 4
_regs: .skip (4 * 17)

View File

@@ -32,48 +32,10 @@
#define REG_DUMP_SIZE 4 * 17
#define CODE_DUMP_SIZE 48
bool cannotAccessAddress(const void *address)
{
u32 regionSettings[8];
u32 addr = (u32)address;
u32 dataAccessPermissions = readMPUConfig(regionSettings);
for(u32 i = 0; i < 8; i++)
{
if((dataAccessPermissions & 0xF) == 0 || (regionSettings[i] & 1) == 0)
continue; //No access / region not enabled
u32 regionAddrBase = regionSettings[i] & ~0xFFF;
u32 regionSize = 1 << (((regionSettings[i] >> 1) & 0x1F) + 1);
if(addr >= regionAddrBase && addr < regionAddrBase + regionSize)
return false;
dataAccessPermissions >>= 4;
}
return true;
}
static u32 __attribute__((noinline)) copyMemory(void *dst, const void *src, u32 size, u32 alignment)
{
u8 *out = (u8 *)dst;
const u8 *in = (const u8 *)src;
if(((u32)src & (alignment - 1)) != 0 || cannotAccessAddress(src) || (size != 0 && cannotAccessAddress((u8 *)src + size - 1)))
return 0;
for(u32 i = 0; i < size; i++)
*out++ = *in++;
return size;
}
void __attribute__((noreturn)) mainHandler(u32 *regs, u32 type)
void __attribute__((noreturn)) mainHandler(u32 *registerDump, u32 type)
{
ExceptionDumpHeader dumpHeader;
u32 registerDump[REG_DUMP_SIZE / 4];
u8 codeDump[CODE_DUMP_SIZE];
dumpHeader.magic[0] = 0xDEADC0DE;
@@ -89,27 +51,22 @@ void __attribute__((noreturn)) mainHandler(u32 *regs, u32 type)
dumpHeader.codeDumpSize = CODE_DUMP_SIZE;
dumpHeader.additionalDataSize = 0;
//Dump registers
//Current order of saved regs: cpsr, pc, r8-r14, r0-r7
u32 cpsr = regs[0];
u32 pc = regs[1] - (type < 3 ? (((cpsr & 0x20) != 0 && type == 1) ? 2 : 4) : 8);
u32 cpsr = registerDump[16];
u32 pc = registerDump[15] - (type < 3 ? (((cpsr & 0x20) != 0 && type == 1) ? 2 : 4) : 8);
registerDump[15] = pc;
registerDump[16] = cpsr;
for(u32 i = 0; i < 7; i++) registerDump[8 + i] = regs[2 + i];
for(u32 i = 0; i < 8; i++) registerDump[i] = regs[9 + i];
//Dump code
u8 *instr = (u8 *)pc + ((cpsr & 0x20) ? 2 : 4) - dumpHeader.codeDumpSize; //Doesn't work well on 32-bit Thumb instructions, but it isn't much of a problem
dumpHeader.codeDumpSize = copyMemory(codeDump, instr, dumpHeader.codeDumpSize, ((cpsr & 0x20) != 0) ? 2 : 4);
u8 *instr = (u8 *)pc + ((cpsr & 0x20) ? 2 : 4) - dumpHeader.codeDumpSize; //wouldn't work well on 32-bit Thumb instructions, but it isn't much of a problem
dumpHeader.codeDumpSize = ((u32)instr & (((cpsr & 0x20) != 0) ? 1 : 3)) != 0 ? 0 : safecpy(codeDump, instr, dumpHeader.codeDumpSize);
//Copy register dump and code dump
//Copy register dump and code dump
u8 *final = (u8 *)(FINAL_BUFFER + sizeof(ExceptionDumpHeader));
final += copyMemory(final, registerDump, dumpHeader.registerDumpSize, 1);
final += copyMemory(final, codeDump, dumpHeader.codeDumpSize, 1);
final += safecpy(final, registerDump, dumpHeader.registerDumpSize);
final += safecpy(final, codeDump, dumpHeader.codeDumpSize);
//Dump stack in place
dumpHeader.stackDumpSize = copyMemory(final, (const void *)registerDump[13], 0x1000 - (registerDump[13] & 0xFFF), 1);
dumpHeader.stackDumpSize = safecpy(final, (const void *)registerDump[13], 0x1000 - (registerDump[13] & 0xFFF));
dumpHeader.totalSize = sizeof(ExceptionDumpHeader) + dumpHeader.registerDumpSize + dumpHeader.codeDumpSize + dumpHeader.stackDumpSize + dumpHeader.additionalDataSize;

View File

@@ -26,8 +26,12 @@
.align 4
.global _start
_start:
add pc, r0, #(handlers - .) @ Dummy instruction to prevent compiler optimizations
add pc, r0, #(handlers - .) @ Dummy instruction
.global BreakPtr
BreakPtr: .word 0
.global handlers
handlers:
.word FIQHandler
.word undefinedInstructionHandler

View File

@@ -19,6 +19,7 @@ enum multiOptions
DEFAULTEMU = 0,
BRIGHTNESS,
SPLASH,
SPLASH_DURATION,
PIN,
NEWCPU
};

View File

@@ -159,7 +159,7 @@ _commonHandler:
_no_L2C:
cps #0x1F
msr cpsr_cxsf, #0xdf @ finally, switch to system mode, mask interrupts and clear flags (in case of double faults)
ldr sp, =exceptionStackTop
ldr sp, [sp]
sub sp, #0x100
@@ -221,7 +221,8 @@ prefetchAbortHandler:
pop {r8-r11}
ldr lr, [sp, #8]!
ldr sp, [sp, #4]
msr spsr, sp
msr spsr_cxsf, sp
tst sp, #0x20
addne lr, #2 @ adjust address for later
GEN_USUAL_HANDLER _prefetchAbortNormal, 2, 12

View File

@@ -37,7 +37,7 @@ bool isExceptionFatal(u32 spsr, u32 *regs, u32 index)
{
if(CONFIG(DISABLEARM11EXCHANDLERS)) return false;
if((spsr & 0x1f) != 0x10) return true;
if((spsr & 0x1F) != 0x10) return true;
KThread *thread = currentCoreContext->objectContext.currentThread;
KProcess *currentProcess = currentCoreContext->objectContext.currentProcess;
@@ -65,7 +65,7 @@ bool isExceptionFatal(u32 spsr, u32 *regs, u32 index)
extern u32 safecpy_sz;
bool isDataAbortExceptionRangeControlled(u32 spsr, u32 addr)
{
return ((spsr & 0x1F) != 0x10) && (
return (!(spsr & 0x20) && (spsr & 0x1F) != 0x10) && (
((u32)kernelUsrCopyFuncsStart <= addr && addr < (u32)kernelUsrCopyFuncsEnd) ||
((u32)safecpy <= addr && addr < (u32)safecpy + safecpy_sz)
);
@@ -96,7 +96,7 @@ void fatalExceptionHandlersMain(u32 *registerDump, u32 type, u32 cpuId)
registerDump[15] = pc;
//Dump code
u8 *instr = (u8 *)pc + ((cpsr & 0x20) ? 2 : 4) - dumpHeader.codeDumpSize; //Doesn't work well on 32-bit Thumb instructions, but it isn't much of a problem
u8 *instr = (u8 *)pc + ((cpsr & 0x20) ? 2 : 4) - dumpHeader.codeDumpSize; //wouldn't work well on 32-bit Thumb instructions, but it isn't much of a problem
dumpHeader.codeDumpSize = ((u32)instr & (((cpsr & 0x20) != 0) ? 1 : 3)) != 0 ? 0 : safecpy(codeDump, instr, dumpHeader.codeDumpSize);
//Copy register dump and code dump

View File

@@ -116,9 +116,7 @@ fname: .ascii "FILE"
.align 4
kernelcode_start:
mrs r0, cpsr ; disable interrupts
orr r0, #0xC0
msr cpsr, r0
msr cpsr_cxsf, #0xD3 ; disable interrupts and clear flags
ldr sp, =copy_launch_stub_stack_top

View File

@@ -27,6 +27,7 @@
#include "config.h"
#include "memory.h"
#include "fs.h"
#include "strings.h"
#include "utils.h"
#include "screen.h"
#include "draw.h"
@@ -81,6 +82,7 @@ void configMenu(bool oldPinStatus, u32 oldPinMode)
static const char *multiOptionsText[] = { "Default EmuNAND: 1( ) 2( ) 3( ) 4( )",
"Screen brightness: 4( ) 3( ) 2( ) 1( )",
"Splash: Off( ) Before( ) After( ) payloads",
"Splash duration: 1( ) 3( ) 5( ) 7( ) seconds",
"PIN lock: Off( ) 4( ) 6( ) 8( ) digits",
"New 3DS CPU: Off( ) Clock( ) L2( ) Clock+L2( )",
};
@@ -109,6 +111,11 @@ void configMenu(bool oldPinStatus, u32 oldPinMode)
"\t* 'After payloads' displays it\n"
"afterwards.",
"Select how long the splash screen\n"
"displays.\n\n"
"This has no effect if the splash\n"
"screen is not enabled.",
"Activate a PIN lock.\n\n"
"The PIN will be asked each time\n"
"Luma3DS boots.\n\n"
@@ -195,11 +202,12 @@ void configMenu(bool oldPinStatus, u32 oldPinMode)
u32 enabled;
bool visible;
} multiOptions[] = {
{ .posXs = {19, 24, 29, 34}, .visible = isSdMode },
{ .posXs = {21, 26, 31, 36}, .visible = true },
{ .posXs = {12, 22, 31, 0}, .visible = true },
{ .posXs = {14, 19, 24, 29}, .visible = true },
{ .posXs = {17, 26, 32, 44}, .visible = ISN3DS },
{ .visible = isSdMode },
{ .visible = true },
{ .visible = true },
{ .visible = true },
{ .visible = true },
{ .visible = ISN3DS },
};
struct singleOption {
@@ -227,7 +235,15 @@ void configMenu(bool oldPinStatus, u32 oldPinMode)
//Parse the existing options
for(u32 i = 0; i < multiOptionsAmount; i++)
{
//Detect the positions where the "x" should go
u32 optionNum = 0;
for(u32 j = 0; optionNum < 4 && j < strlen(multiOptionsText[i]); j++)
if(multiOptionsText[i][j] == '(') multiOptions[i].posXs[optionNum++] = j + 1;
while(optionNum < 4) multiOptions[i].posXs[optionNum++] = 0;
multiOptions[i].enabled = MULTICONFIG(i);
}
for(u32 i = 0; i < singleOptionsAmount; i++)
singleOptions[i].enabled = CONFIG(i);

View File

@@ -34,7 +34,7 @@
#define CONFIG_FILE "config.bin"
#define CONFIG_VERSIONMAJOR 2
#define CONFIG_VERSIONMINOR 2
#define CONFIG_VERSIONMINOR 3
#define BOOTCFG_NAND BOOTCONFIG(0, 7)
#define BOOTCFG_FIRM BOOTCONFIG(3, 7)
@@ -46,6 +46,7 @@ enum multiOptions
DEFAULTEMU = 0,
BRIGHTNESS,
SPLASH,
SPLASH_DURATION,
PIN,
NEWCPU
};

View File

@@ -36,6 +36,7 @@
#include "fs.h"
#include "fmt.h"
#include "font.h"
#include "config.h"
bool loadSplash(void)
{
@@ -56,7 +57,9 @@ bool loadSplash(void)
if(!isTopSplashValid && !isBottomSplashValid) return false;
swapFramebuffers(true);
wait(3000ULL);
u32 durationIndex = MULTICONFIG(SPLASH_DURATION);
wait(1000ULL + (durationIndex * 2000ULL));
return true;
}

View File

@@ -37,7 +37,7 @@
void installArm9Handlers(void)
{
memcpy((void *)0x01FF8000, arm9_exceptions_bin + 32, arm9_exceptions_bin_size - 32);
memcpy((void *)0x01FF8000, arm9_exceptions_bin, arm9_exceptions_bin_size);
/* IRQHandler is at 0x08000000, but we won't handle it for some reasons
svcHandler is at 0x08000010, but we won't handle svc either */
@@ -47,8 +47,10 @@ void installArm9Handlers(void)
for(u32 i = 0; i < 4; i++)
{
*(vu32 *)(0x08000000 + offsets[i]) = 0xE51FF004;
*(vu32 *)(0x08000000 + offsets[i] + 4) = *((u32 *)arm9_exceptions_bin + 1 + i);
*(vu32 *)(0x08000000 + offsets[i] + 4) = *(vu32 *)(0x01FF8008 + 4 * i);
}
*(vu32 *)0x01FF8004 = 0; //BreakPtr
}
void detectAndProcessExceptionDumps(void)

View File

@@ -123,7 +123,7 @@ static inline u32 loadFirmFromStorage(FirmwareType firmType)
"cetk_sysupdater"
};
u32 firmSize = fileRead(firm, firmType == NATIVE_FIRM1X2X ? firmwareFiles[0] : firmwareFiles[(u32)firmType], 0x400000 + sizeof(Cxi) + 0x200);
u32 firmSize = fileRead(firm, firmwareFiles[(u32)firmType], 0x400000 + sizeof(Cxi) + 0x200);
if(!firmSize) return 0;
@@ -137,7 +137,7 @@ static inline u32 loadFirmFromStorage(FirmwareType firmType)
u8 cetk[0xA50];
if(fileRead(cetk, firmType == NATIVE_FIRM1X2X ? cetkFiles[0] : cetkFiles[(u32)firmType], sizeof(cetk)) != sizeof(cetk))
if(fileRead(cetk, cetkFiles[(u32)firmType], sizeof(cetk)) != sizeof(cetk))
error("The cetk is missing or corrupted.");
firmSize = decryptNusFirm((Ticket *)(cetk + 0x140), (Cxi *)firm, firmSize);
@@ -152,18 +152,42 @@ static inline u32 loadFirmFromStorage(FirmwareType firmType)
u32 loadNintendoFirm(FirmwareType *firmType, FirmwareSource nandType, bool loadFromStorage, bool isSafeMode)
{
if(isSdMode && !mountFs(false, false)) error("Failed to mount CTRNAND.");
u32 firmVersion,
firmSize;
//Load FIRM from CTRNAND
u32 firmVersion = firmRead(firm, (u32)*firmType);
bool ctrNandError = isSdMode && !mountFs(false, false);
if(firmVersion == 0xFFFFFFFF) error("Failed to get the CTRNAND FIRM.");
if(!ctrNandError)
{
//Load FIRM from CTRNAND
firmVersion = firmRead(firm, (u32)*firmType);
u32 firmSize = decryptExeFs((Cxi *)firm);
if(firmVersion == 0xFFFFFFFF) ctrNandError = true;
else
{
firmSize = decryptExeFs((Cxi *)firm);
if(!firmSize) error("Failed to decrypt the CTRNAND FIRM.");
if(!firmSize || !checkFirm(firmSize)) ctrNandError = true;
}
}
if(!checkFirm(firmSize)) error("The CTRNAND FIRM is invalid or corrupted.");
bool loadedFromStorage = false;
if(loadFromStorage || ctrNandError)
{
u32 result = loadFirmFromStorage(*firmType);
if(result != 0)
{
loadedFromStorage = true;
firmSize = result;
}
else if(ctrNandError) error("Unable to mount CTRNAND or load the CTRNAND FIRM.\nPlease use an external one.");
}
//Check that the FIRM is right for the console from the ARM9 section address
if((firm->section[3].offset != 0 ? firm->section[3].address : firm->section[2].address) != (ISN3DS ? (u8 *)0x8006000 : (u8 *)0x8006800))
error("The %s FIRM is not for this console.", loadedFromStorage ? "external" : "CTRNAND");
if(!ISN3DS && *firmType == NATIVE_FIRM && firm->section[0].address == (u8 *)0x1FF80000)
{
@@ -175,23 +199,6 @@ u32 loadNintendoFirm(FirmwareType *firmType, FirmwareSource nandType, bool loadF
*firmType = NATIVE_FIRM1X2X;
}
bool loadedFromStorage = false;
if(loadFromStorage)
{
u32 result = loadFirmFromStorage(*firmType);
if(result != 0)
{
loadedFromStorage = true;
firmSize = result;
}
}
//Check that the FIRM is right for the console from the ARM9 section address
if((firm->section[3].offset != 0 ? firm->section[3].address : firm->section[2].address) != (ISN3DS ? (u8 *)0x8006000 : (u8 *)0x8006800))
error("The %s FIRM is not for this console.", loadedFromStorage ? "external" : "CTRNAND");
if(loadedFromStorage || ISDEVUNIT)
{
firmVersion = 0xFFFFFFFF;

View File

@@ -454,7 +454,9 @@ u32 patchArm9ExceptionHandlersInstall(u8 *pos, u32 size)
if(temp == NULL) return 1;
u32 *off = (u32 *)(temp - 0xA);
u32 *off;
for(off = (u32 *)(temp - 2); *off != 0xE5801000; off--); //Until str r1, [r0]
for(u32 r0 = 0x08000000; *off != 0xE3A01040; off++) //Until mov r1, #0x40
{
@@ -491,7 +493,15 @@ u32 patchSvcBreak9(u8 *pos, u32 size, u32 kernel9Address)
while(*arm9SvcTable != 0) arm9SvcTable++; //Look for SVC0 (NULL)
u32 *addr = (u32 *)(pos + arm9SvcTable[0x3C] - kernel9Address);
*addr = 0xE12FFF7F;
/*
mov r8, sp
bkpt 0xffff
*/
addr[0] = 0xE1A0800D;
addr[1] = 0xE12FFF7F;
*(vu32 *)0x01FF8004 = arm9SvcTable[0x3C]; //BreakPtr
return 0;
}

View File

@@ -146,21 +146,32 @@ bool verifyPin(u32 pinMode)
initScreens();
swapFramebuffers(true);
drawString(true, 10, 10, COLOR_TITLE, "Enter the PIN using ABXY and the DPad to proceed");
drawString(true, 10, 10 + SPACING_Y, COLOR_TITLE, "Press START to shutdown, SELECT to clear");
drawFormattedString(true, 10, 10 + 3 * SPACING_Y, COLOR_WHITE, "PIN (%u digits): ", lengthBlock[0]);
static const char *messageFile = "pinmessage.txt";
char message[801];
u32 messageSize = fileRead(message, messageFile, sizeof(message) - 1);
if(messageSize != 0)
bool isBottomSplashValid = getFileSize("splashpin.bin") == SCREEN_BOTTOM_FBSIZE;
if(isBottomSplashValid)
{
message[messageSize] = 0;
drawString(false, 10, 10, COLOR_WHITE, message);
isBottomSplashValid = fileRead(fbs[0].bottom, "splashpin.bin", SCREEN_BOTTOM_FBSIZE) == SCREEN_BOTTOM_FBSIZE;
}
else
{
static const char *messageFile = "pinmessage.txt";
char message[801];
u32 messageSize = fileRead(message, messageFile, sizeof(message) - 1);
if(messageSize != 0)
{
message[messageSize] = 0;
drawString(false, 10, 10, COLOR_WHITE, message);
}
}
swapFramebuffers(false);
//Pad to AES block length with zeroes
__attribute__((aligned(4))) u8 enteredPassword[AES_BLOCK_SIZE] = {0};

View File

@@ -49,7 +49,7 @@ struct fb {
u8 *top_left;
u8 *top_right;
u8 *bottom;
} __attribute__((packed));
};
typedef enum
{

View File

@@ -27,9 +27,7 @@
.global _start
_start:
@ Disable interrupts and switch to supervisor mode (also clear flags)
mov r4, #0x13
orr r4, #0x1C0
msr cpsr_cxsf, r4
msr cpsr_cxsf, #0xD3
@ Check if r0-r2 are 0 (r0-sp are supposed to be 0), and for regions 0, 5 and 7 of the MPU config
@ This is not foolproof but should work well enough

View File

@@ -20,7 +20,7 @@ LIBPATHS := $(foreach dir,$(LIBDIRS),-L$(dir)/lib)
INCLUDE := $(foreach dir,$(LIBDIRS),-I$(dir)/include)
ASFLAGS := -mcpu=mpcore -mfloat-abi=hard
CFLAGS := -Wall -Wextra $(ASFLAGS) -fno-builtin -std=c11 -O2 -flto -ffast-math $(INCLUDE) -DARM11 -D_3DS
CFLAGS := -Wall -Wextra $(ASFLAGS) -fno-builtin -std=c11 -O2 -ffast-math $(INCLUDE) -DARM11 -D_3DS
LDFLAGS := -specs=3dsx.specs $(ASFLAGS) -Wl,--section-start,.text=0x14000000
objects = $(patsubst $(dir_source)/%.c, $(dir_build)/%.o, \
@@ -51,7 +51,7 @@ $(dir_build)/%.bin.o: $(dir_build)/%.bin
@$(bin2o)
$(dir_build)/%.bin: $(dir_patches)/%.s
@mkdir -p "$(@D)"
@mkdir -p "$(@D)"
@armips $<
$(dir_build)/memory.o $(dir_build)/strings.o: CFLAGS += -O3

View File

@@ -21,6 +21,7 @@ enum multiOptions
DEFAULTEMU = 0,
BRIGHTNESS,
SPLASH,
SPLASH_DURATION,
PIN,
NEWCPU
};

View File

@@ -21,7 +21,7 @@ INCLUDE := $(foreach dir,$(LIBDIRS),-I$(dir)/include)
ARCH := -mcpu=mpcore -mfloat-abi=hard
ASFLAGS := -g $(ARCH)
CFLAGS := -Wall -Wextra -MMD -MP -marm $(ASFLAGS) -mtp=soft -fno-builtin -std=c11 -O2 -flto -ffast-math -mword-relocations \
CFLAGS := -Wall -Wextra -MMD -MP -marm $(ASFLAGS) -mtp=soft -fno-builtin -std=c11 -O2 -ffast-math -mword-relocations \
-fomit-frame-pointer -ffunction-sections -fdata-sections $(INCLUDE) -I$(dir_include) -DARM11 -D_3DS
LDFLAGS := -specs=3dsx.specs -g $(ARCH) -mtp=soft -Wl,--section-start,.text=0x14000000 -Wl,--gc-sections

View File

@@ -34,6 +34,7 @@
GDB_DECLARE_REMOTE_COMMAND_HANDLER(SyncRequestInfo);
GDB_DECLARE_REMOTE_COMMAND_HANDLER(TranslateHandle);
GDB_DECLARE_REMOTE_COMMAND_HANDLER(GetMmuConfig);
GDB_DECLARE_REMOTE_COMMAND_HANDLER(GetMemRegions);
GDB_DECLARE_REMOTE_COMMAND_HANDLER(FlushCaches);
GDB_DECLARE_REMOTE_COMMAND_HANDLER(ToggleExternalMemoryAccess);

View File

@@ -37,3 +37,4 @@ void RosalinaMenu_ShowCredits(void);
void RosalinaMenu_ProcessList(void);
void RosalinaMenu_PowerOff(void);
void RosalinaMenu_Reboot(void);
void RosalinaMenu_Cheats(void);

View File

@@ -0,0 +1,36 @@
/*
* This file is part of Luma3DS
* Copyright (C) 2016-2017 Aurora Wright, TuxSH
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*
* Additional Terms 7.b and 7.c of GPLv3 apply to this file:
* * Requiring preservation of specified reasonable legal notices or
* author attributions in that material or in the Appropriate Legal
* Notices displayed by works containing it.
* * Prohibiting misrepresentation of the origin of that material,
* or requiring that modified versions of such material be marked in
* reasonable ways as different from the original version.
*/
/* This file was entirely written by Duckbill */
#pragma once
#include <3ds/types.h>
#define CHEATS_PER_MENU_PAGE 18
void RosalinaMenu_Cheats(void);
void Cheat_ApplyKeyCheats();

View File

@@ -26,10 +26,22 @@
#include "MyThread.h"
#include "memory.h"
#include <3ds/srv.h>
static void _thread_begin(void* arg)
{
MyThread *t = (MyThread *)arg;
// ROSALINA HACKJOB BEGIN
// NORMAL APPS SHOULD NOT DO THIS, EVER
u32 *tls = (u32 *)getThreadLocalStorage();
memset(tls, 0, 0x80);
tls[0] = 0x21545624;
// ROSALINA HACKJOB END
// Rosalina specific:
srvSetBlockingPolicy(true); // GetServiceHandle nonblocking if service port is full
t->ep();
MyThread_Exit();
}

View File

@@ -39,6 +39,7 @@ struct
{ "syncrequestinfo" , GDB_REMOTE_COMMAND_HANDLER(SyncRequestInfo) },
{ "translatehandle" , GDB_REMOTE_COMMAND_HANDLER(TranslateHandle) },
{ "getmmuconfig" , GDB_REMOTE_COMMAND_HANDLER(GetMmuConfig) },
{ "getmemregions" , GDB_REMOTE_COMMAND_HANDLER(GetMemRegions) },
{ "flushcaches" , GDB_REMOTE_COMMAND_HANDLER(FlushCaches) },
{ "toggleextmemaccess", GDB_REMOTE_COMMAND_HANDLER(ToggleExternalMemoryAccess) },
};
@@ -226,6 +227,84 @@ GDB_DECLARE_REMOTE_COMMAND_HANDLER(GetMmuConfig)
return GDB_SendHexPacket(ctx, outbuf, n);
}
static const char *FormatMemPerm(u32 perm)
{
if (perm == MEMPERM_DONTCARE)
return "???";
static char buf[4] = {0};
buf[0] = perm & MEMPERM_READ ? 'r' : '-';
buf[1] = perm & MEMPERM_WRITE ? 'w' : '-';
buf[2] = perm & MEMPERM_EXECUTE ? 'x' : '-';
return buf;
}
static const char *FormatMemState(u32 state)
{
if (state > 11)
return "Unknown";
static const char *states[12] =
{
"Free",
"Reserved",
"IO",
"Static",
"Code",
"Private",
"Shared",
"Continuous",
"Aliased",
"Alias",
"AliasCode",
"Locked"
};
return states[state];
}
GDB_DECLARE_REMOTE_COMMAND_HANDLER(GetMemRegions)
{
u32 address = 0;
u32 posInBuffer = 0;
u32 maxPosInBuffer = GDB_BUF_LEN / 2 - 35; ///< 35 is the maximum length of a formatted region
Handle handle;
MemInfo memi;
PageInfo pagei;
char outbuf[GDB_BUF_LEN / 2 + 1];
if(R_FAILED(svcOpenProcess(&handle, ctx->pid)))
{
posInBuffer = sprintf(outbuf, "Invalid process (wtf?)\n");
goto end;
}
while (address < 0x40000000 ///< Limit to check for regions
&& posInBuffer < maxPosInBuffer
&& R_SUCCEEDED(svcQueryProcessMemory(&memi, &pagei, handle, address)))
{
// Update the address for next region
address = memi.base_addr + memi.size;
// If region isn't FREE then add it to the list
if (memi.state != MEMSTATE_FREE)
{
const char *perm = FormatMemPerm(memi.perm);
const char *state = FormatMemState(memi.state);
posInBuffer += sprintf(outbuf + posInBuffer, "%08X - %08X %s %s\n",
memi.base_addr, address, perm, state);
}
}
svcCloseHandle(handle);
end:
return GDB_SendHexPacket(ctx, outbuf, posInBuffer);
}
GDB_DECLARE_REMOTE_COMMAND_HANDLER(FlushCaches)
{
if(ctx->commandData[0] != 0)

View File

@@ -89,6 +89,16 @@ void initSystem()
ProcessPatchesMenu_PatchUnpatchFSDirectly();
__sync_init();
__appInit();
// ROSALINA HACKJOB BEGIN
// NORMAL APPS SHOULD NOT DO THIS, EVER
u32 *tls = (u32 *)getThreadLocalStorage();
memset(tls, 0, 0x80);
tls[0] = 0x21545624;
// ROSALINA HACKJOB END
// Rosalina specific:
srvSetBlockingPolicy(true); // GetServiceHandle nonblocking if service port is full
}
bool terminationRequest = false;

View File

@@ -33,6 +33,7 @@
#include "menus.h"
#include "utils.h"
#include "menus/n3ds.h"
#include "menus/cheats.h"
#include "minisoc.h"
u32 waitInputWithTimeout(u32 msec)
@@ -142,20 +143,35 @@ void menuThreadMain(void)
if(!isN3DS)
{
rosalinaMenu.nbItems--;
for(u32 i = 2; i <= rosalinaMenu.nbItems; i++)
for(u32 i = 3; i <= rosalinaMenu.nbItems; i++)
rosalinaMenu.items[i] = rosalinaMenu.items[i+1];
}
else
N3DSMenu_UpdateStatus();
bool isAcURegistered = false;
while(!terminationRequest)
{
if((HID_PAD & menuCombo) == menuCombo)
{
menuEnter();
if(isN3DS) N3DSMenu_UpdateStatus();
menuShow(&rosalinaMenu);
menuLeave();
if (!isAcURegistered)
isAcURegistered = R_SUCCEEDED(srvIsServiceRegistered(&isAcURegistered, "ac:u"))
&& isAcURegistered;
if (isAcURegistered)
{
menuEnter();
if(isN3DS) N3DSMenu_UpdateStatus();
menuShow(&rosalinaMenu);
menuLeave();
}
}
else
{
if (HID_PAD & 0xFFF) {
Cheat_ApplyKeyCheats();
}
}
svcSleepThread(50 * 1000 * 1000LL);
}
@@ -193,13 +209,16 @@ static void menuDraw(Menu *menu, u32 selected)
s64 out;
u32 version, commitHash;
bool isRelease;
bool isMcuHwcRegistered;
if(R_SUCCEEDED(mcuHwcInit()))
if(R_SUCCEEDED(srvIsServiceRegistered(&isMcuHwcRegistered, "mcu::HWC")) && isMcuHwcRegistered && R_SUCCEEDED(mcuHwcInit()))
{
if(R_FAILED(mcuHwcGetBatteryLevel(&batteryLevel)))
if(R_FAILED(MCUHWC_GetBatteryLevel(&batteryLevel)))
batteryLevel = 255;
mcuHwcExit();
}
else
batteryLevel = 255;
svcGetSystemInfo(&out, 0x10000, 0);
version = (u32)out;

View File

@@ -41,8 +41,9 @@
Menu rosalinaMenu = {
"Rosalina menu",
.nbItems = 9,
.nbItems = 10,
{
{ "Cheats...", METHOD, .method = &RosalinaMenu_Cheats },
{ "Process list", METHOD, .method = &RosalinaMenu_ProcessList },
{ "Take screenshot (slow!)", METHOD, .method = &RosalinaMenu_TakeScreenshot },
{ "New 3DS menu...", MENU, .menu = &N3DSMenu },

File diff suppressed because it is too large Load Diff

View File

@@ -69,12 +69,10 @@ void DebuggerMenu_EnableDebugger(void)
bool done = false, alreadyEnabled = gdbServer.super.running;
Result res = 0;
char buf[65];
bool cantStart;
Handle dummy;
bool isSocURegistered;
res = OpenProcessByName("socket", &dummy);
cantStart = R_FAILED(res);
svcCloseHandle(dummy);
res = srvIsServiceRegistered(&isSocURegistered, "soc:U");
isSocURegistered = R_SUCCEEDED(res) && isSocURegistered;
Draw_Lock();
Draw_ClearFramebuffer();
@@ -88,7 +86,7 @@ void DebuggerMenu_EnableDebugger(void)
if(alreadyEnabled)
Draw_DrawString(10, 30, COLOR_WHITE, "Already enabled!");
else if(cantStart)
else if(!isSocURegistered)
Draw_DrawString(10, 30, COLOR_WHITE, "Can't start the debugger before the system has fi-\nnished loading.");
else
{

View File

@@ -258,19 +258,19 @@ void MiscellaneousMenu_InputRedirection(void)
}
else
{
Handle dummy;
s64 dummyInfo;
bool isN3DS = svcGetSystemInfo(&dummyInfo, 0x10001, 0) == 0;
s64 dummyInfo;
bool isN3DS = svcGetSystemInfo(&dummyInfo, 0x10001, 0) == 0;
bool isSocURegistered;
res = OpenProcessByName("socket", &dummy);
cantStart = R_FAILED(res);
svcCloseHandle(dummy);
res = srvIsServiceRegistered(&isSocURegistered, "soc:U");
cantStart = R_FAILED(res) || !isSocURegistered;
if(!cantStart && isN3DS)
{
res = OpenProcessByName("ir", &dummy);
cantStart = R_FAILED(res);
svcCloseHandle(dummy);
bool isIrRstRegistered;
res = srvIsServiceRegistered(&isIrRstRegistered, "ir:rst");
cantStart = R_FAILED(res) || !isIrRstRegistered;
}
}
@@ -285,7 +285,7 @@ void MiscellaneousMenu_InputRedirection(void)
Draw_DrawString(10, 10, COLOR_TITLE, "Miscellaneous options menu");
if(!wasEnabled && cantStart)
Draw_DrawString(10, 30, COLOR_WHITE, "Can't start the debugger before the system has fi-\nnished loading.");
Draw_DrawString(10, 30, COLOR_WHITE, "Can't start the input redirection before the system\nhas finished loading.");
else if(!wasEnabled)
{
Draw_DrawString(10, 30, COLOR_WHITE, "Starting InputRedirection...");

View File

@@ -66,9 +66,9 @@ void SysConfigMenu_ToggleLEDs(void)
{
mcuHwcInit();
u8 result;
mcuHwcReadRegister(0x28, &result, 1);
MCUHWC_ReadRegister(0x28, &result, 1);
result = ~result;
mcuHwcWriteRegister(0x28, &result, 1);
MCUHWC_WriteRegister(0x28, &result, 1);
mcuHwcExit();
}
else if(pressed & BUTTON_B)

View File

@@ -80,6 +80,18 @@ Result miniSocInit()
u32 tmp = 0;
Result ret = 0;
bool isSocURegistered;
ret = srvIsServiceRegistered(&isSocURegistered, "soc:U");
if(ret != 0) goto cleanup;
if(!isSocURegistered)
{
ret = -1;
goto cleanup;
}
ret = srvGetServiceHandle(&SOCU_handle, "soc:U");
if(ret != 0) goto cleanup;
ret = svcControlMemory(&tmp, socContextAddr, 0, socContextSize, MEMOP_ALLOC, MEMPERM_READ | MEMPERM_WRITE);
if(ret != 0) goto cleanup;
@@ -89,8 +101,7 @@ Result miniSocInit()
ret = svcCreateMemoryBlock(&socMemhandle, (u32)socContextAddr, socContextSize, 0, 3);
if(ret != 0) goto cleanup;
ret = srvGetServiceHandle(&SOCU_handle, "soc:U");
if(ret != 0) goto cleanup;
ret = SOCU_Initialize(socMemhandle, socContextSize);
if(ret != 0) goto cleanup;

View File

@@ -135,33 +135,30 @@ void server_bind(struct sock_server *serv, u16 port)
server_sockfd = socSocket(AF_INET, SOCK_STREAM, 0);
}
if(server_sockfd != -1)
struct sockaddr_in saddr;
saddr.sin_family = AF_INET;
saddr.sin_port = htons(port);
saddr.sin_addr.s_addr = gethostid();
res = socBind(server_sockfd, (struct sockaddr*)&saddr, sizeof(struct sockaddr_in));
if(res == 0)
{
struct sockaddr_in saddr;
saddr.sin_family = AF_INET;
saddr.sin_port = htons(port);
saddr.sin_addr.s_addr = gethostid();
res = socBind(server_sockfd, (struct sockaddr*)&saddr, sizeof(struct sockaddr_in));
res = socListen(server_sockfd, 2);
if(res == 0)
{
res = socListen(server_sockfd, 2);
if(res == 0)
{
int idx = serv->nfds;
serv->nfds++;
serv->poll_fds[idx].fd = server_sockfd;
serv->poll_fds[idx].events = POLLIN;
int idx = serv->nfds;
serv->nfds++;
serv->poll_fds[idx].fd = server_sockfd;
serv->poll_fds[idx].events = POLLIN;
struct sock_ctx *new_ctx = server_alloc_server_ctx(serv);
memcpy(&new_ctx->addr_in, &saddr, sizeof(struct sockaddr_in));
new_ctx->type = SOCK_SERVER;
new_ctx->sockfd = server_sockfd;
new_ctx->n = 0;
new_ctx->i = idx;
serv->ctx_ptrs[idx] = new_ctx;
}
struct sock_ctx *new_ctx = server_alloc_server_ctx(serv);
memcpy(&new_ctx->addr_in, &saddr, sizeof(struct sockaddr_in));
new_ctx->type = SOCK_SERVER;
new_ctx->sockfd = server_sockfd;
new_ctx->n = 0;
new_ctx->i = idx;
serv->ctx_ptrs[idx] = new_ctx;
}
}
}

View File

@@ -58,13 +58,16 @@ Result UnregisterProcess(u32 pid)
svcCloseHandle(processData->notificationSemaphore);
// Unregister the services registered by the process
for(u32 i = 0; i < nbServices; i++)
u32 i = 0;
while(i < nbServices)
{
if(servicesInfo[i].pid == pid)
{
svcCloseHandle(servicesInfo[i].clientPort);
servicesInfo[i] = servicesInfo[--nbServices];
}
else
++i;
}
moveNode(processData, &freeProcessDataList, false);