Skip to content

Niveau 8 · Chapitre 8.4

Disques durs, SSD et RAID

Comment on garde les bits quand le courant est coupé : la géométrie et les temps d’accès d’un disque dur avec un exemple chiffré, de l’IDE et du SCSI au SATA et au NVMe, comment un SSD cache les bizarreries de la mémoire flash derrière une couche de traduction, le SSD de ce Mac mesuré, et les niveaux de RAID de 0 à 10, avec une parité XOR qui reconstruit un disque perdu en direct.

La mémoire principale oublie tout quand le courant est coupé, et elle n’est jamais assez grande. En dessous d’elle dans la hiérarchie mémoire — la pyramide que le chapitre sur les caches a gravie depuis le sommet — se trouve la mémoire secondaire : plus lente, bien plus grande, moins chère par octet, et non volatile. Pendant cinquante ans, cela a voulu dire des disques magnétiques en rotation. Aujourd’hui, ce sont surtout des SSD (solid-state drives) faits de mémoire flash, les disques durs étant gardés pour la capacité en masse. Ce chapitre regarde comment fonctionnent les uns et les autres, quelle est leur vitesse réelle, et comment le RAID en combine plusieurs pour que la perte de l’un ne fasse rien perdre.

Le disque dur

Un disque dur (HDD) stocke les bits sous forme de minuscules régions aimantées à la surface de plateaux en rotation. Une tête qui flotte à quelques nanomètres au-dessus de chaque surface aimante ces régions pour écrire et les détecte pour lire (Stocker un bit, au niveau de la physique, traite du magnétisme). Toutes les têtes sont montées sur un même bras qui les déplace ensemble sur les surfaces.

La géométrie en découle :

  • Une piste est l’anneau de bits qui passe sous une tête tant que le bras ne bouge pas.
  • Chaque piste est divisée en secteurs, la plus petite unité que le disque lit ou écrit. Chaque secteur contient un préambule de synchronisation, les données et un code correcteur d’erreurs — un code de Reed–Solomon ou plus puissant encore, pour qu’une rayure ou un point faible puisse être corrigé (l’idée est expliquée dans le chapitre des fondations sur la correction d’erreurs).
  • L’ensemble des pistes situées sous toutes les têtes pour une position du bras forme un cylindre.
  • Les pistes extérieures sont plus longues que les pistes intérieures, donc les disques utilisent des zones : plus une piste est à l’extérieur, plus elle contient de secteurs. Le disque tourne à vitesse constante, donc les pistes extérieures débitent les données plus vite.

Tanenbaum décrit des secteurs de 512 octets. C’était la norme jusque vers 2010 ; depuis, les disques utilisent des secteurs physiques de 4 096 octets, l’Advanced Format, qui demandent moins de place en espacements et en codes par octet stocké. Beaucoup font encore semblant d’avoir des secteurs de 512 octets par compatibilité, et effectuent en interne une lecture–modification–écriture quand l’hôte écrit moins de 4 Kio. Les plus gros disques actuels utilisent l’enregistrement magnétique assisté par la chaleur (HAMR), où un laser chauffe brièvement chaque point au moment où il est écrit : en 2025, Seagate a annoncé des disques allant jusqu’à 36 To, faits de dix plateaux de 3,6 To chacun. Beaucoup de gros disques sont scellés et remplis d’hélium au lieu d’air, ce qui permet à des plateaux plus fins de tourner avec moins de turbulences.

Combien de temps prend une lecture

La lecture d’un secteur se fait en trois étapes :

  1. Positionnement (seek) : amener le bras sur le bon cylindre. En moyenne sur des positions aléatoires, cela prend plusieurs millisecondes.
  2. Latence de rotation : attendre que le secteur arrive sous la tête. En moyenne, cela représente un demi-tour.
  3. Transfert : lire les bits pendant qu’ils défilent.

Faisons le calcul pour un disque à 7 200 tr/min, en supposant un temps de positionnement moyen de 8 ms et un débit soutenu de 200 Mo/s (deux valeurs typiques, mais ce sont des hypothèses, pas des mesures) :

ÉtapeCalculTemps
un tour60 s / 7 2008,33 ms
latence de rotationun demi-tour4,17 ms
positionnementsupposé8 ms
transfert de 4 Kio4 096 o / 200 Mo/s0,02 ms
total12,2 ms

