常见汇编指令整理

2023-11-18

本文会整理在逆向中常见的指令汇总

目录

汇编符号

汇编指令的组成

mov

movzx 

lea

xchg

加法指令

减法指令

带进位加法

带进位减法

自增自减

乘法运算

除法运算

and

or

xor

not

shl

shr

逻辑指令

字符串操作

STOS

REP

movss指令

eax 与 [eax] 区别

test指令

 cmp指令

jle指令

jnz指令

cmovnz指令


汇编符号

在查询资料时,往往会遇见一些符号,需要对常见的符号先做一个了解

  • reg:通用寄存器    reg8 reg16 reg32
  • sreg:段寄存器
  • imm:立即数 数字 123456     imm8 imm16 imm32
  • mem:内存     mem8 mem16 mem32

汇编指令的组成

汇编指令是由 操作码和操作数 组成的

操作数的类型:

  • 立即数
  • 寄存器
  • 内存

mov

mov指令的作用就是将源操作数赋值给目的操作数。

mov 目的操作数,源操作数

注意事项

  1. 不能把一个大的值传给一个小的容器
  2. mov指令不允许这样操纵  mov mem,mem  传送数据少的化,可以借助寄存器中转
mov eax,ebx

movzx 

将源操作数(寄存器或内存位置)的内容复制到目标操作数(寄存器),并按照零扩展方式将值扩展到 16 或 32 位。转换后的值的大小取决于操作数大小属性。

mov eax,0xFFFF

低4为被FFFF覆盖,其它位置被0覆盖

lea

将源操作数的地址传送到目标操作数的寄存器中

lea eax,dword ptr ds:[0x00BCFB64]

dword ptr 表示偏移量为4个字节,表示以0x00BCFB64向下偏移4个字节

xchg

执行操作:将目标操作数与源操作数的内容进行交换

xchg dword ptr ds:[0x00BCFB64], eax

EAX寄存器的值和0x00BCFB64并偏移4个字节的值进行交换。

加法指令

add指令有两个操作数,add指令会把两个操作数相加,然后把结果存放在第一个操作数里面。操作数 的类型和mov指令一样

add eax,ecx

标志寄存器CF,x64dbg的解释

  • 有符号数计算,进位,借位进行设置
  • 无符号运算发生溢出

设置EAX为0xFF,令 al 加上 EAX.测试CF标志位变化

执行后,EAX被置为0

add eax,0x1

查看标志寄存器变化

  • ZF表示最近一次计算的结果为0,就设置为1
  • CF表示发生了进位借位,置为1
  • PF表示最近计算结果最低字节位,1的个数为偶数设置为1

减法指令

用第一个操作数减去第二个操作数,结果存放到第一个操作数里面

sub eax,ecx

带进位加法

带进位的加法,和add加法的区别在于会在原来的基础上,加上进位标志。格式和操作数跟add一样。

mov dl,0;
mov al,0xFF;
add al,1;
adc dl,0;

结果

dl=0+0=0+1(进位标志)
dl=00000001

带进位减法

在原来的减法基础上,再减去进位标志

mov edx,7;
mov eax,1;
sub eax,2;
sbb edx,0;

结果

edx=7;
eax=1;
eax=1-2=0xFFFFFFFF = -1
edx=7-0-1=6

自增自减

他们都只有一个操作数

inc eax
dec eax

乘法运算

无符号乘法

mov eax,0x12345;
mov ebx,0x10;
mul ebx;

乘法里面有两个东西,一个是乘数,一个是被乘数。 mul只有一个操作数,ebx是乘数,另外一个隐藏的操作数叫被乘数,这个操作数是隐藏的,也就是这 条指令执行的时候

mul ebx;=ebx=ebx*eax;

有符号乘法

mov eax.0x12345;
mov ebx,0x100000;
imul ebx,eax;

OF标志位发生了变化

此时注意OF位,会被置为1,这是因为计算结果 1234500000 ,已经超过了有符号位存储的范围了

补充:

imul ebx,eax,ecx;

第二个操作数和第三个操作数相乘,结果放到第一个操作数里面

除法运算

无符号 div 有符号 idiv

mov eax,5
mov ebx,3
div ebx

