Product SiteDocumentation Site

Chapitre 12. Administration avancée

12.1. RAID et LVM
12.1.1. RAID logiciel
12.1.2. LVM
12.1.3. RAID ou LVM ?
12.2. Virtualisation
12.2.1. Xen
12.2.2. LXC
12.2.3. Virtualisation avec KVM
12.3. Installation automatisée
12.3.1. Fully Automatic Installer (FAI)
12.3.2. Debian-installer avec préconfiguration
12.3.3. Simple-CDD : la solution tout en un
12.4. Supervision
12.4.1. Mise en œuvre de Munin
12.4.2. Mise en œuvre de Nagios
Ce chapitre est l'occasion de revenir sur des aspects déjà abordés mais avec une nouvelle perspective : au lieu d'installer une machine, nous étudierons les solutions pour déployer un parc de machines ; au lieu de créer une partition RAID ou LVM avec les outils intégrés à l'installateur, nous apprendrons à le faire manuellement afin de pouvoir revenir sur les choix initiaux. Enfin, la découverte des outils de supervision et de virtualisation parachèvera ce chapitre avant tout destiné aux administrateurs professionnels plus qu'aux particuliers responsables de leur réseau familial.

12.1. RAID et LVM

Le Chapitre 4, Installation a présenté ces technologies en montrant comment l'installateur facilitait leur déploiement. Au delà de cette étape cruciale, un bon administrateur doit pouvoir gérer l'évolution de ses besoins en espace de stockage sans devoir recourir à une coûteuse réinstallation. Il convient donc de maîtriser les outils qui servent à manipuler des volumes RAID et LVM.
Ces deux techniques permettent d'abstraire les volumes à monter de leurs contreparties physiques (disques durs ou partitions), la première pour sécuriser les données face aux pannes matérielles en dupliquant les informations et la seconde pour gérer ses données à sa guise en faisant abstraction de la taille réelle de ses disques. Dans les deux cas, cela se traduit par de nouveaux périphériques de type bloc sur lesquels on pourra donc créer des systèmes de fichiers, ou des espaces de mémoire virtuelle, qui ne correspondent pas directement à un seul disque dur réel. Bien que ces deux systèmes aient des origines bien distinctes, leurs fonctionnalités se recoupent en partie ; c'est pourquoi ils sont souvent mentionnés ensemble.
À la fois pour RAID et pour LVM, le noyau fournit un fichier de périphérique accessible en mode bloc (donc de la même manière qu'un disque dur ou une partition de celui-ci). Lorsqu'une application, ou une autre partie du noyau, a besoin d'accéder à un bloc de ce périphérique, le sous-système correspondant se charge d'effectuer le routage de ce bloc vers la couche physique appropriée, ce bloc pouvant être stocké sur un ou plusieurs disques, à un endroit non directement corrélé avec l'emplacement demandé dans le périphérique logique.

12.1.1. RAID logiciel

RAID signifie Redundant Array of Independent Disks (ensemble redondant de disques indépendants). Ce système a vu le jour pour fournir une protection contre les pannes de disques durs. Le principe général est simple : les données sont stockées sur un ensemble de plusieurs disques physiques au lieu d'être concentrées sur un seul, avec un certain degré (variable) de redondance. Selon ce niveau de redondance, en cas de panne subite d'un de ces disques, les données peuvent être reconstruites à l'identique à partir des disques qui restent opérationnels, ce qui évite de les perdre.
Le RAID peut être mis en œuvre par du matériel dédié (soit des modules RAID intégrés à des cartes pour contrôleur SCSI, soit directement sur la carte-mère) ou par l'abstraction logicielle (le noyau). Qu'il soit matériel ou logiciel, un système RAID disposant de suffisamment de redondance peut, en cas de défaillance d'un disque, rester opérationnel en toute transparence, le niveau supérieur (les applications) pouvant même continuer à accéder aux données sans interruption malgré la panne. Évidemment, ce « mode dégradé » peut avoir des implications en termes de performances et il réduit la quantité de redondance du système ; une deuxième panne simultanée peut aboutir à la perte des données. Il est donc d'usage de ne rester en mode dégradé que le temps de se procurer un remplaçant pour le disque défaillant. Une fois qu'il est mis en place, le système RAID peut reconstruire les données qui doivent y être présentes, de manière à revenir à un état sécurisé. Le tout se fait bien entendu de manière invisible pour les applications, hormis les baisses éventuelles de performances pendant la durée du mode dégradé et la phase de reconstruction qui s'ensuit.
Lorsque le RAID est implémenté par le matériel, c'est le setup du BIOS qui permet généralement de le configurer et le noyau Linux va considérer le volume RAID comme un seul disque, fonctionnant comme un disque standard, à ceci près que le nom du périphérique peut différer. Ainsi, le noyau de Squeeze présentait certains volumes RAID matériels sous le périphérique /dev/cciss/c0d0 ; le noyau de Wheezy l'a changé en quelque chose de plus naturel, à savoir /dev/sda. Toutefois, d'autres contrôleurs RAID peuvent encore avoir des noms différents.
Nous ne traiterons que du RAID logiciel dans ce livre.

12.1.1.1. Différents niveaux de RAID

On distingue plusieurs niveaux de RAID, différant dans l'agencement des données et le degré de redondance qu'ils proposent. Plus la redondance est élevée, plus la résistance aux pannes sera forte, puisque le système pourra continuer à fonctionner avec un plus grand nombre de disques en panne ; la contrepartie est que le volume utile de données devient plus restreint (ou, pour voir les choses différemment, qu'il sera nécessaire d'avoir plus de disques pour stocker la même quantité de données).
RAID linéaire
Bien que le sous-système RAID du noyau permette la mise en œuvre de « RAID linéaire », il ne s'agit pas à proprement parler de RAID, puisqu'il n'y a aucune redondance. Le noyau se contente d'agréger plusieurs disques les uns à la suite des autres et de les proposer comme un seul disque virtuel (en fait, un seul périphérique bloc). C'est à peu près sa seule utilité et il n'est que rarement utilisé seul (voir plus loin), d'autant que l'absence de redondance signifie que la défaillance d'un seul disque rend la totalité des données inaccessibles.
RAID-0
Ici non plus, aucune redondance n'est proposée, mais les disques ne sont plus simplement mis bout à bout : ils sont en réalité découpés en stripes (bandes), ces bandes étant alors intercalées dans le disque logique. Ainsi, dans le cas de RAID-0 à deux disques, les blocs impairs du volume virtuel seront stockés sur le premier disque et les blocs pairs sur le second.
Le but de ce système n'est pas d'augmenter la fiabilité, puisqu'ici aussi un seul disque en panne rend inaccessible la totalité des données, mais d'améliorer les performances : lors d'un accès séquentiel à de grandes quantités de données contiguës, le noyau pourra lire (ou écrire) en parallèle depuis les deux (ou plus...) disques qui composent l'ensemble, ce qui augmente le débit. L'usage du RAID-0 a tendance à disparaître au profit de LVM, qui sera abordé par la suite.
RAID-1
Aussi connu sous le nom de « RAID miroir », c'est le système RAID le plus simple. Il utilise en général deux disques physiques de tailles identiques et fournit un volume logique de la même taille. Les données sont stockées à l'identique sur les deux disques, d'où l'appellation de « miroir ». En cas de panne d'un disque, les données restent accessibles sur l'autre. Pour les données vraiment critiques, on peut utiliser le RAID-1 sur plus de deux disques, au prix de devoir multiplier le rapport entre le coût des disques et la quantité de données utiles.
Ce niveau de RAID, bien qu'onéreux (puisque seule la moitié, au mieux, de l'espace disque physique se retrouve utilisable), reste assez utilisé en pratique. Il est en effet conceptuellement simple et il permet de réaliser très simplement des sauvegardes (puisque les deux disques sont identiques, on peut en extraire temporairement un sans perturber le fonctionnement du système). Les performances en lecture sont généralement améliorées par rapport à un simple disque (puisque le système peut théoriquement lire la moitié des données sur chaque disque, en parallèle sur les deux), sans trop de perte en vitesse d'écriture. Dans le cas de RAID-1 à N disques, les données restent disponibles même en cas de panne de N-1 disques.
RAID-4
Ce niveau de RAID, assez peu usité, utilise N disques pour stocker les données utiles, et un disque supplémentaire pour des informations de redondance. Si ce disque tombe en panne, le système peut le reconstruire à l'aide des N autres. Si c'est un des N disques de données qui tombe, les N-1 restants et le disque de parité contiennent suffisamment d'informations pour reconstruire les données.
Le RAID-4 est peu onéreux (puisqu'il n'entraîne qu'un surcoût d'un disque pour N), n'a pas d'impact notable sur les performances en lecture, mais ralentit les écritures. De plus, comme chaque écriture sur un des N disques s'accompagne d'une écriture sur le disque de parité, celui-ci se voit confier beaucoup plus d'écritures que ceux-là et peut voir sa durée de vie considérablement réduite en conséquence. Il résiste au maximum à la panne d'un disque parmi les N+1.
RAID-5
Le RAID-5 corrige ce dernier défaut du RAID-4, en répartissant les blocs de parité sur les N+1 disques, qui jouent à présent un rôle identique.
Les performances en lecture et en écriture sont inchangées par rapport au RAID-4. Là encore, le système reste fonctionnel en cas de défaillance d'un disque parmi les N+1, mais pas plus.
RAID-6
Le RAID-6 peut être considéré comme une extension du RAID-5, dans laquelle à chaque série de N blocs correspondent non plus un mais deux blocs de parité, qui sont ici aussi répartis sur les N+2 disques.
Ce niveau de RAID, légèrement plus coûteux que les deux précédents, apporte également une protection supplémentaire puisqu'il conserve l'intégralité des données même en cas de panne simultanée de deux disques (sur N+2). La contrepartie est que les opérations d'écriture impliquent dorénavant l'écriture d'un bloc de données et de deux blocs de contrôle, ce qui les ralentit d'autant plus.
RAID-1+0
Il ne s'agit pas à proprement parler d'un niveau de RAID, mais d'un RAID à deux niveaux. Si l'on dispose de 2×N disques, on commence par les apparier en N volumes de RAID-1. Ces N volumes sont alors agrégés en un seul, soit par le biais de RAID linéaire, soit par du RAID-0, voire (de plus en plus fréquemment) par LVM. On sort dans ce dernier cas du RAID pur, mais cela ne pose pas de problème.
Le RAID-1+0 tolère la panne de disques multiples, jusqu'à N dans le cas d'un groupe de 2×N, à condition qu'au moins un disque reste fonctionnel dans chaque paire associée en RAID-1.
On choisira bien entendu le niveau de RAID en fonction des contraintes et des besoins spécifiques de chaque application. Notons qu'on peut constituer plusieurs volumes RAID distincts, avec des configurations différentes, sur le même ordinateur.

