## Introduction

Systemd est puissant, mais ses messages d'erreur peuvent sembler obscurs lorsqu'une unité ne démarre pas ou redémarre en boucle. Ce guide se concentre sur les erreurs systemd les plus fréquentes en pratique, explique pourquoi elles se produisent, comment les diagnostiquer rapidement et les corriger en toute sécurité.

Vous obtiendrez :

- Un flux de travail de dépannage répétable

- Une aide-mémoire des commandes d'inspection

- Erreurs pratiques, causes racines et correctifs prêts à l'emploi

- Un plan de pilote local pour vous exercer sans risque avant la production

## Vue d'ensemble du flux de travail de dépannage

Utilisez cette séquence de bout en bout. Elle est rapide, sûre et répétable.

- Identifier l'unité et reproduire en sécurité

- Connaître le nom exact de l'unité (ex. nginx.service ). Évitez les suppositions.

- Si possible, reproduisez d'abord dans un environnement non productif.

- Inspecter l'état en premier

systemctl status nginx.service --no-pager -l 
 Recherchez : état actif, ExecStart, PID principal, code/statut, dernières lignes de journal.

- Lire les journaux avec contexte

journalctl -xeu nginx.service --no-pager
 # Ou restreindre au démarrage actuel
 journalctl -u nginx.service -b --no-pager 

- Vérifier la syntaxe de l'unité et voir le fichier chargé par systemd

 systemctl cat nginx.service
 systemctl show nginx.service -p FragmentPath -p DropInPaths
 systemd-analyze verify /etc/systemd/system/nginx.service 

- Tester la commande en dehors de systemd

- Exécutez la commande ExecStart manuellement en tant qu'utilisateur du service si applicable.

- Exemple : sudo -u nginx /usr/sbin/nginx -t pour tester la configuration nginx.

- Vérifiez les permissions et l'existence des binaires et scripts.

- Pour les scripts, confirmez le bit d'exécution et le shebang correct.

- Vérifier l'ordre et les dépendances

 systemctl list-dependencies --reverse nginx.service
 systemd-analyze critical-chain nginx.service 
 Ajustez Wants= , Requires= et After= selon les besoins. La sortie critical-chain montre quelles unités retardent le démarrage.

- Examiner le bac à sable (sandboxing) et les systèmes de fichiers

- Des options comme ProtectSystem , ReadWritePaths , PrivateTmp , DynamicUser et WorkingDirectory peuvent bloquer les écritures ou l'accès.

- Si les écritures échouent, soit assouplissez les protections, soit écrivez dans les chemins autorisés comme RuntimeDirectory .

- Appliquer les modifications en toute sécurité et recharger

systemctl daemon-reload
 systemctl restart nginx.service 
 Préférez l'utilisation de drop-ins via :

systemctl edit nginx.service 
 Cela crée /etc/systemd/system/nginx.service.d/override.conf .

- Confirmer et surveiller

systemctl is-active nginx.service && echo OK
 journalctl -u nginx.service -b -n 50 --no-pager 

## Aide-mémoire des diagnostics

- État et derniers journaux

 systemctl status <unité> --no-pager -l
 journalctl -xeu <unité> --no-pager 

- Afficher l'unité chargée et les drop-ins

 systemctl cat <unité>
 systemctl show <unité> -p FragmentPath -p DropInPaths 

- Valider la syntaxe de l'unité

 systemd-analyze verify /etc/systemd/system/<unité> 

- Journaux limités au démarrage actuel

 journalctl -u <unité> -b --no-pager 

- Dépendances et chaîne critique

 systemctl list-dependencies --reverse <unité>
 systemd-analyze critical-chain <unité> 

- Environnement

 systemctl show <unité> -p Environment -p EnvironmentFiles 

## Erreurs courantes et correctifs

 Voici les erreurs que vous rencontrerez probablement, avec leurs causes, diagnostics et correctifs sûrs.

### 1) "Unit <name>.service not found"

Symptôme :

systemctl start myapp
Failed to start myapp.service: Unit myapp.service not found. 
 Pourquoi ça arrive :

- Le fichier d'unité est absent ou mal nommé.

- Vous avez créé ou modifié une unité sans exécuter daemon-reload .

Diagnostiquer :

ls /etc/systemd/system/myapp.service /lib/systemd/system/myapp.service
systemctl daemon-reload && systemctl list-unit-files | grep myapp 
 Corriger :

- Assurez-vous que le fichier est placé à /etc/systemd/system/myapp.service .

- Corrigez le nom et l'extension de l'unité.

- Rechargez et démarrez :

systemctl daemon-reload
 systemctl enable --now myapp.service 

### 2) "Unit is masked"

 Symptôme :

systemctl start docker
Failed to start docker.service: Unit docker.service is masked. 
 Pourquoi ça arrive :

- L'unité est liée à /dev/null pour empêcher son activation.

Diagnostiquer :

