Commit 536129c8 authored by Eliad Peller's avatar Eliad Peller Committed by Luciano Coelho

wl12xx: move bss_type into wlvif

move bss_type into the per-interface data, rather than
being global.
Signed-off-by: default avatarEliad Peller <eliad@wizery.com>
Signed-off-by: default avatarLuciano Coelho <coelho@ti.com>
parent cdf09495
......@@ -1042,7 +1042,7 @@ int wl12xx_cmd_build_null_data(struct wl1271 *wl, struct wl12xx_vif *wlvif)
int ret = -ENOMEM;
if (wl->bss_type == BSS_TYPE_IBSS) {
if (wlvif->bss_type == BSS_TYPE_IBSS) {
size = sizeof(struct wl12xx_null_data_template);
ptr = NULL;
} else {
......
......@@ -350,7 +350,6 @@ static ssize_t driver_state_read(struct file *file, char __user *user_buf,
DRIVER_STATE_PRINT_INT(rx_counter);
DRIVER_STATE_PRINT_INT(session_counter);
DRIVER_STATE_PRINT_INT(state);
DRIVER_STATE_PRINT_INT(bss_type);
DRIVER_STATE_PRINT_INT(channel);
DRIVER_STATE_PRINT_INT(band);
DRIVER_STATE_PRINT_INT(beacon_int);
......
......@@ -178,9 +178,9 @@ static void wl1271_event_rssi_trigger(struct wl1271 *wl,
wl->last_rssi_event = event;
}
static void wl1271_stop_ba_event(struct wl1271 *wl)
static void wl1271_stop_ba_event(struct wl1271 *wl, struct wl12xx_vif *wlvif)
{
if (wl->bss_type != BSS_TYPE_AP_BSS) {
if (wlvif->bss_type != BSS_TYPE_AP_BSS) {
if (!wl->ba_rx_bitmap)
return;
ieee80211_stop_rx_ba_session(wl->vif, wl->ba_rx_bitmap,
......@@ -229,7 +229,7 @@ static int wl1271_event_process(struct wl1271 *wl, struct event_mailbox *mbox)
int ret;
u32 vector;
bool beacon_loss = false;
bool is_ap = (wl->bss_type == BSS_TYPE_AP_BSS);
bool is_ap = (wlvif->bss_type == BSS_TYPE_AP_BSS);
bool disconnect_sta = false;
unsigned long sta_bitmap = 0;
......@@ -263,7 +263,7 @@ static int wl1271_event_process(struct wl1271 *wl, struct event_mailbox *mbox)
}
if (vector & SOFT_GEMINI_SENSE_EVENT_ID &&
wl->bss_type == BSS_TYPE_STA_BSS)
wlvif->bss_type == BSS_TYPE_STA_BSS)
wl12xx_event_soft_gemini_sense(wl,
mbox->soft_gemini_sense_info);
......@@ -306,7 +306,7 @@ static int wl1271_event_process(struct wl1271 *wl, struct event_mailbox *mbox)
wl->ba_allowed = !!mbox->rx_ba_allowed;
if (wl->vif && !wl->ba_allowed)
wl1271_stop_ba_event(wl);
wl1271_stop_ba_event(wl, wlvif);
}
if ((vector & CHANNEL_SWITCH_COMPLETE_EVENT_ID) && !is_ap) {
......
......@@ -478,7 +478,7 @@ int wl1271_init_ap_rates(struct wl1271 *wl, struct wl12xx_vif *wlvif)
return 0;
}
static int wl1271_set_ba_policies(struct wl1271 *wl)
static int wl1271_set_ba_policies(struct wl1271 *wl, struct wl12xx_vif *wlvif)
{
/* Reset the BA RX indicators */
wl->ba_rx_bitmap = 0;
......@@ -486,8 +486,8 @@ static int wl1271_set_ba_policies(struct wl1271 *wl)
wl->ba_rx_session_count = 0;
/* BA is supported in STA/AP modes */
if (wl->bss_type != BSS_TYPE_AP_BSS &&
wl->bss_type != BSS_TYPE_STA_BSS) {
if (wlvif->bss_type != BSS_TYPE_AP_BSS &&
wlvif->bss_type != BSS_TYPE_STA_BSS) {
wl->ba_support = false;
return 0;
}
......@@ -572,7 +572,7 @@ int wl1271_init_vif_specific(struct wl1271 *wl, struct ieee80211_vif *vif)
struct wl12xx_vif *wlvif = wl12xx_vif_to_data(vif);
struct conf_tx_ac_category *conf_ac;
struct conf_tx_tid *conf_tid;
bool is_ap = (wl->bss_type == BSS_TYPE_AP_BSS);
bool is_ap = (wlvif->bss_type == BSS_TYPE_AP_BSS);
int ret, i;
......@@ -635,7 +635,7 @@ int wl1271_init_vif_specific(struct wl1271 *wl, struct ieee80211_vif *vif)
return ret;
/* Configure initiator BA sessions policies */
ret = wl1271_set_ba_policies(wl);
ret = wl1271_set_ba_policies(wl, wlvif);
if (ret < 0)
return ret;
......
This diff is collapsed.
......@@ -185,6 +185,8 @@ static int wl1271_rx_handle_data(struct wl1271 *wl, u8 *data, u32 length,
void wl12xx_rx(struct wl1271 *wl, struct wl12xx_fw_status *status)
{
struct wl1271_acx_mem_map *wl_mem_map = wl->target_mem_map;
struct ieee80211_vif *vif = wl->vif; /* TODO: get as param */
struct wl12xx_vif *wlvif = wl12xx_vif_to_data(vif);
u32 buf_size;
u32 fw_rx_counter = status->fw_rx_counter & NUM_RX_PKT_DESC_MOD_MASK;
u32 drv_rx_counter = wl->rx_counter & NUM_RX_PKT_DESC_MOD_MASK;
......@@ -192,7 +194,7 @@ void wl12xx_rx(struct wl1271 *wl, struct wl12xx_fw_status *status)
u32 mem_block;
u32 pkt_length;
u32 pkt_offset;
bool is_ap = (wl->bss_type == BSS_TYPE_AP_BSS);
bool is_ap = (wlvif->bss_type == BSS_TYPE_AP_BSS);
bool had_data = false;
bool unaligned = false;
......
......@@ -34,6 +34,7 @@ void wl1271_scan_complete_work(struct work_struct *work)
{
struct delayed_work *dwork;
struct wl1271 *wl;
struct wl12xx_vif *wlvif;
int ret;
bool is_sta, is_ibss;
......@@ -50,6 +51,8 @@ void wl1271_scan_complete_work(struct work_struct *work)
if (wl->scan.state == WL1271_SCAN_STATE_IDLE)
goto out;
wlvif = wl12xx_vif_to_data(wl->scan_vif);
wl->scan.state = WL1271_SCAN_STATE_IDLE;
memset(wl->scan.scanned_ch, 0, sizeof(wl->scan.scanned_ch));
wl->scan.req = NULL;
......@@ -65,8 +68,8 @@ void wl1271_scan_complete_work(struct work_struct *work)
}
/* return to ROC if needed */
is_sta = (wl->bss_type == BSS_TYPE_STA_BSS);
is_ibss = (wl->bss_type == BSS_TYPE_IBSS);
is_sta = (wlvif->bss_type == BSS_TYPE_STA_BSS);
is_ibss = (wlvif->bss_type == BSS_TYPE_IBSS);
if (((is_sta && !test_bit(WL1271_FLAG_STA_ASSOCIATED, &wl->flags)) ||
(is_ibss && !test_bit(WL1271_FLAG_IBSS_JOINED, &wl->flags))) &&
!test_bit(wl->dev_role_id, wl->roc_map)) {
......@@ -589,6 +592,7 @@ wl12xx_scan_sched_scan_ssid_list(struct wl1271 *wl,
}
int wl1271_scan_sched_scan_config(struct wl1271 *wl,
struct wl12xx_vif *wlvif,
struct cfg80211_sched_scan_request *req,
struct ieee80211_sched_scan_ies *ies)
{
......@@ -671,14 +675,14 @@ int wl1271_scan_sched_scan_config(struct wl1271 *wl,
return ret;
}
int wl1271_scan_sched_scan_start(struct wl1271 *wl)
int wl1271_scan_sched_scan_start(struct wl1271 *wl, struct wl12xx_vif *wlvif)
{
struct wl1271_cmd_sched_scan_start *start;
int ret = 0;
wl1271_debug(DEBUG_CMD, "cmd periodic scan start");
if (wl->bss_type != BSS_TYPE_STA_BSS)
if (wlvif->bss_type != BSS_TYPE_STA_BSS)
return -EOPNOTSUPP;
if (!test_bit(WL1271_FLAG_IDLE, &wl->flags))
......
......@@ -36,9 +36,10 @@ int wl1271_scan_build_probe_req(struct wl1271 *wl,
void wl1271_scan_stm(struct wl1271 *wl, struct ieee80211_vif *vif);
void wl1271_scan_complete_work(struct work_struct *work);
int wl1271_scan_sched_scan_config(struct wl1271 *wl,
struct wl12xx_vif *wlvif,
struct cfg80211_sched_scan_request *req,
struct ieee80211_sched_scan_ies *ies);
int wl1271_scan_sched_scan_start(struct wl1271 *wl);
int wl1271_scan_sched_scan_start(struct wl1271 *wl, struct wl12xx_vif *wlvif);
void wl1271_scan_sched_scan_stop(struct wl1271 *wl);
void wl1271_scan_sched_scan_results(struct wl1271 *wl);
......
......@@ -32,10 +32,11 @@
#include "tx.h"
#include "event.h"
static int wl1271_set_default_wep_key(struct wl1271 *wl, u8 id)
static int wl1271_set_default_wep_key(struct wl1271 *wl,
struct wl12xx_vif *wlvif, u8 id)
{
int ret;
bool is_ap = (wl->bss_type == BSS_TYPE_AP_BSS);
bool is_ap = (wlvif->bss_type == BSS_TYPE_AP_BSS);
if (is_ap)
ret = wl12xx_cmd_set_default_wep_key(wl, id,
......@@ -178,14 +179,17 @@ u8 wl12xx_tx_get_hlid_ap(struct wl1271 *wl, struct sk_buff *skb)
}
}
static u8 wl1271_tx_get_hlid(struct wl1271 *wl, struct sk_buff *skb)
static u8 wl1271_tx_get_hlid(struct wl1271 *wl, struct ieee80211_vif *vif,
struct sk_buff *skb)
{
struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)skb->data;
struct wl12xx_vif *wlvif = wl12xx_vif_to_data(vif);
if (wl12xx_is_dummy_packet(wl, skb))
return wl->system_hlid;
if (wl->bss_type == BSS_TYPE_AP_BSS)
if (wlvif->bss_type == BSS_TYPE_AP_BSS)
return wl12xx_tx_get_hlid_ap(wl, skb);
wl1271_tx_update_filters(wl, skb);
......@@ -208,9 +212,11 @@ static unsigned int wl12xx_calc_packet_alignment(struct wl1271 *wl,
return ALIGN(packet_length, WL1271_TX_ALIGN_TO);
}
static int wl1271_tx_allocate(struct wl1271 *wl, struct sk_buff *skb, u32 extra,
u32 buf_offset, u8 hlid)
static int wl1271_tx_allocate(struct wl1271 *wl, struct ieee80211_vif *vif,
struct sk_buff *skb, u32 extra, u32 buf_offset,
u8 hlid)
{
struct wl12xx_vif *wlvif = wl12xx_vif_to_data(vif);
struct wl1271_tx_hw_descr *desc;
u32 total_len = skb->len + sizeof(struct wl1271_tx_hw_descr) + extra;
u32 len;
......@@ -257,7 +263,7 @@ static int wl1271_tx_allocate(struct wl1271 *wl, struct sk_buff *skb, u32 extra,
ac = wl1271_tx_get_queue(skb_get_queue_mapping(skb));
wl->tx_allocated_pkts[ac]++;
if (wl->bss_type == BSS_TYPE_AP_BSS &&
if (wlvif->bss_type == BSS_TYPE_AP_BSS &&
hlid >= WL1271_AP_STA_HLID_START)
wl->links[hlid].allocated_pkts++;
......@@ -273,10 +279,11 @@ static int wl1271_tx_allocate(struct wl1271 *wl, struct sk_buff *skb, u32 extra,
return ret;
}
static void wl1271_tx_fill_hdr(struct wl1271 *wl, struct sk_buff *skb,
u32 extra, struct ieee80211_tx_info *control,
u8 hlid)
static void wl1271_tx_fill_hdr(struct wl1271 *wl, struct ieee80211_vif *vif,
struct sk_buff *skb, u32 extra,
struct ieee80211_tx_info *control, u8 hlid)
{
struct wl12xx_vif *wlvif = wl12xx_vif_to_data(vif);
struct timespec ts;
struct wl1271_tx_hw_descr *desc;
int aligned_len, ac, rate_idx;
......@@ -298,7 +305,7 @@ static void wl1271_tx_fill_hdr(struct wl1271 *wl, struct sk_buff *skb,
hosttime = (timespec_to_ns(&ts) >> 10);
desc->start_time = cpu_to_le32(hosttime - wl->time_offset);
if (wl->bss_type != BSS_TYPE_AP_BSS)
if (wlvif->bss_type != BSS_TYPE_AP_BSS)
desc->life_time = cpu_to_le16(TX_HW_MGMT_PKT_LIFETIME_TU);
else
desc->life_time = cpu_to_le16(TX_HW_AP_MODE_PKT_LIFETIME_TU);
......@@ -324,8 +331,7 @@ static void wl1271_tx_fill_hdr(struct wl1271 *wl, struct sk_buff *skb,
}
desc->hlid = hlid;
if (wl->bss_type != BSS_TYPE_AP_BSS) {
if (wlvif->bss_type != BSS_TYPE_AP_BSS) {
/* if the packets are destined for AP (have a STA entry)
send them with AP rate policies, otherwise use default
basic rates */
......@@ -383,16 +389,27 @@ static int wl1271_prepare_tx_frame(struct wl1271 *wl, struct sk_buff *skb,
u32 buf_offset)
{
struct ieee80211_tx_info *info;
struct ieee80211_vif *vif;
struct wl12xx_vif *wlvif;
u32 extra = 0;
int ret = 0;
u32 total_len;
u8 hlid;
bool is_dummy;
if (!skb)
return -EINVAL;
info = IEEE80211_SKB_CB(skb);
/* TODO: handle dummy packets on multi-vifs */
is_dummy = wl12xx_is_dummy_packet(wl, skb);
if (is_dummy)
info->control.vif = wl->vif;
vif = info->control.vif;
wlvif = wl12xx_vif_to_data(vif);
if (info->control.hw_key &&
info->control.hw_key->cipher == WLAN_CIPHER_SUITE_TKIP)
extra = WL1271_TKIP_IV_SPACE;
......@@ -406,26 +423,25 @@ static int wl1271_prepare_tx_frame(struct wl1271 *wl, struct sk_buff *skb,
(cipher == WLAN_CIPHER_SUITE_WEP104);
if (unlikely(is_wep && wl->default_key != idx)) {
ret = wl1271_set_default_wep_key(wl, idx);
ret = wl1271_set_default_wep_key(wl, wlvif, idx);
if (ret < 0)
return ret;
wl->default_key = idx;
}
}
hlid = wl1271_tx_get_hlid(wl, skb);
hlid = wl1271_tx_get_hlid(wl, vif, skb);
if (hlid == WL12XX_INVALID_LINK_ID) {
wl1271_error("invalid hlid. dropping skb 0x%p", skb);
return -EINVAL;
}
ret = wl1271_tx_allocate(wl, skb, extra, buf_offset, hlid);
ret = wl1271_tx_allocate(wl, vif, skb, extra, buf_offset, hlid);
if (ret < 0)
return ret;
wl1271_tx_fill_hdr(wl, skb, extra, info, hlid);
wl1271_tx_fill_hdr(wl, vif, skb, extra, info, hlid);
if (wl->bss_type == BSS_TYPE_AP_BSS) {
if (wlvif->bss_type == BSS_TYPE_AP_BSS && !is_dummy) {
wl1271_tx_ap_update_inconnection_sta(wl, skb);
wl1271_tx_regulate_link(wl, hlid);
}
......@@ -444,7 +460,7 @@ static int wl1271_prepare_tx_frame(struct wl1271 *wl, struct sk_buff *skb,
memset(wl->aggr_buf + buf_offset + skb->len, 0, total_len - skb->len);
/* Revert side effects in the dummy packet skb, so it can be reused */
if (wl12xx_is_dummy_packet(wl, skb))
if (is_dummy)
skb_pull(skb, sizeof(struct wl1271_tx_hw_descr));
return total_len;
......@@ -586,12 +602,13 @@ static struct sk_buff *wl1271_ap_skb_dequeue(struct wl1271 *wl)
return skb;
}
static struct sk_buff *wl1271_skb_dequeue(struct wl1271 *wl)
static struct sk_buff *wl1271_skb_dequeue(struct wl1271 *wl,
struct wl12xx_vif *wlvif)
{
unsigned long flags;
struct sk_buff *skb = NULL;
if (wl->bss_type == BSS_TYPE_AP_BSS)
if (wlvif->bss_type == BSS_TYPE_AP_BSS)
skb = wl1271_ap_skb_dequeue(wl);
else
skb = wl1271_sta_skb_dequeue(wl);
......@@ -610,15 +627,17 @@ static struct sk_buff *wl1271_skb_dequeue(struct wl1271 *wl)
return skb;
}
static void wl1271_skb_queue_head(struct wl1271 *wl, struct sk_buff *skb)
static void wl1271_skb_queue_head(struct wl1271 *wl, struct ieee80211_vif *vif,
struct sk_buff *skb)
{
struct wl12xx_vif *wlvif = wl12xx_vif_to_data(vif);
unsigned long flags;
int q = wl1271_tx_get_queue(skb_get_queue_mapping(skb));
if (wl12xx_is_dummy_packet(wl, skb)) {
set_bit(WL1271_FLAG_DUMMY_PACKET_PENDING, &wl->flags);
} else if (wl->bss_type == BSS_TYPE_AP_BSS) {
u8 hlid = wl1271_tx_get_hlid(wl, skb);
} else if (wlvif->bss_type == BSS_TYPE_AP_BSS) {
u8 hlid = wl1271_tx_get_hlid(wl, vif, skb);
skb_queue_head(&wl->links[hlid].tx_queue[q], skb);
/* make sure we dequeue the same packet next time */
......@@ -639,19 +658,20 @@ static bool wl1271_tx_is_data_present(struct sk_buff *skb)
return ieee80211_is_data_present(hdr->frame_control);
}
void wl1271_tx_work_locked(struct wl1271 *wl)
void wl1271_tx_work_locked(struct wl1271 *wl, struct ieee80211_vif *vif)
{
struct wl12xx_vif *wlvif = wl12xx_vif_to_data(vif);
struct sk_buff *skb;
u32 buf_offset = 0;
bool sent_packets = false;
bool had_data = false;
bool is_ap = (wl->bss_type == BSS_TYPE_AP_BSS);
bool is_ap = (wlvif->bss_type == BSS_TYPE_AP_BSS);
int ret;
if (unlikely(wl->state == WL1271_STATE_OFF))
return;
while ((skb = wl1271_skb_dequeue(wl))) {
while ((skb = wl1271_skb_dequeue(wl, wlvif))) {
if (wl1271_tx_is_data_present(skb))
had_data = true;
......@@ -661,7 +681,7 @@ void wl1271_tx_work_locked(struct wl1271 *wl)
* Aggregation buffer is full.
* Flush buffer and try again.
*/
wl1271_skb_queue_head(wl, skb);
wl1271_skb_queue_head(wl, vif, skb);
wl1271_write(wl, WL1271_SLV_MEM_DATA, wl->aggr_buf,
buf_offset, true);
sent_packets = true;
......@@ -672,7 +692,7 @@ void wl1271_tx_work_locked(struct wl1271 *wl)
* Firmware buffer is full.
* Queue back last skb, and stop aggregating.
*/
wl1271_skb_queue_head(wl, skb);
wl1271_skb_queue_head(wl, vif, skb);
/* No work left, avoid scheduling redundant tx work */
set_bit(WL1271_FLAG_FW_TX_BUSY, &wl->flags);
goto out_ack;
......@@ -726,7 +746,7 @@ void wl1271_tx_work(struct work_struct *work)
if (ret < 0)
goto out;
wl1271_tx_work_locked(wl);
wl1271_tx_work_locked(wl, wl->vif);
wl1271_ps_elp_sleep(wl);
out:
......@@ -888,12 +908,14 @@ void wl1271_tx_reset_link_queues(struct wl1271 *wl, u8 hlid)
/* caller must hold wl->mutex and TX must be stopped */
void wl1271_tx_reset(struct wl1271 *wl, bool reset_tx_queues)
{
struct ieee80211_vif *vif = wl->vif; /* TODO: get as param */
struct wl12xx_vif *wlvif = wl12xx_vif_to_data(vif);
int i;
struct sk_buff *skb;
struct ieee80211_tx_info *info;
/* TX failure */
if (wl->bss_type == BSS_TYPE_AP_BSS) {
if (wlvif->bss_type == BSS_TYPE_AP_BSS) {
for (i = 0; i < AP_MAX_LINKS; i++) {
wl1271_free_sta(wl, i);
wl1271_tx_reset_link_queues(wl, i);
......
......@@ -204,7 +204,7 @@ static inline int wl1271_tx_total_queue_count(struct wl1271 *wl)
}
void wl1271_tx_work(struct work_struct *work);
void wl1271_tx_work_locked(struct wl1271 *wl);
void wl1271_tx_work_locked(struct wl1271 *wl, struct ieee80211_vif *vif);
void wl1271_tx_complete(struct wl1271 *wl);
void wl1271_tx_reset(struct wl1271 *wl, bool reset_tx_queues);
void wl1271_tx_flush(struct wl1271 *wl);
......
......@@ -400,7 +400,6 @@ struct wl1271 {
s8 hw_pg_ver;
u8 mac_addr[ETH_ALEN];
u8 bss_type;
u8 set_bss_type;
u8 p2p; /* we are using p2p role */
u8 ssid[IEEE80211_MAX_SSID_LEN + 1];
......@@ -630,6 +629,8 @@ struct wl1271_station {
};
struct wl12xx_vif {
u8 bss_type;
u32 basic_rate_set;
/*
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment