1. 作业_6
1.1 主函数反汇编分析

1.2 映射C语言代码

2. Level_1
2.1 func_401019()_反汇编分析

2.2 映射C语言代码

2.3 文章反汇编重点:
核心 1:读取三个输入数字(变量定位,关键!)
c
00401191 |. 68 4C604200 push offset <%d,%d,%d>
00401196 |. E8 E50B0000 call _scanf ; 输入3个整数
; 三个核心变量存储位置(必记)
ebp-0x4 = 数字1
ebp-0x8 = 数字2
ebp-0xC = 数字3
核心 2:整个函数的灵魂 → 调用交换 / 排序函数(最重要!)
c
004011BC |. E8 4EFEFFFF call exchange ; 对三个数字进行交换排序(核心逻辑)
核心 3:输出排序后的结果
c
004011D0 |. 68 3C604200 push offset \n%d,%d,%d\n
004011D5 |. E8 260B0000 call _printf ; 打印处理后的三个数
【极简复习笔记】
c
函数功能:输入3个整数 → 调用exchange交换排序 → 输出结果
核心变量:ebp-0x4、ebp-0x8、ebp-0xC 存储三个输入数字
核心指令:call <exchange> (唯一业务核心)
2.4 func_40100F()_子函数_反汇编分析

2.5 映射C语言代码

2.6 本章反汇编重点
核心 1:函数参数(最关键!指针类型)
c
mov eax,dword ptr ss:[ebp+0x8] ; 参数1:int* a(第一个数的地址)
mov ecx,dword ptr ss:[ebp+0xC] ; 参数2:int* b(第二个数的地址)
mov edx,dword ptr ss:[ebp+0x10] ; 参数3:int* c(第三个数的地址)
✅ 笔记:接收 3 个int 指针(三个数字的内存地址)
核心 2:三组「比较 + 交换」逻辑(函数灵魂)
第 1 组:比较 a 和 b,小则交换
c
cmp edx,dword ptr ds:[ecx] ; 比较 *a 和 *b
jge short 004010F4 ; 大于等于 → 不交换
call swap ; 小于 → 交换a、b
第 2 组:比较 a 和 c,小则交换
c
cmp ecx,dword ptr ds:[eax] ; 比较 *a 和 *c
jge short 00401110 ; 大于等于 → 不交换
call swap ; 小于 → 交换a、c
第 3 组:比较 b 和 c,小则交换
c
cmp eax,dword ptr ds:[edx] ; 比较 *b 和 *c
jge short 0040112C ; 大于等于 → 不交换
call swap ; 小于 → 交换b、c
核心 3:核心指令总结
cmp(比较值)+ jge(条件跳过)+ call swap(执行交换)
【极简复习笔记】
c
函数名:exchange(三数排序函数)
参数:3个int指针(ebp+8/0xC/0x10)
核心逻辑:
1. 两两比较3个数字
2. 前 < 后 → 调用swap交换
3. 最终实现三数升序排列
灵魂指令:cmp + jge + call swap
一句话总结重点
整段汇编只有「三次两两比较 + 调用 swap 交换」是核心。
2.7 func_401005()_子函数_反汇编分析

2.8 映射C语言代码

3. Level_2
3.1 func_401014()_反汇编分析

3.2 映射C语言代码

