- Link ntoskrnl against libwdmguid.a.
- Report device arrival events to the user-mode pnp manager.
Modified: trunk/reactos/include/ntos/ntpnp.h
Modified: trunk/reactos/ntoskrnl/Makefile
Modified: trunk/reactos/ntoskrnl/include/internal/io.h
Modified: trunk/reactos/ntoskrnl/io/plugplay.c
Modified: trunk/reactos/ntoskrnl/io/pnpmgr.c
_____
Modified: trunk/reactos/include/ntos/ntpnp.h
--- trunk/reactos/include/ntos/ntpnp.h 2005-02-04 23:24:32 UTC (rev
13408)
+++ trunk/reactos/include/ntos/ntpnp.h 2005-02-05 00:04:52 UTC (rev
13409)
@@ -244,6 +244,8 @@
* ...
*/
+#define PLUGPLAY_USER_RESPONSE 0x07
+
NTSTATUS STDCALL
NtPlugPlayControl(
ULONG ControlCode,
_____
Modified: trunk/reactos/ntoskrnl/Makefile
--- trunk/reactos/ntoskrnl/Makefile 2005-02-04 23:24:32 UTC (rev
13408)
+++ trunk/reactos/ntoskrnl/Makefile 2005-02-05 00:04:52 UTC (rev
13409)
@@ -185,9 +185,9 @@
io/parttab.o \
io/plugplay.o \
io/process.o \
- io/pnpnotify.o \
io/pnpdma.o \
io/pnpmgr.o \
+ io/pnpnotify.o \
io/pnpreport.o \
io/pnproot.o \
io/queue.o \
@@ -516,6 +516,7 @@
$(SDK_PATH_LIB)/libstring.a \
$(SDK_PATH_LIB)/librosrtl.a \
$(SDK_PATH_LIB)/libpseh.a \
+ $(SDK_PATH_LIB)/libwdmguid.a \
$(PATH_TO_TOP)/drivers/lib/csq/csq.o
TARGET_LFLAGS = \
@@ -542,7 +543,7 @@
TARGET_CLEAN = \
$(PATH_TO_TOP)/include/reactos/bugcodes.h \
- $(DEP_OBJECTS) $(DEP_FILES) MSG00409.bin bugcodes.rc
+ $(DEP_OBJECTS) $(DEP_FILES) MSG00409.bin bugcodes.rc
ex/napi.o: ex/zw.S $(PATH_TO_TOP)/include/ntdll/napi.h
_____
Modified: trunk/reactos/ntoskrnl/include/internal/io.h
--- trunk/reactos/ntoskrnl/include/internal/io.h 2005-02-04
23:24:32 UTC (rev 13408)
+++ trunk/reactos/ntoskrnl/include/internal/io.h 2005-02-05
00:04:52 UTC (rev 13409)
@@ -501,12 +501,16 @@
IopReinitializeDrivers(VOID);
-/* pnpevent.c */
+/* plugplay.c */
NTSTATUS INIT_FUNCTION
IopInitPlugPlayEvents(VOID);
+NTSTATUS
+IopQueueTargetDeviceEvent(const GUID *Guid,
+ PUNICODE_STRING DeviceIds);
+
/* pnpmgr.c */
NTSTATUS
_____
Modified: trunk/reactos/ntoskrnl/io/plugplay.c
--- trunk/reactos/ntoskrnl/io/plugplay.c 2005-02-04 23:24:32 UTC
(rev 13408)
+++ trunk/reactos/ntoskrnl/io/plugplay.c 2005-02-05 00:04:52 UTC
(rev 13409)
@@ -15,9 +15,17 @@
#define NDEBUG
#include <internal/debug.h>
+
+typedef struct _PNP_EVENT_ENTRY
+{
+ LIST_ENTRY ListEntry;
+ PLUGPLAY_EVENT_BLOCK Event;
+} PNP_EVENT_ENTRY, *PPNP_EVENT_ENTRY;
+
+
/* GLOBALS
*******************************************************************/
-static LIST_ENTRY IopPnpEventListHead;
+static LIST_ENTRY IopPnpEventQueueHead;
static KEVENT IopPnpNotifyEvent;
/* FUNCTIONS
*****************************************************************/
@@ -26,41 +34,77 @@
IopInitPlugPlayEvents(VOID)
{
- InitializeListHead(&IopPnpEventListHead);
+ InitializeListHead(&IopPnpEventQueueHead);
KeInitializeEvent(&IopPnpNotifyEvent,
- NotificationEvent,
+ SynchronizationEvent,
FALSE);
return STATUS_SUCCESS;
}
-#if 0
-/* Insert a new pnp event at the head of the event queue */
-VOID
-IopEnqueuePlugPlayEvent(VOID)
+NTSTATUS
+IopQueueTargetDeviceEvent(const GUID *Guid,
+ PUNICODE_STRING DeviceIds)
{
+ PPNP_EVENT_ENTRY EventEntry;
+ DWORD TotalSize;
+ TotalSize =
+ FIELD_OFFSET(PLUGPLAY_EVENT_BLOCK, TargetDevice.DeviceIds) +
+ DeviceIds->MaximumLength;
+
+ EventEntry = ExAllocatePool(NonPagedPool,
+ TotalSize + FIELD_OFFSET(PNP_EVENT_ENTRY,
Event));
+ if (EventEntry == NULL)
+ return STATUS_INSUFFICIENT_RESOURCES;
+
+ memcpy(&EventEntry->Event.EventGuid,
+ Guid,
+ sizeof(GUID));
+ EventEntry->Event.EventCategory = TargetDeviceChangeEvent;
+ EventEntry->Event.TotalSize = TotalSize;
+
+ memcpy(&EventEntry->Event.TargetDevice.DeviceIds,
+ DeviceIds->Buffer,
+ DeviceIds->MaximumLength);
+
+ InsertHeadList(&IopPnpEventQueueHead,
+ &EventEntry->ListEntry);
+ KeSetEvent(&IopPnpNotifyEvent,
+ 0,
+ FALSE);
+
+ return STATUS_SUCCESS;
}
-#endif
-#if 0
/*
* Remove the current PnP event from the tail of the event queue
* and signal IopPnpNotifyEvent if there is yet another event in the
queue.
*/
-VOID
-IopDequeuePlugPlayEvent(VOID)
+static VOID
+IopRemovePlugPlayEvent(VOID)
{
+ /* Remove a pnp event entry from the tail of the queue */
+ if (!IsListEmpty(&IopPnpEventQueueHead))
+ {
+ ExFreePool(RemoveTailList(&IopPnpEventQueueHead));
+ }
+ /* Signal the next pnp event in the queue */
+ if (!IsListEmpty(&IopPnpEventQueueHead))
+ {
+ KeSetEvent(&IopPnpNotifyEvent,
+ 0,
+ FALSE);
+ }
}
-#endif
/*
- * @unimplemented
+ * @implemented
*/
NTSTATUS STDCALL
NtGetPlugPlayEvent(IN ULONG Reserved1,
@@ -68,6 +112,7 @@
OUT PPLUGPLAY_EVENT_BLOCK Buffer,
IN ULONG BufferLength)
{
+ PPNP_EVENT_ENTRY Entry;
NTSTATUS Status;
DPRINT("NtGetPlugPlayEvent() called\n");
@@ -83,7 +128,7 @@
if (!SeSinglePrivilegeCheck(SeTcbPrivilege,
UserMode))
{
- DPRINT1("NtGetPlugPlayEvent: Caller requires the SeTcbPrivilege
privilege!\n");
+ DPRINT1("NtGetPlugPlayEvent: Caller does not hold the
SeTcbPrivilege privilege!\n");
return STATUS_PRIVILEGE_NOT_HELD;
}
@@ -94,31 +139,30 @@
KernelMode,
FALSE,
NULL);
- if (NT_SUCCESS(Status))
+ if (!NT_SUCCESS(Status))
{
- DPRINT("Waiting done\n");
+ DPRINT1("KeWaitForSingleObject() failed (Status %lx)\n", Status);
+ return Status;
+ }
-#if 0
- /* Get entry from the tail of the list */
- Entry = IopPnpEventListHead.Blink;
+ /* Get entry from the tail of the queue */
+ Entry = (PPNP_EVENT_ENTRY)IopPnpEventQueueHead.Blink;
- /* Check the buffer size */
- if (BufferLength < Entry->Event.Size)
- {
- DPRINT1("Buffer is too small for the pnp-event\n");
- return STATUS_BUFFER_TOO_SMALL;
- }
-
- /* Copy event data to user buffer */
- memcpy(Buffer,
- &Entry->Event,
- &Entry->Event.Size);
-#endif
+ /* Check the buffer size */
+ if (BufferLength < Entry->Event.TotalSize)
+ {
+ DPRINT1("Buffer is too small for the pnp-event\n");
+ return STATUS_BUFFER_TOO_SMALL;
}
+ /* Copy event data to the user buffer */
+ memcpy(Buffer,
+ &Entry->Event,
+ Entry->Event.TotalSize);
+
DPRINT("NtGetPlugPlayEvent() done\n");
- return Status;
+ return STATUS_SUCCESS;
}
@@ -130,7 +174,16 @@
IN OUT PVOID Buffer,
IN ULONG BufferLength)
{
- UNIMPLEMENTED;
+ DPRINT("NtPlugPlayControl(%lu %p %lu) called\n",
+ ControlCode, Buffer, BufferLength);
+
+ switch (ControlCode)
+ {
+ case PLUGPLAY_USER_RESPONSE:
+ IopRemovePlugPlayEvent();
+ return STATUS_SUCCESS;
+ }
+
return STATUS_NOT_IMPLEMENTED;
}
_____
Modified: trunk/reactos/ntoskrnl/io/pnpmgr.c
--- trunk/reactos/ntoskrnl/io/pnpmgr.c 2005-02-04 23:24:32 UTC (rev
13408)
+++ trunk/reactos/ntoskrnl/io/pnpmgr.c 2005-02-05 00:04:52 UTC (rev
13409)
@@ -11,6 +11,7 @@
/* INCLUDES
******************************************************************/
#include <ntoskrnl.h>
+#include <ddk/wdmguid.h>
#define NDEBUG
#include <internal/debug.h>
@@ -434,7 +435,7 @@
BOOLEAN
IopCreateUnicodeString(
- PUNICODE_STRING Destination,
+ PUNICODE_STRING Destination,
PWSTR Source,
POOL_TYPE PoolType)
{
@@ -1318,6 +1319,10 @@
DeviceNode->Flags |= DNF_PROCESSED;
+ /* Report the device to the user-mode pnp manager */
+ IopQueueTargetDeviceEvent(&GUID_DEVICE_ARRIVAL,
+ &DeviceNode->InstancePath);
+
return STATUS_SUCCESS;
}