16汇编完结Call变为函数以及指令的最后讲解

学了10天的16位汇编,这一讲就结束了,这里总结一下昨天的LOOP指令的缺陷,因为lOOP指令的缺陷,所以我们都改为下面的汇编代码使用了,自己去写,其中条件是你自己写的

请看汇编代码:

do while 的汇编代码WHILE:mov ax,axcmp ax, 10jl WHILE

while 的汇编代码WHILE:cmp ax, 10jge WHILE_ENDmov ax,axjmp WHILE
WHILE_END:

一丶Call指令(子程序)变为函数调用(重要,这个以后逆向会天天看到所以一定掌握)

首先我们明白一点,昨天我们写的只是一个单独的子程序(什么保存栈地址,开辟局部变量空间,....都没有写,只是单独的平栈),今天我们就写一个Call变为函数调用的例子,一步一步的看为什么这么做,对以后的逆向很有帮助

1.首先我们明白Call调用的几种方式

段内:   一个段中去调用,或者跳转

段间:   代码不在同一个段中,从一个段跳跃到另一个段

Call指令分为4中类型 (类似于JMP)

Call  label(标号) ;                                                       段内调用丶直接寻址

Call r16/m16 (16位寄存器,或者2字节内存)                段内调用丶间接选址

Call  far ptr label;                 段间调用丶直接寻址

Call  far ptr mem;                                                        段间调用丶间接寻址

昨天我们写的简单的子程序例子:

mov ax,1
push ax
mov bx,2
push bx
Call   标号
add sp,4....
标号:mov bp,sp   mov ax,[bp +2]   mov bx,[bp +4]   add ax,bxret

我们压入了两个参数,一个Ax,一个Bx,在Call的时候,会把下一行的地址压入到栈中,也就是 add sp,4的所在的地址

我们画一下栈

可以看出,这个就是当前的栈结构了, 我们执行代码的时候,首先 bp 和 sp是平等的了

现在 bp+2  能寻得bx, bp +4 能寻得 ax

然后ret  注意,ret只是把sp +2了,也就是弹栈弹出了返回地址,并且给IP了,现在IP就会跳转到下一条指令执行的位置

也就是(add sp,4)  现在要注意了,bx 和 ax 都还在栈中,我们没办法让栈恢复所以在外面用 add sp,4 让sp的位置(现在的位置+2了,已经在bx的位置了)变为栈底了

所以这个就是C语言的 C调用约定

如果我们想StdCall  (std 调用约定,标准的调用约定) 就要用retn 这个指令了,不能是ret了,

写成 retn  4  代表先把返回地址返回出去,然后再让sp +4 个字节,相当于在函数内部就平栈了,这样外部就不用写

add sp,4了,不用自己平栈了

2.由Call 变为函数一步一步来

现在基于上面的原理我们知道如何平衡一个栈了,但是你有没有发现,为什么我们一开始要把sp 给Bp

也就是让 BP和SP一样的位置

这个是有原因的

首先C语言调用函数的时候会进行几步操作

1.保存栈底

2.申请局部变量空间

3.保存环境

4.恢复环境

5.释放局部变量空间

6.恢复栈底

7.弹栈返回

好看上面的我们可能有点不明白,下面我把整体的栈图放出来

整体的栈是这样的,这里为什么要一开始把bp和sp相等,是有原因的,我们不妨这样想,如果我们申请局部变量空间的

时候,是不是参数的偏移也要改动,这样每次都要自己计算偏移,相当麻烦,所以只能这样,

我们以后找参数就  bp + xxx (因为bp一开始就在栈底的值这一栏)  这样就能寻找到参数,你开辟多大的局部变量看空间都和我没关系,所以以后我只需要 bp-xxx 就是找到的局部变量

现在看下汇编代码的模版吧

MY_ADD:  ;stdcall    push bpmov bp, sp    ;1. 保存栈底sub sp, 10    ;2. 申请局部变量空间这里随你便,申请的时候先抬栈,让sp高一点,但是不会影响bppush bx       ;3.保存环境 保存环境的意思就是外面的寄存器的值要保存一下,这样恢复寄存器的值mov word ptr [bp-4], 1        ;每次我只需要 bp -xxx 就知道寻找局部变量mov word ptr  [bp-2], 2mov ax, [bp+6]  ;参数1         ;每次我bp+ xxx 就知道我是找参数,所以不会冲突,打死参数的地址不会变add ax, [bp+8]  ;参数2;xxxxxxxpop bx          ;4. 恢复环境      弹栈的时候寄存器信息先回复mov sp, bp     ;5. 释放局部变量空间  而且恢复变量控件的时候也很容易,直接把bp当前的位置给sp即可,释放空间了pop bp        ;恢复以前的栈底的值retf         ;6. 返回   ,retf下面详细讲

在这里主要是掌握bp所在的位置即可,就能明白为什么这样写了,不信的话自己写个程序,看下反汇编,大体的就是这个套路,这里讲解的是为什么这样做,不是和市面的汇编视频一样,你看到 bp -xxx 就知道他在访问局部变量就行

其实这个是错误的,我们要知其然,并知其所以然

看下栈图,掌握bp所在的位置

只要掌握bp所在的位置即可,上面的代码即可明白

3.Call指令的retf段间转移

这个我们首先要明白,在Call的时候会把Call下边一条指令的地址保存到栈中,出栈的时候要给IP,让其更改跳转,

跳转到Call下一条指令执行的位置的地方

但是现在我们是段间Call,也就是不在一个段中,这个时候栈不光会保存返回地址,还会保存当前CS段寄存器的地址

这样返回的时候  CS:IP返回,但是现在有一个问题,就是我们自己根本就平不了栈,我们把IP拿出来了,给IP,CS段寄存器根本没办法改,这样我们必须同时修改CS:IP的值才能回到以前的地方,但是现在没办法了,因为你改IP回跳,改CS会跳,必须同时改,弄不了,所以弄一个retf的指令去帮我们去做

注意retf 你也需要平栈,比如我们压入了两个参数,就要 retf 4, retf会默认把栈顶4个字节的数据取出来分别给 ip和CS段寄存器,但是剩下4个字节都是我们的参数,比如自己去释放,让SP的加4到栈底才可以

二丶中断指令

1.什么是中断指令

中断,是有一种改变程序执行顺序的方法

中断具有很多的中断类型

中断的指令有3条

  1.INT i8(i8代表一个八位的立即数)

  2.IRET  IRET 和Call差不对,Call的ret返回的时候会把栈顶的元素弹出两个字节,这两个字节是返回地址,所以可以回到正确的地方执行指令,但是IRET明显比ret保存的东西多,其中ret我们可以手工的pop和jmp去执行,IRET也可以自己去做,但是你要完整的模拟才可以,一般还是调用IRET即可

  3.INTO

2.中断指令的自我理解

  其实中断指令就是调用硬件提供的API(也称为系统调用)我们前边用过很多次了

比如显示一个字符串

  

mov ah,09h
int 21h

其中参数是09,int 21h代表执行,还有很多

介绍下指令

  INT I8:  中断的调用指令: 产生I8号中断,就是调用int代表我要调用了,其中指令是什么使我们给的,是一个八位立即数比如 09

  IRET:  中断的返回指令,理解为返回,可以进行下一条指令的执行

  INTO:  不常用,不讲解.

3.21h中断,到底是个啥玩意

我们每次都调用21h什么的,但是不知道他是个啥玩意

他是DOS提供给用户的,用于调用系统功能的中断(简单理解就是DOS提供的API,让用户调用),他有近百个功能让公户选择使用.包括设备管理,目录管理,和文件管理

ROM-BIOS(主板的BIOS)也是这种形式,这就是为什么程序一开机显示器就会显示字符,别忘了这个时候系统还没有启动,还没有操作系统一说

看下图:

  

现在操作系统也还是这样调用,操作系统的API很多,底层就依赖于这256个中断,只不过操作系统可能处理的方式更多,比如根据AH的值,调用一个函数指针,也就是一个函数的地址,这个函数地址里面又有很多封装,慢慢的操作系统API就越来越多.这些都是我们不关心的

