Skip to content

Commit

Permalink
arch/x86: Enable UMIP, SMEP and SMAP
Browse files Browse the repository at this point in the history
  • Loading branch information
Qwinci committed Nov 1, 2023
1 parent 13a462c commit 284e657
Show file tree
Hide file tree
Showing 5 changed files with 55 additions and 4 deletions.
3 changes: 3 additions & 0 deletions src/arch/x86/cpu.h
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,9 @@ typedef struct {
bool xsave;
bool avx;
bool avx512;
bool umip;
bool smep;
bool smap;
} CpuFeatures;

extern CpuFeatures CPU_FEATURES;
Expand Down
4 changes: 4 additions & 0 deletions src/arch/x86/mem/misc.S
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,9 @@ arch_mem_copy_to_user:
mov %rax, %gs:X86TASK_HANDLER_IP_OFF
mov %rsp, %gs:X86TASK_HANDLER_SP_OFF

stac
call memcpy
clac

xor %edi, %edi
mov %rdi, %gs:X86TASK_HANDLER_IP_OFF
Expand All @@ -44,7 +46,9 @@ arch_mem_copy_to_kernel:
mov %rax, %gs:X86TASK_HANDLER_IP_OFF
mov %rsp, %gs:X86TASK_HANDLER_SP_OFF

stac
call memcpy
clac

xor %edi, %edi
mov %rdi, %gs:X86TASK_HANDLER_IP_OFF
Expand Down
4 changes: 4 additions & 0 deletions src/arch/x86/sched/usermode.S
Original file line number Diff line number Diff line change
Expand Up @@ -14,8 +14,12 @@

x86_usermode_ret:
swapgs
// rip
pop %rcx
// arg
pop %rdi
// rsp
pop %rsp

xor %eax, %eax
xor %edx, %edx
Expand Down
10 changes: 6 additions & 4 deletions src/arch/x86/sched/x86_task.c
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@ typedef struct {
void (*usermode_ret)();
void (*fn)(void*);
void* arg;
void* rsp;
u64 null_rbp;
u64 null_rip;
} UserInitStackFrame;
Expand Down Expand Up @@ -81,14 +82,15 @@ Task* arch_create_user_task(Process* process, const char* name, void (*fn)(void*
u8* stack_base = stack;
memset(stack, 0, USER_STACK_SIZE);
task->stack_base = (usize) user_stack;
stack += USER_STACK_SIZE - sizeof(UserInitStackFrame);
user_stack += USER_STACK_SIZE - sizeof(UserInitStackFrame);
stack += USER_STACK_SIZE;
user_stack += USER_STACK_SIZE;

UserInitStackFrame* frame = (UserInitStackFrame*) stack;
UserInitStackFrame* frame = (UserInitStackFrame*) (task->kernel_rsp - sizeof(UserInitStackFrame));
frame->after_switch = x86_switch_from_init;
frame->usermode_ret = x86_usermode_ret;
frame->fn = fn;
frame->arg = arg;
frame->rsp = user_stack;
frame->null_rbp = 0;
frame->null_rip = 0;

Expand All @@ -97,7 +99,7 @@ Task* arch_create_user_task(Process* process, const char* name, void (*fn)(void*
strncpy(task->common.name, name, sizeof(task->common.name));
task->common.status = TASK_STATUS_READY;

task->rsp = (usize) user_stack;
task->rsp = (usize) frame;
task->common.level = SCHED_MAX_LEVEL - 1;
task->user = true;
task->common.priority = 0;
Expand Down
38 changes: 38 additions & 0 deletions src/arch/x86/smp.c
Original file line number Diff line number Diff line change
Expand Up @@ -109,6 +109,19 @@ static void init_simd() {

init_simd();

u64 cr4;
__asm__ volatile("mov %%cr4, %0" : "=r"(cr4));
if (CPU_FEATURES.umip) {
cr4 |= 1 << 11;
}
if (CPU_FEATURES.smep) {
cr4 |= 1 << 20;
}
if (CPU_FEATURES.smap) {
cr4 |= 1 << 21;
}
__asm__ volatile("mov %0, %%cr4" : : "r"(cr4));

lapic_init();
lapic_timer_init();

Expand Down Expand Up @@ -145,6 +158,16 @@ static void detect_cpu_features() {

CPU_FEATURES.xsave_area_size = cpuid(0xD, 0).ecx;
}
info = cpuid(7, 0);
if (info.ecx & 1 << 2) {
CPU_FEATURES.umip = true;
}
if (info.ebx & 1 << 7) {
CPU_FEATURES.smep = true;
}
if (info.ebx & 1 << 20) {
CPU_FEATURES.smap = true;
}
}

void arch_init_smp() {
Expand Down Expand Up @@ -180,6 +203,21 @@ void arch_init_smp() {
kprintf("[kernel][timer]: apic frequency %uhz\n", CPUS[0].lapic_timer.freq);

init_simd();
u64 cr4;
__asm__ volatile("mov %%cr4, %0" : "=r"(cr4));
if (CPU_FEATURES.umip) {
kprintf("[kernel][x86]: enabling UMIP\n");
cr4 |= 1 << 11;
}
if (CPU_FEATURES.smep) {
kprintf("[kernel][x86]: enabling SMEP\n");
cr4 |= 1 << 20;
}
if (CPU_FEATURES.smap) {
kprintf("[kernel][x86]: enabling SMAP\n");
cr4 |= 1 << 21;
}
__asm__ volatile("mov %0, %%cr4" : : "r"(cr4));

x86_init_usermode();
sched_init(true);
Expand Down

0 comments on commit 284e657

Please sign in to comment.