]> CyberLeo.Net >> Repos - FreeBSD/stable/8.git/blob - sys/dev/bce/if_bce.c
MFC r202717:
[FreeBSD/stable/8.git] / sys / dev / bce / if_bce.c
1 /*-
2  * Copyright (c) 2006-2009 Broadcom Corporation
3  *      David Christensen <davidch@broadcom.com>.  All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions
7  * are met:
8  *
9  * 1. Redistributions of source code must retain the above copyright
10  *    notice, this list of conditions and the following disclaimer.
11  * 2. Redistributions in binary form must reproduce the above copyright
12  *    notice, this list of conditions and the following disclaimer in the
13  *    documentation and/or other materials provided with the distribution.
14  * 3. Neither the name of Broadcom Corporation nor the name of its contributors
15  *    may be used to endorse or promote products derived from this software
16  *    without specific prior written consent.
17  *
18  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS'
19  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
20  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
21  * ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS
22  * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
23  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
24  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
25  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
26  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
27  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
28  * THE POSSIBILITY OF SUCH DAMAGE.
29  */
30
31 #include <sys/cdefs.h>
32 __FBSDID("$FreeBSD$");
33
34 /*
35  * The following controllers are supported by this driver:
36  *   BCM5706C A2, A3
37  *   BCM5706S A2, A3
38  *   BCM5708C B1, B2
39  *   BCM5708S B1, B2
40  *   BCM5709C A1, C0
41  *       BCM5716C C0
42  *
43  * The following controllers are not supported by this driver:
44  *   BCM5706C A0, A1 (pre-production)
45  *   BCM5706S A0, A1 (pre-production)
46  *   BCM5708C A0, B0 (pre-production)
47  *   BCM5708S A0, B0 (pre-production)
48  *   BCM5709C A0  B0, B1, B2 (pre-production)
49  *   BCM5709S A0, A1, B0, B1, B2, C0 (pre-production)
50  */
51
52 #include "opt_bce.h"
53
54 #include <dev/bce/if_bcereg.h>
55 #include <dev/bce/if_bcefw.h>
56
57 /****************************************************************************/
58 /* BCE Debug Options                                                        */
59 /****************************************************************************/
60 #ifdef BCE_DEBUG
61         u32 bce_debug = BCE_WARN;
62
63         /*          0 = Never              */
64         /*          1 = 1 in 2,147,483,648 */
65         /*        256 = 1 in     8,388,608 */
66         /*       2048 = 1 in     1,048,576 */
67         /*      65536 = 1 in        32,768 */
68         /*    1048576 = 1 in         2,048 */
69         /*  268435456 = 1 in             8 */
70         /*  536870912 = 1 in             4 */
71         /* 1073741824 = 1 in             2 */
72
73         /* Controls how often the l2_fhdr frame error check will fail. */
74         int l2fhdr_error_sim_control = 0;
75
76         /* Controls how often the unexpected attention check will fail. */
77         int unexpected_attention_sim_control = 0;
78
79         /* Controls how often to simulate an mbuf allocation failure. */
80         int mbuf_alloc_failed_sim_control = 0;
81
82         /* Controls how often to simulate a DMA mapping failure. */
83         int dma_map_addr_failed_sim_control = 0;
84
85         /* Controls how often to simulate a bootcode failure. */
86         int bootcode_running_failure_sim_control = 0;
87 #endif
88
89 /****************************************************************************/
90 /* BCE Build Time Options                                                   */
91 /****************************************************************************/
92 /* #define BCE_NVRAM_WRITE_SUPPORT 1 */
93
94
95 /****************************************************************************/
96 /* PCI Device ID Table                                                      */
97 /*                                                                          */
98 /* Used by bce_probe() to identify the devices supported by this driver.    */
99 /****************************************************************************/
100 #define BCE_DEVDESC_MAX         64
101
102 static struct bce_type bce_devs[] = {
103         /* BCM5706C Controllers and OEM boards. */
104         { BRCM_VENDORID, BRCM_DEVICEID_BCM5706,  HP_VENDORID, 0x3101,
105                 "HP NC370T Multifunction Gigabit Server Adapter" },
106         { BRCM_VENDORID, BRCM_DEVICEID_BCM5706,  HP_VENDORID, 0x3106,
107                 "HP NC370i Multifunction Gigabit Server Adapter" },
108         { BRCM_VENDORID, BRCM_DEVICEID_BCM5706,  HP_VENDORID, 0x3070,
109                 "HP NC380T PCIe DP Multifunc Gig Server Adapter" },
110         { BRCM_VENDORID, BRCM_DEVICEID_BCM5706,  HP_VENDORID, 0x1709,
111                 "HP NC371i Multifunction Gigabit Server Adapter" },
112         { BRCM_VENDORID, BRCM_DEVICEID_BCM5706,  PCI_ANY_ID,  PCI_ANY_ID,
113                 "Broadcom NetXtreme II BCM5706 1000Base-T" },
114
115         /* BCM5706S controllers and OEM boards. */
116         { BRCM_VENDORID, BRCM_DEVICEID_BCM5706S, HP_VENDORID, 0x3102,
117                 "HP NC370F Multifunction Gigabit Server Adapter" },
118         { BRCM_VENDORID, BRCM_DEVICEID_BCM5706S, PCI_ANY_ID,  PCI_ANY_ID,
119                 "Broadcom NetXtreme II BCM5706 1000Base-SX" },
120
121         /* BCM5708C controllers and OEM boards. */
122         { BRCM_VENDORID, BRCM_DEVICEID_BCM5708,  HP_VENDORID, 0x7037,
123                 "HP NC373T PCIe Multifunction Gig Server Adapter" },
124         { BRCM_VENDORID, BRCM_DEVICEID_BCM5708,  HP_VENDORID, 0x7038,
125                 "HP NC373i Multifunction Gigabit Server Adapter" },
126         { BRCM_VENDORID, BRCM_DEVICEID_BCM5708,  HP_VENDORID, 0x7045,
127                 "HP NC374m PCIe Multifunction Adapter" },
128         { BRCM_VENDORID, BRCM_DEVICEID_BCM5708,  PCI_ANY_ID,  PCI_ANY_ID,
129                 "Broadcom NetXtreme II BCM5708 1000Base-T" },
130
131         /* BCM5708S controllers and OEM boards. */
132         { BRCM_VENDORID, BRCM_DEVICEID_BCM5708S,  HP_VENDORID, 0x1706,
133                 "HP NC373m Multifunction Gigabit Server Adapter" },
134         { BRCM_VENDORID, BRCM_DEVICEID_BCM5708S,  HP_VENDORID, 0x703b,
135                 "HP NC373i Multifunction Gigabit Server Adapter" },
136         { BRCM_VENDORID, BRCM_DEVICEID_BCM5708S,  HP_VENDORID, 0x703d,
137                 "HP NC373F PCIe Multifunc Giga Server Adapter" },
138         { BRCM_VENDORID, BRCM_DEVICEID_BCM5708S,  PCI_ANY_ID,  PCI_ANY_ID,
139                 "Broadcom NetXtreme II BCM5708 1000Base-SX" },
140
141         /* BCM5709C controllers and OEM boards. */
142         { BRCM_VENDORID, BRCM_DEVICEID_BCM5709,  HP_VENDORID, 0x7055,
143                 "HP NC382i DP Multifunction Gigabit Server Adapter" },
144         { BRCM_VENDORID, BRCM_DEVICEID_BCM5709,  HP_VENDORID, 0x7059,
145                 "HP NC382T PCIe DP Multifunction Gigabit Server Adapter" },
146         { BRCM_VENDORID, BRCM_DEVICEID_BCM5709,  PCI_ANY_ID,  PCI_ANY_ID,
147                 "Broadcom NetXtreme II BCM5709 1000Base-T" },
148
149         /* BCM5709S controllers and OEM boards. */
150         { BRCM_VENDORID, BRCM_DEVICEID_BCM5709S,  HP_VENDORID, 0x171d,
151                 "HP NC382m DP 1GbE Multifunction BL-c Adapter" },
152         { BRCM_VENDORID, BRCM_DEVICEID_BCM5709S,  HP_VENDORID, 0x7056,
153                 "HP NC382i DP Multifunction Gigabit Server Adapter" },
154         { BRCM_VENDORID, BRCM_DEVICEID_BCM5709S,  PCI_ANY_ID,  PCI_ANY_ID,
155                 "Broadcom NetXtreme II BCM5709 1000Base-SX" },
156
157         /* BCM5716 controllers and OEM boards. */
158         { BRCM_VENDORID, BRCM_DEVICEID_BCM5716,  PCI_ANY_ID,  PCI_ANY_ID,
159                 "Broadcom NetXtreme II BCM5716 1000Base-T" },
160
161         { 0, 0, 0, 0, NULL }
162 };
163
164
165 /****************************************************************************/
166 /* Supported Flash NVRAM device data.                                       */
167 /****************************************************************************/
168 static struct flash_spec flash_table[] =
169 {
170 #define BUFFERED_FLAGS          (BCE_NV_BUFFERED | BCE_NV_TRANSLATE)
171 #define NONBUFFERED_FLAGS       (BCE_NV_WREN)
172
173         /* Slow EEPROM */
174         {0x00000000, 0x40830380, 0x009f0081, 0xa184a053, 0xaf000400,
175          BUFFERED_FLAGS, SEEPROM_PAGE_BITS, SEEPROM_PAGE_SIZE,
176          SEEPROM_BYTE_ADDR_MASK, SEEPROM_TOTAL_SIZE,
177          "EEPROM - slow"},
178         /* Expansion entry 0001 */
179         {0x08000002, 0x4b808201, 0x00050081, 0x03840253, 0xaf020406,
180          NONBUFFERED_FLAGS, SAIFUN_FLASH_PAGE_BITS, SAIFUN_FLASH_PAGE_SIZE,
181          SAIFUN_FLASH_BYTE_ADDR_MASK, 0,
182          "Entry 0001"},
183         /* Saifun SA25F010 (non-buffered flash) */
184         /* strap, cfg1, & write1 need updates */
185         {0x04000001, 0x47808201, 0x00050081, 0x03840253, 0xaf020406,
186          NONBUFFERED_FLAGS, SAIFUN_FLASH_PAGE_BITS, SAIFUN_FLASH_PAGE_SIZE,
187          SAIFUN_FLASH_BYTE_ADDR_MASK, SAIFUN_FLASH_BASE_TOTAL_SIZE*2,
188          "Non-buffered flash (128kB)"},
189         /* Saifun SA25F020 (non-buffered flash) */
190         /* strap, cfg1, & write1 need updates */
191         {0x0c000003, 0x4f808201, 0x00050081, 0x03840253, 0xaf020406,
192          NONBUFFERED_FLAGS, SAIFUN_FLASH_PAGE_BITS, SAIFUN_FLASH_PAGE_SIZE,
193          SAIFUN_FLASH_BYTE_ADDR_MASK, SAIFUN_FLASH_BASE_TOTAL_SIZE*4,
194          "Non-buffered flash (256kB)"},
195         /* Expansion entry 0100 */
196         {0x11000000, 0x53808201, 0x00050081, 0x03840253, 0xaf020406,
197          NONBUFFERED_FLAGS, SAIFUN_FLASH_PAGE_BITS, SAIFUN_FLASH_PAGE_SIZE,
198          SAIFUN_FLASH_BYTE_ADDR_MASK, 0,
199          "Entry 0100"},
200         /* Entry 0101: ST M45PE10 (non-buffered flash, TetonII B0) */
201         {0x19000002, 0x5b808201, 0x000500db, 0x03840253, 0xaf020406,
202          NONBUFFERED_FLAGS, ST_MICRO_FLASH_PAGE_BITS, ST_MICRO_FLASH_PAGE_SIZE,
203          ST_MICRO_FLASH_BYTE_ADDR_MASK, ST_MICRO_FLASH_BASE_TOTAL_SIZE*2,
204          "Entry 0101: ST M45PE10 (128kB non-bufferred)"},
205         /* Entry 0110: ST M45PE20 (non-buffered flash)*/
206         {0x15000001, 0x57808201, 0x000500db, 0x03840253, 0xaf020406,
207          NONBUFFERED_FLAGS, ST_MICRO_FLASH_PAGE_BITS, ST_MICRO_FLASH_PAGE_SIZE,
208          ST_MICRO_FLASH_BYTE_ADDR_MASK, ST_MICRO_FLASH_BASE_TOTAL_SIZE*4,
209          "Entry 0110: ST M45PE20 (256kB non-bufferred)"},
210         /* Saifun SA25F005 (non-buffered flash) */
211         /* strap, cfg1, & write1 need updates */
212         {0x1d000003, 0x5f808201, 0x00050081, 0x03840253, 0xaf020406,
213          NONBUFFERED_FLAGS, SAIFUN_FLASH_PAGE_BITS, SAIFUN_FLASH_PAGE_SIZE,
214          SAIFUN_FLASH_BYTE_ADDR_MASK, SAIFUN_FLASH_BASE_TOTAL_SIZE,
215          "Non-buffered flash (64kB)"},
216         /* Fast EEPROM */
217         {0x22000000, 0x62808380, 0x009f0081, 0xa184a053, 0xaf000400,
218          BUFFERED_FLAGS, SEEPROM_PAGE_BITS, SEEPROM_PAGE_SIZE,
219          SEEPROM_BYTE_ADDR_MASK, SEEPROM_TOTAL_SIZE,
220          "EEPROM - fast"},
221         /* Expansion entry 1001 */
222         {0x2a000002, 0x6b808201, 0x00050081, 0x03840253, 0xaf020406,
223          NONBUFFERED_FLAGS, SAIFUN_FLASH_PAGE_BITS, SAIFUN_FLASH_PAGE_SIZE,
224          SAIFUN_FLASH_BYTE_ADDR_MASK, 0,
225          "Entry 1001"},
226         /* Expansion entry 1010 */
227         {0x26000001, 0x67808201, 0x00050081, 0x03840253, 0xaf020406,
228          NONBUFFERED_FLAGS, SAIFUN_FLASH_PAGE_BITS, SAIFUN_FLASH_PAGE_SIZE,
229          SAIFUN_FLASH_BYTE_ADDR_MASK, 0,
230          "Entry 1010"},
231         /* ATMEL AT45DB011B (buffered flash) */
232         {0x2e000003, 0x6e808273, 0x00570081, 0x68848353, 0xaf000400,
233          BUFFERED_FLAGS, BUFFERED_FLASH_PAGE_BITS, BUFFERED_FLASH_PAGE_SIZE,
234          BUFFERED_FLASH_BYTE_ADDR_MASK, BUFFERED_FLASH_TOTAL_SIZE,
235          "Buffered flash (128kB)"},
236         /* Expansion entry 1100 */
237         {0x33000000, 0x73808201, 0x00050081, 0x03840253, 0xaf020406,
238          NONBUFFERED_FLAGS, SAIFUN_FLASH_PAGE_BITS, SAIFUN_FLASH_PAGE_SIZE,
239          SAIFUN_FLASH_BYTE_ADDR_MASK, 0,
240          "Entry 1100"},
241         /* Expansion entry 1101 */
242         {0x3b000002, 0x7b808201, 0x00050081, 0x03840253, 0xaf020406,
243          NONBUFFERED_FLAGS, SAIFUN_FLASH_PAGE_BITS, SAIFUN_FLASH_PAGE_SIZE,
244          SAIFUN_FLASH_BYTE_ADDR_MASK, 0,
245          "Entry 1101"},
246         /* Ateml Expansion entry 1110 */
247         {0x37000001, 0x76808273, 0x00570081, 0x68848353, 0xaf000400,
248          BUFFERED_FLAGS, BUFFERED_FLASH_PAGE_BITS, BUFFERED_FLASH_PAGE_SIZE,
249          BUFFERED_FLASH_BYTE_ADDR_MASK, 0,
250          "Entry 1110 (Atmel)"},
251         /* ATMEL AT45DB021B (buffered flash) */
252         {0x3f000003, 0x7e808273, 0x00570081, 0x68848353, 0xaf000400,
253          BUFFERED_FLAGS, BUFFERED_FLASH_PAGE_BITS, BUFFERED_FLASH_PAGE_SIZE,
254          BUFFERED_FLASH_BYTE_ADDR_MASK, BUFFERED_FLASH_TOTAL_SIZE*2,
255          "Buffered flash (256kB)"},
256 };
257
258 /*
259  * The BCM5709 controllers transparently handle the
260  * differences between Atmel 264 byte pages and all
261  * flash devices which use 256 byte pages, so no
262  * logical-to-physical mapping is required in the
263  * driver.
264  */
265 static struct flash_spec flash_5709 = {
266         .flags          = BCE_NV_BUFFERED,
267         .page_bits      = BCM5709_FLASH_PAGE_BITS,
268         .page_size      = BCM5709_FLASH_PAGE_SIZE,
269         .addr_mask      = BCM5709_FLASH_BYTE_ADDR_MASK,
270         .total_size     = BUFFERED_FLASH_TOTAL_SIZE * 2,
271         .name           = "5709/5716 buffered flash (256kB)",
272 };
273
274
275 /****************************************************************************/
276 /* FreeBSD device entry points.                                             */
277 /****************************************************************************/
278 static int  bce_probe                           (device_t);
279 static int  bce_attach                          (device_t);
280 static int  bce_detach                          (device_t);
281 static int  bce_shutdown                        (device_t);
282
283
284 /****************************************************************************/
285 /* BCE Debug Data Structure Dump Routines                                   */
286 /****************************************************************************/
287 #ifdef BCE_DEBUG
288 static u32      bce_reg_rd                              (struct bce_softc *, u32);
289 static void     bce_reg_wr                              (struct bce_softc *, u32, u32);
290 static void     bce_reg_wr16                    (struct bce_softc *, u32, u16);
291 static u32  bce_ctx_rd                          (struct bce_softc *, u32, u32);
292 static void bce_dump_enet           (struct bce_softc *, struct mbuf *);
293 static void bce_dump_mbuf                       (struct bce_softc *, struct mbuf *);
294 static void bce_dump_tx_mbuf_chain      (struct bce_softc *, u16, int);
295 static void bce_dump_rx_mbuf_chain      (struct bce_softc *, u16, int);
296 #ifdef BCE_JUMBO_HDRSPLIT
297 static void bce_dump_pg_mbuf_chain      (struct bce_softc *, u16, int);
298 #endif
299 static void bce_dump_txbd                       (struct bce_softc *, int, struct tx_bd *);
300 static void bce_dump_rxbd                       (struct bce_softc *, int, struct rx_bd *);
301 #ifdef BCE_JUMBO_HDRSPLIT
302 static void bce_dump_pgbd                       (struct bce_softc *, int, struct rx_bd *);
303 #endif
304 static void bce_dump_l2fhdr                     (struct bce_softc *, int, struct l2_fhdr *);
305 static void bce_dump_ctx                        (struct bce_softc *, u16);
306 static void bce_dump_ftqs                       (struct bce_softc *);
307 static void bce_dump_tx_chain           (struct bce_softc *, u16, int);
308 static void bce_dump_rx_chain           (struct bce_softc *, u16, int);
309 #ifdef BCE_JUMBO_HDRSPLIT
310 static void bce_dump_pg_chain           (struct bce_softc *, u16, int);
311 #endif
312 static void bce_dump_status_block       (struct bce_softc *);
313 static void bce_dump_stats_block        (struct bce_softc *);
314 static void bce_dump_driver_state       (struct bce_softc *);
315 static void bce_dump_hw_state           (struct bce_softc *);
316 static void bce_dump_mq_regs        (struct bce_softc *);
317 static void bce_dump_bc_state           (struct bce_softc *);
318 static void bce_dump_txp_state          (struct bce_softc *, int);
319 static void bce_dump_rxp_state          (struct bce_softc *, int);
320 static void bce_dump_tpat_state         (struct bce_softc *, int);
321 static void bce_dump_cp_state           (struct bce_softc *, int);
322 static void bce_dump_com_state          (struct bce_softc *, int);
323 static void bce_breakpoint                      (struct bce_softc *);
324 #endif
325
326
327 /****************************************************************************/
328 /* BCE Register/Memory Access Routines                                      */
329 /****************************************************************************/
330 static u32  bce_reg_rd_ind                      (struct bce_softc *, u32);
331 static void bce_reg_wr_ind                      (struct bce_softc *, u32, u32);
332 static void bce_shmem_wr            (struct bce_softc *, u32, u32);
333 static u32  bce_shmem_rd            (struct bce_softc *, u32);
334 static void bce_ctx_wr                          (struct bce_softc *, u32, u32, u32);
335 static int  bce_miibus_read_reg         (device_t, int, int);
336 static int  bce_miibus_write_reg        (device_t, int, int, int);
337 static void bce_miibus_statchg          (device_t);
338
339
340 /****************************************************************************/
341 /* BCE NVRAM Access Routines                                                */
342 /****************************************************************************/
343 static int  bce_acquire_nvram_lock      (struct bce_softc *);
344 static int  bce_release_nvram_lock      (struct bce_softc *);
345 static void bce_enable_nvram_access     (struct bce_softc *);
346 static void     bce_disable_nvram_access(struct bce_softc *);
347 static int  bce_nvram_read_dword        (struct bce_softc *, u32, u8 *, u32);
348 static int  bce_init_nvram                      (struct bce_softc *);
349 static int  bce_nvram_read                      (struct bce_softc *, u32, u8 *, int);
350 static int  bce_nvram_test                      (struct bce_softc *);
351 #ifdef BCE_NVRAM_WRITE_SUPPORT
352 static int  bce_enable_nvram_write      (struct bce_softc *);
353 static void bce_disable_nvram_write     (struct bce_softc *);
354 static int  bce_nvram_erase_page        (struct bce_softc *, u32);
355 static int  bce_nvram_write_dword       (struct bce_softc *, u32, u8 *, u32);
356 static int  bce_nvram_write                     (struct bce_softc *, u32, u8 *, int);
357 #endif
358
359 /****************************************************************************/
360 /*                                                                          */
361 /****************************************************************************/
362 static void bce_get_media                       (struct bce_softc *);
363 static void bce_dma_map_addr            (void *, bus_dma_segment_t *, int, int);
364 static int  bce_dma_alloc                       (device_t);
365 static void bce_dma_free                        (struct bce_softc *);
366 static void bce_release_resources       (struct bce_softc *);
367
368 /****************************************************************************/
369 /* BCE Firmware Synchronization and Load                                    */
370 /****************************************************************************/
371 static int  bce_fw_sync                         (struct bce_softc *, u32);
372 static void bce_load_rv2p_fw            (struct bce_softc *, u32 *, u32, u32);
373 static void bce_load_cpu_fw                     (struct bce_softc *, struct cpu_reg *, struct fw_info *);
374 static void bce_start_cpu           (struct bce_softc *, struct cpu_reg *);
375 static void bce_halt_cpu            (struct bce_softc *, struct cpu_reg *);
376 static void bce_start_rxp_cpu       (struct bce_softc *);
377 static void bce_init_rxp_cpu            (struct bce_softc *);
378 static void bce_init_txp_cpu            (struct bce_softc *);
379 static void bce_init_tpat_cpu           (struct bce_softc *);
380 static void bce_init_cp_cpu                     (struct bce_softc *);
381 static void bce_init_com_cpu            (struct bce_softc *);
382 static void bce_init_cpus                       (struct bce_softc *);
383
384 static void     bce_print_adapter_info  (struct bce_softc *);
385 static void bce_probe_pci_caps          (device_t, struct bce_softc *);
386 static void bce_stop                            (struct bce_softc *);
387 static int  bce_reset                           (struct bce_softc *, u32);
388 static int  bce_chipinit                        (struct bce_softc *);
389 static int  bce_blockinit                       (struct bce_softc *);
390
391 static int  bce_init_tx_chain           (struct bce_softc *);
392 static void bce_free_tx_chain           (struct bce_softc *);
393
394 static int  bce_get_rx_buf                      (struct bce_softc *, struct mbuf *, u16 *, u16 *, u32 *);
395 static int  bce_init_rx_chain           (struct bce_softc *);
396 static void bce_fill_rx_chain           (struct bce_softc *);
397 static void bce_free_rx_chain           (struct bce_softc *);
398
399 #ifdef BCE_JUMBO_HDRSPLIT
400 static int  bce_get_pg_buf                      (struct bce_softc *, struct mbuf *, u16 *, u16 *);
401 static int  bce_init_pg_chain           (struct bce_softc *);
402 static void bce_fill_pg_chain           (struct bce_softc *);
403 static void bce_free_pg_chain           (struct bce_softc *);
404 #endif
405
406 static int  bce_tx_encap                        (struct bce_softc *, struct mbuf **);
407 static void bce_start_locked            (struct ifnet *);
408 static void bce_start                           (struct ifnet *);
409 static int  bce_ioctl                           (struct ifnet *, u_long, caddr_t);
410 static void bce_watchdog                        (struct bce_softc *);
411 static int  bce_ifmedia_upd                     (struct ifnet *);
412 static void bce_ifmedia_upd_locked      (struct ifnet *);
413 static void bce_ifmedia_sts                     (struct ifnet *, struct ifmediareq *);
414 static void bce_init_locked                     (struct bce_softc *);
415 static void bce_init                            (void *);
416 static void bce_mgmt_init_locked        (struct bce_softc *sc);
417
418 static void bce_init_ctx                        (struct bce_softc *);
419 static void bce_get_mac_addr            (struct bce_softc *);
420 static void bce_set_mac_addr            (struct bce_softc *);
421 static void bce_phy_intr                        (struct bce_softc *);
422 static inline u16 bce_get_hw_rx_cons(struct bce_softc *);
423 static void bce_rx_intr                         (struct bce_softc *);
424 static void bce_tx_intr                         (struct bce_softc *);
425 static void bce_disable_intr            (struct bce_softc *);
426 static void bce_enable_intr                     (struct bce_softc *, int);
427
428 static void bce_intr                            (void *);
429 static void bce_set_rx_mode                     (struct bce_softc *);
430 static void bce_stats_update            (struct bce_softc *);
431 static void bce_tick                            (void *);
432 static void bce_pulse                           (void *);
433 static void bce_add_sysctls                     (struct bce_softc *);
434
435
436 /****************************************************************************/
437 /* FreeBSD device dispatch table.                                           */
438 /****************************************************************************/
439 static device_method_t bce_methods[] = {
440         /* Device interface (device_if.h) */
441         DEVMETHOD(device_probe,         bce_probe),
442         DEVMETHOD(device_attach,        bce_attach),
443         DEVMETHOD(device_detach,        bce_detach),
444         DEVMETHOD(device_shutdown,      bce_shutdown),
445 /* Supported by device interface but not used here. */
446 /*      DEVMETHOD(device_identify,      bce_identify),      */
447 /*      DEVMETHOD(device_suspend,       bce_suspend),       */
448 /*      DEVMETHOD(device_resume,        bce_resume),        */
449 /*      DEVMETHOD(device_quiesce,       bce_quiesce),       */
450
451         /* Bus interface (bus_if.h) */
452         DEVMETHOD(bus_print_child,      bus_generic_print_child),
453         DEVMETHOD(bus_driver_added,     bus_generic_driver_added),
454
455         /* MII interface (miibus_if.h) */
456         DEVMETHOD(miibus_readreg,       bce_miibus_read_reg),
457         DEVMETHOD(miibus_writereg,      bce_miibus_write_reg),
458         DEVMETHOD(miibus_statchg,       bce_miibus_statchg),
459 /* Supported by MII interface but not used here.       */
460 /*      DEVMETHOD(miibus_linkchg,       bce_miibus_linkchg),   */
461 /*      DEVMETHOD(miibus_mediainit,     bce_miibus_mediainit), */
462
463         { 0, 0 }
464 };
465
466 static driver_t bce_driver = {
467         "bce",
468         bce_methods,
469         sizeof(struct bce_softc)
470 };
471
472 static devclass_t bce_devclass;
473
474 MODULE_DEPEND(bce, pci, 1, 1, 1);
475 MODULE_DEPEND(bce, ether, 1, 1, 1);
476 MODULE_DEPEND(bce, miibus, 1, 1, 1);
477
478 DRIVER_MODULE(bce, pci, bce_driver, bce_devclass, 0, 0);
479 DRIVER_MODULE(miibus, bce, miibus_driver, miibus_devclass, 0, 0);
480
481
482 /****************************************************************************/
483 /* Tunable device values                                                    */
484 /****************************************************************************/
485 SYSCTL_NODE(_hw, OID_AUTO, bce, CTLFLAG_RD, 0, "bce driver parameters");
486
487 /* Allowable values are TRUE or FALSE */
488 static int bce_tso_enable = TRUE;
489 TUNABLE_INT("hw.bce.tso_enable", &bce_tso_enable);
490 SYSCTL_UINT(_hw_bce, OID_AUTO, tso_enable, CTLFLAG_RDTUN, &bce_tso_enable, 0,
491 "TSO Enable/Disable");
492
493 /* Allowable values are 0 (IRQ), 1 (MSI/IRQ), and 2 (MSI-X/MSI/IRQ) */
494 /* ToDo: Add MSI-X support. */
495 static int bce_msi_enable = 1;
496 TUNABLE_INT("hw.bce.msi_enable", &bce_msi_enable);
497 SYSCTL_UINT(_hw_bce, OID_AUTO, msi_enable, CTLFLAG_RDTUN, &bce_msi_enable, 0,
498 "MSI-X|MSI|INTx selector");
499
500 /* ToDo: Add tunable to enable/disable strict MTU handling. */
501 /* Currently allows "loose" RX MTU checking (i.e. sets the  */
502 /* H/W RX MTU to the size of the largest receive buffer, or */
503 /* 2048 bytes). This will cause a UNH failure but is more   */
504 /* desireable from a functional perspective.                */
505
506
507 /****************************************************************************/
508 /* Device probe function.                                                   */
509 /*                                                                          */
510 /* Compares the device to the driver's list of supported devices and        */
511 /* reports back to the OS whether this is the right driver for the device.  */
512 /*                                                                          */
513 /* Returns:                                                                 */
514 /*   BUS_PROBE_DEFAULT on success, positive value on failure.               */
515 /****************************************************************************/
516 static int
517 bce_probe(device_t dev)
518 {
519         struct bce_type *t;
520         struct bce_softc *sc;
521         char *descbuf;
522         u16 vid = 0, did = 0, svid = 0, sdid = 0;
523
524         t = bce_devs;
525
526         sc = device_get_softc(dev);
527         bzero(sc, sizeof(struct bce_softc));
528         sc->bce_unit = device_get_unit(dev);
529         sc->bce_dev = dev;
530
531         /* Get the data for the device to be probed. */
532         vid  = pci_get_vendor(dev);
533         did  = pci_get_device(dev);
534         svid = pci_get_subvendor(dev);
535         sdid = pci_get_subdevice(dev);
536
537         DBPRINT(sc, BCE_EXTREME_LOAD,
538                 "%s(); VID = 0x%04X, DID = 0x%04X, SVID = 0x%04X, "
539                 "SDID = 0x%04X\n", __FUNCTION__, vid, did, svid, sdid);
540
541         /* Look through the list of known devices for a match. */
542         while(t->bce_name != NULL) {
543
544                 if ((vid == t->bce_vid) && (did == t->bce_did) &&
545                         ((svid == t->bce_svid) || (t->bce_svid == PCI_ANY_ID)) &&
546                         ((sdid == t->bce_sdid) || (t->bce_sdid == PCI_ANY_ID))) {
547
548                         descbuf = malloc(BCE_DEVDESC_MAX, M_TEMP, M_NOWAIT);
549
550                         if (descbuf == NULL)
551                                 return(ENOMEM);
552
553                         /* Print out the device identity. */
554                         snprintf(descbuf, BCE_DEVDESC_MAX, "%s (%c%d)",
555                                 t->bce_name,
556                             (((pci_read_config(dev, PCIR_REVID, 4) & 0xf0) >> 4) + 'A'),
557                             (pci_read_config(dev, PCIR_REVID, 4) & 0xf));
558
559                         device_set_desc_copy(dev, descbuf);
560                         free(descbuf, M_TEMP);
561                         return(BUS_PROBE_DEFAULT);
562                 }
563                 t++;
564         }
565
566         return(ENXIO);
567 }
568
569
570 /****************************************************************************/
571 /* PCI Capabilities Probe Function.                                         */
572 /*                                                                          */
573 /* Walks the PCI capabiites list for the device to find what features are   */
574 /* supported.                                                               */
575 /*                                                                          */
576 /* Returns:                                                                 */
577 /*   None.                                                                  */
578 /****************************************************************************/
579 static void
580 bce_print_adapter_info(struct bce_softc *sc)
581 {
582     int i = 0;
583
584         DBENTER(BCE_VERBOSE_LOAD);
585
586         BCE_PRINTF("ASIC (0x%08X); ", sc->bce_chipid);
587         printf("Rev (%c%d); ", ((BCE_CHIP_ID(sc) & 0xf000) >> 12) + 'A',
588                 ((BCE_CHIP_ID(sc) & 0x0ff0) >> 4));
589
590         /* Bus info. */
591         if (sc->bce_flags & BCE_PCIE_FLAG) {
592                 printf("Bus (PCIe x%d, ", sc->link_width);
593                 switch (sc->link_speed) {
594                         case 1: printf("2.5Gbps); "); break;
595                         case 2: printf("5Gbps); "); break;
596                         default: printf("Unknown link speed); ");
597                 }
598         } else {
599                 printf("Bus (PCI%s, %s, %dMHz); ",
600                         ((sc->bce_flags & BCE_PCIX_FLAG) ? "-X" : ""),
601                         ((sc->bce_flags & BCE_PCI_32BIT_FLAG) ? "32-bit" : "64-bit"),
602                         sc->bus_speed_mhz);
603         }
604
605         /* Firmware version and device features. */
606         printf("B/C (%s); Flags (", sc->bce_bc_ver);
607
608 #ifdef BCE_JUMBO_HDRSPLIT
609         printf("SPLT");
610     i++;
611 #endif
612
613     if (sc->bce_flags & BCE_USING_MSI_FLAG) {
614         if (i > 0) printf("|");
615                 printf("MSI"); i++;
616     }
617
618     if (sc->bce_flags & BCE_USING_MSIX_FLAG) {
619         if (i > 0) printf("|");
620                 printf("MSI-X"); i++;
621     }
622
623     if (sc->bce_phy_flags & BCE_PHY_2_5G_CAPABLE_FLAG) {
624         if (i > 0) printf("|");
625                 printf("2.5G"); i++;
626     }
627
628     if (sc->bce_flags & BCE_MFW_ENABLE_FLAG) {
629         if (i > 0) printf("|");
630         printf("MFW); MFW (%s)\n", sc->bce_mfw_ver);
631     } else {
632         printf(")\n");
633     }
634
635         DBEXIT(BCE_VERBOSE_LOAD);
636 }
637
638
639 /****************************************************************************/
640 /* PCI Capabilities Probe Function.                                         */
641 /*                                                                          */
642 /* Walks the PCI capabiites list for the device to find what features are   */
643 /* supported.                                                               */
644 /*                                                                          */
645 /* Returns:                                                                 */
646 /*   None.                                                                  */
647 /****************************************************************************/
648 static void
649 bce_probe_pci_caps(device_t dev, struct bce_softc *sc)
650 {
651         u32 reg;
652
653         DBENTER(BCE_VERBOSE_LOAD);
654
655         /* Check if PCI-X capability is enabled. */
656         if (pci_find_extcap(dev, PCIY_PCIX, &reg) == 0) {
657                 if (reg != 0)
658                         sc->bce_cap_flags |= BCE_PCIX_CAPABLE_FLAG;
659         }
660
661         /* Check if PCIe capability is enabled. */
662         if (pci_find_extcap(dev, PCIY_EXPRESS, &reg) == 0) {
663                 if (reg != 0) {
664                         u16 link_status = pci_read_config(dev, reg + 0x12, 2);
665                         DBPRINT(sc, BCE_INFO_LOAD, "PCIe link_status = 0x%08X\n",
666                                 link_status);
667                         sc->link_speed = link_status & 0xf;
668                         sc->link_width = (link_status >> 4) & 0x3f;
669                         sc->bce_cap_flags |= BCE_PCIE_CAPABLE_FLAG;
670                         sc->bce_flags |= BCE_PCIE_FLAG;
671                 }
672         }
673
674         /* Check if MSI capability is enabled. */
675         if (pci_find_extcap(dev, PCIY_MSI, &reg) == 0) {
676                 if (reg != 0)
677                         sc->bce_cap_flags |= BCE_MSI_CAPABLE_FLAG;
678         }
679
680         /* Check if MSI-X capability is enabled. */
681         if (pci_find_extcap(dev, PCIY_MSIX, &reg) == 0) {
682                 if (reg != 0)
683                         sc->bce_cap_flags |= BCE_MSIX_CAPABLE_FLAG;
684         }
685
686         DBEXIT(BCE_VERBOSE_LOAD);
687 }
688
689
690 /****************************************************************************/
691 /* Device attach function.                                                  */
692 /*                                                                          */
693 /* Allocates device resources, performs secondary chip identification,      */
694 /* resets and initializes the hardware, and initializes driver instance     */
695 /* variables.                                                               */
696 /*                                                                          */
697 /* Returns:                                                                 */
698 /*   0 on success, positive value on failure.                               */
699 /****************************************************************************/
700 static int
701 bce_attach(device_t dev)
702 {
703         struct bce_softc *sc;
704         struct ifnet *ifp;
705         u32 val;
706         int error, rid, rc = 0;
707
708         sc = device_get_softc(dev);
709         sc->bce_dev = dev;
710
711         DBENTER(BCE_VERBOSE_LOAD | BCE_VERBOSE_RESET);
712
713         sc->bce_unit = device_get_unit(dev);
714
715         /* Set initial device and PHY flags */
716         sc->bce_flags = 0;
717         sc->bce_phy_flags = 0;
718
719         pci_enable_busmaster(dev);
720
721         /* Allocate PCI memory resources. */
722         rid = PCIR_BAR(0);
723         sc->bce_res_mem = bus_alloc_resource_any(dev, SYS_RES_MEMORY,
724                 &rid, RF_ACTIVE);
725
726         if (sc->bce_res_mem == NULL) {
727                 BCE_PRINTF("%s(%d): PCI memory allocation failed\n",
728                         __FILE__, __LINE__);
729                 rc = ENXIO;
730                 goto bce_attach_fail;
731         }
732
733         /* Get various resource handles. */
734         sc->bce_btag    = rman_get_bustag(sc->bce_res_mem);
735         sc->bce_bhandle = rman_get_bushandle(sc->bce_res_mem);
736         sc->bce_vhandle = (vm_offset_t) rman_get_virtual(sc->bce_res_mem);
737
738         bce_probe_pci_caps(dev, sc);
739
740         rid = 1;
741 #if 0
742         /* Try allocating MSI-X interrupts. */
743         if ((sc->bce_cap_flags & BCE_MSIX_CAPABLE_FLAG) &&
744                 (bce_msi_enable >= 2) &&
745                 ((sc->bce_res_irq = bus_alloc_resource_any(dev, SYS_RES_MEMORY,
746                 &rid, RF_ACTIVE)) != NULL)) {
747
748                 msi_needed = sc->bce_msi_count = 1;
749
750                 if (((error = pci_alloc_msix(dev, &sc->bce_msi_count)) != 0) ||
751                         (sc->bce_msi_count != msi_needed)) {
752                         BCE_PRINTF("%s(%d): MSI-X allocation failed! Requested = %d,"
753                                 "Received = %d, error = %d\n", __FILE__, __LINE__,
754                                 msi_needed, sc->bce_msi_count, error);
755                         sc->bce_msi_count = 0;
756                         pci_release_msi(dev);
757                         bus_release_resource(dev, SYS_RES_MEMORY, rid,
758                                 sc->bce_res_irq);
759                         sc->bce_res_irq = NULL;
760                 } else {
761                         DBPRINT(sc, BCE_INFO_LOAD, "%s(): Using MSI-X interrupt.\n",
762                                 __FUNCTION__);
763                         sc->bce_flags |= BCE_USING_MSIX_FLAG;
764                         sc->bce_intr = bce_intr;
765                 }
766         }
767 #endif
768
769         /* Try allocating a MSI interrupt. */
770         if ((sc->bce_cap_flags & BCE_MSI_CAPABLE_FLAG) &&
771                 (bce_msi_enable >= 1) && (sc->bce_msi_count == 0)) {
772                 sc->bce_msi_count = 1;
773                 if ((error = pci_alloc_msi(dev, &sc->bce_msi_count)) != 0) {
774                         BCE_PRINTF("%s(%d): MSI allocation failed! error = %d\n",
775                                 __FILE__, __LINE__, error);
776                         sc->bce_msi_count = 0;
777                         pci_release_msi(dev);
778                 } else {
779                         DBPRINT(sc, BCE_INFO_LOAD, "%s(): Using MSI interrupt.\n",
780                                 __FUNCTION__);
781                         sc->bce_flags |= BCE_USING_MSI_FLAG;
782                         if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
783                                 (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716))
784                                 sc->bce_flags |= BCE_ONE_SHOT_MSI_FLAG;
785                         sc->bce_irq_rid = 1;
786                         sc->bce_intr = bce_intr;
787                 }
788         }
789
790         /* Try allocating a legacy interrupt. */
791         if (sc->bce_msi_count == 0) {
792                 DBPRINT(sc, BCE_INFO_LOAD, "%s(): Using INTx interrupt.\n",
793                         __FUNCTION__);
794                 rid = 0;
795                 sc->bce_intr = bce_intr;
796         }
797
798         sc->bce_res_irq = bus_alloc_resource_any(dev, SYS_RES_IRQ,
799                 &rid, RF_SHAREABLE | RF_ACTIVE);
800
801         sc->bce_irq_rid = rid;
802
803         /* Report any IRQ allocation errors. */
804         if (sc->bce_res_irq == NULL) {
805                 BCE_PRINTF("%s(%d): PCI map interrupt failed!\n",
806                         __FILE__, __LINE__);
807                 rc = ENXIO;
808                 goto bce_attach_fail;
809         }
810
811         /* Initialize mutex for the current device instance. */
812         BCE_LOCK_INIT(sc, device_get_nameunit(dev));
813
814         /*
815          * Configure byte swap and enable indirect register access.
816          * Rely on CPU to do target byte swapping on big endian systems.
817          * Access to registers outside of PCI configurtion space are not
818          * valid until this is done.
819          */
820         pci_write_config(dev, BCE_PCICFG_MISC_CONFIG,
821                                BCE_PCICFG_MISC_CONFIG_REG_WINDOW_ENA |
822                                BCE_PCICFG_MISC_CONFIG_TARGET_MB_WORD_SWAP, 4);
823
824         /* Save ASIC revsion info. */
825         sc->bce_chipid =  REG_RD(sc, BCE_MISC_ID);
826
827         /* Weed out any non-production controller revisions. */
828         switch(BCE_CHIP_ID(sc)) {
829                 case BCE_CHIP_ID_5706_A0:
830                 case BCE_CHIP_ID_5706_A1:
831                 case BCE_CHIP_ID_5708_A0:
832                 case BCE_CHIP_ID_5708_B0:
833                 case BCE_CHIP_ID_5709_A0:
834                 case BCE_CHIP_ID_5709_B0:
835                 case BCE_CHIP_ID_5709_B1:
836                 case BCE_CHIP_ID_5709_B2:
837                         BCE_PRINTF("%s(%d): Unsupported controller revision (%c%d)!\n",
838                                 __FILE__, __LINE__,
839                                 (((pci_read_config(dev, PCIR_REVID, 4) & 0xf0) >> 4) + 'A'),
840                             (pci_read_config(dev, PCIR_REVID, 4) & 0xf));
841                         rc = ENODEV;
842                         goto bce_attach_fail;
843         }
844
845         /*
846          * The embedded PCIe to PCI-X bridge (EPB)
847          * in the 5708 cannot address memory above
848          * 40 bits (E7_5708CB1_23043 & E6_5708SB1_23043).
849          */
850         if (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5708)
851                 sc->max_bus_addr = BCE_BUS_SPACE_MAXADDR;
852         else
853                 sc->max_bus_addr = BUS_SPACE_MAXADDR;
854
855         /*
856          * Find the base address for shared memory access.
857          * Newer versions of bootcode use a signature and offset
858          * while older versions use a fixed address.
859          */
860         val = REG_RD_IND(sc, BCE_SHM_HDR_SIGNATURE);
861         if ((val & BCE_SHM_HDR_SIGNATURE_SIG_MASK) == BCE_SHM_HDR_SIGNATURE_SIG)
862                 /* Multi-port devices use different offsets in shared memory. */
863                 sc->bce_shmem_base = REG_RD_IND(sc, BCE_SHM_HDR_ADDR_0 +
864                         (pci_get_function(sc->bce_dev) << 2));
865         else
866                 sc->bce_shmem_base = HOST_VIEW_SHMEM_BASE;
867
868         DBPRINT(sc, BCE_VERBOSE_FIRMWARE, "%s(): bce_shmem_base = 0x%08X\n",
869                 __FUNCTION__, sc->bce_shmem_base);
870
871         /* Fetch the bootcode revision. */
872     val = bce_shmem_rd(sc, BCE_DEV_INFO_BC_REV);
873     for (int i = 0, j = 0; i < 3; i++) {
874         u8 num;
875
876         num = (u8) (val >> (24 - (i * 8)));
877         for (int k = 100, skip0 = 1; k >= 1; num %= k, k /= 10) {
878             if (num >= k || !skip0 || k == 1) {
879                 sc->bce_bc_ver[j++] = (num / k) + '0';
880                 skip0 = 0;
881             }
882         }
883         if (i != 2)
884             sc->bce_bc_ver[j++] = '.';
885     }
886
887     /* Check if any management firwmare is running. */
888     val = bce_shmem_rd(sc, BCE_PORT_FEATURE);
889     if (val & BCE_PORT_FEATURE_ASF_ENABLED) {
890         sc->bce_flags |= BCE_MFW_ENABLE_FLAG;
891
892         /* Allow time for firmware to enter the running state. */
893         for (int i = 0; i < 30; i++) {
894             val = bce_shmem_rd(sc, BCE_BC_STATE_CONDITION);
895             if (val & BCE_CONDITION_MFW_RUN_MASK)
896                 break;
897             DELAY(10000);
898         }
899     }
900
901     /* Check the current bootcode state. */
902     val = bce_shmem_rd(sc, BCE_BC_STATE_CONDITION);
903     val &= BCE_CONDITION_MFW_RUN_MASK;
904     if (val != BCE_CONDITION_MFW_RUN_UNKNOWN &&
905         val != BCE_CONDITION_MFW_RUN_NONE) {
906         u32 addr = bce_shmem_rd(sc, BCE_MFW_VER_PTR);
907         int i = 0;
908
909         for (int j = 0; j < 3; j++) {
910             val = bce_reg_rd_ind(sc, addr + j * 4);
911             val = bswap32(val);
912             memcpy(&sc->bce_mfw_ver[i], &val, 4);
913             i += 4;
914         }
915     }
916
917         /* Get PCI bus information (speed and type). */
918         val = REG_RD(sc, BCE_PCICFG_MISC_STATUS);
919         if (val & BCE_PCICFG_MISC_STATUS_PCIX_DET) {
920                 u32 clkreg;
921
922                 sc->bce_flags |= BCE_PCIX_FLAG;
923
924                 clkreg = REG_RD(sc, BCE_PCICFG_PCI_CLOCK_CONTROL_BITS);
925
926                 clkreg &= BCE_PCICFG_PCI_CLOCK_CONTROL_BITS_PCI_CLK_SPD_DET;
927                 switch (clkreg) {
928                 case BCE_PCICFG_PCI_CLOCK_CONTROL_BITS_PCI_CLK_SPD_DET_133MHZ:
929                         sc->bus_speed_mhz = 133;
930                         break;
931
932                 case BCE_PCICFG_PCI_CLOCK_CONTROL_BITS_PCI_CLK_SPD_DET_95MHZ:
933                         sc->bus_speed_mhz = 100;
934                         break;
935
936                 case BCE_PCICFG_PCI_CLOCK_CONTROL_BITS_PCI_CLK_SPD_DET_66MHZ:
937                 case BCE_PCICFG_PCI_CLOCK_CONTROL_BITS_PCI_CLK_SPD_DET_80MHZ:
938                         sc->bus_speed_mhz = 66;
939                         break;
940
941                 case BCE_PCICFG_PCI_CLOCK_CONTROL_BITS_PCI_CLK_SPD_DET_48MHZ:
942                 case BCE_PCICFG_PCI_CLOCK_CONTROL_BITS_PCI_CLK_SPD_DET_55MHZ:
943                         sc->bus_speed_mhz = 50;
944                         break;
945
946                 case BCE_PCICFG_PCI_CLOCK_CONTROL_BITS_PCI_CLK_SPD_DET_LOW:
947                 case BCE_PCICFG_PCI_CLOCK_CONTROL_BITS_PCI_CLK_SPD_DET_32MHZ:
948                 case BCE_PCICFG_PCI_CLOCK_CONTROL_BITS_PCI_CLK_SPD_DET_38MHZ:
949                         sc->bus_speed_mhz = 33;
950                         break;
951                 }
952         } else {
953                 if (val & BCE_PCICFG_MISC_STATUS_M66EN)
954                         sc->bus_speed_mhz = 66;
955                 else
956                         sc->bus_speed_mhz = 33;
957         }
958
959         if (val & BCE_PCICFG_MISC_STATUS_32BIT_DET)
960                 sc->bce_flags |= BCE_PCI_32BIT_FLAG;
961
962         /* Reset the controller and announce to bootcode that driver is present. */
963         if (bce_reset(sc, BCE_DRV_MSG_CODE_RESET)) {
964                 BCE_PRINTF("%s(%d): Controller reset failed!\n",
965                         __FILE__, __LINE__);
966                 rc = ENXIO;
967                 goto bce_attach_fail;
968         }
969
970         /* Initialize the controller. */
971         if (bce_chipinit(sc)) {
972                 BCE_PRINTF("%s(%d): Controller initialization failed!\n",
973                         __FILE__, __LINE__);
974                 rc = ENXIO;
975                 goto bce_attach_fail;
976         }
977
978         /* Perform NVRAM test. */
979         if (bce_nvram_test(sc)) {
980                 BCE_PRINTF("%s(%d): NVRAM test failed!\n",
981                         __FILE__, __LINE__);
982                 rc = ENXIO;
983                 goto bce_attach_fail;
984         }
985
986         /* Fetch the permanent Ethernet MAC address. */
987         bce_get_mac_addr(sc);
988
989         /*
990          * Trip points control how many BDs
991          * should be ready before generating an
992          * interrupt while ticks control how long
993          * a BD can sit in the chain before
994          * generating an interrupt.  Set the default
995          * values for the RX and TX chains.
996          */
997
998 #ifdef BCE_DEBUG
999         /* Force more frequent interrupts. */
1000         sc->bce_tx_quick_cons_trip_int = 1;
1001         sc->bce_tx_quick_cons_trip     = 1;
1002         sc->bce_tx_ticks_int           = 0;
1003         sc->bce_tx_ticks               = 0;
1004
1005         sc->bce_rx_quick_cons_trip_int = 1;
1006         sc->bce_rx_quick_cons_trip     = 1;
1007         sc->bce_rx_ticks_int           = 0;
1008         sc->bce_rx_ticks               = 0;
1009 #else
1010         /* Improve throughput at the expense of increased latency. */
1011         sc->bce_tx_quick_cons_trip_int = 20;
1012         sc->bce_tx_quick_cons_trip     = 20;
1013         sc->bce_tx_ticks_int           = 80;
1014         sc->bce_tx_ticks               = 80;
1015
1016         sc->bce_rx_quick_cons_trip_int = 6;
1017         sc->bce_rx_quick_cons_trip     = 6;
1018         sc->bce_rx_ticks_int           = 18;
1019         sc->bce_rx_ticks               = 18;
1020 #endif
1021
1022         /* Update statistics once every second. */
1023         sc->bce_stats_ticks = 1000000 & 0xffff00;
1024
1025         /* Find the media type for the adapter. */
1026         bce_get_media(sc);
1027
1028         /* Store data needed by PHY driver for backplane applications */
1029         sc->bce_shared_hw_cfg = bce_shmem_rd(sc, BCE_SHARED_HW_CFG_CONFIG);
1030         sc->bce_port_hw_cfg   = bce_shmem_rd(sc, BCE_PORT_HW_CFG_CONFIG);
1031
1032         /* Allocate DMA memory resources. */
1033         if (bce_dma_alloc(dev)) {
1034                 BCE_PRINTF("%s(%d): DMA resource allocation failed!\n",
1035                     __FILE__, __LINE__);
1036                 rc = ENXIO;
1037                 goto bce_attach_fail;
1038         }
1039
1040         /* Allocate an ifnet structure. */
1041         ifp = sc->bce_ifp = if_alloc(IFT_ETHER);
1042         if (ifp == NULL) {
1043                 BCE_PRINTF("%s(%d): Interface allocation failed!\n",
1044                         __FILE__, __LINE__);
1045                 rc = ENXIO;
1046                 goto bce_attach_fail;
1047         }
1048
1049         /* Initialize the ifnet interface. */
1050         ifp->if_softc        = sc;
1051         if_initname(ifp, device_get_name(dev), device_get_unit(dev));
1052         ifp->if_flags        = IFF_BROADCAST | IFF_SIMPLEX | IFF_MULTICAST;
1053         ifp->if_ioctl        = bce_ioctl;
1054         ifp->if_start        = bce_start;
1055         ifp->if_init         = bce_init;
1056         ifp->if_mtu          = ETHERMTU;
1057
1058         if (bce_tso_enable) {
1059                 ifp->if_hwassist = BCE_IF_HWASSIST | CSUM_TSO;
1060                 ifp->if_capabilities = BCE_IF_CAPABILITIES | IFCAP_TSO4;
1061         } else {
1062                 ifp->if_hwassist = BCE_IF_HWASSIST;
1063                 ifp->if_capabilities = BCE_IF_CAPABILITIES;
1064         }
1065
1066         ifp->if_capenable    = ifp->if_capabilities;
1067
1068         /*
1069          * Assume standard mbuf sizes for buffer allocation.
1070          * This may change later if the MTU size is set to
1071          * something other than 1500.
1072          */
1073 #ifdef BCE_JUMBO_HDRSPLIT
1074         sc->rx_bd_mbuf_alloc_size = MHLEN;
1075         /* Make sure offset is 16 byte aligned for hardware. */
1076         sc->rx_bd_mbuf_align_pad  = roundup2((MSIZE - MHLEN), 16) -
1077                 (MSIZE - MHLEN);
1078         sc->rx_bd_mbuf_data_len   = sc->rx_bd_mbuf_alloc_size -
1079                 sc->rx_bd_mbuf_align_pad;
1080         sc->pg_bd_mbuf_alloc_size = MCLBYTES;
1081 #else
1082         sc->rx_bd_mbuf_alloc_size = MCLBYTES;
1083         sc->rx_bd_mbuf_align_pad  = roundup2(MCLBYTES, 16) - MCLBYTES;
1084         sc->rx_bd_mbuf_data_len   = sc->rx_bd_mbuf_alloc_size -
1085                 sc->rx_bd_mbuf_align_pad;
1086 #endif
1087
1088         ifp->if_snd.ifq_drv_maxlen = USABLE_TX_BD;
1089         IFQ_SET_MAXLEN(&ifp->if_snd, ifp->if_snd.ifq_drv_maxlen);
1090         IFQ_SET_READY(&ifp->if_snd);
1091
1092         if (sc->bce_phy_flags & BCE_PHY_2_5G_CAPABLE_FLAG)
1093                 ifp->if_baudrate = IF_Mbps(2500ULL);
1094         else
1095                 ifp->if_baudrate = IF_Mbps(1000);
1096
1097         /* Check for an MII child bus by probing the PHY. */
1098         if (mii_phy_probe(dev, &sc->bce_miibus, bce_ifmedia_upd,
1099                 bce_ifmedia_sts)) {
1100                 BCE_PRINTF("%s(%d): No PHY found on child MII bus!\n",
1101                         __FILE__, __LINE__);
1102                 rc = ENXIO;
1103                 goto bce_attach_fail;
1104         }
1105
1106         /* Attach to the Ethernet interface list. */
1107         ether_ifattach(ifp, sc->eaddr);
1108
1109 #if __FreeBSD_version < 500000
1110         callout_init(&sc->bce_tick_callout);
1111         callout_init(&sc->bce_pulse_callout);
1112 #else
1113         callout_init_mtx(&sc->bce_tick_callout, &sc->bce_mtx, 0);
1114         callout_init_mtx(&sc->bce_pulse_callout, &sc->bce_mtx, 0);
1115 #endif
1116
1117         /* Hookup IRQ last. */
1118         rc = bus_setup_intr(dev, sc->bce_res_irq, INTR_TYPE_NET | INTR_MPSAFE,
1119                 NULL, bce_intr, sc, &sc->bce_intrhand);
1120
1121         if (rc) {
1122                 BCE_PRINTF("%s(%d): Failed to setup IRQ!\n",
1123                         __FILE__, __LINE__);
1124                 bce_detach(dev);
1125                 goto bce_attach_exit;
1126         }
1127
1128         /*
1129          * At this point we've acquired all the resources
1130          * we need to run so there's no turning back, we're
1131          * cleared for launch.
1132          */
1133
1134         /* Print some important debugging info. */
1135         DBRUNMSG(BCE_INFO, bce_dump_driver_state(sc));
1136
1137         /* Add the supported sysctls to the kernel. */
1138         bce_add_sysctls(sc);
1139
1140         BCE_LOCK(sc);
1141
1142         /*
1143          * The chip reset earlier notified the bootcode that
1144          * a driver is present.  We now need to start our pulse
1145          * routine so that the bootcode is reminded that we're
1146          * still running.
1147          */
1148         bce_pulse(sc);
1149
1150         bce_mgmt_init_locked(sc);
1151         BCE_UNLOCK(sc);
1152
1153         /* Finally, print some useful adapter info */
1154         bce_print_adapter_info(sc);
1155         DBPRINT(sc, BCE_FATAL, "%s(): sc = %p\n",
1156                 __FUNCTION__, sc);
1157
1158         goto bce_attach_exit;
1159
1160 bce_attach_fail:
1161         bce_release_resources(sc);
1162
1163 bce_attach_exit:
1164
1165         DBEXIT(BCE_VERBOSE_LOAD | BCE_VERBOSE_RESET);
1166
1167         return(rc);
1168 }
1169
1170
1171 /****************************************************************************/
1172 /* Device detach function.                                                  */
1173 /*                                                                          */
1174 /* Stops the controller, resets the controller, and releases resources.     */
1175 /*                                                                          */
1176 /* Returns:                                                                 */
1177 /*   0 on success, positive value on failure.                               */
1178 /****************************************************************************/
1179 static int
1180 bce_detach(device_t dev)
1181 {
1182         struct bce_softc *sc = device_get_softc(dev);
1183         struct ifnet *ifp;
1184         u32 msg;
1185
1186         DBENTER(BCE_VERBOSE_UNLOAD | BCE_VERBOSE_RESET);
1187
1188         ifp = sc->bce_ifp;
1189
1190         /* Stop and reset the controller. */
1191         BCE_LOCK(sc);
1192
1193         /* Stop the pulse so the bootcode can go to driver absent state. */
1194         callout_stop(&sc->bce_pulse_callout);
1195
1196         bce_stop(sc);
1197         if (sc->bce_flags & BCE_NO_WOL_FLAG)
1198                 msg = BCE_DRV_MSG_CODE_UNLOAD_LNK_DN;
1199         else
1200                 msg = BCE_DRV_MSG_CODE_UNLOAD;
1201         bce_reset(sc, msg);
1202
1203         BCE_UNLOCK(sc);
1204
1205         ether_ifdetach(ifp);
1206
1207         /* If we have a child device on the MII bus remove it too. */
1208         bus_generic_detach(dev);
1209         device_delete_child(dev, sc->bce_miibus);
1210
1211         /* Release all remaining resources. */
1212         bce_release_resources(sc);
1213
1214         DBEXIT(BCE_VERBOSE_UNLOAD | BCE_VERBOSE_RESET);
1215
1216         return(0);
1217 }
1218
1219
1220 /****************************************************************************/
1221 /* Device shutdown function.                                                */
1222 /*                                                                          */
1223 /* Stops and resets the controller.                                         */
1224 /*                                                                          */
1225 /* Returns:                                                                 */
1226 /*   0 on success, positive value on failure.                               */
1227 /****************************************************************************/
1228 static int
1229 bce_shutdown(device_t dev)
1230 {
1231         struct bce_softc *sc = device_get_softc(dev);
1232         u32 msg;
1233
1234         DBENTER(BCE_VERBOSE);
1235
1236         BCE_LOCK(sc);
1237         bce_stop(sc);
1238         if (sc->bce_flags & BCE_NO_WOL_FLAG)
1239                 msg = BCE_DRV_MSG_CODE_UNLOAD_LNK_DN;
1240         else
1241                 msg = BCE_DRV_MSG_CODE_UNLOAD;
1242         bce_reset(sc, msg);
1243         BCE_UNLOCK(sc);
1244
1245         DBEXIT(BCE_VERBOSE);
1246
1247         return (0);
1248 }
1249
1250
1251 #ifdef BCE_DEBUG
1252 /****************************************************************************/
1253 /* Register read.                                                           */
1254 /*                                                                          */
1255 /* Returns:                                                                 */
1256 /*   The value of the register.                                             */
1257 /****************************************************************************/
1258 static u32
1259 bce_reg_rd(struct bce_softc *sc, u32 offset)
1260 {
1261         u32 val = bus_space_read_4(sc->bce_btag, sc->bce_bhandle, offset);
1262         DBPRINT(sc, BCE_INSANE_REG, "%s(); offset = 0x%08X, val = 0x%08X\n",
1263                 __FUNCTION__, offset, val);
1264         return val;
1265 }
1266
1267
1268 /****************************************************************************/
1269 /* Register write (16 bit).                                                 */
1270 /*                                                                          */
1271 /* Returns:                                                                 */
1272 /*   Nothing.                                                               */
1273 /****************************************************************************/
1274 static void
1275 bce_reg_wr16(struct bce_softc *sc, u32 offset, u16 val)
1276 {
1277         DBPRINT(sc, BCE_INSANE_REG, "%s(); offset = 0x%08X, val = 0x%04X\n",
1278                 __FUNCTION__, offset, val);
1279         bus_space_write_2(sc->bce_btag, sc->bce_bhandle, offset, val);
1280 }
1281
1282
1283 /****************************************************************************/
1284 /* Register write.                                                          */
1285 /*                                                                          */
1286 /* Returns:                                                                 */
1287 /*   Nothing.                                                               */
1288 /****************************************************************************/
1289 static void
1290 bce_reg_wr(struct bce_softc *sc, u32 offset, u32 val)
1291 {
1292         DBPRINT(sc, BCE_INSANE_REG, "%s(); offset = 0x%08X, val = 0x%08X\n",
1293                 __FUNCTION__, offset, val);
1294         bus_space_write_4(sc->bce_btag, sc->bce_bhandle, offset, val);
1295 }
1296 #endif
1297
1298 /****************************************************************************/
1299 /* Indirect register read.                                                  */
1300 /*                                                                          */
1301 /* Reads NetXtreme II registers using an index/data register pair in PCI    */
1302 /* configuration space.  Using this mechanism avoids issues with posted     */
1303 /* reads but is much slower than memory-mapped I/O.                         */
1304 /*                                                                          */
1305 /* Returns:                                                                 */
1306 /*   The value of the register.                                             */
1307 /****************************************************************************/
1308 static u32
1309 bce_reg_rd_ind(struct bce_softc *sc, u32 offset)
1310 {
1311         device_t dev;
1312         dev = sc->bce_dev;
1313
1314         pci_write_config(dev, BCE_PCICFG_REG_WINDOW_ADDRESS, offset, 4);
1315 #ifdef BCE_DEBUG
1316         {
1317                 u32 val;
1318                 val = pci_read_config(dev, BCE_PCICFG_REG_WINDOW, 4);
1319                 DBPRINT(sc, BCE_INSANE_REG, "%s(); offset = 0x%08X, val = 0x%08X\n",
1320                         __FUNCTION__, offset, val);
1321                 return val;
1322         }
1323 #else
1324         return pci_read_config(dev, BCE_PCICFG_REG_WINDOW, 4);
1325 #endif
1326 }
1327
1328
1329 /****************************************************************************/
1330 /* Indirect register write.                                                 */
1331 /*                                                                          */
1332 /* Writes NetXtreme II registers using an index/data register pair in PCI   */
1333 /* configuration space.  Using this mechanism avoids issues with posted     */
1334 /* writes but is muchh slower than memory-mapped I/O.                       */
1335 /*                                                                          */
1336 /* Returns:                                                                 */
1337 /*   Nothing.                                                               */
1338 /****************************************************************************/
1339 static void
1340 bce_reg_wr_ind(struct bce_softc *sc, u32 offset, u32 val)
1341 {
1342         device_t dev;
1343         dev = sc->bce_dev;
1344
1345         DBPRINT(sc, BCE_INSANE_REG, "%s(); offset = 0x%08X, val = 0x%08X\n",
1346                 __FUNCTION__, offset, val);
1347
1348         pci_write_config(dev, BCE_PCICFG_REG_WINDOW_ADDRESS, offset, 4);
1349         pci_write_config(dev, BCE_PCICFG_REG_WINDOW, val, 4);
1350 }
1351
1352
1353 /****************************************************************************/
1354 /* Shared memory write.                                                     */
1355 /*                                                                          */
1356 /* Writes NetXtreme II shared memory region.                                */
1357 /*                                                                          */
1358 /* Returns:                                                                 */
1359 /*   Nothing.                                                               */
1360 /****************************************************************************/
1361 static void
1362 bce_shmem_wr(struct bce_softc *sc, u32 offset, u32 val)
1363 {
1364         bce_reg_wr_ind(sc, sc->bce_shmem_base + offset, val);
1365 }
1366
1367
1368 /****************************************************************************/
1369 /* Shared memory read.                                                      */
1370 /*                                                                          */
1371 /* Reads NetXtreme II shared memory region.                                 */
1372 /*                                                                          */
1373 /* Returns:                                                                 */
1374 /*   The 32 bit value read.                                                 */
1375 /****************************************************************************/
1376 static u32
1377 bce_shmem_rd(struct bce_softc *sc, u32 offset)
1378 {
1379         return (bce_reg_rd_ind(sc, sc->bce_shmem_base + offset));
1380 }
1381
1382
1383 #ifdef BCE_DEBUG
1384 /****************************************************************************/
1385 /* Context memory read.                                                     */
1386 /*                                                                          */
1387 /* The NetXtreme II controller uses context memory to track connection      */
1388 /* information for L2 and higher network protocols.                         */
1389 /*                                                                          */
1390 /* Returns:                                                                 */
1391 /*   The requested 32 bit value of context memory.                          */
1392 /****************************************************************************/
1393 static u32
1394 bce_ctx_rd(struct bce_softc *sc, u32 cid_addr, u32 ctx_offset)
1395 {
1396         u32 idx, offset, retry_cnt = 5, val;
1397
1398         DBRUNIF((cid_addr > MAX_CID_ADDR || ctx_offset & 0x3 || cid_addr & CTX_MASK),
1399                 BCE_PRINTF("%s(): Invalid CID address: 0x%08X.\n",
1400                         __FUNCTION__, cid_addr));
1401
1402         offset = ctx_offset + cid_addr;
1403
1404         if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
1405                 (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
1406
1407                 REG_WR(sc, BCE_CTX_CTX_CTRL, (offset | BCE_CTX_CTX_CTRL_READ_REQ));
1408
1409                 for (idx = 0; idx < retry_cnt; idx++) {
1410                         val = REG_RD(sc, BCE_CTX_CTX_CTRL);
1411                         if ((val & BCE_CTX_CTX_CTRL_READ_REQ) == 0)
1412                                 break;
1413                         DELAY(5);
1414                 }
1415
1416                 if (val & BCE_CTX_CTX_CTRL_READ_REQ)
1417                         BCE_PRINTF("%s(%d); Unable to read CTX memory: "
1418                                 "cid_addr = 0x%08X, offset = 0x%08X!\n",
1419                                 __FILE__, __LINE__, cid_addr, ctx_offset);
1420
1421                 val = REG_RD(sc, BCE_CTX_CTX_DATA);
1422         } else {
1423                 REG_WR(sc, BCE_CTX_DATA_ADR, offset);
1424                 val = REG_RD(sc, BCE_CTX_DATA);
1425         }
1426
1427         DBPRINT(sc, BCE_EXTREME_CTX, "%s(); cid_addr = 0x%08X, offset = 0x%08X, "
1428                 "val = 0x%08X\n", __FUNCTION__, cid_addr, ctx_offset, val);
1429
1430         return(val);
1431 }
1432 #endif
1433
1434
1435 /****************************************************************************/
1436 /* Context memory write.                                                    */
1437 /*                                                                          */
1438 /* The NetXtreme II controller uses context memory to track connection      */
1439 /* information for L2 and higher network protocols.                         */
1440 /*                                                                          */
1441 /* Returns:                                                                 */
1442 /*   Nothing.                                                               */
1443 /****************************************************************************/
1444 static void
1445 bce_ctx_wr(struct bce_softc *sc, u32 cid_addr, u32 ctx_offset, u32 ctx_val)
1446 {
1447         u32 idx, offset = ctx_offset + cid_addr;
1448         u32 val, retry_cnt = 5;
1449
1450         DBPRINT(sc, BCE_EXTREME_CTX, "%s(); cid_addr = 0x%08X, offset = 0x%08X, "
1451                 "val = 0x%08X\n", __FUNCTION__, cid_addr, ctx_offset, ctx_val);
1452
1453         DBRUNIF((cid_addr > MAX_CID_ADDR || ctx_offset & 0x3 || cid_addr & CTX_MASK),
1454                 BCE_PRINTF("%s(): Invalid CID address: 0x%08X.\n",
1455                         __FUNCTION__, cid_addr));
1456
1457         if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
1458                 (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
1459
1460                 REG_WR(sc, BCE_CTX_CTX_DATA, ctx_val);
1461                 REG_WR(sc, BCE_CTX_CTX_CTRL, (offset | BCE_CTX_CTX_CTRL_WRITE_REQ));
1462
1463                 for (idx = 0; idx < retry_cnt; idx++) {
1464                         val = REG_RD(sc, BCE_CTX_CTX_CTRL);
1465                         if ((val & BCE_CTX_CTX_CTRL_WRITE_REQ) == 0)
1466                                 break;
1467                         DELAY(5);
1468                 }
1469
1470                 if (val & BCE_CTX_CTX_CTRL_WRITE_REQ)
1471                         BCE_PRINTF("%s(%d); Unable to write CTX memory: "
1472                                 "cid_addr = 0x%08X, offset = 0x%08X!\n",
1473                                 __FILE__, __LINE__, cid_addr, ctx_offset);
1474
1475         } else {
1476                 REG_WR(sc, BCE_CTX_DATA_ADR, offset);
1477                 REG_WR(sc, BCE_CTX_DATA, ctx_val);
1478         }
1479 }
1480
1481
1482 /****************************************************************************/
1483 /* PHY register read.                                                       */
1484 /*                                                                          */
1485 /* Implements register reads on the MII bus.                                */
1486 /*                                                                          */
1487 /* Returns:                                                                 */
1488 /*   The value of the register.                                             */
1489 /****************************************************************************/
1490 static int
1491 bce_miibus_read_reg(device_t dev, int phy, int reg)
1492 {
1493         struct bce_softc *sc;
1494         u32 val;
1495         int i;
1496
1497         sc = device_get_softc(dev);
1498
1499         /* Make sure we are accessing the correct PHY address. */
1500         if (phy != sc->bce_phy_addr) {
1501                 DBPRINT(sc, BCE_INSANE_PHY, "Invalid PHY address %d for PHY read!\n", phy);
1502                 return(0);
1503         }
1504
1505         if (sc->bce_phy_flags & BCE_PHY_INT_MODE_AUTO_POLLING_FLAG) {
1506                 val = REG_RD(sc, BCE_EMAC_MDIO_MODE);
1507                 val &= ~BCE_EMAC_MDIO_MODE_AUTO_POLL;
1508
1509                 REG_WR(sc, BCE_EMAC_MDIO_MODE, val);
1510                 REG_RD(sc, BCE_EMAC_MDIO_MODE);
1511
1512                 DELAY(40);
1513         }
1514
1515
1516         val = BCE_MIPHY(phy) | BCE_MIREG(reg) |
1517                 BCE_EMAC_MDIO_COMM_COMMAND_READ | BCE_EMAC_MDIO_COMM_DISEXT |
1518                 BCE_EMAC_MDIO_COMM_START_BUSY;
1519         REG_WR(sc, BCE_EMAC_MDIO_COMM, val);
1520
1521         for (i = 0; i < BCE_PHY_TIMEOUT; i++) {
1522                 DELAY(10);
1523
1524                 val = REG_RD(sc, BCE_EMAC_MDIO_COMM);
1525                 if (!(val & BCE_EMAC_MDIO_COMM_START_BUSY)) {
1526                         DELAY(5);
1527
1528                         val = REG_RD(sc, BCE_EMAC_MDIO_COMM);
1529                         val &= BCE_EMAC_MDIO_COMM_DATA;
1530
1531                         break;
1532                 }
1533         }
1534
1535         if (val & BCE_EMAC_MDIO_COMM_START_BUSY) {
1536                 BCE_PRINTF("%s(%d): Error: PHY read timeout! phy = %d, reg = 0x%04X\n",
1537                         __FILE__, __LINE__, phy, reg);
1538                 val = 0x0;
1539         } else {
1540                 val = REG_RD(sc, BCE_EMAC_MDIO_COMM);
1541         }
1542
1543
1544         if (sc->bce_phy_flags & BCE_PHY_INT_MODE_AUTO_POLLING_FLAG) {
1545                 val = REG_RD(sc, BCE_EMAC_MDIO_MODE);
1546                 val |= BCE_EMAC_MDIO_MODE_AUTO_POLL;
1547
1548                 REG_WR(sc, BCE_EMAC_MDIO_MODE, val);
1549                 REG_RD(sc, BCE_EMAC_MDIO_MODE);
1550
1551                 DELAY(40);
1552         }
1553
1554         DB_PRINT_PHY_REG(reg, val);
1555         return (val & 0xffff);
1556
1557 }
1558
1559
1560 /****************************************************************************/
1561 /* PHY register write.                                                      */
1562 /*                                                                          */
1563 /* Implements register writes on the MII bus.                               */
1564 /*                                                                          */
1565 /* Returns:                                                                 */
1566 /*   The value of the register.                                             */
1567 /****************************************************************************/
1568 static int
1569 bce_miibus_write_reg(device_t dev, int phy, int reg, int val)
1570 {
1571         struct bce_softc *sc;
1572         u32 val1;
1573         int i;
1574
1575         sc = device_get_softc(dev);
1576
1577         /* Make sure we are accessing the correct PHY address. */
1578         if (phy != sc->bce_phy_addr) {
1579                 DBPRINT(sc, BCE_INSANE_PHY, "Invalid PHY address %d for PHY write!\n", phy);
1580                 return(0);
1581         }
1582
1583         DB_PRINT_PHY_REG(reg, val);
1584
1585         if (sc->bce_phy_flags & BCE_PHY_INT_MODE_AUTO_POLLING_FLAG) {
1586                 val1 = REG_RD(sc, BCE_EMAC_MDIO_MODE);
1587                 val1 &= ~BCE_EMAC_MDIO_MODE_AUTO_POLL;
1588
1589                 REG_WR(sc, BCE_EMAC_MDIO_MODE, val1);
1590                 REG_RD(sc, BCE_EMAC_MDIO_MODE);
1591
1592                 DELAY(40);
1593         }
1594
1595         val1 = BCE_MIPHY(phy) | BCE_MIREG(reg) | val |
1596                 BCE_EMAC_MDIO_COMM_COMMAND_WRITE |
1597                 BCE_EMAC_MDIO_COMM_START_BUSY | BCE_EMAC_MDIO_COMM_DISEXT;
1598         REG_WR(sc, BCE_EMAC_MDIO_COMM, val1);
1599
1600         for (i = 0; i < BCE_PHY_TIMEOUT; i++) {
1601                 DELAY(10);
1602
1603                 val1 = REG_RD(sc, BCE_EMAC_MDIO_COMM);
1604                 if (!(val1 & BCE_EMAC_MDIO_COMM_START_BUSY)) {
1605                         DELAY(5);
1606                         break;
1607                 }
1608         }
1609
1610         if (val1 & BCE_EMAC_MDIO_COMM_START_BUSY)
1611                 BCE_PRINTF("%s(%d): PHY write timeout!\n",
1612                         __FILE__, __LINE__);
1613
1614         if (sc->bce_phy_flags & BCE_PHY_INT_MODE_AUTO_POLLING_FLAG) {
1615                 val1 = REG_RD(sc, BCE_EMAC_MDIO_MODE);
1616                 val1 |= BCE_EMAC_MDIO_MODE_AUTO_POLL;
1617
1618                 REG_WR(sc, BCE_EMAC_MDIO_MODE, val1);
1619                 REG_RD(sc, BCE_EMAC_MDIO_MODE);
1620
1621                 DELAY(40);
1622         }
1623
1624         return 0;
1625 }
1626
1627
1628 /****************************************************************************/
1629 /* MII bus status change.                                                   */
1630 /*                                                                          */
1631 /* Called by the MII bus driver when the PHY establishes link to set the    */
1632 /* MAC interface registers.                                                 */
1633 /*                                                                          */
1634 /* Returns:                                                                 */
1635 /*   Nothing.                                                               */
1636 /****************************************************************************/
1637 static void
1638 bce_miibus_statchg(device_t dev)
1639 {
1640         struct bce_softc *sc;
1641         struct mii_data *mii;
1642         int val;
1643
1644         sc = device_get_softc(dev);
1645
1646         DBENTER(BCE_VERBOSE_PHY);
1647
1648         mii = device_get_softc(sc->bce_miibus);
1649
1650         val = REG_RD(sc, BCE_EMAC_MODE);
1651         val &= ~(BCE_EMAC_MODE_PORT | BCE_EMAC_MODE_HALF_DUPLEX |
1652                 BCE_EMAC_MODE_MAC_LOOP | BCE_EMAC_MODE_FORCE_LINK |
1653                 BCE_EMAC_MODE_25G);
1654
1655         /* Set MII or GMII interface based on the speed negotiated by the PHY. */
1656         switch (IFM_SUBTYPE(mii->mii_media_active)) {
1657         case IFM_10_T:
1658                 if (BCE_CHIP_NUM(sc) != BCE_CHIP_NUM_5706) {
1659                         DBPRINT(sc, BCE_INFO, "Enabling 10Mb interface.\n");
1660                         val |= BCE_EMAC_MODE_PORT_MII_10;
1661                         break;
1662                 }
1663                 /* fall-through */
1664         case IFM_100_TX:
1665                 DBPRINT(sc, BCE_INFO, "Enabling MII interface.\n");
1666                 val |= BCE_EMAC_MODE_PORT_MII;
1667                 break;
1668         case IFM_2500_SX:
1669                 DBPRINT(sc, BCE_INFO, "Enabling 2.5G MAC mode.\n");
1670                 val |= BCE_EMAC_MODE_25G;
1671                 /* fall-through */
1672         case IFM_1000_T:
1673         case IFM_1000_SX:
1674                 DBPRINT(sc, BCE_INFO, "Enabling GMII interface.\n");
1675                 val |= BCE_EMAC_MODE_PORT_GMII;
1676                 break;
1677         default:
1678                 DBPRINT(sc, BCE_INFO, "Unknown speed, enabling default GMII "
1679                         "interface.\n");
1680                 val |= BCE_EMAC_MODE_PORT_GMII;
1681         }
1682
1683         /* Set half or full duplex based on the duplicity negotiated by the PHY. */
1684         if ((mii->mii_media_active & IFM_GMASK) == IFM_HDX) {
1685                 DBPRINT(sc, BCE_INFO, "Setting Half-Duplex interface.\n");
1686                 val |= BCE_EMAC_MODE_HALF_DUPLEX;
1687         } else
1688                 DBPRINT(sc, BCE_INFO, "Setting Full-Duplex interface.\n");
1689
1690         REG_WR(sc, BCE_EMAC_MODE, val);
1691
1692 #if 0
1693         /* ToDo: Enable flow control support in brgphy and bge. */
1694         /* FLAG0 is set if RX is enabled and FLAG1 if TX is enabled */
1695         if (mii->mii_media_active & IFM_FLAG0)
1696                 BCE_SETBIT(sc, BCE_EMAC_RX_MODE, BCE_EMAC_RX_MODE_FLOW_EN);
1697         if (mii->mii_media_active & IFM_FLAG1)
1698                 BCE_SETBIT(sc, BCE_EMAC_RX_MODE, BCE_EMAC_TX_MODE_FLOW_EN);
1699 #endif
1700
1701         DBEXIT(BCE_VERBOSE_PHY);
1702 }
1703
1704
1705 /****************************************************************************/
1706 /* Acquire NVRAM lock.                                                      */
1707 /*                                                                          */
1708 /* Before the NVRAM can be accessed the caller must acquire an NVRAM lock.  */
1709 /* Locks 0 and 2 are reserved, lock 1 is used by firmware and lock 2 is     */
1710 /* for use by the driver.                                                   */
1711 /*                                                                          */
1712 /* Returns:                                                                 */
1713 /*   0 on success, positive value on failure.                               */
1714 /****************************************************************************/
1715 static int
1716 bce_acquire_nvram_lock(struct bce_softc *sc)
1717 {
1718         u32 val;
1719         int j, rc = 0;
1720
1721         DBENTER(BCE_VERBOSE_NVRAM);
1722
1723         /* Request access to the flash interface. */
1724         REG_WR(sc, BCE_NVM_SW_ARB, BCE_NVM_SW_ARB_ARB_REQ_SET2);
1725         for (j = 0; j < NVRAM_TIMEOUT_COUNT; j++) {
1726                 val = REG_RD(sc, BCE_NVM_SW_ARB);
1727                 if (val & BCE_NVM_SW_ARB_ARB_ARB2)
1728                         break;
1729
1730                 DELAY(5);
1731         }
1732
1733         if (j >= NVRAM_TIMEOUT_COUNT) {
1734                 DBPRINT(sc, BCE_WARN, "Timeout acquiring NVRAM lock!\n");
1735                 rc = EBUSY;
1736         }
1737
1738         DBEXIT(BCE_VERBOSE_NVRAM);
1739         return (rc);
1740 }
1741
1742
1743 /****************************************************************************/
1744 /* Release NVRAM lock.                                                      */
1745 /*                                                                          */
1746 /* When the caller is finished accessing NVRAM the lock must be released.   */
1747 /* Locks 0 and 2 are reserved, lock 1 is used by firmware and lock 2 is     */
1748 /* for use by the driver.                                                   */
1749 /*                                                                          */
1750 /* Returns:                                                                 */
1751 /*   0 on success, positive value on failure.                               */
1752 /****************************************************************************/
1753 static int
1754 bce_release_nvram_lock(struct bce_softc *sc)
1755 {
1756         u32 val;
1757         int j, rc = 0;
1758
1759         DBENTER(BCE_VERBOSE_NVRAM);
1760
1761         /*
1762          * Relinquish nvram interface.
1763          */
1764         REG_WR(sc, BCE_NVM_SW_ARB, BCE_NVM_SW_ARB_ARB_REQ_CLR2);
1765
1766         for (j = 0; j < NVRAM_TIMEOUT_COUNT; j++) {
1767                 val = REG_RD(sc, BCE_NVM_SW_ARB);
1768                 if (!(val & BCE_NVM_SW_ARB_ARB_ARB2))
1769                         break;
1770
1771                 DELAY(5);
1772         }
1773
1774         if (j >= NVRAM_TIMEOUT_COUNT) {
1775                 DBPRINT(sc, BCE_WARN, "Timeout releasing NVRAM lock!\n");
1776                 rc = EBUSY;
1777         }
1778
1779         DBEXIT(BCE_VERBOSE_NVRAM);
1780         return (rc);
1781 }
1782
1783
1784 #ifdef BCE_NVRAM_WRITE_SUPPORT
1785 /****************************************************************************/
1786 /* Enable NVRAM write access.                                               */
1787 /*                                                                          */
1788 /* Before writing to NVRAM the caller must enable NVRAM writes.             */
1789 /*                                                                          */
1790 /* Returns:                                                                 */
1791 /*   0 on success, positive value on failure.                               */
1792 /****************************************************************************/
1793 static int
1794 bce_enable_nvram_write(struct bce_softc *sc)
1795 {
1796         u32 val;
1797         int rc = 0;
1798
1799         DBENTER(BCE_VERBOSE_NVRAM);
1800
1801         val = REG_RD(sc, BCE_MISC_CFG);
1802         REG_WR(sc, BCE_MISC_CFG, val | BCE_MISC_CFG_NVM_WR_EN_PCI);
1803
1804         if (!(sc->bce_flash_info->flags & BCE_NV_BUFFERED)) {
1805                 int j;
1806
1807                 REG_WR(sc, BCE_NVM_COMMAND, BCE_NVM_COMMAND_DONE);
1808                 REG_WR(sc, BCE_NVM_COMMAND,     BCE_NVM_COMMAND_WREN | BCE_NVM_COMMAND_DOIT);
1809
1810                 for (j = 0; j < NVRAM_TIMEOUT_COUNT; j++) {
1811                         DELAY(5);
1812
1813                         val = REG_RD(sc, BCE_NVM_COMMAND);
1814                         if (val & BCE_NVM_COMMAND_DONE)
1815                                 break;
1816                 }
1817
1818                 if (j >= NVRAM_TIMEOUT_COUNT) {
1819                         DBPRINT(sc, BCE_WARN, "Timeout writing NVRAM!\n");
1820                         rc = EBUSY;
1821                 }
1822         }
1823
1824         DBENTER(BCE_VERBOSE_NVRAM);
1825         return (rc);
1826 }
1827
1828
1829 /****************************************************************************/
1830 /* Disable NVRAM write access.                                              */
1831 /*                                                                          */
1832 /* When the caller is finished writing to NVRAM write access must be        */
1833 /* disabled.                                                                */
1834 /*                                                                          */
1835 /* Returns:                                                                 */
1836 /*   Nothing.                                                               */
1837 /****************************************************************************/
1838 static void
1839 bce_disable_nvram_write(struct bce_softc *sc)
1840 {
1841         u32 val;
1842
1843         DBENTER(BCE_VERBOSE_NVRAM);
1844
1845         val = REG_RD(sc, BCE_MISC_CFG);
1846         REG_WR(sc, BCE_MISC_CFG, val & ~BCE_MISC_CFG_NVM_WR_EN);
1847
1848         DBEXIT(BCE_VERBOSE_NVRAM);
1849
1850 }
1851 #endif
1852
1853
1854 /****************************************************************************/
1855 /* Enable NVRAM access.                                                     */
1856 /*                                                                          */
1857 /* Before accessing NVRAM for read or write operations the caller must      */
1858 /* enabled NVRAM access.                                                    */
1859 /*                                                                          */
1860 /* Returns:                                                                 */
1861 /*   Nothing.                                                               */
1862 /****************************************************************************/
1863 static void
1864 bce_enable_nvram_access(struct bce_softc *sc)
1865 {
1866         u32 val;
1867
1868         DBENTER(BCE_VERBOSE_NVRAM);
1869
1870         val = REG_RD(sc, BCE_NVM_ACCESS_ENABLE);
1871         /* Enable both bits, even on read. */
1872         REG_WR(sc, BCE_NVM_ACCESS_ENABLE,
1873                val | BCE_NVM_ACCESS_ENABLE_EN | BCE_NVM_ACCESS_ENABLE_WR_EN);
1874
1875         DBEXIT(BCE_VERBOSE_NVRAM);
1876 }
1877
1878
1879 /****************************************************************************/
1880 /* Disable NVRAM access.                                                    */
1881 /*                                                                          */
1882 /* When the caller is finished accessing NVRAM access must be disabled.     */
1883 /*                                                                          */
1884 /* Returns:                                                                 */
1885 /*   Nothing.                                                               */
1886 /****************************************************************************/
1887 static void
1888 bce_disable_nvram_access(struct bce_softc *sc)
1889 {
1890         u32 val;
1891
1892         DBENTER(BCE_VERBOSE_NVRAM);
1893
1894         val = REG_RD(sc, BCE_NVM_ACCESS_ENABLE);
1895
1896         /* Disable both bits, even after read. */
1897         REG_WR(sc, BCE_NVM_ACCESS_ENABLE,
1898                 val & ~(BCE_NVM_ACCESS_ENABLE_EN |
1899                         BCE_NVM_ACCESS_ENABLE_WR_EN));
1900
1901         DBEXIT(BCE_VERBOSE_NVRAM);
1902 }
1903
1904
1905 #ifdef BCE_NVRAM_WRITE_SUPPORT
1906 /****************************************************************************/
1907 /* Erase NVRAM page before writing.                                         */
1908 /*                                                                          */
1909 /* Non-buffered flash parts require that a page be erased before it is      */
1910 /* written.                                                                 */
1911 /*                                                                          */
1912 /* Returns:                                                                 */
1913 /*   0 on success, positive value on failure.                               */
1914 /****************************************************************************/
1915 static int
1916 bce_nvram_erase_page(struct bce_softc *sc, u32 offset)
1917 {
1918         u32 cmd;
1919         int j, rc = 0;
1920
1921         DBENTER(BCE_VERBOSE_NVRAM);
1922
1923         /* Buffered flash doesn't require an erase. */
1924         if (sc->bce_flash_info->flags & BCE_NV_BUFFERED)
1925                 goto bce_nvram_erase_page_exit;
1926
1927         /* Build an erase command. */
1928         cmd = BCE_NVM_COMMAND_ERASE | BCE_NVM_COMMAND_WR |
1929               BCE_NVM_COMMAND_DOIT;
1930
1931         /*
1932          * Clear the DONE bit separately, set the NVRAM adress to erase,
1933          * and issue the erase command.
1934          */
1935         REG_WR(sc, BCE_NVM_COMMAND, BCE_NVM_COMMAND_DONE);
1936         REG_WR(sc, BCE_NVM_ADDR, offset & BCE_NVM_ADDR_NVM_ADDR_VALUE);
1937         REG_WR(sc, BCE_NVM_COMMAND, cmd);
1938
1939         /* Wait for completion. */
1940         for (j = 0; j < NVRAM_TIMEOUT_COUNT; j++) {
1941                 u32 val;
1942
1943                 DELAY(5);
1944
1945                 val = REG_RD(sc, BCE_NVM_COMMAND);
1946                 if (val & BCE_NVM_COMMAND_DONE)
1947                         break;
1948         }
1949
1950         if (j >= NVRAM_TIMEOUT_COUNT) {
1951                 DBPRINT(sc, BCE_WARN, "Timeout erasing NVRAM.\n");
1952                 rc = EBUSY;
1953         }
1954
1955 bce_nvram_erase_page_exit:
1956         DBEXIT(BCE_VERBOSE_NVRAM);
1957         return (rc);
1958 }
1959 #endif /* BCE_NVRAM_WRITE_SUPPORT */
1960
1961
1962 /****************************************************************************/
1963 /* Read a dword (32 bits) from NVRAM.                                       */
1964 /*                                                                          */
1965 /* Read a 32 bit word from NVRAM.  The caller is assumed to have already    */
1966 /* obtained the NVRAM lock and enabled the controller for NVRAM access.     */
1967 /*                                                                          */
1968 /* Returns:                                                                 */
1969 /*   0 on success and the 32 bit value read, positive value on failure.     */
1970 /****************************************************************************/
1971 static int
1972 bce_nvram_read_dword(struct bce_softc *sc, u32 offset, u8 *ret_val,
1973                                                         u32 cmd_flags)
1974 {
1975         u32 cmd;
1976         int i, rc = 0;
1977
1978         DBENTER(BCE_EXTREME_NVRAM);
1979
1980         /* Build the command word. */
1981         cmd = BCE_NVM_COMMAND_DOIT | cmd_flags;
1982
1983         /* Calculate the offset for buffered flash if translation is used. */
1984         if (sc->bce_flash_info->flags & BCE_NV_TRANSLATE) {
1985                 offset = ((offset / sc->bce_flash_info->page_size) <<
1986                            sc->bce_flash_info->page_bits) +
1987                           (offset % sc->bce_flash_info->page_size);
1988         }
1989
1990         /*
1991          * Clear the DONE bit separately, set the address to read,
1992          * and issue the read.
1993          */
1994         REG_WR(sc, BCE_NVM_COMMAND, BCE_NVM_COMMAND_DONE);
1995         REG_WR(sc, BCE_NVM_ADDR, offset & BCE_NVM_ADDR_NVM_ADDR_VALUE);
1996         REG_WR(sc, BCE_NVM_COMMAND, cmd);
1997
1998         /* Wait for completion. */
1999         for (i = 0; i < NVRAM_TIMEOUT_COUNT; i++) {
2000                 u32 val;
2001
2002                 DELAY(5);
2003
2004                 val = REG_RD(sc, BCE_NVM_COMMAND);
2005                 if (val & BCE_NVM_COMMAND_DONE) {
2006                         val = REG_RD(sc, BCE_NVM_READ);
2007
2008                         val = bce_be32toh(val);
2009                         memcpy(ret_val, &val, 4);
2010                         break;
2011                 }
2012         }
2013
2014         /* Check for errors. */
2015         if (i >= NVRAM_TIMEOUT_COUNT) {
2016                 BCE_PRINTF("%s(%d): Timeout error reading NVRAM at offset 0x%08X!\n",
2017                         __FILE__, __LINE__, offset);
2018                 rc = EBUSY;
2019         }
2020
2021         DBEXIT(BCE_EXTREME_NVRAM);
2022         return(rc);
2023 }
2024
2025
2026 #ifdef BCE_NVRAM_WRITE_SUPPORT
2027 /****************************************************************************/
2028 /* Write a dword (32 bits) to NVRAM.                                        */
2029 /*                                                                          */
2030 /* Write a 32 bit word to NVRAM.  The caller is assumed to have already     */
2031 /* obtained the NVRAM lock, enabled the controller for NVRAM access, and    */
2032 /* enabled NVRAM write access.                                              */
2033 /*                                                                          */
2034 /* Returns:                                                                 */
2035 /*   0 on success, positive value on failure.                               */
2036 /****************************************************************************/
2037 static int
2038 bce_nvram_write_dword(struct bce_softc *sc, u32 offset, u8 *val,
2039         u32 cmd_flags)
2040 {
2041         u32 cmd, val32;
2042         int j, rc = 0;
2043
2044         DBENTER(BCE_VERBOSE_NVRAM);
2045
2046         /* Build the command word. */
2047         cmd = BCE_NVM_COMMAND_DOIT | BCE_NVM_COMMAND_WR | cmd_flags;
2048
2049         /* Calculate the offset for buffered flash if translation is used. */
2050         if (sc->bce_flash_info->flags & BCE_NV_TRANSLATE) {
2051                 offset = ((offset / sc->bce_flash_info->page_size) <<
2052                           sc->bce_flash_info->page_bits) +
2053                          (offset % sc->bce_flash_info->page_size);
2054         }
2055
2056         /*
2057          * Clear the DONE bit separately, convert NVRAM data to big-endian,
2058          * set the NVRAM address to write, and issue the write command
2059          */
2060         REG_WR(sc, BCE_NVM_COMMAND, BCE_NVM_COMMAND_DONE);
2061         memcpy(&val32, val, 4);
2062         val32 = htobe32(val32);
2063         REG_WR(sc, BCE_NVM_WRITE, val32);
2064         REG_WR(sc, BCE_NVM_ADDR, offset & BCE_NVM_ADDR_NVM_ADDR_VALUE);
2065         REG_WR(sc, BCE_NVM_COMMAND, cmd);
2066
2067         /* Wait for completion. */
2068         for (j = 0; j < NVRAM_TIMEOUT_COUNT; j++) {
2069                 DELAY(5);
2070
2071                 if (REG_RD(sc, BCE_NVM_COMMAND) & BCE_NVM_COMMAND_DONE)
2072                         break;
2073         }
2074         if (j >= NVRAM_TIMEOUT_COUNT) {
2075                 BCE_PRINTF("%s(%d): Timeout error writing NVRAM at offset 0x%08X\n",
2076                         __FILE__, __LINE__, offset);
2077                 rc = EBUSY;
2078         }
2079
2080         DBEXIT(BCE_VERBOSE_NVRAM);
2081         return (rc);
2082 }
2083 #endif /* BCE_NVRAM_WRITE_SUPPORT */
2084
2085
2086 /****************************************************************************/
2087 /* Initialize NVRAM access.                                                 */
2088 /*                                                                          */
2089 /* Identify the NVRAM device in use and prepare the NVRAM interface to      */
2090 /* access that device.                                                      */
2091 /*                                                                          */
2092 /* Returns:                                                                 */
2093 /*   0 on success, positive value on failure.                               */
2094 /****************************************************************************/
2095 static int
2096 bce_init_nvram(struct bce_softc *sc)
2097 {
2098         u32 val;
2099         int j, entry_count, rc = 0;
2100         struct flash_spec *flash;
2101
2102         DBENTER(BCE_VERBOSE_NVRAM);
2103
2104         if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
2105                 (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
2106                 sc->bce_flash_info = &flash_5709;
2107                 goto bce_init_nvram_get_flash_size;
2108         }
2109
2110         /* Determine the selected interface. */
2111         val = REG_RD(sc, BCE_NVM_CFG1);
2112
2113         entry_count = sizeof(flash_table) / sizeof(struct flash_spec);
2114
2115         /*
2116          * Flash reconfiguration is required to support additional
2117          * NVRAM devices not directly supported in hardware.
2118          * Check if the flash interface was reconfigured
2119          * by the bootcode.
2120          */
2121
2122         if (val & 0x40000000) {
2123                 /* Flash interface reconfigured by bootcode. */
2124
2125                 DBPRINT(sc,BCE_INFO_LOAD,
2126                         "bce_init_nvram(): Flash WAS reconfigured.\n");
2127
2128                 for (j = 0, flash = &flash_table[0]; j < entry_count;
2129                      j++, flash++) {
2130                         if ((val & FLASH_BACKUP_STRAP_MASK) ==
2131                             (flash->config1 & FLASH_BACKUP_STRAP_MASK)) {
2132                                 sc->bce_flash_info = flash;
2133                                 break;
2134                         }
2135                 }
2136         } else {
2137                 /* Flash interface not yet reconfigured. */
2138                 u32 mask;
2139
2140                 DBPRINT(sc, BCE_INFO_LOAD, "%s(): Flash was NOT reconfigured.\n",
2141                         __FUNCTION__);
2142
2143                 if (val & (1 << 23))
2144                         mask = FLASH_BACKUP_STRAP_MASK;
2145                 else
2146                         mask = FLASH_STRAP_MASK;
2147
2148                 /* Look for the matching NVRAM device configuration data. */
2149                 for (j = 0, flash = &flash_table[0]; j < entry_count; j++, flash++) {
2150
2151                         /* Check if the device matches any of the known devices. */
2152                         if ((val & mask) == (flash->strapping & mask)) {
2153                                 /* Found a device match. */
2154                                 sc->bce_flash_info = flash;
2155
2156                                 /* Request access to the flash interface. */
2157                                 if ((rc = bce_acquire_nvram_lock(sc)) != 0)
2158                                         return rc;
2159
2160                                 /* Reconfigure the flash interface. */
2161                                 bce_enable_nvram_access(sc);
2162                                 REG_WR(sc, BCE_NVM_CFG1, flash->config1);
2163                                 REG_WR(sc, BCE_NVM_CFG2, flash->config2);
2164                                 REG_WR(sc, BCE_NVM_CFG3, flash->config3);
2165                                 REG_WR(sc, BCE_NVM_WRITE1, flash->write1);
2166                                 bce_disable_nvram_access(sc);
2167                                 bce_release_nvram_lock(sc);
2168
2169                                 break;
2170                         }
2171                 }
2172         }
2173
2174         /* Check if a matching device was found. */
2175         if (j == entry_count) {
2176                 sc->bce_flash_info = NULL;
2177                 BCE_PRINTF("%s(%d): Unknown Flash NVRAM found!\n",
2178                         __FILE__, __LINE__);
2179                 rc = ENODEV;
2180         }
2181
2182 bce_init_nvram_get_flash_size:
2183         /* Write the flash config data to the shared memory interface. */
2184         val = bce_shmem_rd(sc, BCE_SHARED_HW_CFG_CONFIG2);
2185         val &= BCE_SHARED_HW_CFG2_NVM_SIZE_MASK;
2186         if (val)
2187                 sc->bce_flash_size = val;
2188         else
2189                 sc->bce_flash_size = sc->bce_flash_info->total_size;
2190
2191         DBPRINT(sc, BCE_INFO_LOAD, "%s(): Found %s, size = 0x%08X\n",
2192                 __FUNCTION__, sc->bce_flash_info->name,
2193                 sc->bce_flash_info->total_size);
2194
2195         DBEXIT(BCE_VERBOSE_NVRAM);
2196         return rc;
2197 }
2198
2199
2200 /****************************************************************************/
2201 /* Read an arbitrary range of data from NVRAM.                              */
2202 /*                                                                          */
2203 /* Prepares the NVRAM interface for access and reads the requested data     */
2204 /* into the supplied buffer.                                                */
2205 /*                                                                          */
2206 /* Returns:                                                                 */
2207 /*   0 on success and the data read, positive value on failure.             */
2208 /****************************************************************************/
2209 static int
2210 bce_nvram_read(struct bce_softc *sc, u32 offset, u8 *ret_buf,
2211         int buf_size)
2212 {
2213         int rc = 0;
2214         u32 cmd_flags, offset32, len32, extra;
2215
2216         DBENTER(BCE_VERBOSE_NVRAM);
2217
2218         if (buf_size == 0)
2219                 goto bce_nvram_read_exit;
2220
2221         /* Request access to the flash interface. */
2222         if ((rc = bce_acquire_nvram_lock(sc)) != 0)
2223                 goto bce_nvram_read_exit;
2224
2225         /* Enable access to flash interface */
2226         bce_enable_nvram_access(sc);
2227
2228         len32 = buf_size;
2229         offset32 = offset;
2230         extra = 0;
2231
2232         cmd_flags = 0;
2233
2234         if (offset32 & 3) {
2235                 u8 buf[4];
2236                 u32 pre_len;
2237
2238                 offset32 &= ~3;
2239                 pre_len = 4 - (offset & 3);
2240
2241                 if (pre_len >= len32) {
2242                         pre_len = len32;
2243                         cmd_flags = BCE_NVM_COMMAND_FIRST | BCE_NVM_COMMAND_LAST;
2244                 }
2245                 else {
2246                         cmd_flags = BCE_NVM_COMMAND_FIRST;
2247                 }
2248
2249                 rc = bce_nvram_read_dword(sc, offset32, buf, cmd_flags);
2250
2251                 if (rc)
2252                         return rc;
2253
2254                 memcpy(ret_buf, buf + (offset & 3), pre_len);
2255
2256                 offset32 += 4;
2257                 ret_buf += pre_len;
2258                 len32 -= pre_len;
2259         }
2260
2261         if (len32 & 3) {
2262                 extra = 4 - (len32 & 3);
2263                 len32 = (len32 + 4) & ~3;
2264         }
2265
2266         if (len32 == 4) {
2267                 u8 buf[4];
2268
2269                 if (cmd_flags)
2270                         cmd_flags = BCE_NVM_COMMAND_LAST;
2271                 else
2272                         cmd_flags = BCE_NVM_COMMAND_FIRST |
2273                                     BCE_NVM_COMMAND_LAST;
2274
2275                 rc = bce_nvram_read_dword(sc, offset32, buf, cmd_flags);
2276
2277                 memcpy(ret_buf, buf, 4 - extra);
2278         }
2279         else if (len32 > 0) {
2280                 u8 buf[4];
2281
2282                 /* Read the first word. */
2283                 if (cmd_flags)
2284                         cmd_flags = 0;
2285                 else
2286                         cmd_flags = BCE_NVM_COMMAND_FIRST;
2287
2288                 rc = bce_nvram_read_dword(sc, offset32, ret_buf, cmd_flags);
2289
2290                 /* Advance to the next dword. */
2291                 offset32 += 4;
2292                 ret_buf += 4;
2293                 len32 -= 4;
2294
2295                 while (len32 > 4 && rc == 0) {
2296                         rc = bce_nvram_read_dword(sc, offset32, ret_buf, 0);
2297
2298                         /* Advance to the next dword. */
2299                         offset32 += 4;
2300                         ret_buf += 4;
2301                         len32 -= 4;
2302                 }
2303
2304                 if (rc)
2305                         goto bce_nvram_read_locked_exit;
2306
2307                 cmd_flags = BCE_NVM_COMMAND_LAST;
2308                 rc = bce_nvram_read_dword(sc, offset32, buf, cmd_flags);
2309
2310                 memcpy(ret_buf, buf, 4 - extra);
2311         }
2312
2313 bce_nvram_read_locked_exit:
2314         /* Disable access to flash interface and release the lock. */
2315         bce_disable_nvram_access(sc);
2316         bce_release_nvram_lock(sc);
2317
2318 bce_nvram_read_exit:
2319         DBEXIT(BCE_VERBOSE_NVRAM);
2320         return rc;
2321 }
2322
2323
2324 #ifdef BCE_NVRAM_WRITE_SUPPORT
2325 /****************************************************************************/
2326 /* Write an arbitrary range of data from NVRAM.                             */
2327 /*                                                                          */
2328 /* Prepares the NVRAM interface for write access and writes the requested   */
2329 /* data from the supplied buffer.  The caller is responsible for            */
2330 /* calculating any appropriate CRCs.                                        */
2331 /*                                                                          */
2332 /* Returns:                                                                 */
2333 /*   0 on success, positive value on failure.                               */
2334 /****************************************************************************/
2335 static int
2336 bce_nvram_write(struct bce_softc *sc, u32 offset, u8 *data_buf,
2337         int buf_size)
2338 {
2339         u32 written, offset32, len32;
2340         u8 *buf, start[4], end[4];
2341         int rc = 0;
2342         int align_start, align_end;
2343
2344         DBENTER(BCE_VERBOSE_NVRAM);
2345
2346         buf = data_buf;
2347         offset32 = offset;
2348         len32 = buf_size;
2349         align_start = align_end = 0;
2350
2351         if ((align_start = (offset32 & 3))) {
2352                 offset32 &= ~3;
2353                 len32 += align_start;
2354                 if ((rc = bce_nvram_read(sc, offset32, start, 4)))
2355                         goto bce_nvram_write_exit;
2356         }
2357
2358         if (len32 & 3) {
2359                 if ((len32 > 4) || !align_start) {
2360                         align_end = 4 - (len32 & 3);
2361                         len32 += align_end;
2362                         if ((rc = bce_nvram_read(sc, offset32 + len32 - 4,
2363                                 end, 4))) {
2364                                 goto bce_nvram_write_exit;
2365                         }
2366                 }
2367         }
2368
2369         if (align_start || align_end) {
2370                 buf = malloc(len32, M_DEVBUF, M_NOWAIT);
2371                 if (buf == 0) {
2372                         rc = ENOMEM;
2373                         goto bce_nvram_write_exit;
2374                 }
2375
2376                 if (align_start) {
2377                         memcpy(buf, start, 4);
2378                 }
2379
2380                 if (align_end) {
2381                         memcpy(buf + len32 - 4, end, 4);
2382                 }
2383                 memcpy(buf + align_start, data_buf, buf_size);
2384         }
2385
2386         written = 0;
2387         while ((written < len32) && (rc == 0)) {
2388                 u32 page_start, page_end, data_start, data_end;
2389                 u32 addr, cmd_flags;
2390                 int i;
2391                 u8 flash_buffer[264];
2392
2393             /* Find the page_start addr */
2394                 page_start = offset32 + written;
2395                 page_start -= (page_start % sc->bce_flash_info->page_size);
2396                 /* Find the page_end addr */
2397                 page_end = page_start + sc->bce_flash_info->page_size;
2398                 /* Find the data_start addr */
2399                 data_start = (written == 0) ? offset32 : page_start;
2400                 /* Find the data_end addr */
2401                 data_end = (page_end > offset32 + len32) ?
2402                         (offset32 + len32) : page_end;
2403
2404                 /* Request access to the flash interface. */
2405                 if ((rc = bce_acquire_nvram_lock(sc)) != 0)
2406                         goto bce_nvram_write_exit;
2407
2408                 /* Enable access to flash interface */
2409                 bce_enable_nvram_access(sc);
2410
2411                 cmd_flags = BCE_NVM_COMMAND_FIRST;
2412                 if (!(sc->bce_flash_info->flags & BCE_NV_BUFFERED)) {
2413                         int j;
2414
2415                         /* Read the whole page into the buffer
2416                          * (non-buffer flash only) */
2417                         for (j = 0; j < sc->bce_flash_info->page_size; j += 4) {
2418                                 if (j == (sc->bce_flash_info->page_size - 4)) {
2419                                         cmd_flags |= BCE_NVM_COMMAND_LAST;
2420                                 }
2421                                 rc = bce_nvram_read_dword(sc,
2422                                         page_start + j,
2423                                         &flash_buffer[j],
2424                                         cmd_flags);
2425
2426                                 if (rc)
2427                                         goto bce_nvram_write_locked_exit;
2428
2429                                 cmd_flags = 0;
2430                         }
2431                 }
2432
2433                 /* Enable writes to flash interface (unlock write-protect) */
2434                 if ((rc = bce_enable_nvram_write(sc)) != 0)
2435                         goto bce_nvram_write_locked_exit;
2436
2437                 /* Erase the page */
2438                 if ((rc = bce_nvram_erase_page(sc, page_start)) != 0)
2439                         goto bce_nvram_write_locked_exit;
2440
2441                 /* Re-enable the write again for the actual write */
2442                 bce_enable_nvram_write(sc);
2443
2444                 /* Loop to write back the buffer data from page_start to
2445                  * data_start */
2446                 i = 0;
2447                 if (!(sc->bce_flash_info->flags & BCE_NV_BUFFERED)) {
2448                         for (addr = page_start; addr < data_start;
2449                                 addr += 4, i += 4) {
2450
2451                                 rc = bce_nvram_write_dword(sc, addr,
2452                                         &flash_buffer[i], cmd_flags);
2453
2454                                 if (rc != 0)
2455                                         goto bce_nvram_write_locked_exit;
2456
2457                                 cmd_flags = 0;
2458                         }
2459                 }
2460
2461                 /* Loop to write the new data from data_start to data_end */
2462                 for (addr = data_start; addr < data_end; addr += 4, i++) {
2463                         if ((addr == page_end - 4) ||
2464                                 ((sc->bce_flash_info->flags & BCE_NV_BUFFERED) &&
2465                                 (addr == data_end - 4))) {
2466
2467                                 cmd_flags |= BCE_NVM_COMMAND_LAST;
2468                         }
2469                         rc = bce_nvram_write_dword(sc, addr, buf,
2470                                 cmd_flags);
2471
2472                         if (rc != 0)
2473                                 goto bce_nvram_write_locked_exit;
2474
2475                         cmd_flags = 0;
2476                         buf += 4;
2477                 }
2478
2479                 /* Loop to write back the buffer data from data_end
2480                  * to page_end */
2481                 if (!(sc->bce_flash_info->flags & BCE_NV_BUFFERED)) {
2482                         for (addr = data_end; addr < page_end;
2483                                 addr += 4, i += 4) {
2484
2485                                 if (addr == page_end-4) {
2486                                         cmd_flags = BCE_NVM_COMMAND_LAST;
2487                                 }
2488                                 rc = bce_nvram_write_dword(sc, addr,
2489                                         &flash_buffer[i], cmd_flags);
2490
2491                                 if (rc != 0)
2492                                         goto bce_nvram_write_locked_exit;
2493
2494                                 cmd_flags = 0;
2495                         }
2496                 }
2497
2498                 /* Disable writes to flash interface (lock write-protect) */
2499                 bce_disable_nvram_write(sc);
2500
2501                 /* Disable access to flash interface */
2502                 bce_disable_nvram_access(sc);
2503                 bce_release_nvram_lock(sc);
2504
2505                 /* Increment written */
2506                 written += data_end - data_start;
2507         }
2508
2509         goto bce_nvram_write_exit;
2510
2511 bce_nvram_write_locked_exit:
2512                 bce_disable_nvram_write(sc);
2513                 bce_disable_nvram_access(sc);
2514                 bce_release_nvram_lock(sc);
2515
2516 bce_nvram_write_exit:
2517         if (align_start || align_end)
2518                 free(buf, M_DEVBUF);
2519
2520         DBEXIT(BCE_VERBOSE_NVRAM);
2521         return (rc);
2522 }
2523 #endif /* BCE_NVRAM_WRITE_SUPPORT */
2524
2525
2526 /****************************************************************************/
2527 /* Verifies that NVRAM is accessible and contains valid data.               */
2528 /*                                                                          */
2529 /* Reads the configuration data from NVRAM and verifies that the CRC is     */
2530 /* correct.                                                                 */
2531 /*                                                                          */
2532 /* Returns:                                                                 */
2533 /*   0 on success, positive value on failure.                               */
2534 /****************************************************************************/
2535 static int
2536 bce_nvram_test(struct bce_softc *sc)
2537 {
2538         u32 buf[BCE_NVRAM_SIZE / 4];
2539         u8 *data = (u8 *) buf;
2540         int rc = 0;
2541         u32 magic, csum;
2542
2543         DBENTER(BCE_VERBOSE_NVRAM | BCE_VERBOSE_LOAD | BCE_VERBOSE_RESET);
2544
2545         /*
2546          * Check that the device NVRAM is valid by reading
2547          * the magic value at offset 0.
2548          */
2549         if ((rc = bce_nvram_read(sc, 0, data, 4)) != 0) {
2550                 BCE_PRINTF("%s(%d): Unable to read NVRAM!\n", __FILE__, __LINE__);
2551                 goto bce_nvram_test_exit;
2552         }
2553
2554         /*
2555          * Verify that offset 0 of the NVRAM contains
2556          * a valid magic number.
2557          */
2558     magic = bce_be32toh(buf[0]);
2559         if (magic != BCE_NVRAM_MAGIC) {
2560                 rc = ENODEV;
2561                 BCE_PRINTF("%s(%d): Invalid NVRAM magic value! Expected: 0x%08X, "
2562                         "Found: 0x%08X\n",
2563                         __FILE__, __LINE__, BCE_NVRAM_MAGIC, magic);
2564                 goto bce_nvram_test_exit;
2565         }
2566
2567         /*
2568          * Verify that the device NVRAM includes valid
2569          * configuration data.
2570          */
2571         if ((rc = bce_nvram_read(sc, 0x100, data, BCE_NVRAM_SIZE)) != 0) {
2572                 BCE_PRINTF("%s(%d): Unable to read Manufacturing Information from "
2573                         "NVRAM!\n", __FILE__, __LINE__);
2574                 goto bce_nvram_test_exit;
2575         }
2576
2577         csum = ether_crc32_le(data, 0x100);
2578         if (csum != BCE_CRC32_RESIDUAL) {
2579                 rc = ENODEV;
2580                 BCE_PRINTF("%s(%d): Invalid Manufacturing Information NVRAM CRC! "
2581                         "Expected: 0x%08X, Found: 0x%08X\n",
2582                         __FILE__, __LINE__, BCE_CRC32_RESIDUAL, csum);
2583                 goto bce_nvram_test_exit;
2584         }
2585
2586         csum = ether_crc32_le(data + 0x100, 0x100);
2587         if (csum != BCE_CRC32_RESIDUAL) {
2588                 rc = ENODEV;
2589                 BCE_PRINTF("%s(%d): Invalid Feature Configuration Information "
2590                         "NVRAM CRC! Expected: 0x%08X, Found: 08%08X\n",
2591                         __FILE__, __LINE__, BCE_CRC32_RESIDUAL, csum);
2592         }
2593
2594 bce_nvram_test_exit:
2595         DBEXIT(BCE_VERBOSE_NVRAM | BCE_VERBOSE_LOAD | BCE_VERBOSE_RESET);
2596         return rc;
2597 }
2598
2599
2600 /****************************************************************************/
2601 /* Identifies the current media type of the controller and sets the PHY     */
2602 /* address.                                                                 */
2603 /*                                                                          */
2604 /* Returns:                                                                 */
2605 /*   Nothing.                                                               */
2606 /****************************************************************************/
2607 static void
2608 bce_get_media(struct bce_softc *sc)
2609 {
2610         u32 val;
2611
2612         DBENTER(BCE_VERBOSE);
2613
2614         /* Assume PHY address for copper controllers. */
2615         sc->bce_phy_addr = 1;
2616
2617         if (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) {
2618                 u32 val = REG_RD(sc, BCE_MISC_DUAL_MEDIA_CTRL);
2619                 u32 bond_id = val & BCE_MISC_DUAL_MEDIA_CTRL_BOND_ID;
2620                 u32 strap;
2621
2622                 /*
2623                  * The BCM5709S is software configurable
2624                  * for Copper or SerDes operation.
2625                  */
2626                 if (bond_id == BCE_MISC_DUAL_MEDIA_CTRL_BOND_ID_C) {
2627                         DBPRINT(sc, BCE_INFO_LOAD, "5709 bonded for copper.\n");
2628                         goto bce_get_media_exit;
2629                 } else if (bond_id == BCE_MISC_DUAL_MEDIA_CTRL_BOND_ID_S) {
2630                         DBPRINT(sc, BCE_INFO_LOAD, "5709 bonded for dual media.\n");
2631                         sc->bce_phy_flags |= BCE_PHY_SERDES_FLAG;
2632                         goto bce_get_media_exit;
2633                 }
2634
2635                 if (val & BCE_MISC_DUAL_MEDIA_CTRL_STRAP_OVERRIDE)
2636                         strap = (val & BCE_MISC_DUAL_MEDIA_CTRL_PHY_CTRL) >> 21;
2637                 else
2638                         strap = (val & BCE_MISC_DUAL_MEDIA_CTRL_PHY_CTRL_STRAP) >> 8;
2639
2640                 if (pci_get_function(sc->bce_dev) == 0) {
2641                         switch (strap) {
2642                         case 0x4:
2643                         case 0x5:
2644                         case 0x6:
2645                                 DBPRINT(sc, BCE_INFO_LOAD,
2646                                         "BCM5709 s/w configured for SerDes.\n");
2647                                 sc->bce_phy_flags |= BCE_PHY_SERDES_FLAG;
2648                         default:
2649                                 DBPRINT(sc, BCE_INFO_LOAD,
2650                                         "BCM5709 s/w configured for Copper.\n");
2651                         }
2652                 } else {
2653                         switch (strap) {
2654                         case 0x1:
2655                         case 0x2:
2656                         case 0x4:
2657                                 DBPRINT(sc, BCE_INFO_LOAD,
2658                                         "BCM5709 s/w configured for SerDes.\n");
2659                                 sc->bce_phy_flags |= BCE_PHY_SERDES_FLAG;
2660                         default:
2661                                 DBPRINT(sc, BCE_INFO_LOAD,
2662                                         "BCM5709 s/w configured for Copper.\n");
2663                         }
2664                 }
2665
2666         } else if (BCE_CHIP_BOND_ID(sc) & BCE_CHIP_BOND_ID_SERDES_BIT)
2667                 sc->bce_phy_flags |= BCE_PHY_SERDES_FLAG;
2668
2669         if (sc->bce_phy_flags & BCE_PHY_SERDES_FLAG) {
2670                 sc->bce_flags |= BCE_NO_WOL_FLAG;
2671                 if (BCE_CHIP_NUM(sc) != BCE_CHIP_NUM_5706) {
2672                         sc->bce_phy_addr = 2;
2673                         val = bce_shmem_rd(sc, BCE_SHARED_HW_CFG_CONFIG);
2674                         if (val & BCE_SHARED_HW_CFG_PHY_2_5G) {
2675                                 sc->bce_phy_flags |= BCE_PHY_2_5G_CAPABLE_FLAG;
2676                                 DBPRINT(sc, BCE_INFO_LOAD, "Found 2.5Gb capable adapter\n");
2677                         }
2678                 }
2679         } else if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5706) ||
2680                    (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5708))
2681                 sc->bce_phy_flags |= BCE_PHY_CRC_FIX_FLAG;
2682
2683 bce_get_media_exit:
2684         DBPRINT(sc, (BCE_INFO_LOAD | BCE_INFO_PHY),
2685                 "Using PHY address %d.\n", sc->bce_phy_addr);
2686
2687         DBEXIT(BCE_VERBOSE);
2688 }
2689
2690
2691 /****************************************************************************/
2692 /* Free any DMA memory owned by the driver.                                 */
2693 /*                                                                          */
2694 /* Scans through each data structre that requires DMA memory and frees      */
2695 /* the memory if allocated.                                                 */
2696 /*                                                                          */
2697 /* Returns:                                                                 */
2698 /*   Nothing.                                                               */
2699 /****************************************************************************/
2700 static void
2701 bce_dma_free(struct bce_softc *sc)
2702 {
2703         int i;
2704
2705         DBENTER(BCE_VERBOSE_RESET | BCE_VERBOSE_UNLOAD | BCE_VERBOSE_CTX);
2706
2707         /* Free, unmap, and destroy the status block. */
2708         if (sc->status_block != NULL) {
2709                 bus_dmamem_free(
2710                         sc->status_tag,
2711                     sc->status_block,
2712                     sc->status_map);
2713                 sc->status_block = NULL;
2714         }
2715
2716         if (sc->status_map != NULL) {
2717                 bus_dmamap_unload(
2718                         sc->status_tag,
2719                     sc->status_map);
2720                 bus_dmamap_destroy(sc->status_tag,
2721                     sc->status_map);
2722                 sc->status_map = NULL;
2723         }
2724
2725         if (sc->status_tag != NULL) {
2726                 bus_dma_tag_destroy(sc->status_tag);
2727                 sc->status_tag = NULL;
2728         }
2729
2730
2731         /* Free, unmap, and destroy the statistics block. */
2732         if (sc->stats_block != NULL) {
2733                 bus_dmamem_free(
2734                         sc->stats_tag,
2735                     sc->stats_block,
2736                     sc->stats_map);
2737                 sc->stats_block = NULL;
2738         }
2739
2740         if (sc->stats_map != NULL) {
2741                 bus_dmamap_unload(
2742                         sc->stats_tag,
2743                     sc->stats_map);
2744                 bus_dmamap_destroy(sc->stats_tag,
2745                     sc->stats_map);
2746                 sc->stats_map = NULL;
2747         }
2748
2749         if (sc->stats_tag != NULL) {
2750                 bus_dma_tag_destroy(sc->stats_tag);
2751                 sc->stats_tag = NULL;
2752         }
2753
2754
2755         /* Free, unmap and destroy all context memory pages. */
2756         if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
2757                 (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
2758                 for (i = 0; i < sc->ctx_pages; i++ ) {
2759                         if (sc->ctx_block[i] != NULL) {
2760                                 bus_dmamem_free(
2761                                         sc->ctx_tag,
2762                                     sc->ctx_block[i],
2763                                     sc->ctx_map[i]);
2764                                 sc->ctx_block[i] = NULL;
2765                         }
2766
2767                         if (sc->ctx_map[i] != NULL) {
2768                                 bus_dmamap_unload(
2769                                         sc->ctx_tag,
2770                                 sc->ctx_map[i]);
2771                                 bus_dmamap_destroy(
2772                                         sc->ctx_tag,
2773                                     sc->ctx_map[i]);
2774                                 sc->ctx_map[i] = NULL;
2775                         }
2776                 }
2777
2778                 /* Destroy the context memory tag. */
2779                 if (sc->ctx_tag != NULL) {
2780                         bus_dma_tag_destroy(sc->ctx_tag);
2781                         sc->ctx_tag = NULL;
2782                 }
2783         }
2784
2785
2786         /* Free, unmap and destroy all TX buffer descriptor chain pages. */
2787         for (i = 0; i < TX_PAGES; i++ ) {
2788                 if (sc->tx_bd_chain[i] != NULL) {
2789                         bus_dmamem_free(
2790                                 sc->tx_bd_chain_tag,
2791                             sc->tx_bd_chain[i],
2792                             sc->tx_bd_chain_map[i]);
2793                         sc->tx_bd_chain[i] = NULL;
2794                 }
2795
2796                 if (sc->tx_bd_chain_map[i] != NULL) {
2797                         bus_dmamap_unload(
2798                                 sc->tx_bd_chain_tag,
2799                         sc->tx_bd_chain_map[i]);
2800                         bus_dmamap_destroy(
2801                                 sc->tx_bd_chain_tag,
2802                             sc->tx_bd_chain_map[i]);
2803                         sc->tx_bd_chain_map[i] = NULL;
2804                 }
2805         }
2806
2807         /* Destroy the TX buffer descriptor tag. */
2808         if (sc->tx_bd_chain_tag != NULL) {
2809                 bus_dma_tag_destroy(sc->tx_bd_chain_tag);
2810                 sc->tx_bd_chain_tag = NULL;
2811         }
2812
2813
2814         /* Free, unmap and destroy all RX buffer descriptor chain pages. */
2815         for (i = 0; i < RX_PAGES; i++ ) {
2816                 if (sc->rx_bd_chain[i] != NULL) {
2817                         bus_dmamem_free(
2818                                 sc->rx_bd_chain_tag,
2819                             sc->rx_bd_chain[i],
2820                             sc->rx_bd_chain_map[i]);
2821                         sc->rx_bd_chain[i] = NULL;
2822                 }
2823
2824                 if (sc->rx_bd_chain_map[i] != NULL) {
2825                         bus_dmamap_unload(
2826                                 sc->rx_bd_chain_tag,
2827                         sc->rx_bd_chain_map[i]);
2828                         bus_dmamap_destroy(
2829                                 sc->rx_bd_chain_tag,
2830                             sc->rx_bd_chain_map[i]);
2831                         sc->rx_bd_chain_map[i] = NULL;
2832                 }
2833         }
2834
2835         /* Destroy the RX buffer descriptor tag. */
2836         if (sc->rx_bd_chain_tag != NULL) {
2837                 bus_dma_tag_destroy(sc->rx_bd_chain_tag);
2838                 sc->rx_bd_chain_tag = NULL;
2839         }
2840
2841
2842 #ifdef BCE_JUMBO_HDRSPLIT
2843         /* Free, unmap and destroy all page buffer descriptor chain pages. */
2844         for (i = 0; i < PG_PAGES; i++ ) {
2845                 if (sc->pg_bd_chain[i] != NULL) {
2846                         bus_dmamem_free(
2847                                 sc->pg_bd_chain_tag,
2848                             sc->pg_bd_chain[i],
2849                             sc->pg_bd_chain_map[i]);
2850                         sc->pg_bd_chain[i] = NULL;
2851                 }
2852
2853                 if (sc->pg_bd_chain_map[i] != NULL) {
2854                         bus_dmamap_unload(
2855                                 sc->pg_bd_chain_tag,
2856                         sc->pg_bd_chain_map[i]);
2857                         bus_dmamap_destroy(
2858                                 sc->pg_bd_chain_tag,
2859                             sc->pg_bd_chain_map[i]);
2860                         sc->pg_bd_chain_map[i] = NULL;
2861                 }
2862         }
2863
2864         /* Destroy the page buffer descriptor tag. */
2865         if (sc->pg_bd_chain_tag != NULL) {
2866                 bus_dma_tag_destroy(sc->pg_bd_chain_tag);
2867                 sc->pg_bd_chain_tag = NULL;
2868         }
2869 #endif
2870
2871
2872         /* Unload and destroy the TX mbuf maps. */
2873         for (i = 0; i < TOTAL_TX_BD; i++) {
2874                 if (sc->tx_mbuf_map[i] != NULL) {
2875                         bus_dmamap_unload(sc->tx_mbuf_tag,
2876                                 sc->tx_mbuf_map[i]);
2877                         bus_dmamap_destroy(sc->tx_mbuf_tag,
2878                                 sc->tx_mbuf_map[i]);
2879                         sc->tx_mbuf_map[i] = NULL;
2880                 }
2881         }
2882
2883         /* Destroy the TX mbuf tag. */
2884         if (sc->tx_mbuf_tag != NULL) {
2885                 bus_dma_tag_destroy(sc->tx_mbuf_tag);
2886                 sc->tx_mbuf_tag = NULL;
2887         }
2888
2889         /* Unload and destroy the RX mbuf maps. */
2890         for (i = 0; i < TOTAL_RX_BD; i++) {
2891                 if (sc->rx_mbuf_map[i] != NULL) {
2892                         bus_dmamap_unload(sc->rx_mbuf_tag,
2893                                 sc->rx_mbuf_map[i]);
2894                         bus_dmamap_destroy(sc->rx_mbuf_tag,
2895                                 sc->rx_mbuf_map[i]);
2896                         sc->rx_mbuf_map[i] = NULL;
2897                 }
2898         }
2899
2900         /* Destroy the RX mbuf tag. */
2901         if (sc->rx_mbuf_tag != NULL) {
2902                 bus_dma_tag_destroy(sc->rx_mbuf_tag);
2903                 sc->rx_mbuf_tag = NULL;
2904         }
2905
2906 #ifdef BCE_JUMBO_HDRSPLIT
2907         /* Unload and destroy the page mbuf maps. */
2908         for (i = 0; i < TOTAL_PG_BD; i++) {
2909                 if (sc->pg_mbuf_map[i] != NULL) {
2910                         bus_dmamap_unload(sc->pg_mbuf_tag,
2911                                 sc->pg_mbuf_map[i]);
2912                         bus_dmamap_destroy(sc->pg_mbuf_tag,
2913                                 sc->pg_mbuf_map[i]);
2914                         sc->pg_mbuf_map[i] = NULL;
2915                 }
2916         }
2917
2918         /* Destroy the page mbuf tag. */
2919         if (sc->pg_mbuf_tag != NULL) {
2920                 bus_dma_tag_destroy(sc->pg_mbuf_tag);
2921                 sc->pg_mbuf_tag = NULL;
2922         }
2923 #endif
2924
2925         /* Destroy the parent tag */
2926         if (sc->parent_tag != NULL) {
2927                 bus_dma_tag_destroy(sc->parent_tag);
2928                 sc->parent_tag = NULL;
2929         }
2930
2931         DBEXIT(BCE_VERBOSE_RESET | BCE_VERBOSE_UNLOAD | BCE_VERBOSE_CTX);
2932 }
2933
2934
2935 /****************************************************************************/
2936 /* Get DMA memory from the OS.                                              */
2937 /*                                                                          */
2938 /* Validates that the OS has provided DMA buffers in response to a          */
2939 /* bus_dmamap_load() call and saves the physical address of those buffers.  */
2940 /* When the callback is used the OS will return 0 for the mapping function  */
2941 /* (bus_dmamap_load()) so we use the value of map_arg->maxsegs to pass any  */
2942 /* failures back to the caller.                                             */
2943 /*                                                                          */
2944 /* Returns:                                                                 */
2945 /*   Nothing.                                                               */
2946 /****************************************************************************/
2947 static void
2948 bce_dma_map_addr(void *arg, bus_dma_segment_t *segs, int nseg, int error)
2949 {
2950         bus_addr_t *busaddr = arg;
2951
2952         /* Simulate a mapping failure. */
2953         DBRUNIF(DB_RANDOMTRUE(dma_map_addr_failed_sim_control),
2954                 error = ENOMEM);
2955
2956         /* Check for an error and signal the caller that an error occurred. */
2957         if (error) {
2958                 *busaddr = 0;
2959         } else {
2960                 *busaddr = segs->ds_addr;
2961         }
2962
2963         return;
2964 }
2965
2966
2967 /****************************************************************************/
2968 /* Allocate any DMA memory needed by the driver.                            */
2969 /*                                                                          */
2970 /* Allocates DMA memory needed for the various global structures needed by  */
2971 /* hardware.                                                                */
2972 /*                                                                          */
2973 /* Memory alignment requirements:                                           */
2974 /* +-----------------+----------+----------+----------+----------+          */
2975 /* |                 |   5706   |   5708   |   5709   |   5716   |          */
2976 /* +-----------------+----------+----------+----------+----------+          */
2977 /* |Status Block     | 8 bytes  | 8 bytes  | 16 bytes | 16 bytes |          */
2978 /* |Statistics Block | 8 bytes  | 8 bytes  | 16 bytes | 16 bytes |          */
2979 /* |RX Buffers       | 16 bytes | 16 bytes | 16 bytes | 16 bytes |          */
2980 /* |PG Buffers       |   none   |   none   |   none   |   none   |          */
2981 /* |TX Buffers       |   none   |   none   |   none   |   none   |          */
2982 /* |Chain Pages(1)   |   4KiB   |   4KiB   |   4KiB   |   4KiB   |          */
2983 /* |Context Memory   |          |          |          |          |          */
2984 /* +-----------------+----------+----------+----------+----------+          */
2985 /*                                                                          */
2986 /* (1) Must align with CPU page size (BCM_PAGE_SZIE).                       */
2987 /*                                                                          */
2988 /* Returns:                                                                 */
2989 /*   0 for success, positive value for failure.                             */
2990 /****************************************************************************/
2991 static int
2992 bce_dma_alloc(device_t dev)
2993 {
2994         struct bce_softc *sc;
2995         int i, error, rc = 0;
2996         bus_size_t max_size, max_seg_size;
2997         int max_segments;
2998
2999         sc = device_get_softc(dev);
3000
3001         DBENTER(BCE_VERBOSE_RESET | BCE_VERBOSE_CTX);
3002
3003         /*
3004          * Allocate the parent bus DMA tag appropriate for PCI.
3005          */
3006         if (bus_dma_tag_create(NULL,
3007                         1,
3008                         BCE_DMA_BOUNDARY,
3009                         sc->max_bus_addr,
3010                         BUS_SPACE_MAXADDR,
3011                         NULL, NULL,
3012                         MAXBSIZE,
3013                         BUS_SPACE_UNRESTRICTED,
3014                         BUS_SPACE_MAXSIZE_32BIT,
3015                         0,
3016                         NULL, NULL,
3017                         &sc->parent_tag)) {
3018                 BCE_PRINTF("%s(%d): Could not allocate parent DMA tag!\n",
3019                         __FILE__, __LINE__);
3020                 rc = ENOMEM;
3021                 goto bce_dma_alloc_exit;
3022         }
3023
3024         /*
3025          * Create a DMA tag for the status block, allocate and clear the
3026          * memory, map the memory into DMA space, and fetch the physical
3027          * address of the block.
3028          */
3029         if (bus_dma_tag_create(sc->parent_tag,
3030                 BCE_DMA_ALIGN,
3031                 BCE_DMA_BOUNDARY,
3032                 sc->max_bus_addr,
3033                 BUS_SPACE_MAXADDR,
3034                 NULL, NULL,
3035                 BCE_STATUS_BLK_SZ,
3036                 1,
3037                 BCE_STATUS_BLK_SZ,
3038                 0,
3039                 NULL, NULL,
3040                 &sc->status_tag)) {
3041                 BCE_PRINTF("%s(%d): Could not allocate status block DMA tag!\n",
3042                         __FILE__, __LINE__);
3043                 rc = ENOMEM;
3044                 goto bce_dma_alloc_exit;
3045         }
3046
3047         if(bus_dmamem_alloc(sc->status_tag,
3048                 (void **)&sc->status_block,
3049                 BUS_DMA_NOWAIT,
3050                 &sc->status_map)) {
3051                 BCE_PRINTF("%s(%d): Could not allocate status block DMA memory!\n",
3052                         __FILE__, __LINE__);
3053                 rc = ENOMEM;
3054                 goto bce_dma_alloc_exit;
3055         }
3056
3057         bzero((char *)sc->status_block, BCE_STATUS_BLK_SZ);
3058
3059         error = bus_dmamap_load(sc->status_tag,
3060                 sc->status_map,
3061                 sc->status_block,
3062                 BCE_STATUS_BLK_SZ,
3063                 bce_dma_map_addr,
3064                 &sc->status_block_paddr,
3065                 BUS_DMA_NOWAIT);
3066
3067         if (error) {
3068                 BCE_PRINTF("%s(%d): Could not map status block DMA memory!\n",
3069                         __FILE__, __LINE__);
3070                 rc = ENOMEM;
3071                 goto bce_dma_alloc_exit;
3072         }
3073
3074         DBPRINT(sc, BCE_INFO, "%s(): status_block_paddr = 0x%jX\n",
3075                 __FUNCTION__, (uintmax_t) sc->status_block_paddr);
3076
3077         /*
3078          * Create a DMA tag for the statistics block, allocate and clear the
3079          * memory, map the memory into DMA space, and fetch the physical
3080          * address of the block.
3081          */
3082         if (bus_dma_tag_create(sc->parent_tag,
3083                 BCE_DMA_ALIGN,
3084                 BCE_DMA_BOUNDARY,
3085                 sc->max_bus_addr,
3086                 BUS_SPACE_MAXADDR,
3087                 NULL, NULL,
3088                 BCE_STATS_BLK_SZ,
3089                 1,
3090                 BCE_STATS_BLK_SZ,
3091                 0,
3092                 NULL, NULL,
3093                 &sc->stats_tag)) {
3094                 BCE_PRINTF("%s(%d): Could not allocate statistics block DMA tag!\n",
3095                         __FILE__, __LINE__);
3096                 rc = ENOMEM;
3097                 goto bce_dma_alloc_exit;
3098         }
3099
3100         if (bus_dmamem_alloc(sc->stats_tag,
3101                 (void **)&sc->stats_block,
3102                 BUS_DMA_NOWAIT,
3103                 &sc->stats_map)) {
3104                 BCE_PRINTF("%s(%d): Could not allocate statistics block DMA memory!\n",
3105                         __FILE__, __LINE__);
3106                 rc = ENOMEM;
3107                 goto bce_dma_alloc_exit;
3108         }
3109
3110         bzero((char *)sc->stats_block, BCE_STATS_BLK_SZ);
3111
3112         error = bus_dmamap_load(sc->stats_tag,
3113                 sc->stats_map,
3114                 sc->stats_block,
3115                 BCE_STATS_BLK_SZ,
3116                 bce_dma_map_addr,
3117                 &sc->stats_block_paddr,
3118                 BUS_DMA_NOWAIT);
3119
3120         if(error) {
3121                 BCE_PRINTF("%s(%d): Could not map statistics block DMA memory!\n",
3122                         __FILE__, __LINE__);
3123                 rc = ENOMEM;
3124                 goto bce_dma_alloc_exit;
3125         }
3126
3127         DBPRINT(sc, BCE_INFO, "%s(): stats_block_paddr = 0x%jX\n",
3128                 __FUNCTION__, (uintmax_t) sc->stats_block_paddr);
3129
3130         /* BCM5709 uses host memory as cache for context memory. */
3131         if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
3132                 (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
3133                 sc->ctx_pages = 0x2000 / BCM_PAGE_SIZE;
3134                 if (sc->ctx_pages == 0)
3135                         sc->ctx_pages = 1;
3136
3137                 DBRUNIF((sc->ctx_pages > 512),
3138                         BCE_PRINTF("%s(%d): Too many CTX pages! %d > 512\n",
3139                                 __FILE__, __LINE__, sc->ctx_pages));
3140
3141                 /*
3142                  * Create a DMA tag for the context pages,
3143                  * allocate and clear the memory, map the
3144                  * memory into DMA space, and fetch the
3145                  * physical address of the block.
3146                  */
3147                 if(bus_dma_tag_create(sc->parent_tag,
3148                         BCM_PAGE_SIZE,
3149                     BCE_DMA_BOUNDARY,
3150                         sc->max_bus_addr,
3151                         BUS_SPACE_MAXADDR,
3152                         NULL, NULL,
3153                         BCM_PAGE_SIZE,
3154                         1,
3155                         BCM_PAGE_SIZE,
3156                         0,
3157                         NULL, NULL,
3158                         &sc->ctx_tag)) {
3159                         BCE_PRINTF("%s(%d): Could not allocate CTX DMA tag!\n",
3160                                 __FILE__, __LINE__);
3161                         rc = ENOMEM;
3162                         goto bce_dma_alloc_exit;
3163                 }
3164
3165                 for (i = 0; i < sc->ctx_pages; i++) {
3166
3167                         if(bus_dmamem_alloc(sc->ctx_tag,
3168                                 (void **)&sc->ctx_block[i],
3169                         BUS_DMA_NOWAIT,
3170                         &sc->ctx_map[i])) {
3171                                 BCE_PRINTF("%s(%d): Could not allocate CTX "
3172                                         "DMA memory!\n", __FILE__, __LINE__);
3173                                 rc = ENOMEM;
3174                                 goto bce_dma_alloc_exit;
3175                         }
3176
3177                         bzero((char *)sc->ctx_block[i], BCM_PAGE_SIZE);
3178
3179                         error = bus_dmamap_load(sc->ctx_tag,
3180                         sc->ctx_map[i],
3181                         sc->ctx_block[i],
3182                         BCM_PAGE_SIZE,
3183                         bce_dma_map_addr,
3184                         &sc->ctx_paddr[i],
3185                         BUS_DMA_NOWAIT);
3186
3187                         if (error) {
3188                                 BCE_PRINTF("%s(%d): Could not map CTX DMA memory!\n",
3189                                         __FILE__, __LINE__);
3190                                 rc = ENOMEM;
3191                                 goto bce_dma_alloc_exit;
3192                         }
3193
3194                         DBPRINT(sc, BCE_INFO, "%s(): ctx_paddr[%d] = 0x%jX\n",
3195                                 __FUNCTION__, i, (uintmax_t) sc->ctx_paddr[i]);
3196                 }
3197         }
3198
3199         /*
3200          * Create a DMA tag for the TX buffer descriptor chain,
3201          * allocate and clear the  memory, and fetch the
3202          * physical address of the block.
3203          */
3204         if(bus_dma_tag_create(sc->parent_tag,
3205                         BCM_PAGE_SIZE,
3206                     BCE_DMA_BOUNDARY,
3207                         sc->max_bus_addr,
3208                         BUS_SPACE_MAXADDR,
3209                         NULL, NULL,
3210                         BCE_TX_CHAIN_PAGE_SZ,
3211                         1,
3212                         BCE_TX_CHAIN_PAGE_SZ,
3213                         0,
3214                         NULL, NULL,
3215                         &sc->tx_bd_chain_tag)) {
3216                 BCE_PRINTF("%s(%d): Could not allocate TX descriptor chain DMA tag!\n",
3217                         __FILE__, __LINE__);
3218                 rc = ENOMEM;
3219                 goto bce_dma_alloc_exit;
3220         }
3221
3222         for (i = 0; i < TX_PAGES; i++) {
3223
3224                 if(bus_dmamem_alloc(sc->tx_bd_chain_tag,
3225                         (void **)&sc->tx_bd_chain[i],
3226                         BUS_DMA_NOWAIT,
3227                         &sc->tx_bd_chain_map[i])) {
3228                         BCE_PRINTF("%s(%d): Could not allocate TX descriptor "
3229                                 "chain DMA memory!\n", __FILE__, __LINE__);
3230                         rc = ENOMEM;
3231                         goto bce_dma_alloc_exit;
3232                 }
3233
3234                 error = bus_dmamap_load(sc->tx_bd_chain_tag,
3235                         sc->tx_bd_chain_map[i],
3236                         sc->tx_bd_chain[i],
3237                         BCE_TX_CHAIN_PAGE_SZ,
3238                         bce_dma_map_addr,
3239                         &sc->tx_bd_chain_paddr[i],
3240                         BUS_DMA_NOWAIT);
3241
3242                 if (error) {
3243                         BCE_PRINTF("%s(%d): Could not map TX descriptor chain DMA memory!\n",
3244                                 __FILE__, __LINE__);
3245                         rc = ENOMEM;
3246                         goto bce_dma_alloc_exit;
3247                 }
3248
3249                 DBPRINT(sc, BCE_INFO, "%s(): tx_bd_chain_paddr[%d] = 0x%jX\n",
3250                         __FUNCTION__, i, (uintmax_t) sc->tx_bd_chain_paddr[i]);
3251         }
3252
3253         /* Check the required size before mapping to conserve resources. */
3254         if (bce_tso_enable) {
3255                 max_size     = BCE_TSO_MAX_SIZE;
3256                 max_segments = BCE_MAX_SEGMENTS;
3257                 max_seg_size = BCE_TSO_MAX_SEG_SIZE;
3258         } else {
3259                 max_size     = MCLBYTES * BCE_MAX_SEGMENTS;
3260                 max_segments = BCE_MAX_SEGMENTS;
3261                 max_seg_size = MCLBYTES;
3262         }
3263
3264         /* Create a DMA tag for TX mbufs. */
3265         if (bus_dma_tag_create(sc->parent_tag,
3266                         1,
3267                         BCE_DMA_BOUNDARY,
3268                         sc->max_bus_addr,
3269                         BUS_SPACE_MAXADDR,
3270                         NULL, NULL,
3271                         max_size,
3272                         max_segments,
3273                         max_seg_size,
3274                         0,
3275                         NULL, NULL,
3276                         &sc->tx_mbuf_tag)) {
3277                 BCE_PRINTF("%s(%d): Could not allocate TX mbuf DMA tag!\n",
3278                         __FILE__, __LINE__);
3279                 rc = ENOMEM;
3280                 goto bce_dma_alloc_exit;
3281         }
3282
3283         /* Create DMA maps for the TX mbufs clusters. */
3284         for (i = 0; i < TOTAL_TX_BD; i++) {
3285                 if (bus_dmamap_create(sc->tx_mbuf_tag, BUS_DMA_NOWAIT,
3286                         &sc->tx_mbuf_map[i])) {
3287                         BCE_PRINTF("%s(%d): Unable to create TX mbuf DMA map!\n",
3288                                 __FILE__, __LINE__);
3289                         rc = ENOMEM;
3290                         goto bce_dma_alloc_exit;
3291                 }
3292         }
3293
3294         /*
3295          * Create a DMA tag for the RX buffer descriptor chain,
3296          * allocate and clear the memory, and fetch the physical
3297          * address of the blocks.
3298          */
3299         if (bus_dma_tag_create(sc->parent_tag,
3300                         BCM_PAGE_SIZE,
3301                         BCE_DMA_BOUNDARY,
3302                         BUS_SPACE_MAXADDR,
3303                         sc->max_bus_addr,
3304                         NULL, NULL,
3305                         BCE_RX_CHAIN_PAGE_SZ,
3306                         1,
3307                         BCE_RX_CHAIN_PAGE_SZ,
3308                         0,
3309                         NULL, NULL,
3310                         &sc->rx_bd_chain_tag)) {
3311                 BCE_PRINTF("%s(%d): Could not allocate RX descriptor chain DMA tag!\n",
3312                         __FILE__, __LINE__);
3313                 rc = ENOMEM;
3314                 goto bce_dma_alloc_exit;
3315         }
3316
3317         for (i = 0; i < RX_PAGES; i++) {
3318
3319                 if (bus_dmamem_alloc(sc->rx_bd_chain_tag,
3320                         (void **)&sc->rx_bd_chain[i],
3321                         BUS_DMA_NOWAIT,
3322                         &sc->rx_bd_chain_map[i])) {
3323                         BCE_PRINTF("%s(%d): Could not allocate RX descriptor chain "
3324                                 "DMA memory!\n", __FILE__, __LINE__);
3325                         rc = ENOMEM;
3326                         goto bce_dma_alloc_exit;
3327                 }
3328
3329                 bzero((char *)sc->rx_bd_chain[i], BCE_RX_CHAIN_PAGE_SZ);
3330
3331                 error = bus_dmamap_load(sc->rx_bd_chain_tag,
3332                         sc->rx_bd_chain_map[i],
3333                         sc->rx_bd_chain[i],
3334                         BCE_RX_CHAIN_PAGE_SZ,
3335                         bce_dma_map_addr,
3336                         &sc->rx_bd_chain_paddr[i],
3337                         BUS_DMA_NOWAIT);
3338
3339                 if (error) {
3340                         BCE_PRINTF("%s(%d): Could not map RX descriptor chain DMA memory!\n",
3341                                 __FILE__, __LINE__);
3342                         rc = ENOMEM;
3343                         goto bce_dma_alloc_exit;
3344                 }
3345
3346                 DBPRINT(sc, BCE_INFO, "%s(): rx_bd_chain_paddr[%d] = 0x%jX\n",
3347                         __FUNCTION__, i, (uintmax_t) sc->rx_bd_chain_paddr[i]);
3348         }
3349
3350         /*
3351          * Create a DMA tag for RX mbufs.
3352          */
3353 #ifdef BCE_JUMBO_HDRSPLIT
3354         max_size = max_seg_size = ((sc->rx_bd_mbuf_alloc_size < MCLBYTES) ?
3355                 MCLBYTES : sc->rx_bd_mbuf_alloc_size);
3356 #else
3357         max_size = max_seg_size = MJUM9BYTES;
3358 #endif
3359         max_segments = 1;
3360
3361         DBPRINT(sc, BCE_INFO, "%s(): Creating rx_mbuf_tag (max size = 0x%jX "
3362                 "max segments = %d, max segment size = 0x%jX)\n", __FUNCTION__,
3363                 (uintmax_t) max_size, max_segments, (uintmax_t) max_seg_size);
3364
3365         if (bus_dma_tag_create(sc->parent_tag,
3366                         1,
3367                         BCE_DMA_BOUNDARY,
3368                         sc->max_bus_addr,
3369                         BUS_SPACE_MAXADDR,
3370                         NULL, NULL,
3371                         max_size,
3372                         max_segments,
3373                         max_seg_size,
3374                         0,
3375                         NULL, NULL,
3376                 &sc->rx_mbuf_tag)) {
3377                 BCE_PRINTF("%s(%d): Could not allocate RX mbuf DMA tag!\n",
3378                         __FILE__, __LINE__);
3379                 rc = ENOMEM;
3380                 goto bce_dma_alloc_exit;
3381         }
3382
3383         /* Create DMA maps for the RX mbuf clusters. */
3384         for (i = 0; i < TOTAL_RX_BD; i++) {
3385                 if (bus_dmamap_create(sc->rx_mbuf_tag, BUS_DMA_NOWAIT,
3386                                 &sc->rx_mbuf_map[i])) {
3387                         BCE_PRINTF("%s(%d): Unable to create RX mbuf DMA map!\n",
3388                                 __FILE__, __LINE__);
3389                         rc = ENOMEM;
3390                         goto bce_dma_alloc_exit;
3391                 }
3392         }
3393
3394 #ifdef BCE_JUMBO_HDRSPLIT
3395         /*
3396          * Create a DMA tag for the page buffer descriptor chain,
3397          * allocate and clear the memory, and fetch the physical
3398          * address of the blocks.
3399          */
3400         if (bus_dma_tag_create(sc->parent_tag,
3401                         BCM_PAGE_SIZE,
3402                         BCE_DMA_BOUNDARY,
3403                         BUS_SPACE_MAXADDR,
3404                         sc->max_bus_addr,
3405                         NULL, NULL,
3406                         BCE_PG_CHAIN_PAGE_SZ,
3407                         1,
3408                         BCE_PG_CHAIN_PAGE_SZ,
3409                         0,
3410                         NULL, NULL,
3411                         &sc->pg_bd_chain_tag)) {
3412                 BCE_PRINTF("%s(%d): Could not allocate page descriptor chain DMA tag!\n",
3413                         __FILE__, __LINE__);
3414                 rc = ENOMEM;
3415                 goto bce_dma_alloc_exit;
3416         }
3417
3418         for (i = 0; i < PG_PAGES; i++) {
3419
3420                 if (bus_dmamem_alloc(sc->pg_bd_chain_tag,
3421                         (void **)&sc->pg_bd_chain[i],
3422                         BUS_DMA_NOWAIT,
3423                         &sc->pg_bd_chain_map[i])) {
3424                         BCE_PRINTF("%s(%d): Could not allocate page descriptor chain "
3425                                 "DMA memory!\n", __FILE__, __LINE__);
3426                         rc = ENOMEM;
3427                         goto bce_dma_alloc_exit;
3428                 }
3429
3430                 bzero((char *)sc->pg_bd_chain[i], BCE_PG_CHAIN_PAGE_SZ);
3431
3432                 error = bus_dmamap_load(sc->pg_bd_chain_tag,
3433                         sc->pg_bd_chain_map[i],
3434                         sc->pg_bd_chain[i],
3435                         BCE_PG_CHAIN_PAGE_SZ,
3436                         bce_dma_map_addr,
3437                         &sc->pg_bd_chain_paddr[i],
3438                         BUS_DMA_NOWAIT);
3439
3440                 if (error) {
3441                         BCE_PRINTF("%s(%d): Could not map page descriptor chain DMA memory!\n",
3442                                 __FILE__, __LINE__);
3443                         rc = ENOMEM;
3444                         goto bce_dma_alloc_exit;
3445                 }
3446
3447                 DBPRINT(sc, BCE_INFO, "%s(): pg_bd_chain_paddr[%d] = 0x%jX\n",
3448                         __FUNCTION__, i, (uintmax_t) sc->pg_bd_chain_paddr[i]);
3449         }
3450
3451         /*
3452          * Create a DMA tag for page mbufs.
3453          */
3454         max_size = max_seg_size = ((sc->pg_bd_mbuf_alloc_size < MCLBYTES) ?
3455                 MCLBYTES : sc->pg_bd_mbuf_alloc_size);
3456
3457         if (bus_dma_tag_create(sc->parent_tag,
3458                         1,
3459                         BCE_DMA_BOUNDARY,
3460                         sc->max_bus_addr,
3461                         BUS_SPACE_MAXADDR,
3462                         NULL, NULL,
3463                         max_size,
3464                         1,
3465                         max_seg_size,
3466                         0,
3467                         NULL, NULL,
3468                 &sc->pg_mbuf_tag)) {
3469                 BCE_PRINTF("%s(%d): Could not allocate page mbuf DMA tag!\n",
3470                         __FILE__, __LINE__);
3471                 rc = ENOMEM;
3472                 goto bce_dma_alloc_exit;
3473         }
3474
3475         /* Create DMA maps for the page mbuf clusters. */
3476         for (i = 0; i < TOTAL_PG_BD; i++) {
3477                 if (bus_dmamap_create(sc->pg_mbuf_tag, BUS_DMA_NOWAIT,
3478                                 &sc->pg_mbuf_map[i])) {
3479                         BCE_PRINTF("%s(%d): Unable to create page mbuf DMA map!\n",
3480                                 __FILE__, __LINE__);
3481                         rc = ENOMEM;
3482                         goto bce_dma_alloc_exit;
3483                 }
3484         }
3485 #endif
3486
3487 bce_dma_alloc_exit:
3488         DBEXIT(BCE_VERBOSE_RESET | BCE_VERBOSE_CTX);
3489         return(rc);
3490 }
3491
3492
3493 /****************************************************************************/
3494 /* Release all resources used by the driver.                                */
3495 /*                                                                          */
3496 /* Releases all resources acquired by the driver including interrupts,      */
3497 /* interrupt handler, interfaces, mutexes, and DMA memory.                  */
3498 /*                                                                          */
3499 /* Returns:                                                                 */
3500 /*   Nothing.                                                               */
3501 /****************************************************************************/
3502 static void
3503 bce_release_resources(struct bce_softc *sc)
3504 {
3505         device_t dev;
3506
3507         DBENTER(BCE_VERBOSE_RESET);
3508
3509         dev = sc->bce_dev;
3510
3511         bce_dma_free(sc);
3512
3513         if (sc->bce_intrhand != NULL) {
3514                 DBPRINT(sc, BCE_INFO_RESET, "Removing interrupt handler.\n");
3515                 bus_teardown_intr(dev, sc->bce_res_irq, sc->bce_intrhand);
3516         }
3517
3518         if (sc->bce_res_irq != NULL) {
3519                 DBPRINT(sc, BCE_INFO_RESET, "Releasing IRQ.\n");
3520                 bus_release_resource(dev, SYS_RES_IRQ, sc->bce_irq_rid,
3521                         sc->bce_res_irq);
3522         }
3523
3524         if (sc->bce_flags & (BCE_USING_MSI_FLAG | BCE_USING_MSIX_FLAG)) {
3525                 DBPRINT(sc, BCE_INFO_RESET, "Releasing MSI/MSI-X vector.\n");
3526                 pci_release_msi(dev);
3527         }
3528
3529         if (sc->bce_res_mem != NULL) {
3530                 DBPRINT(sc, BCE_INFO_RESET, "Releasing PCI memory.\n");
3531                 bus_release_resource(dev, SYS_RES_MEMORY, PCIR_BAR(0), sc->bce_res_mem);
3532         }
3533
3534         if (sc->bce_ifp != NULL) {
3535                 DBPRINT(sc, BCE_INFO_RESET, "Releasing IF.\n");
3536                 if_free(sc->bce_ifp);
3537         }
3538
3539         if (mtx_initialized(&sc->bce_mtx))
3540                 BCE_LOCK_DESTROY(sc);
3541
3542         DBEXIT(BCE_VERBOSE_RESET);
3543 }
3544
3545
3546 /****************************************************************************/
3547 /* Firmware synchronization.                                                */
3548 /*                                                                          */
3549 /* Before performing certain events such as a chip reset, synchronize with  */
3550 /* the firmware first.                                                      */
3551 /*                                                                          */
3552 /* Returns:                                                                 */
3553 /*   0 for success, positive value for failure.                             */
3554 /****************************************************************************/
3555 static int
3556 bce_fw_sync(struct bce_softc *sc, u32 msg_data)
3557 {
3558         int i, rc = 0;
3559         u32 val;
3560
3561         DBENTER(BCE_VERBOSE_RESET);
3562
3563         /* Don't waste any time if we've timed out before. */
3564         if (sc->bce_fw_timed_out) {
3565                 rc = EBUSY;
3566                 goto bce_fw_sync_exit;
3567         }
3568
3569         /* Increment the message sequence number. */
3570         sc->bce_fw_wr_seq++;
3571         msg_data |= sc->bce_fw_wr_seq;
3572
3573         DBPRINT(sc, BCE_VERBOSE_FIRMWARE, "bce_fw_sync(): msg_data = 0x%08X\n",
3574                 msg_data);
3575
3576         /* Send the message to the bootcode driver mailbox. */
3577         bce_shmem_wr(sc, BCE_DRV_MB, msg_data);
3578
3579         /* Wait for the bootcode to acknowledge the message. */
3580         for (i = 0; i < FW_ACK_TIME_OUT_MS; i++) {
3581                 /* Check for a response in the bootcode firmware mailbox. */
3582                 val = bce_shmem_rd(sc, BCE_FW_MB);
3583                 if ((val & BCE_FW_MSG_ACK) == (msg_data & BCE_DRV_MSG_SEQ))
3584                         break;
3585                 DELAY(1000);
3586         }
3587
3588         /* If we've timed out, tell the bootcode that we've stopped waiting. */
3589         if (((val & BCE_FW_MSG_ACK) != (msg_data & BCE_DRV_MSG_SEQ)) &&
3590                 ((msg_data & BCE_DRV_MSG_DATA) != BCE_DRV_MSG_DATA_WAIT0)) {
3591
3592                 BCE_PRINTF("%s(%d): Firmware synchronization timeout! "
3593                         "msg_data = 0x%08X\n",
3594                         __FILE__, __LINE__, msg_data);
3595
3596                 msg_data &= ~BCE_DRV_MSG_CODE;
3597                 msg_data |= BCE_DRV_MSG_CODE_FW_TIMEOUT;
3598
3599                 bce_shmem_wr(sc, BCE_DRV_MB, msg_data);
3600
3601                 sc->bce_fw_timed_out = 1;
3602                 rc = EBUSY;
3603         }
3604
3605 bce_fw_sync_exit:
3606         DBEXIT(BCE_VERBOSE_RESET);
3607         return (rc);
3608 }
3609
3610
3611 /****************************************************************************/
3612 /* Load Receive Virtual 2 Physical (RV2P) processor firmware.               */
3613 /*                                                                          */
3614 /* Returns:                                                                 */
3615 /*   Nothing.                                                               */
3616 /****************************************************************************/
3617 static void
3618 bce_load_rv2p_fw(struct bce_softc *sc, u32 *rv2p_code,
3619         u32 rv2p_code_len, u32 rv2p_proc)
3620 {
3621         int i;
3622         u32 val;
3623
3624         DBENTER(BCE_VERBOSE_RESET);
3625
3626         /* Set the page size used by RV2P. */
3627         if (rv2p_proc == RV2P_PROC2) {
3628                 BCE_RV2P_PROC2_CHG_MAX_BD_PAGE(USABLE_RX_BD_PER_PAGE);
3629         }
3630
3631         for (i = 0; i < rv2p_code_len; i += 8) {
3632                 REG_WR(sc, BCE_RV2P_INSTR_HIGH, *rv2p_code);
3633                 rv2p_code++;
3634                 REG_WR(sc, BCE_RV2P_INSTR_LOW, *rv2p_code);
3635                 rv2p_code++;
3636
3637                 if (rv2p_proc == RV2P_PROC1) {
3638                         val = (i / 8) | BCE_RV2P_PROC1_ADDR_CMD_RDWR;
3639                         REG_WR(sc, BCE_RV2P_PROC1_ADDR_CMD, val);
3640                 }
3641                 else {
3642                         val = (i / 8) | BCE_RV2P_PROC2_ADDR_CMD_RDWR;
3643                         REG_WR(sc, BCE_RV2P_PROC2_ADDR_CMD, val);
3644                 }
3645         }
3646
3647         /* Reset the processor, un-stall is done later. */
3648         if (rv2p_proc == RV2P_PROC1) {
3649                 REG_WR(sc, BCE_RV2P_COMMAND, BCE_RV2P_COMMAND_PROC1_RESET);
3650         }
3651         else {
3652                 REG_WR(sc, BCE_RV2P_COMMAND, BCE_RV2P_COMMAND_PROC2_RESET);
3653         }
3654
3655         DBEXIT(BCE_VERBOSE_RESET);
3656 }
3657
3658
3659 /****************************************************************************/
3660 /* Load RISC processor firmware.                                            */
3661 /*                                                                          */
3662 /* Loads firmware from the file if_bcefw.h into the scratchpad memory       */
3663 /* associated with a particular processor.                                  */
3664 /*                                                                          */
3665 /* Returns:                                                                 */
3666 /*   Nothing.                                                               */
3667 /****************************************************************************/
3668 static void
3669 bce_load_cpu_fw(struct bce_softc *sc, struct cpu_reg *cpu_reg,
3670         struct fw_info *fw)
3671 {
3672         u32 offset;
3673
3674         DBENTER(BCE_VERBOSE_RESET);
3675
3676     bce_halt_cpu(sc, cpu_reg);
3677
3678         /* Load the Text area. */
3679         offset = cpu_reg->spad_base + (fw->text_addr - cpu_reg->mips_view_base);
3680         if (fw->text) {
3681                 int j;
3682
3683                 for (j = 0; j < (fw->text_len / 4); j++, offset += 4) {
3684                         REG_WR_IND(sc, offset, fw->text[j]);
3685                 }
3686         }
3687
3688         /* Load the Data area. */
3689         offset = cpu_reg->spad_base + (fw->data_addr - cpu_reg->mips_view_base);
3690         if (fw->data) {
3691                 int j;
3692
3693                 for (j = 0; j < (fw->data_len / 4); j++, offset += 4) {
3694                         REG_WR_IND(sc, offset, fw->data[j]);
3695                 }
3696         }
3697
3698         /* Load the SBSS area. */
3699         offset = cpu_reg->spad_base + (fw->sbss_addr - cpu_reg->mips_view_base);
3700         if (fw->sbss) {
3701                 int j;
3702
3703                 for (j = 0; j < (fw->sbss_len / 4); j++, offset += 4) {
3704                         REG_WR_IND(sc, offset, fw->sbss[j]);
3705                 }
3706         }
3707
3708         /* Load the BSS area. */
3709         offset = cpu_reg->spad_base + (fw->bss_addr - cpu_reg->mips_view_base);
3710         if (fw->bss) {
3711                 int j;
3712
3713                 for (j = 0; j < (fw->bss_len/4); j++, offset += 4) {
3714                         REG_WR_IND(sc, offset, fw->bss[j]);
3715                 }
3716         }
3717
3718         /* Load the Read-Only area. */
3719         offset = cpu_reg->spad_base +
3720                 (fw->rodata_addr - cpu_reg->mips_view_base);
3721         if (fw->rodata) {
3722                 int j;
3723
3724                 for (j = 0; j < (fw->rodata_len / 4); j++, offset += 4) {
3725                         REG_WR_IND(sc, offset, fw->rodata[j]);
3726                 }
3727         }
3728
3729     /* Clear the pre-fetch instruction and set the FW start address. */
3730     REG_WR_IND(sc, cpu_reg->inst, 0);
3731     REG_WR_IND(sc, cpu_reg->pc, fw->start_addr);
3732
3733         DBEXIT(BCE_VERBOSE_RESET);
3734 }
3735
3736
3737 /****************************************************************************/
3738 /* Starts the RISC processor.                                               */
3739 /*                                                                          */
3740 /* Assumes the CPU starting address has already been set.                   */
3741 /*                                                                          */
3742 /* Returns:                                                                 */
3743 /*   Nothing.                                                               */
3744 /****************************************************************************/
3745 static void
3746 bce_start_cpu(struct bce_softc *sc, struct cpu_reg *cpu_reg)
3747 {
3748         u32 val;
3749
3750         DBENTER(BCE_VERBOSE_RESET);
3751
3752         /* Start the CPU. */
3753         val = REG_RD_IND(sc, cpu_reg->mode);
3754         val &= ~cpu_reg->mode_value_halt;
3755         REG_WR_IND(sc, cpu_reg->state, cpu_reg->state_value_clear);
3756         REG_WR_IND(sc, cpu_reg->mode, val);
3757
3758         DBEXIT(BCE_VERBOSE_RESET);
3759 }
3760
3761
3762 /****************************************************************************/
3763 /* Halts the RISC processor.                                                */
3764 /*                                                                          */
3765 /* Returns:                                                                 */
3766 /*   Nothing.                                                               */
3767 /****************************************************************************/
3768 static void
3769 bce_halt_cpu(struct bce_softc *sc, struct cpu_reg *cpu_reg)
3770 {
3771         u32 val;
3772
3773         DBENTER(BCE_VERBOSE_RESET);
3774
3775     /* Halt the CPU. */
3776     val = REG_RD_IND(sc, cpu_reg->mode);
3777     val |= cpu_reg->mode_value_halt;
3778     REG_WR_IND(sc, cpu_reg->mode, val);
3779     REG_WR_IND(sc, cpu_reg->state, cpu_reg->state_value_clear);
3780
3781         DBEXIT(BCE_VERBOSE_RESET);
3782 }
3783
3784
3785 /****************************************************************************/
3786 /* Initialize the RX CPU.                                                   */
3787 /*                                                                          */
3788 /* Returns:                                                                 */
3789 /*   Nothing.                                                               */
3790 /****************************************************************************/
3791 static void
3792 bce_start_rxp_cpu(struct bce_softc *sc)
3793 {
3794         struct cpu_reg cpu_reg;
3795
3796         DBENTER(BCE_VERBOSE_RESET);
3797
3798         cpu_reg.mode = BCE_RXP_CPU_MODE;
3799         cpu_reg.mode_value_halt = BCE_RXP_CPU_MODE_SOFT_HALT;
3800         cpu_reg.mode_value_sstep = BCE_RXP_CPU_MODE_STEP_ENA;
3801         cpu_reg.state = BCE_RXP_CPU_STATE;
3802         cpu_reg.state_value_clear = 0xffffff;
3803         cpu_reg.gpr0 = BCE_RXP_CPU_REG_FILE;
3804         cpu_reg.evmask = BCE_RXP_CPU_EVENT_MASK;
3805         cpu_reg.pc = BCE_RXP_CPU_PROGRAM_COUNTER;
3806         cpu_reg.inst = BCE_RXP_CPU_INSTRUCTION;
3807         cpu_reg.bp = BCE_RXP_CPU_HW_BREAKPOINT;
3808         cpu_reg.spad_base = BCE_RXP_SCRATCH;
3809         cpu_reg.mips_view_base = 0x8000000;
3810
3811         DBPRINT(sc, BCE_INFO_RESET, "Starting RX firmware.\n");
3812         bce_start_cpu(sc, &cpu_reg);
3813
3814         DBEXIT(BCE_VERBOSE_RESET);
3815 }
3816
3817
3818 /****************************************************************************/
3819 /* Initialize the RX CPU.                                                   */
3820 /*                                                                          */
3821 /* Returns:                                                                 */
3822 /*   Nothing.                                                               */
3823 /****************************************************************************/
3824 static void
3825 bce_init_rxp_cpu(struct bce_softc *sc)
3826 {
3827         struct cpu_reg cpu_reg;
3828         struct fw_info fw;
3829
3830         DBENTER(BCE_VERBOSE_RESET);
3831
3832         cpu_reg.mode = BCE_RXP_CPU_MODE;
3833         cpu_reg.mode_value_halt = BCE_RXP_CPU_MODE_SOFT_HALT;
3834         cpu_reg.mode_value_sstep = BCE_RXP_CPU_MODE_STEP_ENA;
3835         cpu_reg.state = BCE_RXP_CPU_STATE;
3836         cpu_reg.state_value_clear = 0xffffff;
3837         cpu_reg.gpr0 = BCE_RXP_CPU_REG_FILE;
3838         cpu_reg.evmask = BCE_RXP_CPU_EVENT_MASK;
3839         cpu_reg.pc = BCE_RXP_CPU_PROGRAM_COUNTER;
3840         cpu_reg.inst = BCE_RXP_CPU_INSTRUCTION;
3841         cpu_reg.bp = BCE_RXP_CPU_HW_BREAKPOINT;
3842         cpu_reg.spad_base = BCE_RXP_SCRATCH;
3843         cpu_reg.mips_view_base = 0x8000000;
3844
3845         if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
3846                 (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
3847                 fw.ver_major = bce_RXP_b09FwReleaseMajor;
3848                 fw.ver_minor = bce_RXP_b09FwReleaseMinor;
3849                 fw.ver_fix = bce_RXP_b09FwReleaseFix;
3850                 fw.start_addr = bce_RXP_b09FwStartAddr;
3851
3852                 fw.text_addr = bce_RXP_b09FwTextAddr;
3853                 fw.text_len = bce_RXP_b09FwTextLen;
3854                 fw.text_index = 0;
3855                 fw.text = bce_RXP_b09FwText;
3856
3857                 fw.data_addr = bce_RXP_b09FwDataAddr;
3858                 fw.data_len = bce_RXP_b09FwDataLen;
3859                 fw.data_index = 0;
3860                 fw.data = bce_RXP_b09FwData;
3861
3862                 fw.sbss_addr = bce_RXP_b09FwSbssAddr;
3863                 fw.sbss_len = bce_RXP_b09FwSbssLen;
3864                 fw.sbss_index = 0;
3865                 fw.sbss = bce_RXP_b09FwSbss;
3866
3867                 fw.bss_addr = bce_RXP_b09FwBssAddr;
3868                 fw.bss_len = bce_RXP_b09FwBssLen;
3869                 fw.bss_index = 0;
3870                 fw.bss = bce_RXP_b09FwBss;
3871
3872                 fw.rodata_addr = bce_RXP_b09FwRodataAddr;
3873                 fw.rodata_len = bce_RXP_b09FwRodataLen;
3874                 fw.rodata_index = 0;
3875                 fw.rodata = bce_RXP_b09FwRodata;
3876         } else {
3877                 fw.ver_major = bce_RXP_b06FwReleaseMajor;
3878                 fw.ver_minor = bce_RXP_b06FwReleaseMinor;
3879                 fw.ver_fix = bce_RXP_b06FwReleaseFix;
3880                 fw.start_addr = bce_RXP_b06FwStartAddr;
3881
3882                 fw.text_addr = bce_RXP_b06FwTextAddr;
3883                 fw.text_len = bce_RXP_b06FwTextLen;
3884                 fw.text_index = 0;
3885                 fw.text = bce_RXP_b06FwText;
3886
3887                 fw.data_addr = bce_RXP_b06FwDataAddr;
3888                 fw.data_len = bce_RXP_b06FwDataLen;
3889                 fw.data_index = 0;
3890                 fw.data = bce_RXP_b06FwData;
3891
3892                 fw.sbss_addr = bce_RXP_b06FwSbssAddr;
3893                 fw.sbss_len = bce_RXP_b06FwSbssLen;
3894                 fw.sbss_index = 0;
3895                 fw.sbss = bce_RXP_b06FwSbss;
3896
3897                 fw.bss_addr = bce_RXP_b06FwBssAddr;
3898                 fw.bss_len = bce_RXP_b06FwBssLen;
3899                 fw.bss_index = 0;
3900                 fw.bss = bce_RXP_b06FwBss;
3901
3902                 fw.rodata_addr = bce_RXP_b06FwRodataAddr;
3903                 fw.rodata_len = bce_RXP_b06FwRodataLen;
3904                 fw.rodata_index = 0;
3905                 fw.rodata = bce_RXP_b06FwRodata;
3906         }
3907
3908         DBPRINT(sc, BCE_INFO_RESET, "Loading RX firmware.\n");
3909         bce_load_cpu_fw(sc, &cpu_reg, &fw);
3910
3911     /* Delay RXP start until initialization is complete. */
3912
3913         DBEXIT(BCE_VERBOSE_RESET);
3914 }
3915
3916
3917 /****************************************************************************/
3918 /* Initialize the TX CPU.                                                   */
3919 /*                                                                          */
3920 /* Returns:                                                                 */
3921 /*   Nothing.                                                               */
3922 /****************************************************************************/
3923 static void
3924 bce_init_txp_cpu(struct bce_softc *sc)
3925 {
3926         struct cpu_reg cpu_reg;
3927         struct fw_info fw;
3928
3929         DBENTER(BCE_VERBOSE_RESET);
3930
3931         cpu_reg.mode = BCE_TXP_CPU_MODE;
3932         cpu_reg.mode_value_halt = BCE_TXP_CPU_MODE_SOFT_HALT;
3933         cpu_reg.mode_value_sstep = BCE_TXP_CPU_MODE_STEP_ENA;
3934         cpu_reg.state = BCE_TXP_CPU_STATE;
3935         cpu_reg.state_value_clear = 0xffffff;
3936         cpu_reg.gpr0 = BCE_TXP_CPU_REG_FILE;
3937         cpu_reg.evmask = BCE_TXP_CPU_EVENT_MASK;
3938         cpu_reg.pc = BCE_TXP_CPU_PROGRAM_COUNTER;
3939         cpu_reg.inst = BCE_TXP_CPU_INSTRUCTION;
3940         cpu_reg.bp = BCE_TXP_CPU_HW_BREAKPOINT;
3941         cpu_reg.spad_base = BCE_TXP_SCRATCH;
3942         cpu_reg.mips_view_base = 0x8000000;
3943
3944         if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
3945                 (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
3946                 fw.ver_major = bce_TXP_b09FwReleaseMajor;
3947                 fw.ver_minor = bce_TXP_b09FwReleaseMinor;
3948                 fw.ver_fix = bce_TXP_b09FwReleaseFix;
3949                 fw.start_addr = bce_TXP_b09FwStartAddr;
3950
3951                 fw.text_addr = bce_TXP_b09FwTextAddr;
3952                 fw.text_len = bce_TXP_b09FwTextLen;
3953                 fw.text_index = 0;
3954                 fw.text = bce_TXP_b09FwText;
3955
3956                 fw.data_addr = bce_TXP_b09FwDataAddr;
3957                 fw.data_len = bce_TXP_b09FwDataLen;
3958                 fw.data_index = 0;
3959                 fw.data = bce_TXP_b09FwData;
3960
3961                 fw.sbss_addr = bce_TXP_b09FwSbssAddr;
3962                 fw.sbss_len = bce_TXP_b09FwSbssLen;
3963                 fw.sbss_index = 0;
3964                 fw.sbss = bce_TXP_b09FwSbss;
3965
3966                 fw.bss_addr = bce_TXP_b09FwBssAddr;
3967                 fw.bss_len = bce_TXP_b09FwBssLen;
3968                 fw.bss_index = 0;
3969                 fw.bss = bce_TXP_b09FwBss;
3970
3971                 fw.rodata_addr = bce_TXP_b09FwRodataAddr;
3972                 fw.rodata_len = bce_TXP_b09FwRodataLen;
3973                 fw.rodata_index = 0;
3974                 fw.rodata = bce_TXP_b09FwRodata;
3975         } else {
3976                 fw.ver_major = bce_TXP_b06FwReleaseMajor;
3977                 fw.ver_minor = bce_TXP_b06FwReleaseMinor;
3978                 fw.ver_fix = bce_TXP_b06FwReleaseFix;
3979                 fw.start_addr = bce_TXP_b06FwStartAddr;
3980
3981                 fw.text_addr = bce_TXP_b06FwTextAddr;
3982                 fw.text_len = bce_TXP_b06FwTextLen;
3983                 fw.text_index = 0;
3984                 fw.text = bce_TXP_b06FwText;
3985
3986                 fw.data_addr = bce_TXP_b06FwDataAddr;
3987                 fw.data_len = bce_TXP_b06FwDataLen;
3988                 fw.data_index = 0;
3989                 fw.data = bce_TXP_b06FwData;
3990
3991                 fw.sbss_addr = bce_TXP_b06FwSbssAddr;
3992                 fw.sbss_len = bce_TXP_b06FwSbssLen;
3993                 fw.sbss_index = 0;
3994                 fw.sbss = bce_TXP_b06FwSbss;
3995
3996                 fw.bss_addr = bce_TXP_b06FwBssAddr;
3997                 fw.bss_len = bce_TXP_b06FwBssLen;
3998                 fw.bss_index = 0;
3999                 fw.bss = bce_TXP_b06FwBss;
4000
4001                 fw.rodata_addr = bce_TXP_b06FwRodataAddr;
4002                 fw.rodata_len = bce_TXP_b06FwRodataLen;
4003                 fw.rodata_index = 0;
4004                 fw.rodata = bce_TXP_b06FwRodata;
4005         }
4006
4007         DBPRINT(sc, BCE_INFO_RESET, "Loading TX firmware.\n");
4008         bce_load_cpu_fw(sc, &cpu_reg, &fw);
4009     bce_start_cpu(sc, &cpu_reg);
4010
4011         DBEXIT(BCE_VERBOSE_RESET);
4012 }
4013
4014
4015 /****************************************************************************/
4016 /* Initialize the TPAT CPU.                                                 */
4017 /*                                                                          */
4018 /* Returns:                                                                 */
4019 /*   Nothing.                                                               */
4020 /****************************************************************************/
4021 static void
4022 bce_init_tpat_cpu(struct bce_softc *sc)
4023 {
4024         struct cpu_reg cpu_reg;
4025         struct fw_info fw;
4026
4027         DBENTER(BCE_VERBOSE_RESET);
4028
4029         cpu_reg.mode = BCE_TPAT_CPU_MODE;
4030         cpu_reg.mode_value_halt = BCE_TPAT_CPU_MODE_SOFT_HALT;
4031         cpu_reg.mode_value_sstep = BCE_TPAT_CPU_MODE_STEP_ENA;
4032         cpu_reg.state = BCE_TPAT_CPU_STATE;
4033         cpu_reg.state_value_clear = 0xffffff;
4034         cpu_reg.gpr0 = BCE_TPAT_CPU_REG_FILE;
4035         cpu_reg.evmask = BCE_TPAT_CPU_EVENT_MASK;
4036         cpu_reg.pc = BCE_TPAT_CPU_PROGRAM_COUNTER;
4037         cpu_reg.inst = BCE_TPAT_CPU_INSTRUCTION;
4038         cpu_reg.bp = BCE_TPAT_CPU_HW_BREAKPOINT;
4039         cpu_reg.spad_base = BCE_TPAT_SCRATCH;
4040         cpu_reg.mips_view_base = 0x8000000;
4041
4042         if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
4043                 (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
4044                 fw.ver_major = bce_TPAT_b09FwReleaseMajor;
4045                 fw.ver_minor = bce_TPAT_b09FwReleaseMinor;
4046                 fw.ver_fix = bce_TPAT_b09FwReleaseFix;
4047                 fw.start_addr = bce_TPAT_b09FwStartAddr;
4048
4049                 fw.text_addr = bce_TPAT_b09FwTextAddr;
4050                 fw.text_len = bce_TPAT_b09FwTextLen;
4051                 fw.text_index = 0;
4052                 fw.text = bce_TPAT_b09FwText;
4053
4054                 fw.data_addr = bce_TPAT_b09FwDataAddr;
4055                 fw.data_len = bce_TPAT_b09FwDataLen;
4056                 fw.data_index = 0;
4057                 fw.data = bce_TPAT_b09FwData;
4058
4059                 fw.sbss_addr = bce_TPAT_b09FwSbssAddr;
4060                 fw.sbss_len = bce_TPAT_b09FwSbssLen;
4061                 fw.sbss_index = 0;
4062                 fw.sbss = bce_TPAT_b09FwSbss;
4063
4064                 fw.bss_addr = bce_TPAT_b09FwBssAddr;
4065                 fw.bss_len = bce_TPAT_b09FwBssLen;
4066                 fw.bss_index = 0;
4067                 fw.bss = bce_TPAT_b09FwBss;
4068
4069                 fw.rodata_addr = bce_TPAT_b09FwRodataAddr;
4070                 fw.rodata_len = bce_TPAT_b09FwRodataLen;
4071                 fw.rodata_index = 0;
4072                 fw.rodata = bce_TPAT_b09FwRodata;
4073         } else {
4074                 fw.ver_major = bce_TPAT_b06FwReleaseMajor;
4075                 fw.ver_minor = bce_TPAT_b06FwReleaseMinor;
4076                 fw.ver_fix = bce_TPAT_b06FwReleaseFix;
4077                 fw.start_addr = bce_TPAT_b06FwStartAddr;
4078
4079                 fw.text_addr = bce_TPAT_b06FwTextAddr;
4080                 fw.text_len = bce_TPAT_b06FwTextLen;
4081                 fw.text_index = 0;
4082                 fw.text = bce_TPAT_b06FwText;
4083
4084                 fw.data_addr = bce_TPAT_b06FwDataAddr;
4085                 fw.data_len = bce_TPAT_b06FwDataLen;
4086                 fw.data_index = 0;
4087                 fw.data = bce_TPAT_b06FwData;
4088
4089                 fw.sbss_addr = bce_TPAT_b06FwSbssAddr;
4090                 fw.sbss_len = bce_TPAT_b06FwSbssLen;
4091                 fw.sbss_index = 0;
4092                 fw.sbss = bce_TPAT_b06FwSbss;
4093
4094                 fw.bss_addr = bce_TPAT_b06FwBssAddr;
4095                 fw.bss_len = bce_TPAT_b06FwBssLen;
4096                 fw.bss_index = 0;
4097                 fw.bss = bce_TPAT_b06FwBss;
4098
4099                 fw.rodata_addr = bce_TPAT_b06FwRodataAddr;
4100                 fw.rodata_len = bce_TPAT_b06FwRodataLen;
4101                 fw.rodata_index = 0;
4102                 fw.rodata = bce_TPAT_b06FwRodata;
4103         }
4104
4105         DBPRINT(sc, BCE_INFO_RESET, "Loading TPAT firmware.\n");
4106         bce_load_cpu_fw(sc, &cpu_reg, &fw);
4107     bce_start_cpu(sc, &cpu_reg);
4108
4109         DBEXIT(BCE_VERBOSE_RESET);
4110 }
4111
4112
4113 /****************************************************************************/
4114 /* Initialize the CP CPU.                                                   */
4115 /*                                                                          */
4116 /* Returns:                                                                 */
4117 /*   Nothing.                                                               */
4118 /****************************************************************************/
4119 static void
4120 bce_init_cp_cpu(struct bce_softc *sc)
4121 {
4122         struct cpu_reg cpu_reg;
4123         struct fw_info fw;
4124
4125         DBENTER(BCE_VERBOSE_RESET);
4126
4127         cpu_reg.mode = BCE_CP_CPU_MODE;
4128         cpu_reg.mode_value_halt = BCE_CP_CPU_MODE_SOFT_HALT;
4129         cpu_reg.mode_value_sstep = BCE_CP_CPU_MODE_STEP_ENA;
4130         cpu_reg.state = BCE_CP_CPU_STATE;
4131         cpu_reg.state_value_clear = 0xffffff;
4132         cpu_reg.gpr0 = BCE_CP_CPU_REG_FILE;
4133         cpu_reg.evmask = BCE_CP_CPU_EVENT_MASK;
4134         cpu_reg.pc = BCE_CP_CPU_PROGRAM_COUNTER;
4135         cpu_reg.inst = BCE_CP_CPU_INSTRUCTION;
4136         cpu_reg.bp = BCE_CP_CPU_HW_BREAKPOINT;
4137         cpu_reg.spad_base = BCE_CP_SCRATCH;
4138         cpu_reg.mips_view_base = 0x8000000;
4139
4140         if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
4141                 (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
4142                 fw.ver_major = bce_CP_b09FwReleaseMajor;
4143                 fw.ver_minor = bce_CP_b09FwReleaseMinor;
4144                 fw.ver_fix = bce_CP_b09FwReleaseFix;
4145                 fw.start_addr = bce_CP_b09FwStartAddr;
4146
4147                 fw.text_addr = bce_CP_b09FwTextAddr;
4148                 fw.text_len = bce_CP_b09FwTextLen;
4149                 fw.text_index = 0;
4150                 fw.text = bce_CP_b09FwText;
4151
4152                 fw.data_addr = bce_CP_b09FwDataAddr;
4153                 fw.data_len = bce_CP_b09FwDataLen;
4154                 fw.data_index = 0;
4155                 fw.data = bce_CP_b09FwData;
4156
4157                 fw.sbss_addr = bce_CP_b09FwSbssAddr;
4158                 fw.sbss_len = bce_CP_b09FwSbssLen;
4159                 fw.sbss_index = 0;
4160                 fw.sbss = bce_CP_b09FwSbss;
4161
4162                 fw.bss_addr = bce_CP_b09FwBssAddr;
4163                 fw.bss_len = bce_CP_b09FwBssLen;
4164                 fw.bss_index = 0;
4165                 fw.bss = bce_CP_b09FwBss;
4166
4167                 fw.rodata_addr = bce_CP_b09FwRodataAddr;
4168                 fw.rodata_len = bce_CP_b09FwRodataLen;
4169                 fw.rodata_index = 0;
4170                 fw.rodata = bce_CP_b09FwRodata;
4171         } else {
4172                 fw.ver_major = bce_CP_b06FwReleaseMajor;
4173                 fw.ver_minor = bce_CP_b06FwReleaseMinor;
4174                 fw.ver_fix = bce_CP_b06FwReleaseFix;
4175                 fw.start_addr = bce_CP_b06FwStartAddr;
4176
4177                 fw.text_addr = bce_CP_b06FwTextAddr;
4178                 fw.text_len = bce_CP_b06FwTextLen;
4179                 fw.text_index = 0;
4180                 fw.text = bce_CP_b06FwText;
4181
4182                 fw.data_addr = bce_CP_b06FwDataAddr;
4183                 fw.data_len = bce_CP_b06FwDataLen;
4184                 fw.data_index = 0;
4185                 fw.data = bce_CP_b06FwData;
4186
4187                 fw.sbss_addr = bce_CP_b06FwSbssAddr;
4188                 fw.sbss_len = bce_CP_b06FwSbssLen;
4189                 fw.sbss_index = 0;
4190                 fw.sbss = bce_CP_b06FwSbss;
4191
4192                 fw.bss_addr = bce_CP_b06FwBssAddr;
4193                 fw.bss_len = bce_CP_b06FwBssLen;
4194                 fw.bss_index = 0;
4195                 fw.bss = bce_CP_b06FwBss;
4196
4197                 fw.rodata_addr = bce_CP_b06FwRodataAddr;
4198                 fw.rodata_len = bce_CP_b06FwRodataLen;
4199                 fw.rodata_index = 0;
4200                 fw.rodata = bce_CP_b06FwRodata;
4201         }
4202
4203         DBPRINT(sc, BCE_INFO_RESET, "Loading CP firmware.\n");
4204         bce_load_cpu_fw(sc, &cpu_reg, &fw);
4205     bce_start_cpu(sc, &cpu_reg);
4206
4207         DBEXIT(BCE_VERBOSE_RESET);
4208 }
4209
4210
4211 /****************************************************************************/
4212 /* Initialize the COM CPU.                                                 */
4213 /*                                                                          */
4214 /* Returns:                                                                 */
4215 /*   Nothing.                                                               */
4216 /****************************************************************************/
4217 static void
4218 bce_init_com_cpu(struct bce_softc *sc)
4219 {
4220         struct cpu_reg cpu_reg;
4221         struct fw_info fw;
4222
4223         DBENTER(BCE_VERBOSE_RESET);
4224
4225         cpu_reg.mode = BCE_COM_CPU_MODE;
4226         cpu_reg.mode_value_halt = BCE_COM_CPU_MODE_SOFT_HALT;
4227         cpu_reg.mode_value_sstep = BCE_COM_CPU_MODE_STEP_ENA;
4228         cpu_reg.state = BCE_COM_CPU_STATE;
4229         cpu_reg.state_value_clear = 0xffffff;
4230         cpu_reg.gpr0 = BCE_COM_CPU_REG_FILE;
4231         cpu_reg.evmask = BCE_COM_CPU_EVENT_MASK;
4232         cpu_reg.pc = BCE_COM_CPU_PROGRAM_COUNTER;
4233         cpu_reg.inst = BCE_COM_CPU_INSTRUCTION;
4234         cpu_reg.bp = BCE_COM_CPU_HW_BREAKPOINT;
4235         cpu_reg.spad_base = BCE_COM_SCRATCH;
4236         cpu_reg.mips_view_base = 0x8000000;
4237
4238         if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
4239                 (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
4240                 fw.ver_major = bce_COM_b09FwReleaseMajor;
4241                 fw.ver_minor = bce_COM_b09FwReleaseMinor;
4242                 fw.ver_fix = bce_COM_b09FwReleaseFix;
4243                 fw.start_addr = bce_COM_b09FwStartAddr;
4244
4245                 fw.text_addr = bce_COM_b09FwTextAddr;
4246                 fw.text_len = bce_COM_b09FwTextLen;
4247                 fw.text_index = 0;
4248                 fw.text = bce_COM_b09FwText;
4249
4250                 fw.data_addr = bce_COM_b09FwDataAddr;
4251                 fw.data_len = bce_COM_b09FwDataLen;
4252                 fw.data_index = 0;
4253                 fw.data = bce_COM_b09FwData;
4254
4255                 fw.sbss_addr = bce_COM_b09FwSbssAddr;
4256                 fw.sbss_len = bce_COM_b09FwSbssLen;
4257                 fw.sbss_index = 0;
4258                 fw.sbss = bce_COM_b09FwSbss;
4259
4260                 fw.bss_addr = bce_COM_b09FwBssAddr;
4261                 fw.bss_len = bce_COM_b09FwBssLen;
4262                 fw.bss_index = 0;
4263                 fw.bss = bce_COM_b09FwBss;
4264
4265                 fw.rodata_addr = bce_COM_b09FwRodataAddr;
4266                 fw.rodata_len = bce_COM_b09FwRodataLen;
4267                 fw.rodata_index = 0;
4268                 fw.rodata = bce_COM_b09FwRodata;
4269         } else {
4270                 fw.ver_major = bce_COM_b06FwReleaseMajor;
4271                 fw.ver_minor = bce_COM_b06FwReleaseMinor;
4272                 fw.ver_fix = bce_COM_b06FwReleaseFix;
4273                 fw.start_addr = bce_COM_b06FwStartAddr;
4274
4275                 fw.text_addr = bce_COM_b06FwTextAddr;
4276                 fw.text_len = bce_COM_b06FwTextLen;
4277                 fw.text_index = 0;
4278                 fw.text = bce_COM_b06FwText;
4279
4280                 fw.data_addr = bce_COM_b06FwDataAddr;
4281                 fw.data_len = bce_COM_b06FwDataLen;
4282                 fw.data_index = 0;
4283                 fw.data = bce_COM_b06FwData;
4284
4285                 fw.sbss_addr = bce_COM_b06FwSbssAddr;
4286                 fw.sbss_len = bce_COM_b06FwSbssLen;
4287                 fw.sbss_index = 0;
4288                 fw.sbss = bce_COM_b06FwSbss;
4289
4290                 fw.bss_addr = bce_COM_b06FwBssAddr;
4291                 fw.bss_len = bce_COM_b06FwBssLen;
4292                 fw.bss_index = 0;
4293                 fw.bss = bce_COM_b06FwBss;
4294
4295                 fw.rodata_addr = bce_COM_b06FwRodataAddr;
4296                 fw.rodata_len = bce_COM_b06FwRodataLen;
4297                 fw.rodata_index = 0;
4298                 fw.rodata = bce_COM_b06FwRodata;
4299         }
4300
4301         DBPRINT(sc, BCE_INFO_RESET, "Loading COM firmware.\n");
4302         bce_load_cpu_fw(sc, &cpu_reg, &fw);
4303     bce_start_cpu(sc, &cpu_reg);
4304
4305         DBEXIT(BCE_VERBOSE_RESET);
4306 }
4307
4308
4309 /****************************************************************************/
4310 /* Initialize the RV2P, RX, TX, TPAT, COM, and CP CPUs.                     */
4311 /*                                                                          */
4312 /* Loads the firmware for each CPU and starts the CPU.                      */
4313 /*                                                                          */
4314 /* Returns:                                                                 */
4315 /*   Nothing.                                                               */
4316 /****************************************************************************/
4317 static void
4318 bce_init_cpus(struct bce_softc *sc)
4319 {
4320         DBENTER(BCE_VERBOSE_RESET);
4321
4322         if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
4323                 (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
4324
4325                 if ((BCE_CHIP_REV(sc) == BCE_CHIP_REV_Ax)) {
4326                         bce_load_rv2p_fw(sc, bce_xi90_rv2p_proc1, 
4327                                 sizeof(bce_xi90_rv2p_proc1), RV2P_PROC1);
4328                         bce_load_rv2p_fw(sc, bce_xi90_rv2p_proc2, 
4329                                 sizeof(bce_xi90_rv2p_proc2), RV2P_PROC2);
4330                 } else {
4331                         bce_load_rv2p_fw(sc, bce_xi_rv2p_proc1, 
4332                                 sizeof(bce_xi_rv2p_proc1), RV2P_PROC1);
4333                         bce_load_rv2p_fw(sc, bce_xi_rv2p_proc2, 
4334                                 sizeof(bce_xi_rv2p_proc2), RV2P_PROC2);
4335                 }
4336
4337         } else {
4338                 bce_load_rv2p_fw(sc, bce_rv2p_proc1, 
4339                         sizeof(bce_rv2p_proc1), RV2P_PROC1);
4340                 bce_load_rv2p_fw(sc, bce_rv2p_proc2,
4341                         sizeof(bce_rv2p_proc2), RV2P_PROC2);
4342         }
4343
4344         bce_init_rxp_cpu(sc);
4345         bce_init_txp_cpu(sc);
4346         bce_init_tpat_cpu(sc);
4347         bce_init_com_cpu(sc);
4348         bce_init_cp_cpu(sc);
4349
4350         DBEXIT(BCE_VERBOSE_RESET);
4351 }
4352
4353
4354 /****************************************************************************/
4355 /* Initialize context memory.                                               */
4356 /*                                                                          */
4357 /* Clears the memory associated with each Context ID (CID).                 */
4358 /*                                                                          */
4359 /* Returns:                                                                 */
4360 /*   Nothing.                                                               */
4361 /****************************************************************************/
4362 static void
4363 bce_init_ctx(struct bce_softc *sc)
4364 {
4365
4366         DBENTER(BCE_VERBOSE_RESET | BCE_VERBOSE_CTX);
4367
4368         if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
4369                 (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
4370                 int i, retry_cnt = CTX_INIT_RETRY_COUNT;
4371                 u32 val;
4372
4373                 DBPRINT(sc, BCE_INFO_CTX, "Initializing 5709 context.\n");
4374
4375                 /*
4376                  * BCM5709 context memory may be cached
4377                  * in host memory so prepare the host memory
4378                  * for access.
4379                  */
4380                 val = BCE_CTX_COMMAND_ENABLED | BCE_CTX_COMMAND_MEM_INIT | (1 << 12);
4381                 val |= (BCM_PAGE_BITS - 8) << 16;
4382                 REG_WR(sc, BCE_CTX_COMMAND, val);
4383
4384                 /* Wait for mem init command to complete. */
4385                 for (i = 0; i < retry_cnt; i++) {
4386                         val = REG_RD(sc, BCE_CTX_COMMAND);
4387                         if (!(val & BCE_CTX_COMMAND_MEM_INIT))
4388                                 break;
4389                         DELAY(2);
4390                 }
4391
4392                 /* ToDo: Consider returning an error here. */
4393                 DBRUNIF((val & BCE_CTX_COMMAND_MEM_INIT),
4394                         BCE_PRINTF("%s(): Context memory initialization failed!\n",
4395                         __FUNCTION__));
4396
4397                 for (i = 0; i < sc->ctx_pages; i++) {
4398                         int j;
4399
4400                         /* Set the physical address of the context memory cache. */
4401                         REG_WR(sc, BCE_CTX_HOST_PAGE_TBL_DATA0,
4402                                 BCE_ADDR_LO(sc->ctx_paddr[i] & 0xfffffff0) |
4403                                 BCE_CTX_HOST_PAGE_TBL_DATA0_VALID);
4404                         REG_WR(sc, BCE_CTX_HOST_PAGE_TBL_DATA1,
4405                                 BCE_ADDR_HI(sc->ctx_paddr[i]));
4406                         REG_WR(sc, BCE_CTX_HOST_PAGE_TBL_CTRL, i |
4407                                 BCE_CTX_HOST_PAGE_TBL_CTRL_WRITE_REQ);
4408
4409                         /* Verify that the context memory write was successful. */
4410                         for (j = 0; j < retry_cnt; j++) {
4411                                 val = REG_RD(sc, BCE_CTX_HOST_PAGE_TBL_CTRL);
4412                                 if ((val & BCE_CTX_HOST_PAGE_TBL_CTRL_WRITE_REQ) == 0)
4413                                         break;
4414                                 DELAY(5);
4415                         }
4416
4417                         /* ToDo: Consider returning an error here. */
4418                         DBRUNIF((val & BCE_CTX_HOST_PAGE_TBL_CTRL_WRITE_REQ),
4419                                 BCE_PRINTF("%s(): Failed to initialize context page %d!\n",
4420                                 __FUNCTION__, i));
4421                 }
4422         } else {
4423                 u32 vcid_addr, offset;
4424
4425                 DBPRINT(sc, BCE_INFO, "Initializing 5706/5708 context.\n");
4426
4427                 /*
4428                  * For the 5706/5708, context memory is local to
4429                  * the controller, so initialize the controller
4430                  * context memory.
4431                  */
4432
4433                 vcid_addr = GET_CID_ADDR(96);
4434                 while (vcid_addr) {
4435
4436                         vcid_addr -= PHY_CTX_SIZE;
4437
4438                         REG_WR(sc, BCE_CTX_VIRT_ADDR, 0);
4439                         REG_WR(sc, BCE_CTX_PAGE_TBL, vcid_addr);
4440
4441             for(offset = 0; offset < PHY_CTX_SIZE; offset += 4) {
4442                 CTX_WR(sc, 0x00, offset, 0);
4443             }
4444
4445                         REG_WR(sc, BCE_CTX_VIRT_ADDR, vcid_addr);
4446                         REG_WR(sc, BCE_CTX_PAGE_TBL, vcid_addr);
4447                 }
4448
4449         }
4450         DBEXIT(BCE_VERBOSE_RESET | BCE_VERBOSE_CTX);
4451 }
4452
4453
4454 /****************************************************************************/
4455 /* Fetch the permanent MAC address of the controller.                       */
4456 /*                                                                          */
4457 /* Returns:                                                                 */
4458 /*   Nothing.                                                               */
4459 /****************************************************************************/
4460 static void
4461 bce_get_mac_addr(struct bce_softc *sc)
4462 {
4463         u32 mac_lo = 0, mac_hi = 0;
4464
4465         DBENTER(BCE_VERBOSE_RESET);
4466         /*
4467          * The NetXtreme II bootcode populates various NIC
4468          * power-on and runtime configuration items in a
4469          * shared memory area.  The factory configured MAC
4470          * address is available from both NVRAM and the
4471          * shared memory area so we'll read the value from
4472          * shared memory for speed.
4473          */
4474
4475         mac_hi = bce_shmem_rd(sc, BCE_PORT_HW_CFG_MAC_UPPER);
4476         mac_lo = bce_shmem_rd(sc, BCE_PORT_HW_CFG_MAC_LOWER);
4477
4478         if ((mac_lo == 0) && (mac_hi == 0)) {
4479                 BCE_PRINTF("%s(%d): Invalid Ethernet address!\n",
4480                         __FILE__, __LINE__);
4481         } else {
4482                 sc->eaddr[0] = (u_char)(mac_hi >> 8);
4483                 sc->eaddr[1] = (u_char)(mac_hi >> 0);
4484                 sc->eaddr[2] = (u_char)(mac_lo >> 24);
4485                 sc->eaddr[3] = (u_char)(mac_lo >> 16);
4486                 sc->eaddr[4] = (u_char)(mac_lo >> 8);
4487                 sc->eaddr[5] = (u_char)(mac_lo >> 0);
4488         }
4489
4490         DBPRINT(sc, BCE_INFO_MISC, "Permanent Ethernet address = %6D\n", sc->eaddr, ":");
4491         DBEXIT(BCE_VERBOSE_RESET);
4492 }
4493
4494
4495 /****************************************************************************/
4496 /* Program the MAC address.                                                 */
4497 /*                                                                          */
4498 /* Returns:                                                                 */
4499 /*   Nothing.                                                               */
4500 /****************************************************************************/
4501 static void
4502 bce_set_mac_addr(struct bce_softc *sc)
4503 {
4504         u32 val;
4505         u8 *mac_addr = sc->eaddr;
4506
4507         /* ToDo: Add support for setting multiple MAC addresses. */
4508
4509         DBENTER(BCE_VERBOSE_RESET);
4510         DBPRINT(sc, BCE_INFO_MISC, "Setting Ethernet address = %6D\n", sc->eaddr, ":");
4511
4512         val = (mac_addr[0] << 8) | mac_addr[1];
4513
4514         REG_WR(sc, BCE_EMAC_MAC_MATCH0, val);
4515
4516         val = (mac_addr[2] << 24) | (mac_addr[3] << 16) |
4517                 (mac_addr[4] << 8) | mac_addr[5];
4518
4519         REG_WR(sc, BCE_EMAC_MAC_MATCH1, val);
4520
4521         DBEXIT(BCE_VERBOSE_RESET);
4522 }
4523
4524
4525 /****************************************************************************/
4526 /* Stop the controller.                                                     */
4527 /*                                                                          */
4528 /* Returns:                                                                 */
4529 /*   Nothing.                                                               */
4530 /****************************************************************************/
4531 static void
4532 bce_stop(struct bce_softc *sc)
4533 {
4534         struct ifnet *ifp;
4535         struct ifmedia_entry *ifm;
4536         struct mii_data *mii = NULL;
4537         int mtmp, itmp;
4538
4539         DBENTER(BCE_VERBOSE_RESET);
4540
4541         BCE_LOCK_ASSERT(sc);
4542
4543         ifp = sc->bce_ifp;
4544
4545         mii = device_get_softc(sc->bce_miibus);
4546
4547         callout_stop(&sc->bce_tick_callout);
4548
4549         /* Disable the transmit/receive blocks. */
4550         REG_WR(sc, BCE_MISC_ENABLE_CLR_BITS, BCE_MISC_ENABLE_CLR_DEFAULT);
4551         REG_RD(sc, BCE_MISC_ENABLE_CLR_BITS);
4552         DELAY(20);
4553
4554         bce_disable_intr(sc);
4555
4556         /* Free RX buffers. */
4557 #ifdef BCE_JUMBO_HDRSPLIT
4558         bce_free_pg_chain(sc);
4559 #endif
4560         bce_free_rx_chain(sc);
4561
4562         /* Free TX buffers. */
4563         bce_free_tx_chain(sc);
4564
4565         /*
4566          * Isolate/power down the PHY, but leave the media selection
4567          * unchanged so that things will be put back to normal when
4568          * we bring the interface back up.
4569          */
4570
4571         itmp = ifp->if_flags;
4572         ifp->if_flags |= IFF_UP;
4573
4574         /* If we are called from bce_detach(), mii is already NULL. */
4575         if (mii != NULL) {
4576                 ifm = mii->mii_media.ifm_cur;
4577                 mtmp = ifm->ifm_media;
4578                 ifm->ifm_media = IFM_ETHER | IFM_NONE;
4579                 mii_mediachg(mii);
4580                 ifm->ifm_media = mtmp;
4581         }
4582
4583         ifp->if_flags = itmp;
4584         sc->watchdog_timer = 0;
4585
4586         sc->bce_link = 0;
4587
4588         ifp->if_drv_flags &= ~(IFF_DRV_RUNNING | IFF_DRV_OACTIVE);
4589
4590         DBEXIT(BCE_VERBOSE_RESET);
4591 }
4592
4593
4594 static int
4595 bce_reset(struct bce_softc *sc, u32 reset_code)
4596 {
4597         u32 val;
4598         int i, rc = 0;
4599
4600         DBENTER(BCE_VERBOSE_RESET);
4601
4602         DBPRINT(sc, BCE_VERBOSE_RESET, "%s(): reset_code = 0x%08X\n",
4603                 __FUNCTION__, reset_code);
4604
4605         /* Wait for pending PCI transactions to complete. */
4606         REG_WR(sc, BCE_MISC_ENABLE_CLR_BITS,
4607                BCE_MISC_ENABLE_CLR_BITS_TX_DMA_ENABLE |
4608                BCE_MISC_ENABLE_CLR_BITS_DMA_ENGINE_ENABLE |
4609                BCE_MISC_ENABLE_CLR_BITS_RX_DMA_ENABLE |
4610                BCE_MISC_ENABLE_CLR_BITS_HOST_COALESCE_ENABLE);
4611         val = REG_RD(sc, BCE_MISC_ENABLE_CLR_BITS);
4612         DELAY(5);
4613
4614         /* Disable DMA */
4615         if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
4616                 (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
4617                 val = REG_RD(sc, BCE_MISC_NEW_CORE_CTL);
4618                 val &= ~BCE_MISC_NEW_CORE_CTL_DMA_ENABLE;
4619                 REG_WR(sc, BCE_MISC_NEW_CORE_CTL, val);
4620         }
4621
4622         /* Assume bootcode is running. */
4623         sc->bce_fw_timed_out = 0;
4624
4625         /* Give the firmware a chance to prepare for the reset. */
4626         rc = bce_fw_sync(sc, BCE_DRV_MSG_DATA_WAIT0 | reset_code);
4627         if (rc)
4628                 goto bce_reset_exit;
4629
4630         /* Set a firmware reminder that this is a soft reset. */
4631         bce_shmem_wr(sc, BCE_DRV_RESET_SIGNATURE, BCE_DRV_RESET_SIGNATURE_MAGIC);
4632
4633         /* Dummy read to force the chip to complete all current transactions. */
4634         val = REG_RD(sc, BCE_MISC_ID);
4635
4636         /* Chip reset. */
4637         if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
4638                 (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
4639                 REG_WR(sc, BCE_MISC_COMMAND, BCE_MISC_COMMAND_SW_RESET);
4640                 REG_RD(sc, BCE_MISC_COMMAND);
4641                 DELAY(5);
4642
4643                 val = BCE_PCICFG_MISC_CONFIG_REG_WINDOW_ENA |
4644                       BCE_PCICFG_MISC_CONFIG_TARGET_MB_WORD_SWAP;
4645
4646                 pci_write_config(sc->bce_dev, BCE_PCICFG_MISC_CONFIG, val, 4);
4647         } else {
4648                 val = BCE_PCICFG_MISC_CONFIG_CORE_RST_REQ |
4649                         BCE_PCICFG_MISC_CONFIG_REG_WINDOW_ENA |
4650                         BCE_PCICFG_MISC_CONFIG_TARGET_MB_WORD_SWAP;
4651                 REG_WR(sc, BCE_PCICFG_MISC_CONFIG, val);
4652
4653                 /* Allow up to 30us for reset to complete. */
4654                 for (i = 0; i < 10; i++) {
4655                         val = REG_RD(sc, BCE_PCICFG_MISC_CONFIG);
4656                         if ((val & (BCE_PCICFG_MISC_CONFIG_CORE_RST_REQ |
4657                                 BCE_PCICFG_MISC_CONFIG_CORE_RST_BSY)) == 0) {
4658                                 break;
4659                         }
4660                         DELAY(10);
4661                 }
4662
4663                 /* Check that reset completed successfully. */
4664                 if (val & (BCE_PCICFG_MISC_CONFIG_CORE_RST_REQ |
4665                         BCE_PCICFG_MISC_CONFIG_CORE_RST_BSY)) {
4666                         BCE_PRINTF("%s(%d): Reset failed!\n",
4667                                 __FILE__, __LINE__);
4668                         rc = EBUSY;
4669                         goto bce_reset_exit;
4670                 }
4671         }
4672
4673         /* Make sure byte swapping is properly configured. */
4674         val = REG_RD(sc, BCE_PCI_SWAP_DIAG0);
4675         if (val != 0x01020304) {
4676                 BCE_PRINTF("%s(%d): Byte swap is incorrect!\n",
4677                         __FILE__, __LINE__);
4678                 rc = ENODEV;
4679                 goto bce_reset_exit;
4680         }
4681
4682         /* Just completed a reset, assume that firmware is running again. */
4683         sc->bce_fw_timed_out = 0;
4684
4685         /* Wait for the firmware to finish its initialization. */
4686         rc = bce_fw_sync(sc, BCE_DRV_MSG_DATA_WAIT1 | reset_code);
4687         if (rc)
4688                 BCE_PRINTF("%s(%d): Firmware did not complete initialization!\n",
4689                         __FILE__, __LINE__);
4690
4691 bce_reset_exit:
4692         DBEXIT(BCE_VERBOSE_RESET);
4693         return (rc);
4694 }
4695
4696
4697 static int
4698 bce_chipinit(struct bce_softc *sc)
4699 {
4700         u32 val;
4701         int rc = 0;
4702
4703         DBENTER(BCE_VERBOSE_RESET);
4704
4705         bce_disable_intr(sc);
4706
4707         /*
4708          * Initialize DMA byte/word swapping, configure the number of DMA
4709          * channels and PCI clock compensation delay.
4710          */
4711         val = BCE_DMA_CONFIG_DATA_BYTE_SWAP |
4712               BCE_DMA_CONFIG_DATA_WORD_SWAP |
4713 #if BYTE_ORDER == BIG_ENDIAN
4714               BCE_DMA_CONFIG_CNTL_BYTE_SWAP |
4715 #endif
4716               BCE_DMA_CONFIG_CNTL_WORD_SWAP |
4717               DMA_READ_CHANS << 12 |
4718               DMA_WRITE_CHANS << 16;
4719
4720         val |= (0x2 << 20) | BCE_DMA_CONFIG_CNTL_PCI_COMP_DLY;
4721
4722         if ((sc->bce_flags & BCE_PCIX_FLAG) && (sc->bus_speed_mhz == 133))
4723                 val |= BCE_DMA_CONFIG_PCI_FAST_CLK_CMP;
4724
4725         /*
4726          * This setting resolves a problem observed on certain Intel PCI
4727          * chipsets that cannot handle multiple outstanding DMA operations.
4728          * See errata E9_5706A1_65.
4729          */
4730         if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5706) &&
4731             (BCE_CHIP_ID(sc) != BCE_CHIP_ID_5706_A0) &&
4732             !(sc->bce_flags & BCE_PCIX_FLAG))
4733                 val |= BCE_DMA_CONFIG_CNTL_PING_PONG_DMA;
4734
4735         REG_WR(sc, BCE_DMA_CONFIG, val);
4736
4737         /* Enable the RX_V2P and Context state machines before access. */
4738         REG_WR(sc, BCE_MISC_ENABLE_SET_BITS,
4739                BCE_MISC_ENABLE_SET_BITS_HOST_COALESCE_ENABLE |
4740                BCE_MISC_ENABLE_STATUS_BITS_RX_V2P_ENABLE |
4741                BCE_MISC_ENABLE_STATUS_BITS_CONTEXT_ENABLE);
4742
4743         /* Initialize context mapping and zero out the quick contexts. */
4744         bce_init_ctx(sc);
4745
4746         /* Initialize the on-boards CPUs */
4747         bce_init_cpus(sc);
4748
4749     /* Enable management frames (NC-SI) to flow to the MCP. */
4750     if (sc->bce_flags & BCE_MFW_ENABLE_FLAG) {
4751         val = REG_RD(sc, BCE_RPM_MGMT_PKT_CTRL) | BCE_RPM_MGMT_PKT_CTRL_MGMT_EN;
4752         REG_WR(sc, BCE_RPM_MGMT_PKT_CTRL, val);
4753     }
4754
4755         /* Prepare NVRAM for access. */
4756         if (bce_init_nvram(sc)) {
4757                 rc = ENODEV;
4758                 goto bce_chipinit_exit;
4759         }
4760
4761         /* Set the kernel bypass block size */
4762         val = REG_RD(sc, BCE_MQ_CONFIG);
4763         val &= ~BCE_MQ_CONFIG_KNL_BYP_BLK_SIZE;
4764         val |= BCE_MQ_CONFIG_KNL_BYP_BLK_SIZE_256;
4765
4766         /* Enable bins used on the 5709. */
4767         if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
4768                 (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
4769                 val |= BCE_MQ_CONFIG_BIN_MQ_MODE;
4770                 if (BCE_CHIP_ID(sc) == BCE_CHIP_ID_5709_A1)
4771                         val |= BCE_MQ_CONFIG_HALT_DIS;
4772         }
4773
4774         REG_WR(sc, BCE_MQ_CONFIG, val);
4775
4776         val = 0x10000 + (MAX_CID_CNT * MB_KERNEL_CTX_SIZE);
4777         REG_WR(sc, BCE_MQ_KNL_BYP_WIND_START, val);
4778         REG_WR(sc, BCE_MQ_KNL_WIND_END, val);
4779
4780         /* Set the page size and clear the RV2P processor stall bits. */
4781         val = (BCM_PAGE_BITS - 8) << 24;
4782         REG_WR(sc, BCE_RV2P_CONFIG, val);
4783
4784         /* Configure page size. */
4785         val = REG_RD(sc, BCE_TBDR_CONFIG);
4786         val &= ~BCE_TBDR_CONFIG_PAGE_SIZE;
4787         val |= (BCM_PAGE_BITS - 8) << 24 | 0x40;
4788         REG_WR(sc, BCE_TBDR_CONFIG, val);
4789
4790         /* Set the perfect match control register to default. */
4791         REG_WR_IND(sc, BCE_RXP_PM_CTRL, 0);
4792
4793 bce_chipinit_exit:
4794         DBEXIT(BCE_VERBOSE_RESET);
4795
4796         return(rc);
4797 }
4798
4799
4800 /****************************************************************************/
4801 /* Initialize the controller in preparation to send/receive traffic.        */
4802 /*                                                                          */
4803 /* Returns:                                                                 */
4804 /*   0 for success, positive value for failure.                             */
4805 /****************************************************************************/
4806 static int
4807 bce_blockinit(struct bce_softc *sc)
4808 {
4809         u32 reg, val;
4810         int rc = 0;
4811
4812         DBENTER(BCE_VERBOSE_RESET);
4813
4814         /* Load the hardware default MAC address. */
4815         bce_set_mac_addr(sc);
4816
4817         /* Set the Ethernet backoff seed value */
4818         val = sc->eaddr[0]         + (sc->eaddr[1] << 8) +
4819               (sc->eaddr[2] << 16) + (sc->eaddr[3]     ) +
4820               (sc->eaddr[4] << 8)  + (sc->eaddr[5] << 16);
4821         REG_WR(sc, BCE_EMAC_BACKOFF_SEED, val);
4822
4823         sc->last_status_idx = 0;
4824         sc->rx_mode = BCE_EMAC_RX_MODE_SORT_MODE;
4825
4826         /* Set up link change interrupt generation. */
4827         REG_WR(sc, BCE_EMAC_ATTENTION_ENA, BCE_EMAC_ATTENTION_ENA_LINK);
4828
4829         /* Program the physical address of the status block. */
4830         REG_WR(sc, BCE_HC_STATUS_ADDR_L,
4831                 BCE_ADDR_LO(sc->status_block_paddr));
4832         REG_WR(sc, BCE_HC_STATUS_ADDR_H,
4833                 BCE_ADDR_HI(sc->status_block_paddr));
4834
4835         /* Program the physical address of the statistics block. */
4836         REG_WR(sc, BCE_HC_STATISTICS_ADDR_L,
4837                 BCE_ADDR_LO(sc->stats_block_paddr));
4838         REG_WR(sc, BCE_HC_STATISTICS_ADDR_H,
4839                 BCE_ADDR_HI(sc->stats_block_paddr));
4840
4841         /* Program various host coalescing parameters. */
4842         REG_WR(sc, BCE_HC_TX_QUICK_CONS_TRIP,
4843                 (sc->bce_tx_quick_cons_trip_int << 16) | sc->bce_tx_quick_cons_trip);
4844         REG_WR(sc, BCE_HC_RX_QUICK_CONS_TRIP,
4845                 (sc->bce_rx_quick_cons_trip_int << 16) | sc->bce_rx_quick_cons_trip);
4846         REG_WR(sc, BCE_HC_COMP_PROD_TRIP,
4847                 (sc->bce_comp_prod_trip_int << 16) | sc->bce_comp_prod_trip);
4848         REG_WR(sc, BCE_HC_TX_TICKS,
4849                 (sc->bce_tx_ticks_int << 16) | sc->bce_tx_ticks);
4850         REG_WR(sc, BCE_HC_RX_TICKS,
4851                 (sc->bce_rx_ticks_int << 16) | sc->bce_rx_ticks);
4852         REG_WR(sc, BCE_HC_COM_TICKS,
4853                 (sc->bce_com_ticks_int << 16) | sc->bce_com_ticks);
4854         REG_WR(sc, BCE_HC_CMD_TICKS,
4855                 (sc->bce_cmd_ticks_int << 16) | sc->bce_cmd_ticks);
4856         REG_WR(sc, BCE_HC_STATS_TICKS,
4857                 (sc->bce_stats_ticks & 0xffff00));
4858         REG_WR(sc, BCE_HC_STAT_COLLECT_TICKS, 0xbb8);  /* 3ms */
4859
4860         /* Configure the Host Coalescing block. */
4861         val = BCE_HC_CONFIG_RX_TMR_MODE | BCE_HC_CONFIG_TX_TMR_MODE |
4862                       BCE_HC_CONFIG_COLLECT_STATS;
4863
4864 #if 0
4865         /* ToDo: Add MSI-X support. */
4866         if (sc->bce_flags & BCE_USING_MSIX_FLAG) {
4867                 u32 base = ((BCE_TX_VEC - 1) * BCE_HC_SB_CONFIG_SIZE) +
4868                            BCE_HC_SB_CONFIG_1;
4869
4870                 REG_WR(sc, BCE_HC_MSIX_BIT_VECTOR, BCE_HC_MSIX_BIT_VECTOR_VAL);
4871
4872                 REG_WR(sc, base, BCE_HC_SB_CONFIG_1_TX_TMR_MODE |
4873                         BCE_HC_SB_CONFIG_1_ONE_SHOT);
4874
4875                 REG_WR(sc, base + BCE_HC_TX_QUICK_CONS_TRIP_OFF,
4876                         (sc->tx_quick_cons_trip_int << 16) |
4877                          sc->tx_quick_cons_trip);
4878
4879                 REG_WR(sc, base + BCE_HC_TX_TICKS_OFF,
4880                         (sc->tx_ticks_int << 16) | sc->tx_ticks);
4881
4882                 val |= BCE_HC_CONFIG_SB_ADDR_INC_128B;
4883         }
4884
4885         /*
4886          * Tell the HC block to automatically set the
4887          * INT_MASK bit after an MSI/MSI-X interrupt
4888          * is generated so the driver doesn't have to.
4889          */
4890         if (sc->bce_flags & BCE_ONE_SHOT_MSI_FLAG)
4891                 val |= BCE_HC_CONFIG_ONE_SHOT;
4892
4893         /* Set the MSI-X status blocks to 128 byte boundaries. */
4894         if (sc->bce_flags & BCE_USING_MSIX_FLAG)
4895                 val |= BCE_HC_CONFIG_SB_ADDR_INC_128B;
4896 #endif
4897
4898         REG_WR(sc, BCE_HC_CONFIG, val);
4899
4900         /* Clear the internal statistics counters. */
4901         REG_WR(sc, BCE_HC_COMMAND, BCE_HC_COMMAND_CLR_STAT_NOW);
4902
4903         /* Verify that bootcode is running. */
4904         reg = bce_shmem_rd(sc, BCE_DEV_INFO_SIGNATURE);
4905
4906         DBRUNIF(DB_RANDOMTRUE(bootcode_running_failure_sim_control),
4907                 BCE_PRINTF("%s(%d): Simulating bootcode failure.\n",
4908                         __FILE__, __LINE__);
4909                 reg = 0);
4910
4911         if ((reg & BCE_DEV_INFO_SIGNATURE_MAGIC_MASK) !=
4912             BCE_DEV_INFO_SIGNATURE_MAGIC) {
4913                 BCE_PRINTF("%s(%d): Bootcode not running! Found: 0x%08X, "
4914                         "Expected: 08%08X\n", __FILE__, __LINE__,
4915                         (reg & BCE_DEV_INFO_SIGNATURE_MAGIC_MASK),
4916                         BCE_DEV_INFO_SIGNATURE_MAGIC);
4917                 rc = ENODEV;
4918                 goto bce_blockinit_exit;
4919         }
4920
4921         /* Enable DMA */
4922         if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
4923                 (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
4924                 val = REG_RD(sc, BCE_MISC_NEW_CORE_CTL);
4925                 val |= BCE_MISC_NEW_CORE_CTL_DMA_ENABLE;
4926                 REG_WR(sc, BCE_MISC_NEW_CORE_CTL, val);
4927         }
4928
4929         /* Allow bootcode to apply any additional fixes before enabling MAC. */
4930         rc = bce_fw_sync(sc, BCE_DRV_MSG_DATA_WAIT2 | BCE_DRV_MSG_CODE_RESET);
4931
4932         /* Enable link state change interrupt generation. */
4933         REG_WR(sc, BCE_HC_ATTN_BITS_ENABLE, STATUS_ATTN_BITS_LINK_STATE);
4934
4935     /* Enable the RXP. */
4936     bce_start_rxp_cpu(sc);
4937
4938     /* Disable management frames (NC-SI) from flowing to the MCP. */
4939     if (sc->bce_flags & BCE_MFW_ENABLE_FLAG) {
4940         val = REG_RD(sc, BCE_RPM_MGMT_PKT_CTRL) & ~BCE_RPM_MGMT_PKT_CTRL_MGMT_EN;
4941         REG_WR(sc, BCE_RPM_MGMT_PKT_CTRL, val);
4942     }
4943
4944         /* Enable all remaining blocks in the MAC. */
4945         if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709)     ||
4946                 (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716))
4947                 REG_WR(sc, BCE_MISC_ENABLE_SET_BITS, BCE_MISC_ENABLE_DEFAULT_XI);
4948         else
4949                 REG_WR(sc, BCE_MISC_ENABLE_SET_BITS, BCE_MISC_ENABLE_DEFAULT);
4950
4951         REG_RD(sc, BCE_MISC_ENABLE_SET_BITS);
4952         DELAY(20);
4953
4954         /* Save the current host coalescing block settings. */
4955         sc->hc_command = REG_RD(sc, BCE_HC_COMMAND);
4956
4957 bce_blockinit_exit:
4958         DBEXIT(BCE_VERBOSE_RESET);
4959
4960         return (rc);
4961 }
4962
4963
4964 /****************************************************************************/
4965 /* Encapsulate an mbuf into the rx_bd chain.                                */
4966 /*                                                                          */
4967 /* Returns:                                                                 */
4968 /*   0 for success, positive value for failure.                             */
4969 /****************************************************************************/
4970 static int
4971 bce_get_rx_buf(struct bce_softc *sc, struct mbuf *m, u16 *prod,
4972         u16 *chain_prod, u32 *prod_bseq)
4973 {
4974         bus_dmamap_t map;
4975         bus_dma_segment_t segs[BCE_MAX_SEGMENTS];
4976         struct mbuf *m_new = NULL;
4977         struct rx_bd *rxbd;
4978         int nsegs, error, rc = 0;
4979 #ifdef BCE_DEBUG
4980         u16 debug_chain_prod = *chain_prod;
4981 #endif
4982
4983         DBENTER(BCE_EXTREME_RESET | BCE_EXTREME_RECV | BCE_EXTREME_LOAD);
4984
4985         /* Make sure the inputs are valid. */
4986         DBRUNIF((*chain_prod > MAX_RX_BD),
4987                 BCE_PRINTF("%s(%d): RX producer out of range: 0x%04X > 0x%04X\n",
4988                 __FILE__, __LINE__, *chain_prod, (u16) MAX_RX_BD));
4989
4990         DBPRINT(sc, BCE_EXTREME_RECV, "%s(enter): prod = 0x%04X, chain_prod = 0x%04X, "
4991                 "prod_bseq = 0x%08X\n", __FUNCTION__, *prod, *chain_prod, *prod_bseq);
4992
4993         /* Update some debug statistic counters */
4994         DBRUNIF((sc->free_rx_bd < sc->rx_low_watermark),
4995                 sc->rx_low_watermark = sc->free_rx_bd);
4996         DBRUNIF((sc->free_rx_bd == sc->max_rx_bd), sc->rx_empty_count++);
4997
4998         /* Check whether this is a new mbuf allocation. */
4999         if (m == NULL) {
5000
5001                 /* Simulate an mbuf allocation failure. */
5002                 DBRUNIF(DB_RANDOMTRUE(mbuf_alloc_failed_sim_control),
5003                         sc->mbuf_alloc_failed_count++;
5004                         sc->mbuf_alloc_failed_sim_count++;
5005                         rc = ENOBUFS;
5006                         goto bce_get_rx_buf_exit);
5007
5008                 /* This is a new mbuf allocation. */
5009 #ifdef BCE_JUMBO_HDRSPLIT
5010                 MGETHDR(m_new, M_DONTWAIT, MT_DATA);
5011 #else
5012                 if (sc->rx_bd_mbuf_alloc_size <= MCLBYTES)
5013                         m_new = m_getcl(M_DONTWAIT, MT_DATA, M_PKTHDR);
5014                 else
5015                         m_new = m_getjcl(M_DONTWAIT, MT_DATA, M_PKTHDR, sc->rx_bd_mbuf_alloc_size);
5016 #endif
5017
5018                 if (m_new == NULL) {
5019                         sc->mbuf_alloc_failed_count++;
5020                         rc = ENOBUFS;
5021                         goto bce_get_rx_buf_exit;
5022                 }
5023
5024                 DBRUN(sc->debug_rx_mbuf_alloc++);
5025         } else {
5026                 /* Reuse an existing mbuf. */
5027                 m_new = m;
5028         }
5029
5030         /* Make sure we have a valid packet header. */
5031         M_ASSERTPKTHDR(m_new);
5032
5033         /* Initialize the mbuf size and pad if necessary for alignment. */
5034         m_new->m_pkthdr.len = m_new->m_len = sc->rx_bd_mbuf_alloc_size;
5035         m_adj(m_new, sc->rx_bd_mbuf_align_pad);
5036
5037         /* ToDo: Consider calling m_fragment() to test error handling. */
5038
5039         /* Map the mbuf cluster into device memory. */
5040         map = sc->rx_mbuf_map[*chain_prod];
5041         error = bus_dmamap_load_mbuf_sg(sc->rx_mbuf_tag, map, m_new,
5042             segs, &nsegs, BUS_DMA_NOWAIT);
5043
5044         /* Handle any mapping errors. */
5045         if (error) {
5046                 BCE_PRINTF("%s(%d): Error mapping mbuf into RX chain (%d)!\n",
5047                         __FILE__, __LINE__, error);
5048
5049                 sc->dma_map_addr_rx_failed_count++;
5050                 m_freem(m_new);
5051
5052                 DBRUN(sc->debug_rx_mbuf_alloc--);
5053
5054                 rc = ENOBUFS;
5055                 goto bce_get_rx_buf_exit;
5056         }
5057
5058         /* All mbufs must map to a single segment. */
5059         KASSERT(nsegs == 1, ("%s(): Too many segments returned (%d)!",
5060                  __FUNCTION__, nsegs));
5061
5062         /* ToDo: Do we need bus_dmamap_sync(,,BUS_DMASYNC_PREREAD) here? */
5063
5064         /* Setup the rx_bd for the segment. */
5065         rxbd = &sc->rx_bd_chain[RX_PAGE(*chain_prod)][RX_IDX(*chain_prod)];
5066
5067         rxbd->rx_bd_haddr_lo  = htole32(BCE_ADDR_LO(segs[0].ds_addr));
5068         rxbd->rx_bd_haddr_hi  = htole32(BCE_ADDR_HI(segs[0].ds_addr));
5069         rxbd->rx_bd_len       = htole32(segs[0].ds_len);
5070         rxbd->rx_bd_flags     = htole32(RX_BD_FLAGS_START | RX_BD_FLAGS_END);
5071         *prod_bseq += segs[0].ds_len;
5072
5073         /* Save the mbuf and update our counter. */
5074         sc->rx_mbuf_ptr[*chain_prod] = m_new;
5075         sc->free_rx_bd -= nsegs;
5076
5077         DBRUNMSG(BCE_INSANE_RECV, bce_dump_rx_mbuf_chain(sc, debug_chain_prod,
5078                 nsegs));
5079
5080         DBPRINT(sc, BCE_EXTREME_RECV, "%s(exit): prod = 0x%04X, chain_prod = 0x%04X, "
5081                 "prod_bseq = 0x%08X\n", __FUNCTION__, *prod, *chain_prod, *prod_bseq);
5082
5083 bce_get_rx_buf_exit:
5084         DBEXIT(BCE_EXTREME_RESET | BCE_EXTREME_RECV | BCE_EXTREME_LOAD);
5085
5086         return(rc);
5087 }
5088
5089
5090 #ifdef BCE_JUMBO_HDRSPLIT
5091 /****************************************************************************/
5092 /* Encapsulate an mbuf cluster into the page chain.                        */
5093 /*                                                                          */
5094 /* Returns:                                                                 */
5095 /*   0 for success, positive value for failure.                             */
5096 /****************************************************************************/
5097 static int
5098 bce_get_pg_buf(struct bce_softc *sc, struct mbuf *m, u16 *prod,
5099         u16 *prod_idx)
5100 {
5101         bus_dmamap_t map;
5102         bus_addr_t busaddr;
5103         struct mbuf *m_new = NULL;
5104         struct rx_bd *pgbd;
5105         int error, rc = 0;
5106 #ifdef BCE_DEBUG
5107         u16 debug_prod_idx = *prod_idx;
5108 #endif
5109
5110         DBENTER(BCE_EXTREME_RESET | BCE_EXTREME_RECV | BCE_EXTREME_LOAD);
5111
5112         /* Make sure the inputs are valid. */
5113         DBRUNIF((*prod_idx > MAX_PG_BD),
5114                 BCE_PRINTF("%s(%d): page producer out of range: 0x%04X > 0x%04X\n",
5115                 __FILE__, __LINE__, *prod_idx, (u16) MAX_PG_BD));
5116
5117         DBPRINT(sc, BCE_EXTREME_RECV, "%s(enter): prod = 0x%04X, "
5118                 "chain_prod = 0x%04X\n", __FUNCTION__, *prod, *prod_idx);
5119
5120         /* Update counters if we've hit a new low or run out of pages. */
5121         DBRUNIF((sc->free_pg_bd < sc->pg_low_watermark),
5122                 sc->pg_low_watermark = sc->free_pg_bd);
5123         DBRUNIF((sc->free_pg_bd == sc->max_pg_bd), sc->pg_empty_count++);
5124
5125         /* Check whether this is a new mbuf allocation. */
5126         if (m == NULL) {
5127
5128                 /* Simulate an mbuf allocation failure. */
5129                 DBRUNIF(DB_RANDOMTRUE(mbuf_alloc_failed_sim_control),
5130                         sc->mbuf_alloc_failed_count++;
5131                         sc->mbuf_alloc_failed_sim_count++;
5132                         rc = ENOBUFS;
5133                         goto bce_get_pg_buf_exit);
5134
5135                 /* This is a new mbuf allocation. */
5136                 m_new = m_getcl(M_DONTWAIT, MT_DATA, 0);
5137                 if (m_new == NULL) {
5138                         sc->mbuf_alloc_failed_count++;
5139                         rc = ENOBUFS;
5140                         goto bce_get_pg_buf_exit;
5141                 }
5142
5143                 DBRUN(sc->debug_pg_mbuf_alloc++);
5144         } else {
5145                 /* Reuse an existing mbuf. */
5146                 m_new = m;
5147                 m_new->m_data = m_new->m_ext.ext_buf;
5148         }
5149
5150         m_new->m_len = sc->pg_bd_mbuf_alloc_size;
5151
5152         /* ToDo: Consider calling m_fragment() to test error handling. */
5153
5154         /* Map the mbuf cluster into device memory. */
5155         map = sc->pg_mbuf_map[*prod_idx];
5156         error = bus_dmamap_load(sc->pg_mbuf_tag, map, mtod(m_new, void *),
5157             sc->pg_bd_mbuf_alloc_size, bce_dma_map_addr, &busaddr, BUS_DMA_NOWAIT);
5158
5159         /* Handle any mapping errors. */
5160         if (error) {
5161                 BCE_PRINTF("%s(%d): Error mapping mbuf into page chain!\n",
5162                         __FILE__, __LINE__);
5163
5164                 m_freem(m_new);
5165                 DBRUN(sc->debug_pg_mbuf_alloc--);
5166
5167                 rc = ENOBUFS;
5168                 goto bce_get_pg_buf_exit;
5169         }
5170
5171         /* ToDo: Do we need bus_dmamap_sync(,,BUS_DMASYNC_PREREAD) here? */
5172
5173         /*
5174          * The page chain uses the same rx_bd data structure
5175          * as the receive chain but doesn't require a byte sequence (bseq).
5176          */
5177         pgbd = &sc->pg_bd_chain[PG_PAGE(*prod_idx)][PG_IDX(*prod_idx)];
5178
5179         pgbd->rx_bd_haddr_lo  = htole32(BCE_ADDR_LO(busaddr));
5180         pgbd->rx_bd_haddr_hi  = htole32(BCE_ADDR_HI(busaddr));
5181         pgbd->rx_bd_len       = htole32(sc->pg_bd_mbuf_alloc_size);
5182         pgbd->rx_bd_flags     = htole32(RX_BD_FLAGS_START | RX_BD_FLAGS_END);
5183
5184         /* Save the mbuf and update our counter. */
5185         sc->pg_mbuf_ptr[*prod_idx] = m_new;
5186         sc->free_pg_bd--;
5187
5188         DBRUNMSG(BCE_INSANE_RECV, bce_dump_pg_mbuf_chain(sc, debug_prod_idx,
5189                 1));
5190
5191         DBPRINT(sc, BCE_EXTREME_RECV, "%s(exit): prod = 0x%04X, "
5192                 "prod_idx = 0x%04X\n", __FUNCTION__, *prod, *prod_idx);
5193
5194 bce_get_pg_buf_exit:
5195         DBEXIT(BCE_EXTREME_RESET | BCE_EXTREME_RECV | BCE_EXTREME_LOAD);
5196
5197         return(rc);
5198 }
5199 #endif /* BCE_JUMBO_HDRSPLIT */
5200
5201 /****************************************************************************/
5202 /* Initialize the TX context memory.                                        */
5203 /*                                                                          */
5204 /* Returns:                                                                 */
5205 /*   Nothing                                                                */
5206 /****************************************************************************/
5207 static void
5208 bce_init_tx_context(struct bce_softc *sc)
5209 {
5210         u32 val;
5211
5212         DBENTER(BCE_VERBOSE_RESET | BCE_VERBOSE_SEND | BCE_VERBOSE_CTX);
5213
5214         /* Initialize the context ID for an L2 TX chain. */
5215         if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
5216                 (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
5217                 /* Set the CID type to support an L2 connection. */
5218                 val = BCE_L2CTX_TX_TYPE_TYPE_L2_XI | BCE_L2CTX_TX_TYPE_SIZE_L2_XI;
5219                 CTX_WR(sc, GET_CID_ADDR(TX_CID), BCE_L2CTX_TX_TYPE_XI, val);
5220                 val = BCE_L2CTX_TX_CMD_TYPE_TYPE_L2_XI | (8 << 16);
5221                 CTX_WR(sc, GET_CID_ADDR(TX_CID), BCE_L2CTX_TX_CMD_TYPE_XI, val);
5222
5223                 /* Point the hardware to the first page in the chain. */
5224                 val = BCE_ADDR_HI(sc->tx_bd_chain_paddr[0]);
5225                 CTX_WR(sc, GET_CID_ADDR(TX_CID), BCE_L2CTX_TX_TBDR_BHADDR_HI_XI, val);
5226                 val = BCE_ADDR_LO(sc->tx_bd_chain_paddr[0]);
5227                 CTX_WR(sc, GET_CID_ADDR(TX_CID), BCE_L2CTX_TX_TBDR_BHADDR_LO_XI, val);
5228         } else {
5229                 /* Set the CID type to support an L2 connection. */
5230                 val = BCE_L2CTX_TX_TYPE_TYPE_L2 | BCE_L2CTX_TX_TYPE_SIZE_L2;
5231                 CTX_WR(sc, GET_CID_ADDR(TX_CID), BCE_L2CTX_TX_TYPE, val);
5232                 val = BCE_L2CTX_TX_CMD_TYPE_TYPE_L2 | (8 << 16);
5233                 CTX_WR(sc, GET_CID_ADDR(TX_CID), BCE_L2CTX_TX_CMD_TYPE, val);
5234
5235                 /* Point the hardware to the first page in the chain. */
5236                 val = BCE_ADDR_HI(sc->tx_bd_chain_paddr[0]);
5237                 CTX_WR(sc, GET_CID_ADDR(TX_CID), BCE_L2CTX_TX_TBDR_BHADDR_HI, val);
5238                 val = BCE_ADDR_LO(sc->tx_bd_chain_paddr[0]);
5239                 CTX_WR(sc, GET_CID_ADDR(TX_CID), BCE_L2CTX_TX_TBDR_BHADDR_LO, val);
5240         }
5241
5242         DBEXIT(BCE_VERBOSE_RESET | BCE_VERBOSE_SEND | BCE_VERBOSE_CTX);
5243 }
5244
5245
5246 /****************************************************************************/
5247 /* Allocate memory and initialize the TX data structures.                   */
5248 /*                                                                          */
5249 /* Returns:                                                                 */
5250 /*   0 for success, positive value for failure.                             */
5251 /****************************************************************************/
5252 static int
5253 bce_init_tx_chain(struct bce_softc *sc)
5254 {
5255         struct tx_bd *txbd;
5256         int i, rc = 0;
5257
5258         DBENTER(BCE_VERBOSE_RESET | BCE_VERBOSE_SEND | BCE_VERBOSE_LOAD);
5259
5260         /* Set the initial TX producer/consumer indices. */
5261         sc->tx_prod        = 0;
5262         sc->tx_cons        = 0;
5263         sc->tx_prod_bseq   = 0;
5264         sc->used_tx_bd     = 0;
5265         sc->max_tx_bd      = USABLE_TX_BD;
5266         DBRUN(sc->tx_hi_watermark = USABLE_TX_BD);
5267         DBRUN(sc->tx_full_count = 0);
5268
5269         /*
5270          * The NetXtreme II supports a linked-list structre called
5271          * a Buffer Descriptor Chain (or BD chain).  A BD chain
5272          * consists of a series of 1 or more chain pages, each of which
5273          * consists of a fixed number of BD entries.
5274          * The last BD entry on each page is a pointer to the next page
5275          * in the chain, and the last pointer in the BD chain
5276          * points back to the beginning of the chain.
5277          */
5278
5279         /* Set the TX next pointer chain entries. */
5280         for (i = 0; i < TX_PAGES; i++) {
5281                 int j;
5282
5283                 txbd = &sc->tx_bd_chain[i][USABLE_TX_BD_PER_PAGE];
5284
5285                 /* Check if we've reached the last page. */
5286                 if (i == (TX_PAGES - 1))
5287                         j = 0;
5288                 else
5289                         j = i + 1;
5290
5291                 txbd->tx_bd_haddr_hi = htole32(BCE_ADDR_HI(sc->tx_bd_chain_paddr[j]));
5292                 txbd->tx_bd_haddr_lo = htole32(BCE_ADDR_LO(sc->tx_bd_chain_paddr[j]));
5293         }
5294
5295         bce_init_tx_context(sc);
5296
5297         DBRUNMSG(BCE_INSANE_SEND, bce_dump_tx_chain(sc, 0, TOTAL_TX_BD));
5298         DBEXIT(BCE_VERBOSE_RESET | BCE_VERBOSE_SEND | BCE_VERBOSE_LOAD);
5299
5300         return(rc);
5301 }
5302
5303
5304 /****************************************************************************/
5305 /* Free memory and clear the TX data structures.                            */
5306 /*                                                                          */
5307 /* Returns:                                                                 */
5308 /*   Nothing.                                                               */
5309 /****************************************************************************/
5310 static void
5311 bce_free_tx_chain(struct bce_softc *sc)
5312 {
5313         int i;
5314
5315         DBENTER(BCE_VERBOSE_RESET | BCE_VERBOSE_SEND | BCE_VERBOSE_UNLOAD);
5316
5317         /* Unmap, unload, and free any mbufs still in the TX mbuf chain. */
5318         for (i = 0; i < TOTAL_TX_BD; i++) {
5319                 if (sc->tx_mbuf_ptr[i] != NULL) {
5320                         if (sc->tx_mbuf_map[i] != NULL)
5321                                 bus_dmamap_sync(sc->tx_mbuf_tag, sc->tx_mbuf_map[i],
5322                                         BUS_DMASYNC_POSTWRITE);
5323                         m_freem(sc->tx_mbuf_ptr[i]);
5324                         sc->tx_mbuf_ptr[i] = NULL;
5325                         DBRUN(sc->debug_tx_mbuf_alloc--);
5326                 }
5327         }
5328
5329         /* Clear each TX chain page. */
5330         for (i = 0; i < TX_PAGES; i++)
5331                 bzero((char *)sc->tx_bd_chain[i], BCE_TX_CHAIN_PAGE_SZ);
5332
5333         sc->used_tx_bd     = 0;
5334
5335         /* Check if we lost any mbufs in the process. */
5336         DBRUNIF((sc->debug_tx_mbuf_alloc),
5337                 BCE_PRINTF("%s(%d): Memory leak! Lost %d mbufs "
5338                         "from tx chain!\n",
5339                         __FILE__, __LINE__, sc->debug_tx_mbuf_alloc));
5340
5341         DBEXIT(BCE_VERBOSE_RESET | BCE_VERBOSE_SEND | BCE_VERBOSE_UNLOAD);
5342 }
5343
5344
5345 /****************************************************************************/
5346 /* Initialize the RX context memory.                                        */
5347 /*                                                                          */
5348 /* Returns:                                                                 */
5349 /*   Nothing                                                                */
5350 /****************************************************************************/
5351 static void
5352 bce_init_rx_context(struct bce_softc *sc)
5353 {
5354         u32 val;
5355
5356         DBENTER(BCE_VERBOSE_RESET | BCE_VERBOSE_RECV | BCE_VERBOSE_CTX);
5357
5358         /* Initialize the type, size, and BD cache levels for the RX context. */
5359         val = BCE_L2CTX_RX_CTX_TYPE_CTX_BD_CHN_TYPE_VALUE |
5360                 BCE_L2CTX_RX_CTX_TYPE_SIZE_L2 |
5361                 (0x02 << BCE_L2CTX_RX_BD_PRE_READ_SHIFT);
5362
5363         /*
5364          * Set the level for generating pause frames
5365          * when the number of available rx_bd's gets
5366          * too low (the low watermark) and the level
5367          * when pause frames can be stopped (the high
5368          * watermark).
5369          */
5370         if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
5371                 (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
5372                 u32 lo_water, hi_water;
5373
5374                 lo_water = BCE_L2CTX_RX_LO_WATER_MARK_DEFAULT;
5375                 hi_water = USABLE_RX_BD / 4;
5376
5377                 lo_water /= BCE_L2CTX_RX_LO_WATER_MARK_SCALE;
5378                 hi_water /= BCE_L2CTX_RX_HI_WATER_MARK_SCALE;
5379
5380                 if (hi_water > 0xf)
5381                         hi_water = 0xf;
5382                 else if (hi_water == 0)
5383                         lo_water = 0;
5384                 val |= (lo_water << BCE_L2CTX_RX_LO_WATER_MARK_SHIFT) |
5385                         (hi_water << BCE_L2CTX_RX_HI_WATER_MARK_SHIFT);
5386         }
5387
5388         CTX_WR(sc, GET_CID_ADDR(RX_CID), BCE_L2CTX_RX_CTX_TYPE, val);
5389
5390         /* Setup the MQ BIN mapping for l2_ctx_host_bseq. */
5391         if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
5392                 (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
5393                 val = REG_RD(sc, BCE_MQ_MAP_L2_5);
5394                 REG_WR(sc, BCE_MQ_MAP_L2_5, val | BCE_MQ_MAP_L2_5_ARM);
5395         }
5396
5397         /* Point the hardware to the first page in the chain. */
5398         val = BCE_ADDR_HI(sc->rx_bd_chain_paddr[0]);
5399         CTX_WR(sc, GET_CID_ADDR(RX_CID), BCE_L2CTX_RX_NX_BDHADDR_HI, val);
5400         val = BCE_ADDR_LO(sc->rx_bd_chain_paddr[0]);
5401         CTX_WR(sc, GET_CID_ADDR(RX_CID), BCE_L2CTX_RX_NX_BDHADDR_LO, val);
5402
5403         DBEXIT(BCE_VERBOSE_RESET | BCE_VERBOSE_RECV | BCE_VERBOSE_CTX);
5404 }
5405
5406
5407 /****************************************************************************/
5408 /* Allocate memory and initialize the RX data structures.                   */
5409 /*                                                                          */
5410 /* Returns:                                                                 */
5411 /*   0 for success, positive value for failure.                             */
5412 /****************************************************************************/
5413 static int
5414 bce_init_rx_chain(struct bce_softc *sc)
5415 {
5416         struct rx_bd *rxbd;
5417         int i, rc = 0;
5418
5419         DBENTER(BCE_VERBOSE_RESET | BCE_VERBOSE_RECV | BCE_VERBOSE_LOAD |
5420                 BCE_VERBOSE_CTX);
5421
5422         /* Initialize the RX producer and consumer indices. */
5423         sc->rx_prod        = 0;
5424         sc->rx_cons        = 0;
5425         sc->rx_prod_bseq   = 0;
5426         sc->free_rx_bd     = USABLE_RX_BD;
5427         sc->max_rx_bd      = USABLE_RX_BD;
5428         DBRUN(sc->rx_low_watermark = sc->max_rx_bd);
5429         DBRUN(sc->rx_empty_count = 0);
5430
5431         /* Initialize the RX next pointer chain entries. */
5432         for (i = 0; i < RX_PAGES; i++) {
5433                 int j;
5434
5435                 rxbd = &sc->rx_bd_chain[i][USABLE_RX_BD_PER_PAGE];
5436
5437                 /* Check if we've reached the last page. */
5438                 if (i == (RX_PAGES - 1))
5439                         j = 0;
5440                 else
5441                         j = i + 1;
5442
5443                 /* Setup the chain page pointers. */
5444                 rxbd->rx_bd_haddr_hi = htole32(BCE_ADDR_HI(sc->rx_bd_chain_paddr[j]));
5445                 rxbd->rx_bd_haddr_lo = htole32(BCE_ADDR_LO(sc->rx_bd_chain_paddr[j]));
5446         }
5447
5448         /* Fill up the RX chain. */
5449         bce_fill_rx_chain(sc);
5450
5451         for (i = 0; i < RX_PAGES; i++) {
5452                 bus_dmamap_sync(sc->rx_bd_chain_tag, sc->rx_bd_chain_map[i],
5453                     BUS_DMASYNC_PREREAD | BUS_DMASYNC_PREWRITE);
5454         }
5455
5456         bce_init_rx_context(sc);
5457
5458         DBRUNMSG(BCE_EXTREME_RECV, bce_dump_rx_chain(sc, 0, TOTAL_RX_BD));
5459         DBEXIT(BCE_VERBOSE_RESET | BCE_VERBOSE_RECV | BCE_VERBOSE_LOAD |
5460                 BCE_VERBOSE_CTX);
5461         /* ToDo: Are there possible failure modes here? */
5462         return(rc);
5463 }
5464
5465
5466 /****************************************************************************/
5467 /* Add mbufs to the RX chain until its full or an mbuf allocation error     */
5468 /* occurs.                                                                  */
5469 /*                                                                          */
5470 /* Returns:                                                                 */
5471 /*   Nothing                                                                */
5472 /****************************************************************************/
5473 static void
5474 bce_fill_rx_chain(struct bce_softc *sc)
5475 {
5476         u16 prod, prod_idx;
5477         u32 prod_bseq;
5478
5479         DBENTER(BCE_VERBOSE_RESET | BCE_EXTREME_RECV | BCE_VERBOSE_LOAD |
5480                 BCE_VERBOSE_CTX);
5481
5482         /* Get the RX chain producer indices. */
5483         prod      = sc->rx_prod;
5484         prod_bseq = sc->rx_prod_bseq;
5485
5486         /* Keep filling the RX chain until it's full. */
5487         while (sc->free_rx_bd > 0) {
5488                 prod_idx = RX_CHAIN_IDX(prod);
5489                 if (bce_get_rx_buf(sc, NULL, &prod, &prod_idx, &prod_bseq)) {
5490                         /* Bail out if we can't add an mbuf to the chain. */
5491                         break;
5492                 }
5493                 prod = NEXT_RX_BD(prod);
5494         }
5495
5496         /* Save the RX chain producer indices. */
5497         sc->rx_prod      = prod;
5498         sc->rx_prod_bseq = prod_bseq;
5499
5500         DBRUNIF(((prod & USABLE_RX_BD_PER_PAGE) == USABLE_RX_BD_PER_PAGE),
5501                 BCE_PRINTF("%s(): Invalid rx_prod value: 0x%04X\n",
5502                 __FUNCTION__, sc->rx_prod));
5503
5504         /* Write the mailbox and tell the chip about the waiting rx_bd's. */
5505         REG_WR16(sc, MB_GET_CID_ADDR(RX_CID) + BCE_L2MQ_RX_HOST_BDIDX,
5506                 sc->rx_prod);
5507         REG_WR(sc, MB_GET_CID_ADDR(RX_CID) + BCE_L2MQ_RX_HOST_BSEQ,
5508                 sc->rx_prod_bseq);
5509
5510         DBEXIT(BCE_VERBOSE_RESET | BCE_EXTREME_RECV | BCE_VERBOSE_LOAD |
5511                 BCE_VERBOSE_CTX);
5512 }
5513
5514
5515 /****************************************************************************/
5516 /* Free memory and clear the RX data structures.                            */
5517 /*                                                                          */
5518 /* Returns:                                                                 */
5519 /*   Nothing.                                                               */
5520 /****************************************************************************/
5521 static void
5522 bce_free_rx_chain(struct bce_softc *sc)
5523 {
5524         int i;
5525
5526         DBENTER(BCE_VERBOSE_RESET | BCE_VERBOSE_RECV | BCE_VERBOSE_UNLOAD);
5527
5528         /* Free any mbufs still in the RX mbuf chain. */
5529         for (i = 0; i < TOTAL_RX_BD; i++) {
5530                 if (sc->rx_mbuf_ptr[i] != NULL) {
5531                         if (sc->rx_mbuf_map[i] != NULL)
5532                                 bus_dmamap_sync(sc->rx_mbuf_tag, sc->rx_mbuf_map[i],
5533                                         BUS_DMASYNC_POSTREAD);
5534                         m_freem(sc->rx_mbuf_ptr[i]);
5535                         sc->rx_mbuf_ptr[i] = NULL;
5536                         DBRUN(sc->debug_rx_mbuf_alloc--);
5537                 }
5538         }
5539
5540         /* Clear each RX chain page. */
5541         for (i = 0; i < RX_PAGES; i++)
5542                 bzero((char *)sc->rx_bd_chain[i], BCE_RX_CHAIN_PAGE_SZ);
5543
5544         sc->free_rx_bd = sc->max_rx_bd;
5545
5546         /* Check if we lost any mbufs in the process. */
5547         DBRUNIF((sc->debug_rx_mbuf_alloc),
5548                 BCE_PRINTF("%s(): Memory leak! Lost %d mbufs from rx chain!\n",
5549                         __FUNCTION__, sc->debug_rx_mbuf_alloc));
5550
5551         DBEXIT(BCE_VERBOSE_RESET | BCE_VERBOSE_RECV | BCE_VERBOSE_UNLOAD);
5552 }
5553
5554
5555 #ifdef BCE_JUMBO_HDRSPLIT
5556 /****************************************************************************/
5557 /* Allocate memory and initialize the page data structures.                 */
5558 /* Assumes that bce_init_rx_chain() has not already been called.            */
5559 /*                                                                          */
5560 /* Returns:                                                                 */
5561 /*   0 for success, positive value for failure.                             */
5562 /****************************************************************************/
5563 static int
5564 bce_init_pg_chain(struct bce_softc *sc)
5565 {
5566         struct rx_bd *pgbd;
5567         int i, rc = 0;
5568         u32 val;
5569
5570         DBENTER(BCE_VERBOSE_RESET | BCE_VERBOSE_RECV | BCE_VERBOSE_LOAD |
5571                 BCE_VERBOSE_CTX);
5572
5573         /* Initialize the page producer and consumer indices. */
5574         sc->pg_prod        = 0;
5575         sc->pg_cons        = 0;
5576         sc->free_pg_bd     = USABLE_PG_BD;
5577         sc->max_pg_bd      = USABLE_PG_BD;
5578         DBRUN(sc->pg_low_watermark = sc->max_pg_bd);
5579         DBRUN(sc->pg_empty_count = 0);
5580
5581         /* Initialize the page next pointer chain entries. */
5582         for (i = 0; i < PG_PAGES; i++) {
5583                 int j;
5584
5585                 pgbd = &sc->pg_bd_chain[i][USABLE_PG_BD_PER_PAGE];
5586
5587                 /* Check if we've reached the last page. */
5588                 if (i == (PG_PAGES - 1))
5589                         j = 0;
5590                 else
5591                         j = i + 1;
5592
5593                 /* Setup the chain page pointers. */
5594                 pgbd->rx_bd_haddr_hi = htole32(BCE_ADDR_HI(sc->pg_bd_chain_paddr[j]));
5595                 pgbd->rx_bd_haddr_lo = htole32(BCE_ADDR_LO(sc->pg_bd_chain_paddr[j]));
5596         }
5597
5598         /* Setup the MQ BIN mapping for host_pg_bidx. */
5599         if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709)     ||
5600                 (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716))
5601                 REG_WR(sc, BCE_MQ_MAP_L2_3, BCE_MQ_MAP_L2_3_DEFAULT);
5602
5603         CTX_WR(sc, GET_CID_ADDR(RX_CID), BCE_L2CTX_RX_PG_BUF_SIZE, 0);
5604
5605         /* Configure the rx_bd and page chain mbuf cluster size. */
5606         val = (sc->rx_bd_mbuf_data_len << 16) | sc->pg_bd_mbuf_alloc_size;
5607         CTX_WR(sc, GET_CID_ADDR(RX_CID), BCE_L2CTX_RX_PG_BUF_SIZE, val);
5608
5609         /* Configure the context reserved for jumbo support. */
5610         CTX_WR(sc, GET_CID_ADDR(RX_CID), BCE_L2CTX_RX_RBDC_KEY,
5611                 BCE_L2CTX_RX_RBDC_JUMBO_KEY);
5612
5613         /* Point the hardware to the first page in the page chain. */
5614         val = BCE_ADDR_HI(sc->pg_bd_chain_paddr[0]);
5615         CTX_WR(sc, GET_CID_ADDR(RX_CID), BCE_L2CTX_RX_NX_PG_BDHADDR_HI, val);
5616         val = BCE_ADDR_LO(sc->pg_bd_chain_paddr[0]);
5617         CTX_WR(sc, GET_CID_ADDR(RX_CID), BCE_L2CTX_RX_NX_PG_BDHADDR_LO, val);
5618
5619         /* Fill up the page chain. */
5620         bce_fill_pg_chain(sc);
5621
5622         for (i = 0; i < PG_PAGES; i++) {
5623                 bus_dmamap_sync(sc->pg_bd_chain_tag, sc->pg_bd_chain_map[i],
5624                     BUS_DMASYNC_PREREAD | BUS_DMASYNC_PREWRITE);
5625         }
5626
5627         DBRUNMSG(BCE_EXTREME_RECV, bce_dump_pg_chain(sc, 0, TOTAL_PG_BD));
5628         DBEXIT(BCE_VERBOSE_RESET | BCE_VERBOSE_RECV | BCE_VERBOSE_LOAD |
5629                 BCE_VERBOSE_CTX);
5630         return(rc);
5631 }
5632
5633
5634 /****************************************************************************/
5635 /* Add mbufs to the page chain until its full or an mbuf allocation error   */
5636 /* occurs.                                                                  */
5637 /*                                                                          */
5638 /* Returns:                                                                 */
5639 /*   Nothing                                                                */
5640 /****************************************************************************/
5641 static void
5642 bce_fill_pg_chain(struct bce_softc *sc)
5643 {
5644         u16 prod, prod_idx;
5645
5646         DBENTER(BCE_VERBOSE_RESET | BCE_EXTREME_RECV | BCE_VERBOSE_LOAD |
5647                 BCE_VERBOSE_CTX);
5648
5649         /* Get the page chain prodcuer index. */
5650         prod = sc->pg_prod;
5651
5652         /* Keep filling the page chain until it's full. */
5653         while (sc->free_pg_bd > 0) {
5654                 prod_idx = PG_CHAIN_IDX(prod);
5655                 if (bce_get_pg_buf(sc, NULL, &prod, &prod_idx)) {
5656                         /* Bail out if we can't add an mbuf to the chain. */
5657                         break;
5658                 }
5659                 prod = NEXT_PG_BD(prod);
5660         }
5661
5662         /* Save the page chain producer index. */
5663         sc->pg_prod = prod;
5664
5665         DBRUNIF(((prod & USABLE_RX_BD_PER_PAGE) == USABLE_RX_BD_PER_PAGE),
5666                 BCE_PRINTF("%s(): Invalid pg_prod value: 0x%04X\n",
5667                 __FUNCTION__, sc->pg_prod));
5668
5669         /*
5670          * Write the mailbox and tell the chip about
5671          * the new rx_bd's in the page chain.
5672          */
5673         REG_WR16(sc, MB_GET_CID_ADDR(RX_CID) + BCE_L2MQ_RX_HOST_PG_BDIDX,
5674                 sc->pg_prod);
5675
5676         DBEXIT(BCE_VERBOSE_RESET | BCE_EXTREME_RECV | BCE_VERBOSE_LOAD |
5677                 BCE_VERBOSE_CTX);
5678 }
5679
5680
5681 /****************************************************************************/
5682 /* Free memory and clear the RX data structures.                            */
5683 /*                                                                          */
5684 /* Returns:                                                                 */
5685 /*   Nothing.                                                               */
5686 /****************************************************************************/
5687 static void
5688 bce_free_pg_chain(struct bce_softc *sc)
5689 {
5690         int i;
5691
5692         DBENTER(BCE_VERBOSE_RESET | BCE_VERBOSE_RECV | BCE_VERBOSE_UNLOAD);
5693
5694         /* Free any mbufs still in the mbuf page chain. */
5695         for (i = 0; i < TOTAL_PG_BD; i++) {
5696                 if (sc->pg_mbuf_ptr[i] != NULL) {
5697                         if (sc->pg_mbuf_map[i] != NULL)
5698                                 bus_dmamap_sync(sc->pg_mbuf_tag, sc->pg_mbuf_map[i],
5699                                         BUS_DMASYNC_POSTREAD);
5700                         m_freem(sc->pg_mbuf_ptr[i]);
5701                         sc->pg_mbuf_ptr[i] = NULL;
5702                         DBRUN(sc->debug_pg_mbuf_alloc--);
5703                 }
5704         }
5705
5706         /* Clear each page chain pages. */
5707         for (i = 0; i < PG_PAGES; i++)
5708                 bzero((char *)sc->pg_bd_chain[i], BCE_PG_CHAIN_PAGE_SZ);
5709
5710         sc->free_pg_bd = sc->max_pg_bd;
5711
5712         /* Check if we lost any mbufs in the process. */
5713         DBRUNIF((sc->debug_pg_mbuf_alloc),
5714                 BCE_PRINTF("%s(): Memory leak! Lost %d mbufs from page chain!\n",
5715                         __FUNCTION__, sc->debug_pg_mbuf_alloc));
5716
5717         DBEXIT(BCE_VERBOSE_RESET | BCE_VERBOSE_RECV | BCE_VERBOSE_UNLOAD);
5718 }
5719 #endif /* BCE_JUMBO_HDRSPLIT */
5720
5721
5722 /****************************************************************************/
5723 /* Set media options.                                                       */
5724 /*                                                                          */
5725 /* Returns:                                                                 */
5726 /*   0 for success, positive value for failure.                             */
5727 /****************************************************************************/
5728 static int
5729 bce_ifmedia_upd(struct ifnet *ifp)
5730 {
5731         struct bce_softc *sc = ifp->if_softc;
5732
5733         DBENTER(BCE_VERBOSE);
5734
5735         BCE_LOCK(sc);
5736         bce_ifmedia_upd_locked(ifp);
5737         BCE_UNLOCK(sc);
5738
5739         DBEXIT(BCE_VERBOSE);
5740         return (0);
5741 }
5742
5743
5744 /****************************************************************************/
5745 /* Set media options.                                                       */
5746 /*                                                                          */
5747 /* Returns:                                                                 */
5748 /*   Nothing.                                                               */
5749 /****************************************************************************/
5750 static void
5751 bce_ifmedia_upd_locked(struct ifnet *ifp)
5752 {
5753         struct bce_softc *sc = ifp->if_softc;
5754         struct mii_data *mii;
5755
5756         DBENTER(BCE_VERBOSE);
5757
5758         BCE_LOCK_ASSERT(sc);
5759
5760         mii = device_get_softc(sc->bce_miibus);
5761
5762         /* Make sure the MII bus has been enumerated. */
5763         if (mii) {
5764                 sc->bce_link = 0;
5765                 if (mii->mii_instance) {
5766                         struct mii_softc *miisc;
5767
5768                         LIST_FOREACH(miisc, &mii->mii_phys, mii_list)
5769                                 mii_phy_reset(miisc);
5770                 }
5771                 mii_mediachg(mii);
5772         }
5773
5774         DBEXIT(BCE_VERBOSE);
5775 }
5776
5777
5778 /****************************************************************************/
5779 /* Reports current media status.                                            */
5780 /*                                                                          */
5781 /* Returns:                                                                 */
5782 /*   Nothing.                                                               */
5783 /****************************************************************************/
5784 static void
5785 bce_ifmedia_sts(struct ifnet *ifp, struct ifmediareq *ifmr)
5786 {
5787         struct bce_softc *sc = ifp->if_softc;
5788         struct mii_data *mii;
5789
5790         DBENTER(BCE_VERBOSE);
5791
5792         BCE_LOCK(sc);
5793
5794         mii = device_get_softc(sc->bce_miibus);
5795
5796         mii_pollstat(mii);
5797         ifmr->ifm_active = mii->mii_media_active;
5798         ifmr->ifm_status = mii->mii_media_status;
5799
5800         BCE_UNLOCK(sc);
5801
5802         DBEXIT(BCE_VERBOSE);
5803 }
5804
5805
5806 /****************************************************************************/
5807 /* Handles PHY generated interrupt events.                                  */
5808 /*                                                                          */
5809 /* Returns:                                                                 */
5810 /*   Nothing.                                                               */
5811 /****************************************************************************/
5812 static void
5813 bce_phy_intr(struct bce_softc *sc)
5814 {
5815         u32 new_link_state, old_link_state;
5816
5817         DBENTER(BCE_VERBOSE_PHY | BCE_VERBOSE_INTR);
5818
5819         new_link_state = sc->status_block->status_attn_bits &
5820                 STATUS_ATTN_BITS_LINK_STATE;
5821         old_link_state = sc->status_block->status_attn_bits_ack &
5822                 STATUS_ATTN_BITS_LINK_STATE;
5823
5824         /* Handle any changes if the link state has changed. */
5825         if (new_link_state != old_link_state) {
5826
5827                 /* Update the status_attn_bits_ack field in the status block. */
5828                 if (new_link_state) {
5829                         REG_WR(sc, BCE_PCICFG_STATUS_BIT_SET_CMD,
5830                                 STATUS_ATTN_BITS_LINK_STATE);
5831                         DBPRINT(sc, BCE_INFO_PHY, "%s(): Link is now UP.\n",
5832                                 __FUNCTION__);
5833                 }
5834                 else {
5835                         REG_WR(sc, BCE_PCICFG_STATUS_BIT_CLEAR_CMD,
5836                                 STATUS_ATTN_BITS_LINK_STATE);
5837                         DBPRINT(sc, BCE_INFO_PHY, "%s(): Link is now DOWN.\n",
5838                                 __FUNCTION__);
5839                 }
5840
5841                 /*
5842                  * Assume link is down and allow
5843                  * tick routine to update the state
5844                  * based on the actual media state.
5845                  */
5846                 sc->bce_link = 0;
5847                 callout_stop(&sc->bce_tick_callout);
5848                 bce_tick(sc);
5849         }
5850
5851         /* Acknowledge the link change interrupt. */
5852         REG_WR(sc, BCE_EMAC_STATUS, BCE_EMAC_STATUS_LINK_CHANGE);
5853
5854         DBEXIT(BCE_VERBOSE_PHY | BCE_VERBOSE_INTR);
5855 }
5856
5857
5858 /****************************************************************************/
5859 /* Reads the receive consumer value from the status block (skipping over    */
5860 /* chain page pointer if necessary).                                        */
5861 /*                                                                          */
5862 /* Returns:                                                                 */
5863 /*   hw_cons                                                                */
5864 /****************************************************************************/
5865 static inline u16
5866 bce_get_hw_rx_cons(struct bce_softc *sc)
5867 {
5868         u16 hw_cons;
5869
5870         rmb();
5871         hw_cons = sc->status_block->status_rx_quick_consumer_index0;
5872         if ((hw_cons & USABLE_RX_BD_PER_PAGE) == USABLE_RX_BD_PER_PAGE)
5873                 hw_cons++;
5874
5875         return hw_cons;
5876 }
5877
5878 /****************************************************************************/
5879 /* Handles received frame interrupt events.                                 */
5880 /*                                                                          */
5881 /* Returns:                                                                 */
5882 /*   Nothing.                                                               */
5883 /****************************************************************************/
5884 static void
5885 bce_rx_intr(struct bce_softc *sc)
5886 {
5887         struct ifnet *ifp = sc->bce_ifp;
5888         struct l2_fhdr *l2fhdr;
5889         unsigned int pkt_len;
5890         u16 sw_rx_cons, sw_rx_cons_idx, hw_rx_cons;
5891         u32 status;
5892 #ifdef BCE_JUMBO_HDRSPLIT
5893         unsigned int rem_len;
5894         u16 sw_pg_cons, sw_pg_cons_idx;
5895 #endif
5896
5897         DBENTER(BCE_VERBOSE_RECV | BCE_VERBOSE_INTR);
5898         DBRUN(sc->rx_interrupts++);
5899         DBPRINT(sc, BCE_EXTREME_RECV, "%s(enter): rx_prod = 0x%04X, "
5900                 "rx_cons = 0x%04X, rx_prod_bseq = 0x%08X\n",
5901                 __FUNCTION__, sc->rx_prod, sc->rx_cons, sc->rx_prod_bseq);
5902
5903         /* Prepare the RX chain pages to be accessed by the host CPU. */
5904         for (int i = 0; i < RX_PAGES; i++)
5905                 bus_dmamap_sync(sc->rx_bd_chain_tag,
5906                     sc->rx_bd_chain_map[i], BUS_DMASYNC_POSTREAD);
5907
5908 #ifdef BCE_JUMBO_HDRSPLIT
5909         /* Prepare the page chain pages to be accessed by the host CPU. */
5910         for (int i = 0; i < PG_PAGES; i++)
5911                 bus_dmamap_sync(sc->pg_bd_chain_tag,
5912                     sc->pg_bd_chain_map[i], BUS_DMASYNC_POSTREAD);
5913 #endif
5914
5915         /* Get the hardware's view of the RX consumer index. */
5916         hw_rx_cons = sc->hw_rx_cons = bce_get_hw_rx_cons(sc);
5917
5918         /* Get working copies of the driver's view of the consumer indices. */
5919         sw_rx_cons = sc->rx_cons;
5920 #ifdef BCE_JUMBO_HDRSPLIT
5921         sw_pg_cons = sc->pg_cons;
5922 #endif
5923
5924         /* Update some debug statistics counters */
5925         DBRUNIF((sc->free_rx_bd < sc->rx_low_watermark),
5926                 sc->rx_low_watermark = sc->free_rx_bd);
5927         DBRUNIF((sc->free_rx_bd == sc->max_rx_bd), sc->rx_empty_count++);
5928
5929         /* Scan through the receive chain as long as there is work to do */
5930         /* ToDo: Consider setting a limit on the number of packets processed. */
5931         rmb();
5932         while (sw_rx_cons != hw_rx_cons) {
5933                 struct mbuf *m0;
5934
5935                 /* Convert the producer/consumer indices to an actual rx_bd index. */
5936                 sw_rx_cons_idx = RX_CHAIN_IDX(sw_rx_cons);
5937
5938                 /* Unmap the mbuf from DMA space. */
5939                 bus_dmamap_sync(sc->rx_mbuf_tag, sc->rx_mbuf_map[sw_rx_cons_idx],
5940                     BUS_DMASYNC_POSTREAD);
5941                 bus_dmamap_unload(sc->rx_mbuf_tag,
5942                     sc->rx_mbuf_map[sw_rx_cons_idx]);
5943
5944                 /* Remove the mbuf from the RX chain. */
5945                 m0 = sc->rx_mbuf_ptr[sw_rx_cons_idx];
5946                 sc->rx_mbuf_ptr[sw_rx_cons_idx] = NULL;
5947                 DBRUN(sc->debug_rx_mbuf_alloc--);
5948                 sc->free_rx_bd++;
5949
5950         if(m0 == NULL) {
5951             DBPRINT(sc, BCE_EXTREME_RECV, "%s(): Oops! Empty mbuf pointer "
5952                 "found in sc->rx_mbuf_ptr[0x%04X]!\n",
5953                 __FUNCTION__, sw_rx_cons_idx);
5954             goto bce_rx_int_next_rx;
5955         }
5956
5957         /*
5958          * Frames received on the NetXteme II are prepended     with an
5959          * l2_fhdr structure which provides status information about
5960          * the received frame (including VLAN tags and checksum info).
5961          * The frames are also automatically adjusted to align the IP
5962          * header (i.e. two null bytes are inserted before the Ethernet
5963          * header).  As a result the data DMA'd by the controller into
5964          * the mbuf is as follows:
5965          * 
5966          * +---------+-----+---------------------+-----+
5967          * | l2_fhdr | pad | packet data         | FCS |
5968          * +---------+-----+---------------------+-----+
5969          * 
5970          * The l2_fhdr needs to be checked and skipped and the FCS needs
5971          * to be stripped before sending the packet up the stack.
5972          */
5973                 l2fhdr  = mtod(m0, struct l2_fhdr *);
5974
5975                 /* Get the packet data + FCS length and the status. */
5976                 pkt_len = l2fhdr->l2_fhdr_pkt_len;
5977                 status  = l2fhdr->l2_fhdr_status;
5978
5979                 /*
5980                  * Skip over the l2_fhdr and pad, resulting in the
5981                  * following data in the mbuf:
5982                  * +---------------------+-----+
5983                  * | packet data         | FCS |
5984                  * +---------------------+-----+
5985                  */
5986                 m_adj(m0, sizeof(struct l2_fhdr) + ETHER_ALIGN);
5987
5988 #ifdef BCE_JUMBO_HDRSPLIT
5989                 /*
5990                  * Check whether the received frame fits in a single
5991                  * mbuf or not (i.e. packet data + FCS <=
5992                  * sc->rx_bd_mbuf_data_len bytes).
5993                  */
5994                 if (pkt_len > m0->m_len) {
5995                         /*
5996                          * The received frame is larger than a single mbuf.
5997                          * If the frame was a TCP frame then only the TCP
5998                          * header is placed in the mbuf, the remaining
5999                          * payload (including FCS) is placed in the page
6000                          * chain, the SPLIT flag is set, and the header
6001                          * length is placed in the IP checksum field.
6002                          * If the frame is not a TCP frame then the mbuf
6003                          * is filled and the remaining bytes are placed
6004                          * in the page chain.
6005                          */
6006
6007                         DBPRINT(sc, BCE_INFO_RECV, "%s(): Found a large packet.\n",
6008                                 __FUNCTION__);
6009
6010                         /*
6011                          * When the page chain is enabled and the TCP
6012                          * header has been split from the TCP payload,
6013                          * the ip_xsum structure will reflect the length
6014                          * of the TCP header, not the IP checksum.  Set
6015                          * the packet length of the mbuf accordingly.
6016                          */
6017                         if (status & L2_FHDR_STATUS_SPLIT)
6018                                 m0->m_len = l2fhdr->l2_fhdr_ip_xsum;
6019
6020                         rem_len = pkt_len - m0->m_len;
6021
6022                         /* Pull mbufs off the page chain for the remaining data. */
6023                         while (rem_len > 0) {
6024                                 struct mbuf *m_pg;
6025
6026                                 sw_pg_cons_idx = PG_CHAIN_IDX(sw_pg_cons);
6027
6028                                 /* Remove the mbuf from the page chain. */
6029                                 m_pg = sc->pg_mbuf_ptr[sw_pg_cons_idx];
6030                                 sc->pg_mbuf_ptr[sw_pg_cons_idx] = NULL;
6031                                 DBRUN(sc->debug_pg_mbuf_alloc--);
6032                                 sc->free_pg_bd++;
6033
6034                                 /* Unmap the page chain mbuf from DMA space. */
6035                                 bus_dmamap_sync(sc->pg_mbuf_tag,
6036                                         sc->pg_mbuf_map[sw_pg_cons_idx],
6037                                         BUS_DMASYNC_POSTREAD);
6038                                 bus_dmamap_unload(sc->pg_mbuf_tag,
6039                                         sc->pg_mbuf_map[sw_pg_cons_idx]);
6040
6041                                 /* Adjust the mbuf length. */
6042                                 if (rem_len < m_pg->m_len) {
6043                                         /* The mbuf chain is complete. */
6044                                         m_pg->m_len = rem_len;
6045                                         rem_len = 0;
6046                                 } else {
6047                                         /* More packet data is waiting. */
6048                                         rem_len -= m_pg->m_len;
6049                                 }
6050
6051                                 /* Concatenate the mbuf cluster to the mbuf. */
6052                                 m_cat(m0, m_pg);
6053
6054                                 sw_pg_cons = NEXT_PG_BD(sw_pg_cons);
6055                         }
6056
6057                         /* Set the total packet length. */
6058                         m0->m_pkthdr.len = pkt_len;
6059
6060                 } else {
6061                         /*
6062                          * The received packet is small and fits in a
6063                          * single mbuf (i.e. the l2_fhdr + pad + packet +
6064                          * FCS <= MHLEN).  In other words, the packet is
6065                          * 154 bytes or less in size.
6066                          */
6067
6068                         DBPRINT(sc, BCE_INFO_RECV, "%s(): Found a small packet.\n",
6069                                 __FUNCTION__);
6070
6071                         /* Set the total packet length. */
6072                         m0->m_pkthdr.len = m0->m_len = pkt_len;
6073                 }
6074 #else
6075         /* Set the total packet length. */
6076                 m0->m_pkthdr.len = m0->m_len = pkt_len;
6077 #endif
6078
6079                 /* Remove the trailing Ethernet FCS. */
6080                 m_adj(m0, -ETHER_CRC_LEN);
6081
6082                 /* Check that the resulting mbuf chain is valid. */
6083                 DBRUN(m_sanity(m0, FALSE));
6084                 DBRUNIF(((m0->m_len < ETHER_HDR_LEN) |
6085                         (m0->m_pkthdr.len > BCE_MAX_JUMBO_ETHER_MTU_VLAN)),
6086                         BCE_PRINTF("Invalid Ethernet frame size!\n");
6087                         m_print(m0, 128));
6088
6089                 DBRUNIF(DB_RANDOMTRUE(l2fhdr_error_sim_control),
6090                         BCE_PRINTF("Simulating l2_fhdr status error.\n");
6091                         sc->l2fhdr_error_sim_count++;
6092                         status = status | L2_FHDR_ERRORS_PHY_DECODE);
6093
6094                 /* Check the received frame for errors. */
6095                 if (status & (L2_FHDR_ERRORS_BAD_CRC |
6096                         L2_FHDR_ERRORS_PHY_DECODE | L2_FHDR_ERRORS_ALIGNMENT |
6097                         L2_FHDR_ERRORS_TOO_SHORT  | L2_FHDR_ERRORS_GIANT_FRAME)) {
6098
6099                         /* Log the error and release the mbuf. */
6100                         ifp->if_ierrors++;
6101                         sc->l2fhdr_error_count++;
6102
6103                         m_freem(m0);
6104                         m0 = NULL;
6105                         goto bce_rx_int_next_rx;
6106                 }
6107
6108                 /* Send the packet to the appropriate interface. */
6109                 m0->m_pkthdr.rcvif = ifp;
6110
6111                 /* Assume no hardware checksum. */
6112                 m0->m_pkthdr.csum_flags = 0;
6113
6114                 /* Validate the checksum if offload enabled. */
6115                 if (ifp->if_capenable & IFCAP_RXCSUM) {
6116
6117                         /* Check for an IP datagram. */
6118                         if (!(status & L2_FHDR_STATUS_SPLIT) &&
6119                                 (status & L2_FHDR_STATUS_IP_DATAGRAM)) {
6120                                 m0->m_pkthdr.csum_flags |= CSUM_IP_CHECKED;
6121
6122                                 /* Check if the IP checksum is valid. */
6123                                 if ((l2fhdr->l2_fhdr_ip_xsum ^ 0xffff) == 0)
6124                                         m0->m_pkthdr.csum_flags |= CSUM_IP_VALID;
6125                         }
6126
6127                         /* Check for a valid TCP/UDP frame. */
6128                         if (status & (L2_FHDR_STATUS_TCP_SEGMENT |
6129                                 L2_FHDR_STATUS_UDP_DATAGRAM)) {
6130
6131                                 /* Check for a good TCP/UDP checksum. */
6132                                 if ((status & (L2_FHDR_ERRORS_TCP_XSUM |
6133                                               L2_FHDR_ERRORS_UDP_XSUM)) == 0) {
6134                                         m0->m_pkthdr.csum_data =
6135                                             l2fhdr->l2_fhdr_tcp_udp_xsum;
6136                                         m0->m_pkthdr.csum_flags |= (CSUM_DATA_VALID
6137                                                 | CSUM_PSEUDO_HDR);
6138                                 }
6139                         }
6140                 }
6141
6142                 /* Attach the VLAN tag. */
6143                 if (status & L2_FHDR_STATUS_L2_VLAN_TAG) {
6144 #if __FreeBSD_version < 700000
6145                         VLAN_INPUT_TAG(ifp, m0, l2fhdr->l2_fhdr_vlan_tag, continue);
6146 #else
6147                         m0->m_pkthdr.ether_vtag = l2fhdr->l2_fhdr_vlan_tag;
6148                         m0->m_flags |= M_VLANTAG;
6149 #endif
6150                 }
6151
6152                 /* Increment received packet statistics. */
6153                 ifp->if_ipackets++;
6154
6155 bce_rx_int_next_rx:
6156                 sw_rx_cons = NEXT_RX_BD(sw_rx_cons);
6157
6158                 /* If we have a packet, pass it up the stack */
6159                 if (m0) {
6160                         /* Make sure we don't lose our place when we release the lock. */
6161                         sc->rx_cons = sw_rx_cons;
6162 #ifdef BCE_JUMBO_HDRSPLIT
6163                         sc->pg_cons = sw_pg_cons;
6164 #endif
6165
6166                         BCE_UNLOCK(sc);
6167                         (*ifp->if_input)(ifp, m0);
6168                         BCE_LOCK(sc);
6169
6170                         /* Recover our place. */
6171                         sw_rx_cons = sc->rx_cons;
6172 #ifdef BCE_JUMBO_HDRSPLIT
6173                         sw_pg_cons = sc->pg_cons;
6174 #endif
6175                 }
6176
6177                 /* Refresh hw_cons to see if there's new work */
6178                 if (sw_rx_cons == hw_rx_cons)
6179                         hw_rx_cons = sc->hw_rx_cons = bce_get_hw_rx_cons(sc);
6180         }
6181
6182         /* No new packets to process.  Refill the RX and page chains and exit. */
6183 #ifdef BCE_JUMBO_HDRSPLIT
6184         sc->pg_cons = sw_pg_cons;
6185         bce_fill_pg_chain(sc);
6186 #endif
6187
6188         sc->rx_cons = sw_rx_cons;
6189         bce_fill_rx_chain(sc);
6190
6191         /* Prepare the page chain pages to be accessed by the NIC. */
6192         for (int i = 0; i < RX_PAGES; i++)
6193                 bus_dmamap_sync(sc->rx_bd_chain_tag,
6194                     sc->rx_bd_chain_map[i], BUS_DMASYNC_PREWRITE);
6195
6196 #ifdef BCE_JUMBO_HDRSPLIT
6197         for (int i = 0; i < PG_PAGES; i++)
6198                 bus_dmamap_sync(sc->pg_bd_chain_tag,
6199                     sc->pg_bd_chain_map[i], BUS_DMASYNC_PREWRITE);
6200 #endif
6201
6202         DBPRINT(sc, BCE_EXTREME_RECV, "%s(exit): rx_prod = 0x%04X, "
6203                 "rx_cons = 0x%04X, rx_prod_bseq = 0x%08X\n",
6204                 __FUNCTION__, sc->rx_prod, sc->rx_cons, sc->rx_prod_bseq);
6205         DBEXIT(BCE_VERBOSE_RECV | BCE_VERBOSE_INTR);
6206 }
6207
6208
6209 /****************************************************************************/
6210 /* Reads the transmit consumer value from the status block (skipping over   */
6211 /* chain page pointer if necessary).                                        */
6212 /*                                                                          */
6213 /* Returns:                                                                 */
6214 /*   hw_cons                                                                */
6215 /****************************************************************************/
6216 static inline u16
6217 bce_get_hw_tx_cons(struct bce_softc *sc)
6218 {
6219         u16 hw_cons;
6220
6221         mb();
6222         hw_cons = sc->status_block->status_tx_quick_consumer_index0;
6223         if ((hw_cons & USABLE_TX_BD_PER_PAGE) == USABLE_TX_BD_PER_PAGE)
6224                 hw_cons++;
6225
6226         return hw_cons;
6227 }
6228
6229
6230 /****************************************************************************/
6231 /* Handles transmit completion interrupt events.                            */
6232 /*                                                                          */
6233 /* Returns:                                                                 */
6234 /*   Nothing.                                                               */
6235 /****************************************************************************/
6236 static void
6237 bce_tx_intr(struct bce_softc *sc)
6238 {
6239         struct ifnet *ifp = sc->bce_ifp;
6240         u16 hw_tx_cons, sw_tx_cons, sw_tx_chain_cons;
6241
6242         DBENTER(BCE_VERBOSE_SEND | BCE_VERBOSE_INTR);
6243         DBRUN(sc->tx_interrupts++);
6244         DBPRINT(sc, BCE_EXTREME_SEND, "%s(enter): tx_prod = 0x%04X, "
6245                 "tx_cons = 0x%04X, tx_prod_bseq = 0x%08X\n",
6246                 __FUNCTION__, sc->tx_prod, sc->tx_cons, sc->tx_prod_bseq);
6247
6248         BCE_LOCK_ASSERT(sc);
6249
6250         /* Get the hardware's view of the TX consumer index. */
6251         hw_tx_cons = sc->hw_tx_cons = bce_get_hw_tx_cons(sc);
6252         sw_tx_cons = sc->tx_cons;
6253
6254         /* Prevent speculative reads from getting ahead of the status block. */
6255         bus_space_barrier(sc->bce_btag, sc->bce_bhandle, 0, 0,
6256                 BUS_SPACE_BARRIER_READ);
6257
6258         /* Cycle through any completed TX chain page entries. */
6259         while (sw_tx_cons != hw_tx_cons) {
6260 #ifdef BCE_DEBUG
6261                 struct tx_bd *txbd = NULL;
6262 #endif
6263                 sw_tx_chain_cons = TX_CHAIN_IDX(sw_tx_cons);
6264
6265                 DBPRINT(sc, BCE_INFO_SEND,
6266                         "%s(): hw_tx_cons = 0x%04X, sw_tx_cons = 0x%04X, "
6267                         "sw_tx_chain_cons = 0x%04X\n",
6268                         __FUNCTION__, hw_tx_cons, sw_tx_cons, sw_tx_chain_cons);
6269
6270                 DBRUNIF((sw_tx_chain_cons > MAX_TX_BD),
6271                         BCE_PRINTF("%s(%d): TX chain consumer out of range! "
6272                                 " 0x%04X > 0x%04X\n", __FILE__, __LINE__, sw_tx_chain_cons,
6273                                 (int) MAX_TX_BD);
6274                         bce_breakpoint(sc));
6275
6276                 DBRUN(txbd = &sc->tx_bd_chain[TX_PAGE(sw_tx_chain_cons)]
6277                                 [TX_IDX(sw_tx_chain_cons)]);
6278
6279                 DBRUNIF((txbd == NULL),
6280                         BCE_PRINTF("%s(%d): Unexpected NULL tx_bd[0x%04X]!\n",
6281                                 __FILE__, __LINE__, sw_tx_chain_cons);
6282                         bce_breakpoint(sc));
6283
6284                 DBRUNMSG(BCE_INFO_SEND, BCE_PRINTF("%s(): ", __FUNCTION__);
6285                         bce_dump_txbd(sc, sw_tx_chain_cons, txbd));
6286
6287                 /*
6288                  * Free the associated mbuf. Remember
6289                  * that only the last tx_bd of a packet
6290                  * has an mbuf pointer and DMA map.
6291                  */
6292                 if (sc->tx_mbuf_ptr[sw_tx_chain_cons] != NULL) {
6293
6294                         /* Validate that this is the last tx_bd. */
6295                         DBRUNIF((!(txbd->tx_bd_flags & TX_BD_FLAGS_END)),
6296                                 BCE_PRINTF("%s(%d): tx_bd END flag not set but "
6297                                 "txmbuf == NULL!\n", __FILE__, __LINE__);
6298                                 bce_breakpoint(sc));
6299
6300                         DBRUNMSG(BCE_INFO_SEND,
6301                                 BCE_PRINTF("%s(): Unloading map/freeing mbuf "
6302                                         "from tx_bd[0x%04X]\n", __FUNCTION__, sw_tx_chain_cons));
6303
6304                         /* Unmap the mbuf. */
6305                         bus_dmamap_unload(sc->tx_mbuf_tag,
6306                             sc->tx_mbuf_map[sw_tx_chain_cons]);
6307
6308                         /* Free the mbuf. */
6309                         m_freem(sc->tx_mbuf_ptr[sw_tx_chain_cons]);
6310                         sc->tx_mbuf_ptr[sw_tx_chain_cons] = NULL;
6311                         DBRUN(sc->debug_tx_mbuf_alloc--);
6312
6313                         ifp->if_opackets++;
6314                 }
6315
6316                 sc->used_tx_bd--;
6317                 sw_tx_cons = NEXT_TX_BD(sw_tx_cons);
6318
6319                 /* Refresh hw_cons to see if there's new work. */
6320                 hw_tx_cons = sc->hw_tx_cons = bce_get_hw_tx_cons(sc);
6321
6322                 /* Prevent speculative reads from getting ahead of the status block. */
6323                 bus_space_barrier(sc->bce_btag, sc->bce_bhandle, 0, 0,
6324                         BUS_SPACE_BARRIER_READ);
6325         }
6326
6327         /* Clear the TX timeout timer. */
6328         sc->watchdog_timer = 0;
6329
6330         /* Clear the tx hardware queue full flag. */
6331         if (sc->used_tx_bd < sc->max_tx_bd) {
6332                 DBRUNIF((ifp->if_drv_flags & IFF_DRV_OACTIVE),
6333                         DBPRINT(sc, BCE_INFO_SEND,
6334                                 "%s(): Open TX chain! %d/%d (used/total)\n",
6335                                 __FUNCTION__, sc->used_tx_bd, sc->max_tx_bd));
6336                 ifp->if_drv_flags &= ~IFF_DRV_OACTIVE;
6337         }
6338
6339         sc->tx_cons = sw_tx_cons;
6340
6341         DBPRINT(sc, BCE_EXTREME_SEND, "%s(exit): tx_prod = 0x%04X, "
6342                 "tx_cons = 0x%04X, tx_prod_bseq = 0x%08X\n",
6343                 __FUNCTION__, sc->tx_prod, sc->tx_cons, sc->tx_prod_bseq);
6344         DBEXIT(BCE_VERBOSE_SEND | BCE_VERBOSE_INTR);
6345 }
6346
6347
6348 /****************************************************************************/
6349 /* Disables interrupt generation.                                           */
6350 /*                                                                          */
6351 /* Returns:                                                                 */
6352 /*   Nothing.                                                               */
6353 /****************************************************************************/
6354 static void
6355 bce_disable_intr(struct bce_softc *sc)
6356 {
6357         DBENTER(BCE_VERBOSE_INTR);
6358
6359         REG_WR(sc, BCE_PCICFG_INT_ACK_CMD, BCE_PCICFG_INT_ACK_CMD_MASK_INT);
6360         REG_RD(sc, BCE_PCICFG_INT_ACK_CMD);
6361
6362         DBEXIT(BCE_VERBOSE_INTR);
6363 }
6364
6365
6366 /****************************************************************************/
6367 /* Enables interrupt generation.                                            */
6368 /*                                                                          */
6369 /* Returns:                                                                 */
6370 /*   Nothing.                                                               */
6371 /****************************************************************************/
6372 static void
6373 bce_enable_intr(struct bce_softc *sc, int coal_now)
6374 {
6375         DBENTER(BCE_VERBOSE_INTR);
6376
6377         REG_WR(sc, BCE_PCICFG_INT_ACK_CMD,
6378                BCE_PCICFG_INT_ACK_CMD_INDEX_VALID |
6379                BCE_PCICFG_INT_ACK_CMD_MASK_INT | sc->last_status_idx);
6380
6381         REG_WR(sc, BCE_PCICFG_INT_ACK_CMD,
6382                BCE_PCICFG_INT_ACK_CMD_INDEX_VALID | sc->last_status_idx);
6383
6384         /* Force an immediate interrupt (whether there is new data or not). */
6385         if (coal_now)
6386                 REG_WR(sc, BCE_HC_COMMAND, sc->hc_command | BCE_HC_COMMAND_COAL_NOW);
6387
6388         DBEXIT(BCE_VERBOSE_INTR);
6389 }
6390
6391
6392 /****************************************************************************/
6393 /* Handles controller initialization.                                       */
6394 /*                                                                          */
6395 /* Returns:                                                                 */
6396 /*   Nothing.                                                               */
6397 /****************************************************************************/
6398 static void
6399 bce_init_locked(struct bce_softc *sc)
6400 {
6401         struct ifnet *ifp;
6402         u32 ether_mtu = 0;
6403
6404         DBENTER(BCE_VERBOSE_RESET);
6405
6406         BCE_LOCK_ASSERT(sc);
6407
6408         ifp = sc->bce_ifp;
6409
6410         /* Check if the driver is still running and bail out if it is. */
6411         if (ifp->if_drv_flags & IFF_DRV_RUNNING)
6412                 goto bce_init_locked_exit;
6413
6414         bce_stop(sc);
6415
6416         if (bce_reset(sc, BCE_DRV_MSG_CODE_RESET)) {
6417                 BCE_PRINTF("%s(%d): Controller reset failed!\n",
6418                         __FILE__, __LINE__);
6419                 goto bce_init_locked_exit;
6420         }
6421
6422         if (bce_chipinit(sc)) {
6423                 BCE_PRINTF("%s(%d): Controller initialization failed!\n",
6424                         __FILE__, __LINE__);
6425                 goto bce_init_locked_exit;
6426         }
6427
6428         if (bce_blockinit(sc)) {
6429                 BCE_PRINTF("%s(%d): Block initialization failed!\n",
6430                         __FILE__, __LINE__);
6431                 goto bce_init_locked_exit;
6432         }
6433
6434         /* Load our MAC address. */
6435         bcopy(IF_LLADDR(sc->bce_ifp), sc->eaddr, ETHER_ADDR_LEN);
6436         bce_set_mac_addr(sc);
6437
6438         /*
6439          * Calculate and program the hardware Ethernet MTU
6440          * size. Be generous on the receive if we have room.
6441          */
6442 #ifdef BCE_JUMBO_HDRSPLIT
6443         if (ifp->if_mtu <= (sc->rx_bd_mbuf_data_len + sc->pg_bd_mbuf_alloc_size))
6444                 ether_mtu = sc->rx_bd_mbuf_data_len + sc->pg_bd_mbuf_alloc_size;
6445 #else
6446         if (ifp->if_mtu <= sc->rx_bd_mbuf_data_len)
6447                 ether_mtu = sc->rx_bd_mbuf_data_len;
6448 #endif
6449         else
6450                 ether_mtu = ifp->if_mtu;
6451
6452         ether_mtu += ETHER_HDR_LEN + ETHER_VLAN_ENCAP_LEN + ETHER_CRC_LEN;
6453
6454         DBPRINT(sc, BCE_INFO_MISC, "%s(): setting h/w mtu = %d\n", __FUNCTION__,
6455                 ether_mtu);
6456
6457         /* Program the mtu, enabling jumbo frame support if necessary. */
6458         if (ether_mtu > (ETHER_MAX_LEN + ETHER_VLAN_ENCAP_LEN))
6459                 REG_WR(sc, BCE_EMAC_RX_MTU_SIZE,
6460                         min(ether_mtu, BCE_MAX_JUMBO_ETHER_MTU) |
6461                         BCE_EMAC_RX_MTU_SIZE_JUMBO_ENA);
6462         else
6463                 REG_WR(sc, BCE_EMAC_RX_MTU_SIZE, ether_mtu);
6464
6465         DBPRINT(sc, BCE_INFO_LOAD,
6466                 "%s(): rx_bd_mbuf_alloc_size = %d, rx_bce_mbuf_data_len = %d, "
6467                 "rx_bd_mbuf_align_pad = %d\n", __FUNCTION__, 
6468                 sc->rx_bd_mbuf_alloc_size, sc->rx_bd_mbuf_data_len,
6469                 sc->rx_bd_mbuf_align_pad);
6470
6471         /* Program appropriate promiscuous/multicast filtering. */
6472         bce_set_rx_mode(sc);
6473
6474 #ifdef BCE_JUMBO_HDRSPLIT
6475         DBPRINT(sc, BCE_INFO_LOAD, "%s(): pg_bd_mbuf_alloc_size = %d\n",
6476                 __FUNCTION__, sc->pg_bd_mbuf_alloc_size);
6477
6478         /* Init page buffer descriptor chain. */
6479         bce_init_pg_chain(sc);
6480 #endif
6481
6482         /* Init RX buffer descriptor chain. */
6483         bce_init_rx_chain(sc);
6484
6485         /* Init TX buffer descriptor chain. */
6486         bce_init_tx_chain(sc);
6487
6488         /* Enable host interrupts. */
6489         bce_enable_intr(sc, 1);
6490
6491         bce_ifmedia_upd_locked(ifp);
6492
6493         /* Let the OS know the driver is up and running. */
6494         ifp->if_drv_flags |= IFF_DRV_RUNNING;
6495         ifp->if_drv_flags &= ~IFF_DRV_OACTIVE;
6496
6497         callout_reset(&sc->bce_tick_callout, hz, bce_tick, sc);
6498
6499 bce_init_locked_exit:
6500         DBEXIT(BCE_VERBOSE_RESET);
6501 }
6502
6503
6504 /****************************************************************************/
6505 /* Initialize the controller just enough so that any management firmware    */
6506 /* running on the device will continue to operate correctly.                */
6507 /*                                                                          */
6508 /* Returns:                                                                 */
6509 /*   Nothing.                                                               */
6510 /****************************************************************************/
6511 static void
6512 bce_mgmt_init_locked(struct bce_softc *sc)
6513 {
6514         struct ifnet *ifp;
6515
6516         DBENTER(BCE_VERBOSE_RESET);
6517
6518         BCE_LOCK_ASSERT(sc);
6519
6520         /* Bail out if management firmware is not running. */
6521         if (!(sc->bce_flags & BCE_MFW_ENABLE_FLAG)) {
6522                 DBPRINT(sc, BCE_VERBOSE_SPECIAL,
6523                         "No management firmware running...\n");
6524                 goto bce_mgmt_init_locked_exit;
6525         }
6526
6527         ifp = sc->bce_ifp;
6528
6529         /* Enable all critical blocks in the MAC. */
6530         REG_WR(sc, BCE_MISC_ENABLE_SET_BITS, BCE_MISC_ENABLE_DEFAULT);
6531         REG_RD(sc, BCE_MISC_ENABLE_SET_BITS);
6532         DELAY(20);
6533
6534         bce_ifmedia_upd_locked(ifp);
6535
6536 bce_mgmt_init_locked_exit:
6537         DBEXIT(BCE_VERBOSE_RESET);
6538 }
6539
6540
6541 /****************************************************************************/
6542 /* Handles controller initialization when called from an unlocked routine.  */
6543 /*                                                                          */
6544 /* Returns:                                                                 */
6545 /*   Nothing.                                                               */
6546 /****************************************************************************/
6547 static void
6548 bce_init(void *xsc)
6549 {
6550         struct bce_softc *sc = xsc;
6551
6552         DBENTER(BCE_VERBOSE_RESET);
6553
6554         BCE_LOCK(sc);
6555         bce_init_locked(sc);
6556         BCE_UNLOCK(sc);
6557
6558         DBEXIT(BCE_VERBOSE_RESET);
6559 }
6560
6561
6562 /****************************************************************************/
6563 /* Encapsultes an mbuf cluster into the tx_bd chain structure and makes the */
6564 /* memory visible to the controller.                                        */
6565 /*                                                                          */
6566 /* Returns:                                                                 */
6567 /*   0 for success, positive value for failure.                             */
6568 /* Modified:                                                                */
6569 /*   m_head: May be set to NULL if MBUF is excessively fragmented.          */
6570 /****************************************************************************/
6571 static int
6572 bce_tx_encap(struct bce_softc *sc, struct mbuf **m_head)
6573 {
6574         bus_dma_segment_t segs[BCE_MAX_SEGMENTS];
6575         bus_dmamap_t map;
6576         struct tx_bd *txbd = NULL;
6577         struct mbuf *m0;
6578         struct ether_vlan_header *eh;
6579         struct ip *ip;
6580         struct tcphdr *th;
6581         u16 prod, chain_prod, etype, mss = 0, vlan_tag = 0, flags = 0;
6582         u32 prod_bseq;
6583         int hdr_len = 0, e_hlen = 0, ip_hlen = 0, tcp_hlen = 0, ip_len = 0;
6584
6585 #ifdef BCE_DEBUG
6586         u16 debug_prod;
6587 #endif
6588         int i, error, nsegs, rc = 0;
6589
6590         DBENTER(BCE_VERBOSE_SEND);
6591         DBPRINT(sc, BCE_INFO_SEND,
6592                 "%s(enter): tx_prod = 0x%04X, tx_chain_prod = %04X, "
6593                 "tx_prod_bseq = 0x%08X\n",
6594                 __FUNCTION__, sc->tx_prod, (u16) TX_CHAIN_IDX(sc->tx_prod),
6595                 sc->tx_prod_bseq);
6596
6597         /* Transfer any checksum offload flags to the bd. */
6598         m0 = *m_head;
6599         if (m0->m_pkthdr.csum_flags) {
6600                 if (m0->m_pkthdr.csum_flags & CSUM_IP)
6601                         flags |= TX_BD_FLAGS_IP_CKSUM;
6602                 if (m0->m_pkthdr.csum_flags & (CSUM_TCP | CSUM_UDP))
6603                         flags |= TX_BD_FLAGS_TCP_UDP_CKSUM;
6604                 if (m0->m_pkthdr.csum_flags & CSUM_TSO) {
6605                         /* For TSO the controller needs two pieces of info, */
6606                         /* the MSS and the IP+TCP options length.           */
6607                         mss = htole16(m0->m_pkthdr.tso_segsz);
6608
6609                         /* Map the header and find the Ethernet type & header length */
6610                         eh = mtod(m0, struct ether_vlan_header *);
6611                         if (eh->evl_encap_proto == htons(ETHERTYPE_VLAN)) {
6612                                 etype = ntohs(eh->evl_proto);
6613                                 e_hlen = ETHER_HDR_LEN + ETHER_VLAN_ENCAP_LEN;
6614                         } else {
6615                                 etype = ntohs(eh->evl_encap_proto);
6616                                 e_hlen = ETHER_HDR_LEN;
6617                         }
6618
6619                         /* Check for supported TSO Ethernet types (only IPv4 for now) */
6620                         switch (etype) {
6621                                 case ETHERTYPE_IP:
6622                                         ip = (struct ip *)(m0->m_data + e_hlen);
6623
6624                                         /* TSO only supported for TCP protocol */
6625                                         if (ip->ip_p != IPPROTO_TCP) {
6626                                                 BCE_PRINTF("%s(%d): TSO enabled for non-TCP frame!.\n",
6627                                                         __FILE__, __LINE__);
6628                                                 goto bce_tx_encap_skip_tso;
6629                                         }
6630
6631                                         /* Get IP header length in bytes (min 20) */
6632                                         ip_hlen = ip->ip_hl << 2;
6633
6634                                         /* Get the TCP header length in bytes (min 20) */
6635                                         th = (struct tcphdr *)((caddr_t)ip + ip_hlen);
6636                                         tcp_hlen = (th->th_off << 2);
6637
6638                                         /* IP header length and checksum will be calc'd by hardware */
6639                                         ip_len = ip->ip_len;
6640                                         ip->ip_len = 0;
6641                                         ip->ip_sum = 0;
6642                                         break;
6643                                 case ETHERTYPE_IPV6:
6644                                         BCE_PRINTF("%s(%d): TSO over IPv6 not supported!.\n",
6645                                                 __FILE__, __LINE__);
6646                                         goto bce_tx_encap_skip_tso;
6647                                 default:
6648                                         BCE_PRINTF("%s(%d): TSO enabled for unsupported protocol!.\n",
6649                                                 __FILE__, __LINE__);
6650                                         goto bce_tx_encap_skip_tso;
6651                         }
6652
6653                         hdr_len = e_hlen + ip_hlen + tcp_hlen;
6654
6655                         DBPRINT(sc, BCE_EXTREME_SEND,
6656                                 "%s(): hdr_len = %d, e_hlen = %d, ip_hlen = %d, tcp_hlen = %d, ip_len = %d\n",
6657                                  __FUNCTION__, hdr_len, e_hlen, ip_hlen, tcp_hlen, ip_len);
6658
6659                         /* Set the LSO flag in the TX BD */
6660                         flags |= TX_BD_FLAGS_SW_LSO;
6661                         /* Set the length of IP + TCP options (in 32 bit words) */
6662                         flags |= (((ip_hlen + tcp_hlen - 40) >> 2) << 8);
6663
6664 bce_tx_encap_skip_tso:
6665                         DBRUN(sc->requested_tso_frames++);
6666                 }
6667         }
6668
6669         /* Transfer any VLAN tags to the bd. */
6670         if (m0->m_flags & M_VLANTAG) {
6671                 flags |= TX_BD_FLAGS_VLAN_TAG;
6672                 vlan_tag = m0->m_pkthdr.ether_vtag;
6673         }
6674
6675         /* Map the mbuf into DMAable memory. */
6676         prod = sc->tx_prod;
6677         chain_prod = TX_CHAIN_IDX(prod);
6678         map = sc->tx_mbuf_map[chain_prod];
6679
6680         /* Map the mbuf into our DMA address space. */
6681         error = bus_dmamap_load_mbuf_sg(sc->tx_mbuf_tag, map, m0,
6682             segs, &nsegs, BUS_DMA_NOWAIT);
6683
6684         /* Check if the DMA mapping was successful */
6685         if (error == EFBIG) {
6686
6687                 sc->fragmented_mbuf_count++;
6688
6689                 /* Try to defrag the mbuf. */
6690                 m0 = m_defrag(*m_head, M_DONTWAIT);
6691                 if (m0 == NULL) {
6692                         /* Defrag was unsuccessful */
6693                         m_freem(*m_head);
6694                         *m_head = NULL;
6695                         sc->mbuf_alloc_failed_count++;
6696                         rc = ENOBUFS;
6697                         goto bce_tx_encap_exit;
6698                 }
6699
6700                 /* Defrag was successful, try mapping again */
6701                 *m_head = m0;
6702                 error = bus_dmamap_load_mbuf_sg(sc->tx_mbuf_tag, map, m0,
6703                     segs, &nsegs, BUS_DMA_NOWAIT);
6704
6705                 /* Still getting an error after a defrag. */
6706                 if (error == ENOMEM) {
6707                         /* Insufficient DMA buffers available. */
6708                         sc->dma_map_addr_tx_failed_count++;
6709                         rc = error;
6710                         goto bce_tx_encap_exit;
6711                 } else if (error != 0) {
6712                         /* Still can't map the mbuf, release it and return an error. */
6713                         BCE_PRINTF(
6714                             "%s(%d): Unknown error mapping mbuf into TX chain!\n",
6715                             __FILE__, __LINE__);
6716                         m_freem(m0);
6717                         *m_head = NULL;
6718                         sc->dma_map_addr_tx_failed_count++;
6719                         rc = ENOBUFS;
6720                         goto bce_tx_encap_exit;
6721                 }
6722         } else if (error == ENOMEM) {
6723                 /* Insufficient DMA buffers available. */
6724                 sc->dma_map_addr_tx_failed_count++;
6725                 rc = error;
6726                 goto bce_tx_encap_exit;
6727         } else if (error != 0) {
6728                 m_freem(m0);
6729                 *m_head = NULL;
6730                 sc->dma_map_addr_tx_failed_count++;
6731                 rc = error;
6732                 goto bce_tx_encap_exit;
6733         }
6734
6735         /* Make sure there's room in the chain */
6736         if (nsegs > (sc->max_tx_bd - sc->used_tx_bd)) {
6737                 bus_dmamap_unload(sc->tx_mbuf_tag, map);
6738                 rc = ENOBUFS;
6739                 goto bce_tx_encap_exit;
6740         }
6741
6742         /* prod points to an empty tx_bd at this point. */
6743         prod_bseq  = sc->tx_prod_bseq;
6744
6745 #ifdef BCE_DEBUG
6746         debug_prod = chain_prod;
6747 #endif
6748
6749         DBPRINT(sc, BCE_INFO_SEND,
6750                 "%s(start): prod = 0x%04X, chain_prod = 0x%04X, "
6751                 "prod_bseq = 0x%08X\n",
6752                 __FUNCTION__, prod, chain_prod, prod_bseq);
6753
6754         /*
6755          * Cycle through each mbuf segment that makes up
6756          * the outgoing frame, gathering the mapping info
6757          * for that segment and creating a tx_bd for
6758          * the mbuf.
6759          */
6760         for (i = 0; i < nsegs ; i++) {
6761
6762                 chain_prod = TX_CHAIN_IDX(prod);
6763                 txbd= &sc->tx_bd_chain[TX_PAGE(chain_prod)][TX_IDX(chain_prod)];
6764
6765                 txbd->tx_bd_haddr_lo = htole32(BCE_ADDR_LO(segs[i].ds_addr));
6766                 txbd->tx_bd_haddr_hi = htole32(BCE_ADDR_HI(segs[i].ds_addr));
6767                 txbd->tx_bd_mss_nbytes = htole32(mss << 16) | htole16(segs[i].ds_len);
6768                 txbd->tx_bd_vlan_tag = htole16(vlan_tag);
6769                 txbd->tx_bd_flags = htole16(flags);
6770                 prod_bseq += segs[i].ds_len;
6771                 if (i == 0)
6772                         txbd->tx_bd_flags |= htole16(TX_BD_FLAGS_START);
6773                 prod = NEXT_TX_BD(prod);
6774         }
6775
6776         /* Set the END flag on the last TX buffer descriptor. */
6777         txbd->tx_bd_flags |= htole16(TX_BD_FLAGS_END);
6778
6779         DBRUNMSG(BCE_EXTREME_SEND, bce_dump_tx_chain(sc, debug_prod, nsegs));
6780
6781         DBPRINT(sc, BCE_INFO_SEND,
6782                 "%s( end ): prod = 0x%04X, chain_prod = 0x%04X, "
6783                 "prod_bseq = 0x%08X\n",
6784                 __FUNCTION__, prod, chain_prod, prod_bseq);
6785
6786         /*
6787          * Ensure that the mbuf pointer for this transmission
6788          * is placed at the array index of the last
6789          * descriptor in this chain.  This is done
6790          * because a single map is used for all
6791          * segments of the mbuf and we don't want to
6792          * unload the map before all of the segments
6793          * have been freed.
6794          */
6795         sc->tx_mbuf_ptr[chain_prod] = m0;
6796         sc->used_tx_bd += nsegs;
6797
6798         /* Update some debug statistic counters */
6799         DBRUNIF((sc->used_tx_bd > sc->tx_hi_watermark),
6800                 sc->tx_hi_watermark = sc->used_tx_bd);
6801         DBRUNIF((sc->used_tx_bd == sc->max_tx_bd), sc->tx_full_count++);
6802         DBRUNIF(sc->debug_tx_mbuf_alloc++);
6803
6804         DBRUNMSG(BCE_EXTREME_SEND, bce_dump_tx_mbuf_chain(sc, chain_prod, 1));
6805
6806         /* prod points to the next free tx_bd at this point. */
6807         sc->tx_prod = prod;
6808         sc->tx_prod_bseq = prod_bseq;
6809
6810         DBPRINT(sc, BCE_INFO_SEND,
6811                 "%s(exit): prod = 0x%04X, chain_prod = %04X, "
6812                 "prod_bseq = 0x%08X\n",
6813                 __FUNCTION__, sc->tx_prod, (u16) TX_CHAIN_IDX(sc->tx_prod),
6814                 sc->tx_prod_bseq);
6815
6816 bce_tx_encap_exit:
6817         DBEXIT(BCE_VERBOSE_SEND);
6818         return(rc);
6819 }
6820
6821
6822 /****************************************************************************/
6823 /* Main transmit routine when called from another routine with a lock.      */
6824 /*                                                                          */
6825 /* Returns:                                                                 */
6826 /*   Nothing.                                                               */
6827 /****************************************************************************/
6828 static void
6829 bce_start_locked(struct ifnet *ifp)
6830 {
6831         struct bce_softc *sc = ifp->if_softc;
6832         struct mbuf *m_head = NULL;
6833         int count = 0;
6834         u16 tx_prod, tx_chain_prod;
6835
6836         DBENTER(BCE_VERBOSE_SEND | BCE_VERBOSE_CTX);
6837
6838         BCE_LOCK_ASSERT(sc);
6839
6840         /* prod points to the next free tx_bd. */
6841         tx_prod = sc->tx_prod;
6842         tx_chain_prod = TX_CHAIN_IDX(tx_prod);
6843
6844         DBPRINT(sc, BCE_INFO_SEND,
6845                 "%s(enter): tx_prod = 0x%04X, tx_chain_prod = 0x%04X, "
6846                 "tx_prod_bseq = 0x%08X\n",
6847                 __FUNCTION__, tx_prod, tx_chain_prod, sc->tx_prod_bseq);
6848
6849         /* If there's no link or the transmit queue is empty then just exit. */
6850         if (!sc->bce_link) {
6851                 DBPRINT(sc, BCE_INFO_SEND, "%s(): No link.\n",
6852                         __FUNCTION__);
6853                 goto bce_start_locked_exit;
6854         }
6855
6856         if (IFQ_DRV_IS_EMPTY(&ifp->if_snd)) {
6857                 DBPRINT(sc, BCE_INFO_SEND, "%s(): Transmit queue empty.\n",
6858                         __FUNCTION__);
6859                 goto bce_start_locked_exit;
6860         }
6861
6862         /*
6863          * Keep adding entries while there is space in the ring.
6864          */
6865         while (sc->used_tx_bd < sc->max_tx_bd) {
6866
6867                 /* Check for any frames to send. */
6868                 IFQ_DRV_DEQUEUE(&ifp->if_snd, m_head);
6869
6870                 /* Stop when the transmit queue is empty. */
6871                 if (m_head == NULL)
6872                         break;
6873
6874                 /*
6875                  * Pack the data into the transmit ring. If we
6876                  * don't have room, place the mbuf back at the
6877                  * head of the queue and set the OACTIVE flag
6878                  * to wait for the NIC to drain the chain.
6879                  */
6880                 if (bce_tx_encap(sc, &m_head)) {
6881                         /* No room, put the frame back on the transmit queue. */
6882                         if (m_head != NULL)
6883                                 IFQ_DRV_PREPEND(&ifp->if_snd, m_head);
6884                         ifp->if_drv_flags |= IFF_DRV_OACTIVE;
6885                         DBPRINT(sc, BCE_INFO_SEND,
6886                                 "TX chain is closed for business! Total tx_bd used = %d\n",
6887                                 sc->used_tx_bd);
6888                         break;
6889                 }
6890
6891                 count++;
6892
6893                 /* Send a copy of the frame to any BPF listeners. */
6894                 ETHER_BPF_MTAP(ifp, m_head);
6895         }
6896
6897         /* Exit if no packets were dequeued. */
6898         if (count == 0) {
6899                 DBPRINT(sc, BCE_VERBOSE_SEND, "%s(): No packets were dequeued\n",
6900                         __FUNCTION__);
6901                 goto bce_start_locked_exit;
6902         }
6903
6904         DBPRINT(sc, BCE_VERBOSE_SEND, "%s(): Inserted %d frames into send queue.\n",
6905                 __FUNCTION__, count);
6906
6907         REG_WR(sc, BCE_MQ_COMMAND, REG_RD(sc, BCE_MQ_COMMAND) | BCE_MQ_COMMAND_NO_MAP_ERROR);
6908
6909         /* Write the mailbox and tell the chip about the waiting tx_bd's. */
6910         DBPRINT(sc, BCE_VERBOSE_SEND, "%s(): MB_GET_CID_ADDR(TX_CID) = 0x%08X; "
6911                 "BCE_L2MQ_TX_HOST_BIDX = 0x%08X, sc->tx_prod = 0x%04X\n",
6912                 __FUNCTION__,
6913                 MB_GET_CID_ADDR(TX_CID), BCE_L2MQ_TX_HOST_BIDX, sc->tx_prod);
6914         REG_WR16(sc, MB_GET_CID_ADDR(TX_CID) + BCE_L2MQ_TX_HOST_BIDX, sc->tx_prod);
6915         DBPRINT(sc, BCE_VERBOSE_SEND, "%s(): MB_GET_CID_ADDR(TX_CID) = 0x%08X; "
6916                 "BCE_L2MQ_TX_HOST_BSEQ = 0x%08X, sc->tx_prod_bseq = 0x%04X\n",
6917                 __FUNCTION__,
6918                 MB_GET_CID_ADDR(TX_CID), BCE_L2MQ_TX_HOST_BSEQ, sc->tx_prod_bseq);
6919         REG_WR(sc, MB_GET_CID_ADDR(TX_CID) + BCE_L2MQ_TX_HOST_BSEQ, sc->tx_prod_bseq);
6920
6921         /* Set the tx timeout. */
6922         sc->watchdog_timer = BCE_TX_TIMEOUT;
6923
6924         DBRUNMSG(BCE_VERBOSE_SEND, bce_dump_ctx(sc, TX_CID));
6925         DBRUNMSG(BCE_VERBOSE_SEND, bce_dump_mq_regs(sc));
6926
6927 bce_start_locked_exit:
6928         DBEXIT(BCE_VERBOSE_SEND | BCE_VERBOSE_CTX);
6929         return;
6930 }
6931
6932
6933 /****************************************************************************/
6934 /* Main transmit routine when called from another routine without a lock.   */
6935 /*                                                                          */
6936 /* Returns:                                                                 */
6937 /*   Nothing.                                                               */
6938 /****************************************************************************/
6939 static void
6940 bce_start(struct ifnet *ifp)
6941 {
6942         struct bce_softc *sc = ifp->if_softc;
6943
6944         DBENTER(BCE_VERBOSE_SEND);
6945
6946         BCE_LOCK(sc);
6947         bce_start_locked(ifp);
6948         BCE_UNLOCK(sc);
6949
6950         DBEXIT(BCE_VERBOSE_SEND);
6951 }
6952
6953
6954 /****************************************************************************/
6955 /* Handles any IOCTL calls from the operating system.                       */
6956 /*                                                                          */
6957 /* Returns:                                                                 */
6958 /*   0 for success, positive value for failure.                             */
6959 /****************************************************************************/
6960 static int
6961 bce_ioctl(struct ifnet *ifp, u_long command, caddr_t data)
6962 {
6963         struct bce_softc *sc = ifp->if_softc;
6964         struct ifreq *ifr = (struct ifreq *) data;
6965         struct mii_data *mii;
6966         int mask, error = 0;
6967
6968         DBENTER(BCE_VERBOSE_MISC);
6969
6970         switch(command) {
6971
6972                 /* Set the interface MTU. */
6973                 case SIOCSIFMTU:
6974                         /* Check that the MTU setting is supported. */
6975                         if ((ifr->ifr_mtu < BCE_MIN_MTU) ||
6976                                 (ifr->ifr_mtu > BCE_MAX_JUMBO_MTU)) {
6977                                 error = EINVAL;
6978                                 break;
6979                         }
6980
6981                         DBPRINT(sc, BCE_INFO_MISC,
6982                                 "SIOCSIFMTU: Changing MTU from %d to %d\n",
6983                                 (int) ifp->if_mtu, (int) ifr->ifr_mtu);
6984
6985                         BCE_LOCK(sc);
6986                         ifp->if_mtu = ifr->ifr_mtu;
6987                         ifp->if_drv_flags &= ~IFF_DRV_RUNNING;
6988 #ifdef BCE_JUMBO_HDRSPLIT
6989                         /* No buffer allocation size changes are necessary. */
6990 #else
6991                         /* Recalculate our buffer allocation sizes. */
6992                         if ((ifp->if_mtu + ETHER_HDR_LEN + ETHER_VLAN_ENCAP_LEN + ETHER_CRC_LEN) > MCLBYTES) {
6993                                 sc->rx_bd_mbuf_alloc_size = MJUM9BYTES;
6994                                 sc->rx_bd_mbuf_align_pad  = roundup2(MJUM9BYTES, 16) - MJUM9BYTES;
6995                                 sc->rx_bd_mbuf_data_len   = sc->rx_bd_mbuf_alloc_size -
6996                                         sc->rx_bd_mbuf_align_pad;
6997                         } else {
6998                                 sc->rx_bd_mbuf_alloc_size = MCLBYTES;
6999                                 sc->rx_bd_mbuf_align_pad  = roundup2(MCLBYTES, 16) - MCLBYTES;
7000                                 sc->rx_bd_mbuf_data_len   = sc->rx_bd_mbuf_alloc_size -
7001                                         sc->rx_bd_mbuf_align_pad;
7002                         }
7003 #endif
7004
7005                         bce_init_locked(sc);
7006                         BCE_UNLOCK(sc);
7007                         break;
7008
7009                 /* Set interface flags. */
7010                 case SIOCSIFFLAGS:
7011                         DBPRINT(sc, BCE_VERBOSE_SPECIAL, "Received SIOCSIFFLAGS\n");
7012
7013                         BCE_LOCK(sc);
7014
7015                         /* Check if the interface is up. */
7016                         if (ifp->if_flags & IFF_UP) {
7017                                 if (ifp->if_drv_flags & IFF_DRV_RUNNING) {
7018                                         /* Change promiscuous/multicast flags as necessary. */
7019                                         bce_set_rx_mode(sc);
7020                                 } else {
7021                                         /* Start the HW */
7022                                         bce_init_locked(sc);
7023                                 }
7024                         } else {
7025                                 /* The interface is down, check if driver is running. */
7026                                 if (ifp->if_drv_flags & IFF_DRV_RUNNING) {
7027                                         bce_stop(sc);
7028
7029                                         /* If MFW is running, restart the controller a bit. */
7030                                         if (sc->bce_flags & BCE_MFW_ENABLE_FLAG) {
7031                                                 bce_reset(sc, BCE_DRV_MSG_CODE_RESET);
7032                                                 bce_chipinit(sc);
7033                                                 bce_mgmt_init_locked(sc);
7034                                         }
7035                                 }
7036                         }
7037
7038                         BCE_UNLOCK(sc);
7039                         error = 0;
7040
7041                         break;
7042
7043                 /* Add/Delete multicast address */
7044                 case SIOCADDMULTI:
7045                 case SIOCDELMULTI:
7046                         DBPRINT(sc, BCE_VERBOSE_MISC, "Received SIOCADDMULTI/SIOCDELMULTI\n");
7047
7048                         BCE_LOCK(sc);
7049                         if (ifp->if_drv_flags & IFF_DRV_RUNNING) {
7050                                 bce_set_rx_mode(sc);
7051                                 error = 0;
7052                         }
7053                         BCE_UNLOCK(sc);
7054
7055                         break;
7056
7057                 /* Set/Get Interface media */
7058                 case SIOCSIFMEDIA:
7059                 case SIOCGIFMEDIA:
7060                         DBPRINT(sc, BCE_VERBOSE_MISC, "Received SIOCSIFMEDIA/SIOCGIFMEDIA\n");
7061
7062                         mii = device_get_softc(sc->bce_miibus);
7063                         error = ifmedia_ioctl(ifp, ifr,
7064                             &mii->mii_media, command);
7065                         break;
7066
7067                 /* Set interface capability */
7068                 case SIOCSIFCAP:
7069                         mask = ifr->ifr_reqcap ^ ifp->if_capenable;
7070                         DBPRINT(sc, BCE_INFO_MISC, "Received SIOCSIFCAP = 0x%08X\n", (u32) mask);
7071
7072                         /* Toggle the TX checksum capabilites enable flag. */
7073                         if (mask & IFCAP_TXCSUM) {
7074                                 ifp->if_capenable ^= IFCAP_TXCSUM;
7075                                 if (IFCAP_TXCSUM & ifp->if_capenable)
7076                                         ifp->if_hwassist = BCE_IF_HWASSIST;
7077                                 else
7078                                         ifp->if_hwassist = 0;
7079                         }
7080
7081                         /* Toggle the RX checksum capabilities enable flag. */
7082                         if (mask & IFCAP_RXCSUM) {
7083                                 ifp->if_capenable ^= IFCAP_RXCSUM;
7084                                 if (IFCAP_RXCSUM & ifp->if_capenable)
7085                                         ifp->if_hwassist = BCE_IF_HWASSIST;
7086                                 else
7087                                         ifp->if_hwassist = 0;
7088                         }
7089
7090                         /* Toggle the TSO capabilities enable flag. */
7091                         if (bce_tso_enable && (mask & IFCAP_TSO4)) {
7092                                 ifp->if_capenable ^= IFCAP_TSO4;
7093                                 if (IFCAP_RXCSUM & ifp->if_capenable)
7094                                         ifp->if_hwassist = BCE_IF_HWASSIST;
7095                                 else
7096                                         ifp->if_hwassist = 0;
7097                         }
7098
7099                         /* Toggle VLAN_MTU capabilities enable flag. */
7100                         if (mask & IFCAP_VLAN_MTU) {
7101                                 BCE_PRINTF("%s(%d): Changing VLAN_MTU not supported.\n",
7102                                         __FILE__, __LINE__);
7103                         }
7104
7105                         /* Toggle VLANHWTAG capabilities enabled flag. */
7106                         if (mask & IFCAP_VLAN_HWTAGGING) {
7107                                 if (sc->bce_flags & BCE_MFW_ENABLE_FLAG)
7108                                         BCE_PRINTF("%s(%d): Cannot change VLAN_HWTAGGING while "
7109                                                 "management firmware (ASF/IPMI/UMP) is running!\n",
7110                                                 __FILE__, __LINE__);
7111                                 else
7112                                         BCE_PRINTF("%s(%d): Changing VLAN_HWTAGGING not supported!\n",
7113                                                 __FILE__, __LINE__);
7114                         }
7115
7116                         break;
7117                 default:
7118                         /* We don't know how to handle the IOCTL, pass it on. */
7119                         error = ether_ioctl(ifp, command, data);
7120                         break;
7121         }
7122
7123         DBEXIT(BCE_VERBOSE_MISC);
7124         return(error);
7125 }
7126
7127
7128 /****************************************************************************/
7129 /* Transmit timeout handler.                                                */
7130 /*                                                                          */
7131 /* Returns:                                                                 */
7132 /*   Nothing.                                                               */
7133 /****************************************************************************/
7134 static void
7135 bce_watchdog(struct bce_softc *sc)
7136 {
7137         DBENTER(BCE_EXTREME_SEND);
7138
7139         BCE_LOCK_ASSERT(sc);
7140
7141         /* If the watchdog timer hasn't expired then just exit. */
7142         if (sc->watchdog_timer == 0 || --sc->watchdog_timer)
7143                 goto bce_watchdog_exit;
7144
7145         /* If pause frames are active then don't reset the hardware. */
7146         /* ToDo: Should we reset the timer here? */
7147         if (REG_RD(sc, BCE_EMAC_TX_STATUS) & BCE_EMAC_TX_STATUS_XOFFED)
7148                 goto bce_watchdog_exit;
7149
7150         BCE_PRINTF("%s(%d): Watchdog timeout occurred, resetting!\n",
7151                 __FILE__, __LINE__);
7152
7153         DBRUNMSG(BCE_INFO,
7154                 bce_dump_driver_state(sc);
7155                 bce_dump_status_block(sc);
7156                 bce_dump_stats_block(sc);
7157                 bce_dump_ftqs(sc);
7158                 bce_dump_txp_state(sc, 0);
7159                 bce_dump_rxp_state(sc, 0);
7160                 bce_dump_tpat_state(sc, 0);
7161                 bce_dump_cp_state(sc, 0);
7162                 bce_dump_com_state(sc, 0));
7163
7164         DBRUN(bce_breakpoint(sc));
7165
7166         sc->bce_ifp->if_drv_flags &= ~IFF_DRV_RUNNING;
7167
7168         bce_init_locked(sc);
7169         sc->bce_ifp->if_oerrors++;
7170
7171 bce_watchdog_exit:
7172         DBEXIT(BCE_EXTREME_SEND);
7173 }
7174
7175
7176 /*
7177  * Interrupt handler.
7178  */
7179 /****************************************************************************/
7180 /* Main interrupt entry point.  Verifies that the controller generated the  */
7181 /* interrupt and then calls a separate routine for handle the various       */
7182 /* interrupt causes (PHY, TX, RX).                                          */
7183 /*                                                                          */
7184 /* Returns:                                                                 */
7185 /*   0 for success, positive value for failure.                             */
7186 /****************************************************************************/
7187 static void
7188 bce_intr(void *xsc)
7189 {
7190         struct bce_softc *sc;
7191         struct ifnet *ifp;
7192         u32 status_attn_bits;
7193         u16 hw_rx_cons, hw_tx_cons;
7194
7195         sc = xsc;
7196         ifp = sc->bce_ifp;
7197
7198         DBENTER(BCE_VERBOSE_SEND | BCE_VERBOSE_RECV | BCE_VERBOSE_INTR);
7199         DBRUNMSG(BCE_VERBOSE_INTR, bce_dump_status_block(sc));
7200
7201         BCE_LOCK(sc);
7202
7203         DBRUN(sc->interrupts_generated++);
7204
7205         /* Synchnorize before we read from interface's status block */
7206         bus_dmamap_sync(sc->status_tag, sc->status_map,
7207             BUS_DMASYNC_POSTREAD);
7208
7209         /*
7210          * If the hardware status block index
7211          * matches the last value read by the
7212          * driver and we haven't asserted our
7213          * interrupt then there's nothing to do.
7214          */
7215         if ((sc->status_block->status_idx == sc->last_status_idx) &&
7216                 (REG_RD(sc, BCE_PCICFG_MISC_STATUS) & BCE_PCICFG_MISC_STATUS_INTA_VALUE)) {
7217                         DBPRINT(sc, BCE_VERBOSE_INTR, "%s(): Spurious interrupt.\n",
7218                                 __FUNCTION__);
7219                         goto bce_intr_exit;
7220         }
7221
7222         /* Ack the interrupt and stop others from occuring. */
7223         REG_WR(sc, BCE_PCICFG_INT_ACK_CMD,
7224                 BCE_PCICFG_INT_ACK_CMD_USE_INT_HC_PARAM |
7225                 BCE_PCICFG_INT_ACK_CMD_MASK_INT);
7226
7227         /* Check if the hardware has finished any work. */
7228         hw_rx_cons = bce_get_hw_rx_cons(sc);
7229         hw_tx_cons = bce_get_hw_tx_cons(sc);
7230
7231         /* Keep processing data as long as there is work to do. */
7232         for (;;) {
7233
7234                 status_attn_bits = sc->status_block->status_attn_bits;
7235
7236         DBRUNIF(DB_RANDOMTRUE(unexpected_attention_sim_control),
7237                 BCE_PRINTF("Simulating unexpected status attention bit set.");
7238                 sc->unexpected_attention_sim_count++;
7239                 status_attn_bits = status_attn_bits | STATUS_ATTN_BITS_PARITY_ERROR);
7240
7241                 /* Was it a link change interrupt? */
7242                 if ((status_attn_bits & STATUS_ATTN_BITS_LINK_STATE) !=
7243                         (sc->status_block->status_attn_bits_ack & STATUS_ATTN_BITS_LINK_STATE)) {
7244                         bce_phy_intr(sc);
7245
7246                         /* Clear any transient status updates during link state change. */
7247                         REG_WR(sc, BCE_HC_COMMAND,
7248                                 sc->hc_command | BCE_HC_COMMAND_COAL_NOW_WO_INT);
7249                         REG_RD(sc, BCE_HC_COMMAND);
7250                 }
7251
7252                 /* If any other attention is asserted then the chip is toast. */
7253                 if (((status_attn_bits & ~STATUS_ATTN_BITS_LINK_STATE) !=
7254                         (sc->status_block->status_attn_bits_ack &
7255                         ~STATUS_ATTN_BITS_LINK_STATE))) {
7256
7257                 sc->unexpected_attention_count++;
7258
7259                         BCE_PRINTF("%s(%d): Fatal attention detected: 0x%08X\n",
7260                                 __FILE__, __LINE__, sc->status_block->status_attn_bits);
7261
7262                         DBRUNMSG(BCE_FATAL,
7263                                 if (unexpected_attention_sim_control == 0)
7264                                         bce_breakpoint(sc));
7265
7266                         bce_init_locked(sc);
7267                         goto bce_intr_exit;
7268                 }
7269
7270                 /* Check for any completed RX frames. */
7271                 if (hw_rx_cons != sc->hw_rx_cons)
7272                         bce_rx_intr(sc);
7273
7274                 /* Check for any completed TX frames. */
7275                 if (hw_tx_cons != sc->hw_tx_cons)
7276                         bce_tx_intr(sc);
7277
7278                 /* Save the status block index value for use during the next interrupt. */
7279                 sc->last_status_idx = sc->status_block->status_idx;
7280
7281                 /* Prevent speculative reads from getting ahead of the status block. */
7282                 bus_space_barrier(sc->bce_btag, sc->bce_bhandle, 0, 0,
7283                         BUS_SPACE_BARRIER_READ);
7284
7285                 /* If there's no work left then exit the interrupt service routine. */
7286                 hw_rx_cons = bce_get_hw_rx_cons(sc);
7287                 hw_tx_cons = bce_get_hw_tx_cons(sc);
7288
7289                 if ((hw_rx_cons == sc->hw_rx_cons) && (hw_tx_cons == sc->hw_tx_cons))
7290                         break;
7291
7292         }
7293
7294         bus_dmamap_sync(sc->status_tag, sc->status_map,
7295             BUS_DMASYNC_PREREAD);
7296
7297         /* Re-enable interrupts. */
7298         bce_enable_intr(sc, 0);
7299
7300         /* Handle any frames that arrived while handling the interrupt. */
7301         if (ifp->if_drv_flags & IFF_DRV_RUNNING && !IFQ_DRV_IS_EMPTY(&ifp->if_snd))
7302                 bce_start_locked(ifp);
7303
7304 bce_intr_exit:
7305         BCE_UNLOCK(sc);
7306
7307         DBEXIT(BCE_VERBOSE_SEND | BCE_VERBOSE_RECV | BCE_VERBOSE_INTR);
7308 }
7309
7310
7311 /****************************************************************************/
7312 /* Programs the various packet receive modes (broadcast and multicast).     */
7313 /*                                                                          */
7314 /* Returns:                                                                 */
7315 /*   Nothing.                                                               */
7316 /****************************************************************************/
7317 static void
7318 bce_set_rx_mode(struct bce_softc *sc)
7319 {
7320         struct ifnet *ifp;
7321         struct ifmultiaddr *ifma;
7322         u32 hashes[NUM_MC_HASH_REGISTERS] = { 0, 0, 0, 0, 0, 0, 0, 0 };
7323         u32 rx_mode, sort_mode;
7324         int h, i;
7325
7326         DBENTER(BCE_VERBOSE_MISC);
7327
7328         BCE_LOCK_ASSERT(sc);
7329
7330         ifp = sc->bce_ifp;
7331
7332         /* Initialize receive mode default settings. */
7333         rx_mode   = sc->rx_mode & ~(BCE_EMAC_RX_MODE_PROMISCUOUS |
7334                             BCE_EMAC_RX_MODE_KEEP_VLAN_TAG);
7335         sort_mode = 1 | BCE_RPM_SORT_USER0_BC_EN;
7336
7337         /*
7338          * ASF/IPMI/UMP firmware requires that VLAN tag stripping
7339          * be enbled.
7340          */
7341         if (!(BCE_IF_CAPABILITIES & IFCAP_VLAN_HWTAGGING) &&
7342                 (!(sc->bce_flags & BCE_MFW_ENABLE_FLAG)))
7343                 rx_mode |= BCE_EMAC_RX_MODE_KEEP_VLAN_TAG;
7344
7345         /*
7346          * Check for promiscuous, all multicast, or selected
7347          * multicast address filtering.
7348          */
7349         if (ifp->if_flags & IFF_PROMISC) {
7350                 DBPRINT(sc, BCE_INFO_MISC, "Enabling promiscuous mode.\n");
7351
7352                 /* Enable promiscuous mode. */
7353                 rx_mode |= BCE_EMAC_RX_MODE_PROMISCUOUS;
7354                 sort_mode |= BCE_RPM_SORT_USER0_PROM_EN;
7355         } else if (ifp->if_flags & IFF_ALLMULTI) {
7356                 DBPRINT(sc, BCE_INFO_MISC, "Enabling all multicast mode.\n");
7357
7358                 /* Enable all multicast addresses. */
7359                 for (i = 0; i < NUM_MC_HASH_REGISTERS; i++) {
7360                         REG_WR(sc, BCE_EMAC_MULTICAST_HASH0 + (i * 4), 0xffffffff);
7361         }
7362                 sort_mode |= BCE_RPM_SORT_USER0_MC_EN;
7363         } else {
7364                 /* Accept one or more multicast(s). */
7365                 DBPRINT(sc, BCE_INFO_MISC, "Enabling selective multicast mode.\n");
7366
7367                 if_maddr_rlock(ifp);
7368                 TAILQ_FOREACH(ifma, &ifp->if_multiaddrs, ifma_link) {
7369                         if (ifma->ifma_addr->sa_family != AF_LINK)
7370                                 continue;
7371                         h = ether_crc32_le(LLADDR((struct sockaddr_dl *)
7372                             ifma->ifma_addr), ETHER_ADDR_LEN) & 0xFF;
7373                             hashes[(h & 0xE0) >> 5] |= 1 << (h & 0x1F);
7374                 }
7375                 if_maddr_runlock(ifp);
7376
7377                 for (i = 0; i < NUM_MC_HASH_REGISTERS; i++)
7378                         REG_WR(sc, BCE_EMAC_MULTICAST_HASH0 + (i * 4), hashes[i]);
7379
7380                 sort_mode |= BCE_RPM_SORT_USER0_MC_HSH_EN;
7381         }
7382
7383         /* Only make changes if the recive mode has actually changed. */
7384         if (rx_mode != sc->rx_mode) {
7385                 DBPRINT(sc, BCE_VERBOSE_MISC, "Enabling new receive mode: 0x%08X\n",
7386                         rx_mode);
7387
7388                 sc->rx_mode = rx_mode;
7389                 REG_WR(sc, BCE_EMAC_RX_MODE, rx_mode);
7390         }
7391
7392         /* Disable and clear the exisitng sort before enabling a new sort. */
7393         REG_WR(sc, BCE_RPM_SORT_USER0, 0x0);
7394         REG_WR(sc, BCE_RPM_SORT_USER0, sort_mode);
7395         REG_WR(sc, BCE_RPM_SORT_USER0, sort_mode | BCE_RPM_SORT_USER0_ENA);
7396
7397         DBEXIT(BCE_VERBOSE_MISC);
7398 }
7399
7400
7401 /****************************************************************************/
7402 /* Called periodically to updates statistics from the controllers           */
7403 /* statistics block.                                                        */
7404 /*                                                                          */
7405 /* Returns:                                                                 */
7406 /*   Nothing.                                                               */
7407 /****************************************************************************/
7408 static void
7409 bce_stats_update(struct bce_softc *sc)
7410 {
7411         struct ifnet *ifp;
7412         struct statistics_block *stats;
7413
7414         DBENTER(BCE_EXTREME_MISC);
7415
7416         ifp = sc->bce_ifp;
7417
7418         stats = (struct statistics_block *) sc->stats_block;
7419
7420         /*
7421          * Certain controllers don't report
7422          * carrier sense errors correctly.
7423          * See errata E11_5708CA0_1165.
7424          */
7425         if (!(BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5706) &&
7426             !(BCE_CHIP_ID(sc) == BCE_CHIP_ID_5708_A0))
7427                 ifp->if_oerrors += (u_long) stats->stat_Dot3StatsCarrierSenseErrors;
7428
7429         /*
7430          * Update the sysctl statistics from the
7431          * hardware statistics.
7432          */
7433         sc->stat_IfHCInOctets =
7434                 ((u64) stats->stat_IfHCInOctets_hi << 32) +
7435                  (u64) stats->stat_IfHCInOctets_lo;
7436
7437         sc->stat_IfHCInBadOctets =
7438                 ((u64) stats->stat_IfHCInBadOctets_hi << 32) +
7439                  (u64) stats->stat_IfHCInBadOctets_lo;
7440
7441         sc->stat_IfHCOutOctets =
7442                 ((u64) stats->stat_IfHCOutOctets_hi << 32) +
7443                  (u64) stats->stat_IfHCOutOctets_lo;
7444
7445         sc->stat_IfHCOutBadOctets =
7446                 ((u64) stats->stat_IfHCOutBadOctets_hi << 32) +
7447                  (u64) stats->stat_IfHCOutBadOctets_lo;
7448
7449         sc->stat_IfHCInUcastPkts =
7450                 ((u64) stats->stat_IfHCInUcastPkts_hi << 32) +
7451                  (u64) stats->stat_IfHCInUcastPkts_lo;
7452
7453         sc->stat_IfHCInMulticastPkts =
7454                 ((u64) stats->stat_IfHCInMulticastPkts_hi << 32) +
7455                  (u64) stats->stat_IfHCInMulticastPkts_lo;
7456
7457         sc->stat_IfHCInBroadcastPkts =
7458                 ((u64) stats->stat_IfHCInBroadcastPkts_hi << 32) +
7459                  (u64) stats->stat_IfHCInBroadcastPkts_lo;
7460
7461         sc->stat_IfHCOutUcastPkts =
7462                 ((u64) stats->stat_IfHCOutUcastPkts_hi << 32) +
7463                  (u64) stats->stat_IfHCOutUcastPkts_lo;
7464
7465         sc->stat_IfHCOutMulticastPkts =
7466                 ((u64) stats->stat_IfHCOutMulticastPkts_hi << 32) +
7467                  (u64) stats->stat_IfHCOutMulticastPkts_lo;
7468
7469         sc->stat_IfHCOutBroadcastPkts =
7470                 ((u64) stats->stat_IfHCOutBroadcastPkts_hi << 32) +
7471                  (u64) stats->stat_IfHCOutBroadcastPkts_lo;
7472
7473         sc->stat_emac_tx_stat_dot3statsinternalmactransmiterrors =
7474                 stats->stat_emac_tx_stat_dot3statsinternalmactransmiterrors;
7475
7476         sc->stat_Dot3StatsCarrierSenseErrors =
7477                 stats->stat_Dot3StatsCarrierSenseErrors;
7478
7479         sc->stat_Dot3StatsFCSErrors =
7480                 stats->stat_Dot3StatsFCSErrors;
7481
7482         sc->stat_Dot3StatsAlignmentErrors =
7483                 stats->stat_Dot3StatsAlignmentErrors;
7484
7485         sc->stat_Dot3StatsSingleCollisionFrames =
7486                 stats->stat_Dot3StatsSingleCollisionFrames;
7487
7488         sc->stat_Dot3StatsMultipleCollisionFrames =
7489                 stats->stat_Dot3StatsMultipleCollisionFrames;
7490
7491         sc->stat_Dot3StatsDeferredTransmissions =
7492                 stats->stat_Dot3StatsDeferredTransmissions;
7493
7494         sc->stat_Dot3StatsExcessiveCollisions =
7495                 stats->stat_Dot3StatsExcessiveCollisions;
7496
7497         sc->stat_Dot3StatsLateCollisions =
7498                 stats->stat_Dot3StatsLateCollisions;
7499
7500         sc->stat_EtherStatsCollisions =
7501                 stats->stat_EtherStatsCollisions;
7502
7503         sc->stat_EtherStatsFragments =
7504                 stats->stat_EtherStatsFragments;
7505
7506         sc->stat_EtherStatsJabbers =
7507                 stats->stat_EtherStatsJabbers;
7508
7509         sc->stat_EtherStatsUndersizePkts =
7510                 stats->stat_EtherStatsUndersizePkts;
7511
7512         sc->stat_EtherStatsOversizePkts =
7513                 stats->stat_EtherStatsOversizePkts;
7514
7515         sc->stat_EtherStatsPktsRx64Octets =
7516                 stats->stat_EtherStatsPktsRx64Octets;
7517
7518         sc->stat_EtherStatsPktsRx65Octetsto127Octets =
7519                 stats->stat_EtherStatsPktsRx65Octetsto127Octets;
7520
7521         sc->stat_EtherStatsPktsRx128Octetsto255Octets =
7522                 stats->stat_EtherStatsPktsRx128Octetsto255Octets;
7523
7524         sc->stat_EtherStatsPktsRx256Octetsto511Octets =
7525                 stats->stat_EtherStatsPktsRx256Octetsto511Octets;
7526
7527         sc->stat_EtherStatsPktsRx512Octetsto1023Octets =
7528                 stats->stat_EtherStatsPktsRx512Octetsto1023Octets;
7529
7530         sc->stat_EtherStatsPktsRx1024Octetsto1522Octets =
7531                 stats->stat_EtherStatsPktsRx1024Octetsto1522Octets;
7532
7533         sc->stat_EtherStatsPktsRx1523Octetsto9022Octets =
7534                 stats->stat_EtherStatsPktsRx1523Octetsto9022Octets;
7535
7536         sc->stat_EtherStatsPktsTx64Octets =
7537                 stats->stat_EtherStatsPktsTx64Octets;
7538
7539         sc->stat_EtherStatsPktsTx65Octetsto127Octets =
7540                 stats->stat_EtherStatsPktsTx65Octetsto127Octets;
7541
7542         sc->stat_EtherStatsPktsTx128Octetsto255Octets =
7543                 stats->stat_EtherStatsPktsTx128Octetsto255Octets;
7544
7545         sc->stat_EtherStatsPktsTx256Octetsto511Octets =
7546                 stats->stat_EtherStatsPktsTx256Octetsto511Octets;
7547
7548         sc->stat_EtherStatsPktsTx512Octetsto1023Octets =
7549                 stats->stat_EtherStatsPktsTx512Octetsto1023Octets;
7550
7551         sc->stat_EtherStatsPktsTx1024Octetsto1522Octets =
7552                 stats->stat_EtherStatsPktsTx1024Octetsto1522Octets;
7553
7554         sc->stat_EtherStatsPktsTx1523Octetsto9022Octets =
7555                 stats->stat_EtherStatsPktsTx1523Octetsto9022Octets;
7556
7557         sc->stat_XonPauseFramesReceived =
7558                 stats->stat_XonPauseFramesReceived;
7559
7560         sc->stat_XoffPauseFramesReceived =
7561                 stats->stat_XoffPauseFramesReceived;
7562
7563         sc->stat_OutXonSent =
7564                 stats->stat_OutXonSent;
7565
7566         sc->stat_OutXoffSent =
7567                 stats->stat_OutXoffSent;
7568
7569         sc->stat_FlowControlDone =
7570                 stats->stat_FlowControlDone;
7571
7572         sc->stat_MacControlFramesReceived =
7573                 stats->stat_MacControlFramesReceived;
7574
7575         sc->stat_XoffStateEntered =
7576                 stats->stat_XoffStateEntered;
7577
7578         sc->stat_IfInFramesL2FilterDiscards =
7579                 stats->stat_IfInFramesL2FilterDiscards;
7580
7581         sc->stat_IfInRuleCheckerDiscards =
7582                 stats->stat_IfInRuleCheckerDiscards;
7583
7584         sc->stat_IfInFTQDiscards =
7585                 stats->stat_IfInFTQDiscards;
7586
7587         sc->stat_IfInMBUFDiscards =
7588                 stats->stat_IfInMBUFDiscards;
7589
7590         sc->stat_IfInRuleCheckerP4Hit =
7591                 stats->stat_IfInRuleCheckerP4Hit;
7592
7593         sc->stat_CatchupInRuleCheckerDiscards =
7594                 stats->stat_CatchupInRuleCheckerDiscards;
7595
7596         sc->stat_CatchupInFTQDiscards =
7597                 stats->stat_CatchupInFTQDiscards;
7598
7599         sc->stat_CatchupInMBUFDiscards =
7600                 stats->stat_CatchupInMBUFDiscards;
7601
7602         sc->stat_CatchupInRuleCheckerP4Hit =
7603                 stats->stat_CatchupInRuleCheckerP4Hit;
7604
7605         sc->com_no_buffers = REG_RD_IND(sc, 0x120084);
7606
7607         /*
7608          * Update the interface statistics from the
7609          * hardware statistics.
7610          */
7611         ifp->if_collisions =
7612                 (u_long) sc->stat_EtherStatsCollisions;
7613
7614         /* ToDo: This method loses soft errors. */
7615         ifp->if_ierrors =
7616                 (u_long) sc->stat_EtherStatsUndersizePkts +
7617                 (u_long) sc->stat_EtherStatsOversizePkts +
7618                 (u_long) sc->stat_IfInMBUFDiscards +
7619                 (u_long) sc->stat_Dot3StatsAlignmentErrors +
7620                 (u_long) sc->stat_Dot3StatsFCSErrors +
7621                 (u_long) sc->stat_IfInRuleCheckerDiscards +
7622                 (u_long) sc->stat_IfInFTQDiscards +
7623                 (u_long) sc->com_no_buffers;
7624
7625         /* ToDo: This method loses soft errors. */
7626         ifp->if_oerrors =
7627                 (u_long) sc->stat_emac_tx_stat_dot3statsinternalmactransmiterrors +
7628                 (u_long) sc->stat_Dot3StatsExcessiveCollisions +
7629                 (u_long) sc->stat_Dot3StatsLateCollisions;
7630
7631         /* ToDo: Add additional statistics. */
7632
7633         DBEXIT(BCE_EXTREME_MISC);
7634 }
7635
7636
7637 /****************************************************************************/
7638 /* Periodic function to notify the bootcode that the driver is still        */
7639 /* present.                                                                 */
7640 /*                                                                          */
7641 /* Returns:                                                                 */
7642 /*   Nothing.                                                               */
7643 /****************************************************************************/
7644 static void
7645 bce_pulse(void *xsc)
7646 {
7647         struct bce_softc *sc = xsc;
7648         u32 msg;
7649
7650         DBENTER(BCE_EXTREME_MISC);
7651
7652         BCE_LOCK_ASSERT(sc);
7653
7654         /* Tell the firmware that the driver is still running. */
7655         msg = (u32) ++sc->bce_fw_drv_pulse_wr_seq;
7656         bce_shmem_wr(sc, BCE_DRV_PULSE_MB, msg);
7657
7658         /* Schedule the next pulse. */
7659         callout_reset(&sc->bce_pulse_callout, hz, bce_pulse, sc);
7660
7661         DBEXIT(BCE_EXTREME_MISC);
7662 }
7663
7664
7665 /****************************************************************************/
7666 /* Periodic function to perform maintenance tasks.                          */
7667 /*                                                                          */
7668 /* Returns:                                                                 */
7669 /*   Nothing.                                                               */
7670 /****************************************************************************/
7671 static void
7672 bce_tick(void *xsc)
7673 {
7674         struct bce_softc *sc = xsc;
7675         struct mii_data *mii;
7676         struct ifnet *ifp;
7677
7678         ifp = sc->bce_ifp;
7679
7680         DBENTER(BCE_EXTREME_MISC);
7681
7682         BCE_LOCK_ASSERT(sc);
7683
7684         /* Schedule the next tick. */
7685         callout_reset(&sc->bce_tick_callout, hz, bce_tick, sc);
7686
7687         /* Update the statistics from the hardware statistics block. */
7688         bce_stats_update(sc);
7689
7690         /* Top off the receive and page chains. */
7691 #ifdef BCE_JUMBO_HDRSPLIT
7692         bce_fill_pg_chain(sc);
7693 #endif
7694         bce_fill_rx_chain(sc);
7695
7696         /* Check that chip hasn't hung. */
7697         bce_watchdog(sc);
7698
7699         /* If link is up already up then we're done. */
7700         if (sc->bce_link)
7701                 goto bce_tick_exit;
7702
7703         /* Link is down.  Check what the PHY's doing. */
7704         mii = device_get_softc(sc->bce_miibus);
7705         mii_tick(mii);
7706
7707         /* Check if the link has come up. */
7708         if ((mii->mii_media_status & IFM_ACTIVE) &&
7709             (IFM_SUBTYPE(mii->mii_media_active) != IFM_NONE)) {
7710                 DBPRINT(sc, BCE_VERBOSE_MISC, "%s(): Link up!\n", __FUNCTION__);
7711                 sc->bce_link++;
7712                 if ((IFM_SUBTYPE(mii->mii_media_active) == IFM_1000_T ||
7713                     IFM_SUBTYPE(mii->mii_media_active) == IFM_1000_SX) &&
7714                     bootverbose)
7715                         BCE_PRINTF("Gigabit link up!\n");
7716                 /* Now that link is up, handle any outstanding TX traffic. */
7717                 if (!IFQ_DRV_IS_EMPTY(&ifp->if_snd)) {
7718                         DBPRINT(sc, BCE_VERBOSE_MISC, "%s(): Found pending TX traffic.\n",
7719                                  __FUNCTION__);
7720                         bce_start_locked(ifp);
7721                 }
7722         }
7723
7724 bce_tick_exit:
7725         DBEXIT(BCE_EXTREME_MISC);
7726         return;
7727 }
7728
7729
7730 #ifdef BCE_DEBUG
7731 /****************************************************************************/
7732 /* Allows the driver state to be dumped through the sysctl interface.       */
7733 /*                                                                          */
7734 /* Returns:                                                                 */
7735 /*   0 for success, positive value for failure.                             */
7736 /****************************************************************************/
7737 static int
7738 bce_sysctl_driver_state(SYSCTL_HANDLER_ARGS)
7739 {
7740         int error;
7741         int result;
7742         struct bce_softc *sc;
7743
7744         result = -1;
7745         error = sysctl_handle_int(oidp, &result, 0, req);
7746
7747         if (error || !req->newptr)
7748                 return (error);
7749
7750         if (result == 1) {
7751                 sc = (struct bce_softc *)arg1;
7752                 bce_dump_driver_state(sc);
7753         }
7754
7755         return error;
7756 }
7757
7758
7759 /****************************************************************************/
7760 /* Allows the hardware state to be dumped through the sysctl interface.     */
7761 /*                                                                          */
7762 /* Returns:                                                                 */
7763 /*   0 for success, positive value for failure.                             */
7764 /****************************************************************************/
7765 static int
7766 bce_sysctl_hw_state(SYSCTL_HANDLER_ARGS)
7767 {
7768         int error;
7769         int result;
7770         struct bce_softc *sc;
7771
7772         result = -1;
7773         error = sysctl_handle_int(oidp, &result, 0, req);
7774
7775         if (error || !req->newptr)
7776                 return (error);
7777
7778         if (result == 1) {
7779                 sc = (struct bce_softc *)arg1;
7780                 bce_dump_hw_state(sc);
7781         }
7782
7783         return error;
7784 }
7785
7786
7787 /****************************************************************************/
7788 /* Allows the bootcode state to be dumped through the sysctl interface.     */
7789 /*                                                                          */
7790 /* Returns:                                                                 */
7791 /*   0 for success, positive value for failure.                             */
7792 /****************************************************************************/
7793 static int
7794 bce_sysctl_bc_state(SYSCTL_HANDLER_ARGS)
7795 {
7796         int error;
7797         int result;
7798         struct bce_softc *sc;
7799
7800         result = -1;
7801         error = sysctl_handle_int(oidp, &result, 0, req);
7802
7803         if (error || !req->newptr)
7804                 return (error);
7805
7806         if (result == 1) {
7807                 sc = (struct bce_softc *)arg1;
7808                 bce_dump_bc_state(sc);
7809         }
7810
7811         return error;
7812 }
7813
7814
7815 /****************************************************************************/
7816 /* Provides a sysctl interface to allow dumping the RX chain.               */
7817 /*                                                                          */
7818 /* Returns:                                                                 */
7819 /*   0 for success, positive value for failure.                             */
7820 /****************************************************************************/
7821 static int
7822 bce_sysctl_dump_rx_chain(SYSCTL_HANDLER_ARGS)
7823 {
7824         int error;
7825         int result;
7826         struct bce_softc *sc;
7827
7828         result = -1;
7829         error = sysctl_handle_int(oidp, &result, 0, req);
7830
7831         if (error || !req->newptr)
7832                 return (error);
7833
7834         if (result == 1) {
7835                 sc = (struct bce_softc *)arg1;
7836                 bce_dump_rx_chain(sc, 0, TOTAL_RX_BD);
7837         }
7838
7839         return error;
7840 }
7841
7842
7843 /****************************************************************************/
7844 /* Provides a sysctl interface to allow dumping the TX chain.               */
7845 /*                                                                          */
7846 /* Returns:                                                                 */
7847 /*   0 for success, positive value for failure.                             */
7848 /****************************************************************************/
7849 static int
7850 bce_sysctl_dump_tx_chain(SYSCTL_HANDLER_ARGS)
7851 {
7852         int error;
7853         int result;
7854         struct bce_softc *sc;
7855
7856         result = -1;
7857         error = sysctl_handle_int(oidp, &result, 0, req);
7858
7859         if (error || !req->newptr)
7860                 return (error);
7861
7862         if (result == 1) {
7863                 sc = (struct bce_softc *)arg1;
7864                 bce_dump_tx_chain(sc, 0, USABLE_TX_BD);
7865         }
7866
7867         return error;
7868 }
7869
7870
7871 #ifdef BCE_JUMBO_HDRSPLIT
7872 /****************************************************************************/
7873 /* Provides a sysctl interface to allow dumping the page chain.             */
7874 /*                                                                          */
7875 /* Returns:                                                                 */
7876 /*   0 for success, positive value for failure.                             */
7877 /****************************************************************************/
7878 static int
7879 bce_sysctl_dump_pg_chain(SYSCTL_HANDLER_ARGS)
7880 {
7881         int error;
7882         int result;
7883         struct bce_softc *sc;
7884
7885         result = -1;
7886         error = sysctl_handle_int(oidp, &result, 0, req);
7887
7888         if (error || !req->newptr)
7889                 return (error);
7890
7891         if (result == 1) {
7892                 sc = (struct bce_softc *)arg1;
7893                 bce_dump_pg_chain(sc, 0, TOTAL_PG_BD);
7894         }
7895
7896         return error;
7897 }
7898 #endif
7899
7900 /****************************************************************************/
7901 /* Provides a sysctl interface to allow reading arbitrary NVRAM offsets in  */
7902 /* the device.  DO NOT ENABLE ON PRODUCTION SYSTEMS!                        */
7903 /*                                                                          */
7904 /* Returns:                                                                 */
7905 /*   0 for success, positive value for failure.                             */
7906 /****************************************************************************/
7907 static int
7908 bce_sysctl_nvram_read(SYSCTL_HANDLER_ARGS)
7909 {
7910         struct bce_softc *sc = (struct bce_softc *)arg1;
7911         int error;
7912         u32 result;
7913         u32 val[1];
7914         u8 *data = (u8 *) val;
7915
7916         result = -1;
7917         error = sysctl_handle_int(oidp, &result, 0, req);
7918         if (error || (req->newptr == NULL))
7919                 return (error);
7920
7921         bce_nvram_read(sc, result, data, 4);
7922         BCE_PRINTF("offset 0x%08X = 0x%08X\n", result, bce_be32toh(val[0]));
7923
7924         return (error);
7925 }
7926
7927
7928 /****************************************************************************/
7929 /* Provides a sysctl interface to allow reading arbitrary registers in the  */
7930 /* device.  DO NOT ENABLE ON PRODUCTION SYSTEMS!                            */
7931 /*                                                                          */
7932 /* Returns:                                                                 */
7933 /*   0 for success, positive value for failure.                             */
7934 /****************************************************************************/
7935 static int
7936 bce_sysctl_reg_read(SYSCTL_HANDLER_ARGS)
7937 {
7938         struct bce_softc *sc = (struct bce_softc *)arg1;
7939         int error;
7940         u32 val, result;
7941
7942         result = -1;
7943         error = sysctl_handle_int(oidp, &result, 0, req);
7944         if (error || (req->newptr == NULL))
7945                 return (error);
7946
7947         /* Make sure the register is accessible. */
7948         if (result < 0x8000) {
7949                 val = REG_RD(sc, result);
7950                 BCE_PRINTF("reg 0x%08X = 0x%08X\n", result, val);
7951         } else if (result < 0x0280000) {
7952                 val = REG_RD_IND(sc, result);
7953                 BCE_PRINTF("reg 0x%08X = 0x%08X\n", result, val);
7954         }
7955
7956         return (error);
7957 }
7958
7959
7960 /****************************************************************************/
7961 /* Provides a sysctl interface to allow reading arbitrary PHY registers in  */
7962 /* the device.  DO NOT ENABLE ON PRODUCTION SYSTEMS!                        */
7963 /*                                                                          */
7964 /* Returns:                                                                 */
7965 /*   0 for success, positive value for failure.                             */
7966 /****************************************************************************/
7967 static int
7968 bce_sysctl_phy_read(SYSCTL_HANDLER_ARGS)
7969 {
7970         struct bce_softc *sc;
7971         device_t dev;
7972         int error, result;
7973         u16 val;
7974
7975         result = -1;
7976         error = sysctl_handle_int(oidp, &result, 0, req);
7977         if (error || (req->newptr == NULL))
7978                 return (error);
7979
7980         /* Make sure the register is accessible. */
7981         if (result < 0x20) {
7982                 sc = (struct bce_softc *)arg1;
7983                 dev = sc->bce_dev;
7984                 val = bce_miibus_read_reg(dev, sc->bce_phy_addr, result);
7985                 BCE_PRINTF("phy 0x%02X = 0x%04X\n", result, val);
7986         }
7987         return (error);
7988 }
7989
7990
7991 /****************************************************************************/
7992 /* Provides a sysctl interface to allow reading a CID.                      */
7993 /*                                                                          */
7994 /* Returns:                                                                 */
7995 /*   0 for success, positive value for failure.                             */
7996 /****************************************************************************/
7997 static int
7998 bce_sysctl_dump_ctx(SYSCTL_HANDLER_ARGS)
7999 {
8000         struct bce_softc *sc;
8001         int error;
8002         u16 result;
8003
8004         result = -1;
8005         error = sysctl_handle_int(oidp, &result, 0, req);
8006         if (error || (req->newptr == NULL))
8007                 return (error);
8008
8009         /* Make sure the register is accessible. */
8010         if (result <= TX_CID) {
8011                 sc = (struct bce_softc *)arg1;
8012                 bce_dump_ctx(sc, result);
8013         }
8014
8015         return (error);
8016 }
8017
8018
8019  /****************************************************************************/
8020 /* Provides a sysctl interface to forcing the driver to dump state and      */
8021 /* enter the debugger.  DO NOT ENABLE ON PRODUCTION SYSTEMS!                */
8022 /*                                                                          */
8023 /* Returns:                                                                 */
8024 /*   0 for success, positive value for failure.                             */
8025 /****************************************************************************/
8026 static int
8027 bce_sysctl_breakpoint(SYSCTL_HANDLER_ARGS)
8028 {
8029         int error;
8030         int result;
8031         struct bce_softc *sc;
8032
8033         result = -1;
8034         error = sysctl_handle_int(oidp, &result, 0, req);
8035
8036         if (error || !req->newptr)
8037                 return (error);
8038
8039         if (result == 1) {
8040                 sc = (struct bce_softc *)arg1;
8041                 bce_breakpoint(sc);
8042         }
8043
8044         return error;
8045 }
8046 #endif
8047
8048
8049 /****************************************************************************/
8050 /* Adds any sysctl parameters for tuning or debugging purposes.             */
8051 /*                                                                          */
8052 /* Returns:                                                                 */
8053 /*   0 for success, positive value for failure.                             */
8054 /****************************************************************************/
8055 static void
8056 bce_add_sysctls(struct bce_softc *sc)
8057 {
8058         struct sysctl_ctx_list *ctx;
8059         struct sysctl_oid_list *children;
8060
8061         DBENTER(BCE_VERBOSE_MISC);
8062
8063         ctx = device_get_sysctl_ctx(sc->bce_dev);
8064         children = SYSCTL_CHILDREN(device_get_sysctl_tree(sc->bce_dev));
8065
8066 #ifdef BCE_DEBUG
8067         SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8068                 "l2fhdr_error_sim_control",
8069                 CTLFLAG_RW, &l2fhdr_error_sim_control,
8070                 0, "Debug control to force l2fhdr errors");
8071
8072         SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8073                 "l2fhdr_error_sim_count",
8074                 CTLFLAG_RD, &sc->l2fhdr_error_sim_count,
8075                 0, "Number of simulated l2_fhdr errors");
8076 #endif
8077
8078         SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8079                 "l2fhdr_error_count",
8080                 CTLFLAG_RD, &sc->l2fhdr_error_count,
8081                 0, "Number of l2_fhdr errors");
8082
8083 #ifdef BCE_DEBUG
8084         SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8085                 "mbuf_alloc_failed_sim_control",
8086                 CTLFLAG_RW, &mbuf_alloc_failed_sim_control,
8087                 0, "Debug control to force mbuf allocation failures");
8088
8089         SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8090                 "mbuf_alloc_failed_sim_count",
8091                 CTLFLAG_RD, &sc->mbuf_alloc_failed_sim_count,
8092                 0, "Number of simulated mbuf cluster allocation failures");
8093 #endif
8094
8095         SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8096                 "mbuf_alloc_failed_count",
8097                 CTLFLAG_RD, &sc->mbuf_alloc_failed_count,
8098                 0, "Number of mbuf allocation failures");
8099
8100         SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8101                 "fragmented_mbuf_count",
8102                 CTLFLAG_RD, &sc->fragmented_mbuf_count,
8103                 0, "Number of fragmented mbufs");
8104
8105 #ifdef BCE_DEBUG
8106         SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8107                 "dma_map_addr_failed_sim_control",
8108                 CTLFLAG_RW, &dma_map_addr_failed_sim_control,
8109                 0, "Debug control to force DMA mapping failures");
8110
8111         /* ToDo: Figure out how to update this value in bce_dma_map_addr(). */
8112         SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8113                 "dma_map_addr_failed_sim_count",
8114                 CTLFLAG_RD, &sc->dma_map_addr_failed_sim_count,
8115                 0, "Number of simulated DMA mapping failures");
8116         
8117 #endif
8118
8119         SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8120                 "dma_map_addr_rx_failed_count",
8121                 CTLFLAG_RD, &sc->dma_map_addr_rx_failed_count,
8122                 0, "Number of RX DMA mapping failures");
8123
8124         SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8125                 "dma_map_addr_tx_failed_count",
8126                 CTLFLAG_RD, &sc->dma_map_addr_tx_failed_count,
8127                 0, "Number of TX DMA mapping failures");
8128
8129 #ifdef BCE_DEBUG
8130         SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8131                 "unexpected_attention_sim_control",
8132                 CTLFLAG_RW, &unexpected_attention_sim_control,
8133                 0, "Debug control to simulate unexpected attentions");
8134
8135         SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8136                 "unexpected_attention_sim_count",
8137                 CTLFLAG_RW, &sc->unexpected_attention_sim_count,
8138                 0, "Number of simulated unexpected attentions");
8139 #endif
8140
8141         SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8142                 "unexpected_attention_count",
8143                 CTLFLAG_RW, &sc->unexpected_attention_count,
8144                 0, "Number of unexpected attentions");
8145
8146 #ifdef BCE_DEBUG
8147         SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8148                 "debug_bootcode_running_failure",
8149                 CTLFLAG_RW, &bootcode_running_failure_sim_control,
8150                 0, "Debug control to force bootcode running failures");
8151
8152         SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8153                 "rx_low_watermark",
8154                 CTLFLAG_RD, &sc->rx_low_watermark,
8155                 0, "Lowest level of free rx_bd's");
8156
8157         SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8158                 "rx_empty_count",
8159                 CTLFLAG_RD, &sc->rx_empty_count,
8160                 0, "Number of times the RX chain was empty");
8161
8162         SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8163                 "tx_hi_watermark",
8164                 CTLFLAG_RD, &sc->tx_hi_watermark,
8165                 0, "Highest level of used tx_bd's");
8166
8167         SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8168                 "tx_full_count",
8169                 CTLFLAG_RD, &sc->tx_full_count,
8170                 0, "Number of times the TX chain was full");
8171
8172         SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8173                 "requested_tso_frames",
8174                 CTLFLAG_RD, &sc->requested_tso_frames,
8175                 0, "Number of TSO frames received");
8176
8177         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8178                 "rx_interrupts",
8179                 CTLFLAG_RD, &sc->rx_interrupts,
8180                 0, "Number of RX interrupts");
8181
8182         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8183                 "tx_interrupts",
8184                 CTLFLAG_RD, &sc->tx_interrupts,
8185                 0, "Number of TX interrupts");
8186
8187         SYSCTL_ADD_ULONG(ctx, children, OID_AUTO,
8188                 "rx_intr_time",
8189                 CTLFLAG_RD, &sc->rx_intr_time,
8190                 "RX interrupt time");
8191
8192         SYSCTL_ADD_ULONG(ctx, children, OID_AUTO,
8193                 "tx_intr_time",
8194                 CTLFLAG_RD, &sc->tx_intr_time,
8195                 "TX interrupt time");
8196 #endif
8197
8198         SYSCTL_ADD_ULONG(ctx, children, OID_AUTO,
8199                 "stat_IfHcInOctets",
8200                 CTLFLAG_RD, &sc->stat_IfHCInOctets,
8201                 "Bytes received");
8202
8203         SYSCTL_ADD_ULONG(ctx, children, OID_AUTO,
8204                 "stat_IfHCInBadOctets",
8205                 CTLFLAG_RD, &sc->stat_IfHCInBadOctets,
8206                 "Bad bytes received");
8207
8208         SYSCTL_ADD_ULONG(ctx, children, OID_AUTO,
8209                 "stat_IfHCOutOctets",
8210                 CTLFLAG_RD, &sc->stat_IfHCOutOctets,
8211                 "Bytes sent");
8212
8213         SYSCTL_ADD_ULONG(ctx, children, OID_AUTO,
8214                 "stat_IfHCOutBadOctets",
8215                 CTLFLAG_RD, &sc->stat_IfHCOutBadOctets,
8216                 "Bad bytes sent");
8217
8218         SYSCTL_ADD_ULONG(ctx, children, OID_AUTO,
8219                 "stat_IfHCInUcastPkts",
8220                 CTLFLAG_RD, &sc->stat_IfHCInUcastPkts,
8221                 "Unicast packets received");
8222
8223         SYSCTL_ADD_ULONG(ctx, children, OID_AUTO,
8224                 "stat_IfHCInMulticastPkts",
8225                 CTLFLAG_RD, &sc->stat_IfHCInMulticastPkts,
8226                 "Multicast packets received");
8227
8228         SYSCTL_ADD_ULONG(ctx, children, OID_AUTO,
8229                 "stat_IfHCInBroadcastPkts",
8230                 CTLFLAG_RD, &sc->stat_IfHCInBroadcastPkts,
8231                 "Broadcast packets received");
8232
8233         SYSCTL_ADD_ULONG(ctx, children, OID_AUTO,
8234                 "stat_IfHCOutUcastPkts",
8235                 CTLFLAG_RD, &sc->stat_IfHCOutUcastPkts,
8236                 "Unicast packets sent");
8237
8238         SYSCTL_ADD_ULONG(ctx, children, OID_AUTO,
8239                 "stat_IfHCOutMulticastPkts",
8240                 CTLFLAG_RD, &sc->stat_IfHCOutMulticastPkts,
8241                 "Multicast packets sent");
8242
8243         SYSCTL_ADD_ULONG(ctx, children, OID_AUTO,
8244                 "stat_IfHCOutBroadcastPkts",
8245                 CTLFLAG_RD, &sc->stat_IfHCOutBroadcastPkts,
8246                 "Broadcast packets sent");
8247
8248         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8249                 "stat_emac_tx_stat_dot3statsinternalmactransmiterrors",
8250                 CTLFLAG_RD, &sc->stat_emac_tx_stat_dot3statsinternalmactransmiterrors,
8251                 0, "Internal MAC transmit errors");
8252
8253         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8254                 "stat_Dot3StatsCarrierSenseErrors",
8255                 CTLFLAG_RD, &sc->stat_Dot3StatsCarrierSenseErrors,
8256                 0, "Carrier sense errors");
8257
8258         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8259                 "stat_Dot3StatsFCSErrors",
8260                 CTLFLAG_RD, &sc->stat_Dot3StatsFCSErrors,
8261                 0, "Frame check sequence errors");
8262
8263         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8264                 "stat_Dot3StatsAlignmentErrors",
8265                 CTLFLAG_RD, &sc->stat_Dot3StatsAlignmentErrors,
8266                 0, "Alignment errors");
8267
8268         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8269                 "stat_Dot3StatsSingleCollisionFrames",
8270                 CTLFLAG_RD, &sc->stat_Dot3StatsSingleCollisionFrames,
8271                 0, "Single Collision Frames");
8272
8273         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8274                 "stat_Dot3StatsMultipleCollisionFrames",
8275                 CTLFLAG_RD, &sc->stat_Dot3StatsMultipleCollisionFrames,
8276                 0, "Multiple Collision Frames");
8277
8278         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8279                 "stat_Dot3StatsDeferredTransmissions",
8280                 CTLFLAG_RD, &sc->stat_Dot3StatsDeferredTransmissions,
8281                 0, "Deferred Transmissions");
8282
8283         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8284                 "stat_Dot3StatsExcessiveCollisions",
8285                 CTLFLAG_RD, &sc->stat_Dot3StatsExcessiveCollisions,
8286                 0, "Excessive Collisions");
8287
8288         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8289                 "stat_Dot3StatsLateCollisions",
8290                 CTLFLAG_RD, &sc->stat_Dot3StatsLateCollisions,
8291                 0, "Late Collisions");
8292
8293         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8294                 "stat_EtherStatsCollisions",
8295                 CTLFLAG_RD, &sc->stat_EtherStatsCollisions,
8296                 0, "Collisions");
8297
8298         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8299                 "stat_EtherStatsFragments",
8300                 CTLFLAG_RD, &sc->stat_EtherStatsFragments,
8301                 0, "Fragments");
8302
8303         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8304                 "stat_EtherStatsJabbers",
8305                 CTLFLAG_RD, &sc->stat_EtherStatsJabbers,
8306                 0, "Jabbers");
8307
8308         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8309                 "stat_EtherStatsUndersizePkts",
8310                 CTLFLAG_RD, &sc->stat_EtherStatsUndersizePkts,
8311                 0, "Undersize packets");
8312
8313         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8314                 "stat_EtherStatsOversizePkts",
8315                 CTLFLAG_RD, &sc->stat_EtherStatsOversizePkts,
8316                 0, "stat_EtherStatsOversizePkts");
8317
8318         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8319                 "stat_EtherStatsPktsRx64Octets",
8320                 CTLFLAG_RD, &sc->stat_EtherStatsPktsRx64Octets,
8321                 0, "Bytes received in 64 byte packets");
8322
8323         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8324                 "stat_EtherStatsPktsRx65Octetsto127Octets",
8325                 CTLFLAG_RD, &sc->stat_EtherStatsPktsRx65Octetsto127Octets,
8326                 0, "Bytes received in 65 to 127 byte packets");
8327
8328         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8329                 "stat_EtherStatsPktsRx128Octetsto255Octets",
8330                 CTLFLAG_RD, &sc->stat_EtherStatsPktsRx128Octetsto255Octets,
8331                 0, "Bytes received in 128 to 255 byte packets");
8332
8333         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8334                 "stat_EtherStatsPktsRx256Octetsto511Octets",
8335                 CTLFLAG_RD, &sc->stat_EtherStatsPktsRx256Octetsto511Octets,
8336                 0, "Bytes received in 256 to 511 byte packets");
8337
8338         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8339                 "stat_EtherStatsPktsRx512Octetsto1023Octets",
8340                 CTLFLAG_RD, &sc->stat_EtherStatsPktsRx512Octetsto1023Octets,
8341                 0, "Bytes received in 512 to 1023 byte packets");
8342
8343         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8344                 "stat_EtherStatsPktsRx1024Octetsto1522Octets",
8345                 CTLFLAG_RD, &sc->stat_EtherStatsPktsRx1024Octetsto1522Octets,
8346                 0, "Bytes received in 1024 t0 1522 byte packets");
8347
8348         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8349                 "stat_EtherStatsPktsRx1523Octetsto9022Octets",
8350                 CTLFLAG_RD, &sc->stat_EtherStatsPktsRx1523Octetsto9022Octets,
8351                 0, "Bytes received in 1523 to 9022 byte packets");
8352
8353         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8354                 "stat_EtherStatsPktsTx64Octets",
8355                 CTLFLAG_RD, &sc->stat_EtherStatsPktsTx64Octets,
8356                 0, "Bytes sent in 64 byte packets");
8357
8358         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8359                 "stat_EtherStatsPktsTx65Octetsto127Octets",
8360                 CTLFLAG_RD, &sc->stat_EtherStatsPktsTx65Octetsto127Octets,
8361                 0, "Bytes sent in 65 to 127 byte packets");
8362
8363         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8364                 "stat_EtherStatsPktsTx128Octetsto255Octets",
8365                 CTLFLAG_RD, &sc->stat_EtherStatsPktsTx128Octetsto255Octets,
8366                 0, "Bytes sent in 128 to 255 byte packets");
8367
8368         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8369                 "stat_EtherStatsPktsTx256Octetsto511Octets",
8370                 CTLFLAG_RD, &sc->stat_EtherStatsPktsTx256Octetsto511Octets,
8371                 0, "Bytes sent in 256 to 511 byte packets");
8372
8373         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8374                 "stat_EtherStatsPktsTx512Octetsto1023Octets",
8375                 CTLFLAG_RD, &sc->stat_EtherStatsPktsTx512Octetsto1023Octets,
8376                 0, "Bytes sent in 512 to 1023 byte packets");
8377
8378         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8379                 "stat_EtherStatsPktsTx1024Octetsto1522Octets",
8380                 CTLFLAG_RD, &sc->stat_EtherStatsPktsTx1024Octetsto1522Octets,
8381                 0, "Bytes sent in 1024 to 1522 byte packets");
8382
8383         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8384                 "stat_EtherStatsPktsTx1523Octetsto9022Octets",
8385                 CTLFLAG_RD, &sc->stat_EtherStatsPktsTx1523Octetsto9022Octets,
8386                 0, "Bytes sent in 1523 to 9022 byte packets");
8387
8388         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8389                 "stat_XonPauseFramesReceived",
8390                 CTLFLAG_RD, &sc->stat_XonPauseFramesReceived,
8391                 0, "XON pause frames receved");
8392
8393         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8394                 "stat_XoffPauseFramesReceived",
8395                 CTLFLAG_RD, &sc->stat_XoffPauseFramesReceived,
8396                 0, "XOFF pause frames received");
8397
8398         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8399                 "stat_OutXonSent",
8400                 CTLFLAG_RD, &sc->stat_OutXonSent,
8401                 0, "XON pause frames sent");
8402
8403         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8404                 "stat_OutXoffSent",
8405                 CTLFLAG_RD, &sc->stat_OutXoffSent,
8406                 0, "XOFF pause frames sent");
8407
8408         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8409                 "stat_FlowControlDone",
8410                 CTLFLAG_RD, &sc->stat_FlowControlDone,
8411                 0, "Flow control done");
8412
8413         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8414                 "stat_MacControlFramesReceived",
8415                 CTLFLAG_RD, &sc->stat_MacControlFramesReceived,
8416                 0, "MAC control frames received");
8417
8418         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8419                 "stat_XoffStateEntered",
8420                 CTLFLAG_RD, &sc->stat_XoffStateEntered,
8421                 0, "XOFF state entered");
8422
8423         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8424                 "stat_IfInFramesL2FilterDiscards",
8425                 CTLFLAG_RD, &sc->stat_IfInFramesL2FilterDiscards,
8426                 0, "Received L2 packets discarded");
8427
8428         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8429                 "stat_IfInRuleCheckerDiscards",
8430                 CTLFLAG_RD, &sc->stat_IfInRuleCheckerDiscards,
8431                 0, "Received packets discarded by rule");
8432
8433         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8434                 "stat_IfInFTQDiscards",
8435                 CTLFLAG_RD, &sc->stat_IfInFTQDiscards,
8436                 0, "Received packet FTQ discards");
8437
8438         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8439                 "stat_IfInMBUFDiscards",
8440                 CTLFLAG_RD, &sc->stat_IfInMBUFDiscards,
8441                 0, "Received packets discarded due to lack of controller buffer memory");
8442
8443         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8444                 "stat_IfInRuleCheckerP4Hit",
8445                 CTLFLAG_RD, &sc->stat_IfInRuleCheckerP4Hit,
8446                 0, "Received packets rule checker hits");
8447
8448         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8449                 "stat_CatchupInRuleCheckerDiscards",
8450                 CTLFLAG_RD, &sc->stat_CatchupInRuleCheckerDiscards,
8451                 0, "Received packets discarded in Catchup path");
8452
8453         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8454                 "stat_CatchupInFTQDiscards",
8455                 CTLFLAG_RD, &sc->stat_CatchupInFTQDiscards,
8456                 0, "Received packets discarded in FTQ in Catchup path");
8457
8458         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8459                 "stat_CatchupInMBUFDiscards",
8460                 CTLFLAG_RD, &sc->stat_CatchupInMBUFDiscards,
8461                 0, "Received packets discarded in controller buffer memory in Catchup path");
8462
8463         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8464                 "stat_CatchupInRuleCheckerP4Hit",
8465                 CTLFLAG_RD, &sc->stat_CatchupInRuleCheckerP4Hit,
8466                 0, "Received packets rule checker hits in Catchup path");
8467
8468         SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8469                 "com_no_buffers",
8470                 CTLFLAG_RD, &sc->com_no_buffers,
8471                 0, "Valid packets received but no RX buffers available");
8472
8473 #ifdef BCE_DEBUG
8474         SYSCTL_ADD_PROC(ctx, children, OID_AUTO,
8475                 "driver_state", CTLTYPE_INT | CTLFLAG_RW,
8476                 (void *)sc, 0,
8477                 bce_sysctl_driver_state, "I", "Drive state information");
8478
8479         SYSCTL_ADD_PROC(ctx, children, OID_AUTO,
8480                 "hw_state", CTLTYPE_INT | CTLFLAG_RW,
8481                 (void *)sc, 0,
8482                 bce_sysctl_hw_state, "I", "Hardware state information");
8483
8484         SYSCTL_ADD_PROC(ctx, children, OID_AUTO,
8485                 "bc_state", CTLTYPE_INT | CTLFLAG_RW,
8486                 (void *)sc, 0,
8487                 bce_sysctl_bc_state, "I", "Bootcode state information");
8488
8489         SYSCTL_ADD_PROC(ctx, children, OID_AUTO,
8490                 "dump_rx_chain", CTLTYPE_INT | CTLFLAG_RW,
8491                 (void *)sc, 0,
8492                 bce_sysctl_dump_rx_chain, "I", "Dump rx_bd chain");
8493
8494         SYSCTL_ADD_PROC(ctx, children, OID_AUTO,
8495                 "dump_tx_chain", CTLTYPE_INT | CTLFLAG_RW,
8496                 (void *)sc, 0,
8497                 bce_sysctl_dump_tx_chain, "I", "Dump tx_bd chain");
8498
8499 #ifdef BCE_JUMBO_HDRSPLIT
8500         SYSCTL_ADD_PROC(ctx, children, OID_AUTO,
8501                 "dump_pg_chain", CTLTYPE_INT | CTLFLAG_RW,
8502                 (void *)sc, 0,
8503                 bce_sysctl_dump_pg_chain, "I", "Dump page chain");
8504 #endif
8505         SYSCTL_ADD_PROC(ctx, children, OID_AUTO,
8506                 "dump_ctx", CTLTYPE_INT | CTLFLAG_RW,
8507                 (void *)sc, 0,
8508                 bce_sysctl_dump_ctx, "I", "Dump context memory");
8509
8510         SYSCTL_ADD_PROC(ctx, children, OID_AUTO,
8511                 "breakpoint", CTLTYPE_INT | CTLFLAG_RW,
8512                 (void *)sc, 0,
8513                 bce_sysctl_breakpoint, "I", "Driver breakpoint");
8514
8515         SYSCTL_ADD_PROC(ctx, children, OID_AUTO,
8516                 "reg_read", CTLTYPE_INT | CTLFLAG_RW,
8517                 (void *)sc, 0,
8518                 bce_sysctl_reg_read, "I", "Register read");
8519
8520         SYSCTL_ADD_PROC(ctx, children, OID_AUTO,
8521                 "nvram_read", CTLTYPE_INT | CTLFLAG_RW,
8522                 (void *)sc, 0,
8523                 bce_sysctl_nvram_read, "I", "NVRAM read");
8524
8525         SYSCTL_ADD_PROC(ctx, children, OID_AUTO,
8526                 "phy_read", CTLTYPE_INT | CTLFLAG_RW,
8527                 (void *)sc, 0,
8528                 bce_sysctl_phy_read, "I", "PHY register read");
8529
8530 #endif
8531
8532         DBEXIT(BCE_VERBOSE_MISC);
8533 }
8534
8535
8536 /****************************************************************************/
8537 /* BCE Debug Routines                                                       */
8538 /****************************************************************************/
8539 #ifdef BCE_DEBUG
8540
8541 /****************************************************************************/
8542 /* Freezes the controller to allow for a cohesive state dump.               */
8543 /*                                                                          */
8544 /* Returns:                                                                 */
8545 /*   Nothing.                                                               */
8546 /****************************************************************************/
8547 static void
8548 bce_freeze_controller(struct bce_softc *sc)
8549 {
8550         u32 val;
8551         val = REG_RD(sc, BCE_MISC_COMMAND);
8552         val |= BCE_MISC_COMMAND_DISABLE_ALL;
8553         REG_WR(sc, BCE_MISC_COMMAND, val);
8554 }
8555
8556
8557 /****************************************************************************/
8558 /* Unfreezes the controller after a freeze operation.  This may not always  */
8559 /* work and the controller will require a reset!                            */
8560 /*                                                                          */
8561 /* Returns:                                                                 */
8562 /*   Nothing.                                                               */
8563 /****************************************************************************/
8564 static void
8565 bce_unfreeze_controller(struct bce_softc *sc)
8566 {
8567         u32 val;
8568         val = REG_RD(sc, BCE_MISC_COMMAND);
8569         val |= BCE_MISC_COMMAND_ENABLE_ALL;
8570         REG_WR(sc, BCE_MISC_COMMAND, val);
8571 }
8572
8573
8574 /****************************************************************************/
8575 /* Prints out Ethernet frame information from an mbuf.                      */
8576 /*                                                                          */
8577 /* Partially decode an Ethernet frame to look at some important headers.    */
8578 /*                                                                          */
8579 /* Returns:                                                                 */
8580 /*   Nothing.                                                               */
8581 /****************************************************************************/
8582 static void
8583 bce_dump_enet(struct bce_softc *sc, struct mbuf *m)
8584 {
8585         struct ether_vlan_header *eh;
8586         u16 etype;
8587         int ehlen;
8588         struct ip *ip;
8589         struct tcphdr *th;
8590         struct udphdr *uh;
8591         struct arphdr *ah;
8592
8593                 BCE_PRINTF(
8594                         "-----------------------------"
8595                         " Frame Decode "
8596                         "-----------------------------\n");
8597
8598         eh = mtod(m, struct ether_vlan_header *);
8599
8600         /* Handle VLAN encapsulation if present. */
8601         if (eh->evl_encap_proto == htons(ETHERTYPE_VLAN)) {
8602                 etype = ntohs(eh->evl_proto);
8603                 ehlen = ETHER_HDR_LEN + ETHER_VLAN_ENCAP_LEN;
8604         } else {
8605                 etype = ntohs(eh->evl_encap_proto);
8606                 ehlen = ETHER_HDR_LEN;
8607         }
8608
8609         /* ToDo: Add VLAN output. */
8610         BCE_PRINTF("enet: dest = %6D, src = %6D, type = 0x%04X, hlen = %d\n",
8611                 eh->evl_dhost, ":", eh->evl_shost, ":", etype, ehlen);
8612
8613         switch (etype) {
8614                 case ETHERTYPE_IP:
8615                         ip = (struct ip *)(m->m_data + ehlen);
8616                         BCE_PRINTF("--ip: dest = 0x%08X , src = 0x%08X, len = %d bytes, "
8617                                 "protocol = 0x%02X, xsum = 0x%04X\n",
8618                                 ntohl(ip->ip_dst.s_addr), ntohl(ip->ip_src.s_addr),
8619                                 ntohs(ip->ip_len), ip->ip_p, ntohs(ip->ip_sum));
8620
8621                         switch (ip->ip_p) {
8622                                 case IPPROTO_TCP:
8623                                         th = (struct tcphdr *)((caddr_t)ip + (ip->ip_hl << 2));
8624                                         BCE_PRINTF("-tcp: dest = %d, src = %d, hlen = %d bytes, "
8625                                                 "flags = 0x%b, csum = 0x%04X\n",
8626                                                 ntohs(th->th_dport), ntohs(th->th_sport), (th->th_off << 2),
8627                                                 th->th_flags, "\20\10CWR\07ECE\06URG\05ACK\04PSH\03RST\02SYN\01FIN",
8628                                                 ntohs(th->th_sum));
8629                                         break;
8630                                 case IPPROTO_UDP:
8631                             uh = (struct udphdr *)((caddr_t)ip + (ip->ip_hl << 2));
8632                                         BCE_PRINTF("-udp: dest = %d, src = %d, len = %d bytes, "
8633                                                 "csum = 0x%04X\n", ntohs(uh->uh_dport), ntohs(uh->uh_sport),
8634                                                 ntohs(uh->uh_ulen), ntohs(uh->uh_sum));
8635                                         break;
8636                                 case IPPROTO_ICMP:
8637                                         BCE_PRINTF("icmp:\n");
8638                                         break;
8639                                 default:
8640                                         BCE_PRINTF("----: Other IP protocol.\n");
8641                         }
8642                         break;
8643                 case ETHERTYPE_IPV6:
8644                         BCE_PRINTF("ipv6: No decode supported.\n");
8645                         break;
8646                 case ETHERTYPE_ARP:
8647                         BCE_PRINTF("-arp: ");
8648                         ah = (struct arphdr *) (m->m_data + ehlen);
8649                         switch (ntohs(ah->ar_op)) {
8650                                 case ARPOP_REVREQUEST:
8651                                         printf("reverse ARP request\n");
8652                                         break;
8653                                 case ARPOP_REVREPLY:
8654                                         printf("reverse ARP reply\n");
8655                                         break;
8656                                 case ARPOP_REQUEST:
8657                                         printf("ARP request\n");
8658                                         break;
8659                                 case ARPOP_REPLY:
8660                                         printf("ARP reply\n");
8661                                         break;
8662                                 default:
8663                                         printf("other ARP operation\n");
8664                         }
8665                         break;
8666                 default:
8667                         BCE_PRINTF("----: Other protocol.\n");
8668         }
8669
8670         BCE_PRINTF(
8671                 "-----------------------------"
8672                 "--------------"
8673                 "-----------------------------\n");
8674 }
8675
8676
8677 /****************************************************************************/
8678 /* Prints out information about an mbuf.                                    */
8679 /*                                                                          */
8680 /* Returns:                                                                 */
8681 /*   Nothing.                                                               */
8682 /****************************************************************************/
8683 static __attribute__ ((noinline)) void
8684 bce_dump_mbuf(struct bce_softc *sc, struct mbuf *m)
8685 {
8686         struct mbuf *mp = m;
8687
8688         if (m == NULL) {
8689                 BCE_PRINTF("mbuf: null pointer\n");
8690                 return;
8691         }
8692
8693         while (mp) {
8694                 BCE_PRINTF("mbuf: %p, m_len = %d, m_flags = 0x%b, m_data = %p\n",
8695                         mp, mp->m_len, mp->m_flags,
8696                         "\20\1M_EXT\2M_PKTHDR\3M_EOR\4M_RDONLY",
8697                         mp->m_data);
8698
8699                 if (mp->m_flags & M_PKTHDR) {
8700                         BCE_PRINTF("- m_pkthdr: len = %d, flags = 0x%b, csum_flags = %b\n",
8701                                 mp->m_pkthdr.len, mp->m_flags,
8702                                 "\20\12M_BCAST\13M_MCAST\14M_FRAG\15M_FIRSTFRAG"
8703                                 "\16M_LASTFRAG\21M_VLANTAG\22M_PROMISC\23M_NOFREE",
8704                                 mp->m_pkthdr.csum_flags,
8705                                 "\20\1CSUM_IP\2CSUM_TCP\3CSUM_UDP\4CSUM_IP_FRAGS"
8706                                 "\5CSUM_FRAGMENT\6CSUM_TSO\11CSUM_IP_CHECKED"
8707                                 "\12CSUM_IP_VALID\13CSUM_DATA_VALID\14CSUM_PSEUDO_HDR");
8708                 }
8709
8710                 if (mp->m_flags & M_EXT) {
8711                         BCE_PRINTF("- m_ext: %p, ext_size = %d, type = ",
8712                                 mp->m_ext.ext_buf, mp->m_ext.ext_size);
8713                         switch (mp->m_ext.ext_type) {
8714                                 case EXT_CLUSTER:    printf("EXT_CLUSTER\n"); break;
8715                                 case EXT_SFBUF:      printf("EXT_SFBUF\n"); break;
8716                                 case EXT_JUMBO9:     printf("EXT_JUMBO9\n"); break;
8717                                 case EXT_JUMBO16:    printf("EXT_JUMBO16\n"); break;
8718                                 case EXT_PACKET:     printf("EXT_PACKET\n"); break;
8719                                 case EXT_MBUF:       printf("EXT_MBUF\n"); break;
8720                                 case EXT_NET_DRV:    printf("EXT_NET_DRV\n"); break;
8721                                 case EXT_MOD_TYPE:   printf("EXT_MDD_TYPE\n"); break;
8722                                 case EXT_DISPOSABLE: printf("EXT_DISPOSABLE\n"); break;
8723                                 case EXT_EXTREF:     printf("EXT_EXTREF\n"); break;
8724                                 default:             printf("UNKNOWN\n");
8725                         }
8726                 }
8727
8728                 mp = mp->m_next;
8729         }
8730 }
8731
8732
8733 /****************************************************************************/
8734 /* Prints out the mbufs in the TX mbuf chain.                               */
8735 /*                                                                          */
8736 /* Returns:                                                                 */
8737 /*   Nothing.                                                               */
8738 /****************************************************************************/
8739 static __attribute__ ((noinline)) void
8740 bce_dump_tx_mbuf_chain(struct bce_softc *sc, u16 chain_prod, int count)
8741 {
8742         struct mbuf *m;
8743
8744         BCE_PRINTF(
8745                 "----------------------------"
8746                 "  tx mbuf data  "
8747                 "----------------------------\n");
8748
8749         for (int i = 0; i < count; i++) {
8750                 m = sc->tx_mbuf_ptr[chain_prod];
8751                 BCE_PRINTF("txmbuf[0x%04X]\n", chain_prod);
8752                 bce_dump_mbuf(sc, m);
8753                 chain_prod = TX_CHAIN_IDX(NEXT_TX_BD(chain_prod));
8754         }
8755
8756         BCE_PRINTF(
8757                 "----------------------------"
8758                 "----------------"
8759                 "----------------------------\n");
8760 }
8761
8762
8763 /****************************************************************************/
8764 /* Prints out the mbufs in the RX mbuf chain.                               */
8765 /*                                                                          */
8766 /* Returns:                                                                 */
8767 /*   Nothing.                                                               */
8768 /****************************************************************************/
8769 static __attribute__ ((noinline)) void
8770 bce_dump_rx_mbuf_chain(struct bce_softc *sc, u16 chain_prod, int count)
8771 {
8772         struct mbuf *m;
8773
8774         BCE_PRINTF(
8775                 "----------------------------"
8776                 "  rx mbuf data  "
8777                 "----------------------------\n");
8778
8779         for (int i = 0; i < count; i++) {
8780                 m = sc->rx_mbuf_ptr[chain_prod];
8781                 BCE_PRINTF("rxmbuf[0x%04X]\n", chain_prod);
8782                 bce_dump_mbuf(sc, m);
8783                 chain_prod = RX_CHAIN_IDX(NEXT_RX_BD(chain_prod));
8784         }
8785
8786
8787         BCE_PRINTF(
8788                 "----------------------------"
8789                 "----------------"
8790                 "----------------------------\n");
8791 }
8792
8793
8794 #ifdef BCE_JUMBO_HDRSPLIT
8795 /****************************************************************************/
8796 /* Prints out the mbufs in the mbuf page chain.                             */
8797 /*                                                                          */
8798 /* Returns:                                                                 */
8799 /*   Nothing.                                                               */
8800 /****************************************************************************/
8801 static __attribute__ ((noinline)) void
8802 bce_dump_pg_mbuf_chain(struct bce_softc *sc, u16 chain_prod, int count)
8803 {
8804         struct mbuf *m;
8805
8806         BCE_PRINTF(
8807                 "----------------------------"
8808                 "  pg mbuf data  "
8809                 "----------------------------\n");
8810
8811         for (int i = 0; i < count; i++) {
8812                 m = sc->pg_mbuf_ptr[chain_prod];
8813                 BCE_PRINTF("pgmbuf[0x%04X]\n", chain_prod);
8814                 bce_dump_mbuf(sc, m);
8815                 chain_prod = PG_CHAIN_IDX(NEXT_PG_BD(chain_prod));
8816         }
8817
8818
8819         BCE_PRINTF(
8820                 "----------------------------"
8821                 "----------------"
8822                 "----------------------------\n");
8823 }
8824 #endif
8825
8826
8827 /****************************************************************************/
8828 /* Prints out a tx_bd structure.                                            */
8829 /*                                                                          */
8830 /* Returns:                                                                 */
8831 /*   Nothing.                                                               */
8832 /****************************************************************************/
8833 static __attribute__ ((noinline)) void
8834 bce_dump_txbd(struct bce_softc *sc, int idx, struct tx_bd *txbd)
8835 {
8836         if (idx > MAX_TX_BD)
8837                 /* Index out of range. */
8838                 BCE_PRINTF("tx_bd[0x%04X]: Invalid tx_bd index!\n", idx);
8839         else if ((idx & USABLE_TX_BD_PER_PAGE) == USABLE_TX_BD_PER_PAGE)
8840                 /* TX Chain page pointer. */
8841                 BCE_PRINTF("tx_bd[0x%04X]: haddr = 0x%08X:%08X, chain page pointer\n",
8842                         idx, txbd->tx_bd_haddr_hi, txbd->tx_bd_haddr_lo);
8843         else {
8844                         /* Normal tx_bd entry. */
8845                         BCE_PRINTF("tx_bd[0x%04X]: haddr = 0x%08X:%08X, nbytes = 0x%08X, "
8846                                 "vlan tag= 0x%04X, flags = 0x%04X (", idx,
8847                                 txbd->tx_bd_haddr_hi, txbd->tx_bd_haddr_lo,
8848                                 txbd->tx_bd_mss_nbytes, txbd->tx_bd_vlan_tag,
8849                                 txbd->tx_bd_flags);
8850
8851                         if (txbd->tx_bd_flags & TX_BD_FLAGS_CONN_FAULT)
8852                                 printf(" CONN_FAULT");
8853
8854                         if (txbd->tx_bd_flags & TX_BD_FLAGS_TCP_UDP_CKSUM)
8855                                 printf(" TCP_UDP_CKSUM");
8856
8857                         if (txbd->tx_bd_flags & TX_BD_FLAGS_IP_CKSUM)
8858                                 printf(" IP_CKSUM");
8859
8860                         if (txbd->tx_bd_flags & TX_BD_FLAGS_VLAN_TAG)
8861                                 printf("  VLAN");
8862
8863                         if (txbd->tx_bd_flags & TX_BD_FLAGS_COAL_NOW)
8864                                 printf(" COAL_NOW");
8865
8866                         if (txbd->tx_bd_flags & TX_BD_FLAGS_DONT_GEN_CRC)
8867                                 printf(" DONT_GEN_CRC");
8868
8869                         if (txbd->tx_bd_flags & TX_BD_FLAGS_START)
8870                                 printf(" START");
8871
8872                         if (txbd->tx_bd_flags & TX_BD_FLAGS_END)
8873                                 printf(" END");
8874
8875                         if (txbd->tx_bd_flags & TX_BD_FLAGS_SW_LSO)
8876                                 printf(" LSO");
8877
8878                         if (txbd->tx_bd_flags & TX_BD_FLAGS_SW_OPTION_WORD)
8879                                 printf(" OPTION_WORD");
8880
8881                         if (txbd->tx_bd_flags & TX_BD_FLAGS_SW_FLAGS)
8882                                 printf(" FLAGS");
8883
8884                         if (txbd->tx_bd_flags & TX_BD_FLAGS_SW_SNAP)
8885                                 printf(" SNAP");
8886
8887                         printf(" )\n");
8888                 }
8889
8890 }
8891
8892
8893 /****************************************************************************/
8894 /* Prints out a rx_bd structure.                                            */
8895 /*                                                                          */
8896 /* Returns:                                                                 */
8897 /*   Nothing.                                                               */
8898 /****************************************************************************/
8899 static __attribute__ ((noinline)) void
8900 bce_dump_rxbd(struct bce_softc *sc, int idx, struct rx_bd *rxbd)
8901 {
8902         if (idx > MAX_RX_BD)
8903                 /* Index out of range. */
8904                 BCE_PRINTF("rx_bd[0x%04X]: Invalid rx_bd index!\n", idx);
8905         else if ((idx & USABLE_RX_BD_PER_PAGE) == USABLE_RX_BD_PER_PAGE)
8906                 /* RX Chain page pointer. */
8907                 BCE_PRINTF("rx_bd[0x%04X]: haddr = 0x%08X:%08X, chain page pointer\n",
8908                         idx, rxbd->rx_bd_haddr_hi, rxbd->rx_bd_haddr_lo);
8909         else
8910                 /* Normal rx_bd entry. */
8911                 BCE_PRINTF("rx_bd[0x%04X]: haddr = 0x%08X:%08X, nbytes = 0x%08X, "
8912                         "flags = 0x%08X\n", idx,
8913                         rxbd->rx_bd_haddr_hi, rxbd->rx_bd_haddr_lo,
8914                         rxbd->rx_bd_len, rxbd->rx_bd_flags);
8915 }
8916
8917
8918 #ifdef BCE_JUMBO_HDRSPLIT
8919 /****************************************************************************/
8920 /* Prints out a rx_bd structure in the page chain.                          */
8921 /*                                                                          */
8922 /* Returns:                                                                 */
8923 /*   Nothing.                                                               */
8924 /****************************************************************************/
8925 static __attribute__ ((noinline)) void
8926 bce_dump_pgbd(struct bce_softc *sc, int idx, struct rx_bd *pgbd)
8927 {
8928         if (idx > MAX_PG_BD)
8929                 /* Index out of range. */
8930                 BCE_PRINTF("pg_bd[0x%04X]: Invalid pg_bd index!\n", idx);
8931         else if ((idx & USABLE_PG_BD_PER_PAGE) == USABLE_PG_BD_PER_PAGE)
8932                 /* Page Chain page pointer. */
8933                 BCE_PRINTF("px_bd[0x%04X]: haddr = 0x%08X:%08X, chain page pointer\n",
8934                         idx, pgbd->rx_bd_haddr_hi, pgbd->rx_bd_haddr_lo);
8935         else
8936                 /* Normal rx_bd entry. */
8937                 BCE_PRINTF("pg_bd[0x%04X]: haddr = 0x%08X:%08X, nbytes = 0x%08X, "
8938                         "flags = 0x%08X\n", idx,
8939                         pgbd->rx_bd_haddr_hi, pgbd->rx_bd_haddr_lo,
8940                         pgbd->rx_bd_len, pgbd->rx_bd_flags);
8941 }
8942 #endif
8943
8944
8945 /****************************************************************************/
8946 /* Prints out a l2_fhdr structure.                                          */
8947 /*                                                                          */
8948 /* Returns:                                                                 */
8949 /*   Nothing.                                                               */
8950 /****************************************************************************/
8951 static __attribute__ ((noinline)) void
8952 bce_dump_l2fhdr(struct bce_softc *sc, int idx, struct l2_fhdr *l2fhdr)
8953 {
8954         BCE_PRINTF("l2_fhdr[0x%04X]: status = 0x%b, "
8955                 "pkt_len = %d, vlan = 0x%04x, ip_xsum/hdr_len = 0x%04X, "
8956                 "tcp_udp_xsum = 0x%04X\n", idx,
8957                 l2fhdr->l2_fhdr_status, BCE_L2FHDR_PRINTFB,
8958                 l2fhdr->l2_fhdr_pkt_len, l2fhdr->l2_fhdr_vlan_tag,
8959                 l2fhdr->l2_fhdr_ip_xsum, l2fhdr->l2_fhdr_tcp_udp_xsum);
8960 }
8961
8962
8963 /****************************************************************************/
8964 /* Prints out context memory info.  (Only useful for CID 0 to 16.)          */
8965 /*                                                                          */
8966 /* Returns:                                                                 */
8967 /*   Nothing.                                                               */
8968 /****************************************************************************/
8969 static __attribute__ ((noinline)) void
8970 bce_dump_ctx(struct bce_softc *sc, u16 cid)
8971 {
8972         if (cid <= TX_CID) {
8973                 BCE_PRINTF(
8974                         "----------------------------"
8975                         "    CTX Data    "
8976                         "----------------------------\n");
8977
8978                 BCE_PRINTF("     0x%04X - (CID) Context ID\n", cid);
8979
8980                 if (cid == RX_CID) {
8981                         BCE_PRINTF(" 0x%08X - (L2CTX_RX_HOST_BDIDX) host rx "
8982                                 "producer index\n",
8983                                 CTX_RD(sc, GET_CID_ADDR(cid), BCE_L2CTX_RX_HOST_BDIDX));
8984                         BCE_PRINTF(" 0x%08X - (L2CTX_RX_HOST_BSEQ) host byte sequence\n",
8985                                 CTX_RD(sc, GET_CID_ADDR(cid), BCE_L2CTX_RX_HOST_BSEQ));
8986                         BCE_PRINTF(" 0x%08X - (L2CTX_RX_NX_BSEQ) h/w byte sequence\n",
8987                                 CTX_RD(sc, GET_CID_ADDR(cid), BCE_L2CTX_RX_NX_BSEQ));
8988                         BCE_PRINTF(" 0x%08X - (L2CTX_RX_NX_BDHADDR_HI) h/w buffer "
8989                                 "descriptor address\n",
8990                                 CTX_RD(sc, GET_CID_ADDR(cid), BCE_L2CTX_RX_NX_BDHADDR_HI));
8991                         BCE_PRINTF(" 0x%08X - (L2CTX_RX_NX_BDHADDR_LO) h/w buffer "
8992                                 "descriptor address\n",
8993                                 CTX_RD(sc, GET_CID_ADDR(cid), BCE_L2CTX_RX_NX_BDHADDR_LO));
8994                         BCE_PRINTF(" 0x%08X - (L2CTX_RX_NX_BDIDX) h/w rx consumer index\n",
8995                                 CTX_RD(sc, GET_CID_ADDR(cid), BCE_L2CTX_RX_NX_BDIDX));
8996                         BCE_PRINTF(" 0x%08X - (L2CTX_RX_HOST_PG_BDIDX) host page "
8997                                 "producer index\n",
8998                                 CTX_RD(sc, GET_CID_ADDR(cid), BCE_L2CTX_RX_HOST_PG_BDIDX));
8999                         BCE_PRINTF(" 0x%08X - (L2CTX_RX_PG_BUF_SIZE) host rx_bd/page "
9000                                 "buffer size\n",
9001                                 CTX_RD(sc, GET_CID_ADDR(cid), BCE_L2CTX_RX_PG_BUF_SIZE));
9002                         BCE_PRINTF(" 0x%08X - (L2CTX_RX_NX_PG_BDHADDR_HI) h/w page "
9003                                 "chain address\n",
9004                                 CTX_RD(sc, GET_CID_ADDR(cid), BCE_L2CTX_RX_NX_PG_BDHADDR_HI));
9005                         BCE_PRINTF(" 0x%08X - (L2CTX_RX_NX_PG_BDHADDR_LO) h/w page "
9006                                 "chain address\n",
9007                                 CTX_RD(sc, GET_CID_ADDR(cid), BCE_L2CTX_RX_NX_PG_BDHADDR_LO));
9008                         BCE_PRINTF(" 0x%08X - (L2CTX_RX_NX_PG_BDIDX) h/w page "
9009                                 "consumer index\n",
9010                                 CTX_RD(sc, GET_CID_ADDR(cid), BCE_L2CTX_RX_NX_PG_BDIDX));
9011                 } else if (cid == TX_CID) {
9012                         if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
9013                                 (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
9014                                 BCE_PRINTF(" 0x%08X - (L2CTX_TX_TYPE_XI) ctx type\n",
9015                                         CTX_RD(sc, GET_CID_ADDR(cid), BCE_L2CTX_TX_TYPE_XI));
9016                                 BCE_PRINTF(" 0x%08X - (L2CTX_CMD_TX_TYPE_XI) ctx cmd\n",
9017                                         CTX_RD(sc, GET_CID_ADDR(cid), BCE_L2CTX_TX_CMD_TYPE_XI));
9018                                 BCE_PRINTF(" 0x%08X - (L2CTX_TX_TBDR_BDHADDR_HI_XI) h/w buffer "
9019                                         "descriptor address\n", CTX_RD(sc,
9020                                         GET_CID_ADDR(cid), BCE_L2CTX_TX_TBDR_BHADDR_HI_XI));
9021                                 BCE_PRINTF(" 0x%08X - (L2CTX_TX_TBDR_BHADDR_LO_XI) h/w buffer "
9022                                         "descriptor address\n", CTX_RD(sc,
9023                                         GET_CID_ADDR(cid), BCE_L2CTX_TX_TBDR_BHADDR_LO_XI));
9024                                 BCE_PRINTF(" 0x%08X - (L2CTX_TX_HOST_BIDX_XI) host producer "
9025                                         "index\n", CTX_RD(sc, GET_CID_ADDR(cid),
9026                                         BCE_L2CTX_TX_HOST_BIDX_XI));
9027                                 BCE_PRINTF(" 0x%08X - (L2CTX_TX_HOST_BSEQ_XI) host byte "
9028                                         "sequence\n", CTX_RD(sc, GET_CID_ADDR(cid),
9029                                         BCE_L2CTX_TX_HOST_BSEQ_XI));
9030                         } else {
9031                                 BCE_PRINTF(" 0x%08X - (L2CTX_TX_TYPE) ctx type\n",
9032                                         CTX_RD(sc, GET_CID_ADDR(cid), BCE_L2CTX_TX_TYPE));
9033                                 BCE_PRINTF(" 0x%08X - (L2CTX_TX_CMD_TYPE) ctx cmd\n",
9034                                         CTX_RD(sc, GET_CID_ADDR(cid), BCE_L2CTX_TX_CMD_TYPE));
9035                                 BCE_PRINTF(" 0x%08X - (L2CTX_TX_TBDR_BDHADDR_HI) h/w buffer "
9036                                         "descriptor address\n", CTX_RD(sc, GET_CID_ADDR(cid),
9037                                         BCE_L2CTX_TX_TBDR_BHADDR_HI));
9038                                 BCE_PRINTF(" 0x%08X - (L2CTX_TX_TBDR_BHADDR_LO) h/w buffer "
9039                                         "descriptor address\n", CTX_RD(sc, GET_CID_ADDR(cid),
9040                                         BCE_L2CTX_TX_TBDR_BHADDR_LO));
9041                                 BCE_PRINTF(" 0x%08X - (L2CTX_TX_HOST_BIDX) host producer "
9042                                         "index\n", CTX_RD(sc, GET_CID_ADDR(cid),
9043                                         BCE_L2CTX_TX_HOST_BIDX));
9044                                 BCE_PRINTF(" 0x%08X - (L2CTX_TX_HOST_BSEQ) host byte "
9045                                         "sequence\n", CTX_RD(sc, GET_CID_ADDR(cid),
9046                                         BCE_L2CTX_TX_HOST_BSEQ));
9047                         }
9048                 } else
9049                         BCE_PRINTF(" Unknown CID\n");
9050
9051                 BCE_PRINTF(
9052                         "----------------------------"
9053                         "    Raw CTX     "
9054                         "----------------------------\n");
9055
9056                 for (int i = 0x0; i < 0x300; i += 0x10) {
9057                         BCE_PRINTF("0x%04X: 0x%08X 0x%08X 0x%08X 0x%08X\n", i,
9058                                 CTX_RD(sc, GET_CID_ADDR(cid), i),
9059                                 CTX_RD(sc, GET_CID_ADDR(cid), i + 0x4),
9060                                 CTX_RD(sc, GET_CID_ADDR(cid), i + 0x8),
9061                                 CTX_RD(sc, GET_CID_ADDR(cid), i + 0xc));
9062                 }
9063
9064
9065                 BCE_PRINTF(
9066                         "----------------------------"
9067                         "----------------"
9068                         "----------------------------\n");
9069         }
9070 }
9071
9072
9073 /****************************************************************************/
9074 /* Prints out the FTQ data.                                                 */
9075 /*                                                                          */
9076 /* Returns:                                                                */
9077 /*   Nothing.                                                               */
9078 /****************************************************************************/
9079 static __attribute__ ((noinline)) void
9080 bce_dump_ftqs(struct bce_softc *sc)
9081 {
9082         u32 cmd, ctl, cur_depth, max_depth, valid_cnt, val;
9083
9084         BCE_PRINTF(
9085                 "----------------------------"
9086                 "    FTQ Data    "
9087                 "----------------------------\n");
9088
9089         BCE_PRINTF("   FTQ    Command    Control   Depth_Now  Max_Depth  Valid_Cnt \n");
9090         BCE_PRINTF(" ------- ---------- ---------- ---------- ---------- ----------\n");
9091
9092         /* Setup the generic statistic counters for the FTQ valid count. */
9093         val = (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_RV2PPQ_VALID_CNT << 24) |
9094                 (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_RXPCQ_VALID_CNT  << 16) |
9095                 (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_RXPQ_VALID_CNT   <<  8) |
9096                 (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_RLUPQ_VALID_CNT);
9097         REG_WR(sc, BCE_HC_STAT_GEN_SEL_0, val);
9098
9099         val = (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_TSCHQ_VALID_CNT  << 24) |
9100                 (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_RDMAQ_VALID_CNT  << 16) |
9101                 (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_RV2PTQ_VALID_CNT <<  8) |
9102                 (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_RV2PMQ_VALID_CNT);
9103         REG_WR(sc, BCE_HC_STAT_GEN_SEL_1, val);
9104
9105         val = (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_TPATQ_VALID_CNT  << 24) |
9106                 (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_TDMAQ_VALID_CNT  << 16) |
9107                 (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_TXPQ_VALID_CNT   <<  8) |
9108                 (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_TBDRQ_VALID_CNT);
9109         REG_WR(sc, BCE_HC_STAT_GEN_SEL_2, val);
9110
9111         val = (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_COMQ_VALID_CNT   << 24) |
9112                 (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_COMTQ_VALID_CNT  << 16) |
9113                 (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_COMXQ_VALID_CNT  <<  8) |
9114                 (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_TASQ_VALID_CNT);
9115         REG_WR(sc, BCE_HC_STAT_GEN_SEL_3, val);
9116
9117         /* Input queue to the Receive Lookup state machine */
9118         cmd = REG_RD(sc, BCE_RLUP_FTQ_CMD);
9119         ctl = REG_RD(sc, BCE_RLUP_FTQ_CTL);
9120         cur_depth = (ctl & BCE_RLUP_FTQ_CTL_CUR_DEPTH) >> 22;
9121         max_depth = (ctl & BCE_RLUP_FTQ_CTL_MAX_DEPTH) >> 12;
9122         valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT0);
9123         BCE_PRINTF(" RLUP    0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9124                 cmd, ctl, cur_depth, max_depth, valid_cnt);
9125
9126         /* Input queue to the Receive Processor */
9127         cmd = REG_RD_IND(sc, BCE_RXP_FTQ_CMD);
9128         ctl = REG_RD_IND(sc, BCE_RXP_FTQ_CTL);
9129         cur_depth = (ctl & BCE_RXP_FTQ_CTL_CUR_DEPTH) >> 22;
9130         max_depth = (ctl & BCE_RXP_FTQ_CTL_MAX_DEPTH) >> 12;
9131         valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT1);
9132         BCE_PRINTF(" RXP     0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9133                 cmd, ctl, cur_depth, max_depth, valid_cnt);
9134
9135         /* Input queue to the Recevie Processor */
9136         cmd = REG_RD_IND(sc, BCE_RXP_CFTQ_CMD);
9137         ctl = REG_RD_IND(sc, BCE_RXP_CFTQ_CTL);
9138         cur_depth = (ctl & BCE_RXP_CFTQ_CTL_CUR_DEPTH) >> 22;
9139         max_depth = (ctl & BCE_RXP_CFTQ_CTL_MAX_DEPTH) >> 12;
9140         valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT2);
9141         BCE_PRINTF(" RXPC    0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9142                 cmd, ctl, cur_depth, max_depth, valid_cnt);
9143
9144         /* Input queue to the Receive Virtual to Physical state machine */
9145         cmd = REG_RD(sc, BCE_RV2P_PFTQ_CMD);
9146         ctl = REG_RD(sc, BCE_RV2P_PFTQ_CTL);
9147         cur_depth = (ctl & BCE_RV2P_PFTQ_CTL_CUR_DEPTH) >> 22;
9148         max_depth = (ctl & BCE_RV2P_PFTQ_CTL_MAX_DEPTH) >> 12;
9149         valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT3);
9150         BCE_PRINTF(" RV2PP   0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9151                 cmd, ctl, cur_depth, max_depth, valid_cnt);
9152
9153         /* Input queue to the Recevie Virtual to Physical state machine */
9154         cmd = REG_RD(sc, BCE_RV2P_MFTQ_CMD);
9155         ctl = REG_RD(sc, BCE_RV2P_MFTQ_CTL);
9156         cur_depth = (ctl & BCE_RV2P_MFTQ_CTL_CUR_DEPTH) >> 22;
9157         max_depth = (ctl & BCE_RV2P_MFTQ_CTL_MAX_DEPTH) >> 12;
9158         valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT4);
9159         BCE_PRINTF(" RV2PM   0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9160                 cmd, ctl, cur_depth, max_depth, valid_cnt);
9161
9162         /* Input queue to the Receive Virtual to Physical state machine */
9163         cmd = REG_RD(sc, BCE_RV2P_TFTQ_CMD);
9164         ctl = REG_RD(sc, BCE_RV2P_TFTQ_CTL);
9165         cur_depth = (ctl & BCE_RV2P_TFTQ_CTL_CUR_DEPTH) >> 22;
9166         max_depth = (ctl & BCE_RV2P_TFTQ_CTL_MAX_DEPTH) >> 12;
9167         valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT5);
9168         BCE_PRINTF(" RV2PT   0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9169                 cmd, ctl, cur_depth, max_depth, valid_cnt);
9170
9171         /* Input queue to the Receive DMA state machine */
9172         cmd = REG_RD(sc, BCE_RDMA_FTQ_CMD);
9173         ctl = REG_RD(sc, BCE_RDMA_FTQ_CTL);
9174         cur_depth = (ctl & BCE_RDMA_FTQ_CTL_CUR_DEPTH) >> 22;
9175         max_depth = (ctl & BCE_RDMA_FTQ_CTL_MAX_DEPTH) >> 12;
9176         valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT6);
9177         BCE_PRINTF(" RDMA    0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9178                 cmd, ctl, cur_depth, max_depth, valid_cnt);
9179
9180         /* Input queue to the Transmit Scheduler state machine */
9181         cmd = REG_RD(sc, BCE_TSCH_FTQ_CMD);
9182         ctl = REG_RD(sc, BCE_TSCH_FTQ_CTL);
9183         cur_depth = (ctl & BCE_TSCH_FTQ_CTL_CUR_DEPTH) >> 22;
9184         max_depth = (ctl & BCE_TSCH_FTQ_CTL_MAX_DEPTH) >> 12;
9185         valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT7);
9186         BCE_PRINTF(" TSCH    0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9187                 cmd, ctl, cur_depth, max_depth, valid_cnt);
9188
9189         /* Input queue to the Transmit Buffer Descriptor state machine */
9190         cmd = REG_RD(sc, BCE_TBDR_FTQ_CMD);
9191         ctl = REG_RD(sc, BCE_TBDR_FTQ_CTL);
9192         cur_depth = (ctl & BCE_TBDR_FTQ_CTL_CUR_DEPTH) >> 22;
9193         max_depth = (ctl & BCE_TBDR_FTQ_CTL_MAX_DEPTH) >> 12;
9194         valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT8);
9195         BCE_PRINTF(" TBDR    0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9196                 cmd, ctl, cur_depth, max_depth, valid_cnt);
9197
9198         /* Input queue to the Transmit Processor */
9199         cmd = REG_RD_IND(sc, BCE_TXP_FTQ_CMD);
9200         ctl = REG_RD_IND(sc, BCE_TXP_FTQ_CTL);
9201         cur_depth = (ctl & BCE_TXP_FTQ_CTL_CUR_DEPTH) >> 22;
9202         max_depth = (ctl & BCE_TXP_FTQ_CTL_MAX_DEPTH) >> 12;
9203         valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT9);
9204         BCE_PRINTF(" TXP     0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9205                 cmd, ctl, cur_depth, max_depth, valid_cnt);
9206
9207         /* Input queue to the Transmit DMA state machine */
9208         cmd = REG_RD(sc, BCE_TDMA_FTQ_CMD);
9209         ctl = REG_RD(sc, BCE_TDMA_FTQ_CTL);
9210         cur_depth = (ctl & BCE_TDMA_FTQ_CTL_CUR_DEPTH) >> 22;
9211         max_depth = (ctl & BCE_TDMA_FTQ_CTL_MAX_DEPTH) >> 12;
9212         valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT10);
9213         BCE_PRINTF(" TDMA    0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9214                 cmd, ctl, cur_depth, max_depth, valid_cnt);
9215
9216         /* Input queue to the Transmit Patch-Up Processor */
9217         cmd = REG_RD_IND(sc, BCE_TPAT_FTQ_CMD);
9218         ctl = REG_RD_IND(sc, BCE_TPAT_FTQ_CTL);
9219         cur_depth = (ctl & BCE_TPAT_FTQ_CTL_CUR_DEPTH) >> 22;
9220         max_depth = (ctl & BCE_TPAT_FTQ_CTL_MAX_DEPTH) >> 12;
9221         valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT11);
9222         BCE_PRINTF(" TPAT    0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9223                 cmd, ctl, cur_depth, max_depth, valid_cnt);
9224
9225         /* Input queue to the Transmit Assembler state machine */
9226         cmd = REG_RD_IND(sc, BCE_TAS_FTQ_CMD);
9227         ctl = REG_RD_IND(sc, BCE_TAS_FTQ_CTL);
9228         cur_depth = (ctl & BCE_TAS_FTQ_CTL_CUR_DEPTH) >> 22;
9229         max_depth = (ctl & BCE_TAS_FTQ_CTL_MAX_DEPTH) >> 12;
9230         valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT12);
9231         BCE_PRINTF(" TAS     0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9232                 cmd, ctl, cur_depth, max_depth, valid_cnt);
9233
9234         /* Input queue to the Completion Processor */
9235         cmd = REG_RD_IND(sc, BCE_COM_COMXQ_FTQ_CMD);
9236         ctl = REG_RD_IND(sc, BCE_COM_COMXQ_FTQ_CTL);
9237         cur_depth = (ctl & BCE_COM_COMXQ_FTQ_CTL_CUR_DEPTH) >> 22;
9238         max_depth = (ctl & BCE_COM_COMXQ_FTQ_CTL_MAX_DEPTH) >> 12;
9239         valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT13);
9240         BCE_PRINTF(" COMX    0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9241                 cmd, ctl, cur_depth, max_depth, valid_cnt);
9242
9243         /* Input queue to the Completion Processor */
9244         cmd = REG_RD_IND(sc, BCE_COM_COMTQ_FTQ_CMD);
9245         ctl = REG_RD_IND(sc, BCE_COM_COMTQ_FTQ_CTL);
9246         cur_depth = (ctl & BCE_COM_COMTQ_FTQ_CTL_CUR_DEPTH) >> 22;
9247         max_depth = (ctl & BCE_COM_COMTQ_FTQ_CTL_MAX_DEPTH) >> 12;
9248         valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT14);
9249         BCE_PRINTF(" COMT    0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9250                 cmd, ctl, cur_depth, max_depth, valid_cnt);
9251
9252         /* Input queue to the Completion Processor */
9253         cmd = REG_RD_IND(sc, BCE_COM_COMQ_FTQ_CMD);
9254         ctl = REG_RD_IND(sc, BCE_COM_COMQ_FTQ_CTL);
9255         cur_depth = (ctl & BCE_COM_COMQ_FTQ_CTL_CUR_DEPTH) >> 22;
9256         max_depth = (ctl & BCE_COM_COMQ_FTQ_CTL_MAX_DEPTH) >> 12;
9257         valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT15);
9258         BCE_PRINTF(" COMX    0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9259                 cmd, ctl, cur_depth, max_depth, valid_cnt);
9260
9261         /* Setup the generic statistic counters for the FTQ valid count. */
9262         val = (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_CSQ_VALID_CNT  << 16) |
9263                 (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_CPQ_VALID_CNT  <<  8) |
9264                 (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_MGMQ_VALID_CNT);
9265
9266         if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709)     ||
9267                 (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716))
9268                 val = val | (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_RV2PCSQ_VALID_CNT_XI << 24);
9269                 REG_WR(sc, BCE_HC_STAT_GEN_SEL_0, val);
9270
9271         /* Input queue to the Management Control Processor */
9272         cmd = REG_RD_IND(sc, BCE_MCP_MCPQ_FTQ_CMD);
9273         ctl = REG_RD_IND(sc, BCE_MCP_MCPQ_FTQ_CTL);
9274         cur_depth = (ctl & BCE_MCP_MCPQ_FTQ_CTL_CUR_DEPTH) >> 22;
9275         max_depth = (ctl & BCE_MCP_MCPQ_FTQ_CTL_MAX_DEPTH) >> 12;
9276         valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT0);
9277         BCE_PRINTF(" MCP     0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9278                 cmd, ctl, cur_depth, max_depth, valid_cnt);
9279
9280         /* Input queue to the Command Processor */
9281         cmd = REG_RD_IND(sc, BCE_CP_CPQ_FTQ_CMD);
9282         ctl = REG_RD_IND(sc, BCE_CP_CPQ_FTQ_CTL);
9283         cur_depth = (ctl & BCE_CP_CPQ_FTQ_CTL_CUR_DEPTH) >> 22;
9284         max_depth = (ctl & BCE_CP_CPQ_FTQ_CTL_MAX_DEPTH) >> 12;
9285         valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT1);
9286         BCE_PRINTF(" CP      0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9287                 cmd, ctl, cur_depth, max_depth, valid_cnt);
9288
9289         /* Input queue to the Completion Scheduler state machine */
9290         cmd = REG_RD(sc, BCE_CSCH_CH_FTQ_CMD);
9291         ctl = REG_RD(sc, BCE_CSCH_CH_FTQ_CTL);
9292         cur_depth = (ctl & BCE_CSCH_CH_FTQ_CTL_CUR_DEPTH) >> 22;
9293         max_depth = (ctl & BCE_CSCH_CH_FTQ_CTL_MAX_DEPTH) >> 12;
9294         valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT2);
9295         BCE_PRINTF(" CS      0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9296                 cmd, ctl, cur_depth, max_depth, valid_cnt);
9297
9298         if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
9299                 (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
9300                 /* Input queue to the Receive Virtual to Physical Command Scheduler */
9301                 cmd = REG_RD(sc, BCE_RV2PCSR_FTQ_CMD);
9302                 ctl = REG_RD(sc, BCE_RV2PCSR_FTQ_CTL);
9303                 cur_depth = (ctl & 0xFFC00000) >> 22;
9304                 max_depth = (ctl & 0x003FF000) >> 12;
9305                 valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT3);
9306                 BCE_PRINTF(" RV2PCSR 0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9307                         cmd, ctl, cur_depth, max_depth, valid_cnt);
9308         }
9309
9310         BCE_PRINTF(
9311                 "----------------------------"
9312                 "----------------"
9313                 "----------------------------\n");
9314 }
9315
9316
9317 /****************************************************************************/
9318 /* Prints out the TX chain.                                                 */
9319 /*                                                                          */
9320 /* Returns:                                                                 */
9321 /*   Nothing.                                                               */
9322 /****************************************************************************/
9323 static __attribute__ ((noinline)) void
9324 bce_dump_tx_chain(struct bce_softc *sc, u16 tx_prod, int count)
9325 {
9326         struct tx_bd *txbd;
9327
9328         /* First some info about the tx_bd chain structure. */
9329         BCE_PRINTF(
9330                 "----------------------------"
9331                 "  tx_bd  chain  "
9332                 "----------------------------\n");
9333
9334         BCE_PRINTF("page size      = 0x%08X, tx chain pages        = 0x%08X\n",
9335                 (u32) BCM_PAGE_SIZE, (u32) TX_PAGES);
9336
9337         BCE_PRINTF("tx_bd per page = 0x%08X, usable tx_bd per page = 0x%08X\n",
9338                 (u32) TOTAL_TX_BD_PER_PAGE, (u32) USABLE_TX_BD_PER_PAGE);
9339
9340         BCE_PRINTF("total tx_bd    = 0x%08X\n", (u32) TOTAL_TX_BD);
9341
9342         BCE_PRINTF(
9343                 "----------------------------"
9344                 "   tx_bd data   "
9345                 "----------------------------\n");
9346
9347         /* Now print out the tx_bd's themselves. */
9348         for (int i = 0; i < count; i++) {
9349                 txbd = &sc->tx_bd_chain[TX_PAGE(tx_prod)][TX_IDX(tx_prod)];
9350                 bce_dump_txbd(sc, tx_prod, txbd);
9351                 tx_prod = NEXT_TX_BD(tx_prod);
9352         }
9353
9354         BCE_PRINTF(
9355                 "----------------------------"
9356                 "----------------"
9357                 "----------------------------\n");
9358 }
9359
9360
9361 /****************************************************************************/
9362 /* Prints out the RX chain.                                                 */
9363 /*                                                                          */
9364 /* Returns:                                                                 */
9365 /*   Nothing.                                                               */
9366 /****************************************************************************/
9367 static __attribute__ ((noinline)) void
9368 bce_dump_rx_chain(struct bce_softc *sc, u16 rx_prod, int count)
9369 {
9370         struct rx_bd *rxbd;
9371
9372         /* First some info about the rx_bd chain structure. */
9373         BCE_PRINTF(
9374                 "----------------------------"
9375                 "  rx_bd  chain  "
9376                 "----------------------------\n");
9377
9378         BCE_PRINTF("page size      = 0x%08X, rx chain pages        = 0x%08X\n",
9379                 (u32) BCM_PAGE_SIZE, (u32) RX_PAGES);
9380
9381         BCE_PRINTF("rx_bd per page = 0x%08X, usable rx_bd per page = 0x%08X\n",
9382                 (u32) TOTAL_RX_BD_PER_PAGE, (u32) USABLE_RX_BD_PER_PAGE);
9383
9384         BCE_PRINTF("total rx_bd    = 0x%08X\n", (u32) TOTAL_RX_BD);
9385
9386         BCE_PRINTF(
9387                 "----------------------------"
9388                 "   rx_bd data   "
9389                 "----------------------------\n");
9390
9391         /* Now print out the rx_bd's themselves. */
9392         for (int i = 0; i < count; i++) {
9393                 rxbd = &sc->rx_bd_chain[RX_PAGE(rx_prod)][RX_IDX(rx_prod)];
9394                 bce_dump_rxbd(sc, rx_prod, rxbd);
9395                 rx_prod = RX_CHAIN_IDX(rx_prod + 1);
9396         }
9397
9398         BCE_PRINTF(
9399                 "----------------------------"
9400                 "----------------"
9401                 "----------------------------\n");
9402 }
9403
9404
9405 #ifdef BCE_JUMBO_HDRSPLIT
9406 /****************************************************************************/
9407 /* Prints out the page chain.                                               */
9408 /*                                                                          */
9409 /* Returns:                                                                 */
9410 /*   Nothing.                                                               */
9411 /****************************************************************************/
9412 static __attribute__ ((noinline)) void
9413 bce_dump_pg_chain(struct bce_softc *sc, u16 pg_prod, int count)
9414 {
9415         struct rx_bd *pgbd;
9416
9417         /* First some info about the page chain structure. */
9418         BCE_PRINTF(
9419                 "----------------------------"
9420                 "   page chain   "
9421                 "----------------------------\n");
9422
9423         BCE_PRINTF("page size      = 0x%08X, pg chain pages        = 0x%08X\n",
9424                 (u32) BCM_PAGE_SIZE, (u32) PG_PAGES);
9425
9426         BCE_PRINTF("rx_bd per page = 0x%08X, usable rx_bd per page = 0x%08X\n",
9427                 (u32) TOTAL_PG_BD_PER_PAGE, (u32) USABLE_PG_BD_PER_PAGE);
9428
9429         BCE_PRINTF("total rx_bd    = 0x%08X, max_pg_bd             = 0x%08X\n",
9430                 (u32) TOTAL_PG_BD, (u32) MAX_PG_BD);
9431
9432         BCE_PRINTF(
9433                 "----------------------------"
9434                 "   page data    "
9435                 "----------------------------\n");
9436
9437         /* Now print out the rx_bd's themselves. */
9438         for (int i = 0; i < count; i++) {
9439                 pgbd = &sc->pg_bd_chain[PG_PAGE(pg_prod)][PG_IDX(pg_prod)];
9440                 bce_dump_pgbd(sc, pg_prod, pgbd);
9441                 pg_prod = PG_CHAIN_IDX(pg_prod + 1);
9442         }
9443
9444         BCE_PRINTF(
9445                 "----------------------------"
9446                 "----------------"
9447                 "----------------------------\n");
9448 }
9449 #endif
9450
9451
9452 /****************************************************************************/
9453 /* Prints out the status block from host memory.                            */
9454 /*                                                                          */
9455 /* Returns:                                                                 */
9456 /*   Nothing.                                                               */
9457 /****************************************************************************/
9458 static __attribute__ ((noinline)) void
9459 bce_dump_status_block(struct bce_softc *sc)
9460 {
9461         struct status_block *sblk;
9462
9463         sblk = sc->status_block;
9464
9465         BCE_PRINTF(
9466                 "----------------------------"
9467                 "  Status Block  "
9468                 "----------------------------\n");
9469
9470         BCE_PRINTF("    0x%08X - attn_bits\n",
9471                 sblk->status_attn_bits);
9472
9473         BCE_PRINTF("    0x%08X - attn_bits_ack\n",
9474                 sblk->status_attn_bits_ack);
9475
9476         BCE_PRINTF("0x%04X(0x%04X) - rx_cons0\n",
9477                 sblk->status_rx_quick_consumer_index0,
9478                 (u16) RX_CHAIN_IDX(sblk->status_rx_quick_consumer_index0));
9479
9480         BCE_PRINTF("0x%04X(0x%04X) - tx_cons0\n",
9481                 sblk->status_tx_quick_consumer_index0,
9482                 (u16) TX_CHAIN_IDX(sblk->status_tx_quick_consumer_index0));
9483
9484         BCE_PRINTF("        0x%04X - status_idx\n", sblk->status_idx);
9485
9486         /* Theses indices are not used for normal L2 drivers. */
9487         if (sblk->status_rx_quick_consumer_index1)
9488                 BCE_PRINTF("0x%04X(0x%04X) - rx_cons1\n",
9489                         sblk->status_rx_quick_consumer_index1,
9490                         (u16) RX_CHAIN_IDX(sblk->status_rx_quick_consumer_index1));
9491
9492         if (sblk->status_tx_quick_consumer_index1)
9493                 BCE_PRINTF("0x%04X(0x%04X) - tx_cons1\n",
9494                         sblk->status_tx_quick_consumer_index1,
9495                         (u16) TX_CHAIN_IDX(sblk->status_tx_quick_consumer_index1));
9496
9497         if (sblk->status_rx_quick_consumer_index2)
9498                 BCE_PRINTF("0x%04X(0x%04X)- rx_cons2\n",
9499                         sblk->status_rx_quick_consumer_index2,
9500                         (u16) RX_CHAIN_IDX(sblk->status_rx_quick_consumer_index2));
9501
9502         if (sblk->status_tx_quick_consumer_index2)
9503                 BCE_PRINTF("0x%04X(0x%04X) - tx_cons2\n",
9504                         sblk->status_tx_quick_consumer_index2,
9505                         (u16) TX_CHAIN_IDX(sblk->status_tx_quick_consumer_index2));
9506
9507         if (sblk->status_rx_quick_consumer_index3)
9508                 BCE_PRINTF("0x%04X(0x%04X) - rx_cons3\n",
9509                         sblk->status_rx_quick_consumer_index3,
9510                         (u16) RX_CHAIN_IDX(sblk->status_rx_quick_consumer_index3));
9511
9512         if (sblk->status_tx_quick_consumer_index3)
9513                 BCE_PRINTF("0x%04X(0x%04X) - tx_cons3\n",
9514                         sblk->status_tx_quick_consumer_index3,
9515                         (u16) TX_CHAIN_IDX(sblk->status_tx_quick_consumer_index3));
9516
9517         if (sblk->status_rx_quick_consumer_index4 ||
9518                 sblk->status_rx_quick_consumer_index5)
9519                 BCE_PRINTF("rx_cons4  = 0x%08X, rx_cons5      = 0x%08X\n",
9520                         sblk->status_rx_quick_consumer_index4,
9521                         sblk->status_rx_quick_consumer_index5);
9522
9523         if (sblk->status_rx_quick_consumer_index6 ||
9524                 sblk->status_rx_quick_consumer_index7)
9525                 BCE_PRINTF("rx_cons6  = 0x%08X, rx_cons7      = 0x%08X\n",
9526                         sblk->status_rx_quick_consumer_index6,
9527                         sblk->status_rx_quick_consumer_index7);
9528
9529         if (sblk->status_rx_quick_consumer_index8 ||
9530                 sblk->status_rx_quick_consumer_index9)
9531                 BCE_PRINTF("rx_cons8  = 0x%08X, rx_cons9      = 0x%08X\n",
9532                         sblk->status_rx_quick_consumer_index8,
9533                         sblk->status_rx_quick_consumer_index9);
9534
9535         if (sblk->status_rx_quick_consumer_index10 ||
9536                 sblk->status_rx_quick_consumer_index11)
9537                 BCE_PRINTF("rx_cons10 = 0x%08X, rx_cons11     = 0x%08X\n",
9538                         sblk->status_rx_quick_consumer_index10,
9539                         sblk->status_rx_quick_consumer_index11);
9540
9541         if (sblk->status_rx_quick_consumer_index12 ||
9542                 sblk->status_rx_quick_consumer_index13)
9543                 BCE_PRINTF("rx_cons12 = 0x%08X, rx_cons13     = 0x%08X\n",
9544                         sblk->status_rx_quick_consumer_index12,
9545                         sblk->status_rx_quick_consumer_index13);
9546
9547         if (sblk->status_rx_quick_consumer_index14 ||
9548                 sblk->status_rx_quick_consumer_index15)
9549                 BCE_PRINTF("rx_cons14 = 0x%08X, rx_cons15     = 0x%08X\n",
9550                         sblk->status_rx_quick_consumer_index14,
9551                         sblk->status_rx_quick_consumer_index15);
9552
9553         if (sblk->status_completion_producer_index ||
9554                 sblk->status_cmd_consumer_index)
9555                 BCE_PRINTF("com_prod  = 0x%08X, cmd_cons      = 0x%08X\n",
9556                         sblk->status_completion_producer_index,
9557                         sblk->status_cmd_consumer_index);
9558
9559         BCE_PRINTF(
9560                 "----------------------------"
9561                 "----------------"
9562                 "----------------------------\n");
9563 }
9564
9565
9566 /****************************************************************************/
9567 /* Prints out the statistics block from host memory.                        */
9568 /*                                                                          */
9569 /* Returns:                                                                 */
9570 /*   Nothing.                                                               */
9571 /****************************************************************************/
9572 static __attribute__ ((noinline)) void
9573 bce_dump_stats_block(struct bce_softc *sc)
9574 {
9575         struct statistics_block *sblk;
9576
9577         sblk = sc->stats_block;
9578
9579         BCE_PRINTF(
9580                 "---------------"
9581                 " Stats Block  (All Stats Not Shown Are 0) "
9582                 "---------------\n");
9583
9584         if (sblk->stat_IfHCInOctets_hi
9585                 || sblk->stat_IfHCInOctets_lo)
9586                 BCE_PRINTF("0x%08X:%08X : "
9587                         "IfHcInOctets\n",
9588                         sblk->stat_IfHCInOctets_hi,
9589                         sblk->stat_IfHCInOctets_lo);
9590
9591         if (sblk->stat_IfHCInBadOctets_hi
9592                 || sblk->stat_IfHCInBadOctets_lo)
9593                 BCE_PRINTF("0x%08X:%08X : "
9594                         "IfHcInBadOctets\n",
9595                         sblk->stat_IfHCInBadOctets_hi,
9596                         sblk->stat_IfHCInBadOctets_lo);
9597
9598         if (sblk->stat_IfHCOutOctets_hi
9599                 || sblk->stat_IfHCOutOctets_lo)
9600                 BCE_PRINTF("0x%08X:%08X : "
9601                         "IfHcOutOctets\n",
9602                         sblk->stat_IfHCOutOctets_hi,
9603                         sblk->stat_IfHCOutOctets_lo);
9604
9605         if (sblk->stat_IfHCOutBadOctets_hi
9606                 || sblk->stat_IfHCOutBadOctets_lo)
9607                 BCE_PRINTF("0x%08X:%08X : "
9608                         "IfHcOutBadOctets\n",
9609                         sblk->stat_IfHCOutBadOctets_hi,
9610                         sblk->stat_IfHCOutBadOctets_lo);
9611
9612         if (sblk->stat_IfHCInUcastPkts_hi
9613                 || sblk->stat_IfHCInUcastPkts_lo)
9614                 BCE_PRINTF("0x%08X:%08X : "
9615                         "IfHcInUcastPkts\n",
9616                         sblk->stat_IfHCInUcastPkts_hi,
9617                         sblk->stat_IfHCInUcastPkts_lo);
9618
9619         if (sblk->stat_IfHCInBroadcastPkts_hi
9620                 || sblk->stat_IfHCInBroadcastPkts_lo)
9621                 BCE_PRINTF("0x%08X:%08X : "
9622                         "IfHcInBroadcastPkts\n",
9623                         sblk->stat_IfHCInBroadcastPkts_hi,
9624                         sblk->stat_IfHCInBroadcastPkts_lo);
9625
9626         if (sblk->stat_IfHCInMulticastPkts_hi
9627                 || sblk->stat_IfHCInMulticastPkts_lo)
9628                 BCE_PRINTF("0x%08X:%08X : "
9629                         "IfHcInMulticastPkts\n",
9630                         sblk->stat_IfHCInMulticastPkts_hi,
9631                         sblk->stat_IfHCInMulticastPkts_lo);
9632
9633         if (sblk->stat_IfHCOutUcastPkts_hi
9634                 || sblk->stat_IfHCOutUcastPkts_lo)
9635                 BCE_PRINTF("0x%08X:%08X : "
9636                         "IfHcOutUcastPkts\n",
9637                         sblk->stat_IfHCOutUcastPkts_hi,
9638                         sblk->stat_IfHCOutUcastPkts_lo);
9639
9640         if (sblk->stat_IfHCOutBroadcastPkts_hi
9641                 || sblk->stat_IfHCOutBroadcastPkts_lo)
9642                 BCE_PRINTF("0x%08X:%08X : "
9643                         "IfHcOutBroadcastPkts\n",
9644                         sblk->stat_IfHCOutBroadcastPkts_hi,
9645                         sblk->stat_IfHCOutBroadcastPkts_lo);
9646
9647         if (sblk->stat_IfHCOutMulticastPkts_hi
9648                 || sblk->stat_IfHCOutMulticastPkts_lo)
9649                 BCE_PRINTF("0x%08X:%08X : "
9650                         "IfHcOutMulticastPkts\n",
9651                         sblk->stat_IfHCOutMulticastPkts_hi,
9652                         sblk->stat_IfHCOutMulticastPkts_lo);
9653
9654         if (sblk->stat_emac_tx_stat_dot3statsinternalmactransmiterrors)
9655                 BCE_PRINTF("         0x%08X : "
9656                         "emac_tx_stat_dot3statsinternalmactransmiterrors\n",
9657                         sblk->stat_emac_tx_stat_dot3statsinternalmactransmiterrors);
9658
9659         if (sblk->stat_Dot3StatsCarrierSenseErrors)
9660                 BCE_PRINTF("         0x%08X : Dot3StatsCarrierSenseErrors\n",
9661                         sblk->stat_Dot3StatsCarrierSenseErrors);
9662
9663         if (sblk->stat_Dot3StatsFCSErrors)
9664                 BCE_PRINTF("         0x%08X : Dot3StatsFCSErrors\n",
9665                         sblk->stat_Dot3StatsFCSErrors);
9666
9667         if (sblk->stat_Dot3StatsAlignmentErrors)
9668                 BCE_PRINTF("         0x%08X : Dot3StatsAlignmentErrors\n",
9669                         sblk->stat_Dot3StatsAlignmentErrors);
9670
9671         if (sblk->stat_Dot3StatsSingleCollisionFrames)
9672                 BCE_PRINTF("         0x%08X : Dot3StatsSingleCollisionFrames\n",
9673                         sblk->stat_Dot3StatsSingleCollisionFrames);
9674
9675         if (sblk->stat_Dot3StatsMultipleCollisionFrames)
9676                 BCE_PRINTF("         0x%08X : Dot3StatsMultipleCollisionFrames\n",
9677                         sblk->stat_Dot3StatsMultipleCollisionFrames);
9678
9679         if (sblk->stat_Dot3StatsDeferredTransmissions)
9680                 BCE_PRINTF("         0x%08X : Dot3StatsDeferredTransmissions\n",
9681                         sblk->stat_Dot3StatsDeferredTransmissions);
9682
9683         if (sblk->stat_Dot3StatsExcessiveCollisions)
9684                 BCE_PRINTF("         0x%08X : Dot3StatsExcessiveCollisions\n",
9685                         sblk->stat_Dot3StatsExcessiveCollisions);
9686
9687         if (sblk->stat_Dot3StatsLateCollisions)
9688                 BCE_PRINTF("         0x%08X : Dot3StatsLateCollisions\n",
9689                         sblk->stat_Dot3StatsLateCollisions);
9690
9691         if (sblk->stat_EtherStatsCollisions)
9692                 BCE_PRINTF("         0x%08X : EtherStatsCollisions\n",
9693                         sblk->stat_EtherStatsCollisions);
9694
9695         if (sblk->stat_EtherStatsFragments)
9696                 BCE_PRINTF("         0x%08X : EtherStatsFragments\n",
9697                         sblk->stat_EtherStatsFragments);
9698
9699         if (sblk->stat_EtherStatsJabbers)
9700                 BCE_PRINTF("         0x%08X : EtherStatsJabbers\n",
9701                         sblk->stat_EtherStatsJabbers);
9702
9703         if (sblk->stat_EtherStatsUndersizePkts)
9704                 BCE_PRINTF("         0x%08X : EtherStatsUndersizePkts\n",
9705                         sblk->stat_EtherStatsUndersizePkts);
9706
9707         if (sblk->stat_EtherStatsOversizePkts)
9708                 BCE_PRINTF("         0x%08X : EtherStatsOverrsizePkts\n",
9709                         sblk->stat_EtherStatsOversizePkts);
9710
9711         if (sblk->stat_EtherStatsPktsRx64Octets)
9712                 BCE_PRINTF("         0x%08X : EtherStatsPktsRx64Octets\n",
9713                         sblk->stat_EtherStatsPktsRx64Octets);
9714
9715         if (sblk->stat_EtherStatsPktsRx65Octetsto127Octets)
9716                 BCE_PRINTF("         0x%08X : EtherStatsPktsRx65Octetsto127Octets\n",
9717                         sblk->stat_EtherStatsPktsRx65Octetsto127Octets);
9718
9719         if (sblk->stat_EtherStatsPktsRx128Octetsto255Octets)
9720                 BCE_PRINTF("         0x%08X : EtherStatsPktsRx128Octetsto255Octets\n",
9721                         sblk->stat_EtherStatsPktsRx128Octetsto255Octets);
9722
9723         if (sblk->stat_EtherStatsPktsRx256Octetsto511Octets)
9724                 BCE_PRINTF("         0x%08X : EtherStatsPktsRx256Octetsto511Octets\n",
9725                         sblk->stat_EtherStatsPktsRx256Octetsto511Octets);
9726
9727         if (sblk->stat_EtherStatsPktsRx512Octetsto1023Octets)
9728                 BCE_PRINTF("         0x%08X : EtherStatsPktsRx512Octetsto1023Octets\n",
9729                         sblk->stat_EtherStatsPktsRx512Octetsto1023Octets);
9730
9731         if (sblk->stat_EtherStatsPktsRx1024Octetsto1522Octets)
9732                 BCE_PRINTF("         0x%08X : EtherStatsPktsRx1024Octetsto1522Octets\n",
9733                         sblk->stat_EtherStatsPktsRx1024Octetsto1522Octets);
9734
9735         if (sblk->stat_EtherStatsPktsRx1523Octetsto9022Octets)
9736                 BCE_PRINTF("         0x%08X : EtherStatsPktsRx1523Octetsto9022Octets\n",
9737                         sblk->stat_EtherStatsPktsRx1523Octetsto9022Octets);
9738
9739         if (sblk->stat_EtherStatsPktsTx64Octets)
9740                 BCE_PRINTF("         0x%08X : EtherStatsPktsTx64Octets\n",
9741                         sblk->stat_EtherStatsPktsTx64Octets);
9742
9743         if (sblk->stat_EtherStatsPktsTx65Octetsto127Octets)
9744                 BCE_PRINTF("         0x%08X : EtherStatsPktsTx65Octetsto127Octets\n",
9745                         sblk->stat_EtherStatsPktsTx65Octetsto127Octets);
9746
9747         if (sblk->stat_EtherStatsPktsTx128Octetsto255Octets)
9748                 BCE_PRINTF("         0x%08X : EtherStatsPktsTx128Octetsto255Octets\n",
9749                         sblk->stat_EtherStatsPktsTx128Octetsto255Octets);
9750
9751         if (sblk->stat_EtherStatsPktsTx256Octetsto511Octets)
9752                 BCE_PRINTF("         0x%08X : EtherStatsPktsTx256Octetsto511Octets\n",
9753                         sblk->stat_EtherStatsPktsTx256Octetsto511Octets);
9754
9755         if (sblk->stat_EtherStatsPktsTx512Octetsto1023Octets)
9756                 BCE_PRINTF("         0x%08X : EtherStatsPktsTx512Octetsto1023Octets\n",
9757                         sblk->stat_EtherStatsPktsTx512Octetsto1023Octets);
9758
9759         if (sblk->stat_EtherStatsPktsTx1024Octetsto1522Octets)
9760                 BCE_PRINTF("         0x%08X : EtherStatsPktsTx1024Octetsto1522Octets\n",
9761                         sblk->stat_EtherStatsPktsTx1024Octetsto1522Octets);
9762
9763         if (sblk->stat_EtherStatsPktsTx1523Octetsto9022Octets)
9764                 BCE_PRINTF("         0x%08X : EtherStatsPktsTx1523Octetsto9022Octets\n",
9765                         sblk->stat_EtherStatsPktsTx1523Octetsto9022Octets);
9766
9767         if (sblk->stat_XonPauseFramesReceived)
9768                 BCE_PRINTF("         0x%08X : XonPauseFramesReceived\n",
9769                         sblk->stat_XonPauseFramesReceived);
9770
9771         if (sblk->stat_XoffPauseFramesReceived)
9772            BCE_PRINTF("          0x%08X : XoffPauseFramesReceived\n",
9773                         sblk->stat_XoffPauseFramesReceived);
9774
9775         if (sblk->stat_OutXonSent)
9776                 BCE_PRINTF("         0x%08X : OutXonSent\n",
9777                         sblk->stat_OutXonSent);
9778
9779         if (sblk->stat_OutXoffSent)
9780                 BCE_PRINTF("         0x%08X : OutXoffSent\n",
9781                         sblk->stat_OutXoffSent);
9782
9783         if (sblk->stat_FlowControlDone)
9784                 BCE_PRINTF("         0x%08X : FlowControlDone\n",
9785                         sblk->stat_FlowControlDone);
9786
9787         if (sblk->stat_MacControlFramesReceived)
9788                 BCE_PRINTF("         0x%08X : MacControlFramesReceived\n",
9789                         sblk->stat_MacControlFramesReceived);
9790
9791         if (sblk->stat_XoffStateEntered)
9792                 BCE_PRINTF("         0x%08X : XoffStateEntered\n",
9793                         sblk->stat_XoffStateEntered);
9794
9795         if (sblk->stat_IfInFramesL2FilterDiscards)
9796                 BCE_PRINTF("         0x%08X : IfInFramesL2FilterDiscards\n",
9797                         sblk->stat_IfInFramesL2FilterDiscards);
9798
9799         if (sblk->stat_IfInRuleCheckerDiscards)
9800                 BCE_PRINTF("         0x%08X : IfInRuleCheckerDiscards\n",
9801                         sblk->stat_IfInRuleCheckerDiscards);
9802
9803         if (sblk->stat_IfInFTQDiscards)
9804                 BCE_PRINTF("         0x%08X : IfInFTQDiscards\n",
9805                         sblk->stat_IfInFTQDiscards);
9806
9807         if (sblk->stat_IfInMBUFDiscards)
9808                 BCE_PRINTF("         0x%08X : IfInMBUFDiscards\n",
9809                         sblk->stat_IfInMBUFDiscards);
9810
9811         if (sblk->stat_IfInRuleCheckerP4Hit)
9812                 BCE_PRINTF("         0x%08X : IfInRuleCheckerP4Hit\n",
9813                         sblk->stat_IfInRuleCheckerP4Hit);
9814
9815         if (sblk->stat_CatchupInRuleCheckerDiscards)
9816                 BCE_PRINTF("         0x%08X : CatchupInRuleCheckerDiscards\n",
9817                         sblk->stat_CatchupInRuleCheckerDiscards);
9818
9819         if (sblk->stat_CatchupInFTQDiscards)
9820                 BCE_PRINTF("         0x%08X : CatchupInFTQDiscards\n",
9821                         sblk->stat_CatchupInFTQDiscards);
9822
9823         if (sblk->stat_CatchupInMBUFDiscards)
9824                 BCE_PRINTF("         0x%08X : CatchupInMBUFDiscards\n",
9825                         sblk->stat_CatchupInMBUFDiscards);
9826
9827         if (sblk->stat_CatchupInRuleCheckerP4Hit)
9828                 BCE_PRINTF("         0x%08X : CatchupInRuleCheckerP4Hit\n",
9829                         sblk->stat_CatchupInRuleCheckerP4Hit);
9830
9831         BCE_PRINTF(
9832                 "----------------------------"
9833                 "----------------"
9834                 "----------------------------\n");
9835 }
9836
9837
9838 /****************************************************************************/
9839 /* Prints out a summary of the driver state.                                */
9840 /*                                                                          */
9841 /* Returns:                                                                 */
9842 /*   Nothing.                                                               */
9843 /****************************************************************************/
9844 static __attribute__ ((noinline)) void
9845 bce_dump_driver_state(struct bce_softc *sc)
9846 {
9847         u32 val_hi, val_lo;
9848
9849         BCE_PRINTF(
9850                 "-----------------------------"
9851                 " Driver State "
9852                 "-----------------------------\n");
9853
9854         val_hi = BCE_ADDR_HI(sc);
9855         val_lo = BCE_ADDR_LO(sc);
9856         BCE_PRINTF("0x%08X:%08X - (sc) driver softc structure virtual address\n",
9857                 val_hi, val_lo);
9858
9859         val_hi = BCE_ADDR_HI(sc->bce_vhandle);
9860         val_lo = BCE_ADDR_LO(sc->bce_vhandle);
9861         BCE_PRINTF("0x%08X:%08X - (sc->bce_vhandle) PCI BAR virtual address\n",
9862                 val_hi, val_lo);
9863
9864         val_hi = BCE_ADDR_HI(sc->status_block);
9865         val_lo = BCE_ADDR_LO(sc->status_block);
9866         BCE_PRINTF("0x%08X:%08X - (sc->status_block) status block virtual address\n",
9867                 val_hi, val_lo);
9868
9869         val_hi = BCE_ADDR_HI(sc->stats_block);
9870         val_lo = BCE_ADDR_LO(sc->stats_block);
9871         BCE_PRINTF("0x%08X:%08X - (sc->stats_block) statistics block virtual address\n",
9872                 val_hi, val_lo);
9873
9874         val_hi = BCE_ADDR_HI(sc->tx_bd_chain);
9875         val_lo = BCE_ADDR_LO(sc->tx_bd_chain);
9876         BCE_PRINTF(
9877                 "0x%08X:%08X - (sc->tx_bd_chain) tx_bd chain virtual adddress\n",
9878                 val_hi, val_lo);
9879
9880         val_hi = BCE_ADDR_HI(sc->rx_bd_chain);
9881         val_lo = BCE_ADDR_LO(sc->rx_bd_chain);
9882         BCE_PRINTF(
9883                 "0x%08X:%08X - (sc->rx_bd_chain) rx_bd chain virtual address\n",
9884                 val_hi, val_lo);
9885
9886 #ifdef BCE_JUMBO_HDRSPLIT
9887         val_hi = BCE_ADDR_HI(sc->pg_bd_chain);
9888         val_lo = BCE_ADDR_LO(sc->pg_bd_chain);
9889         BCE_PRINTF(
9890                 "0x%08X:%08X - (sc->pg_bd_chain) page chain virtual address\n",
9891                 val_hi, val_lo);
9892 #endif
9893
9894         val_hi = BCE_ADDR_HI(sc->tx_mbuf_ptr);
9895         val_lo = BCE_ADDR_LO(sc->tx_mbuf_ptr);
9896         BCE_PRINTF(
9897                 "0x%08X:%08X - (sc->tx_mbuf_ptr) tx mbuf chain virtual address\n",
9898                 val_hi, val_lo);
9899
9900         val_hi = BCE_ADDR_HI(sc->rx_mbuf_ptr);
9901         val_lo = BCE_ADDR_LO(sc->rx_mbuf_ptr);
9902         BCE_PRINTF(
9903                 "0x%08X:%08X - (sc->rx_mbuf_ptr) rx mbuf chain virtual address\n",
9904                 val_hi, val_lo);
9905
9906 #ifdef BCE_JUMBO_HDRSPLIT
9907         val_hi = BCE_ADDR_HI(sc->pg_mbuf_ptr);
9908         val_lo = BCE_ADDR_LO(sc->pg_mbuf_ptr);
9909         BCE_PRINTF(
9910                 "0x%08X:%08X - (sc->pg_mbuf_ptr) page mbuf chain virtual address\n",
9911                 val_hi, val_lo);
9912 #endif
9913
9914         BCE_PRINTF("         0x%08X - (sc->interrupts_generated) h/w intrs\n",
9915                 sc->interrupts_generated);
9916
9917         BCE_PRINTF("         0x%08X - (sc->rx_interrupts) rx interrupts handled\n",
9918                 sc->rx_interrupts);
9919
9920         BCE_PRINTF("         0x%08X - (sc->tx_interrupts) tx interrupts handled\n",
9921                 sc->tx_interrupts);
9922
9923         BCE_PRINTF("         0x%08X - (sc->last_status_idx) status block index\n",
9924                 sc->last_status_idx);
9925
9926         BCE_PRINTF("     0x%04X(0x%04X) - (sc->tx_prod) tx producer index\n",
9927                 sc->tx_prod, (u16) TX_CHAIN_IDX(sc->tx_prod));
9928
9929         BCE_PRINTF("     0x%04X(0x%04X) - (sc->tx_cons) tx consumer index\n",
9930                 sc->tx_cons, (u16) TX_CHAIN_IDX(sc->tx_cons));
9931
9932         BCE_PRINTF("         0x%08X - (sc->tx_prod_bseq) tx producer bseq index\n",
9933                 sc->tx_prod_bseq);
9934
9935         BCE_PRINTF("         0x%08X - (sc->debug_tx_mbuf_alloc) tx mbufs allocated\n",
9936                 sc->debug_tx_mbuf_alloc);
9937
9938         BCE_PRINTF("         0x%08X - (sc->used_tx_bd) used tx_bd's\n",
9939                 sc->used_tx_bd);
9940
9941         BCE_PRINTF("0x%08X/%08X - (sc->tx_hi_watermark) tx hi watermark\n",
9942                 sc->tx_hi_watermark, sc->max_tx_bd);
9943
9944         BCE_PRINTF("     0x%04X(0x%04X) - (sc->rx_prod) rx producer index\n",
9945                 sc->rx_prod, (u16) RX_CHAIN_IDX(sc->rx_prod));
9946
9947         BCE_PRINTF("     0x%04X(0x%04X) - (sc->rx_cons) rx consumer index\n",
9948                 sc->rx_cons, (u16) RX_CHAIN_IDX(sc->rx_cons));
9949
9950         BCE_PRINTF("         0x%08X - (sc->rx_prod_bseq) rx producer bseq index\n",
9951                 sc->rx_prod_bseq);
9952
9953         BCE_PRINTF("         0x%08X - (sc->debug_rx_mbuf_alloc) rx mbufs allocated\n",
9954                 sc->debug_rx_mbuf_alloc);
9955
9956         BCE_PRINTF("         0x%08X - (sc->free_rx_bd) free rx_bd's\n",
9957                 sc->free_rx_bd);
9958
9959 #ifdef BCE_JUMBO_HDRSPLIT
9960         BCE_PRINTF("     0x%04X(0x%04X) - (sc->pg_prod) page producer index\n",
9961                 sc->pg_prod, (u16) PG_CHAIN_IDX(sc->pg_prod));
9962
9963         BCE_PRINTF("     0x%04X(0x%04X) - (sc->pg_cons) page consumer index\n",
9964                 sc->pg_cons, (u16) PG_CHAIN_IDX(sc->pg_cons));
9965
9966         BCE_PRINTF("         0x%08X - (sc->debug_pg_mbuf_alloc) page mbufs allocated\n",
9967                 sc->debug_pg_mbuf_alloc);
9968
9969         BCE_PRINTF("         0x%08X - (sc->free_pg_bd) free page rx_bd's\n",
9970                 sc->free_pg_bd);
9971
9972         BCE_PRINTF("0x%08X/%08X - (sc->pg_low_watermark) page low watermark\n",
9973                 sc->pg_low_watermark, sc->max_pg_bd);
9974 #endif
9975
9976         BCE_PRINTF("         0x%08X - (sc->mbuf_alloc_failed_count) "
9977                 "mbuf alloc failures\n",
9978                 sc->mbuf_alloc_failed_count);
9979
9980         BCE_PRINTF("         0x%08X - (sc->bce_flags) bce mac flags\n",
9981                 sc->bce_flags);
9982
9983         BCE_PRINTF("         0x%08X - (sc->bce_phy_flags) bce phy flags\n",
9984                 sc->bce_phy_flags);
9985
9986         BCE_PRINTF(
9987                 "----------------------------"
9988                 "----------------"
9989                 "----------------------------\n");
9990 }
9991
9992
9993 /****************************************************************************/
9994 /* Prints out the hardware state through a summary of important register,   */
9995 /* followed by a complete register dump.                                    */
9996 /*                                                                          */
9997 /* Returns:                                                                 */
9998 /*   Nothing.                                                               */
9999 /****************************************************************************/
10000 static __attribute__ ((noinline)) void
10001 bce_dump_hw_state(struct bce_softc *sc)
10002 {
10003         u32 val;
10004
10005         BCE_PRINTF(
10006                 "----------------------------"
10007                 " Hardware State "
10008                 "----------------------------\n");
10009
10010         BCE_PRINTF("%s - bootcode version\n", sc->bce_bc_ver);
10011
10012         val = REG_RD(sc, BCE_MISC_ENABLE_STATUS_BITS);
10013         BCE_PRINTF("0x%08X - (0x%06X) misc_enable_status_bits\n",
10014                 val, BCE_MISC_ENABLE_STATUS_BITS);
10015
10016         val = REG_RD(sc, BCE_DMA_STATUS);
10017         BCE_PRINTF("0x%08X - (0x%06X) dma_status\n", val, BCE_DMA_STATUS);
10018
10019         val = REG_RD(sc, BCE_CTX_STATUS);
10020         BCE_PRINTF("0x%08X - (0x%06X) ctx_status\n", val, BCE_CTX_STATUS);
10021
10022         val = REG_RD(sc, BCE_EMAC_STATUS);
10023         BCE_PRINTF("0x%08X - (0x%06X) emac_status\n", val, BCE_EMAC_STATUS);
10024
10025         val = REG_RD(sc, BCE_RPM_STATUS);
10026         BCE_PRINTF("0x%08X - (0x%06X) rpm_status\n", val, BCE_RPM_STATUS);
10027
10028         val = REG_RD(sc, 0x2004);
10029         BCE_PRINTF("0x%08X - (0x%06X) rlup_status\n", val, 0x2004);
10030
10031         val = REG_RD(sc, BCE_RV2P_STATUS);
10032         BCE_PRINTF("0x%08X - (0x%06X) rv2p_status\n", val, BCE_RV2P_STATUS);
10033
10034         val = REG_RD(sc, 0x2c04);
10035         BCE_PRINTF("0x%08X - (0x%06X) rdma_status\n", val, 0x2c04);
10036
10037         val = REG_RD(sc, BCE_TBDR_STATUS);
10038         BCE_PRINTF("0x%08X - (0x%06X) tbdr_status\n", val, BCE_TBDR_STATUS);
10039
10040         val = REG_RD(sc, BCE_TDMA_STATUS);
10041         BCE_PRINTF("0x%08X - (0x%06X) tdma_status\n", val, BCE_TDMA_STATUS);
10042
10043         val = REG_RD(sc, BCE_HC_STATUS);
10044         BCE_PRINTF("0x%08X - (0x%06X) hc_status\n", val, BCE_HC_STATUS);
10045
10046         val = REG_RD_IND(sc, BCE_TXP_CPU_STATE);
10047         BCE_PRINTF("0x%08X - (0x%06X) txp_cpu_state\n", val, BCE_TXP_CPU_STATE);
10048
10049         val = REG_RD_IND(sc, BCE_TPAT_CPU_STATE);
10050         BCE_PRINTF("0x%08X - (0x%06X) tpat_cpu_state\n", val, BCE_TPAT_CPU_STATE);
10051
10052         val = REG_RD_IND(sc, BCE_RXP_CPU_STATE);
10053         BCE_PRINTF("0x%08X - (0x%06X) rxp_cpu_state\n", val, BCE_RXP_CPU_STATE);
10054
10055         val = REG_RD_IND(sc, BCE_COM_CPU_STATE);
10056         BCE_PRINTF("0x%08X - (0x%06X) com_cpu_state\n", val, BCE_COM_CPU_STATE);
10057
10058         val = REG_RD_IND(sc, BCE_MCP_CPU_STATE);
10059         BCE_PRINTF("0x%08X - (0x%06X) mcp_cpu_state\n", val, BCE_MCP_CPU_STATE);
10060
10061         val = REG_RD_IND(sc, BCE_CP_CPU_STATE);
10062         BCE_PRINTF("0x%08X - (0x%06X) cp_cpu_state\n", val, BCE_CP_CPU_STATE);
10063
10064         BCE_PRINTF(
10065                 "----------------------------"
10066                 "----------------"
10067                 "----------------------------\n");
10068
10069         BCE_PRINTF(
10070                 "----------------------------"
10071                 " Register  Dump "
10072                 "----------------------------\n");
10073
10074         for (int i = 0x400; i < 0x8000; i += 0x10) {
10075                 BCE_PRINTF("0x%04X: 0x%08X 0x%08X 0x%08X 0x%08X\n",
10076                         i, REG_RD(sc, i), REG_RD(sc, i + 0x4),
10077                         REG_RD(sc, i + 0x8), REG_RD(sc, i + 0xC));
10078         }
10079
10080         BCE_PRINTF(
10081                 "----------------------------"
10082                 "----------------"
10083                 "----------------------------\n");
10084 }
10085
10086
10087 /****************************************************************************/
10088 /* Prints out the mailbox queue registers.                                  */
10089 /*                                                                          */
10090 /* Returns:                                                                 */
10091 /*   Nothing.                                                               */
10092 /****************************************************************************/
10093 static __attribute__ ((noinline)) void
10094 bce_dump_mq_regs(struct bce_softc *sc)
10095 {
10096         BCE_PRINTF(
10097                 "----------------------------"
10098                 "    MQ Regs     "
10099                 "----------------------------\n");
10100
10101         BCE_PRINTF(
10102                 "----------------------------"
10103                 "----------------"
10104                 "----------------------------\n");
10105
10106         for (int i = 0x3c00; i < 0x4000; i += 0x10) {
10107                 BCE_PRINTF("0x%04X: 0x%08X 0x%08X 0x%08X 0x%08X\n",
10108                         i, REG_RD(sc, i), REG_RD(sc, i + 0x4),
10109                         REG_RD(sc, i + 0x8), REG_RD(sc, i + 0xC));
10110         }
10111
10112         BCE_PRINTF(
10113                 "----------------------------"
10114                 "----------------"
10115                 "----------------------------\n");
10116 }
10117
10118
10119 /****************************************************************************/
10120 /* Prints out the bootcode state.                                           */
10121 /*                                                                          */
10122 /* Returns:                                                                 */
10123 /*   Nothing.                                                               */
10124 /****************************************************************************/
10125 static __attribute__ ((noinline)) void
10126 bce_dump_bc_state(struct bce_softc *sc)
10127 {
10128         u32 val;
10129
10130         BCE_PRINTF(
10131                 "----------------------------"
10132                 " Bootcode State "
10133                 "----------------------------\n");
10134
10135         BCE_PRINTF("%s - bootcode version\n", sc->bce_bc_ver);
10136
10137         val = bce_shmem_rd(sc, BCE_BC_RESET_TYPE);
10138         BCE_PRINTF("0x%08X - (0x%06X) reset_type\n",
10139                 val, BCE_BC_RESET_TYPE);
10140
10141         val = bce_shmem_rd(sc, BCE_BC_STATE);
10142         BCE_PRINTF("0x%08X - (0x%06X) state\n",
10143                 val, BCE_BC_STATE);
10144
10145         val = bce_shmem_rd(sc, BCE_BC_STATE_CONDITION);
10146         BCE_PRINTF("0x%08X - (0x%06X) condition\n",
10147                 val, BCE_BC_STATE_CONDITION);
10148
10149         val = bce_shmem_rd(sc, BCE_BC_STATE_DEBUG_CMD);
10150         BCE_PRINTF("0x%08X - (0x%06X) debug_cmd\n",
10151                 val, BCE_BC_STATE_DEBUG_CMD);
10152
10153         BCE_PRINTF(
10154                 "----------------------------"
10155                 "----------------"
10156                 "----------------------------\n");
10157 }
10158
10159
10160 /****************************************************************************/
10161 /* Prints out the TXP processor state.                                      */
10162 /*                                                                          */
10163 /* Returns:                                                                 */
10164 /*   Nothing.                                                               */
10165 /****************************************************************************/
10166 static __attribute__ ((noinline)) void
10167 bce_dump_txp_state(struct bce_softc *sc, int regs)
10168 {
10169         u32 val;
10170         u32 fw_version[3];
10171
10172         BCE_PRINTF(
10173                 "----------------------------"
10174                 "   TXP  State   "
10175                 "----------------------------\n");
10176
10177         for (int i = 0; i < 3; i++)
10178                 fw_version[i] = htonl(REG_RD_IND(sc,
10179                         (BCE_TXP_SCRATCH + 0x10 + i * 4)));
10180         BCE_PRINTF("Firmware version - %s\n", (char *) fw_version);
10181
10182         val = REG_RD_IND(sc, BCE_TXP_CPU_MODE);
10183         BCE_PRINTF("0x%08X - (0x%06X) txp_cpu_mode\n", val, BCE_TXP_CPU_MODE);
10184
10185         val = REG_RD_IND(sc, BCE_TXP_CPU_STATE);
10186         BCE_PRINTF("0x%08X - (0x%06X) txp_cpu_state\n", val, BCE_TXP_CPU_STATE);
10187
10188         val = REG_RD_IND(sc, BCE_TXP_CPU_EVENT_MASK);
10189         BCE_PRINTF("0x%08X - (0x%06X) txp_cpu_event_mask\n", val,
10190                 BCE_TXP_CPU_EVENT_MASK);
10191
10192         if (regs) {
10193                 BCE_PRINTF(
10194                         "----------------------------"
10195                         " Register  Dump "
10196                         "----------------------------\n");
10197
10198                 for (int i = BCE_TXP_CPU_MODE; i < 0x68000; i += 0x10) {
10199                         /* Skip the big blank spaces */
10200                         if (i < 0x454000 && i > 0x5ffff)
10201                                 BCE_PRINTF("0x%04X: 0x%08X 0x%08X 0x%08X 0x%08X\n",
10202                                         i, REG_RD_IND(sc, i), REG_RD_IND(sc, i + 0x4),
10203                                         REG_RD_IND(sc, i + 0x8), REG_RD_IND(sc, i + 0xC));
10204                 }
10205         }
10206
10207         BCE_PRINTF(
10208                 "----------------------------"
10209                 "----------------"
10210                 "----------------------------\n");
10211 }
10212
10213
10214 /****************************************************************************/
10215 /* Prints out the RXP processor state.                                      */
10216 /*                                                                          */
10217 /* Returns:                                                                 */
10218 /*   Nothing.                                                               */
10219 /****************************************************************************/
10220 static __attribute__ ((noinline)) void
10221 bce_dump_rxp_state(struct bce_softc *sc, int regs)
10222 {
10223         u32 val;
10224         u32 fw_version[3];
10225
10226         BCE_PRINTF(
10227                 "----------------------------"
10228                 "   RXP  State   "
10229                 "----------------------------\n");
10230
10231         for (int i = 0; i < 3; i++)
10232                 fw_version[i] = htonl(REG_RD_IND(sc,
10233                         (BCE_RXP_SCRATCH + 0x10 + i * 4)));
10234         BCE_PRINTF("Firmware version - %s\n", (char *) fw_version);
10235
10236         val = REG_RD_IND(sc, BCE_RXP_CPU_MODE);
10237         BCE_PRINTF("0x%08X - (0x%06X) rxp_cpu_mode\n", val, BCE_RXP_CPU_MODE);
10238
10239         val = REG_RD_IND(sc, BCE_RXP_CPU_STATE);
10240         BCE_PRINTF("0x%08X - (0x%06X) rxp_cpu_state\n", val, BCE_RXP_CPU_STATE);
10241
10242         val = REG_RD_IND(sc, BCE_RXP_CPU_EVENT_MASK);
10243         BCE_PRINTF("0x%08X - (0x%06X) rxp_cpu_event_mask\n", val,
10244                 BCE_RXP_CPU_EVENT_MASK);
10245
10246         if (regs) {
10247                 BCE_PRINTF(
10248                         "----------------------------"
10249                         " Register  Dump "
10250                         "----------------------------\n");
10251
10252                 for (int i = BCE_RXP_CPU_MODE; i < 0xe8fff; i += 0x10) {
10253                         /* Skip the big blank sapces */
10254                         if (i < 0xc5400 && i > 0xdffff)
10255                                 BCE_PRINTF("0x%04X: 0x%08X 0x%08X 0x%08X 0x%08X\n",
10256                                         i, REG_RD_IND(sc, i), REG_RD_IND(sc, i + 0x4),
10257                                         REG_RD_IND(sc, i + 0x8), REG_RD_IND(sc, i + 0xC));
10258                 }
10259         }
10260
10261         BCE_PRINTF(
10262                 "----------------------------"
10263                 "----------------"
10264                 "----------------------------\n");
10265 }
10266
10267
10268 /****************************************************************************/
10269 /* Prints out the TPAT processor state.                                     */
10270 /*                                                                          */
10271 /* Returns:                                                                 */
10272 /*   Nothing.                                                               */
10273 /****************************************************************************/
10274 static __attribute__ ((noinline)) void
10275 bce_dump_tpat_state(struct bce_softc *sc, int regs)
10276 {
10277         u32 val;
10278         u32 fw_version[3];
10279
10280         BCE_PRINTF(
10281                 "----------------------------"
10282                 "   TPAT State   "
10283                 "----------------------------\n");
10284
10285         for (int i = 0; i < 3; i++)
10286                 fw_version[i] = htonl(REG_RD_IND(sc,
10287                         (BCE_TPAT_SCRATCH + 0x410 + i * 4)));
10288         BCE_PRINTF("Firmware version - %s\n", (char *) fw_version);
10289
10290         val = REG_RD_IND(sc, BCE_TPAT_CPU_MODE);
10291         BCE_PRINTF("0x%08X - (0x%06X) tpat_cpu_mode\n", val, BCE_TPAT_CPU_MODE);
10292
10293         val = REG_RD_IND(sc, BCE_TPAT_CPU_STATE);
10294         BCE_PRINTF("0x%08X - (0x%06X) tpat_cpu_state\n", val, BCE_TPAT_CPU_STATE);
10295
10296         val = REG_RD_IND(sc, BCE_TPAT_CPU_EVENT_MASK);
10297         BCE_PRINTF("0x%08X - (0x%06X) tpat_cpu_event_mask\n", val,
10298                 BCE_TPAT_CPU_EVENT_MASK);
10299
10300         if (regs) {
10301                 BCE_PRINTF(
10302                         "----------------------------"
10303                         " Register  Dump "
10304                         "----------------------------\n");
10305
10306                 for (int i = BCE_TPAT_CPU_MODE; i < 0xa3fff; i += 0x10) {
10307                         /* Skip the big blank spaces */
10308                         if (i < 0x854000 && i > 0x9ffff)
10309                                 BCE_PRINTF("0x%04X: 0x%08X 0x%08X 0x%08X 0x%08X\n",
10310                                         i, REG_RD_IND(sc, i), REG_RD_IND(sc, i + 0x4),
10311                                         REG_RD_IND(sc, i + 0x8), REG_RD_IND(sc, i + 0xC));
10312                 }
10313         }
10314
10315         BCE_PRINTF(
10316                 "----------------------------"
10317                 "----------------"
10318                 "----------------------------\n");
10319 }
10320
10321
10322 /****************************************************************************/
10323 /* Prints out the Command Procesor (CP) state.                              */
10324 /*                                                                          */
10325 /* Returns:                                                                 */
10326 /*   Nothing.                                                               */
10327 /****************************************************************************/
10328 static __attribute__ ((noinline)) void
10329 bce_dump_cp_state(struct bce_softc *sc, int regs)
10330 {
10331         u32 val;
10332         u32 fw_version[3];
10333
10334         BCE_PRINTF(
10335                 "----------------------------"
10336                 "    CP State    "
10337                 "----------------------------\n");
10338
10339         for (int i = 0; i < 3; i++)
10340                 fw_version[i] = htonl(REG_RD_IND(sc,
10341                         (BCE_CP_SCRATCH + 0x10 + i * 4)));
10342         BCE_PRINTF("Firmware version - %s\n", (char *) fw_version);
10343
10344         val = REG_RD_IND(sc, BCE_CP_CPU_MODE);
10345         BCE_PRINTF("0x%08X - (0x%06X) cp_cpu_mode\n", val, BCE_CP_CPU_MODE);
10346
10347         val = REG_RD_IND(sc, BCE_CP_CPU_STATE);
10348         BCE_PRINTF("0x%08X - (0x%06X) cp_cpu_state\n", val, BCE_CP_CPU_STATE);
10349
10350         val = REG_RD_IND(sc, BCE_CP_CPU_EVENT_MASK);
10351         BCE_PRINTF("0x%08X - (0x%06X) cp_cpu_event_mask\n", val,
10352                 BCE_CP_CPU_EVENT_MASK);
10353
10354         if (regs) {
10355                 BCE_PRINTF(
10356                         "----------------------------"
10357                         " Register  Dump "
10358                         "----------------------------\n");
10359
10360                 for (int i = BCE_CP_CPU_MODE; i < 0x1aa000; i += 0x10) {
10361                         /* Skip the big blank spaces */
10362                         if (i < 0x185400 && i > 0x19ffff)
10363                                 BCE_PRINTF("0x%04X: 0x%08X 0x%08X 0x%08X 0x%08X\n",
10364                                         i, REG_RD_IND(sc, i), REG_RD_IND(sc, i + 0x4),
10365                                         REG_RD_IND(sc, i + 0x8), REG_RD_IND(sc, i + 0xC));
10366                 }
10367         }
10368
10369         BCE_PRINTF(
10370                 "----------------------------"
10371                 "----------------"
10372                 "----------------------------\n");
10373 }
10374
10375
10376 /****************************************************************************/
10377 /* Prints out the Completion Procesor (COM) state.                          */
10378 /*                                                                          */
10379 /* Returns:                                                                 */
10380 /*   Nothing.                                                               */
10381 /****************************************************************************/
10382 static __attribute__ ((noinline)) void
10383 bce_dump_com_state(struct bce_softc *sc, int regs)
10384 {
10385         u32 val;
10386         u32 fw_version[3];
10387
10388         BCE_PRINTF(
10389                 "----------------------------"
10390                 "   COM State    "
10391                 "----------------------------\n");
10392
10393         for (int i = 0; i < 3; i++)
10394                 fw_version[i] = htonl(REG_RD_IND(sc,
10395                         (BCE_COM_SCRATCH + 0x10 + i * 4)));
10396         BCE_PRINTF("Firmware version - %s\n", (char *) fw_version);
10397
10398         val = REG_RD_IND(sc, BCE_COM_CPU_MODE);
10399         BCE_PRINTF("0x%08X - (0x%06X) com_cpu_mode\n", val, BCE_COM_CPU_MODE);
10400
10401         val = REG_RD_IND(sc, BCE_COM_CPU_STATE);
10402         BCE_PRINTF("0x%08X - (0x%06X) com_cpu_state\n", val, BCE_COM_CPU_STATE);
10403
10404         val = REG_RD_IND(sc, BCE_COM_CPU_EVENT_MASK);
10405         BCE_PRINTF("0x%08X - (0x%06X) com_cpu_event_mask\n", val,
10406                 BCE_COM_CPU_EVENT_MASK);
10407
10408         if (regs) {
10409                 BCE_PRINTF(
10410                         "----------------------------"
10411                         " Register  Dump "
10412                         "----------------------------\n");
10413
10414                 for (int i = BCE_COM_CPU_MODE; i < 0x1053e8; i += 0x10) {
10415                         BCE_PRINTF("0x%04X: 0x%08X 0x%08X 0x%08X 0x%08X\n",
10416                                 i, REG_RD_IND(sc, i), REG_RD_IND(sc, i + 0x4),
10417                                 REG_RD_IND(sc, i + 0x8), REG_RD_IND(sc, i + 0xC));
10418                 }
10419         }
10420
10421         BCE_PRINTF(
10422                 "----------------------------"
10423                 "----------------"
10424                 "----------------------------\n");
10425 }
10426
10427
10428 /****************************************************************************/
10429 /* Prints out the driver state and then enters the debugger.                */
10430 /*                                                                          */
10431 /* Returns:                                                                 */
10432 /*   Nothing.                                                               */
10433 /****************************************************************************/
10434 static void
10435 bce_breakpoint(struct bce_softc *sc)
10436 {
10437
10438         /*
10439          * Unreachable code to silence compiler warnings
10440          * about unused functions.
10441          */
10442         if (0) {
10443                 bce_freeze_controller(sc);
10444                 bce_unfreeze_controller(sc);
10445                 bce_dump_enet(sc, NULL);
10446                 bce_dump_txbd(sc, 0, NULL);
10447                 bce_dump_rxbd(sc, 0, NULL);
10448                 bce_dump_tx_mbuf_chain(sc, 0, USABLE_TX_BD);
10449                 bce_dump_rx_mbuf_chain(sc, 0, USABLE_RX_BD);
10450                 bce_dump_l2fhdr(sc, 0, NULL);
10451                 bce_dump_ctx(sc, RX_CID);
10452                 bce_dump_ftqs(sc);
10453                 bce_dump_tx_chain(sc, 0, USABLE_TX_BD);
10454                 bce_dump_rx_chain(sc, 0, USABLE_RX_BD);
10455                 bce_dump_status_block(sc);
10456                 bce_dump_stats_block(sc);
10457                 bce_dump_driver_state(sc);
10458                 bce_dump_hw_state(sc);
10459                 bce_dump_bc_state(sc);
10460                 bce_dump_txp_state(sc, 0);
10461                 bce_dump_rxp_state(sc, 0);
10462                 bce_dump_tpat_state(sc, 0);
10463                 bce_dump_cp_state(sc, 0);
10464                 bce_dump_com_state(sc, 0);
10465 #ifdef BCE_JUMBO_HDRSPLIT
10466                 bce_dump_pgbd(sc, 0, NULL);
10467                 bce_dump_pg_mbuf_chain(sc, 0, USABLE_PG_BD);
10468                 bce_dump_pg_chain(sc, 0, USABLE_PG_BD);
10469 #endif
10470         }
10471
10472         bce_dump_status_block(sc);
10473         bce_dump_driver_state(sc);
10474
10475         /* Call the debugger. */
10476         breakpoint();
10477
10478         return;
10479 }
10480 #endif
10481