Les verous de fichiers
Mécanismes de contrôle d'accès concurrents à un fichier, les verrous sont d'une grande utilité dans les applications de gestion et dans l'élaboration de bases de données partagées. Les verrous sont rattachés aux inoeuds. Ainsi toutes les ouvertures d'un même fichier, et à fortiori tous les descripteurs sur ces ouvertures, voient le verrou. La protection réalisée par le verrou a donc lieu sur le fichier physique. Un verrou est la propriété d'un seul processus, et seul le processus propriétaire du verrou peut le modifier ou l'enlever, attention le verrou ne protège pas contre les accès du processus propriétaire
Caractéristiques d'un verrou
Les verrous sont définis par deux caractéristiques
- La portée : ensemble de positions du fichier auxquelles le verrou
s'applique. Cet ensemble est un intervalle, soit une portion de fichier
[position1, position2]
soit jusqu'à la fin du fichier[position1, fin de fichier[
dans ce dernier cas si le fichier augmente, le verrou protège les nouvelles positions - Le type : qui décrit les possibilités de cohabitation des différents verrous
Le mode opératoire des verrous
Le mode opératoire joue sur le comportement des primitives read
et write
.
Les verrous d'un fichier sont soit consultatifs soit impératifs. Dans le premier
mode, la présence d'un verrou n'est testée qu'à la pose d'un verrou, la pose
sera refusée s'il existe un verrou de portée non disjointe et que l'un des deux
verrous est exclusif. Dans le second mode, la présence de verrous est testée
pour la pose mais aussi pour les appels systèmes read
et write
. Dans le mode
consultatif, les verrous n'ont d'effet que sur les processus jouant
effectivement le jeu, c'est à dire, posant des verrous sur les zones du fichiers
sur lesquels ils veulent réaliser une lecture (verrou partagé) ou une écriture
(verrou exclusif).
Dans le mode impératif, les verrous ont un impact sur les lectures / écritures de tous les processus :
- sur les verrous de type partagé, toute tentative d'écriture par un autre processus est bloquée
- sur les verrous de type exclusif, toute tentative de lecture ou d'écriture par un autre processus est bloquée
Pour rendre l'utilisation impérative il faut sous linux monter le disque avec
l'option -o mand
. Puis il faut utiliser la commande chmod
pour positionner
le SETGID bit
Manipulation des verrous
La structure de verrou flock
:
struct flock{
short l_type; //F_RDLCK (verrou partagé), F_WRLCK (verrou exclusif), F_UNCLK (déverrouillage)
short l_whence; //SEEK_SET, SEEK_CUR, SEEK_END
off_t l_start; //position relative à l_whence
off_t l_len; //longueur de l'intervalle
pid_t l_pid; //PID du processus propriétaire
};
Les manipulations de verrous se font avec la primitive fcntl
, c'est à dire par
le biais d'un descripteur. Pour poser un verrou partagé, ce descripteur doit
pointer sur une ouverture en lecture. De même, il faut un descripteur sur une
ouverture en écriture pour un verrou de type exclusif
Pour décrire la portée du verrou que l'on veut poser, on utilise la même syntaxe
que pour la primitive lseek
, le début de l'intervalle est whence+l_start
La longueur du verrou est définie par le champ l_len
. Si cette valeur est
nulle, le verrou va jusqu'à la fin du fichier. Le champ l_pid
contient le pid
du processus propriétaire du verrou, ce champ est rempli par fcntl
dans le cas
d'un appel consultatif (F_GETLK
).
Utilisation de fcntl
pour manipuler les verrous
#include <sys/types.h>
#include <unistd.h>
#include <fcntl.h>
int fcntl(int desc, int commande, struct flock *verrou);
Trois commandes sont possible :
F_SETLK
pose non bloquanteF_SETLKW
pose bloquante (Wait)F_GETLK
test d'existence d'un verrou incompatible avec le verrou passé en paramètre