mirror of
https://github.com/acidanthera/audk.git
synced 2025-04-07 19:45:07 +02:00
Ring3: Added helper function AllocateCoreCopy(), refactored SysCall.
This commit is contained in:
parent
87a397740d
commit
de01af7081
@ -90,7 +90,8 @@ EFI_BOOT_SERVICES mBootServices = {
|
||||
(EFI_COPY_MEM)CopyMem, // CopyMem
|
||||
(EFI_SET_MEM)SetMem, // SetMem
|
||||
(EFI_CREATE_EVENT_EX)CoreCreateEventEx, // CreateEventEx
|
||||
(EFI_ALLOCATE_RING3_PAGES)AllocateRing3Pages
|
||||
(EFI_ALLOCATE_RING3_PAGES)AllocateRing3Pages,
|
||||
(EFI_ALLOCATE_CORE_COPY)AllocateCopyPool
|
||||
};
|
||||
|
||||
EFI_DXE_SERVICES mDxeServices = {
|
||||
|
@ -6599,6 +6599,7 @@ AsmReadEflags (
|
||||
UINTN
|
||||
EFIAPI
|
||||
CoreBootServices (
|
||||
IN UINT8 Type,
|
||||
IN UINTN FunctionAddress,
|
||||
...
|
||||
);
|
||||
|
@ -220,6 +220,13 @@ EFI_STATUS
|
||||
IN OUT VOID **Memory
|
||||
);
|
||||
|
||||
typedef
|
||||
VOID *
|
||||
(EFIAPI *EFI_ALLOCATE_CORE_COPY)(
|
||||
IN UINTN AllocationSize,
|
||||
IN CONST VOID *Buffer
|
||||
);
|
||||
|
||||
/**
|
||||
Frees memory pages.
|
||||
|
||||
@ -2019,6 +2026,7 @@ typedef struct {
|
||||
EFI_SET_MEM SetMem;
|
||||
EFI_CREATE_EVENT_EX CreateEventEx;
|
||||
EFI_ALLOCATE_RING3_PAGES AllocateRing3Pages;
|
||||
EFI_ALLOCATE_CORE_COPY AllocateCoreCopy;
|
||||
} EFI_BOOT_SERVICES;
|
||||
|
||||
///
|
||||
|
@ -93,22 +93,27 @@ ASM_PFX(InternalEnterUserImage):
|
||||
retfq
|
||||
|
||||
;------------------------------------------------------------------------------
|
||||
; UINTN
|
||||
; EFIAPI
|
||||
; CoreBootServices (
|
||||
; IN UINTN FunctionAddress,
|
||||
; ...
|
||||
; );
|
||||
;
|
||||
; (rcx) RIP of the next instruction saved by SYSCALL in SysCall().
|
||||
; (rdx) Argument 1 of the called function.
|
||||
; (r8) Argument 2 of the called function.
|
||||
; (r9) Argument 3 of the called function.
|
||||
; (r10) FunctionAddress.
|
||||
; (r11) RFLAGS saved by SYSCALL in SysCall().
|
||||
;On stack Argument 4, 5, ...
|
||||
; typedef enum {
|
||||
; SysCallReadMemory = 0,
|
||||
; SysCallAllocateRing3Pages = 1,
|
||||
; SysCallAllocateCoreCopy = 2,
|
||||
; SysCallLocateProtocol = 3,
|
||||
; SysCallMax
|
||||
; } SYS_CALL_TYPE;
|
||||
;------------------------------------------------------------------------------
|
||||
|
||||
%define READ_MEMORY 0
|
||||
%define ALLOCATE_RING3_PAGES 1
|
||||
%define ALLOCATE_CORE_COPY 2
|
||||
%define LOCATE_PROTOCOL 3
|
||||
|
||||
%macro CallSysRet 0
|
||||
; Prepare SYSRET arguments.
|
||||
pop rcx
|
||||
|
||||
; Switch from Core to User data segment selectors.
|
||||
pop r11
|
||||
|
||||
o16 mov ds, r11
|
||||
o16 mov es, r11
|
||||
o16 mov fs, r11
|
||||
@ -128,11 +133,45 @@ o64 sysret
|
||||
; SYSRET copies the value in RCX into RIP and loads RFLAGS from R11.
|
||||
%endmacro
|
||||
|
||||
%macro DisableSMAP 0
|
||||
pushfq
|
||||
pop rcx
|
||||
or rcx, 0x40000 ; Set AC (bit 18)
|
||||
push rcx
|
||||
popfq
|
||||
%endmacro
|
||||
|
||||
%macro EnableSMAP 0
|
||||
pushfq
|
||||
pop rcx
|
||||
and rcx, ~0x40000 ; Clear AC (bit 18)
|
||||
push rcx
|
||||
popfq
|
||||
%endmacro
|
||||
|
||||
;------------------------------------------------------------------------------
|
||||
; UINTN
|
||||
; EFIAPI
|
||||
; CoreBootServices (
|
||||
; IN UINT8 Type,
|
||||
; IN UINTN FunctionAddress,
|
||||
; ...
|
||||
; );
|
||||
;
|
||||
; (rcx) RIP of the next instruction saved by SYSCALL in SysCall().
|
||||
; (rdx) FunctionAddress.
|
||||
; (r8) Argument 1 of the called function.
|
||||
; (r9) Argument 2 of the called function.
|
||||
; (r10) Type.
|
||||
; (r11) RFLAGS saved by SYSCALL in SysCall().
|
||||
;On stack Argument 3, 4, ...
|
||||
;------------------------------------------------------------------------------
|
||||
global ASM_PFX(CoreBootServices)
|
||||
ASM_PFX(CoreBootServices):
|
||||
; Save User data segment selector.
|
||||
; Save User data segment selector temporarily in R11.
|
||||
mov r11, ds
|
||||
|
||||
; Switch from User to Core data segment selectors.
|
||||
mov ax, ss
|
||||
mov ds, ax
|
||||
mov es, ax
|
||||
@ -148,34 +187,115 @@ ASM_PFX(CoreBootServices):
|
||||
push rbp
|
||||
mov rbp, rsp
|
||||
|
||||
cmp r10, 0
|
||||
je readMemory
|
||||
; Save User data segment selector on Core SysCall Stack.
|
||||
push r11
|
||||
|
||||
; Save FunctionAddress in R11 as it will be called later.
|
||||
mov r11, rdx
|
||||
|
||||
; Save return address for SYSRET.
|
||||
push rcx
|
||||
|
||||
; Replace argument according to UEFI calling convention.
|
||||
mov rcx, rdx
|
||||
mov rdx, r8
|
||||
mov r8, r9
|
||||
; mov r9, [rax + 8*3]
|
||||
; mov r11, [rax + 8*4]
|
||||
; push r11
|
||||
; ...
|
||||
cmp r10, READ_MEMORY
|
||||
je readMemory
|
||||
|
||||
; Call Boot Service by FunctionAddress.
|
||||
call [r10]
|
||||
cmp r10, ALLOCATE_RING3_PAGES
|
||||
je allocateRing3Pages
|
||||
|
||||
; Prepare SYSRET arguments.
|
||||
pop rcx
|
||||
cmp r10, ALLOCATE_CORE_COPY
|
||||
je allocateCoreCopy
|
||||
|
||||
CallSysRet
|
||||
cmp r10, LOCATE_PROTOCOL
|
||||
je locateProtocol
|
||||
|
||||
;------------------------------------------------------------------------------
|
||||
; UINTN
|
||||
; ReadMemory (
|
||||
; IN UINTN Address
|
||||
; );
|
||||
readMemory:
|
||||
mov rax, [rdx]
|
||||
|
||||
CallSysRet
|
||||
|
||||
;------------------------------------------------------------------------------
|
||||
; EFI_STATUS
|
||||
; AllocateRing3Pages (
|
||||
; IN UINTN NumberOfPages,
|
||||
; IN OUT VOID **Memory
|
||||
; );
|
||||
allocateRing3Pages:
|
||||
; Save User (VOID **)Memory on Core SysCall Stack.
|
||||
push r9
|
||||
|
||||
; Replace argument according to UEFI calling convention.
|
||||
mov rcx, r8
|
||||
; Allocate space for (VOID *)Memory on Core SysCall Stack.
|
||||
sub rsp, 8
|
||||
mov rdx, rsp
|
||||
|
||||
; Call Boot Service by FunctionAddress.
|
||||
call [r11]
|
||||
|
||||
DisableSMAP
|
||||
|
||||
; Copy (VOID *)Memory from Core SysCall Stack to User Stack.
|
||||
pop rdx
|
||||
pop r9
|
||||
mov [r9], rdx
|
||||
|
||||
EnableSMAP
|
||||
|
||||
CallSysRet
|
||||
|
||||
;------------------------------------------------------------------------------
|
||||
; VOID *
|
||||
; AllocateCoreCopy (
|
||||
; IN UINTN AllocationSize,
|
||||
; IN CONST VOID *Buffer
|
||||
; );
|
||||
allocateCoreCopy:
|
||||
DisableSMAP
|
||||
|
||||
; Replace argument according to UEFI calling convention.
|
||||
mov rcx, r8
|
||||
mov rdx, r9
|
||||
|
||||
; Call Boot Service by FunctionAddress.
|
||||
call [r11]
|
||||
|
||||
EnableSMAP
|
||||
|
||||
CallSysRet
|
||||
|
||||
;------------------------------------------------------------------------------
|
||||
; EFI_STATUS
|
||||
; LocateProtocol (
|
||||
; IN EFI_GUID *Protocol,
|
||||
; IN VOID *Registration OPTIONAL,
|
||||
; OUT VOID **Interface
|
||||
; );
|
||||
locateProtocol:
|
||||
; Replace argument according to UEFI calling convention.
|
||||
mov rcx, r8
|
||||
mov rdx, r9
|
||||
; Allocate space for (VOID *)Interface on Core SysCall Stack.
|
||||
sub rsp, 8
|
||||
mov r8, rsp
|
||||
|
||||
; Call Boot Service by FunctionAddress.
|
||||
call [r11]
|
||||
|
||||
DisableSMAP
|
||||
|
||||
; Copy (VOID *)Interface from Core SysCall Stack to User Stack.
|
||||
pop rcx
|
||||
mov rdx, [rbp + 8] ; rdx = User rsp
|
||||
mov [rdx + 8*4], rcx ; 5th argument of SysCall (SysCallLocateProtocol)
|
||||
|
||||
EnableSMAP
|
||||
|
||||
CallSysRet
|
||||
|
||||
SECTION .data
|
||||
|
||||
|
@ -5,14 +5,22 @@
|
||||
|
||||
**/
|
||||
|
||||
typedef enum {
|
||||
SysCallReadMemory = 0,
|
||||
SysCallAllocateRing3Pages = 1,
|
||||
SysCallAllocateCoreCopy = 2,
|
||||
SysCallLocateProtocol = 3,
|
||||
SysCallMax
|
||||
} SYS_CALL_TYPE;
|
||||
|
||||
UINTN
|
||||
EFIAPI
|
||||
SysCall (
|
||||
IN UINT8 Type,
|
||||
IN UINTN FunctionAddress,
|
||||
...
|
||||
);
|
||||
|
||||
|
||||
/**
|
||||
Raise the task priority level to the new level.
|
||||
High level is implemented by disabling processor interrupts.
|
||||
|
@ -94,7 +94,7 @@ UefiBootServicesTableLibConstructor (
|
||||
// Cache pointer to the EFI Boot Services Table
|
||||
//
|
||||
mCoreBS = (EFI_BOOT_SERVICES *)SysCall (
|
||||
0,
|
||||
SysCallReadMemory,
|
||||
(UINTN)SystemTable + OFFSET_OF (EFI_SYSTEM_TABLE, BootServices)
|
||||
);
|
||||
ASSERT (mCoreBS != NULL);
|
||||
@ -504,16 +504,31 @@ EFI_STATUS
|
||||
EFIAPI
|
||||
Ring3LocateProtocol (
|
||||
IN EFI_GUID *Protocol,
|
||||
IN VOID *Registration OPTIONAL,
|
||||
IN VOID *CoreRegistration OPTIONAL,
|
||||
OUT VOID **Interface
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
EFI_STATUS Status;
|
||||
EFI_GUID *CoreProtocol;
|
||||
|
||||
EFI_DEVICE_PATH_UTILITIES_PROTOCOL *UserProtocol;
|
||||
|
||||
CoreProtocol = (VOID *)SysCall (
|
||||
SysCallAllocateCoreCopy,
|
||||
(UINTN)mCoreBS + OFFSET_OF (EFI_BOOT_SERVICES, AllocateCoreCopy),
|
||||
sizeof (EFI_GUID),
|
||||
Protocol
|
||||
);
|
||||
if (CoreProtocol == NULL) {
|
||||
DEBUG ((DEBUG_ERROR, "Ring3: Failed to allocate core copy of the Protocol variable.\n"));
|
||||
return EFI_OUT_OF_RESOURCES;
|
||||
}
|
||||
|
||||
Status = (EFI_STATUS)SysCall (
|
||||
SysCallLocateProtocol,
|
||||
(UINTN)mCoreBS + OFFSET_OF (EFI_BOOT_SERVICES, LocateProtocol),
|
||||
Protocol,
|
||||
Registration,
|
||||
CoreProtocol,
|
||||
CoreRegistration,
|
||||
Interface
|
||||
);
|
||||
if (EFI_ERROR (Status)) {
|
||||
@ -522,11 +537,10 @@ Ring3LocateProtocol (
|
||||
}
|
||||
|
||||
if (CompareGuid (Protocol, &gEfiDevicePathUtilitiesProtocolGuid)) {
|
||||
EFI_DEVICE_PATH_UTILITIES_PROTOCOL *UserProtocol;
|
||||
|
||||
mCoreDevicePathUtilitiesProtocol = (EFI_DEVICE_PATH_UTILITIES_PROTOCOL *)*Interface;
|
||||
|
||||
Status = (EFI_STATUS)SysCall (
|
||||
SysCallAllocateRing3Pages,
|
||||
(UINTN)mCoreBS + OFFSET_OF (EFI_BOOT_SERVICES, AllocateRing3Pages),
|
||||
EFI_SIZE_TO_PAGES (sizeof (EFI_DEVICE_PATH_UTILITIES_PROTOCOL)),
|
||||
(VOID **)&UserProtocol
|
||||
|
@ -10,13 +10,14 @@
|
||||
; UINTN
|
||||
; EFIAPI
|
||||
; SysCall (
|
||||
; IN UINT8 Type,
|
||||
; IN UINTN FunctionAddress,
|
||||
; ...
|
||||
; );
|
||||
;------------------------------------------------------------------------------
|
||||
global ASM_PFX(SysCall)
|
||||
ASM_PFX(SysCall):
|
||||
; Save FunctionAddress for CoreBootServices().
|
||||
; Save Type for CoreBootServices().
|
||||
mov r10, rcx
|
||||
|
||||
; SYSCALL saves RFLAGS into R11 and the RIP of the next instruction into RCX.
|
||||
|
Loading…
x
Reference in New Issue
Block a user