STM32之DP83848

/******************************************************************************
* 文 件  名 称:BspDp83848.c
* 文件功能概述:实现DP83848的接口
* 文 件  作 者:xxx
* 版        本:V1.0.0.0
* 修 订  记 录:2017-6-30创建
******************************************************************************/
#include "BspDp83848.h"

/*
 * 用于记录DP83848的地址信息
 */
static uint16 stDP83848Addr = 0xFFFF;

/*
 * 用于记录DP83848的连接速度 :10M或100M
 */
static uint16 stDP83848LinkSpeed = 0;

/*
 * 用于记录DP83848的工作模式:半双工或全双工
 */
static uint16 stDP83848Mode = 0;

#define DP83848_DelayMs DelayMs
/*******************************************************************************
 * 函 数 名:static void DP83848_DelayMs(uint16 Ms)
 * 参    数:uint16 Ms : 延时单位
 * 返    回:无
 * 创 建 人:xxx
 * 创建时间:2017-6-30
 * 详    述:DP83848使用的延时函数
 * 修改记录:2017-6-30创建
*******************************************************************************/
//static __inline void DP83848_DelayMs(uint16 Ms)
//{
//  DelayMs(Ms);
//} 

/*******************************************************************************
 * 函 数 名:static sint8 DP83848_AutoDiscover(void)
 * 参    数:uint16 *pPhyAddr:phy芯片地址指针
 * 返    回:0:正常返回 非0:发生错误
 * 创 建 人:xxx
 * 创建时间:2017-6-30
 * 详    述:自动发现PHY芯片的地址
 * 修改记录:2017-6-30创建
*******************************************************************************/
static sint8 DP83848_AutoDiscover(void)
{
  uint16 ChipAddr = 0;
  uint16 ChipData = 0;
  
  for(ChipAddr=0; ChipAddr<0xff; ChipAddr ++)
  {
    MiiRead(ChipAddr, PHY_PHYIDR1, &ChipData);
    if((0xFFFF!=ChipData) && (0x0000!=ChipData))
    {
      DP83848_Print("The DP83848's addr read is 0x%x\r\n", ChipAddr);
      stDP83848Addr = ChipAddr;
      break;     
    }
  }
  
  if(ChipAddr >= 0xff)
  {
    return -1;
  }
  else
  {
    return 0;
  }
}

/*******************************************************************************
 * 函 数 名:sint8 DP83848WireIsLinked(uint16 chip_addr)
 * 参    数:uint16 chip_addr   : PHY芯片地址
 * 返    回:0:未建立连接  1:已经建立连接
 * 创 建 人:xxx
 * 创建时间:2017-6-30
 * 详    述:判断phy芯片是否已经建立连接
 * 修改记录:2017-6-30创建
*******************************************************************************/

sint8 DP83848WireIsLinked(uint16 chip_addr)
{
  uint16 result = 0;
  
  MiiRead(chip_addr, PHY_STS, &result);
  
  if(result & PHYx_LINK_STATUS)
  {
    return 1;
  }
  else
  {
    return 0;
  }
    
}