Une lecture aléatoire de 4 Kio prend environ 12 ms, donc le disque en fait environ 82 par seconde — 0,34 Mo/s. Lisez les mêmes données séquentiellement et elles défilent à 200 Mo/s, 600 fois plus vite. Presque tout le temps part dans la mécanique : le transfert représente 0,2 % du total. C’est pourquoi les systèmes de fichiers et les bases de données se donnent tant de mal pour garder ensemble sur le disque les données liées, et pourquoi un disque dur comme disque système rendait les ordinateurs si lents à l’usage.

Tanenbaum cite des vitesses de rotation de 5 400, 7 200 et 10 800 tr/min. Les disques rapides pour entreprises tournaient en réalité à 10 000 et 15 000 tr/min, et ils ont pratiquement disparu : un SSD les bat sur tous les plans sauf la capacité par dollar. Les disques encore vendus tournent à 5 400–7 200 tr/min et rivalisent sur la capacité.

De l’IDE et du SCSI au SATA et au NVMe

Le livre consacre plusieurs pages à l’IDE, à l’EIDE, à l’ATA et au SCSI, les interfaces à câble parallèle des années 1980–2000. Elles appartiennent aujourd’hui à l’histoire, mais quelques-unes de leurs idées leur ont survécu :

  • L’adressage logique de blocs (LBA) : au lieu de numéros de cylindre, de tête et de secteur, le disque présente un tableau plat de blocs numérotés à partir de 0, et gère lui-même la géométrie. Avec des LBA de 48 bits et des blocs de 512 octets, la limite est de 128 Pio, bien au-delà des disques actuels.
  • Le SATA (serial ATA), que le livre annonce comme l’avenir, s’est bien imposé. Sa troisième génération fonctionne à 6 Gbit/s, ce qui, une fois déduit le surcoût du codage, transporte au plus environ 600 Mo/s.
  • Le jeu de commandes SCSI a survécu au bus SCSI : le SAS (serial attached SCSI) est l’interface des disques de serveurs, et les périphériques de stockage USB transportent eux aussi des commandes SCSI.

Les disques rapides d’aujourd’hui se passent de tout cela et utilisent le NVMe (non-volatile memory express), un protocole conçu pour la flash, sur PCI Express. L’interface de commandes du SATA a été conçue pour un disque qui ne fait qu’une chose à la fois ; le NVMe donne au disque jusqu’à 65 535 files d’attente de jusqu’à 65 536 commandes chacune, si bien que chaque cœur peut soumettre ses requêtes dans sa propre file sans verrou, et que le disque peut en traiter des centaines en parallèle. Ce parallélisme, comme on va le mesurer plus loin, est exactement ce dont la flash a besoin.

À l’intérieur d’un SSD

Un SSD stocke les bits sous forme de charge électrique piégée dans des cellules de flash NAND : des transistors dotés d’une couche de stockage supplémentaire, isolée. La charge présente dans cette couche décale la tension à laquelle le transistor devient passant, et le disque lit le bit en testant ce seuil. Le fonctionnement des cellules en tant que puces est traité dans le chapitre sur les puces SRAM, DRAM, ROM et flash, au niveau de la logique numérique ; ici, on regarde le disque construit à partir d’elles.

La flash a trois propriétés gênantes :

  1. Les lectures et les écritures portent sur des pages — en général de 4 à 16 Kio —, pas sur des octets.
  2. Une page ne peut pas être réécrite. Avant d’y écrire à nouveau, il faut l’effacer, et l’effacement ne porte que sur un bloc entier de centaines de pages, plusieurs mégaoctets.
  3. Chaque bloc s’use au bout d’un nombre limité de cycles de programmation/effacement.

Un SSD cache ces trois défauts derrière une couche de traduction flash (flash translation layer, FTL), un micrologiciel qui tourne sur le processeur du disque lui-même. L’hôte voit un tableau ordinaire de blocs logiques. La FTL tient une table de correspondance entre chaque bloc logique et une page physique, et :

  • Les écritures vont dans des pages neuves. Réécrire le bloc logique 42 écrit les nouvelles données dans une page déjà effacée, ailleurs, met à jour la table et marque l’ancienne page comme périmée. Aucun effacement n’est nécessaire pendant l’écriture.
  • Le ramasse-miettes (garbage collection) tourne en arrière-plan : il choisit un bloc contenant beaucoup de pages périmées, recopie ailleurs ses pages encore valides, puis l’efface. Le disque garde une capacité de réserve, le sur-approvisionnement (over-provisioning), pour qu’il y ait toujours un endroit où écrire.
  • La répartition de l’usure (wear leveling) distribue les effacements uniformément sur tous les blocs, y compris ceux qui contiennent des données qui ne changent jamais, et qu’elle déplace de temps en temps.

