Por que o Linux mostra mais e menos memória do que eu fisicamente instalei?

11

Eu sei sobre swap - esta questão não é sobre isso. No dmesg, o kernel do Linux (x86-64) me diz isso sobre quanta memória tenho:

[    0.000000] Memory: 3890880k/4915200k available (6073k kernel code, 861160k absent, 163160k reserved, 5015k data, 1596k init)

cat /proc/meminfo me diz que eu tenho

MemTotal:        3910472 kB

Pelos meus cálculos, acho que deveria ter exatamente 4 * 1024 * 1024 = 4194304k RAM. Que é bem menor que a segunda figura na linha dmesg acima!

O que há com todas essas figuras diferentes?

A propósito, uname -aresultados:

Linux pavilion 3.2.2-1.fc16.x86_64 #1 SMP Thu Jan 26 03:21:58 UTC 2012 x86_64 x86_64 x86_64 GNU/Linux
Robin Green
fonte

Respostas:

20

Você deve ler os dmesgvalores "Memory Akb / Bkb available" como:

No momento, há A disponível para uso e o número de quadro de página mais alto do sistema multiplicado pelo tamanho da página é B.

Isto é de arch/x86/mm/init_64.c:

printk(KERN_INFO "Memory: %luk/%luk available (%ldk kernel code, "
                 "%ldk absent, %ldk reserved, %ldk data, %ldk init)\n",
                 nr_free_pages() << (PAGE_SHIFT-10),
                 max_pfn << (PAGE_SHIFT-10),
                 codesize >> 10,
                 absent_pages << (PAGE_SHIFT-10),
                 reservedpages << (PAGE_SHIFT-10),
                 datasize >> 10,
                 initsize >> 10);

nr_free_pages()retorna a quantidade de memória física, gerenciada pelo kernel, que não está em uso no momento. max_pfné o número de quadro de página mais alto (o PAGE_SHIFTturno o converte em kb). O número de quadro de página mais alto pode ser (muito) maior do que o esperado - o mapeamento de memória feito pelo BIOS pode conter falhas.
Quanto esses furos ocupam é rastreado pela absent_pagesvariável, exibida como kB absent. Isso deve explicar a maior parte da diferença entre o segundo número na saída "disponível" e a RAM instalada real.

Você pode pesquisar por BIOS-e820em dmesg"ver" esses buracos. O mapa de memória é exibido lá (logo na parte superior da dmesgsaída após a inicialização). Você deve poder ver em quais endereços físicos você possui RAM real e utilizável.
(Outras peculiaridades do x86 e áreas de memória reservada provavelmente são responsáveis ​​pelo resto - não conheço os detalhes lá.)

MemTotalin /proc/meminfoindica RAM disponível para uso. Logo no final da sequência de inicialização, o kernel libera os initdados que não precisam mais; portanto, o valor relatado /proc/meminfopode ser um pouco maior do que o que o kernel imprime durante as partes iniciais da sequência de inicialização.

( meminfousa indiretamente totalram_pagespara essa exibição. Para x86_64, isso também é calculado por arch/x86/mm/init_64.cmeio do free_all_bootmem()qual ele é usado para mm/bootmem.ckernels que não são da NUMA.)

Esteira
fonte