Assembly 在引导扇区中,内存在16位实模式下运行异常

Assembly 在引导扇区中,内存在16位实模式下运行异常,assembly,memory,x86,x86-16,bootloader,Assembly,Memory,X86,X86 16,Bootloader,我一直在研究操作系统的开发,一直在研究引导扇区,试图将其打印到屏幕上 [org 0x7c00] ; Print 'Hello World' to the screen mov bx, MSG call print_string ; Hang jmp $ ; Includes %include "boot_sect_print.asm" ; Global Variables MSG: db "Hello World", 0 ; Padding

我一直在研究操作系统的开发,一直在研究引导扇区,试图将其打印到屏幕上

[org 0x7c00]

; Print 'Hello World' to the screen
mov bx, MSG
call print_string

; Hang
jmp $


; Includes
%include "boot_sect_print.asm"


; Global Variables
MSG: db "Hello World", 0


; Padding
times 510-($-$$) db 0
; Magic Number
dw 0xaa55
下面是打印功能代码:

; Print a string from bx
print_string:
    pusha

; Loop through and print each character
start:
    mov al, [bx]
    cmp al, 0
    je done

    mov ah, 0x0e
    int 0x10

    add bx, 1
    jmp start

done:
    popa
    ret

当我在模拟器(qemu)上运行它时,它工作得很好,但是当我把代码放在usb上并从它引导我的电脑时,一些奇怪的行为正在发生。我已经确认打印是有效的,因为如果我将一个字符移动到'al'中,然后调用'int 0x10',它在我的电脑上可以很好地打印。但是,当从内存访问字符串时,在这种情况下,'MSG'不是从内存加载正确的值,而是加载了不同的内容,因此无法正确打印。我做了一些测试,它似乎从'MSG'而不是'H'的第一个字节得到255(0xff)。我现在真的不知道该怎么做,因为它在qemu上似乎可以很好地工作,但在实际的PC上却不行。

初始化段寄存器。搜索此站点时,有很多示例。由于您使用的是
ORG 0x7c00
,因此请使用0初始化DS。引导加载程序代码的开头是xor ax,ax
mov-ds,ax
。我这里有一些一般引导加载程序提示,讨论了不设置段寄存器的问题:。如果您使用USB在真正的硬件上引导,并且BIOS设置为USB软盘模拟(FDD),那么您可能会遇到另一个没有BIOS参数块(BPB)的问题:非常感谢,我设法使其工作,现在已引导到内核中。BPB不是一个问题,但读起来很有趣。是段寄存器导致了我所有的问题。我想我理解了ORG指令和段在实际模式下的工作方式,但我想我需要做一些进一步的阅读。我注意到你写了一些关于组织指令Michael的东西,所以我会仔细看看。谢谢你的帮助!不要在你的问题中添加解决方案。相反,将其作为答案发布。初始化段寄存器。搜索此站点时,有很多示例。由于您使用的是
ORG 0x7c00
,因此请使用0初始化DS。引导加载程序代码的开头是xor ax,ax
mov-ds,ax
。我这里有一些一般引导加载程序提示,讨论了不设置段寄存器的问题:。如果您使用USB在真正的硬件上引导,并且BIOS设置为USB软盘模拟(FDD),那么您可能会遇到另一个没有BIOS参数块(BPB)的问题:非常感谢,我设法使其工作,现在已引导到内核中。BPB不是一个问题,但读起来很有趣。是段寄存器导致了我所有的问题。我想我理解了ORG指令和段在实际模式下的工作方式,但我想我需要做一些进一步的阅读。我注意到你写了一些关于组织指令Michael的东西,所以我会仔细看看。谢谢你的帮助!不要在你的问题中添加解决方案。相反,将其作为答案发布。