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.
522 lines
12 KiB
522 lines
12 KiB
/*++
|
|
|
|
Copyright (c) 1989 Microsoft Corporation
|
|
|
|
Module Name:
|
|
|
|
init.c
|
|
|
|
Abstract:
|
|
|
|
This module contains the initialization code of the NT browser
|
|
File System Driver (FSD) and File System Process (FSP).
|
|
|
|
|
|
Author:
|
|
|
|
Larry Osterman (larryo) 24-May-1990
|
|
|
|
Environment:
|
|
|
|
Kernel mode, FSD, and FSP
|
|
|
|
Revision History:
|
|
|
|
30-May-1990 LarryO
|
|
|
|
Created
|
|
|
|
--*/
|
|
|
|
//
|
|
// Include modules
|
|
//
|
|
|
|
#include "precomp.h"
|
|
#pragma hdrstop
|
|
|
|
HANDLE
|
|
BowserServerAnnouncementEventHandle = {0};
|
|
|
|
PKEVENT
|
|
BowserServerAnnouncementEvent = {0};
|
|
|
|
PDOMAIN_INFO BowserPrimaryDomainInfo = NULL;
|
|
|
|
|
|
// External functions
|
|
|
|
//(fsctl.c)
|
|
NTSTATUS
|
|
StopBowser (
|
|
IN BOOLEAN Wait,
|
|
IN BOOLEAN InFsd,
|
|
IN PBOWSER_FS_DEVICE_OBJECT DeviceObject,
|
|
IN PLMDR_REQUEST_PACKET InputBuffer,
|
|
IN ULONG InputBufferLength
|
|
);
|
|
|
|
|
|
// Local functions
|
|
|
|
VOID
|
|
BowserReadBowserConfiguration(
|
|
PUNICODE_STRING RegistryPath
|
|
);
|
|
|
|
#ifdef ALLOC_PRAGMA
|
|
#pragma alloc_text(INIT, BowserDriverEntry)
|
|
#pragma alloc_text(PAGE, BowserUnload)
|
|
#pragma alloc_text(INIT, BowserReadBowserConfiguration)
|
|
#endif
|
|
|
|
NTSTATUS
|
|
BowserDriverEntry(
|
|
IN PDRIVER_OBJECT DriverObject,
|
|
IN PUNICODE_STRING RegistryPath
|
|
)
|
|
|
|
/*++
|
|
|
|
Routine Description:
|
|
|
|
This is the initialization routine for the file system. It is invoked once
|
|
when the driver is loaded into the system. Its job is to initialize all
|
|
the structures which will be used by the FSD and the FSP. It also creates
|
|
the process from which all of the file system threads will be executed. It
|
|
then registers the file system with the I/O system as a valid file system
|
|
resident in the system.
|
|
|
|
Arguments:
|
|
|
|
DriverObject - Pointer to driver object created by the system.
|
|
|
|
Return Value:
|
|
|
|
None.
|
|
|
|
--*/
|
|
|
|
{
|
|
NTSTATUS Status;
|
|
UNICODE_STRING unicodeEventName;
|
|
UNICODE_STRING DummyDomain;
|
|
|
|
PDEVICE_OBJECT DeviceObject;
|
|
OBJECT_ATTRIBUTES obja;
|
|
|
|
PAGED_CODE();
|
|
|
|
#if DBG
|
|
BowserInitializeTraceLog();
|
|
#endif
|
|
|
|
//
|
|
// Create the device object for this file system.
|
|
//
|
|
|
|
RtlInitUnicodeString( &BowserNameString, DD_BROWSER_DEVICE_NAME_U );
|
|
|
|
dlog(DPRT_INIT, ("Creating device %wZ\n", &BowserNameString));
|
|
|
|
|
|
#if DBG
|
|
#define BOWSER_LOAD_BP 0
|
|
#if BOWSER_LOAD_BP
|
|
dlog(DPRT_INIT, ("DebugBreakPoint...\n"));
|
|
DbgBreakPoint();
|
|
#endif
|
|
#endif
|
|
|
|
dlog(DPRT_INIT, ("DriverObject at %08lx\n", DriverObject));
|
|
|
|
Status = IoCreateDevice( DriverObject,
|
|
sizeof(BOWSER_FS_DEVICE_OBJECT) - sizeof(DEVICE_OBJECT),
|
|
&BowserNameString,
|
|
FILE_DEVICE_NETWORK_BROWSER,
|
|
0,
|
|
FALSE,
|
|
&DeviceObject );
|
|
|
|
if (!NT_SUCCESS(Status)) {
|
|
InternalError(("Unable to create redirector device"));
|
|
}
|
|
|
|
dlog(DPRT_INIT, ("Device created at %08lx\n", DeviceObject));
|
|
|
|
|
|
|
|
Status = BowserInitializeSecurity(DeviceObject);
|
|
|
|
if (!NT_SUCCESS(Status)) {
|
|
InternalError(("Unable to initialize security."));
|
|
}
|
|
|
|
dlog(DPRT_INIT, ("Initialized Browser security at %p\n", g_pBowSecurityDescriptor));
|
|
|
|
|
|
ExInitializeResourceLite( &BowserDataResource );
|
|
|
|
//
|
|
// Save the device object address for this file system driver.
|
|
//
|
|
|
|
BowserDeviceObject = (PBOWSER_FS_DEVICE_OBJECT )DeviceObject;
|
|
|
|
BowserReadBowserConfiguration(RegistryPath);
|
|
|
|
DeviceObject->StackSize = (CCHAR)BowserIrpStackSize;
|
|
|
|
dlog(DPRT_INIT, ("Stacksize is %d\n",DeviceObject->StackSize));
|
|
|
|
//
|
|
// Initialize the TDI package
|
|
//
|
|
|
|
BowserpInitializeTdi();
|
|
|
|
//
|
|
// Initialize the datagram buffer structures
|
|
//
|
|
|
|
BowserpInitializeMailslot();
|
|
|
|
BowserInitializeFsd();
|
|
|
|
BowserpInitializeIrpQueue();
|
|
|
|
//
|
|
// Initialize the code to receive a browser server list.
|
|
//
|
|
|
|
BowserpInitializeGetBrowserServerList();
|
|
|
|
//
|
|
// Initialize the bowser FSP.
|
|
//
|
|
|
|
if (!NT_SUCCESS(Status = BowserpInitializeFsp(DriverObject))) {
|
|
return Status;
|
|
}
|
|
|
|
if (!NT_SUCCESS(Status = BowserpInitializeNames())) {
|
|
return Status;
|
|
}
|
|
|
|
#if DBG
|
|
//
|
|
// If we have a preconfigured trace level, open the browser trace log
|
|
// right away.
|
|
//
|
|
|
|
if (BowserDebugLogLevel != 0) {
|
|
BowserOpenTraceLogFile(L"\\SystemRoot\\Bowser.Log");
|
|
}
|
|
#endif
|
|
|
|
// //
|
|
// // Set up the browsers unload routine.
|
|
// //
|
|
//
|
|
// DriverObject->DriverUnload = BowserUnload;
|
|
|
|
BowserInitializeDiscardableCode();
|
|
|
|
|
|
//
|
|
// Set the timer up for the idle timer.
|
|
//
|
|
|
|
IoInitializeTimer((PDEVICE_OBJECT )BowserDeviceObject, BowserIdleTimer,
|
|
NULL);
|
|
|
|
|
|
|
|
RtlInitUnicodeString( &unicodeEventName, SERVER_ANNOUNCE_EVENT_W );
|
|
InitializeObjectAttributes( &obja, &unicodeEventName, OBJ_OPENIF, NULL, NULL );
|
|
|
|
Status = ZwCreateEvent(
|
|
&BowserServerAnnouncementEventHandle,
|
|
SYNCHRONIZE | EVENT_QUERY_STATE | EVENT_MODIFY_STATE,
|
|
&obja,
|
|
SynchronizationEvent,
|
|
FALSE
|
|
);
|
|
|
|
if (NT_SUCCESS(Status)) {
|
|
Status = ObReferenceObjectByHandle(BowserServerAnnouncementEventHandle,
|
|
EVENT_MODIFY_STATE,
|
|
NULL,
|
|
KernelMode,
|
|
&BowserServerAnnouncementEvent,
|
|
NULL);
|
|
}
|
|
|
|
//
|
|
// Always create a domain structure for the primary domain.
|
|
//
|
|
RtlInitUnicodeString( &DummyDomain, NULL );
|
|
BowserPrimaryDomainInfo = BowserCreateDomain( &DummyDomain, &DummyDomain );
|
|
|
|
return Status;
|
|
|
|
}
|
|
|
|
|
|
VOID
|
|
BowserUnload(
|
|
IN PDRIVER_OBJECT DriverObject
|
|
)
|
|
/*++
|
|
|
|
Routine Description:
|
|
|
|
This is the unload routine for the bowser device.
|
|
|
|
Arguments:
|
|
|
|
DriverObject - pointer to the driver object for the browser driver
|
|
|
|
Return Value:
|
|
|
|
None
|
|
|
|
--*/
|
|
|
|
{
|
|
PAGED_CODE();
|
|
|
|
if ( BowserData.Initialized ){
|
|
|
|
//
|
|
// StopBowser was never called (mem cleanup skipped etc).
|
|
// Call it before exiting (see bug 359407).
|
|
//
|
|
|
|
// Fake (unused) paramters
|
|
BOWSER_FS_DEVICE_OBJECT fsDevice;
|
|
LMDR_REQUEST_PACKET InputBuffer;
|
|
|
|
fsDevice.DeviceObject = *DriverObject->DeviceObject;
|
|
|
|
// set fake input buffer. It is unused (except param check) in
|
|
// StopBowser
|
|
InputBuffer.Version = LMDR_REQUEST_PACKET_VERSION_DOM;
|
|
|
|
|
|
ASSERT ((IoGetCurrentProcess() == BowserFspProcess));
|
|
(VOID) StopBowser(
|
|
TRUE,
|
|
TRUE,
|
|
&fsDevice,
|
|
&InputBuffer,
|
|
sizeof(LMDR_REQUEST_PACKET) );
|
|
|
|
}
|
|
|
|
//
|
|
// Ditch the global reference to the primary domain.
|
|
//
|
|
|
|
if ( BowserPrimaryDomainInfo != NULL ) {
|
|
// break if we're leaking memory. StopBowser should
|
|
// have cleaned all references.
|
|
ASSERT ( BowserPrimaryDomainInfo->ReferenceCount == 1 );
|
|
BowserDereferenceDomain( BowserPrimaryDomainInfo );
|
|
}
|
|
|
|
//
|
|
// Uninitialize the bowser name structures.
|
|
//
|
|
|
|
BowserpUninitializeNames();
|
|
|
|
//
|
|
// Uninitialize the bowser FSP.
|
|
//
|
|
|
|
BowserpUninitializeFsp();
|
|
|
|
//
|
|
// Uninitialize the routines involved in retrieving browser server lists.
|
|
//
|
|
|
|
BowserpUninitializeGetBrowserServerList();
|
|
|
|
//
|
|
// Uninitialize the mailslot related functions.
|
|
//
|
|
|
|
BowserpUninitializeMailslot();
|
|
|
|
//
|
|
// Uninitialize the TDI related functions.
|
|
//
|
|
|
|
BowserpUninitializeTdi();
|
|
|
|
//
|
|
// Delete the resource protecting the bowser global data.
|
|
//
|
|
|
|
ExDeleteResourceLite(&BowserDataResource);
|
|
|
|
ObDereferenceObject(BowserServerAnnouncementEvent);
|
|
|
|
ZwClose(BowserServerAnnouncementEventHandle);
|
|
|
|
#if DBG
|
|
BowserUninitializeTraceLog();
|
|
#endif
|
|
|
|
//
|
|
// Delete the browser device object.
|
|
//
|
|
|
|
IoDeleteDevice((PDEVICE_OBJECT)BowserDeviceObject);
|
|
|
|
BowserUninitializeDiscardableCode();
|
|
|
|
return;
|
|
}
|
|
|
|
VOID
|
|
BowserReadBowserConfiguration(
|
|
PUNICODE_STRING RegistryPath
|
|
)
|
|
{
|
|
ULONG Storage[256];
|
|
UNICODE_STRING UnicodeString;
|
|
HANDLE RedirConfigHandle;
|
|
HANDLE ParametersHandle;
|
|
NTSTATUS Status;
|
|
ULONG BytesRead;
|
|
OBJECT_ATTRIBUTES ObjectAttributes;
|
|
PBOWSER_CONFIG_INFO ConfigEntry;
|
|
PKEY_VALUE_FULL_INFORMATION Value = (PKEY_VALUE_FULL_INFORMATION)Storage;
|
|
|
|
PAGED_CODE();
|
|
|
|
InitializeObjectAttributes(
|
|
&ObjectAttributes,
|
|
RegistryPath, // name
|
|
OBJ_CASE_INSENSITIVE, // attributes
|
|
NULL, // root
|
|
NULL // security descriptor
|
|
);
|
|
|
|
Status = ZwOpenKey (&RedirConfigHandle, KEY_READ, &ObjectAttributes);
|
|
|
|
if (!NT_SUCCESS(Status)) {
|
|
BowserWriteErrorLogEntry (
|
|
EVENT_BOWSER_CANT_READ_REGISTRY,
|
|
Status,
|
|
NULL,
|
|
0,
|
|
0
|
|
);
|
|
|
|
return;
|
|
}
|
|
|
|
RtlInitUnicodeString(&UnicodeString, BOWSER_CONFIG_PARAMETERS);
|
|
|
|
InitializeObjectAttributes(
|
|
&ObjectAttributes,
|
|
&UnicodeString,
|
|
OBJ_CASE_INSENSITIVE,
|
|
RedirConfigHandle,
|
|
NULL
|
|
);
|
|
|
|
|
|
Status = ZwOpenKey (&ParametersHandle, KEY_READ, &ObjectAttributes);
|
|
|
|
if (!NT_SUCCESS(Status)) {
|
|
BowserWriteErrorLogEntry (
|
|
EVENT_BOWSER_CANT_READ_REGISTRY,
|
|
Status,
|
|
NULL,
|
|
0,
|
|
0
|
|
);
|
|
|
|
ZwClose(RedirConfigHandle);
|
|
|
|
return;
|
|
}
|
|
|
|
for (ConfigEntry = BowserConfigEntries;
|
|
ConfigEntry->ConfigParameterName != NULL;
|
|
ConfigEntry += 1) {
|
|
|
|
RtlInitUnicodeString(&UnicodeString, ConfigEntry->ConfigParameterName);
|
|
|
|
Status = ZwQueryValueKey(ParametersHandle,
|
|
&UnicodeString,
|
|
KeyValueFullInformation,
|
|
Value,
|
|
sizeof(Storage),
|
|
&BytesRead);
|
|
|
|
|
|
if (NT_SUCCESS(Status)) {
|
|
|
|
if (Value->DataLength != 0) {
|
|
|
|
if (ConfigEntry->ConfigValueType == REG_BOOLEAN) {
|
|
if (Value->Type != REG_DWORD ||
|
|
Value->DataLength != REG_BOOLEAN_SIZE) {
|
|
BowserWriteErrorLogEntry (
|
|
EVENT_BOWSER_CANT_READ_REGISTRY,
|
|
STATUS_INVALID_PARAMETER,
|
|
ConfigEntry->ConfigParameterName,
|
|
(USHORT)(wcslen(ConfigEntry->ConfigParameterName)*sizeof(WCHAR)),
|
|
0
|
|
);
|
|
|
|
} else {
|
|
ULONG_PTR ConfigValue = (ULONG_PTR)((PCHAR)Value)+Value->DataOffset;
|
|
|
|
*(PBOOLEAN)(ConfigEntry->ConfigValue) = (BOOLEAN)(*((PULONG)ConfigValue) != 0);
|
|
}
|
|
|
|
} else if (Value->Type != ConfigEntry->ConfigValueType ||
|
|
Value->DataLength != ConfigEntry->ConfigValueSize) {
|
|
|
|
BowserWriteErrorLogEntry (
|
|
EVENT_BOWSER_CANT_READ_REGISTRY,
|
|
STATUS_INVALID_PARAMETER,
|
|
ConfigEntry->ConfigParameterName,
|
|
(USHORT)(wcslen(ConfigEntry->ConfigParameterName)*sizeof(WCHAR)),
|
|
0
|
|
);
|
|
|
|
} else {
|
|
|
|
RtlCopyMemory(ConfigEntry->ConfigValue, ((PCHAR)Value)+Value->DataOffset, Value->DataLength);
|
|
}
|
|
} else {
|
|
BowserWriteErrorLogEntry (
|
|
EVENT_BOWSER_CANT_READ_REGISTRY,
|
|
STATUS_INVALID_PARAMETER,
|
|
ConfigEntry->ConfigParameterName,
|
|
(USHORT)(wcslen(ConfigEntry->ConfigParameterName)*sizeof(WCHAR)),
|
|
0
|
|
);
|
|
}
|
|
}
|
|
|
|
}
|
|
|
|
|
|
ZwClose(ParametersHandle);
|
|
|
|
ZwClose(RedirConfigHandle);
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|