Retour

Construire avec Exten : le moteur de stockage par blocs NVMe exclusif d’OVHcloud

Tristan Groléat06/08/20267 min de lecture

Construire avec Exten : le moteur de stockage par blocs NVMe exclusif d’OVHcloud

Fiable et bien intégré à OpenStack, nous avons utilisé Ceph comme solution de stockage par blocs pendant des années. Pour proposer plus de performances à moindre coût, nous avons acquis Exten et sommes désormais en mesure de construire notre propre solution de stockage par blocs NVMe en C++ et Go. Nos objectifs de construction sont les suivants :

  • utilisation de disques NVMe pour offrir des volumes haute performance ;
  • utilisation d’algorithmes d'encodage intelligents pour occuper moins d'espace sur les disques (codage de Reed-Solomon, compression) ;
  • petits clusters faciles à maintenir.

Exten est désormais en production depuis plus d'un an. Dans cet article de blog, nous détaillons son fonctionnement et les possibilités que son architecture ouvrira à l’avenir.

 Cliquez sur le lien en bas de page pour donner votre avis et nous aider à façonner l'avenir d'Exten.

CONSENSUS GRPC RAFT

Anatomie d'un cluster

Un cluster Exten typique est composé de six serveurs. Ces derniers sont placés à proximité les uns des autres pour que la latence entre eux soit faible, mais pas trop proches pour limiter les risques que plusieurs serveurs tombent en panne simultanément. Chaque serveur est équipé de dizaines de disques NVMe pour stocker les données utilisateur.

Exten est construit autour du protocole NVMe. Il utilise des disques NVMe, mais également le protocole NVMe over Fabrics pour exposer les volumes des utilisatrices et utilisateurs ainsi que pour communiquer entre hôtes. Les volumes sont des lecteurs virtuels que les clientes et clients peuvent connecter à leurs machines virtuelles. Ce protocole utilise les mêmes commandes que les disques NVMe, mais sur un lien réseau (TCP ou RDMA). Il est en outre conçu pour une performance élevée et une faible latence.

Un avantage de NVMe over Fabrics est que le noyau Linux le supporte nativement. Connecter un volume Exten à un hôte Linux est aussi simple que d'exécuter la commande nvme connect avec les bons paramètres : le volume apparaît alors comme n'importe quel autre lecteur NVMe local. En tant que cliente ou client Public Cloud, vous ne voyez rien de tout cela : le volume est simplement attaché à votre instance, exactement comme avec Ceph.

Exten est divisé en un plan de données écrit en C++ et un plan de contrôle écrit en Go. Les deux communiquent via gRPC. Le plan de données reçoit les E/S via NVMe over Fabrics et les achemine vers les disques NVMe. Le plan de contrôle fournit une API pour créer et supprimer des volumes ainsi que pour gérer le cluster.

Comment protéger vos données

La protection des données client est la principale responsabilité d'un cluster Exten et nous la gérons à plusieurs niveaux.

Du côté du plan de contrôle, nous utilisons l’algorithme de consensus renommé Raft pour garantir l'intégrité du cluster d’une manière tolérante aux pannes. Il fonctionne en élisant un leader et en consignant toute nouvelle information : un nouveau volume créé, un disque activé, dans un journal répliqué sur chaque hôte. En cas de défaillance d'un hôte, les autres continuent à fonctionner. La seule limite est qu'une majorité d'hôtes doit rester active pour éviter les problèmes de

split-brain.

Ainsi, un cluster à six nœuds peut perdre deux hôtes tout en continuant de fonctionner.

Les données utilisateur elles-mêmes, ou les E/S réelles effectuées sur les volumes, ne passent pas par Raft. Cela serait en effet beaucoup trop lent. Nous utilisons plutôt un autre algorithme bien connu : un code de Reed-Solomon.

