Flag when we have a pending TUR. Don't schedule another one when we
have one pending. Otherwise, we can race and send two, which is wasteful in close proximity. It can also cause the acaquire/release count for TUR to be > 1, which is undexpected. PR: 226510 Differential Review: https://reviews.freebsd.org/D14792
This commit is contained in:
parent
8363051739
commit
6a6c0d5844
Notes:
svn2git
2020-12-20 02:59:44 +00:00
svn path=/head/; revision=331435
@ -116,7 +116,8 @@ typedef enum {
|
||||
DA_FLAG_CAN_ATA_LOG = 0x008000,
|
||||
DA_FLAG_CAN_ATA_IDLOG = 0x010000,
|
||||
DA_FLAG_CAN_ATA_SUPCAP = 0x020000,
|
||||
DA_FLAG_CAN_ATA_ZONE = 0x040000
|
||||
DA_FLAG_CAN_ATA_ZONE = 0x040000,
|
||||
DA_FLAG_TUR_PENDING = 0x080000
|
||||
} da_flags;
|
||||
|
||||
typedef enum {
|
||||
@ -2068,7 +2069,8 @@ daasync(void *callback_arg, u_int32_t code,
|
||||
case AC_SCSI_AEN:
|
||||
softc = (struct da_softc *)periph->softc;
|
||||
cam_periph_lock(periph);
|
||||
if (!cam_iosched_has_work_flags(softc->cam_iosched, DA_WORK_TUR)) {
|
||||
if (!cam_iosched_has_work_flags(softc->cam_iosched, DA_WORK_TUR) &&
|
||||
(softc->flags & DA_FLAG_TUR_PENDING) == 0) {
|
||||
if (da_periph_acquire(periph, DA_REF_TUR) == 0) {
|
||||
cam_iosched_set_work_flags(softc->cam_iosched, DA_WORK_TUR);
|
||||
daschedule(periph);
|
||||
@ -3113,6 +3115,7 @@ dastart(struct cam_periph *periph, union ccb *start_ccb)
|
||||
bp = cam_iosched_next_bio(softc->cam_iosched);
|
||||
if (bp == NULL) {
|
||||
if (cam_iosched_has_work_flags(softc->cam_iosched, DA_WORK_TUR)) {
|
||||
softc->flags |= DA_FLAG_TUR_PENDING;
|
||||
cam_iosched_clr_work_flags(softc->cam_iosched, DA_WORK_TUR);
|
||||
scsi_test_unit_ready(&start_ccb->csio,
|
||||
/*retries*/ da_retry_count,
|
||||
@ -5570,7 +5573,7 @@ dadone(struct cam_periph *periph, union ccb *done_ccb)
|
||||
if (daerror(done_ccb, CAM_RETRY_SELTO,
|
||||
SF_RETRY_UA | SF_NO_RECOVERY | SF_NO_PRINT) ==
|
||||
ERESTART)
|
||||
return;
|
||||
return; /* Will complete again, keep reference */
|
||||
if ((done_ccb->ccb_h.status & CAM_DEV_QFRZN) != 0)
|
||||
cam_release_devq(done_ccb->ccb_h.path,
|
||||
/*relsim_flags*/0,
|
||||
@ -5579,6 +5582,7 @@ dadone(struct cam_periph *periph, union ccb *done_ccb)
|
||||
/*getcount_only*/0);
|
||||
}
|
||||
xpt_release_ccb(done_ccb);
|
||||
softc->flags &= ~DA_FLAG_TUR_PENDING;
|
||||
da_periph_release_locked(periph, DA_REF_TUR);
|
||||
return;
|
||||
}
|
||||
@ -5700,6 +5704,7 @@ damediapoll(void *arg)
|
||||
struct da_softc *softc = periph->softc;
|
||||
|
||||
if (!cam_iosched_has_work_flags(softc->cam_iosched, DA_WORK_TUR) &&
|
||||
(softc->flags & DA_FLAG_TUR_PENDING) == 0 &&
|
||||
LIST_EMPTY(&softc->pending_ccbs)) {
|
||||
if (da_periph_acquire(periph, DA_REF_TUR) == 0) {
|
||||
cam_iosched_set_work_flags(softc->cam_iosched, DA_WORK_TUR);
|
||||
|
Loading…
Reference in New Issue
Block a user