Le système de fichiers aide grâce à la commande TRIM (appelée deallocate en NVMe) : quand un fichier est supprimé, le système d’exploitation indique au disque quels blocs logiques ne contiennent plus rien d’utile, pour que le ramasse-miettes ne perde pas son temps à recopier des données mortes. Sur ce Mac, system_profiler SPNVMeDataType affiche le disque interne et TRIM Support: Yes.

Une cellule peut stocker plus d’un bit en distinguant davantage de niveaux de charge : le SLC stocke 1 bit par cellule (2 niveaux), le MLC 2 bits (4 niveaux), le TLC 3 bits (8 niveaux) et le QLC 4 bits (16 niveaux). Plus de bits par cellule, c’est moins cher par gigaoctet, mais les niveaux sont plus rapprochés, donc les lectures sont plus lentes et les cellules supportent moins de cycles d’effacement. Depuis le milieu des années 2010, la flash est aussi construite en trois dimensions : les cellules sont empilées sur plus d’une centaine de couches, parfois plusieurs centaines, sur une même puce.

Ce que dit le livre sur les SSD, et ce qui a changé

La section de Tanenbaum sur les SSD date du début des années 2010, et plusieurs points sont à corriger :

  • Il dit qu’une cellule est programmée par injection de porteurs chauds. C’est ainsi qu’on programme la flash NOR ; la flash NAND des SSD est programmée et effacée par effet tunnel Fowler–Nordheim, où un champ intense fait traverser l’isolant mince aux électrons. Et la plupart des flash NAND 3D n’utilisent pas du tout de grille flottante conductrice, mais une couche isolante à piégeage de charge (charge trap) qui maintient les électrons en place.
  • Il donne une endurance d’environ 100 000 écritures par cellule. C’est un chiffre de flash SLC. La plupart des SSD actuels utilisent des cellules TLC ou QLC, prévues pour environ un millier à quelques milliers de cycles de programmation/effacement ; ce sont la répartition de l’usure et le sur-approvisionnement qui rendent cela suffisant.
  • Les « cellules flash multiniveaux » codent plusieurs bits par cellule, et non « par octet » comme le dit le livre, et elles vont désormais jusqu’à quatre bits, pas deux.
  • Il dit qu’un SSD est « deux à trois fois plus rapide » qu’un disque à 100 Mo/s, et coûte « un à trois dollars par gigaoctet ». Le prix a baissé d’un ordre de grandeur ou plus depuis, et la vitesse a augmenté bien davantage, comme le montre la section suivante.

Mesuré : le SSD de ce Mac

Le M2 Ultra sur lequel ce chapitre a été écrit a un SSD interne de 1 To (APPLE SSD AP1024Z) ; son contrôleur flash est intégré à la puce M2 Ultra, et macOS le présente comme un disque NVMe. diskutil info / affiche Solid State: Yes et un Device Block Size de 4 096 octets.

Un petit programme C l’a mesuré. Il écrit un fichier de 2 Gio avec F_NOCACHE (pour que macOS ne garde pas les données dans son cache de pages), suivi de F_FULLFSYNC (pour que les données atteignent vraiment la flash), le relit séquentiellement par morceaux de 8 Mio, puis effectue 20 000 lectures aléatoires de 4 Kio, une à la fois. Six exécutions :

TestRésultat
écriture séquentielle956–1 412 Mo/s sur cinq exécutions, 240 Mo/s sur une
lecture séquentielle5,0–5,4 Go/s
lecture aléatoire de 4 Kio, une à la fois9 700–11 300 par seconde ; latence médiane de 80–85 µs

Le disque était plein à 98 % pendant le test, ce qui laisse peu de place libre à la FTL pour le ramasse-miettes, et explique probablement l’irrégularité des écritures — l’exécution lente était la toute première. Les lectures étaient stables.

Ce sont les lectures aléatoires qui sont intéressantes. 82 µs par lecture aléatoire, contre environ 12 ms pour le disque dur plus haut : environ 150 fois plus rapide, sans aucune pièce mobile. Mais 10 000 lectures par seconde de 4 Kio ne font qu’environ 40 Mo/s, bien loin des 5 Go/s séquentiels. Le disque attend, lui aussi : une lecture à la fois ne peut pas faire travailler en parallèle ses nombreuses puces flash. Un second programme a émis les mêmes lectures depuis plusieurs threads à la fois :

