On Friday 05 October 2012 15:24:25 Felix Fietkau wrote: > On 2012-10-05 3:07 PM, Sven Eckelmann wrote: > > On Friday 05 October 2012 14:34:28 Felix Fietkau wrote: > >> On 2012-10-05 1:08 PM, Sven Eckelmann wrote: > > [...] > > > >> Please try this patch to see if it gets rid of these interrupts: > >> --- > >> --- a/drivers/net/wireless/ath/ath9k/ani.c > >> +++ b/drivers/net/wireless/ath/ath9k/ani.c > >> @@ -307,7 +307,8 @@ void ath9k_ani_reset(struct ath_hw *ah, > >> > >> if (IS_CHAN_2GHZ(chan)) { > >> > >> ah->ani_function = (ATH9K_ANI_SPUR_IMMUNITY_LEVEL | > >> > >> ATH9K_ANI_FIRSTEP_LEVEL); > >> > >> - if (AR_SREV_9300_20_OR_LATER(ah)) > >> + if (AR_SREV_9300_20_OR_LATER(ah) && > >> + ah->caps.rx_chainmask != 1) > >> > >> ah->ani_function |= ATH9K_ANI_MRC_CCK; > >> > >> } else > >> > >> ah->ani_function = 0; > > > > Looks partially good. At least this patch fixed parts my friday :D > > > > I have more similar bugs, but at least this one is related to a bandwidth > > problem which I also wanted to check today. But it didn't fix _this_ > > invalid register access on the client device (but I don't see it anymore > > on the AP device). > > Are you sure that it's still the same register access on the client > side? I don't see how it could still access MRC related registers with > this part masked out. Yes, I am sure. Let's read some code: if (ah->opmode == NL80211_IFTYPE_AP) { if (IS_CHAN_2GHZ(chan)) { ah->ani_function = (ATH9K_ANI_SPUR_IMMUNITY_LEVEL | ATH9K_ANI_FIRSTEP_LEVEL); if (AR_SREV_9300_20_OR_LATER(ah) && ah->caps.rx_chainmask != 1) ah->ani_function |= ATH9K_ANI_MRC_CCK; } else ah->ani_function = 0; } Now raise your hands when you see the "ah->opmode == NL80211_IFTYPE_AP". I've just added following after this block if (!AR_SREV_9300_20_OR_LATER(ah) || ah->caps.rx_chainmask == 1) ah->ani_function &= ~ATH9K_ANI_MRC_CCK; But maybe it is better to fix the test in __ath9k_hw_init if (!AR_SREV_9300_20_OR_LATER(ah) || ah->caps.rx_chainmask == 1) ah->ani_function &= ~ATH9K_ANI_MRC_CCK; The problem in __ath9k_hw_init is the value of ah->caps.rx_chainmask ... which is not yet initialized correctly (and therefore ends up as 0). I've attached my "please don't enable MRC CCK" version of the patch. Feel free to submit it because you've submitted the initial version... or other things with it ;) And thanks a lot for the help. > Maybe it would make sense to come up with a debugging patch that checks > the IRQ status register on every register access to see if an error was > reported by the last one, and if there is an error, throw a stack trace. Already done that. But got not enough useful information from this spam of half backed stackdumps. But storing the value of the sync_cause register helped a lot. Kind regards, Sven
--- a/drivers/net/wireless/ath/ath9k/ani.c +++ b/drivers/net/wireless/ath/ath9k/ani.c @@ -307,12 +307,16 @@ void ath9k_ani_reset(struct ath_hw *ah, if (IS_CHAN_2GHZ(chan)) { ah->ani_function = (ATH9K_ANI_SPUR_IMMUNITY_LEVEL | ATH9K_ANI_FIRSTEP_LEVEL); - if (AR_SREV_9300_20_OR_LATER(ah)) + if (AR_SREV_9300_20_OR_LATER(ah) && + ah->caps.rx_chainmask != 1) ah->ani_function |= ATH9K_ANI_MRC_CCK; } else ah->ani_function = 0; } + if (!AR_SREV_9300_20_OR_LATER(ah) || ah->caps.rx_chainmask == 1) + ah->ani_function &= ~ATH9K_ANI_MRC_CCK; + /* always allow mode (on/off) to be controlled */ ah->ani_function |= ATH9K_ANI_MODE; --- a/drivers/net/wireless/ath/ath9k/hw.c +++ b/drivers/net/wireless/ath/ath9k/hw.c @@ -674,7 +674,7 @@ static int __ath9k_hw_init(struct ath_hw ah->ani_function = ATH9K_ANI_ALL; if (AR_SREV_9280_20_OR_LATER(ah) && !AR_SREV_9300_20_OR_LATER(ah)) ah->ani_function &= ~ATH9K_ANI_NOISE_IMMUNITY_LEVEL; - if (!AR_SREV_9300_20_OR_LATER(ah)) + if (!AR_SREV_9300_20_OR_LATER(ah) || ah->caps.rx_chainmask == 1) ah->ani_function &= ~ATH9K_ANI_MRC_CCK; ath9k_hw_init_mode_regs(ah);
Attachment:
signature.asc
Description: This is a digitally signed message part.