Студопедия

Главная страница Случайная страница

Разделы сайта

АвтомобилиАстрономияБиологияГеографияДом и садДругие языкиДругоеИнформатикаИсторияКультураЛитератураЛогикаМатематикаМедицинаМеталлургияМеханикаОбразованиеОхрана трудаПедагогикаПолитикаПравоПсихологияРелигияРиторикаСоциологияСпортСтроительствоТехнологияТуризмФизикаФилософияФинансыХимияЧерчениеЭкологияЭкономикаЭлектроника






Обработчики завершения






Есть несколько способов блокировки файла. Конкретный выбор зависит, в частности, от того, как оставшаяся часть программы будет использовать блокировку. Нужно также учесть проблемы эффективности и мобильности программы. Далее будут описаны два метода: один

использует системный вызов fcntl(2), другой – библиотечную функцию lockf(3C)(удовлетворяющую стандарту /usr/group).

 

Блокировка всего файла на самом деле является частным случаем блокировки сегмента, поскольку и концепция, и результат блокировки одинаковы. Файл блокируется начиная с байта со смещением ноль и кончая максимально возможным размером файла, что нужно для предотвращения блокировок каких-либо сегментов файла. В этом случае значение длины блокировки устанавливается в ноль. Далее приведен фрагмент исходного текста, использующего для достижения цели системный вызов fcntl(2):

 

#include < fcntl.h>

...

#define MAX_TRY 10

int try;

struct flock lck;

try = 0;

/* Заполним структуру, нужную для блокировки сегмента.

Адрес структуры передается системному вызову fcntl */

lck.l_type = F_WRLCK; /* Блокировка на запись */

lck.l_whence = 0; /* Смещение от начала будет равно l_start */

lck.l_start = 0L; /* Блокировка от начала файла */

lck.l_len = 0L; /* и до конца */

/* Делаем не более MAX_TRY попыток блокировки */

while (fcntl (fd, F_SETLK, & lck) < 0) {

if (errno == EAGAIN || errno == EACCES) {

/* Могут быть и другие ошибки, при которых

надо повторить попытку */

if (++try < MAX_TRY) (

(void) sleep (2);

continue;

}

(void) fprintf (stderr, " Файл занят\n");

return;

}

perror(" fcntl");

exit(2);

}

...

Приведенная часть исходного текста пытается заблокировать файл. Попытки повторяются несколько раз до тех пор, пока не случится одно из событий:

Файл удалось заблокировать.

Возникла ошибка.

Попытки прекращены из-за того, что их количество превысило MAX_TRY.

 

Чтобы выполнить эту же задачу, используя функцию lockf(3C), исходный текст должен иметь следующий вид:

 

#include < unistd.h>

#define MAX_TRY 10

int try;

try = 0;

/* Устанавливаем указатель текущей позиции в начало файла */

lseek (fd, OL, O);

/* Делаем не более MAX_TRY попыток блокировки */

while (lockf (fd, F_TLOCK, 0L) < 0) {

if (errno == EAGAIN || errno == EACCES) {

/* Могут быть и другие ошибки, при которых

надо повторить попытку */

if (++try < MAX_TRY) {

(void) sleep (2);

continue;

}

(void) fprintf (stderr, " Файл занят\n");

return;

}

perror(" lockf");

exit(2);

}

...

Надо заметить, что пример с использованием lockf(3C) выглядит проще, однако пример с fcntl(2) демонстрирует дополнительную гибкость. При использовании fcntl(2) можно установить тип блокировки и начало блокируемого сегмента просто путем присваивания нужных значений компонентам структуры. В случае lockf(3C) просто устанавливается блокировка на запись (монопольная); для того, чтобы указать начало блокируемого сегмента, нужен дополнительный системный вызов [lseek(2)].

 






© 2023 :: MyLektsii.ru :: Мои Лекции
Все материалы представленные на сайте исключительно с целью ознакомления читателями и не преследуют коммерческих целей или нарушение авторских прав.
Копирование текстов разрешено только с указанием индексируемой ссылки на источник.