1203945Sweongyo/*- 2203945Sweongyo * Copyright (c) 2009-2010 Weongyo Jeong <weongyo@freebsd.org> 3203945Sweongyo * All rights reserved. 4203945Sweongyo * 5203945Sweongyo * Redistribution and use in source and binary forms, with or without 6203945Sweongyo * modification, are permitted provided that the following conditions 7203945Sweongyo * are met: 8203945Sweongyo * 1. Redistributions of source code must retain the above copyright 9203945Sweongyo * notice, this list of conditions and the following disclaimer, 10203945Sweongyo * without modification. 11203945Sweongyo * 2. Redistributions in binary form must reproduce at minimum a disclaimer 12203945Sweongyo * similar to the "NO WARRANTY" disclaimer below ("Disclaimer") and any 13203945Sweongyo * redistribution must be conditioned upon including a substantially 14203945Sweongyo * similar Disclaimer requirement for further binary redistribution. 15203945Sweongyo * 16203945Sweongyo * NO WARRANTY 17203945Sweongyo * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 18203945Sweongyo * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 19203945Sweongyo * LIMITED TO, THE IMPLIED WARRANTIES OF NONINFRINGEMENT, MERCHANTIBILITY 20203945Sweongyo * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL 21203945Sweongyo * THE COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, 22203945Sweongyo * OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 23203945Sweongyo * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 24203945Sweongyo * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER 25203945Sweongyo * IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 26203945Sweongyo * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF 27203945Sweongyo * THE POSSIBILITY OF SUCH DAMAGES. 28203945Sweongyo * 29203945Sweongyo * $FreeBSD: stable/11/sys/dev/bwn/if_bwnvar.h 355454 2019-12-06 18:15:27Z brooks $ 30203945Sweongyo */ 31203945Sweongyo 32203945Sweongyo#ifndef _IF_BWNVAR_H 33203945Sweongyo#define _IF_BWNVAR_H 34203945Sweongyo 35203945Sweongyostruct siba_dev_softc; 36203945Sweongyostruct bwn_softc; 37203945Sweongyostruct bwn_mac; 38203945Sweongyo 39203945Sweongyo#define N(a) (sizeof(a) / sizeof(a[0])) 40203945Sweongyo#define BWN_ALIGN 0x1000 41203945Sweongyo#define BWN_BUS_SPACE_MAXADDR_30BIT 0x3fffffff 42203945Sweongyo#define BWN_RETRY_SHORT 7 43203945Sweongyo#define BWN_RETRY_LONG 4 44203945Sweongyo#define BWN_STAID_MAX 64 45203945Sweongyo#define BWN_TXPWR_IGNORE_TIME (1 << 0) 46203945Sweongyo#define BWN_TXPWR_IGNORE_TSSI (1 << 1) 47203945Sweongyo#define BWN_HAS_TXMAG(phy) \ 48203945Sweongyo (((phy)->rev >= 2) && ((phy)->rf_ver == 0x2050) && \ 49203945Sweongyo ((phy)->rf_rev == 8)) 50203945Sweongyo#define BWN_HAS_LOOPBACK(phy) \ 51203945Sweongyo (((phy)->rev > 1) || ((phy)->gmode)) 52203945Sweongyo#define BWN_TXERROR_MAX 1000 53203945Sweongyo#define BWN_GETTIME(v) do { \ 54203945Sweongyo struct timespec ts; \ 55203945Sweongyo nanouptime(&ts); \ 56203945Sweongyo (v) = ts.tv_nsec / 1000000 + ts.tv_sec * 1000; \ 57203945Sweongyo} while (0) 58203945Sweongyo#define BWN_ISOLDFMT(mac) ((mac)->mac_fw.rev <= 351) 59203945Sweongyo#define BWN_TSSI2DBM(num, den) \ 60203945Sweongyo ((int32_t)((num < 0) ? num / den : (num + den / 2) / den)) 61299790Sadrian#define BWN_HDRSIZE(mac) bwn_tx_hdrsize(mac) 62300075Sadrian#define BWN_MAXTXHDRSIZE (112 + (sizeof(struct bwn_plcp6))) 63299790Sadrian 64203945Sweongyo#define BWN_PIO_COOKIE(tq, tp) \ 65203945Sweongyo ((uint16_t)((((uint16_t)tq->tq_index + 1) << 12) | tp->tp_index)) 66203945Sweongyo#define BWN_DMA_COOKIE(dr, slot) \ 67203945Sweongyo ((uint16_t)(((uint16_t)dr->dr_index + 1) << 12) | (uint16_t)slot) 68204922Sweongyo#define BWN_READ_2(mac, o) (siba_read_2(mac->mac_sc->sc_dev, o)) 69204922Sweongyo#define BWN_READ_4(mac, o) (siba_read_4(mac->mac_sc->sc_dev, o)) 70204922Sweongyo#define BWN_WRITE_2(mac, o, v) \ 71204922Sweongyo (siba_write_2(mac->mac_sc->sc_dev, o, v)) 72299790Sadrian#define BWN_WRITE_2_F(mac, o, v) do { \ 73299790Sadrian (BWN_WRITE_2(mac, o, v)); \ 74299790Sadrian BWN_READ_2(mac, o); \ 75299790Sadrian} while(0) 76299790Sadrian#define BWN_WRITE_SETMASK2(mac, offset, mask, set) \ 77299790Sadrian BWN_WRITE_2(mac, offset, (BWN_READ_2(mac, offset) & mask) | set) 78204922Sweongyo#define BWN_WRITE_4(mac, o, v) \ 79204922Sweongyo (siba_write_4(mac->mac_sc->sc_dev, o, v)) 80299790Sadrian#define BWN_WRITE_SETMASK4(mac, offset, mask, set) \ 81299790Sadrian BWN_WRITE_4(mac, offset, (BWN_READ_4(mac, offset) & mask) | set) 82203945Sweongyo#define BWN_PIO_TXQOFFSET(mac) \ 83204922Sweongyo ((siba_get_revid(mac->mac_sc->sc_dev) >= 11) ? 0x18 : 0) 84203945Sweongyo#define BWN_PIO_RXQOFFSET(mac) \ 85204922Sweongyo ((siba_get_revid(mac->mac_sc->sc_dev) >= 11) ? 0x38 : 8) 86203945Sweongyo#define BWN_SEC_NEWAPI(mac) (mac->mac_fw.rev >= 351) 87203945Sweongyo#define BWN_SEC_KEY2FW(mac, idx) \ 88203945Sweongyo (BWN_SEC_NEWAPI(mac) ? idx : ((idx >= 4) ? idx - 4 : idx)) 89203945Sweongyo#define BWN_RF_READ(mac, r) (mac->mac_phy.rf_read(mac, r)) 90203945Sweongyo#define BWN_RF_WRITE(mac, r, v) (mac->mac_phy.rf_write(mac, r, v)) 91203945Sweongyo#define BWN_RF_MASK(mac, o, m) \ 92203945Sweongyo BWN_RF_WRITE(mac, o, BWN_RF_READ(mac, o) & m) 93203945Sweongyo#define BWN_RF_SETMASK(mac, offset, mask, set) \ 94203945Sweongyo BWN_RF_WRITE(mac, offset, (BWN_RF_READ(mac, offset) & mask) | set) 95203945Sweongyo#define BWN_RF_SET(mac, offset, set) \ 96203945Sweongyo BWN_RF_WRITE(mac, offset, BWN_RF_READ(mac, offset) | set) 97203945Sweongyo#define BWN_PHY_READ(mac, r) (mac->mac_phy.phy_read(mac, r)) 98203945Sweongyo#define BWN_PHY_WRITE(mac, r, v) \ 99203945Sweongyo (mac->mac_phy.phy_write(mac, r, v)) 100203945Sweongyo#define BWN_PHY_SET(mac, offset, set) do { \ 101203945Sweongyo if (mac->mac_phy.phy_maskset != NULL) { \ 102203945Sweongyo KASSERT(mac->mac_status < BWN_MAC_STATUS_INITED || \ 103203945Sweongyo mac->mac_suspended > 0, \ 104203945Sweongyo ("dont access PHY or RF registers after turning on MAC")); \ 105203945Sweongyo mac->mac_phy.phy_maskset(mac, offset, 0xffff, set); \ 106203945Sweongyo } else \ 107203945Sweongyo BWN_PHY_WRITE(mac, offset, \ 108203945Sweongyo BWN_PHY_READ(mac, offset) | (set)); \ 109203945Sweongyo} while (0) 110203945Sweongyo#define BWN_PHY_SETMASK(mac, offset, mask, set) do { \ 111203945Sweongyo if (mac->mac_phy.phy_maskset != NULL) { \ 112203945Sweongyo KASSERT(mac->mac_status < BWN_MAC_STATUS_INITED || \ 113203945Sweongyo mac->mac_suspended > 0, \ 114203945Sweongyo ("dont access PHY or RF registers after turning on MAC")); \ 115203945Sweongyo mac->mac_phy.phy_maskset(mac, offset, mask, set); \ 116203945Sweongyo } else \ 117203945Sweongyo BWN_PHY_WRITE(mac, offset, \ 118203945Sweongyo (BWN_PHY_READ(mac, offset) & (mask)) | (set)); \ 119203945Sweongyo} while (0) 120203945Sweongyo#define BWN_PHY_MASK(mac, offset, mask) do { \ 121203945Sweongyo if (mac->mac_phy.phy_maskset != NULL) { \ 122203945Sweongyo KASSERT(mac->mac_status < BWN_MAC_STATUS_INITED || \ 123203945Sweongyo mac->mac_suspended > 0, \ 124203945Sweongyo ("dont access PHY or RF registers after turning on MAC")); \ 125203945Sweongyo mac->mac_phy.phy_maskset(mac, offset, mask, 0); \ 126203945Sweongyo } else \ 127203945Sweongyo BWN_PHY_WRITE(mac, offset, \ 128355454Sbrooks BWN_PHY_READ(mac, offset) & (mask)); \ 129203945Sweongyo} while (0) 130203945Sweongyo#define BWN_PHY_COPY(mac, dst, src) do { \ 131203945Sweongyo KASSERT(mac->mac_status < BWN_MAC_STATUS_INITED || \ 132203945Sweongyo mac->mac_suspended > 0, \ 133203945Sweongyo ("dont access PHY or RF registers after turning on MAC")); \ 134203945Sweongyo BWN_PHY_WRITE(mac, dst, BWN_PHY_READ(mac, src)); \ 135203945Sweongyo} while (0) 136203945Sweongyo#define BWN_LO_CALIB_EXPIRE (1000 * (30 - 2)) 137203945Sweongyo#define BWN_LO_PWRVEC_EXPIRE (1000 * (30 - 2)) 138203945Sweongyo#define BWN_LO_TXCTL_EXPIRE (1000 * (180 - 4)) 139203945Sweongyo#define BWN_DMA_BIT_MASK(n) (((n) == 64) ? ~0ULL : ((1ULL<<(n))-1)) 140203945Sweongyo#define BWN_LPD(L, P, D) (((L) << 2) | ((P) << 1) | ((D) << 0)) 141203945Sweongyo#define BWN_BITREV4(tmp) (BWN_BITREV8(tmp) >> 4) 142203945Sweongyo#define BWN_BITREV8(byte) (bwn_bitrev_table[byte]) 143203945Sweongyo#define BWN_BBATTCMP(a, b) ((a)->att == (b)->att) 144203945Sweongyo#define BWN_RFATTCMP(a, b) \ 145203945Sweongyo (((a)->att == (b)->att) && ((a)->padmix == (b)->padmix)) 146203945Sweongyo#define BWN_PIO_WRITE_2(mac, tq, offset, value) \ 147203945Sweongyo BWN_WRITE_2(mac, (tq)->tq_base + offset, value) 148203945Sweongyo#define BWN_PIO_READ_4(mac, tq, offset) \ 149203945Sweongyo BWN_READ_4(mac, tq->tq_base + offset) 150203945Sweongyo#define BWN_ISCCKRATE(rate) \ 151203945Sweongyo (rate == BWN_CCK_RATE_1MB || rate == BWN_CCK_RATE_2MB || \ 152203945Sweongyo rate == BWN_CCK_RATE_5MB || rate == BWN_CCK_RATE_11MB) 153203945Sweongyo#define BWN_ISOFDMRATE(rate) (!BWN_ISCCKRATE(rate)) 154204922Sweongyo#define BWN_BARRIER(mac, flags) siba_barrier(mac->mac_sc->sc_dev, flags) 155203945Sweongyo#define BWN_DMA_READ(dr, offset) \ 156203945Sweongyo (BWN_READ_4(dr->dr_mac, dr->dr_base + offset)) 157203945Sweongyo#define BWN_DMA_WRITE(dr, offset, value) \ 158203945Sweongyo (BWN_WRITE_4(dr->dr_mac, dr->dr_base + offset, value)) 159203945Sweongyo 160299790Sadrian 161299790Sadriantypedef enum { 162299790Sadrian BWN_PHY_BAND_2G = 0, 163299790Sadrian BWN_PHY_BAND_5G_LO = 1, 164299790Sadrian BWN_PHY_BAND_5G_MI = 2, 165299790Sadrian BWN_PHY_BAND_5G_HI = 3 166299790Sadrian} bwn_phy_band_t; 167299790Sadrian 168299790Sadriantypedef enum { 169299790Sadrian BWN_BAND_2G, 170299790Sadrian BWN_BAND_5G, 171299790Sadrian} bwn_band_t; 172299790Sadrian 173299790Sadriantypedef enum { 174299790Sadrian BWN_CHAN_TYPE_20, 175299790Sadrian BWN_CHAN_TYPE_20_HT, 176299790Sadrian BWN_CHAN_TYPE_40_HT_U, 177299790Sadrian BWN_CHAN_TYPE_40_HT_D, 178299790Sadrian} bwn_chan_type_t; 179299790Sadrian 180203945Sweongyostruct bwn_rate { 181203945Sweongyo uint16_t rateid; 182203945Sweongyo uint32_t flags; 183203945Sweongyo}; 184203945Sweongyo 185203945Sweongyo#define BWN_ANT0 0 186203945Sweongyo#define BWN_ANT1 1 187203945Sweongyo#define BWN_ANTAUTO0 2 188203945Sweongyo#define BWN_ANTAUTO1 3 189203945Sweongyo#define BWN_ANT2 4 190203945Sweongyo#define BWN_ANT3 8 191203945Sweongyo#define BWN_ANTAUTO BWN_ANTAUTO0 192203945Sweongyo#define BWN_ANT_DEFAULT BWN_ANTAUTO 193203945Sweongyo#define BWN_TX_SLOTS_PER_FRAME 2 194203945Sweongyo 195203945Sweongyostruct bwn_channel { 196203945Sweongyo unsigned freq; 197203945Sweongyo unsigned ieee; 198203945Sweongyo unsigned maxTxPow; 199203945Sweongyo}; 200203945Sweongyo 201203945Sweongyostruct bwn_channelinfo { 202203945Sweongyo struct bwn_channel channels[IEEE80211_CHAN_MAX]; 203203945Sweongyo unsigned nchannels; 204203945Sweongyo}; 205203945Sweongyo 206203945Sweongyostruct bwn_bbatt { 207203945Sweongyo uint8_t att; 208203945Sweongyo}; 209203945Sweongyo 210203945Sweongyostruct bwn_bbatt_list { 211203945Sweongyo const struct bwn_bbatt *array; 212203945Sweongyo uint8_t len; 213203945Sweongyo uint8_t min; 214203945Sweongyo uint8_t max; 215203945Sweongyo}; 216203945Sweongyo 217203945Sweongyostruct bwn_rfatt { 218203945Sweongyo uint8_t att; 219203945Sweongyo int padmix; 220203945Sweongyo}; 221203945Sweongyo 222203945Sweongyostruct bwn_rfatt_list { 223203945Sweongyo const struct bwn_rfatt *array; 224203945Sweongyo uint8_t len; 225203945Sweongyo uint8_t min; 226203945Sweongyo uint8_t max; 227203945Sweongyo}; 228203945Sweongyo 229203945Sweongyo#define BWN_DC_LT_SIZE 32 230203945Sweongyo 231203945Sweongyostruct bwn_loctl { 232203945Sweongyo int8_t i; 233203945Sweongyo int8_t q; 234203945Sweongyo}; 235203945Sweongyo 236299790Sadriantypedef enum { 237299790Sadrian BWN_TXPWR_RES_NEED_ADJUST, 238299790Sadrian BWN_TXPWR_RES_DONE, 239299790Sadrian} bwn_txpwr_result_t; 240299790Sadrian 241203945Sweongyostruct bwn_lo_calib { 242203945Sweongyo struct bwn_bbatt bbatt; 243203945Sweongyo struct bwn_rfatt rfatt; 244203945Sweongyo struct bwn_loctl ctl; 245203945Sweongyo unsigned long calib_time; 246203945Sweongyo TAILQ_ENTRY(bwn_lo_calib) list; 247203945Sweongyo}; 248203945Sweongyo 249203945Sweongyostruct bwn_rxhdr4 { 250203945Sweongyo uint16_t frame_len; 251203945Sweongyo uint8_t pad1[2]; 252203945Sweongyo uint16_t phy_status0; 253203945Sweongyo union { 254203945Sweongyo struct { 255203945Sweongyo uint8_t rssi; 256203945Sweongyo uint8_t sig_qual; 257203945Sweongyo } __packed abg; 258203945Sweongyo struct { 259203945Sweongyo int8_t power0; 260203945Sweongyo int8_t power1; 261203945Sweongyo } __packed n; 262203945Sweongyo } __packed phy; 263299790Sadrian union { 264299790Sadrian struct { 265299790Sadrian int8_t power2; 266299790Sadrian uint8_t pad; 267299790Sadrian } __packed n; 268299790Sadrian struct { 269299790Sadrian uint8_t pad; 270299790Sadrian int8_t ht_power0; 271299790Sadrian } __packed ht; 272299790Sadrian uint16_t phy_status2; 273299790Sadrian } __packed ps2; 274300114Sadrian union { 275300114Sadrian struct { 276300114Sadrian uint16_t phy_status3; 277300114Sadrian } __packed lp; 278300114Sadrian struct { 279300114Sadrian int8_t phy_ht_power1; 280300114Sadrian int8_t phy_ht_power2; 281300114Sadrian } __packed ht; 282300114Sadrian } __packed ps3; 283300114Sadrian union { 284300114Sadrian struct { 285300114Sadrian uint32_t mac_status; 286300114Sadrian uint16_t mac_time; 287300114Sadrian uint16_t channel; 288300114Sadrian } __packed r351; 289300114Sadrian struct { 290300114Sadrian uint16_t phy_status4; 291300114Sadrian uint16_t phy_status5; 292300114Sadrian uint32_t mac_status; 293300114Sadrian uint16_t mac_time; 294300114Sadrian uint16_t channel; 295300114Sadrian } __packed r598; 296300114Sadrian } __packed ps4; 297203945Sweongyo} __packed; 298203945Sweongyo 299203945Sweongyostruct bwn_txstatus { 300203945Sweongyo uint16_t cookie; 301203945Sweongyo uint16_t seq; 302203945Sweongyo uint8_t phy_stat; 303203945Sweongyo uint8_t framecnt; 304203945Sweongyo uint8_t rtscnt; 305203945Sweongyo uint8_t sreason; 306203945Sweongyo uint8_t pm; 307203945Sweongyo uint8_t im; 308203945Sweongyo uint8_t ampdu; 309203945Sweongyo uint8_t ack; 310203945Sweongyo}; 311203945Sweongyo 312203945Sweongyo#define BWN_TXCTL_PA3DB 0x40 313203945Sweongyo#define BWN_TXCTL_PA2DB 0x20 314203945Sweongyo#define BWN_TXCTL_TXMIX 0x10 315203945Sweongyo 316203945Sweongyostruct bwn_txpwr_loctl { 317203945Sweongyo struct bwn_rfatt_list rfatt; 318203945Sweongyo struct bwn_bbatt_list bbatt; 319203945Sweongyo uint16_t dc_lt[BWN_DC_LT_SIZE]; 320203945Sweongyo TAILQ_HEAD(, bwn_lo_calib) calib_list; 321203945Sweongyo unsigned long pwr_vec_read_time; 322203945Sweongyo unsigned long txctl_measured_time; 323203945Sweongyo uint8_t tx_bias; 324203945Sweongyo uint8_t tx_magn; 325203945Sweongyo uint64_t power_vector; 326203945Sweongyo}; 327203945Sweongyo 328203945Sweongyo#define BWN_OFDMTAB_DIR_UNKNOWN 0 329203945Sweongyo#define BWN_OFDMTAB_DIR_READ 1 330203945Sweongyo#define BWN_OFDMTAB_DIR_WRITE 2 331203945Sweongyo 332203945Sweongyostruct bwn_phy_g { 333203945Sweongyo unsigned pg_flags; 334203945Sweongyo#define BWN_PHY_G_FLAG_TSSITABLE_ALLOC (1 << 0) 335203945Sweongyo#define BWN_PHY_G_FLAG_RADIOCTX_VALID (1 << 1) 336203945Sweongyo int pg_aci_enable; 337203945Sweongyo int pg_aci_wlan_automatic; 338203945Sweongyo int pg_aci_hw_rssi; 339203945Sweongyo int pg_rf_on; 340203945Sweongyo uint16_t pg_radioctx_over; 341203945Sweongyo uint16_t pg_radioctx_overval; 342203945Sweongyo uint16_t pg_minlowsig[2]; 343203945Sweongyo uint16_t pg_minlowsigpos[2]; 344203945Sweongyo int8_t *pg_tssi2dbm; 345203945Sweongyo int pg_idletssi; 346203945Sweongyo int pg_curtssi; 347203945Sweongyo uint8_t pg_avgtssi; 348203945Sweongyo struct bwn_bbatt pg_bbatt; 349203945Sweongyo struct bwn_rfatt pg_rfatt; 350203945Sweongyo uint8_t pg_txctl; 351203945Sweongyo int pg_bbatt_delta; 352203945Sweongyo int pg_rfatt_delta; 353203945Sweongyo 354203945Sweongyo struct bwn_txpwr_loctl pg_loctl; 355203945Sweongyo int16_t pg_max_lb_gain; 356203945Sweongyo int16_t pg_trsw_rx_gain; 357203945Sweongyo int16_t pg_lna_lod_gain; 358203945Sweongyo int16_t pg_lna_gain; 359203945Sweongyo int16_t pg_pga_gain; 360203945Sweongyo int pg_immode; 361203945Sweongyo#define BWN_INTERFSTACK_SIZE 26 362203945Sweongyo uint32_t pg_interfstack[BWN_INTERFSTACK_SIZE]; 363203945Sweongyo 364203945Sweongyo int16_t pg_nrssi[2]; 365203945Sweongyo int32_t pg_nrssi_slope; 366203945Sweongyo int8_t pg_nrssi_lt[64]; 367203945Sweongyo 368203945Sweongyo uint16_t pg_lofcal; 369203945Sweongyo 370203945Sweongyo uint16_t pg_initval; 371203945Sweongyo uint16_t pg_ofdmtab_addr; 372203945Sweongyo unsigned pg_ofdmtab_dir; 373203945Sweongyo}; 374203945Sweongyo 375203945Sweongyo#define BWN_IMMODE_NONE 0 376203945Sweongyo#define BWN_IMMODE_NONWLAN 1 377203945Sweongyo#define BWN_IMMODE_MANUAL 2 378203945Sweongyo#define BWN_IMMODE_AUTO 3 379203945Sweongyo 380203945Sweongyo#define BWN_PHYLP_TXPCTL_UNKNOWN 0 381203945Sweongyo#define BWN_PHYLP_TXPCTL_OFF 1 382203945Sweongyo#define BWN_PHYLP_TXPCTL_ON_SW 2 383203945Sweongyo#define BWN_PHYLP_TXPCTL_ON_HW 3 384203945Sweongyo 385203945Sweongyostruct bwn_phy_lp { 386203945Sweongyo uint8_t plp_chan; 387203945Sweongyo uint8_t plp_chanfullcal; 388203945Sweongyo int32_t plp_antenna; 389203945Sweongyo uint8_t plp_txpctlmode; 390203945Sweongyo uint8_t plp_txisoband_h; 391203945Sweongyo uint8_t plp_txisoband_m; 392203945Sweongyo uint8_t plp_txisoband_l; 393203945Sweongyo uint8_t plp_rxpwroffset; 394203945Sweongyo int8_t plp_txpwridx; 395203945Sweongyo uint16_t plp_tssiidx; 396203945Sweongyo uint16_t plp_tssinpt; 397203945Sweongyo uint8_t plp_rssivf; 398203945Sweongyo uint8_t plp_rssivc; 399203945Sweongyo uint8_t plp_rssigs; 400203945Sweongyo uint8_t plp_rccap; 401203945Sweongyo uint8_t plp_bxarch; 402203945Sweongyo uint8_t plp_crsusr_off; 403203945Sweongyo uint8_t plp_crssys_off; 404203945Sweongyo uint32_t plp_div; 405203945Sweongyo int32_t plp_tonefreq; 406203945Sweongyo uint16_t plp_digfilt[9]; 407203945Sweongyo}; 408203945Sweongyo 409203945Sweongyo/* for LP */ 410203945Sweongyostruct bwn_txgain { 411203945Sweongyo uint16_t tg_gm; 412203945Sweongyo uint16_t tg_pga; 413203945Sweongyo uint16_t tg_pad; 414203945Sweongyo uint16_t tg_dac; 415203945Sweongyo}; 416203945Sweongyo 417203945Sweongyostruct bwn_rxcompco { 418203945Sweongyo uint8_t rc_chan; 419203945Sweongyo int8_t rc_c1; 420203945Sweongyo int8_t rc_c0; 421203945Sweongyo}; 422203945Sweongyo 423203945Sweongyostruct bwn_phy_lp_iq_est { 424203945Sweongyo uint32_t ie_iqprod; 425203945Sweongyo uint32_t ie_ipwr; 426203945Sweongyo uint32_t ie_qpwr; 427203945Sweongyo}; 428203945Sweongyo 429203945Sweongyostruct bwn_txgain_entry { 430203945Sweongyo uint8_t te_gm; 431203945Sweongyo uint8_t te_pga; 432203945Sweongyo uint8_t te_pad; 433203945Sweongyo uint8_t te_dac; 434203945Sweongyo uint8_t te_bbmult; 435203945Sweongyo}; 436203945Sweongyo 437203945Sweongyo/* only for LP PHY */ 438203945Sweongyostruct bwn_stxtable { 439203945Sweongyo uint16_t st_phyoffset; 440203945Sweongyo uint16_t st_physhift; 441203945Sweongyo uint16_t st_rfaddr; 442203945Sweongyo uint16_t st_rfshift; 443203945Sweongyo uint16_t st_mask; 444203945Sweongyo}; 445203945Sweongyo 446203945Sweongyostruct bwn_b206x_chan { 447203945Sweongyo uint8_t bc_chan; 448203945Sweongyo uint16_t bc_freq; 449203945Sweongyo const uint8_t *bc_data; 450203945Sweongyo}; 451203945Sweongyo 452203945Sweongyostruct bwn_b206x_rfinit_entry { 453203945Sweongyo uint16_t br_offset; 454203945Sweongyo uint16_t br_valuea; 455203945Sweongyo uint16_t br_valueg; 456203945Sweongyo uint8_t br_flags; 457203945Sweongyo}; 458203945Sweongyo 459299790Sadrianstruct bwn_phy_n; 460299790Sadrian 461203945Sweongyostruct bwn_phy { 462203945Sweongyo uint8_t type; 463203945Sweongyo uint8_t rev; 464203945Sweongyo uint8_t analog; 465203945Sweongyo 466203945Sweongyo int supports_2ghz; 467203945Sweongyo int supports_5ghz; 468203945Sweongyo 469203945Sweongyo int gmode; 470203945Sweongyo struct bwn_phy_g phy_g; 471203945Sweongyo struct bwn_phy_lp phy_lp; 472203945Sweongyo 473299790Sadrian /* 474299790Sadrian * I'd like the newer PHY code to not hide in the top-level 475299790Sadrian * structs.. 476299790Sadrian */ 477299790Sadrian struct bwn_phy_n *phy_n; 478299790Sadrian 479203945Sweongyo uint16_t rf_manuf; 480203945Sweongyo uint16_t rf_ver; 481203945Sweongyo uint8_t rf_rev; 482203945Sweongyo int rf_on; 483299790Sadrian int phy_do_full_init; 484203945Sweongyo 485203945Sweongyo int txpower; 486203945Sweongyo int hwpctl; 487203945Sweongyo unsigned long nexttime; 488203945Sweongyo unsigned int chan; 489203945Sweongyo int txerrors; 490203945Sweongyo 491203945Sweongyo int (*attach)(struct bwn_mac *); 492203945Sweongyo void (*detach)(struct bwn_mac *); 493203945Sweongyo int (*prepare_hw)(struct bwn_mac *); 494203945Sweongyo void (*init_pre)(struct bwn_mac *); 495203945Sweongyo int (*init)(struct bwn_mac *); 496203945Sweongyo void (*exit)(struct bwn_mac *); 497203945Sweongyo uint16_t (*phy_read)(struct bwn_mac *, uint16_t); 498203945Sweongyo void (*phy_write)(struct bwn_mac *, uint16_t, 499203945Sweongyo uint16_t); 500203945Sweongyo void (*phy_maskset)(struct bwn_mac *, 501203945Sweongyo uint16_t, uint16_t, uint16_t); 502203945Sweongyo uint16_t (*rf_read)(struct bwn_mac *, uint16_t); 503203945Sweongyo void (*rf_write)(struct bwn_mac *, uint16_t, 504203945Sweongyo uint16_t); 505203945Sweongyo int (*use_hwpctl)(struct bwn_mac *); 506203945Sweongyo void (*rf_onoff)(struct bwn_mac *, int); 507203945Sweongyo void (*switch_analog)(struct bwn_mac *, int); 508203945Sweongyo int (*switch_channel)(struct bwn_mac *, 509203945Sweongyo unsigned int); 510203945Sweongyo uint32_t (*get_default_chan)(struct bwn_mac *); 511203945Sweongyo void (*set_antenna)(struct bwn_mac *, int); 512203945Sweongyo int (*set_im)(struct bwn_mac *, int); 513299790Sadrian bwn_txpwr_result_t (*recalc_txpwr)(struct bwn_mac *, int); 514203945Sweongyo void (*set_txpwr)(struct bwn_mac *); 515203945Sweongyo void (*task_15s)(struct bwn_mac *); 516203945Sweongyo void (*task_60s)(struct bwn_mac *); 517203945Sweongyo}; 518203945Sweongyo 519203945Sweongyostruct bwn_chan_band { 520203945Sweongyo uint32_t flags; 521203945Sweongyo uint8_t nchan; 522203945Sweongyo#define BWN_MAX_CHAN_PER_BAND 14 523203945Sweongyo uint8_t chan[BWN_MAX_CHAN_PER_BAND]; 524203945Sweongyo}; 525203945Sweongyo 526203945Sweongyo#define BWN_NR_WMEPARAMS 16 527203945Sweongyoenum { 528203945Sweongyo BWN_WMEPARAM_TXOP = 0, 529203945Sweongyo BWN_WMEPARAM_CWMIN, 530203945Sweongyo BWN_WMEPARAM_CWMAX, 531203945Sweongyo BWN_WMEPARAM_CWCUR, 532203945Sweongyo BWN_WMEPARAM_AIFS, 533203945Sweongyo BWN_WMEPARAM_BSLOTS, 534203945Sweongyo BWN_WMEPARAM_REGGAP, 535203945Sweongyo BWN_WMEPARAM_STATUS, 536203945Sweongyo}; 537203945Sweongyo 538203945Sweongyo#define BWN_WME_PARAMS(queue) \ 539203945Sweongyo (BWN_SHARED_EDCFQ + (BWN_NR_WMEPARAMS * sizeof(uint16_t) * (queue))) 540203945Sweongyo#define BWN_WME_BACKGROUND BWN_WME_PARAMS(0) 541203945Sweongyo#define BWN_WME_BESTEFFORT BWN_WME_PARAMS(1) 542203945Sweongyo#define BWN_WME_VIDEO BWN_WME_PARAMS(2) 543203945Sweongyo#define BWN_WME_VOICE BWN_WME_PARAMS(3) 544203945Sweongyo 545203945Sweongyo/* 546203945Sweongyo * Radio capture format. 547203945Sweongyo */ 548203945Sweongyo#define BWN_RX_RADIOTAP_PRESENT ( \ 549203945Sweongyo (1 << IEEE80211_RADIOTAP_TSFT) | \ 550203945Sweongyo (1 << IEEE80211_RADIOTAP_FLAGS) | \ 551203945Sweongyo (1 << IEEE80211_RADIOTAP_RATE) | \ 552203945Sweongyo (1 << IEEE80211_RADIOTAP_CHANNEL) | \ 553203945Sweongyo (1 << IEEE80211_RADIOTAP_ANTENNA) | \ 554203945Sweongyo (1 << IEEE80211_RADIOTAP_DBM_ANTSIGNAL) | \ 555203945Sweongyo (1 << IEEE80211_RADIOTAP_DBM_ANTNOISE) | \ 556203945Sweongyo 0) 557203945Sweongyo 558203945Sweongyostruct bwn_rx_radiotap_header { 559203945Sweongyo struct ieee80211_radiotap_header wr_ihdr; 560203945Sweongyo uint64_t wr_tsf; 561203945Sweongyo u_int8_t wr_flags; 562203945Sweongyo u_int8_t wr_rate; 563203945Sweongyo u_int16_t wr_chan_freq; 564203945Sweongyo u_int16_t wr_chan_flags; 565203945Sweongyo int8_t wr_antsignal; 566203945Sweongyo int8_t wr_antnoise; 567203945Sweongyo u_int8_t wr_antenna; 568345636Savos} __packed __aligned(8); 569203945Sweongyo 570203945Sweongyo#define BWN_TX_RADIOTAP_PRESENT ( \ 571203945Sweongyo (1 << IEEE80211_RADIOTAP_FLAGS) | \ 572203945Sweongyo (1 << IEEE80211_RADIOTAP_RATE) | \ 573203945Sweongyo (1 << IEEE80211_RADIOTAP_CHANNEL) | \ 574203945Sweongyo (1 << IEEE80211_RADIOTAP_DBM_TX_POWER) | \ 575203945Sweongyo (1 << IEEE80211_RADIOTAP_ANTENNA) | \ 576203945Sweongyo 0) 577203945Sweongyo 578203945Sweongyostruct bwn_tx_radiotap_header { 579203945Sweongyo struct ieee80211_radiotap_header wt_ihdr; 580203945Sweongyo u_int8_t wt_flags; 581203945Sweongyo u_int8_t wt_rate; 582203945Sweongyo u_int16_t wt_chan_freq; 583203945Sweongyo u_int16_t wt_chan_flags; 584203945Sweongyo u_int8_t wt_txpower; 585203945Sweongyo u_int8_t wt_antenna; 586345636Savos} __packed; 587203945Sweongyo 588203945Sweongyostruct bwn_stats { 589204257Sweongyo int32_t rtsfail; 590204257Sweongyo int32_t rts; 591203945Sweongyo int32_t link_noise; 592203945Sweongyo}; 593203945Sweongyo 594203945Sweongyo/* Noise Calculation (Link Quality) */ 595203945Sweongyostruct bwn_noise { 596203945Sweongyo uint8_t noi_running; 597203945Sweongyo uint8_t noi_nsamples; 598203945Sweongyo int8_t noi_samples[8][4]; 599203945Sweongyo}; 600203945Sweongyo 601203945Sweongyo#define BWN_DMA_30BIT 30 602203945Sweongyo#define BWN_DMA_32BIT 32 603203945Sweongyo#define BWN_DMA_64BIT 64 604203945Sweongyo 605203945Sweongyostruct bwn_dmadesc_meta { 606203945Sweongyo bus_dmamap_t mt_dmap; 607203945Sweongyo bus_addr_t mt_paddr; 608203945Sweongyo struct mbuf *mt_m; 609203945Sweongyo struct ieee80211_node *mt_ni; 610203945Sweongyo uint8_t mt_txtype; 611203945Sweongyo#define BWN_DMADESC_METATYPE_HEADER 0 612203945Sweongyo#define BWN_DMADESC_METATYPE_BODY 1 613203945Sweongyo uint8_t mt_islast; 614203945Sweongyo}; 615203945Sweongyo 616203945Sweongyo#define BWN_DMAINTR_FATALMASK \ 617203945Sweongyo ((1 << 10) | (1 << 11) | (1 << 12) | (1 << 14) | (1 << 15)) 618203945Sweongyo#define BWN_DMAINTR_NONFATALMASK (1 << 13) 619203945Sweongyo#define BWN_DMAINTR_RX_DONE (1 << 16) 620203945Sweongyo 621203945Sweongyo#define BWN_DMA32_DCTL_BYTECNT 0x00001fff 622203945Sweongyo#define BWN_DMA32_DCTL_ADDREXT_MASK 0x00030000 623203945Sweongyo#define BWN_DMA32_DCTL_ADDREXT_SHIFT 16 624203945Sweongyo#define BWN_DMA32_DCTL_DTABLEEND 0x10000000 625203945Sweongyo#define BWN_DMA32_DCTL_IRQ 0x20000000 626203945Sweongyo#define BWN_DMA32_DCTL_FRAMEEND 0x40000000 627203945Sweongyo#define BWN_DMA32_DCTL_FRAMESTART 0x80000000 628203945Sweongyostruct bwn_dmadesc32 { 629203945Sweongyo uint32_t control; 630203945Sweongyo uint32_t address; 631203945Sweongyo} __packed; 632203945Sweongyo 633203945Sweongyo#define BWN_DMA64_DCTL0_DTABLEEND 0x10000000 634203945Sweongyo#define BWN_DMA64_DCTL0_IRQ 0x20000000 635203945Sweongyo#define BWN_DMA64_DCTL0_FRAMEEND 0x40000000 636203945Sweongyo#define BWN_DMA64_DCTL0_FRAMESTART 0x80000000 637203945Sweongyo#define BWN_DMA64_DCTL1_BYTECNT 0x00001fff 638203945Sweongyo#define BWN_DMA64_DCTL1_ADDREXT_MASK 0x00030000 639203945Sweongyo#define BWN_DMA64_DCTL1_ADDREXT_SHIFT 16 640203945Sweongyostruct bwn_dmadesc64 { 641203945Sweongyo uint32_t control0; 642203945Sweongyo uint32_t control1; 643203945Sweongyo uint32_t address_low; 644203945Sweongyo uint32_t address_high; 645203945Sweongyo} __packed; 646203945Sweongyo 647203945Sweongyostruct bwn_dmadesc_generic { 648203945Sweongyo union { 649203945Sweongyo struct bwn_dmadesc32 dma32; 650203945Sweongyo struct bwn_dmadesc64 dma64; 651203945Sweongyo } __packed dma; 652203945Sweongyo} __packed; 653203945Sweongyo 654203945Sweongyostruct bwn_dma_ring; 655203945Sweongyo 656203945Sweongyostruct bwn_dma_ring { 657203945Sweongyo struct bwn_mac *dr_mac; 658203945Sweongyo const struct bwn_dma_ops *dr_ops; 659203945Sweongyo struct bwn_dmadesc_meta *dr_meta; 660203945Sweongyo void *dr_txhdr_cache; 661203945Sweongyo bus_dma_tag_t dr_ring_dtag; 662203945Sweongyo bus_dma_tag_t dr_txring_dtag; 663203945Sweongyo bus_dmamap_t dr_spare_dmap; /* only for RX */ 664203945Sweongyo bus_dmamap_t dr_ring_dmap; 665203945Sweongyo bus_addr_t dr_txring_paddr; 666203945Sweongyo void *dr_ring_descbase; 667203945Sweongyo bus_addr_t dr_ring_dmabase; 668203945Sweongyo int dr_numslots; 669203945Sweongyo int dr_usedslot; 670203945Sweongyo int dr_curslot; 671203945Sweongyo uint32_t dr_frameoffset; 672203945Sweongyo uint16_t dr_rx_bufsize; 673203945Sweongyo uint16_t dr_base; 674203945Sweongyo int dr_index; 675203945Sweongyo uint8_t dr_tx; 676203945Sweongyo uint8_t dr_stop; 677203945Sweongyo int dr_type; 678203945Sweongyo 679203945Sweongyo void (*getdesc)(struct bwn_dma_ring *, 680203945Sweongyo int, struct bwn_dmadesc_generic **, 681203945Sweongyo struct bwn_dmadesc_meta **); 682203945Sweongyo void (*setdesc)(struct bwn_dma_ring *, 683203945Sweongyo struct bwn_dmadesc_generic *, 684203945Sweongyo bus_addr_t, uint16_t, int, int, 685203945Sweongyo int); 686203945Sweongyo void (*start_transfer)(struct bwn_dma_ring *, 687203945Sweongyo int); 688203945Sweongyo void (*suspend)(struct bwn_dma_ring *); 689203945Sweongyo void (*resume)(struct bwn_dma_ring *); 690203945Sweongyo int (*get_curslot)(struct bwn_dma_ring *); 691203945Sweongyo void (*set_curslot)(struct bwn_dma_ring *, 692203945Sweongyo int); 693203945Sweongyo}; 694203945Sweongyo 695203945Sweongyostruct bwn_dma { 696203945Sweongyo int dmatype; 697203945Sweongyo bus_dma_tag_t parent_dtag; 698203945Sweongyo bus_dma_tag_t rxbuf_dtag; 699203945Sweongyo bus_dma_tag_t txbuf_dtag; 700203945Sweongyo 701203945Sweongyo struct bwn_dma_ring *wme[5]; 702203945Sweongyo struct bwn_dma_ring *mcast; 703203945Sweongyo struct bwn_dma_ring *rx; 704203945Sweongyo uint64_t lastseq; /* XXX FIXME */ 705203945Sweongyo}; 706203945Sweongyo 707203945Sweongyostruct bwn_pio_rxqueue { 708203945Sweongyo struct bwn_mac *prq_mac; 709203945Sweongyo uint16_t prq_base; 710203945Sweongyo uint8_t prq_rev; 711203945Sweongyo}; 712203945Sweongyo 713203945Sweongyostruct bwn_pio_txqueue; 714203945Sweongyostruct bwn_pio_txpkt { 715203945Sweongyo struct bwn_pio_txqueue *tp_queue; 716203945Sweongyo struct ieee80211_node *tp_ni; 717203945Sweongyo struct mbuf *tp_m; 718203945Sweongyo uint8_t tp_index; 719203945Sweongyo TAILQ_ENTRY(bwn_pio_txpkt) tp_list; 720203945Sweongyo}; 721203945Sweongyo 722203945Sweongyo#define BWN_PIO_MAX_TXPACKETS 32 723203945Sweongyostruct bwn_pio_txqueue { 724203945Sweongyo uint16_t tq_base; 725203945Sweongyo uint16_t tq_size; 726203945Sweongyo uint16_t tq_used; 727203945Sweongyo uint16_t tq_free; 728203945Sweongyo uint8_t tq_index; 729203945Sweongyo struct bwn_pio_txpkt tq_pkts[BWN_PIO_MAX_TXPACKETS]; 730203945Sweongyo TAILQ_HEAD(, bwn_pio_txpkt) tq_pktlist; 731203945Sweongyo}; 732203945Sweongyo 733203945Sweongyostruct bwn_pio { 734203945Sweongyo struct bwn_pio_txqueue wme[5]; 735203945Sweongyo struct bwn_pio_txqueue mcast; 736203945Sweongyo struct bwn_pio_rxqueue rx; 737203945Sweongyo}; 738203945Sweongyo 739203945Sweongyostruct bwn_plcp4 { 740203945Sweongyo union { 741203945Sweongyo uint32_t data; 742203945Sweongyo uint8_t raw[4]; 743203945Sweongyo } __packed o; 744203945Sweongyo} __packed; 745203945Sweongyo 746203945Sweongyostruct bwn_plcp6 { 747203945Sweongyo union { 748203945Sweongyo uint32_t data; 749203945Sweongyo uint8_t raw[6]; 750203945Sweongyo } __packed o; 751203945Sweongyo} __packed; 752203945Sweongyo 753203945Sweongyostruct bwn_txhdr { 754203945Sweongyo uint32_t macctl; 755203945Sweongyo uint8_t macfc[2]; 756203945Sweongyo uint16_t tx_festime; 757203945Sweongyo uint16_t phyctl; 758203945Sweongyo uint16_t phyctl_1; 759203945Sweongyo uint16_t phyctl_1fb; 760203945Sweongyo uint16_t phyctl_1rts; 761203945Sweongyo uint16_t phyctl_1rtsfb; 762203945Sweongyo uint8_t phyrate; 763203945Sweongyo uint8_t phyrate_rts; 764203945Sweongyo uint8_t eftypes; /* extra frame types */ 765203945Sweongyo uint8_t chan; 766203945Sweongyo uint8_t iv[16]; 767203945Sweongyo uint8_t addr1[IEEE80211_ADDR_LEN]; 768203945Sweongyo uint16_t tx_festime_fb; 769203945Sweongyo struct bwn_plcp6 rts_plcp_fb; 770203945Sweongyo uint16_t rts_dur_fb; 771203945Sweongyo struct bwn_plcp6 plcp_fb; 772203945Sweongyo uint16_t dur_fb; 773203945Sweongyo uint16_t mimo_modelen; 774203945Sweongyo uint16_t mimo_ratelen_fb; 775203945Sweongyo uint32_t timeout; 776203945Sweongyo 777203945Sweongyo union { 778203945Sweongyo /* format <= r351 */ 779203945Sweongyo struct { 780203945Sweongyo uint8_t pad0[2]; 781203945Sweongyo uint16_t cookie; 782203945Sweongyo uint16_t tx_status; 783203945Sweongyo struct bwn_plcp6 rts_plcp; 784203945Sweongyo uint8_t rts_frame[16]; 785228399Seadler uint8_t pad1[2]; 786203945Sweongyo struct bwn_plcp6 plcp; 787300114Sadrian } __packed r351; 788300114Sadrian /* format > r410 < r598 */ 789203945Sweongyo struct { 790203945Sweongyo uint16_t mimo_antenna; 791203945Sweongyo uint16_t preload_size; 792203945Sweongyo uint8_t pad0[2]; 793203945Sweongyo uint16_t cookie; 794203945Sweongyo uint16_t tx_status; 795203945Sweongyo struct bwn_plcp6 rts_plcp; 796203945Sweongyo uint8_t rts_frame[16]; 797203945Sweongyo uint8_t pad1[2]; 798203945Sweongyo struct bwn_plcp6 plcp; 799300114Sadrian } __packed r410; 800300114Sadrian struct { 801300114Sadrian uint16_t mimo_antenna; 802300114Sadrian uint16_t preload_size; 803300114Sadrian uint8_t pad0[2]; 804300114Sadrian uint16_t cookie; 805300114Sadrian uint16_t tx_status; 806300114Sadrian uint16_t max_n_mpdus; 807300114Sadrian uint16_t max_a_bytes_mrt; 808300114Sadrian uint16_t max_a_bytes_fbr; 809300114Sadrian uint16_t min_m_bytes; 810300114Sadrian struct bwn_plcp6 rts_plcp; 811300114Sadrian uint8_t rts_frame[16]; 812300114Sadrian uint8_t pad1[2]; 813300114Sadrian struct bwn_plcp6 plcp; 814300114Sadrian } __packed r598; 815203945Sweongyo } __packed body; 816203945Sweongyo} __packed; 817203945Sweongyo 818203945Sweongyo#define BWN_FWTYPE_UCODE 'u' 819203945Sweongyo#define BWN_FWTYPE_PCM 'p' 820203945Sweongyo#define BWN_FWTYPE_IV 'i' 821203945Sweongyostruct bwn_fwhdr { 822203945Sweongyo uint8_t type; 823203945Sweongyo uint8_t ver; 824203945Sweongyo uint8_t pad[2]; 825203945Sweongyo uint32_t size; 826203945Sweongyo} __packed; 827203945Sweongyo 828203945Sweongyo#define BWN_FWINITVALS_OFFSET_MASK 0x7fff 829203945Sweongyo#define BWN_FWINITVALS_32BIT 0x8000 830203945Sweongyostruct bwn_fwinitvals { 831203945Sweongyo uint16_t offset_size; 832203945Sweongyo union { 833203945Sweongyo uint16_t d16; 834203945Sweongyo uint32_t d32; 835203945Sweongyo } __packed data; 836203945Sweongyo} __packed; 837203945Sweongyo 838299110Sadrianenum bwn_fw_hdr_format { 839299110Sadrian BWN_FW_HDR_598, 840299110Sadrian BWN_FW_HDR_410, 841299110Sadrian BWN_FW_HDR_351, 842299110Sadrian}; 843299110Sadrian 844203945Sweongyoenum bwn_fwtype { 845203945Sweongyo BWN_FWTYPE_DEFAULT, 846203945Sweongyo BWN_FWTYPE_OPENSOURCE, 847203945Sweongyo BWN_NR_FWTYPES, 848203945Sweongyo}; 849203945Sweongyo 850203945Sweongyostruct bwn_fwfile { 851203945Sweongyo const char *filename; 852203945Sweongyo const struct firmware *fw; 853203945Sweongyo enum bwn_fwtype type; 854203945Sweongyo}; 855203945Sweongyo 856203945Sweongyostruct bwn_key { 857203945Sweongyo void *keyconf; 858203945Sweongyo uint8_t algorithm; 859203945Sweongyo}; 860203945Sweongyo 861203945Sweongyostruct bwn_fw { 862203945Sweongyo struct bwn_fwfile ucode; 863203945Sweongyo struct bwn_fwfile pcm; 864203945Sweongyo struct bwn_fwfile initvals; 865203945Sweongyo struct bwn_fwfile initvals_band; 866299110Sadrian enum bwn_fw_hdr_format fw_hdr_format; 867203945Sweongyo 868203945Sweongyo uint16_t rev; 869203945Sweongyo uint16_t patch; 870203945Sweongyo uint8_t opensource; 871203945Sweongyo uint8_t no_pcmfile; 872203945Sweongyo}; 873203945Sweongyo 874203945Sweongyostruct bwn_lo_g_sm { 875203945Sweongyo int curstate; 876203945Sweongyo int nmeasure; 877203945Sweongyo int multipler; 878203945Sweongyo uint16_t feedth; 879203945Sweongyo struct bwn_loctl loctl; 880203945Sweongyo}; 881203945Sweongyo 882203945Sweongyostruct bwn_lo_g_value { 883203945Sweongyo uint8_t old_channel; 884203945Sweongyo uint16_t phy_lomask; 885203945Sweongyo uint16_t phy_extg; 886203945Sweongyo uint16_t phy_dacctl_hwpctl; 887203945Sweongyo uint16_t phy_dacctl; 888203945Sweongyo uint16_t phy_hpwr_tssictl; 889203945Sweongyo uint16_t phy_analogover; 890203945Sweongyo uint16_t phy_analogoverval; 891203945Sweongyo uint16_t phy_rfover; 892203945Sweongyo uint16_t phy_rfoverval; 893203945Sweongyo uint16_t phy_classctl; 894203945Sweongyo uint16_t phy_crs0; 895203945Sweongyo uint16_t phy_pgactl; 896203945Sweongyo uint16_t phy_syncctl; 897203945Sweongyo uint16_t phy_cck0; 898203945Sweongyo uint16_t phy_cck1; 899203945Sweongyo uint16_t phy_cck2; 900203945Sweongyo uint16_t phy_cck3; 901203945Sweongyo uint16_t phy_cck4; 902203945Sweongyo uint16_t reg0; 903203945Sweongyo uint16_t reg1; 904203945Sweongyo uint16_t rf0; 905203945Sweongyo uint16_t rf1; 906203945Sweongyo uint16_t rf2; 907203945Sweongyo}; 908203945Sweongyo 909203945Sweongyo#define BWN_LED_MAX 4 910203945Sweongyo 911203945Sweongyo#define BWN_LED_EVENT_NONE -1 912203945Sweongyo#define BWN_LED_EVENT_POLL 0 913203945Sweongyo#define BWN_LED_EVENT_TX 1 914203945Sweongyo#define BWN_LED_EVENT_RX 2 915203945Sweongyo#define BWN_LED_SLOWDOWN(dur) (dur) = (((dur) * 3) / 2) 916203945Sweongyo 917203945Sweongyostruct bwn_led { 918203945Sweongyo uint8_t led_flags; /* BWN_LED_F_ */ 919203945Sweongyo uint8_t led_act; /* BWN_LED_ACT_ */ 920203945Sweongyo uint8_t led_mask; 921203945Sweongyo}; 922203945Sweongyo 923203945Sweongyo#define BWN_LED_F_ACTLOW 0x1 924203945Sweongyo#define BWN_LED_F_BLINK 0x2 925203945Sweongyo#define BWN_LED_F_POLLABLE 0x4 926203945Sweongyo#define BWN_LED_F_SLOW 0x8 927203945Sweongyo 928203945Sweongyostruct bwn_mac { 929203945Sweongyo struct bwn_softc *mac_sc; 930203945Sweongyo unsigned mac_status; 931203945Sweongyo#define BWN_MAC_STATUS_UNINIT 0 932203945Sweongyo#define BWN_MAC_STATUS_INITED 1 933203945Sweongyo#define BWN_MAC_STATUS_STARTED 2 934203945Sweongyo unsigned mac_flags; 935203945Sweongyo /* use "Bad Frames Preemption" */ 936203945Sweongyo#define BWN_MAC_FLAG_BADFRAME_PREEMP (1 << 0) 937203945Sweongyo#define BWN_MAC_FLAG_DFQVALID (1 << 1) 938203945Sweongyo#define BWN_MAC_FLAG_RADIO_ON (1 << 2) 939203945Sweongyo#define BWN_MAC_FLAG_DMA (1 << 3) 940203945Sweongyo#define BWN_MAC_FLAG_WME (1 << 4) 941203945Sweongyo#define BWN_MAC_FLAG_HWCRYPTO (1 << 5) 942203945Sweongyo 943203945Sweongyo struct resource_spec *mac_intr_spec; 944203945Sweongyo#define BWN_MSI_MESSAGES 1 945203945Sweongyo struct resource *mac_res_irq[BWN_MSI_MESSAGES]; 946203945Sweongyo void *mac_intrhand[BWN_MSI_MESSAGES]; 947203945Sweongyo int mac_msi; 948203945Sweongyo 949203945Sweongyo struct bwn_noise mac_noise; 950203945Sweongyo struct bwn_phy mac_phy; 951203945Sweongyo struct bwn_stats mac_stats; 952203945Sweongyo uint32_t mac_reason_intr; 953203945Sweongyo uint32_t mac_reason[6]; 954203945Sweongyo uint32_t mac_intr_mask; 955203945Sweongyo int mac_suspended; 956203945Sweongyo 957203945Sweongyo struct bwn_fw mac_fw; 958203945Sweongyo 959203945Sweongyo union { 960203945Sweongyo struct bwn_dma dma; 961203945Sweongyo struct bwn_pio pio; 962203945Sweongyo } mac_method; 963203945Sweongyo 964203945Sweongyo uint16_t mac_ktp; /* Key table pointer */ 965203945Sweongyo uint8_t mac_max_nr_keys; 966203945Sweongyo struct bwn_key mac_key[58]; 967203945Sweongyo 968203945Sweongyo unsigned int mac_task_state; 969203945Sweongyo struct task mac_intrtask; 970203945Sweongyo struct task mac_hwreset; 971203945Sweongyo struct task mac_txpower; 972203945Sweongyo 973203945Sweongyo TAILQ_ENTRY(bwn_mac) mac_list; 974203945Sweongyo}; 975203945Sweongyo 976299790Sadrianstatic inline int 977299790Sadrianbwn_tx_hdrsize(struct bwn_mac *mac) 978299790Sadrian{ 979299790Sadrian switch (mac->mac_fw.fw_hdr_format) { 980299790Sadrian case BWN_FW_HDR_598: 981299790Sadrian return (112 + (sizeof(struct bwn_plcp6))); 982299790Sadrian case BWN_FW_HDR_410: 983299790Sadrian return (104 + (sizeof(struct bwn_plcp6))); 984299790Sadrian case BWN_FW_HDR_351: 985299790Sadrian return (100 + (sizeof(struct bwn_plcp6))); 986299790Sadrian default: 987299790Sadrian printf("%s: unknown header format (%d)\n", __func__, 988299790Sadrian mac->mac_fw.fw_hdr_format); 989299790Sadrian return (112 + (sizeof(struct bwn_plcp6))); 990299790Sadrian } 991299790Sadrian} 992299790Sadrian 993203945Sweongyo/* 994203945Sweongyo * Driver-specific vap state. 995203945Sweongyo */ 996203945Sweongyostruct bwn_vap { 997203945Sweongyo struct ieee80211vap bv_vap; /* base class */ 998203945Sweongyo int (*bv_newstate)(struct ieee80211vap *, 999203945Sweongyo enum ieee80211_state, int); 1000203945Sweongyo}; 1001203945Sweongyo#define BWN_VAP(vap) ((struct bwn_vap *)(vap)) 1002203945Sweongyo#define BWN_VAP_CONST(vap) ((const struct mwl_vap *)(vap)) 1003203945Sweongyo 1004203945Sweongyostruct bwn_softc { 1005203945Sweongyo device_t sc_dev; 1006203945Sweongyo struct mtx sc_mtx; 1007287197Sglebius struct ieee80211com sc_ic; 1008287197Sglebius struct mbufq sc_snd; 1009203945Sweongyo unsigned sc_flags; 1010203945Sweongyo#define BWN_FLAG_ATTACHED (1 << 0) 1011203945Sweongyo#define BWN_FLAG_INVALID (1 << 1) 1012203945Sweongyo#define BWN_FLAG_NEED_BEACON_TP (1 << 2) 1013287197Sglebius#define BWN_FLAG_RUNNING (1 << 3) 1014203945Sweongyo unsigned sc_debug; 1015203945Sweongyo 1016203945Sweongyo struct bwn_mac *sc_curmac; 1017203945Sweongyo TAILQ_HEAD(, bwn_mac) sc_maclist; 1018203945Sweongyo 1019203945Sweongyo uint8_t sc_bssid[IEEE80211_ADDR_LEN]; 1020203945Sweongyo unsigned int sc_filters; 1021203945Sweongyo uint8_t sc_beacons[2]; 1022203945Sweongyo uint8_t sc_rf_enabled; 1023203945Sweongyo 1024203945Sweongyo struct wmeParams sc_wmeParams[4]; 1025203945Sweongyo 1026203945Sweongyo struct callout sc_rfswitch_ch; /* for laptop */ 1027203945Sweongyo struct callout sc_task_ch; 1028203945Sweongyo struct callout sc_watchdog_ch; 1029203945Sweongyo int sc_watchdog_timer; 1030203945Sweongyo struct taskqueue *sc_tq; /* private task queue */ 1031203945Sweongyo int (*sc_newstate)(struct ieee80211com *, 1032203945Sweongyo enum ieee80211_state, int); 1033203945Sweongyo void (*sc_node_cleanup)( 1034203945Sweongyo struct ieee80211_node *); 1035203945Sweongyo 1036203945Sweongyo int sc_rx_rate; 1037203945Sweongyo int sc_tx_rate; 1038203945Sweongyo 1039203945Sweongyo int sc_led_blinking; 1040203945Sweongyo int sc_led_ticks; 1041203945Sweongyo struct bwn_led *sc_blink_led; 1042203945Sweongyo struct callout sc_led_blink_ch; 1043203945Sweongyo int sc_led_blink_offdur; 1044203945Sweongyo struct bwn_led sc_leds[BWN_LED_MAX]; 1045203945Sweongyo int sc_led_idle; 1046203945Sweongyo int sc_led_blink; 1047203945Sweongyo 1048203945Sweongyo struct bwn_tx_radiotap_header sc_tx_th; 1049203945Sweongyo struct bwn_rx_radiotap_header sc_rx_th; 1050203945Sweongyo}; 1051203945Sweongyo 1052203945Sweongyo#define BWN_LOCK_INIT(sc) \ 1053203945Sweongyo mtx_init(&(sc)->sc_mtx, device_get_nameunit((sc)->sc_dev), \ 1054203945Sweongyo MTX_NETWORK_LOCK, MTX_DEF) 1055203945Sweongyo#define BWN_LOCK_DESTROY(sc) mtx_destroy(&(sc)->sc_mtx) 1056203945Sweongyo#define BWN_LOCK(sc) mtx_lock(&(sc)->sc_mtx) 1057203945Sweongyo#define BWN_UNLOCK(sc) mtx_unlock(&(sc)->sc_mtx) 1058203945Sweongyo#define BWN_ASSERT_LOCKED(sc) mtx_assert(&(sc)->sc_mtx, MA_OWNED) 1059203945Sweongyo 1060299790Sadrianstatic inline bwn_band_t 1061299790Sadrianbwn_channel_band(struct bwn_mac *mac, struct ieee80211_channel *c) 1062299790Sadrian{ 1063299790Sadrian if (IEEE80211_IS_CHAN_5GHZ(c)) 1064299790Sadrian return BWN_BAND_5G; 1065299790Sadrian /* XXX check 2g, log error if not 2g or 5g? */ 1066299790Sadrian return BWN_BAND_2G; 1067299790Sadrian} 1068299790Sadrian 1069299790Sadrianstatic inline bwn_band_t 1070299790Sadrianbwn_current_band(struct bwn_mac *mac) 1071299790Sadrian{ 1072299790Sadrian struct ieee80211com *ic = &mac->mac_sc->sc_ic; 1073299790Sadrian if (IEEE80211_IS_CHAN_5GHZ(ic->ic_curchan)) 1074299790Sadrian return BWN_BAND_5G; 1075299790Sadrian /* XXX check 2g, log error if not 2g or 5g? */ 1076299790Sadrian return BWN_BAND_2G; 1077299790Sadrian} 1078299790Sadrian 1079299790Sadrianstatic inline bool 1080299790Sadrianbwn_is_40mhz(struct bwn_mac *mac) 1081299790Sadrian{ 1082299790Sadrian struct ieee80211com *ic = &mac->mac_sc->sc_ic; 1083299790Sadrian 1084299790Sadrian return !! (IEEE80211_IS_CHAN_HT40(ic->ic_curchan)); 1085299790Sadrian} 1086299790Sadrian 1087299790Sadrianstatic inline int 1088299790Sadrianbwn_get_centre_freq(struct bwn_mac *mac) 1089299790Sadrian{ 1090299790Sadrian 1091299790Sadrian struct ieee80211com *ic = &mac->mac_sc->sc_ic; 1092299790Sadrian /* XXX TODO: calculate correctly for HT40 mode */ 1093299790Sadrian return ic->ic_curchan->ic_freq; 1094299790Sadrian} 1095299790Sadrian 1096299790Sadrianstatic inline int 1097299790Sadrianbwn_get_chan_centre_freq(struct bwn_mac *mac, struct ieee80211_channel *chan) 1098299790Sadrian{ 1099299790Sadrian 1100299790Sadrian /* XXX TODO: calculate correctly for HT40 mode */ 1101299790Sadrian return chan->ic_freq; 1102299790Sadrian} 1103299790Sadrian 1104299790Sadrianstatic inline int 1105299790Sadrianbwn_get_chan(struct bwn_mac *mac) 1106299790Sadrian{ 1107299790Sadrian 1108299790Sadrian struct ieee80211com *ic = &mac->mac_sc->sc_ic; 1109299790Sadrian /* XXX TODO: calculate correctly for HT40 mode */ 1110299790Sadrian return ic->ic_curchan->ic_ieee; 1111299790Sadrian} 1112299790Sadrian 1113299790Sadrianstatic inline struct ieee80211_channel * 1114299790Sadrianbwn_get_channel(struct bwn_mac *mac) 1115299790Sadrian{ 1116299790Sadrian 1117299790Sadrian struct ieee80211com *ic = &mac->mac_sc->sc_ic; 1118299790Sadrian return ic->ic_curchan; 1119299790Sadrian} 1120299790Sadrian 1121299790Sadrianstatic inline bool 1122299790Sadrianbwn_is_chan_passive(struct bwn_mac *mac) 1123299790Sadrian{ 1124299790Sadrian 1125299790Sadrian struct ieee80211com *ic = &mac->mac_sc->sc_ic; 1126299790Sadrian return !! IEEE80211_IS_CHAN_PASSIVE(ic->ic_curchan); 1127299790Sadrian} 1128299790Sadrian 1129299790Sadrianstatic inline bwn_chan_type_t 1130299790Sadrianbwn_get_chan_type(struct bwn_mac *mac, struct ieee80211_channel *c) 1131299790Sadrian{ 1132299790Sadrian struct ieee80211com *ic = &mac->mac_sc->sc_ic; 1133299790Sadrian if (c == NULL) 1134299790Sadrian c = ic->ic_curchan; 1135299790Sadrian if (IEEE80211_IS_CHAN_HT40U(c)) 1136299790Sadrian return BWN_CHAN_TYPE_40_HT_U; 1137299790Sadrian else if (IEEE80211_IS_CHAN_HT40D(c)) 1138299790Sadrian return BWN_CHAN_TYPE_40_HT_D; 1139299790Sadrian else if (IEEE80211_IS_CHAN_HT20(c)) 1140299790Sadrian return BWN_CHAN_TYPE_20_HT; 1141299790Sadrian else 1142299790Sadrian return BWN_CHAN_TYPE_20; 1143299790Sadrian} 1144299790Sadrian 1145299790Sadrianstatic inline int 1146299790Sadrianbwn_get_chan_power(struct bwn_mac *mac, struct ieee80211_channel *c) 1147299790Sadrian{ 1148299790Sadrian 1149299790Sadrian /* return in dbm */ 1150299790Sadrian return c->ic_maxpower / 2; 1151299790Sadrian} 1152299790Sadrian 1153299790Sadrian/* 1154299790Sadrian * For now there's no bhnd bus support. Places where it matters 1155299790Sadrian * should call this routine so we can start logging things. 1156299790Sadrian */ 1157299790Sadrianstatic inline int 1158299790Sadrianbwn_is_bus_siba(struct bwn_mac *mac) 1159299790Sadrian{ 1160299790Sadrian 1161299790Sadrian return 1; 1162299790Sadrian} 1163203945Sweongyo#endif /* !_IF_BWNVAR_H */ 1164