PDEVICE_OBJECT PhysicalDeviceObject;
CHAR Name[MAXNAMELEN];
- PXENFILT_THREAD SystemPowerThread;
- PIRP SystemPowerIrp;
- PXENFILT_THREAD DevicePowerThread;
- PIRP DevicePowerIrp;
-
MUTEX Mutex;
LIST_ENTRY List;
ULONG References;
return status;
}
+__drv_functionClass(IO_COMPLETION_ROUTINE)
+__drv_sameIRQL
static NTSTATUS
-FdoSetDevicePowerUp(
- IN PXENFILT_FDO Fdo,
- IN PIRP Irp
+FdoSetDevicePowerUpComplete(
+ IN PDEVICE_OBJECT DeviceObject,
+ IN PIRP Irp,
+ IN PVOID Context
)
{
+ PXENFILT_FDO Fdo = (PXENFILT_FDO)Context;
PIO_STACK_LOCATION StackLocation;
- DEVICE_POWER_STATE DeviceState;
POWER_STATE PowerState;
- NTSTATUS status;
+
+ UNREFERENCED_PARAMETER(DeviceObject);
StackLocation = IoGetCurrentIrpStackLocation(Irp);
- DeviceState = StackLocation->Parameters.Power.State.DeviceState;
+ PowerState = StackLocation->Parameters.Power.State;
- ASSERT3U(DeviceState, <, __FdoGetDevicePowerState(Fdo));
+ ASSERT3U(PowerState.DeviceState, <, __FdoGetDevicePowerState(Fdo));
- status = FdoForwardIrpSynchronously(Fdo, Irp);
- if (!NT_SUCCESS(status))
- goto done;
+ if (Irp->PendingReturned)
+ IoMarkIrpPending(Irp);
Trace("%s: %s -> %s\n",
__FdoGetName(Fdo),
DevicePowerStateName(__FdoGetDevicePowerState(Fdo)),
- DevicePowerStateName(DeviceState));
+ DevicePowerStateName(PowerState.DeviceState));
- PowerState.DeviceState = DeviceState;
PoSetPowerState(Fdo->Dx->DeviceObject,
DevicePowerState,
PowerState);
- __FdoSetDevicePowerState(Fdo, DeviceState);
+ __FdoSetDevicePowerState(Fdo, PowerState.DeviceState);
-done:
- IoCompleteRequest(Irp, IO_NO_INCREMENT);
+ return STATUS_CONTINUE_COMPLETION;
+}
- return status;
+static FORCEINLINE NTSTATUS
+__FdoSetDevicePowerUp(
+ IN PXENFILT_FDO Fdo,
+ IN PIRP Irp
+ )
+{
+ IoCopyCurrentIrpStackLocationToNext(Irp);
+ IoSetCompletionRoutine(Irp,
+ FdoSetDevicePowerUpComplete,
+ Fdo,
+ TRUE,
+ TRUE,
+ TRUE);
+
+ return IoCallDriver(Fdo->LowerDeviceObject, Irp);
}
static NTSTATUS
-FdoSetDevicePowerDown(
+__FdoSetDevicePowerDown(
IN PXENFILT_FDO Fdo,
IN PIRP Irp
)
{
PIO_STACK_LOCATION StackLocation;
- DEVICE_POWER_STATE DeviceState;
POWER_STATE PowerState;
- NTSTATUS status;
StackLocation = IoGetCurrentIrpStackLocation(Irp);
- DeviceState = StackLocation->Parameters.Power.State.DeviceState;
+ PowerState = StackLocation->Parameters.Power.State;
- ASSERT3U(DeviceState, >, __FdoGetDevicePowerState(Fdo));
+ ASSERT3U(PowerState.DeviceState, >, __FdoGetDevicePowerState(Fdo));
Trace("%s: %s -> %s\n",
__FdoGetName(Fdo),
DevicePowerStateName(__FdoGetDevicePowerState(Fdo)),
- DevicePowerStateName(DeviceState));
+ DevicePowerStateName(PowerState.DeviceState));
- PowerState.DeviceState = DeviceState;
PoSetPowerState(Fdo->Dx->DeviceObject,
DevicePowerState,
PowerState);
- __FdoSetDevicePowerState(Fdo, DeviceState);
+ __FdoSetDevicePowerState(Fdo, PowerState.DeviceState);
- status = FdoForwardIrpSynchronously(Fdo, Irp);
- IoCompleteRequest(Irp, IO_NO_INCREMENT);
-
- return status;
+ IoSkipCurrentIrpStackLocation(Irp);
+ return IoCallDriver(Fdo->LowerDeviceObject, Irp);
}
static NTSTATUS
PowerActionName(PowerAction));
if (DeviceState == __FdoGetDevicePowerState(Fdo)) {
- status = FdoForwardIrpSynchronously(Fdo, Irp);
- IoCompleteRequest(Irp, IO_NO_INCREMENT);
+ IoSkipCurrentIrpStackLocation(Irp);
+ status = IoCallDriver(Fdo->LowerDeviceObject, Irp);
goto done;
}
status = (DeviceState < __FdoGetDevicePowerState(Fdo)) ?
- FdoSetDevicePowerUp(Fdo, Irp) :
- FdoSetDevicePowerDown(Fdo, Irp);
+ __FdoSetDevicePowerUp(Fdo, Irp) :
+ __FdoSetDevicePowerDown(Fdo, Irp);
done:
Trace("%s: <==== (%s:%s)(%08x)\n",
return status;
}
-static NTSTATUS
-FdoSetSystemPowerUp(
+static FORCEINLINE NTSTATUS
+__FdoDispatchDevicePower(
IN PXENFILT_FDO Fdo,
IN PIRP Irp
)
{
PIO_STACK_LOCATION StackLocation;
- SYSTEM_POWER_STATE SystemState;
+ UCHAR MinorFunction;
NTSTATUS status;
StackLocation = IoGetCurrentIrpStackLocation(Irp);
- SystemState = StackLocation->Parameters.Power.State.SystemState;
-
- ASSERT3U(SystemState, <, __FdoGetSystemPowerState(Fdo));
-
- status = FdoForwardIrpSynchronously(Fdo, Irp);
- if (!NT_SUCCESS(status))
- goto done;
-
- Trace("%s: %s -> %s\n",
- __FdoGetName(Fdo),
- SystemPowerStateName(__FdoGetSystemPowerState(Fdo)),
- SystemPowerStateName(SystemState));
+ MinorFunction = StackLocation->MinorFunction;
- __FdoSetSystemPowerState(Fdo, SystemState);
+ switch (MinorFunction) {
+ case IRP_MN_SET_POWER:
+ status = FdoSetDevicePower(Fdo, Irp);
+ break;
-done:
- IoCompleteRequest(Irp, IO_NO_INCREMENT);
+ default:
+ IoSkipCurrentIrpStackLocation(Irp);
+ status = IoCallDriver(Fdo->LowerDeviceObject, Irp);
+ break;
+ }
return status;
}
+__drv_functionClass(IO_COMPLETION_ROUTINE)
+__drv_sameIRQL
static NTSTATUS
-FdoSetSystemPowerDown(
- IN PXENFILT_FDO Fdo,
- IN PIRP Irp
+FdoSetSystemPowerUpComplete(
+ IN PDEVICE_OBJECT DeviceObject,
+ IN PIRP Irp,
+ IN PVOID Context
)
{
+ PXENFILT_FDO Fdo = (PXENFILT_FDO)Context;
PIO_STACK_LOCATION StackLocation;
SYSTEM_POWER_STATE SystemState;
- NTSTATUS status;
+
+ UNREFERENCED_PARAMETER(DeviceObject);
StackLocation = IoGetCurrentIrpStackLocation(Irp);
SystemState = StackLocation->Parameters.Power.State.SystemState;
- ASSERT3U(SystemState, >, __FdoGetSystemPowerState(Fdo));
+ ASSERT3U(SystemState, <, __FdoGetSystemPowerState(Fdo));
+
+ if (Irp->PendingReturned)
+ IoMarkIrpPending(Irp);
Trace("%s: %s -> %s\n",
__FdoGetName(Fdo),
__FdoSetSystemPowerState(Fdo, SystemState);
- status = FdoForwardIrpSynchronously(Fdo, Irp);
- IoCompleteRequest(Irp, IO_NO_INCREMENT);
-
- return status;
-}
-
-static NTSTATUS
-FdoSetSystemPower(
- IN PXENFILT_FDO Fdo,
- IN PIRP Irp
- )
-{
- PIO_STACK_LOCATION StackLocation;
- SYSTEM_POWER_STATE SystemState;
- POWER_ACTION PowerAction;
- NTSTATUS status;
-
- StackLocation = IoGetCurrentIrpStackLocation(Irp);
- SystemState = StackLocation->Parameters.Power.State.SystemState;
- PowerAction = StackLocation->Parameters.Power.ShutdownType;
-
- Trace("%s: ====> (%s:%s)\n",
- __FdoGetName(Fdo),
- SystemPowerStateName(SystemState),
- PowerActionName(PowerAction));
-
- if (SystemState == __FdoGetSystemPowerState(Fdo)) {
- status = FdoForwardIrpSynchronously(Fdo, Irp);
- IoCompleteRequest(Irp, IO_NO_INCREMENT);
-
- goto done;
- }
-
- status = (SystemState < __FdoGetSystemPowerState(Fdo)) ?
- FdoSetSystemPowerUp(Fdo, Irp) :
- FdoSetSystemPowerDown(Fdo, Irp);
-
-done:
- Trace("%s: <==== (%s:%s)(%08x)\n",
- __FdoGetName(Fdo),
- SystemPowerStateName(SystemState),
- PowerActionName(PowerAction),
- status);
- return status;
-}
-
-static NTSTATUS
-FdoQueryDevicePowerUp(
- IN PXENFILT_FDO Fdo,
- IN PIRP Irp
- )
-{
- PIO_STACK_LOCATION StackLocation;
- DEVICE_POWER_STATE DeviceState;
- NTSTATUS status;
-
- StackLocation = IoGetCurrentIrpStackLocation(Irp);
- DeviceState = StackLocation->Parameters.Power.State.DeviceState;
-
- ASSERT3U(DeviceState, <, __FdoGetDevicePowerState(Fdo));
-
- status = FdoForwardIrpSynchronously(Fdo, Irp);
-
- IoCompleteRequest(Irp, IO_NO_INCREMENT);
-
- return status;
+ return STATUS_CONTINUE_COMPLETION;
}
-static NTSTATUS
-FdoQueryDevicePowerDown(
- IN PXENFILT_FDO Fdo,
- IN PIRP Irp
- )
-{
- PIO_STACK_LOCATION StackLocation;
- DEVICE_POWER_STATE DeviceState;
- NTSTATUS status;
-
- StackLocation = IoGetCurrentIrpStackLocation(Irp);
- DeviceState = StackLocation->Parameters.Power.State.DeviceState;
-
- ASSERT3U(DeviceState, >, __FdoGetDevicePowerState(Fdo));
-
- status = FdoForwardIrpSynchronously(Fdo, Irp);
- IoCompleteRequest(Irp, IO_NO_INCREMENT);
-
- return status;
-}
-
-static NTSTATUS
-FdoQueryDevicePower(
+static FORCEINLINE NTSTATUS
+__FdoSetSystemPowerUp(
IN PXENFILT_FDO Fdo,
IN PIRP Irp
)
{
- PIO_STACK_LOCATION StackLocation;
- DEVICE_POWER_STATE DeviceState;
- POWER_ACTION PowerAction;
- NTSTATUS status;
-
- StackLocation = IoGetCurrentIrpStackLocation(Irp);
- DeviceState = StackLocation->Parameters.Power.State.DeviceState;
- PowerAction = StackLocation->Parameters.Power.ShutdownType;
-
- Trace("%s: ====> (%s:%s)\n",
- __FdoGetName(Fdo),
- DevicePowerStateName(DeviceState),
- PowerActionName(PowerAction));
-
- if (DeviceState == __FdoGetDevicePowerState(Fdo)) {
- status = FdoForwardIrpSynchronously(Fdo, Irp);
- IoCompleteRequest(Irp, IO_NO_INCREMENT);
-
- goto done;
- }
-
- status = (DeviceState < __FdoGetDevicePowerState(Fdo)) ?
- FdoQueryDevicePowerUp(Fdo, Irp) :
- FdoQueryDevicePowerDown(Fdo, Irp);
-
-done:
- Trace("%s: <==== (%s:%s)(%08x)\n",
- __FdoGetName(Fdo),
- DevicePowerStateName(DeviceState),
- PowerActionName(PowerAction),
- status);
- return status;
-}
-
-static NTSTATUS
-FdoQuerySystemPowerUp(
- IN PXENFILT_FDO Fdo,
- IN PIRP Irp
- )
-{
- PIO_STACK_LOCATION StackLocation;
- SYSTEM_POWER_STATE SystemState;
- NTSTATUS status;
-
- StackLocation = IoGetCurrentIrpStackLocation(Irp);
- SystemState = StackLocation->Parameters.Power.State.SystemState;
-
- ASSERT3U(SystemState, <, __FdoGetSystemPowerState(Fdo));
-
- status = FdoForwardIrpSynchronously(Fdo, Irp);
-
- IoCompleteRequest(Irp, IO_NO_INCREMENT);
-
- return status;
+ IoCopyCurrentIrpStackLocationToNext(Irp);
+ IoSetCompletionRoutine(Irp,
+ FdoSetSystemPowerUpComplete,
+ Fdo,
+ TRUE,
+ TRUE,
+ TRUE);
+ return IoCallDriver(Fdo->LowerDeviceObject, Irp);
}
-static NTSTATUS
-FdoQuerySystemPowerDown(
+static FORCEINLINE NTSTATUS
+__FdoSetSystemPowerDown(
IN PXENFILT_FDO Fdo,
IN PIRP Irp
)
{
PIO_STACK_LOCATION StackLocation;
SYSTEM_POWER_STATE SystemState;
- NTSTATUS status;
StackLocation = IoGetCurrentIrpStackLocation(Irp);
SystemState = StackLocation->Parameters.Power.State.SystemState;
ASSERT3U(SystemState, >, __FdoGetSystemPowerState(Fdo));
- status = FdoForwardIrpSynchronously(Fdo, Irp);
- IoCompleteRequest(Irp, IO_NO_INCREMENT);
+ Trace("%s: %s -> %s\n",
+ __FdoGetName(Fdo),
+ SystemPowerStateName(__FdoGetSystemPowerState(Fdo)),
+ SystemPowerStateName(SystemState));
- return status;
+ __FdoSetSystemPowerState(Fdo, SystemState);
+
+ IoSkipCurrentIrpStackLocation(Irp);
+ return IoCallDriver(Fdo->LowerDeviceObject, Irp);
}
static NTSTATUS
-FdoQuerySystemPower(
+FdoSetSystemPower(
IN PXENFILT_FDO Fdo,
IN PIRP Irp
)
PowerActionName(PowerAction));
if (SystemState == __FdoGetSystemPowerState(Fdo)) {
- status = FdoForwardIrpSynchronously(Fdo, Irp);
- IoCompleteRequest(Irp, IO_NO_INCREMENT);
+ IoSkipCurrentIrpStackLocation(Irp);
+ status = IoCallDriver(Fdo->LowerDeviceObject, Irp);
goto done;
}
status = (SystemState < __FdoGetSystemPowerState(Fdo)) ?
- FdoQuerySystemPowerUp(Fdo, Irp) :
- FdoQuerySystemPowerDown(Fdo, Irp);
+ __FdoSetSystemPowerUp(Fdo, Irp) :
+ __FdoSetSystemPowerDown(Fdo, Irp);
done:
Trace("%s: <==== (%s:%s)(%08x)\n",
SystemPowerStateName(SystemState),
PowerActionName(PowerAction),
status);
-
return status;
}
-static NTSTATUS
-FdoDevicePower(
- IN PXENFILT_THREAD Self,
- IN PVOID Context
- )
-{
- PXENFILT_FDO Fdo = Context;
- PKEVENT Event;
-
- Event = ThreadGetEvent(Self);
-
- for (;;) {
- PIRP Irp;
- PIO_STACK_LOCATION StackLocation;
- UCHAR MinorFunction;
-
- if (Fdo->DevicePowerIrp == NULL) {
- (VOID) KeWaitForSingleObject(Event,
- Executive,
- KernelMode,
- FALSE,
- NULL);
- KeClearEvent(Event);
- }
-
- if (ThreadIsAlerted(Self))
- break;
-
- Irp = Fdo->DevicePowerIrp;
-
- if (Irp == NULL)
- continue;
-
- Fdo->DevicePowerIrp = NULL;
- KeMemoryBarrier();
-
- StackLocation = IoGetCurrentIrpStackLocation(Irp);
- MinorFunction = StackLocation->MinorFunction;
-
- switch (StackLocation->MinorFunction) {
- case IRP_MN_SET_POWER:
- (VOID) FdoSetDevicePower(Fdo, Irp);
- break;
-
- case IRP_MN_QUERY_POWER:
- (VOID) FdoQueryDevicePower(Fdo, Irp);
- break;
-
- default:
- ASSERT(FALSE);
- break;
- }
-
- IoReleaseRemoveLock(&Fdo->Dx->RemoveLock, Irp);
- }
-
- return STATUS_SUCCESS;
-}
-
-static NTSTATUS
-FdoSystemPower(
- IN PXENFILT_THREAD Self,
- IN PVOID Context
+static FORCEINLINE NTSTATUS
+__FdoDispatchSystemPower(
+ IN PXENFILT_FDO Fdo,
+ IN PIRP Irp
)
{
- PXENFILT_FDO Fdo = Context;
- PKEVENT Event;
-
- Event = ThreadGetEvent(Self);
-
- for (;;) {
- PIRP Irp;
- PIO_STACK_LOCATION StackLocation;
- UCHAR MinorFunction;
-
- if (Fdo->SystemPowerIrp == NULL) {
- (VOID) KeWaitForSingleObject(Event,
- Executive,
- KernelMode,
- FALSE,
- NULL);
- KeClearEvent(Event);
- }
-
- if (ThreadIsAlerted(Self))
- break;
-
- Irp = Fdo->SystemPowerIrp;
-
- if (Irp == NULL)
- continue;
-
- Fdo->SystemPowerIrp = NULL;
- KeMemoryBarrier();
-
- StackLocation = IoGetCurrentIrpStackLocation(Irp);
- MinorFunction = StackLocation->MinorFunction;
-
- switch (StackLocation->MinorFunction) {
- case IRP_MN_SET_POWER:
- (VOID) FdoSetSystemPower(Fdo, Irp);
- break;
+ PIO_STACK_LOCATION StackLocation;
+ UCHAR MinorFunction;
+ NTSTATUS status;
- case IRP_MN_QUERY_POWER:
- (VOID) FdoQuerySystemPower(Fdo, Irp);
- break;
+ StackLocation = IoGetCurrentIrpStackLocation(Irp);
+ MinorFunction = StackLocation->MinorFunction;
- default:
- ASSERT(FALSE);
- break;
- }
+ switch (MinorFunction) {
+ case IRP_MN_SET_POWER:
+ status = FdoSetSystemPower(Fdo, Irp);
+ break;
- IoReleaseRemoveLock(&Fdo->Dx->RemoveLock, Irp);
+ default:
+ IoSkipCurrentIrpStackLocation(Irp);
+ status = IoCallDriver(Fdo->LowerDeviceObject, Irp);
+ break;
}
- return STATUS_SUCCESS;
+ return status;
}
static NTSTATUS
StackLocation = IoGetCurrentIrpStackLocation(Irp);
MinorFunction = StackLocation->MinorFunction;
- if (MinorFunction != IRP_MN_QUERY_POWER &&
- MinorFunction != IRP_MN_SET_POWER) {
+ if (MinorFunction != IRP_MN_SET_POWER) {
IoSkipCurrentIrpStackLocation(Irp);
status = IoCallDriver(Fdo->LowerDeviceObject, Irp);
switch (PowerType) {
case DevicePowerState:
- IoMarkIrpPending(Irp);
-
- ASSERT3P(Fdo->DevicePowerIrp, ==, NULL);
- Fdo->DevicePowerIrp = Irp;
- KeMemoryBarrier();
-
- ThreadWake(Fdo->DevicePowerThread);
-
- status = STATUS_PENDING;
+ status = __FdoDispatchDevicePower(Fdo, Irp);
+ IoReleaseRemoveLock(&Fdo->Dx->RemoveLock, Irp);
break;
case SystemPowerState:
- IoMarkIrpPending(Irp);
-
- ASSERT3P(Fdo->SystemPowerIrp, ==, NULL);
- Fdo->SystemPowerIrp = Irp;
- KeMemoryBarrier();
-
- ThreadWake(Fdo->SystemPowerThread);
-
- status = STATUS_PENDING;
+ status = __FdoDispatchSystemPower(Fdo, Irp);
+ IoReleaseRemoveLock(&Fdo->Dx->RemoveLock, Irp);
break;
default:
Fdo->LowerDeviceObject = LowerDeviceObject;
Fdo->Type = Type;
- status = ThreadCreate(FdoSystemPower, Fdo, &Fdo->SystemPowerThread);
- if (!NT_SUCCESS(status))
- goto fail4;
-
- status = ThreadCreate(FdoDevicePower, Fdo, &Fdo->DevicePowerThread);
- if (!NT_SUCCESS(status))
- goto fail5;
-
status = __FdoSetDeviceID(Fdo);
if (!NT_SUCCESS(status))
- goto fail6;
+ goto fail4;
status = __FdoSetInstanceID(Fdo);
if (!NT_SUCCESS(status))
- goto fail7;
+ goto fail5;
__FdoSetName(Fdo);
return STATUS_SUCCESS;
-fail7:
- Error("fail7\n");
-
- __FdoClearDeviceID(Fdo);
-
-fail6:
- Error("fail6\n");
-
- ThreadAlert(Fdo->DevicePowerThread);
- ThreadJoin(Fdo->DevicePowerThread);
- Fdo->DevicePowerThread = NULL;
-
fail5:
Error("fail5\n");
- ThreadAlert(Fdo->SystemPowerThread);
- ThreadJoin(Fdo->SystemPowerThread);
- Fdo->SystemPowerThread = NULL;
+ __FdoClearDeviceID(Fdo);
fail4:
Error("fail4\n");
__FdoClearInstanceID(Fdo);
__FdoClearDeviceID(Fdo);
- ThreadAlert(Fdo->DevicePowerThread);
- ThreadJoin(Fdo->DevicePowerThread);
- Fdo->DevicePowerThread = NULL;
-
- ThreadAlert(Fdo->SystemPowerThread);
- ThreadJoin(Fdo->SystemPowerThread);
- Fdo->SystemPowerThread = NULL;
-
Fdo->Type = XENFILT_EMULATED_OBJECT_TYPE_UNKNOWN;
Fdo->LowerDeviceObject = NULL;
Fdo->PhysicalDeviceObject = NULL;
PDEVICE_OBJECT PhysicalDeviceObject;
CHAR Name[MAXNAMELEN];
- PXENFILT_THREAD SystemPowerThread;
- PIRP SystemPowerIrp;
- PXENFILT_THREAD DevicePowerThread;
- PIRP DevicePowerIrp;
-
PXENFILT_FDO Fdo;
BOOLEAN Missing;
const CHAR *Reason;
return status;
}
+__drv_functionClass(IO_COMPLETION_ROUTINE)
+__drv_sameIRQL
static NTSTATUS
-PdoSetDevicePowerUp(
- IN PXENFILT_PDO Pdo,
- IN PIRP Irp
+PdoSetDevicePowerUpComplete(
+ IN PDEVICE_OBJECT DeviceObject,
+ IN PIRP Irp,
+ IN PVOID Context
)
{
+ PXENFILT_PDO Pdo = (PXENFILT_PDO)Context;
PIO_STACK_LOCATION StackLocation;
- DEVICE_POWER_STATE DeviceState;
POWER_STATE PowerState;
- NTSTATUS status;
+
+ UNREFERENCED_PARAMETER(DeviceObject);
StackLocation = IoGetCurrentIrpStackLocation(Irp);
- DeviceState = StackLocation->Parameters.Power.State.DeviceState;
+ PowerState = StackLocation->Parameters.Power.State;
- ASSERT3U(DeviceState, <, __PdoGetDevicePowerState(Pdo));
+ ASSERT3U(PowerState.DeviceState, <, __PdoGetDevicePowerState(Pdo));
- status = PdoForwardIrpSynchronously(Pdo, Irp);
- if (!NT_SUCCESS(status))
- goto done;
+ if (Irp->PendingReturned)
+ IoMarkIrpPending(Irp);
Trace("%s: %s -> %s\n",
__PdoGetName(Pdo),
DevicePowerStateName(__PdoGetDevicePowerState(Pdo)),
- DevicePowerStateName(DeviceState));
+ DevicePowerStateName(PowerState.DeviceState));
- PowerState.DeviceState = DeviceState;
PoSetPowerState(__PdoGetDeviceObject(Pdo),
DevicePowerState,
PowerState);
- __PdoSetDevicePowerState(Pdo, DeviceState);
+ __PdoSetDevicePowerState(Pdo, PowerState.DeviceState);
-done:
- Irp->IoStatus.Status = status;
- IoCompleteRequest(Irp, IO_NO_INCREMENT);
+ return STATUS_CONTINUE_COMPLETION;
+}
- return status;
+static FORCEINLINE NTSTATUS
+__PdoSetDevicePowerUp(
+ IN PXENFILT_PDO Pdo,
+ IN PIRP Irp
+ )
+{
+ IoCopyCurrentIrpStackLocationToNext(Irp);
+ IoSetCompletionRoutine(Irp,
+ PdoSetDevicePowerUpComplete,
+ Pdo,
+ TRUE,
+ TRUE,
+ TRUE);
+ return IoCallDriver(Pdo->LowerDeviceObject, Irp);
}
static NTSTATUS
-PdoSetDevicePowerDown(
+__PdoSetDevicePowerDown(
IN PXENFILT_PDO Pdo,
IN PIRP Irp
)
{
PIO_STACK_LOCATION StackLocation;
- DEVICE_POWER_STATE DeviceState;
POWER_STATE PowerState;
- NTSTATUS status;
StackLocation = IoGetCurrentIrpStackLocation(Irp);
- DeviceState = StackLocation->Parameters.Power.State.DeviceState;
+ PowerState = StackLocation->Parameters.Power.State;
- ASSERT3U(DeviceState, >, __PdoGetDevicePowerState(Pdo));
+ ASSERT3U(PowerState.DeviceState, >, __PdoGetDevicePowerState(Pdo));
Trace("%s: %s -> %s\n",
__PdoGetName(Pdo),
DevicePowerStateName(__PdoGetDevicePowerState(Pdo)),
- DevicePowerStateName(DeviceState));
+ DevicePowerStateName(PowerState.DeviceState));
- PowerState.DeviceState = DeviceState;
PoSetPowerState(__PdoGetDeviceObject(Pdo),
DevicePowerState,
PowerState);
- __PdoSetDevicePowerState(Pdo, DeviceState);
+ __PdoSetDevicePowerState(Pdo, PowerState.DeviceState);
- status = PdoForwardIrpSynchronously(Pdo, Irp);
- IoCompleteRequest(Irp, IO_NO_INCREMENT);
-
- return status;
+ IoSkipCurrentIrpStackLocation(Irp);
+ return IoCallDriver(Pdo->LowerDeviceObject, Irp);
}
static NTSTATUS
PowerActionName(PowerAction));
if (DeviceState == __PdoGetDevicePowerState(Pdo)) {
- status = PdoForwardIrpSynchronously(Pdo, Irp);
- IoCompleteRequest(Irp, IO_NO_INCREMENT);
+ IoSkipCurrentIrpStackLocation(Irp);
+ status = IoCallDriver(Pdo->LowerDeviceObject, Irp);
goto done;
}
status = (DeviceState < __PdoGetDevicePowerState(Pdo)) ?
- PdoSetDevicePowerUp(Pdo, Irp) :
- PdoSetDevicePowerDown(Pdo, Irp);
+ __PdoSetDevicePowerUp(Pdo, Irp) :
+ __PdoSetDevicePowerDown(Pdo, Irp);
done:
Trace("%s: <==== (%s:%s)(%08x)\n",
return status;
}
-static NTSTATUS
-PdoSetSystemPowerUp(
+static FORCEINLINE NTSTATUS
+__PdoDispatchDevicePower(
IN PXENFILT_PDO Pdo,
IN PIRP Irp
)
{
PIO_STACK_LOCATION StackLocation;
- SYSTEM_POWER_STATE SystemState;
+ UCHAR MinorFunction;
NTSTATUS status;
StackLocation = IoGetCurrentIrpStackLocation(Irp);
- SystemState = StackLocation->Parameters.Power.State.SystemState;
-
- ASSERT3U(SystemState, <, __PdoGetSystemPowerState(Pdo));
-
- status = PdoForwardIrpSynchronously(Pdo, Irp);
- if (!NT_SUCCESS(status))
- goto done;
-
- Trace("%s: %s -> %s\n",
- __PdoGetName(Pdo),
- SystemPowerStateName(__PdoGetSystemPowerState(Pdo)),
- SystemPowerStateName(SystemState));
+ MinorFunction = StackLocation->MinorFunction;
- __PdoSetSystemPowerState(Pdo, SystemState);
+ switch (MinorFunction) {
+ case IRP_MN_SET_POWER:
+ status = PdoSetDevicePower(Pdo, Irp);
+ break;
-done:
- Irp->IoStatus.Status = status;
- IoCompleteRequest(Irp, IO_NO_INCREMENT);
+ default:
+ IoSkipCurrentIrpStackLocation(Irp);
+ status = IoCallDriver(Pdo->LowerDeviceObject, Irp);
+ break;
+ }
return status;
}
+__drv_functionClass(IO_COMPLETION_ROUTINE)
+__drv_sameIRQL
static NTSTATUS
-PdoSetSystemPowerDown(
- IN PXENFILT_PDO Pdo,
- IN PIRP Irp
+PdoSetSystemPowerUpComplete(
+ IN PDEVICE_OBJECT DeviceObject,
+ IN PIRP Irp,
+ IN PVOID Context
)
{
+ PXENFILT_PDO Pdo = (PXENFILT_PDO)Context;
PIO_STACK_LOCATION StackLocation;
SYSTEM_POWER_STATE SystemState;
- NTSTATUS status;
+
+ UNREFERENCED_PARAMETER(DeviceObject);
StackLocation = IoGetCurrentIrpStackLocation(Irp);
SystemState = StackLocation->Parameters.Power.State.SystemState;
- ASSERT3U(SystemState, >, __PdoGetSystemPowerState(Pdo));
+ ASSERT3U(SystemState, <, __PdoGetSystemPowerState(Pdo));
+
+ if (Irp->PendingReturned)
+ IoMarkIrpPending(Irp);
Trace("%s: %s -> %s\n",
__PdoGetName(Pdo),
__PdoSetSystemPowerState(Pdo, SystemState);
- status = PdoForwardIrpSynchronously(Pdo, Irp);
- IoCompleteRequest(Irp, IO_NO_INCREMENT);
-
- return status;
-}
-
-static NTSTATUS
-PdoSetSystemPower(
- IN PXENFILT_PDO Pdo,
- IN PIRP Irp
- )
-{
- PIO_STACK_LOCATION StackLocation;
- SYSTEM_POWER_STATE SystemState;
- POWER_ACTION PowerAction;
- NTSTATUS status;
-
- StackLocation = IoGetCurrentIrpStackLocation(Irp);
- SystemState = StackLocation->Parameters.Power.State.SystemState;
- PowerAction = StackLocation->Parameters.Power.ShutdownType;
-
- Trace("%s: ====> (%s:%s)\n",
- __PdoGetName(Pdo),
- SystemPowerStateName(SystemState),
- PowerActionName(PowerAction));
-
- if (SystemState == __PdoGetSystemPowerState(Pdo)) {
- status = PdoForwardIrpSynchronously(Pdo, Irp);
- IoCompleteRequest(Irp, IO_NO_INCREMENT);
-
- goto done;
- }
-
- status = (SystemState < __PdoGetSystemPowerState(Pdo)) ?
- PdoSetSystemPowerUp(Pdo, Irp) :
- PdoSetSystemPowerDown(Pdo, Irp);
-
-done:
- Trace("%s: <==== (%s:%s)(%08x)\n",
- __PdoGetName(Pdo),
- SystemPowerStateName(SystemState),
- PowerActionName(PowerAction),
- status);
- return status;
-}
-
-static NTSTATUS
-PdoQueryDevicePowerUp(
- IN PXENFILT_PDO Pdo,
- IN PIRP Irp
- )
-{
- PIO_STACK_LOCATION StackLocation;
- DEVICE_POWER_STATE DeviceState;
- NTSTATUS status;
-
- StackLocation = IoGetCurrentIrpStackLocation(Irp);
- DeviceState = StackLocation->Parameters.Power.State.DeviceState;
-
- ASSERT3U(DeviceState, <, __PdoGetDevicePowerState(Pdo));
-
- status = PdoForwardIrpSynchronously(Pdo, Irp);
-
- Irp->IoStatus.Status = status;
- IoCompleteRequest(Irp, IO_NO_INCREMENT);
-
- return status;
-}
-
-static NTSTATUS
-PdoQueryDevicePowerDown(
- IN PXENFILT_PDO Pdo,
- IN PIRP Irp
- )
-{
- PIO_STACK_LOCATION StackLocation;
- DEVICE_POWER_STATE DeviceState;
- NTSTATUS status;
-
- StackLocation = IoGetCurrentIrpStackLocation(Irp);
- DeviceState = StackLocation->Parameters.Power.State.DeviceState;
-
- ASSERT3U(DeviceState, >, __PdoGetDevicePowerState(Pdo));
-
- status = PdoForwardIrpSynchronously(Pdo, Irp);
- IoCompleteRequest(Irp, IO_NO_INCREMENT);
-
- return status;
+ return STATUS_CONTINUE_COMPLETION;
}
-static NTSTATUS
-PdoQueryDevicePower(
+static FORCEINLINE NTSTATUS
+__PdoSetSystemPowerUp(
IN PXENFILT_PDO Pdo,
IN PIRP Irp
)
{
- PIO_STACK_LOCATION StackLocation;
- DEVICE_POWER_STATE DeviceState;
- POWER_ACTION PowerAction;
- NTSTATUS status;
-
- StackLocation = IoGetCurrentIrpStackLocation(Irp);
- DeviceState = StackLocation->Parameters.Power.State.DeviceState;
- PowerAction = StackLocation->Parameters.Power.ShutdownType;
-
- Trace("%s: ====> (%s:%s)\n",
- __PdoGetName(Pdo),
- DevicePowerStateName(DeviceState),
- PowerActionName(PowerAction));
-
- if (DeviceState == __PdoGetDevicePowerState(Pdo)) {
- status = PdoForwardIrpSynchronously(Pdo, Irp);
- IoCompleteRequest(Irp, IO_NO_INCREMENT);
-
- goto done;
- }
-
- status = (DeviceState < __PdoGetDevicePowerState(Pdo)) ?
- PdoQueryDevicePowerUp(Pdo, Irp) :
- PdoQueryDevicePowerDown(Pdo, Irp);
-
-done:
- Trace("%s: <==== (%s:%s)(%08x)\n",
- __PdoGetName(Pdo),
- DevicePowerStateName(DeviceState),
- PowerActionName(PowerAction),
- status);
- return status;
-}
-
-static NTSTATUS
-PdoQuerySystemPowerUp(
- IN PXENFILT_PDO Pdo,
- IN PIRP Irp
- )
-{
- PIO_STACK_LOCATION StackLocation;
- SYSTEM_POWER_STATE SystemState;
- NTSTATUS status;
-
- StackLocation = IoGetCurrentIrpStackLocation(Irp);
- SystemState = StackLocation->Parameters.Power.State.SystemState;
-
- ASSERT3U(SystemState, <, __PdoGetSystemPowerState(Pdo));
-
- status = PdoForwardIrpSynchronously(Pdo, Irp);
-
- Irp->IoStatus.Status = status;
- IoCompleteRequest(Irp, IO_NO_INCREMENT);
-
- return status;
+ IoCopyCurrentIrpStackLocationToNext(Irp);
+ IoSetCompletionRoutine(Irp,
+ PdoSetSystemPowerUpComplete,
+ Pdo,
+ TRUE,
+ TRUE,
+ TRUE);
+ return IoCallDriver(Pdo->LowerDeviceObject, Irp);
}
-static NTSTATUS
-PdoQuerySystemPowerDown(
+static FORCEINLINE NTSTATUS
+__PdoSetSystemPowerDown(
IN PXENFILT_PDO Pdo,
IN PIRP Irp
)
{
PIO_STACK_LOCATION StackLocation;
SYSTEM_POWER_STATE SystemState;
- NTSTATUS status;
StackLocation = IoGetCurrentIrpStackLocation(Irp);
SystemState = StackLocation->Parameters.Power.State.SystemState;
ASSERT3U(SystemState, >, __PdoGetSystemPowerState(Pdo));
- status = PdoForwardIrpSynchronously(Pdo, Irp);
- IoCompleteRequest(Irp, IO_NO_INCREMENT);
+ Trace("%s: %s -> %s\n",
+ __PdoGetName(Pdo),
+ SystemPowerStateName(__PdoGetSystemPowerState(Pdo)),
+ SystemPowerStateName(SystemState));
- return status;
+ __PdoSetSystemPowerState(Pdo, SystemState);
+
+ IoSkipCurrentIrpStackLocation(Irp);
+ return IoCallDriver(Pdo->LowerDeviceObject, Irp);
}
static NTSTATUS
-PdoQuerySystemPower(
+PdoSetSystemPower(
IN PXENFILT_PDO Pdo,
IN PIRP Irp
)
PowerActionName(PowerAction));
if (SystemState == __PdoGetSystemPowerState(Pdo)) {
- status = PdoForwardIrpSynchronously(Pdo, Irp);
- IoCompleteRequest(Irp, IO_NO_INCREMENT);
+ IoSkipCurrentIrpStackLocation(Irp);
+ status = IoCallDriver(Pdo->LowerDeviceObject, Irp);
goto done;
}
status = (SystemState < __PdoGetSystemPowerState(Pdo)) ?
- PdoQuerySystemPowerUp(Pdo, Irp) :
- PdoQuerySystemPowerDown(Pdo, Irp);
+ __PdoSetSystemPowerUp(Pdo, Irp) :
+ __PdoSetSystemPowerDown(Pdo, Irp);
done:
Trace("%s: <==== (%s:%s)(%08x)\n",
SystemPowerStateName(SystemState),
PowerActionName(PowerAction),
status);
-
return status;
}
-static NTSTATUS
-PdoDevicePower(
- IN PXENFILT_THREAD Self,
- IN PVOID Context
- )
-{
- PXENFILT_PDO Pdo = Context;
- PKEVENT Event;
-
- Event = ThreadGetEvent(Self);
-
- for (;;) {
- PIRP Irp;
- PIO_STACK_LOCATION StackLocation;
- UCHAR MinorFunction;
-
- if (Pdo->DevicePowerIrp == NULL) {
- (VOID) KeWaitForSingleObject(Event,
- Executive,
- KernelMode,
- FALSE,
- NULL);
- KeClearEvent(Event);
- }
-
- if (ThreadIsAlerted(Self))
- break;
-
- Irp = Pdo->DevicePowerIrp;
-
- if (Irp == NULL)
- continue;
-
- Pdo->DevicePowerIrp = NULL;
- KeMemoryBarrier();
-
- StackLocation = IoGetCurrentIrpStackLocation(Irp);
- MinorFunction = StackLocation->MinorFunction;
-
- switch (StackLocation->MinorFunction) {
- case IRP_MN_SET_POWER:
- (VOID) PdoSetDevicePower(Pdo, Irp);
- break;
-
- case IRP_MN_QUERY_POWER:
- (VOID) PdoQueryDevicePower(Pdo, Irp);
- break;
-
- default:
- ASSERT(FALSE);
- break;
- }
-
- IoReleaseRemoveLock(&Pdo->Dx->RemoveLock, Irp);
- }
-
- return STATUS_SUCCESS;
-}
-
-static NTSTATUS
-PdoSystemPower(
- IN PXENFILT_THREAD Self,
- IN PVOID Context
+static FORCEINLINE NTSTATUS
+__PdoDispatchSystemPower(
+ IN PXENFILT_PDO Pdo,
+ IN PIRP Irp
)
{
- PXENFILT_PDO Pdo = Context;
- PKEVENT Event;
-
- Event = ThreadGetEvent(Self);
-
- for (;;) {
- PIRP Irp;
- PIO_STACK_LOCATION StackLocation;
- UCHAR MinorFunction;
-
- if (Pdo->SystemPowerIrp == NULL) {
- (VOID) KeWaitForSingleObject(Event,
- Executive,
- KernelMode,
- FALSE,
- NULL);
- KeClearEvent(Event);
- }
-
- if (ThreadIsAlerted(Self))
- break;
-
- Irp = Pdo->SystemPowerIrp;
-
- if (Irp == NULL)
- continue;
-
- Pdo->SystemPowerIrp = NULL;
- KeMemoryBarrier();
-
- StackLocation = IoGetCurrentIrpStackLocation(Irp);
- MinorFunction = StackLocation->MinorFunction;
-
- switch (StackLocation->MinorFunction) {
- case IRP_MN_SET_POWER:
- (VOID) PdoSetSystemPower(Pdo, Irp);
- break;
+ PIO_STACK_LOCATION StackLocation;
+ UCHAR MinorFunction;
+ NTSTATUS status;
- case IRP_MN_QUERY_POWER:
- (VOID) PdoQuerySystemPower(Pdo, Irp);
- break;
+ StackLocation = IoGetCurrentIrpStackLocation(Irp);
+ MinorFunction = StackLocation->MinorFunction;
- default:
- ASSERT(FALSE);
- break;
- }
+ switch (MinorFunction) {
+ case IRP_MN_SET_POWER:
+ status = PdoSetSystemPower(Pdo, Irp);
+ break;
- IoReleaseRemoveLock(&Pdo->Dx->RemoveLock, Irp);
+ default:
+ IoSkipCurrentIrpStackLocation(Irp);
+ status = IoCallDriver(Pdo->LowerDeviceObject, Irp);
+ break;
}
- return STATUS_SUCCESS;
+ return status;
}
static NTSTATUS
StackLocation = IoGetCurrentIrpStackLocation(Irp);
MinorFunction = StackLocation->MinorFunction;
- if (MinorFunction != IRP_MN_QUERY_POWER &&
- MinorFunction != IRP_MN_SET_POWER) {
+ if (MinorFunction != IRP_MN_SET_POWER) {
IoSkipCurrentIrpStackLocation(Irp);
status = IoCallDriver(Pdo->LowerDeviceObject, Irp);
switch (PowerType) {
case DevicePowerState:
- IoMarkIrpPending(Irp);
-
- ASSERT3P(Pdo->DevicePowerIrp, ==, NULL);
- Pdo->DevicePowerIrp = Irp;
- KeMemoryBarrier();
-
- ThreadWake(Pdo->DevicePowerThread);
-
- status = STATUS_PENDING;
+ status = __PdoDispatchDevicePower(Pdo, Irp);
+ IoReleaseRemoveLock(&Pdo->Dx->RemoveLock, Irp);
break;
case SystemPowerState:
- IoMarkIrpPending(Irp);
-
- ASSERT3P(Pdo->SystemPowerIrp, ==, NULL);
- Pdo->SystemPowerIrp = Irp;
- KeMemoryBarrier();
-
- ThreadWake(Pdo->SystemPowerThread);
-
- status = STATUS_PENDING;
+ status = __PdoDispatchSystemPower(Pdo, Irp);
+ IoReleaseRemoveLock(&Pdo->Dx->RemoveLock, Irp);
break;
default:
Pdo->LowerDeviceObject = LowerDeviceObject;
Pdo->Type = Type;
- status = ThreadCreate(PdoSystemPower, Pdo, &Pdo->SystemPowerThread);
- if (!NT_SUCCESS(status))
- goto fail4;
-
- status = ThreadCreate(PdoDevicePower, Pdo, &Pdo->DevicePowerThread);
- if (!NT_SUCCESS(status))
- goto fail5;
-
status = PdoSetDeviceInformation(Pdo);
if (!NT_SUCCESS(status))
- goto fail6;
+ goto fail4;
status = DriverQueryId(Pdo->LowerDeviceObject,
BusQueryCompatibleIDs,
__PdoGetType(Pdo),
&Pdo->EmulatedObject);
if (!NT_SUCCESS(status))
- goto fail7;
+ goto fail5;
if (CompatibleIDs)
ExFreePool(CompatibleIDs);
return STATUS_SUCCESS;
-fail7:
- Error("fail7\n");
+fail5:
+ Error("fail5\n");
if (CompatibleIDs)
ExFreePool(CompatibleIDs);
PdoClearDeviceInformation(Pdo);
-fail6:
- Error("fail6\n");
-
- ThreadAlert(Pdo->DevicePowerThread);
- ThreadJoin(Pdo->DevicePowerThread);
- Pdo->DevicePowerThread = NULL;
-
-fail5:
- Error("fail5\n");
-
- ThreadAlert(Pdo->SystemPowerThread);
- ThreadJoin(Pdo->SystemPowerThread);
- Pdo->SystemPowerThread = NULL;
-
fail4:
Error("fail4\n");
PdoClearDeviceInformation(Pdo);
- ThreadAlert(Pdo->DevicePowerThread);
- ThreadJoin(Pdo->DevicePowerThread);
- Pdo->DevicePowerThread = NULL;
-
- ThreadAlert(Pdo->SystemPowerThread);
- ThreadJoin(Pdo->SystemPowerThread);
- Pdo->SystemPowerThread = NULL;
-
Pdo->Type = XENFILT_EMULATED_OBJECT_TYPE_UNKNOWN;
Pdo->PhysicalDeviceObject = NULL;
Pdo->LowerDeviceObject = NULL;