Bootloader
The bootloader is the program that brings your operating system to life. So it needs to bring the kernel into memory somehow. Before transfering control to the kernel, it would be great to setup an environment that the kernel likes, e.g., protected mode.
The bootloader runs in real mode. Because of this, it has easy access to the BIOS.
Checklist:
- Setup 16-bit segment registers and stack
- Print startup message
- Check presence of PCI, CPUID, MSRs
- Enable and confirm enabled A20 line
- Load GDTR
- Inform BIOS of target processor mode
- Get memory map from BIOS
- Locate kernel in filesystem
- Allocate memory to load kernel image
- Load kernel image into buffer
- Enable graphics mode
- Check kernel image ELF headers
- Enable long mode, if 64-bit
- Allocate and map memory for kernel segments
- Setup stack
- Setup COM serial output port
- Setup IDT
- Disable PIC
- Check presence of CPU features (NX, SMEP, x87, PCID, global pages, TCE, WP, MMX, SSE, SYSCALL), and enable them
- Assign a PAT to write combining
- Setup FS/GS base
- Load IDTR
- Enable APIC and setup using information in ACPI tables
- Setup GDT and TSS
BIOS vs UEFI
With a computer running legacy BIOS, the BIOS and the boot loader run in Real mode. The 64-bit operating system kernel checks and switches the CPU into Long mode and then starts new kernel-mode threads running 64-bit code.
With a computer running UEFI, the UEFI firmware (except CSM and legacy Option ROM), the UEFI boot loader and the UEFI operating system kernel all run in Long mode.