All of lore.kernel.org
 help / color / mirror / Atom feed
From: Ursula Braun <ubraun@linux.ibm.com>
To: davem@davemloft.net
Cc: netdev@vger.kernel.org, linux-s390@vger.kernel.org,
	schwidefsky@de.ibm.com, heiko.carstens@de.ibm.com,
	raspl@linux.ibm.com, hwippel@linux.ibm.com, sebott@linux.ibm.com,
	ubraun@linux.ibm.com
Subject: [PATCH net-next 06/10] net/smc: add SMC-D support in CLC messages
Date: Thu, 28 Jun 2018 19:05:09 +0200	[thread overview]
Message-ID: <20180628170513.5089-7-ubraun@linux.ibm.com> (raw)
In-Reply-To: <20180628170513.5089-1-ubraun@linux.ibm.com>

From: Hans Wippel <hwippel@linux.ibm.com>

There are two types of SMC: SMC-R and SMC-D. These types are signaled
within the CLC messages during the CLC handshake. This patch adds
support for and checks of the SMC type.

Also, SMC-R and SMC-D need to exchange different information during the
CLC handshake. So, this patch extends the current message formats to
support the SMC-D header fields. The Proposal message can contain both
SMC-R and SMC-D information. The Accept and Confirm messages contain
either SMC-R or SMC-D information.

Signed-off-by: Hans Wippel <hwippel@linux.ibm.com>
Signed-off-by: Ursula Braun <ubraun@linux.ibm.com>
Suggested-by: Thomas Richter <tmricht@linux.ibm.com>
---
 net/smc/af_smc.c  |   9 +--
 net/smc/smc_clc.c | 193 ++++++++++++++++++++++++++++++++++++++----------------
 net/smc/smc_clc.h |  81 ++++++++++++++++++-----
 3 files changed, 205 insertions(+), 78 deletions(-)

diff --git a/net/smc/af_smc.c b/net/smc/af_smc.c
index 8ce48799cf68..20afa94be8bb 100644
--- a/net/smc/af_smc.c
+++ b/net/smc/af_smc.c
@@ -451,14 +451,14 @@ static int smc_check_rdma(struct smc_sock *smc, struct smc_ib_device **ibdev,
 }
 
 /* CLC handshake during connect */