12.1.1.2. Mise en place du RAID

La mise en place de volumes RAID se fait grâce au paquet mdadm ; ce dernier contient la commande du même nom, qui permet de créer et manipuler des ensembles RAID, ainsi que les scripts et outils permettant l'intégration avec le système et la supervision.
Prenons l'exemple d'un serveur sur lequel sont branchés un certain nombre de disques, dont certains sont occupés et d'autres peuvent être utilisés pour établir du RAID. On dispose initialement des disques et partitions suivants :
  • le disque sdb, de 4 Go, est entièrement disponible ;
  • le disque sdc, de 4 Go, est également entièrement disponible ;
  • sur le disque sdd, seule la partition sdd2 d'environ 4 Go est disponible ;
  • enfin, un disque sde, toujours de 4 Go, est entièrement disponible.
Nous allons construire sur ces éléments physiques deux volumes, l'un en RAID-0, l'autre en miroir. Commençons par le RAID-0 :
# mdadm --create /dev/md0 --level=0 --raid-devices=2 /dev/sda /dev/sde
mdadm: Defaulting to version 1.2 metadata
mdadm: array /dev/md0 started.
# mdadm --query /dev/md0
/dev/md0: 7.100GiB raid0 2 devices, 0 spares. Use mdadm --detail for more detail.
# mdadm --detail /dev/md0
/dev/md0:
        Version : 1.2
  Creation Time : Thu Jan 17 15:56:55 2013
     Raid Level : raid0
     Array Size : 8387584 (8.00 GiB 8.59 GB)
   Raid Devices : 2
  Total Devices : 2
    Persistence : Superblock is persistent

    Update Time : Thu Jan 17 15:56:55 2013
          State : clean
 Active Devices : 2
