diff options
author | Kenneth R Westerback <krw@cvs.openbsd.org> | 2008-05-09 06:19:34 +0000 |
---|---|---|
committer | Kenneth R Westerback <krw@cvs.openbsd.org> | 2008-05-09 06:19:34 +0000 |
commit | 537b4a46ccabb1f2e4c4c19a4a221797d8f8b9f6 (patch) | |
tree | ec6cc546dd7d37c2891a448e86641a13db61d434 /sys | |
parent | 1db7e2643891a3d757248b6af905d54573e7f803 (diff) |
Lock in removable media while trying to determine the disk parameters. This
should fix a number of 'drive offline' situations where the device claims
it has no media loaded until the lock in occurs. Like a Blackberry Pearl
Todd Fries found and probably other USB devices. Move the lock in during
device open to before the test unit ready to eliminate similar spurious
rejections of the device.
Feedback from marco@, tests by todd@ and miod@.
ok deraadt@ beck@ dlg@ miod@
Diffstat (limited to 'sys')
-rw-r--r-- | sys/scsi/sd.c | 35 |
1 files changed, 24 insertions, 11 deletions
diff --git a/sys/scsi/sd.c b/sys/scsi/sd.c index 0242673d9ca..471acce7187 100644 --- a/sys/scsi/sd.c +++ b/sys/scsi/sd.c @@ -1,4 +1,4 @@ -/* $OpenBSD: sd.c,v 1.142 2008/03/21 19:57:44 krw Exp $ */ +/* $OpenBSD: sd.c,v 1.143 2008/05/09 06:19:33 krw Exp $ */ /* $NetBSD: sd.c,v 1.111 1997/04/02 02:29:41 mycroft Exp $ */ /*- @@ -209,6 +209,14 @@ sdattach(struct device *parent, struct device *self, void *aux) scsi_start(sc_link, SSS_START, scsi_autoconf | SCSI_SILENT | SCSI_IGNORE_ILLEGAL_REQUEST | SCSI_IGNORE_MEDIA_CHANGE); + /* + * Some devices (e.g. Blackberry Pearl) won't admit they have + * media loaded unless its been locked in. + */ + if ((sc_link->flags & SDEV_REMOVABLE) != 0) + scsi_prevent(sc_link, PR_PREVENT, SCSI_IGNORE_ILLEGAL_REQUEST | + SCSI_IGNORE_MEDIA_CHANGE); + /* Check that it is still responding and ok. */ error = scsi_test_unit_ready(sd->sc_link, TEST_READY_RETRIES, scsi_autoconf | SCSI_IGNORE_ILLEGAL_REQUEST | @@ -220,6 +228,11 @@ sdattach(struct device *parent, struct device *self, void *aux) result = sd_get_parms(sd, &sd->params, scsi_autoconf | SCSI_SILENT | SCSI_IGNORE_MEDIA_CHANGE); + if ((sc_link->flags & SDEV_REMOVABLE) != 0) + scsi_prevent(sc_link, PR_ALLOW, + SCSI_IGNORE_ILLEGAL_REQUEST | + SCSI_IGNORE_MEDIA_CHANGE); + printf("%s: ", sd->sc_dev.dv_xname); switch (result) { case SDGP_RESULT_OK: @@ -361,6 +374,16 @@ sdopen(dev_t dev, int flag, int fmt, struct proc *p) */ sc_link->flags |= SDEV_OPEN; + /* + * Try to prevent the unloading of a removable device while + * it's open. But allow the open to proceed if the device can't + * be locked in. + */ + if ((sc_link->flags & SDEV_REMOVABLE) != 0) + scsi_prevent(sc_link, PR_PREVENT, + SCSI_IGNORE_ILLEGAL_REQUEST | + SCSI_IGNORE_MEDIA_CHANGE); + /* Check that it is still responding and ok. */ error = scsi_test_unit_ready(sc_link, TEST_READY_RETRIES, (rawopen ? SCSI_SILENT : 0) | @@ -374,16 +397,6 @@ sdopen(dev_t dev, int flag, int fmt, struct proc *p) goto bad; } - /* - * Try to prevent the unloading of a removable device while - * it's open. But allow the open to proceed if the device can't - * be locked in. - */ - if ((sc_link->flags & SDEV_REMOVABLE) != 0) - scsi_prevent(sc_link, PR_PREVENT, - SCSI_IGNORE_ILLEGAL_REQUEST | - SCSI_IGNORE_MEDIA_CHANGE); - /* Load the physical device parameters. */ sc_link->flags |= SDEV_MEDIA_LOADED; if (sd_get_parms(sd, &sd->params, (rawopen ? SCSI_SILENT : 0)) |