PERFORCE change 162821 for review
Alexander Motin
mav at FreeBSD.org
Tue May 26 21:40:53 UTC 2009
http://perforce.freebsd.org/chv.cgi?CH=162821
Change 162821 by mav at mav_mavbook on 2009/05/26 21:40:39
Some parts of ATAPI support.
Affected files ...
.. //depot/projects/scottl-camlock/src/sys/cam/ata/ata_all.c#3 edit
.. //depot/projects/scottl-camlock/src/sys/cam/ata/ata_all.h#3 edit
.. //depot/projects/scottl-camlock/src/sys/cam/ata/ata_xpt.c#7 edit
Differences ...
==== //depot/projects/scottl-camlock/src/sys/cam/ata/ata_all.c#3 (text+ko) ====
@@ -46,25 +46,6 @@
#include <sys/sbuf.h>
void
-ata_ident(struct ccb_ataio *ataio, u_int32_t retries,
- void (*cbfcnp)(struct cam_periph *, union ccb *),
- u_int8_t tag_action, u_int8_t *inq_buf, u_int32_t inq_len,
- u_int32_t timeout)
-{
-
- cam_fill_ataio(ataio,
- retries,
- cbfcnp,
- /*flags*/CAM_DIR_IN,
- tag_action,
- /*data_ptr*/inq_buf,
- /*dxfer_len*/inq_len,
- timeout);
-
- ataio->cmd.command = ATA_ATA_IDENTIFY;
-}
-
-void
ata_print_ident(struct ata_params *ident_data)
{
char product[48], revision[16];
==== //depot/projects/scottl-camlock/src/sys/cam/ata/ata_all.h#3 (text+ko) ====
@@ -41,12 +41,6 @@
};
void
-ata_ident(struct ccb_ataio *ataio, u_int32_t retries,
- void (*cbfcnp)(struct cam_periph *, union ccb *),
- u_int8_t tag_action, u_int8_t *inq_buf, u_int32_t inq_len,
- u_int32_t timeout);
-
-void
ata_print_ident(struct ata_params *ident_data);
void
==== //depot/projects/scottl-camlock/src/sys/cam/ata/ata_xpt.c#7 (text+ko) ====
@@ -92,11 +92,15 @@
typedef enum {
PROBE_IDENTIFY,
+ PROBE_INQUIRY,
+ PROBE_FULL_INQUIRY,
PROBE_INVALID
} probe_action;
static char *probe_action_text[] = {
"PROBE_IDENTIFY",
+ "PROBE_INQUIRY",
+ "PROBE_FULL_INQUIRY",
"PROBE_INVALID"
};
@@ -308,12 +312,14 @@
{
/* Probe the device that our peripheral driver points to */
struct ccb_ataio *ataio;
+ struct ccb_scsiio *csio;
probe_softc *softc;
CAM_DEBUG(start_ccb->ccb_h.path, CAM_DEBUG_TRACE, ("probestart\n"));
softc = (probe_softc *)periph->softc;
ataio = &start_ccb->ataio;
+ csio = &start_ccb->csio;
switch (softc->action) {
case PROBE_IDENTIFY:
@@ -339,12 +345,51 @@
MD5Final(softc->digest, &context);
}
- ata_ident(ataio,
+ cam_fill_ataio(ataio,
+ 4,
+ probedone,
+ /*flags*/CAM_DIR_IN,
+ MSG_SIMPLE_Q_TAG,
+ /*data_ptr*/(u_int8_t *)ident_buf,
+ /*dxfer_len*/sizeof(struct ata_params),
+ 60 * 1000);
+
+ if (periph->path->device->protocol == PROTO_ATA)
+ ataio->cmd.command = ATA_ATA_IDENTIFY;
+ else
+ ataio->cmd.command = ATA_ATAPI_IDENTIFY;
+ break;
+ }
+ case PROBE_INQUIRY:
+ case PROBE_FULL_INQUIRY:
+ {
+ u_int inquiry_len;
+ struct scsi_inquiry_data *inq_buf;
+
+ inq_buf = &periph->path->device->inq_data;
+
+ if (softc->action == PROBE_INQUIRY)
+ inquiry_len = SHORT_INQUIRY_LENGTH;
+ else
+ inquiry_len = SID_ADDITIONAL_LENGTH(inq_buf);
+
+ /*
+ * Some parallel SCSI devices fail to send an
+ * ignore wide residue message when dealing with
+ * odd length inquiry requests. Round up to be
+ * safe.
+ */
+ inquiry_len = roundup2(inquiry_len, 2);
+
+ scsi_inquiry(csio,
/*retries*/4,
probedone,
MSG_SIMPLE_Q_TAG,
- (u_int8_t *)ident_buf,
- sizeof(struct ata_params),
+ (u_int8_t *)inq_buf,
+ inquiry_len,
+ /*evpd*/FALSE,
+ /*page_code*/0,
+ SSD_MIN_SIZE,
/*timeout*/60 * 1000);
break;
}
@@ -573,16 +618,101 @@
// else
// PROBE_SET_ACTION(softc, PROBE_SERIAL_NUM_0);
- path->device->flags &= ~CAM_DEV_UNCONFIGURED;
+// if ((softc->flags & PROBE_NO_ANNOUNCE) == 0) {
+ if (path->device->protocol == PROTO_ATA) {
+ path->device->flags &= ~CAM_DEV_UNCONFIGURED;
+ done_ccb->ccb_h.func_code = XPT_GDEV_TYPE;
+ xpt_action(done_ccb);
+ xpt_async(AC_FOUND_DEVICE, done_ccb->ccb_h.path,
+ done_ccb);
+ xpt_release_ccb(done_ccb);
+ break;
+ } else {
+ PROBE_SET_ACTION(softc, PROBE_INQUIRY);
+ xpt_release_ccb(done_ccb);
+ xpt_schedule(periph, priority);
+ return;
+ }
+ } else if (cam_periph_error(done_ccb, 0,
+ done_ccb->ccb_h.target_lun > 0
+ ? SF_RETRY_UA|SF_QUIET_IR
+ : SF_RETRY_UA,
+ &softc->saved_ccb) == ERESTART) {
+ return;
+ } else if ((done_ccb->ccb_h.status & CAM_DEV_QFRZN) != 0) {
+ /* Don't wedge the queue */
+ xpt_release_devq(done_ccb->ccb_h.path, /*count*/1,
+ /*run_queue*/TRUE);
+ }
+ /*
+ * If we get to this point, we got an error status back
+ * from the inquiry and the error status doesn't require
+ * automatically retrying the command. Therefore, the
+ * inquiry failed. If we had inquiry information before
+ * for this device, but this latest inquiry command failed,
+ * the device has probably gone away. If this device isn't
+ * already marked unconfigured, notify the peripheral
+ * drivers that this device is no more.
+ */
+ if ((path->device->flags & CAM_DEV_UNCONFIGURED) == 0)
+ /* Send the async notification. */
+ xpt_async(AC_LOST_DEVICE, path, NULL);
+
+ xpt_release_ccb(done_ccb);
+ break;
+ }
+ case PROBE_INQUIRY:
+ case PROBE_FULL_INQUIRY:
+ {
+ if ((done_ccb->ccb_h.status & CAM_STATUS_MASK) == CAM_REQ_CMP) {
+ struct scsi_inquiry_data *inq_buf;
+ u_int8_t periph_qual;
+
+ path->device->flags |= CAM_DEV_INQUIRY_DATA_VALID;
+ inq_buf = &path->device->inq_data;
+
+ periph_qual = SID_QUAL(inq_buf);
+
+ switch(periph_qual) {
+ case SID_QUAL_LU_CONNECTED:
+ {
+ u_int8_t len;
+
+ /*
+ * We conservatively request only
+ * SHORT_INQUIRY_LEN bytes of inquiry
+ * information during our first try
+ * at sending an INQUIRY. If the device
+ * has more information to give,
+ * perform a second request specifying
+ * the amount of information the device
+ * is willing to give.
+ */
+ len = inq_buf->additional_length
+ + offsetof(struct scsi_inquiry_data,
+ additional_length) + 1;
+ if (softc->action == PROBE_INQUIRY
+ && len > SHORT_INQUIRY_LENGTH) {
+ PROBE_SET_ACTION(softc, PROBE_FULL_INQUIRY);
+ xpt_release_ccb(done_ccb);
+ xpt_schedule(periph, priority);
+ return;
+ }
+
+ scsi_find_quirk(path->device);
-// if ((softc->flags & PROBE_NO_ANNOUNCE) == 0) {
+// scsi_devise_transport(path);
+ path->device->flags &= ~CAM_DEV_UNCONFIGURED;
done_ccb->ccb_h.func_code = XPT_GDEV_TYPE;
xpt_action(done_ccb);
xpt_async(AC_FOUND_DEVICE, done_ccb->ccb_h.path,
done_ccb);
-// }
- xpt_release_ccb(done_ccb);
- break;
+ xpt_release_ccb(done_ccb);
+ return;
+ }
+ default:
+ break;
+ }
} else if (cam_periph_error(done_ccb, 0,
done_ccb->ccb_h.target_lun > 0
? SF_RETRY_UA|SF_QUIET_IR
More information about the p4-projects
mailing list