/*******************************************************************************
 * 函 数 名:sint8 DP83848Init(void)
 * 参    数:无
 * 返    回:0:正常返回  非0:发生错误
 * 创 建 人:xxx
 * 创建时间:2017-6-30
 * 详    述:完成PHY芯片的初始化
 * 修改记录:2017-6-30创建
*******************************************************************************/
sint8 DP83848Init(void)
{
  sint8 ret = 0;
  
  MiiInit();
  
  if(0 == DP83848_AutoDiscover())
  {
    uint8 counter=0;
    uint16 ChipData = 0;
    uint16 ChipAddr = stDP83848Addr;
    
    /* 复位DP83848,发出复位命令后延迟100ms才去读取复位状态 */
    MiiWrite(ChipAddr, PHY_BMCR, PHY_BMCR_RESET);
    DP83848_DelayMs(100);        
    for(counter=0; counter<10; counter ++)
    {
      MiiRead(ChipAddr, PHY_PHYIDR1, &ChipData);
      if((ChipData!=0xFFFF) && (ChipData!=0x0000))
      {
        DP83848_Print("The DP83848 0x%x Reset OK\r\n", ChipAddr);
        break;
      }
      DP83848_DelayMs(10);            
    }
    
    /* 判断复位超时 */
    if(counter < 10)
    {
      /* 使能DP83848自动协商功能 */
      DP83848_Print("DP83848 0x%x start auto-negotiation!\r\n", ChipAddr);
      
      MiiWrite(ChipAddr, PHY_BMCR, (PHY_BMCR_FDX | PHY_BMCR_SPEED ));
      
      for(counter=0; counter<50; counter ++)
      {        
        DP83848_DelayMs(100);    
        MiiRead(ChipAddr, PHY_BMSR, &ChipData);
        if(ChipData & PHY_BMSR_LINK)
        {
          DP83848_Print("DP83848 0x%x auto-negotiation OK!\r\n", ChipAddr);
          break;
        }
        else
        {
          /* do nothing */
        }
      }
      
      /* 判断自动协商超时 */
      if(counter < 50)
      {
        MiiRead(ChipAddr, PHY_STS, &ChipData);
      
        if((ChipData & PHYx_LINK_STATUS) != (uint32)RESET)
        {
          DP83848_Print("DP83848 0x%x is linked!\r\n", ChipAddr);
        }
        else
        {
          DP83848_Print("DP83848 0x%x is not linked!\r\n", ChipAddr);
        }
        
        /* Configure the MAC with the Duplex Mode fixed by the auto-negotiation process */
        if((ChipData & PHYx_DUPLEX_STATUS) != (uint32)RESET)
        {
          /* Set Ethernet duplex mode to Full-duplex following the auto-negotiation */
          stDP83848Mode = 1;  
        }
        else
        {
          /* Set Ethernet duplex mode to Half-duplex following the auto-negotiation */
          stDP83848Mode = 0;           
        }
        
        /* Configure the MAC with the speed fixed by the auto-negotiation process */
        if((ChipData & PHYx_SPEED_STATUS)!= (uint32)RESET)
        {  
          /* Set Ethernet speed to 10M following the auto-negotiation */    
          stDP83848LinkSpeed = 0; 
        }
        else
        {   
          /* Set Ethernet speed to 100M following the auto-negotiation */ 
          stDP83848LinkSpeed = 1;      
        }
      }
      else
      {
        DP83848_Print("DP83848 0x%x auto-negotiation Failed!\r\n", ChipAddr);
        ret = -1;
      }
    }
    else
    {
      DP83848_Print("DP83848 0x%x  Reset Failed!\r\n", ChipAddr);
      ret = -1;
    }
  }
  else
  {
    DP83848_Print("We can't find DP83848!\r\n");
    ret = -1;
  }
  
  return ret;
}

/*******************************************************************************
 * 函 数 名:uint16 DP83848GetAddr(void)
 * 参    数:无
 * 返    回:stDP83848Addr : DP83848的地址
 * 创 建 人:xxx
 * 创建时间:2017-6-30
 * 详    述:获取DP83848的地址,在DP83848完成初始化之后方可使用
 * 修改记录:2017-6-30创建
*******************************************************************************/
uint16 DP83848GetAddr(void)
{    
  return stDP83848Addr;
}

/*******************************************************************************
 * 函 数 名:uint8 DP83848GetMode(void)
 * 参    数:无
 * 返    回:stDP83848Mode : 0:半双工  1:全双工
 * 创 建 人:xxx
 * 创建时间:2017-6-30
 * 详    述:获取DP83848的工作模式,在DP83848完成初始化之后方可使用
 * 修改记录:2017-6-30创建
*******************************************************************************/
uint8 DP83848GetMode(void)
{    
  return stDP83848Mode;
}

/*******************************************************************************
 * 函 数 名:uint8 DP83848GetLinkSpeed(void)
 * 参    数:无
 * 返    回:stDP83848LinkSpeed : 0 : 10M    1 :100M
 * 创 建 人:xxx
 * 创建时间:2017-6-30
 * 详    述:获取DP83848的连接状态,在DP83848完成初始化之后方可使用
 * 修改记录:2017-6-30创建
*******************************************************************************/
uint8 DP83848GetLinkSpeed(void)
{    
  return stDP83848LinkSpeed;
}

 

头文件

/******************************************************************************
* 文 件  名 称:BspDp83848.h
* 文件功能概述:实现DP83848的驱动接口声明
* 文 件  作 者:xxx
* 版        本:V1.0.0.0
* 修 订  记 录:2017-6-30创建
******************************************************************************/
#ifndef __BSP_Dp83848_H__
#define __BSP_Dp83848_H__

/*----------------------------------------------*
 * 包含头文件                                   *
 *----------------------------------------------*/
#include "..\BspInterface.h"
/*----------------------------------------------*
 * 宏定义                                       *
 *----------------------------------------------*/
 
//#define DP83848_Debug
#ifdef DP83848_Debug
  #include ".\inc\BllDebug.h"
	#define DP83848_Print BllDebugPrint 
#else
  #define DP83848_Print(...) 
#endif
 