ls -l /etc/systemd/system/docker.service
systemctl status docker 
 Corriger (comprenez d'abord pourquoi elle était masquée) :

systemctl unmask docker.service
systemctl enable --now docker.service 

### 3) "Failed at step EXEC spawning ...: No such file or directory"

 Symptôme :

systemd[1]: myapp.service: Failed at step EXEC spawning /usr/local/bin/myapp: No such file or directory 
 Pourquoi ça arrive :

- Le chemin ExecStart est erroné ou manquant.

- Le script a un shebang avec un chemin d'interpréteur invalide.

Diagnostiquer :

file /usr/local/bin/myapp
head -n1 /usr/local/bin/myapp
which myapp 
 Corriger :

- Pointez ExecStart vers le chemin absolu correct.

- Pour les scripts, utilisez un shebang valide comme :

#!/usr/bin/env bash 

- Assurez-vous du bit d'exécution :

 chmod +x /usr/local/bin/myapp 

### 4) "Exec format error" ou permission refusée pour les scripts

 Symptôme :

... myapp.sh: Exec format error 
 Pourquoi ça arrive :

- Fins de ligne Windows (CRLF).

- Pas exécutable ou interpréteur manquant.

Diagnostiquer et corriger :

file myapp.sh # affiche CRLF si présent
sed -i 's/
$//' myapp.sh # convertir en LF
chmod +x myapp.sh
head -n1 myapp.sh # confirmer le shebang 

### 5) "Start request repeated too quickly" (boucle de plantage)

 Symptôme :

systemd[1]: myapp.service: Start request repeated too quickly. 
 Pourquoi ça arrive :

- Le service se termine rapidement, souvent avec Restart=always .

Diagnostiquer :

journalctl -u myapp -b -n 100 --no-pager
systemctl show myapp -p Restart -p StartLimitBurst -p StartLimitIntervalSec 
 Corriger :

- Corrigez d'abord le plantage sous-jacent (mauvaise config, variable d'environnement manquante, mauvais chemin).

- Optionnellement, assouplissez les limites pendant le débogage :

[Unit]
 StartLimitIntervalSec=60
 StartLimitBurst=10

 [Service]
 Restart=on-failure
 RestartSec=2s 
 Appliquez via :

systemctl edit myapp.service
 systemctl daemon-reload && systemctl restart myapp 

### 6) "Dependency failed" ou problèmes d'ordre

 Symptôme :

systemd[1]: Dependency failed for myapp.service 
 Pourquoi ça arrive :

- L'unité requiert une autre unité qui est inactive.

- Le réseau n'est pas prêt mais le service l'attend.

Diagnostiquer :

systemctl list-dependencies --reverse myapp.service
systemd-analyze critical-chain myapp.service 
 Corriger (exemple : attendre le réseau) :

[Unit]
Wants=network-online.target
After=network-online.target 
 Sur les systèmes utilisant systemd-networkd, activez aussi :

systemctl enable --now systemd-networkd-wait-online.service 

### 7) EnvironmentFile introuvable

 Symptôme :

... Failed to load environment files: No such file or directory 
 Pourquoi ça arrive :

- Le chemin EnvironmentFile est erroné ou le fichier manque.

Diagnostiquer :

systemctl show myapp -p EnvironmentFiles
ls -l /etc/default/myapp.env 
 Corriger :

- Créez le fichier et sécurisez les permissions :

install -m 0640 -o root -g root /dev/null /etc/default/myapp.env
 echo 'MYAPP_PORT=8080' | tee -a /etc/default/myapp.env >/dev/null 

- Dans l'unité :

 [Service]
 EnvironmentFile=/etc/default/myapp.env 

- Rechargez et redémarrez.

### 8) WorkingDirectory inexistant

 Symptôme :

... myapp.service: WorkingDirectory=/opt/myapp: No such file or directory 
 Pourquoi ça arrive :

- Le répertoire est absent ou appartient au mauvais utilisateur.

Corriger :

install -d -o myuser -g myuser /opt/myapp 
 Ou utilisez RuntimeDirectory pour les chemins éphémères :

[Service]
RuntimeDirectory=myapp
WorkingDirectory=/run/myapp 

### 9) Permission refusée à cause des options de durcissement

 Symptôme :

... myapp: permission denied writing /var/log/myapp/output.log 
 Pourquoi ça arrive :

- ProtectSystem=strict ou similaire empêche les écritures.

Diagnostiquer :

systemctl cat myapp | sed -n '/\[Service\]/,$p' 
 Corriger proprement :

- Préférez écrire dans un RuntimeDirectory et laissez systemd le gérer :

[Service]
 RuntimeDirectory=myapp
 # l'application écrit dans /run/myapp/ 

- Ou autorisez des chemins d'écriture spécifiques :

 [Service]
 ProtectSystem=strict
 ReadWritePaths=/var/log/myapp 

