@@ -241,6 +241,64 @@ static void ath11k_pci_clear_dbg_registers(struct ath11k_base *ab)
ath11k_dbg(ab, ATH11K_DBG_PCI, "soc reset cause:%d\n", val);
}
+static bool ath11k_pci_set_link_reg(struct ath11k_base *ab,
+ u32 offset, u32 value, u32 mask)
+{
+ u32 ret;
+ int count = 10;
+
+ ret = ath11k_pci_read32(ab, offset);
+ if ((ret & mask) == value)
+ return true;
+
+ while (count > 0) {
+ ath11k_pci_write32(ab, offset, (ret & ~mask) | value);
+ ret = ath11k_pci_read32(ab, offset);
+ if ((ret & mask) == value)
+ return true;
+
+ mdelay(2);
+ count--;
+ }
+
+ ath11k_err(ab, "%s: Failed to set Pcie Link Register 0x%08x to 0x%08x\n",
+ __func__, offset, ret);
+ return false;
+}
+
+static void ath11k_pci_fix_l1ss(struct ath11k_base *ab)
+{
+ if (!ath11k_pci_set_link_reg(ab,
+ PCIE_QSERDES_COM_SYSCLK_EN_SEL_REG,
+ PCIE_QSERDES_COM_SYSCLK_EN_SEL_VAL,
+ PCIE_QSERDES_COM_SYSCLK_EN_SEL_MSK)) {
+ ath11k_err(ab, "%s set sysclk error\n", __func__);
+ return;
+ }
+
+ if (!ath11k_pci_set_link_reg(ab,
+ PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG1_REG,
+ PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG1_VAL,
+ PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG_MSK)) {
+ ath11k_err(ab, "%s set dtct_config1 error\n", __func__);
+ return;
+ }
+
+ if (!ath11k_pci_set_link_reg(ab,
+ PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG2_REG,
+ PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG2_VAL,
+ PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG_MSK)) {
+ ath11k_err(ab, "%s set dtct_config2 error\n", __func__);
+ return;
+ }
+
+ if (!ath11k_pci_set_link_reg(ab,
+ PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG4_REG,
+ PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG4_VAL,
+ PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG_MSK))
+ ath11k_err(ab, "%s set dtct_config4 error\n", __func__);
+}
+
static void ath11k_pci_enable_LTSSM(struct ath11k_base *ab)
{
u32 val;
@@ -300,6 +358,7 @@ static void ath11k_pci_sw_reset(struct ath11k_base *ab, bool power_on)
if (power_on) {
ath11k_pci_enable_LTSSM(ab);
ath11k_pci_clear_all_intrs(ab);
+ ath11k_pci_fix_l1ss(ab);
}
ath11k_mhi_clear_vector(ab);
@@ -34,6 +34,17 @@
#define PCIE_SMLH_REQ_RST_LINK_DOWN 0x2
#define PCIE_INT_CLEAR_ALL 0xFFFFFFFF
+#define PCIE_QSERDES_COM_SYSCLK_EN_SEL_REG 0x01E0C0AC
+#define PCIE_QSERDES_COM_SYSCLK_EN_SEL_VAL 0x10
+#define PCIE_QSERDES_COM_SYSCLK_EN_SEL_MSK 0xFFFFFFFF
+#define PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG1_REG 0x01E0C628
+#define PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG1_VAL 0x02
+#define PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG2_REG 0x01E0C62C
+#define PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG2_VAL 0x52
+#define PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG4_REG 0x01E0C634
+#define PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG4_VAL 0xFF
+#define PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG_MSK 0x000000FF
+
struct ath11k_msi_user {
char *name;
int num_vectors;