Résumé

  • Un abonnement DNS Push accepté autorise le client à ne plus décrémenter le TTL des enregistrements concernés, car le serveur s’engage à lui annoncer les changements pendant la session DSO.
  • La fermeture de la connexion met fin aux abonnements. La reprise cryptographique de TLS accélère la reconnexion, mais elle ne restitue aucun état DSO : le client doit se réabonner et recevoir un nouvel état initial.
  • La preuve de fraîcheur doit relier découverte, authentification, session, réponse SUBSCRIBE, messages PUSH ordonnés, état de l’horloge TTL et santé réelle du service. Aucun voyant unique ne porte ces six affirmations.

Le certificat est revenu, pas l’obligation

Imaginons un cas d’exploitation, explicitement fictif. Une application suit un RRset SRV qui désigne un service local. Le serveur accepte l’abonnement et envoie immédiatement un premier PUSH contenant une cible assortie d’un TTL de 120 secondes. Tant que l’abonnement reste actif, le client conserve cette valeur sans faire descendre le compteur. Dix minutes plus tard, l’opérateur retire la cible. Presque simultanément, un équipement intermédiaire coupe la connexion persistante.

TLS reprend vite grâce à un ticket. La supervision du transport passe au vert. Pourtant, aucun nouveau SUBSCRIBE n’est envoyé sur la nouvelle session DSO. L’ancienne obligation du serveur — avertir ce client de la suppression — n’existe plus. Si le cache continue malgré tout à figer le TTL, il donne une durée indéfinie à une donnée dont l’autorité n’avait accordé que 120 secondes.

RFC 8765 ne laisse pas cette frontière implicite. La fermeture de la connexion TLS termine la session DSO, et la reprise TLS ne restaure aucun abonnement. Il faut recréer chacun d’eux. Le gain cryptographique de la reprise n’est donc pas une continuité de l’état applicatif. Confondre les deux, c’est attribuer au canal un mandat que seul un échange SUBSCRIBE accepté pouvait créer.

La fraîcheur change de dépositaire

Dans le DNS classique, le TTL organise une responsabilité simple. Le producteur publie une durée de conservation ; le cache la fait décroître ; à zéro, il doit cesser de présenter la donnée comme fraîche. Une interrogation ultérieure renouvelle éventuellement cette preuve. Pour un ensemble qui change souvent, cette discipline peut provoquer beaucoup de requêtes ne rapportant aucune nouveauté.

DNS Push remplace ce coût répétitif par de l’état. Le client demande un abonnement pour un triplet exact NAME, TYPE, CLASS. Le serveur accepte ou refuse chaque demande. Si l’ensemble de réponses est déjà non vide au moment de l’acceptation, un PUSH initial suit immédiatement. Les additions et retraits suivants sont transmis de manière asynchrone sur le flux TLS/TCP ordonné.

Le mécanisme justifie alors une règle exceptionnelle : le client enregistre le TTL d’un ajout, mais ne le décrémente plus pendant que l’abonnement pertinent est actif. Une modification du TTL serait elle-même annoncée ; la disparition d’un RR doit aussi l’être. La fraîcheur n’a pas été rendue éternelle. Son dépositaire a changé. Le compte à rebours est remplacé par une obligation de livraison attachée à une session.

Cette substitution a une date de fin vérifiable. UNSUBSCRIBE met fin à un abonnement ; la fermeture de la session DSO les termine tous. Le vieillissement reprend alors à partir du TTL mémorisé, jusqu’à l’élimination à zéro. Un cache qui ne peut pas montrer l’instant exact du gel et de la reprise de l’horloge ne peut pas justifier son verdict « à jour ».

Découvrir un serveur n’est pas lui céder toute autorité

Le premier chemin passe normalement par le résolveur récursif configuré, sur DNS over TLS au port 853. S’il accepte, il peut maintenir un abonnement amont et relayer les résultats. Dans d’autres cas, la découverte s’appuie sur _dns-push-tls._tcp.<zone>. Le TTL de cette découverte, la zone concernée et la validation éventuelle doivent rester dans le dossier de preuve.

