RDMA/cm: Use SLID in the work completion as the DLID in responder side
authorMark Zhang <markzhang@nvidia.com>
Thu, 8 Sep 2022 10:09:02 +0000 (13:09 +0300)
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Wed, 26 Oct 2022 10:35:13 +0000 (12:35 +0200)
[ Upstream commit b7d95040c13f61a4a6a859c5355faf583eff9658 ]

The responder should always use WC's SLID as the dlid, to follow the
IB SPEC section "13.5.4.2 COMMON RESPONSE ACTIONS":
A responder always takes the following actions in constructing a
response packet:
- The SLID of the received packet is used as the DLID in the response
  packet.

Fixes: ac3a949fb2ff ("IB/CM: Set appropriate slid and dlid when handling CM request")
Signed-off-by: Mark Zhang <markzhang@nvidia.com>
Reviewed-by: Mark Bloch <mbloch@nvidia.com>
Link: https://lore.kernel.org/r/cd17c240231e059d2fc07c17dfe555d548b917eb.1662631201.git.leonro@nvidia.com
Signed-off-by: Leon Romanovsky <leon@kernel.org>
Signed-off-by: Sasha Levin <sashal@kernel.org>
drivers/infiniband/core/cm.c

index b985e0d..5c910f5 100644 (file)
@@ -1632,14 +1632,13 @@ static void cm_path_set_rec_type(struct ib_device *ib_device, u32 port_num,
 
 static void cm_format_path_lid_from_req(struct cm_req_msg *req_msg,
                                        struct sa_path_rec *primary_path,
-                                       struct sa_path_rec *alt_path)
+                                       struct sa_path_rec *alt_path,
+                                       struct ib_wc *wc)
 {
        u32 lid;
 
        if (primary_path->rec_type != SA_PATH_REC_TYPE_OPA) {
-               sa_path_set_dlid(primary_path,
-                                IBA_GET(CM_REQ_PRIMARY_LOCAL_PORT_LID,
-                                        req_msg));
+               sa_path_set_dlid(primary_path, wc->slid);
                sa_path_set_slid(primary_path,
                                 IBA_GET(CM_REQ_PRIMARY_REMOTE_PORT_LID,
                                         req_msg));
@@ -1676,7 +1675,8 @@ static void cm_format_path_lid_from_req(struct cm_req_msg *req_msg,
 
 static void cm_format_paths_from_req(struct cm_req_msg *req_msg,
                                     struct sa_path_rec *primary_path,
-                                    struct sa_path_rec *alt_path)
+                                    struct sa_path_rec *alt_path,
+                                    struct ib_wc *wc)
 {
        primary_path->dgid =
                *IBA_GET_MEM_PTR(CM_REQ_PRIMARY_LOCAL_PORT_GID, req_msg);
@@ -1734,7 +1734,7 @@ static void cm_format_paths_from_req(struct cm_req_msg *req_msg,
                if (sa_path_is_roce(alt_path))
                        alt_path->roce.route_resolved = false;
        }
-       cm_format_path_lid_from_req(req_msg, primary_path, alt_path);
+       cm_format_path_lid_from_req(req_msg, primary_path, alt_path, wc);
 }
 
 static u16 cm_get_bth_pkey(struct cm_work *work)
@@ -2148,7 +2148,7 @@ static int cm_req_handler(struct cm_work *work)
        if (cm_req_has_alt_path(req_msg))
                work->path[1].rec_type = work->path[0].rec_type;
        cm_format_paths_from_req(req_msg, &work->path[0],
-                                &work->path[1]);
+                                &work->path[1], work->mad_recv_wc->wc);
        if (cm_id_priv->av.ah_attr.type == RDMA_AH_ATTR_TYPE_ROCE)
                sa_path_set_dmac(&work->path[0],
                                 cm_id_priv->av.ah_attr.roce.dmac);