Модульное ядро ​​против микроядра / монолитное ядро

Я программист на C и новичок в программировании ядра Linux. Я мог бы найти, что есть 3 типа ядра: монолитное, микро и модульное ядро. В то время как поиск в Google, я мог найти какой-то сайт, на котором говорится, что у linux монолитное ядро ​​(в переполнении стека), а некоторые другие говорят, что микроядро, а остальные говорят, что гибридное ядро. Поэтому я полностью сбит с толку, читая модульную концепцию, в которой говорится, что новый модуль для драйвера можно добавить без перекомпиляции ядра, что противоречит моему предположению, что Linux использует монолитное ядро. Монолитное ядро ​​работает в едином адресном пространстве, и в качестве одного процесса это также немного сбивает с толку, если так

3 ответа

Прежде чем пытаться понять эти различия, вы должны сначала понять другие концепции:

1. Модульное программирование.

Модуль является функционально завершенной частью программы. Модуль обычно имеет следующие свойства:

  1. Разделение интерфейса и реализации.
  2. Процедуры инициализации и деинициализации. Оба являются необязательными. Процедура деинициализации, вероятно, будет отсутствовать в среде с GC (сборщик мусора).
  3. Модули, используемые программой, составляют ориентированный ациклический граф или граф зависимостей (вы, возможно, слышали об этом - циклические зависимости недопустимы, зависимость инициализируется перед зависимым модулем).

Модульное программирование необходимо при создании больших систем. Каждое большое ядро ​​является модульным ядром, независимо от того, является ли оно монолитным, гибридным или микроядром.

Иногда модули могут загружаться и выгружаться динамически. Динамические модули являются неотъемлемой частью любой расширяемой системы. Это могут быть плагины или, если говорить о ядрах, драйверы, которые разрабатываются и распространяются отдельно от ядра.

2. Безопасные и небезопасные языки.

Безопасные языки очень строго определяют, что может происходить в программе. Самое главное, они не имеют понятия о неправильно сформированной программе (или бессмысленной программе). Каждая программа действительна, и ее выполнение всегда следует спецификации языка. Делает ли программа то, что от нее ожидает программист, в данном контексте не имеет значения.

Общие черты безопасных языков:

  1. Они используют сборщик мусора.
  2. У них нет указательной арифметики. Это означает, что запись или чтение по произвольному адресу запрещены.
  3. Они предотвращают доступ к массиву вне диапазона (если есть такая концепция). Исключения или аналогичные механизмы могут использоваться для сигнализации и восстановления после таких сбоев.
  4. Ссылки (или указатели) имеют только два возможных состояния: нулевая ссылка и ссылка на действительный объект. Это гарантировано сборщиком мусора. На самом деле, GC является ключевым компонентом здесь. Некоторые языки идут еще дальше и вообще не допускают нулевых ссылок.
  5. Каждому объекту (используемому фрагменту памяти) назначена информация о типе, доступ к объекту возможен только через ссылку соответствующего типа, например, вы не можете получить доступ к массиву целых чисел через ссылку на строку.

Вы можете добавить больше записей в этот список, но основная идея состоит в том, чтобы гарантировать, что программа может получить доступ только к действительным областям памяти, используя допустимые операции. Имейте в виду, что некоторые небезопасные языки могут иметь некоторые или даже все эти черты.

Примеры безопасных языков: Python, Java, безопасное подмножество C#.

Небезопасные языки определяют, что можно и что нельзя делать в программе, но обычно практически ничего не мешает программисту поступать неправильно. Программа, которая нарушает эти правила, называется некорректной программой. С языковой точки зрения такая программа не имеет смысла, и язык даже не пытается определить ее поведение, как это обычно практически невозможно сделать. С точки зрения C поведение такой программы не определено.

Примеры небезопасных языков: Ассемблер, С, С ++, Паскаль.

3. Аппаратное обеспечение небезопасно и, следовательно, должно быть запрограммировано с использованием небезопасного языка.

Большая часть оборудования ничего не делает для обеспечения безопасной среды. Существовали некоторые процессоры, которые использовали для прикрепления информации о типе к каждой ячейке памяти (см. Теговую архитектуру), но современные не делают этого, поскольку это усложняет оборудование, делая его медленнее, дороже и менее универсальным.

Тем не менее, предоставляются некоторые функции, позволяющие реализовать безопасные среды в небезопасной аппаратной среде, такие как защита памяти, отдельные адресные пространства и разделение режимов выполнения в пользовательском режиме и режиме ядра (также называемом режимом супервизора).

Ядро - это то, что работает на голом металле, и поэтому большая часть его должна быть написана на небезопасных языках, таких как C и Assembly. Другая причина - производительность - безопасные среды подразумевают огромные накладные расходы.

Микроядро и Монолитное ядро

Монолитное ядро ​​и его модули работают в едином общем адресном пространстве. А поскольку все обычно пишется на небезопасном языке, любая часть ядра может получить доступ (и повредить) память, которая принадлежит другой части ядра, из-за ошибок в коде. Небезопасная природа этой среды делает невозможным обнаружение или восстановление после этих сбоев и, что наиболее важно, прогнозирование поведения ядра после таких сбоев.

Микроядро - это попытка преодолеть это ограничение, перемещая различные части ядра в отдельные адресные пространства, эффективно изолируя их друг от друга, но обеспечивая безопасный способ связи друг с другом (обычно посредством передачи сообщений). Такое разделение создает безопасную среду, состоящую из нескольких небезопасных процессов, позволяя ядру восстанавливаться после сбоя некоторых его подсистем.

В то же время монолитное ядро ​​может запускать его части в отдельном адресном пространстве ( FUSE), в то время как ничто не мешает микроядру поддерживать модули, которые совместно используют адресное пространство с основной частью ядра.

Если большая часть ядра работает в одном адресном пространстве, оно считается монолитным ядром. Если большинство из них работает в отдельных адресных пространствах, такое ядро ​​считается микроядром. Если ядро ​​находится где-то посередине и активно использует оба подхода, у вас есть гибридное ядро.

Гибридное ядро

Концепция гибридного ядра подразумевает объединение лучшего из обоих миров и была изобретена Microsoft для увеличения продаж Windows NT в 90-х годах. Шутка! Но это почти правда. Каждая важная часть Windows NT работает в общем адресном пространстве, поэтому это еще один пример монолитного проектирования.

Многие люди используют этот термин при описании монолитного ядра, способного динамически загружать модули. Это связано с тем, что в прошлом монолитные ядра не поддерживали динамическую загрузку модулей и должны были перекомпилироваться при каждом добавлении модуля в ядро. Микроядро связано не с динамической загрузкой модуля, а с надежностью ядра, с его способностью восстанавливаться после сбоев его подсистем.


Ответ: Linux - это монолитное ядро.


Монолитное ядро может быть модульным и может динамически загружать модули. Микроядро, с другой стороны, должно быть модульным и должно иметь возможность динамически загружать модули - вся идея заключается в запуске их в отдельном адресном пространстве.


Микроядро - не единственный способ преодоления небезопасной природы монолитного ядра. Другой способ - написать монолитное ядро ​​на безопасном языке. Одна из проблем такого подхода заключается в том, что безопасная среда должна быть либо обеспечена аппаратными средствами (и будет очень ограниченной), либо должна быть реализована в программном обеспечении с использованием небезопасных языков. Реализация такой среды будет чрезвычайно сложной и, скорее всего, будет иметь много ошибок (подумайте обо всех ошибках, найденных в JVM).

Примером этого может служить экспериментальная ОС Singularity.

См. Этот предыдущий вопрос Stackru для получения дополнительной информации о вашем вопросе. Вкратце, звучит так, будто вам интересно...

... чтение модульной концепции, которая гласит, что новый модуль для драйвера может быть добавлен без перекомпиляции ядра, что противоречит моему предположению, что Linux использует монолитное ядро. монолитное ядро ​​работает в едином адресном пространстве и как единый процесс...

Эти два понятия ("модульное ядро" и "единое адресное пространство") на самом деле не противоречат друг другу. Вы можете собрать новый модуль ядра без перекомпиляции всего ядра Linux. Когда вы загружаете этот новый модуль ядра, он фактически загружается в то же адресное пространство, что и само работающее ядро. По ссылке выше...

Не путайте термин "модульное ядро" с чем-либо, кроме монолитного. Некоторые монолитные ядра могут быть скомпилированы для модульности (например, Linux), важно то, что модуль вставляется и запускается из того же пространства, которое обрабатывает функциональность ядра (пространство ядра).

Как вы обнаружили, существует несколько способов классификации ядер, и различные типы не обязательно являются взаимоисключающими.

Что ж, учитывая, что у меня может быть тест на это завтра, я смогу помочь тебе. Тем не менее, я все еще учусь, и хотя мой пост может содержать некоторые технические ошибки, он должен быть концептуально обоснованным

По сути, как вы понимаете, для ОС существуют разные типы ядер.

Монолитные ядра объединяют все свои системные функции и сервисы в одну гигантскую программу, занимая одно адресное пространство. Микроядра, с другой стороны, имеют минимальные системные программы и сервисы на микроядре. Большинство сервисов, которые ранее рассматривались как часть ядра (во время монолитной версии ядра), такие как планировщик процессов и т. Д., Теперь находятся в пользовательском пространстве и называются серверами. эти серверы обмениваются данными друг с другом через микроядро, используя межпроцессное взаимодействие, форму общения, устанавливаемую микроядром. Модульный подход основывается на этом, делая эти "серверы" динамически загружаемыми. Таким образом, можно динамически загружать определенный "сервер" (в ядре этого типа, называемом модулем) без необходимости пересобирать ядро.

Ядро Linux является монолитным ядром, но большинство разновидностей Linux, таких как Ubuntu и Solaris, используют гибридное ядро, то есть сочетание подхода монолитного и модульного ядра. Это довольно распространено, имеет различную структуру ядра, имеет разные плюсы и минусы, и для достижения баланса требуется гибридная структура.

Другие вопросы по тегам