Commit 7562a13d authored by Karsten Graul's avatar Karsten Graul Committed by David S. Miller

net/smc: multiple link support for rmb buffer registration

The CONFIRM_RKEY LLC processing handles all links in one LLC message.
Move the call to this processing out of smcr_link_reg_rmb() which does
processing per link, into smcr_lgr_reg_rmbs() which is responsible for
link group level processing. Move smcr_link_reg_rmb() into module
smc_core.c.
>From af_smc.c now call smcr_lgr_reg_rmbs() to register new rmbs on all
available links.
Signed-off-by: default avatarKarsten Graul <kgraul@linux.ibm.com>
Reviewed-by: default avatarUrsula Braun <ubraun@linux.ibm.com>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 47c0b580
...@@ -337,46 +337,30 @@ static void smc_copy_sock_settings_to_smc(struct smc_sock *smc) ...@@ -337,46 +337,30 @@ static void smc_copy_sock_settings_to_smc(struct smc_sock *smc)
smc_copy_sock_settings(&smc->sk, smc->clcsock->sk, SK_FLAGS_CLC_TO_SMC); smc_copy_sock_settings(&smc->sk, smc->clcsock->sk, SK_FLAGS_CLC_TO_SMC);
} }
/* register a new rmb, send confirm_rkey msg to register with peer */
static int smcr_link_reg_rmb(struct smc_link *link,
struct smc_buf_desc *rmb_desc, bool conf_rkey)
{
if (!rmb_desc->is_reg_mr[link->link_idx]) {
/* register memory region for new rmb */
if (smc_wr_reg_send(link, rmb_desc->mr_rx[link->link_idx])) {
rmb_desc->is_reg_err = true;
return -EFAULT;
}
rmb_desc->is_reg_mr[link->link_idx] = true;
}
if (!conf_rkey)
return 0;
/* exchange confirm_rkey msg with peer */
if (!rmb_desc->is_conf_rkey) {
if (smc_llc_do_confirm_rkey(link, rmb_desc)) {
rmb_desc->is_reg_err = true;
return -EFAULT;
}
rmb_desc->is_conf_rkey = true;
}
return 0;
}
/* register the new rmb on all links */ /* register the new rmb on all links */
static int smcr_lgr_reg_rmbs(struct smc_link_group *lgr, static int smcr_lgr_reg_rmbs(struct smc_link *link,
struct smc_buf_desc *rmb_desc) struct smc_buf_desc *rmb_desc)
{ {
int i, rc; struct smc_link_group *lgr = link->lgr;
int i, rc = 0;
for (i = 0; i < SMC_LINKS_PER_LGR_MAX; i++) { for (i = 0; i < SMC_LINKS_PER_LGR_MAX; i++) {
if (lgr->lnk[i].state != SMC_LNK_ACTIVE) if (lgr->lnk[i].state != SMC_LNK_ACTIVE)
continue; continue;
rc = smcr_link_reg_rmb(&lgr->lnk[i], rmb_desc, true); rc = smcr_link_reg_rmb(&lgr->lnk[i], rmb_desc);
if (rc) if (rc)
return rc; goto out;
} }
return 0;
/* exchange confirm_rkey msg with peer */
rc = smc_llc_do_confirm_rkey(link, rmb_desc);
if (rc) {
rc = -EFAULT;
goto out;
}
rmb_desc->is_conf_rkey = true;
out:
return rc;
} }
static int smcr_clnt_conf_first_link(struct smc_sock *smc) static int smcr_clnt_conf_first_link(struct smc_sock *smc)
...@@ -408,7 +392,7 @@ static int smcr_clnt_conf_first_link(struct smc_sock *smc) ...@@ -408,7 +392,7 @@ static int smcr_clnt_conf_first_link(struct smc_sock *smc)
smc_wr_remember_qp_attr(link); smc_wr_remember_qp_attr(link);
if (smcr_link_reg_rmb(link, smc->conn.rmb_desc, false)) if (smcr_link_reg_rmb(link, smc->conn.rmb_desc))
return SMC_CLC_DECL_ERR_REGRMB; return SMC_CLC_DECL_ERR_REGRMB;
/* confirm_rkey is implicit on 1st contact */ /* confirm_rkey is implicit on 1st contact */
...@@ -670,7 +654,7 @@ static int smc_connect_rdma(struct smc_sock *smc, ...@@ -670,7 +654,7 @@ static int smc_connect_rdma(struct smc_sock *smc,
return smc_connect_abort(smc, SMC_CLC_DECL_ERR_RDYLNK, return smc_connect_abort(smc, SMC_CLC_DECL_ERR_RDYLNK,
ini->cln_first_contact); ini->cln_first_contact);
} else { } else {
if (smcr_lgr_reg_rmbs(smc->conn.lgr, smc->conn.rmb_desc)) if (smcr_lgr_reg_rmbs(link, smc->conn.rmb_desc))
return smc_connect_abort(smc, SMC_CLC_DECL_ERR_REGRMB, return smc_connect_abort(smc, SMC_CLC_DECL_ERR_REGRMB,
ini->cln_first_contact); ini->cln_first_contact);
} }
...@@ -1045,7 +1029,7 @@ static int smcr_serv_conf_first_link(struct smc_sock *smc) ...@@ -1045,7 +1029,7 @@ static int smcr_serv_conf_first_link(struct smc_sock *smc)
link->lgr->type = SMC_LGR_SINGLE; link->lgr->type = SMC_LGR_SINGLE;
if (smcr_link_reg_rmb(link, smc->conn.rmb_desc, false)) if (smcr_link_reg_rmb(link, smc->conn.rmb_desc))
return SMC_CLC_DECL_ERR_REGRMB; return SMC_CLC_DECL_ERR_REGRMB;
/* send CONFIRM LINK request to client over the RoCE fabric */ /* send CONFIRM LINK request to client over the RoCE fabric */
...@@ -1220,7 +1204,7 @@ static int smc_listen_rdma_reg(struct smc_sock *new_smc, int local_contact) ...@@ -1220,7 +1204,7 @@ static int smc_listen_rdma_reg(struct smc_sock *new_smc, int local_contact)
struct smc_connection *conn = &new_smc->conn; struct smc_connection *conn = &new_smc->conn;
if (local_contact != SMC_FIRST_CONTACT) { if (local_contact != SMC_FIRST_CONTACT) {
if (smcr_lgr_reg_rmbs(conn->lgr, conn->rmb_desc)) if (smcr_lgr_reg_rmbs(conn->lnk, conn->rmb_desc))
return SMC_CLC_DECL_ERR_REGRMB; return SMC_CLC_DECL_ERR_REGRMB;
} }
smc_rmb_sync_sg_for_device(&new_smc->conn); smc_rmb_sync_sg_for_device(&new_smc->conn);
......
...@@ -1127,6 +1127,22 @@ static int smcr_buf_map_link(struct smc_buf_desc *buf_desc, bool is_rmb, ...@@ -1127,6 +1127,22 @@ static int smcr_buf_map_link(struct smc_buf_desc *buf_desc, bool is_rmb,
return rc; return rc;
} }
/* register a new rmb on IB device */
int smcr_link_reg_rmb(struct smc_link *link, struct smc_buf_desc *rmb_desc)
{
if (list_empty(&link->lgr->list))
return -ENOLINK;
if (!rmb_desc->is_reg_mr[link->link_idx]) {
/* register memory region for new rmb */
if (smc_wr_reg_send(link, rmb_desc->mr_rx[link->link_idx])) {
rmb_desc->is_reg_err = true;
return -EFAULT;
}
rmb_desc->is_reg_mr[link->link_idx] = true;
}
return 0;
}
static struct smc_buf_desc *smcr_new_buf_create(struct smc_link_group *lgr, static struct smc_buf_desc *smcr_new_buf_create(struct smc_link_group *lgr,
bool is_rmb, int bufsize) bool is_rmb, int bufsize)
{ {
......
...@@ -367,6 +367,7 @@ void smc_lgr_schedule_free_work_fast(struct smc_link_group *lgr); ...@@ -367,6 +367,7 @@ void smc_lgr_schedule_free_work_fast(struct smc_link_group *lgr);
int smc_core_init(void); int smc_core_init(void);
void smc_core_exit(void); void smc_core_exit(void);
int smcr_link_reg_rmb(struct smc_link *link, struct smc_buf_desc *rmb_desc);
static inline struct smc_link_group *smc_get_lgr(struct smc_link *link) static inline struct smc_link_group *smc_get_lgr(struct smc_link *link)
{ {
return link->lgr; return link->lgr;
......
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