具体的中断,可以看下第一课所有的课堂资料中的指令字典,寻找一下中断号自己去调用

比如判断按键的汇编例子

getkey:    mov ah,01h    ;功能号:ah←01hint 21h              ;功能调用cmp al,’Y’           ;处理出口参数alje yeskey            ;是“Y”cmp al,’N’je nokey             ;是“N”jne getkey...
yeskey:    ...
nokey:    ...

三丶最后的指令详解

LOCK指令  封锁总线,不让总线接受指令

这个常用与多线程的时候操作,多线程的操作中的同步对象的 自加锁就是这样实现的

比如:

  

lock add word ptr[bp],3

当我们吧3给内存的时候,其余的程序也可能再往这里写数据,所以同步一下,这样就完成这一条指令,才可以进行下一条指令的操作

自减锁就是 把add 变为sub,交换锁就是 把指令变为 xchg lock只能同时处理一条指令,这是为防止我们把系统总线都锁死,这样操作系统就会崩溃,信息到不了,不过这个不是我们关心的

解锁是CPU自己解锁的,没有解锁指令

HLT 暂停指令

这个就比较简单的,我们电脑都有休眠功能,就是用的这个指令,让CPU功耗降低,不执行,以前是无限循环NOP指令

但是NOP也是一个指令也会有功耗,所以现在改为HLT指令了,执行了这个指令HLT不进行任何操作,当我们发送了一条指令过去之后,就会脱离暂停状态

就好比电脑挂机了,屏幕黑了,就是进入HLT了,我们点击鼠标或者键盘,发送了一条指令,接着就唤醒了

交权指令

ESC 6位立即数,reg/mem

我们都知道,以前算浮点数的时候都是CPU一个去做的,现在有了浮点处理器,也就是协处理器,专门算浮点的一个CPU

我们的CPU计算浮点数的时候,要把权力交给浮点处理器,这时候就称为交权,在这个时候CPU要等待浮点处理器返回的结果,期间一直等待

FADD FDIV 是浮点计算指令,就是我们计算指令前面加F就会计算浮点数了

浮点数有7个寄存器

ST -> st7 按照标号来的

浮点处理器的st不能和通用寄存器一样去使用,它是吧ST寄存器压入栈中,让前两个栈中的数据相加返回的

关于浮点处理,后面再说,这个不是16为汇编中使用的

WAIT 等待指令

这个就简单了,CPU交权后,就使用这个指令去等待浮点处理器返回结果

总结:

  16位汇编在我的博客上都精简了,但是你想搞明白就要多花点时间,细细品味汇编的内容,掌握汇编

过几天开始32位汇编的讲解,如果觉得好,请评论一下,关注一下,加个粉丝.支持一下,谢谢

对于Call变为函数的哪里,一定要掌握,不懂的可以去看下C语言的栈内存结构,或者看下它的汇编代码,一定搞明白

这个以后逆向的时候天天看.

学习资料: 链接:http://pan.baidu.com/s/1nuPNUFf 密码:x44c

转载于:https://www.cnblogs.com/iBinary/p/7492517.html

