[Intel汇编-NASM]程序的加载以及硬盘访问

本文介绍了用户程序的结构,包括NASM中段的定义和属性,强调了应用程序头部在加载过程中的作用。通过手写加载器模拟操作系统功能,实现程序的加载和执行。用户程序部分展示如何处理字符串输出和控制字符,加载器部分涉及了重定位表和程序在内存中的定位。最终,通过在虚拟硬盘上运行验证加载器的正确性。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

1. 用户程序的结构:

    1) 一般源程序都以段的形式进行组织,这样可以使逻辑更加清晰,在NASM中使用section关键字定义一个段,形式是:section 段名

    2) 程序可以用段名来引用段,但是NASM编译器并不关心段的具体用途,或者说是根本不知道段的用途(代码段还是数据段等),同时NASM对段的数量也没有任何限制,如果代码中没有定一段则整个程序自成一段;

    3) 定义段的同时可以定义段的一些属性,比如可以使用关键字align来定义段的对其方式,比如:section code align=16,这样就表示该段的其实地址是以16字节对齐的,即段的起始位置必须是16的整数倍;

!注意:该属性只影响段的起始位置的对其但不影响段的末尾对齐方式,事实上NASM也无法判断一个段的末尾,只有当遇到一个新的段的定义的时候才能知道前一个段结束了;

    4) 段的起始位置:就是该段中第一行指令的地址(指令可以是普通指令也当然可以是数据定义指令db、dw等等;

    5) 和加载程序之间的约定——应用程序头部Header:

        i. 在有操作系统的环境下编译完一个程序之后编译器会隐式地、默认地添加一个应用程序头部(位置处于程序的起始位置处);

        ii. 头部包含着加载器该如何加载该程序的一些信息,或者说是加载器和程序之间的某些约定或规范,而加载器通过这些信息将程序正确地加载进内存中;

        iii. 在有操作系统的环境下,应用程序头部和加载器都是操作系统负责的,但是在这里我们模拟一下这个操作系统的工作,即手写完成加载器和程序头部来模拟操作系统的这两个功能;


2. 用户程序和加载器的简单实现:

用户程序:默认程序已经正确加载到了内存的空闲位置,并且从定义的标号start处该是执行程序,作用是将两个数据段中的字符串打印到屏幕上,并且处理回车和换行两个控制符

!注意用户程序头部的定义,里面包含了程序大小、程序开始执行的入口、程序中各个段的起始位置等信息;

!其中重定位表的作用就是:编译后各项保存的是各段在源程序中的绝对汇编地址,经加载程序加载后就将各项修改成在物理内存中实际的地址,因此称为重定位表;

app.nas,编译后生成app.bin

; 应用程序头
; 用于提供加载器相关加载信息
; 是应用程序规范的一部分
section header vstart=0
	app_size		dd	app_end					; [APP_SIZE:0x00] 程序的大小(字节)
	app_entry		dw	start					; [APP_ENTRY:0x04] 入口处偏移地址
	app_entry_seg	dd	section.code1.start		; [APP_ENTRY_SEG:0x06] 入口处段地址
	; section.段名.start是NASM提供的伪指令,用于段起始位置在源程序中的绝对汇编地址
	; 绝对汇编地址是指相对于整个源程序头的偏移量,而整个程序头的绝对汇编地址是0
	; 绝对汇编地址是一个32位无符号数,因此使用dd表示

	c_realloc_tbl	dw	(tbl_end - tbl_start) / 4		; [C_REALLOC_TBL:0x0A] 重定位表表项数目
tbl_start:	; [TBL_START:0x0C]
	seg_addr_code1	dd	section.code1.start
	seg_addr_code2	dd	section.code2.start
	seg_addr_data1	dd	section.data1.start
	seg_addr_data2	dd	section.data2.start
	seg_addr_stack	dd	section.stack.start
tbl_end:
; section header end


;;
;;
section stack align=16 vstart=0
	resb 256
stack_end:
; section stack end


;;
;;
section data1 align=16 vstart=0
	msg0 db '  This is NASM - the famous Netwid
随书附送光盘内容一览表 光盘目录 对应的书目录 目标文件名 程序功能 09\JIAN-H 第9章的9.1 JIAN-H.EXE 建立汉字库头文件 09\HZCALL 第9章的9.2 HZCALL.OBJ 显示汉字程序模块 09\NAME 第9章的9.3 NAME.OBJ 图形方式下处理输入字符 10\ARSE 第10章的10.1 ARSE.EXE 读扇区数据(汇编) 10\CRSE 第10章的10.2 CRSE.EXE 读扇区数据(C) 10\HCRSE 第10章的10.3 HCRSE.EXE 读扇区数据(C、汉显) 11\AWSE 第11章的11.1 AWSE.EXE 写扇区数据(汇编) 11\CWSE 第11章的11.2 CWSE.EXE 写扇区数据(C) 11\HCWSE 第11章的11.3 HCWSE.EXE 写扇区数据(C、汉显) 12\ALLSE 第12章的12.1 ALLSE.EXE 对扇区进行多种操作 12\HALLSE 第12章的12.2 HALLSE.EXE 对扇区进行多种操作(汉显) 13\READSF 第13章的13.1 READSF.EXE 读扇区备份文件 13\HREADSF 第13章的13.2 HREADSF.EXE 读扇区备份文件(汉显) 14\SEDIT 第14章的14.1 SEDIT.EXE 编辑扇区文件字节值 14\HSEDIT 第14章的14.2 HSEDIT.EXE 编辑扇区文件字节值(汉显) 15\SBLOCK 第15章的15.1 SBLOCK.EXE 扇区文件块拷贝 15\HSBLOCK 第15章的15.2 HSBLOCK.EXE 扇区文件块拷贝(汉显) 16\JIAN-H1 第16章的16.2.3 JIAN-H1.EXE 扩充汉字库头文件 16\HZCALL1 第16章的16.2.3 HZCALL1.OBJ 重新编译汉字显示程序模块 16\COMPSF 第16章的16.1 COMPSF.EXE 比较扇区文件 16\HCOMPSF 第16章的16.2 HCOMPSF.EXE 比较扇区文件(汉显) 17\0SE63 第17章的17.1 0SE63.EXE 显示0磁道扇区数据 17\H0SE63 第17章的17.2 H0SE63.EXE 显示0磁道扇区数据(汉显) 18\EARSE 第18章的18.2 EARSE.EXE 扩展读扇区数据(汇编) 19\EAWSE 第19章 EAWSE.EXE 扩展写扇区数据(汇编) 20\RSECTOR 第20章的20.1-20.3 RSECTOR.EXE C调用汇编扩展读 20\HRSECTOR 第20章的20.4 HRSECTOR.EXE C调用汇编扩展读(汉显) 21\WSECTOR 第21章的21.1-21.3 WSECTOR.EXE C调用汇编扩展写 21\HWSECTOR 第21章的21.4 HWSECTOR.EXE C调用汇编扩展写(汉显) 22\EALLSE 第22章的22.1 EALLSE.EXE 对扇区多种扩展操作 22\HEALLSE 第22章的22.2 HEALLSE.EXE 对扇区多种扩展操作(汉显) 23\JIAN-H2 第23章的23.2 JIAN-H2.EXE 扩充汉字库头文件 23\HZCALL2 第23章的23.2
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值