div指令的除法,商放在eax里,余数放在edx里。 有符号除法几乎与无符号除法几乎完全一样。

and

将操作数1与操作数2进行按位与运算,结果存储到操作数1中

and eax,1 如果eax=0xFFFF,则结果eax=0001

or

将操作数1与操作数2进行按位或运算,结果存储到操作数1中

or eax,1 如果eax=0xFFF0,则结果eax=0xFFF1

xor

将操作数1与操作数2进行按位异或运算,结果存储到操作数1中

xor eax,0x1F 如果eax=0xFFF0,则结果eax=0xFFEF

not

将目标操作数执行按位取反结果存储到目标操作数的位置

not eax; 如果eax=0xFF00,则结果eax=00FF

shl

左移,等于*2

shr

右移,等于/2

逻辑指令

逻辑运算都不会得到运算结果,仅仅设置标志寄存器中的相应标志位,通常都是配合跳转指令,实现汇 编程序中的选择或者循环结构

cmp用于比较两个数的大小;test指令最常用的功能就是测试某一个寄存器的值是不是0

指令:cmp

操作数个数:2

操作数1:reg

操作数2:reg/mem/imm

指令结构:CMP 源操作数,源操作数

执行操作:用操作数1减去操作数2,并根据结果设置EFLAGS寄存器中的状态标志

例子:

        cmp eax,1; 如果eax=0,比较之后由于最高位为1.因此符号位SF为1;

        cmp eax,0; 如果eax=0,比较之后由于结果为零,因此零标志位ZF为1

指令:test

操作数个数:2

操作数1:reg

操作数2:reg/mem/imm

指令结构:TEST 源操作数,源操作数

执行操作:将操作数1和操作数2进行按位与运算,并根据结果设置SF ZF PF状态标志,然后丢弃结果

例子:

        test eax,eax;

        jz XXX

        如果eax为零,设置ZF零标志为1,jz跳转。

字符串操作

要把内存中的一块区域复制从一个地方复制到另外一个地方。这种 操作我们称为串操作指令。

串操作指令用到的寄存器都是EDI和ESI,不能使用其他寄存器。ESI存储的是源地址,EDI存储的是目标 地址。

MOVS BYTE PTR ES:[EDI],BYTE PTR DS:[ESI];------------------>简写:MOVSB
MOVS WORD PTR ES:[EDI],WORD PTR DS:[ESI];------------------>简写:MOVSW
MOVS DWORD PTR ES:[EDI],DWORD PTR DS:[ESI];----------------->简写:MOVSD

以C语言为例,EDI就相当于是dest,ESI就相当于是src,size,BYTE/WERD/DWORD就相当于是size

strcpy(dest,src,size);
  • MOVSB 一次复制一个字节
  • MOVSW 一次复制两个字节
  • MOVSD 一次复制四个字节
     
MOVS BYTE PTR ES:[EDI],BYTE PTR DS:[ESI]

movsb

当这条指令执行完成之后,从源地址复制了一个字节到目标地址;并且ESI和EDI的指针自动增加了1, 所以这种用来复制内存的方式是非常方便的。

如果想一次复制4个字节,可以用下面的指令

MOVS DWORD PTR ES:[EDI],DWORD PTR DS:[ESI];

关于DF标志位

  • 方向标志位,如果DF标志位为0,那么使用movs指令时,ESI和EDI的地址都会增加。
  • 相反,如果DF标志位为1,那么ESI和EDI的地址都会相减,MOVSB会减1,MOVSW会减2,MOVSD会 减4.

测试DF为0时

从esi开始向后4个字节复制给edi,并且esi,edi都加4

测试DF为1时

从esi开始向后4个字节复制给edi,并且esi,edi都减4

EDI,ESI都是指向内存空间的一个地址

STOS

将AL/AX/EAX的值存储到EDI里。

和MOVS指令对比,STOS少了一个源寄存器,这个源寄存器EAX是默认省略的。

执行完成之后,EDI的值也会加或者减,加或者减取决于DF标志位。加多少取决于复制的操作数大小。

STOS BYTE PTR ES:[EDI]----->简写为STOSB

STOS WORD PTR ES:[EDI]----->简写为STOSW

STOS DWORD PTR ES:[EDI]---->简写为STOSD

