svn commit: r199279 - in head/sys/cam: . scsi
Alexander Motin
mav at FreeBSD.org
Sat Nov 14 20:13:39 UTC 2009
Author: mav
Date: Sat Nov 14 20:13:38 2009
New Revision: 199279
URL: http://svn.freebsd.org/changeset/base/199279
Log:
MFp4:
Fix several device freeze counting bugs.
Modified:
head/sys/cam/cam_periph.c
head/sys/cam/scsi/scsi_cd.c
head/sys/cam/scsi/scsi_ch.c
Modified: head/sys/cam/cam_periph.c
==============================================================================
--- head/sys/cam/cam_periph.c Sat Nov 14 20:06:04 2009 (r199278)
+++ head/sys/cam/cam_periph.c Sat Nov 14 20:13:38 2009 (r199279)
@@ -981,16 +981,21 @@ camperiphdone(struct cam_periph *periph,
{
union ccb *saved_ccb;
cam_status status;
- int frozen;
+ int frozen = 0;
int sense;
struct scsi_start_stop_unit *scsi_cmd;
u_int32_t relsim_flags, timeout;
- u_int32_t qfrozen_cnt;
- int xpt_done_ccb;
+ int xpt_done_ccb = FALSE;
- xpt_done_ccb = FALSE;
status = done_ccb->ccb_h.status;
- frozen = (status & CAM_DEV_QFRZN) != 0;
+ if (status & CAM_DEV_QFRZN) {
+ frozen = 1;
+ /*
+ * Clear freeze flag now for case of retry,
+ * freeze will be dropped later.
+ */
+ done_ccb->ccb_h.status &= ~CAM_DEV_QFRZN;
+ }
sense = (status & CAM_AUTOSNS_VALID) != 0;
status &= CAM_STATUS_MASK;
@@ -998,17 +1003,6 @@ camperiphdone(struct cam_periph *periph,
relsim_flags = 0;
saved_ccb = (union ccb *)done_ccb->ccb_h.saved_ccb_ptr;
- /*
- * Unfreeze the queue once if it is already frozen..
- */
- if (frozen != 0) {
- qfrozen_cnt = cam_release_devq(done_ccb->ccb_h.path,
- /*relsim_flags*/0,
- /*openings*/0,
- /*timeout*/0,
- /*getcount_only*/0);
- }
-
switch (status) {
case CAM_REQ_CMP:
{
@@ -1185,14 +1179,33 @@ camperiphdone(struct cam_periph *periph,
*/
if (done_ccb->ccb_h.retry_count > 0)
done_ccb->ccb_h.retry_count--;
-
- qfrozen_cnt = cam_release_devq(done_ccb->ccb_h.path,
- /*relsim_flags*/relsim_flags,
- /*openings*/0,
- /*timeout*/timeout,
- /*getcount_only*/0);
- if (xpt_done_ccb == TRUE)
+ /*
+ * Drop freeze taken due to CAM_DEV_QFREEZE flag set on recovery
+ * request.
+ */
+ cam_release_devq(done_ccb->ccb_h.path,
+ /*relsim_flags*/relsim_flags,
+ /*openings*/0,
+ /*timeout*/timeout,
+ /*getcount_only*/0);
+ if (xpt_done_ccb == TRUE) {
+ /*
+ * Copy frozen flag from recovery request if it is set there
+ * for some reason.
+ */
+ if (frozen != 0)
+ done_ccb->ccb_h.status |= CAM_DEV_QFRZN;
(*done_ccb->ccb_h.cbfcnp)(periph, done_ccb);
+ } else {
+ /* Drop freeze taken, if this recovery request got error. */
+ if (frozen != 0) {
+ cam_release_devq(done_ccb->ccb_h.path,
+ /*relsim_flags*/0,
+ /*openings*/0,
+ /*timeout*/0,
+ /*getcount_only*/0);
+ }
+ }
}
/*
Modified: head/sys/cam/scsi/scsi_cd.c
==============================================================================
--- head/sys/cam/scsi/scsi_cd.c Sat Nov 14 20:06:04 2009 (r199278)
+++ head/sys/cam/scsi/scsi_cd.c Sat Nov 14 20:13:38 2009 (r199279)
@@ -1570,7 +1570,8 @@ cddone(struct cam_periph *periph, union
bp->bio_resid = bp->bio_bcount;
bp->bio_error = error;
bp->bio_flags |= BIO_ERROR;
- cam_release_devq(done_ccb->ccb_h.path,
+ if ((done_ccb->ccb_h.status & CAM_DEV_QFRZN) != 0)
+ cam_release_devq(done_ccb->ccb_h.path,
/*relsim_flags*/0,
/*reduction*/0,
/*timeout*/0,
@@ -1658,7 +1659,8 @@ cddone(struct cam_periph *periph, union
struct ccb_getdev cgd;
/* Don't wedge this device's queue */
- cam_release_devq(done_ccb->ccb_h.path,
+ if ((done_ccb->ccb_h.status & CAM_DEV_QFRZN) != 0)
+ cam_release_devq(done_ccb->ccb_h.path,
/*relsim_flags*/0,
/*reduction*/0,
/*timeout*/0,
Modified: head/sys/cam/scsi/scsi_ch.c
==============================================================================
--- head/sys/cam/scsi/scsi_ch.c Sat Nov 14 20:06:04 2009 (r199278)
+++ head/sys/cam/scsi/scsi_ch.c Sat Nov 14 20:13:38 2009 (r199279)
@@ -606,7 +606,8 @@ chdone(struct cam_periph *periph, union
retry_scheduled = 0;
/* Don't wedge this device's queue */
- cam_release_devq(done_ccb->ccb_h.path,
+ if ((done_ccb->ccb_h.status & CAM_DEV_QFRZN) != 0)
+ cam_release_devq(done_ccb->ccb_h.path,
/*relsim_flags*/0,
/*reduction*/0,
/*timeout*/0,
More information about the svn-src-head
mailing list