The scheduler's create_process now sets up the stack to iretq into a load_process function, which will load the process image into memory from within the process' own virtual memory space. Currently this loading is just copying the old 'taskA' function from kernel space.
225 lines
3.1 KiB
ArmAsm
225 lines
3.1 KiB
ArmAsm
extern g_idtr
|
|
extern g_gdtr
|
|
|
|
global idt_write
|
|
idt_write:
|
|
lidt [rel g_idtr]
|
|
ret
|
|
|
|
global idt_load
|
|
idt_load:
|
|
sidt [rel g_idtr]
|
|
ret
|
|
|
|
global gdt_write
|
|
gdt_write:
|
|
lgdt [rel g_gdtr]
|
|
mov ax, si ; second arg is data segment
|
|
mov ds, ax
|
|
mov es, ax
|
|
mov fs, ax
|
|
mov gs, ax
|
|
mov ss, ax
|
|
push qword rdi ; first arg is code segment
|
|
lea rax, [rel .next]
|
|
push rax
|
|
o64 retf
|
|
.next:
|
|
ltr dx
|
|
ret
|
|
|
|
global gdt_load
|
|
gdt_load:
|
|
sgdt [rel g_gdtr]
|
|
ret
|
|
|
|
%macro push_all_and_segments 0
|
|
push rax
|
|
push rcx
|
|
push rdx
|
|
push rbx
|
|
push rbp
|
|
push rsi
|
|
push rdi
|
|
|
|
push r8
|
|
push r9
|
|
push r10
|
|
push r11
|
|
push r12
|
|
push r13
|
|
push r14
|
|
push r15
|
|
|
|
mov ax, ds
|
|
push rax
|
|
%endmacro
|
|
|
|
%macro pop_all_and_segments 0
|
|
pop rax
|
|
mov ds, ax
|
|
mov es, ax
|
|
mov fs, ax
|
|
mov gs, ax
|
|
|
|
pop r15
|
|
pop r14
|
|
pop r13
|
|
pop r12
|
|
pop r11
|
|
pop r10
|
|
pop r9
|
|
pop r8
|
|
|
|
pop rdi
|
|
pop rsi
|
|
pop rbp
|
|
pop rbx
|
|
pop rdx
|
|
pop rcx
|
|
pop rax
|
|
%endmacro
|
|
|
|
extern isr_handler
|
|
global isr_handler_prelude
|
|
isr_handler_prelude:
|
|
push_all_and_segments
|
|
|
|
mov rdi, rsp
|
|
call isr_handler
|
|
mov rsp, rax
|
|
|
|
pop_all_and_segments
|
|
|
|
add rsp, 16 ; because the ISRs added err/num
|
|
sti
|
|
iretq
|
|
|
|
extern irq_handler
|
|
global irq_handler_prelude
|
|
irq_handler_prelude:
|
|
push_all_and_segments
|
|
|
|
mov rdi, rsp
|
|
call irq_handler
|
|
mov rsp, rax
|
|
|
|
pop_all_and_segments
|
|
|
|
add rsp, 16 ; because the ISRs added err/num
|
|
sti
|
|
iretq
|
|
|
|
%macro EMIT_ISR 2
|
|
global %1
|
|
%1:
|
|
cli
|
|
push 0
|
|
push %2
|
|
jmp isr_handler_prelude
|
|
%endmacro
|
|
|
|
%macro EMIT_EISR 2
|
|
global %1
|
|
%1:
|
|
cli
|
|
push %2
|
|
jmp isr_handler_prelude
|
|
%endmacro
|
|
|
|
%macro EMIT_IRQ 2
|
|
global %1
|
|
%1:
|
|
cli
|
|
push 0
|
|
push %2
|
|
jmp irq_handler_prelude
|
|
%endmacro
|
|
|
|
%define EISR(i, name) EMIT_EISR name, i
|
|
%define ISR(i, name) EMIT_ISR name, i
|
|
%define IRQ(i, q, name) EMIT_IRQ name, i
|
|
|
|
section .isrs
|
|
%include "interrupt_isrs.inc"
|
|
|
|
extern syscall_handler
|
|
syscall_handler_prelude:
|
|
push 0 ; ss, doesn't matter here
|
|
push rsp
|
|
pushf
|
|
push 0 ; cs, doesn't matter here
|
|
push rcx ; user rip
|
|
push 0 ; bogus interrupt
|
|
push 0 ; bogus errorcode
|
|
push_all_and_segments
|
|
|
|
mov rdi, rsp
|
|
call syscall_handler
|
|
mov rsp, rax
|
|
|
|
pop_all_and_segments
|
|
add rsp, 16 ; ignore bogus interrupt / error
|
|
pop rcx ; user rip
|
|
add rsp, 32 ; ignore cs, flags, rsp, ss
|
|
|
|
o64 sysret
|
|
|
|
global syscall_enable
|
|
syscall_enable:
|
|
; IA32_EFER - set bit 0, syscall enable
|
|
mov rcx, 0xc0000080
|
|
rdmsr
|
|
or rax, 0x1
|
|
wrmsr
|
|
|
|
; IA32_STAR - cs for syscall
|
|
mov rcx, 0xc0000081
|
|
mov rax, 0 ; not used
|
|
mov rdx, 0x00180008 ; GDT:3 (user code), GDT:1 (kernel code)
|
|
wrmsr
|
|
|
|
; IA32_LSTAR - RIP for syscall
|
|
mov rcx, 0xc0000082
|
|
lea rax, [rel syscall_handler_prelude]
|
|
mov rdx, rax
|
|
shr rdx, 32
|
|
wrmsr
|
|
|
|
; IA32_FMASK - FLAGS mask inside syscall
|
|
mov rcx, 0xc0000084
|
|
mov rax, 0x200
|
|
mov rdx, 0
|
|
wrmsr
|
|
|
|
ret
|
|
|
|
extern load_process
|
|
global ramdisk_process_loader
|
|
ramdisk_process_loader:
|
|
|
|
; create_process already pushed a cpu_state onto the stack for us, this
|
|
; acts both as the cpu_state parameter to load_process, and the saved
|
|
; state for the following iretq
|
|
mov rdi, rax
|
|
mov rsi, rbx
|
|
call load_process
|
|
|
|
pop_all_and_segments
|
|
add rsp, 16 ; because the ISRs add err/num
|
|
iretq
|
|
|
|
|
|
global taskA
|
|
taskA:
|
|
push rbp
|
|
mov rbp, rsp
|
|
mov rax, 0xaaaaaaaaaaaaaaaa
|
|
|
|
.loop:
|
|
syscall
|
|
jmp .loop
|
|
|
|
global taskAend
|
|
taskAend:
|