Skip to content

Commit 0699940

Browse files
Carl HuangKalle Valo
authored andcommitted
ath11k: pci: fix L1ss clock unstable problem
For QCA6390, one PCI related clock drifts sometimes, and it makes PCI link difficult to quit L1ss. Fix it by writing some registers which are known to fix the problem. Tested-on: QCA6390 hw2.0 PCI WLAN.HST.1.0.1-01740-QCAHSTSWPLZ_V2_TO_X86-1 Signed-off-by: Carl Huang <[email protected]> Signed-off-by: Kalle Valo <[email protected]> Link: https://lore.kernel.org/r/[email protected]
1 parent babb0ce commit 0699940

File tree

2 files changed

+81
-0
lines changed

2 files changed

+81
-0
lines changed

drivers/net/wireless/ath/ath11k/pci.c

Lines changed: 70 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -239,6 +239,75 @@ static void ath11k_pci_clear_dbg_registers(struct ath11k_base *ab)
239239
ath11k_dbg(ab, ATH11K_DBG_PCI, "soc reset cause:%d\n", val);
240240
}
241241

242+
static int ath11k_pci_set_link_reg(struct ath11k_base *ab,
243+
u32 offset, u32 value, u32 mask)
244+
{
245+
u32 v;
246+
int i;
247+
248+
v = ath11k_pci_read32(ab, offset);
249+
if ((v & mask) == value)
250+
return 0;
251+
252+
for (i = 0; i < 10; i++) {
253+
ath11k_pci_write32(ab, offset, (v & ~mask) | value);
254+
255+
v = ath11k_pci_read32(ab, offset);
256+
if ((v & mask) == value)
257+
return 0;
258+
259+
mdelay(2);
260+
}
261+
262+
ath11k_warn(ab, "failed to set pcie link register 0x%08x: 0x%08x != 0x%08x\n",
263+
offset, v & mask, value);
264+
265+
return -ETIMEDOUT;
266+
}
267+
268+
static int ath11k_pci_fix_l1ss(struct ath11k_base *ab)
269+
{
270+
int ret;
271+
272+
ret = ath11k_pci_set_link_reg(ab,
273+
PCIE_QSERDES_COM_SYSCLK_EN_SEL_REG,
274+
PCIE_QSERDES_COM_SYSCLK_EN_SEL_VAL,
275+
PCIE_QSERDES_COM_SYSCLK_EN_SEL_MSK);
276+
if (!ret) {
277+
ath11k_warn(ab, "failed to set sysclk: %d\n", ret);
278+
return ret;
279+
}
280+
281+
ret = ath11k_pci_set_link_reg(ab,
282+
PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG1_REG,
283+
PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG1_VAL,
284+
PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG_MSK);
285+
if (!ret) {
286+
ath11k_warn(ab, "failed to set dtct config1 error: %d\n", ret);
287+
return ret;
288+
}
289+
290+
ret = ath11k_pci_set_link_reg(ab,
291+
PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG2_REG,
292+
PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG2_VAL,
293+
PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG_MSK);
294+
if (!ret) {
295+
ath11k_warn(ab, "failed to set dtct config2: %d\n", ret);
296+
return ret;
297+
}
298+
299+
ret = ath11k_pci_set_link_reg(ab,
300+
PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG4_REG,
301+
PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG4_VAL,
302+
PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG_MSK);
303+
if (!ret) {
304+
ath11k_warn(ab, "failed to set dtct config4: %d\n", ret);
305+
return ret;
306+
}
307+
308+
return 0;
309+
}
310+
242311
static void ath11k_pci_enable_ltssm(struct ath11k_base *ab)
243312
{
244313
u32 val;
@@ -288,6 +357,7 @@ static void ath11k_pci_sw_reset(struct ath11k_base *ab, bool power_on)
288357
if (power_on) {
289358
ath11k_pci_enable_ltssm(ab);
290359
ath11k_pci_clear_all_intrs(ab);
360+
ath11k_pci_fix_l1ss(ab);
291361
}
292362

293363
ath11k_mhi_clear_vector(ab);

drivers/net/wireless/ath/ath11k/pci.h

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,17 @@
3434
#define PCIE_SMLH_REQ_RST_LINK_DOWN 0x2
3535
#define PCIE_INT_CLEAR_ALL 0xffffffff
3636

37+
#define PCIE_QSERDES_COM_SYSCLK_EN_SEL_REG 0x01e0c0ac
38+
#define PCIE_QSERDES_COM_SYSCLK_EN_SEL_VAL 0x10
39+
#define PCIE_QSERDES_COM_SYSCLK_EN_SEL_MSK 0xffffffff
40+
#define PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG1_REG 0x01e0c628
41+
#define PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG1_VAL 0x02
42+
#define PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG2_REG 0x01e0c62c
43+
#define PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG2_VAL 0x52
44+
#define PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG4_REG 0x01e0c634
45+
#define PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG4_VAL 0xff
46+
#define PCIE_USB3_PCS_MISC_OSC_DTCT_CONFIG_MSK 0x000000ff
47+
3748
struct ath11k_msi_user {
3849
char *name;
3950
int num_vectors;

0 commit comments

Comments
 (0)