Threads émettant des lecturesLectures aléatoires de 4 Kio par seconde
1environ 12 000 (4 100 lors d’une exécution)
4environ 49 000
16126 000–141 000
32141 000–156 000

Avec 16 requêtes en cours, le disque fait plus de dix fois plus de lectures par seconde. La latence de chaque lecture change à peine ; le disque en traite simplement beaucoup à la fois. C’est à cela que servent les files profondes du NVMe, et c’est pourquoi les logiciels de stockage gardent de nombreuses requêtes en cours. Les fichiers de test ont été supprimés après chaque exécution.

Le RAID

En 1988, Patterson, Gibson et Katz ont proposé de remplacer un gros disque coûteux par un ensemble redondant de disques bon marché (redundant array of inexpensive disks) — le RAID —, qui apparaît comme un seul disque au système d’exploitation mais répartit les données sur plusieurs. L’industrie a plus tard remplacé « inexpensive » par « independent ». Les différentes organisations s’appellent des niveaux de RAID, bien que, comme le note Tanenbaum, ce soient des variantes et non une hiérarchie.

NiveauOrganisationCapacité utile (n disques)Survit à
0entrelacement (striping) : les bandes consécutives vont sur des disques consécutifsnaucune panne
1miroir (mirroring) : chaque bande est écrite sur deux disquesn/2un disque par paire
5entrelacement plus une bande de parité par agrégat, qui tourne d’un disque à l’autren − 1n’importe quel disque
6entrelacement plus deux bandes de parité indépendantesn − 2deux disques quelconques
10un entrelacement (RAID 0) sur des paires en miroir (RAID 1)n/2un disque par paire

Le RAID 0 est rapide pour les gros transferts, puisque tous les disques travaillent en parallèle, mais la moindre panne fait tout perdre : avec quatre disques, une panne est quatre fois plus probable qu’avec un seul. Le RAID 1 lit l’une ou l’autre copie et survit trivialement à une panne, au prix de la moitié de la capacité. Tanenbaum décrit aussi les niveaux 2, 3 et 4. Les niveaux 2 et 3 répartissent chaque mot bit par bit sur des disques qui tournent en synchronisme ; plus personne ne les construit. Le niveau 4 est un niveau 5 dont toute la parité est sur un seul disque, qui devient un goulet d’étranglement pour les écritures ; les systèmes de stockage de NetApp sont les utilisateurs les plus connus d’une variante de ce niveau.

La parité par XOR

Le RAID 5 protège les données avec le OU exclusif. La bande de parité est le XOR des bandes de données du même agrégat :

P = D0 ⊕ D1 ⊕ D2

Comme x ⊕ x = 0, n’importe quelle bande est le XOR de toutes les autres, parité comprise. Si le disque 1 meurt, D1 = D0 ⊕ D2 ⊕ P. Pour trois bandes contenant les octets RAID, five et XOR!, le premier octet de chacune donne :

D0 'R'   01010010
D1 'f'   01100110
D2 'X'   01011000
P        01101100   (0x6c) = D0 ^ D1 ^ D2

et le XOR de D0, D2 et P redonne 01100110, le f perdu. La même chose, exécutée sur l’émulateur — trois disques de données de quatre octets, un disque de parité, puis le disque 1 effacé et reconstruit :

Live · Parité RAID 5 : perdre un disque, le reconstruire par XOR

À essayer : Appuyez sur Step pour exécuter une instruction, Run pour animer ou Continue pour aller au bout ; les boutons L2 à L7 changent de niveau, vers le bas ou le haut.

C source — click a line number for a breakpoint
  1. char disk[4][4]; /* 3 data disks + 1 parity disk, 4 bytes each */
  2. int main() {
  3. strcpy(disk[0], "RAI");
  4. strcpy(disk[1], "D-5");
  5. strcpy(disk[2], "ok!");
  6. for (int i = 0; i < 4; i++) /* parity = D0 ^ D1 ^ D2 */
  7. disk[3][i] = disk[0][i] ^ disk[1][i] ^ disk[2][i];
  8. memset(disk[1], 0, 4); /* disk 1 dies */
  9. for (int i = 0; i < 4; i++) /* rebuild it from the survivors */
  10. disk[1][i] = disk[0][i] ^ disk[2][i] ^ disk[3][i];
  11. printf("rebuilt: %s\n", disk[1]);
  12. return disk[3][0] & 0xff;
  13. }
step 0
Loading emulator…
Your program as you wrote it: the current line, its variables by name, and its output.

