|
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] [win-pv-devel] [PATCH] Update VIF interface to version 5
Unfortunately VIF interface version 4 suffers from a shutdown race with
the TransmitterQueuePacket method. If a call to this races with the Disable
method then a NULL callback function pointer can be invoked.
This patch fixes the race by having TransmitterQueuePacket return a status
code to indicate whether a packet has been queued (rather than invoking the
completion callback if it has not), but this necessitates a interface change
so the VIF interface version is also updated to 5 and a new PDO revision is
added.
Signed-off-by: Paul Durrant <paul.durrant@xxxxxxxxxx>
---
include/revision.h | 3 +-
include/vif_interface.h | 48 ++++++++++++++++++++++++++--
src/xenvif/vif.c | 83 ++++++++++++++++++++++++++++++++++++++++++++++++-
3 files changed, 129 insertions(+), 5 deletions(-)
diff --git a/include/revision.h b/include/revision.h
index eda8871..78de3a1 100644
--- a/include/revision.h
+++ b/include/revision.h
@@ -43,7 +43,8 @@
DEFINE_REVISION(0x08000002, 1, 2, 0, 0), \
DEFINE_REVISION(0x08000003, 1, 3, 0, 0), \
DEFINE_REVISION(0x08000004, 1, 3, 2, 1), \
- DEFINE_REVISION(0x08000006, 1, 4, 2, 1)
+ DEFINE_REVISION(0x08000006, 1, 4, 2, 1), \
+ DEFINE_REVISION(0x08000007, 1, 5, 2, 1)
// Revision 0x08000005 is already in use in the staging-8.1 branch.
diff --git a/include/vif_interface.h b/include/vif_interface.h
index 27c5d2d..5a064fd 100644
--- a/include/vif_interface.h
+++ b/include/vif_interface.h
@@ -460,6 +460,19 @@ typedef NTSTATUS
IN PLIST_ENTRY List
);
+typedef VOID
+(*XENVIF_VIF_TRANSMITTER_QUEUE_PACKET_V4)(
+ IN PINTERFACE Interface,
+ IN PMDL Mdl,
+ IN ULONG Offset,
+ IN ULONG Length,
+ IN XENVIF_VIF_OFFLOAD_OPTIONS OffloadOptions,
+ IN USHORT MaximumSegmentSize,
+ IN USHORT TagControlInformation,
+ IN PXENVIF_PACKET_HASH Hash,
+ IN PVOID Cookie
+ );
+
/*! \typedef XENVIF_VIF_TRANSMITTER_QUEUE_PACKET
\brief Queue a packet at the provider's transmit side
@@ -473,7 +486,7 @@ typedef NTSTATUS
\param Hash Hash information for the packet
\param Cookie A cookie specified by the caller that will be passed to the
XENVIF_TRANSMITTER_RETURN_PACKET callback
*/
-typedef VOID
+typedef NTSTATUS
(*XENVIF_VIF_TRANSMITTER_QUEUE_PACKET)(
IN PINTERFACE Interface,
IN PMDL Mdl,
@@ -766,6 +779,35 @@ struct _XENVIF_VIF_INTERFACE_V4 {
XENVIF_VIF_RECEIVER_SET_OFFLOAD_OPTIONS ReceiverSetOffloadOptions;
XENVIF_VIF_RECEIVER_SET_BACKFILL_SIZE ReceiverSetBackfillSize;
XENVIF_VIF_RECEIVER_QUERY_RING_SIZE ReceiverQueryRingSize;
+ XENVIF_VIF_TRANSMITTER_QUEUE_PACKET_V4
TransmitterQueuePacketVersion4;
+ XENVIF_VIF_TRANSMITTER_QUERY_OFFLOAD_OPTIONS
TransmitterQueryOffloadOptions;
+ XENVIF_VIF_TRANSMITTER_QUERY_LARGE_PACKET_SIZE
TransmitterQueryLargePacketSize;
+ XENVIF_VIF_TRANSMITTER_QUERY_RING_SIZE TransmitterQueryRingSize;
+ XENVIF_VIF_MAC_QUERY_STATE MacQueryState;
+ XENVIF_VIF_MAC_QUERY_MAXIMUM_FRAME_SIZE MacQueryMaximumFrameSize;
+ XENVIF_VIF_MAC_QUERY_PERMANENT_ADDRESS MacQueryPermanentAddress;
+ XENVIF_VIF_MAC_QUERY_CURRENT_ADDRESS MacQueryCurrentAddress;
+ XENVIF_VIF_MAC_QUERY_MULTICAST_ADDRESSES MacQueryMulticastAddresses;
+ XENVIF_VIF_MAC_SET_MULTICAST_ADDRESSES MacSetMulticastAddresses;
+ XENVIF_VIF_MAC_SET_FILTER_LEVEL MacSetFilterLevel;
+ XENVIF_VIF_MAC_QUERY_FILTER_LEVEL MacQueryFilterLevel;
+};
+
+/*! \struct _XENVIF_VIF_INTERFACE_V5
+ \brief VIF interface version 5
+ \ingroup interfaces
+*/
+struct _XENVIF_VIF_INTERFACE_V5 {
+ INTERFACE Interface;
+ XENVIF_VIF_ACQUIRE Acquire;
+ XENVIF_VIF_RELEASE Release;
+ XENVIF_VIF_ENABLE Enable;
+ XENVIF_VIF_DISABLE Disable;
+ XENVIF_VIF_QUERY_STATISTIC QueryStatistic;
+ XENVIF_VIF_RECEIVER_RETURN_PACKET ReceiverReturnPacket;
+ XENVIF_VIF_RECEIVER_SET_OFFLOAD_OPTIONS ReceiverSetOffloadOptions;
+ XENVIF_VIF_RECEIVER_SET_BACKFILL_SIZE ReceiverSetBackfillSize;
+ XENVIF_VIF_RECEIVER_QUERY_RING_SIZE ReceiverQueryRingSize;
XENVIF_VIF_TRANSMITTER_QUEUE_PACKET TransmitterQueuePacket;
XENVIF_VIF_TRANSMITTER_QUERY_OFFLOAD_OPTIONS
TransmitterQueryOffloadOptions;
XENVIF_VIF_TRANSMITTER_QUERY_LARGE_PACKET_SIZE
TransmitterQueryLargePacketSize;
@@ -780,7 +822,7 @@ struct _XENVIF_VIF_INTERFACE_V4 {
XENVIF_VIF_MAC_QUERY_FILTER_LEVEL MacQueryFilterLevel;
};
-typedef struct _XENVIF_VIF_INTERFACE_V4 XENVIF_VIF_INTERFACE,
*PXENVIF_VIF_INTERFACE;
+typedef struct _XENVIF_VIF_INTERFACE_V5 XENVIF_VIF_INTERFACE,
*PXENVIF_VIF_INTERFACE;
/*! \def XENVIF_VIF
\brief Macro at assist in method invocation
@@ -791,6 +833,6 @@ typedef struct _XENVIF_VIF_INTERFACE_V4
XENVIF_VIF_INTERFACE, *PXENVIF_VIF_INTER
#endif // _WINDLL
#define XENVIF_VIF_INTERFACE_VERSION_MIN 2
-#define XENVIF_VIF_INTERFACE_VERSION_MAX 4
+#define XENVIF_VIF_INTERFACE_VERSION_MAX 5
#endif // _XENVIF_INTERFACE_H
diff --git a/src/xenvif/vif.c b/src/xenvif/vif.c
index cd8aafc..3d40ad0 100644
--- a/src/xenvif/vif.c
+++ b/src/xenvif/vif.c
@@ -396,7 +396,7 @@ done:
}
static VOID
-VifTransmitterQueuePacket(
+VifTransmitterQueuePacketVersion4(
IN PINTERFACE Interface,
IN PMDL Mdl,
IN ULONG Offset,
@@ -444,6 +444,45 @@ done:
}
}
+static NTSTATUS
+VifTransmitterQueuePacket(
+ IN PINTERFACE Interface,
+ IN PMDL Mdl,
+ IN ULONG Offset,
+ IN ULONG Length,
+ IN XENVIF_VIF_OFFLOAD_OPTIONS OffloadOptions,
+ IN USHORT MaximumSegmentSize,
+ IN USHORT TagControlInformation,
+ IN PXENVIF_PACKET_HASH Hash,
+ IN PVOID Cookie
+ )
+{
+ PXENVIF_VIF_CONTEXT Context = Interface->Context;
+ NTSTATUS status;
+
+ AcquireMrswLockShared(&Context->Lock);
+
+ status = STATUS_UNSUCCESSFUL;
+ if (Context->Enabled == FALSE)
+ goto done;
+
+ ASSERT3U(VifGetVersion(Context), >=, 5);
+ status = TransmitterQueuePacket(FrontendGetTransmitter(Context->Frontend),
+ Mdl,
+ Offset,
+ Length,
+ OffloadOptions,
+ MaximumSegmentSize,
+ TagControlInformation,
+ Hash,
+ Cookie);
+
+done:
+ ReleaseMrswLockShared(&Context->Lock);
+
+ return status;
+}
+
static VOID
VifTransmitterQueryOffloadOptions(
IN PINTERFACE Interface,
@@ -809,6 +848,31 @@ static struct _XENVIF_VIF_INTERFACE_V4
VifInterfaceVersion4 = {
VifReceiverSetOffloadOptions,
VifReceiverSetBackfillSize,
VifReceiverQueryRingSize,
+ VifTransmitterQueuePacketVersion4,
+ VifTransmitterQueryOffloadOptions,
+ VifTransmitterQueryLargePacketSize,
+ VifTransmitterQueryRingSize,
+ VifMacQueryState,
+ VifMacQueryMaximumFrameSize,
+ VifMacQueryPermanentAddress,
+ VifMacQueryCurrentAddress,
+ VifMacQueryMulticastAddresses,
+ VifMacSetMulticastAddresses,
+ VifMacSetFilterLevel,
+ VifMacQueryFilterLevel
+};
+
+static struct _XENVIF_VIF_INTERFACE_V5 VifInterfaceVersion5 = {
+ { sizeof (struct _XENVIF_VIF_INTERFACE_V5), 5, NULL, NULL, NULL },
+ VifAcquire,
+ VifRelease,
+ VifEnable,
+ VifDisable,
+ VifQueryStatistic,
+ VifReceiverReturnPacket,
+ VifReceiverSetOffloadOptions,
+ VifReceiverSetBackfillSize,
+ VifReceiverQueryRingSize,
VifTransmitterQueuePacket,
VifTransmitterQueryOffloadOptions,
VifTransmitterQueryLargePacketSize,
@@ -938,6 +1002,23 @@ VifGetInterface(
status = STATUS_SUCCESS;
break;
}
+ case 5: {
+ struct _XENVIF_VIF_INTERFACE_V5 *VifInterface;
+
+ VifInterface = (struct _XENVIF_VIF_INTERFACE_V5 *)Interface;
+
+ status = STATUS_BUFFER_OVERFLOW;
+ if (Size < sizeof (struct _XENVIF_VIF_INTERFACE_V5))
+ break;
+
+ *VifInterface = VifInterfaceVersion5;
+
+ ASSERT3U(Interface->Version, ==, Version);
+ Interface->Context = Context;
+
+ status = STATUS_SUCCESS;
+ break;
+ }
default:
status = STATUS_NOT_SUPPORTED;
break;
--
2.1.1
_______________________________________________
win-pv-devel mailing list
win-pv-devel@xxxxxxxxxxxxxxxxxxxx
http://lists.xenproject.org/cgi-bin/mailman/listinfo/win-pv-devel
|
![]() |
Lists.xenproject.org is hosted with RackSpace, monitoring our |