RFC 8765 impose le profil Strict Privacy. TLS protège le canal contre l’écoute et l’altération en transit et authentifie un nom selon les identifiants choisis. Mais un SRV falsifié peut conduire à un canal parfaitement chiffré vers le mauvais serveur. Il faut donc conserver séparément le résultat DNSSEC de la découverte, le nom cible, SNI, le certificat ou TLSA, ainsi que l’adresse réellement jointe.

La connexion ne suffit toujours pas. Un échange Keepalive ou la première demande SUBSCRIBE établit DSO. La demande identifie un seul NAME, TYPE et CLASS et possède un MESSAGE ID. La réponse, avec son RCODE, décide de cet abonnement. Un serveur peut parler DSO sans prendre en charge Push ; il peut prendre en charge Push sans être compétent pour ce nom ; il peut enfin refuser de nouvelles souscriptions parce que sa mémoire, ses descripteurs ou sa capacité réseau sont bornés.

Cette finitude est saine. Le protocole coordonne la forme de la demande et les significations de l’erreur ; il ne transforme pas une ressource locale en droit universel. Le serveur garde son budget d’admission. Le client doit fermer les abonnements qui ne servent plus à un écran ou à un processus actif, au lieu de conserver un inventaire « chaud » en permanence.

Un flux de changements sans numéro de continuité

PUSH est un message DSO unidirectionnel émis par le serveur. Son MESSAGE ID vaut zéro et le client ne répond pas. Les enregistrements transportés ont trois fonctions. Une valeur TTL comprise entre zéro et 0x7FFFFFFF ajoute un RR. 0xFFFFFFFF retire un RR individuel. 0xFFFFFFFE décrit un retrait collectif, avec RDATA vide et un périmètre déterminé par TYPE et CLASS.

Avant toute mutation du cache, le client doit trouver au moins un abonnement actif correspondant sur cette session. Un changement arrivé pendant la course entre un PUSH entrant et un UNSUBSCRIBE sortant peut être ignoré si aucun abonnement ne correspond encore. Cette tolérance explique pourquoi les octets seuls ne suffisent pas : il faut l’identité de session et l’état de l’abonnement au moment de leur réception.

Le flux TCP préserve l’ordre à l’intérieur d’une connexion. Il ne fabrique pas pour autant un curseur durable entre deux connexions. Le MESSAGE ID nul des PUSH n’est pas un numéro de séquence. Plusieurs changements peuvent partager un même message. Après une rupture, aucun compteur ne permet d’affirmer que le nouveau flux reprend exactement après le dernier octet de l’ancien. La procédure sûre consiste à rétablir l’abonnement et à recevoir un nouvel état initial, non à inventer une continuité.

Un ensemble vide mérite la même précision. La norme impose un PUSH initial si l’ensemble est non vide. Elle n’impose pas un faux enregistrement « vide ». Une réponse SUBSCRIBE réussie suivie de silence peut signifier que l’abonnement est actif et qu’aucune donnée n’existe actuellement. L’observabilité doit enregistrer l’acceptation et l’absence d’état non vide, sans transformer le silence en panne ni en contenu.

Keepalive ne certifie pas le service

DSO distingue un délai d’inactivité et un intervalle Keepalive. Les messages de maintien entretiennent l’état des NAT et pare-feu et permettent aux deux extrémités de vérifier leur connectivité. Un abonnement actif empêche la session d’être classée inactive même si aucun RR ne change pendant longtemps.

Cette preuve reste étroite. Elle ne démontre pas que le relais récursif garde son propre abonnement amont, que le serveur a vu toutes les modifications, que le client les a toutes appliquées, ni que la cible SRV accepte des connexions. Une panne applicative peut coexister avec un DNS parfaitement courant ; une panne Push peut coexister avec un service encore fonctionnel.

