1 /*- 2 * SPDX-License-Identifier: BSD-2-Clause-FreeBSD 3 * 4 * Copyright (c) 2002-2010 Adaptec, Inc. 5 * Copyright (c) 2010-2012 PMC-Sierra, Inc. 6 * All rights reserved. 7 * 8 * Redistribution and use in source and binary forms, with or without 9 * modification, are permitted provided that the following conditions 10 * are met: 11 * 1. Redistributions of source code must retain the above copyright 12 * notice, this list of conditions and the following disclaimer. 13 * 2. Redistributions in binary form must reproduce the above copyright 14 * notice, this list of conditions and the following disclaimer in the 15 * documentation and/or other materials provided with the distribution. 16 * 17 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 18 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 19 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 20 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 21 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 22 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 23 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 24 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 25 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 26 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 27 * SUCH DAMAGE. 28 */ 29 30 #include <sys/cdefs.h> 31 __FBSDID("$FreeBSD$"); 32 33 /* 34 * CAM front-end for communicating with non-DASD devices 35 */ 36 37 #include "opt_aacraid.h" 38 39 #include <sys/param.h> 40 #include <sys/systm.h> 41 #include <sys/kernel.h> 42 #include <sys/sysctl.h> 43 #include <sys/lock.h> 44 #include <sys/malloc.h> 45 #include <sys/module.h> 46 #include <sys/mutex.h> 47 48 #include <cam/cam.h> 49 #include <cam/cam_ccb.h> 50 #include <cam/cam_debug.h> 51 #include <cam/cam_periph.h> 52 #include <cam/cam_sim.h> 53 #include <cam/cam_xpt_sim.h> 54 #include <cam/scsi/scsi_all.h> 55 #include <cam/scsi/scsi_message.h> 56 57 #include <sys/bus.h> 58 #include <sys/conf.h> 59 #include <sys/disk.h> 60 61 #include <machine/md_var.h> 62 #include <machine/bus.h> 63 #include <sys/rman.h> 64 65 #include <vm/vm.h> 66 #include <vm/pmap.h> 67 68 #include <dev/aacraid/aacraid_reg.h> 69 #include <sys/aac_ioctl.h> 70 #include <dev/aacraid/aacraid_debug.h> 71 #include <dev/aacraid/aacraid_var.h> 72 #include <dev/aacraid/aacraid_endian.h> 73 74 #ifndef CAM_NEW_TRAN_CODE 75 #define CAM_NEW_TRAN_CODE 1 76 #endif 77 78 #ifndef SVPD_SUPPORTED_PAGE_LIST 79 struct scsi_vpd_supported_page_list 80 { 81 u_int8_t device; 82 u_int8_t page_code; 83 #define SVPD_SUPPORTED_PAGE_LIST 0x00 84 u_int8_t reserved; 85 u_int8_t length; /* number of VPD entries */ 86 #define SVPD_SUPPORTED_PAGES_SIZE 251 87 u_int8_t list[SVPD_SUPPORTED_PAGES_SIZE]; 88 }; 89 #endif 90 91 /************************** Version Compatibility *************************/ 92 #define aac_sim_alloc cam_sim_alloc 93 94 struct aac_cam { 95 device_t dev; 96 struct aac_sim *inf; 97 struct cam_sim *sim; 98 struct cam_path *path; 99 }; 100 101 static int aac_cam_probe(device_t dev); 102 static int aac_cam_attach(device_t dev); 103 static int aac_cam_detach(device_t dev); 104 static void aac_cam_action(struct cam_sim *, union ccb *); 105 static void aac_cam_poll(struct cam_sim *); 106 static void aac_cam_complete(struct aac_command *); 107 static void aac_container_complete(struct aac_command *); 108 static void aac_cam_rescan(struct aac_softc *sc, uint32_t channel, 109 uint32_t target_id); 110 static void aac_set_scsi_error(struct aac_softc *sc, union ccb *ccb, 111 u_int8_t status, u_int8_t key, u_int8_t asc, u_int8_t ascq); 112 static int aac_load_map_command_sg(struct aac_softc *, struct aac_command *); 113 static u_int64_t aac_eval_blockno(u_int8_t *); 114 static void aac_container_rw_command(struct cam_sim *, union ccb *, u_int8_t *); 115 static void aac_container_special_command(struct cam_sim *, union ccb *, 116 u_int8_t *); 117 static void aac_passthrough_command(struct cam_sim *, union ccb *); 118 119 static u_int32_t aac_cam_reset_bus(struct cam_sim *, union ccb *); 120 static u_int32_t aac_cam_abort_ccb(struct cam_sim *, union ccb *); 121 static u_int32_t aac_cam_term_io(struct cam_sim *, union ccb *); 122 123 static devclass_t aacraid_pass_devclass; 124 125 static device_method_t aacraid_pass_methods[] = { 126 DEVMETHOD(device_probe, aac_cam_probe), 127 DEVMETHOD(device_attach, aac_cam_attach), 128 DEVMETHOD(device_detach, aac_cam_detach), 129 { 0, 0 } 130 }; 131 132 static driver_t aacraid_pass_driver = { 133 "aacraidp", 134 aacraid_pass_methods, 135 sizeof(struct aac_cam) 136 }; 137 138 DRIVER_MODULE(aacraidp, aacraid, aacraid_pass_driver, aacraid_pass_devclass, 0, 0); 139 MODULE_DEPEND(aacraidp, cam, 1, 1, 1); 140 141 MALLOC_DEFINE(M_AACRAIDCAM, "aacraidcam", "AACRAID CAM info"); 142 143 static void 144 aac_set_scsi_error(struct aac_softc *sc, union ccb *ccb, u_int8_t status, 145 u_int8_t key, u_int8_t asc, u_int8_t ascq) 146 { 147 struct scsi_sense_data_fixed *sense = 148 (struct scsi_sense_data_fixed *)&ccb->csio.sense_data; 149 150 fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "Error %d!", status); 151 152 ccb->ccb_h.status = CAM_SCSI_STATUS_ERROR; 153 ccb->csio.scsi_status = status; 154 if (status == SCSI_STATUS_CHECK_COND) { 155 ccb->ccb_h.status |= CAM_AUTOSNS_VALID; 156 bzero(&ccb->csio.sense_data, ccb->csio.sense_len); 157 ccb->csio.sense_data.error_code = 158 SSD_CURRENT_ERROR | SSD_ERRCODE_VALID; 159 sense->flags = key; 160 if (ccb->csio.sense_len >= 14) { 161 sense->extra_len = 6; 162 sense->add_sense_code = asc; 163 sense->add_sense_code_qual = ascq; 164 } 165 } 166 } 167 168 static void 169 aac_cam_rescan(struct aac_softc *sc, uint32_t channel, uint32_t target_id) 170 { 171 union ccb *ccb; 172 struct aac_sim *sim; 173 struct aac_cam *camsc; 174 175 if (target_id == AAC_CAM_TARGET_WILDCARD) 176 target_id = CAM_TARGET_WILDCARD; 177 178 TAILQ_FOREACH(sim, &sc->aac_sim_tqh, sim_link) { 179 camsc = sim->aac_cam; 180 if (camsc == NULL || camsc->inf == NULL || 181 camsc->inf->BusNumber != channel) 182 continue; 183 184 ccb = xpt_alloc_ccb_nowait(); 185 if (ccb == NULL) { 186 device_printf(sc->aac_dev, 187 "Cannot allocate ccb for bus rescan.\n"); 188 return; 189 } 190 191 if (xpt_create_path(&ccb->ccb_h.path, xpt_periph, 192 cam_sim_path(camsc->sim), 193 target_id, CAM_LUN_WILDCARD) != CAM_REQ_CMP) { 194 xpt_free_ccb(ccb); 195 device_printf(sc->aac_dev, 196 "Cannot create path for bus rescan.\n"); 197 return; 198 } 199 xpt_rescan(ccb); 200 break; 201 } 202 } 203 204 static void 205 aac_cam_event(struct aac_softc *sc, struct aac_event *event, void *arg) 206 { 207 union ccb *ccb; 208 struct aac_cam *camsc; 209 210 switch (event->ev_type) { 211 case AAC_EVENT_CMFREE: 212 ccb = arg; 213 camsc = ccb->ccb_h.sim_priv.entries[0].ptr; 214 free(event, M_AACRAIDCAM); 215 xpt_release_simq(camsc->sim, 1); 216 ccb->ccb_h.status = CAM_REQUEUE_REQ; 217 xpt_done(ccb); 218 break; 219 default: 220 device_printf(sc->aac_dev, "unknown event %d in aac_cam\n", 221 event->ev_type); 222 break; 223 } 224 225 return; 226 } 227 228 static int 229 aac_cam_probe(device_t dev) 230 { 231 struct aac_cam *camsc; 232 233 camsc = (struct aac_cam *)device_get_softc(dev); 234 if (!camsc->inf) 235 return (0); 236 fwprintf(camsc->inf->aac_sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, ""); 237 return (0); 238 } 239 240 static int 241 aac_cam_detach(device_t dev) 242 { 243 struct aac_softc *sc; 244 struct aac_cam *camsc; 245 246 camsc = (struct aac_cam *)device_get_softc(dev); 247 if (!camsc->inf) 248 return (0); 249 sc = camsc->inf->aac_sc; 250 fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, ""); 251 camsc->inf->aac_cam = NULL; 252 253 mtx_lock(&sc->aac_io_lock); 254 255 xpt_async(AC_LOST_DEVICE, camsc->path, NULL); 256 xpt_free_path(camsc->path); 257 xpt_bus_deregister(cam_sim_path(camsc->sim)); 258 cam_sim_free(camsc->sim, /*free_devq*/TRUE); 259 260 sc->cam_rescan_cb = NULL; 261 262 mtx_unlock(&sc->aac_io_lock); 263 264 return (0); 265 } 266 267 /* 268 * Register the driver as a CAM SIM 269 */ 270 static int 271 aac_cam_attach(device_t dev) 272 { 273 struct cam_devq *devq; 274 struct cam_sim *sim; 275 struct cam_path *path; 276 struct aac_cam *camsc; 277 struct aac_sim *inf; 278 279 camsc = (struct aac_cam *)device_get_softc(dev); 280 inf = (struct aac_sim *)device_get_ivars(dev); 281 if (!inf) 282 return (EIO); 283 fwprintf(inf->aac_sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, ""); 284 camsc->inf = inf; 285 camsc->inf->aac_cam = camsc; 286 287 devq = cam_simq_alloc(inf->TargetsPerBus); 288 if (devq == NULL) 289 return (EIO); 290 291 sim = aac_sim_alloc(aac_cam_action, aac_cam_poll, "aacraidp", camsc, 292 device_get_unit(dev), &inf->aac_sc->aac_io_lock, 1, 1, devq); 293 if (sim == NULL) { 294 cam_simq_free(devq); 295 return (EIO); 296 } 297 298 /* Since every bus has it's own sim, every bus 'appears' as bus 0 */ 299 mtx_lock(&inf->aac_sc->aac_io_lock); 300 if (aac_xpt_bus_register(sim, dev, 0) != CAM_SUCCESS) { 301 cam_sim_free(sim, TRUE); 302 mtx_unlock(&inf->aac_sc->aac_io_lock); 303 return (EIO); 304 } 305 306 if (xpt_create_path(&path, NULL, cam_sim_path(sim), 307 CAM_TARGET_WILDCARD, CAM_LUN_WILDCARD) != CAM_REQ_CMP) { 308 xpt_bus_deregister(cam_sim_path(sim)); 309 cam_sim_free(sim, TRUE); 310 mtx_unlock(&inf->aac_sc->aac_io_lock); 311 return (EIO); 312 } 313 314 inf->aac_sc->cam_rescan_cb = aac_cam_rescan; 315 mtx_unlock(&inf->aac_sc->aac_io_lock); 316 317 camsc->sim = sim; 318 camsc->path = path; 319 320 return (0); 321 } 322 323 static u_int64_t 324 aac_eval_blockno(u_int8_t *cmdp) 325 { 326 u_int64_t blockno; 327 328 switch (cmdp[0]) { 329 case READ_6: 330 case WRITE_6: 331 blockno = scsi_3btoul(((struct scsi_rw_6 *)cmdp)->addr); 332 break; 333 case READ_10: 334 case WRITE_10: 335 blockno = scsi_4btoul(((struct scsi_rw_10 *)cmdp)->addr); 336 break; 337 case READ_12: 338 case WRITE_12: 339 blockno = scsi_4btoul(((struct scsi_rw_12 *)cmdp)->addr); 340 break; 341 case READ_16: 342 case WRITE_16: 343 blockno = scsi_8btou64(((struct scsi_rw_16 *)cmdp)->addr); 344 break; 345 default: 346 blockno = 0; 347 break; 348 } 349 return(blockno); 350 } 351 352 static void 353 aac_container_rw_command(struct cam_sim *sim, union ccb *ccb, u_int8_t *cmdp) 354 { 355 struct aac_cam *camsc; 356 struct aac_softc *sc; 357 struct aac_command *cm; 358 struct aac_fib *fib; 359 u_int64_t blockno; 360 361 camsc = (struct aac_cam *)cam_sim_softc(sim); 362 sc = camsc->inf->aac_sc; 363 mtx_assert(&sc->aac_io_lock, MA_OWNED); 364 365 if (aacraid_alloc_command(sc, &cm)) { 366 struct aac_event *event; 367 368 xpt_freeze_simq(sim, 1); 369 ccb->ccb_h.status = CAM_RESRC_UNAVAIL; 370 ccb->ccb_h.sim_priv.entries[0].ptr = camsc; 371 event = malloc(sizeof(struct aac_event), M_AACRAIDCAM, 372 M_NOWAIT | M_ZERO); 373 if (event == NULL) { 374 device_printf(sc->aac_dev, 375 "Warning, out of memory for event\n"); 376 return; 377 } 378 event->ev_callback = aac_cam_event; 379 event->ev_arg = ccb; 380 event->ev_type = AAC_EVENT_CMFREE; 381 aacraid_add_event(sc, event); 382 return; 383 } 384 385 fib = cm->cm_fib; 386 switch (ccb->ccb_h.flags & CAM_DIR_MASK) { 387 case CAM_DIR_IN: 388 cm->cm_flags |= AAC_CMD_DATAIN; 389 break; 390 case CAM_DIR_OUT: 391 cm->cm_flags |= AAC_CMD_DATAOUT; 392 break; 393 case CAM_DIR_NONE: 394 break; 395 default: 396 cm->cm_flags |= AAC_CMD_DATAIN | AAC_CMD_DATAOUT; 397 break; 398 } 399 400 blockno = aac_eval_blockno(cmdp); 401 402 cm->cm_complete = aac_container_complete; 403 cm->cm_ccb = ccb; 404 cm->cm_timestamp = time_uptime; 405 cm->cm_data = (void *)ccb->csio.data_ptr; 406 cm->cm_datalen = ccb->csio.dxfer_len; 407 408 fib->Header.Size = sizeof(struct aac_fib_header); 409 fib->Header.XferState = 410 AAC_FIBSTATE_HOSTOWNED | 411 AAC_FIBSTATE_INITIALISED | 412 AAC_FIBSTATE_EMPTY | 413 AAC_FIBSTATE_FROMHOST | 414 AAC_FIBSTATE_REXPECTED | 415 AAC_FIBSTATE_NORM | 416 AAC_FIBSTATE_ASYNC | 417 AAC_FIBSTATE_FAST_RESPONSE; 418 419 if (sc->flags & AAC_FLAGS_NEW_COMM_TYPE2) { 420 struct aac_raw_io2 *raw; 421 /* NOTE: LE conversion handled at aacraid_map_command_sg() */ 422 raw = (struct aac_raw_io2 *)&fib->data[0]; 423 bzero(raw, sizeof(struct aac_raw_io2)); 424 fib->Header.Command = RawIo2; 425 raw->strtBlkLow = (u_int32_t)blockno; 426 raw->strtBlkHigh = (u_int32_t)(blockno >> 32); 427 raw->byteCnt = cm->cm_datalen; 428 raw->ldNum = ccb->ccb_h.target_id; 429 fib->Header.Size += sizeof(struct aac_raw_io2); 430 cm->cm_sgtable = (struct aac_sg_table *)raw->sge; 431 if (cm->cm_flags & AAC_CMD_DATAIN) 432 raw->flags = RIO2_IO_TYPE_READ | RIO2_SG_FORMAT_IEEE1212; 433 else 434 raw->flags = RIO2_IO_TYPE_WRITE | RIO2_SG_FORMAT_IEEE1212; 435 } else if (sc->flags & AAC_FLAGS_RAW_IO) { 436 struct aac_raw_io *raw; 437 /* NOTE: LE conversion handled at aacraid_map_command_sg() */ 438 raw = (struct aac_raw_io *)&fib->data[0]; 439 bzero(raw, sizeof(struct aac_raw_io)); 440 fib->Header.Command = RawIo; 441 raw->BlockNumber = blockno; 442 raw->ByteCount = cm->cm_datalen; 443 raw->ContainerId = ccb->ccb_h.target_id; 444 fib->Header.Size += sizeof(struct aac_raw_io); 445 cm->cm_sgtable = (struct aac_sg_table *) 446 &raw->SgMapRaw; 447 if (cm->cm_flags & AAC_CMD_DATAIN) 448 raw->Flags = 1; 449 } else if ((sc->flags & AAC_FLAGS_SG_64BIT) == 0) { 450 fib->Header.Command = ContainerCommand; 451 if (cm->cm_flags & AAC_CMD_DATAIN) { 452 struct aac_blockread *br; 453 br = (struct aac_blockread *)&fib->data[0]; 454 br->Command = VM_CtBlockRead; 455 br->ContainerId = ccb->ccb_h.target_id; 456 br->BlockNumber = blockno; 457 br->ByteCount = cm->cm_datalen; 458 aac_blockread_tole(br); 459 fib->Header.Size += sizeof(struct aac_blockread); 460 cm->cm_sgtable = &br->SgMap; 461 } else { 462 struct aac_blockwrite *bw; 463 bw = (struct aac_blockwrite *)&fib->data[0]; 464 bw->Command = VM_CtBlockWrite; 465 bw->ContainerId = ccb->ccb_h.target_id; 466 bw->BlockNumber = blockno; 467 bw->ByteCount = cm->cm_datalen; 468 bw->Stable = CUNSTABLE; 469 aac_blockwrite_tole(bw); 470 fib->Header.Size += sizeof(struct aac_blockwrite); 471 cm->cm_sgtable = &bw->SgMap; 472 } 473 } else { 474 fib->Header.Command = ContainerCommand64; 475 if (cm->cm_flags & AAC_CMD_DATAIN) { 476 struct aac_blockread64 *br; 477 br = (struct aac_blockread64 *)&fib->data[0]; 478 br->Command = VM_CtHostRead64; 479 br->ContainerId = ccb->ccb_h.target_id; 480 br->SectorCount = cm->cm_datalen/AAC_BLOCK_SIZE; 481 br->BlockNumber = blockno; 482 br->Pad = 0; 483 br->Flags = 0; 484 aac_blockread64_tole(br); 485 fib->Header.Size += sizeof(struct aac_blockread64); 486 cm->cm_sgtable = (struct aac_sg_table *)&br->SgMap64; 487 } else { 488 struct aac_blockwrite64 *bw; 489 bw = (struct aac_blockwrite64 *)&fib->data[0]; 490 bw->Command = VM_CtHostWrite64; 491 bw->ContainerId = ccb->ccb_h.target_id; 492 bw->SectorCount = cm->cm_datalen/AAC_BLOCK_SIZE; 493 bw->BlockNumber = blockno; 494 bw->Pad = 0; 495 bw->Flags = 0; 496 aac_blockwrite64_tole(bw); 497 fib->Header.Size += sizeof(struct aac_blockwrite64); 498 cm->cm_sgtable = (struct aac_sg_table *)&bw->SgMap64; 499 } 500 } 501 aac_enqueue_ready(cm); 502 aacraid_startio(cm->cm_sc); 503 } 504 505 static void 506 aac_container_special_command(struct cam_sim *sim, union ccb *ccb, 507 u_int8_t *cmdp) 508 { 509 struct aac_cam *camsc; 510 struct aac_softc *sc; 511 struct aac_container *co; 512 513 camsc = (struct aac_cam *)cam_sim_softc(sim); 514 sc = camsc->inf->aac_sc; 515 mtx_assert(&sc->aac_io_lock, MA_OWNED); 516 517 TAILQ_FOREACH(co, &sc->aac_container_tqh, co_link) { 518 fwprintf(sc, HBA_FLAGS_DBG_ERROR_B, "found container %d search for %d", co->co_mntobj.ObjectId, ccb->ccb_h.target_id); 519 if (co->co_mntobj.ObjectId == ccb->ccb_h.target_id) 520 break; 521 } 522 if (co == NULL || ccb->ccb_h.target_lun != 0) { 523 fwprintf(sc, HBA_FLAGS_DBG_ERROR_B, 524 "Container not present: cmd 0x%x id %d lun %d len %d", 525 *cmdp, ccb->ccb_h.target_id, ccb->ccb_h.target_lun, 526 ccb->csio.dxfer_len); 527 ccb->ccb_h.status = CAM_DEV_NOT_THERE; 528 xpt_done(ccb); 529 return; 530 } 531 532 if (ccb->csio.dxfer_len) 533 bzero(ccb->csio.data_ptr, ccb->csio.dxfer_len); 534 535 switch (*cmdp) { 536 case INQUIRY: 537 { 538 struct scsi_inquiry *inq = (struct scsi_inquiry *)cmdp; 539 540 fwprintf(sc, HBA_FLAGS_DBG_COMM_B, 541 "Container INQUIRY id %d lun %d len %d VPD 0x%x Page 0x%x", 542 ccb->ccb_h.target_id, ccb->ccb_h.target_lun, 543 ccb->csio.dxfer_len, inq->byte2, inq->page_code); 544 if (!(inq->byte2 & SI_EVPD)) { 545 struct scsi_inquiry_data *p = 546 (struct scsi_inquiry_data *)ccb->csio.data_ptr; 547 if (inq->page_code != 0) { 548 aac_set_scsi_error(sc, ccb, 549 SCSI_STATUS_CHECK_COND, 550 SSD_KEY_ILLEGAL_REQUEST, 0x24, 0x00); 551 xpt_done(ccb); 552 return; 553 } 554 p->device = T_DIRECT; 555 p->version = SCSI_REV_SPC2; 556 p->response_format = 2; 557 if (ccb->csio.dxfer_len >= 36) { 558 p->additional_length = 31; 559 p->flags = SID_WBus16|SID_Sync|SID_CmdQue; 560 /* OEM Vendor defines */ 561 strncpy(p->vendor, "Adaptec ", sizeof(p->vendor)); 562 strncpy(p->product, "Array ", 563 sizeof(p->product)); 564 strncpy(p->revision, "V1.0", 565 sizeof(p->revision)); 566 } 567 } else { 568 if (inq->page_code == SVPD_SUPPORTED_PAGE_LIST) { 569 struct scsi_vpd_supported_page_list *p = 570 (struct scsi_vpd_supported_page_list *) 571 ccb->csio.data_ptr; 572 p->device = T_DIRECT; 573 p->page_code = SVPD_SUPPORTED_PAGE_LIST; 574 p->length = 2; 575 p->list[0] = SVPD_SUPPORTED_PAGE_LIST; 576 p->list[1] = SVPD_UNIT_SERIAL_NUMBER; 577 } else if (inq->page_code == SVPD_UNIT_SERIAL_NUMBER) { 578 struct scsi_vpd_unit_serial_number *p = 579 (struct scsi_vpd_unit_serial_number *) 580 ccb->csio.data_ptr; 581 p->device = T_DIRECT; 582 p->page_code = SVPD_UNIT_SERIAL_NUMBER; 583 p->length = sprintf((char *)p->serial_num, 584 "%08X%02X", co->co_uid, 585 ccb->ccb_h.target_id); 586 } else { 587 aac_set_scsi_error(sc, ccb, 588 SCSI_STATUS_CHECK_COND, 589 SSD_KEY_ILLEGAL_REQUEST, 0x24, 0x00); 590 xpt_done(ccb); 591 return; 592 } 593 } 594 ccb->ccb_h.status = CAM_REQ_CMP; 595 break; 596 } 597 598 case REPORT_LUNS: 599 fwprintf(sc, HBA_FLAGS_DBG_COMM_B, 600 "Container REPORT_LUNS id %d lun %d len %d", 601 ccb->ccb_h.target_id, ccb->ccb_h.target_lun, 602 ccb->csio.dxfer_len); 603 ccb->ccb_h.status = CAM_REQ_CMP; 604 break; 605 606 case START_STOP: 607 { 608 struct scsi_start_stop_unit *ss = 609 (struct scsi_start_stop_unit *)cmdp; 610 fwprintf(sc, HBA_FLAGS_DBG_COMM_B, 611 "Container START_STOP id %d lun %d len %d", 612 ccb->ccb_h.target_id, ccb->ccb_h.target_lun, 613 ccb->csio.dxfer_len); 614 if (sc->aac_support_opt2 & AAC_SUPPORTED_POWER_MANAGEMENT) { 615 struct aac_command *cm; 616 struct aac_fib *fib; 617 struct aac_cnt_config *ccfg; 618 619 if (aacraid_alloc_command(sc, &cm)) { 620 struct aac_event *event; 621 622 xpt_freeze_simq(sim, 1); 623 ccb->ccb_h.status = CAM_RESRC_UNAVAIL; 624 ccb->ccb_h.sim_priv.entries[0].ptr = camsc; 625 event = malloc(sizeof(struct aac_event), M_AACRAIDCAM, 626 M_NOWAIT | M_ZERO); 627 if (event == NULL) { 628 device_printf(sc->aac_dev, 629 "Warning, out of memory for event\n"); 630 return; 631 } 632 event->ev_callback = aac_cam_event; 633 event->ev_arg = ccb; 634 event->ev_type = AAC_EVENT_CMFREE; 635 aacraid_add_event(sc, event); 636 return; 637 } 638 639 fib = cm->cm_fib; 640 cm->cm_timestamp = time_uptime; 641 cm->cm_datalen = 0; 642 643 fib->Header.Size = 644 sizeof(struct aac_fib_header) + sizeof(struct aac_cnt_config); 645 fib->Header.XferState = 646 AAC_FIBSTATE_HOSTOWNED | 647 AAC_FIBSTATE_INITIALISED | 648 AAC_FIBSTATE_EMPTY | 649 AAC_FIBSTATE_FROMHOST | 650 AAC_FIBSTATE_REXPECTED | 651 AAC_FIBSTATE_NORM | 652 AAC_FIBSTATE_ASYNC | 653 AAC_FIBSTATE_FAST_RESPONSE; 654 fib->Header.Command = ContainerCommand; 655 656 /* Start unit */ 657 ccfg = (struct aac_cnt_config *)&fib->data[0]; 658 bzero(ccfg, sizeof (*ccfg) - CT_PACKET_SIZE); 659 ccfg->Command = VM_ContainerConfig; 660 ccfg->CTCommand.command = CT_PM_DRIVER_SUPPORT; 661 ccfg->CTCommand.param[0] = (ss->how & SSS_START ? 662 AAC_PM_DRIVERSUP_START_UNIT : 663 AAC_PM_DRIVERSUP_STOP_UNIT); 664 ccfg->CTCommand.param[1] = co->co_mntobj.ObjectId; 665 ccfg->CTCommand.param[2] = 0; /* 1 - immediate */ 666 aac_cnt_config_tole(ccfg); 667 668 if (aacraid_wait_command(cm) != 0 || 669 le32toh(*(u_int32_t *)&fib->data[0]) != 0) { 670 printf("Power Management: Error start/stop container %d\n", 671 co->co_mntobj.ObjectId); 672 } 673 aacraid_release_command(cm); 674 } 675 ccb->ccb_h.status = CAM_REQ_CMP; 676 break; 677 } 678 679 case TEST_UNIT_READY: 680 fwprintf(sc, HBA_FLAGS_DBG_COMM_B, 681 "Container TEST_UNIT_READY id %d lun %d len %d", 682 ccb->ccb_h.target_id, ccb->ccb_h.target_lun, 683 ccb->csio.dxfer_len); 684 ccb->ccb_h.status = CAM_REQ_CMP; 685 break; 686 687 case REQUEST_SENSE: 688 fwprintf(sc, HBA_FLAGS_DBG_COMM_B, 689 "Container REQUEST_SENSE id %d lun %d len %d", 690 ccb->ccb_h.target_id, ccb->ccb_h.target_lun, 691 ccb->csio.dxfer_len); 692 ccb->ccb_h.status = CAM_REQ_CMP; 693 break; 694 695 case READ_CAPACITY: 696 { 697 struct scsi_read_capacity_data *p = 698 (struct scsi_read_capacity_data *)ccb->csio.data_ptr; 699 fwprintf(sc, HBA_FLAGS_DBG_COMM_B, 700 "Container READ_CAPACITY id %d lun %d len %d", 701 ccb->ccb_h.target_id, ccb->ccb_h.target_lun, 702 ccb->csio.dxfer_len); 703 scsi_ulto4b(co->co_mntobj.ObjExtension.BlockDevice.BlockSize, p->length); 704 /* check if greater than 2TB */ 705 if (co->co_mntobj.CapacityHigh) { 706 if (sc->flags & AAC_FLAGS_LBA_64BIT) 707 scsi_ulto4b(0xffffffff, p->addr); 708 } else { 709 scsi_ulto4b(co->co_mntobj.Capacity-1, p->addr); 710 } 711 ccb->ccb_h.status = CAM_REQ_CMP; 712 break; 713 } 714 715 case SERVICE_ACTION_IN: 716 { 717 struct scsi_read_capacity_data_long *p = 718 (struct scsi_read_capacity_data_long *) 719 ccb->csio.data_ptr; 720 fwprintf(sc, HBA_FLAGS_DBG_COMM_B, 721 "Container SERVICE_ACTION_IN id %d lun %d len %d", 722 ccb->ccb_h.target_id, ccb->ccb_h.target_lun, 723 ccb->csio.dxfer_len); 724 if (((struct scsi_read_capacity_16 *)cmdp)->service_action != 725 SRC16_SERVICE_ACTION) { 726 aac_set_scsi_error(sc, ccb, SCSI_STATUS_CHECK_COND, 727 SSD_KEY_ILLEGAL_REQUEST, 0x24, 0x00); 728 xpt_done(ccb); 729 return; 730 } 731 scsi_ulto4b(co->co_mntobj.ObjExtension.BlockDevice.BlockSize, p->length); 732 scsi_ulto4b(co->co_mntobj.CapacityHigh, p->addr); 733 scsi_ulto4b(co->co_mntobj.Capacity-1, &p->addr[4]); 734 735 if (ccb->csio.dxfer_len >= 14) { 736 u_int32_t mapping = co->co_mntobj.ObjExtension.BlockDevice.bdLgclPhysMap; 737 p->prot_lbppbe = 0; 738 while (mapping > 1) { 739 mapping >>= 1; 740 p->prot_lbppbe++; 741 } 742 p->prot_lbppbe &= 0x0f; 743 } 744 745 ccb->ccb_h.status = CAM_REQ_CMP; 746 break; 747 } 748 749 case MODE_SENSE_6: 750 { 751 struct scsi_mode_sense_6 *msp =(struct scsi_mode_sense_6 *)cmdp; 752 struct ms6_data { 753 struct scsi_mode_hdr_6 hd; 754 struct scsi_mode_block_descr bd; 755 char pages; 756 } *p = (struct ms6_data *)ccb->csio.data_ptr; 757 char *pagep; 758 int return_all_pages = FALSE; 759 760 fwprintf(sc, HBA_FLAGS_DBG_COMM_B, 761 "Container MODE_SENSE id %d lun %d len %d page %d", 762 ccb->ccb_h.target_id, ccb->ccb_h.target_lun, 763 ccb->csio.dxfer_len, msp->page); 764 p->hd.datalen = sizeof(struct scsi_mode_hdr_6) - 1; 765 if (co->co_mntobj.ContentState & AAC_FSCS_READONLY) 766 p->hd.dev_specific = 0x80; /* WP */ 767 p->hd.dev_specific |= 0x10; /* DPOFUA */ 768 if (msp->byte2 & SMS_DBD) { 769 p->hd.block_descr_len = 0; 770 } else { 771 p->hd.block_descr_len = 772 sizeof(struct scsi_mode_block_descr); 773 p->hd.datalen += p->hd.block_descr_len; 774 scsi_ulto3b(co->co_mntobj.ObjExtension.BlockDevice.BlockSize, p->bd.block_len); 775 if (co->co_mntobj.Capacity > 0xffffff || 776 co->co_mntobj.CapacityHigh) { 777 p->bd.num_blocks[0] = 0xff; 778 p->bd.num_blocks[1] = 0xff; 779 p->bd.num_blocks[2] = 0xff; 780 } else { 781 p->bd.num_blocks[0] = (u_int8_t) 782 (co->co_mntobj.Capacity >> 16); 783 p->bd.num_blocks[1] = (u_int8_t) 784 (co->co_mntobj.Capacity >> 8); 785 p->bd.num_blocks[2] = (u_int8_t) 786 (co->co_mntobj.Capacity); 787 } 788 } 789 pagep = &p->pages; 790 switch (msp->page & SMS_PAGE_CODE) { 791 case SMS_ALL_PAGES_PAGE: 792 return_all_pages = TRUE; 793 case SMS_CONTROL_MODE_PAGE: 794 { 795 struct scsi_control_page *cp = 796 (struct scsi_control_page *)pagep; 797 798 if (ccb->csio.dxfer_len <= p->hd.datalen + 8) { 799 aac_set_scsi_error(sc, ccb, 800 SCSI_STATUS_CHECK_COND, 801 SSD_KEY_ILLEGAL_REQUEST, 0x24, 0x00); 802 xpt_done(ccb); 803 return; 804 } 805 cp->page_code = SMS_CONTROL_MODE_PAGE; 806 cp->page_length = 6; 807 p->hd.datalen += 8; 808 pagep += 8; 809 if (!return_all_pages) 810 break; 811 } 812 case SMS_VENDOR_SPECIFIC_PAGE: 813 break; 814 default: 815 aac_set_scsi_error(sc, ccb, SCSI_STATUS_CHECK_COND, 816 SSD_KEY_ILLEGAL_REQUEST, 0x24, 0x00); 817 xpt_done(ccb); 818 return; 819 } 820 ccb->ccb_h.status = CAM_REQ_CMP; 821 break; 822 } 823 824 case SYNCHRONIZE_CACHE: 825 fwprintf(sc, HBA_FLAGS_DBG_COMM_B, 826 "Container SYNCHRONIZE_CACHE id %d lun %d len %d", 827 ccb->ccb_h.target_id, ccb->ccb_h.target_lun, 828 ccb->csio.dxfer_len); 829 ccb->ccb_h.status = CAM_REQ_CMP; 830 break; 831 832 default: 833 fwprintf(sc, HBA_FLAGS_DBG_ERROR_B, 834 "Container unsupp. cmd 0x%x id %d lun %d len %d", 835 *cmdp, ccb->ccb_h.target_id, ccb->ccb_h.target_lun, 836 ccb->csio.dxfer_len); 837 ccb->ccb_h.status = CAM_REQ_CMP; /*CAM_REQ_INVALID*/ 838 break; 839 } 840 xpt_done(ccb); 841 } 842 843 static void 844 aac_passthrough_command(struct cam_sim *sim, union ccb *ccb) 845 { 846 struct aac_cam *camsc; 847 struct aac_softc *sc; 848 struct aac_command *cm; 849 struct aac_fib *fib; 850 struct aac_srb *srb; 851 852 camsc = (struct aac_cam *)cam_sim_softc(sim); 853 sc = camsc->inf->aac_sc; 854 mtx_assert(&sc->aac_io_lock, MA_OWNED); 855 856 if (aacraid_alloc_command(sc, &cm)) { 857 struct aac_event *event; 858 859 xpt_freeze_simq(sim, 1); 860 ccb->ccb_h.status = CAM_RESRC_UNAVAIL; 861 ccb->ccb_h.sim_priv.entries[0].ptr = camsc; 862 event = malloc(sizeof(struct aac_event), M_AACRAIDCAM, 863 M_NOWAIT | M_ZERO); 864 if (event == NULL) { 865 device_printf(sc->aac_dev, 866 "Warning, out of memory for event\n"); 867 return; 868 } 869 event->ev_callback = aac_cam_event; 870 event->ev_arg = ccb; 871 event->ev_type = AAC_EVENT_CMFREE; 872 aacraid_add_event(sc, event); 873 return; 874 } 875 876 fib = cm->cm_fib; 877 switch (ccb->ccb_h.flags & CAM_DIR_MASK) { 878 case CAM_DIR_IN: 879 cm->cm_flags |= AAC_CMD_DATAIN; 880 break; 881 case CAM_DIR_OUT: 882 cm->cm_flags |= AAC_CMD_DATAOUT; 883 break; 884 case CAM_DIR_NONE: 885 break; 886 default: 887 cm->cm_flags |= AAC_CMD_DATAIN | AAC_CMD_DATAOUT; 888 break; 889 } 890 891 srb = (struct aac_srb *)&fib->data[0]; 892 srb->function = AAC_SRB_FUNC_EXECUTE_SCSI; 893 if (cm->cm_flags & (AAC_CMD_DATAIN|AAC_CMD_DATAOUT)) 894 srb->flags = AAC_SRB_FLAGS_UNSPECIFIED_DIRECTION; 895 if (cm->cm_flags & AAC_CMD_DATAIN) 896 srb->flags = AAC_SRB_FLAGS_DATA_IN; 897 else if (cm->cm_flags & AAC_CMD_DATAOUT) 898 srb->flags = AAC_SRB_FLAGS_DATA_OUT; 899 else 900 srb->flags = AAC_SRB_FLAGS_NO_DATA_XFER; 901 902 /* 903 * Copy the CDB into the SRB. It's only 6-16 bytes, 904 * so a copy is not too expensive. 905 */ 906 srb->cdb_len = ccb->csio.cdb_len; 907 if (ccb->ccb_h.flags & CAM_CDB_POINTER) 908 bcopy(ccb->csio.cdb_io.cdb_ptr, (u_int8_t *)&srb->cdb[0], 909 srb->cdb_len); 910 else 911 bcopy(ccb->csio.cdb_io.cdb_bytes, (u_int8_t *)&srb->cdb[0], 912 srb->cdb_len); 913 914 /* Set command */ 915 fib->Header.Command = (sc->flags & AAC_FLAGS_SG_64BIT) ? 916 ScsiPortCommandU64 : ScsiPortCommand; 917 fib->Header.Size = sizeof(struct aac_fib_header) + 918 sizeof(struct aac_srb); 919 920 /* Map the s/g list */ 921 cm->cm_sgtable = &srb->sg_map; 922 if ((ccb->ccb_h.flags & CAM_DIR_MASK) != CAM_DIR_NONE) { 923 /* 924 * Arrange things so that the S/G 925 * map will get set up automagically 926 */ 927 cm->cm_data = (void *)ccb->csio.data_ptr; 928 cm->cm_datalen = ccb->csio.dxfer_len; 929 srb->data_len = ccb->csio.dxfer_len; 930 } else { 931 cm->cm_data = NULL; 932 cm->cm_datalen = 0; 933 srb->data_len = 0; 934 } 935 936 srb->bus = camsc->inf->BusNumber - 1; /* Bus no. rel. to the card */ 937 srb->target = ccb->ccb_h.target_id; 938 srb->lun = ccb->ccb_h.target_lun; 939 srb->timeout = ccb->ccb_h.timeout; /* XXX */ 940 srb->retry_limit = 0; 941 aac_srb_tole(srb); 942 943 cm->cm_complete = aac_cam_complete; 944 cm->cm_ccb = ccb; 945 cm->cm_timestamp = time_uptime; 946 947 fib->Header.XferState = 948 AAC_FIBSTATE_HOSTOWNED | 949 AAC_FIBSTATE_INITIALISED | 950 AAC_FIBSTATE_FROMHOST | 951 AAC_FIBSTATE_REXPECTED | 952 AAC_FIBSTATE_NORM | 953 AAC_FIBSTATE_ASYNC | 954 AAC_FIBSTATE_FAST_RESPONSE; 955 956 aac_enqueue_ready(cm); 957 aacraid_startio(cm->cm_sc); 958 } 959 960 static void 961 aac_cam_action(struct cam_sim *sim, union ccb *ccb) 962 { 963 struct aac_cam *camsc; 964 struct aac_softc *sc; 965 966 camsc = (struct aac_cam *)cam_sim_softc(sim); 967 sc = camsc->inf->aac_sc; 968 fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, ""); 969 mtx_assert(&sc->aac_io_lock, MA_OWNED); 970 971 /* Synchronous ops, and ops that don't require communication with the 972 * controller */ 973 switch(ccb->ccb_h.func_code) { 974 case XPT_SCSI_IO: 975 /* This is handled down below */ 976 break; 977 case XPT_CALC_GEOMETRY: 978 { 979 struct ccb_calc_geometry *ccg; 980 u_int32_t size_mb; 981 u_int32_t secs_per_cylinder; 982 983 ccg = &ccb->ccg; 984 size_mb = ccg->volume_size / 985 ((1024L * 1024L) / ccg->block_size); 986 if (size_mb >= (2 * 1024)) { /* 2GB */ 987 ccg->heads = 255; 988 ccg->secs_per_track = 63; 989 } else if (size_mb >= (1 * 1024)) { /* 1GB */ 990 ccg->heads = 128; 991 ccg->secs_per_track = 32; 992 } else { 993 ccg->heads = 64; 994 ccg->secs_per_track = 32; 995 } 996 secs_per_cylinder = ccg->heads * ccg->secs_per_track; 997 ccg->cylinders = ccg->volume_size / secs_per_cylinder; 998 999 ccb->ccb_h.status = CAM_REQ_CMP; 1000 xpt_done(ccb); 1001 return; 1002 } 1003 case XPT_PATH_INQ: 1004 { 1005 struct ccb_pathinq *cpi = &ccb->cpi; 1006 1007 cpi->version_num = 1; 1008 cpi->target_sprt = 0; 1009 cpi->hba_eng_cnt = 0; 1010 cpi->max_target = camsc->inf->TargetsPerBus - 1; 1011 cpi->max_lun = 7; /* Per the controller spec */ 1012 cpi->initiator_id = camsc->inf->InitiatorBusId; 1013 cpi->bus_id = camsc->inf->BusNumber; 1014 cpi->maxio = AAC_MAXIO_SIZE(sc); 1015 1016 /* 1017 * Resetting via the passthrough or parallel bus scan 1018 * causes problems. 1019 */ 1020 cpi->hba_misc = PIM_NOBUSRESET; 1021 cpi->hba_inquiry = PI_TAG_ABLE; 1022 cpi->base_transfer_speed = 300000; 1023 #ifdef CAM_NEW_TRAN_CODE 1024 cpi->hba_misc |= PIM_SEQSCAN; 1025 cpi->protocol = PROTO_SCSI; 1026 cpi->transport = XPORT_SAS; 1027 cpi->transport_version = 0; 1028 cpi->protocol_version = SCSI_REV_SPC2; 1029 #endif 1030 strlcpy(cpi->sim_vid, "FreeBSD", SIM_IDLEN); 1031 strlcpy(cpi->hba_vid, "PMC-Sierra", HBA_IDLEN); 1032 strlcpy(cpi->dev_name, cam_sim_name(sim), DEV_IDLEN); 1033 cpi->unit_number = cam_sim_unit(sim); 1034 ccb->ccb_h.status = CAM_REQ_CMP; 1035 xpt_done(ccb); 1036 return; 1037 } 1038 case XPT_GET_TRAN_SETTINGS: 1039 { 1040 #ifdef CAM_NEW_TRAN_CODE 1041 struct ccb_trans_settings_scsi *scsi = 1042 &ccb->cts.proto_specific.scsi; 1043 struct ccb_trans_settings_spi *spi = 1044 &ccb->cts.xport_specific.spi; 1045 ccb->cts.protocol = PROTO_SCSI; 1046 ccb->cts.protocol_version = SCSI_REV_SPC2; 1047 ccb->cts.transport = XPORT_SAS; 1048 ccb->cts.transport_version = 0; 1049 scsi->valid = CTS_SCSI_VALID_TQ; 1050 scsi->flags = CTS_SCSI_FLAGS_TAG_ENB; 1051 spi->valid |= CTS_SPI_VALID_DISC; 1052 spi->flags |= CTS_SPI_FLAGS_DISC_ENB; 1053 #else 1054 ccb->cts.flags = ~(CCB_TRANS_DISC_ENB | CCB_TRANS_TAG_ENB); 1055 ccb->cts.valid = CCB_TRANS_DISC_VALID | CCB_TRANS_TQ_VALID; 1056 #endif 1057 ccb->ccb_h.status = CAM_REQ_CMP; 1058 xpt_done(ccb); 1059 return; 1060 } 1061 case XPT_SET_TRAN_SETTINGS: 1062 ccb->ccb_h.status = CAM_FUNC_NOTAVAIL; 1063 xpt_done(ccb); 1064 return; 1065 case XPT_RESET_BUS: 1066 if (!(sc->flags & AAC_FLAGS_CAM_NORESET) && 1067 camsc->inf->BusType != CONTAINER_BUS) { 1068 ccb->ccb_h.status = aac_cam_reset_bus(sim, ccb); 1069 } else { 1070 ccb->ccb_h.status = CAM_REQ_CMP; 1071 } 1072 xpt_done(ccb); 1073 return; 1074 case XPT_RESET_DEV: 1075 ccb->ccb_h.status = CAM_REQ_CMP; 1076 xpt_done(ccb); 1077 return; 1078 case XPT_ABORT: 1079 ccb->ccb_h.status = aac_cam_abort_ccb(sim, ccb); 1080 xpt_done(ccb); 1081 return; 1082 case XPT_TERM_IO: 1083 ccb->ccb_h.status = aac_cam_term_io(sim, ccb); 1084 xpt_done(ccb); 1085 return; 1086 default: 1087 device_printf(sc->aac_dev, "Unsupported command 0x%x\n", 1088 ccb->ccb_h.func_code); 1089 ccb->ccb_h.status = CAM_PROVIDE_FAIL; 1090 xpt_done(ccb); 1091 return; 1092 } 1093 1094 /* Async ops that require communcation with the controller */ 1095 if (camsc->inf->BusType == CONTAINER_BUS) { 1096 u_int8_t *cmdp; 1097 1098 if (ccb->ccb_h.flags & CAM_CDB_POINTER) 1099 cmdp = ccb->csio.cdb_io.cdb_ptr; 1100 else 1101 cmdp = &ccb->csio.cdb_io.cdb_bytes[0]; 1102 1103 if (*cmdp==READ_6 || *cmdp==WRITE_6 || *cmdp==READ_10 || 1104 *cmdp==WRITE_10 || *cmdp==READ_12 || *cmdp==WRITE_12 || 1105 *cmdp==READ_16 || *cmdp==WRITE_16) 1106 aac_container_rw_command(sim, ccb, cmdp); 1107 else 1108 aac_container_special_command(sim, ccb, cmdp); 1109 } else { 1110 aac_passthrough_command(sim, ccb); 1111 } 1112 } 1113 1114 static void 1115 aac_cam_poll(struct cam_sim *sim) 1116 { 1117 /* 1118 * Pinging the interrupt routine isn't very safe, nor is it 1119 * really necessary. Do nothing. 1120 */ 1121 } 1122 1123 static void 1124 aac_container_complete(struct aac_command *cm) 1125 { 1126 union ccb *ccb; 1127 u_int32_t status; 1128 1129 fwprintf(cm->cm_sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, ""); 1130 ccb = cm->cm_ccb; 1131 status = le32toh(((u_int32_t *)cm->cm_fib->data)[0]); 1132 1133 if (cm->cm_flags & AAC_CMD_RESET) { 1134 ccb->ccb_h.status = CAM_SCSI_BUS_RESET; 1135 } else if (status == ST_OK) { 1136 ccb->ccb_h.status = CAM_REQ_CMP; 1137 } else if (status == ST_NOT_READY) { 1138 ccb->ccb_h.status = CAM_BUSY; 1139 } else { 1140 ccb->ccb_h.status = CAM_REQ_CMP_ERR; 1141 } 1142 1143 aacraid_release_command(cm); 1144 xpt_done(ccb); 1145 } 1146 1147 static void 1148 aac_cam_complete(struct aac_command *cm) 1149 { 1150 union ccb *ccb; 1151 struct aac_srb_response *srbr; 1152 struct aac_softc *sc; 1153 1154 sc = cm->cm_sc; 1155 fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, ""); 1156 ccb = cm->cm_ccb; 1157 srbr = (struct aac_srb_response *)&cm->cm_fib->data[0]; 1158 aac_srb_response_toh(srbr); 1159 1160 if (cm->cm_flags & AAC_CMD_FASTRESP) { 1161 /* fast response */ 1162 srbr->srb_status = CAM_REQ_CMP; 1163 srbr->scsi_status = SCSI_STATUS_OK; 1164 srbr->sense_len = 0; 1165 } 1166 1167 if (cm->cm_flags & AAC_CMD_RESET) { 1168 ccb->ccb_h.status = CAM_SCSI_BUS_RESET; 1169 } else if (srbr->fib_status != 0) { 1170 device_printf(sc->aac_dev, "Passthru FIB failed!\n"); 1171 ccb->ccb_h.status = CAM_REQ_ABORTED; 1172 } else { 1173 /* 1174 * The SRB error codes just happen to match the CAM error 1175 * codes. How convenient! 1176 */ 1177 ccb->ccb_h.status = srbr->srb_status; 1178 1179 /* Take care of SCSI_IO ops. */ 1180 if (ccb->ccb_h.func_code == XPT_SCSI_IO) { 1181 u_int8_t command, device; 1182 1183 ccb->csio.scsi_status = srbr->scsi_status; 1184 1185 /* Take care of autosense */ 1186 if (srbr->sense_len) { 1187 int sense_len, scsi_sense_len; 1188 1189 scsi_sense_len = sizeof(struct scsi_sense_data); 1190 bzero(&ccb->csio.sense_data, scsi_sense_len); 1191 sense_len = (srbr->sense_len > 1192 scsi_sense_len) ? scsi_sense_len : 1193 srbr->sense_len; 1194 bcopy(&srbr->sense[0], &ccb->csio.sense_data, 1195 sense_len); 1196 ccb->csio.sense_len = sense_len; 1197 ccb->ccb_h.status |= CAM_AUTOSNS_VALID; 1198 // scsi_sense_print(&ccb->csio); 1199 } 1200 1201 /* If this is an inquiry command, fake things out */ 1202 if (ccb->ccb_h.flags & CAM_CDB_POINTER) 1203 command = ccb->csio.cdb_io.cdb_ptr[0]; 1204 else 1205 command = ccb->csio.cdb_io.cdb_bytes[0]; 1206 1207 if (command == INQUIRY) { 1208 /* Ignore Data Overrun errors on INQUIRY */ 1209 if ((ccb->ccb_h.status & CAM_STATUS_MASK) == 1210 CAM_DATA_RUN_ERR) 1211 ccb->ccb_h.status = (ccb->ccb_h.status & 1212 ~CAM_STATUS_MASK) | CAM_REQ_CMP; 1213 1214 if (ccb->ccb_h.status == CAM_REQ_CMP) { 1215 device = ccb->csio.data_ptr[0] & 0x1f; 1216 /* 1217 * We want DASD and PROC devices to only be 1218 * visible through the pass device. 1219 */ 1220 if ((device == T_DIRECT && 1221 !(sc->aac_feature_bits & AAC_SUPPL_SUPPORTED_JBOD)) || 1222 (device == T_PROCESSOR)) 1223 ccb->csio.data_ptr[0] = 1224 ((device & 0xe0) | T_NODEVICE); 1225 1226 /* handle phys. components of a log. drive */ 1227 if (ccb->csio.data_ptr[0] & 0x20) { 1228 if (sc->hint_flags & 8) { 1229 /* expose phys. device (daXX) */ 1230 ccb->csio.data_ptr[0] &= 0xdf; 1231 } else { 1232 /* phys. device only visible through pass device (passXX) */ 1233 ccb->csio.data_ptr[0] |= 0x10; 1234 } 1235 } 1236 } else if (ccb->ccb_h.status == CAM_SEL_TIMEOUT && 1237 ccb->ccb_h.target_lun != 0) { 1238 /* fix for INQUIRYs on Lun>0 */ 1239 ccb->ccb_h.status = CAM_DEV_NOT_THERE; 1240 } 1241 } 1242 } 1243 } 1244 1245 aacraid_release_command(cm); 1246 xpt_done(ccb); 1247 } 1248 1249 static u_int32_t 1250 aac_cam_reset_bus(struct cam_sim *sim, union ccb *ccb) 1251 { 1252 struct aac_command *cm; 1253 struct aac_fib *fib; 1254 struct aac_softc *sc; 1255 struct aac_cam *camsc; 1256 struct aac_vmioctl *vmi; 1257 struct aac_resetbus *rbc; 1258 u_int32_t rval; 1259 1260 camsc = (struct aac_cam *)cam_sim_softc(sim); 1261 sc = camsc->inf->aac_sc; 1262 1263 if (sc == NULL) { 1264 printf("aac: Null sc?\n"); 1265 return (CAM_REQ_ABORTED); 1266 } 1267 1268 if (aacraid_alloc_command(sc, &cm)) { 1269 struct aac_event *event; 1270 1271 xpt_freeze_simq(sim, 1); 1272 ccb->ccb_h.status = CAM_RESRC_UNAVAIL; 1273 ccb->ccb_h.sim_priv.entries[0].ptr = camsc; 1274 event = malloc(sizeof(struct aac_event), M_AACRAIDCAM, 1275 M_NOWAIT | M_ZERO); 1276 if (event == NULL) { 1277 device_printf(sc->aac_dev, 1278 "Warning, out of memory for event\n"); 1279 return (CAM_REQ_ABORTED); 1280 } 1281 event->ev_callback = aac_cam_event; 1282 event->ev_arg = ccb; 1283 event->ev_type = AAC_EVENT_CMFREE; 1284 aacraid_add_event(sc, event); 1285 return (CAM_REQ_ABORTED); 1286 } 1287 1288 fib = cm->cm_fib; 1289 cm->cm_timestamp = time_uptime; 1290 cm->cm_datalen = 0; 1291 1292 fib->Header.Size = 1293 sizeof(struct aac_fib_header) + sizeof(struct aac_vmioctl); 1294 fib->Header.XferState = 1295 AAC_FIBSTATE_HOSTOWNED | 1296 AAC_FIBSTATE_INITIALISED | 1297 AAC_FIBSTATE_EMPTY | 1298 AAC_FIBSTATE_FROMHOST | 1299 AAC_FIBSTATE_REXPECTED | 1300 AAC_FIBSTATE_NORM | 1301 AAC_FIBSTATE_ASYNC | 1302 AAC_FIBSTATE_FAST_RESPONSE; 1303 fib->Header.Command = ContainerCommand; 1304 1305 vmi = (struct aac_vmioctl *)&fib->data[0]; 1306 bzero(vmi, sizeof(struct aac_vmioctl)); 1307 1308 vmi->Command = VM_Ioctl; 1309 vmi->ObjType = FT_DRIVE; 1310 vmi->MethId = sc->scsi_method_id; 1311 vmi->ObjId = 0; 1312 vmi->IoctlCmd = ResetBus; 1313 1314 rbc = (struct aac_resetbus *)&vmi->IoctlBuf[0]; 1315 rbc->BusNumber = camsc->inf->BusNumber - 1; 1316 aac_vmioctl_tole(vmi); 1317 1318 if (aacraid_wait_command(cm) != 0) { 1319 device_printf(sc->aac_dev,"Error sending ResetBus command\n"); 1320 rval = CAM_REQ_ABORTED; 1321 } else { 1322 rval = CAM_REQ_CMP; 1323 } 1324 aacraid_release_command(cm); 1325 return (rval); 1326 } 1327 1328 static u_int32_t 1329 aac_cam_abort_ccb(struct cam_sim *sim, union ccb *ccb) 1330 { 1331 return (CAM_UA_ABORT); 1332 } 1333 1334 static u_int32_t 1335 aac_cam_term_io(struct cam_sim *sim, union ccb *ccb) 1336 { 1337 return (CAM_UA_TERMIO); 1338 } 1339 1340 static int 1341 aac_load_map_command_sg(struct aac_softc *sc, struct aac_command *cm) 1342 { 1343 int error; 1344 1345 fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, ""); 1346 error = bus_dmamap_load(sc->aac_buffer_dmat, 1347 cm->cm_datamap, cm->cm_data, cm->cm_datalen, 1348 aacraid_map_command_sg, cm, 0); 1349 if (error == EINPROGRESS) { 1350 fwprintf(sc, HBA_FLAGS_DBG_INIT_B, "freezing queue\n"); 1351 sc->flags |= AAC_QUEUE_FRZN; 1352 error = 0; 1353 } else if (error != 0) { 1354 panic("aac_load_map_command_sg: unexpected error %d from " 1355 "busdma", error); 1356 } 1357 return(error); 1358 } 1359 1360 /* 1361 * Start as much queued I/O as possible on the controller 1362 */ 1363 void 1364 aacraid_startio(struct aac_softc *sc) 1365 { 1366 struct aac_command *cm; 1367 1368 fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, ""); 1369 1370 for (;;) { 1371 if (sc->aac_state & AAC_STATE_RESET) { 1372 fwprintf(sc, HBA_FLAGS_DBG_ERROR_B, "AAC_STATE_RESET"); 1373 break; 1374 } 1375 /* 1376 * This flag might be set if the card is out of resources. 1377 * Checking it here prevents an infinite loop of deferrals. 1378 */ 1379 if (sc->flags & AAC_QUEUE_FRZN) { 1380 fwprintf(sc, HBA_FLAGS_DBG_ERROR_B, "AAC_QUEUE_FRZN"); 1381 break; 1382 } 1383 1384 /* 1385 * Try to get a command that's been put off for lack of 1386 * resources 1387 */ 1388 if ((sc->flags & AAC_FLAGS_SYNC_MODE) && sc->aac_sync_cm) 1389 break; 1390 cm = aac_dequeue_ready(sc); 1391 1392 /* nothing to do? */ 1393 if (cm == NULL) 1394 break; 1395 1396 /* don't map more than once */ 1397 if (cm->cm_flags & AAC_CMD_MAPPED) 1398 panic("aac: command %p already mapped", cm); 1399 1400 /* 1401 * Set up the command to go to the controller. If there are no 1402 * data buffers associated with the command then it can bypass 1403 * busdma. 1404 */ 1405 if (cm->cm_datalen) 1406 aac_load_map_command_sg(sc, cm); 1407 else 1408 aacraid_map_command_sg(cm, NULL, 0, 0); 1409 } 1410 } 1411