📄 skaddr.c
字号:
int Flags) /* logical/physical MAC address */{#ifndef SK_NO_RLMT SK_EVPARA Para;#endif /* !SK_NO_RLMT */ SK_U32 NetNumber; SK_U32 i; SK_U16 SK_FAR *OutAddr;#ifndef SK_NO_RLMT NetNumber = pAC->Rlmt.Port[PortNumber].Net->NetNumber;#else NetNumber = 0;#endif /* SK_NO_RLMT */#if (!defined(SK_SLIM) || defined(DEBUG)) if (PortNumber >= (SK_U32) pAC->GIni.GIMacsFound) { return (SK_ADDR_ILLEGAL_PORT); }#endif /* !SK_SLIM || DEBUG */ if (pNewAddr != NULL && (pNewAddr->a[0] & SK_MC_BIT) != 0) { return (SK_ADDR_MULTICAST_ADDRESS); } if (!pAC->Addr.Net[NetNumber].CurrentMacAddressSet) { return (SK_ADDR_TOO_EARLY); } if (Flags & SK_ADDR_SET_LOGICAL) { /* Activate logical MAC address. */ /* Parameter *pNewAddr is ignored. */ for (i = 0; i < (SK_U32) pAC->GIni.GIMacsFound; i++) { if (!pAC->Addr.Port[i].CurrentMacAddressSet) { return (SK_ADDR_TOO_EARLY); } }#ifndef SK_NO_RLMT /* Set PortNumber to number of net's active port. */ PortNumber = pAC->Rlmt.Net[NetNumber]. Port[pAC->Addr.Net[NetNumber].ActivePort]->PortNumber;#endif /* !SK_NO_RLMT */ pAC->Addr.Port[PortNumber].Exact[0] = pAC->Addr.Net[NetNumber].CurrentMacAddress; /* Write address to first exact match entry of active port. */ (void) SkAddrMcUpdate(pAC, IoC, PortNumber); } else if (Flags & SK_ADDR_CLEAR_LOGICAL) { /* Deactivate logical MAC address. */ /* Parameter *pNewAddr is ignored. */ for (i = 0; i < (SK_U32) pAC->GIni.GIMacsFound; i++) { if (!pAC->Addr.Port[i].CurrentMacAddressSet) { return (SK_ADDR_TOO_EARLY); } }#ifndef SK_NO_RLMT /* Set PortNumber to number of net's active port. */ PortNumber = pAC->Rlmt.Net[NetNumber]. Port[pAC->Addr.Net[NetNumber].ActivePort]->PortNumber;#endif /* !SK_NO_RLMT */ for (i = 0; i < SK_MAC_ADDR_LEN; i++ ) { pAC->Addr.Port[PortNumber].Exact[0].a[i] = 0; } /* Write address to first exact match entry of active port. */ (void) SkAddrMcUpdate(pAC, IoC, PortNumber); } else if (pNewAddr == NULL) { /* Prevent accessing a NULL pointer (was complained by Prefast) */ return (SK_MC_ILLEGAL_ADDRESS); } else { if (Flags & SK_ADDR_PHYSICAL_ADDRESS) { /* Physical MAC address. */ for (i = 0; i < (SK_U32) pAC->GIni.GIMacsFound; i++) { if (!pAC->Addr.Port[i].CurrentMacAddressSet) { return (SK_ADDR_TOO_EARLY); } } /* * In dual net mode it should be possible to set all MAC * addresses independently. Therefore the equality checks * against the locical address of the same port and the * physical address of the other port are suppressed here. */#ifndef SK_NO_RLMT if (pAC->Rlmt.NumNets == 1) {#endif /* SK_NO_RLMT */ if (SK_ADDR_EQUAL(pNewAddr->a, pAC->Addr.Net[NetNumber].CurrentMacAddress.a)) { return (SK_ADDR_DUPLICATE_ADDRESS); } for (i = 0; i < (SK_U32) pAC->GIni.GIMacsFound; i++) { if (SK_ADDR_EQUAL(pNewAddr->a, pAC->Addr.Port[i].CurrentMacAddress.a)) { if (i == PortNumber) { return (SK_ADDR_SUCCESS); } else { return (SK_ADDR_DUPLICATE_ADDRESS); } } }#ifndef SK_NO_RLMT } else { if (SK_ADDR_EQUAL(pNewAddr->a, pAC->Addr.Port[PortNumber].CurrentMacAddress.a)) { return (SK_ADDR_SUCCESS); } }#endif /* SK_NO_RLMT */ pAC->Addr.Port[PortNumber].PreviousMacAddress = pAC->Addr.Port[PortNumber].CurrentMacAddress; pAC->Addr.Port[PortNumber].CurrentMacAddress = *pNewAddr; /* Change port's physical MAC address. */ OutAddr = (SK_U16 SK_FAR *) pNewAddr; GM_OUTADDR(IoC, PortNumber, GM_SRC_ADDR_1L, OutAddr);#ifndef SK_NO_RLMT /* Report address change to RLMT. */ Para.Para32[0] = PortNumber; Para.Para32[0] = -1; SkEventQueue(pAC, SKGE_RLMT, SK_RLMT_PORT_ADDR, Para);#endif /* !SK_NO_RLMT */ } else { /* Logical MAC address. */ if (SK_ADDR_EQUAL(pNewAddr->a, pAC->Addr.Net[NetNumber].CurrentMacAddress.a)) { return (SK_ADDR_SUCCESS); } for (i = 0; i < (SK_U32) pAC->GIni.GIMacsFound; i++) { if (!pAC->Addr.Port[i].CurrentMacAddressSet) { return (SK_ADDR_TOO_EARLY); } } /* * In dual net mode on Yukon-2 adapters the physical address * of port 0 and the logical address of port 1 are equal - in * this case the equality check of the physical address leads * to an error and is suppressed here. */#ifndef SK_NO_RLMT if (pAC->Rlmt.NumNets == 1) {#endif /* SK_NO_RLMT */ for (i = 0; i < (SK_U32) pAC->GIni.GIMacsFound; i++) { if (SK_ADDR_EQUAL(pNewAddr->a, pAC->Addr.Port[i].CurrentMacAddress.a)) { return (SK_ADDR_DUPLICATE_ADDRESS); } }#ifndef SK_NO_RLMT }#endif /* SK_NO_RLMT */ /* * In case that the physical and the logical MAC addresses are equal * we must also change the physical MAC address here. * In this case we have an adapter which initially was programmed with * two identical MAC addresses. */ if (SK_ADDR_EQUAL(pAC->Addr.Port[PortNumber].CurrentMacAddress.a, pAC->Addr.Port[PortNumber].Exact[0].a)) { pAC->Addr.Port[PortNumber].PreviousMacAddress = pAC->Addr.Port[PortNumber].CurrentMacAddress; pAC->Addr.Port[PortNumber].CurrentMacAddress = *pNewAddr;#ifndef SK_NO_RLMT /* Report address change to RLMT. */ Para.Para32[0] = PortNumber; Para.Para32[0] = -1; SkEventQueue(pAC, SKGE_RLMT, SK_RLMT_PORT_ADDR, Para);#endif /* !SK_NO_RLMT */ }#ifndef SK_NO_RLMT /* Set PortNumber to number of net's active port. */ PortNumber = pAC->Rlmt.Net[NetNumber]. Port[pAC->Addr.Net[NetNumber].ActivePort]->PortNumber;#endif /* !SK_NO_RLMT */ pAC->Addr.Net[NetNumber].CurrentMacAddress = *pNewAddr; pAC->Addr.Port[PortNumber].Exact[0] = *pNewAddr;#ifdef DEBUG SK_DBG_MSG(pAC,SK_DBGMOD_ADDR, SK_DBGCAT_CTRL, ("SkAddrOverride: Permanent MAC Address: %02X %02X %02X %02X %02X %02X\n", pAC->Addr.Net[NetNumber].PermanentMacAddress.a[0], pAC->Addr.Net[NetNumber].PermanentMacAddress.a[1], pAC->Addr.Net[NetNumber].PermanentMacAddress.a[2], pAC->Addr.Net[NetNumber].PermanentMacAddress.a[3], pAC->Addr.Net[NetNumber].PermanentMacAddress.a[4], pAC->Addr.Net[NetNumber].PermanentMacAddress.a[5])); SK_DBG_MSG(pAC,SK_DBGMOD_ADDR, SK_DBGCAT_CTRL, ("SkAddrOverride: New logical MAC Address: %02X %02X %02X %02X %02X %02X\n", pAC->Addr.Net[NetNumber].CurrentMacAddress.a[0], pAC->Addr.Net[NetNumber].CurrentMacAddress.a[1], pAC->Addr.Net[NetNumber].CurrentMacAddress.a[2], pAC->Addr.Net[NetNumber].CurrentMacAddress.a[3], pAC->Addr.Net[NetNumber].CurrentMacAddress.a[4], pAC->Addr.Net[NetNumber].CurrentMacAddress.a[5]));#endif /* DEBUG */ /* Write address to first exact match entry of active port. */ (void)SkAddrMcUpdate(pAC, IoC, PortNumber); } } return (SK_ADDR_SUCCESS);} /* SkAddrOverride */#endif /* SK_NO_MAO *//****************************************************************************** * * SkAddrPromiscuousChange - set promiscuous mode for given port * * Description: * This routine manages promiscuous mode: * - none * - all LLC frames * - all MC frames * * It calls either SkAddrXmacPromiscuousChange or * SkAddrGmacPromiscuousChange, according to the adapter in use. * The real work is done there. * * Context: * runtime, pageable * may be called after SK_INIT_IO * * Returns: * SK_ADDR_SUCCESS * SK_ADDR_ILLEGAL_PORT */int SkAddrPromiscuousChange(SK_AC *pAC, /* adapter context */SK_IOC IoC, /* I/O context */SK_U32 PortNumber, /* port whose promiscuous mode changes */int NewPromMode) /* new promiscuous mode */{ int ReturnCode = SK_ADDR_ILLEGAL_PORT;#if (!defined(SK_SLIM) || defined(DEBUG)) if (PortNumber >= (SK_U32) pAC->GIni.GIMacsFound) { return (SK_ADDR_ILLEGAL_PORT); }#endif /* !SK_SLIM || DEBUG */ ReturnCode = SkAddrGmacPromiscuousChange(pAC, IoC, PortNumber, NewPromMode); return (ReturnCode);} /* SkAddrPromiscuousChange *//****************************************************************************** * * SkAddrGmacPromiscuousChange - set promiscuous mode for given port * * Description: * This routine manages promiscuous mode: * - none * - all LLC frames * - all MC frames * * Context: * runtime, pageable * may be called after SK_INIT_IO * * Returns: * SK_ADDR_SUCCESS * SK_ADDR_ILLEGAL_PORT */int SkAddrGmacPromiscuousChange(SK_AC *pAC, /* adapter context */SK_IOC IoC, /* I/O context */SK_U32 PortNumber, /* port whose promiscuous mode changes */int NewPromMode) /* new promiscuous mode */{ if (PortNumber >= (SK_U32)pAC->GIni.GIMacsFound) { return (SK_ADDR_ILLEGAL_PORT); } pAC->Addr.Port[PortNumber].PromMode = NewPromMode; switch(NewPromMode) { case (SK_PROM_MODE_NONE): /* 0 */ /* Normal receive mode */ SkMacPromiscMode(pAC, IoC, (int) PortNumber, SK_FALSE); break; case (SK_PROM_MODE_LLC): /* 1 */ /* This mode is ignored and mapped to prom. mode */ case (SK_PROM_MODE_LLC | SK_PROM_MODE_ALL_MC): /* 3 */ /* Set the MAC to promiscuous mode. */ SkMacPromiscMode(pAC, IoC, (int) PortNumber, SK_TRUE); break; case (SK_PROM_MODE_ALL_MC): /* 2 */ /* Disable MC hashing */ SkMacHashing(pAC, IoC, (int) PortNumber, SK_FALSE); break; default: break; } return (SK_ADDR_SUCCESS);} /* SkAddrGmacPromiscuousChange */#ifndef SK_SLIM/****************************************************************************** * * SkAddrSwap - swap address info * * Description: * This routine swaps address info of two ports. * * Context: * runtime, pageable * may be called after SK_INIT_IO * * Returns: * SK_ADDR_SUCCESS * SK_ADDR_ILLEGAL_PORT */int SkAddrSwap(SK_AC *pAC, /* adapter context */SK_IOC IoC, /* I/O context */SK_U32 FromPortNumber, /* Port1 Index */SK_U32 ToPortNumber) /* Port2 Index */{ int i; SK_U8 Byte; SK_MAC_ADDR MacAddr; if (FromPortNumber >= (SK_U32) pAC->GIni.GIMacsFound) { return (SK_ADDR_ILLEGAL_PORT); } if (ToPortNumber >= (SK_U32) pAC->GIni.GIMacsFound) { return (SK_ADDR_ILLEGAL_PORT); } if (pAC->Rlmt.Port[FromPortNumber].Net != pAC->Rlmt.Port[ToPortNumber].Net) { return (SK_ADDR_ILLEGAL_PORT); } /* * Swap: * - Exact Match Entries: * Yukon uses first entry for the logical MAC * address (stored in the second GMAC register). * - 64-bit filter (InexactFilter) * - Promiscuous Mode * of ports. */ for (i = 0; i < SK_ADDR_EXACT_MATCHES; i++) { MacAddr = pAC->Addr.Port[FromPortNumber].Exact[i]; pAC->Addr.Port[FromPortNumber].Exact[i] = pAC->Addr.Port[ToPortNumber].Exact[i]; pAC->Addr.Port[ToPortNumber].Exact[i] = MacAddr; } for (i = 0; i < 8; i++) { Byte = pAC->Addr.Port[FromPortNumber].InexactFilter.Bytes[i]; pAC->Addr.Port[FromPortNumber].InexactFilter.Bytes[i] = pAC->Addr.Port[ToPortNumber].InexactFilter.Bytes[i]; pAC->Addr.Port[ToPortNumber].InexactFilter.Bytes[i] = Byte; } i = pAC->Addr.Port[FromPortNumber].PromMode; pAC->Addr.Port[FromPortNumber].PromMode = pAC->Addr.Port[ToPortNumber].PromMode; pAC->Addr.Port[ToPortNumber].PromMode = i; /* CAUTION: Solution works if only ports of one adapter are in use. */ for (i = 0; (SK_U32) i < pAC->Rlmt.Net[pAC->Rlmt.Port[ToPortNumber]. Net->NetNumber].NumPorts; i++) { if (pAC->Rlmt.Net[pAC->Rlmt.Port[ToPortNumber].Net->NetNumber]. Port[i]->PortNumber == ToPortNumber) { pAC->Addr.Net[pAC->Rlmt.Port[ToPortNumber].Net->NetNumber]. ActivePort = i; /* 20001207 RA: Was "ToPortNumber;". */ } } (void) SkAddrMcUpdate(pAC, IoC, FromPortNumber); (void) SkAddrMcUpdate(pAC, IoC, ToPortNumber); return (SK_ADDR_SUCCESS);} /* SkAddrSwap */#endif /* !SK_SLIM */#ifdef __cplusplus}#endif /* __cplusplus */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -