⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 skaddr.c

📁 这是Marvell Technology Group Ltd. 4355 (rev 12)网卡在linux下的驱动程序源代码
💻 C
📖 第 1 页 / 共 3 页
字号:
/****************************************************************************** * * Name:	skaddr.c * Project:	Gigabit Ethernet Adapters, ADDR-Module * Version:	$Revision: 2.15 $ * Date:	$Date: 2008/04/02 10:42:40 $ * Purpose:	Manage Addresses (Multicast and Unicast) and Promiscuous Mode. * ******************************************************************************//****************************************************************************** * *	LICENSE: *	(C)Copyright Marvell. *	 *	This program is free software; you can redistribute it and/or modify *	it under the terms of the GNU General Public License as published by *	the Free Software Foundation; either version 2 of the License, or *	(at your option) any later version. *	 *	The information in this file is provided "AS IS" without warranty. *	/LICENSE * ******************************************************************************//****************************************************************************** * * Description: * * This module is intended to manage multicast addresses, address override, * and promiscuous mode on Yukon adapters. * * Address Layout: *	port address:		physical MAC address * * Include File Hierarchy: * *	"skdrv1st.h" *	"skdrv2nd.h" * ******************************************************************************/#if (defined(DEBUG) || ((!defined(LINT)) && (!defined(SK_SLIM))))static const char SysKonnectFileId[] =	"@(#) $Id: skaddr.c,v 2.15 2008/04/02 10:42:40 tschilli Exp $ (C) Marvell.";#endif /* DEBUG ||!LINT || !SK_SLIM */#define __SKADDR_C#ifdef __cplusplusextern "C" {#endif	/* cplusplus */#include "h/skdrv1st.h"#include "h/skdrv2nd.h"/* defines ********************************************************************/#define XMAC_POLY	0xEDB88320UL	/* CRC32-Poly - XMAC: Little Endian */#define GMAC_POLY	0x04C11DB7L	/* CRC16-Poly - GMAC: Little Endian */#define HASH_BITS	6				/* #bits in hash */#define SK_MC_BIT	0x01/* Error numbers and messages. */#define SKERR_ADDR_E001		(SK_ERRBASE_ADDR + 0)#define SKERR_ADDR_E001MSG	"Bad Flags."#define SKERR_ADDR_E002		(SKERR_ADDR_E001 + 1)#define SKERR_ADDR_E002MSG	"New Error."/* typedefs *******************************************************************//* None. *//* global variables ***********************************************************//* 64-bit hash values with all bits set. */SK_U16	OnesHash[4] = {0xffff, 0xffff, 0xffff, 0xffff};/* local variables ************************************************************/#ifdef DEBUGstatic int	Next0[SK_MAX_MACS] = {0};#endif	/* DEBUG *//* functions ******************************************************************//****************************************************************************** * *	SkAddrInit - initialize data, set state to init * * Description: * *	SK_INIT_DATA *	============ * *	This routine clears the multicast tables and resets promiscuous mode. *	Some entries are reserved for the "logical MAC address", the *	SK-RLMT multicast address, and the BPDU multicast address. * * *	SK_INIT_IO *	========== * *	All permanent MAC addresses are read from EPROM. *	If the current MAC addresses are not already set in software, *	they are set to the values of the permanent addresses. *	The current addresses are written to the corresponding MAC. * * *	SK_INIT_RUN *	=========== * *	Nothing. * * Context: *	init, pageable * * Returns: *	SK_ADDR_SUCCESS */int	SkAddrInit(SK_AC	*pAC,	/* the adapter context */SK_IOC	IoC,	/* I/O context */int		Level)	/* initialization level */{	int			j;	SK_U32		i;	SK_U8		*InAddr;	SK_U16		*OutAddr;	SK_ADDR_PORT	*pAPort;	switch (Level) {	case SK_INIT_DATA:		SK_MEMSET((char *)&pAC->Addr, (SK_U8)0, (SK_U16)sizeof(SK_ADDR));		for (i = 0; i < SK_MAX_MACS; i++) {			pAPort = &pAC->Addr.Port[i];			pAPort->PromMode = SK_PROM_MODE_NONE;			pAPort->FirstExactMatchRlmt = SK_ADDR_FIRST_MATCH_RLMT;			pAPort->FirstExactMatchDrv = SK_ADDR_FIRST_MATCH_DRV;			pAPort->NextExactMatchRlmt = SK_ADDR_FIRST_MATCH_RLMT;			pAPort->NextExactMatchDrv = SK_ADDR_FIRST_MATCH_DRV;		}#ifdef xDEBUG		for (i = 0; i < SK_MAX_MACS; i++) {			if (pAC->Addr.Port[i].NextExactMatchRlmt <				SK_ADDR_FIRST_MATCH_RLMT) {				Next0[i] |= 4;			}		}#endif	/* DEBUG */		/* pAC->Addr.InitDone = SK_INIT_DATA; */		break;	case SK_INIT_IO:#ifndef SK_NO_RLMT		for (i = 0; i < SK_MAX_NETS; i++) {			pAC->Addr.Net[i].ActivePort = pAC->Rlmt.Net[i].ActivePort;		}#endif /* !SK_NO_RLMT */#ifdef xDEBUG		for (i = 0; i < SK_MAX_MACS; i++) {			if (pAC->Addr.Port[i].NextExactMatchRlmt <				SK_ADDR_FIRST_MATCH_RLMT) {				Next0[i] |= 8;			}		}#endif	/* DEBUG */		/* Read permanent logical MAC address from Control Register File. */		for (j = 0; j < SK_MAC_ADDR_LEN; j++) {			InAddr = (SK_U8 *) &pAC->Addr.Net[0].PermanentMacAddress.a[j];			SK_IN8(IoC, B2_MAC_1 + j, InAddr);		}		if (!pAC->Addr.Net[0].CurrentMacAddressSet) {			/* Set the current logical MAC address to the permanent one. */			pAC->Addr.Net[0].CurrentMacAddress =				pAC->Addr.Net[0].PermanentMacAddress;			pAC->Addr.Net[0].CurrentMacAddressSet = SK_TRUE;		}		/* Set the current logical MAC address. */		pAC->Addr.Port[pAC->Addr.Net[0].ActivePort].Exact[0] =			pAC->Addr.Net[0].CurrentMacAddress;#if SK_MAX_NETS > 1		/* Set logical MAC address for net 2 to. */		if (!pAC->Addr.Net[1].CurrentMacAddressSet) {			pAC->Addr.Net[1].PermanentMacAddress =				pAC->Addr.Net[0].PermanentMacAddress;			pAC->Addr.Net[1].PermanentMacAddress.a[5] += 1;			/* Set the current logical MAC address to the permanent one. */			pAC->Addr.Net[1].CurrentMacAddress =				pAC->Addr.Net[1].PermanentMacAddress;			pAC->Addr.Net[1].CurrentMacAddressSet = SK_TRUE;		}#endif	/* SK_MAX_NETS > 1 */#ifdef DEBUG		for (i = 0; i < (SK_U32) pAC->GIni.GIMacsFound; i++) {			SK_DBG_MSG(pAC, SK_DBGMOD_ADDR, SK_DBGCAT_INIT,				("Permanent MAC Address (Net%d): %02X %02X %02X %02X %02X %02X\n",					i,					pAC->Addr.Net[i].PermanentMacAddress.a[0],					pAC->Addr.Net[i].PermanentMacAddress.a[1],					pAC->Addr.Net[i].PermanentMacAddress.a[2],					pAC->Addr.Net[i].PermanentMacAddress.a[3],					pAC->Addr.Net[i].PermanentMacAddress.a[4],					pAC->Addr.Net[i].PermanentMacAddress.a[5]));			SK_DBG_MSG(pAC, SK_DBGMOD_ADDR, SK_DBGCAT_INIT,				("Logical MAC Address (Net%d): %02X %02X %02X %02X %02X %02X\n",					i,					pAC->Addr.Net[i].CurrentMacAddress.a[0],					pAC->Addr.Net[i].CurrentMacAddress.a[1],					pAC->Addr.Net[i].CurrentMacAddress.a[2],					pAC->Addr.Net[i].CurrentMacAddress.a[3],					pAC->Addr.Net[i].CurrentMacAddress.a[4],					pAC->Addr.Net[i].CurrentMacAddress.a[5]));		}#endif	/* DEBUG */		for (i = 0; i < (SK_U32) pAC->GIni.GIMacsFound; i++) {			pAPort = &pAC->Addr.Port[i];			/* Read permanent port addresses from Control Register File. */			for (j = 0; j < SK_MAC_ADDR_LEN; j++) {				InAddr = (SK_U8 *) &pAPort->PermanentMacAddress.a[j];				SK_IN8(IoC, B2_MAC_2 + 8 * i + j, InAddr);			}			if (!pAPort->CurrentMacAddressSet) {				/*				 * Set the current and previous physical MAC address				 * of this port to its permanent MAC address.				 */				pAPort->CurrentMacAddress = pAPort->PermanentMacAddress;				pAPort->PreviousMacAddress = pAPort->PermanentMacAddress;				pAPort->CurrentMacAddressSet = SK_TRUE;			}			/* Set port's current physical MAC address. */			OutAddr = (SK_U16 *) &pAPort->CurrentMacAddress.a[0];			GM_OUTADDR(IoC, i, GM_SRC_ADDR_1L, OutAddr);#ifdef DEBUG			SK_DBG_MSG(pAC, SK_DBGMOD_ADDR, SK_DBGCAT_INIT,				("SkAddrInit: Permanent Physical MAC Address: %02X %02X %02X %02X %02X %02X\n",					pAPort->PermanentMacAddress.a[0],					pAPort->PermanentMacAddress.a[1],					pAPort->PermanentMacAddress.a[2],					pAPort->PermanentMacAddress.a[3],					pAPort->PermanentMacAddress.a[4],					pAPort->PermanentMacAddress.a[5]));			SK_DBG_MSG(pAC, SK_DBGMOD_ADDR, SK_DBGCAT_INIT,				("SkAddrInit: Physical MAC Address: %02X %02X %02X %02X %02X %02X\n",					pAPort->CurrentMacAddress.a[0],					pAPort->CurrentMacAddress.a[1],					pAPort->CurrentMacAddress.a[2],					pAPort->CurrentMacAddress.a[3],					pAPort->CurrentMacAddress.a[4],					pAPort->CurrentMacAddress.a[5]));#endif /* DEBUG */		}		/* pAC->Addr.InitDone = SK_INIT_IO; */		break;	case SK_INIT_RUN:#ifdef xDEBUG		for (i = 0; i < SK_MAX_MACS; i++) {			if (pAC->Addr.Port[i].NextExactMatchRlmt <				SK_ADDR_FIRST_MATCH_RLMT) {				Next0[i] |= 16;			}		}#endif	/* DEBUG */		/* pAC->Addr.InitDone = SK_INIT_RUN; */		break;	default:	/* error */		break;	}	return (SK_ADDR_SUCCESS);}	/* SkAddrInit */#ifndef SK_SLIM/****************************************************************************** * *	SkAddrMcClear - clear the multicast table * * Description: *	This routine clears the multicast table. * *	If not suppressed by Flag SK_MC_SW_ONLY, the hardware is updated *	immediately. * *	It calls either SkAddrXmacMcClear or SkAddrGmacMcClear, according *	to the adapter in use. The real work is done there. * * Context: *	runtime, pageable *	may be called starting with SK_INIT_DATA with flag SK_MC_SW_ONLY *	may be called after SK_INIT_IO without limitation * * Returns: *	SK_ADDR_SUCCESS *	SK_ADDR_ILLEGAL_PORT */int	SkAddrMcClear(SK_AC	*pAC,		/* adapter context */SK_IOC	IoC,		/* I/O context */SK_U32	PortNumber,	/* Index of affected port */int		Flags)		/* permanent/non-perm, sw-only */{	int ReturnCode;	if (PortNumber >= (SK_U32) pAC->GIni.GIMacsFound) {		return (SK_ADDR_ILLEGAL_PORT);	}	ReturnCode = SkAddrGmacMcClear(pAC, IoC, PortNumber, Flags);	return (ReturnCode);}	/* SkAddrMcClear *//****************************************************************************** * *	SkAddrGmacMcClear - clear the multicast table * * Description: *	This routine clears the multicast hashing table (InexactFilter) *	(either the RLMT or the driver bits) of the given port. * *	If not suppressed by Flag SK_MC_SW_ONLY, the hardware is updated *	immediately. * * Context: *	runtime, pageable *	may be called starting with SK_INIT_DATA with flag SK_MC_SW_ONLY *	may be called after SK_INIT_IO without limitation * * Returns: *	SK_ADDR_SUCCESS *	SK_ADDR_ILLEGAL_PORT */int	SkAddrGmacMcClear(SK_AC	*pAC,		/* adapter context */SK_IOC	IoC,		/* I/O context */SK_U32	PortNumber,	/* Index of affected port */int		Flags)		/* permanent/non-perm, sw-only */{	int i;#ifdef DEBUG	SK_DBG_MSG(pAC, SK_DBGMOD_ADDR, SK_DBGCAT_CTRL,		("GMAC InexactFilter (not cleared): %02X %02X %02X %02X %02X %02X %02X %02X\n",			pAC->Addr.Port[PortNumber].InexactFilter.Bytes[0],			pAC->Addr.Port[PortNumber].InexactFilter.Bytes[1],			pAC->Addr.Port[PortNumber].InexactFilter.Bytes[2],			pAC->Addr.Port[PortNumber].InexactFilter.Bytes[3],			pAC->Addr.Port[PortNumber].InexactFilter.Bytes[4],			pAC->Addr.Port[PortNumber].InexactFilter.Bytes[5],			pAC->Addr.Port[PortNumber].InexactFilter.Bytes[6],			pAC->Addr.Port[PortNumber].InexactFilter.Bytes[7]));#endif	/* DEBUG */	/* Clear InexactFilter */	for (i = 0; i < 8; i++) {		pAC->Addr.Port[PortNumber].InexactFilter.Bytes[i] = 0;	}	if (Flags & SK_ADDR_PERMANENT) {	/* permanent => RLMT */		/* Copy DRV bits to InexactFilter. */		for (i = 0; i < 8; i++) {			pAC->Addr.Port[PortNumber].InexactFilter.Bytes[i] |=				pAC->Addr.Port[PortNumber].InexactDrvFilter.Bytes[i];			/* Clear InexactRlmtFilter. */			pAC->Addr.Port[PortNumber].InexactRlmtFilter.Bytes[i] = 0;		}	}	else {	/* not permanent => DRV */		/* Copy RLMT bits to InexactFilter. */		for (i = 0; i < 8; i++) {			pAC->Addr.Port[PortNumber].InexactFilter.Bytes[i] |=				pAC->Addr.Port[PortNumber].InexactRlmtFilter.Bytes[i];			/* Clear InexactDrvFilter. */			pAC->Addr.Port[PortNumber].InexactDrvFilter.Bytes[i] = 0;		}	}#ifdef DEBUG	SK_DBG_MSG(pAC, SK_DBGMOD_ADDR, SK_DBGCAT_CTRL,		("GMAC InexactFilter (cleared): %02X %02X %02X %02X %02X %02X %02X %02X\n",			pAC->Addr.Port[PortNumber].InexactFilter.Bytes[0],			pAC->Addr.Port[PortNumber].InexactFilter.Bytes[1],			pAC->Addr.Port[PortNumber].InexactFilter.Bytes[2],			pAC->Addr.Port[PortNumber].InexactFilter.Bytes[3],			pAC->Addr.Port[PortNumber].InexactFilter.Bytes[4],			pAC->Addr.Port[PortNumber].InexactFilter.Bytes[5],			pAC->Addr.Port[PortNumber].InexactFilter.Bytes[6],			pAC->Addr.Port[PortNumber].InexactFilter.Bytes[7]));

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -