xref: /onnv-gate/usr/src/uts/common/io/ntxn/unm_nic_isr.c (revision 8687:5dca9cd6354a)
17956Sxiuyan.wang@Sun.COM /*
27956Sxiuyan.wang@Sun.COM  * CDDL HEADER START
37956Sxiuyan.wang@Sun.COM  *
47956Sxiuyan.wang@Sun.COM  * The contents of this file are subject to the terms of the
57956Sxiuyan.wang@Sun.COM  * Common Development and Distribution License (the "License").
67956Sxiuyan.wang@Sun.COM  * You may not use this file except in compliance with the License.
77956Sxiuyan.wang@Sun.COM  *
87956Sxiuyan.wang@Sun.COM  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
97956Sxiuyan.wang@Sun.COM  * or http://www.opensolaris.org/os/licensing.
107956Sxiuyan.wang@Sun.COM  * See the License for the specific language governing permissions
117956Sxiuyan.wang@Sun.COM  * and limitations under the License.
127956Sxiuyan.wang@Sun.COM  *
137956Sxiuyan.wang@Sun.COM  * When distributing Covered Code, include this CDDL HEADER in each
147956Sxiuyan.wang@Sun.COM  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
157956Sxiuyan.wang@Sun.COM  * If applicable, add the following below this CDDL HEADER, with the
167956Sxiuyan.wang@Sun.COM  * fields enclosed by brackets "[]" replaced with your own identifying
177956Sxiuyan.wang@Sun.COM  * information: Portions Copyright [yyyy] [name of copyright owner]
187956Sxiuyan.wang@Sun.COM  *
197956Sxiuyan.wang@Sun.COM  * CDDL HEADER END
207956Sxiuyan.wang@Sun.COM  */
21*8687SJing.Xiong@Sun.COM 
227956Sxiuyan.wang@Sun.COM /*
237956Sxiuyan.wang@Sun.COM  * Copyright 2008 NetXen, Inc.  All rights reserved.
247956Sxiuyan.wang@Sun.COM  * Use is subject to license terms.
257956Sxiuyan.wang@Sun.COM  */
26*8687SJing.Xiong@Sun.COM 
277956Sxiuyan.wang@Sun.COM #include <sys/types.h>
287956Sxiuyan.wang@Sun.COM #include <sys/conf.h>
297956Sxiuyan.wang@Sun.COM #include <sys/debug.h>
307956Sxiuyan.wang@Sun.COM #include <sys/stropts.h>
317956Sxiuyan.wang@Sun.COM #include <sys/stream.h>
327956Sxiuyan.wang@Sun.COM #include <sys/strlog.h>
337956Sxiuyan.wang@Sun.COM #include <sys/kmem.h>
347956Sxiuyan.wang@Sun.COM #include <sys/stat.h>
357956Sxiuyan.wang@Sun.COM #include <sys/kstat.h>
367956Sxiuyan.wang@Sun.COM #include <sys/vtrace.h>
377956Sxiuyan.wang@Sun.COM #include <sys/dlpi.h>
387956Sxiuyan.wang@Sun.COM #include <sys/strsun.h>
397956Sxiuyan.wang@Sun.COM #include <sys/ethernet.h>
407956Sxiuyan.wang@Sun.COM #include <sys/modctl.h>
417956Sxiuyan.wang@Sun.COM #include <sys/errno.h>
427956Sxiuyan.wang@Sun.COM #include <sys/dditypes.h>
437956Sxiuyan.wang@Sun.COM #include <sys/ddi.h>
447956Sxiuyan.wang@Sun.COM #include <sys/sunddi.h>
457956Sxiuyan.wang@Sun.COM #include <sys/sysmacros.h>
467956Sxiuyan.wang@Sun.COM 
477956Sxiuyan.wang@Sun.COM #include <sys/pci.h>
487956Sxiuyan.wang@Sun.COM 
497956Sxiuyan.wang@Sun.COM #include "unm_nic.h"
507956Sxiuyan.wang@Sun.COM #include "unm_nic_hw.h"
517956Sxiuyan.wang@Sun.COM #include "nic_cmn.h"
527956Sxiuyan.wang@Sun.COM #include "nic_phan_reg.h"
537956Sxiuyan.wang@Sun.COM 
547956Sxiuyan.wang@Sun.COM static void
unm_nic_isr_other(struct unm_adapter_s * adapter)557956Sxiuyan.wang@Sun.COM unm_nic_isr_other(struct unm_adapter_s *adapter)
567956Sxiuyan.wang@Sun.COM {
577956Sxiuyan.wang@Sun.COM 	u32 portno = adapter->portnum;
587956Sxiuyan.wang@Sun.COM 	u32 val, linkup, qg_linksup = adapter->ahw.linkup;
597956Sxiuyan.wang@Sun.COM 
607956Sxiuyan.wang@Sun.COM 	UNM_READ_LOCK(&adapter->adapter_lock);
617956Sxiuyan.wang@Sun.COM 	adapter->unm_nic_hw_read_wx(adapter, CRB_XG_STATE, &val, 4);
627956Sxiuyan.wang@Sun.COM 	UNM_READ_UNLOCK(&adapter->adapter_lock);
637956Sxiuyan.wang@Sun.COM 
647956Sxiuyan.wang@Sun.COM 	linkup = 1 & (val >> adapter->physical_port);
657956Sxiuyan.wang@Sun.COM 	adapter->ahw.linkup = linkup;
667956Sxiuyan.wang@Sun.COM 
677956Sxiuyan.wang@Sun.COM 	if (linkup != qg_linksup) {
687956Sxiuyan.wang@Sun.COM 		cmn_err(CE_WARN, "%s: PORT %d link %s\n", unm_nic_driver_name,
697956Sxiuyan.wang@Sun.COM 		    portno, ((linkup == 0) ? "down" : "up"));
707956Sxiuyan.wang@Sun.COM 		mac_link_update(adapter->mach, linkup);
717956Sxiuyan.wang@Sun.COM 		if (linkup)
727956Sxiuyan.wang@Sun.COM 			unm_nic_set_link_parameters(adapter);
737956Sxiuyan.wang@Sun.COM 	}
747956Sxiuyan.wang@Sun.COM }
757956Sxiuyan.wang@Sun.COM 
767956Sxiuyan.wang@Sun.COM void
unm_nic_handle_phy_intr(struct unm_adapter_s * adapter)777956Sxiuyan.wang@Sun.COM unm_nic_handle_phy_intr(struct unm_adapter_s *adapter)
787956Sxiuyan.wang@Sun.COM {
797956Sxiuyan.wang@Sun.COM 	uint32_t	val, val1, linkupval;
807956Sxiuyan.wang@Sun.COM 
817956Sxiuyan.wang@Sun.COM 	switch (adapter->ahw.board_type) {
827956Sxiuyan.wang@Sun.COM 		case UNM_NIC_GBE:
837956Sxiuyan.wang@Sun.COM 			if (NX_IS_REVISION_P2(adapter->ahw.revision_id)) {
847956Sxiuyan.wang@Sun.COM 				unm_nic_isr_other(adapter);
857956Sxiuyan.wang@Sun.COM 				break;
867956Sxiuyan.wang@Sun.COM 			}
877956Sxiuyan.wang@Sun.COM 		/* FALLTHROUGH */
887956Sxiuyan.wang@Sun.COM 
897956Sxiuyan.wang@Sun.COM 		case UNM_NIC_XGBE:
907956Sxiuyan.wang@Sun.COM 			/* WINDOW = 1 */
917956Sxiuyan.wang@Sun.COM 		UNM_READ_LOCK(&adapter->adapter_lock);
927956Sxiuyan.wang@Sun.COM 		if (NX_IS_REVISION_P3(adapter->ahw.revision_id)) {
937956Sxiuyan.wang@Sun.COM 			adapter->unm_nic_hw_read_wx(adapter, CRB_XG_STATE_P3,
947956Sxiuyan.wang@Sun.COM 			    &val, 4);
957956Sxiuyan.wang@Sun.COM 			val1 = XG_LINK_STATE_P3(adapter->ahw.pci_func, val);
967956Sxiuyan.wang@Sun.COM 			linkupval = XG_LINK_UP_P3;
977956Sxiuyan.wang@Sun.COM 		} else {
987956Sxiuyan.wang@Sun.COM 			adapter->unm_nic_hw_read_wx(adapter, CRB_XG_STATE,
997956Sxiuyan.wang@Sun.COM 			    &val, 4);
1007956Sxiuyan.wang@Sun.COM 			val >>= (adapter->portnum * 8);
1017956Sxiuyan.wang@Sun.COM 			val1 = val & 0xff;
1027956Sxiuyan.wang@Sun.COM 			linkupval = XG_LINK_UP;
1037956Sxiuyan.wang@Sun.COM 		}
1047956Sxiuyan.wang@Sun.COM 		UNM_READ_UNLOCK(&adapter->adapter_lock);
1057956Sxiuyan.wang@Sun.COM 
1067956Sxiuyan.wang@Sun.COM 		if (adapter->ahw.linkup && (val1 != linkupval)) {
1077956Sxiuyan.wang@Sun.COM 			if (verbmsg != 0)
1087956Sxiuyan.wang@Sun.COM 				cmn_err(CE_NOTE, "%s%d: NIC Link is down\n",
1097956Sxiuyan.wang@Sun.COM 				    adapter->name, adapter->portnum);
1107956Sxiuyan.wang@Sun.COM 			mac_link_update(adapter->mach, LINK_STATE_DOWN);
1117956Sxiuyan.wang@Sun.COM 			adapter->ahw.linkup = 0;
1127956Sxiuyan.wang@Sun.COM 		} else if ((adapter->ahw.linkup == 0) && (val1 == linkupval)) {
1137956Sxiuyan.wang@Sun.COM 			if (verbmsg != 0)
1147956Sxiuyan.wang@Sun.COM 				cmn_err(CE_NOTE, "%s%d: NIC Link is up\n",
1157956Sxiuyan.wang@Sun.COM 				    adapter->name, adapter->portnum);
1167956Sxiuyan.wang@Sun.COM 			mac_link_update(adapter->mach, LINK_STATE_UP);
1177956Sxiuyan.wang@Sun.COM 			adapter->ahw.linkup = 1;
1187956Sxiuyan.wang@Sun.COM 
1197956Sxiuyan.wang@Sun.COM 			if (adapter->ahw.board_type == UNM_NIC_GBE)
1207956Sxiuyan.wang@Sun.COM 				unm_nic_set_link_parameters(adapter);
1217956Sxiuyan.wang@Sun.COM 		}
1227956Sxiuyan.wang@Sun.COM 
1237956Sxiuyan.wang@Sun.COM 		break;
1247956Sxiuyan.wang@Sun.COM 
1257956Sxiuyan.wang@Sun.COM 		default:
1267956Sxiuyan.wang@Sun.COM 		DPRINTF(0, (CE_WARN, "%s%d ISR: Unknown board type\n",
1277956Sxiuyan.wang@Sun.COM 		    unm_nic_driver_name, adapter->portnum));
1287956Sxiuyan.wang@Sun.COM 	}
1297956Sxiuyan.wang@Sun.COM }
130