天天看点

计算机系统-程序加载器

本文将实现一个简单的程序加载器,首先要先了解一下实模式下的内存空间分配,这是固定好的

计算机系统-程序加载器

要实现一个程序加载器,需要实现下面4个步骤

1.将用户程序从硬盘中读取到10000处(当然,放到10000-9FFFF任意位置都可以)

2.设置段地址(段的重定位,注意段地址最低位必须是0)

3.找到用户的程序的入口(从哪开始执行)

4.跳转到程序入口执行

关于NASM的vstart关键字

由于本文使用NASM实现,所以有必要了解vstart关键字,如果一个段声明了vstart子句,则段内所有的汇编地址,编译之后,都等于vstart+偏移量

vstart示例1:下面代码vstart=0,jmp指令所在的汇编地址是3

Segment code1 vstart=0
mov ax,0x001 ;这条指令占3个字节
jmp bx      

下图中最上面的绿色位置(vstart=0处)表示第1个开始计数的位置,这个位置=0,所以到jmp指令,正好是3

计算机系统-程序加载器

vstart示例2:下面代码vstart=2,mov指令所在的汇编地址是5

Segment code1 vstart=2
mov ax,0x001 ;这条指令占3个字节
jmp bx      

下图中最上面的绿色位置(vstart=2处)表示第1个开始计数的位置,这个位置=0,所以到jmp指令,正好是5

计算机系统-程序加载器

日记:关于这个vstart,可以理解成将起始位置向上拓展延伸

关于标号

标号是相对于当前段的偏移量(字节数),而不是相对于程序的偏移量,不管NASM还是MASM,都是这样的
segment code vstart=0x7c00

;设置空栈
xor ax,ax
mov ss,ax
mov sp,ax

;设置用户程序的段地址
mov eax,[cs:app_address]
shr eax,4
mov ds,ax
mov es,ax

;设置用户程序要加载到0x10000位置
app_address dd 0x10000

;设置55AA
times 510-($-$$) db 00
dw 0xAA55