-static int smc_connect_clc(struct smc_sock *smc,
+static int smc_connect_clc(struct smc_sock *smc, int smc_type,
 			   struct smc_clc_msg_accept_confirm *aclc,
 			   struct smc_ib_device *ibdev, u8 ibport)
 {
 	int rc = 0;
 
 	/* do inband token exchange */
-	rc = smc_clc_send_proposal(smc, ibdev, ibport);
+	rc = smc_clc_send_proposal(smc, smc_type, ibdev, ibport, NULL);
 	if (rc)
 		return rc;
 	/* receive SMC Accept CLC message */
@@ -564,7 +564,7 @@ static int __smc_connect(struct smc_sock *smc)
 		return smc_connect_decline_fallback(smc, SMC_CLC_DECL_CNFERR);
 
 	/* perform CLC handshake */
-	rc = smc_connect_clc(smc, &aclc, ibdev, ibport);
+	rc = smc_connect_clc(smc, SMC_TYPE_R, &aclc, ibdev, ibport);
 	if (rc)
 		return smc_connect_decline_fallback(smc, rc);
 
@@ -1008,7 +1008,8 @@ static void smc_listen_work(struct work_struct *work)
 	smc_tx_init(new_smc);
 
 	/* check if RDMA is available */
-	if (smc_check_rdma(new_smc, &ibdev, &ibport) ||
+	if ((pclc->hdr.path != SMC_TYPE_R && pclc->hdr.path != SMC_TYPE_B) ||
+	    smc_check_rdma(new_smc, &ibdev, &ibport) ||
 	    smc_listen_rdma_check(new_smc, pclc) ||
 	    smc_listen_rdma_init(new_smc, pclc, ibdev, ibport,
 				 &local_contact) ||
diff --git a/net/smc/smc_clc.c b/net/smc/smc_clc.c
index 717449b1da0b..038d70ef7892 100644
--- a/net/smc/smc_clc.c
+++ b/net/smc/smc_clc.c
@@ -23,9 +23,15 @@
 #include "smc_core.h"
 #include "smc_clc.h"
 #include "smc_ib.h"
+#include "smc_ism.h"
+
+#define SMCR_CLC_ACCEPT_CONFIRM_LEN 68
+#define SMCD_CLC_ACCEPT_CONFIRM_LEN 48
 
 /* eye catcher "SMCR" EBCDIC for CLC messages */
 static const char SMC_EYECATCHER[4] = {'\xe2', '\xd4', '\xc3', '\xd9'};
+/* eye catcher "SMCD" EBCDIC for CLC messages */
+static const char SMCD_EYECATCHER[4] = {'\xe2', '\xd4', '\xc3', '\xc4'};
 
 /* check if received message has a correct header length and contains valid
  * heading and trailing eyecatchers
@@ -38,10 +44,14 @@ static bool smc_clc_msg_hdr_valid(struct smc_clc_msg_hdr *clcm)
 	struct smc_clc_msg_decline *dclc;
 	struct smc_clc_msg_trail *trl;
 
-	if (memcmp(clcm->eyecatcher, SMC_EYECATCHER, sizeof(SMC_EYECATCHER)))
+	if (memcmp(clcm->eyecatcher, SMC_EYECATCHER, sizeof(SMC_EYECATCHER)) &&
+	    memcmp(clcm->eyecatcher, SMCD_EYECATCHER, sizeof(SMCD_EYECATCHER)))
 		return false;
 	switch (clcm->type) {
 	case SMC_CLC_PROPOSAL:
+		if (clcm->path != SMC_TYPE_R && clcm->path != SMC_TYPE_D &&
+		    clcm->path != SMC_TYPE_B)
+			return false;
 		pclc = (struct smc_clc_msg_proposal *)clcm;
 		pclc_prfx = smc_clc_proposal_get_prefix(pclc);
 		if (ntohs(pclc->hdr.length) !=
@@ -56,10 +66,16 @@ static bool smc_clc_msg_hdr_valid(struct smc_clc_msg_hdr *clcm)
 		break;
 	case SMC_CLC_ACCEPT:
 	case SMC_CLC_CONFIRM:
+		if (clcm->path != SMC_TYPE_R && clcm->path != SMC_TYPE_D)
+			return false;
 		clc = (struct smc_clc_msg_accept_confirm *)clcm;
-		if (ntohs(clc->hdr.length) != sizeof(*clc))
+		if ((clcm->path == SMC_TYPE_R &&
+		     ntohs(clc->hdr.length) != SMCR_CLC_ACCEPT_CONFIRM_LEN) ||
+		    (clcm->path == SMC_TYPE_D &&
+		     ntohs(clc->hdr.length) != SMCD_CLC_ACCEPT_CONFIRM_LEN))
 			return false;
-		trl = &clc->trl;
+		trl = (struct smc_clc_msg_trail *)
+			((u8 *)clc + ntohs(clc->hdr.length) - sizeof(*trl));
 		break;
 	case SMC_CLC_DECLINE:
 		dclc = (struct smc_clc_msg_decline *)clcm;
@@ -70,7 +86,8 @@ static bool smc_clc_msg_hdr_valid(struct smc_clc_msg_hdr *clcm)
 	default:
 		return false;
 	}
-	if (memcmp(trl->eyecatcher, SMC_EYECATCHER, sizeof(SMC_EYECATCHER)))
+	if (memcmp(trl->eyecatcher, SMC_EYECATCHER, sizeof(SMC_EYECATCHER)) &&
+	    memcmp(trl->eyecatcher, SMCD_EYECATCHER, sizeof(SMCD_EYECATCHER)))
 		return false;
 	return true;
 }
@@ -295,6 +312,9 @@ int smc_clc_wait_msg(struct smc_sock *smc, void *buf, int buflen,
 	datlen = ntohs(clcm->length);
 	if ((len < sizeof(struct smc_clc_msg_hdr)) ||
 	    (datlen > buflen) ||
+	    (clcm->version != SMC_CLC_V1) ||
+	    (clcm->path != SMC_TYPE_R && clcm->path != SMC_TYPE_D &&
+	     clcm->path != SMC_TYPE_B) ||
 	    ((clcm->type != SMC_CLC_DECLINE) &&
 	     (clcm->type != expected_type))) {
 		smc->sk.sk_err = EPROTO;
@@ -356,17 +376,18 @@ int smc_clc_send_decline(struct smc_sock *smc, u32 peer_diag_info)
 }
 
 /* send CLC PROPOSAL message across internal TCP socket */
-int smc_clc_send_proposal(struct smc_sock *smc,
-			  struct smc_ib_device *smcibdev,
-			  u8 ibport)
+int smc_clc_send_proposal(struct smc_sock *smc, int smc_type,
+			  struct smc_ib_device *ibdev, u8 ibport,
+			  struct smcd_dev *ismdev)
 {
 	struct smc_clc_ipv6_prefix ipv6_prfx[SMC_CLC_MAX_V6_PREFIX];
 	struct smc_clc_msg_proposal_prefix pclc_prfx;
+	struct smc_clc_msg_smcd pclc_smcd;
 	struct smc_clc_msg_proposal pclc;
 	struct smc_clc_msg_trail trl;
 	int len, i, plen, rc;
 	int reason_code = 0;
-	struct kvec vec[4];
+	struct kvec vec[5];
 	struct msghdr msg;
 
 	/* retrieve ip prefixes for CLC proposal msg */
@@ -381,18 +402,34 @@ int smc_clc_send_proposal(struct smc_sock *smc,
 	memset(&pclc, 0, sizeof(pclc));
 	memcpy(pclc.hdr.eyecatcher, SMC_EYECATCHER, sizeof(SMC_EYECATCHER));
 	pclc.hdr.type = SMC_CLC_PROPOSAL;
-	pclc.hdr.length = htons(plen);
 	pclc.hdr.version = SMC_CLC_V1;		/* SMC version */
-	memcpy(pclc.lcl.id_for_peer, local_systemid, sizeof(local_systemid));
-	memcpy(&pclc.lcl.gid, &smcibdev->gid[ibport - 1], SMC_GID_SIZE);
-	memcpy(&pclc.lcl.mac, &smcibdev->mac[ibport - 1], ETH_ALEN);
-	pclc.iparea_offset = htons(0);
+	pclc.hdr.path = smc_type;
+	if (smc_type == SMC_TYPE_R || smc_type == SMC_TYPE_B) {
+		/* add SMC-R specifics */
+		memcpy(pclc.lcl.id_for_peer, local_systemid,
+		       sizeof(local_systemid));
+		memcpy(&pclc.lcl.gid, &ibdev->gid[ibport - 1], SMC_GID_SIZE);
+		memcpy(&pclc.lcl.mac, &ibdev->mac[ibport - 1], ETH_ALEN);
+		pclc.iparea_offset = htons(0);
+	}
+	if (smc_type == SMC_TYPE_D || smc_type == SMC_TYPE_B) {
+		/* add SMC-D specifics */
+		memset(&pclc_smcd, 0, sizeof(pclc_smcd));
+		plen += sizeof(pclc_smcd);
+		pclc.iparea_offset = htons(SMC_CLC_PROPOSAL_MAX_OFFSET);
+		pclc_smcd.gid = ismdev->local_gid;
+	}
+	pclc.hdr.length = htons(plen);
 
 	memcpy(trl.eyecatcher, SMC_EYECATCHER, sizeof(SMC_EYECATCHER));
 	memset(&msg, 0, sizeof(msg));
 	i = 0;
 	vec[i].iov_base = &pclc;
 	vec[i++].iov_len = sizeof(pclc);
+	if (smc_type == SMC_TYPE_D || smc_type == SMC_TYPE_B) {
+		vec[i].iov_base = &pclc_smcd;
+		vec[i++].iov_len = sizeof(pclc_smcd);
+	}
 	vec[i].iov_base = &pclc_prfx;
 	vec[i++].iov_len = sizeof(pclc_prfx);
 	if (pclc_prfx.ipv6_prefixes_cnt > 0) {
@@ -428,35 +465,56 @@ int smc_clc_send_confirm(struct smc_sock *smc)
 	struct kvec vec;
 	int len;
 
-	link = &conn->lgr->lnk[SMC_SINGLE_LINK];
 	/* send SMC Confirm CLC msg */
 	memset(&cclc, 0, sizeof(cclc));
-	memcpy(cclc.hdr.eyecatcher, SMC_EYECATCHER, sizeof(SMC_EYECATCHER));
 	cclc.hdr.type = SMC_CLC_CONFIRM;
-	cclc.hdr.length = htons(sizeof(cclc));
 	cclc.hdr.version = SMC_CLC_V1;		/* SMC version */
-	memcpy(cclc.lcl.id_for_peer, local_systemid, sizeof(local_systemid));
-	memcpy(&cclc.lcl.gid, &link->smcibdev->gid[link->ibport - 1],
-	       SMC_GID_SIZE);
-	memcpy(&cclc.lcl.mac, &link->smcibdev->mac[link->ibport - 1], ETH_ALEN);
-	hton24(cclc.qpn, link->roce_qp->qp_num);
-	cclc.rmb_rkey =
-		htonl(conn->rmb_desc->mr_rx[SMC_SINGLE_LINK]->rkey);
-	cclc.rmbe_idx = 1; /* for now: 1 RMB = 1 RMBE */
-	cclc.rmbe_alert_token = htonl(conn->alert_token_local);
-	cclc.qp_mtu = min(link->path_mtu, link->peer_mtu);
-	cclc.rmbe_size = conn->rmbe_size_short;
-	cclc.rmb_dma_addr = cpu_to_be64(
-		(u64)sg_dma_address(conn->rmb_desc->sgt[SMC_SINGLE_LINK].sgl));
-	hton24(cclc.psn, link->psn_initial);
-
-	memcpy(cclc.trl.eyecatcher, SMC_EYECATCHER, sizeof(SMC_EYECATCHER));
+	if (smc->conn.lgr->is_smcd) {
+		/* SMC-D specific settings */
+		memcpy(cclc.hdr.eyecatcher, SMCD_EYECATCHER,
+		       sizeof(SMCD_EYECATCHER));
+		cclc.hdr.path = SMC_TYPE_D;
+		cclc.hdr.length = htons(SMCD_CLC_ACCEPT_CONFIRM_LEN);
+		cclc.gid = conn->lgr->smcd->local_gid;
+		cclc.token = conn->rmb_desc->token;
+		cclc.dmbe_size = conn->rmbe_size_short;
+		cclc.dmbe_idx = 0;
+		memcpy(&cclc.linkid, conn->lgr->id, SMC_LGR_ID_SIZE);
+		memcpy(cclc.smcd_trl.eyecatcher, SMCD_EYECATCHER,
+		       sizeof(SMCD_EYECATCHER));
+	} else {
+		/* SMC-R specific settings */
+		link = &conn->lgr->lnk[SMC_SINGLE_LINK];
+		memcpy(cclc.hdr.eyecatcher, SMC_EYECATCHER,
+		       sizeof(SMC_EYECATCHER));
+		cclc.hdr.path = SMC_TYPE_R;
+		cclc.hdr.length = htons(SMCR_CLC_ACCEPT_CONFIRM_LEN);
+		memcpy(cclc.lcl.id_for_peer, local_systemid,
+		       sizeof(local_systemid));
+		memcpy(&cclc.lcl.gid, &link->smcibdev->gid[link->ibport - 1],
+		       SMC_GID_SIZE);
+		memcpy(&cclc.lcl.mac, &link->smcibdev->mac[link->ibport - 1],
+		       ETH_ALEN);
+		hton24(cclc.qpn, link->roce_qp->qp_num);
+		cclc.rmb_rkey =
+			htonl(conn->rmb_desc->mr_rx[SMC_SINGLE_LINK]->rkey);
+		cclc.rmbe_idx = 1; /* for now: 1 RMB = 1 RMBE */
+		cclc.rmbe_alert_token = htonl(conn->alert_token_local);
+		cclc.qp_mtu = min(link->path_mtu, link->peer_mtu);
+		cclc.rmbe_size = conn->rmbe_size_short;
+		cclc.rmb_dma_addr = cpu_to_be64((u64)sg_dma_address
+				(conn->rmb_desc->sgt[SMC_SINGLE_LINK].sgl));
+		hton24(cclc.psn, link->psn_initial);
+		memcpy(cclc.smcr_trl.eyecatcher, SMC_EYECATCHER,
+		       sizeof(SMC_EYECATCHER));
+	}
 
 	memset(&msg, 0, sizeof(msg));
 	vec.iov_base = &cclc;
-	vec.iov_len = sizeof(cclc);
-	len = kernel_sendmsg(smc->clcsock, &msg, &vec, 1, sizeof(cclc));
-	if (len < sizeof(cclc)) {
+	vec.iov_len = ntohs(cclc.hdr.length);
+	len = kernel_sendmsg(smc->clcsock, &msg, &vec, 1,
+			     ntohs(cclc.hdr.length));
+	if (len < ntohs(cclc.hdr.length)) {
 		if (len >= 0) {
 			reason_code = -ENETUNREACH;
 			smc->sk.sk_err = -reason_code;
@@ -479,35 +537,58 @@ int smc_clc_send_accept(struct smc_sock *new_smc, int srv_first_contact)
 	int rc = 0;
 	int len;
 
-	link = &conn->lgr->lnk[SMC_SINGLE_LINK];
 	memset(&aclc, 0, sizeof(aclc));
-	memcpy(aclc.hdr.eyecatcher, SMC_EYECATCHER, sizeof(SMC_EYECATCHER));
 	aclc.hdr.type = SMC_CLC_ACCEPT;
-	aclc.hdr.length = htons(sizeof(aclc));
 	aclc.hdr.version = SMC_CLC_V1;		/* SMC version */
 	if (srv_first_contact)
 		aclc.hdr.flag = 1;
-	memcpy(aclc.lcl.id_for_peer, local_systemid, sizeof(local_systemid));
-	memcpy(&aclc.lcl.gid, &link->smcibdev->gid[link->ibport - 1],
-	       SMC_GID_SIZE);
-	memcpy(&aclc.lcl.mac, link->smcibdev->mac[link->ibport - 1], ETH_ALEN);
-	hton24(aclc.qpn, link->roce_qp->qp_num);
-	aclc.rmb_rkey =
-		htonl(conn->rmb_desc->mr_rx[SMC_SINGLE_LINK]->rkey);
-	aclc.rmbe_idx = 1;			/* as long as 1 RMB = 1 RMBE */
-	aclc.rmbe_alert_token = htonl(conn->alert_token_local);
-	aclc.qp_mtu = link->path_mtu;
-	aclc.rmbe_size = conn->rmbe_size_short,
-	aclc.rmb_dma_addr = cpu_to_be64(
-		(u64)sg_dma_address(conn->rmb_desc->sgt[SMC_SINGLE_LINK].sgl));
-	hton24(aclc.psn, link->psn_initial);
-	memcpy(aclc.trl.eyecatcher, SMC_EYECATCHER, sizeof(SMC_EYECATCHER));
+
+	if (new_smc->conn.lgr->is_smcd) {
+		/* SMC-D specific settings */
+		aclc.hdr.length = htons(SMCD_CLC_ACCEPT_CONFIRM_LEN);
+		memcpy(aclc.hdr.eyecatcher, SMCD_EYECATCHER,
+		       sizeof(SMCD_EYECATCHER));
+		aclc.hdr.path = SMC_TYPE_D;
+		aclc.gid = conn->lgr->smcd->local_gid;
+		aclc.token = conn->rmb_desc->token;
+		aclc.dmbe_size = conn->rmbe_size_short;
+		aclc.dmbe_idx = 0;
+		memcpy(&aclc.linkid, conn->lgr->id, SMC_LGR_ID_SIZE);
+		memcpy(aclc.smcd_trl.eyecatcher, SMCD_EYECATCHER,
+		       sizeof(SMCD_EYECATCHER));
+	} else {
+		/* SMC-R specific settings */
+		aclc.hdr.length = htons(SMCR_CLC_ACCEPT_CONFIRM_LEN);
+		memcpy(aclc.hdr.eyecatcher, SMC_EYECATCHER,
+		       sizeof(SMC_EYECATCHER));
+		aclc.hdr.path = SMC_TYPE_R;
+		link = &conn->lgr->lnk[SMC_SINGLE_LINK];
+		memcpy(aclc.lcl.id_for_peer, local_systemid,
+		       sizeof(local_systemid));
+		memcpy(&aclc.lcl.gid, &link->smcibdev->gid[link->ibport - 1],
+		       SMC_GID_SIZE);
+		memcpy(&aclc.lcl.mac, link->smcibdev->mac[link->ibport - 1],
+		       ETH_ALEN);
+		hton24(aclc.qpn, link->roce_qp->qp_num);
+		aclc.rmb_rkey =
+			htonl(conn->rmb_desc->mr_rx[SMC_SINGLE_LINK]->rkey);
+		aclc.rmbe_idx = 1;		/* as long as 1 RMB = 1 RMBE */
+		aclc.rmbe_alert_token = htonl(conn->alert_token_local);
+		aclc.qp_mtu = link->path_mtu;
+		aclc.rmbe_size = conn->rmbe_size_short,
+		aclc.rmb_dma_addr = cpu_to_be64((u64)sg_dma_address
+				(conn->rmb_desc->sgt[SMC_SINGLE_LINK].sgl));
+		hton24(aclc.psn, link->psn_initial);
+		memcpy(aclc.smcr_trl.eyecatcher, SMC_EYECATCHER,
+		       sizeof(SMC_EYECATCHER));
+	}
 
 	memset(&msg, 0, sizeof(msg));
 	vec.iov_base = &aclc;
-	vec.iov_len = sizeof(aclc);
-	len = kernel_sendmsg(new_smc->clcsock, &msg, &vec, 1, sizeof(aclc));
-	if (len < sizeof(aclc)) {
+	vec.iov_len = ntohs(aclc.hdr.length);
+	len = kernel_sendmsg(new_smc->clcsock, &msg, &vec, 1,
+			     ntohs(aclc.hdr.length));
+	if (len < ntohs(aclc.hdr.length)) {
 		if (len >= 0)
 			new_smc->sk.sk_err = EPROTO;
 		else
diff --git a/net/smc/smc_clc.h b/net/smc/smc_clc.h
index 41ff9ea96139..100e988ad1a8 100644
--- a/net/smc/smc_clc.h
+++ b/net/smc/smc_clc.h
@@ -23,6 +23,9 @@
 #define SMC_CLC_DECLINE		0x04
 
 #define SMC_CLC_V1		0x1		/* SMC version                */
+#define SMC_TYPE_R		0		/* SMC-R only		      */
+#define SMC_TYPE_D		1		/* SMC-D only		      */
+#define SMC_TYPE_B		3		/* SMC-R and SMC-D	      */
 #define CLC_WAIT_TIME		(6 * HZ)	/* max. wait time on clcsock  */
 #define SMC_CLC_DECL_MEM	0x01010000  /* insufficient memory resources  */
 #define SMC_CLC_DECL_TIMEOUT	0x02000000  /* timeout                        */
@@ -42,9 +45,11 @@ struct smc_clc_msg_hdr {	/* header1 of clc messages */
 #if defined(__BIG_ENDIAN_BITFIELD)
 	u8 version : 4,
 	   flag    : 1,
-	   rsvd    : 3;
+	   rsvd	   : 1,
+	   path	   : 2;
 #elif defined(__LITTLE_ENDIAN_BITFIELD)
-	u8 rsvd    : 3,
+	u8 path    : 2,
+	   rsvd    : 1,
 	   flag    : 1,
 	   version : 4;
 #endif
@@ -77,6 +82,11 @@ struct smc_clc_msg_proposal_prefix {	/* prefix part of clc proposal message*/
 	u8 ipv6_prefixes_cnt;	/* number of IPv6 prefixes in prefix array */
 } __aligned(4);
 
+struct smc_clc_msg_smcd {	/* SMC-D GID information */
+	u64 gid;		/* ISM GID of requestor */
+	u8 res[32];
+};
+
 struct smc_clc_msg_proposal {	/* clc proposal message sent by Linux */
 	struct smc_clc_msg_hdr hdr;
 	struct smc_clc_msg_local lcl;
@@ -94,23 +104,45 @@ struct smc_clc_msg_proposal {	/* clc proposal message sent by Linux */
 
 struct smc_clc_msg_accept_confirm {	/* clc accept / confirm message */
 	struct smc_clc_msg_hdr hdr;
-	struct smc_clc_msg_local lcl;
-	u8 qpn[3];		/* QP number */
-	__be32 rmb_rkey;	/* RMB rkey */
-	u8 rmbe_idx;		/* Index of RMBE in RMB */
-	__be32 rmbe_alert_token;/* unique connection id */
+	union {
+		struct { /* SMC-R */
+			struct smc_clc_msg_local lcl;
+			u8 qpn[3];		/* QP number */
+			__be32 rmb_rkey;	/* RMB rkey */
+			u8 rmbe_idx;		/* Index of RMBE in RMB */
+			__be32 rmbe_alert_token;/* unique connection id */
 #if defined(__BIG_ENDIAN_BITFIELD)
-	u8 rmbe_size : 4,	/* RMBE buf size (compressed notation) */
-	   qp_mtu   : 4;	/* QP mtu */
+			u8 rmbe_size : 4,	/* buf size (compressed) */
+			   qp_mtu   : 4;	/* QP mtu */
 #elif defined(__LITTLE_ENDIAN_BITFIELD)
-	u8 qp_mtu   : 4,
-	   rmbe_size : 4;
+			u8 qp_mtu   : 4,
+			   rmbe_size : 4;
 #endif
-	u8 reserved;
-	__be64 rmb_dma_addr;	/* RMB virtual address */
-	u8 reserved2;
-	u8 psn[3];		/* initial packet sequence number */
-	struct smc_clc_msg_trail trl; /* eye catcher "SMCR" EBCDIC */
+			u8 reserved;
+			__be64 rmb_dma_addr;	/* RMB virtual address */
+			u8 reserved2;
+			u8 psn[3];		/* packet sequence number */
+			struct smc_clc_msg_trail smcr_trl;
+						/* eye catcher "SMCR" EBCDIC */
+		} __packed;
+		struct { /* SMC-D */
+			u64 gid;		/* Sender GID */
+			u64 token;		/* DMB token */
+			u8 dmbe_idx;		/* DMBE index */
+#if defined(__BIG_ENDIAN_BITFIELD)
+			u8 dmbe_size : 4,	/* buf size (compressed) */
+			   reserved3 : 4;
+#elif defined(__LITTLE_ENDIAN_BITFIELD)
+			u8 reserved3 : 4,
+			   dmbe_size : 4;
+#endif
+			u16 reserved4;
+			u32 linkid;		/* Link identifier */
+			u32 reserved5[3];
+			struct smc_clc_msg_trail smcd_trl;
+						/* eye catcher "SMCD" EBCDIC */
+		} __packed;
+	};
 } __packed;			/* format defined in RFC7609 */
 
 struct smc_clc_msg_decline {	/* clc decline message */
@@ -129,13 +161,26 @@ smc_clc_proposal_get_prefix(struct smc_clc_msg_proposal *pclc)
 	       ((u8 *)pclc + sizeof(*pclc) + ntohs(pclc->iparea_offset));
 }
 
+/* get SMC-D info from proposal message */
+static inline struct smc_clc_msg_smcd *
+smc_get_clc_msg_smcd(struct smc_clc_msg_proposal *prop)
+{
+	if (ntohs(prop->iparea_offset) != sizeof(struct smc_clc_msg_smcd))
+		return NULL;
+
+	return (struct smc_clc_msg_smcd *)(prop + 1);
+}
+
+struct smcd_dev;
+
 int smc_clc_prfx_match(struct socket *clcsock,
 		       struct smc_clc_msg_proposal_prefix *prop);
 int smc_clc_wait_msg(struct smc_sock *smc, void *buf, int buflen,
 		     u8 expected_type);
 int smc_clc_send_decline(struct smc_sock *smc, u32 peer_diag_info);
-int smc_clc_send_proposal(struct smc_sock *smc, struct smc_ib_device *smcibdev,
-			  u8 ibport);
+int smc_clc_send_proposal(struct smc_sock *smc, int smc_type,
+			  struct smc_ib_device *smcibdev, u8 ibport,
+			  struct smcd_dev *ismdev);
 int smc_clc_send_confirm(struct smc_sock *smc);
 int smc_clc_send_accept(struct smc_sock *smc, int srv_first_contact);
 
-- 
2.16.4

  parent reply	other threads:[~2018-06-28 17:05 UTC|newest]

Thread overview: 12+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2018-06-28 17:05 [PATCH net-next 00/10] pnetid and SMC-D support Ursula Braun
2018-06-28 17:05 ` [PATCH net-next 01/10] net/smc: determine port attributes independent from pnet table Ursula Braun
2018-06-28 17:05 ` [PATCH net-next 02/10] net/smc: add pnetid support Ursula Braun
2018-06-28 17:05 ` [PATCH net-next 03/10] net/smc: optimize consumer cursor updates Ursula Braun
2018-06-28 17:05 ` [PATCH net-next 04/10] net/smc: add base infrastructure for SMC-D and ISM Ursula Braun
2018-06-28 17:05 ` [PATCH net-next 05/10] net/smc: add pnetid support " Ursula Braun
2018-06-28 17:05 ` Ursula Braun [this message]
2018-06-28 17:05 ` [PATCH net-next 07/10] net/smc: add SMC-D support in data transfer Ursula Braun
2018-06-28 17:05 ` [PATCH net-next 08/10] net/smc: add SMC-D support in af_smc Ursula Braun
2018-06-28 17:05 ` [PATCH net-next 09/10] net/smc: add SMC-D diag support Ursula Braun
2018-06-28 17:05 ` [PATCH net-next 10/10] s390/ism: add device driver for internal shared memory Ursula Braun
2018-06-30 11:46 ` [PATCH net-next 00/10] pnetid and SMC-D support David Miller

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20180628170513.5089-7-ubraun@linux.ibm.com \
    --to=ubraun@linux.ibm.com \
    --cc=davem@davemloft.net \
    --cc=heiko.carstens@de.ibm.com \
    --cc=hwippel@linux.ibm.com \
    --cc=linux-s390@vger.kernel.org \
    --cc=netdev@vger.kernel.org \
    --cc=raspl@linux.ibm.com \
    --cc=schwidefsky@de.ibm.com \
    --cc=sebott@linux.ibm.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.