[ofw] [PATCH] [RFC] winverbs/qp: add support for modify qp
Sean Hefty
sean.hefty at intel.com
Thu May 1 19:05:48 PDT 2008
Initial implementation for QP:Modify.
The underlying channel interface does not support asynchronous modify, so
the implementation is restricted to synchronous operation.
Signed-off-by: Sean Hefty <sean.hefty at intel.com>
---
Index: core/winverbs/kernel/wv_driver.c
===================================================================
--- core/winverbs/kernel/wv_driver.c (revision 1103)
+++ core/winverbs/kernel/wv_driver.c (working copy)
@@ -269,7 +269,7 @@
WvQpQuery(prov, Request);
break;
case WV_IOCTL_QP_MODIFY:
- //WvQpModify(prov, Request);
+ WvQpModify(prov, Request);
WdfRequestComplete(Request, STATUS_NOT_IMPLEMENTED);
break;
case WV_IOCTL_QP_ATTACH:
Index: core/winverbs/kernel/wv_qp.c
===================================================================
--- core/winverbs/kernel/wv_qp.c (revision 1103)
+++ core/winverbs/kernel/wv_qp.c (working copy)
@@ -62,7 +62,7 @@
case IB_QPS_INIT: return WV_IO_QP_STATE_INIT;
case IB_QPS_RTR: return WV_IO_QP_STATE_RTR;
case IB_QPS_RTS: return WV_IO_QP_STATE_RTS;
- case IB_QPS_SQD: return WV_IO_QP_STATE_SDQ;
+ case IB_QPS_SQD: return WV_IO_QP_STATE_SQD;
case IB_QPS_SQERR: return WV_IO_QP_STATE_SQERROR;
default: return WV_IO_QP_STATE_ERROR;
}
@@ -84,6 +84,22 @@
pAv->SourcePathBits = pVerbsAv->path_bits;
}
+static void WvVerbsConvertAv(ib_av_attr_t *pVerbsAv, WV_IO_AV *pAv)
+{
+ if (pAv->GrhValid) {
+ RtlCopyMemory(&pVerbsAv->grh, pAv, sizeof pVerbsAv->grh);
+ pVerbsAv->grh_valid = 1;
+ } else {
+ pVerbsAv->grh_valid = 0;
+ }
+
+ pVerbsAv->port_num = pAv->PortNumber;
+ pVerbsAv->sl = pAv->ServiceLevel;
+ pVerbsAv->dlid = pAv->DLid;
+ pVerbsAv->static_rate = pAv->StaticRate;
+ pVerbsAv->path_bits = pAv->SourcePathBits;
+}
+
static void WvQpAttrConvertVerbs(WV_IO_QP_ATTRIBUTES *pAttr, ib_qp_attr_t *pVerbsAttr)
{
pAttr->QpType = pVerbsAttr->qp_type;
@@ -123,6 +139,147 @@
pAttr->RnrRetryCount = pVerbsAttr->primary_av.conn.rnr_retry_cnt;
}
+static ib_qp_opts_t WvVerbsConvertOptions(UINT32 Options)
+{
+ UINT32 opt = 0;
+
+ if ((Options & WV_IO_QP_ATTR_CURRENT_STATE) == WV_IO_QP_ATTR_CURRENT_STATE) {
+ opt |= IB_MOD_QP_CURRENT_STATE;
+ }
+ if ((Options & WV_IO_QP_ATTR_ACCESS_FLAGS) == WV_IO_QP_ATTR_ACCESS_FLAGS) {
+ opt |= IB_MOD_QP_ACCESS_CTRL;
+ }
+ if ((Options & WV_IO_QP_ATTR_PKEY_INDEX) == WV_IO_QP_ATTR_PKEY_INDEX) {
+ opt |= IB_MOD_QP_PKEY;
+ }
+ if ((Options & WV_IO_QP_ATTR_PORT) == WV_IO_QP_ATTR_PORT) {
+ opt |= IB_MOD_QP_PRIMARY_PORT;
+ }
+ if ((Options & WV_IO_QP_ATTR_QKEY) == WV_IO_QP_ATTR_QKEY) {
+ opt |= IB_MOD_QP_QKEY;
+ }
+ if ((Options & WV_IO_QP_ATTR_AV) == WV_IO_QP_ATTR_AV ||
+ (Options & WV_IO_QP_ATTR_PATH_MTU) == WV_IO_QP_ATTR_PATH_MTU) {
+ opt |= IB_MOD_QP_PRIMARY_AV;
+ }
+ if ((Options & WV_IO_QP_ATTR_TIMEOUT) == WV_IO_QP_ATTR_TIMEOUT) {
+ opt |= IB_MOD_QP_LOCAL_ACK_TIMEOUT;
+ }
+ if ((Options & WV_IO_QP_ATTR_RETRY_COUNT) == WV_IO_QP_ATTR_RETRY_COUNT) {
+ opt |= IB_MOD_QP_RETRY_CNT;
+ }
+ if ((Options & WV_IO_QP_ATTR_RNR_RETRY) == WV_IO_QP_ATTR_RNR_RETRY) {
+ opt |= IB_MOD_QP_RNR_RETRY_CNT;
+ }
+ if ((Options & WV_IO_QP_ATTR_INITIATOR_DEPTH) == WV_IO_QP_ATTR_INITIATOR_DEPTH) {
+ opt |= IB_MOD_QP_INIT_DEPTH;
+ }
+ if ((Options & WV_IO_QP_ATTR_ALTERNATE_AV) == WV_IO_QP_ATTR_ALTERNATE_AV) {
+ opt |= IB_MOD_QP_ALTERNATE_AV;
+ }
+ if ((Options & WV_IO_QP_ATTR_MIN_RNR_TIMER) == WV_IO_QP_ATTR_MIN_RNR_TIMER) {
+ opt |= IB_MOD_QP_RNR_NAK_TIMEOUT;
+ }
+ if ((Options & WV_IO_QP_ATTR_RESPONDER_RESOURCES) == WV_IO_QP_ATTR_RESPONDER_RESOURCES) {
+ opt |= IB_MOD_QP_RESP_RES;
+ }
+ if ((Options & WV_IO_QP_ATTR_PATH_MIG_STATE) == WV_IO_QP_ATTR_PATH_MIG_STATE) {
+ opt |= IB_MOD_QP_APM_STATE;
+ }
+ if ((Options & WV_IO_QP_ATTR_CAPABILITIES) == WV_IO_QP_ATTR_CAPABILITIES) {
+ opt |= IB_MOD_QP_SQ_DEPTH | IB_MOD_QP_RQ_DEPTH;
+ }
+
+ return (ib_qp_opts_t) opt;
+}
+
+static ib_qp_state_t WvVerbsConvertState(UINT8 State)
+{
+ switch (State) {
+ case WV_IO_QP_STATE_RESET: return IB_QPS_RESET;
+ case WV_IO_QP_STATE_INIT: return IB_QPS_INIT;
+ case WV_IO_QP_STATE_RTR: return IB_QPS_RTR;
+ case WV_IO_QP_STATE_RTS: return IB_QPS_RTS;
+ case WV_IO_QP_STATE_SQD: return IB_QPS_SQD;
+ case WV_IO_QP_STATE_SQERROR: return IB_QPS_SQERR;
+ default: return IB_QPS_ERROR;
+ }
+}
+
+static void WvVerbsConvertAttr(ib_qp_mod_t *pVerbsAttr, WV_IO_QP_ATTRIBUTES *pAttr)
+{
+ switch (pAttr->QpState) {
+ case WV_IO_QP_STATE_RESET:
+ pVerbsAttr->req_state = IB_QPS_RESET;
+ break;
+ case WV_IO_QP_STATE_INIT:
+ pVerbsAttr->req_state = IB_QPS_INIT;
+
+ pVerbsAttr->state.init.primary_port = pAttr->PrimaryAddressVector.PortNumber;
+ pVerbsAttr->state.init.qkey = pAttr->Qkey;
+ pVerbsAttr->state.init.pkey_index = pAttr->PkeyIndex;
+ pVerbsAttr->state.init.access_ctrl = pAttr->AccessFlags;
+ break;
+ case WV_IO_QP_STATE_RTR:
+ pVerbsAttr->req_state = IB_QPS_RTR;
+
+ pVerbsAttr->state.rtr.rq_psn = pAttr->ReceivePsn;
+ pVerbsAttr->state.rtr.dest_qp = pAttr->DestinationQpn;
+ WvVerbsConvertAv(&pVerbsAttr->state.rtr.primary_av,
+ &pAttr->PrimaryAddressVector);
+ pVerbsAttr->state.rtr.resp_res = (UINT8) pAttr->ResponderResources;
+ pVerbsAttr->state.rtr.rnr_nak_timeout = pAttr->RnrNakTimeout;
+
+ pVerbsAttr->state.rtr.opts = WvVerbsConvertOptions(pAttr->Options);
+ WvVerbsConvertAv(&pVerbsAttr->state.rtr.alternate_av,
+ &pAttr->AlternateAddressVector);
+ pVerbsAttr->state.rtr.qkey = pAttr->Qkey;
+ pVerbsAttr->state.rtr.pkey_index = pAttr->PkeyIndex;
+ pVerbsAttr->state.rtr.access_ctrl = pAttr->AccessFlags;
+ pVerbsAttr->state.rtr.sq_depth = pAttr->SendDepth;
+ pVerbsAttr->state.rtr.rq_depth = pAttr->ReceiveDepth;
+ break;
+ case WV_IO_QP_STATE_RTS:
+ pVerbsAttr->req_state = IB_QPS_RTS;
+
+ pVerbsAttr->state.rts.sq_psn = pAttr->SendPsn;
+ pVerbsAttr->state.rts.retry_cnt = pAttr->SequenceErrorRetryCount;
+ pVerbsAttr->state.rts.rnr_retry_cnt = pAttr->RnrRetryCount;
+ pVerbsAttr->state.rts.local_ack_timeout = pAttr->LocalAckTimeout;
+ pVerbsAttr->state.rts.init_depth = (UINT8) pAttr->InitiatorDepth;
+
+ pVerbsAttr->state.rts.opts = WvVerbsConvertOptions(pAttr->Options);
+ pVerbsAttr->state.rts.rnr_nak_timeout = pAttr->RnrNakTimeout;
+ pVerbsAttr->state.rts.current_state = WvVerbsConvertState(pAttr->CurrentQpState);
+ pVerbsAttr->state.rts.qkey = pAttr->Qkey;
+ pVerbsAttr->state.rts.access_ctrl = pAttr->AccessFlags;
+ pVerbsAttr->state.rts.resp_res = (UINT8) pAttr->ResponderResources;
+
+ WvVerbsConvertAv(&pVerbsAttr->state.rts.primary_av,
+ &pAttr->PrimaryAddressVector);
+ WvVerbsConvertAv(&pVerbsAttr->state.rts.alternate_av,
+ &pAttr->AlternateAddressVector);
+
+ pVerbsAttr->state.rts.sq_depth = pAttr->SendDepth;
+ pVerbsAttr->state.rts.rq_depth = pAttr->ReceiveDepth;
+
+ pVerbsAttr->state.rts.apm_state = pAttr->ApmState;
+ pVerbsAttr->state.rts.primary_port = pAttr->PrimaryAddressVector.PortNumber;
+ pVerbsAttr->state.rts.pkey_index = pAttr->PkeyIndex;
+ break;
+ case WV_IO_QP_STATE_SQD:
+ pVerbsAttr->req_state = IB_QPS_SQD;
+ pVerbsAttr->state.sqd.sqd_event = 1;
+ break;
+ case WV_IO_QP_STATE_SQERROR:
+ pVerbsAttr->req_state = IB_QPS_SQERR;
+ break;
+ default:
+ pVerbsAttr->req_state = IB_QPS_ERROR;
+ break;
+ }
+}
+
static void WvQpGet(WV_QUEUE_PAIR *pQp)
{
InterlockedIncrement(&pQp->Ref);
@@ -406,6 +563,41 @@
WdfRequestCompleteWithInformation(Request, status, len);
}
+void WvQpModify(WV_PROVIDER *pProvider, WDFREQUEST Request)
+{
+ WV_IO_QP_ATTRIBUTES *pattr;
+ UINT8 *out;
+ size_t outlen, len = 0;
+ WV_QUEUE_PAIR *qp;
+ ib_qp_mod_t attr;
+ NTSTATUS status;
+ ib_api_status_t ib_status;
+
+ status = WdfRequestRetrieveInputBuffer(Request, sizeof(WV_IO_QP_ATTRIBUTES),
+ &pattr, NULL);
+ if (!NT_SUCCESS(status)) {
+ goto complete;
+ }
+ status = WdfRequestRetrieveOutputBuffer(Request, 0, &out, &outlen);
+ if (!NT_SUCCESS(status) && status != STATUS_BUFFER_TOO_SMALL) {
+ goto complete;
+ }
+
+ WvVerbsConvertAttr(&attr, pattr);
+ qp = WvQpAcquire(pProvider, pattr->Id.Id);
+ if (qp == NULL) {
+ status = STATUS_NOT_FOUND;
+ goto complete;
+ }
+
+ ib_status = qp->pVerbs->ndi_modify_qp(qp->hVerbsQp, &attr, NULL, outlen, out);
+ WvQpRelease(qp);
+ len = outlen;
+
+complete:
+ WdfRequestCompleteWithInformation(Request, status, len);
+}
+
void WvQpAttach(WV_PROVIDER *pProvider, WDFREQUEST Request)
{
WV_MULTICAST *pmc;
Index: core/winverbs/kernel/wv_qp.h
===================================================================
--- core/winverbs/kernel/wv_qp.h (revision 1103)
+++ core/winverbs/kernel/wv_qp.h (working copy)
@@ -64,7 +64,7 @@
void WvQpFree(WV_QUEUE_PAIR *pQp);
void WvQpRemoveHandler(WV_QUEUE_PAIR *pQp);
-//void WvQpModify(WV_PROVIDER *pProvider, WDFREQUEST Request);
+void WvQpModify(WV_PROVIDER *pProvider, WDFREQUEST Request);
void WvQpQuery(WV_PROVIDER *pProvider, WDFREQUEST Request);
void WvQpAttach(WV_PROVIDER *pProvider, WDFREQUEST Request);
void WvQpDetach(WV_PROVIDER *pProvider, WDFREQUEST Request);
Index: core/winverbs/user/wv_qp.cpp
===================================================================
--- core/winverbs/user/wv_qp.cpp (revision 1007)
+++ core/winverbs/user/wv_qp.cpp (working copy)
@@ -168,6 +168,7 @@
pAttr->PathMtu = pIoAttr->PathMtu;
pAttr->LocalAckTimeout = pIoAttr->LocalAckTimeout;
+ pAttr->RnrNakTimeout = pIoAttr->RnrNakTimeout;
pAttr->SequenceErrorRetryCount = pIoAttr->SequenceErrorRetryCount;
pAttr->RnrRetryCount = pIoAttr->RnrRetryCount;
}
@@ -202,6 +203,7 @@
pIoAttr->PathMtu = pAttr->PathMtu;
pIoAttr->LocalAckTimeout = pAttr->LocalAckTimeout;
+ pIoAttr->RnrNakTimeout = pAttr->RnrNakTimeout;
pIoAttr->SequenceErrorRetryCount = pAttr->SequenceErrorRetryCount;
pIoAttr->RnrRetryCount = pAttr->RnrRetryCount;
}
Index: core/winverbs/wv_ioctl.h
===================================================================
--- core/winverbs/wv_ioctl.h (revision 1097)
+++ core/winverbs/wv_ioctl.h (working copy)
@@ -500,10 +500,32 @@
#define WV_IO_QP_STATE_INIT 1
#define WV_IO_QP_STATE_RTR 2
#define WV_IO_QP_STATE_RTS 3
-#define WV_IO_QP_STATE_SDQ 4
+#define WV_IO_QP_STATE_SQD 4
#define WV_IO_QP_STATE_SQERROR 5
#define WV_IO_QP_STATE_ERROR 6
+#define WV_IO_QP_ATTR_STATE 0x00000001
+#define WV_IO_QP_ATTR_CURRENT_STATE 0x00000002
+#define WV_IO_QP_ATTR_ENABLE_SQD_ASYNC_NOTIFY 0x00000004
+#define WV_IO_QP_ATTR_ACCESS_FLAGS 0x00000008
+#define WV_IO_QP_ATTR_PKEY_INDEX 0x00000010
+#define WV_IO_QP_ATTR_PORT 0x00000020
+#define WV_IO_QP_ATTR_QKEY 0x00000040
+#define WV_IO_QP_ATTR_AV 0x00000080
+#define WV_IO_QP_ATTR_PATH_MTU 0x00000100
+#define WV_IO_QP_ATTR_TIMEOUT 0x00000200
+#define WV_IO_QP_ATTR_RETRY_COUNT 0x00000400
+#define WV_IO_QP_ATTR_RNR_RETRY 0x00000800
+#define WV_IO_QP_ATTR_RQ_PSN 0x00001000
+#define WV_IO_QP_ATTR_INITIATOR_DEPTH 0x00002000
+#define WV_IO_QP_ATTR_ALTERNATE_AV 0x00004000
+#define WV_IO_QP_ATTR_MIN_RNR_TIMER 0x00008000
+#define WV_IO_QP_ATTR_SQ_PSN 0x00010000
+#define WV_IO_QP_ATTR_RESPONDER_RESOURCES 0x00020000
+#define WV_IO_QP_ATTR_PATH_MIG_STATE 0x00040000
+#define WV_IO_QP_ATTR_CAPABILITIES 0x00080000
+#define WV_IO_QP_ATTR_DESTINATION_QPN 0x00100000
+
typedef struct _WV_IO_QP_ATTRIBUTES
{
WV_IO_ID Id;
@@ -534,9 +556,10 @@
UINT8 PathMtu;
UINT8 LocalAckTimeout;
+ UINT8 RnrNakTimeout;
UINT8 SequenceErrorRetryCount;
UINT8 RnrRetryCount;
- UINT32 Reserved;
+ UINT8 Reserved[3];
} WV_IO_QP_ATTRIBUTES;
Index: inc/user/rdma/winverbs.h
===================================================================
--- inc/user/rdma/winverbs.h (revision 1070)
+++ inc/user/rdma/winverbs.h (working copy)
@@ -392,6 +392,7 @@
UINT8 PathMtu;
UINT8 LocalAckTimeout;
+ UINT8 RnrNakTimeout;
UINT8 SequenceErrorRetryCount;
UINT8 RnrRetryCount;
More information about the ofw
mailing list