diff options
author | David S. Miller <davem@davemloft.net> | 2008-06-14 20:15:39 -0400 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2008-06-14 20:15:39 -0400 |
commit | 942e7b102a4827fdb69a39c7f07c544542589ef9 (patch) | |
tree | 4c47174c91eb76aaa31abc141adbee1acc649987 /net | |
parent | 7d06b2e053d2d536348e3a0f6bb02982a41bea37 (diff) | |
parent | 87291c0269e77b029282676448fed3706a54211a (diff) |
Merge branch 'master' of master.kernel.org:/pub/scm/linux/kernel/git/linville/wireless-next-2.6
Diffstat (limited to 'net')
-rw-r--r-- | net/mac80211/ieee80211_i.h | 2 | ||||
-rw-r--r-- | net/mac80211/main.c | 3 | ||||
-rw-r--r-- | net/mac80211/mlme.c | 17 | ||||
-rw-r--r-- | net/mac80211/rx.c | 29 | ||||
-rw-r--r-- | net/mac80211/tkip.c | 85 | ||||
-rw-r--r-- | net/mac80211/tkip.h | 4 | ||||
-rw-r--r-- | net/mac80211/tx.c | 8 | ||||
-rw-r--r-- | net/mac80211/util.c | 81 | ||||
-rw-r--r-- | net/mac80211/wme.c | 18 | ||||
-rw-r--r-- | net/mac80211/wpa.c | 71 | ||||
-rw-r--r-- | net/wireless/reg.c | 18 |
11 files changed, 174 insertions, 162 deletions
diff --git a/net/mac80211/ieee80211_i.h b/net/mac80211/ieee80211_i.h index b19bd16703b2..14fccf16b80f 100644 --- a/net/mac80211/ieee80211_i.h +++ b/net/mac80211/ieee80211_i.h | |||
@@ -876,7 +876,7 @@ void ieee80211_rx_bss_list_deinit(struct net_device *dev); | |||
876 | int ieee80211_sta_set_extra_ie(struct net_device *dev, char *ie, size_t len); | 876 | int ieee80211_sta_set_extra_ie(struct net_device *dev, char *ie, size_t len); |
877 | struct sta_info *ieee80211_ibss_add_sta(struct net_device *dev, | 877 | struct sta_info *ieee80211_ibss_add_sta(struct net_device *dev, |
878 | struct sk_buff *skb, u8 *bssid, | 878 | struct sk_buff *skb, u8 *bssid, |
879 | u8 *addr); | 879 | u8 *addr, u64 supp_rates); |
880 | int ieee80211_sta_deauthenticate(struct net_device *dev, u16 reason); | 880 | int ieee80211_sta_deauthenticate(struct net_device *dev, u16 reason); |
881 | int ieee80211_sta_disassociate(struct net_device *dev, u16 reason); | 881 | int ieee80211_sta_disassociate(struct net_device *dev, u16 reason); |
882 | void ieee80211_bss_info_change_notify(struct ieee80211_sub_if_data *sdata, | 882 | void ieee80211_bss_info_change_notify(struct ieee80211_sub_if_data *sdata, |
diff --git a/net/mac80211/main.c b/net/mac80211/main.c index b182f018a187..5c5396edad32 100644 --- a/net/mac80211/main.c +++ b/net/mac80211/main.c | |||
@@ -1707,7 +1707,8 @@ int ieee80211_register_hw(struct ieee80211_hw *hw) | |||
1707 | 1707 | ||
1708 | debugfs_hw_add(local); | 1708 | debugfs_hw_add(local); |
1709 | 1709 | ||
1710 | local->hw.conf.beacon_int = 1000; | 1710 | if (local->hw.conf.beacon_int < 10) |
1711 | local->hw.conf.beacon_int = 100; | ||
1711 | 1712 | ||
1712 | local->wstats_flags |= local->hw.flags & (IEEE80211_HW_SIGNAL_UNSPEC | | 1713 | local->wstats_flags |= local->hw.flags & (IEEE80211_HW_SIGNAL_UNSPEC | |
1713 | IEEE80211_HW_SIGNAL_DB | | 1714 | IEEE80211_HW_SIGNAL_DB | |
diff --git a/net/mac80211/mlme.c b/net/mac80211/mlme.c index 7f05820dc629..55659a730dc1 100644 --- a/net/mac80211/mlme.c +++ b/net/mac80211/mlme.c | |||
@@ -2863,7 +2863,8 @@ static void ieee80211_rx_bss_info(struct net_device *dev, | |||
2863 | dev->name, print_mac(mac, mgmt->bssid)); | 2863 | dev->name, print_mac(mac, mgmt->bssid)); |
2864 | ieee80211_sta_join_ibss(dev, &sdata->u.sta, bss); | 2864 | ieee80211_sta_join_ibss(dev, &sdata->u.sta, bss); |
2865 | ieee80211_ibss_add_sta(dev, NULL, | 2865 | ieee80211_ibss_add_sta(dev, NULL, |
2866 | mgmt->bssid, mgmt->sa); | 2866 | mgmt->bssid, mgmt->sa, |
2867 | BIT(rx_status->rate_idx)); | ||
2867 | } | 2868 | } |
2868 | } | 2869 | } |
2869 | 2870 | ||
@@ -3583,7 +3584,7 @@ static int ieee80211_sta_create_ibss(struct net_device *dev, | |||
3583 | sband = local->hw.wiphy->bands[bss->band]; | 3584 | sband = local->hw.wiphy->bands[bss->band]; |
3584 | 3585 | ||
3585 | if (local->hw.conf.beacon_int == 0) | 3586 | if (local->hw.conf.beacon_int == 0) |
3586 | local->hw.conf.beacon_int = 10000; | 3587 | local->hw.conf.beacon_int = 100; |
3587 | bss->beacon_int = local->hw.conf.beacon_int; | 3588 | bss->beacon_int = local->hw.conf.beacon_int; |
3588 | bss->last_update = jiffies; | 3589 | bss->last_update = jiffies; |
3589 | bss->capability = WLAN_CAPABILITY_IBSS; | 3590 | bss->capability = WLAN_CAPABILITY_IBSS; |
@@ -4307,12 +4308,13 @@ int ieee80211_sta_set_extra_ie(struct net_device *dev, char *ie, size_t len) | |||
4307 | 4308 | ||
4308 | struct sta_info *ieee80211_ibss_add_sta(struct net_device *dev, | 4309 | struct sta_info *ieee80211_ibss_add_sta(struct net_device *dev, |
4309 | struct sk_buff *skb, u8 *bssid, | 4310 | struct sk_buff *skb, u8 *bssid, |
4310 | u8 *addr) | 4311 | u8 *addr, u64 supp_rates) |
4311 | { | 4312 | { |
4312 | struct ieee80211_local *local = wdev_priv(dev->ieee80211_ptr); | 4313 | struct ieee80211_local *local = wdev_priv(dev->ieee80211_ptr); |
4313 | struct sta_info *sta; | 4314 | struct sta_info *sta; |
4314 | struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev); | 4315 | struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev); |
4315 | DECLARE_MAC_BUF(mac); | 4316 | DECLARE_MAC_BUF(mac); |
4317 | int band = local->hw.conf.channel->band; | ||
4316 | 4318 | ||
4317 | /* TODO: Could consider removing the least recently used entry and | 4319 | /* TODO: Could consider removing the least recently used entry and |
4318 | * allow new one to be added. */ | 4320 | * allow new one to be added. */ |
@@ -4324,6 +4326,9 @@ struct sta_info *ieee80211_ibss_add_sta(struct net_device *dev, | |||
4324 | return NULL; | 4326 | return NULL; |
4325 | } | 4327 | } |
4326 | 4328 | ||
4329 | if (!ieee80211_bssid_match(bssid, sdata->u.sta.bssid)) | ||
4330 | return NULL; | ||
4331 | |||
4327 | printk(KERN_DEBUG "%s: Adding new IBSS station %s (dev=%s)\n", | 4332 | printk(KERN_DEBUG "%s: Adding new IBSS station %s (dev=%s)\n", |
4328 | wiphy_name(local->hw.wiphy), print_mac(mac, addr), dev->name); | 4333 | wiphy_name(local->hw.wiphy), print_mac(mac, addr), dev->name); |
4329 | 4334 | ||
@@ -4333,8 +4338,10 @@ struct sta_info *ieee80211_ibss_add_sta(struct net_device *dev, | |||
4333 | 4338 | ||
4334 | set_sta_flags(sta, WLAN_STA_AUTHORIZED); | 4339 | set_sta_flags(sta, WLAN_STA_AUTHORIZED); |
4335 | 4340 | ||
4336 | sta->supp_rates[local->hw.conf.channel->band] = | 4341 | if (supp_rates) |
4337 | sdata->u.sta.supp_rates_bits[local->hw.conf.channel->band]; | 4342 | sta->supp_rates[band] = supp_rates; |
4343 | else | ||
4344 | sta->supp_rates[band] = sdata->u.sta.supp_rates_bits[band]; | ||
4338 | 4345 | ||
4339 | rate_control_rate_init(sta, local); | 4346 | rate_control_rate_init(sta, local); |
4340 | 4347 | ||
diff --git a/net/mac80211/rx.c b/net/mac80211/rx.c index a3643fd86af9..c32a0bcd53b7 100644 --- a/net/mac80211/rx.c +++ b/net/mac80211/rx.c | |||
@@ -67,12 +67,9 @@ static inline int should_drop_frame(struct ieee80211_rx_status *status, | |||
67 | return 1; | 67 | return 1; |
68 | if (unlikely(skb->len < 16 + present_fcs_len + radiotap_len)) | 68 | if (unlikely(skb->len < 16 + present_fcs_len + radiotap_len)) |
69 | return 1; | 69 | return 1; |
70 | if (((hdr->frame_control & cpu_to_le16(IEEE80211_FCTL_FTYPE)) == | 70 | if (ieee80211_is_ctl(hdr->frame_control) && |
71 | cpu_to_le16(IEEE80211_FTYPE_CTL)) && | 71 | !ieee80211_is_pspoll(hdr->frame_control) && |
72 | ((hdr->frame_control & cpu_to_le16(IEEE80211_FCTL_STYPE)) != | 72 | !ieee80211_is_back_req(hdr->frame_control)) |
73 | cpu_to_le16(IEEE80211_STYPE_PSPOLL)) && | ||
74 | ((hdr->frame_control & cpu_to_le16(IEEE80211_FCTL_STYPE)) != | ||
75 | cpu_to_le16(IEEE80211_STYPE_BACK_REQ))) | ||
76 | return 1; | 73 | return 1; |
77 | return 0; | 74 | return 0; |
78 | } | 75 | } |
@@ -1826,8 +1823,13 @@ static int prepare_for_handlers(struct ieee80211_sub_if_data *sdata, | |||
1826 | if (!bssid) | 1823 | if (!bssid) |
1827 | return 0; | 1824 | return 0; |
1828 | if ((rx->fc & IEEE80211_FCTL_FTYPE) == IEEE80211_FTYPE_MGMT && | 1825 | if ((rx->fc & IEEE80211_FCTL_FTYPE) == IEEE80211_FTYPE_MGMT && |
1829 | (rx->fc & IEEE80211_FCTL_STYPE) == IEEE80211_STYPE_BEACON) | 1826 | (rx->fc & IEEE80211_FCTL_STYPE) == IEEE80211_STYPE_BEACON) { |
1827 | if (!rx->sta) | ||
1828 | rx->sta = ieee80211_ibss_add_sta(sdata->dev, | ||
1829 | rx->skb, bssid, hdr->addr2, | ||
1830 | BIT(rx->status->rate_idx)); | ||
1830 | return 1; | 1831 | return 1; |
1832 | } | ||
1831 | else if (!ieee80211_bssid_match(bssid, sdata->u.sta.bssid)) { | 1833 | else if (!ieee80211_bssid_match(bssid, sdata->u.sta.bssid)) { |
1832 | if (!(rx->flags & IEEE80211_RX_IN_SCAN)) | 1834 | if (!(rx->flags & IEEE80211_RX_IN_SCAN)) |
1833 | return 0; | 1835 | return 0; |
@@ -1840,7 +1842,8 @@ static int prepare_for_handlers(struct ieee80211_sub_if_data *sdata, | |||
1840 | rx->flags &= ~IEEE80211_RX_RA_MATCH; | 1842 | rx->flags &= ~IEEE80211_RX_RA_MATCH; |
1841 | } else if (!rx->sta) | 1843 | } else if (!rx->sta) |
1842 | rx->sta = ieee80211_ibss_add_sta(sdata->dev, rx->skb, | 1844 | rx->sta = ieee80211_ibss_add_sta(sdata->dev, rx->skb, |
1843 | bssid, hdr->addr2); | 1845 | bssid, hdr->addr2, |
1846 | BIT(rx->status->rate_idx)); | ||
1844 | break; | 1847 | break; |
1845 | case IEEE80211_IF_TYPE_MESH_POINT: | 1848 | case IEEE80211_IF_TYPE_MESH_POINT: |
1846 | if (!multicast && | 1849 | if (!multicast && |
@@ -2118,7 +2121,7 @@ static u8 ieee80211_rx_reorder_ampdu(struct ieee80211_local *local, | |||
2118 | struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) skb->data; | 2121 | struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) skb->data; |
2119 | struct sta_info *sta; | 2122 | struct sta_info *sta; |
2120 | struct tid_ampdu_rx *tid_agg_rx; | 2123 | struct tid_ampdu_rx *tid_agg_rx; |
2121 | u16 fc, sc; | 2124 | u16 sc; |
2122 | u16 mpdu_seq_num; | 2125 | u16 mpdu_seq_num; |
2123 | u8 ret = 0, *qc; | 2126 | u8 ret = 0, *qc; |
2124 | int tid; | 2127 | int tid; |
@@ -2127,14 +2130,12 @@ static u8 ieee80211_rx_reorder_ampdu(struct ieee80211_local *local, | |||
2127 | if (!sta) | 2130 | if (!sta) |
2128 | return ret; | 2131 | return ret; |
2129 | 2132 | ||
2130 | fc = le16_to_cpu(hdr->frame_control); | ||
2131 | |||
2132 | /* filter the QoS data rx stream according to | 2133 | /* filter the QoS data rx stream according to |
2133 | * STA/TID and check if this STA/TID is on aggregation */ | 2134 | * STA/TID and check if this STA/TID is on aggregation */ |
2134 | if (!WLAN_FC_IS_QOS_DATA(fc)) | 2135 | if (!ieee80211_is_data_qos(hdr->frame_control)) |
2135 | goto end_reorder; | 2136 | goto end_reorder; |
2136 | 2137 | ||
2137 | qc = skb->data + ieee80211_get_hdrlen(fc) - QOS_CONTROL_LEN; | 2138 | qc = ieee80211_get_qos_ctl(hdr); |
2138 | tid = qc[0] & QOS_CONTROL_TID_MASK; | 2139 | tid = qc[0] & QOS_CONTROL_TID_MASK; |
2139 | 2140 | ||
2140 | if (sta->ampdu_mlme.tid_state_rx[tid] != HT_AGG_STATE_OPERATIONAL) | 2141 | if (sta->ampdu_mlme.tid_state_rx[tid] != HT_AGG_STATE_OPERATIONAL) |
@@ -2143,7 +2144,7 @@ static u8 ieee80211_rx_reorder_ampdu(struct ieee80211_local *local, | |||
2143 | tid_agg_rx = sta->ampdu_mlme.tid_rx[tid]; | 2144 | tid_agg_rx = sta->ampdu_mlme.tid_rx[tid]; |
2144 | 2145 | ||
2145 | /* null data frames are excluded */ | 2146 | /* null data frames are excluded */ |
2146 | if (unlikely(fc & IEEE80211_STYPE_NULLFUNC)) | 2147 | if (unlikely(ieee80211_is_nullfunc(hdr->frame_control))) |
2147 | goto end_reorder; | 2148 | goto end_reorder; |
2148 | 2149 | ||
2149 | /* new un-ordered ampdu frame - process it */ | 2150 | /* new un-ordered ampdu frame - process it */ |
diff --git a/net/mac80211/tkip.c b/net/mac80211/tkip.c index a00cf1ea7719..e710243d82e2 100644 --- a/net/mac80211/tkip.c +++ b/net/mac80211/tkip.c | |||
@@ -64,6 +64,14 @@ static u16 tkipS(u16 val) | |||
64 | return tkip_sbox[val & 0xff] ^ swab16(tkip_sbox[val >> 8]); | 64 | return tkip_sbox[val & 0xff] ^ swab16(tkip_sbox[val >> 8]); |
65 | } | 65 | } |
66 | 66 | ||
67 | static u8 *write_tkip_iv(u8 *pos, u16 iv16) | ||
68 | { | ||
69 | *pos++ = iv16 >> 8; | ||
70 | *pos++ = ((iv16 >> 8) | 0x20) & 0x7f; | ||
71 | *pos++ = iv16 & 0xFF; | ||
72 | return pos; | ||
73 | } | ||
74 | |||
67 | /* | 75 | /* |
68 | * P1K := Phase1(TA, TK, TSC) | 76 | * P1K := Phase1(TA, TK, TSC) |
69 | * TA = transmitter address (48 bits) | 77 | * TA = transmitter address (48 bits) |
@@ -71,11 +79,10 @@ static u16 tkipS(u16 val) | |||
71 | * TSC = TKIP sequence counter (48 bits, only 32 msb bits used) | 79 | * TSC = TKIP sequence counter (48 bits, only 32 msb bits used) |
72 | * P1K: 80 bits | 80 | * P1K: 80 bits |
73 | */ | 81 | */ |
74 | static void tkip_mixing_phase1(struct ieee80211_key *key, const u8 *ta, | 82 | static void tkip_mixing_phase1(const u8 *tk, struct tkip_ctx *ctx, |
75 | struct tkip_ctx *ctx, u32 tsc_IV32) | 83 | const u8 *ta, u32 tsc_IV32) |
76 | { | 84 | { |
77 | int i, j; | 85 | int i, j; |
78 | const u8 *tk = &key->conf.key[ALG_TKIP_TEMP_ENCR_KEY]; | ||
79 | u16 *p1k = ctx->p1k; | 86 | u16 *p1k = ctx->p1k; |
80 | 87 | ||
81 | p1k[0] = tsc_IV32 & 0xFFFF; | 88 | p1k[0] = tsc_IV32 & 0xFFFF; |
@@ -95,12 +102,11 @@ static void tkip_mixing_phase1(struct ieee80211_key *key, const u8 *ta, | |||
95 | ctx->initialized = 1; | 102 | ctx->initialized = 1; |
96 | } | 103 | } |
97 | 104 | ||
98 | static void tkip_mixing_phase2(struct ieee80211_key *key, struct tkip_ctx *ctx, | 105 | static void tkip_mixing_phase2(const u8 *tk, struct tkip_ctx *ctx, |
99 | u16 tsc_IV16, u8 *rc4key) | 106 | u16 tsc_IV16, u8 *rc4key) |
100 | { | 107 | { |
101 | u16 ppk[6]; | 108 | u16 ppk[6]; |
102 | const u16 *p1k = ctx->p1k; | 109 | const u16 *p1k = ctx->p1k; |
103 | const u8 *tk = &key->conf.key[ALG_TKIP_TEMP_ENCR_KEY]; | ||
104 | int i; | 110 | int i; |
105 | 111 | ||
106 | ppk[0] = p1k[0]; | 112 | ppk[0] = p1k[0]; |
@@ -123,12 +129,9 @@ static void tkip_mixing_phase2(struct ieee80211_key *key, struct tkip_ctx *ctx, | |||
123 | ppk[4] += ror16(ppk[3], 1); | 129 | ppk[4] += ror16(ppk[3], 1); |
124 | ppk[5] += ror16(ppk[4], 1); | 130 | ppk[5] += ror16(ppk[4], 1); |
125 | 131 | ||
126 | rc4key[0] = tsc_IV16 >> 8; | 132 | rc4key = write_tkip_iv(rc4key, tsc_IV16); |
127 | rc4key[1] = ((tsc_IV16 >> 8) | 0x20) & 0x7f; | 133 | *rc4key++ = ((ppk[5] ^ get_unaligned_le16(tk)) >> 1) & 0xFF; |
128 | rc4key[2] = tsc_IV16 & 0xFF; | ||
129 | rc4key[3] = ((ppk[5] ^ get_unaligned_le16(tk)) >> 1) & 0xFF; | ||
130 | 134 | ||
131 | rc4key += 4; | ||
132 | for (i = 0; i < 6; i++) | 135 | for (i = 0; i < 6; i++) |
133 | put_unaligned_le16(ppk[i], rc4key + 2 * i); | 136 | put_unaligned_le16(ppk[i], rc4key + 2 * i); |
134 | } | 137 | } |
@@ -136,51 +139,41 @@ static void tkip_mixing_phase2(struct ieee80211_key *key, struct tkip_ctx *ctx, | |||
136 | /* Add TKIP IV and Ext. IV at @pos. @iv0, @iv1, and @iv2 are the first octets | 139 | /* Add TKIP IV and Ext. IV at @pos. @iv0, @iv1, and @iv2 are the first octets |
137 | * of the IV. Returns pointer to the octet following IVs (i.e., beginning of | 140 | * of the IV. Returns pointer to the octet following IVs (i.e., beginning of |
138 | * the packet payload). */ | 141 | * the packet payload). */ |
139 | u8 *ieee80211_tkip_add_iv(u8 *pos, struct ieee80211_key *key, | 142 | u8 *ieee80211_tkip_add_iv(u8 *pos, struct ieee80211_key *key, u16 iv16) |
140 | u8 iv0, u8 iv1, u8 iv2) | ||
141 | { | 143 | { |
142 | *pos++ = iv0; | 144 | pos = write_tkip_iv(pos, iv16); |
143 | *pos++ = iv1; | ||
144 | *pos++ = iv2; | ||
145 | *pos++ = (key->conf.keyidx << 6) | (1 << 5) /* Ext IV */; | 145 | *pos++ = (key->conf.keyidx << 6) | (1 << 5) /* Ext IV */; |
146 | put_unaligned_le32(key->u.tkip.tx.iv32, pos); | 146 | put_unaligned_le32(key->u.tkip.tx.iv32, pos); |
147 | return pos + 4; | 147 | return pos + 4; |
148 | } | 148 | } |
149 | 149 | ||
150 | static void ieee80211_tkip_gen_rc4key(struct ieee80211_key *key, u8 *ta, | ||
151 | u8 *rc4key) | ||
152 | { | ||
153 | /* Calculate per-packet key */ | ||
154 | if (key->u.tkip.tx.iv16 == 0 || !key->u.tkip.tx.initialized) | ||
155 | tkip_mixing_phase1(key, ta, &key->u.tkip.tx, key->u.tkip.tx.iv32); | ||
156 | |||
157 | tkip_mixing_phase2(key, &key->u.tkip.tx, key->u.tkip.tx.iv16, rc4key); | ||
158 | } | ||
159 | |||
160 | void ieee80211_get_tkip_key(struct ieee80211_key_conf *keyconf, | 150 | void ieee80211_get_tkip_key(struct ieee80211_key_conf *keyconf, |
161 | struct sk_buff *skb, enum ieee80211_tkip_key_type type, | 151 | struct sk_buff *skb, enum ieee80211_tkip_key_type type, |
162 | u8 *outkey) | 152 | u8 *outkey) |
163 | { | 153 | { |
164 | struct ieee80211_key *key = (struct ieee80211_key *) | 154 | struct ieee80211_key *key = (struct ieee80211_key *) |
165 | container_of(keyconf, struct ieee80211_key, conf); | 155 | container_of(keyconf, struct ieee80211_key, conf); |
166 | struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) skb->data; | 156 | struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)skb->data; |
167 | u8 *data = (u8 *) hdr; | 157 | u8 *data; |
168 | u16 fc = le16_to_cpu(hdr->frame_control); | 158 | const u8 *tk; |
169 | int hdr_len = ieee80211_get_hdrlen(fc); | 159 | struct tkip_ctx *ctx; |
170 | u8 *ta = hdr->addr2; | ||
171 | u16 iv16; | 160 | u16 iv16; |
172 | u32 iv32; | 161 | u32 iv32; |
173 | 162 | ||
174 | iv16 = data[hdr_len + 2] | (data[hdr_len] << 8); | 163 | data = (u8 *)hdr + ieee80211_hdrlen(hdr->frame_control); |
175 | iv32 = get_unaligned_le32(data + hdr_len + 4); | 164 | iv16 = data[2] | (data[0] << 8); |
165 | iv32 = get_unaligned_le32(&data[4]); | ||
166 | |||
167 | tk = &key->conf.key[ALG_TKIP_TEMP_ENCR_KEY]; | ||
168 | ctx = &key->u.tkip.tx; | ||
176 | 169 | ||
177 | #ifdef CONFIG_TKIP_DEBUG | 170 | #ifdef CONFIG_TKIP_DEBUG |
178 | printk(KERN_DEBUG "TKIP encrypt: iv16 = 0x%04x, iv32 = 0x%08x\n", | 171 | printk(KERN_DEBUG "TKIP encrypt: iv16 = 0x%04x, iv32 = 0x%08x\n", |
179 | iv16, iv32); | 172 | iv16, iv32); |
180 | 173 | ||
181 | if (iv32 != key->u.tkip.tx.iv32) { | 174 | if (iv32 != ctx->iv32) { |
182 | printk(KERN_DEBUG "skb: iv32 = 0x%08x key: iv32 = 0x%08x\n", | 175 | printk(KERN_DEBUG "skb: iv32 = 0x%08x key: iv32 = 0x%08x\n", |
183 | iv32, key->u.tkip.tx.iv32); | 176 | iv32, ctx->iv32); |
184 | printk(KERN_DEBUG "Wrap around of iv16 in the middle of a " | 177 | printk(KERN_DEBUG "Wrap around of iv16 in the middle of a " |
185 | "fragmented packet\n"); | 178 | "fragmented packet\n"); |
186 | } | 179 | } |
@@ -189,15 +182,15 @@ void ieee80211_get_tkip_key(struct ieee80211_key_conf *keyconf, | |||
189 | /* Update the p1k only when the iv16 in the packet wraps around, this | 182 | /* Update the p1k only when the iv16 in the packet wraps around, this |
190 | * might occur after the wrap around of iv16 in the key in case of | 183 | * might occur after the wrap around of iv16 in the key in case of |
191 | * fragmented packets. */ | 184 | * fragmented packets. */ |
192 | if (iv16 == 0 || !key->u.tkip.tx.initialized) | 185 | if (iv16 == 0 || !ctx->initialized) |
193 | tkip_mixing_phase1(key, ta, &key->u.tkip.tx, iv32); | 186 | tkip_mixing_phase1(tk, ctx, hdr->addr2, iv32); |
194 | 187 | ||
195 | if (type == IEEE80211_TKIP_P1_KEY) { | 188 | if (type == IEEE80211_TKIP_P1_KEY) { |
196 | memcpy(outkey, key->u.tkip.tx.p1k, sizeof(u16) * 5); | 189 | memcpy(outkey, ctx->p1k, sizeof(u16) * 5); |
197 | return; | 190 | return; |
198 | } | 191 | } |
199 | 192 | ||
200 | tkip_mixing_phase2(key, &key->u.tkip.tx, iv16, outkey); | 193 | tkip_mixing_phase2(tk, ctx, iv16, outkey); |
201 | } | 194 | } |
202 | EXPORT_SYMBOL(ieee80211_get_tkip_key); | 195 | EXPORT_SYMBOL(ieee80211_get_tkip_key); |
203 | 196 | ||
@@ -211,9 +204,16 @@ void ieee80211_tkip_encrypt_data(struct crypto_blkcipher *tfm, | |||
211 | u8 *pos, size_t payload_len, u8 *ta) | 204 | u8 *pos, size_t payload_len, u8 *ta) |
212 | { | 205 | { |
213 | u8 rc4key[16]; | 206 | u8 rc4key[16]; |
207 | struct tkip_ctx *ctx = &key->u.tkip.tx; | ||
208 | const u8 *tk = &key->conf.key[ALG_TKIP_TEMP_ENCR_KEY]; | ||
214 | 209 | ||
215 | ieee80211_tkip_gen_rc4key(key, ta, rc4key); | 210 | /* Calculate per-packet key */ |
216 | pos = ieee80211_tkip_add_iv(pos, key, rc4key[0], rc4key[1], rc4key[2]); | 211 | if (ctx->iv16 == 0 || !ctx->initialized) |
212 | tkip_mixing_phase1(tk, ctx, ta, ctx->iv32); | ||
213 | |||
214 | tkip_mixing_phase2(tk, ctx, ctx->iv16, rc4key); | ||
215 | |||
216 | pos = ieee80211_tkip_add_iv(pos, key, key->u.tkip.tx.iv16); | ||
217 | ieee80211_wep_encrypt_data(tfm, rc4key, 16, pos, payload_len); | 217 | ieee80211_wep_encrypt_data(tfm, rc4key, 16, pos, payload_len); |
218 | } | 218 | } |
219 | 219 | ||
@@ -231,6 +231,7 @@ int ieee80211_tkip_decrypt_data(struct crypto_blkcipher *tfm, | |||
231 | u32 iv16; | 231 | u32 iv16; |
232 | u8 rc4key[16], keyid, *pos = payload; | 232 | u8 rc4key[16], keyid, *pos = payload; |
233 | int res; | 233 | int res; |
234 | const u8 *tk = &key->conf.key[ALG_TKIP_TEMP_ENCR_KEY]; | ||
234 | 235 | ||
235 | if (payload_len < 12) | 236 | if (payload_len < 12) |
236 | return -1; | 237 | return -1; |
@@ -281,7 +282,7 @@ int ieee80211_tkip_decrypt_data(struct crypto_blkcipher *tfm, | |||
281 | if (!key->u.tkip.rx[queue].initialized || | 282 | if (!key->u.tkip.rx[queue].initialized || |
282 | key->u.tkip.rx[queue].iv32 != iv32) { | 283 | key->u.tkip.rx[queue].iv32 != iv32) { |
283 | /* IV16 wrapped around - perform TKIP phase 1 */ | 284 | /* IV16 wrapped around - perform TKIP phase 1 */ |
284 | tkip_mixing_phase1(key, ta, &key->u.tkip.rx[queue], iv32); | 285 | tkip_mixing_phase1(tk, &key->u.tkip.rx[queue], ta, iv32); |
285 | #ifdef CONFIG_TKIP_DEBUG | 286 | #ifdef CONFIG_TKIP_DEBUG |
286 | { | 287 | { |
287 | int i; | 288 | int i; |
@@ -314,7 +315,7 @@ int ieee80211_tkip_decrypt_data(struct crypto_blkcipher *tfm, | |||
314 | } | 315 | } |
315 | } | 316 | } |
316 | 317 | ||
317 | tkip_mixing_phase2(key, &key->u.tkip.rx[queue], iv16, rc4key); | 318 | tkip_mixing_phase2(tk, &key->u.tkip.rx[queue], iv16, rc4key); |
318 | #ifdef CONFIG_TKIP_DEBUG | 319 | #ifdef CONFIG_TKIP_DEBUG |
319 | { | 320 | { |
320 | int i; | 321 | int i; |
diff --git a/net/mac80211/tkip.h b/net/mac80211/tkip.h index b890427fc959..d4714383f5fc 100644 --- a/net/mac80211/tkip.h +++ b/net/mac80211/tkip.h | |||
@@ -13,8 +13,8 @@ | |||
13 | #include <linux/crypto.h> | 13 | #include <linux/crypto.h> |
14 | #include "key.h" | 14 | #include "key.h" |
15 | 15 | ||
16 | u8 *ieee80211_tkip_add_iv(u8 *pos, struct ieee80211_key *key, | 16 | u8 *ieee80211_tkip_add_iv(u8 *pos, struct ieee80211_key *key, u16 iv16); |
17 | u8 iv0, u8 iv1, u8 iv2); | 17 | |
18 | void ieee80211_tkip_encrypt_data(struct crypto_blkcipher *tfm, | 18 | void ieee80211_tkip_encrypt_data(struct crypto_blkcipher *tfm, |
19 | struct ieee80211_key *key, | 19 | struct ieee80211_key *key, |
20 | u8 *pos, size_t payload_len, u8 *ta); | 20 | u8 *pos, size_t payload_len, u8 *ta); |
diff --git a/net/mac80211/tx.c b/net/mac80211/tx.c index 1ad9e664f287..195cb6dd02a0 100644 --- a/net/mac80211/tx.c +++ b/net/mac80211/tx.c | |||
@@ -660,9 +660,8 @@ ieee80211_tx_h_fragment(struct ieee80211_tx_data *tx) | |||
660 | 660 | ||
661 | /* | 661 | /* |
662 | * Warn when submitting a fragmented A-MPDU frame and drop it. | 662 | * Warn when submitting a fragmented A-MPDU frame and drop it. |
663 | * This is an error and needs to be fixed elsewhere, but when | 663 | * This scenario is handled in __ieee80211_tx_prepare but extra |
664 | * done needs to take care of monitor interfaces (injection) | 664 | * caution taken here as fragmented ampdu may cause Tx stop. |
665 | * etc. | ||
666 | */ | 665 | */ |
667 | if (WARN_ON(tx->flags & IEEE80211_TX_CTL_AMPDU || | 666 | if (WARN_ON(tx->flags & IEEE80211_TX_CTL_AMPDU || |
668 | skb_get_queue_mapping(tx->skb) >= | 667 | skb_get_queue_mapping(tx->skb) >= |
@@ -981,7 +980,8 @@ __ieee80211_tx_prepare(struct ieee80211_tx_data *tx, | |||
981 | if (tx->flags & IEEE80211_TX_FRAGMENTED) { | 980 | if (tx->flags & IEEE80211_TX_FRAGMENTED) { |
982 | if ((tx->flags & IEEE80211_TX_UNICAST) && | 981 | if ((tx->flags & IEEE80211_TX_UNICAST) && |
983 | skb->len + FCS_LEN > local->fragmentation_threshold && | 982 | skb->len + FCS_LEN > local->fragmentation_threshold && |
984 | !local->ops->set_frag_threshold) | 983 | !local->ops->set_frag_threshold && |
984 | !(info->flags & IEEE80211_TX_CTL_AMPDU)) | ||
985 | tx->flags |= IEEE80211_TX_FRAGMENTED; | 985 | tx->flags |= IEEE80211_TX_FRAGMENTED; |
986 | else | 986 | else |
987 | tx->flags &= ~IEEE80211_TX_FRAGMENTED; | 987 | tx->flags &= ~IEEE80211_TX_FRAGMENTED; |
diff --git a/net/mac80211/util.c b/net/mac80211/util.c index 6513bc2d2707..ce62b163b82c 100644 --- a/net/mac80211/util.c +++ b/net/mac80211/util.c | |||
@@ -45,38 +45,37 @@ const unsigned char bridge_tunnel_header[] __aligned(2) = | |||
45 | u8 *ieee80211_get_bssid(struct ieee80211_hdr *hdr, size_t len, | 45 | u8 *ieee80211_get_bssid(struct ieee80211_hdr *hdr, size_t len, |
46 | enum ieee80211_if_types type) | 46 | enum ieee80211_if_types type) |
47 | { | 47 | { |
48 | u16 fc; | 48 | __le16 fc = hdr->frame_control; |
49 | 49 | ||
50 | /* drop ACK/CTS frames and incorrect hdr len (ctrl) */ | 50 | /* drop ACK/CTS frames and incorrect hdr len (ctrl) */ |
51 | if (len < 16) | 51 | if (len < 16) |
52 | return NULL; | 52 | return NULL; |
53 | 53 | ||
54 | fc = le16_to_cpu(hdr->frame_control); | 54 | if (ieee80211_is_data(fc)) { |
55 | |||
56 | switch (fc & IEEE80211_FCTL_FTYPE) { | ||
57 | case IEEE80211_FTYPE_DATA: | ||
58 | if (len < 24) /* drop incorrect hdr len (data) */ | 55 | if (len < 24) /* drop incorrect hdr len (data) */ |
59 | return NULL; | 56 | return NULL; |
60 | switch (fc & (IEEE80211_FCTL_TODS | IEEE80211_FCTL_FROMDS)) { | 57 | |
61 | case IEEE80211_FCTL_TODS: | 58 | if (ieee80211_has_a4(fc)) |
62 | return hdr->addr1; | ||
63 | case (IEEE80211_FCTL_TODS | IEEE80211_FCTL_FROMDS): | ||
64 | return NULL; | 59 | return NULL; |
65 | case IEEE80211_FCTL_FROMDS: | 60 | if (ieee80211_has_tods(fc)) |
61 | return hdr->addr1; | ||
62 | if (ieee80211_has_fromds(fc)) | ||
66 | return hdr->addr2; | 63 | return hdr->addr2; |
67 | case 0: | 64 | |
68 | return hdr->addr3; | 65 | return hdr->addr3; |
69 | } | 66 | } |
70 | break; | 67 | |
71 | case IEEE80211_FTYPE_MGMT: | 68 | if (ieee80211_is_mgmt(fc)) { |
72 | if (len < 24) /* drop incorrect hdr len (mgmt) */ | 69 | if (len < 24) /* drop incorrect hdr len (mgmt) */ |
73 | return NULL; | 70 | return NULL; |
74 | return hdr->addr3; | 71 | return hdr->addr3; |
75 | case IEEE80211_FTYPE_CTL: | 72 | } |
76 | if ((fc & IEEE80211_FCTL_STYPE) == IEEE80211_STYPE_PSPOLL) | 73 | |
74 | if (ieee80211_is_ctl(fc)) { | ||
75 | if(ieee80211_is_pspoll(fc)) | ||
77 | return hdr->addr1; | 76 | return hdr->addr1; |
78 | else if ((fc & IEEE80211_FCTL_STYPE) == | 77 | |
79 | IEEE80211_STYPE_BACK_REQ) { | 78 | if (ieee80211_is_back_req(fc)) { |
80 | switch (type) { | 79 | switch (type) { |
81 | case IEEE80211_IF_TYPE_STA: | 80 | case IEEE80211_IF_TYPE_STA: |
82 | return hdr->addr2; | 81 | return hdr->addr2; |
@@ -84,11 +83,9 @@ u8 *ieee80211_get_bssid(struct ieee80211_hdr *hdr, size_t len, | |||
84 | case IEEE80211_IF_TYPE_VLAN: | 83 | case IEEE80211_IF_TYPE_VLAN: |
85 | return hdr->addr1; | 84 | return hdr->addr1; |
86 | default: | 85 | default: |
87 | return NULL; | 86 | break; /* fall through to the return */ |
88 | } | 87 | } |
89 | } | 88 | } |
90 | else | ||
91 | return NULL; | ||
92 | } | 89 | } |
93 | 90 | ||
94 | return NULL; | 91 | return NULL; |
@@ -133,14 +130,46 @@ int ieee80211_get_hdrlen(u16 fc) | |||
133 | } | 130 | } |
134 | EXPORT_SYMBOL(ieee80211_get_hdrlen); | 131 | EXPORT_SYMBOL(ieee80211_get_hdrlen); |
135 | 132 | ||
136 | int ieee80211_get_hdrlen_from_skb(const struct sk_buff *skb) | 133 | unsigned int ieee80211_hdrlen(__le16 fc) |
134 | { | ||
135 | unsigned int hdrlen = 24; | ||
136 | |||
137 | if (ieee80211_is_data(fc)) { | ||
138 | if (ieee80211_has_a4(fc)) | ||
139 | hdrlen = 30; | ||
140 | if (ieee80211_is_data_qos(fc)) | ||
141 | hdrlen += IEEE80211_QOS_CTL_LEN; | ||
142 | goto out; | ||
143 | } | ||
144 | |||
145 | if (ieee80211_is_ctl(fc)) { | ||
146 | /* | ||
147 | * ACK and CTS are 10 bytes, all others 16. To see how | ||
148 | * to get this condition consider | ||
149 | * subtype mask: 0b0000000011110000 (0x00F0) | ||
150 | * ACK subtype: 0b0000000011010000 (0x00D0) | ||
151 | * CTS subtype: 0b0000000011000000 (0x00C0) | ||
152 | * bits that matter: ^^^ (0x00E0) | ||
153 | * value of those: 0b0000000011000000 (0x00C0) | ||
154 | */ | ||
155 | if ((fc & cpu_to_le16(0x00E0)) == cpu_to_le16(0x00C0)) | ||
156 | hdrlen = 10; | ||
157 | else | ||
158 | hdrlen = 16; | ||
159 | } | ||
160 | out: | ||
161 | return hdrlen; | ||
162 | } | ||
163 | EXPORT_SYMBOL(ieee80211_hdrlen); | ||
164 | |||
165 | unsigned int ieee80211_get_hdrlen_from_skb(const struct sk_buff *skb) | ||
137 | { | 166 | { |
138 | const struct ieee80211_hdr *hdr = (const struct ieee80211_hdr *) skb->data; | 167 | const struct ieee80211_hdr *hdr = (const struct ieee80211_hdr *)skb->data; |
139 | int hdrlen; | 168 | unsigned int hdrlen; |
140 | 169 | ||
141 | if (unlikely(skb->len < 10)) | 170 | if (unlikely(skb->len < 10)) |
142 | return 0; | 171 | return 0; |
143 | hdrlen = ieee80211_get_hdrlen(le16_to_cpu(hdr->frame_control)); | 172 | hdrlen = ieee80211_hdrlen(hdr->frame_control); |
144 | if (unlikely(hdrlen > skb->len)) | 173 | if (unlikely(hdrlen > skb->len)) |
145 | return 0; | 174 | return 0; |
146 | return hdrlen; | 175 | return hdrlen; |
diff --git a/net/mac80211/wme.c b/net/mac80211/wme.c index 14a9ff10a1e9..d8c2f9688b25 100644 --- a/net/mac80211/wme.c +++ b/net/mac80211/wme.c | |||
@@ -105,11 +105,8 @@ static int classify80211(struct sk_buff *skb, struct Qdisc *qd) | |||
105 | { | 105 | { |
106 | struct ieee80211_local *local = wdev_priv(qd->dev->ieee80211_ptr); | 106 | struct ieee80211_local *local = wdev_priv(qd->dev->ieee80211_ptr); |
107 | struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) skb->data; | 107 | struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) skb->data; |
108 | unsigned short fc = le16_to_cpu(hdr->frame_control); | ||
109 | int qos; | ||
110 | 108 | ||
111 | /* see if frame is data or non data frame */ | 109 | if (!ieee80211_is_data(hdr->frame_control)) { |
112 | if (unlikely((fc & IEEE80211_FCTL_FTYPE) != IEEE80211_FTYPE_DATA)) { | ||
113 | /* management frames go on AC_VO queue, but are sent | 110 | /* management frames go on AC_VO queue, but are sent |
114 | * without QoS control fields */ | 111 | * without QoS control fields */ |
115 | return 0; | 112 | return 0; |
@@ -119,10 +116,7 @@ static int classify80211(struct sk_buff *skb, struct Qdisc *qd) | |||
119 | /* use AC from radiotap */ | 116 | /* use AC from radiotap */ |
120 | } | 117 | } |
121 | 118 | ||
122 | /* is this a QoS frame? */ | 119 | if (!ieee80211_is_data_qos(hdr->frame_control)) { |
123 | qos = fc & IEEE80211_STYPE_QOS_DATA; | ||
124 | |||
125 | if (!qos) { | ||
126 | skb->priority = 0; /* required for correct WPA/11i MIC */ | 120 | skb->priority = 0; /* required for correct WPA/11i MIC */ |
127 | return ieee802_1d_to_ac[skb->priority]; | 121 | return ieee802_1d_to_ac[skb->priority]; |
128 | } | 122 | } |
@@ -151,7 +145,6 @@ static int wme_qdiscop_enqueue(struct sk_buff *skb, struct Qdisc* qd) | |||
151 | struct ieee80211_sched_data *q = qdisc_priv(qd); | 145 | struct ieee80211_sched_data *q = qdisc_priv(qd); |
152 | struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb); | 146 | struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb); |
153 | struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) skb->data; | 147 | struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) skb->data; |
154 | unsigned short fc = le16_to_cpu(hdr->frame_control); | ||
155 | struct Qdisc *qdisc; | 148 | struct Qdisc *qdisc; |
156 | struct sta_info *sta; | 149 | struct sta_info *sta; |
157 | int err, queue; | 150 | int err, queue; |
@@ -185,16 +178,15 @@ static int wme_qdiscop_enqueue(struct sk_buff *skb, struct Qdisc* qd) | |||
185 | 178 | ||
186 | /* now we know the 1d priority, fill in the QoS header if there is one | 179 | /* now we know the 1d priority, fill in the QoS header if there is one |
187 | */ | 180 | */ |
188 | if (WLAN_FC_IS_QOS_DATA(fc)) { | 181 | if (ieee80211_is_data_qos(hdr->frame_control)) { |
189 | u8 *p = skb->data + ieee80211_get_hdrlen(fc) - 2; | 182 | u8 *p = ieee80211_get_qos_ctl(hdr); |
190 | u8 ack_policy = 0; | 183 | u8 ack_policy = 0; |
191 | tid = skb->priority & QOS_CONTROL_TAG1D_MASK; | 184 | tid = skb->priority & QOS_CONTROL_TAG1D_MASK; |
192 | if (local->wifi_wme_noack_test) | 185 | if (local->wifi_wme_noack_test) |
193 | ack_policy |= QOS_CONTROL_ACK_POLICY_NOACK << | 186 | ack_policy |= QOS_CONTROL_ACK_POLICY_NOACK << |
194 | QOS_CONTROL_ACK_POLICY_SHIFT; | 187 | QOS_CONTROL_ACK_POLICY_SHIFT; |
195 | /* qos header is 2 bytes, second reserved */ | 188 | /* qos header is 2 bytes, second reserved */ |
196 | *p = ack_policy | tid; | 189 | *p++ = ack_policy | tid; |
197 | p++; | ||
198 | *p = 0; | 190 | *p = 0; |
199 | 191 | ||
200 | rcu_read_lock(); | 192 | rcu_read_lock(); |
diff --git a/net/mac80211/wpa.c b/net/mac80211/wpa.c index 9f6fd20374e1..345e10e9b313 100644 --- a/net/mac80211/wpa.c +++ b/net/mac80211/wpa.c | |||
@@ -24,46 +24,22 @@ static int ieee80211_get_hdr_info(const struct sk_buff *skb, u8 **sa, u8 **da, | |||
24 | { | 24 | { |
25 | struct ieee80211_hdr *hdr; | 25 | struct ieee80211_hdr *hdr; |
26 | size_t hdrlen; | 26 | size_t hdrlen; |
27 | u16 fc; | 27 | __le16 fc; |
28 | int a4_included; | ||
29 | u8 *pos; | ||
30 | 28 | ||
31 | hdr = (struct ieee80211_hdr *) skb->data; | 29 | hdr = (struct ieee80211_hdr *)skb->data; |
32 | fc = le16_to_cpu(hdr->frame_control); | 30 | fc = hdr->frame_control; |
33 | |||
34 | hdrlen = 24; | ||
35 | if ((fc & (IEEE80211_FCTL_FROMDS | IEEE80211_FCTL_TODS)) == | ||
36 | (IEEE80211_FCTL_FROMDS | IEEE80211_FCTL_TODS)) { | ||
37 | hdrlen += ETH_ALEN; | ||
38 | *sa = hdr->addr4; | ||
39 | *da = hdr->addr3; | ||
40 | } else if (fc & IEEE80211_FCTL_FROMDS) { | ||
41 | *sa = hdr->addr3; | ||
42 | *da = hdr->addr1; | ||
43 | } else if (fc & IEEE80211_FCTL_TODS) { | ||
44 | *sa = hdr->addr2; | ||
45 | *da = hdr->addr3; | ||
46 | } else { | ||
47 | *sa = hdr->addr2; | ||
48 | *da = hdr->addr1; | ||
49 | } | ||
50 | 31 | ||
51 | if (fc & 0x80) | 32 | hdrlen = ieee80211_hdrlen(fc); |
52 | hdrlen += 2; | 33 | |
34 | *sa = ieee80211_get_SA(hdr); | ||
35 | *da = ieee80211_get_DA(hdr); | ||
53 | 36 | ||
54 | *data = skb->data + hdrlen; | 37 | *data = skb->data + hdrlen; |
55 | *data_len = skb->len - hdrlen; | 38 | *data_len = skb->len - hdrlen; |
56 | 39 | ||
57 | a4_included = (fc & (IEEE80211_FCTL_TODS | IEEE80211_FCTL_FROMDS)) == | 40 | if (ieee80211_is_data_qos(fc)) |
58 | (IEEE80211_FCTL_TODS | IEEE80211_FCTL_FROMDS); | 41 | *qos_tid = (*ieee80211_get_qos_ctl(hdr) & 0x0f) | 0x80; |
59 | if ((fc & IEEE80211_FCTL_FTYPE) == IEEE80211_FTYPE_DATA && | 42 | else |
60 | fc & IEEE80211_STYPE_QOS_DATA) { | ||
61 | pos = (u8 *) &hdr->addr4; | ||
62 | if (a4_included) | ||
63 | pos += 6; | ||
64 | *qos_tid = pos[0] & 0x0f; | ||
65 | *qos_tid |= 0x80; /* qos_included flag */ | ||
66 | } else | ||
67 | *qos_tid = 0; | 43 | *qos_tid = 0; |
68 | 44 | ||
69 | return skb->len < hdrlen ? -1 : 0; | 45 | return skb->len < hdrlen ? -1 : 0; |
@@ -186,8 +162,8 @@ static int tkip_encrypt_skb(struct ieee80211_tx_data *tx, struct sk_buff *skb) | |||
186 | struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) skb->data; | 162 | struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) skb->data; |
187 | struct ieee80211_key *key = tx->key; | 163 | struct ieee80211_key *key = tx->key; |
188 | struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb); | 164 | struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb); |
189 | int hdrlen, len, tail; | 165 | unsigned int hdrlen; |
190 | u16 fc; | 166 | int len, tail; |
191 | u8 *pos; | 167 | u8 *pos; |
192 | 168 | ||
193 | info->control.icv_len = TKIP_ICV_LEN; | 169 | info->control.icv_len = TKIP_ICV_LEN; |
@@ -200,8 +176,7 @@ static int tkip_encrypt_skb(struct ieee80211_tx_data *tx, struct sk_buff *skb) | |||
200 | return 0; | 176 | return 0; |
201 | } | 177 | } |
202 | 178 | ||
203 | fc = le16_to_cpu(hdr->frame_control); | 179 | hdrlen = ieee80211_hdrlen(hdr->frame_control); |
204 | hdrlen = ieee80211_get_hdrlen(fc); | ||
205 | len = skb->len - hdrlen; | 180 | len = skb->len - hdrlen; |
206 | 181 | ||
207 | if (tx->key->flags & KEY_FLAG_UPLOADED_TO_HARDWARE) | 182 | if (tx->key->flags & KEY_FLAG_UPLOADED_TO_HARDWARE) |
@@ -223,14 +198,8 @@ static int tkip_encrypt_skb(struct ieee80211_tx_data *tx, struct sk_buff *skb) | |||
223 | key->u.tkip.tx.iv32++; | 198 | key->u.tkip.tx.iv32++; |
224 | 199 | ||
225 | if (tx->key->flags & KEY_FLAG_UPLOADED_TO_HARDWARE) { | 200 | if (tx->key->flags & KEY_FLAG_UPLOADED_TO_HARDWARE) { |
226 | hdr = (struct ieee80211_hdr *)skb->data; | ||
227 | |||
228 | /* hwaccel - with preallocated room for IV */ | 201 | /* hwaccel - with preallocated room for IV */ |
229 | ieee80211_tkip_add_iv(pos, key, | 202 | ieee80211_tkip_add_iv(pos, key, key->u.tkip.tx.iv16); |
230 | (u8) (key->u.tkip.tx.iv16 >> 8), | ||
231 | (u8) (((key->u.tkip.tx.iv16 >> 8) | 0x20) & | ||
232 | 0x7f), | ||
233 | (u8) key->u.tkip.tx.iv16); | ||
234 | 203 | ||
235 | info->control.hw_key = &tx->key->conf; | 204 | info->control.hw_key = &tx->key->conf; |
236 | return 0; | 205 | return 0; |
@@ -272,14 +241,12 @@ ieee80211_rx_result | |||
272 | ieee80211_crypto_tkip_decrypt(struct ieee80211_rx_data *rx) | 241 | ieee80211_crypto_tkip_decrypt(struct ieee80211_rx_data *rx) |
273 | { | 242 | { |
274 | struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) rx->skb->data; | 243 | struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) rx->skb->data; |
275 | u16 fc; | ||
276 | int hdrlen, res, hwaccel = 0, wpa_test = 0; | 244 | int hdrlen, res, hwaccel = 0, wpa_test = 0; |
277 | struct ieee80211_key *key = rx->key; | 245 | struct ieee80211_key *key = rx->key; |
278 | struct sk_buff *skb = rx->skb; | 246 | struct sk_buff *skb = rx->skb; |
279 | DECLARE_MAC_BUF(mac); | 247 | DECLARE_MAC_BUF(mac); |
280 | 248 | ||
281 | fc = le16_to_cpu(hdr->frame_control); | 249 | hdrlen = ieee80211_hdrlen(hdr->frame_control); |
282 | hdrlen = ieee80211_get_hdrlen(fc); | ||
283 | 250 | ||
284 | if ((rx->fc & IEEE80211_FCTL_FTYPE) != IEEE80211_FTYPE_DATA) | 251 | if ((rx->fc & IEEE80211_FCTL_FTYPE) != IEEE80211_FTYPE_DATA) |
285 | return RX_CONTINUE; | 252 | return RX_CONTINUE; |
@@ -427,7 +394,6 @@ static int ccmp_encrypt_skb(struct ieee80211_tx_data *tx, struct sk_buff *skb) | |||
427 | struct ieee80211_key *key = tx->key; | 394 | struct ieee80211_key *key = tx->key; |
428 | struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb); | 395 | struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb); |
429 | int hdrlen, len, tail; | 396 | int hdrlen, len, tail; |
430 | u16 fc; | ||
431 | u8 *pos, *pn, *b_0, *aad, *scratch; | 397 | u8 *pos, *pn, *b_0, *aad, *scratch; |
432 | int i; | 398 | int i; |
433 | 399 | ||
@@ -446,8 +412,7 @@ static int ccmp_encrypt_skb(struct ieee80211_tx_data *tx, struct sk_buff *skb) | |||
446 | b_0 = scratch + 3 * AES_BLOCK_LEN; | 412 | b_0 = scratch + 3 * AES_BLOCK_LEN; |
447 | aad = scratch + 4 * AES_BLOCK_LEN; | 413 | aad = scratch + 4 * AES_BLOCK_LEN; |
448 | 414 | ||
449 | fc = le16_to_cpu(hdr->frame_control); | 415 | hdrlen = ieee80211_hdrlen(hdr->frame_control); |
450 | hdrlen = ieee80211_get_hdrlen(fc); | ||
451 | len = skb->len - hdrlen; | 416 | len = skb->len - hdrlen; |
452 | 417 | ||
453 | if (key->flags & KEY_FLAG_UPLOADED_TO_HARDWARE) | 418 | if (key->flags & KEY_FLAG_UPLOADED_TO_HARDWARE) |
@@ -516,7 +481,6 @@ ieee80211_rx_result | |||
516 | ieee80211_crypto_ccmp_decrypt(struct ieee80211_rx_data *rx) | 481 | ieee80211_crypto_ccmp_decrypt(struct ieee80211_rx_data *rx) |
517 | { | 482 | { |
518 | struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) rx->skb->data; | 483 | struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) rx->skb->data; |
519 | u16 fc; | ||
520 | int hdrlen; | 484 | int hdrlen; |
521 | struct ieee80211_key *key = rx->key; | 485 | struct ieee80211_key *key = rx->key; |
522 | struct sk_buff *skb = rx->skb; | 486 | struct sk_buff *skb = rx->skb; |
@@ -524,8 +488,7 @@ ieee80211_crypto_ccmp_decrypt(struct ieee80211_rx_data *rx) | |||
524 | int data_len; | 488 | int data_len; |
525 | DECLARE_MAC_BUF(mac); | 489 | DECLARE_MAC_BUF(mac); |
526 | 490 | ||
527 | fc = le16_to_cpu(hdr->frame_control); | 491 | hdrlen = ieee80211_hdrlen(hdr->frame_control); |
528 | hdrlen = ieee80211_get_hdrlen(fc); | ||
529 | 492 | ||
530 | if ((rx->fc & IEEE80211_FCTL_FTYPE) != IEEE80211_FTYPE_DATA) | 493 | if ((rx->fc & IEEE80211_FCTL_FTYPE) != IEEE80211_FTYPE_DATA) |
531 | return RX_CONTINUE; | 494 | return RX_CONTINUE; |
diff --git a/net/wireless/reg.c b/net/wireless/reg.c index 185488da2466..855bff4b3250 100644 --- a/net/wireless/reg.c +++ b/net/wireless/reg.c | |||
@@ -80,6 +80,23 @@ static const struct ieee80211_channel_range ieee80211_JP_channels[] = { | |||
80 | IEEE80211_CHAN_RADAR), | 80 | IEEE80211_CHAN_RADAR), |
81 | }; | 81 | }; |
82 | 82 | ||
83 | static const struct ieee80211_channel_range ieee80211_EU_channels[] = { | ||
84 | /* IEEE 802.11b/g, channels 1..13 */ | ||
85 | RANGE_PWR(2412, 2472, 20, 6, 0), | ||
86 | /* IEEE 802.11a, channel 36*/ | ||
87 | RANGE_PWR(5180, 5180, 23, 6, IEEE80211_CHAN_PASSIVE_SCAN), | ||
88 | /* IEEE 802.11a, channel 40*/ | ||
89 | RANGE_PWR(5200, 5200, 23, 6, IEEE80211_CHAN_PASSIVE_SCAN), | ||
90 | /* IEEE 802.11a, channel 44*/ | ||
91 | RANGE_PWR(5220, 5220, 23, 6, IEEE80211_CHAN_PASSIVE_SCAN), | ||
92 | /* IEEE 802.11a, channels 48..64 */ | ||
93 | RANGE_PWR(5240, 5320, 23, 6, IEEE80211_CHAN_NO_IBSS | | ||
94 | IEEE80211_CHAN_RADAR), | ||
95 | /* IEEE 802.11a, channels 100..140 */ | ||
96 | RANGE_PWR(5500, 5700, 30, 6, IEEE80211_CHAN_NO_IBSS | | ||
97 | IEEE80211_CHAN_RADAR), | ||
98 | }; | ||
99 | |||
83 | #define REGDOM(_code) \ | 100 | #define REGDOM(_code) \ |
84 | { \ | 101 | { \ |
85 | .code = __stringify(_code), \ | 102 | .code = __stringify(_code), \ |
@@ -90,6 +107,7 @@ static const struct ieee80211_channel_range ieee80211_JP_channels[] = { | |||
90 | static const struct ieee80211_regdomain ieee80211_regdoms[] = { | 107 | static const struct ieee80211_regdomain ieee80211_regdoms[] = { |
91 | REGDOM(US), | 108 | REGDOM(US), |
92 | REGDOM(JP), | 109 | REGDOM(JP), |
110 | REGDOM(EU), | ||
93 | }; | 111 | }; |
94 | 112 | ||
95 | 113 | ||