Ubuntu 24.04 — Erreurs TLS et certificats après dérive horaire : réparer Chrony/NTP correctement

Cet article vous a aidé ?

Vous ne « déboguez » pas vraiment TLS. Vous déboguez l’heure. Le symptôme ressemble à des certificats qui « expirent » soudainement ou « ne sont pas encore valables », les mises à jour de paquets échouent, les API refusent la communication, et votre pageur commence à exprimer un avis sur votre rythme de sommeil.

Sur Ubuntu 24.04, la bonne réparation est ennuyeuse : rendre la synchronisation temporelle déterministe, observable et résiliente. Cela signifie généralement configurer Chrony intentionnellement, pas « comme l’image l’a fourni ». Faisons-le sérieusement.

Ce qui casse quand l’heure dérive (et pourquoi TLS panique)

La dérive d’horloge est une de ces pannes qui ressemble à « tout est cassé » parce qu’elle attaque les hypothèses sous-jacentes à tout. TLS est juste le premier système à se plaindre fortement parce qu’il a un sens du réel strict : les certificats ne sont valables que dans une fenêtre temporelle. Si l’horloge de votre hôte est incorrecte, le certificat peut être :

  • Pas encore valide (votre horloge est trop en retard)
  • Expiré (votre horloge est trop en avance)

Ce n’est que le premier acte. Vous pouvez aussi voir :

  • Échecs APT : les dépôts « échouent soudainement » avec des erreurs de poignée de main TLS ou des problèmes de validité des métadonnées.
  • Échecs OAuth/JWT : les tokens ont des claims nbf et exp ; une horloge décalée rend des tokens valides invalides.
  • Échecs Kerberos : Kerberos est notoirement strict sur le décalage horaire.
  • Comportements étranges du stockage distribué : baux, battements de cœur et hypothèses d’ordonnancement monotone peuvent dysfonctionner lors de sauts d’horloge.
  • Monitoring trompeur : les graphes ont des trous, les alertes déclenchent tard, ou les logs arrivent « du futur ».

Voici le modèle mental le plus important : corriger l’heure n’est pas la même chose que faire un saut immédiat de l’horloge. Dans les systèmes de production, des sauts brusques peuvent aussi casser des choses — en particulier les bases de données, caches et tout ce qui utilise l’expiration ou l’ordonnancement basé sur le temps. Chrony existe en partie parce qu’il peut corriger l’heure graduellement (« slew ») tout en restant raisonnable.

Une citation à garder : « L’espoir n’est pas une stratégie. » — idée souvent paraphrasée liée au management d’ingénierie et à la culture de la fiabilité. La synchronisation temporelle doit être conçue, pas espérée.

Mode opératoire de diagnostic rapide

Si vous êtes en astreinte et que TLS vient d’exploser sur une flotte, vous avez besoin d’une voie rapide. Ne poursuivez pas la chaîne de certificats pendant une heure. Vérifiez d’abord l’heure, puis décidez comment la corriger en toute sécurité.

Première étape : confirmez que vous avez réellement un problème d’heure

  1. Vérifiez l’heure locale et l’état de synchronisation (est-elle grossièrement erronée ? est-elle synchronisée ?).
  2. Vérifiez la santé de Chrony (sources, offset, statut de leap).
  3. Vérifiez si l’heure saute (reprise de VM, problèmes RTC, modifications manuelles).

Deuxième étape : déterminez le rayon d’impact

  1. S’agit-il d’un seul hôte (RTC défectueux, chrony mal configuré, problème d’hôte VM) ?
  2. S’agit-il d’un cluster entier (NTP interne cassé, règles de pare-feu, régression d’image) ?
  3. S’agit-il d’un seul segment réseau (UDP/123 bloqué, NAT étrange, DNS à horizon partagé) ?

Troisième étape : corriger l’heure par la méthode la moins dangereuse

  1. Si la dérive est faible : laissez Chrony la ramener par slew.
  2. Si la dérive est importante (minutes/heures) : planifiez un step contrôlé (impact sur les services), puis vérifiez TLS et les chemins d’authentification.
  3. Si l’heure continue de dériver : corrigez la cause sous-jacente (mauvaises sources NTP, réglages VM, RTC cassé, économies d’énergie agressives, instances en suspension).

Faits intéressants et contexte historique

La gestion du temps en informatique est plus ancienne que votre service le plus « legacy ». Quelques faits concrets qui aident à expliquer le comportement actuel :

  1. NTP précède le web commercial. Il a été conçu dans les années 1980 pour synchroniser des horloges sur des réseaux peu fiables — encore pertinent et encore utilisé.
  2. La validité TLS est volontairement temporelle pour que des certificats volés ne puissent pas être utilisés indéfiniment, et pour que les clients puissent raisonner sur la révocation et la rotation.
  3. Les secondes intercalaires existent, et les logiciels les ont historiquement gérées de manière inconsistante ; certains systèmes stepent, d’autres smearent, d’autres paniquent.
  4. Chrony a été conçu pour gérer la connectivité intermittente mieux que ntpd classique, ce qui compte pour les laptops, VM et sous-réseaux isolés.
  5. Les machines virtuelles peuvent beaucoup dériver après pause/suspension/migration — surtout quand l’intégration de la gestion du temps de l’hôte est mal configurée.
  6. Temps wall-clock et temps monotone sont différents. Beaucoup de systèmes dépendent de timers monotones pour les intervalles ; TLS se soucie du temps wall-clock.
  7. La durée de vie des certificats a diminué dans l’industrie pour réduire le risque, ce qui rend la précision temporelle encore plus importante.
  8. Certaines entreprises exécutent des hiérarchies NTP internes avec des ACL strictes ; une seule mauvaise modification peut isoler des milliers de machines du temps.

