scsi: ufs: Fixes line-reset and adapt sequence

Fix adapt sequence for G4 and don't dump registers
on Line-reset.

Change-Id: Ibbe09d75c1655d2400878305e7b38e7e2f744e52
Signed-off-by: Asutosh Das <asutoshd@codeaurora.org>
This commit is contained in:
Asutosh Das 2020-06-11 13:39:47 -07:00
commit ab3e3b4bed
3 changed files with 82 additions and 15 deletions

View file

@ -1380,6 +1380,46 @@ static void ufs_qcom_dev_ref_clk_ctrl(struct ufs_qcom_host *host, bool enable)
}
}
#if defined(CONFIG_SCSI_UFSHCD_QTI)
static void ufs_qcom_set_adapt(struct ufs_hba *hba)
{
u32 peer_rx_hs_adapt_initial_cap;
int ret;
ret = ufshcd_dme_peer_get(hba,
UIC_ARG_MIB_SEL(RX_HS_ADAPT_INITIAL_CAPABILITY,
UIC_ARG_MPHY_RX_GEN_SEL_INDEX(0)),
&peer_rx_hs_adapt_initial_cap);
if (ret) {
dev_err(hba->dev,
"%s: RX_HS_ADAPT_INITIAL_CAP get failed %d\n",
__func__, ret);
peer_rx_hs_adapt_initial_cap =
PA_PEERRXHSADAPTINITIAL_Default;
}
ret = ufshcd_dme_set(hba, UIC_ARG_MIB(PA_PEERRXHSADAPTINITIAL),
peer_rx_hs_adapt_initial_cap);
if (ret)
dev_err(hba->dev,
"%s: PA_PEERRXHSADAPTINITIAL set failed %d\n",
__func__, ret);
/* INITIAL ADAPT */
ufshcd_dme_set(hba,
UIC_ARG_MIB(PA_TXHSADAPTTYPE),
PA_INITIAL_ADAPT);
}
#else
static void ufs_qcom_set_adapt(struct ufs_hba *hba)
{
/* INITIAL ADAPT */
ufshcd_dme_set(hba,
UIC_ARG_MIB(PA_TXHSADAPTTYPE),
PA_INITIAL_ADAPT);
}
#endif
static int ufs_qcom_pwr_change_notify(struct ufs_hba *hba,
enum ufs_notify_change_status status,
struct ufs_pa_layer_attr *dev_max_params,
@ -1450,19 +1490,14 @@ static int ufs_qcom_pwr_change_notify(struct ufs_hba *hba,
ufshcd_is_hs_mode(dev_req_params))
ufs_qcom_dev_ref_clk_ctrl(host, true);
if (host->hw_ver.major >= 0x4) {
if (dev_req_params->gear_tx == UFS_HS_G4) {
/* INITIAL ADAPT */
ufshcd_dme_set(hba,
UIC_ARG_MIB(PA_TXHSADAPTTYPE),
PA_INITIAL_ADAPT);
} else {
/* NO ADAPT */
ufshcd_dme_set(hba,
UIC_ARG_MIB(PA_TXHSADAPTTYPE),
PA_NO_ADAPT);
}
}
if ((host->hw_ver.major >= 0x4) &&
(dev_req_params->gear_tx == UFS_HS_G4))
ufs_qcom_set_adapt(hba);
else
/* NO ADAPT */
ufshcd_dme_set(hba,
UIC_ARG_MIB(PA_TXHSADAPTTYPE),
PA_NO_ADAPT);
break;
case POST_CHANGE:
if (ufs_qcom_cfg_timers(hba, dev_req_params->gear_rx,
@ -2768,6 +2803,24 @@ static void ufs_qcom_print_utp_hci_testbus(struct ufs_hba *hba)
kfree(testbus);
}
static void ufshcd_print_fsm_state(struct ufs_hba *hba)
{
int err = 0, tx_fsm_val = 0, rx_fsm_val = 0;
err = ufshcd_dme_get(hba,
UIC_ARG_MIB_SEL(MPHY_TX_FSM_STATE,
UIC_ARG_MPHY_TX_GEN_SEL_INDEX(0)),
&tx_fsm_val);
dev_err(hba->dev, "%s: TX_FSM_STATE = %u, err = %d\n", __func__,
tx_fsm_val, err);
err = ufshcd_dme_get(hba,
UIC_ARG_MIB_SEL(MPHY_RX_FSM_STATE,
UIC_ARG_MPHY_RX_GEN_SEL_INDEX(0)),
&rx_fsm_val);
dev_err(hba->dev, "%s: RX_FSM_STATE = %u, err = %d\n", __func__,
rx_fsm_val, err);
}
static void ufs_qcom_dump_dbg_regs(struct ufs_hba *hba)
{
struct ufs_qcom_host *host = ufshcd_get_variant(hba);
@ -2791,6 +2844,7 @@ static void ufs_qcom_dump_dbg_regs(struct ufs_hba *hba)
usleep_range(1000, 1100);
ufs_qcom_phy_dbg_register_dump(phy);
}
ufshcd_print_fsm_state(hba);
}
/*

View file

@ -58,8 +58,13 @@
#define UFSHCD_ENABLE_INTRS (UTP_TRANSFER_REQ_COMPL |\
UTP_TASK_REQ_COMPL |\
UFSHCD_ERROR_MASK)
#if defined(CONFIG_SCSI_UFSHCD_QTI)
/* UIC command timeout, unit: ms */
#define UIC_CMD_TIMEOUT 999
#else
/* UIC command timeout, unit: ms */
#define UIC_CMD_TIMEOUT 500
#endif
/* NOP OUT retries waiting for NOP IN response */
#define NOP_OUT_RETRIES 10
@ -5849,6 +5854,10 @@ static irqreturn_t ufshcd_update_uic_error(struct ufs_hba *hba)
/* PHY layer lane error */
reg = ufshcd_readl(hba, REG_UIC_ERROR_CODE_PHY_ADAPTER_LAYER);
#if defined(CONFIG_SCSI_UFSHCD_QTI)
if (reg & UIC_PHY_ADAPTER_LAYER_GENERIC_ERROR)
dev_err(hba->dev, "line-reset: 0x%08x\n", reg);
#endif
/* Ignore LINERESET indication, as this is not an error */
if ((reg & UIC_PHY_ADAPTER_LAYER_ERROR) &&
(reg & UIC_PHY_ADAPTER_LAYER_LANE_ERR_MASK)) {
@ -6096,6 +6105,10 @@ static irqreturn_t ufshcd_intr(int irq, void *__hba)
if (enabled_intr_status)
retval |= ufshcd_sl_intr(hba, enabled_intr_status);
#if defined(CONFIG_SCSI_UFSHCD_QTI)
if (enabled_intr_status)
retval = IRQ_HANDLED;
#endif
intr_status = ufshcd_readl(hba, REG_INTERRUPT_STATUS);
} while (intr_status && --retries);

View file

@ -941,9 +941,9 @@ struct ufs_hba {
#endif
#ifdef CONFIG_SCSI_UFSHCD_QTI
#define UFSHCD_CAP_POWER_COLLAPSE_DURING_HIBERN8 (1 << 7)
#define UFSHCD_CAP_POWER_COLLAPSE_DURING_HIBERN8 (1 << 8)
/* Allow standalone Hibern8 enter on idle */
#define UFSHCD_CAP_HIBERN8_ENTER_ON_IDLE (1 << 5)
#define UFSHCD_CAP_HIBERN8_ENTER_ON_IDLE (1 << 9)
struct rw_semaphore lock;
/* Bitmask for enabling debug prints */
u32 ufshcd_dbg_print;