XFE Git
XFE Studio Git
Git 首页 全局搜索
XFE 主站 文档 NuGet

XFESystem

【Rust】XFE系统,基于Rust和汇编

公开
关注 0 Fork 0 Star 0
UTF-8
using System.Runtime.InteropServices;

namespace XFESystem.NativeKernel;

public static unsafe partial class Kernel
{
    public static bool Ready;
    public static NativeBootInfo* Boot;
    static partial void OnKernelReady();

    [UnmanagedCallersOnly(EntryPoint = "XfeKernelMain")]
    public static void Main(NativeBootInfo* boot)
    {
        Boot = boot;
        Serial.Initialize();
        Serial.Line("XFE_NATIVE_ENTRY CSharp zero-library independent kernel");
        if (boot == null || boot->ProtocolSupported == 0) Fail("LIMINE_PROTOCOL");
        bool display = Framebuffer.Initialize(boot->Framebuffer);
        if (display) Framebuffer.Fill(0);
        if (!Cpu.Initialize()) Fail("CPU_BASELINE");
        Serial.Write("XFE_CPU_OK bsp_apic="); Serial.Number(Cpu.ApicId);
        Serial.Write(" cr3="); Serial.Hex(Native.ReadCr3()); Serial.Line("");
        Framebuffer.BootStage(25);
        if (!PhysicalMemory.Initialize(boot)) Fail("MEMORY_MAP");
        Serial.Write("XFE_MEMORY_MAP_OK free_pages="); Serial.Number(PhysicalMemory.AvailablePages);
        Serial.Write(" usable_bytes_above_cap="); Serial.Number(PhysicalMemory.IgnoredUsableBytes); Serial.Line("");
        if (!PhysicalMemory.SelfTest()) Fail("PAGE_ALLOCATOR");
        Serial.Line("XFE_PAGES_OK zero reuse ownership contiguous");
        if (Native.LibcSelfTest() != 1) Fail("LIBC_SELFTEST");
        Serial.Line("XFE_LIBC_OK allocate realloc free overlap alignment");
        if (Native.StdioSelfTest() != 1) Fail("STDIO_SELFTEST");
        Serial.Line("XFE_STDIO_SELFTEST_OK");
        if (Native.LoadedElfSelfTest() != 1) Fail("ELF_IMAGE_SELFTEST");
        Serial.Line("XFE_LOADED_ELF_SELFTEST_OK");
        Framebuffer.BootStage(50);
        if (!Cpu.InstallDescriptors()) Fail("GDT_IDT_TRAP");
        Serial.Line("XFE_DESCRIPTORS_OK GDT TSS IDT INT3");
        if (!VirtualMemory.Initialize() || !VirtualMemory.SelfTest()) Fail("VIRTUAL_MEMORY");
        Serial.Line("XFE_VIRTUAL_MEMORY_OK reserve commit decommit release RW NX guard faults");
        if (!MonotonicClock.Initialize()) Fail("MONOTONIC_CLOCK");
        Serial.Write("XFE_CLOCK_OK tsc_hz="); Serial.Number(MonotonicClock.Frequency);
        Serial.Write(" invariant="); Serial.Number(MonotonicClock.Invariant ? 1UL : 0UL); Serial.Line("");
        ulong fileTime = UtcClock.ReadFileTime();
        if (fileTime == 0) Serial.Line("XFE_RTC_UNAVAILABLE");
        else { Serial.Write("XFE_RTC_FILETIME source=CMOS_RTC_UTC_EXPECTED value="); Serial.Number(fileTime); Serial.Line(""); }
        Framebuffer.BootStage(75);
        if (!display || !Framebuffer.SelfTest()) Fail("FRAMEBUFFER_32BIT");
        Serial.Write("XFE_FRAMEBUFFER_OK width="); Serial.Number(Framebuffer.Width);
        Serial.Write(" height="); Serial.Number(Framebuffer.Height); Serial.Line("");
        GpuHardwareBridge.Initialize(boot);
        NvidiaBootProbe.Initialize(boot);
        if (!Threads.Initialize() || !ThreadSelfTest.Run()) Fail("THREADS_TIMER_TLS_FPU_EVENTS");
        if (!BootSplash.Start()) Fail("BOOT_VISUAL_WORKER");
        Serial.Write("XFE_THREADS_OK switches="); Serial.Number(Threads.Switches);
        Serial.Write(" preemptions="); Serial.Number(Threads.Preemptions); Serial.Line(" TLS FPU red_zone private_IRQ_stacks guarded_stacks events");
        Ps2Input.Initialize();
        if (!DiskHardware.Start()) Serial.Line("XFE_DISK|WORKER_START_FAILED");
        if (!UsbXhci.Start()) Serial.Line("XFE_USB|WORKER_START_FAILED");
        Framebuffer.BootStage(100);
        Ready = true;
        Serial.Line("XFE_NATIVE_SELFTEST_OK independent_cpu_memory_interrupt_framebuffer");
        Native.IrqRestore(0x202);
        OnKernelReady();
        for (;;) Native.Idle();
    }