Ce code de correction d'erreurs est simple dans sa conception. Prenons l'exemple du RS 4+2 : nous divisons les données en quatre parties égales, puis calculons deux nouvelles parties de la même taille. Si vous pouvez lire n'importe lesquelles de ces six parties, vous pouvez récupérer les données d'origine : le code vous permet de calculer les deux parties manquantes. Cela donne un ratio de 1.5 (données stockées/données reçues). Deux disques peuvent donc être perdus sans perte de données. C'est une façon très efficace d'ajouter de la redondance. L'alternative, généralement appelée mirroring, constitue en la copie multiple de l'ensemble des données sur différents disques. Elle nécessiterait trois copies pour survivre à la perte de deux disques. Avec Reed-Solomon, nous stockons la moitié des données pour le même niveau de redondance.

Les disques défectueux peuvent être détectés de deux manières : soit la lecture échoue simplement, soit elle retourne des données corrompues. Ces dernières sont détectées grâce à un checksum que nous ajoutons à chaque secteur. Lorsqu'un disque tombe en panne, un processus automatique recalculera la partie manquante et la stockera sur un disque sain, réduisant ainsi le risque de perte de données.

Faire des E/S rapidement

Avec des CPU et de la RAM qui travaillent plus vite, le stockage doit suivre. L'objectif d'Exten est de tirer le meilleur parti du matériel sur lequel il fonctionne et de fournir des E/S haute performance à sa clientèle. Le choix du protocole NVMe over Fabrics est un premier pas vers des E/S avec le moins d’overhead possible. Cependant, l'ensemble de la pile logicielle est conçu pour la performance.

Le modèle de traitement est centré sur les données. Au niveau de la carte réseau (NIC), nous recevons et envoyons des données via une liste de buffers de taille fixe stockés en RAM. Un CPU donné traite chaque buffer avec deux objectifs : éviter les copies de données ainsi que les changements de contexte.

Pour éviter les copies de données, le code manipule des buffers pré-alloués via des pointeurs sur tout le trajet, de la carte d’interface réseau au disque. Nous ne modifions les données que lorsque c'est inévitable (ex. compression, encodage Reed-Solomon). Pour éviter les changements de contexte, nous gérons les E/S via des méthodes entièrement asynchrones qui travaillent sur de petites portions de données. Un CPU donné effectue autant de traitements que possible sur un buffer avant de passer au suivant. Mais il s’agit d’un équilibre : le prochain buffer ne peut pas être retardé trop longtemps et le traitement doit rester équitable. Nous avons construit un cadre C++ complet adapté à ces besoins pour garder un code clair et maintenable.

Au-delà du code lui-même, plusieurs autres facteurs contribuent à améliorer les performances :

  • le choix de l'algorithme de compression (aucune compression constitue parfois le meilleur choix, par exemple sur le trafic chiffré) ;
  • le choix du protocole réseau : RDMA est plus rapide que TCP, mais implique plus de contraintes de déploiement ;
  • la manière dont nous allouons les cœurs CPU aux volumes.

Sur nos offres Public Cloud, nous appliquons également des règles de qualité de service (QoS) pour assurer l'équité entre tous les volumes.

Les prochaines étapes pour Exten

Exten est désormais en production et fournit des volumes aux clientes et clients Public Cloud dès aujourd'hui. Il est transparent pour notre clientèle et soutient actuellement les mêmes offres que Ceph. Il s’agit cependant d’une pile logicielle que nous contrôlons entièrement, construite autour de NVMe pour de hautes performances.

Nous l'améliorons constamment, en visant à offrir des volumes de performances plus élevées, plus de flexibilité et plus de fiabilité aux clientes et clients. Nous explorons par exemple l'utilisation de RDMA pour améliorer les performances (nous utilisons actuellement TCP).

La première étape du changement vers Exten consistait à fournir une offre fiable remplaçant Ceph. Maintenant que nous contrôlons entièrement la pile, nous sommes prêts à ajouter de nouvelles fonctionnalités et à adapter l'offre aux besoins des clientes et clients.

Avez-vous des cas d'usage de Block Storage que nous devrions connaître, ou des fonctionnalités qui vous semblent manquantes ?

Parlez-nous d'eux sur Discord ou la mailing-list cloud. Vos retours façonnent l’avenir d’Exten.


Partager sur :