/* MII寄存器地址*/
#define PHY_BMCR                    (0x00) /* Basic Control */
#define PHY_BMSR                    (0x01) /* Basic Status */
#define PHY_PHYIDR1                 (0x02) /* PHY Identifer 1 */
#define PHY_PHYIDR2                 (0x03) /* PHY Identifer 2 */
#define PHY_ANAR                    (0x04) /* Auto-Negotiation Advertisement */
#define PHY_ANLPAR                  (0x05) /* Auto-Negotiation Link Partner Ability */
#define PHY_ANER                    (0x06) /* Auto-Negotiation Expansion */
#define PHY_LPNPA                   (0x07) /* Link Partner Next Page Ability */
#define PHY_RXERC                   (0x15) /* RXER Counter */
#define PHY_ICS                     (0x1B) /* Interrupt Control/Status */
#define PHY_PHYC1                   (0x1E) /* PHY Control 1 */
#define PHY_PHYC2                   (0x1F) /* PHY Control 2 */     
     
     
/* PHY_BMCR寄存器位定义 */
#define PHY_BMCR_RESET              (0x8000)
#define PHY_BMCR_LOOP               (0x4000)
#define PHY_BMCR_SPEED              (0x2000)
#define PHY_BMCR_AN_ENABLE          (0x1000)
#define PHY_BMCR_POWERDOWN          (0x0800)
#define PHY_BMCR_ISOLATE            (0x0400)
#define PHY_BMCR_AN_RESTART         (0x0200)
#define PHY_BMCR_FDX                (0x0100)
#define PHY_BMCR_COL_TEST           (0x0080)

/* PHY_BMSR寄存器位定义*/
#define PHY_BMSR_100BT4             (0x8000)
#define PHY_BMSR_100BTX_FDX         (0x4000)
#define PHY_BMSR_100BTX             (0x2000)
#define PHY_BMSR_10BT_FDX           (0x1000)
#define PHY_BMSR_10BT               (0x0800)
#define PHY_BMSR_NO_PREAMBLE        (0x0040)
#define PHY_BMSR_AN_COMPLETE        (0x0020)
#define PHY_BMSR_REMOTE_FAULT       (0x0010)
#define PHY_BMSR_AN_ABILITY         (0x0008)
#define PHY_BMSR_LINK               (0x0004)
#define PHY_BMSR_JABBER             (0x0002)
#define PHY_BMSR_EXTENDED           (0x0001)

/* PHY_ANAR寄存器位定义 */
#define PHY_ANAR_NEXT_PAGE          (0x8001)
#define PHY_ANAR_REM_FAULT          (0x2001)
#define PHY_ANAR_PAUSE              (0x0401)
#define PHY_ANAR_100BT4             (0x0201)
#define PHY_ANAR_100BTX_FDX         (0x0101)
#define PHY_ANAR_100BTX             (0x0081)
#define PHY_ANAR_10BT_FDX           (0x0041)
#define PHY_ANAR_10BT               (0x0021)
#define PHY_ANAR_802_3              (0x0001)

/* PHY_ANLPAR寄存器位定义 */
#define PHY_ANLPAR_NEXT_PAGE        (0x8000)
#define PHY_ANLPAR_ACK              (0x4000)
#define PHY_ANLPAR_REM_FAULT        (0x2000)
#define PHY_ANLPAR_PAUSE            (0x0400)
#define PHY_ANLPAR_100BT4           (0x0200)
#define PHY_ANLPAR_100BTX_FDX       (0x0100)
#define PHY_ANLPAR_100BTX           (0x0080)
#define PHY_ANLPAR_10BTX_FDX        (0x0040)
#define PHY_ANLPAR_10BT             (0x0020)

/* PHY 扩展寄存器 */
#define PHY_STS                         ((uint16)0x10)    /*!< PHY status register Offset                      */
#define PHY_MICR                        ((uint16)0x11)    /*!< MII Interrupt Control Register                  */
#define PHY_MISR                        ((uint16)0x12)    /*!< MII Interrupt Status and Misc. Control Register */
 
/* PHY硬件特性 对应PHY_PHYC2 */
#define PHYx_DUPLEX_STATUS           ((uint16)0x0004)
#define PHYx_SPEED_STATUS            ((uint16)0x0002)
#define PHYx_LINK_STATUS             ((uint16)0x0001)

/* PHY 状态定义 */
#define Linked     1
#define NotLinked  0

/*----------------------------------------------*
 * 常量定义                                     *
 *----------------------------------------------*/

/*----------------------------------------------*
 * 外部变量说明                                 *
 *----------------------------------------------*/

/*----------------------------------------------*
 * 全局变量                                     *
 *----------------------------------------------*/

/*----------------------------------------------*
 * 模块级变量                                   *
 *----------------------------------------------*/
 
/*----------------------------------------------*
 * 外部函数原型说明                             *
 *----------------------------------------------*/

/*----------------------------------------------*
 * 内部函数原型说明                             *
 *----------------------------------------------*/
sint8 DP83848Init(void);

sint8 DP83848WireIsLinked(uint16 chip_addr);

uint16 DP83848GetAddr(void);

uint8 DP83848GetMode(void);

uint8 DP83848GetLinkSpeed(void);

#endif /* _BspDp83848_H_ */

STM32之DP83848_第1张图片

你可能感兴趣的:(ARM)