[ Страница назад | Страница вперед | Содержание | Индекс | Библиотека | Юридическая информация | Поиск ]

Программирование: Разработка и отладка программ


Создание нитей

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

Более подробно создание нитей описывается в следующих разделах:

Объект атрибутов нити

Атрибуты нити хранятся в объекте со скрытой реализацией - объекте атрибутов нити, который используется при создании нити. Этот объект хранит набор атрибутов, зависящий от реализации опций POSIX. Доступ к нему осуществляется через переменную типа pthread_attr_t. В AIX тип данных pthread_attr_t обозначает указатель; в других системах это может быть структура или иной тип данных.

Создание и удаление объекта атрибутов нити

Объект атрибутов нити инициализируется значениями по умолчанию с помощью процедуры pthread_attr_init. Для работы с атрибутами предназначены специальные функции. Объект атрибутов нити удаляется с помощью процедуры pthread_attr_destroy. Эта процедура может освобождать память, выделенную процедурой pthread_attr_init, в зависимости от реализации библиотеки нитей.

В приведенном ниже примере объект атрибутов нити создается и инициализируется со значениями по умолчанию, затем используется при создании нити и удаляется:

pthread_attr_t attributes;
                /* создается объект атрибутов */
...
if (!pthread_attr_init(&attributes)) {
                /* объект атрибутов инициализируется */
        ...
                /* работа с объектом атрибутов */
        ...
        pthread_attr_destroy(&attributes);
                /* удаление объекта атрибутов */
}

Один объект атрибутов может применяться для создания нескольких нитей. Между вызовами операции создания нитей атрибуты объекта можно изменить. После создания нитей объект атрибутов можно удалить - эта операция не повлияет на работу созданных нитей.

Атрибут detachstate

Описанный ниже атрибут определен всегда.

Detachstate Определяет состояние запуска нити.

Значение атрибута может быть считать процедурой pthread_attr_getdetachstate и установить процедурой pthread_attr_setdetachstate. Атрибут может принимать значение одной из следующих констант:

PTHREAD_CREATE_DETACHED Указывает, что нить будет создана в автономном режиме.
PTHREAD_CREATE_JOINABLE Указывает, что нить будет создана в подключаемом режиме.

Значение по умолчанию - PTHREAD_CREATE_JOINABLE.

Если нить создается в подключаемом состоянии, для нее должна быть вызвана процедура pthread_join (Вызов функции pthread_join). В противном случае, в системе может оказаться недостаточно памяти для создания новой нити, так как каждая нить занимает относительно большой объем.

Другие атрибуты

Ниже перечислены другие атрибуты, определенные в AIX. Они предназначены для более точного управления нитями, и для их применения могут потребоваться специальные права доступа. Большинство программ нормально работают со значениями по умолчанию.

Область действия Задает область действия нити.
Inheritsched Задает параметры наследования атрибутов планировщика нити.
Schedparam Задает параметры планировщика для нити.
Schedpolicy Задает стратегию планирования для нити.

Применение этих атрибутов описано в разделе Атрибуты планировщика.

Stacksize Задает размер стека нити.
Stackaddr Указывает адрес стека нити.
Guardsize Определяет размер контрольной области для стека нити.

Применение этих атрибутов описано в разделе Атрибуты стека.

Создание нити

Для создания нити предназначена процедура pthread_create. Эта процедура создает новую нить и запускает ее.

Применение объекта атрибутов нити

В вызове процедуры pthread_create можно указать объект атрибутов нити. Если задан указатель NULL, нить создается со значением атрибутов по умолчанию. Следовательно, фрагмент кода:

pthread_t thread;
pthread_attr_t attr;
...
pthread_attr_init(&attr);
pthread_create(&thread, &attr, init_routine, NULL);
pthread_attr_destroy(&attr);

эквивалентен следующему:

pthread_t thread;
...
pthread_create(&thread, NULL, init_routine, NULL);

Процедура точки входа