3.3 本章重点
核心 1:经典 for 循环 + 数组输入(逆向必考核心)
c
; 循环计数器 i = ebp-0x4
mov dword ptr ss:[ebp-0x4],0x0 ; i=0
cmp dword ptr ss:[ebp-0x4],0xA ; i < 10
jge 结束循环
; 数组寻址:ebp-0x2C = 数组首地址,int arr[10]
lea edx,dword ptr ss:[ebp+ecx*4-0x2C] ; arr[i] 寻址
call _scanf ; 循环输入10个数字
jmp 循环自增
✅ 考点:x86 循环结构、数组下标寻址(ecx*4 int 型数组)
核心 2:整个程序的灵魂 → 调用核心函数
c
push edx ; 数组首地址
push 0xA ; 数组长度10
call max_min ; 【核心】计算数组的最大值、最小值
👉 这一行是业务核心:输入数组 → 计算最大 / 最小值
核心 3:结果输出(变量定位)
c
; 存储结果的变量
ebp-0x30 = 最大值
ebp-0x34 = 最小值
; 打印结果
call _printf
极简复习笔记
c
函数功能:输入10个整数 → 调用max_min求最大最小值 → 打印结果
核心考点:
1. for循环实现 (i=0; i<10; i++)
2. int数组寻址:[ebp+索引*4+偏移]
3. 核心业务:call max_min (数组处理函数)
关键变量:
ebp-0x4 = 循环变量i
ebp-0x2C = 数组首地址
ebp-0x30/0x34 = 最大/最小值
一句话总结
- 这段汇编最有价值的重点就是「循环输入数组」的汇编特征,这是 PC 逆向面试、实战中最常考的基础核心,剩下的全是辅助逻辑!
3.4 func_40100A()_子函数_反汇编分析

3.5 映射C语言代码

3.6 本章重点
函数参数(栈传参,必考!)
c
ebp+0x8 = 数组首地址(int*)
ebp+0xC = 数组长度(10)
ebp+0x10 = 最大值存储指针(输出)
ebp+0x14 = 最小值存储指针(输出)
初始化逻辑(核心起点)
取数组第一个元素,同时赋值给 最大值、最小值变量。
核心循环(数组指针遍历,PC 逆向必考)
c
; 用指针遍历数组,而非下标
mov ecx, dword ptr ss:[ebp-0x4] ; 遍历指针
add ecx, 4 ; 指针+4(int类型)
cmp 指针, 数组尾地址 ; 遍历结束判断
✅ 特征:优化后的数组遍历 → 指针移动,无显式循环变量i。
核心业务逻辑(函数灵魂)
c
; 当前元素 > 最大值 → 更新最大值
cmp ecx, dword ptr ds:[eax]
jle short
mov dword ptr ds:[edx], ecx
; 当前元素 < 最小值 → 更新最小值
cmp ecx, dword ptr ds:[eax]
jge short
mov dword ptr ds:[edx], ecx
极简复习笔记
c
函数名:max_min(求数组最大/最小值)
参数:数组指针、长度、最大值指针、最小值指针
核心逻辑:
1. 用数组首元素初始化最大/最小值
2. 指针遍历整个数组
3. 逐个比较,动态更新最大、最小值
逆向考点:指针遍历数组、栈传参、最值算法
一句话总结
- 这段汇编最核心的价值就是「指针遍历数组 + 动态更新最值」,是 PC 逆向、面试中最经典的基础算法汇编特征!
4. Level_3
4.1 func_40102D()_反汇编分析

4.2 映射C语言代码

4.3 本章重点
核心数据结构(最关键:字符串指针数组)
c
; 定义 char* name[5] = {"赵XX","钱XX","孙XX","李XX","周XX"}
ebp-0x20 ~ ebp-0x10 = 5个字符串指针
ebp-0x4 = 数组长度 5
✅ 逆向考点:字符指针数组 定义与寻址(区别于普通 int 数组)
数组寻址特征(必考汇编写法)
c
mov ecx,dword ptr ss:[ebp+eax*4-0x20] ; 指针数组遍历:arr[i]
✅ 特征:基址 + 索引*4 + 偏移(指针占 4 字节)
核心业务流程(函数灵魂)
c
1. 初始化5个姓氏的指针数组
2. for循环 → 打印【排序前】数组
3. call sort ; 【核心】调用排序函数(对字符串指针排序)
4. for循环 → 打印【排序后】数组
极简复习笔记
c
函数名:fun2
功能:字符串指针数组排序演示
核心:
1. 数据:char* arr[5](5个姓氏指针)
2. 流程:打印前 → call sort排序 → 打印后
3. 考点:指针数组寻址、for循环打印、字符串数组处理
灵魂指令:call sort
一句话总结
- 这段汇编核心价值是 「字符串指针数组的定义 + 遍历 + 调用排序」,是 PC 逆向中数组类型进阶(指针数组) 的经典案例!
4.4 func_40101E()_子函数_反汇编分析

