Если ваш вопрос «почему int verbose = 0;
выделено для [heap]
отображения памяти в соответствии с /proc/self/maps
?», Ответ таков:
- все
[heap]
понятие действительно является пережитком давно забытого прошлого, и
- традиционный
[heap]
начинается сразу после .bss
, и они обычно разделяют одно и то же отображение, так что ничего здесь не удивит.
Немного расширив точку 1, в традиционной старой модели памяти UNIX (до того как потоки и mmap
стали единым целым), на процессорах, где стек уменьшается, верхняя половина памяти была зарезервирована для пространства ядра, стек запущенная в самом верхнем пользовательском запоминающем устройстве, сама программа .text
запускалась по адресу 0, сразу после нее следовали .data
и .bss
, а затем сразу же начиналась куча (тип brk
/ sbrk
). Это позволило куче расти до более высоких адресов, а объединенная куча + стек максимально доступной памяти.
Эта модель не работает вообще при наличии потоков, разделяемых библиотек и файлов отображения памяти, и была в значительной степени заброшена современными malloc
реализациями, которые редко вообще беспокоят sbrk
. Вместо этого они просто mmap
нужной памяти (и любая такая память не будет отображаться в [heap]
, что вы видите в procfs
).
приписка
- Идея отображения нулевой страницы в пространство процесса давно отброшена, поскольку она приводит только к ошибкам. Вот почему
.text
начинается с более высоких адресов во всех современных UNIXen.
- Предоставление ядру половины доступного адресного пространства также довольно расточительно, и 32-битный Linux начал предоставлять ядру намного меньше места. В 64-разрядных системах исчерпание адресного пространства больше не является проблемой.
Обновление:
То есть вы имеете в виду, что [куча] содержит как .bss, так и часть кучи. Таким образом, единственный способ определить, находится ли адрес внутри кучи, состоит в том, чтобы отслеживать вызовы malloc (), free (), ...?
Не думаю, что я объяснил это хорошо.
Понятие о том, что в пространстве процессов есть одна область, называемая "кучей", устарело. Современная реализация malloc
, скорее всего, имеет несколько специфичных для потока арен, полученных из системы через mmap
, и объект, выделенный в куче, может находиться в любой из них.
Вы не можете легко сказать «о, этот адрес 0x568901234 выглядит как куча», потому что это может быть что угодно.
Каков стандартный способ определения диапазонов адресов для областей виртуальной памяти (например, .text, heap и .bss) процесса в Linux, если вывод procfs устарел?
Здесь снова вы пытаетесь объяснить структуру памяти в терминах, которые несколько устарели: не один .text
или .bss
в большинстве процессов, потому что каждая общая библиотека будет иметь свою собственный (в дополнение к основному исполняемому файлу). А также есть множество дополнительных секций (.tls
, .plt
, .got
и т. Д.) И секций даже не требуется в время выполнения вообще - ELF (во время выполнения) нуждается только в сегментах и не заботится о разделах.