Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

mac80211: save wmm_acm per sdata

Save and configure the wmm_acm per sdata, rather than
per hardware.

If wmm_acm is saved per hardware when running two
interfaces simultaneously on the same hardware one
interface's wmm policy will be affected by the other
interface.

Signed-off-by: Yoni Divinsky <yoni.divinsky@ti.com>
Signed-off-by: Luciano Coelho <coelho@ti.com>
Signed-off-by: Johannes Berg <johannes.berg@intel.com>

authored by

Yoni Divinsky and committed by
Johannes Berg
00e96dec 50ae34a2

+17 -14
+3 -1
net/mac80211/ieee80211_i.h
··· 680 680 /* TID bitmap for NoAck policy */ 681 681 u16 noack_map; 682 682 683 + /* bit field of ACM bits (BIT(802.1D tag)) */ 684 + u8 wmm_acm; 685 + 683 686 struct ieee80211_key __rcu *keys[NUM_DEFAULT_KEYS + NUM_DEFAULT_MGMT_KEYS]; 684 687 struct ieee80211_key __rcu *default_unicast_key; 685 688 struct ieee80211_key __rcu *default_multicast_key; ··· 1028 1025 int total_ps_buffered; /* total number of all buffered unicast and 1029 1026 * multicast packets for power saving stations 1030 1027 */ 1031 - unsigned int wmm_acm; /* bit field of ACM bits (BIT(802.1D tag)) */ 1032 1028 1033 1029 bool pspolling; 1034 1030 bool offchannel_ps_enabled;
+1 -1
net/mac80211/iface.c
··· 808 808 809 809 hdr = (void *)((u8 *)skb->data + le16_to_cpu(rtap->it_len)); 810 810 811 - return ieee80211_select_queue_80211(local, skb, hdr); 811 + return ieee80211_select_queue_80211(sdata, skb, hdr); 812 812 } 813 813 814 814 static const struct net_device_ops ieee80211_monitorif_ops = {
+5 -5
net/mac80211/mlme.c
··· 1141 1141 1142 1142 memset(&params, 0, sizeof(params)); 1143 1143 1144 - local->wmm_acm = 0; 1144 + sdata->wmm_acm = 0; 1145 1145 for (; left >= 4; left -= 4, pos += 4) { 1146 1146 int aci = (pos[0] >> 5) & 0x03; 1147 1147 int acm = (pos[0] >> 4) & 0x01; ··· 1152 1152 case 1: /* AC_BK */ 1153 1153 queue = 3; 1154 1154 if (acm) 1155 - local->wmm_acm |= BIT(1) | BIT(2); /* BK/- */ 1155 + sdata->wmm_acm |= BIT(1) | BIT(2); /* BK/- */ 1156 1156 if (uapsd_queues & IEEE80211_WMM_IE_STA_QOSINFO_AC_BK) 1157 1157 uapsd = true; 1158 1158 break; 1159 1159 case 2: /* AC_VI */ 1160 1160 queue = 1; 1161 1161 if (acm) 1162 - local->wmm_acm |= BIT(4) | BIT(5); /* CL/VI */ 1162 + sdata->wmm_acm |= BIT(4) | BIT(5); /* CL/VI */ 1163 1163 if (uapsd_queues & IEEE80211_WMM_IE_STA_QOSINFO_AC_VI) 1164 1164 uapsd = true; 1165 1165 break; 1166 1166 case 3: /* AC_VO */ 1167 1167 queue = 0; 1168 1168 if (acm) 1169 - local->wmm_acm |= BIT(6) | BIT(7); /* VO/NC */ 1169 + sdata->wmm_acm |= BIT(6) | BIT(7); /* VO/NC */ 1170 1170 if (uapsd_queues & IEEE80211_WMM_IE_STA_QOSINFO_AC_VO) 1171 1171 uapsd = true; 1172 1172 break; ··· 1174 1174 default: 1175 1175 queue = 2; 1176 1176 if (acm) 1177 - local->wmm_acm |= BIT(0) | BIT(3); /* BE/EE */ 1177 + sdata->wmm_acm |= BIT(0) | BIT(3); /* BE/EE */ 1178 1178 if (uapsd_queues & IEEE80211_WMM_IE_STA_QOSINFO_AC_BE) 1179 1179 uapsd = true; 1180 1180 break;
+1 -1
net/mac80211/rx.c
··· 1935 1935 ether_addr_equal(sdata->vif.addr, hdr->addr3)) 1936 1936 return RX_CONTINUE; 1937 1937 1938 - q = ieee80211_select_queue_80211(local, skb, hdr); 1938 + q = ieee80211_select_queue_80211(sdata, skb, hdr); 1939 1939 if (ieee80211_queue_stopped(&local->hw, q)) { 1940 1940 IEEE80211_IFSTA_MESH_CTR_INC(ifmsh, dropped_frames_congestion); 1941 1941 return RX_DROP_MONITOR;
+6 -5
net/mac80211/wme.c
··· 52 52 } 53 53 } 54 54 55 - static u16 ieee80211_downgrade_queue(struct ieee80211_local *local, 55 + static u16 ieee80211_downgrade_queue(struct ieee80211_sub_if_data *sdata, 56 56 struct sk_buff *skb) 57 57 { 58 58 /* in case we are a client verify acm is not set for this ac */ 59 - while (unlikely(local->wmm_acm & BIT(skb->priority))) { 59 + while (unlikely(sdata->wmm_acm & BIT(skb->priority))) { 60 60 if (wme_downgrade_ac(skb)) { 61 61 /* 62 62 * This should not really happen. The AP has marked all ··· 73 73 } 74 74 75 75 /* Indicate which queue to use for this fully formed 802.11 frame */ 76 - u16 ieee80211_select_queue_80211(struct ieee80211_local *local, 76 + u16 ieee80211_select_queue_80211(struct ieee80211_sub_if_data *sdata, 77 77 struct sk_buff *skb, 78 78 struct ieee80211_hdr *hdr) 79 79 { 80 + struct ieee80211_local *local = sdata->local; 80 81 u8 *p; 81 82 82 83 if (local->hw.queues < IEEE80211_NUM_ACS) ··· 95 94 p = ieee80211_get_qos_ctl(hdr); 96 95 skb->priority = *p & IEEE80211_QOS_CTL_TAG1D_MASK; 97 96 98 - return ieee80211_downgrade_queue(local, skb); 97 + return ieee80211_downgrade_queue(sdata, skb); 99 98 } 100 99 101 100 /* Indicate which queue to use. */ ··· 157 156 * data frame has */ 158 157 skb->priority = cfg80211_classify8021d(skb); 159 158 160 - return ieee80211_downgrade_queue(local, skb); 159 + return ieee80211_downgrade_queue(sdata, skb); 161 160 } 162 161 163 162 void ieee80211_set_qos_hdr(struct ieee80211_sub_if_data *sdata,
+1 -1
net/mac80211/wme.h
··· 15 15 16 16 extern const int ieee802_1d_to_ac[8]; 17 17 18 - u16 ieee80211_select_queue_80211(struct ieee80211_local *local, 18 + u16 ieee80211_select_queue_80211(struct ieee80211_sub_if_data *sdata, 19 19 struct sk_buff *skb, 20 20 struct ieee80211_hdr *hdr); 21 21 u16 ieee80211_select_queue(struct ieee80211_sub_if_data *sdata,