Warning: file_get_contents(/data/phpspider/zhask/data//catemap/0/assembly/5.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Assembly BIOS INT 10,AH=0E第二阶段的奇数行为_Assembly_X86 16_Bootloader_Osdev_Sanity Check - Fatal编程技术网

Assembly BIOS INT 10,AH=0E第二阶段的奇数行为

Assembly BIOS INT 10,AH=0E第二阶段的奇数行为,assembly,x86-16,bootloader,osdev,sanity-check,Assembly,X86 16,Bootloader,Osdev,Sanity Check,我已经开发了大约一年的内核,只是使用GRUB作为引导加载程序。然而,现在我想为我的内核开发一个引导加载程序 尽管我做出了努力,但我似乎无法解决装载机第二阶段的奇怪问题 生成文件: BOOTLOADER_FOLDER := boot KERNEL_FOLDER := kernel BOOTLOADER_SOURCES := $(shell find $(BOOTLOADER_FOLDER) -type f -iname "*.asm") BOOTLOAD

我已经开发了大约一年的内核,只是使用GRUB作为引导加载程序。然而,现在我想为我的内核开发一个引导加载程序

尽管我做出了努力,但我似乎无法解决装载机第二阶段的奇怪问题

生成文件:

BOOTLOADER_FOLDER       := boot
KERNEL_FOLDER           := kernel

BOOTLOADER_SOURCES      := $(shell find $(BOOTLOADER_FOLDER) -type f -iname "*.asm")
BOOTLOADER_OBJECTS      := $(subst .asm,.bin,$(BOOTLOADER_SOURCES))

BOOTLOADER_IMAGE        := $(BOOTLOADER_FOLDER)/boot.img

KERNEL_SOURCES          := $(shell find . -type f -iname "*.c")
KERNEL_OBJECTS          := $(foreach x,$(basename $(C_SOURCES)),$(x).o)

OS_IMAGE                := os.img

ALLFILES                := $(BOOTLOADER_SOURCES) $(KERNEL_SOURCES)

NASM                    := nasm
NASM_FLAGS              := -f bin

DD                      := dd
DD_FLAGS                := bs=512

GCC                     := GCC
GCC_FLAGS               := -g -std=gnu99 -Wall -Wextra -pedantic -Wshadow -Wpointer-arith \
                           -Wcast-align -Wwrite-strings -Wmissing-prototypes -Wmissing-declarations \
                           -Wredundant-decls -Wnested-externs -Winline -Wno-long-long \
                           -Wconversion -Wstrict-prototypes

QEMU                    := qemu-system-i386
QEMU_FLAGS              := -fda

all: clean compile todo run

clean:
    -rm -r $(BOOTLOADER_OBJECTS) $(KERNEL_OBJECTS) $(BOOTLOADER_IMAGE) $(OS_IMAGE)

compile: $(BOOTLOADER_OBJECTS) $(KERNEL_OBJECTS)

%.bin:%.asm
    @$(NASM) $(NASM_FLAGS) $< -o $@

%.o:%.c
    @$(GCC) $(GCC_FLAGS) -o $@ $<

$(BOOTLOADER_IMAGE):$(BOOTLOADER_OBJECTS)
    @$(foreach file,$(BOOTLOADER_OBJECTS),dd bs=512 if=$(file) >> $(BOOTLOADER_IMAGE);)

$(KERNEL_IMAGE):$(KERNEL_OBJECTS)

$(OS_IMAGE):$(BOOTLOADER_IMAGE) $(KERNEL_IMAGE)
    @$(DD) $(DD_FLAGS) if=$(BOOTLOADER_IMAGE) >> $(OS_IMAGE)

run:$(OS_IMAGE)
    @DISPLAY=:0 \
    $(QEMU) $(QEMU_FLAGS) $(OS_IMAGE);

todo:
    -@for file in $(ALLFILES:Makefile=); do fgrep -H -e TODO -e FIXME $$file; done; true
stage2.asm:

[BITS 16]
[ORG 0x500]

jmp main

print_string:
    lodsb
    or      al, al
    jz      .done
    mov     ah, 0x0E
    int     0x10
    jmp     print_string
.done:
    ret

loading_message     db  "Loading...", 0x0

main:
    mov     si, loading_message
    call    print_string

    cli
    hlt

我希望这只是打印
加载…
并停止系统。但是,它会打印以下内容:
☺ 您的错误是
stage1_address dw 0x500
,它将其声明为内存中的数据字,但随后您继续将其用作符号。将其更改为
stage1\u地址eq 0x500


学习使用反汇编程序和调试器。

这通常意味着
ds
段寄存器值和
org
之间不匹配。如果您的数据正在执行,这意味着您跳到了错误的第2阶段。在这两种情况下,都要使用调试器。提供包括第一阶段在内的所有代码以及如何构建磁盘映像都会很有帮助。@MichaelPetch我有一个第一阶段,它使用BIOS将第二阶段从磁盘加载到地址0x0000:0x0500编辑:我将上载第一阶段;没有看到你的评论。@MichaelPetch我使用QEMU@JonathonReinhart:我不推荐QEMU/GDB用于实模式调试,尤其是在调试任何软件中断的情况下。QEMU在这方面严重缺乏支持,因为它不理解20位段:偏移寻址。使用0x0000以外的段将完全混淆GDB。我建议只使用Bochs,它实际上有一个能够理解实模式的调试器,并且对实模式有适当的调试支持。如果您理解QEMU/GDB的缺陷,那么这是可能的(我写了一篇关于这个主题的长篇大论),谢谢您的帮助,我非常感谢!
[BITS 16]
[ORG 0x500]

jmp main

print_string:
    lodsb
    or      al, al
    jz      .done
    mov     ah, 0x0E
    int     0x10
    jmp     print_string
.done:
    ret

loading_message     db  "Loading...", 0x0

main:
    mov     si, loading_message
    call    print_string

    cli
    hlt