Skip site navigation (1)Skip section navigation (2)
Date:      Mon, 21 Feb 2011 16:55:54 +0000 (UTC)
From:      "Kenneth D. Merry" <ken@FreeBSD.org>
To:        src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-stable@freebsd.org, svn-src-stable-8@freebsd.org
Subject:   svn commit: r218921 - stable/8/sys/dev/mps
Message-ID:  <201102211655.p1LGtsk5076942@svn.freebsd.org>

next in thread | raw e-mail | index | archive | help
Author: ken
Date: Mon Feb 21 16:55:53 2011
New Revision: 218921
URL: http://svn.freebsd.org/changeset/base/218921

Log:
  MFC: r218811:
  
  In the MPS driver, during device removal processing, don't assume that
  the controller firmware will return all of our commands.  Instead, keep
  track of outstanding I/Os and return them to CAM once device removal
  processing completes.
  
  mpsvar.h:	Declare the new "io_list" in the mps_softc.
  
  mps.c:		Initialize the new "io_list" in the mps softc.
  
  mps_sas.c:	o Track SCSI I/O requests on the io_list from the
  		  time of mpssas_action() through mpssas_scsiio_complete().
  		o Zero out the request structures used for device
  		  removal commands prior to filling them out.
  		o Once the target reset task management function completes
  		  during device removal processing, assume any SCSI I/O
  		  commands that are still oustanding will never return
  		  from the controller, and process them manually.
  
  Submitted by:	gibbs

Modified:
  stable/8/sys/dev/mps/mps.c
  stable/8/sys/dev/mps/mps_sas.c
  stable/8/sys/dev/mps/mpsvar.h
Directory Properties:
  stable/8/sys/   (props changed)
  stable/8/sys/amd64/include/xen/   (props changed)
  stable/8/sys/cddl/contrib/opensolaris/   (props changed)
  stable/8/sys/contrib/dev/acpica/   (props changed)
  stable/8/sys/contrib/pf/   (props changed)

Modified: stable/8/sys/dev/mps/mps.c
==============================================================================
--- stable/8/sys/dev/mps/mps.c	Mon Feb 21 16:33:01 2011	(r218920)
+++ stable/8/sys/dev/mps/mps.c	Mon Feb 21 16:55:53 2011	(r218921)
@@ -898,6 +898,7 @@ mps_attach(struct mps_softc *sc)
 	TAILQ_INIT(&sc->req_list);
 	TAILQ_INIT(&sc->chain_list);
 	TAILQ_INIT(&sc->tm_list);