4.5 映射C语言代码

4.6 本章重点
函数参数(栈传参,指针数组核心)
c
ebp+0x8 = char* 数组首地址(字符串指针数组)
ebp+0xC = 数组长度(5)
核心结构:双重 for 循环(冒泡排序经典特征)
c
外层循环:ebp-0x8 = i
内层循环:ebp-0xC = j
✅ 逆向特征:双层循环 + 条件判断 + 数据交换 = 冒泡排序
核心比较逻辑(字符串专用)
c
call _strcmp ; 【关键】库函数比较两个字符串大小
test eax,eax
jle short ; 不满足条件则不交换
✅ 区别于数值排序:依赖 strcmp 进行字符串字典序比较
核心操作:字符串指针交换
c
; 交换数组中两个字符串指针(冒泡排序核心)
mov dword ptr ds:[eax+edx*4],ecx
✅ 考点:只交换指针,不交换字符串本身(高效排序)
极简复习笔记
c
函数名:sort(字符串指针数组排序)
算法:冒泡排序(升序)
核心:
1. 双层for循环实现冒泡
2. call strcmp 比较字符串
3. 交换数组中的指针地址
适用:char* 数组字典序排序
一句话总结
- 这段汇编是PC 逆向最经典的「字符串指针数组 + 冒泡排序」,双层循环 + strcmp + 指针交换是核心特征,也是面试高频考点!
5. Level_4
5.1 func_401028()_反汇编

5.2 映射C语言代码

5.3 本章重点
核心数据
初始化int 数组 1,2,3,4,5,6,7,8,9,0,长度 10,存储位置:ebp-0x2C
核心流程(函数灵魂)
c
1. for循环 → 打印【原始数组】
2. call inverte ; 【核心】调用数组反转函数
3. for循环 → 打印【反转后数组】
经典特征
c
两段完全一致的 for 循环,负责数组遍历打印,汇编写法:[ebp+索引*4+偏移] 数组寻址
极简笔记
c
函数名:fun3
功能:int数组反转演示
核心:
1. 初始化10个元素的int数组
2. 打印原数组 → call inverte反转 → 打印新数组
3. 考点:数组遍历寻址、函数调用
灵魂指令:call inverte
一句话总结
- 这段汇编无复杂算法,核心是 「数组初始化 + 遍历打印 + 调用反转函数」,是逆向中数组基础操作的经典模板!
5.4 func_401032()_子函数_反汇编分析

5.5 映射C语言代码

5.6 本章重点
【绝对点睛核心】逐行精准拆解
c
004016D8 mov eax, [ebp+0xC] ; eax = 数组长度 len
004016DB sub eax, 1 ; eax = len - 1 ✅【关键第一步】
004016DE cdq ; 符号位扩展(编译器优化配套指令)
004016DF sub eax, edx ; 消除符号影响
004016E1 sar eax, 1 ; 算术右移1位 = 除以2
004016E3 mov [ebp-0x14], eax ; 最终结果:(len - 1) / 2
核心真相:
- 这是0 起始数组的双指针反转中点计算公式,是这段汇编的灵魂,也是你精准抓住的核心!
数组反转只需要遍历一半元素,这是核心特征
c
mov eax,dword ptr ss:[ebp-0xC] ; [ebp - 0xC] 左指针
cmp eax,dword ptr ss:[ebp-0x4] ; [ebp - 0x4] 中间指针
ja short 逆向6.0040173D ; [ebp - 0xC] > [ebp - 0x4] 则跳转
极简笔记
c
函数名:inverte(数组反转)
核心:
1. 双指针(头+尾)向中间靠拢
2. 计算数组中点,遍历前半段
3. 交换左右指针元素
经典特征:指针±4移动 + 元素交换
一句话总结
- 这段汇编是PC 逆向最经典的「双指针数组反转」,核心就是头尾指针移动 + 元素交换,比记循环变量 i/j 简洁 10 倍!
本章完~