SCI_STATUS scif_domain_discover( SCI_DOMAIN_HANDLE_T domain, U32 discover_timeout, U32 device_timeout ) { SCIF_SAS_DOMAIN_T * fw_domain = (SCIF_SAS_DOMAIN_T*) domain; SCI_STATUS status = SCI_SUCCESS; SCI_STATUS op_status = SCI_SUCCESS; SCIF_LOG_TRACE(( sci_base_object_get_logger(domain), SCIF_LOG_OBJECT_DOMAIN | SCIF_LOG_OBJECT_DOMAIN_DISCOVERY, "scif_domain_discover(0x%x, 0x%x, 0x%x) enter\n", domain, discover_timeout, device_timeout )); // Check to make sure the size of the domain doesn't cause potential issues // with the remote device timer and the domain timer. if ((device_timeout * sci_abstract_list_size(&fw_domain->remote_device_list)) > discover_timeout) status = SCI_WARNING_TIMER_CONFLICT; op_status = fw_domain->state_handlers->discover_handler( &fw_domain->parent, discover_timeout, device_timeout ); // The status of the discover operation takes priority. if ( (status == SCI_SUCCESS) || (status != SCI_SUCCESS && op_status != SCI_SUCCESS) ) { status = op_status; } return status; }
/** * @brief This method implements the actions taken when entering the * DISCOVERING state. This includes determining from which * state we entered. If we entered from stopping that some sort * of hot-remove of the port occurred. In the hot-remove case * all devices should be in the STOPPED state already and, as * a result, are removed from the domain with a notification sent * to the framework user. * * @note This method currently only handles hot-insert/hot-remove of * direct attached SSP devices. * * @param[in] object This parameter specifies the base object for which * the state transition is occurring. This is cast into a * SCIF_SAS_DOMAIN object in the method implementation. * * @return none */ static void scif_sas_domain_discovering_state_enter( SCI_BASE_OBJECT_T * object ) { SCIF_SAS_DOMAIN_T * fw_domain = (SCIF_SAS_DOMAIN_T *)object; SET_STATE_HANDLER( fw_domain, scif_sas_domain_state_handler_table, SCI_BASE_DOMAIN_STATE_DISCOVERING ); SCIF_LOG_TRACE(( sci_base_object_get_logger(fw_domain), SCIF_LOG_OBJECT_DOMAIN | SCIF_LOG_OBJECT_DOMAIN_DISCOVERY, "scif_sas_domain_discovering_state_enter(0x%x) enter\n", fw_domain )); fw_domain->broadcast_change_count = 0; // Did the domain just go through a port not ready action? If it did, // then we will be entering from the STOPPED state. if (fw_domain->parent.state_machine.previous_state_id != SCI_BASE_DOMAIN_STATE_STOPPED) { SCIF_SAS_REMOTE_DEVICE_T * remote_device; SCIC_PORT_PROPERTIES_T properties; scic_port_get_properties(fw_domain->core_object, &properties); // If the device has not yet been added to the domain, then // inform the user that the device is new. remote_device = (SCIF_SAS_REMOTE_DEVICE_T *) scif_domain_get_device_by_sas_address( fw_domain, &properties.remote.sas_address ); if (remote_device == SCI_INVALID_HANDLE) { // simply notify the user of the new DA device and be done // with discovery. scif_cb_domain_da_device_added( fw_domain->controller, fw_domain, &properties.remote.sas_address, &properties.remote.protocols ); } else { if(properties.remote.protocols.u.bits.smp_target) //kick off the smp discover process. scif_sas_domain_start_smp_discover(fw_domain, remote_device); } } else //entered from STOPPED state. { SCI_ABSTRACT_ELEMENT_T * current_element = sci_abstract_list_get_front(&(fw_domain->remote_device_list) ); SCIF_SAS_REMOTE_DEVICE_T * fw_device; while (current_element != NULL) { fw_device = (SCIF_SAS_REMOTE_DEVICE_T *) sci_abstract_list_get_object(current_element); ASSERT(fw_device->parent.state_machine.current_state_id == SCI_BASE_REMOTE_DEVICE_STATE_STOPPED); current_element = sci_abstract_list_get_next(current_element); SCIF_LOG_INFO(( sci_base_object_get_logger(fw_domain), SCIF_LOG_OBJECT_DOMAIN | SCIF_LOG_OBJECT_DOMAIN_DISCOVERY, "Controller:0x%x Domain:0x%x Device:0x%x removed\n", fw_domain->controller, fw_domain, fw_device )); // Notify the framework user of the device removal. scif_cb_domain_device_removed( fw_domain->controller, fw_domain, fw_device ); } ASSERT(fw_domain->request_list.element_count == 0); ASSERT(sci_abstract_list_size(&fw_domain->remote_device_list) == 0); sci_base_state_machine_change_state( &fw_domain->parent.state_machine, SCI_BASE_DOMAIN_STATE_STARTING ); } }