diff options
Diffstat (limited to 'drivers')
-rw-r--r-- | drivers/net/wireless/ath/ath9k/ar9002_hw.c | 6 | ||||
-rw-r--r-- | drivers/net/wireless/ath/ath9k/ar9003_hw.c | 6 | ||||
-rw-r--r-- | drivers/net/wireless/ath/ath9k/hw.c | 11 | ||||
-rw-r--r-- | drivers/net/wireless/ath/ath9k/hw.h | 3 | ||||
-rw-r--r-- | drivers/net/wireless/ath/ath9k/pci.c | 27 |
5 files changed, 40 insertions, 13 deletions
diff --git a/drivers/net/wireless/ath/ath9k/ar9002_hw.c b/drivers/net/wireless/ath/ath9k/ar9002_hw.c index 9ff7c30573b8..44d9d8d56490 100644 --- a/drivers/net/wireless/ath/ath9k/ar9002_hw.c +++ b/drivers/net/wireless/ath/ath9k/ar9002_hw.c | |||
@@ -309,11 +309,7 @@ static void ar9002_hw_configpcipowersave(struct ath_hw *ah, | |||
309 | u8 i; | 309 | u8 i; |
310 | u32 val; | 310 | u32 val; |
311 | 311 | ||
312 | if (ah->is_pciexpress != true) | 312 | if (ah->is_pciexpress != true || ah->aspm_enabled != true) |
313 | return; | ||
314 | |||
315 | /* Do not touch SerDes registers */ | ||
316 | if (ah->config.pcie_powersave_enable == 2) | ||
317 | return; | 313 | return; |
318 | 314 | ||
319 | /* Nothing to do on restore for 11N */ | 315 | /* Nothing to do on restore for 11N */ |
diff --git a/drivers/net/wireless/ath/ath9k/ar9003_hw.c b/drivers/net/wireless/ath/ath9k/ar9003_hw.c index 8efdec247c02..ad2bb2bf4e8a 100644 --- a/drivers/net/wireless/ath/ath9k/ar9003_hw.c +++ b/drivers/net/wireless/ath/ath9k/ar9003_hw.c | |||
@@ -519,11 +519,7 @@ static void ar9003_hw_configpcipowersave(struct ath_hw *ah, | |||
519 | int restore, | 519 | int restore, |
520 | int power_off) | 520 | int power_off) |
521 | { | 521 | { |
522 | if (ah->is_pciexpress != true) | 522 | if (ah->is_pciexpress != true || ah->aspm_enabled != true) |
523 | return; | ||
524 | |||
525 | /* Do not touch SerDes registers */ | ||
526 | if (ah->config.pcie_powersave_enable == 2) | ||
527 | return; | 523 | return; |
528 | 524 | ||
529 | /* Nothing to do on restore for 11N */ | 525 | /* Nothing to do on restore for 11N */ |
diff --git a/drivers/net/wireless/ath/ath9k/hw.c b/drivers/net/wireless/ath/ath9k/hw.c index 8006ce0c7357..8dcefe74f4c3 100644 --- a/drivers/net/wireless/ath/ath9k/hw.c +++ b/drivers/net/wireless/ath/ath9k/hw.c | |||
@@ -318,6 +318,14 @@ static void ath9k_hw_disablepcie(struct ath_hw *ah) | |||
318 | REG_WRITE(ah, AR_PCIE_SERDES2, 0x00000000); | 318 | REG_WRITE(ah, AR_PCIE_SERDES2, 0x00000000); |
319 | } | 319 | } |
320 | 320 | ||
321 | static void ath9k_hw_aspm_init(struct ath_hw *ah) | ||
322 | { | ||
323 | struct ath_common *common = ath9k_hw_common(ah); | ||
324 | |||
325 | if (common->bus_ops->aspm_init) | ||
326 | common->bus_ops->aspm_init(common); | ||
327 | } | ||
328 | |||
321 | /* This should work for all families including legacy */ | 329 | /* This should work for all families including legacy */ |
322 | static bool ath9k_hw_chip_test(struct ath_hw *ah) | 330 | static bool ath9k_hw_chip_test(struct ath_hw *ah) |
323 | { | 331 | { |
@@ -378,7 +386,6 @@ static void ath9k_hw_init_config(struct ath_hw *ah) | |||
378 | ah->config.additional_swba_backoff = 0; | 386 | ah->config.additional_swba_backoff = 0; |
379 | ah->config.ack_6mb = 0x0; | 387 | ah->config.ack_6mb = 0x0; |
380 | ah->config.cwm_ignore_extcca = 0; | 388 | ah->config.cwm_ignore_extcca = 0; |
381 | ah->config.pcie_powersave_enable = 0; | ||
382 | ah->config.pcie_clock_req = 0; | 389 | ah->config.pcie_clock_req = 0; |
383 | ah->config.pcie_waen = 0; | 390 | ah->config.pcie_waen = 0; |
384 | ah->config.analog_shiftreg = 1; | 391 | ah->config.analog_shiftreg = 1; |
@@ -598,7 +605,7 @@ static int __ath9k_hw_init(struct ath_hw *ah) | |||
598 | 605 | ||
599 | 606 | ||
600 | if (ah->is_pciexpress) | 607 | if (ah->is_pciexpress) |
601 | ath9k_hw_configpcipowersave(ah, 0, 0); | 608 | ath9k_hw_aspm_init(ah); |
602 | else | 609 | else |
603 | ath9k_hw_disablepcie(ah); | 610 | ath9k_hw_disablepcie(ah); |
604 | 611 | ||
diff --git a/drivers/net/wireless/ath/ath9k/hw.h b/drivers/net/wireless/ath/ath9k/hw.h index 6acd0f975ae1..c79889036ec4 100644 --- a/drivers/net/wireless/ath/ath9k/hw.h +++ b/drivers/net/wireless/ath/ath9k/hw.h | |||
@@ -219,7 +219,6 @@ struct ath9k_ops_config { | |||
219 | int additional_swba_backoff; | 219 | int additional_swba_backoff; |
220 | int ack_6mb; | 220 | int ack_6mb; |
221 | u32 cwm_ignore_extcca; | 221 | u32 cwm_ignore_extcca; |
222 | u8 pcie_powersave_enable; | ||
223 | bool pcieSerDesWrite; | 222 | bool pcieSerDesWrite; |
224 | u8 pcie_clock_req; | 223 | u8 pcie_clock_req; |
225 | u32 pcie_waen; | 224 | u32 pcie_waen; |
@@ -673,6 +672,7 @@ struct ath_hw { | |||
673 | 672 | ||
674 | bool sw_mgmt_crypto; | 673 | bool sw_mgmt_crypto; |
675 | bool is_pciexpress; | 674 | bool is_pciexpress; |
675 | bool aspm_enabled; | ||
676 | bool is_monitoring; | 676 | bool is_monitoring; |
677 | bool need_an_top2_fixup; | 677 | bool need_an_top2_fixup; |
678 | u16 tx_trig_level; | 678 | u16 tx_trig_level; |
@@ -874,6 +874,7 @@ struct ath_bus_ops { | |||
874 | bool (*eeprom_read)(struct ath_common *common, u32 off, u16 *data); | 874 | bool (*eeprom_read)(struct ath_common *common, u32 off, u16 *data); |
875 | void (*bt_coex_prep)(struct ath_common *common); | 875 | void (*bt_coex_prep)(struct ath_common *common); |
876 | void (*extn_synch_en)(struct ath_common *common); | 876 | void (*extn_synch_en)(struct ath_common *common); |
877 | void (*aspm_init)(struct ath_common *common); | ||
877 | }; | 878 | }; |
878 | 879 | ||
879 | static inline struct ath_common *ath9k_hw_common(struct ath_hw *ah) | 880 | static inline struct ath_common *ath9k_hw_common(struct ath_hw *ah) |
diff --git a/drivers/net/wireless/ath/ath9k/pci.c b/drivers/net/wireless/ath/ath9k/pci.c index 3bad0b2cf9a3..be4ea1329813 100644 --- a/drivers/net/wireless/ath/ath9k/pci.c +++ b/drivers/net/wireless/ath/ath9k/pci.c | |||
@@ -16,6 +16,7 @@ | |||
16 | 16 | ||
17 | #include <linux/nl80211.h> | 17 | #include <linux/nl80211.h> |
18 | #include <linux/pci.h> | 18 | #include <linux/pci.h> |
19 | #include <linux/pci-aspm.h> | ||
19 | #include <linux/ath9k_platform.h> | 20 | #include <linux/ath9k_platform.h> |
20 | #include "ath9k.h" | 21 | #include "ath9k.h" |
21 | 22 | ||
@@ -115,12 +116,38 @@ static void ath_pci_extn_synch_enable(struct ath_common *common) | |||
115 | pci_write_config_byte(pdev, sc->sc_ah->caps.pcie_lcr_offset, lnkctl); | 116 | pci_write_config_byte(pdev, sc->sc_ah->caps.pcie_lcr_offset, lnkctl); |
116 | } | 117 | } |
117 | 118 | ||
119 | static void ath_pci_aspm_init(struct ath_common *common) | ||
120 | { | ||
121 | struct ath_softc *sc = (struct ath_softc *) common->priv; | ||
122 | struct ath_hw *ah = sc->sc_ah; | ||
123 | struct pci_dev *pdev = to_pci_dev(sc->dev); | ||
124 | struct pci_dev *parent; | ||
125 | int pos; | ||
126 | u8 aspm; | ||
127 | |||
128 | if (!pci_is_pcie(pdev)) | ||
129 | return; | ||
130 | |||
131 | parent = pdev->bus->self; | ||
132 | if (WARN_ON(!parent)) | ||
133 | return; | ||
134 | |||
135 | pos = pci_pcie_cap(parent); | ||
136 | pci_read_config_byte(parent, pos + PCI_EXP_LNKCTL, &aspm); | ||
137 | if (aspm & (PCIE_LINK_STATE_L0S | PCIE_LINK_STATE_L1)) { | ||
138 | ah->aspm_enabled = true; | ||
139 | /* Initialize PCIe PM and SERDES registers. */ | ||
140 | ath9k_hw_configpcipowersave(ah, 0, 0); | ||
141 | } | ||
142 | } | ||
143 | |||
118 | static const struct ath_bus_ops ath_pci_bus_ops = { | 144 | static const struct ath_bus_ops ath_pci_bus_ops = { |
119 | .ath_bus_type = ATH_PCI, | 145 | .ath_bus_type = ATH_PCI, |
120 | .read_cachesize = ath_pci_read_cachesize, | 146 | .read_cachesize = ath_pci_read_cachesize, |
121 | .eeprom_read = ath_pci_eeprom_read, | 147 | .eeprom_read = ath_pci_eeprom_read, |
122 | .bt_coex_prep = ath_pci_bt_coex_prep, | 148 | .bt_coex_prep = ath_pci_bt_coex_prep, |
123 | .extn_synch_en = ath_pci_extn_synch_enable, | 149 | .extn_synch_en = ath_pci_extn_synch_enable, |
150 | .aspm_init = ath_pci_aspm_init, | ||
124 | }; | 151 | }; |
125 | 152 | ||
126 | static int ath_pci_probe(struct pci_dev *pdev, const struct pci_device_id *id) | 153 | static int ath_pci_probe(struct pci_dev *pdev, const struct pci_device_id *id) |