前言
作者:
浪子花梦
,一个有趣的程序员 ~
此系列文章都是一些基础的文章,每篇文章都通过几个小例子快速的了解 Win32反汇编与OD的使用,在此作个笔记
如若对您有帮助,记得三连哟 ~
前文链接
Win32反汇编(一) 初步探索Win32反汇编 与 Ollydbg的简单使用
Win32反汇编(二)几种常见的指令反汇编详解:EAX、MOVSX与MOVZX、LEA、SUB、CMP与转移指令
文章目录
- JMP 与 goto
- 有符号:JL JNGE、JLE JNE(小于、小于等于)跳转指令
- 有符号:JG JNLE、JGE JNL(大于、大于等于)跳转指令
- 无符号:JA JNBE、JNB JAE JNC(大于、大于等于)跳转指令
- 无符号:JB JNAE JC、 JBE JNA(小于、小于等于)跳转指令
- 条件转移指令集合(有符号)
- 标志寄存器复习汇总
此文章涉及的指令比较多,多动手才能熟悉这些东西, ^ _ ^
不开玩笑了,直接开讲 . . .
JMP 与 goto
jmp 是无条件跳转指令,不会影响标志位
,对应着 C/C++ 中的 goto语句,我们来演示一下 jmp与goto的用法,观察如下的 cpp代码,上面使用 goto语句进行跳转,下面嵌入一行汇编指令,造成了死循环,他们的本身是一样,代码如下所示:
// jmp 演示
#include <cstdio>
int main() {
printf("start\n");
goto end;
printf("langzi\n");
printf("huameng\n");
end:
printf("end!!!\n");
// 循环打印
loopShow:
printf("while!\n");
__asm jmp loopShow
return 0;
}
使用 OD进行调试观察如下所示:
至于上面为什么有两个 jmp,这就是 od的翻译问题了,我们不作太多的了解,程序的执行流程如下所示:
第二个跳转到上面的指令,所以一直在跳转,实现了死循环,我们可以显示的改变指令的内容,如下所示:
使其跳转到跳转指令的下一条指令,暴力破解的原理 . . .
.
.
在上篇文章中我们学习了 je、jne指令,分别是==转移 和 != 转移,下面我们来学习一下 >、<、>=、<=,这些操作分为有符号的转移和无符号的转移 . . .
有符号:JL JNGE、JLE JNE(小于、小于等于)跳转指令
1)JL JNGE 小于跳转指令:
指令对应的翻译为:
JL:Jump if less
JNGE:Jump if not greater or equal
这两个指令的本质是一样的,OD一般会翻译成 JL,可以手动改变指令 . . .
cpp 程序代码如下所示:
#include <cstdio>
int main() {
int a = 0x11;
int b = 0x33;
// a < b 跳转
if (a >= b) {
printf("do a >= b\n");
}
printf("do a < b\n");
__asm {
mov eax, b
cmp a, eax
jl end // a < b 跳转
}
printf("a >= b!!!\n");
end:
printf("a < b!!!\n");
return 0;
}
上面是用CPP的 if语句,下面是嵌入汇编指令,它们演示的都是一个意思,只有当 a < b时才发生跳转,OD 调试动图如下所示:
标志位计算:SF=1
时跳转
.
2)JLE JNE 小于等于跳转指令:
这两个指令的意思是一样的,都表示着小于等于时跳转,使用方式与上面的小于跳转指令相似,代码如下所示:
#include <cstdio>
int main() {
int a = 0x11;
int b = 0x33;
if (a > b) {
printf("do a > b\n");
}
printf("do a <= b\n");
__asm {
mov eax, b
cmp a, eax
jle end // a <= b 跳转
}
printf("a > b!!!\n");
end:
printf("a <= b!!!\n");
return 0;
}
OD调试如下所示,发现指令已经由原来的 jl 变成了jle了:
标志位计算:SF=1 || SF != OF
时跳转 . . .
.
.
有符号:JG JNLE、JGE JNL(大于、大于等于)跳转指令
1)JG JNLE 大于跳转指令:
指令对应的翻译为:
JG:Jump if Greater
JNLE:Jump if not Less or Equal
这两个指令的本质是一样的,OD一般会翻译成 JG,可以手动改变指令 . . .
cpp 程序代码如下所示:
#include <cstdio>
int main() {
int a = 0x55;
int b = 0x33;
// a > b 跳转
if (a <= b) {
printf("do a <= b\n");
}
printf("do a > b\n");
__asm {
mov eax, b
cmp a, eax
jg end // a > b 跳转
}
printf("a <= b!!!\n");
end:
printf("a > b!!!\n");
return 0;
}
上面是用CPP的 if语句,下面是嵌入汇编指令,它们演示的都是一个意思,只有当 a < b时才发生跳转,OD 调试动图如下所示:
.
2)JGE JNL 大于等于跳转指令:
这两个指令的意思是一样的,都表示着大于等于时跳转,使用方式与上面的大于跳转指令相似,代码如下所示:
#include <cstdio>
int main() {
int a = 0x55;
int b = 0x33;
if (a < b) {
printf("do a < b\n");
}
printf("do a >= b\n");
__asm {
mov eax, b
cmp a, eax
jge end // a >= b 跳转
}
printf("a < b!!!\n");
end:
printf("a >= b!!!\n");
return 0;
}
OD调试如下所示,发现指令已经由原来的 jg 变成了jge了:
标志位计算:ZF = 0 && SF = 0F
. . .
.
.
无符号:JA JNBE、JNB JAE JNC(大于、大于等于)跳转指令
无符号转移指令和有符号转移指令的使用都是差不多的,只是指令不同而已,下面我们就介绍一下指令,然后快速的使用一下就行 . . .
1)JA JNBE 无符号大于转移指令:
JA:Jump Above(高于)
JNBE:Jump not Below(低于)
cpp 代码如下所示:
#include <cstdio>
int main() {
unsigned int a = 0x55;
unsigned int b = 0x33;
if (a <= b) {
printf("do a <= b\n");
}
printf("do a > b\n");
__asm {
mov eax, b
cmp a, eax
ja end // a > b 跳转
}
printf("a <= b!!!\n");
end:
printf("a > b!!!\n");
return 0;
}
OD 调试动图如下所示:
标志位计算:CF = 0 && ZF = 0
时跳转 . . .
.
2)JNB JAE JNC无符号大于等于转移指令:
JNB:Jump not Below(不低于)
JAE:Jump above equal(高于等于)
JNC:Jump not carry(没有进位时跳转 CF = 0)
cpp 代码如下所示:
#include <cstdio>
int main() {
unsigned int a = 0x33;
unsigned int b = 0x33;
if (a < b) {
printf("do a < b\n");
}
printf("do a >= b\n");
__asm {
mov eax, b
cmp a, eax
jnb end // a >= b 跳转
}
printf("a < b!!!\n");
end:
printf("a >= b!!!\n");
return 0;
}
这两个数是相同的,下面我们来试试OD调试一下:
.
.
无符号:JB JNAE JC、 JBE JNA(小于、小于等于)跳转指令
1)JB JNAE JC 无符号小于转移指令:
JB:Jump Below(低于)
JNAE:Jump not Above Equal(不高于等于)
JC:Jump Carry(进位时跳转)CF = 1
cpp 代码如下所示:
#include <cstdio>
int main() {
unsigned int a = 0x11;
unsigned int b = 0x33;
// a < b 跳转
if (a >= b) {
printf("do a >= b\n");
}
printf("do a < b\n");
__asm {
mov eax, b
cmp a, eax
jb end // a < b 跳转
}
printf("a >= b!!!\n");
end:
printf("a < b!!!\n");
return 0;
}
OD 调试动图如下所示:
.
2)JBE JNA无符号小于等于转移指令:
JBE:Jump Below Equal(低于等于)
JNA:Jump not above(不高于)
cpp 代码如下所示:
#include <cstdio>
int main() {
unsigned int a = 0x33;
unsigned int b = 0x33;
// a < b 跳转
if (a > b) {
printf("do a > b\n");
}
printf("do a <= b\n");
__asm {
mov eax, b
cmp a, eax
jbe end // a < b 跳转
}
printf("a > b!!!\n");
end:
printf("a <= b!!!\n");
return 0;
}
这两个数是相同的,下面我们来试试OD调试一下:
.
.
条件转移指令集合(有符号)
标志寄存器复习汇总
.
.