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

📄 if_fei.c

📁 Tornado 2.0.2 source code!vxworks的源代码
💻 C
📖 第 1 页 / 共 4 页
字号:
	LINK_WR (&pDrvCtrl->pCSR->scbGP, addr);    pDrvCtrl->pCSR->scbCommand |= cmd;	/* write SCB command byte */    return (OK);    }#ifdef  FEI_DEBUG/********************************************************************************* feiDumpPrint - Display statistical counters** This routine displays i82557 statistical counters** RETURNS: OK, or ERROR if the DUMP command failed.*/LOCAL STATUS feiDumpPrint    (    int         unit    )    {    UINT32      dumpArray [18];    UINT32 *    pDump;    STATUS status = OK;    /* dump area must be long-word allign */    pDump = (UINT32 *) (((UINT32) dumpArray + 4) & 0xfffffffc);    status = feiErrCounterDump(unit,pDump);     printf ("\n");    printf ("Tx good frames:             %d\n", *pDump++);    printf ("Tx MAXCOL errors:           %d\n", *pDump++);    printf ("Tx LATECOL errors:          %d\n", *pDump++);    printf ("Tx underrun errors:         %d\n", *pDump++);    printf ("Tx lost CRS errors:         %d\n", *pDump++);    printf ("Tx deferred:                %d\n", *pDump++);    printf ("Tx single collisions:       %d\n", *pDump++);    printf ("Tx multiple collisions:     %d\n", *pDump++);    printf ("Tx total collisions:        %d\n", *pDump++);    printf ("Rx good frames:             %d\n", *pDump++);    printf ("Rx CRC errors:              %d\n", *pDump++);    printf ("Rx allignment errors:       %d\n", *pDump++);    printf ("Rx resource errors:         %d\n", *pDump++);    printf ("Rx overrun errors:          %d\n", *pDump++);    printf ("Rx collision detect errors: %d\n", *pDump++);    printf ("Rx short frame errors:      %d\n", *pDump++);    return (status);    }/******************************************************************************* feiErrCounterDump - dump statistical counters ** This routine dumps statistical counters for the purpose of debugging and* tuning the 82557.** The <memAddr> parameter is the pointer to an array of 68 bytes in the* local memory.  This memory region must be allocated before this routine is* called.  The memory space must also be DWORD (4 bytes) aligned.  When the* last DWORD (4 bytes) is written to a value, 0xa007, it indicates the dump* command has completed.  To determine the meaning of each statistical* counter, see the Intel 82557 manual.** RETURNS: OK or ERROR.*/LOCAL STATUS feiErrCounterDump     (    int unit,    UINT32 *memAddr    )    {    DRV_CTRL *  pDrvCtrl = &drvCtrl [unit];    STATUS status = OK;    int i;     int         s = splimp ();   /* block network access to 82557 resource */    memAddr[16]=0;    /* make sure the last DWORD is 0 */    /* tells the 82557 where to write dump data */    if (feiSCBCommand (pDrvCtrl, SCB_C_CULDDUMP, TRUE,	    (UINT32 *) LOCAL_TO_SYS_ADDR(unit,(UINT32)memAddr) ) == ERROR)        status = ERROR;    /* issue the dump and reset counter command */    if (feiSCBCommand (pDrvCtrl, SCB_C_CUDUMPRST,FALSE,(UINT32)0) == ERROR)	status = ERROR;        splx (s);   /* release 82557 resource to network */    /* waits for it done */     for (i=0;i<60;i++)	{	if (memAddr[16] == (UINT32)0xa007)	    break;        taskDelay(2);	}    if (i==60)	status = ERROR;    return (status);    }#endif  /* FEI_DEBUG *//****************************************************************************** feiMDIRead - read the MDI register** This routine reads the specific register in the PHY device* Valid PHY address is 0-31** RETURNS: OK or ERROR.**/static int feiMDIRead     (    int unit,    int regAddr,    int phyAddr,    UINT16 *retVal    )    {    DRV_CTRL *  pDrvCtrl = &drvCtrl [unit];    int i;    UINT32 mdrValue;    volatile UINT32 *mdiReg = (volatile UINT32 *)&pDrvCtrl->pCSR->mdiCR;       mdrValue = ((regAddr<<16) | (phyAddr << 21) | (MDI_READ<<26) );       /* write to MDI */    *mdiReg = mdrValue;    taskDelay(2);    /* wait for a while */    /* check if it's done */    for (i=0;i<40;i++)        {        if ( (*mdiReg) & (1<<28) )            break;        taskDelay(1);        }     if (i==40)         return (ERROR);     *retVal = (UINT16)((*mdiReg)&0xffff);     return(OK);     } /**************************************************************************** feiMDIWrite - write to the MDI register** This routine writes the specific register in the PHY device* Valid PHY address is 0-31** RETURNS: OK or ERROR.*/static int feiMDIWrite    (    int unit,    int regAddr,    int phyAddr,    UINT16 writeData     )    {    DRV_CTRL *  pDrvCtrl = &drvCtrl [unit];    int i;    UINT32 mdrValue;    volatile UINT32 *mdrReg = (volatile UINT32 *)&pDrvCtrl->pCSR->mdiCR;      mdrValue = ((regAddr<<16) | (phyAddr << 21) | (MDI_WRITE<<26) | writeData );       /* write to M */    *mdrReg = mdrValue;    taskDelay(2);    /* wait for a while */    /* check if it's done */    for (i=0;i<40;i++)        {        if ( (*mdrReg) & (1<<28) )            break;        taskDelay(1);        }     if (i==40)         return (ERROR);     return(OK);     }/****************************************************************************** feiMDIPhyLinkSet - detect and set the link for the PHY device** This routine first checks if the link has been established.  If not, it* isolates the other one, and tries to establish the link.  PHY device 0 is* always at PHY address 0.  PHY 1 can be at 1-31 PHY addresses.** RETURNS: OK or ERROR.**/static int feiMDIPhyLinkSet    (    int unit,    int phyAddr    )    {    UINT16 ctlReg;    UINT16 statusReg;    int isoDev,i;    /* read control register */    feiMDIRead (unit, MDI_CTRL_REG, phyAddr, &ctlReg);    /* read again */    feiMDIRead (unit, MDI_CTRL_REG, phyAddr, &ctlReg);    /* check if the PHY is there */    if (ctlReg == (UINT16)0xffff)        return (ERROR);   /* no PHY present */#if 0    /* CR RESET will cause link down */    feiMDIWrite (unit,MDI_CTRL_REG,phyAddr,MDI_CR_RESET);     taskDelay(4);#endif    /* The PHY is there, read status register  */    feiMDIRead (unit, MDI_STATUS_REG, phyAddr,&statusReg);    /* in case the status bit is the latched bit */    if ( !(statusReg & MDI_SR_LINK_STATUS))        feiMDIRead (unit, MDI_STATUS_REG, phyAddr, &statusReg);    if (statusReg & MDI_SR_LINK_STATUS)        return (OK);  /* Device found and link OK */    /* no link is established, let's configure it */        /* isolates the other PHY */    isoDev = (phyAddr)?0:1;    feiMDIWrite (unit,MDI_CTRL_REG,isoDev,MDI_CR_ISOLATE);    /* wait for a while */    taskDelay (2);    /* enable the PHY device we try to configure */    feiMDIWrite (unit,MDI_CTRL_REG,phyAddr,MDI_CR_SELECT);    taskDelay (2); /* wait for a while for command take effect */    /* restart the auto negotiation process, execute anyways even if     * it has no such capability.     */    feiMDIWrite (unit,MDI_CTRL_REG,phyAddr,MDI_CR_RESTART | MDI_CR_SELECT);    /* wait for auto-negotiation to complete */    for (i=0;i<80;i++)        {        /* read the status register */        feiMDIRead (unit, MDI_STATUS_REG, phyAddr, &statusReg);        feiMDIRead (unit, MDI_STATUS_REG, phyAddr, &statusReg);           if (statusReg & (MDI_SR_AUTO_NEG | MDI_SR_REMOTE_FAULT) )            break;        taskDelay (2);	if (!(statusReg & MDI_SR_AUTO_SELECT) )	    break;  /* no such capability */        }    /* Read the status register */    feiMDIRead (unit, MDI_STATUS_REG, phyAddr, &statusReg);    /* some of the status bits require to clear a latch */    if ( !(statusReg & MDI_SR_LINK_STATUS))        feiMDIRead (unit, MDI_STATUS_REG, phyAddr, &statusReg);    if (statusReg & MDI_SR_LINK_STATUS)        return (OK);  /* Link configure done and successful */            return (PHY_LINK_ERROR);   /* device is there, cann't establish link */    }/***************************************************************************** feiMDIPhyConfig - configure the PHY device** This routine configures the PHY device according to the parameters* specified by users or the default value.** RETURNS: OK or ERROR.**/static int feiMDIPhyConfig     (    int unit,    int phyAddr    )    {    DRV_CTRL *  pDrvCtrl = &drvCtrl [unit];    UINT16 ctlReg = 0;    int fullDpx=FALSE;    int autoSelect =FALSE;    UINT16 statusReg;    int status,i;    /* find out what capabilities the device have */    /*  read status register  */    feiMDIRead (unit, MDI_STATUS_REG, phyAddr,&statusReg);    /* some of the status bits require to read twice */    feiMDIRead (unit, MDI_STATUS_REG, phyAddr, &statusReg);    /* The device at least has to have the half duplex and 10mb speed */    if (statusReg & (MDI_SR_10T_FULL_DPX | MDI_SR_TX_FULL_DPX) )        fullDpx = TRUE;    if (statusReg & MDI_SR_AUTO_SELECT)        autoSelect = TRUE;#ifdef	FEI_DEBUG     logMsg ("status REG = %x !!!! \n",statusReg,0,0,0,0,0);#endif	/* FEI_DEBUG */    if (pDrvCtrl->board.phyDpx == PHY_FULL_DPX && fullDpx == TRUE)        ctlReg |= MDI_CR_FDX;    if (pDrvCtrl->board.phySpeed == PHY_100MBS)        ctlReg |= MDI_CR_100;    if (pDrvCtrl->board.phySpeed == PHY_AUTO_SPEED || 			       pDrvCtrl->board.phyDpx == PHY_AUTO_DPX )        {	if (autoSelect != TRUE)	    {	    /* set back to default */	    pDrvCtrl->board.phySpeed = PHY_10MBS;	    pDrvCtrl->board.phyDpx = PHY_HALF_DPX;	    ctlReg |= (PHY_10MBS | PHY_HALF_DPX);	    }	    else                ctlReg |= (MDI_CR_SELECT|MDI_CR_RESTART);         }    /* or other possible board level selection */    ctlReg |= pDrvCtrl->board.others;    /* configure the PHY */    feiMDIWrite (unit,MDI_CTRL_REG,phyAddr,ctlReg);       taskDelay (2);   /* wait for a while */    if (! (ctlReg & MDI_CR_RESTART) )        return (OK);    /* we are here if the restart auto negotiation is selected */#ifdef	FEI_DEBUG    logMsg ("auto NEGOTIATION STARTS !!!! \n",0,0,0,0,0,0);#endif	/* FEI_DEBUG */    /* wait for it done */    for (status = PHY_AUTO_FAIL,i=0;i<80;i++)       {       /*  read status register, some bits have the latch,first read clears */       feiMDIRead (unit, MDI_STATUS_REG, phyAddr,&statusReg);       feiMDIRead (unit, MDI_STATUS_REG, phyAddr, &statusReg);       if (statusReg & MDI_SR_AUTO_NEG)           {           status = OK;  /* auto negotiation completed */           break;           }       if (statusReg & MDI_SR_REMOTE_FAULT)           {           status = PHY_AUTO_FAIL;  /* auto negotiation fails */           break;           }        }                    return (status);      } /**************************************************************************** feiPhyInit - initialize and configure the PHY device if there is one** This routine initialize and configure the PHY device if there is one.** RETURNS: OK or ERROR.**/static int feiPhyInit    (    int unit    )    {    int status;    int phyDevice;    DRV_CTRL *  pDrvCtrl = &drvCtrl [unit];    if (pDrvCtrl->board.phyAddr > 31)        return (OK);  /* not a MII interface,no need to initialize PHY */     /* configure the Physical layer medium if it's MII interface */     /* starts with logical PHY 1 */     phyDevice = pDrvCtrl->board.phyAddr?pDrvCtrl->board.phyAddr:1;     status = feiMDIPhyLinkSet(unit,phyDevice);     if (status != OK)         {         phyDevice = 0;         status = feiMDIPhyLinkSet(unit,phyDevice);         }     if (status != OK)	 {         printf ("LINK_FAIL error, check the line connection !!!\n");         return (status);         }     /* we are here if a valid link is established */     status = feiMDIPhyConfig (unit,phyDevice);      if (status == PHY_AUTO_FAIL)         {         /* force default speed and duplex */         pDrvCtrl->board.phySpeed = PHY_10MBS;         pDrvCtrl->board.phyDpx = PHY_HALF_DPX;          pDrvCtrl->board.others = 0;         /* and configure it again */         status = feiMDIPhyConfig (unit,phyDevice);           }     return (status);     } 

⌨️ 快捷键说明

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