1/*-
2 * SPDX-License-Identifier: BSD-3-Clause
3 *
4 * Copyright (C) 2013 Emulex
5 * All rights reserved.
6 *
7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following conditions are met:
9 *
10 * 1. Redistributions of source code must retain the above copyright notice,
11 *    this list of conditions and the following disclaimer.
12 *
13 * 2. Redistributions in binary form must reproduce the above copyright
14 *    notice, this list of conditions and the following disclaimer in the
15 *    documentation and/or other materials provided with the distribution.
16 *
17 * 3. Neither the name of the Emulex Corporation nor the names of its
18 *    contributors may be used to endorse or promote products derived from
19 *    this software without specific prior written permission.
20 *
21 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
22 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
23 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
24 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
25 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
26 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
27 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
28 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
29 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
30 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
31 * POSSIBILITY OF SUCH DAMAGE.
32 *
33 * Contact Information:
34 * freebsd-drivers@emulex.com
35 *
36 * Emulex
37 * 3333 Susan Street
38 * Costa Mesa, CA 92626
39 */
40
41/* $FreeBSD$ */
42
43#include "oce_if.h"
44
45static void copy_stats_to_sc_xe201(POCE_SOFTC sc);
46static void copy_stats_to_sc_be3(POCE_SOFTC sc);
47static void copy_stats_to_sc_be2(POCE_SOFTC sc);
48static void copy_stats_to_sc_sh(POCE_SOFTC sc);
49static int  oce_sysctl_loopback(SYSCTL_HANDLER_ARGS);
50static int  oce_sys_aic_enable(SYSCTL_HANDLER_ARGS);
51static int  oce_be3_fwupgrade(POCE_SOFTC sc, const struct firmware *fw);
52static int oce_skyhawk_fwupgrade(POCE_SOFTC sc, const struct firmware *fw);
53static int  oce_sys_fwupgrade(SYSCTL_HANDLER_ARGS);
54static int  oce_lancer_fwupgrade(POCE_SOFTC sc, const struct firmware *fw);
55static int oce_sysctl_sfp_vpd_dump(SYSCTL_HANDLER_ARGS);
56static boolean_t oce_phy_flashing_required(POCE_SOFTC sc);
57static boolean_t oce_img_flashing_required(POCE_SOFTC sc, const char *p,
58				int img_optype, uint32_t img_offset,
59				uint32_t img_size, uint32_t hdrs_size);
60static void oce_add_stats_sysctls_be3(POCE_SOFTC sc,
61				struct sysctl_ctx_list *ctx,
62				struct sysctl_oid *stats_node);
63static void oce_add_stats_sysctls_xe201(POCE_SOFTC sc,
64				struct sysctl_ctx_list *ctx,
65				struct sysctl_oid *stats_node);
66
67extern char component_revision[32];
68uint8_t sfp_vpd_dump_buffer[TRANSCEIVER_DATA_SIZE];
69
70struct flash_img_attri {
71	int img_offset;
72	int img_size;
73	int img_type;
74	bool skip_image;
75	int optype;
76};
77
78void
79oce_add_sysctls(POCE_SOFTC sc)
80{
81
82	struct sysctl_ctx_list *ctx = device_get_sysctl_ctx(sc->dev);
83	struct sysctl_oid *tree = device_get_sysctl_tree(sc->dev);
84	struct sysctl_oid_list *child = SYSCTL_CHILDREN(tree);
85	struct sysctl_oid *stats_node;
86
87	SYSCTL_ADD_STRING(ctx, child,
88			OID_AUTO, "component_revision",
89			CTLFLAG_RD,
90			component_revision,
91			sizeof(component_revision),
92			"EMULEX One-Connect device driver revision");
93
94	SYSCTL_ADD_STRING(ctx, child,
95			OID_AUTO, "firmware_version",
96			CTLFLAG_RD,
97			sc->fw_version,
98			sizeof(sc->fw_version),
99			"EMULEX One-Connect Firmware Version");
100
101	SYSCTL_ADD_INT(ctx, child,
102			OID_AUTO, "max_rsp_handled",
103			CTLFLAG_RW,
104			&oce_max_rsp_handled,
105			sizeof(oce_max_rsp_handled),
106			"Maximum receive frames handled per interupt");
107
108	if ((sc->function_mode & FNM_FLEX10_MODE) ||
109	    (sc->function_mode & FNM_UMC_MODE))
110		SYSCTL_ADD_UINT(ctx, child,
111				OID_AUTO, "speed",
112				CTLFLAG_RD,
113				&sc->qos_link_speed,
114				0,"QOS Speed");
115	else
116		SYSCTL_ADD_UINT(ctx, child,
117				OID_AUTO, "speed",
118				CTLFLAG_RD,
119				&sc->speed,
120				0,"Link Speed");
121
122	if (sc->function_mode & FNM_UMC_MODE)
123		SYSCTL_ADD_UINT(ctx, child,
124				OID_AUTO, "pvid",
125				CTLFLAG_RD,
126				&sc->pvid,
127				0,"PVID");
128
129	SYSCTL_ADD_PROC(ctx, child, OID_AUTO, "loop_back",
130	    CTLTYPE_INT | CTLFLAG_RW | CTLFLAG_NEEDGIANT, (void *)sc, 0,
131	    oce_sysctl_loopback, "I", "Loop Back Tests");
132
133	SYSCTL_ADD_PROC(ctx, child, OID_AUTO, "fw_upgrade",
134	    CTLTYPE_STRING | CTLFLAG_RW | CTLFLAG_NEEDGIANT, (void *)sc, 0,
135	    oce_sys_fwupgrade, "A", "Firmware ufi file");
136
137	SYSCTL_ADD_PROC(ctx, child, OID_AUTO, "aic_enable",
138	    CTLTYPE_INT | CTLFLAG_RW | CTLFLAG_NEEDGIANT, (void *)sc, 1,
139	    oce_sys_aic_enable, "I", "aic flags");
140
141        /*
142         *  Dumps Transceiver data
143	 *  "sysctl dev.oce.0.sfp_vpd_dump=0"
144         *  "sysctl -x dev.oce.0.sfp_vpd_dump_buffer" for hex dump
145         *  "sysctl -b dev.oce.0.sfp_vpd_dump_buffer > sfp.bin" for binary dump
146         */
147	SYSCTL_ADD_PROC(ctx, child, OID_AUTO, "sfp_vpd_dump",
148	    CTLTYPE_INT | CTLFLAG_RW | CTLFLAG_NEEDGIANT, (void *)sc, 0,
149	    oce_sysctl_sfp_vpd_dump, "I", "Initiate a sfp_vpd_dump operation");
150	SYSCTL_ADD_OPAQUE(ctx, child, OID_AUTO, "sfp_vpd_dump_buffer",
151			CTLFLAG_RD, sfp_vpd_dump_buffer,
152			TRANSCEIVER_DATA_SIZE, "IU", "Access sfp_vpd_dump buffer");
153
154	stats_node = SYSCTL_ADD_NODE(ctx, child, OID_AUTO, "stats",
155	    CTLFLAG_RD | CTLFLAG_MPSAFE, NULL, "Ethernet Statistics");
156
157	if (IS_BE(sc) || IS_SH(sc))
158		oce_add_stats_sysctls_be3(sc, ctx, stats_node);
159	else
160		oce_add_stats_sysctls_xe201(sc, ctx, stats_node);
161
162}
163
164static uint32_t
165oce_loopback_test(struct oce_softc *sc, uint8_t loopback_type)
166{
167	uint32_t status = 0;
168
169	oce_mbox_cmd_set_loopback(sc, sc->port_id, loopback_type, 1);
170	status = oce_mbox_cmd_test_loopback(sc, sc->port_id, loopback_type,
171				1500, 2, 0xabc);
172	oce_mbox_cmd_set_loopback(sc, sc->port_id, OCE_NO_LOOPBACK, 1);
173
174	return status;
175}
176
177static int
178oce_sys_aic_enable(SYSCTL_HANDLER_ARGS)
179{
180	int value = 0;
181	uint32_t status, vector;
182	POCE_SOFTC sc = (struct oce_softc *)arg1;
183	struct oce_aic_obj *aic;
184
185	/* set current value for proper sysctl logging */
186	value = sc->aic_obj[0].enable;
187	status = sysctl_handle_int(oidp, &value, 0, req);
188	if (status || !req->newptr)
189		return status;
190
191	for (vector = 0; vector < sc->intr_count; vector++) {
192		aic = &sc->aic_obj[vector];
193
194		if (value == 0){
195			aic->max_eqd = aic->min_eqd = aic->et_eqd = 0;
196			aic->enable = 0;
197		}
198		else {
199			aic->max_eqd = OCE_MAX_EQD;
200			aic->min_eqd = OCE_MIN_EQD;
201			aic->et_eqd = OCE_MIN_EQD;
202			aic->enable = TRUE;
203		}
204	}
205	return 0;
206}
207
208static int
209oce_sysctl_loopback(SYSCTL_HANDLER_ARGS)
210{
211	int value = 0;
212	uint32_t status;
213	struct oce_softc *sc  = (struct oce_softc *)arg1;
214
215	status = sysctl_handle_int(oidp, &value, 0, req);
216	if (status || !req->newptr)
217		return status;
218
219	if (value != 1) {
220		device_printf(sc->dev,
221			"Not a Valid value. Set to loop_back=1 to run tests\n");
222		return 0;
223	}
224
225	if ((status = oce_loopback_test(sc, OCE_MAC_LOOPBACK))) {
226		device_printf(sc->dev,
227			"MAC Loopback Test = Failed (Error status = %d)\n",
228			 status);
229	} else
230		device_printf(sc->dev, "MAC Loopback Test = Success\n");
231
232	if ((status = oce_loopback_test(sc, OCE_PHY_LOOPBACK))) {
233		device_printf(sc->dev,
234			"PHY Loopback Test = Failed (Error status = %d)\n",
235			 status);
236	} else
237		device_printf(sc->dev, "PHY Loopback Test = Success\n");
238
239	if ((status = oce_loopback_test(sc, OCE_ONE_PORT_EXT_LOOPBACK))) {
240		device_printf(sc->dev,
241			"EXT Loopback Test = Failed (Error status = %d)\n",
242			 status);
243	} else
244		device_printf(sc->dev, "EXT Loopback Test = Success\n");
245
246	return 0;
247}
248
249static int
250oce_sys_fwupgrade(SYSCTL_HANDLER_ARGS)
251{
252	char ufiname[256] = {0};
253	uint32_t status = 1;
254	struct oce_softc *sc  = (struct oce_softc *)arg1;
255	const struct firmware *fw;
256
257	status = sysctl_handle_string(oidp, ufiname, sizeof(ufiname), req);
258	if (status || !req->newptr)
259		return status;
260
261	fw = firmware_get(ufiname);
262	if (fw == NULL) {
263		device_printf(sc->dev, "Unable to get Firmware. "
264			"Make sure %s is copied to /boot/modules\n", ufiname);
265		return ENOENT;
266	}
267
268	if (IS_BE(sc)) {
269		if ((sc->flags & OCE_FLAGS_BE2)) {
270			device_printf(sc->dev,
271				"Flashing not supported for BE2 yet.\n");
272			status = 1;
273			goto done;
274		}
275		status = oce_be3_fwupgrade(sc, fw);
276	} else if (IS_SH(sc)) {
277		status = oce_skyhawk_fwupgrade(sc,fw);
278	} else
279		status = oce_lancer_fwupgrade(sc, fw);
280done:
281	if (status) {
282		device_printf(sc->dev, "Firmware Upgrade failed\n");
283	} else {
284		device_printf(sc->dev, "Firmware Flashed successfully\n");
285	}
286
287	/* Release Firmware*/
288	firmware_put(fw, FIRMWARE_UNLOAD);
289
290	return status;
291}
292
293static void oce_fill_flash_img_data(POCE_SOFTC sc, const struct flash_sec_info * fsec,
294				struct flash_img_attri *pimg, int i,
295				const struct firmware *fw, int bin_offset)
296{
297	if (IS_SH(sc)) {
298		pimg->img_offset = HOST_32(fsec->fsec_entry[i].offset);
299		pimg->img_size   = HOST_32(fsec->fsec_entry[i].pad_size);
300	}
301
302	pimg->img_type = HOST_32(fsec->fsec_entry[i].type);
303	pimg->skip_image = FALSE;
304	switch (pimg->img_type) {
305		case IMG_ISCSI:
306			pimg->optype = 0;
307			if (IS_BE3(sc)) {
308				pimg->img_offset = 2097152;
309				pimg->img_size   = 2097152;
310			}
311			break;
312		case IMG_REDBOOT:
313			pimg->optype = 1;
314			if (IS_BE3(sc)) {
315				pimg->img_offset = 262144;
316				pimg->img_size   = 1048576;
317			}
318			if (!oce_img_flashing_required(sc, fw->data,
319						pimg->optype,
320						pimg->img_offset,
321						pimg->img_size,
322						bin_offset))
323				pimg->skip_image = TRUE;
324			break;
325		case IMG_BIOS:
326			pimg->optype = 2;
327			if (IS_BE3(sc)) {
328				pimg->img_offset = 12582912;
329				pimg->img_size   = 524288;
330			}
331			break;
332		case IMG_PXEBIOS:
333			pimg->optype = 3;
334			if (IS_BE3(sc)) {
335				pimg->img_offset =  13107200;
336				pimg->img_size   = 524288;
337			}
338			break;
339		case IMG_FCOEBIOS:
340			pimg->optype = 8;
341			if (IS_BE3(sc)) {
342				pimg->img_offset = 13631488;
343				pimg->img_size   = 524288;
344			}
345			break;
346		case IMG_ISCSI_BAK:
347			pimg->optype = 9;
348			if (IS_BE3(sc)) {
349				pimg->img_offset = 4194304;
350				pimg->img_size   = 2097152;
351			}
352			break;
353		case IMG_FCOE:
354			pimg->optype = 10;
355			if (IS_BE3(sc)) {
356				pimg->img_offset = 6291456;
357				pimg->img_size   = 2097152;
358			}
359			break;
360		case IMG_FCOE_BAK:
361			pimg->optype = 11;
362			if (IS_BE3(sc)) {
363				pimg->img_offset = 8388608;
364				pimg->img_size   = 2097152;
365			}
366			break;
367		case IMG_NCSI:
368			pimg->optype = 13;
369			if (IS_BE3(sc)) {
370				pimg->img_offset = 15990784;
371				pimg->img_size   = 262144;
372			}
373			break;
374		case IMG_PHY:
375			pimg->optype = 99;
376			if (IS_BE3(sc)) {
377				pimg->img_offset = 1310720;
378				pimg->img_size   = 262144;
379			}
380			if (!oce_phy_flashing_required(sc))
381				pimg->skip_image = TRUE;
382			break;
383		default:
384			pimg->skip_image = TRUE;
385			break;
386	}
387
388}
389
390static int
391oce_sh_be3_flashdata(POCE_SOFTC sc, const struct firmware *fw, int32_t num_imgs)
392{
393	char cookie[2][16] =    {"*** SE FLAS", "H DIRECTORY *** "};
394	const char *p = (const char *)fw->data;
395	const struct flash_sec_info *fsec = NULL;
396	struct mbx_common_read_write_flashrom *req;
397	int rc = 0, i, bin_offset = 0, opcode, num_bytes;
398	OCE_DMA_MEM dma_mem;
399	struct flash_img_attri imgatt;
400
401	/* Validate Cookie */
402	bin_offset = (sizeof(struct flash_file_hdr) +
403			(num_imgs * sizeof(struct image_hdr)));
404	p += bin_offset;
405	while (p < ((const char *)fw->data + fw->datasize)) {
406		fsec = (const struct flash_sec_info *)p;
407		if (!memcmp(cookie, fsec->cookie, sizeof(cookie)))
408			break;
409		fsec = NULL;
410		p += 32;
411	}
412
413	if (!fsec) {
414		device_printf(sc->dev,
415				"Invalid Cookie. Firmware image corrupted ?\n");
416		return EINVAL;
417	}
418
419	rc = oce_dma_alloc(sc, sizeof(struct mbx_common_read_write_flashrom),
420				&dma_mem, 0);
421	if (rc) {
422		device_printf(sc->dev,
423				"Memory allocation failure while flashing\n");
424		return ENOMEM;
425	}
426	req = OCE_DMAPTR(&dma_mem, struct mbx_common_read_write_flashrom);
427
428	if (IS_SH(sc))
429		num_imgs = HOST_32(fsec->fsec_hdr.num_images);
430	else if (IS_BE3(sc))
431		num_imgs = MAX_FLASH_COMP;
432
433	for (i = 0; i < num_imgs; i++) {
434		bzero(&imgatt, sizeof(struct flash_img_attri));
435
436		oce_fill_flash_img_data(sc, fsec, &imgatt, i, fw, bin_offset);
437
438		if (imgatt.skip_image)
439			continue;
440
441		p = fw->data;
442		p = p + bin_offset + imgatt.img_offset;
443
444		if ((p + imgatt.img_size) > ((const char *)fw->data + fw->datasize)) {
445			rc = 1;
446			goto ret;
447		}
448
449		while (imgatt.img_size) {
450			if (imgatt.img_size > 32*1024)
451				num_bytes = 32*1024;
452			else
453				num_bytes = imgatt.img_size;
454			imgatt.img_size -= num_bytes;
455
456			if (!imgatt.img_size)
457				opcode = FLASHROM_OPER_FLASH;
458			else
459				opcode = FLASHROM_OPER_SAVE;
460
461			memcpy(req->data_buffer, p, num_bytes);
462			p += num_bytes;
463
464			rc = oce_mbox_write_flashrom(sc, imgatt.optype, opcode,
465					&dma_mem, num_bytes);
466			if (rc) {
467				device_printf(sc->dev,
468						"cmd to write to flash rom failed.\n");
469				rc = EIO;
470				goto ret;
471			}
472			/* Leave the CPU for others for some time */
473			pause("yield", 10);
474		}
475	}
476
477ret:
478	oce_dma_free(sc, &dma_mem);
479	return rc;
480}
481
482#define UFI_TYPE2               2
483#define UFI_TYPE3               3
484#define UFI_TYPE3R              10
485#define UFI_TYPE4               4
486#define UFI_TYPE4R              11
487static int oce_get_ufi_type(POCE_SOFTC sc,
488                           const struct flash_file_hdr *fhdr)
489{
490        if (fhdr == NULL)
491                goto be_get_ufi_exit;
492
493        if (IS_SH(sc) && fhdr->build[0] == '4') {
494                if (fhdr->asic_type_rev >= 0x10)
495                        return UFI_TYPE4R;
496                else
497                        return UFI_TYPE4;
498        } else if (IS_BE3(sc) && fhdr->build[0] == '3') {
499                if (fhdr->asic_type_rev == 0x10)
500                        return UFI_TYPE3R;
501                else
502                        return UFI_TYPE3;
503        } else if (IS_BE2(sc) && fhdr->build[0] == '2')
504                return UFI_TYPE2;
505
506be_get_ufi_exit:
507        device_printf(sc->dev,
508                "UFI and Interface are not compatible for flashing\n");
509        return -1;
510}
511
512static int
513oce_skyhawk_fwupgrade(POCE_SOFTC sc, const struct firmware *fw)
514{
515	int rc = 0, num_imgs = 0, i = 0, ufi_type;
516	const struct flash_file_hdr *fhdr;
517	const struct image_hdr *img_ptr;
518
519	fhdr = (const struct flash_file_hdr *)fw->data;
520
521	ufi_type = oce_get_ufi_type(sc, fhdr);
522
523	/* Display flash version */
524	device_printf(sc->dev, "Flashing Firmware %s\n", &fhdr->build[2]);
525
526	num_imgs = fhdr->num_imgs;
527	for (i = 0; i < num_imgs; i++) {
528		img_ptr = (const struct image_hdr *)((const char *)fw->data +
529				sizeof(struct flash_file_hdr) +
530				(i * sizeof(struct image_hdr)));
531
532		if (img_ptr->imageid != 1)
533			continue;
534
535		switch (ufi_type) {
536			case UFI_TYPE4R:
537				rc = oce_sh_be3_flashdata(sc, fw,
538						num_imgs);
539				break;
540			case UFI_TYPE4:
541				if (sc->asic_revision < 0x10)
542					rc = oce_sh_be3_flashdata(sc, fw,
543								   num_imgs);
544				else {
545					rc = -1;
546					device_printf(sc->dev,
547						"Cant load SH A0 UFI on B0\n");
548				}
549				break;
550			default:
551				rc = -1;
552				break;
553		}
554	}
555
556	return rc;
557}
558
559static int
560oce_be3_fwupgrade(POCE_SOFTC sc, const struct firmware *fw)
561{
562	int rc = 0, num_imgs = 0, i = 0;
563	const struct flash_file_hdr *fhdr;
564	const struct image_hdr *img_ptr;
565
566	fhdr = (const struct flash_file_hdr *)fw->data;
567	if (fhdr->build[0] != '3') {
568		device_printf(sc->dev, "Invalid BE3 firmware image\n");
569		return EINVAL;
570	}
571	/* Display flash version */
572	device_printf(sc->dev, "Flashing Firmware %s\n", &fhdr->build[2]);
573
574	num_imgs = fhdr->num_imgs;
575	for (i = 0; i < num_imgs; i++) {
576		img_ptr = (const struct image_hdr *)((const char *)fw->data +
577				sizeof(struct flash_file_hdr) +
578				(i * sizeof(struct image_hdr)));
579		if (img_ptr->imageid == 1) {
580			rc = oce_sh_be3_flashdata(sc, fw, num_imgs);
581
582			break;
583		}
584	}
585
586	return rc;
587}
588
589static boolean_t
590oce_phy_flashing_required(POCE_SOFTC sc)
591{
592	int status = 0;
593	struct oce_phy_info phy_info;
594
595	status = oce_mbox_get_phy_info(sc, &phy_info);
596	if (status)
597		return FALSE;
598
599	if ((phy_info.phy_type == TN_8022) &&
600		(phy_info.interface_type == PHY_TYPE_BASET_10GB)) {
601		return TRUE;
602	}
603
604	return FALSE;
605}
606
607static boolean_t
608oce_img_flashing_required(POCE_SOFTC sc, const char *p,
609				int img_optype, uint32_t img_offset,
610				uint32_t img_size, uint32_t hdrs_size)
611{
612	uint32_t crc_offset;
613	uint8_t flashed_crc[4];
614	int status;
615
616	crc_offset = hdrs_size + img_offset + img_size - 4;
617
618	p += crc_offset;
619
620	status = oce_mbox_get_flashrom_crc(sc, flashed_crc,
621			(img_size - 4), img_optype);
622	if (status)
623		return TRUE; /* Some thing worng. ReFlash */
624
625	/*update redboot only if crc does not match*/
626	if (bcmp(flashed_crc, p, 4))
627		return TRUE;
628	else
629		return FALSE;
630}
631
632static int
633oce_lancer_fwupgrade(POCE_SOFTC sc, const struct firmware *fw)
634{
635
636	int rc = 0;
637	OCE_DMA_MEM dma_mem;
638	const uint8_t *data = NULL;
639	uint8_t *dest_image_ptr = NULL;
640	size_t size = 0;
641	uint32_t data_written = 0, chunk_size = 0;
642	uint32_t offset = 0, add_status = 0;
643
644	if (!IS_ALIGNED(fw->datasize, sizeof(uint32_t))) {
645		device_printf(sc->dev,
646			"Lancer FW image is not 4 byte aligned.");
647		return EINVAL;
648	}
649
650	rc = oce_dma_alloc(sc, 32*1024, &dma_mem, 0);
651	if (rc) {
652		device_printf(sc->dev,
653			"Memory allocation failure while flashing Lancer\n");
654		return ENOMEM;
655	}
656
657	size = fw->datasize;
658	data = fw->data;
659	dest_image_ptr = OCE_DMAPTR(&dma_mem, uint8_t);
660
661	while (size) {
662		chunk_size = MIN(size, (32*1024));
663
664		bcopy(data, dest_image_ptr, chunk_size);
665
666		rc = oce_mbox_lancer_write_flashrom(sc, chunk_size, offset,
667				&dma_mem, &data_written, &add_status);
668
669		if (rc)
670			break;
671
672		size	-= data_written;
673		data	+= data_written;
674		offset	+= data_written;
675		pause("yield", 10);
676	}
677
678	if (!rc)
679		/* Commit the firmware*/
680		rc = oce_mbox_lancer_write_flashrom(sc, 0, offset, &dma_mem,
681						&data_written, &add_status);
682	if (rc) {
683		device_printf(sc->dev, "Lancer firmware load error. "
684			"Addstatus = 0x%x, status = %d \n", add_status, rc);
685		rc = EIO;
686	}
687	oce_dma_free(sc, &dma_mem);
688	return rc;
689
690}
691
692static void
693oce_add_stats_sysctls_be3(POCE_SOFTC sc,
694				  struct sysctl_ctx_list *ctx,
695				  struct sysctl_oid *stats_node)
696{
697	struct sysctl_oid *rx_stats_node, *tx_stats_node;
698	struct sysctl_oid_list *rx_stat_list, *tx_stat_list;
699	struct sysctl_oid_list *queue_stats_list;
700	struct sysctl_oid *queue_stats_node;
701	struct oce_drv_stats *stats;
702	char prefix[32];
703	int i;
704
705	stats = &sc->oce_stats_info;
706
707	rx_stats_node = SYSCTL_ADD_NODE(ctx,
708	    SYSCTL_CHILDREN(stats_node), OID_AUTO,"rx",
709	    CTLFLAG_RD | CTLFLAG_MPSAFE, NULL, "RX Ethernet Statistics");
710	rx_stat_list = SYSCTL_CHILDREN(rx_stats_node);
711
712	SYSCTL_ADD_QUAD(ctx, rx_stat_list, OID_AUTO, "total_pkts",
713			CTLFLAG_RD, &stats->rx.t_rx_pkts,
714			"Total Received Packets");
715	SYSCTL_ADD_QUAD(ctx, rx_stat_list, OID_AUTO, "total_bytes",
716			CTLFLAG_RD, &stats->rx.t_rx_bytes,
717			"Total Received Bytes");
718	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "total_frags",
719			CTLFLAG_RD, &stats->rx.t_rx_frags, 0,
720			"Total Received Fragements");
721	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "total_mcast_pkts",
722			CTLFLAG_RD, &stats->rx.t_rx_mcast_pkts, 0,
723			"Total Received Multicast Packets");
724	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "total_ucast_pkts",
725			CTLFLAG_RD, &stats->rx.t_rx_ucast_pkts, 0,
726			"Total Received Unicast Packets");
727	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "total_rxcp_errs",
728			CTLFLAG_RD, &stats->rx.t_rxcp_errs, 0,
729			"Total Receive completion errors");
730	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "pause_frames",
731			CTLFLAG_RD, &stats->u0.be.rx_pause_frames, 0,
732			"Pause Frames");
733	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "priority_pause_frames",
734			CTLFLAG_RD, &stats->u0.be.rx_priority_pause_frames, 0,
735			"Priority Pause Frames");
736	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "control_frames",
737			CTLFLAG_RD, &stats->u0.be.rx_control_frames, 0,
738			"Control Frames");
739
740	for (i = 0; i < sc->nrqs; i++) {
741		sprintf(prefix, "queue%d",i);
742		queue_stats_node = SYSCTL_ADD_NODE(ctx,
743		    SYSCTL_CHILDREN(rx_stats_node), OID_AUTO, prefix,
744		    CTLFLAG_RD | CTLFLAG_MPSAFE, NULL, "Queue name");
745		queue_stats_list = SYSCTL_CHILDREN(queue_stats_node);
746
747		SYSCTL_ADD_QUAD(ctx, queue_stats_list, OID_AUTO, "rx_pkts",
748			CTLFLAG_RD, &sc->rq[i]->rx_stats.rx_pkts,
749			"Receive Packets");
750		SYSCTL_ADD_QUAD(ctx, queue_stats_list, OID_AUTO, "rx_bytes",
751			CTLFLAG_RD, &sc->rq[i]->rx_stats.rx_bytes,
752			"Recived Bytes");
753		SYSCTL_ADD_UINT(ctx, queue_stats_list, OID_AUTO, "rx_frags",
754			CTLFLAG_RD, &sc->rq[i]->rx_stats.rx_frags, 0,
755			"Received Fragments");
756		SYSCTL_ADD_UINT(ctx, queue_stats_list, OID_AUTO,
757				"rx_mcast_pkts", CTLFLAG_RD,
758				&sc->rq[i]->rx_stats.rx_mcast_pkts, 0,
759					"Received Multicast Packets");
760		SYSCTL_ADD_UINT(ctx, queue_stats_list, OID_AUTO,
761				"rx_ucast_pkts", CTLFLAG_RD,
762				&sc->rq[i]->rx_stats.rx_ucast_pkts, 0,
763					"Received Unicast Packets");
764		SYSCTL_ADD_UINT(ctx, queue_stats_list, OID_AUTO, "rxcp_err",
765			CTLFLAG_RD, &sc->rq[i]->rx_stats.rxcp_err, 0,
766			"Received Completion Errors");
767		if(IS_SH(sc)) {
768			SYSCTL_ADD_UINT(ctx, queue_stats_list, OID_AUTO, "rx_drops_no_frags",
769                        	CTLFLAG_RD, &sc->rq[i]->rx_stats.rx_drops_no_frags, 0,
770                        	"num of packet drops due to no fragments");
771		}
772	}
773
774	rx_stats_node = SYSCTL_ADD_NODE(ctx,
775	    SYSCTL_CHILDREN(rx_stats_node), OID_AUTO, "err",
776	        CTLFLAG_RD | CTLFLAG_MPSAFE, NULL, "Receive Error Stats");
777	rx_stat_list = SYSCTL_CHILDREN(rx_stats_node);
778
779	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "crc_errs",
780			CTLFLAG_RD, &stats->u0.be.rx_crc_errors, 0,
781			"CRC Errors");
782	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "pbuf_errors",
783			CTLFLAG_RD, &stats->u0.be.rx_drops_no_pbuf, 0,
784			"Drops due to pbuf full");
785	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "erx_errors",
786			CTLFLAG_RD, &stats->u0.be.rx_drops_no_erx_descr, 0,
787			"ERX Errors");
788	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "alignment_errors",
789			CTLFLAG_RD, &stats->u0.be.rx_drops_too_many_frags, 0,
790			"RX Alignmnet Errors");
791	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "in_range_errors",
792			CTLFLAG_RD, &stats->u0.be.rx_in_range_errors, 0,
793			"In Range Errors");
794	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "out_range_errors",
795			CTLFLAG_RD, &stats->u0.be.rx_out_range_errors, 0,
796			"Out Range Errors");
797	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "frame_too_long",
798			CTLFLAG_RD, &stats->u0.be.rx_frame_too_long, 0,
799			"Frame Too Long");
800	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "address_match_errors",
801			CTLFLAG_RD, &stats->u0.be.rx_address_match_errors, 0,
802			"Address Match Errors");
803	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "dropped_too_small",
804			CTLFLAG_RD, &stats->u0.be.rx_dropped_too_small, 0,
805			"Dropped Too Small");
806	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "dropped_too_short",
807			CTLFLAG_RD, &stats->u0.be.rx_dropped_too_short, 0,
808			"Dropped Too Short");
809	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO,
810			"dropped_header_too_small", CTLFLAG_RD,
811			&stats->u0.be.rx_dropped_header_too_small, 0,
812			"Dropped Header Too Small");
813	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "dropped_tcp_length",
814			CTLFLAG_RD, &stats->u0.be.rx_dropped_tcp_length, 0,
815			"Dropped TCP Length");
816	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "dropped_runt",
817			CTLFLAG_RD, &stats->u0.be.rx_dropped_runt, 0,
818			"Dropped runt");
819	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "ip_checksum_errs",
820			CTLFLAG_RD, &stats->u0.be.rx_ip_checksum_errs, 0,
821			"IP Checksum Errors");
822	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "tcp_checksum_errs",
823			CTLFLAG_RD, &stats->u0.be.rx_tcp_checksum_errs, 0,
824			"TCP Checksum Errors");
825	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "udp_checksum_errs",
826			CTLFLAG_RD, &stats->u0.be.rx_udp_checksum_errs, 0,
827			"UDP Checksum Errors");
828	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "fifo_overflow_drop",
829			CTLFLAG_RD, &stats->u0.be.rxpp_fifo_overflow_drop, 0,
830			"FIFO Overflow Drop");
831	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO,
832			"input_fifo_overflow_drop", CTLFLAG_RD,
833			&stats->u0.be.rx_input_fifo_overflow_drop, 0,
834			"Input FIFO Overflow Drop");
835
836	tx_stats_node = SYSCTL_ADD_NODE(ctx,
837	    SYSCTL_CHILDREN(stats_node), OID_AUTO,
838	        "tx", CTLFLAG_RD | CTLFLAG_MPSAFE, NULL,
839		"TX Ethernet Statistics");
840	tx_stat_list = SYSCTL_CHILDREN(tx_stats_node);
841
842	SYSCTL_ADD_QUAD(ctx, tx_stat_list, OID_AUTO, "total_tx_pkts",
843			CTLFLAG_RD, &stats->tx.t_tx_pkts,
844			"Total Transmit Packets");
845	SYSCTL_ADD_QUAD(ctx, tx_stat_list, OID_AUTO, "total_tx_bytes",
846			CTLFLAG_RD, &stats->tx.t_tx_bytes,
847			"Total Transmit Bytes");
848	SYSCTL_ADD_UINT(ctx, tx_stat_list, OID_AUTO, "total_tx_reqs",
849			CTLFLAG_RD, &stats->tx.t_tx_reqs, 0,
850			"Total Transmit Requests");
851	SYSCTL_ADD_UINT(ctx, tx_stat_list, OID_AUTO, "total_tx_stops",
852			CTLFLAG_RD, &stats->tx.t_tx_stops, 0,
853			"Total Transmit Stops");
854	SYSCTL_ADD_UINT(ctx, tx_stat_list, OID_AUTO, "total_tx_wrbs",
855			CTLFLAG_RD, &stats->tx.t_tx_wrbs, 0,
856			"Total Transmit WRB's");
857	SYSCTL_ADD_UINT(ctx, tx_stat_list, OID_AUTO, "total_tx_compl",
858			CTLFLAG_RD, &stats->tx.t_tx_compl, 0,
859			"Total Transmit Completions");
860	SYSCTL_ADD_UINT(ctx, tx_stat_list, OID_AUTO,
861			"total_ipv6_ext_hdr_tx_drop", CTLFLAG_RD,
862			&stats->tx.t_ipv6_ext_hdr_tx_drop, 0,
863			"Total Transmit IPV6 Drops");
864	SYSCTL_ADD_UINT(ctx, tx_stat_list, OID_AUTO, "pauseframes",
865			CTLFLAG_RD, &stats->u0.be.tx_pauseframes, 0,
866			"Pause Frames");
867	SYSCTL_ADD_UINT(ctx, tx_stat_list, OID_AUTO, "priority_pauseframes",
868			CTLFLAG_RD, &stats->u0.be.tx_priority_pauseframes, 0,
869			"Priority Pauseframes");
870	SYSCTL_ADD_UINT(ctx, tx_stat_list, OID_AUTO, "controlframes",
871			CTLFLAG_RD, &stats->u0.be.tx_controlframes, 0,
872			"Tx Control Frames");
873
874	for (i = 0; i < sc->nwqs; i++) {
875		sprintf(prefix, "queue%d",i);
876		queue_stats_node = SYSCTL_ADD_NODE(ctx,
877		    SYSCTL_CHILDREN(tx_stats_node), OID_AUTO, prefix,
878		        CTLFLAG_RD | CTLFLAG_MPSAFE, NULL, "Queue name");
879		queue_stats_list = SYSCTL_CHILDREN(queue_stats_node);
880
881		SYSCTL_ADD_QUAD(ctx, queue_stats_list, OID_AUTO, "tx_pkts",
882			CTLFLAG_RD, &sc->wq[i]->tx_stats.tx_pkts,
883			"Transmit Packets");
884		SYSCTL_ADD_QUAD(ctx, queue_stats_list, OID_AUTO, "tx_bytes",
885			CTLFLAG_RD, &sc->wq[i]->tx_stats.tx_bytes,
886			"Transmit Bytes");
887		SYSCTL_ADD_UINT(ctx, queue_stats_list, OID_AUTO, "tx_reqs",
888			CTLFLAG_RD, &sc->wq[i]->tx_stats.tx_reqs, 0,
889			"Transmit Requests");
890		SYSCTL_ADD_UINT(ctx, queue_stats_list, OID_AUTO, "tx_stops",
891			CTLFLAG_RD, &sc->wq[i]->tx_stats.tx_stops, 0,
892			"Transmit Stops");
893		SYSCTL_ADD_UINT(ctx, queue_stats_list, OID_AUTO, "tx_wrbs",
894			CTLFLAG_RD, &sc->wq[i]->tx_stats.tx_wrbs, 0,
895			"Transmit WRB's");
896		SYSCTL_ADD_UINT(ctx, queue_stats_list, OID_AUTO, "tx_compl",
897			CTLFLAG_RD, &sc->wq[i]->tx_stats.tx_compl, 0,
898			"Transmit Completions");
899		SYSCTL_ADD_UINT(ctx, queue_stats_list, OID_AUTO,
900			"ipv6_ext_hdr_tx_drop",CTLFLAG_RD,
901			&sc->wq[i]->tx_stats.ipv6_ext_hdr_tx_drop, 0,
902			"Transmit IPV6 Ext Header Drop");
903	}
904	return;
905}
906
907static void
908oce_add_stats_sysctls_xe201(POCE_SOFTC sc,
909				  struct sysctl_ctx_list *ctx,
910				  struct sysctl_oid *stats_node)
911{
912	struct sysctl_oid *rx_stats_node, *tx_stats_node;
913	struct sysctl_oid_list *rx_stat_list, *tx_stat_list;
914	struct sysctl_oid_list *queue_stats_list;
915	struct sysctl_oid *queue_stats_node;
916	struct oce_drv_stats *stats;
917	char prefix[32];
918	int i;
919
920	stats = &sc->oce_stats_info;
921
922	rx_stats_node = SYSCTL_ADD_NODE(ctx,
923	    SYSCTL_CHILDREN(stats_node), OID_AUTO, "rx",
924	    CTLFLAG_RD | CTLFLAG_MPSAFE, NULL,
925	    "RX Ethernet Statistics");
926	rx_stat_list = SYSCTL_CHILDREN(rx_stats_node);
927
928	SYSCTL_ADD_QUAD(ctx, rx_stat_list, OID_AUTO, "total_pkts",
929			CTLFLAG_RD, &stats->rx.t_rx_pkts,
930			"Total Received Packets");
931	SYSCTL_ADD_QUAD(ctx, rx_stat_list, OID_AUTO, "total_bytes",
932			CTLFLAG_RD, &stats->rx.t_rx_bytes,
933			"Total Received Bytes");
934	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "total_frags",
935			CTLFLAG_RD, &stats->rx.t_rx_frags, 0,
936			"Total Received Fragements");
937	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "total_mcast_pkts",
938			CTLFLAG_RD, &stats->rx.t_rx_mcast_pkts, 0,
939			"Total Received Multicast Packets");
940	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "total_ucast_pkts",
941			CTLFLAG_RD, &stats->rx.t_rx_ucast_pkts, 0,
942			"Total Received Unicast Packets");
943	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "total_rxcp_errs",
944			CTLFLAG_RD, &stats->rx.t_rxcp_errs, 0,
945			"Total Receive completion errors");
946	SYSCTL_ADD_UQUAD(ctx, rx_stat_list, OID_AUTO, "pause_frames",
947			CTLFLAG_RD, &stats->u0.xe201.rx_pause_frames,
948			"Pause Frames");
949	SYSCTL_ADD_UQUAD(ctx, rx_stat_list, OID_AUTO, "control_frames",
950			CTLFLAG_RD, &stats->u0.xe201.rx_control_frames,
951			"Control Frames");
952
953	for (i = 0; i < sc->nrqs; i++) {
954		sprintf(prefix, "queue%d",i);
955		queue_stats_node = SYSCTL_ADD_NODE(ctx,
956		    SYSCTL_CHILDREN(rx_stats_node), OID_AUTO, prefix,
957		    CTLFLAG_RD | CTLFLAG_MPSAFE, NULL, "Queue name");
958		queue_stats_list = SYSCTL_CHILDREN(queue_stats_node);
959
960		SYSCTL_ADD_QUAD(ctx, queue_stats_list, OID_AUTO, "rx_pkts",
961			CTLFLAG_RD, &sc->rq[i]->rx_stats.rx_pkts,
962			"Receive Packets");
963		SYSCTL_ADD_QUAD(ctx, queue_stats_list, OID_AUTO, "rx_bytes",
964			CTLFLAG_RD, &sc->rq[i]->rx_stats.rx_bytes,
965			"Recived Bytes");
966		SYSCTL_ADD_UINT(ctx, queue_stats_list, OID_AUTO, "rx_frags",
967			CTLFLAG_RD, &sc->rq[i]->rx_stats.rx_frags, 0,
968			"Received Fragments");
969		SYSCTL_ADD_UINT(ctx, queue_stats_list, OID_AUTO,
970			"rx_mcast_pkts", CTLFLAG_RD,
971			&sc->rq[i]->rx_stats.rx_mcast_pkts, 0,
972			"Received Multicast Packets");
973		SYSCTL_ADD_UINT(ctx, queue_stats_list, OID_AUTO,
974			"rx_ucast_pkts",CTLFLAG_RD,
975			&sc->rq[i]->rx_stats.rx_ucast_pkts, 0,
976			"Received Unicast Packets");
977		SYSCTL_ADD_UINT(ctx, queue_stats_list, OID_AUTO, "rxcp_err",
978			CTLFLAG_RD, &sc->rq[i]->rx_stats.rxcp_err, 0,
979			"Received Completion Errors");
980
981	}
982
983	rx_stats_node = SYSCTL_ADD_NODE(ctx,
984	    SYSCTL_CHILDREN(rx_stats_node), OID_AUTO, "err",
985	        CTLFLAG_RD | CTLFLAG_MPSAFE, NULL, "Receive Error Stats");
986	rx_stat_list = SYSCTL_CHILDREN(rx_stats_node);
987
988	SYSCTL_ADD_UQUAD(ctx, rx_stat_list, OID_AUTO, "crc_errs",
989			CTLFLAG_RD, &stats->u0.xe201.rx_crc_errors,
990			"CRC Errors");
991	SYSCTL_ADD_UQUAD(ctx, rx_stat_list, OID_AUTO, "alignment_errors",
992			CTLFLAG_RD, &stats->u0.xe201.rx_alignment_errors,
993			"RX Alignmnet Errors");
994	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "in_range_errors",
995			CTLFLAG_RD, &stats->u0.xe201.rx_in_range_errors, 0,
996			"In Range Errors");
997	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "out_range_errors",
998			CTLFLAG_RD, &stats->u0.xe201.rx_out_of_range_errors, 0,
999			"Out Range Errors");
1000	SYSCTL_ADD_UQUAD(ctx, rx_stat_list, OID_AUTO, "frame_too_long",
1001			CTLFLAG_RD, &stats->u0.xe201.rx_frames_too_long,
1002			"Frame Too Long");
1003	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "address_match_errors",
1004			CTLFLAG_RD, &stats->u0.xe201.rx_address_match_errors, 0,
1005			"Address Match Errors");
1006	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "dropped_too_small",
1007			CTLFLAG_RD, &stats->u0.xe201.rx_dropped_too_small, 0,
1008			"Dropped Too Small");
1009	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "dropped_too_short",
1010			CTLFLAG_RD, &stats->u0.xe201.rx_dropped_too_short, 0,
1011			"Dropped Too Short");
1012	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO,
1013			"dropped_header_too_small", CTLFLAG_RD,
1014			&stats->u0.xe201.rx_dropped_header_too_small, 0,
1015			"Dropped Header Too Small");
1016	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO,
1017			"dropped_tcp_length", CTLFLAG_RD,
1018			&stats->u0.xe201.rx_dropped_invalid_tcp_length, 0,
1019			"Dropped TCP Length");
1020	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "dropped_runt",
1021			CTLFLAG_RD, &stats->u0.xe201.rx_dropped_runt, 0,
1022			"Dropped runt");
1023	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "ip_checksum_errs",
1024			CTLFLAG_RD, &stats->u0.xe201.rx_ip_checksum_errors, 0,
1025			"IP Checksum Errors");
1026	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "tcp_checksum_errs",
1027			CTLFLAG_RD, &stats->u0.xe201.rx_tcp_checksum_errors, 0,
1028			"TCP Checksum Errors");
1029	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "udp_checksum_errs",
1030			CTLFLAG_RD, &stats->u0.xe201.rx_udp_checksum_errors, 0,
1031			"UDP Checksum Errors");
1032	SYSCTL_ADD_UINT(ctx, rx_stat_list, OID_AUTO, "input_fifo_overflow_drop",
1033			CTLFLAG_RD, &stats->u0.xe201.rx_fifo_overflow, 0,
1034			"Input FIFO Overflow Drop");
1035
1036	tx_stats_node = SYSCTL_ADD_NODE(ctx,
1037	    SYSCTL_CHILDREN(stats_node), OID_AUTO, "tx",
1038	        CTLFLAG_RD | CTLFLAG_MPSAFE, NULL, "TX Ethernet Statistics");
1039	tx_stat_list = SYSCTL_CHILDREN(tx_stats_node);
1040
1041	SYSCTL_ADD_QUAD(ctx, tx_stat_list, OID_AUTO, "total_tx_pkts",
1042			CTLFLAG_RD, &stats->tx.t_tx_pkts,
1043			"Total Transmit Packets");
1044	SYSCTL_ADD_QUAD(ctx, tx_stat_list, OID_AUTO, "total_tx_bytes",
1045			CTLFLAG_RD, &stats->tx.t_tx_bytes,
1046			"Total Transmit Bytes");
1047	SYSCTL_ADD_UINT(ctx, tx_stat_list, OID_AUTO, "total_tx_reqs",
1048			CTLFLAG_RD, &stats->tx.t_tx_reqs, 0,
1049			"Total Transmit Requests");
1050	SYSCTL_ADD_UINT(ctx, tx_stat_list, OID_AUTO, "total_tx_stops",
1051			CTLFLAG_RD, &stats->tx.t_tx_stops, 0,
1052			"Total Transmit Stops");
1053	SYSCTL_ADD_UINT(ctx, tx_stat_list, OID_AUTO, "total_tx_wrbs",
1054			CTLFLAG_RD, &stats->tx.t_tx_wrbs, 0,
1055			"Total Transmit WRB's");
1056	SYSCTL_ADD_UINT(ctx, tx_stat_list, OID_AUTO, "total_tx_compl",
1057			CTLFLAG_RD, &stats->tx.t_tx_compl, 0,
1058			"Total Transmit Completions");
1059	SYSCTL_ADD_UINT(ctx, tx_stat_list, OID_AUTO,
1060			"total_ipv6_ext_hdr_tx_drop",
1061			CTLFLAG_RD, &stats->tx.t_ipv6_ext_hdr_tx_drop, 0,
1062			"Total Transmit IPV6 Drops");
1063	SYSCTL_ADD_UQUAD(ctx, tx_stat_list, OID_AUTO, "pauseframes",
1064			CTLFLAG_RD, &stats->u0.xe201.tx_pause_frames,
1065			"Pause Frames");
1066	SYSCTL_ADD_UQUAD(ctx, tx_stat_list, OID_AUTO, "controlframes",
1067			CTLFLAG_RD, &stats->u0.xe201.tx_control_frames,
1068			"Tx Control Frames");
1069
1070	for (i = 0; i < sc->nwqs; i++) {
1071		sprintf(prefix, "queue%d",i);
1072		queue_stats_node = SYSCTL_ADD_NODE(ctx,
1073		    SYSCTL_CHILDREN(tx_stats_node), OID_AUTO, prefix,
1074		        CTLFLAG_RD | CTLFLAG_MPSAFE, NULL, "Queue name");
1075		queue_stats_list = SYSCTL_CHILDREN(queue_stats_node);
1076
1077		SYSCTL_ADD_QUAD(ctx, queue_stats_list, OID_AUTO, "tx_pkts",
1078			CTLFLAG_RD, &sc->wq[i]->tx_stats.tx_pkts,
1079			"Transmit Packets");
1080		SYSCTL_ADD_QUAD(ctx, queue_stats_list, OID_AUTO, "tx_bytes",
1081			CTLFLAG_RD, &sc->wq[i]->tx_stats.tx_bytes,
1082			"Transmit Bytes");
1083		SYSCTL_ADD_UINT(ctx, queue_stats_list, OID_AUTO, "tx_reqs",
1084			CTLFLAG_RD, &sc->wq[i]->tx_stats.tx_reqs, 0,
1085			"Transmit Requests");
1086		SYSCTL_ADD_UINT(ctx, queue_stats_list, OID_AUTO, "tx_stops",
1087			CTLFLAG_RD, &sc->wq[i]->tx_stats.tx_stops, 0,
1088			"Transmit Stops");
1089		SYSCTL_ADD_UINT(ctx, queue_stats_list, OID_AUTO, "tx_wrbs",
1090			CTLFLAG_RD, &sc->wq[i]->tx_stats.tx_wrbs, 0,
1091			"Transmit WRB's");
1092		SYSCTL_ADD_UINT(ctx, queue_stats_list, OID_AUTO, "tx_compl",
1093			CTLFLAG_RD, &sc->wq[i]->tx_stats.tx_compl, 0,
1094			"Transmit Completions");
1095		SYSCTL_ADD_UINT(ctx, queue_stats_list, OID_AUTO,
1096			"ipv6_ext_hdr_tx_drop", CTLFLAG_RD,
1097			&sc->wq[i]->tx_stats.ipv6_ext_hdr_tx_drop, 0,
1098			"Transmit IPV6 Ext Header Drop");
1099	}
1100	return;
1101}
1102
1103void
1104oce_refresh_queue_stats(POCE_SOFTC sc)
1105{
1106	struct oce_drv_stats *adapter_stats;
1107	int i;
1108
1109	adapter_stats = &sc->oce_stats_info;
1110
1111	/* Caluculate total TX and TXstats from all queues */
1112
1113	bzero(&adapter_stats->rx, sizeof(struct oce_rx_stats));
1114	for (i = 0; i < sc->nrqs; i++) {
1115
1116		adapter_stats->rx.t_rx_pkts += sc->rq[i]->rx_stats.rx_pkts;
1117		adapter_stats->rx.t_rx_bytes += sc->rq[i]->rx_stats.rx_bytes;
1118		adapter_stats->rx.t_rx_frags += sc->rq[i]->rx_stats.rx_frags;
1119		adapter_stats->rx.t_rx_mcast_pkts +=
1120					sc->rq[i]->rx_stats.rx_mcast_pkts;
1121		adapter_stats->rx.t_rx_ucast_pkts +=
1122					sc->rq[i]->rx_stats.rx_ucast_pkts;
1123		adapter_stats->rx.t_rxcp_errs += sc-> rq[i]->rx_stats.rxcp_err;
1124	}
1125
1126	bzero(&adapter_stats->tx, sizeof(struct oce_tx_stats));
1127	for (i = 0; i < sc->nwqs; i++) {
1128		adapter_stats->tx.t_tx_reqs += sc->wq[i]->tx_stats.tx_reqs;
1129		adapter_stats->tx.t_tx_stops += sc->wq[i]->tx_stats.tx_stops;
1130		adapter_stats->tx.t_tx_wrbs += sc->wq[i]->tx_stats.tx_wrbs;
1131		adapter_stats->tx.t_tx_compl += sc->wq[i]->tx_stats.tx_compl;
1132		adapter_stats->tx.t_tx_bytes += sc->wq[i]->tx_stats.tx_bytes;
1133		adapter_stats->tx.t_tx_pkts += sc->wq[i]->tx_stats.tx_pkts;
1134		adapter_stats->tx.t_ipv6_ext_hdr_tx_drop +=
1135				sc->wq[i]->tx_stats.ipv6_ext_hdr_tx_drop;
1136	}
1137
1138}
1139
1140static void
1141copy_stats_to_sc_xe201(POCE_SOFTC sc)
1142{
1143	struct oce_xe201_stats *adapter_stats;
1144	struct mbx_get_pport_stats *nic_mbx;
1145	struct pport_stats *port_stats;
1146
1147	nic_mbx = OCE_DMAPTR(&sc->stats_mem, struct mbx_get_pport_stats);
1148	port_stats = &nic_mbx->params.rsp.pps;
1149	adapter_stats = &sc->oce_stats_info.u0.xe201;
1150
1151	adapter_stats->tx_pkts = port_stats->tx_pkts;
1152	adapter_stats->tx_unicast_pkts = port_stats->tx_unicast_pkts;
1153	adapter_stats->tx_multicast_pkts = port_stats->tx_multicast_pkts;
1154	adapter_stats->tx_broadcast_pkts = port_stats->tx_broadcast_pkts;
1155	adapter_stats->tx_bytes = port_stats->tx_bytes;
1156	adapter_stats->tx_unicast_bytes = port_stats->tx_unicast_bytes;
1157	adapter_stats->tx_multicast_bytes = port_stats->tx_multicast_bytes;
1158	adapter_stats->tx_broadcast_bytes = port_stats->tx_broadcast_bytes;
1159	adapter_stats->tx_discards = port_stats->tx_discards;
1160	adapter_stats->tx_errors = port_stats->tx_errors;
1161	adapter_stats->tx_pause_frames = port_stats->tx_pause_frames;
1162	adapter_stats->tx_pause_on_frames = port_stats->tx_pause_on_frames;
1163	adapter_stats->tx_pause_off_frames = port_stats->tx_pause_off_frames;
1164	adapter_stats->tx_internal_mac_errors =
1165		port_stats->tx_internal_mac_errors;
1166	adapter_stats->tx_control_frames = port_stats->tx_control_frames;
1167	adapter_stats->tx_pkts_64_bytes = port_stats->tx_pkts_64_bytes;
1168	adapter_stats->tx_pkts_65_to_127_bytes =
1169		port_stats->tx_pkts_65_to_127_bytes;
1170	adapter_stats->tx_pkts_128_to_255_bytes =
1171		port_stats->tx_pkts_128_to_255_bytes;
1172	adapter_stats->tx_pkts_256_to_511_bytes =
1173		port_stats->tx_pkts_256_to_511_bytes;
1174	adapter_stats->tx_pkts_512_to_1023_bytes =
1175		port_stats->tx_pkts_512_to_1023_bytes;
1176	adapter_stats->tx_pkts_1024_to_1518_bytes =
1177		port_stats->tx_pkts_1024_to_1518_bytes;
1178	adapter_stats->tx_pkts_1519_to_2047_bytes =
1179		port_stats->tx_pkts_1519_to_2047_bytes;
1180	adapter_stats->tx_pkts_2048_to_4095_bytes =
1181		port_stats->tx_pkts_2048_to_4095_bytes;
1182	adapter_stats->tx_pkts_4096_to_8191_bytes =
1183		port_stats->tx_pkts_4096_to_8191_bytes;
1184	adapter_stats->tx_pkts_8192_to_9216_bytes =
1185		port_stats->tx_pkts_8192_to_9216_bytes;
1186	adapter_stats->tx_lso_pkts = port_stats->tx_lso_pkts;
1187	adapter_stats->rx_pkts = port_stats->rx_pkts;
1188	adapter_stats->rx_unicast_pkts = port_stats->rx_unicast_pkts;
1189	adapter_stats->rx_multicast_pkts = port_stats->rx_multicast_pkts;
1190	adapter_stats->rx_broadcast_pkts = port_stats->rx_broadcast_pkts;
1191	adapter_stats->rx_bytes = port_stats->rx_bytes;
1192	adapter_stats->rx_unicast_bytes = port_stats->rx_unicast_bytes;
1193	adapter_stats->rx_multicast_bytes = port_stats->rx_multicast_bytes;
1194	adapter_stats->rx_broadcast_bytes = port_stats->rx_broadcast_bytes;
1195	adapter_stats->rx_unknown_protos = port_stats->rx_unknown_protos;
1196	adapter_stats->rx_discards = port_stats->rx_discards;
1197	adapter_stats->rx_errors = port_stats->rx_errors;
1198	adapter_stats->rx_crc_errors = port_stats->rx_crc_errors;
1199	adapter_stats->rx_alignment_errors = port_stats->rx_alignment_errors;
1200	adapter_stats->rx_symbol_errors = port_stats->rx_symbol_errors;
1201	adapter_stats->rx_pause_frames = port_stats->rx_pause_frames;
1202	adapter_stats->rx_pause_on_frames = port_stats->rx_pause_on_frames;
1203	adapter_stats->rx_pause_off_frames = port_stats->rx_pause_off_frames;
1204	adapter_stats->rx_frames_too_long = port_stats->rx_frames_too_long;
1205	adapter_stats->rx_internal_mac_errors =
1206		port_stats->rx_internal_mac_errors;
1207	adapter_stats->rx_undersize_pkts = port_stats->rx_undersize_pkts;
1208	adapter_stats->rx_oversize_pkts = port_stats->rx_oversize_pkts;
1209	adapter_stats->rx_fragment_pkts = port_stats->rx_fragment_pkts;
1210	adapter_stats->rx_jabbers = port_stats->rx_jabbers;
1211	adapter_stats->rx_control_frames = port_stats->rx_control_frames;
1212	adapter_stats->rx_control_frames_unknown_opcode =
1213		port_stats->rx_control_frames_unknown_opcode;
1214	adapter_stats->rx_in_range_errors = port_stats->rx_in_range_errors;
1215	adapter_stats->rx_out_of_range_errors =
1216		port_stats->rx_out_of_range_errors;
1217	adapter_stats->rx_address_match_errors =
1218		port_stats->rx_address_match_errors;
1219	adapter_stats->rx_vlan_mismatch_errors =
1220		port_stats->rx_vlan_mismatch_errors;
1221	adapter_stats->rx_dropped_too_small = port_stats->rx_dropped_too_small;
1222	adapter_stats->rx_dropped_too_short = port_stats->rx_dropped_too_short;
1223	adapter_stats->rx_dropped_header_too_small =
1224		port_stats->rx_dropped_header_too_small;
1225	adapter_stats->rx_dropped_invalid_tcp_length =
1226		port_stats->rx_dropped_invalid_tcp_length;
1227	adapter_stats->rx_dropped_runt = port_stats->rx_dropped_runt;
1228	adapter_stats->rx_ip_checksum_errors =
1229		port_stats->rx_ip_checksum_errors;
1230	adapter_stats->rx_tcp_checksum_errors =
1231		port_stats->rx_tcp_checksum_errors;
1232	adapter_stats->rx_udp_checksum_errors =
1233		port_stats->rx_udp_checksum_errors;
1234	adapter_stats->rx_non_rss_pkts = port_stats->rx_non_rss_pkts;
1235	adapter_stats->rx_ipv4_pkts = port_stats->rx_ipv4_pkts;
1236	adapter_stats->rx_ipv6_pkts = port_stats->rx_ipv6_pkts;
1237	adapter_stats->rx_ipv4_bytes = port_stats->rx_ipv4_bytes;
1238	adapter_stats->rx_ipv6_bytes = port_stats->rx_ipv6_bytes;
1239	adapter_stats->rx_nic_pkts = port_stats->rx_nic_pkts;
1240	adapter_stats->rx_tcp_pkts = port_stats->rx_tcp_pkts;
1241	adapter_stats->rx_iscsi_pkts = port_stats->rx_iscsi_pkts;
1242	adapter_stats->rx_management_pkts = port_stats->rx_management_pkts;
1243	adapter_stats->rx_switched_unicast_pkts =
1244		port_stats->rx_switched_unicast_pkts;
1245	adapter_stats->rx_switched_multicast_pkts =
1246		port_stats->rx_switched_multicast_pkts;
1247	adapter_stats->rx_switched_broadcast_pkts =
1248		port_stats->rx_switched_broadcast_pkts;
1249	adapter_stats->num_forwards = port_stats->num_forwards;
1250	adapter_stats->rx_fifo_overflow = port_stats->rx_fifo_overflow;
1251	adapter_stats->rx_input_fifo_overflow =
1252		port_stats->rx_input_fifo_overflow;
1253	adapter_stats->rx_drops_too_many_frags =
1254		port_stats->rx_drops_too_many_frags;
1255	adapter_stats->rx_drops_invalid_queue =
1256		port_stats->rx_drops_invalid_queue;
1257	adapter_stats->rx_drops_mtu = port_stats->rx_drops_mtu;
1258	adapter_stats->rx_pkts_64_bytes = port_stats->rx_pkts_64_bytes;
1259	adapter_stats->rx_pkts_65_to_127_bytes =
1260		port_stats->rx_pkts_65_to_127_bytes;
1261	adapter_stats->rx_pkts_128_to_255_bytes =
1262		port_stats->rx_pkts_128_to_255_bytes;
1263	adapter_stats->rx_pkts_256_to_511_bytes =
1264		port_stats->rx_pkts_256_to_511_bytes;
1265	adapter_stats->rx_pkts_512_to_1023_bytes =
1266		port_stats->rx_pkts_512_to_1023_bytes;
1267	adapter_stats->rx_pkts_1024_to_1518_bytes =
1268		port_stats->rx_pkts_1024_to_1518_bytes;
1269	adapter_stats->rx_pkts_1519_to_2047_bytes =
1270		port_stats->rx_pkts_1519_to_2047_bytes;
1271	adapter_stats->rx_pkts_2048_to_4095_bytes =
1272		port_stats->rx_pkts_2048_to_4095_bytes;
1273	adapter_stats->rx_pkts_4096_to_8191_bytes =
1274		port_stats->rx_pkts_4096_to_8191_bytes;
1275	adapter_stats->rx_pkts_8192_to_9216_bytes =
1276		port_stats->rx_pkts_8192_to_9216_bytes;
1277}
1278
1279static void
1280copy_stats_to_sc_be2(POCE_SOFTC sc)
1281{
1282	struct oce_be_stats *adapter_stats;
1283	struct oce_pmem_stats *pmem;
1284	struct oce_rxf_stats_v0 *rxf_stats;
1285	struct oce_port_rxf_stats_v0 *port_stats;
1286	struct mbx_get_nic_stats_v0 *nic_mbx;
1287	uint32_t port = sc->port_id;
1288
1289	nic_mbx = OCE_DMAPTR(&sc->stats_mem, struct mbx_get_nic_stats_v0);
1290	pmem = &nic_mbx->params.rsp.stats.pmem;
1291	rxf_stats = &nic_mbx->params.rsp.stats.rxf;
1292	port_stats = &nic_mbx->params.rsp.stats.rxf.port[port];
1293
1294	adapter_stats = &sc->oce_stats_info.u0.be;
1295
1296	/* Update stats */
1297	adapter_stats->rx_pause_frames = port_stats->rx_pause_frames;
1298	adapter_stats->rx_crc_errors = port_stats->rx_crc_errors;
1299	adapter_stats->rx_control_frames = port_stats->rx_control_frames;
1300	adapter_stats->rx_in_range_errors = port_stats->rx_in_range_errors;
1301	adapter_stats->rx_frame_too_long = port_stats->rx_frame_too_long;
1302	adapter_stats->rx_dropped_runt = port_stats->rx_dropped_runt;
1303	adapter_stats->rx_ip_checksum_errs = port_stats->rx_ip_checksum_errs;
1304	adapter_stats->rx_tcp_checksum_errs = port_stats->rx_tcp_checksum_errs;
1305	adapter_stats->rx_udp_checksum_errs = port_stats->rx_udp_checksum_errs;
1306	adapter_stats->rxpp_fifo_overflow_drop =
1307					port_stats->rxpp_fifo_overflow_drop;
1308	adapter_stats->rx_dropped_tcp_length =
1309		port_stats->rx_dropped_tcp_length;
1310	adapter_stats->rx_dropped_too_small = port_stats->rx_dropped_too_small;
1311	adapter_stats->rx_dropped_too_short = port_stats->rx_dropped_too_short;
1312	adapter_stats->rx_out_range_errors = port_stats->rx_out_range_errors;
1313	adapter_stats->rx_dropped_header_too_small =
1314		port_stats->rx_dropped_header_too_small;
1315	adapter_stats->rx_input_fifo_overflow_drop =
1316		port_stats->rx_input_fifo_overflow_drop;
1317	adapter_stats->rx_address_match_errors =
1318		port_stats->rx_address_match_errors;
1319	adapter_stats->rx_alignment_symbol_errors =
1320		port_stats->rx_alignment_symbol_errors;
1321	adapter_stats->tx_pauseframes = port_stats->tx_pauseframes;
1322	adapter_stats->tx_controlframes = port_stats->tx_controlframes;
1323
1324	if (sc->if_id)
1325		adapter_stats->jabber_events = rxf_stats->port1_jabber_events;
1326	else
1327		adapter_stats->jabber_events = rxf_stats->port0_jabber_events;
1328
1329	adapter_stats->rx_drops_no_pbuf = rxf_stats->rx_drops_no_pbuf;
1330	adapter_stats->rx_drops_no_txpb = rxf_stats->rx_drops_no_txpb;
1331	adapter_stats->rx_drops_no_erx_descr = rxf_stats->rx_drops_no_erx_descr;
1332	adapter_stats->rx_drops_invalid_ring = rxf_stats->rx_drops_invalid_ring;
1333	adapter_stats->forwarded_packets = rxf_stats->forwarded_packets;
1334	adapter_stats->rx_drops_mtu = rxf_stats->rx_drops_mtu;
1335	adapter_stats->rx_drops_no_tpre_descr =
1336		rxf_stats->rx_drops_no_tpre_descr;
1337	adapter_stats->rx_drops_too_many_frags =
1338		rxf_stats->rx_drops_too_many_frags;
1339	adapter_stats->eth_red_drops = pmem->eth_red_drops;
1340}
1341
1342static void
1343copy_stats_to_sc_be3(POCE_SOFTC sc)
1344{
1345	struct oce_be_stats *adapter_stats;
1346	struct oce_pmem_stats *pmem;
1347	struct oce_rxf_stats_v1 *rxf_stats;
1348	struct oce_port_rxf_stats_v1 *port_stats;
1349	struct mbx_get_nic_stats_v1 *nic_mbx;
1350	uint32_t port = sc->port_id;
1351
1352	nic_mbx = OCE_DMAPTR(&sc->stats_mem, struct mbx_get_nic_stats_v1);
1353	pmem = &nic_mbx->params.rsp.stats.pmem;
1354	rxf_stats = &nic_mbx->params.rsp.stats.rxf;
1355	port_stats = &nic_mbx->params.rsp.stats.rxf.port[port];
1356
1357	adapter_stats = &sc->oce_stats_info.u0.be;
1358
1359	/* Update stats */
1360	adapter_stats->pmem_fifo_overflow_drop =
1361		port_stats->pmem_fifo_overflow_drop;
1362	adapter_stats->rx_priority_pause_frames =
1363		port_stats->rx_priority_pause_frames;
1364	adapter_stats->rx_pause_frames = port_stats->rx_pause_frames;
1365	adapter_stats->rx_crc_errors = port_stats->rx_crc_errors;
1366	adapter_stats->rx_control_frames = port_stats->rx_control_frames;
1367	adapter_stats->rx_in_range_errors = port_stats->rx_in_range_errors;
1368	adapter_stats->rx_frame_too_long = port_stats->rx_frame_too_long;
1369	adapter_stats->rx_dropped_runt = port_stats->rx_dropped_runt;
1370	adapter_stats->rx_ip_checksum_errs = port_stats->rx_ip_checksum_errs;
1371	adapter_stats->rx_tcp_checksum_errs = port_stats->rx_tcp_checksum_errs;
1372	adapter_stats->rx_udp_checksum_errs = port_stats->rx_udp_checksum_errs;
1373	adapter_stats->rx_dropped_tcp_length =
1374		port_stats->rx_dropped_tcp_length;
1375	adapter_stats->rx_dropped_too_small = port_stats->rx_dropped_too_small;
1376	adapter_stats->rx_dropped_too_short = port_stats->rx_dropped_too_short;
1377	adapter_stats->rx_out_range_errors = port_stats->rx_out_range_errors;
1378	adapter_stats->rx_dropped_header_too_small =
1379		port_stats->rx_dropped_header_too_small;
1380	adapter_stats->rx_input_fifo_overflow_drop =
1381		port_stats->rx_input_fifo_overflow_drop;
1382	adapter_stats->rx_address_match_errors =
1383		port_stats->rx_address_match_errors;
1384	adapter_stats->rx_alignment_symbol_errors =
1385		port_stats->rx_alignment_symbol_errors;
1386	adapter_stats->rxpp_fifo_overflow_drop =
1387		port_stats->rxpp_fifo_overflow_drop;
1388	adapter_stats->tx_pauseframes = port_stats->tx_pauseframes;
1389	adapter_stats->tx_controlframes = port_stats->tx_controlframes;
1390	adapter_stats->jabber_events = port_stats->jabber_events;
1391
1392	adapter_stats->rx_drops_no_pbuf = rxf_stats->rx_drops_no_pbuf;
1393	adapter_stats->rx_drops_no_txpb = rxf_stats->rx_drops_no_txpb;
1394	adapter_stats->rx_drops_no_erx_descr = rxf_stats->rx_drops_no_erx_descr;
1395	adapter_stats->rx_drops_invalid_ring = rxf_stats->rx_drops_invalid_ring;
1396	adapter_stats->forwarded_packets = rxf_stats->forwarded_packets;
1397	adapter_stats->rx_drops_mtu = rxf_stats->rx_drops_mtu;
1398	adapter_stats->rx_drops_no_tpre_descr =
1399		rxf_stats->rx_drops_no_tpre_descr;
1400	adapter_stats->rx_drops_too_many_frags =
1401		rxf_stats->rx_drops_too_many_frags;
1402
1403	adapter_stats->eth_red_drops = pmem->eth_red_drops;
1404}
1405
1406static void
1407copy_stats_to_sc_sh(POCE_SOFTC sc)
1408{
1409        struct oce_be_stats *adapter_stats;
1410        struct oce_pmem_stats *pmem;
1411        struct oce_rxf_stats_v2 *rxf_stats;
1412        struct oce_port_rxf_stats_v2 *port_stats;
1413        struct mbx_get_nic_stats_v2 *nic_mbx;
1414	struct oce_erx_stats_v2 *erx_stats;
1415        uint32_t port = sc->port_id;
1416
1417        nic_mbx = OCE_DMAPTR(&sc->stats_mem, struct mbx_get_nic_stats_v2);
1418        pmem = &nic_mbx->params.rsp.stats.pmem;
1419        rxf_stats = &nic_mbx->params.rsp.stats.rxf;
1420	erx_stats = &nic_mbx->params.rsp.stats.erx;
1421        port_stats = &nic_mbx->params.rsp.stats.rxf.port[port];
1422
1423        adapter_stats = &sc->oce_stats_info.u0.be;
1424
1425        /* Update stats */
1426        adapter_stats->pmem_fifo_overflow_drop =
1427                port_stats->pmem_fifo_overflow_drop;
1428        adapter_stats->rx_priority_pause_frames =
1429                port_stats->rx_priority_pause_frames;
1430        adapter_stats->rx_pause_frames = port_stats->rx_pause_frames;
1431        adapter_stats->rx_crc_errors = port_stats->rx_crc_errors;
1432        adapter_stats->rx_control_frames = port_stats->rx_control_frames;
1433        adapter_stats->rx_in_range_errors = port_stats->rx_in_range_errors;
1434        adapter_stats->rx_frame_too_long = port_stats->rx_frame_too_long;
1435        adapter_stats->rx_dropped_runt = port_stats->rx_dropped_runt;
1436        adapter_stats->rx_ip_checksum_errs = port_stats->rx_ip_checksum_errs;
1437        adapter_stats->rx_tcp_checksum_errs = port_stats->rx_tcp_checksum_errs;
1438        adapter_stats->rx_udp_checksum_errs = port_stats->rx_udp_checksum_errs;
1439        adapter_stats->rx_dropped_tcp_length =
1440                port_stats->rx_dropped_tcp_length;
1441        adapter_stats->rx_dropped_too_small = port_stats->rx_dropped_too_small;
1442        adapter_stats->rx_dropped_too_short = port_stats->rx_dropped_too_short;
1443        adapter_stats->rx_out_range_errors = port_stats->rx_out_range_errors;
1444        adapter_stats->rx_dropped_header_too_small =
1445                port_stats->rx_dropped_header_too_small;
1446        adapter_stats->rx_input_fifo_overflow_drop =
1447                port_stats->rx_input_fifo_overflow_drop;
1448        adapter_stats->rx_address_match_errors =
1449                port_stats->rx_address_match_errors;
1450        adapter_stats->rx_alignment_symbol_errors =
1451                port_stats->rx_alignment_symbol_errors;
1452        adapter_stats->rxpp_fifo_overflow_drop =
1453                port_stats->rxpp_fifo_overflow_drop;
1454        adapter_stats->tx_pauseframes = port_stats->tx_pauseframes;
1455        adapter_stats->tx_controlframes = port_stats->tx_controlframes;
1456        adapter_stats->jabber_events = port_stats->jabber_events;
1457
1458        adapter_stats->rx_drops_no_pbuf = rxf_stats->rx_drops_no_pbuf;
1459        adapter_stats->rx_drops_no_txpb = rxf_stats->rx_drops_no_txpb;
1460        adapter_stats->rx_drops_no_erx_descr = rxf_stats->rx_drops_no_erx_descr;
1461        adapter_stats->rx_drops_invalid_ring = rxf_stats->rx_drops_invalid_ring;
1462        adapter_stats->forwarded_packets = rxf_stats->forwarded_packets;
1463        adapter_stats->rx_drops_mtu = rxf_stats->rx_drops_mtu;
1464        adapter_stats->rx_drops_no_tpre_descr =
1465                rxf_stats->rx_drops_no_tpre_descr;
1466        adapter_stats->rx_drops_too_many_frags =
1467                rxf_stats->rx_drops_too_many_frags;
1468
1469        adapter_stats->eth_red_drops = pmem->eth_red_drops;
1470
1471	/* populate erx stats */
1472	for (int i = 0; i < sc->nrqs; i++)
1473		sc->rq[i]->rx_stats.rx_drops_no_frags = erx_stats->rx_drops_no_fragments[sc->rq[i]->rq_id];
1474}
1475
1476int
1477oce_stats_init(POCE_SOFTC sc)
1478{
1479	int rc = 0, sz = 0;
1480
1481        if( IS_BE2(sc) )
1482		sz = sizeof(struct mbx_get_nic_stats_v0);
1483        else if( IS_BE3(sc) )
1484		sz = sizeof(struct mbx_get_nic_stats_v1);
1485        else if( IS_SH(sc))
1486		sz = sizeof(struct mbx_get_nic_stats_v2);
1487        else if( IS_XE201(sc) )
1488		sz = sizeof(struct mbx_get_pport_stats);
1489
1490	rc = oce_dma_alloc(sc, sz, &sc->stats_mem, 0);
1491
1492	return rc;
1493}
1494
1495void
1496oce_stats_free(POCE_SOFTC sc)
1497{
1498
1499	oce_dma_free(sc, &sc->stats_mem);
1500
1501}
1502
1503int
1504oce_refresh_nic_stats(POCE_SOFTC sc)
1505{
1506	int rc = 0, reset = 0;
1507
1508	if( IS_BE2(sc) ) {
1509		rc = oce_mbox_get_nic_stats_v0(sc, &sc->stats_mem);
1510		if (!rc)
1511			copy_stats_to_sc_be2(sc);
1512	}else if( IS_BE3(sc) ) {
1513		rc = oce_mbox_get_nic_stats_v1(sc, &sc->stats_mem);
1514		if (!rc)
1515			copy_stats_to_sc_be3(sc);
1516	}else if( IS_SH(sc)) {
1517		rc = oce_mbox_get_nic_stats_v2(sc, &sc->stats_mem);
1518		if (!rc)
1519			copy_stats_to_sc_sh(sc);
1520	}else if( IS_XE201(sc) ){
1521		rc = oce_mbox_get_pport_stats(sc, &sc->stats_mem, reset);
1522		if (!rc)
1523			copy_stats_to_sc_xe201(sc);
1524	}
1525
1526	return rc;
1527}
1528
1529static int
1530oce_sysctl_sfp_vpd_dump(SYSCTL_HANDLER_ARGS)
1531{
1532	int result = 0, error;
1533	int rc = 0;
1534	POCE_SOFTC sc = (POCE_SOFTC) arg1;
1535
1536	/* sysctl default handler */
1537	error = sysctl_handle_int(oidp, &result, 0, req);
1538	if (error || !req->newptr)
1539		return (error);
1540
1541	if(result == -1) {
1542		return EINVAL;
1543	}
1544	bzero((char *)sfp_vpd_dump_buffer, TRANSCEIVER_DATA_SIZE);
1545
1546	rc = oce_mbox_read_transrecv_data(sc, PAGE_NUM_A0);
1547	if(rc)
1548		return rc;
1549
1550	rc = oce_mbox_read_transrecv_data(sc, PAGE_NUM_A2);
1551	if(rc)
1552		return rc;
1553
1554	return rc;
1555}
1556