Working Devices : 2
 Failed Devices : 0
  Spare Devices : 0

     Chunk Size : 512K

           Name : mirwiz:0  (local to host mirwiz)
           UUID : bb085b35:28e821bd:20d697c9:650152bb
         Events : 0

    Number   Major   Minor   RaidDevice State
       0       8       16        0      active sync   /dev/sdb
       1       8       32        1      active sync   /dev/sdc
# mkfs.ext4 /dev/md0

mke2fs 1.42.5 (29-Jul-2012)
Étiquette de système de fichiers=
Type de système d'exploitation : Linux
Taille de bloc=4096 (log=2)
Taille de fragment=4096 (log=2)
« Stride » = 128 blocs, « Stripe width » = 256 blocs
1048576 i-noeuds, 2096896 blocs
104856 blocs (5.00%) réservés pour le super utilisateur
Premier bloc de données=0
Nombre maximum de blocs du système de fichiers=2147483648
64 groupes de blocs
32768 blocs par groupe, 32768 fragments par groupe
8192 i-noeuds par groupe
Superblocs de secours stockés sur les blocs : 
        32768, 98304, 163840, 229376, 294912, 819200, 884736, 1605632

Allocation des tables de groupe : complété
Écriture des tables d'i-noeuds : complété
Création du journal (32768 blocs) : complété
Écriture des superblocs et de l'information de comptabilité du système de
fichiers : complété
# mkdir /srv/raid-0
# mount /dev/md0 /srv/raid-0
# df -h /srv/raid-0
Sys. de fichiers      Tail. Uti. Disp. Uti% Monté sur
/dev/md0              7,9G  147M  7,4G   2% /srv/raid-0
La commande mdadm --create requiert en arguments le nom du volume à créer (/dev/md*, MD signifiant Multiple Device), le niveau de RAID, le nombre de disques (qui prend tout son sens à partir du RAID-1 mais qui est systématiquement obligatoire) et les périphériques à utiliser. Une fois le périphérique créé, nous pouvons l'utiliser comme une partition normale, y créer un système de fichiers, le monter, etc. On notera que le fait que nous ayons créé un volume RAID-0 sur md0 est une pure coïncidence et que le numéro d'un ensemble n'a pas à être corrélé avec le modèle de redondance (ou non) choisi. Il est également possible de créer des volumes RAID nommés, en indiquant à mdadm des noms de volume comme /dev/md/lineaire au lieu de /dev/md0.
La création d'un volume RAID-1 se fait de manière similaire, les différences n'apparaissant qu'après sa création :
# mdadm --create /dev/md1 --level=1 --raid-devices=2 /dev/sdd2 /dev/sde
mdadm: Note: this array has metadata at the start and
    may not be suitable as a boot device.  If you plan to
    store '/boot' on this device please ensure that
    your boot-loader understands md/v1.x metadata, or use
    --metadata=0.90
mdadm: largest drive (/dev/sdd2) exceeds size (4192192K) by more than 1%
Continue creating array? y
mdadm: Defaulting to version 1.2 metadata
mdadm: array /dev/md1 started.
# mdadm --query /dev/md1
/dev/md1: 4.00GiB raid1 2 devices, 0 spares. Use mdadm --detail for more detail.
# mdadm --detail /dev/md1
/dev/md1:
        Version : 1.2
  Creation Time : Thu Jan 17 16:13:04 2013
     Raid Level : raid1
     Array Size : 4192192 (4.00 GiB 4.29 GB)
  Used Dev Size : 4192192 (4.00 GiB 4.29 GB)
   Raid Devices : 2
  Total Devices : 2
    Persistence : Superblock is persistent

    Update Time : Thu Jan 17 16:13:04 2013
          State : clean, resyncing (PENDING)
 Active Devices : 2
Working Devices : 2
 Failed Devices : 0
  Spare Devices : 0

           Name : mirwiz:1  (local to host mirwiz)
           UUID : 6ec558ca:0c2c04a0:19bca283:95f67464
         Events : 0

    Number   Major   Minor   RaidDevice State
       0       8       50        0      active sync   /dev/sdd2
       1       8       64        1      active sync   /dev/sde
# mdadm --detail /dev/md1
/dev/md1:
[...]
          State : clean
[...]
Plusieurs remarques ici. Premièrement, mdadm constate que les deux éléments physiques n'ont pas la même taille ; comme cela implique que de l'espace sera perdu sur le plus gros des deux éléments, une confirmation est nécessaire.
La deuxième remarque, plus importante, concerne l'état du miroir. Les deux disques sont en effet censés avoir, en fonctionnement normal, un contenu rigoureusement identique. Comme rien ne garantit que ce soit le cas à la création du volume, le système RAID va s'en assurer. Il y a donc une phase de synchronisation, automatique, dès la création du périphérique RAID. Si l'on patiente quelques instants (qui varient selon la taille des disques...), on obtient finalement un état « actif ». Il est à noter que durant cette étape de reconstruction du miroir, l'ensemble RAID est en mode dégradé et que la redondance n'est pas assurée. Une panne de l'un des disques pendant cette fenêtre sensible peut donc aboutir à la perte de l'intégralité des données. Il est cependant rare que de grandes quantités de données critiques soient placées sur un volume RAID fraîchement créé avant que celui-ci ait eu le temps de se synchroniser. On notera également que même en mode dégradé, le périphérique /dev/md1 est utilisable (pour créer le système de fichiers et commencer à copier des données, éventuellement).
Voyons à présent ce qui se passe en cas de panne d'un élément de l'ensemble RAID-1. mdadm permet de simuler cette défaillance, grâce à son option --fail :
# mdadm /dev/md1 --fail /dev/sde
mdadm: set /dev/sde faulty in /dev/md1
# mdadm --detail /dev/md1
/dev/md1:
[...]
    Update Time : Thu Jan 17 16:14:09 2013
          State : active, degraded
 Active Devices : 1
