summaryrefslogtreecommitdiff
path: root/package/kernel/mac80211/patches/906-wlcore-wl12xx-wl18xx-configure-num_links-per-hw.patch
diff options
context:
space:
mode:
authorkaloz <kaloz@3c298f89-4303-0410-b956-a3cf2f4a3e73>2014-03-18 18:55:54 +0000
committerkaloz <kaloz@3c298f89-4303-0410-b956-a3cf2f4a3e73>2014-03-18 18:55:54 +0000
commit2ead16490139642a2cb5d191e90729d6c27455d1 (patch)
tree2559a20fed9cca97addaeeb1a9f3a2948311b424 /package/kernel/mac80211/patches/906-wlcore-wl12xx-wl18xx-configure-num_links-per-hw.patch
parentee194135dc0e12c78515a6349d651ada3807ae12 (diff)
[mac80211]: add add new firmware support and additional fixes for wl18xx
Signed-off-by: Imre Kaloz <kaloz@openwrt.org> git-svn-id: svn://svn.openwrt.org/openwrt/trunk@39947 3c298f89-4303-0410-b956-a3cf2f4a3e73
Diffstat (limited to 'package/kernel/mac80211/patches/906-wlcore-wl12xx-wl18xx-configure-num_links-per-hw.patch')
-rw-r--r--package/kernel/mac80211/patches/906-wlcore-wl12xx-wl18xx-configure-num_links-per-hw.patch345
1 files changed, 345 insertions, 0 deletions
diff --git a/package/kernel/mac80211/patches/906-wlcore-wl12xx-wl18xx-configure-num_links-per-hw.patch b/package/kernel/mac80211/patches/906-wlcore-wl12xx-wl18xx-configure-num_links-per-hw.patch
new file mode 100644
index 0000000000..5c342f5e1d
--- /dev/null
+++ b/package/kernel/mac80211/patches/906-wlcore-wl12xx-wl18xx-configure-num_links-per-hw.patch
@@ -0,0 +1,345 @@
+Upcoming fw versions will have different max links support
+(according to the hw). Get ready for it by configuring
+wl->num_links per-hw, instead of using the const WL12XX_MAX_LINKS.
+
+However, continue using WLCORE_MAX_LINKS in order to simplify
+structs declarations (we use it in multiple bitmaps, and converting
+them to dynamic arrays is just cumbersome).
+
+Signed-off-by: Eliad Peller <eliad@wizery.com>
+
+---
+drivers/net/wireless/ti/wl12xx/main.c | 3 +++
+ drivers/net/wireless/ti/wl12xx/wl12xx.h | 2 ++
+ drivers/net/wireless/ti/wl18xx/main.c | 3 +++
+ drivers/net/wireless/ti/wl18xx/wl18xx.h | 4 +++-
+ drivers/net/wireless/ti/wlcore/cmd.c | 4 ++--
+ drivers/net/wireless/ti/wlcore/event.c | 4 ++--
+ drivers/net/wireless/ti/wlcore/main.c | 12 ++++++++----
+ drivers/net/wireless/ti/wlcore/rx.c | 8 ++++----
+ drivers/net/wireless/ti/wlcore/tx.c | 20 ++++++++++----------
+ drivers/net/wireless/ti/wlcore/wlcore.h | 8 +++++---
+ drivers/net/wireless/ti/wlcore/wlcore_i.h | 13 +++++++++----
+ 11 files changed, 51 insertions(+), 30 deletions(-)
+
+--- a/drivers/net/wireless/ti/wl12xx/main.c
++++ b/drivers/net/wireless/ti/wl12xx/main.c
+@@ -1749,9 +1749,12 @@ static int wl12xx_setup(struct wl1271 *w
+ struct wlcore_platdev_data *pdev_data = dev_get_platdata(&wl->pdev->dev);
+ struct wl12xx_platform_data *pdata = pdev_data->pdata;
+
++ BUILD_BUG_ON(WL12XX_MAX_LINKS > WLCORE_MAX_LINKS);
++
+ wl->rtable = wl12xx_rtable;
+ wl->num_tx_desc = WL12XX_NUM_TX_DESCRIPTORS;
+ wl->num_rx_desc = WL12XX_NUM_RX_DESCRIPTORS;
++ wl->num_links = WL12XX_MAX_LINKS;
+ wl->num_channels = 1;
+ wl->num_mac_addr = WL12XX_NUM_MAC_ADDRESSES;
+ wl->band_rate_to_idx = wl12xx_band_rate_to_idx;
+--- a/drivers/net/wireless/ti/wl12xx/wl12xx.h
++++ b/drivers/net/wireless/ti/wl12xx/wl12xx.h
+@@ -65,6 +65,8 @@
+
+ #define WL12XX_RX_BA_MAX_SESSIONS 3
+
++#define WL12XX_MAX_LINKS 12
++
+ struct wl127x_rx_mem_pool_addr {
+ u32 addr;
+ u32 addr_extra;
+--- a/drivers/net/wireless/ti/wl18xx/main.c
++++ b/drivers/net/wireless/ti/wl18xx/main.c
+@@ -1752,9 +1752,12 @@ static int wl18xx_setup(struct wl1271 *w
+ struct wl18xx_priv *priv = wl->priv;
+ int ret;
+
++ BUILD_BUG_ON(WL18XX_MAX_LINKS > WLCORE_MAX_LINKS);
++
+ wl->rtable = wl18xx_rtable;
+ wl->num_tx_desc = WL18XX_NUM_TX_DESCRIPTORS;
+ wl->num_rx_desc = WL18XX_NUM_RX_DESCRIPTORS;
++ wl->num_links = WL18XX_MAX_LINKS;
+ wl->num_channels = 2;
+ wl->num_mac_addr = WL18XX_NUM_MAC_ADDRESSES;
+ wl->band_rate_to_idx = wl18xx_band_rate_to_idx;
+--- a/drivers/net/wireless/ti/wl18xx/wl18xx.h
++++ b/drivers/net/wireless/ti/wl18xx/wl18xx.h
+@@ -42,6 +42,8 @@
+
+ #define WL18XX_RX_BA_MAX_SESSIONS 5
+
++#define WL18XX_MAX_LINKS 12
++
+ struct wl18xx_priv {
+ /* buffer for sending commands to FW */
+ u8 cmd_buf[WL18XX_CMD_MAX_SIZE];
+@@ -114,7 +116,7 @@ struct wl18xx_fw_packet_counters {
+ u8 tx_released_pkts[NUM_TX_QUEUES];
+
+ /* Cumulative counter of freed packets per HLID */
+- u8 tx_lnk_free_pkts[WL12XX_MAX_LINKS];
++ u8 tx_lnk_free_pkts[WL18XX_MAX_LINKS];
+
+ /* Cumulative counter of released Voice memory blocks */
+ u8 tx_voice_released_blks;
+--- a/drivers/net/wireless/ti/wlcore/cmd.c
++++ b/drivers/net/wireless/ti/wlcore/cmd.c
+@@ -312,8 +312,8 @@ static int wlcore_get_new_session_id(str
+ int wl12xx_allocate_link(struct wl1271 *wl, struct wl12xx_vif *wlvif, u8 *hlid)
+ {
+ unsigned long flags;
+- u8 link = find_first_zero_bit(wl->links_map, WL12XX_MAX_LINKS);
+- if (link >= WL12XX_MAX_LINKS)
++ u8 link = find_first_zero_bit(wl->links_map, wl->num_links);
++ if (link >= wl->num_links)
+ return -EBUSY;
+
+ wl->session_ids[link] = wlcore_get_new_session_id(wl, link);
+--- a/drivers/net/wireless/ti/wlcore/event.c
++++ b/drivers/net/wireless/ti/wlcore/event.c
+@@ -68,7 +68,7 @@ static void wl1271_stop_ba_event(struct
+ u8 hlid;
+ struct wl1271_link *lnk;
+ for_each_set_bit(hlid, wlvif->ap.sta_hlid_map,
+- WL12XX_MAX_LINKS) {
++ wl->num_links) {
+ lnk = &wl->links[hlid];
+ if (!lnk->ba_bitmap)
+ continue;
+@@ -173,7 +173,7 @@ static void wlcore_disconnect_sta(struct
+ const u8 *addr;
+ int h;
+
+- for_each_set_bit(h, &sta_bitmap, WL12XX_MAX_LINKS) {
++ for_each_set_bit(h, &sta_bitmap, wl->num_links) {
+ bool found = false;
+ /* find the ap vif connected to this sta */
+ wl12xx_for_each_wlvif_ap(wl, wlvif) {
+--- a/drivers/net/wireless/ti/wlcore/main.c
++++ b/drivers/net/wireless/ti/wlcore/main.c
+@@ -372,7 +372,7 @@ static void wl12xx_irq_update_links_stat
+ wl->ap_fw_ps_map = cur_fw_ps_map;
+ }
+
+- for_each_set_bit(hlid, wlvif->ap.sta_hlid_map, WL12XX_MAX_LINKS)
++ for_each_set_bit(hlid, wlvif->ap.sta_hlid_map, wl->num_links)
+ wl12xx_irq_ps_regulate_link(wl, wlvif, hlid,
+ wl->links[hlid].allocated_pkts);
+ }
+@@ -412,7 +412,7 @@ static int wlcore_fw_status(struct wl127
+ }
+
+
+- for_each_set_bit(i, wl->links_map, WL12XX_MAX_LINKS) {
++ for_each_set_bit(i, wl->links_map, wl->num_links) {
+ u8 diff;
+ lnk = &wl->links[i];
+
+@@ -5888,7 +5888,7 @@ struct ieee80211_hw *wlcore_alloc_hw(siz
+ int i, j, ret;
+ unsigned int order;
+
+- BUILD_BUG_ON(AP_MAX_STATIONS > WL12XX_MAX_LINKS);
++ BUILD_BUG_ON(AP_MAX_STATIONS > WLCORE_MAX_LINKS);
+
+ hw = ieee80211_alloc_hw(sizeof(*wl), &wl1271_ops);
+ if (!hw) {
+@@ -5911,8 +5911,12 @@ struct ieee80211_hw *wlcore_alloc_hw(siz
+
+ wl->hw = hw;
+
++ /*
++ * wl->num_links is not configured yet, so just use WLCORE_MAX_LINKS.
++ * we don't allocate any additional resource here, so that's fine.
++ */
+ for (i = 0; i < NUM_TX_QUEUES; i++)
+- for (j = 0; j < WL12XX_MAX_LINKS; j++)
++ for (j = 0; j < WLCORE_MAX_LINKS; j++)
+ skb_queue_head_init(&wl->links[j].tx_queue[i]);
+
+ skb_queue_head_init(&wl->deferred_rx_queue);
+--- a/drivers/net/wireless/ti/wlcore/rx.c
++++ b/drivers/net/wireless/ti/wlcore/rx.c
+@@ -205,7 +205,7 @@ static int wl1271_rx_handle_data(struct
+
+ int wlcore_rx(struct wl1271 *wl, struct wl_fw_status *status)
+ {
+- unsigned long active_hlids[BITS_TO_LONGS(WL12XX_MAX_LINKS)] = {0};
++ unsigned long active_hlids[BITS_TO_LONGS(WLCORE_MAX_LINKS)] = {0};
+ u32 buf_size;
+ u32 fw_rx_counter = status->fw_rx_counter % wl->num_rx_desc;
+ u32 drv_rx_counter = wl->rx_counter % wl->num_rx_desc;
+@@ -263,12 +263,12 @@ int wlcore_rx(struct wl1271 *wl, struct
+ wl->aggr_buf + pkt_offset,
+ pkt_len, rx_align,
+ &hlid) == 1) {
+- if (hlid < WL12XX_MAX_LINKS)
++ if (hlid < wl->num_links)
+ __set_bit(hlid, active_hlids);
+ else
+ WARN(1,
+- "hlid exceeded WL12XX_MAX_LINKS "
+- "(%d)\n", hlid);
++ "hlid (%d) exceeded MAX_LINKS\n",
++ hlid);
+ }
+
+ wl->rx_counter++;
+--- a/drivers/net/wireless/ti/wlcore/tx.c
++++ b/drivers/net/wireless/ti/wlcore/tx.c
+@@ -565,11 +565,11 @@ static struct sk_buff *wlcore_vif_dequeu
+ int i, h, start_hlid;
+
+ /* start from the link after the last one */
+- start_hlid = (wlvif->last_tx_hlid + 1) % WL12XX_MAX_LINKS;
++ start_hlid = (wlvif->last_tx_hlid + 1) % wl->num_links;
+
+ /* dequeue according to AC, round robin on each link */
+- for (i = 0; i < WL12XX_MAX_LINKS; i++) {
+- h = (start_hlid + i) % WL12XX_MAX_LINKS;
++ for (i = 0; i < wl->num_links; i++) {
++ h = (start_hlid + i) % wl->num_links;
+
+ /* only consider connected stations */
+ if (!test_bit(h, wlvif->links_map))
+@@ -693,8 +693,8 @@ static void wl1271_skb_queue_head(struct
+ skb_queue_head(&wl->links[hlid].tx_queue[q], skb);
+
+ /* make sure we dequeue the same packet next time */
+- wlvif->last_tx_hlid = (hlid + WL12XX_MAX_LINKS - 1) %
+- WL12XX_MAX_LINKS;
++ wlvif->last_tx_hlid = (hlid + wl->num_links - 1) %
++ wl->num_links;
+ }
+
+ spin_lock_irqsave(&wl->wl_lock, flags);
+@@ -727,7 +727,7 @@ void wl12xx_rearm_rx_streaming(struct wl
+ timeout = wl->conf.rx_streaming.duration;
+ wl12xx_for_each_wlvif_sta(wl, wlvif) {
+ bool found = false;
+- for_each_set_bit(hlid, active_hlids, WL12XX_MAX_LINKS) {
++ for_each_set_bit(hlid, active_hlids, wl->num_links) {
+ if (test_bit(hlid, wlvif->links_map)) {
+ found = true;
+ break;
+@@ -764,7 +764,7 @@ int wlcore_tx_work_locked(struct wl1271
+ struct wl1271_tx_hw_descr *desc;
+ u32 buf_offset = 0, last_len = 0;
+ bool sent_packets = false;
+- unsigned long active_hlids[BITS_TO_LONGS(WL12XX_MAX_LINKS)] = {0};
++ unsigned long active_hlids[BITS_TO_LONGS(WLCORE_MAX_LINKS)] = {0};
+ int ret = 0;
+ int bus_ret = 0;
+ u8 hlid;
+@@ -1066,7 +1066,7 @@ void wl12xx_tx_reset_wlvif(struct wl1271
+ int i;
+
+ /* TX failure */
+- for_each_set_bit(i, wlvif->links_map, WL12XX_MAX_LINKS) {
++ for_each_set_bit(i, wlvif->links_map, wl->num_links) {
+ if (wlvif->bss_type == BSS_TYPE_AP_BSS &&
+ i != wlvif->ap.bcast_hlid && i != wlvif->ap.global_hlid) {
+ /* this calls wl12xx_free_link */
+@@ -1090,7 +1090,7 @@ void wl12xx_tx_reset(struct wl1271 *wl)
+
+ /* only reset the queues if something bad happened */
+ if (wl1271_tx_total_queue_count(wl) != 0) {
+- for (i = 0; i < WL12XX_MAX_LINKS; i++)
++ for (i = 0; i < wl->num_links; i++)
+ wl1271_tx_reset_link_queues(wl, i);
+
+ for (i = 0; i < NUM_TX_QUEUES; i++)
+@@ -1183,7 +1183,7 @@ void wl1271_tx_flush(struct wl1271 *wl)
+ WL1271_TX_FLUSH_TIMEOUT / 1000);
+
+ /* forcibly flush all Tx buffers on our queues */
+- for (i = 0; i < WL12XX_MAX_LINKS; i++)
++ for (i = 0; i < wl->num_links; i++)
+ wl1271_tx_reset_link_queues(wl, i);
+
+ out_wake:
+--- a/drivers/net/wireless/ti/wlcore/wlcore.h
++++ b/drivers/net/wireless/ti/wlcore/wlcore.h
+@@ -224,7 +224,7 @@ struct wl1271 {
+ int channel;
+ u8 system_hlid;
+
+- unsigned long links_map[BITS_TO_LONGS(WL12XX_MAX_LINKS)];
++ unsigned long links_map[BITS_TO_LONGS(WLCORE_MAX_LINKS)];
+ unsigned long roles_map[BITS_TO_LONGS(WL12XX_MAX_ROLES)];
+ unsigned long roc_map[BITS_TO_LONGS(WL12XX_MAX_ROLES)];
+ unsigned long rate_policies_map[
+@@ -232,7 +232,7 @@ struct wl1271 {
+ unsigned long klv_templates_map[
+ BITS_TO_LONGS(WLCORE_MAX_KLV_TEMPLATES)];
+
+- u8 session_ids[WL12XX_MAX_LINKS];
++ u8 session_ids[WLCORE_MAX_LINKS];
+
+ struct list_head wlvif_list;
+
+@@ -380,7 +380,7 @@ struct wl1271 {
+ * AP-mode - links indexed by HLID. The global and broadcast links
+ * are always active.
+ */
+- struct wl1271_link links[WL12XX_MAX_LINKS];
++ struct wl1271_link links[WLCORE_MAX_LINKS];
+
+ /* number of currently active links */
+ int active_link_count;
+@@ -438,6 +438,8 @@ struct wl1271 {
+ u32 num_tx_desc;
+ /* number of RX descriptors the HW supports. */
+ u32 num_rx_desc;
++ /* number of links the HW supports */
++ u8 num_links;
+
+ /* translate HW Tx rates to standard rate-indices */
+ const u8 **band_rate_to_idx;
+--- a/drivers/net/wireless/ti/wlcore/wlcore_i.h
++++ b/drivers/net/wireless/ti/wlcore/wlcore_i.h
+@@ -58,10 +58,15 @@
+ #define WL1271_DEFAULT_DTIM_PERIOD 1
+
+ #define WL12XX_MAX_ROLES 4
+-#define WL12XX_MAX_LINKS 12
+ #define WL12XX_INVALID_ROLE_ID 0xff
+ #define WL12XX_INVALID_LINK_ID 0xff
+
++/*
++ * max number of links allowed by all HWs.
++ * this is NOT the actual max links supported by the current hw.
++ */
++#define WLCORE_MAX_LINKS 12
++
+ /* the driver supports the 2.4Ghz and 5Ghz bands */
+ #define WLCORE_NUM_BANDS 2
+
+@@ -156,7 +161,7 @@ struct wl_fw_status {
+
+ /*
+ * Cumulative counter of freed packets per HLID
+- * (length of the array is WL12XX_MAX_LINKS)
++ * (length of the array is wl->num_links)
+ */
+ u8 *tx_lnk_free_pkts;
+
+@@ -357,7 +362,7 @@ struct wl12xx_vif {
+
+ /* HLIDs bitmap of associated stations */
+ unsigned long sta_hlid_map[BITS_TO_LONGS(
+- WL12XX_MAX_LINKS)];
++ WLCORE_MAX_LINKS)];
+
+ /* recoreded keys - set here before AP startup */
+ struct wl1271_ap_key *recorded_keys[MAX_NUM_KEYS];
+@@ -374,7 +379,7 @@ struct wl12xx_vif {
+ /* counters of packets per AC, across all links in the vif */
+ int tx_queue_count[NUM_TX_QUEUES];
+
+- unsigned long links_map[BITS_TO_LONGS(WL12XX_MAX_LINKS)];
++ unsigned long links_map[BITS_TO_LONGS(WLCORE_MAX_LINKS)];
+
+ u8 ssid[IEEE80211_MAX_SSID_LEN + 1];
+ u8 ssid_len;