Unix 使用终端通过USB(不是软盘、CD-ROM或模拟器)的Helloworld引导加载程序
我是bootloader的新手,我读了几十篇关于bootleader的文章,但似乎没有人支持我 他们都提到了传统的步骤:Unix 使用终端通过USB(不是软盘、CD-ROM或模拟器)的Helloworld引导加载程序,unix,assembly,bootloader,usb-drive,dd,Unix,Assembly,Bootloader,Usb Drive,Dd,我是bootloader的新手,我读了几十篇关于bootleader的文章,但似乎没有人支持我 他们都提到了传统的步骤: umount dd sync 同上 首先让我告诉你,使用unetbootin,我试过了,效果非常好。然后,我尝试从终端运行它,使用isohybrid工具将它从ISOLINUX转换为SYSLINUX。除了dd工具之外,它也可以工作 接下来,我尝试使用在屏幕上打印“Hello world”的汇编代码制作一个引导加载程序。当然,我是从这样的工作开始的 我作为root用户所做的工
umount
dd
sync
unetbootin
,我试过了,效果非常好。然后,我尝试从终端运行它,使用isohybrid
工具将它从ISOLINUX转换为SYSLINUX。除了dd
工具之外,它也可以工作
接下来,我尝试使用在屏幕上打印“Hello world”的汇编代码制作一个引导加载程序。当然,我是从这样的工作开始的
我作为root用户所做的工作如下:
- 使用FAT32格式化闪存:
mkdosfs-n“USB驱动器名称”-I/dev/sdb-F 32
- 确保它已卸载
,其中umount/dev/sdb*
是我的USB驱动器/dev/sdb
- 汇编代码:
nasm-f bin-o myfirst.bin myfirst.asm
- 将其安装到USB的MBR中:
dd if=myfirst.bin of=/dev/sdb bs=512
sync
- 重新启动
;------------------------------------------------------------;
;
; 打印hello world的最小引导加载程序
; 然后停下来。
;
; nasm-f bin hello-boot.asm-o hello-boot.bin
;
; @尤里亚克斯
;
;----------------------------------------------;
组织0x7c00;BIOS在此地址加载
位16;16位实模式
; 打印欢迎信息。
; 我们这里没有DOS和Linux内核。
; 因此,我们将使用bios int 0x10。
开始:
cli;屏蔽中断
mov-si,msg;SI指向消息
mov-ah,0x0e;打印字符服务
.loop lodsb;所有您需要向我们展示您的引导加载程序,以便我们告诉您它有什么问题。在调用int 0x10
之前,请尝试将bx
设置为零,否则可能不会显示输出。另外,每次在循环中尝试设置ah
,不确定int 0x10
是否会破坏它。好的,我添加了一个简单的:Hello world code。注意,即使它将启动,它也可能无法工作,因为您没有将DS
初始化为已知值。代码加载在物理地址7c00
是正确的,但可以是0:7c00
或7c0:0
,这只是针对CS
,DS
可能完全是另外一回事。除非您使用的是UEFI之前的固件,否则它不会引导设备,除非它们识别一些常见的代码模式。另一个是跳过BPB的jmp…
(固件可能会尝试修补!)。可能需要一个可引导分区,即使是假的。此外,您不需要使用FAT FS格式化设备,只需要使用没有分区表的自定义MBR(只需添加它)来销毁它。
;----------------------------------------------;
;
; A minimal bootloader that prints a hello world
; then halts.
;
; nasm -f bin hello-boot.asm -o hello-boot.bin
;
; @YouriAckx
;
;----------------------------------------------;
org 0x7c00 ; BIOS loads at this address
bits 16 ; 16 bits real mode
; Print a welcome message.
; We have no DOS nor Linux kernel here.
; Therefore, we will use bios int 0x10.
start:
cli ; disable interrupts
mov si, msg ; SI points to message
mov ah, 0x0e ; print char service
.loop lodsb ; AL <- [DS:SI] && SI++
or al, al ; end of string?
jz halt
int 0x10 ; print char
jmp .loop ; next char
halt: hlt ; halt
msg: db "Hello, World!", 0
;----------------------------------------------;
; Bootloader signature must be located
; at bytes #511 and #512.
; Fill with 0 in between.
; $ = address of the current line
; $$ = address of the 1st instruction
;----------------------------------------------;
times 510 - ($-$$) db 0
dw 0xaa55