Lines Matching +full:command +full:- +full:sequencer

1 /*-
4 * Copyright (c) 1994-2001 Justin T. Gibbs.
75 path_id = cam_sim_path(ahc->platform_data->sim_b);
77 path_id = cam_sim_path(ahc->platform_data->sim);
91 shareable = (ahc->flags & AHC_EDGE_INTERRUPT) ? 0: RF_SHAREABLE;
92 ahc->platform_data->irq =
93 bus_alloc_resource_any(ahc->dev_softc, SYS_RES_IRQ, &zero,
95 if (ahc->platform_data->irq == NULL) {
96 device_printf(ahc->dev_softc,
100 ahc->platform_data->irq_res_type = SYS_RES_IRQ;
103 error = bus_setup_intr(ahc->dev_softc, ahc->platform_data->irq,
105 ahc_platform_intr, ahc, &ahc->platform_data->ih);
108 device_printf(ahc->dev_softc, "bus_setup_intr() failed: %d\n",
120 regs = bus_alloc_resource_any(ahc->dev_softc, SYS_RES_IOPORT, &rid,
123 device_printf(ahc->dev_softc, "Unable to map I/O space?!\n");
126 ahc->platform_data->regs_res_type = SYS_RES_IOPORT;
127 ahc->platform_data->regs_res_id = rid;
128 ahc->platform_data->regs = regs;
129 ahc->tag = rman_get_bustag(regs);
130 ahc->bsh = rman_get_bushandle(regs);
135 * Attach all the sub-devices we can find
171 if ((ahc->features & AHC_TWIN) != 0
172 && (ahc->flags & AHC_PRIMARY_CHANNEL) != 0) {
191 device_get_unit(ahc->dev_softc),
192 &ahc->platform_data->mtx, 1, AHC_MAX_QUEUE, devq);
198 if (xpt_bus_register(sim, ahc->dev_softc, bus_id) != CAM_SUCCESS) {
222 if (ahc->features & AHC_TWIN) {
224 ahc, device_get_unit(ahc->dev_softc),
225 &ahc->platform_data->mtx, 1,
234 if (xpt_bus_register(sim2, ahc->dev_softc, bus_id2) !=
265 if ((ahc->features & AHC_TWIN) != 0
266 && (ahc->flags & AHC_PRIMARY_CHANNEL) != 0) {
267 ahc->platform_data->sim_b = sim;
268 ahc->platform_data->path_b = path;
269 ahc->platform_data->sim = sim2;
270 ahc->platform_data->path = path2;
272 ahc->platform_data->sim = sim;
273 ahc->platform_data->path = path;
274 ahc->platform_data->sim_b = sim2;
275 ahc->platform_data->path_b = path2;
281 ahc->platform_data->eh =
310 if (ccb->ccb_h.func_code == XPT_CONT_TARGET_IO)
315 if ((ccb->ccb_h.flags & CAM_DIR_MASK) == rdmask)
320 bus_dmamap_sync(ahc->buffer_dmat, scb->dmamap, op);
333 CAM_DEBUG(scb->io_ctx->ccb_h.path, CAM_DEBUG_TRACE,
334 ("ahc_done - scb %d\n", scb->hscb->tag));
336 ccb = scb->io_ctx;
338 if ((scb->flags & SCB_TIMEDOUT) != 0)
340 if ((scb->flags & SCB_UNTAGGEDQ) != 0) {
345 untagged_q = &ahc->untagged_queues[target_offset];
347 scb->flags &= ~SCB_UNTAGGEDQ;
351 callout_stop(&scb->io_timer);
353 if ((ccb->ccb_h.flags & CAM_DIR_MASK) != CAM_DIR_NONE) {
355 bus_dmamap_unload(ahc->buffer_dmat, scb->dmamap);
358 if (ccb->ccb_h.func_code == XPT_CONT_TARGET_IO) {
364 * XXX - There may be error states that cause where
367 ccb_path = ccb->ccb_h.path;
368 if (ahc->pending_device != NULL
369 && xpt_path_comp(ahc->pending_device->path, ccb_path) == 0) {
370 if ((ccb->ccb_h.flags & CAM_SEND_STATUS) != 0) {
371 ahc->pending_device = NULL;
374 xpt_print_path(ccb->ccb_h.path);
382 ccb->ccb_h.status |= CAM_REQ_CMP;
383 ccb->ccb_h.status &= ~CAM_SIM_QUEUED;
393 if ((scb->flags & SCB_RECOVERY_SCB) != 0) {
396 ahc->scb_data->recovery_scbs--;
402 if (ahc->scb_data->recovery_scbs == 0) {
408 LIST_FOREACH(list_scb, &ahc->pending_scbs,
416 ccb->ccb_h.status);
422 ccb->ccb_h.status |= CAM_REQ_CMP;
423 } else if ((scb->flags & SCB_SENSE) != 0) {
431 * through buffers accessible via bus-space by
434 memset(&ccb->csio.sense_data, 0, sizeof(ccb->csio.sense_data));
435 memcpy(&ccb->csio.sense_data,
437 (aic_le32toh(scb->sg_list->len) & AHC_SG_LEN_MASK)
438 - ccb->csio.sense_resid);
439 scb->io_ctx->ccb_h.status |= CAM_AUTOSNS_VALID;
441 ccb->ccb_h.status &= ~CAM_SIM_QUEUED;
454 CAM_DEBUG(ccb->ccb_h.path, CAM_DEBUG_TRACE, ("ahc_action\n"));
458 target_id = ccb->ccb_h.target_id;
461 switch (ccb->ccb_h.func_code) {
473 if (ccb->ccb_h.func_code == XPT_CONT_TARGET_IO) {
476 lstate = ahc->black_hole;
478 ccb->ccb_h.status = status;
483 if (ccb->ccb_h.func_code == XPT_ACCEPT_TARGET_IO) {
484 SLIST_INSERT_HEAD(&lstate->accept_tios, &ccb->ccb_h,
486 ccb->ccb_h.status = CAM_REQ_INPROG;
487 if ((ahc->flags & AHC_TQINFIFO_BLOCKED) != 0)
495 * the original command.
498 target_id = ccb->csio.init_id;
507 if ((ahc->flags & AHC_INITIATORROLE) == 0
508 && (ccb->ccb_h.func_code == XPT_SCSI_IO
509 || ccb->ccb_h.func_code == XPT_RESET_DEV)) {
510 ccb->ccb_h.status = CAM_PROVIDE_FAIL;
520 ahc->flags |= AHC_RESOURCE_SHORTAGE;
521 ccb->ccb_h.status = CAM_REQUEUE_REQ;
526 hscb = scb->hscb;
528 CAM_DEBUG(ccb->ccb_h.path, CAM_DEBUG_SUBTRACE,
530 scb->io_ctx = ccb;
534 ccb->ccb_h.ccb_scb_ptr = scb;
539 hscb->control = 0;
540 hscb->scsiid = BUILD_SCSIID(ahc, sim, target_id, our_id);
541 hscb->lun = ccb->ccb_h.target_lun;
542 if (ccb->ccb_h.func_code == XPT_RESET_DEV) {
543 hscb->cdb_len = 0;
544 scb->flags |= SCB_DEVICE_RESET;
545 hscb->control |= MK_MESSAGE;
548 if (ccb->ccb_h.func_code == XPT_CONT_TARGET_IO) {
551 tdata = &hscb->shared_data.tdata;
552 if (ahc->pending_device == lstate)
553 scb->flags |= SCB_TARGET_IMMEDIATE;
554 hscb->control |= TARGET_SCB;
555 scb->flags |= SCB_TARGET_SCB;
556 tdata->target_phases = 0;
557 if ((ccb->ccb_h.flags & CAM_SEND_STATUS) != 0) {
558 tdata->target_phases |= SPHASE_PENDING;
559 tdata->scsi_status =
560 ccb->csio.scsi_status;
562 if (ccb->ccb_h.flags & CAM_DIS_DISCONNECT)
563 tdata->target_phases |= NO_DISCONNECT;
565 tdata->initiator_tag = ccb->csio.tag_id;
567 if (ccb->ccb_h.flags & CAM_TAG_ACTION_VALID)
568 hscb->control |= ccb->csio.tag_action;
570 ahc_setup_data(ahc, sim, &ccb->csio, scb);
585 ccb->ccb_h.status = status;
589 SLIST_INSERT_HEAD(&lstate->immed_notifies, &ccb->ccb_h,
591 ccb->ccb_h.status = CAM_REQ_INPROG;
616 cts = &ccb->cts;
617 scsi = &cts->proto_specific.scsi;
618 spi = &cts->xport_specific.spi;
620 cts->ccb_h.target_id,
621 cts->ccb_h.target_lun,
628 if (cts->type == CTS_TYPE_CURRENT_SETTINGS) {
630 discenable = &tstate->discenable;
631 tagenable = &tstate->tagenable;
632 tinfo->curr.protocol_version =
633 cts->protocol_version;
634 tinfo->curr.transport_version =
635 cts->transport_version;
636 tinfo->goal.protocol_version =
637 cts->protocol_version;
638 tinfo->goal.transport_version =
639 cts->transport_version;
640 } else if (cts->type == CTS_TYPE_USER_SETTINGS) {
642 discenable = &ahc->user_discenable;
643 tagenable = &ahc->user_tagenable;
644 tinfo->user.protocol_version =
645 cts->protocol_version;
646 tinfo->user.transport_version =
647 cts->transport_version;
649 ccb->ccb_h.status = CAM_REQ_INVALID;
654 if ((spi->valid & CTS_SPI_VALID_DISC) != 0) {
655 if ((spi->flags & CTS_SPI_FLAGS_DISC_ENB) != 0)
661 if ((scsi->valid & CTS_SCSI_VALID_TQ) != 0) {
662 if ((scsi->flags & CTS_SCSI_FLAGS_TAG_ENB) != 0)
668 if ((spi->valid & CTS_SPI_VALID_BUS_WIDTH) != 0) {
670 &spi->bus_width, ROLE_UNKNOWN);
671 ahc_set_width(ahc, &devinfo, spi->bus_width,
675 if ((spi->valid & CTS_SPI_VALID_PPR_OPTIONS) == 0) {
677 spi->ppr_options = tinfo->user.ppr_options;
679 spi->ppr_options = tinfo->goal.ppr_options;
682 if ((spi->valid & CTS_SPI_VALID_SYNC_OFFSET) == 0) {
684 spi->sync_offset = tinfo->user.offset;
686 spi->sync_offset = tinfo->goal.offset;
689 if ((spi->valid & CTS_SPI_VALID_SYNC_RATE) == 0) {
691 spi->sync_period = tinfo->user.period;
693 spi->sync_period = tinfo->goal.period;
696 if (((spi->valid & CTS_SPI_VALID_SYNC_RATE) != 0)
697 || ((spi->valid & CTS_SPI_VALID_SYNC_OFFSET) != 0)) {
701 if ((ahc->features & AHC_ULTRA2) != 0)
703 else if ((ahc->features & AHC_ULTRA) != 0)
708 if (spi->bus_width != MSG_EXT_WDTR_BUS_16_BIT)
709 spi->ppr_options &= ~MSG_EXT_PPR_DT_REQ;
711 syncrate = ahc_find_syncrate(ahc, &spi->sync_period,
712 &spi->ppr_options,
715 syncrate, &spi->sync_offset,
716 spi->bus_width, ROLE_UNKNOWN);
719 if (spi->sync_offset == 0) {
720 spi->sync_period = 0;
721 spi->ppr_options = 0;
725 spi->sync_period, spi->sync_offset,
726 spi->ppr_options, update_type,
729 ccb->ccb_h.status = CAM_REQ_CMP;
737 SIM_CHANNEL(ahc, sim), &ccb->cts);
746 ? ahc->flags & AHC_EXTENDED_TRANS_B
747 : ahc->flags & AHC_EXTENDED_TRANS_A;
748 aic_calc_geometry(&ccb->ccg, extended);
763 ccb->ccb_h.status = CAM_REQ_CMP;
769 ccb->ccb_h.status = CAM_REQ_INVALID;
774 struct ccb_pathinq *cpi = &ccb->cpi;
776 cpi->version_num = 1; /* XXX??? */
777 cpi->hba_inquiry = PI_SDTR_ABLE|PI_TAG_ABLE;
778 if ((ahc->features & AHC_WIDE) != 0)
779 cpi->hba_inquiry |= PI_WIDE_16;
780 if ((ahc->features & AHC_TARGETMODE) != 0) {
781 cpi->target_sprt = PIT_PROCESSOR
785 cpi->target_sprt = 0;
787 cpi->hba_misc = 0;
788 cpi->hba_eng_cnt = 0;
789 cpi->max_target = (ahc->features & AHC_WIDE) ? 15 : 7;
790 cpi->max_lun = AHC_NUM_LUNS - 1;
792 cpi->initiator_id = ahc->our_id_b;
793 if ((ahc->flags & AHC_RESET_BUS_B) == 0)
794 cpi->hba_misc |= PIM_NOBUSRESET;
796 cpi->initiator_id = ahc->our_id;
797 if ((ahc->flags & AHC_RESET_BUS_A) == 0)
798 cpi->hba_misc |= PIM_NOBUSRESET;
800 cpi->bus_id = cam_sim_bus(sim);
801 cpi->base_transfer_speed = 3300;
802 strlcpy(cpi->sim_vid, "FreeBSD", SIM_IDLEN);
803 strlcpy(cpi->hba_vid, "Adaptec", HBA_IDLEN);
804 strlcpy(cpi->dev_name, cam_sim_name(sim), DEV_IDLEN);
805 cpi->unit_number = cam_sim_unit(sim);
806 cpi->protocol = PROTO_SCSI;
807 cpi->protocol_version = SCSI_REV_2;
808 cpi->transport = XPORT_SPI;
809 cpi->transport_version = 2;
810 cpi->xport_specific.spi.ppr_options = SID_SPI_CLOCK_ST;
811 if ((ahc->features & AHC_DT) != 0) {
812 cpi->transport_version = 3;
813 cpi->xport_specific.spi.ppr_options =
816 cpi->ccb_h.status = CAM_REQ_CMP;
821 ccb->ccb_h.status = CAM_PROVIDE_FAIL;
838 scsi = &cts->proto_specific.scsi;
839 spi = &cts->xport_specific.spi;
841 cts->ccb_h.target_id,
842 cts->ccb_h.target_lun,
848 if (cts->type == CTS_TYPE_CURRENT_SETTINGS)
849 tinfo = &targ_info->curr;
851 tinfo = &targ_info->user;
853 scsi->flags &= ~CTS_SCSI_FLAGS_TAG_ENB;
854 spi->flags &= ~CTS_SPI_FLAGS_DISC_ENB;
855 if (cts->type == CTS_TYPE_USER_SETTINGS) {
856 if ((ahc->user_discenable & devinfo.target_mask) != 0)
857 spi->flags |= CTS_SPI_FLAGS_DISC_ENB;
859 if ((ahc->user_tagenable & devinfo.target_mask) != 0)
860 scsi->flags |= CTS_SCSI_FLAGS_TAG_ENB;
862 if ((tstate->discenable & devinfo.target_mask) != 0)
863 spi->flags |= CTS_SPI_FLAGS_DISC_ENB;
865 if ((tstate->tagenable & devinfo.target_mask) != 0)
866 scsi->flags |= CTS_SCSI_FLAGS_TAG_ENB;
868 cts->protocol_version = tinfo->protocol_version;
869 cts->transport_version = tinfo->transport_version;
871 spi->sync_period = tinfo->period;
872 spi->sync_offset = tinfo->offset;
873 spi->bus_width = tinfo->width;
874 spi->ppr_options = tinfo->ppr_options;
876 cts->protocol = PROTO_SCSI;
877 cts->transport = XPORT_SPI;
878 spi->valid = CTS_SPI_VALID_SYNC_RATE
883 if (cts->ccb_h.target_lun != CAM_LUN_WILDCARD) {
884 scsi->valid = CTS_SCSI_VALID_TQ;
885 spi->valid |= CTS_SPI_VALID_DISC;
887 scsi->valid = 0;
890 cts->ccb_h.status = CAM_REQ_CMP;
941 ccb = scb->io_ctx;
942 ahc = scb->ahc_softc;
950 bus_dmamap_unload(ahc->buffer_dmat, scb->dmamap);
962 sg = scb->sg_list;
966 sg->addr = aic_htole32(dm_segs->ds_addr);
967 len = dm_segs->ds_len
968 | ((dm_segs->ds_addr >> 8) & 0x7F000000);
969 sg->len = aic_htole32(len);
977 * sequencer will clear as soon as a data transfer
980 scb->hscb->sgptr = aic_htole32(scb->sg_list_phys|SG_FULL_RESID);
984 if (ccb->ccb_h.func_code == XPT_CONT_TARGET_IO) {
987 tdata = &scb->hscb->shared_data.tdata;
988 tdata->target_phases |= DPHASE_PENDING;
992 if ((ccb->ccb_h.flags & CAM_DIR_MASK) == CAM_DIR_OUT)
993 tdata->data_phase = P_DATAOUT;
995 tdata->data_phase = P_DATAIN;
999 * "in" direction (scsi->HostBus), then it may
1001 * non-Ultra2 chips. Force the total data-length
1005 * this command is executed.
1007 if ((ahc->bugs & AHC_TMODE_WIDEODD_BUG) != 0
1008 && (ccb->csio.dxfer_len & 0x1) != 0
1009 && (ccb->ccb_h.flags & CAM_DIR_MASK) == CAM_DIR_OUT) {
1014 bus_dmamap_unload(ahc->buffer_dmat,
1015 scb->dmamap);
1020 sg->addr = aic_htole32(ahc->dma_bug_buf);
1021 sg->len = aic_htole32(1);
1025 sg--;
1026 sg->len |= aic_htole32(AHC_DMA_LAST_SEG);
1029 scb->hscb->dataptr = scb->sg_list->addr;
1030 scb->hscb->datacnt = scb->sg_list->len;
1032 scb->hscb->sgptr = aic_htole32(SG_LIST_NULL);
1033 scb->hscb->dataptr = 0;
1034 scb->hscb->datacnt = 0;
1037 scb->sg_count = nsegments;
1045 bus_dmamap_unload(ahc->buffer_dmat, scb->dmamap);
1051 tinfo = ahc_fetch_transinfo(ahc, SCSIID_CHANNEL(ahc, scb->hscb->scsiid),
1052 SCSIID_OUR_ID(scb->hscb->scsiid),
1053 SCSIID_TARGET(ahc, scb->hscb->scsiid),
1057 scb->hscb->scsirate = tinfo->scsirate;
1058 scb->hscb->scsioffset = tinfo->curr.offset;
1059 if ((tstate->ultraenb & mask) != 0)
1060 scb->hscb->control |= ULTRAENB;
1062 if ((tstate->discenable & mask) != 0
1063 && (ccb->ccb_h.flags & CAM_DIS_DISCONNECT) == 0)
1064 scb->hscb->control |= DISCENB;
1066 if ((ccb->ccb_h.flags & CAM_NEGOTIATE) != 0
1067 && (tinfo->goal.width != 0
1068 || tinfo->goal.offset != 0
1069 || tinfo->goal.ppr_options != 0)) {
1070 scb->flags |= SCB_NEGOTIATE;
1071 scb->hscb->control |= MK_MESSAGE;
1072 } else if ((tstate->auto_negotiate & mask) != 0) {
1073 scb->flags |= SCB_AUTO_NEGOTIATE;
1074 scb->hscb->control |= MK_MESSAGE;
1077 LIST_INSERT_HEAD(&ahc->pending_scbs, scb, pending_links);
1079 ccb->ccb_h.status |= CAM_SIM_QUEUED;
1087 if ((scb->hscb->control & (TARGET_SCB|TAG_ENB)) == 0
1088 && (ahc->flags & AHC_SCB_BTT) == 0) {
1093 untagged_q = &(ahc->untagged_queues[target_offset]);
1095 scb->flags |= SCB_UNTAGGEDQ;
1100 scb->flags |= SCB_ACTIVE;
1107 if ((scb->flags & SCB_TARGET_IMMEDIATE) != 0) {
1109 ahc->scb_data->scbindex[scb->hscb->tag] = scb;
1111 if ((ahc->flags & AHC_PAGESCBS) == 0)
1112 ahc_outb(ahc, SCBPTR, scb->hscb->tag);
1113 ahc_outb(ahc, TARG_IMMEDIATE_SCB, scb->hscb->tag);
1137 hscb = scb->hscb;
1138 ccb_h = &csio->ccb_h;
1140 csio->resid = 0;
1141 csio->sense_resid = 0;
1142 if (ccb_h->func_code == XPT_SCSI_IO) {
1143 hscb->cdb_len = csio->cdb_len;
1144 if ((ccb_h->flags & CAM_CDB_POINTER) != 0) {
1145 if (hscb->cdb_len > sizeof(hscb->cdb32)
1146 || (ccb_h->flags & CAM_CDB_PHYS) != 0) {
1153 if (hscb->cdb_len > 12) {
1154 memcpy(hscb->cdb32,
1155 csio->cdb_io.cdb_ptr,
1156 hscb->cdb_len);
1157 scb->flags |= SCB_CDB32_PTR;
1159 memcpy(hscb->shared_data.cdb,
1160 csio->cdb_io.cdb_ptr,
1161 hscb->cdb_len);
1164 if (hscb->cdb_len > 12) {
1165 memcpy(hscb->cdb32, csio->cdb_io.cdb_bytes,
1166 hscb->cdb_len);
1167 scb->flags |= SCB_CDB32_PTR;
1169 memcpy(hscb->shared_data.cdb,
1170 csio->cdb_io.cdb_bytes,
1171 hscb->cdb_len);
1176 error = bus_dmamap_load_ccb(ahc->buffer_dmat,
1177 scb->dmamap,
1190 scb->io_ctx->ccb_h.status |= CAM_RELEASE_SIMQ;
1199 abort_ccb = ccb->cab.abort_ccb;
1200 switch (abort_ccb->ccb_h.func_code) {
1214 ccb->ccb_h.status = status;
1218 if (abort_ccb->ccb_h.func_code == XPT_ACCEPT_TARGET_IO)
1219 list = &lstate->accept_tios;
1220 else if (abort_ccb->ccb_h.func_code == XPT_IMMEDIATE_NOTIFY)
1221 list = &lstate->immed_notifies;
1231 if (curelm == &abort_ccb->ccb_h) {
1241 if (nextelm == &abort_ccb->ccb_h) {
1254 abort_ccb->ccb_h.status = CAM_REQ_ABORTED;
1256 ccb->ccb_h.status = CAM_REQ_CMP;
1258 xpt_print_path(abort_ccb->ccb_h.path);
1260 ccb->ccb_h.status = CAM_PATH_INVALID;
1268 ccb->ccb_h.status = CAM_UA_ABORT;
1271 ccb->ccb_h.status = CAM_REQ_INVALID;
1302 ahc_get_tran_settings(ahc, channel == 'A' ? ahc->our_id
1303 : ahc->our_id_b,
1306 scsi->valid &= ~CTS_SCSI_VALID_TQ;
1307 scsi->flags &= ~CTS_SCSI_FLAGS_TAG_ENB;
1311 scsi->flags |= ~CTS_SCSI_FLAGS_TAG_ENB;
1312 scsi->valid |= CTS_SCSI_VALID_TQ;
1334 ahc->platform_data = malloc(sizeof(struct ahc_platform_data), M_DEVBUF,
1336 if (ahc->platform_data == NULL)
1346 pdata = ahc->platform_data;
1348 if (pdata->regs != NULL)
1349 bus_release_resource(ahc->dev_softc,
1350 pdata->regs_res_type,
1351 pdata->regs_res_id,
1352 pdata->regs);
1354 if (pdata->irq != NULL)
1355 bus_release_resource(ahc->dev_softc,
1356 pdata->irq_res_type,
1357 0, pdata->irq);
1359 if (pdata->sim_b != NULL) {
1360 xpt_async(AC_LOST_DEVICE, pdata->path_b, NULL);
1361 xpt_free_path(pdata->path_b);
1362 xpt_bus_deregister(cam_sim_path(pdata->sim_b));
1363 cam_sim_free(pdata->sim_b, /*free_devq*/TRUE);
1365 if (pdata->sim != NULL) {
1366 xpt_async(AC_LOST_DEVICE, pdata->path, NULL);
1367 xpt_free_path(pdata->path);
1368 xpt_bus_deregister(cam_sim_path(pdata->sim));
1369 cam_sim_free(pdata->sim, /*free_devq*/TRUE);
1371 if (pdata->eh != NULL)
1372 EVENTHANDLER_DEREGISTER(shutdown_final, pdata->eh);
1373 free(ahc->platform_data, M_DEVBUF);
1394 bus_teardown_intr(dev, ahc->platform_data->irq, ahc->platform_data->ih);
1408 byte = &cmd->initiator_channel;