Другие примитивы синхронизации Программирование с использованием POSIX thread library.

Презентация:



Advertisements
Похожие презентации
POSIX Threads. Общая модель Программа Общая память Поток 1 CPU Поток 2 Поток N Потоки – наборы инструкций, исполняющиеся на CPU. Все потоки одной программы.
Advertisements

Система реального времени QNX/Neutrino (QNX6). QNX Микpоядеpная Cетевая Мyльтизадачная Многопользовательcкая.
Мутексы Программирование с использованием POSIX thread library.
POSIX Threads & OpenMP Общая память Сергей Петрович Нечаев, Сибирский Суперкомпьютерный центр.
Блокировки чтения-записи Введение Получение и сброс блокировки чтения-записи Атрибуты блокировки чтения-записи Реализация Отмена выполнения потоков Пример.
Атрибуты мутекса. pthread_mutexattr_t #include int pthread_mutexattr_init( pthread_mutexattr_t * attr); int pthread_mutexattr_destroy( pthread_mutexattr_t.
Семафоры-счетчики POSIX Программирование с использованием POSIX thread library.
POSIX Threads МО ВВС ИВМ и МГ СО РАН Городничев Максим Александрович.
ВСТРОЕННЫЕ ИНФОРМАЦИОННО- УПРАВЛЯЮЩИЕ СИСТЕМЫ РЕАЛЬНОГО ВРЕМЕНИ Лекция 5 Операционные системы реального времени Кафедра АСВК, Лаборатория Вычислительных.
Создание и завершение нитей Программирование с использованием POSIX thread library Иртегов Д.В. Учебное пособие подготовлено по заказу и при.
Многопоточное программирование Java Advanced. 2Georgiy Korneev Краткое содержание 1.Введение 2.Классические задачи многопоточного программирования 3.Атомарные.
Многопоточное программирование. Виды параллелизма. Общая память Распределенная память.
Посыпкин М.А. (С) Многопоточное программирование.
Параллельное программирование с использованием технологии OpenMP Аксёнов Сергей Владимирович к.т.н., доцент каф.ОСУ ТПУ Лекция 3 Томский политехнический.
Многопоточное программирование на Java Java Advanced.
Многопоточное программирование на Java Java Advanced.
СИСТЕМНЫЕ ВЫЗОВЫ ВВОДА И ВЫВОДА Системные вызовы и библиотеки Unix SVR4.
Управление процессами Синхронизация процессов и потоков.
Асинхронный ввод/вывод Системные вызовы и библиотеки Unix SVR4 Иртегов Д.В. ФФ/ФИТ НГУ Электронный лекционный курс подготовлен в рамках реализации Программы.
Основы операционных систем. Тема 6. Механизмы синхронизации.
Транксрипт:

Другие примитивы синхронизации Программирование с использованием POSIX thread library

Блокировки чтения/записи pthread_rwlock_init pthread_rwlock_rdlock pthread_rwlock_wrlock pthread_rwlock_unlock pthread_rwlock_destroy

Pthread_rwlock_init(3C) #include int pthread_rwlock_init( pthread_rwlock_t *restrict rwlock, const pthread_rwlockattr_t *restrict attr); pthread_rwlock_t rwlock=PTHREAD_RWLOCK_INITIALIZER; int pthread_rwlock_destroy( pthread_rwlock_t **rwlock);

pthread_rwlock_rdlock(3C) #include int pthread_rwlock_rdlock( pthread_rwlock_t *rwlock); int pthread_rwlock_tryrdlock( pthread_rwlock_t *rwlock);

pthread_rwlock_wrlock(3C) #include int pthread_rwlock_wrlock( pthread_rwlock_t *rwlock); int pthread_rwlock_trywrlock( pthread_rwlock_t *rwlock);

Свойства блокировок чтения/записи Несколько нитей могут одновременно держать одну и ту же блокировку на чтение Блокировка на чтение рекурсивна (одна нить может захватывать ее несколько раз) Блокировку на запись может держать только одна нить. При этом никто не может держать ту же блокировку на чтение. Блокировка на запись нерекурсивна

