Ядро Linux в комментариях

       

Процессы и потоки


Строго говоря, главной задачей операционной системы является создание среды для выполнения программ. По терминологии Unix выполняющаяся программа называется процессом. Ядро Linux, подобно ядру всех вариантов Unix, является многозадачным; оно может распределять время между несколькими процессами, создавая впечатление, будто все они выполняются одновременно. При этом, как и всегда, ядро регулирует доступ к ресурсам. А в данном случае ресурсом является время центрального процессора.

Традиционно процесс имеет единый контекст выполнения. Проще говоря, в ходе процесса одновременно выполняется только одно действие. В каждый данный момент времени можно точно сказать, какая часть кода выполняется. Но иногда было бы желательно, чтобы единый процесс одновременно выполнял более одного действия. Например, может возникнуть потребность, чтобы Web-браузер загружал и отображал Web-страницу, продолжая отслеживать, не щелкает ли пользователь по кнопке Stop. Запуск совершенно новой программы лишь для того, чтобы отслеживать состояние кнопки Stop — явное излишество, но Web-браузеру не всегда удобно делить свое время. В этом случае ему пришлось бы загрузить часть страницы, проверить состояние кнопки Stop, загрузить еще часть страницы, снова проверить состояние кнопки Stop и т.д.

Популярным решением этой проблемы является поток (thread). Концептуально, потоки — это отдельные контексты выполнения внутри одного и того же процесса. Проще говоря, они обеспечивают возможность единому процессу одновременно выполнять более одного действия, как если бы процесс был самостоятельной миниатюрной многозадачной операционной системой. Потоки внутри группы совместно используют все свои глобальные переменные и имеют одну и ту же кучу; таким образом, память, выделенная оператором malloc одному потоку внутри группы, доступна для чтения и записи другим потокам. Но при этом они имеют различные стеки (они не используют совместно локальные переменные) и могут выполняться одновременно в различных местах внутри кода процесса. Таким образом, Web-браузер может иметь один поток, занимающийся загрузкой и отображением страницы, пока другой поток следит за состоянием кнопки Stop и прерывает первый поток в случае щелчка по этой кнопке.


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

Содержание раздела