[openib-general] [PATCH] [SRP] srp_cm_handler expanded response handling

John Kingman kingman at austin.rr.com
Thu Oct 27 13:41:04 PDT 2005


This patch expands the srp_cm_handler code to recognize more response
cases and provides a place holder for future code to handle SRP target
exceptions such as IB_CM_REJ_CONSUMER_DEFINED with reason code
0x00010002 (requested max_it_iu_len too large).

Patch has been tested with our target.

Signed-off-by: John Kingman <kingman at storagegear.com>

Index: ib_srp.c
===================================================================
--- ib_srp.c	(revision 3883)
+++ ib_srp.c	(working copy)
@@ -975,6 +975,7 @@ static int srp_cm_handler(struct ib_cm_i
 	struct ib_qp_attr *qp_attr = NULL;
 	int attr_mask = 0;
 	int comp = 0;
+	int rsp_opcode = 0;
 
 	switch (event->event) {
 	case IB_CM_REQ_ERROR:
@@ -985,17 +986,20 @@ static int srp_cm_handler(struct ib_cm_i
 
 	case IB_CM_REP_RECEIVED:
 		comp = 1;
+		rsp_opcode = *(u8 *) event->private_data;
 
-		{
+		if (rsp_opcode == SRP_LOGIN_RSP) {
 			struct srp_login_rsp *rsp = event->private_data;
 
-			/* XXX check that opcode is SRP RSP */
-
 			target->max_ti_iu_len = be32_to_cpu(rsp->max_ti_iu_len);
 			target->req_lim       = be32_to_cpu(rsp->req_lim_delta);
 
 			target->scsi_host->can_queue = min(target->req_lim,
 							   target->scsi_host->can_queue);
+		} else {
+			printk(KERN_WARNING PFX "Unhandled RSP opcode %#x\n", rsp_opcode);
+			target->status = -ECONNRESET;
+			break;
 		}
 
 		target->status = srp_alloc_iu_bufs(target);
@@ -1043,7 +1047,8 @@ static int srp_cm_handler(struct ib_cm_i
 		printk(KERN_DEBUG PFX "REJ received\n");
 		comp = 1;
 
-		if (event->param.rej_rcvd.reason == IB_CM_REJ_PORT_CM_REDIRECT) {
+		switch (event->param.rej_rcvd.reason) {
+		case IB_CM_REJ_PORT_CM_REDIRECT:
 			cpi = event->param.rej_rcvd.ari;
 			target->path.dlid = cpi->redirect_lid;
 			target->path.pkey = cpi->redirect_pkey;
@@ -1052,23 +1057,52 @@ static int srp_cm_handler(struct ib_cm_i
 
 			target->status = target->path.dlid ?
 				SRP_DLID_REDIRECT : SRP_PORT_REDIRECT;
-		} else if (topspin_workarounds &&
-			   !memcmp(&target->ioc_guid, topspin_oui, 3) &&
-			   event->param.rej_rcvd.reason == IB_CM_REJ_PORT_REDIRECT) {
-			/*
-			 * Topspin/Cisco SRP gateways incorrectly send
-			 * reject reason code 25 when they mean 24
-			 * (port redirect).
-			 */
-			memcpy(target->path.dgid.raw,
-			       event->param.rej_rcvd.ari, 16);
-
-			printk(KERN_DEBUG PFX "Topspin/Cisco redirect to target port GID %016llx%016llx\n",
-			       (unsigned long long) be64_to_cpu(target->path.dgid.global.subnet_prefix),
-			       (unsigned long long) be64_to_cpu(target->path.dgid.global.interface_id));
+			break;
 
-			target->status = SRP_PORT_REDIRECT;
-		} else {
+		case IB_CM_REJ_PORT_REDIRECT:
+			if (topspin_workarounds &&
+			   !memcmp(&target->ioc_guid, topspin_oui, 3)) {
+				/*
+				 * Topspin/Cisco SRP gateways incorrectly send
+				 * reject reason code 25 when they mean 24
+				 * (port redirect).
+				 */
+				memcpy(target->path.dgid.raw,
+				       event->param.rej_rcvd.ari, 16);
+
+				printk(KERN_DEBUG PFX "Topspin/Cisco redirect to target port GID %016llx%016llx\n",
+				       (unsigned long long) be64_to_cpu(target->path.dgid.global.subnet_prefix),
+				       (unsigned long long) be64_to_cpu(target->path.dgid.global.interface_id));
+
+				target->status = SRP_PORT_REDIRECT;
+			} else {
+				printk(KERN_WARNING "  REJ reason: IB_CM_REJ_PORT_REDIRECT\n");
+				target->status = -ECONNRESET;
+			}
+			break;
+
+		case IB_CM_REJ_DUPLICATE_LOCAL_COMM_ID:
+			printk(KERN_WARNING "  REJ reason: IB_CM_REJ_DUPLICATE_LOCAL_COMM_ID\n");
+			target->status = -ECONNRESET;
+			break;
+
+		case IB_CM_REJ_CONSUMER_DEFINED:
+			if(*(u8 *) event->private_data == SRP_LOGIN_REJ) {
+				struct srp_login_rej *rej = event->private_data;
+				u32 reason = be32_to_cpu(rej->reason);
+
+				if (reason == 0x00010002)  
+					printk(KERN_WARNING PFX 
+					       "SRP_LOGIN_REJ: requested max_it_iu_len too large\n");
+				else
+					printk(KERN_WARNING PFX 
+					       "SRP LOGIN REJECTED, reason 0x%8.8x\n", reason);
+			} else
+				printk(KERN_WARNING "  REJ reason: IB_CM_REJ_CONSUMER_DEFINED\n");
+			target->status = -ECONNRESET;
+			break;
+
+		default:
 			printk(KERN_WARNING "  REJ reason 0x%x\n",
 			       event->param.rej_rcvd.reason);
 			target->status = -ECONNRESET;



More information about the general mailing list