1 /*- 2 * Copyright 2009 Solarflare Communications Inc. All rights reserved. 3 * 4 * Redistribution and use in source and binary forms, with or without 5 * modification, are permitted provided that the following conditions 6 * are met: 7 * 1. Redistributions of source code must retain the above copyright 8 * notice, this list of conditions and the following disclaimer. 9 * 2. Redistributions in binary form must reproduce the above copyright 10 * notice, this list of conditions and the following disclaimer in the 11 * documentation and/or other materials provided with the distribution. 12 * 13 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS AND 14 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 15 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 16 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 17 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 18 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 19 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 20 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 21 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 22 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 23 * SUCH DAMAGE. 24 */ 25 26 #include <sys/cdefs.h> 27 __FBSDID("$FreeBSD$"); 28 29 #include "efsys.h" 30 #include "efx.h" 31 #include "efx_impl.h" 32 33 #if EFSYS_OPT_SIENA 34 35 void 36 siena_sram_init( 37 __in efx_nic_t *enp) 38 { 39 efx_nic_cfg_t *encp = &(enp->en_nic_cfg); 40 efx_oword_t oword; 41 uint32_t rx_base, tx_base; 42 43 EFSYS_ASSERT3U(enp->en_magic, ==, EFX_NIC_MAGIC); 44 EFSYS_ASSERT(enp->en_family == EFX_FAMILY_SIENA); 45 46 rx_base = encp->enc_buftbl_limit; 47 tx_base = rx_base + (encp->enc_rxq_limit * 64); 48 49 /* Initialize the transmit descriptor cache */ 50 EFX_POPULATE_OWORD_1(oword, FRF_AZ_SRM_TX_DC_BASE_ADR, tx_base); 51 EFX_BAR_WRITEO(enp, FR_AZ_SRM_TX_DC_CFG_REG, &oword); 52 53 EFX_POPULATE_OWORD_1(oword, FRF_AZ_TX_DC_SIZE, 1); /* 16 descriptors */ 54 EFX_BAR_WRITEO(enp, FR_AZ_TX_DC_CFG_REG, &oword); 55 56 /* Initialize the receive descriptor cache */ 57 EFX_POPULATE_OWORD_1(oword, FRF_AZ_SRM_RX_DC_BASE_ADR, rx_base); 58 EFX_BAR_WRITEO(enp, FR_AZ_SRM_RX_DC_CFG_REG, &oword); 59 60 EFX_POPULATE_OWORD_1(oword, FRF_AZ_RX_DC_SIZE, 3); /* 64 descriptors */ 61 EFX_BAR_WRITEO(enp, FR_AZ_RX_DC_CFG_REG, &oword); 62 63 /* Set receive descriptor pre-fetch low water mark */ 64 EFX_POPULATE_OWORD_1(oword, FRF_AZ_RX_DC_PF_LWM, 56); 65 EFX_BAR_WRITEO(enp, FR_AZ_RX_DC_PF_WM_REG, &oword); 66 67 /* Set the event queue to use for SRAM updates */ 68 EFX_POPULATE_OWORD_1(oword, FRF_AZ_SRM_UPD_EVQ_ID, 0); 69 EFX_BAR_WRITEO(enp, FR_AZ_SRM_UPD_EVQ_REG, &oword); 70 } 71 72 #if EFSYS_OPT_DIAG 73 74 __checkReturn int 75 siena_sram_test( 76 __in efx_nic_t *enp, 77 __in efx_sram_pattern_fn_t func) 78 { 79 efx_oword_t oword; 80 efx_qword_t qword; 81 efx_qword_t verify; 82 size_t rows; 83 unsigned int wptr; 84 unsigned int rptr; 85 int rc; 86 87 EFSYS_ASSERT(enp->en_family == EFX_FAMILY_SIENA); 88 89 /* Reconfigure into HALF buffer table mode */ 90 EFX_POPULATE_OWORD_1(oword, FRF_AZ_BUF_TBL_MODE, 0); 91 EFX_BAR_WRITEO(enp, FR_AZ_BUF_TBL_CFG_REG, &oword); 92 93 /* 94 * Move the descriptor caches up to the top of SRAM, and test 95 * all of SRAM below them. We only miss out one row here. 96 */ 97 rows = SIENA_SRAM_ROWS - 1; 98 EFX_POPULATE_OWORD_1(oword, FRF_AZ_SRM_RX_DC_BASE_ADR, rows); 99 EFX_BAR_WRITEO(enp, FR_AZ_SRM_RX_DC_CFG_REG, &oword); 100 101 EFX_POPULATE_OWORD_1(oword, FRF_AZ_SRM_TX_DC_BASE_ADR, rows + 1); 102 EFX_BAR_WRITEO(enp, FR_AZ_SRM_TX_DC_CFG_REG, &oword); 103 104 /* 105 * Write the pattern through BUF_HALF_TBL. Write 106 * in 64 entry batches, waiting 1us in between each batch 107 * to guarantee not to overflow the SRAM fifo 108 */ 109 for (wptr = 0, rptr = 0; wptr < rows; ++wptr) { 110 func(wptr, B_FALSE, &qword); 111 EFX_BAR_TBL_WRITEQ(enp, FR_AZ_BUF_HALF_TBL, wptr, &qword); 112 113 if ((wptr - rptr) < 64 && wptr < rows - 1) 114 continue; 115 116 EFSYS_SPIN(1); 117 118 for (; rptr <= wptr; ++rptr) { 119 func(rptr, B_FALSE, &qword); 120 EFX_BAR_TBL_READQ(enp, FR_AZ_BUF_HALF_TBL, rptr, 121 &verify); 122 123 if (!EFX_QWORD_IS_EQUAL(verify, qword)) { 124 rc = EFAULT; 125 goto fail1; 126 } 127 } 128 } 129 130 /* And do the same negated */ 131 for (wptr = 0, rptr = 0; wptr < rows; ++wptr) { 132 func(wptr, B_TRUE, &qword); 133 EFX_BAR_TBL_WRITEQ(enp, FR_AZ_BUF_HALF_TBL, wptr, &qword); 134 135 if ((wptr - rptr) < 64 && wptr < rows - 1) 136 continue; 137 138 EFSYS_SPIN(1); 139 140 for (; rptr <= wptr; ++rptr) { 141 func(rptr, B_TRUE, &qword); 142 EFX_BAR_TBL_READQ(enp, FR_AZ_BUF_HALF_TBL, rptr, 143 &verify); 144 145 if (!EFX_QWORD_IS_EQUAL(verify, qword)) { 146 rc = EFAULT; 147 goto fail2; 148 } 149 } 150 } 151 152 /* Restore back to FULL buffer table mode */ 153 EFX_POPULATE_OWORD_1(oword, FRF_AZ_BUF_TBL_MODE, 1); 154 EFX_BAR_WRITEO(enp, FR_AZ_BUF_TBL_CFG_REG, &oword); 155 156 /* 157 * We don't need to reconfigure SRAM again because the API 158 * requires efx_nic_fini() to be called after an sram test. 159 */ 160 return (0); 161 162 fail2: 163 EFSYS_PROBE(fail2); 164 fail1: 165 EFSYS_PROBE1(fail1, int, rc); 166 167 /* Restore back to FULL buffer table mode */ 168 EFX_POPULATE_OWORD_1(oword, FRF_AZ_BUF_TBL_MODE, 1); 169 EFX_BAR_WRITEO(enp, FR_AZ_BUF_TBL_CFG_REG, &oword); 170 171 return (rc); 172 } 173 174 #endif /* EFSYS_OPT_DIAG */ 175 176 #endif /* EFSYS_OPT_SIENA */ 177