Rien ne gâche plus une garde tranquille que « nous avons acheté deux téraoctets de cache NVMe et les performances ont empiré ». On regarde les graphiques : les disques ont l’air en forme, les CPU semblent désœuvrés, et la latence fait toujours des pics comme si elle était payée au milliseconde.
L2ARC est le réglage le plus tentant dans ZFS parce qu’il ressemble à un échange simple : du flash rapide et bon marché remplace de la RAM coûteuse. En production, c’est plus compliqué. Parfois 200 Go de L2ARC sont une victoire claire. Parfois 2 To ne servent qu’à chauffer un NVMe coûteux tout en pompant votre RAM.
Le modèle mental : ce qu’est vraiment L2ARC
ARC est votre cache de premier niveau : en mémoire, rapide et fortement optimisé. L2ARC n’est pas « l’ARC sur SSD ». C’est un cache de deuxième niveau pour des blocs qui ont déjà été dans l’ARC et qui ont été évincés. Ce détail change tout.
ARC et L2ARC ne résolvent pas les mêmes problèmes
ARC est l’endroit où ZFS veut idéalement être. Il met en cache les blocs récents et fréquemment utilisés, les métadonnées, et il s’adapte entre MRU (récent) et MFU (fréquent). Les hits ARC sont bon marché.
L2ARC est un cache « victim ». Il stocke des données que l’ARC n’a pas pu garder. Ça signifie que L2ARC n’aide que lorsque :
- Votre charge de travail a un jeu de travail plus grand que la RAM, mais suffisamment petit pour tenir de manière utile dans L2ARC.
- Il y a de la réutilisation. L2ARC ne sert à rien pour des lectures « one-and-done ».
- La pénalité de manque sur les disques est suffisamment élevée pour qu’un hit SSD soit nettement meilleur.
Voici la partie qu’on oublie : L2ARC consomme de la RAM pour stocker des pointeurs SSD
L2ARC maintient des métadonnées en RAM qui mappent les en-têtes ARC aux blocs stockés sur le périphérique L2. Un L2ARC plus grand implique plus de métadonnées en mémoire. Si ces métadonnées comprimment l’ARC, vous risquez de perdre plus que vous ne gagnez.
De plus, remplir L2ARC n’est pas gratuit. Cela consomme de la bande passante I/O et des cycles CPU pour écrire sur le périphérique de cache. Sous forte churn, ça peut devenir une pression auto-infligée.
Ce que vous dimensionnez réellement
Quand vous « dimensionnez L2ARC », vous équilibrez :
- Gain de taux de hits (combien de lectures évitent le média plus lent)
- Réduction de l’ARC (RAM consommée par les métadonnées L2ARC et le comportement d’alimentation)
- Amplification d’écriture (écritures de remplissage L2ARC ; plus toute option de persistance)
- Profil de latence (NVMe est rapide, mais pas gratuit ; et tous les misses ne se valent pas)
- Comportement en cas de défaillance et de récupération (temps de réchauffement du cache ; impacts au redémarrage ; perte de périphérique)
Idée paraphrasée de Werner Vogels (CTO d’Amazon) : Tout échoue, tout le temps — concevez et opérez en partant de ce principe.
Cela s’applique aussi aux caches. L2ARC est une optimisation de performance. Traitez-le comme un feature flag avec un plan de sortie.
Faits intéressants et un peu d’histoire
Un peu de contexte rend les réglages moins mystiques. Faits courts et concrets :
- L2ARC a été introduit tôt dans Solaris ZFS comme moyen d’étendre le cache au-delà de la RAM, initialement ciblé sur les dispositifs flash d’entreprise.
- ARC précède l’engouement moderne pour « page cache + eviction sophistiquée » ; ZFS a construit un cache cohérent avec sa propre logique d’éviction plutôt que de s’appuyer entièrement sur le page cache de l’OS.
- Historiquement, L2ARC n’était pas persistant : un reboot signifiait un cache froid et un long réchauffement ; plus tard OpenZFS a ajouté des options de persistance L2ARC sur certaines plateformes.
- Les premiers designs L2ARC étaient limités par l’endurance SSD ; alimenter L2ARC pouvait écrire beaucoup plus que prévu.
- Le coût en métadonnées a toujours été la taxe ; au fur et à mesure que l’ARC devenait plus intelligent (et plus grand), L2ARC est parfois devenu moins convaincant pour des charges générales.
- L2ARC ne met en cache que les lectures ; il n’accélère pas les écritures synchrones (c’est le domaine du SLOG, et là encore c’est nuancé).
- Les vdevs spéciaux ont changé la donne : placer les métadonnées (et éventuellement les petits blocs) sur du flash peut battre L2ARC car cela change où les données résident, pas seulement où elles sont en cache.
- NVMe a rendu « L2ARC énorme » abordable, d’où de plus en plus de cas où les gens le surdimensionnent et découvrent la facture RAM/métadonnées.
Pourquoi 200 Go peut battre 2 To
Le titre n’est pas une astuce. Un L2ARC plus petit gagne souvent parce que le caching porte sur la densité de réutilisation, pas la capacité brute. Si vous mettez en cache beaucoup de blocs qui ne seront pas réutilisés, vous avez construit une décharge très rapide.
1) Votre jeu de travail a un « noyau chaud » et une « queue froide »
La plupart des charges de production ont ça. Pensez : tempêtes de démarrage de VM versus données utilisateurs anciennes ; index de base de données versus tables historiques ; artéfacts de build versus artéfacts de la semaine dernière.
Un L2ARC de 200 Go qui contient le noyau chaud des évictions ARC peut fournir un taux de hits élevé. Un L2ARC de 2 To peut embarquer aussi la queue froide, gaspillanter les métadonnées en RAM et la bande passante de feed. Quand ça arrive, l’ARC rétrécit, les métadonnées chaudes tombent, et vous perdez les hits ARC les moins coûteux.
2) L2ARC concurrence indirectement l’ARC pour la RAM
La performance ZFS dépend souvent de la mémoire. Pas un simple « plus de mémoire c’est mieux » — spécifiquement : avez-vous assez d’ARC pour garder les métadonnées et vos blocs chauds en mémoire ?
Un grand L2ARC augmente la quantité de bookkeeping en mémoire. Cela réduit l’espace effectif de l’ARC pour les données réellement mises en cache. Si les misses ARC augmentent quand vous agrandissez L2ARC, vous pouvez régresser.
3) L2ARC a un taux de remplissage ; les très gros caches ne suivent pas
L2ARC se remplit progressivement. Si votre charge parcourt des données plus vite que L2ARC ne peut se peupler, le cache ne devient jamais représentatif. Vous payez pour le remplir sans obtenir assez de hits en retour.
Un L2ARC plus petit chauffe plus vite et reste pertinent. Dans des environnements avec redémarrages fréquents, basculements ou maintenances, le temps de réchauffement n’est pas académique.
4) Tous les « hits » ne se valent pas
Même un taux de hits L2ARC parfait peut être un mauvais deal si le goulot d’étranglement n’est pas la lecture depuis un média lent. Si vous êtes lié CPU (compression, chiffrement, checksums), ou verrouillé par une application mono-thread, la capacité L2ARC ne réparera pas ça.
5) La pénalité de lecture aléatoire est là où L2ARC justifie son coût
Si votre pool repose sur des HDD, les lectures aléatoires sont coûteuses, et L2ARC peut être spectaculaire — si les données sont réutilisées. Si votre pool est déjà tout-NVMe, L2ARC devient souvent négligeable. Un grand L2ARC sur un pool rapide peut encore nuire en consommant des métadonnées en RAM et en générant des écritures supplémentaires.
Blague n°1 : Acheter un L2ARC plus grand pour corriger la latence, c’est comme acheter un frigo plus grand pour guérir la faim — vous risquez juste d’avoir plus de restes.
Une méthode de dimensionnement qui ne repose pas sur l’intuition
Si vous ne retenez qu’une règle : ne dimensionnez pas L2ARC en fonction de la taille des disques ; dimensionnez-le par la réutilisation mesurée et la marge mémoire.
Étape 1 : Prouvez que vous avez un problème de misses en lecture
Commencez par répondre à trois questions :
- Sommes-nous limités par la latence des lectures depuis le pool ?
- Les hits ARC sont élevés mais insuffisants, ce qui signifie que le jeu de travail dépasse la RAM ?
- Y a-t-il réutilisation dans le flux d’éviction (c.-à-d. qu’un L2ARC serait réellement touché) ?
Si vous ne pouvez pas le démontrer, la recommandation par défaut est ennuyeuse : ajoutez de la RAM ou corrigez la charge de travail.
Étape 2 : Estimez le jeu de travail « digne de L2 »
Vous cherchez des blocs qui sont :
- Fréquemment accédés, mais pas assez pour rester dans l’ARC sous pression
- Coûteux à récupérer depuis le pool (lectures aléatoires sur HDD, ou latence SAN distante)
- Assez stables pour bénéficier d’un réchauffement du cache
En pratique, cet ensemble « digne de L2 » est souvent beaucoup plus petit que la taille totale des données. Ce peut être 50–300 Go de blocs OS de VM, ou quelques centaines de gigaoctets d’index de base de données, pas « les 12 To de fichiers utilisateurs ».
Étape 3 : Assurez-vous d’une marge mémoire pour les métadonnées ARC et les en-têtes L2ARC
Un L2ARC surdimensionné peut affamer l’ARC. Le signe : la taille de l’ARC cesse de croître, les misses de métadonnées augmentent, et le système devient « saccadé » sous charge.
Règle pratique réellement utilisable : si vous luttez déjà contre la pression ARC, n’ajoutez pas encore de L2ARC. Augmentez la RAM, déplacez les métadonnées sur un vdev spécial, ou réduisez le jeu de travail.
Étape 4 : Choisissez la classe de périphérique et l’endurance comme un adulte
L2ARC s’écrit. Pas constamment comme un journal, mais suffisamment pour compter. Les QLC grand public peuvent convenir pour des caches modestes avec un comportement de remplissage conservateur ; elles peuvent aussi mourir très vite sous des charges à churn élevé.
Choisissez un NVMe avec protection contre la perte d’alimentation si vous tenez à la cohérence lors de coupures. L2ARC est « juste un cache », mais un comportement défaillant du périphérique peut ajouter des modes de panne et des timeouts pénibles.
Étape 5 : Commencez petit, mesurez, puis augmentez
N’installez pas 2 To parce que c’était en promotion. Installez 200–400 Go. Mesurez le taux de hits, la latence, le comportement ARC et la charge d’écriture pendant une semaine. Ensuite décidez d’augmenter.
Blague n°2 : L2ARC, c’est comme un canal Slack de toute l’entreprise — utile quand il est curaté, catastrophe quand tout le monde y déverse tout.
Tâches pratiques : commandes, sorties, décisions (12+)
Voici les vérifications quotidiennes qui vous gardent honnête. Les sorties sont des exemples ; vos chiffres seront différents. L’important est ce que chaque élément vous dit, et la décision qui suit.
Task 1: Confirm pool and vdev layout (because nothing else makes sense without it)
cr0x@server:~$ zpool status -v tank
pool: tank
state: ONLINE
scan: scrub repaired 0B in 00:32:11 with 0 errors on Tue Dec 24 02:14:22 2025
config:
NAME STATE READ WRITE CKSUM
tank ONLINE 0 0 0
raidz2-0 ONLINE 0 0 0
sda ONLINE 0 0 0
sdb ONLINE 0 0 0
sdc ONLINE 0 0 0
sdd ONLINE 0 0 0
sde ONLINE 0 0 0
sdf ONLINE 0 0 0
cache
nvme0n1 ONLINE 0 0 0
errors: No known data errors
Sens : Vous êtes sur des RAIDZ2 HDD avec un NVMe en cache. La pénalité des lectures aléatoires sur HDD est réelle, donc L2ARC peut être utile.
Décision : Si tout était tout-NVMe ou des SSD en miroir, je serais sceptique sur la valeur de L2ARC et me concentrerais d’abord sur l’ARC et la charge.
Task 2: Check ARC size, target, and pressure
cr0x@server:~$ arc_summary | head -n 25
ARC Summary:
Memory Throttle Count: 0
ARC Size: 22.5 GiB
Target Size: 24.0 GiB
Min Size (Hard Limit): 8.0 GiB
Max Size (High Water): 24.0 GiB
Most Recently Used Cache Size: 7.1 GiB
Most Frequently Used Cache Size: 13.8 GiB
Sens : L’ARC est proche du maximum. Ça peut être correct ou signe d’une limitation mémoire.
Décision : Si l’ARC est bloqué au maximum et que votre OS swappe ou que les services manquent de mémoire, n’augmentez pas L2ARC — ajoutez de la RAM ou réduisez l’ARC max seulement si nécessaire.
Task 3: Measure ARC hit ratio and demand data misses
cr0x@server:~$ arcstat 1 5
time read miss miss% dmis dm% pmis pm% mmis mm% arcsz c
12:01:01 8320 410 4 320 3 62 1 28 0 22G 23.8G
12:01:02 8011 398 4 310 3 59 1 29 0 22G 23.8G
12:01:03 8550 460 5 370 4 61 1 29 0 22G 23.8G
12:01:04 7902 402 5 322 4 55 1 25 0 22G 23.8G
12:01:05 8122 405 4 330 4 53 1 22 0 22G 23.8G
Sens : Le taux de misses ARC est d’environ 4–5%, les misses de données à la demande dominent. Ce n’est pas terrible. Si L2ARC aide dépend du coût de ces misses.
Décision : Si miss% est bas et que la latence est toujours mauvaise, suspectez d’autres goulots non liés au stockage. Si miss% est élevé et les lectures sont aléatoires, L2ARC peut aider.
Task 4: Check L2ARC presence and hit ratio
cr0x@server:~$ arc_summary | sed -n '60,110p'
L2ARC Summary:
L2ARC Size: 186.2 GiB
L2ARC Evict Misses: 0
L2ARC Hits: 1823124
L2ARC Misses: 9311042
L2ARC Read Hit Ratio: 16.4%
L2ARC Writes: 412019
Sens : Le taux de hits L2ARC est ~16%. Ça peut avoir de la valeur sur des pools HDD, moins sur des pools SSD.
Décision : Si le taux de hits est en chiffre unique et que le périphérique est occupé, réduisez ou retirez L2ARC et concentrez-vous ailleurs. S’il est >15–30% et que la latence de lecture s’améliore, conservez-le et considérez une croissance modeste.
Task 5: Verify L2ARC feed behavior and whether the device is saturated
cr0x@server:~$ iostat -x 1 3 nvme0n1
Linux 6.8.0 (server) 12/26/2025 _x86_64_ (32 CPU)
avg-cpu: %user %nice %system %iowait %steal %idle
10.12 0.00 3.21 1.02 0.00 85.65
Device r/s rkB/s rrqm/s %rrqm r_await rareq-sz w/s wkB/s w_await wareq-sz aqu-sz %util
nvme0n1 820.0 89200.0 0.0 0.00 0.35 108.78 290.0 38100.0 1.90 131.38 0.80 48.00
Sens : Le NVMe n’est pas saturé (%util 48%). Bien. S’il était proche de 100% avec un w_await élevé, le remplissage L2ARC pourrait nuire.
Décision : Si le périphérique de cache est saturé, limitez le remplissage L2ARC (tunables spécifiques à la plateforme) ou réduisez L2ARC.
Task 6: Confirm whether the pool is actually the latency source
cr0x@server:~$ zpool iostat -v tank 1 3
capacity operations bandwidth
pool alloc free read write read write
---------- ----- ----- ----- ----- ----- -----
tank 38.2T 12.1T 1400 520 180M 62.1M
raidz2-0 38.2T 12.1T 1400 520 180M 62.1M
sda - - 230 90 30.1M 10.2M
sdb - - 240 85 29.8M 10.1M
sdc - - 225 88 29.6M 10.3M
sdd - - 235 86 30.2M 10.4M
sde - - 240 86 30.5M 10.2M
sdf - - 230 85 29.8M 10.1M
cache - - 710 260 86.0M 38.1M
nvme0n1 - - 710 260 86.0M 38.1M
---------- ----- ----- ----- ----- ----- -----
Sens : Le périphérique de cache réalise des lectures significatives. L2ARC paie son loyer.
Décision : Si « cache » montre presque zéro lecture alors que les misses sont élevés, L2ARC n’est pas utilisé (ou ne peut pas chauffer). Investiguer le churn, un mismatch de recordsize, ou une charge streaming.
Task 7: Spot streaming reads that L2ARC won’t help
cr0x@server:~$ zfs get -o name,property,value -s local,default recordsize,primarycache,secondarycache tank/data
NAME PROPERTY VALUE
tank/data primarycache all
tank/data secondarycache all
tank/data recordsize 128K
Sens : Le dataset met en cache ARC et L2ARC et utilise des enregistrements de 128K. Les scans séquentiels larges peuvent pulvériser l’utilité du cache.
Décision : Pour des datasets de streaming/sauvegarde, régler secondarycache=none (ou même primarycache=metadata) pour protéger le cache pour les données sensibles à la latence.
Task 8: Apply per-dataset cache policy (safely, surgically)
cr0x@server:~$ sudo zfs set secondarycache=none tank/backups
cr0x@server:~$ zfs get -o name,property,value secondarycache tank/backups
NAME PROPERTY VALUE
tank/backups secondarycache none
Sens : Les lectures de sauvegarde ne pollueront pas L2ARC. L’ARC peut toujours mettre en cache selon primarycache.
Décision : Faites cela quand vous avez des charges mixtes et que les sauvegardes/reconstitutions écrasent les taux de hit du cache.
Task 9: Check metadata pressure and whether a special vdev is a better answer
cr0x@server:~$ arc_summary | sed -n '25,60p'
ARC Miscellaneous:
Deleted: 112.3 MiB
Mutex Misses: 0
Demand Data Hits: 51234123
Demand Data Misses: 9123421
Demand Metadata Hits: 88123411
Demand Metadata Misses: 923412
Sens : Les misses de métadonnées existent mais n’explosent pas. Si les misses de métadonnées étaient énormes et la latence instable lors des parcours de répertoire/ops VM, un vdev spécial pour métadonnées pourrait dépasser L2ARC.
Décision : Si votre douleur est centrée sur les métadonnées (patterns VMFS-like, beaucoup de petits fichiers, traversées de répertoires), envisagez un vdev spécial avant d’agrandir L2ARC.
Task 10: Verify you’re not confusing SLOG with L2ARC
cr0x@server:~$ zpool status tank | sed -n '1,25p'
pool: tank
state: ONLINE
config:
NAME STATE READ WRITE CKSUM
tank ONLINE 0 0 0
raidz2-0 ONLINE 0 0 0
sda ONLINE 0 0 0
sdb ONLINE 0 0 0
sdc ONLINE 0 0 0
sdd ONLINE 0 0 0
sde ONLINE 0 0 0
sdf ONLINE 0 0 0
logs
nvme1n1 ONLINE 0 0 0
cache
nvme0n1 ONLINE 0 0 0
Sens : Vous avez un périphérique de log séparé (SLOG) et un périphérique de cache (L2ARC). Bonne séparation.
Décision : Si votre souci est la latence d’écriture synchrone et que vous continuez à ajouter L2ARC, arrêtez. Mesurez la charge sync et le comportement du SLOG à la place.
Task 11: Validate that the workload is actually reading (not waiting on locks or CPU)
cr0x@server:~$ pidstat -dru 1 3
Linux 6.8.0 (server) 12/26/2025 _x86_64_ (32 CPU)
12:10:11 UID PID %usr %system %wait %CPU CPU kB_rd/s kB_wr/s Command
12:10:12 999 18322 2.00 0.50 15.00 2.50 6 1200.00 200.00 postgres
12:10:12 0 1421 0.10 0.20 0.00 0.30 2 0.00 0.00 zfs
Sens : L’application montre %wait. Ça peut être de l’attente I/O, mais aussi des verrous selon la pile. C’est un signal à corréler avec la latence du stockage.
Décision : Si le CPU est saturé ou que l’app est bloquée par des verrous, changer la taille du L2ARC ne corrigera pas ça. Ne faites pas de « theatre de cache ».
Task 12: Watch real I/O latency at the device level
cr0x@server:~$ iostat -x 1 3 sda
Device r/s rkB/s r_await w/s wkB/s w_await aqu-sz %util
sda 220.0 30100.0 18.20 85.0 10200.0 6.40 4.10 98.00
sda 235.0 31000.0 21.50 92.0 11000.0 7.10 4.80 99.00
sda 210.0 29000.0 16.80 80.0 9800.0 5.90 3.70 96.00
Sens : Le HDD est saturé et le r_await de lecture est élevé. Si L2ARC peut absorber certaines lectures, vous diminuerez cela.
Décision : Si les HDD sont saturés en lectures, L2ARC aide probablement. Si les HDD sont au repos et que la latence est toujours élevée, votre problème est ailleurs.
Task 13: Confirm compression and recordsize alignment (cache efficiency depends on it)
cr0x@server:~$ zfs get -o name,property,value compression,recordsize tank/pg
NAME PROPERTY VALUE
tank/pg compression lz4
tank/pg recordsize 16K
Sens : recordsize 16K pour un dataset de base de données ; ça peut améliorer la localité et l’utilité du cache pour des patterns OLTP.
Décision : Si vous mettez en cache de gros enregistrements de 1M pour des lectures aléatoires, vous gaspillez le cache. Ajustez recordsize par dataset.
Task 14: Evaluate memory headroom quickly
cr0x@server:~$ free -h
total used free shared buff/cache available
Mem: 128Gi 41Gi 12Gi 1.0Gi 75Gi 78Gi
Swap: 16Gi 0.0Gi 16Gi
Sens : Beaucoup de mémoire disponible ; l’ARC peut être grand sans affamer l’espace utilisateur.
Décision : Si la mémoire disponible est faible et que le swap est actif, corrigez cela d’abord. L2ARC n’est pas un substitut à la RAM quand l’OS suffoque.
Task 15: Baseline L2ARC write rate (endurance reality check)
cr0x@server:~$ sudo smartctl -a /dev/nvme0 | sed -n '1,80p'
SMART/Health Information (NVMe Log 0x02)
Critical Warning: 0x00
Temperature: 41 Celsius
Available Spare: 100%
Percentage Used: 3%
Data Units Read: 18,240,112
Data Units Written: 9,882,441
Host Read Commands: 312,114,901
Host Write Commands: 210,441,022
Sens : « Data Units Written » augmente avec le feed L2ARC et la charge. Suivez-le au fil du temps.
Décision : Si l’endurance du périphérique de cache est consommée rapidement, réduisez le churn L2ARC (politiques dataset, L2ARC plus petit, meilleur dimensionnement ARC) ou utilisez un disque plus durable.
Méthode de diagnostic rapide
Vous êtes en incident. Pas le temps pour des débats philosophiques sur le caching. Voici ce qu’il faut vérifier en premier, deuxième, troisième, pour trouver le goulot sans se mentir.
Premier : est-ce vraiment le stockage ?
- Vérifiez la saturation CPU de l’hôte et la file d’attente. Si le CPU est saturé, le tuning du stockage est une distraction.
- Vérifiez les attentes au niveau application (verrous DB, pools de threads). Les graphiques de stockage peuvent sembler coupables par association.
Deuxième : si c’est le stockage, s’agit-il de lectures, écritures ou métadonnées ?
- Lectures : latence de lecture élevée sur vdevs HDD ; miss% ARC en hausse ; lectures L2ARC significatives.
- Écritures synchrones : pics de latence corrélés aux fsync ; métriques SLOG et latence du périphérique importantes.
- Métadonnées : traversées de répertoire lentes ; opérations VM lentes ; misses de métadonnées élevées ; un vdev spécial peut être préférable.
Troisième : le cache aide-t-il ou nuit-il maintenant ?
- Taille ARC proche du max avec mauvais taux de hits : probablement jeu de travail trop grand ou charge streaming.
- Taux de hits L2ARC faible avec forte utilisation du périphérique : churn de cache ; réduire L2ARC ou exclure des datasets.
- Taux de hits L2ARC correct mais aucune amélioration de latence : le pool est peut-être déjà rapide, ou le goulot est ailleurs.
Quatrième : choisissez le bon levier
- Ajouter de la RAM quand l’ARC est contraint et que les misses de métadonnées font mal.
- Ajouter ou tuner L2ARC quand les misses de lecture sont coûteux et réutilisés.
- Ajouter un vdev spécial quand les métadonnées et les petits blocs dominent.
- Corriger les politiques dataset quand les sauvegardes ou scans polluent le cache.
- Corriger la charge quand les patterns d’accès sont pathologiques (grosses lectures aléatoires, mismatches recordsize, scans non bornés).
Trois mini-récits d’entreprise issus du terrain
Mini-récit 1 : L’incident causé par une mauvaise hypothèse
L’entreprise exploitait un cluster de virtualisation sur un serveur de stockage ZFS : RAIDZ2 HDD pour la capacité, une paire de NVMe pour le « truc performance ». L’équipe a supposé que L2ARC était essentiellement « plus de RAM mais moins cher », alors ils ont taillé la plupart d’un NVMe en une tranche L2ARC de plusieurs téraoctets. Gros chiffre, grand gain. C’était l’hypothèse.
Un mois plus tard, un redémarrage de maintenance habituel est devenu une panne lente. Après le boot, la latence VM était horrible pendant des heures. Pas « un peu dégradée ». Les locataires ont ouvert des tickets. La direction a demandé si l’équipe stockage avait changé quelque chose. La réponse fut « non », techniquement vraie et opérationnellement inutile.
L’histoire réelle : L2ARC portait beaucoup de blocs chauds dont le jeu de travail dépendait pendant les heures ouvrées. Le redémarrage a tout effacé. L’ARC seul ne tenait pas l’ensemble. L2ARC a mis beaucoup de temps à se réchauffer parce que le taux de remplissage ne suivait pas le churn. Pire, pendant le réchauffement il a consommé de la bande passante I/O pour écrire du contenu de cache alors que les locataires attendaient déjà des lectures.
La correction n’a pas été héroïque. Ils ont réduit L2ARC à quelques centaines de gigaoctets pour qu’il chauffe vite, exclu les datasets de sauvegarde du secondarycache, et documenté que les redémarrages impliquent une fenêtre de réchauffement. Résultat surprenant : un L2ARC plus petit a donné des performances plus stables et un temps d’« affreuse période post-redémarrage » plus court.
Mini-récit 2 : L’optimisation qui a mal tourné
Une autre équipe hébergeait un cluster de bases de données sur ZFS. Ils ont constaté des misses en lecture et ont décidé de « tout miser » : L2ARC massif, réglages agressifs pour l’alimenter plus vite, et un NVMe dédié flambant neuf. Les graphiques avaient l’air super pendant un jour. Le taux de hits du cache est monté. Tout le monde se sentait malin.
Puis les plaintes sur la latence d’écriture ont commencé. Pas seulement sur le dataset DB — sur l’hôte entier. Le NVMe dédié montrait une forte utilisation et une latence d’écriture augmentée. Le pool HDD avait l’air plus chargé aussi, même s’ils essayaient de réduire les lectures. L’équipe avait construit une machine qui déplaçait constamment des blocs vers L2ARC, les évincait, puis répétait le processus. Le churn de cache était devenu une charge.
Ils brûlaient aussi de la RAM pour les métadonnées L2ARC, réduisant silencieusement la capacité de l’ARC à garder les vraies métadonnées chaudes. Plus de misses ARC. Plus de trafic disque. Vous devinez la suite.
Le plan de rollback les a sauvés : désactiver le feed agressif, réduire la taille du L2ARC, et déplacer les datasets lourds en métadonnées vers un vdev spécial. Les performances sont revenues au niveau de base. Après cela, ils ont traité L2ARC comme un scalpel, pas un mode de vie.
Mini-récit 3 : La pratique ennuyeuse mais correcte qui a sauvé la mise
Une plateforme média avait une flotte de stockage ZFS avec des charges mixtes : uploads utilisateurs, lectures de transcodage, scans analytiques, et sauvegardes nocturnes. Ils ne faisaient jamais confiance aveuglément aux caches. Ils avaient une pratique établie : chaque dataset à haut débit recevait une politique de cache explicite, et chaque périphérique de cache avait une surveillance d’endurance avec alertes.
Une nuit, les jobs analytiques ont changé et ont commencé à faire de gros scans contre un dataset toujours configuré en secondarycache=all. Le taux de hits L2ARC a chuté, les écritures NVMe ont grimpé, et les charges interactives ont vu une latence plus élevée. Le système n’a pas planté ; il est juste devenu désagréable.
L’on-call a suivi leur runbook : vérifier arcstat, confirmer le churn L2ARC, identifier le dataset par l’horaire de la charge, et basculer la politique dataset. Ils ont mis secondarycache=none sur le dataset analytique et laissé primarycache intact. En quelques minutes, L2ARC s’est stabilisé et les performances interactives ont récupéré.
Pas d’héroïsme. Pas de « on devrait repenser le stockage ». Juste l’hygiène ennuyeuse : politiques de cache par dataset et surveiller le périphérique de cache comme du matériel de production — parce que c’en est.
Erreurs courantes : symptôme → cause → correctif
1) Symptom: performance got worse after adding a huge L2ARC
Cause racine : Le coût des métadonnées L2ARC et le churn de feed réduisent l’ARC effectif et ajoutent des écritures ; le cache stocke des blocs à faible réutilisation.
Correctif : Réduire L2ARC ; exclure les datasets en streaming (secondarycache=none) ; confirmer que l’ARC a de la marge ; envisager d’ajouter de la RAM.
2) Symptom: L2ARC hit ratio is low (single digits) and never improves
Cause racine : Charge streaming/scan, faible réutilisation, cache qui chauffe trop lentement, ou datasets non éligibles pour L2ARC.
Correctif : Identifier les datasets de scan et désactiver secondarycache ; garder L2ARC plus petit ; vérifier les réglages secondarycache ; mesurer le taux de hits sur une fenêtre représentative.
3) Symptom: great L2ARC hit ratio but latency doesn’t improve
Cause racine : Le goulot n’est pas les lectures lentes (CPU, verrous, réseau, écritures sync, vdevs fragmentés). Ou le pool est déjà rapide SSD.
Correctif : Corréler la latence applicative avec le r_await du périphérique ; vérifier le SLOG pour les charges sync ; vérifier CPU et ordonnancement ; arrêter d’acheter du cache inutilement.
4) Symptom: after reboot/failover, system is slow for hours
Cause racine : L2ARC non persistant (ou persistance inefficace) plus cache surdimensionné avec réchauffement lent ; le jeu de travail dépend des blocs en cache.
Correctif : Réduire la taille L2ARC ; s’assurer que la charge supporte un cache froid ; planifier des lectures de warmup si approprié ; documenter le comportement de réchauffement attendu.
5) Symptom: NVMe cache device wears out faster than expected
Cause racine : Churn élevé et écritures continues de feed ; L2ARC utilisé comme dépotoir pour données froides.
Correctif : Réduire la taille du cache ; désactiver L2ARC pour les datasets de scan ; choisir un disque avec endurance adaptée ; surveiller SMART « Percentage Used » et les tendances d’octets écrits.
6) Symptom: directory listings, VM operations, and “small IO” workloads are slow
Cause racine : Charge liée aux métadonnées ; L2ARC aide parfois, mais le placement persistant (vdev spécial) est souvent plus efficace.
Correctif : Envisager un vdev spécial pour métadonnées/petits blocs ; confirmer le comportement des misses de métadonnées ; assurer suffisamment de RAM pour les métadonnées dans l’ARC.
7) Symptom: cache device is at 100% utilization with high write latency
Cause racine : Remplissage L2ARC en compétition avec les lectures ; périphérique de cache trop petit/lent pour le churn ; alimentation agressive.
Correctif : Limiter le taux de feed/tunables quand applicable ; réduire L2ARC ; migrer vers un NVMe plus rapide ; réduire les datasets éligibles.
Listes de contrôle / plan pas-à-pas
Checklist de décision : devriez-vous ajouter L2ARC du tout ?
- Média du pool : majoritairement HDD ou backend à haute latence ? Si oui, L2ARC peut aider. Tout-NVMe ? Soyez sceptique.
- ARC saturé et toujours des misses : Confirmez que l’ARC est proche du max et que les misses importent.
- Réutilisation : Confirmez que la charge revisite les données (pas du pur streaming).
- Marge mémoire : Assurez-vous que l’espace utilisateur ne swappe pas ; l’ARC peut supporter un peu de métadonnées additionnelles.
- Tolérance opérationnelle : Acceptez-vous le réchauffement après reboot ? Sinon, gardez petit ou planifiez la persistance.
Pas-à-pas : dimensionner L2ARC en sécurité
- Base de référence sur 7 jours. Capturez : arcstat miss%, L2ARC hit%, latence des devices du pool, et utilisation du périphérique de cache.
- Définissez les politiques dataset. Excluez d’abord les sauvegardes/scans du L2ARC (
secondarycache=none). - Commencez par 200–400 Go. Préférez « petit et chaud » à « énorme et obsolète ».
- Vérifiez son usage. Consultez
zpool iostatpour les lectures « cache » et le taux de hits L2ARC. - Surveillez le comportement mémoire. Taille ARC, misses de métadonnées, et disponibilité mémoire système.
- Surveillez l’endurance. Suivez les écritures NVMe et le « Percentage Used » au fil du temps.
- Augmentez uniquement avec des preuves. Si le taux de hits s’améliore et la latence baisse sans affamer l’ARC, augmentez par incréments.
- Gardez un plan de rollback. Pouvoir détacher le périphérique de cache et revenir rapidement sur les politiques dataset.
Quand arrêter d’augmenter L2ARC
- Les misses de métadonnées ARC augmentent ou l’ARC rétrécit sensiblement.
- L’utilisation du périphérique de cache augmente sans baisse correspondante de la latence.
- Le taux de hits L2ARC plafonne : les gigaoctets supplémentaires contiennent des blocs de plus en plus froids.
- Le temps de réchauffement devient opérationnellement douloureux.
FAQ
1) L2ARC « en vaut-il la peine » sur un pool tout-SSD ou tout-NVMe ?
Généralement non. Si votre pool sert déjà des lectures aléatoires en dessous de la milliseconde, L2ARC ajoute de la complexité, une surcharge RAM et des écritures pour de petits gains. Travaillez d’abord sur le dimensionnement ARC, le recordsize et l’optimisation de la charge.
2) Pourquoi un L2ARC plus petit chauffe-t-il plus vite ?
Parce que le cache se remplit dans le temps. Un cache plus petit atteint un ensemble représentatif d’objets souvent évincés plus rapidement. Un cache énorme peut rester partiellement non représentatif longtemps sous churn.
3) L2ARC peut-il causer une latence plus élevée même si le taux de hits s’améliore ?
Oui. Si le remplissage L2ARC entre en concurrence avec les I/O du pool ou si le périphérique de cache devient un goulot, vous pouvez augmenter le travail background. De plus, si les métadonnées L2ARC réduisent l’efficacité de l’ARC, vous perdez des hits ARC bon marché et finissez par faire plus d’I/O lentes.
4) Dois-je ajouter de la RAM plutôt que L2ARC ?
Si vous le pouvez, oui — surtout quand votre ARC est contraint et que les misses de métadonnées font mal. La RAM améliore directement l’ARC, aide les métadonnées, et n’a pas de problème de réchauffement ni d’endurance. L2ARC est pertinent quand le jeu de travail dépasse la RAM et que les misses de lecture sont coûteux.
5) L2ARC aide-t-il les écritures ?
Non. L2ARC est un cache de lecture. Si votre douleur vient de la latence d’écriture synchrone, regardez le SLOG, les réglages sync, et les patterns fsync de l’application.
6) Quels réglages dataset influencent le plus le comportement L2ARC ?
secondarycache contrôle l’éligibilité au L2ARC. primarycache contrôle l’éligibilité ARC. recordsize affecte la granularité et l’efficacité du cache. La compression peut aider en faisant tenir plus de données logiques par octet mis en cache.
7) Un vdev spécial est-il meilleur que L2ARC ?
Outil différent. Un vdev spécial change le placement des métadonnées (et éventuellement des petits blocs), améliorant souvent la latence de façon prédictible pour les charges orientées métadonnées. L2ARC met en cache ce que l’ARC évince. Si votre goulot est les métadonnées et les petites lectures aléatoires, les vdevs spéciaux surpassent fréquemment « ajouter juste plus de L2ARC ».
8) Quel est un bon taux de hits L2ARC cible ?
Il n’y a pas de nombre magique. Sur des pools HDD, même 10–20% peut être un gain important si ça touche les lectures coûteuses. Sur des pools SSD rapides, il faudra souvent beaucoup plus pour justifier la surcharge. Reliez toujours cela à des améliorations de latence et une réduction du r_await HDD.
9) Comment empêcher les sauvegardes et scans de détruire mon cache ?
Mettez-les dans leurs propres datasets et configurez secondarycache=none. Pour les flux particulièrement abusifs, envisagez aussi primarycache=metadata selon les patterns d’accès.
10) Que se passe-t-il si le périphérique L2ARC tombe en panne ?
ZFS peut continuer à fonctionner ; c’est un périphérique de cache, pas de données. Mais la défaillance peut créer du bruit opérationnel : erreurs I/O, timeouts, et variations de performance quand les hits disparaissent. Surveillez et soyez prêt à le détacher proprement.
Conclusion : étapes pratiques suivantes
Si vous êtes sur le point d’acheter 2 To de « cache » parce que votre machine ZFS semble lente, faites une pause. Mesurez d’abord. La meilleure taille L2ARC est rarement « aussi grande que possible ». C’est « aussi petite que nécessaire pour capturer les misses réutilisés sans voler le déjeuner de l’ARC ».
Étapes à faire cette semaine
- Exécutez
arcstatpendant les pics et corrélez miss% avec la latence visible par les utilisateurs. - Listez les datasets et marquez les streamers : sauvegardes, scans analytiques, copies massives. Mettez
secondarycache=nonesur eux. - Si vous avez déjà L2ARC, vérifiez le taux de hits et l’utilisation du périphérique de cache. S’il est faible en hits et très occupé, réduisez-le.
- Décidez : si vous manquez de mémoire, achetez de la RAM avant d’acheter du cache.
- Si les métadonnées posent problème, planifiez un vdev spécial plutôt qu’un L2ARC plus grand.
Faites le travail de mesure ennuyeux. Ensuite, choisissez le plus petit changement qui vous apporte une amélioration stable. C’est ainsi qu’on empêche les caches de devenir un second boulot.