Working Devices : 1
 Failed Devices : 1
  Spare Devices : 0

           Name : mirwiz:1  (local to host mirwiz)
           UUID : 6ec558ca:0c2c04a0:19bca283:95f67464
         Events : 19

    Number   Major   Minor   RaidDevice State
       0       8       50        0      active sync   /dev/sdd2
       1       0        0        1      removed

       1       8       64        -      faulty spare   /dev/sde
Le contenu du volume reste accessible (et, s'il est monté, les applications ne s'aperçoivent de rien), mais la sécurité des données n'est plus assurée : si le disque sdd venait à tomber en panne, les données seraient perdues. Pour éviter ce risque, nous allons remplacer ce disque par un neuf, sdf :
# mdadm /dev/md1 --add /dev/sdf
mdadm: added /dev/sdf
# mdadm --detail /dev/md1
/dev/md1:
[...]
   Raid Devices : 2
  Total Devices : 3
    Persistence : Superblock is persistent

    Update Time : Thu Jan 17 16:16:36 2013
          State : clean, degraded, recovering
 Active Devices : 1
Working Devices : 2
 Failed Devices : 1
  Spare Devices : 1

 Rebuild Status : 28% complete

           Name : mirwiz:1  (local to host mirwiz)
           UUID : 6ec558ca:0c2c04a0:19bca283:95f67464
         Events : 26

    Number   Major   Minor   RaidDevice State
       0       8       50        0      active sync   /dev/sdd2
       2       8       80        1      spare rebuilding   /dev/sdf

       1       8       64        -      faulty spare   /dev/sde
# [...]
[...]
# mdadm --detail /dev/md1
/dev/md1:
[...]
    Update Time : Thu Jan 17 16:16:36 2013
          State : clean
 Active Devices : 2
Working Devices : 2
 Failed Devices : 1
  Spare Devices : 0

           Name : mirwiz:1  (local to host mirwiz)
           UUID : 6ec558ca:0c2c04a0:19bca283:95f67464
         Events : 41

    Number   Major   Minor   RaidDevice State
       0       8       50        0      active sync   /dev/sdd2
       2       8       80        1      active sync   /dev/sdf

       1       8       64        -      faulty spare   /dev/sde
Ici encore, nous avons une phase de reconstruction, déclenchée automatiquement, pendant laquelle le volume, bien qu'accessible, reste en mode dégradé. Une fois qu'elle est terminée, le RAID revient dans son état normal. On peut alors signaler au système que l'on va retirer le disque sde de l'ensemble, pour se retrouver avec un miroir classique sur deux disques :
# mdadm /dev/md1 --remove /dev/sde
mdadm: hot removed /dev/sde from /dev/md1
# mdadm --detail /dev/md1
/dev/md1:
[...]
    Number   Major   Minor   RaidDevice State
       0       8       50        0      active sync   /dev/sdd2
       2       8       80        1      active sync   /dev/sdf
Le disque pourra alors être démonté physiquement lors d'une extinction de la machine. Dans certaines configurations matérielles, les disques peuvent même être remplacés à chaud, ce qui permet de se passer de cette extinction. Parmi ces configurations, on trouvera certains contrôleurs SCSI, la plupart des systèmes SATA et les disques externes sur bus USB ou Firewire.

12.1.1.3. Sauvegarde de la configuration

La plupart des méta-données concernant les volumes RAID sont sauvegardées directement sur les disques qui les composent, de sorte que le noyau peut détecter les différents ensembles avec leurs composants et les assembler automatiquement lors du démarrage du système. Cela dit, il convient de sauvegarder cette configuration, car cette détection n'est pas infaillible et aura tendance à faillir précisément en période sensible. Si dans notre exemple la panne du disque sde était réelle, et si on redémarrait le système sans le retirer, ce disque pourrait, à la faveur du redémarrage, « retomber en marche ». Le noyau aurait alors trois éléments physiques, chacun prétendant représenter la moitié du même volume RAID. Une autre source de confusion peut subvenir si l'on consolide des volumes RAID de deux serveurs sur un seul. Si ces ensembles étaient en fonctionnement normal avant le déplacement des disques, le noyau saura reconstituer les paires correctement. Mais pour peu que les disques déplacés soient agrégés en un /dev/md1 et qu'il existe également un md1 sur le serveur consolidé, l'un des miroirs sera contraint de changer de nom.
Il est donc important de sauvegarder la configuration, ne serait-ce qu'à des fins de référence. Pour cela, on éditera le fichier /etc/mdadm/mdadm.conf, dont un exemple est donné ci-dessous.

Exemple 12.1. Fichier de configuration de mdadm

# mdadm.conf
#
# Please refer to mdadm.conf(5) for information about this file.
#

# by default (built-in), scan all partitions (/proc/partitions) and all
# containers for MD superblocks. alternatively, specify devices to scan, using
# wildcards if desired.
DEVICE /dev/sd*

# auto-create devices with Debian standard permissions
CREATE owner=root group=disk mode=0660 auto=yes

# automatically tag new arrays as belonging to the local system
HOMEHOST <system>

# instruct the monitoring daemon where to send mail alerts
MAILADDR root

# definitions of existing MD arrays
ARRAY /dev/md0 metadata=1.2 name=mirwiz:0 UUID=bb085b35:28e821bd:20d697c9:650152bb
ARRAY /dev/md1 metadata=1.2 name=mirwiz:1 UUID=6ec558ca:0c2c04a0:19bca283:95f67464

