#include <Copyright.h>
/********************************************************************************
* gtHwCntl.c
*
* DESCRIPTION:
*       Functions declarations for Hw accessing quarterDeck phy, internal and
*       global registers.
*
* DEPENDENCIES:
*       None.
*
* FILE REVISION NUMBER:
*       $Revision: 5 $
*
*******************************************************************************/

#include <gtDrvSwRegs.h>
#include <gtHwCntl.h>
#include <gtMiiSmiIf.h>
#include <gtSem.h>


static GT_STATUS hwReadPPU(GT_QD_DEV *dev, GT_U16 *data);
static GT_STATUS hwWritePPU(GT_QD_DEV *dev, GT_U16 data);
static GT_STATUS coreReadPhyReg
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    portNum,
    IN  GT_U8    regAddr,
    OUT GT_U16   *data
);
static GT_STATUS coreWritePhyReg
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    portNum,
    IN  GT_U8    regAddr,
    IN  GT_U16   data
);
static GT_STATUS coreReadPagedPhyReg
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    portNum,
    IN  GT_U8    pageNum,
    IN  GT_U8    regAddr,
    IN  GT_U32     anyPage,
    OUT GT_U16   *data
);
static GT_STATUS coreWritePagedPhyReg
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    portNum,
    IN  GT_U8    pageNum,
    IN  GT_U8    regAddr,
    IN  GT_U32     anyPage,
    IN  GT_U16   data
);

GT_STATUS phyRegReadPPUEn (GT_QD_DEV* dev, unsigned int phyAddr , unsigned int regAddr,
                        GT_U16* value);
GT_STATUS phyRegWritePPUEn (GT_QD_DEV* dev, unsigned int phyAddr , unsigned int regAddr,
                       GT_U16 value);
#ifndef GT_RMGMT_ACCESS
static GT_STATUS phyReadGlobal2Reg
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    regAddr,
    OUT GT_U16   *data
);
static GT_STATUS phyWriteGlobal2Reg
(
    IN  GT_QD_DEV *dev,
    IN  GT_U8    regAddr,
    IN  GT_U16   data
);
#endif


/*******************************************************************************
* portToSmiMapping
*
* DESCRIPTION:
*       This function mapps port to smi address
*
* INPUTS:
*        dev - device context
*       portNum - Port number to read the register for.
*        accessType - type of register (Phy, Port, or Global)
*
* OUTPUTS:
*       None.
*
* RETURNS:
*       smiAddr    - smi address.
*
*******************************************************************************/
GT_U8 portToSmiMapping
(
    IN GT_QD_DEV *dev,
    IN GT_U8    portNum,
    IN GT_U32    accessType
)
{
    GT_U8 smiAddr;

    if(IS_IN_DEV_GROUP(dev,DEV_8PORT_SWITCH))
    {
        switch(accessType)
        {
            case PHY_ACCESS:
              if (dev->validPhyVec & (1<<portNum))
                smiAddr = PHY_REGS_START_ADDR_8PORT + portNum;
              else
			  {
                smiAddr = 0xFF;
                if(IS_IN_DEV_GROUP(dev,DEV_SERDES_CORE))
				{
                  if (dev->validSerdesVec & (1<<portNum))
                    smiAddr = PHY_REGS_START_ADDR_8PORT + portNum;
				}
			  }
              break;
            case PORT_ACCESS:
                    if (dev->validPortVec & (1<<portNum))
                        smiAddr = PORT_REGS_START_ADDR_8PORT + portNum;
                    else
                        smiAddr = 0xFF;
                    break;
            case GLOBAL_REG_ACCESS:
                    smiAddr = GLOBAL_REGS_START_ADDR_8PORT;
                    break;
            case GLOBAL3_REG_ACCESS:
                    smiAddr = GLOBAL_REGS_START_ADDR_8PORT + 2;
                    break;
            default:
                    smiAddr = GLOBAL_REGS_START_ADDR_8PORT + 1;
                    break;
        }
    }
    else
    {
        smiAddr = dev->baseRegAddr;
        switch(accessType)
        {
            case PHY_ACCESS:
              if (dev->validPhyVec & (1<<portNum))
                smiAddr += PHY_REGS_START_ADDR + portNum;
              else
			  {
                smiAddr = 0xFF;
                if(IS_IN_DEV_GROUP(dev,DEV_SERDES_CORE))
				{
                  if (dev->validSerdesVec & (1<<portNum))
                    smiAddr += PHY_REGS_START_ADDR + portNum;
				}
			  }
              break;
            case PORT_ACCESS:
                    if (dev->validPortVec & (1<<portNum))
                        smiAddr += PORT_REGS_START_ADDR + portNum;
                    else
                        smiAddr = 0xFF;
                    break;
            case GLOBAL_REG_ACCESS:
                    smiAddr += GLOBAL_REGS_START_ADDR;
                    break;
            default:
                    /*  88EC0XX uses PORT_REGS_START_ADDR -1 */
                    if(IS_IN_DEV_GROUP(dev,DEV_MELODY_SWITCH))
                      smiAddr += PORT_REGS_START_ADDR - 1;
                    else
                      smiAddr += GLOBAL_REGS_START_ADDR - 1;
                    break;
        }
    }
    return smiAddr;
}


/****************************************************************************/
/* Phy registers related functions.                                         */
/****************************************************************************/

/*******************************************************************************
* hwReadPhyReg
*
* DESCRIPTION:
*       This function reads a switch's port phy register.
*
* INPUTS:
*       portNum - Port number to read the register for.
*       regAddr - The register's address.
*
* OUTPUTS:
*       data    - The read register's data.
*
* RETURNS:
*       GT_OK on success, or
*       GT_FAIL otherwise.
*
* COMMENTS:
*       None.
*
*******************************************************************************/
GT_STATUS hwReadPhyReg
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    portNum,
    IN  GT_U8    regAddr,
    OUT GT_U16   *data
)
{
    GT_STATUS   retVal;

    gtSemTake(dev,dev->multiAddrSem,OS_WAIT_FOREVER);

    retVal = coreReadPhyReg(dev, portNum, regAddr, data);

    gtSemGive(dev,dev->multiAddrSem);

    return retVal;
}


/*******************************************************************************
* hwWritePhyReg
*
* DESCRIPTION:
*       This function writes to a switch's port phy register.
*
* INPUTS:
*       portNum - Port number to write the register for.
*       regAddr - The register's address.
*       data    - The data to be written.
*
* OUTPUTS:
*       None.
*
* RETURNS:
*       GT_OK on success, or
*       GT_FAIL otherwise.
*
* COMMENTS:
*       None.
*
*******************************************************************************/
GT_STATUS hwWritePhyReg
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    portNum,
    IN  GT_U8    regAddr,
    IN  GT_U16   data
)
{
    GT_STATUS   retVal;

    gtSemTake(dev,dev->multiAddrSem,OS_WAIT_FOREVER);

    retVal = coreWritePhyReg(dev, portNum, regAddr, data);

    gtSemGive(dev,dev->multiAddrSem);

    return retVal;
}


/*******************************************************************************
* hwGetPhyRegField
*
* DESCRIPTION:
*       This function reads a specified field from a switch's port phy register.
*
* INPUTS:
*       portNum     - Port number to read the register for.
*       regAddr     - The register's address.
*       fieldOffset - The field start bit index. (0 - 15)
*       fieldLength - Number of bits to read.
*
* OUTPUTS:
*       data        - The read register field.
*
* RETURNS:
*       GT_OK on success, or
*       GT_FAIL otherwise.
*
* COMMENTS:
*       1.  The sum of fieldOffset & fieldLength parameters must be smaller-
*           equal to 16.
*
*******************************************************************************/
GT_STATUS hwGetPhyRegField
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    portNum,
    IN  GT_U8    regAddr,
    IN  GT_U8    fieldOffset,
    IN  GT_U8    fieldLength,
    OUT GT_U16   *data
)
{
    GT_U16 mask;            /* Bits mask to be read */
    GT_U16 tmpData;
    GT_STATUS   retVal;

    gtSemTake(dev,dev->multiAddrSem,OS_WAIT_FOREVER);

    retVal = coreReadPhyReg(dev, portNum, regAddr, &tmpData);

    gtSemGive(dev,dev->multiAddrSem);

    if (retVal != GT_OK)
        return retVal;

    CALC_MASK(fieldOffset,fieldLength,mask);

    tmpData = (tmpData & mask) >> fieldOffset;
    *data = tmpData;

    DBG_INFO(("Read from phy(%d) register: regAddr 0x%x, ",
              portNum,regAddr));
    DBG_INFO(("fOff %d, fLen %d, data 0x%x.\n",fieldOffset,fieldLength,*data));

    return retVal;
}


/*******************************************************************************
* hwSetPhyRegField
*
* DESCRIPTION:
*       This function writes to specified field in a switch's port phy register.
*
* INPUTS:
*       portNum     - Port number to write the register for.
*       regAddr     - The register's address.
*       fieldOffset - The field start bit index. (0 - 15)
*       fieldLength - Number of bits to write.
*       data        - Data to be written.
*
* OUTPUTS:
*       None.
*
* RETURNS:
*       GT_OK on success, or
*       GT_FAIL otherwise.
*
* COMMENTS:
*       1.  The sum of fieldOffset & fieldLength parameters must be smaller-
*           equal to 16.
*
*******************************************************************************/
GT_STATUS hwSetPhyRegField
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    portNum,
    IN  GT_U8    regAddr,
    IN  GT_U8    fieldOffset,
    IN  GT_U8    fieldLength,
    IN  GT_U16   data
)
{
    GT_U16 mask;
    GT_U16 tmpData;
    GT_STATUS   retVal;

    gtSemTake(dev,dev->multiAddrSem,OS_WAIT_FOREVER);

    retVal = coreReadPhyReg(dev, portNum, regAddr, &tmpData);

    if(retVal != GT_OK)
    {
        gtSemGive(dev,dev->multiAddrSem);
        return retVal;
    }

    CALC_MASK(fieldOffset,fieldLength,mask);

    /* Set the desired bits to 0.                       */
    tmpData &= ~mask;
    /* Set the given data into the above reset bits.    */
    tmpData |= ((data << fieldOffset) & mask);

    DBG_INFO(("Write to phy(%d) register: regAddr 0x%x, ",
              portNum,regAddr));
    DBG_INFO(("fieldOff %d, fieldLen %d, data 0x%x.\n",fieldOffset,
              fieldLength,data));

    retVal = coreWritePhyReg(dev, portNum, regAddr, tmpData);

    gtSemGive(dev,dev->multiAddrSem);
    return retVal;
}