Условные переменные pthread_cond_init pthread_cond_wait pthread_cond_signal pthread_cond_broadcast pthread_cond_destroy

pthread_cond_init(3C) #include int pthread_cond_init( pthread_cond_t *restrict cond, const pthread_condattr_t *restrict attr); pthread_cond_t cond= PTHREAD_COND_INITIALIZER; int pthread_cond_destroy( pthread_cond_t *cond);

pthread_cond_wait(3C) #include int pthread_cond_wait( pthread_cond_t *restrict cond, pthread_mutex_t *restrict mutex); int pthread_cond_timedwait( pthread_cond_t *restrict cond, pthread_mutex_t *restrict mutex, const struct timespec *restrict abstime); /* Solaris only */ int pthread_cond_reltimedwait_np( pthread_cond_t *cond, pthread_mutex_t *mutex, const struct timespec *reltime);

Pthread_cond_signal(3C) #include int pthread_cond_signal( pthread_cond_t *cond); int pthread_cond_broadcast( pthread_cond_t *cond);

Что же такое условная переменная «Культурный» способ организации холостого цикла. Идея в том, что условная переменная защищает какой-то предикат (условие). Вызов pthread_cond_signal(3C)/broadcast означает, что это условие, возможно, изменилось Это не означает, что оно действительно изменилось Т.е. после пробуждения из wait предикат обязательно надо снова проверить. Это касается не только timedwait, но и простого wait Стандарт POSIX допускает ложные сработки, т.е. выход из cond_wait без вызова кем-либо signal

Еще про условную переменную Всегда применяется в паре с мутексом. Перед вызовом pthread_cond_wait(3C) мутекс должен быть захвачен При входе в wait мутекс освобождается, при пробуждении снова захватывается В соответствии с Solaris man, нельзя использовать одну и ту же переменную с разными мутексами (результат не определен) Мутекс должен защищать данные, используемые при вычислении предиката

Применение условной переменной Задача производитель-потребитель –Если решать только на мутексах, нужно 3 мутекса и холостой цикл на входе –Решается с одним мутексом и одной условной переменной (т.е. условная переменная ~ эквивалентна 2 мутексам)

Открытие файлов Многопоточная программа открывает много файлов. Например, задача «Многопоточный cp –R» Если ручки файлов кончаются, надо подождать, пока кто-то закроет файл.

Открытие файлов - пример pthread_mutex_lock(&fileopen_mutex); do { srcfile=open(srcpathname, O_RDONLY, 0); if (srcfile < 0 && errno!=EMFILE) { perror(dstpathname); pthread_mutex_unlock(&fileopen_mutex); return NULL; } if (srcfile>0) { dstfile=open(dstpathname, O_WRONLY | O_CREAT, stat.st_mode); if (dstfile < 0 && errno != EMFILE) { perror(dstpathname); close(srcfile); pthread_cond_signal(&fileopen_cond); pthread_mutex_unlock(&fileopen_mutex); return NULL; } if (srcfile

Атомарный захват нескольких мутексов void get_forks (int phil, int fork1, int fork2) { int res; pthread_mutex_lock(&getting_forks_mx); do { if (res=pthread_mutex_trylock(&forks[fork1])) { res=pthread_mutex_trylock(&forks[fork2]); if (res) pthread_mutex_unlock(&forks[fork1]); } if (res) pthread_cond_wait(&getting_forks_cond, &getting_forks_mx); } while(res); pthread_mutex_unlock(&getting_forks_mx); } void down_forks (int f1, int f2) { pthread_mutex_lock(&getting_forks_mx); pthread_mutex_unlock (&forks[f1]); pthread_mutex_unlock (&forks[f2]); pthread_cond_broadcast(&getting_forks_cond); pthread_mutex_unlock(&getting_forks_mx); }