mirror of
https://github.com/reactos/reactos.git
synced 2024-12-28 01:55:19 +00:00
[NTOS:KE] Rewrite KiSystemCallTrampoline in assembly
Instead of making assumptions about what the compiler does with forced-inline functions
This commit is contained in:
parent
2eaf0afcd2
commit
0d3825862f
2 changed files with 38 additions and 64 deletions
|
@ -684,71 +684,11 @@ KiDispatchException2Args(IN NTSTATUS Code,
|
|||
//
|
||||
// Performs a system call
|
||||
//
|
||||
|
||||
/*
|
||||
* This sequence does a RtlCopyMemory(Stack - StackBytes, Arguments, StackBytes)
|
||||
* and then calls the function associated with the system call.
|
||||
*
|
||||
* It's done in assembly for two reasons: we need to muck with the stack,
|
||||
* and the call itself restores the stack back for us. The only way to do
|
||||
* this in C is to do manual C handlers for every possible number of args on
|
||||
* the stack, and then have the handler issue a call by pointer. This is
|
||||
* wasteful since it'll basically push the values twice and require another
|
||||
* level of call indirection.
|
||||
*
|
||||
* The ARM kernel currently does this, but it should probably be changed
|
||||
* later to function like this as well.
|
||||
*
|
||||
*/
|
||||
#ifdef __GNUC__
|
||||
FORCEINLINE
|
||||
NTSTATUS
|
||||
KiSystemCallTrampoline(IN PVOID Handler,
|
||||
IN PVOID Arguments,
|
||||
IN ULONG StackBytes)
|
||||
{
|
||||
NTSTATUS Result;
|
||||
|
||||
__asm__ __volatile__
|
||||
(
|
||||
"subl %1, %%esp\n\t"
|
||||
"movl %%esp, %%edi\n\t"
|
||||
"movl %2, %%esi\n\t"
|
||||
"shrl $2, %1\n\t"
|
||||
"rep movsd\n\t"
|
||||
"call *%3\n\t"
|
||||
"movl %%eax, %0"
|
||||
: "=r"(Result)
|
||||
: "c"(StackBytes),
|
||||
"d"(Arguments),
|
||||
"r"(Handler)
|
||||
: "%esp", "%esi", "%edi"
|
||||
);
|
||||
return Result;
|
||||
}
|
||||
#elif defined(_MSC_VER)
|
||||
FORCEINLINE
|
||||
NTSTATUS
|
||||
KiSystemCallTrampoline(IN PVOID Handler,
|
||||
IN PVOID Arguments,
|
||||
IN ULONG StackBytes)
|
||||
{
|
||||
__asm
|
||||
{
|
||||
mov ecx, StackBytes
|
||||
mov esi, Arguments
|
||||
mov eax, Handler
|
||||
sub esp, ecx
|
||||
mov edi, esp
|
||||
shr ecx, 2
|
||||
rep movsd
|
||||
call eax
|
||||
}
|
||||
/* Return with result in EAX */
|
||||
}
|
||||
#else
|
||||
#error Unknown Compiler
|
||||
#endif
|
||||
NTAPI
|
||||
KiSystemCallTrampoline(_In_ PVOID Handler,
|
||||
_In_ PVOID Arguments,
|
||||
_In_ ULONG StackBytes);
|
||||
|
||||
|
||||
//
|
||||
|
|
|
@ -220,4 +220,38 @@ _KiConvertToGuiThread@0:
|
|||
/* return to the caller */
|
||||
ret
|
||||
|
||||
/*
|
||||
NTSTATUS
|
||||
NTAPI
|
||||
KiSystemCallTrampoline(IN PVOID Handler,
|
||||
IN PVOID Arguments,
|
||||
IN ULONG StackBytes);
|
||||
*/
|
||||
PUBLIC _KiSystemCallTrampoline@12
|
||||
_KiSystemCallTrampoline@12:
|
||||
push ebp
|
||||
mov ebp, esp
|
||||
push esi
|
||||
push edi
|
||||
|
||||
/* Get handler */
|
||||
mov eax, [ebp + 8]
|
||||
/* Get arguments */
|
||||
mov esi, [ebp + 12]
|
||||
/* Get stack bytes */
|
||||
mov ecx, [ebp + 16]
|
||||
|
||||
/* Copy args to the stack */
|
||||
sub esp, ecx
|
||||
mov edi, esp
|
||||
shr ecx, 2
|
||||
rep movsd
|
||||
|
||||
call eax
|
||||
|
||||
pop edi
|
||||
pop esi
|
||||
leave
|
||||
|
||||
ret 12
|
||||
END
|
||||
|
|
Loading…
Reference in a new issue