/*++ Module Name: context.c Abstract: This module contains the context management routines for Win32 Author: Revision History: --*/ #include "basedll.h" #include "kxia64.h" VOID BaseInitializeContext( OUT PCONTEXT Context, IN PVOID Parameter OPTIONAL, IN PVOID InitialPc OPTIONAL, IN PVOID InitialSp OPTIONAL, IN BASE_CONTEXT_TYPE ContextType ) /*++ Routine Description: This function initializes a context structure so that it can be used in a subsequent call to NtCreateThread. Arguments: Context - Supplies a context buffer to be initialized by this routine. Parameter - Supplies the thread's parameter. InitialPc - Supplies an initial program counter value. InitialSp - Supplies an initial stack pointer value. NewThread - Supplies a flag that specifies that this is a new thread, or a new process. Return Value: Raises STATUS_BAD_INITIAL_STACK if the value of InitialSp is not properly aligned. Raises STATUS_BAD_INITIAL_PC if the value of InitialPc is not properly aligned. --*/ { ULONG ArgumentsCount; // // Initialize the Context // RtlZeroMemory((PVOID)Context, sizeof(CONTEXT)); Context->StFPSR = USER_FPSR_INITIAL; Context->StIPSR = USER_PSR_INITIAL; Context->RsBSP = Context->IntSp = (ULONG_PTR)InitialSp; Context->IntSp -= STACK_SCRATCH_AREA; // scratch area as per convention Context->IntS1 = (ULONG_PTR)InitialPc; Context->IntS2 = (ULONG_PTR)Parameter; // // Enable RSE engine // Context->RsRSC = (RSC_MODE_EA<IntS0 = Context->StIIP = (ULONG_PTR)BaseThreadStartThunk; } else if ( ContextType == BaseContextTypeFiber ) { Context->IntS0 = Context->StIIP = (ULONG_PTR)BaseFiberStart; // // set up the return pointer here.. // when SwitchToFiber restores context and calls return, // the contorl goes to this routine // Context->BrRp = *((ULONGLONG *)((PUCHAR)BaseFiberStart)); // // set up sof = 96 in pfs. This will be used to set up CFM for above // routine // Context->RsPFS = 0x60; } else { Context->IntS0 = Context->StIIP = (ULONG_PTR)(LONG_PTR)BaseProcessStartThunk; } Context->RsPFS |= MASK_IA64(PFS_PPL, 3i64); Context->ContextFlags = CONTEXT_CONTROL| CONTEXT_INTEGER; Context->Eflag = 0x3000i64; } VOID BaseFiberStart( VOID ) /*++ Routine Description: This function is called to start a Win32 fiber. Its purpose is to call BaseThreadStart, getting the necessary arguments from the fiber context record. Arguments: None. Return Value: None. --*/ { PFIBER Fiber; Fiber = GetCurrentFiber(); BaseThreadStart( (LPTHREAD_START_ROUTINE)Fiber->FiberContext.IntS1, (LPVOID)Fiber->FiberContext.IntS2 ); } VOID BaseProcessStartupIA64( 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 argument registers. Arguments: StartRoutine - User Target start program counter ThreadParameter Return Value: Never Returns --*/ { (StartRoutine)(ThreadParameter); }