在RT-Thread下为MPU手搓以太网MAC驱动-2

2024-05-25 16:44

本文主要是介绍在RT-Thread下为MPU手搓以太网MAC驱动-2,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

文章目录

    • MAC驱动兼容不同的MPU平台
      • MAC驱动中断处理代码
      • MAC驱动下MDIO访问接口的实现
    • MAC驱动支持不同的PHY芯片
      • 对PHY设备的抽象

这是个人驱动开发过程中做的一些记录,仅代表个人意见和理解,不喜勿喷

  • MAC驱动需要兼容不同的MPU平台

MAC驱动兼容不同的MPU平台

MAC驱动中断处理代码

在MAC驱动下,提供了通用的中断处理代码,在通用中断处理代码下会调用每个MAC驱动实际注册的中断处理函数:

static void h3_macplib_interrupt(int vector, void *param)
{struct h3_macplib_dev *macplib_dev;RT_ASSERT(param != RT_NULL);macplib_dev = (struct h3_macplib_dev *)param;RT_ASSERT((int)macplib_dev->irqnum == vector);macplib_dev->mac_ops->macdev_interrupt(&macplib_dev->mac_dev);
}

MAC驱动在向RT-Thread注册network device时,所提供的初始化接口的实现:

static rt_err_t h3_macplib_initial(rt_device_t dev)
{struct mac_async_filter filter = {0};struct h3_macplib_dev *macplib_dev;macplib_dev = (struct h3_macplib_dev *)dev->user_data;RT_ASSERT(macplib_dev != RT_NULL);/* Disable GMAC interrupt and register IRQ handler */rt_hw_interrupt_mask(macplib_dev->irqnum);rt_hw_interrupt_install(macplib_dev->irqnum, h3_macplib_interrupt,(void *)macplib_dev, macplib_dev->name);/* Device is ready to work after final initialization */macplib_dev->mac_ops->macdev_init(&macplib_dev->mac_dev,(void *)macplib_dev->regs);/* Register frame RX callback function to notify Ethernet driver */macplib_dev->mac_ops->macdev_register(&macplib_dev->mac_dev,MAC_ASYNC_RECEIVE_CB,h3_macplib_rxcallback);/* set MAC hardware address */memcpy(filter.mac, macplib_dev->mac_addr, 6);filter.tid_enable = false;macplib_dev->mac_ops->macdev_filter(&macplib_dev->mac_dev, 0, &filter);/* Enable GMAC device */macplib_dev->mac_ops->macdev_enable(&macplib_dev->mac_dev);/* The last should enable GMAC interrupt handler */rt_hw_interrupt_umask(macplib_dev->irqnum);return RT_EOK;
}

MAC驱动下MDIO访问接口的实现

在定义MAC驱动操作接口的抽象时,就有定义PHY的寄存器读写接口,而MDIO操作PHY寄存器时就需要用到MAC操作接口所提供的PHY读写接口:

/* RT-Thread MDIO bus operation */
static struct rt_mdio_bus_ops h3_mdiobus_ops =
{.init   = h3_mdioplib_init,.read   = h3_mdioplib_read,.write  = h3_mdioplib_write,.uninit = RT_NULL,
};

MDIO操作接口读取接口的代码实现:

static rt_size_t h3_mdioplib_read(void *bus, rt_uint32_t addr,rt_uint32_t reg, void *data, rt_uint32_t size)
{rt_uint16_t val;rt_uint32_t *data_ptr = (rt_uint32_t *)data;struct h3_macplib_dev *macplib_dev;struct rt_mdio_bus    *mdioplib_bus = (struct rt_mdio_bus *)bus;RT_ASSERT(data != NULL);RT_ASSERT(bus  != NULL);if (4 != size) {return 0;}macplib_dev = (struct h3_macplib_dev *)mdioplib_bus->hw_obj;macplib_dev->mac_ops->macdev_readphy(&macplib_dev->mac_dev,(rt_uint16_t)addr, (rt_uint16_t)reg,&val);/* Get data from MII register. */*data_ptr = (rt_uint32_t)val;return 4;
}

那到这里的话,整个MAC驱动中最重要的部分已经完成,接下来将介绍PHY驱动代码的实现。

  • MAC驱动需要支持不同的PHY芯片

MAC驱动支持不同的PHY芯片

对PHY设备的抽象

需要对PHY设备做出抽象,不同的MPU产品中会存在MAC接口外接不同的PHY芯片,那在我们系统中每个PHY芯片就会有对应数量的PHY设备实例:

struct h3_kszplib_dev
{const char    *name;uint32_t       phy_addr;struct rt_phy_device rt_phydev;
} ;

RT-Thread下对PHY设备的操作接口做出抽象,在编写MAC驱动的时候,也需要完成对PHY设备操作接口的实现:

