MLOCK(2)

NOM
mlock, munlock, mlockall, munlockall - Vérouiller et dévérouiller la mémoire

SYNOPSIS
#include <sys/mman.h>

int mlock(const void *addr, size_t len);

int munlock(const void *addr, size_t len);

int mlockall(int flags);

int munlockall(void);

DESCRIPTION
mlockall() et mlock() verrouillent respectivement tout ou partie de l'espace mémoire virtuelle du processus appelant dans la RAM, évitant que cette mémoire ne soit paginée dans l'espace swap. munlockall() et munlock() effectuent l'opération inverse, déverrouillant respectivement tout ou partie de l'espace mémoire virtuelle du processus appelant. Ainsi, les pages se trouvant dans l'espace mémoire virtuelle spécifié pourront être swappées si le gestionnaire de mémoire du noyau le juge nécessaire.

  mlock() et munlock()
mlock() verrouille les pages pour la portion de mémoire débutant à l'adresse addr et continuant sur len octets. Toutes les pages qui contiennent une partie de l'intervalle d'adresse spécifié sont garanties de résider en RAM lorsque l'appel s'achève avec succès. Il est garanti que ces pages restent en RAM jusqu'à ce qu'elles soient déverrouillées. munlock() déverrouille les pages dans la portion de mémoire débutant à l'adresse addr et continuant sur len octets. Après cet appel, toutes les pages qui contiennent une partie de l'espace mémoire spécifié peuvent à nouveau être déplacées vers l'espace swap externe par le noyau.

  mlockall() et munlockall()
mlockall() verrouille toutes les pages situées dans l'espace d'adresse du processus appelant. Cela inclut les pages de code et de données, le segment de pile, les bibliothèques partagées, les données noyau de l'espace utilisateur, la mémoire partagée et les fichiers mappés en mémoire. Toutes les pages mappées sont garanties de résider en RAM lorsque l'appel s'achève avec succès. Il est garanti que ces pages restent en RAM jusqu'à ce qu'elles soient déverrouillées. L'argument flags est contruit par un OU bit à bit de l'une ou plusieurs des constantes suivantes :

MCL_CURRENT
    verrouiller toutes les pages qui sont actuellement mappées dans l'espace d'adresse du processus.

MCL_FUTURE
    Verrouiller toutes les pages qui seront mappées plus tard dans l'espace d'adresse du processus. Cela peut être, par exemple, de nouvelles pages rendues nécessaires par l'accroissement du tas et de la pile aussi bien que pour des fichiers mappés en mémoire ou des régions de mémoires partagées.

Si MCL_FUTURE a été spécifiée, un appel système ultérieur (par exemple : mmap(2), sbrk(2), malloc(3)), peut échouer s'il fait que le nombre d'octets verrouillés excède le maximum autorisé (voir plus loin). Dans les mêmes circonstances, un accroissement de la pile peut échouer de la même manière : le noyau refusera l'extension de la pile et délivrera un signal SIGSEGV au processus. munlockall() déverrouille toutes les pages mappées dans l'espace d'adresse du processus appelant.

VALEUR RENVOYÉE
S'ils réussissent, ces appels renvoient 0 ; s'ils échouent, ils renvoient -1 et errno contient le code d'erreur.

ERREURS

ENOMEM
    (Linux 2.6.9 et suivants) L'appelant a une limite de ressources logicielles RLIMIT_MEMLOCK non nulle mais a essayé de verrouiller plus de mémoire que la limite ne lui permettait. Cette limite ne s'applique pas si le processus est privilégié (CAP_IPC_LOCK).

ENOMEM
    (Linux 2.4 et précédents) Le processus appelant a essayé de verouillé plus de la moitié de la RAM.

EPERM
    (Linux 2.6.9 et suivants) Le processus appelant n'est pas privilégié (CAP_IPC_LOCK) et sa limite des ressources logicielles RLIMIT_MEMLOCK est nulle.

EPERM
    (Linux 2.6.8 et précédents) Le processus appelant n'a pas les privilèges suffisants pour appeler munlockall(). Sous Linux, la capacité CAP_IPC_LOCK est nécessaire.

Pour mlock() et munlock() :

EINVAL
    len est négatif.

EINVAL
    (Pas sous Linux) addr n'est pas un multiple de la taille de page.

ENOMEM
    Une partie des adresses incluses dans la zone désirée ne correspond pas à une page de l'espace d'adressage accessible du processus.

Pour mlockall() :

EINVAL
    Les flags spécifiés sont inconnus.

Pour munlockall() :

EPERM
    (Linux 2.6.8 et précédents) L'appelant n'est pas privilégié (CAP_IPC_LOCK).

CONFORMITÉ
POSIX.1-2001, SVr4.

