lua - 为什么在64位平台上LuaJIT的内存限制为1-2 GB?

标签 lua luajit

在64位平台上,LuaJIT仅允许最多1-2GB的数据(不计算使用malloc分配的对象)。这种限制从何而来,为什么比32位平台上的限制还要少?

最佳答案

LuaJIT设计为使用32位指针。在x64平台上,限制来自使用mmapMAP_32BIT标志。


MAP_32BIT(从Linux 2.4.20,2.6开始):

将映射放入进程地址空间的前2 GB。对于64位程序,仅x86-64支持此标志。它被添加以允许在前2GB内存中的某个位置分配线程堆栈,从而提高某些早期64位处理器上的上下文切换性能。


本质上,使用此标志将限制为前31位,而不是顾名思义的前32位。请查看here,以在Linux内核中使用MAP_32BIT很好地概述1GB限制。

即使您可以拥有超过1GB的容量,LuaJIT作者也解释了为什么这样做会降低性能:



完整的GC比分配本身花费的时间多50%。
如果启用了GC,它将使分配时间加倍。
为了模拟真实的应用程序,对象之间的链接在第三轮中被随机化。这使GC时间加倍!


那只是1GB!现在想象一下使用8GB内存-完整的GC周期将使CPU繁忙长达24秒!
好的,所以正常模式是使用增量GC。但这只是意味着开销增加了约30%,混合在分配之间,并且每次都会驱逐CPU缓存。基本上,您的应用程序将由GC开销控制,您会开始怀疑为什么它运行缓慢....

tl; dr版本:请勿在家中尝试。并且GC需要重写(推迟到LuaJIT 2.1)。


总而言之,1GB的限制是Linux内核和LuaJIT垃圾收集器的限制。这仅适用于LuaJIT状态内的对象,可以通过使用malloc克服,它将在较低的32位地址空间之外进行分配。另外,可以在32位模式下使用在x86上构建的x64并访问完整的4GB。

查看这些链接以获取更多信息:


How to get past 1gb memory limit of 64 bit LuaJIT on Linux?
LuaJIT x64 limited to 31 bit address space, even without MAP_32BIT restrictions?
LuaJIT strange memory limit
Digging out the craziest bug you never heard about from 2008: a linux threading regression

关于lua - 为什么在64位平台上LuaJIT的内存限制为1-2 GB?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/35155444/

相关文章:

c - 读取文件 lua 时出现紧急错误

unit-testing - Lua API 单元测试

Lua:从 float 转换为 int

c++ - 如何将函数从 C++ 可执行文件公开给 LuaJIT

LuaJIT,如何将cdata转换为userdata?

c++ - C++ socket.http 中嵌入的 LUA [错误 : attempt to call a nil value]

c - Lua 从 C 获取并执行函数

LuaJIT 需要模块错误

lua - "loadall.so"是什么?

nginx - Luasocket + nginx 错误 - lua 入口线程中止 : runtime error: attempt to yield across C-call boundary