/*******************************************************************************
* hwReadPagedPhyReg
*
* DESCRIPTION:
*       This function reads a switch's port phy register in page mode.
*
* INPUTS:
*       portNum - Port number to read the register for.
*       pageNum - Page number of the register to be read.
*       regAddr - The register's address.
*        anyPage - Any Page register vector
*
* OUTPUTS:
*       data    - The read register's data.
*
* RETURNS:
*       GT_OK on success, or
*       GT_FAIL otherwise.
*
* COMMENTS:
*       None.
*
*******************************************************************************/
GT_STATUS hwReadPagedPhyReg
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    portNum,
    IN  GT_U8    pageNum,
    IN  GT_U8    regAddr,
    IN  GT_U32     anyPage,
    OUT GT_U16   *data
)
{
    GT_STATUS   retVal;

    gtSemTake(dev,dev->multiAddrSem,OS_WAIT_FOREVER);

    retVal = coreReadPagedPhyReg(dev,portNum,pageNum,regAddr,anyPage,data);

    gtSemGive(dev,dev->multiAddrSem);

    return retVal;
}


/*******************************************************************************
* hwWritePagedPhyReg
*
* DESCRIPTION:
*       This function writes to a switch's port phy register in page mode.
*
* INPUTS:
*       portNum - Port number to write the register for.
*       pageNum - Page number of the register to be written.
*       regAddr - The register's address.
*        anyPage - Any Page register vector
*       data    - The data to be written.
*
* OUTPUTS:
*       None.
*
* RETURNS:
*       GT_OK on success, or
*       GT_FAIL otherwise.
*
* COMMENTS:
*       None.
*
*******************************************************************************/
GT_STATUS hwWritePagedPhyReg
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    portNum,
    IN  GT_U8    pageNum,
    IN  GT_U8    regAddr,
    IN  GT_U32     anyPage,
    IN  GT_U16   data
)
{
    GT_STATUS   retVal;

    gtSemTake(dev,dev->multiAddrSem,OS_WAIT_FOREVER);

    retVal = coreWritePagedPhyReg(dev,portNum,pageNum,regAddr,anyPage,data);

    gtSemGive(dev,dev->multiAddrSem);

    return retVal;
}


/*******************************************************************************
* hwGetPagedPhyRegField
*
* DESCRIPTION:
*       This function reads a specified field from a switch's port phy register
*        in page mode.
*
* INPUTS:
*       portNum     - Port number to read the register for.
*       pageNum     - Page number of the register to be read.
*       regAddr     - The register's address.
*       fieldOffset - The field start bit index. (0 - 15)
*       fieldLength - Number of bits to read.
*        anyPage     - Any Page register vector
*
* OUTPUTS:
*       data        - The read register field.
*
* RETURNS:
*       GT_OK on success, or
*       GT_FAIL otherwise.
*
* COMMENTS:
*       1.  The sum of fieldOffset & fieldLength parameters must be smaller-
*           equal to 16.
*
*******************************************************************************/
GT_STATUS hwGetPagedPhyRegField
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    portNum,
    IN  GT_U8    pageNum,
    IN  GT_U8    regAddr,
    IN  GT_U8    fieldOffset,
    IN  GT_U8    fieldLength,
    IN  GT_U32     anyPage,
    OUT GT_U16   *data
)
{
    GT_U16 mask;            /* Bits mask to be read */
    GT_U16 tmpData;
    GT_STATUS   retVal;

    gtSemTake(dev,dev->multiAddrSem,OS_WAIT_FOREVER);

    retVal = coreReadPagedPhyReg(dev,portNum,pageNum,regAddr,anyPage,&tmpData);

    gtSemGive(dev,dev->multiAddrSem);

    if(retVal != GT_OK)
    {
        return retVal;
    }

    CALC_MASK(fieldOffset,fieldLength,mask);

    tmpData = (tmpData & mask) >> fieldOffset;
    *data = tmpData;

    DBG_INFO(("Read from phy(%d) register: regAddr 0x%x, ",
              portNum,regAddr));
    DBG_INFO(("fOff %d, fLen %d, data 0x%x.\n",fieldOffset,fieldLength,*data));

    return GT_OK;
}


/*******************************************************************************
* hwSetPagedPhyRegField
*
* DESCRIPTION:
*       This function writes to specified field in a switch's port phy register
*        in page mode
*
* INPUTS:
*       portNum     - Port number to write the register for.
*       pageNum     - Page number of the register to be read.
*       regAddr     - The register's address.
*       fieldOffset - The field start bit index. (0 - 15)
*       fieldLength - Number of bits to write.
*        anyPage     - Any Page register vector
*       data        - Data to be written.
*
* OUTPUTS:
*       None.
*
* RETURNS:
*       GT_OK on success, or
*       GT_FAIL otherwise.
*
* COMMENTS:
*       1.  The sum of fieldOffset & fieldLength parameters must be smaller-
*           equal to 16.
*
*******************************************************************************/
GT_STATUS hwSetPagedPhyRegField
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    portNum,
    IN  GT_U8    pageNum,
    IN  GT_U8    regAddr,
    IN  GT_U8    fieldOffset,
    IN  GT_U8    fieldLength,
    IN  GT_U32     anyPage,
    IN  GT_U16   data
)
{
    GT_U16 mask;
    GT_U16 tmpData;
    GT_STATUS   retVal;

    gtSemTake(dev,dev->multiAddrSem,OS_WAIT_FOREVER);

    if((retVal=coreReadPagedPhyReg(dev,portNum,pageNum,regAddr,anyPage,&tmpData)) != GT_OK)
    {
        gtSemGive(dev,dev->multiAddrSem);
        return retVal;
    }

    CALC_MASK(fieldOffset,fieldLength,mask);

    /* Set the desired bits to 0.                       */
    tmpData &= ~mask;
    /* Set the given data into the above reset bits.    */
    tmpData |= ((data << fieldOffset) & mask);

    DBG_INFO(("Write to phy(%d) register: regAddr 0x%x, ",
              portNum,regAddr));
    DBG_INFO(("fieldOff %d, fieldLen %d, data 0x%x.\n",fieldOffset,
              fieldLength,data));
    retVal = coreWritePagedPhyReg(dev,portNum,pageNum,regAddr,anyPage,tmpData);

    gtSemGive(dev,dev->multiAddrSem);

    return retVal;
}


/*******************************************************************************
* hwPhyReset
*
* DESCRIPTION:
*       This function performs softreset and waits until reset completion.
*
* INPUTS:
*       portNum     - Port number to write the register for.
*       u16Data     - data should be written into Phy control register.
*                      if this value is 0xFF, normal operation occcurs (read,
*                      update, and write back.)
*
* OUTPUTS:
*       None.
*
* RETURNS:
*       GT_OK on success, or
*       GT_FAIL otherwise.
*
* COMMENTS:
*
*******************************************************************************/
GT_STATUS hwPhyReset
(
    IN  GT_QD_DEV    *dev,
    IN  GT_U8        portNum,
    IN    GT_U16        u16Data
)
{
    GT_U16 tmpData;
    GT_STATUS   retVal;
    GT_U32 retryCount;
    GT_BOOL    pd = GT_FALSE;

    gtSemTake(dev,dev->multiAddrSem,OS_WAIT_FOREVER);

    if((retVal=coreReadPhyReg(dev,portNum,0,&tmpData))
           != GT_OK)
    {
           DBG_INFO(("Reading Register failed\n"));
        gtSemGive(dev,dev->multiAddrSem);
           return retVal;
    }

    if (tmpData & 0x800)
    {
        pd = GT_TRUE;
    }

    if (u16Data != 0xFF)
    {
        tmpData = u16Data;
    }

    /* Set the desired bits to 0. */
    if (pd)
    {
        tmpData |= 0x800;
    }
    else
    {
        tmpData |= 0x8000;
    }

    if((retVal=coreWritePhyReg(dev,portNum,0,tmpData))
        != GT_OK)
    {
        DBG_INFO(("Writing to register failed\n"));
        gtSemGive(dev,dev->multiAddrSem);
        return retVal;
    }

    if (pd)
    {
        gtSemGive(dev,dev->multiAddrSem);
        return GT_OK;
    }

    for (retryCount = 0x1000; retryCount > 0; retryCount--)
    {
        if((retVal=coreReadPhyReg(dev,portNum,0,&tmpData)) != GT_OK)
        {
            DBG_INFO(("Reading register failed\n"));
            gtSemGive(dev,dev->multiAddrSem);
            return retVal;
        }
        if ((tmpData & 0x8000) == 0)
            break;
    }

    gtSemGive(dev,dev->multiAddrSem);

    if (retryCount == 0)
    {
        DBG_INFO(("Reset bit is not cleared\n"));
        return GT_FAIL;
    }

    return GT_OK;
}

/****************************************************************************/
/* Per port registers related functions.                                    */
/****************************************************************************/

/*******************************************************************************
* hwReadPortReg
*
* DESCRIPTION:
*       This function reads a switch's port register.
*
* INPUTS:
*       portNum - Port number to read the register for.
*       regAddr - The register's address.
*
* OUTPUTS:
*       data    - The read register's data.
*
* RETURNS:
*       GT_OK on success, or
*       GT_FAIL otherwise.
*
* COMMENTS:
*       None.
*
*******************************************************************************/
GT_STATUS hwReadPortReg
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    portNum,
    IN  GT_U8    regAddr,
    OUT GT_U16   *data
)
{
    GT_U8       phyAddr;
    GT_STATUS   retVal;

    phyAddr = CALC_SMI_DEV_ADDR(dev, portNum, PORT_ACCESS);
    if (phyAddr == 0xFF)
    {
        return GT_BAD_PARAM;
    }

    gtSemTake(dev,dev->multiAddrSem,OS_WAIT_FOREVER);

    retVal =  miiSmiIfReadRegister(dev,phyAddr,regAddr,data);

    gtSemGive(dev,dev->multiAddrSem);

    DBG_INFO(("Read from port(%d) register: phyAddr 0x%x, regAddr 0x%x, ",
              portNum,phyAddr,regAddr));
    DBG_INFO(("data 0x%x.\n",*data));
    return retVal;
}


