跳转到保护模式连接内核后不工作 [英] Jump to Protected Mode not working after linking the kernel
问题描述
我一直在开发一个引导程序和链接C ++ code时,我的组装阶段2 code之前,我联系了第二阶段将跳转到保护模式,然后以长模式的文件,没有任何问题,遇到了一个问题但现在我已经联系在一起后,似乎有一个问题跳转到保护模式时,这里是code我用跳转到保护模式:
I have been developing a Bootloader and have run into a problem when linking c++ code to my assembly stage2 code before I linked the files the second stage would jump to protected mode then to long mode without any problems but now after I have linked it there seems to be a problem when jumping to protected mode Here is the code I use to jump to protected mode:
main:
;first stage of bootloader is loaded at the address 0x07c0:0
;second stage of bootloader is loaded at address 0x200:0x0
cli
xor ax, ax ; All segments set to 0, flat memory model
mov ds, ax
mov es, ax
mov gs, ax
mov fs, ax
mov ss, ax
;
; Set stack top SS:0xffff
;
mov sp, 0x0FFFF
;
mov [CDDriveNumber], dl
SwitchToProtectedMode:
lgdt [GDT_32];load the gdt
call EnableA20
mov eax, cr0
or eax, 1
mov cr0, eax
; Flush CS and set code selector
;
jmp 0x8:Protected_Mode
[BITS 32];Declare 32 bits
Protected_Mode:
下面是GDT:
GDT_START:
;null descriptor
dd 0
dd 0
;data descriptor
dw 0xFFFF
dw 0
db 0
db 10011010b
db 11001111b
db 0
;code descriptor
dw 0xFFFF
dw 0
db 0
db 10010010b
db 11001111b
db 0
GDT_END:
align 4
GDT_32:
dw GDT_END - GDT_START - 1
dd GDT_START
下面是我用链接我的C语言和汇编code中的链接脚本
Here is the linker script I use to link my c and assembly code
KernAddr = 0x200;
ENTRY(_Start)
SECTIONS
{
. = KernAddr;
.text : AT(ADDR(.text) - KernAddr)
{
_code = .;
*(.text)
*(.rodata*)
. = ALIGN(4096);
}
.data : AT(ADDR(.data) - KernAddr)
{
_data = .;
*(.data)
. = ALIGN(4096);
}
.eh_frame : AT(ADDR(.eh_frame) - KernAddr)
{
_ehframe = .;
*(.eh_frame)
. = ALIGN(4096);
}
.bss : AT(ADDR(.bss) - KernAddr)
{
_bss = .;
*(.bss)
/*
* You usually need to include generated COMMON symbols
* under kernel BSS section or use gcc's -fno-common
*/
*(COMMON)
. = ALIGN(4096);
}
_end = .;
/DISCARD/ :
{
*(.comment)
}
}
下面是我做出的一切建立批处理程序:
Here is the batch program I made to build everything:
nasm Stage1.asm -o Stage1.bin
nasm -f elf64 Stage2.asm -o Stage2.o
x86_64-elf-g++ -ffreestanding -mcmodel=large -mno-red-zone -mno-mmx -mno-sse -mno-sse2 -mno-sse3 -mno-3dnow -c -o kernel.o kernel.cpp
x86_64-elf-ld -T linkerscript.ld -o Anmu.bin Stage2.o kernel.o -nostdlib
copy Stage1.bin Root
copy Anmu.bin Root
mkisofs -b Stage1.bin -no-emul-boot -boot-info-table -o BootLoader.iso ./Root
在code的其余部分可以在这里找到: https://github.com/AnonymousUser1337/Anmu
推荐答案
您说,2阶段在加载的段的 0x0200
,这是地址为0x2000
,但你的链接表示,在开始的偏移的 0x0200
。
You say that Stage2 is loaded at segment 0x0200
, which is address 0x2000
, but your linker says it starts at offset 0x0200
.
此外,尽管命名你的输出安牧。斌,你的文件实际上仍然是一个ELF可执行文件,这意味着所有的头和诸如此类的东西仍在present的文件中。相反,你需要使用 objcopy把
,以去除所有页眉和调试符号,给你一个平坦的二进制文件:
Also, despite naming your output "Anmu.bin", your file is actually still an ELF executable, which means all of the headers and whatnot are still present in the file. Instead, you need to use objcopy
to strip all of the headers and debugging symbols, giving you a flat binary:
objcopy -S -O binary Anmu.bin Anmu-flat.bin
现在,安牧-flat.bin只不过是code和数据,并且该文件的第一个字节是第一指令的起始
Now, "Anmu-flat.bin" is nothing but code and data, and the first byte of the file is the start of the first instruction.
这篇关于跳转到保护模式连接内核后不工作的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!