# This configuration was auto-generated on Thu, 17 Jan 2013 16:21:01 +0100
# by mkconf 3.2.5-3
Une des informations les plus souvent utiles est l'option DEVICE, qui spécifie l'ensemble des périphériques sur lesquels le système va chercher automatiquement des composants de volumes RAID au démarrage. Nous avons ici remplacé la valeur implicite, partitions containers, par une liste explicite de fichiers de périphérique ; nous avons en effet choisi d'utiliser des disques entiers, et non simplement des partitions, pour certains volumes.
Les deux dernières lignes de notre exemple sont celles qui permettent au noyau de choisir en toute sécurité quel numéro de volume associer à quel ensemble. Les méta-informations stockées sur les disques sont en effet suffisantes pour reconstituer les volumes, mais pas pour en déterminer le numéro (donc le périphérique /dev/md* correspondant).
Fort heureusement, ces lignes peuvent être générées automatiquement :
# mdadm --misc --detail --brief /dev/md?
ARRAY /dev/md0 metadata=1.2 name=mirwiz:0 UUID=bb085b35:28e821bd:20d697c9:650152bb
ARRAY /dev/md1 metadata=1.2 name=mirwiz:1 UUID=6ec558ca:0c2c04a0:19bca283:95f67464
Le contenu de ces deux dernières lignes ne dépend pas de la liste des disques qui composent les volumes. On pourra donc se passer de les régénérer si l'on remplace un disque défectueux par un neuf. En revanche, il faudra prendre soin de les mettre à jour après chaque création ou suppression de volume.

12.1.2. LVM

LVM, ou Logical Volume Manager, est une autre approche servant à abstraire les volumes logiques des disques physiques. Le but principal était ici non de gagner en fiabilité des données mais en souplesse d'utilisation. LVM permet en effet de modifier dynamiquement un volume logique, en toute transparence du point de vue des applications. On peut ainsi par exemple ajouter de nouveaux disques, migrer les données dessus et récupérer les anciens disques ainsi libérés, sans démonter le volume.

12.1.2.1. Concepts de LVM

LVM manipule trois types de volumes pour atteindre cette flexibilité.
Premièrement, les PV ou physical volumes sont les entités les plus proches du matériel : il peut s'agir de partitions sur des disques ou de disques entiers, voire de n'importe quel périphérique en mode bloc (y compris, par exemple, un volume RAID). Attention, lorsqu'un élément physique est initialisé en PV pour LVM, il ne faudra plus l'utiliser directement, sous peine d'embrouiller le système.
Les PV sont alors regroupés en VG (volume groups), que l'on peut considérer comme des disques virtuels (et extensibles, comme on le verra). Les VG sont abstraits et ne disposent pas de fichier spécial dans /dev/, aucun risque donc de les utiliser directement.
Enfin, les LV (logical volumes) sont des subdivisions des VG, que l'on peut comparer à des partitions sur les disques virtuels que les VG représentent. Ces LV deviennent des périphériques, que l'on peut utiliser comme toute partition physique (par exemple pour y établir des systèmes de fichiers).
Il faut bien réaliser que la subdivision d'un groupe de volumes en LV est entièrement décorrélée de sa composition physique (les PV). On peut ainsi avoir un VG subdivisé en une douzaine de volumes logiques tout en ne comportant qu'un volume physique (un disque, par exemple), ou au contraire un seul gros volume logique réparti sur plusieurs disques physiques ou partitions. La seule contrainte, bien entendu, est que la somme des tailles des LV d'un groupe ne doive pas excéder la capacité totale des PV qui le composent.
En revanche, il est souvent utile de grouper dans un même VG des éléments physiques présentant des caractéristiques similaires et de subdiviser ce VG en volumes logiques qui seront utilisés de manière comparable également. Par exemple, si l'on dispose de disques rapides et de disques lents, on pourra regrouper les rapides dans un VG et les plus lents dans un autre. Les subdivisions logiques du premier VG pourront alors être affectées à des tâches nécessitant de bonnes performances, celles du second étant réservées aux tâches qui peuvent se contenter de vitesses médiocres.
Dans tous les cas, il faut également garder à l'esprit qu'un LV n'est pas accroché à un PV ou un autre. Même si on peut influencer l'emplacement physique où les données d'un LV sont écrites, en fonctionnement normal c'est une information qui n'a pas d'intérêt particulier. Au contraire : lors d'une modification des composants physiques d'un groupe, les LV peuvent être amenés à se déplacer (tout en restant, bien entendu, confinés aux PV qui composent ce groupe).

12.1.2.2. Mise en place de LVM

Nous allons suivre pas à pas une utilisation typique de LVM, pour simplifier une situation complexe. De telles situations sont souvent le résultat d'un historique chargé, où des solutions temporaires se sont accumulées au fil du temps. Considérons donc pour notre exemple un serveur dont les besoins en stockage ont varié et pour lequel on se retrouve avec une configuration complexe de partitions disponibles, morcelées sur différents disques hétéroclites et partiellement utilisés. Concrètement, on dispose des partitions suivantes :
  • sur le disque sdb, une partition sdb2 de 4 Go ;
  • sur le disque sdc, une partition sdc3 de 3 Go ;
  • le disque sdd, de 4 Go, est entièrement disponible ;
  • sur le disque sdf, une partition sdf1 de 4 Go et une sdf2 de 5 Go.
On notera de plus que les disques sdb et sdf ont de meilleures performances que les deux autres.
Le but de la manœuvre est de mettre en place trois volumes logiques distincts, pour trois applications séparées : un serveur de fichiers (qui nécessite 5 Go), une base de données (1 Go) et un emplacement pour les sauvegardes (12 Go). Les deux premières ont de forts besoins de performance, mais pas la troisième, qui est moins critique. Ces contraintes empêchent l'utilisation des partitions isolément ; l'utilisation de LVM permet de s'affranchir des limites imposées par leurs tailles individuelles, pour n'être limité que par leur capacité totale.
Le prérequis est le paquet lvm2 (et ses dépendances). Lorsque ce paquet est installé, la mise en place de LVM se fait en trois étapes, correspondant aux trois couches de LVM.
Commençons par préparer les volumes physiques à l'aide de pvcreate :
# pvdisplay
# pvcreate /dev/sdb2
  Writing physical volume data to disk "/dev/sdb2"
Physical volume "/dev/sdb2" successfully created
# pvdisplay

  "/dev/sdb2" is a new physical volume of "4,00 GiB"
  --- NEW Physical volume ---
  PV Name               /dev/sdb2
  VG Name
  PV Size               4,00 GiB
  Allocatable           NO
  PE Size               0
  Total PE              0
  Free PE               0
  Allocated PE          0
  PV UUID               0zuiQQ-j1Oe-P593-4tsN-9FGy-TY0d-Quz31I