/*******************************************************************************
* hwWritePortReg
*
* DESCRIPTION:
*       This function writes to a switch's port register.
*
* INPUTS:
*       portNum - Port number to write the register for.
*       regAddr - The register's address.
*       data    - The data to be written.
*
* OUTPUTS:
*       None.
*
* RETURNS:
*       GT_OK on success, or
*       GT_FAIL otherwise.
*
* COMMENTS:
*       None.
*
*******************************************************************************/
GT_STATUS hwWritePortReg
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    portNum,
    IN  GT_U8    regAddr,
    IN  GT_U16   data
)
{
    GT_U8   phyAddr;
    GT_STATUS   retVal;

    phyAddr = CALC_SMI_DEV_ADDR(dev, portNum, PORT_ACCESS);
    if (phyAddr == 0xFF)
    {
        return GT_BAD_PARAM;
    }

    DBG_INFO(("Write to port(%d) register: phyAddr 0x%x, regAddr 0x%x, ",
              portNum,phyAddr,regAddr));
    DBG_INFO(("data 0x%x.\n",data));

    gtSemTake(dev,dev->multiAddrSem,OS_WAIT_FOREVER);

    retVal = miiSmiIfWriteRegister(dev,phyAddr,regAddr,data);

    gtSemGive(dev,dev->multiAddrSem);

    return retVal;
}


/*******************************************************************************
* hwGetPortRegField
*
* DESCRIPTION:
*       This function reads a specified field from a switch's port register.
*
* INPUTS:
*       portNum     - Port number to read the register for.
*       regAddr     - The register's address.
*       fieldOffset - The field start bit index. (0 - 15)
*       fieldLength - Number of bits to read.
*
* OUTPUTS:
*       data        - The read register field.
*
* RETURNS:
*       GT_OK on success, or
*       GT_FAIL otherwise.
*
* COMMENTS:
*       1.  The sum of fieldOffset & fieldLength parameters must be smaller-
*           equal to 16.
*
*******************************************************************************/
GT_STATUS hwGetPortRegField
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    portNum,
    IN  GT_U8    regAddr,
    IN  GT_U8    fieldOffset,
    IN  GT_U8    fieldLength,
    OUT GT_U16   *data
)
{
    GT_U16 mask;            /* Bits mask to be read */
    GT_U16 tmpData;
    GT_STATUS   retVal;
    GT_U8       phyAddr;

    phyAddr = CALC_SMI_DEV_ADDR(dev, portNum, PORT_ACCESS);
    if (phyAddr == 0xFF)
    {
        return GT_BAD_PARAM;
    }

    gtSemTake(dev,dev->multiAddrSem,OS_WAIT_FOREVER);

    retVal =  miiSmiIfReadRegister(dev,phyAddr,regAddr,&tmpData);

    gtSemGive(dev,dev->multiAddrSem);

    if (retVal != GT_OK)
        return retVal;

    CALC_MASK(fieldOffset,fieldLength,mask);

    tmpData = (tmpData & mask) >> fieldOffset;
    *data = tmpData;
    DBG_INFO(("Read from port(%d) register: regAddr 0x%x, ",
              portNum,regAddr));
    DBG_INFO(("fOff %d, fLen %d, data 0x%x.\n",fieldOffset,fieldLength,*data));

    return GT_OK;
}


/*******************************************************************************
* hwSetPortRegField
*
* DESCRIPTION:
*       This function writes to specified field in a switch's port register.
*
* INPUTS:
*       portNum     - Port number to write the register for.
*       regAddr     - The register's address.
*       fieldOffset - The field start bit index. (0 - 15)
*       fieldLength - Number of bits to write.
*       data        - Data to be written.
*
* OUTPUTS:
*       None.
*
* RETURNS:
*       GT_OK on success, or
*       GT_FAIL otherwise.
*
* COMMENTS:
*       1.  The sum of fieldOffset & fieldLength parameters must be smaller-
*           equal to 16.
*
*******************************************************************************/
GT_STATUS hwSetPortRegField
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    portNum,
    IN  GT_U8    regAddr,
    IN  GT_U8    fieldOffset,
    IN  GT_U8    fieldLength,
    IN  GT_U16   data
)
{
    GT_U16 mask;
    GT_U16 tmpData;
    GT_STATUS   retVal;
    GT_U8       phyAddr;

    phyAddr = CALC_SMI_DEV_ADDR(dev, portNum, PORT_ACCESS);
    if (phyAddr == 0xFF)
    {
        return GT_BAD_PARAM;
    }

    gtSemTake(dev,dev->multiAddrSem,OS_WAIT_FOREVER);

    retVal =  miiSmiIfReadRegister(dev,phyAddr,regAddr,&tmpData);

    if(retVal != GT_OK)
    {
        gtSemGive(dev,dev->multiAddrSem);
        return retVal;
    }

    CALC_MASK(fieldOffset,fieldLength,mask);

    /* Set the desired bits to 0.                       */
    tmpData &= ~mask;
    /* Set the given data into the above reset bits.    */
    tmpData |= ((data << fieldOffset) & mask);
    DBG_INFO(("Write to port(%d) register: regAddr 0x%x, ",
              portNum,regAddr));
    DBG_INFO(("fieldOff %d, fieldLen %d, data 0x%x.\n",fieldOffset,
              fieldLength,data));

    retVal = miiSmiIfWriteRegister(dev,phyAddr,regAddr,tmpData);

    gtSemGive(dev,dev->multiAddrSem);

    return retVal;
}


/*******************************************************************************
* hwSetPortRegBits
*
* DESCRIPTION:
*       This function writes to specified bits in a switch's port register.
*
* INPUTS:
*       portNum     - Port number to write the register for.
*       regAddr     - The register's address.
*       mask         - The bits to write.
*       data        - Data to be written.
*
* OUTPUTS:
*       None.
*
* RETURNS:
*       GT_OK on success, or
*       GT_FAIL otherwise.
*
* COMMENTS:
*       1.  When Data is 0x1002 and mask is 0xF00F, 0001b is written to bit[31:24]
*            and 0010b is written to bit[3:0]
*
*******************************************************************************/
GT_STATUS hwSetPortRegBits
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    portNum,
    IN  GT_U8    regAddr,
    IN  GT_U16   mask,
    IN  GT_U16   data
)
{
    GT_U16 tmpData;
    GT_STATUS   retVal;
    GT_U8       phyAddr;

    phyAddr = CALC_SMI_DEV_ADDR(dev, portNum, PORT_ACCESS);
    if (phyAddr == 0xFF)
    {
        return GT_BAD_PARAM;
    }

    gtSemTake(dev,dev->multiAddrSem,OS_WAIT_FOREVER);

    retVal =  miiSmiIfReadRegister(dev,phyAddr,regAddr,&tmpData);

    if(retVal != GT_OK)
    {
        gtSemGive(dev,dev->multiAddrSem);
        return retVal;
    }

    /* Set the desired bits to 0.                       */
    tmpData &= ~mask;
    /* Set the given data into the above reset bits.    */
    tmpData |= (data & mask);
    DBG_INFO(("Write to port(%d) register: regAddr 0x%x, ",
              portNum,regAddr));
    DBG_INFO(("mask %d, data 0x%x.\n",mask,data));

    retVal = miiSmiIfWriteRegister(dev,phyAddr,regAddr,tmpData);

    gtSemGive(dev,dev->multiAddrSem);

    return retVal;
}



/****************************************************************************/
/* Global registers related functions.                                      */
/****************************************************************************/

/*******************************************************************************
* hwReadGlobalReg
*
* DESCRIPTION:
*       This function reads a switch's global register.
*
* INPUTS:
*       regAddr - The register's address.
*
* OUTPUTS:
*       data    - The read register's data.
*
* RETURNS:
*       GT_OK on success, or
*       GT_FAIL otherwise.
*
* COMMENTS:
*       None.
*
*******************************************************************************/
GT_STATUS hwReadGlobalReg
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    regAddr,
    OUT GT_U16   *data
)
{
    GT_U8       phyAddr;
    GT_STATUS   retVal;

    phyAddr = CALC_SMI_DEV_ADDR(dev, 0, GLOBAL_REG_ACCESS);

    gtSemTake(dev,dev->multiAddrSem,OS_WAIT_FOREVER);

    retVal = miiSmiIfReadRegister(dev,phyAddr,regAddr,data);

    gtSemGive(dev,dev->multiAddrSem);

    DBG_INFO(("read from global register: phyAddr 0x%x, regAddr 0x%x, ",
              phyAddr,regAddr));
    DBG_INFO(("data 0x%x.\n",*data));
    return retVal;
}


/*******************************************************************************
* hwWriteGlobalReg
*
* DESCRIPTION:
*       This function writes to a switch's global register.
*
* INPUTS:
*       regAddr - The register's address.
*       data    - The data to be written.
*
* OUTPUTS:
*       None.
*
* RETURNS:
*       GT_OK on success, or
*       GT_FAIL otherwise.
*
* COMMENTS:
*       None.
*
*******************************************************************************/
GT_STATUS hwWriteGlobalReg
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    regAddr,
    IN  GT_U16   data
)
{
    GT_U8   phyAddr;
    GT_STATUS   retVal;

    phyAddr = CALC_SMI_DEV_ADDR(dev, 0, GLOBAL_REG_ACCESS);

    DBG_INFO(("Write to global register: phyAddr 0x%x, regAddr 0x%x, ",
              phyAddr,regAddr));
    DBG_INFO(("data 0x%x.\n",data));

    gtSemTake(dev,dev->multiAddrSem,OS_WAIT_FOREVER);

    retVal = miiSmiIfWriteRegister(dev,phyAddr,regAddr,data);

    gtSemGive(dev,dev->multiAddrSem);

    return retVal;
}