Le temps est une dépendance comme le DNS. Vous ne la remarquez pas tant qu’elle n’est plus là, puis tout devient un ballet interprété.

Blague #1 : La dérive horaire est le seul bug qui peut faire dire à vos logs que la panne s’est terminée avant d’avoir commencé. C’est comme voyager dans le temps, mais avec une documentation pire.

Tâches pratiques : commandes, sorties, décisions

Ci-dessous des tâches pratiques à exécuter sur Ubuntu 24.04 pour diagnostiquer et réparer des problèmes de synchronisation temporelle. Chaque tâche inclut : une commande, ce que la sortie typique signifie, et quelle décision prendre.

Task 1: Check system time, RTC, and sync flag

cr0x@server:~$ timedatectl
               Local time: Sun 2025-12-28 10:41:12 UTC
           Universal time: Sun 2025-12-28 10:41:12 UTC
                 RTC time: Sun 2025-12-28 10:41:10
                Time zone: Etc/UTC (UTC, +0000)
System clock synchronized: no
              NTP service: active
          RTC in local TZ: no

Ce que cela signifie : Le service NTP est « active » mais l’horloge système n’est pas synchronisée. Cela signifie généralement que le démon tourne mais ne peut pas atteindre les sources ou ne leur fait pas encore confiance.

Décision : Passez à l’état de Chrony et aux sources. Si « System clock synchronized » reste no pendant plus de quelques minutes après le démarrage, vous avez probablement des problèmes de source/connectivité.

Task 2: Identify whether Chrony is actually installed and running

cr0x@server:~$ systemctl status chrony --no-pager
● chrony.service - chrony, an NTP client/server
     Loaded: loaded (/usr/lib/systemd/system/chrony.service; enabled; preset: enabled)
     Active: active (running) since Sun 2025-12-28 10:39:44 UTC; 1min 26s ago
       Docs: man:chronyd(8)
             man:chronyc(1)
   Main PID: 1325 (chronyd)
      Tasks: 1 (limit: 38228)
     Memory: 2.7M (peak: 3.1M)
        CPU: 148ms
     CGroup: /system.slice/chrony.service
             └─1325 /usr/sbin/chronyd -F 1

Ce que cela signifie : Chrony fonctionne. Bien. Il faut maintenant vérifier s’il a des sources utilisables.

Décision : Si Chrony n’est pas installé, installez-le et désactivez les démons de temps concurrents. S’il tourne, inspectez son état de tracking et ses sources.

Task 3: Check Chrony tracking (the single most useful snapshot)

cr0x@server:~$ chronyc tracking
Reference ID    : 00000000 ()
Stratum         : 0
Ref time (UTC)  : Thu Jan 01 00:00:00 1970
System time     : 12.483912345 seconds slow of NTP time
Last offset     : +0.000000000 seconds
RMS offset      : 0.000000000 seconds
Frequency       : 0.000 ppm
Residual freq   : 0.000 ppm
Skew            : 0.000 ppm
Root delay      : 1.000000000 seconds
Root dispersion : 1.000000000 seconds
Update interval : 0.0 seconds
Leap status     : Not synchronised

Ce que cela signifie : Stratum 0, Reference ID vide, leap status not synchronized : Chrony n’est pas verrouillé sur une source. L’horloge a 12,48 secondes de retard ; c’est suffisant pour déclencher des vérifications TLS strictes dans certains environnements.

Décision : Regardez chronyc sources -v. Si les sources sont inaccessibles, corrigez le réseau/DNS/ACLs. Si accessibles mais « non sélectionnées », corrigez la liste des serveurs NTP ou les paramètres de confiance.

Task 4: Inspect sources and selection

cr0x@server:~$ chronyc sources -v
  .-- Source mode  '^' = server, '=' = peer, '#' = local clock.
/ .- Source state '*' = current best, '+' = combined, '-' = not combined,
| /             'x' = may be in error, '~' = too variable, '?' = unusable.
||                                                 .- xxxx [ yyyy ] +/- zzzz
||      Reachability register (octal)              |  xxxx = adjusted offset,
||      Log2(Polling interval)                     |  yyyy = measured offset,
||                                                 |  zzzz = estimated error.
||                                                 |
MS Name/IP address         Stratum Poll Reach LastRx Last sample
===============================================================================
^? ntp1.corp.local               0   6     0     -     +0ns[   +0ns] +/-    0ns
^? ntp2.corp.local               0   6     0     -     +0ns[   +0ns] +/-    0ns

Ce que cela signifie : ^? indique des sources inutilisables, et Reach est 0. Chrony ne peut pas leur parler (échec DNS, routage, pare-feu, ACL, ou les serveurs sont hors service).

