使用 TCP 跨进程共享内存

Posted

技术标签:

【中文标题】使用 TCP 跨进程共享内存【英文标题】:Using TCP for memory sharing across processes 【发布时间】:2015-11-30 17:35:59 【问题描述】:

我在开始处理nodejs 时犯了一个错误,因为我没有使用RedisMemcache 或其他内存存储系统。现在,重写所有内容以在这些 API 中容纳和关联我的代码为时已晚。

但是,我最近才发现分叉流程及其益处;特别是因为我正在开发游戏服务器。

我遇到的问题是:The memory is not shared between cores in nodejs.. 直到我找到了一个名为 Amensia 的 TCP 内存共享模块。

说了这么多,我有一些关于nodejstcp 的问题:

1) maximum size of a TCP packet 大约是 64k,所以在使用这个模块时我只能共享最大 64k 的数据?

2) 我使用全局 GAMESusers 对象来存储玩家数据。当玩家在地图中移动(x,y 位置)和其他操作时,这些对象会更新。通过 TCP 发送所有这些数据会导致瓶颈吗?

【问题讨论】:

共享​​>这个模块意味着将数据复制到不同的进程。那是你想要的吗?此外,我认为将您的存储/获取机制抽象为能够使用 Redis/Memcached/etc 不会太复杂...... 好点.. 我刚才在想这个。我会说不,因为这些临时对象可以保存数百个玩家数据,并且将它们扔在 TCP 协议周围只是自找麻烦,对吗?也许 Redis/Memcache 是我必须要做的……只是,超过 20k 行,它将成为一个 PITA。 可能存储/获取代码将是 100 行。我强烈推荐 Redis @NiCkNewman 我是否正确地告诉了您大多数进程在同一个本地主机上运行?如果是,那么通过使用 ZeroMQ / inproc:// 传输类来避免 TCP 开销并让您通过智能(可扩展)正式通信模式处理“讨论”可能是有意义的。我来自低延迟角落,所以在这个方向上有点变形,低内存占用和每纳秒计数,如果您的游戏环境有其他优先级和/或操作系统功能不允许使用这种方法,那么抱歉:o ) 【参考方案1】:

最小开销方法

为您的所有 localhost 分叉进程配备进程间智能消息传递层。

通过这种方式,您的“共享”可以在抽象意义上和(在 ZeroMQ 的情况下非常有吸引力)在字面意义上实现,因此 ZeroMQ 允许您通过共享缓冲区避免数据重复(ZeroCopy 格言)。

如果您的操作系统允许 IPC://inproc:// 传输类几乎没有开销,而 inproc:// 甚至不需要(感谢 ZeroMQ 团队的出色架构思想)需要 _any_additional_ 线程 ( CPU/RAM-overheads ) 一旦通过 ZeroThread 调用-context( 0 )

一种更不受开销影响的方法( if your app fits nanomsg )

如果 ZeroMQ 对于你的特定目标来说似乎太强大了,可能会对它的妹妹 Martin Sustrik 感兴趣,ZeroMQ 的共同父亲已经分拆 - nanomsg which also has node.js port available

去哪里了解更多详情?

在 ether ZeroMQ / nanomsg 案例中,你可以做的最好的下一步是获得更多的全局视图,这对于尝试使用 ZeroMQ 编码的前几件事来说可能听起来很复杂,但如果你至少跳转到Code Connected, Volume 1 的第 265 页,如果不是在那里逐步阅读的话。

有史以来最快的学习曲线是首先在 图 60 重新发布更新和图 62 HA 克隆服务器对上获得未公开的视图,以获得可能的高可用性方法和然后回到根源、元素和细节。

如果您爱上了这种思维方式,您会喜欢 Martin Sustrik 的博客文章 - 确实是个聪明人。至少值得花时间从他的观点和经验中获得启发。

【讨论】:

在开始我的节点应用程序之前,我应该阅读有关缩放和 IPC 的信息。希望现在还不算太晚,我有很多重写工作要做。 祝你好运,NiCk,不过,使用低开销、无 db,您将通过 nano / Zero 智能消息传递远远领先于“传统”人群。恕我直言,值得你的汗水和泪水,丘吉尔会说......【参考方案2】:

1) TCP 数据包大小应该没有任何问题。如果数据太大,节点将缓冲/排队您的数据,并在操作系统为其提供可写套接字的文件描述符时发送它们。仅当您每秒写入的网络带宽超过网络带宽时,您才可能遇到性能问题。此时 Node 也会使用更多的 RAM 来对所有这些消息进行排队。

https://nodejs.org/api/net.html#net_socket_buffersize

2) 大多数游戏使用 TCP 或 UDP 进行实时通信。它可能是瓶颈,就像其他任何东西(RAM、CPU、带宽、存储)一样。在某些压力点,一个或多个资源将结束/失败/表现不佳。当所有优化都针对您的瓶颈完成并且您仍然需要向游戏服务器添加更多同时用户时,使用可以水平增长(添加更多机器)的架构通常是一个好习惯。

https://1024monkeys.wordpress.com/2014/04/01/game-servers-udp-vs-tcp/

您可能会使用 TCP 连接到 Redis 服务器(但您也可以使用 unix 套接字)。

如果你只需要进程间通信(而不是机器间),你应该看看“集群”Node.js 核心模块。内置IPC。

【讨论】:

以上是关于使用 TCP 跨进程共享内存的主要内容,如果未能解决你的问题,请参考以下文章

Android跨进程通信-共享内存

Android跨进程通信-mmap函数

Android 基于共享内存实现跨进程大数据的高效传输

Android 基于共享内存实现跨进程大数据的高效传输

Android 基于共享内存实现跨进程大数据的高效传输

跨进程内存屏障