Skip to content

Commit 8dbd3cf

Browse files
Add files via upload
1 parent 730e3e6 commit 8dbd3cf

File tree

2 files changed

+127
-20
lines changed

2 files changed

+127
-20
lines changed

source/defines.h

+15
Original file line numberDiff line numberDiff line change
@@ -149,6 +149,7 @@ struct ucred {
149149
struct proc {
150150
char useless[64];
151151
struct ucred *p_ucred;
152+
struct filedesc *p_fd;
152153
};
153154

154155
struct thread {
@@ -170,6 +171,20 @@ struct fileops {
170171
int fo_flags; /* DFLAG_* below */
171172
};
172173

174+
struct filedesc {
175+
void *useless1[3];
176+
void *fd_rdir;
177+
void *fd_jdir;
178+
};
179+
180+
struct kpayload_args{
181+
uint64_t user_arg;
182+
};
183+
184+
struct kdump_args{
185+
uint64_t argArrayPtr;
186+
};
187+
173188
#define X86_CR0_WP (1 << 16)
174189

175190
static inline __attribute__((always_inline)) uint64_t readCr0(void) {

source/main.c

+112-20
Original file line numberDiff line numberDiff line change
@@ -3,31 +3,72 @@
33
#include "ps4.h"
44
#include "defines.h"
55

6+
#define KERN_XFAST_SYSCALL 0x30EB30
7+
8+
#define CTL_KERN 1 /* "high kernel": proc, limits */
9+
#define KERN_PROC 14 /* struct: process entries */
10+
#define KERN_PROC_VMMAP 32 /* VM map entries for process */
11+
#define KERN_PROC_PID 1 /* by process id */
12+
613
extern char kexec[];
714
extern unsigned kexec_size;
815

916
static int sock;
1017

1118
void usbthing();
1219

13-
int _main(void) {
20+
unsigned int long long __readmsr(unsigned long __register) {
21+
// Loads the contents of a 64-bit model specific register (MSR) specified in
22+
// the ECX register into registers EDX:EAX. The EDX register is loaded with
23+
// the high-order 32 bits of the MSR and the EAX register is loaded with the
24+
// low-order 32 bits. If less than 64 bits are implemented in the MSR being
25+
// read, the values returned to EDX:EAX in unimplemented bit locations are
26+
// undefined.
27+
unsigned long __edx;
28+
unsigned long __eax;
29+
__asm__ ("rdmsr" : "=d"(__edx), "=a"(__eax) : "c"(__register));
30+
return (((unsigned int long long)__edx) << 32) | (unsigned int long long)__eax;
31+
}
1432

15-
initKernel();
16-
initLibc();
17-
initNetwork();
33+
int kpayload(struct thread *td, struct kpayload_args* args){
1834

19-
struct sockaddr_in server;
35+
printfsocket("Starting kpayload...\n");
2036

21-
server.sin_len = sizeof(server);
22-
server.sin_family = AF_INET;
23-
server.sin_addr.s_addr = IP(192, 168, 1, 12);
24-
server.sin_port = sceNetHtons(9023);
25-
memset(server.sin_zero, 0, sizeof(server.sin_zero));
26-
sock = sceNetSocket("debug", AF_INET, SOCK_STREAM, 0);
27-
sceNetConnect(sock, (struct sockaddr *)&server, sizeof(server));
28-
int flag = 1;
29-
sceNetSetsockopt(sock, IPPROTO_TCP, TCP_NODELAY, (char *)&flag, sizeof(int));
37+
struct ucred* cred;
38+
struct filedesc* fd;
39+
40+
fd = td->td_proc->p_fd;
41+
cred = td->td_proc->p_ucred;
42+
43+
printfsocket("Reading kernel_base...\n");
44+
void* kernel_base = &((uint8_t*)__readmsr(0xC0000082))[-0x30EB30];
45+
uint8_t* kernel_ptr = (uint8_t*)kernel_base;
46+
void** got_prison0 = (void**)&kernel_ptr[0xF26010];
47+
void** got_rootvnode = (void**)&kernel_ptr[0x206D250];
48+
49+
printfsocket("Resolve kernel functions...\n");
50+
51+
int (*copyout)(const void *kaddr, void *uaddr, size_t len) = (void *)(kernel_base + 0x286d70);
52+
int (*printfkernel)(const char *fmt, ...) = (void *)(kernel_base + 0x347580);
53+
int (*copyin)(const void *uaddr, void *kaddr, size_t len) = (void *)(kernel_base + 0x286df0);
54+
55+
cred->cr_uid = 0;
56+
cred->cr_ruid = 0;
57+
cred->cr_rgid = 0;
58+
cred->cr_groups[0] = 0;
59+
60+
cred->cr_prison = *got_prison0;
61+
fd->fd_rdir = fd->fd_jdir = *got_rootvnode;
62+
63+
printfsocket("Enabling uart...\n");
64+
uint16_t *securityFlags = (uint64_t *)(kernel_base+0x2001516);
65+
*securityFlags = *securityFlags & ~(1 << 15);
3066

67+
printfsocket("Disabling write protection...\n");
68+
uint64_t cr0 = readCr0();
69+
writeCr0(cr0 & ~X86_CR0_WP);
70+
71+
//Kexec
3172
printfsocket("Kexec init...\n");
3273

3374
void *DT_HASH_SEGMENT = (void *)0xffffffff82200160;
@@ -36,7 +77,7 @@ int _main(void) {
3677

3778
printfsocket("Kexec size [%d]\n", kexec_size);
3879

39-
memcpy(DT_HASH_SEGMENT, kexec, kexec_size); //Fails here
80+
copyin(DT_HASH_SEGMENT, kexec, kexec_size);
4081

4182
printfsocket("Kexec init [1]\n");
4283

@@ -45,26 +86,76 @@ int _main(void) {
4586
printfsocket("Kexec init [2]\n");
4687

4788
kexec_init(NULL, NULL);
89+
90+
printfsocket("Kexec inited successfully!\n");
91+
92+
// Say hello and put the kernel base in userland to we can use later
93+
94+
printfkernel("\n\n\nHELLO FROM YOUR KERN DUDE =)\n\n\n");
95+
96+
printfkernel("kernel base is:0x%016llx\n", kernel_base);
97+
98+
uint64_t uaddr;
99+
memcpy(&uaddr,&args[2],8);
100+
101+
printfkernel("uaddr is:0x%016llx\n", uaddr);
102+
103+
copyout(&kernel_base, uaddr, 8);
104+
105+
return 0;
106+
}
107+
108+
int _main(struct thread *td) {
109+
110+
initKernel();
111+
initLibc();
112+
initNetwork();
113+
initPthread();
114+
115+
struct sockaddr_in server;
116+
117+
server.sin_len = sizeof(server);
118+
server.sin_family = AF_INET;
119+
server.sin_addr.s_addr = IP(192, 168, 1, 12);
120+
server.sin_port = sceNetHtons(9023);
121+
memset(server.sin_zero, 0, sizeof(server.sin_zero));
122+
sock = sceNetSocket("debug", AF_INET, SOCK_STREAM, 0);
123+
sceNetConnect(sock, (struct sockaddr *)&server, sizeof(server));
124+
int flag = 1;
125+
sceNetSetsockopt(sock, IPPROTO_TCP, TCP_NODELAY, (char *)&flag, sizeof(int));
48126

127+
printfsocket("Connected!\n");
128+
129+
uint64_t* dump = mmap(NULL, 0x1000, PROT_READ | PROT_WRITE, MAP_ANONYMOUS | MAP_PRIVATE, -1, 0);
130+
131+
printfsocket("Starting kernel patch...\n");
132+
133+
int sRet = syscall(11,kpayload,td,dump);
134+
135+
printfsocket("Kernel patched!\n");
136+
49137
printfsocket("Starting PS4 Linux Loader\n");
50138

51139
usbthing();
52140

53141
printfsocket("Done!\n");
142+
54143
sceNetSocketClose(sock);
55144

56145
return 0;
146+
57147
}
58148

59149
void usbthing()
60150
{
61-
// Open bzImage file from USB
151+
152+
printfsocket("Open bzImage file from USB\n");
62153
FILE *fkernel = fopen("/mnt/usb0/bzImage", "r");
63154
fseek(fkernel, 0L, SEEK_END);
64155
int kernelsize = ftell(fkernel);
65156
fseek(fkernel, 0L, SEEK_SET);
66157

67-
// Open initramfs file from USB
158+
printfsocket("Open initramfs file from USB\n");
68159
FILE *finitramfs = fopen("/mnt/usb0/initramfs.cpio.gz", "r");
69160
fseek(finitramfs, 0L, SEEK_END);
70161
int initramfssize = ftell(finitramfs);
@@ -73,7 +164,7 @@ void usbthing()
73164
printfsocket("kernelsize = %d\n", kernelsize);
74165
printfsocket("initramfssize = %d\n", initramfssize);
75166

76-
// Sanity checks
167+
printfsocket("Checks if the files are here\n");
77168
if(kernelsize == 0 || initramfssize == 0) {
78169
printfsocket("no file error im dead");
79170
fclose(fkernel);
@@ -98,15 +189,16 @@ void usbthing()
98189
fclose(fkernel);
99190
fclose(finitramfs);
100191

101-
// Call sys_kexec
192+
printfsocket("Call sys_kexec (153 syscall)");
102193
syscall(153, kernel, kernelsize, initramfs, initramfssize, cmd_line);
103194

104195
free(kernel);
105196
free(initramfs);
106197

107-
// Reboot PS4
198+
printfsocket("Reboot PS4");
108199
int evf = syscall(540, "SceSysCoreReboot");
109200
syscall(546, evf, 0x4000, 0);
110201
syscall(541, evf);
111202
syscall(37, 1, 30);
203+
112204
}

0 commit comments

Comments
 (0)