Source-Changes-HG archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

[src/trunk]: src/sys/dev/scsipi Some older devices do not understand the `dis...



details:   https://anonhg.NetBSD.org/src/rev/47a5b6c29f38
branches:  trunk
changeset: 556678:47a5b6c29f38
user:      pk <pk%NetBSD.org@localhost>
date:      Tue Dec 23 13:12:25 2003 +0000

description:
Some older devices do not understand the `disable block descriptors' bit in
the mode sense request. So fall back on mode sense data including a block
descriptor section.

XXX this applies to the `page 4' case. The `page 5' didn't consider the
possible presence of a block descriptor at all, though it did allow the
device to return one.  While that's fixed now, the `page 5' mode sense
does not use the `disable block descriptors' bit.

I'm not sure we should bother with this at all..

diffstat:

 sys/dev/scsipi/sd.c |  64 +++++++++++++++++++++++++++++++++++-----------------
 1 files changed, 43 insertions(+), 21 deletions(-)

diffs (168 lines):

diff -r e06ab527b06c -r 47a5b6c29f38 sys/dev/scsipi/sd.c
--- a/sys/dev/scsipi/sd.c       Tue Dec 23 11:55:43 2003 +0000
+++ b/sys/dev/scsipi/sd.c       Tue Dec 23 13:12:25 2003 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: sd.c,v 1.213 2003/10/29 21:26:43 mycroft Exp $ */
+/*     $NetBSD: sd.c,v 1.214 2003/12/23 13:12:25 pk Exp $      */
 
 /*-
  * Copyright (c) 1998, 2003 The NetBSD Foundation, Inc.
@@ -54,7 +54,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: sd.c,v 1.213 2003/10/29 21:26:43 mycroft Exp $");
+__KERNEL_RCSID(0, "$NetBSD: sd.c,v 1.214 2003/12/23 13:12:25 pk Exp $");
 
 #include "opt_scsi.h"
 #include "opt_bufq.h"
@@ -607,7 +607,7 @@
  * close the device.. only called if we are the LAST occurence of an open
  * device.  Convenient now but usually a pain.
  */
-int 
+int
 sdclose(dev, flag, fmt, p)
        dev_t dev;
        int flag, fmt;
@@ -743,10 +743,10 @@
                blkno = bp->b_blkno / (lp->d_secsize / DEV_BSIZE);
        else
                blkno = bp->b_blkno * (DEV_BSIZE / lp->d_secsize);
- 
+
        if (SDPART(bp->b_dev) != RAW_PART)
                blkno += lp->d_partitions[SDPART(bp->b_dev)].p_offset;
- 
+
        bp->b_rawblkno = blkno;
 
        s = splbio();
@@ -794,7 +794,7 @@
  * must be called at the correct (highish) spl level
  * sdstart() is called at splbio from sdstrategy and scsipi_done
  */
-void 
+void
 sdstart(periph)
        struct scsipi_periph *periph;
 {
@@ -1130,7 +1130,7 @@
        case DIOCLOCK:
                return (scsipi_prevent(periph,
                    (*(int *)addr) ? PR_PREVENT : PR_ALLOW, 0));
-       
+
        case DIOCEJECT:
                if ((periph->periph_flags & PERIPH_REMOVABLE) == 0)
                        return (ENOTTY);
@@ -1650,7 +1650,7 @@
                return (SDGP_RESULT_OFFLINE);           /* XXX? */
 
        dp->blksize = _2btol(scsipi_sense.lbs);
-       if (dp->blksize == 0) 
+       if (dp->blksize == 0)
                dp->blksize = 512;
 
        /*
@@ -1776,6 +1776,7 @@
        struct sd_mode_sense_data scsipi_sense;
        int error;
        int big;
+       int byte2;
        union scsi_disk_pages *pages;
 #if 0
        int i;
@@ -1796,17 +1797,31 @@
        if (sd->type == T_OPTICAL)
                goto page0;
 
+       /* Try MODE SENSE with `disable block descriptors' first */
+       byte2 = SMS_DBD;
+do_ms_again:
        memset(&scsipi_sense, 0, sizeof(scsipi_sense));
