Я написал main.c
в Linux:
int main()
{
while (1){}
}
Когда я компилирую и запускаю, я могу pmap
это:
# pmap 28578
28578: ./a.out
0000000000400000 4K r-x-- /root/a.out
0000000000600000 4K r---- /root/a.out
0000000000601000 4K rw--- /root/a.out
00007f87c16c2000 1524K r-x-- /lib/libc-2.11.1.so
00007f87c183f000 2044K ----- /lib/libc-2.11.1.so
00007f87c1a3e000 16K r---- /lib/libc-2.11.1.so
00007f87c1a42000 4K rw--- /lib/libc-2.11.1.so
00007f87c1a43000 20K rw--- [ anon ]
00007f87c1a48000 128K r-x-- /lib/ld-2.11.1.so
00007f87c1c55000 12K rw--- [ anon ]
00007f87c1c65000 8K rw--- [ anon ]
00007f87c1c67000 4K r---- /lib/ld-2.11.1.so
00007f87c1c68000 4K rw--- /lib/ld-2.11.1.so
00007f87c1c69000 4K rw--- [ anon ]
00007fff19b82000 84K rw--- [ stack ]
00007fff19bfe000 8K r-x-- [ anon ]
ffffffffff600000 4K r-x-- [ anon ]
total 3876K
Итого (3876), деленное на K, равно VIRT
столбцу в выходных данных top
. Теперь, где текстовый сегмент? На 400000, 600000 и 601000, верно? Где я могу прочитать объяснение, что где? man pmap
не помогло.
linux
process
memory
virtual-memory
Торстен Стэрк
источник
источник
Ответы:
Текстовый сегмент - это отображение в 0x400000 - он помечен как rx для удобочитаемого и исполняемого. Отображение в 0x600000 доступно только для чтения, так что это почти наверняка раздел «.rodata» исполняемого файла. GCC помещает строковые литералы C в раздел только для чтения. Отображение в 0x601000 'rw-', так что это, вероятно, знаменитая куча. Вы можете иметь исполняемый файл
malloc()
размером 1024 байта и распечатать адрес, чтобы убедиться в этом.Вы можете получить немного больше информации, найдя PID вашего процесса и выполнив:
cat /proc/$PID/maps
- на моем ноутбуке Arch, что дает дополнительную информацию. На нем запущено ядро 3.12, так что у него также есть/proc/$PID/numa_maps
и catting, что также может дать небольшую информацию.Другие вещи для запуска исполняемого файла:
nm
иobjdump -x
. Первый может дать вам представление о том, где находятся различные объекты на карте памяти, поэтому вы можете увидеть, что находится в разделе 0x4000000 по сравнению с другими разделами.objdump -x
Показывает заголовки файлов ELF среди множества других вещей, так что вы можете увидеть все разделы, заполненные именами разделов, и их отображением во время выполнения или нет.Чтобы найти письменное объяснение «что это где», вам придется сделать что-то вроде google для «ELF FILE memory layout». Помните, что формат файла ELF может поддерживать более экзотические макеты памяти, чем обычно используются. GCC и Gnu ld и glibc делают упрощенные предположения о том, как исполняемый файл размещается и затем отображается в памяти во время выполнения. Существует множество веб-страниц, предназначенных для документирования этого, но они применяются только к более старым версиям Linux, более старым версиям GCC или glibc или только к исполняемым файлам x86. Если у вас его нет, получите
readelf
команду. Если вы можете писать программы на C, создайте свою собственную версиюobjdump -x
илиreadelf
ознакомьтесь с тем, как работают исполняемые файлы и что в них.источник
readelf
илиobjdump
выяснить это, и любой исполняемый файл, который вы сделали. Мой пакет Linux для Linux использует /usr/lib/libc-2.18.so, поэтому он сильно отличается от вашего.0x601000
это сегмент данных. Она содержит.data
,.bss
и может быть расширена с помощьюbrk()
.[anon]
указывает на не файловую резервную копию памяти (поэтому поддерживается swap), полученную черезmmap()
. dlmalloc используетbrk()
для распределений, меньших чем ~ 64Kb IIRC, иmmap()
для больших распределений. Куча - это все, что выделяет malloc, как расширенная часть сегмента данных, так иmmap()
распределения на основе.