Zynq7000网络驱动调试笔记

来源:本站
导读:目前正在解读《Zynq7000网络驱动调试笔记》的相关信息,《Zynq7000网络驱动调试笔记》是由用户自行发布的知识型内容!下面请观看由(电工技术网 - www.9ddd.net)用户发布《Zynq7000网络驱动调试笔记》的详细说明。
简介:本文是一篇关于Zynq7000网络驱动调试笔记。

Zynq7000的网络控制器与Atmel公司的SAMA5D3x处理器的千兆网控制器是相同的均是Cadence公司的的IP,很奇怪两个公司各自设计了一套驱动程序。不过看着Zynq7000中Linux的设备树文件,Zynq7000并没有使用自己的驱动程序,而是使用Atmel编写的驱动程序macb.c。

在裸机代码上,Atmel提供的裸机代码可阅读性比Xilinx的好很多(这里不得不吐槽下Xilinx的裸机程序代码,一个驱动程序竟然拆分在多个文件中,十分不方便阅读)。

通过参考Atmel的裸机代码很方便的将网络驱动移植到了SylixOS下,需要注意Zynq7000的中断需要手动清除,而Atmel的中断读取状态时就会自动清除。当然这个方便的前提是对SylixOS的驱动已经有了一定的了解,对SylixOS下的驱动建议参考imx283的驱动作为模板进行设计。不过由于是千兆网,这里没有使用SylixOS自带的MII库,而是根据Atmel裸机代码库自行编写了网络链接检测线程,具体方法可以参考AM335x的驱动文件。

但在网络完成基本的通信后,出现了两个较大的问题:

l 对GEM的DMA发送描述符,总会莫名其妙的出现问题;

l 不能实现1000和100状态切换,固化后发现如果uboot不初始化连通信都实现不了。

经过长时间调试,偶然间发现通过在网络发送函数里面加入100us延时,即触发网络发送数据后,延时100us。发送函数就工作正常了,这是一个巨大的进步,原来一直以为是DMA描述符的使用上有问题,这个现象说明在DMA描述符使用上是没有问题的。这个问题最终是由一个同事帮助解决,他查看了这个问题后,有听取了我之前各种测试方法。果断做了两个改动,一个是在DMA描述符中增加volatile关键字,随后将发送后延时更改为发送前检测,检测当前DMA是否是否能够使用。结果系统可以正常工作(之前测试时也有类似检查,但仍然是存在问题,因此总体分析应该是volatile起到了作用)。

在检测当前发送描述符是否可用时需要注意一个细节,如果当前不可以,可以使用API_TimeSleep函数等待一段时间,但不要将函数返回,频繁调用发送函数也会让网络无法正常工作,很奇怪这个问题,但现象就是这样。

对于1000M和100M状态切换问题,包括不使用uboot初始化就无法通信问题,开始一直以为是PHY的问题,以至于将Linux的PHY读写函数内加入调试信息,全程跟踪Linux的PHY初始化过程。并没有什么收获。同样是那个同事提醒,uboot在探测网络连接后,不仅更改了MAC控制器的相关标志位,还更改了一个时钟类型的寄存器。经过跟着代码了解到,Zynq7000 的以太网控制器在状态切换时需要在SCLR控制器中更改其参考时钟频率。否则无法正常工作。由于代码配置十分复杂,这里通过读取相应状态的数据,在链接状态改变时写入相应寄存器。之后测试网络可以正常实现链接状态改变。

使用iperf对zynq进行单socket tcp传输速率测试;无网络损伤时,单向网络带宽约为600Mbps,双向网络带宽相加约400Mbps;50ms延时,1ms抖动,无丢包时,单向网络带宽约为155Mbps,双向网络带宽相加约40Mbps;和内核版本无关,经技术支持确定为PS GEM DMA的双向传输存在缺陷。

总结

zynq7000的bsp调试过程中历时较长,从年前到年后历时近2个月,除去中间一段时间做IMX6Q处理器的驱动,Zynq7000的驱动共花费时间近2个月,而网络暂用了一多半的时间,前后请了两位同事协助也没能解决,最终在第三位同事的协助下仅仅使用三天时间得以完美解决。得到的最大的教训是第三位同事做事的严谨程度远高于我们,正式对一些细节抓住不放,是问题得到了很好的理解。而自己由于对细节把握不仔细,虽然考虑到过类似问题,竟然傻乎乎的认为关闭Cache能起到volatile相同的作用。

提醒:《Zynq7000网络驱动调试笔记》最后刷新时间 2024-03-14 01:13:02,本站为公益型个人网站,仅供个人学习和记录信息,不进行任何商业性质的盈利。如果内容、图片资源失效或内容涉及侵权,请反馈至,我们会及时处理。本站只保证内容的可读性,无法保证真实性,《Zynq7000网络驱动调试笔记》该内容的真实性请自行鉴别。