-       error = sd_mode_sense(sd, SMS_DBD, &scsipi_sense,
+       error = sd_mode_sense(sd, byte2, &scsipi_sense,
            sizeof(scsipi_sense.blk_desc) +
            sizeof(scsipi_sense.pages.rigid_geometry), 4,
            flags | XS_CTL_SILENT, &big);
+       if (error != 0 && byte2 == SMS_DBD) {
+               /* No result; try once more with DBD off */
+               byte2 = 0;
+               goto do_ms_again;
+       }
+
        if (!error) {
-               if (big)
-                       pages = (void *)(&scsipi_sense.header.big + 1);
-               else
-                       pages = (void *)(&scsipi_sense.header.small + 1);
+               int poffset;
+               if (big) {
+                       poffset = sizeof scsipi_sense.header.big;
+                       poffset += _2btol(scsipi_sense.header.big.blk_desc_len);
+               } else {
+                       poffset = sizeof scsipi_sense.header.small;
+                       poffset += scsipi_sense.header.small.blk_desc_len;
+               }
 
+               pages = (void *)((u_long)&scsipi_sense + poffset);
 #if 0
 printf("page 4 sense:"); for (i = sizeof(scsipi_sense), p = (void *)&scsipi_sense; i; i--, p++) printf(" %02x", *p); printf("\n");
 printf("page 4 pg_code=%d sense=%p/%p\n", pages->rigid_geometry.pg_code, &scsipi_sense, pages);
@@ -1814,7 +1829,7 @@
 
                if ((pages->rigid_geometry.pg_code & PGCODE_MASK) != 4)
                        goto page5;
-                       
+
                SC_DEBUG(sd->sc_periph, SCSIPI_DB3,
                    ("%d cyls, %d heads, %d precomp, %d red_write, %d land_zone\n",
                    _3btol(pages->rigid_geometry.ncyl),
@@ -1846,16 +1861,23 @@
        }
 
 page5:
-       memset(&scsipi_sense, SMS_DBD, sizeof(scsipi_sense));
+       /* XXX - Try with SMS_DBD first, like in the page 4 case? */
+       memset(&scsipi_sense, 0, sizeof(scsipi_sense));
        error = sd_mode_sense(sd, 0, &scsipi_sense,
            sizeof(scsipi_sense.blk_desc) +
            sizeof(scsipi_sense.pages.flex_geometry), 5,
            flags | XS_CTL_SILENT, &big);
        if (!error) {
-               if (big)
-                       pages = (void *)(&scsipi_sense.header.big + 1);
-               else
-                       pages = (void *)(&scsipi_sense.header.small + 1);
+               int poffset;
+               if (big) {
+                       poffset = sizeof scsipi_sense.header.big;
+                       poffset += _2btol(scsipi_sense.header.big.blk_desc_len);
+               } else {
+                       poffset = sizeof scsipi_sense.header.small;
+                       poffset += scsipi_sense.header.small.blk_desc_len;
+               }
+
+               pages = (void *)((u_long)&scsipi_sense + poffset);
 
 #if 0
 printf("page 5 sense:"); for (i = sizeof(scsipi_sense), p = (void *)&scsipi_sense; i; i--, p++) printf(" %02x", *p); printf("\n");
@@ -1864,7 +1886,7 @@
 
                if ((pages->flex_geometry.pg_code & PGCODE_MASK) != 5)
                        goto page0;
-                       
+
                SC_DEBUG(sd->sc_periph, SCSIPI_DB3,
                    ("%d cyls, %d heads, %d sec, %d bytes/sec\n",
                    _3btol(pages->flex_geometry.ncyl),
@@ -2015,7 +2037,7 @@
 
        memset(&scsipi_sense, 0, sizeof(scsipi_sense));
        error = sd_mode_sense(sd, SMS_DBD, &scsipi_sense,
-           sizeof(scsipi_sense.pages.caching_params), 8, 0, &big); 
+           sizeof(scsipi_sense.pages.caching_params), 8, 0, &big);
        if (error)
                return (error);
 



Home | Main Index | Thread Index | Old Index