Скачиваний:
90
Добавлен:
12.05.2015
Размер:
913.92 Кб
Скачать

14.9. Принудительное завершение потоков

Два атрибута потоков, которые не входят в состав структуры pthread_attr_t, – это атрибут возможности принудительного завершения потока и атрибут типа принудительного завершения. Эти атрибуты определяют реакцию потока в ответ на вызов функции pthread_cancel (раздел 14.5).

Атрибут возможности принудительного завершения потока может иметь значение PTHREAD_CANCEL_ENABLE или PTHREAD_CANCEL_DISABLE. Поток может изменить значение этого атрибута с помощью вызова функции pthread_setcancelstate.

#include <pthread.h>

int pthread_setcancelstate (int state, int *oldstate);

/* функция возвращает 0 в случае успеха, код ошибки – в случае неудачи */

Функция pthread_setcancelstate производит одну атомарную операцию, изменяя значение атрибута возможности принудительного завершения потока в соответствии со значением аргумента state, и сохраняет прежнее значение атрибута по адресу, который передается в аргументе oldstate.

В разделе 14.5 мы уже говорили, что функция pthread_cancel не ждет, пока поток завершит работу. По умолчанию поток продолжает работу после вызова этой функции, пока не достигнет точки выхода. Точка выхода – это место в программе, где поток может обнаружить запрос на принудительное завершение и откликнуться на него. Некоторые из функций, определенные стандартом Posix.1 как точки выхода, перечислены в табл. 14.3.

Таблица 14.3

Некоторые точки выхода, определенные стандартом Posix.1

accept

close

connect

creat

fsync

getmsg

msgrcv

msgsnd

open

poll

putmsg

read

recv

recvfrom

recvmsg

select

sem_wait

send

sendmsg

sendto

sigpause

sigsuspend

sigwait

sleep

system

wait

waitpid

write

В момент запуска потока значение его атрибута возможности принудительного завершения устанавливается равным PTHREAD_CANCEL_ENABLE. Если поток установит значение этого атрибута равным PTHREAD_CANCEL_DISABLE, то вызов функции pthread_cancel не приведет к завершению потока. Вместо этого запрос на принудительное завершение потока становится в режим ожидания. Когда поток опять разрешит принудительное завершение, то он откликнется на ожидающий запрос в ближайшей точке выхода.

Если поток не обращается к функциям, определенным стандартом Posix.1 как точки выхода, достаточно продолжительное время, то можно определить свою собственную точку выхода с помощью функции pthread_testcancel.

#include <pthread.h>

void pthread_testcancel (void);

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

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

#include <pthread.h>

int pthread_setcanceltype (int type, int *oldtype);

/* функция возвращает 0 в случае успеха, код ошибки – в случае неудачи */

Аргумент type может содержать значение PTHREAD_CANCEL_DEFERRED или PTHREAD_CANCEL_ASYNCHRONOUS. Функция pthread_setcanceltype устанавливает значение атрибута в соответствии с аргументом type и возвращает предыдущее значение атрибута в переменной, адрес которой содержит аргумент oldtype.

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

Соседние файлы в папке Chapter.4