新闻中心

EEPW首页>嵌入式系统>设计应用> 一种嵌入式RPC的设计与实现

一种嵌入式RPC的设计与实现

作者: 时间:2011-06-10 来源:网络 收藏

过程调用的类型定义如下。_TYPE_SIMPLE_WRITEREAD是简单的读写,输入参数和输出参数都在头信息和过程的参数数据结构中。_TYPE_READ指返回结果保存在单独的内存。_TYPE_WRITE指写信息保存在单独的内存。RPC_TYPE_WRITE_READ调用是需要内存保存输入数据,返回时需要保存输出的结果。
f.JPG
每个过程定义自己的输入输出参数结构。例如对获取串口状态GetCommState过程,建立RPC_GETCOMMSTATE结构。
h.JPG
由于各个编译器对struct数据结构的成员的对齐不同。这样同样的struct在客户端和服务器端的大小可能不同,同样的成员在结构中的位置不同。为了确保客户端和服务器端有相同的对齐,我们采用字节对齐用#pragma pack(1)。
3.2 Packet内存布局
开始依次是头信息和参数,其余部分根据特定的过程而不同。以RPC_TYPE_WRITE_READ类型的布局为例:头信息,参数,输入内存块[1…N],输出内存块[1…N]。其他的过程类型布局类似。
3.3 服务器端
3.3.1 网络模块
RPC在单独的任务中执行。图5为RPC任务流程图。调用VxWorks的系统函数taskSpawn建立RPC任务。调用socket( )建立面向连接的SOCK_ STREAM套接字,bind将套接字与本地网络地址和端口号捆绑,listen申明要在该端口侦听客户连接请求,accept阻塞等待请求的到来。

本文引用地址://m.amcfsurvey.com/article/150615.htm

h.JPG


3.3.2 状态机实现
当accept后,进入服务器端状态机。设置accept返回的socket为非阻塞状态。在阻塞的socket上调用send时,如果没有足够的输出缓冲区,该调用将被阻塞。Recv也是一样,要读的数据没有就绪时,调用者阻塞。服务器不知道每次要读取的字节数,所以阻塞的socket无法工作。
分配2块内存:A和B。内存A用来保存recv的内容,内存B用来保存客户端发送的Packet内容。因为服务器不知道客户会发送多大的内容过来,每次从内存A拷贝到内存B之前检查内存B的大小,如果内存B剩余大小不够则重新分配。
在得到了整个Packet后,即GetComplatePacket后,根据dwCallID调用服务器的本地过程,待返回后将返回值和内存打包发送给客户端。
3.4 客户端实现
客户端的流程如图6所示。在Windows下运行,首先调用WSAStartup,Windows根据请求的Socket版本来搜索相应的Socket库,然后绑定找到的Socket库到该应用程序中。然后初始化socket,连接到服务器,接着过程调用。比如过程调用1会进入图4状态机。状态机和服务器端类似,只是首先参数打包,发送给服务器,返回后拆包并拷贝返回信息到内存中。

i.JPG



4 结束语
本文和实现的RPC可应用于白盒测试、跨平台开发环境和开发客户端软件等。商用的IDE软件都很昂贵,通过本RPC,测试人员就可用开源的环境如cygwin等开发白盒测试代码。另外对于有大量操作界面的开发,需要频繁下载到开发板上验证,本文RPC可应用于构建跨平台的开发环境,直接在Windows上开发界面部分,最后下载到开发板上,从而大大提高开发效率。大多数的软件都有相应的PC客户端软件,本文的实现也适用于开发PC客户端软件。

linux操作系统文章专题:linux操作系统详解(linux不再难懂)

上一页 1 2 3 下一页

评论


相关推荐

技术专区

关闭