В вызове процедуры pthread_create должна указываться процедура точки входа. Эта процедура, описанная в программе, аналогична функции main процесса. Она является первой процедурой, запускаемой в новой нити. При выходе из этой процедуры нить автоматически завершается.

Процедура точки входа имеет один параметр - указатель типа void, который задается при вызове pthread_create. Он может применяться для передачи указателя на некоторые данные - например, на строку или структуру. Создающая (вызывающая процедуру pthread_create) и создаваемая нить должны согласовать фактический тип этого указателя.

Процедура точки входа возвращает указатель типа void. После завершения нити этот указатель хранится библиотекой нитей до момента удаления нити. Дополнительная информация о работе с этим указателем приведена в разделе Обзор синхронизации.

Возвращаемая информация

Процедура pthread_create возвращает идентификатор новой нити. Вызывающая нить может использовать этот идентификатор для выполнения различных действий с созданной нитью.

В зависимости от заданных для нитей параметров планирования, новая нить может начать работу до того, как процедура pthread_create вернет значение вызывающей программе. Может оказаться, что в момент завершения работы функции pthread_create новая нить уже будет завершена. В этом случае процедура pthread_create возвращает в параметре thread неправильный идентификатор. Поэтому при работе с процедурами библиотеки нитей, которым передается идентификатор нити в качестве параметра, необходимо сравнивать результаты операций с кодом ошибки ESRCH.

Если процедура pthread_create не может создать нить, то параметр thread содержит недопустимый идентификатор, а процедура возвращает код ошибки.

Работа с идентификаторами нитей

Идентификатор новой нити передается вызывающей нити в параметре thread. Идентификатор текущей нити можно получить с помощью процедуры pthread_self.

Идентификатор нити - это объект со скрытой реализацией типа pthread_t. В AIX pthread_t совпадает с типом int. В других системах он может быть структурой, указателем или другим типом.

Для повышения переносимости программ, использующих библиотеку нитей, ИД нити должен всегда обрабатываться как объект со скрытой реализацией. По этой причине сравнение идентификаторов нитей должно выполняться с помощью процедуры pthread_equal. Не используйте оператор сравнения C (==), так как тип данных pthread_t может отличаться от арифметического типа данных или указателя.

Простая многонитевая программа

Ниже приведено краткое описание простой многонитевой программы. Она выводит приветствие на английском и французском языках на 5 секунд. Эта программа должна быть откомпилирована с опцией cc_r или xlc_r. Дополнительная информация о компиляции многонитевых программ приведена в разделе Создание программ с несколькими нитями.

#include <pthread.h>    /* первый включаемый файл - pthread.h */
#include <stdio.h>      /* поддержка функции printf() */
#include <unistd.h>     /* поддержка функции sleep()          */

void *Thread(void *string)
{ 
      while (1) 
              printf("%s\n", (char *)string); 
      pthread_exit(NULL);
}

int main()
{
        char *e_str = "Hello!";
        char *f_str = "Bonjour !";
 
        pthread_t e_th;
        pthread_t f_th;
 
        int rc;
 
        rc = pthread_create(&e_th, NULL, Thread, (void *)e_str);
        if (rc)
                exit(-1);
        rc = pthread_create(&f_th, NULL, Thread, (void *)f_str);
        if (rc)
                exit(-1);
        sleep(5);
 
        /* Обычно процедура exit не используется.
           Объяснение приведено ниже. */
        exit(0);
}

Исходная нить (в которой выполняется функция main) создает две нити. Обе нити используют одну процедуру точки входа (Thread), но с разными параметрами. В качестве параметра передается указатель на выводимую строку.

Связанная информация

Основные сведения о нитях

Обзор основных операций с нитями

Завершение работы нитей

Список основных функций работы с нитями

Необязательные компоненты библиотеки работы с нитями


[ Страница назад | Страница вперед | Содержание | Индекс | Библиотека | Юридическая информация | Поиск ]