1 // SPDX-License-Identifier: BSD-3-Clause-Clear 2 /* 3 * Copyright (C) 2024 Felix Fietkau <nbd@nbd.name> 4 */ 5 #include "mt76.h" 6 7 static void mt76_scan_complete(struct mt76_dev *dev, bool abort) 8 { 9 struct mt76_phy *phy = dev->scan.phy; 10 struct cfg80211_scan_info info = { 11 .aborted = abort, 12 }; 13 14 if (!phy) 15 return; 16 17 clear_bit(MT76_SCANNING, &phy->state); 18 19 if (dev->scan.chan && phy->main_chandef.chan && phy->offchannel && 20 !test_bit(MT76_MCU_RESET, &dev->phy.state)) { 21 mt76_set_channel(phy, &phy->main_chandef, false); 22 mt76_offchannel_notify(phy, false); 23 } 24 mt76_put_vif_phy_link(phy, dev->scan.vif, dev->scan.mlink); 25 memset(&dev->scan, 0, sizeof(dev->scan)); 26 if (!test_bit(MT76_MCU_RESET, &dev->phy.state)) 27 ieee80211_scan_completed(phy->hw, &info); 28 } 29 30 void mt76_abort_scan(struct mt76_dev *dev) 31 { 32 spin_lock_bh(&dev->scan_lock); 33 dev->scan.beacon_wait = false; 34 spin_unlock_bh(&dev->scan_lock); 35 36 cancel_delayed_work_sync(&dev->scan_work); 37 mt76_scan_complete(dev, true); 38 } 39 EXPORT_SYMBOL_GPL(mt76_abort_scan); 40 41 static void 42 mt76_scan_send_probe(struct mt76_dev *dev, struct cfg80211_ssid *ssid) 43 { 44 struct cfg80211_scan_request *req = dev->scan.req; 45 struct ieee80211_vif *vif = dev->scan.vif; 46 struct mt76_vif_link *mvif = dev->scan.mlink; 47 enum nl80211_band band = dev->scan.chan->band; 48 struct mt76_phy *phy = dev->scan.phy; 49 struct ieee80211_tx_info *info; 50 struct sk_buff *skb; 51 52 skb = ieee80211_probereq_get(phy->hw, vif->addr, ssid->ssid, 53 ssid->ssid_len, req->ie_len); 54 if (!skb) 55 return; 56 57 if (is_unicast_ether_addr(req->bssid)) { 58 struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)skb->data; 59 60 ether_addr_copy(hdr->addr1, req->bssid); 61 ether_addr_copy(hdr->addr3, req->bssid); 62 } 63 64 if (req->ie_len) 65 skb_put_data(skb, req->ie, req->ie_len); 66 67 skb->priority = 7; 68 skb_set_queue_mapping(skb, IEEE80211_AC_VO); 69 70 rcu_read_lock(); 71 72 if (!ieee80211_tx_prepare_skb(phy->hw, vif, skb, band, NULL)) 73 goto out; 74 75 info = IEEE80211_SKB_CB(skb); 76 if (req->no_cck) 77 info->flags |= IEEE80211_TX_CTL_NO_CCK_RATE; 78 info->control.flags |= IEEE80211_TX_CTRL_DONT_USE_RATE_MASK; 79 80 mt76_tx(phy, NULL, mvif->wcid, skb); 81 82 out: 83 rcu_read_unlock(); 84 } 85 86 void mt76_scan_rx_beacon(struct mt76_dev *dev, struct ieee80211_channel *chan) 87 { 88 struct mt76_phy *phy; 89 90 spin_lock(&dev->scan_lock); 91 92 if (!dev->scan.beacon_wait || dev->scan.beacon_received || 93 dev->scan.chan != chan) 94 goto out; 95 96 phy = dev->scan.phy; 97 if (!phy) 98 goto out; 99 100 dev->scan.beacon_received = true; 101 ieee80211_queue_delayed_work(phy->hw, &dev->scan_work, 0); 102 103 out: 104 spin_unlock(&dev->scan_lock); 105 } 106 107 void mt76_scan_work(struct work_struct *work) 108 { 109 struct mt76_dev *dev = container_of(work, struct mt76_dev, 110 scan_work.work); 111 struct cfg80211_scan_request *req = dev->scan.req; 112 struct cfg80211_chan_def chandef = {}; 113 struct mt76_phy *phy = dev->scan.phy; 114 int duration = HZ / 9; /* ~110 ms */ 115 bool beacon_rx, offchannel = true; 116 int i; 117 118 if (!phy || !req) 119 return; 120 121 spin_lock_bh(&dev->scan_lock); 122 beacon_rx = dev->scan.beacon_wait && dev->scan.beacon_received; 123 dev->scan.beacon_wait = false; 124 spin_unlock_bh(&dev->scan_lock); 125 126 if (beacon_rx) 127 goto probe; 128 129 if (dev->scan.chan_idx >= req->n_channels) { 130 mt76_scan_complete(dev, false); 131 return; 132 } 133 134 if (dev->scan.chan && phy->num_sta && phy->offchannel) { 135 dev->scan.chan = NULL; 136 mt76_set_channel(phy, &phy->main_chandef, false); 137 mt76_offchannel_notify(phy, false); 138 goto out; 139 } 140 141 dev->scan.chan = req->channels[dev->scan.chan_idx++]; 142 offchannel = mt76_offchannel_chandef(phy, dev->scan.chan, &chandef); 143 144 if (offchannel) 145 mt76_offchannel_notify(phy, true); 146 mt76_set_channel(phy, &chandef, offchannel); 147 148 if (!req->n_ssids) 149 goto out; 150 151 if (chandef.chan->flags & (IEEE80211_CHAN_NO_IR | IEEE80211_CHAN_RADAR)) { 152 spin_lock_bh(&dev->scan_lock); 153 dev->scan.beacon_received = false; 154 dev->scan.beacon_wait = true; 155 spin_unlock_bh(&dev->scan_lock); 156 goto out; 157 } 158 159 probe: 160 if (phy->offchannel) 161 duration = HZ / 16; /* ~60 ms */ 162 local_bh_disable(); 163 for (i = 0; i < req->n_ssids; i++) 164 mt76_scan_send_probe(dev, &req->ssids[i]); 165 local_bh_enable(); 166 167 out: 168 if (dev->scan.chan && phy->offchannel) 169 duration = max_t(int, duration, 170 msecs_to_jiffies(req->duration + 171 (req->duration >> 5))); 172 173 ieee80211_queue_delayed_work(dev->phy.hw, &dev->scan_work, duration); 174 } 175 176 int mt76_hw_scan(struct ieee80211_hw *hw, struct ieee80211_vif *vif, 177 struct ieee80211_scan_request *req) 178 { 179 struct mt76_phy *phy = hw->priv; 180 struct mt76_dev *dev = phy->dev; 181 struct mt76_vif_link *mlink; 182 int ret = 0; 183 184 if (hw->wiphy->n_radio > 1) { 185 phy = dev->band_phys[req->req.channels[0]->band]; 186 if (!phy) 187 return -EINVAL; 188 } 189 190 mutex_lock(&dev->mutex); 191 192 if (dev->scan.req || phy->roc_vif || 193 test_bit(MT76_MCU_RESET, &dev->phy.state)) { 194 ret = -EBUSY; 195 goto out; 196 } 197 198 mlink = mt76_get_vif_phy_link(phy, vif); 199 if (IS_ERR(mlink)) { 200 ret = PTR_ERR(mlink); 201 goto out; 202 } 203 204 memset(&dev->scan, 0, sizeof(dev->scan)); 205 dev->scan.req = &req->req; 206 dev->scan.vif = vif; 207 dev->scan.phy = phy; 208 dev->scan.mlink = mlink; 209 ieee80211_queue_delayed_work(dev->phy.hw, &dev->scan_work, 0); 210 211 out: 212 mutex_unlock(&dev->mutex); 213 214 return ret; 215 } 216 EXPORT_SYMBOL_GPL(mt76_hw_scan); 217 218 void mt76_cancel_hw_scan(struct ieee80211_hw *hw, struct ieee80211_vif *vif) 219 { 220 struct mt76_phy *phy = hw->priv; 221 222 mt76_abort_scan(phy->dev); 223 } 224 EXPORT_SYMBOL_GPL(mt76_cancel_hw_scan); 225