Skip to content

Commit 35f11c3

Browse files
committed
Merge branch 'pci/aspm'
- Save parent L1 PM Substates config so when we restore it along with an endpoint's config, the parent info isn't junk (Jian-Hong Pan) * pci/aspm: PCI/ASPM: Save parent L1SS config in pci_save_aspm_l1ss_state()
2 parents 40384c8 + 1db806e commit 35f11c3

File tree

1 file changed

+28
-5
lines changed

1 file changed

+28
-5
lines changed

drivers/pci/pcie/aspm.c

Lines changed: 28 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -81,24 +81,47 @@ void pci_configure_aspm_l1ss(struct pci_dev *pdev)
8181

8282
void pci_save_aspm_l1ss_state(struct pci_dev *pdev)
8383
{
84+
struct pci_dev *parent = pdev->bus->self;
8485
struct pci_cap_saved_state *save_state;
85-
u16 l1ss = pdev->l1ss;
8686
u32 *cap;
8787

88+
/*
89+
* If this is a Downstream Port, we never restore the L1SS state
90+
* directly; we only restore it when we restore the state of the
91+
* Upstream Port below it.
92+
*/
93+
if (pcie_downstream_port(pdev) || !parent)
94+
return;
95+
96+
if (!pdev->l1ss || !parent->l1ss)
97+
return;
98+
8899
/*
89100
* Save L1 substate configuration. The ASPM L0s/L1 configuration
90101
* in PCI_EXP_LNKCTL_ASPMC is saved by pci_save_pcie_state().
91102
*/
92-
if (!l1ss)
103+
save_state = pci_find_saved_ext_cap(pdev, PCI_EXT_CAP_ID_L1SS);
104+
if (!save_state)
93105
return;
94106

95-
save_state = pci_find_saved_ext_cap(pdev, PCI_EXT_CAP_ID_L1SS);
107+
cap = &save_state->cap.data[0];
108+
pci_read_config_dword(pdev, pdev->l1ss + PCI_L1SS_CTL2, cap++);
109+
pci_read_config_dword(pdev, pdev->l1ss + PCI_L1SS_CTL1, cap++);
110+
111+
if (parent->state_saved)
112+
return;
113+
114+
/*
115+
* Save parent's L1 substate configuration so we have it for
116+
* pci_restore_aspm_l1ss_state(pdev) to restore.
117+
*/
118+
save_state = pci_find_saved_ext_cap(parent, PCI_EXT_CAP_ID_L1SS);
96119
if (!save_state)
97120
return;
98121

99122
cap = &save_state->cap.data[0];
100-
pci_read_config_dword(pdev, l1ss + PCI_L1SS_CTL2, cap++);
101-
pci_read_config_dword(pdev, l1ss + PCI_L1SS_CTL1, cap++);
123+
pci_read_config_dword(parent, parent->l1ss + PCI_L1SS_CTL2, cap++);
124+
pci_read_config_dword(parent, parent->l1ss + PCI_L1SS_CTL1, cap++);
102125
}
103126

104127
void pci_restore_aspm_l1ss_state(struct pci_dev *pdev)

0 commit comments

Comments
 (0)