在芯片设计中,常常有这样的应用场景。硬件给软件传递消息,软件通过polling的方式获取。在我们的案例中,我们约定,硬件每次都上送128bit的数据。
实际操作如下:
软件在内存中分配了一段内存空间,用于硬件写数据,软件不断读此段内存获取硬件上送的数据。
那么问题来了,硬件是如何知道这段内存地址的呢?
通常在硬件内部实现了至少两个寄存器字段:起始地址(0x10000)和length 字段。
这两个字段说明了内存空间的位置和大小。软件和硬件两哥们商量好:硬件这从起始地址开始写数据,软件从起始地址开始读数据,硬件写数据占用内存空间,软件读数据释放内存空间。硬件占用,软件释放,硬件写到最后一个内存地址时,则翻转跳转到起始地址,形成buffer ring,可以用少量的内存空间实现大量的数据传输。
那么又有个问题来了,硬件是如何知道某段地址空间被软件释放了呢?
其实在硬件内部还需要实现一个寄存器(我们称之为doorbell),由软件负责写寄存器,写入软件下一个要读的消息地址序号,硬件比较之前的地址序号和当前的地址序号可以得知软件释放了多大的内存空间。
那么问题来了,软件是如何知道当前的内存中存在有效数据?
软件通过polling(不断询问)的方式不断访问此段内存空间,它是如何知道当前的地址存在有效数据的呢?
其实我们在128bit的消息中还定义了一个flag标志位,软件自己也维护了一个sw_flag标识位。
软件初始化流程中,首先将已分配的内存空间初始化为0,将sw_flag初始化为1,将硬件hw_flag初始化为1。每完成一轮地址访问,软件将sw_flag翻转一次,硬件将hw_flag翻转一次。软件每次读内存,都会将消息字段中flag与sw_flag进行比较,如果相等,则表示此消息是硬件上送的有效消息,此时读地址rd_ptr加1(为了简化说明,我们以rd_ptr代表软件下一个要读的地址,wr_ptr代表硬件下一个要写的地址)。
作者:C小鸽
文章来源:IC的世界
推荐阅读
更多IC设计干货请关注IC设计专栏。欢迎添加极术小姐姐微信(id:aijishu20)加入技术交流群,请备注研究方向。