Книга: UNIX: взаимодействие процессов

Пример

Пример

Вернемся к нашему примеру из листинга 9.2 и перепишем функции my_lock и my_unlock из листинга 9.1 так, чтобы воспользоваться блокировкой записей Posix. Текст этих функций приведен в листинге 9.3.

Листинг 9.3. Блокировка записей fcntl по стандарту Posix

//lock/lockfcntl.c
1  #include "unpipc.h"
2  void
3  my_lock(int fd)
4  {
5   struct flock lock;
6   lock.l_type = F_WRLCK;
7   lock.l_whence = SEEK_SET;
8   lock.l_start = 0;
9   lock.l_len = 0; /* блокирование всего файла на запись */
10  Fcntl(fd, F_SETLKW, &lock);
11 }
12 void
13 my_unlock(int fd)
14 {
15  struct flock lock;
16  lock.l_type = F_UNLCK;
17  lock.l_whence = SEEK_SET;
18  lock.l_start = 0;
19  lock.l_len = 0; /* разблокирование всего файла */
20  Fcntl(fd. F_SETLK, &lock);
21 }

Обратите внимание, что мы устанавливаем блокировку на запись, что гарантирует единственность изменяющего данные процесса (см. упражнение 9.4). При получении блокировки мы используем команду F_SETLKW, чтобы приостановить выполнение процесса при невозможности установки блокировки.

ПРИМЕЧАНИЕ

Зная определение структуры flock, приведенное выше, мы могли бы проинициализировать структуру my_lock как

static struct flock lock = { F_WRLCK, SEEK_SET, 0, 0, 0 };

но это неверно. Posix определяет только обязательные поля структуры, а реализации могут менять их порядок и добавлять к ним дополнительные.

Мы не приводим результат работы пpoгрaммы, но она, судя по всему, работает правильно. Выполнение этой программы не дает возможности утверждать, что в ней нет ошибок. Если результат оказывается неправильным, то можно сказать с уверенностью, что что-то не так. Но успешное выполнение программы еще ни о чем не говорит. Ядро могло выполнить сначала одну программу, затем другую, и если они не выполнялись параллельно, мы не имеем возможности увидеть ошибку. Увеличить шансы обнаружения ошибки можно, изменив функцию main таким образом, чтобы последовательный номер увеличивался 10000 раз, и запустив 20 экземпляров программы одновременно. Если начальное значение последовательного номера в файле было 1, мы можем ожидать, что после завершения работы всех этих процессов мы увидим в файле число 200001.

Оглавление книги


Генерация: 0.093. Запросов К БД/Cache: 0 / 0
поделиться
Вверх Вниз