📄 halw90p710mac.c
字号:
{
return TRUE;
}
/**
* @brief
* 获取该网络设备的网络连接情况。
*
* @param[in] vpEtherDevData 设备数据块指针,该结构的类型由HAL定义。
* @param[out] wplineStatus 连接状态。
DNET_IFOPERSTATUS_UP 或者 DNET_IFOPERSTATUS_DOWN。
*
* @return FALSE 失败(始终返回该值)。
*/
T_BOOL W90P710MAC_LineCheck(T_VOID *vpEtherDevData, T_WORD *wplineStatus)
{
return FALSE;
}
/**
* @brief
* 获取设备的MAC地址。
*
* @param[in vpEtherDevData 设备数据块指针,该结构的类型由HAL定义。
* @param[out] bpmacAddr 存放MAC地址的缓存。
*
* @return TRUE 成功 (始终返回该值)。
*/
T_BOOL W90P710MAC_GetMacAddr(T_VOID *vpEtherDevData, T_CHAR *bpmacAddr)
{
T_WORD i;
T_HAL_W90P710MAC_DEV_DATA *tpEtherDevDataTable = (T_HAL_W90P710MAC_DEV_DATA *)vpEtherDevData;
for(i = 0; i < 6; i++)
{
bpmacAddr[i] = tpEtherDevDataTable->p710_priv->devmac[i];
}
return TRUE;
}
/**
* @brief
* 获取设备的MAC地址。
*
* @param[in vpEtherDevData 设备数据块指针,该结构的类型由HAL定义。
* @param[out] bpmacAddr 存放MAC地址的缓存。
*
* @return TRUE 成功 (始终返回该值)。
*/
T_BOOL W90P710MAC_SetMacAddr( T_VOID *vpEtherDevData, T_CHAR *bpmacAddr )
{
T_HAL_W90P710MAC_DEV_DATA *tpEtherDevDataTable = (T_HAL_W90P710MAC_DEV_DATA *)vpEtherDevData;
p710_WriteCam(tpEtherDevDataTable->p710_priv->which,0,bpmacAddr);
return TRUE;
}
/**
* @brief
* 增加一个组播地址到该网卡
*
* @param[in] pEtherDevData 设备数据块指针,该结构的类型由HAL定义
*
* @param[in] macAddr 指向一个6字节的存储空间,内容为需要增加的组播MAC地址
*
* @param[in] multiMacChian 指向一个组播地址链,该链上的组播地址应该都被设置进入该网卡.该链的结构是
* typedef struct ether_multi{
* char haddr[6]; //组播地址
* unsigned short emc_users; //该组播地址的用户数,对于驱动,不需要关心该参数
* struct ether_multi * next; //指向下一节点
* }ETHER_MULTI;
*
* typedef struct macforhash{
* unsigned char macaddr[6]; //要操作的组播MAC地址
* ETHER_MULTI * chainpointer; //该设备需要设置的组播地址链
* }T_MACHASH;
* multiMacChian为 T_MACHASH 指针类型,该参数的使用是可选的.
* 即,HAL中,增加组播地址的实现既可仅根据macaddr参数进行操作,
* 也可以根据multiMacChain来全部重新设定网卡组播地址
*
* @return
* FALSE 失败
* TRUE 成功
*/
T_BOOL W90P710MAC_AddMultiAddr( T_VOID * vpEtherDevData, T_CHAR *bMacAddr, T_VOID * vMultiMacChain)
{
return TRUE;
}
/**
* @brief
* 删除该网卡的一个组播地址
*
* @param[in] pEtherDevData 设备数据块指针,该结构的类型由HAL定义
*
* @param[in] macAddr 指向一个6字节的存储空间,内容为需要删除的组播MAC地址
*
* @param[in] multiMacChian 指向一个组播地址链,该链上的组播地址应该都被设置进入该网卡.该链的结构是
* typedef struct ether_multi{
* char haddr[6]; //组播地址
* unsigned short emc_users; //该组播地址的用户数,对于驱动,不需要关心该参数
* struct ether_multi * next; //指向下一节点
* }ETHER_MULTI;
*
* typedef struct macforhash{
* unsigned char macaddr[6]; //要操作的组播MAC地址
* ETHER_MULTI * chainpointer; //该设备需要设置的组播地址链
* }T_MACHASH;
* multiMacChian为 T_MACHASH 指针类型,该参数的使用是可选的.
* 即,HAL中,删除组播地址的实现既可仅根据macaddr参数进行操作,
* 也可以根据multiMacChain来全部重新设定网卡组播地址
*
* @return
* FALSE 失败
* TRUE 成功
*/
T_BOOL W90P710MAC_DelMultiAddr( T_VOID * vpEtherDevData, T_CHAR *bMacAddr, T_VOID * vMultiMacChain)
{
return TRUE;
}
/**
* @brief
* 通过读取芯片的vendor,判断W90P710MAC是否存在。
*
* @param[in] tpEtherDevDataTable 设备数据块指针,该结构的类型由HAL定义。
* @param[in] wIndex 该设备在系统中相同设备的索引。
*
* @return
* FALSE 失败
* TRUE 成功
*/
T_MODULE T_BOOL Probe(T_HAL_W90P710MAC_DEV_DATA * vpEtherDevData)
{
//T_HAL_W90P710MAC_DEV_DATA *tpEtherDevDataTable = (T_HAL_W90P710MAC_DEV_DATA *)vpEtherDevData;
*((T_VUWORD *) 0xFFF83020) = 0x55555;//设置 GPIO Port2 Configuration to PHY
return TRUE;
}
/**
* @brief
* 初始化发送和接收环。
*
* @param[in] tpEtherDevDataTable 设备数据块指针,该结构的类型由HAL定义。
*
* @return
* FALSE 失败
* TRUE 成功
*/
T_MODULE T_VOID init_rxtx_rings(T_HAL_W90P710MAC_DEV_DATA *vpEtherDevData)
{
T_WORD i;
T_HAL_W90P710MAC_DEV_DATA *tpEtherDevDataTable = (T_HAL_W90P710MAC_DEV_DATA *)vpEtherDevData;
tpEtherDevDataTable->p710_priv->start_tx_ptr = (T_UWORD)&tpEtherDevDataTable->p710_priv->tx_desc[0]| NON_CACHE_FLAG;
tpEtherDevDataTable->p710_priv->start_tx_buf = (T_UWORD)&tpEtherDevDataTable->p710_priv->tx_buf[0] | NON_CACHE_FLAG;
tpEtherDevDataTable->p710_priv->start_rx_ptr = (T_UWORD)&tpEtherDevDataTable->p710_priv->rx_desc[0]| NON_CACHE_FLAG;
tpEtherDevDataTable->p710_priv->start_rx_buf = (T_UWORD)&tpEtherDevDataTable->p710_priv->rx_buf[0] | NON_CACHE_FLAG;
//Tx Ring
for ( i = 0 ; i < TX_DESC_SIZE ; i++ )
{
//p710_priv->tx_desc[i]=0;
tpEtherDevDataTable->p710_priv->tx_desc[i].SL = 0;
tpEtherDevDataTable->p710_priv->tx_desc[i].mode = 0;
tpEtherDevDataTable->p710_priv->tx_desc[i].buffer = (T_UWORD)&tpEtherDevDataTable->p710_priv->tx_buf[i]|NON_CACHE_FLAG;
tpEtherDevDataTable->p710_priv->tx_desc[i].next = (T_UWORD)&tpEtherDevDataTable->p710_priv->tx_desc[i+1]|NON_CACHE_FLAG;
//printf(" *tx cur %d desc %x buffer %x", i, &tpEtherDevDataTable->p710_priv->tx_desc[i],tpEtherDevDataTable->p710_priv->tx_desc[i].buffer);
//printf(" next %x\n",tpEtherDevDataTable->p710_priv->tx_desc[i].next);
}
tpEtherDevDataTable->p710_priv->tx_desc[i-1].next = (T_UWORD)&tpEtherDevDataTable->p710_priv->tx_desc[0]|NON_CACHE_FLAG;
//printf(" * cur %d desc %x buffer %x", i-1, &tpEtherDevDataTable->p710_priv->tx_desc[i-1],tpEtherDevDataTable->p710_priv->tx_desc[i-1].buffer);
//printf(" next %x\n",tpEtherDevDataTable->p710_priv->tx_desc[i-1].next);
//Rx Ring
for( i = 0 ; i < RX_DESC_SIZE ; i++)
{
tpEtherDevDataTable->p710_priv->rx_desc[i].SL = RXfOwnership_DMA;
tpEtherDevDataTable->p710_priv->rx_desc[i].buffer = (T_UWORD)&tpEtherDevDataTable->p710_priv->rx_buf[i]|NON_CACHE_FLAG;
tpEtherDevDataTable->p710_priv->rx_desc[i].next = (T_UWORD)&tpEtherDevDataTable->p710_priv->rx_desc[i+1]|NON_CACHE_FLAG;
}
tpEtherDevDataTable->p710_priv->rx_desc[i-1].next = (T_UWORD)&tpEtherDevDataTable->p710_priv->rx_desc[0]|NON_CACHE_FLAG;
}
/**
* @brief
* 重设MAC控制器。
*
* @param[in] tpEtherDevDataTable 设备数据块指针,该结构的类型由HAL定义。
*
* @return
* 空
*
*/
T_VOID ResetMAC(T_HAL_W90P710MAC_DEV_DATA *vpEtherDevData)
{
T_HAL_W90P710MAC_DEV_DATA *tpEtherDevDataTable = (T_HAL_W90P710MAC_DEV_DATA *)vpEtherDevData;
T_WORD which = tpEtherDevDataTable->p710_priv->which ;
T_UWORD val = p710_ReadReg(MCMDR,which);
p710_WriteReg(FIFOTHD,0x10000,which); //0x10100
p710_WriteReg(MCMDR,p710_ReadReg(MCMDR,which)&~(MCMDR_TXON|MCMDR_RXON),which);
p710_WriteReg(FIFOTHD,0x100300,which); //0x10100
p710_WriteReg(MCMDR,p710_ReadReg(MCMDR,which)|SWR,which); //Software reset
//printk("Reset MAC MCMDR:%x\n",p710_ReadReg(MCMDR,which));
init_rxtx_rings(tpEtherDevDataTable);
tpEtherDevDataTable->p710_priv->cur_tx_entry = 0;
tpEtherDevDataTable->p710_priv->cur_rx_entry = 0;
tpEtherDevDataTable->p710_priv->rx_ptr = tpEtherDevDataTable->p710_priv->start_rx_ptr ;
tpEtherDevDataTable->p710_priv->tx_ptr = tpEtherDevDataTable->p710_priv->start_tx_ptr ;
tpEtherDevDataTable->p710_priv->tx_finish_ptr = tpEtherDevDataTable->p710_priv->tx_ptr;
p710_WriteReg(RXDLSA,tpEtherDevDataTable->p710_priv->start_rx_ptr,which);
p710_WriteReg(TXDLSA,tpEtherDevDataTable->p710_priv->start_tx_ptr,which);
p710_WriteReg(DMARFC,PACKET_SIZE,which);
p710_WriteCam(tpEtherDevDataTable->p710_priv->which,0,tpEtherDevDataTable->p710_priv->devmac); // set mac
p710_WriteReg(CAMEN,p710_ReadReg(CAMEN,tpEtherDevDataTable->p710_priv->which) | 1,tpEtherDevDataTable->p710_priv->which);
p710_WriteReg(CAMCMR,CAMCMR_ECMP|CAMCMR_ABP|CAMCMR_AMP,which);
/* Configure the MAC control registers. */
p710_WriteReg(MIEN,gMIEN,which);
//Enable_Int(INT_EMCTXINT0);
//Enable_Int(INT_EMCRXINT0);
p710_WriteReg(MCMDR,MCMDR_TXON|MCMDR_RXON|val,which);
p710_WriteReg(TSDR ,0,which);
p710_WriteReg(RSDR ,0,which);
p710_WriteReg(MISTA,p710_ReadReg(MISTA,which),which); //clear interrupt
}
T_VOID p710_WriteCam(T_WORD which, T_WORD x, T_UBYTE *pval)
{
T_UWORD msw;
T_UWORD lsw;
msw = (pval[0] << 24) |
(pval[1] << 16) |
(pval[2] << 8) |
pval[3];
lsw = (pval[4] << 24) |
(pval[5] << 16);
p710_WriteCam0(which,0,lsw,msw);
}
/**
* @brief
* 重设phy控制器。
*
* @param[in] tpEtherDevDataTable 设备数据块指针,该结构的类型由HAL定义。
*
* @return
* 空
*
*/
T_VOID ResetP(T_WORD num)
{
MiiStationWrite(num,PHY_CNTL_REG,0x0100,RESET_PHY);
}
/**
* @brief
* MiiStationWrite: 写到MII 状态控制寄存器。
*
* @param[in] num 设备数据块指针,该结构的类型由HAL定义。
* @param[in] PhyInAddr PHY 寄存器地址
* @param[in] PhyAddr 地址写到
* @param[in] PhyWrData 数据写
*
* @return
* FALSE 失败
* TRUE 成功
*
*/
T_WORD MiiStationWrite(T_WORD num, T_UWORD PhyInAddr, T_UWORD PhyAddr, T_UWORD PhyWrData)
{
volatile int i = 1000;
int which=num;
volatile int loop=1000*100;
#ifdef IC_PLUS1
num = 0;
#endif
which=num;
p710_WriteReg(MIID,PhyWrData,which);
p710_WriteReg(MIIDA,PhyInAddr|PhyAddr|PHYBUSY|PHYWR|MDCCR1,which);
while(i--);
while((p710_ReadReg(MIIDA,which) &PHYBUSY))
{
loop--;
if(loop==0)
return 1;
}
//printk("MiiStationWrite 1\n");
return 0;
}
/**
* @brief
* MiiStationRead: 从MII读 状态控制寄存器。
*
* @param[in] num 设备数据块指针,该结构的类型由HAL定义。
* @param[in] PhyInAddr PHY 寄存器地址
* @param[in] PhyAddr 地址写到
* @param[in] PhyWrData 数据写
*
* @return
* PhyRdData
*
*
*/
T_UWORD MiiStationRead(T_WORD num, T_UWORD PhyInAddr, T_UWORD PhyAddr)
{
T_UWORD PhyRdData ;
T_WORD which=num;
T_VWORD loop=1000*100;
which=num;
#define MDCCR1 0x00a00000 // MDC clock rating
p710_WriteReg(MIIDA, PhyInAddr | PhyAddr | PHYBUSY | MDCCR1,which);
while( (p710_ReadReg(MIIDA,which)& PHYBUSY) )
{
loop--;
if(loop==0)
return (unsigned long)1;
}
PhyRdData = p710_ReadReg(MIID,which) ;
return PhyRdData ;
}
/**
* @brief
* 重设PHY控制器。
*
* @param[in] tpEtherDevDataTable 设备数据块指针,该结构的类型由HAL定义。
*
* @return
* 空
*
*/
T_WORD ResetPhyChip(T_WORD num)
{
T_UWORD RdValue;
T_WORD which = num;
T_VWORD loop=1000*100;
//MiiStationWrite(which, PHY_ANA_REG, PHYAD, DR10_TX_HALF|IEEE_802_3_CSMA_CD);
if(MiiStationWrite(which, PHY_CNTL_REG, PHYAD, ENABLE_AN | RESTART_AN)==1)
{
return 1;
}
while (1) /* wait for auto-negotiation complete */
{
RdValue = MiiStationRead(which, PHY_STATUS_REG, PHYAD) ;
if(RdValue==(unsigned long)1)
{
printk("ResetPhyChip failed 1\n");
return 1;
}
if ((RdValue & AN_COMPLETE) != 0)
{
break;
}
loop--;
if(loop==0)
{
return 1;
}
}
/* read the result of auto-negotiation */
RdValue = MiiStationRead(which, PHY_CNTL_REG, PHYAD) ;
if(RdValue==(T_UWORD)1)
return 1;
if ((RdValue & DR_100MB)!=0) /* 100MB */
{
p710_WriteReg(MCMDR,p710_ReadReg(MCMDR,which)|MCMDR_OPMOD,which);
}
else
{
p710_WriteReg(MCMDR,p710_ReadReg(MCMDR,which)&~MCMDR_OPMOD,which);
}
if ((RdValue & PHY_FULLDUPLEX) != 0) /* Full Duplex */
{
p710_WriteReg(MCMDR,p710_ReadReg(MCMDR,which)|MCMDR_FDUP,which);
}
else
{
p710_WriteReg(MCMDR,p710_ReadReg(MCMDR,which)&~MCMDR_FDUP,which);
}
return 0;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -