外挂phy移植说明


REVISION HISTORY

Revision No.
Description
Date
1.0
  • Initial release
  • 04/24/2025
    1.1
  • Remove unnecessary steps from 7.1
  • 07/25/2025

    1. 概述

    在客户支持过程中难免遇到需要适配新的片外phy的问题, 因此以本文来说明适配片外phy的注意点。

    在阅读本文前,可以先查看 Ethernet使用参考,了解下相关规格

    2. 关键字说明

    • EMAC

      Ethernet Media Access Controller(以太网媒体访问控制器)简称为EMAC

    • Ephy

      Ethernet Physical Layer(以太网物理接口收发器)简称为Ephy

    • MII

      MII(Media Independent Interface)即媒体独立接口,MII接口是MAC与PHY连接的标准接口,MII接口提供了MAC与PHY之间的互联支持

    • RMII

      RMII(Reduced Media Independant Interface)即简化媒体独立接口,是标准的以太网接口之一,比MII有更少的I/O传输引脚

    • RX

      接收器(Receiver)或接收(Reception)。

    • TX

      发射器(Transmitter)或传输(Transmission)。

    • MDIO

      MDIO(Management Data Input/Output), 管理数据的输入输出双向接口。

    • MDC

      MDC(Management Data Clock), 是管理数据的时钟信号。

    3. 硬件电路

    • 确认引脚物理连接正常。可以通过示波器量信号,该步可以找HW CAE咨询。

    • padmux确认配对。可以咨询GPIO owner或HW CAE确认padmux的正确性。

    • phy的外部晶振频率一般是25M,但具体需要根据phy手册确认。芯片这边不提供CLK。

    4. 适配前需要获取必要的PHY原厂支持

    4.1. phy驱动

    拿到一个新的phy芯片, 需要找原厂提供 配套的phy 芯片手册

    有些phy芯片还需要 配套的phy驱动 。若不需要配套的phy驱动, 则使用默认的通用phy驱动即可。

    如果当前已有相关的phy驱动,也需要咨询原厂 是否需要更新对应的驱动

    若需要更新,这部分信息也需要找phy原厂支持,主要是提供: 对应的代码、更新方法、启用驱动的方法以及特殊设定配置等等。

    驱动更新后kernel跑起来后,通过命令: ls /sys/bus/mdio_bus/drivers 来确认是否有将驱动更新成功。

        ls /sys/bus/mdio_bus/drivers
    

    图 4-1 show mdio bus

    如图4-1所示,可以看到匹配的是默认的驱动:Generic PHY。

    4.2. reset时序

    询问原厂, 或者翻看phy芯片手册, 找到phy reset的时序要求。

    • reset 生效时间: 即需要拉低多久。当前 pcupid 默认拉低20ms。

    • reset 恢复时间: 即需要保持拉高多久。phy芯片reset之后需要多长时间后phy芯片内部才完成内部电路初始化。当前 pcupid 默认拉高50ms。

    以RTL8211为例:

    图 4-2 RTL8211_reset_time

    如图4-2中红线所划, RTL8211要求:reset生效时间至少为 10ms, reset恢复时间至少为 72ms。

    5. Uboot下适配介绍

    5.1. Uboot下的padmux配置

    • 需要将 padmux.dtsi 与 硬件电路对应起来。

    图 5-1 eth hardware

    图 5-2 eth0 pin mapping

    图 5-3 eth1 pin mapping

    以 SSM001A-S01A-S 为例,找到 eth0 和 eth1 对应的pin脚,并将其映射关系写入 pcupid-ssm001a-s01a-padmux.dtsi 文件中。

    • eth0 & eth1 padmux
      //eth0 rmii
      <PAD_GPIOE_08            PINMUX_FOR_GPIO_MODE             MDRV_PUSE_ETH0_PHY_RESET>,
      <PAD_GPIOE_20            PINMUX_FOR_ETH_MODE_3            MDRV_PUSE_ETH0_COL>,
      <PAD_GPIOE_21            PINMUX_FOR_ETH_MODE_3            MDRV_PUSE_ETH0_RXD0>,
      <PAD_GPIOE_22            PINMUX_FOR_ETH_MODE_3            MDRV_PUSE_ETH0_RXD1>,
      <PAD_GPIOE_23            PINMUX_FOR_ETH_MODE_3            MDRV_PUSE_ETH0_TX_CLK>,
      <PAD_GPIOE_24            PINMUX_FOR_ETH_MODE_3            MDRV_PUSE_ETH0_TXD0>,
      <PAD_GPIOE_25            PINMUX_FOR_ETH_MODE_3            MDRV_PUSE_ETH0_TXD1>,
      <PAD_GPIOE_26            PINMUX_FOR_ETH_MODE_3            MDRV_PUSE_ETH0_TX_CTL>,
      <PAD_GPIOE_27            PINMUX_FOR_ETH_MODE_3            MDRV_PUSE_ETH0_MDIO>,
      <PAD_GPIOE_28            PINMUX_FOR_ETH_MODE_3            MDRV_PUSE_ETH0_MDC>,
      //eth1 rmii
      <PAD_SAR_ADC0_03         PINMUX_FOR_GPIO_MODE             MDRV_PUSE_ETH1_PHY_RESET>,
      <PAD_GPIOB_00            PINMUX_FOR_ETH1_MODE_2           MDRV_PUSE_ETH1_COL>,
      <PAD_GPIOB_01            PINMUX_FOR_ETH1_MODE_2           MDRV_PUSE_ETH1_RXD0>,
      <PAD_GPIOB_02            PINMUX_FOR_ETH1_MODE_2           MDRV_PUSE_ETH1_RXD1>,
      <PAD_GPIOB_03            PINMUX_FOR_ETH1_MODE_2           MDRV_PUSE_ETH1_TX_CLK>,
      <PAD_GPIOB_04            PINMUX_FOR_ETH1_MODE_2           MDRV_PUSE_ETH1_TXD0>,
      <PAD_GPIOB_05            PINMUX_FOR_ETH1_MODE_2           MDRV_PUSE_ETH1_TXD1>,
      <PAD_GPIOB_06            PINMUX_FOR_ETH1_MODE_2           MDRV_PUSE_ETH1_TX_CTL>,
      <PAD_GPIOB_07            PINMUX_FOR_ETH1_MODE_2           MDRV_PUSE_ETH1_MDIO>,
      <PAD_GPIOB_08            PINMUX_FOR_ETH1_MODE_2           MDRV_PUSE_ETH1_MDC>,
      

    5.2. Uboot下的phy reset时间配置

    根据 4.2获取的reset时序信息 , 在初始化时对phy进行配置。

    Uboot下可以通过KConfig配置 reset生效时间(拉低) 和 reset恢复时间(拉高)。

    • EMAC0 RMII + phy reset

      [*] SigmaStar drivers  --->
          SigmaStar EMAC --->
              [*] SigmaStar EMAC
              [*]   EMAC supply to RMII
              [ ]     EMAC supply to IC+ Phy
              [ ]   EMAC fix link to mii/rmii
              [*]   EMAC phy reset reverse
              [*]   EMAC 0
              [*]     EMAC0 PHY RESET
              (17)      EMAC 0 FOR PHY RESET PAD
              (20)      EMAC 0 FOR PHY RESET HOLD MS
              (50)      EMAC 0 FOR PHY WAIT READY MS
              [ ]   EMAC 1
      
    • 片外phy需要 开启宏SSTAR_ETHERNET_RMII ,切换为 rmii mode。

    • 设置EMAC0 reset生效时间 和 reset恢复时间。默认配置下,reset生效时间 20ms , reset恢复时间 50ms。

    • 当padmux.dtsi文件未配置reset引脚时,会使用Kconfig配置的引脚进行reset。上面配置的即为 pad 17。

    • 根据板子设计,有时候会添加反向电路,此时需要配置 EMAC phy reset reverse 。使能后reset流程会变成软件 先拉高20ms, 再拉低50ms

    更详细的KCONFIG配置内容可以参考 Ethernet使用参考 文档中的 2.1. Uboot CONFIG 配置说明

    5.3. 检查mdio通信是否正常

    如果phy连接正常,mdio可以正常读取phy信息。 Uboot下使用命令 estart 初始化时会打印phy寄存器信息,且信息不为全0或全F。

    或使用 phy_r 和 phy_w 命令可以正常读取phy寄存器信息,且信息不为全0或全F。

    • Uboot使用estart命令正常初始化

      # estart
      phy [0]=ffff
      phy [1]=786d
      MAC Address 00:00:83:05:00:01
      Auto-Negotiation...
      Link Status Speed:100 Full-duplex:1
      (Re)start EMAC...
      
    • Uboot下使用phy_r读取phy reg

      # phy_r 0
      phy read address[0] value is 3100
      # phy_r 1
      phy read address[1] value is 786d
      
    • Uboot下使用phy_w 写 phy reg

      # phy_w 0 0x1000
      phy write address[0] value is 1000
      

    5.4. 检查网络通信是否正常

    该步骤是验证数据引脚的正确性,可以使用 ping(正常ping通) 或者 tftp(文件传输或升级正常) 验证。

    相关内容可以参考 Ethernet使用参考 文档中的 5.2. Uboot cmd参数说明

    6. Kernel下适配介绍

    6.1. Kernel下的phy reset时间配置

    kernel下的 reset生效时间 和 reset恢复时间 也是通过Kconfig配置。

    EMAC0_PHY_RESET_HOLD_MS 和 EMAC1_PHY_RESET_HOLD_MS是reset生效时间,默认值为 20ms。

    EMAC0_PHY_RESET_WAIT_READY_MS 和 EMAC1_PHY_RESET_WAIT_READY_MS 是reset恢复时间,默认值为 50ms。

    • 配置 kernel下的 reset生效时间 和 reset恢复时间
      Device Drivers --->
          SStar Soc platform drivers --->
              (20)  Set emac0 phy reset padmux low in millisecond
              (50)  Set emac0 phy reset padmux high wait ready in millisecond
              (20)  Set emac1 phy reset padmux low in millisecond
              (50)  Set emac1 phy reset padmux high wait ready in millisecond
      

    6.2. Kernel下的dts配置

    参考Ethernet使用参考 文档中的 6.2. Kernel DTS配置 ,配置dts文件。

    需要注意,如果外接反向电路,需要配置 reset_reverse 属性。

    6.3. Kernel下的padmux配置

    参考 5.1. Uboot下的padmux配置Ethernet使用参考 文档中的 6.3. Kernel Padmux配置 ,配置padmux文件。

    6.4. 检查mdio通信是否正常

    kernel下会通过 emac_phy_connect 函数连接phy芯片。可以通过检查启机log,查看是否正常连接到 phy。

    以 SSM001A-S01A-S 为例,启机会进行phy connect,获取phy的uid并匹配phy驱动。一般phy的uid不为全0或全F,即可正常读取phy reg信息。

    • dmesg查看phy connect状态
      / # dmesg | grep emac_phy_connect
      [emac_phy_connect][2999] connected mac emac0 to PHY at mdio-bus@emac0:01 [uid=02430c54, driver=Generic PHY]
      

    另外的,也可以通过phytool或debug节点读取phy reg,只要读取的phy reg不为全0或全F,即为正常。

    phytool的使用,可以参考Ethernet使用参考 文档中的 6.5.4. phytool

    debug节点命令,可以参考Ethernet使用参考 文档中的 6.6.2. phyStatusWR phy读写 debug节点

    6.5. 检查网络通信是否正常

    kernel下可使用iperf工具,进行网络通信稳定性的检验。可以参考Ethernet使用参考 文档中的 6.5.1. iperf3

    7. 常见的phy适配问题

    7.1. mdio读取异常, phy id读取信息是全F或全0

    适配过程中经常会有读不到phy reg的问题, mdc mdio都出去的信号全为FFFF或全0。

    建议HW CAE介入协助排查量测波形,检查电路连接。

    常见的错误有以下几点原因:

    错误原因 排查方法 解决方法
    物理连接异常 HW CAE协助量测波形,或检查电路连接 参考HW CAE意见
    GPIO配置异常 HW CAE检查padmux映射 修改padmux
    GPIO无法拉低拉高 按照gpio问题排查,可以请GPIO owner协助 按照GPIO问题解决
    phy reset异常 使用示波器量测启机时候reset引脚的波形是否符合预期 参考phy手册进行设置,debug阶段可以将 reset生效时间和恢复时间设置到1s或更大,确保reset正常

    7.2. 收发包速率未达预期,或存在丢包等问题

    如果速率不达预期,一般是信号质量问题或相位问题,需要由HW CAE主导排查。这里给出几点常见排查项:

    • 确认 phy/switch 提供的CLK是否是 50MHz。MAC端不提供RX_CLK。

    • 确认信号幅值或相位,如果波形异常,需要尝试参考phy手册,通过调整phy端寄存器来调整phy端的driving能力。

    • 检查 phy的外部晶振,一般是25M,但具体根据phy手册确认。如果phy没有任何响应,需要客户排查外部晶振频率是否正常供给。

    7.3. phy驱动注册异常

    • kernel下通过命令: ls /sys/bus/mdio_bus/drivers 来确认驱动是否更新成功。该命令会显示当前设备支持的驱动。

    • 确认mdio连接是否正常,参考 7.1. mdio读取异常, phy id读取信息是全F或全0 进行排查。

    • mdio连接正常的情况下,参考 6.4. 检查mdio通信是否正常 排查获取的 phy uid是否正常。

    • phy uid若不为全0或全F,检查驱动是否匹配phy uid。若uid值与 .phy_id 不一致,则无法匹配驱动程序。

    • icpplus driver

      static struct phy_driver icplus_driver[] = {
      {
          .phy_id         = 0x02430c54,
          .name           = "ICPlus IP101A/G",
          .phy_id_mask    = 0x0ffffff0,
          /* PHY_BASIC_FEATURES */
          .probe          = ip101a_g_probe,
          .config_intr    = ip101a_g_config_intr,
          .did_interrupt  = ip101a_g_did_interrupt,
          .ack_interrupt  = ip101a_g_ack_interrupt,
          .config_init    = &ip101a_g_config_init,
          .suspend        = genphy_suspend,
          .resume         = genphy_resume,
      } };