Module: wine Branch: master Commit: a2adc8881554887c03ed985a6d08c565e675e657 URL: http://source.winehq.org/git/wine.git/?a=commit;h=a2adc8881554887c03ed985a6d...
Author: Alexandre Julliard julliard@winehq.org Date: Tue May 15 21:41:50 2007 +0200
ntoskrnl.exe: Implemented IoCreateDevice and IoDeleteDevice.
---
dlls/ntoskrnl.exe/Makefile.in | 3 + dlls/ntoskrnl.exe/ntoskrnl.c | 163 +++++++++++++++++++++++++++++++++++ dlls/ntoskrnl.exe/ntoskrnl.exe.spec | 4 +- 3 files changed, 168 insertions(+), 2 deletions(-)
diff --git a/dlls/ntoskrnl.exe/Makefile.in b/dlls/ntoskrnl.exe/Makefile.in index 448eb1f..2e91316 100644 --- a/dlls/ntoskrnl.exe/Makefile.in +++ b/dlls/ntoskrnl.exe/Makefile.in @@ -6,6 +6,9 @@ MODULE = ntoskrnl.exe IMPORTLIB = libntoskrnl.exe.$(IMPLIBEXT) IMPORTS = kernel32 ntdll
+C_SRCS = \ + ntoskrnl.c + @MAKE_DLL_RULES@
@DEPENDENCIES@ # everything below this line is overwritten by make depend diff --git a/dlls/ntoskrnl.exe/ntoskrnl.c b/dlls/ntoskrnl.exe/ntoskrnl.c new file mode 100644 index 0000000..ae78665 --- /dev/null +++ b/dlls/ntoskrnl.exe/ntoskrnl.c @@ -0,0 +1,163 @@ +/* + * ntoskrnl.exe implementation + * + * Copyright (C) 2007 Alexandre Julliard + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA + */ + +#include "config.h" +#include "wine/port.h" + +#include <stdarg.h> + +#define NONAMELESSUNION +#define NONAMELESSSTRUCT + +#include "ntstatus.h" +#define WIN32_NO_STATUS +#include "windef.h" +#include "winternl.h" +#include "ddk/wdm.h" +#include "wine/unicode.h" +#include "wine/server.h" +#include "wine/debug.h" + +WINE_DEFAULT_DEBUG_CHANNEL(ntoskrnl); + +static inline LPCSTR debugstr_us( const UNICODE_STRING *us ) +{ + if (!us) return "<null>"; + return debugstr_wn( us->Buffer, us->Length / sizeof(WCHAR) ); +} + +static HANDLE get_device_manager(void) +{ + static HANDLE device_manager; + HANDLE handle = 0, ret = device_manager; + + if (!ret) + { + SERVER_START_REQ( create_device_manager ) + { + req->access = SYNCHRONIZE; + req->attributes = 0; + if (!wine_server_call( req )) handle = reply->handle; + } + SERVER_END_REQ; + + if (!handle) + { + ERR( "failed to create the device manager\n" ); + return 0; + } + if (!(ret = InterlockedCompareExchangePointer( &device_manager, handle, 0 ))) + ret = handle; + else + NtClose( handle ); /* somebody beat us to it */ + } + return ret; +} + + +/*********************************************************************** + * IoCreateDevice (NTOSKRNL.EXE.@) + */ +NTSTATUS WINAPI IoCreateDevice( DRIVER_OBJECT *driver, ULONG ext_size, + UNICODE_STRING *name, DEVICE_TYPE type, + ULONG characteristics, BOOLEAN exclusive, + DEVICE_OBJECT **ret_device ) +{ + NTSTATUS status; + DEVICE_OBJECT *device; + HANDLE handle = 0; + HANDLE manager = get_device_manager(); + + TRACE( "(%p, %u, %s, %u, %x, %u, %p)\n", + driver, ext_size, debugstr_us(name), type, characteristics, exclusive, ret_device ); + + if (!(device = HeapAlloc( GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*device) + ext_size ))) + return STATUS_NO_MEMORY; + + SERVER_START_REQ( create_device ) + { + req->access = 0; + req->attributes = 0; + req->rootdir = 0; + req->manager = manager; + req->user_ptr = device; + if (name) wine_server_add_data( req, name->Buffer, name->Length ); + if (!(status = wine_server_call( req ))) handle = reply->handle; + } + SERVER_END_REQ; + + if (status == STATUS_SUCCESS) + { + device->DriverObject = driver; + device->DeviceExtension = device + 1; + device->DeviceType = type; + device->Reserved = handle; + + device->NextDevice = driver->DeviceObject; + driver->DeviceObject = device; + + *ret_device = device; + } + else HeapFree( GetProcessHeap(), 0, device ); + + return status; +} + + +/*********************************************************************** + * IoDeleteDevice (NTOSKRNL.EXE.@) + */ +void WINAPI IoDeleteDevice( DEVICE_OBJECT *device ) +{ + NTSTATUS status; + + TRACE( "%p\n", device ); + + SERVER_START_REQ( delete_device ) + { + req->handle = device->Reserved; + status = wine_server_call( req ); + } + SERVER_END_REQ; + + if (status == STATUS_SUCCESS) + { + DEVICE_OBJECT **prev = &device->DriverObject->DeviceObject; + while (*prev && *prev != device) prev = &(*prev)->NextDevice; + if (*prev) *prev = (*prev)->NextDevice; + NtClose( device->Reserved ); + HeapFree( GetProcessHeap(), 0, device ); + } +} + + +/***************************************************** + * DllMain + */ +BOOL WINAPI DllMain( HINSTANCE inst, DWORD reason, LPVOID reserved ) +{ + switch(reason) + { + case DLL_PROCESS_ATTACH: + DisableThreadLibraryCalls( inst ); + break; + } + return TRUE; +} diff --git a/dlls/ntoskrnl.exe/ntoskrnl.exe.spec b/dlls/ntoskrnl.exe/ntoskrnl.exe.spec index 4e6a38c..04591ba 100644 --- a/dlls/ntoskrnl.exe/ntoskrnl.exe.spec +++ b/dlls/ntoskrnl.exe/ntoskrnl.exe.spec @@ -336,7 +336,7 @@ @ stub IoCompleteRequest @ stub IoConnectInterrupt @ stub IoCreateController -@ stub IoCreateDevice +@ stdcall IoCreateDevice(ptr long ptr long long long ptr) @ stub IoCreateDisk @ stub IoCreateDriver @ stub IoCreateFile @@ -353,7 +353,7 @@ @ stub IoCsqRemoveIrp @ stub IoCsqRemoveNextIrp @ stub IoDeleteController -@ stub IoDeleteDevice +@ stdcall IoDeleteDevice(ptr) @ stub IoDeleteDriver @ stub IoDeleteSymbolicLink @ stub IoDetachDevice