/*******************************************************************************
* hwGetGlobalRegField
*
* DESCRIPTION:
*       This function reads a specified field from a switch's global register.
*
* INPUTS:
*       regAddr     - The register's address.
*       fieldOffset - The field start bit index. (0 - 15)
*       fieldLength - Number of bits to read.
*
* OUTPUTS:
*       data        - The read register field.
*
* RETURNS:
*       GT_OK on success, or
*       GT_FAIL otherwise.
*
* COMMENTS:
*       1.  The sum of fieldOffset & fieldLength parameters must be smaller-
*           equal to 16.
*
*******************************************************************************/
GT_STATUS hwGetGlobalRegField
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    regAddr,
    IN  GT_U8    fieldOffset,
    IN  GT_U8    fieldLength,
    OUT GT_U16   *data
)
{
    GT_U16 mask;            /* Bits mask to be read */
    GT_U16 tmpData;
    GT_STATUS   retVal;
    GT_U8       phyAddr;

    phyAddr = CALC_SMI_DEV_ADDR(dev, 0, GLOBAL_REG_ACCESS);

    if (phyAddr == 0xFF)
    {
        return GT_BAD_PARAM;
    }

    gtSemTake(dev,dev->multiAddrSem,OS_WAIT_FOREVER);

    retVal = miiSmiIfReadRegister(dev,phyAddr,regAddr,&tmpData);

    gtSemGive(dev,dev->multiAddrSem);

    if(retVal != GT_OK)
    {
        return retVal;
    }

    CALC_MASK(fieldOffset,fieldLength,mask);
    tmpData = (tmpData & mask) >> fieldOffset;
    *data = tmpData;
    DBG_INFO(("Read from global register: regAddr 0x%x, ",
              regAddr));
    DBG_INFO(("fOff %d, fLen %d, data 0x%x.\n",fieldOffset,fieldLength,*data));

    return GT_OK;
}


/*******************************************************************************
* hwSetGlobalRegField
*
* DESCRIPTION:
*       This function writes to specified field in a switch's global register.
*
* INPUTS:
*       regAddr     - The register's address.
*       fieldOffset - The field start bit index. (0 - 15)
*       fieldLength - Number of bits to write.
*       data        - Data to be written.
*
* OUTPUTS:
*       None.
*
* RETURNS:
*       GT_OK on success, or
*       GT_FAIL otherwise.
*
* COMMENTS:
*       1.  The sum of fieldOffset & fieldLength parameters must be smaller-
*           equal to 16.
*
*******************************************************************************/
GT_STATUS hwSetGlobalRegField
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    regAddr,
    IN  GT_U8    fieldOffset,
    IN  GT_U8    fieldLength,
    IN  GT_U16   data
)
{
    GT_U16 mask;
    GT_U16 tmpData;
    GT_STATUS   retVal;
    GT_U8       phyAddr;

    phyAddr = CALC_SMI_DEV_ADDR(dev, 0, GLOBAL_REG_ACCESS);
    if (phyAddr == 0xFF)
    {
        return GT_BAD_PARAM;
    }

    gtSemTake(dev,dev->multiAddrSem,OS_WAIT_FOREVER);

    retVal =  miiSmiIfReadRegister(dev,phyAddr,regAddr,&tmpData);

    if(retVal != GT_OK)
    {
        gtSemGive(dev,dev->multiAddrSem);
        return retVal;
    }

    CALC_MASK(fieldOffset,fieldLength,mask);

    /* Set the desired bits to 0.                       */
    tmpData &= ~mask;
    /* Set the given data into the above reset bits.    */
    tmpData |= ((data << fieldOffset) & mask);

    DBG_INFO(("Write to global register: regAddr 0x%x, ",
              regAddr));
    DBG_INFO(("fieldOff %d, fieldLen %d, data 0x%x.\n",fieldOffset,
              fieldLength,data));

    retVal = miiSmiIfWriteRegister(dev,phyAddr,regAddr,tmpData);

    gtSemGive(dev,dev->multiAddrSem);

    return retVal;
}

/*******************************************************************************
* hwReadGlobal2Reg
*
* DESCRIPTION:
*       This function reads a switch's global 2 register.
*
* INPUTS:
*       regAddr - The register's address.
*
* OUTPUTS:
*       data    - The read register's data.
*
* RETURNS:
*       GT_OK on success, or
*       GT_FAIL otherwise.
*
* COMMENTS:
*       None.
*
*******************************************************************************/
GT_STATUS hwReadGlobal2Reg
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    regAddr,
    OUT GT_U16   *data
)
{
    GT_U8       phyAddr;
    GT_STATUS   retVal;

    phyAddr = CALC_SMI_DEV_ADDR(dev, 0, GLOBAL2_REG_ACCESS);
    if (phyAddr == 0xFF)
    {
        return GT_BAD_PARAM;
    }

    gtSemTake(dev,dev->multiAddrSem,OS_WAIT_FOREVER);

    retVal = miiSmiIfReadRegister(dev,phyAddr,regAddr,data);

    gtSemGive(dev,dev->multiAddrSem);

    DBG_INFO(("read from global 2 register: phyAddr 0x%x, regAddr 0x%x, ", phyAddr,regAddr));
    DBG_INFO(("data 0x%x.\n",*data));
    return retVal;
}


/*******************************************************************************
* hwWriteGlobal2Reg
*
* DESCRIPTION:
*       This function writes to a switch's global 2 register.
*
* INPUTS:
*       regAddr - The register's address.
*       data    - The data to be written.
*
* OUTPUTS:
*       None.
*
* RETURNS:
*       GT_OK on success, or
*       GT_FAIL otherwise.
*
* COMMENTS:
*       None.
*
*******************************************************************************/
GT_STATUS hwWriteGlobal2Reg
(
    IN  GT_QD_DEV *dev,
    IN  GT_U8    regAddr,
    IN  GT_U16   data
)
{
    GT_U8   phyAddr;
    GT_STATUS   retVal;

    phyAddr = CALC_SMI_DEV_ADDR(dev, 0, GLOBAL2_REG_ACCESS);
    if (phyAddr == 0xFF)
    {
        return GT_BAD_PARAM;
    }

    DBG_INFO(("Write to global 2 register: phyAddr 0x%x, regAddr 0x%x, ", phyAddr,regAddr));
    DBG_INFO(("data 0x%x.\n",data));

    gtSemTake(dev,dev->multiAddrSem,OS_WAIT_FOREVER);

    retVal = miiSmiIfWriteRegister(dev,phyAddr,regAddr,data);

    gtSemGive(dev,dev->multiAddrSem);

    return retVal;
}


/*******************************************************************************
* hwGetGlobal2RegField
*
* DESCRIPTION:
*       This function reads a specified field from a switch's global 2 register.
*
* INPUTS:
*       regAddr     - The register's address.
*       fieldOffset - The field start bit index. (0 - 15)
*       fieldLength - Number of bits to read.
*
* OUTPUTS:
*       data        - The read register field.
*
* RETURNS:
*       GT_OK on success, or
*       GT_FAIL otherwise.
*
* COMMENTS:
*       1.  The sum of fieldOffset & fieldLength parameters must be smaller-
*           equal to 16.
*
*******************************************************************************/
GT_STATUS hwGetGlobal2RegField
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    regAddr,
    IN  GT_U8    fieldOffset,
    IN  GT_U8    fieldLength,
    OUT GT_U16   *data
)
{
    GT_U16 mask;            /* Bits mask to be read */
    GT_U16 tmpData;
    GT_STATUS   retVal;
    GT_U8       phyAddr;

    phyAddr = CALC_SMI_DEV_ADDR(dev, 0, GLOBAL2_REG_ACCESS);
    if (phyAddr == 0xFF)
    {
        return GT_BAD_PARAM;
    }

    gtSemTake(dev,dev->multiAddrSem,OS_WAIT_FOREVER);

    retVal = miiSmiIfReadRegister(dev,phyAddr,regAddr,&tmpData);

    gtSemGive(dev,dev->multiAddrSem);

    if(retVal != GT_OK)
        return retVal;

    CALC_MASK(fieldOffset,fieldLength,mask);
    tmpData = (tmpData & mask) >> fieldOffset;
    *data = tmpData;
    DBG_INFO(("Read from global 2 register: regAddr 0x%x, ",
              regAddr));
    DBG_INFO(("fOff %d, fLen %d, data 0x%x.\n",fieldOffset,fieldLength,*data));

    return GT_OK;
}


/*******************************************************************************
* hwSetGlobal2RegField
*
* DESCRIPTION:
*       This function writes to specified field in a switch's global 2 register.
*
* INPUTS:
*       regAddr     - The register's address.
*       fieldOffset - The field start bit index. (0 - 15)
*       fieldLength - Number of bits to write.
*       data        - Data to be written.
*
* OUTPUTS:
*       None.
*
* RETURNS:
*       GT_OK on success, or
*       GT_FAIL otherwise.
*
* COMMENTS:
*       1.  The sum of fieldOffset & fieldLength parameters must be smaller-
*           equal to 16.
*
*******************************************************************************/
GT_STATUS hwSetGlobal2RegField
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    regAddr,
    IN  GT_U8    fieldOffset,
    IN  GT_U8    fieldLength,
    IN  GT_U16   data
)
{
    GT_U16 mask;
    GT_U16 tmpData;
    GT_STATUS   retVal;
    GT_U8       phyAddr;

    phyAddr = CALC_SMI_DEV_ADDR(dev, 0, GLOBAL2_REG_ACCESS);
    if (phyAddr == 0xFF)
    {
        return GT_BAD_PARAM;
    }

    gtSemTake(dev,dev->multiAddrSem,OS_WAIT_FOREVER);

    retVal = miiSmiIfReadRegister(dev,phyAddr,regAddr,&tmpData);

    if(retVal != GT_OK)
    {
        gtSemGive(dev,dev->multiAddrSem);
        return retVal;
    }

    CALC_MASK(fieldOffset,fieldLength,mask);

    /* Set the desired bits to 0.                       */
    tmpData &= ~mask;
    /* Set the given data into the above reset bits.    */
    tmpData |= ((data << fieldOffset) & mask);

    DBG_INFO(("Write to global 2 register: regAddr 0x%x, ",
              regAddr));
    DBG_INFO(("fieldOff %d, fieldLen %d, data 0x%x.\n",fieldOffset,
              fieldLength,data));

    retVal = miiSmiIfWriteRegister(dev,phyAddr,regAddr,tmpData);

    gtSemGive(dev,dev->multiAddrSem);

    return retVal;
}

