|
@@ -481,7 +481,29 @@ static void sci_stp_optimized_request_construct(struct isci_request *ireq,
|
|
|
}
|
|
|
}
|
|
|
|
|
|
+static void sci_atapi_construct(struct isci_request *ireq)
|
|
|
+{
|
|
|
+ struct host_to_dev_fis *h2d_fis = &ireq->stp.cmd;
|
|
|
+ struct sas_task *task;
|
|
|
+
|
|
|
+ /* To simplify the implementation we take advantage of the
|
|
|
+ * silicon's partial acceleration of atapi protocol (dma data
|
|
|
+ * transfers), so we promote all commands to dma protocol. This
|
|
|
+ * breaks compatibility with ATA_HORKAGE_ATAPI_MOD16_DMA drives.
|
|
|
+ */
|
|
|
+ h2d_fis->features |= ATAPI_PKT_DMA;
|
|
|
+
|
|
|
+ scu_stp_raw_request_construct_task_context(ireq);
|
|
|
+
|
|
|
+ task = isci_request_access_task(ireq);
|
|
|
+ if (task->data_dir == DMA_NONE)
|
|
|
+ task->total_xfer_len = 0;
|
|
|
|
|
|
+ /* clear the response so we can detect arrivial of an
|
|
|
+ * unsolicited h2d fis
|
|
|
+ */
|
|
|
+ ireq->stp.rsp.fis_type = 0;
|
|
|
+}
|
|
|
|
|
|
static enum sci_status
|
|
|
sci_io_request_construct_sata(struct isci_request *ireq,
|
|
@@ -491,6 +513,7 @@ sci_io_request_construct_sata(struct isci_request *ireq,
|
|
|
{
|
|
|
enum sci_status status = SCI_SUCCESS;
|
|
|
struct sas_task *task = isci_request_access_task(ireq);
|
|
|
+ struct domain_device *dev = ireq->target_device->domain_dev;
|
|
|
|
|
|
/* check for management protocols */
|
|
|
if (ireq->ttype == tmf_task) {
|
|
@@ -519,6 +542,13 @@ sci_io_request_construct_sata(struct isci_request *ireq,
|
|
|
|
|
|
}
|
|
|
|
|
|
+ /* ATAPI */
|
|
|
+ if (dev->sata_dev.command_set == ATAPI_COMMAND_SET &&
|
|
|
+ task->ata_task.fis.command == ATA_CMD_PACKET) {
|
|
|
+ sci_atapi_construct(ireq);
|
|
|
+ return SCI_SUCCESS;
|
|
|
+ }
|
|
|
+
|
|
|
/* non data */
|
|
|
if (task->data_dir == DMA_NONE) {
|
|
|
scu_stp_raw_request_construct_task_context(ireq);
|
|
@@ -627,7 +657,7 @@ enum sci_status sci_task_request_construct_sata(struct isci_request *ireq)
|
|
|
|
|
|
/**
|
|
|
* sci_req_tx_bytes - bytes transferred when reply underruns request
|
|
|
- * @sci_req: request that was terminated early
|
|
|
+ * @ireq: request that was terminated early
|
|
|
*/
|
|
|
#define SCU_TASK_CONTEXT_SRAM 0x200000
|
|
|
static u32 sci_req_tx_bytes(struct isci_request *ireq)
|
|
@@ -729,6 +759,10 @@ sci_io_request_terminate(struct isci_request *ireq)
|
|
|
case SCI_REQ_STP_SOFT_RESET_WAIT_H2D_ASSERTED:
|
|
|
case SCI_REQ_STP_SOFT_RESET_WAIT_H2D_DIAG:
|
|
|
case SCI_REQ_STP_SOFT_RESET_WAIT_D2H:
|
|
|
+ case SCI_REQ_ATAPI_WAIT_H2D:
|
|
|
+ case SCI_REQ_ATAPI_WAIT_PIO_SETUP:
|
|
|
+ case SCI_REQ_ATAPI_WAIT_D2H:
|
|
|
+ case SCI_REQ_ATAPI_WAIT_TC_COMP:
|
|
|
sci_change_state(&ireq->sm, SCI_REQ_ABORTING);
|
|
|
return SCI_SUCCESS;
|
|
|
case SCI_REQ_TASK_WAIT_TC_RESP:
|
|
@@ -1194,8 +1228,8 @@ static enum sci_status sci_stp_request_pio_data_out_transmit_data(struct isci_re
|
|
|
{
|
|
|
struct isci_stp_request *stp_req = &ireq->stp.req;
|
|
|
struct scu_sgl_element_pair *sgl_pair;
|
|
|
+ enum sci_status status = SCI_SUCCESS;
|
|
|
struct scu_sgl_element *sgl;
|
|
|
- enum sci_status status;
|
|
|
u32 offset;
|
|
|
u32 len = 0;
|
|
|
|
|
@@ -1249,7 +1283,7 @@ static enum sci_status sci_stp_request_pio_data_out_transmit_data(struct isci_re
|
|
|
*/
|
|
|
static enum sci_status
|
|
|
sci_stp_request_pio_data_in_copy_data_buffer(struct isci_stp_request *stp_req,
|
|
|
- u8 *data_buf, u32 len)
|
|
|
+ u8 *data_buf, u32 len)
|
|
|
{
|
|
|
struct isci_request *ireq;
|
|
|
u8 *src_addr;
|
|
@@ -1423,6 +1457,128 @@ static enum sci_status sci_stp_request_udma_general_frame_handler(struct isci_re
|
|
|
return status;
|
|
|
}
|
|
|
|
|
|
+static enum sci_status process_unsolicited_fis(struct isci_request *ireq,
|
|
|
+ u32 frame_index)
|
|
|
+{
|
|
|
+ struct isci_host *ihost = ireq->owning_controller;
|
|
|
+ enum sci_status status;
|
|
|
+ struct dev_to_host_fis *frame_header;
|
|
|
+ u32 *frame_buffer;
|
|
|
+
|
|
|
+ status = sci_unsolicited_frame_control_get_header(&ihost->uf_control,
|
|
|
+ frame_index,
|
|
|
+ (void **)&frame_header);
|
|
|
+
|
|
|
+ if (status != SCI_SUCCESS)
|
|
|
+ return status;
|
|
|
+
|
|
|
+ if (frame_header->fis_type != FIS_REGD2H) {
|
|
|
+ dev_err(&ireq->isci_host->pdev->dev,
|
|
|
+ "%s ERROR: invalid fis type 0x%X\n",
|
|
|
+ __func__, frame_header->fis_type);
|
|
|
+ return SCI_FAILURE;
|
|
|
+ }
|
|
|
+
|
|
|
+ sci_unsolicited_frame_control_get_buffer(&ihost->uf_control,
|
|
|
+ frame_index,
|
|
|
+ (void **)&frame_buffer);
|
|
|
+
|
|
|
+ sci_controller_copy_sata_response(&ireq->stp.rsp,
|
|
|
+ (u32 *)frame_header,
|
|
|
+ frame_buffer);
|
|
|
+
|
|
|
+ /* Frame has been decoded return it to the controller */
|
|
|
+ sci_controller_release_frame(ihost, frame_index);
|
|
|
+
|
|
|
+ return status;
|
|
|
+}
|
|
|
+
|
|
|
+static enum sci_status atapi_d2h_reg_frame_handler(struct isci_request *ireq,
|
|
|
+ u32 frame_index)
|
|
|
+{
|
|
|
+ struct sas_task *task = isci_request_access_task(ireq);
|
|
|
+ enum sci_status status;
|
|
|
+
|
|
|
+ status = process_unsolicited_fis(ireq, frame_index);
|
|
|
+
|
|
|
+ if (status == SCI_SUCCESS) {
|
|
|
+ if (ireq->stp.rsp.status & ATA_ERR)
|
|
|
+ status = SCI_IO_FAILURE_RESPONSE_VALID;
|
|
|
+ } else {
|
|
|
+ status = SCI_IO_FAILURE_RESPONSE_VALID;
|
|
|
+ }
|
|
|
+
|
|
|
+ if (status != SCI_SUCCESS) {
|
|
|
+ ireq->scu_status = SCU_TASK_DONE_CHECK_RESPONSE;
|
|
|
+ ireq->sci_status = status;
|
|
|
+ } else {
|
|
|
+ ireq->scu_status = SCU_TASK_DONE_GOOD;
|
|
|
+ ireq->sci_status = SCI_SUCCESS;
|
|
|
+ }
|
|
|
+
|
|
|
+ /* the d2h ufi is the end of non-data commands */
|
|
|
+ if (task->data_dir == DMA_NONE)
|
|
|
+ sci_change_state(&ireq->sm, SCI_REQ_COMPLETED);
|
|
|
+
|
|
|
+ return status;
|
|
|
+}
|
|
|
+
|
|
|
+static void scu_atapi_reconstruct_raw_frame_task_context(struct isci_request *ireq)
|
|
|
+{
|
|
|
+ struct ata_device *dev = sas_to_ata_dev(ireq->target_device->domain_dev);
|
|
|
+ void *atapi_cdb = ireq->ttype_ptr.io_task_ptr->ata_task.atapi_packet;
|
|
|
+ struct scu_task_context *task_context = ireq->tc;
|
|
|
+
|
|
|
+ /* fill in the SCU Task Context for a DATA fis containing CDB in Raw Frame
|
|
|
+ * type. The TC for previous Packet fis was already there, we only need to
|
|
|
+ * change the H2D fis content.
|
|
|
+ */
|
|
|
+ memset(&ireq->stp.cmd, 0, sizeof(struct host_to_dev_fis));
|
|
|
+ memcpy(((u8 *)&ireq->stp.cmd + sizeof(u32)), atapi_cdb, ATAPI_CDB_LEN);
|
|
|
+ memset(&(task_context->type.stp), 0, sizeof(struct stp_task_context));
|
|
|
+ task_context->type.stp.fis_type = FIS_DATA;
|
|
|
+ task_context->transfer_length_bytes = dev->cdb_len;
|
|
|
+}
|
|
|
+
|
|
|
+static void scu_atapi_construct_task_context(struct isci_request *ireq)
|
|
|
+{
|
|
|
+ struct ata_device *dev = sas_to_ata_dev(ireq->target_device->domain_dev);
|
|
|
+ struct sas_task *task = isci_request_access_task(ireq);
|
|
|
+ struct scu_task_context *task_context = ireq->tc;
|
|
|
+ int cdb_len = dev->cdb_len;
|
|
|
+
|
|
|
+ /* reference: SSTL 1.13.4.2
|
|
|
+ * task_type, sata_direction
|
|
|
+ */
|
|
|
+ if (task->data_dir == DMA_TO_DEVICE) {
|
|
|
+ task_context->task_type = SCU_TASK_TYPE_PACKET_DMA_OUT;
|
|
|
+ task_context->sata_direction = 0;
|
|
|
+ } else {
|
|
|
+ /* todo: for NO_DATA command, we need to send out raw frame. */
|
|
|
+ task_context->task_type = SCU_TASK_TYPE_PACKET_DMA_IN;
|
|
|
+ task_context->sata_direction = 1;
|
|
|
+ }
|
|
|
+
|
|
|
+ memset(&task_context->type.stp, 0, sizeof(task_context->type.stp));
|
|
|
+ task_context->type.stp.fis_type = FIS_DATA;
|
|
|
+
|
|
|
+ memset(&ireq->stp.cmd, 0, sizeof(ireq->stp.cmd));
|
|
|
+ memcpy(&ireq->stp.cmd.lbal, task->ata_task.atapi_packet, cdb_len);
|
|
|
+ task_context->ssp_command_iu_length = cdb_len / sizeof(u32);
|
|
|
+
|
|
|
+ /* task phase is set to TX_CMD */
|
|
|
+ task_context->task_phase = 0x1;
|
|
|
+
|
|
|
+ /* retry counter */
|
|
|
+ task_context->stp_retry_count = 0;
|
|
|
+
|
|
|
+ /* data transfer size. */
|
|
|
+ task_context->transfer_length_bytes = task->total_xfer_len;
|
|
|
+
|
|
|
+ /* setup sgl */
|
|
|
+ sci_request_build_sgl(ireq);
|
|
|
+}
|
|
|
+
|
|
|
enum sci_status
|
|
|
sci_io_request_frame_handler(struct isci_request *ireq,
|
|
|
u32 frame_index)
|
|
@@ -1835,6 +1991,24 @@ sci_io_request_frame_handler(struct isci_request *ireq,
|
|
|
|
|
|
return status;
|
|
|
}
|
|
|
+ case SCI_REQ_ATAPI_WAIT_PIO_SETUP: {
|
|
|
+ struct sas_task *task = isci_request_access_task(ireq);
|
|
|
+
|
|
|
+ sci_controller_release_frame(ihost, frame_index);
|
|
|
+ ireq->target_device->working_request = ireq;
|
|
|
+ if (task->data_dir == DMA_NONE) {
|
|
|
+ sci_change_state(&ireq->sm, SCI_REQ_ATAPI_WAIT_TC_COMP);
|
|
|
+ scu_atapi_reconstruct_raw_frame_task_context(ireq);
|
|
|
+ } else {
|
|
|
+ sci_change_state(&ireq->sm, SCI_REQ_ATAPI_WAIT_D2H);
|
|
|
+ scu_atapi_construct_task_context(ireq);
|
|
|
+ }
|
|
|
+
|
|
|
+ sci_controller_continue_io(ireq);
|
|
|
+ return SCI_SUCCESS;
|
|
|
+ }
|
|
|
+ case SCI_REQ_ATAPI_WAIT_D2H:
|
|
|
+ return atapi_d2h_reg_frame_handler(ireq, frame_index);
|
|
|
case SCI_REQ_ABORTING:
|
|
|
/*
|
|
|
* TODO: Is it even possible to get an unsolicited frame in the
|
|
@@ -1966,6 +2140,112 @@ stp_request_soft_reset_await_h2d_diagnostic_tc_event(struct isci_request *ireq,
|
|
|
return SCI_SUCCESS;
|
|
|
}
|
|
|
|
|
|
+static enum sci_status atapi_raw_completion(struct isci_request *ireq, u32 completion_code,
|
|
|
+ enum sci_base_request_states next)
|
|
|
+{
|
|
|
+ enum sci_status status = SCI_SUCCESS;
|
|
|
+
|
|
|
+ switch (SCU_GET_COMPLETION_TL_STATUS(completion_code)) {
|
|
|
+ case SCU_MAKE_COMPLETION_STATUS(SCU_TASK_DONE_GOOD):
|
|
|
+ ireq->scu_status = SCU_TASK_DONE_GOOD;
|
|
|
+ ireq->sci_status = SCI_SUCCESS;
|
|
|
+ sci_change_state(&ireq->sm, next);
|
|
|
+ break;
|
|
|
+ default:
|
|
|
+ /* All other completion status cause the IO to be complete.
|
|
|
+ * If a NAK was received, then it is up to the user to retry
|
|
|
+ * the request.
|
|
|
+ */
|
|
|
+ ireq->scu_status = SCU_NORMALIZE_COMPLETION_STATUS(completion_code);
|
|
|
+ ireq->sci_status = SCI_FAILURE_CONTROLLER_SPECIFIC_IO_ERR;
|
|
|
+
|
|
|
+ sci_change_state(&ireq->sm, SCI_REQ_COMPLETED);
|
|
|
+ break;
|
|
|
+ }
|
|
|
+
|
|
|
+ return status;
|
|
|
+}
|
|
|
+
|
|
|
+static enum sci_status atapi_data_tc_completion_handler(struct isci_request *ireq,
|
|
|
+ u32 completion_code)
|
|
|
+{
|
|
|
+ struct isci_remote_device *idev = ireq->target_device;
|
|
|
+ struct dev_to_host_fis *d2h = &ireq->stp.rsp;
|
|
|
+ enum sci_status status = SCI_SUCCESS;
|
|
|
+
|
|
|
+ switch (SCU_GET_COMPLETION_TL_STATUS(completion_code)) {
|
|
|
+ case (SCU_TASK_DONE_GOOD << SCU_COMPLETION_TL_STATUS_SHIFT):
|
|
|
+ sci_change_state(&ireq->sm, SCI_REQ_COMPLETED);
|
|
|
+ break;
|
|
|
+
|
|
|
+ case (SCU_TASK_DONE_UNEXP_FIS << SCU_COMPLETION_TL_STATUS_SHIFT): {
|
|
|
+ u16 len = sci_req_tx_bytes(ireq);
|
|
|
+
|
|
|
+ /* likely non-error data underrrun, workaround missing
|
|
|
+ * d2h frame from the controller
|
|
|
+ */
|
|
|
+ if (d2h->fis_type != FIS_REGD2H) {
|
|
|
+ d2h->fis_type = FIS_REGD2H;
|
|
|
+ d2h->flags = (1 << 6);
|
|
|
+ d2h->status = 0x50;
|
|
|
+ d2h->error = 0;
|
|
|
+ d2h->lbal = 0;
|
|
|
+ d2h->byte_count_low = len & 0xff;
|
|
|
+ d2h->byte_count_high = len >> 8;
|
|
|
+ d2h->device = 0xa0;
|
|
|
+ d2h->lbal_exp = 0;
|
|
|
+ d2h->lbam_exp = 0;
|
|
|
+ d2h->lbah_exp = 0;
|
|
|
+ d2h->_r_a = 0;
|
|
|
+ d2h->sector_count = 0x3;
|
|
|
+ d2h->sector_count_exp = 0;
|
|
|
+ d2h->_r_b = 0;
|
|
|
+ d2h->_r_c = 0;
|
|
|
+ d2h->_r_d = 0;
|
|
|
+ }
|
|
|
+
|
|
|
+ ireq->scu_status = SCU_TASK_DONE_GOOD;
|
|
|
+ ireq->sci_status = SCI_SUCCESS_IO_DONE_EARLY;
|
|
|
+ status = ireq->sci_status;
|
|
|
+
|
|
|
+ /* the hw will have suspended the rnc, so complete the
|
|
|
+ * request upon pending resume
|
|
|
+ */
|
|
|
+ sci_change_state(&idev->sm, SCI_STP_DEV_ATAPI_ERROR);
|
|
|
+ break;
|
|
|
+ }
|
|
|
+ case (SCU_TASK_DONE_EXCESS_DATA << SCU_COMPLETION_TL_STATUS_SHIFT):
|
|
|
+ /* In this case, there is no UF coming after.
|
|
|
+ * compelte the IO now.
|
|
|
+ */
|
|
|
+ ireq->scu_status = SCU_TASK_DONE_GOOD;
|
|
|
+ ireq->sci_status = SCI_SUCCESS;
|
|
|
+ sci_change_state(&ireq->sm, SCI_REQ_COMPLETED);
|
|
|
+ break;
|
|
|
+
|
|
|
+ default:
|
|
|
+ if (d2h->fis_type == FIS_REGD2H) {
|
|
|
+ /* UF received change the device state to ATAPI_ERROR */
|
|
|
+ status = ireq->sci_status;
|
|
|
+ sci_change_state(&idev->sm, SCI_STP_DEV_ATAPI_ERROR);
|
|
|
+ } else {
|
|
|
+ /* If receiving any non-sucess TC status, no UF
|
|
|
+ * received yet, then an UF for the status fis
|
|
|
+ * is coming after (XXX: suspect this is
|
|
|
+ * actually a protocol error or a bug like the
|
|
|
+ * DONE_UNEXP_FIS case)
|
|
|
+ */
|
|
|
+ ireq->scu_status = SCU_TASK_DONE_CHECK_RESPONSE;
|
|
|
+ ireq->sci_status = SCI_FAILURE_IO_RESPONSE_VALID;
|
|
|
+
|
|
|
+ sci_change_state(&ireq->sm, SCI_REQ_ATAPI_WAIT_D2H);
|
|
|
+ }
|
|
|
+ break;
|
|
|
+ }
|
|
|
+
|
|
|
+ return status;
|
|
|
+}
|
|
|
+
|
|
|
enum sci_status
|
|
|
sci_io_request_tc_completion(struct isci_request *ireq,
|
|
|
u32 completion_code)
|
|
@@ -2017,6 +2297,17 @@ sci_io_request_tc_completion(struct isci_request *ireq,
|
|
|
return request_aborting_state_tc_event(ireq,
|
|
|
completion_code);
|
|
|
|
|
|
+ case SCI_REQ_ATAPI_WAIT_H2D:
|
|
|
+ return atapi_raw_completion(ireq, completion_code,
|
|
|
+ SCI_REQ_ATAPI_WAIT_PIO_SETUP);
|
|
|
+
|
|
|
+ case SCI_REQ_ATAPI_WAIT_TC_COMP:
|
|
|
+ return atapi_raw_completion(ireq, completion_code,
|
|
|
+ SCI_REQ_ATAPI_WAIT_D2H);
|
|
|
+
|
|
|
+ case SCI_REQ_ATAPI_WAIT_D2H:
|
|
|
+ return atapi_data_tc_completion_handler(ireq, completion_code);
|
|
|
+
|
|
|
default:
|
|
|
dev_warn(&ihost->pdev->dev,
|
|
|
"%s: SCIC IO Request given task completion "
|
|
@@ -2423,6 +2714,8 @@ static void isci_process_stp_response(struct sas_task *task, struct dev_to_host_
|
|
|
*/
|
|
|
if (fis->status & ATA_DF)
|
|
|
ts->stat = SAS_PROTO_RESPONSE;
|
|
|
+ else if (fis->status & ATA_ERR)
|
|
|
+ ts->stat = SAM_STAT_CHECK_CONDITION;
|
|
|
else
|
|
|
ts->stat = SAM_STAT_GOOD;
|
|
|
|
|
@@ -2782,6 +3075,7 @@ static void sci_request_started_state_enter(struct sci_base_state_machine *sm)
|
|
|
{
|
|
|
struct isci_request *ireq = container_of(sm, typeof(*ireq), sm);
|
|
|
struct domain_device *dev = ireq->target_device->domain_dev;
|
|
|
+ enum sci_base_request_states state;
|
|
|
struct sas_task *task;
|
|
|
|
|
|
/* XXX as hch said always creating an internal sas_task for tmf
|
|
@@ -2793,26 +3087,30 @@ static void sci_request_started_state_enter(struct sci_base_state_machine *sm)
|
|
|
* substates
|
|
|
*/
|
|
|
if (!task && dev->dev_type == SAS_END_DEV) {
|
|
|
- sci_change_state(sm, SCI_REQ_TASK_WAIT_TC_COMP);
|
|
|
+ state = SCI_REQ_TASK_WAIT_TC_COMP;
|
|
|
} else if (!task &&
|
|
|
(isci_request_access_tmf(ireq)->tmf_code == isci_tmf_sata_srst_high ||
|
|
|
isci_request_access_tmf(ireq)->tmf_code == isci_tmf_sata_srst_low)) {
|
|
|
- sci_change_state(sm, SCI_REQ_STP_SOFT_RESET_WAIT_H2D_ASSERTED);
|
|
|
+ state = SCI_REQ_STP_SOFT_RESET_WAIT_H2D_ASSERTED;
|
|
|
} else if (task && task->task_proto == SAS_PROTOCOL_SMP) {
|
|
|
- sci_change_state(sm, SCI_REQ_SMP_WAIT_RESP);
|
|
|
+ state = SCI_REQ_SMP_WAIT_RESP;
|
|
|
} else if (task && sas_protocol_ata(task->task_proto) &&
|
|
|
!task->ata_task.use_ncq) {
|
|
|
- u32 state;
|
|
|
-
|
|
|
- if (task->data_dir == DMA_NONE)
|
|
|
+ if (dev->sata_dev.command_set == ATAPI_COMMAND_SET &&
|
|
|
+ task->ata_task.fis.command == ATA_CMD_PACKET) {
|
|
|
+ state = SCI_REQ_ATAPI_WAIT_H2D;
|
|
|
+ } else if (task->data_dir == DMA_NONE) {
|
|
|
state = SCI_REQ_STP_NON_DATA_WAIT_H2D;
|
|
|
- else if (task->ata_task.dma_xfer)
|
|
|
+ } else if (task->ata_task.dma_xfer) {
|
|
|
state = SCI_REQ_STP_UDMA_WAIT_TC_COMP;
|
|
|
- else /* PIO */
|
|
|
+ } else /* PIO */ {
|
|
|
state = SCI_REQ_STP_PIO_WAIT_H2D;
|
|
|
-
|
|
|
- sci_change_state(sm, state);
|
|
|
+ }
|
|
|
+ } else {
|
|
|
+ /* SSP or NCQ are fully accelerated, no substates */
|
|
|
+ return;
|
|
|
}
|
|
|
+ sci_change_state(sm, state);
|
|
|
}
|
|
|
|
|
|
static void sci_request_completed_state_enter(struct sci_base_state_machine *sm)
|
|
@@ -2904,6 +3202,10 @@ static const struct sci_base_state sci_request_state_table[] = {
|
|
|
[SCI_REQ_TASK_WAIT_TC_RESP] = { },
|
|
|
[SCI_REQ_SMP_WAIT_RESP] = { },
|
|
|
[SCI_REQ_SMP_WAIT_TC_COMP] = { },
|
|
|
+ [SCI_REQ_ATAPI_WAIT_H2D] = { },
|
|
|
+ [SCI_REQ_ATAPI_WAIT_PIO_SETUP] = { },
|
|
|
+ [SCI_REQ_ATAPI_WAIT_D2H] = { },
|
|
|
+ [SCI_REQ_ATAPI_WAIT_TC_COMP] = { },
|
|
|
[SCI_REQ_COMPLETED] = {
|
|
|
.enter_state = sci_request_completed_state_enter,
|
|
|
},
|