SysCall: Refactored data segment selectors' switching.

This commit is contained in:
Mikhail Krichanov 2024-03-08 12:12:00 +03:00
parent 6c8b19286d
commit eba7b947da
2 changed files with 25 additions and 34 deletions

View File

@ -144,8 +144,8 @@ typedef struct {
// Stack: // Stack:
// rsp - User Rsp // rsp - User Rsp
// rbp - User Rbp // rbp - User Rbp
// rcx - Rip for SYSCALL // rcx - User Rip for SYSCALL
// r11 - User data segment selector // r11 - User RFLAGS for SYSCALL
// r9 - Argument 3 // r9 - Argument 3
// r8 - Argument 2 // r8 - Argument 2
// rdx - Argument 1 <- CoreRbp // rdx - Argument 1 <- CoreRbp

View File

@ -94,6 +94,19 @@ copy:
ret ret
%macro SetRing3DataSegmentSelectors 0
mov rcx, MSR_IA32_STAR
call ASM_PFX(AsmReadMsr64)
; rax = ((RING3_CODE64_SEL - 16) << 16 | RING0_CODE64_SEL) << 32
shr rax, 48
add rax, 8
mov ds, ax
mov es, ax
mov fs, ax
mov gs, ax
%endmacro
;------------------------------------------------------------------------------ ;------------------------------------------------------------------------------
; EFI_STATUS ; EFI_STATUS
; EFIAPI ; EFIAPI
@ -114,9 +127,6 @@ copy:
global ASM_PFX(CoreBootServices) global ASM_PFX(CoreBootServices)
ASM_PFX(CoreBootServices): ASM_PFX(CoreBootServices):
cli cli
; Save User data segment selector temporarily in R11.
mov r11, ds
; Switch from User to Core data segment selectors. ; Switch from User to Core data segment selectors.
mov ax, ss mov ax, ss
mov ds, ax mov ds, ax
@ -136,7 +146,7 @@ ASM_PFX(CoreBootServices):
push rbp push rbp
; Save return address for SYSRET. ; Save return address for SYSRET.
push rcx push rcx
; Save User data segment selector. ; Save User RFLAGS for SYSRET.
push r11 push r11
; Save User Arguments [1..3]. ; Save User Arguments [1..3].
push r9 push r9
@ -152,24 +162,20 @@ ASM_PFX(CoreBootServices):
sti sti
call ASM_PFX(CallBootService) call ASM_PFX(CallBootService)
push rax
cli cli
SetRing3DataSegmentSelectors
pop rax
; Step over Arguments [1..3]. ; Step over Arguments [1..3].
add rsp, 8*3 add rsp, 8*3
; Switch from Core to User data segment selectors.
pop r11
o16 mov ds, r11
o16 mov es, r11
o16 mov fs, r11
o16 mov gs, r11
; Prepare SYSRET arguments. ; Prepare SYSRET arguments.
pop rcx
pushfq
pop r11 pop r11
pop rcx
; Switch to User Stack. ; Switch to User Stack.
pop rbp pop rbp
@ -194,31 +200,16 @@ global ASM_PFX(CallRing3)
ASM_PFX(CallRing3): ASM_PFX(CallRing3):
cli cli
; Save input Arguments. ; Save input Arguments.
push r12 push rcx
mov r12, rcx
; Extract User Data selector. SetRing3DataSegmentSelectors
mov rcx, MSR_IA32_STAR
call ASM_PFX(AsmReadMsr64)
; rax = ((RING3_CODE64_SEL - 16) << 16 | RING0_CODE64_SEL) << 32
shr rax, 48
add rax, 8
; Set Data selectors
mov ds, ax
mov es, ax
mov fs, ax
mov gs, ax
; Prepare SYSRET arguments. ; Prepare SYSRET arguments.
mov rcx, [gRing3EntryPoint] mov rcx, [gRing3EntryPoint]
mov rdx, r12 pop rdx
pushfq pushfq
pop r11 pop r11
; Restore stack and registers.
pop r12
; Save Core Stack pointers and switch to User Stack. ; Save Core Stack pointers and switch to User Stack.
mov [ASM_PFX(CoreRsp)], rsp mov [ASM_PFX(CoreRsp)], rsp
mov [ASM_PFX(CoreRbp)], rbp mov [ASM_PFX(CoreRbp)], rbp