/*******************************************************************************
* hwSetGlobal2RegBits
*
* DESCRIPTION:
*       This function writes to specified bits in a switch's global 2 register.
*
* INPUTS:
*       regAddr     - The register's address.
*       mask         - The bits to write.
*       data        - Data to be written.
*
* OUTPUTS:
*       None.
*
* RETURNS:
*       GT_OK on success, or
*       GT_FAIL otherwise.
*
* COMMENTS:
*       1.  When Data is 0x1002 and mask is 0xF00F, 0001b is written to bit[31:24]
*            and 0010b is written to bit[3:0]
*
*******************************************************************************/
GT_STATUS hwSetGlobal2RegBits
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    regAddr,
    IN  GT_U16   mask,
    IN  GT_U16   data
)
{
    GT_U16 tmpData;
    GT_STATUS   retVal;
    GT_U8       phyAddr;

    phyAddr = CALC_SMI_DEV_ADDR(dev, 0, GLOBAL2_REG_ACCESS);
    if (phyAddr == 0xFF)
    {
        return GT_BAD_PARAM;
    }

    gtSemTake(dev,dev->multiAddrSem,OS_WAIT_FOREVER);

    retVal = miiSmiIfReadRegister(dev,phyAddr,regAddr,&tmpData);

    if(retVal != GT_OK)
    {
        gtSemGive(dev,dev->multiAddrSem);
        return retVal;
    }

    /* Set the desired bits to 0.                       */
    tmpData &= ~mask;
    /* Set the given data into the above reset bits.    */
    tmpData |= (data & mask);

    DBG_INFO(("Write to global 2 register: regAddr 0x%x, ",
              regAddr));
    DBG_INFO(("mask %d, data 0x%x.\n",mask,data));

    retVal = miiSmiIfWriteRegister(dev,phyAddr,regAddr,tmpData);

    gtSemGive(dev,dev->multiAddrSem);

    return retVal;
}


/*******************************************************************************
* hwReadGlobal3Reg
*
* DESCRIPTION:
*       This function reads a switch's global 3 register.
*
* INPUTS:
*       regAddr - The register's address.
*
* OUTPUTS:
*       data    - The read register's data.
*
* RETURNS:
*       GT_OK on success, or
*       GT_FAIL otherwise.
*
* COMMENTS:
*       None.
*
*******************************************************************************/
GT_STATUS hwReadGlobal3Reg
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    regAddr,
    OUT GT_U16   *data
)
{
    GT_U8       phyAddr;
    GT_STATUS   retVal;

    phyAddr = CALC_SMI_DEV_ADDR(dev, 0, GLOBAL3_REG_ACCESS);
    if (phyAddr == 0xFF)
    {
        return GT_BAD_PARAM;
    }

    gtSemTake(dev,dev->multiAddrSem,OS_WAIT_FOREVER);

    retVal = miiSmiIfReadRegister(dev,phyAddr,regAddr,data);

    gtSemGive(dev,dev->multiAddrSem);

    DBG_INFO(("read from global 3 register: phyAddr 0x%x, regAddr 0x%x, ", phyAddr,regAddr));
    DBG_INFO(("data 0x%x.\n",*data));
    return retVal;
}


/*******************************************************************************
* hwWriteGlobal3Reg
*
* DESCRIPTION:
*       This function writes to a switch's global 3 register.
*
* INPUTS:
*       regAddr - The register's address.
*       data    - The data to be written.
*
* OUTPUTS:
*       None.
*
* RETURNS:
*       GT_OK on success, or
*       GT_FAIL otherwise.
*
* COMMENTS:
*       None.
*
*******************************************************************************/
GT_STATUS hwWriteGlobal3Reg
(
    IN  GT_QD_DEV *dev,
    IN  GT_U8    regAddr,
    IN  GT_U16   data
)
{
    GT_U8   phyAddr;
    GT_STATUS   retVal;

    phyAddr = CALC_SMI_DEV_ADDR(dev, 0, GLOBAL3_REG_ACCESS);
    if (phyAddr == 0xFF)
    {
        return GT_BAD_PARAM;
    }

    DBG_INFO(("Write to global 3 register: phyAddr 0x%x, regAddr 0x%x, ", phyAddr,regAddr));
    DBG_INFO(("data 0x%x.\n",data));

    gtSemTake(dev,dev->multiAddrSem,OS_WAIT_FOREVER);

    retVal = miiSmiIfWriteRegister(dev,phyAddr,regAddr,data);

    gtSemGive(dev,dev->multiAddrSem);

    return retVal;
}


/*******************************************************************************
* hwGetGlobal3RegField
*
* DESCRIPTION:
*       This function reads a specified field from a switch's global 3 register.
*
* INPUTS:
*       regAddr     - The register's address.
*       fieldOffset - The field start bit index. (0 - 15)
*       fieldLength - Number of bits to read.
*
* OUTPUTS:
*       data        - The read register field.
*
* RETURNS:
*       GT_OK on success, or
*       GT_FAIL otherwise.
*
* COMMENTS:
*       1.  The sum of fieldOffset & fieldLength parameters must be smaller-
*           equal to 16.
*
*******************************************************************************/
GT_STATUS hwGetGlobal3RegField
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    regAddr,
    IN  GT_U8    fieldOffset,
    IN  GT_U8    fieldLength,
    OUT GT_U16   *data
)
{
    GT_U16 mask;            /* Bits mask to be read */
    GT_U16 tmpData;
    GT_STATUS   retVal;
    GT_U8       phyAddr;

    phyAddr = CALC_SMI_DEV_ADDR(dev, 0, GLOBAL3_REG_ACCESS);
    if (phyAddr == 0xFF)
    {
        return GT_BAD_PARAM;
    }

    gtSemTake(dev,dev->multiAddrSem,OS_WAIT_FOREVER);

    retVal = miiSmiIfReadRegister(dev,phyAddr,regAddr,&tmpData);

    gtSemGive(dev,dev->multiAddrSem);

    if(retVal != GT_OK)
        return retVal;

    CALC_MASK(fieldOffset,fieldLength,mask);
    tmpData = (tmpData & mask) >> fieldOffset;
    *data = tmpData;
    DBG_INFO(("Read from global 3 register: regAddr 0x%x, ",
              regAddr));
    DBG_INFO(("fOff %d, fLen %d, data 0x%x.\n",fieldOffset,fieldLength,*data));

    return GT_OK;
}


/*******************************************************************************
* hwSetGlobal3RegField
*
* DESCRIPTION:
*       This function writes to specified field in a switch's global 3 register.
*
* INPUTS:
*       regAddr     - The register's address.
*       fieldOffset - The field start bit index. (0 - 15)
*       fieldLength - Number of bits to write.
*       data        - Data to be written.
*
* OUTPUTS:
*       None.
*
* RETURNS:
*       GT_OK on success, or
*       GT_FAIL otherwise.
*
* COMMENTS:
*       1.  The sum of fieldOffset & fieldLength parameters must be smaller-
*           equal to 16.
*
*******************************************************************************/
GT_STATUS hwSetGlobal3RegField
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    regAddr,
    IN  GT_U8    fieldOffset,
    IN  GT_U8    fieldLength,
    IN  GT_U16   data
)
{
    GT_U16 mask;
    GT_U16 tmpData;
    GT_STATUS   retVal;
    GT_U8       phyAddr;

    phyAddr = CALC_SMI_DEV_ADDR(dev, 0, GLOBAL3_REG_ACCESS);
    if (phyAddr == 0xFF)
    {
        return GT_BAD_PARAM;
    }

    gtSemTake(dev,dev->multiAddrSem,OS_WAIT_FOREVER);

    retVal = miiSmiIfReadRegister(dev,phyAddr,regAddr,&tmpData);

    if(retVal != GT_OK)
    {
        gtSemGive(dev,dev->multiAddrSem);
        return retVal;
    }

    CALC_MASK(fieldOffset,fieldLength,mask);

    /* Set the desired bits to 0.                       */
    tmpData &= ~mask;
    /* Set the given data into the above reset bits.    */
    tmpData |= ((data << fieldOffset) & mask);

    DBG_INFO(("Write to global 3 register: regAddr 0x%x, ",
              regAddr));
    DBG_INFO(("fieldOff %d, fieldLen %d, data 0x%x.\n",fieldOffset,
              fieldLength,data));

    retVal = miiSmiIfWriteRegister(dev,phyAddr,regAddr,tmpData);

    gtSemGive(dev,dev->multiAddrSem);

    return retVal;
}

/*******************************************************************************
* hwSetGlobal3RegBits
*
* DESCRIPTION:
*       This function writes to specified bits in a switch's global 3 register.
*
* INPUTS:
*       regAddr     - The register's address.
*       mask         - The bits to write.
*       data        - Data to be written.
*
* OUTPUTS:
*       None.
*
* RETURNS:
*       GT_OK on success, or
*       GT_FAIL otherwise.
*
* COMMENTS:
*       1.  When Data is 0x1002 and mask is 0xF00F, 0001b is written to bit[31:24]
*            and 0010b is written to bit[3:0]
*
*******************************************************************************/
GT_STATUS hwSetGlobal3RegBits
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    regAddr,
    IN  GT_U16   mask,
    IN  GT_U16   data
)
{
    GT_U16 tmpData;
    GT_STATUS   retVal;
    GT_U8       phyAddr;

    phyAddr = CALC_SMI_DEV_ADDR(dev, 0, GLOBAL3_REG_ACCESS);
    if (phyAddr == 0xFF)
    {
        return GT_BAD_PARAM;
    }

    gtSemTake(dev,dev->multiAddrSem,OS_WAIT_FOREVER);

    retVal = miiSmiIfReadRegister(dev,phyAddr,regAddr,&tmpData);

    if(retVal != GT_OK)
    {
        gtSemGive(dev,dev->multiAddrSem);
        return retVal;
    }

    /* Set the desired bits to 0.                       */
    tmpData &= ~mask;
    /* Set the given data into the above reset bits.    */
    tmpData |= (data & mask);

    DBG_INFO(("Write to global 3 register: regAddr 0x%x, ",
              regAddr));
    DBG_INFO(("mask %d, data 0x%x.\n",mask,data));

    retVal = miiSmiIfWriteRegister(dev,phyAddr,regAddr,tmpData);

    gtSemGive(dev,dev->multiAddrSem);

    return retVal;
}


/*********************************************************************************************/

/*******************************************************************************
* hwReadMiiReg
*
* DESCRIPTION:
*       This function reads a switch register.
*
* INPUTS:
*       phyAddr - Phy Address to read the register for.( 0 ~ 0x1F )
*       regAddr - The register's address.
*
* OUTPUTS:
*       data    - The read register's data.
*
* RETURNS:
*       GT_OK on success, or
*       GT_FAIL otherwise.
*
* COMMENTS:
*       None.
*
*******************************************************************************/
GT_STATUS hwReadMiiReg
(
    IN  GT_QD_DEV *dev,
    IN  GT_U8     phyAddr,
    IN  GT_U8     regAddr,
    OUT GT_U16    *data
)
{
    GT_STATUS   retVal;

    gtSemTake(dev,dev->multiAddrSem,OS_WAIT_FOREVER);

    retVal = miiSmiIfReadRegister(dev,phyAddr,regAddr,data);

     gtSemGive(dev,dev->multiAddrSem);

    DBG_INFO(("Read from phy(0x%x) register: regAddr 0x%x, data 0x%x.\n",
              phyAddr,regAddr,*data));

    return retVal;
}