Décision : Testez la résolution DNS et la connectivité UDP/123. Si le NTP interne est injoignable, vous avez besoin d’une alternative publique/interne temporaire approuvée par la politique — ou de déployer une source temporelle locale.

Task 5: Verify DNS resolution for NTP sources

cr0x@server:~$ resolvectl query ntp1.corp.local
ntp1.corp.local: 10.20.30.40                       -- link: eth0

-- Information acquired via protocol DNS in 5.2ms.
-- Data is authenticated: no

Ce que cela signifie : DNS résout. Bien. Si cela échoue, vous déboguez DNS, pas NTP.

Décision : Si le DNS échoue, corrigez la configuration du résolveur ou les problèmes de split-horizon. Si le DNS fonctionne, testez la portée réseau vers UDP/123.

Task 6: Test NTP reachability (UDP/123) with chronyc

cr0x@server:~$ chronyc -N ntpdata ntp1.corp.local
Remote address  : 10.20.30.40 (10.20.30.40)
Leap status     : Normal
Version         : 4
Stratum         : 2
Poll interval   : 6 (64 seconds)
Precision       : -23 (119.209ns)
Root delay      : 0.001297 seconds
Root dispersion : 0.003418 seconds
Reference ID    : 4C4F434C
Reference time  : Sun Dec 28 10:41:10 2025
Offset          : -0.000412345 seconds
Peer delay      : 0.000812 seconds
Peer dispersion : 0.000244 seconds

Ce que cela signifie : Le serveur répond et semble sain (stratum 2, leap status normal). Cela suggère que le chemin réseau est correct et que le problème est la configuration ou la sélection de Chrony.

Décision : Si ntpdata expire, corrigez le pare-feu/ACL/routage. Si cela fonctionne mais que les sources montrent toujours ^?, cherchez des restrictions Chrony, un mauvais binding d’interface, ou un sandboxing systemd.

Task 7: Check whether another time service is fighting Chrony

cr0x@server:~$ systemctl list-units --type=service | grep -E 'chrony|timesync|ntp'
chrony.service                          loaded active running chrony, an NTP client/server
systemd-timesyncd.service               loaded active running Network Time Synchronization

Ce que cela signifie : Chrony et systemd-timesyncd tournent tous les deux. Ce n’est pas un plan de redondance intelligent ; c’est deux pilotes se battant pour le volant.

Décision : Choisissez-en un. Sur les serveurs, préférez Chrony. Désactivez systemd-timesyncd quand vous utilisez Chrony.

Task 8: Disable systemd-timesyncd if Chrony is your chosen source of truth

cr0x@server:~$ sudo systemctl disable --now systemd-timesyncd
Removed "/etc/systemd/system/sysinit.target.wants/systemd-timesyncd.service".
Stopped systemd-timesyncd.service - Network Time Synchronization.

Ce que cela signifie : timesyncd ne tourne plus ; Chrony peut faire son travail sans interférence.

Décision : Vérifiez de nouveau timedatectl et les sources Chrony après une minute.

Task 9: Inspect Chrony configuration for bad server lines and policies

cr0x@server:~$ grep -E '^(server|pool|makestep|rtcsync|keyfile|driftfile|bindcmdaddress|bindaddress)' /etc/chrony/chrony.conf
pool ntp.ubuntu.com iburst
makestep 1 3
rtcsync
driftfile /var/lib/chrony/chrony.drift

Ce que cela signifie : Le pool par défaut est utilisé, makestep 1 3 permet de stepper l’horloge par n’importe quel montant seulement durant les trois premières mises à jour (généralement juste après le démarrage), ensuite il fera du slew. rtcsync synchronise périodiquement l’horloge matérielle.

Décision : Dans les réseaux d’entreprise, on veut généralement des serveurs NTP internes explicites, pas des pools publics. Décidez aussi si makestep est approprié pour votre flotte (plus bas on en parle).

Task 10: Replace NTP sources with explicit, redundant servers (example)

cr0x@server:~$ sudoedit /etc/chrony/chrony.conf
...file opened in editor...

Ce que cela signifie : Vous éditez pour l’intention. Une bonne liste de serveurs est explicite, redondante et locale par rapport à votre topologie réseau.

Décision : Utilisez au moins 3 sources si possible. Préférez des serveurs internes stratum 1/2. Conservez iburst pour une synchronisation initiale plus rapide.

Task 11: Restart Chrony and force a quick re-evaluation of sources

cr0x@server:~$ sudo systemctl restart chrony
cr0x@server:~$ sudo chronyc online
200 OK
cr0x@server:~$ chronyc sources -v
MS Name/IP address         Stratum Poll Reach LastRx Last sample
===============================================================================
^+ ntp1.corp.local               2   6   377    12   -221us[ -341us] +/-  6.1ms
^* ntp2.corp.local               2   6   377    10    -12us[ -128us] +/-  4.8ms
^+ ntp3.corp.local               3   6   377    11   +145us[  +31us] +/-  8.9ms

Ce que cela signifie : Reach 377 signifie que les paquets circulent. ^* est la meilleure source sélectionnée. Des offsets en microsecondes sont acceptables ; une erreur estimée en millisecondes est acceptable pour TLS et la plupart des systèmes distribués.

