diff options
Diffstat (limited to 'drivers/net/wireless/iwlwifi/iwl-agn.c')
-rw-r--r-- | drivers/net/wireless/iwlwifi/iwl-agn.c | 70 |
1 files changed, 25 insertions, 45 deletions
diff --git a/drivers/net/wireless/iwlwifi/iwl-agn.c b/drivers/net/wireless/iwlwifi/iwl-agn.c index fe9307424a91..2cac09405afe 100644 --- a/drivers/net/wireless/iwlwifi/iwl-agn.c +++ b/drivers/net/wireless/iwlwifi/iwl-agn.c | |||
@@ -636,23 +636,22 @@ static void iwl_activate_qos(struct iwl_priv *priv, u8 force) | |||
636 | 636 | ||
637 | #define MAX_UCODE_BEACON_INTERVAL 4096 | 637 | #define MAX_UCODE_BEACON_INTERVAL 4096 |
638 | 638 | ||
639 | static __le16 iwl4965_adjust_beacon_interval(u16 beacon_val) | 639 | static u16 iwl_adjust_beacon_interval(u16 beacon_val) |
640 | { | 640 | { |
641 | u16 new_val = 0; | 641 | u16 new_val = 0; |
642 | u16 beacon_factor = 0; | 642 | u16 beacon_factor = 0; |
643 | 643 | ||
644 | beacon_factor = | 644 | beacon_factor = (beacon_val + MAX_UCODE_BEACON_INTERVAL) |
645 | (beacon_val + MAX_UCODE_BEACON_INTERVAL) | 645 | / MAX_UCODE_BEACON_INTERVAL; |
646 | / MAX_UCODE_BEACON_INTERVAL; | ||
647 | new_val = beacon_val / beacon_factor; | 646 | new_val = beacon_val / beacon_factor; |
648 | 647 | ||
649 | return cpu_to_le16(new_val); | 648 | return new_val; |
650 | } | 649 | } |
651 | 650 | ||
652 | static void iwl4965_setup_rxon_timing(struct iwl_priv *priv) | 651 | static void iwl_setup_rxon_timing(struct iwl_priv *priv) |
653 | { | 652 | { |
654 | u64 interval_tm_unit; | 653 | u64 tsf; |
655 | u64 tsf, result; | 654 | s32 interval_tm, rem; |
656 | unsigned long flags; | 655 | unsigned long flags; |
657 | struct ieee80211_conf *conf = NULL; | 656 | struct ieee80211_conf *conf = NULL; |
658 | u16 beacon_int = 0; | 657 | u16 beacon_int = 0; |
@@ -660,49 +659,32 @@ static void iwl4965_setup_rxon_timing(struct iwl_priv *priv) | |||
660 | conf = ieee80211_get_hw_conf(priv->hw); | 659 | conf = ieee80211_get_hw_conf(priv->hw); |
661 | 660 | ||
662 | spin_lock_irqsave(&priv->lock, flags); | 661 | spin_lock_irqsave(&priv->lock, flags); |
663 | priv->rxon_timing.timestamp.dw[1] = cpu_to_le32(priv->timestamp >> 32); | 662 | priv->rxon_timing.timestamp = cpu_to_le64(priv->timestamp); |
664 | priv->rxon_timing.timestamp.dw[0] = | ||
665 | cpu_to_le32(priv->timestamp & 0xFFFFFFFF); | ||
666 | |||
667 | priv->rxon_timing.listen_interval = cpu_to_le16(conf->listen_interval); | 663 | priv->rxon_timing.listen_interval = cpu_to_le16(conf->listen_interval); |
668 | 664 | ||
669 | tsf = priv->timestamp; | ||
670 | |||
671 | beacon_int = priv->beacon_int; | ||
672 | spin_unlock_irqrestore(&priv->lock, flags); | ||
673 | |||
674 | if (priv->iw_mode == NL80211_IFTYPE_STATION) { | 665 | if (priv->iw_mode == NL80211_IFTYPE_STATION) { |
675 | if (beacon_int == 0) { | 666 | beacon_int = iwl_adjust_beacon_interval(priv->beacon_int); |
676 | priv->rxon_timing.beacon_interval = cpu_to_le16(100); | ||
677 | priv->rxon_timing.beacon_init_val = cpu_to_le32(102400); | ||
678 | } else { | ||
679 | priv->rxon_timing.beacon_interval = | ||
680 | cpu_to_le16(beacon_int); | ||
681 | priv->rxon_timing.beacon_interval = | ||
682 | iwl4965_adjust_beacon_interval( | ||
683 | le16_to_cpu(priv->rxon_timing.beacon_interval)); | ||
684 | } | ||
685 | |||
686 | priv->rxon_timing.atim_window = 0; | 667 | priv->rxon_timing.atim_window = 0; |
687 | } else { | 668 | } else { |
688 | priv->rxon_timing.beacon_interval = | 669 | beacon_int = iwl_adjust_beacon_interval(conf->beacon_int); |
689 | iwl4965_adjust_beacon_interval(conf->beacon_int); | 670 | |
690 | /* TODO: we need to get atim_window from upper stack | 671 | /* TODO: we need to get atim_window from upper stack |
691 | * for now we set to 0 */ | 672 | * for now we set to 0 */ |
692 | priv->rxon_timing.atim_window = 0; | 673 | priv->rxon_timing.atim_window = 0; |
693 | } | 674 | } |
694 | 675 | ||
695 | interval_tm_unit = | 676 | priv->rxon_timing.beacon_interval = cpu_to_le16(beacon_int); |
696 | (le16_to_cpu(priv->rxon_timing.beacon_interval) * 1024); | ||
697 | result = do_div(tsf, interval_tm_unit); | ||
698 | priv->rxon_timing.beacon_init_val = | ||
699 | cpu_to_le32((u32) ((u64) interval_tm_unit - result)); | ||
700 | 677 | ||
701 | IWL_DEBUG_ASSOC | 678 | tsf = priv->timestamp; /* tsf is modifed by do_div: copy it */ |
702 | ("beacon interval %d beacon timer %d beacon tim %d\n", | 679 | interval_tm = beacon_int * 1024; |
703 | le16_to_cpu(priv->rxon_timing.beacon_interval), | 680 | rem = do_div(tsf, interval_tm); |
704 | le32_to_cpu(priv->rxon_timing.beacon_init_val), | 681 | priv->rxon_timing.beacon_init_val = cpu_to_le32(interval_tm - rem); |
705 | le16_to_cpu(priv->rxon_timing.atim_window)); | 682 | |
683 | spin_unlock_irqrestore(&priv->lock, flags); | ||
684 | IWL_DEBUG_ASSOC("beacon interval %d beacon timer %d beacon tim %d\n", | ||
685 | le16_to_cpu(priv->rxon_timing.beacon_interval), | ||
686 | le32_to_cpu(priv->rxon_timing.beacon_init_val), | ||
687 | le16_to_cpu(priv->rxon_timing.atim_window)); | ||
706 | } | 688 | } |
707 | 689 | ||
708 | static void iwl_set_flags_for_band(struct iwl_priv *priv, | 690 | static void iwl_set_flags_for_band(struct iwl_priv *priv, |
@@ -2488,8 +2470,7 @@ static void iwl4965_post_associate(struct iwl_priv *priv) | |||
2488 | priv->staging_rxon.filter_flags &= ~RXON_FILTER_ASSOC_MSK; | 2470 | priv->staging_rxon.filter_flags &= ~RXON_FILTER_ASSOC_MSK; |
2489 | iwl4965_commit_rxon(priv); | 2471 | iwl4965_commit_rxon(priv); |
2490 | 2472 | ||
2491 | memset(&priv->rxon_timing, 0, sizeof(struct iwl4965_rxon_time_cmd)); | 2473 | iwl_setup_rxon_timing(priv); |
2492 | iwl4965_setup_rxon_timing(priv); | ||
2493 | ret = iwl_send_cmd_pdu(priv, REPLY_RXON_TIMING, | 2474 | ret = iwl_send_cmd_pdu(priv, REPLY_RXON_TIMING, |
2494 | sizeof(priv->rxon_timing), &priv->rxon_timing); | 2475 | sizeof(priv->rxon_timing), &priv->rxon_timing); |
2495 | if (ret) | 2476 | if (ret) |
@@ -2879,15 +2860,14 @@ static void iwl4965_config_ap(struct iwl_priv *priv) | |||
2879 | return; | 2860 | return; |
2880 | 2861 | ||
2881 | /* The following should be done only at AP bring up */ | 2862 | /* The following should be done only at AP bring up */ |
2882 | if (!(iwl_is_associated(priv))) { | 2863 | if (!iwl_is_associated(priv)) { |
2883 | 2864 | ||
2884 | /* RXON - unassoc (to set timing command) */ | 2865 | /* RXON - unassoc (to set timing command) */ |
2885 | priv->staging_rxon.filter_flags &= ~RXON_FILTER_ASSOC_MSK; | 2866 | priv->staging_rxon.filter_flags &= ~RXON_FILTER_ASSOC_MSK; |
2886 | iwl4965_commit_rxon(priv); | 2867 | iwl4965_commit_rxon(priv); |
2887 | 2868 | ||
2888 | /* RXON Timing */ | 2869 | /* RXON Timing */ |
2889 | memset(&priv->rxon_timing, 0, sizeof(struct iwl4965_rxon_time_cmd)); | 2870 | iwl_setup_rxon_timing(priv); |
2890 | iwl4965_setup_rxon_timing(priv); | ||
2891 | ret = iwl_send_cmd_pdu(priv, REPLY_RXON_TIMING, | 2871 | ret = iwl_send_cmd_pdu(priv, REPLY_RXON_TIMING, |
2892 | sizeof(priv->rxon_timing), &priv->rxon_timing); | 2872 | sizeof(priv->rxon_timing), &priv->rxon_timing); |
2893 | if (ret) | 2873 | if (ret) |