diff --git a/SystemCalls/Native.cpp b/SystemCalls/Native.cpp index 2e6df15..7d44bc4 100644 --- a/SystemCalls/Native.cpp +++ b/SystemCalls/Native.cpp @@ -372,9 +372,22 @@ static int sys_fork(SyscallsFrame *Frame) strncpy(NewThread->Name, Thread->Name, sizeof(Thread->Name)); NewThread->Info = Thread->Info; + NewThread->ShadowGSBase = Thread->ShadowGSBase; NewThread->GSBase = Thread->GSBase; NewThread->FSBase = Thread->FSBase; - TaskManager->Sleep(10); /* Re-schedule */ + + CriticalSection cs; + static int RetChild = 0; + +#if defined(a86) + asmv("int $0x30"); /* This will trigger the IRQ16 instantly so we won't execute the next instruction */ +#elif defined(aa64) + asmv("svc #0x30"); /* This will trigger the IRQ16 instantly so we won't execute the next instruction */ +#endif + if (RetChild--) + return 0; + RetChild = 1; + NewThread->Registers = Thread->Registers; debug("Forked thread \"%s\"(%d) from process \"%s\"(%d)", NewThread->Name, NewThread->ID, NewProcess->Name, NewProcess->ID); diff --git a/Tasking/Scheduler.cpp b/Tasking/Scheduler.cpp index 7d41026..7a81521 100644 --- a/Tasking/Scheduler.cpp +++ b/Tasking/Scheduler.cpp @@ -522,6 +522,7 @@ namespace Tasking { CurrentCPU->CurrentThread->Registers = *Frame; CPU::x64::fxsave(CurrentCPU->CurrentThread->FPU); + CurrentCPU->CurrentThread->ShadowGSBase = CPU::x64::rdmsr(CPU::x64::MSR_SHADOW_GS_BASE); CurrentCPU->CurrentThread->GSBase = CPU::x64::rdmsr(CPU::x64::MSR_GS_BASE); CurrentCPU->CurrentThread->FSBase = CPU::x64::rdmsr(CPU::x64::MSR_FS_BASE); @@ -604,6 +605,7 @@ namespace Tasking asmv("movq %cr3, %rax"); asmv("movq %rax, %cr3"); CPU::x64::fxrstor(CurrentCPU->CurrentThread->FPU); + CPU::x64::wrmsr(CPU::x64::MSR_SHADOW_GS_BASE, CurrentCPU->CurrentThread->ShadowGSBase); CPU::x64::wrmsr(CPU::x64::MSR_GS_BASE, CurrentCPU->CurrentThread->GSBase); CPU::x64::wrmsr(CPU::x64::MSR_FS_BASE, CurrentCPU->CurrentThread->FSBase); diff --git a/Tasking/Task.cpp b/Tasking/Task.cpp index db930d3..49e81e5 100644 --- a/Tasking/Task.cpp +++ b/Tasking/Task.cpp @@ -429,6 +429,7 @@ namespace Tasking Thread->Stack = new Memory::StackGuard(false, Parent->PageTable); #if defined(a64) SecurityManager.TrustToken(Thread->Security.UniqueToken, TTL::TrustedByKernel); + Thread->ShadowGSBase = CPU::x64::rdmsr(CPU::x64::MSRID::MSR_SHADOW_GS_BASE); Thread->GSBase = CPU::x64::rdmsr(CPU::x64::MSRID::MSR_GS_BASE); Thread->FSBase = CPU::x64::rdmsr(CPU::x64::MSRID::MSR_FS_BASE); Thread->Registers.cs = GDT_KERNEL_CODE; @@ -448,6 +449,7 @@ namespace Tasking Thread->Stack = new Memory::StackGuard(true, Parent->PageTable); #if defined(a64) SecurityManager.TrustToken(Thread->Security.UniqueToken, TTL::Untrusted); + Thread->ShadowGSBase = CPU::x64::rdmsr(CPU::x64::MSRID::MSR_SHADOW_GS_BASE); Thread->GSBase = 0; Thread->FSBase = 0; Thread->Registers.cs = GDT_USER_CODE; diff --git a/include/task.hpp b/include/task.hpp index 0d92a00..36989ec 100644 --- a/include/task.hpp +++ b/include/task.hpp @@ -120,7 +120,7 @@ namespace Tasking TaskStatus Status; #if defined(a64) CPU::x64::TrapFrame Registers; - uint64_t GSBase, FSBase; + uint64_t ShadowGSBase, GSBase, FSBase; #elif defined(a32) CPU::x32::TrapFrame Registers; // TODO uint64_t GSBase, FSBase;