2 points par GN⁺ 2025-08-24 | Aucun commentaire pour le moment. | Partager sur WhatsApp
  • Nitro est un système d’init et superviseur de processus ultra-léger adapté aussi bien à l’embarqué qu’aux serveurs, postes de travail et conteneurs
  • Il stocke l’état du système uniquement en RAM, ce qui lui permet de fonctionner sans difficulté sur des systèmes de fichiers en lecture seule, avec une conception rapide et efficace, basée sur les événements
  • La configuration repose sur une simple structure de répertoires de scripts, ce qui permet de gérer les services sans fichiers de configuration complexes ni étape de build supplémentaire
  • Il prend en charge des services paramétrés, des redémarrages robustes et une journalisation fiable par service, avec des fonctions optimisées pour les conteneurs et les environnements embarqués
  • Il garantit une grande souplesse et un contrôle fin, notamment grâce au contrôle à distance via l’outil nitroctl et à un pilotage par signaux

Aperçu

Nitro est un superviseur de processus ultra-léger pouvant aussi être utilisé comme pid 1 sous Linux

Principaux cas d’usage :

  • init pour des machines Linux de types variés : embarqué, poste de travail, serveur, etc.
  • init de Linux initramfs
  • init pour environnements conteneurisés comme Docker/Podman/LXC/Kubernetes
  • démon de supervision fonctionnant sans privilèges sur des systèmes POSIX

La configuration utilise une structure de scripts basée sur des répertoires, avec /etc/nitro comme emplacement par défaut

Exigences

  • prise en charge des sockets Unix par le noyau
  • tmpfs ou répertoire /run accessible en écriture

Avantages par rapport aux autres systèmes

  • Toutes les informations d’état sont conservées uniquement en RAM, ce qui permet de fonctionner sur un système de fichiers racine en lecture seule sans astuce particulière
  • Fonctionnement basé sur les événements, sans polling, pour plus d’efficacité
  • Aucune allocation dynamique de mémoire à l’exécution
  • Les descripteurs de fichiers ne sont pas consommés indéfiniment
  • Un seul binaire autonome est nécessaire (avec, en option, un binaire de contrôle supplémentaire)
  • Pas besoin de conversion ou de compilation de fichiers de configuration : un service est simplement un répertoire contenant des scripts
  • Prise en charge des chaînes de redémarrage et de journalisation des services
  • Fonctionne correctement même si l’horloge système n’est pas précise
  • Peut être exécuté via /etc/ttys sur FreeBSD
  • Il est possible de produire un binaire statique ultra-compact avec musl libc

Gestion des services

  • Chaque répertoire de service (par défaut dans /etc/nitro) peut contenir les fichiers suivants

    • setup : script (optionnel) exécuté avant le démarrage du service ; le service ne peut démarrer que si ce script se termine avec succès (0)
    • run : script d’exécution du service ; tant qu’il ne se termine pas, le service est considéré comme actif ; s’il n’est pas implémenté, le service est traité comme un service one-shot
    • finish : script (optionnel) exécuté après la fin de run, recevant en argument l’état de sortie et la valeur du signal
    • log : lien symbolique vers un autre répertoire de service ; la sortie de run est reliée par pipe à l’entrée de ce service (utile pour les chaînes de journalisation)
    • down : si ce fichier existe, nitro ne démarre pas ce service par défaut
    • si le nom du répertoire se termine par @, il est ignoré et peut servir de service paramétré
    • le nom du service doit faire moins de 64 caractères et ne peut pas contenir /, , ni de saut de ligne
  • L’utilitaire chpst de runit est utile pour écrire les scripts run

