《汇编语言》第四章第一个程序



第四章:第一个程序

📌 主要内容

本章通过一个简单的汇编示例,详细讲解从源程序编写可执行文件运行的全流程,包括编辑、汇编、链接、加载与跟踪调试,每一步都深入剖析其原理与命令使用,帮助理解汇编程序的执行机制与工具链协作。


🧠 笔记重点

4.1 一个源程序从写出到执行的过程
  • 流程总览

    1. 编写源程序(.asm 文件),包含段定义、指令与伪指令;
    2. 汇编(Assembler,MASM):.asm.obj(目标文件);
    3. 链接(Linker):.obj.exe(可执行文件);
    4. 加载(Loader):DOS 将 .exe 装入内存,设置段寄存器;
    5. 执行:CPU 从 CS:IP 开始逐条取指并运行。
  • 关键概念

    • 段与偏移:所有地址均由“段地址 ×16 + 偏移”计算;
    • 目标文件:包含机器码和重定位信息;
    • 可执行文件格式:含 MZ 头,DOS 加载器解析后再执行。
  • 图示

    源程序.asm ──汇编──► .obj ──链接──► .exe ──加载──► 内存中程序 ──执行──► 运行结果
    

4.2 源程序
  • 结构要素

    • ASSUME:段寄存器与段名对应;
    • data segment … data ends:数据段定义;
    • code segment … code ends:代码段定义;
    • end <入口标号>:指定程序起始位置。
  • 示例

    assume cs:code, ds:data
    
    data segment
        msg db 'Hello, ASM!', 0dh,0ah,'$'
    data ends
    
    code segment
    start:
        ; 初始化 DS
        mov ax, data
        mov ds, ax
        ; 调用 DOS 中断打印字符串
        mov dx, offset msg
        mov ah, 9
        int 21h
        ; 退出程序
        mov ah, 4Ch
        int 21h
    code ends
    end start
    

4.3 编辑源程序
  • 编辑工具
    • 推荐使用 VSCode、Notepad++ 或 DEBUG 自带编辑模式;
  • 保存注意
    • 文件扩展名应为 .asm
    • 文本编码须为 ANSI/ASCII,避免 UTF-8 BOM;
  • DEBUG 编辑示例
    debug
    - n Hello.asm         ; 指定文件名
    - a 100               ; 在地址 0100h 开始输入
        mov ax, 4C00h
        int 21h
        <空行结束>
    - rcx
    

4.4 编译
  • MASM 使用
    masm Hello.asm;      ; 生成 Hello.obj
    
  • 过程详解
    1. 解析伪指令,分配段和符号表;
    2. 翻译每条汇编指令为机器码;
    3. 生成重定位表与符号信息,输出 .obj
  • 常见错误
    • 段未定义或 ASSUME 错误;
    • 语法错误;
    • 标号重复。

4.5 连接
  • Link 命令
    link Hello.obj;      ; 生成 Hello.exe
    
  • 细节
    1. 解析 .obj 中所有段和重定位信息;
    2. 合并同名段(如多个 code segment);
    3. 计算最终每段在内存的起始地址;
    4. 修正所有重定位引用,输出 .exe
  • 检查
    • 确保 .obj 与库文件路径正确;
    • 使用 dumpbin /headers Hello.exe 查看 MZ 头信息。

4.6 以简化的方式进行编译和连接
  • 可执行文件直接生成

    • 在masm后面加上被编译的源程序文件的路径、文件名,在命令行的结尾加分号:
      masm Hello.asm;
      link Hello.obj;
      
  • 优缺点

    • 简单快捷,适合演示和小程序;
    • 不支持多段与复杂重定位。

4.7 1.exe 的执行
  • DOS 加载流程
    1. 读取 MZ 头,验证签名“MZ”;
    2. 按头部指定的段布局分配内存;
    3. 将程序体复制到分配区;
    4. 设置 CS:IP 指向程序入口;
    5. 转交控制权给程序入口。
  • 寄存器初始化
    • CS 指向代码段,IP=入口偏移;
    • DS=CS
    • 栈段 SS:SP 由 DOS 按默认或头部值设置。

4.8 谁将可执行文件中的程序装载进入内存并使它运行?

-image-20250506170414609


4.9 程序执行过程的跟踪
  • 使用 DEBUG
    1. debug Hello.exe 加载程序;
    2. u 100 反汇编查看机器码;
    3. r 查看所有寄存器初始状态;
    4. t 单步执行,观察 CS:IPDSAX/BX…的变化;
    5. d ds:offset msg 查看数据段中字符串内容。
    6. p 执行int 21命令
  • 观察要点
    • 段寄存器是否按预期初始化;
    • 每条指令执行后寄存器和内存的变化;
    • 中断调用后程序流向和返回值。

🧪 实验3:编写、汇编、链接并跟踪第一个程序

  1. 编辑 Hello.asm,写入上文示例;
  2. 汇编masm Hello.asm; 输出 Hello.obj
  3. 链接link Hello.obj; 输出 Hello.exe
  4. 执行debug Hello.exe,使用 urtd 等命令逐步跟踪;
  5. 验证:在屏幕上看到 “Hello, ASM!” 并正常返回。

🔍 拓展理解

  • 深入研究 MZ 文件格式,有助于理解现代 PE 格式演变;
  • 掌握汇编工具链(MASM、LINK、DEBUG)使用,是高效调试与性能优化的基础;
  • 通过逐条单步跟踪,可以窥见 CPU 指令执行与中断调用的底层细节。

📖 下一篇预告 | 第五章 [BX]和loop指令

第五章:[BX] 和 LOOP 指令


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值