You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

119 lines
2.3 KiB
ArmAsm

/* Copyright (C) 2021,2022 fef <owo@fef.moe>. All rights reserved. */
#include <asm/common.h>
#include <arch/multiboot.h>
#include <gay/config.h>
/*
* miscellaneous utility routines shared among both i386 and amd64 startup
* sequences (these are called before entering long mode)
*/
.code32
.section .multiboot.text, "ax", @progbits
/*
* miscellaneous utility routines
*/
/* void _x86_write_tss_base(u64 *gdt_entry, struct x86_tss *tss) */
ENTRY(_x86_write_tss_base)
movl 4(%esp), %edi
movl 8(%esp), %eax
movw %ax, 2(%edi)
shrl $16, %eax
movb %al, 4(%edi)
movb %ah, 7(%edi)
ret
END(_x86_write_tss_base)
/* __noreturn void print_err_and_hlt(char *message) */
L_ENTRY(print_err_and_hlt)
mov $0x000b8000, %edx
mov 4(%esp), %ecx
movb $0x4f, %ah /* BIOS color code: white text on red background */
1: movb (%ecx), %al
testb %al, %al
jz 2f
movw %ax, (%edx)
addl $2, %edx
incl %ecx
jmp 1b
2: cli /* interrupts should already be off, but it won't hurt */
hlt
jmp 2b
L_END(print_err_and_hlt)
ENTRY(_x86_check_multiboot)
cmpl $MB2_BOOTLOADER_MAGIC, 4(%esp)
jne 1f
ret
1: pushl $errmsg_no_multiboot
jmp print_err_and_hlt
END(_x86_check_multiboot)
/*
* check if the CPU supports the CPUID instruction
* this is done by checking whether we can flip bit 21 in EFLAGS (??)
*/
ENTRY(_x86_check_cpuid)
pushf
pop %eax
movl %eax, %ecx
xorl $(1 << 21), %eax
push %eax
popf
pushf
pop %eax
push %ecx /* restore original flags */
popf
cmp %eax, %ecx
je 1f
ret
1: pushl $errmsg_no_cpuid
jmp print_err_and_hlt
END(_x86_err_no_cpuid)
ENTRY(_x86_check_ext_cpuid)
movl $0x80000000, %eax
cpuid
cmpl $0x80000001, %eax
jb 1f
ret
1: pushl $errmsg_no_ext_cpuid
jmp print_err_and_hlt
END(_x86_check_ext_cpuid)
ENTRY(_x86_check_ia32e)
movl $0x80000001, %eax
cpuid
test $(1 << 29), %edx
jz 1f
ret
1: pushl $errmsg_no_ia32e
jmp print_err_and_hlt
END(_x86_check_ia32e)
.section .multiboot.data, "a", @progbits
L_DATA(errmsg_no_multiboot)
.asciz "Invalid Multiboot 2 magic number in %eax"
L_END(errmsg_no_multiboot)
L_DATA(errmsg_no_cpuid)
.asciz "CPUID instruction not supported"
L_END(errmsg_no_cpuid)
L_DATA(errmsg_no_ext_cpuid)
.asciz "No extended CPUID features available"
L_END(errmsg_no_ext_cpuid)
L_DATA(errmsg_no_ia32e)
.asciz "CPU does not appear to support IA-32e mode"
L_END(errmsg_no_ia32e)