Je vais t'expliquer comment vm.max_map_count comprendre, mesurer et régler sans risque sur les serveurs de bases de données Linux. Cet article présente des étapes concrètes, des valeurs types et des contrôles éprouvés dans la pratique pour garantir le bon fonctionnement de PostgreSQL, MySQL/MariaDB, Elasticsearch ou OpenSearch sous charge.
Points centraux
- Fonction: Limite maximale pour les zones de mémoire virtuelle (VMA) par processus
- Pertinence: bases de données, systèmes de recherche, piles Java comportant de nombreux mappages
- Symptômes: „ Impossible d'allouer de la mémoire “, erreur au démarrage, plantages
- Valeurs de la pratique: de 262 144 à 1 048 576 pour les charges de travail importantes
- Procédure: Évaluer les besoins, les augmenter en prévoyant une marge, intégrer le suivi
Que signifie « vm.max_map_count » ?
Ce paramètre du noyau définit le nombre de Zones de mémoire (VMAs) qu'un processus peut créer au maximum. Chaque opération mmap, chaque objet partagé chargé, de nombreuses allocations et blocs de mémoire partagée augmentent ce nombre. Je ne limite pas ainsi la quantité de RAM, mais la Quantité des zones distinctes dans l'espace d'adressage virtuel. Les processus volumineux peuvent utiliser beaucoup de mémoire avec quelques mappages de grande taille, tandis que les charges de travail fragmentées atteignent rapidement leurs limites avec de nombreux petits mappages. Quiconque utilise des logiciels gourmands en mémoire doit connaître cette limite maximale, sinon l'erreur ne se manifestera qu'en cas de charge élevée.
Pourquoi les serveurs de bases de données sont-ils concernés ?
Les bases de données et les moteurs de recherche s'appuient largement sur mmap, la mémoire partagée, les caches et de nombreuses bibliothèques. Les instances PostgreSQL comportant de nombreuses extensions et connexions, MySQL/MariaDB avec des plugins ou Elasticsearch/OpenSearch avec de nombreux segments d’index génèrent un grand nombre de VMA. Si ce nombre s’approche de la limite, les mappages supplémentaires échouent et le processus signale Erreur de mémoire. C'est précisément dans ces cas-là que les services ne démarrent pas, s'interrompent sous la charge ou perdent des nœuds dans les clusters. J'empêche ce genre de comportement en déterminant au préalable la limite maximale nécessaire et en la configurant correctement.
Symptômes et risques liés à un mauvais réglage
Les signes les plus fréquents d'un seuil trop bas sont les suivants : erreur de démarrage malgré la mémoire libre. Des services tels qu’Elasticsearch affichent le message „ Cannot allocate memory “, alors que la machine dispose encore de ressources libres. Des interruptions sporadiques de processus surviennent également dès que le nombre de VMA nécessaires en interne dépasse la limite autorisée. Une valeur trop élevée n’est généralement pas préjudiciable, car le noyau n’utilise alors qu’un peu plus Administration nécessaire pour les vm_area_structs. Cela ne devient pertinent que lorsque les processus créent réellement des millions de mappages, ce que les charges de travail typiques des bases de données n'atteignent généralement pas.
Données issues de la pratique et mise en perspective
De nombreuses distributions utilisent des valeurs par défaut prudentes, de l'ordre de 65 536, ce qui suffit pour des services simples, mais s'avère insuffisant pour les charges liées à la recherche et à l'analyse. Dans les configurations d’hébergement classiques, j’utilise 262 144 comme valeur de départ fiable pour les piles plus importantes. Pour les très grandes instances Elasticsearch/OpenSearch, je prévois 1 048 576, à condition que les mesures aillent dans ce sens. Une valeur plus élevée n’apporte pas de gain de puissance, il permet d'éviter les erreurs lorsque de nombreux mappages sont nécessaires. La documentation du noyau Linux et les retours d'expérience confirmés confirment cette classification.
| Type d'application | Profil VMA (typique) | Valeur initiale de vm.max_map_count | Limite supérieure (si nécessaire) |
|---|---|---|---|
| Petites bases de données / Outils | faible à moyen | 65.536 | 262.144 |
| PostgreSQL / MySQL | moyen-élevé | 262.144 | 524.288 |
| Elasticsearch / OpenSearch | élevé - très élevé | 262.144 | 1.048.576 |
| Grandes piles Java | moyen-élevé | 262.144 | 524.288 |
Évaluer les besoins actuels
Avant chaque modification, je vérifie la version actuelle Réglage avec sysctl vm.max_map_count ou par cat /proc/sys/vm/max_map_count. Ensuite, je détermine les besoins réels d'un processus à l'aide de wc -l /proc//maps, idéalement sous charge. Cette valeur varie en fonction des modules, des caches et de la charge de travail ; c’est pourquoi je l’observe sur plusieurs fenêtres de charge. Dès que le pic atteint 50 à 70 % de la limite, je mets en place une réserve appropriée. Je prends ainsi une décision éclairée Décision au lieu de deviner.
Comment ajuster vm.max_map_count en toute sécurité ?
Pour les tests, je définis temporairement cette valeur avec sysctl -w vm.max_map_count=262144, ce qui prend effet immédiatement et disparaît au redémarrage. Pour un fonctionnement continu, je saisis la valeur dans /etc/sysctl.conf et télécharge-le avec sysctl --system nouveau, afin que la Configuration reste inchangé. Les grands clusters de recherche ou les piles de bases de données très modulaires bénéficient, selon les mesures, de 524 288 à 1 048 576. J'augmente progressivement, je vérifie les journaux et je surveille les indicateurs d'utilisation de la mémoire. C'est ainsi que je maintiens le Risque est faible en fonctionnement et permet de constituer une réserve prévisible.
Bonnes pratiques pour les environnements de production
Je procède à des mesures répétées en conditions de charge typique et de charge de pointe, plutôt que de me fier à des valeurs ponctuelles. Je ne fixe pas la limite supérieure à la valeur exacte, mais en la multipliant par un facteur compris entre deux et quatre par rapport au pic observé. Dans les clusters, je choisis des valeurs cohérentes afin que tous les nœuds réagissent de la même manière et qu’aucun Fugueurs générer. Le système de surveillance vérifie les erreurs liées à mmap/malloc ainsi que l'évolution du nombre de VMA par processus. Avant la mise en production, je teste les nouvelles Valeurs en environnement de test avec une charge comparable.
Interaction avec d'autres paramètres du noyau : swappiness, ratios de fichiers sales, limites de fichiers
vm.max_map_count n'est jamais pris isolément, car d'autres paramètres influent sur ce paramètre Conduite De même. Le paramètre « swappiness » détermine avec quelle agressivité le système place les pages dans la zone d'échange, ce qui peut augmenter les latences. Les « dirty ratios » déterminent à quel moment les pages modifiées sont renvoyées sur le disque, ce qui peut lisser ou accentuer les pics d’E/S. Les limites pour les fichiers ouverts déterminent le nombre de fichiers et de sockets que les bases de données sont autorisées à maintenir en parallèle. Je vérifie ces Paramètres ensemble, afin d'éviter la formation d'un nouveau goulot d'étranglement.
Vérifier de manière ciblée les « Huge Pages » transparentes
Le THP influence la gestion de la mémoire en regroupant les grandes pages, ce qui modifie les schémas d’accès. Les bases de données sont sensibles au THP selon la charge de travail ; c’est pourquoi je vérifie leur état et leur mode, et je les règle sur „ madvise “ ou „ never “ lorsque les latences augmentent. Vous trouverez plus de détails sur les effets et le réglage dans ma note sur Pages transparentes volumineuses en résumé. Il reste important d'étayer ce changement par des indicateurs et de ne pas opérer la transition à l'aveuglette. Ainsi, le Comportement de stockage compréhensible et reproductible.
Comprendre l'impression via le cache VFS
Le cache VFS stocke les métadonnées et le contenu des fichiers en mémoire vive, entrant ainsi en concurrence avec les pages de base de données. Grâce au paramètre permettant de Impression à partir du cache VFS Je contrôle la vitesse à laquelle le système libère ce cache. Une pression trop élevée peut augmenter la charge d'E/S, tandis qu'une pression trop faible évince les caches de la base de données et nuit aux latences. J'effectue des ajustements par petits paliers et je mesure leurs effets sur le taux de réussite du cache de pages, le temps d'attente d'E/S et le débit. Ceci Réglage fin a souvent un impact plus important que prévu lorsque les bases de données et les systèmes de fichiers fonctionnent en étroite interaction.
Directives NUMA et bases de données
Les architectures NUMA répartissent la mémoire entre les nœuds, ce qui influe sur les temps d'accès. En l'absence de règles adaptées, les pages se retrouvent sur les „ mauvais “ nœuds, ce qui augmente les latences et les échecs de cache. Vous trouverez des informations sur les modes et les politiques à l'adresse suivante : Directives NUMA, y compris des paramètres de démarrage adaptés à la pratique. Pour les processus de base de données volumineux, je définis des nœuds prioritaires et je vérifie l’entrelacement afin que les accès à la mémoire local restent inchangés. L'interaction avec vm.max_map_count a un effet positif lorsque les processus bénéficient de nombreux mappages via des stratégies NUMA cohérentes.
Comment naissent les VMA – et pourquoi ils peuvent faire un tabac
Je distingue trois sources principales de VMA : (1) les mappages liés à des fichiers (par exemple, les segments de données et d’index d’Elasticsearch/OpenSearch), (2) les mappages anonymes via des allocateurs (glibc, jemalloc, tcmalloc) et (3) les piles des threads. De nombreux petits objets partagés, le code JIT (par exemple dans les JVM) et les schémas d’allocation fragmentés génèrent des zones supplémentaires. Chaque thread comporte au moins une VMA de pile ; lorsque le nombre de threads de travail augmente, le nombre de VMA augmente également. Cela explique pourquoi les systèmes atteignent plus rapidement leurs limites avec une quantité de données identique, mais un plus grand nombre de threads ou de plugins.
Important : je fais la distinction entre „ beaucoup de mémoire “ et „ beaucoup de mappings “. Les grandes zones contiguës posent rarement problème. La situation devient critique lorsque le logiciel doit fréquemment gérer de nombreux petits objets mmap utilise (stratégies d'allocation), charge des bibliothèques de manière dynamique ou mappe un très grand nombre de fichiers en parallèle.
La surcharge par VMA est modérée (quelques centaines d'octets de données de gestion). Une valeur limite plus élevée élargit l'éventail des structures théoriquement possibles sans occuper de mémoire vive, tant que les processus ne les utilisent pas. Ce n'est que lorsque des centaines de milliers, voire des millions de VMA sont créées que la charge de gestion du noyau devient perceptible de manière mesurable.
Approfondir les méthodes de mesure : détecter les pics de manière fiable
- Je réalise des mesures à différents moments de la journée et en période de charge de travail maximale (exécutions par lots, réindexation, fenêtres de maintenance).
- Je ne surveille pas seulement un processus, mais l'ensemble des services critiques (base de données, sidecars, agents de sauvegarde et de surveillance).
- Pour obtenir des résultats reproductibles, je fais la distinction entre „ à froid “ (cache Page vide) et „ à chaud “ (cache rempli) et je consigne les différences.
Des outils pratiques pour repérer les points d'accès VMA :
# Les 10 processus les plus importants en nombre de VMA
for p in /proc/[0-9]*; do
pid=${p##*/}; test -r "$p/maps" || continue
c=$(wc -l /dev/null || echo 0)
cmd=$(tr -d '\0' /dev/null)]}"
done | sort -k2,2nr | head -n 10
Dans le cas des clusters, j'analyse les résultats sur plusieurs nœuds et je recherche les anomalies systématiques (par exemple, certains shards, des extensions ou des versions spécifiques). Je déclenche des alertes lorsqu'un processus dépasse la limite de 70 % ou lorsque la charge de pointe affiche une tendance à la hausse.
Dépannage : messages de journalisation typiques et vérifications
Lorsque la limite est atteinte, je constate souvent des messages du type „ Cannot allocate memory “, „ mmap failed “, „ failed to map segment from shared object “ ou des échecs de démarrage sans qu'il y ait de pénurie évidente de mémoire vive. Je vérifie alors :
grep -i mmap /var/log/*et les journaux spécifiques au service concernant les notifications ENOMEM- Nombre actuel de mappages :
wc -l /proc//maps - Limites Ulimit/Nofile, car de nombreux fichiers segmentés ne peuvent pas être mappés correctement sans un nombre suffisant de fichiers ouverts
- Nombre de fils (
ps -eLo pid,comm,nlwp | sort -k3 -nr | head), car de nombreux threads augmentent la valeur VMA
Je mets ces résultats en corrélation avec les profils de charge (création d'index, Vacuum/Analyze, importations volumineuses). Si les chiffres VMA présentent des pics nets correspondant à des tâches bien définies, je dimensionne la réserve en conséquence.
Conteneurs, cloud et orchestration : particularités
Dans les conteneurs, il y a vm.max_map_count dans la pratique, il s'agit généralement d'une Paramètres de l'hôte. Je définis la valeur sur le nœud (serveur physique ou machine virtuelle) via sysctl et télécharge-le de manière permanente via /etc/sysctl.conf ou des fichiers dans /etc/sysctl.d/. Dans les environnements Docker, je peux certes --sysctl Bien que vm.max_map_count semble s'appliquer à l'échelle de l'hôte, je prévois donc d'appliquer cette modification au niveau de chaque nœud. Dans les orchestrateurs (par exemple Kubernetes), je préfère définir cette valeur via Node-Init/Cloud-Init ou l’image machine, afin que les pods démarrent correctement sans privilèges. Important : je documente le choix Ligne de conformité (quel type de nœud héberge quelle valeur), afin que la planification et la mise à l'échelle automatique restent cohérentes.
Automatisation et conformité
Je consigne ce paramètre „ sous forme de code “, par exemple dans le cadre de la gestion de la configuration. À titre d'exemple, j'utilise un fichier sysctl « drop-in » :
# /etc/sysctl.d/90-db-mappings.conf
vm.max_map_count = 524288
Le déploiement s'effectue de manière contrôlée (Staging → Canary → déploiement à grande échelle). Immédiatement après les déploiements, j'effectue des contrôles d'intégrité et je vérifie que les nouveaux pods/services respectent la même limite. À des fins d'audit, j'enregistre les données de mesure (VMA de pointe, facteur de réserve, date du dernier ajustement) dans la documentation d'exploitation.
Réglage avec Overcommit et OOM-Killer
Une limite VMA plus élevée ne réduit pas l'occupation de la mémoire vive, mais elle autorise davantage de mappages. En période de pic d'activité, l'interaction avec les stratégies d'overcommit et l'OOM-Killer peut s'avérer pertinente : si j'autorise davantage de mappages, les processus peuvent réserver de la mémoire de manière plus agressive. Je considère donc que vm.overcommit_memory et vm.overcommit_ratio Je garde cela à l'œil et veille à disposer de réserves suffisantes (swap/marge) ou à mettre en place des politiques d'overcommit plus restrictives lorsque les charges de travail ont tendance à entraîner une surcharge. L'objectif est de disposer d'une fenêtre d'alerte précoce : au lieu d'un OOM soudain, je reçois à temps, dans le système de surveillance, des signaux indiquant une augmentation des taux d'erreur ou de la latence, qui m'incitent à prendre des contre-mesures.
Cas limites : 32 bits, nombreux threads, choix de l'allocateur
- Processus 32 bits: L'espace d'adressage virtuel est plus restreint, et la fragmentation se fait plus rapidement sentir. Une valeur plus élevée de vm.max_map_count ne résout pas le problème de manque d'espace d'adressage ; dans ce cas, il faut recourir à des versions 64 bits ou changer d'architecture.
- Services à nombreux threads: Chaque thread dispose d'au moins une VMA de pile dédiée. Si le nombre de workers augmente fortement, le nombre de VMA augmente de manière linéaire. Je veille à ce que les pools de threads soient limités et dimensionnés de manière appropriée.
- Allocateur: Certains allocateurs utilisent
mmapexcessif pour les blocs volumineux ou les nombreux petits blocs. En cas de pics de VMA notables, je teste d'autres allocateurs ou leurs options de réglage afin de réduire le nombre de mappages. - Bibliothèques partagées: La présence de nombreux petits modules chargés dynamiquement fait grimper le nombre de mappages. Je vérifie s'il est possible de regrouper des modules ou de supprimer des plugins inutiles.
Liste de contrôle avant la modification
- Déterminer et consigner les limites actuelles
- Mesurer les pics VMA spécifiques au processus sur plusieurs fenêtres de charge
- Déterminer la réserve (facteur 2 à 4 par rapport au pic) et planifier les tests de staging
- Vérifier les limites associées (nofile), le nombre de threads, le THP, le swappiness et les ratios de données sales
- Activer la surveillance et les alertes concernant le dépassement de la limite VMA, les erreurs mmap et les événements OOM
- Définir le chemin de déploiement et de restauration (Canary, fenêtre de maintenance, fichiers sysctl.d)
- Garantir et documenter la cohérence des clusters et des nœuds
Planification des pôles de compétitivité et de la croissance
Je ne tiens pas seulement compte de la situation actuelle, mais aussi de la croissance prévue des données et des indices. De nouvelles fonctionnalités, un nombre accru de clients ou des extensions supplémentaires augmentent souvent le nombre de Mappings. C'est pourquoi je prévois une marge au-delà du pic observé et je consigne clairement cette décision. Dans les clusters, je synchronise les valeurs afin que les nœuds réagissent de manière identique et que le basculement ne se heurte pas à des limites. Des vérifications régulières pendant les fenêtres de maintenance garantissent la Continuité des paramètres.
En résumé : configuration sécurisée pour les serveurs de bases de données
Je vérifie la limite actuelle, je mesure le nombre de VMA sous charge et je définis vm.max_map_count en prévoyant une marge. Pour de nombreuses charges de travail liées aux bases de données et à la recherche, la valeur 262 144 convient valeur initiale et 1 048 576 comme niveau supérieur, si les mesures et la croissance l'exigent. Cette modification n’entraîne pas de gain de performance immédiat, mais elle permet d’éviter des erreurs dès lors qu’un très grand nombre de mappages est nécessaire. La stabilité est assurée lorsque j’examine conjointement les journaux, les métriques et les paramètres du noyau associés. Ainsi, le Exploitation de bases de données résistant, prévisible et prêt à faire face à des charges croissantes.


