wl12xx: add set_rate_mgmt_params acx
[pandora-kernel.git] / drivers / net / wireless / wl12xx / main.c
index e58c22d..3db191d 100644 (file)
@@ -379,6 +379,27 @@ static struct conf_drv_settings default_conf = {
                .threshold                    = 0,
        },
        .hci_io_ds = HCI_IO_DS_6MA,
+       .rate = {
+               .rate_retry_score = 32000,
+               .per_add = 8192,
+               .per_th1 = 2048,
+               .per_th2 = 4096,
+               .max_per = 8100,
+               .inverse_curiosity_factor = 5,
+               .tx_fail_low_th = 4,
+               .tx_fail_high_th = 10,
+               .per_alpha_shift = 4,
+               .per_add_shift = 13,
+               .per_beta1_shift = 10,
+               .per_beta2_shift = 8,
+               .rate_check_up = 2,
+               .rate_check_down = 12,
+               .rate_retry_policy = {
+                       0x00, 0x00, 0x00, 0x00, 0x00,
+                       0x00, 0x00, 0x00, 0x00, 0x00,
+                       0x00, 0x00, 0x00,
+               },
+       },
 };
 
 static char *fwlog_param;
@@ -415,7 +436,7 @@ static int wl1271_check_operstate(struct wl1271 *wl, unsigned char operstate)
        if (test_and_set_bit(WL1271_FLAG_STA_STATE_SENT, &wl->flags))
                return 0;
 
-       ret = wl1271_cmd_set_sta_state(wl);
+       ret = wl12xx_cmd_set_peer_state(wl);
        if (ret < 0)
                return ret;
 
@@ -718,7 +739,7 @@ static int wl1271_plt_init(struct wl1271 *wl)
        if (ret < 0)
                goto out_free_memmap;
 
-       ret = wl1271_acx_sta_mem_cfg(wl);
+       ret = wl12xx_acx_mem_cfg(wl);
        if (ret < 0)
                goto out_free_memmap;
 
@@ -773,6 +794,7 @@ static int wl1271_plt_init(struct wl1271 *wl)
        return ret;
 }
 
+#if 0
 static void wl1271_irq_ps_regulate_link(struct wl1271 *wl, u8 hlid, u8 tx_blks)
 {
        bool fw_ps;
@@ -823,34 +845,16 @@ static void wl1271_irq_update_links_status(struct wl1271 *wl,
                                            wl->links[hlid].allocated_blks);
        }
 }
+#endif
 
