mirror of
https://github.com/reactos/reactos.git
synced 2025-01-13 01:22:03 +00:00
c424146e2c
svn path=/branches/cmake-bringup/; revision=48236
779 lines
22 KiB
C
779 lines
22 KiB
C
/*
|
|
* COPYRIGHT: See COPYING in the top level directory
|
|
* PROJECT: ReactOS CSR Sub System
|
|
* FILE: subsys/csr/csrsrv/init.c
|
|
* PURPOSE: CSR Server DLL Initialization
|
|
* PROGRAMMERS: ReactOS Portable Systems Group
|
|
*/
|
|
|
|
/* INCLUDES *******************************************************************/
|
|
|
|
#include "srv.h"
|
|
#define NDEBUG
|
|
#include <debug.h>
|
|
|
|
/* DATA ***********************************************************************/
|
|
|
|
HANDLE CsrHeap = (HANDLE) 0;
|
|
HANDLE CsrObjectDirectory = (HANDLE) 0;
|
|
UNICODE_STRING CsrDirectoryName;
|
|
extern HANDLE CsrssApiHeap;
|
|
static unsigned ServerProcCount;
|
|
static CSRPLUGIN_SERVER_PROCS *ServerProcs = NULL;
|
|
HANDLE hSbApiPort = (HANDLE) 0;
|
|
HANDLE hBootstrapOk = (HANDLE) 0;
|
|
HANDLE hSmApiPort = (HANDLE) 0;
|
|
HANDLE hApiPort = (HANDLE) 0;
|
|
|
|
/* PRIVATE FUNCTIONS **********************************************************/
|
|
|
|
ULONG
|
|
InitializeVideoAddressSpace(VOID)
|
|
{
|
|
OBJECT_ATTRIBUTES ObjectAttributes;
|
|
UNICODE_STRING PhysMemName = RTL_CONSTANT_STRING(L"\\Device\\PhysicalMemory");
|
|
NTSTATUS Status;
|
|
HANDLE PhysMemHandle;
|
|
PVOID BaseAddress;
|
|
LARGE_INTEGER Offset;
|
|
SIZE_T ViewSize;
|
|
CHAR IVTAndBda[1024+256];
|
|
|
|
/* Open the physical memory section */
|
|
InitializeObjectAttributes(&ObjectAttributes,
|
|
&PhysMemName,
|
|
0,
|
|
NULL,
|
|
NULL);
|
|
Status = ZwOpenSection(&PhysMemHandle,
|
|
SECTION_ALL_ACCESS,
|
|
&ObjectAttributes);
|
|
if (!NT_SUCCESS(Status))
|
|
{
|
|
DPRINT1("Couldn't open \\Device\\PhysicalMemory\n");
|
|
return 0;
|
|
}
|
|
|
|
/* Map the BIOS and device registers into the address space */
|
|
Offset.QuadPart = 0xa0000;
|
|
ViewSize = 0x100000 - 0xa0000;
|
|
BaseAddress = (PVOID)0xa0000;
|
|
Status = ZwMapViewOfSection(PhysMemHandle,
|
|
NtCurrentProcess(),
|
|
&BaseAddress,
|
|
0,
|
|
ViewSize,
|
|
&Offset,
|
|
&ViewSize,
|
|
ViewUnmap,
|
|
0,
|
|
PAGE_EXECUTE_READWRITE);
|
|
if (!NT_SUCCESS(Status))
|
|
{
|
|
DPRINT1("Couldn't map physical memory (%x)\n", Status);
|
|
ZwClose(PhysMemHandle);
|
|
return 0;
|
|
}
|
|
|
|
/* Close physical memory section handle */
|
|
ZwClose(PhysMemHandle);
|
|
|
|
if (BaseAddress != (PVOID)0xa0000)
|
|
{
|
|
DPRINT1("Couldn't map physical memory at the right address (was %x)\n",
|
|
BaseAddress);
|
|
return 0;
|
|
}
|
|
|
|
/* Allocate some low memory to use for the non-BIOS
|
|
* parts of the v86 mode address space
|
|
*/
|
|
BaseAddress = (PVOID)0x1;
|
|
ViewSize = 0xa0000 - 0x1000;
|
|
Status = ZwAllocateVirtualMemory(NtCurrentProcess(),
|
|
&BaseAddress,
|
|
0,
|
|
&ViewSize,
|
|
MEM_COMMIT,
|
|
PAGE_EXECUTE_READWRITE);
|
|
if (!NT_SUCCESS(Status))
|
|
{
|
|
DPRINT1("Failed to allocate virtual memory (Status %x)\n", Status);
|
|
return 0;
|
|
}
|
|
if (BaseAddress != (PVOID)0x0)
|
|
{
|
|
DPRINT1("Failed to allocate virtual memory at right address (was %x)\n",
|
|
BaseAddress);
|
|
return 0;
|
|
}
|
|
|
|
/* Get the real mode IVT and BDA from the kernel */
|
|
Status = NtVdmControl(VdmInitialize, IVTAndBda);
|
|
if (!NT_SUCCESS(Status))
|
|
{
|
|
DPRINT1("NtVdmControl failed (status %x)\n", Status);
|
|
return 0;
|
|
}
|
|
|
|
/* Return success */
|
|
return 1;
|
|
}
|
|
|
|
|
|
static NTSTATUS FASTCALL
|
|
CsrpAddServerProcs(CSRPLUGIN_SERVER_PROCS *Procs)
|
|
{
|
|
CSRPLUGIN_SERVER_PROCS *NewProcs;
|
|
|
|
DPRINT("CSR: %s called\n", __FUNCTION__);
|
|
|
|
NewProcs = RtlAllocateHeap(CsrssApiHeap, 0,
|
|
(ServerProcCount + 1)
|
|
* sizeof(CSRPLUGIN_SERVER_PROCS));
|
|
if (NULL == NewProcs)
|
|
{
|
|
return STATUS_NO_MEMORY;
|
|
}
|
|
if (0 != ServerProcCount)
|
|
{
|
|
RtlCopyMemory(NewProcs, ServerProcs,
|
|
ServerProcCount * sizeof(CSRPLUGIN_SERVER_PROCS));
|
|
RtlFreeHeap(CsrssApiHeap, 0, ServerProcs);
|
|
}
|
|
NewProcs[ServerProcCount] = *Procs;
|
|
ServerProcs = NewProcs;
|
|
ServerProcCount++;
|
|
|
|
return STATUS_SUCCESS;
|
|
}
|
|
|
|
/**********************************************************************
|
|
* CallInitComplete/0
|
|
*/
|
|
static BOOL FASTCALL
|
|
CallInitComplete(void)
|
|
{
|
|
BOOL Ok;
|
|
unsigned i;
|
|
|
|
DPRINT("CSR: %s called\n", __FUNCTION__);
|
|
|
|
Ok = TRUE;
|
|
for (i = 0; i < ServerProcCount && Ok; i++)
|
|
{
|
|
Ok = (*ServerProcs[i].InitCompleteProc)();
|
|
}
|
|
|
|
return Ok;
|
|
}
|
|
|
|
BOOL
|
|
CallHardError(IN PCSRSS_PROCESS_DATA ProcessData,
|
|
IN PHARDERROR_MSG HardErrorMessage)
|
|
{
|
|
BOOL Ok;
|
|
unsigned i;
|
|
|
|
DPRINT("CSR: %s called\n", __FUNCTION__);
|
|
|
|
Ok = TRUE;
|
|
for (i = 0; i < ServerProcCount && Ok; i++)
|
|
{
|
|
Ok = (*ServerProcs[i].HardErrorProc)(ProcessData, HardErrorMessage);
|
|
}
|
|
|
|
return Ok;
|
|
}
|
|
|
|
NTSTATUS
|
|
CallProcessInherit(IN PCSRSS_PROCESS_DATA SourceProcessData,
|
|
IN PCSRSS_PROCESS_DATA TargetProcessData)
|
|
{
|
|
NTSTATUS Status = STATUS_SUCCESS;
|
|
unsigned i;
|
|
|
|
DPRINT("CSR: %s called\n", __FUNCTION__);
|
|
|
|
for (i = 0; i < ServerProcCount && NT_SUCCESS(Status); i++)
|
|
Status = (*ServerProcs[i].ProcessInheritProc)(SourceProcessData, TargetProcessData);
|
|
|
|
return Status;
|
|
}
|
|
|
|
NTSTATUS
|
|
CallProcessDeleted(IN PCSRSS_PROCESS_DATA ProcessData)
|
|
{
|
|
NTSTATUS Status = STATUS_SUCCESS;
|
|
unsigned i;
|
|
|
|
DPRINT("CSR: %s called\n", __FUNCTION__);
|
|
|
|
for (i = 0; i < ServerProcCount && NT_SUCCESS(Status); i++)
|
|
Status = (*ServerProcs[i].ProcessDeletedProc)(ProcessData);
|
|
|
|
return Status;
|
|
}
|
|
|
|
|
|
ULONG
|
|
InitializeVideoAddressSpace(VOID);
|
|
|
|
/**********************************************************************
|
|
* CsrpCreateObjectDirectory/3
|
|
*/
|
|
static NTSTATUS
|
|
CsrpCreateObjectDirectory (int argc, char ** argv, char ** envp)
|
|
{
|
|
NTSTATUS Status;
|
|
OBJECT_ATTRIBUTES Attributes;
|
|
|
|
DPRINT("CSR: %s called\n", __FUNCTION__);
|
|
|
|
|
|
/* create object directory ('\Windows') */
|
|
RtlCreateUnicodeString (&CsrDirectoryName,
|
|
L"\\Windows");
|
|
|
|
InitializeObjectAttributes (&Attributes,
|
|
&CsrDirectoryName,
|
|
OBJ_OPENIF,
|
|
NULL,
|
|
NULL);
|
|
|
|
Status = NtOpenDirectoryObject(&CsrObjectDirectory,
|
|
DIRECTORY_ALL_ACCESS,
|
|
&Attributes);
|
|
return Status;
|
|
}
|
|
|
|
/**********************************************************************
|
|
* CsrpInitVideo/3
|
|
*
|
|
* TODO: we need a virtual device for sessions other than
|
|
* TODO: the console one
|
|
*/
|
|
static NTSTATUS
|
|
CsrpInitVideo (int argc, char ** argv, char ** envp)
|
|
{
|
|
OBJECT_ATTRIBUTES ObjectAttributes;
|
|
UNICODE_STRING DeviceName = RTL_CONSTANT_STRING(L"\\??\\DISPLAY1");
|
|
IO_STATUS_BLOCK Iosb;
|
|
HANDLE VideoHandle = (HANDLE) 0;
|
|
NTSTATUS Status = STATUS_SUCCESS;
|
|
|
|
DPRINT("CSR: %s called\n", __FUNCTION__);
|
|
|
|
InitializeVideoAddressSpace();
|
|
|
|
InitializeObjectAttributes(&ObjectAttributes,
|
|
&DeviceName,
|
|
0,
|
|
NULL,
|
|
NULL);
|
|
Status = NtOpenFile(&VideoHandle,
|
|
FILE_ALL_ACCESS,
|
|
&ObjectAttributes,
|
|
&Iosb,
|
|
0,
|
|
0);
|
|
if (NT_SUCCESS(Status))
|
|
{
|
|
NtClose(VideoHandle);
|
|
}
|
|
return Status;
|
|
}
|
|
|
|
/**********************************************************************
|
|
* CsrpInitWin32Csr/3
|
|
*
|
|
* TODO: this function should be turned more general to load an
|
|
* TODO: hosted server DLL as received from the command line;
|
|
* TODO: for instance: ServerDll=winsrv:ConServerDllInitialization,2
|
|
* TODO: ^method ^dll ^api ^sid
|
|
* TODO:
|
|
* TODO: CsrpHostServerDll (LPWSTR DllName,
|
|
* TODO: LPWSTR ApiName,
|
|
* TODO: DWORD ServerId)
|
|
*/
|
|
static NTSTATUS
|
|
CsrpInitWin32Csr (int argc, char ** argv, char ** envp)
|
|
{
|
|
NTSTATUS Status;
|
|
UNICODE_STRING DllName;
|
|
HINSTANCE hInst;
|
|
ANSI_STRING ProcName;
|
|
CSRPLUGIN_INITIALIZE_PROC InitProc;
|
|
CSRSS_EXPORTED_FUNCS Exports;
|
|
PCSRSS_API_DEFINITION ApiDefinitions;
|
|
CSRPLUGIN_SERVER_PROCS ServerProcs;
|
|
|
|
DPRINT("CSR: %s called\n", __FUNCTION__);
|
|
|
|
RtlInitUnicodeString(&DllName, L"win32csr.dll");
|
|
Status = LdrLoadDll(NULL, 0, &DllName, (PVOID *) &hInst);
|
|
if (! NT_SUCCESS(Status))
|
|
{
|
|
return Status;
|
|
}
|
|
RtlInitAnsiString(&ProcName, "Win32CsrInitialization");
|
|
Status = LdrGetProcedureAddress(hInst, &ProcName, 0, (PVOID *) &InitProc);
|
|
if (! NT_SUCCESS(Status))
|
|
{
|
|
return Status;
|
|
}
|
|
Exports.CsrEnumProcessesProc = CsrEnumProcesses;
|
|
if (! (*InitProc)(&ApiDefinitions, &ServerProcs, &Exports, CsrssApiHeap))
|
|
{
|
|
return STATUS_UNSUCCESSFUL;
|
|
}
|
|
|
|
Status = CsrApiRegisterDefinitions(ApiDefinitions);
|
|
if (! NT_SUCCESS(Status))
|
|
{
|
|
return Status;
|
|
}
|
|
Status = CsrpAddServerProcs(&ServerProcs);
|
|
return Status;
|
|
}
|
|
|
|
CSRSS_API_DEFINITION NativeDefinitions[] =
|
|
{
|
|
CSRSS_DEFINE_API(CREATE_PROCESS, CsrCreateProcess),
|
|
CSRSS_DEFINE_API(CREATE_THREAD, CsrSrvCreateThread),
|
|
CSRSS_DEFINE_API(TERMINATE_PROCESS, CsrTerminateProcess),
|
|
CSRSS_DEFINE_API(CONNECT_PROCESS, CsrConnectProcess),
|
|
CSRSS_DEFINE_API(REGISTER_SERVICES_PROCESS, CsrRegisterServicesProcess),
|
|
CSRSS_DEFINE_API(GET_SHUTDOWN_PARAMETERS, CsrGetShutdownParameters),
|
|
CSRSS_DEFINE_API(SET_SHUTDOWN_PARAMETERS, CsrSetShutdownParameters),
|
|
{ 0, 0, NULL }
|
|
};
|
|
|
|
static NTSTATUS WINAPI
|
|
CsrpCreateListenPort (IN LPWSTR Name,
|
|
IN OUT PHANDLE Port,
|
|
IN PTHREAD_START_ROUTINE ListenThread)
|
|
{
|
|
NTSTATUS Status = STATUS_SUCCESS;
|
|
OBJECT_ATTRIBUTES PortAttributes;
|
|
UNICODE_STRING PortName;
|
|
HANDLE ServerThread;
|
|
CLIENT_ID ClientId;
|
|
|
|
DPRINT("CSR: %s called\n", __FUNCTION__);
|
|
|
|
RtlInitUnicodeString (& PortName, Name);
|
|
InitializeObjectAttributes (& PortAttributes,
|
|
& PortName,
|
|
0,
|
|
NULL,
|
|
NULL);
|
|
Status = NtCreatePort ( Port,
|
|
& PortAttributes,
|
|
LPC_MAX_DATA_LENGTH, /* TODO: make caller set it*/
|
|
LPC_MAX_MESSAGE_LENGTH, /* TODO: make caller set it*/
|
|
0); /* TODO: make caller set it*/
|
|
if(!NT_SUCCESS(Status))
|
|
{
|
|
DPRINT1("CSR: %s: NtCreatePort failed (Status=%08lx)\n",
|
|
__FUNCTION__, Status);
|
|
return Status;
|
|
}
|
|
Status = RtlCreateUserThread(NtCurrentProcess(),
|
|
NULL,
|
|
TRUE,
|
|
0,
|
|
0,
|
|
0,
|
|
(PTHREAD_START_ROUTINE) ListenThread,
|
|
*Port,
|
|
&ServerThread,
|
|
&ClientId);
|
|
|
|
if (ListenThread == (PVOID)ClientConnectionThread)
|
|
{
|
|
CsrAddStaticServerThread(ServerThread, &ClientId, 0);
|
|
}
|
|
|
|
NtResumeThread(ServerThread, NULL);
|
|
NtClose(ServerThread);
|
|
return Status;
|
|
}
|
|
|
|
/* === INIT ROUTINES === */
|
|
|
|
/**********************************************************************
|
|
* CsrpCreateBNODirectory/3
|
|
*
|
|
* These used to be part of kernel32 startup, but that clearly wasn't a good
|
|
* idea, as races were definately possible. These are moved (as in the
|
|
* previous fixmes).
|
|
*/
|
|
static NTSTATUS
|
|
CsrpCreateBNODirectory (int argc, char ** argv, char ** envp)
|
|
{
|
|
NTSTATUS Status;
|
|
OBJECT_ATTRIBUTES ObjectAttributes;
|
|
UNICODE_STRING Name = RTL_CONSTANT_STRING(L"\\BaseNamedObjects");
|
|
UNICODE_STRING SymName = RTL_CONSTANT_STRING(L"Local");
|
|
UNICODE_STRING SymName2 = RTL_CONSTANT_STRING(L"Global");
|
|
HANDLE DirHandle, SymHandle;
|
|
|
|
/* Seems like a good place to create these objects which are needed by
|
|
* win32 processes */
|
|
InitializeObjectAttributes(&ObjectAttributes,
|
|
&Name,
|
|
OBJ_CASE_INSENSITIVE,
|
|
NULL,
|
|
NULL);
|
|
|
|
Status = NtCreateDirectoryObject(&DirHandle,
|
|
DIRECTORY_ALL_ACCESS,
|
|
&ObjectAttributes);
|
|
if (!NT_SUCCESS(Status))
|
|
{
|
|
DPRINT1("NtCreateDirectoryObject() failed %08x\n", Status);
|
|
}
|
|
|
|
/* Create the "local" Symbolic Link.
|
|
* FIXME: CSR should do this -- Fixed */
|
|
InitializeObjectAttributes(&ObjectAttributes,
|
|
&SymName,
|
|
OBJ_CASE_INSENSITIVE,
|
|
DirHandle,
|
|
NULL);
|
|
Status = NtCreateSymbolicLinkObject(&SymHandle,
|
|
SYMBOLIC_LINK_ALL_ACCESS,
|
|
&ObjectAttributes,
|
|
&Name);
|
|
if (!NT_SUCCESS(Status))
|
|
{
|
|
DPRINT1("NtCreateDirectoryObject() failed %08x\n", Status);
|
|
}
|
|
|
|
/* Create the "global" Symbolic Link. */
|
|
InitializeObjectAttributes(&ObjectAttributes,
|
|
&SymName2,
|
|
OBJ_CASE_INSENSITIVE,
|
|
DirHandle,
|
|
NULL);
|
|
Status = NtCreateSymbolicLinkObject(&SymHandle,
|
|
SYMBOLIC_LINK_ALL_ACCESS,
|
|
&ObjectAttributes,
|
|
&Name);
|
|
if (!NT_SUCCESS(Status))
|
|
{
|
|
DPRINT1("NtCreateDirectoryObject() failed %08x\n", Status);
|
|
}
|
|
|
|
return Status;
|
|
}
|
|
|
|
/**********************************************************************
|
|
* CsrpCreateHeap/3
|
|
*/
|
|
static NTSTATUS
|
|
CsrpCreateHeap (int argc, char ** argv, char ** envp)
|
|
{
|
|
DPRINT("CSR: %s called\n", __FUNCTION__);
|
|
|
|
CsrssApiHeap = RtlCreateHeap(HEAP_GROWABLE,
|
|
NULL,
|
|
65536,
|
|
65536,
|
|
NULL,
|
|
NULL);
|
|
if (CsrssApiHeap == NULL)
|
|
{
|
|
return STATUS_UNSUCCESSFUL;
|
|
}
|
|
return STATUS_SUCCESS;
|
|
}
|
|
|
|
/**********************************************************************
|
|
* CsrpCreateCallbackPort/3
|
|
*/
|
|
static NTSTATUS
|
|
CsrpCreateCallbackPort (int argc, char ** argv, char ** envp)
|
|
{
|
|
DPRINT("CSR: %s called\n", __FUNCTION__);
|
|
|
|
return CsrpCreateListenPort (L"\\Windows\\SbApiPort",
|
|
& hSbApiPort,
|
|
ServerSbApiPortThread);
|
|
}
|
|
|
|
/**********************************************************************
|
|
* CsrpRegisterSubsystem/3
|
|
*/
|
|
static NTSTATUS
|
|
CsrpRegisterSubsystem (int argc, char ** argv, char ** envp)
|
|
{
|
|
NTSTATUS Status = STATUS_SUCCESS;
|
|
OBJECT_ATTRIBUTES BootstrapOkAttributes;
|
|
UNICODE_STRING Name;
|
|
|
|
DPRINT("CSR: %s called\n", __FUNCTION__);
|
|
|
|
/*
|
|
* Create the event object the callback port
|
|
* thread will signal *if* the SM will
|
|
* authorize us to bootstrap.
|
|
*/
|
|
RtlInitUnicodeString (& Name, L"\\CsrssBooting");
|
|
InitializeObjectAttributes(& BootstrapOkAttributes,
|
|
& Name,
|
|
0, NULL, NULL);
|
|
Status = NtCreateEvent (& hBootstrapOk,
|
|
EVENT_ALL_ACCESS,
|
|
& BootstrapOkAttributes,
|
|
SynchronizationEvent,
|
|
FALSE);
|
|
if(!NT_SUCCESS(Status))
|
|
{
|
|
DPRINT("CSR: %s: NtCreateEvent failed (Status=0x%08lx)\n",
|
|
__FUNCTION__, Status);
|
|
return Status;
|
|
}
|
|
/*
|
|
* Let's tell the SM a new environment
|
|
* subsystem server is in the system.
|
|
*/
|
|
RtlInitUnicodeString (& Name, L"\\Windows\\SbApiPort");
|
|
DPRINT("CSR: %s: registering with SM for\n IMAGE_SUBSYSTEM_WINDOWS_CUI == 3\n", __FUNCTION__);
|
|
Status = SmConnectApiPort (& Name,
|
|
hSbApiPort,
|
|
IMAGE_SUBSYSTEM_WINDOWS_CUI,
|
|
& hSmApiPort);
|
|
if(!NT_SUCCESS(Status))
|
|
{
|
|
DPRINT("CSR: %s unable to connect to the SM (Status=0x%08lx)\n",
|
|
__FUNCTION__, Status);
|
|
NtClose (hBootstrapOk);
|
|
return Status;
|
|
}
|
|
/*
|
|
* Wait for SM to reply OK... If the SM
|
|
* won't answer, we hang here forever!
|
|
*/
|
|
DPRINT("CSR: %s: waiting for SM to OK boot...\n", __FUNCTION__);
|
|
Status = NtWaitForSingleObject (hBootstrapOk,
|
|
FALSE,
|
|
NULL);
|
|
NtClose (hBootstrapOk);
|
|
return Status;
|
|
}
|
|
|
|
/**********************************************************************
|
|
* CsrpLoadKernelModeDriver/3
|
|
*/
|
|
static NTSTATUS
|
|
CsrpLoadKernelModeDriver (int argc, char ** argv, char ** envp)
|
|
{
|
|
NTSTATUS Status = STATUS_SUCCESS;
|
|
WCHAR Data [MAX_PATH + 1];
|
|
ULONG DataLength = sizeof Data;
|
|
ULONG DataType = 0;
|
|
//UNICODE_STRING Environment;
|
|
|
|
|
|
DPRINT1("SM: %s called\n", __FUNCTION__);
|
|
|
|
|
|
//EnvpToUnicodeString (envp, & Environment);
|
|
Status = SmLookupSubsystem (L"Kmode",
|
|
Data,
|
|
& DataLength,
|
|
& DataType,
|
|
NULL);
|
|
//RtlFreeUnicodeString (& Environment);
|
|
if((STATUS_SUCCESS == Status) && (DataLength > sizeof Data[0]))
|
|
{
|
|
WCHAR ImagePath [MAX_PATH + 1] = {0};
|
|
UNICODE_STRING ModuleName;
|
|
|
|
wcscpy (ImagePath, L"\\SYSTEMROOT\\system32\\win32k.sys");
|
|
// wcscat (ImagePath, Data);
|
|
RtlInitUnicodeString (& ModuleName, ImagePath);
|
|
Status = NtSetSystemInformation(/* FIXME: SystemLoadAndCallImage */
|
|
SystemExtendServiceTableInformation,
|
|
& ModuleName,
|
|
sizeof ModuleName);
|
|
if(!NT_SUCCESS(Status))
|
|
{
|
|
DPRINT1("WIN: %s: loading Kmode failed (Status=0x%08lx)\n",
|
|
__FUNCTION__, Status);
|
|
}
|
|
}
|
|
return Status;
|
|
}
|
|
|
|
/**********************************************************************
|
|
* CsrpCreateApiPort/2
|
|
*/
|
|
static NTSTATUS
|
|
CsrpCreateApiPort (int argc, char ** argv, char ** envp)
|
|
{
|
|
DPRINT("CSR: %s called\n", __FUNCTION__);
|
|
|
|
CsrInitProcessData();
|
|
|
|
return CsrpCreateListenPort(L"\\Windows\\ApiPort", &hApiPort,
|
|
(PTHREAD_START_ROUTINE)ClientConnectionThread);
|
|
}
|
|
|
|
/**********************************************************************
|
|
* CsrpApiRegisterDef/0
|
|
*/
|
|
static NTSTATUS
|
|
CsrpApiRegisterDef (int argc, char ** argv, char ** envp)
|
|
{
|
|
return CsrApiRegisterDefinitions(NativeDefinitions);
|
|
}
|
|
|
|
/**********************************************************************
|
|
* CsrpCCTS/2
|
|
*/
|
|
static NTSTATUS
|
|
CsrpCCTS (int argc, char ** argv, char ** envp)
|
|
{
|
|
ULONG Dummy;
|
|
ULONG DummyLength = sizeof(Dummy);
|
|
return CsrClientConnectToServer(L"\\Windows",
|
|
0, &Dummy, &DummyLength, NULL);
|
|
}
|
|
|
|
/**********************************************************************
|
|
* CsrpRunWinlogon/0
|
|
*
|
|
* Start the logon process (winlogon.exe).
|
|
*
|
|
* TODO: this should be moved in CsrpCreateSession/x (one per session)
|
|
* TODO: in its own desktop (one logon desktop per winstation).
|
|
*/
|
|
static NTSTATUS
|
|
CsrpRunWinlogon (int argc, char ** argv, char ** envp)
|
|
{
|
|
NTSTATUS Status = STATUS_SUCCESS;
|
|
UNICODE_STRING ImagePath;
|
|
UNICODE_STRING CommandLine;
|
|
PRTL_USER_PROCESS_PARAMETERS ProcessParameters = NULL;
|
|
RTL_USER_PROCESS_INFORMATION ProcessInfo;
|
|
|
|
|
|
DPRINT("CSR: %s called\n", __FUNCTION__);
|
|
|
|
/* initialize the process parameters */
|
|
RtlInitUnicodeString (& ImagePath, L"\\SystemRoot\\system32\\winlogon.exe");
|
|
RtlInitUnicodeString (& CommandLine, L"");
|
|
RtlCreateProcessParameters(& ProcessParameters,
|
|
& ImagePath,
|
|
NULL,
|
|
NULL,
|
|
& CommandLine,
|
|
NULL,
|
|
NULL,
|
|
NULL,
|
|
NULL,
|
|
NULL);
|
|
/* Create the winlogon process */
|
|
Status = RtlCreateUserProcess (& ImagePath,
|
|
OBJ_CASE_INSENSITIVE,
|
|
ProcessParameters,
|
|
NULL,
|
|
NULL,
|
|
NULL,
|
|
FALSE,
|
|
NULL,
|
|
NULL,
|
|
& ProcessInfo);
|
|
/* Cleanup */
|
|
RtlDestroyProcessParameters (ProcessParameters);
|
|
if (!NT_SUCCESS(Status))
|
|
{
|
|
DPRINT1("SM: %s: loading winlogon.exe failed (Status=%08lx)\n",
|
|
__FUNCTION__, Status);
|
|
}
|
|
|
|
ZwResumeThread(ProcessInfo.ThreadHandle, NULL);
|
|
return Status;
|
|
}
|
|
|
|
static NTSTATUS
|
|
CsrpCreateHardErrorPort (int argc, char ** argv, char ** envp)
|
|
{
|
|
return NtSetDefaultHardErrorPort(hApiPort);
|
|
}
|
|
|
|
typedef NTSTATUS (* CSR_INIT_ROUTINE)(int,char**,char**);
|
|
|
|
struct {
|
|
BOOL Required;
|
|
CSR_INIT_ROUTINE EntryPoint;
|
|
PCHAR ErrorMessage;
|
|
} InitRoutine [] = {
|
|
{TRUE, CsrpCreateBNODirectory, "create base named objects directory"},
|
|
{TRUE, CsrpCreateCallbackPort, "create the callback port \\Windows\\SbApiPort"},
|
|
{TRUE, CsrpRegisterSubsystem, "register with SM"},
|
|
{TRUE, CsrpCreateHeap, "create the CSR heap"},
|
|
{TRUE, CsrpCreateApiPort, "create the api port \\Windows\\ApiPort"},
|
|
{TRUE, CsrpCreateHardErrorPort, "create the hard error port"},
|
|
{TRUE, CsrpCreateObjectDirectory,"create the object directory \\Windows"},
|
|
{TRUE, CsrpLoadKernelModeDriver, "load Kmode driver"},
|
|
{TRUE, CsrpInitVideo, "initialize video"},
|
|
{TRUE, CsrpApiRegisterDef, "initialize api definitions"},
|
|
{TRUE, CsrpCCTS, "connect client to server"},
|
|
{TRUE, CsrpInitWin32Csr, "load usermode dll"},
|
|
{TRUE, CsrpRunWinlogon, "run WinLogon"},
|
|
};
|
|
|
|
/* PUBLIC FUNCTIONS ***********************************************************/
|
|
|
|
NTSTATUS
|
|
NTAPI
|
|
CsrServerInitialization(ULONG ArgumentCount,
|
|
PCHAR Arguments[])
|
|
{
|
|
UINT i = 0;
|
|
NTSTATUS Status = STATUS_SUCCESS;
|
|
|
|
DPRINT("CSR: %s called\n", __FUNCTION__);
|
|
|
|
for (i=0; i < (sizeof InitRoutine / sizeof InitRoutine[0]); i++)
|
|
{
|
|
Status = InitRoutine[i].EntryPoint(ArgumentCount,Arguments,NULL);
|
|
if(!NT_SUCCESS(Status))
|
|
{
|
|
DPRINT1("CSR: %s: failed to %s (Status=%08lx)\n",
|
|
__FUNCTION__,
|
|
InitRoutine[i].ErrorMessage,
|
|
Status);
|
|
if (InitRoutine[i].Required)
|
|
{
|
|
return FALSE;
|
|
}
|
|
}
|
|
}
|
|
if (CallInitComplete())
|
|
{
|
|
Status = SmCompleteSession (hSmApiPort,hSbApiPort,hApiPort);
|
|
return STATUS_SUCCESS;
|
|
}
|
|
|
|
return STATUS_UNSUCCESSFUL;
|
|
}
|
|
|
|
BOOL
|
|
NTAPI
|
|
DllMainCRTStartup(HANDLE hDll,
|
|
DWORD dwReason,
|
|
LPVOID lpReserved)
|
|
{
|
|
/* We don't do much */
|
|
UNREFERENCED_PARAMETER(hDll);
|
|
UNREFERENCED_PARAMETER(dwReason);
|
|
UNREFERENCED_PARAMETER(lpReserved);
|
|
return TRUE;
|
|
}
|
|
|
|
/* EOF */
|