首页 > 解决方案 > 为什么这个很小的 ​​C 程序会占用这么多内存?

问题描述

int i = 0;

int main(){
  while (true){
    i = 1;
  }
  return 0;
}

上面的程序(用 gnu g++ 编译,没有额外的编译器标志)只是永远循环,似乎比它应该使用的内存更多(顶部的输出如下所示):

  PID USER      PR  NI    VIRT    RES    SHR S  %CPU %MEM     TIME+ COMMAND                                                                                
 9392 root      20   0    4376    788    728 R 100.0  0.0   2:32.65 a.out  

我明白为什么 CPU 使用率为 100%,因为它在 while 循环中不断旋转。为什么 VIRT 是 4MB?为什么 SHR 是 728KB?我没有使用任何库。最后,也是最重要的,为什么要使用 788KB 来存储一个变量?剩余的 (4376-788)KB 在哪里/如何存储/使用?

标签: cmemory

解决方案


为什么 VIRT 是 4MB?为什么 SHR 是 728kB?我没有使用任何库。

这是不准确的。

让我们编译:

#include <unistd.h>
#include <stdio.h>
#include <stdlib.h>

int main() {
    char buf[100];
    snprintf(buf, sizeof buf, "pmap -x %u", (unsigned)getpid());
    system(buf);
}

用命令gcc -o test -W{all,extra,error} -xc test.cc

并运行它:

$ ./test
7360:   ./test
Address           Kbytes     RSS   Dirty Mode   Mapping
0000000000400000       4       4       4 r-x--  test
0000000000600000       4       4       4 rw---  test
00007f1f4d96a000    1580     788       0 r-x--  libc-2.12.so
00007f1f4daf5000    2044       0       0 -----  libc-2.12.so
00007f1f4dcf4000      16      16      16 r----  libc-2.12.so
00007f1f4dcf8000       8       8       8 rw---  libc-2.12.so
00007f1f4dcfa000      16       8       8 rw---    [ anon ]
00007f1f4dcfe000     128     128       0 r-x--  ld-2.12.so
00007f1f4df0c000      12      12      12 rw---    [ anon ]
00007f1f4df1d000       4       4       4 rw---    [ anon ]
00007f1f4df1e000       4       4       4 r----  ld-2.12.so
00007f1f4df1f000       4       4       4 rw---  ld-2.12.so
00007f1f4df20000       4       4       4 rw---    [ anon ]
00007ffd4a872000     132      12      12 rw---    [ stack ]
00007ffd4a961000      12       0       0 r----    [ anon ]
00007ffd4a964000       8       4       0 r-x--    [ anon ]
ffffffffff600000       4       0       0 r-x--    [ anon ]
----------------  ------  ------  ------
total kB            3984    1000      80

(如果您在pmap -x输出中看到重复的行,这是旧版本中的错误)。

所以,它使用

  • libc.so- C 标准库。
  • ld.so- 动态链接器。

RSS 的 1000kB 被占用:

  • 920kB 是您的可执行文件 (4kB) 和共享库(带r-x--模式的页面)的可执行代码
  • 12kB 是堆栈(标记为[ stack ])。
  • 标记为模式的页面[ anon ]是来自可执行库和共享库的部分的rw---堆和 0 初始化数据,具有静态存储持续时间。.bss
  • 其余的是只读和非 0 初始化数据,具有来自可执行文件和共享库的 (mode) 部分的静态存储.data持续.rodata时间r----

推荐阅读