beacon.c revision ba4903f97a275ed0967b58ff882f8ab41bec24ad
1/* 2 * Copyright (c) 2008-2011 Atheros Communications Inc. 3 * 4 * Permission to use, copy, modify, and/or distribute this software for any 5 * purpose with or without fee is hereby granted, provided that the above 6 * copyright notice and this permission notice appear in all copies. 7 * 8 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 9 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 10 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 11 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 12 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 13 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 14 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 15 */ 16 17#include "ath9k.h" 18 19#define FUDGE 2 20 21static void ath9k_reset_beacon_status(struct ath_softc *sc) 22{ 23 sc->beacon.tx_processed = false; 24 sc->beacon.tx_last = false; 25} 26 27/* 28 * This function will modify certain transmit queue properties depending on 29 * the operating mode of the station (AP or AdHoc). Parameters are AIFS 30 * settings and channel width min/max 31*/ 32int ath_beaconq_config(struct ath_softc *sc) 33{ 34 struct ath_hw *ah = sc->sc_ah; 35 struct ath_common *common = ath9k_hw_common(ah); 36 struct ath9k_tx_queue_info qi, qi_be; 37 struct ath_txq *txq; 38 39 ath9k_hw_get_txq_props(ah, sc->beacon.beaconq, &qi); 40 if (sc->sc_ah->opmode == NL80211_IFTYPE_AP) { 41 /* Always burst out beacon and CAB traffic. */ 42 qi.tqi_aifs = 1; 43 qi.tqi_cwmin = 0; 44 qi.tqi_cwmax = 0; 45 } else { 46 /* Adhoc mode; important thing is to use 2x cwmin. */ 47 txq = sc->tx.txq_map[WME_AC_BE]; 48 ath9k_hw_get_txq_props(ah, txq->axq_qnum, &qi_be); 49 qi.tqi_aifs = qi_be.tqi_aifs; 50 qi.tqi_cwmin = 4*qi_be.tqi_cwmin; 51 qi.tqi_cwmax = qi_be.tqi_cwmax; 52 } 53 54 if (!ath9k_hw_set_txq_props(ah, sc->beacon.beaconq, &qi)) { 55 ath_err(common, 56 "Unable to update h/w beacon queue parameters\n"); 57 return 0; 58 } else { 59 ath9k_hw_resettxqueue(ah, sc->beacon.beaconq); 60 return 1; 61 } 62} 63 64/* 65 * Associates the beacon frame buffer with a transmit descriptor. Will set 66 * up rate codes, and channel flags. Beacons are always sent out at the 67 * lowest rate, and are not retried. 68*/ 69static void ath_beacon_setup(struct ath_softc *sc, struct ath_vif *avp, 70 struct ath_buf *bf, int rateidx) 71{ 72 struct sk_buff *skb = bf->bf_mpdu; 73 struct ath_hw *ah = sc->sc_ah; 74 struct ath_common *common = ath9k_hw_common(ah); 75 struct ath_desc *ds; 76 struct ath9k_11n_rate_series series[4]; 77 int flags, ctsrate = 0, ctsduration = 0; 78 struct ieee80211_supported_band *sband; 79 u8 rate = 0; 80 81 ath9k_reset_beacon_status(sc); 82 83 ds = bf->bf_desc; 84 flags = ATH9K_TXDESC_NOACK; 85 86 ds->ds_link = 0; 87 88 sband = &sc->sbands[common->hw->conf.channel->band]; 89 rate = sband->bitrates[rateidx].hw_value; 90 if (sc->sc_flags & SC_OP_PREAMBLE_SHORT) 91 rate |= sband->bitrates[rateidx].hw_value_short; 92 93 ath9k_hw_set11n_txdesc(ah, ds, skb->len + FCS_LEN, 94 ATH9K_PKT_TYPE_BEACON, 95 MAX_RATE_POWER, 96 ATH9K_TXKEYIX_INVALID, 97 ATH9K_KEY_TYPE_CLEAR, 98 flags); 99 100 /* NB: beacon's BufLen must be a multiple of 4 bytes */ 101 ath9k_hw_filltxdesc(ah, ds, roundup(skb->len, 4), 102 true, true, ds, bf->bf_buf_addr, 103 sc->beacon.beaconq); 104 105 memset(series, 0, sizeof(struct ath9k_11n_rate_series) * 4); 106 series[0].Tries = 1; 107 series[0].Rate = rate; 108 series[0].ChSel = ath_txchainmask_reduction(sc, 109 common->tx_chainmask, series[0].Rate); 110 series[0].RateFlags = (ctsrate) ? ATH9K_RATESERIES_RTS_CTS : 0; 111 ath9k_hw_set11n_ratescenario(ah, ds, ds, 0, ctsrate, ctsduration, 112 series, 4, 0); 113} 114 115static void ath_tx_cabq(struct ieee80211_hw *hw, struct sk_buff *skb) 116{ 117 struct ath_softc *sc = hw->priv; 118 struct ath_common *common = ath9k_hw_common(sc->sc_ah); 119 struct ath_tx_control txctl; 120 121 memset(&txctl, 0, sizeof(struct ath_tx_control)); 122 txctl.txq = sc->beacon.cabq; 123 124 ath_dbg(common, ATH_DBG_XMIT, 125 "transmitting CABQ packet, skb: %p\n", skb); 126 127 if (ath_tx_start(hw, skb, &txctl) != 0) { 128 ath_dbg(common, ATH_DBG_XMIT, "CABQ TX failed\n"); 129 dev_kfree_skb_any(skb); 130 } 131} 132 133static struct ath_buf *ath_beacon_generate(struct ieee80211_hw *hw, 134 struct ieee80211_vif *vif) 135{ 136 struct ath_softc *sc = hw->priv; 137 struct ath_common *common = ath9k_hw_common(sc->sc_ah); 138 struct ath_buf *bf; 139 struct ath_vif *avp; 140 struct sk_buff *skb; 141 struct ath_txq *cabq; 142 struct ieee80211_tx_info *info; 143 int cabq_depth; 144 145 ath9k_reset_beacon_status(sc); 146 147 avp = (void *)vif->drv_priv; 148 cabq = sc->beacon.cabq; 149 150 if ((avp->av_bcbuf == NULL) || !avp->is_bslot_active) 151 return NULL; 152 153 /* Release the old beacon first */ 154 155 bf = avp->av_bcbuf; 156 skb = bf->bf_mpdu; 157 if (skb) { 158 dma_unmap_single(sc->dev, bf->bf_buf_addr, 159 skb->len, DMA_TO_DEVICE); 160 dev_kfree_skb_any(skb); 161 bf->bf_buf_addr = 0; 162 } 163 164 /* Get a new beacon from mac80211 */ 165 166 skb = ieee80211_beacon_get(hw, vif); 167 bf->bf_mpdu = skb; 168 if (skb == NULL) 169 return NULL; 170 ((struct ieee80211_mgmt *)skb->data)->u.beacon.timestamp = 171 avp->tsf_adjust; 172 173 info = IEEE80211_SKB_CB(skb); 174 if (info->flags & IEEE80211_TX_CTL_ASSIGN_SEQ) { 175 /* 176 * TODO: make sure the seq# gets assigned properly (vs. other 177 * TX frames) 178 */ 179 struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)skb->data; 180 sc->tx.seq_no += 0x10; 181 hdr->seq_ctrl &= cpu_to_le16(IEEE80211_SCTL_FRAG); 182 hdr->seq_ctrl |= cpu_to_le16(sc->tx.seq_no); 183 } 184 185 bf->bf_buf_addr = dma_map_single(sc->dev, skb->data, 186 skb->len, DMA_TO_DEVICE); 187 if (unlikely(dma_mapping_error(sc->dev, bf->bf_buf_addr))) { 188 dev_kfree_skb_any(skb); 189 bf->bf_mpdu = NULL; 190 bf->bf_buf_addr = 0; 191 ath_err(common, "dma_mapping_error on beaconing\n"); 192 return NULL; 193 } 194 195 skb = ieee80211_get_buffered_bc(hw, vif); 196 197 /* 198 * if the CABQ traffic from previous DTIM is pending and the current 199 * beacon is also a DTIM. 200 * 1) if there is only one vif let the cab traffic continue. 201 * 2) if there are more than one vif and we are using staggered 202 * beacons, then drain the cabq by dropping all the frames in 203 * the cabq so that the current vifs cab traffic can be scheduled. 204 */ 205 spin_lock_bh(&cabq->axq_lock); 206 cabq_depth = cabq->axq_depth; 207 spin_unlock_bh(&cabq->axq_lock); 208 209 if (skb && cabq_depth) { 210 if (sc->nvifs > 1) { 211 ath_dbg(common, ATH_DBG_BEACON, 212 "Flushing previous cabq traffic\n"); 213 ath_draintxq(sc, cabq, false); 214 } 215 } 216 217 ath_beacon_setup(sc, avp, bf, info->control.rates[0].idx); 218 219 while (skb) { 220 ath_tx_cabq(hw, skb); 221 skb = ieee80211_get_buffered_bc(hw, vif); 222 } 223 224 return bf; 225} 226 227int ath_beacon_alloc(struct ath_softc *sc, struct ieee80211_vif *vif) 228{ 229 struct ath_common *common = ath9k_hw_common(sc->sc_ah); 230 struct ath_vif *avp; 231 struct ath_buf *bf; 232 struct sk_buff *skb; 233 struct ath_beacon_config *cur_conf = &sc->cur_beacon_conf; 234 __le64 tstamp; 235 236 avp = (void *)vif->drv_priv; 237 238 /* Allocate a beacon descriptor if we haven't done so. */ 239 if (!avp->av_bcbuf) { 240 /* Allocate beacon state for hostap/ibss. We know 241 * a buffer is available. */ 242 avp->av_bcbuf = list_first_entry(&sc->beacon.bbuf, 243 struct ath_buf, list); 244 list_del(&avp->av_bcbuf->list); 245 246 if (ath9k_uses_beacons(vif->type)) { 247 int slot; 248 /* 249 * Assign the vif to a beacon xmit slot. As 250 * above, this cannot fail to find one. 251 */ 252 avp->av_bslot = 0; 253 for (slot = 0; slot < ATH_BCBUF; slot++) 254 if (sc->beacon.bslot[slot] == NULL) { 255 avp->av_bslot = slot; 256 avp->is_bslot_active = false; 257 258 /* NB: keep looking for a double slot */ 259 if (slot == 0 || !sc->beacon.bslot[slot-1]) 260 break; 261 } 262 BUG_ON(sc->beacon.bslot[avp->av_bslot] != NULL); 263 sc->beacon.bslot[avp->av_bslot] = vif; 264 sc->nbcnvifs++; 265 } 266 } 267 268 /* release the previous beacon frame, if it already exists. */ 269 bf = avp->av_bcbuf; 270 if (bf->bf_mpdu != NULL) { 271 skb = bf->bf_mpdu; 272 dma_unmap_single(sc->dev, bf->bf_buf_addr, 273 skb->len, DMA_TO_DEVICE); 274 dev_kfree_skb_any(skb); 275 bf->bf_mpdu = NULL; 276 bf->bf_buf_addr = 0; 277 } 278 279 /* NB: the beacon data buffer must be 32-bit aligned. */ 280 skb = ieee80211_beacon_get(sc->hw, vif); 281 if (skb == NULL) 282 return -ENOMEM; 283 284 tstamp = ((struct ieee80211_mgmt *)skb->data)->u.beacon.timestamp; 285 sc->beacon.bc_tstamp = (u32) le64_to_cpu(tstamp); 286 /* Calculate a TSF adjustment factor required for staggered beacons. */ 287 if (avp->av_bslot > 0) { 288 u64 tsfadjust; 289 int intval; 290 291 intval = cur_conf->beacon_interval ? : ATH_DEFAULT_BINTVAL; 292 293 /* 294 * Calculate the TSF offset for this beacon slot, i.e., the 295 * number of usecs that need to be added to the timestamp field 296 * in Beacon and Probe Response frames. Beacon slot 0 is 297 * processed at the correct offset, so it does not require TSF 298 * adjustment. Other slots are adjusted to get the timestamp 299 * close to the TBTT for the BSS. 300 */ 301 tsfadjust = TU_TO_USEC(intval * avp->av_bslot) / ATH_BCBUF; 302 avp->tsf_adjust = cpu_to_le64(tsfadjust); 303 304 ath_dbg(common, ATH_DBG_BEACON, 305 "stagger beacons, bslot %d intval %u tsfadjust %llu\n", 306 avp->av_bslot, intval, (unsigned long long)tsfadjust); 307 308 ((struct ieee80211_mgmt *)skb->data)->u.beacon.timestamp = 309 avp->tsf_adjust; 310 } else 311 avp->tsf_adjust = cpu_to_le64(0); 312 313 bf->bf_mpdu = skb; 314 bf->bf_buf_addr = dma_map_single(sc->dev, skb->data, 315 skb->len, DMA_TO_DEVICE); 316 if (unlikely(dma_mapping_error(sc->dev, bf->bf_buf_addr))) { 317 dev_kfree_skb_any(skb); 318 bf->bf_mpdu = NULL; 319 bf->bf_buf_addr = 0; 320 ath_err(common, "dma_mapping_error on beacon alloc\n"); 321 return -ENOMEM; 322 } 323 avp->is_bslot_active = true; 324 325 return 0; 326} 327 328void ath_beacon_return(struct ath_softc *sc, struct ath_vif *avp) 329{ 330 if (avp->av_bcbuf != NULL) { 331 struct ath_buf *bf; 332 333 avp->is_bslot_active = false; 334 if (avp->av_bslot != -1) { 335 sc->beacon.bslot[avp->av_bslot] = NULL; 336 sc->nbcnvifs--; 337 avp->av_bslot = -1; 338 } 339 340 bf = avp->av_bcbuf; 341 if (bf->bf_mpdu != NULL) { 342 struct sk_buff *skb = bf->bf_mpdu; 343 dma_unmap_single(sc->dev, bf->bf_buf_addr, 344 skb->len, DMA_TO_DEVICE); 345 dev_kfree_skb_any(skb); 346 bf->bf_mpdu = NULL; 347 bf->bf_buf_addr = 0; 348 } 349 list_add_tail(&bf->list, &sc->beacon.bbuf); 350 351 avp->av_bcbuf = NULL; 352 } 353} 354 355void ath_beacon_tasklet(unsigned long data) 356{ 357 struct ath_softc *sc = (struct ath_softc *)data; 358 struct ath_beacon_config *cur_conf = &sc->cur_beacon_conf; 359 struct ath_hw *ah = sc->sc_ah; 360 struct ath_common *common = ath9k_hw_common(ah); 361 struct ath_buf *bf = NULL; 362 struct ieee80211_vif *vif; 363 int slot; 364 u32 bfaddr, bc = 0; 365 366 /* 367 * Check if the previous beacon has gone out. If 368 * not don't try to post another, skip this period 369 * and wait for the next. Missed beacons indicate 370 * a problem and should not occur. If we miss too 371 * many consecutive beacons reset the device. 372 */ 373 if (ath9k_hw_numtxpending(ah, sc->beacon.beaconq) != 0) { 374 sc->beacon.bmisscnt++; 375 376 if (sc->beacon.bmisscnt < BSTUCK_THRESH * sc->nbcnvifs) { 377 ath_dbg(common, ATH_DBG_BSTUCK, 378 "missed %u consecutive beacons\n", 379 sc->beacon.bmisscnt); 380 ath9k_hw_stop_dma_queue(ah, sc->beacon.beaconq); 381 if (sc->beacon.bmisscnt > 3) 382 ath9k_hw_bstuck_nfcal(ah); 383 } else if (sc->beacon.bmisscnt >= BSTUCK_THRESH) { 384 ath_dbg(common, ATH_DBG_BSTUCK, 385 "beacon is officially stuck\n"); 386 sc->sc_flags |= SC_OP_TSF_RESET; 387 ath_reset(sc, true); 388 } 389 390 return; 391 } 392 393 /* 394 * Generate beacon frames. we are sending frames 395 * staggered so calculate the slot for this frame based 396 * on the tsf to safeguard against missing an swba. 397 */ 398 399 400 if (ah->opmode == NL80211_IFTYPE_AP) { 401 u16 intval; 402 u32 tsftu; 403 u64 tsf; 404 405 intval = cur_conf->beacon_interval ? : ATH_DEFAULT_BINTVAL; 406 tsf = ath9k_hw_gettsf64(ah); 407 tsf += TU_TO_USEC(ah->config.sw_beacon_response_time); 408 tsftu = TSF_TO_TU((tsf * ATH_BCBUF) >>32, tsf * ATH_BCBUF); 409 slot = (tsftu % (intval * ATH_BCBUF)) / intval; 410 vif = sc->beacon.bslot[slot]; 411 412 ath_dbg(common, ATH_DBG_BEACON, 413 "slot %d [tsf %llu tsftu %u intval %u] vif %p\n", 414 slot, tsf, tsftu / ATH_BCBUF, intval, vif); 415 } else { 416 slot = 0; 417 vif = sc->beacon.bslot[slot]; 418 } 419 420 421 bfaddr = 0; 422 if (vif) { 423 bf = ath_beacon_generate(sc->hw, vif); 424 if (bf != NULL) { 425 bfaddr = bf->bf_daddr; 426 bc = 1; 427 } 428 429 if (sc->beacon.bmisscnt != 0) { 430 ath_dbg(common, ATH_DBG_BSTUCK, 431 "resume beacon xmit after %u misses\n", 432 sc->beacon.bmisscnt); 433 sc->beacon.bmisscnt = 0; 434 } 435 } 436 437 /* 438 * Handle slot time change when a non-ERP station joins/leaves 439 * an 11g network. The 802.11 layer notifies us via callback, 440 * we mark updateslot, then wait one beacon before effecting 441 * the change. This gives associated stations at least one 442 * beacon interval to note the state change. 443 * 444 * NB: The slot time change state machine is clocked according 445 * to whether we are bursting or staggering beacons. We 446 * recognize the request to update and record the current 447 * slot then don't transition until that slot is reached 448 * again. If we miss a beacon for that slot then we'll be 449 * slow to transition but we'll be sure at least one beacon 450 * interval has passed. When bursting slot is always left 451 * set to ATH_BCBUF so this check is a noop. 452 */ 453 if (sc->beacon.updateslot == UPDATE) { 454 sc->beacon.updateslot = COMMIT; /* commit next beacon */ 455 sc->beacon.slotupdate = slot; 456 } else if (sc->beacon.updateslot == COMMIT && sc->beacon.slotupdate == slot) { 457 ah->slottime = sc->beacon.slottime; 458 ath9k_hw_init_global_settings(ah); 459 sc->beacon.updateslot = OK; 460 } 461 if (bfaddr != 0) { 462 /* NB: cabq traffic should already be queued and primed */ 463 ath9k_hw_puttxbuf(ah, sc->beacon.beaconq, bfaddr); 464 ath9k_hw_txstart(ah, sc->beacon.beaconq); 465 466 sc->beacon.ast_be_xmit += bc; /* XXX per-vif? */ 467 } 468} 469 470static void ath9k_beacon_init(struct ath_softc *sc, 471 u32 next_beacon, 472 u32 beacon_period) 473{ 474 if (sc->sc_flags & SC_OP_TSF_RESET) { 475 ath9k_ps_wakeup(sc); 476 ath9k_hw_reset_tsf(sc->sc_ah); 477 } 478 479 ath9k_hw_beaconinit(sc->sc_ah, next_beacon, beacon_period); 480 481 if (sc->sc_flags & SC_OP_TSF_RESET) { 482 ath9k_ps_restore(sc); 483 sc->sc_flags &= ~SC_OP_TSF_RESET; 484 } 485} 486 487/* 488 * For multi-bss ap support beacons are either staggered evenly over N slots or 489 * burst together. For the former arrange for the SWBA to be delivered for each 490 * slot. Slots that are not occupied will generate nothing. 491 */ 492static void ath_beacon_config_ap(struct ath_softc *sc, 493 struct ath_beacon_config *conf) 494{ 495 struct ath_hw *ah = sc->sc_ah; 496 u32 nexttbtt, intval; 497 498 /* NB: the beacon interval is kept internally in TU's */ 499 intval = TU_TO_USEC(conf->beacon_interval & ATH9K_BEACON_PERIOD); 500 intval /= ATH_BCBUF; /* for staggered beacons */ 501 nexttbtt = intval; 502 503 /* 504 * In AP mode we enable the beacon timers and SWBA interrupts to 505 * prepare beacon frames. 506 */ 507 ah->imask |= ATH9K_INT_SWBA; 508 ath_beaconq_config(sc); 509 510 /* Set the computed AP beacon timers */ 511 512 ath9k_hw_disable_interrupts(ah); 513 ath9k_beacon_init(sc, nexttbtt, intval); 514 sc->beacon.bmisscnt = 0; 515 ath9k_hw_set_interrupts(ah, ah->imask); 516} 517 518/* 519 * This sets up the beacon timers according to the timestamp of the last 520 * received beacon and the current TSF, configures PCF and DTIM 521 * handling, programs the sleep registers so the hardware will wakeup in 522 * time to receive beacons, and configures the beacon miss handling so 523 * we'll receive a BMISS interrupt when we stop seeing beacons from the AP 524 * we've associated with. 525 */ 526static void ath_beacon_config_sta(struct ath_softc *sc, 527 struct ath_beacon_config *conf) 528{ 529 struct ath_hw *ah = sc->sc_ah; 530 struct ath_common *common = ath9k_hw_common(ah); 531 struct ath9k_beacon_state bs; 532 int dtimperiod, dtimcount, sleepduration; 533 int cfpperiod, cfpcount; 534 u32 nexttbtt = 0, intval, tsftu; 535 u64 tsf; 536 int num_beacons, offset, dtim_dec_count, cfp_dec_count; 537 538 /* No need to configure beacon if we are not associated */ 539 if (!common->curaid) { 540 ath_dbg(common, ATH_DBG_BEACON, 541 "STA is not yet associated..skipping beacon config\n"); 542 return; 543 } 544 545 memset(&bs, 0, sizeof(bs)); 546 intval = conf->beacon_interval & ATH9K_BEACON_PERIOD; 547 548 /* 549 * Setup dtim and cfp parameters according to 550 * last beacon we received (which may be none). 551 */ 552 dtimperiod = conf->dtim_period; 553 dtimcount = conf->dtim_count; 554 if (dtimcount >= dtimperiod) /* NB: sanity check */ 555 dtimcount = 0; 556 cfpperiod = 1; /* NB: no PCF support yet */ 557 cfpcount = 0; 558 559 sleepduration = conf->listen_interval * intval; 560 561 /* 562 * Pull nexttbtt forward to reflect the current 563 * TSF and calculate dtim+cfp state for the result. 564 */ 565 tsf = ath9k_hw_gettsf64(ah); 566 tsftu = TSF_TO_TU(tsf>>32, tsf) + FUDGE; 567 568 num_beacons = tsftu / intval + 1; 569 offset = tsftu % intval; 570 nexttbtt = tsftu - offset; 571 if (offset) 572 nexttbtt += intval; 573 574 /* DTIM Beacon every dtimperiod Beacon */ 575 dtim_dec_count = num_beacons % dtimperiod; 576 /* CFP every cfpperiod DTIM Beacon */ 577 cfp_dec_count = (num_beacons / dtimperiod) % cfpperiod; 578 if (dtim_dec_count) 579 cfp_dec_count++; 580 581 dtimcount -= dtim_dec_count; 582 if (dtimcount < 0) 583 dtimcount += dtimperiod; 584 585 cfpcount -= cfp_dec_count; 586 if (cfpcount < 0) 587 cfpcount += cfpperiod; 588 589 bs.bs_intval = intval; 590 bs.bs_nexttbtt = nexttbtt; 591 bs.bs_dtimperiod = dtimperiod*intval; 592 bs.bs_nextdtim = bs.bs_nexttbtt + dtimcount*intval; 593 bs.bs_cfpperiod = cfpperiod*bs.bs_dtimperiod; 594 bs.bs_cfpnext = bs.bs_nextdtim + cfpcount*bs.bs_dtimperiod; 595 bs.bs_cfpmaxduration = 0; 596 597 /* 598 * Calculate the number of consecutive beacons to miss* before taking 599 * a BMISS interrupt. The configuration is specified in TU so we only 600 * need calculate based on the beacon interval. Note that we clamp the 601 * result to at most 15 beacons. 602 */ 603 if (sleepduration > intval) { 604 bs.bs_bmissthreshold = conf->listen_interval * 605 ATH_DEFAULT_BMISS_LIMIT / 2; 606 } else { 607 bs.bs_bmissthreshold = DIV_ROUND_UP(conf->bmiss_timeout, intval); 608 if (bs.bs_bmissthreshold > 15) 609 bs.bs_bmissthreshold = 15; 610 else if (bs.bs_bmissthreshold <= 0) 611 bs.bs_bmissthreshold = 1; 612 } 613 614 /* 615 * Calculate sleep duration. The configuration is given in ms. 616 * We ensure a multiple of the beacon period is used. Also, if the sleep 617 * duration is greater than the DTIM period then it makes senses 618 * to make it a multiple of that. 619 * 620 * XXX fixed at 100ms 621 */ 622 623 bs.bs_sleepduration = roundup(IEEE80211_MS_TO_TU(100), sleepduration); 624 if (bs.bs_sleepduration > bs.bs_dtimperiod) 625 bs.bs_sleepduration = bs.bs_dtimperiod; 626 627 /* TSF out of range threshold fixed at 1 second */ 628 bs.bs_tsfoor_threshold = ATH9K_TSFOOR_THRESHOLD; 629 630 ath_dbg(common, ATH_DBG_BEACON, "tsf: %llu tsftu: %u\n", tsf, tsftu); 631 ath_dbg(common, ATH_DBG_BEACON, 632 "bmiss: %u sleep: %u cfp-period: %u maxdur: %u next: %u\n", 633 bs.bs_bmissthreshold, bs.bs_sleepduration, 634 bs.bs_cfpperiod, bs.bs_cfpmaxduration, bs.bs_cfpnext); 635 636 /* Set the computed STA beacon timers */ 637 638 ath9k_hw_disable_interrupts(ah); 639 ath9k_hw_set_sta_beacon_timers(ah, &bs); 640 ah->imask |= ATH9K_INT_BMISS; 641 642 /* 643 * If the beacon config is called beacause of TSFOOR, 644 * Interrupts will be enabled back at the end of ath9k_tasklet 645 */ 646 if (!(sc->ps_flags & PS_TSFOOR_SYNC)) 647 ath9k_hw_set_interrupts(ah, ah->imask); 648} 649 650static void ath_beacon_config_adhoc(struct ath_softc *sc, 651 struct ath_beacon_config *conf) 652{ 653 struct ath_hw *ah = sc->sc_ah; 654 struct ath_common *common = ath9k_hw_common(ah); 655 u32 tsf, delta, intval, nexttbtt; 656 657 ath9k_reset_beacon_status(sc); 658 659 tsf = ath9k_hw_gettsf32(ah) + TU_TO_USEC(FUDGE); 660 intval = TU_TO_USEC(conf->beacon_interval & ATH9K_BEACON_PERIOD); 661 662 if (!sc->beacon.bc_tstamp) 663 nexttbtt = tsf + intval; 664 else { 665 if (tsf > sc->beacon.bc_tstamp) 666 delta = (tsf - sc->beacon.bc_tstamp); 667 else 668 delta = (tsf + 1 + (~0U - sc->beacon.bc_tstamp)); 669 nexttbtt = tsf + intval - (delta % intval); 670 } 671 672 ath_dbg(common, ATH_DBG_BEACON, 673 "IBSS nexttbtt %u intval %u (%u)\n", 674 nexttbtt, intval, conf->beacon_interval); 675 676 /* 677 * In IBSS mode enable the beacon timers but only enable SWBA interrupts 678 * if we need to manually prepare beacon frames. Otherwise we use a 679 * self-linked tx descriptor and let the hardware deal with things. 680 */ 681 ah->imask |= ATH9K_INT_SWBA; 682 683 ath_beaconq_config(sc); 684 685 /* Set the computed ADHOC beacon timers */ 686 687 ath9k_hw_disable_interrupts(ah); 688 ath9k_beacon_init(sc, nexttbtt, intval); 689 sc->beacon.bmisscnt = 0; 690 /* 691 * If the beacon config is called beacause of TSFOOR, 692 * Interrupts will be enabled back at the end of ath9k_tasklet 693 */ 694 if (!(sc->ps_flags & PS_TSFOOR_SYNC)) 695 ath9k_hw_set_interrupts(ah, ah->imask); 696} 697 698static bool ath9k_allow_beacon_config(struct ath_softc *sc, 699 struct ieee80211_vif *vif) 700{ 701 struct ath_beacon_config *cur_conf = &sc->cur_beacon_conf; 702 struct ath_common *common = ath9k_hw_common(sc->sc_ah); 703 struct ieee80211_bss_conf *bss_conf = &vif->bss_conf; 704 struct ath_vif *avp = (void *)vif->drv_priv; 705 706 /* 707 * Can not have different beacon interval on multiple 708 * AP interface case 709 */ 710 if ((sc->sc_ah->opmode == NL80211_IFTYPE_AP) && 711 (sc->nbcnvifs > 1) && 712 (vif->type == NL80211_IFTYPE_AP) && 713 (cur_conf->beacon_interval != bss_conf->beacon_int)) { 714 ath_dbg(common, ATH_DBG_CONFIG, 715 "Changing beacon interval of multiple \ 716 AP interfaces !\n"); 717 return false; 718 } 719 /* 720 * Can not configure station vif's beacon config 721 * while on AP opmode 722 */ 723 if ((sc->sc_ah->opmode == NL80211_IFTYPE_AP) && 724 (vif->type != NL80211_IFTYPE_AP)) { 725 ath_dbg(common, ATH_DBG_CONFIG, 726 "STA vif's beacon not allowed on AP mode\n"); 727 return false; 728 } 729 /* 730 * Do not allow beacon config if HW was already configured 731 * with another STA vif 732 */ 733 if ((sc->sc_ah->opmode == NL80211_IFTYPE_STATION) && 734 (vif->type == NL80211_IFTYPE_STATION) && 735 (sc->sc_flags & SC_OP_BEACONS) && 736 !avp->primary_sta_vif) { 737 ath_dbg(common, ATH_DBG_CONFIG, 738 "Beacon already configured for a station interface\n"); 739 return false; 740 } 741 return true; 742} 743 744void ath_beacon_config(struct ath_softc *sc, struct ieee80211_vif *vif) 745{ 746 struct ath_beacon_config *cur_conf = &sc->cur_beacon_conf; 747 struct ieee80211_bss_conf *bss_conf = &vif->bss_conf; 748 749 if (!ath9k_allow_beacon_config(sc, vif)) 750 return; 751 752 /* Setup the beacon configuration parameters */ 753 cur_conf->beacon_interval = bss_conf->beacon_int; 754 cur_conf->dtim_period = bss_conf->dtim_period; 755 cur_conf->listen_interval = 1; 756 cur_conf->dtim_count = 1; 757 cur_conf->bmiss_timeout = 758 ATH_DEFAULT_BMISS_LIMIT * cur_conf->beacon_interval; 759 760 /* 761 * It looks like mac80211 may end up using beacon interval of zero in 762 * some cases (at least for mesh point). Avoid getting into an 763 * infinite loop by using a bit safer value instead. To be safe, 764 * do sanity check on beacon interval for all operating modes. 765 */ 766 if (cur_conf->beacon_interval == 0) 767 cur_conf->beacon_interval = 100; 768 769 /* 770 * We don't parse dtim period from mac80211 during the driver 771 * initialization as it breaks association with hidden-ssid 772 * AP and it causes latency in roaming 773 */ 774 if (cur_conf->dtim_period == 0) 775 cur_conf->dtim_period = 1; 776 777 ath_set_beacon(sc); 778} 779 780static bool ath_has_valid_bslot(struct ath_softc *sc) 781{ 782 struct ath_vif *avp; 783 int slot; 784 bool found = false; 785 786 for (slot = 0; slot < ATH_BCBUF; slot++) { 787 if (sc->beacon.bslot[slot]) { 788 avp = (void *)sc->beacon.bslot[slot]->drv_priv; 789 if (avp->is_bslot_active) { 790 found = true; 791 break; 792 } 793 } 794 } 795 return found; 796} 797 798 799void ath_set_beacon(struct ath_softc *sc) 800{ 801 struct ath_common *common = ath9k_hw_common(sc->sc_ah); 802 struct ath_beacon_config *cur_conf = &sc->cur_beacon_conf; 803 804 switch (sc->sc_ah->opmode) { 805 case NL80211_IFTYPE_AP: 806 if (ath_has_valid_bslot(sc)) 807 ath_beacon_config_ap(sc, cur_conf); 808 break; 809 case NL80211_IFTYPE_ADHOC: 810 case NL80211_IFTYPE_MESH_POINT: 811 ath_beacon_config_adhoc(sc, cur_conf); 812 break; 813 case NL80211_IFTYPE_STATION: 814 ath_beacon_config_sta(sc, cur_conf); 815 break; 816 default: 817 ath_dbg(common, ATH_DBG_CONFIG, 818 "Unsupported beaconing mode\n"); 819 return; 820 } 821 822 sc->sc_flags |= SC_OP_BEACONS; 823} 824 825void ath9k_set_beaconing_status(struct ath_softc *sc, bool status) 826{ 827 struct ath_hw *ah = sc->sc_ah; 828 829 if (!ath_has_valid_bslot(sc)) 830 return; 831 832 ath9k_ps_wakeup(sc); 833 if (status) { 834 /* Re-enable beaconing */ 835 ah->imask |= ATH9K_INT_SWBA; 836 ath9k_hw_set_interrupts(ah, ah->imask); 837 } else { 838 /* Disable SWBA interrupt */ 839 ah->imask &= ~ATH9K_INT_SWBA; 840 ath9k_hw_set_interrupts(ah, ah->imask); 841 tasklet_kill(&sc->bcon_tasklet); 842 ath9k_hw_stop_dma_queue(ah, sc->beacon.beaconq); 843 } 844 ath9k_ps_restore(sc); 845} 846