1 /* 2 * Copyright (c) 1997-2007 Kenneth D. Merry 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions 7 * are met: 8 * 1. Redistributions of source code must retain the above copyright 9 * notice, this list of conditions and the following disclaimer. 10 * 2. Redistributions in binary form must reproduce the above copyright 11 * notice, this list of conditions and the following disclaimer in the 12 * documentation and/or other materials provided with the distribution. 13 * 3. The name of the author may not be used to endorse or promote products 14 * derived from this software without specific prior written permission. 15 * 16 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 17 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 18 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 19 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 20 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 21 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 22 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 23 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 24 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 25 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 26 * SUCH DAMAGE. 27 */ 28 29 #include <sys/cdefs.h> 30 __FBSDID("$FreeBSD$"); 31 32 #include <sys/ioctl.h> 33 #include <sys/stdint.h> 34 #include <sys/types.h> 35 #include <sys/stat.h> 36 #include <sys/endian.h> 37 #include <sys/sbuf.h> 38 39 #include <stdio.h> 40 #include <stdlib.h> 41 #include <string.h> 42 #include <unistd.h> 43 #include <inttypes.h> 44 #include <limits.h> 45 #include <fcntl.h> 46 #include <ctype.h> 47 #include <err.h> 48 #include <libutil.h> 49 #ifndef MINIMALISTIC 50 #include <limits.h> 51 #include <inttypes.h> 52 #endif 53 54 #include <cam/cam.h> 55 #include <cam/cam_debug.h> 56 #include <cam/cam_ccb.h> 57 #include <cam/scsi/scsi_all.h> 58 #include <cam/scsi/scsi_da.h> 59 #include <cam/scsi/scsi_pass.h> 60 #include <cam/scsi/scsi_message.h> 61 #include <cam/scsi/smp_all.h> 62 #include <cam/ata/ata_all.h> 63 #include <camlib.h> 64 #include "camcontrol.h" 65 66 typedef enum { 67 CAM_CMD_NONE = 0x00000000, 68 CAM_CMD_DEVLIST = 0x00000001, 69 CAM_CMD_TUR = 0x00000002, 70 CAM_CMD_INQUIRY = 0x00000003, 71 CAM_CMD_STARTSTOP = 0x00000004, 72 CAM_CMD_RESCAN = 0x00000005, 73 CAM_CMD_READ_DEFECTS = 0x00000006, 74 CAM_CMD_MODE_PAGE = 0x00000007, 75 CAM_CMD_SCSI_CMD = 0x00000008, 76 CAM_CMD_DEVTREE = 0x00000009, 77 CAM_CMD_USAGE = 0x0000000a, 78 CAM_CMD_DEBUG = 0x0000000b, 79 CAM_CMD_RESET = 0x0000000c, 80 CAM_CMD_FORMAT = 0x0000000d, 81 CAM_CMD_TAG = 0x0000000e, 82 CAM_CMD_RATE = 0x0000000f, 83 CAM_CMD_DETACH = 0x00000010, 84 CAM_CMD_REPORTLUNS = 0x00000011, 85 CAM_CMD_READCAP = 0x00000012, 86 CAM_CMD_IDENTIFY = 0x00000013, 87 CAM_CMD_IDLE = 0x00000014, 88 CAM_CMD_STANDBY = 0x00000015, 89 CAM_CMD_SLEEP = 0x00000016, 90 CAM_CMD_SMP_CMD = 0x00000017, 91 CAM_CMD_SMP_RG = 0x00000018, 92 CAM_CMD_SMP_PC = 0x00000019, 93 CAM_CMD_SMP_PHYLIST = 0x0000001a, 94 CAM_CMD_SMP_MANINFO = 0x0000001b, 95 CAM_CMD_DOWNLOAD_FW = 0x0000001c, 96 CAM_CMD_SECURITY = 0x0000001d, 97 CAM_CMD_HPA = 0x0000001e, 98 CAM_CMD_SANITIZE = 0x0000001f, 99 CAM_CMD_PERSIST = 0x00000020, 100 CAM_CMD_APM = 0x00000021, 101 CAM_CMD_AAM = 0x00000022, 102 CAM_CMD_ATTRIB = 0x00000023, 103 CAM_CMD_OPCODES = 0x00000024, 104 CAM_CMD_REPROBE = 0x00000025, 105 CAM_CMD_ZONE = 0x00000026, 106 CAM_CMD_EPC = 0x00000027 107 } cam_cmdmask; 108 109 typedef enum { 110 CAM_ARG_NONE = 0x00000000, 111 CAM_ARG_VERBOSE = 0x00000001, 112 CAM_ARG_DEVICE = 0x00000002, 113 CAM_ARG_BUS = 0x00000004, 114 CAM_ARG_TARGET = 0x00000008, 115 CAM_ARG_LUN = 0x00000010, 116 CAM_ARG_EJECT = 0x00000020, 117 CAM_ARG_UNIT = 0x00000040, 118 CAM_ARG_FORMAT_BLOCK = 0x00000080, 119 CAM_ARG_FORMAT_BFI = 0x00000100, 120 CAM_ARG_FORMAT_PHYS = 0x00000200, 121 CAM_ARG_PLIST = 0x00000400, 122 CAM_ARG_GLIST = 0x00000800, 123 CAM_ARG_GET_SERIAL = 0x00001000, 124 CAM_ARG_GET_STDINQ = 0x00002000, 125 CAM_ARG_GET_XFERRATE = 0x00004000, 126 CAM_ARG_INQ_MASK = 0x00007000, 127 CAM_ARG_MODE_EDIT = 0x00008000, 128 CAM_ARG_PAGE_CNTL = 0x00010000, 129 CAM_ARG_TIMEOUT = 0x00020000, 130 CAM_ARG_CMD_IN = 0x00040000, 131 CAM_ARG_CMD_OUT = 0x00080000, 132 CAM_ARG_DBD = 0x00100000, 133 CAM_ARG_ERR_RECOVER = 0x00200000, 134 CAM_ARG_RETRIES = 0x00400000, 135 CAM_ARG_START_UNIT = 0x00800000, 136 CAM_ARG_DEBUG_INFO = 0x01000000, 137 CAM_ARG_DEBUG_TRACE = 0x02000000, 138 CAM_ARG_DEBUG_SUBTRACE = 0x04000000, 139 CAM_ARG_DEBUG_CDB = 0x08000000, 140 CAM_ARG_DEBUG_XPT = 0x10000000, 141 CAM_ARG_DEBUG_PERIPH = 0x20000000, 142 CAM_ARG_DEBUG_PROBE = 0x40000000, 143 } cam_argmask; 144 145 struct camcontrol_opts { 146 const char *optname; 147 uint32_t cmdnum; 148 cam_argmask argnum; 149 const char *subopt; 150 }; 151 152 #ifndef MINIMALISTIC 153 struct ata_res_pass16 { 154 u_int16_t reserved[5]; 155 u_int8_t flags; 156 u_int8_t error; 157 u_int8_t sector_count_exp; 158 u_int8_t sector_count; 159 u_int8_t lba_low_exp; 160 u_int8_t lba_low; 161 u_int8_t lba_mid_exp; 162 u_int8_t lba_mid; 163 u_int8_t lba_high_exp; 164 u_int8_t lba_high; 165 u_int8_t device; 166 u_int8_t status; 167 }; 168 169 struct ata_set_max_pwd 170 { 171 u_int16_t reserved1; 172 u_int8_t password[32]; 173 u_int16_t reserved2[239]; 174 }; 175 176 static const char scsicmd_opts[] = "a:c:dfi:o:r"; 177 static const char readdefect_opts[] = "f:GPqsS:X"; 178 static const char negotiate_opts[] = "acD:M:O:qR:T:UW:"; 179 static const char smprg_opts[] = "l"; 180 static const char smppc_opts[] = "a:A:d:lm:M:o:p:s:S:T:"; 181 static const char smpphylist_opts[] = "lq"; 182 static char pwd_opt; 183 #endif 184 185 static struct camcontrol_opts option_table[] = { 186 #ifndef MINIMALISTIC 187 {"tur", CAM_CMD_TUR, CAM_ARG_NONE, NULL}, 188 {"inquiry", CAM_CMD_INQUIRY, CAM_ARG_NONE, "DSR"}, 189 {"identify", CAM_CMD_IDENTIFY, CAM_ARG_NONE, NULL}, 190 {"start", CAM_CMD_STARTSTOP, CAM_ARG_START_UNIT, NULL}, 191 {"stop", CAM_CMD_STARTSTOP, CAM_ARG_NONE, NULL}, 192 {"load", CAM_CMD_STARTSTOP, CAM_ARG_START_UNIT | CAM_ARG_EJECT, NULL}, 193 {"eject", CAM_CMD_STARTSTOP, CAM_ARG_EJECT, NULL}, 194 {"reportluns", CAM_CMD_REPORTLUNS, CAM_ARG_NONE, "clr:"}, 195 {"readcapacity", CAM_CMD_READCAP, CAM_ARG_NONE, "bhHNqs"}, 196 {"reprobe", CAM_CMD_REPROBE, CAM_ARG_NONE, NULL}, 197 #endif /* MINIMALISTIC */ 198 {"rescan", CAM_CMD_RESCAN, CAM_ARG_NONE, NULL}, 199 {"reset", CAM_CMD_RESET, CAM_ARG_NONE, NULL}, 200 #ifndef MINIMALISTIC 201 {"cmd", CAM_CMD_SCSI_CMD, CAM_ARG_NONE, scsicmd_opts}, 202 {"command", CAM_CMD_SCSI_CMD, CAM_ARG_NONE, scsicmd_opts}, 203 {"smpcmd", CAM_CMD_SMP_CMD, CAM_ARG_NONE, "r:R:"}, 204 {"smprg", CAM_CMD_SMP_RG, CAM_ARG_NONE, smprg_opts}, 205 {"smpreportgeneral", CAM_CMD_SMP_RG, CAM_ARG_NONE, smprg_opts}, 206 {"smppc", CAM_CMD_SMP_PC, CAM_ARG_NONE, smppc_opts}, 207 {"smpphycontrol", CAM_CMD_SMP_PC, CAM_ARG_NONE, smppc_opts}, 208 {"smpplist", CAM_CMD_SMP_PHYLIST, CAM_ARG_NONE, smpphylist_opts}, 209 {"smpphylist", CAM_CMD_SMP_PHYLIST, CAM_ARG_NONE, smpphylist_opts}, 210 {"smpmaninfo", CAM_CMD_SMP_MANINFO, CAM_ARG_NONE, "l"}, 211 {"defects", CAM_CMD_READ_DEFECTS, CAM_ARG_NONE, readdefect_opts}, 212 {"defectlist", CAM_CMD_READ_DEFECTS, CAM_ARG_NONE, readdefect_opts}, 213 #endif /* MINIMALISTIC */ 214 {"devlist", CAM_CMD_DEVTREE, CAM_ARG_NONE, "-b"}, 215 #ifndef MINIMALISTIC 216 {"periphlist", CAM_CMD_DEVLIST, CAM_ARG_NONE, NULL}, 217 {"modepage", CAM_CMD_MODE_PAGE, CAM_ARG_NONE, "bdelm:P:"}, 218 {"tags", CAM_CMD_TAG, CAM_ARG_NONE, "N:q"}, 219 {"negotiate", CAM_CMD_RATE, CAM_ARG_NONE, negotiate_opts}, 220 {"rate", CAM_CMD_RATE, CAM_ARG_NONE, negotiate_opts}, 221 {"debug", CAM_CMD_DEBUG, CAM_ARG_NONE, "IPTSXcp"}, 222 {"format", CAM_CMD_FORMAT, CAM_ARG_NONE, "qrwy"}, 223 {"sanitize", CAM_CMD_SANITIZE, CAM_ARG_NONE, "a:c:IP:qrUwy"}, 224 {"idle", CAM_CMD_IDLE, CAM_ARG_NONE, "t:"}, 225 {"standby", CAM_CMD_STANDBY, CAM_ARG_NONE, "t:"}, 226 {"sleep", CAM_CMD_SLEEP, CAM_ARG_NONE, ""}, 227 {"apm", CAM_CMD_APM, CAM_ARG_NONE, "l:"}, 228 {"aam", CAM_CMD_AAM, CAM_ARG_NONE, "l:"}, 229 {"fwdownload", CAM_CMD_DOWNLOAD_FW, CAM_ARG_NONE, "f:qsy"}, 230 {"security", CAM_CMD_SECURITY, CAM_ARG_NONE, "d:e:fh:k:l:qs:T:U:y"}, 231 {"hpa", CAM_CMD_HPA, CAM_ARG_NONE, "Pflp:qs:U:y"}, 232 {"persist", CAM_CMD_PERSIST, CAM_ARG_NONE, "ai:I:k:K:o:ps:ST:U"}, 233 {"attrib", CAM_CMD_ATTRIB, CAM_ARG_NONE, "a:ce:F:p:r:s:T:w:V:"}, 234 {"opcodes", CAM_CMD_OPCODES, CAM_ARG_NONE, "No:s:T"}, 235 {"zone", CAM_CMD_ZONE, CAM_ARG_NONE, "ac:l:No:P:"}, 236 {"epc", CAM_CMD_EPC, CAM_ARG_NONE, "c:dDeHp:Pr:sS:T:"}, 237 #endif /* MINIMALISTIC */ 238 {"help", CAM_CMD_USAGE, CAM_ARG_NONE, NULL}, 239 {"-?", CAM_CMD_USAGE, CAM_ARG_NONE, NULL}, 240 {"-h", CAM_CMD_USAGE, CAM_ARG_NONE, NULL}, 241 {NULL, 0, 0, NULL} 242 }; 243 244 struct cam_devitem { 245 struct device_match_result dev_match; 246 int num_periphs; 247 struct periph_match_result *periph_matches; 248 struct scsi_vpd_device_id *device_id; 249 int device_id_len; 250 STAILQ_ENTRY(cam_devitem) links; 251 }; 252 253 struct cam_devlist { 254 STAILQ_HEAD(, cam_devitem) dev_queue; 255 path_id_t path_id; 256 }; 257 258 static cam_cmdmask cmdlist; 259 static cam_argmask arglist; 260 261 camcontrol_optret getoption(struct camcontrol_opts *table, char *arg, 262 uint32_t *cmdnum, cam_argmask *argnum, 263 const char **subopt); 264 #ifndef MINIMALISTIC 265 static int getdevlist(struct cam_device *device); 266 #endif /* MINIMALISTIC */ 267 static int getdevtree(int argc, char **argv, char *combinedopt); 268 #ifndef MINIMALISTIC 269 static int testunitready(struct cam_device *device, int retry_count, 270 int timeout, int quiet); 271 static int scsistart(struct cam_device *device, int startstop, int loadeject, 272 int retry_count, int timeout); 273 static int scsiinquiry(struct cam_device *device, int retry_count, int timeout); 274 static int scsiserial(struct cam_device *device, int retry_count, int timeout); 275 #endif /* MINIMALISTIC */ 276 static int parse_btl(char *tstr, path_id_t *bus, target_id_t *target, 277 lun_id_t *lun, cam_argmask *arglst); 278 static int dorescan_or_reset(int argc, char **argv, int rescan); 279 static int rescan_or_reset_bus(path_id_t bus, int rescan); 280 static int scanlun_or_reset_dev(path_id_t bus, target_id_t target, 281 lun_id_t lun, int scan); 282 #ifndef MINIMALISTIC 283 static int readdefects(struct cam_device *device, int argc, char **argv, 284 char *combinedopt, int retry_count, int timeout); 285 static void modepage(struct cam_device *device, int argc, char **argv, 286 char *combinedopt, int retry_count, int timeout); 287 static int scsicmd(struct cam_device *device, int argc, char **argv, 288 char *combinedopt, int retry_count, int timeout); 289 static int smpcmd(struct cam_device *device, int argc, char **argv, 290 char *combinedopt, int retry_count, int timeout); 291 static int smpreportgeneral(struct cam_device *device, int argc, char **argv, 292 char *combinedopt, int retry_count, int timeout); 293 static int smpphycontrol(struct cam_device *device, int argc, char **argv, 294 char *combinedopt, int retry_count, int timeout); 295 static int smpmaninfo(struct cam_device *device, int argc, char **argv, 296 char *combinedopt, int retry_count, int timeout); 297 static int getdevid(struct cam_devitem *item); 298 static int buildbusdevlist(struct cam_devlist *devlist); 299 static void freebusdevlist(struct cam_devlist *devlist); 300 static struct cam_devitem *findsasdevice(struct cam_devlist *devlist, 301 uint64_t sasaddr); 302 static int smpphylist(struct cam_device *device, int argc, char **argv, 303 char *combinedopt, int retry_count, int timeout); 304 static int tagcontrol(struct cam_device *device, int argc, char **argv, 305 char *combinedopt); 306 static void cts_print(struct cam_device *device, 307 struct ccb_trans_settings *cts); 308 static void cpi_print(struct ccb_pathinq *cpi); 309 static int get_cpi(struct cam_device *device, struct ccb_pathinq *cpi); 310 static int get_cgd(struct cam_device *device, struct ccb_getdev *cgd); 311 static int get_print_cts(struct cam_device *device, int user_settings, 312 int quiet, struct ccb_trans_settings *cts); 313 static int ratecontrol(struct cam_device *device, int retry_count, 314 int timeout, int argc, char **argv, char *combinedopt); 315 static int scsiformat(struct cam_device *device, int argc, char **argv, 316 char *combinedopt, int retry_count, int timeout); 317 static int scsisanitize(struct cam_device *device, int argc, char **argv, 318 char *combinedopt, int retry_count, int timeout); 319 static int scsireportluns(struct cam_device *device, int argc, char **argv, 320 char *combinedopt, int retry_count, int timeout); 321 static int scsireadcapacity(struct cam_device *device, int argc, char **argv, 322 char *combinedopt, int retry_count, int timeout); 323 static int atapm(struct cam_device *device, int argc, char **argv, 324 char *combinedopt, int retry_count, int timeout); 325 static int atasecurity(struct cam_device *device, int retry_count, int timeout, 326 int argc, char **argv, char *combinedopt); 327 static int atahpa(struct cam_device *device, int retry_count, int timeout, 328 int argc, char **argv, char *combinedopt); 329 static int scsiprintoneopcode(struct cam_device *device, int req_opcode, 330 int sa_set, int req_sa, uint8_t *buf, 331 uint32_t valid_len); 332 static int scsiprintopcodes(struct cam_device *device, int td_req, uint8_t *buf, 333 uint32_t valid_len); 334 static int scsiopcodes(struct cam_device *device, int argc, char **argv, 335 char *combinedopt, int retry_count, int timeout, 336 int verbose); 337 static int scsireprobe(struct cam_device *device); 338 339 #endif /* MINIMALISTIC */ 340 #ifndef min 341 #define min(a,b) (((a)<(b))?(a):(b)) 342 #endif 343 #ifndef max 344 #define max(a,b) (((a)>(b))?(a):(b)) 345 #endif 346 347 camcontrol_optret 348 getoption(struct camcontrol_opts *table, char *arg, uint32_t *cmdnum, 349 cam_argmask *argnum, const char **subopt) 350 { 351 struct camcontrol_opts *opts; 352 int num_matches = 0; 353 354 for (opts = table; (opts != NULL) && (opts->optname != NULL); 355 opts++) { 356 if (strncmp(opts->optname, arg, strlen(arg)) == 0) { 357 *cmdnum = opts->cmdnum; 358 *argnum = opts->argnum; 359 *subopt = opts->subopt; 360 if (++num_matches > 1) 361 return(CC_OR_AMBIGUOUS); 362 } 363 } 364 365 if (num_matches > 0) 366 return(CC_OR_FOUND); 367 else 368 return(CC_OR_NOT_FOUND); 369 } 370 371 #ifndef MINIMALISTIC 372 static int 373 getdevlist(struct cam_device *device) 374 { 375 union ccb *ccb; 376 char status[32]; 377 int error = 0; 378 379 ccb = cam_getccb(device); 380 381 ccb->ccb_h.func_code = XPT_GDEVLIST; 382 ccb->ccb_h.flags = CAM_DIR_NONE; 383 ccb->ccb_h.retry_count = 1; 384 ccb->cgdl.index = 0; 385 ccb->cgdl.status = CAM_GDEVLIST_MORE_DEVS; 386 while (ccb->cgdl.status == CAM_GDEVLIST_MORE_DEVS) { 387 if (cam_send_ccb(device, ccb) < 0) { 388 perror("error getting device list"); 389 cam_freeccb(ccb); 390 return(1); 391 } 392 393 status[0] = '\0'; 394 395 switch (ccb->cgdl.status) { 396 case CAM_GDEVLIST_MORE_DEVS: 397 strcpy(status, "MORE"); 398 break; 399 case CAM_GDEVLIST_LAST_DEVICE: 400 strcpy(status, "LAST"); 401 break; 402 case CAM_GDEVLIST_LIST_CHANGED: 403 strcpy(status, "CHANGED"); 404 break; 405 case CAM_GDEVLIST_ERROR: 406 strcpy(status, "ERROR"); 407 error = 1; 408 break; 409 } 410 411 fprintf(stdout, "%s%d: generation: %d index: %d status: %s\n", 412 ccb->cgdl.periph_name, 413 ccb->cgdl.unit_number, 414 ccb->cgdl.generation, 415 ccb->cgdl.index, 416 status); 417 418 /* 419 * If the list has changed, we need to start over from the 420 * beginning. 421 */ 422 if (ccb->cgdl.status == CAM_GDEVLIST_LIST_CHANGED) 423 ccb->cgdl.index = 0; 424 } 425 426 cam_freeccb(ccb); 427 428 return(error); 429 } 430 #endif /* MINIMALISTIC */ 431 432 static int 433 getdevtree(int argc, char **argv, char *combinedopt) 434 { 435 union ccb ccb; 436 int bufsize, fd; 437 unsigned int i; 438 int need_close = 0; 439 int error = 0; 440 int skip_device = 0; 441 int busonly = 0; 442 int c; 443 444 while ((c = getopt(argc, argv, combinedopt)) != -1) { 445 switch(c) { 446 case 'b': 447 if ((arglist & CAM_ARG_VERBOSE) == 0) 448 busonly = 1; 449 break; 450 default: 451 break; 452 } 453 } 454 455 if ((fd = open(XPT_DEVICE, O_RDWR)) == -1) { 456 warn("couldn't open %s", XPT_DEVICE); 457 return(1); 458 } 459 460 bzero(&ccb, sizeof(union ccb)); 461 462 ccb.ccb_h.path_id = CAM_XPT_PATH_ID; 463 ccb.ccb_h.target_id = CAM_TARGET_WILDCARD; 464 ccb.ccb_h.target_lun = CAM_LUN_WILDCARD; 465 466 ccb.ccb_h.func_code = XPT_DEV_MATCH; 467 bufsize = sizeof(struct dev_match_result) * 100; 468 ccb.cdm.match_buf_len = bufsize; 469 ccb.cdm.matches = (struct dev_match_result *)malloc(bufsize); 470 if (ccb.cdm.matches == NULL) { 471 warnx("can't malloc memory for matches"); 472 close(fd); 473 return(1); 474 } 475 ccb.cdm.num_matches = 0; 476 477 /* 478 * We fetch all nodes, since we display most of them in the default 479 * case, and all in the verbose case. 480 */ 481 ccb.cdm.num_patterns = 0; 482 ccb.cdm.pattern_buf_len = 0; 483 484 /* 485 * We do the ioctl multiple times if necessary, in case there are 486 * more than 100 nodes in the EDT. 487 */ 488 do { 489 if (ioctl(fd, CAMIOCOMMAND, &ccb) == -1) { 490 warn("error sending CAMIOCOMMAND ioctl"); 491 error = 1; 492 break; 493 } 494 495 if ((ccb.ccb_h.status != CAM_REQ_CMP) 496 || ((ccb.cdm.status != CAM_DEV_MATCH_LAST) 497 && (ccb.cdm.status != CAM_DEV_MATCH_MORE))) { 498 warnx("got CAM error %#x, CDM error %d\n", 499 ccb.ccb_h.status, ccb.cdm.status); 500 error = 1; 501 break; 502 } 503 504 for (i = 0; i < ccb.cdm.num_matches; i++) { 505 switch (ccb.cdm.matches[i].type) { 506 case DEV_MATCH_BUS: { 507 struct bus_match_result *bus_result; 508 509 /* 510 * Only print the bus information if the 511 * user turns on the verbose flag. 512 */ 513 if ((busonly == 0) && 514 (arglist & CAM_ARG_VERBOSE) == 0) 515 break; 516 517 bus_result = 518 &ccb.cdm.matches[i].result.bus_result; 519 520 if (need_close) { 521 fprintf(stdout, ")\n"); 522 need_close = 0; 523 } 524 525 fprintf(stdout, "scbus%d on %s%d bus %d%s\n", 526 bus_result->path_id, 527 bus_result->dev_name, 528 bus_result->unit_number, 529 bus_result->bus_id, 530 (busonly ? "" : ":")); 531 break; 532 } 533 case DEV_MATCH_DEVICE: { 534 struct device_match_result *dev_result; 535 char vendor[16], product[48], revision[16]; 536 char fw[5], tmpstr[256]; 537 538 if (busonly == 1) 539 break; 540 541 dev_result = 542 &ccb.cdm.matches[i].result.device_result; 543 544 if ((dev_result->flags 545 & DEV_RESULT_UNCONFIGURED) 546 && ((arglist & CAM_ARG_VERBOSE) == 0)) { 547 skip_device = 1; 548 break; 549 } else 550 skip_device = 0; 551 552 if (dev_result->protocol == PROTO_SCSI) { 553 cam_strvis(vendor, dev_result->inq_data.vendor, 554 sizeof(dev_result->inq_data.vendor), 555 sizeof(vendor)); 556 cam_strvis(product, 557 dev_result->inq_data.product, 558 sizeof(dev_result->inq_data.product), 559 sizeof(product)); 560 cam_strvis(revision, 561 dev_result->inq_data.revision, 562 sizeof(dev_result->inq_data.revision), 563 sizeof(revision)); 564 sprintf(tmpstr, "<%s %s %s>", vendor, product, 565 revision); 566 } else if (dev_result->protocol == PROTO_ATA || 567 dev_result->protocol == PROTO_SATAPM) { 568 cam_strvis(product, 569 dev_result->ident_data.model, 570 sizeof(dev_result->ident_data.model), 571 sizeof(product)); 572 cam_strvis(revision, 573 dev_result->ident_data.revision, 574 sizeof(dev_result->ident_data.revision), 575 sizeof(revision)); 576 sprintf(tmpstr, "<%s %s>", product, 577 revision); 578 } else if (dev_result->protocol == PROTO_SEMB) { 579 struct sep_identify_data *sid; 580 581 sid = (struct sep_identify_data *) 582 &dev_result->ident_data; 583 cam_strvis(vendor, sid->vendor_id, 584 sizeof(sid->vendor_id), 585 sizeof(vendor)); 586 cam_strvis(product, sid->product_id, 587 sizeof(sid->product_id), 588 sizeof(product)); 589 cam_strvis(revision, sid->product_rev, 590 sizeof(sid->product_rev), 591 sizeof(revision)); 592 cam_strvis(fw, sid->firmware_rev, 593 sizeof(sid->firmware_rev), 594 sizeof(fw)); 595 sprintf(tmpstr, "<%s %s %s %s>", 596 vendor, product, revision, fw); 597 } else { 598 sprintf(tmpstr, "<>"); 599 } 600 if (need_close) { 601 fprintf(stdout, ")\n"); 602 need_close = 0; 603 } 604 605 fprintf(stdout, "%-33s at scbus%d " 606 "target %d lun %jx (", 607 tmpstr, 608 dev_result->path_id, 609 dev_result->target_id, 610 (uintmax_t)dev_result->target_lun); 611 612 need_close = 1; 613 614 break; 615 } 616 case DEV_MATCH_PERIPH: { 617 struct periph_match_result *periph_result; 618 619 periph_result = 620 &ccb.cdm.matches[i].result.periph_result; 621 622 if (busonly || skip_device != 0) 623 break; 624 625 if (need_close > 1) 626 fprintf(stdout, ","); 627 628 fprintf(stdout, "%s%d", 629 periph_result->periph_name, 630 periph_result->unit_number); 631 632 need_close++; 633 break; 634 } 635 default: 636 fprintf(stdout, "unknown match type\n"); 637 break; 638 } 639 } 640 641 } while ((ccb.ccb_h.status == CAM_REQ_CMP) 642 && (ccb.cdm.status == CAM_DEV_MATCH_MORE)); 643 644 if (need_close) 645 fprintf(stdout, ")\n"); 646 647 close(fd); 648 649 return(error); 650 } 651 652 #ifndef MINIMALISTIC 653 static int 654 testunitready(struct cam_device *device, int retry_count, int timeout, 655 int quiet) 656 { 657 int error = 0; 658 union ccb *ccb; 659 660 ccb = cam_getccb(device); 661 662 scsi_test_unit_ready(&ccb->csio, 663 /* retries */ retry_count, 664 /* cbfcnp */ NULL, 665 /* tag_action */ MSG_SIMPLE_Q_TAG, 666 /* sense_len */ SSD_FULL_SIZE, 667 /* timeout */ timeout ? timeout : 5000); 668 669 /* Disable freezing the device queue */ 670 ccb->ccb_h.flags |= CAM_DEV_QFRZDIS; 671 672 if (arglist & CAM_ARG_ERR_RECOVER) 673 ccb->ccb_h.flags |= CAM_PASS_ERR_RECOVER; 674 675 if (cam_send_ccb(device, ccb) < 0) { 676 if (quiet == 0) 677 perror("error sending test unit ready"); 678 679 if (arglist & CAM_ARG_VERBOSE) { 680 cam_error_print(device, ccb, CAM_ESF_ALL, 681 CAM_EPF_ALL, stderr); 682 } 683 684 cam_freeccb(ccb); 685 return(1); 686 } 687 688 if ((ccb->ccb_h.status & CAM_STATUS_MASK) == CAM_REQ_CMP) { 689 if (quiet == 0) 690 fprintf(stdout, "Unit is ready\n"); 691 } else { 692 if (quiet == 0) 693 fprintf(stdout, "Unit is not ready\n"); 694 error = 1; 695 696 if (arglist & CAM_ARG_VERBOSE) { 697 cam_error_print(device, ccb, CAM_ESF_ALL, 698 CAM_EPF_ALL, stderr); 699 } 700 } 701 702 cam_freeccb(ccb); 703 704 return(error); 705 } 706 707 static int 708 scsistart(struct cam_device *device, int startstop, int loadeject, 709 int retry_count, int timeout) 710 { 711 union ccb *ccb; 712 int error = 0; 713 714 ccb = cam_getccb(device); 715 716 /* 717 * If we're stopping, send an ordered tag so the drive in question 718 * will finish any previously queued writes before stopping. If 719 * the device isn't capable of tagged queueing, or if tagged 720 * queueing is turned off, the tag action is a no-op. 721 */ 722 scsi_start_stop(&ccb->csio, 723 /* retries */ retry_count, 724 /* cbfcnp */ NULL, 725 /* tag_action */ startstop ? MSG_SIMPLE_Q_TAG : 726 MSG_ORDERED_Q_TAG, 727 /* start/stop */ startstop, 728 /* load_eject */ loadeject, 729 /* immediate */ 0, 730 /* sense_len */ SSD_FULL_SIZE, 731 /* timeout */ timeout ? timeout : 120000); 732 733 /* Disable freezing the device queue */ 734 ccb->ccb_h.flags |= CAM_DEV_QFRZDIS; 735 736 if (arglist & CAM_ARG_ERR_RECOVER) 737 ccb->ccb_h.flags |= CAM_PASS_ERR_RECOVER; 738 739 if (cam_send_ccb(device, ccb) < 0) { 740 perror("error sending start unit"); 741 742 if (arglist & CAM_ARG_VERBOSE) { 743 cam_error_print(device, ccb, CAM_ESF_ALL, 744 CAM_EPF_ALL, stderr); 745 } 746 747 cam_freeccb(ccb); 748 return(1); 749 } 750 751 if ((ccb->ccb_h.status & CAM_STATUS_MASK) == CAM_REQ_CMP) 752 if (startstop) { 753 fprintf(stdout, "Unit started successfully"); 754 if (loadeject) 755 fprintf(stdout,", Media loaded\n"); 756 else 757 fprintf(stdout,"\n"); 758 } else { 759 fprintf(stdout, "Unit stopped successfully"); 760 if (loadeject) 761 fprintf(stdout, ", Media ejected\n"); 762 else 763 fprintf(stdout, "\n"); 764 } 765 else { 766 error = 1; 767 if (startstop) 768 fprintf(stdout, 769 "Error received from start unit command\n"); 770 else 771 fprintf(stdout, 772 "Error received from stop unit command\n"); 773 774 if (arglist & CAM_ARG_VERBOSE) { 775 cam_error_print(device, ccb, CAM_ESF_ALL, 776 CAM_EPF_ALL, stderr); 777 } 778 } 779 780 cam_freeccb(ccb); 781 782 return(error); 783 } 784 785 int 786 scsidoinquiry(struct cam_device *device, int argc, char **argv, 787 char *combinedopt, int retry_count, int timeout) 788 { 789 int c; 790 int error = 0; 791 792 while ((c = getopt(argc, argv, combinedopt)) != -1) { 793 switch(c) { 794 case 'D': 795 arglist |= CAM_ARG_GET_STDINQ; 796 break; 797 case 'R': 798 arglist |= CAM_ARG_GET_XFERRATE; 799 break; 800 case 'S': 801 arglist |= CAM_ARG_GET_SERIAL; 802 break; 803 default: 804 break; 805 } 806 } 807 808 /* 809 * If the user didn't specify any inquiry options, he wants all of 810 * them. 811 */ 812 if ((arglist & CAM_ARG_INQ_MASK) == 0) 813 arglist |= CAM_ARG_INQ_MASK; 814 815 if (arglist & CAM_ARG_GET_STDINQ) 816 error = scsiinquiry(device, retry_count, timeout); 817 818 if (error != 0) 819 return(error); 820 821 if (arglist & CAM_ARG_GET_SERIAL) 822 scsiserial(device, retry_count, timeout); 823 824 if (arglist & CAM_ARG_GET_XFERRATE) 825 error = camxferrate(device); 826 827 return(error); 828 } 829 830 static int 831 scsiinquiry(struct cam_device *device, int retry_count, int timeout) 832 { 833 union ccb *ccb; 834 struct scsi_inquiry_data *inq_buf; 835 int error = 0; 836 837 ccb = cam_getccb(device); 838 839 if (ccb == NULL) { 840 warnx("couldn't allocate CCB"); 841 return(1); 842 } 843 844 /* cam_getccb cleans up the header, caller has to zero the payload */ 845 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->csio); 846 847 inq_buf = (struct scsi_inquiry_data *)malloc( 848 sizeof(struct scsi_inquiry_data)); 849 850 if (inq_buf == NULL) { 851 cam_freeccb(ccb); 852 warnx("can't malloc memory for inquiry\n"); 853 return(1); 854 } 855 bzero(inq_buf, sizeof(*inq_buf)); 856 857 /* 858 * Note that although the size of the inquiry buffer is the full 859 * 256 bytes specified in the SCSI spec, we only tell the device 860 * that we have allocated SHORT_INQUIRY_LENGTH bytes. There are 861 * two reasons for this: 862 * 863 * - The SCSI spec says that when a length field is only 1 byte, 864 * a value of 0 will be interpreted as 256. Therefore 865 * scsi_inquiry() will convert an inq_len (which is passed in as 866 * a u_int32_t, but the field in the CDB is only 1 byte) of 256 867 * to 0. Evidently, very few devices meet the spec in that 868 * regard. Some devices, like many Seagate disks, take the 0 as 869 * 0, and don't return any data. One Pioneer DVD-R drive 870 * returns more data than the command asked for. 871 * 872 * So, since there are numerous devices that just don't work 873 * right with the full inquiry size, we don't send the full size. 874 * 875 * - The second reason not to use the full inquiry data length is 876 * that we don't need it here. The only reason we issue a 877 * standard inquiry is to get the vendor name, device name, 878 * and revision so scsi_print_inquiry() can print them. 879 * 880 * If, at some point in the future, more inquiry data is needed for 881 * some reason, this code should use a procedure similar to the 882 * probe code. i.e., issue a short inquiry, and determine from 883 * the additional length passed back from the device how much 884 * inquiry data the device supports. Once the amount the device 885 * supports is determined, issue an inquiry for that amount and no 886 * more. 887 * 888 * KDM, 2/18/2000 889 */ 890 scsi_inquiry(&ccb->csio, 891 /* retries */ retry_count, 892 /* cbfcnp */ NULL, 893 /* tag_action */ MSG_SIMPLE_Q_TAG, 894 /* inq_buf */ (u_int8_t *)inq_buf, 895 /* inq_len */ SHORT_INQUIRY_LENGTH, 896 /* evpd */ 0, 897 /* page_code */ 0, 898 /* sense_len */ SSD_FULL_SIZE, 899 /* timeout */ timeout ? timeout : 5000); 900 901 /* Disable freezing the device queue */ 902 ccb->ccb_h.flags |= CAM_DEV_QFRZDIS; 903 904 if (arglist & CAM_ARG_ERR_RECOVER) 905 ccb->ccb_h.flags |= CAM_PASS_ERR_RECOVER; 906 907 if (cam_send_ccb(device, ccb) < 0) { 908 perror("error sending SCSI inquiry"); 909 910 if (arglist & CAM_ARG_VERBOSE) { 911 cam_error_print(device, ccb, CAM_ESF_ALL, 912 CAM_EPF_ALL, stderr); 913 } 914 915 cam_freeccb(ccb); 916 return(1); 917 } 918 919 if ((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP) { 920 error = 1; 921 922 if (arglist & CAM_ARG_VERBOSE) { 923 cam_error_print(device, ccb, CAM_ESF_ALL, 924 CAM_EPF_ALL, stderr); 925 } 926 } 927 928 cam_freeccb(ccb); 929 930 if (error != 0) { 931 free(inq_buf); 932 return(error); 933 } 934 935 fprintf(stdout, "%s%d: ", device->device_name, 936 device->dev_unit_num); 937 scsi_print_inquiry(inq_buf); 938 939 free(inq_buf); 940 941 return(0); 942 } 943 944 static int 945 scsiserial(struct cam_device *device, int retry_count, int timeout) 946 { 947 union ccb *ccb; 948 struct scsi_vpd_unit_serial_number *serial_buf; 949 char serial_num[SVPD_SERIAL_NUM_SIZE + 1]; 950 int error = 0; 951 952 ccb = cam_getccb(device); 953 954 if (ccb == NULL) { 955 warnx("couldn't allocate CCB"); 956 return(1); 957 } 958 959 /* cam_getccb cleans up the header, caller has to zero the payload */ 960 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->csio); 961 962 serial_buf = (struct scsi_vpd_unit_serial_number *) 963 malloc(sizeof(*serial_buf)); 964 965 if (serial_buf == NULL) { 966 cam_freeccb(ccb); 967 warnx("can't malloc memory for serial number"); 968 return(1); 969 } 970 971 scsi_inquiry(&ccb->csio, 972 /*retries*/ retry_count, 973 /*cbfcnp*/ NULL, 974 /* tag_action */ MSG_SIMPLE_Q_TAG, 975 /* inq_buf */ (u_int8_t *)serial_buf, 976 /* inq_len */ sizeof(*serial_buf), 977 /* evpd */ 1, 978 /* page_code */ SVPD_UNIT_SERIAL_NUMBER, 979 /* sense_len */ SSD_FULL_SIZE, 980 /* timeout */ timeout ? timeout : 5000); 981 982 /* Disable freezing the device queue */ 983 ccb->ccb_h.flags |= CAM_DEV_QFRZDIS; 984 985 if (arglist & CAM_ARG_ERR_RECOVER) 986 ccb->ccb_h.flags |= CAM_PASS_ERR_RECOVER; 987 988 if (cam_send_ccb(device, ccb) < 0) { 989 warn("error getting serial number"); 990 991 if (arglist & CAM_ARG_VERBOSE) { 992 cam_error_print(device, ccb, CAM_ESF_ALL, 993 CAM_EPF_ALL, stderr); 994 } 995 996 cam_freeccb(ccb); 997 free(serial_buf); 998 return(1); 999 } 1000 1001 if ((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP) { 1002 error = 1; 1003 1004 if (arglist & CAM_ARG_VERBOSE) { 1005 cam_error_print(device, ccb, CAM_ESF_ALL, 1006 CAM_EPF_ALL, stderr); 1007 } 1008 } 1009 1010 cam_freeccb(ccb); 1011 1012 if (error != 0) { 1013 free(serial_buf); 1014 return(error); 1015 } 1016 1017 bcopy(serial_buf->serial_num, serial_num, serial_buf->length); 1018 serial_num[serial_buf->length] = '\0'; 1019 1020 if ((arglist & CAM_ARG_GET_STDINQ) 1021 || (arglist & CAM_ARG_GET_XFERRATE)) 1022 fprintf(stdout, "%s%d: Serial Number ", 1023 device->device_name, device->dev_unit_num); 1024 1025 fprintf(stdout, "%.60s\n", serial_num); 1026 1027 free(serial_buf); 1028 1029 return(0); 1030 } 1031 1032 int 1033 camxferrate(struct cam_device *device) 1034 { 1035 struct ccb_pathinq cpi; 1036 u_int32_t freq = 0; 1037 u_int32_t speed = 0; 1038 union ccb *ccb; 1039 u_int mb; 1040 int retval = 0; 1041 1042 if ((retval = get_cpi(device, &cpi)) != 0) 1043 return (1); 1044 1045 ccb = cam_getccb(device); 1046 1047 if (ccb == NULL) { 1048 warnx("couldn't allocate CCB"); 1049 return(1); 1050 } 1051 1052 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->cts); 1053 1054 ccb->ccb_h.func_code = XPT_GET_TRAN_SETTINGS; 1055 ccb->cts.type = CTS_TYPE_CURRENT_SETTINGS; 1056 1057 if (((retval = cam_send_ccb(device, ccb)) < 0) 1058 || ((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP)) { 1059 const char error_string[] = "error getting transfer settings"; 1060 1061 if (retval < 0) 1062 warn(error_string); 1063 else 1064 warnx(error_string); 1065 1066 if (arglist & CAM_ARG_VERBOSE) 1067 cam_error_print(device, ccb, CAM_ESF_ALL, 1068 CAM_EPF_ALL, stderr); 1069 1070 retval = 1; 1071 1072 goto xferrate_bailout; 1073 1074 } 1075 1076 speed = cpi.base_transfer_speed; 1077 freq = 0; 1078 if (ccb->cts.transport == XPORT_SPI) { 1079 struct ccb_trans_settings_spi *spi = 1080 &ccb->cts.xport_specific.spi; 1081 1082 if ((spi->valid & CTS_SPI_VALID_SYNC_RATE) != 0) { 1083 freq = scsi_calc_syncsrate(spi->sync_period); 1084 speed = freq; 1085 } 1086 if ((spi->valid & CTS_SPI_VALID_BUS_WIDTH) != 0) { 1087 speed *= (0x01 << spi->bus_width); 1088 } 1089 } else if (ccb->cts.transport == XPORT_FC) { 1090 struct ccb_trans_settings_fc *fc = 1091 &ccb->cts.xport_specific.fc; 1092 1093 if (fc->valid & CTS_FC_VALID_SPEED) 1094 speed = fc->bitrate; 1095 } else if (ccb->cts.transport == XPORT_SAS) { 1096 struct ccb_trans_settings_sas *sas = 1097 &ccb->cts.xport_specific.sas; 1098 1099 if (sas->valid & CTS_SAS_VALID_SPEED) 1100 speed = sas->bitrate; 1101 } else if (ccb->cts.transport == XPORT_ATA) { 1102 struct ccb_trans_settings_pata *pata = 1103 &ccb->cts.xport_specific.ata; 1104 1105 if (pata->valid & CTS_ATA_VALID_MODE) 1106 speed = ata_mode2speed(pata->mode); 1107 } else if (ccb->cts.transport == XPORT_SATA) { 1108 struct ccb_trans_settings_sata *sata = 1109 &ccb->cts.xport_specific.sata; 1110 1111 if (sata->valid & CTS_SATA_VALID_REVISION) 1112 speed = ata_revision2speed(sata->revision); 1113 } 1114 1115 mb = speed / 1000; 1116 if (mb > 0) { 1117 fprintf(stdout, "%s%d: %d.%03dMB/s transfers", 1118 device->device_name, device->dev_unit_num, 1119 mb, speed % 1000); 1120 } else { 1121 fprintf(stdout, "%s%d: %dKB/s transfers", 1122 device->device_name, device->dev_unit_num, 1123 speed); 1124 } 1125 1126 if (ccb->cts.transport == XPORT_SPI) { 1127 struct ccb_trans_settings_spi *spi = 1128 &ccb->cts.xport_specific.spi; 1129 1130 if (((spi->valid & CTS_SPI_VALID_SYNC_OFFSET) != 0) 1131 && (spi->sync_offset != 0)) 1132 fprintf(stdout, " (%d.%03dMHz, offset %d", freq / 1000, 1133 freq % 1000, spi->sync_offset); 1134 1135 if (((spi->valid & CTS_SPI_VALID_BUS_WIDTH) != 0) 1136 && (spi->bus_width > 0)) { 1137 if (((spi->valid & CTS_SPI_VALID_SYNC_OFFSET) != 0) 1138 && (spi->sync_offset != 0)) { 1139 fprintf(stdout, ", "); 1140 } else { 1141 fprintf(stdout, " ("); 1142 } 1143 fprintf(stdout, "%dbit)", 8 * (0x01 << spi->bus_width)); 1144 } else if (((spi->valid & CTS_SPI_VALID_SYNC_OFFSET) != 0) 1145 && (spi->sync_offset != 0)) { 1146 fprintf(stdout, ")"); 1147 } 1148 } else if (ccb->cts.transport == XPORT_ATA) { 1149 struct ccb_trans_settings_pata *pata = 1150 &ccb->cts.xport_specific.ata; 1151 1152 printf(" ("); 1153 if (pata->valid & CTS_ATA_VALID_MODE) 1154 printf("%s, ", ata_mode2string(pata->mode)); 1155 if ((pata->valid & CTS_ATA_VALID_ATAPI) && pata->atapi != 0) 1156 printf("ATAPI %dbytes, ", pata->atapi); 1157 if (pata->valid & CTS_ATA_VALID_BYTECOUNT) 1158 printf("PIO %dbytes", pata->bytecount); 1159 printf(")"); 1160 } else if (ccb->cts.transport == XPORT_SATA) { 1161 struct ccb_trans_settings_sata *sata = 1162 &ccb->cts.xport_specific.sata; 1163 1164 printf(" ("); 1165 if (sata->valid & CTS_SATA_VALID_REVISION) 1166 printf("SATA %d.x, ", sata->revision); 1167 else 1168 printf("SATA, "); 1169 if (sata->valid & CTS_SATA_VALID_MODE) 1170 printf("%s, ", ata_mode2string(sata->mode)); 1171 if ((sata->valid & CTS_SATA_VALID_ATAPI) && sata->atapi != 0) 1172 printf("ATAPI %dbytes, ", sata->atapi); 1173 if (sata->valid & CTS_SATA_VALID_BYTECOUNT) 1174 printf("PIO %dbytes", sata->bytecount); 1175 printf(")"); 1176 } 1177 1178 if (ccb->cts.protocol == PROTO_SCSI) { 1179 struct ccb_trans_settings_scsi *scsi = 1180 &ccb->cts.proto_specific.scsi; 1181 if (scsi->valid & CTS_SCSI_VALID_TQ) { 1182 if (scsi->flags & CTS_SCSI_FLAGS_TAG_ENB) { 1183 fprintf(stdout, ", Command Queueing Enabled"); 1184 } 1185 } 1186 } 1187 1188 fprintf(stdout, "\n"); 1189 1190 xferrate_bailout: 1191 1192 cam_freeccb(ccb); 1193 1194 return(retval); 1195 } 1196 1197 static void 1198 atahpa_print(struct ata_params *parm, u_int64_t hpasize, int header) 1199 { 1200 u_int32_t lbasize = (u_int32_t)parm->lba_size_1 | 1201 ((u_int32_t)parm->lba_size_2 << 16); 1202 1203 u_int64_t lbasize48 = ((u_int64_t)parm->lba_size48_1) | 1204 ((u_int64_t)parm->lba_size48_2 << 16) | 1205 ((u_int64_t)parm->lba_size48_3 << 32) | 1206 ((u_int64_t)parm->lba_size48_4 << 48); 1207 1208 if (header) { 1209 printf("\nFeature " 1210 "Support Enabled Value\n"); 1211 } 1212 1213 printf("Host Protected Area (HPA) "); 1214 if (parm->support.command1 & ATA_SUPPORT_PROTECTED) { 1215 u_int64_t lba = lbasize48 ? lbasize48 : lbasize; 1216 printf("yes %s %ju/%ju\n", (hpasize > lba) ? "yes" : "no ", 1217 lba, hpasize); 1218 1219 printf("HPA - Security "); 1220 if (parm->support.command1 & ATA_SUPPORT_MAXSECURITY) 1221 printf("yes\n"); 1222 else 1223 printf("no\n"); 1224 } else { 1225 printf("no\n"); 1226 } 1227 } 1228 1229 static int 1230 atasata(struct ata_params *parm) 1231 { 1232 1233 1234 if (parm->satacapabilities != 0xffff && 1235 parm->satacapabilities != 0x0000) 1236 return 1; 1237 1238 return 0; 1239 } 1240 1241 static void 1242 atacapprint(struct ata_params *parm) 1243 { 1244 u_int32_t lbasize = (u_int32_t)parm->lba_size_1 | 1245 ((u_int32_t)parm->lba_size_2 << 16); 1246 1247 u_int64_t lbasize48 = ((u_int64_t)parm->lba_size48_1) | 1248 ((u_int64_t)parm->lba_size48_2 << 16) | 1249 ((u_int64_t)parm->lba_size48_3 << 32) | 1250 ((u_int64_t)parm->lba_size48_4 << 48); 1251 1252 printf("\n"); 1253 printf("protocol "); 1254 printf("ATA/ATAPI-%d", ata_version(parm->version_major)); 1255 if (parm->satacapabilities && parm->satacapabilities != 0xffff) { 1256 if (parm->satacapabilities & ATA_SATA_GEN3) 1257 printf(" SATA 3.x\n"); 1258 else if (parm->satacapabilities & ATA_SATA_GEN2) 1259 printf(" SATA 2.x\n"); 1260 else if (parm->satacapabilities & ATA_SATA_GEN1) 1261 printf(" SATA 1.x\n"); 1262 else 1263 printf(" SATA\n"); 1264 } 1265 else 1266 printf("\n"); 1267 printf("device model %.40s\n", parm->model); 1268 printf("firmware revision %.8s\n", parm->revision); 1269 printf("serial number %.20s\n", parm->serial); 1270 if (parm->enabled.extension & ATA_SUPPORT_64BITWWN) { 1271 printf("WWN %04x%04x%04x%04x\n", 1272 parm->wwn[0], parm->wwn[1], parm->wwn[2], parm->wwn[3]); 1273 } 1274 if (parm->enabled.extension & ATA_SUPPORT_MEDIASN) { 1275 printf("media serial number %.30s\n", 1276 parm->media_serial); 1277 } 1278 1279 printf("cylinders %d\n", parm->cylinders); 1280 printf("heads %d\n", parm->heads); 1281 printf("sectors/track %d\n", parm->sectors); 1282 printf("sector size logical %u, physical %lu, offset %lu\n", 1283 ata_logical_sector_size(parm), 1284 (unsigned long)ata_physical_sector_size(parm), 1285 (unsigned long)ata_logical_sector_offset(parm)); 1286 1287 if (parm->config == ATA_PROTO_CFA || 1288 (parm->support.command2 & ATA_SUPPORT_CFA)) 1289 printf("CFA supported\n"); 1290 1291 printf("LBA%ssupported ", 1292 parm->capabilities1 & ATA_SUPPORT_LBA ? " " : " not "); 1293 if (lbasize) 1294 printf("%d sectors\n", lbasize); 1295 else 1296 printf("\n"); 1297 1298 printf("LBA48%ssupported ", 1299 parm->support.command2 & ATA_SUPPORT_ADDRESS48 ? " " : " not "); 1300 if (lbasize48) 1301 printf("%ju sectors\n", (uintmax_t)lbasize48); 1302 else 1303 printf("\n"); 1304 1305 printf("PIO supported PIO"); 1306 switch (ata_max_pmode(parm)) { 1307 case ATA_PIO4: 1308 printf("4"); 1309 break; 1310 case ATA_PIO3: 1311 printf("3"); 1312 break; 1313 case ATA_PIO2: 1314 printf("2"); 1315 break; 1316 case ATA_PIO1: 1317 printf("1"); 1318 break; 1319 default: 1320 printf("0"); 1321 } 1322 if ((parm->capabilities1 & ATA_SUPPORT_IORDY) == 0) 1323 printf(" w/o IORDY"); 1324 printf("\n"); 1325 1326 printf("DMA%ssupported ", 1327 parm->capabilities1 & ATA_SUPPORT_DMA ? " " : " not "); 1328 if (parm->capabilities1 & ATA_SUPPORT_DMA) { 1329 if (parm->mwdmamodes & 0xff) { 1330 printf("WDMA"); 1331 if (parm->mwdmamodes & 0x04) 1332 printf("2"); 1333 else if (parm->mwdmamodes & 0x02) 1334 printf("1"); 1335 else if (parm->mwdmamodes & 0x01) 1336 printf("0"); 1337 printf(" "); 1338 } 1339 if ((parm->atavalid & ATA_FLAG_88) && 1340 (parm->udmamodes & 0xff)) { 1341 printf("UDMA"); 1342 if (parm->udmamodes & 0x40) 1343 printf("6"); 1344 else if (parm->udmamodes & 0x20) 1345 printf("5"); 1346 else if (parm->udmamodes & 0x10) 1347 printf("4"); 1348 else if (parm->udmamodes & 0x08) 1349 printf("3"); 1350 else if (parm->udmamodes & 0x04) 1351 printf("2"); 1352 else if (parm->udmamodes & 0x02) 1353 printf("1"); 1354 else if (parm->udmamodes & 0x01) 1355 printf("0"); 1356 printf(" "); 1357 } 1358 } 1359 printf("\n"); 1360 1361 if (parm->media_rotation_rate == 1) { 1362 printf("media RPM non-rotating\n"); 1363 } else if (parm->media_rotation_rate >= 0x0401 && 1364 parm->media_rotation_rate <= 0xFFFE) { 1365 printf("media RPM %d\n", 1366 parm->media_rotation_rate); 1367 } 1368 1369 printf("\nFeature " 1370 "Support Enabled Value Vendor\n"); 1371 printf("read ahead %s %s\n", 1372 parm->support.command1 & ATA_SUPPORT_LOOKAHEAD ? "yes" : "no", 1373 parm->enabled.command1 & ATA_SUPPORT_LOOKAHEAD ? "yes" : "no"); 1374 printf("write cache %s %s\n", 1375 parm->support.command1 & ATA_SUPPORT_WRITECACHE ? "yes" : "no", 1376 parm->enabled.command1 & ATA_SUPPORT_WRITECACHE ? "yes" : "no"); 1377 printf("flush cache %s %s\n", 1378 parm->support.command2 & ATA_SUPPORT_FLUSHCACHE ? "yes" : "no", 1379 parm->enabled.command2 & ATA_SUPPORT_FLUSHCACHE ? "yes" : "no"); 1380 printf("overlap %s\n", 1381 parm->capabilities1 & ATA_SUPPORT_OVERLAP ? "yes" : "no"); 1382 printf("Tagged Command Queuing (TCQ) %s %s", 1383 parm->support.command2 & ATA_SUPPORT_QUEUED ? "yes" : "no", 1384 parm->enabled.command2 & ATA_SUPPORT_QUEUED ? "yes" : "no"); 1385 if (parm->support.command2 & ATA_SUPPORT_QUEUED) { 1386 printf(" %d tags\n", 1387 ATA_QUEUE_LEN(parm->queue) + 1); 1388 } else 1389 printf("\n"); 1390 printf("Native Command Queuing (NCQ) "); 1391 if (parm->satacapabilities != 0xffff && 1392 (parm->satacapabilities & ATA_SUPPORT_NCQ)) { 1393 printf("yes %d tags\n", 1394 ATA_QUEUE_LEN(parm->queue) + 1); 1395 } else 1396 printf("no\n"); 1397 1398 printf("NCQ Queue Management %s\n", atasata(parm) && 1399 parm->satacapabilities2 & ATA_SUPPORT_NCQ_QMANAGEMENT ? 1400 "yes" : "no"); 1401 printf("NCQ Streaming %s\n", atasata(parm) && 1402 parm->satacapabilities2 & ATA_SUPPORT_NCQ_STREAM ? 1403 "yes" : "no"); 1404 printf("Receive & Send FPDMA Queued %s\n", atasata(parm) && 1405 parm->satacapabilities2 & ATA_SUPPORT_RCVSND_FPDMA_QUEUED ? 1406 "yes" : "no"); 1407 1408 printf("SMART %s %s\n", 1409 parm->support.command1 & ATA_SUPPORT_SMART ? "yes" : "no", 1410 parm->enabled.command1 & ATA_SUPPORT_SMART ? "yes" : "no"); 1411 printf("microcode download %s %s\n", 1412 parm->support.command2 & ATA_SUPPORT_MICROCODE ? "yes" : "no", 1413 parm->enabled.command2 & ATA_SUPPORT_MICROCODE ? "yes" : "no"); 1414 printf("security %s %s\n", 1415 parm->support.command1 & ATA_SUPPORT_SECURITY ? "yes" : "no", 1416 parm->enabled.command1 & ATA_SUPPORT_SECURITY ? "yes" : "no"); 1417 printf("power management %s %s\n", 1418 parm->support.command1 & ATA_SUPPORT_POWERMGT ? "yes" : "no", 1419 parm->enabled.command1 & ATA_SUPPORT_POWERMGT ? "yes" : "no"); 1420 printf("advanced power management %s %s", 1421 parm->support.command2 & ATA_SUPPORT_APM ? "yes" : "no", 1422 parm->enabled.command2 & ATA_SUPPORT_APM ? "yes" : "no"); 1423 if (parm->support.command2 & ATA_SUPPORT_APM) { 1424 printf(" %d/0x%02X\n", 1425 parm->apm_value & 0xff, parm->apm_value & 0xff); 1426 } else 1427 printf("\n"); 1428 printf("automatic acoustic management %s %s", 1429 parm->support.command2 & ATA_SUPPORT_AUTOACOUSTIC ? "yes" :"no", 1430 parm->enabled.command2 & ATA_SUPPORT_AUTOACOUSTIC ? "yes" :"no"); 1431 if (parm->support.command2 & ATA_SUPPORT_AUTOACOUSTIC) { 1432 printf(" %d/0x%02X %d/0x%02X\n", 1433 ATA_ACOUSTIC_CURRENT(parm->acoustic), 1434 ATA_ACOUSTIC_CURRENT(parm->acoustic), 1435 ATA_ACOUSTIC_VENDOR(parm->acoustic), 1436 ATA_ACOUSTIC_VENDOR(parm->acoustic)); 1437 } else 1438 printf("\n"); 1439 printf("media status notification %s %s\n", 1440 parm->support.command2 & ATA_SUPPORT_NOTIFY ? "yes" : "no", 1441 parm->enabled.command2 & ATA_SUPPORT_NOTIFY ? "yes" : "no"); 1442 printf("power-up in Standby %s %s\n", 1443 parm->support.command2 & ATA_SUPPORT_STANDBY ? "yes" : "no", 1444 parm->enabled.command2 & ATA_SUPPORT_STANDBY ? "yes" : "no"); 1445 printf("write-read-verify %s %s", 1446 parm->support2 & ATA_SUPPORT_WRITEREADVERIFY ? "yes" : "no", 1447 parm->enabled2 & ATA_SUPPORT_WRITEREADVERIFY ? "yes" : "no"); 1448 if (parm->support2 & ATA_SUPPORT_WRITEREADVERIFY) { 1449 printf(" %d/0x%x\n", 1450 parm->wrv_mode, parm->wrv_mode); 1451 } else 1452 printf("\n"); 1453 printf("unload %s %s\n", 1454 parm->support.extension & ATA_SUPPORT_UNLOAD ? "yes" : "no", 1455 parm->enabled.extension & ATA_SUPPORT_UNLOAD ? "yes" : "no"); 1456 printf("general purpose logging %s %s\n", 1457 parm->support.extension & ATA_SUPPORT_GENLOG ? "yes" : "no", 1458 parm->enabled.extension & ATA_SUPPORT_GENLOG ? "yes" : "no"); 1459 printf("free-fall %s %s\n", 1460 parm->support2 & ATA_SUPPORT_FREEFALL ? "yes" : "no", 1461 parm->enabled2 & ATA_SUPPORT_FREEFALL ? "yes" : "no"); 1462 printf("Data Set Management (DSM/TRIM) "); 1463 if (parm->support_dsm & ATA_SUPPORT_DSM_TRIM) { 1464 printf("yes\n"); 1465 printf("DSM - max 512byte blocks "); 1466 if (parm->max_dsm_blocks == 0x00) 1467 printf("yes not specified\n"); 1468 else 1469 printf("yes %d\n", 1470 parm->max_dsm_blocks); 1471 1472 printf("DSM - deterministic read "); 1473 if (parm->support3 & ATA_SUPPORT_DRAT) { 1474 if (parm->support3 & ATA_SUPPORT_RZAT) 1475 printf("yes zeroed\n"); 1476 else 1477 printf("yes any value\n"); 1478 } else { 1479 printf("no\n"); 1480 } 1481 } else { 1482 printf("no\n"); 1483 } 1484 } 1485 1486 static int 1487 scsi_cam_pass_16_send(struct cam_device *device, union ccb *ccb, int quiet) 1488 { 1489 struct ata_pass_16 *ata_pass_16; 1490 struct ata_cmd ata_cmd; 1491 1492 ata_pass_16 = (struct ata_pass_16 *)ccb->csio.cdb_io.cdb_bytes; 1493 ata_cmd.command = ata_pass_16->command; 1494 ata_cmd.control = ata_pass_16->control; 1495 ata_cmd.features = ata_pass_16->features; 1496 1497 if (arglist & CAM_ARG_VERBOSE) { 1498 warnx("sending ATA %s via pass_16 with timeout of %u msecs", 1499 ata_op_string(&ata_cmd), 1500 ccb->csio.ccb_h.timeout); 1501 } 1502 1503 /* Disable freezing the device queue */ 1504 ccb->ccb_h.flags |= CAM_DEV_QFRZDIS; 1505 1506 if (arglist & CAM_ARG_ERR_RECOVER) 1507 ccb->ccb_h.flags |= CAM_PASS_ERR_RECOVER; 1508 1509 if (cam_send_ccb(device, ccb) < 0) { 1510 if (quiet != 1 || arglist & CAM_ARG_VERBOSE) { 1511 warn("error sending ATA %s via pass_16", 1512 ata_op_string(&ata_cmd)); 1513 } 1514 1515 if (arglist & CAM_ARG_VERBOSE) { 1516 cam_error_print(device, ccb, CAM_ESF_ALL, 1517 CAM_EPF_ALL, stderr); 1518 } 1519 1520 return (1); 1521 } 1522 1523 if (!(ata_pass_16->flags & AP_FLAG_CHK_COND) && 1524 (ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP) { 1525 if (quiet != 1 || arglist & CAM_ARG_VERBOSE) { 1526 warnx("ATA %s via pass_16 failed", 1527 ata_op_string(&ata_cmd)); 1528 } 1529 if (arglist & CAM_ARG_VERBOSE) { 1530 cam_error_print(device, ccb, CAM_ESF_ALL, 1531 CAM_EPF_ALL, stderr); 1532 } 1533 1534 return (1); 1535 } 1536 1537 return (0); 1538 } 1539 1540 1541 static int 1542 ata_cam_send(struct cam_device *device, union ccb *ccb, int quiet) 1543 { 1544 if (arglist & CAM_ARG_VERBOSE) { 1545 warnx("sending ATA %s with timeout of %u msecs", 1546 ata_op_string(&(ccb->ataio.cmd)), 1547 ccb->ataio.ccb_h.timeout); 1548 } 1549 1550 /* Disable freezing the device queue */ 1551 ccb->ccb_h.flags |= CAM_DEV_QFRZDIS; 1552 1553 if (arglist & CAM_ARG_ERR_RECOVER) 1554 ccb->ccb_h.flags |= CAM_PASS_ERR_RECOVER; 1555 1556 if (cam_send_ccb(device, ccb) < 0) { 1557 if (quiet != 1 || arglist & CAM_ARG_VERBOSE) { 1558 warn("error sending ATA %s", 1559 ata_op_string(&(ccb->ataio.cmd))); 1560 } 1561 1562 if (arglist & CAM_ARG_VERBOSE) { 1563 cam_error_print(device, ccb, CAM_ESF_ALL, 1564 CAM_EPF_ALL, stderr); 1565 } 1566 1567 return (1); 1568 } 1569 1570 if ((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP) { 1571 if (quiet != 1 || arglist & CAM_ARG_VERBOSE) { 1572 warnx("ATA %s failed: %d", 1573 ata_op_string(&(ccb->ataio.cmd)), quiet); 1574 } 1575 1576 if (arglist & CAM_ARG_VERBOSE) { 1577 cam_error_print(device, ccb, CAM_ESF_ALL, 1578 CAM_EPF_ALL, stderr); 1579 } 1580 1581 return (1); 1582 } 1583 1584 return (0); 1585 } 1586 1587 static int 1588 ata_do_pass_16(struct cam_device *device, union ccb *ccb, int retries, 1589 u_int32_t flags, u_int8_t protocol, u_int8_t ata_flags, 1590 u_int8_t tag_action, u_int8_t command, u_int8_t features, 1591 u_int64_t lba, u_int8_t sector_count, u_int8_t *data_ptr, 1592 u_int16_t dxfer_len, int timeout, int quiet) 1593 { 1594 if (data_ptr != NULL) { 1595 ata_flags |= AP_FLAG_BYT_BLOK_BYTES | 1596 AP_FLAG_TLEN_SECT_CNT; 1597 if (flags & CAM_DIR_OUT) 1598 ata_flags |= AP_FLAG_TDIR_TO_DEV; 1599 else 1600 ata_flags |= AP_FLAG_TDIR_FROM_DEV; 1601 } else { 1602 ata_flags |= AP_FLAG_TLEN_NO_DATA; 1603 } 1604 1605 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->csio); 1606 1607 scsi_ata_pass_16(&ccb->csio, 1608 retries, 1609 NULL, 1610 flags, 1611 tag_action, 1612 protocol, 1613 ata_flags, 1614 features, 1615 sector_count, 1616 lba, 1617 command, 1618 /*control*/0, 1619 data_ptr, 1620 dxfer_len, 1621 /*sense_len*/SSD_FULL_SIZE, 1622 timeout); 1623 1624 return scsi_cam_pass_16_send(device, ccb, quiet); 1625 } 1626 1627 static int 1628 ata_try_pass_16(struct cam_device *device) 1629 { 1630 struct ccb_pathinq cpi; 1631 1632 if (get_cpi(device, &cpi) != 0) { 1633 warnx("couldn't get CPI"); 1634 return (-1); 1635 } 1636 1637 if (cpi.protocol == PROTO_SCSI) { 1638 /* possibly compatible with pass_16 */ 1639 return (1); 1640 } 1641 1642 /* likely not compatible with pass_16 */ 1643 return (0); 1644 } 1645 1646 static int 1647 ata_do_28bit_cmd(struct cam_device *device, union ccb *ccb, int retries, 1648 u_int32_t flags, u_int8_t protocol, u_int8_t tag_action, 1649 u_int8_t command, u_int8_t features, u_int32_t lba, 1650 u_int8_t sector_count, u_int8_t *data_ptr, u_int16_t dxfer_len, 1651 int timeout, int quiet) 1652 { 1653 1654 1655 switch (ata_try_pass_16(device)) { 1656 case -1: 1657 return (1); 1658 case 1: 1659 /* Try using SCSI Passthrough */ 1660 return ata_do_pass_16(device, ccb, retries, flags, protocol, 1661 0, tag_action, command, features, lba, 1662 sector_count, data_ptr, dxfer_len, 1663 timeout, quiet); 1664 } 1665 1666 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->ataio); 1667 cam_fill_ataio(&ccb->ataio, 1668 retries, 1669 NULL, 1670 flags, 1671 tag_action, 1672 data_ptr, 1673 dxfer_len, 1674 timeout); 1675 1676 ata_28bit_cmd(&ccb->ataio, command, features, lba, sector_count); 1677 return ata_cam_send(device, ccb, quiet); 1678 } 1679 1680 static int 1681 ata_do_cmd(struct cam_device *device, union ccb *ccb, int retries, 1682 u_int32_t flags, u_int8_t protocol, u_int8_t ata_flags, 1683 u_int8_t tag_action, u_int8_t command, u_int8_t features, 1684 u_int64_t lba, u_int8_t sector_count, u_int8_t *data_ptr, 1685 u_int16_t dxfer_len, int timeout, int force48bit) 1686 { 1687 int retval; 1688 1689 retval = ata_try_pass_16(device); 1690 if (retval == -1) 1691 return (1); 1692 1693 if (retval == 1) { 1694 int error; 1695 1696 /* Try using SCSI Passthrough */ 1697 error = ata_do_pass_16(device, ccb, retries, flags, protocol, 1698 ata_flags, tag_action, command, features, 1699 lba, sector_count, data_ptr, dxfer_len, 1700 timeout, 0); 1701 1702 if (ata_flags & AP_FLAG_CHK_COND) { 1703 /* Decode ata_res from sense data */ 1704 struct ata_res_pass16 *res_pass16; 1705 struct ata_res *res; 1706 u_int i; 1707 u_int16_t *ptr; 1708 1709 /* sense_data is 4 byte aligned */ 1710 ptr = (uint16_t*)(uintptr_t)&ccb->csio.sense_data; 1711 for (i = 0; i < sizeof(*res_pass16) / 2; i++) 1712 ptr[i] = le16toh(ptr[i]); 1713 1714 /* sense_data is 4 byte aligned */ 1715 res_pass16 = (struct ata_res_pass16 *)(uintptr_t) 1716 &ccb->csio.sense_data; 1717 res = &ccb->ataio.res; 1718 res->flags = res_pass16->flags; 1719 res->status = res_pass16->status; 1720 res->error = res_pass16->error; 1721 res->lba_low = res_pass16->lba_low; 1722 res->lba_mid = res_pass16->lba_mid; 1723 res->lba_high = res_pass16->lba_high; 1724 res->device = res_pass16->device; 1725 res->lba_low_exp = res_pass16->lba_low_exp; 1726 res->lba_mid_exp = res_pass16->lba_mid_exp; 1727 res->lba_high_exp = res_pass16->lba_high_exp; 1728 res->sector_count = res_pass16->sector_count; 1729 res->sector_count_exp = res_pass16->sector_count_exp; 1730 } 1731 1732 return (error); 1733 } 1734 1735 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->ataio); 1736 cam_fill_ataio(&ccb->ataio, 1737 retries, 1738 NULL, 1739 flags, 1740 tag_action, 1741 data_ptr, 1742 dxfer_len, 1743 timeout); 1744 1745 if (force48bit || lba > ATA_MAX_28BIT_LBA) 1746 ata_48bit_cmd(&ccb->ataio, command, features, lba, sector_count); 1747 else 1748 ata_28bit_cmd(&ccb->ataio, command, features, lba, sector_count); 1749 1750 if (ata_flags & AP_FLAG_CHK_COND) 1751 ccb->ataio.cmd.flags |= CAM_ATAIO_NEEDRESULT; 1752 1753 return ata_cam_send(device, ccb, 0); 1754 } 1755 1756 static void 1757 dump_data(uint16_t *ptr, uint32_t len) 1758 { 1759 u_int i; 1760 1761 for (i = 0; i < len / 2; i++) { 1762 if ((i % 8) == 0) 1763 printf(" %3d: ", i); 1764 printf("%04hx ", ptr[i]); 1765 if ((i % 8) == 7) 1766 printf("\n"); 1767 } 1768 if ((i % 8) != 7) 1769 printf("\n"); 1770 } 1771 1772 static int 1773 atahpa_proc_resp(struct cam_device *device, union ccb *ccb, 1774 int is48bit, u_int64_t *hpasize) 1775 { 1776 struct ata_res *res; 1777 1778 res = &ccb->ataio.res; 1779 if (res->status & ATA_STATUS_ERROR) { 1780 if (arglist & CAM_ARG_VERBOSE) { 1781 cam_error_print(device, ccb, CAM_ESF_ALL, 1782 CAM_EPF_ALL, stderr); 1783 printf("error = 0x%02x, sector_count = 0x%04x, " 1784 "device = 0x%02x, status = 0x%02x\n", 1785 res->error, res->sector_count, 1786 res->device, res->status); 1787 } 1788 1789 if (res->error & ATA_ERROR_ID_NOT_FOUND) { 1790 warnx("Max address has already been set since " 1791 "last power-on or hardware reset"); 1792 } 1793 1794 return (1); 1795 } 1796 1797 if (arglist & CAM_ARG_VERBOSE) { 1798 fprintf(stdout, "%s%d: Raw native max data:\n", 1799 device->device_name, device->dev_unit_num); 1800 /* res is 4 byte aligned */ 1801 dump_data((uint16_t*)(uintptr_t)res, sizeof(struct ata_res)); 1802 1803 printf("error = 0x%02x, sector_count = 0x%04x, device = 0x%02x, " 1804 "status = 0x%02x\n", res->error, res->sector_count, 1805 res->device, res->status); 1806 } 1807 1808 if (hpasize != NULL) { 1809 if (is48bit) { 1810 *hpasize = (((u_int64_t)((res->lba_high_exp << 16) | 1811 (res->lba_mid_exp << 8) | res->lba_low_exp) << 24) | 1812 ((res->lba_high << 16) | (res->lba_mid << 8) | 1813 res->lba_low)) + 1; 1814 } else { 1815 *hpasize = (((res->device & 0x0f) << 24) | 1816 (res->lba_high << 16) | (res->lba_mid << 8) | 1817 res->lba_low) + 1; 1818 } 1819 } 1820 1821 return (0); 1822 } 1823 1824 static int 1825 ata_read_native_max(struct cam_device *device, int retry_count, 1826 u_int32_t timeout, union ccb *ccb, 1827 struct ata_params *parm, u_int64_t *hpasize) 1828 { 1829 int error; 1830 u_int cmd, is48bit; 1831 u_int8_t protocol; 1832 1833 is48bit = parm->support.command2 & ATA_SUPPORT_ADDRESS48; 1834 protocol = AP_PROTO_NON_DATA; 1835 1836 if (is48bit) { 1837 cmd = ATA_READ_NATIVE_MAX_ADDRESS48; 1838 protocol |= AP_EXTEND; 1839 } else { 1840 cmd = ATA_READ_NATIVE_MAX_ADDRESS; 1841 } 1842 1843 error = ata_do_cmd(device, 1844 ccb, 1845 retry_count, 1846 /*flags*/CAM_DIR_NONE, 1847 /*protocol*/protocol, 1848 /*ata_flags*/AP_FLAG_CHK_COND, 1849 /*tag_action*/MSG_SIMPLE_Q_TAG, 1850 /*command*/cmd, 1851 /*features*/0, 1852 /*lba*/0, 1853 /*sector_count*/0, 1854 /*data_ptr*/NULL, 1855 /*dxfer_len*/0, 1856 timeout ? timeout : 1000, 1857 is48bit); 1858 1859 if (error) 1860 return (error); 1861 1862 return atahpa_proc_resp(device, ccb, is48bit, hpasize); 1863 } 1864 1865 static int 1866 atahpa_set_max(struct cam_device *device, int retry_count, 1867 u_int32_t timeout, union ccb *ccb, 1868 int is48bit, u_int64_t maxsize, int persist) 1869 { 1870 int error; 1871 u_int cmd; 1872 u_int8_t protocol; 1873 1874 protocol = AP_PROTO_NON_DATA; 1875 1876 if (is48bit) { 1877 cmd = ATA_SET_MAX_ADDRESS48; 1878 protocol |= AP_EXTEND; 1879 } else { 1880 cmd = ATA_SET_MAX_ADDRESS; 1881 } 1882 1883 /* lba's are zero indexed so the max lba is requested max - 1 */ 1884 if (maxsize) 1885 maxsize--; 1886 1887 error = ata_do_cmd(device, 1888 ccb, 1889 retry_count, 1890 /*flags*/CAM_DIR_NONE, 1891 /*protocol*/protocol, 1892 /*ata_flags*/AP_FLAG_CHK_COND, 1893 /*tag_action*/MSG_SIMPLE_Q_TAG, 1894 /*command*/cmd, 1895 /*features*/ATA_HPA_FEAT_MAX_ADDR, 1896 /*lba*/maxsize, 1897 /*sector_count*/persist, 1898 /*data_ptr*/NULL, 1899 /*dxfer_len*/0, 1900 timeout ? timeout : 1000, 1901 is48bit); 1902 1903 if (error) 1904 return (error); 1905 1906 return atahpa_proc_resp(device, ccb, is48bit, NULL); 1907 } 1908 1909 static int 1910 atahpa_password(struct cam_device *device, int retry_count, 1911 u_int32_t timeout, union ccb *ccb, 1912 int is48bit, struct ata_set_max_pwd *pwd) 1913 { 1914 int error; 1915 u_int cmd; 1916 u_int8_t protocol; 1917 1918 protocol = AP_PROTO_PIO_OUT; 1919 cmd = (is48bit) ? ATA_SET_MAX_ADDRESS48 : ATA_SET_MAX_ADDRESS; 1920 1921 error = ata_do_cmd(device, 1922 ccb, 1923 retry_count, 1924 /*flags*/CAM_DIR_OUT, 1925 /*protocol*/protocol, 1926 /*ata_flags*/AP_FLAG_CHK_COND, 1927 /*tag_action*/MSG_SIMPLE_Q_TAG, 1928 /*command*/cmd, 1929 /*features*/ATA_HPA_FEAT_SET_PWD, 1930 /*lba*/0, 1931 /*sector_count*/0, 1932 /*data_ptr*/(u_int8_t*)pwd, 1933 /*dxfer_len*/sizeof(struct ata_set_max_pwd), 1934 timeout ? timeout : 1000, 1935 is48bit); 1936 1937 if (error) 1938 return (error); 1939 1940 return atahpa_proc_resp(device, ccb, is48bit, NULL); 1941 } 1942 1943 static int 1944 atahpa_lock(struct cam_device *device, int retry_count, 1945 u_int32_t timeout, union ccb *ccb, int is48bit) 1946 { 1947 int error; 1948 u_int cmd; 1949 u_int8_t protocol; 1950 1951 protocol = AP_PROTO_NON_DATA; 1952 cmd = (is48bit) ? ATA_SET_MAX_ADDRESS48 : ATA_SET_MAX_ADDRESS; 1953 1954 error = ata_do_cmd(device, 1955 ccb, 1956 retry_count, 1957 /*flags*/CAM_DIR_NONE, 1958 /*protocol*/protocol, 1959 /*ata_flags*/AP_FLAG_CHK_COND, 1960 /*tag_action*/MSG_SIMPLE_Q_TAG, 1961 /*command*/cmd, 1962 /*features*/ATA_HPA_FEAT_LOCK, 1963 /*lba*/0, 1964 /*sector_count*/0, 1965 /*data_ptr*/NULL, 1966 /*dxfer_len*/0, 1967 timeout ? timeout : 1000, 1968 is48bit); 1969 1970 if (error) 1971 return (error); 1972 1973 return atahpa_proc_resp(device, ccb, is48bit, NULL); 1974 } 1975 1976 static int 1977 atahpa_unlock(struct cam_device *device, int retry_count, 1978 u_int32_t timeout, union ccb *ccb, 1979 int is48bit, struct ata_set_max_pwd *pwd) 1980 { 1981 int error; 1982 u_int cmd; 1983 u_int8_t protocol; 1984 1985 protocol = AP_PROTO_PIO_OUT; 1986 cmd = (is48bit) ? ATA_SET_MAX_ADDRESS48 : ATA_SET_MAX_ADDRESS; 1987 1988 error = ata_do_cmd(device, 1989 ccb, 1990 retry_count, 1991 /*flags*/CAM_DIR_OUT, 1992 /*protocol*/protocol, 1993 /*ata_flags*/AP_FLAG_CHK_COND, 1994 /*tag_action*/MSG_SIMPLE_Q_TAG, 1995 /*command*/cmd, 1996 /*features*/ATA_HPA_FEAT_UNLOCK, 1997 /*lba*/0, 1998 /*sector_count*/0, 1999 /*data_ptr*/(u_int8_t*)pwd, 2000 /*dxfer_len*/sizeof(struct ata_set_max_pwd), 2001 timeout ? timeout : 1000, 2002 is48bit); 2003 2004 if (error) 2005 return (error); 2006 2007 return atahpa_proc_resp(device, ccb, is48bit, NULL); 2008 } 2009 2010 static int 2011 atahpa_freeze_lock(struct cam_device *device, int retry_count, 2012 u_int32_t timeout, union ccb *ccb, int is48bit) 2013 { 2014 int error; 2015 u_int cmd; 2016 u_int8_t protocol; 2017 2018 protocol = AP_PROTO_NON_DATA; 2019 cmd = (is48bit) ? ATA_SET_MAX_ADDRESS48 : ATA_SET_MAX_ADDRESS; 2020 2021 error = ata_do_cmd(device, 2022 ccb, 2023 retry_count, 2024 /*flags*/CAM_DIR_NONE, 2025 /*protocol*/protocol, 2026 /*ata_flags*/AP_FLAG_CHK_COND, 2027 /*tag_action*/MSG_SIMPLE_Q_TAG, 2028 /*command*/cmd, 2029 /*features*/ATA_HPA_FEAT_FREEZE, 2030 /*lba*/0, 2031 /*sector_count*/0, 2032 /*data_ptr*/NULL, 2033 /*dxfer_len*/0, 2034 timeout ? timeout : 1000, 2035 is48bit); 2036 2037 if (error) 2038 return (error); 2039 2040 return atahpa_proc_resp(device, ccb, is48bit, NULL); 2041 } 2042 2043 2044 int 2045 ata_do_identify(struct cam_device *device, int retry_count, int timeout, 2046 union ccb *ccb, struct ata_params** ident_bufp) 2047 { 2048 struct ata_params *ident_buf; 2049 struct ccb_pathinq cpi; 2050 struct ccb_getdev cgd; 2051 u_int i, error; 2052 int16_t *ptr; 2053 u_int8_t command, retry_command; 2054 2055 if (get_cpi(device, &cpi) != 0) { 2056 warnx("couldn't get CPI"); 2057 return (-1); 2058 } 2059 2060 /* Neither PROTO_ATAPI or PROTO_SATAPM are used in cpi.protocol */ 2061 if (cpi.protocol == PROTO_ATA) { 2062 if (get_cgd(device, &cgd) != 0) { 2063 warnx("couldn't get CGD"); 2064 return (-1); 2065 } 2066 2067 command = (cgd.protocol == PROTO_ATA) ? 2068 ATA_ATA_IDENTIFY : ATA_ATAPI_IDENTIFY; 2069 retry_command = 0; 2070 } else { 2071 /* We don't know which for sure so try both */ 2072 command = ATA_ATA_IDENTIFY; 2073 retry_command = ATA_ATAPI_IDENTIFY; 2074 } 2075 2076 ptr = (uint16_t *)calloc(1, sizeof(struct ata_params)); 2077 if (ptr == NULL) { 2078 warnx("can't calloc memory for identify\n"); 2079 return (1); 2080 } 2081 2082 error = ata_do_28bit_cmd(device, 2083 ccb, 2084 /*retries*/retry_count, 2085 /*flags*/CAM_DIR_IN, 2086 /*protocol*/AP_PROTO_PIO_IN, 2087 /*tag_action*/MSG_SIMPLE_Q_TAG, 2088 /*command*/command, 2089 /*features*/0, 2090 /*lba*/0, 2091 /*sector_count*/(u_int8_t)sizeof(struct ata_params), 2092 /*data_ptr*/(u_int8_t *)ptr, 2093 /*dxfer_len*/sizeof(struct ata_params), 2094 /*timeout*/timeout ? timeout : 30 * 1000, 2095 /*quiet*/1); 2096 2097 if (error != 0) { 2098 if (retry_command == 0) { 2099 free(ptr); 2100 return (1); 2101 } 2102 error = ata_do_28bit_cmd(device, 2103 ccb, 2104 /*retries*/retry_count, 2105 /*flags*/CAM_DIR_IN, 2106 /*protocol*/AP_PROTO_PIO_IN, 2107 /*tag_action*/MSG_SIMPLE_Q_TAG, 2108 /*command*/retry_command, 2109 /*features*/0, 2110 /*lba*/0, 2111 /*sector_count*/(u_int8_t) 2112 sizeof(struct ata_params), 2113 /*data_ptr*/(u_int8_t *)ptr, 2114 /*dxfer_len*/sizeof(struct ata_params), 2115 /*timeout*/timeout ? timeout : 30 * 1000, 2116 /*quiet*/0); 2117 2118 if (error != 0) { 2119 free(ptr); 2120 return (1); 2121 } 2122 } 2123 2124 error = 1; 2125 for (i = 0; i < sizeof(struct ata_params) / 2; i++) { 2126 ptr[i] = le16toh(ptr[i]); 2127 if (ptr[i] != 0) 2128 error = 0; 2129 } 2130 2131 if (arglist & CAM_ARG_VERBOSE) { 2132 fprintf(stdout, "%s%d: Raw identify data:\n", 2133 device->device_name, device->dev_unit_num); 2134 dump_data(ptr, sizeof(struct ata_params)); 2135 } 2136 2137 /* check for invalid (all zero) response */ 2138 if (error != 0) { 2139 warnx("Invalid identify response detected"); 2140 free(ptr); 2141 return (error); 2142 } 2143 2144 ident_buf = (struct ata_params *)ptr; 2145 if (strncmp(ident_buf->model, "FX", 2) && 2146 strncmp(ident_buf->model, "NEC", 3) && 2147 strncmp(ident_buf->model, "Pioneer", 7) && 2148 strncmp(ident_buf->model, "SHARP", 5)) { 2149 ata_bswap(ident_buf->model, sizeof(ident_buf->model)); 2150 ata_bswap(ident_buf->revision, sizeof(ident_buf->revision)); 2151 ata_bswap(ident_buf->serial, sizeof(ident_buf->serial)); 2152 ata_bswap(ident_buf->media_serial, sizeof(ident_buf->media_serial)); 2153 } 2154 ata_btrim(ident_buf->model, sizeof(ident_buf->model)); 2155 ata_bpack(ident_buf->model, ident_buf->model, sizeof(ident_buf->model)); 2156 ata_btrim(ident_buf->revision, sizeof(ident_buf->revision)); 2157 ata_bpack(ident_buf->revision, ident_buf->revision, sizeof(ident_buf->revision)); 2158 ata_btrim(ident_buf->serial, sizeof(ident_buf->serial)); 2159 ata_bpack(ident_buf->serial, ident_buf->serial, sizeof(ident_buf->serial)); 2160 ata_btrim(ident_buf->media_serial, sizeof(ident_buf->media_serial)); 2161 ata_bpack(ident_buf->media_serial, ident_buf->media_serial, 2162 sizeof(ident_buf->media_serial)); 2163 2164 *ident_bufp = ident_buf; 2165 2166 return (0); 2167 } 2168 2169 2170 static int 2171 ataidentify(struct cam_device *device, int retry_count, int timeout) 2172 { 2173 union ccb *ccb; 2174 struct ata_params *ident_buf; 2175 u_int64_t hpasize; 2176 2177 if ((ccb = cam_getccb(device)) == NULL) { 2178 warnx("couldn't allocate CCB"); 2179 return (1); 2180 } 2181 2182 if (ata_do_identify(device, retry_count, timeout, ccb, &ident_buf) != 0) { 2183 cam_freeccb(ccb); 2184 return (1); 2185 } 2186 2187 if (ident_buf->support.command1 & ATA_SUPPORT_PROTECTED) { 2188 if (ata_read_native_max(device, retry_count, timeout, ccb, 2189 ident_buf, &hpasize) != 0) { 2190 cam_freeccb(ccb); 2191 return (1); 2192 } 2193 } else { 2194 hpasize = 0; 2195 } 2196 2197 printf("%s%d: ", device->device_name, device->dev_unit_num); 2198 ata_print_ident(ident_buf); 2199 camxferrate(device); 2200 atacapprint(ident_buf); 2201 atahpa_print(ident_buf, hpasize, 0); 2202 2203 free(ident_buf); 2204 cam_freeccb(ccb); 2205 2206 return (0); 2207 } 2208 #endif /* MINIMALISTIC */ 2209 2210 2211 #ifndef MINIMALISTIC 2212 enum { 2213 ATA_SECURITY_ACTION_PRINT, 2214 ATA_SECURITY_ACTION_FREEZE, 2215 ATA_SECURITY_ACTION_UNLOCK, 2216 ATA_SECURITY_ACTION_DISABLE, 2217 ATA_SECURITY_ACTION_ERASE, 2218 ATA_SECURITY_ACTION_ERASE_ENHANCED, 2219 ATA_SECURITY_ACTION_SET_PASSWORD 2220 }; 2221 2222 static void 2223 atasecurity_print_time(u_int16_t tw) 2224 { 2225 2226 if (tw == 0) 2227 printf("unspecified"); 2228 else if (tw >= 255) 2229 printf("> 508 min"); 2230 else 2231 printf("%i min", 2 * tw); 2232 } 2233 2234 static u_int32_t 2235 atasecurity_erase_timeout_msecs(u_int16_t timeout) 2236 { 2237 2238 if (timeout == 0) 2239 return 2 * 3600 * 1000; /* default: two hours */ 2240 else if (timeout > 255) 2241 return (508 + 60) * 60 * 1000; /* spec says > 508 minutes */ 2242 2243 return ((2 * timeout) + 5) * 60 * 1000; /* add a 5min margin */ 2244 } 2245 2246 2247 static void 2248 atasecurity_notify(u_int8_t command, struct ata_security_password *pwd) 2249 { 2250 struct ata_cmd cmd; 2251 2252 bzero(&cmd, sizeof(cmd)); 2253 cmd.command = command; 2254 printf("Issuing %s", ata_op_string(&cmd)); 2255 2256 if (pwd != NULL) { 2257 char pass[sizeof(pwd->password)+1]; 2258 2259 /* pwd->password may not be null terminated */ 2260 pass[sizeof(pwd->password)] = '\0'; 2261 strncpy(pass, pwd->password, sizeof(pwd->password)); 2262 printf(" password='%s', user='%s'", 2263 pass, 2264 (pwd->ctrl & ATA_SECURITY_PASSWORD_MASTER) ? 2265 "master" : "user"); 2266 2267 if (command == ATA_SECURITY_SET_PASSWORD) { 2268 printf(", mode='%s'", 2269 (pwd->ctrl & ATA_SECURITY_LEVEL_MAXIMUM) ? 2270 "maximum" : "high"); 2271 } 2272 } 2273 2274 printf("\n"); 2275 } 2276 2277 static int 2278 atasecurity_freeze(struct cam_device *device, union ccb *ccb, 2279 int retry_count, u_int32_t timeout, int quiet) 2280 { 2281 2282 if (quiet == 0) 2283 atasecurity_notify(ATA_SECURITY_FREEZE_LOCK, NULL); 2284 2285 return ata_do_28bit_cmd(device, 2286 ccb, 2287 retry_count, 2288 /*flags*/CAM_DIR_NONE, 2289 /*protocol*/AP_PROTO_NON_DATA, 2290 /*tag_action*/MSG_SIMPLE_Q_TAG, 2291 /*command*/ATA_SECURITY_FREEZE_LOCK, 2292 /*features*/0, 2293 /*lba*/0, 2294 /*sector_count*/0, 2295 /*data_ptr*/NULL, 2296 /*dxfer_len*/0, 2297 /*timeout*/timeout, 2298 /*quiet*/0); 2299 } 2300 2301 static int 2302 atasecurity_unlock(struct cam_device *device, union ccb *ccb, 2303 int retry_count, u_int32_t timeout, 2304 struct ata_security_password *pwd, int quiet) 2305 { 2306 2307 if (quiet == 0) 2308 atasecurity_notify(ATA_SECURITY_UNLOCK, pwd); 2309 2310 return ata_do_28bit_cmd(device, 2311 ccb, 2312 retry_count, 2313 /*flags*/CAM_DIR_OUT, 2314 /*protocol*/AP_PROTO_PIO_OUT, 2315 /*tag_action*/MSG_SIMPLE_Q_TAG, 2316 /*command*/ATA_SECURITY_UNLOCK, 2317 /*features*/0, 2318 /*lba*/0, 2319 /*sector_count*/0, 2320 /*data_ptr*/(u_int8_t *)pwd, 2321 /*dxfer_len*/sizeof(*pwd), 2322 /*timeout*/timeout, 2323 /*quiet*/0); 2324 } 2325 2326 static int 2327 atasecurity_disable(struct cam_device *device, union ccb *ccb, 2328 int retry_count, u_int32_t timeout, 2329 struct ata_security_password *pwd, int quiet) 2330 { 2331 2332 if (quiet == 0) 2333 atasecurity_notify(ATA_SECURITY_DISABLE_PASSWORD, pwd); 2334 return ata_do_28bit_cmd(device, 2335 ccb, 2336 retry_count, 2337 /*flags*/CAM_DIR_OUT, 2338 /*protocol*/AP_PROTO_PIO_OUT, 2339 /*tag_action*/MSG_SIMPLE_Q_TAG, 2340 /*command*/ATA_SECURITY_DISABLE_PASSWORD, 2341 /*features*/0, 2342 /*lba*/0, 2343 /*sector_count*/0, 2344 /*data_ptr*/(u_int8_t *)pwd, 2345 /*dxfer_len*/sizeof(*pwd), 2346 /*timeout*/timeout, 2347 /*quiet*/0); 2348 } 2349 2350 2351 static int 2352 atasecurity_erase_confirm(struct cam_device *device, 2353 struct ata_params* ident_buf) 2354 { 2355 2356 printf("\nYou are about to ERASE ALL DATA from the following" 2357 " device:\n%s%d,%s%d: ", device->device_name, 2358 device->dev_unit_num, device->given_dev_name, 2359 device->given_unit_number); 2360 ata_print_ident(ident_buf); 2361 2362 for(;;) { 2363 char str[50]; 2364 printf("\nAre you SURE you want to ERASE ALL DATA? (yes/no) "); 2365 2366 if (fgets(str, sizeof(str), stdin) != NULL) { 2367 if (strncasecmp(str, "yes", 3) == 0) { 2368 return (1); 2369 } else if (strncasecmp(str, "no", 2) == 0) { 2370 return (0); 2371 } else { 2372 printf("Please answer \"yes\" or " 2373 "\"no\"\n"); 2374 } 2375 } 2376 } 2377 2378 /* NOTREACHED */ 2379 return (0); 2380 } 2381 2382 static int 2383 atasecurity_erase(struct cam_device *device, union ccb *ccb, 2384 int retry_count, u_int32_t timeout, 2385 u_int32_t erase_timeout, 2386 struct ata_security_password *pwd, int quiet) 2387 { 2388 int error; 2389 2390 if (quiet == 0) 2391 atasecurity_notify(ATA_SECURITY_ERASE_PREPARE, NULL); 2392 2393 error = ata_do_28bit_cmd(device, 2394 ccb, 2395 retry_count, 2396 /*flags*/CAM_DIR_NONE, 2397 /*protocol*/AP_PROTO_NON_DATA, 2398 /*tag_action*/MSG_SIMPLE_Q_TAG, 2399 /*command*/ATA_SECURITY_ERASE_PREPARE, 2400 /*features*/0, 2401 /*lba*/0, 2402 /*sector_count*/0, 2403 /*data_ptr*/NULL, 2404 /*dxfer_len*/0, 2405 /*timeout*/timeout, 2406 /*quiet*/0); 2407 2408 if (error != 0) 2409 return error; 2410 2411 if (quiet == 0) 2412 atasecurity_notify(ATA_SECURITY_ERASE_UNIT, pwd); 2413 2414 error = ata_do_28bit_cmd(device, 2415 ccb, 2416 retry_count, 2417 /*flags*/CAM_DIR_OUT, 2418 /*protocol*/AP_PROTO_PIO_OUT, 2419 /*tag_action*/MSG_SIMPLE_Q_TAG, 2420 /*command*/ATA_SECURITY_ERASE_UNIT, 2421 /*features*/0, 2422 /*lba*/0, 2423 /*sector_count*/0, 2424 /*data_ptr*/(u_int8_t *)pwd, 2425 /*dxfer_len*/sizeof(*pwd), 2426 /*timeout*/erase_timeout, 2427 /*quiet*/0); 2428 2429 if (error == 0 && quiet == 0) 2430 printf("\nErase Complete\n"); 2431 2432 return error; 2433 } 2434 2435 static int 2436 atasecurity_set_password(struct cam_device *device, union ccb *ccb, 2437 int retry_count, u_int32_t timeout, 2438 struct ata_security_password *pwd, int quiet) 2439 { 2440 2441 if (quiet == 0) 2442 atasecurity_notify(ATA_SECURITY_SET_PASSWORD, pwd); 2443 2444 return ata_do_28bit_cmd(device, 2445 ccb, 2446 retry_count, 2447 /*flags*/CAM_DIR_OUT, 2448 /*protocol*/AP_PROTO_PIO_OUT, 2449 /*tag_action*/MSG_SIMPLE_Q_TAG, 2450 /*command*/ATA_SECURITY_SET_PASSWORD, 2451 /*features*/0, 2452 /*lba*/0, 2453 /*sector_count*/0, 2454 /*data_ptr*/(u_int8_t *)pwd, 2455 /*dxfer_len*/sizeof(*pwd), 2456 /*timeout*/timeout, 2457 /*quiet*/0); 2458 } 2459 2460 static void 2461 atasecurity_print(struct ata_params *parm) 2462 { 2463 2464 printf("\nSecurity Option Value\n"); 2465 if (arglist & CAM_ARG_VERBOSE) { 2466 printf("status %04x\n", 2467 parm->security_status); 2468 } 2469 printf("supported %s\n", 2470 parm->security_status & ATA_SECURITY_SUPPORTED ? "yes" : "no"); 2471 if (!(parm->security_status & ATA_SECURITY_SUPPORTED)) 2472 return; 2473 printf("enabled %s\n", 2474 parm->security_status & ATA_SECURITY_ENABLED ? "yes" : "no"); 2475 printf("drive locked %s\n", 2476 parm->security_status & ATA_SECURITY_LOCKED ? "yes" : "no"); 2477 printf("security config frozen %s\n", 2478 parm->security_status & ATA_SECURITY_FROZEN ? "yes" : "no"); 2479 printf("count expired %s\n", 2480 parm->security_status & ATA_SECURITY_COUNT_EXP ? "yes" : "no"); 2481 printf("security level %s\n", 2482 parm->security_status & ATA_SECURITY_LEVEL ? "maximum" : "high"); 2483 printf("enhanced erase supported %s\n", 2484 parm->security_status & ATA_SECURITY_ENH_SUPP ? "yes" : "no"); 2485 printf("erase time "); 2486 atasecurity_print_time(parm->erase_time); 2487 printf("\n"); 2488 printf("enhanced erase time "); 2489 atasecurity_print_time(parm->enhanced_erase_time); 2490 printf("\n"); 2491 printf("master password rev %04x%s\n", 2492 parm->master_passwd_revision, 2493 parm->master_passwd_revision == 0x0000 || 2494 parm->master_passwd_revision == 0xFFFF ? " (unsupported)" : ""); 2495 } 2496 2497 /* 2498 * Validates and copies the password in optarg to the passed buffer. 2499 * If the password in optarg is the same length as the buffer then 2500 * the data will still be copied but no null termination will occur. 2501 */ 2502 static int 2503 ata_getpwd(u_int8_t *passwd, int max, char opt) 2504 { 2505 int len; 2506 2507 len = strlen(optarg); 2508 if (len > max) { 2509 warnx("-%c password is too long", opt); 2510 return (1); 2511 } else if (len == 0) { 2512 warnx("-%c password is missing", opt); 2513 return (1); 2514 } else if (optarg[0] == '-'){ 2515 warnx("-%c password starts with '-' (generic arg?)", opt); 2516 return (1); 2517 } else if (strlen(passwd) != 0 && strcmp(passwd, optarg) != 0) { 2518 warnx("-%c password conflicts with existing password from -%c", 2519 opt, pwd_opt); 2520 return (1); 2521 } 2522 2523 /* Callers pass in a buffer which does NOT need to be terminated */ 2524 strncpy(passwd, optarg, max); 2525 pwd_opt = opt; 2526 2527 return (0); 2528 } 2529 2530 enum { 2531 ATA_HPA_ACTION_PRINT, 2532 ATA_HPA_ACTION_SET_MAX, 2533 ATA_HPA_ACTION_SET_PWD, 2534 ATA_HPA_ACTION_LOCK, 2535 ATA_HPA_ACTION_UNLOCK, 2536 ATA_HPA_ACTION_FREEZE_LOCK 2537 }; 2538 2539 static int 2540 atahpa_set_confirm(struct cam_device *device, struct ata_params* ident_buf, 2541 u_int64_t maxsize, int persist) 2542 { 2543 printf("\nYou are about to configure HPA to limit the user accessible\n" 2544 "sectors to %ju %s on the device:\n%s%d,%s%d: ", maxsize, 2545 persist ? "persistently" : "temporarily", 2546 device->device_name, device->dev_unit_num, 2547 device->given_dev_name, device->given_unit_number); 2548 ata_print_ident(ident_buf); 2549 2550 for(;;) { 2551 char str[50]; 2552 printf("\nAre you SURE you want to configure HPA? (yes/no) "); 2553 2554 if (NULL != fgets(str, sizeof(str), stdin)) { 2555 if (0 == strncasecmp(str, "yes", 3)) { 2556 return (1); 2557 } else if (0 == strncasecmp(str, "no", 2)) { 2558 return (0); 2559 } else { 2560 printf("Please answer \"yes\" or " 2561 "\"no\"\n"); 2562 } 2563 } 2564 } 2565 2566 /* NOTREACHED */ 2567 return (0); 2568 } 2569 2570 static int 2571 atahpa(struct cam_device *device, int retry_count, int timeout, 2572 int argc, char **argv, char *combinedopt) 2573 { 2574 union ccb *ccb; 2575 struct ata_params *ident_buf; 2576 struct ccb_getdev cgd; 2577 struct ata_set_max_pwd pwd; 2578 int error, confirm, quiet, c, action, actions, persist; 2579 int security, is48bit, pwdsize; 2580 u_int64_t hpasize, maxsize; 2581 2582 actions = 0; 2583 confirm = 0; 2584 quiet = 0; 2585 maxsize = 0; 2586 persist = 0; 2587 security = 0; 2588 2589 memset(&pwd, 0, sizeof(pwd)); 2590 2591 /* default action is to print hpa information */ 2592 action = ATA_HPA_ACTION_PRINT; 2593 pwdsize = sizeof(pwd.password); 2594 2595 while ((c = getopt(argc, argv, combinedopt)) != -1) { 2596 switch(c){ 2597 case 's': 2598 action = ATA_HPA_ACTION_SET_MAX; 2599 maxsize = strtoumax(optarg, NULL, 0); 2600 actions++; 2601 break; 2602 2603 case 'p': 2604 if (ata_getpwd(pwd.password, pwdsize, c) != 0) 2605 return (1); 2606 action = ATA_HPA_ACTION_SET_PWD; 2607 security = 1; 2608 actions++; 2609 break; 2610 2611 case 'l': 2612 action = ATA_HPA_ACTION_LOCK; 2613 security = 1; 2614 actions++; 2615 break; 2616 2617 case 'U': 2618 if (ata_getpwd(pwd.password, pwdsize, c) != 0) 2619 return (1); 2620 action = ATA_HPA_ACTION_UNLOCK; 2621 security = 1; 2622 actions++; 2623 break; 2624 2625 case 'f': 2626 action = ATA_HPA_ACTION_FREEZE_LOCK; 2627 security = 1; 2628 actions++; 2629 break; 2630 2631 case 'P': 2632 persist = 1; 2633 break; 2634 2635 case 'y': 2636 confirm++; 2637 break; 2638 2639 case 'q': 2640 quiet++; 2641 break; 2642 } 2643 } 2644 2645 if (actions > 1) { 2646 warnx("too many hpa actions specified"); 2647 return (1); 2648 } 2649 2650 if (get_cgd(device, &cgd) != 0) { 2651 warnx("couldn't get CGD"); 2652 return (1); 2653 } 2654 2655 ccb = cam_getccb(device); 2656 if (ccb == NULL) { 2657 warnx("couldn't allocate CCB"); 2658 return (1); 2659 } 2660 2661 error = ata_do_identify(device, retry_count, timeout, ccb, &ident_buf); 2662 if (error != 0) { 2663 cam_freeccb(ccb); 2664 return (1); 2665 } 2666 2667 if (quiet == 0) { 2668 printf("%s%d: ", device->device_name, device->dev_unit_num); 2669 ata_print_ident(ident_buf); 2670 camxferrate(device); 2671 } 2672 2673 if (action == ATA_HPA_ACTION_PRINT) { 2674 error = ata_read_native_max(device, retry_count, timeout, ccb, 2675 ident_buf, &hpasize); 2676 if (error == 0) 2677 atahpa_print(ident_buf, hpasize, 1); 2678 2679 cam_freeccb(ccb); 2680 free(ident_buf); 2681 return (error); 2682 } 2683 2684 if (!(ident_buf->support.command1 & ATA_SUPPORT_PROTECTED)) { 2685 warnx("HPA is not supported by this device"); 2686 cam_freeccb(ccb); 2687 free(ident_buf); 2688 return (1); 2689 } 2690 2691 if (security && !(ident_buf->support.command1 & ATA_SUPPORT_MAXSECURITY)) { 2692 warnx("HPA Security is not supported by this device"); 2693 cam_freeccb(ccb); 2694 free(ident_buf); 2695 return (1); 2696 } 2697 2698 is48bit = ident_buf->support.command2 & ATA_SUPPORT_ADDRESS48; 2699 2700 /* 2701 * The ATA spec requires: 2702 * 1. Read native max addr is called directly before set max addr 2703 * 2. Read native max addr is NOT called before any other set max call 2704 */ 2705 switch(action) { 2706 case ATA_HPA_ACTION_SET_MAX: 2707 if (confirm == 0 && 2708 atahpa_set_confirm(device, ident_buf, maxsize, 2709 persist) == 0) { 2710 cam_freeccb(ccb); 2711 free(ident_buf); 2712 return (1); 2713 } 2714 2715 error = ata_read_native_max(device, retry_count, timeout, 2716 ccb, ident_buf, &hpasize); 2717 if (error == 0) { 2718 error = atahpa_set_max(device, retry_count, timeout, 2719 ccb, is48bit, maxsize, persist); 2720 if (error == 0) { 2721 /* redo identify to get new lba values */ 2722 error = ata_do_identify(device, retry_count, 2723 timeout, ccb, 2724 &ident_buf); 2725 atahpa_print(ident_buf, hpasize, 1); 2726 } 2727 } 2728 break; 2729 2730 case ATA_HPA_ACTION_SET_PWD: 2731 error = atahpa_password(device, retry_count, timeout, 2732 ccb, is48bit, &pwd); 2733 if (error == 0) 2734 printf("HPA password has been set\n"); 2735 break; 2736 2737 case ATA_HPA_ACTION_LOCK: 2738 error = atahpa_lock(device, retry_count, timeout, 2739 ccb, is48bit); 2740 if (error == 0) 2741 printf("HPA has been locked\n"); 2742 break; 2743 2744 case ATA_HPA_ACTION_UNLOCK: 2745 error = atahpa_unlock(device, retry_count, timeout, 2746 ccb, is48bit, &pwd); 2747 if (error == 0) 2748 printf("HPA has been unlocked\n"); 2749 break; 2750 2751 case ATA_HPA_ACTION_FREEZE_LOCK: 2752 error = atahpa_freeze_lock(device, retry_count, timeout, 2753 ccb, is48bit); 2754 if (error == 0) 2755 printf("HPA has been frozen\n"); 2756 break; 2757 2758 default: 2759 errx(1, "Option currently not supported"); 2760 } 2761 2762 cam_freeccb(ccb); 2763 free(ident_buf); 2764 2765 return (error); 2766 } 2767 2768 static int 2769 atasecurity(struct cam_device *device, int retry_count, int timeout, 2770 int argc, char **argv, char *combinedopt) 2771 { 2772 union ccb *ccb; 2773 struct ata_params *ident_buf; 2774 int error, confirm, quiet, c, action, actions, setpwd; 2775 int security_enabled, erase_timeout, pwdsize; 2776 struct ata_security_password pwd; 2777 2778 actions = 0; 2779 setpwd = 0; 2780 erase_timeout = 0; 2781 confirm = 0; 2782 quiet = 0; 2783 2784 memset(&pwd, 0, sizeof(pwd)); 2785 2786 /* default action is to print security information */ 2787 action = ATA_SECURITY_ACTION_PRINT; 2788 2789 /* user is master by default as its safer that way */ 2790 pwd.ctrl |= ATA_SECURITY_PASSWORD_MASTER; 2791 pwdsize = sizeof(pwd.password); 2792 2793 while ((c = getopt(argc, argv, combinedopt)) != -1) { 2794 switch(c){ 2795 case 'f': 2796 action = ATA_SECURITY_ACTION_FREEZE; 2797 actions++; 2798 break; 2799 2800 case 'U': 2801 if (strcasecmp(optarg, "user") == 0) { 2802 pwd.ctrl |= ATA_SECURITY_PASSWORD_USER; 2803 pwd.ctrl &= ~ATA_SECURITY_PASSWORD_MASTER; 2804 } else if (strcasecmp(optarg, "master") == 0) { 2805 pwd.ctrl |= ATA_SECURITY_PASSWORD_MASTER; 2806 pwd.ctrl &= ~ATA_SECURITY_PASSWORD_USER; 2807 } else { 2808 warnx("-U argument '%s' is invalid (must be " 2809 "'user' or 'master')", optarg); 2810 return (1); 2811 } 2812 break; 2813 2814 case 'l': 2815 if (strcasecmp(optarg, "high") == 0) { 2816 pwd.ctrl |= ATA_SECURITY_LEVEL_HIGH; 2817 pwd.ctrl &= ~ATA_SECURITY_LEVEL_MAXIMUM; 2818 } else if (strcasecmp(optarg, "maximum") == 0) { 2819 pwd.ctrl |= ATA_SECURITY_LEVEL_MAXIMUM; 2820 pwd.ctrl &= ~ATA_SECURITY_LEVEL_HIGH; 2821 } else { 2822 warnx("-l argument '%s' is unknown (must be " 2823 "'high' or 'maximum')", optarg); 2824 return (1); 2825 } 2826 break; 2827 2828 case 'k': 2829 if (ata_getpwd(pwd.password, pwdsize, c) != 0) 2830 return (1); 2831 action = ATA_SECURITY_ACTION_UNLOCK; 2832 actions++; 2833 break; 2834 2835 case 'd': 2836 if (ata_getpwd(pwd.password, pwdsize, c) != 0) 2837 return (1); 2838 action = ATA_SECURITY_ACTION_DISABLE; 2839 actions++; 2840 break; 2841 2842 case 'e': 2843 if (ata_getpwd(pwd.password, pwdsize, c) != 0) 2844 return (1); 2845 action = ATA_SECURITY_ACTION_ERASE; 2846 actions++; 2847 break; 2848 2849 case 'h': 2850 if (ata_getpwd(pwd.password, pwdsize, c) != 0) 2851 return (1); 2852 pwd.ctrl |= ATA_SECURITY_ERASE_ENHANCED; 2853 action = ATA_SECURITY_ACTION_ERASE_ENHANCED; 2854 actions++; 2855 break; 2856 2857 case 's': 2858 if (ata_getpwd(pwd.password, pwdsize, c) != 0) 2859 return (1); 2860 setpwd = 1; 2861 if (action == ATA_SECURITY_ACTION_PRINT) 2862 action = ATA_SECURITY_ACTION_SET_PASSWORD; 2863 /* 2864 * Don't increment action as this can be combined 2865 * with other actions. 2866 */ 2867 break; 2868 2869 case 'y': 2870 confirm++; 2871 break; 2872 2873 case 'q': 2874 quiet++; 2875 break; 2876 2877 case 'T': 2878 erase_timeout = atoi(optarg) * 1000; 2879 break; 2880 } 2881 } 2882 2883 if (actions > 1) { 2884 warnx("too many security actions specified"); 2885 return (1); 2886 } 2887 2888 if ((ccb = cam_getccb(device)) == NULL) { 2889 warnx("couldn't allocate CCB"); 2890 return (1); 2891 } 2892 2893 error = ata_do_identify(device, retry_count, timeout, ccb, &ident_buf); 2894 if (error != 0) { 2895 cam_freeccb(ccb); 2896 return (1); 2897 } 2898 2899 if (quiet == 0) { 2900 printf("%s%d: ", device->device_name, device->dev_unit_num); 2901 ata_print_ident(ident_buf); 2902 camxferrate(device); 2903 } 2904 2905 if (action == ATA_SECURITY_ACTION_PRINT) { 2906 atasecurity_print(ident_buf); 2907 free(ident_buf); 2908 cam_freeccb(ccb); 2909 return (0); 2910 } 2911 2912 if ((ident_buf->support.command1 & ATA_SUPPORT_SECURITY) == 0) { 2913 warnx("Security not supported"); 2914 free(ident_buf); 2915 cam_freeccb(ccb); 2916 return (1); 2917 } 2918 2919 /* default timeout 15 seconds the same as linux hdparm */ 2920 timeout = timeout ? timeout : 15 * 1000; 2921 2922 security_enabled = ident_buf->security_status & ATA_SECURITY_ENABLED; 2923 2924 /* first set the password if requested */ 2925 if (setpwd == 1) { 2926 /* confirm we can erase before setting the password if erasing */ 2927 if (confirm == 0 && 2928 (action == ATA_SECURITY_ACTION_ERASE_ENHANCED || 2929 action == ATA_SECURITY_ACTION_ERASE) && 2930 atasecurity_erase_confirm(device, ident_buf) == 0) { 2931 cam_freeccb(ccb); 2932 free(ident_buf); 2933 return (error); 2934 } 2935 2936 if (pwd.ctrl & ATA_SECURITY_PASSWORD_MASTER) { 2937 pwd.revision = ident_buf->master_passwd_revision; 2938 if (pwd.revision != 0 && pwd.revision != 0xfff && 2939 --pwd.revision == 0) { 2940 pwd.revision = 0xfffe; 2941 } 2942 } 2943 error = atasecurity_set_password(device, ccb, retry_count, 2944 timeout, &pwd, quiet); 2945 if (error != 0) { 2946 cam_freeccb(ccb); 2947 free(ident_buf); 2948 return (error); 2949 } 2950 security_enabled = 1; 2951 } 2952 2953 switch(action) { 2954 case ATA_SECURITY_ACTION_FREEZE: 2955 error = atasecurity_freeze(device, ccb, retry_count, 2956 timeout, quiet); 2957 break; 2958 2959 case ATA_SECURITY_ACTION_UNLOCK: 2960 if (security_enabled) { 2961 if (ident_buf->security_status & ATA_SECURITY_LOCKED) { 2962 error = atasecurity_unlock(device, ccb, 2963 retry_count, timeout, &pwd, quiet); 2964 } else { 2965 warnx("Can't unlock, drive is not locked"); 2966 error = 1; 2967 } 2968 } else { 2969 warnx("Can't unlock, security is disabled"); 2970 error = 1; 2971 } 2972 break; 2973 2974 case ATA_SECURITY_ACTION_DISABLE: 2975 if (security_enabled) { 2976 /* First unlock the drive if its locked */ 2977 if (ident_buf->security_status & ATA_SECURITY_LOCKED) { 2978 error = atasecurity_unlock(device, ccb, 2979 retry_count, 2980 timeout, 2981 &pwd, 2982 quiet); 2983 } 2984 2985 if (error == 0) { 2986 error = atasecurity_disable(device, 2987 ccb, 2988 retry_count, 2989 timeout, 2990 &pwd, 2991 quiet); 2992 } 2993 } else { 2994 warnx("Can't disable security (already disabled)"); 2995 error = 1; 2996 } 2997 break; 2998 2999 case ATA_SECURITY_ACTION_ERASE: 3000 if (security_enabled) { 3001 if (erase_timeout == 0) { 3002 erase_timeout = atasecurity_erase_timeout_msecs( 3003 ident_buf->erase_time); 3004 } 3005 3006 error = atasecurity_erase(device, ccb, retry_count, 3007 timeout, erase_timeout, &pwd, 3008 quiet); 3009 } else { 3010 warnx("Can't secure erase (security is disabled)"); 3011 error = 1; 3012 } 3013 break; 3014 3015 case ATA_SECURITY_ACTION_ERASE_ENHANCED: 3016 if (security_enabled) { 3017 if (ident_buf->security_status & ATA_SECURITY_ENH_SUPP) { 3018 if (erase_timeout == 0) { 3019 erase_timeout = 3020 atasecurity_erase_timeout_msecs( 3021 ident_buf->enhanced_erase_time); 3022 } 3023 3024 error = atasecurity_erase(device, ccb, 3025 retry_count, timeout, 3026 erase_timeout, &pwd, 3027 quiet); 3028 } else { 3029 warnx("Enhanced erase is not supported"); 3030 error = 1; 3031 } 3032 } else { 3033 warnx("Can't secure erase (enhanced), " 3034 "(security is disabled)"); 3035 error = 1; 3036 } 3037 break; 3038 } 3039 3040 cam_freeccb(ccb); 3041 free(ident_buf); 3042 3043 return (error); 3044 } 3045 #endif /* MINIMALISTIC */ 3046 3047 /* 3048 * Parse out a bus, or a bus, target and lun in the following 3049 * format: 3050 * bus 3051 * bus:target 3052 * bus:target:lun 3053 * 3054 * Returns the number of parsed components, or 0. 3055 */ 3056 static int 3057 parse_btl(char *tstr, path_id_t *bus, target_id_t *target, lun_id_t *lun, 3058 cam_argmask *arglst) 3059 { 3060 char *tmpstr; 3061 int convs = 0; 3062 3063 while (isspace(*tstr) && (*tstr != '\0')) 3064 tstr++; 3065 3066 tmpstr = (char *)strtok(tstr, ":"); 3067 if ((tmpstr != NULL) && (*tmpstr != '\0')) { 3068 *bus = strtol(tmpstr, NULL, 0); 3069 *arglst |= CAM_ARG_BUS; 3070 convs++; 3071 tmpstr = (char *)strtok(NULL, ":"); 3072 if ((tmpstr != NULL) && (*tmpstr != '\0')) { 3073 *target = strtol(tmpstr, NULL, 0); 3074 *arglst |= CAM_ARG_TARGET; 3075 convs++; 3076 tmpstr = (char *)strtok(NULL, ":"); 3077 if ((tmpstr != NULL) && (*tmpstr != '\0')) { 3078 *lun = strtol(tmpstr, NULL, 0); 3079 *arglst |= CAM_ARG_LUN; 3080 convs++; 3081 } 3082 } 3083 } 3084 3085 return convs; 3086 } 3087 3088 static int 3089 dorescan_or_reset(int argc, char **argv, int rescan) 3090 { 3091 static const char must[] = 3092 "you must specify \"all\", a bus, or a bus:target:lun to %s"; 3093 int rv, error = 0; 3094 path_id_t bus = CAM_BUS_WILDCARD; 3095 target_id_t target = CAM_TARGET_WILDCARD; 3096 lun_id_t lun = CAM_LUN_WILDCARD; 3097 char *tstr; 3098 3099 if (argc < 3) { 3100 warnx(must, rescan? "rescan" : "reset"); 3101 return(1); 3102 } 3103 3104 tstr = argv[optind]; 3105 while (isspace(*tstr) && (*tstr != '\0')) 3106 tstr++; 3107 if (strncasecmp(tstr, "all", strlen("all")) == 0) 3108 arglist |= CAM_ARG_BUS; 3109 else { 3110 rv = parse_btl(argv[optind], &bus, &target, &lun, &arglist); 3111 if (rv != 1 && rv != 3) { 3112 warnx(must, rescan? "rescan" : "reset"); 3113 return(1); 3114 } 3115 } 3116 3117 if ((arglist & CAM_ARG_BUS) 3118 && (arglist & CAM_ARG_TARGET) 3119 && (arglist & CAM_ARG_LUN)) 3120 error = scanlun_or_reset_dev(bus, target, lun, rescan); 3121 else 3122 error = rescan_or_reset_bus(bus, rescan); 3123 3124 return(error); 3125 } 3126 3127 static int 3128 rescan_or_reset_bus(path_id_t bus, int rescan) 3129 { 3130 union ccb ccb, matchccb; 3131 int fd, retval; 3132 int bufsize; 3133 3134 retval = 0; 3135 3136 if ((fd = open(XPT_DEVICE, O_RDWR)) < 0) { 3137 warnx("error opening transport layer device %s", XPT_DEVICE); 3138 warn("%s", XPT_DEVICE); 3139 return(1); 3140 } 3141 3142 if (bus != CAM_BUS_WILDCARD) { 3143 ccb.ccb_h.func_code = rescan ? XPT_SCAN_BUS : XPT_RESET_BUS; 3144 ccb.ccb_h.path_id = bus; 3145 ccb.ccb_h.target_id = CAM_TARGET_WILDCARD; 3146 ccb.ccb_h.target_lun = CAM_LUN_WILDCARD; 3147 ccb.crcn.flags = CAM_FLAG_NONE; 3148 3149 /* run this at a low priority */ 3150 ccb.ccb_h.pinfo.priority = 5; 3151 3152 if (ioctl(fd, CAMIOCOMMAND, &ccb) == -1) { 3153 warn("CAMIOCOMMAND ioctl failed"); 3154 close(fd); 3155 return(1); 3156 } 3157 3158 if ((ccb.ccb_h.status & CAM_STATUS_MASK) == CAM_REQ_CMP) { 3159 fprintf(stdout, "%s of bus %d was successful\n", 3160 rescan ? "Re-scan" : "Reset", bus); 3161 } else { 3162 fprintf(stdout, "%s of bus %d returned error %#x\n", 3163 rescan ? "Re-scan" : "Reset", bus, 3164 ccb.ccb_h.status & CAM_STATUS_MASK); 3165 retval = 1; 3166 } 3167 3168 close(fd); 3169 return(retval); 3170 3171 } 3172 3173 3174 /* 3175 * The right way to handle this is to modify the xpt so that it can 3176 * handle a wildcarded bus in a rescan or reset CCB. At the moment 3177 * that isn't implemented, so instead we enumerate the busses and 3178 * send the rescan or reset to those busses in the case where the 3179 * given bus is -1 (wildcard). We don't send a rescan or reset 3180 * to the xpt bus; sending a rescan to the xpt bus is effectively a 3181 * no-op, sending a rescan to the xpt bus would result in a status of 3182 * CAM_REQ_INVALID. 3183 */ 3184 CCB_CLEAR_ALL_EXCEPT_HDR(&matchccb.cdm); 3185 matchccb.ccb_h.func_code = XPT_DEV_MATCH; 3186 matchccb.ccb_h.path_id = CAM_BUS_WILDCARD; 3187 bufsize = sizeof(struct dev_match_result) * 20; 3188 matchccb.cdm.match_buf_len = bufsize; 3189 matchccb.cdm.matches=(struct dev_match_result *)malloc(bufsize); 3190 if (matchccb.cdm.matches == NULL) { 3191 warnx("can't malloc memory for matches"); 3192 retval = 1; 3193 goto bailout; 3194 } 3195 matchccb.cdm.num_matches = 0; 3196 3197 matchccb.cdm.num_patterns = 1; 3198 matchccb.cdm.pattern_buf_len = sizeof(struct dev_match_pattern); 3199 3200 matchccb.cdm.patterns = (struct dev_match_pattern *)malloc( 3201 matchccb.cdm.pattern_buf_len); 3202 if (matchccb.cdm.patterns == NULL) { 3203 warnx("can't malloc memory for patterns"); 3204 retval = 1; 3205 goto bailout; 3206 } 3207 matchccb.cdm.patterns[0].type = DEV_MATCH_BUS; 3208 matchccb.cdm.patterns[0].pattern.bus_pattern.flags = BUS_MATCH_ANY; 3209 3210 do { 3211 unsigned int i; 3212 3213 if (ioctl(fd, CAMIOCOMMAND, &matchccb) == -1) { 3214 warn("CAMIOCOMMAND ioctl failed"); 3215 retval = 1; 3216 goto bailout; 3217 } 3218 3219 if ((matchccb.ccb_h.status != CAM_REQ_CMP) 3220 || ((matchccb.cdm.status != CAM_DEV_MATCH_LAST) 3221 && (matchccb.cdm.status != CAM_DEV_MATCH_MORE))) { 3222 warnx("got CAM error %#x, CDM error %d\n", 3223 matchccb.ccb_h.status, matchccb.cdm.status); 3224 retval = 1; 3225 goto bailout; 3226 } 3227 3228 for (i = 0; i < matchccb.cdm.num_matches; i++) { 3229 struct bus_match_result *bus_result; 3230 3231 /* This shouldn't happen. */ 3232 if (matchccb.cdm.matches[i].type != DEV_MATCH_BUS) 3233 continue; 3234 3235 bus_result = &matchccb.cdm.matches[i].result.bus_result; 3236 3237 /* 3238 * We don't want to rescan or reset the xpt bus. 3239 * See above. 3240 */ 3241 if (bus_result->path_id == CAM_XPT_PATH_ID) 3242 continue; 3243 3244 ccb.ccb_h.func_code = rescan ? XPT_SCAN_BUS : 3245 XPT_RESET_BUS; 3246 ccb.ccb_h.path_id = bus_result->path_id; 3247 ccb.ccb_h.target_id = CAM_TARGET_WILDCARD; 3248 ccb.ccb_h.target_lun = CAM_LUN_WILDCARD; 3249 ccb.crcn.flags = CAM_FLAG_NONE; 3250 3251 /* run this at a low priority */ 3252 ccb.ccb_h.pinfo.priority = 5; 3253 3254 if (ioctl(fd, CAMIOCOMMAND, &ccb) == -1) { 3255 warn("CAMIOCOMMAND ioctl failed"); 3256 retval = 1; 3257 goto bailout; 3258 } 3259 3260 if ((ccb.ccb_h.status & CAM_STATUS_MASK) ==CAM_REQ_CMP){ 3261 fprintf(stdout, "%s of bus %d was successful\n", 3262 rescan? "Re-scan" : "Reset", 3263 bus_result->path_id); 3264 } else { 3265 /* 3266 * Don't bail out just yet, maybe the other 3267 * rescan or reset commands will complete 3268 * successfully. 3269 */ 3270 fprintf(stderr, "%s of bus %d returned error " 3271 "%#x\n", rescan? "Re-scan" : "Reset", 3272 bus_result->path_id, 3273 ccb.ccb_h.status & CAM_STATUS_MASK); 3274 retval = 1; 3275 } 3276 } 3277 } while ((matchccb.ccb_h.status == CAM_REQ_CMP) 3278 && (matchccb.cdm.status == CAM_DEV_MATCH_MORE)); 3279 3280 bailout: 3281 3282 if (fd != -1) 3283 close(fd); 3284 3285 if (matchccb.cdm.patterns != NULL) 3286 free(matchccb.cdm.patterns); 3287 if (matchccb.cdm.matches != NULL) 3288 free(matchccb.cdm.matches); 3289 3290 return(retval); 3291 } 3292 3293 static int 3294 scanlun_or_reset_dev(path_id_t bus, target_id_t target, lun_id_t lun, int scan) 3295 { 3296 union ccb ccb; 3297 struct cam_device *device; 3298 int fd; 3299 3300 device = NULL; 3301 3302 if (bus == CAM_BUS_WILDCARD) { 3303 warnx("invalid bus number %d", bus); 3304 return(1); 3305 } 3306 3307 if (target == CAM_TARGET_WILDCARD) { 3308 warnx("invalid target number %d", target); 3309 return(1); 3310 } 3311 3312 if (lun == CAM_LUN_WILDCARD) { 3313 warnx("invalid lun number %jx", (uintmax_t)lun); 3314 return(1); 3315 } 3316 3317 fd = -1; 3318 3319 bzero(&ccb, sizeof(union ccb)); 3320 3321 if (scan) { 3322 if ((fd = open(XPT_DEVICE, O_RDWR)) < 0) { 3323 warnx("error opening transport layer device %s\n", 3324 XPT_DEVICE); 3325 warn("%s", XPT_DEVICE); 3326 return(1); 3327 } 3328 } else { 3329 device = cam_open_btl(bus, target, lun, O_RDWR, NULL); 3330 if (device == NULL) { 3331 warnx("%s", cam_errbuf); 3332 return(1); 3333 } 3334 } 3335 3336 ccb.ccb_h.func_code = (scan)? XPT_SCAN_LUN : XPT_RESET_DEV; 3337 ccb.ccb_h.path_id = bus; 3338 ccb.ccb_h.target_id = target; 3339 ccb.ccb_h.target_lun = lun; 3340 ccb.ccb_h.timeout = 5000; 3341 ccb.crcn.flags = CAM_FLAG_NONE; 3342 3343 /* run this at a low priority */ 3344 ccb.ccb_h.pinfo.priority = 5; 3345 3346 if (scan) { 3347 if (ioctl(fd, CAMIOCOMMAND, &ccb) < 0) { 3348 warn("CAMIOCOMMAND ioctl failed"); 3349 close(fd); 3350 return(1); 3351 } 3352 } else { 3353 if (cam_send_ccb(device, &ccb) < 0) { 3354 warn("error sending XPT_RESET_DEV CCB"); 3355 cam_close_device(device); 3356 return(1); 3357 } 3358 } 3359 3360 if (scan) 3361 close(fd); 3362 else 3363 cam_close_device(device); 3364 3365 /* 3366 * An error code of CAM_BDR_SENT is normal for a BDR request. 3367 */ 3368 if (((ccb.ccb_h.status & CAM_STATUS_MASK) == CAM_REQ_CMP) 3369 || ((!scan) 3370 && ((ccb.ccb_h.status & CAM_STATUS_MASK) == CAM_BDR_SENT))) { 3371 fprintf(stdout, "%s of %d:%d:%jx was successful\n", 3372 scan? "Re-scan" : "Reset", bus, target, (uintmax_t)lun); 3373 return(0); 3374 } else { 3375 fprintf(stdout, "%s of %d:%d:%jx returned error %#x\n", 3376 scan? "Re-scan" : "Reset", bus, target, (uintmax_t)lun, 3377 ccb.ccb_h.status & CAM_STATUS_MASK); 3378 return(1); 3379 } 3380 } 3381 3382 #ifndef MINIMALISTIC 3383 3384 static struct scsi_nv defect_list_type_map[] = { 3385 { "block", SRDD10_BLOCK_FORMAT }, 3386 { "extbfi", SRDD10_EXT_BFI_FORMAT }, 3387 { "extphys", SRDD10_EXT_PHYS_FORMAT }, 3388 { "longblock", SRDD10_LONG_BLOCK_FORMAT }, 3389 { "bfi", SRDD10_BYTES_FROM_INDEX_FORMAT }, 3390 { "phys", SRDD10_PHYSICAL_SECTOR_FORMAT } 3391 }; 3392 3393 static int 3394 readdefects(struct cam_device *device, int argc, char **argv, 3395 char *combinedopt, int retry_count, int timeout) 3396 { 3397 union ccb *ccb = NULL; 3398 struct scsi_read_defect_data_hdr_10 *hdr10 = NULL; 3399 struct scsi_read_defect_data_hdr_12 *hdr12 = NULL; 3400 size_t hdr_size = 0, entry_size = 0; 3401 int use_12byte = 0; 3402 int hex_format = 0; 3403 u_int8_t *defect_list = NULL; 3404 u_int8_t list_format = 0; 3405 int list_type_set = 0; 3406 u_int32_t dlist_length = 0; 3407 u_int32_t returned_length = 0, valid_len = 0; 3408 u_int32_t num_returned = 0, num_valid = 0; 3409 u_int32_t max_possible_size = 0, hdr_max = 0; 3410 u_int32_t starting_offset = 0; 3411 u_int8_t returned_format, returned_type; 3412 unsigned int i; 3413 int summary = 0, quiet = 0; 3414 int c, error = 0; 3415 int lists_specified = 0; 3416 int get_length = 1, first_pass = 1; 3417 int mads = 0; 3418 3419 while ((c = getopt(argc, argv, combinedopt)) != -1) { 3420 switch(c){ 3421 case 'f': 3422 { 3423 scsi_nv_status status; 3424 int entry_num = 0; 3425 3426 status = scsi_get_nv(defect_list_type_map, 3427 sizeof(defect_list_type_map) / 3428 sizeof(defect_list_type_map[0]), optarg, 3429 &entry_num, SCSI_NV_FLAG_IG_CASE); 3430 3431 if (status == SCSI_NV_FOUND) { 3432 list_format = defect_list_type_map[ 3433 entry_num].value; 3434 list_type_set = 1; 3435 } else { 3436 warnx("%s: %s %s option %s", __func__, 3437 (status == SCSI_NV_AMBIGUOUS) ? 3438 "ambiguous" : "invalid", "defect list type", 3439 optarg); 3440 error = 1; 3441 goto defect_bailout; 3442 } 3443 break; 3444 } 3445 case 'G': 3446 arglist |= CAM_ARG_GLIST; 3447 break; 3448 case 'P': 3449 arglist |= CAM_ARG_PLIST; 3450 break; 3451 case 'q': 3452 quiet = 1; 3453 break; 3454 case 's': 3455 summary = 1; 3456 break; 3457 case 'S': { 3458 char *endptr; 3459 3460 starting_offset = strtoul(optarg, &endptr, 0); 3461 if (*endptr != '\0') { 3462 error = 1; 3463 warnx("invalid starting offset %s", optarg); 3464 goto defect_bailout; 3465 } 3466 break; 3467 } 3468 case 'X': 3469 hex_format = 1; 3470 break; 3471 default: 3472 break; 3473 } 3474 } 3475 3476 if (list_type_set == 0) { 3477 error = 1; 3478 warnx("no defect list format specified"); 3479 goto defect_bailout; 3480 } 3481 3482 if (arglist & CAM_ARG_PLIST) { 3483 list_format |= SRDD10_PLIST; 3484 lists_specified++; 3485 } 3486 3487 if (arglist & CAM_ARG_GLIST) { 3488 list_format |= SRDD10_GLIST; 3489 lists_specified++; 3490 } 3491 3492 /* 3493 * This implies a summary, and was the previous behavior. 3494 */ 3495 if (lists_specified == 0) 3496 summary = 1; 3497 3498 ccb = cam_getccb(device); 3499 3500 retry_12byte: 3501 3502 /* 3503 * We start off asking for just the header to determine how much 3504 * defect data is available. Some Hitachi drives return an error 3505 * if you ask for more data than the drive has. Once we know the 3506 * length, we retry the command with the returned length. 3507 */ 3508 if (use_12byte == 0) 3509 dlist_length = sizeof(*hdr10); 3510 else 3511 dlist_length = sizeof(*hdr12); 3512 3513 retry: 3514 if (defect_list != NULL) { 3515 free(defect_list); 3516 defect_list = NULL; 3517 } 3518 defect_list = malloc(dlist_length); 3519 if (defect_list == NULL) { 3520 warnx("can't malloc memory for defect list"); 3521 error = 1; 3522 goto defect_bailout; 3523 } 3524 3525 next_batch: 3526 bzero(defect_list, dlist_length); 3527 3528 /* 3529 * cam_getccb() zeros the CCB header only. So we need to zero the 3530 * payload portion of the ccb. 3531 */ 3532 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->csio); 3533 3534 scsi_read_defects(&ccb->csio, 3535 /*retries*/ retry_count, 3536 /*cbfcnp*/ NULL, 3537 /*tag_action*/ MSG_SIMPLE_Q_TAG, 3538 /*list_format*/ list_format, 3539 /*addr_desc_index*/ starting_offset, 3540 /*data_ptr*/ defect_list, 3541 /*dxfer_len*/ dlist_length, 3542 /*minimum_cmd_size*/ use_12byte ? 12 : 0, 3543 /*sense_len*/ SSD_FULL_SIZE, 3544 /*timeout*/ timeout ? timeout : 5000); 3545 3546 /* Disable freezing the device queue */ 3547 ccb->ccb_h.flags |= CAM_DEV_QFRZDIS; 3548 3549 if (cam_send_ccb(device, ccb) < 0) { 3550 perror("error reading defect list"); 3551 3552 if (arglist & CAM_ARG_VERBOSE) { 3553 cam_error_print(device, ccb, CAM_ESF_ALL, 3554 CAM_EPF_ALL, stderr); 3555 } 3556 3557 error = 1; 3558 goto defect_bailout; 3559 } 3560 3561 valid_len = ccb->csio.dxfer_len - ccb->csio.resid; 3562 3563 if (use_12byte == 0) { 3564 hdr10 = (struct scsi_read_defect_data_hdr_10 *)defect_list; 3565 hdr_size = sizeof(*hdr10); 3566 hdr_max = SRDDH10_MAX_LENGTH; 3567 3568 if (valid_len >= hdr_size) { 3569 returned_length = scsi_2btoul(hdr10->length); 3570 returned_format = hdr10->format; 3571 } else { 3572 returned_length = 0; 3573 returned_format = 0; 3574 } 3575 } else { 3576 hdr12 = (struct scsi_read_defect_data_hdr_12 *)defect_list; 3577 hdr_size = sizeof(*hdr12); 3578 hdr_max = SRDDH12_MAX_LENGTH; 3579 3580 if (valid_len >= hdr_size) { 3581 returned_length = scsi_4btoul(hdr12->length); 3582 returned_format = hdr12->format; 3583 } else { 3584 returned_length = 0; 3585 returned_format = 0; 3586 } 3587 } 3588 3589 returned_type = returned_format & SRDDH10_DLIST_FORMAT_MASK; 3590 switch (returned_type) { 3591 case SRDD10_BLOCK_FORMAT: 3592 entry_size = sizeof(struct scsi_defect_desc_block); 3593 break; 3594 case SRDD10_LONG_BLOCK_FORMAT: 3595 entry_size = sizeof(struct scsi_defect_desc_long_block); 3596 break; 3597 case SRDD10_EXT_PHYS_FORMAT: 3598 case SRDD10_PHYSICAL_SECTOR_FORMAT: 3599 entry_size = sizeof(struct scsi_defect_desc_phys_sector); 3600 break; 3601 case SRDD10_EXT_BFI_FORMAT: 3602 case SRDD10_BYTES_FROM_INDEX_FORMAT: 3603 entry_size = sizeof(struct scsi_defect_desc_bytes_from_index); 3604 break; 3605 default: 3606 warnx("Unknown defect format 0x%x\n", returned_type); 3607 error = 1; 3608 goto defect_bailout; 3609 break; 3610 } 3611 3612 max_possible_size = (hdr_max / entry_size) * entry_size; 3613 num_returned = returned_length / entry_size; 3614 num_valid = min(returned_length, valid_len - hdr_size); 3615 num_valid /= entry_size; 3616 3617 if (get_length != 0) { 3618 get_length = 0; 3619 3620 if ((ccb->ccb_h.status & CAM_STATUS_MASK) == 3621 CAM_SCSI_STATUS_ERROR) { 3622 struct scsi_sense_data *sense; 3623 int error_code, sense_key, asc, ascq; 3624 3625 sense = &ccb->csio.sense_data; 3626 scsi_extract_sense_len(sense, ccb->csio.sense_len - 3627 ccb->csio.sense_resid, &error_code, &sense_key, 3628 &asc, &ascq, /*show_errors*/ 1); 3629 3630 /* 3631 * If the drive is reporting that it just doesn't 3632 * support the defect list format, go ahead and use 3633 * the length it reported. Otherwise, the length 3634 * may not be valid, so use the maximum. 3635 */ 3636 if ((sense_key == SSD_KEY_RECOVERED_ERROR) 3637 && (asc == 0x1c) && (ascq == 0x00) 3638 && (returned_length > 0)) { 3639 if ((use_12byte == 0) 3640 && (returned_length >= max_possible_size)) { 3641 get_length = 1; 3642 use_12byte = 1; 3643 goto retry_12byte; 3644 } 3645 dlist_length = returned_length + hdr_size; 3646 } else if ((sense_key == SSD_KEY_RECOVERED_ERROR) 3647 && (asc == 0x1f) && (ascq == 0x00) 3648 && (returned_length > 0)) { 3649 /* Partial defect list transfer */ 3650 /* 3651 * Hitachi drives return this error 3652 * along with a partial defect list if they 3653 * have more defects than the 10 byte 3654 * command can support. Retry with the 12 3655 * byte command. 3656 */ 3657 if (use_12byte == 0) { 3658 get_length = 1; 3659 use_12byte = 1; 3660 goto retry_12byte; 3661 } 3662 dlist_length = returned_length + hdr_size; 3663 } else if ((sense_key == SSD_KEY_ILLEGAL_REQUEST) 3664 && (asc == 0x24) && (ascq == 0x00)) { 3665 /* Invalid field in CDB */ 3666 /* 3667 * SBC-3 says that if the drive has more 3668 * defects than can be reported with the 3669 * 10 byte command, it should return this 3670 * error and no data. Retry with the 12 3671 * byte command. 3672 */ 3673 if (use_12byte == 0) { 3674 get_length = 1; 3675 use_12byte = 1; 3676 goto retry_12byte; 3677 } 3678 dlist_length = returned_length + hdr_size; 3679 } else { 3680 /* 3681 * If we got a SCSI error and no valid length, 3682 * just use the 10 byte maximum. The 12 3683 * byte maximum is too large. 3684 */ 3685 if (returned_length == 0) 3686 dlist_length = SRDD10_MAX_LENGTH; 3687 else { 3688 if ((use_12byte == 0) 3689 && (returned_length >= 3690 max_possible_size)) { 3691 get_length = 1; 3692 use_12byte = 1; 3693 goto retry_12byte; 3694 } 3695 dlist_length = returned_length + 3696 hdr_size; 3697 } 3698 } 3699 } else if ((ccb->ccb_h.status & CAM_STATUS_MASK) != 3700 CAM_REQ_CMP){ 3701 error = 1; 3702 warnx("Error reading defect header"); 3703 if (arglist & CAM_ARG_VERBOSE) 3704 cam_error_print(device, ccb, CAM_ESF_ALL, 3705 CAM_EPF_ALL, stderr); 3706 goto defect_bailout; 3707 } else { 3708 if ((use_12byte == 0) 3709 && (returned_length >= max_possible_size)) { 3710 get_length = 1; 3711 use_12byte = 1; 3712 goto retry_12byte; 3713 } 3714 dlist_length = returned_length + hdr_size; 3715 } 3716 if (summary != 0) { 3717 fprintf(stdout, "%u", num_returned); 3718 if (quiet == 0) { 3719 fprintf(stdout, " defect%s", 3720 (num_returned != 1) ? "s" : ""); 3721 } 3722 fprintf(stdout, "\n"); 3723 3724 goto defect_bailout; 3725 } 3726 3727 /* 3728 * We always limit the list length to the 10-byte maximum 3729 * length (0xffff). The reason is that some controllers 3730 * can't handle larger I/Os, and we can transfer the entire 3731 * 10 byte list in one shot. For drives that support the 12 3732 * byte read defects command, we'll step through the list 3733 * by specifying a starting offset. For drives that don't 3734 * support the 12 byte command's starting offset, we'll 3735 * just display the first 64K. 3736 */ 3737 dlist_length = min(dlist_length, SRDD10_MAX_LENGTH); 3738 3739 goto retry; 3740 } 3741 3742 3743 if (((ccb->ccb_h.status & CAM_STATUS_MASK) == CAM_SCSI_STATUS_ERROR) 3744 && (ccb->csio.scsi_status == SCSI_STATUS_CHECK_COND) 3745 && ((ccb->ccb_h.status & CAM_AUTOSNS_VALID) != 0)) { 3746 struct scsi_sense_data *sense; 3747 int error_code, sense_key, asc, ascq; 3748 3749 sense = &ccb->csio.sense_data; 3750 scsi_extract_sense_len(sense, ccb->csio.sense_len - 3751 ccb->csio.sense_resid, &error_code, &sense_key, &asc, 3752 &ascq, /*show_errors*/ 1); 3753 3754 /* 3755 * According to the SCSI spec, if the disk doesn't support 3756 * the requested format, it will generally return a sense 3757 * key of RECOVERED ERROR, and an additional sense code 3758 * of "DEFECT LIST NOT FOUND". HGST drives also return 3759 * Primary/Grown defect list not found errors. So just 3760 * check for an ASC of 0x1c. 3761 */ 3762 if ((sense_key == SSD_KEY_RECOVERED_ERROR) 3763 && (asc == 0x1c)) { 3764 const char *format_str; 3765 3766 format_str = scsi_nv_to_str(defect_list_type_map, 3767 sizeof(defect_list_type_map) / 3768 sizeof(defect_list_type_map[0]), 3769 list_format & SRDD10_DLIST_FORMAT_MASK); 3770 warnx("requested defect format %s not available", 3771 format_str ? format_str : "unknown"); 3772 3773 format_str = scsi_nv_to_str(defect_list_type_map, 3774 sizeof(defect_list_type_map) / 3775 sizeof(defect_list_type_map[0]), returned_type); 3776 if (format_str != NULL) { 3777 warnx("Device returned %s format", 3778 format_str); 3779 } else { 3780 error = 1; 3781 warnx("Device returned unknown defect" 3782 " data format %#x", returned_type); 3783 goto defect_bailout; 3784 } 3785 } else { 3786 error = 1; 3787 warnx("Error returned from read defect data command"); 3788 if (arglist & CAM_ARG_VERBOSE) 3789 cam_error_print(device, ccb, CAM_ESF_ALL, 3790 CAM_EPF_ALL, stderr); 3791 goto defect_bailout; 3792 } 3793 } else if ((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP) { 3794 error = 1; 3795 warnx("Error returned from read defect data command"); 3796 if (arglist & CAM_ARG_VERBOSE) 3797 cam_error_print(device, ccb, CAM_ESF_ALL, 3798 CAM_EPF_ALL, stderr); 3799 goto defect_bailout; 3800 } 3801 3802 if (first_pass != 0) { 3803 fprintf(stderr, "Got %d defect", num_returned); 3804 3805 if ((lists_specified == 0) || (num_returned == 0)) { 3806 fprintf(stderr, "s.\n"); 3807 goto defect_bailout; 3808 } else if (num_returned == 1) 3809 fprintf(stderr, ":\n"); 3810 else 3811 fprintf(stderr, "s:\n"); 3812 3813 first_pass = 0; 3814 } 3815 3816 /* 3817 * XXX KDM I should probably clean up the printout format for the 3818 * disk defects. 3819 */ 3820 switch (returned_type) { 3821 case SRDD10_PHYSICAL_SECTOR_FORMAT: 3822 case SRDD10_EXT_PHYS_FORMAT: 3823 { 3824 struct scsi_defect_desc_phys_sector *dlist; 3825 3826 dlist = (struct scsi_defect_desc_phys_sector *) 3827 (defect_list + hdr_size); 3828 3829 for (i = 0; i < num_valid; i++) { 3830 uint32_t sector; 3831 3832 sector = scsi_4btoul(dlist[i].sector); 3833 if (returned_type == SRDD10_EXT_PHYS_FORMAT) { 3834 mads = (sector & SDD_EXT_PHYS_MADS) ? 3835 0 : 1; 3836 sector &= ~SDD_EXT_PHYS_FLAG_MASK; 3837 } 3838 if (hex_format == 0) 3839 fprintf(stdout, "%d:%d:%d%s", 3840 scsi_3btoul(dlist[i].cylinder), 3841 dlist[i].head, 3842 scsi_4btoul(dlist[i].sector), 3843 mads ? " - " : "\n"); 3844 else 3845 fprintf(stdout, "0x%x:0x%x:0x%x%s", 3846 scsi_3btoul(dlist[i].cylinder), 3847 dlist[i].head, 3848 scsi_4btoul(dlist[i].sector), 3849 mads ? " - " : "\n"); 3850 mads = 0; 3851 } 3852 if (num_valid < num_returned) { 3853 starting_offset += num_valid; 3854 goto next_batch; 3855 } 3856 break; 3857 } 3858 case SRDD10_BYTES_FROM_INDEX_FORMAT: 3859 case SRDD10_EXT_BFI_FORMAT: 3860 { 3861 struct scsi_defect_desc_bytes_from_index *dlist; 3862 3863 dlist = (struct scsi_defect_desc_bytes_from_index *) 3864 (defect_list + hdr_size); 3865 3866 for (i = 0; i < num_valid; i++) { 3867 uint32_t bfi; 3868 3869 bfi = scsi_4btoul(dlist[i].bytes_from_index); 3870 if (returned_type == SRDD10_EXT_BFI_FORMAT) { 3871 mads = (bfi & SDD_EXT_BFI_MADS) ? 1 : 0; 3872 bfi &= ~SDD_EXT_BFI_FLAG_MASK; 3873 } 3874 if (hex_format == 0) 3875 fprintf(stdout, "%d:%d:%d%s", 3876 scsi_3btoul(dlist[i].cylinder), 3877 dlist[i].head, 3878 scsi_4btoul(dlist[i].bytes_from_index), 3879 mads ? " - " : "\n"); 3880 else 3881 fprintf(stdout, "0x%x:0x%x:0x%x%s", 3882 scsi_3btoul(dlist[i].cylinder), 3883 dlist[i].head, 3884 scsi_4btoul(dlist[i].bytes_from_index), 3885 mads ? " - " : "\n"); 3886 3887 mads = 0; 3888 } 3889 if (num_valid < num_returned) { 3890 starting_offset += num_valid; 3891 goto next_batch; 3892 } 3893 break; 3894 } 3895 case SRDDH10_BLOCK_FORMAT: 3896 { 3897 struct scsi_defect_desc_block *dlist; 3898 3899 dlist = (struct scsi_defect_desc_block *) 3900 (defect_list + hdr_size); 3901 3902 for (i = 0; i < num_valid; i++) { 3903 if (hex_format == 0) 3904 fprintf(stdout, "%u\n", 3905 scsi_4btoul(dlist[i].address)); 3906 else 3907 fprintf(stdout, "0x%x\n", 3908 scsi_4btoul(dlist[i].address)); 3909 } 3910 3911 if (num_valid < num_returned) { 3912 starting_offset += num_valid; 3913 goto next_batch; 3914 } 3915 3916 break; 3917 } 3918 case SRDD10_LONG_BLOCK_FORMAT: 3919 { 3920 struct scsi_defect_desc_long_block *dlist; 3921 3922 dlist = (struct scsi_defect_desc_long_block *) 3923 (defect_list + hdr_size); 3924 3925 for (i = 0; i < num_valid; i++) { 3926 if (hex_format == 0) 3927 fprintf(stdout, "%ju\n", 3928 (uintmax_t)scsi_8btou64( 3929 dlist[i].address)); 3930 else 3931 fprintf(stdout, "0x%jx\n", 3932 (uintmax_t)scsi_8btou64( 3933 dlist[i].address)); 3934 } 3935 3936 if (num_valid < num_returned) { 3937 starting_offset += num_valid; 3938 goto next_batch; 3939 } 3940 break; 3941 } 3942 default: 3943 fprintf(stderr, "Unknown defect format 0x%x\n", 3944 returned_type); 3945 error = 1; 3946 break; 3947 } 3948 defect_bailout: 3949 3950 if (defect_list != NULL) 3951 free(defect_list); 3952 3953 if (ccb != NULL) 3954 cam_freeccb(ccb); 3955 3956 return(error); 3957 } 3958 #endif /* MINIMALISTIC */ 3959 3960 #if 0 3961 void 3962 reassignblocks(struct cam_device *device, u_int32_t *blocks, int num_blocks) 3963 { 3964 union ccb *ccb; 3965 3966 ccb = cam_getccb(device); 3967 3968 cam_freeccb(ccb); 3969 } 3970 #endif 3971 3972 #ifndef MINIMALISTIC 3973 void 3974 mode_sense(struct cam_device *device, int mode_page, int page_control, 3975 int dbd, int retry_count, int timeout, u_int8_t *data, int datalen) 3976 { 3977 union ccb *ccb; 3978 int retval; 3979 3980 ccb = cam_getccb(device); 3981 3982 if (ccb == NULL) 3983 errx(1, "mode_sense: couldn't allocate CCB"); 3984 3985 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->csio); 3986 3987 scsi_mode_sense(&ccb->csio, 3988 /* retries */ retry_count, 3989 /* cbfcnp */ NULL, 3990 /* tag_action */ MSG_SIMPLE_Q_TAG, 3991 /* dbd */ dbd, 3992 /* page_code */ page_control << 6, 3993 /* page */ mode_page, 3994 /* param_buf */ data, 3995 /* param_len */ datalen, 3996 /* sense_len */ SSD_FULL_SIZE, 3997 /* timeout */ timeout ? timeout : 5000); 3998 3999 if (arglist & CAM_ARG_ERR_RECOVER) 4000 ccb->ccb_h.flags |= CAM_PASS_ERR_RECOVER; 4001 4002 /* Disable freezing the device queue */ 4003 ccb->ccb_h.flags |= CAM_DEV_QFRZDIS; 4004 4005 if (((retval = cam_send_ccb(device, ccb)) < 0) 4006 || ((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP)) { 4007 if (arglist & CAM_ARG_VERBOSE) { 4008 cam_error_print(device, ccb, CAM_ESF_ALL, 4009 CAM_EPF_ALL, stderr); 4010 } 4011 cam_freeccb(ccb); 4012 cam_close_device(device); 4013 if (retval < 0) 4014 err(1, "error sending mode sense command"); 4015 else 4016 errx(1, "error sending mode sense command"); 4017 } 4018 4019 cam_freeccb(ccb); 4020 } 4021 4022 void 4023 mode_select(struct cam_device *device, int save_pages, int retry_count, 4024 int timeout, u_int8_t *data, int datalen) 4025 { 4026 union ccb *ccb; 4027 int retval; 4028 4029 ccb = cam_getccb(device); 4030 4031 if (ccb == NULL) 4032 errx(1, "mode_select: couldn't allocate CCB"); 4033 4034 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->csio); 4035 4036 scsi_mode_select(&ccb->csio, 4037 /* retries */ retry_count, 4038 /* cbfcnp */ NULL, 4039 /* tag_action */ MSG_SIMPLE_Q_TAG, 4040 /* scsi_page_fmt */ 1, 4041 /* save_pages */ save_pages, 4042 /* param_buf */ data, 4043 /* param_len */ datalen, 4044 /* sense_len */ SSD_FULL_SIZE, 4045 /* timeout */ timeout ? timeout : 5000); 4046 4047 if (arglist & CAM_ARG_ERR_RECOVER) 4048 ccb->ccb_h.flags |= CAM_PASS_ERR_RECOVER; 4049 4050 /* Disable freezing the device queue */ 4051 ccb->ccb_h.flags |= CAM_DEV_QFRZDIS; 4052 4053 if (((retval = cam_send_ccb(device, ccb)) < 0) 4054 || ((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP)) { 4055 if (arglist & CAM_ARG_VERBOSE) { 4056 cam_error_print(device, ccb, CAM_ESF_ALL, 4057 CAM_EPF_ALL, stderr); 4058 } 4059 cam_freeccb(ccb); 4060 cam_close_device(device); 4061 4062 if (retval < 0) 4063 err(1, "error sending mode select command"); 4064 else 4065 errx(1, "error sending mode select command"); 4066 4067 } 4068 4069 cam_freeccb(ccb); 4070 } 4071 4072 void 4073 modepage(struct cam_device *device, int argc, char **argv, char *combinedopt, 4074 int retry_count, int timeout) 4075 { 4076 int c, mode_page = -1, page_control = 0; 4077 int binary = 0, list = 0; 4078 4079 while ((c = getopt(argc, argv, combinedopt)) != -1) { 4080 switch(c) { 4081 case 'b': 4082 binary = 1; 4083 break; 4084 case 'd': 4085 arglist |= CAM_ARG_DBD; 4086 break; 4087 case 'e': 4088 arglist |= CAM_ARG_MODE_EDIT; 4089 break; 4090 case 'l': 4091 list = 1; 4092 break; 4093 case 'm': 4094 mode_page = strtol(optarg, NULL, 0); 4095 if (mode_page < 0) 4096 errx(1, "invalid mode page %d", mode_page); 4097 break; 4098 case 'P': 4099 page_control = strtol(optarg, NULL, 0); 4100 if ((page_control < 0) || (page_control > 3)) 4101 errx(1, "invalid page control field %d", 4102 page_control); 4103 arglist |= CAM_ARG_PAGE_CNTL; 4104 break; 4105 default: 4106 break; 4107 } 4108 } 4109 4110 if (mode_page == -1 && list == 0) 4111 errx(1, "you must specify a mode page!"); 4112 4113 if (list) { 4114 mode_list(device, page_control, arglist & CAM_ARG_DBD, 4115 retry_count, timeout); 4116 } else { 4117 mode_edit(device, mode_page, page_control, 4118 arglist & CAM_ARG_DBD, arglist & CAM_ARG_MODE_EDIT, binary, 4119 retry_count, timeout); 4120 } 4121 } 4122 4123 static int 4124 scsicmd(struct cam_device *device, int argc, char **argv, char *combinedopt, 4125 int retry_count, int timeout) 4126 { 4127 union ccb *ccb; 4128 u_int32_t flags = CAM_DIR_NONE; 4129 u_int8_t *data_ptr = NULL; 4130 u_int8_t cdb[20]; 4131 u_int8_t atacmd[12]; 4132 struct get_hook hook; 4133 int c, data_bytes = 0; 4134 int cdb_len = 0; 4135 int atacmd_len = 0; 4136 int dmacmd = 0; 4137 int fpdmacmd = 0; 4138 int need_res = 0; 4139 char *datastr = NULL, *tstr, *resstr = NULL; 4140 int error = 0; 4141 int fd_data = 0, fd_res = 0; 4142 int retval; 4143 4144 ccb = cam_getccb(device); 4145 4146 if (ccb == NULL) { 4147 warnx("scsicmd: error allocating ccb"); 4148 return(1); 4149 } 4150 4151 CCB_CLEAR_ALL_EXCEPT_HDR(ccb); 4152 4153 while ((c = getopt(argc, argv, combinedopt)) != -1) { 4154 switch(c) { 4155 case 'a': 4156 tstr = optarg; 4157 while (isspace(*tstr) && (*tstr != '\0')) 4158 tstr++; 4159 hook.argc = argc - optind; 4160 hook.argv = argv + optind; 4161 hook.got = 0; 4162 atacmd_len = buff_encode_visit(atacmd, sizeof(atacmd), tstr, 4163 iget, &hook); 4164 /* 4165 * Increment optind by the number of arguments the 4166 * encoding routine processed. After each call to 4167 * getopt(3), optind points to the argument that 4168 * getopt should process _next_. In this case, 4169 * that means it points to the first command string 4170 * argument, if there is one. Once we increment 4171 * this, it should point to either the next command 4172 * line argument, or it should be past the end of 4173 * the list. 4174 */ 4175 optind += hook.got; 4176 break; 4177 case 'c': 4178 tstr = optarg; 4179 while (isspace(*tstr) && (*tstr != '\0')) 4180 tstr++; 4181 hook.argc = argc - optind; 4182 hook.argv = argv + optind; 4183 hook.got = 0; 4184 cdb_len = buff_encode_visit(cdb, sizeof(cdb), tstr, 4185 iget, &hook); 4186 /* 4187 * Increment optind by the number of arguments the 4188 * encoding routine processed. After each call to 4189 * getopt(3), optind points to the argument that 4190 * getopt should process _next_. In this case, 4191 * that means it points to the first command string 4192 * argument, if there is one. Once we increment 4193 * this, it should point to either the next command 4194 * line argument, or it should be past the end of 4195 * the list. 4196 */ 4197 optind += hook.got; 4198 break; 4199 case 'd': 4200 dmacmd = 1; 4201 break; 4202 case 'f': 4203 fpdmacmd = 1; 4204 break; 4205 case 'i': 4206 if (arglist & CAM_ARG_CMD_OUT) { 4207 warnx("command must either be " 4208 "read or write, not both"); 4209 error = 1; 4210 goto scsicmd_bailout; 4211 } 4212 arglist |= CAM_ARG_CMD_IN; 4213 flags = CAM_DIR_IN; 4214 data_bytes = strtol(optarg, NULL, 0); 4215 if (data_bytes <= 0) { 4216 warnx("invalid number of input bytes %d", 4217 data_bytes); 4218 error = 1; 4219 goto scsicmd_bailout; 4220 } 4221 hook.argc = argc - optind; 4222 hook.argv = argv + optind; 4223 hook.got = 0; 4224 optind++; 4225 datastr = cget(&hook, NULL); 4226 /* 4227 * If the user supplied "-" instead of a format, he 4228 * wants the data to be written to stdout. 4229 */ 4230 if ((datastr != NULL) 4231 && (datastr[0] == '-')) 4232 fd_data = 1; 4233 4234 data_ptr = (u_int8_t *)malloc(data_bytes); 4235 if (data_ptr == NULL) { 4236 warnx("can't malloc memory for data_ptr"); 4237 error = 1; 4238 goto scsicmd_bailout; 4239 } 4240 break; 4241 case 'o': 4242 if (arglist & CAM_ARG_CMD_IN) { 4243 warnx("command must either be " 4244 "read or write, not both"); 4245 error = 1; 4246 goto scsicmd_bailout; 4247 } 4248 arglist |= CAM_ARG_CMD_OUT; 4249 flags = CAM_DIR_OUT; 4250 data_bytes = strtol(optarg, NULL, 0); 4251 if (data_bytes <= 0) { 4252 warnx("invalid number of output bytes %d", 4253 data_bytes); 4254 error = 1; 4255 goto scsicmd_bailout; 4256 } 4257 hook.argc = argc - optind; 4258 hook.argv = argv + optind; 4259 hook.got = 0; 4260 datastr = cget(&hook, NULL); 4261 data_ptr = (u_int8_t *)malloc(data_bytes); 4262 if (data_ptr == NULL) { 4263 warnx("can't malloc memory for data_ptr"); 4264 error = 1; 4265 goto scsicmd_bailout; 4266 } 4267 bzero(data_ptr, data_bytes); 4268 /* 4269 * If the user supplied "-" instead of a format, he 4270 * wants the data to be read from stdin. 4271 */ 4272 if ((datastr != NULL) 4273 && (datastr[0] == '-')) 4274 fd_data = 1; 4275 else 4276 buff_encode_visit(data_ptr, data_bytes, datastr, 4277 iget, &hook); 4278 optind += hook.got; 4279 break; 4280 case 'r': 4281 need_res = 1; 4282 hook.argc = argc - optind; 4283 hook.argv = argv + optind; 4284 hook.got = 0; 4285 resstr = cget(&hook, NULL); 4286 if ((resstr != NULL) && (resstr[0] == '-')) 4287 fd_res = 1; 4288 optind += hook.got; 4289 break; 4290 default: 4291 break; 4292 } 4293 } 4294 4295 /* 4296 * If fd_data is set, and we're writing to the device, we need to 4297 * read the data the user wants written from stdin. 4298 */ 4299 if ((fd_data == 1) && (arglist & CAM_ARG_CMD_OUT)) { 4300 ssize_t amt_read; 4301 int amt_to_read = data_bytes; 4302 u_int8_t *buf_ptr = data_ptr; 4303 4304 for (amt_read = 0; amt_to_read > 0; 4305 amt_read = read(STDIN_FILENO, buf_ptr, amt_to_read)) { 4306 if (amt_read == -1) { 4307 warn("error reading data from stdin"); 4308 error = 1; 4309 goto scsicmd_bailout; 4310 } 4311 amt_to_read -= amt_read; 4312 buf_ptr += amt_read; 4313 } 4314 } 4315 4316 if (arglist & CAM_ARG_ERR_RECOVER) 4317 flags |= CAM_PASS_ERR_RECOVER; 4318 4319 /* Disable freezing the device queue */ 4320 flags |= CAM_DEV_QFRZDIS; 4321 4322 if (cdb_len) { 4323 /* 4324 * This is taken from the SCSI-3 draft spec. 4325 * (T10/1157D revision 0.3) 4326 * The top 3 bits of an opcode are the group code. 4327 * The next 5 bits are the command code. 4328 * Group 0: six byte commands 4329 * Group 1: ten byte commands 4330 * Group 2: ten byte commands 4331 * Group 3: reserved 4332 * Group 4: sixteen byte commands 4333 * Group 5: twelve byte commands 4334 * Group 6: vendor specific 4335 * Group 7: vendor specific 4336 */ 4337 switch((cdb[0] >> 5) & 0x7) { 4338 case 0: 4339 cdb_len = 6; 4340 break; 4341 case 1: 4342 case 2: 4343 cdb_len = 10; 4344 break; 4345 case 3: 4346 case 6: 4347 case 7: 4348 /* computed by buff_encode_visit */ 4349 break; 4350 case 4: 4351 cdb_len = 16; 4352 break; 4353 case 5: 4354 cdb_len = 12; 4355 break; 4356 } 4357 4358 /* 4359 * We should probably use csio_build_visit or something like that 4360 * here, but it's easier to encode arguments as you go. The 4361 * alternative would be skipping the CDB argument and then encoding 4362 * it here, since we've got the data buffer argument by now. 4363 */ 4364 bcopy(cdb, &ccb->csio.cdb_io.cdb_bytes, cdb_len); 4365 4366 cam_fill_csio(&ccb->csio, 4367 /*retries*/ retry_count, 4368 /*cbfcnp*/ NULL, 4369 /*flags*/ flags, 4370 /*tag_action*/ MSG_SIMPLE_Q_TAG, 4371 /*data_ptr*/ data_ptr, 4372 /*dxfer_len*/ data_bytes, 4373 /*sense_len*/ SSD_FULL_SIZE, 4374 /*cdb_len*/ cdb_len, 4375 /*timeout*/ timeout ? timeout : 5000); 4376 } else { 4377 atacmd_len = 12; 4378 bcopy(atacmd, &ccb->ataio.cmd.command, atacmd_len); 4379 if (need_res) 4380 ccb->ataio.cmd.flags |= CAM_ATAIO_NEEDRESULT; 4381 if (dmacmd) 4382 ccb->ataio.cmd.flags |= CAM_ATAIO_DMA; 4383 if (fpdmacmd) 4384 ccb->ataio.cmd.flags |= CAM_ATAIO_FPDMA; 4385 4386 cam_fill_ataio(&ccb->ataio, 4387 /*retries*/ retry_count, 4388 /*cbfcnp*/ NULL, 4389 /*flags*/ flags, 4390 /*tag_action*/ 0, 4391 /*data_ptr*/ data_ptr, 4392 /*dxfer_len*/ data_bytes, 4393 /*timeout*/ timeout ? timeout : 5000); 4394 } 4395 4396 if (((retval = cam_send_ccb(device, ccb)) < 0) 4397 || ((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP)) { 4398 const char warnstr[] = "error sending command"; 4399 4400 if (retval < 0) 4401 warn(warnstr); 4402 else 4403 warnx(warnstr); 4404 4405 if (arglist & CAM_ARG_VERBOSE) { 4406 cam_error_print(device, ccb, CAM_ESF_ALL, 4407 CAM_EPF_ALL, stderr); 4408 } 4409 4410 error = 1; 4411 goto scsicmd_bailout; 4412 } 4413 4414 if (atacmd_len && need_res) { 4415 if (fd_res == 0) { 4416 buff_decode_visit(&ccb->ataio.res.status, 11, resstr, 4417 arg_put, NULL); 4418 fprintf(stdout, "\n"); 4419 } else { 4420 fprintf(stdout, 4421 "%02X %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X\n", 4422 ccb->ataio.res.status, 4423 ccb->ataio.res.error, 4424 ccb->ataio.res.lba_low, 4425 ccb->ataio.res.lba_mid, 4426 ccb->ataio.res.lba_high, 4427 ccb->ataio.res.device, 4428 ccb->ataio.res.lba_low_exp, 4429 ccb->ataio.res.lba_mid_exp, 4430 ccb->ataio.res.lba_high_exp, 4431 ccb->ataio.res.sector_count, 4432 ccb->ataio.res.sector_count_exp); 4433 fflush(stdout); 4434 } 4435 } 4436 4437 if (((ccb->ccb_h.status & CAM_STATUS_MASK) == CAM_REQ_CMP) 4438 && (arglist & CAM_ARG_CMD_IN) 4439 && (data_bytes > 0)) { 4440 if (fd_data == 0) { 4441 buff_decode_visit(data_ptr, data_bytes, datastr, 4442 arg_put, NULL); 4443 fprintf(stdout, "\n"); 4444 } else { 4445 ssize_t amt_written; 4446 int amt_to_write = data_bytes; 4447 u_int8_t *buf_ptr = data_ptr; 4448 4449 for (amt_written = 0; (amt_to_write > 0) && 4450 (amt_written =write(1, buf_ptr,amt_to_write))> 0;){ 4451 amt_to_write -= amt_written; 4452 buf_ptr += amt_written; 4453 } 4454 if (amt_written == -1) { 4455 warn("error writing data to stdout"); 4456 error = 1; 4457 goto scsicmd_bailout; 4458 } else if ((amt_written == 0) 4459 && (amt_to_write > 0)) { 4460 warnx("only wrote %u bytes out of %u", 4461 data_bytes - amt_to_write, data_bytes); 4462 } 4463 } 4464 } 4465 4466 scsicmd_bailout: 4467 4468 if ((data_bytes > 0) && (data_ptr != NULL)) 4469 free(data_ptr); 4470 4471 cam_freeccb(ccb); 4472 4473 return(error); 4474 } 4475 4476 static int 4477 camdebug(int argc, char **argv, char *combinedopt) 4478 { 4479 int c, fd; 4480 path_id_t bus = CAM_BUS_WILDCARD; 4481 target_id_t target = CAM_TARGET_WILDCARD; 4482 lun_id_t lun = CAM_LUN_WILDCARD; 4483 char *tstr, *tmpstr = NULL; 4484 union ccb ccb; 4485 int error = 0; 4486 4487 bzero(&ccb, sizeof(union ccb)); 4488 4489 while ((c = getopt(argc, argv, combinedopt)) != -1) { 4490 switch(c) { 4491 case 'I': 4492 arglist |= CAM_ARG_DEBUG_INFO; 4493 ccb.cdbg.flags |= CAM_DEBUG_INFO; 4494 break; 4495 case 'P': 4496 arglist |= CAM_ARG_DEBUG_PERIPH; 4497 ccb.cdbg.flags |= CAM_DEBUG_PERIPH; 4498 break; 4499 case 'S': 4500 arglist |= CAM_ARG_DEBUG_SUBTRACE; 4501 ccb.cdbg.flags |= CAM_DEBUG_SUBTRACE; 4502 break; 4503 case 'T': 4504 arglist |= CAM_ARG_DEBUG_TRACE; 4505 ccb.cdbg.flags |= CAM_DEBUG_TRACE; 4506 break; 4507 case 'X': 4508 arglist |= CAM_ARG_DEBUG_XPT; 4509 ccb.cdbg.flags |= CAM_DEBUG_XPT; 4510 break; 4511 case 'c': 4512 arglist |= CAM_ARG_DEBUG_CDB; 4513 ccb.cdbg.flags |= CAM_DEBUG_CDB; 4514 break; 4515 case 'p': 4516 arglist |= CAM_ARG_DEBUG_PROBE; 4517 ccb.cdbg.flags |= CAM_DEBUG_PROBE; 4518 break; 4519 default: 4520 break; 4521 } 4522 } 4523 4524 if ((fd = open(XPT_DEVICE, O_RDWR)) < 0) { 4525 warnx("error opening transport layer device %s", XPT_DEVICE); 4526 warn("%s", XPT_DEVICE); 4527 return(1); 4528 } 4529 argc -= optind; 4530 argv += optind; 4531 4532 if (argc <= 0) { 4533 warnx("you must specify \"off\", \"all\" or a bus,"); 4534 warnx("bus:target, or bus:target:lun"); 4535 close(fd); 4536 return(1); 4537 } 4538 4539 tstr = *argv; 4540 4541 while (isspace(*tstr) && (*tstr != '\0')) 4542 tstr++; 4543 4544 if (strncmp(tstr, "off", 3) == 0) { 4545 ccb.cdbg.flags = CAM_DEBUG_NONE; 4546 arglist &= ~(CAM_ARG_DEBUG_INFO|CAM_ARG_DEBUG_PERIPH| 4547 CAM_ARG_DEBUG_TRACE|CAM_ARG_DEBUG_SUBTRACE| 4548 CAM_ARG_DEBUG_XPT|CAM_ARG_DEBUG_PROBE); 4549 } else if (strncmp(tstr, "all", 3) != 0) { 4550 tmpstr = (char *)strtok(tstr, ":"); 4551 if ((tmpstr != NULL) && (*tmpstr != '\0')){ 4552 bus = strtol(tmpstr, NULL, 0); 4553 arglist |= CAM_ARG_BUS; 4554 tmpstr = (char *)strtok(NULL, ":"); 4555 if ((tmpstr != NULL) && (*tmpstr != '\0')){ 4556 target = strtol(tmpstr, NULL, 0); 4557 arglist |= CAM_ARG_TARGET; 4558 tmpstr = (char *)strtok(NULL, ":"); 4559 if ((tmpstr != NULL) && (*tmpstr != '\0')){ 4560 lun = strtol(tmpstr, NULL, 0); 4561 arglist |= CAM_ARG_LUN; 4562 } 4563 } 4564 } else { 4565 error = 1; 4566 warnx("you must specify \"all\", \"off\", or a bus,"); 4567 warnx("bus:target, or bus:target:lun to debug"); 4568 } 4569 } 4570 4571 if (error == 0) { 4572 4573 ccb.ccb_h.func_code = XPT_DEBUG; 4574 ccb.ccb_h.path_id = bus; 4575 ccb.ccb_h.target_id = target; 4576 ccb.ccb_h.target_lun = lun; 4577 4578 if (ioctl(fd, CAMIOCOMMAND, &ccb) == -1) { 4579 warn("CAMIOCOMMAND ioctl failed"); 4580 error = 1; 4581 } 4582 4583 if (error == 0) { 4584 if ((ccb.ccb_h.status & CAM_STATUS_MASK) == 4585 CAM_FUNC_NOTAVAIL) { 4586 warnx("CAM debugging not available"); 4587 warnx("you need to put options CAMDEBUG in" 4588 " your kernel config file!"); 4589 error = 1; 4590 } else if ((ccb.ccb_h.status & CAM_STATUS_MASK) != 4591 CAM_REQ_CMP) { 4592 warnx("XPT_DEBUG CCB failed with status %#x", 4593 ccb.ccb_h.status); 4594 error = 1; 4595 } else { 4596 if (ccb.cdbg.flags == CAM_DEBUG_NONE) { 4597 fprintf(stderr, 4598 "Debugging turned off\n"); 4599 } else { 4600 fprintf(stderr, 4601 "Debugging enabled for " 4602 "%d:%d:%jx\n", 4603 bus, target, (uintmax_t)lun); 4604 } 4605 } 4606 } 4607 close(fd); 4608 } 4609 4610 return(error); 4611 } 4612 4613 static int 4614 tagcontrol(struct cam_device *device, int argc, char **argv, 4615 char *combinedopt) 4616 { 4617 int c; 4618 union ccb *ccb; 4619 int numtags = -1; 4620 int retval = 0; 4621 int quiet = 0; 4622 char pathstr[1024]; 4623 4624 ccb = cam_getccb(device); 4625 4626 if (ccb == NULL) { 4627 warnx("tagcontrol: error allocating ccb"); 4628 return(1); 4629 } 4630 4631 while ((c = getopt(argc, argv, combinedopt)) != -1) { 4632 switch(c) { 4633 case 'N': 4634 numtags = strtol(optarg, NULL, 0); 4635 if (numtags < 0) { 4636 warnx("tag count %d is < 0", numtags); 4637 retval = 1; 4638 goto tagcontrol_bailout; 4639 } 4640 break; 4641 case 'q': 4642 quiet++; 4643 break; 4644 default: 4645 break; 4646 } 4647 } 4648 4649 cam_path_string(device, pathstr, sizeof(pathstr)); 4650 4651 if (numtags >= 0) { 4652 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->crs); 4653 ccb->ccb_h.func_code = XPT_REL_SIMQ; 4654 ccb->ccb_h.flags = CAM_DEV_QFREEZE; 4655 ccb->crs.release_flags = RELSIM_ADJUST_OPENINGS; 4656 ccb->crs.openings = numtags; 4657 4658 4659 if (cam_send_ccb(device, ccb) < 0) { 4660 perror("error sending XPT_REL_SIMQ CCB"); 4661 retval = 1; 4662 goto tagcontrol_bailout; 4663 } 4664 4665 if ((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP) { 4666 warnx("XPT_REL_SIMQ CCB failed"); 4667 cam_error_print(device, ccb, CAM_ESF_ALL, 4668 CAM_EPF_ALL, stderr); 4669 retval = 1; 4670 goto tagcontrol_bailout; 4671 } 4672 4673 4674 if (quiet == 0) 4675 fprintf(stdout, "%stagged openings now %d\n", 4676 pathstr, ccb->crs.openings); 4677 } 4678 4679 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->cgds); 4680 4681 ccb->ccb_h.func_code = XPT_GDEV_STATS; 4682 4683 if (cam_send_ccb(device, ccb) < 0) { 4684 perror("error sending XPT_GDEV_STATS CCB"); 4685 retval = 1; 4686 goto tagcontrol_bailout; 4687 } 4688 4689 if ((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP) { 4690 warnx("XPT_GDEV_STATS CCB failed"); 4691 cam_error_print(device, ccb, CAM_ESF_ALL, 4692 CAM_EPF_ALL, stderr); 4693 retval = 1; 4694 goto tagcontrol_bailout; 4695 } 4696 4697 if (arglist & CAM_ARG_VERBOSE) { 4698 fprintf(stdout, "%s", pathstr); 4699 fprintf(stdout, "dev_openings %d\n", ccb->cgds.dev_openings); 4700 fprintf(stdout, "%s", pathstr); 4701 fprintf(stdout, "dev_active %d\n", ccb->cgds.dev_active); 4702 fprintf(stdout, "%s", pathstr); 4703 fprintf(stdout, "allocated %d\n", ccb->cgds.allocated); 4704 fprintf(stdout, "%s", pathstr); 4705 fprintf(stdout, "queued %d\n", ccb->cgds.queued); 4706 fprintf(stdout, "%s", pathstr); 4707 fprintf(stdout, "held %d\n", ccb->cgds.held); 4708 fprintf(stdout, "%s", pathstr); 4709 fprintf(stdout, "mintags %d\n", ccb->cgds.mintags); 4710 fprintf(stdout, "%s", pathstr); 4711 fprintf(stdout, "maxtags %d\n", ccb->cgds.maxtags); 4712 } else { 4713 if (quiet == 0) { 4714 fprintf(stdout, "%s", pathstr); 4715 fprintf(stdout, "device openings: "); 4716 } 4717 fprintf(stdout, "%d\n", ccb->cgds.dev_openings + 4718 ccb->cgds.dev_active); 4719 } 4720 4721 tagcontrol_bailout: 4722 4723 cam_freeccb(ccb); 4724 return(retval); 4725 } 4726 4727 static void 4728 cts_print(struct cam_device *device, struct ccb_trans_settings *cts) 4729 { 4730 char pathstr[1024]; 4731 4732 cam_path_string(device, pathstr, sizeof(pathstr)); 4733 4734 if (cts->transport == XPORT_SPI) { 4735 struct ccb_trans_settings_spi *spi = 4736 &cts->xport_specific.spi; 4737 4738 if ((spi->valid & CTS_SPI_VALID_SYNC_RATE) != 0) { 4739 4740 fprintf(stdout, "%ssync parameter: %d\n", pathstr, 4741 spi->sync_period); 4742 4743 if (spi->sync_offset != 0) { 4744 u_int freq; 4745 4746 freq = scsi_calc_syncsrate(spi->sync_period); 4747 fprintf(stdout, "%sfrequency: %d.%03dMHz\n", 4748 pathstr, freq / 1000, freq % 1000); 4749 } 4750 } 4751 4752 if (spi->valid & CTS_SPI_VALID_SYNC_OFFSET) { 4753 fprintf(stdout, "%soffset: %d\n", pathstr, 4754 spi->sync_offset); 4755 } 4756 4757 if (spi->valid & CTS_SPI_VALID_BUS_WIDTH) { 4758 fprintf(stdout, "%sbus width: %d bits\n", pathstr, 4759 (0x01 << spi->bus_width) * 8); 4760 } 4761 4762 if (spi->valid & CTS_SPI_VALID_DISC) { 4763 fprintf(stdout, "%sdisconnection is %s\n", pathstr, 4764 (spi->flags & CTS_SPI_FLAGS_DISC_ENB) ? 4765 "enabled" : "disabled"); 4766 } 4767 } 4768 if (cts->transport == XPORT_FC) { 4769 struct ccb_trans_settings_fc *fc = 4770 &cts->xport_specific.fc; 4771 4772 if (fc->valid & CTS_FC_VALID_WWNN) 4773 fprintf(stdout, "%sWWNN: 0x%llx\n", pathstr, 4774 (long long) fc->wwnn); 4775 if (fc->valid & CTS_FC_VALID_WWPN) 4776 fprintf(stdout, "%sWWPN: 0x%llx\n", pathstr, 4777 (long long) fc->wwpn); 4778 if (fc->valid & CTS_FC_VALID_PORT) 4779 fprintf(stdout, "%sPortID: 0x%x\n", pathstr, fc->port); 4780 if (fc->valid & CTS_FC_VALID_SPEED) 4781 fprintf(stdout, "%stransfer speed: %d.%03dMB/s\n", 4782 pathstr, fc->bitrate / 1000, fc->bitrate % 1000); 4783 } 4784 if (cts->transport == XPORT_SAS) { 4785 struct ccb_trans_settings_sas *sas = 4786 &cts->xport_specific.sas; 4787 4788 if (sas->valid & CTS_SAS_VALID_SPEED) 4789 fprintf(stdout, "%stransfer speed: %d.%03dMB/s\n", 4790 pathstr, sas->bitrate / 1000, sas->bitrate % 1000); 4791 } 4792 if (cts->transport == XPORT_ATA) { 4793 struct ccb_trans_settings_pata *pata = 4794 &cts->xport_specific.ata; 4795 4796 if ((pata->valid & CTS_ATA_VALID_MODE) != 0) { 4797 fprintf(stdout, "%sATA mode: %s\n", pathstr, 4798 ata_mode2string(pata->mode)); 4799 } 4800 if ((pata->valid & CTS_ATA_VALID_ATAPI) != 0) { 4801 fprintf(stdout, "%sATAPI packet length: %d\n", pathstr, 4802 pata->atapi); 4803 } 4804 if ((pata->valid & CTS_ATA_VALID_BYTECOUNT) != 0) { 4805 fprintf(stdout, "%sPIO transaction length: %d\n", 4806 pathstr, pata->bytecount); 4807 } 4808 } 4809 if (cts->transport == XPORT_SATA) { 4810 struct ccb_trans_settings_sata *sata = 4811 &cts->xport_specific.sata; 4812 4813 if ((sata->valid & CTS_SATA_VALID_REVISION) != 0) { 4814 fprintf(stdout, "%sSATA revision: %d.x\n", pathstr, 4815 sata->revision); 4816 } 4817 if ((sata->valid & CTS_SATA_VALID_MODE) != 0) { 4818 fprintf(stdout, "%sATA mode: %s\n", pathstr, 4819 ata_mode2string(sata->mode)); 4820 } 4821 if ((sata->valid & CTS_SATA_VALID_ATAPI) != 0) { 4822 fprintf(stdout, "%sATAPI packet length: %d\n", pathstr, 4823 sata->atapi); 4824 } 4825 if ((sata->valid & CTS_SATA_VALID_BYTECOUNT) != 0) { 4826 fprintf(stdout, "%sPIO transaction length: %d\n", 4827 pathstr, sata->bytecount); 4828 } 4829 if ((sata->valid & CTS_SATA_VALID_PM) != 0) { 4830 fprintf(stdout, "%sPMP presence: %d\n", pathstr, 4831 sata->pm_present); 4832 } 4833 if ((sata->valid & CTS_SATA_VALID_TAGS) != 0) { 4834 fprintf(stdout, "%sNumber of tags: %d\n", pathstr, 4835 sata->tags); 4836 } 4837 if ((sata->valid & CTS_SATA_VALID_CAPS) != 0) { 4838 fprintf(stdout, "%sSATA capabilities: %08x\n", pathstr, 4839 sata->caps); 4840 } 4841 } 4842 if (cts->protocol == PROTO_ATA) { 4843 struct ccb_trans_settings_ata *ata= 4844 &cts->proto_specific.ata; 4845 4846 if (ata->valid & CTS_ATA_VALID_TQ) { 4847 fprintf(stdout, "%stagged queueing: %s\n", pathstr, 4848 (ata->flags & CTS_ATA_FLAGS_TAG_ENB) ? 4849 "enabled" : "disabled"); 4850 } 4851 } 4852 if (cts->protocol == PROTO_SCSI) { 4853 struct ccb_trans_settings_scsi *scsi= 4854 &cts->proto_specific.scsi; 4855 4856 if (scsi->valid & CTS_SCSI_VALID_TQ) { 4857 fprintf(stdout, "%stagged queueing: %s\n", pathstr, 4858 (scsi->flags & CTS_SCSI_FLAGS_TAG_ENB) ? 4859 "enabled" : "disabled"); 4860 } 4861 } 4862 4863 } 4864 4865 /* 4866 * Get a path inquiry CCB for the specified device. 4867 */ 4868 static int 4869 get_cpi(struct cam_device *device, struct ccb_pathinq *cpi) 4870 { 4871 union ccb *ccb; 4872 int retval = 0; 4873 4874 ccb = cam_getccb(device); 4875 if (ccb == NULL) { 4876 warnx("get_cpi: couldn't allocate CCB"); 4877 return(1); 4878 } 4879 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->cpi); 4880 ccb->ccb_h.func_code = XPT_PATH_INQ; 4881 if (cam_send_ccb(device, ccb) < 0) { 4882 warn("get_cpi: error sending Path Inquiry CCB"); 4883 if (arglist & CAM_ARG_VERBOSE) 4884 cam_error_print(device, ccb, CAM_ESF_ALL, 4885 CAM_EPF_ALL, stderr); 4886 retval = 1; 4887 goto get_cpi_bailout; 4888 } 4889 if ((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP) { 4890 if (arglist & CAM_ARG_VERBOSE) 4891 cam_error_print(device, ccb, CAM_ESF_ALL, 4892 CAM_EPF_ALL, stderr); 4893 retval = 1; 4894 goto get_cpi_bailout; 4895 } 4896 bcopy(&ccb->cpi, cpi, sizeof(struct ccb_pathinq)); 4897 4898 get_cpi_bailout: 4899 cam_freeccb(ccb); 4900 return(retval); 4901 } 4902 4903 /* 4904 * Get a get device CCB for the specified device. 4905 */ 4906 static int 4907 get_cgd(struct cam_device *device, struct ccb_getdev *cgd) 4908 { 4909 union ccb *ccb; 4910 int retval = 0; 4911 4912 ccb = cam_getccb(device); 4913 if (ccb == NULL) { 4914 warnx("get_cgd: couldn't allocate CCB"); 4915 return(1); 4916 } 4917 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->cgd); 4918 ccb->ccb_h.func_code = XPT_GDEV_TYPE; 4919 if (cam_send_ccb(device, ccb) < 0) { 4920 warn("get_cgd: error sending Path Inquiry CCB"); 4921 if (arglist & CAM_ARG_VERBOSE) 4922 cam_error_print(device, ccb, CAM_ESF_ALL, 4923 CAM_EPF_ALL, stderr); 4924 retval = 1; 4925 goto get_cgd_bailout; 4926 } 4927 if ((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP) { 4928 if (arglist & CAM_ARG_VERBOSE) 4929 cam_error_print(device, ccb, CAM_ESF_ALL, 4930 CAM_EPF_ALL, stderr); 4931 retval = 1; 4932 goto get_cgd_bailout; 4933 } 4934 bcopy(&ccb->cgd, cgd, sizeof(struct ccb_getdev)); 4935 4936 get_cgd_bailout: 4937 cam_freeccb(ccb); 4938 return(retval); 4939 } 4940 4941 /* 4942 * Returns 1 if the device has the VPD page, 0 if it does not, and -1 on an 4943 * error. 4944 */ 4945 int 4946 dev_has_vpd_page(struct cam_device *dev, uint8_t page_id, int retry_count, 4947 int timeout, int verbosemode) 4948 { 4949 union ccb *ccb = NULL; 4950 struct scsi_vpd_supported_page_list sup_pages; 4951 int i; 4952 int retval = 0; 4953 4954 ccb = cam_getccb(dev); 4955 if (ccb == NULL) { 4956 warn("Unable to allocate CCB"); 4957 retval = -1; 4958 goto bailout; 4959 } 4960 4961 /* cam_getccb cleans up the header, caller has to zero the payload */ 4962 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->csio); 4963 4964 bzero(&sup_pages, sizeof(sup_pages)); 4965 4966 scsi_inquiry(&ccb->csio, 4967 /*retries*/ retry_count, 4968 /*cbfcnp*/ NULL, 4969 /* tag_action */ MSG_SIMPLE_Q_TAG, 4970 /* inq_buf */ (u_int8_t *)&sup_pages, 4971 /* inq_len */ sizeof(sup_pages), 4972 /* evpd */ 1, 4973 /* page_code */ SVPD_SUPPORTED_PAGE_LIST, 4974 /* sense_len */ SSD_FULL_SIZE, 4975 /* timeout */ timeout ? timeout : 5000); 4976 4977 /* Disable freezing the device queue */ 4978 ccb->ccb_h.flags |= CAM_DEV_QFRZDIS; 4979 4980 if (retry_count != 0) 4981 ccb->ccb_h.flags |= CAM_PASS_ERR_RECOVER; 4982 4983 if (cam_send_ccb(dev, ccb) < 0) { 4984 cam_freeccb(ccb); 4985 ccb = NULL; 4986 retval = -1; 4987 goto bailout; 4988 } 4989 4990 if ((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP) { 4991 if (verbosemode != 0) 4992 cam_error_print(dev, ccb, CAM_ESF_ALL, 4993 CAM_EPF_ALL, stderr); 4994 retval = -1; 4995 goto bailout; 4996 } 4997 4998 for (i = 0; i < sup_pages.length; i++) { 4999 if (sup_pages.list[i] == page_id) { 5000 retval = 1; 5001 goto bailout; 5002 } 5003 } 5004 bailout: 5005 if (ccb != NULL) 5006 cam_freeccb(ccb); 5007 5008 return (retval); 5009 } 5010 5011 /* 5012 * devtype is filled in with the type of device. 5013 * Returns 0 for success, non-zero for failure. 5014 */ 5015 int 5016 get_device_type(struct cam_device *dev, int retry_count, int timeout, 5017 int verbosemode, camcontrol_devtype *devtype) 5018 { 5019 struct ccb_getdev cgd; 5020 int retval = 0; 5021 5022 retval = get_cgd(dev, &cgd); 5023 if (retval != 0) 5024 goto bailout; 5025 5026 switch (cgd.protocol) { 5027 case PROTO_SCSI: 5028 break; 5029 case PROTO_ATA: 5030 case PROTO_ATAPI: 5031 case PROTO_SATAPM: 5032 *devtype = CC_DT_ATA; 5033 goto bailout; 5034 break; /*NOTREACHED*/ 5035 default: 5036 *devtype = CC_DT_UNKNOWN; 5037 goto bailout; 5038 break; /*NOTREACHED*/ 5039 } 5040 5041 /* 5042 * Check for the ATA Information VPD page (0x89). If this is an 5043 * ATA device behind a SCSI to ATA translation layer, this VPD page 5044 * should be present. 5045 * 5046 * If that VPD page isn't present, or we get an error back from the 5047 * INQUIRY command, we'll just treat it as a normal SCSI device. 5048 */ 5049 retval = dev_has_vpd_page(dev, SVPD_ATA_INFORMATION, retry_count, 5050 timeout, verbosemode); 5051 if (retval == 1) 5052 *devtype = CC_DT_ATA_BEHIND_SCSI; 5053 else 5054 *devtype = CC_DT_SCSI; 5055 5056 retval = 0; 5057 5058 bailout: 5059 return (retval); 5060 } 5061 5062 int 5063 build_ata_cmd(union ccb *ccb, uint32_t retry_count, uint32_t flags, 5064 uint8_t tag_action, uint8_t protocol, uint8_t ata_flags, uint16_t features, 5065 uint16_t sector_count, uint64_t lba, uint8_t command, uint32_t auxiliary, 5066 uint8_t *data_ptr, uint32_t dxfer_len, uint8_t *cdb_storage, 5067 size_t cdb_storage_len, uint8_t sense_len, uint32_t timeout, 5068 int is48bit, camcontrol_devtype devtype) 5069 { 5070 int retval = 0; 5071 5072 if (devtype == CC_DT_ATA) { 5073 cam_fill_ataio(&ccb->ataio, 5074 /*retries*/ retry_count, 5075 /*cbfcnp*/ NULL, 5076 /*flags*/ flags, 5077 /*tag_action*/ tag_action, 5078 /*data_ptr*/ data_ptr, 5079 /*dxfer_len*/ dxfer_len, 5080 /*timeout*/ timeout); 5081 if (is48bit || lba > ATA_MAX_28BIT_LBA) 5082 ata_48bit_cmd(&ccb->ataio, command, features, lba, 5083 sector_count); 5084 else 5085 ata_28bit_cmd(&ccb->ataio, command, features, lba, 5086 sector_count); 5087 5088 if (auxiliary != 0) { 5089 ccb->ataio.ata_flags |= ATA_FLAG_AUX; 5090 ccb->ataio.aux = auxiliary; 5091 } 5092 5093 if (ata_flags & AP_FLAG_CHK_COND) 5094 ccb->ataio.cmd.flags |= CAM_ATAIO_NEEDRESULT; 5095 5096 if ((protocol & AP_PROTO_MASK) == AP_PROTO_DMA) 5097 ccb->ataio.cmd.flags |= CAM_ATAIO_DMA; 5098 else if ((protocol & AP_PROTO_MASK) == AP_PROTO_FPDMA) 5099 ccb->ataio.cmd.flags |= CAM_ATAIO_FPDMA; 5100 } else { 5101 if (is48bit || lba > ATA_MAX_28BIT_LBA) 5102 protocol |= AP_EXTEND; 5103 5104 retval = scsi_ata_pass(&ccb->csio, 5105 /*retries*/ retry_count, 5106 /*cbfcnp*/ NULL, 5107 /*flags*/ flags, 5108 /*tag_action*/ tag_action, 5109 /*protocol*/ protocol, 5110 /*ata_flags*/ ata_flags, 5111 /*features*/ features, 5112 /*sector_count*/ sector_count, 5113 /*lba*/ lba, 5114 /*command*/ command, 5115 /*device*/ 0, 5116 /*icc*/ 0, 5117 /*auxiliary*/ auxiliary, 5118 /*control*/ 0, 5119 /*data_ptr*/ data_ptr, 5120 /*dxfer_len*/ dxfer_len, 5121 /*cdb_storage*/ cdb_storage, 5122 /*cdb_storage_len*/ cdb_storage_len, 5123 /*minimum_cmd_size*/ 0, 5124 /*sense_len*/ sense_len, 5125 /*timeout*/ timeout); 5126 } 5127 5128 return (retval); 5129 } 5130 5131 int 5132 get_ata_status(struct cam_device *dev, union ccb *ccb, uint8_t *error, 5133 uint16_t *count, uint64_t *lba, uint8_t *device, uint8_t *status) 5134 { 5135 int retval = 0; 5136 5137 switch (ccb->ccb_h.func_code) { 5138 case XPT_SCSI_IO: { 5139 uint8_t opcode; 5140 int error_code = 0, sense_key = 0, asc = 0, ascq = 0; 5141 5142 /* 5143 * In this case, we have SCSI ATA PASS-THROUGH command, 12 5144 * or 16 byte, and need to see what 5145 */ 5146 if (ccb->ccb_h.flags & CAM_CDB_POINTER) 5147 opcode = ccb->csio.cdb_io.cdb_ptr[0]; 5148 else 5149 opcode = ccb->csio.cdb_io.cdb_bytes[0]; 5150 if ((opcode != ATA_PASS_12) 5151 && (opcode != ATA_PASS_16)) { 5152 retval = 1; 5153 warnx("%s: unsupported opcode %02x", __func__, opcode); 5154 goto bailout; 5155 } 5156 5157 retval = scsi_extract_sense_ccb(ccb, &error_code, &sense_key, 5158 &asc, &ascq); 5159 /* Note: the _ccb() variant returns 0 for an error */ 5160 if (retval == 0) { 5161 retval = 1; 5162 goto bailout; 5163 } else 5164 retval = 0; 5165 5166 switch (error_code) { 5167 case SSD_DESC_CURRENT_ERROR: 5168 case SSD_DESC_DEFERRED_ERROR: { 5169 struct scsi_sense_data_desc *sense; 5170 struct scsi_sense_ata_ret_desc *desc; 5171 uint8_t *desc_ptr; 5172 5173 sense = (struct scsi_sense_data_desc *) 5174 &ccb->csio.sense_data; 5175 5176 desc_ptr = scsi_find_desc(sense, ccb->csio.sense_len - 5177 ccb->csio.sense_resid, SSD_DESC_ATA); 5178 if (desc_ptr == NULL) { 5179 cam_error_print(dev, ccb, CAM_ESF_ALL, 5180 CAM_EPF_ALL, stderr); 5181 retval = 1; 5182 goto bailout; 5183 } 5184 desc = (struct scsi_sense_ata_ret_desc *)desc_ptr; 5185 5186 *error = desc->error; 5187 *count = (desc->count_15_8 << 8) | 5188 desc->count_7_0; 5189 *lba = ((uint64_t)desc->lba_47_40 << 40) | 5190 ((uint64_t)desc->lba_39_32 << 32) | 5191 ((uint64_t)desc->lba_31_24 << 24) | 5192 (desc->lba_23_16 << 16) | 5193 (desc->lba_15_8 << 8) | 5194 desc->lba_7_0; 5195 *device = desc->device; 5196 *status = desc->status; 5197 5198 /* 5199 * If the extend bit isn't set, the result is for a 5200 * 12-byte ATA PASS-THROUGH command or a 16 or 32 byte 5201 * command without the extend bit set. This means 5202 * that the device is supposed to return 28-bit 5203 * status. The count field is only 8 bits, and the 5204 * LBA field is only 8 bits. 5205 */ 5206 if ((desc->flags & SSD_DESC_ATA_FLAG_EXTEND) == 0){ 5207 *count &= 0xff; 5208 *lba &= 0x0fffffff; 5209 } 5210 break; 5211 } 5212 case SSD_CURRENT_ERROR: 5213 case SSD_DEFERRED_ERROR: { 5214 #if 0 5215 struct scsi_sense_data_fixed *sense; 5216 #endif 5217 /* 5218 * XXX KDM need to support fixed sense data. 5219 */ 5220 warnx("%s: Fixed sense data not supported yet", 5221 __func__); 5222 retval = 1; 5223 goto bailout; 5224 break; /*NOTREACHED*/ 5225 } 5226 default: 5227 retval = 1; 5228 goto bailout; 5229 break; 5230 } 5231 5232 break; 5233 } 5234 case XPT_ATA_IO: { 5235 struct ata_res *res; 5236 5237 /* 5238 * In this case, we have an ATA command, and we need to 5239 * fill in the requested values from the result register 5240 * set. 5241 */ 5242 res = &ccb->ataio.res; 5243 *error = res->error; 5244 *status = res->status; 5245 *device = res->device; 5246 *count = res->sector_count; 5247 *lba = (res->lba_high << 16) | 5248 (res->lba_mid << 8) | 5249 (res->lba_low); 5250 if (res->flags & CAM_ATAIO_48BIT) { 5251 *count |= (res->sector_count_exp << 8); 5252 *lba |= ((uint64_t)res->lba_low_exp << 24) | 5253 ((uint64_t)res->lba_mid_exp << 32) | 5254 ((uint64_t)res->lba_high_exp << 40); 5255 } else { 5256 *lba |= (res->device & 0xf) << 24; 5257 } 5258 break; 5259 } 5260 default: 5261 retval = 1; 5262 break; 5263 } 5264 bailout: 5265 return (retval); 5266 } 5267 5268 static void 5269 cpi_print(struct ccb_pathinq *cpi) 5270 { 5271 char adapter_str[1024]; 5272 int i; 5273 5274 snprintf(adapter_str, sizeof(adapter_str), 5275 "%s%d:", cpi->dev_name, cpi->unit_number); 5276 5277 fprintf(stdout, "%s SIM/HBA version: %d\n", adapter_str, 5278 cpi->version_num); 5279 5280 for (i = 1; i < 0xff; i = i << 1) { 5281 const char *str; 5282 5283 if ((i & cpi->hba_inquiry) == 0) 5284 continue; 5285 5286 fprintf(stdout, "%s supports ", adapter_str); 5287 5288 switch(i) { 5289 case PI_MDP_ABLE: 5290 str = "MDP message"; 5291 break; 5292 case PI_WIDE_32: 5293 str = "32 bit wide SCSI"; 5294 break; 5295 case PI_WIDE_16: 5296 str = "16 bit wide SCSI"; 5297 break; 5298 case PI_SDTR_ABLE: 5299 str = "SDTR message"; 5300 break; 5301 case PI_LINKED_CDB: 5302 str = "linked CDBs"; 5303 break; 5304 case PI_TAG_ABLE: 5305 str = "tag queue messages"; 5306 break; 5307 case PI_SOFT_RST: 5308 str = "soft reset alternative"; 5309 break; 5310 case PI_SATAPM: 5311 str = "SATA Port Multiplier"; 5312 break; 5313 default: 5314 str = "unknown PI bit set"; 5315 break; 5316 } 5317 fprintf(stdout, "%s\n", str); 5318 } 5319 5320 for (i = 1; i < 0xff; i = i << 1) { 5321 const char *str; 5322 5323 if ((i & cpi->hba_misc) == 0) 5324 continue; 5325 5326 fprintf(stdout, "%s ", adapter_str); 5327 5328 switch(i) { 5329 case PIM_SCANHILO: 5330 str = "bus scans from high ID to low ID"; 5331 break; 5332 case PIM_NOREMOVE: 5333 str = "removable devices not included in scan"; 5334 break; 5335 case PIM_NOINITIATOR: 5336 str = "initiator role not supported"; 5337 break; 5338 case PIM_NOBUSRESET: 5339 str = "user has disabled initial BUS RESET or" 5340 " controller is in target/mixed mode"; 5341 break; 5342 case PIM_NO_6_BYTE: 5343 str = "do not send 6-byte commands"; 5344 break; 5345 case PIM_SEQSCAN: 5346 str = "scan bus sequentially"; 5347 break; 5348 default: 5349 str = "unknown PIM bit set"; 5350 break; 5351 } 5352 fprintf(stdout, "%s\n", str); 5353 } 5354 5355 for (i = 1; i < 0xff; i = i << 1) { 5356 const char *str; 5357 5358 if ((i & cpi->target_sprt) == 0) 5359 continue; 5360 5361 fprintf(stdout, "%s supports ", adapter_str); 5362 switch(i) { 5363 case PIT_PROCESSOR: 5364 str = "target mode processor mode"; 5365 break; 5366 case PIT_PHASE: 5367 str = "target mode phase cog. mode"; 5368 break; 5369 case PIT_DISCONNECT: 5370 str = "disconnects in target mode"; 5371 break; 5372 case PIT_TERM_IO: 5373 str = "terminate I/O message in target mode"; 5374 break; 5375 case PIT_GRP_6: 5376 str = "group 6 commands in target mode"; 5377 break; 5378 case PIT_GRP_7: 5379 str = "group 7 commands in target mode"; 5380 break; 5381 default: 5382 str = "unknown PIT bit set"; 5383 break; 5384 } 5385 5386 fprintf(stdout, "%s\n", str); 5387 } 5388 fprintf(stdout, "%s HBA engine count: %d\n", adapter_str, 5389 cpi->hba_eng_cnt); 5390 fprintf(stdout, "%s maximum target: %d\n", adapter_str, 5391 cpi->max_target); 5392 fprintf(stdout, "%s maximum LUN: %d\n", adapter_str, 5393 cpi->max_lun); 5394 fprintf(stdout, "%s highest path ID in subsystem: %d\n", 5395 adapter_str, cpi->hpath_id); 5396 fprintf(stdout, "%s initiator ID: %d\n", adapter_str, 5397 cpi->initiator_id); 5398 fprintf(stdout, "%s SIM vendor: %s\n", adapter_str, cpi->sim_vid); 5399 fprintf(stdout, "%s HBA vendor: %s\n", adapter_str, cpi->hba_vid); 5400 fprintf(stdout, "%s HBA vendor ID: 0x%04x\n", 5401 adapter_str, cpi->hba_vendor); 5402 fprintf(stdout, "%s HBA device ID: 0x%04x\n", 5403 adapter_str, cpi->hba_device); 5404 fprintf(stdout, "%s HBA subvendor ID: 0x%04x\n", 5405 adapter_str, cpi->hba_subvendor); 5406 fprintf(stdout, "%s HBA subdevice ID: 0x%04x\n", 5407 adapter_str, cpi->hba_subdevice); 5408 fprintf(stdout, "%s bus ID: %d\n", adapter_str, cpi->bus_id); 5409 fprintf(stdout, "%s base transfer speed: ", adapter_str); 5410 if (cpi->base_transfer_speed > 1000) 5411 fprintf(stdout, "%d.%03dMB/sec\n", 5412 cpi->base_transfer_speed / 1000, 5413 cpi->base_transfer_speed % 1000); 5414 else 5415 fprintf(stdout, "%dKB/sec\n", 5416 (cpi->base_transfer_speed % 1000) * 1000); 5417 fprintf(stdout, "%s maximum transfer size: %u bytes\n", 5418 adapter_str, cpi->maxio); 5419 } 5420 5421 static int 5422 get_print_cts(struct cam_device *device, int user_settings, int quiet, 5423 struct ccb_trans_settings *cts) 5424 { 5425 int retval; 5426 union ccb *ccb; 5427 5428 retval = 0; 5429 ccb = cam_getccb(device); 5430 5431 if (ccb == NULL) { 5432 warnx("get_print_cts: error allocating ccb"); 5433 return(1); 5434 } 5435 5436 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->cts); 5437 5438 ccb->ccb_h.func_code = XPT_GET_TRAN_SETTINGS; 5439 5440 if (user_settings == 0) 5441 ccb->cts.type = CTS_TYPE_CURRENT_SETTINGS; 5442 else 5443 ccb->cts.type = CTS_TYPE_USER_SETTINGS; 5444 5445 if (cam_send_ccb(device, ccb) < 0) { 5446 perror("error sending XPT_GET_TRAN_SETTINGS CCB"); 5447 if (arglist & CAM_ARG_VERBOSE) 5448 cam_error_print(device, ccb, CAM_ESF_ALL, 5449 CAM_EPF_ALL, stderr); 5450 retval = 1; 5451 goto get_print_cts_bailout; 5452 } 5453 5454 if ((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP) { 5455 warnx("XPT_GET_TRANS_SETTINGS CCB failed"); 5456 if (arglist & CAM_ARG_VERBOSE) 5457 cam_error_print(device, ccb, CAM_ESF_ALL, 5458 CAM_EPF_ALL, stderr); 5459 retval = 1; 5460 goto get_print_cts_bailout; 5461 } 5462 5463 if (quiet == 0) 5464 cts_print(device, &ccb->cts); 5465 5466 if (cts != NULL) 5467 bcopy(&ccb->cts, cts, sizeof(struct ccb_trans_settings)); 5468 5469 get_print_cts_bailout: 5470 5471 cam_freeccb(ccb); 5472 5473 return(retval); 5474 } 5475 5476 static int 5477 ratecontrol(struct cam_device *device, int retry_count, int timeout, 5478 int argc, char **argv, char *combinedopt) 5479 { 5480 int c; 5481 union ccb *ccb; 5482 int user_settings = 0; 5483 int retval = 0; 5484 int disc_enable = -1, tag_enable = -1; 5485 int mode = -1; 5486 int offset = -1; 5487 double syncrate = -1; 5488 int bus_width = -1; 5489 int quiet = 0; 5490 int change_settings = 0, send_tur = 0; 5491 struct ccb_pathinq cpi; 5492 5493 ccb = cam_getccb(device); 5494 if (ccb == NULL) { 5495 warnx("ratecontrol: error allocating ccb"); 5496 return(1); 5497 } 5498 while ((c = getopt(argc, argv, combinedopt)) != -1) { 5499 switch(c){ 5500 case 'a': 5501 send_tur = 1; 5502 break; 5503 case 'c': 5504 user_settings = 0; 5505 break; 5506 case 'D': 5507 if (strncasecmp(optarg, "enable", 6) == 0) 5508 disc_enable = 1; 5509 else if (strncasecmp(optarg, "disable", 7) == 0) 5510 disc_enable = 0; 5511 else { 5512 warnx("-D argument \"%s\" is unknown", optarg); 5513 retval = 1; 5514 goto ratecontrol_bailout; 5515 } 5516 change_settings = 1; 5517 break; 5518 case 'M': 5519 mode = ata_string2mode(optarg); 5520 if (mode < 0) { 5521 warnx("unknown mode '%s'", optarg); 5522 retval = 1; 5523 goto ratecontrol_bailout; 5524 } 5525 change_settings = 1; 5526 break; 5527 case 'O': 5528 offset = strtol(optarg, NULL, 0); 5529 if (offset < 0) { 5530 warnx("offset value %d is < 0", offset); 5531 retval = 1; 5532 goto ratecontrol_bailout; 5533 } 5534 change_settings = 1; 5535 break; 5536 case 'q': 5537 quiet++; 5538 break; 5539 case 'R': 5540 syncrate = atof(optarg); 5541 if (syncrate < 0) { 5542 warnx("sync rate %f is < 0", syncrate); 5543 retval = 1; 5544 goto ratecontrol_bailout; 5545 } 5546 change_settings = 1; 5547 break; 5548 case 'T': 5549 if (strncasecmp(optarg, "enable", 6) == 0) 5550 tag_enable = 1; 5551 else if (strncasecmp(optarg, "disable", 7) == 0) 5552 tag_enable = 0; 5553 else { 5554 warnx("-T argument \"%s\" is unknown", optarg); 5555 retval = 1; 5556 goto ratecontrol_bailout; 5557 } 5558 change_settings = 1; 5559 break; 5560 case 'U': 5561 user_settings = 1; 5562 break; 5563 case 'W': 5564 bus_width = strtol(optarg, NULL, 0); 5565 if (bus_width < 0) { 5566 warnx("bus width %d is < 0", bus_width); 5567 retval = 1; 5568 goto ratecontrol_bailout; 5569 } 5570 change_settings = 1; 5571 break; 5572 default: 5573 break; 5574 } 5575 } 5576 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->cpi); 5577 /* 5578 * Grab path inquiry information, so we can determine whether 5579 * or not the initiator is capable of the things that the user 5580 * requests. 5581 */ 5582 ccb->ccb_h.func_code = XPT_PATH_INQ; 5583 if (cam_send_ccb(device, ccb) < 0) { 5584 perror("error sending XPT_PATH_INQ CCB"); 5585 if (arglist & CAM_ARG_VERBOSE) { 5586 cam_error_print(device, ccb, CAM_ESF_ALL, 5587 CAM_EPF_ALL, stderr); 5588 } 5589 retval = 1; 5590 goto ratecontrol_bailout; 5591 } 5592 if ((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP) { 5593 warnx("XPT_PATH_INQ CCB failed"); 5594 if (arglist & CAM_ARG_VERBOSE) { 5595 cam_error_print(device, ccb, CAM_ESF_ALL, 5596 CAM_EPF_ALL, stderr); 5597 } 5598 retval = 1; 5599 goto ratecontrol_bailout; 5600 } 5601 bcopy(&ccb->cpi, &cpi, sizeof(struct ccb_pathinq)); 5602 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->cts); 5603 if (quiet == 0) { 5604 fprintf(stdout, "%s parameters:\n", 5605 user_settings ? "User" : "Current"); 5606 } 5607 retval = get_print_cts(device, user_settings, quiet, &ccb->cts); 5608 if (retval != 0) 5609 goto ratecontrol_bailout; 5610 5611 if (arglist & CAM_ARG_VERBOSE) 5612 cpi_print(&cpi); 5613 5614 if (change_settings) { 5615 int didsettings = 0; 5616 struct ccb_trans_settings_spi *spi = NULL; 5617 struct ccb_trans_settings_pata *pata = NULL; 5618 struct ccb_trans_settings_sata *sata = NULL; 5619 struct ccb_trans_settings_ata *ata = NULL; 5620 struct ccb_trans_settings_scsi *scsi = NULL; 5621 5622 if (ccb->cts.transport == XPORT_SPI) 5623 spi = &ccb->cts.xport_specific.spi; 5624 if (ccb->cts.transport == XPORT_ATA) 5625 pata = &ccb->cts.xport_specific.ata; 5626 if (ccb->cts.transport == XPORT_SATA) 5627 sata = &ccb->cts.xport_specific.sata; 5628 if (ccb->cts.protocol == PROTO_ATA) 5629 ata = &ccb->cts.proto_specific.ata; 5630 if (ccb->cts.protocol == PROTO_SCSI) 5631 scsi = &ccb->cts.proto_specific.scsi; 5632 ccb->cts.xport_specific.valid = 0; 5633 ccb->cts.proto_specific.valid = 0; 5634 if (spi && disc_enable != -1) { 5635 spi->valid |= CTS_SPI_VALID_DISC; 5636 if (disc_enable == 0) 5637 spi->flags &= ~CTS_SPI_FLAGS_DISC_ENB; 5638 else 5639 spi->flags |= CTS_SPI_FLAGS_DISC_ENB; 5640 didsettings++; 5641 } 5642 if (tag_enable != -1) { 5643 if ((cpi.hba_inquiry & PI_TAG_ABLE) == 0) { 5644 warnx("HBA does not support tagged queueing, " 5645 "so you cannot modify tag settings"); 5646 retval = 1; 5647 goto ratecontrol_bailout; 5648 } 5649 if (ata) { 5650 ata->valid |= CTS_SCSI_VALID_TQ; 5651 if (tag_enable == 0) 5652 ata->flags &= ~CTS_ATA_FLAGS_TAG_ENB; 5653 else 5654 ata->flags |= CTS_ATA_FLAGS_TAG_ENB; 5655 didsettings++; 5656 } else if (scsi) { 5657 scsi->valid |= CTS_SCSI_VALID_TQ; 5658 if (tag_enable == 0) 5659 scsi->flags &= ~CTS_SCSI_FLAGS_TAG_ENB; 5660 else 5661 scsi->flags |= CTS_SCSI_FLAGS_TAG_ENB; 5662 didsettings++; 5663 } 5664 } 5665 if (spi && offset != -1) { 5666 if ((cpi.hba_inquiry & PI_SDTR_ABLE) == 0) { 5667 warnx("HBA is not capable of changing offset"); 5668 retval = 1; 5669 goto ratecontrol_bailout; 5670 } 5671 spi->valid |= CTS_SPI_VALID_SYNC_OFFSET; 5672 spi->sync_offset = offset; 5673 didsettings++; 5674 } 5675 if (spi && syncrate != -1) { 5676 int prelim_sync_period; 5677 5678 if ((cpi.hba_inquiry & PI_SDTR_ABLE) == 0) { 5679 warnx("HBA is not capable of changing " 5680 "transfer rates"); 5681 retval = 1; 5682 goto ratecontrol_bailout; 5683 } 5684 spi->valid |= CTS_SPI_VALID_SYNC_RATE; 5685 /* 5686 * The sync rate the user gives us is in MHz. 5687 * We need to translate it into KHz for this 5688 * calculation. 5689 */ 5690 syncrate *= 1000; 5691 /* 5692 * Next, we calculate a "preliminary" sync period 5693 * in tenths of a nanosecond. 5694 */ 5695 if (syncrate == 0) 5696 prelim_sync_period = 0; 5697 else 5698 prelim_sync_period = 10000000 / syncrate; 5699 spi->sync_period = 5700 scsi_calc_syncparam(prelim_sync_period); 5701 didsettings++; 5702 } 5703 if (sata && syncrate != -1) { 5704 if ((cpi.hba_inquiry & PI_SDTR_ABLE) == 0) { 5705 warnx("HBA is not capable of changing " 5706 "transfer rates"); 5707 retval = 1; 5708 goto ratecontrol_bailout; 5709 } 5710 if (!user_settings) { 5711 warnx("You can modify only user rate " 5712 "settings for SATA"); 5713 retval = 1; 5714 goto ratecontrol_bailout; 5715 } 5716 sata->revision = ata_speed2revision(syncrate * 100); 5717 if (sata->revision < 0) { 5718 warnx("Invalid rate %f", syncrate); 5719 retval = 1; 5720 goto ratecontrol_bailout; 5721 } 5722 sata->valid |= CTS_SATA_VALID_REVISION; 5723 didsettings++; 5724 } 5725 if ((pata || sata) && mode != -1) { 5726 if ((cpi.hba_inquiry & PI_SDTR_ABLE) == 0) { 5727 warnx("HBA is not capable of changing " 5728 "transfer rates"); 5729 retval = 1; 5730 goto ratecontrol_bailout; 5731 } 5732 if (!user_settings) { 5733 warnx("You can modify only user mode " 5734 "settings for ATA/SATA"); 5735 retval = 1; 5736 goto ratecontrol_bailout; 5737 } 5738 if (pata) { 5739 pata->mode = mode; 5740 pata->valid |= CTS_ATA_VALID_MODE; 5741 } else { 5742 sata->mode = mode; 5743 sata->valid |= CTS_SATA_VALID_MODE; 5744 } 5745 didsettings++; 5746 } 5747 /* 5748 * The bus_width argument goes like this: 5749 * 0 == 8 bit 5750 * 1 == 16 bit 5751 * 2 == 32 bit 5752 * Therefore, if you shift the number of bits given on the 5753 * command line right by 4, you should get the correct 5754 * number. 5755 */ 5756 if (spi && bus_width != -1) { 5757 /* 5758 * We might as well validate things here with a 5759 * decipherable error message, rather than what 5760 * will probably be an indecipherable error message 5761 * by the time it gets back to us. 5762 */ 5763 if ((bus_width == 16) 5764 && ((cpi.hba_inquiry & PI_WIDE_16) == 0)) { 5765 warnx("HBA does not support 16 bit bus width"); 5766 retval = 1; 5767 goto ratecontrol_bailout; 5768 } else if ((bus_width == 32) 5769 && ((cpi.hba_inquiry & PI_WIDE_32) == 0)) { 5770 warnx("HBA does not support 32 bit bus width"); 5771 retval = 1; 5772 goto ratecontrol_bailout; 5773 } else if ((bus_width != 8) 5774 && (bus_width != 16) 5775 && (bus_width != 32)) { 5776 warnx("Invalid bus width %d", bus_width); 5777 retval = 1; 5778 goto ratecontrol_bailout; 5779 } 5780 spi->valid |= CTS_SPI_VALID_BUS_WIDTH; 5781 spi->bus_width = bus_width >> 4; 5782 didsettings++; 5783 } 5784 if (didsettings == 0) { 5785 goto ratecontrol_bailout; 5786 } 5787 ccb->ccb_h.func_code = XPT_SET_TRAN_SETTINGS; 5788 if (cam_send_ccb(device, ccb) < 0) { 5789 perror("error sending XPT_SET_TRAN_SETTINGS CCB"); 5790 if (arglist & CAM_ARG_VERBOSE) { 5791 cam_error_print(device, ccb, CAM_ESF_ALL, 5792 CAM_EPF_ALL, stderr); 5793 } 5794 retval = 1; 5795 goto ratecontrol_bailout; 5796 } 5797 if ((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP) { 5798 warnx("XPT_SET_TRANS_SETTINGS CCB failed"); 5799 if (arglist & CAM_ARG_VERBOSE) { 5800 cam_error_print(device, ccb, CAM_ESF_ALL, 5801 CAM_EPF_ALL, stderr); 5802 } 5803 retval = 1; 5804 goto ratecontrol_bailout; 5805 } 5806 } 5807 if (send_tur) { 5808 retval = testunitready(device, retry_count, timeout, 5809 (arglist & CAM_ARG_VERBOSE) ? 0 : 1); 5810 /* 5811 * If the TUR didn't succeed, just bail. 5812 */ 5813 if (retval != 0) { 5814 if (quiet == 0) 5815 fprintf(stderr, "Test Unit Ready failed\n"); 5816 goto ratecontrol_bailout; 5817 } 5818 } 5819 if ((change_settings || send_tur) && !quiet && 5820 (ccb->cts.transport == XPORT_ATA || 5821 ccb->cts.transport == XPORT_SATA || send_tur)) { 5822 fprintf(stdout, "New parameters:\n"); 5823 retval = get_print_cts(device, user_settings, 0, NULL); 5824 } 5825 5826 ratecontrol_bailout: 5827 cam_freeccb(ccb); 5828 return(retval); 5829 } 5830 5831 static int 5832 scsiformat(struct cam_device *device, int argc, char **argv, 5833 char *combinedopt, int retry_count, int timeout) 5834 { 5835 union ccb *ccb; 5836 int c; 5837 int ycount = 0, quiet = 0; 5838 int error = 0, retval = 0; 5839 int use_timeout = 10800 * 1000; 5840 int immediate = 1; 5841 struct format_defect_list_header fh; 5842 u_int8_t *data_ptr = NULL; 5843 u_int32_t dxfer_len = 0; 5844 u_int8_t byte2 = 0; 5845 int num_warnings = 0; 5846 int reportonly = 0; 5847 5848 ccb = cam_getccb(device); 5849 5850 if (ccb == NULL) { 5851 warnx("scsiformat: error allocating ccb"); 5852 return(1); 5853 } 5854 5855 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->csio); 5856 5857 while ((c = getopt(argc, argv, combinedopt)) != -1) { 5858 switch(c) { 5859 case 'q': 5860 quiet++; 5861 break; 5862 case 'r': 5863 reportonly = 1; 5864 break; 5865 case 'w': 5866 immediate = 0; 5867 break; 5868 case 'y': 5869 ycount++; 5870 break; 5871 } 5872 } 5873 5874 if (reportonly) 5875 goto doreport; 5876 5877 if (quiet == 0) { 5878 fprintf(stdout, "You are about to REMOVE ALL DATA from the " 5879 "following device:\n"); 5880 5881 error = scsidoinquiry(device, argc, argv, combinedopt, 5882 retry_count, timeout); 5883 5884 if (error != 0) { 5885 warnx("scsiformat: error sending inquiry"); 5886 goto scsiformat_bailout; 5887 } 5888 } 5889 5890 if (ycount == 0) { 5891 if (!get_confirmation()) { 5892 error = 1; 5893 goto scsiformat_bailout; 5894 } 5895 } 5896 5897 if (timeout != 0) 5898 use_timeout = timeout; 5899 5900 if (quiet == 0) { 5901 fprintf(stdout, "Current format timeout is %d seconds\n", 5902 use_timeout / 1000); 5903 } 5904 5905 /* 5906 * If the user hasn't disabled questions and didn't specify a 5907 * timeout on the command line, ask them if they want the current 5908 * timeout. 5909 */ 5910 if ((ycount == 0) 5911 && (timeout == 0)) { 5912 char str[1024]; 5913 int new_timeout = 0; 5914 5915 fprintf(stdout, "Enter new timeout in seconds or press\n" 5916 "return to keep the current timeout [%d] ", 5917 use_timeout / 1000); 5918 5919 if (fgets(str, sizeof(str), stdin) != NULL) { 5920 if (str[0] != '\0') 5921 new_timeout = atoi(str); 5922 } 5923 5924 if (new_timeout != 0) { 5925 use_timeout = new_timeout * 1000; 5926 fprintf(stdout, "Using new timeout value %d\n", 5927 use_timeout / 1000); 5928 } 5929 } 5930 5931 /* 5932 * Keep this outside the if block below to silence any unused 5933 * variable warnings. 5934 */ 5935 bzero(&fh, sizeof(fh)); 5936 5937 /* 5938 * If we're in immediate mode, we've got to include the format 5939 * header 5940 */ 5941 if (immediate != 0) { 5942 fh.byte2 = FU_DLH_IMMED; 5943 data_ptr = (u_int8_t *)&fh; 5944 dxfer_len = sizeof(fh); 5945 byte2 = FU_FMT_DATA; 5946 } else if (quiet == 0) { 5947 fprintf(stdout, "Formatting..."); 5948 fflush(stdout); 5949 } 5950 5951 scsi_format_unit(&ccb->csio, 5952 /* retries */ retry_count, 5953 /* cbfcnp */ NULL, 5954 /* tag_action */ MSG_SIMPLE_Q_TAG, 5955 /* byte2 */ byte2, 5956 /* ileave */ 0, 5957 /* data_ptr */ data_ptr, 5958 /* dxfer_len */ dxfer_len, 5959 /* sense_len */ SSD_FULL_SIZE, 5960 /* timeout */ use_timeout); 5961 5962 /* Disable freezing the device queue */ 5963 ccb->ccb_h.flags |= CAM_DEV_QFRZDIS; 5964 5965 if (arglist & CAM_ARG_ERR_RECOVER) 5966 ccb->ccb_h.flags |= CAM_PASS_ERR_RECOVER; 5967 5968 if (((retval = cam_send_ccb(device, ccb)) < 0) 5969 || ((immediate == 0) 5970 && ((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP))) { 5971 const char errstr[] = "error sending format command"; 5972 5973 if (retval < 0) 5974 warn(errstr); 5975 else 5976 warnx(errstr); 5977 5978 if (arglist & CAM_ARG_VERBOSE) { 5979 cam_error_print(device, ccb, CAM_ESF_ALL, 5980 CAM_EPF_ALL, stderr); 5981 } 5982 error = 1; 5983 goto scsiformat_bailout; 5984 } 5985 5986 /* 5987 * If we ran in non-immediate mode, we already checked for errors 5988 * above and printed out any necessary information. If we're in 5989 * immediate mode, we need to loop through and get status 5990 * information periodically. 5991 */ 5992 if (immediate == 0) { 5993 if (quiet == 0) { 5994 fprintf(stdout, "Format Complete\n"); 5995 } 5996 goto scsiformat_bailout; 5997 } 5998 5999 doreport: 6000 do { 6001 cam_status status; 6002 6003 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->csio); 6004 6005 /* 6006 * There's really no need to do error recovery or 6007 * retries here, since we're just going to sit in a 6008 * loop and wait for the device to finish formatting. 6009 */ 6010 scsi_test_unit_ready(&ccb->csio, 6011 /* retries */ 0, 6012 /* cbfcnp */ NULL, 6013 /* tag_action */ MSG_SIMPLE_Q_TAG, 6014 /* sense_len */ SSD_FULL_SIZE, 6015 /* timeout */ 5000); 6016 6017 /* Disable freezing the device queue */ 6018 ccb->ccb_h.flags |= CAM_DEV_QFRZDIS; 6019 6020 retval = cam_send_ccb(device, ccb); 6021 6022 /* 6023 * If we get an error from the ioctl, bail out. SCSI 6024 * errors are expected. 6025 */ 6026 if (retval < 0) { 6027 warn("error sending CAMIOCOMMAND ioctl"); 6028 if (arglist & CAM_ARG_VERBOSE) { 6029 cam_error_print(device, ccb, CAM_ESF_ALL, 6030 CAM_EPF_ALL, stderr); 6031 } 6032 error = 1; 6033 goto scsiformat_bailout; 6034 } 6035 6036 status = ccb->ccb_h.status & CAM_STATUS_MASK; 6037 6038 if ((status != CAM_REQ_CMP) 6039 && (status == CAM_SCSI_STATUS_ERROR) 6040 && ((ccb->ccb_h.status & CAM_AUTOSNS_VALID) != 0)) { 6041 struct scsi_sense_data *sense; 6042 int error_code, sense_key, asc, ascq; 6043 6044 sense = &ccb->csio.sense_data; 6045 scsi_extract_sense_len(sense, ccb->csio.sense_len - 6046 ccb->csio.sense_resid, &error_code, &sense_key, 6047 &asc, &ascq, /*show_errors*/ 1); 6048 6049 /* 6050 * According to the SCSI-2 and SCSI-3 specs, a 6051 * drive that is in the middle of a format should 6052 * return NOT READY with an ASC of "logical unit 6053 * not ready, format in progress". The sense key 6054 * specific bytes will then be a progress indicator. 6055 */ 6056 if ((sense_key == SSD_KEY_NOT_READY) 6057 && (asc == 0x04) && (ascq == 0x04)) { 6058 uint8_t sks[3]; 6059 6060 if ((scsi_get_sks(sense, ccb->csio.sense_len - 6061 ccb->csio.sense_resid, sks) == 0) 6062 && (quiet == 0)) { 6063 int val; 6064 u_int64_t percentage; 6065 6066 val = scsi_2btoul(&sks[1]); 6067 percentage = 10000 * val; 6068 6069 fprintf(stdout, 6070 "\rFormatting: %ju.%02u %% " 6071 "(%d/%d) done", 6072 (uintmax_t)(percentage / 6073 (0x10000 * 100)), 6074 (unsigned)((percentage / 6075 0x10000) % 100), 6076 val, 0x10000); 6077 fflush(stdout); 6078 } else if ((quiet == 0) 6079 && (++num_warnings <= 1)) { 6080 warnx("Unexpected SCSI Sense Key " 6081 "Specific value returned " 6082 "during format:"); 6083 scsi_sense_print(device, &ccb->csio, 6084 stderr); 6085 warnx("Unable to print status " 6086 "information, but format will " 6087 "proceed."); 6088 warnx("will exit when format is " 6089 "complete"); 6090 } 6091 sleep(1); 6092 } else { 6093 warnx("Unexpected SCSI error during format"); 6094 cam_error_print(device, ccb, CAM_ESF_ALL, 6095 CAM_EPF_ALL, stderr); 6096 error = 1; 6097 goto scsiformat_bailout; 6098 } 6099 6100 } else if (status != CAM_REQ_CMP) { 6101 warnx("Unexpected CAM status %#x", status); 6102 if (arglist & CAM_ARG_VERBOSE) 6103 cam_error_print(device, ccb, CAM_ESF_ALL, 6104 CAM_EPF_ALL, stderr); 6105 error = 1; 6106 goto scsiformat_bailout; 6107 } 6108 6109 } while((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP); 6110 6111 if (quiet == 0) 6112 fprintf(stdout, "\nFormat Complete\n"); 6113 6114 scsiformat_bailout: 6115 6116 cam_freeccb(ccb); 6117 6118 return(error); 6119 } 6120 6121 static int 6122 scsisanitize(struct cam_device *device, int argc, char **argv, 6123 char *combinedopt, int retry_count, int timeout) 6124 { 6125 union ccb *ccb; 6126 u_int8_t action = 0; 6127 int c; 6128 int ycount = 0, quiet = 0; 6129 int error = 0, retval = 0; 6130 int use_timeout = 10800 * 1000; 6131 int immediate = 1; 6132 int invert = 0; 6133 int passes = 0; 6134 int ause = 0; 6135 int fd = -1; 6136 const char *pattern = NULL; 6137 u_int8_t *data_ptr = NULL; 6138 u_int32_t dxfer_len = 0; 6139 u_int8_t byte2 = 0; 6140 int num_warnings = 0; 6141 int reportonly = 0; 6142 6143 ccb = cam_getccb(device); 6144 6145 if (ccb == NULL) { 6146 warnx("scsisanitize: error allocating ccb"); 6147 return(1); 6148 } 6149 6150 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->csio); 6151 6152 while ((c = getopt(argc, argv, combinedopt)) != -1) { 6153 switch(c) { 6154 case 'a': 6155 if (strcasecmp(optarg, "overwrite") == 0) 6156 action = SSZ_SERVICE_ACTION_OVERWRITE; 6157 else if (strcasecmp(optarg, "block") == 0) 6158 action = SSZ_SERVICE_ACTION_BLOCK_ERASE; 6159 else if (strcasecmp(optarg, "crypto") == 0) 6160 action = SSZ_SERVICE_ACTION_CRYPTO_ERASE; 6161 else if (strcasecmp(optarg, "exitfailure") == 0) 6162 action = SSZ_SERVICE_ACTION_EXIT_MODE_FAILURE; 6163 else { 6164 warnx("invalid service operation \"%s\"", 6165 optarg); 6166 error = 1; 6167 goto scsisanitize_bailout; 6168 } 6169 break; 6170 case 'c': 6171 passes = strtol(optarg, NULL, 0); 6172 if (passes < 1 || passes > 31) { 6173 warnx("invalid passes value %d", passes); 6174 error = 1; 6175 goto scsisanitize_bailout; 6176 } 6177 break; 6178 case 'I': 6179 invert = 1; 6180 break; 6181 case 'P': 6182 pattern = optarg; 6183 break; 6184 case 'q': 6185 quiet++; 6186 break; 6187 case 'U': 6188 ause = 1; 6189 break; 6190 case 'r': 6191 reportonly = 1; 6192 break; 6193 case 'w': 6194 immediate = 0; 6195 break; 6196 case 'y': 6197 ycount++; 6198 break; 6199 } 6200 } 6201 6202 if (reportonly) 6203 goto doreport; 6204 6205 if (action == 0) { 6206 warnx("an action is required"); 6207 error = 1; 6208 goto scsisanitize_bailout; 6209 } else if (action == SSZ_SERVICE_ACTION_OVERWRITE) { 6210 struct scsi_sanitize_parameter_list *pl; 6211 struct stat sb; 6212 ssize_t sz, amt; 6213 6214 if (pattern == NULL) { 6215 warnx("overwrite action requires -P argument"); 6216 error = 1; 6217 goto scsisanitize_bailout; 6218 } 6219 fd = open(pattern, O_RDONLY); 6220 if (fd < 0) { 6221 warn("cannot open pattern file %s", pattern); 6222 error = 1; 6223 goto scsisanitize_bailout; 6224 } 6225 if (fstat(fd, &sb) < 0) { 6226 warn("cannot stat pattern file %s", pattern); 6227 error = 1; 6228 goto scsisanitize_bailout; 6229 } 6230 sz = sb.st_size; 6231 if (sz > SSZPL_MAX_PATTERN_LENGTH) { 6232 warnx("pattern file size exceeds maximum value %d", 6233 SSZPL_MAX_PATTERN_LENGTH); 6234 error = 1; 6235 goto scsisanitize_bailout; 6236 } 6237 dxfer_len = sizeof(*pl) + sz; 6238 data_ptr = calloc(1, dxfer_len); 6239 if (data_ptr == NULL) { 6240 warnx("cannot allocate parameter list buffer"); 6241 error = 1; 6242 goto scsisanitize_bailout; 6243 } 6244 6245 amt = read(fd, data_ptr + sizeof(*pl), sz); 6246 if (amt < 0) { 6247 warn("cannot read pattern file"); 6248 error = 1; 6249 goto scsisanitize_bailout; 6250 } else if (amt != sz) { 6251 warnx("short pattern file read"); 6252 error = 1; 6253 goto scsisanitize_bailout; 6254 } 6255 6256 pl = (struct scsi_sanitize_parameter_list *)data_ptr; 6257 if (passes == 0) 6258 pl->byte1 = 1; 6259 else 6260 pl->byte1 = passes; 6261 if (invert != 0) 6262 pl->byte1 |= SSZPL_INVERT; 6263 scsi_ulto2b(sz, pl->length); 6264 } else { 6265 const char *arg; 6266 6267 if (passes != 0) 6268 arg = "-c"; 6269 else if (invert != 0) 6270 arg = "-I"; 6271 else if (pattern != NULL) 6272 arg = "-P"; 6273 else 6274 arg = NULL; 6275 if (arg != NULL) { 6276 warnx("%s argument only valid with overwrite " 6277 "operation", arg); 6278 error = 1; 6279 goto scsisanitize_bailout; 6280 } 6281 } 6282 6283 if (quiet == 0) { 6284 fprintf(stdout, "You are about to REMOVE ALL DATA from the " 6285 "following device:\n"); 6286 6287 error = scsidoinquiry(device, argc, argv, combinedopt, 6288 retry_count, timeout); 6289 6290 if (error != 0) { 6291 warnx("scsisanitize: error sending inquiry"); 6292 goto scsisanitize_bailout; 6293 } 6294 } 6295 6296 if (ycount == 0) { 6297 if (!get_confirmation()) { 6298 error = 1; 6299 goto scsisanitize_bailout; 6300 } 6301 } 6302 6303 if (timeout != 0) 6304 use_timeout = timeout; 6305 6306 if (quiet == 0) { 6307 fprintf(stdout, "Current sanitize timeout is %d seconds\n", 6308 use_timeout / 1000); 6309 } 6310 6311 /* 6312 * If the user hasn't disabled questions and didn't specify a 6313 * timeout on the command line, ask them if they want the current 6314 * timeout. 6315 */ 6316 if ((ycount == 0) 6317 && (timeout == 0)) { 6318 char str[1024]; 6319 int new_timeout = 0; 6320 6321 fprintf(stdout, "Enter new timeout in seconds or press\n" 6322 "return to keep the current timeout [%d] ", 6323 use_timeout / 1000); 6324 6325 if (fgets(str, sizeof(str), stdin) != NULL) { 6326 if (str[0] != '\0') 6327 new_timeout = atoi(str); 6328 } 6329 6330 if (new_timeout != 0) { 6331 use_timeout = new_timeout * 1000; 6332 fprintf(stdout, "Using new timeout value %d\n", 6333 use_timeout / 1000); 6334 } 6335 } 6336 6337 byte2 = action; 6338 if (ause != 0) 6339 byte2 |= SSZ_UNRESTRICTED_EXIT; 6340 if (immediate != 0) 6341 byte2 |= SSZ_IMMED; 6342 6343 scsi_sanitize(&ccb->csio, 6344 /* retries */ retry_count, 6345 /* cbfcnp */ NULL, 6346 /* tag_action */ MSG_SIMPLE_Q_TAG, 6347 /* byte2 */ byte2, 6348 /* control */ 0, 6349 /* data_ptr */ data_ptr, 6350 /* dxfer_len */ dxfer_len, 6351 /* sense_len */ SSD_FULL_SIZE, 6352 /* timeout */ use_timeout); 6353 6354 /* Disable freezing the device queue */ 6355 ccb->ccb_h.flags |= CAM_DEV_QFRZDIS; 6356 6357 if (arglist & CAM_ARG_ERR_RECOVER) 6358 ccb->ccb_h.flags |= CAM_PASS_ERR_RECOVER; 6359 6360 if (cam_send_ccb(device, ccb) < 0) { 6361 warn("error sending sanitize command"); 6362 error = 1; 6363 goto scsisanitize_bailout; 6364 } 6365 6366 if ((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP) { 6367 struct scsi_sense_data *sense; 6368 int error_code, sense_key, asc, ascq; 6369 6370 if ((ccb->ccb_h.status & CAM_STATUS_MASK) == 6371 CAM_SCSI_STATUS_ERROR) { 6372 sense = &ccb->csio.sense_data; 6373 scsi_extract_sense_len(sense, ccb->csio.sense_len - 6374 ccb->csio.sense_resid, &error_code, &sense_key, 6375 &asc, &ascq, /*show_errors*/ 1); 6376 6377 if (sense_key == SSD_KEY_ILLEGAL_REQUEST && 6378 asc == 0x20 && ascq == 0x00) 6379 warnx("sanitize is not supported by " 6380 "this device"); 6381 else 6382 warnx("error sanitizing this device"); 6383 } else 6384 warnx("error sanitizing this device"); 6385 6386 if (arglist & CAM_ARG_VERBOSE) { 6387 cam_error_print(device, ccb, CAM_ESF_ALL, 6388 CAM_EPF_ALL, stderr); 6389 } 6390 error = 1; 6391 goto scsisanitize_bailout; 6392 } 6393 6394 /* 6395 * If we ran in non-immediate mode, we already checked for errors 6396 * above and printed out any necessary information. If we're in 6397 * immediate mode, we need to loop through and get status 6398 * information periodically. 6399 */ 6400 if (immediate == 0) { 6401 if (quiet == 0) { 6402 fprintf(stdout, "Sanitize Complete\n"); 6403 } 6404 goto scsisanitize_bailout; 6405 } 6406 6407 doreport: 6408 do { 6409 cam_status status; 6410 6411 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->csio); 6412 6413 /* 6414 * There's really no need to do error recovery or 6415 * retries here, since we're just going to sit in a 6416 * loop and wait for the device to finish sanitizing. 6417 */ 6418 scsi_test_unit_ready(&ccb->csio, 6419 /* retries */ 0, 6420 /* cbfcnp */ NULL, 6421 /* tag_action */ MSG_SIMPLE_Q_TAG, 6422 /* sense_len */ SSD_FULL_SIZE, 6423 /* timeout */ 5000); 6424 6425 /* Disable freezing the device queue */ 6426 ccb->ccb_h.flags |= CAM_DEV_QFRZDIS; 6427 6428 retval = cam_send_ccb(device, ccb); 6429 6430 /* 6431 * If we get an error from the ioctl, bail out. SCSI 6432 * errors are expected. 6433 */ 6434 if (retval < 0) { 6435 warn("error sending CAMIOCOMMAND ioctl"); 6436 if (arglist & CAM_ARG_VERBOSE) { 6437 cam_error_print(device, ccb, CAM_ESF_ALL, 6438 CAM_EPF_ALL, stderr); 6439 } 6440 error = 1; 6441 goto scsisanitize_bailout; 6442 } 6443 6444 status = ccb->ccb_h.status & CAM_STATUS_MASK; 6445 6446 if ((status != CAM_REQ_CMP) 6447 && (status == CAM_SCSI_STATUS_ERROR) 6448 && ((ccb->ccb_h.status & CAM_AUTOSNS_VALID) != 0)) { 6449 struct scsi_sense_data *sense; 6450 int error_code, sense_key, asc, ascq; 6451 6452 sense = &ccb->csio.sense_data; 6453 scsi_extract_sense_len(sense, ccb->csio.sense_len - 6454 ccb->csio.sense_resid, &error_code, &sense_key, 6455 &asc, &ascq, /*show_errors*/ 1); 6456 6457 /* 6458 * According to the SCSI-3 spec, a drive that is in the 6459 * middle of a sanitize should return NOT READY with an 6460 * ASC of "logical unit not ready, sanitize in 6461 * progress". The sense key specific bytes will then 6462 * be a progress indicator. 6463 */ 6464 if ((sense_key == SSD_KEY_NOT_READY) 6465 && (asc == 0x04) && (ascq == 0x1b)) { 6466 uint8_t sks[3]; 6467 6468 if ((scsi_get_sks(sense, ccb->csio.sense_len - 6469 ccb->csio.sense_resid, sks) == 0) 6470 && (quiet == 0)) { 6471 int val; 6472 u_int64_t percentage; 6473 6474 val = scsi_2btoul(&sks[1]); 6475 percentage = 10000 * val; 6476 6477 fprintf(stdout, 6478 "\rSanitizing: %ju.%02u %% " 6479 "(%d/%d) done", 6480 (uintmax_t)(percentage / 6481 (0x10000 * 100)), 6482 (unsigned)((percentage / 6483 0x10000) % 100), 6484 val, 0x10000); 6485 fflush(stdout); 6486 } else if ((quiet == 0) 6487 && (++num_warnings <= 1)) { 6488 warnx("Unexpected SCSI Sense Key " 6489 "Specific value returned " 6490 "during sanitize:"); 6491 scsi_sense_print(device, &ccb->csio, 6492 stderr); 6493 warnx("Unable to print status " 6494 "information, but sanitze will " 6495 "proceed."); 6496 warnx("will exit when sanitize is " 6497 "complete"); 6498 } 6499 sleep(1); 6500 } else { 6501 warnx("Unexpected SCSI error during sanitize"); 6502 cam_error_print(device, ccb, CAM_ESF_ALL, 6503 CAM_EPF_ALL, stderr); 6504 error = 1; 6505 goto scsisanitize_bailout; 6506 } 6507 6508 } else if (status != CAM_REQ_CMP) { 6509 warnx("Unexpected CAM status %#x", status); 6510 if (arglist & CAM_ARG_VERBOSE) 6511 cam_error_print(device, ccb, CAM_ESF_ALL, 6512 CAM_EPF_ALL, stderr); 6513 error = 1; 6514 goto scsisanitize_bailout; 6515 } 6516 } while((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP); 6517 6518 if (quiet == 0) 6519 fprintf(stdout, "\nSanitize Complete\n"); 6520 6521 scsisanitize_bailout: 6522 if (fd >= 0) 6523 close(fd); 6524 if (data_ptr != NULL) 6525 free(data_ptr); 6526 cam_freeccb(ccb); 6527 6528 return(error); 6529 } 6530 6531 static int 6532 scsireportluns(struct cam_device *device, int argc, char **argv, 6533 char *combinedopt, int retry_count, int timeout) 6534 { 6535 union ccb *ccb; 6536 int c, countonly, lunsonly; 6537 struct scsi_report_luns_data *lundata; 6538 int alloc_len; 6539 uint8_t report_type; 6540 uint32_t list_len, i, j; 6541 int retval; 6542 6543 retval = 0; 6544 lundata = NULL; 6545 report_type = RPL_REPORT_DEFAULT; 6546 ccb = cam_getccb(device); 6547 6548 if (ccb == NULL) { 6549 warnx("%s: error allocating ccb", __func__); 6550 return (1); 6551 } 6552 6553 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->csio); 6554 6555 countonly = 0; 6556 lunsonly = 0; 6557 6558 while ((c = getopt(argc, argv, combinedopt)) != -1) { 6559 switch (c) { 6560 case 'c': 6561 countonly++; 6562 break; 6563 case 'l': 6564 lunsonly++; 6565 break; 6566 case 'r': 6567 if (strcasecmp(optarg, "default") == 0) 6568 report_type = RPL_REPORT_DEFAULT; 6569 else if (strcasecmp(optarg, "wellknown") == 0) 6570 report_type = RPL_REPORT_WELLKNOWN; 6571 else if (strcasecmp(optarg, "all") == 0) 6572 report_type = RPL_REPORT_ALL; 6573 else { 6574 warnx("%s: invalid report type \"%s\"", 6575 __func__, optarg); 6576 retval = 1; 6577 goto bailout; 6578 } 6579 break; 6580 default: 6581 break; 6582 } 6583 } 6584 6585 if ((countonly != 0) 6586 && (lunsonly != 0)) { 6587 warnx("%s: you can only specify one of -c or -l", __func__); 6588 retval = 1; 6589 goto bailout; 6590 } 6591 /* 6592 * According to SPC-4, the allocation length must be at least 16 6593 * bytes -- enough for the header and one LUN. 6594 */ 6595 alloc_len = sizeof(*lundata) + 8; 6596 6597 retry: 6598 6599 lundata = malloc(alloc_len); 6600 6601 if (lundata == NULL) { 6602 warn("%s: error mallocing %d bytes", __func__, alloc_len); 6603 retval = 1; 6604 goto bailout; 6605 } 6606 6607 scsi_report_luns(&ccb->csio, 6608 /*retries*/ retry_count, 6609 /*cbfcnp*/ NULL, 6610 /*tag_action*/ MSG_SIMPLE_Q_TAG, 6611 /*select_report*/ report_type, 6612 /*rpl_buf*/ lundata, 6613 /*alloc_len*/ alloc_len, 6614 /*sense_len*/ SSD_FULL_SIZE, 6615 /*timeout*/ timeout ? timeout : 5000); 6616 6617 /* Disable freezing the device queue */ 6618 ccb->ccb_h.flags |= CAM_DEV_QFRZDIS; 6619 6620 if (arglist & CAM_ARG_ERR_RECOVER) 6621 ccb->ccb_h.flags |= CAM_PASS_ERR_RECOVER; 6622 6623 if (cam_send_ccb(device, ccb) < 0) { 6624 warn("error sending REPORT LUNS command"); 6625 6626 if (arglist & CAM_ARG_VERBOSE) 6627 cam_error_print(device, ccb, CAM_ESF_ALL, 6628 CAM_EPF_ALL, stderr); 6629 6630 retval = 1; 6631 goto bailout; 6632 } 6633 6634 if ((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP) { 6635 cam_error_print(device, ccb, CAM_ESF_ALL, CAM_EPF_ALL, stderr); 6636 retval = 1; 6637 goto bailout; 6638 } 6639 6640 6641 list_len = scsi_4btoul(lundata->length); 6642 6643 /* 6644 * If we need to list the LUNs, and our allocation 6645 * length was too short, reallocate and retry. 6646 */ 6647 if ((countonly == 0) 6648 && (list_len > (alloc_len - sizeof(*lundata)))) { 6649 alloc_len = list_len + sizeof(*lundata); 6650 free(lundata); 6651 goto retry; 6652 } 6653 6654 if (lunsonly == 0) 6655 fprintf(stdout, "%u LUN%s found\n", list_len / 8, 6656 ((list_len / 8) > 1) ? "s" : ""); 6657 6658 if (countonly != 0) 6659 goto bailout; 6660 6661 for (i = 0; i < (list_len / 8); i++) { 6662 int no_more; 6663 6664 no_more = 0; 6665 for (j = 0; j < sizeof(lundata->luns[i].lundata); j += 2) { 6666 if (j != 0) 6667 fprintf(stdout, ","); 6668 switch (lundata->luns[i].lundata[j] & 6669 RPL_LUNDATA_ATYP_MASK) { 6670 case RPL_LUNDATA_ATYP_PERIPH: 6671 if ((lundata->luns[i].lundata[j] & 6672 RPL_LUNDATA_PERIPH_BUS_MASK) != 0) 6673 fprintf(stdout, "%d:", 6674 lundata->luns[i].lundata[j] & 6675 RPL_LUNDATA_PERIPH_BUS_MASK); 6676 else if ((j == 0) 6677 && ((lundata->luns[i].lundata[j+2] & 6678 RPL_LUNDATA_PERIPH_BUS_MASK) == 0)) 6679 no_more = 1; 6680 6681 fprintf(stdout, "%d", 6682 lundata->luns[i].lundata[j+1]); 6683 break; 6684 case RPL_LUNDATA_ATYP_FLAT: { 6685 uint8_t tmplun[2]; 6686 tmplun[0] = lundata->luns[i].lundata[j] & 6687 RPL_LUNDATA_FLAT_LUN_MASK; 6688 tmplun[1] = lundata->luns[i].lundata[j+1]; 6689 6690 fprintf(stdout, "%d", scsi_2btoul(tmplun)); 6691 no_more = 1; 6692 break; 6693 } 6694 case RPL_LUNDATA_ATYP_LUN: 6695 fprintf(stdout, "%d:%d:%d", 6696 (lundata->luns[i].lundata[j+1] & 6697 RPL_LUNDATA_LUN_BUS_MASK) >> 5, 6698 lundata->luns[i].lundata[j] & 6699 RPL_LUNDATA_LUN_TARG_MASK, 6700 lundata->luns[i].lundata[j+1] & 6701 RPL_LUNDATA_LUN_LUN_MASK); 6702 break; 6703 case RPL_LUNDATA_ATYP_EXTLUN: { 6704 int field_len_code, eam_code; 6705 6706 eam_code = lundata->luns[i].lundata[j] & 6707 RPL_LUNDATA_EXT_EAM_MASK; 6708 field_len_code = (lundata->luns[i].lundata[j] & 6709 RPL_LUNDATA_EXT_LEN_MASK) >> 4; 6710 6711 if ((eam_code == RPL_LUNDATA_EXT_EAM_WK) 6712 && (field_len_code == 0x00)) { 6713 fprintf(stdout, "%d", 6714 lundata->luns[i].lundata[j+1]); 6715 } else if ((eam_code == 6716 RPL_LUNDATA_EXT_EAM_NOT_SPEC) 6717 && (field_len_code == 0x03)) { 6718 uint8_t tmp_lun[8]; 6719 6720 /* 6721 * This format takes up all 8 bytes. 6722 * If we aren't starting at offset 0, 6723 * that's a bug. 6724 */ 6725 if (j != 0) { 6726 fprintf(stdout, "Invalid " 6727 "offset %d for " 6728 "Extended LUN not " 6729 "specified format", j); 6730 no_more = 1; 6731 break; 6732 } 6733 bzero(tmp_lun, sizeof(tmp_lun)); 6734 bcopy(&lundata->luns[i].lundata[j+1], 6735 &tmp_lun[1], sizeof(tmp_lun) - 1); 6736 fprintf(stdout, "%#jx", 6737 (intmax_t)scsi_8btou64(tmp_lun)); 6738 no_more = 1; 6739 } else { 6740 fprintf(stderr, "Unknown Extended LUN" 6741 "Address method %#x, length " 6742 "code %#x", eam_code, 6743 field_len_code); 6744 no_more = 1; 6745 } 6746 break; 6747 } 6748 default: 6749 fprintf(stderr, "Unknown LUN address method " 6750 "%#x\n", lundata->luns[i].lundata[0] & 6751 RPL_LUNDATA_ATYP_MASK); 6752 break; 6753 } 6754 /* 6755 * For the flat addressing method, there are no 6756 * other levels after it. 6757 */ 6758 if (no_more != 0) 6759 break; 6760 } 6761 fprintf(stdout, "\n"); 6762 } 6763 6764 bailout: 6765 6766 cam_freeccb(ccb); 6767 6768 free(lundata); 6769 6770 return (retval); 6771 } 6772 6773 static int 6774 scsireadcapacity(struct cam_device *device, int argc, char **argv, 6775 char *combinedopt, int retry_count, int timeout) 6776 { 6777 union ccb *ccb; 6778 int blocksizeonly, humanize, numblocks, quiet, sizeonly, baseten; 6779 struct scsi_read_capacity_data rcap; 6780 struct scsi_read_capacity_data_long rcaplong; 6781 uint64_t maxsector; 6782 uint32_t block_len; 6783 int retval; 6784 int c; 6785 6786 blocksizeonly = 0; 6787 humanize = 0; 6788 numblocks = 0; 6789 quiet = 0; 6790 sizeonly = 0; 6791 baseten = 0; 6792 retval = 0; 6793 6794 ccb = cam_getccb(device); 6795 6796 if (ccb == NULL) { 6797 warnx("%s: error allocating ccb", __func__); 6798 return (1); 6799 } 6800 6801 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->csio); 6802 6803 while ((c = getopt(argc, argv, combinedopt)) != -1) { 6804 switch (c) { 6805 case 'b': 6806 blocksizeonly++; 6807 break; 6808 case 'h': 6809 humanize++; 6810 baseten = 0; 6811 break; 6812 case 'H': 6813 humanize++; 6814 baseten++; 6815 break; 6816 case 'N': 6817 numblocks++; 6818 break; 6819 case 'q': 6820 quiet++; 6821 break; 6822 case 's': 6823 sizeonly++; 6824 break; 6825 default: 6826 break; 6827 } 6828 } 6829 6830 if ((blocksizeonly != 0) 6831 && (numblocks != 0)) { 6832 warnx("%s: you can only specify one of -b or -N", __func__); 6833 retval = 1; 6834 goto bailout; 6835 } 6836 6837 if ((blocksizeonly != 0) 6838 && (sizeonly != 0)) { 6839 warnx("%s: you can only specify one of -b or -s", __func__); 6840 retval = 1; 6841 goto bailout; 6842 } 6843 6844 if ((humanize != 0) 6845 && (quiet != 0)) { 6846 warnx("%s: you can only specify one of -h/-H or -q", __func__); 6847 retval = 1; 6848 goto bailout; 6849 } 6850 6851 if ((humanize != 0) 6852 && (blocksizeonly != 0)) { 6853 warnx("%s: you can only specify one of -h/-H or -b", __func__); 6854 retval = 1; 6855 goto bailout; 6856 } 6857 6858 scsi_read_capacity(&ccb->csio, 6859 /*retries*/ retry_count, 6860 /*cbfcnp*/ NULL, 6861 /*tag_action*/ MSG_SIMPLE_Q_TAG, 6862 &rcap, 6863 SSD_FULL_SIZE, 6864 /*timeout*/ timeout ? timeout : 5000); 6865 6866 /* Disable freezing the device queue */ 6867 ccb->ccb_h.flags |= CAM_DEV_QFRZDIS; 6868 6869 if (arglist & CAM_ARG_ERR_RECOVER) 6870 ccb->ccb_h.flags |= CAM_PASS_ERR_RECOVER; 6871 6872 if (cam_send_ccb(device, ccb) < 0) { 6873 warn("error sending READ CAPACITY command"); 6874 6875 if (arglist & CAM_ARG_VERBOSE) 6876 cam_error_print(device, ccb, CAM_ESF_ALL, 6877 CAM_EPF_ALL, stderr); 6878 6879 retval = 1; 6880 goto bailout; 6881 } 6882 6883 if ((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP) { 6884 cam_error_print(device, ccb, CAM_ESF_ALL, CAM_EPF_ALL, stderr); 6885 retval = 1; 6886 goto bailout; 6887 } 6888 6889 maxsector = scsi_4btoul(rcap.addr); 6890 block_len = scsi_4btoul(rcap.length); 6891 6892 /* 6893 * A last block of 2^32-1 means that the true capacity is over 2TB, 6894 * and we need to issue the long READ CAPACITY to get the real 6895 * capacity. Otherwise, we're all set. 6896 */ 6897 if (maxsector != 0xffffffff) 6898 goto do_print; 6899 6900 scsi_read_capacity_16(&ccb->csio, 6901 /*retries*/ retry_count, 6902 /*cbfcnp*/ NULL, 6903 /*tag_action*/ MSG_SIMPLE_Q_TAG, 6904 /*lba*/ 0, 6905 /*reladdr*/ 0, 6906 /*pmi*/ 0, 6907 /*rcap_buf*/ (uint8_t *)&rcaplong, 6908 /*rcap_buf_len*/ sizeof(rcaplong), 6909 /*sense_len*/ SSD_FULL_SIZE, 6910 /*timeout*/ timeout ? timeout : 5000); 6911 6912 /* Disable freezing the device queue */ 6913 ccb->ccb_h.flags |= CAM_DEV_QFRZDIS; 6914 6915 if (arglist & CAM_ARG_ERR_RECOVER) 6916 ccb->ccb_h.flags |= CAM_PASS_ERR_RECOVER; 6917 6918 if (cam_send_ccb(device, ccb) < 0) { 6919 warn("error sending READ CAPACITY (16) command"); 6920 6921 if (arglist & CAM_ARG_VERBOSE) 6922 cam_error_print(device, ccb, CAM_ESF_ALL, 6923 CAM_EPF_ALL, stderr); 6924 6925 retval = 1; 6926 goto bailout; 6927 } 6928 6929 if ((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP) { 6930 cam_error_print(device, ccb, CAM_ESF_ALL, CAM_EPF_ALL, stderr); 6931 retval = 1; 6932 goto bailout; 6933 } 6934 6935 maxsector = scsi_8btou64(rcaplong.addr); 6936 block_len = scsi_4btoul(rcaplong.length); 6937 6938 do_print: 6939 if (blocksizeonly == 0) { 6940 /* 6941 * Humanize implies !quiet, and also implies numblocks. 6942 */ 6943 if (humanize != 0) { 6944 char tmpstr[6]; 6945 int64_t tmpbytes; 6946 int ret; 6947 6948 tmpbytes = (maxsector + 1) * block_len; 6949 ret = humanize_number(tmpstr, sizeof(tmpstr), 6950 tmpbytes, "", HN_AUTOSCALE, 6951 HN_B | HN_DECIMAL | 6952 ((baseten != 0) ? 6953 HN_DIVISOR_1000 : 0)); 6954 if (ret == -1) { 6955 warnx("%s: humanize_number failed!", __func__); 6956 retval = 1; 6957 goto bailout; 6958 } 6959 fprintf(stdout, "Device Size: %s%s", tmpstr, 6960 (sizeonly == 0) ? ", " : "\n"); 6961 } else if (numblocks != 0) { 6962 fprintf(stdout, "%s%ju%s", (quiet == 0) ? 6963 "Blocks: " : "", (uintmax_t)maxsector + 1, 6964 (sizeonly == 0) ? ", " : "\n"); 6965 } else { 6966 fprintf(stdout, "%s%ju%s", (quiet == 0) ? 6967 "Last Block: " : "", (uintmax_t)maxsector, 6968 (sizeonly == 0) ? ", " : "\n"); 6969 } 6970 } 6971 if (sizeonly == 0) 6972 fprintf(stdout, "%s%u%s\n", (quiet == 0) ? 6973 "Block Length: " : "", block_len, (quiet == 0) ? 6974 " bytes" : ""); 6975 bailout: 6976 cam_freeccb(ccb); 6977 6978 return (retval); 6979 } 6980 6981 static int 6982 smpcmd(struct cam_device *device, int argc, char **argv, char *combinedopt, 6983 int retry_count, int timeout) 6984 { 6985 int c, error = 0; 6986 union ccb *ccb; 6987 uint8_t *smp_request = NULL, *smp_response = NULL; 6988 int request_size = 0, response_size = 0; 6989 int fd_request = 0, fd_response = 0; 6990 char *datastr = NULL; 6991 struct get_hook hook; 6992 int retval; 6993 int flags = 0; 6994 6995 /* 6996 * Note that at the moment we don't support sending SMP CCBs to 6997 * devices that aren't probed by CAM. 6998 */ 6999 ccb = cam_getccb(device); 7000 if (ccb == NULL) { 7001 warnx("%s: error allocating CCB", __func__); 7002 return (1); 7003 } 7004 7005 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->smpio); 7006 7007 while ((c = getopt(argc, argv, combinedopt)) != -1) { 7008 switch (c) { 7009 case 'R': 7010 arglist |= CAM_ARG_CMD_IN; 7011 response_size = strtol(optarg, NULL, 0); 7012 if (response_size <= 0) { 7013 warnx("invalid number of response bytes %d", 7014 response_size); 7015 error = 1; 7016 goto smpcmd_bailout; 7017 } 7018 hook.argc = argc - optind; 7019 hook.argv = argv + optind; 7020 hook.got = 0; 7021 optind++; 7022 datastr = cget(&hook, NULL); 7023 /* 7024 * If the user supplied "-" instead of a format, he 7025 * wants the data to be written to stdout. 7026 */ 7027 if ((datastr != NULL) 7028 && (datastr[0] == '-')) 7029 fd_response = 1; 7030 7031 smp_response = (u_int8_t *)malloc(response_size); 7032 if (smp_response == NULL) { 7033 warn("can't malloc memory for SMP response"); 7034 error = 1; 7035 goto smpcmd_bailout; 7036 } 7037 break; 7038 case 'r': 7039 arglist |= CAM_ARG_CMD_OUT; 7040 request_size = strtol(optarg, NULL, 0); 7041 if (request_size <= 0) { 7042 warnx("invalid number of request bytes %d", 7043 request_size); 7044 error = 1; 7045 goto smpcmd_bailout; 7046 } 7047 hook.argc = argc - optind; 7048 hook.argv = argv + optind; 7049 hook.got = 0; 7050 datastr = cget(&hook, NULL); 7051 smp_request = (u_int8_t *)malloc(request_size); 7052 if (smp_request == NULL) { 7053 warn("can't malloc memory for SMP request"); 7054 error = 1; 7055 goto smpcmd_bailout; 7056 } 7057 bzero(smp_request, request_size); 7058 /* 7059 * If the user supplied "-" instead of a format, he 7060 * wants the data to be read from stdin. 7061 */ 7062 if ((datastr != NULL) 7063 && (datastr[0] == '-')) 7064 fd_request = 1; 7065 else 7066 buff_encode_visit(smp_request, request_size, 7067 datastr, 7068 iget, &hook); 7069 optind += hook.got; 7070 break; 7071 default: 7072 break; 7073 } 7074 } 7075 7076 /* 7077 * If fd_data is set, and we're writing to the device, we need to 7078 * read the data the user wants written from stdin. 7079 */ 7080 if ((fd_request == 1) && (arglist & CAM_ARG_CMD_OUT)) { 7081 ssize_t amt_read; 7082 int amt_to_read = request_size; 7083 u_int8_t *buf_ptr = smp_request; 7084 7085 for (amt_read = 0; amt_to_read > 0; 7086 amt_read = read(STDIN_FILENO, buf_ptr, amt_to_read)) { 7087 if (amt_read == -1) { 7088 warn("error reading data from stdin"); 7089 error = 1; 7090 goto smpcmd_bailout; 7091 } 7092 amt_to_read -= amt_read; 7093 buf_ptr += amt_read; 7094 } 7095 } 7096 7097 if (((arglist & CAM_ARG_CMD_IN) == 0) 7098 || ((arglist & CAM_ARG_CMD_OUT) == 0)) { 7099 warnx("%s: need both the request (-r) and response (-R) " 7100 "arguments", __func__); 7101 error = 1; 7102 goto smpcmd_bailout; 7103 } 7104 7105 flags |= CAM_DEV_QFRZDIS; 7106 7107 cam_fill_smpio(&ccb->smpio, 7108 /*retries*/ retry_count, 7109 /*cbfcnp*/ NULL, 7110 /*flags*/ flags, 7111 /*smp_request*/ smp_request, 7112 /*smp_request_len*/ request_size, 7113 /*smp_response*/ smp_response, 7114 /*smp_response_len*/ response_size, 7115 /*timeout*/ timeout ? timeout : 5000); 7116 7117 ccb->smpio.flags = SMP_FLAG_NONE; 7118 7119 if (((retval = cam_send_ccb(device, ccb)) < 0) 7120 || ((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP)) { 7121 const char warnstr[] = "error sending command"; 7122 7123 if (retval < 0) 7124 warn(warnstr); 7125 else 7126 warnx(warnstr); 7127 7128 if (arglist & CAM_ARG_VERBOSE) { 7129 cam_error_print(device, ccb, CAM_ESF_ALL, 7130 CAM_EPF_ALL, stderr); 7131 } 7132 } 7133 7134 if (((ccb->ccb_h.status & CAM_STATUS_MASK) == CAM_REQ_CMP) 7135 && (response_size > 0)) { 7136 if (fd_response == 0) { 7137 buff_decode_visit(smp_response, response_size, 7138 datastr, arg_put, NULL); 7139 fprintf(stdout, "\n"); 7140 } else { 7141 ssize_t amt_written; 7142 int amt_to_write = response_size; 7143 u_int8_t *buf_ptr = smp_response; 7144 7145 for (amt_written = 0; (amt_to_write > 0) && 7146 (amt_written = write(STDOUT_FILENO, buf_ptr, 7147 amt_to_write)) > 0;){ 7148 amt_to_write -= amt_written; 7149 buf_ptr += amt_written; 7150 } 7151 if (amt_written == -1) { 7152 warn("error writing data to stdout"); 7153 error = 1; 7154 goto smpcmd_bailout; 7155 } else if ((amt_written == 0) 7156 && (amt_to_write > 0)) { 7157 warnx("only wrote %u bytes out of %u", 7158 response_size - amt_to_write, 7159 response_size); 7160 } 7161 } 7162 } 7163 smpcmd_bailout: 7164 if (ccb != NULL) 7165 cam_freeccb(ccb); 7166 7167 if (smp_request != NULL) 7168 free(smp_request); 7169 7170 if (smp_response != NULL) 7171 free(smp_response); 7172 7173 return (error); 7174 } 7175 7176 static int 7177 smpreportgeneral(struct cam_device *device, int argc, char **argv, 7178 char *combinedopt, int retry_count, int timeout) 7179 { 7180 union ccb *ccb; 7181 struct smp_report_general_request *request = NULL; 7182 struct smp_report_general_response *response = NULL; 7183 struct sbuf *sb = NULL; 7184 int error = 0; 7185 int c, long_response = 0; 7186 int retval; 7187 7188 /* 7189 * Note that at the moment we don't support sending SMP CCBs to 7190 * devices that aren't probed by CAM. 7191 */ 7192 ccb = cam_getccb(device); 7193 if (ccb == NULL) { 7194 warnx("%s: error allocating CCB", __func__); 7195 return (1); 7196 } 7197 7198 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->smpio); 7199 7200 while ((c = getopt(argc, argv, combinedopt)) != -1) { 7201 switch (c) { 7202 case 'l': 7203 long_response = 1; 7204 break; 7205 default: 7206 break; 7207 } 7208 } 7209 request = malloc(sizeof(*request)); 7210 if (request == NULL) { 7211 warn("%s: unable to allocate %zd bytes", __func__, 7212 sizeof(*request)); 7213 error = 1; 7214 goto bailout; 7215 } 7216 7217 response = malloc(sizeof(*response)); 7218 if (response == NULL) { 7219 warn("%s: unable to allocate %zd bytes", __func__, 7220 sizeof(*response)); 7221 error = 1; 7222 goto bailout; 7223 } 7224 7225 try_long: 7226 smp_report_general(&ccb->smpio, 7227 retry_count, 7228 /*cbfcnp*/ NULL, 7229 request, 7230 /*request_len*/ sizeof(*request), 7231 (uint8_t *)response, 7232 /*response_len*/ sizeof(*response), 7233 /*long_response*/ long_response, 7234 timeout); 7235 7236 if (((retval = cam_send_ccb(device, ccb)) < 0) 7237 || ((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP)) { 7238 const char warnstr[] = "error sending command"; 7239 7240 if (retval < 0) 7241 warn(warnstr); 7242 else 7243 warnx(warnstr); 7244 7245 if (arglist & CAM_ARG_VERBOSE) { 7246 cam_error_print(device, ccb, CAM_ESF_ALL, 7247 CAM_EPF_ALL, stderr); 7248 } 7249 error = 1; 7250 goto bailout; 7251 } 7252 7253 /* 7254 * If the device supports the long response bit, try again and see 7255 * if we can get all of the data. 7256 */ 7257 if ((response->long_response & SMP_RG_LONG_RESPONSE) 7258 && (long_response == 0)) { 7259 ccb->ccb_h.status = CAM_REQ_INPROG; 7260 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->smpio); 7261 long_response = 1; 7262 goto try_long; 7263 } 7264 7265 /* 7266 * XXX KDM detect and decode SMP errors here. 7267 */ 7268 sb = sbuf_new_auto(); 7269 if (sb == NULL) { 7270 warnx("%s: error allocating sbuf", __func__); 7271 goto bailout; 7272 } 7273 7274 smp_report_general_sbuf(response, sizeof(*response), sb); 7275 7276 if (sbuf_finish(sb) != 0) { 7277 warnx("%s: sbuf_finish", __func__); 7278 goto bailout; 7279 } 7280 7281 printf("%s", sbuf_data(sb)); 7282 7283 bailout: 7284 if (ccb != NULL) 7285 cam_freeccb(ccb); 7286 7287 if (request != NULL) 7288 free(request); 7289 7290 if (response != NULL) 7291 free(response); 7292 7293 if (sb != NULL) 7294 sbuf_delete(sb); 7295 7296 return (error); 7297 } 7298 7299 static struct camcontrol_opts phy_ops[] = { 7300 {"nop", SMP_PC_PHY_OP_NOP, CAM_ARG_NONE, NULL}, 7301 {"linkreset", SMP_PC_PHY_OP_LINK_RESET, CAM_ARG_NONE, NULL}, 7302 {"hardreset", SMP_PC_PHY_OP_HARD_RESET, CAM_ARG_NONE, NULL}, 7303 {"disable", SMP_PC_PHY_OP_DISABLE, CAM_ARG_NONE, NULL}, 7304 {"clearerrlog", SMP_PC_PHY_OP_CLEAR_ERR_LOG, CAM_ARG_NONE, NULL}, 7305 {"clearaffiliation", SMP_PC_PHY_OP_CLEAR_AFFILIATON, CAM_ARG_NONE,NULL}, 7306 {"sataportsel", SMP_PC_PHY_OP_TRANS_SATA_PSS, CAM_ARG_NONE, NULL}, 7307 {"clearitnl", SMP_PC_PHY_OP_CLEAR_STP_ITN_LS, CAM_ARG_NONE, NULL}, 7308 {"setdevname", SMP_PC_PHY_OP_SET_ATT_DEV_NAME, CAM_ARG_NONE, NULL}, 7309 {NULL, 0, 0, NULL} 7310 }; 7311 7312 static int 7313 smpphycontrol(struct cam_device *device, int argc, char **argv, 7314 char *combinedopt, int retry_count, int timeout) 7315 { 7316 union ccb *ccb; 7317 struct smp_phy_control_request *request = NULL; 7318 struct smp_phy_control_response *response = NULL; 7319 int long_response = 0; 7320 int retval = 0; 7321 int phy = -1; 7322 uint32_t phy_operation = SMP_PC_PHY_OP_NOP; 7323 int phy_op_set = 0; 7324 uint64_t attached_dev_name = 0; 7325 int dev_name_set = 0; 7326 uint32_t min_plr = 0, max_plr = 0; 7327 uint32_t pp_timeout_val = 0; 7328 int slumber_partial = 0; 7329 int set_pp_timeout_val = 0; 7330 int c; 7331 7332 /* 7333 * Note that at the moment we don't support sending SMP CCBs to 7334 * devices that aren't probed by CAM. 7335 */ 7336 ccb = cam_getccb(device); 7337 if (ccb == NULL) { 7338 warnx("%s: error allocating CCB", __func__); 7339 return (1); 7340 } 7341 7342 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->smpio); 7343 7344 while ((c = getopt(argc, argv, combinedopt)) != -1) { 7345 switch (c) { 7346 case 'a': 7347 case 'A': 7348 case 's': 7349 case 'S': { 7350 int enable = -1; 7351 7352 if (strcasecmp(optarg, "enable") == 0) 7353 enable = 1; 7354 else if (strcasecmp(optarg, "disable") == 0) 7355 enable = 2; 7356 else { 7357 warnx("%s: Invalid argument %s", __func__, 7358 optarg); 7359 retval = 1; 7360 goto bailout; 7361 } 7362 switch (c) { 7363 case 's': 7364 slumber_partial |= enable << 7365 SMP_PC_SAS_SLUMBER_SHIFT; 7366 break; 7367 case 'S': 7368 slumber_partial |= enable << 7369 SMP_PC_SAS_PARTIAL_SHIFT; 7370 break; 7371 case 'a': 7372 slumber_partial |= enable << 7373 SMP_PC_SATA_SLUMBER_SHIFT; 7374 break; 7375 case 'A': 7376 slumber_partial |= enable << 7377 SMP_PC_SATA_PARTIAL_SHIFT; 7378 break; 7379 default: 7380 warnx("%s: programmer error", __func__); 7381 retval = 1; 7382 goto bailout; 7383 break; /*NOTREACHED*/ 7384 } 7385 break; 7386 } 7387 case 'd': 7388 attached_dev_name = (uintmax_t)strtoumax(optarg, 7389 NULL,0); 7390 dev_name_set = 1; 7391 break; 7392 case 'l': 7393 long_response = 1; 7394 break; 7395 case 'm': 7396 /* 7397 * We don't do extensive checking here, so this 7398 * will continue to work when new speeds come out. 7399 */ 7400 min_plr = strtoul(optarg, NULL, 0); 7401 if ((min_plr == 0) 7402 || (min_plr > 0xf)) { 7403 warnx("%s: invalid link rate %x", 7404 __func__, min_plr); 7405 retval = 1; 7406 goto bailout; 7407 } 7408 break; 7409 case 'M': 7410 /* 7411 * We don't do extensive checking here, so this 7412 * will continue to work when new speeds come out. 7413 */ 7414 max_plr = strtoul(optarg, NULL, 0); 7415 if ((max_plr == 0) 7416 || (max_plr > 0xf)) { 7417 warnx("%s: invalid link rate %x", 7418 __func__, max_plr); 7419 retval = 1; 7420 goto bailout; 7421 } 7422 break; 7423 case 'o': { 7424 camcontrol_optret optreturn; 7425 cam_argmask argnums; 7426 const char *subopt; 7427 7428 if (phy_op_set != 0) { 7429 warnx("%s: only one phy operation argument " 7430 "(-o) allowed", __func__); 7431 retval = 1; 7432 goto bailout; 7433 } 7434 7435 phy_op_set = 1; 7436 7437 /* 7438 * Allow the user to specify the phy operation 7439 * numerically, as well as with a name. This will 7440 * future-proof it a bit, so options that are added 7441 * in future specs can be used. 7442 */ 7443 if (isdigit(optarg[0])) { 7444 phy_operation = strtoul(optarg, NULL, 0); 7445 if ((phy_operation == 0) 7446 || (phy_operation > 0xff)) { 7447 warnx("%s: invalid phy operation %#x", 7448 __func__, phy_operation); 7449 retval = 1; 7450 goto bailout; 7451 } 7452 break; 7453 } 7454 optreturn = getoption(phy_ops, optarg, &phy_operation, 7455 &argnums, &subopt); 7456 7457 if (optreturn == CC_OR_AMBIGUOUS) { 7458 warnx("%s: ambiguous option %s", __func__, 7459 optarg); 7460 usage(0); 7461 retval = 1; 7462 goto bailout; 7463 } else if (optreturn == CC_OR_NOT_FOUND) { 7464 warnx("%s: option %s not found", __func__, 7465 optarg); 7466 usage(0); 7467 retval = 1; 7468 goto bailout; 7469 } 7470 break; 7471 } 7472 case 'p': 7473 phy = atoi(optarg); 7474 break; 7475 case 'T': 7476 pp_timeout_val = strtoul(optarg, NULL, 0); 7477 if (pp_timeout_val > 15) { 7478 warnx("%s: invalid partial pathway timeout " 7479 "value %u, need a value less than 16", 7480 __func__, pp_timeout_val); 7481 retval = 1; 7482 goto bailout; 7483 } 7484 set_pp_timeout_val = 1; 7485 break; 7486 default: 7487 break; 7488 } 7489 } 7490 7491 if (phy == -1) { 7492 warnx("%s: a PHY (-p phy) argument is required",__func__); 7493 retval = 1; 7494 goto bailout; 7495 } 7496 7497 if (((dev_name_set != 0) 7498 && (phy_operation != SMP_PC_PHY_OP_SET_ATT_DEV_NAME)) 7499 || ((phy_operation == SMP_PC_PHY_OP_SET_ATT_DEV_NAME) 7500 && (dev_name_set == 0))) { 7501 warnx("%s: -d name and -o setdevname arguments both " 7502 "required to set device name", __func__); 7503 retval = 1; 7504 goto bailout; 7505 } 7506 7507 request = malloc(sizeof(*request)); 7508 if (request == NULL) { 7509 warn("%s: unable to allocate %zd bytes", __func__, 7510 sizeof(*request)); 7511 retval = 1; 7512 goto bailout; 7513 } 7514 7515 response = malloc(sizeof(*response)); 7516 if (response == NULL) { 7517 warn("%s: unable to allocate %zd bytes", __func__, 7518 sizeof(*response)); 7519 retval = 1; 7520 goto bailout; 7521 } 7522 7523 smp_phy_control(&ccb->smpio, 7524 retry_count, 7525 /*cbfcnp*/ NULL, 7526 request, 7527 sizeof(*request), 7528 (uint8_t *)response, 7529 sizeof(*response), 7530 long_response, 7531 /*expected_exp_change_count*/ 0, 7532 phy, 7533 phy_operation, 7534 (set_pp_timeout_val != 0) ? 1 : 0, 7535 attached_dev_name, 7536 min_plr, 7537 max_plr, 7538 slumber_partial, 7539 pp_timeout_val, 7540 timeout); 7541 7542 if (((retval = cam_send_ccb(device, ccb)) < 0) 7543 || ((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP)) { 7544 const char warnstr[] = "error sending command"; 7545 7546 if (retval < 0) 7547 warn(warnstr); 7548 else 7549 warnx(warnstr); 7550 7551 if (arglist & CAM_ARG_VERBOSE) { 7552 /* 7553 * Use CAM_EPF_NORMAL so we only get one line of 7554 * SMP command decoding. 7555 */ 7556 cam_error_print(device, ccb, CAM_ESF_ALL, 7557 CAM_EPF_NORMAL, stderr); 7558 } 7559 retval = 1; 7560 goto bailout; 7561 } 7562 7563 /* XXX KDM print out something here for success? */ 7564 bailout: 7565 if (ccb != NULL) 7566 cam_freeccb(ccb); 7567 7568 if (request != NULL) 7569 free(request); 7570 7571 if (response != NULL) 7572 free(response); 7573 7574 return (retval); 7575 } 7576 7577 static int 7578 smpmaninfo(struct cam_device *device, int argc, char **argv, 7579 char *combinedopt, int retry_count, int timeout) 7580 { 7581 union ccb *ccb; 7582 struct smp_report_manuf_info_request request; 7583 struct smp_report_manuf_info_response response; 7584 struct sbuf *sb = NULL; 7585 int long_response = 0; 7586 int retval = 0; 7587 int c; 7588 7589 /* 7590 * Note that at the moment we don't support sending SMP CCBs to 7591 * devices that aren't probed by CAM. 7592 */ 7593 ccb = cam_getccb(device); 7594 if (ccb == NULL) { 7595 warnx("%s: error allocating CCB", __func__); 7596 return (1); 7597 } 7598 7599 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->smpio); 7600 7601 while ((c = getopt(argc, argv, combinedopt)) != -1) { 7602 switch (c) { 7603 case 'l': 7604 long_response = 1; 7605 break; 7606 default: 7607 break; 7608 } 7609 } 7610 bzero(&request, sizeof(request)); 7611 bzero(&response, sizeof(response)); 7612 7613 smp_report_manuf_info(&ccb->smpio, 7614 retry_count, 7615 /*cbfcnp*/ NULL, 7616 &request, 7617 sizeof(request), 7618 (uint8_t *)&response, 7619 sizeof(response), 7620 long_response, 7621 timeout); 7622 7623 if (((retval = cam_send_ccb(device, ccb)) < 0) 7624 || ((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP)) { 7625 const char warnstr[] = "error sending command"; 7626 7627 if (retval < 0) 7628 warn(warnstr); 7629 else 7630 warnx(warnstr); 7631 7632 if (arglist & CAM_ARG_VERBOSE) { 7633 cam_error_print(device, ccb, CAM_ESF_ALL, 7634 CAM_EPF_ALL, stderr); 7635 } 7636 retval = 1; 7637 goto bailout; 7638 } 7639 7640 sb = sbuf_new_auto(); 7641 if (sb == NULL) { 7642 warnx("%s: error allocating sbuf", __func__); 7643 goto bailout; 7644 } 7645 7646 smp_report_manuf_info_sbuf(&response, sizeof(response), sb); 7647 7648 if (sbuf_finish(sb) != 0) { 7649 warnx("%s: sbuf_finish", __func__); 7650 goto bailout; 7651 } 7652 7653 printf("%s", sbuf_data(sb)); 7654 7655 bailout: 7656 7657 if (ccb != NULL) 7658 cam_freeccb(ccb); 7659 7660 if (sb != NULL) 7661 sbuf_delete(sb); 7662 7663 return (retval); 7664 } 7665 7666 static int 7667 getdevid(struct cam_devitem *item) 7668 { 7669 int retval = 0; 7670 union ccb *ccb = NULL; 7671 7672 struct cam_device *dev; 7673 7674 dev = cam_open_btl(item->dev_match.path_id, 7675 item->dev_match.target_id, 7676 item->dev_match.target_lun, O_RDWR, NULL); 7677 7678 if (dev == NULL) { 7679 warnx("%s", cam_errbuf); 7680 retval = 1; 7681 goto bailout; 7682 } 7683 7684 item->device_id_len = 0; 7685 7686 ccb = cam_getccb(dev); 7687 if (ccb == NULL) { 7688 warnx("%s: error allocating CCB", __func__); 7689 retval = 1; 7690 goto bailout; 7691 } 7692 7693 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->cdai); 7694 7695 /* 7696 * On the first try, we just probe for the size of the data, and 7697 * then allocate that much memory and try again. 7698 */ 7699 retry: 7700 ccb->ccb_h.func_code = XPT_DEV_ADVINFO; 7701 ccb->ccb_h.flags = CAM_DIR_IN; 7702 ccb->cdai.flags = CDAI_FLAG_NONE; 7703 ccb->cdai.buftype = CDAI_TYPE_SCSI_DEVID; 7704 ccb->cdai.bufsiz = item->device_id_len; 7705 if (item->device_id_len != 0) 7706 ccb->cdai.buf = (uint8_t *)item->device_id; 7707 7708 if (cam_send_ccb(dev, ccb) < 0) { 7709 warn("%s: error sending XPT_GDEV_ADVINFO CCB", __func__); 7710 retval = 1; 7711 goto bailout; 7712 } 7713 7714 if (ccb->ccb_h.status != CAM_REQ_CMP) { 7715 warnx("%s: CAM status %#x", __func__, ccb->ccb_h.status); 7716 retval = 1; 7717 goto bailout; 7718 } 7719 7720 if (item->device_id_len == 0) { 7721 /* 7722 * This is our first time through. Allocate the buffer, 7723 * and then go back to get the data. 7724 */ 7725 if (ccb->cdai.provsiz == 0) { 7726 warnx("%s: invalid .provsiz field returned with " 7727 "XPT_GDEV_ADVINFO CCB", __func__); 7728 retval = 1; 7729 goto bailout; 7730 } 7731 item->device_id_len = ccb->cdai.provsiz; 7732 item->device_id = malloc(item->device_id_len); 7733 if (item->device_id == NULL) { 7734 warn("%s: unable to allocate %d bytes", __func__, 7735 item->device_id_len); 7736 retval = 1; 7737 goto bailout; 7738 } 7739 ccb->ccb_h.status = CAM_REQ_INPROG; 7740 goto retry; 7741 } 7742 7743 bailout: 7744 if (dev != NULL) 7745 cam_close_device(dev); 7746 7747 if (ccb != NULL) 7748 cam_freeccb(ccb); 7749 7750 return (retval); 7751 } 7752 7753 /* 7754 * XXX KDM merge this code with getdevtree()? 7755 */ 7756 static int 7757 buildbusdevlist(struct cam_devlist *devlist) 7758 { 7759 union ccb ccb; 7760 int bufsize, fd = -1; 7761 struct dev_match_pattern *patterns; 7762 struct cam_devitem *item = NULL; 7763 int skip_device = 0; 7764 int retval = 0; 7765 7766 if ((fd = open(XPT_DEVICE, O_RDWR)) == -1) { 7767 warn("couldn't open %s", XPT_DEVICE); 7768 return(1); 7769 } 7770 7771 bzero(&ccb, sizeof(union ccb)); 7772 7773 ccb.ccb_h.path_id = CAM_XPT_PATH_ID; 7774 ccb.ccb_h.target_id = CAM_TARGET_WILDCARD; 7775 ccb.ccb_h.target_lun = CAM_LUN_WILDCARD; 7776 7777 ccb.ccb_h.func_code = XPT_DEV_MATCH; 7778 bufsize = sizeof(struct dev_match_result) * 100; 7779 ccb.cdm.match_buf_len = bufsize; 7780 ccb.cdm.matches = (struct dev_match_result *)malloc(bufsize); 7781 if (ccb.cdm.matches == NULL) { 7782 warnx("can't malloc memory for matches"); 7783 close(fd); 7784 return(1); 7785 } 7786 ccb.cdm.num_matches = 0; 7787 ccb.cdm.num_patterns = 2; 7788 ccb.cdm.pattern_buf_len = sizeof(struct dev_match_pattern) * 7789 ccb.cdm.num_patterns; 7790 7791 patterns = (struct dev_match_pattern *)malloc(ccb.cdm.pattern_buf_len); 7792 if (patterns == NULL) { 7793 warnx("can't malloc memory for patterns"); 7794 retval = 1; 7795 goto bailout; 7796 } 7797 7798 ccb.cdm.patterns = patterns; 7799 bzero(patterns, ccb.cdm.pattern_buf_len); 7800 7801 patterns[0].type = DEV_MATCH_DEVICE; 7802 patterns[0].pattern.device_pattern.flags = DEV_MATCH_PATH; 7803 patterns[0].pattern.device_pattern.path_id = devlist->path_id; 7804 patterns[1].type = DEV_MATCH_PERIPH; 7805 patterns[1].pattern.periph_pattern.flags = PERIPH_MATCH_PATH; 7806 patterns[1].pattern.periph_pattern.path_id = devlist->path_id; 7807 7808 /* 7809 * We do the ioctl multiple times if necessary, in case there are 7810 * more than 100 nodes in the EDT. 7811 */ 7812 do { 7813 unsigned int i; 7814 7815 if (ioctl(fd, CAMIOCOMMAND, &ccb) == -1) { 7816 warn("error sending CAMIOCOMMAND ioctl"); 7817 retval = 1; 7818 goto bailout; 7819 } 7820 7821 if ((ccb.ccb_h.status != CAM_REQ_CMP) 7822 || ((ccb.cdm.status != CAM_DEV_MATCH_LAST) 7823 && (ccb.cdm.status != CAM_DEV_MATCH_MORE))) { 7824 warnx("got CAM error %#x, CDM error %d\n", 7825 ccb.ccb_h.status, ccb.cdm.status); 7826 retval = 1; 7827 goto bailout; 7828 } 7829 7830 for (i = 0; i < ccb.cdm.num_matches; i++) { 7831 switch (ccb.cdm.matches[i].type) { 7832 case DEV_MATCH_DEVICE: { 7833 struct device_match_result *dev_result; 7834 7835 dev_result = 7836 &ccb.cdm.matches[i].result.device_result; 7837 7838 if (dev_result->flags & 7839 DEV_RESULT_UNCONFIGURED) { 7840 skip_device = 1; 7841 break; 7842 } else 7843 skip_device = 0; 7844 7845 item = malloc(sizeof(*item)); 7846 if (item == NULL) { 7847 warn("%s: unable to allocate %zd bytes", 7848 __func__, sizeof(*item)); 7849 retval = 1; 7850 goto bailout; 7851 } 7852 bzero(item, sizeof(*item)); 7853 bcopy(dev_result, &item->dev_match, 7854 sizeof(*dev_result)); 7855 STAILQ_INSERT_TAIL(&devlist->dev_queue, item, 7856 links); 7857 7858 if (getdevid(item) != 0) { 7859 retval = 1; 7860 goto bailout; 7861 } 7862 break; 7863 } 7864 case DEV_MATCH_PERIPH: { 7865 struct periph_match_result *periph_result; 7866 7867 periph_result = 7868 &ccb.cdm.matches[i].result.periph_result; 7869 7870 if (skip_device != 0) 7871 break; 7872 item->num_periphs++; 7873 item->periph_matches = realloc( 7874 item->periph_matches, 7875 item->num_periphs * 7876 sizeof(struct periph_match_result)); 7877 if (item->periph_matches == NULL) { 7878 warn("%s: error allocating periph " 7879 "list", __func__); 7880 retval = 1; 7881 goto bailout; 7882 } 7883 bcopy(periph_result, &item->periph_matches[ 7884 item->num_periphs - 1], 7885 sizeof(*periph_result)); 7886 break; 7887 } 7888 default: 7889 fprintf(stderr, "%s: unexpected match " 7890 "type %d\n", __func__, 7891 ccb.cdm.matches[i].type); 7892 retval = 1; 7893 goto bailout; 7894 break; /*NOTREACHED*/ 7895 } 7896 } 7897 } while ((ccb.ccb_h.status == CAM_REQ_CMP) 7898 && (ccb.cdm.status == CAM_DEV_MATCH_MORE)); 7899 bailout: 7900 7901 if (fd != -1) 7902 close(fd); 7903 7904 free(patterns); 7905 7906 free(ccb.cdm.matches); 7907 7908 if (retval != 0) 7909 freebusdevlist(devlist); 7910 7911 return (retval); 7912 } 7913 7914 static void 7915 freebusdevlist(struct cam_devlist *devlist) 7916 { 7917 struct cam_devitem *item, *item2; 7918 7919 STAILQ_FOREACH_SAFE(item, &devlist->dev_queue, links, item2) { 7920 STAILQ_REMOVE(&devlist->dev_queue, item, cam_devitem, 7921 links); 7922 free(item->device_id); 7923 free(item->periph_matches); 7924 free(item); 7925 } 7926 } 7927 7928 static struct cam_devitem * 7929 findsasdevice(struct cam_devlist *devlist, uint64_t sasaddr) 7930 { 7931 struct cam_devitem *item; 7932 7933 STAILQ_FOREACH(item, &devlist->dev_queue, links) { 7934 struct scsi_vpd_id_descriptor *idd; 7935 7936 /* 7937 * XXX KDM look for LUN IDs as well? 7938 */ 7939 idd = scsi_get_devid(item->device_id, 7940 item->device_id_len, 7941 scsi_devid_is_sas_target); 7942 if (idd == NULL) 7943 continue; 7944 7945 if (scsi_8btou64(idd->identifier) == sasaddr) 7946 return (item); 7947 } 7948 7949 return (NULL); 7950 } 7951 7952 static int 7953 smpphylist(struct cam_device *device, int argc, char **argv, 7954 char *combinedopt, int retry_count, int timeout) 7955 { 7956 struct smp_report_general_request *rgrequest = NULL; 7957 struct smp_report_general_response *rgresponse = NULL; 7958 struct smp_discover_request *disrequest = NULL; 7959 struct smp_discover_response *disresponse = NULL; 7960 struct cam_devlist devlist; 7961 union ccb *ccb; 7962 int long_response = 0; 7963 int num_phys = 0; 7964 int quiet = 0; 7965 int retval; 7966 int i, c; 7967 7968 /* 7969 * Note that at the moment we don't support sending SMP CCBs to 7970 * devices that aren't probed by CAM. 7971 */ 7972 ccb = cam_getccb(device); 7973 if (ccb == NULL) { 7974 warnx("%s: error allocating CCB", __func__); 7975 return (1); 7976 } 7977 7978 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->smpio); 7979 STAILQ_INIT(&devlist.dev_queue); 7980 7981 rgrequest = malloc(sizeof(*rgrequest)); 7982 if (rgrequest == NULL) { 7983 warn("%s: unable to allocate %zd bytes", __func__, 7984 sizeof(*rgrequest)); 7985 retval = 1; 7986 goto bailout; 7987 } 7988 7989 rgresponse = malloc(sizeof(*rgresponse)); 7990 if (rgresponse == NULL) { 7991 warn("%s: unable to allocate %zd bytes", __func__, 7992 sizeof(*rgresponse)); 7993 retval = 1; 7994 goto bailout; 7995 } 7996 7997 while ((c = getopt(argc, argv, combinedopt)) != -1) { 7998 switch (c) { 7999 case 'l': 8000 long_response = 1; 8001 break; 8002 case 'q': 8003 quiet = 1; 8004 break; 8005 default: 8006 break; 8007 } 8008 } 8009 8010 smp_report_general(&ccb->smpio, 8011 retry_count, 8012 /*cbfcnp*/ NULL, 8013 rgrequest, 8014 /*request_len*/ sizeof(*rgrequest), 8015 (uint8_t *)rgresponse, 8016 /*response_len*/ sizeof(*rgresponse), 8017 /*long_response*/ long_response, 8018 timeout); 8019 8020 ccb->ccb_h.flags |= CAM_DEV_QFRZDIS; 8021 8022 if (((retval = cam_send_ccb(device, ccb)) < 0) 8023 || ((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP)) { 8024 const char warnstr[] = "error sending command"; 8025 8026 if (retval < 0) 8027 warn(warnstr); 8028 else 8029 warnx(warnstr); 8030 8031 if (arglist & CAM_ARG_VERBOSE) { 8032 cam_error_print(device, ccb, CAM_ESF_ALL, 8033 CAM_EPF_ALL, stderr); 8034 } 8035 retval = 1; 8036 goto bailout; 8037 } 8038 8039 num_phys = rgresponse->num_phys; 8040 8041 if (num_phys == 0) { 8042 if (quiet == 0) 8043 fprintf(stdout, "%s: No Phys reported\n", __func__); 8044 retval = 1; 8045 goto bailout; 8046 } 8047 8048 devlist.path_id = device->path_id; 8049 8050 retval = buildbusdevlist(&devlist); 8051 if (retval != 0) 8052 goto bailout; 8053 8054 if (quiet == 0) { 8055 fprintf(stdout, "%d PHYs:\n", num_phys); 8056 fprintf(stdout, "PHY Attached SAS Address\n"); 8057 } 8058 8059 disrequest = malloc(sizeof(*disrequest)); 8060 if (disrequest == NULL) { 8061 warn("%s: unable to allocate %zd bytes", __func__, 8062 sizeof(*disrequest)); 8063 retval = 1; 8064 goto bailout; 8065 } 8066 8067 disresponse = malloc(sizeof(*disresponse)); 8068 if (disresponse == NULL) { 8069 warn("%s: unable to allocate %zd bytes", __func__, 8070 sizeof(*disresponse)); 8071 retval = 1; 8072 goto bailout; 8073 } 8074 8075 for (i = 0; i < num_phys; i++) { 8076 struct cam_devitem *item; 8077 struct device_match_result *dev_match; 8078 char vendor[16], product[48], revision[16]; 8079 char tmpstr[256]; 8080 int j; 8081 8082 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->smpio); 8083 8084 ccb->ccb_h.status = CAM_REQ_INPROG; 8085 ccb->ccb_h.flags |= CAM_DEV_QFRZDIS; 8086 8087 smp_discover(&ccb->smpio, 8088 retry_count, 8089 /*cbfcnp*/ NULL, 8090 disrequest, 8091 sizeof(*disrequest), 8092 (uint8_t *)disresponse, 8093 sizeof(*disresponse), 8094 long_response, 8095 /*ignore_zone_group*/ 0, 8096 /*phy*/ i, 8097 timeout); 8098 8099 if (((retval = cam_send_ccb(device, ccb)) < 0) 8100 || (((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP) 8101 && (disresponse->function_result != SMP_FR_PHY_VACANT))) { 8102 const char warnstr[] = "error sending command"; 8103 8104 if (retval < 0) 8105 warn(warnstr); 8106 else 8107 warnx(warnstr); 8108 8109 if (arglist & CAM_ARG_VERBOSE) { 8110 cam_error_print(device, ccb, CAM_ESF_ALL, 8111 CAM_EPF_ALL, stderr); 8112 } 8113 retval = 1; 8114 goto bailout; 8115 } 8116 8117 if (disresponse->function_result == SMP_FR_PHY_VACANT) { 8118 if (quiet == 0) 8119 fprintf(stdout, "%3d <vacant>\n", i); 8120 continue; 8121 } 8122 8123 if (disresponse->attached_device == SMP_DIS_AD_TYPE_NONE) { 8124 item = NULL; 8125 } else { 8126 item = findsasdevice(&devlist, 8127 scsi_8btou64(disresponse->attached_sas_address)); 8128 } 8129 8130 if ((quiet == 0) 8131 || (item != NULL)) { 8132 fprintf(stdout, "%3d 0x%016jx", i, 8133 (uintmax_t)scsi_8btou64( 8134 disresponse->attached_sas_address)); 8135 if (item == NULL) { 8136 fprintf(stdout, "\n"); 8137 continue; 8138 } 8139 } else if (quiet != 0) 8140 continue; 8141 8142 dev_match = &item->dev_match; 8143 8144 if (dev_match->protocol == PROTO_SCSI) { 8145 cam_strvis(vendor, dev_match->inq_data.vendor, 8146 sizeof(dev_match->inq_data.vendor), 8147 sizeof(vendor)); 8148 cam_strvis(product, dev_match->inq_data.product, 8149 sizeof(dev_match->inq_data.product), 8150 sizeof(product)); 8151 cam_strvis(revision, dev_match->inq_data.revision, 8152 sizeof(dev_match->inq_data.revision), 8153 sizeof(revision)); 8154 sprintf(tmpstr, "<%s %s %s>", vendor, product, 8155 revision); 8156 } else if ((dev_match->protocol == PROTO_ATA) 8157 || (dev_match->protocol == PROTO_SATAPM)) { 8158 cam_strvis(product, dev_match->ident_data.model, 8159 sizeof(dev_match->ident_data.model), 8160 sizeof(product)); 8161 cam_strvis(revision, dev_match->ident_data.revision, 8162 sizeof(dev_match->ident_data.revision), 8163 sizeof(revision)); 8164 sprintf(tmpstr, "<%s %s>", product, revision); 8165 } else { 8166 sprintf(tmpstr, "<>"); 8167 } 8168 fprintf(stdout, " %-33s ", tmpstr); 8169 8170 /* 8171 * If we have 0 periphs, that's a bug... 8172 */ 8173 if (item->num_periphs == 0) { 8174 fprintf(stdout, "\n"); 8175 continue; 8176 } 8177 8178 fprintf(stdout, "("); 8179 for (j = 0; j < item->num_periphs; j++) { 8180 if (j > 0) 8181 fprintf(stdout, ","); 8182 8183 fprintf(stdout, "%s%d", 8184 item->periph_matches[j].periph_name, 8185 item->periph_matches[j].unit_number); 8186 8187 } 8188 fprintf(stdout, ")\n"); 8189 } 8190 bailout: 8191 if (ccb != NULL) 8192 cam_freeccb(ccb); 8193 8194 free(rgrequest); 8195 8196 free(rgresponse); 8197 8198 free(disrequest); 8199 8200 free(disresponse); 8201 8202 freebusdevlist(&devlist); 8203 8204 return (retval); 8205 } 8206 8207 static int 8208 atapm(struct cam_device *device, int argc, char **argv, 8209 char *combinedopt, int retry_count, int timeout) 8210 { 8211 union ccb *ccb; 8212 int retval = 0; 8213 int t = -1; 8214 int c; 8215 u_char cmd, sc; 8216 8217 ccb = cam_getccb(device); 8218 8219 if (ccb == NULL) { 8220 warnx("%s: error allocating ccb", __func__); 8221 return (1); 8222 } 8223 8224 while ((c = getopt(argc, argv, combinedopt)) != -1) { 8225 switch (c) { 8226 case 't': 8227 t = atoi(optarg); 8228 break; 8229 default: 8230 break; 8231 } 8232 } 8233 if (strcmp(argv[1], "idle") == 0) { 8234 if (t == -1) 8235 cmd = ATA_IDLE_IMMEDIATE; 8236 else 8237 cmd = ATA_IDLE_CMD; 8238 } else if (strcmp(argv[1], "standby") == 0) { 8239 if (t == -1) 8240 cmd = ATA_STANDBY_IMMEDIATE; 8241 else 8242 cmd = ATA_STANDBY_CMD; 8243 } else { 8244 cmd = ATA_SLEEP; 8245 t = -1; 8246 } 8247 8248 if (t < 0) 8249 sc = 0; 8250 else if (t <= (240 * 5)) 8251 sc = (t + 4) / 5; 8252 else if (t <= (252 * 5)) 8253 /* special encoding for 21 minutes */ 8254 sc = 252; 8255 else if (t <= (11 * 30 * 60)) 8256 sc = (t - 1) / (30 * 60) + 241; 8257 else 8258 sc = 253; 8259 8260 retval = ata_do_28bit_cmd(device, 8261 ccb, 8262 /*retries*/retry_count, 8263 /*flags*/CAM_DIR_NONE, 8264 /*protocol*/AP_PROTO_NON_DATA, 8265 /*tag_action*/MSG_SIMPLE_Q_TAG, 8266 /*command*/cmd, 8267 /*features*/0, 8268 /*lba*/0, 8269 /*sector_count*/sc, 8270 /*data_ptr*/NULL, 8271 /*dxfer_len*/0, 8272 /*timeout*/timeout ? timeout : 30 * 1000, 8273 /*quiet*/1); 8274 8275 cam_freeccb(ccb); 8276 return (retval); 8277 } 8278 8279 static int 8280 ataaxm(struct cam_device *device, int argc, char **argv, 8281 char *combinedopt, int retry_count, int timeout) 8282 { 8283 union ccb *ccb; 8284 int retval = 0; 8285 int l = -1; 8286 int c; 8287 u_char cmd, sc; 8288 8289 ccb = cam_getccb(device); 8290 8291 if (ccb == NULL) { 8292 warnx("%s: error allocating ccb", __func__); 8293 return (1); 8294 } 8295 8296 while ((c = getopt(argc, argv, combinedopt)) != -1) { 8297 switch (c) { 8298 case 'l': 8299 l = atoi(optarg); 8300 break; 8301 default: 8302 break; 8303 } 8304 } 8305 sc = 0; 8306 if (strcmp(argv[1], "apm") == 0) { 8307 if (l == -1) 8308 cmd = 0x85; 8309 else { 8310 cmd = 0x05; 8311 sc = l; 8312 } 8313 } else /* aam */ { 8314 if (l == -1) 8315 cmd = 0xC2; 8316 else { 8317 cmd = 0x42; 8318 sc = l; 8319 } 8320 } 8321 8322 retval = ata_do_28bit_cmd(device, 8323 ccb, 8324 /*retries*/retry_count, 8325 /*flags*/CAM_DIR_NONE, 8326 /*protocol*/AP_PROTO_NON_DATA, 8327 /*tag_action*/MSG_SIMPLE_Q_TAG, 8328 /*command*/ATA_SETFEATURES, 8329 /*features*/cmd, 8330 /*lba*/0, 8331 /*sector_count*/sc, 8332 /*data_ptr*/NULL, 8333 /*dxfer_len*/0, 8334 /*timeout*/timeout ? timeout : 30 * 1000, 8335 /*quiet*/1); 8336 8337 cam_freeccb(ccb); 8338 return (retval); 8339 } 8340 8341 int 8342 scsigetopcodes(struct cam_device *device, int opcode_set, int opcode, 8343 int show_sa_errors, int sa_set, int service_action, 8344 int timeout_desc, int retry_count, int timeout, int verbosemode, 8345 uint32_t *fill_len, uint8_t **data_ptr) 8346 { 8347 union ccb *ccb = NULL; 8348 uint8_t *buf = NULL; 8349 uint32_t alloc_len = 0, num_opcodes; 8350 uint32_t valid_len = 0; 8351 uint32_t avail_len = 0; 8352 struct scsi_report_supported_opcodes_all *all_hdr; 8353 struct scsi_report_supported_opcodes_one *one; 8354 int options = 0; 8355 int retval = 0; 8356 8357 /* 8358 * Make it clear that we haven't yet allocated or filled anything. 8359 */ 8360 *fill_len = 0; 8361 *data_ptr = NULL; 8362 8363 ccb = cam_getccb(device); 8364 if (ccb == NULL) { 8365 warnx("couldn't allocate CCB"); 8366 retval = 1; 8367 goto bailout; 8368 } 8369 8370 /* cam_getccb cleans up the header, caller has to zero the payload */ 8371 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->csio); 8372 8373 if (opcode_set != 0) { 8374 options |= RSO_OPTIONS_OC; 8375 num_opcodes = 1; 8376 alloc_len = sizeof(*one) + CAM_MAX_CDBLEN; 8377 } else { 8378 num_opcodes = 256; 8379 alloc_len = sizeof(*all_hdr) + (num_opcodes * 8380 sizeof(struct scsi_report_supported_opcodes_descr)); 8381 } 8382 8383 if (timeout_desc != 0) { 8384 options |= RSO_RCTD; 8385 alloc_len += num_opcodes * 8386 sizeof(struct scsi_report_supported_opcodes_timeout); 8387 } 8388 8389 if (sa_set != 0) { 8390 options |= RSO_OPTIONS_OC_SA; 8391 if (show_sa_errors != 0) 8392 options &= ~RSO_OPTIONS_OC; 8393 } 8394 8395 retry_alloc: 8396 if (buf != NULL) { 8397 free(buf); 8398 buf = NULL; 8399 } 8400 8401 buf = malloc(alloc_len); 8402 if (buf == NULL) { 8403 warn("Unable to allocate %u bytes", alloc_len); 8404 retval = 1; 8405 goto bailout; 8406 } 8407 bzero(buf, alloc_len); 8408 8409 scsi_report_supported_opcodes(&ccb->csio, 8410 /*retries*/ retry_count, 8411 /*cbfcnp*/ NULL, 8412 /*tag_action*/ MSG_SIMPLE_Q_TAG, 8413 /*options*/ options, 8414 /*req_opcode*/ opcode, 8415 /*req_service_action*/ service_action, 8416 /*data_ptr*/ buf, 8417 /*dxfer_len*/ alloc_len, 8418 /*sense_len*/ SSD_FULL_SIZE, 8419 /*timeout*/ timeout ? timeout : 10000); 8420 8421 ccb->ccb_h.flags |= CAM_DEV_QFRZDIS; 8422 8423 if (retry_count != 0) 8424 ccb->ccb_h.flags |= CAM_PASS_ERR_RECOVER; 8425 8426 if (cam_send_ccb(device, ccb) < 0) { 8427 perror("error sending REPORT SUPPORTED OPERATION CODES"); 8428 retval = 1; 8429 goto bailout; 8430 } 8431 8432 if ((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP) { 8433 if (verbosemode != 0) 8434 cam_error_print(device, ccb, CAM_ESF_ALL, 8435 CAM_EPF_ALL, stderr); 8436 8437 retval = 1; 8438 goto bailout; 8439 } 8440 8441 valid_len = ccb->csio.dxfer_len - ccb->csio.resid; 8442 8443 if (((options & RSO_OPTIONS_MASK) == RSO_OPTIONS_ALL) 8444 && (valid_len >= sizeof(*all_hdr))) { 8445 all_hdr = (struct scsi_report_supported_opcodes_all *)buf; 8446 avail_len = scsi_4btoul(all_hdr->length) + sizeof(*all_hdr); 8447 } else if (((options & RSO_OPTIONS_MASK) != RSO_OPTIONS_ALL) 8448 && (valid_len >= sizeof(*one))) { 8449 uint32_t cdb_length; 8450 8451 one = (struct scsi_report_supported_opcodes_one *)buf; 8452 cdb_length = scsi_2btoul(one->cdb_length); 8453 avail_len = sizeof(*one) + cdb_length; 8454 if (one->support & RSO_ONE_CTDP) { 8455 struct scsi_report_supported_opcodes_timeout *td; 8456 8457 td = (struct scsi_report_supported_opcodes_timeout *) 8458 &buf[avail_len]; 8459 if (valid_len >= (avail_len + sizeof(td->length))) { 8460 avail_len += scsi_2btoul(td->length) + 8461 sizeof(td->length); 8462 } else { 8463 avail_len += sizeof(*td); 8464 } 8465 } 8466 } 8467 8468 /* 8469 * avail_len could be zero if we didn't get enough data back from 8470 * thet target to determine 8471 */ 8472 if ((avail_len != 0) 8473 && (avail_len > valid_len)) { 8474 alloc_len = avail_len; 8475 goto retry_alloc; 8476 } 8477 8478 *fill_len = valid_len; 8479 *data_ptr = buf; 8480 bailout: 8481 if (retval != 0) 8482 free(buf); 8483 8484 cam_freeccb(ccb); 8485 8486 return (retval); 8487 } 8488 8489 static int 8490 scsiprintoneopcode(struct cam_device *device, int req_opcode, int sa_set, 8491 int req_sa, uint8_t *buf, uint32_t valid_len) 8492 { 8493 struct scsi_report_supported_opcodes_one *one; 8494 struct scsi_report_supported_opcodes_timeout *td; 8495 uint32_t cdb_len = 0, td_len = 0; 8496 const char *op_desc = NULL; 8497 unsigned int i; 8498 int retval = 0; 8499 8500 one = (struct scsi_report_supported_opcodes_one *)buf; 8501 8502 /* 8503 * If we don't have the full single opcode descriptor, no point in 8504 * continuing. 8505 */ 8506 if (valid_len < __offsetof(struct scsi_report_supported_opcodes_one, 8507 cdb_length)) { 8508 warnx("Only %u bytes returned, not enough to verify support", 8509 valid_len); 8510 retval = 1; 8511 goto bailout; 8512 } 8513 8514 op_desc = scsi_op_desc(req_opcode, &device->inq_data); 8515 8516 printf("%s (0x%02x)", op_desc != NULL ? op_desc : "UNKNOWN", 8517 req_opcode); 8518 if (sa_set != 0) 8519 printf(", SA 0x%x", req_sa); 8520 printf(": "); 8521 8522 switch (one->support & RSO_ONE_SUP_MASK) { 8523 case RSO_ONE_SUP_UNAVAIL: 8524 printf("No command support information currently available\n"); 8525 break; 8526 case RSO_ONE_SUP_NOT_SUP: 8527 printf("Command not supported\n"); 8528 retval = 1; 8529 goto bailout; 8530 break; /*NOTREACHED*/ 8531 case RSO_ONE_SUP_AVAIL: 8532 printf("Command is supported, complies with a SCSI standard\n"); 8533 break; 8534 case RSO_ONE_SUP_VENDOR: 8535 printf("Command is supported, vendor-specific " 8536 "implementation\n"); 8537 break; 8538 default: 8539 printf("Unknown command support flags 0x%#x\n", 8540 one->support & RSO_ONE_SUP_MASK); 8541 break; 8542 } 8543 8544 /* 8545 * If we don't have the CDB length, it isn't exactly an error, the 8546 * command probably isn't supported. 8547 */ 8548 if (valid_len < __offsetof(struct scsi_report_supported_opcodes_one, 8549 cdb_usage)) 8550 goto bailout; 8551 8552 cdb_len = scsi_2btoul(one->cdb_length); 8553 8554 /* 8555 * If our valid data doesn't include the full reported length, 8556 * return. The caller should have detected this and adjusted his 8557 * allocation length to get all of the available data. 8558 */ 8559 if (valid_len < sizeof(*one) + cdb_len) { 8560 retval = 1; 8561 goto bailout; 8562 } 8563 8564 /* 8565 * If all we have is the opcode, there is no point in printing out 8566 * the usage bitmap. 8567 */ 8568 if (cdb_len <= 1) { 8569 retval = 1; 8570 goto bailout; 8571 } 8572 8573 printf("CDB usage bitmap:"); 8574 for (i = 0; i < cdb_len; i++) { 8575 printf(" %02x", one->cdb_usage[i]); 8576 } 8577 printf("\n"); 8578 8579 /* 8580 * If we don't have a timeout descriptor, we're done. 8581 */ 8582 if ((one->support & RSO_ONE_CTDP) == 0) 8583 goto bailout; 8584 8585 /* 8586 * If we don't have enough valid length to include the timeout 8587 * descriptor length, we're done. 8588 */ 8589 if (valid_len < (sizeof(*one) + cdb_len + sizeof(td->length))) 8590 goto bailout; 8591 8592 td = (struct scsi_report_supported_opcodes_timeout *) 8593 &buf[sizeof(*one) + cdb_len]; 8594 td_len = scsi_2btoul(td->length); 8595 td_len += sizeof(td->length); 8596 8597 /* 8598 * If we don't have the full timeout descriptor, we're done. 8599 */ 8600 if (td_len < sizeof(*td)) 8601 goto bailout; 8602 8603 /* 8604 * If we don't have enough valid length to contain the full timeout 8605 * descriptor, we're done. 8606 */ 8607 if (valid_len < (sizeof(*one) + cdb_len + td_len)) 8608 goto bailout; 8609 8610 printf("Timeout information:\n"); 8611 printf("Command-specific: 0x%02x\n", td->cmd_specific); 8612 printf("Nominal timeout: %u seconds\n", 8613 scsi_4btoul(td->nominal_time)); 8614 printf("Recommended timeout: %u seconds\n", 8615 scsi_4btoul(td->recommended_time)); 8616 8617 bailout: 8618 return (retval); 8619 } 8620 8621 static int 8622 scsiprintopcodes(struct cam_device *device, int td_req, uint8_t *buf, 8623 uint32_t valid_len) 8624 { 8625 struct scsi_report_supported_opcodes_all *hdr; 8626 struct scsi_report_supported_opcodes_descr *desc; 8627 uint32_t avail_len = 0, used_len = 0; 8628 uint8_t *cur_ptr; 8629 int retval = 0; 8630 8631 if (valid_len < sizeof(*hdr)) { 8632 warnx("%s: not enough returned data (%u bytes) opcode list", 8633 __func__, valid_len); 8634 retval = 1; 8635 goto bailout; 8636 } 8637 hdr = (struct scsi_report_supported_opcodes_all *)buf; 8638 avail_len = scsi_4btoul(hdr->length); 8639 avail_len += sizeof(hdr->length); 8640 /* 8641 * Take the lesser of the amount of data the drive claims is 8642 * available, and the amount of data the HBA says was returned. 8643 */ 8644 avail_len = MIN(avail_len, valid_len); 8645 8646 used_len = sizeof(hdr->length); 8647 8648 printf("%-6s %4s %8s ", 8649 "Opcode", "SA", "CDB len" ); 8650 8651 if (td_req != 0) 8652 printf("%5s %6s %6s ", "CS", "Nom", "Rec"); 8653 printf(" Description\n"); 8654 8655 while ((avail_len - used_len) > sizeof(*desc)) { 8656 struct scsi_report_supported_opcodes_timeout *td; 8657 uint32_t td_len; 8658 const char *op_desc = NULL; 8659 8660 cur_ptr = &buf[used_len]; 8661 desc = (struct scsi_report_supported_opcodes_descr *)cur_ptr; 8662 8663 op_desc = scsi_op_desc(desc->opcode, &device->inq_data); 8664 if (op_desc == NULL) 8665 op_desc = "UNKNOWN"; 8666 8667 printf("0x%02x %#4x %8u ", desc->opcode, 8668 scsi_2btoul(desc->service_action), 8669 scsi_2btoul(desc->cdb_length)); 8670 8671 used_len += sizeof(*desc); 8672 8673 if ((desc->flags & RSO_CTDP) == 0) { 8674 printf(" %s\n", op_desc); 8675 continue; 8676 } 8677 8678 /* 8679 * If we don't have enough space to fit a timeout 8680 * descriptor, then we're done. 8681 */ 8682 if (avail_len - used_len < sizeof(*td)) { 8683 used_len = avail_len; 8684 printf(" %s\n", op_desc); 8685 continue; 8686 } 8687 cur_ptr = &buf[used_len]; 8688 td = (struct scsi_report_supported_opcodes_timeout *)cur_ptr; 8689 td_len = scsi_2btoul(td->length); 8690 td_len += sizeof(td->length); 8691 8692 used_len += td_len; 8693 /* 8694 * If the given timeout descriptor length is less than what 8695 * we understand, skip it. 8696 */ 8697 if (td_len < sizeof(*td)) { 8698 printf(" %s\n", op_desc); 8699 continue; 8700 } 8701 8702 printf(" 0x%02x %6u %6u %s\n", td->cmd_specific, 8703 scsi_4btoul(td->nominal_time), 8704 scsi_4btoul(td->recommended_time), op_desc); 8705 } 8706 bailout: 8707 return (retval); 8708 } 8709 8710 static int 8711 scsiopcodes(struct cam_device *device, int argc, char **argv, 8712 char *combinedopt, int retry_count, int timeout, int verbosemode) 8713 { 8714 int c; 8715 uint32_t opcode = 0, service_action = 0; 8716 int td_set = 0, opcode_set = 0, sa_set = 0; 8717 int show_sa_errors = 1; 8718 uint32_t valid_len = 0; 8719 uint8_t *buf = NULL; 8720 char *endptr; 8721 int retval = 0; 8722 8723 while ((c = getopt(argc, argv, combinedopt)) != -1) { 8724 switch (c) { 8725 case 'N': 8726 show_sa_errors = 0; 8727 break; 8728 case 'o': 8729 opcode = strtoul(optarg, &endptr, 0); 8730 if (*endptr != '\0') { 8731 warnx("Invalid opcode \"%s\", must be a number", 8732 optarg); 8733 retval = 1; 8734 goto bailout; 8735 } 8736 if (opcode > 0xff) { 8737 warnx("Invalid opcode 0x%#x, must be between" 8738 "0 and 0xff inclusive", opcode); 8739 retval = 1; 8740 goto bailout; 8741 } 8742 opcode_set = 1; 8743 break; 8744 case 's': 8745 service_action = strtoul(optarg, &endptr, 0); 8746 if (*endptr != '\0') { 8747 warnx("Invalid service action \"%s\", must " 8748 "be a number", optarg); 8749 retval = 1; 8750 goto bailout; 8751 } 8752 if (service_action > 0xffff) { 8753 warnx("Invalid service action 0x%#x, must " 8754 "be between 0 and 0xffff inclusive", 8755 service_action); 8756 retval = 1; 8757 } 8758 sa_set = 1; 8759 break; 8760 case 'T': 8761 td_set = 1; 8762 break; 8763 default: 8764 break; 8765 } 8766 } 8767 8768 if ((sa_set != 0) 8769 && (opcode_set == 0)) { 8770 warnx("You must specify an opcode with -o if a service " 8771 "action is given"); 8772 retval = 1; 8773 goto bailout; 8774 } 8775 retval = scsigetopcodes(device, opcode_set, opcode, show_sa_errors, 8776 sa_set, service_action, td_set, retry_count, 8777 timeout, verbosemode, &valid_len, &buf); 8778 if (retval != 0) 8779 goto bailout; 8780 8781 if ((opcode_set != 0) 8782 || (sa_set != 0)) { 8783 retval = scsiprintoneopcode(device, opcode, sa_set, 8784 service_action, buf, valid_len); 8785 } else { 8786 retval = scsiprintopcodes(device, td_set, buf, valid_len); 8787 } 8788 8789 bailout: 8790 free(buf); 8791 8792 return (retval); 8793 } 8794 8795 #endif /* MINIMALISTIC */ 8796 8797 static int 8798 scsireprobe(struct cam_device *device) 8799 { 8800 union ccb *ccb; 8801 int retval = 0; 8802 8803 ccb = cam_getccb(device); 8804 8805 if (ccb == NULL) { 8806 warnx("%s: error allocating ccb", __func__); 8807 return (1); 8808 } 8809 8810 CCB_CLEAR_ALL_EXCEPT_HDR(&ccb->csio); 8811 8812 ccb->ccb_h.func_code = XPT_REPROBE_LUN; 8813 8814 if (cam_send_ccb(device, ccb) < 0) { 8815 warn("error sending XPT_REPROBE_LUN CCB"); 8816 retval = 1; 8817 goto bailout; 8818 } 8819 8820 if ((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP) { 8821 cam_error_print(device, ccb, CAM_ESF_ALL, CAM_EPF_ALL, stderr); 8822 retval = 1; 8823 goto bailout; 8824 } 8825 8826 bailout: 8827 cam_freeccb(ccb); 8828 8829 return (retval); 8830 } 8831 8832 void 8833 usage(int printlong) 8834 { 8835 8836 fprintf(printlong ? stdout : stderr, 8837 "usage: camcontrol <command> [device id][generic args][command args]\n" 8838 " camcontrol devlist [-b] [-v]\n" 8839 #ifndef MINIMALISTIC 8840 " camcontrol periphlist [dev_id][-n dev_name] [-u unit]\n" 8841 " camcontrol tur [dev_id][generic args]\n" 8842 " camcontrol inquiry [dev_id][generic args] [-D] [-S] [-R]\n" 8843 " camcontrol identify [dev_id][generic args] [-v]\n" 8844 " camcontrol reportluns [dev_id][generic args] [-c] [-l] [-r report]\n" 8845 " camcontrol readcap [dev_id][generic args] [-b] [-h] [-H] [-N]\n" 8846 " [-q] [-s]\n" 8847 " camcontrol start [dev_id][generic args]\n" 8848 " camcontrol stop [dev_id][generic args]\n" 8849 " camcontrol load [dev_id][generic args]\n" 8850 " camcontrol eject [dev_id][generic args]\n" 8851 " camcontrol reprobe [dev_id][generic args]\n" 8852 #endif /* MINIMALISTIC */ 8853 " camcontrol rescan <all | bus[:target:lun]>\n" 8854 " camcontrol reset <all | bus[:target:lun]>\n" 8855 #ifndef MINIMALISTIC 8856 " camcontrol defects [dev_id][generic args] <-f format> [-P][-G]\n" 8857 " [-q][-s][-S offset][-X]\n" 8858 " camcontrol modepage [dev_id][generic args] <-m page | -l>\n" 8859 " [-P pagectl][-e | -b][-d]\n" 8860 " camcontrol cmd [dev_id][generic args]\n" 8861 " <-a cmd [args] | -c cmd [args]>\n" 8862 " [-d] [-f] [-i len fmt|-o len fmt [args]] [-r fmt]\n" 8863 " camcontrol smpcmd [dev_id][generic args]\n" 8864 " <-r len fmt [args]> <-R len fmt [args]>\n" 8865 " camcontrol smprg [dev_id][generic args][-l]\n" 8866 " camcontrol smppc [dev_id][generic args] <-p phy> [-l]\n" 8867 " [-o operation][-d name][-m rate][-M rate]\n" 8868 " [-T pp_timeout][-a enable|disable]\n" 8869 " [-A enable|disable][-s enable|disable]\n" 8870 " [-S enable|disable]\n" 8871 " camcontrol smpphylist [dev_id][generic args][-l][-q]\n" 8872 " camcontrol smpmaninfo [dev_id][generic args][-l]\n" 8873 " camcontrol debug [-I][-P][-T][-S][-X][-c]\n" 8874 " <all|bus[:target[:lun]]|off>\n" 8875 " camcontrol tags [dev_id][generic args] [-N tags] [-q] [-v]\n" 8876 " camcontrol negotiate [dev_id][generic args] [-a][-c]\n" 8877 " [-D <enable|disable>][-M mode][-O offset]\n" 8878 " [-q][-R syncrate][-v][-T <enable|disable>]\n" 8879 " [-U][-W bus_width]\n" 8880 " camcontrol format [dev_id][generic args][-q][-r][-w][-y]\n" 8881 " camcontrol sanitize [dev_id][generic args]\n" 8882 " [-a overwrite|block|crypto|exitfailure]\n" 8883 " [-c passes][-I][-P pattern][-q][-U][-r][-w]\n" 8884 " [-y]\n" 8885 " camcontrol idle [dev_id][generic args][-t time]\n" 8886 " camcontrol standby [dev_id][generic args][-t time]\n" 8887 " camcontrol sleep [dev_id][generic args]\n" 8888 " camcontrol apm [dev_id][generic args][-l level]\n" 8889 " camcontrol aam [dev_id][generic args][-l level]\n" 8890 " camcontrol fwdownload [dev_id][generic args] <-f fw_image> [-q]\n" 8891 " [-s][-y]\n" 8892 " camcontrol security [dev_id][generic args]\n" 8893 " <-d pwd | -e pwd | -f | -h pwd | -k pwd>\n" 8894 " [-l <high|maximum>] [-q] [-s pwd] [-T timeout]\n" 8895 " [-U <user|master>] [-y]\n" 8896 " camcontrol hpa [dev_id][generic args] [-f] [-l] [-P] [-p pwd]\n" 8897 " [-q] [-s max_sectors] [-U pwd] [-y]\n" 8898 " camcontrol persist [dev_id][generic args] <-i action|-o action>\n" 8899 " [-a][-I tid][-k key][-K sa_key][-p][-R rtp]\n" 8900 " [-s scope][-S][-T type][-U]\n" 8901 " camcontrol attrib [dev_id][generic args] <-r action|-w attr>\n" 8902 " [-a attr_num][-c][-e elem][-F form1,form1]\n" 8903 " [-p part][-s start][-T type][-V vol]\n" 8904 " camcontrol opcodes [dev_id][generic args][-o opcode][-s SA]\n" 8905 " [-N][-T]\n" 8906 " camcontrol zone [dev_id][generic args]<-c cmd> [-a] [-l LBA]\n" 8907 " [-o rep_opts] [-P print_opts]\n" 8908 " camcontrol epc [dev_id][generic_args]<-c cmd> [-d] [-D] [-e]\n" 8909 " [-H] [-p power_cond] [-P] [-r rst_src] [-s]\n" 8910 " [-S power_src] [-T timer]\n" 8911 #endif /* MINIMALISTIC */ 8912 " camcontrol help\n"); 8913 if (!printlong) 8914 return; 8915 #ifndef MINIMALISTIC 8916 fprintf(stdout, 8917 "Specify one of the following options:\n" 8918 "devlist list all CAM devices\n" 8919 "periphlist list all CAM peripheral drivers attached to a device\n" 8920 "tur send a test unit ready to the named device\n" 8921 "inquiry send a SCSI inquiry command to the named device\n" 8922 "identify send a ATA identify command to the named device\n" 8923 "reportluns send a SCSI report luns command to the device\n" 8924 "readcap send a SCSI read capacity command to the device\n" 8925 "start send a Start Unit command to the device\n" 8926 "stop send a Stop Unit command to the device\n" 8927 "load send a Start Unit command to the device with the load bit set\n" 8928 "eject send a Stop Unit command to the device with the eject bit set\n" 8929 "reprobe update capacity information of the given device\n" 8930 "rescan rescan all busses, the given bus, or bus:target:lun\n" 8931 "reset reset all busses, the given bus, or bus:target:lun\n" 8932 "defects read the defect list of the specified device\n" 8933 "modepage display or edit (-e) the given mode page\n" 8934 "cmd send the given SCSI command, may need -i or -o as well\n" 8935 "smpcmd send the given SMP command, requires -o and -i\n" 8936 "smprg send the SMP Report General command\n" 8937 "smppc send the SMP PHY Control command, requires -p\n" 8938 "smpphylist display phys attached to a SAS expander\n" 8939 "smpmaninfo send the SMP Report Manufacturer Info command\n" 8940 "debug turn debugging on/off for a bus, target, or lun, or all devices\n" 8941 "tags report or set the number of transaction slots for a device\n" 8942 "negotiate report or set device negotiation parameters\n" 8943 "format send the SCSI FORMAT UNIT command to the named device\n" 8944 "sanitize send the SCSI SANITIZE command to the named device\n" 8945 "idle send the ATA IDLE command to the named device\n" 8946 "standby send the ATA STANDBY command to the named device\n" 8947 "sleep send the ATA SLEEP command to the named device\n" 8948 "fwdownload program firmware of the named device with the given image\n" 8949 "security report or send ATA security commands to the named device\n" 8950 "persist send the SCSI PERSISTENT RESERVE IN or OUT commands\n" 8951 "attrib send the SCSI READ or WRITE ATTRIBUTE commands\n" 8952 "opcodes send the SCSI REPORT SUPPORTED OPCODES command\n" 8953 "zone manage Zoned Block (Shingled) devices\n" 8954 "epc send ATA Extended Power Conditions commands\n" 8955 "help this message\n" 8956 "Device Identifiers:\n" 8957 "bus:target specify the bus and target, lun defaults to 0\n" 8958 "bus:target:lun specify the bus, target and lun\n" 8959 "deviceUNIT specify the device name, like \"da4\" or \"cd2\"\n" 8960 "Generic arguments:\n" 8961 "-v be verbose, print out sense information\n" 8962 "-t timeout command timeout in seconds, overrides default timeout\n" 8963 "-n dev_name specify device name, e.g. \"da\", \"cd\"\n" 8964 "-u unit specify unit number, e.g. \"0\", \"5\"\n" 8965 "-E have the kernel attempt to perform SCSI error recovery\n" 8966 "-C count specify the SCSI command retry count (needs -E to work)\n" 8967 "modepage arguments:\n" 8968 "-l list all available mode pages\n" 8969 "-m page specify the mode page to view or edit\n" 8970 "-e edit the specified mode page\n" 8971 "-b force view to binary mode\n" 8972 "-d disable block descriptors for mode sense\n" 8973 "-P pgctl page control field 0-3\n" 8974 "defects arguments:\n" 8975 "-f format specify defect list format (block, bfi or phys)\n" 8976 "-G get the grown defect list\n" 8977 "-P get the permanent defect list\n" 8978 "inquiry arguments:\n" 8979 "-D get the standard inquiry data\n" 8980 "-S get the serial number\n" 8981 "-R get the transfer rate, etc.\n" 8982 "reportluns arguments:\n" 8983 "-c only report a count of available LUNs\n" 8984 "-l only print out luns, and not a count\n" 8985 "-r <reporttype> specify \"default\", \"wellknown\" or \"all\"\n" 8986 "readcap arguments\n" 8987 "-b only report the blocksize\n" 8988 "-h human readable device size, base 2\n" 8989 "-H human readable device size, base 10\n" 8990 "-N print the number of blocks instead of last block\n" 8991 "-q quiet, print numbers only\n" 8992 "-s only report the last block/device size\n" 8993 "cmd arguments:\n" 8994 "-c cdb [args] specify the SCSI CDB\n" 8995 "-i len fmt specify input data and input data format\n" 8996 "-o len fmt [args] specify output data and output data fmt\n" 8997 "smpcmd arguments:\n" 8998 "-r len fmt [args] specify the SMP command to be sent\n" 8999 "-R len fmt [args] specify SMP response format\n" 9000 "smprg arguments:\n" 9001 "-l specify the long response format\n" 9002 "smppc arguments:\n" 9003 "-p phy specify the PHY to operate on\n" 9004 "-l specify the long request/response format\n" 9005 "-o operation specify the phy control operation\n" 9006 "-d name set the attached device name\n" 9007 "-m rate set the minimum physical link rate\n" 9008 "-M rate set the maximum physical link rate\n" 9009 "-T pp_timeout set the partial pathway timeout value\n" 9010 "-a enable|disable enable or disable SATA slumber\n" 9011 "-A enable|disable enable or disable SATA partial phy power\n" 9012 "-s enable|disable enable or disable SAS slumber\n" 9013 "-S enable|disable enable or disable SAS partial phy power\n" 9014 "smpphylist arguments:\n" 9015 "-l specify the long response format\n" 9016 "-q only print phys with attached devices\n" 9017 "smpmaninfo arguments:\n" 9018 "-l specify the long response format\n" 9019 "debug arguments:\n" 9020 "-I CAM_DEBUG_INFO -- scsi commands, errors, data\n" 9021 "-T CAM_DEBUG_TRACE -- routine flow tracking\n" 9022 "-S CAM_DEBUG_SUBTRACE -- internal routine command flow\n" 9023 "-c CAM_DEBUG_CDB -- print out SCSI CDBs only\n" 9024 "tags arguments:\n" 9025 "-N tags specify the number of tags to use for this device\n" 9026 "-q be quiet, don't report the number of tags\n" 9027 "-v report a number of tag-related parameters\n" 9028 "negotiate arguments:\n" 9029 "-a send a test unit ready after negotiation\n" 9030 "-c report/set current negotiation settings\n" 9031 "-D <arg> \"enable\" or \"disable\" disconnection\n" 9032 "-M mode set ATA mode\n" 9033 "-O offset set command delay offset\n" 9034 "-q be quiet, don't report anything\n" 9035 "-R syncrate synchronization rate in MHz\n" 9036 "-T <arg> \"enable\" or \"disable\" tagged queueing\n" 9037 "-U report/set user negotiation settings\n" 9038 "-W bus_width set the bus width in bits (8, 16 or 32)\n" 9039 "-v also print a Path Inquiry CCB for the controller\n" 9040 "format arguments:\n" 9041 "-q be quiet, don't print status messages\n" 9042 "-r run in report only mode\n" 9043 "-w don't send immediate format command\n" 9044 "-y don't ask any questions\n" 9045 "sanitize arguments:\n" 9046 "-a operation operation mode: overwrite, block, crypto or exitfailure\n" 9047 "-c passes overwrite passes to perform (1 to 31)\n" 9048 "-I invert overwrite pattern after each pass\n" 9049 "-P pattern path to overwrite pattern file\n" 9050 "-q be quiet, don't print status messages\n" 9051 "-r run in report only mode\n" 9052 "-U run operation in unrestricted completion exit mode\n" 9053 "-w don't send immediate sanitize command\n" 9054 "-y don't ask any questions\n" 9055 "idle/standby arguments:\n" 9056 "-t <arg> number of seconds before respective state.\n" 9057 "fwdownload arguments:\n" 9058 "-f fw_image path to firmware image file\n" 9059 "-q don't print informational messages, only errors\n" 9060 "-s run in simulation mode\n" 9061 "-v print info for every firmware segment sent to device\n" 9062 "-y don't ask any questions\n" 9063 "security arguments:\n" 9064 "-d pwd disable security using the given password for the selected\n" 9065 " user\n" 9066 "-e pwd erase the device using the given pwd for the selected user\n" 9067 "-f freeze the security configuration of the specified device\n" 9068 "-h pwd enhanced erase the device using the given pwd for the\n" 9069 " selected user\n" 9070 "-k pwd unlock the device using the given pwd for the selected\n" 9071 " user\n" 9072 "-l <high|maximum> specifies which security level to set: high or maximum\n" 9073 "-q be quiet, do not print any status messages\n" 9074 "-s pwd password the device (enable security) using the given\n" 9075 " pwd for the selected user\n" 9076 "-T timeout overrides the timeout (seconds) used for erase operation\n" 9077 "-U <user|master> specifies which user to set: user or master\n" 9078 "-y don't ask any questions\n" 9079 "hpa arguments:\n" 9080 "-f freeze the HPA configuration of the device\n" 9081 "-l lock the HPA configuration of the device\n" 9082 "-P make the HPA max sectors persist\n" 9083 "-p pwd Set the HPA configuration password required for unlock\n" 9084 " calls\n" 9085 "-q be quiet, do not print any status messages\n" 9086 "-s sectors configures the maximum user accessible sectors of the\n" 9087 " device\n" 9088 "-U pwd unlock the HPA configuration of the device\n" 9089 "-y don't ask any questions\n" 9090 "persist arguments:\n" 9091 "-i action specify read_keys, read_reservation, report_cap, or\n" 9092 " read_full_status\n" 9093 "-o action specify register, register_ignore, reserve, release,\n" 9094 " clear, preempt, preempt_abort, register_move, replace_lost\n" 9095 "-a set the All Target Ports (ALL_TG_PT) bit\n" 9096 "-I tid specify a Transport ID, e.g.: sas,0x1234567812345678\n" 9097 "-k key specify the Reservation Key\n" 9098 "-K sa_key specify the Service Action Reservation Key\n" 9099 "-p set the Activate Persist Through Power Loss bit\n" 9100 "-R rtp specify the Relative Target Port\n" 9101 "-s scope specify the scope: lun, extent, element or a number\n" 9102 "-S specify Transport ID for register, requires -I\n" 9103 "-T res_type specify the reservation type: read_shared, wr_ex, rd_ex,\n" 9104 " ex_ac, wr_ex_ro, ex_ac_ro, wr_ex_ar, ex_ac_ar\n" 9105 "-U unregister the current initiator for register_move\n" 9106 "attrib arguments:\n" 9107 "-r action specify attr_values, attr_list, lv_list, part_list, or\n" 9108 " supp_attr\n" 9109 "-w attr specify an attribute to write, one -w argument per attr\n" 9110 "-a attr_num only display this attribute number\n" 9111 "-c get cached attributes\n" 9112 "-e elem_addr request attributes for the given element in a changer\n" 9113 "-F form1,form2 output format, comma separated list: text_esc, text_raw,\n" 9114 " nonascii_esc, nonascii_trim, nonascii_raw, field_all,\n" 9115 " field_none, field_desc, field_num, field_size, field_rw\n" 9116 "-p partition request attributes for the given partition\n" 9117 "-s start_attr request attributes starting at the given number\n" 9118 "-T elem_type specify the element type (used with -e)\n" 9119 "-V logical_vol specify the logical volume ID\n" 9120 "opcodes arguments:\n" 9121 "-o opcode specify the individual opcode to list\n" 9122 "-s service_action specify the service action for the opcode\n" 9123 "-N do not return SCSI error for unsupported SA\n" 9124 "-T request nominal and recommended timeout values\n" 9125 "zone arguments:\n" 9126 "-c cmd required: rz, open, close, finish, or rwp\n" 9127 "-a apply the action to all zones\n" 9128 "-l LBA specify the zone starting LBA\n" 9129 "-o rep_opts report zones options: all, empty, imp_open, exp_open,\n" 9130 " closed, full, ro, offline, reset, nonseq, nonwp\n" 9131 "-P print_opt report zones printing: normal, summary, script\n" 9132 "epc arguments:\n" 9133 "-c cmd required: restore, goto, timer, state, enable, disable,\n" 9134 " source, status, list\n" 9135 "-d disable power mode (timer, state)\n" 9136 "-D delayed entry (goto)\n" 9137 "-e enable power mode (timer, state)\n" 9138 "-H hold power mode (goto)\n" 9139 "-p power_cond Idle_a, Idle_b, Idle_c, Standby_y, Standby_z (timer,\n" 9140 " state, goto)\n" 9141 "-P only display power mode (status)\n" 9142 "-r rst_src restore settings from: default, saved (restore)\n" 9143 "-s save mode (timer, state, restore)\n" 9144 "-S power_src set power source: battery, nonbattery (source)\n" 9145 "-T timer set timer, seconds, .1 sec resolution (timer)\n" 9146 ); 9147 #endif /* MINIMALISTIC */ 9148 } 9149 9150 int 9151 main(int argc, char **argv) 9152 { 9153 int c; 9154 char *device = NULL; 9155 int unit = 0; 9156 struct cam_device *cam_dev = NULL; 9157 int timeout = 0, retry_count = 1; 9158 camcontrol_optret optreturn; 9159 char *tstr; 9160 const char *mainopt = "C:En:t:u:v"; 9161 const char *subopt = NULL; 9162 char combinedopt[256]; 9163 int error = 0, optstart = 2; 9164 int devopen = 1; 9165 #ifndef MINIMALISTIC 9166 path_id_t bus; 9167 target_id_t target; 9168 lun_id_t lun; 9169 #endif /* MINIMALISTIC */ 9170 9171 cmdlist = CAM_CMD_NONE; 9172 arglist = CAM_ARG_NONE; 9173 9174 if (argc < 2) { 9175 usage(0); 9176 exit(1); 9177 } 9178 9179 /* 9180 * Get the base option. 9181 */ 9182 optreturn = getoption(option_table,argv[1], &cmdlist, &arglist,&subopt); 9183 9184 if (optreturn == CC_OR_AMBIGUOUS) { 9185 warnx("ambiguous option %s", argv[1]); 9186 usage(0); 9187 exit(1); 9188 } else if (optreturn == CC_OR_NOT_FOUND) { 9189 warnx("option %s not found", argv[1]); 9190 usage(0); 9191 exit(1); 9192 } 9193 9194 /* 9195 * Ahh, getopt(3) is a pain. 9196 * 9197 * This is a gross hack. There really aren't many other good 9198 * options (excuse the pun) for parsing options in a situation like 9199 * this. getopt is kinda braindead, so you end up having to run 9200 * through the options twice, and give each invocation of getopt 9201 * the option string for the other invocation. 9202 * 9203 * You would think that you could just have two groups of options. 9204 * The first group would get parsed by the first invocation of 9205 * getopt, and the second group would get parsed by the second 9206 * invocation of getopt. It doesn't quite work out that way. When 9207 * the first invocation of getopt finishes, it leaves optind pointing 9208 * to the argument _after_ the first argument in the second group. 9209 * So when the second invocation of getopt comes around, it doesn't 9210 * recognize the first argument it gets and then bails out. 9211 * 9212 * A nice alternative would be to have a flag for getopt that says 9213 * "just keep parsing arguments even when you encounter an unknown 9214 * argument", but there isn't one. So there's no real clean way to 9215 * easily parse two sets of arguments without having one invocation 9216 * of getopt know about the other. 9217 * 9218 * Without this hack, the first invocation of getopt would work as 9219 * long as the generic arguments are first, but the second invocation 9220 * (in the subfunction) would fail in one of two ways. In the case 9221 * where you don't set optreset, it would fail because optind may be 9222 * pointing to the argument after the one it should be pointing at. 9223 * In the case where you do set optreset, and reset optind, it would 9224 * fail because getopt would run into the first set of options, which 9225 * it doesn't understand. 9226 * 9227 * All of this would "sort of" work if you could somehow figure out 9228 * whether optind had been incremented one option too far. The 9229 * mechanics of that, however, are more daunting than just giving 9230 * both invocations all of the expect options for either invocation. 9231 * 9232 * Needless to say, I wouldn't mind if someone invented a better 9233 * (non-GPL!) command line parsing interface than getopt. I 9234 * wouldn't mind if someone added more knobs to getopt to make it 9235 * work better. Who knows, I may talk myself into doing it someday, 9236 * if the standards weenies let me. As it is, it just leads to 9237 * hackery like this and causes people to avoid it in some cases. 9238 * 9239 * KDM, September 8th, 1998 9240 */ 9241 if (subopt != NULL) 9242 sprintf(combinedopt, "%s%s", mainopt, subopt); 9243 else 9244 sprintf(combinedopt, "%s", mainopt); 9245 9246 /* 9247 * For these options we do not parse optional device arguments and 9248 * we do not open a passthrough device. 9249 */ 9250 if ((cmdlist == CAM_CMD_RESCAN) 9251 || (cmdlist == CAM_CMD_RESET) 9252 || (cmdlist == CAM_CMD_DEVTREE) 9253 || (cmdlist == CAM_CMD_USAGE) 9254 || (cmdlist == CAM_CMD_DEBUG)) 9255 devopen = 0; 9256 9257 #ifndef MINIMALISTIC 9258 if ((devopen == 1) 9259 && (argc > 2 && argv[2][0] != '-')) { 9260 char name[30]; 9261 int rv; 9262 9263 if (isdigit(argv[2][0])) { 9264 /* device specified as bus:target[:lun] */ 9265 rv = parse_btl(argv[2], &bus, &target, &lun, &arglist); 9266 if (rv < 2) 9267 errx(1, "numeric device specification must " 9268 "be either bus:target, or " 9269 "bus:target:lun"); 9270 /* default to 0 if lun was not specified */ 9271 if ((arglist & CAM_ARG_LUN) == 0) { 9272 lun = 0; 9273 arglist |= CAM_ARG_LUN; 9274 } 9275 optstart++; 9276 } else { 9277 if (cam_get_device(argv[2], name, sizeof name, &unit) 9278 == -1) 9279 errx(1, "%s", cam_errbuf); 9280 device = strdup(name); 9281 arglist |= CAM_ARG_DEVICE | CAM_ARG_UNIT; 9282 optstart++; 9283 } 9284 } 9285 #endif /* MINIMALISTIC */ 9286 /* 9287 * Start getopt processing at argv[2/3], since we've already 9288 * accepted argv[1..2] as the command name, and as a possible 9289 * device name. 9290 */ 9291 optind = optstart; 9292 9293 /* 9294 * Now we run through the argument list looking for generic 9295 * options, and ignoring options that possibly belong to 9296 * subfunctions. 9297 */ 9298 while ((c = getopt(argc, argv, combinedopt))!= -1){ 9299 switch(c) { 9300 case 'C': 9301 retry_count = strtol(optarg, NULL, 0); 9302 if (retry_count < 0) 9303 errx(1, "retry count %d is < 0", 9304 retry_count); 9305 arglist |= CAM_ARG_RETRIES; 9306 break; 9307 case 'E': 9308 arglist |= CAM_ARG_ERR_RECOVER; 9309 break; 9310 case 'n': 9311 arglist |= CAM_ARG_DEVICE; 9312 tstr = optarg; 9313 while (isspace(*tstr) && (*tstr != '\0')) 9314 tstr++; 9315 device = (char *)strdup(tstr); 9316 break; 9317 case 't': 9318 timeout = strtol(optarg, NULL, 0); 9319 if (timeout < 0) 9320 errx(1, "invalid timeout %d", timeout); 9321 /* Convert the timeout from seconds to ms */ 9322 timeout *= 1000; 9323 arglist |= CAM_ARG_TIMEOUT; 9324 break; 9325 case 'u': 9326 arglist |= CAM_ARG_UNIT; 9327 unit = strtol(optarg, NULL, 0); 9328 break; 9329 case 'v': 9330 arglist |= CAM_ARG_VERBOSE; 9331 break; 9332 default: 9333 break; 9334 } 9335 } 9336 9337 #ifndef MINIMALISTIC 9338 /* 9339 * For most commands we'll want to open the passthrough device 9340 * associated with the specified device. In the case of the rescan 9341 * commands, we don't use a passthrough device at all, just the 9342 * transport layer device. 9343 */ 9344 if (devopen == 1) { 9345 if (((arglist & (CAM_ARG_BUS|CAM_ARG_TARGET)) == 0) 9346 && (((arglist & CAM_ARG_DEVICE) == 0) 9347 || ((arglist & CAM_ARG_UNIT) == 0))) { 9348 errx(1, "subcommand \"%s\" requires a valid device " 9349 "identifier", argv[1]); 9350 } 9351 9352 if ((cam_dev = ((arglist & (CAM_ARG_BUS | CAM_ARG_TARGET))? 9353 cam_open_btl(bus, target, lun, O_RDWR, NULL) : 9354 cam_open_spec_device(device,unit,O_RDWR,NULL))) 9355 == NULL) 9356 errx(1,"%s", cam_errbuf); 9357 } 9358 #endif /* MINIMALISTIC */ 9359 9360 /* 9361 * Reset optind to 2, and reset getopt, so these routines can parse 9362 * the arguments again. 9363 */ 9364 optind = optstart; 9365 optreset = 1; 9366 9367 switch(cmdlist) { 9368 #ifndef MINIMALISTIC 9369 case CAM_CMD_DEVLIST: 9370 error = getdevlist(cam_dev); 9371 break; 9372 case CAM_CMD_HPA: 9373 error = atahpa(cam_dev, retry_count, timeout, 9374 argc, argv, combinedopt); 9375 break; 9376 #endif /* MINIMALISTIC */ 9377 case CAM_CMD_DEVTREE: 9378 error = getdevtree(argc, argv, combinedopt); 9379 break; 9380 #ifndef MINIMALISTIC 9381 case CAM_CMD_TUR: 9382 error = testunitready(cam_dev, retry_count, timeout, 0); 9383 break; 9384 case CAM_CMD_INQUIRY: 9385 error = scsidoinquiry(cam_dev, argc, argv, combinedopt, 9386 retry_count, timeout); 9387 break; 9388 case CAM_CMD_IDENTIFY: 9389 error = ataidentify(cam_dev, retry_count, timeout); 9390 break; 9391 case CAM_CMD_STARTSTOP: 9392 error = scsistart(cam_dev, arglist & CAM_ARG_START_UNIT, 9393 arglist & CAM_ARG_EJECT, retry_count, 9394 timeout); 9395 break; 9396 #endif /* MINIMALISTIC */ 9397 case CAM_CMD_RESCAN: 9398 error = dorescan_or_reset(argc, argv, 1); 9399 break; 9400 case CAM_CMD_RESET: 9401 error = dorescan_or_reset(argc, argv, 0); 9402 break; 9403 #ifndef MINIMALISTIC 9404 case CAM_CMD_READ_DEFECTS: 9405 error = readdefects(cam_dev, argc, argv, combinedopt, 9406 retry_count, timeout); 9407 break; 9408 case CAM_CMD_MODE_PAGE: 9409 modepage(cam_dev, argc, argv, combinedopt, 9410 retry_count, timeout); 9411 break; 9412 case CAM_CMD_SCSI_CMD: 9413 error = scsicmd(cam_dev, argc, argv, combinedopt, 9414 retry_count, timeout); 9415 break; 9416 case CAM_CMD_SMP_CMD: 9417 error = smpcmd(cam_dev, argc, argv, combinedopt, 9418 retry_count, timeout); 9419 break; 9420 case CAM_CMD_SMP_RG: 9421 error = smpreportgeneral(cam_dev, argc, argv, 9422 combinedopt, retry_count, 9423 timeout); 9424 break; 9425 case CAM_CMD_SMP_PC: 9426 error = smpphycontrol(cam_dev, argc, argv, combinedopt, 9427 retry_count, timeout); 9428 break; 9429 case CAM_CMD_SMP_PHYLIST: 9430 error = smpphylist(cam_dev, argc, argv, combinedopt, 9431 retry_count, timeout); 9432 break; 9433 case CAM_CMD_SMP_MANINFO: 9434 error = smpmaninfo(cam_dev, argc, argv, combinedopt, 9435 retry_count, timeout); 9436 break; 9437 case CAM_CMD_DEBUG: 9438 error = camdebug(argc, argv, combinedopt); 9439 break; 9440 case CAM_CMD_TAG: 9441 error = tagcontrol(cam_dev, argc, argv, combinedopt); 9442 break; 9443 case CAM_CMD_RATE: 9444 error = ratecontrol(cam_dev, retry_count, timeout, 9445 argc, argv, combinedopt); 9446 break; 9447 case CAM_CMD_FORMAT: 9448 error = scsiformat(cam_dev, argc, argv, 9449 combinedopt, retry_count, timeout); 9450 break; 9451 case CAM_CMD_REPORTLUNS: 9452 error = scsireportluns(cam_dev, argc, argv, 9453 combinedopt, retry_count, 9454 timeout); 9455 break; 9456 case CAM_CMD_READCAP: 9457 error = scsireadcapacity(cam_dev, argc, argv, 9458 combinedopt, retry_count, 9459 timeout); 9460 break; 9461 case CAM_CMD_IDLE: 9462 case CAM_CMD_STANDBY: 9463 case CAM_CMD_SLEEP: 9464 error = atapm(cam_dev, argc, argv, 9465 combinedopt, retry_count, timeout); 9466 break; 9467 case CAM_CMD_APM: 9468 case CAM_CMD_AAM: 9469 error = ataaxm(cam_dev, argc, argv, 9470 combinedopt, retry_count, timeout); 9471 break; 9472 case CAM_CMD_SECURITY: 9473 error = atasecurity(cam_dev, retry_count, timeout, 9474 argc, argv, combinedopt); 9475 break; 9476 case CAM_CMD_DOWNLOAD_FW: 9477 error = fwdownload(cam_dev, argc, argv, combinedopt, 9478 arglist & CAM_ARG_VERBOSE, retry_count, timeout); 9479 break; 9480 case CAM_CMD_SANITIZE: 9481 error = scsisanitize(cam_dev, argc, argv, 9482 combinedopt, retry_count, timeout); 9483 break; 9484 case CAM_CMD_PERSIST: 9485 error = scsipersist(cam_dev, argc, argv, combinedopt, 9486 retry_count, timeout, arglist & CAM_ARG_VERBOSE, 9487 arglist & CAM_ARG_ERR_RECOVER); 9488 break; 9489 case CAM_CMD_ATTRIB: 9490 error = scsiattrib(cam_dev, argc, argv, combinedopt, 9491 retry_count, timeout, arglist & CAM_ARG_VERBOSE, 9492 arglist & CAM_ARG_ERR_RECOVER); 9493 break; 9494 case CAM_CMD_OPCODES: 9495 error = scsiopcodes(cam_dev, argc, argv, combinedopt, 9496 retry_count, timeout, arglist & CAM_ARG_VERBOSE); 9497 break; 9498 case CAM_CMD_REPROBE: 9499 error = scsireprobe(cam_dev); 9500 break; 9501 case CAM_CMD_ZONE: 9502 error = zone(cam_dev, argc, argv, combinedopt, 9503 retry_count, timeout, arglist & CAM_ARG_VERBOSE); 9504 break; 9505 case CAM_CMD_EPC: 9506 error = epc(cam_dev, argc, argv, combinedopt, 9507 retry_count, timeout, arglist & CAM_ARG_VERBOSE); 9508 break; 9509 #endif /* MINIMALISTIC */ 9510 case CAM_CMD_USAGE: 9511 usage(1); 9512 break; 9513 default: 9514 usage(0); 9515 error = 1; 9516 break; 9517 } 9518 9519 if (cam_dev != NULL) 9520 cam_close_device(cam_dev); 9521 9522 exit(error); 9523 } 9524