]> www.infradead.org Git - users/jedix/linux-maple.git/commitdiff
rds_rdma: rds_sendmsg should return EAGAIN if connection not setup
authorWengang Wang <wen.gang.wang@oracle.com>
Tue, 4 Aug 2015 08:00:55 +0000 (16:00 +0800)
committerMukesh Kacker <mukesh.kacker@oracle.com>
Wed, 12 Aug 2015 22:44:34 +0000 (15:44 -0700)
In rds_sendmsg(), in the case RDS_CMSG_RDMA_MAP is requested and
rds_cmsg_send() is called, a "struct rds_mr" needs to be created.
For creating the "struct rds_mr", the connection needs to be
established(ready) for rds_ib_transport. Otherwise, __rds_rdma_map()
would fail because it can't find the right rds_ib_device (which is
associated with the ip address matching rds_sock's bound ip address).
The ip address is set at the completion of the rdma connection.

But actually in code, the connecting is triggered after the call of call
rds_cmsg_send() so rds_cmsg_send() would fail with -NODEV.

The fix is to move the trigger of connection before calling
rds_cmsg_send() and return -EAGAIN in case connection is not
ready yet when we are calling rds_cmsg_send().

Orabug: 21551474

Signed-off-by: Wengang Wang <wen.gang.wang@oracle.com>
Reviewed-by: Chien-Hua Yen <chien.yen@oracle.com>
net/rds/send.c

index a8a2dc0881c9dc8c5c9aeca8781fd1074abe11dc..3174eb02c166e3310b816823016c90845adbacbc 100644 (file)
@@ -1226,11 +1226,6 @@ int rds_sendmsg(struct socket *sock, struct msghdr *msg, size_t payload_len)
 
        rm->m_daddr = daddr;
 
-       /* Parse any control messages the user may have included. */
-       ret = rds_cmsg_send(rs, rm, msg, &allocated_mr);
-       if (ret)
-               goto out;
-
        if (rm->rdma.op_active)
                total_payload_len += rm->rdma.op_bytes;
 
@@ -1318,6 +1313,16 @@ int rds_sendmsg(struct socket *sock, struct msghdr *msg, size_t payload_len)
                goto out;
        }
 
+       if (!rds_conn_up(conn)) {
+               ret = -EAGAIN;
+               goto out;
+       }
+
+       /* Parse any control messages the user may have included. */
+       ret = rds_cmsg_send(rs, rm, msg, &allocated_mr);
+       if (ret)
+               goto out;
+
        while (!rds_send_queue_rm(rs, conn, rm, rs->rs_bound_port,
                                  dport, &queued)) {
                rds_stats_inc(s_send_queue_full);