pci linux时序函数,实时Linux下的PCI驱动开发(下)
发布日期:2021-06-24 14:12:41 浏览次数:2 分类:技术文章

本文共 1453 字,大约阅读时间需要 4 分钟。

进入驱动的HPI相关部分后,就要好好研究pci2040的datasheet了。说实话,一个驱动程序的大部分内容,就是把datasheet里的内容翻译成代码,所以每一个驱动工程师都应该深入的阅读硬件文档。

首先看pci2040的配置空间,如下所示

有两个最重要的基地址,一个是HPI CSR内存基地址,可以通过它把PCI2040的HPI CSR寄存器群映射到主机的内存;还有一个是控制空间基地址,可以把PCI2040的32KB的控制空间映射到主机内存。

56c577fb3a4182d6550a084cdffa0917.png

HPI CSR寄存器如上所示,根据ioremap返回的基址加上相应的偏移,就可以顺序访问这些HPI CSR寄存器。可以看出这些寄存器都是用来控制DSP的工作状态的,比如中断的开关,重启DSP等等。那我们怎么把数据传递给DSP并获得DSP的运算结果?PCI2040的datasheet也提供了HPI DSP的资料,从中可以知道,与DSP的通信需要三个寄存器:地址寄存器HPIA,控制寄存器HPIC,数据寄存器HPID。这三个寄存器都可以通过映射PCI2040的控制空间来访问。映射成功后,每次与DSP的通信步骤如下:

(1)通过HPIC设置DSP访问模式

(2)通过HPIA设置访问的DSP内存地址

(3)通过HPID写入或者读取DSP的内存数据。

如果可以顺利访问DSP的内存了,那PCI2040驱动到这里就基本算完成了,可是用户态的应用程序怎么调用这个驱动呢?一般的设备驱动,都是需要先open,然后再ioctl来调用驱动的,不过这次我们的开发环境是rtai+linux,可以利用rtai的共享内存机制,来实现用户态程序与内核态驱动的通信。

在probe函数的最后,我们调用hpi_open()函数,该函数主要功能如下所示:

static int hpi_open (struct hpi_private_data *tp)

{

......

//开共享内存空间

g_shm=(lmcc_shm *)rtai_kmalloc(nam2num(LMCC_SHM_NAME), sizeof(lmcc_shm));

......

//设置任务模式

rt_set_oneshot_mode();

......

//初始化实时任务,相当于开一个内核线程

retval=rt_task_init(&g_task, UserRequestProc, 0, 8192, 3, 1, 0);

......

//启动rt定时器

period=start_rt_timer(0);

now=rt_get_time()+100*period;

//设置实时任务周期

rt_task_make_periodic(&g_task, now, nano2count(500000));// 0.5ms

......

}

用户态应用程序通过g_shm=(lmcc_shm *)rtai_malloc(nam2num(LMCC_SHM_NAME), sizeof(lmcc_shm))就可以得到这片共享内存的基地址,从而读写共享内存。实时任务每0.5ms查询一次共享内存,并对共享内存的改变做出反应。这样就实现了用户程序与驱动的通信。

至此,用户态的应用程序就可以读写DSP内存了,实现了驱动的基本功能,再根据用户需求,对读写操作做一层封装,方便用户使用,驱动就真正完成了。通过这个程序,可以对linux下的驱动到底是什么有个初步的认识,也可以对rtai下的实时linux有一些了解。

转载地址:https://blog.csdn.net/weixin_33326218/article/details/116756286 如侵犯您的版权,请留言回复原文章的地址,我们会给您删除此文章,给您带来不便请您谅解!

上一篇:kvm切换器不了linux系统,KVM切换器使用中最常见故障排除处理
下一篇:linux informatica教程,Informatica Grid 运维手册.doc

发表评论

最新留言

网站不错 人气很旺了 加油
[***.192.178.218]2024年04月01日 19时09分03秒