Atlas 200外设驱动开发和调试指南_RTL8367 网卡
收藏回复举报
Atlas 200外设驱动开发和调试指南_RTL8367 网卡
发表于2023-04-10 18:56:24
0 查看
Atlas 200外设驱动开发和调试指南_RTL8367 网卡

调试基于Atlas 200 参考板驱动包进行重构调试,调试方法请参考 

https://support.huawei.com/enterprise/zh/doc/EDOC1100193743/3db58fa7 

 

1.1 芯片型号 

    网卡芯片使用SWITCH芯片RTL8367。 

1.2 固件烧录 

    是否需要烧录固件:否 

1.3 内核配置 

    是否需要使能内核配置:否 

1.4 驱动调试 

    是否需要驱动支持:否 

1.5 测试工具 

    RTL8367提供了SDK用于支持芯片的初始化和使用,SDK请找厂家获取。 

    RTL8367 SDK源码包中包括以下资源: 

    1. SDK源码 

    2. 《Realtek_Unmanaged_Switch_API_Document.pdf》 

    3. 《Realtek_Unmanaged_Switch_ProgrammingGuide.pdf》 

    4. 《Realtek_Unmanaged_Switch_ReleaseNote.pdf》 

    此处为完成RTL8367芯片的初始化,主要使用SDK源码API和编程指南 

    《Realtek_Unmanaged_Switch_ProgrammingGuide.pdf》。 

    确认硬件设计的管理通道和数据通道 

    通过开发板的硬件原理图或者硬件开发人员确认,RTL8367 Switch使用的通道如下: 

    管理通道:MDIO 

    数据通道:RGMII 

    控制通道的适配 

    使用MDIO通道进行rtl8367的控制配置,访问rtl8367的寄存器,需要在smi.c中进行配 

    置,首先在编译时在M†ÀžfiÞ中必须配置DMDC_MDIO_OPERATION宏, 

    如:CFLAGS += -DMDC_MDIO_OPERATION 

    通过硬件确认RTL8367的PHY ID,PHY ID为0或者29,由硬件管脚配置决定,找硬件 

    确认,当前板子的RTL8367的PHY ID为29,在smi.c中修改宏 MDC_MDIO_PHY_ID的 

    值为29. 

    /* šžfinž the PHY ID currently used */ 

    ȅšžfinž MDC_MDIO_PHY_ID 29 /* PHY ID 0 or 29 */ 

    适配寄存器访问函数 smi_write和smi_read,访问的四个步骤已经在示例代码中给出, 

    但MDC_MDIO_WRITE和MDC_MDIO_READ的实现需要依赖于具体的硬件平台,当前 

    示例代码中为空代码,需要用户适配。 

    /* MDC/MDIO, àžšžfinžȍ²mÝÞmžnì the following Macro */ 

    ȅšžfinž MDC_MDIO_WRITE(preamableLength, phyID, regID, data) 

    ȅšžfinž MDC_MDIO_READ(preamableLength, phyID, regID, pData) 

    通过MDIO通道访问寄存器需要实现对应的MDIO驱动的读写方法,目前在已有的Atlas 

    200 SOC开放源码中已经有MDIO的驱动,结合该MDIO驱动实现MDIO的读写方法。 

    MDIO驱动中对应的ioctl方法只有两个:MDIO_IO_READ和MDIO_IO_WRITE 

    在用户态通过ioctl实现mdio的读写方法: 

    int mdio_write(struct hns_mdio_arg *p_mdio_send); 

    int mdio_read(struct hns_mdio_arg *p_mdio_read); 

    数据结构如下: 

    struct hns_mdio_arg { 

    unsigned short devaddr; 

    unsigned short regaddr; 

    unsigned short value_in; 

    unsigned short value_out; 

    }; 

    进一步实现读写方法: 

    int mdio_8367_dev_read(unsigned int mAddrs, unsigned int *rdVal); 

    int mdio_8367_dev_write(unsigned int mAddrs, const unsigned int wrData); 

    使用实现的mdio的读写方法适配API中smi.c中的smi_read和smi_write两个方法,这样 

    到此打通了控制通道,可以进行初始化配置了。 

    芯片初始化实现 

    默认配置会被写入外挂EEPROM,没有EEPROM的设备需要调用初始化接口进行初始 

    化配置。 

    SDK的API包中提供了初始化接口rtk_switch_init。 

    int rtk_rtl8367_switch_init() 

    { 

    int ret = 0; 

    int retryCnt = 0; 

    while (retryCnt < 3) { 

    retryCnt++; 

    ret = rtk_switch_init(); 

    printf("rtk_switch_init %s , ret = %d \n", ((ret == RT_ERR_OK)) ? "success" : "fail", 

    ret); 

    if (ret == RT_ERR_OK) { 

    break; 

    } 

    usleep(RTL8367_SLEEP_TIME); 

    } 

    return ret; 

    } 

    调测和配置数据通道 

    通过SDK中API进行配置,初始化EXT口 

    int rtl8367_force_ext_interface() 

    { 

    int ret; 

    rtk_mode_ext_t mode = MODE_EXT_RGMII; 

    rtk_port_mac_ability_t mac_cfg; 

    mac_cfg.forcemode = MAC_FORCE; 

    mac_cfg.speed = PORT_SPEED_1000M; 

    mac_cfg.duplex = PORT_FULL_DUPLEX; 

    mac_cfg.link = PORT_LINKUP; 

    mac_cfg.nway = DISABLED; 

    mac_cfg.txpause = ENABLED; 

    mac_cfg.rxpause = ENABLED; 

    ret = rtk_port_macForceLinkExt_set(EXT_PORT0, mode, &mac_cfg); 

    if (ret != RT_ERR_OK) { 

    printf("rtk_port_macForceLinkExt_set failed, ret = %d. \n", ret); 

    return RT_ERR_FAILED; 

    } 

    ret = rtk_port_rgmiiDelayExt_set(EXT_PORT0, 1, 4); 

    if (ret != RT_ERR_OK) { 

    printf("rtk_port_rgmiiDelayExt_set failed, ret = %d. \n", ret); 

    return RT_ERR_FAILED; 

    } 

    return RT_ERR_OK; 

    } 

    初始化PHY 

    int rtl8367_init_phy_port() 

    { 

    int ret; 

    ret = rtk_port_phyEnableAll_set(ENABLED); 

    if (ret != RT_ERR_OK) { 

    printf("rtk_port_phyEnableAll_set failed, ret = %d. \n", ret); 

    } 

    rtk_port_phy_ability_t ability; 

    (void)memset(&ability, 0x00, sizeof(rtk_port_phy_ability_t)); 

    ability.Full_1000 = 1 

    #if 0 

    ability.FC = 1; 

    ability.AsyFC = 1; 

    #endif 

    ret = rtk_port_phyAutoNegoAbility_set(UTP_PORT0, &ability); 

    if (ret != RT_ERR_OK) { 

    printf("rtk_port_phyEnableAll_set failed,port is %d, ret = %d. \n", UTP_PORT0, ret); 

    } 

    ret = rtk_port_phyAutoNegoAbility_set(UTP_PORT1, &ability); 

    if (ret != RT_ERR_OK) { 

    printf("rtk_port_phyEnableAll_set failed,port is %d, ret = %d. \n", UTP_PORT1, ret); 

    return RT_ERR_FAILED; 

    } 

    return RT_ERR_OK; 

    } 

    完成初始化工具的实现,编译得到初始化工具rtl8367_init,在系统系统启动后执行初始 

    化工具进行初始化。 

    初始化完成后可通过RTL8367网口登陆系统和传输文件。 

本帖最后由 匿名用户2023/04/15 18:16:52 编辑

我要发帖子