xref: /freebsd/sys/dev/bce/if_bce.c (revision d8b878873e7aa8df1972cc6a642804b17eb61087)
1 /*-
2  * Copyright (c) 2006-2010 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  *   BCM5709S A1, C0
42  *   BCM5716C C0
43  *   BCM5716S C0
44  *
45  * The following controllers are not supported by this driver:
46  *   BCM5706C A0, A1 (pre-production)
47  *   BCM5706S A0, A1 (pre-production)
48  *   BCM5708C A0, B0 (pre-production)
49  *   BCM5708S A0, B0 (pre-production)
50  *   BCM5709C A0  B0, B1, B2 (pre-production)
51  *   BCM5709S A0, B0, B1, B2 (pre-production)
52  */
53 
54 #include "opt_bce.h"
55 
56 #include <dev/bce/if_bcereg.h>
57 #include <dev/bce/if_bcefw.h>
58 
59 /****************************************************************************/
60 /* BCE Debug Options                                                        */
61 /****************************************************************************/
62 #ifdef BCE_DEBUG
63 	u32 bce_debug = BCE_WARN;
64 
65 	/*          0 = Never              */
66 	/*          1 = 1 in 2,147,483,648 */
67 	/*        256 = 1 in     8,388,608 */
68 	/*       2048 = 1 in     1,048,576 */
69 	/*      65536 = 1 in        32,768 */
70 	/*    1048576 = 1 in         2,048 */
71 	/*  268435456 =	1 in             8 */
72 	/*  536870912 = 1 in             4 */
73 	/* 1073741824 = 1 in             2 */
74 
75 	/* Controls how often the l2_fhdr frame error check will fail. */
76 	int l2fhdr_error_sim_control = 0;
77 
78 	/* Controls how often the unexpected attention check will fail. */
79 	int unexpected_attention_sim_control = 0;
80 
81 	/* Controls how often to simulate an mbuf allocation failure. */
82 	int mbuf_alloc_failed_sim_control = 0;
83 
84 	/* Controls how often to simulate a DMA mapping failure. */
85 	int dma_map_addr_failed_sim_control = 0;
86 
87 	/* Controls how often to simulate a bootcode failure. */
88 	int bootcode_running_failure_sim_control = 0;
89 #endif
90 
91 /****************************************************************************/
92 /* BCE Build Time Options                                                   */
93 /****************************************************************************/
94 /* #define BCE_NVRAM_WRITE_SUPPORT 1 */
95 
96 
97 /****************************************************************************/
98 /* PCI Device ID Table                                                      */
99 /*                                                                          */
100 /* Used by bce_probe() to identify the devices supported by this driver.    */
101 /****************************************************************************/
102 #define BCE_DEVDESC_MAX		64
103 
104 static struct bce_type bce_devs[] = {
105 	/* BCM5706C Controllers and OEM boards. */
106 	{ BRCM_VENDORID, BRCM_DEVICEID_BCM5706,  HP_VENDORID, 0x3101,
107 		"HP NC370T Multifunction Gigabit Server Adapter" },
108 	{ BRCM_VENDORID, BRCM_DEVICEID_BCM5706,  HP_VENDORID, 0x3106,
109 		"HP NC370i Multifunction Gigabit Server Adapter" },
110 	{ BRCM_VENDORID, BRCM_DEVICEID_BCM5706,  HP_VENDORID, 0x3070,
111 		"HP NC380T PCIe DP Multifunc Gig Server Adapter" },
112 	{ BRCM_VENDORID, BRCM_DEVICEID_BCM5706,  HP_VENDORID, 0x1709,
113 		"HP NC371i Multifunction Gigabit Server Adapter" },
114 	{ BRCM_VENDORID, BRCM_DEVICEID_BCM5706,  PCI_ANY_ID,  PCI_ANY_ID,
115 		"Broadcom NetXtreme II BCM5706 1000Base-T" },
116 
117 	/* BCM5706S controllers and OEM boards. */
118 	{ BRCM_VENDORID, BRCM_DEVICEID_BCM5706S, HP_VENDORID, 0x3102,
119 		"HP NC370F Multifunction Gigabit Server Adapter" },
120 	{ BRCM_VENDORID, BRCM_DEVICEID_BCM5706S, PCI_ANY_ID,  PCI_ANY_ID,
121 		"Broadcom NetXtreme II BCM5706 1000Base-SX" },
122 
123 	/* BCM5708C controllers and OEM boards. */
124 	{ BRCM_VENDORID, BRCM_DEVICEID_BCM5708,  HP_VENDORID, 0x7037,
125 		"HP NC373T PCIe Multifunction Gig Server Adapter" },
126 	{ BRCM_VENDORID, BRCM_DEVICEID_BCM5708,  HP_VENDORID, 0x7038,
127 		"HP NC373i Multifunction Gigabit Server Adapter" },
128 	{ BRCM_VENDORID, BRCM_DEVICEID_BCM5708,  HP_VENDORID, 0x7045,
129 		"HP NC374m PCIe Multifunction Adapter" },
130 	{ BRCM_VENDORID, BRCM_DEVICEID_BCM5708,  PCI_ANY_ID,  PCI_ANY_ID,
131 		"Broadcom NetXtreme II BCM5708 1000Base-T" },
132 
133 	/* BCM5708S controllers and OEM boards. */
134 	{ BRCM_VENDORID, BRCM_DEVICEID_BCM5708S,  HP_VENDORID, 0x1706,
135 		"HP NC373m Multifunction Gigabit Server Adapter" },
136 	{ BRCM_VENDORID, BRCM_DEVICEID_BCM5708S,  HP_VENDORID, 0x703b,
137 		"HP NC373i Multifunction Gigabit Server Adapter" },
138 	{ BRCM_VENDORID, BRCM_DEVICEID_BCM5708S,  HP_VENDORID, 0x703d,
139 		"HP NC373F PCIe Multifunc Giga Server Adapter" },
140 	{ BRCM_VENDORID, BRCM_DEVICEID_BCM5708S,  PCI_ANY_ID,  PCI_ANY_ID,
141 		"Broadcom NetXtreme II BCM5708 1000Base-SX" },
142 
143 	/* BCM5709C controllers and OEM boards. */
144 	{ BRCM_VENDORID, BRCM_DEVICEID_BCM5709,  HP_VENDORID, 0x7055,
145 		"HP NC382i DP Multifunction Gigabit Server Adapter" },
146 	{ BRCM_VENDORID, BRCM_DEVICEID_BCM5709,  HP_VENDORID, 0x7059,
147 		"HP NC382T PCIe DP Multifunction Gigabit Server Adapter" },
148 	{ BRCM_VENDORID, BRCM_DEVICEID_BCM5709,  PCI_ANY_ID,  PCI_ANY_ID,
149 		"Broadcom NetXtreme II BCM5709 1000Base-T" },
150 
151 	/* BCM5709S controllers and OEM boards. */
152 	{ BRCM_VENDORID, BRCM_DEVICEID_BCM5709S,  HP_VENDORID, 0x171d,
153 		"HP NC382m DP 1GbE Multifunction BL-c Adapter" },
154 	{ BRCM_VENDORID, BRCM_DEVICEID_BCM5709S,  HP_VENDORID, 0x7056,
155 		"HP NC382i DP Multifunction Gigabit Server Adapter" },
156 	{ BRCM_VENDORID, BRCM_DEVICEID_BCM5709S,  PCI_ANY_ID,  PCI_ANY_ID,
157 		"Broadcom NetXtreme II BCM5709 1000Base-SX" },
158 
159 	/* BCM5716 controllers and OEM boards. */
160 	{ BRCM_VENDORID, BRCM_DEVICEID_BCM5716,  PCI_ANY_ID,  PCI_ANY_ID,
161 		"Broadcom NetXtreme II BCM5716 1000Base-T" },
162 
163 	{ 0, 0, 0, 0, NULL }
164 };
165 
166 
167 /****************************************************************************/
168 /* Supported Flash NVRAM device data.                                       */
169 /****************************************************************************/
170 static struct flash_spec flash_table[] =
171 {
172 #define BUFFERED_FLAGS		(BCE_NV_BUFFERED | BCE_NV_TRANSLATE)
173 #define NONBUFFERED_FLAGS	(BCE_NV_WREN)
174 
175 	/* Slow EEPROM */
176 	{0x00000000, 0x40830380, 0x009f0081, 0xa184a053, 0xaf000400,
177 	 BUFFERED_FLAGS, SEEPROM_PAGE_BITS, SEEPROM_PAGE_SIZE,
178 	 SEEPROM_BYTE_ADDR_MASK, SEEPROM_TOTAL_SIZE,
179 	 "EEPROM - slow"},
180 	/* Expansion entry 0001 */
181 	{0x08000002, 0x4b808201, 0x00050081, 0x03840253, 0xaf020406,
182 	 NONBUFFERED_FLAGS, SAIFUN_FLASH_PAGE_BITS, SAIFUN_FLASH_PAGE_SIZE,
183 	 SAIFUN_FLASH_BYTE_ADDR_MASK, 0,
184 	 "Entry 0001"},
185 	/* Saifun SA25F010 (non-buffered flash) */
186 	/* strap, cfg1, & write1 need updates */
187 	{0x04000001, 0x47808201, 0x00050081, 0x03840253, 0xaf020406,
188 	 NONBUFFERED_FLAGS, SAIFUN_FLASH_PAGE_BITS, SAIFUN_FLASH_PAGE_SIZE,
189 	 SAIFUN_FLASH_BYTE_ADDR_MASK, SAIFUN_FLASH_BASE_TOTAL_SIZE*2,
190 	 "Non-buffered flash (128kB)"},
191 	/* Saifun SA25F020 (non-buffered flash) */
192 	/* strap, cfg1, & write1 need updates */
193 	{0x0c000003, 0x4f808201, 0x00050081, 0x03840253, 0xaf020406,
194 	 NONBUFFERED_FLAGS, SAIFUN_FLASH_PAGE_BITS, SAIFUN_FLASH_PAGE_SIZE,
195 	 SAIFUN_FLASH_BYTE_ADDR_MASK, SAIFUN_FLASH_BASE_TOTAL_SIZE*4,
196 	 "Non-buffered flash (256kB)"},
197 	/* Expansion entry 0100 */
198 	{0x11000000, 0x53808201, 0x00050081, 0x03840253, 0xaf020406,
199 	 NONBUFFERED_FLAGS, SAIFUN_FLASH_PAGE_BITS, SAIFUN_FLASH_PAGE_SIZE,
200 	 SAIFUN_FLASH_BYTE_ADDR_MASK, 0,
201 	 "Entry 0100"},
202 	/* Entry 0101: ST M45PE10 (non-buffered flash, TetonII B0) */
203 	{0x19000002, 0x5b808201, 0x000500db, 0x03840253, 0xaf020406,
204 	 NONBUFFERED_FLAGS, ST_MICRO_FLASH_PAGE_BITS, ST_MICRO_FLASH_PAGE_SIZE,
205 	 ST_MICRO_FLASH_BYTE_ADDR_MASK, ST_MICRO_FLASH_BASE_TOTAL_SIZE*2,
206 	 "Entry 0101: ST M45PE10 (128kB non-bufferred)"},
207 	/* Entry 0110: ST M45PE20 (non-buffered flash)*/
208 	{0x15000001, 0x57808201, 0x000500db, 0x03840253, 0xaf020406,
209 	 NONBUFFERED_FLAGS, ST_MICRO_FLASH_PAGE_BITS, ST_MICRO_FLASH_PAGE_SIZE,
210 	 ST_MICRO_FLASH_BYTE_ADDR_MASK, ST_MICRO_FLASH_BASE_TOTAL_SIZE*4,
211 	 "Entry 0110: ST M45PE20 (256kB non-bufferred)"},
212 	/* Saifun SA25F005 (non-buffered flash) */
213 	/* strap, cfg1, & write1 need updates */
214 	{0x1d000003, 0x5f808201, 0x00050081, 0x03840253, 0xaf020406,
215 	 NONBUFFERED_FLAGS, SAIFUN_FLASH_PAGE_BITS, SAIFUN_FLASH_PAGE_SIZE,
216 	 SAIFUN_FLASH_BYTE_ADDR_MASK, SAIFUN_FLASH_BASE_TOTAL_SIZE,
217 	 "Non-buffered flash (64kB)"},
218 	/* Fast EEPROM */
219 	{0x22000000, 0x62808380, 0x009f0081, 0xa184a053, 0xaf000400,
220 	 BUFFERED_FLAGS, SEEPROM_PAGE_BITS, SEEPROM_PAGE_SIZE,
221 	 SEEPROM_BYTE_ADDR_MASK, SEEPROM_TOTAL_SIZE,
222 	 "EEPROM - fast"},
223 	/* Expansion entry 1001 */
224 	{0x2a000002, 0x6b808201, 0x00050081, 0x03840253, 0xaf020406,
225 	 NONBUFFERED_FLAGS, SAIFUN_FLASH_PAGE_BITS, SAIFUN_FLASH_PAGE_SIZE,
226 	 SAIFUN_FLASH_BYTE_ADDR_MASK, 0,
227 	 "Entry 1001"},
228 	/* Expansion entry 1010 */
229 	{0x26000001, 0x67808201, 0x00050081, 0x03840253, 0xaf020406,
230 	 NONBUFFERED_FLAGS, SAIFUN_FLASH_PAGE_BITS, SAIFUN_FLASH_PAGE_SIZE,
231 	 SAIFUN_FLASH_BYTE_ADDR_MASK, 0,
232 	 "Entry 1010"},
233 	/* ATMEL AT45DB011B (buffered flash) */
234 	{0x2e000003, 0x6e808273, 0x00570081, 0x68848353, 0xaf000400,
235 	 BUFFERED_FLAGS, BUFFERED_FLASH_PAGE_BITS, BUFFERED_FLASH_PAGE_SIZE,
236 	 BUFFERED_FLASH_BYTE_ADDR_MASK, BUFFERED_FLASH_TOTAL_SIZE,
237 	 "Buffered flash (128kB)"},
238 	/* Expansion entry 1100 */
239 	{0x33000000, 0x73808201, 0x00050081, 0x03840253, 0xaf020406,
240 	 NONBUFFERED_FLAGS, SAIFUN_FLASH_PAGE_BITS, SAIFUN_FLASH_PAGE_SIZE,
241 	 SAIFUN_FLASH_BYTE_ADDR_MASK, 0,
242 	 "Entry 1100"},
243 	/* Expansion entry 1101 */
244 	{0x3b000002, 0x7b808201, 0x00050081, 0x03840253, 0xaf020406,
245 	 NONBUFFERED_FLAGS, SAIFUN_FLASH_PAGE_BITS, SAIFUN_FLASH_PAGE_SIZE,
246 	 SAIFUN_FLASH_BYTE_ADDR_MASK, 0,
247 	 "Entry 1101"},
248 	/* Ateml Expansion entry 1110 */
249 	{0x37000001, 0x76808273, 0x00570081, 0x68848353, 0xaf000400,
250 	 BUFFERED_FLAGS, BUFFERED_FLASH_PAGE_BITS, BUFFERED_FLASH_PAGE_SIZE,
251 	 BUFFERED_FLASH_BYTE_ADDR_MASK, 0,
252 	 "Entry 1110 (Atmel)"},
253 	/* ATMEL AT45DB021B (buffered flash) */
254 	{0x3f000003, 0x7e808273, 0x00570081, 0x68848353, 0xaf000400,
255 	 BUFFERED_FLAGS, BUFFERED_FLASH_PAGE_BITS, BUFFERED_FLASH_PAGE_SIZE,
256 	 BUFFERED_FLASH_BYTE_ADDR_MASK, BUFFERED_FLASH_TOTAL_SIZE*2,
257 	 "Buffered flash (256kB)"},
258 };
259 
260 /*
261  * The BCM5709 controllers transparently handle the
262  * differences between Atmel 264 byte pages and all
263  * flash devices which use 256 byte pages, so no
264  * logical-to-physical mapping is required in the
265  * driver.
266  */
267 static struct flash_spec flash_5709 = {
268 	.flags		= BCE_NV_BUFFERED,
269 	.page_bits	= BCM5709_FLASH_PAGE_BITS,
270 	.page_size	= BCM5709_FLASH_PAGE_SIZE,
271 	.addr_mask	= BCM5709_FLASH_BYTE_ADDR_MASK,
272 	.total_size	= BUFFERED_FLASH_TOTAL_SIZE * 2,
273 	.name		= "5709/5716 buffered flash (256kB)",
274 };
275 
276 
277 /****************************************************************************/
278 /* FreeBSD device entry points.                                             */
279 /****************************************************************************/
280 static int  bce_probe			(device_t);
281 static int  bce_attach			(device_t);
282 static int  bce_detach			(device_t);
283 static int  bce_shutdown		(device_t);
284 
285 
286 /****************************************************************************/
287 /* BCE Debug Data Structure Dump Routines                                   */
288 /****************************************************************************/
289 #ifdef BCE_DEBUG
290 static u32  bce_reg_rd			(struct bce_softc *, u32);
291 static void bce_reg_wr			(struct bce_softc *, u32, u32);
292 static void bce_reg_wr16		(struct bce_softc *, u32, u16);
293 static u32  bce_ctx_rd			(struct bce_softc *, u32, u32);
294 static void bce_dump_enet		(struct bce_softc *, struct mbuf *);
295 static void bce_dump_mbuf		(struct bce_softc *, struct mbuf *);
296 static void bce_dump_tx_mbuf_chain	(struct bce_softc *, u16, int);
297 static void bce_dump_rx_mbuf_chain	(struct bce_softc *, u16, int);
298 #ifdef BCE_JUMBO_HDRSPLIT
299 static void bce_dump_pg_mbuf_chain	(struct bce_softc *, u16, int);
300 #endif
301 static void bce_dump_txbd		(struct bce_softc *,
302     int, struct tx_bd *);
303 static void bce_dump_rxbd		(struct bce_softc *,
304     int, struct rx_bd *);
305 #ifdef BCE_JUMBO_HDRSPLIT
306 static void bce_dump_pgbd		(struct bce_softc *,
307     int, struct rx_bd *);
308 #endif
309 static void bce_dump_l2fhdr		(struct bce_softc *,
310     int, struct l2_fhdr *);
311 static void bce_dump_ctx		(struct bce_softc *, u16);
312 static void bce_dump_ftqs		(struct bce_softc *);
313 static void bce_dump_tx_chain		(struct bce_softc *, u16, int);
314 static void bce_dump_rx_bd_chain	(struct bce_softc *, u16, int);
315 #ifdef BCE_JUMBO_HDRSPLIT
316 static void bce_dump_pg_chain		(struct bce_softc *, u16, int);
317 #endif
318 static void bce_dump_status_block	(struct bce_softc *);
319 static void bce_dump_stats_block	(struct bce_softc *);
320 static void bce_dump_driver_state	(struct bce_softc *);
321 static void bce_dump_hw_state		(struct bce_softc *);
322 static void bce_dump_mq_regs		(struct bce_softc *);
323 static void bce_dump_bc_state		(struct bce_softc *);
324 static void bce_dump_txp_state		(struct bce_softc *, int);
325 static void bce_dump_rxp_state		(struct bce_softc *, int);
326 static void bce_dump_tpat_state		(struct bce_softc *, int);
327 static void bce_dump_cp_state		(struct bce_softc *, int);
328 static void bce_dump_com_state		(struct bce_softc *, int);
329 static void bce_dump_rv2p_state		(struct bce_softc *);
330 static void bce_breakpoint		(struct bce_softc *);
331 #endif
332 
333 
334 /****************************************************************************/
335 /* BCE Register/Memory Access Routines                                      */
336 /****************************************************************************/
337 static u32  bce_reg_rd_ind		(struct bce_softc *, u32);
338 static void bce_reg_wr_ind		(struct bce_softc *, u32, u32);
339 static void bce_shmem_wr		(struct bce_softc *, u32, u32);
340 static u32  bce_shmem_rd		(struct bce_softc *, u32);
341 static void bce_ctx_wr			(struct bce_softc *, u32, u32, u32);
342 static int  bce_miibus_read_reg		(device_t, int, int);
343 static int  bce_miibus_write_reg	(device_t, int, int, int);
344 static void bce_miibus_statchg		(device_t);
345 
346 
347 /****************************************************************************/
348 /* BCE NVRAM Access Routines                                                */
349 /****************************************************************************/
350 static int  bce_acquire_nvram_lock	(struct bce_softc *);
351 static int  bce_release_nvram_lock	(struct bce_softc *);
352 static void bce_enable_nvram_access	(struct bce_softc *);
353 static void bce_disable_nvram_access	(struct bce_softc *);
354 static int  bce_nvram_read_dword	(struct bce_softc *, u32, u8 *, u32);
355 static int  bce_init_nvram		(struct bce_softc *);
356 static int  bce_nvram_read		(struct bce_softc *, u32, u8 *, int);
357 static int  bce_nvram_test		(struct bce_softc *);
358 #ifdef BCE_NVRAM_WRITE_SUPPORT
359 static int  bce_enable_nvram_write	(struct bce_softc *);
360 static void bce_disable_nvram_write	(struct bce_softc *);
361 static int  bce_nvram_erase_page	(struct bce_softc *, u32);
362 static int  bce_nvram_write_dword	(struct bce_softc *, u32, u8 *, u32);
363 static int  bce_nvram_write		(struct bce_softc *, u32, u8 *, int);
364 #endif
365 
366 /****************************************************************************/
367 /*                                                                          */
368 /****************************************************************************/
369 static void bce_get_media		(struct bce_softc *);
370 static void bce_init_media		(struct bce_softc *);
371 static void bce_dma_map_addr		(void *,
372     bus_dma_segment_t *, int, int);
373 static int  bce_dma_alloc		(device_t);
374 static void bce_dma_free		(struct bce_softc *);
375 static void bce_release_resources	(struct bce_softc *);
376 
377 /****************************************************************************/
378 /* BCE Firmware Synchronization and Load                                    */
379 /****************************************************************************/
380 static int  bce_fw_sync			(struct bce_softc *, u32);
381 static void bce_load_rv2p_fw		(struct bce_softc *, u32 *, u32, u32);
382 static void bce_load_cpu_fw		(struct bce_softc *,
383     struct cpu_reg *, struct fw_info *);
384 static void bce_start_cpu		(struct bce_softc *, struct cpu_reg *);
385 static void bce_halt_cpu		(struct bce_softc *, struct cpu_reg *);
386 static void bce_start_rxp_cpu		(struct bce_softc *);
387 static void bce_init_rxp_cpu		(struct bce_softc *);
388 static void bce_init_txp_cpu 		(struct bce_softc *);
389 static void bce_init_tpat_cpu		(struct bce_softc *);
390 static void bce_init_cp_cpu	  	(struct bce_softc *);
391 static void bce_init_com_cpu	  	(struct bce_softc *);
392 static void bce_init_cpus		(struct bce_softc *);
393 
394 static void	bce_print_adapter_info	(struct bce_softc *);
395 static void bce_probe_pci_caps		(device_t, struct bce_softc *);
396 static void bce_stop			(struct bce_softc *);
397 static int  bce_reset			(struct bce_softc *, u32);
398 static int  bce_chipinit 		(struct bce_softc *);
399 static int  bce_blockinit 		(struct bce_softc *);
400 
401 static int  bce_init_tx_chain		(struct bce_softc *);
402 static void bce_free_tx_chain		(struct bce_softc *);
403 
404 static int  bce_get_rx_buf		(struct bce_softc *,
405     struct mbuf *, u16 *, u16 *, u32 *);
406 static int  bce_init_rx_chain		(struct bce_softc *);
407 static void bce_fill_rx_chain		(struct bce_softc *);
408 static void bce_free_rx_chain		(struct bce_softc *);
409 
410 #ifdef BCE_JUMBO_HDRSPLIT
411 static int  bce_get_pg_buf		(struct bce_softc *,
412     struct mbuf *, u16 *, u16 *);
413 static int  bce_init_pg_chain		(struct bce_softc *);
414 static void bce_fill_pg_chain		(struct bce_softc *);
415 static void bce_free_pg_chain		(struct bce_softc *);
416 #endif
417 
418 static struct mbuf *bce_tso_setup	(struct bce_softc *,
419     struct mbuf **, u16 *);
420 static int  bce_tx_encap		(struct bce_softc *, struct mbuf **);
421 static void bce_start_locked		(struct ifnet *);
422 static void bce_start			(struct ifnet *);
423 static int  bce_ioctl			(struct ifnet *, u_long, caddr_t);
424 static void bce_watchdog		(struct bce_softc *);
425 static int  bce_ifmedia_upd		(struct ifnet *);
426 static void bce_ifmedia_upd_locked	(struct ifnet *);
427 static void bce_ifmedia_sts		(struct ifnet *, struct ifmediareq *);
428 static void bce_init_locked		(struct bce_softc *);
429 static void bce_init			(void *);
430 static void bce_mgmt_init_locked	(struct bce_softc *sc);
431 
432 static void bce_init_ctx		(struct bce_softc *);
433 static void bce_get_mac_addr		(struct bce_softc *);
434 static void bce_set_mac_addr		(struct bce_softc *);
435 static void bce_phy_intr		(struct bce_softc *);
436 static inline u16 bce_get_hw_rx_cons	(struct bce_softc *);
437 static void bce_rx_intr			(struct bce_softc *);
438 static void bce_tx_intr			(struct bce_softc *);
439 static void bce_disable_intr		(struct bce_softc *);
440 static void bce_enable_intr		(struct bce_softc *, int);
441 
442 static void bce_intr			(void *);
443 static void bce_set_rx_mode		(struct bce_softc *);
444 static void bce_stats_update		(struct bce_softc *);
445 static void bce_tick			(void *);
446 static void bce_pulse			(void *);
447 static void bce_add_sysctls		(struct bce_softc *);
448 
449 
450 /****************************************************************************/
451 /* FreeBSD device dispatch table.                                           */
452 /****************************************************************************/
453 static device_method_t bce_methods[] = {
454 	/* Device interface (device_if.h) */
455 	DEVMETHOD(device_probe,		bce_probe),
456 	DEVMETHOD(device_attach,	bce_attach),
457 	DEVMETHOD(device_detach,	bce_detach),
458 	DEVMETHOD(device_shutdown,	bce_shutdown),
459 /* Supported by device interface but not used here. */
460 /*	DEVMETHOD(device_identify,	bce_identify),      */
461 /*	DEVMETHOD(device_suspend,	bce_suspend),       */
462 /*	DEVMETHOD(device_resume,	bce_resume),        */
463 /*	DEVMETHOD(device_quiesce,	bce_quiesce),       */
464 
465 	/* Bus interface (bus_if.h) */
466 	DEVMETHOD(bus_print_child,	bus_generic_print_child),
467 	DEVMETHOD(bus_driver_added,	bus_generic_driver_added),
468 
469 	/* MII interface (miibus_if.h) */
470 	DEVMETHOD(miibus_readreg,	bce_miibus_read_reg),
471 	DEVMETHOD(miibus_writereg,	bce_miibus_write_reg),
472 	DEVMETHOD(miibus_statchg,	bce_miibus_statchg),
473 /* Supported by MII interface but not used here.       */
474 /*	DEVMETHOD(miibus_linkchg,	bce_miibus_linkchg),   */
475 /*	DEVMETHOD(miibus_mediainit,	bce_miibus_mediainit), */
476 
477 	{ 0, 0 }
478 };
479 
480 static driver_t bce_driver = {
481 	"bce",
482 	bce_methods,
483 	sizeof(struct bce_softc)
484 };
485 
486 static devclass_t bce_devclass;
487 
488 MODULE_DEPEND(bce, pci, 1, 1, 1);
489 MODULE_DEPEND(bce, ether, 1, 1, 1);
490 MODULE_DEPEND(bce, miibus, 1, 1, 1);
491 
492 DRIVER_MODULE(bce, pci, bce_driver, bce_devclass, 0, 0);
493 DRIVER_MODULE(miibus, bce, miibus_driver, miibus_devclass, 0, 0);
494 
495 
496 /****************************************************************************/
497 /* Tunable device values                                                    */
498 /****************************************************************************/
499 SYSCTL_NODE(_hw, OID_AUTO, bce, CTLFLAG_RD, 0, "bce driver parameters");
500 
501 /* Allowable values are TRUE or FALSE */
502 static int bce_tso_enable = TRUE;
503 TUNABLE_INT("hw.bce.tso_enable", &bce_tso_enable);
504 SYSCTL_UINT(_hw_bce, OID_AUTO, tso_enable, CTLFLAG_RDTUN, &bce_tso_enable, 0,
505 "TSO Enable/Disable");
506 
507 /* Allowable values are 0 (IRQ), 1 (MSI/IRQ), and 2 (MSI-X/MSI/IRQ) */
508 /* ToDo: Add MSI-X support. */
509 static int bce_msi_enable = 1;
510 TUNABLE_INT("hw.bce.msi_enable", &bce_msi_enable);
511 SYSCTL_UINT(_hw_bce, OID_AUTO, msi_enable, CTLFLAG_RDTUN, &bce_msi_enable, 0,
512 "MSI-X|MSI|INTx selector");
513 
514 /* ToDo: Add tunable to enable/disable strict MTU handling. */
515 /* Currently allows "loose" RX MTU checking (i.e. sets the  */
516 /* H/W RX MTU to the size of the largest receive buffer, or */
517 /* 2048 bytes). This will cause a UNH failure but is more   */
518 /* desireable from a functional perspective.                */
519 
520 
521 /****************************************************************************/
522 /* Device probe function.                                                   */
523 /*                                                                          */
524 /* Compares the device to the driver's list of supported devices and        */
525 /* reports back to the OS whether this is the right driver for the device.  */
526 /*                                                                          */
527 /* Returns:                                                                 */
528 /*   BUS_PROBE_DEFAULT on success, positive value on failure.               */
529 /****************************************************************************/
530 static int
531 bce_probe(device_t dev)
532 {
533 	struct bce_type *t;
534 	struct bce_softc *sc;
535 	char *descbuf;
536 	u16 vid = 0, did = 0, svid = 0, sdid = 0;
537 
538 	t = bce_devs;
539 
540 	sc = device_get_softc(dev);
541 	bzero(sc, sizeof(struct bce_softc));
542 	sc->bce_unit = device_get_unit(dev);
543 	sc->bce_dev = dev;
544 
545 	/* Get the data for the device to be probed. */
546 	vid  = pci_get_vendor(dev);
547 	did  = pci_get_device(dev);
548 	svid = pci_get_subvendor(dev);
549 	sdid = pci_get_subdevice(dev);
550 
551 	DBPRINT(sc, BCE_EXTREME_LOAD,
552 	    "%s(); VID = 0x%04X, DID = 0x%04X, SVID = 0x%04X, "
553 	    "SDID = 0x%04X\n", __FUNCTION__, vid, did, svid, sdid);
554 
555 	/* Look through the list of known devices for a match. */
556 	while(t->bce_name != NULL) {
557 
558 		if ((vid == t->bce_vid) && (did == t->bce_did) &&
559 		    ((svid == t->bce_svid) || (t->bce_svid == PCI_ANY_ID)) &&
560 		    ((sdid == t->bce_sdid) || (t->bce_sdid == PCI_ANY_ID))) {
561 
562 			descbuf = malloc(BCE_DEVDESC_MAX, M_TEMP, M_NOWAIT);
563 
564 			if (descbuf == NULL)
565 				return(ENOMEM);
566 
567 			/* Print out the device identity. */
568 			snprintf(descbuf, BCE_DEVDESC_MAX, "%s (%c%d)",
569 			    t->bce_name, (((pci_read_config(dev,
570 			    PCIR_REVID, 4) & 0xf0) >> 4) + 'A'),
571 			    (pci_read_config(dev, PCIR_REVID, 4) & 0xf));
572 
573 			device_set_desc_copy(dev, descbuf);
574 			free(descbuf, M_TEMP);
575 			return(BUS_PROBE_DEFAULT);
576 		}
577 		t++;
578 	}
579 
580 	return(ENXIO);
581 }
582 
583 
584 /****************************************************************************/
585 /* PCI Capabilities Probe Function.                                         */
586 /*                                                                          */
587 /* Walks the PCI capabiites list for the device to find what features are   */
588 /* supported.                                                               */
589 /*                                                                          */
590 /* Returns:                                                                 */
591 /*   None.                                                                  */
592 /****************************************************************************/
593 static void
594 bce_print_adapter_info(struct bce_softc *sc)
595 {
596     int i = 0;
597 
598 	DBENTER(BCE_VERBOSE_LOAD);
599 
600 	BCE_PRINTF("ASIC (0x%08X); ", sc->bce_chipid);
601 	printf("Rev (%c%d); ", ((BCE_CHIP_ID(sc) & 0xf000) >> 12) + 'A',
602 	    ((BCE_CHIP_ID(sc) & 0x0ff0) >> 4));
603 
604 	/* Bus info. */
605 	if (sc->bce_flags & BCE_PCIE_FLAG) {
606 		printf("Bus (PCIe x%d, ", sc->link_width);
607 		switch (sc->link_speed) {
608 		case 1: printf("2.5Gbps); "); break;
609 		case 2:	printf("5Gbps); "); break;
610 		default: printf("Unknown link speed); ");
611 		}
612 	} else {
613 		printf("Bus (PCI%s, %s, %dMHz); ",
614 		    ((sc->bce_flags & BCE_PCIX_FLAG) ? "-X" : ""),
615 		    ((sc->bce_flags & BCE_PCI_32BIT_FLAG) ?
616 		    "32-bit" : "64-bit"), sc->bus_speed_mhz);
617 	}
618 
619 	/* Firmware version and device features. */
620 	printf("B/C (%s); Flags (", sc->bce_bc_ver);
621 
622 #ifdef BCE_JUMBO_HDRSPLIT
623 	printf("SPLT");
624 	i++;
625 #endif
626 
627 	if (sc->bce_flags & BCE_USING_MSI_FLAG) {
628 		if (i > 0) printf("|");
629 		printf("MSI"); i++;
630 	}
631 
632 	if (sc->bce_flags & BCE_USING_MSIX_FLAG) {
633 		if (i > 0) printf("|");
634 		printf("MSI-X"); i++;
635 	}
636 
637 	if (sc->bce_phy_flags & BCE_PHY_2_5G_CAPABLE_FLAG) {
638 		if (i > 0) printf("|");
639 		printf("2.5G"); i++;
640 	}
641 
642 	if (sc->bce_flags & BCE_MFW_ENABLE_FLAG) {
643 		if (i > 0) printf("|");
644 		printf("MFW); MFW (%s)\n", sc->bce_mfw_ver);
645 	} else {
646 		printf(")\n");
647 	}
648 
649 	DBEXIT(BCE_VERBOSE_LOAD);
650 }
651 
652 
653 /****************************************************************************/
654 /* PCI Capabilities Probe Function.                                         */
655 /*                                                                          */
656 /* Walks the PCI capabiites list for the device to find what features are   */
657 /* supported.                                                               */
658 /*                                                                          */
659 /* Returns:                                                                 */
660 /*   None.                                                                  */
661 /****************************************************************************/
662 static void
663 bce_probe_pci_caps(device_t dev, struct bce_softc *sc)
664 {
665 	u32 reg;
666 
667 	DBENTER(BCE_VERBOSE_LOAD);
668 
669 	/* Check if PCI-X capability is enabled. */
670 	if (pci_find_extcap(dev, PCIY_PCIX, &reg) == 0) {
671 		if (reg != 0)
672 			sc->bce_cap_flags |= BCE_PCIX_CAPABLE_FLAG;
673 	}
674 
675 	/* Check if PCIe capability is enabled. */
676 	if (pci_find_extcap(dev, PCIY_EXPRESS, &reg) == 0) {
677 		if (reg != 0) {
678 			u16 link_status = pci_read_config(dev, reg + 0x12, 2);
679 			DBPRINT(sc, BCE_INFO_LOAD, "PCIe link_status = "
680 			    "0x%08X\n",	link_status);
681 			sc->link_speed = link_status & 0xf;
682 			sc->link_width = (link_status >> 4) & 0x3f;
683 			sc->bce_cap_flags |= BCE_PCIE_CAPABLE_FLAG;
684 			sc->bce_flags |= BCE_PCIE_FLAG;
685 		}
686 	}
687 
688 	/* Check if MSI capability is enabled. */
689 	if (pci_find_extcap(dev, PCIY_MSI, &reg) == 0) {
690 		if (reg != 0)
691 			sc->bce_cap_flags |= BCE_MSI_CAPABLE_FLAG;
692 	}
693 
694 	/* Check if MSI-X capability is enabled. */
695 	if (pci_find_extcap(dev, PCIY_MSIX, &reg) == 0) {
696 		if (reg != 0)
697 			sc->bce_cap_flags |= BCE_MSIX_CAPABLE_FLAG;
698 	}
699 
700 	DBEXIT(BCE_VERBOSE_LOAD);
701 }
702 
703 
704 /****************************************************************************/
705 /* Device attach function.                                                  */
706 /*                                                                          */
707 /* Allocates device resources, performs secondary chip identification,      */
708 /* resets and initializes the hardware, and initializes driver instance     */
709 /* variables.                                                               */
710 /*                                                                          */
711 /* Returns:                                                                 */
712 /*   0 on success, positive value on failure.                               */
713 /****************************************************************************/
714 static int
715 bce_attach(device_t dev)
716 {
717 	struct bce_softc *sc;
718 	struct ifnet *ifp;
719 	u32 val;
720 	int error, rid, rc = 0;
721 
722 	sc = device_get_softc(dev);
723 	sc->bce_dev = dev;
724 
725 	DBENTER(BCE_VERBOSE_LOAD | BCE_VERBOSE_RESET);
726 
727 	sc->bce_unit = device_get_unit(dev);
728 
729 	/* Set initial device and PHY flags */
730 	sc->bce_flags = 0;
731 	sc->bce_phy_flags = 0;
732 
733 	pci_enable_busmaster(dev);
734 
735 	/* Allocate PCI memory resources. */
736 	rid = PCIR_BAR(0);
737 	sc->bce_res_mem = bus_alloc_resource_any(dev, SYS_RES_MEMORY,
738 		&rid, RF_ACTIVE);
739 
740 	if (sc->bce_res_mem == NULL) {
741 		BCE_PRINTF("%s(%d): PCI memory allocation failed\n",
742 		    __FILE__, __LINE__);
743 		rc = ENXIO;
744 		goto bce_attach_fail;
745 	}
746 
747 	/* Get various resource handles. */
748 	sc->bce_btag    = rman_get_bustag(sc->bce_res_mem);
749 	sc->bce_bhandle = rman_get_bushandle(sc->bce_res_mem);
750 	sc->bce_vhandle = (vm_offset_t) rman_get_virtual(sc->bce_res_mem);
751 
752 	bce_probe_pci_caps(dev, sc);
753 
754 	rid = 1;
755 #if 0
756 	/* Try allocating MSI-X interrupts. */
757 	if ((sc->bce_cap_flags & BCE_MSIX_CAPABLE_FLAG) &&
758 		(bce_msi_enable >= 2) &&
759 		((sc->bce_res_irq = bus_alloc_resource_any(dev, SYS_RES_MEMORY,
760 		&rid, RF_ACTIVE)) != NULL)) {
761 
762 		msi_needed = sc->bce_msi_count = 1;
763 
764 		if (((error = pci_alloc_msix(dev, &sc->bce_msi_count)) != 0) ||
765 			(sc->bce_msi_count != msi_needed)) {
766 			BCE_PRINTF("%s(%d): MSI-X allocation failed! Requested = %d,"
767 				"Received = %d, error = %d\n", __FILE__, __LINE__,
768 				msi_needed, sc->bce_msi_count, error);
769 			sc->bce_msi_count = 0;
770 			pci_release_msi(dev);
771 			bus_release_resource(dev, SYS_RES_MEMORY, rid,
772 				sc->bce_res_irq);
773 			sc->bce_res_irq = NULL;
774 		} else {
775 			DBPRINT(sc, BCE_INFO_LOAD, "%s(): Using MSI-X interrupt.\n",
776 				__FUNCTION__);
777 			sc->bce_flags |= BCE_USING_MSIX_FLAG;
778 			sc->bce_intr = bce_intr;
779 		}
780 	}
781 #endif
782 
783 	/* Try allocating a MSI interrupt. */
784 	if ((sc->bce_cap_flags & BCE_MSI_CAPABLE_FLAG) &&
785 		(bce_msi_enable >= 1) && (sc->bce_msi_count == 0)) {
786 		sc->bce_msi_count = 1;
787 		if ((error = pci_alloc_msi(dev, &sc->bce_msi_count)) != 0) {
788 			BCE_PRINTF("%s(%d): MSI allocation failed! error = %d\n",
789 				__FILE__, __LINE__, error);
790 			sc->bce_msi_count = 0;
791 			pci_release_msi(dev);
792 		} else {
793 			DBPRINT(sc, BCE_INFO_LOAD, "%s(): Using MSI interrupt.\n",
794 				__FUNCTION__);
795 			sc->bce_flags |= BCE_USING_MSI_FLAG;
796 			if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
797 				(BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716))
798 				sc->bce_flags |= BCE_ONE_SHOT_MSI_FLAG;
799 			sc->bce_irq_rid = 1;
800 			sc->bce_intr = bce_intr;
801 		}
802 	}
803 
804 	/* Try allocating a legacy interrupt. */
805 	if (sc->bce_msi_count == 0) {
806 		DBPRINT(sc, BCE_INFO_LOAD, "%s(): Using INTx interrupt.\n",
807 			__FUNCTION__);
808 		rid = 0;
809 		sc->bce_intr = bce_intr;
810 	}
811 
812 	sc->bce_res_irq = bus_alloc_resource_any(dev, SYS_RES_IRQ,
813 	    &rid, RF_SHAREABLE | RF_ACTIVE);
814 
815 	sc->bce_irq_rid = rid;
816 
817 	/* Report any IRQ allocation errors. */
818 	if (sc->bce_res_irq == NULL) {
819 		BCE_PRINTF("%s(%d): PCI map interrupt failed!\n",
820 		    __FILE__, __LINE__);
821 		rc = ENXIO;
822 		goto bce_attach_fail;
823 	}
824 
825 	/* Initialize mutex for the current device instance. */
826 	BCE_LOCK_INIT(sc, device_get_nameunit(dev));
827 
828 	/*
829 	 * Configure byte swap and enable indirect register access.
830 	 * Rely on CPU to do target byte swapping on big endian systems.
831 	 * Access to registers outside of PCI configurtion space are not
832 	 * valid until this is done.
833 	 */
834 	pci_write_config(dev, BCE_PCICFG_MISC_CONFIG,
835 	    BCE_PCICFG_MISC_CONFIG_REG_WINDOW_ENA |
836 	    BCE_PCICFG_MISC_CONFIG_TARGET_MB_WORD_SWAP, 4);
837 
838 	/* Save ASIC revsion info. */
839 	sc->bce_chipid =  REG_RD(sc, BCE_MISC_ID);
840 
841 	/* Weed out any non-production controller revisions. */
842 	switch(BCE_CHIP_ID(sc)) {
843 	case BCE_CHIP_ID_5706_A0:
844 	case BCE_CHIP_ID_5706_A1:
845 	case BCE_CHIP_ID_5708_A0:
846 	case BCE_CHIP_ID_5708_B0:
847 	case BCE_CHIP_ID_5709_A0:
848 	case BCE_CHIP_ID_5709_B0:
849 	case BCE_CHIP_ID_5709_B1:
850 	case BCE_CHIP_ID_5709_B2:
851 		BCE_PRINTF("%s(%d): Unsupported controller revision (%c%d)!\n",
852 		    __FILE__, __LINE__,
853 		    (((pci_read_config(dev, PCIR_REVID, 4) & 0xf0) >> 4) + 'A'),
854 		    (pci_read_config(dev, PCIR_REVID, 4) & 0xf));
855 		rc = ENODEV;
856 		goto bce_attach_fail;
857 	}
858 
859 	/*
860 	 * The embedded PCIe to PCI-X bridge (EPB)
861 	 * in the 5708 cannot address memory above
862 	 * 40 bits (E7_5708CB1_23043 & E6_5708SB1_23043).
863 	 */
864 	if (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5708)
865 		sc->max_bus_addr = BCE_BUS_SPACE_MAXADDR;
866 	else
867 		sc->max_bus_addr = BUS_SPACE_MAXADDR;
868 
869 	/*
870 	 * Find the base address for shared memory access.
871 	 * Newer versions of bootcode use a signature and offset
872 	 * while older versions use a fixed address.
873 	 */
874 	val = REG_RD_IND(sc, BCE_SHM_HDR_SIGNATURE);
875 	if ((val & BCE_SHM_HDR_SIGNATURE_SIG_MASK) == BCE_SHM_HDR_SIGNATURE_SIG)
876 		/* Multi-port devices use different offsets in shared memory. */
877 		sc->bce_shmem_base = REG_RD_IND(sc, BCE_SHM_HDR_ADDR_0 +
878 		    (pci_get_function(sc->bce_dev) << 2));
879 	else
880 		sc->bce_shmem_base = HOST_VIEW_SHMEM_BASE;
881 
882 	DBPRINT(sc, BCE_VERBOSE_FIRMWARE, "%s(): bce_shmem_base = 0x%08X\n",
883 	    __FUNCTION__, sc->bce_shmem_base);
884 
885 	/* Fetch the bootcode revision. */
886 	val = bce_shmem_rd(sc, BCE_DEV_INFO_BC_REV);
887 	for (int i = 0, j = 0; i < 3; i++) {
888 		u8 num;
889 
890 		num = (u8) (val >> (24 - (i * 8)));
891 		for (int k = 100, skip0 = 1; k >= 1; num %= k, k /= 10) {
892 			if (num >= k || !skip0 || k == 1) {
893 				sc->bce_bc_ver[j++] = (num / k) + '0';
894 				skip0 = 0;
895 			}
896 		}
897 
898 		if (i != 2)
899 			sc->bce_bc_ver[j++] = '.';
900 	}
901 
902 	/* Check if any management firwmare is enabled. */
903 	val = bce_shmem_rd(sc, BCE_PORT_FEATURE);
904 	if (val & BCE_PORT_FEATURE_ASF_ENABLED) {
905 		sc->bce_flags |= BCE_MFW_ENABLE_FLAG;
906 
907 		/* Allow time for firmware to enter the running state. */
908 		for (int i = 0; i < 30; i++) {
909 			val = bce_shmem_rd(sc, BCE_BC_STATE_CONDITION);
910 			if (val & BCE_CONDITION_MFW_RUN_MASK)
911 				break;
912 			DELAY(10000);
913 		}
914 
915 		/* Check if management firmware is running. */
916 		val = bce_shmem_rd(sc, BCE_BC_STATE_CONDITION);
917 		val &= BCE_CONDITION_MFW_RUN_MASK;
918 		if ((val != BCE_CONDITION_MFW_RUN_UNKNOWN) &&
919 		    (val != BCE_CONDITION_MFW_RUN_NONE)) {
920 			u32 addr = bce_shmem_rd(sc, BCE_MFW_VER_PTR);
921 			int i = 0;
922 
923 			/* Read the management firmware version string. */
924 			for (int j = 0; j < 3; j++) {
925 				val = bce_reg_rd_ind(sc, addr + j * 4);
926 				val = bswap32(val);
927 				memcpy(&sc->bce_mfw_ver[i], &val, 4);
928 				i += 4;
929 			}
930 		} else {
931 			/* May cause firmware synchronization timeouts. */
932 			BCE_PRINTF("%s(%d): Management firmware enabled "
933 			    "but not running!\n", __FILE__, __LINE__);
934 			strcpy(sc->bce_mfw_ver, "NOT RUNNING!");
935 
936 			/* ToDo: Any action the driver should take? */
937 		}
938 	}
939 
940 	/* Get PCI bus information (speed and type). */
941 	val = REG_RD(sc, BCE_PCICFG_MISC_STATUS);
942 	if (val & BCE_PCICFG_MISC_STATUS_PCIX_DET) {
943 		u32 clkreg;
944 
945 		sc->bce_flags |= BCE_PCIX_FLAG;
946 
947 		clkreg = REG_RD(sc, BCE_PCICFG_PCI_CLOCK_CONTROL_BITS);
948 
949 		clkreg &= BCE_PCICFG_PCI_CLOCK_CONTROL_BITS_PCI_CLK_SPD_DET;
950 		switch (clkreg) {
951 		case BCE_PCICFG_PCI_CLOCK_CONTROL_BITS_PCI_CLK_SPD_DET_133MHZ:
952 			sc->bus_speed_mhz = 133;
953 			break;
954 
955 		case BCE_PCICFG_PCI_CLOCK_CONTROL_BITS_PCI_CLK_SPD_DET_95MHZ:
956 			sc->bus_speed_mhz = 100;
957 			break;
958 
959 		case BCE_PCICFG_PCI_CLOCK_CONTROL_BITS_PCI_CLK_SPD_DET_66MHZ:
960 		case BCE_PCICFG_PCI_CLOCK_CONTROL_BITS_PCI_CLK_SPD_DET_80MHZ:
961 			sc->bus_speed_mhz = 66;
962 			break;
963 
964 		case BCE_PCICFG_PCI_CLOCK_CONTROL_BITS_PCI_CLK_SPD_DET_48MHZ:
965 		case BCE_PCICFG_PCI_CLOCK_CONTROL_BITS_PCI_CLK_SPD_DET_55MHZ:
966 			sc->bus_speed_mhz = 50;
967 			break;
968 
969 		case BCE_PCICFG_PCI_CLOCK_CONTROL_BITS_PCI_CLK_SPD_DET_LOW:
970 		case BCE_PCICFG_PCI_CLOCK_CONTROL_BITS_PCI_CLK_SPD_DET_32MHZ:
971 		case BCE_PCICFG_PCI_CLOCK_CONTROL_BITS_PCI_CLK_SPD_DET_38MHZ:
972 			sc->bus_speed_mhz = 33;
973 			break;
974 		}
975 	} else {
976 		if (val & BCE_PCICFG_MISC_STATUS_M66EN)
977 			sc->bus_speed_mhz = 66;
978 		else
979 			sc->bus_speed_mhz = 33;
980 	}
981 
982 	if (val & BCE_PCICFG_MISC_STATUS_32BIT_DET)
983 		sc->bce_flags |= BCE_PCI_32BIT_FLAG;
984 
985 	/* Reset controller and announce to bootcode that driver is present. */
986 	if (bce_reset(sc, BCE_DRV_MSG_CODE_RESET)) {
987 		BCE_PRINTF("%s(%d): Controller reset failed!\n",
988 		    __FILE__, __LINE__);
989 		rc = ENXIO;
990 		goto bce_attach_fail;
991 	}
992 
993 	/* Initialize the controller. */
994 	if (bce_chipinit(sc)) {
995 		BCE_PRINTF("%s(%d): Controller initialization failed!\n",
996 		    __FILE__, __LINE__);
997 		rc = ENXIO;
998 		goto bce_attach_fail;
999 	}
1000 
1001 	/* Perform NVRAM test. */
1002 	if (bce_nvram_test(sc)) {
1003 		BCE_PRINTF("%s(%d): NVRAM test failed!\n",
1004 		    __FILE__, __LINE__);
1005 		rc = ENXIO;
1006 		goto bce_attach_fail;
1007 	}
1008 
1009 	/* Fetch the permanent Ethernet MAC address. */
1010 	bce_get_mac_addr(sc);
1011 
1012 	/*
1013 	 * Trip points control how many BDs
1014 	 * should be ready before generating an
1015 	 * interrupt while ticks control how long
1016 	 * a BD can sit in the chain before
1017 	 * generating an interrupt.  Set the default
1018 	 * values for the RX and TX chains.
1019 	 */
1020 
1021 #ifdef BCE_DEBUG
1022 	/* Force more frequent interrupts. */
1023 	sc->bce_tx_quick_cons_trip_int = 1;
1024 	sc->bce_tx_quick_cons_trip     = 1;
1025 	sc->bce_tx_ticks_int           = 0;
1026 	sc->bce_tx_ticks               = 0;
1027 
1028 	sc->bce_rx_quick_cons_trip_int = 1;
1029 	sc->bce_rx_quick_cons_trip     = 1;
1030 	sc->bce_rx_ticks_int           = 0;
1031 	sc->bce_rx_ticks               = 0;
1032 #else
1033 	/* Improve throughput at the expense of increased latency. */
1034 	sc->bce_tx_quick_cons_trip_int = 20;
1035 	sc->bce_tx_quick_cons_trip     = 20;
1036 	sc->bce_tx_ticks_int           = 80;
1037 	sc->bce_tx_ticks               = 80;
1038 
1039 	sc->bce_rx_quick_cons_trip_int = 6;
1040 	sc->bce_rx_quick_cons_trip     = 6;
1041 	sc->bce_rx_ticks_int           = 18;
1042 	sc->bce_rx_ticks               = 18;
1043 #endif
1044 
1045 	/* Not used for L2. */
1046 	sc->bce_comp_prod_trip_int = 0;
1047 	sc->bce_comp_prod_trip = 0;
1048 	sc->bce_com_ticks_int = 0;
1049 	sc->bce_com_ticks = 0;
1050 	sc->bce_cmd_ticks_int = 0;
1051 	sc->bce_cmd_ticks = 0;
1052 
1053 	/* Update statistics once every second. */
1054 	sc->bce_stats_ticks = 1000000 & 0xffff00;
1055 
1056 	/* Find the media type for the adapter. */
1057 	bce_get_media(sc);
1058 
1059 	/* Store data needed by PHY driver for backplane applications */
1060 	sc->bce_shared_hw_cfg = bce_shmem_rd(sc, BCE_SHARED_HW_CFG_CONFIG);
1061 	sc->bce_port_hw_cfg   = bce_shmem_rd(sc, BCE_PORT_HW_CFG_CONFIG);
1062 
1063 	/* Allocate DMA memory resources. */
1064 	if (bce_dma_alloc(dev)) {
1065 		BCE_PRINTF("%s(%d): DMA resource allocation failed!\n",
1066 		    __FILE__, __LINE__);
1067 		rc = ENXIO;
1068 		goto bce_attach_fail;
1069 	}
1070 
1071 	/* Allocate an ifnet structure. */
1072 	ifp = sc->bce_ifp = if_alloc(IFT_ETHER);
1073 	if (ifp == NULL) {
1074 		BCE_PRINTF("%s(%d): Interface allocation failed!\n",
1075 			__FILE__, __LINE__);
1076 		rc = ENXIO;
1077 		goto bce_attach_fail;
1078 	}
1079 
1080 	/* Initialize the ifnet interface. */
1081 	ifp->if_softc        = sc;
1082 	if_initname(ifp, device_get_name(dev), device_get_unit(dev));
1083 	ifp->if_flags        = IFF_BROADCAST | IFF_SIMPLEX | IFF_MULTICAST;
1084 	ifp->if_ioctl        = bce_ioctl;
1085 	ifp->if_start        = bce_start;
1086 	ifp->if_init         = bce_init;
1087 	ifp->if_mtu          = ETHERMTU;
1088 
1089 	if (bce_tso_enable) {
1090 		ifp->if_hwassist = BCE_IF_HWASSIST | CSUM_TSO;
1091 		ifp->if_capabilities = BCE_IF_CAPABILITIES | IFCAP_TSO4 |
1092 		    IFCAP_VLAN_HWTSO;
1093 	} else {
1094 		ifp->if_hwassist = BCE_IF_HWASSIST;
1095 		ifp->if_capabilities = BCE_IF_CAPABILITIES;
1096 	}
1097 
1098 	ifp->if_capenable    = ifp->if_capabilities;
1099 
1100 	/*
1101 	 * Assume standard mbuf sizes for buffer allocation.
1102 	 * This may change later if the MTU size is set to
1103 	 * something other than 1500.
1104 	 */
1105 #ifdef BCE_JUMBO_HDRSPLIT
1106 	sc->rx_bd_mbuf_alloc_size = MHLEN;
1107 	/* Make sure offset is 16 byte aligned for hardware. */
1108 	sc->rx_bd_mbuf_align_pad  = roundup2((MSIZE - MHLEN), 16) -
1109 		(MSIZE - MHLEN);
1110 	sc->rx_bd_mbuf_data_len   = sc->rx_bd_mbuf_alloc_size -
1111 		sc->rx_bd_mbuf_align_pad;
1112 	sc->pg_bd_mbuf_alloc_size = MCLBYTES;
1113 #else
1114 	sc->rx_bd_mbuf_alloc_size = MCLBYTES;
1115 	sc->rx_bd_mbuf_align_pad  = roundup2(MCLBYTES, 16) - MCLBYTES;
1116 	sc->rx_bd_mbuf_data_len   = sc->rx_bd_mbuf_alloc_size -
1117 		sc->rx_bd_mbuf_align_pad;
1118 #endif
1119 
1120 	ifp->if_snd.ifq_drv_maxlen = USABLE_TX_BD;
1121 	IFQ_SET_MAXLEN(&ifp->if_snd, ifp->if_snd.ifq_drv_maxlen);
1122 	IFQ_SET_READY(&ifp->if_snd);
1123 
1124 	if (sc->bce_phy_flags & BCE_PHY_2_5G_CAPABLE_FLAG)
1125 		ifp->if_baudrate = IF_Mbps(2500ULL);
1126 	else
1127 		ifp->if_baudrate = IF_Mbps(1000);
1128 
1129     /* Handle any special PHY initialization for SerDes PHYs. */
1130     bce_init_media(sc);
1131 
1132 	/* MII child bus by probing the PHY. */
1133 	if (mii_phy_probe(dev, &sc->bce_miibus, bce_ifmedia_upd,
1134 		bce_ifmedia_sts)) {
1135 		BCE_PRINTF("%s(%d): No PHY found on child MII bus!\n",
1136 			__FILE__, __LINE__);
1137 		rc = ENXIO;
1138 		goto bce_attach_fail;
1139 	}
1140 
1141 	/* Attach to the Ethernet interface list. */
1142 	ether_ifattach(ifp, sc->eaddr);
1143 
1144 #if __FreeBSD_version < 500000
1145 	callout_init(&sc->bce_tick_callout);
1146 	callout_init(&sc->bce_pulse_callout);
1147 #else
1148 	callout_init_mtx(&sc->bce_tick_callout, &sc->bce_mtx, 0);
1149 	callout_init_mtx(&sc->bce_pulse_callout, &sc->bce_mtx, 0);
1150 #endif
1151 
1152 	/* Hookup IRQ last. */
1153 	rc = bus_setup_intr(dev, sc->bce_res_irq, INTR_TYPE_NET | INTR_MPSAFE,
1154 		NULL, bce_intr, sc, &sc->bce_intrhand);
1155 
1156 	if (rc) {
1157 		BCE_PRINTF("%s(%d): Failed to setup IRQ!\n",
1158 			__FILE__, __LINE__);
1159 		bce_detach(dev);
1160 		goto bce_attach_exit;
1161 	}
1162 
1163 	/*
1164 	 * At this point we've acquired all the resources
1165 	 * we need to run so there's no turning back, we're
1166 	 * cleared for launch.
1167 	 */
1168 
1169 	/* Print some important debugging info. */
1170 	DBRUNMSG(BCE_INFO, bce_dump_driver_state(sc));
1171 
1172 	/* Add the supported sysctls to the kernel. */
1173 	bce_add_sysctls(sc);
1174 
1175 	BCE_LOCK(sc);
1176 
1177 	/*
1178 	 * The chip reset earlier notified the bootcode that
1179 	 * a driver is present.  We now need to start our pulse
1180 	 * routine so that the bootcode is reminded that we're
1181 	 * still running.
1182 	 */
1183 	bce_pulse(sc);
1184 
1185 	bce_mgmt_init_locked(sc);
1186 	BCE_UNLOCK(sc);
1187 
1188 	/* Finally, print some useful adapter info */
1189 	bce_print_adapter_info(sc);
1190 	DBPRINT(sc, BCE_FATAL, "%s(): sc = %p\n",
1191 		__FUNCTION__, sc);
1192 
1193 	goto bce_attach_exit;
1194 
1195 bce_attach_fail:
1196 	bce_release_resources(sc);
1197 
1198 bce_attach_exit:
1199 
1200 	DBEXIT(BCE_VERBOSE_LOAD | BCE_VERBOSE_RESET);
1201 
1202 	return(rc);
1203 }
1204 
1205 
1206 /****************************************************************************/
1207 /* Device detach function.                                                  */
1208 /*                                                                          */
1209 /* Stops the controller, resets the controller, and releases resources.     */
1210 /*                                                                          */
1211 /* Returns:                                                                 */
1212 /*   0 on success, positive value on failure.                               */
1213 /****************************************************************************/
1214 static int
1215 bce_detach(device_t dev)
1216 {
1217 	struct bce_softc *sc = device_get_softc(dev);
1218 	struct ifnet *ifp;
1219 	u32 msg;
1220 
1221 	DBENTER(BCE_VERBOSE_UNLOAD | BCE_VERBOSE_RESET);
1222 
1223 	ifp = sc->bce_ifp;
1224 
1225 	/* Stop and reset the controller. */
1226 	BCE_LOCK(sc);
1227 
1228 	/* Stop the pulse so the bootcode can go to driver absent state. */
1229 	callout_stop(&sc->bce_pulse_callout);
1230 
1231 	bce_stop(sc);
1232 	if (sc->bce_flags & BCE_NO_WOL_FLAG)
1233 		msg = BCE_DRV_MSG_CODE_UNLOAD_LNK_DN;
1234 	else
1235 		msg = BCE_DRV_MSG_CODE_UNLOAD;
1236 	bce_reset(sc, msg);
1237 
1238 	BCE_UNLOCK(sc);
1239 
1240 	ether_ifdetach(ifp);
1241 
1242 	/* If we have a child device on the MII bus remove it too. */
1243 	bus_generic_detach(dev);
1244 	device_delete_child(dev, sc->bce_miibus);
1245 
1246 	/* Release all remaining resources. */
1247 	bce_release_resources(sc);
1248 
1249 	DBEXIT(BCE_VERBOSE_UNLOAD | BCE_VERBOSE_RESET);
1250 
1251 	return(0);
1252 }
1253 
1254 
1255 /****************************************************************************/
1256 /* Device shutdown function.                                                */
1257 /*                                                                          */
1258 /* Stops and resets the controller.                                         */
1259 /*                                                                          */
1260 /* Returns:                                                                 */
1261 /*   0 on success, positive value on failure.                               */
1262 /****************************************************************************/
1263 static int
1264 bce_shutdown(device_t dev)
1265 {
1266 	struct bce_softc *sc = device_get_softc(dev);
1267 	u32 msg;
1268 
1269 	DBENTER(BCE_VERBOSE);
1270 
1271 	BCE_LOCK(sc);
1272 	bce_stop(sc);
1273 	if (sc->bce_flags & BCE_NO_WOL_FLAG)
1274 		msg = BCE_DRV_MSG_CODE_UNLOAD_LNK_DN;
1275 	else
1276 		msg = BCE_DRV_MSG_CODE_UNLOAD;
1277 	bce_reset(sc, msg);
1278 	BCE_UNLOCK(sc);
1279 
1280 	DBEXIT(BCE_VERBOSE);
1281 
1282 	return (0);
1283 }
1284 
1285 
1286 #ifdef BCE_DEBUG
1287 /****************************************************************************/
1288 /* Register read.                                                           */
1289 /*                                                                          */
1290 /* Returns:                                                                 */
1291 /*   The value of the register.                                             */
1292 /****************************************************************************/
1293 static u32
1294 bce_reg_rd(struct bce_softc *sc, u32 offset)
1295 {
1296 	u32 val = bus_space_read_4(sc->bce_btag, sc->bce_bhandle, offset);
1297 	DBPRINT(sc, BCE_INSANE_REG, "%s(); offset = 0x%08X, val = 0x%08X\n",
1298 		__FUNCTION__, offset, val);
1299 	return val;
1300 }
1301 
1302 
1303 /****************************************************************************/
1304 /* Register write (16 bit).                                                 */
1305 /*                                                                          */
1306 /* Returns:                                                                 */
1307 /*   Nothing.                                                               */
1308 /****************************************************************************/
1309 static void
1310 bce_reg_wr16(struct bce_softc *sc, u32 offset, u16 val)
1311 {
1312 	DBPRINT(sc, BCE_INSANE_REG, "%s(); offset = 0x%08X, val = 0x%04X\n",
1313 		__FUNCTION__, offset, val);
1314 	bus_space_write_2(sc->bce_btag, sc->bce_bhandle, offset, val);
1315 }
1316 
1317 
1318 /****************************************************************************/
1319 /* Register write.                                                          */
1320 /*                                                                          */
1321 /* Returns:                                                                 */
1322 /*   Nothing.                                                               */
1323 /****************************************************************************/
1324 static void
1325 bce_reg_wr(struct bce_softc *sc, u32 offset, u32 val)
1326 {
1327 	DBPRINT(sc, BCE_INSANE_REG, "%s(); offset = 0x%08X, val = 0x%08X\n",
1328 		__FUNCTION__, offset, val);
1329 	bus_space_write_4(sc->bce_btag, sc->bce_bhandle, offset, val);
1330 }
1331 #endif
1332 
1333 /****************************************************************************/
1334 /* Indirect register read.                                                  */
1335 /*                                                                          */
1336 /* Reads NetXtreme II registers using an index/data register pair in PCI    */
1337 /* configuration space.  Using this mechanism avoids issues with posted     */
1338 /* reads but is much slower than memory-mapped I/O.                         */
1339 /*                                                                          */
1340 /* Returns:                                                                 */
1341 /*   The value of the register.                                             */
1342 /****************************************************************************/
1343 static u32
1344 bce_reg_rd_ind(struct bce_softc *sc, u32 offset)
1345 {
1346 	device_t dev;
1347 	dev = sc->bce_dev;
1348 
1349 	pci_write_config(dev, BCE_PCICFG_REG_WINDOW_ADDRESS, offset, 4);
1350 #ifdef BCE_DEBUG
1351 	{
1352 		u32 val;
1353 		val = pci_read_config(dev, BCE_PCICFG_REG_WINDOW, 4);
1354 		DBPRINT(sc, BCE_INSANE_REG, "%s(); offset = 0x%08X, val = 0x%08X\n",
1355 			__FUNCTION__, offset, val);
1356 		return val;
1357 	}
1358 #else
1359 	return pci_read_config(dev, BCE_PCICFG_REG_WINDOW, 4);
1360 #endif
1361 }
1362 
1363 
1364 /****************************************************************************/
1365 /* Indirect register write.                                                 */
1366 /*                                                                          */
1367 /* Writes NetXtreme II registers using an index/data register pair in PCI   */
1368 /* configuration space.  Using this mechanism avoids issues with posted     */
1369 /* writes but is muchh slower than memory-mapped I/O.                       */
1370 /*                                                                          */
1371 /* Returns:                                                                 */
1372 /*   Nothing.                                                               */
1373 /****************************************************************************/
1374 static void
1375 bce_reg_wr_ind(struct bce_softc *sc, u32 offset, u32 val)
1376 {
1377 	device_t dev;
1378 	dev = sc->bce_dev;
1379 
1380 	DBPRINT(sc, BCE_INSANE_REG, "%s(); offset = 0x%08X, val = 0x%08X\n",
1381 		__FUNCTION__, offset, val);
1382 
1383 	pci_write_config(dev, BCE_PCICFG_REG_WINDOW_ADDRESS, offset, 4);
1384 	pci_write_config(dev, BCE_PCICFG_REG_WINDOW, val, 4);
1385 }
1386 
1387 
1388 /****************************************************************************/
1389 /* Shared memory write.                                                     */
1390 /*                                                                          */
1391 /* Writes NetXtreme II shared memory region.                                */
1392 /*                                                                          */
1393 /* Returns:                                                                 */
1394 /*   Nothing.                                                               */
1395 /****************************************************************************/
1396 static void
1397 bce_shmem_wr(struct bce_softc *sc, u32 offset, u32 val)
1398 {
1399 	bce_reg_wr_ind(sc, sc->bce_shmem_base + offset, val);
1400 }
1401 
1402 
1403 /****************************************************************************/
1404 /* Shared memory read.                                                      */
1405 /*                                                                          */
1406 /* Reads NetXtreme II shared memory region.                                 */
1407 /*                                                                          */
1408 /* Returns:                                                                 */
1409 /*   The 32 bit value read.                                                 */
1410 /****************************************************************************/
1411 static u32
1412 bce_shmem_rd(struct bce_softc *sc, u32 offset)
1413 {
1414 	return (bce_reg_rd_ind(sc, sc->bce_shmem_base + offset));
1415 }
1416 
1417 
1418 #ifdef BCE_DEBUG
1419 /****************************************************************************/
1420 /* Context memory read.                                                     */
1421 /*                                                                          */
1422 /* The NetXtreme II controller uses context memory to track connection      */
1423 /* information for L2 and higher network protocols.                         */
1424 /*                                                                          */
1425 /* Returns:                                                                 */
1426 /*   The requested 32 bit value of context memory.                          */
1427 /****************************************************************************/
1428 static u32
1429 bce_ctx_rd(struct bce_softc *sc, u32 cid_addr, u32 ctx_offset)
1430 {
1431 	u32 idx, offset, retry_cnt = 5, val;
1432 
1433 	DBRUNIF((cid_addr > MAX_CID_ADDR || ctx_offset & 0x3 || cid_addr & CTX_MASK),
1434 		BCE_PRINTF("%s(): Invalid CID address: 0x%08X.\n",
1435 			__FUNCTION__, cid_addr));
1436 
1437 	offset = ctx_offset + cid_addr;
1438 
1439 	if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
1440 		(BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
1441 
1442 		REG_WR(sc, BCE_CTX_CTX_CTRL, (offset | BCE_CTX_CTX_CTRL_READ_REQ));
1443 
1444 		for (idx = 0; idx < retry_cnt; idx++) {
1445 			val = REG_RD(sc, BCE_CTX_CTX_CTRL);
1446 			if ((val & BCE_CTX_CTX_CTRL_READ_REQ) == 0)
1447 				break;
1448 			DELAY(5);
1449 		}
1450 
1451 		if (val & BCE_CTX_CTX_CTRL_READ_REQ)
1452 			BCE_PRINTF("%s(%d); Unable to read CTX memory: "
1453 				"cid_addr = 0x%08X, offset = 0x%08X!\n",
1454 				__FILE__, __LINE__, cid_addr, ctx_offset);
1455 
1456 		val = REG_RD(sc, BCE_CTX_CTX_DATA);
1457 	} else {
1458 		REG_WR(sc, BCE_CTX_DATA_ADR, offset);
1459 		val = REG_RD(sc, BCE_CTX_DATA);
1460 	}
1461 
1462 	DBPRINT(sc, BCE_EXTREME_CTX, "%s(); cid_addr = 0x%08X, offset = 0x%08X, "
1463 		"val = 0x%08X\n", __FUNCTION__, cid_addr, ctx_offset, val);
1464 
1465 	return(val);
1466 }
1467 #endif
1468 
1469 
1470 /****************************************************************************/
1471 /* Context memory write.                                                    */
1472 /*                                                                          */
1473 /* The NetXtreme II controller uses context memory to track connection      */
1474 /* information for L2 and higher network protocols.                         */
1475 /*                                                                          */
1476 /* Returns:                                                                 */
1477 /*   Nothing.                                                               */
1478 /****************************************************************************/
1479 static void
1480 bce_ctx_wr(struct bce_softc *sc, u32 cid_addr, u32 ctx_offset, u32 ctx_val)
1481 {
1482 	u32 idx, offset = ctx_offset + cid_addr;
1483 	u32 val, retry_cnt = 5;
1484 
1485 	DBPRINT(sc, BCE_EXTREME_CTX, "%s(); cid_addr = 0x%08X, offset = 0x%08X, "
1486 		"val = 0x%08X\n", __FUNCTION__, cid_addr, ctx_offset, ctx_val);
1487 
1488 	DBRUNIF((cid_addr > MAX_CID_ADDR || ctx_offset & 0x3 || cid_addr & CTX_MASK),
1489 		BCE_PRINTF("%s(): Invalid CID address: 0x%08X.\n",
1490 			__FUNCTION__, cid_addr));
1491 
1492 	if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
1493 		(BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
1494 
1495 		REG_WR(sc, BCE_CTX_CTX_DATA, ctx_val);
1496 		REG_WR(sc, BCE_CTX_CTX_CTRL, (offset | BCE_CTX_CTX_CTRL_WRITE_REQ));
1497 
1498 		for (idx = 0; idx < retry_cnt; idx++) {
1499 			val = REG_RD(sc, BCE_CTX_CTX_CTRL);
1500 			if ((val & BCE_CTX_CTX_CTRL_WRITE_REQ) == 0)
1501 				break;
1502 			DELAY(5);
1503 		}
1504 
1505 		if (val & BCE_CTX_CTX_CTRL_WRITE_REQ)
1506 			BCE_PRINTF("%s(%d); Unable to write CTX memory: "
1507 				"cid_addr = 0x%08X, offset = 0x%08X!\n",
1508 				__FILE__, __LINE__, cid_addr, ctx_offset);
1509 
1510 	} else {
1511 		REG_WR(sc, BCE_CTX_DATA_ADR, offset);
1512 		REG_WR(sc, BCE_CTX_DATA, ctx_val);
1513 	}
1514 }
1515 
1516 
1517 /****************************************************************************/
1518 /* PHY register read.                                                       */
1519 /*                                                                          */
1520 /* Implements register reads on the MII bus.                                */
1521 /*                                                                          */
1522 /* Returns:                                                                 */
1523 /*   The value of the register.                                             */
1524 /****************************************************************************/
1525 static int
1526 bce_miibus_read_reg(device_t dev, int phy, int reg)
1527 {
1528 	struct bce_softc *sc;
1529 	u32 val;
1530 	int i;
1531 
1532 	sc = device_get_softc(dev);
1533 
1534 	/* Make sure we are accessing the correct PHY address. */
1535 	if (phy != sc->bce_phy_addr) {
1536 		DBPRINT(sc, BCE_INSANE_PHY, "Invalid PHY address %d "
1537 		    "for PHY read!\n", phy);
1538 		return(0);
1539 	}
1540 
1541     /*
1542      * The 5709S PHY is an IEEE Clause 45 PHY
1543      * with special mappings to work with IEEE
1544      * Clause 22 register accesses.
1545      */
1546 	if ((sc->bce_phy_flags & BCE_PHY_IEEE_CLAUSE_45_FLAG) != 0) {
1547 		if (reg >= MII_BMCR && reg <= MII_ANLPRNP)
1548 			reg += 0x10;
1549 	}
1550 
1551     if (sc->bce_phy_flags & BCE_PHY_INT_MODE_AUTO_POLLING_FLAG) {
1552 		val = REG_RD(sc, BCE_EMAC_MDIO_MODE);
1553 		val &= ~BCE_EMAC_MDIO_MODE_AUTO_POLL;
1554 
1555 		REG_WR(sc, BCE_EMAC_MDIO_MODE, val);
1556 		REG_RD(sc, BCE_EMAC_MDIO_MODE);
1557 
1558 		DELAY(40);
1559 	}
1560 
1561 
1562 	val = BCE_MIPHY(phy) | BCE_MIREG(reg) |
1563 	    BCE_EMAC_MDIO_COMM_COMMAND_READ | BCE_EMAC_MDIO_COMM_DISEXT |
1564 	    BCE_EMAC_MDIO_COMM_START_BUSY;
1565 	REG_WR(sc, BCE_EMAC_MDIO_COMM, val);
1566 
1567 	for (i = 0; i < BCE_PHY_TIMEOUT; i++) {
1568 		DELAY(10);
1569 
1570 		val = REG_RD(sc, BCE_EMAC_MDIO_COMM);
1571 		if (!(val & BCE_EMAC_MDIO_COMM_START_BUSY)) {
1572 			DELAY(5);
1573 
1574 			val = REG_RD(sc, BCE_EMAC_MDIO_COMM);
1575 			val &= BCE_EMAC_MDIO_COMM_DATA;
1576 
1577 			break;
1578 		}
1579 	}
1580 
1581 	if (val & BCE_EMAC_MDIO_COMM_START_BUSY) {
1582 		BCE_PRINTF("%s(%d): Error: PHY read timeout! phy = %d, "
1583 		    "reg = 0x%04X\n", __FILE__, __LINE__, phy, reg);
1584 		val = 0x0;
1585 	} else {
1586 		val = REG_RD(sc, BCE_EMAC_MDIO_COMM);
1587 	}
1588 
1589 
1590 	if (sc->bce_phy_flags & BCE_PHY_INT_MODE_AUTO_POLLING_FLAG) {
1591 		val = REG_RD(sc, BCE_EMAC_MDIO_MODE);
1592 		val |= BCE_EMAC_MDIO_MODE_AUTO_POLL;
1593 
1594 		REG_WR(sc, BCE_EMAC_MDIO_MODE, val);
1595 		REG_RD(sc, BCE_EMAC_MDIO_MODE);
1596 
1597 		DELAY(40);
1598 	}
1599 
1600 	DB_PRINT_PHY_REG(reg, val);
1601 	return (val & 0xffff);
1602 
1603 }
1604 
1605 
1606 /****************************************************************************/
1607 /* PHY register write.                                                      */
1608 /*                                                                          */
1609 /* Implements register writes on the MII bus.                               */
1610 /*                                                                          */
1611 /* Returns:                                                                 */
1612 /*   The value of the register.                                             */
1613 /****************************************************************************/
1614 static int
1615 bce_miibus_write_reg(device_t dev, int phy, int reg, int val)
1616 {
1617 	struct bce_softc *sc;
1618 	u32 val1;
1619 	int i;
1620 
1621 	sc = device_get_softc(dev);
1622 
1623 	/* Make sure we are accessing the correct PHY address. */
1624 	if (phy != sc->bce_phy_addr) {
1625 		DBPRINT(sc, BCE_INSANE_PHY, "Invalid PHY address %d "
1626 		    "for PHY write!\n", phy);
1627 		return(0);
1628 	}
1629 
1630 	DB_PRINT_PHY_REG(reg, val);
1631 
1632 	/*
1633 	 * The 5709S PHY is an IEEE Clause 45 PHY
1634 	 * with special mappings to work with IEEE
1635 	 * Clause 22 register accesses.
1636 	 */
1637 	if ((sc->bce_phy_flags & BCE_PHY_IEEE_CLAUSE_45_FLAG) != 0) {
1638 		if (reg >= MII_BMCR && reg <= MII_ANLPRNP)
1639 			reg += 0x10;
1640 	}
1641 
1642 	if (sc->bce_phy_flags & BCE_PHY_INT_MODE_AUTO_POLLING_FLAG) {
1643 		val1 = REG_RD(sc, BCE_EMAC_MDIO_MODE);
1644 		val1 &= ~BCE_EMAC_MDIO_MODE_AUTO_POLL;
1645 
1646 		REG_WR(sc, BCE_EMAC_MDIO_MODE, val1);
1647 		REG_RD(sc, BCE_EMAC_MDIO_MODE);
1648 
1649 		DELAY(40);
1650 	}
1651 
1652 	val1 = BCE_MIPHY(phy) | BCE_MIREG(reg) | val |
1653 	    BCE_EMAC_MDIO_COMM_COMMAND_WRITE |
1654 	    BCE_EMAC_MDIO_COMM_START_BUSY | BCE_EMAC_MDIO_COMM_DISEXT;
1655 	REG_WR(sc, BCE_EMAC_MDIO_COMM, val1);
1656 
1657 	for (i = 0; i < BCE_PHY_TIMEOUT; i++) {
1658 		DELAY(10);
1659 
1660 		val1 = REG_RD(sc, BCE_EMAC_MDIO_COMM);
1661 		if (!(val1 & BCE_EMAC_MDIO_COMM_START_BUSY)) {
1662 			DELAY(5);
1663 			break;
1664 		}
1665 	}
1666 
1667 	if (val1 & BCE_EMAC_MDIO_COMM_START_BUSY)
1668 		BCE_PRINTF("%s(%d): PHY write timeout!\n",
1669 		    __FILE__, __LINE__);
1670 
1671 	if (sc->bce_phy_flags & BCE_PHY_INT_MODE_AUTO_POLLING_FLAG) {
1672 		val1 = REG_RD(sc, BCE_EMAC_MDIO_MODE);
1673 		val1 |= BCE_EMAC_MDIO_MODE_AUTO_POLL;
1674 
1675 		REG_WR(sc, BCE_EMAC_MDIO_MODE, val1);
1676 		REG_RD(sc, BCE_EMAC_MDIO_MODE);
1677 
1678 		DELAY(40);
1679 	}
1680 
1681 	return 0;
1682 }
1683 
1684 
1685 /****************************************************************************/
1686 /* MII bus status change.                                                   */
1687 /*                                                                          */
1688 /* Called by the MII bus driver when the PHY establishes link to set the    */
1689 /* MAC interface registers.                                                 */
1690 /*                                                                          */
1691 /* Returns:                                                                 */
1692 /*   Nothing.                                                               */
1693 /****************************************************************************/
1694 static void
1695 bce_miibus_statchg(device_t dev)
1696 {
1697 	struct bce_softc *sc;
1698 	struct mii_data *mii;
1699 	int val;
1700 
1701 	sc = device_get_softc(dev);
1702 
1703 	DBENTER(BCE_VERBOSE_PHY);
1704 
1705 	mii = device_get_softc(sc->bce_miibus);
1706 
1707 	val = REG_RD(sc, BCE_EMAC_MODE);
1708 	val &= ~(BCE_EMAC_MODE_PORT | BCE_EMAC_MODE_HALF_DUPLEX |
1709 		BCE_EMAC_MODE_MAC_LOOP | BCE_EMAC_MODE_FORCE_LINK |
1710 		BCE_EMAC_MODE_25G);
1711 
1712 	/* Set MII or GMII interface based on the speed negotiated by the PHY. */
1713 	switch (IFM_SUBTYPE(mii->mii_media_active)) {
1714 	case IFM_10_T:
1715 		if (BCE_CHIP_NUM(sc) != BCE_CHIP_NUM_5706) {
1716 			DBPRINT(sc, BCE_INFO, "Enabling 10Mb interface.\n");
1717 			val |= BCE_EMAC_MODE_PORT_MII_10;
1718 			break;
1719 		}
1720 		/* fall-through */
1721 	case IFM_100_TX:
1722 		DBPRINT(sc, BCE_INFO, "Enabling MII interface.\n");
1723 		val |= BCE_EMAC_MODE_PORT_MII;
1724 		break;
1725 	case IFM_2500_SX:
1726 		DBPRINT(sc, BCE_INFO, "Enabling 2.5G MAC mode.\n");
1727 		val |= BCE_EMAC_MODE_25G;
1728 		/* fall-through */
1729 	case IFM_1000_T:
1730 	case IFM_1000_SX:
1731 		DBPRINT(sc, BCE_INFO, "Enabling GMII interface.\n");
1732 		val |= BCE_EMAC_MODE_PORT_GMII;
1733 		break;
1734 	default:
1735 		DBPRINT(sc, BCE_INFO, "Unknown speed, enabling default GMII "
1736 			"interface.\n");
1737 		val |= BCE_EMAC_MODE_PORT_GMII;
1738 	}
1739 
1740 	/* Set half or full duplex based on the duplicity negotiated by the PHY. */
1741 	if ((mii->mii_media_active & IFM_GMASK) == IFM_HDX) {
1742 		DBPRINT(sc, BCE_INFO, "Setting Half-Duplex interface.\n");
1743 		val |= BCE_EMAC_MODE_HALF_DUPLEX;
1744 	} else
1745 		DBPRINT(sc, BCE_INFO, "Setting Full-Duplex interface.\n");
1746 
1747 	REG_WR(sc, BCE_EMAC_MODE, val);
1748 
1749 #if 0
1750 	/* ToDo: Enable flow control support in brgphy and bge. */
1751 	/* FLAG0 is set if RX is enabled and FLAG1 if TX is enabled */
1752 	if (mii->mii_media_active & IFM_FLAG0)
1753 		BCE_SETBIT(sc, BCE_EMAC_RX_MODE, BCE_EMAC_RX_MODE_FLOW_EN);
1754 	if (mii->mii_media_active & IFM_FLAG1)
1755 		BCE_SETBIT(sc, BCE_EMAC_RX_MODE, BCE_EMAC_TX_MODE_FLOW_EN);
1756 #endif
1757 
1758 	DBEXIT(BCE_VERBOSE_PHY);
1759 }
1760 
1761 
1762 /****************************************************************************/
1763 /* Acquire NVRAM lock.                                                      */
1764 /*                                                                          */
1765 /* Before the NVRAM can be accessed the caller must acquire an NVRAM lock.  */
1766 /* Locks 0 and 2 are reserved, lock 1 is used by firmware and lock 2 is     */
1767 /* for use by the driver.                                                   */
1768 /*                                                                          */
1769 /* Returns:                                                                 */
1770 /*   0 on success, positive value on failure.                               */
1771 /****************************************************************************/
1772 static int
1773 bce_acquire_nvram_lock(struct bce_softc *sc)
1774 {
1775 	u32 val;
1776 	int j, rc = 0;
1777 
1778 	DBENTER(BCE_VERBOSE_NVRAM);
1779 
1780 	/* Request access to the flash interface. */
1781 	REG_WR(sc, BCE_NVM_SW_ARB, BCE_NVM_SW_ARB_ARB_REQ_SET2);
1782 	for (j = 0; j < NVRAM_TIMEOUT_COUNT; j++) {
1783 		val = REG_RD(sc, BCE_NVM_SW_ARB);
1784 		if (val & BCE_NVM_SW_ARB_ARB_ARB2)
1785 			break;
1786 
1787 		DELAY(5);
1788 	}
1789 
1790 	if (j >= NVRAM_TIMEOUT_COUNT) {
1791 		DBPRINT(sc, BCE_WARN, "Timeout acquiring NVRAM lock!\n");
1792 		rc = EBUSY;
1793 	}
1794 
1795 	DBEXIT(BCE_VERBOSE_NVRAM);
1796 	return (rc);
1797 }
1798 
1799 
1800 /****************************************************************************/
1801 /* Release NVRAM lock.                                                      */
1802 /*                                                                          */
1803 /* When the caller is finished accessing NVRAM the lock must be released.   */
1804 /* Locks 0 and 2 are reserved, lock 1 is used by firmware and lock 2 is     */
1805 /* for use by the driver.                                                   */
1806 /*                                                                          */
1807 /* Returns:                                                                 */
1808 /*   0 on success, positive value on failure.                               */
1809 /****************************************************************************/
1810 static int
1811 bce_release_nvram_lock(struct bce_softc *sc)
1812 {
1813 	u32 val;
1814 	int j, rc = 0;
1815 
1816 	DBENTER(BCE_VERBOSE_NVRAM);
1817 
1818 	/*
1819 	 * Relinquish nvram interface.
1820 	 */
1821 	REG_WR(sc, BCE_NVM_SW_ARB, BCE_NVM_SW_ARB_ARB_REQ_CLR2);
1822 
1823 	for (j = 0; j < NVRAM_TIMEOUT_COUNT; j++) {
1824 		val = REG_RD(sc, BCE_NVM_SW_ARB);
1825 		if (!(val & BCE_NVM_SW_ARB_ARB_ARB2))
1826 			break;
1827 
1828 		DELAY(5);
1829 	}
1830 
1831 	if (j >= NVRAM_TIMEOUT_COUNT) {
1832 		DBPRINT(sc, BCE_WARN, "Timeout releasing NVRAM lock!\n");
1833 		rc = EBUSY;
1834 	}
1835 
1836 	DBEXIT(BCE_VERBOSE_NVRAM);
1837 	return (rc);
1838 }
1839 
1840 
1841 #ifdef BCE_NVRAM_WRITE_SUPPORT
1842 /****************************************************************************/
1843 /* Enable NVRAM write access.                                               */
1844 /*                                                                          */
1845 /* Before writing to NVRAM the caller must enable NVRAM writes.             */
1846 /*                                                                          */
1847 /* Returns:                                                                 */
1848 /*   0 on success, positive value on failure.                               */
1849 /****************************************************************************/
1850 static int
1851 bce_enable_nvram_write(struct bce_softc *sc)
1852 {
1853 	u32 val;
1854 	int rc = 0;
1855 
1856 	DBENTER(BCE_VERBOSE_NVRAM);
1857 
1858 	val = REG_RD(sc, BCE_MISC_CFG);
1859 	REG_WR(sc, BCE_MISC_CFG, val | BCE_MISC_CFG_NVM_WR_EN_PCI);
1860 
1861 	if (!(sc->bce_flash_info->flags & BCE_NV_BUFFERED)) {
1862 		int j;
1863 
1864 		REG_WR(sc, BCE_NVM_COMMAND, BCE_NVM_COMMAND_DONE);
1865 		REG_WR(sc, BCE_NVM_COMMAND,	BCE_NVM_COMMAND_WREN | BCE_NVM_COMMAND_DOIT);
1866 
1867 		for (j = 0; j < NVRAM_TIMEOUT_COUNT; j++) {
1868 			DELAY(5);
1869 
1870 			val = REG_RD(sc, BCE_NVM_COMMAND);
1871 			if (val & BCE_NVM_COMMAND_DONE)
1872 				break;
1873 		}
1874 
1875 		if (j >= NVRAM_TIMEOUT_COUNT) {
1876 			DBPRINT(sc, BCE_WARN, "Timeout writing NVRAM!\n");
1877 			rc = EBUSY;
1878 		}
1879 	}
1880 
1881 	DBENTER(BCE_VERBOSE_NVRAM);
1882 	return (rc);
1883 }
1884 
1885 
1886 /****************************************************************************/
1887 /* Disable NVRAM write access.                                              */
1888 /*                                                                          */
1889 /* When the caller is finished writing to NVRAM write access must be        */
1890 /* disabled.                                                                */
1891 /*                                                                          */
1892 /* Returns:                                                                 */
1893 /*   Nothing.                                                               */
1894 /****************************************************************************/
1895 static void
1896 bce_disable_nvram_write(struct bce_softc *sc)
1897 {
1898 	u32 val;
1899 
1900 	DBENTER(BCE_VERBOSE_NVRAM);
1901 
1902 	val = REG_RD(sc, BCE_MISC_CFG);
1903 	REG_WR(sc, BCE_MISC_CFG, val & ~BCE_MISC_CFG_NVM_WR_EN);
1904 
1905 	DBEXIT(BCE_VERBOSE_NVRAM);
1906 
1907 }
1908 #endif
1909 
1910 
1911 /****************************************************************************/
1912 /* Enable NVRAM access.                                                     */
1913 /*                                                                          */
1914 /* Before accessing NVRAM for read or write operations the caller must      */
1915 /* enabled NVRAM access.                                                    */
1916 /*                                                                          */
1917 /* Returns:                                                                 */
1918 /*   Nothing.                                                               */
1919 /****************************************************************************/
1920 static void
1921 bce_enable_nvram_access(struct bce_softc *sc)
1922 {
1923 	u32 val;
1924 
1925 	DBENTER(BCE_VERBOSE_NVRAM);
1926 
1927 	val = REG_RD(sc, BCE_NVM_ACCESS_ENABLE);
1928 	/* Enable both bits, even on read. */
1929 	REG_WR(sc, BCE_NVM_ACCESS_ENABLE,
1930 	       val | BCE_NVM_ACCESS_ENABLE_EN | BCE_NVM_ACCESS_ENABLE_WR_EN);
1931 
1932 	DBEXIT(BCE_VERBOSE_NVRAM);
1933 }
1934 
1935 
1936 /****************************************************************************/
1937 /* Disable NVRAM access.                                                    */
1938 /*                                                                          */
1939 /* When the caller is finished accessing NVRAM access must be disabled.     */
1940 /*                                                                          */
1941 /* Returns:                                                                 */
1942 /*   Nothing.                                                               */
1943 /****************************************************************************/
1944 static void
1945 bce_disable_nvram_access(struct bce_softc *sc)
1946 {
1947 	u32 val;
1948 
1949 	DBENTER(BCE_VERBOSE_NVRAM);
1950 
1951 	val = REG_RD(sc, BCE_NVM_ACCESS_ENABLE);
1952 
1953 	/* Disable both bits, even after read. */
1954 	REG_WR(sc, BCE_NVM_ACCESS_ENABLE,
1955 		val & ~(BCE_NVM_ACCESS_ENABLE_EN |
1956 			BCE_NVM_ACCESS_ENABLE_WR_EN));
1957 
1958 	DBEXIT(BCE_VERBOSE_NVRAM);
1959 }
1960 
1961 
1962 #ifdef BCE_NVRAM_WRITE_SUPPORT
1963 /****************************************************************************/
1964 /* Erase NVRAM page before writing.                                         */
1965 /*                                                                          */
1966 /* Non-buffered flash parts require that a page be erased before it is      */
1967 /* written.                                                                 */
1968 /*                                                                          */
1969 /* Returns:                                                                 */
1970 /*   0 on success, positive value on failure.                               */
1971 /****************************************************************************/
1972 static int
1973 bce_nvram_erase_page(struct bce_softc *sc, u32 offset)
1974 {
1975 	u32 cmd;
1976 	int j, rc = 0;
1977 
1978 	DBENTER(BCE_VERBOSE_NVRAM);
1979 
1980 	/* Buffered flash doesn't require an erase. */
1981 	if (sc->bce_flash_info->flags & BCE_NV_BUFFERED)
1982 		goto bce_nvram_erase_page_exit;
1983 
1984 	/* Build an erase command. */
1985 	cmd = BCE_NVM_COMMAND_ERASE | BCE_NVM_COMMAND_WR |
1986 	      BCE_NVM_COMMAND_DOIT;
1987 
1988 	/*
1989 	 * Clear the DONE bit separately, set the NVRAM adress to erase,
1990 	 * and issue the erase command.
1991 	 */
1992 	REG_WR(sc, BCE_NVM_COMMAND, BCE_NVM_COMMAND_DONE);
1993 	REG_WR(sc, BCE_NVM_ADDR, offset & BCE_NVM_ADDR_NVM_ADDR_VALUE);
1994 	REG_WR(sc, BCE_NVM_COMMAND, cmd);
1995 
1996 	/* Wait for completion. */
1997 	for (j = 0; j < NVRAM_TIMEOUT_COUNT; j++) {
1998 		u32 val;
1999 
2000 		DELAY(5);
2001 
2002 		val = REG_RD(sc, BCE_NVM_COMMAND);
2003 		if (val & BCE_NVM_COMMAND_DONE)
2004 			break;
2005 	}
2006 
2007 	if (j >= NVRAM_TIMEOUT_COUNT) {
2008 		DBPRINT(sc, BCE_WARN, "Timeout erasing NVRAM.\n");
2009 		rc = EBUSY;
2010 	}
2011 
2012 bce_nvram_erase_page_exit:
2013 	DBEXIT(BCE_VERBOSE_NVRAM);
2014 	return (rc);
2015 }
2016 #endif /* BCE_NVRAM_WRITE_SUPPORT */
2017 
2018 
2019 /****************************************************************************/
2020 /* Read a dword (32 bits) from NVRAM.                                       */
2021 /*                                                                          */
2022 /* Read a 32 bit word from NVRAM.  The caller is assumed to have already    */
2023 /* obtained the NVRAM lock and enabled the controller for NVRAM access.     */
2024 /*                                                                          */
2025 /* Returns:                                                                 */
2026 /*   0 on success and the 32 bit value read, positive value on failure.     */
2027 /****************************************************************************/
2028 static int
2029 bce_nvram_read_dword(struct bce_softc *sc, u32 offset, u8 *ret_val,
2030 							u32 cmd_flags)
2031 {
2032 	u32 cmd;
2033 	int i, rc = 0;
2034 
2035 	DBENTER(BCE_EXTREME_NVRAM);
2036 
2037 	/* Build the command word. */
2038 	cmd = BCE_NVM_COMMAND_DOIT | cmd_flags;
2039 
2040 	/* Calculate the offset for buffered flash if translation is used. */
2041 	if (sc->bce_flash_info->flags & BCE_NV_TRANSLATE) {
2042 		offset = ((offset / sc->bce_flash_info->page_size) <<
2043 			   sc->bce_flash_info->page_bits) +
2044 			  (offset % sc->bce_flash_info->page_size);
2045 	}
2046 
2047 	/*
2048 	 * Clear the DONE bit separately, set the address to read,
2049 	 * and issue the read.
2050 	 */
2051 	REG_WR(sc, BCE_NVM_COMMAND, BCE_NVM_COMMAND_DONE);
2052 	REG_WR(sc, BCE_NVM_ADDR, offset & BCE_NVM_ADDR_NVM_ADDR_VALUE);
2053 	REG_WR(sc, BCE_NVM_COMMAND, cmd);
2054 
2055 	/* Wait for completion. */
2056 	for (i = 0; i < NVRAM_TIMEOUT_COUNT; i++) {
2057 		u32 val;
2058 
2059 		DELAY(5);
2060 
2061 		val = REG_RD(sc, BCE_NVM_COMMAND);
2062 		if (val & BCE_NVM_COMMAND_DONE) {
2063 			val = REG_RD(sc, BCE_NVM_READ);
2064 
2065 			val = bce_be32toh(val);
2066 			memcpy(ret_val, &val, 4);
2067 			break;
2068 		}
2069 	}
2070 
2071 	/* Check for errors. */
2072 	if (i >= NVRAM_TIMEOUT_COUNT) {
2073 		BCE_PRINTF("%s(%d): Timeout error reading NVRAM at offset 0x%08X!\n",
2074 			__FILE__, __LINE__, offset);
2075 		rc = EBUSY;
2076 	}
2077 
2078 	DBEXIT(BCE_EXTREME_NVRAM);
2079 	return(rc);
2080 }
2081 
2082 
2083 #ifdef BCE_NVRAM_WRITE_SUPPORT
2084 /****************************************************************************/
2085 /* Write a dword (32 bits) to NVRAM.                                        */
2086 /*                                                                          */
2087 /* Write a 32 bit word to NVRAM.  The caller is assumed to have already     */
2088 /* obtained the NVRAM lock, enabled the controller for NVRAM access, and    */
2089 /* enabled NVRAM write access.                                              */
2090 /*                                                                          */
2091 /* Returns:                                                                 */
2092 /*   0 on success, positive value on failure.                               */
2093 /****************************************************************************/
2094 static int
2095 bce_nvram_write_dword(struct bce_softc *sc, u32 offset, u8 *val,
2096 	u32 cmd_flags)
2097 {
2098 	u32 cmd, val32;
2099 	int j, rc = 0;
2100 
2101 	DBENTER(BCE_VERBOSE_NVRAM);
2102 
2103 	/* Build the command word. */
2104 	cmd = BCE_NVM_COMMAND_DOIT | BCE_NVM_COMMAND_WR | cmd_flags;
2105 
2106 	/* Calculate the offset for buffered flash if translation is used. */
2107 	if (sc->bce_flash_info->flags & BCE_NV_TRANSLATE) {
2108 		offset = ((offset / sc->bce_flash_info->page_size) <<
2109 			  sc->bce_flash_info->page_bits) +
2110 			 (offset % sc->bce_flash_info->page_size);
2111 	}
2112 
2113 	/*
2114 	 * Clear the DONE bit separately, convert NVRAM data to big-endian,
2115 	 * set the NVRAM address to write, and issue the write command
2116 	 */
2117 	REG_WR(sc, BCE_NVM_COMMAND, BCE_NVM_COMMAND_DONE);
2118 	memcpy(&val32, val, 4);
2119 	val32 = htobe32(val32);
2120 	REG_WR(sc, BCE_NVM_WRITE, val32);
2121 	REG_WR(sc, BCE_NVM_ADDR, offset & BCE_NVM_ADDR_NVM_ADDR_VALUE);
2122 	REG_WR(sc, BCE_NVM_COMMAND, cmd);
2123 
2124 	/* Wait for completion. */
2125 	for (j = 0; j < NVRAM_TIMEOUT_COUNT; j++) {
2126 		DELAY(5);
2127 
2128 		if (REG_RD(sc, BCE_NVM_COMMAND) & BCE_NVM_COMMAND_DONE)
2129 			break;
2130 	}
2131 	if (j >= NVRAM_TIMEOUT_COUNT) {
2132 		BCE_PRINTF("%s(%d): Timeout error writing NVRAM at offset 0x%08X\n",
2133 			__FILE__, __LINE__, offset);
2134 		rc = EBUSY;
2135 	}
2136 
2137 	DBEXIT(BCE_VERBOSE_NVRAM);
2138 	return (rc);
2139 }
2140 #endif /* BCE_NVRAM_WRITE_SUPPORT */
2141 
2142 
2143 /****************************************************************************/
2144 /* Initialize NVRAM access.                                                 */
2145 /*                                                                          */
2146 /* Identify the NVRAM device in use and prepare the NVRAM interface to      */
2147 /* access that device.                                                      */
2148 /*                                                                          */
2149 /* Returns:                                                                 */
2150 /*   0 on success, positive value on failure.                               */
2151 /****************************************************************************/
2152 static int
2153 bce_init_nvram(struct bce_softc *sc)
2154 {
2155 	u32 val;
2156 	int j, entry_count, rc = 0;
2157 	struct flash_spec *flash;
2158 
2159 	DBENTER(BCE_VERBOSE_NVRAM);
2160 
2161 	if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
2162 		(BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
2163 		sc->bce_flash_info = &flash_5709;
2164 		goto bce_init_nvram_get_flash_size;
2165 	}
2166 
2167 	/* Determine the selected interface. */
2168 	val = REG_RD(sc, BCE_NVM_CFG1);
2169 
2170 	entry_count = sizeof(flash_table) / sizeof(struct flash_spec);
2171 
2172 	/*
2173 	 * Flash reconfiguration is required to support additional
2174 	 * NVRAM devices not directly supported in hardware.
2175 	 * Check if the flash interface was reconfigured
2176 	 * by the bootcode.
2177 	 */
2178 
2179 	if (val & 0x40000000) {
2180 		/* Flash interface reconfigured by bootcode. */
2181 
2182 		DBPRINT(sc,BCE_INFO_LOAD,
2183 			"bce_init_nvram(): Flash WAS reconfigured.\n");
2184 
2185 		for (j = 0, flash = &flash_table[0]; j < entry_count;
2186 		     j++, flash++) {
2187 			if ((val & FLASH_BACKUP_STRAP_MASK) ==
2188 			    (flash->config1 & FLASH_BACKUP_STRAP_MASK)) {
2189 				sc->bce_flash_info = flash;
2190 				break;
2191 			}
2192 		}
2193 	} else {
2194 		/* Flash interface not yet reconfigured. */
2195 		u32 mask;
2196 
2197 		DBPRINT(sc, BCE_INFO_LOAD, "%s(): Flash was NOT reconfigured.\n",
2198 			__FUNCTION__);
2199 
2200 		if (val & (1 << 23))
2201 			mask = FLASH_BACKUP_STRAP_MASK;
2202 		else
2203 			mask = FLASH_STRAP_MASK;
2204 
2205 		/* Look for the matching NVRAM device configuration data. */
2206 		for (j = 0, flash = &flash_table[0]; j < entry_count; j++, flash++) {
2207 
2208 			/* Check if the device matches any of the known devices. */
2209 			if ((val & mask) == (flash->strapping & mask)) {
2210 				/* Found a device match. */
2211 				sc->bce_flash_info = flash;
2212 
2213 				/* Request access to the flash interface. */
2214 				if ((rc = bce_acquire_nvram_lock(sc)) != 0)
2215 					return rc;
2216 
2217 				/* Reconfigure the flash interface. */
2218 				bce_enable_nvram_access(sc);
2219 				REG_WR(sc, BCE_NVM_CFG1, flash->config1);
2220 				REG_WR(sc, BCE_NVM_CFG2, flash->config2);
2221 				REG_WR(sc, BCE_NVM_CFG3, flash->config3);
2222 				REG_WR(sc, BCE_NVM_WRITE1, flash->write1);
2223 				bce_disable_nvram_access(sc);
2224 				bce_release_nvram_lock(sc);
2225 
2226 				break;
2227 			}
2228 		}
2229 	}
2230 
2231 	/* Check if a matching device was found. */
2232 	if (j == entry_count) {
2233 		sc->bce_flash_info = NULL;
2234 		BCE_PRINTF("%s(%d): Unknown Flash NVRAM found!\n",
2235 			__FILE__, __LINE__);
2236 		rc = ENODEV;
2237 	}
2238 
2239 bce_init_nvram_get_flash_size:
2240 	/* Write the flash config data to the shared memory interface. */
2241 	val = bce_shmem_rd(sc, BCE_SHARED_HW_CFG_CONFIG2);
2242 	val &= BCE_SHARED_HW_CFG2_NVM_SIZE_MASK;
2243 	if (val)
2244 		sc->bce_flash_size = val;
2245 	else
2246 		sc->bce_flash_size = sc->bce_flash_info->total_size;
2247 
2248 	DBPRINT(sc, BCE_INFO_LOAD, "%s(): Found %s, size = 0x%08X\n",
2249 		__FUNCTION__, sc->bce_flash_info->name,
2250 		sc->bce_flash_info->total_size);
2251 
2252 	DBEXIT(BCE_VERBOSE_NVRAM);
2253 	return rc;
2254 }
2255 
2256 
2257 /****************************************************************************/
2258 /* Read an arbitrary range of data from NVRAM.                              */
2259 /*                                                                          */
2260 /* Prepares the NVRAM interface for access and reads the requested data     */
2261 /* into the supplied buffer.                                                */
2262 /*                                                                          */
2263 /* Returns:                                                                 */
2264 /*   0 on success and the data read, positive value on failure.             */
2265 /****************************************************************************/
2266 static int
2267 bce_nvram_read(struct bce_softc *sc, u32 offset, u8 *ret_buf,
2268 	int buf_size)
2269 {
2270 	int rc = 0;
2271 	u32 cmd_flags, offset32, len32, extra;
2272 
2273 	DBENTER(BCE_VERBOSE_NVRAM);
2274 
2275 	if (buf_size == 0)
2276 		goto bce_nvram_read_exit;
2277 
2278 	/* Request access to the flash interface. */
2279 	if ((rc = bce_acquire_nvram_lock(sc)) != 0)
2280 		goto bce_nvram_read_exit;
2281 
2282 	/* Enable access to flash interface */
2283 	bce_enable_nvram_access(sc);
2284 
2285 	len32 = buf_size;
2286 	offset32 = offset;
2287 	extra = 0;
2288 
2289 	cmd_flags = 0;
2290 
2291 	if (offset32 & 3) {
2292 		u8 buf[4];
2293 		u32 pre_len;
2294 
2295 		offset32 &= ~3;
2296 		pre_len = 4 - (offset & 3);
2297 
2298 		if (pre_len >= len32) {
2299 			pre_len = len32;
2300 			cmd_flags = BCE_NVM_COMMAND_FIRST | BCE_NVM_COMMAND_LAST;
2301 		}
2302 		else {
2303 			cmd_flags = BCE_NVM_COMMAND_FIRST;
2304 		}
2305 
2306 		rc = bce_nvram_read_dword(sc, offset32, buf, cmd_flags);
2307 
2308 		if (rc)
2309 			return rc;
2310 
2311 		memcpy(ret_buf, buf + (offset & 3), pre_len);
2312 
2313 		offset32 += 4;
2314 		ret_buf += pre_len;
2315 		len32 -= pre_len;
2316 	}
2317 
2318 	if (len32 & 3) {
2319 		extra = 4 - (len32 & 3);
2320 		len32 = (len32 + 4) & ~3;
2321 	}
2322 
2323 	if (len32 == 4) {
2324 		u8 buf[4];
2325 
2326 		if (cmd_flags)
2327 			cmd_flags = BCE_NVM_COMMAND_LAST;
2328 		else
2329 			cmd_flags = BCE_NVM_COMMAND_FIRST |
2330 				    BCE_NVM_COMMAND_LAST;
2331 
2332 		rc = bce_nvram_read_dword(sc, offset32, buf, cmd_flags);
2333 
2334 		memcpy(ret_buf, buf, 4 - extra);
2335 	}
2336 	else if (len32 > 0) {
2337 		u8 buf[4];
2338 
2339 		/* Read the first word. */
2340 		if (cmd_flags)
2341 			cmd_flags = 0;
2342 		else
2343 			cmd_flags = BCE_NVM_COMMAND_FIRST;
2344 
2345 		rc = bce_nvram_read_dword(sc, offset32, ret_buf, cmd_flags);
2346 
2347 		/* Advance to the next dword. */
2348 		offset32 += 4;
2349 		ret_buf += 4;
2350 		len32 -= 4;
2351 
2352 		while (len32 > 4 && rc == 0) {
2353 			rc = bce_nvram_read_dword(sc, offset32, ret_buf, 0);
2354 
2355 			/* Advance to the next dword. */
2356 			offset32 += 4;
2357 			ret_buf += 4;
2358 			len32 -= 4;
2359 		}
2360 
2361 		if (rc)
2362 			goto bce_nvram_read_locked_exit;
2363 
2364 		cmd_flags = BCE_NVM_COMMAND_LAST;
2365 		rc = bce_nvram_read_dword(sc, offset32, buf, cmd_flags);
2366 
2367 		memcpy(ret_buf, buf, 4 - extra);
2368 	}
2369 
2370 bce_nvram_read_locked_exit:
2371 	/* Disable access to flash interface and release the lock. */
2372 	bce_disable_nvram_access(sc);
2373 	bce_release_nvram_lock(sc);
2374 
2375 bce_nvram_read_exit:
2376 	DBEXIT(BCE_VERBOSE_NVRAM);
2377 	return rc;
2378 }
2379 
2380 
2381 #ifdef BCE_NVRAM_WRITE_SUPPORT
2382 /****************************************************************************/
2383 /* Write an arbitrary range of data from NVRAM.                             */
2384 /*                                                                          */
2385 /* Prepares the NVRAM interface for write access and writes the requested   */
2386 /* data from the supplied buffer.  The caller is responsible for            */
2387 /* calculating any appropriate CRCs.                                        */
2388 /*                                                                          */
2389 /* Returns:                                                                 */
2390 /*   0 on success, positive value on failure.                               */
2391 /****************************************************************************/
2392 static int
2393 bce_nvram_write(struct bce_softc *sc, u32 offset, u8 *data_buf,
2394 	int buf_size)
2395 {
2396 	u32 written, offset32, len32;
2397 	u8 *buf, start[4], end[4];
2398 	int rc = 0;
2399 	int align_start, align_end;
2400 
2401 	DBENTER(BCE_VERBOSE_NVRAM);
2402 
2403 	buf = data_buf;
2404 	offset32 = offset;
2405 	len32 = buf_size;
2406 	align_start = align_end = 0;
2407 
2408 	if ((align_start = (offset32 & 3))) {
2409 		offset32 &= ~3;
2410 		len32 += align_start;
2411 		if ((rc = bce_nvram_read(sc, offset32, start, 4)))
2412 			goto bce_nvram_write_exit;
2413 	}
2414 
2415 	if (len32 & 3) {
2416 	       	if ((len32 > 4) || !align_start) {
2417 			align_end = 4 - (len32 & 3);
2418 			len32 += align_end;
2419 			if ((rc = bce_nvram_read(sc, offset32 + len32 - 4,
2420 				end, 4))) {
2421 				goto bce_nvram_write_exit;
2422 			}
2423 		}
2424 	}
2425 
2426 	if (align_start || align_end) {
2427 		buf = malloc(len32, M_DEVBUF, M_NOWAIT);
2428 		if (buf == 0) {
2429 			rc = ENOMEM;
2430 			goto bce_nvram_write_exit;
2431 		}
2432 
2433 		if (align_start) {
2434 			memcpy(buf, start, 4);
2435 		}
2436 
2437 		if (align_end) {
2438 			memcpy(buf + len32 - 4, end, 4);
2439 		}
2440 		memcpy(buf + align_start, data_buf, buf_size);
2441 	}
2442 
2443 	written = 0;
2444 	while ((written < len32) && (rc == 0)) {
2445 		u32 page_start, page_end, data_start, data_end;
2446 		u32 addr, cmd_flags;
2447 		int i;
2448 		u8 flash_buffer[264];
2449 
2450 	    /* Find the page_start addr */
2451 		page_start = offset32 + written;
2452 		page_start -= (page_start % sc->bce_flash_info->page_size);
2453 		/* Find the page_end addr */
2454 		page_end = page_start + sc->bce_flash_info->page_size;
2455 		/* Find the data_start addr */
2456 		data_start = (written == 0) ? offset32 : page_start;
2457 		/* Find the data_end addr */
2458 		data_end = (page_end > offset32 + len32) ?
2459 			(offset32 + len32) : page_end;
2460 
2461 		/* Request access to the flash interface. */
2462 		if ((rc = bce_acquire_nvram_lock(sc)) != 0)
2463 			goto bce_nvram_write_exit;
2464 
2465 		/* Enable access to flash interface */
2466 		bce_enable_nvram_access(sc);
2467 
2468 		cmd_flags = BCE_NVM_COMMAND_FIRST;
2469 		if (!(sc->bce_flash_info->flags & BCE_NV_BUFFERED)) {
2470 			int j;
2471 
2472 			/* Read the whole page into the buffer
2473 			 * (non-buffer flash only) */
2474 			for (j = 0; j < sc->bce_flash_info->page_size; j += 4) {
2475 				if (j == (sc->bce_flash_info->page_size - 4)) {
2476 					cmd_flags |= BCE_NVM_COMMAND_LAST;
2477 				}
2478 				rc = bce_nvram_read_dword(sc,
2479 					page_start + j,
2480 					&flash_buffer[j],
2481 					cmd_flags);
2482 
2483 				if (rc)
2484 					goto bce_nvram_write_locked_exit;
2485 
2486 				cmd_flags = 0;
2487 			}
2488 		}
2489 
2490 		/* Enable writes to flash interface (unlock write-protect) */
2491 		if ((rc = bce_enable_nvram_write(sc)) != 0)
2492 			goto bce_nvram_write_locked_exit;
2493 
2494 		/* Erase the page */
2495 		if ((rc = bce_nvram_erase_page(sc, page_start)) != 0)
2496 			goto bce_nvram_write_locked_exit;
2497 
2498 		/* Re-enable the write again for the actual write */
2499 		bce_enable_nvram_write(sc);
2500 
2501 		/* Loop to write back the buffer data from page_start to
2502 		 * data_start */
2503 		i = 0;
2504 		if (!(sc->bce_flash_info->flags & BCE_NV_BUFFERED)) {
2505 			for (addr = page_start; addr < data_start;
2506 				addr += 4, i += 4) {
2507 
2508 				rc = bce_nvram_write_dword(sc, addr,
2509 					&flash_buffer[i], cmd_flags);
2510 
2511 				if (rc != 0)
2512 					goto bce_nvram_write_locked_exit;
2513 
2514 				cmd_flags = 0;
2515 			}
2516 		}
2517 
2518 		/* Loop to write the new data from data_start to data_end */
2519 		for (addr = data_start; addr < data_end; addr += 4, i++) {
2520 			if ((addr == page_end - 4) ||
2521 				((sc->bce_flash_info->flags & BCE_NV_BUFFERED) &&
2522 				(addr == data_end - 4))) {
2523 
2524 				cmd_flags |= BCE_NVM_COMMAND_LAST;
2525 			}
2526 			rc = bce_nvram_write_dword(sc, addr, buf,
2527 				cmd_flags);
2528 
2529 			if (rc != 0)
2530 				goto bce_nvram_write_locked_exit;
2531 
2532 			cmd_flags = 0;
2533 			buf += 4;
2534 		}
2535 
2536 		/* Loop to write back the buffer data from data_end
2537 		 * to page_end */
2538 		if (!(sc->bce_flash_info->flags & BCE_NV_BUFFERED)) {
2539 			for (addr = data_end; addr < page_end;
2540 				addr += 4, i += 4) {
2541 
2542 				if (addr == page_end-4) {
2543 					cmd_flags = BCE_NVM_COMMAND_LAST;
2544                 		}
2545 				rc = bce_nvram_write_dword(sc, addr,
2546 					&flash_buffer[i], cmd_flags);
2547 
2548 				if (rc != 0)
2549 					goto bce_nvram_write_locked_exit;
2550 
2551 				cmd_flags = 0;
2552 			}
2553 		}
2554 
2555 		/* Disable writes to flash interface (lock write-protect) */
2556 		bce_disable_nvram_write(sc);
2557 
2558 		/* Disable access to flash interface */
2559 		bce_disable_nvram_access(sc);
2560 		bce_release_nvram_lock(sc);
2561 
2562 		/* Increment written */
2563 		written += data_end - data_start;
2564 	}
2565 
2566 	goto bce_nvram_write_exit;
2567 
2568 bce_nvram_write_locked_exit:
2569 		bce_disable_nvram_write(sc);
2570 		bce_disable_nvram_access(sc);
2571 		bce_release_nvram_lock(sc);
2572 
2573 bce_nvram_write_exit:
2574 	if (align_start || align_end)
2575 		free(buf, M_DEVBUF);
2576 
2577 	DBEXIT(BCE_VERBOSE_NVRAM);
2578 	return (rc);
2579 }
2580 #endif /* BCE_NVRAM_WRITE_SUPPORT */
2581 
2582 
2583 /****************************************************************************/
2584 /* Verifies that NVRAM is accessible and contains valid data.               */
2585 /*                                                                          */
2586 /* Reads the configuration data from NVRAM and verifies that the CRC is     */
2587 /* correct.                                                                 */
2588 /*                                                                          */
2589 /* Returns:                                                                 */
2590 /*   0 on success, positive value on failure.                               */
2591 /****************************************************************************/
2592 static int
2593 bce_nvram_test(struct bce_softc *sc)
2594 {
2595 	u32 buf[BCE_NVRAM_SIZE / 4];
2596 	u8 *data = (u8 *) buf;
2597 	int rc = 0;
2598 	u32 magic, csum;
2599 
2600 	DBENTER(BCE_VERBOSE_NVRAM | BCE_VERBOSE_LOAD | BCE_VERBOSE_RESET);
2601 
2602 	/*
2603 	 * Check that the device NVRAM is valid by reading
2604 	 * the magic value at offset 0.
2605 	 */
2606 	if ((rc = bce_nvram_read(sc, 0, data, 4)) != 0) {
2607 		BCE_PRINTF("%s(%d): Unable to read NVRAM!\n", __FILE__, __LINE__);
2608 		goto bce_nvram_test_exit;
2609 	}
2610 
2611 	/*
2612 	 * Verify that offset 0 of the NVRAM contains
2613 	 * a valid magic number.
2614 	 */
2615     magic = bce_be32toh(buf[0]);
2616 	if (magic != BCE_NVRAM_MAGIC) {
2617 		rc = ENODEV;
2618 		BCE_PRINTF("%s(%d): Invalid NVRAM magic value! Expected: 0x%08X, "
2619 			"Found: 0x%08X\n",
2620 			__FILE__, __LINE__, BCE_NVRAM_MAGIC, magic);
2621 		goto bce_nvram_test_exit;
2622 	}
2623 
2624 	/*
2625 	 * Verify that the device NVRAM includes valid
2626 	 * configuration data.
2627 	 */
2628 	if ((rc = bce_nvram_read(sc, 0x100, data, BCE_NVRAM_SIZE)) != 0) {
2629 		BCE_PRINTF("%s(%d): Unable to read Manufacturing Information from "
2630 			"NVRAM!\n", __FILE__, __LINE__);
2631 		goto bce_nvram_test_exit;
2632 	}
2633 
2634 	csum = ether_crc32_le(data, 0x100);
2635 	if (csum != BCE_CRC32_RESIDUAL) {
2636 		rc = ENODEV;
2637 		BCE_PRINTF("%s(%d): Invalid Manufacturing Information NVRAM CRC! "
2638 			"Expected: 0x%08X, Found: 0x%08X\n",
2639 			__FILE__, __LINE__, BCE_CRC32_RESIDUAL, csum);
2640 		goto bce_nvram_test_exit;
2641 	}
2642 
2643 	csum = ether_crc32_le(data + 0x100, 0x100);
2644 	if (csum != BCE_CRC32_RESIDUAL) {
2645 		rc = ENODEV;
2646 		BCE_PRINTF("%s(%d): Invalid Feature Configuration Information "
2647 			"NVRAM CRC! Expected: 0x%08X, Found: 08%08X\n",
2648 			__FILE__, __LINE__, BCE_CRC32_RESIDUAL, csum);
2649 	}
2650 
2651 bce_nvram_test_exit:
2652 	DBEXIT(BCE_VERBOSE_NVRAM | BCE_VERBOSE_LOAD | BCE_VERBOSE_RESET);
2653 	return rc;
2654 }
2655 
2656 
2657 /****************************************************************************/
2658 /* Identifies the current media type of the controller and sets the PHY     */
2659 /* address.                                                                 */
2660 /*                                                                          */
2661 /* Returns:                                                                 */
2662 /*   Nothing.                                                               */
2663 /****************************************************************************/
2664 static void
2665 bce_get_media(struct bce_softc *sc)
2666 {
2667 	u32 val;
2668 
2669 	DBENTER(BCE_VERBOSE);
2670 
2671 	/* Assume PHY address for copper controllers. */
2672 	sc->bce_phy_addr = 1;
2673 
2674 	if (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) {
2675  		u32 val = REG_RD(sc, BCE_MISC_DUAL_MEDIA_CTRL);
2676 		u32 bond_id = val & BCE_MISC_DUAL_MEDIA_CTRL_BOND_ID;
2677 		u32 strap;
2678 
2679 		/*
2680 		 * The BCM5709S is software configurable
2681 		 * for Copper or SerDes operation.
2682 		 */
2683 		if (bond_id == BCE_MISC_DUAL_MEDIA_CTRL_BOND_ID_C) {
2684 			DBPRINT(sc, BCE_INFO_LOAD, "5709 bonded "
2685 			    "for copper.\n");
2686 			goto bce_get_media_exit;
2687 		} else if (bond_id == BCE_MISC_DUAL_MEDIA_CTRL_BOND_ID_S) {
2688 			DBPRINT(sc, BCE_INFO_LOAD, "5709 bonded "
2689 			    "for dual media.\n");
2690 			sc->bce_phy_flags |= BCE_PHY_SERDES_FLAG;
2691 			goto bce_get_media_exit;
2692 		}
2693 
2694 		if (val & BCE_MISC_DUAL_MEDIA_CTRL_STRAP_OVERRIDE)
2695 			strap = (val &
2696 			    BCE_MISC_DUAL_MEDIA_CTRL_PHY_CTRL) >> 21;
2697 		else
2698 			strap = (val &
2699 			    BCE_MISC_DUAL_MEDIA_CTRL_PHY_CTRL_STRAP) >> 8;
2700 
2701 		if (pci_get_function(sc->bce_dev) == 0) {
2702 			switch (strap) {
2703 			case 0x4:
2704 			case 0x5:
2705 			case 0x6:
2706 				DBPRINT(sc, BCE_INFO_LOAD,
2707 				    "BCM5709 s/w configured for SerDes.\n");
2708 				sc->bce_phy_flags |= BCE_PHY_SERDES_FLAG;
2709 				break;
2710 			default:
2711 				DBPRINT(sc, BCE_INFO_LOAD,
2712 				    "BCM5709 s/w configured for Copper.\n");
2713 				break;
2714 			}
2715 		} else {
2716 			switch (strap) {
2717 			case 0x1:
2718 			case 0x2:
2719 			case 0x4:
2720 				DBPRINT(sc, BCE_INFO_LOAD,
2721 				    "BCM5709 s/w configured for SerDes.\n");
2722 				sc->bce_phy_flags |= BCE_PHY_SERDES_FLAG;
2723 				break;
2724 			default:
2725 				DBPRINT(sc, BCE_INFO_LOAD,
2726 				    "BCM5709 s/w configured for Copper.\n");
2727 				break;
2728 			}
2729 		}
2730 
2731 	} else if (BCE_CHIP_BOND_ID(sc) & BCE_CHIP_BOND_ID_SERDES_BIT)
2732 		sc->bce_phy_flags |= BCE_PHY_SERDES_FLAG;
2733 
2734 	if (sc->bce_phy_flags & BCE_PHY_SERDES_FLAG) {
2735 
2736 		sc->bce_flags |= BCE_NO_WOL_FLAG;
2737 
2738 		if (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709)
2739 			sc->bce_phy_flags |= BCE_PHY_IEEE_CLAUSE_45_FLAG;
2740 
2741 		if (BCE_CHIP_NUM(sc) != BCE_CHIP_NUM_5706) {
2742 			/* 5708S/09S/16S use a separate PHY for SerDes. */
2743 			sc->bce_phy_addr = 2;
2744 
2745 			val = bce_shmem_rd(sc, BCE_SHARED_HW_CFG_CONFIG);
2746 			if (val & BCE_SHARED_HW_CFG_PHY_2_5G) {
2747 				sc->bce_phy_flags |=
2748 				    BCE_PHY_2_5G_CAPABLE_FLAG;
2749 				DBPRINT(sc, BCE_INFO_LOAD, "Found 2.5Gb "
2750 				    "capable adapter\n");
2751 			}
2752 		}
2753 	} else if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5706) ||
2754 	    (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5708))
2755 		sc->bce_phy_flags |= BCE_PHY_CRC_FIX_FLAG;
2756 
2757 bce_get_media_exit:
2758 	DBPRINT(sc, (BCE_INFO_LOAD | BCE_INFO_PHY),
2759 		"Using PHY address %d.\n", sc->bce_phy_addr);
2760 
2761 	DBEXIT(BCE_VERBOSE);
2762 }
2763 
2764 
2765 /****************************************************************************/
2766 /* Performs PHY initialization required before MII drivers access the       */
2767 /* device.                                                                  */
2768 /*                                                                          */
2769 /* Returns:                                                                 */
2770 /*   Nothing.                                                               */
2771 /****************************************************************************/
2772 static void
2773 bce_init_media(struct bce_softc *sc)
2774 {
2775 	if ((sc->bce_phy_flags & BCE_PHY_IEEE_CLAUSE_45_FLAG) != 0) {
2776 		/*
2777 		 * Configure 5709S/5716S PHYs to use traditional IEEE
2778 		 * Clause 22 method. Otherwise we have no way to attach
2779 		 * the PHY in mii(4) layer. PHY specific configuration
2780 		 * is done in mii layer.
2781 		 */
2782 
2783 		/* Select auto-negotiation MMD of the PHY. */
2784 		bce_miibus_write_reg(sc->bce_dev, sc->bce_phy_addr,
2785 		    BRGPHY_BLOCK_ADDR, BRGPHY_BLOCK_ADDR_ADDR_EXT);
2786 		bce_miibus_write_reg(sc->bce_dev, sc->bce_phy_addr,
2787 		    BRGPHY_ADDR_EXT, BRGPHY_ADDR_EXT_AN_MMD);
2788 
2789 		/* Set IEEE0 block of AN MMD (assumed in brgphy(4) code). */
2790 		bce_miibus_write_reg(sc->bce_dev, sc->bce_phy_addr,
2791 		    BRGPHY_BLOCK_ADDR, BRGPHY_BLOCK_ADDR_COMBO_IEEE0);
2792 	}
2793 }
2794 
2795 
2796 /****************************************************************************/
2797 /* Free any DMA memory owned by the driver.                                 */
2798 /*                                                                          */
2799 /* Scans through each data structre that requires DMA memory and frees      */
2800 /* the memory if allocated.                                                 */
2801 /*                                                                          */
2802 /* Returns:                                                                 */
2803 /*   Nothing.                                                               */
2804 /****************************************************************************/
2805 static void
2806 bce_dma_free(struct bce_softc *sc)
2807 {
2808 	int i;
2809 
2810 	DBENTER(BCE_VERBOSE_RESET | BCE_VERBOSE_UNLOAD | BCE_VERBOSE_CTX);
2811 
2812 	/* Free, unmap, and destroy the status block. */
2813 	if (sc->status_block != NULL) {
2814 		bus_dmamem_free(
2815 		   sc->status_tag,
2816 		    sc->status_block,
2817 		    sc->status_map);
2818 		sc->status_block = NULL;
2819 	}
2820 
2821 	if (sc->status_map != NULL) {
2822 		bus_dmamap_unload(
2823 		    sc->status_tag,
2824 		    sc->status_map);
2825 		bus_dmamap_destroy(sc->status_tag,
2826 		    sc->status_map);
2827 		sc->status_map = NULL;
2828 	}
2829 
2830 	if (sc->status_tag != NULL) {
2831 		bus_dma_tag_destroy(sc->status_tag);
2832 		sc->status_tag = NULL;
2833 	}
2834 
2835 
2836 	/* Free, unmap, and destroy the statistics block. */
2837 	if (sc->stats_block != NULL) {
2838 		bus_dmamem_free(
2839 		    sc->stats_tag,
2840 		    sc->stats_block,
2841 		    sc->stats_map);
2842 		sc->stats_block = NULL;
2843 	}
2844 
2845 	if (sc->stats_map != NULL) {
2846 		bus_dmamap_unload(
2847 		    sc->stats_tag,
2848 		    sc->stats_map);
2849 		bus_dmamap_destroy(sc->stats_tag,
2850 		    sc->stats_map);
2851 		sc->stats_map = NULL;
2852 	}
2853 
2854 	if (sc->stats_tag != NULL) {
2855 		bus_dma_tag_destroy(sc->stats_tag);
2856 		sc->stats_tag = NULL;
2857 	}
2858 
2859 
2860 	/* Free, unmap and destroy all context memory pages. */
2861 	if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
2862 		(BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
2863 		for (i = 0; i < sc->ctx_pages; i++ ) {
2864 			if (sc->ctx_block[i] != NULL) {
2865 				bus_dmamem_free(
2866 				    sc->ctx_tag,
2867 				    sc->ctx_block[i],
2868 				    sc->ctx_map[i]);
2869 				sc->ctx_block[i] = NULL;
2870 			}
2871 
2872 			if (sc->ctx_map[i] != NULL) {
2873 				bus_dmamap_unload(
2874 				    sc->ctx_tag,
2875 				    sc->ctx_map[i]);
2876 				bus_dmamap_destroy(
2877 				    sc->ctx_tag,
2878 				    sc->ctx_map[i]);
2879 				sc->ctx_map[i] = NULL;
2880 			}
2881 		}
2882 
2883 		/* Destroy the context memory tag. */
2884 		if (sc->ctx_tag != NULL) {
2885 			bus_dma_tag_destroy(sc->ctx_tag);
2886 			sc->ctx_tag = NULL;
2887 		}
2888 	}
2889 
2890 
2891 	/* Free, unmap and destroy all TX buffer descriptor chain pages. */
2892 	for (i = 0; i < TX_PAGES; i++ ) {
2893 		if (sc->tx_bd_chain[i] != NULL) {
2894 			bus_dmamem_free(
2895 			    sc->tx_bd_chain_tag,
2896 			    sc->tx_bd_chain[i],
2897 			    sc->tx_bd_chain_map[i]);
2898 			sc->tx_bd_chain[i] = NULL;
2899 		}
2900 
2901 		if (sc->tx_bd_chain_map[i] != NULL) {
2902 			bus_dmamap_unload(
2903 			    sc->tx_bd_chain_tag,
2904 			    sc->tx_bd_chain_map[i]);
2905 			bus_dmamap_destroy(
2906 			    sc->tx_bd_chain_tag,
2907 			    sc->tx_bd_chain_map[i]);
2908 			sc->tx_bd_chain_map[i] = NULL;
2909 		}
2910 	}
2911 
2912 	/* Destroy the TX buffer descriptor tag. */
2913 	if (sc->tx_bd_chain_tag != NULL) {
2914 		bus_dma_tag_destroy(sc->tx_bd_chain_tag);
2915 		sc->tx_bd_chain_tag = NULL;
2916 	}
2917 
2918 
2919 	/* Free, unmap and destroy all RX buffer descriptor chain pages. */
2920 	for (i = 0; i < RX_PAGES; i++ ) {
2921 		if (sc->rx_bd_chain[i] != NULL) {
2922 			bus_dmamem_free(
2923 			    sc->rx_bd_chain_tag,
2924 			    sc->rx_bd_chain[i],
2925 			    sc->rx_bd_chain_map[i]);
2926 			sc->rx_bd_chain[i] = NULL;
2927 		}
2928 
2929 		if (sc->rx_bd_chain_map[i] != NULL) {
2930 			bus_dmamap_unload(
2931 			    sc->rx_bd_chain_tag,
2932 			    sc->rx_bd_chain_map[i]);
2933 			bus_dmamap_destroy(
2934 			    sc->rx_bd_chain_tag,
2935 			    sc->rx_bd_chain_map[i]);
2936 			sc->rx_bd_chain_map[i] = NULL;
2937 		}
2938 	}
2939 
2940 	/* Destroy the RX buffer descriptor tag. */
2941 	if (sc->rx_bd_chain_tag != NULL) {
2942 		bus_dma_tag_destroy(sc->rx_bd_chain_tag);
2943 		sc->rx_bd_chain_tag = NULL;
2944 	}
2945 
2946 
2947 #ifdef BCE_JUMBO_HDRSPLIT
2948 	/* Free, unmap and destroy all page buffer descriptor chain pages. */
2949 	for (i = 0; i < PG_PAGES; i++ ) {
2950 		if (sc->pg_bd_chain[i] != NULL) {
2951 			bus_dmamem_free(
2952 			    sc->pg_bd_chain_tag,
2953 			    sc->pg_bd_chain[i],
2954 			    sc->pg_bd_chain_map[i]);
2955 			sc->pg_bd_chain[i] = NULL;
2956 		}
2957 
2958 		if (sc->pg_bd_chain_map[i] != NULL) {
2959 			bus_dmamap_unload(
2960 			    sc->pg_bd_chain_tag,
2961 			    sc->pg_bd_chain_map[i]);
2962 			bus_dmamap_destroy(
2963 			    sc->pg_bd_chain_tag,
2964 			    sc->pg_bd_chain_map[i]);
2965 			sc->pg_bd_chain_map[i] = NULL;
2966 		}
2967 	}
2968 
2969 	/* Destroy the page buffer descriptor tag. */
2970 	if (sc->pg_bd_chain_tag != NULL) {
2971 		bus_dma_tag_destroy(sc->pg_bd_chain_tag);
2972 		sc->pg_bd_chain_tag = NULL;
2973 	}
2974 #endif
2975 
2976 
2977 	/* Unload and destroy the TX mbuf maps. */
2978 	for (i = 0; i < TOTAL_TX_BD; i++) {
2979 		if (sc->tx_mbuf_map[i] != NULL) {
2980 			bus_dmamap_unload(sc->tx_mbuf_tag,
2981 			    sc->tx_mbuf_map[i]);
2982 			bus_dmamap_destroy(sc->tx_mbuf_tag,
2983 	 		    sc->tx_mbuf_map[i]);
2984 			sc->tx_mbuf_map[i] = NULL;
2985 		}
2986 	}
2987 
2988 	/* Destroy the TX mbuf tag. */
2989 	if (sc->tx_mbuf_tag != NULL) {
2990 		bus_dma_tag_destroy(sc->tx_mbuf_tag);
2991 		sc->tx_mbuf_tag = NULL;
2992 	}
2993 
2994 	/* Unload and destroy the RX mbuf maps. */
2995 	for (i = 0; i < TOTAL_RX_BD; i++) {
2996 		if (sc->rx_mbuf_map[i] != NULL) {
2997 			bus_dmamap_unload(sc->rx_mbuf_tag,
2998 			    sc->rx_mbuf_map[i]);
2999 			bus_dmamap_destroy(sc->rx_mbuf_tag,
3000 	 		    sc->rx_mbuf_map[i]);
3001 			sc->rx_mbuf_map[i] = NULL;
3002 		}
3003 	}
3004 
3005 	/* Destroy the RX mbuf tag. */
3006 	if (sc->rx_mbuf_tag != NULL) {
3007 		bus_dma_tag_destroy(sc->rx_mbuf_tag);
3008 		sc->rx_mbuf_tag = NULL;
3009 	}
3010 
3011 #ifdef BCE_JUMBO_HDRSPLIT
3012 	/* Unload and destroy the page mbuf maps. */
3013 	for (i = 0; i < TOTAL_PG_BD; i++) {
3014 		if (sc->pg_mbuf_map[i] != NULL) {
3015 			bus_dmamap_unload(sc->pg_mbuf_tag,
3016 			    sc->pg_mbuf_map[i]);
3017 			bus_dmamap_destroy(sc->pg_mbuf_tag,
3018 	 		    sc->pg_mbuf_map[i]);
3019 			sc->pg_mbuf_map[i] = NULL;
3020 		}
3021 	}
3022 
3023 	/* Destroy the page mbuf tag. */
3024 	if (sc->pg_mbuf_tag != NULL) {
3025 		bus_dma_tag_destroy(sc->pg_mbuf_tag);
3026 		sc->pg_mbuf_tag = NULL;
3027 	}
3028 #endif
3029 
3030 	/* Destroy the parent tag */
3031 	if (sc->parent_tag != NULL) {
3032 		bus_dma_tag_destroy(sc->parent_tag);
3033 		sc->parent_tag = NULL;
3034 	}
3035 
3036 	DBEXIT(BCE_VERBOSE_RESET | BCE_VERBOSE_UNLOAD | BCE_VERBOSE_CTX);
3037 }
3038 
3039 
3040 /****************************************************************************/
3041 /* Get DMA memory from the OS.                                              */
3042 /*                                                                          */
3043 /* Validates that the OS has provided DMA buffers in response to a          */
3044 /* bus_dmamap_load() call and saves the physical address of those buffers.  */
3045 /* When the callback is used the OS will return 0 for the mapping function  */
3046 /* (bus_dmamap_load()) so we use the value of map_arg->maxsegs to pass any  */
3047 /* failures back to the caller.                                             */
3048 /*                                                                          */
3049 /* Returns:                                                                 */
3050 /*   Nothing.                                                               */
3051 /****************************************************************************/
3052 static void
3053 bce_dma_map_addr(void *arg, bus_dma_segment_t *segs, int nseg, int error)
3054 {
3055 	bus_addr_t *busaddr = arg;
3056 
3057 	/* Simulate a mapping failure. */
3058 	DBRUNIF(DB_RANDOMTRUE(dma_map_addr_failed_sim_control),
3059 		error = ENOMEM);
3060 
3061 	/* Check for an error and signal the caller that an error occurred. */
3062 	if (error) {
3063 		*busaddr = 0;
3064 	} else {
3065 		*busaddr = segs->ds_addr;
3066 	}
3067 
3068 	return;
3069 }
3070 
3071 
3072 /****************************************************************************/
3073 /* Allocate any DMA memory needed by the driver.                            */
3074 /*                                                                          */
3075 /* Allocates DMA memory needed for the various global structures needed by  */
3076 /* hardware.                                                                */
3077 /*                                                                          */
3078 /* Memory alignment requirements:                                           */
3079 /* +-----------------+----------+----------+----------+----------+          */
3080 /* |                 |   5706   |   5708   |   5709   |   5716   |          */
3081 /* +-----------------+----------+----------+----------+----------+          */
3082 /* |Status Block     | 8 bytes  | 8 bytes  | 16 bytes | 16 bytes |          */
3083 /* |Statistics Block | 8 bytes  | 8 bytes  | 16 bytes | 16 bytes |          */
3084 /* |RX Buffers       | 16 bytes | 16 bytes | 16 bytes | 16 bytes |          */
3085 /* |PG Buffers       |   none   |   none   |   none   |   none   |          */
3086 /* |TX Buffers       |   none   |   none   |   none   |   none   |          */
3087 /* |Chain Pages(1)   |   4KiB   |   4KiB   |   4KiB   |   4KiB   |          */
3088 /* |Context Memory   |          |          |          |          |          */
3089 /* +-----------------+----------+----------+----------+----------+          */
3090 /*                                                                          */
3091 /* (1) Must align with CPU page size (BCM_PAGE_SZIE).                       */
3092 /*                                                                          */
3093 /* Returns:                                                                 */
3094 /*   0 for success, positive value for failure.                             */
3095 /****************************************************************************/
3096 static int
3097 bce_dma_alloc(device_t dev)
3098 {
3099 	struct bce_softc *sc;
3100 	int i, error, rc = 0;
3101 	bus_size_t max_size, max_seg_size;
3102 	int max_segments;
3103 
3104 	sc = device_get_softc(dev);
3105 
3106 	DBENTER(BCE_VERBOSE_RESET | BCE_VERBOSE_CTX);
3107 
3108 	/*
3109 	 * Allocate the parent bus DMA tag appropriate for PCI.
3110 	 */
3111 	if (bus_dma_tag_create(NULL, 1,	BCE_DMA_BOUNDARY,
3112 	    sc->max_bus_addr, BUS_SPACE_MAXADDR, NULL, NULL,
3113 	    MAXBSIZE, BUS_SPACE_UNRESTRICTED, BUS_SPACE_MAXSIZE_32BIT,
3114 	    0, NULL, NULL, &sc->parent_tag)) {
3115 		BCE_PRINTF("%s(%d): Could not allocate parent DMA tag!\n",
3116 		    __FILE__, __LINE__);
3117 		rc = ENOMEM;
3118 		goto bce_dma_alloc_exit;
3119 	}
3120 
3121 	/*
3122 	 * Create a DMA tag for the status block, allocate and clear the
3123 	 * memory, map the memory into DMA space, and fetch the physical
3124 	 * address of the block.
3125 	 */
3126 	if (bus_dma_tag_create(sc->parent_tag, BCE_DMA_ALIGN,
3127 	    BCE_DMA_BOUNDARY, sc->max_bus_addr,	BUS_SPACE_MAXADDR,
3128 	    NULL, NULL,	BCE_STATUS_BLK_SZ, 1, BCE_STATUS_BLK_SZ,
3129 	    0, NULL, NULL, &sc->status_tag)) {
3130 		BCE_PRINTF("%s(%d): Could not allocate status block "
3131 		    "DMA tag!\n", __FILE__, __LINE__);
3132 		rc = ENOMEM;
3133 		goto bce_dma_alloc_exit;
3134 	}
3135 
3136 	if(bus_dmamem_alloc(sc->status_tag, (void **)&sc->status_block,
3137 	    BUS_DMA_NOWAIT, &sc->status_map)) {
3138 		BCE_PRINTF("%s(%d): Could not allocate status block "
3139 		    "DMA memory!\n", __FILE__, __LINE__);
3140 		rc = ENOMEM;
3141 		goto bce_dma_alloc_exit;
3142 	}
3143 
3144 	bzero((char *)sc->status_block, BCE_STATUS_BLK_SZ);
3145 
3146 	error = bus_dmamap_load(sc->status_tag,	sc->status_map,
3147 	    sc->status_block, BCE_STATUS_BLK_SZ, bce_dma_map_addr,
3148 	    &sc->status_block_paddr, BUS_DMA_NOWAIT);
3149 
3150 	if (error) {
3151 		BCE_PRINTF("%s(%d): Could not map status block "
3152 		    "DMA memory!\n", __FILE__, __LINE__);
3153 		rc = ENOMEM;
3154 		goto bce_dma_alloc_exit;
3155 	}
3156 
3157 	DBPRINT(sc, BCE_INFO, "%s(): status_block_paddr = 0x%jX\n",
3158 	    __FUNCTION__, (uintmax_t) sc->status_block_paddr);
3159 
3160 	/*
3161 	 * Create a DMA tag for the statistics block, allocate and clear the
3162 	 * memory, map the memory into DMA space, and fetch the physical
3163 	 * address of the block.
3164 	 */
3165 	if (bus_dma_tag_create(sc->parent_tag, BCE_DMA_ALIGN,
3166 	    BCE_DMA_BOUNDARY, sc->max_bus_addr,	BUS_SPACE_MAXADDR,
3167 	    NULL, NULL,	BCE_STATS_BLK_SZ, 1, BCE_STATS_BLK_SZ,
3168 	    0, NULL, NULL, &sc->stats_tag)) {
3169 		BCE_PRINTF("%s(%d): Could not allocate statistics block "
3170 		    "DMA tag!\n", __FILE__, __LINE__);
3171 		rc = ENOMEM;
3172 		goto bce_dma_alloc_exit;
3173 	}
3174 
3175 	if (bus_dmamem_alloc(sc->stats_tag, (void **)&sc->stats_block,
3176 	    BUS_DMA_NOWAIT,	&sc->stats_map)) {
3177 		BCE_PRINTF("%s(%d): Could not allocate statistics block "
3178 		    "DMA memory!\n", __FILE__, __LINE__);
3179 		rc = ENOMEM;
3180 		goto bce_dma_alloc_exit;
3181 	}
3182 
3183 	bzero((char *)sc->stats_block, BCE_STATS_BLK_SZ);
3184 
3185 	error = bus_dmamap_load(sc->stats_tag, sc->stats_map,
3186 	    sc->stats_block, BCE_STATS_BLK_SZ, bce_dma_map_addr,
3187 	    &sc->stats_block_paddr, BUS_DMA_NOWAIT);
3188 
3189 	if(error) {
3190 		BCE_PRINTF("%s(%d): Could not map statistics block "
3191 		    "DMA memory!\n", __FILE__, __LINE__);
3192 		rc = ENOMEM;
3193 		goto bce_dma_alloc_exit;
3194 	}
3195 
3196 	DBPRINT(sc, BCE_INFO, "%s(): stats_block_paddr = 0x%jX\n",
3197 	    __FUNCTION__, (uintmax_t) sc->stats_block_paddr);
3198 
3199 	/* BCM5709 uses host memory as cache for context memory. */
3200 	if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
3201 	    (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
3202 		sc->ctx_pages = 0x2000 / BCM_PAGE_SIZE;
3203 		if (sc->ctx_pages == 0)
3204 			sc->ctx_pages = 1;
3205 
3206 		DBRUNIF((sc->ctx_pages > 512),
3207 		    BCE_PRINTF("%s(%d): Too many CTX pages! %d > 512\n",
3208 		    __FILE__, __LINE__, sc->ctx_pages));
3209 
3210 		/*
3211 		 * Create a DMA tag for the context pages,
3212 		 * allocate and clear the memory, map the
3213 		 * memory into DMA space, and fetch the
3214 		 * physical address of the block.
3215 		 */
3216 		if(bus_dma_tag_create(sc->parent_tag, BCM_PAGE_SIZE,
3217 		    BCE_DMA_BOUNDARY, sc->max_bus_addr,	BUS_SPACE_MAXADDR,
3218 		    NULL, NULL,	BCM_PAGE_SIZE, 1, BCM_PAGE_SIZE,
3219 		    0, NULL, NULL, &sc->ctx_tag)) {
3220 			BCE_PRINTF("%s(%d): Could not allocate CTX DMA tag!\n",
3221 			    __FILE__, __LINE__);
3222 			rc = ENOMEM;
3223 			goto bce_dma_alloc_exit;
3224 		}
3225 
3226 		for (i = 0; i < sc->ctx_pages; i++) {
3227 
3228 			if(bus_dmamem_alloc(sc->ctx_tag,
3229 			    (void **)&sc->ctx_block[i],
3230 			    BUS_DMA_NOWAIT,
3231 			    &sc->ctx_map[i])) {
3232 				BCE_PRINTF("%s(%d): Could not allocate CTX "
3233 				    "DMA memory!\n", __FILE__, __LINE__);
3234 				rc = ENOMEM;
3235 				goto bce_dma_alloc_exit;
3236 			}
3237 
3238 			bzero((char *)sc->ctx_block[i], BCM_PAGE_SIZE);
3239 
3240 			error = bus_dmamap_load(sc->ctx_tag, sc->ctx_map[i],
3241 			    sc->ctx_block[i], BCM_PAGE_SIZE, bce_dma_map_addr,
3242 			    &sc->ctx_paddr[i], BUS_DMA_NOWAIT);
3243 
3244 			if (error) {
3245 				BCE_PRINTF("%s(%d): Could not map CTX "
3246 				    "DMA memory!\n", __FILE__, __LINE__);
3247 				rc = ENOMEM;
3248 				goto bce_dma_alloc_exit;
3249 			}
3250 
3251 			DBPRINT(sc, BCE_INFO, "%s(): ctx_paddr[%d] = 0x%jX\n",
3252 			    __FUNCTION__, i, (uintmax_t) sc->ctx_paddr[i]);
3253 		}
3254 	}
3255 
3256 	/*
3257 	 * Create a DMA tag for the TX buffer descriptor chain,
3258 	 * allocate and clear the  memory, and fetch the
3259 	 * physical address of the block.
3260 	 */
3261 	if(bus_dma_tag_create(sc->parent_tag, BCM_PAGE_SIZE, BCE_DMA_BOUNDARY,
3262 	    sc->max_bus_addr, BUS_SPACE_MAXADDR, NULL, NULL,
3263 	    BCE_TX_CHAIN_PAGE_SZ, 1, BCE_TX_CHAIN_PAGE_SZ, 0,
3264 	    NULL, NULL,	&sc->tx_bd_chain_tag)) {
3265 		BCE_PRINTF("%s(%d): Could not allocate TX descriptor chain "
3266 		    "DMA tag!\n", __FILE__, __LINE__);
3267 		rc = ENOMEM;
3268 		goto bce_dma_alloc_exit;
3269 	}
3270 
3271 	for (i = 0; i < TX_PAGES; i++) {
3272 
3273 		if(bus_dmamem_alloc(sc->tx_bd_chain_tag,
3274 		    (void **)&sc->tx_bd_chain[i], BUS_DMA_NOWAIT,
3275 		    &sc->tx_bd_chain_map[i])) {
3276 			BCE_PRINTF("%s(%d): Could not allocate TX descriptor "
3277 			    "chain DMA memory!\n", __FILE__, __LINE__);
3278 			rc = ENOMEM;
3279 			goto bce_dma_alloc_exit;
3280 		}
3281 
3282 		error = bus_dmamap_load(sc->tx_bd_chain_tag,
3283 		    sc->tx_bd_chain_map[i], sc->tx_bd_chain[i],
3284 		    BCE_TX_CHAIN_PAGE_SZ, bce_dma_map_addr,
3285 		    &sc->tx_bd_chain_paddr[i], BUS_DMA_NOWAIT);
3286 
3287 		if (error) {
3288 			BCE_PRINTF("%s(%d): Could not map TX descriptor "
3289 			    "chain DMA memory!\n", __FILE__, __LINE__);
3290 			rc = ENOMEM;
3291 			goto bce_dma_alloc_exit;
3292 		}
3293 
3294 		DBPRINT(sc, BCE_INFO, "%s(): tx_bd_chain_paddr[%d] = 0x%jX\n",
3295 		    __FUNCTION__, i, (uintmax_t) sc->tx_bd_chain_paddr[i]);
3296 	}
3297 
3298 	/* Check the required size before mapping to conserve resources. */
3299 	if (bce_tso_enable) {
3300 		max_size     = BCE_TSO_MAX_SIZE;
3301 		max_segments = BCE_MAX_SEGMENTS;
3302 		max_seg_size = BCE_TSO_MAX_SEG_SIZE;
3303 	} else {
3304 		max_size     = MCLBYTES * BCE_MAX_SEGMENTS;
3305 		max_segments = BCE_MAX_SEGMENTS;
3306 		max_seg_size = MCLBYTES;
3307 	}
3308 
3309 	/* Create a DMA tag for TX mbufs. */
3310 	if (bus_dma_tag_create(sc->parent_tag, 1, BCE_DMA_BOUNDARY,
3311 	    sc->max_bus_addr, BUS_SPACE_MAXADDR, NULL, NULL, max_size,
3312 	    max_segments, max_seg_size,	0, NULL, NULL, &sc->tx_mbuf_tag)) {
3313 		BCE_PRINTF("%s(%d): Could not allocate TX mbuf DMA tag!\n",
3314 		    __FILE__, __LINE__);
3315 		rc = ENOMEM;
3316 		goto bce_dma_alloc_exit;
3317 	}
3318 
3319 	/* Create DMA maps for the TX mbufs clusters. */
3320 	for (i = 0; i < TOTAL_TX_BD; i++) {
3321 		if (bus_dmamap_create(sc->tx_mbuf_tag, BUS_DMA_NOWAIT,
3322 			&sc->tx_mbuf_map[i])) {
3323 			BCE_PRINTF("%s(%d): Unable to create TX mbuf DMA "
3324 			    "map!\n", __FILE__, __LINE__);
3325 			rc = ENOMEM;
3326 			goto bce_dma_alloc_exit;
3327 		}
3328 	}
3329 
3330 	/*
3331 	 * Create a DMA tag for the RX buffer descriptor chain,
3332 	 * allocate and clear the memory, and fetch the physical
3333 	 * address of the blocks.
3334 	 */
3335 	if (bus_dma_tag_create(sc->parent_tag, BCM_PAGE_SIZE,
3336 			BCE_DMA_BOUNDARY, BUS_SPACE_MAXADDR,
3337 			sc->max_bus_addr, NULL, NULL,
3338 			BCE_RX_CHAIN_PAGE_SZ, 1, BCE_RX_CHAIN_PAGE_SZ,
3339 			0, NULL, NULL, &sc->rx_bd_chain_tag)) {
3340 		BCE_PRINTF("%s(%d): Could not allocate RX descriptor chain "
3341 		    "DMA tag!\n", __FILE__, __LINE__);
3342 		rc = ENOMEM;
3343 		goto bce_dma_alloc_exit;
3344 	}
3345 
3346 	for (i = 0; i < RX_PAGES; i++) {
3347 
3348 		if (bus_dmamem_alloc(sc->rx_bd_chain_tag,
3349 		    (void **)&sc->rx_bd_chain[i], BUS_DMA_NOWAIT,
3350 		    &sc->rx_bd_chain_map[i])) {
3351 			BCE_PRINTF("%s(%d): Could not allocate RX descriptor "
3352 			    "chain DMA memory!\n", __FILE__, __LINE__);
3353 			rc = ENOMEM;
3354 			goto bce_dma_alloc_exit;
3355 		}
3356 
3357 		bzero((char *)sc->rx_bd_chain[i], BCE_RX_CHAIN_PAGE_SZ);
3358 
3359 		error = bus_dmamap_load(sc->rx_bd_chain_tag,
3360 		    sc->rx_bd_chain_map[i], sc->rx_bd_chain[i],
3361 		    BCE_RX_CHAIN_PAGE_SZ, bce_dma_map_addr,
3362 		    &sc->rx_bd_chain_paddr[i], BUS_DMA_NOWAIT);
3363 
3364 		if (error) {
3365 			BCE_PRINTF("%s(%d): Could not map RX descriptor "
3366 			    "chain DMA memory!\n", __FILE__, __LINE__);
3367 			rc = ENOMEM;
3368 			goto bce_dma_alloc_exit;
3369 		}
3370 
3371 		DBPRINT(sc, BCE_INFO, "%s(): rx_bd_chain_paddr[%d] = 0x%jX\n",
3372 		    __FUNCTION__, i, (uintmax_t) sc->rx_bd_chain_paddr[i]);
3373 	}
3374 
3375 	/*
3376 	 * Create a DMA tag for RX mbufs.
3377 	 */
3378 #ifdef BCE_JUMBO_HDRSPLIT
3379 	max_size = max_seg_size = ((sc->rx_bd_mbuf_alloc_size < MCLBYTES) ?
3380 		MCLBYTES : sc->rx_bd_mbuf_alloc_size);
3381 #else
3382 	max_size = max_seg_size = MJUM9BYTES;
3383 #endif
3384 	max_segments = 1;
3385 
3386 	DBPRINT(sc, BCE_INFO, "%s(): Creating rx_mbuf_tag (max size = 0x%jX "
3387 	    "max segments = %d, max segment size = 0x%jX)\n", __FUNCTION__,
3388 	    (uintmax_t) max_size, max_segments, (uintmax_t) max_seg_size);
3389 
3390 	if (bus_dma_tag_create(sc->parent_tag, 1, BCE_DMA_BOUNDARY,
3391 	    sc->max_bus_addr, BUS_SPACE_MAXADDR, NULL, NULL, max_size,
3392 	   max_segments, max_seg_size, 0, NULL, NULL, &sc->rx_mbuf_tag)) {
3393 		BCE_PRINTF("%s(%d): Could not allocate RX mbuf DMA tag!\n",
3394 		    __FILE__, __LINE__);
3395 		rc = ENOMEM;
3396 		goto bce_dma_alloc_exit;
3397 	}
3398 
3399 	/* Create DMA maps for the RX mbuf clusters. */
3400 	for (i = 0; i < TOTAL_RX_BD; i++) {
3401 		if (bus_dmamap_create(sc->rx_mbuf_tag, BUS_DMA_NOWAIT,
3402 		    &sc->rx_mbuf_map[i])) {
3403 			BCE_PRINTF("%s(%d): Unable to create RX mbuf "
3404 			    "DMA map!\n", __FILE__, __LINE__);
3405 			rc = ENOMEM;
3406 			goto bce_dma_alloc_exit;
3407 		}
3408 	}
3409 
3410 #ifdef BCE_JUMBO_HDRSPLIT
3411 	/*
3412 	 * Create a DMA tag for the page buffer descriptor chain,
3413 	 * allocate and clear the memory, and fetch the physical
3414 	 * address of the blocks.
3415 	 */
3416 	if (bus_dma_tag_create(sc->parent_tag, BCM_PAGE_SIZE,
3417 	    BCE_DMA_BOUNDARY, BUS_SPACE_MAXADDR, sc->max_bus_addr,
3418 	    NULL, NULL,	BCE_PG_CHAIN_PAGE_SZ, 1, BCE_PG_CHAIN_PAGE_SZ,
3419 	    0, NULL, NULL, &sc->pg_bd_chain_tag)) {
3420 		BCE_PRINTF("%s(%d): Could not allocate page descriptor "
3421 		    "chain DMA tag!\n",	__FILE__, __LINE__);
3422 		rc = ENOMEM;
3423 		goto bce_dma_alloc_exit;
3424 	}
3425 
3426 	for (i = 0; i < PG_PAGES; i++) {
3427 
3428 		if (bus_dmamem_alloc(sc->pg_bd_chain_tag,
3429 		    (void **)&sc->pg_bd_chain[i], BUS_DMA_NOWAIT,
3430 		    &sc->pg_bd_chain_map[i])) {
3431 			BCE_PRINTF("%s(%d): Could not allocate page "
3432 			    "descriptor chain DMA memory!\n",
3433 			    __FILE__, __LINE__);
3434 			rc = ENOMEM;
3435 			goto bce_dma_alloc_exit;
3436 		}
3437 
3438 		bzero((char *)sc->pg_bd_chain[i], BCE_PG_CHAIN_PAGE_SZ);
3439 
3440 		error = bus_dmamap_load(sc->pg_bd_chain_tag,
3441 		    sc->pg_bd_chain_map[i], sc->pg_bd_chain[i],
3442 		    BCE_PG_CHAIN_PAGE_SZ, bce_dma_map_addr,
3443 		    &sc->pg_bd_chain_paddr[i], BUS_DMA_NOWAIT);
3444 
3445 		if (error) {
3446 			BCE_PRINTF("%s(%d): Could not map page descriptor "
3447 			    "chain DMA memory!\n", __FILE__, __LINE__);
3448 			rc = ENOMEM;
3449 			goto bce_dma_alloc_exit;
3450 		}
3451 
3452 		DBPRINT(sc, BCE_INFO, "%s(): pg_bd_chain_paddr[%d] = 0x%jX\n",
3453 		    __FUNCTION__, i, (uintmax_t) sc->pg_bd_chain_paddr[i]);
3454 	}
3455 
3456 	/*
3457 	 * Create a DMA tag for page mbufs.
3458 	 */
3459 	max_size = max_seg_size = ((sc->pg_bd_mbuf_alloc_size < MCLBYTES) ?
3460 	    MCLBYTES : sc->pg_bd_mbuf_alloc_size);
3461 
3462 	if (bus_dma_tag_create(sc->parent_tag, 1, BCE_DMA_BOUNDARY,
3463 	    sc->max_bus_addr, BUS_SPACE_MAXADDR, NULL, NULL,
3464 	    max_size, 1, max_seg_size, 0, NULL, NULL, &sc->pg_mbuf_tag)) {
3465 		BCE_PRINTF("%s(%d): Could not allocate page mbuf "
3466 		    "DMA tag!\n", __FILE__, __LINE__);
3467 		rc = ENOMEM;
3468 		goto bce_dma_alloc_exit;
3469 	}
3470 
3471 	/* Create DMA maps for the page mbuf clusters. */
3472 	for (i = 0; i < TOTAL_PG_BD; i++) {
3473 		if (bus_dmamap_create(sc->pg_mbuf_tag, BUS_DMA_NOWAIT,
3474 		    &sc->pg_mbuf_map[i])) {
3475 			BCE_PRINTF("%s(%d): Unable to create page mbuf "
3476 			    "DMA map!\n", __FILE__, __LINE__);
3477 			rc = ENOMEM;
3478 			goto bce_dma_alloc_exit;
3479 		}
3480 	}
3481 #endif
3482 
3483 bce_dma_alloc_exit:
3484 	DBEXIT(BCE_VERBOSE_RESET | BCE_VERBOSE_CTX);
3485 	return(rc);
3486 }
3487 
3488 
3489 /****************************************************************************/
3490 /* Release all resources used by the driver.                                */
3491 /*                                                                          */
3492 /* Releases all resources acquired by the driver including interrupts,      */
3493 /* interrupt handler, interfaces, mutexes, and DMA memory.                  */
3494 /*                                                                          */
3495 /* Returns:                                                                 */
3496 /*   Nothing.                                                               */
3497 /****************************************************************************/
3498 static void
3499 bce_release_resources(struct bce_softc *sc)
3500 {
3501 	device_t dev;
3502 
3503 	DBENTER(BCE_VERBOSE_RESET);
3504 
3505 	dev = sc->bce_dev;
3506 
3507 	bce_dma_free(sc);
3508 
3509 	if (sc->bce_intrhand != NULL) {
3510 		DBPRINT(sc, BCE_INFO_RESET, "Removing interrupt handler.\n");
3511 		bus_teardown_intr(dev, sc->bce_res_irq, sc->bce_intrhand);
3512 	}
3513 
3514 	if (sc->bce_res_irq != NULL) {
3515 		DBPRINT(sc, BCE_INFO_RESET, "Releasing IRQ.\n");
3516 		bus_release_resource(dev, SYS_RES_IRQ, sc->bce_irq_rid,
3517 		    sc->bce_res_irq);
3518 	}
3519 
3520 	if (sc->bce_flags & (BCE_USING_MSI_FLAG | BCE_USING_MSIX_FLAG)) {
3521 		DBPRINT(sc, BCE_INFO_RESET, "Releasing MSI/MSI-X vector.\n");
3522 		pci_release_msi(dev);
3523 	}
3524 
3525 	if (sc->bce_res_mem != NULL) {
3526 		DBPRINT(sc, BCE_INFO_RESET, "Releasing PCI memory.\n");
3527 		    bus_release_resource(dev, SYS_RES_MEMORY, PCIR_BAR(0),
3528 		    sc->bce_res_mem);
3529 	}
3530 
3531 	if (sc->bce_ifp != NULL) {
3532 		DBPRINT(sc, BCE_INFO_RESET, "Releasing IF.\n");
3533 		if_free(sc->bce_ifp);
3534 	}
3535 
3536 	if (mtx_initialized(&sc->bce_mtx))
3537 		BCE_LOCK_DESTROY(sc);
3538 
3539 	DBEXIT(BCE_VERBOSE_RESET);
3540 }
3541 
3542 
3543 /****************************************************************************/
3544 /* Firmware synchronization.                                                */
3545 /*                                                                          */
3546 /* Before performing certain events such as a chip reset, synchronize with  */
3547 /* the firmware first.                                                      */
3548 /*                                                                          */
3549 /* Returns:                                                                 */
3550 /*   0 for success, positive value for failure.                             */
3551 /****************************************************************************/
3552 static int
3553 bce_fw_sync(struct bce_softc *sc, u32 msg_data)
3554 {
3555 	int i, rc = 0;
3556 	u32 val;
3557 
3558 	DBENTER(BCE_VERBOSE_RESET);
3559 
3560 	/* Don't waste any time if we've timed out before. */
3561 	if (sc->bce_fw_timed_out == TRUE) {
3562 		rc = EBUSY;
3563 		goto bce_fw_sync_exit;
3564 	}
3565 
3566 	/* Increment the message sequence number. */
3567 	sc->bce_fw_wr_seq++;
3568 	msg_data |= sc->bce_fw_wr_seq;
3569 
3570  	DBPRINT(sc, BCE_VERBOSE_FIRMWARE, "bce_fw_sync(): msg_data = "
3571 	    "0x%08X\n",	msg_data);
3572 
3573 	/* Send the message to the bootcode driver mailbox. */
3574 	bce_shmem_wr(sc, BCE_DRV_MB, msg_data);
3575 
3576 	/* Wait for the bootcode to acknowledge the message. */
3577 	for (i = 0; i < FW_ACK_TIME_OUT_MS; i++) {
3578 		/* Check for a response in the bootcode firmware mailbox. */
3579 		val = bce_shmem_rd(sc, BCE_FW_MB);
3580 		if ((val & BCE_FW_MSG_ACK) == (msg_data & BCE_DRV_MSG_SEQ))
3581 			break;
3582 		DELAY(1000);
3583 	}
3584 
3585 	/* If we've timed out, tell the bootcode that we've stopped waiting. */
3586 	if (((val & BCE_FW_MSG_ACK) != (msg_data & BCE_DRV_MSG_SEQ)) &&
3587 	    ((msg_data & BCE_DRV_MSG_DATA) != BCE_DRV_MSG_DATA_WAIT0)) {
3588 
3589 		BCE_PRINTF("%s(%d): Firmware synchronization timeout! "
3590 		    "msg_data = 0x%08X\n", __FILE__, __LINE__, msg_data);
3591 
3592 		msg_data &= ~BCE_DRV_MSG_CODE;
3593 		msg_data |= BCE_DRV_MSG_CODE_FW_TIMEOUT;
3594 
3595 		bce_shmem_wr(sc, BCE_DRV_MB, msg_data);
3596 
3597 		sc->bce_fw_timed_out = TRUE;
3598 		rc = EBUSY;
3599 	}
3600 
3601 bce_fw_sync_exit:
3602 	DBEXIT(BCE_VERBOSE_RESET);
3603 	return (rc);
3604 }
3605 
3606 
3607 /****************************************************************************/
3608 /* Load Receive Virtual 2 Physical (RV2P) processor firmware.               */
3609 /*                                                                          */
3610 /* Returns:                                                                 */
3611 /*   Nothing.                                                               */
3612 /****************************************************************************/
3613 static void
3614 bce_load_rv2p_fw(struct bce_softc *sc, u32 *rv2p_code,
3615 	u32 rv2p_code_len, u32 rv2p_proc)
3616 {
3617 	int i;
3618 	u32 val;
3619 
3620 	DBENTER(BCE_VERBOSE_RESET);
3621 
3622 	/* Set the page size used by RV2P. */
3623 	if (rv2p_proc == RV2P_PROC2) {
3624 		BCE_RV2P_PROC2_CHG_MAX_BD_PAGE(USABLE_RX_BD_PER_PAGE);
3625 	}
3626 
3627 	for (i = 0; i < rv2p_code_len; i += 8) {
3628 		REG_WR(sc, BCE_RV2P_INSTR_HIGH, *rv2p_code);
3629 		rv2p_code++;
3630 		REG_WR(sc, BCE_RV2P_INSTR_LOW, *rv2p_code);
3631 		rv2p_code++;
3632 
3633 		if (rv2p_proc == RV2P_PROC1) {
3634 			val = (i / 8) | BCE_RV2P_PROC1_ADDR_CMD_RDWR;
3635 			REG_WR(sc, BCE_RV2P_PROC1_ADDR_CMD, val);
3636 		}
3637 		else {
3638 			val = (i / 8) | BCE_RV2P_PROC2_ADDR_CMD_RDWR;
3639 			REG_WR(sc, BCE_RV2P_PROC2_ADDR_CMD, val);
3640 		}
3641 	}
3642 
3643 	/* Reset the processor, un-stall is done later. */
3644 	if (rv2p_proc == RV2P_PROC1) {
3645 		REG_WR(sc, BCE_RV2P_COMMAND, BCE_RV2P_COMMAND_PROC1_RESET);
3646 	}
3647 	else {
3648 		REG_WR(sc, BCE_RV2P_COMMAND, BCE_RV2P_COMMAND_PROC2_RESET);
3649 	}
3650 
3651 	DBEXIT(BCE_VERBOSE_RESET);
3652 }
3653 
3654 
3655 /****************************************************************************/
3656 /* Load RISC processor firmware.                                            */
3657 /*                                                                          */
3658 /* Loads firmware from the file if_bcefw.h into the scratchpad memory       */
3659 /* associated with a particular processor.                                  */
3660 /*                                                                          */
3661 /* Returns:                                                                 */
3662 /*   Nothing.                                                               */
3663 /****************************************************************************/
3664 static void
3665 bce_load_cpu_fw(struct bce_softc *sc, struct cpu_reg *cpu_reg,
3666 	struct fw_info *fw)
3667 {
3668 	u32 offset;
3669 
3670 	DBENTER(BCE_VERBOSE_RESET);
3671 
3672     bce_halt_cpu(sc, cpu_reg);
3673 
3674 	/* Load the Text area. */
3675 	offset = cpu_reg->spad_base + (fw->text_addr - cpu_reg->mips_view_base);
3676 	if (fw->text) {
3677 		int j;
3678 
3679 		for (j = 0; j < (fw->text_len / 4); j++, offset += 4) {
3680 			REG_WR_IND(sc, offset, fw->text[j]);
3681 	        }
3682 	}
3683 
3684 	/* Load the Data area. */
3685 	offset = cpu_reg->spad_base + (fw->data_addr - cpu_reg->mips_view_base);
3686 	if (fw->data) {
3687 		int j;
3688 
3689 		for (j = 0; j < (fw->data_len / 4); j++, offset += 4) {
3690 			REG_WR_IND(sc, offset, fw->data[j]);
3691 		}
3692 	}
3693 
3694 	/* Load the SBSS area. */
3695 	offset = cpu_reg->spad_base + (fw->sbss_addr - cpu_reg->mips_view_base);
3696 	if (fw->sbss) {
3697 		int j;
3698 
3699 		for (j = 0; j < (fw->sbss_len / 4); j++, offset += 4) {
3700 			REG_WR_IND(sc, offset, fw->sbss[j]);
3701 		}
3702 	}
3703 
3704 	/* Load the BSS area. */
3705 	offset = cpu_reg->spad_base + (fw->bss_addr - cpu_reg->mips_view_base);
3706 	if (fw->bss) {
3707 		int j;
3708 
3709 		for (j = 0; j < (fw->bss_len/4); j++, offset += 4) {
3710 			REG_WR_IND(sc, offset, fw->bss[j]);
3711 		}
3712 	}
3713 
3714 	/* Load the Read-Only area. */
3715 	offset = cpu_reg->spad_base +
3716 		(fw->rodata_addr - cpu_reg->mips_view_base);
3717 	if (fw->rodata) {
3718 		int j;
3719 
3720 		for (j = 0; j < (fw->rodata_len / 4); j++, offset += 4) {
3721 			REG_WR_IND(sc, offset, fw->rodata[j]);
3722 		}
3723 	}
3724 
3725 	/* Clear the pre-fetch instruction and set the FW start address. */
3726 	REG_WR_IND(sc, cpu_reg->inst, 0);
3727 	REG_WR_IND(sc, cpu_reg->pc, fw->start_addr);
3728 
3729 	DBEXIT(BCE_VERBOSE_RESET);
3730 }
3731 
3732 
3733 /****************************************************************************/
3734 /* Starts the RISC processor.                                               */
3735 /*                                                                          */
3736 /* Assumes the CPU starting address has already been set.                   */
3737 /*                                                                          */
3738 /* Returns:                                                                 */
3739 /*   Nothing.                                                               */
3740 /****************************************************************************/
3741 static void
3742 bce_start_cpu(struct bce_softc *sc, struct cpu_reg *cpu_reg)
3743 {
3744 	u32 val;
3745 
3746 	DBENTER(BCE_VERBOSE_RESET);
3747 
3748 	/* Start the CPU. */
3749 	val = REG_RD_IND(sc, cpu_reg->mode);
3750 	val &= ~cpu_reg->mode_value_halt;
3751 	REG_WR_IND(sc, cpu_reg->state, cpu_reg->state_value_clear);
3752 	REG_WR_IND(sc, cpu_reg->mode, val);
3753 
3754 	DBEXIT(BCE_VERBOSE_RESET);
3755 }
3756 
3757 
3758 /****************************************************************************/
3759 /* Halts the RISC processor.                                                */
3760 /*                                                                          */
3761 /* Returns:                                                                 */
3762 /*   Nothing.                                                               */
3763 /****************************************************************************/
3764 static void
3765 bce_halt_cpu(struct bce_softc *sc, struct cpu_reg *cpu_reg)
3766 {
3767 	u32 val;
3768 
3769 	DBENTER(BCE_VERBOSE_RESET);
3770 
3771 	/* Halt the CPU. */
3772 	val = REG_RD_IND(sc, cpu_reg->mode);
3773 	val |= cpu_reg->mode_value_halt;
3774 	REG_WR_IND(sc, cpu_reg->mode, val);
3775 	REG_WR_IND(sc, cpu_reg->state, cpu_reg->state_value_clear);
3776 
3777 	DBEXIT(BCE_VERBOSE_RESET);
3778 }
3779 
3780 
3781 /****************************************************************************/
3782 /* Initialize the RX CPU.                                                   */
3783 /*                                                                          */
3784 /* Returns:                                                                 */
3785 /*   Nothing.                                                               */
3786 /****************************************************************************/
3787 static void
3788 bce_start_rxp_cpu(struct bce_softc *sc)
3789 {
3790 	struct cpu_reg cpu_reg;
3791 
3792 	DBENTER(BCE_VERBOSE_RESET);
3793 
3794 	cpu_reg.mode = BCE_RXP_CPU_MODE;
3795 	cpu_reg.mode_value_halt = BCE_RXP_CPU_MODE_SOFT_HALT;
3796 	cpu_reg.mode_value_sstep = BCE_RXP_CPU_MODE_STEP_ENA;
3797 	cpu_reg.state = BCE_RXP_CPU_STATE;
3798 	cpu_reg.state_value_clear = 0xffffff;
3799 	cpu_reg.gpr0 = BCE_RXP_CPU_REG_FILE;
3800 	cpu_reg.evmask = BCE_RXP_CPU_EVENT_MASK;
3801 	cpu_reg.pc = BCE_RXP_CPU_PROGRAM_COUNTER;
3802 	cpu_reg.inst = BCE_RXP_CPU_INSTRUCTION;
3803 	cpu_reg.bp = BCE_RXP_CPU_HW_BREAKPOINT;
3804 	cpu_reg.spad_base = BCE_RXP_SCRATCH;
3805 	cpu_reg.mips_view_base = 0x8000000;
3806 
3807 	DBPRINT(sc, BCE_INFO_RESET, "Starting RX firmware.\n");
3808 	bce_start_cpu(sc, &cpu_reg);
3809 
3810 	DBEXIT(BCE_VERBOSE_RESET);
3811 }
3812 
3813 
3814 /****************************************************************************/
3815 /* Initialize the RX CPU.                                                   */
3816 /*                                                                          */
3817 /* Returns:                                                                 */
3818 /*   Nothing.                                                               */
3819 /****************************************************************************/
3820 static void
3821 bce_init_rxp_cpu(struct bce_softc *sc)
3822 {
3823 	struct cpu_reg cpu_reg;
3824 	struct fw_info fw;
3825 
3826 	DBENTER(BCE_VERBOSE_RESET);
3827 
3828 	cpu_reg.mode = BCE_RXP_CPU_MODE;
3829 	cpu_reg.mode_value_halt = BCE_RXP_CPU_MODE_SOFT_HALT;
3830 	cpu_reg.mode_value_sstep = BCE_RXP_CPU_MODE_STEP_ENA;
3831 	cpu_reg.state = BCE_RXP_CPU_STATE;
3832 	cpu_reg.state_value_clear = 0xffffff;
3833 	cpu_reg.gpr0 = BCE_RXP_CPU_REG_FILE;
3834 	cpu_reg.evmask = BCE_RXP_CPU_EVENT_MASK;
3835 	cpu_reg.pc = BCE_RXP_CPU_PROGRAM_COUNTER;
3836 	cpu_reg.inst = BCE_RXP_CPU_INSTRUCTION;
3837 	cpu_reg.bp = BCE_RXP_CPU_HW_BREAKPOINT;
3838 	cpu_reg.spad_base = BCE_RXP_SCRATCH;
3839 	cpu_reg.mips_view_base = 0x8000000;
3840 
3841 	if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
3842 		(BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
3843  		fw.ver_major = bce_RXP_b09FwReleaseMajor;
3844 		fw.ver_minor = bce_RXP_b09FwReleaseMinor;
3845 		fw.ver_fix = bce_RXP_b09FwReleaseFix;
3846 		fw.start_addr = bce_RXP_b09FwStartAddr;
3847 
3848 		fw.text_addr = bce_RXP_b09FwTextAddr;
3849 		fw.text_len = bce_RXP_b09FwTextLen;
3850 		fw.text_index = 0;
3851 		fw.text = bce_RXP_b09FwText;
3852 
3853 		fw.data_addr = bce_RXP_b09FwDataAddr;
3854 		fw.data_len = bce_RXP_b09FwDataLen;
3855 		fw.data_index = 0;
3856 		fw.data = bce_RXP_b09FwData;
3857 
3858 		fw.sbss_addr = bce_RXP_b09FwSbssAddr;
3859 		fw.sbss_len = bce_RXP_b09FwSbssLen;
3860 		fw.sbss_index = 0;
3861 		fw.sbss = bce_RXP_b09FwSbss;
3862 
3863 		fw.bss_addr = bce_RXP_b09FwBssAddr;
3864 		fw.bss_len = bce_RXP_b09FwBssLen;
3865 		fw.bss_index = 0;
3866 		fw.bss = bce_RXP_b09FwBss;
3867 
3868 		fw.rodata_addr = bce_RXP_b09FwRodataAddr;
3869 		fw.rodata_len = bce_RXP_b09FwRodataLen;
3870 		fw.rodata_index = 0;
3871 		fw.rodata = bce_RXP_b09FwRodata;
3872 	} else {
3873 		fw.ver_major = bce_RXP_b06FwReleaseMajor;
3874 		fw.ver_minor = bce_RXP_b06FwReleaseMinor;
3875 		fw.ver_fix = bce_RXP_b06FwReleaseFix;
3876 		fw.start_addr = bce_RXP_b06FwStartAddr;
3877 
3878 		fw.text_addr = bce_RXP_b06FwTextAddr;
3879 		fw.text_len = bce_RXP_b06FwTextLen;
3880 		fw.text_index = 0;
3881 		fw.text = bce_RXP_b06FwText;
3882 
3883 		fw.data_addr = bce_RXP_b06FwDataAddr;
3884 		fw.data_len = bce_RXP_b06FwDataLen;
3885 		fw.data_index = 0;
3886 		fw.data = bce_RXP_b06FwData;
3887 
3888 		fw.sbss_addr = bce_RXP_b06FwSbssAddr;
3889 		fw.sbss_len = bce_RXP_b06FwSbssLen;
3890 		fw.sbss_index = 0;
3891 		fw.sbss = bce_RXP_b06FwSbss;
3892 
3893 		fw.bss_addr = bce_RXP_b06FwBssAddr;
3894 		fw.bss_len = bce_RXP_b06FwBssLen;
3895 		fw.bss_index = 0;
3896 		fw.bss = bce_RXP_b06FwBss;
3897 
3898 		fw.rodata_addr = bce_RXP_b06FwRodataAddr;
3899 		fw.rodata_len = bce_RXP_b06FwRodataLen;
3900 		fw.rodata_index = 0;
3901 		fw.rodata = bce_RXP_b06FwRodata;
3902 	}
3903 
3904 	DBPRINT(sc, BCE_INFO_RESET, "Loading RX firmware.\n");
3905 	bce_load_cpu_fw(sc, &cpu_reg, &fw);
3906 
3907     /* Delay RXP start until initialization is complete. */
3908 
3909 	DBEXIT(BCE_VERBOSE_RESET);
3910 }
3911 
3912 
3913 /****************************************************************************/
3914 /* Initialize the TX CPU.                                                   */
3915 /*                                                                          */
3916 /* Returns:                                                                 */
3917 /*   Nothing.                                                               */
3918 /****************************************************************************/
3919 static void
3920 bce_init_txp_cpu(struct bce_softc *sc)
3921 {
3922 	struct cpu_reg cpu_reg;
3923 	struct fw_info fw;
3924 
3925 	DBENTER(BCE_VERBOSE_RESET);
3926 
3927 	cpu_reg.mode = BCE_TXP_CPU_MODE;
3928 	cpu_reg.mode_value_halt = BCE_TXP_CPU_MODE_SOFT_HALT;
3929 	cpu_reg.mode_value_sstep = BCE_TXP_CPU_MODE_STEP_ENA;
3930 	cpu_reg.state = BCE_TXP_CPU_STATE;
3931 	cpu_reg.state_value_clear = 0xffffff;
3932 	cpu_reg.gpr0 = BCE_TXP_CPU_REG_FILE;
3933 	cpu_reg.evmask = BCE_TXP_CPU_EVENT_MASK;
3934 	cpu_reg.pc = BCE_TXP_CPU_PROGRAM_COUNTER;
3935 	cpu_reg.inst = BCE_TXP_CPU_INSTRUCTION;
3936 	cpu_reg.bp = BCE_TXP_CPU_HW_BREAKPOINT;
3937 	cpu_reg.spad_base = BCE_TXP_SCRATCH;
3938 	cpu_reg.mips_view_base = 0x8000000;
3939 
3940 	if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
3941 		(BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
3942 		fw.ver_major = bce_TXP_b09FwReleaseMajor;
3943 		fw.ver_minor = bce_TXP_b09FwReleaseMinor;
3944 		fw.ver_fix = bce_TXP_b09FwReleaseFix;
3945 		fw.start_addr = bce_TXP_b09FwStartAddr;
3946 
3947 		fw.text_addr = bce_TXP_b09FwTextAddr;
3948 		fw.text_len = bce_TXP_b09FwTextLen;
3949 		fw.text_index = 0;
3950 		fw.text = bce_TXP_b09FwText;
3951 
3952 		fw.data_addr = bce_TXP_b09FwDataAddr;
3953 		fw.data_len = bce_TXP_b09FwDataLen;
3954 		fw.data_index = 0;
3955 		fw.data = bce_TXP_b09FwData;
3956 
3957 		fw.sbss_addr = bce_TXP_b09FwSbssAddr;
3958 		fw.sbss_len = bce_TXP_b09FwSbssLen;
3959 		fw.sbss_index = 0;
3960 		fw.sbss = bce_TXP_b09FwSbss;
3961 
3962 		fw.bss_addr = bce_TXP_b09FwBssAddr;
3963 		fw.bss_len = bce_TXP_b09FwBssLen;
3964 		fw.bss_index = 0;
3965 		fw.bss = bce_TXP_b09FwBss;
3966 
3967 		fw.rodata_addr = bce_TXP_b09FwRodataAddr;
3968 		fw.rodata_len = bce_TXP_b09FwRodataLen;
3969 		fw.rodata_index = 0;
3970 		fw.rodata = bce_TXP_b09FwRodata;
3971 	} else {
3972 		fw.ver_major = bce_TXP_b06FwReleaseMajor;
3973 		fw.ver_minor = bce_TXP_b06FwReleaseMinor;
3974 		fw.ver_fix = bce_TXP_b06FwReleaseFix;
3975 		fw.start_addr = bce_TXP_b06FwStartAddr;
3976 
3977 		fw.text_addr = bce_TXP_b06FwTextAddr;
3978 		fw.text_len = bce_TXP_b06FwTextLen;
3979 		fw.text_index = 0;
3980 		fw.text = bce_TXP_b06FwText;
3981 
3982 		fw.data_addr = bce_TXP_b06FwDataAddr;
3983 		fw.data_len = bce_TXP_b06FwDataLen;
3984 		fw.data_index = 0;
3985 		fw.data = bce_TXP_b06FwData;
3986 
3987 		fw.sbss_addr = bce_TXP_b06FwSbssAddr;
3988 		fw.sbss_len = bce_TXP_b06FwSbssLen;
3989 		fw.sbss_index = 0;
3990 		fw.sbss = bce_TXP_b06FwSbss;
3991 
3992 		fw.bss_addr = bce_TXP_b06FwBssAddr;
3993 		fw.bss_len = bce_TXP_b06FwBssLen;
3994 		fw.bss_index = 0;
3995 		fw.bss = bce_TXP_b06FwBss;
3996 
3997 		fw.rodata_addr = bce_TXP_b06FwRodataAddr;
3998 		fw.rodata_len = bce_TXP_b06FwRodataLen;
3999 		fw.rodata_index = 0;
4000 		fw.rodata = bce_TXP_b06FwRodata;
4001 	}
4002 
4003 	DBPRINT(sc, BCE_INFO_RESET, "Loading TX firmware.\n");
4004 	bce_load_cpu_fw(sc, &cpu_reg, &fw);
4005     bce_start_cpu(sc, &cpu_reg);
4006 
4007 	DBEXIT(BCE_VERBOSE_RESET);
4008 }
4009 
4010 
4011 /****************************************************************************/
4012 /* Initialize the TPAT CPU.                                                 */
4013 /*                                                                          */
4014 /* Returns:                                                                 */
4015 /*   Nothing.                                                               */
4016 /****************************************************************************/
4017 static void
4018 bce_init_tpat_cpu(struct bce_softc *sc)
4019 {
4020 	struct cpu_reg cpu_reg;
4021 	struct fw_info fw;
4022 
4023 	DBENTER(BCE_VERBOSE_RESET);
4024 
4025 	cpu_reg.mode = BCE_TPAT_CPU_MODE;
4026 	cpu_reg.mode_value_halt = BCE_TPAT_CPU_MODE_SOFT_HALT;
4027 	cpu_reg.mode_value_sstep = BCE_TPAT_CPU_MODE_STEP_ENA;
4028 	cpu_reg.state = BCE_TPAT_CPU_STATE;
4029 	cpu_reg.state_value_clear = 0xffffff;
4030 	cpu_reg.gpr0 = BCE_TPAT_CPU_REG_FILE;
4031 	cpu_reg.evmask = BCE_TPAT_CPU_EVENT_MASK;
4032 	cpu_reg.pc = BCE_TPAT_CPU_PROGRAM_COUNTER;
4033 	cpu_reg.inst = BCE_TPAT_CPU_INSTRUCTION;
4034 	cpu_reg.bp = BCE_TPAT_CPU_HW_BREAKPOINT;
4035 	cpu_reg.spad_base = BCE_TPAT_SCRATCH;
4036 	cpu_reg.mips_view_base = 0x8000000;
4037 
4038 	if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
4039 		(BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
4040 		fw.ver_major = bce_TPAT_b09FwReleaseMajor;
4041 		fw.ver_minor = bce_TPAT_b09FwReleaseMinor;
4042 		fw.ver_fix = bce_TPAT_b09FwReleaseFix;
4043 		fw.start_addr = bce_TPAT_b09FwStartAddr;
4044 
4045 		fw.text_addr = bce_TPAT_b09FwTextAddr;
4046 		fw.text_len = bce_TPAT_b09FwTextLen;
4047 		fw.text_index = 0;
4048 		fw.text = bce_TPAT_b09FwText;
4049 
4050 		fw.data_addr = bce_TPAT_b09FwDataAddr;
4051 		fw.data_len = bce_TPAT_b09FwDataLen;
4052 		fw.data_index = 0;
4053 		fw.data = bce_TPAT_b09FwData;
4054 
4055 		fw.sbss_addr = bce_TPAT_b09FwSbssAddr;
4056 		fw.sbss_len = bce_TPAT_b09FwSbssLen;
4057 		fw.sbss_index = 0;
4058 		fw.sbss = bce_TPAT_b09FwSbss;
4059 
4060 		fw.bss_addr = bce_TPAT_b09FwBssAddr;
4061 		fw.bss_len = bce_TPAT_b09FwBssLen;
4062 		fw.bss_index = 0;
4063 		fw.bss = bce_TPAT_b09FwBss;
4064 
4065 		fw.rodata_addr = bce_TPAT_b09FwRodataAddr;
4066 		fw.rodata_len = bce_TPAT_b09FwRodataLen;
4067 		fw.rodata_index = 0;
4068 		fw.rodata = bce_TPAT_b09FwRodata;
4069 	} else {
4070 		fw.ver_major = bce_TPAT_b06FwReleaseMajor;
4071 		fw.ver_minor = bce_TPAT_b06FwReleaseMinor;
4072 		fw.ver_fix = bce_TPAT_b06FwReleaseFix;
4073 		fw.start_addr = bce_TPAT_b06FwStartAddr;
4074 
4075 		fw.text_addr = bce_TPAT_b06FwTextAddr;
4076 		fw.text_len = bce_TPAT_b06FwTextLen;
4077 		fw.text_index = 0;
4078 		fw.text = bce_TPAT_b06FwText;
4079 
4080 		fw.data_addr = bce_TPAT_b06FwDataAddr;
4081 		fw.data_len = bce_TPAT_b06FwDataLen;
4082 		fw.data_index = 0;
4083 		fw.data = bce_TPAT_b06FwData;
4084 
4085 		fw.sbss_addr = bce_TPAT_b06FwSbssAddr;
4086 		fw.sbss_len = bce_TPAT_b06FwSbssLen;
4087 		fw.sbss_index = 0;
4088 		fw.sbss = bce_TPAT_b06FwSbss;
4089 
4090 		fw.bss_addr = bce_TPAT_b06FwBssAddr;
4091 		fw.bss_len = bce_TPAT_b06FwBssLen;
4092 		fw.bss_index = 0;
4093 		fw.bss = bce_TPAT_b06FwBss;
4094 
4095 		fw.rodata_addr = bce_TPAT_b06FwRodataAddr;
4096 		fw.rodata_len = bce_TPAT_b06FwRodataLen;
4097 		fw.rodata_index = 0;
4098 		fw.rodata = bce_TPAT_b06FwRodata;
4099 	}
4100 
4101 	DBPRINT(sc, BCE_INFO_RESET, "Loading TPAT firmware.\n");
4102 	bce_load_cpu_fw(sc, &cpu_reg, &fw);
4103 	bce_start_cpu(sc, &cpu_reg);
4104 
4105 	DBEXIT(BCE_VERBOSE_RESET);
4106 }
4107 
4108 
4109 /****************************************************************************/
4110 /* Initialize the CP CPU.                                                   */
4111 /*                                                                          */
4112 /* Returns:                                                                 */
4113 /*   Nothing.                                                               */
4114 /****************************************************************************/
4115 static void
4116 bce_init_cp_cpu(struct bce_softc *sc)
4117 {
4118 	struct cpu_reg cpu_reg;
4119 	struct fw_info fw;
4120 
4121 	DBENTER(BCE_VERBOSE_RESET);
4122 
4123 	cpu_reg.mode = BCE_CP_CPU_MODE;
4124 	cpu_reg.mode_value_halt = BCE_CP_CPU_MODE_SOFT_HALT;
4125 	cpu_reg.mode_value_sstep = BCE_CP_CPU_MODE_STEP_ENA;
4126 	cpu_reg.state = BCE_CP_CPU_STATE;
4127 	cpu_reg.state_value_clear = 0xffffff;
4128 	cpu_reg.gpr0 = BCE_CP_CPU_REG_FILE;
4129 	cpu_reg.evmask = BCE_CP_CPU_EVENT_MASK;
4130 	cpu_reg.pc = BCE_CP_CPU_PROGRAM_COUNTER;
4131 	cpu_reg.inst = BCE_CP_CPU_INSTRUCTION;
4132 	cpu_reg.bp = BCE_CP_CPU_HW_BREAKPOINT;
4133 	cpu_reg.spad_base = BCE_CP_SCRATCH;
4134 	cpu_reg.mips_view_base = 0x8000000;
4135 
4136 	if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
4137 		(BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
4138 		fw.ver_major = bce_CP_b09FwReleaseMajor;
4139 		fw.ver_minor = bce_CP_b09FwReleaseMinor;
4140 		fw.ver_fix = bce_CP_b09FwReleaseFix;
4141 		fw.start_addr = bce_CP_b09FwStartAddr;
4142 
4143 		fw.text_addr = bce_CP_b09FwTextAddr;
4144 		fw.text_len = bce_CP_b09FwTextLen;
4145 		fw.text_index = 0;
4146 		fw.text = bce_CP_b09FwText;
4147 
4148 		fw.data_addr = bce_CP_b09FwDataAddr;
4149 		fw.data_len = bce_CP_b09FwDataLen;
4150 		fw.data_index = 0;
4151 		fw.data = bce_CP_b09FwData;
4152 
4153 		fw.sbss_addr = bce_CP_b09FwSbssAddr;
4154 		fw.sbss_len = bce_CP_b09FwSbssLen;
4155 		fw.sbss_index = 0;
4156 		fw.sbss = bce_CP_b09FwSbss;
4157 
4158 		fw.bss_addr = bce_CP_b09FwBssAddr;
4159 		fw.bss_len = bce_CP_b09FwBssLen;
4160 		fw.bss_index = 0;
4161 		fw.bss = bce_CP_b09FwBss;
4162 
4163 		fw.rodata_addr = bce_CP_b09FwRodataAddr;
4164 		fw.rodata_len = bce_CP_b09FwRodataLen;
4165 		fw.rodata_index = 0;
4166 		fw.rodata = bce_CP_b09FwRodata;
4167 	} else {
4168 		fw.ver_major = bce_CP_b06FwReleaseMajor;
4169 		fw.ver_minor = bce_CP_b06FwReleaseMinor;
4170 		fw.ver_fix = bce_CP_b06FwReleaseFix;
4171 		fw.start_addr = bce_CP_b06FwStartAddr;
4172 
4173 		fw.text_addr = bce_CP_b06FwTextAddr;
4174 		fw.text_len = bce_CP_b06FwTextLen;
4175 		fw.text_index = 0;
4176 		fw.text = bce_CP_b06FwText;
4177 
4178 		fw.data_addr = bce_CP_b06FwDataAddr;
4179 		fw.data_len = bce_CP_b06FwDataLen;
4180 		fw.data_index = 0;
4181 		fw.data = bce_CP_b06FwData;
4182 
4183 		fw.sbss_addr = bce_CP_b06FwSbssAddr;
4184 		fw.sbss_len = bce_CP_b06FwSbssLen;
4185 		fw.sbss_index = 0;
4186 		fw.sbss = bce_CP_b06FwSbss;
4187 
4188 		fw.bss_addr = bce_CP_b06FwBssAddr;
4189 		fw.bss_len = bce_CP_b06FwBssLen;
4190 		fw.bss_index = 0;
4191 		fw.bss = bce_CP_b06FwBss;
4192 
4193 		fw.rodata_addr = bce_CP_b06FwRodataAddr;
4194 		fw.rodata_len = bce_CP_b06FwRodataLen;
4195 		fw.rodata_index = 0;
4196 		fw.rodata = bce_CP_b06FwRodata;
4197 	}
4198 
4199 	DBPRINT(sc, BCE_INFO_RESET, "Loading CP firmware.\n");
4200 	bce_load_cpu_fw(sc, &cpu_reg, &fw);
4201 	bce_start_cpu(sc, &cpu_reg);
4202 
4203 	DBEXIT(BCE_VERBOSE_RESET);
4204 }
4205 
4206 
4207 /****************************************************************************/
4208 /* Initialize the COM CPU.                                                 */
4209 /*                                                                          */
4210 /* Returns:                                                                 */
4211 /*   Nothing.                                                               */
4212 /****************************************************************************/
4213 static void
4214 bce_init_com_cpu(struct bce_softc *sc)
4215 {
4216 	struct cpu_reg cpu_reg;
4217 	struct fw_info fw;
4218 
4219 	DBENTER(BCE_VERBOSE_RESET);
4220 
4221 	cpu_reg.mode = BCE_COM_CPU_MODE;
4222 	cpu_reg.mode_value_halt = BCE_COM_CPU_MODE_SOFT_HALT;
4223 	cpu_reg.mode_value_sstep = BCE_COM_CPU_MODE_STEP_ENA;
4224 	cpu_reg.state = BCE_COM_CPU_STATE;
4225 	cpu_reg.state_value_clear = 0xffffff;
4226 	cpu_reg.gpr0 = BCE_COM_CPU_REG_FILE;
4227 	cpu_reg.evmask = BCE_COM_CPU_EVENT_MASK;
4228 	cpu_reg.pc = BCE_COM_CPU_PROGRAM_COUNTER;
4229 	cpu_reg.inst = BCE_COM_CPU_INSTRUCTION;
4230 	cpu_reg.bp = BCE_COM_CPU_HW_BREAKPOINT;
4231 	cpu_reg.spad_base = BCE_COM_SCRATCH;
4232 	cpu_reg.mips_view_base = 0x8000000;
4233 
4234 	if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
4235 		(BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
4236 		fw.ver_major = bce_COM_b09FwReleaseMajor;
4237 		fw.ver_minor = bce_COM_b09FwReleaseMinor;
4238 		fw.ver_fix = bce_COM_b09FwReleaseFix;
4239 		fw.start_addr = bce_COM_b09FwStartAddr;
4240 
4241 		fw.text_addr = bce_COM_b09FwTextAddr;
4242 		fw.text_len = bce_COM_b09FwTextLen;
4243 		fw.text_index = 0;
4244 		fw.text = bce_COM_b09FwText;
4245 
4246 		fw.data_addr = bce_COM_b09FwDataAddr;
4247 		fw.data_len = bce_COM_b09FwDataLen;
4248 		fw.data_index = 0;
4249 		fw.data = bce_COM_b09FwData;
4250 
4251 		fw.sbss_addr = bce_COM_b09FwSbssAddr;
4252 		fw.sbss_len = bce_COM_b09FwSbssLen;
4253 		fw.sbss_index = 0;
4254 		fw.sbss = bce_COM_b09FwSbss;
4255 
4256 		fw.bss_addr = bce_COM_b09FwBssAddr;
4257 		fw.bss_len = bce_COM_b09FwBssLen;
4258 		fw.bss_index = 0;
4259 		fw.bss = bce_COM_b09FwBss;
4260 
4261 		fw.rodata_addr = bce_COM_b09FwRodataAddr;
4262 		fw.rodata_len = bce_COM_b09FwRodataLen;
4263 		fw.rodata_index = 0;
4264 		fw.rodata = bce_COM_b09FwRodata;
4265 	} else {
4266 		fw.ver_major = bce_COM_b06FwReleaseMajor;
4267 		fw.ver_minor = bce_COM_b06FwReleaseMinor;
4268 		fw.ver_fix = bce_COM_b06FwReleaseFix;
4269 		fw.start_addr = bce_COM_b06FwStartAddr;
4270 
4271 		fw.text_addr = bce_COM_b06FwTextAddr;
4272 		fw.text_len = bce_COM_b06FwTextLen;
4273 		fw.text_index = 0;
4274 		fw.text = bce_COM_b06FwText;
4275 
4276 		fw.data_addr = bce_COM_b06FwDataAddr;
4277 		fw.data_len = bce_COM_b06FwDataLen;
4278 		fw.data_index = 0;
4279 		fw.data = bce_COM_b06FwData;
4280 
4281 		fw.sbss_addr = bce_COM_b06FwSbssAddr;
4282 		fw.sbss_len = bce_COM_b06FwSbssLen;
4283 		fw.sbss_index = 0;
4284 		fw.sbss = bce_COM_b06FwSbss;
4285 
4286 		fw.bss_addr = bce_COM_b06FwBssAddr;
4287 		fw.bss_len = bce_COM_b06FwBssLen;
4288 		fw.bss_index = 0;
4289 		fw.bss = bce_COM_b06FwBss;
4290 
4291 		fw.rodata_addr = bce_COM_b06FwRodataAddr;
4292 		fw.rodata_len = bce_COM_b06FwRodataLen;
4293 		fw.rodata_index = 0;
4294 		fw.rodata = bce_COM_b06FwRodata;
4295 	}
4296 
4297 	DBPRINT(sc, BCE_INFO_RESET, "Loading COM firmware.\n");
4298 	bce_load_cpu_fw(sc, &cpu_reg, &fw);
4299 	bce_start_cpu(sc, &cpu_reg);
4300 
4301 	DBEXIT(BCE_VERBOSE_RESET);
4302 }
4303 
4304 
4305 /****************************************************************************/
4306 /* Initialize the RV2P, RX, TX, TPAT, COM, and CP CPUs.                     */
4307 /*                                                                          */
4308 /* Loads the firmware for each CPU and starts the CPU.                      */
4309 /*                                                                          */
4310 /* Returns:                                                                 */
4311 /*   Nothing.                                                               */
4312 /****************************************************************************/
4313 static void
4314 bce_init_cpus(struct bce_softc *sc)
4315 {
4316 	DBENTER(BCE_VERBOSE_RESET);
4317 
4318 	if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
4319 		(BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
4320 
4321 		if ((BCE_CHIP_REV(sc) == BCE_CHIP_REV_Ax)) {
4322 			bce_load_rv2p_fw(sc, bce_xi90_rv2p_proc1,
4323 				sizeof(bce_xi90_rv2p_proc1), RV2P_PROC1);
4324 			bce_load_rv2p_fw(sc, bce_xi90_rv2p_proc2,
4325 				sizeof(bce_xi90_rv2p_proc2), RV2P_PROC2);
4326 		} else {
4327 			bce_load_rv2p_fw(sc, bce_xi_rv2p_proc1,
4328 				sizeof(bce_xi_rv2p_proc1), RV2P_PROC1);
4329 			bce_load_rv2p_fw(sc, bce_xi_rv2p_proc2,
4330 				sizeof(bce_xi_rv2p_proc2), RV2P_PROC2);
4331 		}
4332 
4333 	} else {
4334 		bce_load_rv2p_fw(sc, bce_rv2p_proc1,
4335 			sizeof(bce_rv2p_proc1),	RV2P_PROC1);
4336 		bce_load_rv2p_fw(sc, bce_rv2p_proc2,
4337 			sizeof(bce_rv2p_proc2),	RV2P_PROC2);
4338 	}
4339 
4340 	bce_init_rxp_cpu(sc);
4341 	bce_init_txp_cpu(sc);
4342 	bce_init_tpat_cpu(sc);
4343 	bce_init_com_cpu(sc);
4344 	bce_init_cp_cpu(sc);
4345 
4346 	DBEXIT(BCE_VERBOSE_RESET);
4347 }
4348 
4349 
4350 /****************************************************************************/
4351 /* Initialize context memory.                                               */
4352 /*                                                                          */
4353 /* Clears the memory associated with each Context ID (CID).                 */
4354 /*                                                                          */
4355 /* Returns:                                                                 */
4356 /*   Nothing.                                                               */
4357 /****************************************************************************/
4358 static void
4359 bce_init_ctx(struct bce_softc *sc)
4360 {
4361 
4362 	DBENTER(BCE_VERBOSE_RESET | BCE_VERBOSE_CTX);
4363 
4364 	if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
4365 	    (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
4366 		int i, retry_cnt = CTX_INIT_RETRY_COUNT;
4367 		u32 val;
4368 
4369 		DBPRINT(sc, BCE_INFO_CTX, "Initializing 5709 context.\n");
4370 
4371 		/*
4372 		 * BCM5709 context memory may be cached
4373 		 * in host memory so prepare the host memory
4374 		 * for access.
4375 		 */
4376 		val = BCE_CTX_COMMAND_ENABLED |
4377 		    BCE_CTX_COMMAND_MEM_INIT | (1 << 12);
4378 		val |= (BCM_PAGE_BITS - 8) << 16;
4379 		REG_WR(sc, BCE_CTX_COMMAND, val);
4380 
4381 		/* Wait for mem init command to complete. */
4382 		for (i = 0; i < retry_cnt; i++) {
4383 			val = REG_RD(sc, BCE_CTX_COMMAND);
4384 			if (!(val & BCE_CTX_COMMAND_MEM_INIT))
4385 				break;
4386 			DELAY(2);
4387 		}
4388 
4389 		/* ToDo: Consider returning an error here. */
4390 		DBRUNIF((val & BCE_CTX_COMMAND_MEM_INIT),
4391 		    BCE_PRINTF("%s(): Context memory initialization "
4392 		    "failed!\n", __FUNCTION__));
4393 
4394 		for (i = 0; i < sc->ctx_pages; i++) {
4395 			int j;
4396 
4397 			/* Set the physical address of the context memory. */
4398 			REG_WR(sc, BCE_CTX_HOST_PAGE_TBL_DATA0,
4399 			    BCE_ADDR_LO(sc->ctx_paddr[i] & 0xfffffff0) |
4400 			    BCE_CTX_HOST_PAGE_TBL_DATA0_VALID);
4401 			REG_WR(sc, BCE_CTX_HOST_PAGE_TBL_DATA1,
4402 			    BCE_ADDR_HI(sc->ctx_paddr[i]));
4403 			REG_WR(sc, BCE_CTX_HOST_PAGE_TBL_CTRL, i |
4404 			    BCE_CTX_HOST_PAGE_TBL_CTRL_WRITE_REQ);
4405 
4406 			/* Verify the context memory write was successful. */
4407 			for (j = 0; j < retry_cnt; j++) {
4408 				val = REG_RD(sc, BCE_CTX_HOST_PAGE_TBL_CTRL);
4409 				if ((val &
4410 				    BCE_CTX_HOST_PAGE_TBL_CTRL_WRITE_REQ) == 0)
4411 					break;
4412 				DELAY(5);
4413 			}
4414 
4415 			/* ToDo: Consider returning an error here. */
4416 			DBRUNIF((val & BCE_CTX_HOST_PAGE_TBL_CTRL_WRITE_REQ),
4417 			    BCE_PRINTF("%s(): Failed to initialize "
4418 			    "context page %d!\n", __FUNCTION__, i));
4419 		}
4420 	} else {
4421 		u32 vcid_addr, offset;
4422 
4423 		DBPRINT(sc, BCE_INFO, "Initializing 5706/5708 context.\n");
4424 
4425 		/*
4426 		 * For the 5706/5708, context memory is local to
4427 		 * the controller, so initialize the controller
4428 		 * context memory.
4429 		 */
4430 
4431 		vcid_addr = GET_CID_ADDR(96);
4432 		while (vcid_addr) {
4433 
4434 			vcid_addr -= PHY_CTX_SIZE;
4435 
4436 			REG_WR(sc, BCE_CTX_VIRT_ADDR, 0);
4437 			REG_WR(sc, BCE_CTX_PAGE_TBL, vcid_addr);
4438 
4439 			for(offset = 0; offset < PHY_CTX_SIZE; offset += 4) {
4440 				CTX_WR(sc, 0x00, offset, 0);
4441 			}
4442 
4443 			REG_WR(sc, BCE_CTX_VIRT_ADDR, vcid_addr);
4444 			REG_WR(sc, BCE_CTX_PAGE_TBL, vcid_addr);
4445 		}
4446 
4447 	}
4448 	DBEXIT(BCE_VERBOSE_RESET | BCE_VERBOSE_CTX);
4449 }
4450 
4451 
4452 /****************************************************************************/
4453 /* Fetch the permanent MAC address of the controller.                       */
4454 /*                                                                          */
4455 /* Returns:                                                                 */
4456 /*   Nothing.                                                               */
4457 /****************************************************************************/
4458 static void
4459 bce_get_mac_addr(struct bce_softc *sc)
4460 {
4461 	u32 mac_lo = 0, mac_hi = 0;
4462 
4463 	DBENTER(BCE_VERBOSE_RESET);
4464 	/*
4465 	 * The NetXtreme II bootcode populates various NIC
4466 	 * power-on and runtime configuration items in a
4467 	 * shared memory area.  The factory configured MAC
4468 	 * address is available from both NVRAM and the
4469 	 * shared memory area so we'll read the value from
4470 	 * shared memory for speed.
4471 	 */
4472 
4473 	mac_hi = bce_shmem_rd(sc, BCE_PORT_HW_CFG_MAC_UPPER);
4474 	mac_lo = bce_shmem_rd(sc, BCE_PORT_HW_CFG_MAC_LOWER);
4475 
4476 	if ((mac_lo == 0) && (mac_hi == 0)) {
4477 		BCE_PRINTF("%s(%d): Invalid Ethernet address!\n",
4478 			__FILE__, __LINE__);
4479 	} else {
4480 		sc->eaddr[0] = (u_char)(mac_hi >> 8);
4481 		sc->eaddr[1] = (u_char)(mac_hi >> 0);
4482 		sc->eaddr[2] = (u_char)(mac_lo >> 24);
4483 		sc->eaddr[3] = (u_char)(mac_lo >> 16);
4484 		sc->eaddr[4] = (u_char)(mac_lo >> 8);
4485 		sc->eaddr[5] = (u_char)(mac_lo >> 0);
4486 	}
4487 
4488 	DBPRINT(sc, BCE_INFO_MISC, "Permanent Ethernet address = %6D\n", sc->eaddr, ":");
4489 	DBEXIT(BCE_VERBOSE_RESET);
4490 }
4491 
4492 
4493 /****************************************************************************/
4494 /* Program the MAC address.                                                 */
4495 /*                                                                          */
4496 /* Returns:                                                                 */
4497 /*   Nothing.                                                               */
4498 /****************************************************************************/
4499 static void
4500 bce_set_mac_addr(struct bce_softc *sc)
4501 {
4502 	u32 val;
4503 	u8 *mac_addr = sc->eaddr;
4504 
4505 	/* ToDo: Add support for setting multiple MAC addresses. */
4506 
4507 	DBENTER(BCE_VERBOSE_RESET);
4508 	DBPRINT(sc, BCE_INFO_MISC, "Setting Ethernet address = %6D\n", sc->eaddr, ":");
4509 
4510 	val = (mac_addr[0] << 8) | mac_addr[1];
4511 
4512 	REG_WR(sc, BCE_EMAC_MAC_MATCH0, val);
4513 
4514 	val = (mac_addr[2] << 24) | (mac_addr[3] << 16) |
4515 		(mac_addr[4] << 8) | mac_addr[5];
4516 
4517 	REG_WR(sc, BCE_EMAC_MAC_MATCH1, val);
4518 
4519 	DBEXIT(BCE_VERBOSE_RESET);
4520 }
4521 
4522 
4523 /****************************************************************************/
4524 /* Stop the controller.                                                     */
4525 /*                                                                          */
4526 /* Returns:                                                                 */
4527 /*   Nothing.                                                               */
4528 /****************************************************************************/
4529 static void
4530 bce_stop(struct bce_softc *sc)
4531 {
4532 	struct ifnet *ifp;
4533 	struct ifmedia_entry *ifm;
4534 	struct mii_data *mii = NULL;
4535 	int mtmp, itmp;
4536 
4537 	DBENTER(BCE_VERBOSE_RESET);
4538 
4539 	BCE_LOCK_ASSERT(sc);
4540 
4541 	ifp = sc->bce_ifp;
4542 
4543 	mii = device_get_softc(sc->bce_miibus);
4544 
4545 	callout_stop(&sc->bce_tick_callout);
4546 
4547 	/* Disable the transmit/receive blocks. */
4548 	REG_WR(sc, BCE_MISC_ENABLE_CLR_BITS, BCE_MISC_ENABLE_CLR_DEFAULT);
4549 	REG_RD(sc, BCE_MISC_ENABLE_CLR_BITS);
4550 	DELAY(20);
4551 
4552 	bce_disable_intr(sc);
4553 
4554 	/* Free RX buffers. */
4555 #ifdef BCE_JUMBO_HDRSPLIT
4556 	bce_free_pg_chain(sc);
4557 #endif
4558 	bce_free_rx_chain(sc);
4559 
4560 	/* Free TX buffers. */
4561 	bce_free_tx_chain(sc);
4562 
4563 	/*
4564 	 * Isolate/power down the PHY, but leave the media selection
4565 	 * unchanged so that things will be put back to normal when
4566 	 * we bring the interface back up.
4567 	 */
4568 
4569 	itmp = ifp->if_flags;
4570 	ifp->if_flags |= IFF_UP;
4571 
4572 	/* If we are called from bce_detach(), mii is already NULL. */
4573 	if (mii != NULL) {
4574 		ifm = mii->mii_media.ifm_cur;
4575 		mtmp = ifm->ifm_media;
4576 		ifm->ifm_media = IFM_ETHER | IFM_NONE;
4577 		mii_mediachg(mii);
4578 		ifm->ifm_media = mtmp;
4579 	}
4580 
4581 	ifp->if_flags = itmp;
4582 	sc->watchdog_timer = 0;
4583 
4584 	sc->bce_link_up = FALSE;
4585 
4586 	ifp->if_drv_flags &= ~(IFF_DRV_RUNNING | IFF_DRV_OACTIVE);
4587 
4588 	DBEXIT(BCE_VERBOSE_RESET);
4589 }
4590 
4591 
4592 static int
4593 bce_reset(struct bce_softc *sc, u32 reset_code)
4594 {
4595 	u32 val;
4596 	int i, rc = 0;
4597 
4598 	DBENTER(BCE_VERBOSE_RESET);
4599 
4600 	DBPRINT(sc, BCE_VERBOSE_RESET, "%s(): reset_code = 0x%08X\n",
4601 		__FUNCTION__, reset_code);
4602 
4603 	/* Wait for pending PCI transactions to complete. */
4604 	REG_WR(sc, BCE_MISC_ENABLE_CLR_BITS,
4605 	       BCE_MISC_ENABLE_CLR_BITS_TX_DMA_ENABLE |
4606 	       BCE_MISC_ENABLE_CLR_BITS_DMA_ENGINE_ENABLE |
4607 	       BCE_MISC_ENABLE_CLR_BITS_RX_DMA_ENABLE |
4608 	       BCE_MISC_ENABLE_CLR_BITS_HOST_COALESCE_ENABLE);
4609 	val = REG_RD(sc, BCE_MISC_ENABLE_CLR_BITS);
4610 	DELAY(5);
4611 
4612 	/* Disable DMA */
4613 	if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
4614 		(BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
4615 		val = REG_RD(sc, BCE_MISC_NEW_CORE_CTL);
4616 		val &= ~BCE_MISC_NEW_CORE_CTL_DMA_ENABLE;
4617 		REG_WR(sc, BCE_MISC_NEW_CORE_CTL, val);
4618 	}
4619 
4620 	/* Assume bootcode is running. */
4621 	sc->bce_fw_timed_out = FALSE;
4622 	sc->bce_drv_cardiac_arrest = FALSE;
4623 
4624 	/* Give the firmware a chance to prepare for the reset. */
4625 	rc = bce_fw_sync(sc, BCE_DRV_MSG_DATA_WAIT0 | reset_code);
4626 	if (rc)
4627 		goto bce_reset_exit;
4628 
4629 	/* Set a firmware reminder that this is a soft reset. */
4630 	bce_shmem_wr(sc, BCE_DRV_RESET_SIGNATURE, BCE_DRV_RESET_SIGNATURE_MAGIC);
4631 
4632 	/* Dummy read to force the chip to complete all current transactions. */
4633 	val = REG_RD(sc, BCE_MISC_ID);
4634 
4635 	/* Chip reset. */
4636 	if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
4637 		(BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
4638 		REG_WR(sc, BCE_MISC_COMMAND, BCE_MISC_COMMAND_SW_RESET);
4639 		REG_RD(sc, BCE_MISC_COMMAND);
4640 		DELAY(5);
4641 
4642 		val = BCE_PCICFG_MISC_CONFIG_REG_WINDOW_ENA |
4643 		      BCE_PCICFG_MISC_CONFIG_TARGET_MB_WORD_SWAP;
4644 
4645 		pci_write_config(sc->bce_dev, BCE_PCICFG_MISC_CONFIG, val, 4);
4646 	} else {
4647 		val = BCE_PCICFG_MISC_CONFIG_CORE_RST_REQ |
4648 			BCE_PCICFG_MISC_CONFIG_REG_WINDOW_ENA |
4649 			BCE_PCICFG_MISC_CONFIG_TARGET_MB_WORD_SWAP;
4650 		REG_WR(sc, BCE_PCICFG_MISC_CONFIG, val);
4651 
4652 		/* Allow up to 30us for reset to complete. */
4653 		for (i = 0; i < 10; i++) {
4654 			val = REG_RD(sc, BCE_PCICFG_MISC_CONFIG);
4655 			if ((val & (BCE_PCICFG_MISC_CONFIG_CORE_RST_REQ |
4656 				BCE_PCICFG_MISC_CONFIG_CORE_RST_BSY)) == 0) {
4657 				break;
4658 			}
4659 			DELAY(10);
4660 		}
4661 
4662 		/* Check that reset completed successfully. */
4663 		if (val & (BCE_PCICFG_MISC_CONFIG_CORE_RST_REQ |
4664 			BCE_PCICFG_MISC_CONFIG_CORE_RST_BSY)) {
4665 			BCE_PRINTF("%s(%d): Reset failed!\n",
4666 				__FILE__, __LINE__);
4667 			rc = EBUSY;
4668 			goto bce_reset_exit;
4669 		}
4670 	}
4671 
4672 	/* Make sure byte swapping is properly configured. */
4673 	val = REG_RD(sc, BCE_PCI_SWAP_DIAG0);
4674 	if (val != 0x01020304) {
4675 		BCE_PRINTF("%s(%d): Byte swap is incorrect!\n",
4676 			__FILE__, __LINE__);
4677 		rc = ENODEV;
4678 		goto bce_reset_exit;
4679 	}
4680 
4681 	/* Just completed a reset, assume that firmware is running again. */
4682 	sc->bce_fw_timed_out = FALSE;
4683 	sc->bce_drv_cardiac_arrest = FALSE;
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 additional fixes before enabling MAC. */
4930 	rc = bce_fw_sync(sc, BCE_DRV_MSG_DATA_WAIT2 |
4931 	    BCE_DRV_MSG_CODE_RESET);
4932 
4933 	/* Enable link state change interrupt generation. */
4934 	REG_WR(sc, BCE_HC_ATTN_BITS_ENABLE, STATUS_ATTN_BITS_LINK_STATE);
4935 
4936 	/* Enable the RXP. */
4937 	bce_start_rxp_cpu(sc);
4938 
4939 	/* Disable management frames (NC-SI) from flowing to the MCP. */
4940 	if (sc->bce_flags & BCE_MFW_ENABLE_FLAG) {
4941 		val = REG_RD(sc, BCE_RPM_MGMT_PKT_CTRL) &
4942 		    ~BCE_RPM_MGMT_PKT_CTRL_MGMT_EN;
4943 		REG_WR(sc, BCE_RPM_MGMT_PKT_CTRL, val);
4944 	}
4945 
4946 	/* Enable all remaining blocks in the MAC. */
4947 	if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
4948 	    (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716))
4949 		REG_WR(sc, BCE_MISC_ENABLE_SET_BITS,
4950 		    BCE_MISC_ENABLE_DEFAULT_XI);
4951 	else
4952 		REG_WR(sc, BCE_MISC_ENABLE_SET_BITS,
4953 		    BCE_MISC_ENABLE_DEFAULT);
4954 
4955 	REG_RD(sc, BCE_MISC_ENABLE_SET_BITS);
4956 	DELAY(20);
4957 
4958 	/* Save the current host coalescing block settings. */
4959 	sc->hc_command = REG_RD(sc, BCE_HC_COMMAND);
4960 
4961 bce_blockinit_exit:
4962 	DBEXIT(BCE_VERBOSE_RESET);
4963 
4964 	return (rc);
4965 }
4966 
4967 
4968 /****************************************************************************/
4969 /* Encapsulate an mbuf into the rx_bd chain.                                */
4970 /*                                                                          */
4971 /* Returns:                                                                 */
4972 /*   0 for success, positive value for failure.                             */
4973 /****************************************************************************/
4974 static int
4975 bce_get_rx_buf(struct bce_softc *sc, struct mbuf *m, u16 *prod,
4976     u16 *chain_prod, u32 *prod_bseq)
4977 {
4978 	bus_dmamap_t map;
4979 	bus_dma_segment_t segs[BCE_MAX_SEGMENTS];
4980 	struct mbuf *m_new = NULL;
4981 	struct rx_bd *rxbd;
4982 	int nsegs, error, rc = 0;
4983 #ifdef BCE_DEBUG
4984 	u16 debug_chain_prod = *chain_prod;
4985 #endif
4986 
4987 	DBENTER(BCE_EXTREME_RESET | BCE_EXTREME_RECV | BCE_EXTREME_LOAD);
4988 
4989 	/* Make sure the inputs are valid. */
4990 	DBRUNIF((*chain_prod > MAX_RX_BD),
4991 		BCE_PRINTF("%s(%d): RX producer out of range: 0x%04X > 0x%04X\n",
4992 		__FILE__, __LINE__, *chain_prod, (u16) MAX_RX_BD));
4993 
4994 	DBPRINT(sc, BCE_EXTREME_RECV, "%s(enter): prod = 0x%04X, "
4995 	    "chain_prod = 0x%04X, prod_bseq = 0x%08X\n", __FUNCTION__,
4996 	    *prod, *chain_prod, *prod_bseq);
4997 
4998 	/* Update some debug statistic counters */
4999 	DBRUNIF((sc->free_rx_bd < sc->rx_low_watermark),
5000 		sc->rx_low_watermark = sc->free_rx_bd);
5001 	DBRUNIF((sc->free_rx_bd == sc->max_rx_bd), sc->rx_empty_count++);
5002 
5003 	/* Check whether this is a new mbuf allocation. */
5004 	if (m == NULL) {
5005 
5006 		/* Simulate an mbuf allocation failure. */
5007 		DBRUNIF(DB_RANDOMTRUE(mbuf_alloc_failed_sim_control),
5008 		    sc->mbuf_alloc_failed_count++;
5009 		    sc->mbuf_alloc_failed_sim_count++;
5010 		    rc = ENOBUFS;
5011 		    goto bce_get_rx_buf_exit);
5012 
5013 		/* This is a new mbuf allocation. */
5014 #ifdef BCE_JUMBO_HDRSPLIT
5015 		MGETHDR(m_new, M_DONTWAIT, MT_DATA);
5016 #else
5017 		if (sc->rx_bd_mbuf_alloc_size <= MCLBYTES)
5018 			m_new = m_getcl(M_DONTWAIT, MT_DATA, M_PKTHDR);
5019 		else
5020 			m_new = m_getjcl(M_DONTWAIT, MT_DATA, M_PKTHDR,
5021 			    sc->rx_bd_mbuf_alloc_size);
5022 #endif
5023 
5024 		if (m_new == NULL) {
5025 			sc->mbuf_alloc_failed_count++;
5026 			rc = ENOBUFS;
5027 			goto bce_get_rx_buf_exit;
5028 		}
5029 
5030 		DBRUN(sc->debug_rx_mbuf_alloc++);
5031 	} else {
5032 		/* Reuse an existing mbuf. */
5033 		m_new = m;
5034 	}
5035 
5036 	/* Make sure we have a valid packet header. */
5037 	M_ASSERTPKTHDR(m_new);
5038 
5039 	/* Initialize the mbuf size and pad if necessary for alignment. */
5040 	m_new->m_pkthdr.len = m_new->m_len = sc->rx_bd_mbuf_alloc_size;
5041 	m_adj(m_new, sc->rx_bd_mbuf_align_pad);
5042 
5043 	/* ToDo: Consider calling m_fragment() to test error handling. */
5044 
5045 	/* Map the mbuf cluster into device memory. */
5046 	map = sc->rx_mbuf_map[*chain_prod];
5047 	error = bus_dmamap_load_mbuf_sg(sc->rx_mbuf_tag, map, m_new,
5048 	    segs, &nsegs, BUS_DMA_NOWAIT);
5049 
5050 	/* Handle any mapping errors. */
5051 	if (error) {
5052 		BCE_PRINTF("%s(%d): Error mapping mbuf into RX chain (%d)!\n",
5053 		    __FILE__, __LINE__, error);
5054 
5055 		sc->dma_map_addr_rx_failed_count++;
5056 		m_freem(m_new);
5057 
5058 		DBRUN(sc->debug_rx_mbuf_alloc--);
5059 
5060 		rc = ENOBUFS;
5061 		goto bce_get_rx_buf_exit;
5062 	}
5063 
5064 	/* All mbufs must map to a single segment. */
5065 	KASSERT(nsegs == 1, ("%s(): Too many segments returned (%d)!",
5066 	    __FUNCTION__, nsegs));
5067 
5068 	/* Setup the rx_bd for the segment. */
5069 	rxbd = &sc->rx_bd_chain[RX_PAGE(*chain_prod)][RX_IDX(*chain_prod)];
5070 
5071 	rxbd->rx_bd_haddr_lo  = htole32(BCE_ADDR_LO(segs[0].ds_addr));
5072 	rxbd->rx_bd_haddr_hi  = htole32(BCE_ADDR_HI(segs[0].ds_addr));
5073 	rxbd->rx_bd_len       = htole32(segs[0].ds_len);
5074 	rxbd->rx_bd_flags     = htole32(RX_BD_FLAGS_START | RX_BD_FLAGS_END);
5075 	*prod_bseq += segs[0].ds_len;
5076 
5077 	/* Save the mbuf and update our counter. */
5078 	sc->rx_mbuf_ptr[*chain_prod] = m_new;
5079 	sc->free_rx_bd -= nsegs;
5080 
5081 	DBRUNMSG(BCE_INSANE_RECV,
5082 	    bce_dump_rx_mbuf_chain(sc, debug_chain_prod, nsegs));
5083 
5084 	DBPRINT(sc, BCE_EXTREME_RECV, "%s(exit): prod = 0x%04X, "
5085 	    "chain_prod = 0x%04X, prod_bseq = 0x%08X\n",
5086 	    __FUNCTION__, *prod, *chain_prod, *prod_bseq);
5087 
5088 bce_get_rx_buf_exit:
5089 	DBEXIT(BCE_EXTREME_RESET | BCE_EXTREME_RECV | BCE_EXTREME_LOAD);
5090 
5091 	return(rc);
5092 }
5093 
5094 
5095 #ifdef BCE_JUMBO_HDRSPLIT
5096 /****************************************************************************/
5097 /* Encapsulate an mbuf cluster into the page chain.                         */
5098 /*                                                                          */
5099 /* Returns:                                                                 */
5100 /*   0 for success, positive value for failure.                             */
5101 /****************************************************************************/
5102 static int
5103 bce_get_pg_buf(struct bce_softc *sc, struct mbuf *m, u16 *prod,
5104 	u16 *prod_idx)
5105 {
5106 	bus_dmamap_t map;
5107 	bus_addr_t busaddr;
5108 	struct mbuf *m_new = NULL;
5109 	struct rx_bd *pgbd;
5110 	int error, rc = 0;
5111 #ifdef BCE_DEBUG
5112 	u16 debug_prod_idx = *prod_idx;
5113 #endif
5114 
5115 	DBENTER(BCE_EXTREME_RESET | BCE_EXTREME_RECV | BCE_EXTREME_LOAD);
5116 
5117 	/* Make sure the inputs are valid. */
5118 	DBRUNIF((*prod_idx > MAX_PG_BD),
5119 	    BCE_PRINTF("%s(%d): page producer out of range: 0x%04X > 0x%04X\n",
5120 	    __FILE__, __LINE__, *prod_idx, (u16) MAX_PG_BD));
5121 
5122 	DBPRINT(sc, BCE_EXTREME_RECV, "%s(enter): prod = 0x%04X, "
5123 	    "chain_prod = 0x%04X\n", __FUNCTION__, *prod, *prod_idx);
5124 
5125 	/* Update counters if we've hit a new low or run out of pages. */
5126 	DBRUNIF((sc->free_pg_bd < sc->pg_low_watermark),
5127 	    sc->pg_low_watermark = sc->free_pg_bd);
5128 	DBRUNIF((sc->free_pg_bd == sc->max_pg_bd), sc->pg_empty_count++);
5129 
5130 	/* Check whether this is a new mbuf allocation. */
5131 	if (m == NULL) {
5132 
5133 		/* Simulate an mbuf allocation failure. */
5134 		DBRUNIF(DB_RANDOMTRUE(mbuf_alloc_failed_sim_control),
5135 		    sc->mbuf_alloc_failed_count++;
5136 		    sc->mbuf_alloc_failed_sim_count++;
5137 		    rc = ENOBUFS;
5138 		    goto bce_get_pg_buf_exit);
5139 
5140 		/* This is a new mbuf allocation. */
5141 		m_new = m_getcl(M_DONTWAIT, MT_DATA, 0);
5142 		if (m_new == NULL) {
5143 			sc->mbuf_alloc_failed_count++;
5144 			rc = ENOBUFS;
5145 			goto bce_get_pg_buf_exit;
5146 		}
5147 
5148 		DBRUN(sc->debug_pg_mbuf_alloc++);
5149 	} else {
5150 		/* Reuse an existing mbuf. */
5151 		m_new = m;
5152 		m_new->m_data = m_new->m_ext.ext_buf;
5153 	}
5154 
5155 	m_new->m_len = sc->pg_bd_mbuf_alloc_size;
5156 
5157 	/* ToDo: Consider calling m_fragment() to test error handling. */
5158 
5159 	/* Map the mbuf cluster into device memory. */
5160 	map = sc->pg_mbuf_map[*prod_idx];
5161 	error = bus_dmamap_load(sc->pg_mbuf_tag, map, mtod(m_new, void *),
5162 	    sc->pg_bd_mbuf_alloc_size, bce_dma_map_addr,
5163 	    &busaddr, BUS_DMA_NOWAIT);
5164 
5165 	/* Handle any mapping errors. */
5166 	if (error) {
5167 		BCE_PRINTF("%s(%d): Error mapping mbuf into page chain!\n",
5168 		    __FILE__, __LINE__);
5169 
5170 		m_freem(m_new);
5171 		DBRUN(sc->debug_pg_mbuf_alloc--);
5172 
5173 		rc = ENOBUFS;
5174 		goto bce_get_pg_buf_exit;
5175 	}
5176 
5177 	/* ToDo: Do we need bus_dmamap_sync(,,BUS_DMASYNC_PREREAD) here? */
5178 
5179 	/*
5180 	 * The page chain uses the same rx_bd data structure
5181 	 * as the receive chain but doesn't require a byte sequence (bseq).
5182 	 */
5183 	pgbd = &sc->pg_bd_chain[PG_PAGE(*prod_idx)][PG_IDX(*prod_idx)];
5184 
5185 	pgbd->rx_bd_haddr_lo  = htole32(BCE_ADDR_LO(busaddr));
5186 	pgbd->rx_bd_haddr_hi  = htole32(BCE_ADDR_HI(busaddr));
5187 	pgbd->rx_bd_len       = htole32(sc->pg_bd_mbuf_alloc_size);
5188 	pgbd->rx_bd_flags     = htole32(RX_BD_FLAGS_START | RX_BD_FLAGS_END);
5189 
5190 	/* Save the mbuf and update our counter. */
5191 	sc->pg_mbuf_ptr[*prod_idx] = m_new;
5192 	sc->free_pg_bd--;
5193 
5194 	DBRUNMSG(BCE_INSANE_RECV,
5195 	    bce_dump_pg_mbuf_chain(sc, debug_prod_idx, 1));
5196 
5197 	DBPRINT(sc, BCE_EXTREME_RECV, "%s(exit): prod = 0x%04X, "
5198 	    "prod_idx = 0x%04X\n", __FUNCTION__, *prod, *prod_idx);
5199 
5200 bce_get_pg_buf_exit:
5201 	DBEXIT(BCE_EXTREME_RESET | BCE_EXTREME_RECV | BCE_EXTREME_LOAD);
5202 
5203 	return(rc);
5204 }
5205 #endif /* BCE_JUMBO_HDRSPLIT */
5206 
5207 
5208 /****************************************************************************/
5209 /* Initialize the TX context memory.                                        */
5210 /*                                                                          */
5211 /* Returns:                                                                 */
5212 /*   Nothing                                                                */
5213 /****************************************************************************/
5214 static void
5215 bce_init_tx_context(struct bce_softc *sc)
5216 {
5217 	u32 val;
5218 
5219 	DBENTER(BCE_VERBOSE_RESET | BCE_VERBOSE_SEND | BCE_VERBOSE_CTX);
5220 
5221 	/* Initialize the context ID for an L2 TX chain. */
5222 	if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
5223 		(BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
5224 		/* Set the CID type to support an L2 connection. */
5225 		val = BCE_L2CTX_TX_TYPE_TYPE_L2_XI |
5226 		    BCE_L2CTX_TX_TYPE_SIZE_L2_XI;
5227 		CTX_WR(sc, GET_CID_ADDR(TX_CID), BCE_L2CTX_TX_TYPE_XI, val);
5228 		val = BCE_L2CTX_TX_CMD_TYPE_TYPE_L2_XI | (8 << 16);
5229 		CTX_WR(sc, GET_CID_ADDR(TX_CID),
5230 		    BCE_L2CTX_TX_CMD_TYPE_XI, val);
5231 
5232 		/* Point the hardware to the first page in the chain. */
5233 		val = BCE_ADDR_HI(sc->tx_bd_chain_paddr[0]);
5234 		CTX_WR(sc, GET_CID_ADDR(TX_CID),
5235 		    BCE_L2CTX_TX_TBDR_BHADDR_HI_XI, val);
5236 		val = BCE_ADDR_LO(sc->tx_bd_chain_paddr[0]);
5237 		CTX_WR(sc, GET_CID_ADDR(TX_CID),
5238 		    BCE_L2CTX_TX_TBDR_BHADDR_LO_XI, val);
5239 	} else {
5240 		/* Set the CID type to support an L2 connection. */
5241 		val = BCE_L2CTX_TX_TYPE_TYPE_L2 | BCE_L2CTX_TX_TYPE_SIZE_L2;
5242 		CTX_WR(sc, GET_CID_ADDR(TX_CID), BCE_L2CTX_TX_TYPE, val);
5243 		val = BCE_L2CTX_TX_CMD_TYPE_TYPE_L2 | (8 << 16);
5244 		CTX_WR(sc, GET_CID_ADDR(TX_CID), BCE_L2CTX_TX_CMD_TYPE, val);
5245 
5246 		/* Point the hardware to the first page in the chain. */
5247 		val = BCE_ADDR_HI(sc->tx_bd_chain_paddr[0]);
5248 		CTX_WR(sc, GET_CID_ADDR(TX_CID),
5249 		    BCE_L2CTX_TX_TBDR_BHADDR_HI, val);
5250 		val = BCE_ADDR_LO(sc->tx_bd_chain_paddr[0]);
5251 		CTX_WR(sc, GET_CID_ADDR(TX_CID),
5252 		    BCE_L2CTX_TX_TBDR_BHADDR_LO, val);
5253 	}
5254 
5255 	DBEXIT(BCE_VERBOSE_RESET | BCE_VERBOSE_SEND | BCE_VERBOSE_CTX);
5256 }
5257 
5258 
5259 /****************************************************************************/
5260 /* Allocate memory and initialize the TX data structures.                   */
5261 /*                                                                          */
5262 /* Returns:                                                                 */
5263 /*   0 for success, positive value for failure.                             */
5264 /****************************************************************************/
5265 static int
5266 bce_init_tx_chain(struct bce_softc *sc)
5267 {
5268 	struct tx_bd *txbd;
5269 	int i, rc = 0;
5270 
5271 	DBENTER(BCE_VERBOSE_RESET | BCE_VERBOSE_SEND | BCE_VERBOSE_LOAD);
5272 
5273 	/* Set the initial TX producer/consumer indices. */
5274 	sc->tx_prod        = 0;
5275 	sc->tx_cons        = 0;
5276 	sc->tx_prod_bseq   = 0;
5277 	sc->used_tx_bd     = 0;
5278 	sc->max_tx_bd      = USABLE_TX_BD;
5279 	DBRUN(sc->tx_hi_watermark = 0);
5280 	DBRUN(sc->tx_full_count = 0);
5281 
5282 	/*
5283 	 * The NetXtreme II supports a linked-list structre called
5284 	 * a Buffer Descriptor Chain (or BD chain).  A BD chain
5285 	 * consists of a series of 1 or more chain pages, each of which
5286 	 * consists of a fixed number of BD entries.
5287 	 * The last BD entry on each page is a pointer to the next page
5288 	 * in the chain, and the last pointer in the BD chain
5289 	 * points back to the beginning of the chain.
5290 	 */
5291 
5292 	/* Set the TX next pointer chain entries. */
5293 	for (i = 0; i < TX_PAGES; i++) {
5294 		int j;
5295 
5296 		txbd = &sc->tx_bd_chain[i][USABLE_TX_BD_PER_PAGE];
5297 
5298 		/* Check if we've reached the last page. */
5299 		if (i == (TX_PAGES - 1))
5300 			j = 0;
5301 		else
5302 			j = i + 1;
5303 
5304 		txbd->tx_bd_haddr_hi = htole32(BCE_ADDR_HI(sc->tx_bd_chain_paddr[j]));
5305 		txbd->tx_bd_haddr_lo = htole32(BCE_ADDR_LO(sc->tx_bd_chain_paddr[j]));
5306 	}
5307 
5308 	bce_init_tx_context(sc);
5309 
5310 	DBRUNMSG(BCE_INSANE_SEND, bce_dump_tx_chain(sc, 0, TOTAL_TX_BD));
5311 	DBEXIT(BCE_VERBOSE_RESET | BCE_VERBOSE_SEND | BCE_VERBOSE_LOAD);
5312 
5313 	return(rc);
5314 }
5315 
5316 
5317 /****************************************************************************/
5318 /* Free memory and clear the TX data structures.                            */
5319 /*                                                                          */
5320 /* Returns:                                                                 */
5321 /*   Nothing.                                                               */
5322 /****************************************************************************/
5323 static void
5324 bce_free_tx_chain(struct bce_softc *sc)
5325 {
5326 	int i;
5327 
5328 	DBENTER(BCE_VERBOSE_RESET | BCE_VERBOSE_SEND | BCE_VERBOSE_UNLOAD);
5329 
5330 	/* Unmap, unload, and free any mbufs still in the TX mbuf chain. */
5331 	for (i = 0; i < TOTAL_TX_BD; i++) {
5332 		if (sc->tx_mbuf_ptr[i] != NULL) {
5333 			if (sc->tx_mbuf_map[i] != NULL)
5334 				bus_dmamap_sync(sc->tx_mbuf_tag,
5335 				    sc->tx_mbuf_map[i],
5336 				    BUS_DMASYNC_POSTWRITE);
5337 			m_freem(sc->tx_mbuf_ptr[i]);
5338 			sc->tx_mbuf_ptr[i] = NULL;
5339 			DBRUN(sc->debug_tx_mbuf_alloc--);
5340 		}
5341 	}
5342 
5343 	/* Clear each TX chain page. */
5344 	for (i = 0; i < TX_PAGES; i++)
5345 		bzero((char *)sc->tx_bd_chain[i], BCE_TX_CHAIN_PAGE_SZ);
5346 
5347 	sc->used_tx_bd = 0;
5348 
5349 	/* Check if we lost any mbufs in the process. */
5350 	DBRUNIF((sc->debug_tx_mbuf_alloc),
5351 	    BCE_PRINTF("%s(%d): Memory leak! Lost %d mbufs "
5352 	    "from tx chain!\n",	__FILE__, __LINE__,
5353 	    sc->debug_tx_mbuf_alloc));
5354 
5355 	DBEXIT(BCE_VERBOSE_RESET | BCE_VERBOSE_SEND | BCE_VERBOSE_UNLOAD);
5356 }
5357 
5358 
5359 /****************************************************************************/
5360 /* Initialize the RX context memory.                                        */
5361 /*                                                                          */
5362 /* Returns:                                                                 */
5363 /*   Nothing                                                                */
5364 /****************************************************************************/
5365 static void
5366 bce_init_rx_context(struct bce_softc *sc)
5367 {
5368 	u32 val;
5369 
5370 	DBENTER(BCE_VERBOSE_RESET | BCE_VERBOSE_RECV | BCE_VERBOSE_CTX);
5371 
5372 	/* Init the type, size, and BD cache levels for the RX context. */
5373 	val = BCE_L2CTX_RX_CTX_TYPE_CTX_BD_CHN_TYPE_VALUE |
5374 	    BCE_L2CTX_RX_CTX_TYPE_SIZE_L2 |
5375 	    (0x02 << BCE_L2CTX_RX_BD_PRE_READ_SHIFT);
5376 
5377 	/*
5378 	 * Set the level for generating pause frames
5379 	 * when the number of available rx_bd's gets
5380 	 * too low (the low watermark) and the level
5381 	 * when pause frames can be stopped (the high
5382 	 * watermark).
5383 	 */
5384 	if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
5385 	    (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
5386 		u32 lo_water, hi_water;
5387 
5388 		lo_water = BCE_L2CTX_RX_LO_WATER_MARK_DEFAULT;
5389 		hi_water = USABLE_RX_BD / 4;
5390 
5391 		lo_water /= BCE_L2CTX_RX_LO_WATER_MARK_SCALE;
5392 		hi_water /= BCE_L2CTX_RX_HI_WATER_MARK_SCALE;
5393 
5394 		if (hi_water > 0xf)
5395 			hi_water = 0xf;
5396 		else if (hi_water == 0)
5397 			lo_water = 0;
5398 		val |= (lo_water << BCE_L2CTX_RX_LO_WATER_MARK_SHIFT) |
5399 			(hi_water << BCE_L2CTX_RX_HI_WATER_MARK_SHIFT);
5400 	}
5401 
5402  	CTX_WR(sc, GET_CID_ADDR(RX_CID), BCE_L2CTX_RX_CTX_TYPE, val);
5403 
5404 	/* Setup the MQ BIN mapping for l2_ctx_host_bseq. */
5405 	if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
5406 	    (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
5407 		val = REG_RD(sc, BCE_MQ_MAP_L2_5);
5408 		REG_WR(sc, BCE_MQ_MAP_L2_5, val | BCE_MQ_MAP_L2_5_ARM);
5409 	}
5410 
5411 	/* Point the hardware to the first page in the chain. */
5412 	val = BCE_ADDR_HI(sc->rx_bd_chain_paddr[0]);
5413 	CTX_WR(sc, GET_CID_ADDR(RX_CID), BCE_L2CTX_RX_NX_BDHADDR_HI, val);
5414 	val = BCE_ADDR_LO(sc->rx_bd_chain_paddr[0]);
5415 	CTX_WR(sc, GET_CID_ADDR(RX_CID), BCE_L2CTX_RX_NX_BDHADDR_LO, val);
5416 
5417 	DBEXIT(BCE_VERBOSE_RESET | BCE_VERBOSE_RECV | BCE_VERBOSE_CTX);
5418 }
5419 
5420 
5421 /****************************************************************************/
5422 /* Allocate memory and initialize the RX data structures.                   */
5423 /*                                                                          */
5424 /* Returns:                                                                 */
5425 /*   0 for success, positive value for failure.                             */
5426 /****************************************************************************/
5427 static int
5428 bce_init_rx_chain(struct bce_softc *sc)
5429 {
5430 	struct rx_bd *rxbd;
5431 	int i, rc = 0;
5432 
5433 	DBENTER(BCE_VERBOSE_RESET | BCE_VERBOSE_RECV | BCE_VERBOSE_LOAD |
5434 	    BCE_VERBOSE_CTX);
5435 
5436 	/* Initialize the RX producer and consumer indices. */
5437 	sc->rx_prod        = 0;
5438 	sc->rx_cons        = 0;
5439 	sc->rx_prod_bseq   = 0;
5440 	sc->free_rx_bd     = USABLE_RX_BD;
5441 	sc->max_rx_bd      = USABLE_RX_BD;
5442 
5443 	/* Initialize the RX next pointer chain entries. */
5444 	for (i = 0; i < RX_PAGES; i++) {
5445 		int j;
5446 
5447 		rxbd = &sc->rx_bd_chain[i][USABLE_RX_BD_PER_PAGE];
5448 
5449 		/* Check if we've reached the last page. */
5450 		if (i == (RX_PAGES - 1))
5451 			j = 0;
5452 		else
5453 			j = i + 1;
5454 
5455 		/* Setup the chain page pointers. */
5456 		rxbd->rx_bd_haddr_hi =
5457 		    htole32(BCE_ADDR_HI(sc->rx_bd_chain_paddr[j]));
5458 		rxbd->rx_bd_haddr_lo =
5459 		    htole32(BCE_ADDR_LO(sc->rx_bd_chain_paddr[j]));
5460 	}
5461 
5462 	/* Fill up the RX chain. */
5463 	bce_fill_rx_chain(sc);
5464 
5465 	DBRUN(sc->rx_low_watermark = USABLE_RX_BD);
5466 	DBRUN(sc->rx_empty_count = 0);
5467 	for (i = 0; i < RX_PAGES; i++) {
5468 		bus_dmamap_sync(sc->rx_bd_chain_tag, sc->rx_bd_chain_map[i],
5469 		    BUS_DMASYNC_PREREAD | BUS_DMASYNC_PREWRITE);
5470 	}
5471 
5472 	bce_init_rx_context(sc);
5473 
5474 	DBRUNMSG(BCE_EXTREME_RECV, bce_dump_rx_bd_chain(sc, 0, TOTAL_RX_BD));
5475 	DBEXIT(BCE_VERBOSE_RESET | BCE_VERBOSE_RECV | BCE_VERBOSE_LOAD |
5476 	    BCE_VERBOSE_CTX);
5477 
5478 	/* ToDo: Are there possible failure modes here? */
5479 
5480 	return(rc);
5481 }
5482 
5483 
5484 /****************************************************************************/
5485 /* Add mbufs to the RX chain until its full or an mbuf allocation error     */
5486 /* occurs.                                                                  */
5487 /*                                                                          */
5488 /* Returns:                                                                 */
5489 /*   Nothing                                                                */
5490 /****************************************************************************/
5491 static void
5492 bce_fill_rx_chain(struct bce_softc *sc)
5493 {
5494 	u16 prod, prod_idx;
5495 	u32 prod_bseq;
5496 
5497 	DBENTER(BCE_VERBOSE_RESET | BCE_EXTREME_RECV | BCE_VERBOSE_LOAD |
5498 	    BCE_VERBOSE_CTX);
5499 
5500 	/* Get the RX chain producer indices. */
5501 	prod      = sc->rx_prod;
5502 	prod_bseq = sc->rx_prod_bseq;
5503 
5504 	/* Keep filling the RX chain until it's full. */
5505 	while (sc->free_rx_bd > 0) {
5506 		prod_idx = RX_CHAIN_IDX(prod);
5507 		if (bce_get_rx_buf(sc, NULL, &prod, &prod_idx, &prod_bseq)) {
5508 			/* Bail out if we can't add an mbuf to the chain. */
5509 			break;
5510 		}
5511 		prod = NEXT_RX_BD(prod);
5512 	}
5513 
5514 	/* Save the RX chain producer indices. */
5515 	sc->rx_prod      = prod;
5516 	sc->rx_prod_bseq = prod_bseq;
5517 
5518 	/* We should never end up pointing to a next page pointer. */
5519 	DBRUNIF(((prod & USABLE_RX_BD_PER_PAGE) == USABLE_RX_BD_PER_PAGE),
5520 		BCE_PRINTF("%s(): Invalid rx_prod value: 0x%04X\n",
5521 		__FUNCTION__, sc->rx_prod));
5522 
5523 	/* Write the mailbox and tell the chip about the waiting rx_bd's. */
5524 	REG_WR16(sc, MB_GET_CID_ADDR(RX_CID) + BCE_L2MQ_RX_HOST_BDIDX,
5525 		sc->rx_prod);
5526 	REG_WR(sc, MB_GET_CID_ADDR(RX_CID) + BCE_L2MQ_RX_HOST_BSEQ,
5527 		sc->rx_prod_bseq);
5528 
5529 	DBEXIT(BCE_VERBOSE_RESET | BCE_EXTREME_RECV | BCE_VERBOSE_LOAD |
5530 	    BCE_VERBOSE_CTX);
5531 }
5532 
5533 
5534 /****************************************************************************/
5535 /* Free memory and clear the RX data structures.                            */
5536 /*                                                                          */
5537 /* Returns:                                                                 */
5538 /*   Nothing.                                                               */
5539 /****************************************************************************/
5540 static void
5541 bce_free_rx_chain(struct bce_softc *sc)
5542 {
5543 	int i;
5544 
5545 	DBENTER(BCE_VERBOSE_RESET | BCE_VERBOSE_RECV | BCE_VERBOSE_UNLOAD);
5546 
5547 	/* Free any mbufs still in the RX mbuf chain. */
5548 	for (i = 0; i < TOTAL_RX_BD; i++) {
5549 		if (sc->rx_mbuf_ptr[i] != NULL) {
5550 			if (sc->rx_mbuf_map[i] != NULL)
5551 				bus_dmamap_sync(sc->rx_mbuf_tag,
5552 				    sc->rx_mbuf_map[i],
5553 				    BUS_DMASYNC_POSTREAD);
5554 			m_freem(sc->rx_mbuf_ptr[i]);
5555 			sc->rx_mbuf_ptr[i] = NULL;
5556 			DBRUN(sc->debug_rx_mbuf_alloc--);
5557 		}
5558 	}
5559 
5560 	/* Clear each RX chain page. */
5561 	for (i = 0; i < RX_PAGES; i++)
5562 		if (sc->rx_bd_chain[i] != NULL) {
5563 			bzero((char *)sc->rx_bd_chain[i],
5564 			    BCE_RX_CHAIN_PAGE_SZ);
5565 		}
5566 
5567 	sc->free_rx_bd = sc->max_rx_bd;
5568 
5569 	/* Check if we lost any mbufs in the process. */
5570 	DBRUNIF((sc->debug_rx_mbuf_alloc),
5571 	    BCE_PRINTF("%s(): Memory leak! Lost %d mbufs from rx chain!\n",
5572 	    __FUNCTION__, sc->debug_rx_mbuf_alloc));
5573 
5574 	DBEXIT(BCE_VERBOSE_RESET | BCE_VERBOSE_RECV | BCE_VERBOSE_UNLOAD);
5575 }
5576 
5577 
5578 #ifdef BCE_JUMBO_HDRSPLIT
5579 /****************************************************************************/
5580 /* Allocate memory and initialize the page data structures.                 */
5581 /* Assumes that bce_init_rx_chain() has not already been called.            */
5582 /*                                                                          */
5583 /* Returns:                                                                 */
5584 /*   0 for success, positive value for failure.                             */
5585 /****************************************************************************/
5586 static int
5587 bce_init_pg_chain(struct bce_softc *sc)
5588 {
5589 	struct rx_bd *pgbd;
5590 	int i, rc = 0;
5591 	u32 val;
5592 
5593 	DBENTER(BCE_VERBOSE_RESET | BCE_VERBOSE_RECV | BCE_VERBOSE_LOAD |
5594 		BCE_VERBOSE_CTX);
5595 
5596 	/* Initialize the page producer and consumer indices. */
5597 	sc->pg_prod        = 0;
5598 	sc->pg_cons        = 0;
5599 	sc->free_pg_bd     = USABLE_PG_BD;
5600 	sc->max_pg_bd      = USABLE_PG_BD;
5601 	DBRUN(sc->pg_low_watermark = sc->max_pg_bd);
5602 	DBRUN(sc->pg_empty_count = 0);
5603 
5604 	/* Initialize the page next pointer chain entries. */
5605 	for (i = 0; i < PG_PAGES; i++) {
5606 		int j;
5607 
5608 		pgbd = &sc->pg_bd_chain[i][USABLE_PG_BD_PER_PAGE];
5609 
5610 		/* Check if we've reached the last page. */
5611 		if (i == (PG_PAGES - 1))
5612 			j = 0;
5613 		else
5614 			j = i + 1;
5615 
5616 		/* Setup the chain page pointers. */
5617 		pgbd->rx_bd_haddr_hi = htole32(BCE_ADDR_HI(sc->pg_bd_chain_paddr[j]));
5618 		pgbd->rx_bd_haddr_lo = htole32(BCE_ADDR_LO(sc->pg_bd_chain_paddr[j]));
5619 	}
5620 
5621 	/* Setup the MQ BIN mapping for host_pg_bidx. */
5622 	if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709)	||
5623 		(BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716))
5624 		REG_WR(sc, BCE_MQ_MAP_L2_3, BCE_MQ_MAP_L2_3_DEFAULT);
5625 
5626 	CTX_WR(sc, GET_CID_ADDR(RX_CID), BCE_L2CTX_RX_PG_BUF_SIZE, 0);
5627 
5628 	/* Configure the rx_bd and page chain mbuf cluster size. */
5629 	val = (sc->rx_bd_mbuf_data_len << 16) | sc->pg_bd_mbuf_alloc_size;
5630 	CTX_WR(sc, GET_CID_ADDR(RX_CID), BCE_L2CTX_RX_PG_BUF_SIZE, val);
5631 
5632 	/* Configure the context reserved for jumbo support. */
5633 	CTX_WR(sc, GET_CID_ADDR(RX_CID), BCE_L2CTX_RX_RBDC_KEY,
5634 		BCE_L2CTX_RX_RBDC_JUMBO_KEY);
5635 
5636 	/* Point the hardware to the first page in the page chain. */
5637 	val = BCE_ADDR_HI(sc->pg_bd_chain_paddr[0]);
5638 	CTX_WR(sc, GET_CID_ADDR(RX_CID), BCE_L2CTX_RX_NX_PG_BDHADDR_HI, val);
5639 	val = BCE_ADDR_LO(sc->pg_bd_chain_paddr[0]);
5640 	CTX_WR(sc, GET_CID_ADDR(RX_CID), BCE_L2CTX_RX_NX_PG_BDHADDR_LO, val);
5641 
5642 	/* Fill up the page chain. */
5643 	bce_fill_pg_chain(sc);
5644 
5645 	for (i = 0; i < PG_PAGES; i++) {
5646 		bus_dmamap_sync(sc->pg_bd_chain_tag, sc->pg_bd_chain_map[i],
5647 		    BUS_DMASYNC_PREREAD | BUS_DMASYNC_PREWRITE);
5648 	}
5649 
5650 	DBRUNMSG(BCE_EXTREME_RECV, bce_dump_pg_chain(sc, 0, TOTAL_PG_BD));
5651 	DBEXIT(BCE_VERBOSE_RESET | BCE_VERBOSE_RECV | BCE_VERBOSE_LOAD |
5652 		BCE_VERBOSE_CTX);
5653 	return(rc);
5654 }
5655 
5656 
5657 /****************************************************************************/
5658 /* Add mbufs to the page chain until its full or an mbuf allocation error   */
5659 /* occurs.                                                                  */
5660 /*                                                                          */
5661 /* Returns:                                                                 */
5662 /*   Nothing                                                                */
5663 /****************************************************************************/
5664 static void
5665 bce_fill_pg_chain(struct bce_softc *sc)
5666 {
5667 	u16 prod, prod_idx;
5668 
5669 	DBENTER(BCE_VERBOSE_RESET | BCE_EXTREME_RECV | BCE_VERBOSE_LOAD |
5670 		BCE_VERBOSE_CTX);
5671 
5672 	/* Get the page chain prodcuer index. */
5673 	prod = sc->pg_prod;
5674 
5675 	/* Keep filling the page chain until it's full. */
5676 	while (sc->free_pg_bd > 0) {
5677 		prod_idx = PG_CHAIN_IDX(prod);
5678 		if (bce_get_pg_buf(sc, NULL, &prod, &prod_idx)) {
5679 			/* Bail out if we can't add an mbuf to the chain. */
5680 			break;
5681 		}
5682 		prod = NEXT_PG_BD(prod);
5683 	}
5684 
5685 	/* Save the page chain producer index. */
5686 	sc->pg_prod = prod;
5687 
5688 	DBRUNIF(((prod & USABLE_RX_BD_PER_PAGE) == USABLE_RX_BD_PER_PAGE),
5689 		BCE_PRINTF("%s(): Invalid pg_prod value: 0x%04X\n",
5690 		__FUNCTION__, sc->pg_prod));
5691 
5692 	/*
5693 	 * Write the mailbox and tell the chip about
5694 	 * the new rx_bd's in the page chain.
5695 	 */
5696 	REG_WR16(sc, MB_GET_CID_ADDR(RX_CID) + BCE_L2MQ_RX_HOST_PG_BDIDX,
5697 		sc->pg_prod);
5698 
5699 	DBEXIT(BCE_VERBOSE_RESET | BCE_EXTREME_RECV | BCE_VERBOSE_LOAD |
5700 		BCE_VERBOSE_CTX);
5701 }
5702 
5703 
5704 /****************************************************************************/
5705 /* Free memory and clear the RX data structures.                            */
5706 /*                                                                          */
5707 /* Returns:                                                                 */
5708 /*   Nothing.                                                               */
5709 /****************************************************************************/
5710 static void
5711 bce_free_pg_chain(struct bce_softc *sc)
5712 {
5713 	int i;
5714 
5715 	DBENTER(BCE_VERBOSE_RESET | BCE_VERBOSE_RECV | BCE_VERBOSE_UNLOAD);
5716 
5717 	/* Free any mbufs still in the mbuf page chain. */
5718 	for (i = 0; i < TOTAL_PG_BD; i++) {
5719 		if (sc->pg_mbuf_ptr[i] != NULL) {
5720 			if (sc->pg_mbuf_map[i] != NULL)
5721 				bus_dmamap_sync(sc->pg_mbuf_tag, sc->pg_mbuf_map[i],
5722 					BUS_DMASYNC_POSTREAD);
5723 			m_freem(sc->pg_mbuf_ptr[i]);
5724 			sc->pg_mbuf_ptr[i] = NULL;
5725 			DBRUN(sc->debug_pg_mbuf_alloc--);
5726 		}
5727 	}
5728 
5729 	/* Clear each page chain pages. */
5730 	for (i = 0; i < PG_PAGES; i++)
5731 		bzero((char *)sc->pg_bd_chain[i], BCE_PG_CHAIN_PAGE_SZ);
5732 
5733 	sc->free_pg_bd = sc->max_pg_bd;
5734 
5735 	/* Check if we lost any mbufs in the process. */
5736 	DBRUNIF((sc->debug_pg_mbuf_alloc),
5737 		BCE_PRINTF("%s(): Memory leak! Lost %d mbufs from page chain!\n",
5738 			__FUNCTION__, sc->debug_pg_mbuf_alloc));
5739 
5740 	DBEXIT(BCE_VERBOSE_RESET | BCE_VERBOSE_RECV | BCE_VERBOSE_UNLOAD);
5741 }
5742 #endif /* BCE_JUMBO_HDRSPLIT */
5743 
5744 
5745 /****************************************************************************/
5746 /* Set media options.                                                       */
5747 /*                                                                          */
5748 /* Returns:                                                                 */
5749 /*   0 for success, positive value for failure.                             */
5750 /****************************************************************************/
5751 static int
5752 bce_ifmedia_upd(struct ifnet *ifp)
5753 {
5754 	struct bce_softc *sc = ifp->if_softc;
5755 
5756 	DBENTER(BCE_VERBOSE);
5757 
5758 	BCE_LOCK(sc);
5759 	bce_ifmedia_upd_locked(ifp);
5760 	BCE_UNLOCK(sc);
5761 
5762 	DBEXIT(BCE_VERBOSE);
5763 	return (0);
5764 }
5765 
5766 
5767 /****************************************************************************/
5768 /* Set media options.                                                       */
5769 /*                                                                          */
5770 /* Returns:                                                                 */
5771 /*   Nothing.                                                               */
5772 /****************************************************************************/
5773 static void
5774 bce_ifmedia_upd_locked(struct ifnet *ifp)
5775 {
5776 	struct bce_softc *sc = ifp->if_softc;
5777 	struct mii_data *mii;
5778 
5779 	DBENTER(BCE_VERBOSE);
5780 
5781 	BCE_LOCK_ASSERT(sc);
5782 
5783 	mii = device_get_softc(sc->bce_miibus);
5784 
5785 	/* Make sure the MII bus has been enumerated. */
5786 	if (mii) {
5787 		sc->bce_link_up = FALSE;
5788 		if (mii->mii_instance) {
5789 			struct mii_softc *miisc;
5790 
5791 			LIST_FOREACH(miisc, &mii->mii_phys, mii_list)
5792 			    mii_phy_reset(miisc);
5793 		}
5794 		mii_mediachg(mii);
5795 	}
5796 
5797 	DBEXIT(BCE_VERBOSE);
5798 }
5799 
5800 
5801 /****************************************************************************/
5802 /* Reports current media status.                                            */
5803 /*                                                                          */
5804 /* Returns:                                                                 */
5805 /*   Nothing.                                                               */
5806 /****************************************************************************/
5807 static void
5808 bce_ifmedia_sts(struct ifnet *ifp, struct ifmediareq *ifmr)
5809 {
5810 	struct bce_softc *sc = ifp->if_softc;
5811 	struct mii_data *mii;
5812 
5813 	DBENTER(BCE_VERBOSE);
5814 
5815 	BCE_LOCK(sc);
5816 
5817 	mii = device_get_softc(sc->bce_miibus);
5818 
5819 	mii_pollstat(mii);
5820 	ifmr->ifm_active = mii->mii_media_active;
5821 	ifmr->ifm_status = mii->mii_media_status;
5822 
5823 	BCE_UNLOCK(sc);
5824 
5825 	DBEXIT(BCE_VERBOSE);
5826 }
5827 
5828 
5829 /****************************************************************************/
5830 /* Handles PHY generated interrupt events.                                  */
5831 /*                                                                          */
5832 /* Returns:                                                                 */
5833 /*   Nothing.                                                               */
5834 /****************************************************************************/
5835 static void
5836 bce_phy_intr(struct bce_softc *sc)
5837 {
5838 	u32 new_link_state, old_link_state;
5839 
5840 	DBENTER(BCE_VERBOSE_PHY | BCE_VERBOSE_INTR);
5841 
5842 	DBRUN(sc->phy_interrupts++);
5843 
5844 	new_link_state = sc->status_block->status_attn_bits &
5845 	    STATUS_ATTN_BITS_LINK_STATE;
5846 	old_link_state = sc->status_block->status_attn_bits_ack &
5847 	    STATUS_ATTN_BITS_LINK_STATE;
5848 
5849 	/* Handle any changes if the link state has changed. */
5850 	if (new_link_state != old_link_state) {
5851 
5852 		/* Update the status_attn_bits_ack field. */
5853 		if (new_link_state) {
5854 			REG_WR(sc, BCE_PCICFG_STATUS_BIT_SET_CMD,
5855 			    STATUS_ATTN_BITS_LINK_STATE);
5856 			DBPRINT(sc, BCE_INFO_PHY, "%s(): Link is now UP.\n",
5857 			    __FUNCTION__);
5858 		}
5859 		else {
5860 			REG_WR(sc, BCE_PCICFG_STATUS_BIT_CLEAR_CMD,
5861 			    STATUS_ATTN_BITS_LINK_STATE);
5862 			DBPRINT(sc, BCE_INFO_PHY, "%s(): Link is now DOWN.\n",
5863 			    __FUNCTION__);
5864 		}
5865 
5866 		/*
5867 		 * Assume link is down and allow
5868 		 * tick routine to update the state
5869 		 * based on the actual media state.
5870 		 */
5871 		sc->bce_link_up = FALSE;
5872 		callout_stop(&sc->bce_tick_callout);
5873 		bce_tick(sc);
5874 	}
5875 
5876 	/* Acknowledge the link change interrupt. */
5877 	REG_WR(sc, BCE_EMAC_STATUS, BCE_EMAC_STATUS_LINK_CHANGE);
5878 
5879 	DBEXIT(BCE_VERBOSE_PHY | BCE_VERBOSE_INTR);
5880 }
5881 
5882 
5883 /****************************************************************************/
5884 /* Reads the receive consumer value from the status block (skipping over    */
5885 /* chain page pointer if necessary).                                        */
5886 /*                                                                          */
5887 /* Returns:                                                                 */
5888 /*   hw_cons                                                                */
5889 /****************************************************************************/
5890 static inline u16
5891 bce_get_hw_rx_cons(struct bce_softc *sc)
5892 {
5893 	u16 hw_cons;
5894 
5895 	rmb();
5896 	hw_cons = sc->status_block->status_rx_quick_consumer_index0;
5897 	if ((hw_cons & USABLE_RX_BD_PER_PAGE) == USABLE_RX_BD_PER_PAGE)
5898 		hw_cons++;
5899 
5900 	return hw_cons;
5901 }
5902 
5903 /****************************************************************************/
5904 /* Handles received frame interrupt events.                                 */
5905 /*                                                                          */
5906 /* Returns:                                                                 */
5907 /*   Nothing.                                                               */
5908 /****************************************************************************/
5909 static void
5910 bce_rx_intr(struct bce_softc *sc)
5911 {
5912 	struct ifnet *ifp = sc->bce_ifp;
5913 	struct l2_fhdr *l2fhdr;
5914 	struct ether_vlan_header *vh;
5915 	unsigned int pkt_len;
5916 	u16 sw_rx_cons, sw_rx_cons_idx, hw_rx_cons;
5917 	u32 status;
5918 #ifdef BCE_JUMBO_HDRSPLIT
5919 	unsigned int rem_len;
5920 	u16 sw_pg_cons, sw_pg_cons_idx;
5921 #endif
5922 
5923 	DBENTER(BCE_VERBOSE_RECV | BCE_VERBOSE_INTR);
5924 	DBRUN(sc->rx_interrupts++);
5925 	DBPRINT(sc, BCE_EXTREME_RECV, "%s(enter): rx_prod = 0x%04X, "
5926 	    "rx_cons = 0x%04X, rx_prod_bseq = 0x%08X\n",
5927 	    __FUNCTION__, sc->rx_prod, sc->rx_cons, sc->rx_prod_bseq);
5928 
5929 	/* Prepare the RX chain pages to be accessed by the host CPU. */
5930 	for (int i = 0; i < RX_PAGES; i++)
5931 		bus_dmamap_sync(sc->rx_bd_chain_tag,
5932 		    sc->rx_bd_chain_map[i], BUS_DMASYNC_POSTREAD);
5933 
5934 #ifdef BCE_JUMBO_HDRSPLIT
5935 	/* Prepare the page chain pages to be accessed by the host CPU. */
5936 	for (int i = 0; i < PG_PAGES; i++)
5937 		bus_dmamap_sync(sc->pg_bd_chain_tag,
5938 		    sc->pg_bd_chain_map[i], BUS_DMASYNC_POSTREAD);
5939 #endif
5940 
5941 	/* Get the hardware's view of the RX consumer index. */
5942 	hw_rx_cons = sc->hw_rx_cons = bce_get_hw_rx_cons(sc);
5943 
5944 	/* Get working copies of the driver's view of the consumer indices. */
5945 	sw_rx_cons = sc->rx_cons;
5946 #ifdef BCE_JUMBO_HDRSPLIT
5947 	sw_pg_cons = sc->pg_cons;
5948 #endif
5949 
5950 	/* Update some debug statistics counters */
5951 	DBRUNIF((sc->free_rx_bd < sc->rx_low_watermark),
5952 		sc->rx_low_watermark = sc->free_rx_bd);
5953 	DBRUNIF((sc->free_rx_bd == sc->max_rx_bd), sc->rx_empty_count++);
5954 
5955 	/* Scan through the receive chain as long as there is work to do */
5956 	/* ToDo: Consider setting a limit on the number of packets processed. */
5957 	rmb();
5958 	while (sw_rx_cons != hw_rx_cons) {
5959 		struct mbuf *m0;
5960 
5961 		/* Convert the producer/consumer indices to an actual rx_bd index. */
5962 		sw_rx_cons_idx = RX_CHAIN_IDX(sw_rx_cons);
5963 
5964 		/* Unmap the mbuf from DMA space. */
5965 		bus_dmamap_sync(sc->rx_mbuf_tag,
5966 		    sc->rx_mbuf_map[sw_rx_cons_idx],
5967 		    BUS_DMASYNC_POSTREAD);
5968 		bus_dmamap_unload(sc->rx_mbuf_tag,
5969 		    sc->rx_mbuf_map[sw_rx_cons_idx]);
5970 
5971 		/* Remove the mbuf from the RX chain. */
5972 		m0 = sc->rx_mbuf_ptr[sw_rx_cons_idx];
5973 		sc->rx_mbuf_ptr[sw_rx_cons_idx] = NULL;
5974 		DBRUN(sc->debug_rx_mbuf_alloc--);
5975 		sc->free_rx_bd++;
5976 
5977 		if(m0 == NULL) {
5978 			DBPRINT(sc, BCE_EXTREME_RECV,
5979 			    "%s(): Oops! Empty mbuf pointer "
5980 			    "found in sc->rx_mbuf_ptr[0x%04X]!\n",
5981 			    __FUNCTION__, sw_rx_cons_idx);
5982 			goto bce_rx_int_next_rx;
5983 		}
5984 
5985 		/*
5986 		 * Frames received on the NetXteme II are prepended	with an
5987 		 * l2_fhdr structure which provides status information about
5988 		 * the received frame (including VLAN tags and checksum info).
5989 		 * The frames are also automatically adjusted to align the IP
5990 		 * header (i.e. two null bytes are inserted before the Ethernet
5991 		 * header).  As a result the data DMA'd by the controller into
5992 		 * the mbuf is as follows:
5993 		 *
5994 		 * +---------+-----+---------------------+-----+
5995 		 * | l2_fhdr | pad | packet data         | FCS |
5996 		 * +---------+-----+---------------------+-----+
5997 		 *
5998 		 * The l2_fhdr needs to be checked and skipped and the FCS needs
5999 		 * to be stripped before sending the packet up the stack.
6000 		 */
6001 		l2fhdr  = mtod(m0, struct l2_fhdr *);
6002 
6003 		/* Get the packet data + FCS length and the status. */
6004 		pkt_len = l2fhdr->l2_fhdr_pkt_len;
6005 		status  = l2fhdr->l2_fhdr_status;
6006 
6007 		/*
6008 		 * Skip over the l2_fhdr and pad, resulting in the
6009 		 * following data in the mbuf:
6010 		 * +---------------------+-----+
6011 		 * | packet data         | FCS |
6012 		 * +---------------------+-----+
6013 		 */
6014 		m_adj(m0, sizeof(struct l2_fhdr) + ETHER_ALIGN);
6015 
6016 #ifdef BCE_JUMBO_HDRSPLIT
6017 		/*
6018 		 * Check whether the received frame fits in a single
6019 		 * mbuf or not (i.e. packet data + FCS <=
6020 		 * sc->rx_bd_mbuf_data_len bytes).
6021 		 */
6022 		if (pkt_len > m0->m_len) {
6023 			/*
6024 			 * The received frame is larger than a single mbuf.
6025 			 * If the frame was a TCP frame then only the TCP
6026 			 * header is placed in the mbuf, the remaining
6027 			 * payload (including FCS) is placed in the page
6028 			 * chain, the SPLIT flag is set, and the header
6029 			 * length is placed in the IP checksum field.
6030 			 * If the frame is not a TCP frame then the mbuf
6031 			 * is filled and the remaining bytes are placed
6032 			 * in the page chain.
6033 			 */
6034 
6035 			DBPRINT(sc, BCE_INFO_RECV, "%s(): Found a large "
6036 			    "packet.\n", __FUNCTION__);
6037 
6038 			/*
6039 			 * When the page chain is enabled and the TCP
6040 			 * header has been split from the TCP payload,
6041 			 * the ip_xsum structure will reflect the length
6042 			 * of the TCP header, not the IP checksum.  Set
6043 			 * the packet length of the mbuf accordingly.
6044 			 */
6045 		 	if (status & L2_FHDR_STATUS_SPLIT)
6046 				m0->m_len = l2fhdr->l2_fhdr_ip_xsum;
6047 
6048 			rem_len = pkt_len - m0->m_len;
6049 
6050 			/* Pull mbufs off the page chain for the remaining data. */
6051 			while (rem_len > 0) {
6052 				struct mbuf *m_pg;
6053 
6054 				sw_pg_cons_idx = PG_CHAIN_IDX(sw_pg_cons);
6055 
6056 				/* Remove the mbuf from the page chain. */
6057 				m_pg = sc->pg_mbuf_ptr[sw_pg_cons_idx];
6058 				sc->pg_mbuf_ptr[sw_pg_cons_idx] = NULL;
6059 				DBRUN(sc->debug_pg_mbuf_alloc--);
6060 				sc->free_pg_bd++;
6061 
6062 				/* Unmap the page chain mbuf from DMA space. */
6063 				bus_dmamap_sync(sc->pg_mbuf_tag,
6064 				    sc->pg_mbuf_map[sw_pg_cons_idx],
6065 				    BUS_DMASYNC_POSTREAD);
6066 				bus_dmamap_unload(sc->pg_mbuf_tag,
6067 				    sc->pg_mbuf_map[sw_pg_cons_idx]);
6068 
6069 				/* Adjust the mbuf length. */
6070 				if (rem_len < m_pg->m_len) {
6071 					/* The mbuf chain is complete. */
6072 					m_pg->m_len = rem_len;
6073 					rem_len = 0;
6074 				} else {
6075 					/* More packet data is waiting. */
6076 					rem_len -= m_pg->m_len;
6077 				}
6078 
6079 				/* Concatenate the mbuf cluster to the mbuf. */
6080 				m_cat(m0, m_pg);
6081 
6082 				sw_pg_cons = NEXT_PG_BD(sw_pg_cons);
6083 			}
6084 
6085 			/* Set the total packet length. */
6086 			m0->m_pkthdr.len = pkt_len;
6087 
6088 		} else {
6089 			/*
6090 			 * The received packet is small and fits in a
6091 			 * single mbuf (i.e. the l2_fhdr + pad + packet +
6092 			 * FCS <= MHLEN).  In other words, the packet is
6093 			 * 154 bytes or less in size.
6094 			 */
6095 
6096 			DBPRINT(sc, BCE_INFO_RECV, "%s(): Found a small "
6097 			    "packet.\n", __FUNCTION__);
6098 
6099 			/* Set the total packet length. */
6100 			m0->m_pkthdr.len = m0->m_len = pkt_len;
6101 		}
6102 #else
6103         /* Set the total packet length. */
6104 		m0->m_pkthdr.len = m0->m_len = pkt_len;
6105 #endif
6106 
6107 		/* Remove the trailing Ethernet FCS. */
6108 		m_adj(m0, -ETHER_CRC_LEN);
6109 
6110 		/* Check that the resulting mbuf chain is valid. */
6111 		DBRUN(m_sanity(m0, FALSE));
6112 		DBRUNIF(((m0->m_len < ETHER_HDR_LEN) |
6113 		    (m0->m_pkthdr.len > BCE_MAX_JUMBO_ETHER_MTU_VLAN)),
6114 		     BCE_PRINTF("Invalid Ethernet frame size!\n");
6115 		     m_print(m0, 128));
6116 
6117 		DBRUNIF(DB_RANDOMTRUE(l2fhdr_error_sim_control),
6118 		    BCE_PRINTF("Simulating l2_fhdr status error.\n");
6119 		    sc->l2fhdr_error_sim_count++;
6120 		    status = status | L2_FHDR_ERRORS_PHY_DECODE);
6121 
6122 		/* Check the received frame for errors. */
6123 		if (status & (L2_FHDR_ERRORS_BAD_CRC |
6124 		    L2_FHDR_ERRORS_PHY_DECODE | L2_FHDR_ERRORS_ALIGNMENT |
6125 		    L2_FHDR_ERRORS_TOO_SHORT  | L2_FHDR_ERRORS_GIANT_FRAME)) {
6126 
6127 			/* Log the error and release the mbuf. */
6128 			ifp->if_ierrors++;
6129 			sc->l2fhdr_error_count++;
6130 
6131 			m_freem(m0);
6132 			m0 = NULL;
6133 			goto bce_rx_int_next_rx;
6134 		}
6135 
6136 		/* Send the packet to the appropriate interface. */
6137 		m0->m_pkthdr.rcvif = ifp;
6138 
6139 		/* Assume no hardware checksum. */
6140 		m0->m_pkthdr.csum_flags = 0;
6141 
6142 		/* Validate the checksum if offload enabled. */
6143 		if (ifp->if_capenable & IFCAP_RXCSUM) {
6144 
6145 			/* Check for an IP datagram. */
6146 		 	if (!(status & L2_FHDR_STATUS_SPLIT) &&
6147 				(status & L2_FHDR_STATUS_IP_DATAGRAM)) {
6148 				m0->m_pkthdr.csum_flags |= CSUM_IP_CHECKED;
6149 
6150 				/* Check if the IP checksum is valid. */
6151 				if ((l2fhdr->l2_fhdr_ip_xsum ^ 0xffff) == 0)
6152 					m0->m_pkthdr.csum_flags |=
6153 					    CSUM_IP_VALID;
6154 			}
6155 
6156 			/* Check for a valid TCP/UDP frame. */
6157 			if (status & (L2_FHDR_STATUS_TCP_SEGMENT |
6158 			    L2_FHDR_STATUS_UDP_DATAGRAM)) {
6159 
6160 				/* Check for a good TCP/UDP checksum. */
6161 				if ((status & (L2_FHDR_ERRORS_TCP_XSUM |
6162 				    L2_FHDR_ERRORS_UDP_XSUM)) == 0) {
6163 					m0->m_pkthdr.csum_data =
6164 					    l2fhdr->l2_fhdr_tcp_udp_xsum;
6165 					m0->m_pkthdr.csum_flags |=
6166 					    (CSUM_DATA_VALID
6167 					    | CSUM_PSEUDO_HDR);
6168 				}
6169 			}
6170 		}
6171 
6172 		/* Attach the VLAN tag.	*/
6173 		if (status & L2_FHDR_STATUS_L2_VLAN_TAG) {
6174 			if (ifp->if_capenable & IFCAP_VLAN_HWTAGGING) {
6175 #if __FreeBSD_version < 700000
6176 				VLAN_INPUT_TAG(ifp, m0,
6177 				    l2fhdr->l2_fhdr_vlan_tag, continue);
6178 #else
6179 				m0->m_pkthdr.ether_vtag =
6180 				    l2fhdr->l2_fhdr_vlan_tag;
6181 				m0->m_flags |= M_VLANTAG;
6182 #endif
6183 			} else {
6184 				/*
6185 				 * bce(4) controllers can't disable VLAN
6186 				 * tag stripping if management firmware
6187 				 * (ASF/IPMI/UMP) is running. So we always
6188 				 * strip VLAN tag and manually reconstruct
6189 				 * the VLAN frame by appending stripped
6190 				 * VLAN tag in driver if VLAN tag stripping
6191 				 * was disabled.
6192 				 *
6193 				 * TODO: LLC SNAP handling.
6194 				 */
6195 				bcopy(mtod(m0, uint8_t *),
6196 				    mtod(m0, uint8_t *) - ETHER_VLAN_ENCAP_LEN,
6197 				    ETHER_ADDR_LEN * 2);
6198 				m0->m_data -= ETHER_VLAN_ENCAP_LEN;
6199 				vh = mtod(m0, struct ether_vlan_header *);
6200 				vh->evl_encap_proto = htons(ETHERTYPE_VLAN);
6201 				vh->evl_tag = htons(l2fhdr->l2_fhdr_vlan_tag);
6202 				m0->m_pkthdr.len += ETHER_VLAN_ENCAP_LEN;
6203 				m0->m_len += ETHER_VLAN_ENCAP_LEN;
6204 			}
6205 		}
6206 
6207 		/* Increment received packet statistics. */
6208 		ifp->if_ipackets++;
6209 
6210 bce_rx_int_next_rx:
6211 		sw_rx_cons = NEXT_RX_BD(sw_rx_cons);
6212 
6213 		/* If we have a packet, pass it up the stack */
6214 		if (m0) {
6215 			/* Make sure we don't lose our place when we release the lock. */
6216 			sc->rx_cons = sw_rx_cons;
6217 #ifdef BCE_JUMBO_HDRSPLIT
6218 			sc->pg_cons = sw_pg_cons;
6219 #endif
6220 
6221 			BCE_UNLOCK(sc);
6222 			(*ifp->if_input)(ifp, m0);
6223 			BCE_LOCK(sc);
6224 
6225 			/* Recover our place. */
6226 			sw_rx_cons = sc->rx_cons;
6227 #ifdef BCE_JUMBO_HDRSPLIT
6228 			sw_pg_cons = sc->pg_cons;
6229 #endif
6230 		}
6231 
6232 		/* Refresh hw_cons to see if there's new work */
6233 		if (sw_rx_cons == hw_rx_cons)
6234 			hw_rx_cons = sc->hw_rx_cons = bce_get_hw_rx_cons(sc);
6235 	}
6236 
6237 	/* No new packets to process.  Refill the RX and page chains and exit. */
6238 #ifdef BCE_JUMBO_HDRSPLIT
6239 	sc->pg_cons = sw_pg_cons;
6240 	bce_fill_pg_chain(sc);
6241 #endif
6242 
6243 	sc->rx_cons = sw_rx_cons;
6244 	bce_fill_rx_chain(sc);
6245 
6246 	/* Prepare the page chain pages to be accessed by the NIC. */
6247 	for (int i = 0; i < RX_PAGES; i++)
6248 		bus_dmamap_sync(sc->rx_bd_chain_tag,
6249 		    sc->rx_bd_chain_map[i], BUS_DMASYNC_PREWRITE);
6250 
6251 #ifdef BCE_JUMBO_HDRSPLIT
6252 	for (int i = 0; i < PG_PAGES; i++)
6253 		bus_dmamap_sync(sc->pg_bd_chain_tag,
6254 		    sc->pg_bd_chain_map[i], BUS_DMASYNC_PREWRITE);
6255 #endif
6256 
6257 	DBPRINT(sc, BCE_EXTREME_RECV, "%s(exit): rx_prod = 0x%04X, "
6258 	    "rx_cons = 0x%04X, rx_prod_bseq = 0x%08X\n",
6259 	    __FUNCTION__, sc->rx_prod, sc->rx_cons, sc->rx_prod_bseq);
6260 	DBEXIT(BCE_VERBOSE_RECV | BCE_VERBOSE_INTR);
6261 }
6262 
6263 
6264 /****************************************************************************/
6265 /* Reads the transmit consumer value from the status block (skipping over   */
6266 /* chain page pointer if necessary).                                        */
6267 /*                                                                          */
6268 /* Returns:                                                                 */
6269 /*   hw_cons                                                                */
6270 /****************************************************************************/
6271 static inline u16
6272 bce_get_hw_tx_cons(struct bce_softc *sc)
6273 {
6274 	u16 hw_cons;
6275 
6276 	mb();
6277 	hw_cons = sc->status_block->status_tx_quick_consumer_index0;
6278 	if ((hw_cons & USABLE_TX_BD_PER_PAGE) == USABLE_TX_BD_PER_PAGE)
6279 		hw_cons++;
6280 
6281 	return hw_cons;
6282 }
6283 
6284 
6285 /****************************************************************************/
6286 /* Handles transmit completion interrupt events.                            */
6287 /*                                                                          */
6288 /* Returns:                                                                 */
6289 /*   Nothing.                                                               */
6290 /****************************************************************************/
6291 static void
6292 bce_tx_intr(struct bce_softc *sc)
6293 {
6294 	struct ifnet *ifp = sc->bce_ifp;
6295 	u16 hw_tx_cons, sw_tx_cons, sw_tx_chain_cons;
6296 
6297 	DBENTER(BCE_VERBOSE_SEND | BCE_VERBOSE_INTR);
6298 	DBRUN(sc->tx_interrupts++);
6299 	DBPRINT(sc, BCE_EXTREME_SEND, "%s(enter): tx_prod = 0x%04X, "
6300 	    "tx_cons = 0x%04X, tx_prod_bseq = 0x%08X\n",
6301 	    __FUNCTION__, sc->tx_prod, sc->tx_cons, sc->tx_prod_bseq);
6302 
6303 	BCE_LOCK_ASSERT(sc);
6304 
6305 	/* Get the hardware's view of the TX consumer index. */
6306 	hw_tx_cons = sc->hw_tx_cons = bce_get_hw_tx_cons(sc);
6307 	sw_tx_cons = sc->tx_cons;
6308 
6309 	/* Prevent speculative reads from getting ahead of the status block. */
6310 	bus_space_barrier(sc->bce_btag, sc->bce_bhandle, 0, 0,
6311 	    BUS_SPACE_BARRIER_READ);
6312 
6313 	/* Cycle through any completed TX chain page entries. */
6314 	while (sw_tx_cons != hw_tx_cons) {
6315 #ifdef BCE_DEBUG
6316 		struct tx_bd *txbd = NULL;
6317 #endif
6318 		sw_tx_chain_cons = TX_CHAIN_IDX(sw_tx_cons);
6319 
6320 		DBPRINT(sc, BCE_INFO_SEND,
6321 		    "%s(): hw_tx_cons = 0x%04X, sw_tx_cons = 0x%04X, "
6322 		    "sw_tx_chain_cons = 0x%04X\n",
6323 		    __FUNCTION__, hw_tx_cons, sw_tx_cons, sw_tx_chain_cons);
6324 
6325 		DBRUNIF((sw_tx_chain_cons > MAX_TX_BD),
6326 		    BCE_PRINTF("%s(%d): TX chain consumer out of range! "
6327 		    " 0x%04X > 0x%04X\n", __FILE__, __LINE__, sw_tx_chain_cons,
6328 		    (int) MAX_TX_BD);
6329 		    bce_breakpoint(sc));
6330 
6331 		DBRUN(txbd = &sc->tx_bd_chain[TX_PAGE(sw_tx_chain_cons)]
6332 		    [TX_IDX(sw_tx_chain_cons)]);
6333 
6334 		DBRUNIF((txbd == NULL),
6335 		    BCE_PRINTF("%s(%d): Unexpected NULL tx_bd[0x%04X]!\n",
6336 		    __FILE__, __LINE__, sw_tx_chain_cons);
6337 		    bce_breakpoint(sc));
6338 
6339 		DBRUNMSG(BCE_INFO_SEND, BCE_PRINTF("%s(): ", __FUNCTION__);
6340 		    bce_dump_txbd(sc, sw_tx_chain_cons, txbd));
6341 
6342 		/*
6343 		 * Free the associated mbuf. Remember
6344 		 * that only the last tx_bd of a packet
6345 		 * has an mbuf pointer and DMA map.
6346 		 */
6347 		if (sc->tx_mbuf_ptr[sw_tx_chain_cons] != NULL) {
6348 
6349 			/* Validate that this is the last tx_bd. */
6350 			DBRUNIF((!(txbd->tx_bd_flags & TX_BD_FLAGS_END)),
6351 			    BCE_PRINTF("%s(%d): tx_bd END flag not set but "
6352 			    "txmbuf == NULL!\n", __FILE__, __LINE__);
6353 			    bce_breakpoint(sc));
6354 
6355 			DBRUNMSG(BCE_INFO_SEND,
6356 			    BCE_PRINTF("%s(): Unloading map/freeing mbuf "
6357 			    "from tx_bd[0x%04X]\n", __FUNCTION__,
6358 			    sw_tx_chain_cons));
6359 
6360 			/* Unmap the mbuf. */
6361 			bus_dmamap_unload(sc->tx_mbuf_tag,
6362 			    sc->tx_mbuf_map[sw_tx_chain_cons]);
6363 
6364 			/* Free the mbuf. */
6365 			m_freem(sc->tx_mbuf_ptr[sw_tx_chain_cons]);
6366 			sc->tx_mbuf_ptr[sw_tx_chain_cons] = NULL;
6367 			DBRUN(sc->debug_tx_mbuf_alloc--);
6368 
6369 			ifp->if_opackets++;
6370 		}
6371 
6372 		sc->used_tx_bd--;
6373 		sw_tx_cons = NEXT_TX_BD(sw_tx_cons);
6374 
6375 		/* Refresh hw_cons to see if there's new work. */
6376 		hw_tx_cons = sc->hw_tx_cons = bce_get_hw_tx_cons(sc);
6377 
6378 		/* Prevent speculative reads of the status block. */
6379 		bus_space_barrier(sc->bce_btag, sc->bce_bhandle, 0, 0,
6380 		    BUS_SPACE_BARRIER_READ);
6381 	}
6382 
6383 	/* Clear the TX timeout timer. */
6384 	sc->watchdog_timer = 0;
6385 
6386 	/* Clear the tx hardware queue full flag. */
6387 	if (sc->used_tx_bd < sc->max_tx_bd) {
6388 		DBRUNIF((ifp->if_drv_flags & IFF_DRV_OACTIVE),
6389 		    DBPRINT(sc, BCE_INFO_SEND,
6390 		    "%s(): Open TX chain! %d/%d (used/total)\n",
6391 		    __FUNCTION__, sc->used_tx_bd, sc->max_tx_bd));
6392 		ifp->if_drv_flags &= ~IFF_DRV_OACTIVE;
6393 	}
6394 
6395 	sc->tx_cons = sw_tx_cons;
6396 
6397 	DBPRINT(sc, BCE_EXTREME_SEND, "%s(exit): tx_prod = 0x%04X, "
6398 	    "tx_cons = 0x%04X, tx_prod_bseq = 0x%08X\n",
6399 	    __FUNCTION__, sc->tx_prod, sc->tx_cons, sc->tx_prod_bseq);
6400 	DBEXIT(BCE_VERBOSE_SEND | BCE_VERBOSE_INTR);
6401 }
6402 
6403 
6404 /****************************************************************************/
6405 /* Disables interrupt generation.                                           */
6406 /*                                                                          */
6407 /* Returns:                                                                 */
6408 /*   Nothing.                                                               */
6409 /****************************************************************************/
6410 static void
6411 bce_disable_intr(struct bce_softc *sc)
6412 {
6413 	DBENTER(BCE_VERBOSE_INTR);
6414 
6415 	REG_WR(sc, BCE_PCICFG_INT_ACK_CMD, BCE_PCICFG_INT_ACK_CMD_MASK_INT);
6416 	REG_RD(sc, BCE_PCICFG_INT_ACK_CMD);
6417 
6418 	DBEXIT(BCE_VERBOSE_INTR);
6419 }
6420 
6421 
6422 /****************************************************************************/
6423 /* Enables interrupt generation.                                            */
6424 /*                                                                          */
6425 /* Returns:                                                                 */
6426 /*   Nothing.                                                               */
6427 /****************************************************************************/
6428 static void
6429 bce_enable_intr(struct bce_softc *sc, int coal_now)
6430 {
6431 	DBENTER(BCE_VERBOSE_INTR);
6432 
6433 	REG_WR(sc, BCE_PCICFG_INT_ACK_CMD,
6434 	    BCE_PCICFG_INT_ACK_CMD_INDEX_VALID |
6435 	    BCE_PCICFG_INT_ACK_CMD_MASK_INT | sc->last_status_idx);
6436 
6437 	REG_WR(sc, BCE_PCICFG_INT_ACK_CMD,
6438 	    BCE_PCICFG_INT_ACK_CMD_INDEX_VALID | sc->last_status_idx);
6439 
6440 	/* Force an immediate interrupt (whether there is new data or not). */
6441 	if (coal_now)
6442 		REG_WR(sc, BCE_HC_COMMAND, sc->hc_command | BCE_HC_COMMAND_COAL_NOW);
6443 
6444 	DBEXIT(BCE_VERBOSE_INTR);
6445 }
6446 
6447 
6448 /****************************************************************************/
6449 /* Handles controller initialization.                                       */
6450 /*                                                                          */
6451 /* Returns:                                                                 */
6452 /*   Nothing.                                                               */
6453 /****************************************************************************/
6454 static void
6455 bce_init_locked(struct bce_softc *sc)
6456 {
6457 	struct ifnet *ifp;
6458 	u32 ether_mtu = 0;
6459 
6460 	DBENTER(BCE_VERBOSE_RESET);
6461 
6462 	BCE_LOCK_ASSERT(sc);
6463 
6464 	ifp = sc->bce_ifp;
6465 
6466 	/* Check if the driver is still running and bail out if it is. */
6467 	if (ifp->if_drv_flags & IFF_DRV_RUNNING)
6468 		goto bce_init_locked_exit;
6469 
6470 	bce_stop(sc);
6471 
6472 	if (bce_reset(sc, BCE_DRV_MSG_CODE_RESET)) {
6473 		BCE_PRINTF("%s(%d): Controller reset failed!\n",
6474 		    __FILE__, __LINE__);
6475 		goto bce_init_locked_exit;
6476 	}
6477 
6478 	if (bce_chipinit(sc)) {
6479 		BCE_PRINTF("%s(%d): Controller initialization failed!\n",
6480 		    __FILE__, __LINE__);
6481 		goto bce_init_locked_exit;
6482 	}
6483 
6484 	if (bce_blockinit(sc)) {
6485 		BCE_PRINTF("%s(%d): Block initialization failed!\n",
6486 		    __FILE__, __LINE__);
6487 		goto bce_init_locked_exit;
6488 	}
6489 
6490 	/* Load our MAC address. */
6491 	bcopy(IF_LLADDR(sc->bce_ifp), sc->eaddr, ETHER_ADDR_LEN);
6492 	bce_set_mac_addr(sc);
6493 
6494 	/*
6495 	 * Calculate and program the hardware Ethernet MTU
6496 	 * size. Be generous on the receive if we have room.
6497 	 */
6498 #ifdef BCE_JUMBO_HDRSPLIT
6499 	if (ifp->if_mtu <= (sc->rx_bd_mbuf_data_len +
6500 	    sc->pg_bd_mbuf_alloc_size))
6501 		ether_mtu = sc->rx_bd_mbuf_data_len +
6502 		    sc->pg_bd_mbuf_alloc_size;
6503 #else
6504 	if (ifp->if_mtu <= sc->rx_bd_mbuf_data_len)
6505 		ether_mtu = sc->rx_bd_mbuf_data_len;
6506 #endif
6507 	else
6508 		ether_mtu = ifp->if_mtu;
6509 
6510 	ether_mtu += ETHER_HDR_LEN + ETHER_VLAN_ENCAP_LEN + ETHER_CRC_LEN;
6511 
6512 	DBPRINT(sc, BCE_INFO_MISC, "%s(): setting h/w mtu = %d\n",
6513 	    __FUNCTION__, ether_mtu);
6514 
6515 	/* Program the mtu, enabling jumbo frame support if necessary. */
6516 	if (ether_mtu > (ETHER_MAX_LEN + ETHER_VLAN_ENCAP_LEN))
6517 		REG_WR(sc, BCE_EMAC_RX_MTU_SIZE,
6518 		    min(ether_mtu, BCE_MAX_JUMBO_ETHER_MTU) |
6519 		    BCE_EMAC_RX_MTU_SIZE_JUMBO_ENA);
6520 	else
6521 		REG_WR(sc, BCE_EMAC_RX_MTU_SIZE, ether_mtu);
6522 
6523 	DBPRINT(sc, BCE_INFO_LOAD,
6524 	    "%s(): rx_bd_mbuf_alloc_size = %d, rx_bce_mbuf_data_len = %d, "
6525 	    "rx_bd_mbuf_align_pad = %d\n", __FUNCTION__,
6526 	    sc->rx_bd_mbuf_alloc_size, sc->rx_bd_mbuf_data_len,
6527 	    sc->rx_bd_mbuf_align_pad);
6528 
6529 	/* Program appropriate promiscuous/multicast filtering. */
6530 	bce_set_rx_mode(sc);
6531 
6532 #ifdef BCE_JUMBO_HDRSPLIT
6533 	DBPRINT(sc, BCE_INFO_LOAD, "%s(): pg_bd_mbuf_alloc_size = %d\n",
6534 	    __FUNCTION__, sc->pg_bd_mbuf_alloc_size);
6535 
6536 	/* Init page buffer descriptor chain. */
6537 	bce_init_pg_chain(sc);
6538 #endif
6539 
6540 	/* Init RX buffer descriptor chain. */
6541 	bce_init_rx_chain(sc);
6542 
6543 	/* Init TX buffer descriptor chain. */
6544 	bce_init_tx_chain(sc);
6545 
6546 	/* Enable host interrupts. */
6547 	bce_enable_intr(sc, 1);
6548 
6549 	bce_ifmedia_upd_locked(ifp);
6550 
6551 	/* Let the OS know the driver is up and running. */
6552 	ifp->if_drv_flags |= IFF_DRV_RUNNING;
6553 	ifp->if_drv_flags &= ~IFF_DRV_OACTIVE;
6554 
6555 	callout_reset(&sc->bce_tick_callout, hz, bce_tick, sc);
6556 
6557 bce_init_locked_exit:
6558 	DBEXIT(BCE_VERBOSE_RESET);
6559 }
6560 
6561 
6562 /****************************************************************************/
6563 /* Initialize the controller just enough so that any management firmware    */
6564 /* running on the device will continue to operate correctly.                */
6565 /*                                                                          */
6566 /* Returns:                                                                 */
6567 /*   Nothing.                                                               */
6568 /****************************************************************************/
6569 static void
6570 bce_mgmt_init_locked(struct bce_softc *sc)
6571 {
6572 	struct ifnet *ifp;
6573 
6574 	DBENTER(BCE_VERBOSE_RESET);
6575 
6576 	BCE_LOCK_ASSERT(sc);
6577 
6578 	/* Bail out if management firmware is not running. */
6579 	if (!(sc->bce_flags & BCE_MFW_ENABLE_FLAG)) {
6580 		DBPRINT(sc, BCE_VERBOSE_SPECIAL,
6581 		    "No management firmware running...\n");
6582 		goto bce_mgmt_init_locked_exit;
6583 	}
6584 
6585 	ifp = sc->bce_ifp;
6586 
6587 	/* Enable all critical blocks in the MAC. */
6588 	REG_WR(sc, BCE_MISC_ENABLE_SET_BITS, BCE_MISC_ENABLE_DEFAULT);
6589 	REG_RD(sc, BCE_MISC_ENABLE_SET_BITS);
6590 	DELAY(20);
6591 
6592 	bce_ifmedia_upd_locked(ifp);
6593 
6594 bce_mgmt_init_locked_exit:
6595 	DBEXIT(BCE_VERBOSE_RESET);
6596 }
6597 
6598 
6599 /****************************************************************************/
6600 /* Handles controller initialization when called from an unlocked routine.  */
6601 /*                                                                          */
6602 /* Returns:                                                                 */
6603 /*   Nothing.                                                               */
6604 /****************************************************************************/
6605 static void
6606 bce_init(void *xsc)
6607 {
6608 	struct bce_softc *sc = xsc;
6609 
6610 	DBENTER(BCE_VERBOSE_RESET);
6611 
6612 	BCE_LOCK(sc);
6613 	bce_init_locked(sc);
6614 	BCE_UNLOCK(sc);
6615 
6616 	DBEXIT(BCE_VERBOSE_RESET);
6617 }
6618 
6619 
6620 static struct mbuf *
6621 bce_tso_setup(struct bce_softc *sc, struct mbuf **m_head, u16 *flags)
6622 {
6623 	struct mbuf *m;
6624 	struct ether_header *eh;
6625 	struct ip *ip;
6626 	struct tcphdr *th;
6627 	u16 etype;
6628 	int hdr_len, ip_hlen = 0, tcp_hlen = 0, ip_len = 0;
6629 
6630 	DBRUN(sc->requested_tso_frames++);
6631 	/* Controller requires to monify mbuf chains. */
6632 	if (M_WRITABLE(*m_head) == 0) {
6633 		m = m_dup(*m_head, M_DONTWAIT);
6634 		m_freem(*m_head);
6635 		if (m == NULL) {
6636 			sc->mbuf_alloc_failed_count++;
6637 			*m_head = NULL;
6638 			return (NULL);
6639 		}
6640 		*m_head = m;
6641 	}
6642 	/*
6643 	 * For TSO the controller needs two pieces of info,
6644 	 * the MSS and the IP+TCP options length.
6645 	 */
6646 	m = m_pullup(*m_head, sizeof(struct ether_header) + sizeof(struct ip));
6647 	if (m == NULL) {
6648 		*m_head = NULL;
6649 		return (NULL);
6650 	}
6651 	eh = mtod(m, struct ether_header *);
6652 	etype = ntohs(eh->ether_type);
6653 
6654 	/* Check for supported TSO Ethernet types (only IPv4 for now) */
6655 	switch (etype) {
6656 	case ETHERTYPE_IP:
6657 		ip = (struct ip *)(m->m_data + sizeof(struct ether_header));
6658 		/* TSO only supported for TCP protocol. */
6659 		if (ip->ip_p != IPPROTO_TCP) {
6660 			BCE_PRINTF("%s(%d): TSO enabled for non-TCP frame!.\n",
6661 			    __FILE__, __LINE__);
6662 			m_freem(*m_head);
6663 			*m_head = NULL;
6664 			return (NULL);
6665 		}
6666 
6667 		/* Get IP header length in bytes (min 20) */
6668 		ip_hlen = ip->ip_hl << 2;
6669 		m = m_pullup(*m_head, sizeof(struct ether_header) + ip_hlen +
6670 		    sizeof(struct tcphdr));
6671 		if (m == NULL) {
6672 			*m_head = NULL;
6673 			return (NULL);
6674 		}
6675 
6676 		/* Get the TCP header length in bytes (min 20) */
6677 		th = (struct tcphdr *)((caddr_t)ip + ip_hlen);
6678 		tcp_hlen = (th->th_off << 2);
6679 
6680 		/* Make sure all IP/TCP options live in the same buffer. */
6681 		m = m_pullup(*m_head,  sizeof(struct ether_header)+ ip_hlen +
6682 		    tcp_hlen);
6683 		if (m == NULL) {
6684 			*m_head = NULL;
6685 			return (NULL);
6686 		}
6687 
6688 		/* IP header length and checksum will be calc'd by hardware */
6689 		ip_len = ip->ip_len;
6690 		ip->ip_len = 0;
6691 		ip->ip_sum = 0;
6692 		break;
6693 	case ETHERTYPE_IPV6:
6694 		BCE_PRINTF("%s(%d): TSO over IPv6 not supported!.\n",
6695 		    __FILE__, __LINE__);
6696 		m_freem(*m_head);
6697 		*m_head = NULL;
6698 		return (NULL);
6699 		/* NOT REACHED */
6700 	default:
6701 		BCE_PRINTF("%s(%d): TSO enabled for unsupported protocol!.\n",
6702 		    __FILE__, __LINE__);
6703 		m_freem(*m_head);
6704 		*m_head = NULL;
6705 		return (NULL);
6706 	}
6707 
6708 	hdr_len = sizeof(struct ether_header) + ip_hlen + tcp_hlen;
6709 
6710 	DBPRINT(sc, BCE_EXTREME_SEND, "%s(): hdr_len = %d, e_hlen = %d, "
6711 	    "ip_hlen = %d, tcp_hlen = %d, ip_len = %d\n",
6712 	    __FUNCTION__, hdr_len, (int) sizeof(struct ether_header), ip_hlen,
6713 	    tcp_hlen, ip_len);
6714 
6715 	/* Set the LSO flag in the TX BD */
6716 	*flags |= TX_BD_FLAGS_SW_LSO;
6717 	/* Set the length of IP + TCP options (in 32 bit words) */
6718 	*flags |= (((ip_hlen + tcp_hlen - sizeof(struct ip) -
6719 	    sizeof(struct tcphdr)) >> 2) << 8);
6720 	return (*m_head);
6721 }
6722 
6723 
6724 /****************************************************************************/
6725 /* Encapsultes an mbuf cluster into the tx_bd chain structure and makes the */
6726 /* memory visible to the controller.                                        */
6727 /*                                                                          */
6728 /* Returns:                                                                 */
6729 /*   0 for success, positive value for failure.                             */
6730 /* Modified:                                                                */
6731 /*   m_head: May be set to NULL if MBUF is excessively fragmented.          */
6732 /****************************************************************************/
6733 static int
6734 bce_tx_encap(struct bce_softc *sc, struct mbuf **m_head)
6735 {
6736 	bus_dma_segment_t segs[BCE_MAX_SEGMENTS];
6737 	bus_dmamap_t map;
6738 	struct tx_bd *txbd = NULL;
6739 	struct mbuf *m0;
6740 	u16 prod, chain_prod, mss = 0, vlan_tag = 0, flags = 0;
6741 	u32 prod_bseq;
6742 
6743 #ifdef BCE_DEBUG
6744 	u16 debug_prod;
6745 #endif
6746 	int i, error, nsegs, rc = 0;
6747 
6748 	DBENTER(BCE_VERBOSE_SEND);
6749 	DBPRINT(sc, BCE_INFO_SEND,
6750 	    "%s(enter): tx_prod = 0x%04X, tx_chain_prod = %04X, "
6751 	    "tx_prod_bseq = 0x%08X\n",
6752 	    __FUNCTION__, sc->tx_prod, (u16) TX_CHAIN_IDX(sc->tx_prod),
6753 	    sc->tx_prod_bseq);
6754 
6755 	/* Transfer any checksum offload flags to the bd. */
6756 	m0 = *m_head;
6757 	if (m0->m_pkthdr.csum_flags) {
6758 		if (m0->m_pkthdr.csum_flags & CSUM_TSO) {
6759 			m0 = bce_tso_setup(sc, m_head, &flags);
6760 			if (m0 == NULL)
6761 				goto bce_tx_encap_exit;
6762 			mss = htole16(m0->m_pkthdr.tso_segsz);
6763 		} else {
6764 			if (m0->m_pkthdr.csum_flags & CSUM_IP)
6765 				flags |= TX_BD_FLAGS_IP_CKSUM;
6766 			if (m0->m_pkthdr.csum_flags & (CSUM_TCP | CSUM_UDP))
6767 				flags |= TX_BD_FLAGS_TCP_UDP_CKSUM;
6768 		}
6769 	}
6770 
6771 	/* Transfer any VLAN tags to the bd. */
6772 	if (m0->m_flags & M_VLANTAG) {
6773 		flags |= TX_BD_FLAGS_VLAN_TAG;
6774 		vlan_tag = m0->m_pkthdr.ether_vtag;
6775 	}
6776 
6777 	/* Map the mbuf into DMAable memory. */
6778 	prod = sc->tx_prod;
6779 	chain_prod = TX_CHAIN_IDX(prod);
6780 	map = sc->tx_mbuf_map[chain_prod];
6781 
6782 	/* Map the mbuf into our DMA address space. */
6783 	error = bus_dmamap_load_mbuf_sg(sc->tx_mbuf_tag, map, m0,
6784 	    segs, &nsegs, BUS_DMA_NOWAIT);
6785 
6786 	/* Check if the DMA mapping was successful */
6787 	if (error == EFBIG) {
6788 
6789 		sc->fragmented_mbuf_count++;
6790 
6791 		/* Try to defrag the mbuf. */
6792 		m0 = m_collapse(*m_head, M_DONTWAIT, BCE_MAX_SEGMENTS);
6793 		if (m0 == NULL) {
6794 			/* Defrag was unsuccessful */
6795 			m_freem(*m_head);
6796 			*m_head = NULL;
6797 			sc->mbuf_alloc_failed_count++;
6798 			rc = ENOBUFS;
6799 			goto bce_tx_encap_exit;
6800 		}
6801 
6802 		/* Defrag was successful, try mapping again */
6803 		*m_head = m0;
6804 		error = bus_dmamap_load_mbuf_sg(sc->tx_mbuf_tag, map, m0,
6805 		    segs, &nsegs, BUS_DMA_NOWAIT);
6806 
6807 		/* Still getting an error after a defrag. */
6808 		if (error == ENOMEM) {
6809 			/* Insufficient DMA buffers available. */
6810 			sc->dma_map_addr_tx_failed_count++;
6811 			rc = error;
6812 			goto bce_tx_encap_exit;
6813 		} else if (error != 0) {
6814 			/* Release it and return an error. */
6815 			BCE_PRINTF("%s(%d): Unknown error mapping mbuf into "
6816 			    "TX chain!\n", __FILE__, __LINE__);
6817 			m_freem(m0);
6818 			*m_head = NULL;
6819 			sc->dma_map_addr_tx_failed_count++;
6820 			rc = ENOBUFS;
6821 			goto bce_tx_encap_exit;
6822 		}
6823 	} else if (error == ENOMEM) {
6824 		/* Insufficient DMA buffers available. */
6825 		sc->dma_map_addr_tx_failed_count++;
6826 		rc = error;
6827 		goto bce_tx_encap_exit;
6828 	} else if (error != 0) {
6829 		m_freem(m0);
6830 		*m_head = NULL;
6831 		sc->dma_map_addr_tx_failed_count++;
6832 		rc = error;
6833 		goto bce_tx_encap_exit;
6834 	}
6835 
6836 	/* Make sure there's room in the chain */
6837 	if (nsegs > (sc->max_tx_bd - sc->used_tx_bd)) {
6838 		bus_dmamap_unload(sc->tx_mbuf_tag, map);
6839 		rc = ENOBUFS;
6840 		goto bce_tx_encap_exit;
6841 	}
6842 
6843 	/* prod points to an empty tx_bd at this point. */
6844 	prod_bseq  = sc->tx_prod_bseq;
6845 
6846 #ifdef BCE_DEBUG
6847 	debug_prod = chain_prod;
6848 #endif
6849 
6850 	DBPRINT(sc, BCE_INFO_SEND,
6851 	    "%s(start): prod = 0x%04X, chain_prod = 0x%04X, "
6852 	    "prod_bseq = 0x%08X\n",
6853 	    __FUNCTION__, prod, chain_prod, prod_bseq);
6854 
6855 	/*
6856 	 * Cycle through each mbuf segment that makes up
6857 	 * the outgoing frame, gathering the mapping info
6858 	 * for that segment and creating a tx_bd for
6859 	 * the mbuf.
6860 	 */
6861 	for (i = 0; i < nsegs ; i++) {
6862 
6863 		chain_prod = TX_CHAIN_IDX(prod);
6864 		txbd= &sc->tx_bd_chain[TX_PAGE(chain_prod)]
6865 		    [TX_IDX(chain_prod)];
6866 
6867 		txbd->tx_bd_haddr_lo = htole32(BCE_ADDR_LO(segs[i].ds_addr));
6868 		txbd->tx_bd_haddr_hi = htole32(BCE_ADDR_HI(segs[i].ds_addr));
6869 		txbd->tx_bd_mss_nbytes = htole32(mss << 16) |
6870 		    htole16(segs[i].ds_len);
6871 		txbd->tx_bd_vlan_tag = htole16(vlan_tag);
6872 		txbd->tx_bd_flags = htole16(flags);
6873 		prod_bseq += segs[i].ds_len;
6874 		if (i == 0)
6875 			txbd->tx_bd_flags |= htole16(TX_BD_FLAGS_START);
6876 		prod = NEXT_TX_BD(prod);
6877 	}
6878 
6879 	/* Set the END flag on the last TX buffer descriptor. */
6880 	txbd->tx_bd_flags |= htole16(TX_BD_FLAGS_END);
6881 
6882 	DBRUNMSG(BCE_EXTREME_SEND, bce_dump_tx_chain(sc, debug_prod, nsegs));
6883 
6884 	DBPRINT(sc, BCE_INFO_SEND,
6885 	    "%s( end ): prod = 0x%04X, chain_prod = 0x%04X, "
6886 	    "prod_bseq = 0x%08X\n",
6887 	    __FUNCTION__, prod, chain_prod, prod_bseq);
6888 
6889 	/*
6890 	 * Ensure that the mbuf pointer for this transmission
6891 	 * is placed at the array index of the last
6892 	 * descriptor in this chain.  This is done
6893 	 * because a single map is used for all
6894 	 * segments of the mbuf and we don't want to
6895 	 * unload the map before all of the segments
6896 	 * have been freed.
6897 	 */
6898 	sc->tx_mbuf_ptr[chain_prod] = m0;
6899 	sc->used_tx_bd += nsegs;
6900 
6901 	/* Update some debug statistic counters */
6902 	DBRUNIF((sc->used_tx_bd > sc->tx_hi_watermark),
6903 	    sc->tx_hi_watermark = sc->used_tx_bd);
6904 	DBRUNIF((sc->used_tx_bd == sc->max_tx_bd), sc->tx_full_count++);
6905 	DBRUNIF(sc->debug_tx_mbuf_alloc++);
6906 
6907 	DBRUNMSG(BCE_EXTREME_SEND, bce_dump_tx_mbuf_chain(sc, chain_prod, 1));
6908 
6909 	/* prod points to the next free tx_bd at this point. */
6910 	sc->tx_prod = prod;
6911 	sc->tx_prod_bseq = prod_bseq;
6912 
6913 	DBPRINT(sc, BCE_INFO_SEND,
6914 	    "%s(exit): prod = 0x%04X, chain_prod = %04X, "
6915 	    "prod_bseq = 0x%08X\n", __FUNCTION__,
6916 	    sc->tx_prod, (u16) TX_CHAIN_IDX(sc->tx_prod),
6917 	    sc->tx_prod_bseq);
6918 
6919 bce_tx_encap_exit:
6920 	DBEXIT(BCE_VERBOSE_SEND);
6921 	return(rc);
6922 }
6923 
6924 
6925 /****************************************************************************/
6926 /* Main transmit routine when called from another routine with a lock.      */
6927 /*                                                                          */
6928 /* Returns:                                                                 */
6929 /*   Nothing.                                                               */
6930 /****************************************************************************/
6931 static void
6932 bce_start_locked(struct ifnet *ifp)
6933 {
6934 	struct bce_softc *sc = ifp->if_softc;
6935 	struct mbuf *m_head = NULL;
6936 	int count = 0;
6937 	u16 tx_prod, tx_chain_prod;
6938 
6939 	DBENTER(BCE_VERBOSE_SEND | BCE_VERBOSE_CTX);
6940 
6941 	BCE_LOCK_ASSERT(sc);
6942 
6943 	/* prod points to the next free tx_bd. */
6944 	tx_prod = sc->tx_prod;
6945 	tx_chain_prod = TX_CHAIN_IDX(tx_prod);
6946 
6947 	DBPRINT(sc, BCE_INFO_SEND,
6948 	    "%s(enter): tx_prod = 0x%04X, tx_chain_prod = 0x%04X, "
6949 	    "tx_prod_bseq = 0x%08X\n",
6950 	    __FUNCTION__, tx_prod, tx_chain_prod, sc->tx_prod_bseq);
6951 
6952 	/* If there's no link or the transmit queue is empty then just exit. */
6953 	if (sc->bce_link_up == FALSE) {
6954 		DBPRINT(sc, BCE_INFO_SEND, "%s(): No link.\n",
6955 		    __FUNCTION__);
6956 		goto bce_start_locked_exit;
6957 	}
6958 
6959 	if (IFQ_DRV_IS_EMPTY(&ifp->if_snd)) {
6960 		DBPRINT(sc, BCE_INFO_SEND, "%s(): Transmit queue empty.\n",
6961 		    __FUNCTION__);
6962 		goto bce_start_locked_exit;
6963 	}
6964 
6965 	/*
6966 	 * Keep adding entries while there is space in the ring.
6967 	 */
6968 	while (sc->used_tx_bd < sc->max_tx_bd) {
6969 
6970 		/* Check for any frames to send. */
6971 		IFQ_DRV_DEQUEUE(&ifp->if_snd, m_head);
6972 
6973 		/* Stop when the transmit queue is empty. */
6974 		if (m_head == NULL)
6975 			break;
6976 
6977 		/*
6978 		 * Pack the data into the transmit ring. If we
6979 		 * don't have room, place the mbuf back at the
6980 		 * head of the queue and set the OACTIVE flag
6981 		 * to wait for the NIC to drain the chain.
6982 		 */
6983 		if (bce_tx_encap(sc, &m_head)) {
6984 			if (m_head != NULL)
6985 				IFQ_DRV_PREPEND(&ifp->if_snd, m_head);
6986 			ifp->if_drv_flags |= IFF_DRV_OACTIVE;
6987 			DBPRINT(sc, BCE_INFO_SEND,
6988 			    "TX chain is closed for business! Total "
6989 			    "tx_bd used = %d\n", sc->used_tx_bd);
6990 			break;
6991 		}
6992 
6993 		count++;
6994 
6995 		/* Send a copy of the frame to any BPF listeners. */
6996 		ETHER_BPF_MTAP(ifp, m_head);
6997 	}
6998 
6999 	/* Exit if no packets were dequeued. */
7000 	if (count == 0) {
7001 		DBPRINT(sc, BCE_VERBOSE_SEND, "%s(): No packets were "
7002 		    "dequeued\n", __FUNCTION__);
7003 		goto bce_start_locked_exit;
7004 	}
7005 
7006 	DBPRINT(sc, BCE_VERBOSE_SEND, "%s(): Inserted %d frames into "
7007 	    "send queue.\n", __FUNCTION__, count);
7008 
7009 	REG_WR(sc, BCE_MQ_COMMAND, REG_RD(sc, BCE_MQ_COMMAND) |
7010 	    BCE_MQ_COMMAND_NO_MAP_ERROR);
7011 
7012 	/* Write the mailbox and tell the chip about the waiting tx_bd's. */
7013 	DBPRINT(sc, BCE_VERBOSE_SEND, "%s(): MB_GET_CID_ADDR(TX_CID) = "
7014 	    "0x%08X; BCE_L2MQ_TX_HOST_BIDX = 0x%08X, sc->tx_prod = 0x%04X\n",
7015 	    __FUNCTION__, MB_GET_CID_ADDR(TX_CID),
7016 	    BCE_L2MQ_TX_HOST_BIDX, sc->tx_prod);
7017 	REG_WR16(sc, MB_GET_CID_ADDR(TX_CID) +
7018 	    BCE_L2MQ_TX_HOST_BIDX, sc->tx_prod);
7019 
7020 	DBPRINT(sc, BCE_VERBOSE_SEND, "%s(): MB_GET_CID_ADDR(TX_CID) = "
7021 	    "0x%08X; BCE_L2MQ_TX_HOST_BSEQ = 0x%08X, sc->tx_prod_bseq = "
7022 	    "0x%04X\n",	__FUNCTION__, MB_GET_CID_ADDR(TX_CID),
7023 	    BCE_L2MQ_TX_HOST_BSEQ, sc->tx_prod_bseq);
7024 	REG_WR(sc, MB_GET_CID_ADDR(TX_CID) + BCE_L2MQ_TX_HOST_BSEQ, sc->tx_prod_bseq);
7025 
7026 	/* Set the tx timeout. */
7027 	sc->watchdog_timer = BCE_TX_TIMEOUT;
7028 
7029 	DBRUNMSG(BCE_VERBOSE_SEND, bce_dump_ctx(sc, TX_CID));
7030 	DBRUNMSG(BCE_VERBOSE_SEND, bce_dump_mq_regs(sc));
7031 
7032 bce_start_locked_exit:
7033 	DBEXIT(BCE_VERBOSE_SEND | BCE_VERBOSE_CTX);
7034 	return;
7035 }
7036 
7037 
7038 /****************************************************************************/
7039 /* Main transmit routine when called from another routine without a lock.   */
7040 /*                                                                          */
7041 /* Returns:                                                                 */
7042 /*   Nothing.                                                               */
7043 /****************************************************************************/
7044 static void
7045 bce_start(struct ifnet *ifp)
7046 {
7047 	struct bce_softc *sc = ifp->if_softc;
7048 
7049 	DBENTER(BCE_VERBOSE_SEND);
7050 
7051 	BCE_LOCK(sc);
7052 	bce_start_locked(ifp);
7053 	BCE_UNLOCK(sc);
7054 
7055 	DBEXIT(BCE_VERBOSE_SEND);
7056 }
7057 
7058 
7059 /****************************************************************************/
7060 /* Handles any IOCTL calls from the operating system.                       */
7061 /*                                                                          */
7062 /* Returns:                                                                 */
7063 /*   0 for success, positive value for failure.                             */
7064 /****************************************************************************/
7065 static int
7066 bce_ioctl(struct ifnet *ifp, u_long command, caddr_t data)
7067 {
7068 	struct bce_softc *sc = ifp->if_softc;
7069 	struct ifreq *ifr = (struct ifreq *) data;
7070 	struct mii_data *mii;
7071 	int mask, error = 0, reinit;
7072 
7073 	DBENTER(BCE_VERBOSE_MISC);
7074 
7075 	switch(command) {
7076 
7077 	/* Set the interface MTU. */
7078 	case SIOCSIFMTU:
7079 		/* Check that the MTU setting is supported. */
7080 		if ((ifr->ifr_mtu < BCE_MIN_MTU) ||
7081 			(ifr->ifr_mtu > BCE_MAX_JUMBO_MTU)) {
7082 			error = EINVAL;
7083 			break;
7084 		}
7085 
7086 		DBPRINT(sc, BCE_INFO_MISC,
7087 		    "SIOCSIFMTU: Changing MTU from %d to %d\n",
7088 		    (int) ifp->if_mtu, (int) ifr->ifr_mtu);
7089 
7090 		BCE_LOCK(sc);
7091 		ifp->if_mtu = ifr->ifr_mtu;
7092 		reinit = 0;
7093 		if (ifp->if_drv_flags & IFF_DRV_RUNNING) {
7094 			/*
7095 			 * Because allocation size is used in RX
7096 			 * buffer allocation, stop controller if
7097 			 * it is already running.
7098 			 */
7099 			bce_stop(sc);
7100 			reinit = 1;
7101 		}
7102 #ifdef BCE_JUMBO_HDRSPLIT
7103 		/* No buffer allocation size changes are necessary. */
7104 #else
7105 		/* Recalculate our buffer allocation sizes. */
7106 		if ((ifp->if_mtu + ETHER_HDR_LEN + ETHER_VLAN_ENCAP_LEN +
7107 		     ETHER_CRC_LEN) > MCLBYTES) {
7108 			sc->rx_bd_mbuf_alloc_size = MJUM9BYTES;
7109 			sc->rx_bd_mbuf_align_pad  =
7110 			    roundup2(MJUM9BYTES, 16) - MJUM9BYTES;
7111 			sc->rx_bd_mbuf_data_len =
7112 			    sc->rx_bd_mbuf_alloc_size -
7113 			    sc->rx_bd_mbuf_align_pad;
7114 		} else {
7115 			sc->rx_bd_mbuf_alloc_size = MCLBYTES;
7116 			sc->rx_bd_mbuf_align_pad  =
7117 			    roundup2(MCLBYTES, 16) - MCLBYTES;
7118 			sc->rx_bd_mbuf_data_len =
7119 			    sc->rx_bd_mbuf_alloc_size -
7120 			    sc->rx_bd_mbuf_align_pad;
7121 		}
7122 #endif
7123 
7124 		if (reinit != 0)
7125 			bce_init_locked(sc);
7126 		BCE_UNLOCK(sc);
7127 		break;
7128 
7129 	/* Set interface flags. */
7130 	case SIOCSIFFLAGS:
7131 		DBPRINT(sc, BCE_VERBOSE_SPECIAL, "Received SIOCSIFFLAGS\n");
7132 
7133 		BCE_LOCK(sc);
7134 
7135 		/* Check if the interface is up. */
7136 		if (ifp->if_flags & IFF_UP) {
7137 			if (ifp->if_drv_flags & IFF_DRV_RUNNING) {
7138 				/* Change promiscuous/multicast flags as necessary. */
7139 				bce_set_rx_mode(sc);
7140 			} else {
7141 				/* Start the HW */
7142 				bce_init_locked(sc);
7143 			}
7144 		} else {
7145 			/* The interface is down, check if driver is running. */
7146 			if (ifp->if_drv_flags & IFF_DRV_RUNNING) {
7147 				bce_stop(sc);
7148 
7149 				/* If MFW is running, restart the controller a bit. */
7150 				if (sc->bce_flags & BCE_MFW_ENABLE_FLAG) {
7151 					bce_reset(sc, BCE_DRV_MSG_CODE_RESET);
7152 					bce_chipinit(sc);
7153 					bce_mgmt_init_locked(sc);
7154 				}
7155 			}
7156 		}
7157 
7158 		BCE_UNLOCK(sc);
7159 		break;
7160 
7161 	/* Add/Delete multicast address */
7162 	case SIOCADDMULTI:
7163 	case SIOCDELMULTI:
7164 		DBPRINT(sc, BCE_VERBOSE_MISC,
7165 		    "Received SIOCADDMULTI/SIOCDELMULTI\n");
7166 
7167 		BCE_LOCK(sc);
7168 		if (ifp->if_drv_flags & IFF_DRV_RUNNING)
7169 			bce_set_rx_mode(sc);
7170 		BCE_UNLOCK(sc);
7171 
7172 		break;
7173 
7174 	/* Set/Get Interface media */
7175 	case SIOCSIFMEDIA:
7176 	case SIOCGIFMEDIA:
7177 		DBPRINT(sc, BCE_VERBOSE_MISC,
7178 		    "Received SIOCSIFMEDIA/SIOCGIFMEDIA\n");
7179 
7180 		mii = device_get_softc(sc->bce_miibus);
7181 		error = ifmedia_ioctl(ifp, ifr,
7182 		    &mii->mii_media, command);
7183 		break;
7184 
7185 	/* Set interface capability */
7186 	case SIOCSIFCAP:
7187 		mask = ifr->ifr_reqcap ^ ifp->if_capenable;
7188 		DBPRINT(sc, BCE_INFO_MISC,
7189 		    "Received SIOCSIFCAP = 0x%08X\n", (u32) mask);
7190 
7191 		/* Toggle the TX checksum capabilities enable flag. */
7192 		if (mask & IFCAP_TXCSUM &&
7193 		    ifp->if_capabilities & IFCAP_TXCSUM) {
7194 			ifp->if_capenable ^= IFCAP_TXCSUM;
7195 			if (IFCAP_TXCSUM & ifp->if_capenable)
7196 				ifp->if_hwassist |= BCE_IF_HWASSIST;
7197 			else
7198 				ifp->if_hwassist &= ~BCE_IF_HWASSIST;
7199 		}
7200 
7201 		/* Toggle the RX checksum capabilities enable flag. */
7202 		if (mask & IFCAP_RXCSUM &&
7203 		    ifp->if_capabilities & IFCAP_RXCSUM)
7204 			ifp->if_capenable ^= IFCAP_RXCSUM;
7205 
7206 		/* Toggle the TSO capabilities enable flag. */
7207 		if (bce_tso_enable && (mask & IFCAP_TSO4) &&
7208 		    ifp->if_capabilities & IFCAP_TSO4) {
7209 			ifp->if_capenable ^= IFCAP_TSO4;
7210 			if (IFCAP_TSO4 & ifp->if_capenable)
7211 				ifp->if_hwassist |= CSUM_TSO;
7212 			else
7213 				ifp->if_hwassist &= ~CSUM_TSO;
7214 		}
7215 
7216 		if (mask & IFCAP_VLAN_HWCSUM &&
7217 		    ifp->if_capabilities & IFCAP_VLAN_HWCSUM)
7218 			ifp->if_capenable ^= IFCAP_VLAN_HWCSUM;
7219 
7220 		if ((mask & IFCAP_VLAN_HWTSO) != 0 &&
7221 		    (ifp->if_capabilities & IFCAP_VLAN_HWTSO) != 0)
7222 			ifp->if_capenable ^= IFCAP_VLAN_HWTSO;
7223 		/*
7224 		 * Don't actually disable VLAN tag stripping as
7225 		 * management firmware (ASF/IPMI/UMP) requires the
7226 		 * feature. If VLAN tag stripping is disabled driver
7227 		 * will manually reconstruct the VLAN frame by
7228 		 * appending stripped VLAN tag.
7229 		 */
7230 		if ((mask & IFCAP_VLAN_HWTAGGING) != 0 &&
7231 		    (ifp->if_capabilities & IFCAP_VLAN_HWTAGGING)) {
7232 			ifp->if_capenable ^= IFCAP_VLAN_HWTAGGING;
7233 			if ((ifp->if_capenable & IFCAP_VLAN_HWTAGGING)
7234 			    == 0)
7235 				ifp->if_capenable &= ~IFCAP_VLAN_HWTSO;
7236 		}
7237 		VLAN_CAPABILITIES(ifp);
7238 		break;
7239 	default:
7240 		/* We don't know how to handle the IOCTL, pass it on. */
7241 		error = ether_ioctl(ifp, command, data);
7242 		break;
7243 	}
7244 
7245 	DBEXIT(BCE_VERBOSE_MISC);
7246 	return(error);
7247 }
7248 
7249 
7250 /****************************************************************************/
7251 /* Transmit timeout handler.                                                */
7252 /*                                                                          */
7253 /* Returns:                                                                 */
7254 /*   Nothing.                                                               */
7255 /****************************************************************************/
7256 static void
7257 bce_watchdog(struct bce_softc *sc)
7258 {
7259 	DBENTER(BCE_EXTREME_SEND);
7260 
7261 	BCE_LOCK_ASSERT(sc);
7262 
7263 	/* If the watchdog timer hasn't expired then just exit. */
7264 	if (sc->watchdog_timer == 0 || --sc->watchdog_timer)
7265 		goto bce_watchdog_exit;
7266 
7267 	/* If pause frames are active then don't reset the hardware. */
7268 	/* ToDo: Should we reset the timer here? */
7269 	if (REG_RD(sc, BCE_EMAC_TX_STATUS) & BCE_EMAC_TX_STATUS_XOFFED)
7270 		goto bce_watchdog_exit;
7271 
7272 	BCE_PRINTF("%s(%d): Watchdog timeout occurred, resetting!\n",
7273 		__FILE__, __LINE__);
7274 
7275 	DBRUNMSG(BCE_INFO,
7276 	    bce_dump_driver_state(sc);
7277 	    bce_dump_status_block(sc);
7278 	    bce_dump_stats_block(sc);
7279 	    bce_dump_ftqs(sc);
7280 	    bce_dump_txp_state(sc, 0);
7281 	    bce_dump_rxp_state(sc, 0);
7282 	    bce_dump_tpat_state(sc, 0);
7283 	    bce_dump_cp_state(sc, 0);
7284 	    bce_dump_com_state(sc, 0));
7285 
7286 	DBRUN(bce_breakpoint(sc));
7287 
7288 	sc->bce_ifp->if_drv_flags &= ~IFF_DRV_RUNNING;
7289 
7290 	bce_init_locked(sc);
7291 	sc->bce_ifp->if_oerrors++;
7292 
7293 bce_watchdog_exit:
7294 	DBEXIT(BCE_EXTREME_SEND);
7295 }
7296 
7297 
7298 /*
7299  * Interrupt handler.
7300  */
7301 /****************************************************************************/
7302 /* Main interrupt entry point.  Verifies that the controller generated the  */
7303 /* interrupt and then calls a separate routine for handle the various       */
7304 /* interrupt causes (PHY, TX, RX).                                          */
7305 /*                                                                          */
7306 /* Returns:                                                                 */
7307 /*   0 for success, positive value for failure.                             */
7308 /****************************************************************************/
7309 static void
7310 bce_intr(void *xsc)
7311 {
7312 	struct bce_softc *sc;
7313 	struct ifnet *ifp;
7314 	u32 status_attn_bits;
7315 	u16 hw_rx_cons, hw_tx_cons;
7316 
7317 	sc = xsc;
7318 	ifp = sc->bce_ifp;
7319 
7320 	DBENTER(BCE_VERBOSE_SEND | BCE_VERBOSE_RECV | BCE_VERBOSE_INTR);
7321 	DBRUNMSG(BCE_VERBOSE_INTR, bce_dump_status_block(sc));
7322 	DBRUNMSG(BCE_VERBOSE_INTR, bce_dump_stats_block(sc));
7323 
7324 	BCE_LOCK(sc);
7325 
7326 	DBRUN(sc->interrupts_generated++);
7327 
7328 	/* Synchnorize before we read from interface's status block */
7329 	bus_dmamap_sync(sc->status_tag, sc->status_map,
7330 	    BUS_DMASYNC_POSTREAD);
7331 
7332 	/*
7333 	 * If the hardware status block index
7334 	 * matches the last value read by the
7335 	 * driver and we haven't asserted our
7336 	 * interrupt then there's nothing to do.
7337 	 */
7338 	if ((sc->status_block->status_idx == sc->last_status_idx) &&
7339 	    (REG_RD(sc, BCE_PCICFG_MISC_STATUS) &
7340 	     BCE_PCICFG_MISC_STATUS_INTA_VALUE)) {
7341 		DBPRINT(sc, BCE_VERBOSE_INTR, "%s(): Spurious interrupt.\n",
7342 		    __FUNCTION__);
7343 		goto bce_intr_exit;
7344 	}
7345 
7346 	/* Ack the interrupt and stop others from occuring. */
7347 	REG_WR(sc, BCE_PCICFG_INT_ACK_CMD,
7348 	    BCE_PCICFG_INT_ACK_CMD_USE_INT_HC_PARAM |
7349 	    BCE_PCICFG_INT_ACK_CMD_MASK_INT);
7350 
7351 	/* Check if the hardware has finished any work. */
7352 	hw_rx_cons = bce_get_hw_rx_cons(sc);
7353 	hw_tx_cons = bce_get_hw_tx_cons(sc);
7354 
7355 	/* Keep processing data as long as there is work to do. */
7356 	for (;;) {
7357 
7358 		status_attn_bits = sc->status_block->status_attn_bits;
7359 
7360 		DBRUNIF(DB_RANDOMTRUE(unexpected_attention_sim_control),
7361 		    BCE_PRINTF("Simulating unexpected status attention "
7362 		    "bit set.");
7363 		    sc->unexpected_attention_sim_count++;
7364 		    status_attn_bits = status_attn_bits |
7365 		    STATUS_ATTN_BITS_PARITY_ERROR);
7366 
7367 		/* Was it a link change interrupt? */
7368 		if ((status_attn_bits & STATUS_ATTN_BITS_LINK_STATE) !=
7369 		    (sc->status_block->status_attn_bits_ack &
7370 		     STATUS_ATTN_BITS_LINK_STATE)) {
7371 			bce_phy_intr(sc);
7372 
7373 			/* Clear transient updates during link state change. */
7374 			REG_WR(sc, BCE_HC_COMMAND, sc->hc_command |
7375 			    BCE_HC_COMMAND_COAL_NOW_WO_INT);
7376 			REG_RD(sc, BCE_HC_COMMAND);
7377 		}
7378 
7379 		/* If any other attention is asserted, the chip is toast. */
7380 		if (((status_attn_bits & ~STATUS_ATTN_BITS_LINK_STATE) !=
7381 		    (sc->status_block->status_attn_bits_ack &
7382 		    ~STATUS_ATTN_BITS_LINK_STATE))) {
7383 
7384 			sc->unexpected_attention_count++;
7385 
7386 			BCE_PRINTF("%s(%d): Fatal attention detected: "
7387 			    "0x%08X\n",	__FILE__, __LINE__,
7388 			    sc->status_block->status_attn_bits);
7389 
7390 			DBRUNMSG(BCE_FATAL,
7391 			    if (unexpected_attention_sim_control == 0)
7392 				bce_breakpoint(sc));
7393 
7394 			bce_init_locked(sc);
7395 			goto bce_intr_exit;
7396 		}
7397 
7398 		/* Check for any completed RX frames. */
7399 		if (hw_rx_cons != sc->hw_rx_cons)
7400 			bce_rx_intr(sc);
7401 
7402 		/* Check for any completed TX frames. */
7403 		if (hw_tx_cons != sc->hw_tx_cons)
7404 			bce_tx_intr(sc);
7405 
7406 		/* Save status block index value for the next interrupt. */
7407 		sc->last_status_idx = sc->status_block->status_idx;
7408 
7409  		/*
7410  		 * Prevent speculative reads from getting
7411  		 * ahead of the status block.
7412 		 */
7413 		bus_space_barrier(sc->bce_btag, sc->bce_bhandle, 0, 0,
7414 		    BUS_SPACE_BARRIER_READ);
7415 
7416  		/*
7417  		 * If there's no work left then exit the
7418  		 * interrupt service routine.
7419 		 */
7420 		hw_rx_cons = bce_get_hw_rx_cons(sc);
7421 		hw_tx_cons = bce_get_hw_tx_cons(sc);
7422 
7423 		if ((hw_rx_cons == sc->hw_rx_cons) &&
7424 		    (hw_tx_cons == sc->hw_tx_cons))
7425 			break;
7426 
7427 	}
7428 
7429 	bus_dmamap_sync(sc->status_tag,	sc->status_map,
7430 	    BUS_DMASYNC_PREREAD);
7431 
7432 	/* Re-enable interrupts. */
7433 	bce_enable_intr(sc, 0);
7434 
7435 	/* Handle any frames that arrived while handling the interrupt. */
7436 	if (ifp->if_drv_flags & IFF_DRV_RUNNING &&
7437 	    !IFQ_DRV_IS_EMPTY(&ifp->if_snd))
7438 		bce_start_locked(ifp);
7439 
7440 bce_intr_exit:
7441 	BCE_UNLOCK(sc);
7442 
7443 	DBEXIT(BCE_VERBOSE_SEND | BCE_VERBOSE_RECV | BCE_VERBOSE_INTR);
7444 }
7445 
7446 
7447 /****************************************************************************/
7448 /* Programs the various packet receive modes (broadcast and multicast).     */
7449 /*                                                                          */
7450 /* Returns:                                                                 */
7451 /*   Nothing.                                                               */
7452 /****************************************************************************/
7453 static void
7454 bce_set_rx_mode(struct bce_softc *sc)
7455 {
7456 	struct ifnet *ifp;
7457 	struct ifmultiaddr *ifma;
7458 	u32 hashes[NUM_MC_HASH_REGISTERS] = { 0, 0, 0, 0, 0, 0, 0, 0 };
7459 	u32 rx_mode, sort_mode;
7460 	int h, i;
7461 
7462 	DBENTER(BCE_VERBOSE_MISC);
7463 
7464 	BCE_LOCK_ASSERT(sc);
7465 
7466 	ifp = sc->bce_ifp;
7467 
7468 	/* Initialize receive mode default settings. */
7469 	rx_mode   = sc->rx_mode & ~(BCE_EMAC_RX_MODE_PROMISCUOUS |
7470 	    BCE_EMAC_RX_MODE_KEEP_VLAN_TAG);
7471 	sort_mode = 1 | BCE_RPM_SORT_USER0_BC_EN;
7472 
7473 	/*
7474 	 * ASF/IPMI/UMP firmware requires that VLAN tag stripping
7475 	 * be enbled.
7476 	 */
7477 	if (!(BCE_IF_CAPABILITIES & IFCAP_VLAN_HWTAGGING) &&
7478 	    (!(sc->bce_flags & BCE_MFW_ENABLE_FLAG)))
7479 		rx_mode |= BCE_EMAC_RX_MODE_KEEP_VLAN_TAG;
7480 
7481 	/*
7482 	 * Check for promiscuous, all multicast, or selected
7483 	 * multicast address filtering.
7484 	 */
7485 	if (ifp->if_flags & IFF_PROMISC) {
7486 		DBPRINT(sc, BCE_INFO_MISC, "Enabling promiscuous mode.\n");
7487 
7488 		/* Enable promiscuous mode. */
7489 		rx_mode |= BCE_EMAC_RX_MODE_PROMISCUOUS;
7490 		sort_mode |= BCE_RPM_SORT_USER0_PROM_EN;
7491 	} else if (ifp->if_flags & IFF_ALLMULTI) {
7492 		DBPRINT(sc, BCE_INFO_MISC, "Enabling all multicast mode.\n");
7493 
7494 		/* Enable all multicast addresses. */
7495 		for (i = 0; i < NUM_MC_HASH_REGISTERS; i++) {
7496 			REG_WR(sc, BCE_EMAC_MULTICAST_HASH0 + (i * 4), 0xffffffff);
7497        	}
7498 		sort_mode |= BCE_RPM_SORT_USER0_MC_EN;
7499 	} else {
7500 		/* Accept one or more multicast(s). */
7501 		DBPRINT(sc, BCE_INFO_MISC, "Enabling selective multicast mode.\n");
7502 
7503 		if_maddr_rlock(ifp);
7504 		TAILQ_FOREACH(ifma, &ifp->if_multiaddrs, ifma_link) {
7505 			if (ifma->ifma_addr->sa_family != AF_LINK)
7506 				continue;
7507 			h = ether_crc32_le(LLADDR((struct sockaddr_dl *)
7508 			    ifma->ifma_addr), ETHER_ADDR_LEN) & 0xFF;
7509 			    hashes[(h & 0xE0) >> 5] |= 1 << (h & 0x1F);
7510 		}
7511 		if_maddr_runlock(ifp);
7512 
7513 		for (i = 0; i < NUM_MC_HASH_REGISTERS; i++)
7514 			REG_WR(sc, BCE_EMAC_MULTICAST_HASH0 + (i * 4), hashes[i]);
7515 
7516 		sort_mode |= BCE_RPM_SORT_USER0_MC_HSH_EN;
7517 	}
7518 
7519 	/* Only make changes if the recive mode has actually changed. */
7520 	if (rx_mode != sc->rx_mode) {
7521 		DBPRINT(sc, BCE_VERBOSE_MISC, "Enabling new receive mode: "
7522 		    "0x%08X\n", rx_mode);
7523 
7524 		sc->rx_mode = rx_mode;
7525 		REG_WR(sc, BCE_EMAC_RX_MODE, rx_mode);
7526 	}
7527 
7528 	/* Disable and clear the exisitng sort before enabling a new sort. */
7529 	REG_WR(sc, BCE_RPM_SORT_USER0, 0x0);
7530 	REG_WR(sc, BCE_RPM_SORT_USER0, sort_mode);
7531 	REG_WR(sc, BCE_RPM_SORT_USER0, sort_mode | BCE_RPM_SORT_USER0_ENA);
7532 
7533 	DBEXIT(BCE_VERBOSE_MISC);
7534 }
7535 
7536 
7537 /****************************************************************************/
7538 /* Called periodically to updates statistics from the controllers           */
7539 /* statistics block.                                                        */
7540 /*                                                                          */
7541 /* Returns:                                                                 */
7542 /*   Nothing.                                                               */
7543 /****************************************************************************/
7544 static void
7545 bce_stats_update(struct bce_softc *sc)
7546 {
7547 	struct ifnet *ifp;
7548 	struct statistics_block *stats;
7549 
7550 	DBENTER(BCE_EXTREME_MISC);
7551 
7552 	ifp = sc->bce_ifp;
7553 
7554 	stats = (struct statistics_block *) sc->stats_block;
7555 
7556 	/*
7557 	 * Certain controllers don't report
7558 	 * carrier sense errors correctly.
7559 	 * See errata E11_5708CA0_1165.
7560 	 */
7561 	if (!(BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5706) &&
7562 	    !(BCE_CHIP_ID(sc) == BCE_CHIP_ID_5708_A0))
7563 		ifp->if_oerrors +=
7564 		    (u_long) stats->stat_Dot3StatsCarrierSenseErrors;
7565 
7566 	/*
7567 	 * Update the sysctl statistics from the
7568 	 * hardware statistics.
7569 	 */
7570 	sc->stat_IfHCInOctets =
7571 	    ((u64) stats->stat_IfHCInOctets_hi << 32) +
7572 	     (u64) stats->stat_IfHCInOctets_lo;
7573 
7574 	sc->stat_IfHCInBadOctets =
7575 	    ((u64) stats->stat_IfHCInBadOctets_hi << 32) +
7576 	     (u64) stats->stat_IfHCInBadOctets_lo;
7577 
7578 	sc->stat_IfHCOutOctets =
7579 	    ((u64) stats->stat_IfHCOutOctets_hi << 32) +
7580 	     (u64) stats->stat_IfHCOutOctets_lo;
7581 
7582 	sc->stat_IfHCOutBadOctets =
7583 	    ((u64) stats->stat_IfHCOutBadOctets_hi << 32) +
7584 	     (u64) stats->stat_IfHCOutBadOctets_lo;
7585 
7586 	sc->stat_IfHCInUcastPkts =
7587 	    ((u64) stats->stat_IfHCInUcastPkts_hi << 32) +
7588 	     (u64) stats->stat_IfHCInUcastPkts_lo;
7589 
7590 	sc->stat_IfHCInMulticastPkts =
7591 	    ((u64) stats->stat_IfHCInMulticastPkts_hi << 32) +
7592 	     (u64) stats->stat_IfHCInMulticastPkts_lo;
7593 
7594 	sc->stat_IfHCInBroadcastPkts =
7595 	    ((u64) stats->stat_IfHCInBroadcastPkts_hi << 32) +
7596 	     (u64) stats->stat_IfHCInBroadcastPkts_lo;
7597 
7598 	sc->stat_IfHCOutUcastPkts =
7599 	    ((u64) stats->stat_IfHCOutUcastPkts_hi << 32) +
7600 	     (u64) stats->stat_IfHCOutUcastPkts_lo;
7601 
7602 	sc->stat_IfHCOutMulticastPkts =
7603 	    ((u64) stats->stat_IfHCOutMulticastPkts_hi << 32) +
7604 	     (u64) stats->stat_IfHCOutMulticastPkts_lo;
7605 
7606 	sc->stat_IfHCOutBroadcastPkts =
7607 	    ((u64) stats->stat_IfHCOutBroadcastPkts_hi << 32) +
7608 	     (u64) stats->stat_IfHCOutBroadcastPkts_lo;
7609 
7610 	/* ToDo: Preserve counters beyond 32 bits? */
7611 	/* ToDo: Read the statistics from auto-clear regs? */
7612 
7613 	sc->stat_emac_tx_stat_dot3statsinternalmactransmiterrors =
7614 	    stats->stat_emac_tx_stat_dot3statsinternalmactransmiterrors;
7615 
7616 	sc->stat_Dot3StatsCarrierSenseErrors =
7617 	    stats->stat_Dot3StatsCarrierSenseErrors;
7618 
7619 	sc->stat_Dot3StatsFCSErrors =
7620 	    stats->stat_Dot3StatsFCSErrors;
7621 
7622 	sc->stat_Dot3StatsAlignmentErrors =
7623 	    stats->stat_Dot3StatsAlignmentErrors;
7624 
7625 	sc->stat_Dot3StatsSingleCollisionFrames =
7626 	    stats->stat_Dot3StatsSingleCollisionFrames;
7627 
7628 	sc->stat_Dot3StatsMultipleCollisionFrames =
7629 	    stats->stat_Dot3StatsMultipleCollisionFrames;
7630 
7631 	sc->stat_Dot3StatsDeferredTransmissions =
7632 	    stats->stat_Dot3StatsDeferredTransmissions;
7633 
7634 	sc->stat_Dot3StatsExcessiveCollisions =
7635 	    stats->stat_Dot3StatsExcessiveCollisions;
7636 
7637 	sc->stat_Dot3StatsLateCollisions =
7638 	    stats->stat_Dot3StatsLateCollisions;
7639 
7640 	sc->stat_EtherStatsCollisions =
7641 	    stats->stat_EtherStatsCollisions;
7642 
7643 	sc->stat_EtherStatsFragments =
7644 	    stats->stat_EtherStatsFragments;
7645 
7646 	sc->stat_EtherStatsJabbers =
7647 	    stats->stat_EtherStatsJabbers;
7648 
7649 	sc->stat_EtherStatsUndersizePkts =
7650 	    stats->stat_EtherStatsUndersizePkts;
7651 
7652 	sc->stat_EtherStatsOversizePkts =
7653 	     stats->stat_EtherStatsOversizePkts;
7654 
7655 	sc->stat_EtherStatsPktsRx64Octets =
7656 	    stats->stat_EtherStatsPktsRx64Octets;
7657 
7658 	sc->stat_EtherStatsPktsRx65Octetsto127Octets =
7659 	    stats->stat_EtherStatsPktsRx65Octetsto127Octets;
7660 
7661 	sc->stat_EtherStatsPktsRx128Octetsto255Octets =
7662 	    stats->stat_EtherStatsPktsRx128Octetsto255Octets;
7663 
7664 	sc->stat_EtherStatsPktsRx256Octetsto511Octets =
7665 	    stats->stat_EtherStatsPktsRx256Octetsto511Octets;
7666 
7667 	sc->stat_EtherStatsPktsRx512Octetsto1023Octets =
7668 	    stats->stat_EtherStatsPktsRx512Octetsto1023Octets;
7669 
7670 	sc->stat_EtherStatsPktsRx1024Octetsto1522Octets =
7671 	    stats->stat_EtherStatsPktsRx1024Octetsto1522Octets;
7672 
7673 	sc->stat_EtherStatsPktsRx1523Octetsto9022Octets =
7674 	    stats->stat_EtherStatsPktsRx1523Octetsto9022Octets;
7675 
7676 	sc->stat_EtherStatsPktsTx64Octets =
7677 	    stats->stat_EtherStatsPktsTx64Octets;
7678 
7679 	sc->stat_EtherStatsPktsTx65Octetsto127Octets =
7680 	    stats->stat_EtherStatsPktsTx65Octetsto127Octets;
7681 
7682 	sc->stat_EtherStatsPktsTx128Octetsto255Octets =
7683 	    stats->stat_EtherStatsPktsTx128Octetsto255Octets;
7684 
7685 	sc->stat_EtherStatsPktsTx256Octetsto511Octets =
7686 	    stats->stat_EtherStatsPktsTx256Octetsto511Octets;
7687 
7688 	sc->stat_EtherStatsPktsTx512Octetsto1023Octets =
7689 	    stats->stat_EtherStatsPktsTx512Octetsto1023Octets;
7690 
7691 	sc->stat_EtherStatsPktsTx1024Octetsto1522Octets =
7692 	    stats->stat_EtherStatsPktsTx1024Octetsto1522Octets;
7693 
7694 	sc->stat_EtherStatsPktsTx1523Octetsto9022Octets =
7695 	    stats->stat_EtherStatsPktsTx1523Octetsto9022Octets;
7696 
7697 	sc->stat_XonPauseFramesReceived =
7698 	    stats->stat_XonPauseFramesReceived;
7699 
7700 	sc->stat_XoffPauseFramesReceived =
7701 	    stats->stat_XoffPauseFramesReceived;
7702 
7703 	sc->stat_OutXonSent =
7704 	    stats->stat_OutXonSent;
7705 
7706 	sc->stat_OutXoffSent =
7707 	    stats->stat_OutXoffSent;
7708 
7709 	sc->stat_FlowControlDone =
7710 	    stats->stat_FlowControlDone;
7711 
7712 	sc->stat_MacControlFramesReceived =
7713 	    stats->stat_MacControlFramesReceived;
7714 
7715 	sc->stat_XoffStateEntered =
7716 	    stats->stat_XoffStateEntered;
7717 
7718 	sc->stat_IfInFramesL2FilterDiscards =
7719 	    stats->stat_IfInFramesL2FilterDiscards;
7720 
7721 	sc->stat_IfInRuleCheckerDiscards =
7722 	    stats->stat_IfInRuleCheckerDiscards;
7723 
7724 	sc->stat_IfInFTQDiscards =
7725 	    stats->stat_IfInFTQDiscards;
7726 
7727 	sc->stat_IfInMBUFDiscards =
7728 	    stats->stat_IfInMBUFDiscards;
7729 
7730 	sc->stat_IfInRuleCheckerP4Hit =
7731 	    stats->stat_IfInRuleCheckerP4Hit;
7732 
7733 	sc->stat_CatchupInRuleCheckerDiscards =
7734 	    stats->stat_CatchupInRuleCheckerDiscards;
7735 
7736 	sc->stat_CatchupInFTQDiscards =
7737 	    stats->stat_CatchupInFTQDiscards;
7738 
7739 	sc->stat_CatchupInMBUFDiscards =
7740 	    stats->stat_CatchupInMBUFDiscards;
7741 
7742 	sc->stat_CatchupInRuleCheckerP4Hit =
7743 	    stats->stat_CatchupInRuleCheckerP4Hit;
7744 
7745 	sc->com_no_buffers = REG_RD_IND(sc, 0x120084);
7746 
7747 	/*
7748 	 * Update the interface statistics from the
7749 	 * hardware statistics.
7750 	 */
7751 	ifp->if_collisions =
7752 	    (u_long) sc->stat_EtherStatsCollisions;
7753 
7754 	/* ToDo: This method loses soft errors. */
7755 	ifp->if_ierrors =
7756 	    (u_long) sc->stat_EtherStatsUndersizePkts +
7757 	    (u_long) sc->stat_EtherStatsOversizePkts +
7758 	    (u_long) sc->stat_IfInMBUFDiscards +
7759 	    (u_long) sc->stat_Dot3StatsAlignmentErrors +
7760 	    (u_long) sc->stat_Dot3StatsFCSErrors +
7761 	    (u_long) sc->stat_IfInRuleCheckerDiscards +
7762 	    (u_long) sc->stat_IfInFTQDiscards +
7763 	    (u_long) sc->com_no_buffers;
7764 
7765 	/* ToDo: This method loses soft errors. */
7766 	ifp->if_oerrors =
7767 	    (u_long) sc->stat_emac_tx_stat_dot3statsinternalmactransmiterrors +
7768 	    (u_long) sc->stat_Dot3StatsExcessiveCollisions +
7769 	    (u_long) sc->stat_Dot3StatsLateCollisions;
7770 
7771 	/* ToDo: Add additional statistics? */
7772 
7773 	DBEXIT(BCE_EXTREME_MISC);
7774 }
7775 
7776 
7777 /****************************************************************************/
7778 /* Periodic function to notify the bootcode that the driver is still        */
7779 /* present.                                                                 */
7780 /*                                                                          */
7781 /* Returns:                                                                 */
7782 /*   Nothing.                                                               */
7783 /****************************************************************************/
7784 static void
7785 bce_pulse(void *xsc)
7786 {
7787 	struct bce_softc *sc = xsc;
7788 	u32 msg;
7789 
7790 	DBENTER(BCE_EXTREME_MISC);
7791 
7792 	BCE_LOCK_ASSERT(sc);
7793 
7794 	/* Tell the firmware that the driver is still running. */
7795 	msg = (u32) ++sc->bce_fw_drv_pulse_wr_seq;
7796 	bce_shmem_wr(sc, BCE_DRV_PULSE_MB, msg);
7797 
7798 	/* Update the bootcode condition. */
7799 	sc->bc_state = bce_shmem_rd(sc, BCE_BC_STATE_CONDITION);
7800 
7801 	/* Report whether the bootcode still knows the driver is running. */
7802 	if (sc->bce_drv_cardiac_arrest == FALSE) {
7803 		if (!(sc->bc_state & BCE_CONDITION_DRV_PRESENT)) {
7804 			sc->bce_drv_cardiac_arrest = TRUE;
7805 			BCE_PRINTF("%s(): Bootcode lost the driver pulse! "
7806 			    "(bc_state = 0x%08X)\n", __FUNCTION__,
7807 			    sc->bc_state);
7808 		}
7809 	} else {
7810  		/*
7811  		 * Not supported by all bootcode versions.
7812  		 * (v5.0.11+ and v5.2.1+)  Older bootcode
7813  		 * will require the driver to reset the
7814  		 * controller to clear this condition.
7815 		 */
7816 		if (sc->bc_state & BCE_CONDITION_DRV_PRESENT) {
7817 			sc->bce_drv_cardiac_arrest = FALSE;
7818 			BCE_PRINTF("%s(): Bootcode found the driver pulse! "
7819 			    "(bc_state = 0x%08X)\n", __FUNCTION__,
7820 			    sc->bc_state);
7821 		}
7822 	}
7823 
7824 
7825 	/* Schedule the next pulse. */
7826 	callout_reset(&sc->bce_pulse_callout, hz, bce_pulse, sc);
7827 
7828 	DBEXIT(BCE_EXTREME_MISC);
7829 }
7830 
7831 
7832 /****************************************************************************/
7833 /* Periodic function to perform maintenance tasks.                          */
7834 /*                                                                          */
7835 /* Returns:                                                                 */
7836 /*   Nothing.                                                               */
7837 /****************************************************************************/
7838 static void
7839 bce_tick(void *xsc)
7840 {
7841 	struct bce_softc *sc = xsc;
7842 	struct mii_data *mii;
7843 	struct ifnet *ifp;
7844 
7845 	ifp = sc->bce_ifp;
7846 
7847 	DBENTER(BCE_EXTREME_MISC);
7848 
7849 	BCE_LOCK_ASSERT(sc);
7850 
7851 	/* Schedule the next tick. */
7852 	callout_reset(&sc->bce_tick_callout, hz, bce_tick, sc);
7853 
7854 	/* Update the statistics from the hardware statistics block. */
7855 	bce_stats_update(sc);
7856 
7857 	/* Top off the receive and page chains. */
7858 #ifdef BCE_JUMBO_HDRSPLIT
7859 	bce_fill_pg_chain(sc);
7860 #endif
7861 	bce_fill_rx_chain(sc);
7862 
7863 	/* Check that chip hasn't hung. */
7864 	bce_watchdog(sc);
7865 
7866 	/* If link is up already up then we're done. */
7867 	if (sc->bce_link_up == TRUE)
7868 		goto bce_tick_exit;
7869 
7870 	/* Link is down.  Check what the PHY's doing. */
7871 	mii = device_get_softc(sc->bce_miibus);
7872 	mii_tick(mii);
7873 
7874 	/* Check if the link has come up. */
7875 	if ((mii->mii_media_status & IFM_ACTIVE) &&
7876 	    (IFM_SUBTYPE(mii->mii_media_active) != IFM_NONE)) {
7877 		DBPRINT(sc, BCE_VERBOSE_MISC,
7878 		    "%s(): Link up!\n", __FUNCTION__);
7879 		sc->bce_link_up = TRUE;
7880 		if ((IFM_SUBTYPE(mii->mii_media_active) == IFM_1000_T ||
7881 		    IFM_SUBTYPE(mii->mii_media_active) == IFM_1000_SX ||
7882 		    IFM_SUBTYPE(mii->mii_media_active) == IFM_2500_SX) &&
7883 		    bootverbose)
7884 			BCE_PRINTF("Gigabit link up!\n");
7885 
7886 		/* Now that link is up, handle any outstanding TX traffic. */
7887 		if (!IFQ_DRV_IS_EMPTY(&ifp->if_snd)) {
7888 			DBPRINT(sc, BCE_VERBOSE_MISC, "%s(): Found "
7889 			    "pending TX traffic.\n", __FUNCTION__);
7890 			bce_start_locked(ifp);
7891 		}
7892 	}
7893 
7894 bce_tick_exit:
7895 	DBEXIT(BCE_EXTREME_MISC);
7896 	return;
7897 }
7898 
7899 
7900 #ifdef BCE_DEBUG
7901 /****************************************************************************/
7902 /* Allows the driver state to be dumped through the sysctl interface.       */
7903 /*                                                                          */
7904 /* Returns:                                                                 */
7905 /*   0 for success, positive value for failure.                             */
7906 /****************************************************************************/
7907 static int
7908 bce_sysctl_driver_state(SYSCTL_HANDLER_ARGS)
7909 {
7910 	int error;
7911 	int result;
7912 	struct bce_softc *sc;
7913 
7914 	result = -1;
7915 	error = sysctl_handle_int(oidp, &result, 0, req);
7916 
7917 	if (error || !req->newptr)
7918 		return (error);
7919 
7920 	if (result == 1) {
7921 		sc = (struct bce_softc *)arg1;
7922 		bce_dump_driver_state(sc);
7923 	}
7924 
7925 	return error;
7926 }
7927 
7928 
7929 /****************************************************************************/
7930 /* Allows the hardware state to be dumped through the sysctl interface.     */
7931 /*                                                                          */
7932 /* Returns:                                                                 */
7933 /*   0 for success, positive value for failure.                             */
7934 /****************************************************************************/
7935 static int
7936 bce_sysctl_hw_state(SYSCTL_HANDLER_ARGS)
7937 {
7938 	int error;
7939 	int result;
7940 	struct bce_softc *sc;
7941 
7942 	result = -1;
7943 	error = sysctl_handle_int(oidp, &result, 0, req);
7944 
7945 	if (error || !req->newptr)
7946 		return (error);
7947 
7948 	if (result == 1) {
7949 		sc = (struct bce_softc *)arg1;
7950 		bce_dump_hw_state(sc);
7951 	}
7952 
7953 	return error;
7954 }
7955 
7956 
7957 /****************************************************************************/
7958 /* Allows the status block to be dumped through the sysctl interface.       */
7959 /*                                                                          */
7960 /* Returns:                                                                 */
7961 /*   0 for success, positive value for failure.                             */
7962 /****************************************************************************/
7963 static int
7964 bce_sysctl_status_block(SYSCTL_HANDLER_ARGS)
7965 {
7966 	int error;
7967 	int result;
7968 	struct bce_softc *sc;
7969 
7970 	result = -1;
7971 	error = sysctl_handle_int(oidp, &result, 0, req);
7972 
7973 	if (error || !req->newptr)
7974 		return (error);
7975 
7976 	if (result == 1) {
7977 		sc = (struct bce_softc *)arg1;
7978 		bce_dump_status_block(sc);
7979 	}
7980 
7981 	return error;
7982 }
7983 
7984 
7985 /****************************************************************************/
7986 /* Allows the stats block to be dumped through the sysctl interface.        */
7987 /*                                                                          */
7988 /* Returns:                                                                 */
7989 /*   0 for success, positive value for failure.                             */
7990 /****************************************************************************/
7991 static int
7992 bce_sysctl_stats_block(SYSCTL_HANDLER_ARGS)
7993 {
7994 	int error;
7995 	int result;
7996 	struct bce_softc *sc;
7997 
7998 	result = -1;
7999 	error = sysctl_handle_int(oidp, &result, 0, req);
8000 
8001 	if (error || !req->newptr)
8002 		return (error);
8003 
8004 	if (result == 1) {
8005 		sc = (struct bce_softc *)arg1;
8006 		bce_dump_stats_block(sc);
8007 	}
8008 
8009 	return error;
8010 }
8011 
8012 
8013 /****************************************************************************/
8014 /* Allows the bootcode state to be dumped through the sysctl interface.     */
8015 /*                                                                          */
8016 /* Returns:                                                                 */
8017 /*   0 for success, positive value for failure.                             */
8018 /****************************************************************************/
8019 static int
8020 bce_sysctl_bc_state(SYSCTL_HANDLER_ARGS)
8021 {
8022 	int error;
8023 	int result;
8024 	struct bce_softc *sc;
8025 
8026 	result = -1;
8027 	error = sysctl_handle_int(oidp, &result, 0, req);
8028 
8029 	if (error || !req->newptr)
8030 		return (error);
8031 
8032 	if (result == 1) {
8033 		sc = (struct bce_softc *)arg1;
8034 		bce_dump_bc_state(sc);
8035 	}
8036 
8037 	return error;
8038 }
8039 
8040 
8041 /****************************************************************************/
8042 /* Provides a sysctl interface to allow dumping the RX BD chain.            */
8043 /*                                                                          */
8044 /* Returns:                                                                 */
8045 /*   0 for success, positive value for failure.                             */
8046 /****************************************************************************/
8047 static int
8048 bce_sysctl_dump_rx_bd_chain(SYSCTL_HANDLER_ARGS)
8049 {
8050 	int error;
8051 	int result;
8052 	struct bce_softc *sc;
8053 
8054 	result = -1;
8055 	error = sysctl_handle_int(oidp, &result, 0, req);
8056 
8057 	if (error || !req->newptr)
8058 		return (error);
8059 
8060 	if (result == 1) {
8061 		sc = (struct bce_softc *)arg1;
8062 		bce_dump_rx_bd_chain(sc, 0, TOTAL_RX_BD);
8063 	}
8064 
8065 	return error;
8066 }
8067 
8068 
8069 /****************************************************************************/
8070 /* Provides a sysctl interface to allow dumping the RX MBUF chain.          */
8071 /*                                                                          */
8072 /* Returns:                                                                 */
8073 /*   0 for success, positive value for failure.                             */
8074 /****************************************************************************/
8075 static int
8076 bce_sysctl_dump_rx_mbuf_chain(SYSCTL_HANDLER_ARGS)
8077 {
8078 	int error;
8079 	int result;
8080 	struct bce_softc *sc;
8081 
8082 	result = -1;
8083 	error = sysctl_handle_int(oidp, &result, 0, req);
8084 
8085 	if (error || !req->newptr)
8086 		return (error);
8087 
8088 	if (result == 1) {
8089 		sc = (struct bce_softc *)arg1;
8090 		bce_dump_rx_mbuf_chain(sc, 0, USABLE_RX_BD);
8091 	}
8092 
8093 	return error;
8094 }
8095 
8096 
8097 /****************************************************************************/
8098 /* Provides a sysctl interface to allow dumping the TX chain.               */
8099 /*                                                                          */
8100 /* Returns:                                                                 */
8101 /*   0 for success, positive value for failure.                             */
8102 /****************************************************************************/
8103 static int
8104 bce_sysctl_dump_tx_chain(SYSCTL_HANDLER_ARGS)
8105 {
8106 	int error;
8107 	int result;
8108 	struct bce_softc *sc;
8109 
8110 	result = -1;
8111 	error = sysctl_handle_int(oidp, &result, 0, req);
8112 
8113 	if (error || !req->newptr)
8114 		return (error);
8115 
8116 	if (result == 1) {
8117 		sc = (struct bce_softc *)arg1;
8118 		bce_dump_tx_chain(sc, 0, TOTAL_TX_BD);
8119 	}
8120 
8121 	return error;
8122 }
8123 
8124 
8125 #ifdef BCE_JUMBO_HDRSPLIT
8126 /****************************************************************************/
8127 /* Provides a sysctl interface to allow dumping the page chain.             */
8128 /*                                                                          */
8129 /* Returns:                                                                 */
8130 /*   0 for success, positive value for failure.                             */
8131 /****************************************************************************/
8132 static int
8133 bce_sysctl_dump_pg_chain(SYSCTL_HANDLER_ARGS)
8134 {
8135 	int error;
8136 	int result;
8137 	struct bce_softc *sc;
8138 
8139 	result = -1;
8140 	error = sysctl_handle_int(oidp, &result, 0, req);
8141 
8142 	if (error || !req->newptr)
8143 		return (error);
8144 
8145 	if (result == 1) {
8146 		sc = (struct bce_softc *)arg1;
8147 		bce_dump_pg_chain(sc, 0, TOTAL_PG_BD);
8148 	}
8149 
8150 	return error;
8151 }
8152 #endif
8153 
8154 /****************************************************************************/
8155 /* Provides a sysctl interface to allow reading arbitrary NVRAM offsets in  */
8156 /* the device.  DO NOT ENABLE ON PRODUCTION SYSTEMS!                        */
8157 /*                                                                          */
8158 /* Returns:                                                                 */
8159 /*   0 for success, positive value for failure.                             */
8160 /****************************************************************************/
8161 static int
8162 bce_sysctl_nvram_read(SYSCTL_HANDLER_ARGS)
8163 {
8164 	struct bce_softc *sc = (struct bce_softc *)arg1;
8165 	int error;
8166 	u32 result;
8167 	u32 val[1];
8168 	u8 *data = (u8 *) val;
8169 
8170 	result = -1;
8171 	error = sysctl_handle_int(oidp, &result, 0, req);
8172 	if (error || (req->newptr == NULL))
8173 		return (error);
8174 
8175 	bce_nvram_read(sc, result, data, 4);
8176 	BCE_PRINTF("offset 0x%08X = 0x%08X\n", result, bce_be32toh(val[0]));
8177 
8178 	return (error);
8179 }
8180 
8181 
8182 /****************************************************************************/
8183 /* Provides a sysctl interface to allow reading arbitrary registers in the  */
8184 /* device.  DO NOT ENABLE ON PRODUCTION SYSTEMS!                            */
8185 /*                                                                          */
8186 /* Returns:                                                                 */
8187 /*   0 for success, positive value for failure.                             */
8188 /****************************************************************************/
8189 static int
8190 bce_sysctl_reg_read(SYSCTL_HANDLER_ARGS)
8191 {
8192 	struct bce_softc *sc = (struct bce_softc *)arg1;
8193 	int error;
8194 	u32 val, result;
8195 
8196 	result = -1;
8197 	error = sysctl_handle_int(oidp, &result, 0, req);
8198 	if (error || (req->newptr == NULL))
8199 		return (error);
8200 
8201 	/* Make sure the register is accessible. */
8202 	if (result < 0x8000) {
8203 		val = REG_RD(sc, result);
8204 		BCE_PRINTF("reg 0x%08X = 0x%08X\n", result, val);
8205 	} else if (result < 0x0280000) {
8206 		val = REG_RD_IND(sc, result);
8207 		BCE_PRINTF("reg 0x%08X = 0x%08X\n", result, val);
8208 	}
8209 
8210 	return (error);
8211 }
8212 
8213 
8214 /****************************************************************************/
8215 /* Provides a sysctl interface to allow reading arbitrary PHY registers in  */
8216 /* the device.  DO NOT ENABLE ON PRODUCTION SYSTEMS!                        */
8217 /*                                                                          */
8218 /* Returns:                                                                 */
8219 /*   0 for success, positive value for failure.                             */
8220 /****************************************************************************/
8221 static int
8222 bce_sysctl_phy_read(SYSCTL_HANDLER_ARGS)
8223 {
8224 	struct bce_softc *sc;
8225 	device_t dev;
8226 	int error, result;
8227 	u16 val;
8228 
8229 	result = -1;
8230 	error = sysctl_handle_int(oidp, &result, 0, req);
8231 	if (error || (req->newptr == NULL))
8232 		return (error);
8233 
8234 	/* Make sure the register is accessible. */
8235 	if (result < 0x20) {
8236 		sc = (struct bce_softc *)arg1;
8237 		dev = sc->bce_dev;
8238 		val = bce_miibus_read_reg(dev, sc->bce_phy_addr, result);
8239 		BCE_PRINTF("phy 0x%02X = 0x%04X\n", result, val);
8240 	}
8241 	return (error);
8242 }
8243 
8244 
8245 /****************************************************************************/
8246 /* Provides a sysctl interface to allow reading a CID.                      */
8247 /*                                                                          */
8248 /* Returns:                                                                 */
8249 /*   0 for success, positive value for failure.                             */
8250 /****************************************************************************/
8251 static int
8252 bce_sysctl_dump_ctx(SYSCTL_HANDLER_ARGS)
8253 {
8254 	struct bce_softc *sc;
8255 	int error;
8256 	u16 result;
8257 
8258 	result = -1;
8259 	error = sysctl_handle_int(oidp, &result, 0, req);
8260 	if (error || (req->newptr == NULL))
8261 		return (error);
8262 
8263 	/* Make sure the register is accessible. */
8264 	if (result <= TX_CID) {
8265 		sc = (struct bce_softc *)arg1;
8266 		bce_dump_ctx(sc, result);
8267 	}
8268 
8269 	return (error);
8270 }
8271 
8272 
8273  /****************************************************************************/
8274 /* Provides a sysctl interface to forcing the driver to dump state and      */
8275 /* enter the debugger.  DO NOT ENABLE ON PRODUCTION SYSTEMS!                */
8276 /*                                                                          */
8277 /* Returns:                                                                 */
8278 /*   0 for success, positive value for failure.                             */
8279 /****************************************************************************/
8280 static int
8281 bce_sysctl_breakpoint(SYSCTL_HANDLER_ARGS)
8282 {
8283 	int error;
8284 	int result;
8285 	struct bce_softc *sc;
8286 
8287 	result = -1;
8288 	error = sysctl_handle_int(oidp, &result, 0, req);
8289 
8290 	if (error || !req->newptr)
8291 		return (error);
8292 
8293 	if (result == 1) {
8294 		sc = (struct bce_softc *)arg1;
8295 		bce_breakpoint(sc);
8296 	}
8297 
8298 	return error;
8299 }
8300 #endif
8301 
8302 
8303 /****************************************************************************/
8304 /* Adds any sysctl parameters for tuning or debugging purposes.             */
8305 /*                                                                          */
8306 /* Returns:                                                                 */
8307 /*   0 for success, positive value for failure.                             */
8308 /****************************************************************************/
8309 static void
8310 bce_add_sysctls(struct bce_softc *sc)
8311 {
8312 	struct sysctl_ctx_list *ctx;
8313 	struct sysctl_oid_list *children;
8314 
8315 	DBENTER(BCE_VERBOSE_MISC);
8316 
8317 	ctx = device_get_sysctl_ctx(sc->bce_dev);
8318 	children = SYSCTL_CHILDREN(device_get_sysctl_tree(sc->bce_dev));
8319 
8320 #ifdef BCE_DEBUG
8321 	SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8322 	    "l2fhdr_error_sim_control",
8323 	    CTLFLAG_RW, &l2fhdr_error_sim_control,
8324 	    0, "Debug control to force l2fhdr errors");
8325 
8326 	SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8327 	    "l2fhdr_error_sim_count",
8328 	    CTLFLAG_RD, &sc->l2fhdr_error_sim_count,
8329 	    0, "Number of simulated l2_fhdr errors");
8330 #endif
8331 
8332 	SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8333 	    "l2fhdr_error_count",
8334 	    CTLFLAG_RD, &sc->l2fhdr_error_count,
8335 	    0, "Number of l2_fhdr errors");
8336 
8337 #ifdef BCE_DEBUG
8338 	SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8339 	    "mbuf_alloc_failed_sim_control",
8340 	    CTLFLAG_RW, &mbuf_alloc_failed_sim_control,
8341 	    0, "Debug control to force mbuf allocation failures");
8342 
8343 	SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8344 	    "mbuf_alloc_failed_sim_count",
8345 	    CTLFLAG_RD, &sc->mbuf_alloc_failed_sim_count,
8346 	    0, "Number of simulated mbuf cluster allocation failures");
8347 #endif
8348 
8349 	SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8350 	    "mbuf_alloc_failed_count",
8351 	    CTLFLAG_RD, &sc->mbuf_alloc_failed_count,
8352 	    0, "Number of mbuf allocation failures");
8353 
8354 	SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8355 	    "fragmented_mbuf_count",
8356 	    CTLFLAG_RD, &sc->fragmented_mbuf_count,
8357 	    0, "Number of fragmented mbufs");
8358 
8359 #ifdef BCE_DEBUG
8360 	SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8361 	    "dma_map_addr_failed_sim_control",
8362 	    CTLFLAG_RW, &dma_map_addr_failed_sim_control,
8363 	    0, "Debug control to force DMA mapping failures");
8364 
8365 	/* ToDo: Figure out how to update this value in bce_dma_map_addr(). */
8366 	SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8367 	    "dma_map_addr_failed_sim_count",
8368 	    CTLFLAG_RD, &sc->dma_map_addr_failed_sim_count,
8369 	    0, "Number of simulated DMA mapping failures");
8370 
8371 #endif
8372 
8373 	SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8374 	    "dma_map_addr_rx_failed_count",
8375 	    CTLFLAG_RD, &sc->dma_map_addr_rx_failed_count,
8376 	    0, "Number of RX DMA mapping failures");
8377 
8378 	SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8379 	    "dma_map_addr_tx_failed_count",
8380 	    CTLFLAG_RD, &sc->dma_map_addr_tx_failed_count,
8381 	    0, "Number of TX DMA mapping failures");
8382 
8383 #ifdef BCE_DEBUG
8384 	SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8385 	    "unexpected_attention_sim_control",
8386 	    CTLFLAG_RW, &unexpected_attention_sim_control,
8387 	    0, "Debug control to simulate unexpected attentions");
8388 
8389 	SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8390 	    "unexpected_attention_sim_count",
8391 	    CTLFLAG_RW, &sc->unexpected_attention_sim_count,
8392 	    0, "Number of simulated unexpected attentions");
8393 #endif
8394 
8395 	SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8396 	    "unexpected_attention_count",
8397 	    CTLFLAG_RW, &sc->unexpected_attention_count,
8398 	    0, "Number of unexpected attentions");
8399 
8400 #ifdef BCE_DEBUG
8401 	SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8402 	    "debug_bootcode_running_failure",
8403 	    CTLFLAG_RW, &bootcode_running_failure_sim_control,
8404 	    0, "Debug control to force bootcode running failures");
8405 
8406 	SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8407 	    "rx_low_watermark",
8408 	    CTLFLAG_RD, &sc->rx_low_watermark,
8409 	    0, "Lowest level of free rx_bd's");
8410 
8411 	SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8412 	    "rx_empty_count",
8413 	    CTLFLAG_RD, &sc->rx_empty_count,
8414 	    0, "Number of times the RX chain was empty");
8415 
8416 	SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8417 	    "tx_hi_watermark",
8418 	    CTLFLAG_RD, &sc->tx_hi_watermark,
8419 	    0, "Highest level of used tx_bd's");
8420 
8421 	SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8422 	    "tx_full_count",
8423 	    CTLFLAG_RD, &sc->tx_full_count,
8424 	    0, "Number of times the TX chain was full");
8425 
8426 	SYSCTL_ADD_INT(ctx, children, OID_AUTO,
8427 	    "requested_tso_frames",
8428 	    CTLFLAG_RD, &sc->requested_tso_frames,
8429 	    0, "Number of TSO frames received");
8430 
8431 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8432 	    "rx_interrupts",
8433 	    CTLFLAG_RD, &sc->rx_interrupts,
8434 	    0, "Number of RX interrupts");
8435 
8436 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8437 	    "tx_interrupts",
8438 	    CTLFLAG_RD, &sc->tx_interrupts,
8439 	    0, "Number of TX interrupts");
8440 #endif
8441 
8442 	SYSCTL_ADD_ULONG(ctx, children, OID_AUTO,
8443 	    "stat_IfHcInOctets",
8444 	    CTLFLAG_RD, &sc->stat_IfHCInOctets,
8445 	    "Bytes received");
8446 
8447 	SYSCTL_ADD_ULONG(ctx, children, OID_AUTO,
8448 	    "stat_IfHCInBadOctets",
8449 	    CTLFLAG_RD, &sc->stat_IfHCInBadOctets,
8450 	    "Bad bytes received");
8451 
8452 	SYSCTL_ADD_ULONG(ctx, children, OID_AUTO,
8453 	    "stat_IfHCOutOctets",
8454 	    CTLFLAG_RD, &sc->stat_IfHCOutOctets,
8455 	    "Bytes sent");
8456 
8457 	SYSCTL_ADD_ULONG(ctx, children, OID_AUTO,
8458 	    "stat_IfHCOutBadOctets",
8459 	    CTLFLAG_RD, &sc->stat_IfHCOutBadOctets,
8460 	    "Bad bytes sent");
8461 
8462 	SYSCTL_ADD_ULONG(ctx, children, OID_AUTO,
8463 	    "stat_IfHCInUcastPkts",
8464 	    CTLFLAG_RD, &sc->stat_IfHCInUcastPkts,
8465 	    "Unicast packets received");
8466 
8467 	SYSCTL_ADD_ULONG(ctx, children, OID_AUTO,
8468 	    "stat_IfHCInMulticastPkts",
8469 	    CTLFLAG_RD, &sc->stat_IfHCInMulticastPkts,
8470 	    "Multicast packets received");
8471 
8472 	SYSCTL_ADD_ULONG(ctx, children, OID_AUTO,
8473 	    "stat_IfHCInBroadcastPkts",
8474 	    CTLFLAG_RD, &sc->stat_IfHCInBroadcastPkts,
8475 	    "Broadcast packets received");
8476 
8477 	SYSCTL_ADD_ULONG(ctx, children, OID_AUTO,
8478 	    "stat_IfHCOutUcastPkts",
8479 	    CTLFLAG_RD, &sc->stat_IfHCOutUcastPkts,
8480 	    "Unicast packets sent");
8481 
8482 	SYSCTL_ADD_ULONG(ctx, children, OID_AUTO,
8483 	    "stat_IfHCOutMulticastPkts",
8484 	    CTLFLAG_RD, &sc->stat_IfHCOutMulticastPkts,
8485 	    "Multicast packets sent");
8486 
8487 	SYSCTL_ADD_ULONG(ctx, children, OID_AUTO,
8488 	    "stat_IfHCOutBroadcastPkts",
8489 	    CTLFLAG_RD, &sc->stat_IfHCOutBroadcastPkts,
8490 	    "Broadcast packets sent");
8491 
8492 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8493 	    "stat_emac_tx_stat_dot3statsinternalmactransmiterrors",
8494 	    CTLFLAG_RD, &sc->stat_emac_tx_stat_dot3statsinternalmactransmiterrors,
8495 	    0, "Internal MAC transmit errors");
8496 
8497 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8498 	    "stat_Dot3StatsCarrierSenseErrors",
8499 	    CTLFLAG_RD, &sc->stat_Dot3StatsCarrierSenseErrors,
8500 	    0, "Carrier sense errors");
8501 
8502 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8503 	    "stat_Dot3StatsFCSErrors",
8504 	    CTLFLAG_RD, &sc->stat_Dot3StatsFCSErrors,
8505 	    0, "Frame check sequence errors");
8506 
8507 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8508 	    "stat_Dot3StatsAlignmentErrors",
8509 	    CTLFLAG_RD, &sc->stat_Dot3StatsAlignmentErrors,
8510 	    0, "Alignment errors");
8511 
8512 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8513 	    "stat_Dot3StatsSingleCollisionFrames",
8514 	    CTLFLAG_RD, &sc->stat_Dot3StatsSingleCollisionFrames,
8515 	    0, "Single Collision Frames");
8516 
8517 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8518 	    "stat_Dot3StatsMultipleCollisionFrames",
8519 	    CTLFLAG_RD, &sc->stat_Dot3StatsMultipleCollisionFrames,
8520 	    0, "Multiple Collision Frames");
8521 
8522 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8523 	    "stat_Dot3StatsDeferredTransmissions",
8524 	    CTLFLAG_RD, &sc->stat_Dot3StatsDeferredTransmissions,
8525 	    0, "Deferred Transmissions");
8526 
8527 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8528 	    "stat_Dot3StatsExcessiveCollisions",
8529 	    CTLFLAG_RD, &sc->stat_Dot3StatsExcessiveCollisions,
8530 	    0, "Excessive Collisions");
8531 
8532 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8533 	    "stat_Dot3StatsLateCollisions",
8534 	    CTLFLAG_RD, &sc->stat_Dot3StatsLateCollisions,
8535 	    0, "Late Collisions");
8536 
8537 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8538 	    "stat_EtherStatsCollisions",
8539 	    CTLFLAG_RD, &sc->stat_EtherStatsCollisions,
8540 	    0, "Collisions");
8541 
8542 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8543 	    "stat_EtherStatsFragments",
8544 	    CTLFLAG_RD, &sc->stat_EtherStatsFragments,
8545 	    0, "Fragments");
8546 
8547 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8548 	    "stat_EtherStatsJabbers",
8549 	    CTLFLAG_RD, &sc->stat_EtherStatsJabbers,
8550 	    0, "Jabbers");
8551 
8552 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8553 	    "stat_EtherStatsUndersizePkts",
8554 	    CTLFLAG_RD, &sc->stat_EtherStatsUndersizePkts,
8555 	    0, "Undersize packets");
8556 
8557 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8558 	    "stat_EtherStatsOversizePkts",
8559 	    CTLFLAG_RD, &sc->stat_EtherStatsOversizePkts,
8560 	    0, "stat_EtherStatsOversizePkts");
8561 
8562 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8563 	    "stat_EtherStatsPktsRx64Octets",
8564 	    CTLFLAG_RD, &sc->stat_EtherStatsPktsRx64Octets,
8565 	    0, "Bytes received in 64 byte packets");
8566 
8567 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8568 	    "stat_EtherStatsPktsRx65Octetsto127Octets",
8569 	    CTLFLAG_RD, &sc->stat_EtherStatsPktsRx65Octetsto127Octets,
8570 	    0, "Bytes received in 65 to 127 byte packets");
8571 
8572 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8573 	    "stat_EtherStatsPktsRx128Octetsto255Octets",
8574 	    CTLFLAG_RD, &sc->stat_EtherStatsPktsRx128Octetsto255Octets,
8575 	    0, "Bytes received in 128 to 255 byte packets");
8576 
8577 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8578 	    "stat_EtherStatsPktsRx256Octetsto511Octets",
8579 	    CTLFLAG_RD, &sc->stat_EtherStatsPktsRx256Octetsto511Octets,
8580 	    0, "Bytes received in 256 to 511 byte packets");
8581 
8582 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8583 	    "stat_EtherStatsPktsRx512Octetsto1023Octets",
8584 	    CTLFLAG_RD, &sc->stat_EtherStatsPktsRx512Octetsto1023Octets,
8585 	    0, "Bytes received in 512 to 1023 byte packets");
8586 
8587 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8588 	    "stat_EtherStatsPktsRx1024Octetsto1522Octets",
8589 	    CTLFLAG_RD, &sc->stat_EtherStatsPktsRx1024Octetsto1522Octets,
8590 	    0, "Bytes received in 1024 t0 1522 byte packets");
8591 
8592 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8593 	    "stat_EtherStatsPktsRx1523Octetsto9022Octets",
8594 	    CTLFLAG_RD, &sc->stat_EtherStatsPktsRx1523Octetsto9022Octets,
8595 	    0, "Bytes received in 1523 to 9022 byte packets");
8596 
8597 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8598 	    "stat_EtherStatsPktsTx64Octets",
8599 	    CTLFLAG_RD, &sc->stat_EtherStatsPktsTx64Octets,
8600 	    0, "Bytes sent in 64 byte packets");
8601 
8602 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8603 	    "stat_EtherStatsPktsTx65Octetsto127Octets",
8604 	    CTLFLAG_RD, &sc->stat_EtherStatsPktsTx65Octetsto127Octets,
8605 	    0, "Bytes sent in 65 to 127 byte packets");
8606 
8607 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8608 	    "stat_EtherStatsPktsTx128Octetsto255Octets",
8609 	    CTLFLAG_RD, &sc->stat_EtherStatsPktsTx128Octetsto255Octets,
8610 	    0, "Bytes sent in 128 to 255 byte packets");
8611 
8612 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8613 	    "stat_EtherStatsPktsTx256Octetsto511Octets",
8614 	    CTLFLAG_RD, &sc->stat_EtherStatsPktsTx256Octetsto511Octets,
8615 	    0, "Bytes sent in 256 to 511 byte packets");
8616 
8617 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8618 	    "stat_EtherStatsPktsTx512Octetsto1023Octets",
8619 	    CTLFLAG_RD, &sc->stat_EtherStatsPktsTx512Octetsto1023Octets,
8620 	    0, "Bytes sent in 512 to 1023 byte packets");
8621 
8622 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8623 	    "stat_EtherStatsPktsTx1024Octetsto1522Octets",
8624 	    CTLFLAG_RD, &sc->stat_EtherStatsPktsTx1024Octetsto1522Octets,
8625 	    0, "Bytes sent in 1024 to 1522 byte packets");
8626 
8627 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8628 	    "stat_EtherStatsPktsTx1523Octetsto9022Octets",
8629 	    CTLFLAG_RD, &sc->stat_EtherStatsPktsTx1523Octetsto9022Octets,
8630 	    0, "Bytes sent in 1523 to 9022 byte packets");
8631 
8632 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8633 	    "stat_XonPauseFramesReceived",
8634 	    CTLFLAG_RD, &sc->stat_XonPauseFramesReceived,
8635 	    0, "XON pause frames receved");
8636 
8637 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8638 	    "stat_XoffPauseFramesReceived",
8639 	    CTLFLAG_RD, &sc->stat_XoffPauseFramesReceived,
8640 	    0, "XOFF pause frames received");
8641 
8642 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8643 	    "stat_OutXonSent",
8644 	    CTLFLAG_RD, &sc->stat_OutXonSent,
8645 	    0, "XON pause frames sent");
8646 
8647 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8648 	    "stat_OutXoffSent",
8649 	    CTLFLAG_RD, &sc->stat_OutXoffSent,
8650 	    0, "XOFF pause frames sent");
8651 
8652 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8653 	    "stat_FlowControlDone",
8654 	    CTLFLAG_RD, &sc->stat_FlowControlDone,
8655 	    0, "Flow control done");
8656 
8657 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8658 	    "stat_MacControlFramesReceived",
8659 	    CTLFLAG_RD, &sc->stat_MacControlFramesReceived,
8660 	    0, "MAC control frames received");
8661 
8662 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8663 	    "stat_XoffStateEntered",
8664 	    CTLFLAG_RD, &sc->stat_XoffStateEntered,
8665 	    0, "XOFF state entered");
8666 
8667 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8668 	    "stat_IfInFramesL2FilterDiscards",
8669 	    CTLFLAG_RD, &sc->stat_IfInFramesL2FilterDiscards,
8670 	    0, "Received L2 packets discarded");
8671 
8672 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8673 	    "stat_IfInRuleCheckerDiscards",
8674 	    CTLFLAG_RD, &sc->stat_IfInRuleCheckerDiscards,
8675 	    0, "Received packets discarded by rule");
8676 
8677 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8678 	    "stat_IfInFTQDiscards",
8679 	    CTLFLAG_RD, &sc->stat_IfInFTQDiscards,
8680 	    0, "Received packet FTQ discards");
8681 
8682 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8683 	    "stat_IfInMBUFDiscards",
8684 	    CTLFLAG_RD, &sc->stat_IfInMBUFDiscards,
8685 	    0, "Received packets discarded due to lack "
8686 	    "of controller buffer memory");
8687 
8688 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8689 	    "stat_IfInRuleCheckerP4Hit",
8690 	    CTLFLAG_RD, &sc->stat_IfInRuleCheckerP4Hit,
8691 	    0, "Received packets rule checker hits");
8692 
8693 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8694 	    "stat_CatchupInRuleCheckerDiscards",
8695 	    CTLFLAG_RD, &sc->stat_CatchupInRuleCheckerDiscards,
8696 	    0, "Received packets discarded in Catchup path");
8697 
8698 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8699 	    "stat_CatchupInFTQDiscards",
8700 	    CTLFLAG_RD, &sc->stat_CatchupInFTQDiscards,
8701 	    0, "Received packets discarded in FTQ in Catchup path");
8702 
8703 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8704 	    "stat_CatchupInMBUFDiscards",
8705 	    CTLFLAG_RD, &sc->stat_CatchupInMBUFDiscards,
8706 	    0, "Received packets discarded in controller "
8707 	    "buffer memory in Catchup path");
8708 
8709 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8710 	    "stat_CatchupInRuleCheckerP4Hit",
8711 	    CTLFLAG_RD, &sc->stat_CatchupInRuleCheckerP4Hit,
8712 	    0, "Received packets rule checker hits in Catchup path");
8713 
8714 	SYSCTL_ADD_UINT(ctx, children, OID_AUTO,
8715 	    "com_no_buffers",
8716 	    CTLFLAG_RD, &sc->com_no_buffers,
8717 	    0, "Valid packets received but no RX buffers available");
8718 
8719 #ifdef BCE_DEBUG
8720 	SYSCTL_ADD_PROC(ctx, children, OID_AUTO,
8721 	    "driver_state", CTLTYPE_INT | CTLFLAG_RW,
8722 	    (void *)sc, 0,
8723 	    bce_sysctl_driver_state, "I", "Drive state information");
8724 
8725 	SYSCTL_ADD_PROC(ctx, children, OID_AUTO,
8726 	    "hw_state", CTLTYPE_INT | CTLFLAG_RW,
8727 	    (void *)sc, 0,
8728 	    bce_sysctl_hw_state, "I", "Hardware state information");
8729 
8730 	SYSCTL_ADD_PROC(ctx, children, OID_AUTO,
8731 	    "status_block", CTLTYPE_INT | CTLFLAG_RW,
8732 	    (void *)sc, 0,
8733 	    bce_sysctl_status_block, "I", "Status block");
8734 
8735 	SYSCTL_ADD_PROC(ctx, children, OID_AUTO,
8736 	    "stats_block", CTLTYPE_INT | CTLFLAG_RW,
8737 	    (void *)sc, 0,
8738 	    bce_sysctl_stats_block, "I", "Stats block");
8739 
8740 	SYSCTL_ADD_PROC(ctx, children, OID_AUTO,
8741 	    "bc_state", CTLTYPE_INT | CTLFLAG_RW,
8742 	    (void *)sc, 0,
8743 	    bce_sysctl_bc_state, "I", "Bootcode state information");
8744 
8745 	SYSCTL_ADD_PROC(ctx, children, OID_AUTO,
8746 	    "dump_rx_bd_chain", CTLTYPE_INT | CTLFLAG_RW,
8747 	    (void *)sc, 0,
8748 	    bce_sysctl_dump_rx_bd_chain, "I", "Dump RX BD chain");
8749 
8750 	SYSCTL_ADD_PROC(ctx, children, OID_AUTO,
8751 	    "dump_rx_mbuf_chain", CTLTYPE_INT | CTLFLAG_RW,
8752 	    (void *)sc, 0,
8753 	    bce_sysctl_dump_rx_mbuf_chain, "I", "Dump RX MBUF chain");
8754 
8755 	SYSCTL_ADD_PROC(ctx, children, OID_AUTO,
8756 	    "dump_tx_chain", CTLTYPE_INT | CTLFLAG_RW,
8757 	    (void *)sc, 0,
8758 	    bce_sysctl_dump_tx_chain, "I", "Dump tx_bd chain");
8759 
8760 #ifdef BCE_JUMBO_HDRSPLIT
8761 	SYSCTL_ADD_PROC(ctx, children, OID_AUTO,
8762 	    "dump_pg_chain", CTLTYPE_INT | CTLFLAG_RW,
8763 	    (void *)sc, 0,
8764 	    bce_sysctl_dump_pg_chain, "I", "Dump page chain");
8765 #endif
8766 	SYSCTL_ADD_PROC(ctx, children, OID_AUTO,
8767 	    "dump_ctx", CTLTYPE_INT | CTLFLAG_RW,
8768 	    (void *)sc, 0,
8769 	    bce_sysctl_dump_ctx, "I", "Dump context memory");
8770 
8771 	SYSCTL_ADD_PROC(ctx, children, OID_AUTO,
8772 	    "breakpoint", CTLTYPE_INT | CTLFLAG_RW,
8773 	    (void *)sc, 0,
8774 	    bce_sysctl_breakpoint, "I", "Driver breakpoint");
8775 
8776 	SYSCTL_ADD_PROC(ctx, children, OID_AUTO,
8777 	    "reg_read", CTLTYPE_INT | CTLFLAG_RW,
8778 	    (void *)sc, 0,
8779 	    bce_sysctl_reg_read, "I", "Register read");
8780 
8781 	SYSCTL_ADD_PROC(ctx, children, OID_AUTO,
8782 	    "nvram_read", CTLTYPE_INT | CTLFLAG_RW,
8783 	    (void *)sc, 0,
8784 	    bce_sysctl_nvram_read, "I", "NVRAM read");
8785 
8786 	SYSCTL_ADD_PROC(ctx, children, OID_AUTO,
8787 	    "phy_read", CTLTYPE_INT | CTLFLAG_RW,
8788 	    (void *)sc, 0,
8789 	    bce_sysctl_phy_read, "I", "PHY register read");
8790 
8791 #endif
8792 
8793 	DBEXIT(BCE_VERBOSE_MISC);
8794 }
8795 
8796 
8797 /****************************************************************************/
8798 /* BCE Debug Routines                                                       */
8799 /****************************************************************************/
8800 #ifdef BCE_DEBUG
8801 
8802 /****************************************************************************/
8803 /* Freezes the controller to allow for a cohesive state dump.               */
8804 /*                                                                          */
8805 /* Returns:                                                                 */
8806 /*   Nothing.                                                               */
8807 /****************************************************************************/
8808 static __attribute__ ((noinline)) void
8809 bce_freeze_controller(struct bce_softc *sc)
8810 {
8811 	u32 val;
8812 	val = REG_RD(sc, BCE_MISC_COMMAND);
8813 	val |= BCE_MISC_COMMAND_DISABLE_ALL;
8814 	REG_WR(sc, BCE_MISC_COMMAND, val);
8815 }
8816 
8817 
8818 /****************************************************************************/
8819 /* Unfreezes the controller after a freeze operation.  This may not always  */
8820 /* work and the controller will require a reset!                            */
8821 /*                                                                          */
8822 /* Returns:                                                                 */
8823 /*   Nothing.                                                               */
8824 /****************************************************************************/
8825 static __attribute__ ((noinline)) void
8826 bce_unfreeze_controller(struct bce_softc *sc)
8827 {
8828 	u32 val;
8829 	val = REG_RD(sc, BCE_MISC_COMMAND);
8830 	val |= BCE_MISC_COMMAND_ENABLE_ALL;
8831 	REG_WR(sc, BCE_MISC_COMMAND, val);
8832 }
8833 
8834 
8835 /****************************************************************************/
8836 /* Prints out Ethernet frame information from an mbuf.                      */
8837 /*                                                                          */
8838 /* Partially decode an Ethernet frame to look at some important headers.    */
8839 /*                                                                          */
8840 /* Returns:                                                                 */
8841 /*   Nothing.                                                               */
8842 /****************************************************************************/
8843 static __attribute__ ((noinline)) void
8844 bce_dump_enet(struct bce_softc *sc, struct mbuf *m)
8845 {
8846 	struct ether_vlan_header *eh;
8847 	u16 etype;
8848 	int ehlen;
8849 	struct ip *ip;
8850 	struct tcphdr *th;
8851 	struct udphdr *uh;
8852 	struct arphdr *ah;
8853 
8854 	BCE_PRINTF(
8855 	    "-----------------------------"
8856 	    " Frame Decode "
8857 	    "-----------------------------\n");
8858 
8859 	eh = mtod(m, struct ether_vlan_header *);
8860 
8861 	/* Handle VLAN encapsulation if present. */
8862 	if (eh->evl_encap_proto == htons(ETHERTYPE_VLAN)) {
8863 		etype = ntohs(eh->evl_proto);
8864 		ehlen = ETHER_HDR_LEN + ETHER_VLAN_ENCAP_LEN;
8865 	} else {
8866 		etype = ntohs(eh->evl_encap_proto);
8867 		ehlen = ETHER_HDR_LEN;
8868 	}
8869 
8870 	/* ToDo: Add VLAN output. */
8871 	BCE_PRINTF("enet: dest = %6D, src = %6D, type = 0x%04X, hlen = %d\n",
8872 	    eh->evl_dhost, ":", eh->evl_shost, ":", etype, ehlen);
8873 
8874 	switch (etype) {
8875 	case ETHERTYPE_IP:
8876 		ip = (struct ip *)(m->m_data + ehlen);
8877 		BCE_PRINTF("--ip: dest = 0x%08X , src = 0x%08X, "
8878 		    "len = %d bytes, protocol = 0x%02X, xsum = 0x%04X\n",
8879 		    ntohl(ip->ip_dst.s_addr), ntohl(ip->ip_src.s_addr),
8880 		    ntohs(ip->ip_len), ip->ip_p, ntohs(ip->ip_sum));
8881 
8882 		switch (ip->ip_p) {
8883 		case IPPROTO_TCP:
8884 			th = (struct tcphdr *)((caddr_t)ip + (ip->ip_hl << 2));
8885 			BCE_PRINTF("-tcp: dest = %d, src = %d, hlen = %d bytes, "
8886 			    "flags = 0x%b, csum = 0x%04X\n",
8887 			    ntohs(th->th_dport), ntohs(th->th_sport),
8888 			    (th->th_off << 2), th->th_flags,
8889 			    "\20\10CWR\07ECE\06URG\05ACK\04PSH\03RST"
8890 			    "\02SYN\01FIN", ntohs(th->th_sum));
8891 			break;
8892 		case IPPROTO_UDP:
8893 			uh = (struct udphdr *)((caddr_t)ip + (ip->ip_hl << 2));
8894 			BCE_PRINTF("-udp: dest = %d, src = %d, len = %d "
8895 			    "bytes, csum = 0x%04X\n", ntohs(uh->uh_dport),
8896 			    ntohs(uh->uh_sport), ntohs(uh->uh_ulen),
8897 			    ntohs(uh->uh_sum));
8898 			break;
8899 		case IPPROTO_ICMP:
8900 			BCE_PRINTF("icmp:\n");
8901 			break;
8902 		default:
8903 			BCE_PRINTF("----: Other IP protocol.\n");
8904 			}
8905 		break;
8906 	case ETHERTYPE_IPV6:
8907 		BCE_PRINTF("ipv6: No decode supported.\n");
8908 		break;
8909 	case ETHERTYPE_ARP:
8910 		BCE_PRINTF("-arp: ");
8911 		ah = (struct arphdr *) (m->m_data + ehlen);
8912 		switch (ntohs(ah->ar_op)) {
8913 		case ARPOP_REVREQUEST:
8914 			printf("reverse ARP request\n");
8915 			break;
8916 		case ARPOP_REVREPLY:
8917 			printf("reverse ARP reply\n");
8918 			break;
8919 		case ARPOP_REQUEST:
8920 			printf("ARP request\n");
8921 			break;
8922 		case ARPOP_REPLY:
8923 			printf("ARP reply\n");
8924 			break;
8925 		default:
8926 			printf("other ARP operation\n");
8927 		}
8928 		break;
8929 	default:
8930 		BCE_PRINTF("----: Other protocol.\n");
8931 	}
8932 
8933 	BCE_PRINTF(
8934 		"-----------------------------"
8935 		"--------------"
8936 		"-----------------------------\n");
8937 }
8938 
8939 
8940 /****************************************************************************/
8941 /* Prints out information about an mbuf.                                    */
8942 /*                                                                          */
8943 /* Returns:                                                                 */
8944 /*   Nothing.                                                               */
8945 /****************************************************************************/
8946 static __attribute__ ((noinline)) void
8947 bce_dump_mbuf(struct bce_softc *sc, struct mbuf *m)
8948 {
8949 	struct mbuf *mp = m;
8950 
8951 	if (m == NULL) {
8952 		BCE_PRINTF("mbuf: null pointer\n");
8953 		return;
8954 	}
8955 
8956 	while (mp) {
8957 		BCE_PRINTF("mbuf: %p, m_len = %d, m_flags = 0x%b, "
8958 		    "m_data = %p\n", mp, mp->m_len, mp->m_flags,
8959 		    "\20\1M_EXT\2M_PKTHDR\3M_EOR\4M_RDONLY", mp->m_data);
8960 
8961 		if (mp->m_flags & M_PKTHDR) {
8962 			BCE_PRINTF("- m_pkthdr: len = %d, flags = 0x%b, "
8963 			    "csum_flags = %b\n", mp->m_pkthdr.len,
8964 			    mp->m_flags, "\20\12M_BCAST\13M_MCAST\14M_FRAG"
8965 			    "\15M_FIRSTFRAG\16M_LASTFRAG\21M_VLANTAG"
8966 			    "\22M_PROMISC\23M_NOFREE",
8967 			    mp->m_pkthdr.csum_flags,
8968 			    "\20\1CSUM_IP\2CSUM_TCP\3CSUM_UDP\4CSUM_IP_FRAGS"
8969 			    "\5CSUM_FRAGMENT\6CSUM_TSO\11CSUM_IP_CHECKED"
8970 			    "\12CSUM_IP_VALID\13CSUM_DATA_VALID"
8971 			    "\14CSUM_PSEUDO_HDR");
8972 		}
8973 
8974 		if (mp->m_flags & M_EXT) {
8975 			BCE_PRINTF("- m_ext: %p, ext_size = %d, type = ",
8976 			    mp->m_ext.ext_buf, mp->m_ext.ext_size);
8977 			switch (mp->m_ext.ext_type) {
8978 			case EXT_CLUSTER:
8979 				printf("EXT_CLUSTER\n"); break;
8980 			case EXT_SFBUF:
8981 				printf("EXT_SFBUF\n"); break;
8982 			case EXT_JUMBO9:
8983 				printf("EXT_JUMBO9\n"); break;
8984 			case EXT_JUMBO16:
8985 				printf("EXT_JUMBO16\n"); break;
8986 			case EXT_PACKET:
8987 				printf("EXT_PACKET\n"); break;
8988 			case EXT_MBUF:
8989 				printf("EXT_MBUF\n"); break;
8990 			case EXT_NET_DRV:
8991 				printf("EXT_NET_DRV\n"); break;
8992 			case EXT_MOD_TYPE:
8993 				printf("EXT_MDD_TYPE\n"); break;
8994 			case EXT_DISPOSABLE:
8995 				printf("EXT_DISPOSABLE\n"); break;
8996 			case EXT_EXTREF:
8997 				printf("EXT_EXTREF\n"); break;
8998 			default:
8999 				printf("UNKNOWN\n");
9000 			}
9001 		}
9002 
9003 		mp = mp->m_next;
9004 	}
9005 }
9006 
9007 
9008 /****************************************************************************/
9009 /* Prints out the mbufs in the TX mbuf chain.                               */
9010 /*                                                                          */
9011 /* Returns:                                                                 */
9012 /*   Nothing.                                                               */
9013 /****************************************************************************/
9014 static __attribute__ ((noinline)) void
9015 bce_dump_tx_mbuf_chain(struct bce_softc *sc, u16 chain_prod, int count)
9016 {
9017 	struct mbuf *m;
9018 
9019 	BCE_PRINTF(
9020 		"----------------------------"
9021 		"  tx mbuf data  "
9022 		"----------------------------\n");
9023 
9024 	for (int i = 0; i < count; i++) {
9025 	 	m = sc->tx_mbuf_ptr[chain_prod];
9026 		BCE_PRINTF("txmbuf[0x%04X]\n", chain_prod);
9027 		bce_dump_mbuf(sc, m);
9028 		chain_prod = TX_CHAIN_IDX(NEXT_TX_BD(chain_prod));
9029 	}
9030 
9031 	BCE_PRINTF(
9032 		"----------------------------"
9033 		"----------------"
9034 		"----------------------------\n");
9035 }
9036 
9037 
9038 /****************************************************************************/
9039 /* Prints out the mbufs in the RX mbuf chain.                               */
9040 /*                                                                          */
9041 /* Returns:                                                                 */
9042 /*   Nothing.                                                               */
9043 /****************************************************************************/
9044 static __attribute__ ((noinline)) void
9045 bce_dump_rx_mbuf_chain(struct bce_softc *sc, u16 chain_prod, int count)
9046 {
9047 	struct mbuf *m;
9048 
9049 	BCE_PRINTF(
9050 		"----------------------------"
9051 		"  rx mbuf data  "
9052 		"----------------------------\n");
9053 
9054 	for (int i = 0; i < count; i++) {
9055 	 	m = sc->rx_mbuf_ptr[chain_prod];
9056 		BCE_PRINTF("rxmbuf[0x%04X]\n", chain_prod);
9057 		bce_dump_mbuf(sc, m);
9058 		chain_prod = RX_CHAIN_IDX(NEXT_RX_BD(chain_prod));
9059 	}
9060 
9061 
9062 	BCE_PRINTF(
9063 		"----------------------------"
9064 		"----------------"
9065 		"----------------------------\n");
9066 }
9067 
9068 
9069 #ifdef BCE_JUMBO_HDRSPLIT
9070 /****************************************************************************/
9071 /* Prints out the mbufs in the mbuf page chain.                             */
9072 /*                                                                          */
9073 /* Returns:                                                                 */
9074 /*   Nothing.                                                               */
9075 /****************************************************************************/
9076 static __attribute__ ((noinline)) void
9077 bce_dump_pg_mbuf_chain(struct bce_softc *sc, u16 chain_prod, int count)
9078 {
9079 	struct mbuf *m;
9080 
9081 	BCE_PRINTF(
9082 		"----------------------------"
9083 		"  pg mbuf data  "
9084 		"----------------------------\n");
9085 
9086 	for (int i = 0; i < count; i++) {
9087 	 	m = sc->pg_mbuf_ptr[chain_prod];
9088 		BCE_PRINTF("pgmbuf[0x%04X]\n", chain_prod);
9089 		bce_dump_mbuf(sc, m);
9090 		chain_prod = PG_CHAIN_IDX(NEXT_PG_BD(chain_prod));
9091 	}
9092 
9093 
9094 	BCE_PRINTF(
9095 		"----------------------------"
9096 		"----------------"
9097 		"----------------------------\n");
9098 }
9099 #endif
9100 
9101 
9102 /****************************************************************************/
9103 /* Prints out a tx_bd structure.                                            */
9104 /*                                                                          */
9105 /* Returns:                                                                 */
9106 /*   Nothing.                                                               */
9107 /****************************************************************************/
9108 static __attribute__ ((noinline)) void
9109 bce_dump_txbd(struct bce_softc *sc, int idx, struct tx_bd *txbd)
9110 {
9111 	int i = 0;
9112 
9113 	if (idx > MAX_TX_BD)
9114 		/* Index out of range. */
9115 		BCE_PRINTF("tx_bd[0x%04X]: Invalid tx_bd index!\n", idx);
9116 	else if ((idx & USABLE_TX_BD_PER_PAGE) == USABLE_TX_BD_PER_PAGE)
9117 		/* TX Chain page pointer. */
9118 		BCE_PRINTF("tx_bd[0x%04X]: haddr = 0x%08X:%08X, chain page "
9119 		    "pointer\n", idx, txbd->tx_bd_haddr_hi,
9120 		    txbd->tx_bd_haddr_lo);
9121 	else {
9122 		/* Normal tx_bd entry. */
9123 		BCE_PRINTF("tx_bd[0x%04X]: haddr = 0x%08X:%08X, "
9124 		    "mss_nbytes = 0x%08X, vlan tag = 0x%04X, flags = "
9125 		    "0x%04X (", idx, txbd->tx_bd_haddr_hi,
9126 		    txbd->tx_bd_haddr_lo, txbd->tx_bd_mss_nbytes,
9127 		    txbd->tx_bd_vlan_tag, txbd->tx_bd_flags);
9128 
9129 		if (txbd->tx_bd_flags & TX_BD_FLAGS_CONN_FAULT) {
9130 			if (i>0)
9131 				printf("|");
9132 			printf("CONN_FAULT");
9133 			i++;
9134 		}
9135 
9136 		if (txbd->tx_bd_flags & TX_BD_FLAGS_TCP_UDP_CKSUM) {
9137 			if (i>0)
9138 				printf("|");
9139 			printf("TCP_UDP_CKSUM");
9140 			i++;
9141 		}
9142 
9143 		if (txbd->tx_bd_flags & TX_BD_FLAGS_IP_CKSUM) {
9144 			if (i>0)
9145 				printf("|");
9146 			printf("IP_CKSUM");
9147 			i++;
9148 		}
9149 
9150 		if (txbd->tx_bd_flags & TX_BD_FLAGS_VLAN_TAG) {
9151 			if (i>0)
9152 				printf("|");
9153 			printf("VLAN");
9154 			i++;
9155 		}
9156 
9157 		if (txbd->tx_bd_flags & TX_BD_FLAGS_COAL_NOW) {
9158 			if (i>0)
9159 				printf("|");
9160 			printf("COAL_NOW");
9161 			i++;
9162 		}
9163 
9164 		if (txbd->tx_bd_flags & TX_BD_FLAGS_DONT_GEN_CRC) {
9165 			if (i>0)
9166 				printf("|");
9167 			printf("DONT_GEN_CRC");
9168 			i++;
9169 		}
9170 
9171 		if (txbd->tx_bd_flags & TX_BD_FLAGS_START) {
9172 			if (i>0)
9173 				printf("|");
9174 			printf("START");
9175 			i++;
9176 		}
9177 
9178 		if (txbd->tx_bd_flags & TX_BD_FLAGS_END) {
9179 			if (i>0)
9180 				printf("|");
9181 			printf("END");
9182 			i++;
9183 		}
9184 
9185 		if (txbd->tx_bd_flags & TX_BD_FLAGS_SW_LSO) {
9186 			if (i>0)
9187 				printf("|");
9188 			printf("LSO");
9189 			i++;
9190 		}
9191 
9192 		if (txbd->tx_bd_flags & TX_BD_FLAGS_SW_OPTION_WORD) {
9193 			if (i>0)
9194 				printf("|");
9195 			printf("SW_OPTION=%d", ((txbd->tx_bd_flags &
9196 			    TX_BD_FLAGS_SW_OPTION_WORD) >> 8)); i++;
9197 		}
9198 
9199 		if (txbd->tx_bd_flags & TX_BD_FLAGS_SW_FLAGS) {
9200 			if (i>0)
9201 				printf("|");
9202 			printf("SW_FLAGS");
9203 			i++;
9204 		}
9205 
9206 		if (txbd->tx_bd_flags & TX_BD_FLAGS_SW_SNAP) {
9207 			if (i>0)
9208 				printf("|");
9209 			printf("SNAP)");
9210 		} else {
9211 			printf(")\n");
9212 		}
9213 	}
9214 }
9215 
9216 
9217 /****************************************************************************/
9218 /* Prints out a rx_bd structure.                                            */
9219 /*                                                                          */
9220 /* Returns:                                                                 */
9221 /*   Nothing.                                                               */
9222 /****************************************************************************/
9223 static __attribute__ ((noinline)) void
9224 bce_dump_rxbd(struct bce_softc *sc, int idx, struct rx_bd *rxbd)
9225 {
9226 	if (idx > MAX_RX_BD)
9227 		/* Index out of range. */
9228 		BCE_PRINTF("rx_bd[0x%04X]: Invalid rx_bd index!\n", idx);
9229 	else if ((idx & USABLE_RX_BD_PER_PAGE) == USABLE_RX_BD_PER_PAGE)
9230 		/* RX Chain page pointer. */
9231 		BCE_PRINTF("rx_bd[0x%04X]: haddr = 0x%08X:%08X, chain page "
9232 		    "pointer\n", idx, rxbd->rx_bd_haddr_hi,
9233 		    rxbd->rx_bd_haddr_lo);
9234 	else
9235 		/* Normal rx_bd entry. */
9236 		BCE_PRINTF("rx_bd[0x%04X]: haddr = 0x%08X:%08X, nbytes = "
9237 		    "0x%08X, flags = 0x%08X\n", idx, rxbd->rx_bd_haddr_hi,
9238 		    rxbd->rx_bd_haddr_lo, rxbd->rx_bd_len,
9239 		    rxbd->rx_bd_flags);
9240 }
9241 
9242 
9243 #ifdef BCE_JUMBO_HDRSPLIT
9244 /****************************************************************************/
9245 /* Prints out a rx_bd structure in the page chain.                          */
9246 /*                                                                          */
9247 /* Returns:                                                                 */
9248 /*   Nothing.                                                               */
9249 /****************************************************************************/
9250 static __attribute__ ((noinline)) void
9251 bce_dump_pgbd(struct bce_softc *sc, int idx, struct rx_bd *pgbd)
9252 {
9253 	if (idx > MAX_PG_BD)
9254 		/* Index out of range. */
9255 		BCE_PRINTF("pg_bd[0x%04X]: Invalid pg_bd index!\n", idx);
9256 	else if ((idx & USABLE_PG_BD_PER_PAGE) == USABLE_PG_BD_PER_PAGE)
9257 		/* Page Chain page pointer. */
9258 		BCE_PRINTF("px_bd[0x%04X]: haddr = 0x%08X:%08X, chain page pointer\n",
9259 			idx, pgbd->rx_bd_haddr_hi, pgbd->rx_bd_haddr_lo);
9260 	else
9261 		/* Normal rx_bd entry. */
9262 		BCE_PRINTF("pg_bd[0x%04X]: haddr = 0x%08X:%08X, nbytes = 0x%08X, "
9263 			"flags = 0x%08X\n", idx,
9264 			pgbd->rx_bd_haddr_hi, pgbd->rx_bd_haddr_lo,
9265 			pgbd->rx_bd_len, pgbd->rx_bd_flags);
9266 }
9267 #endif
9268 
9269 
9270 /****************************************************************************/
9271 /* Prints out a l2_fhdr structure.                                          */
9272 /*                                                                          */
9273 /* Returns:                                                                 */
9274 /*   Nothing.                                                               */
9275 /****************************************************************************/
9276 static __attribute__ ((noinline)) void
9277 bce_dump_l2fhdr(struct bce_softc *sc, int idx, struct l2_fhdr *l2fhdr)
9278 {
9279 	BCE_PRINTF("l2_fhdr[0x%04X]: status = 0x%b, "
9280 		"pkt_len = %d, vlan = 0x%04x, ip_xsum/hdr_len = 0x%04X, "
9281 		"tcp_udp_xsum = 0x%04X\n", idx,
9282 		l2fhdr->l2_fhdr_status, BCE_L2FHDR_PRINTFB,
9283 		l2fhdr->l2_fhdr_pkt_len, l2fhdr->l2_fhdr_vlan_tag,
9284 		l2fhdr->l2_fhdr_ip_xsum, l2fhdr->l2_fhdr_tcp_udp_xsum);
9285 }
9286 
9287 
9288 /****************************************************************************/
9289 /* Prints out context memory info.  (Only useful for CID 0 to 16.)          */
9290 /*                                                                          */
9291 /* Returns:                                                                 */
9292 /*   Nothing.                                                               */
9293 /****************************************************************************/
9294 static __attribute__ ((noinline)) void
9295 bce_dump_ctx(struct bce_softc *sc, u16 cid)
9296 {
9297 	if (cid > TX_CID) {
9298 		BCE_PRINTF(" Unknown CID\n");
9299 		return;
9300 	}
9301 
9302 	BCE_PRINTF(
9303 	    "----------------------------"
9304 	    "    CTX Data    "
9305 	    "----------------------------\n");
9306 
9307 	BCE_PRINTF("     0x%04X - (CID) Context ID\n", cid);
9308 
9309 	if (cid == RX_CID) {
9310 		BCE_PRINTF(" 0x%08X - (L2CTX_RX_HOST_BDIDX) host rx "
9311 		   "producer index\n",
9312 		    CTX_RD(sc, GET_CID_ADDR(cid), BCE_L2CTX_RX_HOST_BDIDX));
9313 		BCE_PRINTF(" 0x%08X - (L2CTX_RX_HOST_BSEQ) host "
9314 		    "byte sequence\n", CTX_RD(sc, GET_CID_ADDR(cid),
9315 		    BCE_L2CTX_RX_HOST_BSEQ));
9316 		BCE_PRINTF(" 0x%08X - (L2CTX_RX_NX_BSEQ) h/w byte sequence\n",
9317 		    CTX_RD(sc, GET_CID_ADDR(cid), BCE_L2CTX_RX_NX_BSEQ));
9318 		BCE_PRINTF(" 0x%08X - (L2CTX_RX_NX_BDHADDR_HI) h/w buffer "
9319 		    "descriptor address\n",
9320  		    CTX_RD(sc, GET_CID_ADDR(cid), BCE_L2CTX_RX_NX_BDHADDR_HI));
9321 		BCE_PRINTF(" 0x%08X - (L2CTX_RX_NX_BDHADDR_LO) h/w buffer "
9322 		    "descriptor address\n",
9323 		    CTX_RD(sc, GET_CID_ADDR(cid), BCE_L2CTX_RX_NX_BDHADDR_LO));
9324 		BCE_PRINTF(" 0x%08X - (L2CTX_RX_NX_BDIDX) h/w rx consumer "
9325 		    "index\n", CTX_RD(sc, GET_CID_ADDR(cid),
9326 		    BCE_L2CTX_RX_NX_BDIDX));
9327 		BCE_PRINTF(" 0x%08X - (L2CTX_RX_HOST_PG_BDIDX) host page "
9328 		    "producer index\n", CTX_RD(sc, GET_CID_ADDR(cid),
9329 		    BCE_L2CTX_RX_HOST_PG_BDIDX));
9330 		BCE_PRINTF(" 0x%08X - (L2CTX_RX_PG_BUF_SIZE) host rx_bd/page "
9331 		    "buffer size\n", CTX_RD(sc, GET_CID_ADDR(cid),
9332 		    BCE_L2CTX_RX_PG_BUF_SIZE));
9333 		BCE_PRINTF(" 0x%08X - (L2CTX_RX_NX_PG_BDHADDR_HI) h/w page "
9334 		    "chain address\n", CTX_RD(sc, GET_CID_ADDR(cid),
9335 		    BCE_L2CTX_RX_NX_PG_BDHADDR_HI));
9336 		BCE_PRINTF(" 0x%08X - (L2CTX_RX_NX_PG_BDHADDR_LO) h/w page "
9337 		    "chain address\n", CTX_RD(sc, GET_CID_ADDR(cid),
9338 		    BCE_L2CTX_RX_NX_PG_BDHADDR_LO));
9339 		BCE_PRINTF(" 0x%08X - (L2CTX_RX_NX_PG_BDIDX) h/w page "
9340 		    "consumer index\n",	CTX_RD(sc, GET_CID_ADDR(cid),
9341 		    BCE_L2CTX_RX_NX_PG_BDIDX));
9342 	} else if (cid == TX_CID) {
9343 		if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
9344 		    (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
9345 			BCE_PRINTF(" 0x%08X - (L2CTX_TX_TYPE_XI) ctx type\n",
9346 			    CTX_RD(sc, GET_CID_ADDR(cid),
9347 			    BCE_L2CTX_TX_TYPE_XI));
9348 			BCE_PRINTF(" 0x%08X - (L2CTX_CMD_TX_TYPE_XI) ctx "
9349 			    "cmd\n", CTX_RD(sc, GET_CID_ADDR(cid),
9350 			    BCE_L2CTX_TX_CMD_TYPE_XI));
9351 			BCE_PRINTF(" 0x%08X - (L2CTX_TX_TBDR_BDHADDR_HI_XI) "
9352 			    "h/w buffer descriptor address\n",
9353 			    CTX_RD(sc, GET_CID_ADDR(cid),
9354 			    BCE_L2CTX_TX_TBDR_BHADDR_HI_XI));
9355 			BCE_PRINTF(" 0x%08X - (L2CTX_TX_TBDR_BHADDR_LO_XI) "
9356 			    "h/w buffer	descriptor address\n",
9357 			    CTX_RD(sc, GET_CID_ADDR(cid),
9358 			    BCE_L2CTX_TX_TBDR_BHADDR_LO_XI));
9359 			BCE_PRINTF(" 0x%08X - (L2CTX_TX_HOST_BIDX_XI) "
9360 			    "host producer index\n",
9361 			    CTX_RD(sc, GET_CID_ADDR(cid),
9362 			    BCE_L2CTX_TX_HOST_BIDX_XI));
9363 			BCE_PRINTF(" 0x%08X - (L2CTX_TX_HOST_BSEQ_XI) "
9364 			    "host byte sequence\n",
9365 			    CTX_RD(sc, GET_CID_ADDR(cid),
9366 			    BCE_L2CTX_TX_HOST_BSEQ_XI));
9367 		} else {
9368 			BCE_PRINTF(" 0x%08X - (L2CTX_TX_TYPE) ctx type\n",
9369 			    CTX_RD(sc, GET_CID_ADDR(cid), BCE_L2CTX_TX_TYPE));
9370 			BCE_PRINTF(" 0x%08X - (L2CTX_TX_CMD_TYPE) ctx cmd\n",
9371 			    CTX_RD(sc, GET_CID_ADDR(cid),
9372 			    BCE_L2CTX_TX_CMD_TYPE));
9373 			BCE_PRINTF(" 0x%08X - (L2CTX_TX_TBDR_BDHADDR_HI) "
9374 			    "h/w buffer	descriptor address\n",
9375 			    CTX_RD(sc, GET_CID_ADDR(cid),
9376 			    BCE_L2CTX_TX_TBDR_BHADDR_HI));
9377 			BCE_PRINTF(" 0x%08X - (L2CTX_TX_TBDR_BHADDR_LO) "
9378 			    "h/w buffer	descriptor address\n",
9379 			    CTX_RD(sc, GET_CID_ADDR(cid),
9380 			    BCE_L2CTX_TX_TBDR_BHADDR_LO));
9381 			BCE_PRINTF(" 0x%08X - (L2CTX_TX_HOST_BIDX) host "
9382 			    "producer index\n", CTX_RD(sc, GET_CID_ADDR(cid),
9383 			    BCE_L2CTX_TX_HOST_BIDX));
9384 			BCE_PRINTF(" 0x%08X - (L2CTX_TX_HOST_BSEQ) host byte "
9385 			    "sequence\n", CTX_RD(sc, GET_CID_ADDR(cid),
9386 			    BCE_L2CTX_TX_HOST_BSEQ));
9387 		}
9388 	}
9389 
9390 	BCE_PRINTF(
9391 	   "----------------------------"
9392 	   "    Raw CTX     "
9393 	   "----------------------------\n");
9394 
9395 	for (int i = 0x0; i < 0x300; i += 0x10) {
9396 		BCE_PRINTF("0x%04X: 0x%08X 0x%08X 0x%08X 0x%08X\n", i,
9397 		   CTX_RD(sc, GET_CID_ADDR(cid), i),
9398 		   CTX_RD(sc, GET_CID_ADDR(cid), i + 0x4),
9399 		   CTX_RD(sc, GET_CID_ADDR(cid), i + 0x8),
9400 		   CTX_RD(sc, GET_CID_ADDR(cid), i + 0xc));
9401 	}
9402 
9403 
9404 	BCE_PRINTF(
9405 	   "----------------------------"
9406 	   "----------------"
9407 	   "----------------------------\n");
9408 }
9409 
9410 
9411 /****************************************************************************/
9412 /* Prints out the FTQ data.                                                 */
9413 /*                                                                          */
9414 /* Returns:                                                                */
9415 /*   Nothing.                                                               */
9416 /****************************************************************************/
9417 static __attribute__ ((noinline)) void
9418 bce_dump_ftqs(struct bce_softc *sc)
9419 {
9420 	u32 cmd, ctl, cur_depth, max_depth, valid_cnt, val;
9421 
9422 	BCE_PRINTF(
9423 	    "----------------------------"
9424 	    "    FTQ Data    "
9425 	    "----------------------------\n");
9426 
9427 	BCE_PRINTF("   FTQ    Command    Control   Depth_Now  "
9428 	    "Max_Depth  Valid_Cnt \n");
9429 	BCE_PRINTF(" ------- ---------- ---------- ---------- "
9430 	    "---------- ----------\n");
9431 
9432 	/* Setup the generic statistic counters for the FTQ valid count. */
9433 	val = (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_RV2PPQ_VALID_CNT << 24) |
9434 	    (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_RXPCQ_VALID_CNT  << 16) |
9435 	    (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_RXPQ_VALID_CNT   <<  8) |
9436 	    (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_RLUPQ_VALID_CNT);
9437 	REG_WR(sc, BCE_HC_STAT_GEN_SEL_0, val);
9438 
9439 	val = (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_TSCHQ_VALID_CNT  << 24) |
9440 	    (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_RDMAQ_VALID_CNT  << 16) |
9441 	    (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_RV2PTQ_VALID_CNT <<  8) |
9442 	    (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_RV2PMQ_VALID_CNT);
9443 	REG_WR(sc, BCE_HC_STAT_GEN_SEL_1, val);
9444 
9445 	val = (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_TPATQ_VALID_CNT  << 24) |
9446 	    (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_TDMAQ_VALID_CNT  << 16) |
9447 	    (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_TXPQ_VALID_CNT   <<  8) |
9448 	    (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_TBDRQ_VALID_CNT);
9449 	REG_WR(sc, BCE_HC_STAT_GEN_SEL_2, val);
9450 
9451 	val = (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_COMQ_VALID_CNT   << 24) |
9452 	    (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_COMTQ_VALID_CNT  << 16) |
9453 	    (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_COMXQ_VALID_CNT  <<  8) |
9454 	    (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_TASQ_VALID_CNT);
9455 	REG_WR(sc, BCE_HC_STAT_GEN_SEL_3, val);
9456 
9457 	/* Input queue to the Receive Lookup state machine */
9458 	cmd = REG_RD(sc, BCE_RLUP_FTQ_CMD);
9459 	ctl = REG_RD(sc, BCE_RLUP_FTQ_CTL);
9460 	cur_depth = (ctl & BCE_RLUP_FTQ_CTL_CUR_DEPTH) >> 22;
9461 	max_depth = (ctl & BCE_RLUP_FTQ_CTL_MAX_DEPTH) >> 12;
9462 	valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT0);
9463 	BCE_PRINTF(" RLUP    0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9464 	    cmd, ctl, cur_depth, max_depth, valid_cnt);
9465 
9466 	/* Input queue to the Receive Processor */
9467 	cmd = REG_RD_IND(sc, BCE_RXP_FTQ_CMD);
9468 	ctl = REG_RD_IND(sc, BCE_RXP_FTQ_CTL);
9469 	cur_depth = (ctl & BCE_RXP_FTQ_CTL_CUR_DEPTH) >> 22;
9470 	max_depth = (ctl & BCE_RXP_FTQ_CTL_MAX_DEPTH) >> 12;
9471 	valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT1);
9472 	BCE_PRINTF(" RXP     0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9473 	    cmd, ctl, cur_depth, max_depth, valid_cnt);
9474 
9475 	/* Input queue to the Recevie Processor */
9476 	cmd = REG_RD_IND(sc, BCE_RXP_CFTQ_CMD);
9477 	ctl = REG_RD_IND(sc, BCE_RXP_CFTQ_CTL);
9478 	cur_depth = (ctl & BCE_RXP_CFTQ_CTL_CUR_DEPTH) >> 22;
9479 	max_depth = (ctl & BCE_RXP_CFTQ_CTL_MAX_DEPTH) >> 12;
9480 	valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT2);
9481 	BCE_PRINTF(" RXPC    0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9482 	    cmd, ctl, cur_depth, max_depth, valid_cnt);
9483 
9484 	/* Input queue to the Receive Virtual to Physical state machine */
9485 	cmd = REG_RD(sc, BCE_RV2P_PFTQ_CMD);
9486 	ctl = REG_RD(sc, BCE_RV2P_PFTQ_CTL);
9487 	cur_depth = (ctl & BCE_RV2P_PFTQ_CTL_CUR_DEPTH) >> 22;
9488 	max_depth = (ctl & BCE_RV2P_PFTQ_CTL_MAX_DEPTH) >> 12;
9489 	valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT3);
9490 	BCE_PRINTF(" RV2PP   0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9491 	    cmd, ctl, cur_depth, max_depth, valid_cnt);
9492 
9493 	/* Input queue to the Recevie Virtual to Physical state machine */
9494 	cmd = REG_RD(sc, BCE_RV2P_MFTQ_CMD);
9495 	ctl = REG_RD(sc, BCE_RV2P_MFTQ_CTL);
9496 	cur_depth = (ctl & BCE_RV2P_MFTQ_CTL_CUR_DEPTH) >> 22;
9497 	max_depth = (ctl & BCE_RV2P_MFTQ_CTL_MAX_DEPTH) >> 12;
9498 	valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT4);
9499 	BCE_PRINTF(" RV2PM   0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9500 	    cmd, ctl, cur_depth, max_depth, valid_cnt);
9501 
9502 	/* Input queue to the Receive Virtual to Physical state machine */
9503 	cmd = REG_RD(sc, BCE_RV2P_TFTQ_CMD);
9504 	ctl = REG_RD(sc, BCE_RV2P_TFTQ_CTL);
9505 	cur_depth = (ctl & BCE_RV2P_TFTQ_CTL_CUR_DEPTH) >> 22;
9506 	max_depth = (ctl & BCE_RV2P_TFTQ_CTL_MAX_DEPTH) >> 12;
9507 	valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT5);
9508 	BCE_PRINTF(" RV2PT   0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9509 	    cmd, ctl, cur_depth, max_depth, valid_cnt);
9510 
9511 	/* Input queue to the Receive DMA state machine */
9512 	cmd = REG_RD(sc, BCE_RDMA_FTQ_CMD);
9513 	ctl = REG_RD(sc, BCE_RDMA_FTQ_CTL);
9514 	cur_depth = (ctl & BCE_RDMA_FTQ_CTL_CUR_DEPTH) >> 22;
9515 	max_depth = (ctl & BCE_RDMA_FTQ_CTL_MAX_DEPTH) >> 12;
9516 	valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT6);
9517 	BCE_PRINTF(" RDMA    0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9518 	    cmd, ctl, cur_depth, max_depth, valid_cnt);
9519 
9520 	/* Input queue to the Transmit Scheduler state machine */
9521 	cmd = REG_RD(sc, BCE_TSCH_FTQ_CMD);
9522 	ctl = REG_RD(sc, BCE_TSCH_FTQ_CTL);
9523 	cur_depth = (ctl & BCE_TSCH_FTQ_CTL_CUR_DEPTH) >> 22;
9524 	max_depth = (ctl & BCE_TSCH_FTQ_CTL_MAX_DEPTH) >> 12;
9525 	valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT7);
9526 	BCE_PRINTF(" TSCH    0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9527 	    cmd, ctl, cur_depth, max_depth, valid_cnt);
9528 
9529 	/* Input queue to the Transmit Buffer Descriptor state machine */
9530 	cmd = REG_RD(sc, BCE_TBDR_FTQ_CMD);
9531 	ctl = REG_RD(sc, BCE_TBDR_FTQ_CTL);
9532 	cur_depth = (ctl & BCE_TBDR_FTQ_CTL_CUR_DEPTH) >> 22;
9533 	max_depth = (ctl & BCE_TBDR_FTQ_CTL_MAX_DEPTH) >> 12;
9534 	valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT8);
9535 	BCE_PRINTF(" TBDR    0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9536 	    cmd, ctl, cur_depth, max_depth, valid_cnt);
9537 
9538 	/* Input queue to the Transmit Processor */
9539 	cmd = REG_RD_IND(sc, BCE_TXP_FTQ_CMD);
9540 	ctl = REG_RD_IND(sc, BCE_TXP_FTQ_CTL);
9541 	cur_depth = (ctl & BCE_TXP_FTQ_CTL_CUR_DEPTH) >> 22;
9542 	max_depth = (ctl & BCE_TXP_FTQ_CTL_MAX_DEPTH) >> 12;
9543 	valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT9);
9544 	BCE_PRINTF(" TXP     0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9545 	    cmd, ctl, cur_depth, max_depth, valid_cnt);
9546 
9547 	/* Input queue to the Transmit DMA state machine */
9548 	cmd = REG_RD(sc, BCE_TDMA_FTQ_CMD);
9549 	ctl = REG_RD(sc, BCE_TDMA_FTQ_CTL);
9550 	cur_depth = (ctl & BCE_TDMA_FTQ_CTL_CUR_DEPTH) >> 22;
9551 	max_depth = (ctl & BCE_TDMA_FTQ_CTL_MAX_DEPTH) >> 12;
9552 	valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT10);
9553 	BCE_PRINTF(" TDMA    0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9554 	    cmd, ctl, cur_depth, max_depth, valid_cnt);
9555 
9556 	/* Input queue to the Transmit Patch-Up Processor */
9557 	cmd = REG_RD_IND(sc, BCE_TPAT_FTQ_CMD);
9558 	ctl = REG_RD_IND(sc, BCE_TPAT_FTQ_CTL);
9559 	cur_depth = (ctl & BCE_TPAT_FTQ_CTL_CUR_DEPTH) >> 22;
9560 	max_depth = (ctl & BCE_TPAT_FTQ_CTL_MAX_DEPTH) >> 12;
9561 	valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT11);
9562 	BCE_PRINTF(" TPAT    0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9563 	    cmd, ctl, cur_depth, max_depth, valid_cnt);
9564 
9565 	/* Input queue to the Transmit Assembler state machine */
9566 	cmd = REG_RD_IND(sc, BCE_TAS_FTQ_CMD);
9567 	ctl = REG_RD_IND(sc, BCE_TAS_FTQ_CTL);
9568 	cur_depth = (ctl & BCE_TAS_FTQ_CTL_CUR_DEPTH) >> 22;
9569 	max_depth = (ctl & BCE_TAS_FTQ_CTL_MAX_DEPTH) >> 12;
9570 	valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT12);
9571 	BCE_PRINTF(" TAS     0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9572 	    cmd, ctl, cur_depth, max_depth, valid_cnt);
9573 
9574 	/* Input queue to the Completion Processor */
9575 	cmd = REG_RD_IND(sc, BCE_COM_COMXQ_FTQ_CMD);
9576 	ctl = REG_RD_IND(sc, BCE_COM_COMXQ_FTQ_CTL);
9577 	cur_depth = (ctl & BCE_COM_COMXQ_FTQ_CTL_CUR_DEPTH) >> 22;
9578 	max_depth = (ctl & BCE_COM_COMXQ_FTQ_CTL_MAX_DEPTH) >> 12;
9579 	valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT13);
9580 	BCE_PRINTF(" COMX    0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9581 	    cmd, ctl, cur_depth, max_depth, valid_cnt);
9582 
9583 	/* Input queue to the Completion Processor */
9584 	cmd = REG_RD_IND(sc, BCE_COM_COMTQ_FTQ_CMD);
9585 	ctl = REG_RD_IND(sc, BCE_COM_COMTQ_FTQ_CTL);
9586 	cur_depth = (ctl & BCE_COM_COMTQ_FTQ_CTL_CUR_DEPTH) >> 22;
9587 	max_depth = (ctl & BCE_COM_COMTQ_FTQ_CTL_MAX_DEPTH) >> 12;
9588 	valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT14);
9589 	BCE_PRINTF(" COMT    0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9590 	    cmd, ctl, cur_depth, max_depth, valid_cnt);
9591 
9592 	/* Input queue to the Completion Processor */
9593 	cmd = REG_RD_IND(sc, BCE_COM_COMQ_FTQ_CMD);
9594 	ctl = REG_RD_IND(sc, BCE_COM_COMQ_FTQ_CTL);
9595 	cur_depth = (ctl & BCE_COM_COMQ_FTQ_CTL_CUR_DEPTH) >> 22;
9596 	max_depth = (ctl & BCE_COM_COMQ_FTQ_CTL_MAX_DEPTH) >> 12;
9597 	valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT15);
9598 	BCE_PRINTF(" COMX    0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9599 	    cmd, ctl, cur_depth, max_depth, valid_cnt);
9600 
9601 	/* Setup the generic statistic counters for the FTQ valid count. */
9602 	val = (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_CSQ_VALID_CNT  << 16) |
9603 	    (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_CPQ_VALID_CNT  <<  8) |
9604 	    (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_MGMQ_VALID_CNT);
9605 
9606 	if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
9607 	    (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716))
9608 		val = val |
9609 		    (BCE_HC_STAT_GEN_SEL_0_GEN_SEL_0_RV2PCSQ_VALID_CNT_XI <<
9610 		     24);
9611 	REG_WR(sc, BCE_HC_STAT_GEN_SEL_0, val);
9612 
9613 	/* Input queue to the Management Control Processor */
9614 	cmd = REG_RD_IND(sc, BCE_MCP_MCPQ_FTQ_CMD);
9615 	ctl = REG_RD_IND(sc, BCE_MCP_MCPQ_FTQ_CTL);
9616 	cur_depth = (ctl & BCE_MCP_MCPQ_FTQ_CTL_CUR_DEPTH) >> 22;
9617 	max_depth = (ctl & BCE_MCP_MCPQ_FTQ_CTL_MAX_DEPTH) >> 12;
9618 	valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT0);
9619 	BCE_PRINTF(" MCP     0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9620 	    cmd, ctl, cur_depth, max_depth, valid_cnt);
9621 
9622 	/* Input queue to the Command Processor */
9623 	cmd = REG_RD_IND(sc, BCE_CP_CPQ_FTQ_CMD);
9624 	ctl = REG_RD_IND(sc, BCE_CP_CPQ_FTQ_CTL);
9625 	cur_depth = (ctl & BCE_CP_CPQ_FTQ_CTL_CUR_DEPTH) >> 22;
9626 	max_depth = (ctl & BCE_CP_CPQ_FTQ_CTL_MAX_DEPTH) >> 12;
9627 	valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT1);
9628 	BCE_PRINTF(" CP      0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9629 	    cmd, ctl, cur_depth, max_depth, valid_cnt);
9630 
9631 	/* Input queue to the Completion Scheduler state machine */
9632 	cmd = REG_RD(sc, BCE_CSCH_CH_FTQ_CMD);
9633 	ctl = REG_RD(sc, BCE_CSCH_CH_FTQ_CTL);
9634 	cur_depth = (ctl & BCE_CSCH_CH_FTQ_CTL_CUR_DEPTH) >> 22;
9635 	max_depth = (ctl & BCE_CSCH_CH_FTQ_CTL_MAX_DEPTH) >> 12;
9636 	valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT2);
9637 	BCE_PRINTF(" CS      0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9638 	    cmd, ctl, cur_depth, max_depth, valid_cnt);
9639 
9640 	if ((BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5709) ||
9641 	    (BCE_CHIP_NUM(sc) == BCE_CHIP_NUM_5716)) {
9642 		/* Input queue to the RV2P Command Scheduler */
9643 		cmd = REG_RD(sc, BCE_RV2PCSR_FTQ_CMD);
9644 		ctl = REG_RD(sc, BCE_RV2PCSR_FTQ_CTL);
9645 		cur_depth = (ctl & 0xFFC00000) >> 22;
9646 		max_depth = (ctl & 0x003FF000) >> 12;
9647 		valid_cnt = REG_RD(sc, BCE_HC_STAT_GEN_STAT3);
9648 		BCE_PRINTF(" RV2PCSR 0x%08X 0x%08X 0x%08X 0x%08X 0x%08X\n",
9649 		    cmd, ctl, cur_depth, max_depth, valid_cnt);
9650 	}
9651 
9652 	BCE_PRINTF(
9653 	    "----------------------------"
9654 	    "----------------"
9655 	    "----------------------------\n");
9656 }
9657 
9658 
9659 /****************************************************************************/
9660 /* Prints out the TX chain.                                                 */
9661 /*                                                                          */
9662 /* Returns:                                                                 */
9663 /*   Nothing.                                                               */
9664 /****************************************************************************/
9665 static __attribute__ ((noinline)) void
9666 bce_dump_tx_chain(struct bce_softc *sc, u16 tx_prod, int count)
9667 {
9668 	struct tx_bd *txbd;
9669 
9670 	/* First some info about the tx_bd chain structure. */
9671 	BCE_PRINTF(
9672 	    "----------------------------"
9673 	    "  tx_bd  chain  "
9674 	    "----------------------------\n");
9675 
9676 	BCE_PRINTF("page size      = 0x%08X, tx chain pages        = 0x%08X\n",
9677 	    (u32) BCM_PAGE_SIZE, (u32) TX_PAGES);
9678 	BCE_PRINTF("tx_bd per page = 0x%08X, usable tx_bd per page = 0x%08X\n",
9679 	    (u32) TOTAL_TX_BD_PER_PAGE, (u32) USABLE_TX_BD_PER_PAGE);
9680 	BCE_PRINTF("total tx_bd    = 0x%08X\n", (u32) TOTAL_TX_BD);
9681 
9682 	BCE_PRINTF(
9683 	    "----------------------------"
9684 	    "   tx_bd data   "
9685 	    "----------------------------\n");
9686 
9687 	/* Now print out a decoded list of TX buffer descriptors. */
9688 	for (int i = 0; i < count; i++) {
9689 	 	txbd = &sc->tx_bd_chain[TX_PAGE(tx_prod)][TX_IDX(tx_prod)];
9690 		bce_dump_txbd(sc, tx_prod, txbd);
9691 		tx_prod++;
9692 	}
9693 
9694 	BCE_PRINTF(
9695 	    "----------------------------"
9696 	    "----------------"
9697 	    "----------------------------\n");
9698 }
9699 
9700 
9701 /****************************************************************************/
9702 /* Prints out the RX chain.                                                 */
9703 /*                                                                          */
9704 /* Returns:                                                                 */
9705 /*   Nothing.                                                               */
9706 /****************************************************************************/
9707 static __attribute__ ((noinline)) void
9708 bce_dump_rx_bd_chain(struct bce_softc *sc, u16 rx_prod, int count)
9709 {
9710 	struct rx_bd *rxbd;
9711 
9712 	/* First some info about the rx_bd chain structure. */
9713 	BCE_PRINTF(
9714 	    "----------------------------"
9715 	    "  rx_bd  chain  "
9716 	    "----------------------------\n");
9717 
9718 	BCE_PRINTF("page size      = 0x%08X, rx chain pages        = 0x%08X\n",
9719 	    (u32) BCM_PAGE_SIZE, (u32) RX_PAGES);
9720 
9721 	BCE_PRINTF("rx_bd per page = 0x%08X, usable rx_bd per page = 0x%08X\n",
9722 	    (u32) TOTAL_RX_BD_PER_PAGE, (u32) USABLE_RX_BD_PER_PAGE);
9723 
9724 	BCE_PRINTF("total rx_bd    = 0x%08X\n", (u32) TOTAL_RX_BD);
9725 
9726 	BCE_PRINTF(
9727 	    "----------------------------"
9728 	    "   rx_bd data   "
9729 	    "----------------------------\n");
9730 
9731 	/* Now print out the rx_bd's themselves. */
9732 	for (int i = 0; i < count; i++) {
9733 		rxbd = &sc->rx_bd_chain[RX_PAGE(rx_prod)][RX_IDX(rx_prod)];
9734 		bce_dump_rxbd(sc, rx_prod, rxbd);
9735 		rx_prod = RX_CHAIN_IDX(rx_prod + 1);
9736 	}
9737 
9738 	BCE_PRINTF(
9739 	    "----------------------------"
9740 	    "----------------"
9741 	    "----------------------------\n");
9742 }
9743 
9744 
9745 #ifdef BCE_JUMBO_HDRSPLIT
9746 /****************************************************************************/
9747 /* Prints out the page chain.                                               */
9748 /*                                                                          */
9749 /* Returns:                                                                 */
9750 /*   Nothing.                                                               */
9751 /****************************************************************************/
9752 static __attribute__ ((noinline)) void
9753 bce_dump_pg_chain(struct bce_softc *sc, u16 pg_prod, int count)
9754 {
9755 	struct rx_bd *pgbd;
9756 
9757 	/* First some info about the page chain structure. */
9758 	BCE_PRINTF(
9759 	    "----------------------------"
9760 	    "   page chain   "
9761 	    "----------------------------\n");
9762 
9763 	BCE_PRINTF("page size      = 0x%08X, pg chain pages        = 0x%08X\n",
9764 	    (u32) BCM_PAGE_SIZE, (u32) PG_PAGES);
9765 
9766 	BCE_PRINTF("rx_bd per page = 0x%08X, usable rx_bd per page = 0x%08X\n",
9767 	    (u32) TOTAL_PG_BD_PER_PAGE, (u32) USABLE_PG_BD_PER_PAGE);
9768 
9769 	BCE_PRINTF("total rx_bd    = 0x%08X, max_pg_bd             = 0x%08X\n",
9770 	    (u32) TOTAL_PG_BD, (u32) MAX_PG_BD);
9771 
9772 	BCE_PRINTF(
9773 	    "----------------------------"
9774 	    "   page data    "
9775 	    "----------------------------\n");
9776 
9777 	/* Now print out the rx_bd's themselves. */
9778 	for (int i = 0; i < count; i++) {
9779 		pgbd = &sc->pg_bd_chain[PG_PAGE(pg_prod)][PG_IDX(pg_prod)];
9780 		bce_dump_pgbd(sc, pg_prod, pgbd);
9781 		pg_prod = PG_CHAIN_IDX(pg_prod + 1);
9782 	}
9783 
9784 	BCE_PRINTF(
9785 	    "----------------------------"
9786 	    "----------------"
9787 	    "----------------------------\n");
9788 }
9789 #endif
9790 
9791 
9792 #define BCE_PRINT_RX_CONS(arg)						\
9793 if (sblk->status_rx_quick_consumer_index##arg)				\
9794 	BCE_PRINTF("0x%04X(0x%04X) - rx_quick_consumer_index%d\n",	\
9795 	    sblk->status_rx_quick_consumer_index##arg, (u16)		\
9796 	    RX_CHAIN_IDX(sblk->status_rx_quick_consumer_index##arg),	\
9797 	    arg);
9798 
9799 
9800 #define BCE_PRINT_TX_CONS(arg)						\
9801 if (sblk->status_tx_quick_consumer_index##arg)				\
9802 	BCE_PRINTF("0x%04X(0x%04X) - tx_quick_consumer_index%d\n",	\
9803 	    sblk->status_tx_quick_consumer_index##arg, (u16)		\
9804 	    TX_CHAIN_IDX(sblk->status_tx_quick_consumer_index##arg),	\
9805 	    arg);
9806 
9807 /****************************************************************************/
9808 /* Prints out the status block from host memory.                            */
9809 /*                                                                          */
9810 /* Returns:                                                                 */
9811 /*   Nothing.                                                               */
9812 /****************************************************************************/
9813 static __attribute__ ((noinline)) void
9814 bce_dump_status_block(struct bce_softc *sc)
9815 {
9816 	struct status_block *sblk;
9817 
9818 	sblk = sc->status_block;
9819 
9820 	BCE_PRINTF(
9821 	    "----------------------------"
9822 	    "  Status Block  "
9823 	    "----------------------------\n");
9824 
9825 	/* Theses indices are used for normal L2 drivers. */
9826 	BCE_PRINTF("    0x%08X - attn_bits\n",
9827 	    sblk->status_attn_bits);
9828 
9829 	BCE_PRINTF("    0x%08X - attn_bits_ack\n",
9830 	    sblk->status_attn_bits_ack);
9831 
9832 	BCE_PRINT_RX_CONS(0);
9833 	BCE_PRINT_TX_CONS(0)
9834 
9835 	BCE_PRINTF("        0x%04X - status_idx\n", sblk->status_idx);
9836 
9837 	/* Theses indices are not used for normal L2 drivers. */
9838 	BCE_PRINT_RX_CONS(1);   BCE_PRINT_RX_CONS(2);   BCE_PRINT_RX_CONS(3);
9839 	BCE_PRINT_RX_CONS(4);   BCE_PRINT_RX_CONS(5);   BCE_PRINT_RX_CONS(6);
9840 	BCE_PRINT_RX_CONS(7);   BCE_PRINT_RX_CONS(8);   BCE_PRINT_RX_CONS(9);
9841 	BCE_PRINT_RX_CONS(10);  BCE_PRINT_RX_CONS(11);  BCE_PRINT_RX_CONS(12);
9842 	BCE_PRINT_RX_CONS(13);  BCE_PRINT_RX_CONS(14);  BCE_PRINT_RX_CONS(15);
9843 
9844 	BCE_PRINT_TX_CONS(1);   BCE_PRINT_TX_CONS(2);   BCE_PRINT_TX_CONS(3);
9845 
9846 	if (sblk->status_completion_producer_index ||
9847 	    sblk->status_cmd_consumer_index)
9848 		BCE_PRINTF("com_prod  = 0x%08X, cmd_cons      = 0x%08X\n",
9849 		    sblk->status_completion_producer_index,
9850 		    sblk->status_cmd_consumer_index);
9851 
9852 	BCE_PRINTF(
9853 	    "----------------------------"
9854 	    "----------------"
9855 	    "----------------------------\n");
9856 }
9857 
9858 
9859 #define BCE_PRINT_64BIT_STAT(arg) 				\
9860 if (sblk->arg##_lo || sblk->arg##_hi)				\
9861 	BCE_PRINTF("0x%08X:%08X : %s\n", sblk->arg##_hi,	\
9862 	    sblk->arg##_lo, #arg);
9863 
9864 #define BCE_PRINT_32BIT_STAT(arg)				\
9865 if (sblk->arg)							\
9866 	BCE_PRINTF("         0x%08X : %s\n", 			\
9867 	    sblk->arg, #arg);
9868 
9869 /****************************************************************************/
9870 /* Prints out the statistics block from host memory.                        */
9871 /*                                                                          */
9872 /* Returns:                                                                 */
9873 /*   Nothing.                                                               */
9874 /****************************************************************************/
9875 static __attribute__ ((noinline)) void
9876 bce_dump_stats_block(struct bce_softc *sc)
9877 {
9878 	struct statistics_block *sblk;
9879 
9880 	sblk = sc->stats_block;
9881 
9882 	BCE_PRINTF(
9883 	    "---------------"
9884 	    " Stats Block  (All Stats Not Shown Are 0) "
9885 	    "---------------\n");
9886 
9887 	BCE_PRINT_64BIT_STAT(stat_IfHCInOctets);
9888 	BCE_PRINT_64BIT_STAT(stat_IfHCInBadOctets);
9889 	BCE_PRINT_64BIT_STAT(stat_IfHCOutOctets);
9890 	BCE_PRINT_64BIT_STAT(stat_IfHCOutBadOctets);
9891 	BCE_PRINT_64BIT_STAT(stat_IfHCInUcastPkts);
9892 	BCE_PRINT_64BIT_STAT(stat_IfHCInBroadcastPkts);
9893 	BCE_PRINT_64BIT_STAT(stat_IfHCInMulticastPkts);
9894 	BCE_PRINT_64BIT_STAT(stat_IfHCOutUcastPkts);
9895 	BCE_PRINT_64BIT_STAT(stat_IfHCOutBroadcastPkts);
9896 	BCE_PRINT_64BIT_STAT(stat_IfHCOutMulticastPkts);
9897 	BCE_PRINT_32BIT_STAT(
9898 	    stat_emac_tx_stat_dot3statsinternalmactransmiterrors);
9899 	BCE_PRINT_32BIT_STAT(stat_Dot3StatsCarrierSenseErrors);
9900 	BCE_PRINT_32BIT_STAT(stat_Dot3StatsFCSErrors);
9901 	BCE_PRINT_32BIT_STAT(stat_Dot3StatsAlignmentErrors);
9902 	BCE_PRINT_32BIT_STAT(stat_Dot3StatsSingleCollisionFrames);
9903 	BCE_PRINT_32BIT_STAT(stat_Dot3StatsMultipleCollisionFrames);
9904 	BCE_PRINT_32BIT_STAT(stat_Dot3StatsDeferredTransmissions);
9905 	BCE_PRINT_32BIT_STAT(stat_Dot3StatsExcessiveCollisions);
9906 	BCE_PRINT_32BIT_STAT(stat_Dot3StatsLateCollisions);
9907 	BCE_PRINT_32BIT_STAT(stat_EtherStatsCollisions);
9908 	BCE_PRINT_32BIT_STAT(stat_EtherStatsFragments);
9909 	BCE_PRINT_32BIT_STAT(stat_EtherStatsJabbers);
9910 	BCE_PRINT_32BIT_STAT(stat_EtherStatsUndersizePkts);
9911 	BCE_PRINT_32BIT_STAT(stat_EtherStatsOversizePkts);
9912 	BCE_PRINT_32BIT_STAT(stat_EtherStatsPktsRx64Octets);
9913 	BCE_PRINT_32BIT_STAT(stat_EtherStatsPktsRx65Octetsto127Octets);
9914 	BCE_PRINT_32BIT_STAT(stat_EtherStatsPktsRx128Octetsto255Octets);
9915 	BCE_PRINT_32BIT_STAT(stat_EtherStatsPktsRx256Octetsto511Octets);
9916 	BCE_PRINT_32BIT_STAT(stat_EtherStatsPktsRx512Octetsto1023Octets);
9917 	BCE_PRINT_32BIT_STAT(stat_EtherStatsPktsRx1024Octetsto1522Octets);
9918 	BCE_PRINT_32BIT_STAT(stat_EtherStatsPktsRx1523Octetsto9022Octets);
9919 	BCE_PRINT_32BIT_STAT(stat_EtherStatsPktsTx64Octets);
9920 	BCE_PRINT_32BIT_STAT(stat_EtherStatsPktsTx65Octetsto127Octets);
9921 	BCE_PRINT_32BIT_STAT(stat_EtherStatsPktsTx128Octetsto255Octets);
9922 	BCE_PRINT_32BIT_STAT(stat_EtherStatsPktsTx256Octetsto511Octets);
9923 	BCE_PRINT_32BIT_STAT(stat_EtherStatsPktsTx512Octetsto1023Octets);
9924 	BCE_PRINT_32BIT_STAT(stat_EtherStatsPktsTx1024Octetsto1522Octets);
9925 	BCE_PRINT_32BIT_STAT(stat_EtherStatsPktsTx1523Octetsto9022Octets);
9926 	BCE_PRINT_32BIT_STAT(stat_XonPauseFramesReceived);
9927 	BCE_PRINT_32BIT_STAT(stat_XoffPauseFramesReceived);
9928 	BCE_PRINT_32BIT_STAT(stat_OutXonSent);
9929 	BCE_PRINT_32BIT_STAT(stat_OutXoffSent);
9930 	BCE_PRINT_32BIT_STAT(stat_FlowControlDone);
9931 	BCE_PRINT_32BIT_STAT(stat_MacControlFramesReceived);
9932 	BCE_PRINT_32BIT_STAT(stat_XoffStateEntered);
9933 	BCE_PRINT_32BIT_STAT(stat_IfInFramesL2FilterDiscards);
9934 	BCE_PRINT_32BIT_STAT(stat_IfInRuleCheckerDiscards);
9935 	BCE_PRINT_32BIT_STAT(stat_IfInFTQDiscards);
9936 	BCE_PRINT_32BIT_STAT(stat_IfInMBUFDiscards);
9937 	BCE_PRINT_32BIT_STAT(stat_IfInRuleCheckerP4Hit);
9938 	BCE_PRINT_32BIT_STAT(stat_CatchupInRuleCheckerDiscards);
9939 	BCE_PRINT_32BIT_STAT(stat_CatchupInFTQDiscards);
9940 	BCE_PRINT_32BIT_STAT(stat_CatchupInMBUFDiscards);
9941 	BCE_PRINT_32BIT_STAT(stat_CatchupInRuleCheckerP4Hit);
9942 
9943 	BCE_PRINTF(
9944 	    "----------------------------"
9945 	    "----------------"
9946 	    "----------------------------\n");
9947 }
9948 
9949 
9950 /****************************************************************************/
9951 /* Prints out a summary of the driver state.                                */
9952 /*                                                                          */
9953 /* Returns:                                                                 */
9954 /*   Nothing.                                                               */
9955 /****************************************************************************/
9956 static __attribute__ ((noinline)) void
9957 bce_dump_driver_state(struct bce_softc *sc)
9958 {
9959 	u32 val_hi, val_lo;
9960 
9961 	BCE_PRINTF(
9962 	    "-----------------------------"
9963 	    " Driver State "
9964 	    "-----------------------------\n");
9965 
9966 	val_hi = BCE_ADDR_HI(sc);
9967 	val_lo = BCE_ADDR_LO(sc);
9968 	BCE_PRINTF("0x%08X:%08X - (sc) driver softc structure virtual "
9969 	    "address\n", val_hi, val_lo);
9970 
9971 	val_hi = BCE_ADDR_HI(sc->bce_vhandle);
9972 	val_lo = BCE_ADDR_LO(sc->bce_vhandle);
9973 	BCE_PRINTF("0x%08X:%08X - (sc->bce_vhandle) PCI BAR virtual "
9974 	    "address\n", val_hi, val_lo);
9975 
9976 	val_hi = BCE_ADDR_HI(sc->status_block);
9977 	val_lo = BCE_ADDR_LO(sc->status_block);
9978 	BCE_PRINTF("0x%08X:%08X - (sc->status_block) status block "
9979 	    "virtual address\n",	val_hi, val_lo);
9980 
9981 	val_hi = BCE_ADDR_HI(sc->stats_block);
9982 	val_lo = BCE_ADDR_LO(sc->stats_block);
9983 	BCE_PRINTF("0x%08X:%08X - (sc->stats_block) statistics block "
9984 	    "virtual address\n", val_hi, val_lo);
9985 
9986 	val_hi = BCE_ADDR_HI(sc->tx_bd_chain);
9987 	val_lo = BCE_ADDR_LO(sc->tx_bd_chain);
9988 	BCE_PRINTF("0x%08X:%08X - (sc->tx_bd_chain) tx_bd chain "
9989 	    "virtual adddress\n", val_hi, val_lo);
9990 
9991 	val_hi = BCE_ADDR_HI(sc->rx_bd_chain);
9992 	val_lo = BCE_ADDR_LO(sc->rx_bd_chain);
9993 	BCE_PRINTF("0x%08X:%08X - (sc->rx_bd_chain) rx_bd chain "
9994 	    "virtual address\n", val_hi, val_lo);
9995 
9996 #ifdef BCE_JUMBO_HDRSPLIT
9997 	val_hi = BCE_ADDR_HI(sc->pg_bd_chain);
9998 	val_lo = BCE_ADDR_LO(sc->pg_bd_chain);
9999 	BCE_PRINTF("0x%08X:%08X - (sc->pg_bd_chain) page chain "
10000 	    "virtual address\n", val_hi, val_lo);
10001 #endif
10002 
10003 	val_hi = BCE_ADDR_HI(sc->tx_mbuf_ptr);
10004 	val_lo = BCE_ADDR_LO(sc->tx_mbuf_ptr);
10005 	BCE_PRINTF("0x%08X:%08X - (sc->tx_mbuf_ptr) tx mbuf chain "
10006 	    "virtual address\n",	val_hi, val_lo);
10007 
10008 	val_hi = BCE_ADDR_HI(sc->rx_mbuf_ptr);
10009 	val_lo = BCE_ADDR_LO(sc->rx_mbuf_ptr);
10010 	BCE_PRINTF("0x%08X:%08X - (sc->rx_mbuf_ptr) rx mbuf chain "
10011 	    "virtual address\n", val_hi, val_lo);
10012 
10013 #ifdef BCE_JUMBO_HDRSPLIT
10014 	val_hi = BCE_ADDR_HI(sc->pg_mbuf_ptr);
10015 	val_lo = BCE_ADDR_LO(sc->pg_mbuf_ptr);
10016 	BCE_PRINTF("0x%08X:%08X - (sc->pg_mbuf_ptr) page mbuf chain "
10017 	    "virtual address\n", val_hi, val_lo);
10018 #endif
10019 
10020 	BCE_PRINTF("         0x%08X - (sc->interrupts_generated) "
10021 	    "h/w intrs\n", sc->interrupts_generated);
10022 
10023 	BCE_PRINTF("         0x%08X - (sc->rx_interrupts) "
10024 	    "rx interrupts handled\n", sc->rx_interrupts);
10025 
10026 	BCE_PRINTF("         0x%08X - (sc->tx_interrupts) "
10027 	    "tx interrupts handled\n", sc->tx_interrupts);
10028 
10029 	BCE_PRINTF("         0x%08X - (sc->phy_interrupts) "
10030 	    "phy interrupts handled\n", sc->phy_interrupts);
10031 
10032 	BCE_PRINTF("         0x%08X - (sc->last_status_idx) "
10033 	    "status block index\n", sc->last_status_idx);
10034 
10035 	BCE_PRINTF("     0x%04X(0x%04X) - (sc->tx_prod) tx producer "
10036 	    "index\n", sc->tx_prod, (u16) TX_CHAIN_IDX(sc->tx_prod));
10037 
10038 	BCE_PRINTF("     0x%04X(0x%04X) - (sc->tx_cons) tx consumer "
10039 	    "index\n", sc->tx_cons, (u16) TX_CHAIN_IDX(sc->tx_cons));
10040 
10041 	BCE_PRINTF("         0x%08X - (sc->tx_prod_bseq) tx producer "
10042 	    "byte seq index\n",	sc->tx_prod_bseq);
10043 
10044 	BCE_PRINTF("         0x%08X - (sc->debug_tx_mbuf_alloc) tx "
10045 	    "mbufs allocated\n", sc->debug_tx_mbuf_alloc);
10046 
10047 	BCE_PRINTF("         0x%08X - (sc->used_tx_bd) used "
10048 	    "tx_bd's\n", sc->used_tx_bd);
10049 
10050 	BCE_PRINTF("0x%08X/%08X - (sc->tx_hi_watermark) tx hi "
10051 	    "watermark\n", sc->tx_hi_watermark, sc->max_tx_bd);
10052 
10053 	BCE_PRINTF("     0x%04X(0x%04X) - (sc->rx_prod) rx producer "
10054 	    "index\n", sc->rx_prod, (u16) RX_CHAIN_IDX(sc->rx_prod));
10055 
10056 	BCE_PRINTF("     0x%04X(0x%04X) - (sc->rx_cons) rx consumer "
10057 	    "index\n", sc->rx_cons, (u16) RX_CHAIN_IDX(sc->rx_cons));
10058 
10059 	BCE_PRINTF("         0x%08X - (sc->rx_prod_bseq) rx producer "
10060 	    "byte seq index\n",	sc->rx_prod_bseq);
10061 
10062 	BCE_PRINTF("         0x%08X - (sc->debug_rx_mbuf_alloc) rx "
10063 	    "mbufs allocated\n", sc->debug_rx_mbuf_alloc);
10064 
10065 	BCE_PRINTF("         0x%08X - (sc->free_rx_bd) free "
10066 	    "rx_bd's\n", sc->free_rx_bd);
10067 
10068 #ifdef BCE_JUMBO_HDRSPLIT
10069 	BCE_PRINTF("     0x%04X(0x%04X) - (sc->pg_prod) page producer "
10070 	    "index\n", sc->pg_prod, (u16) PG_CHAIN_IDX(sc->pg_prod));
10071 
10072 	BCE_PRINTF("     0x%04X(0x%04X) - (sc->pg_cons) page consumer "
10073 	    "index\n", sc->pg_cons, (u16) PG_CHAIN_IDX(sc->pg_cons));
10074 
10075 	BCE_PRINTF("         0x%08X - (sc->debug_pg_mbuf_alloc) page "
10076 	    "mbufs allocated\n", sc->debug_pg_mbuf_alloc);
10077 
10078 	BCE_PRINTF("         0x%08X - (sc->free_pg_bd) free page "
10079 	    "rx_bd's\n", sc->free_pg_bd);
10080 
10081 	BCE_PRINTF("0x%08X/%08X - (sc->pg_low_watermark) page low "
10082 	    "watermark\n", sc->pg_low_watermark, sc->max_pg_bd);
10083 #endif
10084 
10085 	BCE_PRINTF("         0x%08X - (sc->mbuf_alloc_failed_count) "
10086 	    "mbuf alloc failures\n", sc->mbuf_alloc_failed_count);
10087 
10088 	BCE_PRINTF("         0x%08X - (sc->bce_flags) "
10089 	    "bce mac flags\n", sc->bce_flags);
10090 
10091 	BCE_PRINTF("         0x%08X - (sc->bce_phy_flags) "
10092 	    "bce phy flags\n", sc->bce_phy_flags);
10093 
10094 	BCE_PRINTF(
10095 	    "----------------------------"
10096 	    "----------------"
10097 	    "----------------------------\n");
10098 }
10099 
10100 
10101 /****************************************************************************/
10102 /* Prints out the hardware state through a summary of important register,   */
10103 /* followed by a complete register dump.                                    */
10104 /*                                                                          */
10105 /* Returns:                                                                 */
10106 /*   Nothing.                                                               */
10107 /****************************************************************************/
10108 static __attribute__ ((noinline)) void
10109 bce_dump_hw_state(struct bce_softc *sc)
10110 {
10111 	u32 val;
10112 
10113 	BCE_PRINTF(
10114 	    "----------------------------"
10115 	    " Hardware State "
10116 	    "----------------------------\n");
10117 
10118 	BCE_PRINTF("%s - bootcode version\n", sc->bce_bc_ver);
10119 
10120 	val = REG_RD(sc, BCE_MISC_ENABLE_STATUS_BITS);
10121 	BCE_PRINTF("0x%08X - (0x%06X) misc_enable_status_bits\n",
10122 	    val, BCE_MISC_ENABLE_STATUS_BITS);
10123 
10124 	val = REG_RD(sc, BCE_DMA_STATUS);
10125 	BCE_PRINTF("0x%08X - (0x%06X) dma_status\n",
10126 	    val, BCE_DMA_STATUS);
10127 
10128 	val = REG_RD(sc, BCE_CTX_STATUS);
10129 	BCE_PRINTF("0x%08X - (0x%06X) ctx_status\n",
10130 	    val, BCE_CTX_STATUS);
10131 
10132 	val = REG_RD(sc, BCE_EMAC_STATUS);
10133 	BCE_PRINTF("0x%08X - (0x%06X) emac_status\n",
10134 	    val, BCE_EMAC_STATUS);
10135 
10136 	val = REG_RD(sc, BCE_RPM_STATUS);
10137 	BCE_PRINTF("0x%08X - (0x%06X) rpm_status\n",
10138 	    val, BCE_RPM_STATUS);
10139 
10140 	/* ToDo: Create a #define for this constant. */
10141 	val = REG_RD(sc, 0x2004);
10142 	BCE_PRINTF("0x%08X - (0x%06X) rlup_status\n",
10143 	    val, 0x2004);
10144 
10145 	val = REG_RD(sc, BCE_RV2P_STATUS);
10146 	BCE_PRINTF("0x%08X - (0x%06X) rv2p_status\n",
10147 	    val, BCE_RV2P_STATUS);
10148 
10149 	/* ToDo: Create a #define for this constant. */
10150 	val = REG_RD(sc, 0x2c04);
10151 	BCE_PRINTF("0x%08X - (0x%06X) rdma_status\n",
10152 	    val, 0x2c04);
10153 
10154 	val = REG_RD(sc, BCE_TBDR_STATUS);
10155 	BCE_PRINTF("0x%08X - (0x%06X) tbdr_status\n",
10156 	    val, BCE_TBDR_STATUS);
10157 
10158 	val = REG_RD(sc, BCE_TDMA_STATUS);
10159 	BCE_PRINTF("0x%08X - (0x%06X) tdma_status\n",
10160 	    val, BCE_TDMA_STATUS);
10161 
10162 	val = REG_RD(sc, BCE_HC_STATUS);
10163 	BCE_PRINTF("0x%08X - (0x%06X) hc_status\n",
10164 	    val, BCE_HC_STATUS);
10165 
10166 	val = REG_RD_IND(sc, BCE_TXP_CPU_STATE);
10167 	BCE_PRINTF("0x%08X - (0x%06X) txp_cpu_state\n",
10168 	    val, BCE_TXP_CPU_STATE);
10169 
10170 	val = REG_RD_IND(sc, BCE_TPAT_CPU_STATE);
10171 	BCE_PRINTF("0x%08X - (0x%06X) tpat_cpu_state\n",
10172 	    val, BCE_TPAT_CPU_STATE);
10173 
10174 	val = REG_RD_IND(sc, BCE_RXP_CPU_STATE);
10175 	BCE_PRINTF("0x%08X - (0x%06X) rxp_cpu_state\n",
10176 	    val, BCE_RXP_CPU_STATE);
10177 
10178 	val = REG_RD_IND(sc, BCE_COM_CPU_STATE);
10179 	BCE_PRINTF("0x%08X - (0x%06X) com_cpu_state\n",
10180 	    val, BCE_COM_CPU_STATE);
10181 
10182 	val = REG_RD_IND(sc, BCE_MCP_CPU_STATE);
10183 	BCE_PRINTF("0x%08X - (0x%06X) mcp_cpu_state\n",
10184 	    val, BCE_MCP_CPU_STATE);
10185 
10186 	val = REG_RD_IND(sc, BCE_CP_CPU_STATE);
10187 	BCE_PRINTF("0x%08X - (0x%06X) cp_cpu_state\n",
10188 	    val, BCE_CP_CPU_STATE);
10189 
10190 	BCE_PRINTF(
10191 	    "----------------------------"
10192 	    "----------------"
10193 	    "----------------------------\n");
10194 
10195 	BCE_PRINTF(
10196 	    "----------------------------"
10197 	    " Register  Dump "
10198 	    "----------------------------\n");
10199 
10200 	for (int i = 0x400; i < 0x8000; i += 0x10) {
10201 		BCE_PRINTF("0x%04X: 0x%08X 0x%08X 0x%08X 0x%08X\n",
10202 		    i, REG_RD(sc, i), REG_RD(sc, i + 0x4),
10203 		    REG_RD(sc, i + 0x8), REG_RD(sc, i + 0xC));
10204 	}
10205 
10206 	BCE_PRINTF(
10207 	    "----------------------------"
10208 	    "----------------"
10209 	    "----------------------------\n");
10210 }
10211 
10212 
10213 /****************************************************************************/
10214 /* Prints out the mailbox queue registers.                                  */
10215 /*                                                                          */
10216 /* Returns:                                                                 */
10217 /*   Nothing.                                                               */
10218 /****************************************************************************/
10219 static __attribute__ ((noinline)) void
10220 bce_dump_mq_regs(struct bce_softc *sc)
10221 {
10222 	BCE_PRINTF(
10223 	    "----------------------------"
10224 	    "    MQ Regs     "
10225 	    "----------------------------\n");
10226 
10227 	BCE_PRINTF(
10228 	    "----------------------------"
10229 	    "----------------"
10230 	    "----------------------------\n");
10231 
10232 	for (int i = 0x3c00; i < 0x4000; i += 0x10) {
10233 		BCE_PRINTF("0x%04X: 0x%08X 0x%08X 0x%08X 0x%08X\n",
10234 		    i, REG_RD(sc, i), REG_RD(sc, i + 0x4),
10235 		    REG_RD(sc, i + 0x8), REG_RD(sc, i + 0xC));
10236 	}
10237 
10238 	BCE_PRINTF(
10239 	    "----------------------------"
10240 	    "----------------"
10241 	    "----------------------------\n");
10242 }
10243 
10244 
10245 /****************************************************************************/
10246 /* Prints out the bootcode state.                                           */
10247 /*                                                                          */
10248 /* Returns:                                                                 */
10249 /*   Nothing.                                                               */
10250 /****************************************************************************/
10251 static __attribute__ ((noinline)) void
10252 bce_dump_bc_state(struct bce_softc *sc)
10253 {
10254 	u32 val;
10255 
10256 	BCE_PRINTF(
10257 	    "----------------------------"
10258 	    " Bootcode State "
10259 	    "----------------------------\n");
10260 
10261 	BCE_PRINTF("%s - bootcode version\n", sc->bce_bc_ver);
10262 
10263 	val = bce_shmem_rd(sc, BCE_BC_RESET_TYPE);
10264 	BCE_PRINTF("0x%08X - (0x%06X) reset_type\n",
10265 	    val, BCE_BC_RESET_TYPE);
10266 
10267 	val = bce_shmem_rd(sc, BCE_BC_STATE);
10268 	BCE_PRINTF("0x%08X - (0x%06X) state\n",
10269 	    val, BCE_BC_STATE);
10270 
10271 	val = bce_shmem_rd(sc, BCE_BC_STATE_CONDITION);
10272 	BCE_PRINTF("0x%08X - (0x%06X) condition\n",
10273 	    val, BCE_BC_STATE_CONDITION);
10274 
10275 	val = bce_shmem_rd(sc, BCE_BC_STATE_DEBUG_CMD);
10276 	BCE_PRINTF("0x%08X - (0x%06X) debug_cmd\n",
10277 	    val, BCE_BC_STATE_DEBUG_CMD);
10278 
10279 	BCE_PRINTF(
10280 	    "----------------------------"
10281 	    "----------------"
10282 	    "----------------------------\n");
10283 }
10284 
10285 
10286 /****************************************************************************/
10287 /* Prints out the TXP processor state.                                      */
10288 /*                                                                          */
10289 /* Returns:                                                                 */
10290 /*   Nothing.                                                               */
10291 /****************************************************************************/
10292 static __attribute__ ((noinline)) void
10293 bce_dump_txp_state(struct bce_softc *sc, int regs)
10294 {
10295 	u32 val;
10296 	u32 fw_version[3];
10297 
10298 	BCE_PRINTF(
10299 	    "----------------------------"
10300 	    "   TXP  State   "
10301 	    "----------------------------\n");
10302 
10303 	for (int i = 0; i < 3; i++)
10304 		fw_version[i] = htonl(REG_RD_IND(sc,
10305 		    (BCE_TXP_SCRATCH + 0x10 + i * 4)));
10306 	BCE_PRINTF("Firmware version - %s\n", (char *) fw_version);
10307 
10308 	val = REG_RD_IND(sc, BCE_TXP_CPU_MODE);
10309 	BCE_PRINTF("0x%08X - (0x%06X) txp_cpu_mode\n",
10310 	    val, BCE_TXP_CPU_MODE);
10311 
10312 	val = REG_RD_IND(sc, BCE_TXP_CPU_STATE);
10313 	BCE_PRINTF("0x%08X - (0x%06X) txp_cpu_state\n",
10314 	    val, BCE_TXP_CPU_STATE);
10315 
10316 	val = REG_RD_IND(sc, BCE_TXP_CPU_EVENT_MASK);
10317 	BCE_PRINTF("0x%08X - (0x%06X) txp_cpu_event_mask\n",
10318 	    val, BCE_TXP_CPU_EVENT_MASK);
10319 
10320 	if (regs) {
10321 		BCE_PRINTF(
10322 		    "----------------------------"
10323 		    " Register  Dump "
10324 		    "----------------------------\n");
10325 
10326 		for (int i = BCE_TXP_CPU_MODE; i < 0x68000; i += 0x10) {
10327 			/* Skip the big blank spaces */
10328 			if (i < 0x454000 && i > 0x5ffff)
10329 				BCE_PRINTF("0x%04X: 0x%08X 0x%08X "
10330 				    "0x%08X 0x%08X\n", i,
10331 				    REG_RD_IND(sc, i),
10332 				    REG_RD_IND(sc, i + 0x4),
10333 				    REG_RD_IND(sc, i + 0x8),
10334 				    REG_RD_IND(sc, i + 0xC));
10335 		}
10336 	}
10337 
10338 	BCE_PRINTF(
10339 	    "----------------------------"
10340 	    "----------------"
10341 	    "----------------------------\n");
10342 }
10343 
10344 
10345 /****************************************************************************/
10346 /* Prints out the RXP processor state.                                      */
10347 /*                                                                          */
10348 /* Returns:                                                                 */
10349 /*   Nothing.                                                               */
10350 /****************************************************************************/
10351 static __attribute__ ((noinline)) void
10352 bce_dump_rxp_state(struct bce_softc *sc, int regs)
10353 {
10354 	u32 val;
10355 	u32 fw_version[3];
10356 
10357 	BCE_PRINTF(
10358 	    "----------------------------"
10359 	    "   RXP  State   "
10360 	    "----------------------------\n");
10361 
10362 	for (int i = 0; i < 3; i++)
10363 		fw_version[i] = htonl(REG_RD_IND(sc,
10364 		    (BCE_RXP_SCRATCH + 0x10 + i * 4)));
10365 
10366 	BCE_PRINTF("Firmware version - %s\n", (char *) fw_version);
10367 
10368 	val = REG_RD_IND(sc, BCE_RXP_CPU_MODE);
10369 	BCE_PRINTF("0x%08X - (0x%06X) rxp_cpu_mode\n",
10370 	    val, BCE_RXP_CPU_MODE);
10371 
10372 	val = REG_RD_IND(sc, BCE_RXP_CPU_STATE);
10373 	BCE_PRINTF("0x%08X - (0x%06X) rxp_cpu_state\n",
10374 	    val, BCE_RXP_CPU_STATE);
10375 
10376 	val = REG_RD_IND(sc, BCE_RXP_CPU_EVENT_MASK);
10377 	BCE_PRINTF("0x%08X - (0x%06X) rxp_cpu_event_mask\n",
10378 	    val, BCE_RXP_CPU_EVENT_MASK);
10379 
10380 	if (regs) {
10381 		BCE_PRINTF(
10382 		    "----------------------------"
10383 		    " Register  Dump "
10384 		    "----------------------------\n");
10385 
10386 		for (int i = BCE_RXP_CPU_MODE; i < 0xe8fff; i += 0x10) {
10387 			/* Skip the big blank sapces */
10388 			if (i < 0xc5400 && i > 0xdffff)
10389 				BCE_PRINTF("0x%04X: 0x%08X 0x%08X "
10390 				    "0x%08X 0x%08X\n", i,
10391 				    REG_RD_IND(sc, i),
10392 				    REG_RD_IND(sc, i + 0x4),
10393 				    REG_RD_IND(sc, i + 0x8),
10394 				    REG_RD_IND(sc, i + 0xC));
10395 		}
10396 	}
10397 
10398 	BCE_PRINTF(
10399 	    "----------------------------"
10400 	    "----------------"
10401 	    "----------------------------\n");
10402 }
10403 
10404 
10405 /****************************************************************************/
10406 /* Prints out the TPAT processor state.                                     */
10407 /*                                                                          */
10408 /* Returns:                                                                 */
10409 /*   Nothing.                                                               */
10410 /****************************************************************************/
10411 static __attribute__ ((noinline)) void
10412 bce_dump_tpat_state(struct bce_softc *sc, int regs)
10413 {
10414 	u32 val;
10415 	u32 fw_version[3];
10416 
10417 	BCE_PRINTF(
10418 	    "----------------------------"
10419 	    "   TPAT State   "
10420 	    "----------------------------\n");
10421 
10422 	for (int i = 0; i < 3; i++)
10423 		fw_version[i] = htonl(REG_RD_IND(sc,
10424 		    (BCE_TPAT_SCRATCH + 0x410 + i * 4)));
10425 
10426 	BCE_PRINTF("Firmware version - %s\n", (char *) fw_version);
10427 
10428 	val = REG_RD_IND(sc, BCE_TPAT_CPU_MODE);
10429 	BCE_PRINTF("0x%08X - (0x%06X) tpat_cpu_mode\n",
10430 	    val, BCE_TPAT_CPU_MODE);
10431 
10432 	val = REG_RD_IND(sc, BCE_TPAT_CPU_STATE);
10433 	BCE_PRINTF("0x%08X - (0x%06X) tpat_cpu_state\n",
10434 	    val, BCE_TPAT_CPU_STATE);
10435 
10436 	val = REG_RD_IND(sc, BCE_TPAT_CPU_EVENT_MASK);
10437 	BCE_PRINTF("0x%08X - (0x%06X) tpat_cpu_event_mask\n",
10438 	    val, BCE_TPAT_CPU_EVENT_MASK);
10439 
10440 	if (regs) {
10441 		BCE_PRINTF(
10442 		    "----------------------------"
10443 		    " Register  Dump "
10444 		    "----------------------------\n");
10445 
10446 		for (int i = BCE_TPAT_CPU_MODE; i < 0xa3fff; i += 0x10) {
10447 			/* Skip the big blank spaces */
10448 			if (i < 0x854000 && i > 0x9ffff)
10449 				BCE_PRINTF("0x%04X: 0x%08X 0x%08X "
10450 				    "0x%08X 0x%08X\n", i,
10451 				    REG_RD_IND(sc, i),
10452 				    REG_RD_IND(sc, i + 0x4),
10453 				    REG_RD_IND(sc, i + 0x8),
10454 				    REG_RD_IND(sc, i + 0xC));
10455 		}
10456 	}
10457 
10458 	BCE_PRINTF(
10459 		"----------------------------"
10460 		"----------------"
10461 		"----------------------------\n");
10462 }
10463 
10464 
10465 /****************************************************************************/
10466 /* Prints out the Command Procesor (CP) state.                              */
10467 /*                                                                          */
10468 /* Returns:                                                                 */
10469 /*   Nothing.                                                               */
10470 /****************************************************************************/
10471 static __attribute__ ((noinline)) void
10472 bce_dump_cp_state(struct bce_softc *sc, int regs)
10473 {
10474 	u32 val;
10475 	u32 fw_version[3];
10476 
10477 	BCE_PRINTF(
10478 	    "----------------------------"
10479 	    "    CP State    "
10480 	    "----------------------------\n");
10481 
10482 	for (int i = 0; i < 3; i++)
10483 		fw_version[i] = htonl(REG_RD_IND(sc,
10484 		    (BCE_CP_SCRATCH + 0x10 + i * 4)));
10485 
10486 	BCE_PRINTF("Firmware version - %s\n", (char *) fw_version);
10487 
10488 	val = REG_RD_IND(sc, BCE_CP_CPU_MODE);
10489 	BCE_PRINTF("0x%08X - (0x%06X) cp_cpu_mode\n",
10490 	    val, BCE_CP_CPU_MODE);
10491 
10492 	val = REG_RD_IND(sc, BCE_CP_CPU_STATE);
10493 	BCE_PRINTF("0x%08X - (0x%06X) cp_cpu_state\n",
10494 	    val, BCE_CP_CPU_STATE);
10495 
10496 	val = REG_RD_IND(sc, BCE_CP_CPU_EVENT_MASK);
10497 	BCE_PRINTF("0x%08X - (0x%06X) cp_cpu_event_mask\n", val,
10498 	    BCE_CP_CPU_EVENT_MASK);
10499 
10500 	if (regs) {
10501 		BCE_PRINTF(
10502 		    "----------------------------"
10503 		    " Register  Dump "
10504 		    "----------------------------\n");
10505 
10506 		for (int i = BCE_CP_CPU_MODE; i < 0x1aa000; i += 0x10) {
10507 			/* Skip the big blank spaces */
10508 			if (i < 0x185400 && i > 0x19ffff)
10509 				BCE_PRINTF("0x%04X: 0x%08X 0x%08X "
10510 				    "0x%08X 0x%08X\n", i,
10511 				    REG_RD_IND(sc, i),
10512 				    REG_RD_IND(sc, i + 0x4),
10513 				    REG_RD_IND(sc, i + 0x8),
10514 				    REG_RD_IND(sc, i + 0xC));
10515 		}
10516 	}
10517 
10518 	BCE_PRINTF(
10519 	    "----------------------------"
10520 	    "----------------"
10521 	    "----------------------------\n");
10522 }
10523 
10524 
10525 /****************************************************************************/
10526 /* Prints out the Completion Procesor (COM) state.                          */
10527 /*                                                                          */
10528 /* Returns:                                                                 */
10529 /*   Nothing.                                                               */
10530 /****************************************************************************/
10531 static __attribute__ ((noinline)) void
10532 bce_dump_com_state(struct bce_softc *sc, int regs)
10533 {
10534 	u32 val;
10535 	u32 fw_version[4];
10536 
10537 	BCE_PRINTF(
10538 	    "----------------------------"
10539 	    "   COM State    "
10540 	    "----------------------------\n");
10541 
10542 	for (int i = 0; i < 3; i++)
10543 		fw_version[i] = htonl(REG_RD_IND(sc,
10544 		    (BCE_COM_SCRATCH + 0x10 + i * 4)));
10545 
10546 	BCE_PRINTF("Firmware version - %s\n", (char *) fw_version);
10547 
10548 	val = REG_RD_IND(sc, BCE_COM_CPU_MODE);
10549 	BCE_PRINTF("0x%08X - (0x%06X) com_cpu_mode\n",
10550 	    val, BCE_COM_CPU_MODE);
10551 
10552 	val = REG_RD_IND(sc, BCE_COM_CPU_STATE);
10553 	BCE_PRINTF("0x%08X - (0x%06X) com_cpu_state\n",
10554 	    val, BCE_COM_CPU_STATE);
10555 
10556 	val = REG_RD_IND(sc, BCE_COM_CPU_EVENT_MASK);
10557 	BCE_PRINTF("0x%08X - (0x%06X) com_cpu_event_mask\n", val,
10558 	    BCE_COM_CPU_EVENT_MASK);
10559 
10560 	if (regs) {
10561 		BCE_PRINTF(
10562 		    "----------------------------"
10563 		    " Register  Dump "
10564 		    "----------------------------\n");
10565 
10566 		for (int i = BCE_COM_CPU_MODE; i < 0x1053e8; i += 0x10) {
10567 			BCE_PRINTF("0x%04X: 0x%08X 0x%08X "
10568 			    "0x%08X 0x%08X\n", i,
10569 			    REG_RD_IND(sc, i),
10570 			    REG_RD_IND(sc, i + 0x4),
10571 			    REG_RD_IND(sc, i + 0x8),
10572 			    REG_RD_IND(sc, i + 0xC));
10573 		}
10574 	}
10575 
10576 	BCE_PRINTF(
10577 		"----------------------------"
10578 		"----------------"
10579 		"----------------------------\n");
10580 }
10581 
10582 
10583 /****************************************************************************/
10584 /* Prints out the Receive Virtual 2 Physical (RV2P) state.                  */
10585 /*                                                                          */
10586 /* Returns:                                                                 */
10587 /*   Nothing.                                                               */
10588 /****************************************************************************/
10589 static __attribute__ ((noinline)) void
10590 bce_dump_rv2p_state(struct bce_softc *sc)
10591 {
10592 	u32 val, pc1, pc2, fw_ver_high, fw_ver_low;
10593 
10594 	BCE_PRINTF(
10595 	    "----------------------------"
10596 	    "   RV2P State   "
10597 	    "----------------------------\n");
10598 
10599 	/* Stall the RV2P processors. */
10600 	val = REG_RD_IND(sc, BCE_RV2P_CONFIG);
10601 	val |= BCE_RV2P_CONFIG_STALL_PROC1 | BCE_RV2P_CONFIG_STALL_PROC2;
10602 	REG_WR_IND(sc, BCE_RV2P_CONFIG, val);
10603 
10604 	/* Read the firmware version. */
10605 	val = 0x00000001;
10606 	REG_WR_IND(sc, BCE_RV2P_PROC1_ADDR_CMD, val);
10607 	fw_ver_low = REG_RD_IND(sc, BCE_RV2P_INSTR_LOW);
10608 	fw_ver_high = REG_RD_IND(sc, BCE_RV2P_INSTR_HIGH) &
10609 	    BCE_RV2P_INSTR_HIGH_HIGH;
10610 	BCE_PRINTF("RV2P1 Firmware version - 0x%08X:0x%08X\n",
10611 	    fw_ver_high, fw_ver_low);
10612 
10613 	val = 0x00000001;
10614 	REG_WR_IND(sc, BCE_RV2P_PROC2_ADDR_CMD, val);
10615 	fw_ver_low = REG_RD_IND(sc, BCE_RV2P_INSTR_LOW);
10616 	fw_ver_high = REG_RD_IND(sc, BCE_RV2P_INSTR_HIGH) &
10617 	    BCE_RV2P_INSTR_HIGH_HIGH;
10618 	BCE_PRINTF("RV2P2 Firmware version - 0x%08X:0x%08X\n",
10619 	    fw_ver_high, fw_ver_low);
10620 
10621 	/* Resume the RV2P processors. */
10622 	val = REG_RD_IND(sc, BCE_RV2P_CONFIG);
10623 	val &= ~(BCE_RV2P_CONFIG_STALL_PROC1 | BCE_RV2P_CONFIG_STALL_PROC2);
10624 	REG_WR_IND(sc, BCE_RV2P_CONFIG, val);
10625 
10626 	/* Fetch the program counter value. */
10627 	val = 0x68007800;
10628 	REG_WR_IND(sc, BCE_RV2P_DEBUG_VECT_PEEK, val);
10629 	val = REG_RD_IND(sc, BCE_RV2P_DEBUG_VECT_PEEK);
10630 	pc1 = (val & BCE_RV2P_DEBUG_VECT_PEEK_1_VALUE);
10631 	pc2 = (val & BCE_RV2P_DEBUG_VECT_PEEK_2_VALUE) >> 16;
10632 	BCE_PRINTF("0x%08X - RV2P1 program counter (1st read)\n", pc1);
10633 	BCE_PRINTF("0x%08X - RV2P2 program counter (1st read)\n", pc2);
10634 
10635 	/* Fetch the program counter value again to see if it is advancing. */
10636 	val = 0x68007800;
10637 	REG_WR_IND(sc, BCE_RV2P_DEBUG_VECT_PEEK, val);
10638 	val = REG_RD_IND(sc, BCE_RV2P_DEBUG_VECT_PEEK);
10639 	pc1 = (val & BCE_RV2P_DEBUG_VECT_PEEK_1_VALUE);
10640 	pc2 = (val & BCE_RV2P_DEBUG_VECT_PEEK_2_VALUE) >> 16;
10641 	BCE_PRINTF("0x%08X - RV2P1 program counter (2nd read)\n", pc1);
10642 	BCE_PRINTF("0x%08X - RV2P2 program counter (2nd read)\n", pc2);
10643 
10644 	BCE_PRINTF(
10645 	    "----------------------------"
10646 	    "----------------"
10647 	    "----------------------------\n");
10648 }
10649 
10650 
10651 /****************************************************************************/
10652 /* Prints out the driver state and then enters the debugger.                */
10653 /*                                                                          */
10654 /* Returns:                                                                 */
10655 /*   Nothing.                                                               */
10656 /****************************************************************************/
10657 static __attribute__ ((noinline)) void
10658 bce_breakpoint(struct bce_softc *sc)
10659 {
10660 
10661 	/*
10662 	 * Unreachable code to silence compiler warnings
10663 	 * about unused functions.
10664 	 */
10665 	if (0) {
10666 		bce_freeze_controller(sc);
10667 		bce_unfreeze_controller(sc);
10668 		bce_dump_enet(sc, NULL);
10669 		bce_dump_txbd(sc, 0, NULL);
10670 		bce_dump_rxbd(sc, 0, NULL);
10671 		bce_dump_tx_mbuf_chain(sc, 0, USABLE_TX_BD);
10672 		bce_dump_rx_mbuf_chain(sc, 0, USABLE_RX_BD);
10673 		bce_dump_l2fhdr(sc, 0, NULL);
10674 		bce_dump_ctx(sc, RX_CID);
10675 		bce_dump_ftqs(sc);
10676 		bce_dump_tx_chain(sc, 0, USABLE_TX_BD);
10677 		bce_dump_rx_bd_chain(sc, 0, USABLE_RX_BD);
10678 		bce_dump_status_block(sc);
10679 		bce_dump_stats_block(sc);
10680 		bce_dump_driver_state(sc);
10681 		bce_dump_hw_state(sc);
10682 		bce_dump_bc_state(sc);
10683 		bce_dump_txp_state(sc, 0);
10684 		bce_dump_rxp_state(sc, 0);
10685 		bce_dump_tpat_state(sc, 0);
10686 		bce_dump_cp_state(sc, 0);
10687 		bce_dump_com_state(sc, 0);
10688 		bce_dump_rv2p_state(sc);
10689 
10690 #ifdef BCE_JUMBO_HDRSPLIT
10691 		bce_dump_pgbd(sc, 0, NULL);
10692 		bce_dump_pg_mbuf_chain(sc, 0, USABLE_PG_BD);
10693 		bce_dump_pg_chain(sc, 0, USABLE_PG_BD);
10694 #endif
10695 	}
10696 
10697 	bce_dump_status_block(sc);
10698 	bce_dump_driver_state(sc);
10699 
10700 	/* Call the debugger. */
10701 	breakpoint();
10702 
10703 	return;
10704 }
10705 #endif
10706 
10707