Décision : Si vous voyez encore ^? ou que Reach reste bas, déboguez la connectivité et la santé des serveurs. Si vous voyez ^~ (trop variable), envisagez la gigue réseau, les chemins VPN ou un hôte VM bruyant.

Task 12: Confirm the system considers time synchronized now

cr0x@server:~$ timedatectl
               Local time: Sun 2025-12-28 10:44:18 UTC
           Universal time: Sun 2025-12-28 10:44:18 UTC
                 RTC time: Sun 2025-12-28 10:44:18
                Time zone: Etc/UTC (UTC, +0000)
System clock synchronized: yes
              NTP service: active
          RTC in local TZ: no

Ce que cela signifie : L’horloge du noyau est synchronisée et le RTC est aligné. Voilà à quoi ressemble une correction réussie.

Décision : Testez de nouveau les chemins clients TLS qui échouaient (apt, curl, votre application).

Task 13: If time is wildly wrong, step safely (and admit it will be disruptive)

cr0x@server:~$ chronyc tracking
Reference ID    : 4C4F434C (ntp2.corp.local)
Stratum         : 3
Ref time (UTC)  : Sun Dec 28 10:44:40 2025
System time     : 4231.218123456 seconds fast of NTP time
Last offset     : -0.003212345 seconds
RMS offset      : 0.001002000 seconds
Frequency       : 18.122 ppm
Residual freq   : -0.441 ppm
Skew            : 2.112 ppm
Root delay      : 0.001102 seconds
Root dispersion : 0.010843 seconds
Update interval : 64.0 seconds
Leap status     : Normal

Ce que cela signifie : Vous avez plus d’une heure d’avance. Laisser cela revenir par slew pourrait prendre beaucoup de temps, et vous aurez entre-temps des échecs TLS/JWT continus.

Décision : Envisagez un step contrôlé. Sur de nombreux services, un saut d’une heure provoquera des bizarreries temporaires ; planifiez-le, communiquez-le et redémarrez les démons les plus sensibles au temps ensuite.

Task 14: Force a step with Chrony (use sparingly)

cr0x@server:~$ sudo chronyc makestep
200 OK

Ce que cela signifie : Chrony a stepé l’horloge immédiatement pour corriger l’offset. Cela peut réparer TLS instantanément, et casser d’autres choses instantanément. Choisissez votre poison, mais choisissez-le consciemment.

Décision : Après un step, validez les applications critiques (bases de données, queues, authentification). Si vous exécutez des services sensibles au temps, des redémarrages peuvent être nécessaires.

Task 15: Check for recent manual time changes (smoking gun)

cr0x@server:~$ journalctl -u chrony -u systemd-timesyncd --since "2 hours ago" --no-pager | tail -n 25
Dec 28 10:39:44 server chronyd[1325]: chronyd version 4.5 starting (+CMDMON +NTP +REFCLOCK +RTC +PRIVDROP +SCFILTER +SIGND +ASYNCDNS +NTS +SECHASH)
Dec 28 10:40:12 server chronyd[1325]: System clock wrong by 12.487 seconds, adjustment started
Dec 28 10:43:01 server chronyd[1325]: Selected source 10.20.30.41
Dec 28 10:44:19 server chronyd[1325]: System clock was stepped by 4231.218 seconds

Ce que cela signifie : Les logs admettent qu’un step a eu lieu. Si vous ne l’avez pas fait, quelque chose d’autre l’a fait (cloud-init, un script mal configuré, une image golden, ou un runbook « corriger le temps » trop zélé).

Décision : Identifiez l’acteur : automatisation, humain, ou plateforme VM. Puis empêchez les récidives. L’incident le plus grave est celui que vous « corrigez » tous les mardis.

Task 16: Validate TLS from the host after time is correct

cr0x@server:~$ openssl s_client -connect archive.ubuntu.com:443 -servername archive.ubuntu.com -brief
CONNECTION ESTABLISHED
Protocol version: TLSv1.3
Ciphersuite: TLS_AES_256_GCM_SHA384
Peer certificate: CN=*.ubuntu.com
Hash used: SHA256
Signature type: RSA-PSS
Verification: OK
Server Temp Key: X25519, 253 bits

Ce que cela signifie : La vérification est OK. Si ceci échouait auparavant avec « not yet valid », le temps en était la cause.

Décision : Si la vérification échoue encore, vous pourriez avoir un problème de magasin de confiance CA ou un proxy d’interception. Le temps est nécessaire mais pas toujours suffisant.

Task 17: Verify APT can negotiate TLS again

cr0x@server:~$ sudo apt-get update
Hit:1 http://archive.ubuntu.com/ubuntu noble InRelease
Hit:2 http://archive.ubuntu.com/ubuntu noble-updates InRelease
Hit:3 http://security.ubuntu.com/ubuntu noble-security InRelease
Reading package lists... Done

Ce que cela signifie : APT est content. Quand l’heure est erronée, vous verrez souvent des erreurs de poignée de main TLS ou des avertissements de validité des métadonnées.

