aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJeff Skirvin <jeffrey.d.skirvin@intel.com>2012-03-09 01:42:09 -0500
committerDan Williams <dan.j.williams@intel.com>2012-05-17 17:33:43 -0400
commit87805162b6af20d2ad386a49aec13b753cca523a (patch)
treebfe5b09eaa3943636263d8695c946550b883b236
parent1f05388933cb6e57ed9e51768c194ff145002f3b (diff)
isci: Restore the ATAPI device RNC management code.
The ATAPI specific and STP general RNC suspension code had been incorrectly removed from the remote device code. Signed-off-by: Jeff Skirvin <jeffrey.d.skirvin@intel.com> Signed-off-by: Dan Williams <dan.j.williams@intel.com>
-rw-r--r--drivers/scsi/isci/remote_device.c49
-rw-r--r--drivers/scsi/isci/remote_device.h2
-rw-r--r--drivers/scsi/isci/request.c3
3 files changed, 34 insertions, 20 deletions
diff --git a/drivers/scsi/isci/remote_device.c b/drivers/scsi/isci/remote_device.c
index 68ab4fb9032e..48765aa84328 100644
--- a/drivers/scsi/isci/remote_device.c
+++ b/drivers/scsi/isci/remote_device.c
@@ -72,8 +72,8 @@ const char *dev_state_name(enum sci_remote_device_states state)
72} 72}
73#undef C 73#undef C
74 74
75static enum sci_status sci_remote_device_suspend(struct isci_remote_device *idev, 75enum sci_status sci_remote_device_suspend(struct isci_remote_device *idev,
76 enum sci_remote_node_suspension_reasons reason) 76 enum sci_remote_node_suspension_reasons reason)
77{ 77{
78 return sci_remote_node_context_suspend(&idev->rnc, reason, 78 return sci_remote_node_context_suspend(&idev->rnc, reason,
79 SCI_SOFTWARE_SUSPEND_EXPECTED_EVENT); 79 SCI_SOFTWARE_SUSPEND_EXPECTED_EVENT);
@@ -565,6 +565,8 @@ enum sci_status sci_remote_device_event_handler(struct isci_remote_device *idev,
565 u32 event_code) 565 u32 event_code)
566{ 566{
567 enum sci_status status; 567 enum sci_status status;
568 struct sci_base_state_machine *sm = &idev->sm;
569 enum sci_remote_device_states state = sm->current_state_id;
568 570
569 switch (scu_get_event_type(event_code)) { 571 switch (scu_get_event_type(event_code)) {
570 case SCU_EVENT_TYPE_RNC_OPS_MISC: 572 case SCU_EVENT_TYPE_RNC_OPS_MISC:
@@ -603,6 +605,30 @@ enum sci_status sci_remote_device_event_handler(struct isci_remote_device *idev,
603 if (status != SCI_SUCCESS) 605 if (status != SCI_SUCCESS)
604 return status; 606 return status;
605 607
608 /* Decode device-specific states that may require an RNC resume during
609 * normal operation. When the abort path is active, these resumes are
610 * managed when the abort path exits.
611 */
612 if (state == SCI_STP_DEV_ATAPI_ERROR) {
613 /* For ATAPI error state resume the RNC right away. */
614 if (scu_get_event_type(event_code) == SCU_EVENT_TYPE_RNC_SUSPEND_TX ||
615 scu_get_event_type(event_code) == SCU_EVENT_TYPE_RNC_SUSPEND_TX_RX) {
616 return sci_remote_node_context_resume(&idev->rnc,
617 atapi_remote_device_resume_done,
618 idev);
619 }
620 }
621
622 if (state == SCI_STP_DEV_IDLE) {
623
624 /* We pick up suspension events to handle specifically to this
625 * state. We resume the RNC right away.
626 */
627 if (scu_get_event_type(event_code) == SCU_EVENT_TYPE_RNC_SUSPEND_TX ||
628 scu_get_event_type(event_code) == SCU_EVENT_TYPE_RNC_SUSPEND_TX_RX)
629 status = sci_remote_node_context_resume(&idev->rnc, NULL, NULL);
630 }
631
606 return status; 632 return status;
607} 633}
608 634
@@ -1137,21 +1163,6 @@ static void sci_stp_remote_device_ready_ncq_error_substate_enter(struct sci_base
1137 idev->not_ready_reason); 1163 idev->not_ready_reason);
1138} 1164}
1139 1165
1140static void sci_stp_remote_device_atapi_error_substate_enter(
1141 struct sci_base_state_machine *sm)
1142{
1143 struct isci_remote_device *idev = container_of(sm, typeof(*idev), sm);
1144
1145 /* This state is entered when an I/O is decoded with an error
1146 * condition. By this point the RNC expected suspension state is set.
1147 * The error conditions suspend the device, so unsuspend here if
1148 * possible.
1149 */
1150 sci_remote_node_context_resume(&idev->rnc,
1151 atapi_remote_device_resume_done,
1152 idev);
1153}
1154
1155static void sci_smp_remote_device_ready_idle_substate_enter(struct sci_base_state_machine *sm) 1166static void sci_smp_remote_device_ready_idle_substate_enter(struct sci_base_state_machine *sm)
1156{ 1167{
1157 struct isci_remote_device *idev = container_of(sm, typeof(*idev), sm); 1168 struct isci_remote_device *idev = container_of(sm, typeof(*idev), sm);
@@ -1202,9 +1213,7 @@ static const struct sci_base_state sci_remote_device_state_table[] = {
1202 [SCI_STP_DEV_NCQ_ERROR] = { 1213 [SCI_STP_DEV_NCQ_ERROR] = {
1203 .enter_state = sci_stp_remote_device_ready_ncq_error_substate_enter, 1214 .enter_state = sci_stp_remote_device_ready_ncq_error_substate_enter,
1204 }, 1215 },
1205 [SCI_STP_DEV_ATAPI_ERROR] = { 1216 [SCI_STP_DEV_ATAPI_ERROR] = { },
1206 .enter_state = sci_stp_remote_device_atapi_error_substate_enter,
1207 },
1208 [SCI_STP_DEV_AWAIT_RESET] = { }, 1217 [SCI_STP_DEV_AWAIT_RESET] = { },
1209 [SCI_SMP_DEV_IDLE] = { 1218 [SCI_SMP_DEV_IDLE] = {
1210 .enter_state = sci_smp_remote_device_ready_idle_substate_enter, 1219 .enter_state = sci_smp_remote_device_ready_idle_substate_enter,
diff --git a/drivers/scsi/isci/remote_device.h b/drivers/scsi/isci/remote_device.h
index ff34c4e8c1b1..7674caae1d88 100644
--- a/drivers/scsi/isci/remote_device.h
+++ b/drivers/scsi/isci/remote_device.h
@@ -382,4 +382,6 @@ enum sci_status isci_remote_device_terminate_requests(
382 struct isci_host *ihost, 382 struct isci_host *ihost,
383 struct isci_remote_device *idev, 383 struct isci_remote_device *idev,
384 struct isci_request *ireq); 384 struct isci_request *ireq);
385enum sci_status sci_remote_device_suspend(struct isci_remote_device *idev,
386 enum sci_remote_node_suspension_reasons reason);
385#endif /* !defined(_ISCI_REMOTE_DEVICE_H_) */ 387#endif /* !defined(_ISCI_REMOTE_DEVICE_H_) */
diff --git a/drivers/scsi/isci/request.c b/drivers/scsi/isci/request.c
index 415d5f55d1c6..6c530e4275e2 100644
--- a/drivers/scsi/isci/request.c
+++ b/drivers/scsi/isci/request.c
@@ -2118,6 +2118,9 @@ static enum sci_status stp_request_udma_await_tc_event(struct isci_request *ireq
2118 * completion. 2118 * completion.
2119 */ 2119 */
2120 if (ireq->stp.rsp.fis_type == FIS_REGD2H) { 2120 if (ireq->stp.rsp.fis_type == FIS_REGD2H) {
2121 sci_remote_device_suspend(ireq->target_device,
2122 SCI_SW_SUSPEND_NORMAL);
2123
2121 ireq->scu_status = SCU_TASK_DONE_CHECK_RESPONSE; 2124 ireq->scu_status = SCU_TASK_DONE_CHECK_RESPONSE;
2122 ireq->sci_status = SCI_FAILURE_IO_RESPONSE_VALID; 2125 ireq->sci_status = SCI_FAILURE_IO_RESPONSE_VALID;
2123 sci_change_state(&ireq->sm, SCI_REQ_COMPLETED); 2126 sci_change_state(&ireq->sm, SCI_REQ_COMPLETED);