简介RTLinux下的一种实时应用通信机制
必须自己定义相应的协议,对于写入共享数据区域的有数据进行保护,如同步控制等。 *数据可以既定格式读/写,各个数据域的更新十分便易。 *不是点对点的通信通道,可以支持多生产者、多消费者的使用模式,能够同时被多个线程访问。
在RTLinux下,共享内存的使用可采用以下两种方式: (1)利用RTLinux中附带的mbuff模块 在使用mbuff之前,要求系统中已经加载了mbuff.o模块。该模块中的两个函数被分别用于分配和释放所需的内存空间。 #include [分配] void * mbuff_alloc(const char * name,int size); 从内核空间中分配一块与name相连,大小为size字节的内存空间,返回地址指针,设备这块空间的引用标识为1。如与name相连的内存空间已经存在,就仅仅返回指向该空间的地址指针,同时将其引用标识加1。 [释放] void mbuff_free(const char * name,int size); 将mbuff的引用标识减1。当引用标识被减为0时,释放mbuff。 注意:①mbuff_alloc使用了vmalloc函数,由于分配内核空间的需要,会交换出一系列的内核空间页面,所以在实时线程、中断处理线程、定时器中断线程中调用这个函数是十分危险的。 ②在进程结束前,一定要调用mbuff_free函数。Mbuff所占内存空间不会因为其引用进程的结束而自行释放。 (2)高地址空间物理内存的直接隔离 在系统启动时,隔离出一定大小的高地址空间物理内存,使其脱离系统运行环境,作为专用的共享内存区域。 图4 共享内存互斥操作流程图 在Linux启动配置文件中,插入一行以append关键字起始的命令行,即可实现高端内存空间的隔离。修改后的/etc/lilo.conf文件如下所示: image=/boot/zImage label=rtlinuxX.X root=/dev/hda2 read_only append=“mem=Xm” 其中,mem的值对应于被隔离空间的起始地址,可以由物理内存总容量减去所需共享空间容量得到。但是必须注意,被隔离出的共享空间的容量必须小于/usr /include/asm/param.h文件中定义的页面长度。Intel Pentium系列芯片的页面长度为4MB。 对共享内存空间的存取操作通过访问其基址来实现。必须首先定义共享内存空间的基址。 #define BASE_ADDRESS(127%26;#215;0x100000) 在实时和非实时模块中有不同的基址访问方法。写时模块运行于内核地址空间,可以直接将基址作为地址指针进行存取,使用语句如下: unsigned short * sharemem; sharemem=(unsigned short *)__va(BASE_ADDRESS); 非实时模块运行于用户地址空间,必须先将该物理地址映射入该进程虚拟地址空间后,才能对其进行存取。使用命令如下: #include #include #include int fd; unsigned short * sharemem; fd=open("/dev/mem",O_RDWR); ① sharemem=(unsigned short *)mmap(0,buflen, PROT_READ|PROT_WRITE, MAP_FILE|MAP_SHARED, Fd,BASE_ADDRESS); ② 注①:访问物理内存必须打开与其对应的设备文件/dev/mem。 注②:mmap命令的作用是将设备文件fd中,从当前进程的虚拟地址空间,其返回值可被非实时进程存取。 以上两种方式在实现机理上的不同之处在于,mbuff利用vmalloc从内核地址空间分配的共享内存空间仅仅在逻辑上连续,空间的大小不受实际物理内存空间的限制;而直接隔离物理内存所获取的缓冲区物理上连续,但是大小受到物理内存空间和当前系统状况的限制。共同之处在于,所获得的内存均被隔离于系统内核的运行环境之外,不会在页面交换中被换出,所以以上两种方法均适用于实时应用之中。
3 两种通信接口的结合 以上两种通信接口具有不同的适用范畴,为了实现一个完整的实时应用,通常需要将两者结合,以一个实时数据采集程序为例,实时模块和非实时模块之间通常需要传送两种类型的数据;结果数据和控制信息。 结果数据:由实时模块周期性产生。非实时模块用于显示和存储,对读/写的时序性要求不高,但是通常需要由多个用户共享,因此,利用共享内存模块传输比较适合。 控制信息:主要用于实现非实时模块和实时模块之间的交互控制,数据量小,但是比较注重信号读/写的时序性和通信过程中实时性,采用RT_FIFO实现比较适合。 图2为通用的抽象数据流图。
3.1 共享内存的内步控制和RT_FIFO的使用 由于对共享内存的存取通过直接访问指针来实现,操作系统不会为其提供任何同步控制,应用程序必须自行提供握手机制,来保证读/写进程之间同步。 实现同步的一种方式是接收方和发送方利用消息通信来实现握手。接收方对共享内存以轮询的方式监测新数据的到来,然后发送接收信息。为了实现握手,发送方对于每条接收消息都
- 硬实时操作系统-RTLinux(04-13)
- RTlinux的介绍(08-15)
- 基于RTLinux的软件无线电侦察预处理系统(05-15)
- 利用RTLinux开发嵌入式应用程序的方案(03-07)
- 一种8路串口转换PCI总线的设计方案(07-20)
- Windows CE 进程、线程和内存管理(11-09)