Décision : Si APT échoue encore mais qu’OpenSSL fonctionne, suspectez une configuration de proxy, des certificats épinglés ou des métadonnées de dépôt problématiques.

Corriger Chrony correctement sur Ubuntu 24.04

Chrony est généralement le bon choix pour les serveurs : convergence rapide, bon comportement sur des réseaux imparfaits, et bonne observabilité. La mauvaise façon de « réparer le temps » est d’exécuter un one-liner au hasard qui steppe l’horloge et de se déclarer victorieux. Vous récupérerez votre TLS puis passerez l’après-midi à déboguer une base de données qui pense maintenant que le futur est déjà arrivé.

Choisissez un seul démon de synchronisation temporelle et engagez-vous

Sur Ubuntu, vous trouverez souvent :

  • systemd-timesyncd : client SNTP léger, suffisant pour des endpoints simples.
  • chronyd (Chrony) : client/serveur NTP complet, meilleures diagnostics et contrôle.

Choisissez-en un. Pour des serveurs de production, choisissez Chrony sauf raison contraire forte. Faire tourner les deux n’est pas de la résilience ; c’est une auto-sabotage avec des ambitions de disponibilité.

Utilisez des sources temporelles explicites, pas des sensations

Les pools par défaut peuvent convenir sur l’Internet public, mais la réalité d’entreprise inclut pare-feu, proxies, DNS à horizon partagé et « egress approuvé ». Sur une flotte, vous voulez des serveurs explicites et redondants :

  • Au moins trois serveurs si possible.
  • Même région / faible latence si possible.
  • Domaines de panne différents (pas trois VM sur le même hôte).

Exemple de fragment de configuration Chrony (illustratif) :

cr0x@server:~$ sudo bash -lc 'cat > /etc/chrony/sources.d/corp.sources <<EOF
server ntp1.corp.local iburst
server ntp2.corp.local iburst
server ntp3.corp.local iburst
EOF'

Ce que cela signifie : Une séparation propre : chrony.conf de base plus un fichier dédié pour les sources d’entreprise. Plus facile à gérer avec des outils de configuration.

Décision : Placez les sources dans un fichier géré pour que « quelqu’un corrige rapidement la liste des serveurs » ne devienne pas votre architecture à long terme.

Comprendre step vs slew (et définir une politique)

Chrony peut corriger l’heure de deux manières :

  • Slew : ajuster progressivement la vitesse de l’horloge. Plus sûr pour les applications. Plus lent pour corriger de grands offsets.
  • Step : sauter l’heure immédiatement. Répare TLS rapidement. Peut casser des logiciels sensibles au temps.

La directive makestep est le bouton de politique. Exemple :

  • makestep 1 3 : faire un step si offset > 1s pendant les 3 premières mises à jour, puis ne plus stepper automatiquement.
  • makestep 0.5 -1 : step si offset > 0.5s à tout moment (agressif ; n’utilisez que si vous savez pourquoi).

Sur des serveurs avec une authentification TLS stricte, stepper au démarrage peut être raisonnable. L’auto-step en état stable est plus risqué ; vous ne voulez pas un saut en plein milieu de la journée parce qu’une source est devenue bizarre et que Chrony « aide ».

Faites se comporter correctement l’horloge matérielle (RTC)

Une mauvaise configuration du RTC est une cause classique de « l’heure est fausse après redémarrage ». Sur les serveurs Linux, gardez le RTC en UTC :

cr0x@server:~$ timedatectl set-local-rtc 0
cr0x@server:~$ timedatectl
               Local time: Sun 2025-12-28 10:45:22 UTC
           Universal time: Sun 2025-12-28 10:45:22 UTC
                 RTC time: Sun 2025-12-28 10:45:22
                Time zone: Etc/UTC (UTC, +0000)
System clock synchronized: yes
              NTP service: active
          RTC in local TZ: no

Ce que cela signifie : RTC est en UTC. Bien. Les systèmes dual-boot définissent parfois le RTC en heure locale ; les serveurs ne devraient pas le faire.

Décision : Si vous dual-bootez un serveur, vous avez des problèmes plus importants, mais oui : gardez le RTC en UTC.

Soyez prudents avec les VM et instances cloud

Si votre hôte est virtualisé, l’heure peut dériver lorsque :

  • La VM est mise en pause/reprise
  • Une migration à chaud a lieu
  • L’hôte est surchargé et l’invité perd du temps CPU
  • L’intégration de synchronisation temporelle de l’hyperviseur lutte contre NTP

La correction dépend de la plateforme, mais le schéma est constant : choisissez une seule autorité. Si l’hyperviseur fournit un temps stable, laissez l’invité utiliser NTP pour discipliner la petite dérive — pas pour se battre contre de grands sauts créés par suspend/reprise. Si vous observez des steps fréquents et importants, corrigez d’abord le comportement du cycle de vie de la VM.

Rendez Chrony observable

Si vous ne pouvez pas mesurer l’offset, vous devinez. Au minimum, capturez :

  • chronyc tracking périodiquement (offset, stratum, leap status)
  • chronyc sources -v pour la portée et la gigue
  • les logs du démon autour du boot et de la reprise

La plupart des incidents ici ne sont pas « Chrony est cassé. » Ils sont « Chrony vous dit la vérité et vous n’avez pas regardé. »