### 10) Champs d'unité invalides ou fautes de frappe

 Symptôme :

... Failed to parse service type, ignoring: simple2 
 Pourquoi ça arrive :

- Fautes de frappe dans des champs comme Type, ExecStart ou noms de sections.

Corriger :

- Comparez avec la documentation systemd.unit et systemd.service.

- Validez :

systemd-analyze verify /etc/systemd/system/myapp.service 

### 11) "Failed to connect to bus: No such file or directory" dans les conteneurs

 Symptôme :

systemctl status
Failed to connect to bus: No such file or directory 
 Pourquoi ça arrive :

- La plupart des conteneurs n'exécutent pas systemd comme PID 1.

Correction et conseil :

- Ne comptez pas sur systemctl dans les conteneurs simples. Exécutez votre processus au premier plan et gérez-le avec le runtime de conteneur.

- Si vous avez vraiment besoin de systemd dans un conteneur, utilisez une image de base conçue pour cela et démarrez le conteneur avec les paramètres init appropriés. Évaluez la sécurité et la complexité avant de procéder.

## Plan de pilote local

Commencez petit, mesurable et facile à inspecter localement.

Objectif : Monter un service minimal, déclencher deux erreurs courantes et les corriger.

- Créer un service simple

cat >/usr/local/bin/hello.sh <<'EOF'
 #!/usr/bin/env bash
 set -euo pipefail
 : "${HELLO_MSG:=Hello}"
 echo "$(date -Is) $HELLO_MSG" | tee -a /var/log/hello/hello.log
 sleep 2
 EOF
 chmod +x /usr/local/bin/hello.sh
 install -d -m 0755 /var/log/hello

 cat >/etc/systemd/system/hello.service <<'EOF'
 [Unit]
 Description=Hello demo service
 Wants=network-online.target
 After=network-online.target

 [Service]
 Type=simple
 EnvironmentFile=-/etc/default/hello
 ExecStart=/usr/local/bin/hello.sh
 Restart=on-failure
 RestartSec=1s
 # Durcir tout en autorisant l'écriture des logs
 ProtectSystem=strict
 ReadWritePaths=/var/log/hello

 [Install]
 WantedBy=multi-user.target
 EOF

 install -m 0644 /dev/null /etc/default/hello
 printf 'HELLO_MSG=Hello from systemd\n' >> /etc/default/hello

 systemctl daemon-reload
 systemctl enable --now hello.service
 systemctl status hello --no-pager -l
 journalctl -u hello -b -n 50 --no-pager 

- Vérification du pilote : valider le comportement

- Attendez-vous à ce que le service démarre et écrive dans /var/log/hello/hello.log .

- Confirmez avec :

 tail -n 5 /var/log/hello/hello.log 

- Introduire l'erreur A : mauvais chemin ExecStart

 systemctl stop hello
 systemctl edit hello.service 
 Ajoutez dans le drop-in :

[Service]
 ExecStart=
 ExecStart=/usr/local/bin/hello-typo.sh 
 Puis :

systemctl daemon-reload
 systemctl start hello
 systemctl status hello -l --no-pager 
 Observez : Failed at step EXEC spawning ... No such file or directory .

Corriger A :

systemctl edit hello.service 
 Remplacez par :

[Service]
 ExecStart=
 ExecStart=/usr/local/bin/hello.sh 
 Rechargez et redémarrez.

- Introduire l'erreur B : boucle de plantage

sed -i '1i exit 1' /usr/local/bin/hello.sh # forcer l'échec au début
 systemctl restart hello
 journalctl -xeu hello --no-pager 
 Observez : Start request repeated too quickly si ça plante vite.

Corriger B :

- Retirez le exit injecté :

sed -i '1d' /usr/local/bin/hello.sh 

- Optionnellement, ajustez les limites pendant les tests :

 systemctl edit hello.service 
 Ajoutez :

[Unit]
 StartLimitIntervalSec=60
 StartLimitBurst=10 
 Rechargez et redémarrez.

- Inspecter et nettoyer

journalctl -u hello -b --no-pager
 systemctl disable --now hello
 rm -f /etc/systemd/system/hello.service
 systemctl daemon-reload 
 Pourquoi ce pilote fonctionne :

- Il est ciblé et mesurable : démarrage, écriture de log, deux échecs induits, deux correctifs.

- Il est facile à inspecter localement sans effets de bord.

## Conclusion

Quand systemd échoue, suivez un flux de travail cohérent : inspectez l'état, lisez les journaux, vérifiez l'unité, testez la commande manuellement, contrôlez les dépendances et le durcissement, puis appliquez les modifications en toute sécurité et rechargez. Gardez une aide-mémoire des commandes à portée de main et entraînez-vous avec un petit pilote local pour reconnaître les schémas rapidement. Avec ces étapes et exemples, vous transformerez des messages confus en causes racines claires et en correctifs sûrs et confiants.