Il affiche rebuilt: D-5 et se termine avec le code 121, le premier octet de parité : 'R' ⊕ 'D' ⊕ 'o' = 0x52 ⊕ 0x44 ⊕ 0x6F = 0x79. La parité, c’est un XOR par octet, fait par l’ALU ou par des instructions vectorielles sur de nombreux octets à la fois, donc son calcul ne coûte presque rien.

Une seule bande de parité ne peut réparer qu’une bande manquante connue — un effacement (erasure) —, pas trouver une erreur inconnue. Cela suffit pour le RAID : quand un disque meurt, le contrôleur sait lequel.

La pénalité des petites écritures

Mettre à jour une bande en RAID 5 n’oblige pas à lire tout l’agrégat. Puisque P est un XOR, la nouvelle parité vaut :

P_new = P_old ⊕ D_old ⊕ D_new

Dans l’exemple, remplacer five par six! fait passer la parité de 6c 67 6d 00 à 79 67 63 44, qu’on la recalcule à partir de toutes les bandes ou à partir de l’ancienne parité, des anciennes données et des nouvelles. Mais cela coûte quand même quatre opérations disque pour une seule écriture logique : lire les anciennes données, lire l’ancienne parité, écrire les nouvelles données, écrire la nouvelle parité. C’est la pénalité des petites écritures que décrit Tanenbaum, et c’est pourquoi les bases de données qui font beaucoup de petites écritures préfèrent le RAID 10.

Le RAID 6 et les temps de reconstruction

Le RAID 6 ajoute une seconde bande de parité, calculée non par XOR mais par un code de Reed–Solomon sur les octets, pour que deux bandes perdues quelconques puissent être recalculées. C’est devenu la norme pour les ensembles de gros disques durs, pour une raison que le livre ne pouvait pas souligner en 2013 : reconstruire un disque en panne, c’est lire chaque secteur de chaque disque survivant. À 200 Mo/s, rien que lire un disque de 36 To prend 50 heures, et plus encore si l’ensemble continue de servir pendant la reconstruction. Une seconde panne, ou un secteur illisible, pendant cette fenêtre ferait perdre des données avec une seule parité.

Le RAID n’est pas une sauvegarde. Il protège contre la panne d’un disque, pas contre la suppression d’un fichier, un bogue qui corrompt des données ou un rançongiciel : tout cela est fidèlement écrit sur chaque disque. Les bandes magnétiques du chapitre suivant sont une réponse à ce problème.

À retenir

  • Un disque dur lit un secteur en se positionnant, en attendant en moyenne un demi-tour, puis en transférant. Pour un disque à 7 200 tr/min avec un positionnement de 8 ms, une lecture aléatoire de 4 Kio prend environ 12 ms : 82 par seconde, contre 200 Mo/s en séquentiel.
  • Les secteurs font aujourd’hui 4 Kio (les 512 octets du livre datent d’avant 2010) ; l’IDE, l’EIDE et le SCSI parallèle appartiennent à l’histoire ; le SATA plafonne vers 600 Mo/s ; les disques rapides utilisent le NVMe sur PCIe, avec des milliers de files.
  • La couche de traduction flash d’un SSD redirige chaque écriture vers une page neuve, fait tourner le ramasse-miettes sur les blocs d’effacement, répartit l’usure et exploite TRIM. La NAND est programmée par effet tunnel (et non par injection de porteurs chauds comme le dit le livre), et les cellules TLC/QLC supportent des milliers de cycles, pas 100 000.
  • Mesuré sur le SSD de ce Mac : 5,0–5,4 Go/s en lecture séquentielle, environ 1–1,4 Go/s en écriture, et 80–85 µs par lecture aléatoire, 150 fois plus rapide que le disque dur ; des requêtes parallèles font passer les lectures aléatoires d’environ 12 000 à plus de 140 000 par seconde.
  • Le RAID 0 entrelace, le 1 met en miroir, le 5 ajoute une parité XOR (toute bande = XOR des autres), le 6 ajoute une seconde parité, de Reed–Solomon, le 10 entrelace des miroirs. Les petites écritures du RAID 5 coûtent quatre E/S. Le RAID n’est pas une sauvegarde.

Dans ce niveau

  1. 8.1Le transistor comme interrupteur
  2. 8.2Construire des portes en CMOS
  3. 8.3Du sable à la puce
  4. 8.4Disques durs, SSD et RAID
  5. 8.5Disques optiques et bandes
  6. 8.6Claviers, écrans, imprimantes et caméras
  7. 8.7Des modems à Ethernet : envoyer des bits sur un fil