Blague #2 : NTP est le seul service où « reach 377 » est une bonne nouvelle. Le réseau est un choix de carrière étrange.

Vérifications TLS/cert après réparation de l’heure

Une fois l’heure stable, validez que les échecs TLS ont réellement disparu — et confirmez que vous n’avez pas découvert un second problème que le temps masquait.

Vérifiez le message d’erreur exact

Les messages TLS courants liés au temps incluent :

  • certificate is not yet valid
  • certificate has expired
  • bad certificate (moins spécifique ; peut encore être lié au temps dans certaines piles)

Si l’erreur concerne « unknown CA » ou « self-signed certificate in certificate chain », corriger l’heure n’aidera pas. Ne forcez pas la situation.

Validez la santé du magasin de confiance local (vérification rapide)

cr0x@server:~$ dpkg -l | grep -E '^ii\s+ca-certificates\s'
ii  ca-certificates  20240203  all  Common CA certificates

Ce que cela signifie : Le paquet de bundle CA est installé. Bien.

Décision : Si manquant ou corrompu, réinstallez. Si présent, concentrez-vous sur le temps, l’interception proxy, ou le pinning applicatif.

Confirmez que le noyau et l’espace utilisateur sont d’accord sur l’heure

cr0x@server:~$ date -u
Sun Dec 28 10:46:01 UTC 2025
cr0x@server:~$ python3 -c 'import datetime; print(datetime.datetime.utcnow().isoformat()+"Z")'
2025-12-28T10:46:02.193847Z

Ce que cela signifie : La concordance entre les outils suggère qu’il n’y a pas de trucs étranges de namespace temporel de conteneur ou d’appels libc du temps cassés.

Décision : Si les conteneurs affichent une heure différente de l’hôte, vérifiez les paramètres du runtime de conteneur et les hypothèses sur le namespace d’horloge de l’hôte (rare, mais réel dans certains environnements durcis).

Trois micro-récits du monde corporate

Mini-récit 1 : L’incident causé par une mauvaise hypothèse

Ils avaient un « réseau interne sécurisé ». Pas d’accès Internet sortant. Tout passait par des points d’egress approuvés, et pour l’heure ils utilisaient deux serveurs NTP internes. Quelqu’un a supposé que ces serveurs NTP étaient aussi fondamentaux que le DNS, donc ils n’en ont jamais fait une partie du catalogue de services monitorés. Ils étaient juste… là. Comme la gravité.

Une fenêtre de changement est passée. Un ingénieur réseau a resserré les ACL sur un switch core, visant à réduire le trafic UDP inutile. UDP/123 n’a pas été explicitement autorisé depuis un nouveau subnet utilisé par des nœuds applicatifs fraîchement provisionnés. Ce n’était pas bloqué par malveillance ; c’était bloqué par indifférence, ce qui est la naissance de la plupart des pannes.

En quelques heures, les nœuds de ce subnet ont commencé à dériver. Rien d’évident au début. Puis une rotation de certificats a poussé une nouvelle feuille avec une date de début de validité légèrement dans le futur par rapport aux nœuds dérivants. Soudain, les services dans le nouveau subnet ne pouvaient rien appeler. L’astreinte a vu des erreurs TLS et a roté à nouveau des certificats, ce qui n’a fait que créer plus de réunions.

La réparation a été deux lignes dans une ACL et une action post-mortem : traiter le NTP interne comme une dépendance Tier-0 avec monitoring, alertes et revue de changement. La mauvaise hypothèse n’était pas « les ACL sont sûres ». C’était « le temps s’occupera de lui-même ».

Mini-récit 2 : L’optimisation qui s’est retournée contre eux

Une équipe soucieuse de performance voulait des temps de boot plus rapides sur du compute éphémère. Ils ont coupé des services. Ils ont désactivé des « daemons supplémentaires ». Ils ont aussi remplacé Chrony par un client SNTP minimal et un stepping agressif parce que « nous avons juste besoin que l’heure soit à peu près correcte ». C’est le genre de phrase qui devrait déclencher une petite alarme dans votre tête.

La plupart du temps ça fonctionnait. Puis une source temporelle en amont a eu un problème de courte durée : un serveur a commencé à rapporter une heure avec un décalage notable. Un client NTP robuste comparerait les sources, détecterait l’incohérence et éviterait de sélectionner l’acteur défaillant. Le client minimal avait moins de garde-fous et a stepé l’horloge en vol.

Le step a fait que leur couche de cache a évincé des entrées incorrectement (logique TTL basée sur le temps partie en sucette). Les métriques se sont brouillées. Quelques jobs en arrière-plan sont passés deux fois parce que la « prochaine exécution » avait reculé. Leur post-mortem a été pénible car les logs n’étaient pas d’accord sur l’ordre entre nœuds. Chaque graphe ressemblait à de l’art moderne.

Ils ont réintroduit Chrony, l’ont fixée sur des sources internes fiables, et ont mis une politique de stepping conservatrice : steppez tôt au boot si besoin, slew en état stable. L’« optimisation » a économisé des secondes et leur a coûté une journée. Ce n’est pas un compromis ; c’est une farce.

