Author: tkreuzer
Date: Sun Feb 23 14:56:48 2014
New Revision: 62302
URL:
http://svn.reactos.org/svn/reactos?rev=62302&view=rev
Log:
[NTOSKRNL]
Implement WmipFastIoDeviceControl, start implementing WmipIoControl
Added:
branches/kernel-fun/reactos/include/reactos/wmiioctl.h
- copied unchanged from r62291,
branches/kernel-fun/reactos/include/reactos/wmiguid.h
Removed:
branches/kernel-fun/reactos/include/reactos/wmiguid.h
Modified:
branches/kernel-fun/reactos/ntoskrnl/wmi/wmidrv.c
Removed: branches/kernel-fun/reactos/include/reactos/wmiguid.h
URL:
http://svn.reactos.org/svn/reactos/branches/kernel-fun/reactos/include/reac…
==============================================================================
--- branches/kernel-fun/reactos/include/reactos/wmiguid.h [iso-8859-1] (original)
+++ branches/kernel-fun/reactos/include/reactos/wmiguid.h (removed)
@@ -1,37 +0,0 @@
-
-#pragma once
-
-#define IOCTL_WMI_QUERY_ALL_DATA CTL_CODE(FILE_DEVICE_UNKNOWN, 0x00, METHOD_BUFFERED,
FILE_READ_ACCESS) // 0x224000
-#define IOCTL_WMI_SINGLE_INSTANCE CTL_CODE(FILE_DEVICE_UNKNOWN, 0x01, METHOD_BUFFERED,
FILE_READ_ACCESS) // 0x224004
-#define IOCTL_WMI_SET_SINGLE_INSTANCE CTL_CODE(FILE_DEVICE_UNKNOWN, 0x02,
METHOD_BUFFERED, FILE_WRITE_ACCESS) // 0x228008
-#define IOCTL_WMI_SET_SINGLE_ITEM CTL_CODE(FILE_DEVICE_UNKNOWN, 0x03, METHOD_BUFFERED,
FILE_WRITE_ACCESS) // 0x22800C
-#define IOCTL_WMI_09 CTL_CODE(FILE_DEVICE_UNKNOWN, 0x09, METHOD_BUFFERED,
FILE_WRITE_ACCESS) // 0x228024
-#define IOCTL_WMI_20 CTL_CODE(FILE_DEVICE_UNKNOWN, 0x20, METHOD_BUFFERED,
FILE_ANY_ACCESS) // 0x220080
-#define IOCTL_WMI_21 CTL_CODE(FILE_DEVICE_UNKNOWN, 0x21, METHOD_BUFFERED,
FILE_ANY_ACCESS) // 0x220084
-#define IOCTL_WMI_22 CTL_CODE(FILE_DEVICE_UNKNOWN, 0x22, METHOD_BUFFERED,
FILE_ANY_ACCESS) // 0x220088
-#define IOCTL_WMI_TRACE_EVENT CTL_CODE(FILE_DEVICE_UNKNOWN, 0x23, METHOD_NEITHER,
FILE_WRITE_ACCESS) // 0x22808F
-#define IOCTL_WMI_24 CTL_CODE(FILE_DEVICE_UNKNOWN, 0x24, METHOD_BUFFERED,
FILE_ANY_ACCESS) // 0x220090
-#define IOCTL_WMI_25 CTL_CODE(FILE_DEVICE_UNKNOWN, 0x25, METHOD_BUFFERED,
FILE_ANY_ACCESS) // 0x220094
-#define IOCTL_WMI_TRACE_USER_MESSAGE CTL_CODE(FILE_DEVICE_UNKNOWN, 0x28, METHOD_NEITHER,
FILE_WRITE_ACCESS) // 0x2280A3
-#define IOCTL_WMI_29 CTL_CODE(FILE_DEVICE_UNKNOWN, 0x29, METHOD_BUFFERED,
FILE_ANY_ACCESS) // 0x2200A4
-#define IOCTL_WMI_2a CTL_CODE(FILE_DEVICE_UNKNOWN, 0x2a, METHOD_BUFFERED,
FILE_ANY_ACCESS) // 0x2200A8
-#define IOCTL_WMI_2b CTL_CODE(FILE_DEVICE_UNKNOWN, 0x2b, METHOD_BUFFERED,
FILE_ANY_ACCESS) // 0x2200AC
-#define IOCTL_WMI_42 CTL_CODE(FILE_DEVICE_UNKNOWN, 0x42, METHOD_BUFFERED,
FILE_READ_ACCESS) // 0x224108
-#define IOCTL_WMI_47 CTL_CODE(FILE_DEVICE_UNKNOWN, 0x47, METHOD_BUFFERED,
FILE_WRITE_ACCESS) // 0x22811C
-#define IOCTL_WMI_49 CTL_CODE(FILE_DEVICE_UNKNOWN, 0x49, METHOD_BUFFERED,
FILE_READ_ACCESS) // 0x224124
-#define IOCTL_WMI_4b CTL_CODE(FILE_DEVICE_UNKNOWN, 0x4b, METHOD_BUFFERED,
FILE_WRITE_ACCESS) // 0x22812C
-#define IOCTL_WMI_4c CTL_CODE(FILE_DEVICE_UNKNOWN, 0x4c, METHOD_BUFFERED,
FILE_WRITE_ACCESS) // 0x228130
-#define IOCTL_WMI_4d CTL_CODE(FILE_DEVICE_UNKNOWN, 0x4d, METHOD_BUFFERED,
FILE_READ_ACCESS) // 0x224134
-#define IOCTL_WMI_4e CTL_CODE(FILE_DEVICE_UNKNOWN, 0x4e, METHOD_BUFFERED,
FILE_READ_ACCESS) // 0x224138
-#define IOCTL_WMI_4f CTL_CODE(FILE_DEVICE_UNKNOWN, 0x4f, METHOD_BUFFERED,
FILE_READ_ACCESS) // 0x22413C
-#define IOCTL_WMI_OPEN_GUID_FOR_EVENTS CTL_CODE(FILE_DEVICE_UNKNOWN, 0x50,
METHOD_BUFFERED, FILE_READ_ACCESS) // 0x224140
-#define IOCTL_WMI_51 CTL_CODE(FILE_DEVICE_UNKNOWN, 0x51, METHOD_BUFFERED,
FILE_WRITE_ACCESS) // 0x228144
-#define IOCTL_WMI_52 CTL_CODE(FILE_DEVICE_UNKNOWN, 0x52, METHOD_BUFFERED,
FILE_READ_ACCESS) // 0x224148
-#define IOCTL_WMI_REGISTER_GUIDS CTL_CODE(FILE_DEVICE_UNKNOWN, 0x53, METHOD_BUFFERED,
FILE_READ_ACCESS) // 0x22414C, called from ntdll!EtwpRegisterGuids
-#define IOCTL_WMI_54 CTL_CODE(FILE_DEVICE_UNKNOWN, 0x54, METHOD_BUFFERED,
FILE_READ_ACCESS) // 0x224150
-#define IOCTL_WMI_55 CTL_CODE(FILE_DEVICE_UNKNOWN, 0x55, METHOD_BUFFERED,
FILE_READ_ACCESS) // 0x224154
-#define IOCTL_WMI_56 CTL_CODE(FILE_DEVICE_UNKNOWN, 0x56, METHOD_BUFFERED,
FILE_READ_ACCESS) // 0x224158
-#define IOCTL_WMI_57 CTL_CODE(FILE_DEVICE_UNKNOWN, 0x57, METHOD_BUFFERED,
FILE_READ_ACCESS) // 0x22415C
-#define IOCTL_WMI_58 CTL_CODE(FILE_DEVICE_UNKNOWN, 0x58, METHOD_BUFFERED,
FILE_READ_ACCESS) // 0x224160
-#define IOCTL_WMI_59 CTL_CODE(FILE_DEVICE_UNKNOWN, 0x59, METHOD_BUFFERED,
FILE_READ_ACCESS) // 0x224164
-#define IOCTL_WMI_5a CTL_CODE(FILE_DEVICE_UNKNOWN, 0x5a, METHOD_BUFFERED,
FILE_WRITE_ACCESS) // 0x228168
Modified: branches/kernel-fun/reactos/ntoskrnl/wmi/wmidrv.c
URL:
http://svn.reactos.org/svn/reactos/branches/kernel-fun/reactos/ntoskrnl/wmi…
==============================================================================
--- branches/kernel-fun/reactos/ntoskrnl/wmi/wmidrv.c [iso-8859-1] (original)
+++ branches/kernel-fun/reactos/ntoskrnl/wmi/wmidrv.c [iso-8859-1] Sun Feb 23 14:56:48
2014
@@ -10,10 +10,34 @@
#include <ntoskrnl.h>
#include <wmistr.h>
-#include <wmiguid.h>
+#include <wmiioctl.h>
+#include "wmip.h"
#define NDEBUG
#include <debug.h>
+
+// FIXME: these should go to a shared header
+typedef struct _WMIP_REGISTER_GUIDS
+{
+ POBJECT_ATTRIBUTES ObjectAttributes;
+ ULONG Unknown04;
+ ULONG Unknown08;
+ ULONG Unknown0C;
+ ULONG Unknown10;
+ ULONG Unknown14;
+
+ WMIREGINFOW RegInfo;
+} WMIP_REGISTER_GUIDS, *PWMIP_REGISTER_GUIDS;
+
+typedef struct _WMIP_RESULT
+{
+ HANDLE Handle;
+ ULONG Unknown04;
+ ULONG Unknown08;
+ ULONG Unknown0C;
+ BOOLEAN Unknown10;
+} WMIP_RESULT, *PWMIP_RESULT;
+
PDEVICE_OBJECT WmipServiceDeviceObject;
PDEVICE_OBJECT WmipAdminDeviceObject;
@@ -42,14 +66,167 @@
return STATUS_SUCCESS;
}
+static
+NTSTATUS
+WmiTraceEvent(
+ PVOID InputBuffer,
+ KPROCESSOR_MODE PreviousMode)
+{
+ UNIMPLEMENTED_DBGBREAK();
+ return STATUS_SUCCESS;
+}
+
+static
+NTSTATUS
+WmiTraceUserMessage(
+ PVOID InputBuffer,
+ ULONG InputBufferLength)
+{
+ UNIMPLEMENTED_DBGBREAK();
+ return STATUS_SUCCESS;
+}
+
+static
+NTSTATUS
+WmipRegisterGuids(
+ _In_ PDEVICE_OBJECT DeviceObject,
+ _In_ PVOID Buffer,
+ _In_ ULONG InputLength,
+ _Inout_ PULONG OutputLength)
+{
+ PWMIP_REGISTER_GUIDS RegisterGuids = (PWMIP_REGISTER_GUIDS)Buffer;
+ PWMIP_RESULT Result = (PWMIP_RESULT)Buffer;
+ OBJECT_ATTRIBUTES LocalObjectAttributes;
+ UNICODE_STRING LocalObjectName;
+ WCHAR LocalObjectNameBuffer[45 + 1];
+ KPROCESSOR_MODE PreviousMode;
+ HANDLE GuidObjectHandle;
+ PVOID GuidObject;
+ NTSTATUS Status;
+
+ /* Make sure the input buffer is large enough */
+ if ((InputLength < sizeof(WMIP_REGISTER_GUIDS)) ||
+ (RegisterGuids->RegInfo.BufferSize >
+ (InputLength - FIELD_OFFSET(WMIP_REGISTER_GUIDS, RegInfo))))
+ {
+ return STATUS_UNSUCCESSFUL;
+ }
+
+ /* Make sure we have a resonable GUID count */
+ if ((RegisterGuids->RegInfo.GuidCount == 0) ||
+ (RegisterGuids->RegInfo.GuidCount > 0x10000))
+ {
+ return STATUS_UNSUCCESSFUL;
+ }
+
+ _SEH2_TRY
+ {
+ /* Probe and copy the object attributes structure */
+ ProbeForRead(RegisterGuids->ObjectAttributes,
+ sizeof(OBJECT_ATTRIBUTES),
+ sizeof(PVOID));
+ LocalObjectAttributes = *RegisterGuids->ObjectAttributes;
+
+ /* Probe and copy the object name UNICODE_STRING */
+ ProbeForRead(LocalObjectAttributes.ObjectName,
+ sizeof(UNICODE_STRING),
+ sizeof(PVOID));
+ LocalObjectName = *LocalObjectAttributes.ObjectName;
+
+ /* Check if the object name has the expected length */
+ if (LocalObjectName.Length != 45 * sizeof(WCHAR))
+ {
+ return STATUS_INVALID_PARAMETER;
+ }
+
+ /* Probe and copy the object name buffer */
+ ProbeForRead(LocalObjectName.Buffer, LocalObjectName.Length, sizeof(WCHAR));
+ RtlCopyMemory(LocalObjectNameBuffer,
+ LocalObjectName.Buffer,
+ LocalObjectName.Length);
+
+ /* Fix pointers */
+ LocalObjectName.Buffer = LocalObjectNameBuffer;
+ LocalObjectAttributes.ObjectName = &LocalObjectName;
+ }
+ _SEH2_EXCEPT(EXCEPTION_EXECUTE_HANDLER)
+ {
+ DPRINT1("Got exception!\n");
+ return _SEH2_GetExceptionCode();
+ }
+ _SEH2_END;
+
+ /* Open a new GUID object */
+ PreviousMode = ExGetPreviousMode();
+ Status = WmipOpenGuidObject(&LocalObjectAttributes,
+ SPECIFIC_RIGHTS_ALL,
+ PreviousMode,
+ &GuidObjectHandle,
+ &GuidObject);
+ if (!NT_SUCCESS(Status))
+ {
+ return Status;
+ }
+
+ /* Derefernce the GUID object */
+ ObDereferenceObject(GuidObject);
+
+ /* Return the handle */
+ Result->Handle = GuidObjectHandle;
+ *OutputLength = 24;
+
+ return STATUS_SUCCESS;
+}
+
NTSTATUS
NTAPI
WmipIoControl(
- _Inout_ PDEVICE_OBJECT DeviceObject,
- _Inout_ PIRP Irp)
-{
- UNIMPLEMENTED_DBGBREAK();
- return STATUS_NOT_IMPLEMENTED;
+ _In_ PDEVICE_OBJECT DeviceObject,
+ _Inout_ PIRP Irp)
+{
+ PIO_STACK_LOCATION IoStackLocation;
+ ULONG IoControlCode;
+ PVOID Buffer;
+ ULONG InputLength, OutputLength;
+ NTSTATUS Status;
+ PAGED_CODE();
+
+ /* Get the current stack location */
+ IoStackLocation = IoGetCurrentIrpStackLocation(Irp);
+
+ /* Get the io control parameters */
+ IoControlCode = IoStackLocation->Parameters.DeviceIoControl.IoControlCode;
+ Buffer = Irp->AssociatedIrp.SystemBuffer;
+ InputLength = IoStackLocation->Parameters.DeviceIoControl.InputBufferLength;
+ OutputLength = IoStackLocation->Parameters.DeviceIoControl.OutputBufferLength;
+
+ switch (IoControlCode)
+ {
+
+ case IOCTL_WMI_REGISTER_GUIDS:
+ {
+ Status = WmipRegisterGuids(DeviceObject,
+ Buffer,
+ InputLength,
+ &OutputLength);
+ break;
+ }
+
+ default:
+ DPRINT1("Unsupported yet IOCTL: 0x%lx\n", IoControlCode);
+ Status = STATUS_INVALID_DEVICE_REQUEST;
+ __debugbreak();
+ break;
+ }
+
+ if (Status == STATUS_PENDING)
+ return Status;
+
+ Irp->IoStatus.Status = Status;
+ Irp->IoStatus.Information = NT_SUCCESS(Status) ? OutputLength : 0;
+
+ IoCompleteRequest(Irp, IO_NO_INCREMENT);
+ return Status;
}
NTSTATUS
@@ -87,7 +264,32 @@
_Out_ PIO_STATUS_BLOCK IoStatus,
_In_ PDEVICE_OBJECT DeviceObject)
{
- UNIMPLEMENTED_DBGBREAK();
+ PAGED_CODE();
+
+ if (IoControlCode == IOCTL_WMI_TRACE_EVENT)
+ {
+ if (InputBufferLength < 0x30)
+ {
+ DPRINT1("Buffer too small\n");
+ return FALSE;
+ }
+
+ IoStatus->Status = WmiTraceEvent(InputBuffer, ExGetPreviousMode());
+ return TRUE;
+ }
+ else if (IoControlCode == IOCTL_WMI_TRACE_USER_MESSAGE)
+ {
+ if (InputBufferLength < 0x30)
+ {
+ DPRINT1("Buffer too small\n");
+ return FALSE;
+ }
+
+ IoStatus->Status = WmiTraceUserMessage(InputBuffer, InputBufferLength);
+ return TRUE;
+ }
+
+ DPRINT1("Invalid io control code for fast dispatch: 0x%lx\n",
IoControlCode);
return FALSE;
}