Hum*_*ger 15 c c++ ipc mmap shared-memory
上下文是进程间通信,其中一个进程("服务器")必须将固定大小的结构发送到在同一台机器上运行的许多侦听进程("客户端").
在Socket Programming中我很自在.为了使服务器和客户端之间的通信更快并减少副本数量,我想尝试使用共享内存(shm)或mmaps.
操作系统是RHEL 64位.
由于我是新手,请建议我应该使用哪个.如果有人能指点我一本书或在线资源来学习同样的东西,我会很感激.
谢谢你的回答.我想补充一点,服务器(市场数据服务器)通常会接收多播数据,这将导致它每秒向"客户端""发送"大约200,000个结构,其中每个结构大约为100字节.shm_open/mmap的实现是否仅对大型数据块或大量小型结构的性能优于套接字?
Jen*_*edt 23
我将mmap与shm_open共享内存映射到进程的虚拟地址空间.这是相对直接和干净的:
"/myRegion"shm_open您在该区域上打开文件描述符ftruncate你扩大细分到你需要的大小mmap您一起将其映射到您的地址空间在shmat和Co接口有(至少在历史上),他们可能有该内存可以映射的最大数量的限制的缺点.
然后,所有的POSIX线程同步工具(pthread_mutex_t,pthread_cond_t,sem_t,pthread_rwlock_t,...)有初始化的接口,使您可以在一个进程共享环境中使用他们.所有现代Linux发行版都支持这一点.
这是否比套接字更可取?性能方面它可能会有所不同,因为你不必复制东西.但我想的主要观点是,一旦你初始化了你的片段,这在概念上就更简单了.要访问项目,您只需要锁定共享锁,读取数据然后再次解锁.
正如@R建议的那样,如果你有多个读者pthread_rwlock_t可能会使用最好的锁结构.
除了已经提出的建议之外,我还想提供另一种方法:IPv6节点/接口本地多播,即受限于环回接口的多播. http://www.iana.org/assignments/ipv6-multicast-addresses/ipv6-multicast-addresses.xml#ipv6-multicast-addresses-1
起初这可能看起来很重,但大多数操作系统在零拷贝架构中实现环回套接字.映射到buf传递给的参数的页面send将被分配一个额外的映射并在写入时标记为复制,这样如果发送程序覆盖其中的数据,或者解除分配,则将保留内容.
您应该使用强大的数据结构,而不是传递原始结构.Netstrings http://cr.yp.to/proto/netstrings.txt和BSON http://bsonspec.org/浮现在脑海中.