Commit ec34f792 authored by David S. Miller's avatar David S. Miller

Merge branch 'smc-fixes'

Ursula Braun says:

====================
net/smc: fixes 2019-01-30

here are some fixes in different areas of the smc code for the net
tree.
====================
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parents 7596175e 46ad0222
...@@ -1505,6 +1505,11 @@ static int smc_recvmsg(struct socket *sock, struct msghdr *msg, size_t len, ...@@ -1505,6 +1505,11 @@ static int smc_recvmsg(struct socket *sock, struct msghdr *msg, size_t len,
smc = smc_sk(sk); smc = smc_sk(sk);
lock_sock(sk); lock_sock(sk);
if (sk->sk_state == SMC_CLOSED && (sk->sk_shutdown & RCV_SHUTDOWN)) {
/* socket was connected before, no more data to read */
rc = 0;
goto out;
}
if ((sk->sk_state == SMC_INIT) || if ((sk->sk_state == SMC_INIT) ||
(sk->sk_state == SMC_LISTEN) || (sk->sk_state == SMC_LISTEN) ||
(sk->sk_state == SMC_CLOSED)) (sk->sk_state == SMC_CLOSED))
...@@ -1840,7 +1845,11 @@ static ssize_t smc_splice_read(struct socket *sock, loff_t *ppos, ...@@ -1840,7 +1845,11 @@ static ssize_t smc_splice_read(struct socket *sock, loff_t *ppos,
smc = smc_sk(sk); smc = smc_sk(sk);
lock_sock(sk); lock_sock(sk);
if (sk->sk_state == SMC_CLOSED && (sk->sk_shutdown & RCV_SHUTDOWN)) {
/* socket was connected before, no more data to read */
rc = 0;
goto out;
}
if (sk->sk_state == SMC_INIT || if (sk->sk_state == SMC_INIT ||
sk->sk_state == SMC_LISTEN || sk->sk_state == SMC_LISTEN ||
sk->sk_state == SMC_CLOSED) sk->sk_state == SMC_CLOSED)
......
...@@ -125,7 +125,10 @@ static int smcr_cdc_get_slot_and_msg_send(struct smc_connection *conn) ...@@ -125,7 +125,10 @@ static int smcr_cdc_get_slot_and_msg_send(struct smc_connection *conn)
if (rc) if (rc)
return rc; return rc;
return smc_cdc_msg_send(conn, wr_buf, pend); spin_lock_bh(&conn->send_lock);
rc = smc_cdc_msg_send(conn, wr_buf, pend);
spin_unlock_bh(&conn->send_lock);
return rc;
} }
int smc_cdc_get_slot_and_msg_send(struct smc_connection *conn) int smc_cdc_get_slot_and_msg_send(struct smc_connection *conn)
......
...@@ -378,7 +378,7 @@ int smc_clc_send_decline(struct smc_sock *smc, u32 peer_diag_info) ...@@ -378,7 +378,7 @@ int smc_clc_send_decline(struct smc_sock *smc, u32 peer_diag_info)
vec.iov_len = sizeof(struct smc_clc_msg_decline); vec.iov_len = sizeof(struct smc_clc_msg_decline);
len = kernel_sendmsg(smc->clcsock, &msg, &vec, 1, len = kernel_sendmsg(smc->clcsock, &msg, &vec, 1,
sizeof(struct smc_clc_msg_decline)); sizeof(struct smc_clc_msg_decline));
if (len < sizeof(struct smc_clc_msg_decline)) if (len < 0 || len < sizeof(struct smc_clc_msg_decline))
len = -EPROTO; len = -EPROTO;
return len > 0 ? 0 : len; return len > 0 ? 0 : len;
} }
......
...@@ -128,6 +128,8 @@ static void smc_lgr_unregister_conn(struct smc_connection *conn) ...@@ -128,6 +128,8 @@ static void smc_lgr_unregister_conn(struct smc_connection *conn)
{ {
struct smc_link_group *lgr = conn->lgr; struct smc_link_group *lgr = conn->lgr;
if (!lgr)
return;
write_lock_bh(&lgr->conns_lock); write_lock_bh(&lgr->conns_lock);
if (conn->alert_token_local) { if (conn->alert_token_local) {
__smc_lgr_unregister_conn(conn); __smc_lgr_unregister_conn(conn);
...@@ -628,6 +630,8 @@ int smc_conn_create(struct smc_sock *smc, bool is_smcd, int srv_first_contact, ...@@ -628,6 +630,8 @@ int smc_conn_create(struct smc_sock *smc, bool is_smcd, int srv_first_contact,
local_contact = SMC_REUSE_CONTACT; local_contact = SMC_REUSE_CONTACT;
conn->lgr = lgr; conn->lgr = lgr;
smc_lgr_register_conn(conn); /* add smc conn to lgr */ smc_lgr_register_conn(conn); /* add smc conn to lgr */
if (delayed_work_pending(&lgr->free_work))
cancel_delayed_work(&lgr->free_work);
write_unlock_bh(&lgr->conns_lock); write_unlock_bh(&lgr->conns_lock);
break; break;
} }
......
...@@ -289,8 +289,8 @@ int smc_ib_create_protection_domain(struct smc_link *lnk) ...@@ -289,8 +289,8 @@ int smc_ib_create_protection_domain(struct smc_link *lnk)
static void smc_ib_qp_event_handler(struct ib_event *ibevent, void *priv) static void smc_ib_qp_event_handler(struct ib_event *ibevent, void *priv)
{ {
struct smc_ib_device *smcibdev = struct smc_link *lnk = (struct smc_link *)priv;
(struct smc_ib_device *)ibevent->device; struct smc_ib_device *smcibdev = lnk->smcibdev;
u8 port_idx; u8 port_idx;
switch (ibevent->event) { switch (ibevent->event) {
...@@ -298,7 +298,7 @@ static void smc_ib_qp_event_handler(struct ib_event *ibevent, void *priv) ...@@ -298,7 +298,7 @@ static void smc_ib_qp_event_handler(struct ib_event *ibevent, void *priv)
case IB_EVENT_GID_CHANGE: case IB_EVENT_GID_CHANGE:
case IB_EVENT_PORT_ERR: case IB_EVENT_PORT_ERR:
case IB_EVENT_QP_ACCESS_ERR: case IB_EVENT_QP_ACCESS_ERR:
port_idx = ibevent->element.port_num - 1; port_idx = ibevent->element.qp->port - 1;
set_bit(port_idx, &smcibdev->port_event_mask); set_bit(port_idx, &smcibdev->port_event_mask);
schedule_work(&smcibdev->port_event_work); schedule_work(&smcibdev->port_event_work);
break; break;
......
...@@ -27,7 +27,7 @@ ...@@ -27,7 +27,7 @@
static struct nla_policy smc_pnet_policy[SMC_PNETID_MAX + 1] = { static struct nla_policy smc_pnet_policy[SMC_PNETID_MAX + 1] = {
[SMC_PNETID_NAME] = { [SMC_PNETID_NAME] = {
.type = NLA_NUL_STRING, .type = NLA_NUL_STRING,
.len = SMC_MAX_PNETID_LEN - 1 .len = SMC_MAX_PNETID_LEN
}, },
[SMC_PNETID_ETHNAME] = { [SMC_PNETID_ETHNAME] = {
.type = NLA_NUL_STRING, .type = NLA_NUL_STRING,
......
...@@ -165,12 +165,11 @@ int smc_tx_sendmsg(struct smc_sock *smc, struct msghdr *msg, size_t len) ...@@ -165,12 +165,11 @@ int smc_tx_sendmsg(struct smc_sock *smc, struct msghdr *msg, size_t len)
conn->local_tx_ctrl.prod_flags.urg_data_pending = 1; conn->local_tx_ctrl.prod_flags.urg_data_pending = 1;
if (!atomic_read(&conn->sndbuf_space) || conn->urg_tx_pend) { if (!atomic_read(&conn->sndbuf_space) || conn->urg_tx_pend) {
if (send_done)
return send_done;
rc = smc_tx_wait(smc, msg->msg_flags); rc = smc_tx_wait(smc, msg->msg_flags);
if (rc) { if (rc)
if (send_done)
return send_done;
goto out_err; goto out_err;
}
continue; continue;
} }
...@@ -489,25 +488,23 @@ static int smcr_tx_sndbuf_nonempty(struct smc_connection *conn) ...@@ -489,25 +488,23 @@ static int smcr_tx_sndbuf_nonempty(struct smc_connection *conn)
struct smc_wr_buf *wr_buf; struct smc_wr_buf *wr_buf;
int rc; int rc;
spin_lock_bh(&conn->send_lock);
rc = smc_cdc_get_free_slot(conn, &wr_buf, &pend); rc = smc_cdc_get_free_slot(conn, &wr_buf, &pend);
if (rc < 0) { if (rc < 0) {
if (rc == -EBUSY) { if (rc == -EBUSY) {
struct smc_sock *smc = struct smc_sock *smc =
container_of(conn, struct smc_sock, conn); container_of(conn, struct smc_sock, conn);
if (smc->sk.sk_err == ECONNABORTED) { if (smc->sk.sk_err == ECONNABORTED)
rc = sock_error(&smc->sk); return sock_error(&smc->sk);
goto out_unlock;
}
rc = 0; rc = 0;
if (conn->alert_token_local) /* connection healthy */ if (conn->alert_token_local) /* connection healthy */
mod_delayed_work(system_wq, &conn->tx_work, mod_delayed_work(system_wq, &conn->tx_work,
SMC_TX_WORK_DELAY); SMC_TX_WORK_DELAY);
} }
goto out_unlock; return rc;
} }
spin_lock_bh(&conn->send_lock);
if (!conn->local_tx_ctrl.prod_flags.urg_data_present) { if (!conn->local_tx_ctrl.prod_flags.urg_data_present) {
rc = smc_tx_rdma_writes(conn); rc = smc_tx_rdma_writes(conn);
if (rc) { if (rc) {
......
...@@ -218,10 +218,10 @@ int smc_wr_tx_put_slot(struct smc_link *link, ...@@ -218,10 +218,10 @@ int smc_wr_tx_put_slot(struct smc_link *link,
u32 idx = pend->idx; u32 idx = pend->idx;
/* clear the full struct smc_wr_tx_pend including .priv */ /* clear the full struct smc_wr_tx_pend including .priv */
memset(&link->wr_tx_pends[pend->idx], 0, memset(&link->wr_tx_pends[idx], 0,
sizeof(link->wr_tx_pends[pend->idx])); sizeof(link->wr_tx_pends[idx]));
memset(&link->wr_tx_bufs[pend->idx], 0, memset(&link->wr_tx_bufs[idx], 0,
sizeof(link->wr_tx_bufs[pend->idx])); sizeof(link->wr_tx_bufs[idx]));
test_and_clear_bit(idx, link->wr_tx_mask); test_and_clear_bit(idx, link->wr_tx_mask);
return 1; return 1;
} }
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment