在使用 GRUB2 启动 multiboot2 投诉操作系统时,阅读我收到的标签
type = 25
以及我对 type = 6
的信息请求被忽略。
不完全确定我的遍历方法是否有效。
不知道这是否是 GRUB2 的问题。
如果正确的话哪里有
type = 25
的资料。
;; multiboot2.asm
%define mb2_magic 0xE85250D6
%define mb2_arch 0
section .boot
_mb2:
dd mb2_magic
dd mb2_arch
dd _emb2 - _mb2
dd 0x100000000 - (mb2_magic + mb2_arch + (_emb2 - _mb2))
align 8
.mb2_ir:
dw 1 ; information request
dw 0
dd .emb2_ir - .mb2_ir
dd 6 ; memory map tag
.emb2_ir:
align 8
.end_tag:
dd 0
dd 8
_emb2:
;entry.asm
[BITS32]
__start:
mov [.mb2_magic], eax
mov [.mb2_info], ebx
;; ...
call check_multiboot
;; ...
lgdt [gdt64.ptr]
jmp gdt64.code:realm64
.mb2_magic:
dd 0
.mb2_info:
dq 0
check_multiboot:
mov eax, [__start.mb2_magic]
cmp eax, 0x36D76289 ; multiboot2 magic number
jne .fail
ret
.fail:
mov ebx, .message
call quick_print ; defined in file
hlt
.message:
db "Boot Check Failed:", 0x0A, 0x0A, "Was not booted from MultiBoot2", 0x0A, "MBR (Master Boot Record) is incompatible", 0x00
;; ...
[BITS 64]
realm64:
;; ...
[extern main]
mov rsi, [__start.mb2_magic]
mov rdi, [__start.mb2_info]
call main
// kernel.c
int main(mb2_info_header* mbd, uint32_t magic) // magic checked in entry.asm
{
tty_init();
mb2_traverse(mbd);
// ...
}
// multiboot2.c
typedef struct s_MB2_tag {
uint32_t type;
uint32_t size;
} mb2_tag;
typedef struct s_MB2_info_header {
uint32_t total_size;
uint32_t __RSV1;
} mb2_info_header;
void mb2_traverse(mb2_info_header *mbd)
{
uint64_t mb2_end = mbd->total_size + (uint64_t)mbd;
mb2_tag *tag = (mb2_tag*)(mbd + sizeof(mb2_info_header));
while ((uint64_t)tag < mb2_end)
{
tty_printf("TAG %d\t[%d] @\t%x\n", tag->type, tag->size, tag);
if (tag->type == 0)
break;
tag += tag->size;
if ((uint64_t)tag & 0x7)
tag += 8 - ((uint64_t)tag & 0x7);
}
}
产量:
TAG N [size] @ ptr
@MichaelPetch 提供了此评论(非常感谢)
经过进一步检查,存在类似的选角问题(参考之前的评论)这里也:
你可以做类似的事情tag += tag->size;
tag = (mb2_tag *) ((uint8_t *) tag + ((tag->size + 7) & ~7)))
将代码调整为
multiboot2.c
中的新遍历之后
// multiboot2.c
void mb2_traverse(mb2_info_header *mbd, uint32_t magic)
{
if (magic != 0x36D76289)
{
tty_printf("Multiboot2 Magic Number is invalid");
asm volatile ("hlt");
}
tty_printf("MB2 [%d]\n", mbd->total_size);
uint64_t mb2_end = mbd->total_size + (uint64_t)mbd;
mb2_tag *tag = (mb2_tag*)(mbd + sizeof(mb2_info_header));
while ((uint64_t)tag < mb2_end)
{
tty_printf("TAG %d\t[%d] @\t%x\n", tag->type, tag->size, tag);
if (tag->type == 0)
break;
switch (tag->type) {
// ...
default: break;
}
tag = (mb2_tag *) ((uint8_t *) tag + ((tag->size + 7) & ~7));
}
}