struct rt_phy_ops
{rt_phy_status (*init)(void *object, rt_uint32_t phy_addr, rt_uint32_t src_clock_hz);rt_phy_status (*read)(rt_uint32_t reg, rt_uint32_t *data);rt_phy_status (*write)(rt_uint32_t reg, rt_uint32_t data);rt_phy_status (*loopback)(rt_uint32_t mode, rt_uint32_t speed, rt_bool_t enable);rt_phy_status (*get_link_status)(rt_bool_t *status);rt_phy_status (*get_link_speed_duplex)(rt_uint32_t *speed, rt_uint32_t *duplex);
};

RT-Thread下定义的PHY操作抽象接口并不是很合理,比如你的系统里面有2个PHY的时候,你需要对每个PHY的操作接口做独立的实现,否则你无法根据当前read操作所传入的参数来区分当前操作的是哪个PHY设备。

如果你对上述说法不是很理解,参考下前面的h3_macplib_initial()函数,可以通过函数传入的参数dev,去获取到当前ethernet device对应的具体以太网设备实例包含的私有信息,根据这个信息用户驱动可以访问到自己定义的数据结构、操作接口等。

这篇关于在RT-Thread下为MPU手搓以太网MAC驱动-2的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/1002058

相关文章

mac中资源库在哪? macOS资源库文件夹详解

《mac中资源库在哪?macOS资源库文件夹详解》经常使用Mac电脑的用户会发现,找不到Mac电脑的资源库,我们怎么打开资源库并使用呢?下面我们就来看看macOS资源库文件夹详解... 在 MACOS 系统中,「资源库」文件夹是用来存放操作系统和 App 设置的核心位置。虽然平时我们很少直接跟它打交道,但了

macOS怎么轻松更换App图标? Mac电脑图标更换指南

《macOS怎么轻松更换App图标?Mac电脑图标更换指南》想要给你的Mac电脑按照自己的喜好来更换App图标?其实非常简单,只需要两步就能搞定,下面我来详细讲解一下... 虽然 MACOS 的个性化定制选项已经「缩水」,不如早期版本那么丰富,www.chinasem.cn但我们仍然可以按照自己的喜好来更换

mac安装redis全过程

《mac安装redis全过程》文章内容主要介绍了如何从官网下载指定版本的Redis,以及如何在自定义目录下安装和启动Redis,还提到了如何修改Redis的密码和配置文件,以及使用RedisInsig... 目录MAC安装Redis安装启动redis 配置redis 常用命令总结mac安装redis官网下

Linux_kernel驱动开发11

一、改回nfs方式挂载根文件系统         在产品将要上线之前,需要制作不同类型格式的根文件系统         在产品研发阶段,我们还是需要使用nfs的方式挂载根文件系统         优点:可以直接在上位机中修改文件系统内容,延长EMMC的寿命         【1】重启上位机nfs服务         sudo service nfs-kernel-server resta

Thread如何划分为Warp?

1 .Thread如何划分为Warp? https://jielahou.com/code/cuda/thread-to-warp.html  Thread Index和Thread ID之间有什么关系呢?(线程架构参考这里:CUDA C++ Programming Guide (nvidia.com)open in new window) 1维的Thread Index,其Thread

mac安装brew 与 HomeBrew

/bin/zsh -c "$(curl -fsSL https://gitee.com/cunkai/HomebrewCN/raw/master/Homebrew.sh)" curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install.sh >> brew_install BREW_REPO="

mac jdk 1.7 dmg 官方版

百度云下载 https://pan.baidu.com/s/1SQiidrPFF5aZr4xlx0ekoQ https://pan.baidu.com/s/1SQiidrPFF5aZr4xlx0ekoQ   补充说明: 实际上oracle对于历史版本的jdk都有归档可以在官方网站上下载,只是需要注册个号就可以了。 地址如下: https://www.oracle.com/cn/java

编程应该用 Mac 还是 PC ?

『有人的地方,就有江湖』—徐克。笑傲江湖。     序     一个竞争的市场,就会有对立的产生,这世界存在著很多不同的领域,领域好比是个江湖的缩影,因此就有许多门派的纷争,例如说浏览器领域有著最大宗的IE派,门派成长速度飞快,武功版号跳的跟台湾物价指数一样快的Chrome门,不断被模仿,一直被超越的Opera派;韧性极强,一直对抗几大势力的Firefox派等等,程序语言也有自己的领域

驱动(RK3588S)第七课时:单节点设备树

目录 需求一、设备树的概念1、设备树的后缀名:2、设备树的语法格式3、设备树的属性(重要)4、设备树格式举例 二、设备树所用函数1、如何在内核层种获取设备树节点:2、从设备树上获取 gpio 口的属性3、获取节点上的属性只针对于字符串属性的4、函数读取 np 结点中的 propname 属性的值,并将读取到的 u32 类型的值保存在 out_value 指向的内存中,函数的返回值表示读取到的

驱动安装注册表指令

HKCR: HKEY_CLASSES_ROOT HKCU: HKEY_CURRENT_USER HKLM: HKEY_LOCAL_MACHINE HKU: HEKY_USER HER: 相对根键