beacon.c (348324c5b10bcba8d9daabdfb85a6927311be34f) | beacon.c (4ed15762dce67192d4662860470a8be1f6d5fd53) |
---|---|
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 --- 462 unchanged lines hidden (view full) --- 471 */ 472static void ath9k_beacon_config_sta(struct ath_softc *sc, 473 struct ath_beacon_config *conf) 474{ 475 struct ath_hw *ah = sc->sc_ah; 476 struct ath_common *common = ath9k_hw_common(ah); 477 struct ath9k_beacon_state bs; 478 int dtimperiod, dtimcount, sleepduration; | 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 --- 462 unchanged lines hidden (view full) --- 471 */ 472static void ath9k_beacon_config_sta(struct ath_softc *sc, 473 struct ath_beacon_config *conf) 474{ 475 struct ath_hw *ah = sc->sc_ah; 476 struct ath_common *common = ath9k_hw_common(ah); 477 struct ath9k_beacon_state bs; 478 int dtimperiod, dtimcount, sleepduration; |
479 int cfpperiod, cfpcount; | |
480 u32 nexttbtt = 0, intval, tsftu; 481 u64 tsf; | 479 u32 nexttbtt = 0, intval, tsftu; 480 u64 tsf; |
482 int num_beacons, offset, dtim_dec_count, cfp_dec_count; | 481 int num_beacons, offset, dtim_dec_count; |
483 484 /* No need to configure beacon if we are not associated */ 485 if (!test_bit(SC_OP_PRIM_STA_VIF, &sc->sc_flags)) { 486 ath_dbg(common, BEACON, 487 "STA is not yet associated..skipping beacon config\n"); 488 return; 489 } 490 491 memset(&bs, 0, sizeof(bs)); 492 intval = conf->beacon_interval; 493 494 /* | 482 483 /* No need to configure beacon if we are not associated */ 484 if (!test_bit(SC_OP_PRIM_STA_VIF, &sc->sc_flags)) { 485 ath_dbg(common, BEACON, 486 "STA is not yet associated..skipping beacon config\n"); 487 return; 488 } 489 490 memset(&bs, 0, sizeof(bs)); 491 intval = conf->beacon_interval; 492 493 /* |
495 * Setup dtim and cfp parameters according to | 494 * Setup dtim parameters according to |
496 * last beacon we received (which may be none). 497 */ 498 dtimperiod = conf->dtim_period; 499 dtimcount = conf->dtim_count; 500 if (dtimcount >= dtimperiod) /* NB: sanity check */ 501 dtimcount = 0; | 495 * last beacon we received (which may be none). 496 */ 497 dtimperiod = conf->dtim_period; 498 dtimcount = conf->dtim_count; 499 if (dtimcount >= dtimperiod) /* NB: sanity check */ 500 dtimcount = 0; |
502 cfpperiod = 1; /* NB: no PCF support yet */ 503 cfpcount = 0; | |
504 505 sleepduration = conf->listen_interval * intval; 506 507 /* 508 * Pull nexttbtt forward to reflect the current | 501 502 sleepduration = conf->listen_interval * intval; 503 504 /* 505 * Pull nexttbtt forward to reflect the current |
509 * TSF and calculate dtim+cfp state for the result. | 506 * TSF and calculate dtim state for the result. |
510 */ 511 tsf = ath9k_hw_gettsf64(ah); 512 tsftu = TSF_TO_TU(tsf>>32, tsf) + FUDGE; 513 514 num_beacons = tsftu / intval + 1; 515 offset = tsftu % intval; 516 nexttbtt = tsftu - offset; 517 if (offset) 518 nexttbtt += intval; 519 520 /* DTIM Beacon every dtimperiod Beacon */ 521 dtim_dec_count = num_beacons % dtimperiod; | 507 */ 508 tsf = ath9k_hw_gettsf64(ah); 509 tsftu = TSF_TO_TU(tsf>>32, tsf) + FUDGE; 510 511 num_beacons = tsftu / intval + 1; 512 offset = tsftu % intval; 513 nexttbtt = tsftu - offset; 514 if (offset) 515 nexttbtt += intval; 516 517 /* DTIM Beacon every dtimperiod Beacon */ 518 dtim_dec_count = num_beacons % dtimperiod; |
522 /* CFP every cfpperiod DTIM Beacon */ 523 cfp_dec_count = (num_beacons / dtimperiod) % cfpperiod; 524 if (dtim_dec_count) 525 cfp_dec_count++; 526 | |
527 dtimcount -= dtim_dec_count; 528 if (dtimcount < 0) 529 dtimcount += dtimperiod; 530 | 519 dtimcount -= dtim_dec_count; 520 if (dtimcount < 0) 521 dtimcount += dtimperiod; 522 |
531 cfpcount -= cfp_dec_count; 532 if (cfpcount < 0) 533 cfpcount += cfpperiod; | 523 bs.bs_intval = TU_TO_USEC(intval); 524 bs.bs_nexttbtt = TU_TO_USEC(nexttbtt); 525 bs.bs_dtimperiod = dtimperiod * bs.bs_intval; 526 bs.bs_nextdtim = bs.bs_nexttbtt + dtimcount * bs.bs_intval; |
534 | 527 |
535 bs.bs_intval = intval; 536 bs.bs_nexttbtt = nexttbtt; 537 bs.bs_dtimperiod = dtimperiod*intval; 538 bs.bs_nextdtim = bs.bs_nexttbtt + dtimcount*intval; 539 bs.bs_cfpperiod = cfpperiod*bs.bs_dtimperiod; 540 bs.bs_cfpnext = bs.bs_nextdtim + cfpcount*bs.bs_dtimperiod; 541 bs.bs_cfpmaxduration = 0; 542 | |
543 /* 544 * Calculate the number of consecutive beacons to miss* before taking 545 * a BMISS interrupt. The configuration is specified in TU so we only 546 * need calculate based on the beacon interval. Note that we clamp the 547 * result to at most 15 beacons. 548 */ 549 if (sleepduration > intval) { 550 bs.bs_bmissthreshold = conf->listen_interval * --- 10 unchanged lines hidden (view full) --- 561 * Calculate sleep duration. The configuration is given in ms. 562 * We ensure a multiple of the beacon period is used. Also, if the sleep 563 * duration is greater than the DTIM period then it makes senses 564 * to make it a multiple of that. 565 * 566 * XXX fixed at 100ms 567 */ 568 | 528 /* 529 * Calculate the number of consecutive beacons to miss* before taking 530 * a BMISS interrupt. The configuration is specified in TU so we only 531 * need calculate based on the beacon interval. Note that we clamp the 532 * result to at most 15 beacons. 533 */ 534 if (sleepduration > intval) { 535 bs.bs_bmissthreshold = conf->listen_interval * --- 10 unchanged lines hidden (view full) --- 546 * Calculate sleep duration. The configuration is given in ms. 547 * We ensure a multiple of the beacon period is used. Also, if the sleep 548 * duration is greater than the DTIM period then it makes senses 549 * to make it a multiple of that. 550 * 551 * XXX fixed at 100ms 552 */ 553 |
569 bs.bs_sleepduration = roundup(IEEE80211_MS_TO_TU(100), sleepduration); | 554 bs.bs_sleepduration = TU_TO_USEC(roundup(IEEE80211_MS_TO_TU(100), 555 sleepduration)); |
570 if (bs.bs_sleepduration > bs.bs_dtimperiod) 571 bs.bs_sleepduration = bs.bs_dtimperiod; 572 573 /* TSF out of range threshold fixed at 1 second */ 574 bs.bs_tsfoor_threshold = ATH9K_TSFOOR_THRESHOLD; 575 576 ath_dbg(common, BEACON, "tsf: %llu tsftu: %u\n", tsf, tsftu); | 556 if (bs.bs_sleepduration > bs.bs_dtimperiod) 557 bs.bs_sleepduration = bs.bs_dtimperiod; 558 559 /* TSF out of range threshold fixed at 1 second */ 560 bs.bs_tsfoor_threshold = ATH9K_TSFOOR_THRESHOLD; 561 562 ath_dbg(common, BEACON, "tsf: %llu tsftu: %u\n", tsf, tsftu); |
577 ath_dbg(common, BEACON, 578 "bmiss: %u sleep: %u cfp-period: %u maxdur: %u next: %u\n", 579 bs.bs_bmissthreshold, bs.bs_sleepduration, 580 bs.bs_cfpperiod, bs.bs_cfpmaxduration, bs.bs_cfpnext); | 563 ath_dbg(common, BEACON, "bmiss: %u sleep: %u\n", 564 bs.bs_bmissthreshold, bs.bs_sleepduration); |
581 582 /* Set the computed STA beacon timers */ 583 584 ath9k_hw_disable_interrupts(ah); 585 ath9k_hw_set_sta_beacon_timers(ah, &bs); 586 ah->imask |= ATH9K_INT_BMISS; 587 588 ath9k_hw_set_interrupts(ah); --- 199 unchanged lines hidden --- | 565 566 /* Set the computed STA beacon timers */ 567 568 ath9k_hw_disable_interrupts(ah); 569 ath9k_hw_set_sta_beacon_timers(ah, &bs); 570 ah->imask |= ATH9K_INT_BMISS; 571 572 ath9k_hw_set_interrupts(ah); --- 199 unchanged lines hidden --- |