diff options
author | Linus Torvalds <torvalds@linux-foundation.org> | 2019-09-18 22:34:53 +0300 |
---|---|---|
committer | Linus Torvalds <torvalds@linux-foundation.org> | 2019-09-18 22:34:53 +0300 |
commit | 81160dda9a7aad13c04e78bb2cfd3c4630e3afab (patch) | |
tree | 4bf79ffa9fc7dc5e2915ff978778c3402c491113 /drivers/net/wireless/mediatek | |
parent | 8b53c76533aa4356602aea98f98a2f3b4051464c (diff) | |
parent | 1bab8d4c488be22d57f9dd09968c90a0ddc413bf (diff) | |
download | linux-81160dda9a7aad13c04e78bb2cfd3c4630e3afab.tar.xz |
Merge git://git.kernel.org/pub/scm/linux/kernel/git/netdev/net-next
Pull networking updates from David Miller:
1) Support IPV6 RA Captive Portal Identifier, from Maciej Żenczykowski.
2) Use bio_vec in the networking instead of custom skb_frag_t, from
Matthew Wilcox.
3) Make use of xmit_more in r8169 driver, from Heiner Kallweit.
4) Add devmap_hash to xdp, from Toke Høiland-Jørgensen.
5) Support all variants of 5750X bnxt_en chips, from Michael Chan.
6) More RTNL avoidance work in the core and mlx5 driver, from Vlad
Buslov.
7) Add TCP syn cookies bpf helper, from Petar Penkov.
8) Add 'nettest' to selftests and use it, from David Ahern.
9) Add extack support to drop_monitor, add packet alert mode and
support for HW drops, from Ido Schimmel.
10) Add VLAN offload to stmmac, from Jose Abreu.
11) Lots of devm_platform_ioremap_resource() conversions, from
YueHaibing.
12) Add IONIC driver, from Shannon Nelson.
13) Several kTLS cleanups, from Jakub Kicinski.
* git://git.kernel.org/pub/scm/linux/kernel/git/netdev/net-next: (1930 commits)
mlxsw: spectrum_buffers: Add the ability to query the CPU port's shared buffer
mlxsw: spectrum: Register CPU port with devlink
mlxsw: spectrum_buffers: Prevent changing CPU port's configuration
net: ena: fix incorrect update of intr_delay_resolution
net: ena: fix retrieval of nonadaptive interrupt moderation intervals
net: ena: fix update of interrupt moderation register
net: ena: remove all old adaptive rx interrupt moderation code from ena_com
net: ena: remove ena_restore_ethtool_params() and relevant fields
net: ena: remove old adaptive interrupt moderation code from ena_netdev
net: ena: remove code duplication in ena_com_update_nonadaptive_moderation_interval _*()
net: ena: enable the interrupt_moderation in driver_supported_features
net: ena: reimplement set/get_coalesce()
net: ena: switch to dim algorithm for rx adaptive interrupt moderation
net: ena: add intr_moder_rx_interval to struct ena_com_dev and use it
net: phy: adin: implement Energy Detect Powerdown mode via phy-tunable
ethtool: implement Energy Detect Powerdown support via phy-tunable
xen-netfront: do not assume sk_buff_head list is empty in error handling
s390/ctcm: Delete unnecessary checks before the macro call “dev_kfree_skb”
net: ena: don't wake up tx queue when down
drop_monitor: Better sanitize notified packets
...
Diffstat (limited to 'drivers/net/wireless/mediatek')
100 files changed, 1876 insertions, 1523 deletions
diff --git a/drivers/net/wireless/mediatek/mt76/agg-rx.c b/drivers/net/wireless/mediatek/mt76/agg-rx.c index 27e3ff039c48..8f3d36a15e17 100644 --- a/drivers/net/wireless/mediatek/mt76/agg-rx.c +++ b/drivers/net/wireless/mediatek/mt76/agg-rx.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2018 Felix Fietkau <nbd@nbd.name> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include "mt76.h" @@ -34,8 +23,9 @@ mt76_aggr_release(struct mt76_rx_tid *tid, struct sk_buff_head *frames, int idx) } static void -mt76_rx_aggr_release_frames(struct mt76_rx_tid *tid, struct sk_buff_head *frames, - u16 head) +mt76_rx_aggr_release_frames(struct mt76_rx_tid *tid, + struct sk_buff_head *frames, + u16 head) { int idx; @@ -74,15 +64,14 @@ mt76_rx_aggr_check_release(struct mt76_rx_tid *tid, struct sk_buff_head *frames) for (idx = (tid->head + 1) % tid->size; idx != start && nframes; idx = (idx + 1) % tid->size) { - skb = tid->reorder_buf[idx]; if (!skb) continue; nframes--; - status = (struct mt76_rx_status *) skb->cb; - if (!time_after(jiffies, status->reorder_time + - REORDER_TIMEOUT)) + status = (struct mt76_rx_status *)skb->cb; + if (!time_after(jiffies, + status->reorder_time + REORDER_TIMEOUT)) continue; mt76_rx_aggr_release_frames(tid, frames, status->seqno); @@ -122,8 +111,8 @@ mt76_rx_aggr_reorder_work(struct work_struct *work) static void mt76_rx_aggr_check_ctl(struct sk_buff *skb, struct sk_buff_head *frames) { - struct mt76_rx_status *status = (struct mt76_rx_status *) skb->cb; - struct ieee80211_bar *bar = (struct ieee80211_bar *) skb->data; + struct mt76_rx_status *status = (struct mt76_rx_status *)skb->cb; + struct ieee80211_bar *bar = (struct ieee80211_bar *)skb->data; struct mt76_wcid *wcid = status->wcid; struct mt76_rx_tid *tid; u16 seqno; @@ -148,8 +137,8 @@ mt76_rx_aggr_check_ctl(struct sk_buff *skb, struct sk_buff_head *frames) void mt76_rx_aggr_reorder(struct sk_buff *skb, struct sk_buff_head *frames) { - struct mt76_rx_status *status = (struct mt76_rx_status *) skb->cb; - struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) skb->data; + struct mt76_rx_status *status = (struct mt76_rx_status *)skb->cb; + struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)skb->data; struct mt76_wcid *wcid = status->wcid; struct ieee80211_sta *sta; struct mt76_rx_tid *tid; @@ -233,7 +222,8 @@ void mt76_rx_aggr_reorder(struct sk_buff *skb, struct sk_buff_head *frames) tid->nframes++; mt76_rx_aggr_release_head(tid, frames); - ieee80211_queue_delayed_work(tid->dev->hw, &tid->reorder_work, REORDER_TIMEOUT); + ieee80211_queue_delayed_work(tid->dev->hw, &tid->reorder_work, + REORDER_TIMEOUT); out: spin_unlock_bh(&tid->lock); diff --git a/drivers/net/wireless/mediatek/mt76/debugfs.c b/drivers/net/wireless/mediatek/mt76/debugfs.c index c6a9fe2aef9d..d95b73fd0d2b 100644 --- a/drivers/net/wireless/mediatek/mt76/debugfs.c +++ b/drivers/net/wireless/mediatek/mt76/debugfs.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include "mt76.h" diff --git a/drivers/net/wireless/mediatek/mt76/dma.c b/drivers/net/wireless/mediatek/mt76/dma.c index d8f61e540bfd..c747eb24581c 100644 --- a/drivers/net/wireless/mediatek/mt76/dma.c +++ b/drivers/net/wireless/mediatek/mt76/dma.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include <linux/dma-mapping.h> @@ -442,6 +431,12 @@ mt76_dma_rx_reset(struct mt76_dev *dev, enum mt76_rxq_id qid) mt76_dma_rx_cleanup(dev, q); mt76_dma_sync_idx(dev, q); mt76_dma_rx_fill(dev, q); + + if (!q->rx_head) + return; + + dev_kfree_skb(q->rx_head); + q->rx_head = NULL; } static void @@ -504,7 +499,7 @@ mt76_dma_rx_process(struct mt76_dev *dev, struct mt76_queue *q, int budget) skb_reserve(skb, q->buf_offset); if (q == &dev->q_rx[MT_RXQ_MCU]) { - u32 *rxfce = (u32 *) skb->cb; + u32 *rxfce = (u32 *)skb->cb; *rxfce = info; } diff --git a/drivers/net/wireless/mediatek/mt76/dma.h b/drivers/net/wireless/mediatek/mt76/dma.h index 03dd2bafa4e8..e7c27697ef04 100644 --- a/drivers/net/wireless/mediatek/mt76/dma.h +++ b/drivers/net/wireless/mediatek/mt76/dma.h @@ -1,17 +1,6 @@ +/* SPDX-License-Identifier: ISC */ /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef __MT76_DMA_H #define __MT76_DMA_H diff --git a/drivers/net/wireless/mediatek/mt76/eeprom.c b/drivers/net/wireless/mediatek/mt76/eeprom.c index b7a49ae6b327..804224e81103 100644 --- a/drivers/net/wireless/mediatek/mt76/eeprom.c +++ b/drivers/net/wireless/mediatek/mt76/eeprom.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include <linux/of.h> #include <linux/of_net.h> diff --git a/drivers/net/wireless/mediatek/mt76/mac80211.c b/drivers/net/wireless/mediatek/mt76/mac80211.c index ec9efb79985f..1a2c143b34d0 100644 --- a/drivers/net/wireless/mediatek/mt76/mac80211.c +++ b/drivers/net/wireless/mediatek/mt76/mac80211.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include <linux/of.h> #include "mt76.h" @@ -294,6 +283,8 @@ mt76_alloc_device(struct device *pdev, unsigned int size, init_waitqueue_head(&dev->tx_wait); skb_queue_head_init(&dev->status_list); + tasklet_init(&dev->tx_tasklet, mt76_tx_tasklet, (unsigned long)dev); + return dev; } EXPORT_SYMBOL_GPL(mt76_alloc_device); @@ -415,11 +406,6 @@ void mt76_set_channel(struct mt76_dev *dev) bool offchannel = hw->conf.flags & IEEE80211_CONF_OFFCHANNEL; int timeout = HZ / 5; - if (offchannel) - set_bit(MT76_OFFCHANNEL, &dev->state); - else - clear_bit(MT76_OFFCHANNEL, &dev->state); - wait_event_timeout(dev->tx_wait, !mt76_has_tx_pending(dev), timeout); if (dev->drv->update_survey) @@ -487,9 +473,10 @@ void mt76_wcid_key_setup(struct mt76_dev *dev, struct mt76_wcid *wcid, if (!key) return; - if (key->cipher == WLAN_CIPHER_SUITE_CCMP) - wcid->rx_check_pn = true; + if (key->cipher != WLAN_CIPHER_SUITE_CCMP) + return; + wcid->rx_check_pn = true; for (i = 0; i < IEEE80211_NUM_TIDS; i++) { ieee80211_get_key_rx_seq(key, i, &seq); memcpy(wcid->rx_key_pn[i], seq.ccmp.pn, sizeof(seq.ccmp.pn)); @@ -497,12 +484,12 @@ void mt76_wcid_key_setup(struct mt76_dev *dev, struct mt76_wcid *wcid, } EXPORT_SYMBOL(mt76_wcid_key_setup); -struct ieee80211_sta *mt76_rx_convert(struct sk_buff *skb) +static struct ieee80211_sta *mt76_rx_convert(struct sk_buff *skb) { struct ieee80211_rx_status *status = IEEE80211_SKB_RXCB(skb); struct mt76_rx_status mstat; - mstat = *((struct mt76_rx_status *) skb->cb); + mstat = *((struct mt76_rx_status *)skb->cb); memset(status, 0, sizeof(*status)); status->flag = mstat.flag; @@ -517,17 +504,18 @@ struct ieee80211_sta *mt76_rx_convert(struct sk_buff *skb) status->chains = mstat.chains; BUILD_BUG_ON(sizeof(mstat) > sizeof(skb->cb)); - BUILD_BUG_ON(sizeof(status->chain_signal) != sizeof(mstat.chain_signal)); - memcpy(status->chain_signal, mstat.chain_signal, sizeof(mstat.chain_signal)); + BUILD_BUG_ON(sizeof(status->chain_signal) != + sizeof(mstat.chain_signal)); + memcpy(status->chain_signal, mstat.chain_signal, + sizeof(mstat.chain_signal)); return wcid_to_sta(mstat.wcid); } -EXPORT_SYMBOL(mt76_rx_convert); static int mt76_check_ccmp_pn(struct sk_buff *skb) { - struct mt76_rx_status *status = (struct mt76_rx_status *) skb->cb; + struct mt76_rx_status *status = (struct mt76_rx_status *)skb->cb; struct mt76_wcid *wcid = status->wcid; struct ieee80211_hdr *hdr; int ret; @@ -543,7 +531,7 @@ mt76_check_ccmp_pn(struct sk_buff *skb) * Validate the first fragment both here and in mac80211 * All further fragments will be validated by mac80211 only. */ - hdr = (struct ieee80211_hdr *) skb->data; + hdr = (struct ieee80211_hdr *)skb->data; if (ieee80211_is_frag(hdr) && !ieee80211_is_first_frag(hdr->frame_control)) return 0; @@ -566,8 +554,8 @@ mt76_check_ccmp_pn(struct sk_buff *skb) static void mt76_check_sta(struct mt76_dev *dev, struct sk_buff *skb) { - struct mt76_rx_status *status = (struct mt76_rx_status *) skb->cb; - struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) skb->data; + struct mt76_rx_status *status = (struct mt76_rx_status *)skb->cb; + struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)skb->data; struct ieee80211_sta *sta; struct mt76_wcid *wcid = status->wcid; bool ps; @@ -576,13 +564,13 @@ mt76_check_sta(struct mt76_dev *dev, struct sk_buff *skb) if (ieee80211_is_pspoll(hdr->frame_control) && !wcid) { sta = ieee80211_find_sta_by_ifaddr(dev->hw, hdr->addr2, NULL); if (sta) - wcid = status->wcid = (struct mt76_wcid *) sta->drv_priv; + wcid = status->wcid = (struct mt76_wcid *)sta->drv_priv; } if (!wcid || !wcid->sta) return; - sta = container_of((void *) wcid, struct ieee80211_sta, drv_priv); + sta = container_of((void *)wcid, struct ieee80211_sta, drv_priv); if (status->signal <= 0) ewma_signal_add(&wcid->rssi, -status->signal); @@ -598,8 +586,8 @@ mt76_check_sta(struct mt76_dev *dev, struct sk_buff *skb) } if (ieee80211_has_morefrags(hdr->frame_control) || - !(ieee80211_is_mgmt(hdr->frame_control) || - ieee80211_is_data(hdr->frame_control))) + !(ieee80211_is_mgmt(hdr->frame_control) || + ieee80211_is_data(hdr->frame_control))) return; ps = ieee80211_has_pm(hdr->frame_control); @@ -628,7 +616,7 @@ mt76_check_sta(struct mt76_dev *dev, struct sk_buff *skb) if (!sta->txq[i]) continue; - mtxq = (struct mt76_txq *) sta->txq[i]->drv_priv; + mtxq = (struct mt76_txq *)sta->txq[i]->drv_priv; if (!skb_queue_empty(&mtxq->retry_q)) ieee80211_schedule_txq(dev->hw, sta->txq[i]); } @@ -714,6 +702,9 @@ void __mt76_sta_remove(struct mt76_dev *dev, struct ieee80211_vif *vif, rcu_assign_pointer(dev->wcid[idx], NULL); synchronize_rcu(); + for (i = 0; i < ARRAY_SIZE(wcid->aggr); i++) + mt76_rx_aggr_stop(dev, wcid, i); + if (dev->drv->sta_remove) dev->drv->sta_remove(dev, vif, sta); @@ -750,7 +741,7 @@ int mt76_sta_state(struct ieee80211_hw *hw, struct ieee80211_vif *vif, dev->drv->sta_assoc(dev, vif, sta); if (old_state == IEEE80211_STA_NONE && - new_state == IEEE80211_STA_NOTEXIST) + new_state == IEEE80211_STA_NOTEXIST) mt76_sta_remove(dev, vif, sta); return 0; @@ -790,7 +781,7 @@ static void __mt76_csa_finish(void *priv, u8 *mac, struct ieee80211_vif *vif) { if (vif->csa_active && ieee80211_csa_is_complete(vif)) - ieee80211_csa_finish(vif); + ieee80211_csa_finish(vif); } void mt76_csa_finish(struct mt76_dev *dev) @@ -878,3 +869,20 @@ int mt76_get_rate(struct mt76_dev *dev, return 0; } EXPORT_SYMBOL_GPL(mt76_get_rate); + +void mt76_sw_scan(struct ieee80211_hw *hw, struct ieee80211_vif *vif, + const u8 *mac) +{ + struct mt76_dev *dev = hw->priv; + + set_bit(MT76_SCANNING, &dev->state); +} +EXPORT_SYMBOL_GPL(mt76_sw_scan); + +void mt76_sw_scan_complete(struct ieee80211_hw *hw, struct ieee80211_vif *vif) +{ + struct mt76_dev *dev = hw->priv; + + clear_bit(MT76_SCANNING, &dev->state); +} +EXPORT_SYMBOL_GPL(mt76_sw_scan_complete); diff --git a/drivers/net/wireless/mediatek/mt76/mcu.c b/drivers/net/wireless/mediatek/mt76/mcu.c index dbb57b593a87..2a976688804d 100644 --- a/drivers/net/wireless/mediatek/mt76/mcu.c +++ b/drivers/net/wireless/mediatek/mt76/mcu.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2019 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include "mt76.h" diff --git a/drivers/net/wireless/mediatek/mt76/mmio.c b/drivers/net/wireless/mediatek/mt76/mmio.c index 38368d19aa6f..1c974df1fe25 100644 --- a/drivers/net/wireless/mediatek/mt76/mmio.c +++ b/drivers/net/wireless/mediatek/mt76/mmio.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include "mt76.h" @@ -40,10 +29,16 @@ static u32 mt76_mmio_rmw(struct mt76_dev *dev, u32 offset, u32 mask, u32 val) return val; } -static void mt76_mmio_copy(struct mt76_dev *dev, u32 offset, const void *data, - int len) +static void mt76_mmio_write_copy(struct mt76_dev *dev, u32 offset, + const void *data, int len) { - __iowrite32_copy(dev->mmio.regs + offset, data, len >> 2); + __iowrite32_copy(dev->mmio.regs + offset, data, DIV_ROUND_UP(len, 4)); +} + +static void mt76_mmio_read_copy(struct mt76_dev *dev, u32 offset, + void *data, int len) +{ + __ioread32_copy(data, dev->mmio.regs + offset, DIV_ROUND_UP(len, 4)); } static int mt76_mmio_wr_rp(struct mt76_dev *dev, u32 base, @@ -89,7 +84,8 @@ void mt76_mmio_init(struct mt76_dev *dev, void __iomem *regs) .rr = mt76_mmio_rr, .rmw = mt76_mmio_rmw, .wr = mt76_mmio_wr, - .copy = mt76_mmio_copy, + .write_copy = mt76_mmio_write_copy, + .read_copy = mt76_mmio_read_copy, .wr_rp = mt76_mmio_wr_rp, .rd_rp = mt76_mmio_rd_rp, .type = MT76_BUS_MMIO, diff --git a/drivers/net/wireless/mediatek/mt76/mt76.h b/drivers/net/wireless/mediatek/mt76/mt76.h index 989386ecb5e4..570c159515a0 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76.h +++ b/drivers/net/wireless/mediatek/mt76/mt76.h @@ -1,17 +1,6 @@ +/* SPDX-License-Identifier: ISC */ /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef __MT76_H @@ -49,8 +38,10 @@ struct mt76_bus_ops { u32 (*rr)(struct mt76_dev *dev, u32 offset); void (*wr)(struct mt76_dev *dev, u32 offset, u32 val); u32 (*rmw)(struct mt76_dev *dev, u32 offset, u32 mask, u32 val); - void (*copy)(struct mt76_dev *dev, u32 offset, const void *data, - int len); + void (*write_copy)(struct mt76_dev *dev, u32 offset, const void *data, + int len); + void (*read_copy)(struct mt76_dev *dev, u32 offset, void *data, + int len); int (*wr_rp)(struct mt76_dev *dev, u32 base, const struct mt76_reg_pair *rp, int len); int (*rd_rp)(struct mt76_dev *dev, u32 base, @@ -213,6 +204,7 @@ struct mt76_wcid { u8 rx_check_pn; u8 rx_key_pn[IEEE80211_NUM_TIDS][6]; + u16 cipher; u32 tx_info; bool sw_iv; @@ -280,7 +272,6 @@ enum { MT76_STATE_MCU_RUNNING, MT76_SCANNING, MT76_RESET, - MT76_OFFCHANNEL, MT76_REMOVED, MT76_READING_STATS, }; @@ -390,7 +381,10 @@ enum mt76u_out_ep { #define MCU_RESP_URB_SIZE 1024 struct mt76_usb { struct mutex usb_ctrl_mtx; - u8 data[32]; + union { + u8 data[32]; + __le32 reg_val; + }; struct tasklet_struct rx_tasklet; struct delayed_work stat_work; @@ -496,6 +490,8 @@ struct mt76_dev { u8 csa_complete; + ktime_t survey_time; + u32 rxfilter; union { @@ -538,7 +534,8 @@ struct mt76_rx_status { #define __mt76_rr(dev, ...) (dev)->bus->rr((dev), __VA_ARGS__) #define __mt76_wr(dev, ...) (dev)->bus->wr((dev), __VA_ARGS__) #define __mt76_rmw(dev, ...) (dev)->bus->rmw((dev), __VA_ARGS__) -#define __mt76_wr_copy(dev, ...) (dev)->bus->copy((dev), __VA_ARGS__) +#define __mt76_wr_copy(dev, ...) (dev)->bus->write_copy((dev), __VA_ARGS__) +#define __mt76_rr_copy(dev, ...) (dev)->bus->read_copy((dev), __VA_ARGS__) #define __mt76_set(dev, offset, val) __mt76_rmw(dev, offset, 0, val) #define __mt76_clear(dev, offset, val) __mt76_rmw(dev, offset, val, 0) @@ -546,7 +543,8 @@ struct mt76_rx_status { #define mt76_rr(dev, ...) (dev)->mt76.bus->rr(&((dev)->mt76), __VA_ARGS__) #define mt76_wr(dev, ...) (dev)->mt76.bus->wr(&((dev)->mt76), __VA_ARGS__) #define mt76_rmw(dev, ...) (dev)->mt76.bus->rmw(&((dev)->mt76), __VA_ARGS__) -#define mt76_wr_copy(dev, ...) (dev)->mt76.bus->copy(&((dev)->mt76), __VA_ARGS__) +#define mt76_wr_copy(dev, ...) (dev)->mt76.bus->write_copy(&((dev)->mt76), __VA_ARGS__) +#define mt76_rr_copy(dev, ...) (dev)->mt76.bus->read_copy(&((dev)->mt76), __VA_ARGS__) #define mt76_wr_rp(dev, ...) (dev)->mt76.bus->wr_rp(&((dev)->mt76), __VA_ARGS__) #define mt76_rd_rp(dev, ...) (dev)->mt76.bus->rd_rp(&((dev)->mt76), __VA_ARGS__) @@ -675,7 +673,7 @@ static inline struct mt76_tx_cb *mt76_tx_skb_cb(struct sk_buff *skb) { BUILD_BUG_ON(sizeof(struct mt76_tx_cb) > sizeof(IEEE80211_SKB_CB(skb)->status.status_driver_data)); - return ((void *) IEEE80211_SKB_CB(skb)->status.status_driver_data); + return ((void *)IEEE80211_SKB_CB(skb)->status.status_driver_data); } static inline void mt76_insert_hdr_pad(struct sk_buff *skb) @@ -710,6 +708,7 @@ void mt76_stop_tx_queues(struct mt76_dev *dev, struct ieee80211_sta *sta, bool send_bar); void mt76_txq_schedule(struct mt76_dev *dev, enum mt76_txq_id qid); void mt76_txq_schedule_all(struct mt76_dev *dev); +void mt76_tx_tasklet(unsigned long data); void mt76_release_buffered_frames(struct ieee80211_hw *hw, struct ieee80211_sta *sta, u16 tids, int nframes, @@ -750,8 +749,6 @@ int mt76_sta_state(struct ieee80211_hw *hw, struct ieee80211_vif *vif, void __mt76_sta_remove(struct mt76_dev *dev, struct ieee80211_vif *vif, struct ieee80211_sta *sta); -struct ieee80211_sta *mt76_rx_convert(struct sk_buff *skb); - int mt76_get_min_avg_rssi(struct mt76_dev *dev); int mt76_get_txpower(struct ieee80211_hw *hw, struct ieee80211_vif *vif, @@ -765,6 +762,10 @@ void mt76_insert_ccmp_hdr(struct sk_buff *skb, u8 key_id); int mt76_get_rate(struct mt76_dev *dev, struct ieee80211_supported_band *sband, int idx, bool cck); +void mt76_sw_scan(struct ieee80211_hw *hw, struct ieee80211_vif *vif, + const u8 *mac); +void mt76_sw_scan_complete(struct ieee80211_hw *hw, + struct ieee80211_vif *vif); /* internal */ void mt76_tx_free(struct mt76_dev *dev); diff --git a/drivers/net/wireless/mediatek/mt76/mt7603/Kconfig b/drivers/net/wireless/mediatek/mt76/mt7603/Kconfig index e108bf881ca8..6a0080f1d91c 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7603/Kconfig +++ b/drivers/net/wireless/mediatek/mt76/mt7603/Kconfig @@ -5,6 +5,8 @@ config MT7603E depends on MAC80211 depends on PCI help - This adds support for MT7603E wireless PCIe devices and the WLAN core on - MT7628/MT7688 SoC devices + This adds support for MT7603E wireless PCIe devices and the WLAN core + on MT7628/MT7688 SoC devices. This family supports IEEE 802.11n 2x2 + to 300Mbps PHY rate + To compile this driver as a module, choose M here. diff --git a/drivers/net/wireless/mediatek/mt76/mt7603/beacon.c b/drivers/net/wireless/mediatek/mt76/mt7603/beacon.c index 58e68fbdbf75..7a41cdf1c4ae 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7603/beacon.c +++ b/drivers/net/wireless/mediatek/mt76/mt7603/beacon.c @@ -1,4 +1,4 @@ -/* SPDX-License-Identifier: ISC */ +// SPDX-License-Identifier: ISC #include "mt7603.h" diff --git a/drivers/net/wireless/mediatek/mt76/mt7603/core.c b/drivers/net/wireless/mediatek/mt76/mt7603/core.c index e7ee58e3379c..e5af4f3389cc 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7603/core.c +++ b/drivers/net/wireless/mediatek/mt76/mt7603/core.c @@ -1,4 +1,4 @@ -/* SPDX-License-Identifier: ISC */ +// SPDX-License-Identifier: ISC #include "mt7603.h" diff --git a/drivers/net/wireless/mediatek/mt76/mt7603/debugfs.c b/drivers/net/wireless/mediatek/mt76/mt7603/debugfs.c index a1bc3103cbe9..5942fe76c6e9 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7603/debugfs.c +++ b/drivers/net/wireless/mediatek/mt76/mt7603/debugfs.c @@ -1,4 +1,4 @@ -/* SPDX-License-Identifier: ISC */ +// SPDX-License-Identifier: ISC #include "mt7603.h" diff --git a/drivers/net/wireless/mediatek/mt76/mt7603/dma.c b/drivers/net/wireless/mediatek/mt76/mt7603/dma.c index 58dc511f93c5..24d82a20d046 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7603/dma.c +++ b/drivers/net/wireless/mediatek/mt76/mt7603/dma.c @@ -1,4 +1,4 @@ -/* SPDX-License-Identifier: ISC */ +// SPDX-License-Identifier: ISC #include "mt7603.h" #include "mac.h" @@ -63,7 +63,7 @@ mt7603_rx_loopback_skb(struct mt7603_dev *dev, struct sk_buff *skb) txd[0] = cpu_to_le32(val); sta = container_of(priv, struct ieee80211_sta, drv_priv); - hdr = (struct ieee80211_hdr *) &skb->data[MT_TXD_SIZE]; + hdr = (struct ieee80211_hdr *)&skb->data[MT_TXD_SIZE]; tid = *ieee80211_get_qos_ctl(hdr) & IEEE80211_QOS_CTL_TID_MASK; ieee80211_sta_set_buffered(sta, tid, true); @@ -135,14 +135,6 @@ mt7603_init_rx_queue(struct mt7603_dev *dev, struct mt76_queue *q, return 0; } -static void -mt7603_tx_tasklet(unsigned long data) -{ - struct mt7603_dev *dev = (struct mt7603_dev *)data; - - mt76_txq_schedule_all(&dev->mt76); -} - static int mt7603_poll_tx(struct napi_struct *napi, int budget) { struct mt7603_dev *dev; @@ -178,11 +170,6 @@ int mt7603_dma_init(struct mt7603_dev *dev) mt76_dma_attach(&dev->mt76); - init_waitqueue_head(&dev->mt76.mmio.mcu.wait); - skb_queue_head_init(&dev->mt76.mmio.mcu.res_q); - - tasklet_init(&dev->mt76.tx_tasklet, mt7603_tx_tasklet, (unsigned long)dev); - mt76_clear(dev, MT_WPDMA_GLO_CFG, MT_WPDMA_GLO_CFG_TX_DMA_EN | MT_WPDMA_GLO_CFG_RX_DMA_EN | diff --git a/drivers/net/wireless/mediatek/mt76/mt7603/eeprom.c b/drivers/net/wireless/mediatek/mt76/mt7603/eeprom.c index 8c120e4461b0..2b6a4d8a8dc7 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7603/eeprom.c +++ b/drivers/net/wireless/mediatek/mt76/mt7603/eeprom.c @@ -1,4 +1,4 @@ -/* SPDX-License-Identifier: ISC */ +// SPDX-License-Identifier: ISC #include "mt7603.h" #include "eeprom.h" diff --git a/drivers/net/wireless/mediatek/mt76/mt7603/init.c b/drivers/net/wireless/mediatek/mt76/mt7603/init.c index 38834c7d0891..ad2ccdbe7258 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7603/init.c +++ b/drivers/net/wireless/mediatek/mt76/mt7603/init.c @@ -1,4 +1,4 @@ -/* SPDX-License-Identifier: ISC */ +// SPDX-License-Identifier: ISC #include <linux/etherdevice.h> #include "mt7603.h" @@ -248,8 +248,7 @@ mt7603_mac_init(struct mt7603_dev *dev) FIELD_PREP(MT_AGG_ARxCR_LIMIT(7), MT7603_RATE_RETRY - 1)); mt76_wr(dev, MT_AGG_ARCR, - (MT_AGG_ARCR_INIT_RATE1 | - FIELD_PREP(MT_AGG_ARCR_RTS_RATE_THR, 2) | + (FIELD_PREP(MT_AGG_ARCR_RTS_RATE_THR, 2) | MT_AGG_ARCR_RATE_DOWN_RATIO_EN | FIELD_PREP(MT_AGG_ARCR_RATE_DOWN_RATIO, 1) | FIELD_PREP(MT_AGG_ARCR_RATE_UP_EXTRA_TH, 4))); @@ -507,7 +506,6 @@ mt7603_init_txpower(struct mt7603_dev *dev, } } - int mt7603_register_device(struct mt7603_dev *dev) { struct mt76_bus_ops *bus_ops; diff --git a/drivers/net/wireless/mediatek/mt76/mt7603/mac.c b/drivers/net/wireless/mediatek/mt76/mt7603/mac.c index 40db1cbc832d..c328192307c4 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7603/mac.c +++ b/drivers/net/wireless/mediatek/mt76/mt7603/mac.c @@ -1,4 +1,4 @@ -/* SPDX-License-Identifier: ISC */ +// SPDX-License-Identifier: ISC #include <linux/etherdevice.h> #include <linux/timekeeping.h> @@ -639,9 +639,11 @@ void mt7603_wtbl_set_rates(struct mt7603_dev *dev, struct mt7603_sta *sta, IEEE80211_TX_RC_40_MHZ_WIDTH) continue; + if (!rates[i].idx) + continue; + rates[i].idx--; } - } w9 &= MT_WTBL2_W9_SHORT_GI_20 | MT_WTBL2_W9_SHORT_GI_40 | @@ -1014,8 +1016,9 @@ mt7603_fill_txs(struct mt7603_dev *dev, struct mt7603_sta *sta, sta->rate_probe = false; } spin_unlock_bh(&dev->mt76.lock); - } else + } else { info->status.rates[0] = rs->rates[first_idx / 2]; + } info->status.rates[0].count = 0; for (i = 0, idx = first_idx; count && idx <= last_idx; idx++) { @@ -1470,8 +1473,9 @@ void mt7603_update_channel(struct mt76_dev *mdev) spin_lock_bh(&dev->mt76.cc_lock); cur_time = ktime_get_boottime(); state->cc_busy += busy; - state->cc_active += ktime_to_us(ktime_sub(cur_time, dev->survey_time)); - dev->survey_time = cur_time; + state->cc_active += ktime_to_us(ktime_sub(cur_time, + dev->mt76.survey_time)); + dev->mt76.survey_time = cur_time; spin_unlock_bh(&dev->mt76.cc_lock); } diff --git a/drivers/net/wireless/mediatek/mt76/mt7603/main.c b/drivers/net/wireless/mediatek/mt76/mt7603/main.c index e5d4cb6381a8..25d5b1608bc9 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7603/main.c +++ b/drivers/net/wireless/mediatek/mt76/mt7603/main.c @@ -1,4 +1,4 @@ -/* SPDX-License-Identifier: ISC */ +// SPDX-License-Identifier: ISC #include <linux/etherdevice.h> #include <linux/platform_device.h> @@ -14,7 +14,7 @@ mt7603_start(struct ieee80211_hw *hw) struct mt7603_dev *dev = hw->priv; mt7603_mac_start(dev); - dev->survey_time = ktime_get_boottime(); + dev->mt76.survey_time = ktime_get_boottime(); set_bit(MT76_STATE_RUNNING, &dev->mt76.state); mt7603_mac_work(&dev->mt76.mac_work.work); @@ -173,7 +173,7 @@ mt7603_set_channel(struct mt7603_dev *dev, struct cfg80211_chan_def *def) mt76_txq_schedule_all(&dev->mt76); ieee80211_queue_delayed_work(mt76_hw(dev), &dev->mt76.mac_work, - MT7603_WATCHDOG_TIME); + msecs_to_jiffies(MT7603_WATCHDOG_TIME)); /* reset channel stats */ mt76_clear(dev, MT_MIB_CTL, MT_MIB_CTL_READ_CLR_DIS); @@ -182,7 +182,7 @@ mt7603_set_channel(struct mt7603_dev *dev, struct cfg80211_chan_def *def) mt76_rr(dev, MT_MIB_STAT_PSCCA); mt7603_cca_stats_reset(dev); - dev->survey_time = ktime_get_boottime(); + dev->mt76.survey_time = ktime_get_boottime(); mt7603_init_edcca(dev); @@ -399,7 +399,7 @@ mt7603_ps_set_more_data(struct sk_buff *skb) { struct ieee80211_hdr *hdr; - hdr = (struct ieee80211_hdr *) &skb->data[MT_TXD_SIZE]; + hdr = (struct ieee80211_hdr *)&skb->data[MT_TXD_SIZE]; hdr->frame_control |= cpu_to_le16(IEEE80211_FCTL_MOREDATA); } @@ -537,23 +537,6 @@ mt7603_conf_tx(struct ieee80211_hw *hw, struct ieee80211_vif *vif, u16 queue, } static void -mt7603_sw_scan(struct ieee80211_hw *hw, struct ieee80211_vif *vif, - const u8 *mac) -{ - struct mt7603_dev *dev = hw->priv; - - set_bit(MT76_SCANNING, &dev->mt76.state); -} - -static void -mt7603_sw_scan_complete(struct ieee80211_hw *hw, struct ieee80211_vif *vif) -{ - struct mt7603_dev *dev = hw->priv; - - clear_bit(MT76_SCANNING, &dev->mt76.state); -} - -static void mt7603_flush(struct ieee80211_hw *hw, struct ieee80211_vif *vif, u32 queues, bool drop) { @@ -569,7 +552,7 @@ mt7603_ampdu_action(struct ieee80211_hw *hw, struct ieee80211_vif *vif, struct ieee80211_txq *txq = sta->txq[params->tid]; struct mt7603_sta *msta = (struct mt7603_sta *)sta->drv_priv; u16 tid = params->tid; - u16 *ssn = ¶ms->ssn; + u16 ssn = params->ssn; u8 ba_size = params->buf_size; struct mt76_txq *mtxq; @@ -580,7 +563,7 @@ mt7603_ampdu_action(struct ieee80211_hw *hw, struct ieee80211_vif *vif, switch (action) { case IEEE80211_AMPDU_RX_START: - mt76_rx_aggr_start(&dev->mt76, &msta->wcid, tid, *ssn, + mt76_rx_aggr_start(&dev->mt76, &msta->wcid, tid, ssn, params->buf_size); mt7603_mac_rx_ba_reset(dev, sta->addr, tid); break; @@ -595,11 +578,10 @@ mt7603_ampdu_action(struct ieee80211_hw *hw, struct ieee80211_vif *vif, case IEEE80211_AMPDU_TX_STOP_FLUSH: case IEEE80211_AMPDU_TX_STOP_FLUSH_CONT: mtxq->aggr = false; - ieee80211_send_bar(vif, sta->addr, tid, mtxq->agg_ssn); mt7603_mac_tx_ba_reset(dev, msta->wcid.idx, tid, -1); break; case IEEE80211_AMPDU_TX_START: - mtxq->agg_ssn = IEEE80211_SN_TO_SEQ(*ssn); + mtxq->agg_ssn = IEEE80211_SN_TO_SEQ(ssn); ieee80211_start_tx_ba_cb_irqsafe(vif, sta->addr, tid); break; case IEEE80211_AMPDU_TX_STOP_CONT: @@ -647,7 +629,8 @@ mt7603_set_coverage_class(struct ieee80211_hw *hw, s16 coverage_class) mt7603_mac_set_timing(dev); } -static void mt7603_tx(struct ieee80211_hw *hw, struct ieee80211_tx_control *control, +static void mt7603_tx(struct ieee80211_hw *hw, + struct ieee80211_tx_control *control, struct sk_buff *skb) { struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb); @@ -682,8 +665,8 @@ const struct ieee80211_ops mt7603_ops = { .sta_state = mt76_sta_state, .set_key = mt7603_set_key, .conf_tx = mt7603_conf_tx, - .sw_scan_start = mt7603_sw_scan, - .sw_scan_complete = mt7603_sw_scan_complete, + .sw_scan_start = mt76_sw_scan, + .sw_scan_complete = mt76_sw_scan_complete, .flush = mt7603_flush, .ampdu_action = mt7603_ampdu_action, .get_txpower = mt76_get_txpower, diff --git a/drivers/net/wireless/mediatek/mt76/mt7603/mcu.c b/drivers/net/wireless/mediatek/mt76/mt7603/mcu.c index 343ddc5543c2..02b2bd60d04d 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7603/mcu.c +++ b/drivers/net/wireless/mediatek/mt76/mt7603/mcu.c @@ -1,4 +1,4 @@ -/* SPDX-License-Identifier: ISC */ +// SPDX-License-Identifier: ISC #include <linux/firmware.h> #include "mt7603.h" diff --git a/drivers/net/wireless/mediatek/mt76/mt7603/mt7603.h b/drivers/net/wireless/mediatek/mt76/mt7603/mt7603.h index 2c6f7b4cf0e9..257300fec4f8 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7603/mt7603.h +++ b/drivers/net/wireless/mediatek/mt76/mt7603/mt7603.h @@ -116,7 +116,6 @@ struct mt7603_dev { s8 tx_power_limit; - ktime_t survey_time; ktime_t ed_time; struct mt76_queue q_rx; diff --git a/drivers/net/wireless/mediatek/mt76/mt7603/pci.c b/drivers/net/wireless/mediatek/mt76/mt7603/pci.c index 4acdbf5d8968..2f2f337e2201 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7603/pci.c +++ b/drivers/net/wireless/mediatek/mt76/mt7603/pci.c @@ -1,4 +1,4 @@ -/* SPDX-License-Identifier: ISC */ +// SPDX-License-Identifier: ISC #include <linux/kernel.h> #include <linux/module.h> diff --git a/drivers/net/wireless/mediatek/mt76/mt7603/soc.c b/drivers/net/wireless/mediatek/mt76/mt7603/soc.c index b920be1f5718..68efb300c0d8 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7603/soc.c +++ b/drivers/net/wireless/mediatek/mt76/mt7603/soc.c @@ -1,4 +1,4 @@ -/* SPDX-License-Identifier: ISC */ +// SPDX-License-Identifier: ISC #include <linux/kernel.h> #include <linux/module.h> @@ -9,7 +9,6 @@ static int mt76_wmac_probe(struct platform_device *pdev) { - struct resource *res = platform_get_resource(pdev, IORESOURCE_MEM, 0); struct mt7603_dev *dev; void __iomem *mem_base; struct mt76_dev *mdev; @@ -17,12 +16,10 @@ mt76_wmac_probe(struct platform_device *pdev) int ret; irq = platform_get_irq(pdev, 0); - if (irq < 0) { - dev_err(&pdev->dev, "Failed to get device IRQ\n"); + if (irq < 0) return irq; - } - mem_base = devm_ioremap_resource(&pdev->dev, res); + mem_base = devm_platform_ioremap_resource(pdev, 0); if (IS_ERR(mem_base)) { dev_err(&pdev->dev, "Failed to get memory resource\n"); return PTR_ERR(mem_base); diff --git a/drivers/net/wireless/mediatek/mt76/mt7615/Kconfig b/drivers/net/wireless/mediatek/mt76/mt7615/Kconfig index 2ed47b309b6e..4cabba9aa2ea 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7615/Kconfig +++ b/drivers/net/wireless/mediatek/mt76/mt7615/Kconfig @@ -5,4 +5,9 @@ config MT7615E depends on MAC80211 depends on PCI help - This adds support for MT7615-based wireless PCIe devices. + This adds support for MT7615-based wireless PCIe devices, + which support concurrent dual-band operation at both 5GHz + and 2.4GHz, IEEE 802.11ac 4x4:4SS 1733Mbps PHY rate, wave2 + MU-MIMO up to 4 users/group and 160MHz channels. + + To compile this driver as a module, choose M here. diff --git a/drivers/net/wireless/mediatek/mt76/mt7615/Makefile b/drivers/net/wireless/mediatek/mt76/mt7615/Makefile index 6397552f6ee3..5aaac69849d6 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7615/Makefile +++ b/drivers/net/wireless/mediatek/mt76/mt7615/Makefile @@ -2,4 +2,5 @@ obj-$(CONFIG_MT7615E) += mt7615e.o -mt7615e-y := pci.o init.o dma.o eeprom.o main.o mcu.o mac.o +mt7615e-y := pci.o init.o dma.o eeprom.o main.o mcu.o mac.o \ + debugfs.o diff --git a/drivers/net/wireless/mediatek/mt76/mt7615/debugfs.c b/drivers/net/wireless/mediatek/mt76/mt7615/debugfs.c new file mode 100644 index 000000000000..2428a4659a1c --- /dev/null +++ b/drivers/net/wireless/mediatek/mt76/mt7615/debugfs.c @@ -0,0 +1,91 @@ +// SPDX-License-Identifier: ISC + +#include "mt7615.h" + +static int +mt7615_radar_pattern_set(void *data, u64 val) +{ + struct mt7615_dev *dev = data; + + return mt7615_mcu_rdd_send_pattern(dev); +} + +DEFINE_DEBUGFS_ATTRIBUTE(fops_radar_pattern, NULL, + mt7615_radar_pattern_set, "%lld\n"); + +static int +mt7615_scs_set(void *data, u64 val) +{ + struct mt7615_dev *dev = data; + + mt7615_mac_set_scs(dev, val); + + return 0; +} + +static int +mt7615_scs_get(void *data, u64 *val) +{ + struct mt7615_dev *dev = data; + + *val = dev->scs_en; + + return 0; +} + +DEFINE_DEBUGFS_ATTRIBUTE(fops_scs, mt7615_scs_get, + mt7615_scs_set, "%lld\n"); + +static int +mt7615_radio_read(struct seq_file *s, void *data) +{ + struct mt7615_dev *dev = dev_get_drvdata(s->private); + + seq_printf(s, "Sensitivity: ofdm=%d cck=%d\n", + dev->ofdm_sensitivity, dev->cck_sensitivity); + seq_printf(s, "False CCA: ofdm=%d cck=%d\n", + dev->false_cca_ofdm, dev->false_cca_cck); + + return 0; +} + +static int mt7615_read_temperature(struct seq_file *s, void *data) +{ + struct mt7615_dev *dev = dev_get_drvdata(s->private); + int temp; + + /* cpu */ + temp = mt7615_mcu_get_temperature(dev, 0); + seq_printf(s, "Temperature: %d\n", temp); + + return 0; +} + +int mt7615_init_debugfs(struct mt7615_dev *dev) +{ + struct dentry *dir; + + dir = mt76_register_debugfs(&dev->mt76); + if (!dir) + return -ENOMEM; + + debugfs_create_file("scs", 0600, dir, dev, &fops_scs); + debugfs_create_devm_seqfile(dev->mt76.dev, "radio", dir, + mt7615_radio_read); + debugfs_create_u32("dfs_hw_pattern", 0400, dir, &dev->hw_pattern); + /* test pattern knobs */ + debugfs_create_u8("pattern_len", 0600, dir, + &dev->radar_pattern.n_pulses); + debugfs_create_u32("pulse_period", 0600, dir, + &dev->radar_pattern.period); + debugfs_create_u16("pulse_width", 0600, dir, + &dev->radar_pattern.width); + debugfs_create_u16("pulse_power", 0600, dir, + &dev->radar_pattern.power); + debugfs_create_file("radar_trigger", 0200, dir, dev, + &fops_radar_pattern); + debugfs_create_devm_seqfile(dev->mt76.dev, "temperature", dir, + mt7615_read_temperature); + + return 0; +} diff --git a/drivers/net/wireless/mediatek/mt76/mt7615/dma.c b/drivers/net/wireless/mediatek/mt76/mt7615/dma.c index 6a70273d4a69..fe532cecbbdd 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7615/dma.c +++ b/drivers/net/wireless/mediatek/mt76/mt7615/dma.c @@ -76,7 +76,7 @@ void mt7615_queue_rx_skb(struct mt76_dev *mdev, enum mt76_rxq_id q, mt7615_mac_tx_free(dev, skb); break; case PKT_TYPE_RX_EVENT: - mt76_mcu_rx_event(&dev->mt76, skb); + mt7615_mcu_rx_event(dev, skb); break; case PKT_TYPE_NORMAL: if (!mt7615_mac_fill_rx(dev, skb)) { @@ -90,13 +90,6 @@ void mt7615_queue_rx_skb(struct mt76_dev *mdev, enum mt76_rxq_id q, } } -static void mt7615_tx_tasklet(unsigned long data) -{ - struct mt7615_dev *dev = (struct mt7615_dev *)data; - - mt76_txq_schedule_all(&dev->mt76); -} - static int mt7615_poll_tx(struct napi_struct *napi, int budget) { static const u8 queue_map[] = { @@ -128,9 +121,6 @@ int mt7615_dma_init(struct mt7615_dev *dev) mt76_dma_attach(&dev->mt76); - tasklet_init(&dev->mt76.tx_tasklet, mt7615_tx_tasklet, - (unsigned long)dev); - mt76_wr(dev, MT_WPDMA_GLO_CFG, MT_WPDMA_GLO_CFG_TX_WRITEBACK_DONE | MT_WPDMA_GLO_CFG_FIFO_LITTLE_ENDIAN | diff --git a/drivers/net/wireless/mediatek/mt76/mt7615/eeprom.c b/drivers/net/wireless/mediatek/mt76/mt7615/eeprom.c index dc94f52e6e8b..515bb58e19fd 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7615/eeprom.c +++ b/drivers/net/wireless/mediatek/mt76/mt7615/eeprom.c @@ -154,6 +154,42 @@ int mt7615_eeprom_get_power_index(struct mt7615_dev *dev, return index; } +static void mt7615_apply_cal_free_data(struct mt7615_dev *dev) +{ + static const u16 ical[] = { + 0x53, 0x54, 0x55, 0x56, 0x57, 0x5c, 0x5d, 0x62, 0x63, 0x68, + 0x69, 0x6e, 0x6f, 0x73, 0x74, 0x78, 0x79, 0x82, 0x83, 0x87, + 0x88, 0x8c, 0x8d, 0x91, 0x92, 0x96, 0x97, 0x9b, 0x9c, 0xa0, + 0xa1, 0xaa, 0xab, 0xaf, 0xb0, 0xb4, 0xb5, 0xb9, 0xba, 0xf4, + 0xf7, 0xff, + 0x140, 0x141, 0x145, 0x146, 0x14a, 0x14b, 0x154, 0x155, 0x159, + 0x15a, 0x15e, 0x15f, 0x163, 0x164, 0x168, 0x169, 0x16d, 0x16e, + 0x172, 0x173, 0x17c, 0x17d, 0x181, 0x182, 0x186, 0x187, 0x18b, + 0x18c + }; + static const u16 ical_nocheck[] = { + 0x110, 0x111, 0x112, 0x113, 0x114, 0x115, 0x116, 0x117, 0x118, + 0x1b5, 0x1b6, 0x1b7, 0x3ac, 0x3ad, 0x3ae, 0x3af, 0x3b0, 0x3b1, + 0x3b2 + }; + u8 *eeprom = dev->mt76.eeprom.data; + u8 *otp = dev->mt76.otp.data; + int i; + + if (!otp) + return; + + for (i = 0; i < ARRAY_SIZE(ical); i++) + if (!otp[ical[i]]) + return; + + for (i = 0; i < ARRAY_SIZE(ical); i++) + eeprom[ical[i]] = otp[ical[i]]; + + for (i = 0; i < ARRAY_SIZE(ical_nocheck); i++) + eeprom[ical_nocheck[i]] = otp[ical_nocheck[i]]; +} + int mt7615_eeprom_init(struct mt7615_dev *dev) { int ret; @@ -166,6 +202,8 @@ int mt7615_eeprom_init(struct mt7615_dev *dev) if (ret && dev->mt76.otp.data) memcpy(dev->mt76.eeprom.data, dev->mt76.otp.data, MT7615_EEPROM_SIZE); + else + mt7615_apply_cal_free_data(dev); mt7615_eeprom_parse_hw_cap(dev); memcpy(dev->mt76.macaddr, dev->mt76.eeprom.data + MT_EE_MAC_ADDR, diff --git a/drivers/net/wireless/mediatek/mt76/mt7615/init.c b/drivers/net/wireless/mediatek/mt76/mt7615/init.c index 859de2454ec6..1104e4c8aaa6 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7615/init.c +++ b/drivers/net/wireless/mediatek/mt76/mt7615/init.c @@ -20,10 +20,24 @@ static void mt7615_phy_init(struct mt7615_dev *dev) static void mt7615_mac_init(struct mt7615_dev *dev) { - /* enable band 0 clk */ - mt76_rmw(dev, MT_CFG_CCR, - MT_CFG_CCR_MAC_D0_1X_GC_EN | MT_CFG_CCR_MAC_D0_2X_GC_EN, - MT_CFG_CCR_MAC_D0_1X_GC_EN | MT_CFG_CCR_MAC_D0_2X_GC_EN); + u32 val; + + /* enable band 0/1 clk */ + mt76_set(dev, MT_CFG_CCR, + MT_CFG_CCR_MAC_D0_1X_GC_EN | MT_CFG_CCR_MAC_D0_2X_GC_EN | + MT_CFG_CCR_MAC_D1_1X_GC_EN | MT_CFG_CCR_MAC_D1_2X_GC_EN); + + val = mt76_rmw(dev, MT_TMAC_TRCR0, + MT_TMAC_TRCR_CCA_SEL | MT_TMAC_TRCR_SEC_CCA_SEL, + FIELD_PREP(MT_TMAC_TRCR_CCA_SEL, 2) | + FIELD_PREP(MT_TMAC_TRCR_SEC_CCA_SEL, 0)); + mt76_wr(dev, MT_TMAC_TRCR1, val); + + val = MT_AGG_ACR_PKT_TIME_EN | MT_AGG_ACR_NO_BA_AR_RULE | + FIELD_PREP(MT_AGG_ACR_CFEND_RATE, 0x49) | /* 24M */ + FIELD_PREP(MT_AGG_ACR_BAR_RATE, 0x4b); /* 6M */ + mt76_wr(dev, MT_AGG_ACR0, val); + mt76_wr(dev, MT_AGG_ACR1, val); mt76_rmw_field(dev, MT_TMAC_CTCR0, MT_TMAC_CTCR0_INS_DDLMT_REFTIME, 0x3f); @@ -36,6 +50,7 @@ static void mt7615_mac_init(struct mt7615_dev *dev) MT_TMAC_CTCR0_INS_DDLMT_EN); mt7615_mcu_set_rts_thresh(dev, 0x92b); + mt7615_mac_set_scs(dev, false); mt76_rmw(dev, MT_AGG_SCR, MT_AGG_SCR_NLNAV_MID_PTEC_DIS, MT_AGG_SCR_NLNAV_MID_PTEC_DIS); @@ -45,11 +60,19 @@ static void mt7615_mac_init(struct mt7615_dev *dev) mt76_wr(dev, MT_DMA_DCR0, MT_DMA_DCR0_RX_VEC_DROP | FIELD_PREP(MT_DMA_DCR0_MAX_RX_LEN, 3072)); - mt76_wr(dev, MT_AGG_ARUCR, FIELD_PREP(MT_AGG_ARxCR_LIMIT(0), 7)); + mt76_wr(dev, MT_AGG_ARUCR, + FIELD_PREP(MT_AGG_ARxCR_LIMIT(0), 7) | + FIELD_PREP(MT_AGG_ARxCR_LIMIT(1), 2) | + FIELD_PREP(MT_AGG_ARxCR_LIMIT(2), 2) | + FIELD_PREP(MT_AGG_ARxCR_LIMIT(3), 2) | + FIELD_PREP(MT_AGG_ARxCR_LIMIT(4), 1) | + FIELD_PREP(MT_AGG_ARxCR_LIMIT(5), 1) | + FIELD_PREP(MT_AGG_ARxCR_LIMIT(6), 1) | + FIELD_PREP(MT_AGG_ARxCR_LIMIT(7), 1)); + mt76_wr(dev, MT_AGG_ARDCR, - FIELD_PREP(MT_AGG_ARxCR_LIMIT(0), 0) | - FIELD_PREP(MT_AGG_ARxCR_LIMIT(1), - max_t(int, 0, MT7615_RATE_RETRY - 2)) | + FIELD_PREP(MT_AGG_ARxCR_LIMIT(0), MT7615_RATE_RETRY - 1) | + FIELD_PREP(MT_AGG_ARxCR_LIMIT(1), MT7615_RATE_RETRY - 1) | FIELD_PREP(MT_AGG_ARxCR_LIMIT(2), MT7615_RATE_RETRY - 1) | FIELD_PREP(MT_AGG_ARxCR_LIMIT(3), MT7615_RATE_RETRY - 1) | FIELD_PREP(MT_AGG_ARxCR_LIMIT(4), MT7615_RATE_RETRY - 1) | @@ -58,8 +81,7 @@ static void mt7615_mac_init(struct mt7615_dev *dev) FIELD_PREP(MT_AGG_ARxCR_LIMIT(7), MT7615_RATE_RETRY - 1)); mt76_wr(dev, MT_AGG_ARCR, - (MT_AGG_ARCR_INIT_RATE1 | - FIELD_PREP(MT_AGG_ARCR_RTS_RATE_THR, 2) | + (FIELD_PREP(MT_AGG_ARCR_RTS_RATE_THR, 2) | MT_AGG_ARCR_RATE_DOWN_RATIO_EN | FIELD_PREP(MT_AGG_ARCR_RATE_DOWN_RATIO, 1) | FIELD_PREP(MT_AGG_ARCR_RATE_UP_EXTRA_TH, 4))); @@ -155,17 +177,6 @@ static const struct ieee80211_iface_combination if_comb[] = { } }; -static int mt7615_init_debugfs(struct mt7615_dev *dev) -{ - struct dentry *dir; - - dir = mt76_register_debugfs(&dev->mt76); - if (!dir) - return -ENOMEM; - - return 0; -} - static void mt7615_init_txpower(struct mt7615_dev *dev, struct ieee80211_supported_band *sband) @@ -208,6 +219,30 @@ mt7615_init_txpower(struct mt7615_dev *dev, } } +static void +mt7615_regd_notifier(struct wiphy *wiphy, + struct regulatory_request *request) +{ + struct ieee80211_hw *hw = wiphy_to_ieee80211_hw(wiphy); + struct mt7615_dev *dev = hw->priv; + struct cfg80211_chan_def *chandef = &dev->mt76.chandef; + + if (request->dfs_region == dev->mt76.region) + return; + + dev->mt76.region = request->dfs_region; + + if (!(chandef->chan->flags & IEEE80211_CHAN_RADAR)) + return; + + mt7615_dfs_stop_radar_detector(dev); + if (request->dfs_region == NL80211_DFS_UNSET) + mt7615_mcu_rdd_cmd(dev, RDD_CAC_END, MT_HW_RDD0, + MT_RX_SEL0, 0); + else + mt7615_dfs_start_radar_detector(dev); +} + int mt7615_register_device(struct mt7615_dev *dev) { struct ieee80211_hw *hw = mt76_hw(dev); @@ -230,6 +265,8 @@ int mt7615_register_device(struct mt7615_dev *dev) wiphy->iface_combinations = if_comb; wiphy->n_iface_combinations = ARRAY_SIZE(if_comb); + wiphy->reg_notifier = mt7615_regd_notifier; + wiphy->flags |= WIPHY_FLAG_HAS_CHANNEL_SWITCH; ieee80211_hw_set(hw, SUPPORTS_REORDERING_BUFFER); ieee80211_hw_set(hw, TX_STATUS_NO_AMPDU_LEN); @@ -243,6 +280,7 @@ int mt7615_register_device(struct mt7615_dev *dev) IEEE80211_VHT_CAP_SUPP_CHAN_WIDTH_160_80PLUS80MHZ; dev->mt76.chainmask = 0x404; dev->mt76.antenna_mask = 0xf; + dev->dfs_state = -1; wiphy->interface_modes = BIT(NL80211_IFTYPE_STATION) | #ifdef CONFIG_MAC80211_MESH diff --git a/drivers/net/wireless/mediatek/mt76/mt7615/mac.c b/drivers/net/wireless/mediatek/mt76/mt7615/mac.c index 1eb0e9c9970c..e07ce2c10013 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7615/mac.c +++ b/drivers/net/wireless/mediatek/mt76/mt7615/mac.c @@ -232,11 +232,9 @@ void mt7615_tx_complete_skb(struct mt76_dev *mdev, enum mt76_txq_id qid, struct mt76_txwi_cache *t; struct mt7615_dev *dev; struct mt7615_txp *txp; - u8 *txwi_ptr; - txwi_ptr = mt76_get_txwi_ptr(mdev, e->txwi); - txp = (struct mt7615_txp *)(txwi_ptr + MT_TXD_SIZE); dev = container_of(mdev, struct mt7615_dev, mt76); + txp = mt7615_txwi_to_txp(mdev, e->txwi); spin_lock_bh(&dev->token_lock); t = idr_remove(&dev->token, le16_to_cpu(txp->token)); @@ -248,12 +246,13 @@ void mt7615_tx_complete_skb(struct mt76_dev *mdev, enum mt76_txq_id qid, mt76_tx_complete_skb(mdev, e->skb); } -u16 mt7615_mac_tx_rate_val(struct mt7615_dev *dev, - const struct ieee80211_tx_rate *rate, - bool stbc, u8 *bw) +static u16 +mt7615_mac_tx_rate_val(struct mt7615_dev *dev, + const struct ieee80211_tx_rate *rate, + bool stbc, u8 *bw) { u8 phy, nss, rate_idx; - u16 rateval; + u16 rateval = 0; *bw = 0; @@ -291,12 +290,14 @@ u16 mt7615_mac_tx_rate_val(struct mt7615_dev *dev, rate_idx = val & 0xff; } - rateval = (FIELD_PREP(MT_TX_RATE_IDX, rate_idx) | - FIELD_PREP(MT_TX_RATE_MODE, phy) | - FIELD_PREP(MT_TX_RATE_NSS, nss - 1)); - - if (stbc && nss == 1) + if (stbc && nss == 1) { + nss++; rateval |= MT_TX_RATE_STBC; + } + + rateval |= (FIELD_PREP(MT_TX_RATE_IDX, rate_idx) | + FIELD_PREP(MT_TX_RATE_MODE, phy) | + FIELD_PREP(MT_TX_RATE_NSS, nss - 1)); return rateval; } @@ -309,9 +310,10 @@ int mt7615_mac_write_txwi(struct mt7615_dev *dev, __le32 *txwi, struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb); struct ieee80211_tx_rate *rate = &info->control.rates[0]; struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)skb->data; + bool multicast = is_multicast_ether_addr(hdr->addr1); struct ieee80211_vif *vif = info->control.vif; int tx_count = 8; - u8 fc_type, fc_stype, p_fmt, q_idx, omac_idx = 0; + u8 fc_type, fc_stype, p_fmt, q_idx, omac_idx = 0, wmm_idx = 0; __le16 fc = hdr->frame_control; u16 seqno = 0; u32 val; @@ -320,6 +322,7 @@ int mt7615_mac_write_txwi(struct mt7615_dev *dev, __le32 *txwi, struct mt7615_vif *mvif = (struct mt7615_vif *)vif->drv_priv; omac_idx = mvif->omac_idx; + wmm_idx = mvif->wmm_idx; } if (sta) { @@ -331,8 +334,9 @@ int mt7615_mac_write_txwi(struct mt7615_dev *dev, __le32 *txwi, fc_type = (le16_to_cpu(fc) & IEEE80211_FCTL_FTYPE) >> 2; fc_stype = (le16_to_cpu(fc) & IEEE80211_FCTL_STYPE) >> 4; - if (ieee80211_is_data(fc)) { - q_idx = skb_get_queue_mapping(skb); + if (ieee80211_is_data(fc) || ieee80211_is_bufferable_mmpdu(fc)) { + q_idx = wmm_idx * MT7615_MAX_WMM_SETS + + skb_get_queue_mapping(skb); p_fmt = MT_TX_TYPE_CT; } else if (ieee80211_is_beacon(fc)) { q_idx = MT_LMAC_BCN0; @@ -360,8 +364,18 @@ int mt7615_mac_write_txwi(struct mt7615_dev *dev, __le32 *txwi, val = FIELD_PREP(MT_TXD2_FRAME_TYPE, fc_type) | FIELD_PREP(MT_TXD2_SUB_TYPE, fc_stype) | - FIELD_PREP(MT_TXD2_MULTICAST, - is_multicast_ether_addr(hdr->addr1)); + FIELD_PREP(MT_TXD2_MULTICAST, multicast); + if (key) { + if (multicast && ieee80211_is_robust_mgmt_frame(skb) && + key->cipher == WLAN_CIPHER_SUITE_AES_CMAC) { + val |= MT_TXD2_BIP; + txwi[3] = 0; + } else { + txwi[3] = cpu_to_le32(MT_TXD3_PROTECT_FRAME); + } + } else { + txwi[3] = 0; + } txwi[2] = cpu_to_le32(val); if (!(info->flags & IEEE80211_TX_CTL_AMPDU)) @@ -418,14 +432,11 @@ int mt7615_mac_write_txwi(struct mt7615_dev *dev, __le32 *txwi, } val |= FIELD_PREP(MT_TXD3_SEQ, seqno); - txwi[3] = cpu_to_le32(val); + txwi[3] |= cpu_to_le32(val); if (info->flags & IEEE80211_TX_CTL_NO_ACK) txwi[3] |= cpu_to_le32(MT_TXD3_NO_ACK); - if (key) - txwi[3] |= cpu_to_le32(MT_TXD3_PROTECT_FRAME); - txwi[7] = FIELD_PREP(MT_TXD7_TYPE, fc_type) | FIELD_PREP(MT_TXD7_SUB_TYPE, fc_stype); @@ -436,16 +447,318 @@ void mt7615_txp_skb_unmap(struct mt76_dev *dev, struct mt76_txwi_cache *t) { struct mt7615_txp *txp; - u8 *txwi; int i; - txwi = mt76_get_txwi_ptr(dev, t); - txp = (struct mt7615_txp *)(txwi + MT_TXD_SIZE); + txp = mt7615_txwi_to_txp(dev, t); for (i = 1; i < txp->nbuf; i++) dma_unmap_single(dev->dev, le32_to_cpu(txp->buf[i]), le16_to_cpu(txp->len[i]), DMA_TO_DEVICE); } +static u32 mt7615_mac_wtbl_addr(int wcid) +{ + return MT_WTBL_BASE + wcid * MT_WTBL_ENTRY_SIZE; +} + +void mt7615_mac_set_rates(struct mt7615_dev *dev, struct mt7615_sta *sta, + struct ieee80211_tx_rate *probe_rate, + struct ieee80211_tx_rate *rates) +{ + struct ieee80211_tx_rate *ref; + int wcid = sta->wcid.idx; + u32 addr = mt7615_mac_wtbl_addr(wcid); + bool stbc = false; + int n_rates = sta->n_rates; + u8 bw, bw_prev, bw_idx = 0; + u16 val[4]; + u16 probe_val; + u32 w5, w27; + bool rateset; + int i, k; + + if (!mt76_poll(dev, MT_WTBL_UPDATE, MT_WTBL_UPDATE_BUSY, 0, 5000)) + return; + + for (i = n_rates; i < 4; i++) + rates[i] = rates[n_rates - 1]; + + rateset = !(sta->rate_set_tsf & BIT(0)); + memcpy(sta->rateset[rateset].rates, rates, + sizeof(sta->rateset[rateset].rates)); + if (probe_rate) { + sta->rateset[rateset].probe_rate = *probe_rate; + ref = &sta->rateset[rateset].probe_rate; + } else { + sta->rateset[rateset].probe_rate.idx = -1; + ref = &sta->rateset[rateset].rates[0]; + } + + rates = sta->rateset[rateset].rates; + for (i = 0; i < ARRAY_SIZE(sta->rateset[rateset].rates); i++) { + /* + * We don't support switching between short and long GI + * within the rate set. For accurate tx status reporting, we + * need to make sure that flags match. + * For improved performance, avoid duplicate entries by + * decrementing the MCS index if necessary + */ + if ((ref->flags ^ rates[i].flags) & IEEE80211_TX_RC_SHORT_GI) + rates[i].flags ^= IEEE80211_TX_RC_SHORT_GI; + + for (k = 0; k < i; k++) { + if (rates[i].idx != rates[k].idx) + continue; + if ((rates[i].flags ^ rates[k].flags) & + (IEEE80211_TX_RC_40_MHZ_WIDTH | + IEEE80211_TX_RC_80_MHZ_WIDTH | + IEEE80211_TX_RC_160_MHZ_WIDTH)) + continue; + + if (!rates[i].idx) + continue; + + rates[i].idx--; + } + } + + val[0] = mt7615_mac_tx_rate_val(dev, &rates[0], stbc, &bw); + bw_prev = bw; + + if (probe_rate) { + probe_val = mt7615_mac_tx_rate_val(dev, probe_rate, stbc, &bw); + if (bw) + bw_idx = 1; + else + bw_prev = 0; + } else { + probe_val = val[0]; + } + + val[1] = mt7615_mac_tx_rate_val(dev, &rates[1], stbc, &bw); + if (bw_prev) { + bw_idx = 3; + bw_prev = bw; + } + + val[2] = mt7615_mac_tx_rate_val(dev, &rates[2], stbc, &bw); + if (bw_prev) { + bw_idx = 5; + bw_prev = bw; + } + + val[3] = mt7615_mac_tx_rate_val(dev, &rates[3], stbc, &bw); + if (bw_prev) + bw_idx = 7; + + w27 = mt76_rr(dev, addr + 27 * 4); + w27 &= ~MT_WTBL_W27_CC_BW_SEL; + w27 |= FIELD_PREP(MT_WTBL_W27_CC_BW_SEL, bw); + + w5 = mt76_rr(dev, addr + 5 * 4); + w5 &= ~(MT_WTBL_W5_BW_CAP | MT_WTBL_W5_CHANGE_BW_RATE | + MT_WTBL_W5_MPDU_OK_COUNT | + MT_WTBL_W5_MPDU_FAIL_COUNT | + MT_WTBL_W5_RATE_IDX); + w5 |= FIELD_PREP(MT_WTBL_W5_BW_CAP, bw) | + FIELD_PREP(MT_WTBL_W5_CHANGE_BW_RATE, bw_idx ? bw_idx - 1 : 7); + + mt76_wr(dev, MT_WTBL_RIUCR0, w5); + + mt76_wr(dev, MT_WTBL_RIUCR1, + FIELD_PREP(MT_WTBL_RIUCR1_RATE0, probe_val) | + FIELD_PREP(MT_WTBL_RIUCR1_RATE1, val[0]) | + FIELD_PREP(MT_WTBL_RIUCR1_RATE2_LO, val[1])); + + mt76_wr(dev, MT_WTBL_RIUCR2, + FIELD_PREP(MT_WTBL_RIUCR2_RATE2_HI, val[1] >> 8) | + FIELD_PREP(MT_WTBL_RIUCR2_RATE3, val[1]) | + FIELD_PREP(MT_WTBL_RIUCR2_RATE4, val[2]) | + FIELD_PREP(MT_WTBL_RIUCR2_RATE5_LO, val[2])); + + mt76_wr(dev, MT_WTBL_RIUCR3, + FIELD_PREP(MT_WTBL_RIUCR3_RATE5_HI, val[2] >> 4) | + FIELD_PREP(MT_WTBL_RIUCR3_RATE6, val[3]) | + FIELD_PREP(MT_WTBL_RIUCR3_RATE7, val[3])); + + mt76_wr(dev, MT_WTBL_UPDATE, + FIELD_PREP(MT_WTBL_UPDATE_WLAN_IDX, wcid) | + MT_WTBL_UPDATE_RATE_UPDATE | + MT_WTBL_UPDATE_TX_COUNT_CLEAR); + + mt76_wr(dev, addr + 27 * 4, w27); + + mt76_set(dev, MT_LPON_T0CR, MT_LPON_T0CR_MODE); /* TSF read */ + sta->rate_set_tsf = (mt76_rr(dev, MT_LPON_UTTR0) & ~BIT(0)) | rateset; + + if (!(sta->wcid.tx_info & MT_WCID_TX_INFO_SET)) + mt76_poll(dev, MT_WTBL_UPDATE, MT_WTBL_UPDATE_BUSY, 0, 5000); + + sta->rate_count = 2 * MT7615_RATE_RETRY * n_rates; + sta->wcid.tx_info |= MT_WCID_TX_INFO_SET; +} + +static enum mt7615_cipher_type +mt7615_mac_get_cipher(int cipher) +{ + switch (cipher) { + case WLAN_CIPHER_SUITE_WEP40: + return MT_CIPHER_WEP40; + case WLAN_CIPHER_SUITE_WEP104: + return MT_CIPHER_WEP104; + case WLAN_CIPHER_SUITE_TKIP: + return MT_CIPHER_TKIP; + case WLAN_CIPHER_SUITE_AES_CMAC: + return MT_CIPHER_BIP_CMAC_128; + case WLAN_CIPHER_SUITE_CCMP: + return MT_CIPHER_AES_CCMP; + case WLAN_CIPHER_SUITE_CCMP_256: + return MT_CIPHER_CCMP_256; + case WLAN_CIPHER_SUITE_GCMP: + return MT_CIPHER_GCMP; + case WLAN_CIPHER_SUITE_GCMP_256: + return MT_CIPHER_GCMP_256; + case WLAN_CIPHER_SUITE_SMS4: + return MT_CIPHER_WAPI; + default: + return MT_CIPHER_NONE; + } +} + +static int +mt7615_mac_wtbl_update_key(struct mt7615_dev *dev, struct mt76_wcid *wcid, + struct ieee80211_key_conf *key, + enum mt7615_cipher_type cipher, + enum set_key_cmd cmd) +{ + u32 addr = mt7615_mac_wtbl_addr(wcid->idx) + 30 * 4; + u8 data[32] = {}; + + if (key->keylen > sizeof(data)) + return -EINVAL; + + mt76_rr_copy(dev, addr, data, sizeof(data)); + if (cmd == SET_KEY) { + if (cipher == MT_CIPHER_TKIP) { + /* Rx/Tx MIC keys are swapped */ + memcpy(data + 16, key->key + 24, 8); + memcpy(data + 24, key->key + 16, 8); + } + if (cipher != MT_CIPHER_BIP_CMAC_128 && wcid->cipher) + memmove(data + 16, data, 16); + if (cipher != MT_CIPHER_BIP_CMAC_128 || !wcid->cipher) + memcpy(data, key->key, key->keylen); + else if (cipher == MT_CIPHER_BIP_CMAC_128) + memcpy(data + 16, key->key, 16); + } else { + if (wcid->cipher & ~BIT(cipher)) { + if (cipher != MT_CIPHER_BIP_CMAC_128) + memmove(data, data + 16, 16); + memset(data + 16, 0, 16); + } else { + memset(data, 0, sizeof(data)); + } + } + mt76_wr_copy(dev, addr, data, sizeof(data)); + + return 0; +} + +static int +mt7615_mac_wtbl_update_pk(struct mt7615_dev *dev, struct mt76_wcid *wcid, + enum mt7615_cipher_type cipher, int keyidx, + enum set_key_cmd cmd) +{ + u32 addr = mt7615_mac_wtbl_addr(wcid->idx), w0, w1; + + if (!mt76_poll(dev, MT_WTBL_UPDATE, MT_WTBL_UPDATE_BUSY, 0, 5000)) + return -ETIMEDOUT; + + w0 = mt76_rr(dev, addr); + w1 = mt76_rr(dev, addr + 4); + if (cmd == SET_KEY) { + w0 |= MT_WTBL_W0_RX_KEY_VALID | + FIELD_PREP(MT_WTBL_W0_RX_IK_VALID, + cipher == MT_CIPHER_BIP_CMAC_128); + if (cipher != MT_CIPHER_BIP_CMAC_128 || + !wcid->cipher) + w0 |= FIELD_PREP(MT_WTBL_W0_KEY_IDX, keyidx); + } else { + if (!(wcid->cipher & ~BIT(cipher))) + w0 &= ~(MT_WTBL_W0_RX_KEY_VALID | + MT_WTBL_W0_KEY_IDX); + if (cipher == MT_CIPHER_BIP_CMAC_128) + w0 &= ~MT_WTBL_W0_RX_IK_VALID; + } + mt76_wr(dev, MT_WTBL_RICR0, w0); + mt76_wr(dev, MT_WTBL_RICR1, w1); + + mt76_wr(dev, MT_WTBL_UPDATE, + FIELD_PREP(MT_WTBL_UPDATE_WLAN_IDX, wcid->idx) | + MT_WTBL_UPDATE_RXINFO_UPDATE); + + if (!mt76_poll(dev, MT_WTBL_UPDATE, MT_WTBL_UPDATE_BUSY, 0, 5000)) + return -ETIMEDOUT; + + return 0; +} + +static void +mt7615_mac_wtbl_update_cipher(struct mt7615_dev *dev, struct mt76_wcid *wcid, + enum mt7615_cipher_type cipher, + enum set_key_cmd cmd) +{ + u32 addr = mt7615_mac_wtbl_addr(wcid->idx); + + if (cmd == SET_KEY) { + if (cipher != MT_CIPHER_BIP_CMAC_128 || !wcid->cipher) + mt76_rmw(dev, addr + 2 * 4, MT_WTBL_W2_KEY_TYPE, + FIELD_PREP(MT_WTBL_W2_KEY_TYPE, cipher)); + } else { + if (cipher != MT_CIPHER_BIP_CMAC_128 && + wcid->cipher & BIT(MT_CIPHER_BIP_CMAC_128)) + mt76_rmw(dev, addr + 2 * 4, MT_WTBL_W2_KEY_TYPE, + FIELD_PREP(MT_WTBL_W2_KEY_TYPE, + MT_CIPHER_BIP_CMAC_128)); + else if (!(wcid->cipher & ~BIT(cipher))) + mt76_clear(dev, addr + 2 * 4, MT_WTBL_W2_KEY_TYPE); + } +} + +int mt7615_mac_wtbl_set_key(struct mt7615_dev *dev, + struct mt76_wcid *wcid, + struct ieee80211_key_conf *key, + enum set_key_cmd cmd) +{ + enum mt7615_cipher_type cipher; + int err; + + cipher = mt7615_mac_get_cipher(key->cipher); + if (cipher == MT_CIPHER_NONE) + return -EOPNOTSUPP; + + spin_lock_bh(&dev->mt76.lock); + + mt7615_mac_wtbl_update_cipher(dev, wcid, cipher, cmd); + err = mt7615_mac_wtbl_update_key(dev, wcid, key, cipher, cmd); + if (err < 0) + goto out; + + err = mt7615_mac_wtbl_update_pk(dev, wcid, cipher, key->keyidx, + cmd); + if (err < 0) + goto out; + + if (cmd == SET_KEY) + wcid->cipher |= BIT(cipher); + else + wcid->cipher &= ~BIT(cipher); + +out: + spin_unlock_bh(&dev->mt76.lock); + + return err; +} + int mt7615_tx_prepare_skb(struct mt76_dev *mdev, void *txwi_ptr, enum mt76_txq_id qid, struct mt76_wcid *wcid, struct ieee80211_sta *sta, @@ -469,9 +782,9 @@ int mt7615_tx_prepare_skb(struct mt76_dev *mdev, void *txwi_ptr, if (info->flags & IEEE80211_TX_CTL_RATE_CTRL_PROBE) { spin_lock_bh(&dev->mt76.lock); - msta->rate_probe = true; - mt7615_mcu_set_rates(dev, msta, &info->control.rates[0], + mt7615_mac_set_rates(dev, msta, &info->control.rates[0], msta->rates); + msta->rate_probe = true; spin_unlock_bh(&dev->mt76.lock); } @@ -523,9 +836,13 @@ static bool mt7615_fill_txs(struct mt7615_dev *dev, struct mt7615_sta *sta, struct ieee80211_tx_info *info, __le32 *txs_data) { struct ieee80211_supported_band *sband; - int i, idx, count, final_idx = 0; + struct mt7615_rate_set *rs; + int first_idx = 0, last_idx; + int i, idx, count; bool fixed_rate, ack_timeout; bool probe, ampdu, cck = false; + bool rs_idx; + u32 rate_set_tsf; u32 final_rate, final_rate_flags, final_nss, txs; fixed_rate = info->status.rates[0].count; @@ -536,6 +853,7 @@ static bool mt7615_fill_txs(struct mt7615_dev *dev, struct mt7615_sta *sta, txs = le32_to_cpu(txs_data[3]); count = FIELD_GET(MT_TXS3_TX_COUNT, txs); + last_idx = FIELD_GET(MT_TXS3_LAST_TX_RATE, txs); txs = le32_to_cpu(txs_data[0]); final_rate = FIELD_GET(MT_TXS0_TX_RATE, txs); @@ -557,38 +875,57 @@ static bool mt7615_fill_txs(struct mt7615_dev *dev, struct mt7615_sta *sta, if (ampdu || (info->flags & IEEE80211_TX_CTL_AMPDU)) info->flags |= IEEE80211_TX_STAT_AMPDU | IEEE80211_TX_CTL_AMPDU; + first_idx = max_t(int, 0, last_idx - (count + 1) / MT7615_RATE_RETRY); + if (fixed_rate && !probe) { info->status.rates[0].count = count; + i = 0; goto out; } - for (i = 0, idx = 0; i < ARRAY_SIZE(info->status.rates); i++) { - int cur_count = min_t(int, count, 2 * MT7615_RATE_RETRY); + rate_set_tsf = READ_ONCE(sta->rate_set_tsf); + rs_idx = !((u32)(FIELD_GET(MT_TXS4_F0_TIMESTAMP, le32_to_cpu(txs_data[4])) - + rate_set_tsf) < 1000000); + rs_idx ^= rate_set_tsf & BIT(0); + rs = &sta->rateset[rs_idx]; - if (!i && probe) { - cur_count = 1; - } else { - info->status.rates[i] = sta->rates[idx]; - idx++; - } + if (!first_idx && rs->probe_rate.idx >= 0) { + info->status.rates[0] = rs->probe_rate; - if (i && info->status.rates[i].idx < 0) { - info->status.rates[i - 1].count += count; - break; + spin_lock_bh(&dev->mt76.lock); + if (sta->rate_probe) { + mt7615_mac_set_rates(dev, sta, NULL, sta->rates); + sta->rate_probe = false; } + spin_unlock_bh(&dev->mt76.lock); + } else { + info->status.rates[0] = rs->rates[first_idx / 2]; + } + info->status.rates[0].count = 0; - if (!count) { - info->status.rates[i].idx = -1; - break; - } + for (i = 0, idx = first_idx; count && idx <= last_idx; idx++) { + struct ieee80211_tx_rate *cur_rate; + int cur_count; - info->status.rates[i].count = cur_count; - final_idx = i; + cur_rate = &rs->rates[idx / 2]; + cur_count = min_t(int, MT7615_RATE_RETRY, count); count -= cur_count; + + if (idx && (cur_rate->idx != info->status.rates[i].idx || + cur_rate->flags != info->status.rates[i].flags)) { + i++; + if (i == ARRAY_SIZE(info->status.rates)) + break; + + info->status.rates[i] = *cur_rate; + info->status.rates[i].count = 0; + } + + info->status.rates[i].count += cur_count; } out: - final_rate_flags = info->status.rates[final_idx].flags; + final_rate_flags = info->status.rates[i].flags; switch (FIELD_GET(MT_TX_RATE_MODE, final_rate)) { case MT_PHY_TYPE_CCK: @@ -613,6 +950,10 @@ out: break; case MT_PHY_TYPE_VHT: final_nss = FIELD_GET(MT_TX_RATE_NSS, final_rate); + + if ((final_rate & MT_TX_RATE_STBC) && final_nss) + final_nss--; + final_rate_flags |= IEEE80211_TX_RC_VHT_MCS; final_rate = (final_rate & MT_TX_RATE_IDX) | (final_nss << 4); break; @@ -620,8 +961,8 @@ out: return false; } - info->status.rates[final_idx].idx = final_rate; - info->status.rates[final_idx].flags = final_rate_flags; + info->status.rates[i].idx = final_rate; + info->status.rates[i].flags = final_rate_flags; return true; } @@ -642,16 +983,6 @@ static bool mt7615_mac_add_txs_skb(struct mt7615_dev *dev, if (skb) { struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb); - if (info->flags & IEEE80211_TX_CTL_RATE_CTRL_PROBE) { - spin_lock_bh(&dev->mt76.lock); - if (sta->rate_probe) { - mt7615_mcu_set_rates(dev, sta, NULL, - sta->rates); - sta->rate_probe = false; - } - spin_unlock_bh(&dev->mt76.lock); - } - if (!mt7615_fill_txs(dev, sta, info, txs_data)) { ieee80211_tx_info_clear_status(info); info->status.rates[0].idx = -1; @@ -735,6 +1066,198 @@ void mt7615_mac_tx_free(struct mt7615_dev *dev, struct sk_buff *skb) dev_kfree_skb(skb); } +static void +mt7615_mac_set_default_sensitivity(struct mt7615_dev *dev) +{ + mt76_rmw(dev, MT_WF_PHY_B0_MIN_PRI_PWR, + MT_WF_PHY_B0_PD_OFDM_MASK, + MT_WF_PHY_B0_PD_OFDM(0x13c)); + mt76_rmw(dev, MT_WF_PHY_B1_MIN_PRI_PWR, + MT_WF_PHY_B1_PD_OFDM_MASK, + MT_WF_PHY_B1_PD_OFDM(0x13c)); + + mt76_rmw(dev, MT_WF_PHY_B0_RXTD_CCK_PD, + MT_WF_PHY_B0_PD_CCK_MASK, + MT_WF_PHY_B0_PD_CCK(0x92)); + mt76_rmw(dev, MT_WF_PHY_B1_RXTD_CCK_PD, + MT_WF_PHY_B1_PD_CCK_MASK, + MT_WF_PHY_B1_PD_CCK(0x92)); + + dev->ofdm_sensitivity = -98; + dev->cck_sensitivity = -110; + dev->last_cca_adj = jiffies; +} + +void mt7615_mac_set_scs(struct mt7615_dev *dev, bool enable) +{ + mutex_lock(&dev->mt76.mutex); + + if (dev->scs_en == enable) + goto out; + + if (enable) { + /* DBDC not supported */ + mt76_set(dev, MT_WF_PHY_B0_MIN_PRI_PWR, + MT_WF_PHY_B0_PD_BLK); + if (is_mt7622(&dev->mt76)) { + mt76_set(dev, MT_MIB_M0_MISC_CR, 0x7 << 8); + mt76_set(dev, MT_MIB_M0_MISC_CR, 0x7); + } + } else { + mt76_clear(dev, MT_WF_PHY_B0_MIN_PRI_PWR, + MT_WF_PHY_B0_PD_BLK); + mt76_clear(dev, MT_WF_PHY_B1_MIN_PRI_PWR, + MT_WF_PHY_B1_PD_BLK); + } + + mt7615_mac_set_default_sensitivity(dev); + dev->scs_en = enable; + +out: + mutex_unlock(&dev->mt76.mutex); +} + +void mt7615_mac_cca_stats_reset(struct mt7615_dev *dev) +{ + mt76_clear(dev, MT_WF_PHY_R0_B0_PHYMUX_5, GENMASK(22, 20)); + mt76_set(dev, MT_WF_PHY_R0_B0_PHYMUX_5, BIT(22) | BIT(20)); +} + +static void +mt7615_mac_adjust_sensitivity(struct mt7615_dev *dev, + u32 rts_err_rate, bool ofdm) +{ + int false_cca = ofdm ? dev->false_cca_ofdm : dev->false_cca_cck; + u16 def_th = ofdm ? -98 : -110; + bool update = false; + s8 *sensitivity; + int signal; + + sensitivity = ofdm ? &dev->ofdm_sensitivity : &dev->cck_sensitivity; + signal = mt76_get_min_avg_rssi(&dev->mt76); + if (!signal) { + mt7615_mac_set_default_sensitivity(dev); + return; + } + + signal = min(signal, -72); + if (false_cca > 500) { + if (rts_err_rate > MT_FRAC(40, 100)) + return; + + /* decrease coverage */ + if (*sensitivity == def_th && signal > -90) { + *sensitivity = -90; + update = true; + } else if (*sensitivity + 2 < signal) { + *sensitivity += 2; + update = true; + } + } else if ((false_cca > 0 && false_cca < 50) || + rts_err_rate > MT_FRAC(60, 100)) { + /* increase coverage */ + if (*sensitivity - 2 >= def_th) { + *sensitivity -= 2; + update = true; + } + } + + if (*sensitivity > signal) { + *sensitivity = signal; + update = true; + } + + if (update) { + u16 val; + + if (ofdm) { + /* DBDC not supported */ + val = *sensitivity * 2 + 512; + mt76_rmw(dev, MT_WF_PHY_B0_MIN_PRI_PWR, + MT_WF_PHY_B0_PD_OFDM_MASK, + MT_WF_PHY_B0_PD_OFDM(val)); + } else { + val = *sensitivity + 256; + mt76_rmw(dev, MT_WF_PHY_B0_RXTD_CCK_PD, + MT_WF_PHY_B0_PD_CCK_MASK, + MT_WF_PHY_B0_PD_CCK(val)); + mt76_rmw(dev, MT_WF_PHY_B1_RXTD_CCK_PD, + MT_WF_PHY_B1_PD_CCK_MASK, + MT_WF_PHY_B1_PD_CCK(val)); + } + dev->last_cca_adj = jiffies; + } +} + +static void +mt7615_mac_scs_check(struct mt7615_dev *dev) +{ + u32 val, rts_cnt = 0, rts_retries_cnt = 0, rts_err_rate = 0; + u32 mdrdy_cck, mdrdy_ofdm, pd_cck, pd_ofdm; + int i; + + if (!dev->scs_en) + return; + + for (i = 0; i < 4; i++) { + u32 data; + + val = mt76_rr(dev, MT_MIB_MB_SDR0(i)); + data = FIELD_GET(MT_MIB_RTS_RETRIES_COUNT_MASK, val); + if (data > rts_retries_cnt) { + rts_cnt = FIELD_GET(MT_MIB_RTS_COUNT_MASK, val); + rts_retries_cnt = data; + } + } + + val = mt76_rr(dev, MT_WF_PHY_R0_B0_PHYCTRL_STS0); + pd_cck = FIELD_GET(MT_WF_PHYCTRL_STAT_PD_CCK, val); + pd_ofdm = FIELD_GET(MT_WF_PHYCTRL_STAT_PD_OFDM, val); + + val = mt76_rr(dev, MT_WF_PHY_R0_B0_PHYCTRL_STS5); + mdrdy_cck = FIELD_GET(MT_WF_PHYCTRL_STAT_MDRDY_CCK, val); + mdrdy_ofdm = FIELD_GET(MT_WF_PHYCTRL_STAT_MDRDY_OFDM, val); + + dev->false_cca_ofdm = pd_ofdm - mdrdy_ofdm; + dev->false_cca_cck = pd_cck - mdrdy_cck; + mt7615_mac_cca_stats_reset(dev); + + if (rts_cnt + rts_retries_cnt) + rts_err_rate = MT_FRAC(rts_retries_cnt, + rts_cnt + rts_retries_cnt); + + /* cck */ + mt7615_mac_adjust_sensitivity(dev, rts_err_rate, false); + /* ofdm */ + mt7615_mac_adjust_sensitivity(dev, rts_err_rate, true); + + if (time_after(jiffies, dev->last_cca_adj + 10 * HZ)) + mt7615_mac_set_default_sensitivity(dev); +} + +void mt7615_update_channel(struct mt76_dev *mdev) +{ + struct mt7615_dev *dev = container_of(mdev, struct mt7615_dev, mt76); + struct mt76_channel_state *state; + ktime_t cur_time; + u32 busy; + + if (!test_bit(MT76_STATE_RUNNING, &mdev->state)) + return; + + state = mt76_channel_state(mdev, mdev->chandef.chan); + /* TODO: add DBDC support */ + busy = mt76_get_field(dev, MT_MIB_SDR16(0), MT_MIB_BUSY_MASK); + + spin_lock_bh(&mdev->cc_lock); + cur_time = ktime_get_boottime(); + state->cc_busy += busy; + state->cc_active += ktime_to_us(ktime_sub(cur_time, + mdev->survey_time)); + mdev->survey_time = cur_time; + spin_unlock_bh(&mdev->cc_lock); +} + void mt7615_mac_work(struct work_struct *work) { struct mt7615_dev *dev; @@ -742,7 +1265,103 @@ void mt7615_mac_work(struct work_struct *work) dev = (struct mt7615_dev *)container_of(work, struct mt76_dev, mac_work.work); + mutex_lock(&dev->mt76.mutex); + mt7615_update_channel(&dev->mt76); + if (++dev->mac_work_count == 5) { + mt7615_mac_scs_check(dev); + dev->mac_work_count = 0; + } + mutex_unlock(&dev->mt76.mutex); + mt76_tx_status_check(&dev->mt76, NULL, false); ieee80211_queue_delayed_work(mt76_hw(dev), &dev->mt76.mac_work, MT7615_WATCHDOG_TIME); } + +int mt7615_dfs_stop_radar_detector(struct mt7615_dev *dev) +{ + struct cfg80211_chan_def *chandef = &dev->mt76.chandef; + int err; + + err = mt7615_mcu_rdd_cmd(dev, RDD_STOP, MT_HW_RDD0, + MT_RX_SEL0, 0); + if (err < 0) + return err; + + if (chandef->width == NL80211_CHAN_WIDTH_160 || + chandef->width == NL80211_CHAN_WIDTH_80P80) + err = mt7615_mcu_rdd_cmd(dev, RDD_STOP, MT_HW_RDD1, + MT_RX_SEL0, 0); + return err; +} + +static int mt7615_dfs_start_rdd(struct mt7615_dev *dev, int chain) +{ + int err; + + err = mt7615_mcu_rdd_cmd(dev, RDD_START, chain, MT_RX_SEL0, 0); + if (err < 0) + return err; + + return mt7615_mcu_rdd_cmd(dev, RDD_DET_MODE, chain, + MT_RX_SEL0, 1); +} + +int mt7615_dfs_start_radar_detector(struct mt7615_dev *dev) +{ + struct cfg80211_chan_def *chandef = &dev->mt76.chandef; + int err; + + /* start CAC */ + err = mt7615_mcu_rdd_cmd(dev, RDD_CAC_START, MT_HW_RDD0, + MT_RX_SEL0, 0); + if (err < 0) + return err; + + /* TODO: DBDC support */ + + err = mt7615_dfs_start_rdd(dev, MT_HW_RDD0); + if (err < 0) + return err; + + if (chandef->width == NL80211_CHAN_WIDTH_160 || + chandef->width == NL80211_CHAN_WIDTH_80P80) { + err = mt7615_dfs_start_rdd(dev, MT_HW_RDD1); + if (err < 0) + return err; + } + + return 0; +} + +int mt7615_dfs_init_radar_detector(struct mt7615_dev *dev) +{ + struct cfg80211_chan_def *chandef = &dev->mt76.chandef; + int err; + + if (dev->mt76.region == NL80211_DFS_UNSET) + return 0; + + if (test_bit(MT76_SCANNING, &dev->mt76.state)) + return 0; + + if (dev->dfs_state == chandef->chan->dfs_state) + return 0; + + dev->dfs_state = chandef->chan->dfs_state; + + if (chandef->chan->flags & IEEE80211_CHAN_RADAR) { + if (chandef->chan->dfs_state != NL80211_DFS_AVAILABLE) + return mt7615_dfs_start_radar_detector(dev); + else + return mt7615_mcu_rdd_cmd(dev, RDD_CAC_END, MT_HW_RDD0, + MT_RX_SEL0, 0); + } else { + err = mt7615_mcu_rdd_cmd(dev, RDD_NORMAL_START, + MT_HW_RDD0, MT_RX_SEL0, 0); + if (err < 0) + return err; + + return mt7615_dfs_stop_radar_detector(dev); + } +} diff --git a/drivers/net/wireless/mediatek/mt76/mt7615/mac.h b/drivers/net/wireless/mediatek/mt76/mt7615/mac.h index b00ce8db58e9..38695d4f92e2 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7615/mac.h +++ b/drivers/net/wireless/mediatek/mt76/mt7615/mac.h @@ -302,4 +302,32 @@ struct mt7615_tx_free { #define MT_TXS6_F1_RCPI_1 GENMASK(15, 8) #define MT_TXS6_F1_RCPI_0 GENMASK(7, 0) +enum mt7615_cipher_type { + MT_CIPHER_NONE, + MT_CIPHER_WEP40, + MT_CIPHER_TKIP, + MT_CIPHER_TKIP_NO_MIC, + MT_CIPHER_AES_CCMP, + MT_CIPHER_WEP104, + MT_CIPHER_BIP_CMAC_128, + MT_CIPHER_WEP128, + MT_CIPHER_WAPI, + MT_CIPHER_CCMP_256 = 10, + MT_CIPHER_GCMP, + MT_CIPHER_GCMP_256, +}; + +static inline struct mt7615_txp * +mt7615_txwi_to_txp(struct mt76_dev *dev, struct mt76_txwi_cache *t) +{ + u8 *txwi; + + if (!t) + return NULL; + + txwi = mt76_get_txwi_ptr(dev, t); + + return (struct mt7615_txp *)(txwi + MT_TXD_SIZE); +} + #endif diff --git a/drivers/net/wireless/mediatek/mt76/mt7615/main.c b/drivers/net/wireless/mediatek/mt76/mt7615/main.c index b4d6af812c54..87c748715b5d 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7615/main.c +++ b/drivers/net/wireless/mediatek/mt76/mt7615/main.c @@ -16,6 +16,7 @@ static int mt7615_start(struct ieee80211_hw *hw) { struct mt7615_dev *dev = hw->priv; + dev->mt76.survey_time = ktime_get_boottime(); set_bit(MT76_STATE_RUNNING, &dev->mt76.state); ieee80211_queue_delayed_work(mt76_hw(dev), &dev->mt76.mac_work, MT7615_WATCHDOG_TIME); @@ -85,9 +86,9 @@ static int mt7615_add_interface(struct ieee80211_hw *hw, } mvif->omac_idx = idx; - /* TODO: DBDC support. Use band 0 and wmm 0 for now */ + /* TODO: DBDC support. Use band 0 for now */ mvif->band_idx = 0; - mvif->wmm_idx = 0; + mvif->wmm_idx = mvif->idx % MT7615_MAX_WMM_SETS; ret = mt7615_mcu_set_dev_info(dev, vif, 1); if (ret) @@ -135,20 +136,32 @@ static int mt7615_set_channel(struct mt7615_dev *dev) int ret; cancel_delayed_work_sync(&dev->mt76.mac_work); + + mutex_lock(&dev->mt76.mutex); set_bit(MT76_RESET, &dev->mt76.state); + mt7615_dfs_check_channel(dev); + mt76_set_channel(&dev->mt76); ret = mt7615_mcu_set_channel(dev); if (ret) - return ret; + goto out; + + ret = mt7615_dfs_init_radar_detector(dev); + mt7615_mac_cca_stats_reset(dev); + dev->mt76.survey_time = ktime_get_boottime(); + /* TODO: add DBDC support */ + mt76_rr(dev, MT_MIB_SDR16(0)); +out: clear_bit(MT76_RESET, &dev->mt76.state); + mutex_unlock(&dev->mt76.mutex); mt76_txq_schedule_all(&dev->mt76); ieee80211_queue_delayed_work(mt76_hw(dev), &dev->mt76.mac_work, MT7615_WATCHDOG_TIME); - return 0; + return ret; } static int mt7615_set_key(struct ieee80211_hw *hw, enum set_key_cmd cmd, @@ -172,18 +185,34 @@ static int mt7615_set_key(struct ieee80211_hw *hw, enum set_key_cmd cmd, !(key->flags & IEEE80211_KEY_FLAG_PAIRWISE)) return -EOPNOTSUPP; + /* fall back to sw encryption for unsupported ciphers */ + switch (key->cipher) { + case WLAN_CIPHER_SUITE_AES_CMAC: + key->flags |= IEEE80211_KEY_FLAG_GENERATE_MMIE; + break; + case WLAN_CIPHER_SUITE_WEP40: + case WLAN_CIPHER_SUITE_WEP104: + case WLAN_CIPHER_SUITE_TKIP: + case WLAN_CIPHER_SUITE_CCMP: + case WLAN_CIPHER_SUITE_CCMP_256: + case WLAN_CIPHER_SUITE_GCMP: + case WLAN_CIPHER_SUITE_GCMP_256: + case WLAN_CIPHER_SUITE_SMS4: + break; + default: + return -EOPNOTSUPP; + } + if (cmd == SET_KEY) { key->hw_key_idx = wcid->idx; wcid->hw_key_idx = idx; - } else { - if (idx == wcid->hw_key_idx) - wcid->hw_key_idx = -1; - - key = NULL; + } else if (idx == wcid->hw_key_idx) { + wcid->hw_key_idx = -1; } - mt76_wcid_key_setup(&dev->mt76, wcid, key); + mt76_wcid_key_setup(&dev->mt76, wcid, + cmd == SET_KEY ? key : NULL); - return mt7615_mcu_set_wtbl_key(dev, wcid->idx, key, cmd); + return mt7615_mac_wtbl_set_key(dev, wcid, key, cmd); } static int mt7615_config(struct ieee80211_hw *hw, u32 changed) @@ -191,14 +220,14 @@ static int mt7615_config(struct ieee80211_hw *hw, u32 changed) struct mt7615_dev *dev = hw->priv; int ret = 0; - mutex_lock(&dev->mt76.mutex); - if (changed & IEEE80211_CONF_CHANGE_CHANNEL) { ieee80211_stop_queues(hw); ret = mt7615_set_channel(dev); ieee80211_wake_queues(hw); } + mutex_lock(&dev->mt76.mutex); + if (changed & IEEE80211_CONF_CHANGE_POWER) ret = mt7615_mcu_set_tx_power(dev); @@ -220,16 +249,12 @@ static int mt7615_conf_tx(struct ieee80211_hw *hw, struct ieee80211_vif *vif, u16 queue, const struct ieee80211_tx_queue_params *params) { + struct mt7615_vif *mvif = (struct mt7615_vif *)vif->drv_priv; struct mt7615_dev *dev = hw->priv; - static const u8 wmm_queue_map[] = { - [IEEE80211_AC_BK] = 0, - [IEEE80211_AC_BE] = 1, - [IEEE80211_AC_VI] = 2, - [IEEE80211_AC_VO] = 3, - }; - /* TODO: hw wmm_set 1~3 */ - return mt7615_mcu_set_wmm(dev, wmm_queue_map[queue], params); + queue += mvif->wmm_idx * MT7615_MAX_WMM_SETS; + + return mt7615_mcu_set_wmm(dev, queue, params); } static void mt7615_configure_filter(struct ieee80211_hw *hw, @@ -299,6 +324,18 @@ static void mt7615_bss_info_changed(struct ieee80211_hw *hw, mutex_unlock(&dev->mt76.mutex); } +static void +mt7615_channel_switch_beacon(struct ieee80211_hw *hw, + struct ieee80211_vif *vif, + struct cfg80211_chan_def *chandef) +{ + struct mt7615_dev *dev = hw->priv; + + mutex_lock(&dev->mt76.mutex); + mt7615_mcu_set_bcn(dev, vif, true); + mutex_unlock(&dev->mt76.mutex); +} + int mt7615_sta_add(struct mt76_dev *mdev, struct ieee80211_vif *vif, struct ieee80211_sta *sta) { @@ -358,7 +395,7 @@ static void mt7615_sta_rate_tbl_update(struct ieee80211_hw *hw, break; } msta->n_rates = i; - mt7615_mcu_set_rates(dev, msta, NULL, msta->rates); + mt7615_mac_set_rates(dev, msta, NULL, msta->rates); msta->rate_probe = false; spin_unlock_bh(&dev->mt76.lock); } @@ -410,7 +447,7 @@ mt7615_ampdu_action(struct ieee80211_hw *hw, struct ieee80211_vif *vif, struct ieee80211_txq *txq = sta->txq[params->tid]; struct mt7615_sta *msta = (struct mt7615_sta *)sta->drv_priv; u16 tid = params->tid; - u16 *ssn = ¶ms->ssn; + u16 ssn = params->ssn; struct mt76_txq *mtxq; if (!txq) @@ -420,7 +457,7 @@ mt7615_ampdu_action(struct ieee80211_hw *hw, struct ieee80211_vif *vif, switch (action) { case IEEE80211_AMPDU_RX_START: - mt76_rx_aggr_start(&dev->mt76, &msta->wcid, tid, *ssn, + mt76_rx_aggr_start(&dev->mt76, &msta->wcid, tid, ssn, params->buf_size); mt7615_mcu_set_rx_ba(dev, params, 1); break; @@ -436,11 +473,10 @@ mt7615_ampdu_action(struct ieee80211_hw *hw, struct ieee80211_vif *vif, case IEEE80211_AMPDU_TX_STOP_FLUSH: case IEEE80211_AMPDU_TX_STOP_FLUSH_CONT: mtxq->aggr = false; - ieee80211_send_bar(vif, sta->addr, tid, mtxq->agg_ssn); mt7615_mcu_set_tx_ba(dev, params, 0); break; case IEEE80211_AMPDU_TX_START: - mtxq->agg_ssn = IEEE80211_SN_TO_SEQ(*ssn); + mtxq->agg_ssn = IEEE80211_SN_TO_SEQ(ssn); ieee80211_start_tx_ba_cb_irqsafe(vif, sta->addr, tid); break; case IEEE80211_AMPDU_TX_STOP_CONT: @@ -453,23 +489,6 @@ mt7615_ampdu_action(struct ieee80211_hw *hw, struct ieee80211_vif *vif, return 0; } -static void -mt7615_sw_scan(struct ieee80211_hw *hw, struct ieee80211_vif *vif, - const u8 *mac) -{ - struct mt7615_dev *dev = hw->priv; - - set_bit(MT76_SCANNING, &dev->mt76.state); -} - -static void -mt7615_sw_scan_complete(struct ieee80211_hw *hw, struct ieee80211_vif *vif) -{ - struct mt7615_dev *dev = hw->priv; - - clear_bit(MT76_SCANNING, &dev->mt76.state); -} - const struct ieee80211_ops mt7615_ops = { .tx = mt7615_tx, .start = mt7615_start, @@ -486,8 +505,10 @@ const struct ieee80211_ops mt7615_ops = { .set_rts_threshold = mt7615_set_rts_threshold, .wake_tx_queue = mt76_wake_tx_queue, .sta_rate_tbl_update = mt7615_sta_rate_tbl_update, - .sw_scan_start = mt7615_sw_scan, - .sw_scan_complete = mt7615_sw_scan_complete, + .sw_scan_start = mt76_sw_scan, + .sw_scan_complete = mt76_sw_scan_complete, .release_buffered_frames = mt76_release_buffered_frames, .get_txpower = mt76_get_txpower, + .channel_switch_beacon = mt7615_channel_switch_beacon, + .get_survey = mt76_get_survey, }; diff --git a/drivers/net/wireless/mediatek/mt76/mt7615/mcu.c b/drivers/net/wireless/mediatek/mt76/mt7615/mcu.c index cdad2c8dc297..275d5eaed3b7 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7615/mcu.c +++ b/drivers/net/wireless/mediatek/mt76/mt7615/mcu.c @@ -75,7 +75,7 @@ static int __mt7615_mcu_msg_send(struct mt7615_dev *dev, struct sk_buff *skb, txd = mcu_txd->txd; - val = FIELD_PREP(MT_TXD0_TX_BYTES, cpu_to_le16(skb->len)) | + val = FIELD_PREP(MT_TXD0_TX_BYTES, skb->len) | FIELD_PREP(MT_TXD0_P_IDX, MT_TX_PORT_IDX_MCU) | FIELD_PREP(MT_TXD0_Q_IDX, q_idx); txd[0] = cpu_to_le32(val); @@ -113,12 +113,38 @@ static int __mt7615_mcu_msg_send(struct mt7615_dev *dev, struct sk_buff *skb, } static int +mt7615_mcu_parse_response(struct mt7615_dev *dev, int cmd, + struct sk_buff *skb, int seq) +{ + struct mt7615_mcu_rxd *rxd = (struct mt7615_mcu_rxd *)skb->data; + int ret = 0; + + if (seq != rxd->seq) + return -EAGAIN; + + switch (cmd) { + case -MCU_CMD_PATCH_SEM_CONTROL: + skb_pull(skb, sizeof(*rxd) - 4); + ret = *skb->data; + break; + case MCU_EXT_CMD_GET_TEMP: + skb_pull(skb, sizeof(*rxd)); + ret = le32_to_cpu(*(__le32 *)skb->data); + break; + default: + break; + } + dev_kfree_skb(skb); + + return ret; +} + +static int mt7615_mcu_msg_send(struct mt76_dev *mdev, int cmd, const void *data, int len, bool wait_resp) { struct mt7615_dev *dev = container_of(mdev, struct mt7615_dev, mt76); unsigned long expires = jiffies + 10 * HZ; - struct mt7615_mcu_rxd *rxd; struct sk_buff *skb; int ret, seq; @@ -141,16 +167,9 @@ mt7615_mcu_msg_send(struct mt76_dev *mdev, int cmd, const void *data, break; } - rxd = (struct mt7615_mcu_rxd *)skb->data; - if (seq != rxd->seq) - continue; - - if (cmd == -MCU_CMD_PATCH_SEM_CONTROL) { - skb_pull(skb, sizeof(*rxd) - 4); - ret = *skb->data; - } - dev_kfree_skb(skb); - break; + ret = mt7615_mcu_parse_response(dev, cmd, skb, seq); + if (ret != -EAGAIN) + break; } out: @@ -159,6 +178,62 @@ out: return ret; } +static void +mt7615_mcu_csa_finish(void *priv, u8 *mac, struct ieee80211_vif *vif) +{ + if (vif->csa_active) + ieee80211_csa_finish(vif); +} + +static void +mt7615_mcu_rx_ext_event(struct mt7615_dev *dev, struct sk_buff *skb) +{ + struct mt7615_mcu_rxd *rxd = (struct mt7615_mcu_rxd *)skb->data; + + switch (rxd->ext_eid) { + case MCU_EXT_EVENT_RDD_REPORT: + ieee80211_radar_detected(dev->mt76.hw); + dev->hw_pattern++; + break; + case MCU_EXT_EVENT_CSA_NOTIFY: + ieee80211_iterate_active_interfaces_atomic(dev->mt76.hw, + IEEE80211_IFACE_ITER_RESUME_ALL, + mt7615_mcu_csa_finish, dev); + break; + default: + break; + } +} + +static void +mt7615_mcu_rx_unsolicited_event(struct mt7615_dev *dev, struct sk_buff *skb) +{ + struct mt7615_mcu_rxd *rxd = (struct mt7615_mcu_rxd *)skb->data; + + switch (rxd->eid) { + case MCU_EVENT_EXT: + mt7615_mcu_rx_ext_event(dev, skb); + break; + default: + break; + } + dev_kfree_skb(skb); +} + +void mt7615_mcu_rx_event(struct mt7615_dev *dev, struct sk_buff *skb) +{ + struct mt7615_mcu_rxd *rxd = (struct mt7615_mcu_rxd *)skb->data; + + if (rxd->ext_eid == MCU_EXT_EVENT_THERMAL_PROTECT || + rxd->ext_eid == MCU_EXT_EVENT_FW_LOG_2_HOST || + rxd->ext_eid == MCU_EXT_EVENT_ASSERT_DUMP || + rxd->ext_eid == MCU_EXT_EVENT_PS_SYNC || + !rxd->seq) + mt7615_mcu_rx_unsolicited_event(dev, skb); + else + mt76_mcu_rx_event(&dev->mt76, skb); +} + static int mt7615_mcu_init_download(struct mt7615_dev *dev, u32 addr, u32 len, u32 mode) { @@ -192,6 +267,7 @@ static int mt7615_mcu_send_firmware(struct mt7615_dev *dev, const void *data, data += cur_len; len -= cur_len; + mt76_queue_tx_cleanup(dev, MT_TXQ_FWDL, false); } return ret; @@ -257,9 +333,9 @@ static int mt7615_driver_own(struct mt7615_dev *dev) static int mt7615_load_patch(struct mt7615_dev *dev) { - const struct firmware *fw; - const struct mt7615_patch_hdr *hdr; const char *firmware = MT7615_ROM_PATCH; + const struct mt7615_patch_hdr *hdr; + const struct firmware *fw = NULL; int len, ret, sem; sem = mt7615_mcu_patch_sem_ctrl(dev, 1); @@ -275,7 +351,7 @@ static int mt7615_load_patch(struct mt7615_dev *dev) ret = request_firmware(&fw, firmware, dev->mt76.dev); if (ret) - return ret; + goto out; if (!fw || !fw->data || fw->size < sizeof(*hdr)) { dev_err(dev->mt76.dev, "Invalid firmware\n"); @@ -323,7 +399,7 @@ out: return ret; } -static u32 gen_dl_mode(u8 feature_set, bool is_cr4) +static u32 mt7615_mcu_gen_dl_mode(u8 feature_set, bool is_cr4) { u32 ret = 0; @@ -337,14 +413,45 @@ static u32 gen_dl_mode(u8 feature_set, bool is_cr4) return ret; } +static int +mt7615_mcu_send_ram_firmware(struct mt7615_dev *dev, + const struct mt7615_fw_trailer *hdr, + const u8 *data, bool is_cr4) +{ + int n_region = is_cr4 ? CR4_REGION_NUM : N9_REGION_NUM; + int err, i, offset = 0; + u32 len, addr, mode; + + for (i = 0; i < n_region; i++) { + mode = mt7615_mcu_gen_dl_mode(hdr[i].feature_set, is_cr4); + len = le32_to_cpu(hdr[i].len) + IMG_CRC_LEN; + addr = le32_to_cpu(hdr[i].addr); + + err = mt7615_mcu_init_download(dev, addr, len, mode); + if (err) { + dev_err(dev->mt76.dev, "Download request failed\n"); + return err; + } + + err = mt7615_mcu_send_firmware(dev, data + offset, len); + if (err) { + dev_err(dev->mt76.dev, "Failed to send firmware to device\n"); + return err; + } + + offset += len; + } + + return 0; +} + static int mt7615_load_ram(struct mt7615_dev *dev) { const struct firmware *fw; const struct mt7615_fw_trailer *hdr; const char *n9_firmware = MT7615_FIRMWARE_N9; const char *cr4_firmware = MT7615_FIRMWARE_CR4; - u32 n9_ilm_addr, offset; - int i, ret; + int ret; ret = request_firmware(&fw, n9_firmware, dev->mt76.dev); if (ret) @@ -362,31 +469,12 @@ static int mt7615_load_ram(struct mt7615_dev *dev) dev_info(dev->mt76.dev, "N9 Firmware Version: %.10s, Build Time: %.15s\n", hdr->fw_ver, hdr->build_date); - n9_ilm_addr = le32_to_cpu(hdr->addr); - - for (offset = 0, i = 0; i < N9_REGION_NUM; i++) { - u32 len, addr, mode; - - len = le32_to_cpu(hdr[i].len) + IMG_CRC_LEN; - addr = le32_to_cpu(hdr[i].addr); - mode = gen_dl_mode(hdr[i].feature_set, false); - - ret = mt7615_mcu_init_download(dev, addr, len, mode); - if (ret) { - dev_err(dev->mt76.dev, "Download request failed\n"); - goto out; - } - - ret = mt7615_mcu_send_firmware(dev, fw->data + offset, len); - if (ret) { - dev_err(dev->mt76.dev, "Failed to send firmware to device\n"); - goto out; - } - - offset += len; - } + ret = mt7615_mcu_send_ram_firmware(dev, hdr, fw->data, false); + if (ret) + goto out; - ret = mt7615_mcu_start_firmware(dev, n9_ilm_addr, FW_START_OVERRIDE); + ret = mt7615_mcu_start_firmware(dev, le32_to_cpu(hdr->addr), + FW_START_OVERRIDE); if (ret) { dev_err(dev->mt76.dev, "Failed to start N9 firmware\n"); goto out; @@ -410,27 +498,9 @@ static int mt7615_load_ram(struct mt7615_dev *dev) dev_info(dev->mt76.dev, "CR4 Firmware Version: %.10s, Build Time: %.15s\n", hdr->fw_ver, hdr->build_date); - for (offset = 0, i = 0; i < CR4_REGION_NUM; i++) { - u32 len, addr, mode; - - len = le32_to_cpu(hdr[i].len) + IMG_CRC_LEN; - addr = le32_to_cpu(hdr[i].addr); - mode = gen_dl_mode(hdr[i].feature_set, true); - - ret = mt7615_mcu_init_download(dev, addr, len, mode); - if (ret) { - dev_err(dev->mt76.dev, "Download request failed\n"); - goto out; - } - - ret = mt7615_mcu_send_firmware(dev, fw->data + offset, len); - if (ret) { - dev_err(dev->mt76.dev, "Failed to send firmware to device\n"); - goto out; - } - - offset += len; - } + ret = mt7615_mcu_send_ram_firmware(dev, hdr, fw->data, true); + if (ret) + goto out; ret = mt7615_mcu_start_firmware(dev, 0, FW_START_WORKING_PDA_CR4); if (ret) @@ -469,6 +539,8 @@ static int mt7615_load_firmware(struct mt7615_dev *dev) return -EIO; } + mt76_queue_tx_cleanup(dev, MT_TXQ_FWDL, false); + dev_dbg(dev->mt76.dev, "Firmware init done\n"); return 0; @@ -573,6 +645,8 @@ int mt7615_mcu_set_wmm(struct mt7615_dev *dev, u8 queue, #define WMM_CW_MIN_SET BIT(1) #define WMM_CW_MAX_SET BIT(2) #define WMM_TXOP_SET BIT(3) +#define WMM_PARAM_SET (WMM_AIFS_SET | WMM_CW_MIN_SET | \ + WMM_CW_MAX_SET | WMM_TXOP_SET) struct req_data { u8 number; u8 rsv[3]; @@ -585,19 +659,17 @@ int mt7615_mcu_set_wmm(struct mt7615_dev *dev, u8 queue, } __packed req = { .number = 1, .queue = queue, - .valid = WMM_AIFS_SET | WMM_TXOP_SET, + .valid = WMM_PARAM_SET, .aifs = params->aifs, + .cw_min = 5, + .cw_max = cpu_to_le16(10), .txop = cpu_to_le16(params->txop), }; - if (params->cw_min) { - req.valid |= WMM_CW_MIN_SET; - req.cw_min = params->cw_min; - } - if (params->cw_max) { - req.valid |= WMM_CW_MAX_SET; - req.cw_max = cpu_to_le16(params->cw_max); - } + if (params->cw_min) + req.cw_min = fls(params->cw_min); + if (params->cw_max) + req.cw_max = cpu_to_le16(fls(params->cw_max)); return __mt76_mcu_send_msg(&dev->mt76, MCU_EXT_CMD_EDCA_UPDATE, &req, sizeof(req), true); @@ -824,78 +896,6 @@ int mt7615_mcu_set_bss_info(struct mt7615_dev *dev, return ret; } -static enum mt7615_cipher_type -mt7615_get_key_info(struct ieee80211_key_conf *key, u8 *key_data) -{ - if (!key || key->keylen > 32) - return MT_CIPHER_NONE; - - memcpy(key_data, key->key, key->keylen); - - switch (key->cipher) { - case WLAN_CIPHER_SUITE_WEP40: - return MT_CIPHER_WEP40; - case WLAN_CIPHER_SUITE_WEP104: - return MT_CIPHER_WEP104; - case WLAN_CIPHER_SUITE_TKIP: - /* Rx/Tx MIC keys are swapped */ - memcpy(key_data + 16, key->key + 24, 8); - memcpy(key_data + 24, key->key + 16, 8); - return MT_CIPHER_TKIP; - case WLAN_CIPHER_SUITE_CCMP: - return MT_CIPHER_AES_CCMP; - case WLAN_CIPHER_SUITE_CCMP_256: - return MT_CIPHER_CCMP_256; - case WLAN_CIPHER_SUITE_GCMP: - return MT_CIPHER_GCMP; - case WLAN_CIPHER_SUITE_GCMP_256: - return MT_CIPHER_GCMP_256; - case WLAN_CIPHER_SUITE_SMS4: - return MT_CIPHER_WAPI; - default: - return MT_CIPHER_NONE; - } -} - -int mt7615_mcu_set_wtbl_key(struct mt7615_dev *dev, int wcid, - struct ieee80211_key_conf *key, - enum set_key_cmd cmd) -{ - struct { - struct wtbl_req_hdr hdr; - struct wtbl_sec_key key; - } req = { - .hdr = { - .wlan_idx = wcid, - .operation = WTBL_SET, - .tlv_num = cpu_to_le16(1), - }, - .key = { - .tag = cpu_to_le16(WTBL_SEC_KEY), - .len = cpu_to_le16(sizeof(struct wtbl_sec_key)), - .add = cmd, - }, - }; - - if (cmd == SET_KEY) { - u8 cipher; - - cipher = mt7615_get_key_info(key, req.key.key_material); - if (cipher == MT_CIPHER_NONE) - return -EOPNOTSUPP; - - req.key.rkv = 1; - req.key.cipher_id = cipher; - req.key.key_id = key->keyidx; - req.key.key_len = key->keylen; - } else { - req.key.key_len = sizeof(req.key.key_material); - } - - return __mt76_mcu_send_msg(&dev->mt76, MCU_EXT_CMD_WTBL_UPDATE, - &req, sizeof(req), true); -} - static int mt7615_mcu_add_wtbl_bmc(struct mt7615_dev *dev, struct mt7615_vif *mvif) @@ -1099,6 +1099,7 @@ int mt7615_mcu_set_bcn(struct mt7615_dev *dev, struct ieee80211_vif *vif, { struct mt7615_vif *mvif = (struct mt7615_vif *)vif->drv_priv; struct mt76_wcid *wcid = &dev->mt76.global_wcid; + struct ieee80211_mutable_offsets offs; struct req { u8 omac_idx; u8 enable; @@ -1119,13 +1120,10 @@ int mt7615_mcu_set_bcn(struct mt7615_dev *dev, struct ieee80211_vif *vif, .enable = en, .wlan_idx = wcid->idx, .band_idx = mvif->band_idx, - /* pky_type: 0 for bcn, 1 for tim */ - .pkt_type = 0, }; struct sk_buff *skb; - u16 tim_off; - skb = ieee80211_beacon_get_tim(mt76_hw(dev), vif, &tim_off, NULL); + skb = ieee80211_beacon_get_template(mt76_hw(dev), vif, &offs); if (!skb) return -EINVAL; @@ -1139,8 +1137,14 @@ int mt7615_mcu_set_bcn(struct mt7615_dev *dev, struct ieee80211_vif *vif, 0, NULL); memcpy(req.pkt + MT_TXD_SIZE, skb->data, skb->len); req.pkt_len = cpu_to_le16(MT_TXD_SIZE + skb->len); - req.tim_ie_pos = cpu_to_le16(MT_TXD_SIZE + tim_off); + req.tim_ie_pos = cpu_to_le16(MT_TXD_SIZE + offs.tim_offset); + if (offs.csa_counter_offs[0]) { + u16 csa_offs; + csa_offs = MT_TXD_SIZE + offs.csa_counter_offs[0] - 4; + req.csa_ie_pos = cpu_to_le16(csa_offs); + req.csa_cnt = skb->data[offs.csa_counter_offs[0]]; + } dev_kfree_skb(skb); return __mt76_mcu_send_msg(&dev->mt76, MCU_EXT_CMD_BCN_OFFLOAD, @@ -1213,9 +1217,62 @@ out: return ret; } +int mt7615_mcu_rdd_cmd(struct mt7615_dev *dev, + enum mt7615_rdd_cmd cmd, u8 index, + u8 rx_sel, u8 val) +{ + struct { + u8 ctrl; + u8 rdd_idx; + u8 rdd_rx_sel; + u8 val; + u8 rsv[4]; + } req = { + .ctrl = cmd, + .rdd_idx = index, + .rdd_rx_sel = rx_sel, + .val = val, + }; + + return __mt76_mcu_send_msg(&dev->mt76, MCU_EXT_CMD_SET_RDD_CTRL, + &req, sizeof(req), true); +} + +int mt7615_mcu_rdd_send_pattern(struct mt7615_dev *dev) +{ + struct { + u8 pulse_num; + u8 rsv[3]; + struct { + u32 start_time; + u16 width; + s16 power; + } pattern[32]; + } req = { + .pulse_num = dev->radar_pattern.n_pulses, + }; + u32 start_time = ktime_to_ms(ktime_get_boottime()); + int i; + + if (dev->radar_pattern.n_pulses > ARRAY_SIZE(req.pattern)) + return -EINVAL; + + /* TODO: add some noise here */ + for (i = 0; i < dev->radar_pattern.n_pulses; i++) { + req.pattern[i].width = dev->radar_pattern.width; + req.pattern[i].power = dev->radar_pattern.power; + req.pattern[i].start_time = start_time + + i * dev->radar_pattern.period; + } + + return __mt76_mcu_send_msg(&dev->mt76, MCU_EXT_CMD_SET_RDD_PATTERN, + &req, sizeof(req), false); +} + int mt7615_mcu_set_channel(struct mt7615_dev *dev) { - struct cfg80211_chan_def *chdef = &dev->mt76.chandef; + struct cfg80211_chan_def *chandef = &dev->mt76.chandef; + int freq1 = chandef->center_freq1, freq2 = chandef->center_freq2; struct { u8 control_chan; u8 center_chan; @@ -1234,17 +1291,20 @@ int mt7615_mcu_set_channel(struct mt7615_dev *dev) u8 rsv1[3]; u8 txpower_sku[53]; u8 rsv2[3]; - } req = {0}; + } req = { + .control_chan = chandef->chan->hw_value, + .center_chan = ieee80211_frequency_to_channel(freq1), + .tx_streams = (dev->mt76.chainmask >> 8) & 0xf, + .rx_streams_mask = dev->mt76.antenna_mask, + .center_chan2 = ieee80211_frequency_to_channel(freq2), + }; int ret; - req.control_chan = chdef->chan->hw_value; - req.center_chan = ieee80211_frequency_to_channel(chdef->center_freq1); - req.tx_streams = (dev->mt76.chainmask >> 8) & 0xf; - req.rx_streams_mask = dev->mt76.antenna_mask; - req.switch_reason = CH_SWITCH_NORMAL; - req.band_idx = 0; - req.center_chan2 = ieee80211_frequency_to_channel(chdef->center_freq2); - req.txpower_drop = 0; + if ((chandef->chan->flags & IEEE80211_CHAN_RADAR) && + chandef->chan->dfs_state != NL80211_DFS_AVAILABLE) + req.switch_reason = CH_SWITCH_DFS; + else + req.switch_reason = CH_SWITCH_NORMAL; switch (dev->mt76.chandef.width) { case NL80211_CHAN_WIDTH_40: @@ -1269,6 +1329,7 @@ int mt7615_mcu_set_channel(struct mt7615_dev *dev) case NL80211_CHAN_WIDTH_20: default: req.bw = CMD_CBW_20MHZ; + break; } memset(req.txpower_sku, 0x3f, 49); @@ -1533,92 +1594,15 @@ int mt7615_mcu_set_rx_ba(struct mt7615_dev *dev, &wtbl_req, sizeof(wtbl_req), true); } -void mt7615_mcu_set_rates(struct mt7615_dev *dev, struct mt7615_sta *sta, - struct ieee80211_tx_rate *probe_rate, - struct ieee80211_tx_rate *rates) +int mt7615_mcu_get_temperature(struct mt7615_dev *dev, int index) { - int wcid = sta->wcid.idx; - u32 addr = MT_WTBL_BASE + wcid * MT_WTBL_ENTRY_SIZE; - bool stbc = false; - int n_rates = sta->n_rates; - u8 bw, bw_prev, bw_idx = 0; - u16 val[4]; - u16 probe_val; - u32 w5, w27; - int i; - - if (!mt76_poll(dev, MT_WTBL_UPDATE, MT_WTBL_UPDATE_BUSY, 0, 5000)) - return; - - for (i = n_rates; i < 4; i++) - rates[i] = rates[n_rates - 1]; - - val[0] = mt7615_mac_tx_rate_val(dev, &rates[0], stbc, &bw); - bw_prev = bw; - - if (probe_rate) { - probe_val = mt7615_mac_tx_rate_val(dev, probe_rate, stbc, &bw); - if (bw) - bw_idx = 1; - else - bw_prev = 0; - } else { - probe_val = val[0]; - } - - val[1] = mt7615_mac_tx_rate_val(dev, &rates[1], stbc, &bw); - if (bw_prev) { - bw_idx = 3; - bw_prev = bw; - } - - val[2] = mt7615_mac_tx_rate_val(dev, &rates[2], stbc, &bw); - if (bw_prev) { - bw_idx = 5; - bw_prev = bw; - } - - val[3] = mt7615_mac_tx_rate_val(dev, &rates[3], stbc, &bw); - if (bw_prev) - bw_idx = 7; - - w27 = mt76_rr(dev, addr + 27 * 4); - w27 &= ~MT_WTBL_W27_CC_BW_SEL; - w27 |= FIELD_PREP(MT_WTBL_W27_CC_BW_SEL, bw); - - w5 = mt76_rr(dev, addr + 5 * 4); - w5 &= ~(MT_WTBL_W5_BW_CAP | MT_WTBL_W5_CHANGE_BW_RATE); - w5 |= FIELD_PREP(MT_WTBL_W5_BW_CAP, bw) | - FIELD_PREP(MT_WTBL_W5_CHANGE_BW_RATE, bw_idx ? bw_idx - 1 : 7); - - mt76_wr(dev, MT_WTBL_RIUCR0, w5); - - mt76_wr(dev, MT_WTBL_RIUCR1, - FIELD_PREP(MT_WTBL_RIUCR1_RATE0, probe_val) | - FIELD_PREP(MT_WTBL_RIUCR1_RATE1, val[0]) | - FIELD_PREP(MT_WTBL_RIUCR1_RATE2_LO, val[0])); - - mt76_wr(dev, MT_WTBL_RIUCR2, - FIELD_PREP(MT_WTBL_RIUCR2_RATE2_HI, val[0] >> 8) | - FIELD_PREP(MT_WTBL_RIUCR2_RATE3, val[1]) | - FIELD_PREP(MT_WTBL_RIUCR2_RATE4, val[1]) | - FIELD_PREP(MT_WTBL_RIUCR2_RATE5_LO, val[2])); - - mt76_wr(dev, MT_WTBL_RIUCR3, - FIELD_PREP(MT_WTBL_RIUCR3_RATE5_HI, val[2] >> 4) | - FIELD_PREP(MT_WTBL_RIUCR3_RATE6, val[2]) | - FIELD_PREP(MT_WTBL_RIUCR3_RATE7, val[3])); - - mt76_wr(dev, MT_WTBL_UPDATE, - FIELD_PREP(MT_WTBL_UPDATE_WLAN_IDX, wcid) | - MT_WTBL_UPDATE_RATE_UPDATE | - MT_WTBL_UPDATE_TX_COUNT_CLEAR); - - mt76_wr(dev, addr + 27 * 4, w27); - - if (!(sta->wcid.tx_info & MT_WCID_TX_INFO_SET)) - mt76_poll(dev, MT_WTBL_UPDATE, MT_WTBL_UPDATE_BUSY, 0, 5000); + struct { + u8 action; + u8 rsv[3]; + } req = { + .action = index, + }; - sta->rate_count = 2 * MT7615_RATE_RETRY * n_rates; - sta->wcid.tx_info |= MT_WCID_TX_INFO_SET; + return __mt76_mcu_send_msg(&dev->mt76, MCU_EXT_CMD_GET_TEMP, &req, + sizeof(req), true); } diff --git a/drivers/net/wireless/mediatek/mt76/mt7615/mcu.h b/drivers/net/wireless/mediatek/mt76/mt7615/mcu.h index f8b51ad25220..1fd7dffa6eef 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7615/mcu.h +++ b/drivers/net/wireless/mediatek/mt76/mt7615/mcu.h @@ -23,6 +23,28 @@ struct mt7615_mcu_txd { u32 reserved[5]; } __packed __aligned(4); +/* event table */ +enum { + MCU_EVENT_TARGET_ADDRESS_LEN = 0x01, + MCU_EVENT_FW_START = 0x01, + MCU_EVENT_GENERIC = 0x01, + MCU_EVENT_ACCESS_REG = 0x02, + MCU_EVENT_MT_PATCH_SEM = 0x04, + MCU_EVENT_CH_PRIVILEGE = 0x18, + MCU_EVENT_EXT = 0xed, + MCU_EVENT_RESTART_DL = 0xef, +}; + +/* ext event table */ +enum { + MCU_EXT_EVENT_PS_SYNC = 0x5, + MCU_EXT_EVENT_FW_LOG_2_HOST = 0x13, + MCU_EXT_EVENT_THERMAL_PROTECT = 0x22, + MCU_EXT_EVENT_ASSERT_DUMP = 0x23, + MCU_EXT_EVENT_RDD_REPORT = 0x3a, + MCU_EXT_EVENT_CSA_NOTIFY = 0x4f, +}; + struct mt7615_mcu_rxd { __le32 rxd[4]; @@ -76,11 +98,14 @@ enum { MCU_EXT_CMD_BSS_INFO_UPDATE = 0x26, MCU_EXT_CMD_EDCA_UPDATE = 0x27, MCU_EXT_CMD_DEV_INFO_UPDATE = 0x2A, + MCU_EXT_CMD_GET_TEMP = 0x2c, MCU_EXT_CMD_WTBL_UPDATE = 0x32, + MCU_EXT_CMD_SET_RDD_CTRL = 0x3a, MCU_EXT_CMD_PROTECT_CTRL = 0x3e, MCU_EXT_CMD_MAC_INIT_CTRL = 0x46, MCU_EXT_CMD_BCN_OFFLOAD = 0x49, MCU_EXT_CMD_SET_RX_PATH = 0x4e, + MCU_EXT_CMD_SET_RDD_PATTERN = 0x7d, }; enum { @@ -264,34 +289,6 @@ struct wtbl_hdr_trans { u8 rsv; } __packed; -enum mt7615_cipher_type { - MT_CIPHER_NONE, - MT_CIPHER_WEP40, - MT_CIPHER_TKIP, - MT_CIPHER_TKIP_NO_MIC, - MT_CIPHER_AES_CCMP, - MT_CIPHER_WEP104, - MT_CIPHER_BIP_CMAC_128, - MT_CIPHER_WEP128, - MT_CIPHER_WAPI, - MT_CIPHER_CCMP_256 = 10, - MT_CIPHER_GCMP, - MT_CIPHER_GCMP_256, -}; - -struct wtbl_sec_key { - __le16 tag; - __le16 len; - u8 add; /* 0: add, 1: remove */ - u8 rkv; - u8 ikv; - u8 cipher_id; - u8 key_id; - u8 key_len; - u8 rsv[2]; - u8 key_material[32]; -} __packed; - enum { MT_BA_TYPE_INVALID, MT_BA_TYPE_ORIGINATOR, @@ -375,7 +372,6 @@ struct wtbl_raw { sizeof(struct wtbl_vht) + \ sizeof(struct wtbl_tx_ps) + \ sizeof(struct wtbl_hdr_trans) + \ - sizeof(struct wtbl_sec_key) + \ sizeof(struct wtbl_ba) + \ sizeof(struct wtbl_bf) + \ sizeof(struct wtbl_smps) + \ diff --git a/drivers/net/wireless/mediatek/mt76/mt7615/mt7615.h b/drivers/net/wireless/mediatek/mt76/mt7615/mt7615.h index f02ffcffe637..cef3fd43cb00 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7615/mt7615.h +++ b/drivers/net/wireless/mediatek/mt76/mt7615/mt7615.h @@ -10,12 +10,13 @@ #include "regs.h" #define MT7615_MAX_INTERFACES 4 +#define MT7615_MAX_WMM_SETS 4 #define MT7615_WTBL_SIZE 128 #define MT7615_WTBL_RESERVED (MT7615_WTBL_SIZE - 1) #define MT7615_WTBL_STA (MT7615_WTBL_RESERVED - \ MT7615_MAX_INTERFACES) -#define MT7615_WATCHDOG_TIME 100 /* ms */ +#define MT7615_WATCHDOG_TIME (HZ / 10) #define MT7615_RATE_RETRY 2 #define MT7615_TX_RING_SIZE 1024 @@ -32,6 +33,9 @@ #define MT7615_EEPROM_SIZE 1024 #define MT7615_TOKEN_SIZE 4096 +#define MT_FRAC_SCALE 12 +#define MT_FRAC(val, div) (((val) << MT_FRAC_SCALE) / (div)) + struct mt7615_vif; struct mt7615_sta; @@ -42,12 +46,21 @@ enum mt7615_hw_txq_id { MT7615_TXQ_FWDL, }; +struct mt7615_rate_set { + struct ieee80211_tx_rate probe_rate; + struct ieee80211_tx_rate rates[4]; +}; + struct mt7615_sta { struct mt76_wcid wcid; /* must be first */ struct mt7615_vif *vif; - struct ieee80211_tx_rate rates[8]; + struct ieee80211_tx_rate rates[4]; + + struct mt7615_rate_set rateset[2]; + u32 rate_set_tsf; + u8 rate_count; u8 n_rates; @@ -68,6 +81,22 @@ struct mt7615_dev { u32 vif_mask; u32 omac_mask; + struct { + u8 n_pulses; + u32 period; + u16 width; + s16 power; + } radar_pattern; + u32 hw_pattern; + int dfs_state; + + int false_cca_ofdm, false_cca_cck; + unsigned long last_cca_adj; + u8 mac_work_count; + s8 ofdm_sensitivity; + s8 cck_sensitivity; + bool scs_en; + spinlock_t token_lock; struct idr token; }; @@ -97,6 +126,30 @@ enum { EXT_BSSID_END }; +enum { + MT_HW_RDD0, + MT_HW_RDD1, +}; + +enum { + MT_RX_SEL0, + MT_RX_SEL1, +}; + +enum mt7615_rdd_cmd { + RDD_STOP, + RDD_START, + RDD_DET_MODE, + RDD_DET_STOP, + RDD_CAC_START, + RDD_CAC_END, + RDD_NORMAL_START, + RDD_DISABLE_DFS_CAL, + RDD_PULSE_DBG, + RDD_READ_PULSE, + RDD_RESUME_BF, +}; + extern const struct ieee80211_ops mt7615_ops; extern struct pci_driver mt7615_pci_driver; @@ -115,10 +168,7 @@ int mt7615_mcu_set_dev_info(struct mt7615_dev *dev, struct ieee80211_vif *vif, bool enable); int mt7615_mcu_set_bss_info(struct mt7615_dev *dev, struct ieee80211_vif *vif, int en); -int mt7615_mcu_set_wtbl_key(struct mt7615_dev *dev, int wcid, - struct ieee80211_key_conf *key, - enum set_key_cmd cmd); -void mt7615_mcu_set_rates(struct mt7615_dev *dev, struct mt7615_sta *sta, +void mt7615_mac_set_rates(struct mt7615_dev *dev, struct mt7615_sta *sta, struct ieee80211_tx_rate *probe_rate, struct ieee80211_tx_rate *rates); int mt7615_mcu_wtbl_bmc(struct mt7615_dev *dev, struct ieee80211_vif *vif, @@ -144,6 +194,29 @@ int mt7615_mcu_set_rx_ba(struct mt7615_dev *dev, bool add); int mt7615_mcu_set_ht_cap(struct mt7615_dev *dev, struct ieee80211_vif *vif, struct ieee80211_sta *sta); +void mt7615_mcu_rx_event(struct mt7615_dev *dev, struct sk_buff *skb); +int mt7615_mcu_rdd_cmd(struct mt7615_dev *dev, + enum mt7615_rdd_cmd cmd, u8 index, + u8 rx_sel, u8 val); +int mt7615_dfs_start_radar_detector(struct mt7615_dev *dev); +int mt7615_dfs_stop_radar_detector(struct mt7615_dev *dev); +int mt7615_mcu_rdd_send_pattern(struct mt7615_dev *dev); + +static inline bool is_mt7622(struct mt76_dev *dev) +{ + return mt76_chip(dev) == 0x7622; +} + +static inline void mt7615_dfs_check_channel(struct mt7615_dev *dev) +{ + enum nl80211_chan_width width = dev->mt76.chandef.width; + u32 freq = dev->mt76.chandef.chan->center_freq; + struct ieee80211_hw *hw = mt76_hw(dev); + + if (hw->conf.chandef.chan->center_freq != freq || + hw->conf.chandef.width != width) + dev->dfs_state = -1; +} static inline void mt7615_irq_enable(struct mt7615_dev *dev, u32 mask) { @@ -155,9 +228,9 @@ static inline void mt7615_irq_disable(struct mt7615_dev *dev, u32 mask) mt76_set_irq_mask(&dev->mt76, MT_INT_MASK_CSR, mask, 0); } -u16 mt7615_mac_tx_rate_val(struct mt7615_dev *dev, - const struct ieee80211_tx_rate *rate, - bool stbc, u8 *bw); +void mt7615_update_channel(struct mt76_dev *mdev); +void mt7615_mac_cca_stats_reset(struct mt7615_dev *dev); +void mt7615_mac_set_scs(struct mt7615_dev *dev, bool enable); int mt7615_mac_write_txwi(struct mt7615_dev *dev, __le32 *txwi, struct sk_buff *skb, struct mt76_wcid *wcid, struct ieee80211_sta *sta, int pid, @@ -165,11 +238,15 @@ int mt7615_mac_write_txwi(struct mt7615_dev *dev, __le32 *txwi, int mt7615_mac_fill_rx(struct mt7615_dev *dev, struct sk_buff *skb); void mt7615_mac_add_txs(struct mt7615_dev *dev, void *data); void mt7615_mac_tx_free(struct mt7615_dev *dev, struct sk_buff *skb); +int mt7615_mac_wtbl_set_key(struct mt7615_dev *dev, struct mt76_wcid *wcid, + struct ieee80211_key_conf *key, + enum set_key_cmd cmd); int mt7615_mcu_set_eeprom(struct mt7615_dev *dev); int mt7615_mcu_init_mac(struct mt7615_dev *dev); int mt7615_mcu_set_rts_thresh(struct mt7615_dev *dev, u32 val); int mt7615_mcu_ctrl_pm_state(struct mt7615_dev *dev, int enter); +int mt7615_mcu_get_temperature(struct mt7615_dev *dev, int index); int mt7615_mcu_set_tx_power(struct mt7615_dev *dev); void mt7615_mcu_exit(struct mt7615_dev *dev); @@ -193,5 +270,9 @@ void mt7615_sta_remove(struct mt76_dev *mdev, struct ieee80211_vif *vif, void mt7615_mac_work(struct work_struct *work); void mt7615_txp_skb_unmap(struct mt76_dev *dev, struct mt76_txwi_cache *txwi); +int mt76_dfs_start_rdd(struct mt7615_dev *dev, bool force); +int mt7615_dfs_init_radar_detector(struct mt7615_dev *dev); + +int mt7615_init_debugfs(struct mt7615_dev *dev); #endif diff --git a/drivers/net/wireless/mediatek/mt76/mt7615/pci.c b/drivers/net/wireless/mediatek/mt76/mt7615/pci.c index 9e82cb53fd60..e250607e0a80 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7615/pci.c +++ b/drivers/net/wireless/mediatek/mt76/mt7615/pci.c @@ -81,6 +81,7 @@ static int mt7615_pci_probe(struct pci_dev *pdev, .sta_add = mt7615_sta_add, .sta_assoc = mt7615_sta_assoc, .sta_remove = mt7615_sta_remove, + .update_survey = mt7615_update_channel, }; struct mt7615_dev *dev; struct mt76_dev *mdev; diff --git a/drivers/net/wireless/mediatek/mt76/mt7615/regs.h b/drivers/net/wireless/mediatek/mt76/mt7615/regs.h index 70e5ace33cc3..b193814d5cf8 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7615/regs.h +++ b/drivers/net/wireless/mediatek/mt76/mt7615/regs.h @@ -71,6 +71,34 @@ #define MT_WF_PHY_WF2_RFCTRL0 MT_WF_PHY(0x1900) #define MT_WF_PHY_WF2_RFCTRL0_LPBCN_EN BIT(9) +#define MT_WF_PHY_R0_B0_PHYMUX_5 MT_WF_PHY(0x0614) + +#define MT_WF_PHY_R0_B0_PHYCTRL_STS0 MT_WF_PHY(0x020c) +#define MT_WF_PHYCTRL_STAT_PD_OFDM GENMASK(31, 16) +#define MT_WF_PHYCTRL_STAT_PD_CCK GENMASK(15, 0) + +#define MT_WF_PHY_R0_B0_PHYCTRL_STS5 MT_WF_PHY(0x0220) +#define MT_WF_PHYCTRL_STAT_MDRDY_OFDM GENMASK(31, 16) +#define MT_WF_PHYCTRL_STAT_MDRDY_CCK GENMASK(15, 0) + +#define MT_WF_PHY_B0_MIN_PRI_PWR MT_WF_PHY(0x229c) +#define MT_WF_PHY_B0_PD_OFDM_MASK GENMASK(28, 20) +#define MT_WF_PHY_B0_PD_OFDM(v) ((v) << 20) +#define MT_WF_PHY_B0_PD_BLK BIT(19) + +#define MT_WF_PHY_B1_MIN_PRI_PWR MT_WF_PHY(0x084) +#define MT_WF_PHY_B1_PD_OFDM_MASK GENMASK(24, 16) +#define MT_WF_PHY_B1_PD_OFDM(v) ((v) << 16) +#define MT_WF_PHY_B1_PD_BLK BIT(25) + +#define MT_WF_PHY_B0_RXTD_CCK_PD MT_WF_PHY(0x2310) +#define MT_WF_PHY_B0_PD_CCK_MASK GENMASK(8, 1) +#define MT_WF_PHY_B0_PD_CCK(v) ((v) << 1) + +#define MT_WF_PHY_B1_RXTD_CCK_PD MT_WF_PHY(0x2314) +#define MT_WF_PHY_B1_PD_CCK_MASK GENMASK(31, 24) +#define MT_WF_PHY_B1_PD_CCK(v) ((v) << 24) + #define MT_WF_CFG_BASE 0x20200 #define MT_WF_CFG(ofs) (MT_WF_CFG_BASE + (ofs)) @@ -97,12 +125,25 @@ MT_AGG_ARxCR_LIMIT_SHIFT(_n), \ MT_AGG_ARxCR_LIMIT_SHIFT(_n)) +#define MT_AGG_ACR0 MT_WF_AGG(0x070) +#define MT_AGG_ACR1 MT_WF_AGG(0x170) +#define MT_AGG_ACR_NO_BA_RULE BIT(0) +#define MT_AGG_ACR_NO_BA_AR_RULE BIT(1) +#define MT_AGG_ACR_PKT_TIME_EN BIT(2) +#define MT_AGG_ACR_CFEND_RATE GENMASK(15, 4) +#define MT_AGG_ACR_BAR_RATE GENMASK(31, 20) + #define MT_AGG_SCR MT_WF_AGG(0x0fc) #define MT_AGG_SCR_NLNAV_MID_PTEC_DIS BIT(3) #define MT_WF_TMAC_BASE 0x21000 #define MT_WF_TMAC(ofs) (MT_WF_TMAC_BASE + (ofs)) +#define MT_TMAC_TRCR0 MT_WF_TMAC(0x09c) +#define MT_TMAC_TRCR1 MT_WF_TMAC(0x070) +#define MT_TMAC_TRCR_CCA_SEL GENMASK(31, 30) +#define MT_TMAC_TRCR_SEC_CCA_SEL GENMASK(29, 28) + #define MT_TMAC_CTCR0 MT_WF_TMAC(0x0f4) #define MT_TMAC_CTCR0_INS_DDLMT_REFTIME GENMASK(5, 0) #define MT_TMAC_CTCR0_INS_DDLMT_DENSITY GENMASK(15, 12) @@ -148,8 +189,15 @@ #define MT_WTBL_OFF_BASE 0x23400 #define MT_WTBL_OFF(n) (MT_WTBL_OFF_BASE + (n)) +#define MT_WTBL_W0_KEY_IDX GENMASK(24, 23) +#define MT_WTBL_W0_RX_KEY_VALID BIT(26) +#define MT_WTBL_W0_RX_IK_VALID BIT(27) + +#define MT_WTBL_W2_KEY_TYPE GENMASK(7, 4) + #define MT_WTBL_UPDATE MT_WTBL_OFF(0x030) #define MT_WTBL_UPDATE_WLAN_IDX GENMASK(7, 0) +#define MT_WTBL_UPDATE_RXINFO_UPDATE BIT(11) #define MT_WTBL_UPDATE_RATE_UPDATE BIT(13) #define MT_WTBL_UPDATE_TX_COUNT_CLEAR BIT(14) #define MT_WTBL_UPDATE_BUSY BIT(31) @@ -157,6 +205,9 @@ #define MT_WTBL_ON_BASE 0x23000 #define MT_WTBL_ON(_n) (MT_WTBL_ON_BASE + (_n)) +#define MT_WTBL_RICR0 MT_WTBL_ON(0x010) +#define MT_WTBL_RICR1 MT_WTBL_ON(0x014) + #define MT_WTBL_RIUCR0 MT_WTBL_ON(0x020) #define MT_WTBL_RIUCR1 MT_WTBL_ON(0x024) @@ -181,8 +232,32 @@ #define MT_WTBL_W5_SHORT_GI_80 BIT(10) #define MT_WTBL_W5_SHORT_GI_160 BIT(11) #define MT_WTBL_W5_BW_CAP GENMASK(13, 12) +#define MT_WTBL_W5_MPDU_FAIL_COUNT GENMASK(25, 23) +#define MT_WTBL_W5_MPDU_OK_COUNT GENMASK(28, 26) +#define MT_WTBL_W5_RATE_IDX GENMASK(31, 29) + #define MT_WTBL_W27_CC_BW_SEL GENMASK(6, 5) +#define MT_LPON_BASE 0x24200 +#define MT_LPON(_n) (MT_LPON_BASE + (_n)) + +#define MT_LPON_T0CR MT_LPON(0x010) +#define MT_LPON_T0CR_MODE GENMASK(1, 0) + +#define MT_LPON_UTTR0 MT_LPON(0x018) +#define MT_LPON_UTTR1 MT_LPON(0x01c) + +#define MT_WF_MIB_BASE 0x24800 +#define MT_WF_MIB(ofs) (MT_WF_MIB_BASE + (ofs)) + +#define MT_MIB_M0_MISC_CR MT_WF_MIB(0x00c) +#define MT_MIB_MB_SDR0(n) MT_WF_MIB(0x100 + ((n) << 4)) +#define MT_MIB_RTS_RETRIES_COUNT_MASK GENMASK(31, 16) +#define MT_MIB_RTS_COUNT_MASK GENMASK(15, 0) + +#define MT_MIB_SDR16(n) MT_WF_MIB(0x48 + ((n) << 9)) +#define MT_MIB_BUSY_MASK GENMASK(23, 0) + #define MT_EFUSE_BASE 0x81070000 #define MT_EFUSE_BASE_CTRL 0x000 #define MT_EFUSE_BASE_CTRL_EMPTY BIT(30) diff --git a/drivers/net/wireless/mediatek/mt76/mt76x0/Kconfig b/drivers/net/wireless/mediatek/mt76/mt76x0/Kconfig index 209d8abc49d5..7c88ed8b8f1e 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x0/Kconfig +++ b/drivers/net/wireless/mediatek/mt76/mt76x0/Kconfig @@ -10,7 +10,11 @@ config MT76x0U depends on MAC80211 depends on USB help - This adds support for MT7610U-based wireless USB dongles. + This adds support for MT7610U-based wireless USB 2.0 dongles, + which comply with IEEE 802.11ac standards and support 1x1 + 433Mbps PHY rate. + + To compile this driver as a module, choose M here. config MT76x0E tristate "MediaTek MT76x0E (PCIe) support" @@ -18,4 +22,8 @@ config MT76x0E depends on MAC80211 depends on PCI help - This adds support for MT7610/MT7630-based wireless PCIe devices. + This adds support for MT7610/MT7630-based wireless PCIe devices, + which comply with IEEE 802.11ac standards and support 1x1 + 433Mbps PHY rate. + + To compile this driver as a module, choose M here. diff --git a/drivers/net/wireless/mediatek/mt76/mt76x0/main.c b/drivers/net/wireless/mediatek/mt76/mt76x0/main.c index d7bf7bc15e52..efb7ca93863d 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x0/main.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x0/main.c @@ -8,18 +8,16 @@ #include <linux/etherdevice.h> #include "mt76x0.h" -static int +static void mt76x0_set_channel(struct mt76x02_dev *dev, struct cfg80211_chan_def *chandef) { - int ret; - cancel_delayed_work_sync(&dev->cal_work); - dev->beacon_ops->pre_tbtt_enable(dev, false); + mt76x02_pre_tbtt_enable(dev, false); if (mt76_is_mmio(dev)) tasklet_disable(&dev->dfs_pd.dfs_tasklet); mt76_set_channel(&dev->mt76); - ret = mt76x0_phy_set_channel(dev, chandef); + mt76x0_phy_set_channel(dev, chandef); /* channel cycle counters read-and-clear */ mt76_rr(dev, MT_CH_IDLE); @@ -31,23 +29,20 @@ mt76x0_set_channel(struct mt76x02_dev *dev, struct cfg80211_chan_def *chandef) mt76x02_dfs_init_params(dev); tasklet_enable(&dev->dfs_pd.dfs_tasklet); } - dev->beacon_ops->pre_tbtt_enable(dev, true); + mt76x02_pre_tbtt_enable(dev, true); mt76_txq_schedule_all(&dev->mt76); - - return ret; } int mt76x0_config(struct ieee80211_hw *hw, u32 changed) { struct mt76x02_dev *dev = hw->priv; - int ret = 0; mutex_lock(&dev->mt76.mutex); if (changed & IEEE80211_CONF_CHANGE_CHANNEL) { ieee80211_stop_queues(hw); - ret = mt76x0_set_channel(dev, &hw->conf.chandef); + mt76x0_set_channel(dev, &hw->conf.chandef); ieee80211_wake_queues(hw); } @@ -69,6 +64,6 @@ int mt76x0_config(struct ieee80211_hw *hw, u32 changed) mutex_unlock(&dev->mt76.mutex); - return ret; + return 0; } EXPORT_SYMBOL_GPL(mt76x0_config); diff --git a/drivers/net/wireless/mediatek/mt76/mt76x0/mt76x0.h b/drivers/net/wireless/mediatek/mt76/mt76x0/mt76x0.h index 97e47cd2d744..26517e062bdb 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x0/mt76x0.h +++ b/drivers/net/wireless/mediatek/mt76/mt76x0/mt76x0.h @@ -54,7 +54,7 @@ int mt76x0_config(struct ieee80211_hw *hw, u32 changed); /* PHY */ void mt76x0_phy_init(struct mt76x02_dev *dev); int mt76x0_phy_wait_bbp_ready(struct mt76x02_dev *dev); -int mt76x0_phy_set_channel(struct mt76x02_dev *dev, +void mt76x0_phy_set_channel(struct mt76x02_dev *dev, struct cfg80211_chan_def *chandef); void mt76x0_phy_set_txpower(struct mt76x02_dev *dev); void mt76x0_phy_calibrate(struct mt76x02_dev *dev, bool power_on); diff --git a/drivers/net/wireless/mediatek/mt76/mt76x0/pci.c b/drivers/net/wireless/mediatek/mt76/mt76x0/pci.c index 6117e6ca08cb..7705e55aa3d1 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x0/pci.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x0/pci.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include <linux/kernel.h> @@ -93,7 +82,7 @@ static const struct ieee80211_ops mt76x0e_ops = { .sta_state = mt76_sta_state, .set_key = mt76x0e_set_key, .conf_tx = mt76x02_conf_tx, - .sw_scan_start = mt76x02_sw_scan, + .sw_scan_start = mt76_sw_scan, .sw_scan_complete = mt76x02_sw_scan_complete, .ampdu_action = mt76x02_ampdu_action, .sta_rate_tbl_update = mt76x02_sta_rate_tbl_update, diff --git a/drivers/net/wireless/mediatek/mt76/mt76x0/pci_mcu.c b/drivers/net/wireless/mediatek/mt76/mt76x0/pci_mcu.c index 490c1869f2c4..038187b390ce 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x0/pci_mcu.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x0/pci_mcu.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2018 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include <linux/kernel.h> #include <linux/firmware.h> diff --git a/drivers/net/wireless/mediatek/mt76/mt76x0/phy.c b/drivers/net/wireless/mediatek/mt76/mt76x0/phy.c index 1ecfc334ae79..711a352dfd5c 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x0/phy.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x0/phy.c @@ -109,7 +109,7 @@ mt76x0_rf_wr(struct mt76x02_dev *dev, u32 offset, u8 val) }; WARN_ON_ONCE(!test_bit(MT76_STATE_MCU_RUNNING, - &dev->mt76.state)); + &dev->mt76.state)); return mt76_wr_rp(dev, MT_MCU_MEMMAP_RF, &pair, 1); } else { return mt76x0_rf_csr_wr(dev, offset, val); @@ -127,7 +127,7 @@ static int mt76x0_rf_rr(struct mt76x02_dev *dev, u32 offset) }; WARN_ON_ONCE(!test_bit(MT76_STATE_MCU_RUNNING, - &dev->mt76.state)); + &dev->mt76.state)); ret = mt76_rd_rp(dev, MT_MCU_MEMMAP_RF, &pair, 1); val = pair.value; } else { @@ -230,7 +230,8 @@ mt76x0_phy_set_band(struct mt76x02_dev *dev, enum nl80211_band band) } static void -mt76x0_phy_set_chan_rf_params(struct mt76x02_dev *dev, u8 channel, u16 rf_bw_band) +mt76x0_phy_set_chan_rf_params(struct mt76x02_dev *dev, u8 channel, + u16 rf_bw_band) { const struct mt76x0_freq_item *freq_item; u16 rf_band = rf_bw_band & 0xff00; @@ -252,9 +253,9 @@ mt76x0_phy_set_chan_rf_params(struct mt76x02_dev *dev, u8 channel, u16 rf_bw_ban rf_band = mt76x0_frequency_plan[i].band; if (b_sdm) - freq_item = &(mt76x0_sdm_frequency_plan[i]); + freq_item = &mt76x0_sdm_frequency_plan[i]; else - freq_item = &(mt76x0_frequency_plan[i]); + freq_item = &mt76x0_frequency_plan[i]; mt76x0_rf_wr(dev, MT_RF(0, 37), freq_item->pllR37); mt76x0_rf_wr(dev, MT_RF(0, 36), freq_item->pllR36); @@ -359,11 +360,12 @@ mt76x0_phy_set_chan_rf_params(struct mt76x02_dev *dev, u8 channel, u16 rf_bw_ban band = (rf_band & RF_G_BAND) ? NL80211_BAND_2GHZ : NL80211_BAND_5GHZ; if (mt76x02_ext_pa_enabled(dev, band)) { - /* - MT_RF_MISC (offset: 0x0518) - [2]1'b1: enable external A band PA, 1'b0: disable external A band PA - [3]1'b1: enable external G band PA, 1'b0: disable external G band PA - */ + /* MT_RF_MISC (offset: 0x0518) + * [2]1'b1: enable external A band PA + * 1'b0: disable external A band PA + * [3]1'b1: enable external G band PA + * 1'b0: disable external G band PA + */ if (rf_band & RF_A_BAND) mt76_set(dev, MT_RF_MISC, BIT(2)); else @@ -385,7 +387,9 @@ mt76x0_phy_set_chan_rf_params(struct mt76x02_dev *dev, u8 channel, u16 rf_bw_ban mt76_wr(dev, MT_TX_ALC_CFG_1, mac_reg); } else { mt76_wr(dev, MT_TX0_RF_GAIN_ATTEN, 0x686A7800); - /* Set Atten mode = 0 For Ext A band, Disable Tx Inc dcoc Cal. */ + /* Set Atten mode = 0 + * For Ext A band, Disable Tx Inc dcoc Cal. + */ mac_reg = mt76_rr(dev, MT_TX_ALC_CFG_1); mac_reg &= 0x890400FF; mt76_wr(dev, MT_TX_ALC_CFG_1, mac_reg); @@ -490,7 +494,7 @@ mt76x0_phy_bbp_set_bw(struct mt76x02_dev *dev, enum nl80211_chan_width width) case NL80211_CHAN_WIDTH_160: case NL80211_CHAN_WIDTH_5: /* TODO error */ - return ; + return; } mt76x02_mcu_function_select(dev, BW_SETTING, bw); @@ -905,8 +909,8 @@ void mt76x0_phy_calibrate(struct mt76x02_dev *dev, bool power_on) } EXPORT_SYMBOL_GPL(mt76x0_phy_calibrate); -int mt76x0_phy_set_channel(struct mt76x02_dev *dev, - struct cfg80211_chan_def *chandef) +void mt76x0_phy_set_channel(struct mt76x02_dev *dev, + struct cfg80211_chan_def *chandef) { u32 ext_cca_chan[4] = { [0] = FIELD_PREP(MT_EXT_CCA_CFG_CCA0, 0) | @@ -940,7 +944,6 @@ int mt76x0_phy_set_channel(struct mt76x02_dev *dev, freq1 = chandef->center_freq1; channel = chandef->chan->hw_value; rf_bw_band = (channel <= 14) ? RF_G_BAND : RF_A_BAND; - dev->mt76.chandef = *chandef; switch (chandef->width) { case NL80211_CHAN_WIDTH_40: @@ -1001,7 +1004,7 @@ int mt76x0_phy_set_channel(struct mt76x02_dev *dev, /* enable vco */ mt76x0_rf_set(dev, MT_RF(0, 4), BIT(7)); if (scan) - return 0; + return; mt76x02_init_agc_gain(dev); mt76x0_phy_calibrate(dev, false); @@ -1009,8 +1012,6 @@ int mt76x0_phy_set_channel(struct mt76x02_dev *dev, ieee80211_queue_delayed_work(dev->mt76.hw, &dev->cal_work, MT_CALIBRATE_INTERVAL); - - return 0; } static void mt76x0_phy_temp_sensor(struct mt76x02_dev *dev) @@ -1074,7 +1075,7 @@ mt76x0_phy_update_channel_gain(struct mt76x02_dev *dev) dev->cal.avg_rssi_all = -75; low_gain = (dev->cal.avg_rssi_all > mt76x02_get_rssi_gain_thresh(dev)) + - (dev->cal.avg_rssi_all > mt76x02_get_low_rssi_gain_thresh(dev)); + (dev->cal.avg_rssi_all > mt76x02_get_low_rssi_gain_thresh(dev)); gain_change = dev->cal.low_gain < 0 || (dev->cal.low_gain & 2) ^ (low_gain & 2); @@ -1169,7 +1170,8 @@ static void mt76x0_phy_rf_init(struct mt76x02_dev *dev) if (item->bw_band == RF_BW_20) mt76x0_rf_wr(dev, item->rf_bank_reg, item->value); - else if (((RF_G_BAND | RF_BW_20) & item->bw_band) == (RF_G_BAND | RF_BW_20)) + else if (((RF_G_BAND | RF_BW_20) & item->bw_band) == + (RF_G_BAND | RF_BW_20)) mt76x0_rf_wr(dev, item->rf_bank_reg, item->value); } @@ -1181,10 +1183,9 @@ static void mt76x0_phy_rf_init(struct mt76x02_dev *dev) } } - /* - Frequency calibration - E1: B0.R22<6:0>: xo_cxo<6:0> - E2: B0.R21<0>: xo_cxo<0>, B0.R22<7:0>: xo_cxo<8:1> + /* Frequency calibration + * E1: B0.R22<6:0>: xo_cxo<6:0> + * E2: B0.R21<0>: xo_cxo<0>, B0.R22<7:0>: xo_cxo<8:1> */ mt76x0_rf_wr(dev, MT_RF(0, 22), min_t(u8, dev->cal.rx.freq_offset, 0xbf)); diff --git a/drivers/net/wireless/mediatek/mt76/mt76x0/phy.h b/drivers/net/wireless/mediatek/mt76/mt76x0/phy.h index b4b2ca747699..441d6559d4fd 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x0/phy.h +++ b/drivers/net/wireless/mediatek/mt76/mt76x0/phy.h @@ -6,8 +6,8 @@ #ifndef _MT76X0_PHY_H_ #define _MT76X0_PHY_H_ -#define RF_G_BAND 0x0100 -#define RF_A_BAND 0x0200 +#define RF_G_BAND 0x0100 +#define RF_A_BAND 0x0200 #define RF_A_BAND_LB 0x0400 #define RF_A_BAND_MB 0x0800 #define RF_A_BAND_HB 0x1000 @@ -18,9 +18,9 @@ #define RF_BW_10 4 #define RF_BW_80 8 -#define MT_RF(bank, reg) ((bank) << 16 | (reg)) -#define MT_RF_BANK(offset) (offset >> 16) -#define MT_RF_REG(offset) (offset & 0xff) +#define MT_RF(bank, reg) ((bank) << 16 | (reg)) +#define MT_RF_BANK(offset) ((offset) >> 16) +#define MT_RF_REG(offset) ((offset) & 0xff) #define MT_RF_VCO_BP_CLOSE_LOOP BIT(3) #define MT_RF_VCO_BP_CLOSE_LOOP_MASK GENMASK(3, 0) diff --git a/drivers/net/wireless/mediatek/mt76/mt76x0/usb.c b/drivers/net/wireless/mediatek/mt76/mt76x0/usb.c index 645f4d15fb61..00a445d27599 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x0/usb.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x0/usb.c @@ -32,10 +32,13 @@ static struct usb_device_id mt76x0_device_table[] = { { USB_DEVICE(0x20f4, 0x806b) }, /* TRENDnet TEW-806UBH */ { USB_DEVICE(0x7392, 0xc711) }, /* Devolo Wifi ac Stick */ { USB_DEVICE(0x0df6, 0x0079) }, /* Sitecom Europe B.V. ac Stick */ - { USB_DEVICE(0x2357, 0x0105), - .driver_info = 1, }, /* TP-LINK Archer T1U */ - { USB_DEVICE_AND_INTERFACE_INFO(0x0E8D, 0x7630, 0xff, 0x2, 0xff)}, /* MT7630U */ - { USB_DEVICE_AND_INTERFACE_INFO(0x0E8D, 0x7650, 0xff, 0x2, 0xff)}, /* MT7650U */ + { USB_DEVICE(0x2357, 0x0123) }, /* TP-LINK T2UHP */ + /* TP-LINK Archer T1U */ + { USB_DEVICE(0x2357, 0x0105), .driver_info = 1, }, + /* MT7630U */ + { USB_DEVICE_AND_INTERFACE_INFO(0x0E8D, 0x7630, 0xff, 0x2, 0xff)}, + /* MT7650U */ + { USB_DEVICE_AND_INTERFACE_INFO(0x0E8D, 0x7650, 0xff, 0x2, 0xff)}, { 0, } }; @@ -125,13 +128,14 @@ static const struct ieee80211_ops mt76x0u_ops = { .sta_state = mt76_sta_state, .set_key = mt76x02_set_key, .conf_tx = mt76x02_conf_tx, - .sw_scan_start = mt76x02_sw_scan, + .sw_scan_start = mt76_sw_scan, .sw_scan_complete = mt76x02_sw_scan_complete, .ampdu_action = mt76x02_ampdu_action, .sta_rate_tbl_update = mt76x02_sta_rate_tbl_update, .set_rts_threshold = mt76x02_set_rts_threshold, .wake_tx_queue = mt76_wake_tx_queue, .get_txpower = mt76_get_txpower, + .get_survey = mt76_get_survey, .set_tim = mt76_set_tim, .release_buffered_frames = mt76_release_buffered_frames, }; @@ -161,6 +165,13 @@ static int mt76x0u_init_hardware(struct mt76x02_dev *dev, bool reset) FIELD_PREP(MT_TXOP_TRUN_EN, 0x3f) | FIELD_PREP(MT_TXOP_EXT_CCA_DLY, 0x58)); + mt76_wr(dev, MT_CH_TIME_CFG, + MT_CH_TIME_CFG_TIMER_EN | + MT_CH_TIME_CFG_TX_AS_BUSY | + MT_CH_TIME_CFG_RX_AS_BUSY | + MT_CH_TIME_CFG_NAV_AS_BUSY | + MT_CH_TIME_CFG_EIFS_AS_BUSY); + return 0; } @@ -200,6 +211,7 @@ static int mt76x0u_probe(struct usb_interface *usb_intf, const struct usb_device_id *id) { static const struct mt76_driver_ops drv_ops = { + .update_survey = mt76x02_update_channel, .tx_prepare_skb = mt76x02u_tx_prepare_skb, .tx_complete_skb = mt76x02u_tx_complete_skb, .tx_status_data = mt76x02_tx_status_data, @@ -236,7 +248,7 @@ static int mt76x0u_probe(struct usb_interface *usb_intf, if (ret) goto err; - /* Disable the HW, otherwise MCU fail to initalize on hot reboot */ + /* Disable the HW, otherwise MCU fail to initialize on hot reboot */ mt76x0_chip_onoff(dev, false, false); if (!mt76x02_wait_for_mac(mdev)) { @@ -274,9 +286,9 @@ err: static void mt76x0_disconnect(struct usb_interface *usb_intf) { struct mt76x02_dev *dev = usb_get_intfdata(usb_intf); - bool initalized = test_bit(MT76_STATE_INITIALIZED, &dev->mt76.state); + bool initialized = test_bit(MT76_STATE_INITIALIZED, &dev->mt76.state); - if (!initalized) + if (!initialized) return; ieee80211_unregister_hw(dev->mt76.hw); diff --git a/drivers/net/wireless/mediatek/mt76/mt76x0/usb_mcu.c b/drivers/net/wireless/mediatek/mt76/mt76x0/usb_mcu.c index 4a282761ca58..888a930a5e08 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x0/usb_mcu.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x0/usb_mcu.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2018 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include <linux/kernel.h> #include <linux/firmware.h> diff --git a/drivers/net/wireless/mediatek/mt76/mt76x02.h b/drivers/net/wireless/mediatek/mt76/mt76x02.h index f7fd53a1738a..e858bba8c8ff 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x02.h +++ b/drivers/net/wireless/mediatek/mt76/mt76x02.h @@ -1,18 +1,7 @@ +/* SPDX-License-Identifier: ISC */ /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> * Copyright (C) 2018 Stanislaw Gruszka <stf_xl@wp.pl> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef __MT76x02_H @@ -71,10 +60,15 @@ struct mt76x02_calibration { struct mt76x02_beacon_ops { unsigned int nslots; unsigned int slot_size; - void (*pre_tbtt_enable) (struct mt76x02_dev *, bool); - void (*beacon_enable) (struct mt76x02_dev *, bool); + void (*pre_tbtt_enable)(struct mt76x02_dev *dev, bool en); + void (*beacon_enable)(struct mt76x02_dev *dev, bool en); }; +#define mt76x02_beacon_enable(dev, enable) \ + (dev)->beacon_ops->beacon_enable(dev, enable) +#define mt76x02_pre_tbtt_enable(dev, enable) \ + (dev)->beacon_ops->pre_tbtt_enable(dev, enable) + struct mt76x02_dev { struct mt76_dev mt76; /* must be first */ @@ -137,8 +131,8 @@ extern struct ieee80211_rate mt76x02_rates[12]; void mt76x02_init_device(struct mt76x02_dev *dev); void mt76x02_configure_filter(struct ieee80211_hw *hw, - unsigned int changed_flags, - unsigned int *total_flags, u64 multicast); + unsigned int changed_flags, + unsigned int *total_flags, u64 multicast); int mt76x02_sta_add(struct mt76_dev *mdev, struct ieee80211_vif *vif, struct ieee80211_sta *sta); void mt76x02_sta_remove(struct mt76_dev *mdev, struct ieee80211_vif *vif, @@ -147,20 +141,20 @@ void mt76x02_sta_remove(struct mt76_dev *mdev, struct ieee80211_vif *vif, void mt76x02_config_mac_addr_list(struct mt76x02_dev *dev); int mt76x02_add_interface(struct ieee80211_hw *hw, - struct ieee80211_vif *vif); + struct ieee80211_vif *vif); void mt76x02_remove_interface(struct ieee80211_hw *hw, - struct ieee80211_vif *vif); + struct ieee80211_vif *vif); int mt76x02_ampdu_action(struct ieee80211_hw *hw, struct ieee80211_vif *vif, - struct ieee80211_ampdu_params *params); + struct ieee80211_ampdu_params *params); int mt76x02_set_key(struct ieee80211_hw *hw, enum set_key_cmd cmd, - struct ieee80211_vif *vif, struct ieee80211_sta *sta, - struct ieee80211_key_conf *key); + struct ieee80211_vif *vif, struct ieee80211_sta *sta, + struct ieee80211_key_conf *key); int mt76x02_conf_tx(struct ieee80211_hw *hw, struct ieee80211_vif *vif, - u16 queue, const struct ieee80211_tx_queue_params *params); + u16 queue, const struct ieee80211_tx_queue_params *params); void mt76x02_sta_rate_tbl_update(struct ieee80211_hw *hw, - struct ieee80211_vif *vif, - struct ieee80211_sta *sta); + struct ieee80211_vif *vif, + struct ieee80211_sta *sta); s8 mt76x02_tx_get_max_txpwr_adj(struct mt76x02_dev *dev, const struct ieee80211_tx_rate *rate); s8 mt76x02_tx_get_txpwr_adj(struct mt76x02_dev *dev, s8 txpwr, @@ -183,8 +177,6 @@ int mt76x02_tx_prepare_skb(struct mt76_dev *mdev, void *txwi, enum mt76_txq_id qid, struct mt76_wcid *wcid, struct ieee80211_sta *sta, struct mt76_tx_info *tx_info); -void mt76x02_sw_scan(struct ieee80211_hw *hw, struct ieee80211_vif *vif, - const u8 *mac); void mt76x02_sw_scan_complete(struct ieee80211_hw *hw, struct ieee80211_vif *vif); void mt76x02_sta_ps(struct mt76_dev *dev, struct ieee80211_sta *sta, bool ps); @@ -197,6 +189,7 @@ struct beacon_bc_data { struct sk_buff_head q; struct sk_buff *tail[8]; }; + void mt76x02_init_beacon_config(struct mt76x02_dev *dev); void mt76x02e_init_beacon_config(struct mt76x02_dev *dev); void mt76x02_resync_beacon_timer(struct mt76x02_dev *dev); diff --git a/drivers/net/wireless/mediatek/mt76/mt76x02_beacon.c b/drivers/net/wireless/mediatek/mt76/mt76x02_beacon.c index d61c686e08de..92305bd31aa1 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x02_beacon.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x02_beacon.c @@ -1,19 +1,8 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> * Copyright (C) 2018 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> * Copyright (C) 2018 Stanislaw Gruszka <stf_xl@wp.pl> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include "mt76x02.h" @@ -115,53 +104,41 @@ int mt76x02_mac_set_beacon(struct mt76x02_dev *dev, u8 vif_idx, } EXPORT_SYMBOL_GPL(mt76x02_mac_set_beacon); -static void -__mt76x02_mac_set_beacon_enable(struct mt76x02_dev *dev, u8 vif_idx, - bool val, struct sk_buff *skb) -{ - u8 old_mask = dev->mt76.beacon_mask; - bool en; - u32 reg; - - if (val) { - dev->mt76.beacon_mask |= BIT(vif_idx); - if (skb) - mt76x02_mac_set_beacon(dev, vif_idx, skb); - } else { - dev->mt76.beacon_mask &= ~BIT(vif_idx); - mt76x02_mac_set_beacon(dev, vif_idx, NULL); - } - - if (!!old_mask == !!dev->mt76.beacon_mask) - return; - - en = dev->mt76.beacon_mask; - - reg = MT_BEACON_TIME_CFG_BEACON_TX | - MT_BEACON_TIME_CFG_TBTT_EN | - MT_BEACON_TIME_CFG_TIMER_EN; - mt76_rmw(dev, MT_BEACON_TIME_CFG, reg, reg * en); - - dev->beacon_ops->beacon_enable(dev, en); -} - void mt76x02_mac_set_beacon_enable(struct mt76x02_dev *dev, - struct ieee80211_vif *vif, bool val) + struct ieee80211_vif *vif, bool enable) { - u8 vif_idx = ((struct mt76x02_vif *)vif->drv_priv)->idx; - struct sk_buff *skb = NULL; - - dev->beacon_ops->pre_tbtt_enable(dev, false); + struct mt76x02_vif *mvif = (struct mt76x02_vif *)vif->drv_priv; + u8 old_mask = dev->mt76.beacon_mask; - if (mt76_is_usb(dev)) - skb = ieee80211_beacon_get(mt76_hw(dev), vif); + mt76x02_pre_tbtt_enable(dev, false); if (!dev->mt76.beacon_mask) dev->tbtt_count = 0; - __mt76x02_mac_set_beacon_enable(dev, vif_idx, val, skb); + if (enable) { + dev->mt76.beacon_mask |= BIT(mvif->idx); + } else { + dev->mt76.beacon_mask &= ~BIT(mvif->idx); + mt76x02_mac_set_beacon(dev, mvif->idx, NULL); + } - dev->beacon_ops->pre_tbtt_enable(dev, true); + if (!!old_mask == !!dev->mt76.beacon_mask) + goto out; + + if (dev->mt76.beacon_mask) + mt76_set(dev, MT_BEACON_TIME_CFG, + MT_BEACON_TIME_CFG_BEACON_TX | + MT_BEACON_TIME_CFG_TBTT_EN | + MT_BEACON_TIME_CFG_TIMER_EN); + else + mt76_clear(dev, MT_BEACON_TIME_CFG, + MT_BEACON_TIME_CFG_BEACON_TX | + MT_BEACON_TIME_CFG_TBTT_EN | + MT_BEACON_TIME_CFG_TIMER_EN); + mt76x02_beacon_enable(dev, !!dev->mt76.beacon_mask); + +out: + mt76x02_pre_tbtt_enable(dev, true); } void @@ -237,7 +214,8 @@ mt76x02_add_buffered_bc(void *priv, u8 *mac, struct ieee80211_vif *vif) } void -mt76x02_enqueue_buffered_bc(struct mt76x02_dev *dev, struct beacon_bc_data *data, +mt76x02_enqueue_buffered_bc(struct mt76x02_dev *dev, + struct beacon_bc_data *data, int max_nframes) { int i, nframes; @@ -281,4 +259,3 @@ void mt76x02_init_beacon_config(struct mt76x02_dev *dev) } EXPORT_SYMBOL_GPL(mt76x02_init_beacon_config); - diff --git a/drivers/net/wireless/mediatek/mt76/mt76x02_debugfs.c b/drivers/net/wireless/mediatek/mt76/mt76x02_debugfs.c index 1b1e424ccbb2..0cb2a7b35fe5 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x02_debugfs.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x02_debugfs.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include <linux/debugfs.h> diff --git a/drivers/net/wireless/mediatek/mt76/mt76x02_dfs.c b/drivers/net/wireless/mediatek/mt76/mt76x02_dfs.c index 50e9b310e496..5dec33ed8527 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x02_dfs.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x02_dfs.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2016 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include "mt76x02.h" diff --git a/drivers/net/wireless/mediatek/mt76/mt76x02_dfs.h b/drivers/net/wireless/mediatek/mt76/mt76x02_dfs.h index 0408613b45a4..491010a32247 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x02_dfs.h +++ b/drivers/net/wireless/mediatek/mt76/mt76x02_dfs.h @@ -1,17 +1,6 @@ +/* SPDX-License-Identifier: ISC */ /* * Copyright (C) 2016 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef __MT76x02_DFS_H diff --git a/drivers/net/wireless/mediatek/mt76/mt76x02_dma.h b/drivers/net/wireless/mediatek/mt76/mt76x02_dma.h index 6394010a565f..4aff4f8e87b6 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x02_dma.h +++ b/drivers/net/wireless/mediatek/mt76/mt76x02_dma.h @@ -1,17 +1,6 @@ +/* SPDX-License-Identifier: ISC */ /* * Copyright (C) 2018 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef __MT76x02_DMA_H diff --git a/drivers/net/wireless/mediatek/mt76/mt76x02_eeprom.c b/drivers/net/wireless/mediatek/mt76/mt76x02_eeprom.c index 07f0496d828a..c54c50fd639a 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x02_eeprom.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x02_eeprom.c @@ -1,18 +1,7 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> * Copyright (C) 2018 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include <asm/unaligned.h> diff --git a/drivers/net/wireless/mediatek/mt76/mt76x02_eeprom.h b/drivers/net/wireless/mediatek/mt76/mt76x02_eeprom.h index 0ba536de3d6e..99941a4700f3 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x02_eeprom.h +++ b/drivers/net/wireless/mediatek/mt76/mt76x02_eeprom.h @@ -1,18 +1,7 @@ +/* SPDX-License-Identifier: ISC */ /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> * Copyright (C) 2018 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef __MT76x02_EEPROM_H diff --git a/drivers/net/wireless/mediatek/mt76/mt76x02_mac.c b/drivers/net/wireless/mediatek/mt76/mt76x02_mac.c index 82bafb5ac326..abacb4ea7179 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x02_mac.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x02_mac.c @@ -1,18 +1,7 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> * Copyright (C) 2018 Stanislaw Gruszka <stf_xl@wp.pl> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include "mt76x02.h" @@ -92,7 +81,6 @@ void mt76x02_mac_wcid_sync_pn(struct mt76x02_dev *dev, u8 idx, atomic64_set(&key->tx_pn, pn); } - int mt76x02_mac_wcid_set_key(struct mt76x02_dev *dev, u8 idx, struct ieee80211_key_conf *key) { @@ -267,7 +255,7 @@ bool mt76x02_mac_load_tx_status(struct mt76x02_dev *dev, static int mt76x02_mac_process_tx_rate(struct ieee80211_tx_rate *txrate, u16 rate, - enum nl80211_band band) + enum nl80211_band band) { u8 idx = FIELD_GET(MT_RXWI_RATE_INDEX, rate); @@ -343,7 +331,7 @@ void mt76x02_mac_write_txwi(struct mt76x02_dev *dev, struct mt76x02_txwi *txwi, ieee80211_has_protected(hdr->frame_control)) { wcid = NULL; ieee80211_get_tx_rates(info->control.vif, sta, skb, - info->control.rates, 1); + info->control.rates, 1); } if (wcid) @@ -353,6 +341,7 @@ void mt76x02_mac_write_txwi(struct mt76x02_dev *dev, struct mt76x02_txwi *txwi, if (wcid && wcid->sw_iv && key) { u64 pn = atomic64_inc_return(&key->tx_pn); + ccmp_pn[0] = pn; ccmp_pn[1] = pn >> 8; ccmp_pn[2] = 0; @@ -445,8 +434,8 @@ mt76x02_tx_rate_fallback(struct ieee80211_tx_rate *rates, int idx, int phy) case MT_PHY_TYPE_HT: /* MCS 8 falls back to MCS 0 */ if (rates[0].idx == 8) { - rates[1].idx = 0; - break; + rates[1].idx = 0; + break; } /* fall through */ default: @@ -568,9 +557,9 @@ void mt76x02_send_tx_status(struct mt76x02_dev *dev, u32 stat_val, stat_cache; stat_val = stat->rate; - stat_val |= ((u32) stat->retry) << 16; + stat_val |= ((u32)stat->retry) << 16; stat_cache = msta->status.rate; - stat_cache |= ((u32) msta->status.retry) << 16; + stat_cache |= ((u32)msta->status.retry) << 16; if (*update == 0 && stat_val == stat_cache && stat->wcid == msta->status.wcid && msta->n_frames < 32) { @@ -718,7 +707,7 @@ mt76x02_mac_get_rssi(struct mt76x02_dev *dev, s8 rssi, int chain) int mt76x02_mac_process_rx(struct mt76x02_dev *dev, struct sk_buff *skb, void *rxi) { - struct mt76_rx_status *status = (struct mt76_rx_status *) skb->cb; + struct mt76_rx_status *status = (struct mt76_rx_status *)skb->cb; struct mt76x02_rxwi *rxwi = rxi; struct mt76x02_sta *sta; u32 rxinfo = le32_to_cpu(rxwi->rxinfo); diff --git a/drivers/net/wireless/mediatek/mt76/mt76x02_mac.h b/drivers/net/wireless/mediatek/mt76/mt76x02_mac.h index cb39da79527a..efa4ef945e35 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x02_mac.h +++ b/drivers/net/wireless/mediatek/mt76/mt76x02_mac.h @@ -1,18 +1,7 @@ +/* SPDX-License-Identifier: ISC */ /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> * Copyright (C) 2018 Stanislaw Gruszka <stf_xl@wp.pl> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef __MT76X02_MAC_H @@ -207,7 +196,7 @@ void mt76x02_mac_set_bssid(struct mt76x02_dev *dev, u8 idx, const u8 *addr); int mt76x02_mac_set_beacon(struct mt76x02_dev *dev, u8 vif_idx, struct sk_buff *skb); void mt76x02_mac_set_beacon_enable(struct mt76x02_dev *dev, - struct ieee80211_vif *vif, bool val); + struct ieee80211_vif *vif, bool enable); void mt76x02_edcca_init(struct mt76x02_dev *dev); #endif diff --git a/drivers/net/wireless/mediatek/mt76/mt76x02_mcu.c b/drivers/net/wireless/mediatek/mt76/mt76x02_mcu.c index 6501b853b65c..4be7a24097cc 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x02_mcu.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x02_mcu.c @@ -1,18 +1,7 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> * Copyright (C) 2018 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include <linux/kernel.h> @@ -65,7 +54,7 @@ int mt76x02_mcu_msg_send(struct mt76_dev *mdev, int cmd, const void *data, break; } - rxfce = (u32 *) skb->cb; + rxfce = (u32 *)skb->cb; if (seq == FIELD_GET(MT_RX_FCE_INFO_CMD_SEQ, *rxfce)) check_seq = true; @@ -86,11 +75,11 @@ int mt76x02_mcu_function_select(struct mt76x02_dev *dev, enum mcu_function func, u32 val) { struct { - __le32 id; - __le32 value; + __le32 id; + __le32 value; } __packed __aligned(4) msg = { - .id = cpu_to_le32(func), - .value = cpu_to_le32(val), + .id = cpu_to_le32(func), + .value = cpu_to_le32(val), }; bool wait = false; @@ -111,7 +100,8 @@ int mt76x02_mcu_set_radio_state(struct mt76x02_dev *dev, bool on) .level = cpu_to_le32(0), }; - return mt76_mcu_send_msg(dev, CMD_POWER_SAVING_OP, &msg, sizeof(msg), false); + return mt76_mcu_send_msg(dev, CMD_POWER_SAVING_OP, &msg, sizeof(msg), + false); } EXPORT_SYMBOL_GPL(mt76x02_mcu_set_radio_state); diff --git a/drivers/net/wireless/mediatek/mt76/mt76x02_mcu.h b/drivers/net/wireless/mediatek/mt76/mt76x02_mcu.h index a7b0d3e5df1d..c81a9655c4c9 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x02_mcu.h +++ b/drivers/net/wireless/mediatek/mt76/mt76x02_mcu.h @@ -1,17 +1,6 @@ +/* SPDX-License-Identifier: ISC */ /* * Copyright (C) 2018 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef __MT76x02_MCU_H diff --git a/drivers/net/wireless/mediatek/mt76/mt76x02_mmio.c b/drivers/net/wireless/mediatek/mt76/mt76x02_mmio.c index 467b28379870..dc773070481d 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x02_mmio.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x02_mmio.c @@ -1,18 +1,7 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> * Copyright (C) 2018 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include <linux/kernel.h> @@ -97,7 +86,8 @@ void mt76x02e_init_beacon_config(struct mt76x02_dev *dev) dev->beacon_ops = &beacon_ops; /* Fire a pre-TBTT interrupt 8 ms before TBTT */ - mt76_rmw_field(dev, MT_INT_TIMER_CFG, MT_INT_TIMER_CFG_PRE_TBTT, 8 << 4); + mt76_rmw_field(dev, MT_INT_TIMER_CFG, MT_INT_TIMER_CFG_PRE_TBTT, + 8 << 4); mt76_rmw_field(dev, MT_INT_TIMER_CFG, MT_INT_TIMER_CFG_GP_TIMER, MT_DFS_GP_INTERVAL); mt76_wr(dev, MT_INT_TIMER_EN, 0); @@ -201,7 +191,7 @@ int mt76x02_dma_init(struct mt76x02_dev *dev) return -ENOMEM; tasklet_init(&dev->mt76.tx_tasklet, mt76x02_tx_tasklet, - (unsigned long) dev); + (unsigned long)dev); tasklet_init(&dev->mt76.pre_tbtt_tasklet, mt76x02_pre_tbtt_tasklet, (unsigned long)dev); @@ -395,12 +385,12 @@ static void mt76x02_key_sync(struct ieee80211_hw *hw, struct ieee80211_vif *vif, struct mt76_wcid *wcid; if (!sta) - return; + return; - wcid = (struct mt76_wcid *) sta->drv_priv; + wcid = (struct mt76_wcid *)sta->drv_priv; if (wcid->hw_key_idx != key->keyidx || wcid->sw_iv) - return; + return; mt76x02_mac_wcid_sync_pn(dev, wcid->idx, key); } diff --git a/drivers/net/wireless/mediatek/mt76/mt76x02_phy.c b/drivers/net/wireless/mediatek/mt76/mt76x02_phy.c index a54b63a96eae..d7334267b530 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x02_phy.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x02_phy.c @@ -1,18 +1,7 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> * Copyright (C) 2018 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include <linux/kernel.h> @@ -183,7 +172,8 @@ bool mt76x02_phy_adjust_vga_gain(struct mt76x02_dev *dev) bool ret = false; u32 false_cca; - false_cca = FIELD_GET(MT_RX_STAT_1_CCA_ERRORS, mt76_rr(dev, MT_RX_STAT_1)); + false_cca = FIELD_GET(MT_RX_STAT_1_CCA_ERRORS, + mt76_rr(dev, MT_RX_STAT_1)); dev->cal.false_cca = false_cca; if (false_cca > 800 && dev->cal.agc_gain_adjust < limit) { dev->cal.agc_gain_adjust += 2; diff --git a/drivers/net/wireless/mediatek/mt76/mt76x02_phy.h b/drivers/net/wireless/mediatek/mt76/mt76x02_phy.h index d2971db06f13..fc2e41006a0d 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x02_phy.h +++ b/drivers/net/wireless/mediatek/mt76/mt76x02_phy.h @@ -1,17 +1,6 @@ +/* SPDX-License-Identifier: ISC */ /* * Copyright (C) 2018 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef __MT76x02_PHY_H diff --git a/drivers/net/wireless/mediatek/mt76/mt76x02_regs.h b/drivers/net/wireless/mediatek/mt76/mt76x02_regs.h index ea7833964ec0..21c0f351fa09 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x02_regs.h +++ b/drivers/net/wireless/mediatek/mt76/mt76x02_regs.h @@ -1,17 +1,6 @@ +/* SPDX-License-Identifier: ISC */ /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef __MT76X02_REGS_H @@ -19,8 +8,8 @@ #define MT_ASIC_VERSION 0x0000 -#define MT76XX_REV_E3 0x22 -#define MT76XX_REV_E4 0x33 +#define MT76XX_REV_E3 0x22 +#define MT76XX_REV_E4 0x33 #define MT_CMB_CTRL 0x0020 #define MT_CMB_CTRL_XTAL_RDY BIT(22) @@ -120,7 +109,7 @@ #define MT_INT_RX_DONE(_n) BIT(_n) #define MT_INT_RX_DONE_ALL GENMASK(1, 0) #define MT_INT_TX_DONE_ALL GENMASK(13, 4) -#define MT_INT_TX_DONE(_n) BIT(_n + 4) +#define MT_INT_TX_DONE(_n) BIT((_n) + 4) #define MT_INT_RX_COHERENT BIT(16) #define MT_INT_TX_COHERENT BIT(17) #define MT_INT_ANY_COHERENT BIT(18) @@ -149,21 +138,21 @@ #define MT_WPDMA_DELAY_INT_CFG 0x0210 -#define MT_WMM_AIFSN 0x0214 +#define MT_WMM_AIFSN 0x0214 #define MT_WMM_AIFSN_MASK GENMASK(3, 0) #define MT_WMM_AIFSN_SHIFT(_n) ((_n) * 4) -#define MT_WMM_CWMIN 0x0218 +#define MT_WMM_CWMIN 0x0218 #define MT_WMM_CWMIN_MASK GENMASK(3, 0) #define MT_WMM_CWMIN_SHIFT(_n) ((_n) * 4) -#define MT_WMM_CWMAX 0x021c +#define MT_WMM_CWMAX 0x021c #define MT_WMM_CWMAX_MASK GENMASK(3, 0) #define MT_WMM_CWMAX_SHIFT(_n) ((_n) * 4) #define MT_WMM_TXOP_BASE 0x0220 #define MT_WMM_TXOP(_n) (MT_WMM_TXOP_BASE + (((_n) / 2) << 2)) -#define MT_WMM_TXOP_SHIFT(_n) ((_n & 1) * 16) +#define MT_WMM_TXOP_SHIFT(_n) (((_n) & 1) * 16) #define MT_WMM_TXOP_MASK GENMASK(15, 0) #define MT_WMM_CTRL 0x0230 /* MT76x0 */ @@ -607,7 +596,7 @@ #define MT_TX_AGG_CNT(_id) ((_id) < 8 ? \ MT_TX_AGG_CNT_BASE0 + ((_id) << 2) : \ - MT_TX_AGG_CNT_BASE1 + ((_id - 8) << 2)) + MT_TX_AGG_CNT_BASE1 + (((_id) - 8) << 2)) #define MT_TX_STAT_FIFO_EXT 0x1798 #define MT_TX_STAT_FIFO_EXT_RETRY GENMASK(7, 0) @@ -680,17 +669,17 @@ #define MT_SKEY_BASE_0 0xac00 #define MT_SKEY_BASE_1 0xb400 -#define MT_SKEY_0(_bss, _idx) (MT_SKEY_BASE_0 + (4 * (_bss) + _idx) * 32) -#define MT_SKEY_1(_bss, _idx) (MT_SKEY_BASE_1 + (4 * ((_bss) & 7) + _idx) * 32) -#define MT_SKEY(_bss, _idx) ((_bss & 8) ? MT_SKEY_1(_bss, _idx) : MT_SKEY_0(_bss, _idx)) +#define MT_SKEY_0(_bss, _idx) (MT_SKEY_BASE_0 + (4 * (_bss) + (_idx)) * 32) +#define MT_SKEY_1(_bss, _idx) (MT_SKEY_BASE_1 + (4 * ((_bss) & 7) + (_idx)) * 32) +#define MT_SKEY(_bss, _idx) (((_bss) & 8) ? MT_SKEY_1(_bss, _idx) : MT_SKEY_0(_bss, _idx)) #define MT_SKEY_MODE_BASE_0 0xb000 #define MT_SKEY_MODE_BASE_1 0xb3f0 -#define MT_SKEY_MODE_0(_bss) (MT_SKEY_MODE_BASE_0 + ((_bss / 2) << 2)) +#define MT_SKEY_MODE_0(_bss) (MT_SKEY_MODE_BASE_0 + (((_bss) / 2) << 2)) #define MT_SKEY_MODE_1(_bss) (MT_SKEY_MODE_BASE_1 + ((((_bss) & 7) / 2) << 2)) -#define MT_SKEY_MODE(_bss) ((_bss & 8) ? MT_SKEY_MODE_1(_bss) : MT_SKEY_MODE_0(_bss)) +#define MT_SKEY_MODE(_bss) (((_bss) & 8) ? MT_SKEY_MODE_1(_bss) : MT_SKEY_MODE_0(_bss)) #define MT_SKEY_MODE_MASK GENMASK(3, 0) -#define MT_SKEY_MODE_SHIFT(_bss, _idx) (4 * ((_idx) + 4 * (_bss & 1))) +#define MT_SKEY_MODE_SHIFT(_bss, _idx) (4 * ((_idx) + 4 * ((_bss) & 1))) #define MT_BEACON_BASE 0xc000 diff --git a/drivers/net/wireless/mediatek/mt76/mt76x02_trace.c b/drivers/net/wireless/mediatek/mt76/mt76x02_trace.c index 5b42d2c87937..a812c3a1e258 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x02_trace.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x02_trace.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include <linux/module.h> diff --git a/drivers/net/wireless/mediatek/mt76/mt76x02_trace.h b/drivers/net/wireless/mediatek/mt76/mt76x02_trace.h index 713f12d3c8de..61ecaf0fe065 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x02_trace.h +++ b/drivers/net/wireless/mediatek/mt76/mt76x02_trace.h @@ -1,17 +1,6 @@ +/* SPDX-License-Identifier: ISC */ /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #if !defined(__MT76x02_TRACE_H) || defined(TRACE_HEADER_MULTI_READ) @@ -25,7 +14,8 @@ #define MAXNAME 32 #define DEV_ENTRY __array(char, wiphy_name, 32) -#define DEV_ASSIGN strlcpy(__entry->wiphy_name, wiphy_name(mt76_hw(dev)->wiphy), MAXNAME) +#define DEV_ASSIGN strlcpy(__entry->wiphy_name, \ + wiphy_name(mt76_hw(dev)->wiphy), MAXNAME) #define DEV_PR_FMT "%s" #define DEV_PR_ARG __entry->wiphy_name diff --git a/drivers/net/wireless/mediatek/mt76/mt76x02_txrx.c b/drivers/net/wireless/mediatek/mt76/mt76x02_txrx.c index 04118f08debc..f27aade34c1e 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x02_txrx.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x02_txrx.c @@ -1,18 +1,7 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> * Copyright (C) 2018 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include <linux/kernel.h> diff --git a/drivers/net/wireless/mediatek/mt76/mt76x02_usb.h b/drivers/net/wireless/mediatek/mt76/mt76x02_usb.h index 7b53f9e57f29..98329debc033 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x02_usb.h +++ b/drivers/net/wireless/mediatek/mt76/mt76x02_usb.h @@ -1,17 +1,6 @@ +/* SPDX-License-Identifier: ISC */ /* * Copyright (C) 2018 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef __MT76x02_USB_H diff --git a/drivers/net/wireless/mediatek/mt76/mt76x02_usb_core.c b/drivers/net/wireless/mediatek/mt76/mt76x02_usb_core.c index e4332d5a5757..78dfc1e7f27b 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x02_usb_core.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x02_usb_core.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2018 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include "mt76x02_usb.h" diff --git a/drivers/net/wireless/mediatek/mt76/mt76x02_usb_mcu.c b/drivers/net/wireless/mediatek/mt76/mt76x02_usb_mcu.c index 0cb8751321a1..a993cd7e9948 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x02_usb_mcu.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x02_usb_mcu.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2018 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include <linux/module.h> diff --git a/drivers/net/wireless/mediatek/mt76/mt76x02_util.c b/drivers/net/wireless/mediatek/mt76/mt76x02_util.c index ad5323447ed4..aec73a0295e8 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x02_util.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x02_util.c @@ -1,18 +1,7 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2018 Stanislaw Gruszka <stf_xl@wp.pl> * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include <linux/module.h> @@ -21,14 +10,14 @@ #define CCK_RATE(_idx, _rate) { \ .bitrate = _rate, \ .flags = IEEE80211_RATE_SHORT_PREAMBLE, \ - .hw_value = (MT_PHY_TYPE_CCK << 8) | _idx, \ - .hw_value_short = (MT_PHY_TYPE_CCK << 8) | (8 + _idx), \ + .hw_value = (MT_PHY_TYPE_CCK << 8) | (_idx), \ + .hw_value_short = (MT_PHY_TYPE_CCK << 8) | (8 + (_idx)), \ } #define OFDM_RATE(_idx, _rate) { \ .bitrate = _rate, \ - .hw_value = (MT_PHY_TYPE_OFDM << 8) | _idx, \ - .hw_value_short = (MT_PHY_TYPE_OFDM << 8) | _idx, \ + .hw_value = (MT_PHY_TYPE_OFDM << 8) | (_idx), \ + .hw_value_short = (MT_PHY_TYPE_OFDM << 8) | (_idx), \ } struct ieee80211_rate mt76x02_rates[] = { @@ -61,6 +50,20 @@ static const struct ieee80211_iface_limit mt76x02_if_limits[] = { }, }; +static const struct ieee80211_iface_limit mt76x02u_if_limits[] = { + { + .max = 1, + .types = BIT(NL80211_IFTYPE_ADHOC) + }, { + .max = 2, + .types = BIT(NL80211_IFTYPE_STATION) | +#ifdef CONFIG_MAC80211_MESH + BIT(NL80211_IFTYPE_MESH_POINT) | +#endif + BIT(NL80211_IFTYPE_AP) + }, +}; + static const struct ieee80211_iface_combination mt76x02_if_comb[] = { { .limits = mt76x02_if_limits, @@ -75,6 +78,16 @@ static const struct ieee80211_iface_combination mt76x02_if_comb[] = { } }; +static const struct ieee80211_iface_combination mt76x02u_if_comb[] = { + { + .limits = mt76x02u_if_limits, + .n_limits = ARRAY_SIZE(mt76x02u_if_limits), + .max_interfaces = 2, + .num_different_channels = 1, + .beacon_int_infra_match = true, + } +}; + static void mt76x02_led_set_config(struct mt76_dev *mdev, u8 delay_on, u8 delay_off) @@ -151,6 +164,8 @@ void mt76x02_init_device(struct mt76x02_dev *dev) if (mt76_is_usb(dev)) { hw->extra_tx_headroom += sizeof(struct mt76x02_txwi) + MT_DMA_HDR_LEN; + wiphy->iface_combinations = mt76x02u_if_comb; + wiphy->n_iface_combinations = ARRAY_SIZE(mt76x02u_if_comb); } else { INIT_DELAYED_WORK(&dev->wdt_work, mt76x02_wdt_work); @@ -281,7 +296,7 @@ mt76x02_vif_init(struct mt76x02_dev *dev, struct ieee80211_vif *vif, mvif->idx = idx; mvif->group_wcid.idx = MT_VIF_WCID(idx); mvif->group_wcid.hw_key_idx = -1; - mtxq = (struct mt76_txq *) vif->txq->drv_priv; + mtxq = (struct mt76_txq *)vif->txq->drv_priv; mtxq->wcid = &mvif->group_wcid; mt76_txq_init(&dev->mt76, vif->txq); @@ -345,10 +360,10 @@ int mt76x02_ampdu_action(struct ieee80211_hw *hw, struct ieee80211_vif *vif, enum ieee80211_ampdu_mlme_action action = params->action; struct ieee80211_sta *sta = params->sta; struct mt76x02_dev *dev = hw->priv; - struct mt76x02_sta *msta = (struct mt76x02_sta *) sta->drv_priv; + struct mt76x02_sta *msta = (struct mt76x02_sta *)sta->drv_priv; struct ieee80211_txq *txq = sta->txq[params->tid]; u16 tid = params->tid; - u16 *ssn = ¶ms->ssn; + u16 ssn = params->ssn; struct mt76_txq *mtxq; if (!txq) @@ -359,7 +374,7 @@ int mt76x02_ampdu_action(struct ieee80211_hw *hw, struct ieee80211_vif *vif, switch (action) { case IEEE80211_AMPDU_RX_START: mt76_rx_aggr_start(&dev->mt76, &msta->wcid, tid, - *ssn, params->buf_size); + ssn, params->buf_size); mt76_set(dev, MT_WCID_ADDR(msta->wcid.idx) + 4, BIT(16 + tid)); break; case IEEE80211_AMPDU_RX_STOP: @@ -375,10 +390,9 @@ int mt76x02_ampdu_action(struct ieee80211_hw *hw, struct ieee80211_vif *vif, case IEEE80211_AMPDU_TX_STOP_FLUSH: case IEEE80211_AMPDU_TX_STOP_FLUSH_CONT: mtxq->aggr = false; - ieee80211_send_bar(vif, sta->addr, tid, mtxq->agg_ssn); break; case IEEE80211_AMPDU_TX_START: - mtxq->agg_ssn = IEEE80211_SN_TO_SEQ(*ssn); + mtxq->agg_ssn = IEEE80211_SN_TO_SEQ(ssn); ieee80211_start_tx_ba_cb_irqsafe(vif, sta->addr, tid); break; case IEEE80211_AMPDU_TX_STOP_CONT: @@ -434,7 +448,7 @@ int mt76x02_set_key(struct ieee80211_hw *hw, enum set_key_cmd cmd, !(key->flags & IEEE80211_KEY_FLAG_PAIRWISE)) return -EOPNOTSUPP; - msta = sta ? (struct mt76x02_sta *) sta->drv_priv : NULL; + msta = sta ? (struct mt76x02_sta *)sta->drv_priv : NULL; wcid = msta ? &msta->wcid : &mvif->group_wcid; if (cmd == SET_KEY) { @@ -558,11 +572,11 @@ int mt76x02_set_rts_threshold(struct ieee80211_hw *hw, u32 val) EXPORT_SYMBOL_GPL(mt76x02_set_rts_threshold); void mt76x02_sta_rate_tbl_update(struct ieee80211_hw *hw, - struct ieee80211_vif *vif, - struct ieee80211_sta *sta) + struct ieee80211_vif *vif, + struct ieee80211_sta *sta) { struct mt76x02_dev *dev = hw->priv; - struct mt76x02_sta *msta = (struct mt76x02_sta *) sta->drv_priv; + struct mt76x02_sta *msta = (struct mt76x02_sta *)sta->drv_priv; struct ieee80211_sta_rates *rates = rcu_dereference(sta->rates); struct ieee80211_tx_rate rate = {}; @@ -588,15 +602,6 @@ void mt76x02_remove_hdr_pad(struct sk_buff *skb, int len) } EXPORT_SYMBOL_GPL(mt76x02_remove_hdr_pad); -void mt76x02_sw_scan(struct ieee80211_hw *hw, struct ieee80211_vif *vif, - const u8 *mac) -{ - struct mt76x02_dev *dev = hw->priv; - - set_bit(MT76_SCANNING, &dev->mt76.state); -} -EXPORT_SYMBOL_GPL(mt76x02_sw_scan); - void mt76x02_sw_scan_complete(struct ieee80211_hw *hw, struct ieee80211_vif *vif) { diff --git a/drivers/net/wireless/mediatek/mt76/mt76x2/Kconfig b/drivers/net/wireless/mediatek/mt76/mt76x2/Kconfig index 1f69908f8373..5fd4973e32df 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x2/Kconfig +++ b/drivers/net/wireless/mediatek/mt76/mt76x2/Kconfig @@ -8,8 +8,12 @@ config MT76x2E select MT76x2_COMMON depends on MAC80211 depends on PCI - ---help--- - This adds support for MT7612/MT7602/MT7662-based wireless PCIe devices. + help + This adds support for MT7612/MT7602/MT7662-based wireless PCIe + devices, which comply with IEEE 802.11ac standards and support + 2SS to 866Mbit/s PHY rate. + + To compile this driver as a module, choose M here. config MT76x2U tristate "MediaTek MT76x2U (USB) support" @@ -18,4 +22,8 @@ config MT76x2U depends on MAC80211 depends on USB help - This adds support for MT7612U-based wireless USB dongles. + This adds support for MT7612U-based wireless USB 3.0 dongles, + which comply with IEEE 802.11ac standards and support 2SS to + 866Mbit/s PHY rate. + + To compile this driver as a module, choose M here. diff --git a/drivers/net/wireless/mediatek/mt76/mt76x2/eeprom.c b/drivers/net/wireless/mediatek/mt76/mt76x2/eeprom.c index 6f6998561d9d..9f91556c7f38 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x2/eeprom.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x2/eeprom.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include <linux/module.h> @@ -33,7 +22,7 @@ mt76x2_eeprom_get_macaddr(struct mt76x02_dev *dev) static bool mt76x2_has_cal_free_data(struct mt76x02_dev *dev, u8 *efuse) { - u16 *efuse_w = (u16 *) efuse; + u16 *efuse_w = (u16 *)efuse; if (efuse_w[MT_EE_NIC_CONF_0] != 0) return false; @@ -372,7 +361,8 @@ mt76x2_get_power_info_2g(struct mt76x02_dev *dev, t->chain[chain].tssi_slope = data[0]; t->chain[chain].tssi_offset = data[1]; t->chain[chain].target_power = data[2]; - t->chain[chain].delta = mt76x02_sign_extend_optional(data[delta_idx], 7); + t->chain[chain].delta = + mt76x02_sign_extend_optional(data[delta_idx], 7); val = mt76x02_eeprom_get(dev, MT_EE_RF_2G_TSSI_OFF_TXPOWER); t->target_power = val >> 8; @@ -381,7 +371,7 @@ mt76x2_get_power_info_2g(struct mt76x02_dev *dev, static void mt76x2_get_power_info_5g(struct mt76x02_dev *dev, struct mt76x2_tx_power_info *t, - struct ieee80211_channel *chan, + struct ieee80211_channel *chan, int chain, int offset) { int channel = chan->hw_value; @@ -423,7 +413,8 @@ mt76x2_get_power_info_5g(struct mt76x02_dev *dev, t->chain[chain].tssi_slope = data[0]; t->chain[chain].tssi_offset = data[1]; t->chain[chain].target_power = data[2]; - t->chain[chain].delta = mt76x02_sign_extend_optional(data[delta_idx], 7); + t->chain[chain].delta = + mt76x02_sign_extend_optional(data[delta_idx], 7); val = mt76x02_eeprom_get(dev, MT_EE_RF_2G_RX_HIGH_GAIN); t->target_power = val & 0xff; diff --git a/drivers/net/wireless/mediatek/mt76/mt76x2/eeprom.h b/drivers/net/wireless/mediatek/mt76/mt76x2/eeprom.h index 9e735524d367..4dcf6518cb0d 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x2/eeprom.h +++ b/drivers/net/wireless/mediatek/mt76/mt76x2/eeprom.h @@ -1,17 +1,6 @@ +/* SPDX-License-Identifier: ISC */ /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef __MT76x2_EEPROM_H diff --git a/drivers/net/wireless/mediatek/mt76/mt76x2/init.c b/drivers/net/wireless/mediatek/mt76/mt76x2/init.c index 97c3543eed8a..79e583eb066b 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x2/init.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x2/init.c @@ -1,18 +1,7 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> * Copyright (C) 2018 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include "mt76x2.h" diff --git a/drivers/net/wireless/mediatek/mt76/mt76x2/mac.c b/drivers/net/wireless/mediatek/mt76/mt76x2/mac.c index e99d4c9bd428..e08740ca3d0c 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x2/mac.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x2/mac.c @@ -1,18 +1,7 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> * Copyright (C) 2018 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include "mt76x2.h" diff --git a/drivers/net/wireless/mediatek/mt76/mt76x2/mac.h b/drivers/net/wireless/mediatek/mt76/mt76x2/mac.h index 42ff221d7706..a1583021e1e9 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x2/mac.h +++ b/drivers/net/wireless/mediatek/mt76/mt76x2/mac.h @@ -1,17 +1,6 @@ +/* SPDX-License-Identifier: ISC */ /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef __MT76x2_MAC_H diff --git a/drivers/net/wireless/mediatek/mt76/mt76x2/mcu.c b/drivers/net/wireless/mediatek/mt76/mt76x2/mcu.c index cd3e082f486c..76d8cd37d4de 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x2/mcu.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x2/mcu.c @@ -1,18 +1,7 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> * Copyright (C) 2018 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include <linux/kernel.h> diff --git a/drivers/net/wireless/mediatek/mt76/mt76x2/mcu.h b/drivers/net/wireless/mediatek/mt76/mt76x2/mcu.h index 40ef43926c06..41fd66563e82 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x2/mcu.h +++ b/drivers/net/wireless/mediatek/mt76/mt76x2/mcu.h @@ -1,17 +1,6 @@ +/* SPDX-License-Identifier: ISC */ /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef __MT76x2_MCU_H @@ -71,7 +60,8 @@ struct mt76x2_tssi_comp { u8 offset1; } __packed __aligned(4); -int mt76x2_mcu_tssi_comp(struct mt76x02_dev *dev, struct mt76x2_tssi_comp *tssi_data); +int mt76x2_mcu_tssi_comp(struct mt76x02_dev *dev, + struct mt76x2_tssi_comp *tssi_data); int mt76x2_mcu_init_gain(struct mt76x02_dev *dev, u8 channel, u32 gain, bool force); diff --git a/drivers/net/wireless/mediatek/mt76/mt76x2/mt76x2.h b/drivers/net/wireless/mediatek/mt76/mt76x2/mt76x2.h index d7abe3d73bad..41680c420cda 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x2/mt76x2.h +++ b/drivers/net/wireless/mediatek/mt76/mt76x2/mt76x2.h @@ -1,17 +1,6 @@ +/* SPDX-License-Identifier: ISC */ /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef __MT76x2_H diff --git a/drivers/net/wireless/mediatek/mt76/mt76x2/mt76x2u.h b/drivers/net/wireless/mediatek/mt76/mt76x2/mt76x2u.h index 76cb1f84eff5..c876bac43751 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x2/mt76x2u.h +++ b/drivers/net/wireless/mediatek/mt76/mt76x2/mt76x2u.h @@ -1,17 +1,6 @@ +/* SPDX-License-Identifier: ISC */ /* * Copyright (C) 2018 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef __MT76x2U_H diff --git a/drivers/net/wireless/mediatek/mt76/mt76x2/pci.c b/drivers/net/wireless/mediatek/mt76/mt76x2/pci.c index e84d5c5911ea..73c3104f8858 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x2/pci.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x2/pci.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include <linux/kernel.h> diff --git a/drivers/net/wireless/mediatek/mt76/mt76x2/pci_init.c b/drivers/net/wireless/mediatek/mt76/mt76x2/pci_init.c index 71aea2832644..343127f2d621 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x2/pci_init.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x2/pci_init.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include <linux/delay.h> @@ -336,4 +325,3 @@ fail: return ret; } - diff --git a/drivers/net/wireless/mediatek/mt76/mt76x2/pci_main.c b/drivers/net/wireless/mediatek/mt76/mt76x2/pci_main.c index 3a1467326f4d..4971685aafe8 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x2/pci_main.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x2/pci_main.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include "mt76x2.h" @@ -176,7 +165,7 @@ const struct ieee80211_ops mt76x2_ops = { .sta_state = mt76_sta_state, .set_key = mt76x02_set_key, .conf_tx = mt76x02_conf_tx, - .sw_scan_start = mt76x02_sw_scan, + .sw_scan_start = mt76_sw_scan, .sw_scan_complete = mt76x02_sw_scan_complete, .flush = mt76x2_flush, .ampdu_action = mt76x02_ampdu_action, diff --git a/drivers/net/wireless/mediatek/mt76/mt76x2/pci_mcu.c b/drivers/net/wireless/mediatek/mt76/mt76x2/pci_mcu.c index 605dc66ae83b..ca6f968411ac 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x2/pci_mcu.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x2/pci_mcu.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include <linux/kernel.h> @@ -66,7 +55,7 @@ mt76pci_load_rom_patch(struct mt76x02_dev *dev) mt76_wr(dev, MT_MCU_PCIE_REMAP_BASE4, MT_MCU_ROM_PATCH_OFFSET); - cur = (__le32 *) (fw->data + sizeof(*hdr)); + cur = (__le32 *)(fw->data + sizeof(*hdr)); len = fw->size - sizeof(*hdr); mt76_wr_copy(dev, MT_MCU_ROM_PATCH_ADDR, cur, len); @@ -121,7 +110,7 @@ mt76pci_load_firmware(struct mt76x02_dev *dev) dev_info(dev->mt76.dev, "Build: %x\n", val); dev_info(dev->mt76.dev, "Build Time: %.16s\n", hdr->build_time); - cur = (__le32 *) (fw->data + sizeof(*hdr)); + cur = (__le32 *)(fw->data + sizeof(*hdr)); len = le32_to_cpu(hdr->ilm_len); mt76_wr(dev, MT_MCU_PCIE_REMAP_BASE4, MT_MCU_ILM_OFFSET); diff --git a/drivers/net/wireless/mediatek/mt76/mt76x2/pci_phy.c b/drivers/net/wireless/mediatek/mt76/mt76x2/pci_phy.c index 2edf1bd0c18c..23f35bf8d47b 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x2/pci_phy.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x2/pci_phy.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include <linux/delay.h> diff --git a/drivers/net/wireless/mediatek/mt76/mt76x2/phy.c b/drivers/net/wireless/mediatek/mt76/mt76x2/phy.c index cdedf95ca4f5..edbab4fa7f6e 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x2/phy.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x2/phy.c @@ -1,18 +1,7 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> * Copyright (C) 2018 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include "mt76x2.h" @@ -25,7 +14,8 @@ mt76x2_adjust_high_lna_gain(struct mt76x02_dev *dev, int reg, s8 offset) { s8 gain; - gain = FIELD_GET(MT_BBP_AGC_LNA_HIGH_GAIN, mt76_rr(dev, MT_BBP(AGC, reg))); + gain = FIELD_GET(MT_BBP_AGC_LNA_HIGH_GAIN, + mt76_rr(dev, MT_BBP(AGC, reg))); gain -= offset / 2; mt76_rmw_field(dev, MT_BBP(AGC, reg), MT_BBP_AGC_LNA_HIGH_GAIN, gain); } @@ -295,7 +285,7 @@ void mt76x2_phy_update_channel_gain(struct mt76x02_dev *dev) dev->cal.avg_rssi_all = -75; low_gain = (dev->cal.avg_rssi_all > mt76x02_get_rssi_gain_thresh(dev)) + - (dev->cal.avg_rssi_all > mt76x02_get_low_rssi_gain_thresh(dev)); + (dev->cal.avg_rssi_all > mt76x02_get_low_rssi_gain_thresh(dev)); gain_change = dev->cal.low_gain < 0 || (dev->cal.low_gain & 2) ^ (low_gain & 2); diff --git a/drivers/net/wireless/mediatek/mt76/mt76x2/usb.c b/drivers/net/wireless/mediatek/mt76/mt76x2/usb.c index 7a994a783510..da5e0f9a8bae 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x2/usb.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x2/usb.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2018 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include <linux/kernel.h> @@ -36,6 +25,7 @@ static int mt76x2u_probe(struct usb_interface *intf, const struct usb_device_id *id) { static const struct mt76_driver_ops drv_ops = { + .update_survey = mt76x02_update_channel, .tx_prepare_skb = mt76x02u_tx_prepare_skb, .tx_complete_skb = mt76x02u_tx_complete_skb, .tx_status_data = mt76x02_tx_status_data, diff --git a/drivers/net/wireless/mediatek/mt76/mt76x2/usb_init.c b/drivers/net/wireless/mediatek/mt76/mt76x2/usb_init.c index 94f52f98019b..e305b374c904 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x2/usb_init.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x2/usb_init.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2018 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include <linux/delay.h> @@ -195,6 +184,13 @@ int mt76x2u_init_hardware(struct mt76x02_dev *dev) mt76x02_phy_set_rxpath(dev); mt76x02_phy_set_txdac(dev); + mt76_wr(dev, MT_CH_TIME_CFG, + MT_CH_TIME_CFG_TIMER_EN | + MT_CH_TIME_CFG_TX_AS_BUSY | + MT_CH_TIME_CFG_RX_AS_BUSY | + MT_CH_TIME_CFG_NAV_AS_BUSY | + MT_CH_TIME_CFG_EIFS_AS_BUSY); + return mt76x2u_mac_stop(dev); } diff --git a/drivers/net/wireless/mediatek/mt76/mt76x2/usb_mac.c b/drivers/net/wireless/mediatek/mt76/mt76x2/usb_mac.c index 3b82345756ea..e7fea3a6f1fd 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x2/usb_mac.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x2/usb_mac.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2018 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include "mt76x2u.h" diff --git a/drivers/net/wireless/mediatek/mt76/mt76x2/usb_main.c b/drivers/net/wireless/mediatek/mt76/mt76x2/usb_main.c index e4dfc3bea3c5..eb73cb856c81 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x2/usb_main.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x2/usb_main.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2018 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include "mt76x2u.h" @@ -48,7 +37,7 @@ mt76x2u_set_channel(struct mt76x02_dev *dev, int err; cancel_delayed_work_sync(&dev->cal_work); - dev->beacon_ops->pre_tbtt_enable(dev, false); + mt76x02_pre_tbtt_enable(dev, false); mutex_lock(&dev->mt76.mutex); set_bit(MT76_RESET, &dev->mt76.state); @@ -59,12 +48,16 @@ mt76x2u_set_channel(struct mt76x02_dev *dev, err = mt76x2u_phy_set_channel(dev, chandef); + /* channel cycle counters read-and-clear */ + mt76_rr(dev, MT_CH_IDLE); + mt76_rr(dev, MT_CH_BUSY); + mt76x2_mac_resume(dev); clear_bit(MT76_RESET, &dev->mt76.state); mutex_unlock(&dev->mt76.mutex); - dev->beacon_ops->pre_tbtt_enable(dev, true); + mt76x02_pre_tbtt_enable(dev, true); mt76_txq_schedule_all(&dev->mt76); return err; @@ -121,10 +114,11 @@ const struct ieee80211_ops mt76x2u_ops = { .bss_info_changed = mt76x02_bss_info_changed, .configure_filter = mt76x02_configure_filter, .conf_tx = mt76x02_conf_tx, - .sw_scan_start = mt76x02_sw_scan, + .sw_scan_start = mt76_sw_scan, .sw_scan_complete = mt76x02_sw_scan_complete, .sta_rate_tbl_update = mt76x02_sta_rate_tbl_update, .get_txpower = mt76_get_txpower, + .get_survey = mt76_get_survey, .set_tim = mt76_set_tim, .release_buffered_frames = mt76_release_buffered_frames, }; diff --git a/drivers/net/wireless/mediatek/mt76/mt76x2/usb_mcu.c b/drivers/net/wireless/mediatek/mt76/mt76x2/usb_mcu.c index 152d41fe9ff5..dd22d8af0901 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x2/usb_mcu.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x2/usb_mcu.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2018 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include <linux/firmware.h> diff --git a/drivers/net/wireless/mediatek/mt76/mt76x2/usb_phy.c b/drivers/net/wireless/mediatek/mt76/mt76x2/usb_phy.c index dfd54f9b0e97..b1381f9df992 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76x2/usb_phy.c +++ b/drivers/net/wireless/mediatek/mt76/mt76x2/usb_phy.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2018 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include "mt76x2u.h" diff --git a/drivers/net/wireless/mediatek/mt76/trace.c b/drivers/net/wireless/mediatek/mt76/trace.c index ea4ab8729ae4..ed3df3c8b4b3 100644 --- a/drivers/net/wireless/mediatek/mt76/trace.c +++ b/drivers/net/wireless/mediatek/mt76/trace.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include <linux/module.h> diff --git a/drivers/net/wireless/mediatek/mt76/trace.h b/drivers/net/wireless/mediatek/mt76/trace.h index ea30895933c5..0b3e635da868 100644 --- a/drivers/net/wireless/mediatek/mt76/trace.h +++ b/drivers/net/wireless/mediatek/mt76/trace.h @@ -1,17 +1,6 @@ +/* SPDX-License-Identifier: ISC */ /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #if !defined(__MT76_TRACE_H) || defined(TRACE_HEADER_MULTI_READ) @@ -24,10 +13,11 @@ #define TRACE_SYSTEM mt76 #define MAXNAME 32 -#define DEV_ENTRY __array(char, wiphy_name, 32) -#define DEV_ASSIGN strlcpy(__entry->wiphy_name, wiphy_name(dev->hw->wiphy), MAXNAME) -#define DEV_PR_FMT "%s" -#define DEV_PR_ARG __entry->wiphy_name +#define DEV_ENTRY __array(char, wiphy_name, 32) +#define DEV_ASSIGN strlcpy(__entry->wiphy_name, \ + wiphy_name(dev->hw->wiphy), MAXNAME) +#define DEV_PR_FMT "%s" +#define DEV_PR_ARG __entry->wiphy_name #define REG_ENTRY __field(u32, reg) __field(u32, val) #define REG_ASSIGN __entry->reg = reg; __entry->val = val diff --git a/drivers/net/wireless/mediatek/mt76/tx.c b/drivers/net/wireless/mediatek/mt76/tx.c index 5397827668b9..c22a05f06fd0 100644 --- a/drivers/net/wireless/mediatek/mt76/tx.c +++ b/drivers/net/wireless/mediatek/mt76/tx.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include "mt76.h" @@ -97,7 +86,7 @@ mt76_txq_get_qid(struct ieee80211_txq *txq) static void mt76_check_agg_ssn(struct mt76_txq *mtxq, struct sk_buff *skb) { - struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) skb->data; + struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)skb->data; if (!ieee80211_is_data_qos(hdr->frame_control) || !ieee80211_is_data_present(hdr->frame_control)) @@ -217,8 +206,8 @@ mt76_tx_status_skb_get(struct mt76_dev *dev, struct mt76_wcid *wcid, int pktid, if (cb->pktid == pktid) return skb; - if (pktid >= 0 && - !time_after(jiffies, cb->jiffies + MT_TX_STATUS_SKB_TIMEOUT)) + if (pktid >= 0 && !time_after(jiffies, cb->jiffies + + MT_TX_STATUS_SKB_TIMEOUT)) continue; __mt76_tx_status_skb_done(dev, skb, MT_TX_CB_TXS_FAILED | @@ -260,7 +249,7 @@ mt76_tx(struct mt76_dev *dev, struct ieee80211_sta *sta, struct mt76_wcid *wcid, struct sk_buff *skb) { struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb); - struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) skb->data; + struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)skb->data; struct mt76_queue *q; int qid = skb_get_queue_mapping(skb); @@ -280,7 +269,7 @@ mt76_tx(struct mt76_dev *dev, struct ieee80211_sta *sta, tid = skb->priority & IEEE80211_QOS_CTL_TID_MASK; txq = sta->txq[tid]; - mtxq = (struct mt76_txq *) txq->drv_priv; + mtxq = (struct mt76_txq *)txq->drv_priv; if (mtxq->aggr) mt76_check_agg_ssn(mtxq, skb); @@ -328,7 +317,7 @@ static void mt76_queue_ps_skb(struct mt76_dev *dev, struct ieee80211_sta *sta, struct sk_buff *skb, bool last) { - struct mt76_wcid *wcid = (struct mt76_wcid *) sta->drv_priv; + struct mt76_wcid *wcid = (struct mt76_wcid *)sta->drv_priv; struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb); info->control.flags |= IEEE80211_TX_CTRL_PS_RESPONSE; @@ -354,7 +343,7 @@ mt76_release_buffered_frames(struct ieee80211_hw *hw, struct ieee80211_sta *sta, spin_lock_bh(&hwq->lock); for (i = 0; tids && nframes; i++, tids >>= 1) { struct ieee80211_txq *txq = sta->txq[i]; - struct mt76_txq *mtxq = (struct mt76_txq *) txq->drv_priv; + struct mt76_txq *mtxq = (struct mt76_txq *)txq->drv_priv; struct sk_buff *skb; if (!(tids & 1)) @@ -438,8 +427,7 @@ mt76_txq_send_burst(struct mt76_dev *dev, struct mt76_sw_queue *sq, if (probe) break; - if (test_bit(MT76_OFFCHANNEL, &dev->state) || - test_bit(MT76_RESET, &dev->state)) + if (test_bit(MT76_RESET, &dev->state)) return -EBUSY; skb = mt76_txq_dequeue(dev, mtxq, false); @@ -498,8 +486,7 @@ mt76_txq_schedule_list(struct mt76_dev *dev, enum mt76_txq_id qid) if (sq->swq_queued >= 4) break; - if (test_bit(MT76_OFFCHANNEL, &dev->state) || - test_bit(MT76_RESET, &dev->state)) { + if (test_bit(MT76_RESET, &dev->state)) { ret = -EBUSY; break; } @@ -568,6 +555,13 @@ void mt76_txq_schedule_all(struct mt76_dev *dev) } EXPORT_SYMBOL_GPL(mt76_txq_schedule_all); +void mt76_tx_tasklet(unsigned long data) +{ + struct mt76_dev *dev = (struct mt76_dev *)data; + + mt76_txq_schedule_all(dev); +} + void mt76_stop_tx_queues(struct mt76_dev *dev, struct ieee80211_sta *sta, bool send_bar) { @@ -610,7 +604,7 @@ void mt76_txq_remove(struct mt76_dev *dev, struct ieee80211_txq *txq) if (!txq) return; - mtxq = (struct mt76_txq *) txq->drv_priv; + mtxq = (struct mt76_txq *)txq->drv_priv; while ((skb = skb_dequeue(&mtxq->retry_q)) != NULL) ieee80211_free_txskb(dev->hw, skb); @@ -619,7 +613,7 @@ EXPORT_SYMBOL_GPL(mt76_txq_remove); void mt76_txq_init(struct mt76_dev *dev, struct ieee80211_txq *txq) { - struct mt76_txq *mtxq = (struct mt76_txq *) txq->drv_priv; + struct mt76_txq *mtxq = (struct mt76_txq *)txq->drv_priv; skb_queue_head_init(&mtxq->retry_q); diff --git a/drivers/net/wireless/mediatek/mt76/usb.c b/drivers/net/wireless/mediatek/mt76/usb.c index fb87ce7fbdf6..20c6fe510e9d 100644 --- a/drivers/net/wireless/mediatek/mt76/usb.c +++ b/drivers/net/wireless/mediatek/mt76/usb.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2018 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include <linux/module.h> @@ -95,9 +84,9 @@ static u32 __mt76u_rr(struct mt76_dev *dev, u32 addr) ret = __mt76u_vendor_request(dev, req, USB_DIR_IN | USB_TYPE_VENDOR, - 0, offset, usb->data, sizeof(__le32)); + 0, offset, &usb->reg_val, sizeof(__le32)); if (ret == sizeof(__le32)) - data = get_unaligned_le32(usb->data); + data = le32_to_cpu(usb->reg_val); trace_usb_reg_rr(dev, addr, data); return data; @@ -131,10 +120,10 @@ static void __mt76u_wr(struct mt76_dev *dev, u32 addr, u32 val) } offset = addr & ~MT_VEND_TYPE_MASK; - put_unaligned_le32(val, usb->data); + usb->reg_val = cpu_to_le32(val); __mt76u_vendor_request(dev, req, USB_DIR_OUT | USB_TYPE_VENDOR, 0, - offset, usb->data, sizeof(__le32)); + offset, &usb->reg_val, sizeof(__le32)); trace_usb_reg_wr(dev, addr, val); } @@ -164,12 +153,12 @@ static void mt76u_copy(struct mt76_dev *dev, u32 offset, int i, ret; mutex_lock(&usb->usb_ctrl_mtx); - for (i = 0; i < (len / 4); i++) { - put_unaligned_le32(val[i], usb->data); + for (i = 0; i < DIV_ROUND_UP(len, 4); i++) { + put_unaligned(val[i], (u32 *)usb->data); ret = __mt76u_vendor_request(dev, MT_VEND_MULTI_WRITE, USB_DIR_OUT | USB_TYPE_VENDOR, 0, offset + i * 4, usb->data, - sizeof(__le32)); + sizeof(u32)); if (ret < 0) break; } @@ -309,7 +298,7 @@ mt76u_fill_rx_sg(struct mt76_dev *dev, struct mt76_queue *q, struct urb *urb, } urb->num_sgs = max_t(int, i, urb->num_sgs); - urb->transfer_buffer_length = urb->num_sgs * q->buf_size, + urb->transfer_buffer_length = urb->num_sgs * q->buf_size; sg_init_marker(urb->sg, urb->num_sgs); return i ? : -ENOMEM; @@ -320,14 +309,13 @@ mt76u_refill_rx(struct mt76_dev *dev, struct urb *urb, int nsgs, gfp_t gfp) { struct mt76_queue *q = &dev->q_rx[MT_RXQ_MAIN]; - if (dev->usb.sg_en) { + if (dev->usb.sg_en) return mt76u_fill_rx_sg(dev, q, urb, nsgs, gfp); - } else { - urb->transfer_buffer_length = q->buf_size; - urb->transfer_buffer = page_frag_alloc(&q->rx_page, - q->buf_size, gfp); - return urb->transfer_buffer ? 0 : -ENOMEM; - } + + urb->transfer_buffer_length = q->buf_size; + urb->transfer_buffer = page_frag_alloc(&q->rx_page, q->buf_size, gfp); + + return urb->transfer_buffer ? 0 : -ENOMEM; } static int @@ -763,13 +751,14 @@ mt76u_tx_setup_buffers(struct mt76_dev *dev, struct sk_buff *skb, if (!dev->usb.sg_en) { urb->transfer_buffer = skb->data; return 0; - } else { - sg_init_table(urb->sg, MT_TX_SG_MAX_SIZE); - urb->num_sgs = skb_to_sgvec(skb, urb->sg, 0, skb->len); - if (urb->num_sgs == 0) - return -ENOMEM; - return urb->num_sgs; } + + sg_init_table(urb->sg, MT_TX_SG_MAX_SIZE); + urb->num_sgs = skb_to_sgvec(skb, urb->sg, 0, skb->len); + if (!urb->num_sgs) + return -ENOMEM; + + return urb->num_sgs; } static int @@ -885,7 +874,8 @@ void mt76u_stop_tx(struct mt76_dev *dev) struct mt76_queue *q; int i, j, ret; - ret = wait_event_timeout(dev->tx_wait, !mt76_has_tx_pending(dev), HZ/5); + ret = wait_event_timeout(dev->tx_wait, !mt76_has_tx_pending(dev), + HZ / 5); if (!ret) { dev_err(dev->dev, "timed out waiting for pending tx\n"); @@ -957,7 +947,7 @@ int mt76u_init(struct mt76_dev *dev, .rr = mt76u_rr, .wr = mt76u_wr, .rmw = mt76u_rmw, - .copy = mt76u_copy, + .write_copy = mt76u_copy, .wr_rp = mt76u_wr_rp, .rd_rp = mt76u_rd_rp, .type = MT76_BUS_USB, diff --git a/drivers/net/wireless/mediatek/mt76/usb_trace.c b/drivers/net/wireless/mediatek/mt76/usb_trace.c index 7e1f540f0b7a..9942bdd6177b 100644 --- a/drivers/net/wireless/mediatek/mt76/usb_trace.c +++ b/drivers/net/wireless/mediatek/mt76/usb_trace.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2018 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include <linux/module.h> diff --git a/drivers/net/wireless/mediatek/mt76/usb_trace.h b/drivers/net/wireless/mediatek/mt76/usb_trace.h index b56c32343eb1..f5ab3215af80 100644 --- a/drivers/net/wireless/mediatek/mt76/usb_trace.h +++ b/drivers/net/wireless/mediatek/mt76/usb_trace.h @@ -1,17 +1,6 @@ +/* SPDX-License-Identifier: ISC */ /* * Copyright (C) 2018 Lorenzo Bianconi <lorenzo.bianconi83@gmail.com> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #if !defined(__MT76_USB_TRACE_H) || defined(TRACE_HEADER_MULTI_READ) @@ -24,10 +13,11 @@ #define TRACE_SYSTEM mt76_usb #define MAXNAME 32 -#define DEV_ENTRY __array(char, wiphy_name, 32) -#define DEV_ASSIGN strlcpy(__entry->wiphy_name, wiphy_name(dev->hw->wiphy), MAXNAME) -#define DEV_PR_FMT "%s " -#define DEV_PR_ARG __entry->wiphy_name +#define DEV_ENTRY __array(char, wiphy_name, 32) +#define DEV_ASSIGN strlcpy(__entry->wiphy_name, \ + wiphy_name(dev->hw->wiphy), MAXNAME) +#define DEV_PR_FMT "%s " +#define DEV_PR_ARG __entry->wiphy_name #define REG_ENTRY __field(u32, reg) __field(u32, val) #define REG_ASSIGN __entry->reg = reg; __entry->val = val @@ -65,7 +55,7 @@ DECLARE_EVENT_CLASS(urb_transfer, TP_PROTO(struct mt76_dev *dev, struct urb *u), TP_ARGS(dev, u), TP_STRUCT__entry( - DEV_ENTRY __field(unsigned, pipe) __field(u32, len) + DEV_ENTRY __field(unsigned int, pipe) __field(u32, len) ), TP_fast_assign( DEV_ASSIGN; diff --git a/drivers/net/wireless/mediatek/mt76/util.c b/drivers/net/wireless/mediatek/mt76/util.c index 69270c1a9091..23d1e1da78b2 100644 --- a/drivers/net/wireless/mediatek/mt76/util.c +++ b/drivers/net/wireless/mediatek/mt76/util.c @@ -1,17 +1,6 @@ +// SPDX-License-Identifier: ISC /* * Copyright (C) 2016 Felix Fietkau <nbd@nbd.name> - * - * Permission to use, copy, modify, and/or distribute this software for any - * purpose with or without fee is hereby granted, provided that the above - * copyright notice and this permission notice appear in all copies. - * - * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES - * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF - * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR - * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES - * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN - * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include <linux/module.h> diff --git a/drivers/net/wireless/mediatek/mt76/util.h b/drivers/net/wireless/mediatek/mt76/util.h index 9f8d59269a9e..fe3479c8e561 100644 --- a/drivers/net/wireless/mediatek/mt76/util.h +++ b/drivers/net/wireless/mediatek/mt76/util.h @@ -12,7 +12,7 @@ #include <linux/bitfield.h> #define MT76_INCR(_var, _size) \ - _var = (((_var) + 1) % _size) + (_var = (((_var) + 1) % (_size))) int mt76_wcid_alloc(unsigned long *mask, int size); @@ -25,7 +25,7 @@ mt76_wcid_free(unsigned long *mask, int idx) static inline void mt76_skb_set_moredata(struct sk_buff *skb, bool enable) { - struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) skb->data; + struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)skb->data; if (enable) hdr->frame_control |= cpu_to_le16(IEEE80211_FCTL_MOREDATA); diff --git a/drivers/net/wireless/mediatek/mt7601u/init.c b/drivers/net/wireless/mediatek/mt7601u/init.c index 9bfac9f1d47f..cada48800928 100644 --- a/drivers/net/wireless/mediatek/mt7601u/init.c +++ b/drivers/net/wireless/mediatek/mt7601u/init.c @@ -557,6 +557,9 @@ mt76_init_sband_2g(struct mt7601u_dev *dev) { dev->sband_2g = devm_kzalloc(dev->dev, sizeof(*dev->sband_2g), GFP_KERNEL); + if (!dev->sband_2g) + return -ENOMEM; + dev->hw->wiphy->bands[NL80211_BAND_2GHZ] = dev->sband_2g; WARN_ON(dev->ee->reg.start - 1 + dev->ee->reg.num > diff --git a/drivers/net/wireless/mediatek/mt7601u/main.c b/drivers/net/wireless/mediatek/mt7601u/main.c index 89a7b1234ffb..72e608cc53af 100644 --- a/drivers/net/wireless/mediatek/mt7601u/main.c +++ b/drivers/net/wireless/mediatek/mt7601u/main.c @@ -351,7 +351,7 @@ mt76_ampdu_action(struct ieee80211_hw *hw, struct ieee80211_vif *vif, struct ieee80211_sta *sta = params->sta; enum ieee80211_ampdu_mlme_action action = params->action; u16 tid = params->tid; - u16 *ssn = ¶ms->ssn; + u16 ssn = params->ssn; struct mt76_sta *msta = (struct mt76_sta *) sta->drv_priv; WARN_ON(msta->wcid.idx > GROUP_WCID(0)); @@ -371,7 +371,7 @@ mt76_ampdu_action(struct ieee80211_hw *hw, struct ieee80211_vif *vif, case IEEE80211_AMPDU_TX_STOP_FLUSH_CONT: break; case IEEE80211_AMPDU_TX_START: - msta->agg_ssn[tid] = *ssn << 4; + msta->agg_ssn[tid] = ssn << 4; ieee80211_start_tx_ba_cb_irqsafe(vif, sta->addr, tid); break; case IEEE80211_AMPDU_TX_STOP_CONT: |