FreeBSD/sys/dev/isci/scil/scic_sds_smp_request.c
/**
 * @brief This method processes an unsolicited frame while the SMP request is
 *        waiting for a response frame.  It will copy the response data, release
 *        the unsolicited frame, and transition the request to the
 *        SCI_BASE_REQUEST_STATE_COMPLETED state.
 *
 * @param[in] this_request This parameter specifies the request for which
 *            the unsolicited frame was received.
 * @param[in] frame_index This parameter indicates the unsolicited frame
 *            index that should contain the response.
 *
 * @return This method returns an indication of whether the response
 *         frame was handled successfully or not.
 * @retval SCI_SUCCESS Currently this value is always returned and indicates
 *         successful processing of the TC response.
 */
@brief This method processes an unsolicited frame while the SMP request is
waiting for a response frame.  It will copy the response data, release
the unsolicited frame, and transition the request to the
SCI_BASE_REQUEST_STATE_COMPLETED state.

@param[in] this_request This parameter specifies the request for which
the unsolicited frame was received.
@param[in] frame_index This parameter indicates the unsolicited frame
index that should contain the response.

@return This method returns an indication of whether the response
frame was handled successfully or not.
@retval SCI_SUCCESS Currently this value is always returned and indicates
successful processing of the TC response.
@brief This method processes an unsolicited frame while the SMP request is waiting for a response frame . It will copy the response data release the unsolicited frame and transition the request to the SCI_BASE_REQUEST_STATE_COMPLETED state . @param [ in ] this_request This parameter specifies the request for which the unsolicited frame was received . @param [ in ] frame_index This parameter indicates the unsolicited frame index that should contain the response . @return This method returns an indication of whether the response frame was handled successfully or not . @retval SCI_SUCCESS Currently this value is always returned and indicates successful processing of the TC response .
static
SCI_STATUS scic_sds_smp_request_await_response_frame_handler(
   SCIC_SDS_REQUEST_T * this_request,
   U32                  frame_index
)
{
   SCI_STATUS              status;
   void                  * frame_header;
   SMP_RESPONSE_HEADER_T * this_frame_header;
   U8                    * user_smp_buffer = this_request->response_buffer;
   SCIC_SDS_CONTROLLER_T * controller = scic_sds_request_get_controller(this_request);
   SCIC_LOG_TRACE((
      sci_base_object_get_logger(this_request),
      SCIC_LOG_OBJECT_SMP_IO_REQUEST,
      "scic_sds_smp_request_await_response_frame_handler(0x%x, 0x%x) enter\n",
      this_request, frame_index
   ));
   status = scic_sds_unsolicited_frame_control_get_header(
      &(controller->uf_control),
      frame_index,
      &frame_header
   );
   scic_word_copy_with_swap(
      (U32*) user_smp_buffer,
      frame_header,
      sizeof(SMP_RESPONSE_HEADER_T)/sizeof(U32)
   );
   this_frame_header = (SMP_RESPONSE_HEADER_T*) user_smp_buffer;
   if (this_frame_header->smp_frame_type == SMP_FRAME_TYPE_RESPONSE)
   {
      void * smp_response_buffer;
      status = scic_sds_unsolicited_frame_control_get_buffer(
         &(controller->uf_control),
         frame_index,
         &smp_response_buffer
      );
      scic_word_copy_with_swap(
         (U32*) (user_smp_buffer + sizeof(SMP_RESPONSE_HEADER_T)),
         smp_response_buffer,
         sizeof(SMP_RESPONSE_BODY_T)/sizeof(U32)
      );
      if (this_frame_header->function == SMP_FUNCTION_DISCOVER)
      {
          SMP_RESPONSE_T * this_smp_response;
          this_smp_response = (SMP_RESPONSE_T *)user_smp_buffer;
          if (this_smp_response->response.discover.protocols.u.bits.attached_sata_device
           && !this_smp_response->response.discover.protocols.u.bits.attached_stp_target)
          {
              this_smp_response->response.discover.protocols.u.bits.attached_stp_target = 1;
              SCIC_LOG_TRACE((
                  sci_base_object_get_logger(this_request),
                 SCIC_LOG_OBJECT_SMP_IO_REQUEST,
                 "scic_sds_smp_request_await_response_frame_handler(0x%x) Found SATA dev, setting STP bit.\n",
                 this_request
              ));
          }
      }
      scic_sds_request_set_status(
         this_request, SCU_TASK_DONE_GOOD, SCI_SUCCESS
      );
      sci_base_state_machine_change_state(
         &this_request->started_substate_machine,
         SCIC_SDS_SMP_REQUEST_STARTED_SUBSTATE_AWAIT_TC_COMPLETION
      );
   }
   else
   {
      SCIC_LOG_ERROR((
         sci_base_object_get_logger(this_request),
         SCIC_LOG_OBJECT_SMP_IO_REQUEST,
         "SCIC SMP Request 0x%08x received unexpected frame %d type 0x%02x\n",
         this_request, frame_index, this_frame_header->smp_frame_type
      ));
     scic_sds_request_set_status(
        this_request,
        SCU_TASK_DONE_SMP_FRM_TYPE_ERR,
        SCI_FAILURE_CONTROLLER_SPECIFIC_IO_ERR
     );
     sci_base_state_machine_change_state(
         &this_request->parent.state_machine,
         SCI_BASE_REQUEST_STATE_COMPLETED
      );
   }
   scic_sds_controller_release_frame(
      controller, frame_index
   );
   return SCI_SUCCESS;
}
static SCI_STATUS scic_sds_smp_request_await_response_frame_handler ( SCIC_SDS_REQUEST_T * this_request , U32 frame_index ) { SCI_STATUS status ; void * frame_header ; SMP_RESPONSE_HEADER_T * this_frame_header ; U8 * user_smp_buffer = this_request -> response_buffer ; SCIC_SDS_CONTROLLER_T * controller = scic_sds_request_get_controller ( this_request ) ; SCIC_LOG_TRACE ( ( sci_base_object_get_logger ( this_request ) , SCIC_LOG_OBJECT_SMP_IO_REQUEST , " \n " , this_request , frame_index ) ) ; status = scic_sds_unsolicited_frame_control_get_header ( & ( controller -> uf_control ) , frame_index , & frame_header ) ; scic_word_copy_with_swap ( ( U32 * ) user_smp_buffer , frame_header , sizeof ( SMP_RESPONSE_HEADER_T ) / sizeof ( U32 ) ) ; this_frame_header = ( SMP_RESPONSE_HEADER_T * ) user_smp_buffer ; if ( this_frame_header -> smp_frame_type == SMP_FRAME_TYPE_RESPONSE ) { void * smp_response_buffer ; status = scic_sds_unsolicited_frame_control_get_buffer ( & ( controller -> uf_control ) , frame_index , & smp_response_buffer ) ; scic_word_copy_with_swap ( ( U32 * ) ( user_smp_buffer + sizeof ( SMP_RESPONSE_HEADER_T ) ) , smp_response_buffer , sizeof ( SMP_RESPONSE_BODY_T ) / sizeof ( U32 ) ) ; if ( this_frame_header -> function == SMP_FUNCTION_DISCOVER ) { SMP_RESPONSE_T * this_smp_response ; this_smp_response = ( SMP_RESPONSE_T * ) user_smp_buffer ; if ( this_smp_response -> response . discover . protocols . u . bits . attached_sata_device && ! this_smp_response -> response . discover . protocols . u . bits . attached_stp_target ) { this_smp_response -> response . discover . protocols . u . bits . attached_stp_target = 1 ; SCIC_LOG_TRACE ( ( sci_base_object_get_logger ( this_request ) , SCIC_LOG_OBJECT_SMP_IO_REQUEST , " \n " , this_request ) ) ; } } scic_sds_request_set_status ( this_request , SCU_TASK_DONE_GOOD , SCI_SUCCESS ) ; sci_base_state_machine_change_state ( & this_request -> started_substate_machine , SCIC_SDS_SMP_REQUEST_STARTED_SUBSTATE_AWAIT_TC_COMPLETION ) ; } else { SCIC_LOG_ERROR ( ( sci_base_object_get_logger ( this_request ) , SCIC_LOG_OBJECT_SMP_IO_REQUEST , " \n " , this_request , frame_index , this_frame_header -> smp_frame_type ) ) ; scic_sds_request_set_status ( this_request , SCU_TASK_DONE_SMP_FRM_TYPE_ERR , SCI_FAILURE_CONTROLLER_SPECIFIC_IO_ERR ) ; sci_base_state_machine_change_state ( & this_request -> parent . state_machine , SCI_BASE_REQUEST_STATE_COMPLETED ) ; } scic_sds_controller_release_frame ( controller , frame_index ) ; return SCI_SUCCESS ; }
@brief This method processes an unsolicited frame while the SMP request is
        waiting for a response frame.
@brief This method processes an unsolicited frame while the SMP request is waiting for a response frame .
// Save off the controller, so that we do not touch the request after it //  is completed. //byte swap the header. // Some expanders only report an attached SATA device, and // not an STP target.  Since the core depends on the STP // target attribute to correctly build I/O, set the bit now // if necessary. //Don't need to copy to user space. User instead will refer to //core request's response buffer. //copy the smp response to framework smp request's response buffer. //scic_sds_smp_request_copy_response(this_request); // This was not a response frame why did it get forwarded?