/*******************************************************************************
* hwWriteMiiReg
*
* DESCRIPTION:
*       This function writes a switch register.
*
* INPUTS:
*       phyAddr - Phy Address to read the register for.( 0 ~ 0x1F )
*       regAddr - The register's address.
*
* OUTPUTS:
*       data    - The read register's data.
*
* RETURNS:
*       GT_OK on success, or
*       GT_FAIL otherwise.
*
* COMMENTS:
*       None.
*
*******************************************************************************/
GT_STATUS hwWriteMiiReg
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    phyAddr,
    IN  GT_U8    regAddr,
    IN  GT_U16   data
)
{
    GT_STATUS   retVal;

    gtSemTake(dev,dev->multiAddrSem,OS_WAIT_FOREVER);

    retVal = miiSmiIfWriteRegister(dev,phyAddr,regAddr,data);

    gtSemGive(dev,dev->multiAddrSem);

    DBG_INFO(("Write to phy(0x%x) register: regAddr 0x%x, data 0x%x.\n",
              phyAddr,regAddr,data));

    return retVal;
}


/*******************************************************************************
* hwReadPPU
*
* DESCRIPTION:
*            This function reads PPU bit in Global Register
*
* INPUTS:
*            None.
*
* OUTPUTS:
*            data    - The read register's data.
*
* RETURNS:
*            GT_OK on success, or
*            GT_FAIL otherwise.
*
* COMMENTS:
*            This function can be used to access PHY register connected to Gigabit
*            Switch.
*            Semaphore should be acquired before this function get called.
*
*******************************************************************************/
static GT_STATUS hwReadPPU
(
    IN  GT_QD_DEV *dev,
    OUT GT_U16    *data
)
{
    GT_STATUS   retVal;
    GT_U16        tmpData;
    GT_U8       phyAddr;

    phyAddr = CALC_SMI_DEV_ADDR(dev, 0, GLOBAL_REG_ACCESS);
    if (phyAddr == 0xFF)
    {
        return GT_BAD_PARAM;
    }

    retVal =  miiSmiIfReadRegister(dev,phyAddr,4,&tmpData);

    if(retVal != GT_OK)
    {
        return retVal;
    }

    *data = (tmpData >> 14) & 0x1;

    DBG_INFO(("OK.\n"));
    return GT_OK;
}

/*******************************************************************************
* hwWritePPU
*
* DESCRIPTION:
*            This function writes PPU bit in Global Register
*
* INPUTS:
*            data - The value to write into PPU bit
*
* OUTPUTS:
*            None.
*
* RETURNS:
*            GT_OK on success, or
*            GT_FAIL otherwise.
*
* COMMENTS:
*            This function can be used to access PHY register connected to Gigabit
*            Switch.
*            Semaphore should be acquired before this function get called.
*
*******************************************************************************/
static GT_STATUS hwWritePPU
(
    IN  GT_QD_DEV *dev,
    IN  GT_U16    data
)
{
    GT_STATUS   retVal;
    GT_U16        tmpData;
    GT_U8       phyAddr;

    phyAddr = CALC_SMI_DEV_ADDR(dev, 0, GLOBAL_REG_ACCESS);
    if (phyAddr == 0xFF)
    {
        return GT_BAD_PARAM;
    }

    retVal =  miiSmiIfReadRegister(dev,phyAddr,4,&tmpData);

    if(retVal != GT_OK)
    {
        return retVal;
    }

    if (data)
        tmpData |= (0x1 << 14);
    else
        tmpData &= ~(0x1 << 14);

    retVal = miiSmiIfWriteRegister(dev,phyAddr,4,tmpData);

    if(retVal != GT_OK)
    {
        return retVal;
    }

    /* busy wait - till PPU is actually disabled */
    if (data == 0) /* disable PPU */
    {
        gtDelay(250);
    }

    DBG_INFO(("OK.\n"));
    return GT_OK;
}


static GT_STATUS coreReadPhyReg
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    portNum,
    IN  GT_U8    regAddr,
    OUT GT_U16   *data
)
{
    GT_U8       phyAddr;
    GT_STATUS   retVal, retPPU = 0;
    GT_U16        orgPPU;
    GT_BOOL        usePPU = GT_FALSE;

    phyAddr = CALC_SMI_DEV_ADDR(dev, portNum, PHY_ACCESS);
    if (phyAddr == 0xFF)
    {
        return GT_BAD_PARAM;
    }

    orgPPU = 0;

    if(IS_IN_DEV_GROUP(dev, DEV_PPU_READ_ONLY))
    {
        if((IS_IN_DEV_GROUP(dev,DEV_PPU_SERDES_ACCESS_RES)) && (dev->validSerdesVec & (1<<phyAddr)))
        {
            if((retPPU=hwReadPPU(dev, &orgPPU)) != GT_OK)
            {
                return retPPU;
            }

            if(orgPPU)
            {
                /* Disable PPU so that External Phy can be accessible */
                if((retPPU=hwWritePPU(dev, 0)) != GT_OK)
                {
                    return retPPU;
                }
            }
        }
        else
        usePPU = GT_TRUE;
    }
    else if(IS_IN_DEV_GROUP(dev,DEV_EXTERNAL_PHY))
    {
        if((retPPU=hwReadPPU(dev, &orgPPU)) != GT_OK)
        {
            return retPPU;
        }

        if(orgPPU)
        {
            if(IS_IN_DEV_GROUP(dev,DEV_PPU_PHY_ACCESS))
            {
                if(IS_IN_DEV_GROUP(dev,DEV_PPU_PHY_ACCESS_RES))
                {
                    if(dev->revision != 0)
                        usePPU = GT_TRUE;
                }
                else
                {
                     usePPU = GT_TRUE;
                }
            }

            /* Disable PPU so that External Phy can be accessible */
            if (!usePPU)
            {
                if((retPPU=hwWritePPU(dev, 0)) != GT_OK)
                {
                    return retPPU;
                }
            }
        }
    }
    else if(IS_IN_DEV_GROUP(dev,DEV_PHY_ACCESS_NO_DIRECTLY))
    {
      usePPU = GT_TRUE;
    }

    if (usePPU)
    {
        retVal = phyRegReadPPUEn (dev,phyAddr,regAddr,data);
    }
    else
    {
        retVal = miiSmiIfReadRegister(dev,phyAddr,regAddr,data);
    }

    DBG_INFO(("Read from phy(%d) register: phyAddr 0x%x, regAddr 0x%x, ", portNum,phyAddr,regAddr));

    if(orgPPU && (!usePPU))
    {
      if((retPPU=hwWritePPU(dev, orgPPU)) != GT_OK)
      {
        return retPPU;
      }
    }

    return retVal;
}


static GT_STATUS coreWritePhyReg
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    portNum,
    IN  GT_U8    regAddr,
    IN  GT_U16   data
)
{
    GT_U8           phyAddr;
    GT_STATUS   retVal, retPPU;
    GT_U16        orgPPU = 0;
    GT_BOOL        usePPU = GT_FALSE;

    phyAddr = CALC_SMI_DEV_ADDR(dev, portNum, PHY_ACCESS);
    if (phyAddr == 0xFF)
    {
        return GT_BAD_PARAM;
    }

    if(IS_IN_DEV_GROUP(dev,DEV_PPU_READ_ONLY))
    {
        if((IS_IN_DEV_GROUP(dev,DEV_PPU_SERDES_ACCESS_RES)) && (dev->validSerdesVec & (1<<phyAddr)))
        {
            if((retPPU=hwReadPPU(dev, &orgPPU)) != GT_OK)
            {
                return retPPU;
            }

            if(orgPPU)
            {
                /* Disable PPU so that External Phy can be accessible */
                if((retPPU=hwWritePPU(dev, 0)) != GT_OK)
                {
                        return retPPU;
                }
            }
        }
        else
          usePPU = GT_TRUE;
    }
    else if(IS_IN_DEV_GROUP(dev,DEV_EXTERNAL_PHY))
    {
        if((retPPU=hwReadPPU(dev, &orgPPU)) != GT_OK)
        {
            return retPPU;
        }

        if(orgPPU)
        {
            if(IS_IN_DEV_GROUP(dev,DEV_PPU_PHY_ACCESS))
            {
                if(IS_IN_DEV_GROUP(dev,DEV_PPU_PHY_ACCESS_RES))
                {
                    if(dev->revision != 0)
                        usePPU = GT_TRUE;
                }
                else
                {
                     usePPU = GT_TRUE;
                }
            }

            /* Disable PPU so that External Phy can be accessible */
            if (!usePPU)
            {
                if((retPPU=hwWritePPU(dev, 0)) != GT_OK)
                {
                    return retPPU;
                }
            }
        }
    }
    else if(IS_IN_DEV_GROUP(dev,DEV_PHY_ACCESS_NO_DIRECTLY))
    {
      usePPU = GT_TRUE;
    }

    DBG_INFO(("Write to phy(%d) register: phyAddr 0x%x, regAddr 0x%x, ",
                portNum,phyAddr,regAddr));
    DBG_INFO(("data 0x%x.\n",data));

    if (usePPU)
    {
        retVal = phyRegWritePPUEn (dev,phyAddr,regAddr,data);
    }
    else
    {
        retVal = miiSmiIfWriteRegister(dev,phyAddr,regAddr,data);
    }

        if(orgPPU && (!usePPU))
        {
            if((retPPU=hwWritePPU(dev, orgPPU)) != GT_OK)
            {
                return retPPU;
            }
        }

    return retVal;
}