Services spéciaux

  • LOG : service par défaut pour enregistrer les journaux de tous les services sans lien log
  • SYS : SYS/setup est exécuté avant le démarrage de tous les services, ce qui permet de mettre en place un démarrage ordonné des services
    • SYS/finish : exécuté avant l’entrée dans la phase d’arrêt globale
    • SYS/final : exécuté après l’arrêt de tous les processus
    • SYS/fatal : exécuté à la place de l’arrêt en cas d’erreur fatale, s’il existe
    • SYS/reincarnate : exécuté à la place du shutdown, utile par exemple pour une réimplémentation d’initramfs

Services paramétrés

  • Les répertoires de service se terminant par @ sont ignorés par nitro, mais peuvent être ciblés directement via un lien symbolique ou la commande nitroctl
  • Le paramètre placé après @ est transmis comme premier argument à chaque script
    • Exemple : s’il existe des liens symboliques agetty@/run et agetty@tty1, alors agetty@/run tty1 est exécuté
    • Avec nitroctl up agetty@tty2, il est possible d’exécuter agetty@/run tty2 (que le répertoire existe ou non)

Modes de fonctionnement

  • Le cycle de vie complet comprend trois étapes : démarrage, exécution des services (supervision), arrêt
    • Démarrage : si le service spécial SYS existe, son setup est exécuté en premier, puis tous les services non marqués down sont lancés
    • Lorsqu’un service se termine, il est redémarré ; si les redémarrages récents sont trop rapprochés, une attente de 2 secondes est appliquée
    • nitroctl Reboot ou Shutdown permet d’envoyer le signal d’arrêt
      • Dans ce cas : SYS/finishSIGTERM à tous les services (attente maximale de 7 secondes) → SIGKILLSYS/final → séquence d’arrêt
    • Dans le cas d’un conteneur ou d’un superviseur sans privilèges, seuls les processus sont arrêtés

Contrôle via nitroctl

  • L’outil CLI nitroctl permet de contrôler nitro à distance

Exemples de commandes :

  • list : affiche la liste des services, leur état, leur PID, leur uptime et leur dernier état de sortie
  • up/down/start/stop/restart : contrôle du démarrage, de l’arrêt et du redémarrage des services
  • envoi de signaux : p(SIGSTOP), c(SIGCONT), h(SIGHUP), a(SIGALRM), i(SIGINT), q(SIGQUIT), 1(SIGUSR1), 2(SIGUSR2), t(SIGTERM), k(SIGKILL)
  • pidof : affiche le PID du service demandé
  • rescan : relit les répertoires de services et prend en compte les services ajoutés ou supprimés
  • Shutdown/Reboot : arrêt ou redémarrage de l’ensemble du système

Contrôle par signaux

  • Il est possible de contrôler nitro en envoyant directement des signaux au processus nitro
    • SIGHUP : rescannage des services (rescan)
    • SIGINT : redémarrage
    • SIGTERM : arrêt (si nitro n’est pas pid 1)

Nitro comme init sous Linux

  • Nitro peut démarrer directement comme pid 1 sous Linux sous forme de binaire autonome
  • Il monte /dev et /run si nécessaire, et les autres opérations sont gérées dans SYS/setup
  • L’événement Ctrl-Alt-Del déclenche un redémarrage ordonné

Utiliser Nitro comme init dans un conteneur Docker

  • Nitro peut être compilé statiquement et intégré facilement dans un conteneur
  • /run doit exister dans le conteneur pour utiliser le chemin de socket par défaut
  • Si la socket de contrôle est montée par bind mount, un contrôle à distance via nitroctl depuis l’extérieur est possible

Nitro sur FreeBSD

  • En ajoutant la ligne suivante dans /etc/ttys, il est possible de faire superviser nitro par l’init de FreeBSD
    /etc/nitro "/usr/local/sbin/nitro" "" on
    

Auteur

Remerciements

  • Développé à partir d’une analyse détaillée de systèmes existants de supervision de processus comme daemontools, freedt, runit, perp et s6

Licence

  • Licence 0BSD (voir le fichier LICENSE pour les détails)

Aucun commentaire pour le moment.

Aucun commentaire pour le moment.