mirror of
https://github.com/subhobhai943/SUB-OS.git
synced 2026-10-25 16:52:29 +00:00
SUB-OS had a syscall table and user GDT descriptors but nothing that could actually leave ring 0: lazybox and the shell run as kernel code, and syscall_handler() was never reachable from a user program. This adds the missing path end to end on x86_64. Address spaces (arch/x86_64/mm/vmspace.c) - The boot page tables identity-map the low 4 GB off PML4[0] and leave the rest empty, so userland is given its own PML4 slot (512 GiB) rather than holes punched in the kernel's 2 MB huge-page map. A process PML4 shares entry 0 with the kernel and privately owns entry 1. - Frames outside the identity map are refused rather than written through an unmapped pointer; lifting that needs a recursive map or a higher-half direct map, which is noted in the file. ELF loader (kernel/elf.c) - Validates ELF64/little-endian/ET_EXEC/machine, bounds-checks every program header against both the image and the user address range, and lays PT_LOAD segments into an address space. Frames arrive zeroed, so .bss is covered. Ring transition (arch/x86_64/cpu/usermode.asm) - user_enter() drops to ring 3 via iretq after scrubbing every GPR, and user_return() unwinds back to it when the process exits, so exec looks like a call that blocks until the program finishes. Syscalls - INT 0x80 installed at DPL 3 with the Linux x86_64 register convention. The process gets its own kernel stack for the trap, because TSS.rsp0 must not point at the stack user_enter() is standing on. - Every user pointer is range-checked before use. The process page tables are still live during a syscall, so without that check a program could pass a kernel address and have write(2) dump kernel text to the console. The new /sbin/init asserts both a wild pointer and a kernel pointer are rejected. - write(2) to stdout/stderr routes through the new console_write(), which reuses printk's routing so output reaches serial and the framebuffer console rather than only the VGA text buffer. Faults - A ring 3 exception now kills that process and reports CR2 instead of panicking the machine. Userland (userland/init/) - /sbin/init is a real freestanding static executable, linked at the user base and embedded in the kernel image by scripts/mkblob.py. It reports its pid, verifies .bss was zeroed and .data is writable, checks the two pointer rejections, and exits. aarch64 and armv8i keep building: the loader and exec path are portable, and those ports get honest vmspace stubs that fail cleanly rather than pretending to run a program with kernel privileges. Verified under QEMU: init loads at 0x80004000a0, reports pid 1, .bss zeroed, .data writable, both bad pointers rejected, and exits 0 back into the shell. Co-Authored-By: Claude Opus 5 <[email protected]> Claude-Session: https://claude.ai/code/session_0161Jh7uCEMLYEMNPsjC1LKf
143 lines
2.9 KiB
NASM
143 lines
2.9 KiB
NASM
[BITS 64]
|
|
|
|
extern isr_handler_common
|
|
global isr_stub_table
|
|
global isr_stub_default
|
|
global isr_stub_syscall
|
|
|
|
%macro ISR_NOERRCODE 1
|
|
isr_stub_%1:
|
|
push qword 0 ; Dummy error code
|
|
push qword %1 ; Interrupt vector number
|
|
jmp isr_common_stub
|
|
%endmacro
|
|
|
|
%macro ISR_ERRCODE 1
|
|
isr_stub_%1:
|
|
push qword %1 ; Interrupt vector number (error code already on stack)
|
|
jmp isr_common_stub
|
|
%endmacro
|
|
|
|
section .text
|
|
|
|
; CPU Exceptions 0-31
|
|
ISR_NOERRCODE 0
|
|
ISR_NOERRCODE 1
|
|
ISR_NOERRCODE 2
|
|
ISR_NOERRCODE 3
|
|
ISR_NOERRCODE 4
|
|
ISR_NOERRCODE 5
|
|
ISR_NOERRCODE 6
|
|
ISR_NOERRCODE 7
|
|
ISR_ERRCODE 8
|
|
ISR_NOERRCODE 9
|
|
ISR_ERRCODE 10
|
|
ISR_ERRCODE 11
|
|
ISR_ERRCODE 12
|
|
ISR_ERRCODE 13
|
|
ISR_ERRCODE 14
|
|
ISR_NOERRCODE 15
|
|
ISR_NOERRCODE 16
|
|
ISR_ERRCODE 17
|
|
ISR_NOERRCODE 18
|
|
ISR_NOERRCODE 19
|
|
ISR_NOERRCODE 20
|
|
ISR_NOERRCODE 21
|
|
ISR_NOERRCODE 22
|
|
ISR_NOERRCODE 23
|
|
ISR_NOERRCODE 24
|
|
ISR_NOERRCODE 25
|
|
ISR_NOERRCODE 26
|
|
ISR_NOERRCODE 27
|
|
ISR_NOERRCODE 28
|
|
ISR_NOERRCODE 29
|
|
ISR_ERRCODE 30
|
|
ISR_NOERRCODE 31
|
|
|
|
; Hardware IRQs 32-47
|
|
ISR_NOERRCODE 32
|
|
ISR_NOERRCODE 33
|
|
ISR_NOERRCODE 34
|
|
ISR_NOERRCODE 35
|
|
ISR_NOERRCODE 36
|
|
ISR_NOERRCODE 37
|
|
ISR_NOERRCODE 38
|
|
ISR_NOERRCODE 39
|
|
ISR_NOERRCODE 40
|
|
ISR_NOERRCODE 41
|
|
ISR_NOERRCODE 42
|
|
ISR_NOERRCODE 43
|
|
ISR_NOERRCODE 44
|
|
ISR_NOERRCODE 45
|
|
ISR_NOERRCODE 46
|
|
ISR_NOERRCODE 47
|
|
|
|
; Software syscall gate. Reached by INT 0x80 from ring 3, so its IDT entry is
|
|
; installed with DPL 3; the CPU switches to TSS.rsp0 on the way in, which the
|
|
; exec path points at a kernel stack owned by the running process.
|
|
isr_stub_syscall:
|
|
push qword 0 ; No error code is pushed for a software interrupt
|
|
push qword 128 ; Vector number, matching the IDT slot
|
|
jmp isr_common_stub
|
|
|
|
isr_stub_default:
|
|
push qword 0
|
|
push qword 255
|
|
jmp isr_common_stub
|
|
|
|
isr_common_stub:
|
|
push rax
|
|
push rbx
|
|
push rcx
|
|
push rdx
|
|
push rsi
|
|
push rdi
|
|
push rbp
|
|
push r8
|
|
push r9
|
|
push r10
|
|
push r11
|
|
push r12
|
|
push r13
|
|
push r14
|
|
push r15
|
|
|
|
mov rdi, rsp
|
|
cld
|
|
call isr_handler_common
|
|
|
|
pop r15
|
|
pop r14
|
|
pop r13
|
|
pop r12
|
|
pop r11
|
|
pop r10
|
|
pop r9
|
|
pop r8
|
|
pop rbp
|
|
pop rdi
|
|
pop rsi
|
|
pop rdx
|
|
pop rcx
|
|
pop rbx
|
|
pop rax
|
|
|
|
add rsp, 16
|
|
iretq
|
|
|
|
section .data
|
|
align 8
|
|
isr_stub_table:
|
|
dq isr_stub_0, isr_stub_1, isr_stub_2, isr_stub_3
|
|
dq isr_stub_4, isr_stub_5, isr_stub_6, isr_stub_7
|
|
dq isr_stub_8, isr_stub_9, isr_stub_10, isr_stub_11
|
|
dq isr_stub_12, isr_stub_13, isr_stub_14, isr_stub_15
|
|
dq isr_stub_16, isr_stub_17, isr_stub_18, isr_stub_19
|
|
dq isr_stub_20, isr_stub_21, isr_stub_22, isr_stub_23
|
|
dq isr_stub_24, isr_stub_25, isr_stub_26, isr_stub_27
|
|
dq isr_stub_28, isr_stub_29, isr_stub_30, isr_stub_31
|
|
dq isr_stub_32, isr_stub_33, isr_stub_34, isr_stub_35
|
|
dq isr_stub_36, isr_stub_37, isr_stub_38, isr_stub_39
|
|
dq isr_stub_40, isr_stub_41, isr_stub_42, isr_stub_43
|
|
dq isr_stub_44, isr_stub_45, isr_stub_46, isr_stub_47
|