static GT_STATUS coreReadPagedPhyReg
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    portNum,
    IN  GT_U8    pageNum,
    IN  GT_U8    regAddr,
    IN  GT_U32     anyPage,
    OUT GT_U16   *data
)
{
    GT_U8       phyAddr,pageAddr;
    GT_STATUS   retVal, retPPU;
    GT_U16        orgPPU, tmpData, orgPage;
    GT_BOOL        usePPU = GT_FALSE;

    phyAddr = CALC_SMI_DEV_ADDR(dev, portNum, PHY_ACCESS);
    if (phyAddr == 0xFF)
    {
        return GT_BAD_PARAM;
    }

    orgPPU = 0;

    if(IS_IN_DEV_GROUP(dev,DEV_PPU_READ_ONLY))
    {
        if((IS_IN_DEV_GROUP(dev,DEV_PPU_SERDES_ACCESS_RES)) && (dev->validSerdesVec & (1<<phyAddr)))
        {
            if((retPPU=hwReadPPU(dev, &orgPPU)) != GT_OK)
            {
                return retPPU;
            }

            if(orgPPU)
            {
                /* Disable PPU so that External Phy can be accessible */
                if((retPPU=hwWritePPU(dev, 0)) != GT_OK)
                {
                    return retPPU;
                }
            }
        }
        else
             usePPU = GT_TRUE;
    }
    else if(IS_IN_DEV_GROUP(dev,DEV_EXTERNAL_PHY))
    {
        if((retPPU=hwReadPPU(dev, &orgPPU)) != GT_OK)
        {
            return retPPU;
        }

        if(orgPPU)
        {
            if(IS_IN_DEV_GROUP(dev,DEV_PPU_PHY_ACCESS))
            {
                if(IS_IN_DEV_GROUP(dev,DEV_PPU_PHY_ACCESS_RES))
                {
                    if(dev->revision != 0)
                        usePPU = GT_TRUE;
                }
                else
                {
                     usePPU = GT_TRUE;
                }
            }

            /* Disable PPU so that External Phy can be accessible */
            if (!usePPU)
            {
                if((retPPU=hwWritePPU(dev, 0)) != GT_OK)
                {
                    return retPPU;
                }
            }
        }
    }

    if(anyPage & (1 << regAddr))
    {
        if (usePPU)
        {
            retVal = phyRegReadPPUEn (dev,phyAddr,regAddr,data);
        }
        else
        {
            retVal = miiSmiIfReadRegister(dev,phyAddr,regAddr,data);
        }
        DBG_INFO(("Read from phy(%d) register: smiAddr 0x%x, pageNum 0x%x, regAddr 0x%x\n",
                    portNum,phyAddr,pageNum,regAddr));
    }
    else
    {
        pageAddr = GT_GET_PAGE_ADDR(regAddr);

        if (usePPU)
        {
            retVal = phyRegReadPPUEn (dev,phyAddr,pageAddr,&orgPage);
        }
        else
        {
            retVal = miiSmiIfReadRegister(dev,phyAddr,pageAddr,&orgPage);
        }

        if (retVal != GT_OK)
        {
            DBG_INFO(("Reading page register failed\n"));
            return retVal;
        }

        if(pageAddr == 22)
            tmpData = orgPage & 0xFF00;
        else
            tmpData = orgPage & 0xFFC0;
        tmpData |= pageNum;

        if (usePPU)
        {
            if((retVal = phyRegWritePPUEn(dev,phyAddr,pageAddr,tmpData)) == GT_OK)
            {
                retVal = phyRegReadPPUEn (dev,phyAddr,regAddr,data);

                DBG_INFO(("Read from phy(%d) register: smiAddr 0x%x, pageNum 0x%x, regAddr 0x%x\n",
                            portNum,phyAddr,pageNum,regAddr));
            }
        }
        else
        {
            if((retVal = miiSmiIfWriteRegister(dev,phyAddr,pageAddr,tmpData)) == GT_OK)
            {
                retVal = miiSmiIfReadRegister(dev,phyAddr,regAddr,data);

                DBG_INFO(("Read from phy(%d) register: smiAddr 0x%x, pageNum 0x%x, regAddr 0x%x\n",
                            portNum,phyAddr,pageNum,regAddr));
            }
        }
    }

        if(orgPPU && (!usePPU))
        {
            if((retPPU=hwWritePPU(dev, orgPPU)) != GT_OK)
            {
                return retPPU;
            }
        }

    return retVal;

}


static GT_STATUS coreWritePagedPhyReg
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    portNum,
    IN  GT_U8    pageNum,
    IN  GT_U8    regAddr,
    IN  GT_U32     anyPage,
    IN  GT_U16   data
)
{
    GT_U8           phyAddr,pageAddr;
    GT_STATUS   retVal, retPPU;
    GT_U16        orgPPU, tmpData, orgPage;
    GT_BOOL        usePPU = GT_FALSE;

    phyAddr = CALC_SMI_DEV_ADDR(dev, portNum, PHY_ACCESS);
    if (phyAddr == 0xFF)
    {
        return GT_BAD_PARAM;
    }

    orgPPU = 0;

    if(IS_IN_DEV_GROUP(dev,DEV_PPU_READ_ONLY))
    {
        if((IS_IN_DEV_GROUP(dev,DEV_PPU_SERDES_ACCESS_RES)) && (dev->validSerdesVec & (1<<phyAddr)))
        {
            if((retPPU=hwReadPPU(dev, &orgPPU)) != GT_OK)
            {
                return retPPU;
            }

            if(orgPPU)
            {
                /* Disable PPU so that External Phy can be accessible */
                if((retPPU=hwWritePPU(dev, 0)) != GT_OK)
                {
                    return retPPU;
                }
            }
        }
        else
             usePPU = GT_TRUE;
    }
    else if(IS_IN_DEV_GROUP(dev,DEV_EXTERNAL_PHY))
    {
        if((retPPU=hwReadPPU(dev, &orgPPU)) != GT_OK)
        {
            return retPPU;
        }

        if(orgPPU)
        {
            if(IS_IN_DEV_GROUP(dev,DEV_PPU_PHY_ACCESS))
            {
                if(IS_IN_DEV_GROUP(dev,DEV_PPU_PHY_ACCESS_RES))
                {
                    if(dev->revision != 0)
                        usePPU = GT_TRUE;
                }
                else
                {
                     usePPU = GT_TRUE;
                }
            }

            /* Disable PPU so that External Phy can be accessible */
            if (!usePPU)
            {
                if((retPPU=hwWritePPU(dev, 0)) != GT_OK)
                {
                    return retPPU;
                }
            }
        }
    }

    DBG_INFO(("Write to phy(%d) register: smiAddr 0x%x, pageNum 0x%x, regAddr 0x%x\n",
                portNum,phyAddr,pageNum,regAddr));
    DBG_INFO(("data 0x%x.\n",data));

    if(anyPage & (1 << regAddr))
    {
        if (usePPU)
        {
            retVal = phyRegWritePPUEn (dev,phyAddr,regAddr,data);
        }
        else
        {
            retVal = miiSmiIfWriteRegister(dev,phyAddr,regAddr,data);
        }
    }
    else
    {
        pageAddr = GT_GET_PAGE_ADDR(regAddr);

        if (usePPU)
        {
            retVal = phyRegReadPPUEn (dev,phyAddr,pageAddr,&orgPage);
        }
        else
        {
            retVal = miiSmiIfReadRegister(dev,phyAddr,pageAddr,&orgPage);
        }

        if (retVal != GT_OK)
        {
            DBG_INFO(("Reading page register failed\n"));
            return retVal;
        }

        if(pageAddr == 22)
            tmpData = orgPage & 0xFF00;
        else
            tmpData = orgPage & 0xFFC0;
        tmpData |= pageNum;

        if (usePPU)
        {
            if((retVal = phyRegWritePPUEn(dev,phyAddr,pageAddr,tmpData)) == GT_OK)
            {
                retVal = phyRegWritePPUEn(dev,phyAddr,regAddr,data);
            }
        }
        else
        {
            if((retVal = miiSmiIfWriteRegister(dev,phyAddr,pageAddr,tmpData)) == GT_OK)
            {
                retVal = miiSmiIfWriteRegister(dev,phyAddr,regAddr,data);
            }
        }
    }

        if(orgPPU && (!usePPU))
        {
            if((retPPU=hwWritePPU(dev, orgPPU)) != GT_OK)
            {
                return retPPU;
            }
        }

    return retVal;
}


/*****************************************************************************
* phyRegReadPPUEn
*
* DESCRIPTION:
*       This function reads phy register data when PPU is enabled.
*
* INPUTS:
*       phyAddr     - The PHY address to be read.
*       regAddr     - The register address to read.
*       value       - The storage where register date to be saved.
*
* OUTPUTS:
*       None.
*
* RETURNS:
*       GT_TRUE   - on success
*       GT_FALSE  - on error
*
* COMMENTS:
*       None.
*
*******************************************************************************/
GT_STATUS phyRegReadPPUEn (GT_QD_DEV* dev, unsigned int phyAddr , unsigned int regAddr,
                        unsigned short* value)
