Управление потоками

Управление потоками

Вероятно, вы не будете удивлены, узнав о том, что у потоков, как и у любого другого объекта Windows, имеются дескрипторы и что для создания потоков, выполняющихся в адресном пространстве вызывающего процесса, предусмотрен системный вызов CreateThread. Как и в случае процессов, мы будем говорить иногда о "родительских" и "дочерних" потоках, хотя ОС не делает в этом отношении никаких различий. Системный вызов CreateThread предъявляет ряд специфических требований:

• Укажите начальный адрес потока в коде процесса.

• Укажите размер стека, и необходимое пространство стека будет выделено из виртуального адресного пространства процесса. Размер стека по умолчанию равен размеру стека основного потока (обычно 1 Мбайт). Первоначально для стека отводится одна страница (см. главу 5). Новые страницы стека выделяются по мере надобности до тех пор, пока стек не достигнет своего максимального размера, поэтому не сможет больше расти.

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

• Функция возвращает значение идентификатора (ID) и дескриптор потока.

В случае ошибки возвращаемое значение равно NULL.

HANDLE CreateThread(LPSECURITY_ATTRIBUTES lpsa, DWORD dwStackSize, LPTHREAD_START_ROUTINE lpStartAddr, LPVOID lpThreadParm, DWORD dwCreationFlags, LPDWORD lpThreadId) 

Параметры

lpsa — указатель на уже хорошо знакомую структуру атрибутов защиты.

dwStackSize — размер стека нового потока в байтах. Значению 0 этого параметра соответствует размер стека по умолчанию, равный размеру стека основного потока.

lpStartAddr — указатель на функцию (принадлежащую контексту процесса), которая должна выполняться. Эта функция принимает единственный аргумент в виде указателя и возвращает 32-битовый код завершения. Этот аргумент может интерпретироваться потоком либо как переменная типа DWORD, либо как указатель. Функция потока (ThreadFunc) имеет следующую сигнатуру: 

DWORD WINAPI ThreadFunc(LPVOID) 

lpThreadParm — указатель, передаваемый потоку в качестве аргумента, который обычно интерпретируется потоком как указатель на структуру аргумента.

dwCreationFlags — если значение этого параметра установлено равным 0, то поток запускается сразу же после вызова функции CreateThread. Установка значения CREATE_SUSPENDED приведет к запуску потока в приостановленном состоянии, из которого поток может быть переведен в состояние готовности путем вызова функции ResumeThread.

lpThreadId — указатель на переменную типа DWORD, которая получает идентификатор нового потока; в Windows 9x и Windows NT 3.51 значение NULL для этого параметра устанавливать нельзя.

Любой поток процесса может сама завершить свое выполнение, вызвав функцию ExitThread, однако более обычным способом самостоятельного завершения потока является возврата из функции потока с использованием кода завершения в качестве возвращаемого значения. По завершении выполнения потока память, занимаемая ее стеком, освобождается. В случае если поток был создан в библиотеке DLL, будет вызвана соответствующая точка входа DllMain (глава 4) с указанием флага DLL_THREAD_DETACH в качестве "причины" этого вызова. 

VOID ExitThread(DWORD dwExitCode) 

Когда завершается выполнение последнего потока, завершается и выполнение самого процесса.

Выполнение потока также может быть завершено другим потоком с помощью функции TerminateThread, однако освобождения ресурсов потока при этом не происходит, обработчики завершения не выполняются и уведомления библиотекам DLL не посылаются. Лучше всего, когда поток сам завершает свое выполнение; применять для этого функцию TerminateThread крайне нежелательно. Функции TerminateThread присущи те же недостатки, что и функции TerminateProcess.

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

BOOL GetExitCodeThread(HANDLE hThread, LPDWORD lpExitCode) 

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

Поделитесь на страничке

Следующая глава >

Похожие главы из других книг

8.4. Управление процессами

Из книги Linux для пользователя автора Костромин Виктор Алексеевич