+	TAILQ_INIT(&sc->io_list);
 
 	if (((error = mps_alloc_queues(sc)) != 0) ||
 	    ((error = mps_alloc_replies(sc)) != 0) ||

Modified: stable/8/sys/dev/mps/mps_sas.c
==============================================================================
--- stable/8/sys/dev/mps/mps_sas.c	Mon Feb 21 16:33:01 2011	(r218920)
+++ stable/8/sys/dev/mps/mps_sas.c	Mon Feb 21 16:55:53 2011	(r218921)
@@ -486,7 +486,10 @@ mpssas_prepare_remove(struct mpssas_soft
 		return;
 	}
 
+	mps_dprint(sc, MPS_INFO, "Preparing to remove target %d\n", targ->tid);
+
 	req = (MPI2_SCSI_TASK_MANAGE_REQUEST *)cm->cm_req;
+	memset(req, 0, sizeof(*req));
 	req->DevHandle = targ->handle;
 	req->Function = MPI2_FUNCTION_SCSI_TASK_MGMT;
 	req->TaskType = MPI2_SCSITASKMGMT_TASKTYPE_TARGET_RESET;
@@ -507,6 +510,7 @@ mpssas_remove_device(struct mps_softc *s
 	MPI2_SCSI_TASK_MANAGE_REPLY *reply;
 	MPI2_SAS_IOUNIT_CONTROL_REQUEST *req;
 	struct mpssas_target *targ;
+	struct mps_command *next_cm;
 	uint16_t handle;
 
 	mps_dprint(sc, MPS_TRACE, "%s\n", __func__);
@@ -523,11 +527,13 @@ mpssas_remove_device(struct mps_softc *s
 		return;
 	}
 
-	mps_printf(sc, "Reset aborted %d commands\n", reply->TerminationCount);
+	mps_dprint(sc, MPS_INFO, "Reset aborted %u commands\n",
+	    reply->TerminationCount);
 	mps_free_reply(sc, cm->cm_reply_data);
 
 	/* Reuse the existing command */
 	req = (MPI2_SAS_IOUNIT_CONTROL_REQUEST *)cm->cm_req;
+	memset(req, 0, sizeof(*req));
 	req->Function = MPI2_FUNCTION_SAS_IO_UNIT_CONTROL;
 	req->Operation = MPI2_SAS_OP_REMOVE_DEVICE;
 	req->DevHandle = handle;
@@ -539,6 +545,17 @@ mpssas_remove_device(struct mps_softc *s
 	mps_map_command(sc, cm);
 
 	mps_dprint(sc, MPS_INFO, "clearing target handle 0x%04x\n", handle);
+	TAILQ_FOREACH_SAFE(cm, &sc->io_list, cm_link, next_cm) {
+		union ccb *ccb;
+
+		if (cm->cm_targ->handle != handle)
+			continue;
+
+		mps_dprint(sc, MPS_INFO, "Completing missed command %p\n", cm);
+		ccb = cm->cm_complete_data;
+		ccb->ccb_h.status = CAM_DEV_NOT_THERE;
+		mpssas_scsiio_complete(sc, cm);
+	}
 	targ = mpssas_find_target(sc->sassc, 0, handle);
 	if (targ != NULL) {
 		targ->handle = 0x0;
@@ -1430,6 +1447,7 @@ mpssas_action_scsiio(struct mpssas_softc
 	cm->cm_complete_data = ccb;
 	cm->cm_targ = targ;
 
+	TAILQ_INSERT_TAIL(&sc->io_list, cm, cm_link);
 	callout_reset(&cm->cm_callout, (ccb->ccb_h.timeout * hz) / 1000,
 	   mpssas_scsiio_timeout, cm);
 
@@ -1449,6 +1467,7 @@ mpssas_scsiio_complete(struct mps_softc 
 	mps_dprint(sc, MPS_TRACE, "%s\n", __func__);
 
 	callout_stop(&cm->cm_callout);
+	TAILQ_REMOVE(&sc->io_list, cm, cm_link);
 
 	sassc = sc->sassc;
 	ccb = cm->cm_complete_data;
@@ -1470,8 +1489,10 @@ mpssas_scsiio_complete(struct mps_softc 
 
 	/* Take the fast path to completion */
 	if (cm->cm_reply == NULL) {
-		ccb->ccb_h.status = CAM_REQ_CMP;
-		ccb->csio.scsi_status = SCSI_STATUS_OK;
+		if ((ccb->ccb_h.status & CAM_STATUS_MASK) == CAM_REQ_INPROG) {
+			ccb->ccb_h.status = CAM_REQ_CMP;
+			ccb->csio.scsi_status = SCSI_STATUS_OK;
+		}
 		mps_free_command(sc, cm);
 		xpt_done(ccb);
 		return;

Modified: stable/8/sys/dev/mps/mpsvar.h
==============================================================================
--- stable/8/sys/dev/mps/mpsvar.h	Mon Feb 21 16:33:01 2011	(r218920)
+++ stable/8/sys/dev/mps/mpsvar.h	Mon Feb 21 16:55:53 2011	(r218921)
@@ -133,6 +133,7 @@ struct mps_softc {
 	TAILQ_HEAD(, mps_command)	req_list;
 	TAILQ_HEAD(, mps_chain)		chain_list;
 	TAILQ_HEAD(, mps_command)	tm_list;
+	TAILQ_HEAD(, mps_command)	io_list;
 	int				replypostindex;
 	int				replyfreeindex;
 



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201102211655.p1LGtsk5076942>