|
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] [win-pv-devel] [PATCH 04/26] Refactor Adapter.c
From: Owen Smith <owen.smith@xxxxxxxxxx>
Signed-off-by: Owen Smith <owen.smith@xxxxxxxxxx>
---
src/xenvbd/adapter.c | 2301 ++++++++++++++++++++++-------------------------
src/xenvbd/adapter.h | 123 +--
src/xenvbd/blockring.c | 22 +-
src/xenvbd/driver.c | 185 +---
src/xenvbd/driver.h | 5 +
src/xenvbd/frontend.c | 133 +--
src/xenvbd/frontend.h | 4 +
src/xenvbd/granter.c | 26 +-
src/xenvbd/notifier.c | 51 +-
src/xenvbd/pdoinquiry.c | 44 +-
src/xenvbd/pdoinquiry.h | 3 +-
src/xenvbd/target.c | 133 ++-
src/xenvbd/target.h | 27 +-
13 files changed, 1292 insertions(+), 1765 deletions(-)
diff --git a/src/xenvbd/adapter.c b/src/xenvbd/adapter.c
index 1e0340b..7fb786f 100644
--- a/src/xenvbd/adapter.c
+++ b/src/xenvbd/adapter.c
@@ -44,6 +44,7 @@
#include <debug_interface.h>
#include <suspend_interface.h>
#include <emulated_interface.h>
+#include <unplug_interface.h>
#include "adapter.h"
#include "driver.h"
@@ -58,553 +59,59 @@
#include "assert.h"
#define MAXNAMELEN 128
-
-#define ADAPTER_SIGNATURE 'odfX'
+#define ADAPTER_POOL_TAG 'adAX'
struct _XENVBD_ADAPTER {
- ULONG Signature;
PDEVICE_OBJECT DeviceObject;
PDEVICE_OBJECT LowerDeviceObject;
PDEVICE_OBJECT PhysicalDeviceObject;
KSPIN_LOCK Lock;
DEVICE_POWER_STATE DevicePower;
- ANSI_STRING Enumerator;
-
- // Power
PXENVBD_THREAD DevicePowerThread;
PIRP DevicePowerIrp;
- // Interfaces to XenBus
- XENBUS_EVTCHN_INTERFACE Evtchn;
- XENBUS_STORE_INTERFACE Store;
- XENBUS_GNTTAB_INTERFACE Gnttab;
- XENBUS_DEBUG_INTERFACE Debug;
- XENBUS_SUSPEND_INTERFACE Suspend;
- XENBUS_UNPLUG_INTERFACE Unplug;
- XENFILT_EMULATED_INTERFACE Emulated;
+ XENBUS_EVTCHN_INTERFACE EvtchnInterface;
+ XENBUS_STORE_INTERFACE StoreInterface;
+ XENBUS_GNTTAB_INTERFACE GnttabInterface;
+ XENBUS_DEBUG_INTERFACE DebugInterface;
+ XENBUS_SUSPEND_INTERFACE SuspendInterface;
+ XENBUS_UNPLUG_INTERFACE UnplugInterface;
+ XENFILT_EMULATED_INTERFACE EmulatedInterface;
- // Debug Callback
PXENBUS_DEBUG_CALLBACK DebugCallback;
PXENBUS_SUSPEND_CALLBACK SuspendCallback;
- // Targets
KSPIN_LOCK TargetLock;
- PXENVBD_TARGET Targets[XENVBD_MAX_TARGETS];
-
- // Target Enumeration
+ PXENVBD_TARGET TargetList[XENVBD_MAX_TARGETS];
PXENVBD_THREAD ScanThread;
KEVENT ScanEvent;
PXENBUS_STORE_WATCH ScanWatch;
- // Statistics
- LONG CurrentSrbs;
- LONG MaximumSrbs;
- LONG TotalSrbs;
+ ULONG BuildIo;
+ ULONG StartIo;
+ ULONG Completed;
};
-//=============================================================================
-static FORCEINLINE BOOLEAN
-__AdapterSetDevicePowerState(
- __in PXENVBD_ADAPTER Adapter,
- __in DEVICE_POWER_STATE State
- )
-{
- KIRQL Irql;
- BOOLEAN Changed = FALSE;
-
- KeAcquireSpinLock(&Adapter->Lock, &Irql);
-
- if (Adapter->DevicePower != State) {
- Verbose("POWER %s to %s\n",
PowerDeviceStateName(Adapter->DevicePower), PowerDeviceStateName(State));
- Changed = TRUE;
- Adapter->DevicePower = State;
- }
-
- KeReleaseSpinLock(&Adapter->Lock, Irql);
-
- return Changed;
-}
-
-static FORCEINLINE DEVICE_POWER_STATE
-__AdapterGetDevicePowerState(
- __in PXENVBD_ADAPTER Adapter
- )
-{
- KIRQL Irql;
- DEVICE_POWER_STATE State;
-
- KeAcquireSpinLock(&Adapter->Lock, &Irql);
- State = Adapter->DevicePower;
- KeReleaseSpinLock(&Adapter->Lock, Irql);
-
- return State;
-}
-
-__checkReturn
-static FORCEINLINE PXENVBD_TARGET
-__AdapterGetTargetAlways(
- __in PXENVBD_ADAPTER Adapter,
- __in ULONG TargetId,
- __in PCHAR Caller
- )
-{
- PXENVBD_TARGET Target;
- KIRQL Irql;
-
- ASSERT3U(TargetId, <, XENVBD_MAX_TARGETS);
-
- KeAcquireSpinLock(&Adapter->TargetLock, &Irql);
- Target = Adapter->Targets[TargetId];
- if (Target) {
- __TargetReference(Target, Caller);
- }
- KeReleaseSpinLock(&Adapter->TargetLock, Irql);
-
- return Target;
-}
-
-__checkReturn
-static FORCEINLINE PXENVBD_TARGET
-___AdapterGetTarget(
- __in PXENVBD_ADAPTER Adapter,
- __in ULONG TargetId,
- __in PCHAR Caller
- )
-{
- PXENVBD_TARGET Target = NULL;
- KIRQL Irql;
-
- ASSERT3U(TargetId, <, XENVBD_MAX_TARGETS);
-
- KeAcquireSpinLock(&Adapter->TargetLock, &Irql);
- if (Adapter->Targets[TargetId] &&
- __TargetReference(Adapter->Targets[TargetId], Caller) > 0) {
- Target = Adapter->Targets[TargetId];
- }
- KeReleaseSpinLock(&Adapter->TargetLock, Irql);
-
- return Target;
-}
-#define __AdapterGetTarget(f, t) ___AdapterGetTarget(f, t, __FUNCTION__)
-
-BOOLEAN
-AdapterLinkTarget(
- __in PXENVBD_ADAPTER Adapter,
- __in PXENVBD_TARGET Target
- )
-{
- KIRQL Irql;
- PXENVBD_TARGET Current;
- BOOLEAN Result = FALSE;
- ULONG TargetId = TargetGetTargetId(Target);
-
- KeAcquireSpinLock(&Adapter->TargetLock, &Irql);
- Current = Adapter->Targets[TargetId];
- if (Adapter->Targets[TargetId] == NULL) {
- Adapter->Targets[TargetId] = Target;
- Result = TRUE;
- }
- KeReleaseSpinLock(&Adapter->TargetLock, Irql);
-
- if (!Result) {
- Warning("Target[%d] : Current 0x%p, New 0x%p\n", TargetId, Current,
Target);
- }
- return Result;
-}
-BOOLEAN
-AdapterUnlinkTarget(
- __in PXENVBD_ADAPTER Adapter,
- __in PXENVBD_TARGET Target
- )
-{
- KIRQL Irql;
- PXENVBD_TARGET Current;
- BOOLEAN Result = FALSE;
- ULONG TargetId = TargetGetTargetId(Target);
-
- KeAcquireSpinLock(&Adapter->TargetLock, &Irql);
- Current = Adapter->Targets[TargetId];
- if (Adapter->Targets[TargetId] == Target) {
- Adapter->Targets[TargetId] = NULL;
- Result = TRUE;
- }
- KeReleaseSpinLock(&Adapter->TargetLock, Irql);
-
- if (!Result) {
- Warning("Target[%d] : Current 0x%p, Expected 0x%p\n", TargetId,
Current, Target);
- }
- return Result;
-}
-
-//=============================================================================
-// QueryInterface
-
-__drv_requiresIRQL(PASSIVE_LEVEL)
-static NTSTATUS
-AdapterQueryInterface(
- IN PXENVBD_ADAPTER Adapter,
- IN const GUID *Guid,
- IN ULONG Version,
- OUT PINTERFACE Interface,
- IN ULONG Size,
- IN BOOLEAN Optional
- )
-{
- KEVENT Event;
- IO_STATUS_BLOCK StatusBlock;
- PIRP Irp;
- PIO_STACK_LOCATION StackLocation;
- NTSTATUS status;
-
- ASSERT3U(KeGetCurrentIrql(), ==, PASSIVE_LEVEL);
-
- KeInitializeEvent(&Event, NotificationEvent, FALSE);
- RtlZeroMemory(&StatusBlock, sizeof(IO_STATUS_BLOCK));
-
- Irp = IoBuildSynchronousFsdRequest(IRP_MJ_PNP,
- Adapter->LowerDeviceObject,
- NULL,
- 0,
- NULL,
- &Event,
- &StatusBlock);
-
- status = STATUS_UNSUCCESSFUL;
- if (Irp == NULL)
- goto fail1;
-
- StackLocation = IoGetNextIrpStackLocation(Irp);
- StackLocation->MinorFunction = IRP_MN_QUERY_INTERFACE;
-
- StackLocation->Parameters.QueryInterface.InterfaceType = Guid;
- StackLocation->Parameters.QueryInterface.Size = (USHORT)Size;
- StackLocation->Parameters.QueryInterface.Version = (USHORT)Version;
- StackLocation->Parameters.QueryInterface.Interface = Interface;
-
- Irp->IoStatus.Status = STATUS_NOT_SUPPORTED;
-
- status = IoCallDriver(Adapter->LowerDeviceObject, Irp);
- if (status == STATUS_PENDING) {
- (VOID) KeWaitForSingleObject(&Event,
- Executive,
- KernelMode,
- FALSE,
- NULL);
- status = StatusBlock.Status;
- }
-
- if (!NT_SUCCESS(status)) {
- if (status == STATUS_NOT_SUPPORTED && Optional)
- goto done;
-
- goto fail2;
- }
-
-done:
- return STATUS_SUCCESS;
-
-fail2:
- Error("fail2\n");
-
-fail1:
- Error("fail1 (%08x)\n", status);
-
- return status;
-}
-
-#define QUERY_INTERFACE(
\
- _Adapter,
\
- _ProviderName,
\
- _InterfaceName,
\
- _Interface,
\
- _Size,
\
- _Optional)
\
- AdapterQueryInterface((_Adapter),
\
- &GUID_ ## _ProviderName ## _ ## _InterfaceName ##
_INTERFACE, \
- _ProviderName ## _ ## _InterfaceName ##
_INTERFACE_VERSION_MAX, \
- (_Interface),
\
- (_Size),
\
- (_Optional))
-
-//=============================================================================
-// Debug
-
-static DECLSPEC_NOINLINE VOID
-AdapterDebugCallback(
- __in PVOID Context,
- __in BOOLEAN Crashing
- )
-{
- PXENVBD_ADAPTER Adapter = Context;
- ULONG TargetId;
-
- if (Adapter == NULL || Adapter->DebugCallback == NULL)
- return;
-
- XENBUS_DEBUG(Printf, &Adapter->Debug,
- "ADAPTER: Version: %d.%d.%d.%d (%d/%d/%d)\n",
- MAJOR_VERSION, MINOR_VERSION, MICRO_VERSION, BUILD_NUMBER,
- DAY, MONTH, YEAR);
- XENBUS_DEBUG(Printf, &Adapter->Debug,
- "ADAPTER: Adapter: 0x%p %s\n",
- Context,
- Crashing ? "CRASHING" : "");
- XENBUS_DEBUG(Printf, &Adapter->Debug,
- "ADAPTER: DevObj 0x%p LowerDevObj 0x%p PhysDevObj 0x%p\n",
- Adapter->DeviceObject,
- Adapter->LowerDeviceObject,
- Adapter->PhysicalDeviceObject);
- XENBUS_DEBUG(Printf, &Adapter->Debug,
- "ADAPTER: DevicePowerState: %s\n",
- PowerDeviceStateName(Adapter->DevicePower));
- XENBUS_DEBUG(Printf, &Adapter->Debug,
- "ADAPTER: Enumerator : %s (0x%p)\n",
- AdapterEnum(Adapter), Adapter->Enumerator.Buffer);
- XENBUS_DEBUG(Printf, &Adapter->Debug,
- "ADAPTER: Srbs : %d / %d (%d Total)\n",
- Adapter->CurrentSrbs, Adapter->MaximumSrbs,
Adapter->TotalSrbs);
-
- BufferDebugCallback(&Adapter->Debug);
-
- for (TargetId = 0; TargetId < XENVBD_MAX_TARGETS; ++TargetId) {
- // no need to use __AdapterGetTarget (which is locked at DISPATCH) as
called at HIGH_LEVEL
- PXENVBD_TARGET Target = Adapter->Targets[TargetId];
- if (Target == NULL)
- continue;
-
- XENBUS_DEBUG(Printf, &Adapter->Debug,
- "ADAPTER: ====> Target[%-3d] : 0x%p\n",
- TargetId, Target);
-
- // call Target's debug callback directly
- TargetDebugCallback(Target, &Adapter->Debug);
-
- XENBUS_DEBUG(Printf, &Adapter->Debug,
- "ADAPTER: <==== Target[%-3d] : 0x%p\n",
- TargetId, Target);
- }
-
- Adapter->MaximumSrbs = Adapter->CurrentSrbs;
- Adapter->TotalSrbs = 0;
-}
-
-//=============================================================================
-// Enumeration
-static FORCEINLINE ULONG
-__ParseVbd(
- __in PCHAR DeviceIdStr
- )
-{
- ULONG DeviceId = strtoul(DeviceIdStr, NULL, 10);
-
- ASSERT3U((DeviceId & ~((1 << 29) - 1)), ==, 0);
-
- if (DeviceId & (1 << 28)) {
- return (DeviceId & ((1 << 20) - 1)) >> 8; /* xvd */
- } else {
- switch (DeviceId >> 8) {
- case 202: return (DeviceId & 0xF0) >> 4; /* xvd */
- case 8: return (DeviceId & 0xF0) >> 4; /* sd */
- case 3: return (DeviceId & 0xC0) >> 6; /* hda..b */
- case 22: return ((DeviceId & 0xC0) >> 6) + 2; /* hdc..d */
- case 33: return ((DeviceId & 0xC0) >> 6) + 4; /* hde..f */
- case 34: return ((DeviceId & 0xC0) >> 6) + 6; /* hdg..h */
- case 56: return ((DeviceId & 0xC0) >> 6) + 8; /* hdi..j */
- case 57: return ((DeviceId & 0xC0) >> 6) + 10; /* hdk..l */
- case 88: return ((DeviceId & 0xC0) >> 6) + 12; /* hdm..n */
- case 89: return ((DeviceId & 0xC0) >> 6) + 14; /* hdo..p */
- default: break;
- }
- }
- Error("Invalid DeviceId %s (%08x)\n", DeviceIdStr, DeviceId);
- return 0xFFFFFFFF; // OBVIOUS ERROR VALUE
-}
-static FORCEINLINE XENVBD_DEVICE_TYPE
-__DeviceType(
- __in PCHAR Type
- )
-{
- if (strcmp(Type, "disk") == 0)
- return XENVBD_DEVICE_TYPE_DISK;
- if (strcmp(Type, "cdrom") == 0)
- return XENVBD_DEVICE_TYPE_CDROM;
- return XENVBD_DEVICE_TYPE_UNKNOWN;
-}
-
-static FORCEINLINE BOOLEAN
-__AdapterHiddenTarget(
- IN PXENVBD_ADAPTER Adapter,
- IN PCHAR DeviceId,
- OUT PXENVBD_DEVICE_TYPE DeviceType
- )
-{
- NTSTATUS status;
- PCHAR Buffer;
- CHAR Path[sizeof("device/vbd/XXXXXXXX")];
- ULONG Value;
-
- *DeviceType = XENVBD_DEVICE_TYPE_UNKNOWN;
- status = RtlStringCbPrintfA(Path,
- sizeof(Path),
- "device/vbd/%s",
- DeviceId);
- if (!NT_SUCCESS(status))
- goto fail;
-
- // Ejected?
- status = XENBUS_STORE(Read, &Adapter->Store, NULL, Path, "ejected",
&Buffer);
- if (NT_SUCCESS(status)) {
- Value = strtoul(Buffer, NULL, 10);
- XENBUS_STORE(Free, &Adapter->Store, Buffer);
-
- if (Value)
- goto ignore;
- }
-
- // Not Disk?
- status = XENBUS_STORE(Read, &Adapter->Store, NULL, Path, "device-type",
&Buffer);
- if (!NT_SUCCESS(status))
- goto ignore;
- *DeviceType = __DeviceType(Buffer);
- XENBUS_STORE(Free, &Adapter->Store, Buffer);
-
- switch (*DeviceType) {
- case XENVBD_DEVICE_TYPE_DISK:
- break;
- default:
- goto ignore;
- }
-
- // Try to Create
- return FALSE;
-
-fail:
- Error("Fail\n");
- return TRUE;
-
-ignore:
- return TRUE;
-}
-__checkReturn
-static FORCEINLINE BOOLEAN
-__AdapterIsTargetUnplugged(
- __in PXENVBD_ADAPTER Adapter,
- __in PCHAR Enumerator,
- __in PCHAR Device,
- __in ULONG Target
+static FORCEINLINE PVOID
+__AdapterAllocate(
+ IN ULONG Size
)
{
- // Only check targets that could be emulated
- if (Target > 3) {
- Verbose("Target[%d] : (%s/%s) Emulated NOT_APPLICABLE (non-IDE
device)\n",
- Target, Enumerator, Device);
- return TRUE;
- }
-
- // Check presense of Emulated interface. Absence indicates emulated cannot
be unplugged
- if (Adapter->Emulated.Interface.Context == NULL) {
- Warning("Target[%d] : (%s/%s) Emulated NOT_KNOWN (assumed PRESENT)\n",
- Target, Enumerator, Device);
- return FALSE;
- }
-
- // Ask XenFilt if Ctrlr(0), Target(Target), Lun(0) is present
- if (XENFILT_EMULATED(IsDiskPresent, &Adapter->Emulated, 0, Target, 0)) {
- Verbose("Target[%d] : (%s/%s) Emulated PRESENT\n",
- Target, Enumerator, Device);
- return FALSE;
- } else {
- Verbose("Target[%d] : (%s/%s) Emulated NOT_PRESENT\n",
- Target, Enumerator, Device);
- return TRUE;
- }
+ PVOID Buffer;
+ Buffer = ExAllocatePoolWithTag(NonPagedPool,
+ Size,
+ ADAPTER_POOL_TAG);
+ if (Buffer)
+ RtlZeroMemory(Buffer, Size);
+ return Buffer;
}
static FORCEINLINE VOID
-__AdapterEnumerate(
- __in PXENVBD_ADAPTER Adapter,
- __in PANSI_STRING Devices,
- __out PBOOLEAN NeedInvalidate,
- __out PBOOLEAN NeedReboot
+__AdapterFree(
+ IN PVOID Buffer
)
{
- ULONG TargetId;
- PANSI_STRING Device;
- ULONG Index;
- PXENVBD_TARGET Target;
-
- *NeedInvalidate = FALSE;
- *NeedReboot = FALSE;
-
- for (TargetId = 0; TargetId < XENVBD_MAX_TARGETS; ++TargetId) {
- BOOLEAN Missing = TRUE;
-
- Target = __AdapterGetTarget(Adapter, TargetId);
- if (Target == NULL)
- continue;
-
- for (Index = 0; Devices[Index].Buffer != NULL; ++Index) {
- ULONG DeviceTargetId;
- Device = &Devices[Index];
- DeviceTargetId = __ParseVbd(Device->Buffer);
- if (TargetId == DeviceTargetId) {
- Missing = FALSE;
- break;
- }
- }
-
- if (Missing && !TargetIsMissing(Target)) {
- TargetSetMissing(Target, "Device Disappeared");
- if (TargetGetDevicePnpState(Target) == Present)
- TargetSetDevicePnpState(Target, Deleted);
- else
- *NeedInvalidate = TRUE;
- }
-
- if (TargetGetDevicePnpState(Target) == Deleted) {
- TargetDereference(Target);
- TargetDestroy(Target);
- } else {
- TargetDereference(Target);
- }
- }
-
- // add new targets
- for (Index = 0; Devices[Index].Buffer != NULL; ++Index) {
- XENVBD_DEVICE_TYPE DeviceType;
-
- Device = &Devices[Index];
-
- TargetId = __ParseVbd(Device->Buffer);
- if (TargetId == 0xFFFFFFFF) {
- continue;
- }
-
- Target = __AdapterGetTarget(Adapter, TargetId);
- if (Target) {
- TargetDereference(Target);
- continue;
- }
-
- if (__AdapterHiddenTarget(Adapter, Device->Buffer, &DeviceType)) {
- continue;
- }
-
- if (!__AdapterIsTargetUnplugged(Adapter,
- AdapterEnum(Adapter),
- Device->Buffer,
- TargetId)) {
- *NeedReboot = TRUE;
- continue;
- }
-
- if (TargetCreate(Adapter,
- Device->Buffer,
- TargetId,
- DeviceType)) {
- *NeedInvalidate = TRUE;
- }
- }
+ ExFreePoolWithTag(Buffer, ADAPTER_POOL_TAG);
}
static FORCEINLINE PANSI_STRING
@@ -632,10 +139,7 @@ __AdapterMultiSzToAnsi(
}
}
- Ansi = __AllocatePoolWithTag(NonPagedPool,
- sizeof (ANSI_STRING) * (Count + 1),
- ADAPTER_SIGNATURE);
-
+ Ansi = __AdapterAllocate(sizeof (ANSI_STRING) * (Count + 1));
status = STATUS_NO_MEMORY;
if (Ansi == NULL)
goto fail1;
@@ -645,9 +149,7 @@ __AdapterMultiSzToAnsi(
Length = (ULONG)strlen(Buffer);
Ansi[Index].MaximumLength = (USHORT)(Length + 1);
- Ansi[Index].Buffer = __AllocatePoolWithTag(NonPagedPool,
- Ansi[Index].MaximumLength,
- ADAPTER_SIGNATURE);
+ Ansi[Index].Buffer = __AdapterAllocate(Ansi[Index].MaximumLength);
status = STATUS_NO_MEMORY;
if (Ansi[Index].Buffer == NULL)
@@ -665,9 +167,9 @@ fail2:
Error("fail2\n");
while (--Index >= 0)
- __FreePoolWithTag(Ansi[Index].Buffer, ADAPTER_SIGNATURE);
+ __AdapterFree(Ansi[Index].Buffer);
- __FreePoolWithTag(Ansi, ADAPTER_SIGNATURE);
+ __AdapterFree(Ansi);
fail1:
Error("fail1 (%08x)\n", status);
@@ -701,105 +203,322 @@ __AdapterMultiSzToUpcaseAnsi(
}
}
- Ansi = __AllocatePoolWithTag(NonPagedPool,
- sizeof (ANSI_STRING) * (Count + 1),
- ADAPTER_SIGNATURE);
-
+ Ansi = __AdapterAllocate(sizeof (ANSI_STRING) * (Count + 1));
status = STATUS_NO_MEMORY;
if (Ansi == NULL)
goto fail1;
- for (Index = 0; Index < Count; Index++) {
- ULONG Length;
+ for (Index = 0; Index < Count; Index++) {
+ ULONG Length;
+
+ Length = (ULONG)strlen(Buffer);
+ Ansi[Index].MaximumLength = (USHORT)(Length + 1);
+ Ansi[Index].Buffer = __AdapterAllocate(Ansi[Index].MaximumLength);
+
+ status = STATUS_NO_MEMORY;
+ if (Ansi[Index].Buffer == NULL)
+ goto fail2;
+
+ RtlCopyMemory(Ansi[Index].Buffer, Buffer, Length);
+ Ansi[Index].Length = (USHORT)Length;
+
+ Buffer += Length + 1;
+ }
+
+ return Ansi;
+
+fail2:
+ Error("fail2\n");
+
+ while (--Index >= 0)
+ __AdapterFree(Ansi[Index].Buffer);
+
+ __AdapterFree(Ansi);
+
+fail1:
+ Error("fail1 (%08x)\n", status);
+
+ return NULL;
+}
+
+static FORCEINLINE VOID
+__AdapterFreeAnsi(
+ IN PANSI_STRING Ansi
+ )
+{
+ ULONG Index;
+
+ for (Index = 0; Ansi[Index].Buffer != NULL; Index++)
+ __AdapterFree(Ansi[Index].Buffer);
+
+ __AdapterFree(Ansi);
+}
+
+static FORCEINLINE BOOLEAN
+__AdapterSetDevicePowerState(
+ IN PXENVBD_ADAPTER Adapter,
+ IN DEVICE_POWER_STATE State
+ )
+{
+ KIRQL Irql;
+ BOOLEAN Changed = FALSE;
+
+ KeAcquireSpinLock(&Adapter->Lock, &Irql);
+
+ if (Adapter->DevicePower != State) {
+ Verbose("POWER %s to %s\n",
PowerDeviceStateName(Adapter->DevicePower), PowerDeviceStateName(State));
+ Changed = TRUE;
+ Adapter->DevicePower = State;
+ }
+
+ KeReleaseSpinLock(&Adapter->Lock, Irql);
+
+ return Changed;
+}
+
+static FORCEINLINE DEVICE_POWER_STATE
+__AdapterGetDevicePowerState(
+ IN PXENVBD_ADAPTER Adapter
+ )
+{
+ KIRQL Irql;
+ DEVICE_POWER_STATE State;
+
+ KeAcquireSpinLock(&Adapter->Lock, &Irql);
+ State = Adapter->DevicePower;
+ KeReleaseSpinLock(&Adapter->Lock, Irql);
+
+ return State;
+}
+
+static FORCEINLINE PXENVBD_TARGET
+AdapterGetTarget(
+ IN PXENVBD_ADAPTER Adapter,
+ IN ULONG TargetId
+ )
+{
+ PXENVBD_TARGET Target;
+ KIRQL Irql;
+
+ ASSERT3U(TargetId, <, XENVBD_MAX_TARGETS);
+
+ KeAcquireSpinLock(&Adapter->TargetLock, &Irql);
+ Target = Adapter->TargetList[TargetId];
+ KeReleaseSpinLock(&Adapter->TargetLock, Irql);
+
+ return Target;
+}
+
+static FORCEINLINE BOOLEAN
+__AdapterHiddenTarget(
+ IN PXENVBD_ADAPTER Adapter,
+ IN PCHAR DeviceId
+ )
+{
+ NTSTATUS status;
+ PCHAR Buffer;
+ CHAR Path[sizeof("device/vbd/XXXXXXXX")];
+ BOOLEAN Ejected;
+ BOOLEAN IsDisk;
+
+ status = RtlStringCbPrintfA(Path,
+ sizeof(Path),
+ "device/vbd/%s",
+ DeviceId);
+ if (!NT_SUCCESS(status))
+ goto fail1;
+
+ // Ejected?
+ status = XENBUS_STORE(Read,
+ &Adapter->StoreInterface,
+ NULL,
+ Path,
+ "ejected",
+ &Buffer);
+ if (NT_SUCCESS(status)) {
+ Ejected = (BOOLEAN)strtoul(Buffer, NULL, 2);
+
+ XENBUS_STORE(Free,
+ &Adapter->StoreInterface,
+ Buffer);
+
+ if (Ejected)
+ goto ignore;
+ }
+
+ // Not Disk?
+ status = XENBUS_STORE(Read,
+ &Adapter->StoreInterface,
+ NULL,
+ Path,
+ "device-type",
+ &Buffer);
+ if (!NT_SUCCESS(status))
+ goto ignore;
+
+ IsDisk = (strcmp(Buffer, "disk") == 0);
+
+ XENBUS_STORE(Free,
+ &Adapter->StoreInterface,
+ Buffer);
+
+ if (!IsDisk)
+ goto ignore;
- Length = (ULONG)strlen(Buffer);
- Ansi[Index].MaximumLength = (USHORT)(Length + 1);
- Ansi[Index].Buffer = __AllocatePoolWithTag(NonPagedPool,
- Ansi[Index].MaximumLength,
- ADAPTER_SIGNATURE);
+ // Try to Create
+ return FALSE;
- status = STATUS_NO_MEMORY;
- if (Ansi[Index].Buffer == NULL)
- goto fail2;
+fail1:
+ Error("fail1\n");
+ return TRUE;
- RtlCopyMemory(Ansi[Index].Buffer, Buffer, Length);
- Ansi[Index].Length = (USHORT)Length;
+ignore:
+ return TRUE;
+}
- Buffer += Length + 1;
- }
+BOOLEAN
+AdapterIsTargetEmulated(
+ IN PXENVBD_ADAPTER Adapter,
+ IN ULONG TargetId
+ )
+{
+ BOOLEAN Emulated;
+ NTSTATUS status;
- return Ansi;
+ // Only check targets that could be emulated
+ if (TargetId > 3)
+ return FALSE;
-fail2:
- Error("fail2\n");
+ // Check presense of Emulated interface. Absence indicates emulated cannot
be unplugged
+ if (Adapter->EmulatedInterface.Interface.Context == NULL)
+ return TRUE;
- while (--Index >= 0)
- __FreePoolWithTag(Ansi[Index].Buffer, ADAPTER_SIGNATURE);
+ // Acquire failed, assume emulated
+ status = XENFILT_EMULATED(Acquire, &Adapter->EmulatedInterface);
+ if (!NT_SUCCESS(status))
+ return TRUE;
- __FreePoolWithTag(Ansi, ADAPTER_SIGNATURE);
+ // Ask XenFilt if Ctrlr(0), Target(Target), Lun(0) is present
+ Emulated = XENFILT_EMULATED(IsDiskPresent,
+ &Adapter->EmulatedInterface,
+ 0,
+ TargetId,
+ 0);
-fail1:
- Error("fail1 (%08x)\n", status);
+ XENFILT_EMULATED(Release, &Adapter->EmulatedInterface);
- return NULL;
+ return Emulated;
}
static FORCEINLINE VOID
-__AdapterFreeAnsi(
- IN PANSI_STRING Ansi
+__AdapterEnumerate(
+ IN PXENVBD_ADAPTER Adapter,
+ IN PANSI_STRING Devices
)
{
+ KIRQL Irql;
+ ULONG TargetId;
+ ULONG DeviceId;
+ PANSI_STRING Device;
ULONG Index;
+ PXENVBD_TARGET Target;
+ BOOLEAN NeedInvalidate;
+ BOOLEAN NeedReboot;
- for (Index = 0; Ansi[Index].Buffer != NULL; Index++)
- __FreePoolWithTag(Ansi[Index].Buffer, ADAPTER_SIGNATURE);
+ NeedInvalidate = FALSE;
+ NeedReboot = FALSE;
- __FreePoolWithTag(Ansi, ADAPTER_SIGNATURE);
-}
+ for (TargetId = 0; TargetId < XENVBD_MAX_TARGETS; ++TargetId) {
+ BOOLEAN Missing = TRUE;
-static DECLSPEC_NOINLINE VOID
-AdapterScanTargets(
- __in PXENVBD_ADAPTER Adapter
- )
-{
- NTSTATUS Status;
- PCHAR Buffer;
- PANSI_STRING Devices;
- BOOLEAN NeedInvalidate;
- BOOLEAN NeedReboot;
+ Target = AdapterGetTarget(Adapter, TargetId);
+ if (Target == NULL)
+ continue;
- Status = XENBUS_STORE(Directory, &Adapter->Store, NULL, "device",
AdapterEnum(Adapter), &Buffer);
- if (!NT_SUCCESS(Status))
- return;
+ for (Index = 0; Devices[Index].Buffer != NULL; ++Index) {
+ Device = &Devices[Index];
- Devices = __AdapterMultiSzToAnsi(Buffer);
- XENBUS_STORE(Free, &Adapter->Store, Buffer);
+ if (Device->Length == 0)
+ continue;
- if (Devices == NULL)
- return;
+ DeviceId = strtoul(Device->Buffer, NULL, 10);
+ if (TargetGetDeviceId(Target) == DeviceId) {
+ Device->Length = 0;
+ Missing = FALSE;
+ break;
+ }
+ }
+
+ if (Missing && !TargetIsMissing(Target)) {
+ TargetSetMissing(Target, "Device Disappeared");
+ if (TargetGetDevicePnpState(Target) == Present)
+ TargetSetDevicePnpState(Target, Deleted);
+ else
+ NeedInvalidate = TRUE;
+ }
- __AdapterEnumerate(Adapter, Devices, &NeedInvalidate, &NeedReboot);
- __AdapterFreeAnsi(Devices);
+ if (TargetGetDevicePnpState(Target) == Deleted) {
+ KeAcquireSpinLock(&Adapter->TargetLock, &Irql);
+ ASSERT3P(Adapter->TargetList[TargetId], ==, Target);
+ Adapter->TargetList[TargetId] = NULL;
+ KeReleaseSpinLock(&Adapter->TargetLock, Irql);
- if (NeedInvalidate) {
- StorPortNotification(BusChangeDetected, Adapter, 0);
+ TargetDestroy(Target);
+ }
}
- if (NeedReboot) {
- DriverRequestReboot();
+
+ // add new targets
+ for (Index = 0; Devices[Index].Buffer != NULL; ++Index) {
+ NTSTATUS status;
+
+ Device = &Devices[Index];
+
+ if (Device->Length == 0)
+ continue;
+
+ if (__AdapterHiddenTarget(Adapter, Device->Buffer))
+ continue;
+
+ status = TargetCreate(Adapter,
+ Device->Buffer,
+ &Target);
+ if (status == STATUS_RETRY)
+ NeedReboot = TRUE;
+ if (!NT_SUCCESS(status))
+ continue;
+
+ TargetId = TargetGetTargetId(Target);
+
+ KeAcquireSpinLock(&Adapter->TargetLock, &Irql);
+ ASSERT3P(Adapter->TargetList[TargetId], ==, NULL);
+ Adapter->TargetList[TargetId] = Target;
+ KeReleaseSpinLock(&Adapter->TargetLock, Irql);
+
+ NeedInvalidate = TRUE;
}
+
+ if (NeedInvalidate)
+ StorPortNotification(BusChangeDetected,
+ Adapter,
+ NULL);
+ if (NeedReboot)
+ DriverRequestReboot();
}
-__checkReturn
static DECLSPEC_NOINLINE NTSTATUS
-AdapterScan(
- __in PXENVBD_THREAD Thread,
- __in PVOID Context
+AdapterScanThread(
+ IN PXENVBD_THREAD Thread,
+ IN PVOID Context
)
{
PXENVBD_ADAPTER Adapter = Context;
- PKEVENT Event = ThreadGetEvent(Thread);
+ PKEVENT Event = ThreadGetEvent(Thread);
for (;;) {
+ NTSTATUS status;
+ PCHAR Buffer;
+ PANSI_STRING Devices;
+
Trace("waiting...\n");
(VOID) KeWaitForSingleObject(Event,
@@ -811,204 +530,39 @@ AdapterScan(
if (ThreadIsAlerted(Thread))
break;
+ if (__AdapterGetDevicePowerState(Adapter) != PowerDeviceD0)
+ goto done;
+
+ status = XENBUS_STORE(Directory,
+ &Adapter->StoreInterface,
+ NULL,
+ "device",
+ "vbd",
+ &Buffer);
+ if (NT_SUCCESS(status)) {
+ Devices = __AdapterMultiSzToAnsi(Buffer);
- if (__AdapterGetDevicePowerState(Adapter) == PowerDeviceD0)
- AdapterScanTargets(Adapter);
-
- KeSetEvent(&Adapter->ScanEvent, IO_NO_INCREMENT, FALSE);
- }
- KeSetEvent(&Adapter->ScanEvent, IO_NO_INCREMENT, FALSE);
-
- return STATUS_SUCCESS;
-}
-
-//=============================================================================
-// Initialize, Start, Stop
-
-__drv_requiresIRQL(PASSIVE_LEVEL)
-static FORCEINLINE NTSTATUS
-__AdapterQueryInterfaces(
- __in PXENVBD_ADAPTER Adapter
- )
-{
- NTSTATUS Status;
-
- ASSERT3U(KeGetCurrentIrql(), ==, PASSIVE_LEVEL);
-
- // Get STORE Interface
- Status = QUERY_INTERFACE(Adapter,
- XENBUS,
- STORE,
- (PINTERFACE)&Adapter->Store,
- sizeof (Adapter->Store),
- FALSE);
- if (!NT_SUCCESS(Status))
- goto fail1;
-
- // Get EVTCHN Interface
- Status = QUERY_INTERFACE(Adapter,
- XENBUS,
- EVTCHN,
- (PINTERFACE)&Adapter->Evtchn,
- sizeof (Adapter->Evtchn),
- FALSE);
- if (!NT_SUCCESS(Status))
- goto fail2;
-
- // Get GNTTAB Interface
- Status = QUERY_INTERFACE(Adapter,
- XENBUS,
- GNTTAB,
- (PINTERFACE)&Adapter->Gnttab,
- sizeof (Adapter->Gnttab),
- FALSE);
- if (!NT_SUCCESS(Status))
- goto fail3;
-
- // Get SUSPEND Interface
- Status = QUERY_INTERFACE(Adapter,
- XENBUS,
- SUSPEND,
- (PINTERFACE)&Adapter->Suspend,
- sizeof (Adapter->Suspend),
- FALSE);
- if (!NT_SUCCESS(Status))
- goto fail4;
-
- // Get DEBUG Interface
- Status = QUERY_INTERFACE(Adapter,
- XENBUS,
- DEBUG,
- (PINTERFACE)&Adapter->Debug,
- sizeof (Adapter->Debug),
- FALSE);
- if (!NT_SUCCESS(Status))
- goto fail5;
-
- // Get UNPLUG Interface
- Status = QUERY_INTERFACE(Adapter,
- XENBUS,
- UNPLUG,
- (PINTERFACE)&Adapter->Unplug,
- sizeof (Adapter->Unplug),
- FALSE);
- if (!NT_SUCCESS(Status))
- goto fail6;
+ XENBUS_STORE(Free,
+ &Adapter->StoreInterface,
+ Buffer);
+ } else {
+ Devices = NULL;
+ }
- // Get EMULATED Interface (optional)
- Status = QUERY_INTERFACE(Adapter,
- XENFILT,
- EMULATED,
- (PINTERFACE)&Adapter->Emulated,
- sizeof (Adapter->Emulated),
- TRUE);
- if (!NT_SUCCESS(Status))
- goto fail7;
+ if (Devices == NULL)
+ goto done;
- return STATUS_SUCCESS;
+ __AdapterEnumerate(Adapter,
+ Devices);
-fail7:
- RtlZeroMemory(&Adapter->Unplug,
- sizeof (XENBUS_UNPLUG_INTERFACE));
-fail6:
- RtlZeroMemory(&Adapter->Debug,
- sizeof (XENBUS_DEBUG_INTERFACE));
-fail5:
- RtlZeroMemory(&Adapter->Suspend,
- sizeof (XENBUS_SUSPEND_INTERFACE));
-fail4:
- RtlZeroMemory(&Adapter->Gnttab,
- sizeof (XENBUS_GNTTAB_INTERFACE));
-fail3:
- RtlZeroMemory(&Adapter->Evtchn,
- sizeof (XENBUS_EVTCHN_INTERFACE));
-fail2:
- RtlZeroMemory(&Adapter->Store,
- sizeof (XENBUS_STORE_INTERFACE));
-fail1:
- return Status;
-}
-static FORCEINLINE VOID
-__AdapterZeroInterfaces(
- __in PXENVBD_ADAPTER Adapter
- )
-{
- RtlZeroMemory(&Adapter->Emulated,
- sizeof (XENFILT_EMULATED_INTERFACE));
- RtlZeroMemory(&Adapter->Unplug,
- sizeof (XENBUS_UNPLUG_INTERFACE));
- RtlZeroMemory(&Adapter->Debug,
- sizeof (XENBUS_DEBUG_INTERFACE));
- RtlZeroMemory(&Adapter->Suspend,
- sizeof (XENBUS_SUSPEND_INTERFACE));
- RtlZeroMemory(&Adapter->Gnttab,
- sizeof (XENBUS_GNTTAB_INTERFACE));
- RtlZeroMemory(&Adapter->Evtchn,
- sizeof (XENBUS_EVTCHN_INTERFACE));
- RtlZeroMemory(&Adapter->Store,
- sizeof (XENBUS_STORE_INTERFACE));
-}
-static FORCEINLINE NTSTATUS
-__AdapterAcquire(
- __in PXENVBD_ADAPTER Adapter
- )
-{
- NTSTATUS status;
+ __AdapterFreeAnsi(Devices);
- if (Adapter->Emulated.Interface.Context) {
- status = XENFILT_EMULATED(Acquire, &Adapter->Emulated);
- if (!NT_SUCCESS(status))
- goto fail1;
+done:
+ KeSetEvent(&Adapter->ScanEvent, IO_NO_INCREMENT, FALSE);
}
-
- status = XENBUS_SUSPEND(Acquire, &Adapter->Suspend);
- if (!NT_SUCCESS(status))
- goto fail2;
-
- status = XENBUS_DEBUG(Acquire, &Adapter->Debug);
- if (!NT_SUCCESS(status))
- goto fail3;
-
- status = XENBUS_GNTTAB(Acquire, &Adapter->Gnttab);
- if (!NT_SUCCESS(status))
- goto fail4;
-
- status = XENBUS_EVTCHN(Acquire, &Adapter->Evtchn);
- if (!NT_SUCCESS(status))
- goto fail5;
-
- status = XENBUS_STORE(Acquire, &Adapter->Store);
- if (!NT_SUCCESS(status))
- goto fail6;
+ KeSetEvent(&Adapter->ScanEvent, IO_NO_INCREMENT, FALSE);
return STATUS_SUCCESS;
-
-fail6:
- XENBUS_EVTCHN(Release, &Adapter->Evtchn);
-fail5:
- XENBUS_GNTTAB(Release, &Adapter->Gnttab);
-fail4:
- XENBUS_DEBUG(Release, &Adapter->Debug);
-fail3:
- XENBUS_SUSPEND(Release, &Adapter->Suspend);
-fail2:
- if (Adapter->Emulated.Interface.Context)
- XENFILT_EMULATED(Release, &Adapter->Emulated);
-fail1:
- return status;
-}
-static FORCEINLINE VOID
-__AdapterRelease(
- __in PXENVBD_ADAPTER Adapter
- )
-{
- XENBUS_STORE(Release, &Adapter->Store);
- XENBUS_EVTCHN(Release, &Adapter->Evtchn);
- XENBUS_GNTTAB(Release, &Adapter->Gnttab);
- XENBUS_DEBUG(Release, &Adapter->Debug);
- XENBUS_SUSPEND(Release, &Adapter->Suspend);
- if (Adapter->Emulated.Interface.Context)
- XENFILT_EMULATED(Release, &Adapter->Emulated);
}
static FORCEINLINE BOOLEAN
@@ -1084,7 +638,7 @@ AdapterClearDistribution(
Trace("====>\n");
status = XENBUS_STORE(Directory,
- &Adapter->Store,
+ &Adapter->StoreInterface,
NULL,
NULL,
"drivers",
@@ -1093,7 +647,7 @@ AdapterClearDistribution(
Distributions = __AdapterMultiSzToUpcaseAnsi(Buffer);
XENBUS_STORE(Free,
- &Adapter->Store,
+ &Adapter->StoreInterface,
Buffer);
} else {
Distributions = NULL;
@@ -1106,7 +660,7 @@ AdapterClearDistribution(
PANSI_STRING Distribution = &Distributions[Index];
status = XENBUS_STORE(Read,
- &Adapter->Store,
+ &Adapter->StoreInterface,
NULL,
"drivers",
Distribution->Buffer,
@@ -1116,13 +670,13 @@ AdapterClearDistribution(
if (__AdapterMatchDistribution(Adapter, Buffer))
(VOID) XENBUS_STORE(Remove,
- &Adapter->Store,
+ &Adapter->StoreInterface,
NULL,
"drivers",
Distribution->Buffer);
XENBUS_STORE(Free,
- &Adapter->Store,
+ &Adapter->StoreInterface,
Buffer);
}
@@ -1158,7 +712,7 @@ AdapterSetDistribution(
ASSERT(NT_SUCCESS(status));
status = XENBUS_STORE(Read,
- &Adapter->Store,
+ &Adapter->StoreInterface,
NULL,
"drivers",
Distribution,
@@ -1171,7 +725,7 @@ AdapterSetDistribution(
}
XENBUS_STORE(Free,
- &Adapter->Store,
+ &Adapter->StoreInterface,
Buffer);
Index++;
@@ -1200,7 +754,7 @@ update:
#endif
(VOID) XENBUS_STORE(Printf,
- &Adapter->Store,
+ &Adapter->StoreInterface,
NULL,
"drivers",
Distribution,
@@ -1229,27 +783,30 @@ fail1:
static FORCEINLINE NTSTATUS
__AdapterD3ToD0(
- __in PXENVBD_ADAPTER Adapter
+ IN PXENVBD_ADAPTER Adapter
)
{
- NTSTATUS Status;
+ NTSTATUS status;
Trace("=====>\n");
+ status = XENBUS_STORE(Acquire, &Adapter->StoreInterface);
+ if (!NT_SUCCESS(status))
+ goto fail1;
+
(VOID) AdapterSetDistribution(Adapter);
- ASSERT3P(Adapter->ScanWatch, ==, NULL);
- Status = XENBUS_STORE(WatchAdd,
- &Adapter->Store,
+ status = XENBUS_STORE(WatchAdd,
+ &Adapter->StoreInterface,
"device",
- AdapterEnum(Adapter),
+ "vbd",
ThreadGetEvent(Adapter->ScanThread),
&Adapter->ScanWatch);
- if (!NT_SUCCESS(Status))
- goto fail1;
+ if (!NT_SUCCESS(status))
+ goto fail2;
(VOID) XENBUS_STORE(Printf,
- &Adapter->Store,
+ &Adapter->StoreInterface,
NULL,
"feature/hotplug",
"vbd",
@@ -1259,193 +816,257 @@ __AdapterD3ToD0(
Trace("<=====\n");
return STATUS_SUCCESS;
+fail2:
+ Error("fail2\n");
+
+ XENBUS_STORE(Release, &Adapter->StoreInterface);
+
fail1:
- Error("fail1 (%08x)\n", Status);
+ Error("fail1 (%08x)\n", status);
- return Status;
+ return status;
}
static FORCEINLINE VOID
__AdapterD0ToD3(
- __in PXENVBD_ADAPTER Adapter
+ IN PXENVBD_ADAPTER Adapter
)
{
Trace("=====>\n");
(VOID) XENBUS_STORE(Remove,
- &Adapter->Store,
+ &Adapter->StoreInterface,
NULL,
"feature/hotplug",
"vbd");
(VOID) XENBUS_STORE(WatchRemove,
- &Adapter->Store,
+ &Adapter->StoreInterface,
Adapter->ScanWatch);
Adapter->ScanWatch = NULL;
AdapterClearDistribution(Adapter);
+ XENBUS_STORE(Release, &Adapter->StoreInterface);
+
Trace("<=====\n");
}
-__drv_requiresIRQL(DISPATCH_LEVEL)
static VOID
AdapterSuspendLateCallback(
- __in PVOID Argument
+ IN PVOID Argument
)
{
- PXENVBD_ADAPTER Adapter = Argument;
- NTSTATUS Status;
+ PXENVBD_ADAPTER Adapter = Argument;
+ NTSTATUS status;
- Verbose("%s (%s)\n",
- MAJOR_VERSION_STR "." MINOR_VERSION_STR "." MICRO_VERSION_STR "."
BUILD_NUMBER_STR,
- DAY_STR "/" MONTH_STR "/" YEAR_STR);
+ Verbose("%u.%u.%u.%u (%02u/%02u/%04u)\n",
+ MAJOR_VERSION,
+ MINOR_VERSION,
+ MICRO_VERSION,
+ BUILD_NUMBER,
+ DAY,
+ MONTH,
+ YEAR);
__AdapterD0ToD3(Adapter);
- Status = __AdapterD3ToD0(Adapter);
- ASSERT(NT_SUCCESS(Status));
+ status = __AdapterD3ToD0(Adapter);
+ ASSERT(NT_SUCCESS(status));
+}
+
+static DECLSPEC_NOINLINE VOID
+AdapterDebugCallback(
+ IN PVOID Context,
+ IN BOOLEAN Crashing
+ )
+{
+ PXENVBD_ADAPTER Adapter = Context;
+ ULONG TargetId;
+
+ XENBUS_DEBUG(Printf,
+ &Adapter->DebugInterface,
+ "ADAPTER: Version: %u.%u.%u.%u (%02u/%02u/%04u)\n",
+ MAJOR_VERSION, MINOR_VERSION, MICRO_VERSION, BUILD_NUMBER,
+ DAY, MONTH, YEAR);
+ XENBUS_DEBUG(Printf,
+ &Adapter->DebugInterface,
+ "ADAPTER: Adapter: 0x%p %s\n",
+ Context,
+ Crashing ? "CRASHING" : "");
+ XENBUS_DEBUG(Printf,
+ &Adapter->DebugInterface,
+ "ADAPTER: DevObj 0x%p LowerDevObj 0x%p PhysDevObj 0x%p\n",
+ Adapter->DeviceObject,
+ Adapter->LowerDeviceObject,
+ Adapter->PhysicalDeviceObject);
+ XENBUS_DEBUG(Printf,
+ &Adapter->DebugInterface,
+ "ADAPTER: DevicePowerState: %s\n",
+ PowerDeviceStateName(Adapter->DevicePower));
+ XENBUS_DEBUG(Printf,
+ &Adapter->DebugInterface,
+ "ADAPTER: Srbs : %u built, %u started, %u
completed\n",
+ Adapter->BuildIo,
+ Adapter->StartIo,
+ Adapter->Completed);
+
+ BufferDebugCallback(&Adapter->DebugInterface);
+
+ for (TargetId = 0; TargetId < XENVBD_MAX_TARGETS; ++TargetId) {
+ // no need to use AdapterGetTarget (which is locked at DISPATCH) as
called at HIGH_LEVEL
+ PXENVBD_TARGET Target = Adapter->TargetList[TargetId];
+ if (Target == NULL)
+ continue;
+
+ XENBUS_DEBUG(Printf, &Adapter->DebugInterface,
+ "ADAPTER: ====> Target[%-3d] : 0x%p\n",
+ TargetId, Target);
+
+ // call Target's debug callback directly
+ TargetDebugCallback(Target, &Adapter->DebugInterface);
+
+ XENBUS_DEBUG(Printf, &Adapter->DebugInterface,
+ "ADAPTER: <==== Target[%-3d] : 0x%p\n",
+ TargetId, Target);
+ }
}
static NTSTATUS
AdapterD3ToD0(
- __in PXENVBD_ADAPTER Adapter
+ IN PXENVBD_ADAPTER Adapter
)
{
- NTSTATUS Status;
- ULONG TargetId;
+ NTSTATUS status;
+ ULONG TargetId;
if (!__AdapterSetDevicePowerState(Adapter, PowerDeviceD0))
return STATUS_SUCCESS;
- Trace("=====> (%d)\n", KeGetCurrentIrql());
Verbose("D3->D0\n");
- // Get Interfaces
- Status = __AdapterAcquire(Adapter);
- if (!NT_SUCCESS(Status))
+ status = XENBUS_SUSPEND(Acquire, &Adapter->SuspendInterface);
+ if (!NT_SUCCESS(status))
goto fail1;
-
- // register debug callback
- ASSERT3P(Adapter->DebugCallback, ==, NULL);
- Status = XENBUS_DEBUG(Register,
- &Adapter->Debug,
+
+ status = XENBUS_DEBUG(Acquire, &Adapter->DebugInterface);
+ if (!NT_SUCCESS(status))
+ goto fail2;
+
+ status = XENBUS_DEBUG(Register,
+ &Adapter->DebugInterface,
__MODULE__,
AdapterDebugCallback,
Adapter,
&Adapter->DebugCallback);
- if (!NT_SUCCESS(Status))
- goto fail2;
+ if (!NT_SUCCESS(status))
+ goto fail3;
+
+ status = __AdapterD3ToD0(Adapter);
+ if (!NT_SUCCESS(status))
+ goto fail4;
- // Power UP any TARGETs
for (TargetId = 0; TargetId < XENVBD_MAX_TARGETS; ++TargetId) {
- PXENVBD_TARGET Target = __AdapterGetTarget(Adapter, TargetId);
- if (Target) {
- Status = TargetD3ToD0(Target);
- TargetDereference(Target);
+ PXENVBD_TARGET Target = AdapterGetTarget(Adapter, TargetId);
+ if (Target == NULL)
+ continue;
- if (!NT_SUCCESS(Status))
- goto fail3;
- }
- }
+ status = TargetD3ToD0(Target);
- Status = __AdapterD3ToD0(Adapter);
- if (!NT_SUCCESS(Status))
- goto fail4;
+ if (!NT_SUCCESS(status))
+ goto fail5;
+ }
- // register suspend callback to re-register the watch
- ASSERT3P(Adapter->SuspendCallback, ==, NULL);
- Status = XENBUS_SUSPEND(Register,
- &Adapter->Suspend,
+ status = XENBUS_SUSPEND(Register,
+ &Adapter->SuspendInterface,
SUSPEND_CALLBACK_LATE,
AdapterSuspendLateCallback,
Adapter,
&Adapter->SuspendCallback);
- if (!NT_SUCCESS(Status))
- goto fail5;
+ if (!NT_SUCCESS(status))
+ goto fail6;
- Trace("<===== (%d)\n", KeGetCurrentIrql());
return STATUS_SUCCESS;
+fail6:
+ Error("fail6\n");
fail5:
- Error("Fail5\n");
+ Error("fail5\n");
+
+ for (TargetId = 0; TargetId < XENVBD_MAX_TARGETS; ++TargetId) {
+ PXENVBD_TARGET Target = AdapterGetTarget(Adapter, TargetId);
+ if (Target == NULL)
+ continue;
+ TargetD0ToD3(Target);
+ }
__AdapterD0ToD3(Adapter);
fail4:
- Error("Fail4\n");
+ Error("fail4\n");
-fail3:
- Error("Fail3\n");
+ XENBUS_DEBUG(Deregister,
+ &Adapter->DebugInterface,
+ Adapter->DebugCallback);
+ Adapter->DebugCallback = NULL;
- for (TargetId = 0; TargetId < XENVBD_MAX_TARGETS; ++TargetId) {
- PXENVBD_TARGET Target = __AdapterGetTarget(Adapter, TargetId);
- if (Target) {
- TargetD0ToD3(Target);
- TargetDereference(Target);
- }
- }
+fail3:
+ Error("fail3\n");
- XENBUS_DEBUG(Deregister, &Adapter->Debug, Adapter->DebugCallback);
- Adapter->DebugCallback = NULL;
+ XENBUS_DEBUG(Release, &Adapter->DebugInterface);
fail2:
- Error("Fail2\n");
+ Error("fail2\n");
+
+ XENBUS_SUSPEND(Release, &Adapter->SuspendInterface);
- __AdapterRelease(Adapter);
-
fail1:
- Error("Fail1 (%08x)\n", Status);
+ Error("fail1 (%08x)\n", status);
__AdapterSetDevicePowerState(Adapter, PowerDeviceD3);
- return Status;
+ return status;
}
static VOID
AdapterD0ToD3(
- __in PXENVBD_ADAPTER Adapter
+ IN PXENVBD_ADAPTER Adapter
)
{
- ULONG TargetId;
+ ULONG TargetId;
if (!__AdapterSetDevicePowerState(Adapter, PowerDeviceD3))
return;
- Trace("=====> (%d)\n", KeGetCurrentIrql());
Verbose("D0->D3\n");
- // remove suspend callback
- XENBUS_SUSPEND(Deregister, &Adapter->Suspend, Adapter->SuspendCallback);
+ XENBUS_SUSPEND(Deregister,
+ &Adapter->SuspendInterface,
+ Adapter->SuspendCallback);
Adapter->SuspendCallback = NULL;
- __AdapterD0ToD3(Adapter);
-
- // Power DOWN any TARGETs
for (TargetId = 0; TargetId < XENVBD_MAX_TARGETS; ++TargetId) {
- PXENVBD_TARGET Target = __AdapterGetTarget(Adapter, TargetId);
- if (Target) {
- TargetD0ToD3(Target);
- TargetDereference(Target);
- }
+ PXENVBD_TARGET Target = AdapterGetTarget(Adapter, TargetId);
+ if (Target == NULL)
+ continue;
+ TargetD0ToD3(Target);
}
- // free debug callback
- if (Adapter->DebugCallback != NULL) {
- XENBUS_DEBUG(Deregister, &Adapter->Debug, Adapter->DebugCallback);
- Adapter->DebugCallback = NULL;
- }
+ __AdapterD0ToD3(Adapter);
- // Release Interfaces
- __AdapterRelease(Adapter);
+ XENBUS_DEBUG(Deregister,
+ &Adapter->DebugInterface,
+ Adapter->DebugCallback);
+ Adapter->DebugCallback = NULL;
- Trace("<===== (%d)\n", KeGetCurrentIrql());
+ XENBUS_DEBUG(Release, &Adapter->DebugInterface);
+
+ XENBUS_SUSPEND(Release, &Adapter->SuspendInterface);
}
-__checkReturn
static DECLSPEC_NOINLINE NTSTATUS
-AdapterDevicePower(
- __in PXENVBD_THREAD Thread,
- __in PVOID Context
+AdapterDevicePowerThread(
+ IN PXENVBD_THREAD Thread,
+ IN PVOID Context
)
{
PXENVBD_ADAPTER Adapter = Context;
@@ -1455,7 +1076,6 @@ AdapterDevicePower(
PIO_STACK_LOCATION Stack;
DEVICE_POWER_STATE DeviceState;
POWER_ACTION Action;
- NTSTATUS Status;
if (!ThreadWait(Thread))
break;
@@ -1474,12 +1094,10 @@ AdapterDevicePower(
case IRP_MN_SET_POWER:
switch (DeviceState) {
case PowerDeviceD0:
- Verbose("ADAPTER:PowerDeviceD0\n");
AdapterD3ToD0(Adapter);
break;
case PowerDeviceD3:
- Verbose("ADAPTER:PowerDeviceD3 (%s)\n",
PowerActionName(Action));
AdapterD0ToD3(Adapter);
break;
@@ -1491,381 +1109,341 @@ AdapterDevicePower(
default:
break;
}
- Status = DriverDispatchPower(Adapter->DeviceObject, Irp);
- if (!NT_SUCCESS(Status)) {
- Warning("StorPort failed PowerIRP with %08x\n", Status);
- }
+ (VOID) DriverDispatchPower(Adapter->DeviceObject, Irp);
}
return STATUS_SUCCESS;
}
-__checkReturn
-__drv_requiresIRQL(PASSIVE_LEVEL)
static NTSTATUS
-__AdapterInitialize(
- __in PXENVBD_ADAPTER Adapter
+__AdapterQueryInterface(
+ IN PXENVBD_ADAPTER Adapter,
+ IN const GUID *Guid,
+ IN ULONG Version,
+ OUT PINTERFACE Interface,
+ IN ULONG Size,
+ IN BOOLEAN Optional
)
{
- ULONG StorStatus;
- NTSTATUS Status;
+ KEVENT Event;
+ IO_STATUS_BLOCK StatusBlock;
+ PIRP Irp;
+ PIO_STACK_LOCATION StackLocation;
+ NTSTATUS status;
+
+ ASSERT3U(KeGetCurrentIrql(), ==, PASSIVE_LEVEL);
+
+ KeInitializeEvent(&Event, NotificationEvent, FALSE);
+ RtlZeroMemory(&StatusBlock, sizeof(IO_STATUS_BLOCK));
+
+ Irp = IoBuildSynchronousFsdRequest(IRP_MJ_PNP,
+ Adapter->LowerDeviceObject,
+ NULL,
+ 0,
+ NULL,
+ &Event,
+ &StatusBlock);
+
+ status = STATUS_UNSUCCESSFUL;
+ if (Irp == NULL)
+ goto fail1;
+
+ StackLocation = IoGetNextIrpStackLocation(Irp);
+ StackLocation->MinorFunction = IRP_MN_QUERY_INTERFACE;
+
+ StackLocation->Parameters.QueryInterface.InterfaceType = Guid;
+ StackLocation->Parameters.QueryInterface.Size = (USHORT)Size;
+ StackLocation->Parameters.QueryInterface.Version = (USHORT)Version;
+ StackLocation->Parameters.QueryInterface.Interface = Interface;
+
+ Irp->IoStatus.Status = STATUS_NOT_SUPPORTED;
+
+ status = IoCallDriver(Adapter->LowerDeviceObject, Irp);
+ if (status == STATUS_PENDING) {
+ (VOID) KeWaitForSingleObject(&Event,
+ Executive,
+ KernelMode,
+ FALSE,
+ NULL);
+ status = StatusBlock.Status;
+ }
+
+ if (!NT_SUCCESS(status)) {
+ if (status == STATUS_NOT_SUPPORTED && Optional)
+ goto done;
+
+ goto fail2;
+ }
+
+done:
+ return STATUS_SUCCESS;
+
+fail2:
+ Error("fail2\n");
+
+fail1:
+ Error("fail1 (%08x)\n", status);
- Trace("=====> (%d)\n", KeGetCurrentIrql());
+ return status;
+}
+
+#define AdapterQueryInterface(_adapter, _name, _itf, _opt) \
+ __AdapterQueryInterface((_adapter), \
+ &GUID_ ## _name ## _INTERFACE, \
+ _name ## _INTERFACE_VERSION_MAX, \
+ (PINTERFACE)(_itf), \
+ sizeof( ## _name ## _INTERFACE), \
+ (_opt))
+static NTSTATUS
+AdapterInitialize(
+ IN PXENVBD_ADAPTER Adapter,
+ IN PDEVICE_OBJECT DeviceObject,
+ IN PDEVICE_OBJECT PhysicalDeviceObject,
+ IN PDEVICE_OBJECT LowerDeviceObject
+ )
+{
+ NTSTATUS status;
ASSERT3U(KeGetCurrentIrql(), <=, DISPATCH_LEVEL);
- // initialize the memory
- Adapter->DevicePower = PowerDeviceD3;
+
+ Adapter->DeviceObject = DeviceObject;
+ Adapter->PhysicalDeviceObject = PhysicalDeviceObject;
+ Adapter->LowerDeviceObject = LowerDeviceObject;
+ Adapter->DevicePower = PowerDeviceD3;
+
KeInitializeSpinLock(&Adapter->TargetLock);
KeInitializeSpinLock(&Adapter->Lock);
KeInitializeEvent(&Adapter->ScanEvent, SynchronizationEvent, FALSE);
- Adapter->Signature = ADAPTER_SIGNATURE;
-
- StorStatus = StorPortGetDeviceObjects(Adapter,
- &Adapter->DeviceObject,
- &Adapter->PhysicalDeviceObject,
- &Adapter->LowerDeviceObject);
- Status = STATUS_UNSUCCESSFUL;
- if (StorStatus != STOR_STATUS_SUCCESS) {
- Error("StorPortGetDeviceObjects() (%x:%s)\n", StorStatus,
StorStatusName(StorStatus));
+ status = AdapterQueryInterface(Adapter,
+ XENBUS_STORE,
+ &Adapter->StoreInterface,
+ FALSE);
+ if (!NT_SUCCESS(status))
goto fail1;
- }
- // get interfaces
- Status = __AdapterQueryInterfaces(Adapter);
- if (!NT_SUCCESS(Status))
+ status = AdapterQueryInterface(Adapter,
+ XENBUS_EVTCHN,
+ &Adapter->EvtchnInterface,
+ FALSE);
+ if (!NT_SUCCESS(status))
goto fail2;
- // start enum thread
- Status = ThreadCreate(AdapterScan, Adapter, &Adapter->ScanThread);
- if (!NT_SUCCESS(Status))
+ status = AdapterQueryInterface(Adapter,
+ XENBUS_GNTTAB,
+ &Adapter->GnttabInterface,
+ FALSE);
+ if (!NT_SUCCESS(status))
goto fail3;
- Status = ThreadCreate(AdapterDevicePower, Adapter,
&Adapter->DevicePowerThread);
- if (!NT_SUCCESS(Status))
+ status = AdapterQueryInterface(Adapter,
+ XENBUS_SUSPEND,
+ &Adapter->SuspendInterface,
+ FALSE);
+ if (!NT_SUCCESS(status))
goto fail4;
- Trace("<===== (%d)\n", KeGetCurrentIrql());
+ status = AdapterQueryInterface(Adapter,
+ XENBUS_DEBUG,
+ &Adapter->DebugInterface,
+ FALSE);
+ if (!NT_SUCCESS(status))
+ goto fail5;
+
+ status = AdapterQueryInterface(Adapter,
+ XENBUS_UNPLUG,
+ &Adapter->UnplugInterface,
+ FALSE);
+ if (!NT_SUCCESS(status))
+ goto fail6;
+
+ status = AdapterQueryInterface(Adapter,
+ XENFILT_EMULATED,
+ &Adapter->EmulatedInterface,
+ TRUE);
+ if (!NT_SUCCESS(status))
+ goto fail7;
+
+ status = ThreadCreate(AdapterScanThread,
+ Adapter,
+ &Adapter->ScanThread);
+ if (!NT_SUCCESS(status))
+ goto fail8;
+
+ status = ThreadCreate(AdapterDevicePowerThread,
+ Adapter,
+ &Adapter->DevicePowerThread);
+ if (!NT_SUCCESS(status))
+ goto fail9;
+
return STATUS_SUCCESS;
-fail4:
- Error("fail4\n");
+fail9:
+ Error("fail9\n");
ThreadAlert(Adapter->ScanThread);
ThreadJoin(Adapter->ScanThread);
Adapter->ScanThread = NULL;
+fail8:
+ Error("fail8\n");
+ RtlZeroMemory(&Adapter->EmulatedInterface,
+ sizeof (XENFILT_EMULATED_INTERFACE));
+fail7:
+ Error("fail7\n");
+ RtlZeroMemory(&Adapter->UnplugInterface,
+ sizeof (XENBUS_UNPLUG_INTERFACE));
+fail6:
+ Error("fail6\n");
+ RtlZeroMemory(&Adapter->DebugInterface,
+ sizeof (XENBUS_DEBUG_INTERFACE));
+fail5:
+ Error("fail5\n");
+ RtlZeroMemory(&Adapter->SuspendInterface,
+ sizeof (XENBUS_SUSPEND_INTERFACE));
+fail4:
+ Error("fail4\n");
+ RtlZeroMemory(&Adapter->GnttabInterface,
+ sizeof (XENBUS_GNTTAB_INTERFACE));
fail3:
Error("fail3\n");
- __AdapterZeroInterfaces(Adapter);
+ RtlZeroMemory(&Adapter->EvtchnInterface,
+ sizeof (XENBUS_EVTCHN_INTERFACE));
fail2:
Error("fail2\n");
- Adapter->DeviceObject = NULL;
- Adapter->PhysicalDeviceObject = NULL;
- Adapter->LowerDeviceObject = NULL;
+ RtlZeroMemory(&Adapter->StoreInterface,
+ sizeof (XENBUS_STORE_INTERFACE));
fail1:
- Error("fail1 (%08x)\n", Status);
- return Status;
+ Error("fail1 (%08x)\n", status);
+
+ RtlZeroMemory(&Adapter->TargetLock, sizeof(KSPIN_LOCK));
+ RtlZeroMemory(&Adapter->Lock, sizeof(KSPIN_LOCK));
+ RtlZeroMemory(&Adapter->ScanEvent, sizeof(KEVENT));
+
+ Adapter->DevicePower = 0;
+ Adapter->DeviceObject = NULL;
+ Adapter->PhysicalDeviceObject = NULL;
+ Adapter->LowerDeviceObject = NULL;
+
+ return status;
}
-__drv_maxIRQL(PASSIVE_LEVEL)
+
static VOID
-__AdapterTerminate(
- __in PXENVBD_ADAPTER Adapter
+AdapterTeardown(
+ IN PXENVBD_ADAPTER Adapter
)
{
- ULONG TargetId;
-
- Trace("=====> (%d)\n", KeGetCurrentIrql());
+ ULONG TargetId;
ASSERT3U(Adapter->DevicePower, ==, PowerDeviceD3);
- // stop device power thread
ThreadAlert(Adapter->DevicePowerThread);
ThreadJoin(Adapter->DevicePowerThread);
Adapter->DevicePowerThread = NULL;
- // stop enum thread
ThreadAlert(Adapter->ScanThread);
ThreadJoin(Adapter->ScanThread);
Adapter->ScanThread = NULL;
- // clear device objects
- Adapter->DeviceObject = NULL;
- Adapter->PhysicalDeviceObject = NULL;
- Adapter->LowerDeviceObject = NULL;
-
- // delete targets
- for (TargetId = 0; TargetId < XENVBD_MAX_TARGETS; ++TargetId) {
- PXENVBD_TARGET Target = __AdapterGetTargetAlways(Adapter, TargetId,
__FUNCTION__);
- if (Target) {
- // Target may not be in Deleted state yet, force it as Adapter is
terminating
- if (TargetGetDevicePnpState(Target) != Deleted)
- TargetSetDevicePnpState(Target, Deleted);
- // update missing (for debug output more than anything else
- TargetSetMissing(Target, "AdapterTerminate");
- // drop ref-count acquired in __AdapterGetTarget *before*
destroying Target
- TargetDereference(Target);
- TargetDestroy(Target);
- }
- }
-
- // cleanup memory
- ASSERT3U(Adapter->DevicePower, ==, PowerDeviceD3);
- ASSERT3P(Adapter->DebugCallback, ==, NULL);
- ASSERT3P(Adapter->SuspendCallback, ==, NULL);
-
- Adapter->Signature = 0;
- Adapter->DevicePower = 0;
- Adapter->CurrentSrbs = Adapter->MaximumSrbs = Adapter->TotalSrbs = 0;
- RtlZeroMemory(&Adapter->Enumerator, sizeof(ANSI_STRING));
- RtlZeroMemory(&Adapter->TargetLock, sizeof(KSPIN_LOCK));
- RtlZeroMemory(&Adapter->Lock, sizeof(KSPIN_LOCK));
- RtlZeroMemory(&Adapter->ScanEvent, sizeof(KEVENT));
- __AdapterZeroInterfaces(Adapter);
-
- ASSERT(IsZeroMemory(Adapter, sizeof(XENVBD_ADAPTER)));
- Trace("<===== (%d)\n", KeGetCurrentIrql());
-}
-//=============================================================================
-// Query Methods
-__checkReturn
-FORCEINLINE PDEVICE_OBJECT
-AdapterGetDeviceObject(
- __in PXENVBD_ADAPTER Adapter
- )
-{
- if (Adapter)
- return Adapter->DeviceObject;
- return NULL;
-}
-
-FORCEINLINE ULONG
-AdapterSizeofXenvbdAdapter(
- )
-{
- return (ULONG)sizeof(XENVBD_ADAPTER);
-}
-
-FORCEINLINE PCHAR
-AdapterEnum(
- __in PXENVBD_ADAPTER Adapter
- )
-{
- if (Adapter->Enumerator.Buffer)
- return Adapter->Enumerator.Buffer;
- else
- return "vbd";
-}
-
-//=============================================================================
-// SRB Methods
-FORCEINLINE VOID
-AdapterStartSrb(
- __in PXENVBD_ADAPTER Adapter,
- __in PSCSI_REQUEST_BLOCK Srb
- )
-{
- LONG Value;
-
- UNREFERENCED_PARAMETER(Srb);
-
- Value = InterlockedIncrement(&Adapter->CurrentSrbs);
- if (Value > Adapter->MaximumSrbs)
- Adapter->MaximumSrbs = Value;
- InterlockedIncrement(&Adapter->TotalSrbs);
-}
-
-FORCEINLINE VOID
-AdapterCompleteSrb(
- __in PXENVBD_ADAPTER Adapter,
- __in PSCSI_REQUEST_BLOCK Srb
- )
-{
- ASSERT3U(Srb->SrbStatus, !=, SRB_STATUS_PENDING);
-
- InterlockedDecrement(&Adapter->CurrentSrbs);
-
- StorPortNotification(RequestComplete, Adapter, Srb);
-}
-
-//=============================================================================
-// StorPort Methods
-BOOLEAN
-AdapterResetBus(
- __in PXENVBD_ADAPTER Adapter
- )
-{
- ULONG TargetId;
-
- Verbose("====>\n");
for (TargetId = 0; TargetId < XENVBD_MAX_TARGETS; ++TargetId) {
- PXENVBD_TARGET Target = __AdapterGetTarget(Adapter, TargetId);
- if (Target) {
- TargetReset(Target);
- TargetDereference(Target);
- }
- }
- Verbose("<====\n");
-
- return TRUE;
-}
-
-static VOID
-AdapterUnplugRequest(
- IN PXENVBD_ADAPTER Adapter,
- IN BOOLEAN Make
- )
-{
- NTSTATUS status;
-
- status = XENBUS_UNPLUG(Acquire, &Adapter->Unplug);
- if (!NT_SUCCESS(status))
- return;
+ PXENVBD_TARGET Target = AdapterGetTarget(Adapter, TargetId);
+ if (Target == NULL)
+ continue;
- XENBUS_UNPLUG(Request,
- &Adapter->Unplug,
- XENBUS_UNPLUG_DEVICE_TYPE_DISKS,
- Make);
+ // Target may not be in Deleted state yet, force it as Adapter is
terminating
+ if (TargetGetDevicePnpState(Target) != Deleted)
+ TargetSetDevicePnpState(Target, Deleted);
+ // update missing (for debug output more than anything else
+ TargetSetMissing(Target, "AdapterTeardown");
+ // drop ref-count acquired in __AdapterGetTarget *before* destroying
Target
+ TargetDestroy(Target);
+ }
- XENBUS_UNPLUG(Release, &Adapter->Unplug);
-}
+ RtlZeroMemory(&Adapter->EmulatedInterface,
+ sizeof (XENFILT_EMULATED_INTERFACE));
-ULONG
-AdapterFindAdapter(
- __in PXENVBD_ADAPTER Adapter,
- __inout PPORT_CONFIGURATION_INFORMATION ConfigInfo
- )
-{
- // setup config info
- ConfigInfo->MaximumTransferLength = XENVBD_MAX_TRANSFER_LENGTH;
- ConfigInfo->NumberOfPhysicalBreaks = XENVBD_MAX_PHYSICAL_BREAKS;
- ConfigInfo->AlignmentMask = 0; // Byte-Aligned
- ConfigInfo->NumberOfBuses = 1;
- ConfigInfo->InitiatorBusId[0] = 1;
- ConfigInfo->ScatterGather = TRUE;
- ConfigInfo->Master = TRUE;
- ConfigInfo->CachesData = FALSE;
- ConfigInfo->MapBuffers = STOR_MAP_NON_READ_WRITE_BUFFERS;
- ConfigInfo->MaximumNumberOfTargets = XENVBD_MAX_TARGETS;
- ConfigInfo->MaximumNumberOfLogicalUnits = 1;
- ConfigInfo->WmiDataProvider = FALSE; // should be TRUE
- ConfigInfo->SynchronizationModel = StorSynchronizeFullDuplex;
+ RtlZeroMemory(&Adapter->UnplugInterface,
+ sizeof (XENBUS_UNPLUG_INTERFACE));
- if (ConfigInfo->Dma64BitAddresses == SCSI_DMA64_SYSTEM_SUPPORTED) {
- Trace("64bit DMA\n");
- ConfigInfo->Dma64BitAddresses = SCSI_DMA64_MINIPORT_SUPPORTED;
- }
+ RtlZeroMemory(&Adapter->DebugInterface,
+ sizeof (XENBUS_DEBUG_INTERFACE));
- // gets called on resume from hibernate, so only setup if not already done
- if (Adapter->Signature == ADAPTER_SIGNATURE) {
- Verbose("ADAPTER already initalized (0x%p)\n", Adapter);
- return SP_RETURN_FOUND;
- }
+ RtlZeroMemory(&Adapter->SuspendInterface,
+ sizeof (XENBUS_SUSPEND_INTERFACE));
- // We need to do this to avoid an assertion in a checked kernel
- (VOID) StorPortGetUncachedExtension(Adapter, ConfigInfo, PAGE_SIZE);
+ RtlZeroMemory(&Adapter->GnttabInterface,
+ sizeof (XENBUS_GNTTAB_INTERFACE));
- if (!NT_SUCCESS(__AdapterInitialize(Adapter)))
- return SP_RETURN_ERROR;
+ RtlZeroMemory(&Adapter->EvtchnInterface,
+ sizeof (XENBUS_EVTCHN_INTERFACE));
- AdapterUnplugRequest(Adapter, TRUE);
+ RtlZeroMemory(&Adapter->StoreInterface,
+ sizeof (XENBUS_STORE_INTERFACE));
- if (!NT_SUCCESS(AdapterD3ToD0(Adapter)))
- return SP_RETURN_ERROR;
+ RtlZeroMemory(&Adapter->TargetLock, sizeof(KSPIN_LOCK));
+ RtlZeroMemory(&Adapter->Lock, sizeof(KSPIN_LOCK));
+ RtlZeroMemory(&Adapter->ScanEvent, sizeof(KEVENT));
- return SP_RETURN_FOUND;
-}
+ Adapter->DevicePower = 0;
+ Adapter->DeviceObject = NULL;
+ Adapter->PhysicalDeviceObject = NULL;
+ Adapter->LowerDeviceObject = NULL;
-static FORCEINLINE VOID
-__AdapterSrbPnp(
- __in PXENVBD_ADAPTER Adapter,
- __in PSCSI_PNP_REQUEST_BLOCK Srb
- )
-{
- if (!(Srb->SrbPnPFlags & SRB_PNP_FLAGS_ADAPTER_REQUEST)) {
- PXENVBD_TARGET Target;
+ Adapter->BuildIo = 0;
+ Adapter->StartIo = 0;
+ Adapter->Completed = 0;
- Target = __AdapterGetTarget(Adapter, Srb->TargetId);
- if (Target) {
- TargetSrbPnp(Target, Srb);
- TargetDereference(Target);
- }
- }
+ ASSERT(IsZeroMemory(Adapter, sizeof(XENVBD_ADAPTER)));
+ Trace("<===== (%d)\n", KeGetCurrentIrql());
}
-BOOLEAN
-AdapterBuildIo(
- __in PXENVBD_ADAPTER Adapter,
- __in PSCSI_REQUEST_BLOCK Srb
+VOID
+AdapterCompleteSrb(
+ IN PXENVBD_ADAPTER Adapter,
+ IN PSCSI_REQUEST_BLOCK Srb
)
{
- InitSrbExt(Srb);
+ ASSERT3U(Srb->SrbStatus, !=, SRB_STATUS_PENDING);
- switch (Srb->Function) {
- case SRB_FUNCTION_EXECUTE_SCSI:
- case SRB_FUNCTION_RESET_DEVICE:
- case SRB_FUNCTION_FLUSH:
- case SRB_FUNCTION_SHUTDOWN:
- AdapterStartSrb(Adapter, Srb);
- return TRUE;
+ ++Adapter->Completed;
- // dont pass to StartIo
- case SRB_FUNCTION_PNP:
- __AdapterSrbPnp(Adapter, (PSCSI_PNP_REQUEST_BLOCK)Srb);
- Srb->SrbStatus = SRB_STATUS_SUCCESS;
- break;
- case SRB_FUNCTION_ABORT_COMMAND:
- Srb->SrbStatus = SRB_STATUS_ABORT_FAILED;
- break;
- case SRB_FUNCTION_RESET_BUS:
- Srb->SrbStatus = SRB_STATUS_SUCCESS;
- AdapterResetBus(Adapter);
- break;
-
- default:
- break;
- }
-
StorPortNotification(RequestComplete, Adapter, Srb);
- return FALSE;
-}
+}
-BOOLEAN
-AdapterStartIo(
- __in PXENVBD_ADAPTER Adapter,
- __in PSCSI_REQUEST_BLOCK Srb
+static VOID
+AdapterUnplugRequest(
+ IN PXENVBD_ADAPTER Adapter,
+ IN BOOLEAN Make
)
{
- PXENVBD_TARGET Target;
- BOOLEAN CompleteSrb = TRUE;
+ NTSTATUS status;
- Target = __AdapterGetTarget(Adapter, Srb->TargetId);
- if (Target) {
- CompleteSrb = TargetStartIo(Target, Srb);
- TargetDereference(Target);
- }
+ status = XENBUS_UNPLUG(Acquire, &Adapter->UnplugInterface);
+ if (!NT_SUCCESS(status))
+ return;
- if (CompleteSrb) {
- AdapterCompleteSrb(Adapter, Srb);
- }
- return TRUE;
+ XENBUS_UNPLUG(Request,
+ &Adapter->UnplugInterface,
+ XENBUS_UNPLUG_DEVICE_TYPE_DISKS,
+ Make);
+
+ XENBUS_UNPLUG(Release, &Adapter->UnplugInterface);
}
static PXENVBD_TARGET
AdapterGetTargetFromDeviceObject(
- __in PXENVBD_ADAPTER Adapter,
- __in PDEVICE_OBJECT DeviceObject
+ IN PXENVBD_ADAPTER Adapter,
+ IN PDEVICE_OBJECT DeviceObject
)
{
- ULONG TargetId;
+ ULONG TargetId;
ASSERT3P(DeviceObject, !=, NULL);
for (TargetId = 0; TargetId < XENVBD_MAX_TARGETS; ++TargetId) {
- PXENVBD_TARGET Target = __AdapterGetTarget(Adapter, TargetId);
- if (Target) {
- if (TargetGetDeviceObject(Target) == DeviceObject)
- return Target;
- TargetDereference(Target);
- }
+ PXENVBD_TARGET Target = AdapterGetTarget(Adapter, TargetId);
+ if (Target == NULL)
+ continue;
+ if (TargetGetDeviceObject(Target) == DeviceObject)
+ return Target;
}
return NULL;
@@ -1873,18 +1451,18 @@ AdapterGetTargetFromDeviceObject(
static PXENVBD_TARGET
AdapterMapDeviceObjectToTarget(
- __in PXENVBD_ADAPTER Adapter,
- __in PDEVICE_OBJECT DeviceObject
+ IN PXENVBD_ADAPTER Adapter,
+ IN PDEVICE_OBJECT DeviceObject
)
{
- PXENVBD_TARGET Target;
- KEVENT Complete;
- PIRP Irp;
- IO_STATUS_BLOCK StatusBlock;
- PIO_STACK_LOCATION Stack;
- NTSTATUS Status;
- PWCHAR String;
- ULONG TargetId;
+ PXENVBD_TARGET Target;
+ KEVENT Complete;
+ PIRP Irp;
+ IO_STATUS_BLOCK StatusBlock;
+ PIO_STACK_LOCATION Stack;
+ NTSTATUS Status;
+ PWCHAR String;
+ ULONG TargetId;
DECLARE_UNICODE_STRING_SIZE(UniStr, 4);
KeInitializeEvent(&Complete, NotificationEvent, FALSE);
@@ -1928,7 +1506,7 @@ AdapterMapDeviceObjectToTarget(
if (!NT_SUCCESS(Status))
goto fail4;
- Target = __AdapterGetTarget(Adapter, TargetId);
+ Target = AdapterGetTarget(Adapter, TargetId);
if (Target == NULL)
goto fail5;
@@ -1946,16 +1524,15 @@ fail1:
return NULL;
}
-__checkReturn
-NTSTATUS
+static NTSTATUS
AdapterForwardPnp(
- __in PXENVBD_ADAPTER Adapter,
- __in PDEVICE_OBJECT DeviceObject,
- __in PIRP Irp
+ IN PXENVBD_ADAPTER Adapter,
+ IN PDEVICE_OBJECT DeviceObject,
+ IN PIRP Irp
)
{
PIO_STACK_LOCATION Stack;
- PXENVBD_TARGET Target;
+ PXENVBD_TARGET Target;
ASSERT3P(DeviceObject, !=, Adapter->DeviceObject);
@@ -1976,26 +1553,25 @@ AdapterForwardPnp(
return DriverDispatchPnp(DeviceObject, Irp);
}
-__checkReturn
NTSTATUS
AdapterDispatchPnp(
- __in PXENVBD_ADAPTER Adapter,
- __in PDEVICE_OBJECT DeviceObject,
- __in PIRP Irp
+ IN PXENVBD_ADAPTER Adapter,
+ IN PDEVICE_OBJECT DeviceObject,
+ IN PIRP Irp
)
{
PIO_STACK_LOCATION Stack;
- ASSERT3P(DeviceObject, ==, Adapter->DeviceObject);
+ if (Adapter->DeviceObject != DeviceObject)
+ return AdapterForwardPnp(Adapter, DeviceObject, Irp);
Stack = IoGetCurrentIrpStackLocation(Irp);
switch (Stack->MinorFunction) {
case IRP_MN_REMOVE_DEVICE:
- Verbose("ADAPTER:IRP_MN_REMOVE_DEVICE\n");
AdapterD0ToD3(Adapter);
AdapterUnplugRequest(Adapter, FALSE);
- __AdapterTerminate(Adapter);
+ AdapterTeardown(Adapter);
break;
case IRP_MN_QUERY_DEVICE_RELATIONS:
@@ -2004,12 +1580,12 @@ AdapterDispatchPnp(
ThreadWake(Adapter->ScanThread);
Trace("waiting for scan thread\n");
-
(VOID) KeWaitForSingleObject(&Adapter->ScanEvent,
Executive,
KernelMode,
FALSE,
NULL);
+ Trace("scan thread wait complete\n");
}
break;
@@ -2020,19 +1596,19 @@ AdapterDispatchPnp(
return DriverDispatchPnp(DeviceObject, Irp);
}
-__checkReturn
NTSTATUS
AdapterDispatchPower(
- __in PXENVBD_ADAPTER Adapter,
- __in PDEVICE_OBJECT DeviceObject,
- __in PIRP Irp
+ IN PXENVBD_ADAPTER Adapter,
+ IN PDEVICE_OBJECT DeviceObject,
+ IN PIRP Irp
)
{
PIO_STACK_LOCATION Stack;
POWER_STATE_TYPE PowerType;
NTSTATUS status;
- ASSERT3P(DeviceObject, ==, Adapter->DeviceObject);
+ if (Adapter->DeviceObject != DeviceObject)
+ return DriverDispatchPower(DeviceObject, Irp);
Stack = IoGetCurrentIrpStackLocation(Irp);
PowerType = Stack->Parameters.Power.Type;
@@ -2065,72 +1641,299 @@ AdapterDispatchPower(
return status;
}
-PXENBUS_STORE_INTERFACE
-AdapterAcquireStore(
- __in PXENVBD_ADAPTER Adapter
+HW_RESET_BUS AdapterHwResetBus;
+
+BOOLEAN
+AdapterHwResetBus(
+ IN PVOID DevExt,
+ IN ULONG PathId
)
{
- NTSTATUS status;
+ PXENVBD_ADAPTER Adapter = DevExt;
+ ULONG TargetId;
- status = XENBUS_STORE(Acquire, &Adapter->Store);
- if (!NT_SUCCESS(status))
- return NULL;
+ UNREFERENCED_PARAMETER(PathId);
+
+ Verbose("====>\n");
+ for (TargetId = 0; TargetId < XENVBD_MAX_TARGETS; ++TargetId) {
+ PXENVBD_TARGET Target = AdapterGetTarget(Adapter, TargetId);
+ if (Target == NULL)
+ continue;
+
+ TargetReset(Target);
+ }
+ Verbose("<====\n");
- return &Adapter->Store;
+ return TRUE;
}
-PXENBUS_EVTCHN_INTERFACE
-AdapterAcquireEvtchn(
- __in PXENVBD_ADAPTER Adapter
+
+static FORCEINLINE VOID
+__AdapterSrbPnp(
+ IN PXENVBD_ADAPTER Adapter,
+ IN PSCSI_PNP_REQUEST_BLOCK Srb
)
{
- NTSTATUS status;
+ if (!(Srb->SrbPnPFlags & SRB_PNP_FLAGS_ADAPTER_REQUEST)) {
+ PXENVBD_TARGET Target;
- status = XENBUS_EVTCHN(Acquire, &Adapter->Evtchn);
- if (!NT_SUCCESS(status))
- return NULL;
+ Target = AdapterGetTarget(Adapter, Srb->TargetId);
+ if (Target) {
+ TargetSrbPnp(Target, Srb);
+ }
+ }
+}
+
+HW_BUILDIO AdapterHwBuildIo;
+
+BOOLEAN
+AdapterHwBuildIo(
+ IN PVOID DevExt,
+ IN PSCSI_REQUEST_BLOCK Srb
+ )
+{
+ PXENVBD_ADAPTER Adapter = DevExt;
+
+ InitSrbExt(Srb);
+
+ switch (Srb->Function) {
+ case SRB_FUNCTION_EXECUTE_SCSI:
+ case SRB_FUNCTION_RESET_DEVICE:
+ case SRB_FUNCTION_FLUSH:
+ case SRB_FUNCTION_SHUTDOWN:
+ ++Adapter->BuildIo;
+ return TRUE;
- return &Adapter->Evtchn;
+ // dont pass to StartIo
+ case SRB_FUNCTION_PNP:
+ __AdapterSrbPnp(Adapter, (PSCSI_PNP_REQUEST_BLOCK)Srb);
+ Srb->SrbStatus = SRB_STATUS_SUCCESS;
+ break;
+ case SRB_FUNCTION_ABORT_COMMAND:
+ Srb->SrbStatus = SRB_STATUS_ABORT_FAILED;
+ break;
+ case SRB_FUNCTION_RESET_BUS:
+ Srb->SrbStatus = SRB_STATUS_SUCCESS;
+ AdapterHwResetBus(Adapter, Srb->PathId);
+ break;
+
+ default:
+ break;
+ }
+
+ StorPortNotification(RequestComplete, Adapter, Srb);
+ return FALSE;
}
-PXENBUS_GNTTAB_INTERFACE
-AdapterAcquireGnttab(
- __in PXENVBD_ADAPTER Adapter
+HW_STARTIO AdapterHwStartIo;
+
+BOOLEAN
+AdapterHwStartIo(
+ IN PVOID DevExt,
+ IN PSCSI_REQUEST_BLOCK Srb
)
{
- NTSTATUS status;
+ PXENVBD_ADAPTER Adapter = DevExt;
+ PXENVBD_TARGET Target;
- status = XENBUS_GNTTAB(Acquire, &Adapter->Gnttab);
- if (!NT_SUCCESS(status))
- return NULL;
+ Target = AdapterGetTarget(Adapter, Srb->TargetId);
+ if (Target == NULL)
+ goto fail1;
+
+ ++Adapter->StartIo;
+ if (TargetStartIo(Target, Srb))
+ AdapterCompleteSrb(Adapter, Srb);
- return &Adapter->Gnttab;
+ return TRUE;
+
+fail1:
+ AdapterCompleteSrb(Adapter, Srb);
+ return TRUE;
}
-PXENBUS_DEBUG_INTERFACE
-AdapterAcquireDebug(
- __in PXENVBD_ADAPTER Adapter
+HW_ADAPTER_CONTROL AdapterHwAdapterControl;
+
+SCSI_ADAPTER_CONTROL_STATUS
+AdapterHwAdapterControl(
+ IN PVOID DevExt,
+ IN SCSI_ADAPTER_CONTROL_TYPE ControlType,
+ IN PVOID Parameters
)
{
- NTSTATUS status;
+ PSCSI_SUPPORTED_CONTROL_TYPE_LIST List;
+
+ UNREFERENCED_PARAMETER(DevExt);
+
+ switch (ControlType) {
+ case ScsiQuerySupportedControlTypes:
+ List = Parameters;
+ List->SupportedTypeList[ScsiQuerySupportedControlTypes] = TRUE;
+ break;
+
+ default:
+ break;
+ }
+ return ScsiAdapterControlSuccess;
+}
+
+HW_FIND_ADAPTER AdapterHwFindAdapter;
+
+ULONG
+AdapterHwFindAdapter(
+ IN PVOID DevExt,
+ IN PVOID Context,
+ IN PVOID BusInformation,
+ IN PCHAR ArgumentString,
+ IN OUT PPORT_CONFIGURATION_INFORMATION ConfigInfo,
+ OUT PBOOLEAN Again
+ )
+{
+ PXENVBD_ADAPTER Adapter = DevExt;
+ PDEVICE_OBJECT DeviceObject;
+ PDEVICE_OBJECT PhysicalDeviceObject;
+ PDEVICE_OBJECT LowerDeviceObject;
+ NTSTATUS status;
+
+ UNREFERENCED_PARAMETER(Context);
+ UNREFERENCED_PARAMETER(BusInformation);
+ UNREFERENCED_PARAMETER(ArgumentString);
+ UNREFERENCED_PARAMETER(Again);
+
+ // setup config info
+ ConfigInfo->MaximumTransferLength = XENVBD_MAX_TRANSFER_LENGTH;
+ ConfigInfo->NumberOfPhysicalBreaks = XENVBD_MAX_PHYSICAL_BREAKS;
+ ConfigInfo->AlignmentMask = 0; // Byte-Aligned
+ ConfigInfo->NumberOfBuses = 1;
+ ConfigInfo->InitiatorBusId[0] = 1;
+ ConfigInfo->ScatterGather = TRUE;
+ ConfigInfo->Master = TRUE;
+ ConfigInfo->CachesData = FALSE;
+ ConfigInfo->MapBuffers = STOR_MAP_NON_READ_WRITE_BUFFERS;
+ ConfigInfo->MaximumNumberOfTargets = XENVBD_MAX_TARGETS;
+ ConfigInfo->MaximumNumberOfLogicalUnits = 1;
+ ConfigInfo->WmiDataProvider = FALSE; // should be TRUE
+ ConfigInfo->SynchronizationModel = StorSynchronizeFullDuplex;
+
+ if (ConfigInfo->Dma64BitAddresses == SCSI_DMA64_SYSTEM_SUPPORTED)
+ ConfigInfo->Dma64BitAddresses = SCSI_DMA64_MINIPORT_SUPPORTED;
+
+ // We need to do this to avoid an assertion in a checked kernel
+ (VOID) StorPortGetUncachedExtension(DevExt, ConfigInfo, PAGE_SIZE);
+
+ (VOID) StorPortGetDeviceObjects(DevExt,
+ &DeviceObject,
+ &PhysicalDeviceObject,
+ &LowerDeviceObject);
+ if (Adapter->DeviceObject == DeviceObject)
+ return SP_RETURN_FOUND;
+
+ status = AdapterInitialize(Adapter,
+ DeviceObject,
+ PhysicalDeviceObject,
+ LowerDeviceObject);
+ if (!NT_SUCCESS(status))
+ goto fail1;
- status = XENBUS_DEBUG(Acquire, &Adapter->Debug);
+ AdapterUnplugRequest(Adapter, TRUE);
+
+ status = AdapterD3ToD0(Adapter);
if (!NT_SUCCESS(status))
- return NULL;
+ goto fail2;
+
+ DriverSetAdapter(Adapter);
+ return SP_RETURN_FOUND;
- return &Adapter->Debug;
+fail2:
+ Error("fail2\n");
+ AdapterUnplugRequest(Adapter, FALSE);
+ AdapterTeardown(Adapter);
+fail1:
+ Error("fail1\n");
+ return SP_RETURN_ERROR;
}
-PXENBUS_SUSPEND_INTERFACE
-AdapterAcquireSuspend(
- __in PXENVBD_ADAPTER Adapter
+HW_INITIALIZE AdapterHwInitialize;
+
+BOOLEAN
+AdapterHwInitialize(
+ IN PVOID DevExt
)
{
- NTSTATUS status;
+ UNREFERENCED_PARAMETER(DevExt);
+ return TRUE;
+}
+
+HW_INTERRUPT AdapterHwInterrupt;
+
+BOOLEAN
+AdapterHwInterrupt(
+ IN PVOID DevExt
+ )
+{
+ UNREFERENCED_PARAMETER(DevExt);
+ return TRUE;
+}
- status = XENBUS_SUSPEND(Acquire, &Adapter->Suspend);
+NTSTATUS
+AdapterDriverEntry(
+ IN PUNICODE_STRING RegistryPath,
+ IN PDRIVER_OBJECT DriverObject
+ )
+{
+ HW_INITIALIZATION_DATA InitData;
+ NTSTATUS status;
+
+ RtlZeroMemory(&InitData, sizeof(InitData));
+ InitData.HwInitializationDataSize = sizeof(InitData);
+ InitData.AdapterInterfaceType = Internal;
+ InitData.HwInitialize = AdapterHwInitialize;
+ InitData.HwStartIo = AdapterHwStartIo;
+ InitData.HwInterrupt = AdapterHwInterrupt;
+#pragma warning(suppress : 4152)
+ InitData.HwFindAdapter = AdapterHwFindAdapter;
+ InitData.HwResetBus = AdapterHwResetBus;
+ InitData.HwDmaStarted = NULL;
+ InitData.HwAdapterState = NULL;
+ InitData.DeviceExtensionSize = sizeof(XENVBD_ADAPTER);
+ InitData.SpecificLuExtensionSize = sizeof(ULONG); // not actually used
+ InitData.SrbExtensionSize = sizeof(XENVBD_SRBEXT);
+ InitData.NumberOfAccessRanges = 2;
+ InitData.MapBuffers = STOR_MAP_NON_READ_WRITE_BUFFERS;
+ InitData.NeedPhysicalAddresses = TRUE;
+ InitData.TaggedQueuing = TRUE;
+ InitData.AutoRequestSense = TRUE;
+ InitData.MultipleRequestPerLu = TRUE;
+ InitData.HwAdapterControl = AdapterHwAdapterControl;
+ InitData.HwBuildIo = AdapterHwBuildIo;
+
+ status = StorPortInitialize(DriverObject,
+ RegistryPath,
+ &InitData,
+ NULL);
if (!NT_SUCCESS(status))
- return NULL;
+ goto fail1;
- return &Adapter->Suspend;
+ return STATUS_SUCCESS;
+
+fail1:
+ Error("fail1 %08x\n", status);
+ return status;
}
+
+#define ADAPTER_GET_INTERFACE(_name, _type) \
+VOID \
+AdapterGet ## _name ## Interface( \
+ IN PXENVBD_ADAPTER Adapter, \
+ OUT _type _name ## Interface \
+ ) \
+{ \
+ * ## _name ## Interface = Adapter-> ## _name ## Interface; \
+}
+
+ADAPTER_GET_INTERFACE(Store, PXENBUS_STORE_INTERFACE)
+ADAPTER_GET_INTERFACE(Debug, PXENBUS_DEBUG_INTERFACE)
+ADAPTER_GET_INTERFACE(Evtchn, PXENBUS_EVTCHN_INTERFACE)
+ADAPTER_GET_INTERFACE(Gnttab, PXENBUS_GNTTAB_INTERFACE)
+ADAPTER_GET_INTERFACE(Suspend, PXENBUS_SUSPEND_INTERFACE)
+
+#undef ADAPTER_GET_INTERFACE
diff --git a/src/xenvbd/adapter.h b/src/xenvbd/adapter.h
index 09d5ee6..2867398 100644
--- a/src/xenvbd/adapter.h
+++ b/src/xenvbd/adapter.h
@@ -37,126 +37,57 @@
typedef struct _XENVBD_ADAPTER XENVBD_ADAPTER, *PXENVBD_ADAPTER;
#include <storport.h>
-#include "target.h"
#include <store_interface.h>
#include <evtchn_interface.h>
#include <gnttab_interface.h>
#include <debug_interface.h>
#include <suspend_interface.h>
-#include <unplug_interface.h>
-// Link TARGETs
-extern BOOLEAN
-AdapterLinkTarget(
- __in PXENVBD_ADAPTER Adapter,
- __in PXENVBD_TARGET Target
- );
-
-extern BOOLEAN
-AdapterUnlinkTarget(
- __in PXENVBD_ADAPTER Adapter,
- __in PXENVBD_TARGET Target
- );
-// Query Methods
-__checkReturn
-extern PDEVICE_OBJECT
-AdapterGetDeviceObject(
- __in PXENVBD_ADAPTER Adapter
+#define ADAPTER_GET_INTERFACE(_name, _type) \
+extern VOID \
+AdapterGet ## _name ## Interface( \
+ IN PXENVBD_ADAPTER Adapter, \
+ OUT _type _name ## Interface \
);
-extern ULONG
-AdapterSizeofXenvbdAdapter(
- );
+ADAPTER_GET_INTERFACE(Store, PXENBUS_STORE_INTERFACE)
+ADAPTER_GET_INTERFACE(Debug, PXENBUS_DEBUG_INTERFACE)
+ADAPTER_GET_INTERFACE(Evtchn, PXENBUS_EVTCHN_INTERFACE)
+ADAPTER_GET_INTERFACE(Gnttab, PXENBUS_GNTTAB_INTERFACE)
+ADAPTER_GET_INTERFACE(Suspend, PXENBUS_SUSPEND_INTERFACE)
-extern PCHAR
-AdapterEnum(
- __in PXENVBD_ADAPTER Adapter
- );
+#undef ADAPTER_GET_INTERFACE
-// SRB Methods
-extern VOID
-AdapterStartSrb(
- __in PXENVBD_ADAPTER Adapter,
- __in PSCSI_REQUEST_BLOCK Srb
+extern BOOLEAN
+AdapterIsTargetEmulated(
+ IN PXENVBD_ADAPTER Adapter,
+ IN ULONG TargetId
);
extern VOID
AdapterCompleteSrb(
- __in PXENVBD_ADAPTER Adapter,
- __in PSCSI_REQUEST_BLOCK Srb
- );
-
-// StorPort Methods
-extern BOOLEAN
-AdapterResetBus(
- __in PXENVBD_ADAPTER Adapter
- );
-
-extern ULONG
-AdapterFindAdapter(
- __in PXENVBD_ADAPTER Adapter,
- __inout PPORT_CONFIGURATION_INFORMATION ConfigInfo
- );
-
-extern BOOLEAN
-AdapterBuildIo(
- __in PXENVBD_ADAPTER Adapter,
- __in PSCSI_REQUEST_BLOCK Srb
- );
-
-extern BOOLEAN
-AdapterStartIo(
- __in PXENVBD_ADAPTER Adapter,
- __in PSCSI_REQUEST_BLOCK Srb
- );
-
-__checkReturn
-extern NTSTATUS
-AdapterForwardPnp(
- __in PXENVBD_ADAPTER Adapter,
- __in PDEVICE_OBJECT DeviceObject,
- __in PIRP Irp
+ IN PXENVBD_ADAPTER Adapter,
+ IN PSCSI_REQUEST_BLOCK Srb
);
-__checkReturn
extern NTSTATUS
AdapterDispatchPnp(
- __in PXENVBD_ADAPTER Adapter,
- __in PDEVICE_OBJECT DeviceObject,
- __in PIRP Irp
+ IN PXENVBD_ADAPTER Adapter,
+ IN PDEVICE_OBJECT DeviceObject,
+ IN PIRP Irp
);
-__checkReturn
extern NTSTATUS
AdapterDispatchPower(
- __in PXENVBD_ADAPTER Adapter,
- __in PDEVICE_OBJECT DeviceObject,
- __in PIRP Irp
- );
-
-extern PXENBUS_STORE_INTERFACE
-AdapterAcquireStore(
- __in PXENVBD_ADAPTER Adapter
+ IN PXENVBD_ADAPTER Adapter,
+ IN PDEVICE_OBJECT DeviceObject,
+ IN PIRP Irp
);
-extern PXENBUS_EVTCHN_INTERFACE
-AdapterAcquireEvtchn(
- __in PXENVBD_ADAPTER Adapter
- );
-
-extern PXENBUS_GNTTAB_INTERFACE
-AdapterAcquireGnttab(
- __in PXENVBD_ADAPTER Adapter
- );
-
-extern PXENBUS_DEBUG_INTERFACE
-AdapterAcquireDebug(
- __in PXENVBD_ADAPTER Adapter
- );
-
-extern PXENBUS_SUSPEND_INTERFACE
-AdapterAcquireSuspend(
- __in PXENVBD_ADAPTER Adapter
+extern NTSTATUS
+AdapterDriverEntry(
+ IN PUNICODE_STRING RegistryPath,
+ IN PDRIVER_OBJECT DriverObject
);
#endif // _XENVBD_ADAPTER_H
diff --git a/src/xenvbd/blockring.c b/src/xenvbd/blockring.c
index a0ba7c7..bcef877 100644
--- a/src/xenvbd/blockring.c
+++ b/src/xenvbd/blockring.c
@@ -49,7 +49,7 @@ struct _XENVBD_BLOCKRING {
BOOLEAN Connected;
BOOLEAN Enabled;
- PXENBUS_STORE_INTERFACE StoreInterface;
+ XENBUS_STORE_INTERFACE StoreInterface;
KSPIN_LOCK Lock;
PMDL Mdl;
@@ -284,10 +284,10 @@ BlockRingConnect(
ASSERT(BlockRing->Connected == FALSE);
- BlockRing->StoreInterface = AdapterAcquireStore(Adapter);
-
- status = STATUS_UNSUCCESSFUL;
- if (BlockRing->StoreInterface == NULL)
+ AdapterGetStoreInterface(Adapter, &BlockRing->StoreInterface);
+
+ status = XENBUS_STORE(Acquire, &BlockRing->StoreInterface);
+ if (!NT_SUCCESS(status))
goto fail1;
status = FrontendStoreReadBackend(BlockRing->Frontend,
"max-ring-page-order", &Value);
@@ -355,7 +355,7 @@ BlockRingStoreWrite(
if (BlockRing->Order == 0) {
status = XENBUS_STORE(Printf,
- BlockRing->StoreInterface,
+ &BlockRing->StoreInterface,
Transaction,
FrontendPath,
"ring-ref",
@@ -367,7 +367,7 @@ BlockRingStoreWrite(
ULONG Index, RingPages;
status = XENBUS_STORE(Printf,
- BlockRing->StoreInterface,
+ &BlockRing->StoreInterface,
Transaction,
FrontendPath,
"ring-page-order",
@@ -383,7 +383,7 @@ BlockRingStoreWrite(
if (!NT_SUCCESS(status))
return status;
status = XENBUS_STORE(Printf,
- BlockRing->StoreInterface,
+ &BlockRing->StoreInterface,
Transaction,
FrontendPath,
Name,
@@ -395,7 +395,7 @@ BlockRingStoreWrite(
}
status = XENBUS_STORE(Printf,
- BlockRing->StoreInterface,
+ &BlockRing->StoreInterface,
Transaction,
FrontendPath,
"protocol",
@@ -453,8 +453,8 @@ BlockRingDisconnect(
BlockRing->Order = 0;
- XENBUS_STORE(Release, BlockRing->StoreInterface);
- BlockRing->StoreInterface = NULL;
+ XENBUS_STORE(Release, &BlockRing->StoreInterface);
+ RtlZeroMemory(&BlockRing->StoreInterface, sizeof(XENBUS_STORE_INTERFACE));
BlockRing->Connected = FALSE;
}
diff --git a/src/xenvbd/driver.c b/src/xenvbd/driver.c
index 233318f..d45c6b6 100644
--- a/src/xenvbd/driver.c
+++ b/src/xenvbd/driver.c
@@ -59,6 +59,16 @@ static XENVBD_DRIVER Driver;
#define XENVBD_POOL_TAG 'dbvX'
+VOID
+DriverSetAdapter(
+ IN PVOID Adapter
+ )
+{
+ ASSERT3P(Driver.Adapter, ==, NULL);
+ ASSERT3P(Adapter, !=, NULL);
+ Driver.Adapter = Adapter;
+}
+
static FORCEINLINE HANDLE
__DriverGetParametersKey(
VOID
@@ -168,141 +178,6 @@ fail1:
Error("fail1 (%08x)\n", status);
}
-HW_INITIALIZE HwInitialize;
-
-BOOLEAN
-HwInitialize(
- IN PVOID DevExt
- )
-{
- UNREFERENCED_PARAMETER(DevExt);
- return TRUE;
-}
-
-HW_INTERRUPT HwInterrupt;
-
-BOOLEAN
-HwInterrupt(
- IN PVOID DevExt
- )
-{
- UNREFERENCED_PARAMETER(DevExt);
- return TRUE;
-}
-
-HW_ADAPTER_CONTROL HwAdapterControl;
-
-SCSI_ADAPTER_CONTROL_STATUS
-HwAdapterControl(
- IN PVOID DevExt,
- IN SCSI_ADAPTER_CONTROL_TYPE ControlType,
- IN PVOID Parameters
- )
-{
- PSCSI_SUPPORTED_CONTROL_TYPE_LIST List;
-
- UNREFERENCED_PARAMETER(DevExt);
-
- switch (ControlType) {
- case ScsiQuerySupportedControlTypes:
- List = Parameters;
- List->SupportedTypeList[ScsiQuerySupportedControlTypes] = TRUE;
- break;
-
- case ScsiStopAdapter:
- case ScsiRestartAdapter:
- case ScsiSetBootConfig:
- case ScsiSetRunningConfig:
- default:
- break;
- }
- return ScsiAdapterControlSuccess;
-}
-
-HW_RESET_BUS HwResetBus;
-
-BOOLEAN
-HwResetBus(
- IN PVOID DevExt,
- IN ULONG PathId
- )
-{
- UNREFERENCED_PARAMETER(PathId);
-
- return AdapterResetBus(DevExt);
-}
-
-HW_FIND_ADAPTER HwFindAdapter;
-
-ULONG
-HwFindAdapter(
- IN PVOID DevExt,
- IN PVOID Context,
- IN PVOID BusInformation,
- IN PCHAR ArgumentString,
- IN OUT PPORT_CONFIGURATION_INFORMATION ConfigInfo,
- OUT PBOOLEAN Again
- )
-{
- ULONG Return;
-
- UNREFERENCED_PARAMETER(Context);
- UNREFERENCED_PARAMETER(BusInformation);
- UNREFERENCED_PARAMETER(ArgumentString);
- UNREFERENCED_PARAMETER(Again);
-
- Return = AdapterFindAdapter(DevExt, ConfigInfo);
- if (Return == SP_RETURN_FOUND)
- Driver.Adapter = DevExt;
- return Return;
-}
-
-static FORCEINLINE BOOLEAN
-__FailStorageRequest(
- IN PVOID DevExt,
- IN PSCSI_REQUEST_BLOCK Srb
- )
-{
- if (Srb->Function == SRB_FUNCTION_STORAGE_REQUEST_BLOCK) {
- // Win8 and above storport request. not supported
- // complete the request (with fail code)
- Srb->SrbStatus = SRB_STATUS_INVALID_REQUEST;
- StorPortNotification(RequestComplete, DevExt, Srb);
- Error("(0x%p) STORAGE_REQUEST_BLOCK not supported\n", DevExt);
- return TRUE;
- }
-
- return FALSE;
-}
-
-HW_BUILDIO HwBuildIo;
-
-BOOLEAN
-HwBuildIo(
- IN PVOID DevExt,
- IN PSCSI_REQUEST_BLOCK Srb
- )
-{
- if (__FailStorageRequest(DevExt, Srb))
- return FALSE; // dont pass to HwStartIo
-
- return AdapterBuildIo(DevExt, Srb);
-}
-
-HW_STARTIO HwStartIo;
-
-BOOLEAN
-HwStartIo(
- IN PVOID DevExt,
- IN PSCSI_REQUEST_BLOCK Srb
- )
-{
- if (__FailStorageRequest(DevExt, Srb))
- return TRUE; // acknowledge the srb
-
- return AdapterStartIo(DevExt, Srb);
-}
-
__drv_dispatchType(IRP_MJ_PNP)
DRIVER_DISPATCH DispatchPnp;
@@ -315,10 +190,7 @@ DispatchPnp(
if (Driver.Adapter == NULL)
return DriverDispatchPnp(DeviceObject, Irp);
- if (AdapterGetDeviceObject(Driver.Adapter) == DeviceObject)
- return AdapterDispatchPnp(Driver.Adapter, DeviceObject, Irp);
-
- return AdapterForwardPnp(Driver.Adapter, DeviceObject, Irp);
+ return AdapterDispatchPnp(Driver.Adapter, DeviceObject, Irp);
}
__drv_dispatchType(IRP_MJ_POWER)
@@ -333,10 +205,7 @@ DispatchPower(
if (Driver.Adapter == NULL)
return DriverDispatchPower(DeviceObject, Irp);
- if (AdapterGetDeviceObject(Driver.Adapter) == DeviceObject)
- return AdapterDispatchPower(Driver.Adapter, DeviceObject, Irp);
-
- return DriverDispatchPower(DeviceObject, Irp);
+ return AdapterDispatchPower(Driver.Adapter, DeviceObject, Irp);
}
DRIVER_UNLOAD DriverUnload;
@@ -378,7 +247,6 @@ DriverEntry(
IN PUNICODE_STRING RegistryPath
)
{
- HW_INITIALIZATION_DATA InitData;
HANDLE ServiceKey;
HANDLE ParametersKey;
NTSTATUS status;
@@ -418,33 +286,8 @@ DriverEntry(
Driver.Adapter = NULL;
BufferInitialize();
- RtlZeroMemory(&InitData, sizeof(InitData));
- InitData.HwInitializationDataSize = sizeof(InitData);
- InitData.AdapterInterfaceType = Internal;
- InitData.HwInitialize = HwInitialize;
- InitData.HwStartIo = HwStartIo;
- InitData.HwInterrupt = HwInterrupt;
-#pragma warning(suppress : 4152)
- InitData.HwFindAdapter = HwFindAdapter;
- InitData.HwResetBus = HwResetBus;
- InitData.HwDmaStarted = NULL;
- InitData.HwAdapterState = NULL;
- InitData.DeviceExtensionSize = AdapterSizeofXenvbdAdapter();
- InitData.SpecificLuExtensionSize = sizeof(ULONG); // not actually used
- InitData.SrbExtensionSize = sizeof(XENVBD_SRBEXT);
- InitData.NumberOfAccessRanges = 2;
- InitData.MapBuffers = STOR_MAP_NON_READ_WRITE_BUFFERS;
- InitData.NeedPhysicalAddresses = TRUE;
- InitData.TaggedQueuing = TRUE;
- InitData.AutoRequestSense = TRUE;
- InitData.MultipleRequestPerLu = TRUE;
- InitData.HwAdapterControl = HwAdapterControl;
- InitData.HwBuildIo = HwBuildIo;
-
- status = StorPortInitialize(DriverObject,
- RegistryPath,
- &InitData,
- NULL);
+ status = AdapterDriverEntry(RegistryPath,
+ DriverObject);
if (!NT_SUCCESS(status))
goto fail4;
diff --git a/src/xenvbd/driver.h b/src/xenvbd/driver.h
index 13c6135..6b73c4d 100644
--- a/src/xenvbd/driver.h
+++ b/src/xenvbd/driver.h
@@ -39,6 +39,11 @@
#define XENVBD_MAX_TRANSFER_LENGTH (XENVBD_MAX_PAGES_PER_SRB * PAGE_SIZE)
#define XENVBD_MAX_PHYSICAL_BREAKS (XENVBD_MAX_PAGES_PER_SRB - 1)
+extern VOID
+DriverSetAdapter(
+ IN PVOID Adapter
+ );
+
extern HANDLE
DriverGetParametersKey(
VOID
diff --git a/src/xenvbd/frontend.c b/src/xenvbd/frontend.c
index 150710d..d82eaa2 100644
--- a/src/xenvbd/frontend.c
+++ b/src/xenvbd/frontend.c
@@ -66,8 +66,8 @@ struct _XENVBD_FRONTEND {
PVOID Inquiry;
// Interfaces to XenBus
- PXENBUS_STORE_INTERFACE Store;
- PXENBUS_SUSPEND_INTERFACE Suspend;
+ XENBUS_STORE_INTERFACE StoreInterface;
+ XENBUS_SUSPEND_INTERFACE SuspendInterface;
PXENBUS_SUSPEND_CALLBACK SuspendLateCallback;
@@ -181,6 +181,13 @@ FrontendGetTargetId(
{
return Frontend->TargetId;
}
+ULONG
+FrontendGetDeviceId(
+ __in PXENVBD_FRONTEND Frontend
+ )
+{
+ return Frontend->DeviceId;
+}
PVOID
FrontendGetInquiry(
__in PXENVBD_FRONTEND Frontend
@@ -225,7 +232,7 @@ FrontendStoreWriteFrontend(
)
{
return XENBUS_STORE(Printf,
- Frontend->Store,
+ &Frontend->StoreInterface,
NULL,
Frontend->FrontendPath,
Name,
@@ -241,24 +248,20 @@ FrontendStoreReadBackend(
NTSTATUS Status;
Status = STATUS_INVALID_PARAMETER;
- if (Frontend->Store == NULL)
- goto fail1;
-
if (Frontend->BackendPath == NULL)
- goto fail2;
+ goto fail1;
Status = XENBUS_STORE(Read,
- Frontend->Store,
+ &Frontend->StoreInterface,
NULL,
Frontend->BackendPath,
Name,
Value);
if (!NT_SUCCESS(Status))
- goto fail3;
+ goto fail2;
return STATUS_SUCCESS;
-fail3:
fail2:
fail1:
return Status;
@@ -270,7 +273,7 @@ FrontendStoreFree(
)
{
XENBUS_STORE(Free,
- Frontend->Store,
+ &Frontend->StoreInterface,
Value);
}
__drv_maxIRQL(DISPATCH_LEVEL)
@@ -282,7 +285,7 @@ FrontendWriteUsage(
NTSTATUS Status;
Status = XENBUS_STORE(Printf,
- Frontend->Store,
+ &Frontend->StoreInterface,
NULL,
Frontend->TargetPath,
"paging",
@@ -292,7 +295,7 @@ FrontendWriteUsage(
goto out;
Status = XENBUS_STORE(Printf,
- Frontend->Store,
+ &Frontend->StoreInterface,
NULL,
Frontend->TargetPath,
"hibernation",
@@ -302,7 +305,7 @@ FrontendWriteUsage(
goto out;
Status = XENBUS_STORE(Printf,
- Frontend->Store,
+ &Frontend->StoreInterface,
NULL,
Frontend->TargetPath,
"dump",
@@ -343,7 +346,7 @@ __UpdateBackendPath(
ULONG Length;
Status = XENBUS_STORE(Read,
- Frontend->Store,
+ &Frontend->StoreInterface,
NULL,
Frontend->FrontendPath,
"backend-id",
@@ -351,14 +354,14 @@ __UpdateBackendPath(
if (NT_SUCCESS(Status)) {
Frontend->BackendId = (USHORT)strtoul(Value, NULL, 10);
XENBUS_STORE(Free,
- Frontend->Store,
+ &Frontend->StoreInterface,
Value);
} else {
Frontend->BackendId = 0;
}
Status = XENBUS_STORE(Read,
- Frontend->Store,
+ &Frontend->StoreInterface,
NULL,
Frontend->FrontendPath,
"backend",
@@ -379,7 +382,7 @@ __UpdateBackendPath(
}
XENBUS_STORE(Free,
- Frontend->Store,
+ &Frontend->StoreInterface,
Value);
} else {
Warning("Failed to read \'backend\' from \'%s\' (%08x)\n",
@@ -401,7 +404,7 @@ __ReadState(
PCHAR Buffer;
Status = XENBUS_STORE(Read,
- Frontend->Store,
+ &Frontend->StoreInterface,
Transaction,
Path,
"state",
@@ -411,7 +414,7 @@ __ReadState(
*State = (XenbusState)strtoul(Buffer, NULL, 10);
XENBUS_STORE(Free,
- Frontend->Store,
+ &Frontend->StoreInterface,
Buffer);
return STATUS_SUCCESS;
@@ -442,7 +445,7 @@ __WaitState(
ASSERT3P(Frontend->BackendPath, !=, NULL);
Status = XENBUS_STORE(WatchAdd,
- Frontend->Store,
+ &Frontend->StoreInterface,
Frontend->BackendPath,
"state",
&Event,
@@ -458,7 +461,7 @@ __WaitState(
if (KeWaitForSingleObject(&Event, Executive, KernelMode,
FALSE, &Timeout) == STATUS_TIMEOUT) {
XENBUS_STORE(Poll,
- Frontend->Store);
+ &Frontend->StoreInterface);
KeQuerySystemTime(&CurrentTime);
if ((CurrentTime.QuadPart - StartTime.QuadPart) > 10000) {
@@ -477,7 +480,7 @@ __WaitState(
}
XENBUS_STORE(WatchRemove,
- Frontend->Store,
+ &Frontend->StoreInterface,
Watch);
Trace("Target[%d] : BACKEND_STATE -> %s\n",
@@ -490,7 +493,7 @@ fail2:
Error("Fail2\n");
XENBUS_STORE(WatchRemove,
- Frontend->Store,
+ &Frontend->StoreInterface,
Watch);
fail1:
Error("Fail1 (%08x)\n", Status);
@@ -507,7 +510,7 @@ ___SetState(
NTSTATUS Status;
Status = XENBUS_STORE(Printf,
- Frontend->Store,
+ &Frontend->StoreInterface,
NULL,
Frontend->FrontendPath,
"state",
@@ -535,8 +538,6 @@ __CheckBackendForEject(
ULONG Attempt;
NTSTATUS Status;
- if (Frontend->Store == NULL)
- return;
if (Frontend->FrontendPath == NULL)
return;
if (Frontend->BackendPath == NULL)
@@ -552,7 +553,7 @@ __CheckBackendForEject(
PCHAR Buffer;
Status = XENBUS_STORE(TransactionStart,
- Frontend->Store,
+ &Frontend->StoreInterface,
&Transaction);
if (!NT_SUCCESS(Status))
break;
@@ -572,7 +573,7 @@ __CheckBackendForEject(
goto abort;
Status = XENBUS_STORE(Read,
- Frontend->Store,
+ &Frontend->StoreInterface,
Transaction,
Frontend->BackendPath,
"online",
@@ -582,11 +583,11 @@ __CheckBackendForEject(
Online = (BOOLEAN)strtol(Buffer, NULL, 2);
XENBUS_STORE(Free,
- Frontend->Store,
+ &Frontend->StoreInterface,
Buffer);
Status = XENBUS_STORE(TransactionEnd,
- Frontend->Store,
+ &Frontend->StoreInterface,
Transaction,
TRUE);
if (Status != STATUS_RETRY || ++Attempt > 10)
@@ -596,7 +597,7 @@ __CheckBackendForEject(
abort:
(VOID) XENBUS_STORE(TransactionEnd,
- Frontend->Store,
+ &Frontend->StoreInterface,
Transaction,
FALSE);
break;
@@ -626,7 +627,7 @@ FrontendReadFeature(
BOOLEAN Old = *Value;
status = XENBUS_STORE(Read,
- Frontend->Store,
+ &Frontend->StoreInterface,
NULL,
Frontend->BackendPath,
Name,
@@ -636,7 +637,7 @@ FrontendReadFeature(
*Value = !!(strtoul(Buffer, NULL, 10));
XENBUS_STORE(Free,
- Frontend->Store,
+ &Frontend->StoreInterface,
Buffer);
// check registry for disable-override
@@ -665,7 +666,7 @@ FrontendReadValue32(
ULONG Old = *Value;
status = XENBUS_STORE(Read,
- Frontend->Store,
+ &Frontend->StoreInterface,
NULL,
Frontend->BackendPath,
Name,
@@ -675,7 +676,7 @@ FrontendReadValue32(
*Value = strtoul(Buffer, NULL, 10);
XENBUS_STORE(Free,
- Frontend->Store,
+ &Frontend->StoreInterface,
Buffer);
// check registry for disable-override
@@ -703,7 +704,7 @@ FrontendReadValue64(
ULONG64 Old = *Value;
status = XENBUS_STORE(Read,
- Frontend->Store,
+ &Frontend->StoreInterface,
NULL,
Frontend->BackendPath,
Name,
@@ -713,7 +714,7 @@ FrontendReadValue64(
*Value = _strtoui64(Buffer, NULL, 10);
XENBUS_STORE(Free,
- Frontend->Store,
+ &Frontend->StoreInterface,
Buffer);
return Old != *Value;
@@ -896,7 +897,7 @@ FrontendClose(
// unwatch backend (null check for initial close operation)
if (Frontend->BackendWatch)
XENBUS_STORE(WatchRemove,
- Frontend->Store,
+ &Frontend->StoreInterface,
Frontend->BackendWatch);
Frontend->BackendWatch = NULL;
@@ -964,7 +965,7 @@ FrontendPrepare(
// watch backend (4 paths needed)
Status = XENBUS_STORE(WatchAdd,
- Frontend->Store,
+ &Frontend->StoreInterface,
NULL,
Frontend->BackendPath,
ThreadGetEvent(Frontend->BackendThread),
@@ -978,7 +979,7 @@ FrontendPrepare(
goto fail3;
Status = XENBUS_STORE(Printf,
- Frontend->Store,
+ &Frontend->StoreInterface,
NULL,
Frontend->TargetPath,
"frontend",
@@ -988,7 +989,7 @@ FrontendPrepare(
goto fail4;
Status = XENBUS_STORE(Printf,
- Frontend->Store,
+ &Frontend->StoreInterface,
NULL,
Frontend->TargetPath,
"device",
@@ -1042,7 +1043,7 @@ fail4:
fail3:
Error("Fail3\n");
(VOID) XENBUS_STORE(WatchRemove,
- Frontend->Store,
+ &Frontend->StoreInterface,
Frontend->BackendWatch);
Frontend->BackendWatch = NULL;
fail2:
@@ -1078,7 +1079,7 @@ FrontendConnect(
PXENBUS_STORE_TRANSACTION Transaction;
Status = XENBUS_STORE(TransactionStart,
- Frontend->Store,
+ &Frontend->StoreInterface,
&Transaction);
if (!NT_SUCCESS(Status))
break;
@@ -1096,7 +1097,7 @@ FrontendConnect(
goto abort;
Status = XENBUS_STORE(Printf,
- Frontend->Store,
+ &Frontend->StoreInterface,
Transaction,
Frontend->FrontendPath,
"target-id",
@@ -1106,7 +1107,7 @@ FrontendConnect(
goto abort;
Status = XENBUS_STORE(Printf,
- Frontend->Store,
+ &Frontend->StoreInterface,
Transaction,
Frontend->FrontendPath,
"feature-surprise-remove",
@@ -1116,7 +1117,7 @@ FrontendConnect(
goto abort;
Status = XENBUS_STORE(Printf,
- Frontend->Store,
+ &Frontend->StoreInterface,
Transaction,
Frontend->FrontendPath,
"feature-online-resize",
@@ -1126,7 +1127,7 @@ FrontendConnect(
goto abort;
Status = XENBUS_STORE(TransactionEnd,
- Frontend->Store,
+ &Frontend->StoreInterface,
Transaction,
TRUE);
if (Status == STATUS_RETRY)
@@ -1136,7 +1137,7 @@ FrontendConnect(
abort:
(VOID) XENBUS_STORE(TransactionEnd,
- Frontend->Store,
+ &Frontend->StoreInterface,
Transaction,
FALSE);
break;
@@ -1436,28 +1437,28 @@ FrontendD3ToD0(
__in PXENVBD_FRONTEND Frontend
)
{
+ PXENVBD_ADAPTER Adapter = TargetGetAdapter(Frontend->Target);
NTSTATUS Status;
KIRQL Irql;
KeAcquireSpinLock(&Frontend->StateLock, &Irql);
// acquire interfaces
- Frontend->Store =
AdapterAcquireStore(TargetGetAdapter(Frontend->Target));
+ AdapterGetStoreInterface(Adapter, &Frontend->StoreInterface);
+ AdapterGetSuspendInterface(Adapter, &Frontend->SuspendInterface);
- Status = STATUS_UNSUCCESSFUL;
- if (Frontend->Store == NULL)
+ Status = XENBUS_STORE(Acquire, &Frontend->StoreInterface);
+ if (!NT_SUCCESS(Status))
goto fail1;
- Frontend->Suspend =
AdapterAcquireSuspend(TargetGetAdapter(Frontend->Target));
-
- Status = STATUS_UNSUCCESSFUL;
- if (Frontend->Suspend == NULL)
+ Status = XENBUS_SUSPEND(Acquire, &Frontend->SuspendInterface);
+ if (!NT_SUCCESS(Status))
goto fail2;
// register suspend callback
ASSERT3P(Frontend->SuspendLateCallback, ==, NULL);
Status = XENBUS_SUSPEND(Register,
- Frontend->Suspend,
+ &Frontend->SuspendInterface,
SUSPEND_CALLBACK_LATE,
FrontendSuspendLateCallback,
Frontend,
@@ -1474,14 +1475,14 @@ FrontendD3ToD0(
fail3:
Error("Fail3\n");
- XENBUS_SUSPEND(Release, Frontend->Suspend);
- Frontend->Suspend = NULL;
+ XENBUS_SUSPEND(Release, &Frontend->SuspendInterface);
+ RtlZeroMemory(&Frontend->SuspendInterface,
sizeof(XENBUS_SUSPEND_INTERFACE));
fail2:
Error("Fail2\n");
- XENBUS_STORE(Release, Frontend->Store);
- Frontend->Store = NULL;
+ XENBUS_STORE(Release, &Frontend->StoreInterface);
+ RtlZeroMemory(&Frontend->StoreInterface, sizeof(XENBUS_STORE_INTERFACE));
fail1:
Error("Fail1 (%08x)\n", Status);
@@ -1506,7 +1507,7 @@ FrontendD0ToD3(
// deregister suspend callback
if (Frontend->SuspendLateCallback != NULL) {
XENBUS_SUSPEND(Deregister,
- Frontend->Suspend,
+ &Frontend->SuspendInterface,
Frontend->SuspendLateCallback);
Frontend->SuspendLateCallback = NULL;
}
@@ -1517,11 +1518,11 @@ FrontendD0ToD3(
}
// release interfaces
- XENBUS_SUSPEND(Release, Frontend->Suspend);
- Frontend->Suspend = NULL;
+ XENBUS_SUSPEND(Release, &Frontend->SuspendInterface);
+ RtlZeroMemory(&Frontend->SuspendInterface,
sizeof(XENBUS_SUSPEND_INTERFACE));
- XENBUS_STORE(Release, Frontend->Store);
- Frontend->Store = NULL;
+ XENBUS_STORE(Release, &Frontend->StoreInterface);
+ RtlZeroMemory(&Frontend->StoreInterface, sizeof(XENBUS_STORE_INTERFACE));
KeReleaseSpinLock(&Frontend->StateLock, Irql);
}
diff --git a/src/xenvbd/frontend.h b/src/xenvbd/frontend.h
index 69dd13b..f466ef8 100644
--- a/src/xenvbd/frontend.h
+++ b/src/xenvbd/frontend.h
@@ -96,6 +96,10 @@ extern ULONG
FrontendGetTargetId(
__in PXENVBD_FRONTEND Frontend
);
+extern ULONG
+FrontendGetDeviceId(
+ __in PXENVBD_FRONTEND Frontend
+ );
extern PVOID
FrontendGetInquiry(
__in PXENVBD_FRONTEND Frontend
diff --git a/src/xenvbd/granter.c b/src/xenvbd/granter.c
index bd0fa5b..57b7df8 100644
--- a/src/xenvbd/granter.c
+++ b/src/xenvbd/granter.c
@@ -42,7 +42,7 @@ struct _XENVBD_GRANTER {
BOOLEAN Connected;
BOOLEAN Enabled;
- PXENBUS_GNTTAB_INTERFACE GnttabInterface;
+ XENBUS_GNTTAB_INTERFACE GnttabInterface;
PXENBUS_GNTTAB_CACHE Cache;
KSPIN_LOCK Lock;
@@ -145,10 +145,10 @@ GranterConnect(
ASSERT(Granter->Connected == FALSE);
- Granter->GnttabInterface = AdapterAcquireGnttab(Adapter);
+ AdapterGetGnttabInterface(Adapter, &Granter->GnttabInterface);
- status = STATUS_UNSUCCESSFUL;
- if (Granter->GnttabInterface == NULL)
+ status = XENBUS_GNTTAB(Acquire, &Granter->GnttabInterface);
+ if (!NT_SUCCESS(status))
goto fail1;
Granter->BackendDomain = BackendDomain;
@@ -161,7 +161,7 @@ GranterConnect(
goto fail2;
status = XENBUS_GNTTAB(CreateCache,
- Granter->GnttabInterface,
+ &Granter->GnttabInterface,
Name,
0,
GranterAcquireLock,
@@ -177,8 +177,8 @@ GranterConnect(
fail3:
fail2:
Granter->BackendDomain = 0;
- XENBUS_GNTTAB(Release, Granter->GnttabInterface);
- Granter->GnttabInterface = NULL;
+ XENBUS_GNTTAB(Release, &Granter->GnttabInterface);
+ RtlZeroMemory(&Granter->GnttabInterface, sizeof(XENBUS_GNTTAB_INTERFACE));
fail1:
return status;
}
@@ -228,12 +228,12 @@ GranterDisconnect(
Granter->Maximum = 0;
XENBUS_GNTTAB(DestroyCache,
- Granter->GnttabInterface,
+ &Granter->GnttabInterface,
Granter->Cache);
Granter->Cache = NULL;
- XENBUS_GNTTAB(Release, Granter->GnttabInterface);
- Granter->GnttabInterface = NULL;
+ XENBUS_GNTTAB(Release, &Granter->GnttabInterface);
+ RtlZeroMemory(&Granter->GnttabInterface, sizeof(XENBUS_GNTTAB_INTERFACE));
Granter->BackendDomain = 0;
Granter->Connected = FALSE;
@@ -273,7 +273,7 @@ GranterGet(
goto fail1;
status = XENBUS_GNTTAB(PermitForeignAccess,
- Granter->GnttabInterface,
+ &Granter->GnttabInterface,
Granter->Cache,
FALSE,
Granter->BackendDomain,
@@ -308,7 +308,7 @@ GranterPut(
return;
status = XENBUS_GNTTAB(RevokeForeignAccess,
- Granter->GnttabInterface,
+ &Granter->GnttabInterface,
Granter->Cache,
FALSE,
Entry);
@@ -329,6 +329,6 @@ GranterReference(
return 0;
return XENBUS_GNTTAB(GetReference,
- Granter->GnttabInterface,
+ &Granter->GnttabInterface,
Entry);
}
diff --git a/src/xenvbd/notifier.c b/src/xenvbd/notifier.c
index 4835a46..1e0c057 100644
--- a/src/xenvbd/notifier.c
+++ b/src/xenvbd/notifier.c
@@ -42,8 +42,8 @@ struct _XENVBD_NOTIFIER {
BOOLEAN Connected;
BOOLEAN Enabled;
- PXENBUS_STORE_INTERFACE StoreInterface;
- PXENBUS_EVTCHN_INTERFACE EvtchnInterface;
+ XENBUS_STORE_INTERFACE StoreInterface;
+ XENBUS_EVTCHN_INTERFACE EvtchnInterface;
PXENBUS_EVTCHN_CHANNEL Channel;
ULONG Port;
@@ -119,7 +119,7 @@ NotifierDpc(
FrontendNotifyResponses(Notifier->Frontend);
XENBUS_EVTCHN(Unmask,
- Notifier->EvtchnInterface,
+ &Notifier->EvtchnInterface,
Notifier->Channel,
FALSE);
}
@@ -167,20 +167,19 @@ NotifierConnect(
ASSERT(Notifier->Connected == FALSE);
- Notifier->StoreInterface = AdapterAcquireStore(Adapter);
+ AdapterGetStoreInterface(Adapter, &Notifier->StoreInterface);
+ AdapterGetEvtchnInterface(Adapter, &Notifier->EvtchnInterface);
- status = STATUS_UNSUCCESSFUL;
- if (Notifier->StoreInterface == NULL)
+ status = XENBUS_STORE(Acquire, &Notifier->StoreInterface);
+ if (!NT_SUCCESS(status))
goto fail1;
- Notifier->EvtchnInterface = AdapterAcquireEvtchn(Adapter);
-
- status = STATUS_UNSUCCESSFUL;
- if (Notifier->EvtchnInterface == NULL)
+ status = XENBUS_EVTCHN(Acquire, &Notifier->EvtchnInterface);
+ if (!NT_SUCCESS(status))
goto fail2;
Notifier->Channel = XENBUS_EVTCHN(Open,
- Notifier->EvtchnInterface,
+ &Notifier->EvtchnInterface,
XENBUS_EVTCHN_TYPE_UNBOUND,
NotifierInterrupt,
Notifier,
@@ -192,11 +191,11 @@ NotifierConnect(
goto fail3;
Notifier->Port = XENBUS_EVTCHN(GetPort,
- Notifier->EvtchnInterface,
+ &Notifier->EvtchnInterface,
Notifier->Channel);
XENBUS_EVTCHN(Unmask,
- Notifier->EvtchnInterface,
+ &Notifier->EvtchnInterface,
Notifier->Channel,
FALSE);
@@ -204,12 +203,12 @@ NotifierConnect(
return STATUS_SUCCESS;
fail3:
- XENBUS_EVTCHN(Release, Notifier->EvtchnInterface);
- Notifier->EvtchnInterface = NULL;
+ XENBUS_EVTCHN(Release, &Notifier->EvtchnInterface);
+ RtlZeroMemory(&Notifier->EvtchnInterface, sizeof(XENBUS_EVTCHN_INTERFACE));
fail2:
- XENBUS_STORE(Release, Notifier->StoreInterface);
- Notifier->StoreInterface = NULL;
+ XENBUS_STORE(Release, &Notifier->StoreInterface);
+ RtlZeroMemory(&Notifier->StoreInterface, sizeof(XENBUS_STORE_INTERFACE));
fail1:
return status;
@@ -223,7 +222,7 @@ NotifierStoreWrite(
)
{
return XENBUS_STORE(Printf,
- Notifier->StoreInterface,
+ &Notifier->StoreInterface,
Transaction,
FrontendPath,
"event-channel",
@@ -239,7 +238,7 @@ NotifierEnable(
ASSERT(Notifier->Enabled == FALSE);
XENBUS_EVTCHN(Trigger,
- Notifier->EvtchnInterface,
+ &Notifier->EvtchnInterface,
Notifier->Channel);
Notifier->Enabled = TRUE;
@@ -263,16 +262,16 @@ NotifierDisconnect(
ASSERT(Notifier->Connected == TRUE);
XENBUS_EVTCHN(Close,
- Notifier->EvtchnInterface,
+ &Notifier->EvtchnInterface,
Notifier->Channel);
Notifier->Channel = NULL;
Notifier->Port = 0;
- XENBUS_EVTCHN(Release, Notifier->EvtchnInterface);
- Notifier->EvtchnInterface = NULL;
+ XENBUS_EVTCHN(Release, &Notifier->EvtchnInterface);
+ RtlZeroMemory(&Notifier->EvtchnInterface, sizeof(XENBUS_EVTCHN_INTERFACE));
- XENBUS_STORE(Release, Notifier->StoreInterface);
- Notifier->StoreInterface = NULL;
+ XENBUS_STORE(Release, &Notifier->StoreInterface);
+ RtlZeroMemory(&Notifier->StoreInterface, sizeof(XENBUS_STORE_INTERFACE));
Notifier->NumInts = Notifier->NumDpcs = 0;
@@ -318,7 +317,7 @@ NotifierTrigger(
{
if (Notifier->Enabled)
XENBUS_EVTCHN(Trigger,
- Notifier->EvtchnInterface,
+ &Notifier->EvtchnInterface,
Notifier->Channel);
}
@@ -329,7 +328,7 @@ NotifierSend(
{
if (Notifier->Enabled)
XENBUS_EVTCHN(Send,
- Notifier->EvtchnInterface,
+ &Notifier->EvtchnInterface,
Notifier->Channel);
}
diff --git a/src/xenvbd/pdoinquiry.c b/src/xenvbd/pdoinquiry.c
index c1ca3cb..2608fbf 100644
--- a/src/xenvbd/pdoinquiry.c
+++ b/src/xenvbd/pdoinquiry.c
@@ -211,7 +211,6 @@ fail1:
static FORCEINLINE BOOLEAN
__HandlePageStd(
- __in XENVBD_DEVICE_TYPE DeviceType,
__in PSCSI_REQUEST_BLOCK Srb
)
{
@@ -221,35 +220,15 @@ __HandlePageStd(
if (Length < INQUIRYDATABUFFERSIZE)
return FALSE;
- switch (DeviceType) {
- case XENVBD_DEVICE_TYPE_DISK:
- Data->DeviceType = DIRECT_ACCESS_DEVICE;
- Data->DeviceTypeQualifier = DEVICE_CONNECTED;
- Data->Versions = 4;
- Data->ResponseDataFormat = 2;
- Data->AdditionalLength = INQUIRYDATABUFFERSIZE - 4;
- Data->CommandQueue = 1;
- RtlCopyMemory(Data->VendorId, "XENSRC ", 8);
- RtlCopyMemory(Data->ProductId, "PVDISK ", 16);
- RtlCopyMemory(Data->ProductRevisionLevel, "2.0 ", 4);
- break;
- case XENVBD_DEVICE_TYPE_CDROM:
- Data->DeviceType = READ_ONLY_DIRECT_ACCESS_DEVICE;
- Data->DeviceTypeQualifier = DEVICE_CONNECTED;
- Data->RemovableMedia = TRUE;
- Data->Versions = 2;
- Data->ResponseDataFormat = 2;
- Data->Wide32Bit = TRUE;
- Data->Synchronous = TRUE;
- Data->AdditionalLength = INQUIRYDATABUFFERSIZE - 4;
- RtlCopyMemory(Data->VendorId, "XENSRC ", 8);
- RtlCopyMemory(Data->ProductId, "PVCDROM ", 16);
- RtlCopyMemory(Data->ProductRevisionLevel, "2.0 ", 4);
- break;
- default:
- return FALSE;
- break;
- }
+ Data->DeviceType = DIRECT_ACCESS_DEVICE;
+ Data->DeviceTypeQualifier = DEVICE_CONNECTED;
+ Data->Versions = 4;
+ Data->ResponseDataFormat = 2;
+ Data->AdditionalLength = INQUIRYDATABUFFERSIZE - 4;
+ Data->CommandQueue = 1;
+ RtlCopyMemory(Data->VendorId, "XENSRC ", 8);
+ RtlCopyMemory(Data->ProductId, "PVDISK ", 16);
+ RtlCopyMemory(Data->ProductRevisionLevel, "2.0 ", 4);
Srb->DataTransferLength = INQUIRYDATABUFFERSIZE;
return TRUE;
@@ -518,8 +497,7 @@ VOID
PdoInquiry(
__in ULONG TargetId,
__in PVOID Inquiry,
- __in PSCSI_REQUEST_BLOCK Srb,
- __in XENVBD_DEVICE_TYPE DeviceType
+ __in PSCSI_REQUEST_BLOCK Srb
)
{
BOOLEAN Success;
@@ -536,7 +514,7 @@ PdoInquiry(
}
} else {
switch (PageCode) {
- case 0x00: Success = __HandlePageStd(DeviceType, Srb); break;
+ case 0x00: Success = __HandlePageStd(Srb); break;
default: Success = FALSE; break;
}
}
diff --git a/src/xenvbd/pdoinquiry.h b/src/xenvbd/pdoinquiry.h
index 41d7c30..a8cb155 100644
--- a/src/xenvbd/pdoinquiry.h
+++ b/src/xenvbd/pdoinquiry.h
@@ -57,8 +57,7 @@ extern VOID
PdoInquiry(
__in ULONG TargetId,
__in PVOID Inquiry,
- __in PSCSI_REQUEST_BLOCK Srb,
- __in XENVBD_DEVICE_TYPE DeviceType
+ __in PSCSI_REQUEST_BLOCK Srb
);
#endif // _XENVBD_PDO_INQUIRY_H
diff --git a/src/xenvbd/target.c b/src/xenvbd/target.c
index 2a48f0a..5764292 100644
--- a/src/xenvbd/target.c
+++ b/src/xenvbd/target.c
@@ -47,6 +47,7 @@
#include <gnttab_interface.h>
#include <debug_interface.h>
#include <suspend_interface.h>
+#include <stdlib.h>
#define XENVBD_MAX_QUEUE_DEPTH (254)
@@ -77,8 +78,6 @@ struct _XENVBD_TARGET {
ULONG Signature;
PXENVBD_ADAPTER Adapter;
PDEVICE_OBJECT DeviceObject;
- KEVENT RemoveEvent;
- LONG ReferenceCount;
DEVICE_PNP_STATE DevicePnpState;
DEVICE_PNP_STATE PrevPnpState;
DEVICE_POWER_STATE DevicePowerState;
@@ -86,7 +85,6 @@ struct _XENVBD_TARGET {
// Frontend (Ring, includes XenBus interfaces)
PXENVBD_FRONTEND Frontend;
- XENVBD_DEVICE_TYPE DeviceType;
// State
LONG Paused;
@@ -274,9 +272,6 @@ TargetDebugCallback(
Target->Adapter,
Target->DeviceObject);
XENBUS_DEBUG(Printf, DebugInterface,
- "TARGET: ReferenceCount %d\n",
- Target->ReferenceCount);
- XENBUS_DEBUG(Printf, DebugInterface,
"TARGET: DevicePnpState %s (%s)\n",
__PnpStateName(Target->DevicePnpState),
__PnpStateName(Target->PrevPnpState));
@@ -438,57 +433,23 @@ __TargetRestoreDevicePnpState(
}
//=============================================================================
-// Reference Counting
-FORCEINLINE LONG
-__TargetReference(
- __in PXENVBD_TARGET Target,
- __in PCHAR Caller
- )
-{
- LONG Result;
-
- ASSERT3P(Target, !=, NULL);
- Result = InterlockedIncrement(&Target->ReferenceCount);
- ASSERTREFCOUNT(Result, >, 0, Caller);
-
- if (Result == 1) {
- Result = InterlockedDecrement(&Target->ReferenceCount);
- Error("Target[%d] : %s: Attempting to take reference of removed TARGET
from %d\n", TargetGetTargetId(Target), Caller, Result);
- return 0;
- } else {
- ASSERTREFCOUNT(Result, >, 1, Caller);
- return Result;
- }
-}
-
-FORCEINLINE LONG
-__TargetDereference(
- __in PXENVBD_TARGET Target,
- __in PCHAR Caller
+// Query Methods
+FORCEINLINE ULONG
+TargetGetTargetId(
+ __in PXENVBD_TARGET Target
)
{
- LONG Result;
-
ASSERT3P(Target, !=, NULL);
- Result = InterlockedDecrement(&Target->ReferenceCount);
- ASSERTREFCOUNT(Result, >=, 0, Caller);
-
- if (Result == 0) {
- Verbose("Final ReferenceCount dropped, Target[%d] able to be
removed\n", TargetGetTargetId(Target));
- KeSetEvent(&Target->RemoveEvent, IO_NO_INCREMENT, FALSE);
- }
- return Result;
+ return FrontendGetTargetId(Target->Frontend);
}
-//=============================================================================
-// Query Methods
-FORCEINLINE ULONG
-TargetGetTargetId(
+ULONG
+TargetGetDeviceId(
__in PXENVBD_TARGET Target
)
{
ASSERT3P(Target, !=, NULL);
- return FrontendGetTargetId(Target->Frontend);
+ return FrontendGetDeviceId(Target->Frontend);
}
__checkReturn
@@ -835,8 +796,6 @@ __TargetPriority(
return HighPagePriority;
}
-#define __min(_x, _y) ((_x) < (_y)) ? (_x) : (_y)
-
static FORCEINLINE VOID
SGListGet(
IN OUT PXENVBD_SG_LIST SGList
@@ -2101,7 +2060,7 @@ __TargetExecuteScsi(
XENVBD_MAX_QUEUE_DEPTH))
Verbose("Target[%d] : Failed to set queue depth\n",
TargetGetTargetId(Target));
- PdoInquiry(TargetGetTargetId(Target),
FrontendGetInquiry(Target->Frontend), Srb, Target->DeviceType);
+ PdoInquiry(TargetGetTargetId(Target),
FrontendGetInquiry(Target->Frontend), Srb);
break;
case SCSIOP_MODE_SENSE:
TargetModeSense(Target, Srb);
@@ -2485,7 +2444,6 @@ TargetDispatchPnp(
default:
break;
}
- TargetDereference(Target);
return DriverDispatchPnp(DeviceObject, Irp);
}
@@ -2587,17 +2545,51 @@ TargetD0ToD3(
Trace("Target[%d] @ (%d) <=====\n", TargetId, KeGetCurrentIrql());
}
+static FORCEINLINE ULONG
+__ParseVbd(
+ IN PCHAR DeviceIdStr
+ )
+{
+ ULONG DeviceId = strtoul(DeviceIdStr, NULL, 10);
+
+ ASSERT3U((DeviceId & ~((1 << 29) - 1)), ==, 0);
+
+ if (DeviceId & (1 << 28))
+ return (DeviceId & ((1 << 20) - 1)) >> 8; /* xvd */
+
+ switch (DeviceId >> 8) {
+ case 202: return (DeviceId & 0xF0) >> 4; /* xvd */
+ case 8: return (DeviceId & 0xF0) >> 4; /* sd */
+ case 3: return (DeviceId & 0xC0) >> 6; /* hda..b */
+ case 22: return ((DeviceId & 0xC0) >> 6) + 2; /* hdc..d */
+ case 33: return ((DeviceId & 0xC0) >> 6) + 4; /* hde..f */
+ case 34: return ((DeviceId & 0xC0) >> 6) + 6; /* hdg..h */
+ case 56: return ((DeviceId & 0xC0) >> 6) + 8; /* hdi..j */
+ case 57: return ((DeviceId & 0xC0) >> 6) + 10; /* hdk..l */
+ case 88: return ((DeviceId & 0xC0) >> 6) + 12; /* hdm..n */
+ case 89: return ((DeviceId & 0xC0) >> 6) + 14; /* hdo..p */
+ default: return 0xFFFFFFFF; /* ERROR */
+ }
+}
+
__checkReturn
-BOOLEAN
+NTSTATUS
TargetCreate(
__in PXENVBD_ADAPTER Adapter,
__in __nullterminated PCHAR DeviceId,
- __in ULONG TargetId,
- __in XENVBD_DEVICE_TYPE DeviceType
+ OUT PXENVBD_TARGET* _Target
)
{
NTSTATUS Status;
PXENVBD_TARGET Target;
+ ULONG TargetId;
+
+ TargetId = __ParseVbd(DeviceId);
+ if (TargetId >= XENVBD_MAX_TARGETS)
+ return STATUS_RETRY;
+
+ if (AdapterIsTargetEmulated(Adapter, TargetId))
+ return STATUS_RETRY;
Trace("Target[%d] @ (%d) =====>\n", TargetId, KeGetCurrentIrql());
@@ -2611,12 +2603,9 @@ TargetCreate(
Target->Signature = TARGET_SIGNATURE;
Target->Adapter = Adapter;
Target->DeviceObject = NULL; // filled in later
- KeInitializeEvent(&Target->RemoveEvent, SynchronizationEvent, FALSE);
- Target->ReferenceCount = 1;
Target->Paused = 1; // Paused until D3->D0 transition
Target->DevicePnpState = Present;
Target->DevicePowerState = PowerDeviceD3;
- Target->DeviceType = DeviceType;
KeInitializeSpinLock(&Target->Lock);
QueueInit(&Target->FreshSrbs);
@@ -2635,16 +2624,11 @@ TargetCreate(
if (!NT_SUCCESS(Status))
goto fail3;
- if (!AdapterLinkTarget(Adapter, Target))
- goto fail4;
+ *_Target = Target;
Verbose("Target[%d] : Created (%s)\n", TargetId, Target);
Trace("Target[%d] @ (%d) <=====\n", TargetId, KeGetCurrentIrql());
- return TRUE;
-
-fail4:
- Error("Fail4\n");
- TargetD0ToD3(Target);
+ return STATUS_SUCCESS;
fail3:
Error("Fail3\n");
@@ -2660,7 +2644,7 @@ fail2:
fail1:
Error("Fail1 (%08x)\n", Status);
- return FALSE;
+ return Status;
}
VOID
@@ -2669,26 +2653,20 @@ TargetDestroy(
)
{
const ULONG TargetId = TargetGetTargetId(Target);
- PVOID Objects[4];
+ PVOID Objects[3];
PKWAIT_BLOCK WaitBlock;
Trace("Target[%d] @ (%d) =====>\n", TargetId, KeGetCurrentIrql());
Verbose("Target[%d] : Destroying\n", TargetId);
ASSERT3U(Target->Signature, ==, TARGET_SIGNATURE);
- if (!AdapterUnlinkTarget(TargetGetAdapter(Target), Target)) {
- Error("Target[%d] : TARGET 0x%p not linked to ADAPTER 0x%p\n",
TargetId, Target, TargetGetAdapter(Target));
- }
TargetD0ToD3(Target);
- TargetDereference(Target); // drop initial ref count
- // Wait for ReferenceCount == 0 and RequestListUsed == 0
- Verbose("Target[%d] : ReferenceCount %d, RequestListUsed %d\n", TargetId,
Target->ReferenceCount, Target->RequestList.Used);
- Objects[0] = &Target->RemoveEvent;
- Objects[1] = &Target->RequestList.Empty;
- Objects[2] = &Target->SegmentList.Empty;
- Objects[3] = &Target->IndirectList.Empty;
+ Verbose("Target[%d] : RequestListUsed %d\n", TargetId,
Target->RequestList.Used);
+ Objects[0] = &Target->RequestList.Empty;
+ Objects[1] = &Target->SegmentList.Empty;
+ Objects[2] = &Target->IndirectList.Empty;
WaitBlock = (PKWAIT_BLOCK)__TargetAlloc(sizeof(KWAIT_BLOCK) *
ARRAYSIZE(Objects));
if (WaitBlock == NULL) {
@@ -2715,7 +2693,6 @@ TargetDestroy(
__TargetFree(WaitBlock);
}
- ASSERT3S(Target->ReferenceCount, ==, 0);
ASSERT3U(TargetGetDevicePnpState(Target), ==, Deleted);
FrontendDestroy(Target->Frontend);
diff --git a/src/xenvbd/target.h b/src/xenvbd/target.h
index cdbc139..f97c121 100644
--- a/src/xenvbd/target.h
+++ b/src/xenvbd/target.h
@@ -50,12 +50,11 @@ TargetDebugCallback(
// Creation/Deletion
__checkReturn
-extern BOOLEAN
+extern NTSTATUS
TargetCreate(
__in PXENVBD_ADAPTER Adapter,
__in __nullterminated PCHAR DeviceId,
- __in ULONG TargetId,
- __in XENVBD_DEVICE_TYPE DeviceType
+ OUT PXENVBD_TARGET* _Target
);
extern VOID
@@ -110,29 +109,17 @@ TargetGetDevicePnpState(
__in PXENVBD_TARGET Target
);
-// Reference Counting
-extern LONG
-__TargetReference(
- __in PXENVBD_TARGET Target,
- __in PCHAR Caller
- );
-
-#define TargetReference(_x_) __TargetReference(_x_, __FUNCTION__)
-
-extern LONG
-__TargetDereference(
- __in PXENVBD_TARGET Target,
- __in PCHAR Caller
- );
-
-#define TargetDereference(_x_) __TargetDereference(_x_, __FUNCTION__)
-
// Query Methods
extern ULONG
TargetGetTargetId(
__in PXENVBD_TARGET Target
);
+extern ULONG
+TargetGetDeviceId(
+ __in PXENVBD_TARGET Target
+ );
+
__checkReturn
extern PDEVICE_OBJECT
TargetGetDeviceObject(
--
2.8.3
_______________________________________________
win-pv-devel mailing list
win-pv-devel@xxxxxxxxxxxxxxxxxxxx
https://lists.xenproject.org/cgi-bin/mailman/listinfo/win-pv-devel
|
![]() |
Lists.xenproject.org is hosted with RackSpace, monitoring our |