#include "hns3_ethdev.h"
#include "hns3_regs.h"
+#include "hns3_intr.h"
#include "hns3_logs.h"
#define hns3_is_csq(ring) ((ring)->flag & HNS3_TYPE_CSQ)
if (!is_valid_csq_clean_head(csq, head)) {
hns3_err(hw, "wrong cmd head (%u, %u-%u)", head,
csq->next_to_use, csq->next_to_clean);
- rte_atomic16_set(&hw->reset.disable_cmd, 1);
+ if (rte_eal_process_type() == RTE_PROC_PRIMARY) {
+ rte_atomic16_set(&hw->reset.disable_cmd, 1);
+ hns3_schedule_delayed_reset(HNS3_DEV_HW_TO_ADAPTER(hw));
+ }
+
return -EIO;
}
case HNS3_CMD_INVALID:
return -EBADR;
default:
- return -EIO;
+ return -EREMOTEIO;
}
}
static int hns3_cmd_poll_reply(struct hns3_hw *hw)
{
+ struct hns3_adapter *hns = HNS3_DEV_HW_TO_ADAPTER(hw);
uint32_t timeout = 0;
do {
return -EBUSY;
}
+ if (is_reset_pending(hns)) {
+ hns3_err(hw, "Don't wait for reply because of reset pending");
+ return -EIO;
+ }
+
rte_delay_us(1);
timeout++;
} while (timeout < hw->cmq.tx_timeout);
hns3_err(hw, "Wait for reply timeout");
- return -EBADE;
+ return -ETIME;
}
/*
* hns3_cmd_send - send command to command queue
- * @hw: pointer to the hw struct
- * @desc: prefilled descriptor for describing the command
- * @num : the number of descriptors to be sent
*
- * This is the main send command for command queue, it
+ * @param hw
+ * pointer to the hw struct
+ * @param desc
+ * prefilled descriptor for describing the command
+ * @param num
+ * the number of descriptors to be sent
+ * @return
+ * - -EBUSY if detect device is in resetting
+ * - -EIO if detect cmd csq corrupted (due to reset) or
+ * there is reset pending
+ * - -ENOMEM/-ETIME/...(Non-Zero) if other error case
+ * - Zero if operation completed successfully
+ *
+ * Note -BUSY/-EIO only used in reset case
+ *
+ * Note this is the main send command for command queue, it
* sends the queue, cleans the queue, etc
*/
int
int
hns3_cmd_init(struct hns3_hw *hw)
{
+ uint32_t version;
int ret;
rte_spinlock_lock(&hw->cmq.csq.lock);
hw->cmq.csq.next_to_use = 0;
hw->cmq.crq.next_to_clean = 0;
hw->cmq.crq.next_to_use = 0;
+ hw->mbx_resp.head = 0;
+ hw->mbx_resp.tail = 0;
+ hw->mbx_resp.lost = 0;
hns3_cmd_init_regs(hw);
rte_spinlock_unlock(&hw->cmq.crq.lock);
rte_spinlock_unlock(&hw->cmq.csq.lock);
+ /*
+ * Check if there is new reset pending, because the higher level
+ * reset may happen when lower level reset is being processed.
+ */
+ if (is_reset_pending(HNS3_DEV_HW_TO_ADAPTER(hw))) {
+ PMD_INIT_LOG(ERR, "New reset pending, keep disable cmd");
+ ret = -EBUSY;
+ goto err_cmd_init;
+ }
rte_atomic16_clear(&hw->reset.disable_cmd);
- ret = hns3_cmd_query_firmware_version(hw, &hw->fw_version);
+ ret = hns3_cmd_query_firmware_version(hw, &version);
if (ret) {
PMD_INIT_LOG(ERR, "firmware version query failed %d", ret);
goto err_cmd_init;
}
- PMD_INIT_LOG(INFO, "The firmware version is %08x", hw->fw_version);
+ hw->fw_version = version;
+ PMD_INIT_LOG(INFO, "The firmware version is %lu.%lu.%lu.%lu",
+ hns3_get_field(version, HNS3_FW_VERSION_BYTE3_M,
+ HNS3_FW_VERSION_BYTE3_S),
+ hns3_get_field(version, HNS3_FW_VERSION_BYTE2_M,
+ HNS3_FW_VERSION_BYTE2_S),
+ hns3_get_field(version, HNS3_FW_VERSION_BYTE1_M,
+ HNS3_FW_VERSION_BYTE1_S),
+ hns3_get_field(version, HNS3_FW_VERSION_BYTE0_M,
+ HNS3_FW_VERSION_BYTE0_S));
return 0;
err_cmd_init:
- hns3_cmd_uninit(hw);
+ rte_atomic16_set(&hw->reset.disable_cmd, 1);
return ret;
}