# for i in sdc3 sdd sdf1 sdf2 ; do pvcreate /dev/$i ; done
  Writing physical volume data to disk "/dev/sdc3"
  Physical volume "/dev/sdc3" successfully created
  Writing physical volume data to disk "/dev/sdd"
  Physical volume "/dev/sdd" successfully created
  Writing physical volume data to disk "/dev/sdf1"
  Physical volume "/dev/sdf1" successfully created
  Writing physical volume data to disk "/dev/sdf2"
  Physical volume "/dev/sdf2" successfully created
# pvdisplay -C
  PV         VG   Fmt  Attr PSize PFree
  /dev/sdb2       lvm2 a--  4,00g 4,00g
  /dev/sdc3       lvm2 a--  3,09g 3,09g
  /dev/sdd        lvm2 a--  4,00g 4,00g
  /dev/sdf1       lvm2 a--  4,10g 4,10g
  /dev/sdf2       lvm2 a--  5,22g 5,22g
Rien de bien sorcier jusqu'à présent ; on remarquera que l'on peut établir un PV aussi bien sur un disque entier que sur des partitions. Comme on le constate, la commande pvdisplay est capable de lister les PV déjà établis, sous deux formes.
Constituons à présent des groupes de volumes (VG) à partir de ces éléments physiques, à l'aide de la commande vgcreate. Nous allons placer dans le VG vg_critique uniquement des PV appartenant à des disques rapides ; le deuxième VG, vg_normal, contiendra des éléments physiques plus lents.
# vgdisplay
  No volume groups found
# vgcreate vg_critique /dev/sdb2 /dev/sdf1
  Volume group "vg_critique" successfully created
# vgdisplay
  --- Volume group ---
  VG Name               vg_critique
  System ID
  Format                lvm2
  Metadata Areas        2
  Metadata Sequence No  1
  VG Access             read/write
  VG Status             resizable
  MAX LV                0
  Cur LV                0
  Open LV               0
  Max PV                0
  Cur PV                2
  Act PV                2
  VG Size               8,09 GiB
  PE Size               4,00 MiB
  Total PE              2071
  Alloc PE / Size       0 / 0
  Free  PE / Size       2071 / 8,09 GiB
  VG UUID               bpq7zO-PzPD-R7HW-V8eN-c10c-S32h-f6rKqp

# vgcreate vg_normal /dev/sdc3 /dev/sdd /dev/sdf2
  Volume group "vg_normal" successfully created
# vgdisplay -C
  VG          #PV #LV #SN Attr   VSize  VFree
  vg_critique   2   0   0 wz--n-  8,09g  8,09g
  vg_normal     3   0   0 wz--n- 12,30g 12,30g
Ici encore, les commandes sont relativement simples (et vgdisplay présente deux formats de sortie). Notons que rien n'empêche de placer deux partitions d'un même disque physique dans deux VG différents ; le préfixe vg_ utilisé ici est une convention, mais n'est pas obligatoire.
Nous disposons maintenant de deux « disques virtuels », respectivement d'environ 8 Go et 12 Go. Nous pouvons donc les subdiviser en « partitions virtuelles » (des LV). Cette opération passe par la commande lvcreate, dont la syntaxe est un peu plus complexe :
# lvdisplay
# lvcreate -n lv_fichiers -L 5G vg_critique
  Logical volume "lv_fichiers" created
# lvdisplay
  --- Logical volume ---
  LV Path                /dev/vg_critique/lv_fichiers
  LV Name                lv_fichiers
  VG Name                vg_critique
  LV UUID                J3V0oE-cBYO-KyDe-5e0m-3f70-nv0S-kCWbpT
  LV Write Access        read/write
  LV Creation host, time mirwiz, 2013-01-17 17:05:13 +0100
  LV Status              available
  # open                 0
  LV Size                5,00 GiB
  Current LE             1280
  Segments               2
  Allocation             inherit
  Read ahead sectors     auto
  - currently set to     256
  Block device           253:0

# lvcreate -n lv_base -L 1G vg_critique
  Logical volume "lv_base" created
# lvcreate -n lv_sauvegardes -L 12G vg_normal
  Logical volume "lv_sauvegardes" created
# lvdisplay -C
  LV             VG          Attr      LSize  Pool Origin Data%  Move Log Copy%  Convert
  lv_base        vg_critique -wi-a---  1,00g
  lv_fichiers    vg_critique -wi-a---  5,00g
  lv_sauvegardes vg_normal   -wi-a--- 12,00g
Deux informations sont obligatoires lors de la création des volumes logiques et doivent être passées sous forme d'options à lvcreate. Le nom du LV à créer est spécifié par l'option -n et sa taille est en général spécifiée par -L. Évidemment, il faut également expliciter à l'intérieur de quel groupe de volumes on souhaite créer le LV, d'où le dernier paramètre de la ligne de commande.
Les volumes logiques, une fois créés, sont représentés par des fichiers de périphérique situés dans /dev/mapper/ :
# ls -l /dev/mapper
total 0
crw------T 1 root root 10, 236 17 janv. 16:52 control
lrwxrwxrwx 1 root root       7 17 janv. 17:05 vg_critique-lv_base -> ../dm-1
lrwxrwxrwx 1 root root       7 17 janv. 17:05 vg_critique-lv_fichiers -> ../dm-0
lrwxrwxrwx 1 root root       7 17 janv. 17:05 vg_normal-lv_sauvegardes -> ../dm-2
# ls -l /dev/dm-*
brw-rw---T 1 root disk 253,  0 17 janv. 17:05 /dev/dm-0
brw-rw---T 1 root disk 253,  1 17 janv. 17:05 /dev/dm-1
brw-rw---T 1 root disk 253,  2 17 janv. 17:05 /dev/dm-2
Pour faciliter les choses, des liens symboliques sont également créés automatiquement dans des répertoires correspondant aux VG :
# ls -l /dev/vg_critique
total 0
lrwxrwxrwx 1 root root 7 17 janv. 17:05 lv_base -> ../dm-1
lrwxrwxrwx 1 root root 7 17 janv. 17:05 lv_fichiers -> ../dm-0
# ls -l /dev/vg_normal
total 0
lrwxrwxrwx 1 root root 7 17 janv. 17:05 lv_sauvegardes -> ../dm-2
On peut dès lors utiliser les LV tout comme on utiliserait des partitions classiques :
# mkfs.ext4 /dev/vg_normal/lv_sauvegardes
mke2fs 1.42.5 (29-Jul-2012)
Étiquette de système de fichiers=
Type de système d'exploitation : Linux
Taille de bloc=4096 (log=2)
[...]
Création du journal (32768 blocs) : complété
Écriture des superblocs et de l'information de comptabilité du système de
fichiers : complété
# mkdir /srv/sauvegardes
# mount /dev/vg_normal/lv_sauvegardes /srv/sauvegardes
# df -h /srv/sauvegardes
Sys. de fichiers      Tail. Uti. Disp. Uti% Monté sur
/dev/mapper/vg_normal-lv_sauvegardes
                       12G  158M   12G   2% /srv/sauvegardes