#ifdef GT_RMGMT_ACCESS
{
  GT_U16 smiReg;
  GT_STATUS   retVal;

  HW_DEV_REG_ACCESS regAccess;

  DBG_INFO(("Read Phy register while PPU Enabled\n"));

  regAccess.entries = 4;

  regAccess.rw_reg_list[0].cmd = HW_REG_WAIT_TILL_0;
  regAccess.rw_reg_list[0].addr = CALC_SMI_DEV_ADDR(dev, 0, GLOBAL2_REG_ACCESS);
  regAccess.rw_reg_list[0].reg = QD_REG_SMI_PHY_CMD;
  regAccess.rw_reg_list[0].data = 15;
  smiReg =  QD_SMI_BUSY | (phyAddr << QD_SMI_DEV_ADDR_BIT) | (QD_SMI_READ << QD_SMI_OP_BIT) | (regAddr << QD_SMI_REG_ADDR_BIT) | (QD_SMI_CLAUSE22 << QD_SMI_MODE_BIT);

  regAccess.rw_reg_list[1].cmd = HW_REG_WRITE;
  regAccess.rw_reg_list[1].addr = CALC_SMI_DEV_ADDR(dev, 0, GLOBAL2_REG_ACCESS);
  regAccess.rw_reg_list[1].reg = QD_REG_SMI_PHY_CMD;
  regAccess.rw_reg_list[1].data = smiReg;

  regAccess.rw_reg_list[2].cmd = HW_REG_WAIT_TILL_0;
  regAccess.rw_reg_list[2].addr = CALC_SMI_DEV_ADDR(dev, 0, GLOBAL2_REG_ACCESS);
  regAccess.rw_reg_list[2].reg = QD_REG_SMI_PHY_CMD;
  regAccess.rw_reg_list[2].data = 15;

  regAccess.rw_reg_list[3].cmd = HW_REG_READ;
  regAccess.rw_reg_list[3].addr = CALC_SMI_DEV_ADDR(dev, 0, GLOBAL2_REG_ACCESS);
  regAccess.rw_reg_list[3].reg = QD_REG_SMI_PHY_DATA;
  regAccess.rw_reg_list[3].data = 0;
  retVal = hwAccessMultiRegs(dev, &regAccess);
  if(retVal != GT_OK)
  {
    return retVal;
  }
  *value = (unsigned short)regAccess.rw_reg_list[3].data;

  return GT_OK;
}
#else
{
    volatile unsigned int timeOut; /* in 100MS units */
    volatile int i;
    GT_U16 smiReg;

    DBG_INFO(("Read Phy register while PPU Enabled\n"));

    /* first check that it is not busy */
    if(phyReadGlobal2Reg(dev,QD_REG_SMI_PHY_CMD, &smiReg) != GT_OK)
    {
        DBG_INFO(("Reading Phy register Failed\n"));
        return GT_FAIL;
    }
    timeOut = QD_SMI_ACCESS_LOOP; /* initialize the loop count */

    if(smiReg & QD_SMI_BUSY)
    {
        for(i = 0 ; i < QD_SMI_TIMEOUT ; i++);
        do
        {
            if(timeOut-- < 1 )
            {
                DBG_INFO(("Reading Phy register Timed Out\n"));
                return GT_FAIL;
            }
            if(phyReadGlobal2Reg(dev,QD_REG_SMI_PHY_CMD, &smiReg) != GT_OK)
            {
                DBG_INFO(("Reading Phy register Failed\n"));
                return GT_FAIL;
            }
        } while (smiReg & QD_SMI_BUSY);
    }

    smiReg =  QD_SMI_BUSY | (phyAddr << QD_SMI_DEV_ADDR_BIT) | (QD_SMI_READ << QD_SMI_OP_BIT) |
            (regAddr << QD_SMI_REG_ADDR_BIT) | (QD_SMI_CLAUSE22 << QD_SMI_MODE_BIT);

    if(phyWriteGlobal2Reg(dev,QD_REG_SMI_PHY_CMD, smiReg) != GT_OK)
    {
        return GT_FAIL;
    }
    timeOut = QD_SMI_ACCESS_LOOP; /* initialize the loop count */
    if(phyReadGlobal2Reg(dev,QD_REG_SMI_PHY_CMD, &smiReg) != GT_OK)
    {
        return GT_FAIL;
    }

    if(smiReg & QD_SMI_BUSY)
    {
        for(i = 0 ; i < QD_SMI_TIMEOUT ; i++);
        do
        {
            if(timeOut-- < 1 )
            {
                DBG_INFO(("Reading Phy register Timed Out\n"));
                return GT_FALSE;
            }
            if(phyReadGlobal2Reg(dev,QD_REG_SMI_PHY_CMD, &smiReg) != GT_OK)
            {
                DBG_INFO(("Reading Phy register Failed\n"));
                return GT_FAIL;
            }
        } while (smiReg & QD_SMI_BUSY);
    }
    if(phyReadGlobal2Reg(dev,QD_REG_SMI_PHY_DATA, &smiReg) != GT_OK)
    {
        DBG_INFO(("Reading Phy register Failed\n"));
        return GT_FAIL;
    }
    *value = (unsigned short)smiReg;

    return GT_OK;
}
#endif

/*****************************************************************************
* phyRegWritePPUEn
*
* DESCRIPTION:
*       This function writes data to a phy register when PPU is enabled.
*
* INPUTS:
*       phyAddr     - The PHY address to be read.
*       regAddr     - The register address to read.
*       value       - The data to be written into the register.
*
* OUTPUTS:
*       None.
*
* RETURNS:
*       GT_TRUE   - on success
*       GT_FALSE  - on error
*
* COMMENTS:
*       None.
*
*******************************************************************************/

GT_STATUS phyRegWritePPUEn (GT_QD_DEV* dev, unsigned int phyAddr , unsigned int regAddr,
                       unsigned short value)
#ifdef GT_RMGMT_ACCESS
{
  GT_U16 smiReg;
  GT_STATUS   retVal;

  HW_DEV_REG_ACCESS regAccess;

  DBG_INFO(("Write Phy register while PPU Enabled\n"));

  regAccess.entries = 3;

  regAccess.rw_reg_list[0].cmd = HW_REG_WAIT_TILL_0;
  regAccess.rw_reg_list[0].addr = CALC_SMI_DEV_ADDR(dev, 0, GLOBAL2_REG_ACCESS);
  regAccess.rw_reg_list[0].reg = QD_REG_SMI_PHY_CMD;
  regAccess.rw_reg_list[0].data = 15;

  regAccess.rw_reg_list[1].cmd = HW_REG_WRITE;
  regAccess.rw_reg_list[1].addr = CALC_SMI_DEV_ADDR(dev, 0, GLOBAL2_REG_ACCESS);
  regAccess.rw_reg_list[1].reg = QD_REG_SMI_PHY_DATA;
  regAccess.rw_reg_list[1].data = value;

  smiReg = QD_SMI_BUSY | (phyAddr << QD_SMI_DEV_ADDR_BIT) | (QD_SMI_WRITE << QD_SMI_OP_BIT) | (regAddr << QD_SMI_REG_ADDR_BIT) | (QD_SMI_CLAUSE22 << QD_SMI_MODE_BIT);

  regAccess.rw_reg_list[2].cmd = HW_REG_WRITE;
  regAccess.rw_reg_list[2].addr = CALC_SMI_DEV_ADDR(dev, 0, GLOBAL2_REG_ACCESS);
  regAccess.rw_reg_list[2].reg = QD_REG_SMI_PHY_CMD;
  regAccess.rw_reg_list[2].data = smiReg;

  retVal = hwAccessMultiRegs(dev, &regAccess);
  if(retVal != GT_OK)
  {
    return retVal;
  }

  return GT_OK;
}
#else
{
    volatile unsigned int timeOut; /* in 100MS units */
    volatile int i;
    GT_U16 smiReg;

    DBG_INFO(("Writing Phy register while PPU Enabled\n"));

    /* first check that it is not busy */
    if(phyReadGlobal2Reg(dev,QD_REG_SMI_PHY_CMD, &smiReg) != GT_OK)
    {
        DBG_INFO(("Reading Phy register Failed\n"));
        return GT_FAIL;
    }
    timeOut = QD_SMI_ACCESS_LOOP; /* initialize the loop count */


    if(smiReg & QD_SMI_BUSY)
    {
        for(i = 0 ; i < QD_SMI_TIMEOUT ; i++);
        do
        {
            if(timeOut-- < 1 )
            {
                DBG_INFO(("Writing Phy register Timed Out\n"));
                return GT_FALSE;
            }
            if(phyReadGlobal2Reg(dev,QD_REG_SMI_PHY_CMD, &smiReg) != GT_OK)
            {
                DBG_INFO(("Writing Phy register Failed\n"));
                return GT_FAIL;
            }
        } while (smiReg & QD_SMI_BUSY);
    }

    if(phyWriteGlobal2Reg(dev,QD_REG_SMI_PHY_DATA, value) != GT_OK)
    {
        DBG_INFO(("Writing Phy Data register Failed\n"));
        return GT_FAIL;
    }
    smiReg = QD_SMI_BUSY | (phyAddr << QD_SMI_DEV_ADDR_BIT) | (QD_SMI_WRITE << QD_SMI_OP_BIT) |
            (regAddr << QD_SMI_REG_ADDR_BIT) | (QD_SMI_CLAUSE22 << QD_SMI_MODE_BIT);

    if(phyWriteGlobal2Reg(dev,QD_REG_SMI_PHY_CMD, smiReg) != GT_OK)
    {
        DBG_INFO(("Writing Phy Command register Failed\n"));
        return GT_FAIL;
    }

    return GT_OK;
}

static GT_STATUS phyReadGlobal2Reg
(
    IN GT_QD_DEV *dev,
    IN  GT_U8    regAddr,
    OUT GT_U16   *data
)
{
    GT_U8       phyAddr;
    GT_STATUS   retVal;

    phyAddr = CALC_SMI_DEV_ADDR(dev, 0, GLOBAL2_REG_ACCESS);
    if (phyAddr == 0xFF)
    {
        return GT_BAD_PARAM;
    }

    retVal = miiSmiIfReadRegister(dev,phyAddr,regAddr,data);

    DBG_INFO(("read from global 2 register: phyAddr 0x%x, regAddr 0x%x, ",
              phyAddr,regAddr));
    DBG_INFO(("data 0x%x.\n",*data));
    return retVal;
}


static GT_STATUS phyWriteGlobal2Reg
(
    IN  GT_QD_DEV *dev,
    IN  GT_U8    regAddr,
    IN  GT_U16   data
)
{
    GT_U8   phyAddr;
    GT_STATUS   retVal;

    phyAddr = CALC_SMI_DEV_ADDR(dev, 0, GLOBAL2_REG_ACCESS);
    if (phyAddr == 0xFF)
    {
        return GT_BAD_PARAM;
    }

    retVal = miiSmiIfWriteRegister(dev,phyAddr,regAddr,data);

    return retVal;
}
#endif

#ifdef GT_RMGMT_ACCESS
/*******************************************************************************
* hwAccessMultiRegs
*
* DESCRIPTION:
*       This function accesses switch's registers.
*
* INPUTS:
*   regList     - list of HW_DEV_RW_REG.
*     HW_DEV_RW_REG:
*     cmd - HW_REG_READ, HW_REG_WRITE, HW_REG_WAIT_TILL_0 or HW_REG_WAIT_TILL_1
*     addr - SMI Address
*     reg  - Register offset
*     data - INPUT,OUTPUT:Value in the Register or Bit number
*
* OUTPUTS:
*   regList
*
* RETURNS:
*       GT_OK on success, or
*       GT_FAIL otherwise.
*
* COMMENTS:
*       None.
*
*******************************************************************************/
GT_STATUS hwAccessMultiRegs
(
    IN GT_QD_DEV *dev,
    INOUT HW_DEV_REG_ACCESS *regList
)
{
  GT_STATUS   retVal;

  gtSemTake(dev,dev->hwAccessRegsSem,OS_WAIT_FOREVER);

  retVal = qdAccessRegs(dev, regList);

  gtSemGive(dev,dev->hwAccessRegsSem);

  return retVal;
}
#endif
