没有合适的资源?快使用搜索试试~ 我知道了~
x86软件逆向分析入门
需积分: 5 0 下载量 37 浏览量
2023-10-10
04:22:52
上传
评论
收藏 81KB DOCX 举报
温馨提示
试读
27页
x86软件逆向分析入门
资源推荐
资源详情
资源评论
X86/X64 软件逆向分析入门
第1课、 课前准备&工具安装与配置
1) 课程回顾:《PC 微信探秘》
2) Visual Studio 2019 开发套件:http://www.microsoft.com
3) x64dbg:动态调试工具:https://x64dbg.com
4) IDA:静态分析工具
a) https://www.hex-rays.com/
b) https://github.com/AngelKitty/IDA7.0
5) 课程源代码:https://github.com/zmrbak/ReverseAnalysis
6) 如何下载课程源代码
第2课、 软件中的逆向分析与非官方功能扩展(1)
1) PPT 来源于本人在成都理工大学的一次公开讲座
2) 《PC 微信探秘》
第3课、 软件中的逆向分析与非官方功能扩展(2)
第4课、 CPU 指令集&最简单的函数
1) 指令码
2) 机器码
3) 汇编语言
4) CPU 寄存器
5) 机器码和编程语言的区别
6) 指令集架构
7) 一个最简单的函数,了解一下返回值的处理。
第5课、 剖析 C 语言中的经典程序-Hello World
1) 把 C 代码转换成汇编语言代码
2) 汇编语言的两种主流语体:Intel、AT&T
3) X64 寄存器、X86 寄存器、16 位寄存器
7
6
5
4
3
2
1
0
X64
RAX
X86
EAX
16 位
AX
AH
AL
RCX、RDX、R8、R9
第6课、 函数的序言、函数的尾声
1) 函数序言
01172400 55 push ebp
01172401 8B EC mov ebp,esp /rsp
01172403 81 EC C0 00 00 00 sub esp,0C0h (为局部变量申请存储空间)
2) 函数尾声
0117243A 8B E5 mov esp,ebp
0117243C 5D pop ebp
0117243D C3 ret
3) 递归调用的问题
int f()
{
f();
}
第7课、 逆向生长的堆栈
1) 栈是 CPU 寄存器中的某个指针指向的一片内存区域。
2) PUSH,减法操作
3) POP,加法操作
4) 栈顶:ESP/RSP
5) 栈底:EBP
6) 为什么栈会逆向生长
低地址 高地址
堆的起点
-----> <-----
栈的起点
第8课、 栈的用途
1) 保存函数结束时的返回地址
010B1025
33C0
xor eax,eax
00AFF838 010B1025 返回到 l008a.010B1025 自 l008a.010B1000
00AFF83C 00AFF884
00AFF83C 00AFF884
00AFF840 010B1269 返回到 l008a.010B1269 自 l008a.010B1010
2) 传递参数
3) 存储局部变量
$-10 00000001 //第 1 个局部变变量
$-C 00000002 //第 2 个局部变变量
$-8 00000000 //第 3 个局部变变量
$-4 008FFD4C //EBP
$ ==> 00251055 //返回地址:到 l008a.00251055 自 l008a.00251000
$+4 00000001 //arg1
$+8 00000002 //arg2
4) Windows 的 SEH 结构化异常处理
5) 缓冲区溢出保护
ESP: 00F5FD08-00F5FAB0
EBP: 00F5FD14
第9课、 栈的噪音
CALL 等价于:PUSH+JMP
RET 等价于:POP+JMP
堆栈的溢出
Release 版本的优化
堆栈的噪音:噪音数据、脏数据
00DAFB24 01381058 返回到 l009.01381058 自 l009.01381000
00DAFB28 00DAFB70
第10课、 函数与参数
第11课、 整数型数据的指针传递(1)
指针:描述某个内存地址的数据
X86 指针:32 位,4 个字节
X64 指针:64 位,8 个字节
Void*
多个返回值的传递处理,scanf()
编译器在类型检查阶段——检查指针数据类型
局部变量:函数内部可以访问,函数外部应该访问不到。
本地变量:ebp+偏移
外部传来的参数:ebp+偏移
X86 栈结构
$-C 00000001 //第 1 个局部变变量
$-8 00000002 //第 2 个局部变变量
$-4 00000000 //第 3 个局部变变量
$==> 008FFD4C //EBP
$+4 00251055 //返回地址:到 l008a.00251055 自 l008a.00251000
$+8 00000001 //arg1
$+C 00000002 //arg2
lea : load effective address
lea eax, DWORD PTR _x$[ebp]
lea eax, [ebp+_x]
lea eax, [ebp-4]
lea eax, [local.1]
第12课、 整数型数据的指针传递(2)
第13课、 整数型数据的指针传递(3)
局部变量 VS 全局变量
全局变量
未初始化
已初始化
第14课、 整数型数据的指针传递(4)
函数返回值
cmpeax, 1
jne SHORT $LN2@main
jne: Jump Not Equal
jmp SHORT $LN3@main
cmpeax, 1
jne SHORT $LN2@main
cmp->jcc: Jump condition code
cmp:本质是减法操作
1-1=0;ZF 置 1
JNE:ZF
JNZ:
SUB—CMP
HACK
补丁
注意:
无论是 x86 还是 x64,函数的返回值都放在 eax 中
EAX 的值不等于 RAX
Int 是 32 位,无论在 x86 还是 x64 都是
64 位寄存器,以 R 开头
32 位寄存器,以 E 开头
第15课、 函数如何获取参数?
调用方:calller
被调用方:callee
X64
sub rsp, 40
Shadow Space:阴影空间
1、 可以避免浪费寄存器资源
2、 便于调试器在程序中断时找到函数参数。
第16课、 如何接收函数的返回值?
1、 int 型函数的返回值
2、 float 型函数的返回值
3、 void 型函数的返回值
4、 函数返回值不被使用的情况
5、 结构体型函数的返回值
X86:
EAX:返回调用结果
Byte、char:EAX,低 8 位->AL
Float:FPU->ST0
exit(main_result);
int const main_result = invoke_main();
static int __cdecl invoke_main()
return main(__argc, __argv, _get_initial_narrow_environment());
fld1 // FLD 类似于 PUSH 指令
fstp dword ptr [a] // FSTP 类似于 POP 指令
cvtss2sd XMM,XMM/m32
把源存储器低 32 位 1 个单精度浮点数变成 1 个双精度浮点数,结果送入目的寄存器的低 64 位,高 64 位不变.
cvtss2sd xmm0,dword ptr [a]
//在俩个 xmm 指令之间或者内存位置和 xmm 寄存器之间复制浮点数
movsd mmword ptr [esp],xmm0
剩余26页未读,继续阅读
资源评论
f4ck3sdn
- 粉丝: 279
- 资源: 17
上传资源 快速赚钱
- 我的内容管理 展开
- 我的资源 快来上传第一个资源
- 我的收益 登录查看自己的收益
- 我的积分 登录查看自己的积分
- 我的C币 登录后查看C币余额
- 我的收藏
- 我的下载
- 下载帮助
安全验证
文档复制为VIP权益,开通VIP直接复制
信息提交成功