Подтвердить что ты не робот

Что происходит в ядре во время malloc?

Мне задали этот вопрос во время интервью. Что они хотели знать, когда пользователь называет malloc (4) распределять 4 байта памяти, как реагирует операционная система (Linux)? Какая подсистема отвечает на этот системный вызов?

Я сказал ему, что malloc() будет обслуживаться подсистемой управления памятью. Реализация malloc() будет проходить через список свободной памяти (физической памяти), мы будем называть ее свободным списком и найти соответствующий фрагмент, который больше или равен 4 байтам. Как только он найдет такой кусок, он будет удален из бесплатного списка и добавлен в использованный список. Затем эта физическая память будет отображена в кучу процесса vma struct. Он, похоже, не вполне удовлетворился этим ответом. Как система приятелей вписывается в это? Любая помощь будет принята с благодарностью.

4b9b3361

Ответ 1

Когда приложения пользовательского пространства вызывают malloc(), этот вызов не реализован в ядре. Вместо этого это вызов библиотеки (реализованный glibc или аналогичный).

Короткий вариант заключается в том, что реализация malloc в glibc либо получает память из системного вызова brk()/sbrk(), либо анонимную память через mmap(). Это дает glibc большой непрерывный (относительно адресов виртуальной памяти) фрагмент памяти, который реализует реализацию malloc, и уменьшает количество кусочков в меньших частях и руки в ваше приложение.

Здесь небольшая реализация malloc, которая даст вам идею, а также множество ссылок.

Обратите внимание, что пока ничего не происходит в физической памяти - обрабатывается системой виртуальной памяти ядра, когда сегмент данных процесса изменяется через brk()/sbrk() или mmap(), и когда на память ссылаются (посредством чтение или запись в память).

Подводя итог:

  • malloc() будет искать свои управляемые фрагменты памяти, чтобы увидеть, есть ли кусок неиспользуемой памяти, удовлетворяющий требованиям распределения.
  • В противном случае malloc() попытается расширить сегмент данных процесса (через sbrk()/brk() или в некоторых случаях mmap()). sbrk() заканчивается в ядре.
  • Вызов brk()/sbrk() в ядре корректирует некоторые смещения в struct mm_struct процесса, поэтому сегмент данных процесса будет больше. Сначала физическая память не будет отображаться на дополнительные виртуальные адреса, которые расширяют сегмент данных.
  • Когда эта немаркированная память сначала затрагивается (вероятно, чтение/запись с помощью реализации malloc), обработчик ошибок будет запускаться и зависеть от ядра, где ядро ​​назначит физическую память для памяти без памяти.

Ответ 2

В вашем ответе есть ошибка - malloc не работает напрямую с физической памятью. Он имеет дело с страничной виртуальной памятью - хотя я не уверен, что это верно для каждой архитектуры.

Когда ваша программа пытается выделить память, а свободный список не содержит кусок равного или большего размера, чем запрошенный размер, выделяется вся новая страница. Размер страницы зависит от архитектуры (4096 байт на x86). Распределение страниц - это то, что может выполнять только ядро, поэтому вызов malloc может вызвать системный вызов. Новый адрес затем добавляется в свободный список, а malloc управляет свободным списком в соответствии с его реализацией (например, glibc).