forked from Minki/linux
Major changes:
iwlwifi: * new Tx power firmware API * bump max firmware API to 17 * fix bug in debug prints * static checker fix * fix unused defines * fix command list on newest firmware brcmfmac: * support NVRAM loading for bcm47xx platform * new debugfs entry for msgbuf protocol layer used with PCIe devices ath10k: * add spectral scan support for qca99x0 * add qca6164 support -----BEGIN PGP SIGNATURE----- Version: GnuPG v1.4.11 (GNU/Linux) iQEcBAABAgAGBQJV3dEKAAoJEG4XJFUm622bKpcH/2+9lcdUY0xplYPOA+eXIJoT lA7fvFzm3Ez17OPOu+RCSYGnsiYHW47ayCdKqBcVkVIiE5kiRaztvDL7NpCN1mCY SIJgixcL0aRinDqc2HZBJ2dG1AUeM7p3SxupuHFovtI2FBs8O+sWcx7/tJ26+f+Y tSRwcZkWKNUOwqjQckFfD/k5PpAo06hxg8Zw85N+qNhWB8NyVgIZqHID1vOwQc02 rtqHl0BZxz2fKmsAeRKpZGlxFqYwc2Y/QT5YLgaOEDQ+gmoUsJKHUIge4fL7zTTG I6UUTUbtu83SMKTAeg6BztM+JklEZRNRL5VLboE36dSmSsUBbZxi/WKf+OG70SE= =W1bH -----END PGP SIGNATURE----- Merge tag 'wireless-drivers-next-for-davem-2015-08-26' of git://git.kernel.org/pub/scm/linux/kernel/git/kvalo/wireless-drivers-next Kalle Valo says: ==================== Major changes: iwlwifi: * new Tx power firmware API * bump max firmware API to 17 * fix bug in debug prints * static checker fix * fix unused defines * fix command list on newest firmware brcmfmac: * support NVRAM loading for bcm47xx platform * new debugfs entry for msgbuf protocol layer used with PCIe devices ath10k: * add spectral scan support for qca99x0 * add qca6164 support ==================== Signed-off-by: David S. Miller <davem@davemloft.net>
This commit is contained in:
commit
395250e483
@ -53,6 +53,7 @@ static const struct ath10k_hw_params ath10k_hw_params_list[] = {
|
||||
.uart_pin = 7,
|
||||
.has_shifted_cc_wraparound = true,
|
||||
.otp_exe_param = 0,
|
||||
.channel_counters_freq_hz = 88000,
|
||||
.fw = {
|
||||
.dir = QCA988X_HW_2_0_FW_DIR,
|
||||
.fw = QCA988X_HW_2_0_FW_FILE,
|
||||
@ -68,6 +69,7 @@ static const struct ath10k_hw_params ath10k_hw_params_list[] = {
|
||||
.patch_load_addr = QCA6174_HW_2_1_PATCH_LOAD_ADDR,
|
||||
.uart_pin = 6,
|
||||
.otp_exe_param = 0,
|
||||
.channel_counters_freq_hz = 88000,
|
||||
.fw = {
|
||||
.dir = QCA6174_HW_2_1_FW_DIR,
|
||||
.fw = QCA6174_HW_2_1_FW_FILE,
|
||||
@ -83,6 +85,7 @@ static const struct ath10k_hw_params ath10k_hw_params_list[] = {
|
||||
.patch_load_addr = QCA6174_HW_3_0_PATCH_LOAD_ADDR,
|
||||
.uart_pin = 6,
|
||||
.otp_exe_param = 0,
|
||||
.channel_counters_freq_hz = 88000,
|
||||
.fw = {
|
||||
.dir = QCA6174_HW_3_0_FW_DIR,
|
||||
.fw = QCA6174_HW_3_0_FW_FILE,
|
||||
@ -98,6 +101,7 @@ static const struct ath10k_hw_params ath10k_hw_params_list[] = {
|
||||
.patch_load_addr = QCA6174_HW_3_0_PATCH_LOAD_ADDR,
|
||||
.uart_pin = 6,
|
||||
.otp_exe_param = 0,
|
||||
.channel_counters_freq_hz = 88000,
|
||||
.fw = {
|
||||
/* uses same binaries as hw3.0 */
|
||||
.dir = QCA6174_HW_3_0_FW_DIR,
|
||||
@ -115,6 +119,7 @@ static const struct ath10k_hw_params ath10k_hw_params_list[] = {
|
||||
.uart_pin = 7,
|
||||
.otp_exe_param = 0x00000700,
|
||||
.continuous_frag_desc = true,
|
||||
.channel_counters_freq_hz = 150000,
|
||||
.fw = {
|
||||
.dir = QCA99X0_HW_2_0_FW_DIR,
|
||||
.fw = QCA99X0_HW_2_0_FW_FILE,
|
||||
@ -231,6 +236,17 @@ static int ath10k_init_configure_target(struct ath10k *ar)
|
||||
return ret;
|
||||
}
|
||||
|
||||
/* Some devices have a special sanity check that verifies the PCI
|
||||
* Device ID is written to this host interest var. It is known to be
|
||||
* required to boot QCA6164.
|
||||
*/
|
||||
ret = ath10k_bmi_write32(ar, hi_hci_uart_pwr_mgmt_params_ext,
|
||||
ar->dev_id);
|
||||
if (ret) {
|
||||
ath10k_err(ar, "failed to set pwr_mgmt_params: %d\n", ret);
|
||||
return ret;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
@ -1411,13 +1427,13 @@ int ath10k_wait_for_suspend(struct ath10k *ar, u32 suspend_opt)
|
||||
void ath10k_core_stop(struct ath10k *ar)
|
||||
{
|
||||
lockdep_assert_held(&ar->conf_mutex);
|
||||
ath10k_debug_stop(ar);
|
||||
|
||||
/* try to suspend target */
|
||||
if (ar->state != ATH10K_STATE_RESTARTING &&
|
||||
ar->state != ATH10K_STATE_UTF)
|
||||
ath10k_wait_for_suspend(ar, WMI_PDEV_SUSPEND_AND_DISABLE_INTR);
|
||||
|
||||
ath10k_debug_stop(ar);
|
||||
ath10k_hif_stop(ar);
|
||||
ath10k_htt_tx_free(&ar->htt);
|
||||
ath10k_htt_rx_free(&ar->htt);
|
||||
|
@ -554,6 +554,7 @@ struct ath10k {
|
||||
u8 mac_addr[ETH_ALEN];
|
||||
|
||||
enum ath10k_hw_rev hw_rev;
|
||||
u16 dev_id;
|
||||
u32 chip_id;
|
||||
u32 target_version;
|
||||
u8 fw_version_major;
|
||||
@ -609,6 +610,8 @@ struct ath10k {
|
||||
*/
|
||||
bool continuous_frag_desc;
|
||||
|
||||
u32 channel_counters_freq_hz;
|
||||
|
||||
struct ath10k_hw_params_fw {
|
||||
const char *dir;
|
||||
const char *fw;
|
||||
|
@ -323,7 +323,7 @@ void ath10k_debug_fw_stats_process(struct ath10k *ar, struct sk_buff *skb)
|
||||
ret = ath10k_wmi_pull_fw_stats(ar, skb, &stats);
|
||||
if (ret) {
|
||||
ath10k_warn(ar, "failed to pull fw stats: %d\n", ret);
|
||||
goto unlock;
|
||||
goto free;
|
||||
}
|
||||
|
||||
/* Stat data may exceed htc-wmi buffer limit. In such case firmware
|
||||
@ -386,7 +386,6 @@ free:
|
||||
ath10k_debug_fw_stats_vdevs_free(&stats.vdevs);
|
||||
ath10k_debug_fw_stats_peers_free(&stats.peers);
|
||||
|
||||
unlock:
|
||||
spin_unlock_bh(&ar->data_lock);
|
||||
}
|
||||
|
||||
|
@ -145,8 +145,10 @@ int ath10k_htc_send(struct ath10k_htc *htc,
|
||||
skb_cb->eid = eid;
|
||||
skb_cb->paddr = dma_map_single(dev, skb->data, skb->len, DMA_TO_DEVICE);
|
||||
ret = dma_mapping_error(dev, skb_cb->paddr);
|
||||
if (ret)
|
||||
if (ret) {
|
||||
ret = -EIO;
|
||||
goto err_credits;
|
||||
}
|
||||
|
||||
sg_item.transfer_id = ep->eid;
|
||||
sg_item.transfer_context = skb;
|
||||
|
@ -442,8 +442,10 @@ int ath10k_htt_mgmt_tx(struct ath10k_htt *htt, struct sk_buff *msdu)
|
||||
skb_cb->paddr = dma_map_single(dev, msdu->data, msdu->len,
|
||||
DMA_TO_DEVICE);
|
||||
res = dma_mapping_error(dev, skb_cb->paddr);
|
||||
if (res)
|
||||
if (res) {
|
||||
res = -EIO;
|
||||
goto err_free_txdesc;
|
||||
}
|
||||
|
||||
skb_put(txdesc, len);
|
||||
cmd = (struct htt_cmd *)txdesc->data;
|
||||
@ -533,8 +535,10 @@ int ath10k_htt_tx(struct ath10k_htt *htt, struct sk_buff *msdu)
|
||||
skb_cb->paddr = dma_map_single(dev, msdu->data, msdu->len,
|
||||
DMA_TO_DEVICE);
|
||||
res = dma_mapping_error(dev, skb_cb->paddr);
|
||||
if (res)
|
||||
if (res) {
|
||||
res = -EIO;
|
||||
goto err_free_txbuf;
|
||||
}
|
||||
|
||||
switch (skb_cb->txmode) {
|
||||
case ATH10K_HW_TXRX_RAW:
|
||||
|
@ -152,6 +152,6 @@ void ath10k_hw_fill_survey_time(struct ath10k *ar, struct survey_info *survey,
|
||||
cc -= cc_prev - cc_fix;
|
||||
rcc -= rcc_prev;
|
||||
|
||||
survey->time = CCNT_TO_MSEC(cc);
|
||||
survey->time_busy = CCNT_TO_MSEC(rcc);
|
||||
survey->time = CCNT_TO_MSEC(ar, cc);
|
||||
survey->time_busy = CCNT_TO_MSEC(ar, rcc);
|
||||
}
|
||||
|
@ -552,8 +552,7 @@ enum ath10k_hw_rate_cck {
|
||||
#define SCRATCH_3_ADDRESS ar->regs->scratch_3_address
|
||||
#define CPU_INTR_ADDRESS 0x0010
|
||||
|
||||
/* Cycle counters are running at 88MHz */
|
||||
#define CCNT_TO_MSEC(x) ((x) / 88000)
|
||||
#define CCNT_TO_MSEC(ar, x) ((x) / ar->hw_params.channel_counters_freq_hz)
|
||||
|
||||
/* Firmware indications to the Host via SCRATCH_3 register. */
|
||||
#define FW_INDICATOR_ADDRESS ar->regs->fw_indicator_address
|
||||
|
@ -247,6 +247,10 @@ static int ath10k_install_peer_wep_keys(struct ath10k_vif *arvif,
|
||||
|
||||
lockdep_assert_held(&ar->conf_mutex);
|
||||
|
||||
if (WARN_ON(arvif->vif->type != NL80211_IFTYPE_AP &&
|
||||
arvif->vif->type != NL80211_IFTYPE_ADHOC))
|
||||
return -EINVAL;
|
||||
|
||||
spin_lock_bh(&ar->data_lock);
|
||||
peer = ath10k_peer_find(ar, arvif->vdev_id, addr);
|
||||
spin_unlock_bh(&ar->data_lock);
|
||||
@ -258,21 +262,34 @@ static int ath10k_install_peer_wep_keys(struct ath10k_vif *arvif,
|
||||
if (arvif->wep_keys[i] == NULL)
|
||||
continue;
|
||||
|
||||
flags = 0;
|
||||
flags |= WMI_KEY_PAIRWISE;
|
||||
switch (arvif->vif->type) {
|
||||
case NL80211_IFTYPE_AP:
|
||||
flags = WMI_KEY_PAIRWISE;
|
||||
|
||||
ret = ath10k_install_key(arvif, arvif->wep_keys[i], SET_KEY,
|
||||
addr, flags);
|
||||
if (ret < 0)
|
||||
return ret;
|
||||
if (arvif->def_wep_key_idx == i)
|
||||
flags |= WMI_KEY_TX_USAGE;
|
||||
|
||||
flags = 0;
|
||||
flags |= WMI_KEY_GROUP;
|
||||
ret = ath10k_install_key(arvif, arvif->wep_keys[i],
|
||||
SET_KEY, addr, flags);
|
||||
if (ret < 0)
|
||||
return ret;
|
||||
break;
|
||||
case NL80211_IFTYPE_ADHOC:
|
||||
ret = ath10k_install_key(arvif, arvif->wep_keys[i],
|
||||
SET_KEY, addr,
|
||||
WMI_KEY_PAIRWISE);
|
||||
if (ret < 0)
|
||||
return ret;
|
||||
|
||||
ret = ath10k_install_key(arvif, arvif->wep_keys[i], SET_KEY,
|
||||
addr, flags);
|
||||
if (ret < 0)
|
||||
return ret;
|
||||
ret = ath10k_install_key(arvif, arvif->wep_keys[i],
|
||||
SET_KEY, addr, WMI_KEY_GROUP);
|
||||
if (ret < 0)
|
||||
return ret;
|
||||
break;
|
||||
default:
|
||||
WARN_ON(1);
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
spin_lock_bh(&ar->data_lock);
|
||||
peer->keys[i] = arvif->wep_keys[i];
|
||||
@ -287,6 +304,9 @@ static int ath10k_install_peer_wep_keys(struct ath10k_vif *arvif,
|
||||
*
|
||||
* FIXME: Revisit. Perhaps this can be done in a less hacky way.
|
||||
*/
|
||||
if (arvif->vif->type != NL80211_IFTYPE_ADHOC)
|
||||
return 0;
|
||||
|
||||
if (arvif->def_wep_key_idx == -1)
|
||||
return 0;
|
||||
|
||||
@ -2999,6 +3019,8 @@ void ath10k_mac_tx_unlock(struct ath10k *ar, int reason)
|
||||
IEEE80211_IFACE_ITER_RESUME_ALL,
|
||||
ath10k_mac_tx_unlock_iter,
|
||||
ar);
|
||||
|
||||
ieee80211_wake_queue(ar->hw, ar->hw->offchannel_tx_hw_queue);
|
||||
}
|
||||
|
||||
void ath10k_mac_vif_tx_lock(struct ath10k_vif *arvif, int reason)
|
||||
@ -4122,7 +4144,8 @@ static int ath10k_add_interface(struct ieee80211_hw *hw,
|
||||
|
||||
if (ar->num_peers >= ar->max_num_peers) {
|
||||
ath10k_warn(ar, "refusing vdev creation due to insufficient peer entry resources in firmware\n");
|
||||
return -ENOBUFS;
|
||||
ret = -ENOBUFS;
|
||||
goto err;
|
||||
}
|
||||
|
||||
if (ar->free_vdev_map == 0) {
|
||||
@ -4340,6 +4363,11 @@ static int ath10k_add_interface(struct ieee80211_hw *hw,
|
||||
}
|
||||
}
|
||||
|
||||
spin_lock_bh(&ar->htt.tx_lock);
|
||||
if (!ar->tx_paused)
|
||||
ieee80211_wake_queue(ar->hw, arvif->vdev_id);
|
||||
spin_unlock_bh(&ar->htt.tx_lock);
|
||||
|
||||
mutex_unlock(&ar->conf_mutex);
|
||||
return 0;
|
||||
|
||||
|
@ -58,11 +58,13 @@ MODULE_PARM_DESC(reset_mode, "0: auto, 1: warm only (default: 0)");
|
||||
#define ATH10K_PCI_NUM_WARM_RESET_ATTEMPTS 3
|
||||
|
||||
#define QCA988X_2_0_DEVICE_ID (0x003c)
|
||||
#define QCA6164_2_1_DEVICE_ID (0x0041)
|
||||
#define QCA6174_2_1_DEVICE_ID (0x003e)
|
||||
#define QCA99X0_2_0_DEVICE_ID (0x0040)
|
||||
|
||||
static const struct pci_device_id ath10k_pci_id_table[] = {
|
||||
{ PCI_VDEVICE(ATHEROS, QCA988X_2_0_DEVICE_ID) }, /* PCI-E QCA988X V2 */
|
||||
{ PCI_VDEVICE(ATHEROS, QCA6164_2_1_DEVICE_ID) }, /* PCI-E QCA6164 V2.1 */
|
||||
{ PCI_VDEVICE(ATHEROS, QCA6174_2_1_DEVICE_ID) }, /* PCI-E QCA6174 V2.1 */
|
||||
{ PCI_VDEVICE(ATHEROS, QCA99X0_2_0_DEVICE_ID) }, /* PCI-E QCA99X0 V2 */
|
||||
{0}
|
||||
@ -74,11 +76,19 @@ static const struct ath10k_pci_supp_chip ath10k_pci_supp_chips[] = {
|
||||
* because of that.
|
||||
*/
|
||||
{ QCA988X_2_0_DEVICE_ID, QCA988X_HW_2_0_CHIP_ID_REV },
|
||||
|
||||
{ QCA6164_2_1_DEVICE_ID, QCA6174_HW_2_1_CHIP_ID_REV },
|
||||
{ QCA6164_2_1_DEVICE_ID, QCA6174_HW_2_2_CHIP_ID_REV },
|
||||
{ QCA6164_2_1_DEVICE_ID, QCA6174_HW_3_0_CHIP_ID_REV },
|
||||
{ QCA6164_2_1_DEVICE_ID, QCA6174_HW_3_1_CHIP_ID_REV },
|
||||
{ QCA6164_2_1_DEVICE_ID, QCA6174_HW_3_2_CHIP_ID_REV },
|
||||
|
||||
{ QCA6174_2_1_DEVICE_ID, QCA6174_HW_2_1_CHIP_ID_REV },
|
||||
{ QCA6174_2_1_DEVICE_ID, QCA6174_HW_2_2_CHIP_ID_REV },
|
||||
{ QCA6174_2_1_DEVICE_ID, QCA6174_HW_3_0_CHIP_ID_REV },
|
||||
{ QCA6174_2_1_DEVICE_ID, QCA6174_HW_3_1_CHIP_ID_REV },
|
||||
{ QCA6174_2_1_DEVICE_ID, QCA6174_HW_3_2_CHIP_ID_REV },
|
||||
|
||||
{ QCA99X0_2_0_DEVICE_ID, QCA99X0_HW_2_0_CHIP_ID_REV },
|
||||
};
|
||||
|
||||
@ -1667,8 +1677,10 @@ static int ath10k_pci_hif_exchange_bmi_msg(struct ath10k *ar,
|
||||
|
||||
req_paddr = dma_map_single(ar->dev, treq, req_len, DMA_TO_DEVICE);
|
||||
ret = dma_mapping_error(ar->dev, req_paddr);
|
||||
if (ret)
|
||||
if (ret) {
|
||||
ret = -EIO;
|
||||
goto err_dma;
|
||||
}
|
||||
|
||||
if (resp && resp_len) {
|
||||
tresp = kzalloc(*resp_len, GFP_KERNEL);
|
||||
@ -1680,8 +1692,10 @@ static int ath10k_pci_hif_exchange_bmi_msg(struct ath10k *ar,
|
||||
resp_paddr = dma_map_single(ar->dev, tresp, *resp_len,
|
||||
DMA_FROM_DEVICE);
|
||||
ret = dma_mapping_error(ar->dev, resp_paddr);
|
||||
if (ret)
|
||||
if (ret) {
|
||||
ret = EIO;
|
||||
goto err_req;
|
||||
}
|
||||
|
||||
xfer.wait_for_resp = true;
|
||||
xfer.resp_len = 0;
|
||||
@ -1810,6 +1824,7 @@ static int ath10k_pci_get_num_banks(struct ath10k *ar)
|
||||
case QCA988X_2_0_DEVICE_ID:
|
||||
case QCA99X0_2_0_DEVICE_ID:
|
||||
return 1;
|
||||
case QCA6164_2_1_DEVICE_ID:
|
||||
case QCA6174_2_1_DEVICE_ID:
|
||||
switch (MS(ar->chip_id, SOC_CHIP_ID_REV)) {
|
||||
case QCA6174_HW_1_0_CHIP_ID_REV:
|
||||
@ -2898,6 +2913,7 @@ static int ath10k_pci_probe(struct pci_dev *pdev,
|
||||
case QCA988X_2_0_DEVICE_ID:
|
||||
hw_rev = ATH10K_HW_QCA988X;
|
||||
break;
|
||||
case QCA6164_2_1_DEVICE_ID:
|
||||
case QCA6174_2_1_DEVICE_ID:
|
||||
hw_rev = ATH10K_HW_QCA6174;
|
||||
break;
|
||||
@ -2922,6 +2938,7 @@ static int ath10k_pci_probe(struct pci_dev *pdev,
|
||||
ar_pci->pdev = pdev;
|
||||
ar_pci->dev = &pdev->dev;
|
||||
ar_pci->ar = ar;
|
||||
ar->dev_id = pci_dev->device;
|
||||
|
||||
if (pdev->subsystem_vendor || pdev->subsystem_device)
|
||||
scnprintf(ar->spec_board_id, sizeof(ar->spec_board_id),
|
||||
|
@ -57,7 +57,7 @@ static uint8_t get_max_exp(s8 max_index, u16 max_magnitude, size_t bin_len,
|
||||
}
|
||||
|
||||
int ath10k_spectral_process_fft(struct ath10k *ar,
|
||||
const struct wmi_phyerr *phyerr,
|
||||
struct wmi_phyerr_ev_arg *phyerr,
|
||||
const struct phyerr_fft_report *fftr,
|
||||
size_t bin_len, u64 tsf)
|
||||
{
|
||||
@ -73,6 +73,15 @@ int ath10k_spectral_process_fft(struct ath10k *ar,
|
||||
if (bin_len < 64 || bin_len > SPECTRAL_ATH10K_MAX_NUM_BINS)
|
||||
return -EINVAL;
|
||||
|
||||
/* qca99x0 reports bin size as 68 bytes (64 bytes + 4 bytes) in
|
||||
* report mode 2. First 64 bytes carries inband tones (-32 to +31)
|
||||
* and last 4 byte carries band edge detection data (+32) mainly
|
||||
* used in radar detection purpose. Strip last 4 byte to make bin
|
||||
* size is valid one.
|
||||
*/
|
||||
if (bin_len == 68)
|
||||
bin_len -= 4;
|
||||
|
||||
reg0 = __le32_to_cpu(fftr->reg0);
|
||||
reg1 = __le32_to_cpu(fftr->reg1);
|
||||
|
||||
@ -118,15 +127,14 @@ int ath10k_spectral_process_fft(struct ath10k *ar,
|
||||
fft_sample->total_gain_db = __cpu_to_be16(total_gain_db);
|
||||
fft_sample->base_pwr_db = __cpu_to_be16(base_pwr_db);
|
||||
|
||||
freq1 = __le16_to_cpu(phyerr->freq1);
|
||||
freq2 = __le16_to_cpu(phyerr->freq2);
|
||||
freq1 = phyerr->freq1;
|
||||
freq2 = phyerr->freq2;
|
||||
fft_sample->freq1 = __cpu_to_be16(freq1);
|
||||
fft_sample->freq2 = __cpu_to_be16(freq2);
|
||||
|
||||
chain_idx = MS(reg0, SEARCH_FFT_REPORT_REG0_FFT_CHN_IDX);
|
||||
|
||||
fft_sample->noise = __cpu_to_be16(
|
||||
__le16_to_cpu(phyerr->nf_chains[chain_idx]));
|
||||
fft_sample->noise = __cpu_to_be16(phyerr->nf_chains[chain_idx]);
|
||||
|
||||
bins = (u8 *)fftr;
|
||||
bins += sizeof(*fftr);
|
||||
|
@ -47,7 +47,7 @@ enum ath10k_spectral_mode {
|
||||
#ifdef CONFIG_ATH10K_DEBUGFS
|
||||
|
||||
int ath10k_spectral_process_fft(struct ath10k *ar,
|
||||
const struct wmi_phyerr *phyerr,
|
||||
struct wmi_phyerr_ev_arg *phyerr,
|
||||
const struct phyerr_fft_report *fftr,
|
||||
size_t bin_len, u64 tsf);
|
||||
int ath10k_spectral_start(struct ath10k *ar);
|
||||
@ -59,7 +59,7 @@ void ath10k_spectral_destroy(struct ath10k *ar);
|
||||
|
||||
static inline int
|
||||
ath10k_spectral_process_fft(struct ath10k *ar,
|
||||
const struct wmi_phyerr *phyerr,
|
||||
struct wmi_phyerr_ev_arg *phyerr,
|
||||
const struct phyerr_fft_report *fftr,
|
||||
size_t bin_len, u64 tsf)
|
||||
{
|
||||
|
@ -37,8 +37,10 @@ struct wmi_ops {
|
||||
struct wmi_peer_kick_ev_arg *arg);
|
||||
int (*pull_swba)(struct ath10k *ar, struct sk_buff *skb,
|
||||
struct wmi_swba_ev_arg *arg);
|
||||
int (*pull_phyerr)(struct ath10k *ar, struct sk_buff *skb,
|
||||
struct wmi_phyerr_ev_arg *arg);
|
||||
int (*pull_phyerr_hdr)(struct ath10k *ar, struct sk_buff *skb,
|
||||
struct wmi_phyerr_hdr_arg *arg);
|
||||
int (*pull_phyerr)(struct ath10k *ar, const void *phyerr_buf,
|
||||
int left_len, struct wmi_phyerr_ev_arg *arg);
|
||||
int (*pull_svc_rdy)(struct ath10k *ar, struct sk_buff *skb,
|
||||
struct wmi_svc_rdy_ev_arg *arg);
|
||||
int (*pull_rdy)(struct ath10k *ar, struct sk_buff *skb,
|
||||
@ -261,13 +263,23 @@ ath10k_wmi_pull_swba(struct ath10k *ar, struct sk_buff *skb,
|
||||
}
|
||||
|
||||
static inline int
|
||||
ath10k_wmi_pull_phyerr(struct ath10k *ar, struct sk_buff *skb,
|
||||
struct wmi_phyerr_ev_arg *arg)
|
||||
ath10k_wmi_pull_phyerr_hdr(struct ath10k *ar, struct sk_buff *skb,
|
||||
struct wmi_phyerr_hdr_arg *arg)
|
||||
{
|
||||
if (!ar->wmi.ops->pull_phyerr_hdr)
|
||||
return -EOPNOTSUPP;
|
||||
|
||||
return ar->wmi.ops->pull_phyerr_hdr(ar, skb, arg);
|
||||
}
|
||||
|
||||
static inline int
|
||||
ath10k_wmi_pull_phyerr(struct ath10k *ar, const void *phyerr_buf,
|
||||
int left_len, struct wmi_phyerr_ev_arg *arg)
|
||||
{
|
||||
if (!ar->wmi.ops->pull_phyerr)
|
||||
return -EOPNOTSUPP;
|
||||
|
||||
return ar->wmi.ops->pull_phyerr(ar, skb, arg);
|
||||
return ar->wmi.ops->pull_phyerr(ar, phyerr_buf, left_len, arg);
|
||||
}
|
||||
|
||||
static inline int
|
||||
|
@ -838,9 +838,9 @@ static int ath10k_wmi_tlv_op_pull_swba_ev(struct ath10k *ar,
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int ath10k_wmi_tlv_op_pull_phyerr_ev(struct ath10k *ar,
|
||||
struct sk_buff *skb,
|
||||
struct wmi_phyerr_ev_arg *arg)
|
||||
static int ath10k_wmi_tlv_op_pull_phyerr_ev_hdr(struct ath10k *ar,
|
||||
struct sk_buff *skb,
|
||||
struct wmi_phyerr_hdr_arg *arg)
|
||||
{
|
||||
const void **tb;
|
||||
const struct wmi_tlv_phyerr_ev *ev;
|
||||
@ -862,10 +862,10 @@ static int ath10k_wmi_tlv_op_pull_phyerr_ev(struct ath10k *ar,
|
||||
return -EPROTO;
|
||||
}
|
||||
|
||||
arg->num_phyerrs = ev->num_phyerrs;
|
||||
arg->tsf_l32 = ev->tsf_l32;
|
||||
arg->tsf_u32 = ev->tsf_u32;
|
||||
arg->buf_len = ev->buf_len;
|
||||
arg->num_phyerrs = __le32_to_cpu(ev->num_phyerrs);
|
||||
arg->tsf_l32 = __le32_to_cpu(ev->tsf_l32);
|
||||
arg->tsf_u32 = __le32_to_cpu(ev->tsf_u32);
|
||||
arg->buf_len = __le32_to_cpu(ev->buf_len);
|
||||
arg->phyerrs = phyerrs;
|
||||
|
||||
kfree(tb);
|
||||
@ -3407,7 +3407,8 @@ static const struct wmi_ops wmi_tlv_ops = {
|
||||
.pull_vdev_start = ath10k_wmi_tlv_op_pull_vdev_start_ev,
|
||||
.pull_peer_kick = ath10k_wmi_tlv_op_pull_peer_kick_ev,
|
||||
.pull_swba = ath10k_wmi_tlv_op_pull_swba_ev,
|
||||
.pull_phyerr = ath10k_wmi_tlv_op_pull_phyerr_ev,
|
||||
.pull_phyerr_hdr = ath10k_wmi_tlv_op_pull_phyerr_ev_hdr,
|
||||
.pull_phyerr = ath10k_wmi_op_pull_phyerr_ev,
|
||||
.pull_svc_rdy = ath10k_wmi_tlv_op_pull_svc_rdy_ev,
|
||||
.pull_rdy = ath10k_wmi_tlv_op_pull_rdy_ev,
|
||||
.pull_fw_stats = ath10k_wmi_tlv_op_pull_fw_stats,
|
||||
|
@ -2412,8 +2412,10 @@ void ath10k_wmi_event_chan_info(struct ath10k *ar, struct sk_buff *skb)
|
||||
ar->ch_info_can_report_survey = true;
|
||||
}
|
||||
|
||||
ar->survey_last_rx_clear_count = rx_clear_count;
|
||||
ar->survey_last_cycle_count = cycle_count;
|
||||
if (!(cmd_flags & WMI_CHAN_INFO_FLAG_PRE_COMPLETE)) {
|
||||
ar->survey_last_rx_clear_count = rx_clear_count;
|
||||
ar->survey_last_cycle_count = cycle_count;
|
||||
}
|
||||
|
||||
exit:
|
||||
spin_unlock_bh(&ar->data_lock);
|
||||
@ -3236,6 +3238,7 @@ void ath10k_wmi_event_host_swba(struct ath10k *ar, struct sk_buff *skb)
|
||||
ath10k_warn(ar, "failed to map beacon: %d\n",
|
||||
ret);
|
||||
dev_kfree_skb_any(bcn);
|
||||
ret = -EIO;
|
||||
goto skip;
|
||||
}
|
||||
|
||||
@ -3269,7 +3272,7 @@ void ath10k_wmi_event_tbttoffset_update(struct ath10k *ar, struct sk_buff *skb)
|
||||
}
|
||||
|
||||
static void ath10k_dfs_radar_report(struct ath10k *ar,
|
||||
const struct wmi_phyerr *phyerr,
|
||||
struct wmi_phyerr_ev_arg *phyerr,
|
||||
const struct phyerr_radar_report *rr,
|
||||
u64 tsf)
|
||||
{
|
||||
@ -3313,7 +3316,7 @@ static void ath10k_dfs_radar_report(struct ath10k *ar,
|
||||
}
|
||||
|
||||
/* report event to DFS pattern detector */
|
||||
tsf32l = __le32_to_cpu(phyerr->tsf_timestamp);
|
||||
tsf32l = phyerr->tsf_timestamp;
|
||||
tsf64 = tsf & (~0xFFFFFFFFULL);
|
||||
tsf64 |= tsf32l;
|
||||
|
||||
@ -3358,7 +3361,7 @@ radar_detected:
|
||||
}
|
||||
|
||||
static int ath10k_dfs_fft_report(struct ath10k *ar,
|
||||
const struct wmi_phyerr *phyerr,
|
||||
struct wmi_phyerr_ev_arg *phyerr,
|
||||
const struct phyerr_fft_report *fftr,
|
||||
u64 tsf)
|
||||
{
|
||||
@ -3396,7 +3399,7 @@ static int ath10k_dfs_fft_report(struct ath10k *ar,
|
||||
}
|
||||
|
||||
void ath10k_wmi_event_dfs(struct ath10k *ar,
|
||||
const struct wmi_phyerr *phyerr,
|
||||
struct wmi_phyerr_ev_arg *phyerr,
|
||||
u64 tsf)
|
||||
{
|
||||
int buf_len, tlv_len, res, i = 0;
|
||||
@ -3405,11 +3408,11 @@ void ath10k_wmi_event_dfs(struct ath10k *ar,
|
||||
const struct phyerr_fft_report *fftr;
|
||||
const u8 *tlv_buf;
|
||||
|
||||
buf_len = __le32_to_cpu(phyerr->buf_len);
|
||||
buf_len = phyerr->buf_len;
|
||||
ath10k_dbg(ar, ATH10K_DBG_REGULATORY,
|
||||
"wmi event dfs err_code %d rssi %d tsfl 0x%X tsf64 0x%llX len %d\n",
|
||||
phyerr->phy_err_code, phyerr->rssi_combined,
|
||||
__le32_to_cpu(phyerr->tsf_timestamp), tsf, buf_len);
|
||||
phyerr->tsf_timestamp, tsf, buf_len);
|
||||
|
||||
/* Skip event if DFS disabled */
|
||||
if (!config_enabled(CONFIG_ATH10K_DFS_CERTIFIED))
|
||||
@ -3461,7 +3464,7 @@ void ath10k_wmi_event_dfs(struct ath10k *ar,
|
||||
}
|
||||
|
||||
void ath10k_wmi_event_spectral_scan(struct ath10k *ar,
|
||||
const struct wmi_phyerr *phyerr,
|
||||
struct wmi_phyerr_ev_arg *phyerr,
|
||||
u64 tsf)
|
||||
{
|
||||
int buf_len, tlv_len, res, i = 0;
|
||||
@ -3470,7 +3473,7 @@ void ath10k_wmi_event_spectral_scan(struct ath10k *ar,
|
||||
const struct phyerr_fft_report *fftr;
|
||||
size_t fftr_len;
|
||||
|
||||
buf_len = __le32_to_cpu(phyerr->buf_len);
|
||||
buf_len = phyerr->buf_len;
|
||||
|
||||
while (i < buf_len) {
|
||||
if (i + sizeof(*tlv) > buf_len) {
|
||||
@ -3514,65 +3517,169 @@ void ath10k_wmi_event_spectral_scan(struct ath10k *ar,
|
||||
}
|
||||
}
|
||||
|
||||
static int ath10k_wmi_op_pull_phyerr_ev(struct ath10k *ar, struct sk_buff *skb,
|
||||
struct wmi_phyerr_ev_arg *arg)
|
||||
static int ath10k_wmi_op_pull_phyerr_ev_hdr(struct ath10k *ar,
|
||||
struct sk_buff *skb,
|
||||
struct wmi_phyerr_hdr_arg *arg)
|
||||
{
|
||||
struct wmi_phyerr_event *ev = (void *)skb->data;
|
||||
|
||||
if (skb->len < sizeof(*ev))
|
||||
return -EPROTO;
|
||||
|
||||
arg->num_phyerrs = ev->num_phyerrs;
|
||||
arg->tsf_l32 = ev->tsf_l32;
|
||||
arg->tsf_u32 = ev->tsf_u32;
|
||||
arg->buf_len = __cpu_to_le32(skb->len - sizeof(*ev));
|
||||
arg->num_phyerrs = __le32_to_cpu(ev->num_phyerrs);
|
||||
arg->tsf_l32 = __le32_to_cpu(ev->tsf_l32);
|
||||
arg->tsf_u32 = __le32_to_cpu(ev->tsf_u32);
|
||||
arg->buf_len = skb->len - sizeof(*ev);
|
||||
arg->phyerrs = ev->phyerrs;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int ath10k_wmi_10_4_op_pull_phyerr_ev_hdr(struct ath10k *ar,
|
||||
struct sk_buff *skb,
|
||||
struct wmi_phyerr_hdr_arg *arg)
|
||||
{
|
||||
struct wmi_10_4_phyerr_event *ev = (void *)skb->data;
|
||||
|
||||
if (skb->len < sizeof(*ev))
|
||||
return -EPROTO;
|
||||
|
||||
/* 10.4 firmware always reports only one phyerr */
|
||||
arg->num_phyerrs = 1;
|
||||
|
||||
arg->tsf_l32 = __le32_to_cpu(ev->tsf_l32);
|
||||
arg->tsf_u32 = __le32_to_cpu(ev->tsf_u32);
|
||||
arg->buf_len = skb->len;
|
||||
arg->phyerrs = skb->data;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int ath10k_wmi_op_pull_phyerr_ev(struct ath10k *ar,
|
||||
const void *phyerr_buf,
|
||||
int left_len,
|
||||
struct wmi_phyerr_ev_arg *arg)
|
||||
{
|
||||
const struct wmi_phyerr *phyerr = phyerr_buf;
|
||||
int i;
|
||||
|
||||
if (left_len < sizeof(*phyerr)) {
|
||||
ath10k_warn(ar, "wrong phyerr event head len %d (need: >=%zd)\n",
|
||||
left_len, sizeof(*phyerr));
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
arg->tsf_timestamp = __le32_to_cpu(phyerr->tsf_timestamp);
|
||||
arg->freq1 = __le16_to_cpu(phyerr->freq1);
|
||||
arg->freq2 = __le16_to_cpu(phyerr->freq2);
|
||||
arg->rssi_combined = phyerr->rssi_combined;
|
||||
arg->chan_width_mhz = phyerr->chan_width_mhz;
|
||||
arg->buf_len = __le32_to_cpu(phyerr->buf_len);
|
||||
arg->buf = phyerr->buf;
|
||||
arg->hdr_len = sizeof(*phyerr);
|
||||
|
||||
for (i = 0; i < 4; i++)
|
||||
arg->nf_chains[i] = __le16_to_cpu(phyerr->nf_chains[i]);
|
||||
|
||||
switch (phyerr->phy_err_code) {
|
||||
case PHY_ERROR_GEN_SPECTRAL_SCAN:
|
||||
arg->phy_err_code = PHY_ERROR_SPECTRAL_SCAN;
|
||||
break;
|
||||
case PHY_ERROR_GEN_FALSE_RADAR_EXT:
|
||||
arg->phy_err_code = PHY_ERROR_FALSE_RADAR_EXT;
|
||||
break;
|
||||
case PHY_ERROR_GEN_RADAR:
|
||||
arg->phy_err_code = PHY_ERROR_RADAR;
|
||||
break;
|
||||
default:
|
||||
arg->phy_err_code = PHY_ERROR_UNKNOWN;
|
||||
break;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int ath10k_wmi_10_4_op_pull_phyerr_ev(struct ath10k *ar,
|
||||
const void *phyerr_buf,
|
||||
int left_len,
|
||||
struct wmi_phyerr_ev_arg *arg)
|
||||
{
|
||||
const struct wmi_10_4_phyerr_event *phyerr = phyerr_buf;
|
||||
u32 phy_err_mask;
|
||||
int i;
|
||||
|
||||
if (left_len < sizeof(*phyerr)) {
|
||||
ath10k_warn(ar, "wrong phyerr event head len %d (need: >=%zd)\n",
|
||||
left_len, sizeof(*phyerr));
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
arg->tsf_timestamp = __le32_to_cpu(phyerr->tsf_timestamp);
|
||||
arg->freq1 = __le16_to_cpu(phyerr->freq1);
|
||||
arg->freq2 = __le16_to_cpu(phyerr->freq2);
|
||||
arg->rssi_combined = phyerr->rssi_combined;
|
||||
arg->chan_width_mhz = phyerr->chan_width_mhz;
|
||||
arg->buf_len = __le32_to_cpu(phyerr->buf_len);
|
||||
arg->buf = phyerr->buf;
|
||||
arg->hdr_len = sizeof(*phyerr);
|
||||
|
||||
for (i = 0; i < 4; i++)
|
||||
arg->nf_chains[i] = __le16_to_cpu(phyerr->nf_chains[i]);
|
||||
|
||||
phy_err_mask = __le32_to_cpu(phyerr->phy_err_mask[0]);
|
||||
|
||||
if (phy_err_mask & PHY_ERROR_10_4_SPECTRAL_SCAN_MASK)
|
||||
arg->phy_err_code = PHY_ERROR_SPECTRAL_SCAN;
|
||||
else if (phy_err_mask & PHY_ERROR_10_4_RADAR_MASK)
|
||||
arg->phy_err_code = PHY_ERROR_RADAR;
|
||||
else
|
||||
arg->phy_err_code = PHY_ERROR_UNKNOWN;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
void ath10k_wmi_event_phyerr(struct ath10k *ar, struct sk_buff *skb)
|
||||
{
|
||||
struct wmi_phyerr_ev_arg arg = {};
|
||||
const struct wmi_phyerr *phyerr;
|
||||
struct wmi_phyerr_hdr_arg hdr_arg = {};
|
||||
struct wmi_phyerr_ev_arg phyerr_arg = {};
|
||||
const void *phyerr;
|
||||
u32 count, i, buf_len, phy_err_code;
|
||||
u64 tsf;
|
||||
int left_len, ret;
|
||||
|
||||
ATH10K_DFS_STAT_INC(ar, phy_errors);
|
||||
|
||||
ret = ath10k_wmi_pull_phyerr(ar, skb, &arg);
|
||||
ret = ath10k_wmi_pull_phyerr_hdr(ar, skb, &hdr_arg);
|
||||
if (ret) {
|
||||
ath10k_warn(ar, "failed to parse phyerr event: %d\n", ret);
|
||||
ath10k_warn(ar, "failed to parse phyerr event hdr: %d\n", ret);
|
||||
return;
|
||||
}
|
||||
|
||||
left_len = __le32_to_cpu(arg.buf_len);
|
||||
|
||||
/* Check number of included events */
|
||||
count = __le32_to_cpu(arg.num_phyerrs);
|
||||
count = hdr_arg.num_phyerrs;
|
||||
|
||||
tsf = __le32_to_cpu(arg.tsf_u32);
|
||||
left_len = hdr_arg.buf_len;
|
||||
|
||||
tsf = hdr_arg.tsf_u32;
|
||||
tsf <<= 32;
|
||||
tsf |= __le32_to_cpu(arg.tsf_l32);
|
||||
tsf |= hdr_arg.tsf_l32;
|
||||
|
||||
ath10k_dbg(ar, ATH10K_DBG_WMI,
|
||||
"wmi event phyerr count %d tsf64 0x%llX\n",
|
||||
count, tsf);
|
||||
|
||||
phyerr = arg.phyerrs;
|
||||
phyerr = hdr_arg.phyerrs;
|
||||
for (i = 0; i < count; i++) {
|
||||
/* Check if we can read event header */
|
||||
if (left_len < sizeof(*phyerr)) {
|
||||
ath10k_warn(ar, "single event (%d) wrong head len\n",
|
||||
ret = ath10k_wmi_pull_phyerr(ar, phyerr, left_len, &phyerr_arg);
|
||||
if (ret) {
|
||||
ath10k_warn(ar, "failed to parse phyerr event (%d)\n",
|
||||
i);
|
||||
return;
|
||||
}
|
||||
|
||||
left_len -= sizeof(*phyerr);
|
||||
|
||||
buf_len = __le32_to_cpu(phyerr->buf_len);
|
||||
phy_err_code = phyerr->phy_err_code;
|
||||
left_len -= phyerr_arg.hdr_len;
|
||||
buf_len = phyerr_arg.buf_len;
|
||||
phy_err_code = phyerr_arg.phy_err_code;
|
||||
|
||||
if (left_len < buf_len) {
|
||||
ath10k_warn(ar, "single event (%d) wrong buf len\n", i);
|
||||
@ -3583,20 +3690,20 @@ void ath10k_wmi_event_phyerr(struct ath10k *ar, struct sk_buff *skb)
|
||||
|
||||
switch (phy_err_code) {
|
||||
case PHY_ERROR_RADAR:
|
||||
ath10k_wmi_event_dfs(ar, phyerr, tsf);
|
||||
ath10k_wmi_event_dfs(ar, &phyerr_arg, tsf);
|
||||
break;
|
||||
case PHY_ERROR_SPECTRAL_SCAN:
|
||||
ath10k_wmi_event_spectral_scan(ar, phyerr, tsf);
|
||||
ath10k_wmi_event_spectral_scan(ar, &phyerr_arg, tsf);
|
||||
break;
|
||||
case PHY_ERROR_FALSE_RADAR_EXT:
|
||||
ath10k_wmi_event_dfs(ar, phyerr, tsf);
|
||||
ath10k_wmi_event_spectral_scan(ar, phyerr, tsf);
|
||||
ath10k_wmi_event_dfs(ar, &phyerr_arg, tsf);
|
||||
ath10k_wmi_event_spectral_scan(ar, &phyerr_arg, tsf);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
phyerr = (void *)phyerr + sizeof(*phyerr) + buf_len;
|
||||
phyerr = phyerr + phyerr_arg.hdr_len + buf_len;
|
||||
}
|
||||
}
|
||||
|
||||
@ -4488,6 +4595,9 @@ static void ath10k_wmi_10_4_op_rx(struct ath10k *ar, struct sk_buff *skb)
|
||||
case WMI_10_4_CHAN_INFO_EVENTID:
|
||||
ath10k_wmi_event_chan_info(ar, skb);
|
||||
break;
|
||||
case WMI_10_4_PHYERR_EVENTID:
|
||||
ath10k_wmi_event_phyerr(ar, skb);
|
||||
break;
|
||||
case WMI_10_4_READY_EVENTID:
|
||||
ath10k_wmi_event_ready(ar, skb);
|
||||
break;
|
||||
@ -6195,6 +6305,7 @@ static const struct wmi_ops wmi_ops = {
|
||||
.pull_vdev_start = ath10k_wmi_op_pull_vdev_start_ev,
|
||||
.pull_peer_kick = ath10k_wmi_op_pull_peer_kick_ev,
|
||||
.pull_swba = ath10k_wmi_op_pull_swba_ev,
|
||||
.pull_phyerr_hdr = ath10k_wmi_op_pull_phyerr_ev_hdr,
|
||||
.pull_phyerr = ath10k_wmi_op_pull_phyerr_ev,
|
||||
.pull_svc_rdy = ath10k_wmi_main_op_pull_svc_rdy_ev,
|
||||
.pull_rdy = ath10k_wmi_op_pull_rdy_ev,
|
||||
@ -6266,6 +6377,7 @@ static const struct wmi_ops wmi_10_1_ops = {
|
||||
.pull_vdev_start = ath10k_wmi_op_pull_vdev_start_ev,
|
||||
.pull_peer_kick = ath10k_wmi_op_pull_peer_kick_ev,
|
||||
.pull_swba = ath10k_wmi_op_pull_swba_ev,
|
||||
.pull_phyerr_hdr = ath10k_wmi_op_pull_phyerr_ev_hdr,
|
||||
.pull_phyerr = ath10k_wmi_op_pull_phyerr_ev,
|
||||
.pull_rdy = ath10k_wmi_op_pull_rdy_ev,
|
||||
.pull_roam_ev = ath10k_wmi_op_pull_roam_ev,
|
||||
@ -6331,6 +6443,7 @@ static const struct wmi_ops wmi_10_2_ops = {
|
||||
.pull_vdev_start = ath10k_wmi_op_pull_vdev_start_ev,
|
||||
.pull_peer_kick = ath10k_wmi_op_pull_peer_kick_ev,
|
||||
.pull_swba = ath10k_wmi_op_pull_swba_ev,
|
||||
.pull_phyerr_hdr = ath10k_wmi_op_pull_phyerr_ev_hdr,
|
||||
.pull_phyerr = ath10k_wmi_op_pull_phyerr_ev,
|
||||
.pull_rdy = ath10k_wmi_op_pull_rdy_ev,
|
||||
.pull_roam_ev = ath10k_wmi_op_pull_roam_ev,
|
||||
@ -6392,6 +6505,7 @@ static const struct wmi_ops wmi_10_2_4_ops = {
|
||||
.pull_vdev_start = ath10k_wmi_op_pull_vdev_start_ev,
|
||||
.pull_peer_kick = ath10k_wmi_op_pull_peer_kick_ev,
|
||||
.pull_swba = ath10k_wmi_op_pull_swba_ev,
|
||||
.pull_phyerr_hdr = ath10k_wmi_op_pull_phyerr_ev_hdr,
|
||||
.pull_phyerr = ath10k_wmi_op_pull_phyerr_ev,
|
||||
.pull_rdy = ath10k_wmi_op_pull_rdy_ev,
|
||||
.pull_roam_ev = ath10k_wmi_op_pull_roam_ev,
|
||||
@ -6447,6 +6561,8 @@ static const struct wmi_ops wmi_10_4_ops = {
|
||||
.pull_vdev_start = ath10k_wmi_op_pull_vdev_start_ev,
|
||||
.pull_peer_kick = ath10k_wmi_op_pull_peer_kick_ev,
|
||||
.pull_swba = ath10k_wmi_10_4_op_pull_swba_ev,
|
||||
.pull_phyerr_hdr = ath10k_wmi_10_4_op_pull_phyerr_ev_hdr,
|
||||
.pull_phyerr = ath10k_wmi_10_4_op_pull_phyerr_ev,
|
||||
.pull_svc_rdy = ath10k_wmi_main_op_pull_svc_rdy_ev,
|
||||
.pull_rdy = ath10k_wmi_op_pull_rdy_ev,
|
||||
.get_txbf_conf_scheme = ath10k_wmi_10_4_txbf_conf_scheme,
|
||||
@ -6466,6 +6582,8 @@ static const struct wmi_ops wmi_10_4_ops = {
|
||||
.gen_vdev_down = ath10k_wmi_op_gen_vdev_down,
|
||||
.gen_vdev_set_param = ath10k_wmi_op_gen_vdev_set_param,
|
||||
.gen_vdev_install_key = ath10k_wmi_op_gen_vdev_install_key,
|
||||
.gen_vdev_spectral_conf = ath10k_wmi_op_gen_vdev_spectral_conf,
|
||||
.gen_vdev_spectral_enable = ath10k_wmi_op_gen_vdev_spectral_enable,
|
||||
.gen_peer_create = ath10k_wmi_op_gen_peer_create,
|
||||
.gen_peer_delete = ath10k_wmi_op_gen_peer_delete,
|
||||
.gen_peer_flush = ath10k_wmi_op_gen_peer_flush,
|
||||
@ -6482,6 +6600,10 @@ static const struct wmi_ops wmi_10_4_ops = {
|
||||
.gen_pktlog_enable = ath10k_wmi_op_gen_pktlog_enable,
|
||||
.gen_pktlog_disable = ath10k_wmi_op_gen_pktlog_disable,
|
||||
.gen_pdev_set_quiet_mode = ath10k_wmi_op_gen_pdev_set_quiet_mode,
|
||||
.gen_addba_clear_resp = ath10k_wmi_op_gen_addba_clear_resp,
|
||||
.gen_addba_send = ath10k_wmi_op_gen_addba_send,
|
||||
.gen_addba_set_resp = ath10k_wmi_op_gen_addba_set_resp,
|
||||
.gen_delba_send = ath10k_wmi_op_gen_delba_send,
|
||||
|
||||
/* shared with 10.2 */
|
||||
.gen_peer_assoc = ath10k_wmi_10_2_op_gen_peer_assoc,
|
||||
|
@ -2973,9 +2973,19 @@ struct wmi_10_4_mgmt_rx_event {
|
||||
#define WMI_RX_STATUS_ERR_MIC 0x10
|
||||
#define WMI_RX_STATUS_ERR_KEY_CACHE_MISS 0x20
|
||||
|
||||
#define PHY_ERROR_SPECTRAL_SCAN 0x26
|
||||
#define PHY_ERROR_FALSE_RADAR_EXT 0x24
|
||||
#define PHY_ERROR_RADAR 0x05
|
||||
#define PHY_ERROR_GEN_SPECTRAL_SCAN 0x26
|
||||
#define PHY_ERROR_GEN_FALSE_RADAR_EXT 0x24
|
||||
#define PHY_ERROR_GEN_RADAR 0x05
|
||||
|
||||
#define PHY_ERROR_10_4_RADAR_MASK 0x4
|
||||
#define PHY_ERROR_10_4_SPECTRAL_SCAN_MASK 0x4000000
|
||||
|
||||
enum phy_err_type {
|
||||
PHY_ERROR_UNKNOWN,
|
||||
PHY_ERROR_SPECTRAL_SCAN,
|
||||
PHY_ERROR_FALSE_RADAR_EXT,
|
||||
PHY_ERROR_RADAR
|
||||
};
|
||||
|
||||
struct wmi_phyerr {
|
||||
__le32 tsf_timestamp;
|
||||
@ -2998,6 +3008,23 @@ struct wmi_phyerr_event {
|
||||
struct wmi_phyerr phyerrs[0];
|
||||
} __packed;
|
||||
|
||||
struct wmi_10_4_phyerr_event {
|
||||
__le32 tsf_l32;
|
||||
__le32 tsf_u32;
|
||||
__le16 freq1;
|
||||
__le16 freq2;
|
||||
u8 rssi_combined;
|
||||
u8 chan_width_mhz;
|
||||
u8 phy_err_code;
|
||||
u8 rsvd0;
|
||||
__le32 rssi_chains[4];
|
||||
__le16 nf_chains[4];
|
||||
__le32 phy_err_mask[2];
|
||||
__le32 tsf_timestamp;
|
||||
__le32 buf_len;
|
||||
u8 buf[0];
|
||||
} __packed;
|
||||
|
||||
#define PHYERR_TLV_SIG 0xBB
|
||||
#define PHYERR_TLV_TAG_SEARCH_FFT_REPORT 0xFB
|
||||
#define PHYERR_TLV_TAG_RADAR_PULSE_SUMMARY 0xF8
|
||||
@ -5590,6 +5617,7 @@ struct wmi_peer_sta_kickout_event {
|
||||
} __packed;
|
||||
|
||||
#define WMI_CHAN_INFO_FLAG_COMPLETE BIT(0)
|
||||
#define WMI_CHAN_INFO_FLAG_PRE_COMPLETE BIT(1)
|
||||
|
||||
/* Beacon filter wmi command info */
|
||||
#define BCN_FLT_MAX_SUPPORTED_IES 256
|
||||
@ -5788,11 +5816,24 @@ struct wmi_swba_ev_arg {
|
||||
};
|
||||
|
||||
struct wmi_phyerr_ev_arg {
|
||||
__le32 num_phyerrs;
|
||||
__le32 tsf_l32;
|
||||
__le32 tsf_u32;
|
||||
__le32 buf_len;
|
||||
const struct wmi_phyerr *phyerrs;
|
||||
u32 tsf_timestamp;
|
||||
u16 freq1;
|
||||
u16 freq2;
|
||||
u8 rssi_combined;
|
||||
u8 chan_width_mhz;
|
||||
u8 phy_err_code;
|
||||
u16 nf_chains[4];
|
||||
u32 buf_len;
|
||||
const u8 *buf;
|
||||
u8 hdr_len;
|
||||
};
|
||||
|
||||
struct wmi_phyerr_hdr_arg {
|
||||
u32 num_phyerrs;
|
||||
u32 tsf_l32;
|
||||
u32 tsf_u32;
|
||||
u32 buf_len;
|
||||
const void *phyerrs;
|
||||
};
|
||||
|
||||
struct wmi_svc_rdy_ev_arg {
|
||||
@ -6070,9 +6111,9 @@ void ath10k_wmi_event_peer_sta_kickout(struct ath10k *ar, struct sk_buff *skb);
|
||||
void ath10k_wmi_event_host_swba(struct ath10k *ar, struct sk_buff *skb);
|
||||
void ath10k_wmi_event_tbttoffset_update(struct ath10k *ar, struct sk_buff *skb);
|
||||
void ath10k_wmi_event_dfs(struct ath10k *ar,
|
||||
const struct wmi_phyerr *phyerr, u64 tsf);
|
||||
struct wmi_phyerr_ev_arg *phyerr, u64 tsf);
|
||||
void ath10k_wmi_event_spectral_scan(struct ath10k *ar,
|
||||
const struct wmi_phyerr *phyerr,
|
||||
struct wmi_phyerr_ev_arg *phyerr,
|
||||
u64 tsf);
|
||||
void ath10k_wmi_event_phyerr(struct ath10k *ar, struct sk_buff *skb);
|
||||
void ath10k_wmi_event_roam(struct ath10k *ar, struct sk_buff *skb);
|
||||
@ -6101,5 +6142,6 @@ void ath10k_wmi_event_vdev_standby_req(struct ath10k *ar, struct sk_buff *skb);
|
||||
void ath10k_wmi_event_vdev_resume_req(struct ath10k *ar, struct sk_buff *skb);
|
||||
void ath10k_wmi_event_service_ready(struct ath10k *ar, struct sk_buff *skb);
|
||||
int ath10k_wmi_event_ready(struct ath10k *ar, struct sk_buff *skb);
|
||||
|
||||
int ath10k_wmi_op_pull_phyerr_ev(struct ath10k *ar, const void *phyerr_buf,
|
||||
int left_len, struct wmi_phyerr_ev_arg *arg);
|
||||
#endif /* _WMI_H_ */
|
||||
|
@ -794,8 +794,11 @@ void ath9k_htc_ani_work(struct work_struct *work)
|
||||
common->ani.longcal_timer = timestamp;
|
||||
}
|
||||
|
||||
/* Short calibration applies only while caldone is false */
|
||||
if (!common->ani.caldone) {
|
||||
/*
|
||||
* Short calibration applies only while caldone
|
||||
* is false or -ETIMEDOUT
|
||||
*/
|
||||
if (common->ani.caldone <= 0) {
|
||||
if ((timestamp - common->ani.shortcal_timer) >=
|
||||
short_cal_interval) {
|
||||
shortcal = true;
|
||||
@ -844,7 +847,11 @@ set_timer:
|
||||
*/
|
||||
cal_interval = ATH_LONG_CALINTERVAL;
|
||||
cal_interval = min(cal_interval, (u32)ATH_ANI_POLLINTERVAL);
|
||||
if (!common->ani.caldone)
|
||||
/*
|
||||
* Short calibration applies only while caldone
|
||||
* is false or -ETIMEDOUT
|
||||
*/
|
||||
if (common->ani.caldone <= 0)
|
||||
cal_interval = min(cal_interval, (u32)short_cal_interval);
|
||||
|
||||
ieee80211_queue_delayed_work(common->hw, &priv->ani_work,
|
||||
|
@ -806,7 +806,7 @@ int wmi_call(struct wil6210_priv *wil, u16 cmdid, void *buf, u16 len,
|
||||
u16 reply_id, void *reply, u8 reply_size, int to_msec)
|
||||
{
|
||||
int rc;
|
||||
int remain;
|
||||
unsigned long remain;
|
||||
|
||||
mutex_lock(&wil->wmi_mutex);
|
||||
|
||||
|
@ -469,6 +469,36 @@ brcmf_find_wpsie(const u8 *parse, u32 len)
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static int brcmf_vif_change_validate(struct brcmf_cfg80211_info *cfg,
|
||||
struct brcmf_cfg80211_vif *vif,
|
||||
enum nl80211_iftype new_type)
|
||||
{
|
||||
int iftype_num[NUM_NL80211_IFTYPES];
|
||||
struct brcmf_cfg80211_vif *pos;
|
||||
|
||||
memset(&iftype_num[0], 0, sizeof(iftype_num));
|
||||
list_for_each_entry(pos, &cfg->vif_list, list)
|
||||
if (pos == vif)
|
||||
iftype_num[new_type]++;
|
||||
else
|
||||
iftype_num[pos->wdev.iftype]++;
|
||||
|
||||
return cfg80211_check_combinations(cfg->wiphy, 1, 0, iftype_num);
|
||||
}
|
||||
|
||||
static int brcmf_vif_add_validate(struct brcmf_cfg80211_info *cfg,
|
||||
enum nl80211_iftype new_type)
|
||||
{
|
||||
int iftype_num[NUM_NL80211_IFTYPES];
|
||||
struct brcmf_cfg80211_vif *pos;
|
||||
|
||||
memset(&iftype_num[0], 0, sizeof(iftype_num));
|
||||
list_for_each_entry(pos, &cfg->vif_list, list)
|
||||
iftype_num[pos->wdev.iftype]++;
|
||||
|
||||
iftype_num[new_type]++;
|
||||
return cfg80211_check_combinations(cfg->wiphy, 1, 0, iftype_num);
|
||||
}
|
||||
|
||||
static void convert_key_from_CPU(struct brcmf_wsec_key *key,
|
||||
struct brcmf_wsec_key_le *key_le)
|
||||
@ -663,8 +693,14 @@ static struct wireless_dev *brcmf_cfg80211_add_iface(struct wiphy *wiphy,
|
||||
struct vif_params *params)
|
||||
{
|
||||
struct wireless_dev *wdev;
|
||||
int err;
|
||||
|
||||
brcmf_dbg(TRACE, "enter: %s type %d\n", name, type);
|
||||
err = brcmf_vif_add_validate(wiphy_to_cfg(wiphy), type);
|
||||
if (err) {
|
||||
brcmf_err("iface validation failed: err=%d\n", err);
|
||||
return ERR_PTR(err);
|
||||
}
|
||||
switch (type) {
|
||||
case NL80211_IFTYPE_ADHOC:
|
||||
case NL80211_IFTYPE_STATION:
|
||||
@ -823,8 +859,12 @@ brcmf_cfg80211_change_iface(struct wiphy *wiphy, struct net_device *ndev,
|
||||
s32 ap = 0;
|
||||
s32 err = 0;
|
||||
|
||||
brcmf_dbg(TRACE, "Enter, ndev=%p, type=%d\n", ndev, type);
|
||||
|
||||
brcmf_dbg(TRACE, "Enter, idx=%d, type=%d\n", ifp->bssidx, type);
|
||||
err = brcmf_vif_change_validate(wiphy_to_cfg(wiphy), vif, type);
|
||||
if (err) {
|
||||
brcmf_err("iface validation failed: err=%d\n", err);
|
||||
return err;
|
||||
}
|
||||
switch (type) {
|
||||
case NL80211_IFTYPE_MONITOR:
|
||||
case NL80211_IFTYPE_WDS:
|
||||
@ -5695,63 +5735,132 @@ brcmf_txrx_stypes[NUM_NL80211_IFTYPES] = {
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* brcmf_setup_ifmodes() - determine interface modes and combinations.
|
||||
*
|
||||
* @wiphy: wiphy object.
|
||||
* @ifp: interface object needed for feat module api.
|
||||
*
|
||||
* The interface modes and combinations are determined dynamically here
|
||||
* based on firmware functionality.
|
||||
*
|
||||
* no p2p and no mbss:
|
||||
*
|
||||
* #STA <= 1, #AP <= 1, channels = 1, 2 total
|
||||
*
|
||||
* no p2p and mbss:
|
||||
*
|
||||
* #STA <= 1, #AP <= 1, channels = 1, 2 total
|
||||
* #AP <= 4, matching BI, channels = 1, 4 total
|
||||
*
|
||||
* p2p, no mchan, and mbss:
|
||||
*
|
||||
* #STA <= 1, #P2P-DEV <= 1, #{P2P-CL, P2P-GO} <= 1, channels = 1, 3 total
|
||||
* #STA <= 1, #P2P-DEV <= 1, #AP <= 1, #P2P-CL <= 1, channels = 1, 4 total
|
||||
* #AP <= 4, matching BI, channels = 1, 4 total
|
||||
*
|
||||
* p2p, mchan, and mbss:
|
||||
*
|
||||
* #STA <= 1, #P2P-DEV <= 1, #{P2P-CL, P2P-GO} <= 1, channels = 2, 3 total
|
||||
* #STA <= 1, #P2P-DEV <= 1, #AP <= 1, #P2P-CL <= 1, channels = 1, 4 total
|
||||
* #AP <= 4, matching BI, channels = 1, 4 total
|
||||
*/
|
||||
static int brcmf_setup_ifmodes(struct wiphy *wiphy, struct brcmf_if *ifp)
|
||||
{
|
||||
struct ieee80211_iface_combination *combo = NULL;
|
||||
struct ieee80211_iface_limit *limits = NULL;
|
||||
int i = 0, max_iface_cnt;
|
||||
struct ieee80211_iface_limit *c0_limits = NULL;
|
||||
struct ieee80211_iface_limit *p2p_limits = NULL;
|
||||
struct ieee80211_iface_limit *mbss_limits = NULL;
|
||||
bool mbss, p2p;
|
||||
int i, c, n_combos;
|
||||
|
||||
combo = kzalloc(sizeof(*combo), GFP_KERNEL);
|
||||
mbss = brcmf_feat_is_enabled(ifp, BRCMF_FEAT_MBSS);
|
||||
p2p = brcmf_feat_is_enabled(ifp, BRCMF_FEAT_P2P);
|
||||
|
||||
n_combos = 1 + !!p2p + !!mbss;
|
||||
combo = kcalloc(n_combos, sizeof(*combo), GFP_KERNEL);
|
||||
if (!combo)
|
||||
goto err;
|
||||
|
||||
limits = kzalloc(sizeof(*limits) * 4, GFP_KERNEL);
|
||||
if (!limits)
|
||||
c0_limits = kcalloc(p2p ? 3 : 2, sizeof(*c0_limits), GFP_KERNEL);
|
||||
if (!c0_limits)
|
||||
goto err;
|
||||
|
||||
if (p2p) {
|
||||
p2p_limits = kcalloc(4, sizeof(*p2p_limits), GFP_KERNEL);
|
||||
if (!p2p_limits)
|
||||
goto err;
|
||||
}
|
||||
|
||||
if (mbss) {
|
||||
mbss_limits = kcalloc(1, sizeof(*mbss_limits), GFP_KERNEL);
|
||||
if (!mbss_limits)
|
||||
goto err;
|
||||
}
|
||||
|
||||
wiphy->interface_modes = BIT(NL80211_IFTYPE_STATION) |
|
||||
BIT(NL80211_IFTYPE_ADHOC) |
|
||||
BIT(NL80211_IFTYPE_AP);
|
||||
|
||||
if (brcmf_feat_is_enabled(ifp, BRCMF_FEAT_MCHAN))
|
||||
combo->num_different_channels = 2;
|
||||
else
|
||||
combo->num_different_channels = 1;
|
||||
|
||||
if (brcmf_feat_is_enabled(ifp, BRCMF_FEAT_MBSS)) {
|
||||
limits[i].max = 1;
|
||||
limits[i++].types = BIT(NL80211_IFTYPE_STATION);
|
||||
limits[i].max = 4;
|
||||
limits[i++].types = BIT(NL80211_IFTYPE_AP);
|
||||
max_iface_cnt = 5;
|
||||
} else {
|
||||
limits[i].max = 2;
|
||||
limits[i++].types = BIT(NL80211_IFTYPE_STATION) |
|
||||
BIT(NL80211_IFTYPE_AP);
|
||||
max_iface_cnt = 2;
|
||||
}
|
||||
|
||||
if (brcmf_feat_is_enabled(ifp, BRCMF_FEAT_P2P)) {
|
||||
c = 0;
|
||||
i = 0;
|
||||
combo[c].num_different_channels = 1;
|
||||
c0_limits[i].max = 1;
|
||||
c0_limits[i++].types = BIT(NL80211_IFTYPE_STATION);
|
||||
if (p2p) {
|
||||
if (brcmf_feat_is_enabled(ifp, BRCMF_FEAT_MCHAN))
|
||||
combo[c].num_different_channels = 2;
|
||||
wiphy->interface_modes |= BIT(NL80211_IFTYPE_P2P_CLIENT) |
|
||||
BIT(NL80211_IFTYPE_P2P_GO) |
|
||||
BIT(NL80211_IFTYPE_P2P_DEVICE);
|
||||
limits[i].max = 1;
|
||||
limits[i++].types = BIT(NL80211_IFTYPE_P2P_CLIENT) |
|
||||
BIT(NL80211_IFTYPE_P2P_GO);
|
||||
limits[i].max = 1;
|
||||
limits[i++].types = BIT(NL80211_IFTYPE_P2P_DEVICE);
|
||||
max_iface_cnt += 2;
|
||||
c0_limits[i].max = 1;
|
||||
c0_limits[i++].types = BIT(NL80211_IFTYPE_P2P_DEVICE);
|
||||
c0_limits[i].max = 1;
|
||||
c0_limits[i++].types = BIT(NL80211_IFTYPE_P2P_CLIENT) |
|
||||
BIT(NL80211_IFTYPE_P2P_GO);
|
||||
} else {
|
||||
c0_limits[i].max = 1;
|
||||
c0_limits[i++].types = BIT(NL80211_IFTYPE_AP);
|
||||
}
|
||||
combo->max_interfaces = max_iface_cnt;
|
||||
combo->limits = limits;
|
||||
combo->n_limits = i;
|
||||
combo[c].max_interfaces = i;
|
||||
combo[c].n_limits = i;
|
||||
combo[c].limits = c0_limits;
|
||||
|
||||
if (p2p) {
|
||||
c++;
|
||||
i = 0;
|
||||
combo[c].num_different_channels = 1;
|
||||
p2p_limits[i].max = 1;
|
||||
p2p_limits[i++].types = BIT(NL80211_IFTYPE_STATION);
|
||||
p2p_limits[i].max = 1;
|
||||
p2p_limits[i++].types = BIT(NL80211_IFTYPE_AP);
|
||||
p2p_limits[i].max = 1;
|
||||
p2p_limits[i++].types = BIT(NL80211_IFTYPE_P2P_CLIENT);
|
||||
p2p_limits[i].max = 1;
|
||||
p2p_limits[i++].types = BIT(NL80211_IFTYPE_P2P_DEVICE);
|
||||
combo[c].max_interfaces = i;
|
||||
combo[c].n_limits = i;
|
||||
combo[c].limits = p2p_limits;
|
||||
}
|
||||
|
||||
if (mbss) {
|
||||
c++;
|
||||
combo[c].beacon_int_infra_match = true;
|
||||
combo[c].num_different_channels = 1;
|
||||
mbss_limits[0].max = 4;
|
||||
mbss_limits[0].types = BIT(NL80211_IFTYPE_AP);
|
||||
combo[c].max_interfaces = 4;
|
||||
combo[c].n_limits = 1;
|
||||
combo[c].limits = mbss_limits;
|
||||
}
|
||||
wiphy->n_iface_combinations = n_combos;
|
||||
wiphy->iface_combinations = combo;
|
||||
wiphy->n_iface_combinations = 1;
|
||||
return 0;
|
||||
|
||||
err:
|
||||
kfree(limits);
|
||||
kfree(c0_limits);
|
||||
kfree(p2p_limits);
|
||||
kfree(mbss_limits);
|
||||
kfree(combo);
|
||||
return -ENOMEM;
|
||||
}
|
||||
@ -5786,7 +5895,9 @@ static void brcmf_wiphy_wowl_params(struct wiphy *wiphy)
|
||||
static int brcmf_setup_wiphy(struct wiphy *wiphy, struct brcmf_if *ifp)
|
||||
{
|
||||
struct brcmf_pub *drvr = ifp->drvr;
|
||||
const struct ieee80211_iface_combination *combo;
|
||||
struct ieee80211_supported_band *band;
|
||||
u16 max_interfaces = 0;
|
||||
__le32 bandlist[3];
|
||||
u32 n_bands;
|
||||
int err, i;
|
||||
@ -5799,8 +5910,13 @@ static int brcmf_setup_wiphy(struct wiphy *wiphy, struct brcmf_if *ifp)
|
||||
if (err)
|
||||
return err;
|
||||
|
||||
for (i = 0; i < wiphy->iface_combinations->max_interfaces &&
|
||||
i < ARRAY_SIZE(drvr->addresses); i++) {
|
||||
for (i = 0, combo = wiphy->iface_combinations;
|
||||
i < wiphy->n_iface_combinations; i++, combo++) {
|
||||
max_interfaces = max(max_interfaces, combo->max_interfaces);
|
||||
}
|
||||
|
||||
for (i = 0; i < max_interfaces && i < ARRAY_SIZE(drvr->addresses);
|
||||
i++) {
|
||||
u8 *addr = drvr->addresses[i].addr;
|
||||
|
||||
memcpy(addr, drvr->mac, ETH_ALEN);
|
||||
@ -6073,11 +6189,15 @@ static void brcmf_cfg80211_reg_notifier(struct wiphy *wiphy,
|
||||
|
||||
static void brcmf_free_wiphy(struct wiphy *wiphy)
|
||||
{
|
||||
int i;
|
||||
|
||||
if (!wiphy)
|
||||
return;
|
||||
|
||||
if (wiphy->iface_combinations)
|
||||
kfree(wiphy->iface_combinations->limits);
|
||||
if (wiphy->iface_combinations) {
|
||||
for (i = 0; i < wiphy->n_iface_combinations; i++)
|
||||
kfree(wiphy->iface_combinations[i].limits);
|
||||
}
|
||||
kfree(wiphy->iface_combinations);
|
||||
if (wiphy->bands[IEEE80211_BAND_2GHZ]) {
|
||||
kfree(wiphy->bands[IEEE80211_BAND_2GHZ]->channels);
|
||||
|
@ -19,6 +19,7 @@
|
||||
#include <linux/device.h>
|
||||
#include <linux/firmware.h>
|
||||
#include <linux/module.h>
|
||||
#include <linux/bcm47xx_nvram.h>
|
||||
|
||||
#include "debug.h"
|
||||
#include "firmware.h"
|
||||
@ -426,19 +427,33 @@ static void brcmf_fw_request_nvram_done(const struct firmware *fw, void *ctx)
|
||||
struct brcmf_fw *fwctx = ctx;
|
||||
u32 nvram_length = 0;
|
||||
void *nvram = NULL;
|
||||
u8 *data = NULL;
|
||||
size_t data_len;
|
||||
bool raw_nvram;
|
||||
|
||||
brcmf_dbg(TRACE, "enter: dev=%s\n", dev_name(fwctx->dev));
|
||||
if (!fw && !(fwctx->flags & BRCMF_FW_REQ_NV_OPTIONAL))
|
||||
goto fail;
|
||||
|
||||
if (fw) {
|
||||
nvram = brcmf_fw_nvram_strip(fw->data, fw->size, &nvram_length,
|
||||
fwctx->domain_nr, fwctx->bus_nr);
|
||||
release_firmware(fw);
|
||||
if (!nvram && !(fwctx->flags & BRCMF_FW_REQ_NV_OPTIONAL))
|
||||
if (fw && fw->data) {
|
||||
data = (u8 *)fw->data;
|
||||
data_len = fw->size;
|
||||
raw_nvram = false;
|
||||
} else {
|
||||
data = bcm47xx_nvram_get_contents(&data_len);
|
||||
if (!data && !(fwctx->flags & BRCMF_FW_REQ_NV_OPTIONAL))
|
||||
goto fail;
|
||||
raw_nvram = true;
|
||||
}
|
||||
|
||||
if (data)
|
||||
nvram = brcmf_fw_nvram_strip(data, data_len, &nvram_length,
|
||||
fwctx->domain_nr, fwctx->bus_nr);
|
||||
|
||||
if (raw_nvram)
|
||||
bcm47xx_nvram_release_contents(data);
|
||||
if (fw)
|
||||
release_firmware(fw);
|
||||
if (!nvram && !(fwctx->flags & BRCMF_FW_REQ_NV_OPTIONAL))
|
||||
goto fail;
|
||||
|
||||
fwctx->done(fwctx->dev, fwctx->code, nvram, nvram_length);
|
||||
kfree(fwctx);
|
||||
return;
|
||||
@ -473,15 +488,9 @@ static void brcmf_fw_request_code_done(const struct firmware *fw, void *ctx)
|
||||
if (!ret)
|
||||
return;
|
||||
|
||||
/* when nvram is optional call .done() callback here */
|
||||
if (fwctx->flags & BRCMF_FW_REQ_NV_OPTIONAL) {
|
||||
fwctx->done(fwctx->dev, fw, NULL, 0);
|
||||
kfree(fwctx);
|
||||
return;
|
||||
}
|
||||
brcmf_fw_request_nvram_done(NULL, fwctx);
|
||||
return;
|
||||
|
||||
/* failed nvram request */
|
||||
release_firmware(fw);
|
||||
fail:
|
||||
brcmf_dbg(TRACE, "failed: dev=%s\n", dev_name(fwctx->dev));
|
||||
device_release_driver(fwctx->dev);
|
||||
|
@ -194,11 +194,15 @@ static void brcmf_flowring_block(struct brcmf_flowring *flow, u8 flowid,
|
||||
spin_lock_irqsave(&flow->block_lock, flags);
|
||||
|
||||
ring = flow->rings[flowid];
|
||||
if (ring->blocked == blocked) {
|
||||
spin_unlock_irqrestore(&flow->block_lock, flags);
|
||||
return;
|
||||
}
|
||||
ifidx = brcmf_flowring_ifidx_get(flow, flowid);
|
||||
|
||||
currently_blocked = false;
|
||||
for (i = 0; i < flow->nrofrings; i++) {
|
||||
if (flow->rings[i]) {
|
||||
if ((flow->rings[i]) && (i != flowid)) {
|
||||
ring = flow->rings[i];
|
||||
if ((ring->status == RING_OPEN) &&
|
||||
(brcmf_flowring_ifidx_get(flow, i) == ifidx)) {
|
||||
@ -209,8 +213,8 @@ static void brcmf_flowring_block(struct brcmf_flowring *flow, u8 flowid,
|
||||
}
|
||||
}
|
||||
}
|
||||
ring->blocked = blocked;
|
||||
if (currently_blocked == blocked) {
|
||||
flow->rings[flowid]->blocked = blocked;
|
||||
if (currently_blocked) {
|
||||
spin_unlock_irqrestore(&flow->block_lock, flags);
|
||||
return;
|
||||
}
|
||||
|
@ -85,7 +85,6 @@ struct brcmf_event;
|
||||
BRCMF_ENUM_DEF(IF, 54) \
|
||||
BRCMF_ENUM_DEF(P2P_DISC_LISTEN_COMPLETE, 55) \
|
||||
BRCMF_ENUM_DEF(RSSI, 56) \
|
||||
BRCMF_ENUM_DEF(PFN_SCAN_COMPLETE, 57) \
|
||||
BRCMF_ENUM_DEF(EXTLOG_MSG, 58) \
|
||||
BRCMF_ENUM_DEF(ACTION_FRAME, 59) \
|
||||
BRCMF_ENUM_DEF(ACTION_FRAME_COMPLETE, 60) \
|
||||
@ -103,8 +102,7 @@ struct brcmf_event;
|
||||
BRCMF_ENUM_DEF(FIFO_CREDIT_MAP, 74) \
|
||||
BRCMF_ENUM_DEF(ACTION_FRAME_RX, 75) \
|
||||
BRCMF_ENUM_DEF(TDLS_PEER_EVENT, 92) \
|
||||
BRCMF_ENUM_DEF(BCMC_CREDIT_SUPPORT, 127) \
|
||||
BRCMF_ENUM_DEF(PSTA_PRIMARY_INTF_IND, 128)
|
||||
BRCMF_ENUM_DEF(BCMC_CREDIT_SUPPORT, 127)
|
||||
|
||||
#define BRCMF_ENUM_DEF(id, val) \
|
||||
BRCMF_E_##id = (val),
|
||||
@ -112,7 +110,11 @@ struct brcmf_event;
|
||||
/* firmware event codes sent by the dongle */
|
||||
enum brcmf_fweh_event_code {
|
||||
BRCMF_FWEH_EVENT_ENUM_DEFLIST
|
||||
BRCMF_E_LAST
|
||||
/* this determines event mask length which must match
|
||||
* minimum length check in device firmware so it is
|
||||
* hard-coded here.
|
||||
*/
|
||||
BRCMF_E_LAST = 139
|
||||
};
|
||||
#undef BRCMF_ENUM_DEF
|
||||
|
||||
|
@ -1360,6 +1360,60 @@ void brcmf_msgbuf_delete_flowring(struct brcmf_pub *drvr, u8 flowid)
|
||||
}
|
||||
}
|
||||
|
||||
#ifdef DEBUG
|
||||
static int brcmf_msgbuf_stats_read(struct seq_file *seq, void *data)
|
||||
{
|
||||
struct brcmf_bus *bus_if = dev_get_drvdata(seq->private);
|
||||
struct brcmf_pub *drvr = bus_if->drvr;
|
||||
struct brcmf_msgbuf *msgbuf = (struct brcmf_msgbuf *)drvr->proto->pd;
|
||||
struct brcmf_commonring *commonring;
|
||||
u16 i;
|
||||
struct brcmf_flowring_ring *ring;
|
||||
struct brcmf_flowring_hash *hash;
|
||||
|
||||
commonring = msgbuf->commonrings[BRCMF_H2D_MSGRING_CONTROL_SUBMIT];
|
||||
seq_printf(seq, "h2d_ctl_submit: rp %4u, wp %4u, depth %4u\n",
|
||||
commonring->r_ptr, commonring->w_ptr, commonring->depth);
|
||||
commonring = msgbuf->commonrings[BRCMF_H2D_MSGRING_RXPOST_SUBMIT];
|
||||
seq_printf(seq, "h2d_rx_submit: rp %4u, wp %4u, depth %4u\n",
|
||||
commonring->r_ptr, commonring->w_ptr, commonring->depth);
|
||||
commonring = msgbuf->commonrings[BRCMF_D2H_MSGRING_CONTROL_COMPLETE];
|
||||
seq_printf(seq, "d2h_ctl_cmplt: rp %4u, wp %4u, depth %4u\n",
|
||||
commonring->r_ptr, commonring->w_ptr, commonring->depth);
|
||||
commonring = msgbuf->commonrings[BRCMF_D2H_MSGRING_TX_COMPLETE];
|
||||
seq_printf(seq, "d2h_tx_cmplt: rp %4u, wp %4u, depth %4u\n",
|
||||
commonring->r_ptr, commonring->w_ptr, commonring->depth);
|
||||
commonring = msgbuf->commonrings[BRCMF_D2H_MSGRING_RX_COMPLETE];
|
||||
seq_printf(seq, "d2h_rx_cmplt: rp %4u, wp %4u, depth %4u\n",
|
||||
commonring->r_ptr, commonring->w_ptr, commonring->depth);
|
||||
|
||||
seq_printf(seq, "\nh2d_flowrings: depth %u\n",
|
||||
BRCMF_H2D_TXFLOWRING_MAX_ITEM);
|
||||
seq_puts(seq, "Active flowrings:\n");
|
||||
hash = msgbuf->flow->hash;
|
||||
for (i = 0; i < msgbuf->flow->nrofrings; i++) {
|
||||
if (!msgbuf->flow->rings[i])
|
||||
continue;
|
||||
ring = msgbuf->flow->rings[i];
|
||||
if (ring->status != RING_OPEN)
|
||||
continue;
|
||||
commonring = msgbuf->flowrings[i];
|
||||
hash = &msgbuf->flow->hash[ring->hash_id];
|
||||
seq_printf(seq, "id %3u: rp %4u, wp %4u, qlen %4u, blocked %u\n"
|
||||
" ifidx %u, fifo %u, da %pM\n",
|
||||
i, commonring->r_ptr, commonring->w_ptr,
|
||||
skb_queue_len(&ring->skblist), ring->blocked,
|
||||
hash->ifidx, hash->fifo, hash->mac);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
#else
|
||||
static int brcmf_msgbuf_stats_read(struct seq_file *seq, void *data)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
int brcmf_proto_msgbuf_attach(struct brcmf_pub *drvr)
|
||||
{
|
||||
@ -1460,6 +1514,8 @@ int brcmf_proto_msgbuf_attach(struct brcmf_pub *drvr)
|
||||
spin_lock_init(&msgbuf->flowring_work_lock);
|
||||
INIT_LIST_HEAD(&msgbuf->work_queue);
|
||||
|
||||
brcmf_debugfs_add_entry(drvr, "msgbuf_stats", brcmf_msgbuf_stats_read);
|
||||
|
||||
return 0;
|
||||
|
||||
fail:
|
||||
|
@ -473,7 +473,7 @@ do { \
|
||||
} while (0)
|
||||
#endif /* CONFIG_IWLWIFI_DEBUG */
|
||||
|
||||
extern const char *const iwl_dvm_cmd_strings[REPLY_MAX];
|
||||
extern const char *const iwl_dvm_cmd_strings[REPLY_MAX + 1];
|
||||
|
||||
static inline const char *iwl_dvm_get_cmd_string(u8 cmd)
|
||||
{
|
||||
|
@ -39,7 +39,7 @@
|
||||
|
||||
#define IWL_CMD_ENTRY(x) [x] = #x
|
||||
|
||||
const char *const iwl_dvm_cmd_strings[REPLY_MAX] = {
|
||||
const char *const iwl_dvm_cmd_strings[REPLY_MAX + 1] = {
|
||||
IWL_CMD_ENTRY(REPLY_ALIVE),
|
||||
IWL_CMD_ENTRY(REPLY_ERROR),
|
||||
IWL_CMD_ENTRY(REPLY_ECHO),
|
||||
|
@ -69,7 +69,7 @@
|
||||
#include "iwl-agn-hw.h"
|
||||
|
||||
/* Highest firmware API version supported */
|
||||
#define IWL7260_UCODE_API_MAX 16
|
||||
#define IWL7260_UCODE_API_MAX 17
|
||||
|
||||
/* Oldest version we won't warn about */
|
||||
#define IWL7260_UCODE_API_OK 12
|
||||
|
@ -69,7 +69,7 @@
|
||||
#include "iwl-agn-hw.h"
|
||||
|
||||
/* Highest firmware API version supported */
|
||||
#define IWL8000_UCODE_API_MAX 16
|
||||
#define IWL8000_UCODE_API_MAX 17
|
||||
|
||||
/* Oldest version we won't warn about */
|
||||
#define IWL8000_UCODE_API_OK 12
|
||||
|
@ -259,6 +259,8 @@ typedef unsigned int __bitwise__ iwl_ucode_tlv_api_t;
|
||||
* @IWL_UCODE_TLV_API_NEW_VERSION: new versioning format
|
||||
* @IWL_UCODE_TLV_API_EXT_SCAN_PRIORITY: scan APIs use 8-level priority
|
||||
* instead of 3.
|
||||
* @IWL_UCODE_TLV_API_TX_POWER_CHAIN: TX power API has larger command size
|
||||
* (command version 3) that supports per-chain limits
|
||||
*/
|
||||
enum iwl_ucode_tlv_api {
|
||||
IWL_UCODE_TLV_API_BT_COEX_SPLIT = (__force iwl_ucode_tlv_api_t)3,
|
||||
@ -274,6 +276,7 @@ enum iwl_ucode_tlv_api {
|
||||
IWL_UCODE_TLV_API_STATS_V10 = (__force iwl_ucode_tlv_api_t)19,
|
||||
IWL_UCODE_TLV_API_NEW_VERSION = (__force iwl_ucode_tlv_api_t)20,
|
||||
IWL_UCODE_TLV_API_EXT_SCAN_PRIORITY = (__force iwl_ucode_tlv_api_t)24,
|
||||
IWL_UCODE_TLV_API_TX_POWER_CHAIN = (__force iwl_ucode_tlv_api_t)27,
|
||||
};
|
||||
|
||||
typedef unsigned int __bitwise__ iwl_ucode_tlv_capa_t;
|
||||
|
@ -949,9 +949,10 @@ static ssize_t iwl_dbgfs_fw_dbg_conf_write(struct iwl_mvm *mvm,
|
||||
char *buf, size_t count,
|
||||
loff_t *ppos)
|
||||
{
|
||||
int ret, conf_id;
|
||||
unsigned int conf_id;
|
||||
int ret;
|
||||
|
||||
ret = kstrtoint(buf, 0, &conf_id);
|
||||
ret = kstrtouint(buf, 0, &conf_id);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
|
@ -339,8 +339,13 @@ enum iwl_wowlan_wakeup_reason {
|
||||
IWL_WOWLAN_WAKEUP_BY_FOUR_WAY_HANDSHAKE = BIT(8),
|
||||
IWL_WOWLAN_WAKEUP_BY_REM_WAKE_LINK_LOSS = BIT(9),
|
||||
IWL_WOWLAN_WAKEUP_BY_REM_WAKE_SIGNATURE_TABLE = BIT(10),
|
||||
/* BIT(11) reserved */
|
||||
IWL_WOWLAN_WAKEUP_BY_REM_WAKE_TCP_EXTERNAL = BIT(11),
|
||||
IWL_WOWLAN_WAKEUP_BY_REM_WAKE_WAKEUP_PACKET = BIT(12),
|
||||
IWL_WOWLAN_WAKEUP_BY_IOAC_MAGIC_PACKET = BIT(13),
|
||||
IWL_WOWLAN_WAKEUP_BY_D3_WAKEUP_HOST_TIMER = BIT(14),
|
||||
IWL_WOWLAN_WAKEUP_BY_RXFRAME_FILTERED_IN = BIT(15),
|
||||
IWL_WOWLAN_WAKEUP_BY_BEACON_FILTERED_IN = BIT(16),
|
||||
|
||||
}; /* WOWLAN_WAKE_UP_REASON_API_E_VER_2 */
|
||||
|
||||
struct iwl_wowlan_gtk_status {
|
||||
|
@ -7,6 +7,7 @@
|
||||
*
|
||||
* Copyright(c) 2012 - 2014 Intel Corporation. All rights reserved.
|
||||
* Copyright(c) 2013 - 2014 Intel Mobile Communications GmbH
|
||||
* Copyright(c) 2015 Intel Deutschland GmbH
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of version 2 of the GNU General Public License as
|
||||
@ -33,6 +34,7 @@
|
||||
*
|
||||
* Copyright(c) 2012 - 2014 Intel Corporation. All rights reserved.
|
||||
* Copyright(c) 2013 - 2014 Intel Mobile Communications GmbH
|
||||
* Copyright(c) 2015 Intel Deutschland GmbH
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
@ -310,17 +312,22 @@ struct iwl_reduce_tx_power_cmd {
|
||||
__le16 pwr_restriction;
|
||||
} __packed; /* TX_REDUCED_POWER_API_S_VER_1 */
|
||||
|
||||
enum iwl_dev_tx_power_cmd_mode {
|
||||
IWL_TX_POWER_MODE_SET_MAC = 0,
|
||||
IWL_TX_POWER_MODE_SET_DEVICE = 1,
|
||||
IWL_TX_POWER_MODE_SET_CHAINS = 2,
|
||||
}; /* TX_POWER_REDUCED_FLAGS_TYPE_API_E_VER_2 */;
|
||||
|
||||
/**
|
||||
* struct iwl_dev_tx_power_cmd - TX power reduction command
|
||||
* REDUCE_TX_POWER_CMD = 0x9f
|
||||
* @set_mode: 0 - MAC tx power, 1 - device tx power
|
||||
* struct iwl_dev_tx_power_cmd_v2 - TX power reduction command
|
||||
* @set_mode: see &enum iwl_dev_tx_power_cmd_mode
|
||||
* @mac_context_id: id of the mac ctx for which we are reducing TX power.
|
||||
* @pwr_restriction: TX power restriction in 1/8 dBms.
|
||||
* @dev_24: device TX power restriction in 1/8 dBms
|
||||
* @dev_52_low: device TX power restriction upper band - low
|
||||
* @dev_52_high: device TX power restriction upper band - high
|
||||
*/
|
||||
struct iwl_dev_tx_power_cmd {
|
||||
struct iwl_dev_tx_power_cmd_v2 {
|
||||
__le32 set_mode;
|
||||
__le32 mac_context_id;
|
||||
__le16 pwr_restriction;
|
||||
@ -329,6 +336,20 @@ struct iwl_dev_tx_power_cmd {
|
||||
__le16 dev_52_high;
|
||||
} __packed; /* TX_REDUCED_POWER_API_S_VER_2 */
|
||||
|
||||
#define IWL_NUM_CHAIN_LIMITS 2
|
||||
#define IWL_NUM_SUB_BANDS 5
|
||||
|
||||
/**
|
||||
* struct iwl_dev_tx_power_cmd - TX power reduction command
|
||||
* @v2: version 2 of the command, embedded here for easier software handling
|
||||
* @per_chain_restriction: per chain restrictions
|
||||
*/
|
||||
struct iwl_dev_tx_power_cmd {
|
||||
/* v3 is just an extension of v2 - keep this here */
|
||||
struct iwl_dev_tx_power_cmd_v2 v2;
|
||||
__le16 per_chain_restriction[IWL_NUM_CHAIN_LIMITS][IWL_NUM_SUB_BANDS];
|
||||
} __packed; /* TX_REDUCED_POWER_API_S_VER_3 */
|
||||
|
||||
#define IWL_DEV_MAX_TX_POWER 0x7FFF
|
||||
|
||||
/**
|
||||
|
@ -1595,20 +1595,23 @@ static int iwl_mvm_set_tx_power(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
|
||||
s16 tx_power)
|
||||
{
|
||||
struct iwl_dev_tx_power_cmd cmd = {
|
||||
.set_mode = 0,
|
||||
.mac_context_id =
|
||||
.v2.set_mode = cpu_to_le32(IWL_TX_POWER_MODE_SET_MAC),
|
||||
.v2.mac_context_id =
|
||||
cpu_to_le32(iwl_mvm_vif_from_mac80211(vif)->id),
|
||||
.pwr_restriction = cpu_to_le16(8 * tx_power),
|
||||
.v2.pwr_restriction = cpu_to_le16(8 * tx_power),
|
||||
};
|
||||
int len = sizeof(cmd);
|
||||
|
||||
if (!fw_has_api(&mvm->fw->ucode_capa, IWL_UCODE_TLV_API_TX_POWER_DEV))
|
||||
return iwl_mvm_set_tx_power_old(mvm, vif, tx_power);
|
||||
|
||||
if (tx_power == IWL_DEFAULT_MAX_TX_POWER)
|
||||
cmd.pwr_restriction = cpu_to_le16(IWL_DEV_MAX_TX_POWER);
|
||||
cmd.v2.pwr_restriction = cpu_to_le16(IWL_DEV_MAX_TX_POWER);
|
||||
|
||||
return iwl_mvm_send_cmd_pdu(mvm, REDUCE_TX_POWER_CMD, 0,
|
||||
sizeof(cmd), &cmd);
|
||||
if (!fw_has_api(&mvm->fw->ucode_capa, IWL_UCODE_TLV_API_TX_POWER_CHAIN))
|
||||
len = sizeof(cmd.v2);
|
||||
|
||||
return iwl_mvm_send_cmd_pdu(mvm, REDUCE_TX_POWER_CMD, 0, len, &cmd);
|
||||
}
|
||||
|
||||
static int iwl_mvm_mac_add_interface(struct ieee80211_hw *hw,
|
||||
|
@ -268,7 +268,7 @@ static const struct iwl_rx_handlers iwl_mvm_rx_handlers[] = {
|
||||
#undef RX_HANDLER_GRP
|
||||
#define CMD(x) [x] = #x
|
||||
|
||||
static const char *const iwl_mvm_cmd_strings[REPLY_MAX] = {
|
||||
static const char *const iwl_mvm_cmd_strings[REPLY_MAX + 1] = {
|
||||
CMD(MVM_ALIVE),
|
||||
CMD(REPLY_ERROR),
|
||||
CMD(INIT_COMPLETE_NOTIF),
|
||||
|
@ -349,10 +349,11 @@ void iwl_mvm_rx_lmac_scan_complete_notif(struct iwl_mvm *mvm,
|
||||
if (mvm->scan_status & IWL_MVM_SCAN_STOPPING_SCHED) {
|
||||
WARN_ON_ONCE(mvm->scan_status & IWL_MVM_SCAN_STOPPING_REGULAR);
|
||||
|
||||
IWL_DEBUG_SCAN(mvm,
|
||||
"Scheduled scan %s, EBS status %s, Last line %d, Last iteration %d, Time after last iteration %d\n",
|
||||
IWL_DEBUG_SCAN(mvm, "Scheduled scan %s, EBS status %s\n",
|
||||
aborted ? "aborted" : "completed",
|
||||
iwl_mvm_ebs_status_str(scan_notif->ebs_status),
|
||||
iwl_mvm_ebs_status_str(scan_notif->ebs_status));
|
||||
IWL_DEBUG_SCAN(mvm,
|
||||
"Last line %d, Last iteration %d, Time after last iteration %d\n",
|
||||
scan_notif->last_schedule_line,
|
||||
scan_notif->last_schedule_iteration,
|
||||
__le32_to_cpu(scan_notif->time_after_last_iter));
|
||||
@ -367,10 +368,11 @@ void iwl_mvm_rx_lmac_scan_complete_notif(struct iwl_mvm *mvm,
|
||||
} else if (mvm->scan_status & IWL_MVM_SCAN_SCHED) {
|
||||
WARN_ON_ONCE(mvm->scan_status & IWL_MVM_SCAN_REGULAR);
|
||||
|
||||
IWL_DEBUG_SCAN(mvm,
|
||||
"Scheduled scan %s, EBS status %s, Last line %d, Last iteration %d, Time after last iteration %d (FW)\n",
|
||||
IWL_DEBUG_SCAN(mvm, "Scheduled scan %s, EBS status %s\n",
|
||||
aborted ? "aborted" : "completed",
|
||||
iwl_mvm_ebs_status_str(scan_notif->ebs_status),
|
||||
iwl_mvm_ebs_status_str(scan_notif->ebs_status));
|
||||
IWL_DEBUG_SCAN(mvm,
|
||||
"Last line %d, Last iteration %d, Time after last iteration %d (FW)\n",
|
||||
scan_notif->last_schedule_line,
|
||||
scan_notif->last_schedule_iteration,
|
||||
__le32_to_cpu(scan_notif->time_after_last_iter));
|
||||
@ -1346,11 +1348,13 @@ void iwl_mvm_rx_umac_scan_complete_notif(struct iwl_mvm *mvm,
|
||||
|
||||
mvm->scan_status &= ~mvm->scan_uid_status[uid];
|
||||
IWL_DEBUG_SCAN(mvm,
|
||||
"Scan completed, uid %u type %u, status %s, EBS status %s, Last line %d, Last iteration %d, Time from last iteration %d\n",
|
||||
"Scan completed, uid %u type %u, status %s, EBS status %s\n",
|
||||
uid, mvm->scan_uid_status[uid],
|
||||
notif->status == IWL_SCAN_OFFLOAD_COMPLETED ?
|
||||
"completed" : "aborted",
|
||||
iwl_mvm_ebs_status_str(notif->ebs_status),
|
||||
iwl_mvm_ebs_status_str(notif->ebs_status));
|
||||
IWL_DEBUG_SCAN(mvm,
|
||||
"Last line %d, Last iteration %d, Time from last iteration %d\n",
|
||||
notif->last_schedule, notif->last_iter,
|
||||
__le32_to_cpu(notif->time_from_last_iter));
|
||||
|
||||
|
@ -203,8 +203,10 @@ static int rsi_load_ta_instructions(struct rsi_common *common)
|
||||
|
||||
/* Copy firmware into DMA-accessible memory */
|
||||
fw = kmemdup(fw_entry->data, fw_entry->size, GFP_KERNEL);
|
||||
if (!fw)
|
||||
return -ENOMEM;
|
||||
if (!fw) {
|
||||
status = -ENOMEM;
|
||||
goto out;
|
||||
}
|
||||
len = fw_entry->size;
|
||||
|
||||
if (len % 4)
|
||||
@ -217,6 +219,8 @@ static int rsi_load_ta_instructions(struct rsi_common *common)
|
||||
|
||||
status = rsi_copy_to_card(common, fw, len, num_blocks);
|
||||
kfree(fw);
|
||||
|
||||
out:
|
||||
release_firmware(fw_entry);
|
||||
return status;
|
||||
}
|
||||
|
@ -148,8 +148,10 @@ static int rsi_load_ta_instructions(struct rsi_common *common)
|
||||
|
||||
/* Copy firmware into DMA-accessible memory */
|
||||
fw = kmemdup(fw_entry->data, fw_entry->size, GFP_KERNEL);
|
||||
if (!fw)
|
||||
return -ENOMEM;
|
||||
if (!fw) {
|
||||
status = -ENOMEM;
|
||||
goto out;
|
||||
}
|
||||
len = fw_entry->size;
|
||||
|
||||
if (len % 4)
|
||||
@ -162,6 +164,8 @@ static int rsi_load_ta_instructions(struct rsi_common *common)
|
||||
|
||||
status = rsi_copy_to_card(common, fw, len, num_blocks);
|
||||
kfree(fw);
|
||||
|
||||
out:
|
||||
release_firmware(fw_entry);
|
||||
return status;
|
||||
}
|
||||
|
@ -321,6 +321,7 @@ static struct usb_device_id rtl8192c_usb_ids[] = {
|
||||
{RTL_USB_DEVICE(0x07b8, 0x8188, rtl92cu_hal_cfg)}, /*Abocom - Abocom*/
|
||||
{RTL_USB_DEVICE(0x07b8, 0x8189, rtl92cu_hal_cfg)}, /*Funai - Abocom*/
|
||||
{RTL_USB_DEVICE(0x0846, 0x9041, rtl92cu_hal_cfg)}, /*NetGear WNA1000M*/
|
||||
{RTL_USB_DEVICE(0x0846, 0x9043, rtl92cu_hal_cfg)}, /*NG WNA1000Mv2*/
|
||||
{RTL_USB_DEVICE(0x0b05, 0x17ba, rtl92cu_hal_cfg)}, /*ASUS-Edimax*/
|
||||
{RTL_USB_DEVICE(0x0bda, 0x5088, rtl92cu_hal_cfg)}, /*Thinkware-CC&C*/
|
||||
{RTL_USB_DEVICE(0x0df6, 0x0052, rtl92cu_hal_cfg)}, /*Sitecom - Edimax*/
|
||||
|
@ -449,7 +449,7 @@ static void _rtl92ee_phy_set_txpower_by_rate_base(struct ieee80211_hw *hw,
|
||||
"Invalid RateSection %d in 2.4G,Rf %d,%dTx\n",
|
||||
rate_section, path, txnum);
|
||||
break;
|
||||
};
|
||||
}
|
||||
} else {
|
||||
RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
|
||||
"Invalid Band %d\n", band);
|
||||
@ -489,7 +489,7 @@ static u8 _rtl92ee_phy_get_txpower_by_rate_base(struct ieee80211_hw *hw,
|
||||
"Invalid RateSection %d in 2.4G,Rf %d,%dTx\n",
|
||||
rate_section, path, txnum);
|
||||
break;
|
||||
};
|
||||
}
|
||||
} else {
|
||||
RT_TRACE(rtlpriv, COMP_INIT, DBG_LOUD,
|
||||
"Invalid Band %d()\n", band);
|
||||
@ -853,7 +853,7 @@ static u8 _rtl92ee_get_rate_section_index(u32 regaddr)
|
||||
else if (regaddr >= 0xE20 && regaddr <= 0xE4C)
|
||||
index = (u8)((regaddr - 0xE20) / 4);
|
||||
break;
|
||||
};
|
||||
}
|
||||
return index;
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user