8.4. Управление процессами Первым делом научимся определять, какие процессы в системе запущены. Для этого в Linux (как и во всех UNIX-системах) имеется команда ps. Если ее запустить без всяких параметров, то она выдает список процессов, запущенных в текущей сессии. Если вы хотите


8.5. Управление пользователями

Из книги Linux-сервер своими руками автора Колисниченко Денис Николаевич

8.5. Управление пользователями Задача управления пользователями имеет большое значение для истинно многопользовательских систем. Для персонального компьютера, о котором идет речь в этой книге, эта задача не так актуальна. Тем не менее, некоторые вопросы отразить


8.6. Управление ресурсами

Из книги UNIX: взаимодействие процессов автора Стивенс Уильям Ричард

8.6. Управление ресурсами В этом разделе мы рассмотрим только один аспект управления ресурсами: как сэкономить тот или иной ресурс, точнее, как поступить в случае, если какого-то ресурса недостаточно. Основными ресурсами компьютера являются память и дисковое пространство.


4.15.3. Управление стримером

Из книги Системное программирование в среде Windows автора Харт Джонсон М

4.15.3. Управление стримером Управление стримером выполняет программа int. Она входит в состав пакета mt-st, который обычно входит в состав дистрибутива. Эта программа точно есть в дистрибутивах Red Hat и Mandrake Linux. Программа mt использует устройство /dev/nftape, которое является ссылкой


5.8. Управление протоколированием

Из книги Linux: Полное руководство автора Колисниченко Денис Николаевич

5.8. Управление протоколированием Этот раздел посвящен демону syslogd, а также управлению протоколированием сообщений системы и ядра с помощью этого демона. Прежде всего следует отметить, что демон находится в пакете sysklogd (если вы, конечно, используете Red Hat-совместимую


15.5.3. Управление кэшем

Из книги Программирование для Linux. Профессиональный подход автора Митчелл Марк

15.5.3. Управление кэшем cache_swap_high числоПри достижении этого уровня заполнения кэша (в процентном соотношении) начинается ускоренный процесс удаления старых объектов. cache_swap_low 90Процесс удаления прекращается при достижении этого уровня. maximum_object_size 4096 KBМаксимальный размер


Автоматическое управление потоками сервера

Из книги UNIX: разработка сетевых приложений автора Стивенс Уильям Ричард

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


Автоматическое управление потоками сервера: несколько процедур

Из книги автора

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


Б.2. Основные функции для работы с потоками: создание и завершение

Из книги автора

Б.2. Основные функции для работы с потоками: создание и завершение В этом разделе мы опишем пять основных функций для работы с потоками.Функция pthread_createПри запуске пpoгрaммы вызовом exec создается единственный поток, называемый начальным потоком, или главным (initial thread).


Дополнительные функции управления потоками

Из книги автора

Дополнительные функции управления потоками Несмотря на то что функций управления потоками, которые мы выше обсуждали, вполне достаточно для большинства случаев, в том числе и для примеров, приведенных в этой книге, в Windows XP и Windows Server 2003 были введены две дополнительные


Дросселирование семафора для уменьшения состязательности между потоками

Из книги автора

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


18.5.3. Управление кэшем

Из книги автора

18.5.3. Управление кэшем За управление кэшем отвечают следующие директивы:? cache_mem <число> — задает размер оперативной памяти, отводимой под кэш. Размер этот указывается в байтах, килобайтах, мегабайтах (MB) или гигабайтах (GB). По умолчанию используется значение 8 MB;? cache_dir


4.1.3. Значения, возвращаемые потоками

Из книги автора

4.1.3. Значения, возвращаемые потоками Если второй аргумент функции pthread_join() не равен NULL, то в него помещается значение, возвращаемое потоком. Как и потоковый аргумент, это значение имеет тип void*. Если поток возвращает обычное число типа int, его можно свободно привести к типу


26.2. Основные функции для работы с потоками: создание и завершение потоков

Из книги автора

26.2. Основные функции для работы с потоками: создание и завершение потоков В этом разделе мы рассматриваем пять основных функций для работы с потоками, а в следующих двух разделах мы используем эти функции для написания потоковой модификации клиента и сервера