VxWorks Reference Manual : Libraries
miiLib - Media Independent Interface library
miiPhyInit( ) - initialize and configure the PHY devices
miiPhyUnInit( ) - uninitialize a PHY
miiPhyOptFuncSet( ) - set the pointer to the MII optional registers handler
miiLibInit( ) - initialize the MII library
miiLibUnInit( ) - uninitialize the MII library
miiShow( ) - show routine for MII library
miiRegsGet( ) - get the contents of MII registers
This module implements a Media Independent Interface (MII) library.
The MII is an inexpensive and easy-to-implement interconnection between the Carrier Sense Multiple Access with Collision Detection (CSMA/CD) media access controllers and the Physical Layer Entities (PHYs).
The purpose of this library is to provide Ethernet drivers in VxWorks with a standardized, MII-compliant, easy-to-use interface to various PHYs. In other words, using the services of this library, network drivers will be able to scan the existing PHYs, run diagnostics, electrically isolate a subset of them, negotiate their technology abilities with other link-partners on the network, and ultimately initialize and configure a specific PHY in a proper, MII-compliant fashion.
In order to initialize and configure a PHY, its MII management interface has to be used. This is made up of two lines: management data clock (MDC) and management data input/output (MDIO). The former provides the timing reference for transfer of information on the MDIO signal. The latter is used to transfer control and status information between the PHY and the MAC controller. For this transfer to be successful, the information itself has to be encoded into a frame format, and both the MDIO and MDC signals have to comply with certain requirements as described in the 802.3u IEEE Standard.
Since no assumption can be made as to the specific MAC-to-MII interface, this library expects the driver's writer to provide it with specialized read and write routines to access that interface. See EXTERNAL SUPPORT REQUIREMENTS below.
The external routines provided by this library are miiPhyInit (), miiPhyUnInit (), miiLibInit (), miiLibUnInit (), miiPhyOptFuncSet ().
STATUS miiLibInit (void);STATUS miiLibUnInit (void);miiPhyInit () should be called with the address of a PHY_INFO sructure as only parameter.STATUS miiPhyInit (PHY_INFO * pPhyInfo);miiPhyUnInit () should be called with the address of a PHY_INFO sructure as only parameter.STATUS miiPhyUnInit (PHY_INFO * pPhyInfo);The routine miiPhyOptFuncSet () should have a valid function pointer as only parameter.void miiPhyOptFuncSet (FUNCPTR optRegsFunc);
- phyReadRtn
STATUS phyReadRtn (DRV_CTRL * pDrvCtrl, UINT8 phyAddr, UINT8 phyReg, UINT16 * value);This routine is expected to perform any driver-specific functions required to read a 16-bit word from the phyReg register of the MII-compliant PHY whose address is specified by phyAddr. Reading is performed through the MII management interface.
- phyWriteRtn
STATUS phyWriteRtn (DRV_CTRL * pDrvCtrl, UINT8 phyAddr, UINT8 phyReg, UINT16 value);This routine is expected to perform any driver-specific functions required to write a 16-bit word to the phyReg register of the MII-compliant PHY whose address is specified by phyAddr. Writing is performed through the MII management interface.
- phyDelayRtn
STATUS phyDelayRtn (UINT32 phyDelayParm);This routine is expected to cause a limited delay to the calling task, no matter whether this is an active delay, or an inactive one. miiPhyInit () calls this routine on several occasions throughout the code with phyDelayParm as parameter. This represents the granularity of the delay itself, whereas the field phyMaxDelay in PHY_INFO is the maximum allowed delay, in phyDelayParm units.The user should be aware that some of these events may take as long as 2-3 seconds to be completed, and he should therefore tune this routine and the parameter phyMaxDelay accordingly.
If the related field phyDelayRtn in the PHY_INFO structure is initialized to NULL, no delay is performed.
- phyLinkDownRtn
STATUS phyLinkDownRtn (DRV_CTRL *);This routine is expected to take any action necessary to re-initialize the media interface, including possibly stopping and restarting the driver itself. It is called when a link down event is detected for any active PHY, with the pointer to the relevant driver control structure as only parameter.
miiLib, IEEE 802.3u Standard
miiPhyInit( ) - initialize and configure the PHY devices
STATUS miiPhyInit ( PHY_INFO * pPhyInfo /* pointer to PHY_INFO structure */ )
This routine scans, initializes and configures the PHY device described in phyInfo. Space for phyInfo is to be provided by the calling task.
This routine is called from the driver's Start routine to perform media inialization and configuration. To access the PHY device through the MII-management interface, it uses the read and write routines which are provided by the driver itself in the fields phyReadRtn( ), phyWriteRtn( ) of the phyInfo structure. Before it attempts to use this routine, the driver has to properly initialize some of the fields in the phyInfo structure, and optionally fill in others, as below:
/* fill in mandatory fields in phyInfo */ pDrvCtrl->phyInfo->pDrvCtrl = (void *) pDrvCtrl; pDrvCtrl->phyInfo->phyWriteRtn = (FUNCPTR) xxxMiiWrite; pDrvCtrl->phyInfo->phyReadRtn = (FUNCPTR) xxxMiiRead; /* fill in some optional fields in phyInfo */ pDrvCtrl->phyInfo->phyFlags = 0; pDrvCtrl->phyInfo->phyAddr = (UINT8) MII_PHY_DEF_ADDR; pDrvCtrl->phyInfo->phyDefMode = (UINT8) PHY_10BASE_T; pDrvCtrl->phyInfo->phyAnOrderTbl = (MII_AN_ORDER_TBL *) &xxxPhyAnOrderTbl; /* @ fill in some more optional fields in phyInfo: the delay stuff @ we want this routine to use our xxxDelay () routine, with @ the constant one as an argument, and the max delay we may @ tolerate is the constant MII_PHY_DEF_DELAY, in xxxDelay units */ pDrvCtrl->phyInfo->phyDelayRtn = (FUNCPTR) xxxDelay; pDrvCtrl->phyInfo->phyMaxDelay = MII_PHY_DEF_DELAY; pDrvCtrl->phyInfo->phyDelayParm = 1; /* @ fill in some more optional fields in phyInfo: the PHY's callback @ to handle "link down" events. This routine is invoked whenever @ the link status in the PHY being used is detected to be low. */ pDrvCtrl->phyInfo->phyStatChngRtn = (FUNCPTR) xxxRestart;Some of the above fields may be overwritten by this routine, since for instance, the logical address of the PHY actually used may differ from the user's initial setting. Likewise, the specific PHY being initialized, may not support all the technology abilities the user has allowed for its operations.This routine first scans for all possible PHY addresses in the range 0-31, checking for an MII-compliant PHY, and attempts at running some diagnostics on it. If none is found, ERROR is returned.
Typically PHYs are scanned from address 0, but if the user specifies an alternative start PHY address via the parameter phyAddr in the phyInfo structure, PHYs are scanned in order starting with the specified PHY address. In addition, if the flag MII_ALL_BUS_SCAN is set, this routine will scan the whole bus even if a valid PHY has already been found, and stores bus topology information. If the flags MII_PHY_ISO, MII_PHY_PWR_DOWN are set, all of the PHYs found but the first will be respectively electrically isolated from the MII interface and/or put in low-power mode. These two flags are meaningless in a configuration where only one PHY is present.
The phyAddr parameter is very important from a performance point of view. Since the MII management interface, through which the PHY is configured, is a very slow one, providing an incorrect or invalid address in this field may result in a particularly long boot process.
If the flag MII_ALL_BUS_SCAN is not set, this routine will assume that the first PHY found is the only one.
This routine then attempts to bring the link up. This routine offers two strategies to select a PHY and establish a valid link. The default strategy is to use the standard 802.3 style auto-negotiation, where both link partners negotiate all their technology abilities at the same time, and the highest common denominator ability is chosen. Before the auto-negotiation is started, the next-page exchange mechanism is disabled.
The user can prevent the PHY from negotiating certain abilities via userFlags -- MII_PHY_FD, MII_PHY_100, MII_PHY_HD, and MII_PHY_10. When MII_PHY_FD is not specified, full duplex will not be negotiated; when MII_PHY_HD is not specified half duplex will not be negotiated, when MII_PHY_100 is not specified, 100Mbps ability will not be negotiated; when MII_PHY_10 is not specified, 10Mbps ability will not be negotiated.
When MII_PHY_TBL is set in the user flags, the BSP specific table whose address may be provided in the phyAnOrderTbl field of the phyInfo structure, is used to obtain the list, and the order of technology abilities to be negotiated. The entries in this table are ordered such that entry 0 is the highest priority, entry 1 in next and so on. Entries in this table may be repeated, and multiple technology abilities can be OR'd to create a single entry. If a PHY cannot support a ability in an entry, that entry is ignored.
If no PHY provides a valid link, and if MII_PHY_DEF_SET is set in the phyFlags field of the PHY_INFO structure, the first PHY that supports the default abilities defined in the phyDefMode of the phyInfo structure will be selected, regardless of the link status.
In addition, this routine adds an entry in a linked list of PHY devices for each active PHY it found. If the flag MII_PHY_MONITOR is set, the link status for the relevant PHY is continually monitored for a link down event. If such event is detected, and if the phyLinkDownRtn in the PHY_INFO * structure is a valid function pointer, then the routine it points at is executed in the context of the netTask (). The macro MII_MONITOR_DELAY may be used to define the period in seconds with which the link status is checked. Its default value is 5.
OK or ERROR if the PHY could not be initialised,
miiPhyUnInit( ) - uninitialize a PHY
STATUS miiPhyUnInit ( PHY_INFO * pPhyInfo /* pointer to PHY_INFO structure */ )
This routine uninitializes the PHY specified in pPhyInfo. It brings it in low-power mode, and electrically isolate it from the MII management interface to which it is attached. In addition, it frees resources previously allocated.
OK, ERROR in case of fatal errors.
miiPhyOptFuncSet( ) - set the pointer to the MII optional registers handler
void miiPhyOptFuncSet ( FUNCPTR optRegsFunc /* function pointer */ )
This routine sets the function pointer in optRegsFunc to the MII optional, PHY-specific registers handler. The handler will be executed before the PHY's technology abilities are negotiated.
N/A.
miiLibInit( ) - initialize the MII library
STATUS miiLibInit ( )
This routine initializes the MII library.
OK or ERROR.
miiLibUnInit( ) - uninitialize the MII library
STATUS miiLibUnInit ( )
This routine uninitializes the MII library. Previously allocated resources are reclaimed back to the system.
OK or ERROR.
miiShow( ) - show routine for MII library
void miiShow ( PHY_INFO * pPhyInfo /* pointer to PHY_INFO structure */ )
This is a show routine for the MII library
OK, always.
miiRegsGet( ) - get the contents of MII registers
STATUS miiRegsGet ( PHY_INFO * pPhyInfo, /* pointer to PHY_INFO structure */ UINT regNum, /* number of registers to display */ UCHAR * buff /* where to read registers to */ )
This routine gets the contents of the first regNum MII registers, and, if buff is not NULL, copies them to the space pointed to by buff.
OK, or ERROR if could not perform the read.