]> git.openfabrics.org - ~shefty/rdma-win.git/commitdiff
uvp/interface: add support for reporting QP context in WCs
authorshefty <shefty@ad392aa1-c5ef-ae45-8dd8-e69d62a5ef86>
Thu, 20 Mar 2008 07:15:54 +0000 (07:15 +0000)
committershefty <shefty@ad392aa1-c5ef-ae45-8dd8-e69d62a5ef86>
Thu, 20 Mar 2008 07:15:54 +0000 (07:15 +0000)
Extend the uvp_interface to include support for reporting the QP context in work completions.  The new interface is moved to version 3, and the Mellanox UVP is updated to support interfaces 1-3.  The required changes are to allow specifying a qp_context in the pre_create_qp() IOCTL call, and reporting the qp_context through the work completion structure.

To minimize changes to the uvp, a new uvp_wc_t structure is defined that can be cast to the existing ib_wc_t structure.  An existing poll_cq_array routine is exposed for retrieving the work completions, which matches up with the WinVerbs CQ::Poll() routine.

Signed-off-by: Sean Hefty <sean.hefty@intel.com>
git-svn-id: svn://openib.tc.cornell.edu/gen1@997 ad392aa1-c5ef-ae45-8dd8-e69d62a5ef86

branches/winverbs/hw/mthca/user/mlnx_ual_main.c
branches/winverbs/hw/mthca/user/mlnx_ual_osbypass.c
branches/winverbs/hw/mthca/user/mlnx_ual_qp.c
branches/winverbs/hw/mthca/user/mlnx_uvp.h
branches/winverbs/hw/mthca/user/mlnx_uvp_cq.c
branches/winverbs/hw/mthca/user/mlnx_uvp_verbs.h
branches/winverbs/inc/user/iba/ib_uvp.h

