diff options
author | Theo de Raadt <deraadt@cvs.openbsd.org> | 2001-03-23 02:16:43 +0000 |
---|---|---|
committer | Theo de Raadt <deraadt@cvs.openbsd.org> | 2001-03-23 02:16:43 +0000 |
commit | 701e28ff72b67897a05119207391d12510875cad (patch) | |
tree | d16fef8a240c2c7e1f38ffaf7b688199dfee1def | |
parent | daa918d5064a0ca12562ca72409d586abc3174f3 (diff) |
atactl SMART support; wouter@yourcreativesolutions.nl
-rw-r--r-- | sbin/atactl/atactl.8 | 214 | ||||
-rw-r--r-- | sbin/atactl/atactl.c | 323 | ||||
-rw-r--r-- | sys/dev/ata/atareg.h | 64 | ||||
-rw-r--r-- | sys/dev/ic/wdcreg.h | 49 |
4 files changed, 604 insertions, 46 deletions
diff --git a/sbin/atactl/atactl.8 b/sbin/atactl/atactl.8 index 42b059d542c..c32c135b039 100644 --- a/sbin/atactl/atactl.8 +++ b/sbin/atactl/atactl.8 @@ -1,4 +1,4 @@ -.\" $OpenBSD: atactl.8,v 1.4 2000/04/12 16:50:52 aaron Exp $ +.\" $OpenBSD: atactl.8,v 1.5 2001/03/23 02:16:42 deraadt Exp $ .\" $NetBSD: atactl.8,v 1.5 1999/02/24 18:49:14 jwise Exp $ .\" .\" Copyright (c) 1998 The NetBSD Foundation, Inc. @@ -71,7 +71,7 @@ command is implied. .Cm identify .Pp Identify the specified device, displaying the device's vendor, product, -revision strings, and the device's capabilities. +revision strings, supported capabilities and enabled capabilities. .Pp .Cm idle .Pp @@ -85,7 +85,7 @@ This mode will consume less power than Idle mode. .Pp .Cm sleep .Pp -Place he specified device into Sleep mode. +Place the specified device into Sleep mode. This mode will consume less power than Standby mode, but requires a device reset to resume operation. Typically the @@ -115,6 +115,199 @@ A value of 0 will disable the Standby timer. .Pp Will print out if the device is in Active, Idle, or Standby power management mode. +.Pp +.Cm apmset +.Ar power-management-level +.Pp +Enables and sets the advanced power management level to the requested +level on the specified device (if supported). Device performance may +increase with increasing power management levels at the cost of +potentially requiring more power. Values up to and including 126 allow +the device to go into standby mode and spin-down the disk. This +.Em may cause disk time-outs +and is therefor +.Em not +recommended. These values are more suitable optimization for low power +usage on infrequently used devices. Values 127 up to and including 253 +do not allow the device to go to standby mode and are more suitable for +optimization for performance. Support for advanced power management is +indicated by the device with +.Sq Advanced Power Management feature set +in the output of the +.Cm identify +command. +.Pp +.Cm apmdisable +.Pp +Disables support for advanced power management on the specified device. +Note that devices supporting advanced powermanagement may refuse to +disable it, resulting in an +.Sq ATA device returned Aborted Command +warning. +.Pp +.Cm acousticset +.Ar acoustic-management-level +.Pp +Enables and sets the automatic acoustic management level to the requested +level on the specified device (if supported). Device performance may +increase with increasing automatic acoustic management levels at the cost of +potentially generating more noise and requiring more power. Valid values are +0 up to and including 126. Support for automatic acoustic management is +indicated by the device with +.Sq Automatic Acoustic Management feature set +in the output of the +.Cm identify +command. +.Pp +.Cm acousticdisable +.Pp +Disables support for automatic acoustic management on the specified device. +Note that devices supporting automatic acoustic management may refuse to +disable it, resulting in an +.Sq ATA device returned Aborted Command +warning. +.Pp +.Cm podenable +.Pp +Allows the specified device to revert to power-on default (pod) settings +after a reset. +.Pp +.Cm poddisable +.Pp +Disallows the specified device to revert to power-on default (pod) settings +after a reset. +.Pp +.Cm puisenable +.Pp +Enables power-up in standby (puis) on the specified device, causing the +device to wait with spinning up the disks after power-up. This may cause +problems at boot if the device is to slow in spin-up. This options is +therefor +.Em not recommended +unless really understand the implications. Note that the power-up in +standby mode stays enabled over power-downs, hardware and software +resets. +Support for power-up in standby is indicated by the device with +.Sq Power-up in standby feature set +in the output of the +.Cm identify +command. +.Pp +.Cm puisdisable +.Pp +Disables power-up in standby (puis) on the specified device, causing the +device to spin up the disks after power-up. This should be the factory +default setting of the device and it is recommended to leave this +setting disabled. +.Pp +.Cm puisspinup +.Pp +Explicitly spins up the device if it powered-up into standby mode (i.e. +power-up in standby was enabled). +.Pp +.Cm readaheadenable +.Pp +Enables read look-ahead on the specified device. This may increase +performance. Support for and status of read look-ahead is indicated by +the device with +.Sq read look-ahead +in the output of the +.Cm identify +command. +.Pp +.Cm readaheaddisable +.Pp +Disables read look-ahead on the specified device. This may decrease +performance. Note that the device may use +.Sq vendor specific +behaviour in implementing this, so it is +.Em not +recommended to issue this command on a disk containing any currently +mounted filesystems. +.Pp +.Cm smartenable +.Pp +Enables SMART (Self-Monitoring, Analysis, and Reporting Technology) on the +specified device (if supported). This causes the device to record information +for prediction of device degradation and/or faults. Support for SMART is +indicated by the device with +.Sq SMART feature set +in the output of the +.Cm identify +command. +.Pp +.Cm smartdisable +.Pp +Disables support for SMART on the specified device. Note that this means that +the device will no longer record any SMART information. +.Pp +.Cm smartstatus +.Pp +Reads the reliability status of the specified device. If the device reports +that one of its thresholds is exceeded (a strong indication of imminent +failure), the warning +.Sq SMART threshold exceeded! +is printed to stderr and a status of 2 is returned. Note that SMART +.Em must +be enabled or the device will return an error. +.Pp +.Cm writecachedisable +.Pp +Disable the write cache on the specified device (if supported). This may +decrease performance. Support for and status of write caching is +indicated by the device with +.Sq write cache +in the output of the +.Cm identify +command. +.Pp +.Cm writecacheenable +.Pp +Enables the write cache on the specified device (if supported). This may +increase performance, however data still in the device's cache at +powerdown +.Em may be lost. +The +.Xr wd 4 +driver performs a cache flush automatically before shutdown. +.Sh EXAMPLES +.Cm atactl /dev/wd0c identify +.Pp +Displays the vendor, product, revision strings and capabilities (such as +support for SMART) as reported by +.Pa /dev/wd0 . +.Pp +.Cm atactl /dev/wd1c smartenable +.Pp +Enables the SMART support on +.Pa /dev/wd1 +for detection of early warning signs of device failure. +.Pp +.Cm 0 * * * * /sbin/atactl /dev/wd0c smartstatus >/dev/null +.Pp +In a +.Xr crontab 5 +entry queries +.Pa /dev/wd0 +each hour for early warning signs of failure. If the device exceeded one +of the SMART thresholds, +.Nm +will output +.Sq SMART threshold exceeded! +to stderr and +.Xr cron 8 +wil mail it. +.Sh DIAGNOSTICS +.Pp +Not all devices are created equally. Some may not support the feature sets +and/or commands needed to perform the requested action, even when the +.Cm identify +command indicates support for the requested action. The device will +typically respond with an +.Sq ATA device returned Aborted Command +if the requested action is not supported. Similarly a device might +not implement all commands in a feature set, so even though disabling a +feature works, enabling might not. .Sh SEE ALSO .Xr ioctl 2 , .Xr wd 4 @@ -125,12 +318,27 @@ command was written by Ken Hornstein. It was based heavily on the .Xr scsictl 8 command written by Jason R. Thorpe. +Support for acoustic management, advanced power management, power-up in +standby, read look-ahead and SMART was added by Wouter Slegers. .Sh HISTORY The .Nm command first appeared in .Ox 2.6 . +Support for acoustic management, advanced power management, power-up in +standby, read look-ahead and SMART was added in +.Ox 2.9 . .Sh BUGS The output from the .Cm identify command is rather ugly. +.Pp +Disabling read look-head with the +.Cm readaheaddisable +might cause problems with mounted filesystems on that device. +.Pp +There is no support for reading SMART logs or initiating a SMART +selftest. +.Pp +There is no support for the Secure Mode commands (in particular the +Security Erase Unit). diff --git a/sbin/atactl/atactl.c b/sbin/atactl/atactl.c index 21ddb5ea625..c9dd66df47f 100644 --- a/sbin/atactl/atactl.c +++ b/sbin/atactl/atactl.c @@ -1,4 +1,4 @@ -/* $OpenBSD: atactl.c,v 1.5 2000/07/13 15:12:34 deraadt Exp $ */ +/* $OpenBSD: atactl.c,v 1.6 2001/03/23 02:16:42 deraadt Exp $ */ /* $NetBSD: atactl.c,v 1.4 1999/02/24 18:49:14 jwise Exp $ */ /*- @@ -82,15 +82,35 @@ void device_identify __P((int, char *[])); void device_setidle __P((int, char *[])); void device_idle __P((int, char *[])); void device_checkpower __P((int, char *[])); +void device_acoustic __P((int, char *[])); +void device_apm __P((int, char *[])); +void device_feature __P((int, char *[])); +void device_smart __P((int, char *[])); struct command commands[] = { - { "identify", device_identify }, - { "setidle", device_setidle }, - { "setstandby", device_setidle }, - { "idle", device_idle }, - { "standby", device_idle }, - { "sleep", device_idle }, - { "checkpower", device_checkpower }, + { "identify", device_identify }, + { "setidle", device_setidle }, + { "setstandby", device_setidle }, + { "idle", device_idle }, + { "standby", device_idle }, + { "sleep", device_idle }, + { "checkpower", device_checkpower }, + { "acousticdisable", device_feature }, + { "acousticset", device_acoustic }, + { "apmdisable", device_feature }, + { "apmset", device_apm }, + { "poddisable", device_feature }, + { "podenable", device_feature }, + { "puisdisable", device_feature }, + { "puisenable", device_feature }, + { "puisspinup", device_feature }, + { "readaheaddisable", device_feature }, + { "readaheadenable", device_feature }, + { "smartenable", device_smart }, + { "smartdisable", device_smart }, + { "smartstatus", device_smart }, + { "writecachedisable", device_feature }, + { "writecacheenable", device_feature }, { NULL, NULL }, }; @@ -107,10 +127,20 @@ struct bitinfo ata_caps[] = { }; struct bitinfo ata_vers[] = { - { WDC_VER_ATA1, "ATA-1" }, - { WDC_VER_ATA2, "ATA-2" }, - { WDC_VER_ATA3, "ATA-3" }, - { WDC_VER_ATA4, "ATA-4" }, + { WDC_VER_ATA1, "ATA-1" }, + { WDC_VER_ATA2, "ATA-2" }, + { WDC_VER_ATA3, "ATA-3" }, + { WDC_VER_ATA4, "ATA-4" }, + { WDC_VER_ATA5, "ATA-5" }, + { WDC_VER_ATA6, "ATA-6" }, + { WDC_VER_ATA7, "ATA-7" }, + { WDC_VER_ATA8, "ATA-8" }, + { WDC_VER_ATA9, "ATA-9" }, + { WDC_VER_ATA10, "ATA-10" }, + { WDC_VER_ATA11, "ATA-11" }, + { WDC_VER_ATA12, "ATA-12" }, + { WDC_VER_ATA13, "ATA-13" }, + { WDC_VER_ATA14, "ATA-14" }, { NULL, NULL }, }; @@ -122,7 +152,7 @@ struct bitinfo ata_cmd_set1[] = { { WDC_CMD1_DVRST, "DEVICE RESET command" }, { WDC_CMD1_SRV, "SERVICE interrupt" }, { WDC_CMD1_RLSE, "release interrupt" }, - { WDC_CMD1_AHEAD, "look-ahead" }, + { WDC_CMD1_AHEAD, "read look-ahead" }, { WDC_CMD1_CACHE, "write cache" }, { WDC_CMD1_PKT, "PACKET command feature set" }, { WDC_CMD1_PM, "Power Management feature set" }, @@ -133,6 +163,14 @@ struct bitinfo ata_cmd_set1[] = { }; struct bitinfo ata_cmd_set2[] = { + { ATAPI_CMD2_FCE, "Flush Cache Ext command" }, + { ATAPI_CMD2_FC, "Flush Cache command" }, + { ATAPI_CMD2_DCO, "Device Configuration Overlay feature set" }, + { ATAPI_CMD2_48AD, "48bit address feature set" }, + { ATAPI_CMD2_AAM, "Automatic Acoustic Management feature set" }, + { ATAPI_CMD2_SM, "Set Max security extension commands" }, + { ATAPI_CMD2_SF, "Set Features subcommand required" }, + { ATAPI_CMD2_PUIS, "Power-up in standby feature set" }, { WDC_CMD2_RMSN, "Removable Media Status Notification feature set" }, { ATA_CMD2_APM, "Advanced Power Management feature set" }, { ATA_CMD2_CFA, "CFA feature set" }, @@ -141,6 +179,13 @@ struct bitinfo ata_cmd_set2[] = { { NULL, NULL }, }; +struct bitinfo ata_cmd_ext[] = { + { ATAPI_CMDE_MSER, "Media serial number" }, + { ATAPI_CMDE_TEST, "SMART self-test" }, + { ATAPI_CMDE_SLOG, "SMART error logging" }, + { NULL, NULL }, +}; + int main(argc, argv) int argc; @@ -237,14 +282,14 @@ ata_command(req) case ATACMD_ERROR: if (req->error & WDCE_ABRT) fprintf(stderr, "ATA device returned Aborted " - "Command\n"); + "Command\n"); else fprintf(stderr, "ATA device returned error register " - "%0x\n", req->error); + "%0x\n", req->error); exit(1); default: fprintf(stderr, "ATAIOCCOMMAND returned unknown result code " - "%d\n", req->retsts); + "%d\n", req->retsts); exit(1); } } @@ -355,9 +400,9 @@ device_identify(argc, argv) } printf("Model: %.*s, Rev: %.*s, Serial #: %.*s\n", - (int) sizeof(inqbuf->atap_model), inqbuf->atap_model, - (int) sizeof(inqbuf->atap_revision), inqbuf->atap_revision, - (int) sizeof(inqbuf->atap_serial), inqbuf->atap_serial); + (int) sizeof(inqbuf->atap_model), inqbuf->atap_model, + (int) sizeof(inqbuf->atap_revision), inqbuf->atap_revision, + (int) sizeof(inqbuf->atap_serial), inqbuf->atap_serial); printf("Device type: %s, %s\n", inqbuf->atap_config & WDC_CFG_ATAPI ? "ATAPI" : "ATA", inqbuf->atap_config & ATA_CFG_FIXED ? "fixed" : @@ -365,14 +410,14 @@ device_identify(argc, argv) if ((inqbuf->atap_config & WDC_CFG_ATAPI_MASK) == 0) printf("Cylinders: %d, heads: %d, sec/track: %d, total " - "sectors: %d\n", inqbuf->atap_cylinders, - inqbuf->atap_heads, inqbuf->atap_sectors, - (inqbuf->atap_capacity[1] << 16) | - inqbuf->atap_capacity[0]); + "sectors: %d\n", inqbuf->atap_cylinders, + inqbuf->atap_heads, inqbuf->atap_sectors, + (inqbuf->atap_capacity[1] << 16) | + inqbuf->atap_capacity[0]); if (inqbuf->atap_queuedepth & WDC_QUEUE_DEPTH_MASK) printf("Device supports command queue depth of %d\n", - inqbuf->atap_queuedepth & 0xf); + inqbuf->atap_queuedepth & 0xf); printf("Device capabilities:\n"); print_bitinfo("\t%s\n", inqbuf->atap_capabilities1, ata_caps); @@ -385,19 +430,26 @@ device_identify(argc, argv) if (inqbuf->atap_cmd_set1 != 0 && inqbuf->atap_cmd_set1 != 0xffff && inqbuf->atap_cmd_set2 != 0 && inqbuf->atap_cmd_set2 != 0xffff) { - printf("Command set support:\n"); + printf("Device supports the following command sets:\n"); print_bitinfo("\t%s\n", inqbuf->atap_cmd_set1, ata_cmd_set1); print_bitinfo("\t%s\n", inqbuf->atap_cmd_set2, ata_cmd_set2); + print_bitinfo("\t%s\n", inqbuf->atap_cmd_ext, ata_cmd_ext); } if (inqbuf->atap_cmd_def != 0 && inqbuf->atap_cmd_def != 0xffff) { - printf("Command sets/features enabled:\n"); + printf("Device has enabled the following command sets/features:\n"); + print_bitinfo("\t%s\n", inqbuf->atap_cmd1_en, ata_cmd_set1); + print_bitinfo("\t%s\n", inqbuf->atap_cmd2_en, ata_cmd_set2); +#if 0 print_bitinfo("\t%s\n", inqbuf->atap_cmd_set1 & - (WDC_CMD1_SRV | WDC_CMD1_RLSE | WDC_CMD1_AHEAD | - WDC_CMD1_CACHE | WDC_CMD1_SEC | WDC_CMD1_SMART), - ata_cmd_set1); + (WDC_CMD1_SRV | WDC_CMD1_RLSE | WDC_CMD1_AHEAD | + WDC_CMD1_CACHE | WDC_CMD1_SEC | WDC_CMD1_SMART), + ata_cmd_set1); print_bitinfo("\t%s\n", inqbuf->atap_cmd_set2 & - (WDC_CMD2_RMSN | ATA_CMD2_APM), ata_cmd_set2); + (WDC_CMD2_RMSN | ATA_CMD2_APM | ATAPI_CMD2_PUIS | + ATAPI_CMD2_AAM | ATAPI_CMD2_48AD | + ATAPI_CMD2_DCO), ata_cmd_set2); +#endif } return; @@ -444,6 +496,213 @@ usage: } /* + * SMART. + * + * issue the SMART ENABLE/DISABLE/STATUS commands to the drive + */ + +void +device_smart(argc, argv) + int argc; + char *argv[]; +{ + struct atareq req; + + /* No arguments. */ + if (argc != 0) + goto usage; + + memset(&req, 0, sizeof(req)); + + req.command = ATAPI_SMART; + req.cylinder = 0xC24F; /* Cylinders is mapped to LBA Mid/Low */ + /* XXX: I assume cylinders is correctly mapped w.r.t. + * endianness? */ + + if (strcmp(cmdname, "smartenable") == 0) + req.features = ATAPI_SMART_EN; + else if (strcmp(cmdname, "smartdisable") == 0) + req.features = ATAPI_SMART_DS; + else if (strcmp(cmdname, "smartstatus") == 0) + req.features = ATAPI_SMART_STATUS; + else + goto usage; + + req.timeout = 1000; + + ata_command(&req); + + if (strcmp(cmdname, "smartstatus") == 0) { + if (req.cylinder == 0xC24F) + printf("No SMART threshold exceeded\n"); + else if (req.cylinder == 0x2CF4) { + fprintf(stderr,"SMART threshold exceeded!\n"); + exit(2); + } else { + fprintf(stderr, "Unknown response %0.2x!\n", + req.cylinder); + exit(1); + } + } + + return; +usage: + fprintf(stderr, "usage: %s device %s\n", __progname, cmdname); + exit(1); +} + +/* + * Set the automatic acoustic managmement on the disk. + */ +void +device_acoustic(argc, argv) + int argc; + char *argv[]; +{ + unsigned long acoustic; + struct atareq req; + char *end; + + /* Only one argument */ + if (argc != 1) + goto usage; + + acoustic = strtoul(argv[0], &end, 0); + + if (*end != '\0') { + fprintf(stderr, "Invalid acoustic management value: \"%s\"" + "(valid values range from 0 to 126)\n", argv[0]); + exit(1); + } + + if (acoustic > 126) { + fprintf(stderr, "Automatic acoustic management has a " + "maximum value of 126\n"); + exit(1); + } + + memset(&req, 0, sizeof(req)); + + req.sec_count = acoustic + 0x80; + + req.command = SET_FEATURES ; + req.features = WDSF_AAM_EN ; + req.timeout = 1000; + + ata_command(&req); + + return; + +usage: + fprintf(stderr, "usage; %s device %s acoustic-management-value\n", + __progname, cmdname); + exit(1); +} + +/* + * Set the advanced power managmement on the disk. Power management + * levels are translated from user-range 0-253 to ATAPI levels 1-0xFD + * to keep a uniform interface to the user. + */ +void +device_apm(argc, argv) + int argc; + char *argv[]; +{ + unsigned long power; + struct atareq req; + char *end; + + /* Only one argument */ + if (argc != 1) + goto usage; + + power = strtoul(argv[0], &end, 0); + + if (*end != '\0') { + fprintf(stderr, "Invalid advanced power management value: " + "\"%s\" (valid values range from 0 to 253)\n", + argv[0]); + exit(1); + } + + if (power > 253) { + fprintf(stderr, "Advanced power management has a " + "maximum value of 253\n"); + exit(1); + } + + memset(&req, 0, sizeof(req)); + + req.sec_count = power + 0x01; + + req.command = SET_FEATURES ; + req.features = WDSF_APM_EN ; + req.timeout = 1000; + + ata_command(&req); + + return; + +usage: + fprintf(stderr, "usage; %s device %s power-management-level\n", + __progname, cmdname); + exit(1); +} + +/* + * En/disable features (the automatic acoustic managmement, Advanced Power + * Management) on the disk. + */ +void +device_feature(argc, argv) + int argc; + char *argv[]; +{ + struct atareq req; + + /* No argument */ + if (argc != 0) + goto usage; + + memset(&req, 0, sizeof(req)); + + req.command = SET_FEATURES ; + + if (strcmp(cmdname, "acousticdisable") == 0) + req.features = WDSF_AAM_DS; + else if (strcmp(cmdname, "readaheadenable") == 0) + req.features = WDSF_READAHEAD_EN; + else if (strcmp(cmdname, "readaheaddisable") == 0) + req.features = WDSF_READAHEAD_DS; + else if (strcmp(cmdname, "writecacheenable") == 0) + req.features = WDSF_EN_WR_CACHE; + else if (strcmp(cmdname, "writecachedisable") == 0) + req.features = WDSF_WRITE_CACHE_DS; + else if (strcmp(cmdname, "apmdisable") == 0) + req.features = WDSF_APM_DS; + else if (strcmp(cmdname, "puisenable") == 0) + req.features = WDSF_PUIS_EN; + else if (strcmp(cmdname, "puisdisable") == 0) + req.features = WDSF_PUIS_DS; + else if (strcmp(cmdname, "puisspinup") == 0) + req.features = WDSF_PUIS_SPINUP; + else + goto usage; + + req.timeout = 1000; + + ata_command(&req); + + return; + +usage: + fprintf(stderr, "usage; %s device %s\n", __progname, + cmdname); + exit(1); +} + +/* * Set the idle timer on the disk. Set it for either idle mode or * standby mode, depending on how we were invoked. */ @@ -470,7 +729,7 @@ device_setidle(argc, argv) if (idle > 19800) { fprintf(stderr, "Idle time has a maximum value of 5.5 " - "hours\n"); + "hours\n"); exit(1); } @@ -495,7 +754,7 @@ device_setidle(argc, argv) usage: fprintf(stderr, "usage; %s device %s idle-time\n", __progname, - cmdname); + cmdname); exit(1); } diff --git a/sys/dev/ata/atareg.h b/sys/dev/ata/atareg.h index d8d1a82c813..75977de25d6 100644 --- a/sys/dev/ata/atareg.h +++ b/sys/dev/ata/atareg.h @@ -1,4 +1,4 @@ -/* $OpenBSD: atareg.h,v 1.2 1999/09/05 21:45:22 niklas Exp $ */ +/* $OpenBSD: atareg.h,v 1.3 2001/03/23 02:16:41 deraadt Exp $ */ /* $NetBSD: atareg.h,v 1.5 1999/01/18 20:06:24 bouyer Exp $ */ /* @@ -109,6 +109,15 @@ struct ataparams { #define WDC_VER_ATA3 0x0008 #define WDC_VER_ATA4 0x0010 #define WDC_VER_ATA5 0x0020 +#define WDC_VER_ATA6 0x0040 +#define WDC_VER_ATA7 0x0080 +#define WDC_VER_ATA8 0x0100 +#define WDC_VER_ATA9 0x0200 +#define WDC_VER_ATA10 0x0400 +#define WDC_VER_ATA11 0x0800 +#define WDC_VER_ATA12 0x1000 +#define WDC_VER_ATA13 0x2000 +#define WDC_VER_ATA14 0x4000 u_int16_t atap_ata_minor; /* 81: Minor version number */ u_int16_t atap_cmd_set1; /* 82: command set suported */ #define WDC_CMD1_NOP 0x4000 @@ -126,17 +135,29 @@ struct ataparams { #define WDC_CMD1_SEC 0x0002 #define WDC_CMD1_SMART 0x0001 u_int16_t atap_cmd_set2; /* 83: command set suported */ +#define ATAPI_CMD2_FCE 0x2000 /* Flush Cache Ext supported */ +#define ATAPI_CMD2_FC 0x1000 /* Flush Cache supported */ +#define ATAPI_CMD2_DCO 0x0800 /* Device Configuration Overlay supported */ +#define ATAPI_CMD2_48AD 0x0400 /* 48bit address supported */ +#define ATAPI_CMD2_AAM 0x0200 /* Automatic Acoustic Management supported */ +#define ATAPI_CMD2_SM 0x0100 /* Set Max security extension supported */ +#define ATAPI_CMD2_SF 0x0040 /* Set Features subcommand required */ +#define ATAPI_CMD2_PUIS 0x0020 /* Power up in standby supported */ #define WDC_CMD2_RMSN 0x0010 -#define WDC_CMD2_DM 0x0001 #define ATA_CMD2_APM 0x0008 #define ATA_CMD2_CFA 0x0004 #define ATA_CMD2_RWQ 0x0002 +#define WDC_CMD2_DM 0x0001 /* Download Microcode supported */ u_int16_t atap_cmd_ext; /* 84: command/features supp. ext. */ +#define ATAPI_CMDE_MSER 0x0004 /* Media serial number supported */ +#define ATAPI_CMDE_TEST 0x0002 /* SMART self-test supported */ +#define ATAPI_CMDE_SLOG 0x0001 /* SMART error logging supported */ u_int16_t atap_cmd1_en; /* 85: cmd/features enabled */ /* bits are the same as atap_cmd_set1 */ u_int16_t atap_cmd2_en; /* 86: cmd/features enabled */ /* bits are the same as atap_cmd_set2 */ u_int16_t atap_cmd_def; /* 87: cmd/features default */ +/* bits are NOT the same as atap_cmd_ext */ #if BYTE_ORDER == LITTLE_ENDIAN u_int8_t atap_udmamode_supp; /* 88: Ultra-DMA mode supported */ u_int8_t atap_udmamode_act; /* Ultra-DMA mode active */ @@ -148,7 +169,28 @@ struct ataparams { u_int16_t atap_seu_time; /* 89: Sec. Erase Unit compl. time */ u_int16_t atap_eseu_time; /* 90: Enhanced SEU compl. time */ u_int16_t atap_apm_val; /* 91: current APM value */ - u_int16_t __reserved6[35]; /* 92-126: reserved */ + u_int16_t atap_mpasswd_rev; /* 92: Master Password revision */ + u_int16_t atap_hwreset_res; /* 93: Hardware reset value */ +#define ATA_HWRES_CBLID 0x2000 /* CBLID above Vih */ +#define ATA_HWRES_D1_PDIAG 0x0800 /* Device 1 PDIAG detect OK */ +#define ATA_HWRES_D1_CSEL 0x0400 /* Device 1 used CSEL for address */ +#define ATA_HWRES_D1_JUMP 0x0200 /* Device 1 jumpered to address */ +#define ATA_HWRES_D0_SEL 0x0040 /* Device 0 responds when Dev 1 selected */ +#define ATA_HWRES_D0_DASP 0x0020 /* Device 0 DASP detect OK */ +#define ATA_HWRES_D0_PDIAG 0x0010 /* Device 0 PDIAG detect OK */ +#define ATA_HWRES_D0_DIAG 0x0008 /* Device 0 diag OK */ +#define ATA_HWRES_D0_CSEL 0x0004 /* Device 0 used CSEL for address */ +#define ATA_HWRES_D0_JUMP 0x0002 /* Device 0 jumpered to address */ +#if BYTE_ORDER == LITTLE_ENDIAN + u_int8_t atap_acoustic_val; /* 94: Current acoustic level */ + u_int8_t atap_acoustic_def; /* recommended level */ +#else + u_int8_t atap_acoustic_def; /* recommended level */ + u_int8_t atap_acoustic_val; /* 94: Current acoustic level */ +#endif + u_int16_t __reserved6[5]; /* 95-99: reserved */ + u_int16_t atap_max_lba[4]; /* 100-103: Max. user LBA add */ + u_int16_t __reserved7[23]; /* 104-126: reserved */ u_int16_t atap_rmsn_supp; /* 127: remov. media status notif. */ #define WDC_RMSN_SUPP_MASK 0x0003 #define WDC_RMSN_SUPP 0x0001 @@ -160,4 +202,20 @@ struct ataparams { #define WDC_SEC_LOCKED 0x0004 #define WDC_SEC_EN 0x0002 #define WDC_SEC_SUPP 0x0001 + u_int16_t __reserved8[31]; /* 129-159: vendor specific */ + u_int16_t atap_cfa_power; /* 160: CFA powermode */ +#define ATAPI_CFA_MAX_MASK 0x0FFF +#define ATAPI_CFA_MODE1_DIS 0x1000 /* CFA Mode 1 Disabled */ +#define ATAPI_CFA_MODE1_REQ 0x2000 /* CFA Mode 1 Required */ +#define ATAPI_CFA_WORD160 0x8000 /* Word 160 supported */ + u_int16_t __reserved9[31]; /* 161-175: reserved for CFA */ + u_int8_t atap_media_serial[60]; /* 176-205: media serial number */ + u_int16_t __reserved10[49]; /* 206-254: reserved */ +#if BYTE_ORDER == LITTLE_ENDIAN + u_int8_t atap_signature; /* 255: Signature */ + u_int8_t atap_checksum; /* Checksum */ +#else + u_int8_t atap_checksum; /* Checksum */ + u_int8_t atap_signature; /* 255: Signature */ +#endif }; diff --git a/sys/dev/ic/wdcreg.h b/sys/dev/ic/wdcreg.h index 207528c45de..1b215582f57 100644 --- a/sys/dev/ic/wdcreg.h +++ b/sys/dev/ic/wdcreg.h @@ -1,4 +1,4 @@ -/* $OpenBSD: wdcreg.h,v 1.2 1999/11/17 01:22:56 csapuntz Exp $ */ +/* $OpenBSD: wdcreg.h,v 1.3 2001/03/23 02:16:41 deraadt Exp $ */ /* $NetBSD: wdcreg.h,v 1.22 1999/03/07 14:02:54 bouyer Exp $ */ /*- @@ -113,22 +113,39 @@ #define WDCC_CHECK_PWR 0xe5 /* check power mode */ /* Subcommands for SET_FEATURES (features register ) */ +#define WDSF_8BIT_PIO_EN 0x01 /* Enable 8bit PIO (CFA featureset) */ #define WDSF_EN_WR_CACHE 0x02 #define WDSF_SET_MODE 0x03 -#define WDSF_REASSIGN_EN 0x04 -#define WDSF_RETRY_DS 0x33 -#define WDSF_SET_CACHE_SGMT 0x54 -#define WDSF_READAHEAD_DS 0x55 +#define WDSF_REASSIGN_EN 0x04 /* Obsolete in ATA-6 */ +#define WDSF_APM_EN 0x05 /* Enable Adv. Power Management */ +#define WDSF_PUIS_EN 0x06 /* Enable Power-Up In Standby */ +#define WDSF_PUIS_SPINUP 0x07 /* Power-Up In Standby spin-up */ +#define WDSF_CFA_MODE1_EN 0x0A /* Enable CFA power mode 1 */ +#define WDSF_RMSN_DS 0x31 /* Disable Removable Media Status */ +#define WDSF_RETRY_DS 0x33 /* Obsolete in ATA-6 */ +#define WDSF_AAM_EN 0x42 /* Enable Autom. Acoustic Management */ +#define WDSF_SET_CACHE_SGMT 0x54 /* Obsolete in ATA-6 */ +#define WDSF_READAHEAD_DS 0x55 /* Disable read look-ahead */ +#define WDSF_RLSE_EN 0x5D /* Enable release interrupt */ +#define WDSF_SRV_EN 0x5E /* Enable SERVICE interrupt */ #define WDSF_POD_DS 0x66 #define WDSF_ECC_DS 0x77 +#define WDSF_8BIT_PIO_DS 0x81 /* Disable 8bit PIO (CFA featureset) */ #define WDSF_WRITE_CACHE_DS 0x82 #define WDSF_REASSIGN_DS 0x84 +#define WDSF_APM_DS 0x85 /* Disable Adv. Power Management */ +#define WDSF_PUIS_DS 0x86 /* Disable Power-Up In Standby */ #define WDSF_ECC_EN 0x88 -#define WDSF_RETRY_EN 0x99 -#define WDSF_SET_CURRENT 0x9A +#define WDSF_CFA_MODE1_DS 0x8A /* Disable CFA power mode 1 */ +#define WDSF_RMSN_EN 0x95 /* Enable Removable Media Status */ +#define WDSF_RETRY_EN 0x99 /* Obsolete in ATA-6 */ +#define WDSF_SET_CURRENT 0x9A /* Obsolete in ATA-6 */ #define WDSF_READAHEAD_EN 0xAA -#define WDSF_PREFETCH_SET 0xAB +#define WDSF_PREFETCH_SET 0xAB /* Obsolete in ATA-6 */ +#define WDSF_AAM_DS 0xC2 /* Disable Autom. Acoustic Management */ #define WDSF_POD_EN 0xCC +#define WDSF_RLSE_DS 0xDD /* Disable release interrupt */ +#define WDSF_SRV_DS 0xDE /* Disable SERVICE interrupt */ /* parameters uploaded to device/heads register */ #define WDSD_IBM 0xa0 /* forced to 512 byte sector, ecc */ @@ -145,6 +162,22 @@ #define ATAPI_SOFT_RESET 0x08 #define ATAPI_SLEEP 0xe6 #define ATAPI_STANDBY_IMMEDIATE 0xe0 +#define ATAPI_SMART 0xB0 /* SMART operations */ +#define ATAPI_SETMAX 0xF9 /* Set Max Address */ +#define ATAPI_WRITEEXT 0x34 /* Write sectors Ext */ +#define ATAPI_SETMAXEXT 0x37 /* Set Max Address Ext */ +#define ATAPI_WRITEMULTIEXT 0x39 /* Write Multi Ext */ + +/* SubCommands for SMART operations */ +#define ATAPI_SMART_READ 0xD0 /* SMART read data */ +#define ATAPI_SMART_AUTOSAVE 0xD2 /* SMART en-/disable attr. autosave */ +#define ATAPI_SMART_SAVE 0xD3 /* SMART save attributes */ +#define ATAPI_SMART_OFFLINE 0xD4 /* SMART execute offline immediately */ +#define ATAPI_SMART_READLOG 0xD5 /* SMART read log */ +#define ATAPI_SMART_WRITELOG 0xD6 /* SMART write log */ +#define ATAPI_SMART_DS 0xD9 /* SMART disable operations */ +#define ATAPI_SMART_EN 0xD8 /* SMART disable operations */ +#define ATAPI_SMART_STATUS 0xDA /* SMART return status */ /* Bytes used by ATAPI_PACKET_COMMAND ( feature register) */ #define ATAPI_PKT_CMD_FTRE_DMA 0x01 |