You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
374 lines
9.9 KiB
374 lines
9.9 KiB
title "Thunks"
|
|
;++
|
|
;
|
|
; Copyright (c) 1989 Microsoft Corporation
|
|
;
|
|
; Module Name:
|
|
;
|
|
; thunk.asm
|
|
;
|
|
; Abstract:
|
|
;
|
|
; This module implements all Win32 thunks. This includes the
|
|
; first level thread starter...
|
|
;
|
|
; Author:
|
|
;
|
|
; Mark Lucovsky (markl) 28-Sep-1990
|
|
;
|
|
; Revision History:
|
|
;
|
|
;--
|
|
.586p
|
|
.xlist
|
|
include ks386.inc
|
|
include callconv.inc
|
|
.list
|
|
_DATA SEGMENT DWORD PUBLIC 'DATA'
|
|
|
|
_BasepTickCountMultiplier dd 0d1b71759H
|
|
|
|
_DATA ENDS
|
|
|
|
|
|
_TEXT SEGMENT PARA PUBLIC 'CODE'
|
|
ASSUME DS:FLAT, ES:FLAT, SS:NOTHING, FS:NOTHING, GS:NOTHING
|
|
|
|
page ,132
|
|
subttl "BaseThreadStartThunk"
|
|
;++
|
|
;
|
|
; VOID
|
|
; BaseThreadStartThunk(
|
|
; IN PTHREAD_START_ROUTINE StartRoutine,
|
|
; IN PVOID ThreadParameter
|
|
; )
|
|
;
|
|
; Routine Description:
|
|
;
|
|
; This function calls to the portable thread starter after moving
|
|
; its arguments from registers to the stack.
|
|
;
|
|
; Arguments:
|
|
;
|
|
; EAX - StartRoutine
|
|
; EBX - ThreadParameter
|
|
;
|
|
; Return Value:
|
|
;
|
|
; Never Returns
|
|
;
|
|
;--
|
|
|
|
EXTRNP _BaseThreadStart,2
|
|
cPublicProc _BaseThreadStartThunk,2
|
|
|
|
xor ebp,ebp
|
|
push ebx
|
|
push eax
|
|
push 0
|
|
jmp _BaseThreadStart@8
|
|
|
|
stdENDP _BaseThreadStartThunk
|
|
|
|
;++
|
|
;
|
|
; VOID
|
|
; BaseProcessStartThunk(
|
|
; IN LPVOID lpProcessStartAddress,
|
|
; IN LPVOID lpParameter
|
|
; );
|
|
;
|
|
; Routine Description:
|
|
;
|
|
; This function calls the process starter after moving
|
|
; its arguments from registers to the stack.
|
|
;
|
|
; Arguments:
|
|
;
|
|
; EAX - StartRoutine
|
|
; EBX - ProcessParameter
|
|
;
|
|
; Return Value:
|
|
;
|
|
; Never Returns
|
|
;
|
|
;--
|
|
|
|
EXTRNP _BaseProcessStart,1
|
|
cPublicProc _BaseProcessStartThunk,2
|
|
|
|
xor ebp,ebp
|
|
push eax
|
|
push 0
|
|
jmp _BaseProcessStart@4
|
|
|
|
stdENDP _BaseProcessStartThunk
|
|
|
|
;++
|
|
;
|
|
; VOID
|
|
; SwitchToFiber(
|
|
; PFIBER NewFiber
|
|
; )
|
|
;
|
|
; Routine Description:
|
|
;
|
|
; This function saves the state of the current fiber and switches
|
|
; to the new fiber.
|
|
;
|
|
; Arguments:
|
|
;
|
|
; NewFiber (TOS+4) - Supplies the address of the new fiber.
|
|
;
|
|
; Return Value:
|
|
;
|
|
; None
|
|
;
|
|
;--
|
|
|
|
LDMXCSR macro
|
|
db 0Fh, 0AEh, 051h, 028h ; ldmxcsr FbFiberContext+CsDr6[eax]
|
|
endm
|
|
|
|
STMXCSR macro
|
|
db 0Fh, 0AEh, 058h, 028h ; stmxcsr FbFiberContext+CsDr6[eax]
|
|
endm
|
|
|
|
FLOAT_SAVE equ FbFiberContext + CsFloatSave
|
|
|
|
SAVE_FLOATING equ CONTEXT_FULL or CONTEXT_FLOATING_POINT
|
|
|
|
XMMI_AVAILABLE equ UsProcessorFeatures + PF_XMMI_INSTRUCTIONS_AVAILABLE
|
|
|
|
cPublicProc _SwitchToFiber,1
|
|
|
|
;
|
|
; Save current fiber context.
|
|
;
|
|
|
|
mov edx, fs:[PcTeb] ; get TEB address
|
|
mov eax, [edx]+TeFiberData ; get current fiber address
|
|
|
|
;
|
|
; Save nonvolatile integer registers.
|
|
;
|
|
|
|
mov [eax]+FbFiberContext+CsEbx, ebx ;
|
|
mov [eax]+FbFiberContext+CsEdi, edi ;
|
|
mov [eax]+FbFiberContext+CsEsi, esi ;
|
|
mov [eax]+FbFiberContext+CsEbp, ebp ;
|
|
|
|
;
|
|
; Save floating state if specified.
|
|
;
|
|
|
|
cmp dword ptr [eax]+FbFiberContext+CsContextFlags, SAVE_FLOATING ; check for save
|
|
jne short STF10 ; if ne, no floating environment switched
|
|
fstsw [eax]+FLOAT_SAVE+FpStatusWord ; save status word
|
|
fnstcw [eax]+FLOAT_SAVE+FpControlWord ; save control word
|
|
cmp byte ptr ds:[MM_SHARED_USER_DATA_VA+XMMI_AVAILABLE], 1 ; check for XMMI support
|
|
jne short STF10 ; if ne, XMMI not supported
|
|
|
|
STMXCSR ; stmxcsr [eax]+FbFiberContext+CsDr6
|
|
|
|
;
|
|
; Save stack pointer and fiber local storage data structure address.
|
|
;
|
|
|
|
STF10: mov [eax]+FbFiberContext+CsEsp, esp ; save stack pointer
|
|
mov ecx, [edx]+TeFlsData ;
|
|
mov [eax]+FbFlsData, ecx ;
|
|
|
|
;
|
|
; Save exception list and stack limit.
|
|
;
|
|
|
|
mov ecx, [edx]+TeExceptionList ;
|
|
mov ebx, [edx]+TeStackLimit ;
|
|
mov [eax]+FbExceptionList, ecx ;
|
|
mov [eax]+FbStackLimit, ebx ;
|
|
|
|
;
|
|
; Restore new fiber context.
|
|
;
|
|
|
|
mov ecx, [esp]+4 ; get new fiber address
|
|
mov [edx]+TeFiberData, ecx ; set fiber address
|
|
|
|
;
|
|
; Restore exception list, stack base, stack limit, and deallocation stack.
|
|
;
|
|
|
|
mov esi, [ecx]+FbExceptionList ;
|
|
mov ebx, [ecx]+FbStackBase ;
|
|
mov [edx]+TeExceptionList, esi ;
|
|
mov [edx]+TeStackBase, ebx ;
|
|
|
|
mov esi, [ecx]+FbStackLimit ;
|
|
mov ebx, [ecx]+FbDeallocationStack ;
|
|
mov [edx]+TeStackLimit, esi ;
|
|
mov [edx]+TeDeallocationStack, ebx ;
|
|
|
|
;
|
|
; Restore floating state if specified.
|
|
;
|
|
|
|
cmp dword ptr [ecx]+FbFiberContext+CsContextFlags, SAVE_FLOATING ; check for save
|
|
jne short STF40 ; if ne, no floating environment switched
|
|
|
|
;
|
|
; If the old floating control and status words are equal to the new control
|
|
; and status words, then there is no need to load any legacy floating state.
|
|
;
|
|
|
|
mov ebx, [eax]+FLOAT_SAVE+FpStatusWord ; get previous status word
|
|
cmp bx, [ecx]+FLOAT_SAVE+FpStatusWord ; check if status words equal
|
|
jne short STF20 ; if ne, status words not equal
|
|
mov ebx, [eax]+FLOAT_SAVE+FpControlWord ; get previous control word
|
|
cmp bx, [ecx]+FLOAT_SAVE+FpControlWord ; check if control words equal
|
|
je short STF30 ; if e, control words equal
|
|
STF20: mov word ptr [ecx]+FLOAT_SAVE+FpTagWord, 0ffffh ; set tag word
|
|
fldenv [ecx]+FLOAT_SAVE ; restore floating environment
|
|
STF30: cmp byte ptr ds:[MM_SHARED_USER_DATA_VA+XMMI_AVAILABLE], 1 ; check for XMMI support
|
|
jne short STF40 ; if ne, XMMI not supported
|
|
|
|
LDMXCSR ; ldmxcsr [eax]+FbFiberContext+CsDr6
|
|
|
|
;
|
|
; Restore nonvolitile integer registers.
|
|
;
|
|
|
|
STF40: mov edi, [ecx]+FbFiberContext+CsEdi ;
|
|
mov esi, [ecx]+FbFiberContext+CsEsi ;
|
|
mov ebp, [ecx]+FbFiberContext+CsEbp ;
|
|
mov ebx, [ecx]+FbFiberContext+CsEbx ;
|
|
|
|
;
|
|
; Restore stack address and fiber local storage data structure address.
|
|
;
|
|
|
|
mov eax, [ecx]+FbFlsData ;
|
|
mov [edx]+TeFlsData, eax ;
|
|
mov esp, [ecx]+FbFiberContext+CsEsp ;
|
|
stdRET _SwitchToFiber
|
|
|
|
stdENDP _SwitchToFiber
|
|
|
|
;++
|
|
;
|
|
; VOID
|
|
; LdrpCallInitRoutine(
|
|
; IN PDLL_INIT_ROUTINE InitRoutine,
|
|
; IN PVOID DllHandle,
|
|
; IN ULONG Reason,
|
|
; IN PCONTEXT Context OPTIONAL
|
|
; )
|
|
;
|
|
; Routine Description:
|
|
;
|
|
; This function calls an x86 DLL init routine. It is robust
|
|
; against DLLs that don't preserve EBX or fail to clean up
|
|
; enough stack.
|
|
;
|
|
; The only register that the DLL init routine cannot trash is ESI.
|
|
;
|
|
; Arguments:
|
|
;
|
|
; InitRoutine - Address of init routine to call
|
|
;
|
|
; DllHandle - Handle of DLL to call
|
|
;
|
|
; Reason - one of the DLL_PROCESS_... or DLL_THREAD... values
|
|
;
|
|
; Context - context pointer or NULL
|
|
;
|
|
; Return Value:
|
|
;
|
|
; FALSE if the init routine fails, TRUE for success.
|
|
;
|
|
;--
|
|
|
|
cPublicProc __ResourceCallEnumLangRoutine , 6
|
|
|
|
EnumRoutine equ [ebp + 8]
|
|
ModuleHandle equ [ebp + 12]
|
|
LpType equ [ebp + 16]
|
|
LpName equ [ebp + 20]
|
|
WLanguage equ [ebp + 24]
|
|
LParam equ [ebp + 28]
|
|
|
|
stdENDP __ResourceCallEnumLangRoutine
|
|
push ebp
|
|
mov ebp, esp
|
|
push esi ; save esi across the call
|
|
push edi ; save edi across the call
|
|
push ebx ; save ebx on the stack across the call
|
|
mov esi,esp ; save the stack pointer in esi across the call
|
|
push LParam
|
|
push WLanguage
|
|
push LpName
|
|
push LpType
|
|
push ModuleHandle
|
|
call EnumRoutine
|
|
mov esp,esi ; restore the stack pointer in case callee forgot to clean up
|
|
pop ebx ; restore ebx
|
|
pop edi ; restore edi
|
|
pop esi ; restore esi
|
|
pop ebp
|
|
stdRET __ResourceCallEnumLangRoutine
|
|
|
|
cPublicProc __ResourceCallEnumNameRoutine , 5
|
|
|
|
EnumRoutine equ [ebp + 8]
|
|
ModuleHandle equ [ebp + 12]
|
|
LpType equ [ebp + 16]
|
|
LpName equ [ebp + 20]
|
|
LParam equ [ebp + 24]
|
|
|
|
stdENDP __ResourceCallEnumNameRoutine
|
|
push ebp
|
|
mov ebp, esp
|
|
push esi ; save esi across the call
|
|
push edi ; save edi across the call
|
|
push ebx ; save ebx on the stack across the call
|
|
mov esi,esp ; save the stack pointer in esi across the call
|
|
push LParam
|
|
push LpName
|
|
push LpType
|
|
push ModuleHandle
|
|
call EnumRoutine
|
|
mov esp,esi ; restore the stack pointer in case callee forgot to clean up
|
|
pop ebx ; restore ebx
|
|
pop edi ; restore edi
|
|
pop esi ; restore esi
|
|
pop ebp
|
|
stdRET __ResourceCallEnumNameRoutine
|
|
|
|
cPublicProc __ResourceCallEnumTypeRoutine , 4
|
|
|
|
EnumRoutine equ [ebp + 8]
|
|
ModuleHandle equ [ebp + 12]
|
|
LpType equ [ebp + 16]
|
|
LParam equ [ebp + 20]
|
|
|
|
stdENDP __ResourceCallEnumTypeRoutine
|
|
push ebp
|
|
mov ebp, esp
|
|
push esi ; save esi across the call
|
|
push edi ; save edi across the call
|
|
push ebx ; save ebx on the stack across the call
|
|
mov esi,esp ; save the stack pointer in esi across the call
|
|
push LParam
|
|
push LpType
|
|
push ModuleHandle
|
|
call EnumRoutine
|
|
mov esp,esi ; restore the stack pointer in case callee forgot to clean up
|
|
pop ebx ; restore ebx
|
|
pop edi ; restore edi
|
|
pop esi ; restore esi
|
|
pop ebp
|
|
stdRET __ResourceCallEnumTypeRoutine
|
|
|
|
_TEXT ends
|
|
end
|