Mini-récit 3 : La pratique ennuyeuse mais correcte qui a sauvé la mise

Une autre entreprise avait une règle terne : chaque image serveur doit embarquer la même configuration Chrony, et chaque environnement doit avoir trois sources NTP accessibles. Pas d’exceptions, pas de finesse. Ils collectaient aussi des métriques de tracking Chrony et ouvraient un ticket automatiquement si l’offset dépassait un petit seuil pendant plus de quelques minutes.

Un matin, un cluster d’hyperviseurs a commencé à subir une charge lourde. Certains invités ont commencé à dériver, pas de quelques secondes mais de dizaines de secondes. Avant que les équipes applicatives ne remarquent, le monitoring a signalé l’anomalie d’offset temporel. Les SRE ont corrélé le problème au pool d’hyperviseurs et ont déplacé la charge pendant que l’équipe de virtualisation résolvait la contention.

Le meilleur : rien de dramatique ne s’est produit. Pas de mélodrame TLS. Pas de tempêtes de tokens. Pas de débogage héroïque à minuit. Le rapport d’incident était court et profondément inintéressant : « Dérive détectée tôt ; charge déplacée ; contention hôte corrigée ; synchronisation vérifiée. » Voilà le genre d’ennui que vous devriez viser.

Erreurs courantes : symptôme → cause racine → correction

Cette section révèle où la plupart des pannes temporelles se sont autoprovocées. Pas parce que les gens sont négligents — parce que les systèmes distribués punissent l’ambiguïté.

1) TLS indique « certificate is not yet valid » juste après un reboot

Cause racine : RTC incorrect, ou Chrony ne peut pas atteindre les sources tôt au démarrage ; le système démarre avec une heure périmée.

Correction : Assurez-vous que le RTC est en UTC, activez rtcsync, et configurez makestep pour stepper lors des premières mises à jour. Vérifiez aussi que les sources NTP sont joignables depuis le sous-réseau au démarrage (ACLs, routage, DNS).

2) « NTP service: active » mais « System clock synchronized: no » pour toujours

Cause racine : Le démon tourne mais n’a pas de sources valides (^?, Reach 0), ou il est en compétition avec un autre démon.

Correction : Utilisez chronyc tracking et chronyc sources -v. Désactivez systemd-timesyncd si vous utilisez Chrony. Corrigez les règles pare-feu pour UDP/123.

3) L’heure saute en arrière/en avant occasionnellement ; les applis deviennent bizarres

Cause racine : Politique de stepping agressive (makestep trop permissif), ou suspend/reprise VM causant de grands sauts et corrections.

Correction : Limitez le stepping au démarrage (ex. makestep 1 3). Corrigez la gestion de l’hôte VM et évitez les conflits guest/hypervisor.

4) Chrony affiche des sources mais les marque « trop variables » (^~)

Cause racine : Chemin à forte gigue (VPN, réseau surchargé, routage asymétrique) ou sources temporelles instables en amont.

Correction : Préférez des serveurs NTP locaux. Réduisez la gigue. Ajoutez de meilleures sources. Si nécessaire, augmentez la stabilité de polling et évitez de traverser WAN/VPN pour le temps primaire.

5) Tout casse après que quelqu’un a exécuté date -s

Cause racine : Le réglage manuel de l’heure fait un step sans coordination ; les applis voient une discontinuité temporelle.

Correction : Arrêtez de régler manuellement l’heure sur des serveurs de production. Utilisez Chrony avec un stepping contrôlé et documentez quand un step forcé est acceptable.

6) Certificats Kubernetes / service mesh échouent de manière intermittente sur des nœuds

Cause racine : Le décalage d’horloge des nœuds provoque des échecs de mTLS ou une désynchronisation lors de rotations de certificats à courte durée de vie.

Correction : Imposer la synchronisation temporelle au bootstrap des nœuds, monitorer la dérive, et bloquer l’ordonnancement sur les nœuds avec un offset élevé jusqu’à correction.

Listes de contrôle / plan pas-à-pas

Checklist A: Immediate incident response (single host)

  1. Exécutez timedatectl ; si « System clock synchronized: no », poursuivez.
  2. Exécutez chronyc tracking ; confirmez leap status et amplitude de l’offset.
  3. Exécutez chronyc sources -v ; vérifiez Reach et la sélection (^*).
  4. Si les sources sont injoignables : testez DNS et portée NTP (resolvectl query, chronyc ntpdata).
  5. Assurez-vous qu’un seul démon de temps est actif (désactivez systemd-timesyncd si vous utilisez Chrony).
  6. Redémarrez Chrony, mettez les sources en ligne (systemctl restart chrony, chronyc online).
  7. Si l’offset est énorme et que vous devez restaurer TLS immédiatement : chronyc makestep, puis validez les services critiques.
  8. Retestez TLS et APT (openssl s_client, apt-get update).

Checklist B: Fleet-wide containment

  1. Choisissez un hôte canari par sous-réseau ; mesurez l’offset et la joignabilité.
  2. Validez la santé des serveurs NTP internes et les ACLs depuis chaque zone réseau.
  3. Déployez la config Chrony avec des serveurs explicites et une politique de stepping conservatrice.
  4. Ajoutez du monitoring : alertez lorsque leap status n’est pas synchronisé pendant une période soutenue ou que l’offset dépasse un seuil.
  5. Bloquez ou cordonnez les nœuds avec forte dérive (spécifique à la plateforme) jusqu’à correction.

