aboutsummaryrefslogtreecommitdiffstats
path: root/drivers
diff options
context:
space:
mode:
authorDan Williams <dan.j.williams@intel.com>2011-05-11 11:29:56 -0400
committerDan Williams <dan.j.williams@intel.com>2011-07-03 07:04:48 -0400
commit79e2b6b27699c916e3c7cda18a26d47fea6017fb (patch)
tree3d8aa7d0f9b203f210f66d6026d9414327a7309c /drivers
parenta7e255a34220ba57eeeb75637c911974e54c08e7 (diff)
isci: remove the completion and event state handlers
With these handlers gone the rest of the state handler infrastructure is removed. Added some WARN_ONCEs where previously we would cause NULL pointer dereferences or silently run handlers from a previous state. Reported-by: Christoph Hellwig <hch@lst.de> Signed-off-by: Dan Williams <dan.j.williams@intel.com>
Diffstat (limited to 'drivers')
-rw-r--r--drivers/scsi/isci/request.c514
-rw-r--r--drivers/scsi/isci/request.h37
2 files changed, 82 insertions, 469 deletions
diff --git a/drivers/scsi/isci/request.c b/drivers/scsi/isci/request.c
index cb13b78d8026..c63064ede38d 100644
--- a/drivers/scsi/isci/request.c
+++ b/drivers/scsi/isci/request.c
@@ -890,21 +890,62 @@ scic_sds_io_request_terminate(struct scic_sds_request *sci_req)
890 return SCI_FAILURE_INVALID_STATE; 890 return SCI_FAILURE_INVALID_STATE;
891} 891}
892 892
893enum sci_status scic_sds_io_request_event_handler( 893enum sci_status scic_sds_request_complete(struct scic_sds_request *sci_req)
894 struct scic_sds_request *request,
895 u32 event_code)
896{ 894{
897 if (request->state_handlers->event_handler) 895 enum sci_base_request_states state;
898 return request->state_handlers->event_handler(request, event_code); 896 struct scic_sds_controller *scic = sci_req->owning_controller;
897
898 state = sci_req->state_machine.current_state_id;
899 if (WARN_ONCE(state != SCI_BASE_REQUEST_STATE_COMPLETED,
900 "isci: request completion from wrong state (%d)\n", state))
901 return SCI_FAILURE_INVALID_STATE;
899 902
900 dev_warn(scic_to_dev(request->owning_controller), 903 if (!sci_req->was_tag_assigned_by_user)
901 "%s: SCIC IO Request given event code notification %x while " 904 scic_controller_free_io_tag(scic, sci_req->io_tag);
902 "in wrong state %d\n",
903 __func__,
904 event_code,
905 sci_base_state_machine_get_state(&request->state_machine));
906 905
907 return SCI_FAILURE_INVALID_STATE; 906 if (sci_req->saved_rx_frame_index != SCU_INVALID_FRAME_INDEX)
907 scic_sds_controller_release_frame(scic,
908 sci_req->saved_rx_frame_index);
909
910 /* XXX can we just stop the machine and remove the 'final' state? */
911 sci_base_state_machine_change_state(&sci_req->state_machine,
912 SCI_BASE_REQUEST_STATE_FINAL);
913 return SCI_SUCCESS;
914}
915
916enum sci_status scic_sds_io_request_event_handler(struct scic_sds_request *sci_req,
917 u32 event_code)
918{
919 enum sci_base_request_states state;
920 struct scic_sds_controller *scic = sci_req->owning_controller;
921
922 state = sci_req->state_machine.current_state_id;
923
924 if (state != SCIC_SDS_STP_REQUEST_STARTED_PIO_DATA_IN_AWAIT_DATA_SUBSTATE) {
925 dev_warn(scic_to_dev(scic), "%s: (%x) in wrong state %d\n",
926 __func__, event_code, state);
927
928 return SCI_FAILURE_INVALID_STATE;
929 }
930
931 switch (scu_get_event_specifier(event_code)) {
932 case SCU_TASK_DONE_CRC_ERR << SCU_EVENT_SPECIFIC_CODE_SHIFT:
933 /* We are waiting for data and the SCU has R_ERR the data frame.
934 * Go back to waiting for the D2H Register FIS
935 */
936 sci_base_state_machine_change_state(&sci_req->state_machine,
937 SCIC_SDS_STP_REQUEST_STARTED_PIO_AWAIT_FRAME_SUBSTATE);
938 return SCI_SUCCESS;
939 default:
940 dev_err(scic_to_dev(scic),
941 "%s: pio request unexpected event %#x\n",
942 __func__, event_code);
943
944 /* TODO Should we fail the PIO request when we get an
945 * unexpected event?
946 */
947 return SCI_FAILURE;
948 }
908} 949}
909 950
910/* 951/*
@@ -1080,34 +1121,8 @@ static enum sci_status request_started_state_tc_event(struct scic_sds_request *s
1080 return SCI_SUCCESS; 1121 return SCI_SUCCESS;
1081} 1122}
1082 1123
1083/* 1124static enum sci_status request_aborting_state_tc_event(struct scic_sds_request *sci_req,
1084 * This method implements the action to be taken when an SCIC_SDS_IO_REQUEST_T 1125 u32 completion_code)
1085 * object receives a scic_sds_request_complete() request. This method frees up
1086 * any io request resources that have been allocated and transitions the
1087 * request to its final state. Consider stopping the state machine instead of
1088 * transitioning to the final state? enum sci_status SCI_SUCCESS
1089 */
1090static enum sci_status scic_sds_request_completed_state_complete_handler(
1091 struct scic_sds_request *request)
1092{
1093 if (request->was_tag_assigned_by_user != true) {
1094 scic_controller_free_io_tag(
1095 request->owning_controller, request->io_tag);
1096 }
1097
1098 if (request->saved_rx_frame_index != SCU_INVALID_FRAME_INDEX) {
1099 scic_sds_controller_release_frame(
1100 request->owning_controller, request->saved_rx_frame_index);
1101 }
1102
1103 sci_base_state_machine_change_state(&request->state_machine,
1104 SCI_BASE_REQUEST_STATE_FINAL);
1105 return SCI_SUCCESS;
1106}
1107
1108static enum sci_status request_aborting_state_tc_event(
1109 struct scic_sds_request *sci_req,
1110 u32 completion_code)
1111{ 1126{
1112 switch (SCU_GET_COMPLETION_TL_STATUS(completion_code)) { 1127 switch (SCU_GET_COMPLETION_TL_STATUS(completion_code)) {
1113 case (SCU_TASK_DONE_GOOD << SCU_COMPLETION_TL_STATUS_SHIFT): 1128 case (SCU_TASK_DONE_GOOD << SCU_COMPLETION_TL_STATUS_SHIFT):
@@ -1585,48 +1600,6 @@ static enum sci_status pio_data_out_tx_done_tc_event(struct scic_sds_request *sc
1585 return status; 1600 return status;
1586} 1601}
1587 1602
1588/**
1589 *
1590 * @request: This is the request which is receiving the event.
1591 * @event_code: This is the event code that the request on which the request is
1592 * expected to take action.
1593 *
1594 * This method will handle any link layer events while waiting for the data
1595 * frame. enum sci_status SCI_SUCCESS SCI_FAILURE
1596 */
1597static enum sci_status scic_sds_stp_request_pio_data_in_await_data_event_handler(
1598 struct scic_sds_request *request,
1599 u32 event_code)
1600{
1601 enum sci_status status;
1602
1603 switch (scu_get_event_specifier(event_code)) {
1604 case SCU_TASK_DONE_CRC_ERR << SCU_EVENT_SPECIFIC_CODE_SHIFT:
1605 /*
1606 * We are waiting for data and the SCU has R_ERR the data frame.
1607 * Go back to waiting for the D2H Register FIS */
1608 sci_base_state_machine_change_state(
1609 &request->state_machine,
1610 SCIC_SDS_STP_REQUEST_STARTED_PIO_AWAIT_FRAME_SUBSTATE
1611 );
1612
1613 status = SCI_SUCCESS;
1614 break;
1615
1616 default:
1617 dev_err(scic_to_dev(request->owning_controller),
1618 "%s: SCIC PIO Request 0x%p received unexpected "
1619 "event 0x%08x\n",
1620 __func__, request, event_code);
1621
1622 /* / @todo Should we fail the PIO request when we get an unexpected event? */
1623 status = SCI_FAILURE;
1624 break;
1625 }
1626
1627 return status;
1628}
1629
1630static void scic_sds_stp_request_udma_complete_request( 1603static void scic_sds_stp_request_udma_complete_request(
1631 struct scic_sds_request *request, 1604 struct scic_sds_request *request,
1632 u32 scu_status, 1605 u32 scu_status,
@@ -2236,37 +2209,6 @@ scic_sds_io_request_tc_completion(struct scic_sds_request *sci_req, u32 completi
2236 } 2209 }
2237} 2210}
2238 2211
2239
2240
2241static const struct scic_sds_io_request_state_handler scic_sds_request_state_handler_table[] = {
2242 [SCI_BASE_REQUEST_STATE_INITIAL] = {},
2243 [SCI_BASE_REQUEST_STATE_CONSTRUCTED] = {},
2244 [SCI_BASE_REQUEST_STATE_STARTED] = { },
2245 [SCIC_SDS_IO_REQUEST_STARTED_TASK_MGMT_SUBSTATE_AWAIT_TC_COMPLETION] = { },
2246 [SCIC_SDS_IO_REQUEST_STARTED_TASK_MGMT_SUBSTATE_AWAIT_TC_RESPONSE] = { },
2247 [SCIC_SDS_SMP_REQUEST_STARTED_SUBSTATE_AWAIT_RESPONSE] = { },
2248 [SCIC_SDS_SMP_REQUEST_STARTED_SUBSTATE_AWAIT_TC_COMPLETION] = { },
2249 [SCIC_SDS_STP_REQUEST_STARTED_UDMA_AWAIT_TC_COMPLETION_SUBSTATE] = { },
2250 [SCIC_SDS_STP_REQUEST_STARTED_UDMA_AWAIT_D2H_REG_FIS_SUBSTATE] = { },
2251 [SCIC_SDS_STP_REQUEST_STARTED_NON_DATA_AWAIT_H2D_COMPLETION_SUBSTATE] = { },
2252 [SCIC_SDS_STP_REQUEST_STARTED_NON_DATA_AWAIT_D2H_SUBSTATE] = { },
2253 [SCIC_SDS_STP_REQUEST_STARTED_PIO_AWAIT_H2D_COMPLETION_SUBSTATE] = { },
2254 [SCIC_SDS_STP_REQUEST_STARTED_PIO_AWAIT_FRAME_SUBSTATE] = { },
2255 [SCIC_SDS_STP_REQUEST_STARTED_PIO_DATA_IN_AWAIT_DATA_SUBSTATE] = {
2256 .event_handler = scic_sds_stp_request_pio_data_in_await_data_event_handler,
2257 },
2258 [SCIC_SDS_STP_REQUEST_STARTED_PIO_DATA_OUT_TRANSMIT_DATA_SUBSTATE] = { },
2259 [SCIC_SDS_STP_REQUEST_STARTED_SOFT_RESET_AWAIT_H2D_ASSERTED_COMPLETION_SUBSTATE] = { },
2260 [SCIC_SDS_STP_REQUEST_STARTED_SOFT_RESET_AWAIT_H2D_DIAGNOSTIC_COMPLETION_SUBSTATE] = { },
2261 [SCIC_SDS_STP_REQUEST_STARTED_SOFT_RESET_AWAIT_D2H_RESPONSE_FRAME_SUBSTATE] = { },
2262 [SCI_BASE_REQUEST_STATE_COMPLETED] = {
2263 .complete_handler = scic_sds_request_completed_state_complete_handler,
2264 },
2265 [SCI_BASE_REQUEST_STATE_ABORTING] = { },
2266 [SCI_BASE_REQUEST_STATE_FINAL] = { },
2267};
2268
2269
2270/** 2212/**
2271 * isci_request_process_response_iu() - This function sets the status and 2213 * isci_request_process_response_iu() - This function sets the status and
2272 * response iu, in the task struct, from the request object for the upper 2214 * response iu, in the task struct, from the request object for the upper
@@ -2958,46 +2900,6 @@ static void isci_request_io_request_complete(struct isci_host *isci_host,
2958 isci_host_can_dequeue(isci_host, 1); 2900 isci_host_can_dequeue(isci_host, 1);
2959} 2901}
2960 2902
2961/**
2962 * scic_sds_request_initial_state_enter() -
2963 * @object: This parameter specifies the base object for which the state
2964 * transition is occurring.
2965 *
2966 * This method implements the actions taken when entering the
2967 * SCI_BASE_REQUEST_STATE_INITIAL state. This state is entered when the initial
2968 * base request is constructed. Entry into the initial state sets all handlers
2969 * for the io request object to their default handlers. none
2970 */
2971static void scic_sds_request_initial_state_enter(void *object)
2972{
2973 struct scic_sds_request *sci_req = object;
2974
2975 SET_STATE_HANDLER(
2976 sci_req,
2977 scic_sds_request_state_handler_table,
2978 SCI_BASE_REQUEST_STATE_INITIAL
2979 );
2980}
2981
2982/**
2983 * scic_sds_request_constructed_state_enter() -
2984 * @object: The io request object that is to enter the constructed state.
2985 *
2986 * This method implements the actions taken when entering the
2987 * SCI_BASE_REQUEST_STATE_CONSTRUCTED state. The method sets the state handlers
2988 * for the the constructed state. none
2989 */
2990static void scic_sds_request_constructed_state_enter(void *object)
2991{
2992 struct scic_sds_request *sci_req = object;
2993
2994 SET_STATE_HANDLER(
2995 sci_req,
2996 scic_sds_request_state_handler_table,
2997 SCI_BASE_REQUEST_STATE_CONSTRUCTED
2998 );
2999}
3000
3001static void scic_sds_request_started_state_enter(void *object) 2903static void scic_sds_request_started_state_enter(void *object)
3002{ 2904{
3003 struct scic_sds_request *sci_req = object; 2905 struct scic_sds_request *sci_req = object;
@@ -3011,12 +2913,6 @@ static void scic_sds_request_started_state_enter(void *object)
3011 */ 2913 */
3012 task = ireq->ttype == io_task ? isci_request_access_task(ireq) : NULL; 2914 task = ireq->ttype == io_task ? isci_request_access_task(ireq) : NULL;
3013 2915
3014 SET_STATE_HANDLER(
3015 sci_req,
3016 scic_sds_request_state_handler_table,
3017 SCI_BASE_REQUEST_STATE_STARTED
3018 );
3019
3020 /* all unaccelerated request types (non ssp or ncq) handled with 2916 /* all unaccelerated request types (non ssp or ncq) handled with
3021 * substates 2917 * substates
3022 */ 2918 */
@@ -3046,30 +2942,13 @@ static void scic_sds_request_started_state_enter(void *object)
3046 } 2942 }
3047} 2943}
3048 2944
3049/**
3050 * scic_sds_request_completed_state_enter() -
3051 * @object: This parameter specifies the base object for which the state
3052 * transition is occurring. This object is cast into a SCIC_SDS_IO_REQUEST
3053 * object.
3054 *
3055 * This method implements the actions taken when entering the
3056 * SCI_BASE_REQUEST_STATE_COMPLETED state. This state is entered when the
3057 * SCIC_SDS_IO_REQUEST has completed. The method will decode the request
3058 * completion status and convert it to an enum sci_status to return in the
3059 * completion callback function. none
3060 */
3061static void scic_sds_request_completed_state_enter(void *object) 2945static void scic_sds_request_completed_state_enter(void *object)
3062{ 2946{
3063 struct scic_sds_request *sci_req = object; 2947 struct scic_sds_request *sci_req = object;
3064 struct scic_sds_controller *scic = 2948 struct scic_sds_controller *scic = sci_req->owning_controller;
3065 scic_sds_request_get_controller(sci_req);
3066 struct isci_host *ihost = scic_to_ihost(scic); 2949 struct isci_host *ihost = scic_to_ihost(scic);
3067 struct isci_request *ireq = sci_req_to_ireq(sci_req); 2950 struct isci_request *ireq = sci_req_to_ireq(sci_req);
3068 2951
3069 SET_STATE_HANDLER(sci_req,
3070 scic_sds_request_state_handler_table,
3071 SCI_BASE_REQUEST_STATE_COMPLETED);
3072
3073 /* Tell the SCI_USER that the IO request is complete */ 2952 /* Tell the SCI_USER that the IO request is complete */
3074 if (sci_req->is_task_management_request == false) 2953 if (sci_req->is_task_management_request == false)
3075 isci_request_io_request_complete(ihost, ireq, 2954 isci_request_io_request_complete(ihost, ireq,
@@ -3078,93 +2957,12 @@ static void scic_sds_request_completed_state_enter(void *object)
3078 isci_task_request_complete(ihost, ireq, sci_req->sci_status); 2957 isci_task_request_complete(ihost, ireq, sci_req->sci_status);
3079} 2958}
3080 2959
3081/**
3082 * scic_sds_request_aborting_state_enter() -
3083 * @object: This parameter specifies the base object for which the state
3084 * transition is occurring. This object is cast into a SCIC_SDS_IO_REQUEST
3085 * object.
3086 *
3087 * This method implements the actions taken when entering the
3088 * SCI_BASE_REQUEST_STATE_ABORTING state. none
3089 */
3090static void scic_sds_request_aborting_state_enter(void *object) 2960static void scic_sds_request_aborting_state_enter(void *object)
3091{ 2961{
3092 struct scic_sds_request *sci_req = object; 2962 struct scic_sds_request *sci_req = object;
3093 2963
3094 /* Setting the abort bit in the Task Context is required by the silicon. */ 2964 /* Setting the abort bit in the Task Context is required by the silicon. */
3095 sci_req->task_context_buffer->abort = 1; 2965 sci_req->task_context_buffer->abort = 1;
3096
3097 SET_STATE_HANDLER(
3098 sci_req,
3099 scic_sds_request_state_handler_table,
3100 SCI_BASE_REQUEST_STATE_ABORTING
3101 );
3102}
3103
3104/**
3105 * scic_sds_request_final_state_enter() -
3106 * @object: This parameter specifies the base object for which the state
3107 * transition is occurring. This is cast into a SCIC_SDS_IO_REQUEST object.
3108 *
3109 * This method implements the actions taken when entering the
3110 * SCI_BASE_REQUEST_STATE_FINAL state. The only action required is to put the
3111 * state handlers in place. none
3112 */
3113static void scic_sds_request_final_state_enter(void *object)
3114{
3115 struct scic_sds_request *sci_req = object;
3116
3117 SET_STATE_HANDLER(
3118 sci_req,
3119 scic_sds_request_state_handler_table,
3120 SCI_BASE_REQUEST_STATE_FINAL
3121 );
3122}
3123
3124static void scic_sds_io_request_started_task_mgmt_await_tc_completion_substate_enter(
3125 void *object)
3126{
3127 struct scic_sds_request *sci_req = object;
3128
3129 SET_STATE_HANDLER(
3130 sci_req,
3131 scic_sds_request_state_handler_table,
3132 SCIC_SDS_IO_REQUEST_STARTED_TASK_MGMT_SUBSTATE_AWAIT_TC_COMPLETION
3133 );
3134}
3135
3136static void scic_sds_io_request_started_task_mgmt_await_task_response_substate_enter(
3137 void *object)
3138{
3139 struct scic_sds_request *sci_req = object;
3140
3141 SET_STATE_HANDLER(
3142 sci_req,
3143 scic_sds_request_state_handler_table,
3144 SCIC_SDS_IO_REQUEST_STARTED_TASK_MGMT_SUBSTATE_AWAIT_TC_RESPONSE
3145 );
3146}
3147
3148static void scic_sds_smp_request_started_await_response_substate_enter(void *object)
3149{
3150 struct scic_sds_request *sci_req = object;
3151
3152 SET_STATE_HANDLER(
3153 sci_req,
3154 scic_sds_request_state_handler_table,
3155 SCIC_SDS_SMP_REQUEST_STARTED_SUBSTATE_AWAIT_RESPONSE
3156 );
3157}
3158
3159static void scic_sds_smp_request_started_await_tc_completion_substate_enter(void *object)
3160{
3161 struct scic_sds_request *sci_req = object;
3162
3163 SET_STATE_HANDLER(
3164 sci_req,
3165 scic_sds_request_state_handler_table,
3166 SCIC_SDS_SMP_REQUEST_STARTED_SUBSTATE_AWAIT_TC_COMPLETION
3167 );
3168} 2966}
3169 2967
3170static void scic_sds_stp_request_started_non_data_await_h2d_completion_enter( 2968static void scic_sds_stp_request_started_non_data_await_h2d_completion_enter(
@@ -3172,133 +2970,27 @@ static void scic_sds_stp_request_started_non_data_await_h2d_completion_enter(
3172{ 2970{
3173 struct scic_sds_request *sci_req = object; 2971 struct scic_sds_request *sci_req = object;
3174 2972
3175 SET_STATE_HANDLER( 2973 scic_sds_remote_device_set_working_request(sci_req->target_device,
3176 sci_req, 2974 sci_req);
3177 scic_sds_request_state_handler_table,
3178 SCIC_SDS_STP_REQUEST_STARTED_NON_DATA_AWAIT_H2D_COMPLETION_SUBSTATE
3179 );
3180
3181 scic_sds_remote_device_set_working_request(
3182 sci_req->target_device, sci_req
3183 );
3184}
3185
3186static void scic_sds_stp_request_started_non_data_await_d2h_enter(void *object)
3187{
3188 struct scic_sds_request *sci_req = object;
3189
3190 SET_STATE_HANDLER(
3191 sci_req,
3192 scic_sds_request_state_handler_table,
3193 SCIC_SDS_STP_REQUEST_STARTED_NON_DATA_AWAIT_D2H_SUBSTATE
3194 );
3195}
3196
3197
3198
3199static void scic_sds_stp_request_started_pio_await_h2d_completion_enter(
3200 void *object)
3201{
3202 struct scic_sds_request *sci_req = object;
3203
3204 SET_STATE_HANDLER(
3205 sci_req,
3206 scic_sds_request_state_handler_table,
3207 SCIC_SDS_STP_REQUEST_STARTED_PIO_AWAIT_H2D_COMPLETION_SUBSTATE
3208 );
3209
3210 scic_sds_remote_device_set_working_request(
3211 sci_req->target_device, sci_req);
3212}
3213
3214static void scic_sds_stp_request_started_pio_await_frame_enter(void *object)
3215{
3216 struct scic_sds_request *sci_req = object;
3217
3218 SET_STATE_HANDLER(
3219 sci_req,
3220 scic_sds_request_state_handler_table,
3221 SCIC_SDS_STP_REQUEST_STARTED_PIO_AWAIT_FRAME_SUBSTATE
3222 );
3223} 2975}
3224 2976
3225static void scic_sds_stp_request_started_pio_data_in_await_data_enter( 2977static void scic_sds_stp_request_started_pio_await_h2d_completion_enter(void *object)
3226 void *object)
3227{ 2978{
3228 struct scic_sds_request *sci_req = object; 2979 struct scic_sds_request *sci_req = object;
3229 2980
3230 SET_STATE_HANDLER( 2981 scic_sds_remote_device_set_working_request(sci_req->target_device,
3231 sci_req, 2982 sci_req);
3232 scic_sds_request_state_handler_table,
3233 SCIC_SDS_STP_REQUEST_STARTED_PIO_DATA_IN_AWAIT_DATA_SUBSTATE
3234 );
3235} 2983}
3236 2984
3237static void scic_sds_stp_request_started_pio_data_out_transmit_data_enter( 2985static void scic_sds_stp_request_started_soft_reset_await_h2d_asserted_completion_enter(void *object)
3238 void *object)
3239{ 2986{
3240 struct scic_sds_request *sci_req = object; 2987 struct scic_sds_request *sci_req = object;
3241 2988
3242 SET_STATE_HANDLER( 2989 scic_sds_remote_device_set_working_request(sci_req->target_device,
3243 sci_req, 2990 sci_req);
3244 scic_sds_request_state_handler_table,
3245 SCIC_SDS_STP_REQUEST_STARTED_PIO_DATA_OUT_TRANSMIT_DATA_SUBSTATE
3246 );
3247} 2991}
3248 2992
3249 2993static void scic_sds_stp_request_started_soft_reset_await_h2d_diagnostic_completion_enter(void *object)
3250
3251static void scic_sds_stp_request_started_udma_await_tc_completion_enter(
3252 void *object)
3253{
3254 struct scic_sds_request *sci_req = object;
3255
3256 SET_STATE_HANDLER(
3257 sci_req,
3258 scic_sds_request_state_handler_table,
3259 SCIC_SDS_STP_REQUEST_STARTED_UDMA_AWAIT_TC_COMPLETION_SUBSTATE
3260 );
3261}
3262
3263/**
3264 *
3265 *
3266 * This state is entered when there is an TC completion failure. The hardware
3267 * received an unexpected condition while processing the IO request and now
3268 * will UF the D2H register FIS to complete the IO.
3269 */
3270static void scic_sds_stp_request_started_udma_await_d2h_reg_fis_enter(
3271 void *object)
3272{
3273 struct scic_sds_request *sci_req = object;
3274
3275 SET_STATE_HANDLER(
3276 sci_req,
3277 scic_sds_request_state_handler_table,
3278 SCIC_SDS_STP_REQUEST_STARTED_UDMA_AWAIT_D2H_REG_FIS_SUBSTATE
3279 );
3280}
3281
3282
3283
3284static void scic_sds_stp_request_started_soft_reset_await_h2d_asserted_completion_enter(
3285 void *object)
3286{
3287 struct scic_sds_request *sci_req = object;
3288
3289 SET_STATE_HANDLER(
3290 sci_req,
3291 scic_sds_request_state_handler_table,
3292 SCIC_SDS_STP_REQUEST_STARTED_SOFT_RESET_AWAIT_H2D_ASSERTED_COMPLETION_SUBSTATE
3293 );
3294
3295 scic_sds_remote_device_set_working_request(
3296 sci_req->target_device, sci_req
3297 );
3298}
3299
3300static void scic_sds_stp_request_started_soft_reset_await_h2d_diagnostic_completion_enter(
3301 void *object)
3302{ 2994{
3303 struct scic_sds_request *sci_req = object; 2995 struct scic_sds_request *sci_req = object;
3304 struct scu_task_context *task_context; 2996 struct scu_task_context *task_context;
@@ -3315,91 +3007,45 @@ static void scic_sds_stp_request_started_soft_reset_await_h2d_diagnostic_complet
3315 task_context->control_frame = 0; 3007 task_context->control_frame = 0;
3316 3008
3317 status = scic_controller_continue_io(sci_req); 3009 status = scic_controller_continue_io(sci_req);
3318 if (status == SCI_SUCCESS) { 3010 WARN_ONCE(status != SCI_SUCCESS, "isci: continue io failure\n");
3319 SET_STATE_HANDLER(
3320 sci_req,
3321 scic_sds_request_state_handler_table,
3322 SCIC_SDS_STP_REQUEST_STARTED_SOFT_RESET_AWAIT_H2D_DIAGNOSTIC_COMPLETION_SUBSTATE
3323 );
3324 }
3325}
3326
3327static void scic_sds_stp_request_started_soft_reset_await_d2h_response_enter(
3328 void *object)
3329{
3330 struct scic_sds_request *sci_req = object;
3331
3332 SET_STATE_HANDLER(
3333 sci_req,
3334 scic_sds_request_state_handler_table,
3335 SCIC_SDS_STP_REQUEST_STARTED_SOFT_RESET_AWAIT_D2H_RESPONSE_FRAME_SUBSTATE
3336 );
3337} 3011}
3338 3012
3339static const struct sci_base_state scic_sds_request_state_table[] = { 3013static const struct sci_base_state scic_sds_request_state_table[] = {
3340 [SCI_BASE_REQUEST_STATE_INITIAL] = { 3014 [SCI_BASE_REQUEST_STATE_INITIAL] = { },
3341 .enter_state = scic_sds_request_initial_state_enter, 3015 [SCI_BASE_REQUEST_STATE_CONSTRUCTED] = { },
3342 },
3343 [SCI_BASE_REQUEST_STATE_CONSTRUCTED] = {
3344 .enter_state = scic_sds_request_constructed_state_enter,
3345 },
3346 [SCI_BASE_REQUEST_STATE_STARTED] = { 3016 [SCI_BASE_REQUEST_STATE_STARTED] = {
3347 .enter_state = scic_sds_request_started_state_enter, 3017 .enter_state = scic_sds_request_started_state_enter,
3348 }, 3018 },
3349 [SCIC_SDS_STP_REQUEST_STARTED_NON_DATA_AWAIT_H2D_COMPLETION_SUBSTATE] = { 3019 [SCIC_SDS_STP_REQUEST_STARTED_NON_DATA_AWAIT_H2D_COMPLETION_SUBSTATE] = {
3350 .enter_state = scic_sds_stp_request_started_non_data_await_h2d_completion_enter, 3020 .enter_state = scic_sds_stp_request_started_non_data_await_h2d_completion_enter,
3351 }, 3021 },
3352 [SCIC_SDS_STP_REQUEST_STARTED_NON_DATA_AWAIT_D2H_SUBSTATE] = { 3022 [SCIC_SDS_STP_REQUEST_STARTED_NON_DATA_AWAIT_D2H_SUBSTATE] = { },
3353 .enter_state = scic_sds_stp_request_started_non_data_await_d2h_enter,
3354 },
3355 [SCIC_SDS_STP_REQUEST_STARTED_PIO_AWAIT_H2D_COMPLETION_SUBSTATE] = { 3023 [SCIC_SDS_STP_REQUEST_STARTED_PIO_AWAIT_H2D_COMPLETION_SUBSTATE] = {
3356 .enter_state = scic_sds_stp_request_started_pio_await_h2d_completion_enter, 3024 .enter_state = scic_sds_stp_request_started_pio_await_h2d_completion_enter,
3357 }, 3025 },
3358 [SCIC_SDS_STP_REQUEST_STARTED_PIO_AWAIT_FRAME_SUBSTATE] = { 3026 [SCIC_SDS_STP_REQUEST_STARTED_PIO_AWAIT_FRAME_SUBSTATE] = { },
3359 .enter_state = scic_sds_stp_request_started_pio_await_frame_enter, 3027 [SCIC_SDS_STP_REQUEST_STARTED_PIO_DATA_IN_AWAIT_DATA_SUBSTATE] = { },
3360 }, 3028 [SCIC_SDS_STP_REQUEST_STARTED_PIO_DATA_OUT_TRANSMIT_DATA_SUBSTATE] = { },
3361 [SCIC_SDS_STP_REQUEST_STARTED_PIO_DATA_IN_AWAIT_DATA_SUBSTATE] = { 3029 [SCIC_SDS_STP_REQUEST_STARTED_UDMA_AWAIT_TC_COMPLETION_SUBSTATE] = { },
3362 .enter_state = scic_sds_stp_request_started_pio_data_in_await_data_enter, 3030 [SCIC_SDS_STP_REQUEST_STARTED_UDMA_AWAIT_D2H_REG_FIS_SUBSTATE] = { },
3363 },
3364 [SCIC_SDS_STP_REQUEST_STARTED_PIO_DATA_OUT_TRANSMIT_DATA_SUBSTATE] = {
3365 .enter_state = scic_sds_stp_request_started_pio_data_out_transmit_data_enter,
3366 },
3367 [SCIC_SDS_STP_REQUEST_STARTED_UDMA_AWAIT_TC_COMPLETION_SUBSTATE] = {
3368 .enter_state = scic_sds_stp_request_started_udma_await_tc_completion_enter,
3369 },
3370 [SCIC_SDS_STP_REQUEST_STARTED_UDMA_AWAIT_D2H_REG_FIS_SUBSTATE] = {
3371 .enter_state = scic_sds_stp_request_started_udma_await_d2h_reg_fis_enter,
3372 },
3373 [SCIC_SDS_STP_REQUEST_STARTED_SOFT_RESET_AWAIT_H2D_ASSERTED_COMPLETION_SUBSTATE] = { 3031 [SCIC_SDS_STP_REQUEST_STARTED_SOFT_RESET_AWAIT_H2D_ASSERTED_COMPLETION_SUBSTATE] = {
3374 .enter_state = scic_sds_stp_request_started_soft_reset_await_h2d_asserted_completion_enter, 3032 .enter_state = scic_sds_stp_request_started_soft_reset_await_h2d_asserted_completion_enter,
3375 }, 3033 },
3376 [SCIC_SDS_STP_REQUEST_STARTED_SOFT_RESET_AWAIT_H2D_DIAGNOSTIC_COMPLETION_SUBSTATE] = { 3034 [SCIC_SDS_STP_REQUEST_STARTED_SOFT_RESET_AWAIT_H2D_DIAGNOSTIC_COMPLETION_SUBSTATE] = {
3377 .enter_state = scic_sds_stp_request_started_soft_reset_await_h2d_diagnostic_completion_enter, 3035 .enter_state = scic_sds_stp_request_started_soft_reset_await_h2d_diagnostic_completion_enter,
3378 }, 3036 },
3379 [SCIC_SDS_STP_REQUEST_STARTED_SOFT_RESET_AWAIT_D2H_RESPONSE_FRAME_SUBSTATE] = { 3037 [SCIC_SDS_STP_REQUEST_STARTED_SOFT_RESET_AWAIT_D2H_RESPONSE_FRAME_SUBSTATE] = { },
3380 .enter_state = scic_sds_stp_request_started_soft_reset_await_d2h_response_enter, 3038 [SCIC_SDS_IO_REQUEST_STARTED_TASK_MGMT_SUBSTATE_AWAIT_TC_COMPLETION] = { },
3381 }, 3039 [SCIC_SDS_IO_REQUEST_STARTED_TASK_MGMT_SUBSTATE_AWAIT_TC_RESPONSE] = { },
3382 [SCIC_SDS_IO_REQUEST_STARTED_TASK_MGMT_SUBSTATE_AWAIT_TC_COMPLETION] = { 3040 [SCIC_SDS_SMP_REQUEST_STARTED_SUBSTATE_AWAIT_RESPONSE] = { },
3383 .enter_state = scic_sds_io_request_started_task_mgmt_await_tc_completion_substate_enter, 3041 [SCIC_SDS_SMP_REQUEST_STARTED_SUBSTATE_AWAIT_TC_COMPLETION] = { },
3384 },
3385 [SCIC_SDS_IO_REQUEST_STARTED_TASK_MGMT_SUBSTATE_AWAIT_TC_RESPONSE] = {
3386 .enter_state = scic_sds_io_request_started_task_mgmt_await_task_response_substate_enter,
3387 },
3388 [SCIC_SDS_SMP_REQUEST_STARTED_SUBSTATE_AWAIT_RESPONSE] = {
3389 .enter_state = scic_sds_smp_request_started_await_response_substate_enter,
3390 },
3391 [SCIC_SDS_SMP_REQUEST_STARTED_SUBSTATE_AWAIT_TC_COMPLETION] = {
3392 .enter_state = scic_sds_smp_request_started_await_tc_completion_substate_enter,
3393 },
3394 [SCI_BASE_REQUEST_STATE_COMPLETED] = { 3042 [SCI_BASE_REQUEST_STATE_COMPLETED] = {
3395 .enter_state = scic_sds_request_completed_state_enter, 3043 .enter_state = scic_sds_request_completed_state_enter,
3396 }, 3044 },
3397 [SCI_BASE_REQUEST_STATE_ABORTING] = { 3045 [SCI_BASE_REQUEST_STATE_ABORTING] = {
3398 .enter_state = scic_sds_request_aborting_state_enter, 3046 .enter_state = scic_sds_request_aborting_state_enter,
3399 }, 3047 },
3400 [SCI_BASE_REQUEST_STATE_FINAL] = { 3048 [SCI_BASE_REQUEST_STATE_FINAL] = { },
3401 .enter_state = scic_sds_request_final_state_enter,
3402 },
3403}; 3049};
3404 3050
3405static void scic_sds_general_request_construct(struct scic_sds_controller *scic, 3051static void scic_sds_general_request_construct(struct scic_sds_controller *scic,
diff --git a/drivers/scsi/isci/request.h b/drivers/scsi/isci/request.h
index e13ca3f7c8d7..31d6d5717473 100644
--- a/drivers/scsi/isci/request.h
+++ b/drivers/scsi/isci/request.h
@@ -224,13 +224,6 @@ struct scic_sds_request {
224 u32 saved_rx_frame_index; 224 u32 saved_rx_frame_index;
225 225
226 /** 226 /**
227 * This field specifies the current state handlers in place for this
228 * IO Request object. This field is updated each time the request
229 * changes state.
230 */
231 const struct scic_sds_io_request_state_handler *state_handlers;
232
233 /**
234 * This field in the recorded device sequence for the io request. This is 227 * This field in the recorded device sequence for the io request. This is
235 * recorded during the build operation and is compared in the start 228 * recorded during the build operation and is compared in the start
236 * operation. If the sequence is different then there was a change of 229 * operation. If the sequence is different then there was a change of
@@ -422,27 +415,6 @@ enum sci_base_request_states {
422 SCI_BASE_REQUEST_STATE_FINAL, 415 SCI_BASE_REQUEST_STATE_FINAL,
423}; 416};
424 417
425typedef enum sci_status (*scic_sds_io_request_handler_t)
426 (struct scic_sds_request *request);
427typedef enum sci_status (*scic_sds_io_request_event_handler_t)
428 (struct scic_sds_request *req, u32 event);
429
430/**
431 * struct scic_sds_io_request_state_handler - This is the SDS core definition
432 * of the state handlers.
433 *
434 *
435 */
436struct scic_sds_io_request_state_handler {
437 /**
438 * The complete_handler specifies the method invoked when a user attempts to
439 * complete a request.
440 */
441 scic_sds_io_request_handler_t complete_handler;
442
443 scic_sds_io_request_event_handler_t event_handler;
444};
445
446/** 418/**
447 * scic_sds_request_get_controller() - 419 * scic_sds_request_get_controller() -
448 * 420 *
@@ -495,13 +467,6 @@ struct scic_sds_io_request_state_handler {
495 (request)->sci_status = (sci_status_code); \ 467 (request)->sci_status = (sci_status_code); \
496 } 468 }
497 469
498#define scic_sds_request_complete(a_request) \
499 ((a_request)->state_handlers->complete_handler(a_request))
500
501
502extern enum sci_status
503scic_sds_io_request_tc_completion(struct scic_sds_request *request, u32 completion_code);
504
505/** 470/**
506 * SCU_SGL_ZERO() - 471 * SCU_SGL_ZERO() -
507 * 472 *
@@ -538,6 +503,8 @@ enum sci_status scic_sds_io_request_event_handler(struct scic_sds_request *sci_r
538enum sci_status scic_sds_io_request_frame_handler(struct scic_sds_request *sci_req, 503enum sci_status scic_sds_io_request_frame_handler(struct scic_sds_request *sci_req,
539 u32 frame_index); 504 u32 frame_index);
540enum sci_status scic_sds_task_request_terminate(struct scic_sds_request *sci_req); 505enum sci_status scic_sds_task_request_terminate(struct scic_sds_request *sci_req);
506extern enum sci_status scic_sds_request_complete(struct scic_sds_request *sci_req);
507extern enum sci_status scic_sds_io_request_tc_completion(struct scic_sds_request *sci_req, u32 code);
541 508
542/* XXX open code in caller */ 509/* XXX open code in caller */
543static inline void *scic_request_get_virt_addr(struct scic_sds_request *sci_req, 510static inline void *scic_request_get_virt_addr(struct scic_sds_request *sci_req,