此时DF标志位为1,所以地址减1,然后EAX的值复制了一个字节,也就是44。复制44的原因是因为小 端存储。

REP

按ECX寄存器中指定的次数重复执行字符串指令

MOV ECX,0x10
REP MOVSD
REP STOSD

上面这些指令会让MOVSD和STOSD执行16次。这三条指令结合起来,就可以实现字符串拷贝的操作

movss指令

用于将单精度浮点数(32 位)从源操作数移动到目标操作数

如果目标操作数是一个寄存器,那么该寄存器的低 32 位将被赋值。

在给浮点数赋值时,往往会这样操作

movss   xmm0, ds:dword_417BE0
movss   [ebp+var_C], xmm0

xmm0 是一个 128 位的 XMM 寄存器,ds 是一个段寄存器,指示要访问的内存段,dword_417BE0 是一个表示内存地址的符号引用,它指向存储单精度浮点数的位置,由417BE0h - 417BE4h这段内存空间(由低向高)取这段空间的值,这是小段存储,低位存地位,高位存高位

小数往往存储在内存某一位置,通过xmm0寄存器给到函数局部变量的位置

eax 与 [eax] 区别

eax,就是往这个寄存器中写东西

[eax]:把eax存储的值视为地址,往这个地址写东西

test指令

"test" 指令是一种按位逻辑运算指令,其操作数是两个寄存器或内存单元的数据。两个操作数进行逐位逻辑与运算,并根据运算结果更新标志寄存器中的相应标志位,而不修改操作数的值;

对标志寄存器的影响:

  • 零标志位(ZF):如果运算结果为零,则 ZF 置位(ZF = 1);否则复位(ZF = 0)。

  • 符号标志位(SF):根据运算结果的最高位来设置 SF 的值。如果最高位为 1,则 SF 置位(SF = 1);否则复位(SF = 0)。

  • 奇偶标志位(PF):根据运算结果中包含的二进制 1 的个数来设置 PF 的值。如果运算结果中包含偶数个 1,则 PF 置位(PF = 1);否则复位(PF = 0)。

 cmp指令

"cmp" (Compare)指令是 x86 汇编语言中的比较指令,用于比较两个操作数的大小关系,并根据比较结果更新标志寄存器中的相应标志位。

cmp operand1, operand2

其中,operand1operand2 是待比较的操作数。

cmp 指令执行时,会进行以下步骤:

  1. 将 operand1 的值与 operand2 的值进行比较。
  2. 根据比较结果设置相应的标志位,包括零标志位(ZF)、进位标志位(CF)、符号标志位(SF)等。

常见的比较指令结果和对应的标志位设置如下:

  • 如果 operand1 等于 operand2,则 ZF 被置为 1;否则,ZF 被置为 0。
  • 如果 operand1 小于 operand2,则 SF 被置为 1;否则,SF 被置为 0。
  • 如果无符号整数的减法导致产生了借位(即 operand1 小于 operand2),则 CF 被置为 1;否则,CF 被置为 0。

需要注意的是,cmp 指令只进行比较操作,不会修改操作数的值。它主要用于在条件分支或循环中进行条件判断,根据比较结果来确定程序的执行路径。

jle指令

"jle" 是 x86 汇编语言中的跳转指令,它根据标志寄存器中的 SF、ZF 和 OF 标志位的组合进行条件跳转。

"jle" 的含义是 "Jump if Less Than or Equal",即如果小于等于关系成立,则进行跳转。

具体的跳转条件如下:

  • 当 SF = 1 (负数) 且 ZF = 0 (不为零) 时,进行跳转。
  • 当 SF = 0 (非负数) 且 ZF = 1 (为零) 时,进行跳转。
  • 当 OF = 1 (溢出) 时,进行跳转。

jnz指令

"jnz" 是 x86 汇编语言中的条件跳转指令,它根据标志寄存器中的零标志位 (ZF) 进行跳转判断。

"jnz" 的含义是 "Jump if Not Zero",即如果零标志位为 0,则进行跳转。

具体的跳转条件如下:

  • 当 ZF = 0 (不为零) 时,进行跳转。
  • 当 ZF = 1 (为零) 时,不进行跳转,继续执行下一条指令。

