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