# [...]
[...]
# cat /etc/fstab
[...]
/dev/vg_critique/lv_base        /srv/base               ext4
/dev/vg_critique/lv_fichiers    /srv/fichiers           ext4
/dev/vg_normal/lv_sauvegardes   /srv/sauvegardes        ext4
On s'est ainsi abstrait, du point de vue applicatif, de la myriade de petites partitions, pour se retrouver avec une seule partition de 12 Go.

12.1.2.3. LVM au fil du temps

Cette capacité à agréger des partitions ou des disques physiques n'est pas le principal attrait de LVM. La souplesse offerte se manifeste surtout au fil du temps, lorsque les besoins évoluent. Supposons par exemple que de nouveaux fichiers volumineux doivent être stockés et que le LV dévolu au serveur de fichiers ne suffise plus. Comme nous n'avons pas utilisé l'intégralité de l'espace disponible dans vg_critique, nous pouvons étendre lv_fichiers. Nous allons pour cela utiliser la commande lvresize pour étendre le LV, puis resize2fs pour ajuster le système de fichiers en conséquence :
# df -h /srv/fichiers/
Sys. de fichiers      Tail. Uti. Disp. Uti% Monté sur
/dev/mapper/vg_critique-lv_fichiers
                      5,0G  4,6G  146M  97% /srv/fichiers
# lvdisplay -C vg_critique/lv_fichiers
  LV          VG          Attr     LSize Pool Origin Data%  Move Log Copy%  Convert
  lv_fichiers vg_critique -wi-ao-- 5,00G
# vgdisplay -C vg_critique
  VG          #PV #LV #SN Attr   VSize VFree
  vg_critique   2   2   0 wz--n- 8,14G 2,14G
# lvresize -L 7G vg_critique/lv_fichiers
  Extending logical volume lv_fichiers to 7,00 GB
  Logical volume lv_fichiers successfully resized
# lvdisplay -C vg_critique/lv_fichiers
  LV          VG          Attr     LSize Pool Origin Data%  Move Log Copy%  Convert
  lv_fichiers vg_critique -wi-ao-- 7,00G
# resize2fs /dev/vg_critique/lv_fichiers
resize2fs 1.42.5 (29-Jul-2012)
Le système de fichiers de /dev/vg_critique/lv_fichiers est monté sur /srv/fichiers ; le changement de taille doit être effectué en ligne
old_desc_blocks = 1, new_desc_blocks = 1
En train d'effectuer un changement de taille en ligne de /dev/vg_critique/lv_fichiers vers 1835008 (4k) blocs.
Le système de fichiers /dev/vg_critique/lv_fichiers a maintenant une taille de 1835008 blocs.

# df -h /srv/fichiers/
Sys. de fich.         Tail. Uti. Disp. Uti% Monté sur
/dev/mapper/vg_critique-lv_fichiers
                      6,9G  4,6G  2,1G  70% /srv/fichiers
On pourrait procéder de même pour étendre le volume qui héberge la base de données, mais on arrive à la limite de la capacité du VG :
# df -h /srv/base/
Sys. de fichiers      Tail. Uti. Disp. Uti% Monté sur
/dev/mapper/vg_critique-lv_base
                     1008M  854M  104M  90% /srv/base
# vgdisplay -C vg_critique
  VG          #PV #LV #SN Attr   VSize VFree
  vg_critique   2   2   0 wz--n- 8,09g 92,00m
Qu'à cela ne tienne, LVM permet également d'ajouter des volumes physiques à des groupes de volumes existants. Par exemple, on a pu s'apercevoir que la partition sdb1, qui jusqu'à présent était utilisée en dehors de LVM, contenait uniquement des archives qui ont pu être déplacées dans lv_sauvegardes. On peut donc l'intégrer au groupe de volumes pour récupérer l'espace disponible. Ceci passe par la commande vgextend. Il faut bien entendu préparer la partition comme un volume physique au préalable. Une fois le VG étendu, on peut suivre le même cheminement que précédemment pour étendre le système de fichiers.
# pvcreate /dev/sdb1
  Writing physical volume data to disk "/dev/sdb1"
  Physical volume "/dev/sdb1" successfully created
# vgextend vg_critique /dev/sdb1
  Volume group "vg_critique" successfully extended
# vgdisplay -C vg_critique
  VG          #PV #LV #SN Attr   VSize VFree
  vg_critique   3   2   0 wz--n- 9,09G 1,09G
# [...]
[...]
# df -h /srv/base/
Sys. de fichiers      Tail. Uti. Disp. Uti% Monté sur
/dev/mapper/vg_critique-lv_base
                      2,0G  854M  1,1G  45% /srv/base

12.1.3. RAID ou LVM ?

