Skip to content

Commit 9da82dc

Browse files
metze-sambasmfrench
authored andcommitted
smb: server: let send_done handle a completion without IB_SEND_SIGNALED
With smbdirect_send_batch processing we likely have requests without IB_SEND_SIGNALED, which will be destroyed in the final request that has IB_SEND_SIGNALED set. If the connection is broken all requests are signaled even without explicit IB_SEND_SIGNALED. Cc: <stable@vger.kernel.org> # 6.18.x Cc: Namjae Jeon <linkinjeon@kernel.org> Cc: Steve French <smfrench@gmail.com> Cc: Tom Talpey <tom@talpey.com> Cc: linux-cifs@vger.kernel.org Cc: samba-technical@lists.samba.org Signed-off-by: Stefan Metzmacher <metze@samba.org> Acked-by: Namjae Jeon <linkinjeon@kernel.org> Signed-off-by: Steve French <stfrench@microsoft.com>
1 parent 8cf2bba commit 9da82dc

1 file changed

Lines changed: 26 additions & 0 deletions

File tree

fs/smb/server/transport_rdma.c

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1059,6 +1059,31 @@ static void send_done(struct ib_cq *cq, struct ib_wc *wc)
10591059
ib_wc_status_msg(wc->status), wc->status,
10601060
wc->opcode);
10611061

1062+
if (unlikely(!(sendmsg->wr.send_flags & IB_SEND_SIGNALED))) {
1063+
/*
1064+
* This happens when smbdirect_send_io is a sibling
1065+
* before the final message, it is signaled on
1066+
* error anyway, so we need to skip
1067+
* smbdirect_connection_free_send_io here,
1068+
* otherwise is will destroy the memory
1069+
* of the siblings too, which will cause
1070+
* use after free problems for the others
1071+
* triggered from ib_drain_qp().
1072+
*/
1073+
if (wc->status != IB_WC_SUCCESS)
1074+
goto skip_free;
1075+
1076+
/*
1077+
* This should not happen!
1078+
* But we better just close the
1079+
* connection...
1080+
*/
1081+
pr_err("unexpected send completion wc->status=%s (%d) wc->opcode=%d\n",
1082+
ib_wc_status_msg(wc->status), wc->status, wc->opcode);
1083+
smb_direct_disconnect_rdma_connection(sc);
1084+
return;
1085+
}
1086+
10621087
/*
10631088
* Free possible siblings and then the main send_io
10641089
*/
@@ -1072,6 +1097,7 @@ static void send_done(struct ib_cq *cq, struct ib_wc *wc)
10721097
lcredits += 1;
10731098

10741099
if (wc->status != IB_WC_SUCCESS || wc->opcode != IB_WC_SEND) {
1100+
skip_free:
10751101
pr_err("Send error. status='%s (%d)', opcode=%d\n",
10761102
ib_wc_status_msg(wc->status), wc->status,
10771103
wc->opcode);

0 commit comments

Comments
 (0)