cmovnz指令

"cmovnz" 的含义是 "Conditional Move if Not Zero",即如果零标志位为非零值,则执行移动操作。

"cmovnz" 是 x86 汇编语言中的条件移动指令,它根据标志寄存器中的零标志位 (ZF) 进行条件判断,并将数据从一个操作数移动到另一个操作数。

该指令将检查 ZF 标志位的值。如果 ZF = 0,则将 source 中的数据移动到 destination 中;如果 ZF = 1,则不进行移动,保持 destination 不变。

"cmovnz" 用于根据零标志位的状态来选择性地将数据从一个位置移动到另一个位置。它常用于简化逻辑或避免条件分支的情况。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

常见汇编指令整理 的相关文章

  • 从 Invoke 方法获取 RETURN

    我正在尝试从另一个线程上的列表框项目中读取值 我尝试创建一种新方法来运行调用命令 我可以设法将命令发送到列表框 例如通过调用方法添加 但我似乎无法得到响应 我似乎无法获取该项目的值 我尝试了几种方法 一旦我将它从空变为字符串 事情就开始变得
  • .pdbs 会减慢发布应用程序的速度吗?

    如果 dll 中包含 pdb 程序调试 文件 则行号将出现在引发的任何异常的堆栈跟踪中 这会影响应用程序的性能吗 这个问题与发布与调试 即优化 无关 这是关于拥有 pdb 文件的性能影响 每次抛出异常时都会读取 pdb 文件吗 加载程序集时
  • C# Outlook 从收件人获取 CompanyName 属性

    我目前正在使用 C 编写 Outlook 2010 AddIn 我想要的是从我从 AppointmentItem 中提取的 Recipient 对象中获取 CompanyName 属性 因此 有了 AppointmentItem 的收件人
  • 在 Mac OS X 上安装 libxml2 时出现问题

    我正在尝试在我的 Mac 操作系统 10 6 4 上安装 libxml2 我实际上正在尝试在 Python 中运行 Scrapy 脚本 这需要我安装 Twisted Zope 现在还需要安装 libxml2 我已经下载了最新版本 2 7 7
  • MSMQ接收和删除

    是否有任何选项可以在读取消息后将其从 MSMQ 中删除 比如 接收 删除可以作为原子操作运行吗 听起来您想查看下一条消息 然后在处理完成后接收它 Message message Queue Peek Queue ReceiveById me
  • 如何查明 .exe 是否正在 C++ 中运行?

    给定进程名称 例如 程序 exe C 标准库没有这样的支持 您需要一个操作系统 API 来执行此操作 如果这是 Windows 那么您将使用 CreateToolhelp32Snapshot 然后使用 Process32First 和 Pr
  • DataGridView 列中的数字文本框

    我有一个DataGridView 我想要它的第一列或任何所需的列 其中有textboxes在其中 成为NUMERIC ONLY 我目前正在使用这段代码 private void dataGridViewItems EditingContro
  • Nhibernate:连接表并从其他表获取单列

    我有以下表格 create table Users Id uniqueidentifier primary key InfoId uniqueidentifier not null unique Password nvarchar 255
  • 关闭整数的最右边设置位

    我只需要关闭最右边的设置位即可 我的方法是找到最右边位的位置 然后离开该位 我编写这段代码是为了这样做 int POS int n int p 0 while n if n 2 0 p else break n n 2 return p i
  • “没有合适的默认构造函数可用”——为什么会调用默认构造函数?

    我已经查看了与此相关的其他一些问题 但我不明白为什么在我的情况下甚至应该调用默认构造函数 我可以只提供一个默认构造函数 但我想了解它为什么这样做以及它会产生什么影响 error C2512 CubeGeometry no appropria
  • 如何在 EF Core 2.1 中定义外键关系

    我的 DAL 使用 EF Core 2 1 这就是我的模型的样子 一名用户只能拥有一种角色 Role entity kind of master public class Role public int RoleId get set pub
  • 在 C++ 代码 gdb 中回溯指针

    我在运行 C 应用程序时遇到段错误 在 gdb 中 它显示我的一个指针位置已损坏 但我在应用程序期间创建了 10 万个这样的对象指针 我怎样才能看到导致崩溃的一个 我可以在 bt 命令中执行任何操作来查看该指针的生命周期吗 谢谢 鲁奇 据我
  • 在 mvc4 中创建通用 mvc 视图

    我以前也提过类似的问题 没有得到答案 如何创建一个通用的 mvc4 视图 该视图可以显示传递给它的模型列表或单个模型 模型可以是个人 组织或团体 无论传递给它的是什么 如果您正在寻找类似的东西 model MyViewModel
  • WPF DataGrid - 在每行末尾添加按钮

    我想在数据网格的每一行的末尾添加一个按钮 我找到了以下 xaml 但它将按钮添加到开头 有人知道如何在所有数据绑定列之后添加它吗 这会将按钮添加到开头而不是末尾
  • 使用 Unity 在 C# 中发送 http 请求

    如何使用 Unity 在 C 中发送 HTTP GET 和 POST 请求 我想要的是 在post请求中发送json数据 我使用Unity序列化器 所以不需要 新的 我只想在发布数据中传递一个字符串并且能够 将 ContentType 设置
  • 用数组或向量实现多维数组

    我想使用单个数组或向量实现多维数组 可以像通常的多维数组一样访问它 例如 a 1 2 3 我陷入困境的是如何实施 操作员 如果数组的维数为 1 则 a 1 应该返回位于索引 1 处的元素 但是如果维数大于一怎么办 对于嵌套向量 例如 3 维
  • 将日期时间显示为 MM/dd/yyyy HH:mm 格式 C#

    在数据库中 日期时间以 MM dd yyyy HH mm ss 格式存储 但是 我想以 MM dd yyyy HH mm 格式显示日期时间 我通过使用 String Format 进行了尝试 txtCampaignStartDate Tex
  • 当 Verb="runas" 时设置 ProcessStartInfo.EnvironmentVariables

    我正在开发一个 C 应用程序 我需要创建变量并将其传递给新进程 我正在使用ProcessStartInfo EnvironmentVariables 新进程必须提升运行 因此我使用 Verb runas var startInfo new
  • 解释这段代码的工作原理;子进程如何返回值以及在哪里返回值?

    我不明白子进程如何返回该值以及返回给谁 输出为 6 7 问题来源 http www cs utexas edu mwalfish classes s11 cs372h hw sol1 html http www cs utexas edu
  • 如何在 Razor 编辑视图中显示选中的单选按钮 Asp net core mvc

    尽管 Razor 视图中的 Asp 网络核心代码 model List