Checklist C: Prevent recurrence (the part people skip)

  1. Faites des sources NTP une dépendance gérée avec contrôle des changements (comme le DNS).
  2. Assurez-vous d’au moins trois sources et testez-les pendant le provisioning.
  3. Journalisez et alertez sur les steps temporels ; les steps inattendus doivent être investigués.
  4. Documentez si votre environnement autorise le stepping en état stable. La plupart ne devraient pas.
  5. Pour les VMs : validez l’intégration hyperviseur et le comportement lors de suspend/reprise/migration.

FAQ

1) Pourquoi les erreurs TLS apparaissent-elles avant tout le reste ?

La validation TLS est explicitement temporelle. Si le wall-clock est faux, la poignée de main échoue immédiatement. D’autres systèmes peuvent tolérer du décalage ou échouer plus tard.

2) Dois-je utiliser systemd-timesyncd ou Chrony sur des serveurs Ubuntu 24.04 ?

Utilisez Chrony pour les serveurs de production sauf si vous avez une raison solide de ne pas le faire. Il offre de meilleurs diagnostics, une meilleure gestion des réseaux imparfaits et plus de contrôle sur le stepping/slewing.

3) Est-il sûr d’exécuter à la fois Chrony et systemd-timesyncd ?

Non. Choisissez-en un. Deux démons ajustant la même horloge est un anti-pattern de fiabilité qui produit des dérives et des steps intermittents difficiles à expliquer.

4) Quelle est la preuve la plus rapide que le temps est le problème ?

timedatectl affichant « System clock synchronized: no » plus chronyc tracking affichant « Leap status: Not synchronised » suffit généralement. Aussi, les erreurs TLS mentionnant « not yet valid » sont presque une confession.

5) Quand devrais-je utiliser chronyc makestep ?

Quand l’offset est suffisamment grand pour que le slew prenne trop de temps et que vous devez restaurer rapidement des chemins TLS/auth critiques. Faites-le en connaissance de cause : le step peut casser des applications sensibles au temps.

6) Pourquoi Chrony montre des sources mais ne synchronise toujours pas ?

Parce que toutes les sources ne sont pas dignes de confiance ou sélectionnables. Vérifiez chronyc sources -v pour ^*, Reach, et des états comme ^? (inutilisable) ou ^x (en erreur).

7) Mes serveurs NTP sont joignables, mais l’offset continue de croître. Que faire ?

Examinez la virtualisation et la charge de l’hôte. Les invités peuvent dériver sous famine CPU, et la suspension/reprise peut causer de grands sauts. Corrigez le comportement de la plateforme ; Chrony ne peut pas violer la physique.

8) Les secondes intercalaires importent-elles encore pour ce problème ?

Normalement non pour les échecs TLS quotidiens, mais elles comptent pour la correction à long terme et pour les systèmes qui gèrent mal les événements de leap. Le point pratique : utilisez un système temporel discipliné, pas des correctifs ad-hoc.

9) Quelle précision est nécessaire pour TLS ?

TLS tolère généralement un petit décalage, mais les systèmes modernes avec certificats de courte durée, clients stricts et auth basée sur des tokens peuvent être sensibles. Visez une synchronisation serrée et alertez sur la dérive avant qu’elle atteigne des secondes à minutes.

10) Après avoir corrigé l’heure, pourquoi certains services échouent-ils encore jusqu’à redémarrage ?

Certaines applications mettent en cache des décisions dépendantes du temps (fenêtres de validation de tokens, expiration de sessions, tâches planifiées) ou sont perturbées après un step temporel. Si vous avez stepé l’heure, redémarrer les composants critiques peut être la récupération la plus propre.

Conclusion : prochaines actions à faire réellement

Si des erreurs TLS/cert sont apparues après une dérive horaire, ne traitez pas cela comme un mystère de certificats. Traitez-le comme une dépendance d’infrastructure qui échoue silencieusement. La bonne voie est cohérente :

  1. Prouvez que c’est le temps : timedatectl, chronyc tracking, chronyc sources -v.
  2. Faites de Chrony l’autorité unique (ou choisissez explicitement timesyncd, mais pas les deux).
  3. Utilisez des sources NTP explicites et redondantes adaptées à votre réalité réseau.
  4. Définissez une politique de stepping acceptable : stepper au démarrage si nécessaire ; éviter les steps surprises en état stable.
  5. Instrumentez et alertez sur la dérive pour corriger l’heure avant qu’elle ne vous corrige.

Faites cela, et la prochaine fois que des certificats « expirent aléatoirement », vous le réparerez en quelques minutes — avec moins de réunions, moins de mystères, et moins de gens découvrant sous stress ce que signifie UTC.

← Précédent
Scénarios de catastrophe ZFS : ce qui casse en premier et ce que vous pouvez sauver
Suivant →
Intel vs AMD dans les jeux : où les benchmarks vous induisent en erreur

Laisser un commentaire