DISPONIBILITÉ
Sur les systèmes POSIX sur lesquels mlock() et munlock() sont disponibles, _POSIX_MEMLOCK_RANGE est définie dans <unistd.h> et le nombre d'octets par page peut être déterminé par la constante PAGESIZE (si elle est définie) de <limits.h> ou par un appel à sysconf(_SC_PAGESIZE). Sur les systèmes POSIX sur lesquels mlockall() et munlockall() sont disponibles, _POSIX_MEMLOCK est définie dans <unistd.h> à une valeur supérieure à 0. (Voir aussi sysconf(3).)

NOTES
Il y a deux domaines principaux d'applications au verrouillage de pages : les algorithmes en temps réel, et le traitement de données confidentielles. Les applications temps réel réclament un comportement temporel déterministe, et la pagination est, avec l'ordonnancement, une cause majeure de délais imprévus. Ces algorithmes basculent habituellement sur un ordonnancement temps réel avec sched_setscheduler(2). Les logiciels de cryptographie manipulent souvent quelques octets hautement confidentiels, comme des mots de passe ou des clés privées. À cause de la pagination, ces données secrètes risquent d'être transférées sur un support physique où elles pourraient être lues par un ennemi longtemps après que le logiciel se soit terminé. (Soyez toutefois conscient que le mode suspendu sur les portables et certains ordinateurs de bureau sauvegarde une copie de la mémoire sur le disque, quelques soient les verrouillages). Les processus temps réel qui utilisent mlockall() pour s'affranchir des délais sur les fautes de pages devraient réserver suffisamment de pages de pile avant d'entrer dans la partie critique, ainsi, aucune faute de page ne serait provoquée par ces appels. Cela peut être fait en appelant une fonction qui alloue, de manière automatique, une grande variable de type tableau et qui écrit dans la mémoire occupée par ce tableau afin de toucher (Ndt : to touch) ces pages de pile. De cette manière, il y aura suffisamment de pages mappées pour la pile verrouillée en RAM. Cette écriture apparement inutile, permet de garantir qu'aucune faute de page (même due au mécanisme de copie-à-l'écriture) ne se produira dans la section critique. Les verrouillages mémoire ne sont pas hérités par un fils créé avec fork(2) et sont automatiquement retirés (déverrouillage) lors d'un execve(2) ou lorsque le processus s'achève. Le verrouillage mémoire sur un espace d'adresse est automatiquement retiré si l'espace d'adresse est démappé avec munmap(2). Il n'y a pas d'empilement des verrouillages mémoire, ce qui signifie qu'une page verrouillée plusieurs fois par mlock() ou mlockall() sera libérée en un seul appel à munlock() pour la zone mémoire correspondante ou par un appel à munlockall(). Les pages qui sont verrouillées par plusieurs zones, ou par plusieurs processus restent verrouillées en mémoire vive tant qu'il y a au moins un processus ou une zone qui les verrouille.

  Notes Linux
Sous Linux, mlock() et munlock() arrondissent par défaut automatiquement à la frontière de page la plus proche. Toutefois, POSIX.1-2001 permet à l'implémentation d'imposer que addr soit alignée sur une frontière de page. Les programmes portables en prendront soin.

  Limites et permissions
Dans Linux 2.6.8 et précédents, un processus devait être privilégié (CAP_IPC_LOCK) afin de verrouiller la mémoire et la limite de ressources logicielles RLIMIT_MEMLOCK définissait une limite sur la taille de la mémoire que le processus pouvait verrouiller. Depuis Linux 2.6.9, aucun limite n'existe sur la taille de mémoire que le processus privilégié peut verrouiller et la limite de ressources logicielles RLIMIT_MEMLOCK définit une limite sur la taille de la mémoire qu'un processus non privilégié peut verrouiller.

BOGUES
Dans les noyaux de la série 2.4 jusqu'au 2.4.17 y compris, un bogue faisait que l'attribut MCL_FUTURE de mlockall() n'était pas hérité à travers fork(2). Cela a été corrigé dans le noyau 2.4.18. Depuis le noyau 2.6.9, si un processus privilégié appelle mlockall(MCL_FUTURE) et par la suite se débarrasse de ses privilèges (perd la capacité CAP_IPC_LOCK en configurant, par exemple, son UID effectif à une valeur non nulle), les allocations mémoires suivantes (par exemple, mmap(2), brk(2)) échoueront si la limite de ressources RLIMIT_MEMLOCK est rencontrée.

VOIR AUSSI
mmap(2), shmctl(2), setrlimit(2), sysconf(3), capabilities(7)

TRADUCTION

Ce document est une traduction réalisée par Christophe Blaess <http://www.blaess.fr/christophe/> le 11 octobre 1996, mise à jour par Alain Portal <aportal AT univ-monpt2 DOT fr> le 30 mai 2006 et révisée le 22 décembre 2007.

L'équipe de traduction a fait le maximum pour réaliser une adaptation française de qualité. La version anglaise la plus à jour de ce document est toujours consultable via la commande : « LANG=C man 2 mlock ». N'hésitez pas à signaler à l'auteur ou au traducteur, selon le cas, toute erreur dans cette page de manuel.