zoukankan      html  css  js  c++  java
  • FileBuffer-ImageBuffer 模拟PE

    这节课的重点是:模拟PE加载过程,按照运行的要求给FileBuffer拉伸放到内存当中,从 FileBuffer 到 ImageBuffer 再到 运行Buffer。

    PE  加载  过程:

    1. 根据sizeofImage    分配空间
    2. 根据sizeofheader    copy头
    3. 按照节表, 根据VaSize,RawSize,SizeOfRawData     copy节

    一,介绍FileBuffer

    sizeofHeanders(位于可选PE头中) 它是 所有头+所有节表 按照 文件对齐以后的大小

    节表和节的关系:节表是节的目录。

    Misc  未初始化,没对齐的节 代表在内存中映射完的大小

    SizeOfRawData 对应的节里面的数据按照文件对齐后的大小

    PointerToRawData 文件的偏移 (在文件中离DOS头有多远)

    二,FileBuffer call到ImageBuffer中

    先call SizeOfHeaders ,然后call节的数据(节表已经交代了节的大小内容)

    ImageBuffer中的地址对应FileBuffer的地址:

    VirtualAddress 代表虚拟的偏移 也就是离DOS头的距离,如何确定在第几个节?

    ① 501234-50000=1234

    ②1234 > VirtualAddress    123456 < VirtualAddress+misc.VirtualSize

    ③1234-1000=234

    400+234=我们想要的地址

    附:

    RVA 相对偏移地址 例如1234就是RVA ,离开始头有多远!注!RVA不是VirtualAddress!!!

    FOA就是上面的 400+234 F是 File 文件 OA就是 offset 偏移

    主要就是要学会把FileBuffer拉伸成为ImageBuffer后 再写成运行Buffer,以后方便把自己的代码塞进去。

    例题、编写一个函数,能够将RVA的值转换成FOA.
    
    //函数声明
    
    //**************************************************************************
    
    //ReadPEFile:将文件读取到缓冲区
    
    //参数说明:
    
    //lpszFile 文件路径 //pFileBuffer 缓冲区指针
    
    //返回值说明:
    
    //读取失败返回0  否则返回实际读取的大小
    
    //******************************************************DWORD ReadPEFile(IN LPSTR lpszFile,OUT LPVOID* pFileBuffer); //******************************************************
    
    //CopyFileBufferToImageBuffer:将文件从FileBuffer复制到ImageBuffer
    
    //参数说明:
    
    //pFileBuffer  FileBuffer指针
    
    //pImageBuffer ImageBuffer指针
    
    //返回值说明: //读取失败返回0  否则返回复制的大小 //****************************************************** DWORD CopyFileBufferToImageBuffer(IN LPVOID pFileBuffer,OUT LPVOID* pImageBuffer); //******************************************************
    
    //CopyImageBufferToNewBuffer:将ImageBuffer中的数据复制到新的缓冲区
    
    //参数说明:
    
    //pImageBuffer ImageBuffer指针
    
    //pNewBuffer NewBuffer指针
    
    //返回值说明:
    
    //读取失败返回0  否则返回复制的大小
    
    //******************************************************DWORD CopyImageBufferToNewBuffer(IN LPVOID pImageBuffer,OUT LPVOID* pNewBuffer); //******************************************************
    
    //MemeryTOFile:将内存中的数据复制到文件
    
    //参数说明:
    
    //pMemBuffer 内存中数据的指针
    
    //size 要复制的大小
    
    //lpszFile 要存储的文件路径
    
    //返回值说明:
    
    //读取失败返回0  否则返回复制的大小
    
    //******************************************************BOOL MemeryTOFile(IN LPVOID pMemBuffer,IN size_t size,OUT LPSTR lpszFile); //******************************************************
    
    //RvaToFileOffset:将内存偏移转换为文件偏移
    
    //参数说明:
    
    //pFileBuffer FileBuffer指针
    
    //dwRva RVA的值
    
    //返回值说明:
    
    //返回转换后的FOA的值  如果失败返回0
    
    //****************************************************** DWORD RvaToFileOffset(IN LPVOID pFileBuffer,IN DWORD dwRva); 
  • 相关阅读:
    python基础学习8(浅拷贝与深拷贝)
    适配器模式(Adapter)
    NHibernate的调试技巧和Log4Net配置
    查看表字段的相关的系统信息
    Asp.net MVC 3 开发一个简单的企业网站系统
    ie8 自动设置 兼容性 代码
    同时安装vs2010和VS2012后IEnumerable<ModelClientValidationRule>编译错误
    各种合同样本
    使用远程桌面的朋友可能经常会遇到“超出最大允许连接数”的问题,
    弹出窗口全屏显示:window.showModalDialog与window.open全屏显示
  • 原文地址:https://www.cnblogs.com/tqing/p/10673029.html
Copyright © 2011-2022 走看看