一、选择结构(if-else)
核心逻辑:
-
比较条件:用
CMP
指令 -
条件跳转:用
JE
(等于跳转)、JNE
(不等于跳转)、JG
(大于跳转)等 -
代码块分割:通过标签(如
label1:
)标记不同分支
示例1:简单 if 语句(x86汇编)
假设要实现以下C代码:
if (a > 10) {a = 5;
}
对应的汇编实现:
mov eax, [a] ; 将变量a的值加载到eax寄存器
cmp eax, 10 ; 比较 eax 和 10
jle end_if ; 如果 a <= 10,跳过if块
mov dword [a], 5 ; 如果 a > 10,执行 a = 5
end_if:
示例2:if-else 语句
C代码:
if (a > 10) {a = 5;
} else {a = 3;
}
汇编实现:
mov eax, [a]
cmp eax, 10
jle else_block ; 如果 a <= 10,跳转到else块
mov dword [a], 5 ; if块
jmp end_if ; 跳过else块
else_block:
mov dword [a], 3 ; else块
end_if:
二、循环结构(for/while)
核心逻辑:
-
初始化计数器:设置循环变量
-
循环条件检查:在循环开始处判断是否继续
-
循环体执行:循环内的操作
-
更新计数器:修改循环变量
-
跳转回检查:回到条件检查处
示例1:while 循环(计算1+2+...+100)
C代码:
int sum = 0;
int i = 1;
while (i <= 100) {sum += i;i++;
}
汇编实现(x86):
section .data
sum dd 0 ; 定义sum变量
i dd 1 ; 定义i变量section .text
loop_start:
mov eax, [i] ; 加载i的值到eax
cmp eax, 100 ; 比较i和100
jg loop_end ; 如果i > 100,跳出循环; 循环体:sum += i
mov ebx, [sum]
add ebx, eax ; sum = sum + i
mov [sum], ebx; i++
inc eax ; i = i + 1
mov [i], eaxjmp loop_start ; 跳回循环开始处loop_end:
示例2:for 循环(优化版)
C代码:
for (int i=0; i<10; i++) {sum += i;
}
汇编实现(x86):
mov ecx, 0 ; ecx作为计数器i(i=0)
mov eax, 0 ; eax保存sum(初始为0)for_loop:
cmp ecx, 10 ; 比较i和10
jge for_end ; 如果i >=10,跳出循环add eax, ecx ; sum += iinc ecx ; i++
jmp for_loop ; 继续循环for_end:
mov [sum], eax ; 保存结果
三、关键指令和技巧
四、对比不同架构(ARM示例)
示例:ARM中的if-else
ldr r0, [a] ; 加载a到r0
cmp r0, #10 ; 比较r0和10
ble else_block ; 如果 <=10 跳转到else; if块
mov r0, #5
str r0, [a] ; a = 5
b end_if ; 跳过elseelse_block:
mov r0, #3
str r0, [a] ; a = 3end_if:
五、调试技巧
-
单步执行:用GDB或调试器观察跳转路径
-
标志寄存器:理解
CMP
如何影响标志位(ZF=零标志,SF=符号标志) -
流程图辅助:手动画出跳转逻辑
六、总结
-
选择结构:依赖
CMP
+ 条件跳转指令(JE/JG/JL
) -
循环结构:本质是
CMP
+ 跳转的重复执行 -
核心思想:所有高级语言的控制流最终都会转换为 标签+跳转 的底层逻辑