index 14382d5f0c0a437625e80e58b39d155d0eb03ec7..e46dec6bda8bef97265b07a36d53b43a170db780 100644 (file)
@@ -217,6 +217,12 @@ uvp_get_interface_n (
        switch (version)\r
        {\r
        case 2:\r
+               if (uvp_interface_size < sizeof(uvp2_interface_t))\r
+               {\r
+                       status = IB_INSUFFICIENT_MEMORY;\r
+               }\r
+               break;\r
+       case 3:\r
                if (uvp_interface_size < sizeof(uvp_interface_t))\r
                {\r
                        status = IB_INSUFFICIENT_MEMORY;\r
@@ -240,7 +246,7 @@ uvp_get_interface_n (
 // Deprecate - for version 2 support only\r
 __declspec(dllexport) ib_api_status_t\r
 uvp_get_interface (\r
-    IN OUT     uvp_interface_t         *p_uvp )\r
+    IN OUT     uvp2_interface_t                *p_uvp )\r
 {\r
        __get_interface(2, (uvp_interface_t *) p_uvp);\r
        p_uvp->version = 101;\r
index b606022be3cfb148a3d4eabe9af848bb91f4d8f2..6fdf2cc49ee3c5498270291aa3890bde0e447726 100644 (file)
@@ -176,6 +176,25 @@ err_invalid_params:
 }\r
 \r
 \r
+static int\r
+__poll_cq_array (\r
+       IN              const   void*                                           h_cq,\r
+       IN              const   int                                                     num_entries,\r
+       IN      OUT                     uvp_wc_t*       const                   wc )\r
+{\r
+       int ne;\r
+       struct mthca_cq *cq = (struct mthca_cq *) h_cq;\r
+\r
+       UVP_ENTER(UVP_DBG_CQ);\r
+       CL_ASSERT (cq);\r
+\r
+       ne = cq->ibv_cq.context->ops.poll_cq(&cq->ibv_cq, num_entries, wc);\r
+\r
+       UVP_EXIT(UVP_DBG_CQ);\r
+       return ne;\r
+}\r
+\r
+\r
 static ib_api_status_t\r
 __enable_cq_notify (\r
        IN              const   void*           __ptr64                 h_cq,\r
@@ -221,7 +240,6 @@ mlnx_get_osbypass_interface (
     IN OUT     uvp_interface_t         *p_uvp )\r
 {\r
 \r
-       UNREFERENCED_PARAMETER(version);\r
     CL_ASSERT(p_uvp);\r
 \r
     /*\r
@@ -244,5 +262,10 @@ mlnx_get_osbypass_interface (
 \r
     /* Memory window bind */\r
     p_uvp->bind_mw = NULL; /* __bind_mw: Not implemented */\r
+\r
+       if (version >= 3)\r
+       {\r
+               p_uvp->poll_cq_array = __poll_cq_array;\r
+       }\r
 }\r
 \r
index 96080d1902f32e79a8eb7bcf03446191e9ca81a9..f71a791005983188b6845f664ce36523d3b96d8e 100644 (file)
@@ -148,6 +148,25 @@ end:
                return status;\r
 }\r
 \r
+static ib_api_status_t\r
+__wv_pre_create_qp (\r
+       IN              const   ib_pd_handle_t                  h_uvp_pd,\r
+       IN              const   uvp_qp_create_t                 *p_create_attr,\r
+       IN OUT                  ci_umv_buf_t                    *p_umv_buf,\r
+           OUT                 ib_qp_handle_t                  *ph_uvp_qp)\r
+{\r
+       struct ibv_qp *qp;\r
+       ib_api_status_t status;\r
+\r
+       status = __pre_create_qp(h_uvp_pd, &p_create_attr->qp_create,\r
+                                                        p_umv_buf, ph_uvp_qp);\r
+       if (status == IB_SUCCESS) {\r
+               qp = (struct ibv_qp *) *ph_uvp_qp;\r
+               qp->context = p_create_attr->context;\r
+       }\r
+       return status;\r
+}\r
+\r
 static ib_api_status_t\r
 __post_create_qp (\r
        IN              const ib_pd_handle_t                            h_uvp_pd,\r
@@ -371,6 +390,11 @@ mlnx_get_qp_interface (
                p_uvp->nd_get_qp_state = __nd_get_qp_state;\r
        }\r
 \r
+       if (version >= 3)\r
+       {\r
+               p_uvp->wv_pre_create_qp = __wv_pre_create_qp;\r
+       }\r
+\r
     UVP_EXIT(UVP_DBG_SHIM);\r
 }\r
 \r
index b5d4702ff0aef28455870d869aec63f6759041c2..12e41860af0da6e7434a8e1884f22267fd2a30b8 100644 (file)
@@ -277,7 +277,7 @@ struct ibv_cq *mthca_create_cq_pre(struct ibv_context *context, int *cqe,
 struct ibv_cq *mthca_create_cq_post(struct ibv_context *context, 
                                 struct ibv_create_cq_resp *resp);
 int mthca_destroy_cq(struct ibv_cq *cq);
-int mthca_poll_cq(struct ibv_cq *cq, int ne, struct _ib_wc *wc);
+int mthca_poll_cq(struct ibv_cq *cq, int ne, struct _uvp_wc *wc);
 int mthca_poll_cq_list(struct ibv_cq *ibcq, 
        struct _ib_wc** const pp_free_wclist,
        struct _ib_wc** const pp_done_wclist );
index 3d592c0d4898bbbc92cb25e16b258db0a5399919..a3a6e35abdd797b66167189b3495e97437827509 100644 (file)
@@ -37,6 +37,7 @@
 #include <opcode.h>
 #include "mlnx_uvp.h"
 #include "mlnx_uvp_doorbell.h"
+#include <iba\ib_uvp.h>
 
 #if defined(EVENT_TRACING)
 #include "mlnx_uvp_cq.tmh"
@@ -442,7 +443,7 @@ out:
        return err;
 }
 
-int mthca_poll_cq(struct ibv_cq *ibcq, int num_entries, struct _ib_wc *entry)
+int mthca_poll_cq(struct ibv_cq *ibcq, int num_entries, struct _uvp_wc *entry)
 {
        struct mthca_cq *cq = to_mcq(ibcq);
        struct mthca_qp *qp = NULL;
@@ -453,9 +454,10 @@ int mthca_poll_cq(struct ibv_cq *ibcq, int num_entries, struct _ib_wc *entry)
        cl_spinlock_acquire(&cq->lock);
 
        for (npolled = 0; npolled < num_entries; ++npolled) {
-               err = mthca_poll_one(cq, &qp, &freed, entry + npolled);
+               err = mthca_poll_one(cq, &qp, &freed, (struct _ib_wc *) (entry + npolled));
                if (err)
                        break;
+               entry[npolled].qp_context = qp->ibv_qp.context;
        }
 
        if (freed) {
index 5ea2dabb394d1c3e2c0d5ecc6f4b3678608a6894..dd9813fb78f404541c8a05cf800a457bc1494bc2 100644 (file)
@@ -446,7 +446,7 @@ struct ibv_context_ops {
                               struct ibv_create_cq *req);
        struct ibv_cq * (*create_cq_post)(struct ibv_context *context, 
                               struct ibv_create_cq_resp *resp);
-       int                     (*poll_cq)(struct ibv_cq *cq, int num_entries, struct _ib_wc *wc);
+       int                     (*poll_cq)(struct ibv_cq *cq, int num_entries, struct _uvp_wc *wc);
        int                     (*poll_cq_list)( struct ibv_cq *ibcq, 
                struct _ib_wc** const                   pp_free_wclist,
                struct _ib_wc** const                   pp_done_wclist );
index 0578c43cd649838a826bf6377e353a0963a7c4cb..d1c84ba7f20bf49f9f9a8e9a07dd9b79cf346d5e 100644 (file)
@@ -1581,6 +1581,24 @@ typedef ib_api_status_t
 *\r
 ********/\r
 \r
+typedef struct _uvp_qp_create\r
+{\r
+       ib_qp_create_t                  qp_create;\r
+\r
+       void                                    *context;\r
+       uint32_t                                max_inline_send;\r
+       uint32_t                                initiator_depth;\r
+       uint32_t                                responder_resources;\r
+\r
+}      uvp_qp_create_t;\r
+\r
+typedef ib_api_status_t\r
+(AL_API *uvp_wv_pre_create_qp) (\r
+       IN              const   ib_pd_handle_t                          h_uvp_pd,\r
+       IN              const   uvp_qp_create_t                         *p_create_attr,\r
+       IN      OUT                     ci_umv_buf_t                            *p_umv_buf,\r
+               OUT                     ib_qp_handle_t                          *ph_uvp_qp);\r
+\r
 /********/\r
 \r
 /****f* user-mode Verbs/uvp_post_create_qp_t\r
@@ -2992,6 +3010,51 @@ typedef ib_api_status_t
 \r
 /********/\r
 \r
+/*\r
+ * Define uvp_wc_t so that we can cast directly to ib_wc_t.\r
+ */\r
+typedef struct _uvp_wc\r
+{\r
+       void*                                   qp_context;\r
+       /* If pointer size is 32-bits, then compiler will pad before uint64_t */\r
+       uint64_t                                wr_id;\r
+       ib_wc_type_t                    wc_type;\r
+\r
+       uint32_t                                length;\r
+       ib_wc_status_t                  status;\r
+       uint64_t                                vendor_specific;\r
+\r
+       union _uvp_wc_recv\r
+       {\r
+               struct _uvp_wc_conn\r
+               {\r
+                       ib_recv_opt_t   recv_opt;\r
+                       ib_net32_t              immediate_data;\r
+\r
+               }       conn;\r
+\r
+               struct _uvp_wc_ud\r
+               {\r
+                       ib_recv_opt_t   recv_opt;\r
+                       ib_net32_t              immediate_data;\r
+                       ib_net32_t              remote_qp;\r
+                       uint16_t                pkey_index;\r
+                       ib_net16_t              remote_lid;\r
+                       uint8_t                 remote_sl;\r
+                       uint8_t                 path_bits;\r
+\r
+               }       ud;\r
+       }       recv;\r
+}      uvp_wc_t;\r
+\r
+typedef int\r
+(AL_API *uvp_poll_cq_array) (\r
+       IN              const   void*                                           h_cq,\r
+       IN              const   int                                                     num_entries,\r
+       IN      OUT                     uvp_wc_t*       const                   wcs);\r
+\r
+/********/\r
+\r
 /****f* user-mode Verbs/uvp_rearm_cq\r
 * NAME\r
 *      uvp_rearm_cq -- Invoke the Completion handler, on next entry added.\r
@@ -3291,7 +3354,7 @@ typedef void
 *\r
 * SOURCE\r
 */\r
-typedef struct _uvp_interface\r
+typedef struct _uvp2_interface\r
 {\r
        ib_net64_t                                      guid;\r
        /*\r
@@ -3435,8 +3498,98 @@ typedef struct _uvp_interface
         */\r
        uvp_nd_modify_qp_t                      nd_modify_qp;\r
        uvp_nd_get_qp_state_t           nd_get_qp_state;\r
+\r
+} uvp2_interface_t;\r
+\r
+typedef struct _uvp_interface\r
+{\r
+       ib_net64_t                                      guid;\r
+       /*\r
+        * Version of the header file this interface export can handle\r
+        */\r
+       uint32_t                                        version;\r
+\r
+       uvp_pre_open_ca_t                       pre_open_ca;\r
+       uvp_post_open_ca_t                      post_open_ca;\r
+       uvp_pre_query_ca                        pre_query_ca;\r
+       uvp_post_query_ca_t                     post_query_ca;\r
+       uvp_pre_modify_ca                       pre_modify_ca;\r
+       uvp_post_modify_ca_t            post_modify_ca;\r
+       uvp_pre_close_ca_t                      pre_close_ca;\r
+       uvp_post_close_ca_t                     post_close_ca;\r
+       uvp_pre_ci_call                         pre_ci_call;\r
+       uvp_post_ci_call                        post_ci_call;\r
+\r
+       uvp_pre_allocate_pd                     pre_allocate_pd;\r
+       uvp_post_allocate_pd_t          post_allocate_pd;\r
+       uvp_pre_deallocate_pd           pre_deallocate_pd;\r
+       uvp_post_deallocate_pd_t        post_deallocate_pd;\r
+\r
+       uvp_pre_create_av                       pre_create_av;\r
+       uvp_post_create_av_t            post_create_av;\r
+       uvp_pre_query_av                        pre_query_av;\r
+       uvp_post_query_av_t                     post_query_av;\r
+       uvp_pre_modify_av                       pre_modify_av;\r
+       uvp_post_modify_av_t            post_modify_av;\r
+       uvp_pre_destroy_av                      pre_destroy_av;\r
+       uvp_post_destroy_av_t           post_destroy_av;\r
+\r
+       uvp_pre_create_srq                      pre_create_srq;\r
+       uvp_post_create_srq_t           post_create_srq;\r
+       uvp_pre_modify_srq                      pre_modify_srq;\r
+       uvp_post_modify_srq_t           post_modify_srq;\r
+       uvp_pre_query_srq                       pre_query_srq;\r
+       uvp_post_query_srq_t            post_query_srq;\r
+       uvp_pre_destroy_srq                     pre_destroy_srq;\r
+       uvp_post_destroy_srq_t          post_destroy_srq;\r
+\r
+       uvp_pre_create_qp                       pre_create_qp;\r
+       uvp_post_create_qp_t            post_create_qp;\r
+       uvp_pre_modify_qp                       pre_modify_qp;\r
+       uvp_post_modify_qp_t            post_modify_qp;\r
+       uvp_pre_query_qp                        pre_query_qp;\r
+       uvp_post_query_qp_t                     post_query_qp;\r
+       uvp_pre_destroy_qp                      pre_destroy_qp;\r
+       uvp_post_destroy_qp_t           post_destroy_qp;\r
+\r
+       uvp_pre_create_cq                       pre_create_cq;\r
+       uvp_post_create_cq_t            post_create_cq;\r
+       uvp_pre_query_cq                        pre_query_cq;\r
+       uvp_post_query_cq_t                     post_query_cq;\r
+       uvp_pre_resize_cq                       pre_resize_cq;\r
+       uvp_post_resize_cq_t            post_resize_cq;\r
+       uvp_pre_destroy_cq                      pre_destroy_cq;\r
+       uvp_post_destroy_cq_t           post_destroy_cq;\r
+\r
+       uvp_pre_create_mw                       pre_create_mw;\r
+       uvp_post_create_mw_t            post_create_mw;\r
+       uvp_pre_query_mw                        pre_query_mw;\r
+       uvp_post_query_mw_t                     post_query_mw;\r
+       uvp_pre_destroy_mw                      pre_destroy_mw;\r
+       uvp_post_destroy_mw_t           post_destroy_mw;\r
+\r
+       uvp_bind_mw                                     bind_mw;\r
+       uvp_post_send                           post_send;\r
+       uvp_post_recv                           post_recv;\r
+       uvp_post_srq_recv                       post_srq_recv;\r
+\r
+       uvp_peek_cq                                     peek_cq;\r
+       uvp_poll_cq                                     poll_cq;\r
+       uvp_rearm_cq                            rearm_cq;\r
+       uvp_rearm_n_cq                          rearm_n_cq;\r
+\r
+       uvp_pre_attach_mcast            pre_attach_mcast;\r
+       uvp_post_attach_mcast           post_attach_mcast;\r
+       uvp_pre_detach_mcast            pre_detach_mcast;\r
+       uvp_post_detach_mcast           post_detach_mcast;\r
+\r
+       uvp_nd_modify_qp_t                      nd_modify_qp;\r
+       uvp_nd_get_qp_state_t           nd_get_qp_state;\r
+\r
+       uvp_wv_pre_create_qp            wv_pre_create_qp;\r
+       uvp_poll_cq_array                       poll_cq_array;\r
        \r
-} uvp_interface_t;\r
+}      uvp_interface_t;\r
 \r
 /********/\r
 \r
@@ -3448,7 +3601,7 @@ typedef struct _uvp_interface
 */\r
 typedef ib_api_status_t\r
 (AL_API *uvp_get_interface_t)(\r
-       IN      OUT                     uvp_interface_t*        const   p_uvp );\r
+       IN      OUT                     uvp2_interface_t*       const   p_uvp );\r
 /*\r
 * DESCRIPTION\r
 *      This routine is called by UAL to get the functions supported by\r
@@ -3461,7 +3614,7 @@ typedef ib_api_status_t
 *\r
 * PARAMETERS\r
 *      p_uvp\r
-*              [in out] Pointer to the uvp_interface_t structure that has the function\r
+*              [in out] Pointer to the uvp2_interface_t structure that has the function\r
 *              vector to support verbs functionality.\r
 *\r
 * RETURN VALUE\r