lindows/lcrash/lcrash.c

168 lines
4.1 KiB
C

#include "lnxboot.h"
#include "util.h"
#include "efi/types.h"
#include "efi/memmap.h"
#include "efi/guid.h"
unsigned short serial_port;
void outb(unsigned short port, unsigned char value) {
asm volatile (
"outb %b0, %1"
::"a" (value)
,"d" (port)
);
}
void serial_putc(char c) {
outb(serial_port, c);
}
void serial_puts(const char* s) {
while (*s) serial_putc(*(s++));
}
void serial_put_formatted_u64(u64 v) {
if (v == 0) {
serial_putc('0');
} else {
u64 max = 1;
while (v > max) max *= 10;
while (v) {
serial_putc('0' + (u8)(v / max));
v %= max;
max /= 10;
}
}
}
/**
* We can't do anything, just hang.
*/
[[noreturn, gnu::naked]]
void Hang() {
// This should make us hang
asm volatile (
" cli\n"
"1: hlt\n"
" jmp 1b"
);
}
/**
* Congratulations, you panicked twice!
*/
[[noreturn]]
void Panic(const char* message) {
// We don't even do anything with the message, but it's nice to have just in case.
Hang();
}
void entry64(struct boot_params* boot_params) {
while (1) {};
Panic("HELLO WORLD.");
/*
// get command line from kernel. we likely won't use it, but its nice to have.
u8* cmdline_ptr = (u8*)((u64)setup_info->cmd_line_ptr | ((u64)boot_params->ext_cmd_line_ptr << 32));
// do we have efi?
struct EfiSystemTable* systab_ptr = 0;
if (boot_params) {
systab_ptr = (struct EfiSystemTable*)(
(u64)boot_params->efi_info.EfiSystemTable |
((u64)boot_params->efi_info.EfiSystemTableHigh << 32)
);
EfiLoadStoredMemoryMap(
(struct EfiMemoryDescription*)(
(u64)boot_params->efi_info.EfiMemoryMap |
((u64)boot_params->efi_info.EfiMemoryMapHigh << 32)
), // this might be 0, we should probably check ---------------V
boot_params->efi_info.EfiMemoryMapSize / boot_params->efi_info.EfiMemoryDescriptionSize,
boot_params->efi_info.EfiMemoryDescriptionSize
);
}
// -- find acpi --
struct AcpiRSDP* AcpiRSDP = 0;
// check bootparams
if (boot_params->acpi_rsdp_addr) AcpiRSDP = boot_params->acpi_rsdp_addr;
while (true) {
volatile void* a = &EFI_ACPI_20_TABLE_GUID;
}
// check efi
if (!AcpiRSDP && systab_ptr && systab_ptr->NumberOfTableEntries) {
struct EfiConfigurationTable* ConfigurationTable = EfiTranslatePointer(systab_ptr->ConfigurationTable);
for (int i = 0; i < systab_ptr->NumberOfTableEntries; i++) {
if (CompareMemory(&ConfigurationTable[i].VendorGuid, &EFI_ACPI_20_TABLE_GUID, sizeof(EfiGuid))) {
AcpiRSDP = ConfigurationTable[i].VendorTable;
while (true) {
volatile void* a = AcpiRSDP;
}
break;
}
}
}
// we're playing where's waldo with this stupid fucking tableS
if (!AcpiRSDP) {
for (struct AcpiRSDP* addr = 0x00000000; addr < 0x000FFFFF; addr = (void*)addr + 16) {
if (addr->Signature[0] == 'R' && addr->Signature[1] == 'S'
&& addr->Signature[2] == 'D' && addr->Signature[3] == ' '
&& addr->Signature[4] == 'P' && addr->Signature[5] == 'T'
&& addr->Signature[6] == 'R' && addr->Signature[7] == ' ') {
AcpiRSDP = addr;
break;
}
}
}
if (!AcpiRSDP) Panic("Failed to find ACPI RSDP");
// do we have acpi?
while (1) {
volatile void* p = AcpiRSDP;
}
// we dont have the privilege of getting a rodata segment. any reads off our stack cause a triple fault
// for some fucking reason. allocate our strings and shit on the stack.
//char s_you_fucked_up[] = "!!! YOU FUCKED UP !!!\n";
//char s_vga_you_fucked_up[] = "YOU FUCKED UP.\n";
//char s_description[] = "A SERIOUS ERROR HAS OCCURED AND LINDOWS HAS STOPPED TO PREVENT FURTHER DAMAGE.";
//char s_registers[] = "REGISTERS:";
//char s_call_trace[] = "CALL TRACE:";
//char s_dumpcore[] = "[(D)UMP CORE]";
//char s_poweroff[] = "[(P)OWER OFF]";
//char s_reboot[] = "[(R)EBOOT ]";
// You fucked up.
//serial_puts(s_you_fucked_up);
//serial_puts(s_description);
//serial_putc('\n');
// register dump
//serial_puts(s_registers);
//serial_putc('\n');
//serial_putc('\n');
// call trace
//serial_puts(s_call_trace);
//serial_putc('\n');
//serial_putc('\n');
// thing
// serial_puts("test\n");
// serial_puts(bzhead.cmd_line_ptr);
// Die.*/
Panic("Nothing left to do.");
}