随机推荐

  • Flutter依赖注入

    依赖注入 依赖注入 Dependency Injection 简称DI 是一种软件设计模式 它的主要目的是将对象之间的依赖关系解耦 使得代码更加可维护 可测试 可扩展 使得代码更易于维护和测试 在Flutter中 DI可以帮助我们管理应用程
  • 设置 Oracle 监听器密码(LISTENER) .

    设置 Oracle 监听器密码 LISTENER 监听器也有安全 Sure 在缺省的情况下 任意用户不需要使用任何密码即通过lsnrctl 工具对Oracle Listener进行操作或关闭 从 而造成任意新的会话都将无法建立连接 在Ora
  • C51流水灯 running water lamp

    include
  • 百度智能云 × 火星人丨厨电智能化,从动“手”到动“口”

    家电智能化时代已至 厨电智能化怎甘落后 火星人厨具股份有限公司 简称 火星人 是一家致力改善人们厨房环境 解决厨房油烟危害的高科技公司 2010年成立以来 火星人集成灶凭借核心技术 目前已在全国发展专卖店达一千七百多家 销售额每年快速增长
  • 区块链技术与应用环境部署day-02

    区块链技术与应用环境部署 关于作者 作者介绍 博客主页 作者主页 简介 云计算领域优质创作者 在校期间参与众多计算机相关的省赛 国赛 斩获系列荣誉 考取华为资深工程师 红帽工程师等系列认证 关注我 简历模板 学习资料 文档下载 技术支持 都
  • python sorted函数详解2023.9.11

    sorted函数详解 1 输入和输出 2 key传入函数 1 输入和输出 help sorted Help on built in function sorted in module builtins sorted iterable key
  • VisualBrush画刷

    VisualBrush派生于TileBrush TileBrush可以用来重复填充目标区域 若要使用图像进行绘制 请使用 ImageBrush 若要通过绘图绘制 请使用 DrawingBrush 若要通过 Visual 进行绘制 请使用 V
  • va_list的原理及用法

    va list原理及用法 分类 编程2010 10 20 11 22 1426人阅读 评论 1 收藏 举报 list编译器平台语言x86编程 VA LIST 是在C语言中解决变参问题的一组宏 变参问题是指参数的个数不定 可以是传入一个参数也
  • 如何设置无需fn直接按F1~F10(HP Pavilion Notebook )

    在Windows10下F1 F12都有特定的功能 必须按Fn F1才可以输出F1功能 给我们游戏玩家带来一定的困扰 网上说Fn esc就可以 实际上win10的多数的都不可以实现这功能 电脑概览 电脑型号 HP HP Pavilion No
  • C#Excel文件加密实现,支持xlsx、docx、pptx(C#/NET/Asp.Net)

    C Excel文件加密实现 支持xlsx docx pptx C Net Asp Net 读在最前面 1 Excel文件加密实现 本文以 Microsoft Office 2007 为案例进行说明 2 Microsoft Office 20
  • 离散型制造业如何做生产质量管控和智能追溯?

    离散型制造业做生产质量管控和智能追溯应该做到完善的质量追踪体系和生产过程中的防错防呆来保证质量 首先质量管理应该建立完善的质量跟踪体系 建立产品的全生命周期的管理 从原材料的采购 入库 批次到生产 装配 完工 销售等一个环节都不能漏掉 比如
  • 前后端交互的两种方式

    方式一 表单提交 表单 form 表单用于收集用户输入信息 并将数据提交给服务器 是一种常见的与服务端数据交互的一种方式 1 action 指定表单的提交地址 2 method 指定表单的提交方式 get post 默认get 3 inpu
  • webshell与防范

    1 WebShell的概念和危害性 WebShell就是以asp php jsp或者cgi等网页文件形式存在的 种命令执行环境 也可以称为 种网页后门 黑客在入侵网站后 通常会将WebShell后门文件与网站服务器WEB目录下正常的网页文件
  • python语法基础学习-有感而发

    基于本次的python学习 我想我大致了解清楚了python内的部分基础模块 总体而言python语法简洁移动 容易上手 值得进一步学习 为之后的AI方向打下一定基础
  • [Python]调用pytdx的代码示例

    安装pytdx pip install pytdx 简单示范 from pytdx hq import TdxHq API api TdxHq API 数据获取接口一般返回list结构 with api connect 119 147 21
  • vue常用面试题(三)

    1 计算属性computed是一个对象的时候 他有哪些选项 有get和set俩个选项 2 computed和methods有什么区别 计算属性具有缓存机制 methods中的方法每使用一次方法就会被调用一次 不管里面的数据是否发生变化 而使
  • 电机系统标幺值基准值的选取

    电机系统标幺化的好处 对于不同功率 电压值的设备标幺值在一定范围内 具有可比性 而测量值则随之变化 定点DSP控制 可有效防止数据溢出 各个基值的选取方式如下 转载于 https www cnblogs com derek32 p 3855
  • React入门小册(六) 状态提升与状态共享

    React 状态提升指的是将多个组件所共享的状态提升到它们的公共父组件中 以便于修改和同步这些数据的变化 一般而言 状态提升对于多个组件的功能需求相似 并且存在一定的层次结构时 是非常有用的 在实际应用开发中 我们经常会遇到需要将数据传递给
  • 问卷数据怎么处理、分析?

    调查问卷分析是一门很系统很成熟的科学 无论是基于何种目的的调查 学术 市场调研 产品调研 用户调研 还是哪种方式发放的问卷 纸质问卷 电子问卷 面对回收的庞杂的问卷 最重要的事情就是如何处理 得出我想想要的结论呢 1 准备工作 在发放问卷前
  • 常见汇编指令整理

    本文会整理在逆向中常见的指令汇总 目录 汇编符号 汇编指令的组成 mov movzx lea xchg 加法指令 减法指令 带进位加法 带进位减法 自增自减 乘法运算 除法运算 and or xor not shl shr 逻辑指令 字符串