Les apports de RAID et LVM sont indéniables dès que l'on s'éloigne d'un poste bureautique simple, à un seul disque dur, dont l'utilisation ne change pas dans le temps. Cependant, RAID et LVM constituent deux directions différentes, chacune ayant sa finalité, et l'on peut se demander lequel de ces systèmes adopter. La réponse dépendra des besoins, présents et futurs.
Dans certains cas simples, la question ne se pose pas vraiment. Si l'on souhaite immuniser des données contre des pannes de matériel, on ne pourra que choisir d'installer du RAID sur un ensemble redondant de disques, puisque LVM ne répond pas à cette problématique. Si au contraire il s'agit d'assouplir un schéma de stockage et de rendre des volumes indépendants de l'agencement des disques qui les composent, RAID ne pourra pas aider et l'on choisira donc LVM.
Un troisième cas est celui où l'on souhaite juste agréger deux disques en un, que ce soit pour des raisons de performance ou pour disposer d'un seul système de fichiers plus gros que chacun des disques dont on dispose. Ce problème peut être résolu aussi bien par la mise en place d'un ensemble RAID-0 (voire linéaire) que par un volume LVM. Dans cette situation, à moins de contraintes spécifiques (par exemple pour rester homogène avec le reste du parc informatique qui n'utilise que RAID), on choisira le plus souvent LVM. La mise en place initiale est légèrement plus complexe, mais elle est un bien maigre investissement au regard de la souplesse offerte par la suite, si les besoins changent ou si l'on désire ajouter des disques.
Vient enfin le cas le plus intéressant, celui où l'on souhaite concilier de la tolérance de pannes et de la souplesse dans l'allocation des volumes. Chacun des deux systèmes étant insuffisant pour répondre à ces besoins, on va devoir faire appel aux deux en même temps — ou plutôt, l'un après l'autre. L'usage qui se répand de plus en plus depuis la maturité des deux systèmes est d'assurer la sécurité des données d'abord, en groupant des disques redondants dans un petit nombre de volumes RAID de grande taille, et d'utiliser ces volumes RAID comme des éléments physiques pour LVM pour y découper des partitions qui seront utilisées pour des systèmes de fichiers. Ceci permet, en cas de défaillance d'un disque, de n'avoir qu'un petit nombre d'ensembles RAID à reconstruire, donc de limiter le temps d'administration.
Prenons un exemple concret : le département des relations publiques de Falcot SA a besoin d'une station de travail adaptée au montage vidéo. En revanche, les contraintes de budget du département ne permettent pas d'investir dans du matériel neuf entièrement haut de gamme. Le choix est fait de privilégier le matériel spécifiquement graphique (écran et carte vidéo) et de rester dans le générique pour les éléments de stockage. Or la vidéo numérique, comme on le sait, a des besoins en stockage particuliers : les données à stocker sont volumineuses et la vitesse de lecture et d'écriture de ces données est importante pour les performances du système (plus que le temps d'accès moyen, par exemple). Il faut donc répondre à ces contraintes avec du matériel générique, en l'occurrence deux disques durs SATA de 300 Go, tout en garantissant la disponibilité du système et de certaines des données. Les films montés doivent en effet rester disponibles, mais les fichiers bruts non encore montés sont moins critiques, puisque les rushes restent sur les bandes.
Le choix se porte donc sur une solution combinant RAID-1 et LVM. Les deux disques sont montés sur deux bus IDE différents (afin d'optimiser les accès parallèles et limiter les risques de panne simultanée) et apparaissent donc comme hda et hdc. Le schéma de partitionnement, identique sur les deux disques, sera le suivant :
# fdisk -l /dev/hda

Disque /dev/hda: 300.0 Go, 300090728448 octets
255 têtes, 63 secteurs/piste, 36483 cylindres
Unités = cylindres de 16065 * 512 = 8225280 octets

Périphér.   Amorce  Début      Fin      Blocs    Id  Système
/dev/hda1   *           1      124      995998+  fd  Linux raid autodetect
/dev/hda2             125      248      996030   82  Linux swap 
/dev/hda3             249    36483   291057637+   5  Extended
/dev/hda5             249    12697    99996561   fd  Linux raid autodetect
/dev/hda6           12698    25146    99996561   fd  Linux raid autodetect
/dev/hda7           25147    36483    91064421   8e  Linux LVM
  • La première partition de chaque disque (environ 1 Go) est utilisée pour assembler un volume RAID-1, md0. Ce miroir est utilisé directement pour stocker le système de fichiers racine.
  • Les partitions hda2 et hdc2 sont utilisées comme partitions d'échange, pour fournir un total de 2 Go de mémoire d'échange. Avec 1 Go de mémoire vive, la station de travail dispose ainsi d'une quantité confortable de mémoire.
  • Les partitions hda5 et hdc5 d'une part, hda6 et hdc6 d'autre part sont utilisées pour monter deux nouveaux volumes RAID-1 de 100 Go chacun, md1 et md2. Ces deux miroirs sont initialisés comme des volumes physiques LVM et affectés au groupe de volumes vg_raid. Ce groupe de volumes dispose ainsi d'environ 200 Go d'espace sécurisé.
  • Les partitions restantes, hda7 et hdc7, sont directement initialisées comme des volumes physiques et affectées à un autre VG, vg_vrac, qui pourra contenir presque 200 Go de données.
Une fois les VG établis, il devient possible de les découper de manière très flexible, en gardant à l'esprit que les LV qui seront créés dans vg_raid seront préservés même en cas de panne d'un des deux disques, à l'opposé des LV pris sur vg_vrac ; en revanche, ces derniers seront alloués en parallèle sur les deux disques, ce qui permettra des débits élevés lors de la lecture ou de l'écriture de gros fichiers.
On créera donc des volumes logiques lv_usr, lv_var, lv_home sur vg_raid, pour y accueillir les systèmes de fichiers correspondants ; on y créera également un lv_films, d'une taille conséquente, pour accueillir les films déjà montés. L'autre VG sera quant à lui utilisé pour un gros lv_rushes, qui accueillera les données directement sorties des caméras numériques, et un lv_tmp, pour les fichiers temporaires. Pour l'espace de travail, la question peut se poser : certes, il est important qu'il offre de bonnes performances, mais doit-on pour autant courir le risque de perdre le travail effectué si un disque défaille alors qu'un montage n'est pas fini ? C'est un choix à faire ; en fonction de ce choix, on créera le LV dans l'un ou l'autre VG.
On dispose ainsi à la fois d'une certaine redondance des données importantes et d'une grande flexibilité dans la répartition de l'espace disponible pour les différentes applications. Si de nouveaux logiciels doivent être installés par la suite (pour des montages sonores, par exemple), on pourra aisément agrandir l'espace utilisé par /usr/.