关键词

TC397 官方例程;TC397 以太网例程;TC397 GETH;


 简介

本篇为 Aurix TriCore TC397 以太网官方例程分析,重点关注其硬件行为

调试所用的开发板型号:KIT-A2G-TC397-5V-TFT

所使用的例程:Ethernet_1_KIT_TC397_TFT

英飞凌 TriCore 官方例程下载地址

https://github.com/Infineon/AURIX_code_examples


目录

1.MDIO 读写方式

2.初始化流程

2.1.复位 RTL8211F

2.2.PHY 设置

2.3.LED 设置

2.4.使能/重启自动协商


// 函数调用栈
core0_main()
    |--> Ifx_Lwip_init()
        |--> netif_add()
            |--> ifx_netif_init()
                |--> low_level_init() // 硬件初始化
                    |--> IfxGeth_Eth_Phy_Rtl8211f_init()

IfxGeth_Eth_Phy_Rtl8211f_init() 完成 PHY(RTL8211F)的初始化:

// Libraries/Ethernet/lwip/port/src/netif.c
static void low_level_init(netif_t *netif)
{
    ...
        IfxGeth_Eth_Phy_Rtl8211f_init();

MDIO 用于配置 PHY 芯片状态、读取寄存器、PHY 地址、LINK 状态等操作,英飞凌定义了 MDIO 接口的读写函数:

  • IfxGeth_Eth_Phy_Rtl8211f_read_mdio_reg():通过 MDIO 读取对应的寄存器;

  • IfxGeth_Eth_Phy_Rtl8211f_write_mdio_reg():通过 MDIO 向对应的寄存器写值;

1.MDIO 读写方式

IfxGeth_Eth_Phy_Rtl8211f_read_mdio_reg() 读取 RTL8211F 的 MDIO 寄存器:

// Libraries/Ethernet/Phy_Rtl8211f/IfxGeth_Phy_Rtl8211f.c
void IfxGeth_Eth_Phy_Rtl8211f_read_mdio_reg(uint32 layeraddr,
                                            uint32 regaddr,
                                            uint32 *pdata)
{
    // 5bit Physical Layer Adddress, 5bit GMII Regnr, 
    // 4bit csrclock divider, Read, Busy
    GETH_MAC_MDIO_ADDRESS.U = (layeraddr << 21) |
                              (regaddr << 16) |
                              (0 << 8) |
                              (3 << 2) |
                              (1 << 0);

    // 等待 MDIO 读写完成,等待 GB == 0
    IFXGETH_PHY_RTL8211F_WAIT_MDIO_READY();
        |--> while (GETH_MAC_MDIO_ADDRESS.B.GB) {}

    // get data,读取数据
    *pdata = GETH_MAC_MDIO_DATA.U;
}

其中,layeraddr 为寄存器页地址,regaddr 为寄存器在该寄存器页中的地址

IfxGeth_Eth_Phy_Rtl8211f_write_mdio_reg() 将数据写入 RTL8211F 的 MDIO 寄存器:

// Libraries/Ethernet/Phy_Rtl8211f/IfxGeth_Phy_Rtl8211f.c
void IfxGeth_Eth_Phy_Rtl8211f_write_mdio_reg(uint32 layeraddr,
                                             uint32 regaddr,
                                             uint32 data)
{
    // put data,写入数据
    GETH_MAC_MDIO_DATA.U = data;

    // 5bit Physical Layer Adddress, 5bit GMII Regnr,
    // 4bit csrclock divider, Write, Busy
    GETH_MAC_MDIO_ADDRESS.U = (layeraddr << 21) |
                              (regaddr << 16) |
                              (0 << 8) |
                              (1 << 2) |
                              (1 << 0);

    // 等待 MDIO 读写完成,等待 GB == 0
    IFXGETH_PHY_RTL8211F_WAIT_MDIO_READY();
        |--> while (GETH_MAC_MDIO_ADDRESS.B.GB) {}
}

其中,layeraddr 为寄存器页地址,regaddr 为寄存器在该寄存器页中的地址,相关寄存器位及其值的含义如下:

  • MAC_MDIO_ADDRESS.PA:Physical Layer Address,[25:21],指示当前访问的 PHY 寄存器页地址;

  • MAC_MDIO_ADDRESS.RDA:Register/Device Address,[20:16],指示当前访问的 PHY 寄存器在该寄存器页中的地址;

  • MAC_MDIO_ADDRESS.CR:CSR Clock Range,[11:8],MDC 的时钟频率;

  • MAC_MDIO_ADDRESS.GOC_0:GMII Operation Command 0,[2],操作码的低位;

  • MAC_MDIO_ADDRESS.GOC_1:GMII Operation Command 1,[3],操作码的高位;

    • GOC_0 和 GOC_1 共同组成操作码,其含义如下:

    • 00:未使用;

    • 01:表示当前执行写入操作;

    • 10:当前操作的是 Clause 45 使用的预读取增量地址;

    • 11:表示当前执行读取操作;

  • MAC_MDIO_ADDRESS.GB:GMII Busy,[0],占用当前 MDIO,当读写操作完成后自动将其置 "0";

  • MAC_MDIO_DATA.GD:GMII Data,[15:0],PHY 寄存器的内容(RTL8211F 的寄存器为 16-bit);

2.初始化流程

IfxGeth_Eth_Phy_Rtl8211f_init() 通过向 RTL8211F 的 MDIO 写入控制信息,控制 PHY 完成初始化

2.1.复位 RTL8211F

发送 RTL8211F 复位请求的流程如下:

  1. 读取 MAC_MDIO_ADDRESS.GB,其值为 "1" 表示 MDIO 被占用(正在读写),等待占用解除(读写完成),数据传输完成后,硬件会自动将该位置 "0",表示解除占用;

  2. 通过 MDIO 操作 RTL8211F 的 BMCR(Basic Mode Control Register) 寄存器,地址为 0x0000,写入值为 0x8000,即 MAC_MDIO_DATA.GD = 0x8000(BMCR 寄存器第 15 位置 "1"),BMCR 的 bit-15 为复位请求,写 "1" 将触发 RTL8211F 的复位操作;

  3. RTL8211F 复位完成后,自动将 BMCR 的 bit-15 设置为 "0",读取 BMCR 寄存器,等待 RTL8211F 复位完成;

// Libraries/Ethernet/Phy_Rtl8211f/IfxGeth_Phy_Rtl8211f.c
uint32 IfxGeth_Eth_Phy_Rtl8211f_init(void)
{
    // 等待 MDIO 解除占用
    IFXGETH_PHY_RTL8211F_WAIT_MDIO_READY();
        |--> while (GETH_MAC_MDIO_ADDRESS.B.GB) {}

    // reset PHY
    IfxGeth_Eth_Phy_Rtl8211f_write_mdio_reg(0, IFXGETH_PHY_RTL8211F_MDIO_BMCR, 0x8000);

    uint32 value;
    do
    { // 等待 PHY 复位完成
      IfxGeth_Eth_Phy_Rtl8211f_read_mdio_reg(0, IFXGETH_PHY_RTL8211F_MDIO_BMCR, &value);
    } while (value & 0x8000); // wait for reset to finish

2.2.PHY 设置

IFXGETH_PHY_RTL8211F_MDIO_PAGSR 为 RTL8211F 的 PAGSR 寄存器地址(0x1F),该寄存器用于切换寄存器页,写入值为 0xD08,即切换至 MIICR (MII Control Register) 寄存器所在页,然后在该页内,读取地址为 0x11 的寄存器,使能发送延迟,然后将值写回 0x11 地址的寄存器:

// Libraries/Ethernet/Phy_Rtl8211f/IfxGeth_Phy_Rtl8211f.c
uint32 IfxGeth_Eth_Phy_Rtl8211f_init(void)
{
    ...
// ---------------------------------------------------------
    // setup PHY
    IfxGeth_Eth_Phy_Rtl8211f_write_mdio_reg(0, IFXGETH_PHY_RTL8211F_MDIO_PAGSR, 0xd08);
    IfxGeth_Eth_Phy_Rtl8211f_read_mdio_reg(0, 0x11, &value);
// ---------------------------------------------------------

// ---------------------------------------------------------
    value |= 0x100; // enable TX-delay
    IfxGeth_Eth_Phy_Rtl8211f_write_mdio_reg(0, 0x11, value);
    IfxGeth_Eth_Phy_Rtl8211f_write_mdio_reg(0, IFXGETH_PHY_RTL8211F_MDIO_PAGSR, 0x0);
// ---------------------------------------------------------

注意:目前尚不明确 0xD08 寄存器页中,地址为 0x11 的寄存器的具体含义

2.3.LED 设置

设置网口的 LED 指示灯:

// Libraries/Ethernet/Phy_Rtl8211f/IfxGeth_Phy_Rtl8211f.c
uint32 IfxGeth_Eth_Phy_Rtl8211f_init(void)
{
    ...
// ---------------------------------------------------------
    /* Set LEDs */
    IfxGeth_Eth_Phy_Rtl8211f_write_mdio_reg(0, IFXGETH_PHY_RTL8211F_MDIO_PAGSR, 0xd04);
    IfxGeth_Eth_Phy_Rtl8211f_write_mdio_reg(0, IFXGETH_PHY_RTL8211F_MDIO_LCR, 0x8170);
// ---------------------------------------------------------

// ---------------------------------------------------------
    // EEE off for all leds
    IfxGeth_Eth_Phy_Rtl8211f_write_mdio_reg(0, IFXGETH_PHY_RTL8211F_MDIO_EEELCR, 0x0);
    IfxGeth_Eth_Phy_Rtl8211f_write_mdio_reg(0, IFXGETH_PHY_RTL8211F_MDIO_PAGSR, 0x0);
// ---------------------------------------------------------

向 RTL8211F 的 PAGSR 寄存器写入 0xD04,将寄存器页切换至 0xD04,RTL8211F 的 LCR 与 EEELCR 两个寄存器均位于该寄存器页中,LCR 寄存器写入 0x8170,EEELCR 寄存器写入 0x0

LCR 寄存器位的定义如下:

EEELCR 寄存器位的定义如下:

2.4.使能/重启自动协商

向 RTL8211F 的 BMCR 寄存器写入 0x1200,涉及以下位:

  • ANE:Auto-Negotiation Enable,置 "1" 使能自动协商;

  • Restart_AN:Restart Auto-Negotiation,置 "1" 重启自动协商;

// Libraries/Ethernet/Phy_Rtl8211f/IfxGeth_Phy_Rtl8211f.c
uint32 IfxGeth_Eth_Phy_Rtl8211f_init(void)
{
    ...
    // enable auto-negotiation, restart auto-negotiation
    IfxGeth_Eth_Phy_Rtl8211f_write_mdio_reg(0, IFXGETH_PHY_RTL8211F_MDIO_BMCR, 0x1200);

最后,标记 RTL8211F 初始化完成(IfxGeth_Eth_Phy_Rtl8211f_iPhyInitDone = 1)

// Libraries/Ethernet/Phy_Rtl8211f/IfxGeth_Phy_Rtl8211f.c
uint32 IfxGeth_Eth_Phy_Rtl8211f_init(void)
{
    ...
    // done
    IfxGeth_Eth_Phy_Rtl8211f_iPhyInitDone = 1;

    return 1;
}

下一篇:TC397以太网例程 - 14.Tx/Rx 使能

Logo

智能硬件社区聚焦AI智能硬件技术生态,汇聚嵌入式AI、物联网硬件开发者,打造交流分享平台,同步全国赛事资讯、开展 OPC 核心人才招募,助力技术落地与开发者成长。

更多推荐