16汇编第十讲完结Call变为函数以及指令的最后讲解相关推荐

  1. 小甲鱼python第二十讲(内嵌函数和闭包)

    内嵌函数 def fun1():print("fun1正在被调用...")def fun2():print("fun2正在被调用..")fun2()#在fun1 ...

  2. c语言函数重用,C语言第10讲--程序重用之函数(修改2).ppt

    C语言第10讲--程序重用之函数(修改2) 主讲老师:刘志强 第十讲 程序重用之函数 数学函数及其调用 C语言提供了一些可以用于计算各种不同数学函数的库函数,通过调用它们可进行相应的计算. 例: 要使 ...

  3. c语言将两个16位变为一个32位,16位汇编第六讲汇编指令详解第第三讲(示例代码)...

    16位汇编第六讲汇编指令详解第第三讲 1.十进制调整指令 1. 十进制数调整指令对二进制运算的结果进行十进制调整,以得到十进制的运算结果 2.分成压缩BCD码和非压缩BCD码调整 简而言之: 以前的时 ...

  4. 逆向知识第十讲,循环在汇编中的表现形式,以及代码还原

    逆向知识第十讲,循环在汇编中的表现形式,以及代码还原 一丶do While在汇编中的表现形式 1.1高级代码: #include "stdafx.h"int main(int ar ...

  5. 32位汇编第六讲,OllyDbg逆向植物大战僵尸,快速定位阳光基址

    32位汇编第六讲,OllyDbg逆向植物大战僵尸,快速定位阳光基址 一丶基址,随机基址的理解 首先,全局变量的地址,我们都知道是固定的,是在PE文件中有保存的 但是高版本有了随机基址,那么要怎么解决这 ...

  6. 树莓派ARM汇编语言编程十讲(第1讲)

    内容简介 树莓派单板机(Raspberry Pi Single Computer)是一种极了不起的产品,用户可以以非常低的成本获得一个Linux环境并带GPIO硬件扩展的迷你计算机系统.新一代树莓派4 ...

  7. 计算机基础知识第十讲,计算机文化基础(第十讲)学习笔记

    计算机文化基础(第十讲)学习笔记 采样和量化PictureElement Pixel(像素)(链接: 采样的实质就是要用多少点(这个点我们叫像素)来描述一张图像,比如,一幅420x570的图像,就表示 ...

  8. 打包文档_苏教版小学数学16年级全十二册教案Word文档打包下载

    扫码查看下载 全部资源 部编小学语文1-6年级课程资料汇总苏教版小学数学1-6年级教学资料汇编苏教版小学数学1-6年级电子课本汇编苏教版小学数学1-6年级期末试题卷汇编▼ 1 年级 苏教版一年级数学上 ...

  9. 32位汇编第七讲,混合编程,内联汇编

    32位汇编第七讲,混合编程 博客园IBinary原创 QQ:2510908331  博客连接:http://www.cnblogs.com/iBinary/ 转载请注明出处,谢谢 混合编程的概念,有时 ...

  10. 16位汇编语言第二讲系统调用原理,以及各个寄存器详解

    16位汇编语言第二讲系统调用原理,以及各个寄存器详解 昨天已将简单的写了一下汇编代码,并且执行了第一个显示到屏幕的helloworld 问题? helloworld怎么显示出来了. 一丶显卡,显存的概 ...

最新文章

  1. 1051 Pop Sequence(两种双指针思路)
  2. Python学习之字符串
  3. 数据结构与算法分析-第一章Java类(04)
  4. webgl 着色器_如何使用AI,AR和WebGL着色器来帮助视障人士
  5. SpringBoot2 整合MinIO中间件,实现文件便捷管理
  6. Polynomial(HDU-6668)
  7. java异常处理语句是,java 异常处理
  8. java se基础复习3
  9. vs 2013远程调试
  10. 微信中打开网址添加请在在浏览器中打开提示遮罩
  11. java 跳转url_URL跳转的几种方式
  12. 安卓通过链接打开淘宝客户端
  13. 利用bat批处理做启动mongodb脚本
  14. eating的中文意思_Eating是什么意思中文
  15. 常用二极管,三极管参数
  16. 图像超分辨率重构实战
  17. 十二星座匹配对象_十二星座爱情配对,看着合适各自谈恋爱的星座
  18. 零基础搭建ASP.NET网站---(2)网站建设
  19. 仅需28步、1.2秒!自学成才的人工智能轻轻松松破解了魔方
  20. centos中如何创建一个txt文件

热门文章

  1. oracle 表复制 long,关于oracle的数据库的数据Long和Number的转化字段
  2. 分三种情况C语言编程,吴进的256basic.h阅读笔记,请问scanline_copy子程序为什么要分三种情况考虑:(1)d...
  3. 力扣题目系列:1. 两数之和
  4. kendoGrid动态列的实现-高级查询结果展示优化过程
  5. ZABBIX 监控 JBOSS 7.1.1
  6. csu 1196 - 去爬山
  7. “System.Web.Extensions, Version=1.0.61025.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35”
  8. blog推荐 - Sources of Insight
  9. 交换局域网(链路层+以太网+交换机)
  10. AHK生成随机但不重复的数字