ar5210_misc.c revision 185377
1185377Ssam/* 2185377Ssam * Copyright (c) 2002-2008 Sam Leffler, Errno Consulting 3185377Ssam * Copyright (c) 2002-2004 Atheros Communications, Inc. 4185377Ssam * 5185377Ssam * Permission to use, copy, modify, and/or distribute this software for any 6185377Ssam * purpose with or without fee is hereby granted, provided that the above 7185377Ssam * copyright notice and this permission notice appear in all copies. 8185377Ssam * 9185377Ssam * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 10185377Ssam * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 11185377Ssam * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 12185377Ssam * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 13185377Ssam * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 14185377Ssam * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 15185377Ssam * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 16185377Ssam * 17185377Ssam * $Id: ar5210_misc.c,v 1.4 2008/11/10 04:08:02 sam Exp $ 18185377Ssam */ 19185377Ssam#include "opt_ah.h" 20185377Ssam 21185377Ssam#ifdef AH_SUPPORT_AR5210 22185377Ssam 23185377Ssam#include "ah.h" 24185377Ssam#include "ah_internal.h" 25185377Ssam 26185377Ssam#include "ar5210/ar5210.h" 27185377Ssam#include "ar5210/ar5210reg.h" 28185377Ssam#include "ar5210/ar5210phy.h" 29185377Ssam 30185377Ssam#define AR_NUM_GPIO 6 /* 6 GPIO bits */ 31185377Ssam#define AR_GPIOD_MASK 0x2f /* 6-bit mask */ 32185377Ssam 33185377Ssamvoid 34185377Ssamar5210GetMacAddress(struct ath_hal *ah, uint8_t *mac) 35185377Ssam{ 36185377Ssam struct ath_hal_5210 *ahp = AH5210(ah); 37185377Ssam 38185377Ssam OS_MEMCPY(mac, ahp->ah_macaddr, IEEE80211_ADDR_LEN); 39185377Ssam} 40185377Ssam 41185377SsamHAL_BOOL 42185377Ssamar5210SetMacAddress(struct ath_hal *ah, const uint8_t *mac) 43185377Ssam{ 44185377Ssam struct ath_hal_5210 *ahp = AH5210(ah); 45185377Ssam 46185377Ssam OS_MEMCPY(ahp->ah_macaddr, mac, IEEE80211_ADDR_LEN); 47185377Ssam return AH_TRUE; 48185377Ssam} 49185377Ssam 50185377Ssamvoid 51185377Ssamar5210GetBssIdMask(struct ath_hal *ah, uint8_t *mask) 52185377Ssam{ 53185377Ssam static const uint8_t ones[IEEE80211_ADDR_LEN] = 54185377Ssam { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff }; 55185377Ssam OS_MEMCPY(mask, ones, IEEE80211_ADDR_LEN); 56185377Ssam} 57185377Ssam 58185377SsamHAL_BOOL 59185377Ssamar5210SetBssIdMask(struct ath_hal *ah, const uint8_t *mask) 60185377Ssam{ 61185377Ssam return AH_FALSE; 62185377Ssam} 63185377Ssam 64185377Ssam/* 65185377Ssam * Read 16 bits of data from the specified EEPROM offset. 66185377Ssam */ 67185377SsamHAL_BOOL 68185377Ssamar5210EepromRead(struct ath_hal *ah, u_int off, uint16_t *data) 69185377Ssam{ 70185377Ssam (void) OS_REG_READ(ah, AR_EP_AIR(off)); /* activate read op */ 71185377Ssam if (!ath_hal_wait(ah, AR_EP_STA, 72185377Ssam AR_EP_STA_RDCMPLT | AR_EP_STA_RDERR, AR_EP_STA_RDCMPLT)) { 73185377Ssam HALDEBUG(ah, HAL_DEBUG_ANY, "%s: read failed for entry 0x%x\n", 74185377Ssam __func__, AR_EP_AIR(off)); 75185377Ssam return AH_FALSE; 76185377Ssam } 77185377Ssam *data = OS_REG_READ(ah, AR_EP_RDATA) & 0xffff; 78185377Ssam return AH_TRUE; 79185377Ssam} 80185377Ssam 81185377Ssam/* 82185377Ssam * Return the wireless modes (a,b,g,t) supported by hardware. 83185377Ssam * 84185377Ssam * This value is what is actually supported by the hardware 85185377Ssam * and is unaffected by regulatory/country code settings. 86185377Ssam * 87185377Ssam */ 88185377Ssamu_int 89185377Ssamar5210GetWirelessModes(struct ath_hal *ah) 90185377Ssam{ 91185377Ssam /* XXX could enable turbo mode but can't do all rates */ 92185377Ssam return HAL_MODE_11A; 93185377Ssam} 94185377Ssam 95185377Ssam/* 96185377Ssam * Called if RfKill is supported (according to EEPROM). Set the interrupt and 97185377Ssam * GPIO values so the ISR and can disable RF on a switch signal 98185377Ssam */ 99185377Ssamvoid 100185377Ssamar5210EnableRfKill(struct ath_hal *ah) 101185377Ssam{ 102185377Ssam uint16_t rfsilent = AH_PRIVATE(ah)->ah_rfsilent; 103185377Ssam int select = MS(rfsilent, AR_EEPROM_RFSILENT_GPIO_SEL); 104185377Ssam int polarity = MS(rfsilent, AR_EEPROM_RFSILENT_POLARITY); 105185377Ssam 106185377Ssam /* 107185377Ssam * If radio disable switch connection to GPIO bit 0 is enabled 108185377Ssam * program GPIO interrupt. 109185377Ssam * If rfkill bit on eeprom is 1, setupeeprommap routine has already 110185377Ssam * verified that it is a later version of eeprom, it has a place for 111185377Ssam * rfkill bit and it is set to 1, indicating that GPIO bit 0 hardware 112185377Ssam * connection is present. 113185377Ssam */ 114185377Ssam ar5210Gpio0SetIntr(ah, select, (ar5210GpioGet(ah, select) == polarity)); 115185377Ssam} 116185377Ssam 117185377Ssam/* 118185377Ssam * Configure GPIO Output lines 119185377Ssam */ 120185377SsamHAL_BOOL 121185377Ssamar5210GpioCfgOutput(struct ath_hal *ah, uint32_t gpio) 122185377Ssam{ 123185377Ssam HALASSERT(gpio < AR_NUM_GPIO); 124185377Ssam 125185377Ssam OS_REG_WRITE(ah, AR_GPIOCR, 126185377Ssam (OS_REG_READ(ah, AR_GPIOCR) &~ AR_GPIOCR_ALL(gpio)) 127185377Ssam | AR_GPIOCR_OUT1(gpio)); 128185377Ssam 129185377Ssam return AH_TRUE; 130185377Ssam} 131185377Ssam 132185377Ssam/* 133185377Ssam * Configure GPIO Input lines 134185377Ssam */ 135185377SsamHAL_BOOL 136185377Ssamar5210GpioCfgInput(struct ath_hal *ah, uint32_t gpio) 137185377Ssam{ 138185377Ssam HALASSERT(gpio < AR_NUM_GPIO); 139185377Ssam 140185377Ssam OS_REG_WRITE(ah, AR_GPIOCR, 141185377Ssam (OS_REG_READ(ah, AR_GPIOCR) &~ AR_GPIOCR_ALL(gpio)) 142185377Ssam | AR_GPIOCR_IN(gpio)); 143185377Ssam 144185377Ssam return AH_TRUE; 145185377Ssam} 146185377Ssam 147185377Ssam/* 148185377Ssam * Once configured for I/O - set output lines 149185377Ssam */ 150185377SsamHAL_BOOL 151185377Ssamar5210GpioSet(struct ath_hal *ah, uint32_t gpio, uint32_t val) 152185377Ssam{ 153185377Ssam uint32_t reg; 154185377Ssam 155185377Ssam HALASSERT(gpio < AR_NUM_GPIO); 156185377Ssam 157185377Ssam reg = OS_REG_READ(ah, AR_GPIODO); 158185377Ssam reg &= ~(1 << gpio); 159185377Ssam reg |= (val&1) << gpio; 160185377Ssam 161185377Ssam OS_REG_WRITE(ah, AR_GPIODO, reg); 162185377Ssam return AH_TRUE; 163185377Ssam} 164185377Ssam 165185377Ssam/* 166185377Ssam * Once configured for I/O - get input lines 167185377Ssam */ 168185377Ssamuint32_t 169185377Ssamar5210GpioGet(struct ath_hal *ah, uint32_t gpio) 170185377Ssam{ 171185377Ssam if (gpio < AR_NUM_GPIO) { 172185377Ssam uint32_t val = OS_REG_READ(ah, AR_GPIODI); 173185377Ssam val = ((val & AR_GPIOD_MASK) >> gpio) & 0x1; 174185377Ssam return val; 175185377Ssam } else { 176185377Ssam return 0xffffffff; 177185377Ssam } 178185377Ssam} 179185377Ssam 180185377Ssam/* 181185377Ssam * Set the GPIO 0 Interrupt 182185377Ssam */ 183185377Ssamvoid 184185377Ssamar5210Gpio0SetIntr(struct ath_hal *ah, u_int gpio, uint32_t ilevel) 185185377Ssam{ 186185377Ssam uint32_t val = OS_REG_READ(ah, AR_GPIOCR); 187185377Ssam 188185377Ssam /* Clear the bits that we will modify. */ 189185377Ssam val &= ~(AR_GPIOCR_INT_SEL(gpio) | AR_GPIOCR_INT_SELH | AR_GPIOCR_INT_ENA | 190185377Ssam AR_GPIOCR_ALL(gpio)); 191185377Ssam 192185377Ssam val |= AR_GPIOCR_INT_SEL(gpio) | AR_GPIOCR_INT_ENA; 193185377Ssam if (ilevel) 194185377Ssam val |= AR_GPIOCR_INT_SELH; 195185377Ssam 196185377Ssam /* Don't need to change anything for low level interrupt. */ 197185377Ssam OS_REG_WRITE(ah, AR_GPIOCR, val); 198185377Ssam 199185377Ssam /* Change the interrupt mask. */ 200185377Ssam ar5210SetInterrupts(ah, AH5210(ah)->ah_maskReg | HAL_INT_GPIO); 201185377Ssam} 202185377Ssam 203185377Ssam/* 204185377Ssam * Change the LED blinking pattern to correspond to the connectivity 205185377Ssam */ 206185377Ssamvoid 207185377Ssamar5210SetLedState(struct ath_hal *ah, HAL_LED_STATE state) 208185377Ssam{ 209185377Ssam uint32_t val; 210185377Ssam 211185377Ssam val = OS_REG_READ(ah, AR_PCICFG); 212185377Ssam switch (state) { 213185377Ssam case HAL_LED_INIT: 214185377Ssam val &= ~(AR_PCICFG_LED_PEND | AR_PCICFG_LED_ACT); 215185377Ssam break; 216185377Ssam case HAL_LED_RUN: 217185377Ssam /* normal blink when connected */ 218185377Ssam val &= ~AR_PCICFG_LED_PEND; 219185377Ssam val |= AR_PCICFG_LED_ACT; 220185377Ssam break; 221185377Ssam default: 222185377Ssam val |= AR_PCICFG_LED_PEND; 223185377Ssam val &= ~AR_PCICFG_LED_ACT; 224185377Ssam break; 225185377Ssam } 226185377Ssam OS_REG_WRITE(ah, AR_PCICFG, val); 227185377Ssam} 228185377Ssam 229185377Ssam/* 230185377Ssam * Return 1 or 2 for the corresponding antenna that is in use 231185377Ssam */ 232185377Ssamu_int 233185377Ssamar5210GetDefAntenna(struct ath_hal *ah) 234185377Ssam{ 235185377Ssam uint32_t val = OS_REG_READ(ah, AR_STA_ID1); 236185377Ssam return (val & AR_STA_ID1_DEFAULT_ANTENNA ? 2 : 1); 237185377Ssam} 238185377Ssam 239185377Ssamvoid 240185377Ssamar5210SetDefAntenna(struct ath_hal *ah, u_int antenna) 241185377Ssam{ 242185377Ssam uint32_t val = OS_REG_READ(ah, AR_STA_ID1); 243185377Ssam 244185377Ssam if (antenna != (val & AR_STA_ID1_DEFAULT_ANTENNA ? 2 : 1)) { 245185377Ssam /* 246185377Ssam * Antenna change requested, force a toggle of the default. 247185377Ssam */ 248185377Ssam OS_REG_WRITE(ah, AR_STA_ID1, val | AR_STA_ID1_DEFAULT_ANTENNA); 249185377Ssam } 250185377Ssam} 251185377Ssam 252185377SsamHAL_ANT_SETTING 253185377Ssamar5210GetAntennaSwitch(struct ath_hal *ah) 254185377Ssam{ 255185377Ssam return HAL_ANT_VARIABLE; 256185377Ssam} 257185377Ssam 258185377SsamHAL_BOOL 259185377Ssamar5210SetAntennaSwitch(struct ath_hal *ah, HAL_ANT_SETTING settings) 260185377Ssam{ 261185377Ssam /* XXX not sure how to fix antenna */ 262185377Ssam return (settings == HAL_ANT_VARIABLE); 263185377Ssam} 264185377Ssam 265185377Ssam/* 266185377Ssam * Change association related fields programmed into the hardware. 267185377Ssam * Writing a valid BSSID to the hardware effectively enables the hardware 268185377Ssam * to synchronize its TSF to the correct beacons and receive frames coming 269185377Ssam * from that BSSID. It is called by the SME JOIN operation. 270185377Ssam */ 271185377Ssamvoid 272185377Ssamar5210WriteAssocid(struct ath_hal *ah, const uint8_t *bssid, uint16_t assocId) 273185377Ssam{ 274185377Ssam struct ath_hal_5210 *ahp = AH5210(ah); 275185377Ssam 276185377Ssam /* XXX save bssid for possible re-use on reset */ 277185377Ssam OS_MEMCPY(ahp->ah_bssid, bssid, IEEE80211_ADDR_LEN); 278185377Ssam OS_REG_WRITE(ah, AR_BSS_ID0, LE_READ_4(ahp->ah_bssid)); 279185377Ssam OS_REG_WRITE(ah, AR_BSS_ID1, LE_READ_2(ahp->ah_bssid+4) | 280185377Ssam ((assocId & 0x3fff)<<AR_BSS_ID1_AID_S)); 281185377Ssam if (assocId == 0) 282185377Ssam OS_REG_SET_BIT(ah, AR_STA_ID1, AR_STA_ID1_NO_PSPOLL); 283185377Ssam else 284185377Ssam OS_REG_CLR_BIT(ah, AR_STA_ID1, AR_STA_ID1_NO_PSPOLL); 285185377Ssam} 286185377Ssam 287185377Ssam/* 288185377Ssam * Get the current hardware tsf for stamlme. 289185377Ssam */ 290185377Ssamuint64_t 291185377Ssamar5210GetTsf64(struct ath_hal *ah) 292185377Ssam{ 293185377Ssam uint32_t low1, low2, u32; 294185377Ssam 295185377Ssam /* sync multi-word read */ 296185377Ssam low1 = OS_REG_READ(ah, AR_TSF_L32); 297185377Ssam u32 = OS_REG_READ(ah, AR_TSF_U32); 298185377Ssam low2 = OS_REG_READ(ah, AR_TSF_L32); 299185377Ssam if (low2 < low1) { /* roll over */ 300185377Ssam /* 301185377Ssam * If we are not preempted this will work. If we are 302185377Ssam * then we re-reading AR_TSF_U32 does no good as the 303185377Ssam * low bits will be meaningless. Likewise reading 304185377Ssam * L32, U32, U32, then comparing the last two reads 305185377Ssam * to check for rollover 306185377Ssam * doesn't help if preempted--so we take this approach 307185377Ssam * as it costs one less PCI read which can be noticeable 308185377Ssam * when doing things like timestamping packets in 309185377Ssam * monitor mode. 310185377Ssam */ 311185377Ssam u32++; 312185377Ssam } 313185377Ssam return (((uint64_t) u32) << 32) | ((uint64_t) low2); 314185377Ssam} 315185377Ssam 316185377Ssam/* 317185377Ssam * Get the current hardware tsf for stamlme. 318185377Ssam */ 319185377Ssamuint32_t 320185377Ssamar5210GetTsf32(struct ath_hal *ah) 321185377Ssam{ 322185377Ssam return OS_REG_READ(ah, AR_TSF_L32); 323185377Ssam} 324185377Ssam 325185377Ssam/* 326185377Ssam * Reset the current hardware tsf for stamlme 327185377Ssam */ 328185377Ssamvoid 329185377Ssamar5210ResetTsf(struct ath_hal *ah) 330185377Ssam{ 331185377Ssam uint32_t val = OS_REG_READ(ah, AR_BEACON); 332185377Ssam 333185377Ssam OS_REG_WRITE(ah, AR_BEACON, val | AR_BEACON_RESET_TSF); 334185377Ssam} 335185377Ssam 336185377Ssam/* 337185377Ssam * Grab a semi-random value from hardware registers - may not 338185377Ssam * change often 339185377Ssam */ 340185377Ssamuint32_t 341185377Ssamar5210GetRandomSeed(struct ath_hal *ah) 342185377Ssam{ 343185377Ssam uint32_t nf; 344185377Ssam 345185377Ssam nf = (OS_REG_READ(ah, AR_PHY_BASE + (25 << 2)) >> 19) & 0x1ff; 346185377Ssam if (nf & 0x100) 347185377Ssam nf = 0 - ((nf ^ 0x1ff) + 1); 348185377Ssam return (OS_REG_READ(ah, AR_TSF_U32) ^ 349185377Ssam OS_REG_READ(ah, AR_TSF_L32) ^ nf); 350185377Ssam} 351185377Ssam 352185377Ssam/* 353185377Ssam * Detect if our card is present 354185377Ssam */ 355185377SsamHAL_BOOL 356185377Ssamar5210DetectCardPresent(struct ath_hal *ah) 357185377Ssam{ 358185377Ssam /* 359185377Ssam * Read the Silicon Revision register and compare that 360185377Ssam * to what we read at attach time. If the same, we say 361185377Ssam * a card/device is present. 362185377Ssam */ 363185377Ssam return (AH_PRIVATE(ah)->ah_macRev == (OS_REG_READ(ah, AR_SREV) & 0xff)); 364185377Ssam} 365185377Ssam 366185377Ssam/* 367185377Ssam * Update MIB Counters 368185377Ssam */ 369185377Ssamvoid 370185377Ssamar5210UpdateMibCounters(struct ath_hal *ah, HAL_MIB_STATS *stats) 371185377Ssam{ 372185377Ssam stats->ackrcv_bad += OS_REG_READ(ah, AR_ACK_FAIL); 373185377Ssam stats->rts_bad += OS_REG_READ(ah, AR_RTS_FAIL); 374185377Ssam stats->fcs_bad += OS_REG_READ(ah, AR_FCS_FAIL); 375185377Ssam stats->rts_good += OS_REG_READ(ah, AR_RTS_OK); 376185377Ssam stats->beacons += OS_REG_READ(ah, AR_BEACON_CNT); 377185377Ssam} 378185377Ssam 379185377SsamHAL_BOOL 380185377Ssamar5210SetSifsTime(struct ath_hal *ah, u_int us) 381185377Ssam{ 382185377Ssam struct ath_hal_5210 *ahp = AH5210(ah); 383185377Ssam 384185377Ssam if (us > ath_hal_mac_usec(ah, 0x7ff)) { 385185377Ssam HALDEBUG(ah, HAL_DEBUG_ANY, "%s: bad SIFS time %u\n", 386185377Ssam __func__, us); 387185377Ssam ahp->ah_sifstime = (u_int) -1; /* restore default handling */ 388185377Ssam return AH_FALSE; 389185377Ssam } else { 390185377Ssam /* convert to system clocks */ 391185377Ssam OS_REG_RMW_FIELD(ah, AR_IFS0, AR_IFS0_SIFS, 392185377Ssam ath_hal_mac_clks(ah, us)); 393185377Ssam ahp->ah_sifstime = us; 394185377Ssam return AH_TRUE; 395185377Ssam } 396185377Ssam} 397185377Ssam 398185377Ssamu_int 399185377Ssamar5210GetSifsTime(struct ath_hal *ah) 400185377Ssam{ 401185377Ssam u_int clks = OS_REG_READ(ah, AR_IFS0) & 0x7ff; 402185377Ssam return ath_hal_mac_usec(ah, clks); /* convert from system clocks */ 403185377Ssam} 404185377Ssam 405185377SsamHAL_BOOL 406185377Ssamar5210SetSlotTime(struct ath_hal *ah, u_int us) 407185377Ssam{ 408185377Ssam struct ath_hal_5210 *ahp = AH5210(ah); 409185377Ssam 410185377Ssam if (us < HAL_SLOT_TIME_9 || us > ath_hal_mac_usec(ah, 0xffff)) { 411185377Ssam HALDEBUG(ah, HAL_DEBUG_ANY, "%s: bad slot time %u\n", 412185377Ssam __func__, us); 413185377Ssam ahp->ah_slottime = (u_int) -1; /* restore default handling */ 414185377Ssam return AH_FALSE; 415185377Ssam } else { 416185377Ssam /* convert to system clocks */ 417185377Ssam OS_REG_WRITE(ah, AR_SLOT_TIME, ath_hal_mac_clks(ah, us)); 418185377Ssam ahp->ah_slottime = us; 419185377Ssam return AH_TRUE; 420185377Ssam } 421185377Ssam} 422185377Ssam 423185377Ssamu_int 424185377Ssamar5210GetSlotTime(struct ath_hal *ah) 425185377Ssam{ 426185377Ssam u_int clks = OS_REG_READ(ah, AR_SLOT_TIME) & 0xffff; 427185377Ssam return ath_hal_mac_usec(ah, clks); /* convert from system clocks */ 428185377Ssam} 429185377Ssam 430185377SsamHAL_BOOL 431185377Ssamar5210SetAckTimeout(struct ath_hal *ah, u_int us) 432185377Ssam{ 433185377Ssam struct ath_hal_5210 *ahp = AH5210(ah); 434185377Ssam 435185377Ssam if (us > ath_hal_mac_usec(ah, MS(0xffffffff, AR_TIME_OUT_ACK))) { 436185377Ssam HALDEBUG(ah, HAL_DEBUG_ANY, "%s: bad ack timeout %u\n", 437185377Ssam __func__, us); 438185377Ssam ahp->ah_acktimeout = (u_int) -1; /* restore default handling */ 439185377Ssam return AH_FALSE; 440185377Ssam } else { 441185377Ssam /* convert to system clocks */ 442185377Ssam OS_REG_RMW_FIELD(ah, AR_TIME_OUT, 443185377Ssam AR_TIME_OUT_ACK, ath_hal_mac_clks(ah, us)); 444185377Ssam ahp->ah_acktimeout = us; 445185377Ssam return AH_TRUE; 446185377Ssam } 447185377Ssam} 448185377Ssam 449185377Ssamu_int 450185377Ssamar5210GetAckTimeout(struct ath_hal *ah) 451185377Ssam{ 452185377Ssam u_int clks = MS(OS_REG_READ(ah, AR_TIME_OUT), AR_TIME_OUT_ACK); 453185377Ssam return ath_hal_mac_usec(ah, clks); /* convert from system clocks */ 454185377Ssam} 455185377Ssam 456185377Ssamu_int 457185377Ssamar5210GetAckCTSRate(struct ath_hal *ah) 458185377Ssam{ 459185377Ssam return ((AH5210(ah)->ah_staId1Defaults & AR_STA_ID1_ACKCTS_6MB) == 0); 460185377Ssam} 461185377Ssam 462185377SsamHAL_BOOL 463185377Ssamar5210SetAckCTSRate(struct ath_hal *ah, u_int high) 464185377Ssam{ 465185377Ssam struct ath_hal_5210 *ahp = AH5210(ah); 466185377Ssam 467185377Ssam if (high) { 468185377Ssam OS_REG_CLR_BIT(ah, AR_STA_ID1, AR_STA_ID1_ACKCTS_6MB); 469185377Ssam ahp->ah_staId1Defaults &= ~AR_STA_ID1_ACKCTS_6MB; 470185377Ssam } else { 471185377Ssam OS_REG_SET_BIT(ah, AR_STA_ID1, AR_STA_ID1_ACKCTS_6MB); 472185377Ssam ahp->ah_staId1Defaults |= AR_STA_ID1_ACKCTS_6MB; 473185377Ssam } 474185377Ssam return AH_TRUE; 475185377Ssam} 476185377Ssam 477185377SsamHAL_BOOL 478185377Ssamar5210SetCTSTimeout(struct ath_hal *ah, u_int us) 479185377Ssam{ 480185377Ssam struct ath_hal_5210 *ahp = AH5210(ah); 481185377Ssam 482185377Ssam if (us > ath_hal_mac_usec(ah, MS(0xffffffff, AR_TIME_OUT_CTS))) { 483185377Ssam HALDEBUG(ah, HAL_DEBUG_ANY, "%s: bad cts timeout %u\n", 484185377Ssam __func__, us); 485185377Ssam ahp->ah_ctstimeout = (u_int) -1; /* restore default handling */ 486185377Ssam return AH_FALSE; 487185377Ssam } else { 488185377Ssam /* convert to system clocks */ 489185377Ssam OS_REG_RMW_FIELD(ah, AR_TIME_OUT, 490185377Ssam AR_TIME_OUT_CTS, ath_hal_mac_clks(ah, us)); 491185377Ssam ahp->ah_ctstimeout = us; 492185377Ssam return AH_TRUE; 493185377Ssam } 494185377Ssam} 495185377Ssam 496185377Ssamu_int 497185377Ssamar5210GetCTSTimeout(struct ath_hal *ah) 498185377Ssam{ 499185377Ssam u_int clks = MS(OS_REG_READ(ah, AR_TIME_OUT), AR_TIME_OUT_CTS); 500185377Ssam return ath_hal_mac_usec(ah, clks); /* convert from system clocks */ 501185377Ssam} 502185377Ssam 503185377SsamHAL_BOOL 504185377Ssamar5210SetDecompMask(struct ath_hal *ah, uint16_t keyidx, int en) 505185377Ssam{ 506185377Ssam /* nothing to do */ 507185377Ssam return AH_TRUE; 508185377Ssam} 509185377Ssam 510185377Ssamvoid 511185377Ssamar5210SetCoverageClass(struct ath_hal *ah, uint8_t coverageclass, int now) 512185377Ssam{ 513185377Ssam} 514185377Ssam 515185377Ssam/* 516185377Ssam * Control Adaptive Noise Immunity Parameters 517185377Ssam */ 518185377SsamHAL_BOOL 519185377Ssamar5210AniControl(struct ath_hal *ah, HAL_ANI_CMD cmd, int param) 520185377Ssam{ 521185377Ssam return AH_FALSE; 522185377Ssam} 523185377Ssam 524185377Ssamvoid 525185377Ssamar5210AniPoll(struct ath_hal *ah, const HAL_NODE_STATS *stats, HAL_CHANNEL *chan) 526185377Ssam{ 527185377Ssam} 528185377Ssam 529185377Ssamvoid 530185377Ssamar5210MibEvent(struct ath_hal *ah, const HAL_NODE_STATS *stats) 531185377Ssam{ 532185377Ssam} 533185377Ssam 534185377Ssam#define AR_DIAG_SW_DIS_CRYPTO (AR_DIAG_SW_DIS_ENC | AR_DIAG_SW_DIS_DEC) 535185377Ssam 536185377SsamHAL_STATUS 537185377Ssamar5210GetCapability(struct ath_hal *ah, HAL_CAPABILITY_TYPE type, 538185377Ssam uint32_t capability, uint32_t *result) 539185377Ssam{ 540185377Ssam 541185377Ssam switch (type) { 542185377Ssam case HAL_CAP_CIPHER: /* cipher handled in hardware */ 543185377Ssam return (capability == HAL_CIPHER_WEP ? HAL_OK : HAL_ENOTSUPP); 544185377Ssam default: 545185377Ssam return ath_hal_getcapability(ah, type, capability, result); 546185377Ssam } 547185377Ssam} 548185377Ssam 549185377SsamHAL_BOOL 550185377Ssamar5210SetCapability(struct ath_hal *ah, HAL_CAPABILITY_TYPE type, 551185377Ssam uint32_t capability, uint32_t setting, HAL_STATUS *status) 552185377Ssam{ 553185377Ssam 554185377Ssam switch (type) { 555185377Ssam case HAL_CAP_DIAG: /* hardware diagnostic support */ 556185377Ssam /* 557185377Ssam * NB: could split this up into virtual capabilities, 558185377Ssam * (e.g. 1 => ACK, 2 => CTS, etc.) but it hardly 559185377Ssam * seems worth the additional complexity. 560185377Ssam */ 561185377Ssam#ifdef AH_DEBUG 562185377Ssam AH_PRIVATE(ah)->ah_diagreg = setting; 563185377Ssam#else 564185377Ssam AH_PRIVATE(ah)->ah_diagreg = setting & 0x6; /* ACK+CTS */ 565185377Ssam#endif 566185377Ssam OS_REG_WRITE(ah, AR_DIAG_SW, AH_PRIVATE(ah)->ah_diagreg); 567185377Ssam return AH_TRUE; 568185377Ssam case HAL_CAP_RXORN_FATAL: /* HAL_INT_RXORN treated as fatal */ 569185377Ssam return AH_FALSE; /* NB: disallow */ 570185377Ssam default: 571185377Ssam return ath_hal_setcapability(ah, type, capability, 572185377Ssam setting, status); 573185377Ssam } 574185377Ssam} 575185377Ssam 576185377SsamHAL_BOOL 577185377Ssamar5210GetDiagState(struct ath_hal *ah, int request, 578185377Ssam const void *args, uint32_t argsize, 579185377Ssam void **result, uint32_t *resultsize) 580185377Ssam{ 581185377Ssam#ifdef AH_PRIVATE_DIAG 582185377Ssam uint32_t pcicfg; 583185377Ssam HAL_BOOL ok; 584185377Ssam 585185377Ssam switch (request) { 586185377Ssam case HAL_DIAG_EEPROM: 587185377Ssam /* XXX */ 588185377Ssam break; 589185377Ssam case HAL_DIAG_EEREAD: 590185377Ssam if (argsize != sizeof(uint16_t)) 591185377Ssam return AH_FALSE; 592185377Ssam pcicfg = OS_REG_READ(ah, AR_PCICFG); 593185377Ssam OS_REG_WRITE(ah, AR_PCICFG, pcicfg | AR_PCICFG_EEPROMSEL); 594185377Ssam ok = ath_hal_eepromRead(ah, *(const uint16_t *)args, *result); 595185377Ssam OS_REG_WRITE(ah, AR_PCICFG, pcicfg); 596185377Ssam if (ok) 597185377Ssam *resultsize = sizeof(uint16_t); 598185377Ssam return ok; 599185377Ssam } 600185377Ssam#endif 601185377Ssam return ath_hal_getdiagstate(ah, request, 602185377Ssam args, argsize, result, resultsize); 603185377Ssam} 604185377Ssam#endif /* AH_SUPPORT_AR5210 */ 605