RECONFIRM illustre bien la limite. Avec un Discovery Proxy, un client qui rencontre une cible apparemment morte peut demander une nouvelle vérification multicast. Si le proxy constate la disparition, il émet ensuite les PUSH nécessaires. Pour les autres types de serveur, l’effet est indéfini et un NOERROR peut n’entraîner aucune action. RECONFIRM est un signal de doute, pas une attestation universelle.

Reprendre proprement

Une remise en service observable doit raconter toute la succession. L’ancienne session se ferme et le vieillissement TTL reprend. La nouvelle connexion TCP est établie. Le journal précise si le handshake TLS est complet ou repris. Une nouvelle session DSO naît. Chaque triplet NAME, TYPE, CLASS souhaité fait l’objet d’un nouveau SUBSCRIBE, reçoit une réponse et, si le contenu est non vide, un nouvel état initial. Ce n’est qu’après cette chaîne que le cache peut recommencer à suspendre l’horloge.

SUBSCRIBE peut être envoyé en early data TLS. Le bénéfice d’un aller-retour en moins n’autorise pas à qualifier la demande d’unique : le 0-RTT n’est pas protégé contre la répétition entre connexions et n’offre pas la même confidentialité persistante. L’accusé d’acceptation sur la session réelle reste nécessaire avant de déclarer l’abonnement actif.

Si la souscription échoue, le polling classique est un repli explicite. RFC 8765 recommande d’espacer les requêtes d’au moins le minimum entre 900 secondes et deux secondes de plus que le TTL du RRset, puis de retenter Push avant chaque interrogation. Cette cadence protège les serveurs ; elle n’abolit pas la fenêtre de retard. Le tableau de bord doit donc afficher « polling » et son âge, pas recycler le voyant « push actif ».

Le dossier qui rend « actuel » défendable

Le dossier commence par la découverte : QNAME, réponse, TTL, validité DNSSEC, résolveur et point d’observation. Il poursuit avec la cible, SNI, pair réseau et résultat du certificat ou de TLSA. Il sépare l’identifiant de connexion TCP, le type de handshake TLS, le début et la fin de DSO, les délais négociés et Retry Delay.

Chaque abonnement conserve son MESSAGE ID, NAME normalisé, TYPE, CLASS, octets de requête, RCODE et heure d’acceptation. Chaque changement conserve son ordre sur le flux, son type d’ajout ou de retrait, le RR, le TTL stocké, l’abonnement correspondant et la décision du cache. Les instants où l’horloge s’arrête et repart sont des événements de premier rang.

Enfin, une interrogation directe de l’autorité vérifie ce que le DNS sert maintenant ; une sonde applicative vérifie que la cible fonctionne. Ces deux tests ne reconstruisent pas l’historique du client, mais empêchent une erreur de cache d’être prise pour une panne du service, ou l’inverse.

Une coordination mince, une responsabilité visible

Le triptyque de Heng Lu — spécification initiale minimale, décision future localisée, adoption volontaire — décrit ici une bonne répartition. La couche commune fixe OPCODE, TLV, identités d’abonnement, retraits, délais, sécurité du transport et fin de session. Elle n’a pas besoin d’imposer un budget mondial de souscriptions, une politique de journalisation ou un seuil unique de reprise.

Ces choix appartiennent aux exploitants qui paient le coût et répondent des erreurs. Le serveur choisit ses admissions. Le client choisit quand la fraîcheur en direct vaut l’état persistant. Les équipes de sécurité choisissent les identifiants d’authentification et la rétention. Les SRE définissent les canaris, le repli et le retour au polling.

La primauté du code en fonctionnement exige alors de regarder l’effet réel : quels octets ont créé l’abonnement, quelle session portait l’obligation, quel changement a modifié le cache, quelle requête applicative en a résulté. Un programme qui garde l’horloge gelée après la disparition de cette obligation prouve sa propre faute de gouvernance. La bonne architecture garde chaque autorité petite et nommée.

Sources