1 1.1 alc /* 2 1.1 alc * Copyright (c) 2002-2008 Sam Leffler, Errno Consulting 3 1.1 alc * Copyright (c) 2002-2008 Atheros Communications, Inc. 4 1.1 alc * 5 1.1 alc * Permission to use, copy, modify, and/or distribute this software for any 6 1.1 alc * purpose with or without fee is hereby granted, provided that the above 7 1.1 alc * copyright notice and this permission notice appear in all copies. 8 1.1 alc * 9 1.1 alc * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 10 1.1 alc * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 11 1.1 alc * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 12 1.1 alc * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 13 1.1 alc * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 14 1.1 alc * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 15 1.1 alc * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 16 1.1 alc * 17 1.1 alc * $Id: ar5416_recv.c,v 1.1.1.1 2008/12/11 04:46:48 alc Exp $ 18 1.1 alc */ 19 1.1 alc #include "opt_ah.h" 20 1.1 alc 21 1.1 alc #include "ah.h" 22 1.1 alc #include "ah_desc.h" 23 1.1 alc #include "ah_internal.h" 24 1.1 alc 25 1.1 alc #include "ar5416/ar5416.h" 26 1.1 alc #include "ar5416/ar5416reg.h" 27 1.1 alc #include "ar5416/ar5416desc.h" 28 1.1 alc 29 1.1 alc /* 30 1.1 alc * Start receive at the PCU engine 31 1.1 alc */ 32 1.1 alc void 33 1.1 alc ar5416StartPcuReceive(struct ath_hal *ah) 34 1.1 alc { 35 1.1 alc struct ath_hal_private *ahp = AH_PRIVATE(ah); 36 1.1 alc 37 1.1 alc HALDEBUG(ah, HAL_DEBUG_RX, "%s: Start PCU Receive \n", __func__); 38 1.1 alc ar5212EnableMibCounters(ah); 39 1.1 alc /* NB: restore current settings */ 40 1.1 alc ar5416AniReset(ah, ahp->ah_curchan, ahp->ah_opmode, AH_TRUE); 41 1.1 alc /* 42 1.1 alc * NB: must do after enabling phy errors to avoid rx 43 1.1 alc * frames w/ corrupted descriptor status. 44 1.1 alc */ 45 1.1 alc OS_REG_CLR_BIT(ah, AR_DIAG_SW, AR_DIAG_RX_DIS | AR_DIAG_RX_ABORT); 46 1.1 alc } 47 1.1 alc 48 1.1 alc /* 49 1.1 alc * Stop receive at the PCU engine 50 1.1 alc * and abort current frame in PCU 51 1.1 alc */ 52 1.1 alc void 53 1.1 alc ar5416StopPcuReceive(struct ath_hal *ah) 54 1.1 alc { 55 1.1 alc OS_REG_SET_BIT(ah, AR_DIAG_SW, AR_DIAG_RX_DIS | AR_DIAG_RX_ABORT); 56 1.1 alc 57 1.1 alc HALDEBUG(ah, HAL_DEBUG_RX, "%s: Stop PCU Receive \n", __func__); 58 1.1 alc ar5212DisableMibCounters(ah); 59 1.1 alc } 60 1.1 alc 61 1.1 alc /* 62 1.1 alc * Initialize RX descriptor, by clearing the status and setting 63 1.1 alc * the size (and any other flags). 64 1.1 alc */ 65 1.1 alc HAL_BOOL 66 1.1 alc ar5416SetupRxDesc(struct ath_hal *ah, struct ath_desc *ds, 67 1.1 alc uint32_t size, u_int flags) 68 1.1 alc { 69 1.1 alc struct ar5416_desc *ads = AR5416DESC(ds); 70 1.1 alc 71 1.1 alc HALASSERT((size &~ AR_BufLen) == 0); 72 1.1 alc 73 1.1 alc ads->ds_ctl1 = size & AR_BufLen; 74 1.1 alc if (flags & HAL_RXDESC_INTREQ) 75 1.1 alc ads->ds_ctl1 |= AR_RxIntrReq; 76 1.1 alc 77 1.1 alc /* this should be enough */ 78 1.1 alc ads->ds_rxstatus8 &= ~AR_RxDone; 79 1.1 alc 80 1.1 alc return AH_TRUE; 81 1.1 alc } 82 1.1 alc 83 1.1 alc /* 84 1.1 alc * Process an RX descriptor, and return the status to the caller. 85 1.1 alc * Copy some hardware specific items into the software portion 86 1.1 alc * of the descriptor. 87 1.1 alc * 88 1.1 alc * NB: the caller is responsible for validating the memory contents 89 1.1 alc * of the descriptor (e.g. flushing any cached copy). 90 1.1 alc */ 91 1.1 alc HAL_STATUS 92 1.1 alc ar5416ProcRxDesc(struct ath_hal *ah, struct ath_desc *ds, 93 1.1 alc uint32_t pa, struct ath_desc *nds, uint64_t tsf, 94 1.1 alc struct ath_rx_status *rs) 95 1.1 alc { 96 1.1 alc struct ar5416_desc *ads = AR5416DESC(ds); 97 1.1 alc struct ar5416_desc *ands = AR5416DESC(nds); 98 1.1 alc 99 1.1 alc if ((ads->ds_rxstatus8 & AR_RxDone) == 0) 100 1.1 alc return HAL_EINPROGRESS; 101 1.1 alc /* 102 1.1 alc * Given the use of a self-linked tail be very sure that the hw is 103 1.1 alc * done with this descriptor; the hw may have done this descriptor 104 1.1 alc * once and picked it up again...make sure the hw has moved on. 105 1.1 alc */ 106 1.1 alc if ((ands->ds_rxstatus8 & AR_RxDone) == 0 107 1.1 alc && OS_REG_READ(ah, AR_RXDP) == pa) 108 1.1 alc return HAL_EINPROGRESS; 109 1.1 alc 110 1.1 alc rs->rs_status = 0; 111 1.1 alc rs->rs_flags = 0; 112 1.1 alc 113 1.1 alc rs->rs_datalen = ads->ds_rxstatus1 & AR_DataLen; 114 1.1 alc rs->rs_tstamp = ads->AR_RcvTimestamp; 115 1.1 alc 116 1.1 alc /* XXX what about KeyCacheMiss? */ 117 1.1 alc 118 1.1 alc rs->rs_rssi = MS(ads->ds_rxstatus4, AR_RxRSSICombined); 119 1.1 alc rs->rs_rssi_ctl[0] = MS(ads->ds_rxstatus0, AR_RxRSSIAnt00); 120 1.1 alc rs->rs_rssi_ctl[1] = MS(ads->ds_rxstatus0, AR_RxRSSIAnt01); 121 1.1 alc rs->rs_rssi_ctl[2] = MS(ads->ds_rxstatus0, AR_RxRSSIAnt02); 122 1.1 alc rs->rs_rssi_ext[0] = MS(ads->ds_rxstatus4, AR_RxRSSIAnt10); 123 1.1 alc rs->rs_rssi_ext[1] = MS(ads->ds_rxstatus4, AR_RxRSSIAnt11); 124 1.1 alc rs->rs_rssi_ext[2] = MS(ads->ds_rxstatus4, AR_RxRSSIAnt12); 125 1.1 alc 126 1.1 alc if (ads->ds_rxstatus8 & AR_RxKeyIdxValid) 127 1.1 alc rs->rs_keyix = MS(ads->ds_rxstatus8, AR_KeyIdx); 128 1.1 alc else 129 1.1 alc rs->rs_keyix = HAL_RXKEYIX_INVALID; 130 1.1 alc 131 1.1 alc /* NB: caller expected to do rate table mapping */ 132 1.1 alc rs->rs_rate = RXSTATUS_RATE(ah, ads); 133 1.1 alc rs->rs_more = (ads->ds_rxstatus1 & AR_RxMore) ? 1 : 0; 134 1.1 alc 135 1.1 alc rs->rs_isaggr = (ads->ds_rxstatus8 & AR_RxAggr) ? 1 : 0; 136 1.1 alc rs->rs_moreaggr = (ads->ds_rxstatus8 & AR_RxMoreAggr) ? 1 : 0; 137 1.1 alc rs->rs_antenna = MS(ads->ds_rxstatus3, AR_RxAntenna); 138 1.1 alc 139 1.1 alc if (ads->ds_rxstatus3 & AR_GI) 140 1.1 alc rs->rs_flags |= HAL_RX_GI; 141 1.1 alc if (ads->ds_rxstatus3 & AR_2040) 142 1.1 alc rs->rs_flags |= HAL_RX_2040; 143 1.1 alc 144 1.1 alc if (ads->ds_rxstatus8 & AR_PreDelimCRCErr) 145 1.1 alc rs->rs_flags |= HAL_RX_DELIM_CRC_PRE; 146 1.1 alc if (ads->ds_rxstatus8 & AR_PostDelimCRCErr) 147 1.1 alc rs->rs_flags |= HAL_RX_DELIM_CRC_POST; 148 1.1 alc if (ads->ds_rxstatus8 & AR_DecryptBusyErr) 149 1.1 alc rs->rs_flags |= HAL_RX_DECRYPT_BUSY; 150 1.1 alc if (ads->ds_rxstatus8 & AR_HiRxChain) 151 1.1 alc rs->rs_flags |= HAL_RX_HI_RX_CHAIN; 152 1.1 alc 153 1.1 alc if ((ads->ds_rxstatus8 & AR_RxFrameOK) == 0) { 154 1.1 alc /* 155 1.1 alc * These four bits should not be set together. The 156 1.1 alc * 5416 spec states a Michael error can only occur if 157 1.1 alc * DecryptCRCErr not set (and TKIP is used). Experience 158 1.1 alc * indicates however that you can also get Michael errors 159 1.1 alc * when a CRC error is detected, but these are specious. 160 1.1 alc * Consequently we filter them out here so we don't 161 1.1 alc * confuse and/or complicate drivers. 162 1.1 alc */ 163 1.1 alc if (ads->ds_rxstatus8 & AR_CRCErr) 164 1.1 alc rs->rs_status |= HAL_RXERR_CRC; 165 1.1 alc else if (ads->ds_rxstatus8 & AR_PHYErr) { 166 1.1 alc u_int phyerr; 167 1.1 alc 168 1.1 alc rs->rs_status |= HAL_RXERR_PHY; 169 1.1 alc phyerr = MS(ads->ds_rxstatus8, AR_PHYErrCode); 170 1.1 alc rs->rs_phyerr = phyerr; 171 1.1 alc } else if (ads->ds_rxstatus8 & AR_DecryptCRCErr) 172 1.1 alc rs->rs_status |= HAL_RXERR_DECRYPT; 173 1.1 alc else if (ads->ds_rxstatus8 & AR_MichaelErr) 174 1.1 alc rs->rs_status |= HAL_RXERR_MIC; 175 1.1 alc } 176 1.1 alc 177 1.1 alc return HAL_OK; 178 1.1 alc } 179