实验1 —— 用机器指令和汇编指令编程(1)

运行环境

在 Windows 环境下 DOSBox 不支持高 DPI 显示,在高分辨率显示器上窗口会变得很小,不易阅读。

不巧的是,我的电脑分辨率较高,出现了上述情况。如果你也出现了上述情况,可以参考我的解决方案。

我的运行环境是在虚拟机中运行的 DOS,为了与 MS-DOS 兼容且避免与微软的版权冲突,我选择了FreeDOS,一个开源的 DOS 项目。虚拟机是 Windows Pro 自带的的 Hyper-V,当然也可以选择其他虚拟机,具体配置方法见 How to install FreeDOS 1.2

以下为安装之后正常运行的截图:

FreeDOS_1@3x.png

debug 常用命令

输入 debug 命令并回车,出现 - 提示符,如下图所示:

FreeDOS_2@3x.png

本部分只展示部分命令,全部命令可在出现 - 提示符后输入 ?(问号)。

r 命令

输入 r (register) 命令并回车,显示所有寄存中的数据,如下图所示:

FreeDOS_3@3x.png

输入 r ax 命令并回车,可修改 ax 寄存器的值,如下图所示:

FreeDOS_4@3x.png

ax 寄存器的值修改为 1111 并显示,如下图所示:

FreeDOS_5@3x.png

可见 ax 寄存器的值已被修改为了 1111

下图展示了将 cs 寄存器和 ip 寄存器的值分别修改为 ff00200:

FreeDOS_6@3x.png

d 命令

输入 d 1000:0 (dump) 命令并回车,如下图所示:

FreeDOS_7@3x.png

可见默认显示从地址 1000:00001000:0070 内存中的数据,共 128 (0x80) 位。

下图展示了从地址 1000:0009 开始及其以后内存中存放的的 128 位数据:

FreeDOS_8@3x.png

当只输入 d 命令时,默认的地址是 cs:ip,如下图所示:

FreeDOS_9@3x.png

当然也可以指定末地址,输入 d 1000:0 9,显示从 1000:01000:9 内存中的数据 (注:第2个参数是偏移地址),如下图所示:

FreeDOS_10@3x.png

如果想查看单个内存单元中的数据可以使用 d cs:ip ip 形式的命令,如下图所示,展示了内存单元 1000:00fff:100100:f000 中的数据:

FreeDOS_11@3x.png

e 命令

输入 e 1000:0 0 1 2 3 4 5 6 7 8 9 并回车,使用 d 1000:0 f 查看内存可知 e 命令改变了从 1000:0 开始的内存中的值,如下图所示:

FreeDOS_12@3x.png

如果在使用 e 命令时只传入地址参数(以 1000:10 举例),系统会默认开始逐个修改内存单元,输入值并回车可以编辑下一个。如果想跳过并修改下一个,可以按 <space> (空格)。结束时直接按 <enter> (回车) 即可。如下图所示:

FreeDOS_13@3x.png

为了方便输入,我们可以直接向内存单元输入特定的值,输入的值需加 '' (引号),如下图所示:

FreeDOS_14@3x.png

可见'a' 'b' 'c' 在内存中以它们的 ASCII 码的形式存储。

也可以输入字符串,输入的值需加 " " (双引号),如下图所示:

FreeDOS_15@3x.png

可见字符串被顺序存储在了内存单元中。

u 命令

我们可以用 u 1000:0(unassemble) 对从 1000:0 开始的内存单元中的数据进行反汇编,如下图所示:

FreeDOS_16@3x.png

t 命令

在执行 t (trace) 命令之前,我们要先确定从哪里开始执行,如果是从默认的地址开始执行,就无需修改 csip 的值;如果从特定的地址开始执行,在之前需要用 r 命令分别修改 csip 的值。如下图可见 t 命令是单步执行的,执行后 ip 的值也发生了改变:

FreeDOS_17@3x.png

下图为继续执行的结果:

FreeDOS_18@3x.png

a 命令

我们知道,就算是程序员也不可能每天只敲一推 16 进制数字,为了方便我们可以使用 a (assemble) 命令向指定的地址输入汇编指令,如下图所示:

FreeDOS_19@3x.png

如果不带地址参数会使用默认地址,如下图所示:

FreeDOS_20@3x.png

实验

本实验为《汇编语言》(王爽著,第3版)第45页 实验任务

  1. 写入程序可以直接输入机器码,如下图所示:

    FreeDOS_21@3x.png

    FreeDOS_22@3x.png

    FreeDOS_23@3x.png

    当然,也可以输入汇编指令,如下图所示:

    FreeDOS_24@3x.png

    FreeDOS_25@3x.png

    FreeDOS_26@3x.png

    FreeDOS_27@3x.png

  2. 在计算 \(2^{8}\) 时,首先将 1 送入寄存器,之后将寄存器中的值迭代 9 次即可 (从 \(2^{0}\) ~ \(2^{8}\)),共 10 次,具体如下图所示:

    FreeDOS_43@3x.png

    FreeDOS_44@3x.png

  3. 首先将物理地址转化成段地址:偏移地址的形式,再使用 d 命令,发现从 FFF0:00F6FFF0:00FD 是一段日期,如下图所示:

    FreeDOS_32@3x.png

    尝试将日期更改为 10/21/2018,发现不可行,表明系统对这块内存有保护 (这块内存是 ROM),如下图所示:

    FreeDOS_33@3x.png

  4. 输入以下代码,发现画面中出现以下图像,表明这块内存负责显示图像,如下图所示:

    FreeDOS_34@3x.png

    尝试改变地址后的参数,显示如下图所示:

    FreeDOS_35@3x.png

    FreeDOS_36@3x.png

    说明这些参数与图像的颜色和形状有关。

    改变地址,显示如下图所示:

    FreeDOS_37@3x.png

    FreeDOS_38@3x.png

    FreeDOS_39@3x.png

    FreeDOS_40@3x.png

    表明地址与显示位置有关。

本文均为个人观点,如有错误,请批评指正。

猜你喜欢

转载自www.cnblogs.com/jordangong/p/9845254.html