xref: /titanic_51/usr/src/uts/common/io/hxge/hpi_pfc.c (revision 63b1987d5d7387bda49397c0f3f063b49651a5bc)
13dec9fcdSqs148142 /*
23dec9fcdSqs148142  * CDDL HEADER START
33dec9fcdSqs148142  *
43dec9fcdSqs148142  * The contents of this file are subject to the terms of the
53dec9fcdSqs148142  * Common Development and Distribution License (the "License").
63dec9fcdSqs148142  * You may not use this file except in compliance with the License.
73dec9fcdSqs148142  *
83dec9fcdSqs148142  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
93dec9fcdSqs148142  * or http://www.opensolaris.org/os/licensing.
103dec9fcdSqs148142  * See the License for the specific language governing permissions
113dec9fcdSqs148142  * and limitations under the License.
123dec9fcdSqs148142  *
133dec9fcdSqs148142  * When distributing Covered Code, include this CDDL HEADER in each
143dec9fcdSqs148142  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
153dec9fcdSqs148142  * If applicable, add the following below this CDDL HEADER, with the
163dec9fcdSqs148142  * fields enclosed by brackets "[]" replaced with your own identifying
173dec9fcdSqs148142  * information: Portions Copyright [yyyy] [name of copyright owner]
183dec9fcdSqs148142  *
193dec9fcdSqs148142  * CDDL HEADER END
203dec9fcdSqs148142  */
213dec9fcdSqs148142 
223dec9fcdSqs148142 /*
23*63b1987dSQiyan Sun - Sun Microsystems - San Diego United States  * Copyright 2009 Sun Microsystems, Inc.  All rights reserved.
243dec9fcdSqs148142  * Use is subject to license terms.
253dec9fcdSqs148142  */
263dec9fcdSqs148142 
273dec9fcdSqs148142 #include <hxge_impl.h>
283dec9fcdSqs148142 #include <hpi_pfc.h>
293dec9fcdSqs148142 
303dec9fcdSqs148142 #define	TCAM_COMPLETION_TRY_COUNT	10
313dec9fcdSqs148142 #define	HXGE_VLAN_TABLE_ENTRIES		128
323dec9fcdSqs148142 #define	HXGE_PFC_INT_STATUS_CLEAR	0x7ULL
333dec9fcdSqs148142 
343dec9fcdSqs148142 static uint64_t
353dec9fcdSqs148142 hpi_pfc_tcam_check_completion(hpi_handle_t handle, tcam_op_t op_type)
363dec9fcdSqs148142 {
373dec9fcdSqs148142 	uint32_t	try_counter, tcam_delay = 10;
383dec9fcdSqs148142 	pfc_tcam_ctrl_t	tctl;
393dec9fcdSqs148142 
403dec9fcdSqs148142 	try_counter = TCAM_COMPLETION_TRY_COUNT;
413dec9fcdSqs148142 
423dec9fcdSqs148142 	switch (op_type) {
433dec9fcdSqs148142 	case TCAM_RWC_STAT:
443dec9fcdSqs148142 		READ_TCAM_REG_CTL(handle, &tctl.value);
453dec9fcdSqs148142 		while ((try_counter) &&
463dec9fcdSqs148142 		    (tctl.bits.status != TCAM_CTL_RWC_RWC_STAT)) {
473dec9fcdSqs148142 			try_counter--;
483dec9fcdSqs148142 			HXGE_DELAY(tcam_delay);
493dec9fcdSqs148142 			READ_TCAM_REG_CTL(handle, &tctl.value);
503dec9fcdSqs148142 		}
513dec9fcdSqs148142 
523dec9fcdSqs148142 		if (!try_counter) {
533dec9fcdSqs148142 			HPI_ERROR_MSG((handle.function, HPI_ERR_CTL,
543dec9fcdSqs148142 			    " TCAM RWC_STAT operation"
553dec9fcdSqs148142 			    " failed to complete \n"));
563dec9fcdSqs148142 			return (HPI_PFC_TCAM_HW_ERROR);
573dec9fcdSqs148142 		}
583dec9fcdSqs148142 
593dec9fcdSqs148142 		tctl.value = 0;
603dec9fcdSqs148142 		break;
613dec9fcdSqs148142 	case TCAM_RWC_MATCH:
623dec9fcdSqs148142 		READ_TCAM_REG_CTL(handle, &tctl.value);
633dec9fcdSqs148142 
643dec9fcdSqs148142 		while ((try_counter) &&
653dec9fcdSqs148142 		    (tctl.bits.match != TCAM_CTL_RWC_RWC_MATCH)) {
663dec9fcdSqs148142 			try_counter--;
673dec9fcdSqs148142 			HXGE_DELAY(tcam_delay);
683dec9fcdSqs148142 			READ_TCAM_REG_CTL(handle, &tctl.value);
693dec9fcdSqs148142 		}
703dec9fcdSqs148142 
713dec9fcdSqs148142 		if (!try_counter) {
723dec9fcdSqs148142 			HPI_ERROR_MSG((handle.function, HPI_ERR_CTL,
733dec9fcdSqs148142 			    " TCAM Match operationfailed to find match \n"));
743dec9fcdSqs148142 		}
753dec9fcdSqs148142 
763dec9fcdSqs148142 		break;
773dec9fcdSqs148142 	default:
783dec9fcdSqs148142 		HPI_ERROR_MSG((handle.function, HPI_ERR_CTL,
793dec9fcdSqs148142 		    " Invalid TCAM completion Request \n"));
803dec9fcdSqs148142 		return (HPI_PFC_ERROR | HPI_TCAM_ERROR | OPCODE_INVALID);
813dec9fcdSqs148142 	}
823dec9fcdSqs148142 
833dec9fcdSqs148142 	return (tctl.value);
843dec9fcdSqs148142 }
853dec9fcdSqs148142 
863dec9fcdSqs148142 hpi_status_t
873dec9fcdSqs148142 hpi_pfc_tcam_entry_read(hpi_handle_t handle, uint32_t location,
883dec9fcdSqs148142     hxge_tcam_entry_t *tcam_ptr)
893dec9fcdSqs148142 {
903dec9fcdSqs148142 	pfc_tcam_ctrl_t tctl;
913dec9fcdSqs148142 	pfc_tcam_ctrl_t tctl_rv;
923dec9fcdSqs148142 
933dec9fcdSqs148142 	/*
943dec9fcdSqs148142 	 * Hydra doesn't allow to read TCAM entries. Use compare instead.
953dec9fcdSqs148142 	 */
963dec9fcdSqs148142 	WRITE_TCAM_REG_MASK0(handle, tcam_ptr->mask0);
973dec9fcdSqs148142 	WRITE_TCAM_REG_MASK1(handle, tcam_ptr->mask1);
983dec9fcdSqs148142 
993dec9fcdSqs148142 	WRITE_TCAM_REG_KEY0(handle, tcam_ptr->key0);
1003dec9fcdSqs148142 	WRITE_TCAM_REG_KEY1(handle, tcam_ptr->key1);
1013dec9fcdSqs148142 
1023dec9fcdSqs148142 	tctl.value = 0;
1033dec9fcdSqs148142 	tctl.bits.addr = location;
1043dec9fcdSqs148142 	tctl.bits.cmd = TCAM_CTL_RWC_TCAM_CMP;
1053dec9fcdSqs148142 
1063dec9fcdSqs148142 	WRITE_TCAM_REG_CTL(handle, tctl.value);
1073dec9fcdSqs148142 
1083dec9fcdSqs148142 	tctl_rv.value = hpi_pfc_tcam_check_completion(handle, TCAM_RWC_MATCH);
1093dec9fcdSqs148142 
1103dec9fcdSqs148142 	if (tctl_rv.bits.match)
1113dec9fcdSqs148142 		return (HPI_SUCCESS);
1123dec9fcdSqs148142 	else
1133dec9fcdSqs148142 		return (HPI_FAILURE);
1143dec9fcdSqs148142 }
1153dec9fcdSqs148142 
1163dec9fcdSqs148142 hpi_status_t
1173dec9fcdSqs148142 hpi_pfc_tcam_asc_ram_entry_read(hpi_handle_t handle,
1183dec9fcdSqs148142     uint32_t location, uint64_t *ram_data)
1193dec9fcdSqs148142 {
1203dec9fcdSqs148142 	uint64_t tcam_stat;
1213dec9fcdSqs148142 	pfc_tcam_ctrl_t tctl;
1223dec9fcdSqs148142 
1233dec9fcdSqs148142 	tctl.value = 0;
1243dec9fcdSqs148142 	tctl.bits.addr = location;
1253dec9fcdSqs148142 	tctl.bits.cmd = TCAM_CTL_RWC_RAM_RD;
1263dec9fcdSqs148142 
1273dec9fcdSqs148142 	WRITE_TCAM_REG_CTL(handle, tctl.value);
1283dec9fcdSqs148142 
1293dec9fcdSqs148142 	tcam_stat = hpi_pfc_tcam_check_completion(handle, TCAM_RWC_STAT);
1303dec9fcdSqs148142 
1313dec9fcdSqs148142 	if (tcam_stat & HPI_FAILURE) {
1323dec9fcdSqs148142 		HPI_ERROR_MSG((handle.function, HPI_ERR_CTL,
1333dec9fcdSqs148142 		    "TCAM RAM read failed loc %d \n", location));
1343dec9fcdSqs148142 		return (HPI_PFC_ASC_RAM_RD_ERROR);
1353dec9fcdSqs148142 	}
1363dec9fcdSqs148142 
1373dec9fcdSqs148142 	READ_TCAM_REG_KEY0(handle, ram_data);
1383dec9fcdSqs148142 
1393dec9fcdSqs148142 	return (HPI_SUCCESS);
1403dec9fcdSqs148142 }
1413dec9fcdSqs148142 
1423dec9fcdSqs148142 hpi_status_t
1433dec9fcdSqs148142 hpi_pfc_tcam_asc_ram_entry_write(hpi_handle_t handle, uint32_t location,
1443dec9fcdSqs148142     uint64_t ram_data)
1453dec9fcdSqs148142 {
1463dec9fcdSqs148142 	uint64_t	tcam_stat = 0;
1473dec9fcdSqs148142 	pfc_tcam_ctrl_t	tctl;
1483dec9fcdSqs148142 
1493dec9fcdSqs148142 	WRITE_TCAM_REG_KEY0(handle, ram_data);
1503dec9fcdSqs148142 
1513dec9fcdSqs148142 	tctl.value = 0;
1523dec9fcdSqs148142 	tctl.bits.addr = location;
1533dec9fcdSqs148142 	tctl.bits.cmd = TCAM_CTL_RWC_RAM_WR;
1543dec9fcdSqs148142 
1553dec9fcdSqs148142 	HPI_DEBUG_MSG((handle.function, HPI_PFC_CTL,
1563dec9fcdSqs148142 	    " tcam ascr write: location %x data %llx ctl value %llx \n",
1573dec9fcdSqs148142 	    location, ram_data, tctl.value));
1583dec9fcdSqs148142 	WRITE_TCAM_REG_CTL(handle, tctl.value);
1593dec9fcdSqs148142 	tcam_stat = hpi_pfc_tcam_check_completion(handle, TCAM_RWC_STAT);
1603dec9fcdSqs148142 
1613dec9fcdSqs148142 	if (tcam_stat & HPI_FAILURE) {
1623dec9fcdSqs148142 		HPI_ERROR_MSG((handle.function, HPI_ERR_CTL,
1633dec9fcdSqs148142 		    "TCAM RAM write failed loc %d \n", location));
1643dec9fcdSqs148142 		return (HPI_PFC_ASC_RAM_WR_ERROR);
1653dec9fcdSqs148142 	}
1663dec9fcdSqs148142 
1673dec9fcdSqs148142 	return (HPI_SUCCESS);
1683dec9fcdSqs148142 }
1693dec9fcdSqs148142 
1703dec9fcdSqs148142 static hpi_status_t
1713dec9fcdSqs148142 hpi_pfc_set_config(hpi_handle_t handle, pfc_config_t config)
1723dec9fcdSqs148142 {
1733dec9fcdSqs148142 	uint64_t offset;
1743dec9fcdSqs148142 
1753dec9fcdSqs148142 	offset = PFC_CONFIG;
1763dec9fcdSqs148142 	REG_PIO_WRITE64(handle, offset, config.value);
1773dec9fcdSqs148142 
1783dec9fcdSqs148142 	return (HPI_SUCCESS);
1793dec9fcdSqs148142 }
1803dec9fcdSqs148142 
1813dec9fcdSqs148142 static hpi_status_t
1823dec9fcdSqs148142 hpi_pfc_get_config(hpi_handle_t handle, pfc_config_t *configp)
1833dec9fcdSqs148142 {
1843dec9fcdSqs148142 	uint64_t offset;
1853dec9fcdSqs148142 
1863dec9fcdSqs148142 	offset = PFC_CONFIG;
1873dec9fcdSqs148142 	REG_PIO_READ64(handle, offset, &configp->value);
1883dec9fcdSqs148142 
1893dec9fcdSqs148142 	return (HPI_SUCCESS);
1903dec9fcdSqs148142 }
1913dec9fcdSqs148142 
1923dec9fcdSqs148142 hpi_status_t
1933dec9fcdSqs148142 hpi_pfc_set_tcam_enable(hpi_handle_t handle, boolean_t tcam)
1943dec9fcdSqs148142 {
1953dec9fcdSqs148142 	pfc_config_t	config;
1963dec9fcdSqs148142 
1973dec9fcdSqs148142 	/*
1983dec9fcdSqs148142 	 * Read the register first.
1993dec9fcdSqs148142 	 */
2003dec9fcdSqs148142 	(void) hpi_pfc_get_config(handle, &config);
2013dec9fcdSqs148142 
2023dec9fcdSqs148142 	if (tcam)
2033dec9fcdSqs148142 		config.bits.tcam_en = 1;
2043dec9fcdSqs148142 	else
2053dec9fcdSqs148142 		config.bits.tcam_en = 0;
2063dec9fcdSqs148142 
2073dec9fcdSqs148142 	return (hpi_pfc_set_config(handle, config));
2083dec9fcdSqs148142 }
2093dec9fcdSqs148142 
2103dec9fcdSqs148142 hpi_status_t
2113dec9fcdSqs148142 hpi_pfc_set_l2_hash(hpi_handle_t handle, boolean_t l2_hash)
2123dec9fcdSqs148142 {
2133dec9fcdSqs148142 	pfc_config_t	config;
2143dec9fcdSqs148142 
2153dec9fcdSqs148142 	/*
2163dec9fcdSqs148142 	 * Read the register first.
2173dec9fcdSqs148142 	 */
2183dec9fcdSqs148142 	(void) hpi_pfc_get_config(handle, &config);
2193dec9fcdSqs148142 
2203dec9fcdSqs148142 	if (l2_hash)
2213dec9fcdSqs148142 		config.bits.l2_hash_en = 1;
2223dec9fcdSqs148142 	else
2233dec9fcdSqs148142 		config.bits.l2_hash_en = 0;
2243dec9fcdSqs148142 
2253dec9fcdSqs148142 	return (hpi_pfc_set_config(handle, config));
2263dec9fcdSqs148142 }
2273dec9fcdSqs148142 
2283dec9fcdSqs148142 hpi_status_t
2293dec9fcdSqs148142 hpi_pfc_set_tcp_cksum(hpi_handle_t handle, boolean_t cksum)
2303dec9fcdSqs148142 {
2313dec9fcdSqs148142 	pfc_config_t	config;
2323dec9fcdSqs148142 
2333dec9fcdSqs148142 	/*
2343dec9fcdSqs148142 	 * Read the register first.
2353dec9fcdSqs148142 	 */
2363dec9fcdSqs148142 	(void) hpi_pfc_get_config(handle, &config);
2373dec9fcdSqs148142 
2383dec9fcdSqs148142 	if (cksum)
2393dec9fcdSqs148142 		config.bits.tcp_cs_en = 1;
2403dec9fcdSqs148142 	else
2413dec9fcdSqs148142 		config.bits.tcp_cs_en = 0;
2423dec9fcdSqs148142 
2433dec9fcdSqs148142 	return (hpi_pfc_set_config(handle, config));
2443dec9fcdSqs148142 }
2453dec9fcdSqs148142 
2463dec9fcdSqs148142 hpi_status_t
2473dec9fcdSqs148142 hpi_pfc_set_default_dma(hpi_handle_t handle, uint32_t dma_channel_no)
2483dec9fcdSqs148142 {
2493dec9fcdSqs148142 	pfc_config_t	config;
2503dec9fcdSqs148142 
2513dec9fcdSqs148142 	(void) hpi_pfc_get_config(handle, &config);
2523dec9fcdSqs148142 
2533dec9fcdSqs148142 	if (dma_channel_no > PFC_MAX_DMA_CHANNELS)
2543dec9fcdSqs148142 		return (HPI_FAILURE);
2553dec9fcdSqs148142 
2563dec9fcdSqs148142 	config.bits.default_dma = dma_channel_no;
2573dec9fcdSqs148142 
2583dec9fcdSqs148142 	return (hpi_pfc_set_config(handle, config));
2593dec9fcdSqs148142 }
2603dec9fcdSqs148142 
2613dec9fcdSqs148142 hpi_status_t
2623dec9fcdSqs148142 hpi_pfc_mac_addr_enable(hpi_handle_t handle, uint32_t slot)
2633dec9fcdSqs148142 {
2643dec9fcdSqs148142 	pfc_config_t	config;
2653dec9fcdSqs148142 	uint32_t	bit;
2663dec9fcdSqs148142 
2673dec9fcdSqs148142 	if (slot >= PFC_N_MAC_ADDRESSES) {
2683dec9fcdSqs148142 		return (HPI_FAILURE);
2693dec9fcdSqs148142 	}
2703dec9fcdSqs148142 
2713dec9fcdSqs148142 	(void) hpi_pfc_get_config(handle, &config);
2723dec9fcdSqs148142 
273fe930412Sqs148142 	if (slot < 24) {
2743dec9fcdSqs148142 		bit = 1 << slot;
275fe930412Sqs148142 		config.bits.mac_addr_en_l = config.bits.mac_addr_en_l | bit;
276fe930412Sqs148142 	} else {
277fe930412Sqs148142 		bit = 1 << (slot - 24);
2783dec9fcdSqs148142 		config.bits.mac_addr_en = config.bits.mac_addr_en | bit;
279fe930412Sqs148142 	}
2803dec9fcdSqs148142 
2813dec9fcdSqs148142 	return (hpi_pfc_set_config(handle, config));
2823dec9fcdSqs148142 }
2833dec9fcdSqs148142 
2843dec9fcdSqs148142 hpi_status_t
2853dec9fcdSqs148142 hpi_pfc_mac_addr_disable(hpi_handle_t handle, uint32_t slot)
2863dec9fcdSqs148142 {
2873dec9fcdSqs148142 	pfc_config_t	config;
2883dec9fcdSqs148142 	uint32_t	bit;
2893dec9fcdSqs148142 
2903dec9fcdSqs148142 	if (slot >= PFC_N_MAC_ADDRESSES) {
2913dec9fcdSqs148142 		return (HPI_FAILURE);
2923dec9fcdSqs148142 	}
2933dec9fcdSqs148142 
2943dec9fcdSqs148142 	(void) hpi_pfc_get_config(handle, &config);
2953dec9fcdSqs148142 
296fe930412Sqs148142 	if (slot < 24) {
2973dec9fcdSqs148142 		bit = 1 << slot;
298fe930412Sqs148142 		config.bits.mac_addr_en_l = config.bits.mac_addr_en_l & ~bit;
299fe930412Sqs148142 	} else {
300fe930412Sqs148142 		bit = 1 << (slot - 24);
3013dec9fcdSqs148142 		config.bits.mac_addr_en = config.bits.mac_addr_en & ~bit;
302fe930412Sqs148142 	}
3033dec9fcdSqs148142 
3043dec9fcdSqs148142 	return (hpi_pfc_set_config(handle, config));
3053dec9fcdSqs148142 }
3063dec9fcdSqs148142 
3073dec9fcdSqs148142 hpi_status_t
3083dec9fcdSqs148142 hpi_pfc_set_force_csum(hpi_handle_t handle, boolean_t force)
3093dec9fcdSqs148142 {
3103dec9fcdSqs148142 	pfc_config_t	config;
3113dec9fcdSqs148142 
3123dec9fcdSqs148142 	(void) hpi_pfc_get_config(handle, &config);
3133dec9fcdSqs148142 
3143dec9fcdSqs148142 	if (force)
3153dec9fcdSqs148142 		config.bits.force_cs_en = 1;
3163dec9fcdSqs148142 	else
3173dec9fcdSqs148142 		config.bits.force_cs_en = 0;
3183dec9fcdSqs148142 
3193dec9fcdSqs148142 	return (hpi_pfc_set_config(handle, config));
3203dec9fcdSqs148142 }
3213dec9fcdSqs148142 
3223dec9fcdSqs148142 hpi_status_t
3233dec9fcdSqs148142 hpi_pfc_cfg_vlan_table_clear(hpi_handle_t handle)
3243dec9fcdSqs148142 {
3253dec9fcdSqs148142 	int			i;
3263dec9fcdSqs148142 	int			offset;
3273dec9fcdSqs148142 	int			step = 8;
3283dec9fcdSqs148142 	pfc_vlan_table_t	table_entry;
3293dec9fcdSqs148142 
3303dec9fcdSqs148142 	table_entry.value = 0;
3313dec9fcdSqs148142 	for (i = 0; i < HXGE_VLAN_TABLE_ENTRIES; i++) {
3323dec9fcdSqs148142 		table_entry.bits.member = 0;
3333dec9fcdSqs148142 		offset = PFC_VLAN_TABLE + i * step;
3343dec9fcdSqs148142 		REG_PIO_WRITE64(handle, offset, table_entry.value);
3353dec9fcdSqs148142 	}
3363dec9fcdSqs148142 
3373dec9fcdSqs148142 	return (HPI_SUCCESS);
3383dec9fcdSqs148142 }
3393dec9fcdSqs148142 
3403dec9fcdSqs148142 hpi_status_t
3413dec9fcdSqs148142 hpi_pfc_cfg_vlan_table_entry_clear(hpi_handle_t handle, vlan_id_t vlan_id)
3423dec9fcdSqs148142 {
3433dec9fcdSqs148142 	uint64_t		offset;
3443dec9fcdSqs148142 	pfc_vlan_table_t	vlan_tbl_entry;
3453dec9fcdSqs148142 	uint64_t		bit;
3463dec9fcdSqs148142 
3473dec9fcdSqs148142 	/*
3483dec9fcdSqs148142 	 * Assumes that the hardware will generate the new parity
3493dec9fcdSqs148142 	 * data.
3503dec9fcdSqs148142 	 */
3513dec9fcdSqs148142 	offset = PFC_VLAN_REG_OFFSET(vlan_id);
3523dec9fcdSqs148142 	REG_PIO_READ64(handle, offset, (uint64_t *)&vlan_tbl_entry.value);
3533dec9fcdSqs148142 
3543dec9fcdSqs148142 	bit = PFC_VLAN_BIT_OFFSET(vlan_id);
3553dec9fcdSqs148142 	bit = 1 << bit;
3563dec9fcdSqs148142 	vlan_tbl_entry.bits.member = vlan_tbl_entry.bits.member & ~bit;
3573dec9fcdSqs148142 
3583dec9fcdSqs148142 	REG_PIO_WRITE64(handle, offset, vlan_tbl_entry.value);
3593dec9fcdSqs148142 
3603dec9fcdSqs148142 	return (HPI_SUCCESS);
3613dec9fcdSqs148142 }
3623dec9fcdSqs148142 
3633dec9fcdSqs148142 hpi_status_t
3643dec9fcdSqs148142 hpi_pfc_cfg_vlan_table_entry_set(hpi_handle_t handle, vlan_id_t vlan_id)
3653dec9fcdSqs148142 {
3663dec9fcdSqs148142 	uint64_t		offset;
3673dec9fcdSqs148142 	pfc_vlan_table_t	vlan_tbl_entry;
3683dec9fcdSqs148142 	uint64_t		bit;
3693dec9fcdSqs148142 
3703dec9fcdSqs148142 	/*
3713dec9fcdSqs148142 	 * Assumes that the hardware will generate the new parity
3723dec9fcdSqs148142 	 * data.
3733dec9fcdSqs148142 	 */
3743dec9fcdSqs148142 	offset = PFC_VLAN_REG_OFFSET(vlan_id);
3753dec9fcdSqs148142 	REG_PIO_READ64(handle, offset, (uint64_t *)&vlan_tbl_entry.value);
3763dec9fcdSqs148142 
3773dec9fcdSqs148142 	bit = PFC_VLAN_BIT_OFFSET(vlan_id);
3783dec9fcdSqs148142 	bit = 1 << bit;
3793dec9fcdSqs148142 	vlan_tbl_entry.bits.member = vlan_tbl_entry.bits.member | bit;
3803dec9fcdSqs148142 
3813dec9fcdSqs148142 	REG_PIO_WRITE64(handle, offset, vlan_tbl_entry.value);
3823dec9fcdSqs148142 
3833dec9fcdSqs148142 	return (HPI_SUCCESS);
3843dec9fcdSqs148142 }
3853dec9fcdSqs148142 
3863dec9fcdSqs148142 hpi_status_t
3873dec9fcdSqs148142 hpi_pfc_cfg_vlan_control_set(hpi_handle_t handle, boolean_t parity,
3883dec9fcdSqs148142     boolean_t valid, vlan_id_t vlan_id)
3893dec9fcdSqs148142 {
3903dec9fcdSqs148142 	pfc_vlan_ctrl_t	vlan_control;
3913dec9fcdSqs148142 
3923dec9fcdSqs148142 	vlan_control.value = 0;
3933dec9fcdSqs148142 
3943dec9fcdSqs148142 	if (parity)
3953dec9fcdSqs148142 		vlan_control.bits.par_en = 1;
3963dec9fcdSqs148142 	else
3973dec9fcdSqs148142 		vlan_control.bits.par_en = 0;
3983dec9fcdSqs148142 
3993dec9fcdSqs148142 	if (valid)
4003dec9fcdSqs148142 		vlan_control.bits.valid = 1;
4013dec9fcdSqs148142 	else
4023dec9fcdSqs148142 		vlan_control.bits.valid = 0;
4033dec9fcdSqs148142 
4043dec9fcdSqs148142 	vlan_control.bits.id = vlan_id;
4053dec9fcdSqs148142 
4063dec9fcdSqs148142 	REG_PIO_WRITE64(handle, PFC_VLAN_CTRL, vlan_control.value);
4073dec9fcdSqs148142 
4083dec9fcdSqs148142 	return (HPI_SUCCESS);
4093dec9fcdSqs148142 }
4103dec9fcdSqs148142 
4113dec9fcdSqs148142 hpi_status_t
4123dec9fcdSqs148142 hpi_pfc_get_vlan_parity_log(hpi_handle_t handle, pfc_vlan_par_err_log_t *logp)
4133dec9fcdSqs148142 {
4143dec9fcdSqs148142 	uint64_t offset;
4153dec9fcdSqs148142 
4163dec9fcdSqs148142 	offset = PFC_VLAN_PAR_ERR_LOG;
4173dec9fcdSqs148142 	REG_PIO_READ64(handle, offset, &logp->value);
4183dec9fcdSqs148142 
4193dec9fcdSqs148142 	return (HPI_SUCCESS);
4203dec9fcdSqs148142 }
4213dec9fcdSqs148142 
4223dec9fcdSqs148142 hpi_status_t
4233dec9fcdSqs148142 hpi_pfc_set_mac_address(hpi_handle_t handle, uint32_t slot, uint64_t address)
4243dec9fcdSqs148142 {
4253dec9fcdSqs148142 	uint64_t		offset;
4263dec9fcdSqs148142 	uint64_t		moffset;
4273dec9fcdSqs148142 	pfc_mac_addr_mask_t	mask;
4283dec9fcdSqs148142 	pfc_mac_addr_t		addr;
4293dec9fcdSqs148142 
4303dec9fcdSqs148142 	if (slot >= PFC_N_MAC_ADDRESSES)
4313dec9fcdSqs148142 		return (HPI_FAILURE);
4323dec9fcdSqs148142 
4333dec9fcdSqs148142 	offset = PFC_MAC_ADDRESS(slot);
4343dec9fcdSqs148142 	moffset = PFC_MAC_ADDRESS_MASK(slot);
4353dec9fcdSqs148142 
436fe930412Sqs148142 	addr.bits.addr = address >> 32;
437fe930412Sqs148142 	addr.bits.addr_l = address & 0xffffffff;
4383dec9fcdSqs148142 	mask.bits.mask = 0x0;
439fe930412Sqs148142 	mask.bits.mask_l = 0x0;
4403dec9fcdSqs148142 
4413dec9fcdSqs148142 	REG_PIO_WRITE64(handle, offset, addr.value);
4423dec9fcdSqs148142 	REG_PIO_WRITE64(handle, moffset, mask.value);
4433dec9fcdSqs148142 
4443dec9fcdSqs148142 	return (hpi_pfc_mac_addr_enable(handle, slot));
4453dec9fcdSqs148142 }
4463dec9fcdSqs148142 
4473dec9fcdSqs148142 hpi_status_t
4483dec9fcdSqs148142 hpi_pfc_clear_mac_address(hpi_handle_t handle, uint32_t slot)
4493dec9fcdSqs148142 {
4503dec9fcdSqs148142 	uint64_t offset, moffset;
4513dec9fcdSqs148142 	uint64_t zaddr = 0x0ULL;
4523dec9fcdSqs148142 	uint64_t zmask = 0x0ULL;
4533dec9fcdSqs148142 
4543dec9fcdSqs148142 	if (slot >= PFC_N_MAC_ADDRESSES)
4553dec9fcdSqs148142 		return (HPI_FAILURE);
4563dec9fcdSqs148142 
4573dec9fcdSqs148142 	(void) hpi_pfc_mac_addr_disable(handle, slot);
4583dec9fcdSqs148142 
4593dec9fcdSqs148142 	offset = PFC_MAC_ADDRESS(slot);
4603dec9fcdSqs148142 	moffset = PFC_MAC_ADDRESS_MASK(slot);
4613dec9fcdSqs148142 
4623dec9fcdSqs148142 	REG_PIO_WRITE64(handle, offset, zaddr);
4633dec9fcdSqs148142 	REG_PIO_WRITE64(handle, moffset, zmask);
4643dec9fcdSqs148142 
4653dec9fcdSqs148142 	return (HPI_SUCCESS);
4663dec9fcdSqs148142 }
4673dec9fcdSqs148142 
4683dec9fcdSqs148142 hpi_status_t
4693dec9fcdSqs148142 hpi_pfc_clear_multicast_hash_table(hpi_handle_t handle, uint32_t slot)
4703dec9fcdSqs148142 {
4713dec9fcdSqs148142 	uint64_t offset;
4723dec9fcdSqs148142 
4733dec9fcdSqs148142 	if (slot >= PFC_N_MAC_ADDRESSES)
4743dec9fcdSqs148142 		return (HPI_FAILURE);
4753dec9fcdSqs148142 
4763dec9fcdSqs148142 	offset = PFC_HASH_ADDR(slot);
4773dec9fcdSqs148142 	REG_PIO_WRITE64(handle, offset, 0ULL);
4783dec9fcdSqs148142 
4793dec9fcdSqs148142 	return (HPI_SUCCESS);
4803dec9fcdSqs148142 }
4813dec9fcdSqs148142 
4823dec9fcdSqs148142 hpi_status_t
4833dec9fcdSqs148142 hpi_pfc_set_multicast_hash_table(hpi_handle_t handle, uint32_t slot,
4843dec9fcdSqs148142 	uint64_t address)
4853dec9fcdSqs148142 {
4863dec9fcdSqs148142 	uint64_t offset;
4873dec9fcdSqs148142 
4883dec9fcdSqs148142 	if (slot >= PFC_N_MAC_ADDRESSES)
4893dec9fcdSqs148142 		return (HPI_FAILURE);
4903dec9fcdSqs148142 
4913dec9fcdSqs148142 	offset = PFC_HASH_ADDR(slot);
4923dec9fcdSqs148142 	REG_PIO_WRITE64(handle, offset, address);
4933dec9fcdSqs148142 
4943dec9fcdSqs148142 	return (HPI_SUCCESS);
4953dec9fcdSqs148142 }
4963dec9fcdSqs148142 
4973dec9fcdSqs148142 hpi_status_t
4983dec9fcdSqs148142 hpi_pfc_set_l2_class_slot(hpi_handle_t handle, uint16_t etype, boolean_t valid,
4993dec9fcdSqs148142     int slot)
5003dec9fcdSqs148142 {
5013dec9fcdSqs148142 	pfc_l2_class_config_t	l2_config;
5023dec9fcdSqs148142 	uint64_t		offset;
5033dec9fcdSqs148142 
5043dec9fcdSqs148142 	if (slot >= PFC_N_MAC_ADDRESSES)
5053dec9fcdSqs148142 		return (HPI_FAILURE);
5063dec9fcdSqs148142 
5073dec9fcdSqs148142 	l2_config.value = 0;
5083dec9fcdSqs148142 
5093dec9fcdSqs148142 	if (valid)
5103dec9fcdSqs148142 		l2_config.bits.valid = 1;
5113dec9fcdSqs148142 	else
5123dec9fcdSqs148142 		l2_config.bits.valid = 0;
5133dec9fcdSqs148142 
5143dec9fcdSqs148142 	l2_config.bits.etype = etype;
5153dec9fcdSqs148142 	l2_config.bits.rsrvd = 0;
5163dec9fcdSqs148142 
5173dec9fcdSqs148142 	offset = PFC_L2_CONFIG(slot);
5183dec9fcdSqs148142 	REG_PIO_WRITE64(handle, offset, l2_config.value);
5193dec9fcdSqs148142 
5203dec9fcdSqs148142 	return (HPI_SUCCESS);
5213dec9fcdSqs148142 }
5223dec9fcdSqs148142 
5233dec9fcdSqs148142 hpi_status_t
5243dec9fcdSqs148142 hpi_pfc_set_l3_class_config(hpi_handle_t handle, tcam_class_t slot,
5253dec9fcdSqs148142     tcam_key_cfg_t cfg)
5263dec9fcdSqs148142 {
5273dec9fcdSqs148142 	pfc_l3_class_config_t	l3_config;
5283dec9fcdSqs148142 	uint64_t		offset;
5293dec9fcdSqs148142 
5303dec9fcdSqs148142 	if (slot >= PFC_N_MAC_ADDRESSES)
5313dec9fcdSqs148142 		return (HPI_FAILURE);
5323dec9fcdSqs148142 
5333dec9fcdSqs148142 	l3_config.value = 0;
5343dec9fcdSqs148142 
5353dec9fcdSqs148142 	if (cfg.lookup_enable)
5363dec9fcdSqs148142 		l3_config.bits.tsel = 1;
5373dec9fcdSqs148142 	else
5383dec9fcdSqs148142 		l3_config.bits.tsel = 0;
5393dec9fcdSqs148142 
5403dec9fcdSqs148142 	if (cfg.discard)
5413dec9fcdSqs148142 		l3_config.bits.discard = 1;
5423dec9fcdSqs148142 	else
5433dec9fcdSqs148142 		l3_config.bits.discard = 0;
5443dec9fcdSqs148142 
5453dec9fcdSqs148142 	offset = PFC_L3_CONFIG(slot);
5463dec9fcdSqs148142 	REG_PIO_WRITE64(handle, offset, l3_config.value);
5473dec9fcdSqs148142 
5483dec9fcdSqs148142 	return (HPI_SUCCESS);
5493dec9fcdSqs148142 }
5503dec9fcdSqs148142 
5513dec9fcdSqs148142 hpi_status_t
5523dec9fcdSqs148142 hpi_pfc_get_l3_class_config(hpi_handle_t handle, tcam_class_t slot,
5533dec9fcdSqs148142     tcam_key_cfg_t *cfg)
5543dec9fcdSqs148142 {
5553dec9fcdSqs148142 	pfc_l3_class_config_t	l3_config;
5563dec9fcdSqs148142 	uint64_t		offset;
5573dec9fcdSqs148142 
5583dec9fcdSqs148142 	if (slot >= PFC_N_MAC_ADDRESSES)
5593dec9fcdSqs148142 		return (HPI_FAILURE);
5603dec9fcdSqs148142 
5613dec9fcdSqs148142 	offset = PFC_L3_CONFIG(slot);
5623dec9fcdSqs148142 	REG_PIO_READ64(handle, offset, &l3_config.value);
5633dec9fcdSqs148142 
5643dec9fcdSqs148142 	if (l3_config.bits.tsel)
5653dec9fcdSqs148142 		cfg->lookup_enable = 1;
5663dec9fcdSqs148142 	else
5673dec9fcdSqs148142 		cfg->lookup_enable = 0;
5683dec9fcdSqs148142 
5693dec9fcdSqs148142 	if (l3_config.bits.discard)
5703dec9fcdSqs148142 		cfg->discard = 1;
5713dec9fcdSqs148142 	else
5723dec9fcdSqs148142 		cfg->discard = 0;
5733dec9fcdSqs148142 
5743dec9fcdSqs148142 	return (HPI_SUCCESS);
5753dec9fcdSqs148142 }
5763dec9fcdSqs148142 
5773dec9fcdSqs148142 static hpi_status_t
5783dec9fcdSqs148142 hpi_pfc_set_tcam_control(hpi_handle_t handle, pfc_tcam_ctrl_t *tcontrolp)
5793dec9fcdSqs148142 {
5803dec9fcdSqs148142 	uint64_t offset;
5813dec9fcdSqs148142 
5823dec9fcdSqs148142 	offset = PFC_TCAM_CTRL;
5833dec9fcdSqs148142 	REG_PIO_WRITE64(handle, offset, tcontrolp->value);
5843dec9fcdSqs148142 
5853dec9fcdSqs148142 	return (HPI_SUCCESS);
5863dec9fcdSqs148142 }
5873dec9fcdSqs148142 
5883dec9fcdSqs148142 hpi_status_t
5893dec9fcdSqs148142 hpi_pfc_tcam_entry_invalidate(hpi_handle_t handle, uint32_t location)
5903dec9fcdSqs148142 {
5913dec9fcdSqs148142 	hxge_tcam_entry_t	tcam_ptr;
5923dec9fcdSqs148142 
5933dec9fcdSqs148142 	(void) memset(&tcam_ptr, 0, sizeof (hxge_tcam_entry_t));
5943dec9fcdSqs148142 	(void) hpi_pfc_tcam_entry_write(handle, location, &tcam_ptr);
5953dec9fcdSqs148142 
5963dec9fcdSqs148142 	return (HPI_SUCCESS);
5973dec9fcdSqs148142 }
5983dec9fcdSqs148142 
5993dec9fcdSqs148142 hpi_status_t
6003dec9fcdSqs148142 hpi_pfc_tcam_invalidate_all(hpi_handle_t handle)
6013dec9fcdSqs148142 {
6023dec9fcdSqs148142 	int		i;
6033dec9fcdSqs148142 	pfc_tcam_ctrl_t	tcontrol;
6043dec9fcdSqs148142 
6053dec9fcdSqs148142 	tcontrol.value = 0;
6063dec9fcdSqs148142 	for (i = 0; i < PFC_N_TCAM_ENTRIES; i++) {
6073dec9fcdSqs148142 		(void) hpi_pfc_set_tcam_control(handle, &tcontrol);
6083dec9fcdSqs148142 		(void) hpi_pfc_tcam_entry_invalidate(handle, i);
6093dec9fcdSqs148142 	}
6103dec9fcdSqs148142 
6113dec9fcdSqs148142 	return (HPI_SUCCESS);
6123dec9fcdSqs148142 }
6133dec9fcdSqs148142 
6143dec9fcdSqs148142 hpi_status_t
6153dec9fcdSqs148142 hpi_pfc_tcam_entry_write(hpi_handle_t handle, uint32_t location,
6163dec9fcdSqs148142     hxge_tcam_entry_t *tcam_ptr)
6173dec9fcdSqs148142 {
6183dec9fcdSqs148142 	uint64_t	tcam_stat;
6193dec9fcdSqs148142 	pfc_tcam_ctrl_t	tctl;
6203dec9fcdSqs148142 
6213dec9fcdSqs148142 	WRITE_TCAM_REG_MASK0(handle, tcam_ptr->mask0);
6223dec9fcdSqs148142 	WRITE_TCAM_REG_MASK1(handle, tcam_ptr->mask1);
6233dec9fcdSqs148142 
6243dec9fcdSqs148142 	WRITE_TCAM_REG_KEY0(handle, tcam_ptr->key0);
6253dec9fcdSqs148142 	WRITE_TCAM_REG_KEY1(handle, tcam_ptr->key1);
6263dec9fcdSqs148142 
6273dec9fcdSqs148142 	HPI_DEBUG_MSG((handle.function, HPI_PFC_CTL,
6283dec9fcdSqs148142 	    " tcam write: location %x\n key:  %llx %llx\n mask: %llx %llx\n",
6293dec9fcdSqs148142 	    location, tcam_ptr->key0, tcam_ptr->key1,
6303dec9fcdSqs148142 	    tcam_ptr->mask0, tcam_ptr->mask1));
6313dec9fcdSqs148142 
6323dec9fcdSqs148142 	tctl.value = 0;
6333dec9fcdSqs148142 	tctl.bits.addr = location;
6343dec9fcdSqs148142 	tctl.bits.cmd = TCAM_CTL_RWC_TCAM_WR;
6353dec9fcdSqs148142 
6363dec9fcdSqs148142 	HPI_DEBUG_MSG((handle.function, HPI_PFC_CTL,
6373dec9fcdSqs148142 	    " tcam write: ctl value %llx \n", tctl.value));
6383dec9fcdSqs148142 
6393dec9fcdSqs148142 	WRITE_TCAM_REG_CTL(handle, tctl.value);
6403dec9fcdSqs148142 
6413dec9fcdSqs148142 	tcam_stat = hpi_pfc_tcam_check_completion(handle, TCAM_RWC_STAT);
6423dec9fcdSqs148142 
6433dec9fcdSqs148142 	if (tcam_stat & HPI_FAILURE) {
6443dec9fcdSqs148142 		HPI_ERROR_MSG((handle.function, HPI_ERR_CTL,
6453dec9fcdSqs148142 		    "TCAM Write failed loc %d \n", location));
6463dec9fcdSqs148142 		return (HPI_PFC_TCAM_WR_ERROR);
6473dec9fcdSqs148142 	}
6483dec9fcdSqs148142 
6493dec9fcdSqs148142 	return (HPI_SUCCESS);
6503dec9fcdSqs148142 }
6513dec9fcdSqs148142 
6523dec9fcdSqs148142 hpi_status_t
6533dec9fcdSqs148142 hpi_pfc_get_tcam_parity_log(hpi_handle_t handle, pfc_tcam_par_err_log_t *logp)
6543dec9fcdSqs148142 {
6553dec9fcdSqs148142 	uint64_t offset;
6563dec9fcdSqs148142 
6573dec9fcdSqs148142 	offset = PFC_TCAM_PAR_ERR_LOG;
6583dec9fcdSqs148142 	REG_PIO_READ64(handle, offset, &logp->value);
6593dec9fcdSqs148142 
6603dec9fcdSqs148142 	return (HPI_SUCCESS);
6613dec9fcdSqs148142 }
6623dec9fcdSqs148142 
6633dec9fcdSqs148142 hpi_status_t
6643dec9fcdSqs148142 hpi_pfc_get_tcam_auto_init(hpi_handle_t handle, pfc_auto_init_t *autoinitp)
6653dec9fcdSqs148142 {
6663dec9fcdSqs148142 	uint64_t offset;
6673dec9fcdSqs148142 
6683dec9fcdSqs148142 	offset = PFC_AUTO_INIT;
6693dec9fcdSqs148142 	REG_PIO_READ64(handle, offset, &autoinitp->value);
6703dec9fcdSqs148142 
6713dec9fcdSqs148142 	return (HPI_SUCCESS);
6723dec9fcdSqs148142 }
6733dec9fcdSqs148142 
6743dec9fcdSqs148142 hpi_status_t
6753dec9fcdSqs148142 hpi_pfc_set_tcp_control_discard(hpi_handle_t handle, boolean_t discard)
6763dec9fcdSqs148142 {
6773dec9fcdSqs148142 	uint64_t	offset;
6783dec9fcdSqs148142 	tcp_ctrl_mask_t	tcp;
6793dec9fcdSqs148142 
6803dec9fcdSqs148142 	tcp.value = 0;
6813dec9fcdSqs148142 
6823dec9fcdSqs148142 	offset = TCP_CTRL_MASK;
6833dec9fcdSqs148142 	REG_PIO_READ64(handle, offset, &tcp.value);
6843dec9fcdSqs148142 
6853dec9fcdSqs148142 	if (discard)
6863dec9fcdSqs148142 		tcp.bits.discard = 1;
6873dec9fcdSqs148142 	else
6883dec9fcdSqs148142 		tcp.bits.discard = 0;
6893dec9fcdSqs148142 
6903dec9fcdSqs148142 	REG_PIO_WRITE64(handle, offset, tcp.value);
6913dec9fcdSqs148142 
6923dec9fcdSqs148142 	return (HPI_SUCCESS);
6933dec9fcdSqs148142 }
6943dec9fcdSqs148142 
6953dec9fcdSqs148142 hpi_status_t
6963dec9fcdSqs148142 hpi_pfc_set_tcp_control_fin(hpi_handle_t handle, boolean_t fin)
6973dec9fcdSqs148142 {
6983dec9fcdSqs148142 	uint64_t	offset;
6993dec9fcdSqs148142 	tcp_ctrl_mask_t	tcp;
7003dec9fcdSqs148142 
7013dec9fcdSqs148142 	tcp.value = 0;
7023dec9fcdSqs148142 
7033dec9fcdSqs148142 	offset = TCP_CTRL_MASK;
7043dec9fcdSqs148142 	REG_PIO_READ64(handle, offset, &tcp.value);
7053dec9fcdSqs148142 
7063dec9fcdSqs148142 	if (fin)
7073dec9fcdSqs148142 		tcp.bits.fin = 1;
7083dec9fcdSqs148142 	else
7093dec9fcdSqs148142 		tcp.bits.fin = 0;
7103dec9fcdSqs148142 
7113dec9fcdSqs148142 	REG_PIO_WRITE64(handle, offset, tcp.value);
7123dec9fcdSqs148142 	return (HPI_SUCCESS);
7133dec9fcdSqs148142 }
7143dec9fcdSqs148142 
7153dec9fcdSqs148142 hpi_status_t
7163dec9fcdSqs148142 hpi_pfc_set_tcp_control_syn(hpi_handle_t handle, boolean_t syn)
7173dec9fcdSqs148142 {
7183dec9fcdSqs148142 	uint64_t	offset;
7193dec9fcdSqs148142 	tcp_ctrl_mask_t	tcp;
7203dec9fcdSqs148142 
7213dec9fcdSqs148142 	tcp.value = 0;
7223dec9fcdSqs148142 
7233dec9fcdSqs148142 	offset = TCP_CTRL_MASK;
7243dec9fcdSqs148142 	REG_PIO_READ64(handle, offset, &tcp.value);
7253dec9fcdSqs148142 
7263dec9fcdSqs148142 	if (syn)
7273dec9fcdSqs148142 		tcp.bits.syn = 1;
7283dec9fcdSqs148142 	else
7293dec9fcdSqs148142 		tcp.bits.syn = 0;
7303dec9fcdSqs148142 
7313dec9fcdSqs148142 	REG_PIO_WRITE64(handle, offset, tcp.value);
7323dec9fcdSqs148142 	return (HPI_SUCCESS);
7333dec9fcdSqs148142 }
7343dec9fcdSqs148142 
7353dec9fcdSqs148142 hpi_status_t
7363dec9fcdSqs148142 hpi_pfc_set_tcp_control_rst(hpi_handle_t handle, boolean_t rst)
7373dec9fcdSqs148142 {
7383dec9fcdSqs148142 	uint64_t	offset;
7393dec9fcdSqs148142 	tcp_ctrl_mask_t	tcp;
7403dec9fcdSqs148142 
7413dec9fcdSqs148142 	tcp.value = 0;
7423dec9fcdSqs148142 
7433dec9fcdSqs148142 	offset = TCP_CTRL_MASK;
7443dec9fcdSqs148142 	REG_PIO_READ64(handle, offset, &tcp.value);
7453dec9fcdSqs148142 
7463dec9fcdSqs148142 	if (rst)
7473dec9fcdSqs148142 		tcp.bits.rst = 1;
7483dec9fcdSqs148142 	else
7493dec9fcdSqs148142 		tcp.bits.rst = 0;
7503dec9fcdSqs148142 
7513dec9fcdSqs148142 	REG_PIO_WRITE64(handle, offset, tcp.value);
7523dec9fcdSqs148142 	return (HPI_SUCCESS);
7533dec9fcdSqs148142 }
7543dec9fcdSqs148142 
7553dec9fcdSqs148142 hpi_status_t
7563dec9fcdSqs148142 hpi_pfc_set_tcp_control_psh(hpi_handle_t handle, boolean_t push)
7573dec9fcdSqs148142 {
7583dec9fcdSqs148142 	uint64_t	offset;
7593dec9fcdSqs148142 	tcp_ctrl_mask_t	tcp;
7603dec9fcdSqs148142 
7613dec9fcdSqs148142 	tcp.value = 0;
7623dec9fcdSqs148142 
7633dec9fcdSqs148142 	offset = TCP_CTRL_MASK;
7643dec9fcdSqs148142 	REG_PIO_READ64(handle, offset, &tcp.value);
7653dec9fcdSqs148142 
7663dec9fcdSqs148142 	if (push)
7673dec9fcdSqs148142 		tcp.bits.psh = 1;
7683dec9fcdSqs148142 	else
7693dec9fcdSqs148142 		tcp.bits.psh = 0;
7703dec9fcdSqs148142 
7713dec9fcdSqs148142 	REG_PIO_WRITE64(handle, offset, tcp.value);
7723dec9fcdSqs148142 	return (HPI_SUCCESS);
7733dec9fcdSqs148142 }
7743dec9fcdSqs148142 
7753dec9fcdSqs148142 hpi_status_t
7763dec9fcdSqs148142 hpi_pfc_set_tcp_control_ack(hpi_handle_t handle, boolean_t ack)
7773dec9fcdSqs148142 {
7783dec9fcdSqs148142 	uint64_t	offset;
7793dec9fcdSqs148142 	tcp_ctrl_mask_t	tcp;
7803dec9fcdSqs148142 
7813dec9fcdSqs148142 	tcp.value = 0;
7823dec9fcdSqs148142 
7833dec9fcdSqs148142 	offset = TCP_CTRL_MASK;
7843dec9fcdSqs148142 	REG_PIO_READ64(handle, offset, &tcp.value);
7853dec9fcdSqs148142 
7863dec9fcdSqs148142 	if (ack)
7873dec9fcdSqs148142 		tcp.bits.ack = 1;
7883dec9fcdSqs148142 	else
7893dec9fcdSqs148142 		tcp.bits.ack = 0;
7903dec9fcdSqs148142 
7913dec9fcdSqs148142 	REG_PIO_WRITE64(handle, offset, tcp.value);
7923dec9fcdSqs148142 	return (HPI_SUCCESS);
7933dec9fcdSqs148142 }
7943dec9fcdSqs148142 
7953dec9fcdSqs148142 hpi_status_t
7963dec9fcdSqs148142 hpi_pfc_set_hash_seed_value(hpi_handle_t handle, uint32_t seed)
7973dec9fcdSqs148142 {
7983dec9fcdSqs148142 	uint64_t	offset;
7993dec9fcdSqs148142 	src_hash_val_t	src_hash_seed;
8003dec9fcdSqs148142 
8013dec9fcdSqs148142 	src_hash_seed.value = 0;
8023dec9fcdSqs148142 	src_hash_seed.bits.seed = seed;
8033dec9fcdSqs148142 
8043dec9fcdSqs148142 	offset = SRC_HASH_VAL;
8053dec9fcdSqs148142 	REG_PIO_WRITE64(handle, offset, src_hash_seed.value);
8063dec9fcdSqs148142 
8073dec9fcdSqs148142 	return (HPI_SUCCESS);
8083dec9fcdSqs148142 }
8093dec9fcdSqs148142 
8103dec9fcdSqs148142 hpi_status_t
8113dec9fcdSqs148142 hpi_pfc_get_interrupt_status(hpi_handle_t handle, pfc_int_status_t *statusp)
8123dec9fcdSqs148142 {
8133dec9fcdSqs148142 	uint64_t offset;
8143dec9fcdSqs148142 
8153dec9fcdSqs148142 	offset = PFC_INT_STATUS;
8163dec9fcdSqs148142 	REG_PIO_READ64(handle, offset, &statusp->value);
8173dec9fcdSqs148142 
8183dec9fcdSqs148142 	return (HPI_SUCCESS);
8193dec9fcdSqs148142 }
8203dec9fcdSqs148142 
8213dec9fcdSqs148142 hpi_status_t
8223dec9fcdSqs148142 hpi_pfc_clear_interrupt_status(hpi_handle_t handle)
8233dec9fcdSqs148142 {
8243dec9fcdSqs148142 	uint64_t offset;
8253dec9fcdSqs148142 
8263dec9fcdSqs148142 	offset = PFC_INT_STATUS;
8273dec9fcdSqs148142 	REG_PIO_WRITE64(handle, offset, HXGE_PFC_INT_STATUS_CLEAR);
8283dec9fcdSqs148142 
8293dec9fcdSqs148142 	return (HPI_SUCCESS);
8303dec9fcdSqs148142 }
8313dec9fcdSqs148142 
8323dec9fcdSqs148142 hpi_status_t
8333dec9fcdSqs148142 hpi_pfc_set_interrupt_mask(hpi_handle_t handle, boolean_t drop,
8343dec9fcdSqs148142 	boolean_t tcam_parity_error, boolean_t vlan_parity_error)
8353dec9fcdSqs148142 {
8363dec9fcdSqs148142 	pfc_int_mask_t	mask;
8373dec9fcdSqs148142 	uint64_t	offset;
8383dec9fcdSqs148142 
8393dec9fcdSqs148142 	mask.value = 0;
8403dec9fcdSqs148142 
8413dec9fcdSqs148142 	if (drop)
8423dec9fcdSqs148142 		mask.bits.pkt_drop_mask = 1;
8433dec9fcdSqs148142 	else
8443dec9fcdSqs148142 		mask.bits.pkt_drop_mask = 0;
8453dec9fcdSqs148142 
8463dec9fcdSqs148142 	if (tcam_parity_error)
8473dec9fcdSqs148142 		mask.bits.tcam_parity_err_mask = 1;
8483dec9fcdSqs148142 	else
8493dec9fcdSqs148142 		mask.bits.tcam_parity_err_mask = 0;
8503dec9fcdSqs148142 
8513dec9fcdSqs148142 	if (vlan_parity_error)
8523dec9fcdSqs148142 		mask.bits.vlan_parity_err_mask = 1;
8533dec9fcdSqs148142 	else
8543dec9fcdSqs148142 		mask.bits.vlan_parity_err_mask = 0;
8553dec9fcdSqs148142 
8563dec9fcdSqs148142 	offset = PFC_INT_MASK;
8573dec9fcdSqs148142 	REG_PIO_WRITE64(handle, offset, mask.value);
8583dec9fcdSqs148142 
8593dec9fcdSqs148142 	return (HPI_SUCCESS);
8603dec9fcdSqs148142 }
8613dec9fcdSqs148142 
8623dec9fcdSqs148142 hpi_status_t
8633dec9fcdSqs148142 hpi_pfc_get_drop_log(hpi_handle_t handle, pfc_drop_log_t *logp)
8643dec9fcdSqs148142 {
8653dec9fcdSqs148142 	uint64_t offset;
8663dec9fcdSqs148142 
8673dec9fcdSqs148142 	offset = PFC_DROP_LOG;
8683dec9fcdSqs148142 	REG_PIO_READ64(handle, offset, &logp->value);
8693dec9fcdSqs148142 
8703dec9fcdSqs148142 	return (HPI_SUCCESS);
8713dec9fcdSqs148142 }
8723dec9fcdSqs148142 
8733dec9fcdSqs148142 hpi_status_t
8743dec9fcdSqs148142 hpi_pfc_set_drop_log_mask(hpi_handle_t handle, boolean_t vlan_drop,
8753dec9fcdSqs148142     boolean_t tcam_drop, boolean_t class_code_drop, boolean_t l2_addr_drop,
8763dec9fcdSqs148142     boolean_t tcp_ctrl_drop)
8773dec9fcdSqs148142 {
8783dec9fcdSqs148142 	uint64_t		offset;
8793dec9fcdSqs148142 	pfc_drop_log_mask_t	log;
8803dec9fcdSqs148142 
8813dec9fcdSqs148142 	log.value = 0;
8823dec9fcdSqs148142 
8833dec9fcdSqs148142 	if (vlan_drop)
8843dec9fcdSqs148142 		log.bits.vlan_drop_mask = 1;
8853dec9fcdSqs148142 	if (tcam_drop)
8863dec9fcdSqs148142 		log.bits.tcam_drop_mask = 1;
8873dec9fcdSqs148142 	if (class_code_drop)
8883dec9fcdSqs148142 		log.bits.class_code_drop_mask = 1;
8893dec9fcdSqs148142 	if (l2_addr_drop)
8903dec9fcdSqs148142 		log.bits.l2_addr_drop_mask = 1;
8913dec9fcdSqs148142 	if (tcp_ctrl_drop)
8923dec9fcdSqs148142 		log.bits.tcp_ctrl_drop_mask = 1;
8933dec9fcdSqs148142 
8943dec9fcdSqs148142 	offset = PFC_DROP_LOG_MASK;
8953dec9fcdSqs148142 	REG_PIO_WRITE64(handle, offset, log.value);
8963dec9fcdSqs148142 
8973dec9fcdSqs148142 	return (HPI_SUCCESS);
8983dec9fcdSqs148142 }
8993dec9fcdSqs148142 
9003dec9fcdSqs148142 hpi_status_t
9013dec9fcdSqs148142 hpi_pfc_get_bad_csum_counter(hpi_handle_t handle, uint64_t *countp)
9023dec9fcdSqs148142 {
9033dec9fcdSqs148142 	uint64_t offset;
9043dec9fcdSqs148142 
9053dec9fcdSqs148142 	offset = PFC_BAD_CS_COUNTER;
9063dec9fcdSqs148142 	REG_PIO_READ64(handle, offset, countp);
9073dec9fcdSqs148142 
9083dec9fcdSqs148142 	return (HPI_SUCCESS);
9093dec9fcdSqs148142 }
9103dec9fcdSqs148142 
9113dec9fcdSqs148142 hpi_status_t
9123dec9fcdSqs148142 hpi_pfc_get_drop_counter(hpi_handle_t handle, uint64_t *countp)
9133dec9fcdSqs148142 {
9143dec9fcdSqs148142 	uint64_t offset;
9153dec9fcdSqs148142 
9163dec9fcdSqs148142 	offset = PFC_DROP_COUNTER;
9173dec9fcdSqs148142 	REG_PIO_READ64(handle, offset, countp);
9183dec9fcdSqs148142 
9193dec9fcdSqs148142 	return (HPI_SUCCESS);
9203dec9fcdSqs148142 }
9213dec9fcdSqs148142 
9223dec9fcdSqs148142 hpi_status_t
9233dec9fcdSqs148142 hpi_pfc_get_number_mac_addrs(hpi_handle_t handle, uint32_t *n_of_addrs)
9243dec9fcdSqs148142 {
9253dec9fcdSqs148142 	HXGE_REG_RD32(handle, HCR_REG + HCR_N_MAC_ADDRS, n_of_addrs);
9263dec9fcdSqs148142 	return (HPI_SUCCESS);
9273dec9fcdSqs148142 }
9283dec9fcdSqs148142 
9293dec9fcdSqs148142 hpi_status_t
9303dec9fcdSqs148142 hpi_pfc_mac_addr_get_i(hpi_handle_t handle, uint8_t *data, int slot)
9313dec9fcdSqs148142 {
9323dec9fcdSqs148142 	uint32_t step = sizeof (uint32_t);
9333dec9fcdSqs148142 	uint32_t addr_hi = 0, addr_lo = 0;
9343dec9fcdSqs148142 
9353dec9fcdSqs148142 	if (slot >= PFC_N_MAC_ADDRESSES)
9363dec9fcdSqs148142 		return (HPI_FAILURE);
9373dec9fcdSqs148142 
9383dec9fcdSqs148142 	/*
9393dec9fcdSqs148142 	 * Read the MAC address out of the SPROM at the blade's
9403dec9fcdSqs148142 	 * specific location.
9413dec9fcdSqs148142 	 */
9423dec9fcdSqs148142 	HXGE_REG_RD32(handle, HCR_REG + HCR_ADDR_LO + slot * step, &addr_lo);
9433dec9fcdSqs148142 	HXGE_REG_RD32(handle, HCR_REG + HCR_ADDR_HI + slot * step, &addr_hi);
9443dec9fcdSqs148142 
9453dec9fcdSqs148142 	data[0] = addr_lo & 0x000000ff;
9463dec9fcdSqs148142 	data[1] = (addr_lo & 0x0000ff00) >> 8;
9473dec9fcdSqs148142 	data[2] = (addr_lo & 0x00ff0000) >> 16;
9483dec9fcdSqs148142 	data[3] = (addr_lo & 0xff000000) >> 24;
949*63b1987dSQiyan Sun - Sun Microsystems - San Diego United States 	data[4] = (addr_hi & 0x0000000ff);
950*63b1987dSQiyan Sun - Sun Microsystems - San Diego United States 	data[5] = (addr_hi & 0x00000ff00) >> 8;
9513dec9fcdSqs148142 
9523dec9fcdSqs148142 	return (HPI_SUCCESS);
9533dec9fcdSqs148142 }
9543dec9fcdSqs148142 
9553dec9fcdSqs148142 hpi_status_t
9563dec9fcdSqs148142 hpi_pfc_num_macs_get(hpi_handle_t handle, uint8_t *data)
9573dec9fcdSqs148142 {
9583dec9fcdSqs148142 	uint8_t	addr[6];
9593dec9fcdSqs148142 	uint8_t	num = 0;
9603dec9fcdSqs148142 	int	i;
9613dec9fcdSqs148142 
9623dec9fcdSqs148142 	for (i = 0; i < 16; i++) {
9633dec9fcdSqs148142 		(void) hpi_pfc_mac_addr_get_i(handle, addr, i);
9643dec9fcdSqs148142 		if (addr[0] || addr[1] || addr[2] ||
9653dec9fcdSqs148142 		    addr[3] || addr[4] || addr[5])
9663dec9fcdSqs148142 			num++;
9673dec9fcdSqs148142 	}
9683dec9fcdSqs148142 
9693dec9fcdSqs148142 	*data = num;
9703dec9fcdSqs148142 
9713dec9fcdSqs148142 	return (HPI_SUCCESS);
9723dec9fcdSqs148142 }
973