Old*_*oil 11 linux memory embedded
这个问题相当长,所以我会在顶部提出问题,然后通过我的方法来回答问题:
在我们的测试系统在过去几天相当密集地运行之后 - 我 telnet 进入系统并检查了测试结果。当我来删除一些数据时,系统返回了命令行(好像命令执行正确一样)。当我来检查目录以获取另一组结果时,我看到该文件仍然存在(使用 ls)。
在此之后,我注意到越来越多的 shell 命令没有按预期执行。
在 rm 无法正确执行后,我将从dmesg的输出开始:
从进程 6821 (rm) 分配长度 61440 失败
每个 CPU 的 DMA:
CPU 0: hi: 0, btch: 1 usd: 0
Active_anon:0 active_file:1 inactive_anon:0 inactive_file:0 unevictable:6 脏:0 回写:0 不稳定:0 空闲:821 平板:353 映射:0 页表:0 弹跳:0
DMA free:3284kB min:360kB low:448kB high:540kB active_anon:0kB inactive_anon:0kB active_file:4kB inactive_file:0kB unvictable:24kB present:8128kB pages_scanned:0 all_unreclaimable?不
lowmem_reserve[]: 0 0 0
DMA:31*4kB 47*8kB 42*16kB 64*32kB 1*64kB 0*128kB 0*256kB 0*512kB 0*1024kB 0*2048kB 0*4096kB = 3284kB
总共 14 个页面缓存页面
无法为过程数据分配 RAM,错误号 12
最初,我以为我无法在连续内存的最大部分运行程序。这意味着 DMA 太碎片化了,我必须找到一种方法让系统对内存进行碎片整理。
然后我做了一个快速的数学/完整性检查,意识到程序应该能够在唯一的 64kB 连续内存插槽中运行。Rm 请求 61440 字节 (60kB)。
我做了一个很好的旧“手动碎片整理”并重新启动了系统。当我重新启动系统时,我输出 /proc/buddyinfo:
Node 0, zone DMA 2 8 3 12 0 1 0 1 0 1 0
我怀疑映射到:
但是,如果对上述值列表求和,则它与/proc/meminfo的输出不匹配:
MemTotal: 6580 kB
MemFree: 3164 kB
Buffers: 0 kB
Cached: 728 kB
SwapCached: 0 kB
Active: 176 kB
Inactive: 524 kB
Active(anon): 0 kB
Inactive(anon): 0 kB
Active(file): 176 kB
Inactive(file): 524 kB`
Unevictable: 0 kB
Mlocked: 0 kB
MmapCopy: 844 kB
SwapTotal: 0 kB
SwapFree: 0 kB
Dirty: 0 kB
Writeback: 0 kB
AnonPages: 0 kB
Mapped: 0 kB
Slab: 1268 kB
SReclaimable: 196 kB
SUnreclaim: 1072 kB
PageTables: 0 kB
NFS_Unstable: 0 kB
Bounce: 0 kB
WritebackTmp: 0 kB
CommitLimit: 3288 kB
Committed_AS: 0 kB
VmallocTotal: 0 kB
VmallocUsed: 0 kB
VmallocChunk: 0 kB
Run Code Online (Sandbox Code Playgroud)
回顾一下,我的问题是:
我正在使用运行 uClinux 2.6.30 版的 Lantronix 的 XPort Pro(8MB,Linux 操作系统)。正在使用的外壳是安静的。
And*_*ner 11
关于您的问题 2(对内存进行碎片整理),引用自https://www.kernel.org/doc/Documentation/sysctl/vm.txt:
紧凑内存
仅在设置 CONFIG_COMPACTION 时可用。当 1 写入文件时,所有区域都会被压缩,以便在可能的情况下在连续块中提供可用内存。这在例如分配大页面时可能很重要,尽管进程也会根据需要直接压缩内存。
这意味着以下命令(以 root 权限执行,并且如果启用了上述内核选项)
echo 1 > /proc/sys/vm/compact_memory
Run Code Online (Sandbox Code Playgroud)
应该告诉内核尽可能多地尝试对内存进行碎片整理。请注意,例如在某些 RHEL6 版本上,这可能会导致内核崩溃...
这花了一些时间,但我想我会推迟回答,直到我回答了所有 3 个子问题。
不过,在开始之前,我会提到,当谈到“碎片化”工作记忆时,正确的术语是“压缩”工作记忆。
我的结论是正确的 - rm 没有执行,因为没有足够的连续 RAM。该系统一直在获取 RAM 并将其碎片化,从而使其无法回收。
事实证明,除了重新启动嵌入式系统之外,没有办法压缩内存。在无 MMU 系统的情况下,预防就是游戏的名称。
我的一部分在思考是否有可能破解 linux 内核以在软件中模拟 MMU。我想如果有可能的话,早就有人做了。我无法想象这是一个全新的概念;)
对于这个项目,每次需要时我都使用 cron 手动启动程序。一个更好的方法是在启动时调用程序,然后强制程序休眠直到需要它。这样,不需要在每次使用时分配内存。从而减少碎片化。
在项目的第一次迭代中,我们依靠我的 shell 脚本调用来执行关键功能(例如 rm)。如果我们不需要,我们认为没有必要重新发明轮子。
但是,对于无 MMU 的系统,我建议尽可能避免使用 shell -
(问题,如果你执行会发生什么ls -la /path/to/directory/ | grep file-i-seek?)
(答案:它启动一个新的子进程)
如果您需要在 C 程序中实现一些核心 shell 脚本功能,我建议您查看BusyBox 中使用的源代码。很有可能你会在你的嵌入式系统中使用 C..