summaryrefslogtreecommitdiffstats
path: root/sys/scsi
diff options
context:
space:
mode:
authordufault <dufault@FreeBSD.org>1995-03-21 11:21:08 +0000
committerdufault <dufault@FreeBSD.org>1995-03-21 11:21:08 +0000
commit274a8d5ee2f5e2f80b359cbb60feedce7879b4fe (patch)
treec976e70835fd9cfefdf009bac7ee768f44b8b8b0 /sys/scsi
parent0d274572e35245942a094cbb30772453c9a4c109 (diff)
downloadFreeBSD-src-274a8d5ee2f5e2f80b359cbb60feedce7879b4fe.zip
FreeBSD-src-274a8d5ee2f5e2f80b359cbb60feedce7879b4fe.tar.gz
cd.c: Julian's CD audio cleanup
sd.c: Julian's removal of subdriver requests st.c, scsi_tape.h: Julian's suport of compressed tape drives Note: compressed tape drives are still not working fully. scsiconf.h, scsi_base.c, scsi_driver.c: address problems in probes and error console logs
Diffstat (limited to 'sys/scsi')
-rw-r--r--sys/scsi/cd.c74
-rw-r--r--sys/scsi/scsi_base.c36
-rw-r--r--sys/scsi/scsi_driver.c11
-rw-r--r--sys/scsi/scsi_tape.h90
-rw-r--r--sys/scsi/scsiconf.c24
-rw-r--r--sys/scsi/scsiconf.h62
-rw-r--r--sys/scsi/sd.c36
-rw-r--r--sys/scsi/st.c214
8 files changed, 362 insertions, 185 deletions
diff --git a/sys/scsi/cd.c b/sys/scsi/cd.c
index 9b8241a..f8713ed 100644
--- a/sys/scsi/cd.c
+++ b/sys/scsi/cd.c
@@ -14,7 +14,7 @@
*
* Ported to run under 386BSD by Julian Elischer (julian@tfs.com) Sept 1992
*
- * $Id: cd.c,v 1.35 1995/03/04 20:50:42 dufault Exp $
+ * $Id: cd.c,v 1.36 1995/03/15 14:22:03 dufault Exp $
*/
#define SPLCD splbio
@@ -71,8 +71,6 @@ void cdstart(u_int32 unit);
struct scsi_data {
u_int32 flags;
#define CDINIT 0x04 /* device has been init'd */
- u_int32 ad_info; /* info about the adapter */
- u_int32 cmdscount; /* cmds allowed outstanding by board */
struct cd_parms {
u_int32 blksize;
u_long disksize; /* total number sectors */
@@ -179,16 +177,8 @@ cdattach(struct scsi_link *sc_link)
unit = sc_link->dev_unit;
dp = &(cd->params);
- if (sc_link->adapter->adapter_info) {
- cd->ad_info = ((*(sc_link->adapter->adapter_info)) (sc_link->adapter_unit));
- cd->cmdscount = cd->ad_info & AD_INF_MAX_CMDS;
- if (cd->cmdscount > CDOUTSTANDING)
- cd->cmdscount = CDOUTSTANDING;
- } else {
- cd->ad_info = 1;
- cd->cmdscount = 1;
- }
- sc_link->opennings = cd->cmdscount;
+ if (sc_link->opennings > CDOUTSTANDING)
+ sc_link->opennings = CDOUTSTANDING;
/*
* Use the subdriver to request information regarding
* the drive. We cannot use interrupts yet, so the
@@ -233,6 +223,15 @@ struct scsi_link *sc_link)
("cd_open: dev=0x%x (unit %d,partition %d)\n",
dev, unit, part));
/*
+ * Check that it is still responding and ok.
+ * if the media has been changed this will result in a
+ * "unit attention" error which the error code will
+ * disregard because the SDEV_OPEN flag is not yet set.
+ * Makes sure that we know it if the media has been changed..
+ */
+ scsi_test_unit_ready(sc_link, SCSI_SILENT);
+
+ /*
* If it's been invalidated, and not everybody has closed it then
* forbid re-entry. (may have changed media)
*/
@@ -241,15 +240,7 @@ struct scsi_link *sc_link)
return (ENXIO);
/*
- * Check that it is still responding and ok.
- * if the media has been changed this will result in a
- * "unit attention" error which the error code will
- * disregard because the SDEV_OPEN flag is not yet set
- */
- scsi_test_unit_ready(sc_link, SCSI_SILENT);
-
- /*
- * Next time actually take notice of error returns
+ * This time actually take notice of error returns
*/
sc_link->flags |= SDEV_OPEN; /* unit attn errors are now errors */
if (scsi_test_unit_ready(sc_link, SCSI_SILENT) != 0) {
@@ -261,10 +252,11 @@ struct scsi_link *sc_link)
/*
* In case it is a funny one, tell it to start
* not needed for some drives
+ * failure here is ignored.
*/
scsi_start_unit(sc_link, CD_START);
scsi_prevent(sc_link, PR_PREVENT, SCSI_SILENT);
- SC_DEBUG(sc_link, SDEV_DB3, ("started "));
+ SC_DEBUG(sc_link, SDEV_DB3, ("'start' attempted "));
/*
* Load the physical device parameters
*/
@@ -281,28 +273,32 @@ struct scsi_link *sc_link)
/*
* Check the partition is legal
*/
- if ((part >= cd->disklabel.d_npartitions)
- && (part != RAW_PART)) {
- SC_DEBUG(sc_link, SDEV_DB3, ("partition %d > %d\n", part
- ,cd->disklabel.d_npartitions));
- errcode = ENXIO;
- goto bad;
- }
- /*
- * Check that the partition exists
- */
- if ((cd->disklabel.d_partitions[part].p_fstype == FS_UNUSED)
- && (part != RAW_PART)) {
- SC_DEBUG(sc_link, SDEV_DB3, ("part %d type UNUSED\n", part));
- errcode = ENXIO;
- goto bad;
+ if(part != RAW_PART) {
+ /*
+ * Check that the partition CAN exist
+ */
+ if (part >= cd->disklabel.d_npartitions) {
+ SC_DEBUG(sc_link, SDEV_DB3, ("partition %d > %d\n", part
+ ,cd->disklabel.d_npartitions));
+ errcode = ENXIO;
+ goto bad;
+ }
+ /*
+ * and that it DOES exist
+ */
+ if (cd->disklabel.d_partitions[part].p_fstype == FS_UNUSED) {
+ SC_DEBUG(sc_link, SDEV_DB3,
+ ("part %d type UNUSED\n", part));
+ errcode = ENXIO;
+ goto bad;
+ }
}
cd->partflags[part] |= CDOPEN;
cd->openparts |= (1 << part);
SC_DEBUG(sc_link, SDEV_DB3, ("open complete\n"));
sc_link->flags |= SDEV_MEDIA_LOADED;
return 0;
- bad:
+ bad:
/*
* if we would have been the only open
diff --git a/sys/scsi/scsi_base.c b/sys/scsi/scsi_base.c
index 5e50f7a..4cae78d 100644
--- a/sys/scsi/scsi_base.c
+++ b/sys/scsi/scsi_base.c
@@ -8,7 +8,7 @@
* file.
*
* Written by Julian Elischer (julian@dialix.oz.au)
- * $Id: scsi_base.c,v 1.22 1995/03/15 14:22:05 dufault Exp $
+ * $Id: scsi_base.c,v 1.23 1995/03/15 14:44:01 dufault Exp $
*/
#define SPLSD splbio
@@ -646,7 +646,7 @@ retry:
/*
* scsi_sense_print will decode the sense data into human
* readable form. Sense handlers can use this to generate
- * a report. This DOES NOT send the closing "\n".
+ * a report. This NOW DOES send the closing "\n".
*/
void scsi_sense_print(xs)
struct scsi_xfer *xs;
@@ -727,7 +727,15 @@ void scsi_sense_print(xs)
ascq = (ext->extra_len >= 6) ? ext->add_sense_code_qual : 0;
if (asc || ascq)
- printf(" asc:%x,%x %s", asc, ascq, scsi_sense_desc(asc, ascq));
+ {
+ char *desc = scsi_sense_desc(asc, ascq);
+ printf(" asc:%x,%x", asc, ascq);
+
+ if (strlen(desc) > 40)
+ sc_print_addr(xs->sc_link);;
+
+ printf("%s", desc);
+ }
if (ext->extra_len >= 7 && ext->fru) {
printf(" fru:%x", ext->fru);
@@ -754,6 +762,8 @@ void scsi_sense_print(xs)
((unsigned long)sense->ext.unextended.blocklow));
}
}
+
+ printf("\n");
}
/*
@@ -840,7 +850,6 @@ scsi_interpret_sense(xs)
if (!silent) {
scsi_sense_print(xs);
- printf("\n");
}
switch (sense->error_code & SSD_ERRCODE) {
@@ -849,7 +858,6 @@ scsi_interpret_sense(xs)
*/
if (silent) {
scsi_sense_print(xs);
- printf("\n");
}
/* BUG:
@@ -999,6 +1007,21 @@ scsi_4btou(bytes)
return rc;
}
+static sc_printing;
+
+void
+sc_print_start(sc_link)
+ struct scsi_link *sc_link;
+{
+ sc_print_addr(sc_link);
+ sc_printing = 1;
+}
+void
+sc_print_finish()
+{
+ sc_printing = 0;
+}
+
/*
* Print out the scsi_link structure's address info.
*/
@@ -1007,6 +1030,9 @@ void
sc_print_addr(sc_link)
struct scsi_link *sc_link;
{
+ if (sc_printing)
+ printf("\n");
+
if (strcmp(sc_link->device->name, "probe") != 0)
printf("%s%d", sc_link->device->name, sc_link->dev_unit);
diff --git a/sys/scsi/scsi_driver.c b/sys/scsi/scsi_driver.c
index b5f3fad..7f78661 100644
--- a/sys/scsi/scsi_driver.c
+++ b/sys/scsi/scsi_driver.c
@@ -35,7 +35,7 @@
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
- * $Id: scsi_driver.c,v 1.5 1995/03/15 14:22:06 dufault Exp $
+ * $Id: scsi_driver.c,v 1.6 1995/03/16 18:15:48 bde Exp $
*
*/
#include <sys/types.h>
@@ -46,6 +46,8 @@
#include <sys/devconf.h>
#include <sys/malloc.h>
+#include <machine/cpu.h> /* XXX For bootverbose (funny place) */
+
#include <scsi/scsi_all.h>
#include <scsi/scsiconf.h>
#include <scsi/scsi_driver.h>
@@ -73,10 +75,14 @@ int scsi_device_attach(struct scsi_link *sc_link)
dev_t dev;
struct scsi_device *device = sc_link->device;
+ if (bootverbose) {
+ sc_link->flags |= SDEV_BOOTVERBOSE;
+ }
+
SC_DEBUG(sc_link, SDEV_DB2,
("%s%dattach: ", device->name, sc_link->dev_unit));
- sc_print_addr(sc_link);
+ sc_print_start(sc_link);
printf("%s ", device->desc);
dev = scsi_dev_lookup(device->open);
@@ -87,6 +93,7 @@ int scsi_device_attach(struct scsi_link *sc_link)
errcode = (device->attach) ? (*(device->attach))(sc_link) : 0;
+ sc_print_finish();
printf("\n");
if (errcode == 0)
diff --git a/sys/scsi/scsi_tape.h b/sys/scsi/scsi_tape.h
index 3741136..ec852ea 100644
--- a/sys/scsi/scsi_tape.h
+++ b/sys/scsi/scsi_tape.h
@@ -21,7 +21,7 @@
/*
* Ported to run under 386BSD by Julian Elischer (julian@tfs.com) Sept 1992
*
- * $Id: scsi_tape.h,v 1.9 1994/09/28 20:16:42 se Exp $
+ * $Id: scsi_tape.h,v 1.10 1994/10/28 13:19:34 jkh Exp $
*/
#ifndef SCSI_SCSI_TAPE_H
#define SCSI_SCSI_TAPE_H 1
@@ -156,6 +156,94 @@ struct blk_desc_cipher
#define SR150_AUI 0x02 /* autoload inhibit */
};
+/*
+ * This structure defines the various mode pages that tapes know about.
+ */
+#define PAGE_HEADERLEN 2
+struct tape_pages
+{
+ u_char pg_code; /* page code */
+#define ST_PAGE_CONFIGURATION 0x10
+#define ST_PAGE_MEDIUM_PART 0x11
+#define ST_PAGE_MEDIUM_PART2 0x12
+#define ST_PAGE_MEDIUM_PART3 0x13
+#define ST_PAGE_MEDIUM_PART4 0x14
+#define ST_P_CODE 0x3F /* page code */
+#define ST_P_PS 0x80 /* page savable */
+ u_char pg_length; /* page length */
+ union
+ {
+ struct
+ {
+ u_char active_format; /* active format for density*/
+#define ST_P_CAP 0x40 /* change active Partition */
+#define ST_P_CAF 0x20 /* change active format */
+#define ST_P_AF 0x1F /* active format */
+ u_char active_partition; /* */
+ u_char write_buffer_full_ratio; /* highwater writing*/
+ u_char read_buffer_empty_ratio; /* lowwater reading*/
+ u_char write_delay_high; /* # 100mSecs before flush*/
+ u_char write_delay_low; /* of buffer to the media */
+ u_char flags1; /* various single bit flags */
+#define ST_P_DBR 0x80 /* supports data-buffer recovery */
+#define ST_P_BIS 0x40 /* supports Block_ID */
+#define ST_P_RSmk 0x20 /* Reports setmarks during reads and spaces */
+#define ST_P_AVC 0x10 /* Supports Automatic Velocity Control */
+#define ST_P_SOCF 0x0C /* Stop On Consecutive Filemarks, */
+#define ST_P_RBO 0x02 /* Recoverd Buffered Data order, 1 = LIFO */
+#define ST_P_REW 0x01 /* Report Early Warning (see SEW) */
+ u_char gap_size; /*I/B gap, 1=min 0=default */
+ u_char flags2; /* various single bit flags */
+#define ST_P_EOD 0xE0 /* What is and EOD....*/
+#define ST_P_EOD_DEF 0x00 /* Drive's default */
+#define ST_P_EOD_FMT 0x20 /* define by format */
+#define ST_P_EOD_SOCF 0x40 /* define by SOCF (above) */
+#define ST_P_EEG 0x10 /* use EOD above */
+#define ST_P_SEW 0x04 /* Synchronise at Early warning.. flush buffers*/
+ u_char early_warn_high;/* buf size at early warning */
+ u_char early_warn_med; /* after early warning, only */
+ u_char early_warn_low; /* buufer this much data */
+ u_char data_compress_alg; /* 0 = off, 1 = default */
+ u_char reserved; /* The standard says so */
+ } configuration;
+ struct
+ {
+#define ST_MAXPARTS 16 /*for now*/
+ u_char max_add_parts; /* that drive allows */
+ u_char parts_defined; /* max min(ST_MAXPARTS,max_add_parts) */
+ u_char flags;
+#define ST_P_FDP 0x80
+#define ST_P_SDP 0x40
+#define ST_P_IDP 0x20
+#define ST_P_PSUM 0x18 /* units of part defs.. */
+#define ST_P_PSUM_BYTES 0x0 /* units of part defs.. */
+#define ST_P_PSUM_KBYTES 0x08 /* units of part defs.. */
+#define ST_P_PSUM_MBYTES 0x10 /* units of part defs.. */
+ u_char medium_format_recog;
+#define ST_P_REC_NONE 0x00
+#define ST_P_REC_FMT 0x01 /* can recognise format of new media */
+#define ST_P_REC_PART 0x02 /* can recognise partitions of new media */
+#define ST_P_REC_FMT_PART 0x03 /* can recognise format and parts */
+ u_char reserved1;
+ u_char reserved2;
+ struct
+ {
+ u_char high;
+ u_char low;
+ }part[ST_MAXPARTS];
+ } medium_partition;
+ struct
+ {
+ struct
+ {
+ u_char high;
+ u_char low;
+ }part[ST_MAXPARTS];
+ } medium_partition_extra;
+ }pages;
+};
+
+
#ifndef NEW_SCSICONF
diff --git a/sys/scsi/scsiconf.c b/sys/scsi/scsiconf.c
index 5724c72..4aac5c6 100644
--- a/sys/scsi/scsiconf.c
+++ b/sys/scsi/scsiconf.c
@@ -16,7 +16,7 @@
*
* New configuration setup: dufault@hda.com
*
- * $Id: scsiconf.c,v 1.24 1995/03/16 18:15:49 bde Exp $
+ * $Id: scsiconf.c,v 1.25 1995/03/19 14:29:06 davidg Exp $
*/
#include <sys/types.h>
@@ -473,9 +473,10 @@ scsi_init(void)
}
/* Feel free to take this out when everyone is sure this config
- * code works well:
+ * code works well. For now it lets us tell new configurations from
+ * old ones.
*/
-#define CONFIGD() printf(" is configured at ")
+#define CONFIG_NOISE
/* scsi_bus_conf: Figure out which bus this is. If it is wired in config
* use that. Otherwise use the next free one.
@@ -492,7 +493,6 @@ scsi_bus_conf(sc_link_proto)
* next available bus.
*/
- printf("scbus");
bus = SCCONF_UNSPEC;
for (i = 0; scsi_cinit[i].driver; i++) {
if (IS_SPECIFIED(scsi_cinit[i].unit))
@@ -500,8 +500,10 @@ scsi_bus_conf(sc_link_proto)
if (!strcmp(sc_link_proto->adapter->name, scsi_cinit[i].driver) &&
(sc_link_proto->adapter_unit == scsi_cinit[i].unit) )
{
- CONFIGD();
bus = scsi_cinit[i].bus;
+#ifdef CONFIG_NOISE
+ printf("Choosing drivers for scbus configured at %d\n", bus);
+#endif
break;
}
}
@@ -510,8 +512,6 @@ scsi_bus_conf(sc_link_proto)
if (bus == SCCONF_UNSPEC)
bus = free_bus++;
- printf("%d: ", bus);
-
return bus;
}
@@ -535,7 +535,7 @@ scsi_assign_unit(struct scsi_link *sc_link)
sc_link->scsibus == scsi_dinit[i].cunit) {
sc_link->dev_unit = scsi_dinit[i].unit;
found = 1;
-#ifdef CONFIGD
+#ifdef CONFIG_NOISE
printf("%s is configured at %d\n",
sc_link->device->name, sc_link->dev_unit);
#endif
@@ -565,6 +565,13 @@ scsi_attachdevs(sc_link_proto)
if ( (scsibus = scsi_bus_conf(sc_link_proto)) == -1) {
return;
}
+ /*
+ * if the adapter didn't give us this, set a default
+ * (compatibility with old adapter drivers)
+ */
+ if(!(sc_link_proto->opennings)) {
+ sc_link_proto->opennings = 1;
+ }
sc_link_proto->scsibus = scsibus;
scbus = malloc(sizeof(struct scsibus_data), M_TEMP, M_NOWAIT);
if(scbus == 0 || extend_set(scbusses, scsibus, scbus) == 0) {
@@ -722,7 +729,6 @@ scsi_probe_bus(int bus, int targ, int lun)
sc_link = malloc(sizeof(*sc_link), M_TEMP, M_NOWAIT);
}
*sc_link = *sc_link_proto; /* struct copy */
- sc_link->opennings = 1;
sc_link->device = &probe_switch;
sc_link->target = targ;
sc_link->lun = lun;
diff --git a/sys/scsi/scsiconf.h b/sys/scsi/scsiconf.h
index 47c963b..66c4fc2 100644
--- a/sys/scsi/scsiconf.h
+++ b/sys/scsi/scsiconf.h
@@ -14,7 +14,7 @@
*
* Ported to run under 386BSD by Julian Elischer (julian@tfs.com) Sept 1992
*
- * $Id: scsiconf.h,v 1.19 1995/03/04 20:51:00 dufault Exp $
+ * $Id: scsiconf.h,v 1.20 1995/03/16 18:15:50 bde Exp $
*/
#ifndef SCSI_SCSICONF_H
#define SCSI_SCSICONF_H 1
@@ -138,8 +138,6 @@ struct scsi_adapter
* Format of adapter_info() response data
* e.g. maximum number of entries queuable to a device by the adapter
*/
-#define AD_INF_MAX_CMDS 0x000000FF
-/* 24 bits of other adapter characteristics go here */
/* Don't poke around inside of "scsi_data". Each low level
* driver has its own definition for it.
@@ -341,21 +339,21 @@ struct scsi_link
/* 40*/ struct scsi_data *sd; /* Device data structure */
/* 44+*/struct scsi_inquiry_data inqbuf; /* Inquiry data */
};
-#define SDEV_MEDIA_LOADED 0x00000001 /* device figures are still valid */
-#define SDEV_WAITING 0x00000002 /* a process is waiting for this */
-#define SDEV_OPEN 0x00000004 /* at least 1 open session */
/* XXX dufault@hda.com: SDEV_BOUNCE is set down in the adapter drivers
* in an sc_link structure to indicate that this host adapter requires
- * ISA DMA bounce buffers. I think eventually the link structure should
+ * ISA DMA bounce buffers. I think the link structure should
* be associated only with the type drive and not the adapter driver,
* and the bounce flag should be in something associated with the
* adapter driver.
*/
-#define SDEV_BOUNCE 0x00000008 /* unit requires DMA bounce buffer */
-
-#define SDEV_DBX 0x000000F0 /* debuging flags (scsi_debug.h) */
-#define SDEV_ONCE_ONLY 0x00010000 /* unit can only be opened once */
+#define SDEV_MEDIA_LOADED 0x0001 /* device figures are still valid */
+#define SDEV_WAITING 0x0002 /* a process is waiting for this */
+#define SDEV_OPEN 0x0004 /* at least 1 open session */
+#define SDEV_BOUNCE 0x0008 /* unit requires DMA bounce buffer */
+#define SDEV_DBX 0x00F0 /* debugging flags (scsi_debug.h) */
+#define SDEV_ONCE_ONLY 0x0100 /* unit can only be opened once */
+#define SDEV_BOOTVERBOSE 0x0200 /* be noisy during boot */
/*
* One of these is allocated and filled in for each scsi bus.
@@ -458,11 +456,11 @@ errval scsi_start_unit( struct scsi_link *sc_link, u_int32 flags);
errval scsi_stop_unit(struct scsi_link *sc_link, u_int32 eject, u_int32 flags);
void scsi_done(struct scsi_xfer *xs);
void scsi_user_done(struct scsi_xfer *xs);
-errval scsi_scsi_cmd( struct scsi_link *sc_link, struct scsi_generic *scsi_cmd,
- u_int32 cmdlen, u_char *data_addr,
- u_int32 datalen, u_int32 retries,
- u_int32 timeout, struct buf *bp,
- u_int32 flags);
+errval scsi_scsi_cmd __P(( struct scsi_link *, struct scsi_generic *,
+ u_int32, u_char *,
+ u_int32, u_int32,
+ u_int32, struct buf *,
+ u_int32));
int scsi_do_ioctl __P((dev_t dev, int cmd, caddr_t addr, int mode,
struct proc *p, struct scsi_link *sc_link));
@@ -472,25 +470,27 @@ struct proc *p)));
int scsi_opened_ok __P((dev_t dev, int flag, int type, struct scsi_link *sc_link));
-char *scsi_sense_desc(int asc, int ascq);
-void scsi_sense_print(struct scsi_xfer *xs);
-void show_scsi_xs(struct scsi_xfer *xs);
-void show_scsi_cmd(struct scsi_xfer *xs);
-void show_mem(unsigned char * , u_int32);
+char *scsi_sense_desc __P((int, int));
+void scsi_sense_print __P((struct scsi_xfer *));
+void show_scsi_xs __P((struct scsi_xfer *));
+void show_scsi_cmd __P((struct scsi_xfer *));
+void show_mem __P((unsigned char * , u_int32));
-void scsi_uto3b __P((u_int32 val, u_char *bytes));
-u_int32 scsi_3btou __P((u_char *bytes));
-int32 scsi_3btoi __P((u_char *bytes));
-void scsi_uto4b __P((u_int32 val, u_char *bytes));
-u_int32 scsi_4btou __P((u_char *bytes));
-void scsi_uto2b __P((u_int32 val, u_char *bytes));
-u_int32 scsi_2btou __P((u_char *bytes));
+void scsi_uto3b __P((u_int32 , u_char *));
+u_int32 scsi_3btou __P((u_char *));
+int32 scsi_3btoi __P((u_char *));
+void scsi_uto4b __P((u_int32, u_char *));
+u_int32 scsi_4btou __P((u_char *));
+void scsi_uto2b __P((u_int32, u_char *));
+u_int32 scsi_2btou __P((u_char *));
-extern void sc_print_addr(struct scsi_link *);
+void sc_print_addr __P((struct scsi_link *));
+void sc_print_start __P((struct scsi_link *));
+void sc_print_finish __P((void));
-extern int scsi_externalize(struct scsi_link *, void *, size_t *);
+extern int scsi_externalize __P((struct scsi_link *, void *, size_t *));
-void scsi_device_register(struct scsi_device *sd);
+void scsi_device_register __P((struct scsi_device *sd));
extern struct kern_devconf kdc_scbus0; /* XXX should go away */
diff --git a/sys/scsi/sd.c b/sys/scsi/sd.c
index 62d05d2..bad3c72 100644
--- a/sys/scsi/sd.c
+++ b/sys/scsi/sd.c
@@ -14,7 +14,7 @@
*
* Ported to run under 386BSD by Julian Elischer (julian@dialix.oz.au) Sept 1992
*
- * $Id: sd.c,v 1.54 1995/03/15 14:22:10 dufault Exp $
+ * $Id: sd.c,v 1.55 1995/03/16 18:15:52 bde Exp $
*/
#define SPLSD splbio
@@ -46,7 +46,7 @@
u_int32 sdstrats, sdqueues;
#define SECSIZE 512
-#define SDOUTSTANDING 2
+#define SDOUTSTANDING 4
#define SD_RETRIES 4
#define MAXTRANSFER 8 /* 1 page at a time */
@@ -70,8 +70,6 @@ struct scsi_data {
#define SDHAVELABEL 0x10 /* have read the label */
#define SDDOSPART 0x20 /* Have read the DOS partition table */
#define SDWRITEPROT 0x40 /* Device in readonly mode (S/W) */
- u_int32 ad_info; /* info about the adapter */
- u_int32 cmdscount; /* cmds allowed outstanding by board */
boolean wlabel; /* label is writable */
struct disk_parms {
u_char heads; /* Number of heads */
@@ -187,20 +185,8 @@ sdattach(struct scsi_link *sc_link)
dp = &(sd->params);
- printf("\n");
- sc_print_addr(sc_link);
-
- if (sc_link->adapter->adapter_info) {
- sd->ad_info = ((*(sc_link->adapter->adapter_info)) (sc_link->adapter_unit));
- sd->cmdscount = sd->ad_info & AD_INF_MAX_CMDS;
- if (sd->cmdscount > SDOUTSTANDING) {
- sd->cmdscount = SDOUTSTANDING;
- }
- } else {
- sd->ad_info = 1;
- sd->cmdscount = 1;
- }
- sc_link->opennings = sd->cmdscount;
+ if (sc_link->opennings > SDOUTSTANDING)
+ sc_link->opennings = SDOUTSTANDING;
/*
* Use the subdriver to request information regarding
* the drive. We cannot use interrupts yet, so the
@@ -213,13 +199,19 @@ sdattach(struct scsi_link *sc_link)
* -- this avoids the division below from falling over
*/
if(dp->secsiz == 0) dp->secsiz = 512;
- printf("%ldMB (%ld sectors), %d C %d H %d S/T %d B/S",
+ printf("%ldMB (%ld %d byte sectors)",
dp->disksize / ((1024L * 1024L) / dp->secsiz),
dp->disksize,
- dp->cyls,
- dp->heads,
- dp->sectors,
dp->secsiz);
+
+ if ( (sc_link->flags & SDEV_BOOTVERBOSE) )
+ {
+ printf("\n");
+ sc_print_addr(sc_link);
+ printf("with %d cyls, %d heads, and an average %d sectors/track",
+ dp->cyls, dp->heads, dp->sectors);
+ }
+
sd->flags |= SDINIT;
sd_registerdev(unit);
diff --git a/sys/scsi/st.c b/sys/scsi/st.c
index d57a7cf..c391b0a 100644
--- a/sys/scsi/st.c
+++ b/sys/scsi/st.c
@@ -12,7 +12,7 @@
* on the understanding that TFS is not responsible for the correct
* functioning of this software in any circumstances.
*
- * $Id: st.c,v 1.29 1995/03/04 20:51:05 dufault Exp $
+ * $Id: st.c,v 1.30 1995/03/15 14:22:11 dufault Exp $
*/
/*
@@ -153,13 +153,16 @@ static struct rogues gallery[] = /* ends with an all-null entry */
errval st_space __P((u_int32 unit, int32 number, u_int32 what, u_int32 flags));
errval st_rewind __P((u_int32 unit, boolean immed, u_int32 flags));
errval st_erase __P((u_int32 unit, boolean immed, u_int32 flags)); /* AKL */
-static errval st_mode_sense __P((u_int32 unit, u_int32 flags));
+static errval st_mode_sense __P((u_int32 unit, u_int32 flags, \
+ struct tape_pages *page, u_int32 pagelen, u_int32 pagecode));
errval st_decide_mode __P((u_int32 unit, boolean first_read));
errval st_rd_blk_lim __P((u_int32 unit, u_int32 flags));
errval st_touch_tape __P((u_int32 unit));
errval st_write_filemarks __P((u_int32 unit, int32 number, u_int32 flags));
errval st_load __P((u_int32 unit, u_int32 type, u_int32 flags));
-errval st_mode_select __P((u_int32 unit, u_int32 flags));
+errval st_mode_select __P((u_int32 unit, u_int32 flags, \
+ struct tape_pages *page, u_int32 pagelen));
+errval st_comp __P((u_int32 unit, u_int32 mode));
void ststrategy();
int32 st_chkeod();
void ststart(u_int32 unit);
@@ -180,6 +183,7 @@ struct scsi_data {
u_int32 flags; /* see below */
u_int32 blksiz; /* blksiz we are using */
u_int32 density; /* present density */
+ u_int32 comp; /* present compression mode */
u_int32 quirks; /* quirks for the open mode */
u_int32 last_dsty; /* last density openned */
/*--------------------parameters reported by the device ----------------------*/
@@ -205,8 +209,10 @@ struct scsi_data {
#define DENSITY_SET_BY_QUIRK 0x02
#define BLKSIZE_SET_BY_USER 0x04
#define BLKSIZE_SET_BY_QUIRK 0x08
+#define COMPRES_SET_BY_USER 0x10
+#define COMPRES_SET_BY_QUIRK 0x20
/*--------------------storage for sense data returned by the drive------------*/
- unsigned char sense_data[12]; /*
+ unsigned char saved_page0[PAGE_0_SENSE_DATA_SIZE]; /*
* additional sense data needed
* for mode sense/select.
*/
@@ -333,7 +339,8 @@ stattach(struct scsi_link *sc_link)
* the drive. We cannot use interrupts yet, so the
* request must specify this.
*/
- if (st_mode_sense(unit, SCSI_NOSLEEP | SCSI_NOMASK | SCSI_SILENT)) {
+ if (st_mode_sense(unit, SCSI_NOSLEEP | SCSI_NOMASK | SCSI_SILENT,
+ NULL, 0, 0)) {
printf("drive offline");
} else {
printf("density code 0x%x, ", st->media_density);
@@ -678,7 +685,7 @@ st_mount_tape(dev, flags)
* As we have a tape in, it should be reflected here.
* If not you may need the "quirk" above.
*/
- if (errno = st_mode_sense(unit, 0)) {
+ if (errno = st_mode_sense(unit, 0, NULL, 0, 0)) {
return errno;
}
/*
@@ -707,7 +714,7 @@ st_mount_tape(dev, flags)
return errno;
}
}
- if (errno = st_mode_select(unit, 0)) {
+ if (errno = st_mode_select(unit, 0, NULL, 0)) {
printf("st%d: Cannot set selected mode", unit);
return errno;
}
@@ -1141,6 +1148,7 @@ struct proc *p, struct scsi_link *sc_link)
g->mt_type = 0x7; /* Ultrix compat *//*? */
g->mt_density = st->density;
g->mt_blksiz = st->blksiz;
+ g->mt_comp = st->comp;
g->mt_density0 = st->modes[0].density;
g->mt_density1 = st->modes[1].density;
g->mt_density2 = st->modes[2].density;
@@ -1149,6 +1157,10 @@ struct proc *p, struct scsi_link *sc_link)
g->mt_blksiz1 = st->modes[1].blksiz;
g->mt_blksiz2 = st->modes[2].blksiz;
g->mt_blksiz3 = st->modes[3].blksiz;
+ g->mt_comp0 = 0;
+ g->mt_comp1 = 0;
+ g->mt_comp2 = 0;
+ g->mt_comp3 = 0;
break;
}
case MTIOCTOP:
@@ -1222,6 +1234,9 @@ struct proc *p, struct scsi_link *sc_link)
}
goto try_new_value;
+ case MTCOMP: /* enable default compression */
+ errcode = st_comp(unit,number);
+ break;
default:
errcode = EINVAL;
}
@@ -1244,7 +1259,7 @@ try_new_value:
* Check that the mode being asked for is aggreeable to the
* drive. If not, put it back the way it was.
*/
- if (errcode = st_mode_select(unit, 0)) { /* put it back as it was */
+ if (errcode = st_mode_select(unit, 0, NULL, 0)) { /* put it back as it was */
printf("st%d: Cannot set selected mode", unit);
st->density = hold_density;
st->blksiz = hold_blksiz;
@@ -1379,86 +1394,83 @@ st_rd_blk_lim(unit, flags)
* ioctl (to reset original blksize)
*/
static errval
-st_mode_sense(unit, flags)
+st_mode_sense(unit, flags, page, pagelen, pagecode)
u_int32 unit, flags;
+ struct tape_pages *page;
+ u_int32 pagelen,pagecode;
{
- u_int32 scsi_sense_len;
+ u_int32 dat_len;
errval errno;
- char *scsi_sense_ptr;
struct scsi_mode_sense scsi_cmd;
- struct scsi_sense {
+ struct {
struct scsi_mode_header header;
struct blk_desc blk_desc;
- } scsi_sense;
+ struct tape_pages page;
+ } dat;
- struct scsi_sense_page_0 {
- struct scsi_mode_header header;
- struct blk_desc blk_desc;
- unsigned char sense_data[PAGE_0_SENSE_DATA_SIZE];
- /* Tandberg tape drives returns page 00
- * with the sense data, whether or not
- * you want it( ie the don't like you
- * saying you want anything less!!!!!
- * They also expect page 00
- * back when you issue a mode select
- */
- } scsi_sense_page_0;
+ /* Tandberg tape drives returns page 00
+ * with the sense data, whether or not
+ * you want it( ie the don't like you
+ * saying you want anything less!!!!!
+ * They also expect page 00
+ * back when you issue a mode select
+ */
struct scsi_link *sc_link = SCSI_LINK(&st_switch, unit);
struct scsi_data *st = sc_link->sd;
/*
- * Define what sort of structure we're working with
+ * Check if we need to use a default page..
*/
- if (st->quirks & ST_Q_NEEDS_PAGE_0) {
- scsi_sense_len = sizeof(scsi_sense_page_0);
- scsi_sense_ptr = (char *) &scsi_sense_page_0;
- } else {
- scsi_sense_len = sizeof(scsi_sense);
- scsi_sense_ptr = (char *) &scsi_sense;
+ if ((st->quirks & ST_Q_NEEDS_PAGE_0) && (!page)) {
+ pagelen = PAGE_0_SENSE_DATA_SIZE;
+ page = (struct tape_pages *) st->saved_page0;
+ pagecode = 0;
}
/*
+ * Now work out the total dat size etc.
+ */
+ dat_len = sizeof(struct scsi_mode_header)
+ + sizeof(struct blk_desc)
+ + (page ? pagelen : 0);
+ /*
* Set up a mode sense
*/
bzero(&scsi_cmd, sizeof(scsi_cmd));
scsi_cmd.op_code = MODE_SENSE;
- scsi_cmd.length = scsi_sense_len;
+ scsi_cmd.page = (u_char) pagecode;
+ scsi_cmd.length = dat_len;
/*
- * do the command, but we don't need the results
- * just print them for our interest's sake, if asked,
+ * do the command,
+ * use the results to set blksiz, numblks and density
* or if we need it as a template for the mode select
* store it away.
*/
if (errno = scsi_scsi_cmd(sc_link,
(struct scsi_generic *) &scsi_cmd,
sizeof(scsi_cmd),
- (u_char *) scsi_sense_ptr,
- scsi_sense_len,
+ (u_char *) &dat,
+ dat_len,
ST_RETRIES,
5000,
NULL,
flags | SCSI_DATA_IN)) {
return errno;
}
- st->numblks = scsi_3btou(((struct scsi_sense *)scsi_sense_ptr)->blk_desc.nblocks);
- st->media_blksiz = scsi_3btou(((struct scsi_sense *)scsi_sense_ptr)->blk_desc.blklen);
- st->media_density = ((struct scsi_sense *) scsi_sense_ptr)->blk_desc.density;
- if (((struct scsi_sense *) scsi_sense_ptr)->header.dev_spec &
- SMH_DSP_WRITE_PROT) {
+ st->numblks = scsi_3btou(dat.blk_desc.nblocks);
+ st->media_blksiz = scsi_3btou(dat.blk_desc.blklen);
+ st->media_density = dat.blk_desc.density;
+ if (dat.header.dev_spec & SMH_DSP_WRITE_PROT) {
st->flags |= ST_READONLY;
}
SC_DEBUG(sc_link, SDEV_DB3,
("density code 0x%x, %d-byte blocks, write-%s, ",
st->media_density, st->media_blksiz,
st->flags & ST_READONLY ? "protected" : "enabled"));
- SC_DEBUG(sc_link, SDEV_DB3,
- ("%sbuffered\n",
- ((struct scsi_sense *) scsi_sense_ptr)->header.dev_spec
- & SMH_DSP_BUFF_MODE ? "" : "un"));
- if (st->quirks & ST_Q_NEEDS_PAGE_0) {
- bcopy(((struct scsi_sense_page_0 *) scsi_sense_ptr)->sense_data,
- st->sense_data,
- sizeof(((struct scsi_sense_page_0 *) scsi_sense_ptr)->sense_data));
+ SC_DEBUG(sc_link, SDEV_DB3, ("%sbuffered\n",
+ ((dat.header.dev_spec & SMH_DSP_BUFF_MODE) ? "" : "un")));
+ if (page) {
+ bcopy(&dat.page, page, pagelen);
}
sc_link->flags |= SDEV_MEDIA_LOADED;
return 0;
@@ -1469,50 +1481,50 @@ st_mode_sense(unit, flags)
* set it into the desire modes etc.
*/
errval
-st_mode_select(unit, flags)
+st_mode_select(unit, flags, page, pagelen)
u_int32 unit, flags;
+ struct tape_pages *page;
+ u_int32 pagelen;
{
u_int32 dat_len;
- char *dat_ptr;
struct scsi_mode_select scsi_cmd;
- struct dat {
+ struct {
struct scsi_mode_header header;
struct blk_desc blk_desc;
+ struct tape_pages page;
} dat;
- struct dat_page_0 {
- struct scsi_mode_header header;
- struct blk_desc blk_desc;
- unsigned char sense_data[PAGE_0_SENSE_DATA_SIZE];
- } dat_page_0;
struct scsi_link *sc_link = SCSI_LINK(&st_switch, unit);
struct scsi_data *st = sc_link->sd;
/*
- * Define what sort of structure we're working with
+ * Check if we need to use a default page..
+ * Gee, hope we saved one before now........
*/
- if (st->quirks & ST_Q_NEEDS_PAGE_0) {
- dat_len = sizeof(dat_page_0);
- dat_ptr = (char *) &dat_page_0;
- } else {
- dat_len = sizeof(dat);
- dat_ptr = (char *) &dat;
+ if ((st->quirks & ST_Q_NEEDS_PAGE_0) && (!page)) {
+ pagelen = PAGE_0_SENSE_DATA_SIZE;
+ page = (struct tape_pages *) st->saved_page0;
}
/*
+ * Now work out the total dat size etc.
+ */
+ dat_len = sizeof(struct scsi_mode_header)
+ + sizeof(struct blk_desc)
+ + (page ? pagelen : 0);
+ /*
* Set up for a mode select
*/
- bzero(dat_ptr, dat_len);
+ bzero(&dat, dat_len);
bzero(&scsi_cmd, sizeof(scsi_cmd));
scsi_cmd.op_code = MODE_SELECT;
scsi_cmd.length = dat_len;
- ((struct dat *) dat_ptr)->header.blk_desc_len = sizeof(struct blk_desc);
- ((struct dat *) dat_ptr)->header.dev_spec |= SMH_DSP_BUFF_MODE_ON;
- ((struct dat *) dat_ptr)->blk_desc.density = st->density;
+ dat.header.blk_desc_len = sizeof(struct blk_desc);
+ dat.header.dev_spec |= SMH_DSP_BUFF_MODE_ON;
+ dat.blk_desc.density = st->density;
if (st->flags & ST_FIXEDBLOCKS) {
- scsi_uto3b(st->blksiz, ((struct dat *) dat_ptr)->blk_desc.blklen);
+ scsi_uto3b(st->blksiz, dat.blk_desc.blklen);
}
- if (st->quirks & ST_Q_NEEDS_PAGE_0) {
- bcopy(st->sense_data, ((struct dat_page_0 *) dat_ptr)->sense_data,
- sizeof(((struct dat_page_0 *) dat_ptr)->sense_data));
+ if (page) {
+ bcopy(page, &dat.page, pagelen);
/* the Tandberg tapes need the block size to */
/* be set on each mode sense/select. */
}
@@ -1522,7 +1534,7 @@ st_mode_select(unit, flags)
return (scsi_scsi_cmd(sc_link,
(struct scsi_generic *) &scsi_cmd,
sizeof(scsi_cmd),
- (u_char *) dat_ptr,
+ (u_char *) &dat,
dat_len,
ST_RETRIES,
5000,
@@ -1530,6 +1542,56 @@ st_mode_select(unit, flags)
flags | SCSI_DATA_OUT));
}
+int noisy_st = 0;
+/***************************************************************\
+* Set the compression mode of the drive to on (1) or off (0) *
+ still doesn't work! grrr!
+\***************************************************************/
+errval st_comp(unit,mode)
+u_int32 unit,mode;
+{
+ struct tape_pages page;
+ int pagesize;
+ int retval;
+ struct scsi_link *sc_link = SCSI_LINK(&st_switch, unit);
+ struct scsi_data *st = sc_link->sd;
+
+ bzero(&page, sizeof(page));
+ pagesize = sizeof(page.pages.configuration) + PAGE_HEADERLEN;
+
+ if ( retval = st_mode_sense(unit, 0,
+ &page, pagesize, ST_PAGE_CONFIGURATION))
+ {
+ printf("sense returned an error of %d\n",retval);
+ return retval;
+ }
+ if ( noisy_st)
+ printf("drive reports value of %d, setting %d\n",
+ page.pages.configuration.data_compress_alg,mode);
+
+ page.pg_code &= ST_P_CODE;
+ page.pg_length = sizeof(page.pages.configuration);
+
+ switch(mode)
+ {
+ case 0:
+ page.pages.configuration.data_compress_alg = 0;
+ break;
+ case 1:
+ page.pages.configuration.data_compress_alg = 1;
+ break;
+ default:
+ printf("st%d: bad value for compression mode\n",unit);
+ return EINVAL;
+ }
+ if ( retval = st_mode_select(unit, 0, &page, pagesize))
+ {
+ printf("select returned an error of %d\n",retval);
+ return retval;
+ }
+ st->comp = mode;
+ return 0;
+}
/*
* skip N blocks/filemarks/seq filemarks/eom
*/
@@ -1969,7 +2031,7 @@ st_touch_tape(unit)
if (!buf)
return (ENOMEM);
- if (errno = st_mode_sense(unit, 0)) {
+ if (errno = st_mode_sense(unit, 0, NULL, 0, 0)) {
goto bad;
}
st->blksiz = 1024;
@@ -1983,7 +2045,7 @@ st_touch_tape(unit)
default:
readsiz = 1;
st->flags &= ~ST_FIXEDBLOCKS;
- } if (errno = st_mode_select(unit, 0)) {
+ } if (errno = st_mode_select(unit, 0, NULL, 0)) {
goto bad;
}
st_read(unit, buf, readsiz, SCSI_SILENT);
OpenPOWER on IntegriCloud