Ошибка "не найден мультизагрузочный заголовок" при попытке скомпилировать мою собственную ОС - PullRequest
0 голосов
/ 28 мая 2018

Я написал голую ОС на c с загрузчиком сборок, но не могу запустить его, каждый раз, когда я запускаю его, я получаю сообщение об ошибке "не найден заголовок мультизагрузки" от grub2.Я знаю, что мой код не проблема, я пытался скомпилировать другие ОС, и они выдают ту же ошибку.Системные спецификации: Ubuntu Linux с gcc версии 7.2.Я уже рассмотрел все остальные вопросы по этому поводу, и ни один из них не помог мне.

Я использую эти команды для компиляции моей ОС:

as boot.s -o boot.o

gcc -c kernel.c -o kernel.o -std=gnu99 -ffreestanding -O2 -Wall -Wextra

gcc -T linker.ld -o MyOS.bin -ffreestanding -O2 -nostdlib kernel.o boot.o -lgcc

grub-file --is-x86-multiboot MyOS.bin

mkdir -p isodir/boot/grub
cp MyOS.bin isodir/boot/MyOS.bin
cp grub.cfg isodir/boot/grub/grub.cfg
grub-mkrescue -o MyOS.iso isodir

qemu-system-x86_64 -cdrom MyOS.iso

bootloader:

    # set magic number to 0x1BADB002 to identified by bootloader   
.set MAGIC,    0x1BADB002  

# set flags to 0  
.set FLAGS,    0  

# set the checksum  
.set CHECKSUM, -(MAGIC + FLAGS)  

# set multiboot enabled  
.section .multiboot  

# define type to long for each data defined as above  
.long MAGIC  
.long FLAGS  
.long CHECKSUM  


# set the stack bottom   
stackBottom:  

# define the maximum size of stack to 512 bytes  
.skip 512  


# set the stack top which grows from higher to lower  
stackTop:  

.section .text  
.global _start  
.type _start, @function  


_start:  

  # assign current stack pointer location to stackTop  
    mov $stackTop, %esp  

  # call the kernel main source  
    call KERNEL_MAIN  

    cli  


# put system in infinite loop  
hltLoop:  

    hlt  
    jmp hltLoop  

.size _start, . - _start  

компоновщик:

/* The bootloader will look at this image and start execution at the symbol designated at the entry point. */
ENTRY(_start)

SECTIONS
{
    /* Begin putting sections at 1 MiB, a conventional place for kernels to be
       loaded at by the bootloader. */
    . = 1M;

    /* First put the multiboot header, as it is required to be put very early in the image or the bootloader won't recognize the file format. Next we'll put the .text section. */
    .text BLOCK(4K) : ALIGN(4K)
    {
        *(.multiboot)
        *(.text)
    }

    /* Read-only data. */
    .rodata BLOCK(4K) : ALIGN(4K)
    {
        *(.rodata)
    }

    /* Read-write data (initialized) */
    .data BLOCK(4K) : ALIGN(4K)
    {
        *(.data)
    }

    /* Read-write data (uninitialized) and stack */
    .bss BLOCK(4K) : ALIGN(4K)
    {
        *(COMMON)
        *(.bss)
        *(.bootstrap_stack)
    }
}

ядро:

#include"kernel.h"  

static UINT16 VGA_DefaultEntry(unsigned char to_print) {  
    return (UINT16) to_print | (UINT16)WHITE_COLOR << 8;  
}  

void KERNEL_MAIN()  
{  
  TERMINAL_BUFFER = (UINT16*) VGA_ADDRESS;  

  TERMINAL_BUFFER[0] = VGA_DefaultEntry('H');  
  TERMINAL_BUFFER[1] = VGA_DefaultEntry('e');  
  TERMINAL_BUFFER[2] = VGA_DefaultEntry('l');  
  TERMINAL_BUFFER[3] = VGA_DefaultEntry('l');  
  TERMINAL_BUFFER[4] = VGA_DefaultEntry('o');  
  TERMINAL_BUFFER[5] = VGA_DefaultEntry(' ');  
  TERMINAL_BUFFER[6] = VGA_DefaultEntry('W');  
  TERMINAL_BUFFER[7] = VGA_DefaultEntry('o');  
  TERMINAL_BUFFER[8] = VGA_DefaultEntry('r');  
  TERMINAL_BUFFER[9] = VGA_DefaultEntry('l');  
  TERMINAL_BUFFER[10] = VGA_DefaultEntry('d');  
}  
...