-static u32 wl1271_tx_allocated_blocks(struct wl1271 *wl)
-{
-       int i;
-       u32 total_alloc_blocks = 0;
-
-       for (i = 0; i < NUM_TX_QUEUES; i++)
-               total_alloc_blocks += wl->tx_allocated_blocks[i];
-
-       return total_alloc_blocks;
-}
-
-static void wl1271_fw_status(struct wl1271 *wl,
-                            struct wl1271_fw_full_status *full_status)
+static void wl12xx_fw_status(struct wl1271 *wl,
+                            struct wl12xx_fw_status *status)
 {
-       struct wl1271_fw_common_status *status = &full_status->common;
        struct timespec ts;
        u32 old_tx_blk_count = wl->tx_blocks_available;
-       u32 freed_blocks = 0, ac_freed_blocks;
-       int i;
+       int avail, freed_blocks;
 
-       if (wl->bss_type == BSS_TYPE_AP_BSS) {
-               wl1271_raw_read(wl, FW_STATUS_ADDR, status,
-                               sizeof(struct wl1271_fw_ap_status), false);
-       } else {
-               wl1271_raw_read(wl, FW_STATUS_ADDR, status,
-                               sizeof(struct wl1271_fw_sta_status), false);
-       }
+       wl1271_raw_read(wl, FW_STATUS_ADDR, status, sizeof(*status), false);
 
        wl1271_debug(DEBUG_IRQ, "intr: 0x%x (fw_rx_counter = %d, "
                     "drv_rx_counter = %d, tx_results_counter = %d)",
@@ -859,42 +863,36 @@ static void wl1271_fw_status(struct wl1271 *wl,
                     status->drv_rx_counter,
                     status->tx_results_counter);
 
-       /* update number of available TX blocks */
-       for (i = 0; i < NUM_TX_QUEUES; i++) {
-               ac_freed_blocks = le32_to_cpu(status->tx_released_blks[i]) -
-                                 wl->tx_blocks_freed[i];
-               freed_blocks += ac_freed_blocks;
+       freed_blocks = le32_to_cpu(status->total_released_blks) -
+                      wl->tx_blocks_freed;
+       wl->tx_blocks_freed = le32_to_cpu(status->total_released_blks);
 
-               wl->tx_allocated_blocks[i] -= ac_freed_blocks;
+       wl->tx_allocated_blocks -= freed_blocks;
 
-               wl->tx_blocks_freed[i] =
-                       le32_to_cpu(status->tx_released_blks[i]);
-       }
+       avail = le32_to_cpu(status->tx_total) - wl->tx_allocated_blocks;
 
-       if (wl->bss_type == BSS_TYPE_AP_BSS) {
-               /* Update num of allocated TX blocks per link and ps status */
-               wl1271_irq_update_links_status(wl, &full_status->ap);
-               wl->tx_blocks_available += freed_blocks;
-       } else {
-               int avail = full_status->sta.tx_total -
-                           wl1271_tx_allocated_blocks(wl);
-
-               /*
-                * The FW might change the total number of TX memblocks before
-                * we get a notification about blocks being released. Thus, the
-                * available blocks calculation might yield a temporary result
-                * which is lower than the actual available blocks. Keeping in
-                * mind that only blocks that were allocated can be moved from
-                * TX to RX, tx_blocks_available should never decrease here.
-                */
-               wl->tx_blocks_available = max((int)wl->tx_blocks_available,
-                                             avail);
-       }
+       /*
+        * The FW might change the total number of TX memblocks before
+        * we get a notification about blocks being released. Thus, the
+        * available blocks calculation might yield a temporary result
+        * which is lower than the actual available blocks. Keeping in
+        * mind that only blocks that were allocated can be moved from
+        * TX to RX, tx_blocks_available should never decrease here.
+        */
+       wl->tx_blocks_available = max((int)wl->tx_blocks_available,
+                                     avail);
 
        /* if more blocks are available now, tx work can be scheduled */
        if (wl->tx_blocks_available > old_tx_blk_count)
                clear_bit(WL1271_FLAG_FW_TX_BUSY, &wl->flags);
 
+       /* for AP update num of allocated TX blocks per link and ps status */
+       if (wl->bss_type == BSS_TYPE_AP_BSS) {
+#if 0
+               wl1271_irq_update_links_status(wl, status);
+#endif
+       }
+
        /* update the host-chipset time offset */
        getnstimeofday(&ts);
        wl->time_offset = (timespec_to_ns(&ts) >> 10) -
@@ -967,8 +965,8 @@ irqreturn_t wl1271_irq(int irq, void *cookie)
                clear_bit(WL1271_FLAG_IRQ_RUNNING, &wl->flags);
                smp_mb__after_clear_bit();
 
-               wl1271_fw_status(wl, wl->fw_status);
-               intr = le32_to_cpu(wl->fw_status->common.intr);
+               wl12xx_fw_status(wl, wl->fw_status);
+               intr = le32_to_cpu(wl->fw_status->intr);
                intr &= WL1271_INTR_MASK;
                if (!intr) {
                        done = true;
@@ -987,7 +985,7 @@ irqreturn_t wl1271_irq(int irq, void *cookie)
                if (likely(intr & WL1271_ACX_INTR_DATA)) {
                        wl1271_debug(DEBUG_IRQ, "WL1271_ACX_INTR_DATA");
 
-                       wl1271_rx(wl, &wl->fw_status->common);
+                       wl12xx_rx(wl, wl->fw_status);
 
                        /* Check if any tx blocks were freed */
                        spin_lock_irqsave(&wl->wl_lock, flags);
@@ -1004,7 +1002,7 @@ irqreturn_t wl1271_irq(int irq, void *cookie)
                        }
 
                        /* check for tx results */
-                       if (wl->fw_status->common.tx_results_counter !=
+                       if (wl->fw_status->tx_results_counter !=
                            (wl->tx_results_count & 0xff))
                                wl1271_tx_complete(wl);
 
@@ -1056,25 +1054,10 @@ static int wl1271_fetch_firmware(struct wl1271 *wl)
        const char *fw_name;
        int ret;
 
-       switch (wl->bss_type) {
-       case BSS_TYPE_AP_BSS:
-               if (wl->chip.id == CHIP_ID_1283_PG20)
-                       fw_name = WL128X_AP_FW_NAME;
-               else
-                       fw_name = WL127X_AP_FW_NAME;
-               break;
-       case BSS_TYPE_IBSS:
-       case BSS_TYPE_STA_BSS:
-               if (wl->chip.id == CHIP_ID_1283_PG20)
-                       fw_name = WL128X_FW_NAME;
-               else
-                       fw_name = WL1271_FW_NAME;
-               break;
-       default:
-               wl1271_error("no compatible firmware for bss_type %d",
-                            wl->bss_type);
-               return -EINVAL;
-       }
+       if (wl->chip.id == CHIP_ID_1283_PG20)
+               fw_name = WL128X_FW_NAME;
+       else
+               fw_name = WL127X_FW_NAME;
 
        wl1271_debug(DEBUG_BOOT, "booting firmware %s", fw_name);
 
@@ -1103,7 +1086,6 @@ static int wl1271_fetch_firmware(struct wl1271 *wl)
        }
 
        memcpy(wl->fw, fw->data, wl->fw_len);
-       wl->fw_bss_type = wl->bss_type;
        ret = 0;
 
 out:
@@ -1194,8 +1176,8 @@ static void wl12xx_read_fwlog_panic(struct wl1271 *wl)
                wl12xx_cmd_stop_fwlog(wl);
 
        /* Read the first memory block address */
-       wl1271_fw_status(wl, wl->fw_status);
-       first_addr = __le32_to_cpu(wl->fw_status->sta.log_start_addr);
+       wl12xx_fw_status(wl, wl->fw_status);
+       first_addr = le32_to_cpu(wl->fw_status->log_start_addr);
        if (!first_addr)
                goto out;
 
@@ -1211,7 +1193,7 @@ static void wl12xx_read_fwlog_panic(struct wl1271 *wl)
                 * of each memory block hold the hardware address of the next
                 * one. The last memory block points to the first one.
                 */
-               addr = __le32_to_cpup((__le32 *)block);
+               addr = le32_to_cpup((__le32 *)block);
                if (!wl12xx_copy_fwlog(wl, block + sizeof(addr),
                                       WL12XX_HW_BLOCK_SIZE - sizeof(addr)))
                        break;
@@ -1374,8 +1356,7 @@ static int wl1271_chip_wakeup(struct wl1271 *wl)
                goto out;
        }
 
-       /* Make sure the firmware type matches the BSS type */
-       if (wl->fw == NULL || wl->fw_bss_type != wl->bss_type) {
+       if (wl->fw == NULL) {
                ret = wl1271_fetch_firmware(wl);
                if (ret < 0)
                        goto out;
@@ -1395,6 +1376,7 @@ out:
 int wl1271_plt_start(struct wl1271 *wl)
 {
        int retries = WL1271_BOOT_RETRIES;
+       struct wiphy *wiphy = wl->hw->wiphy;
        int ret;
 
        mutex_lock(&wl->mutex);
@@ -1428,6 +1410,11 @@ int wl1271_plt_start(struct wl1271 *wl)
                wl1271_notice("firmware booted in PLT mode (%s)",
                              wl->chip.fw_ver_str);
 
+               /* update hw/fw version info in wiphy struct */
+               wiphy->hw_version = wl->chip.id;
+               strncpy(wiphy->fw_version, wl->chip.fw_ver_str,
+                       sizeof(wiphy->fw_version));
+
                goto out;
 
 irq_disable:
@@ -1673,7 +1660,7 @@ static int wl1271_configure_suspend_ap(struct wl1271 *wl)
        if (ret < 0)
                goto out_unlock;
 
-       ret = wl1271_acx_set_ap_beacon_filter(wl, true);
+       ret = wl1271_acx_beacon_filter_opt(wl, true);
 
        wl1271_ps_elp_sleep(wl);
 out_unlock:
@@ -1711,7 +1698,7 @@ static void wl1271_configure_resume(struct wl1271 *wl)
                        wl1271_ps_set_mode(wl, STATION_ACTIVE_MODE,
                                           wl->basic_rate, true);
        } else if (is_ap) {
-               wl1271_acx_set_ap_beacon_filter(wl, false);
+               wl1271_acx_beacon_filter_opt(wl, false);
        }
 
        wl1271_ps_elp_sleep(wl);
@@ -1803,9 +1790,6 @@ static int wl1271_op_start(struct ieee80211_hw *hw)
         *
         * The MAC address is first known when the corresponding interface
         * is added. That is where we will initialize the hardware.
-        *
-        * In addition, we currently have different firmwares for AP and managed
-        * operation. We will know which to boot according to interface type.
         */
 
        return 0;
@@ -1816,6 +1800,21 @@ static void wl1271_op_stop(struct ieee80211_hw *hw)
        wl1271_debug(DEBUG_MAC80211, "mac80211 stop");
 }
 
+static u8 wl12xx_get_role_type(struct wl1271 *wl)
+{
+       switch (wl->bss_type) {
+       case BSS_TYPE_AP_BSS:
+               return WL1271_ROLE_AP;
+
+       case BSS_TYPE_STA_BSS:
+               return WL1271_ROLE_STA;
+
+       default:
+               wl1271_error("invalid bss_type: %d", wl->bss_type);
+       }
+       return WL12XX_INVALID_ROLE_TYPE;
+}
+
 static int wl1271_op_add_interface(struct ieee80211_hw *hw,
                                   struct ieee80211_vif *vif)
 {
@@ -1823,6 +1822,7 @@ static int wl1271_op_add_interface(struct ieee80211_hw *hw,
        struct wiphy *wiphy = hw->wiphy;
        int retries = WL1271_BOOT_RETRIES;
        int ret = 0;
+       u8 role_type;
        bool booted = false;
 
        wl1271_debug(DEBUG_MAC80211, "mac80211 add interface type %d mac %pM",
@@ -1863,6 +1863,11 @@ static int wl1271_op_add_interface(struct ieee80211_hw *hw,
                goto out;
        }
 
+       role_type = wl12xx_get_role_type(wl);
+       if (role_type == WL12XX_INVALID_ROLE_TYPE) {
+               ret = -EINVAL;
+               goto out;
+       }
        memcpy(wl->mac_addr, vif->addr, ETH_ALEN);
 
        if (wl->state != WL1271_STATE_OFF) {
@@ -1882,6 +1887,24 @@ static int wl1271_op_add_interface(struct ieee80211_hw *hw,
                if (ret < 0)
                        goto power_off;
 
+               if (wl->bss_type == BSS_TYPE_STA_BSS) {
+                       /*
+                        * The device role is a special role used for
+                        * rx and tx frames prior to association (as
+                        * the STA role can get packets only from
+                        * its associated bssid)
+                        */
+                       ret = wl12xx_cmd_role_enable(wl,
+                                                        WL1271_ROLE_DEVICE,
+                                                        &wl->dev_role_id);
+                       if (ret < 0)
+                               goto irq_disable;
+               }
+
+               ret = wl12xx_cmd_role_enable(wl, role_type, &wl->role_id);
+               if (ret < 0)
+                       goto irq_disable;
+
                ret = wl1271_hw_init(wl);
                if (ret < 0)
                        goto irq_disable;
@@ -1946,7 +1969,7 @@ out:
 static void __wl1271_op_remove_interface(struct wl1271 *wl,
                                         bool reset_tx_queues)
 {
-       int i;
+       int ret;
 
        wl1271_debug(DEBUG_MAC80211, "mac80211 remove interface");
 
@@ -1971,6 +1994,28 @@ static void __wl1271_op_remove_interface(struct wl1271 *wl,
                ieee80211_scan_completed(wl->hw, true);
        }
 
+       if (!test_bit(WL1271_FLAG_RECOVERY_IN_PROGRESS, &wl->flags)) {
+               /* disable active roles */
+               ret = wl1271_ps_elp_wakeup(wl);
+               if (ret < 0)
+                       goto deinit;
+
+               if (wl->bss_type == BSS_TYPE_STA_BSS) {
+                       ret = wl12xx_cmd_role_disable(wl, &wl->dev_role_id);
+                       if (ret < 0)
+                               goto deinit;
+               }
+
+               ret = wl12xx_cmd_role_disable(wl, &wl->role_id);
+               if (ret < 0)
+                       goto deinit;
+
+               wl1271_ps_elp_sleep(wl);
+       }
+deinit:
+       wl->sta_hlid = WL12XX_INVALID_LINK_ID;
+       wl->dev_hlid = WL12XX_INVALID_LINK_ID;
+
        /*
         * this must be before the cancel_work calls below, so that the work
         * functions don't perform further work.
@@ -1997,7 +2042,7 @@ static void __wl1271_op_remove_interface(struct wl1271 *wl,
        wl1271_power_off(wl);
 
        memset(wl->bssid, 0, ETH_ALEN);
-       memset(wl->ssid, 0, IW_ESSID_MAX_SIZE + 1);
+       memset(wl->ssid, 0, IEEE80211_MAX_SSID_LEN + 1);
        wl->ssid_len = 0;
        wl->bss_type = MAX_BSS_TYPE;
        wl->set_bss_type = MAX_BSS_TYPE;
@@ -2007,18 +2052,22 @@ static void __wl1271_op_remove_interface(struct wl1271 *wl,
        wl->psm_entry_retry = 0;
        wl->power_level = WL1271_DEFAULT_POWER_LEVEL;
        wl->tx_blocks_available = 0;
+       wl->tx_allocated_blocks = 0;
        wl->tx_results_count = 0;
        wl->tx_packets_count = 0;
        wl->time_offset = 0;
        wl->session_counter = 0;
        wl->rate_set = CONF_TX_RATE_MASK_BASIC;
        wl->vif = NULL;
-       wl->filters = 0;
        wl1271_free_ap_keys(wl);
        memset(wl->ap_hlid_map, 0, sizeof(wl->ap_hlid_map));
        wl->ap_fw_ps_map = 0;
        wl->ap_ps_map = 0;
        wl->sched_scanning = false;
+       wl->role_id = WL12XX_INVALID_ROLE_ID;
+       wl->dev_role_id = WL12XX_INVALID_ROLE_ID;
+       memset(wl->roles_map, 0, sizeof(wl->roles_map));
+       memset(wl->links_map, 0, sizeof(wl->links_map));
 
        /*
         * this is performed after the cancel_work calls and the associated
@@ -2027,10 +2076,7 @@ static void __wl1271_op_remove_interface(struct wl1271 *wl,
         */
        wl->flags = 0;
 
-       for (i = 0; i < NUM_TX_QUEUES; i++) {
-               wl->tx_blocks_freed[i] = 0;
-               wl->tx_allocated_blocks[i] = 0;
-       }
+       wl->tx_blocks_freed = 0;
 
        wl1271_debugfs_reset(wl);
 
@@ -2061,39 +2107,6 @@ static void wl1271_op_remove_interface(struct ieee80211_hw *hw,
        cancel_work_sync(&wl->recovery_work);
 }
 
-void wl1271_configure_filters(struct wl1271 *wl, unsigned int filters)
-{
-       wl1271_set_default_filters(wl);
-
-       /* combine requested filters with current filter config */
-       filters = wl->filters | filters;
-
-       wl1271_debug(DEBUG_FILTERS, "RX filters set: ");
-
-       if (filters & FIF_PROMISC_IN_BSS) {
-               wl1271_debug(DEBUG_FILTERS, " - FIF_PROMISC_IN_BSS");
-               wl->rx_config &= ~CFG_UNI_FILTER_EN;
-               wl->rx_config |= CFG_BSSID_FILTER_EN;
-       }
-       if (filters & FIF_BCN_PRBRESP_PROMISC) {
-               wl1271_debug(DEBUG_FILTERS, " - FIF_BCN_PRBRESP_PROMISC");
-               wl->rx_config &= ~CFG_BSSID_FILTER_EN;
-               wl->rx_config &= ~CFG_SSID_FILTER_EN;
-       }
-       if (filters & FIF_OTHER_BSS) {
-               wl1271_debug(DEBUG_FILTERS, " - FIF_OTHER_BSS");
-               wl->rx_config &= ~CFG_BSSID_FILTER_EN;
-       }
-       if (filters & FIF_CONTROL) {
-               wl1271_debug(DEBUG_FILTERS, " - FIF_CONTROL");
-               wl->rx_filter |= CFG_RX_CTL_EN;
-       }
-       if (filters & FIF_FCSFAIL) {
-               wl1271_debug(DEBUG_FILTERS, " - FIF_FCSFAIL");
-               wl->rx_filter |= CFG_RX_FCS_ERROR;
-       }
-}
-
 static int wl1271_dummy_join(struct wl1271 *wl)
 {
        int ret = 0;
@@ -2103,10 +2116,7 @@ static int wl1271_dummy_join(struct wl1271 *wl)
 
        memcpy(wl->bssid, dummy_bssid, ETH_ALEN);
 
-       /* pass through frames from all BSS */
-       wl1271_configure_filters(wl, FIF_OTHER_BSS);
-
-       ret = wl1271_cmd_join(wl, wl->set_bss_type);
+       ret = wl12xx_cmd_role_start_sta(wl);
        if (ret < 0)
                goto out;
 
@@ -2135,7 +2145,7 @@ static int wl1271_join(struct wl1271 *wl, bool set_assoc)
        if (set_assoc)
                set_bit(WL1271_FLAG_STA_ASSOCIATED, &wl->flags);
 
-       ret = wl1271_cmd_join(wl, wl->set_bss_type);
+       ret = wl12xx_cmd_role_start_sta(wl);
        if (ret < 0)
                goto out;
 
@@ -2176,7 +2186,7 @@ static int wl1271_unjoin(struct wl1271 *wl)
        int ret;
 
        /* to stop listening to a channel, we disconnect */
-       ret = wl1271_cmd_disconnect(wl);
+       ret = wl12xx_cmd_role_stop_sta(wl);
        if (ret < 0)
                goto out;
 
@@ -2187,9 +2197,6 @@ static int wl1271_unjoin(struct wl1271 *wl)
        wl->tx_security_last_seq_lsb = 0;
        wl->tx_security_seq = 0;
 
-       /* stop filtering packets based on bssid */
-       wl1271_configure_filters(wl, FIF_OTHER_BSS);
-
 out:
        return ret;
 }
@@ -2458,18 +2465,11 @@ static void wl1271_op_configure_filter(struct ieee80211_hw *hw,
                        goto out_sleep;
        }
 
-       /* determine, whether supported filter values have changed */
-       if (changed == 0)
-               goto out_sleep;
-
-       /* configure filters */
-       wl->filters = *total;
-       wl1271_configure_filters(wl, 0);
-
-       /* apply configured filters */
-       ret = wl1271_acx_rx_config(wl, wl->rx_config, wl->rx_filter);
-       if (ret < 0)
-               goto out_sleep;
+       /*
+        * the fw doesn't provide an api to configure the filters. instead,
+        * the filters configuration is based on the active roles / ROC
+        * state.
+        */
 
 out_sleep:
        wl1271_ps_elp_sleep(wl);
@@ -2558,7 +2558,8 @@ static int wl1271_ap_init_hwenc(struct wl1271 *wl)
        }
 
        if (wep_key_added) {
-               ret = wl1271_cmd_set_ap_default_wep_key(wl, wl->default_key);
+               ret = wl12xx_cmd_set_default_wep_key(wl, wl->default_key,
+                                                    WL1271_AP_BROADCAST_HLID);
                if (ret < 0)
                        goto out;
        }
@@ -2636,8 +2637,9 @@ static int wl1271_set_key(struct wl1271 *wl, u16 action, u8 id, u8 key_type,
 
                /* the default WEP key needs to be configured at least once */
                if (key_type == KEY_WEP) {
-                       ret = wl1271_cmd_set_sta_default_wep_key(wl,
-                                                       wl->default_key);
+                       ret = wl12xx_cmd_set_default_wep_key(wl,
+                                                            wl->default_key,
+                                                            wl->sta_hlid);
                        if (ret < 0)
                                return ret;
                }
@@ -3094,7 +3096,7 @@ static void wl1271_bss_info_changed_ap(struct wl1271 *wl,
        if ((changed & BSS_CHANGED_BEACON_ENABLED)) {
                if (bss_conf->enable_beacon) {
                        if (!test_bit(WL1271_FLAG_AP_STARTED, &wl->flags)) {
-                               ret = wl1271_cmd_start_bss(wl);
+                               ret = wl12xx_cmd_role_start_ap(wl);
                                if (ret < 0)
                                        goto out;
 
@@ -3107,7 +3109,7 @@ static void wl1271_bss_info_changed_ap(struct wl1271 *wl,
                        }
                } else {
                        if (test_bit(WL1271_FLAG_AP_STARTED, &wl->flags)) {
-                               ret = wl1271_cmd_stop_bss(wl);
+                               ret = wl12xx_cmd_role_stop_ap(wl);
                                if (ret < 0)
                                        goto out;
 
@@ -3192,9 +3194,6 @@ static void wl1271_bss_info_changed_sta(struct wl1271 *wl,
                        if (ret < 0)
                                goto out;
 
-                       /* filter out all packets not from this BSSID */
-                       wl1271_configure_filters(wl, 0);
-
                        /* Need to update the BSSID (for filtering etc) */
                        do_join = true;
                }
@@ -3621,7 +3620,7 @@ static int wl1271_op_sta_add(struct ieee80211_hw *hw,
        if (ret < 0)
                goto out_free_sta;
 
-       ret = wl1271_cmd_add_sta(wl, sta, hlid);
+       ret = wl12xx_cmd_add_peer(wl, sta, hlid);
        if (ret < 0)
                goto out_sleep;
 
@@ -3664,7 +3663,7 @@ static int wl1271_op_sta_remove(struct ieee80211_hw *hw,
        if (ret < 0)
                goto out;
 
-       ret = wl1271_cmd_remove_sta(wl, wl_sta->hlid);
+       ret = wl12xx_cmd_remove_peer(wl, wl_sta->hlid);
        if (ret < 0)
                goto out_sleep;
 
@@ -4126,7 +4125,7 @@ static ssize_t wl1271_sysfs_show_hw_pg_ver(struct device *dev,
        return len;
 }
 
-static DEVICE_ATTR(hw_pg_ver, S_IRUGO | S_IWUSR,
+static DEVICE_ATTR(hw_pg_ver, S_IRUGO,
                   wl1271_sysfs_show_hw_pg_ver, NULL);
 
 static ssize_t wl1271_sysfs_read_fwlog(struct file *filp, struct kobject *kobj,
@@ -4288,7 +4287,7 @@ int wl1271_init_ieee80211(struct wl1271 *wl)
         * should be the maximum length possible for a template, without
         * the IEEE80211 header of the template
         */
-       wl->hw->wiphy->max_scan_ie_len = WL1271_CMD_TEMPL_MAX_SIZE -
+       wl->hw->wiphy->max_scan_ie_len = WL1271_CMD_TEMPL_DFLT_SIZE -
                        sizeof(struct ieee80211_header);
 
        /* make sure all our channels fit in the scanned_ch bitmask */
@@ -4387,8 +4386,6 @@ struct ieee80211_hw *wl1271_alloc_hw(void)
        wl->beacon_int = WL1271_DEFAULT_BEACON_INT;
        wl->default_key = 0;
        wl->rx_counter = 0;
-       wl->rx_config = WL1271_DEFAULT_STA_RX_CONFIG;
-       wl->rx_filter = WL1271_DEFAULT_STA_RX_FILTER;
        wl->psm_entry_retry = 0;
        wl->power_level = WL1271_DEFAULT_POWER_LEVEL;
        wl->basic_rate_set = CONF_TX_RATE_MASK_BASIC;
@@ -4401,7 +4398,6 @@ struct ieee80211_hw *wl1271_alloc_hw(void)
        wl->hw_pg_ver = -1;
        wl->bss_type = MAX_BSS_TYPE;
        wl->set_bss_type = MAX_BSS_TYPE;
-       wl->fw_bss_type = MAX_BSS_TYPE;
        wl->last_tx_hlid = 0;
        wl->ap_ps_map = 0;
        wl->ap_fw_ps_map = 0;
@@ -4410,7 +4406,10 @@ struct ieee80211_hw *wl1271_alloc_hw(void)
        wl->sched_scanning = false;
        wl->tx_security_seq = 0;
        wl->tx_security_last_seq_lsb = 0;
-
+       wl->role_id = WL12XX_INVALID_ROLE_ID;
+       wl->sta_hlid = WL12XX_INVALID_LINK_ID;
+       wl->dev_role_id = WL12XX_INVALID_ROLE_ID;
+       wl->dev_hlid = WL12XX_INVALID_LINK_ID;
        setup_timer(&wl->rx_streaming_timer, wl1271_rx_streaming_timer,
                    (unsigned long) wl);
        wl->fwlog_size = 0;
@@ -4522,6 +4521,10 @@ int wl1271_free_hw(struct wl1271 *wl)
        mutex_unlock(&wl->mutex);
 
        device_remove_bin_file(&wl->plat_dev->dev, &fwlog_attr);
+
+       device_remove_file(&wl->plat_dev->dev, &dev_attr_hw_pg_ver);
+
+       device_remove_file(&wl->plat_dev->dev, &dev_attr_bt_coex_state);
        platform_device_unregister(wl->plat_dev);
        free_page((unsigned long)wl->fwlog);
        dev_kfree_skb(wl->dummy_packet);