    [UnmanagedCallersOnly(EntryPoint = "XfeHandleInterrupt")]
    public static void HandleInterrupt(InterruptFrame* frame)
    {
        if (frame != null && frame->Vector == 3)
        {
            Cpu.BreakpointCount++;
            Cpu.BreakpointStackMatches = frame->Rsp == Native.BreakpointStack();
            return;
        }
        if (frame != null && frame->Vector == 14 && Cpu.HandleExpectedFault(frame, Native.ReadCr2())) return;
        if (frame != null && (frame->Vector == 0 || frame->Vector == 14))
        {
            ulong faultAddress = frame->Vector == 14 ? Native.ReadCr2() : 0;
            void* fxSave = (void*)(((ulong)frame & ~15UL) - 512);
            if (Native.HardwareException(frame, faultAddress, fxSave) == 1) return;
        }
        if (frame != null && frame->Vector == 32) { Ps2Input.Poll(); Threads.Timer(frame); return; }
        if (frame != null && frame->Vector == 255) return; // LAPIC spurious: no EOI by architecture contract.
        Serial.Write("XFE_NATIVE_EXCEPTION vector="); Serial.Number(frame == null ? 255UL : frame->Vector);
        if (frame != null)
        {
            Serial.Write(" error="); Serial.Hex(frame->Error);
            Serial.Write(" rip="); Serial.Hex(frame->Rip);
            if (frame->Vector == 14) { Serial.Write(" cr2="); Serial.Hex(Native.ReadCr2()); }
        }
        Serial.Line("");
        if (frame != null) DumpFaultContext(frame);
        Fail("UNHANDLED_EXCEPTION");
    }

    // Fatal diagnostics only: print the CPU's saved values without touching the
    // faulting operand or walking an untrusted stack. This remains allocation-free
    // and bounded even when the current managed heap or frame pointers are invalid.
    static void DumpFaultContext(InterruptFrame* frame)
    {
        Serial.Write("XFE_FAULT_FRAME address="); Serial.Hex((ulong)frame);
        Serial.Write(" rsp="); Serial.Hex(frame->Rsp);
        Serial.Write(" rbp="); Serial.Hex(frame->Rbp);
        Serial.Write(" cs="); Serial.Hex(frame->Cs);
        Serial.Write(" ss="); Serial.Hex(frame->Ss);
        Serial.Write(" rflags="); Serial.Hex(frame->Rflags);
        Serial.Write(" fsbase="); Serial.Hex(Native.ReadMsr(0xc0000100));
        Serial.Write(" cr3="); Serial.Hex(Native.ReadCr3()); Serial.Line("");
        Serial.Write("XFE_FAULT_GPR rax="); Serial.Hex(frame->Rax);
        Serial.Write(" rbx="); Serial.Hex(frame->Rbx);
        Serial.Write(" rcx="); Serial.Hex(frame->Rcx);
        Serial.Write(" rdx="); Serial.Hex(frame->Rdx);
        Serial.Write(" rdi="); Serial.Hex(frame->Rdi);
        Serial.Write(" rsi="); Serial.Hex(frame->Rsi); Serial.Line("");
        Serial.Write("XFE_FAULT_GPR r8="); Serial.Hex(frame->R8);
        Serial.Write(" r9="); Serial.Hex(frame->R9);
        Serial.Write(" r10="); Serial.Hex(frame->R10);
        Serial.Write(" r11="); Serial.Hex(frame->R11);
        Serial.Write(" r12="); Serial.Hex(frame->R12);
        Serial.Write(" r13="); Serial.Hex(frame->R13);
        Serial.Write(" r14="); Serial.Hex(frame->R14);
        Serial.Write(" r15="); Serial.Hex(frame->R15); Serial.Line("");
        KernelThread* thread = Threads.Current;
        Serial.Write("XFE_FAULT_THREAD id="); Serial.Number(thread == null ? 0 : thread->Id);
        Serial.Write(" state="); Serial.Number(thread == null ? 0 : thread->State);
        Serial.Write(" stack_low="); Serial.Hex(thread == null ? 0 : thread->StackLow);
        Serial.Write(" stack_high="); Serial.Hex(thread == null ? 0 : thread->StackHigh);
        Serial.Write(" saved_tls="); Serial.Hex(thread == null ? 0 : thread->Tls);
        Serial.Write(" irq_stack_top="); Serial.Hex(thread == null ? 0 : thread->InterruptStackTop);
        Serial.Write(" runtime_thread="); Serial.Hex(thread == null ? 0 : (ulong)thread->RuntimeThread);
        Serial.Write(" switches="); Serial.Number(Threads.Switches);
        Serial.Write(" preemptions="); Serial.Number(Threads.Preemptions); Serial.Line("");
    }

    public static void Fail(string reason)
    {
        Ready = false;
        Serial.Write("XFE_NATIVE_FAIL "); Serial.Line(reason);
        Framebuffer.BootStage(100, true);
        for (;;) Native.Halt();
    }
}