Guides

Anatomie d'un MP4 : ce qu'est l'atome moov et pourquoi votre vidéo ne se lit pas

L'atome moov est l'index d'un fichier MP4 : la carte qui indique au lecteur où vit chaque image. Il est écrit au moment où un enregistrement est finalisé, et c'est justement pourquoi un plantage ou une coupure de courant vous laisse un fichier qui ne s'ouvre pas alors même que les séquences sont toujours à l'intérieur. Voici une visite du format de fichier, octet par octet, en langage clair.

Un MP4 est une boîte de boîtes

Un fichier MP4 est construit à partir de boîtes(« boxes »). (Leur nom plus ancien dans la spécification,atomes, est celui qui est resté dans les messages d'erreur.) Chaque boîte commence par le même en-tête de 8 octets : 4 octets qui indiquent la taille de la boîte, puis 4 caractères qui indiquent de quel type de boîte il s'agit. Voilà toute la grammaire. Les boîtes peuvent contenir d'autres boîtes, et un analyseur parcourt le fichier en lisant un en-tête, en décidant s'il regarde à l'intérieur, et en sautant en avant de la taille déclarée jusqu'à la suivante.

Ouvrez n'importe quel enregistrement terminé (d'un téléphone, d'une GoPro, d'OBS, d'un drone) et, au niveau supérieur, vous trouverez les trois mêmes boîtes qui font tout le travail :

Disposition en octets d'un enregistrement terminé typique (pas à l'échelle ; le bloc de données écrase tout le reste). Les noms en monospace sont les types de boîte de quatre caractères écrits dans le fichier lui-même ; ce sont eux que des outils comme ffmpeg indiquent dans les messages d'erreur.

Les fichiers MOV, le format QuickTime dont dérive le MP4, partagent exactement cette structure, et c'est pourquoi un MOV qui ne s'ouvre pas et un MP4 qui ne s'ouvre pas sont presque toujours le même problème sous une extension différente.

L'atome moov est la carte

Voici la partie qui surprend : le bloc de données est opaque. Les images compressées se suivent les unes après les autres dans mdat sans rien pour les séparer, sans marqueurs disant « l'image 412 commence ici ». Chaque question à laquelle un lecteur a besoin de réponse vit plutôt dans l'atome moov, dans un ensemble de structures appelées tables d'échantillons :

  • Où est chaque image ? La table des décalages de fragments (stco) consigne les positions en octets dans le fichier.
  • Quelle taille fait chaque image ? La table des tailles d'échantillons (stsz) liste la longueur de chaque image, une entrée par image.
  • Quand chaque image se lit-elle ? La table temps-vers-échantillon (stts) fait correspondre les images à l'horloge du film, pour que l'audio et la vidéo restent parfaitement synchronisés.
  • Vers quels points la lecture peut-elle sauter ? La table des échantillons de synchronisation (stss) liste les images clés, les seules à partir desquelles un décodeur peut démarrer, ce qui rend le déplacement dans la vidéo possible.

Même la configuration du décodeur (les paramètres qui lui indiquent comment la vidéo a été compressée) est stockée dans l'atome moov, pas dans le flux. Un lecteur privé de l'atome moov ne manque pas seulement de marqueurs de chapitre ; il ne sait pas où commence une seule image, combien de temps dure la vidéo, ni comment configurer son décodeur. Imaginez une bibliothèque où les livres seraient rangés sans dos, sans titres et sans catalogue : l'information existe tout entière, et rien n'en est accessible. C'est mdat sans moov, et c'est pourquoi les lecteurs renoncent complètement au lieu de lire « la majeure partie » d'un fichier endommagé.

Pourquoi l'index est écrit en dernier

L'atome moov décrit chaque image : sa position, sa taille, son minutage. Pendant que vous enregistrez, rien de tout cela n'est connaissable : la caméra n'a aucune idée de savoir si vous allez arrêter dans dix secondes ou dans deux heures, et le décalage en octets d'une image ne peut pas être consigné avant que l'image existe. Alors chaque enregistreur fait la seule chose qu'il puisse faire. Il déverse les images compressées dansmdat à mesure qu'elles sont encodées, garde la comptabilité en cours en mémoire, et écrit l'index en une seule passe au moment où vous appuyez sur arrêt.

Pendant l'enregistrement : les images sont ajoutées à mesure qu'elles sont encodées. L'index ne peut pas encore exister ; son contenu n'est pas connu avant que la dernière image soit écrite.

Finalisation : l'enregistreur mesure tout ce qu'il a écrit et ajoute l'atome moov. Ce n'est que maintenant que le fichier est lisible.

Cette conception est efficace et sûre, jusqu'au moment où l'enregistrement n'atteint pas l'étape de finalisation. Une batterie à plat, un plantage d'OBS, un drone dans un lac : le processus qui écrit le fichier s'arrête, et l'index n'est jamais écrit. Ce qui reste sur le disque, c'est un fichier d'une taille saine, des heures de séquences intactes dansmdat, et aucune carte. Tous les lecteurs le refusent ; ffmpeg affiche moov atom not found. Les séquences n'ont pas disparu ; elles sont bloquées. (Les toutes dernières secondes, encore dans la mémoire tampon de la caméra et pas encore écrites sur le stockage,ont bel et bien disparu. Les outils honnêtes le disent.) Cet état « bloqué mais intact » est précisément ce à quoi sert laréparation de l'atome moov, et c'est le mode de défaillance typique des enregistrements OBS qui ont planté.

faststart et MP4 fragmenté

La conception « index à la fin » a deux conséquences bien connues, et l'industrie a bâti un correctif pour chacune.

faststart : déplacer l'index au début, après coup

Un navigateur qui diffuse une vidéo depuis le web lit le fichier de bout en bout. Si l'atome moov est à la fin, la lecture ne peut pas commencer avant que le fichier entier soit téléchargé ; le lecteur tient le livre en main et attend le catalogue. Le correctif est une passe de post-traitement (le -movflags +faststart de ffmpeg) qui réécrit le fichier terminé avec l'atome moov déplacé au début :

Un fichier « faststart » : l'index d'abord, pour que la lecture en streaming puisse commencer immédiatement. Voilà pourquoi certaines vidéos web démarrent à l'instant et d'autres se figent.

Notez ce que faststart n'est pas : une protection contre les plantages. Il s'exécute sur un fichier complet et sain une fois l'encodage terminé. Un enregistrement qui meurt en pleine écriture n'atteint jamais cette étape.

MP4 fragmenté : de nombreux petits index plutôt qu'un seul gros

La seconde conséquence (perdez la finalisation, perdez le fichier) est traitée par le MP4 fragmenté. Au lieu d'un seulmdat et d'un seul moov à la fin, le fichier est écrit comme une chaîne de courts segments auto-descriptifs, chacun une tranche de données avec son propre mini-index (une boîte moof). En termes ffmpeg, -movflags frag_keyframe+empty_moov : un moov squelette au début, puis fragment après fragment. Si l'enregistreur meurt, vous perdez au pire le dernier fragment, et tout ce qui le précède est déjà indexé et lisible. Les services de streaming livrent la vidéo de cette manière pour la même raison. Le compromis, c'est la compatibilité : certains logiciels de montage et certains lecteurs anciens gèrent mal les fichiers fragmentés, et c'est pourquoi les caméras écrivent toujours la disposition classique. La réponse d'OBS (dans OBS 30.2 et versions ultérieures) est le « MP4 hybride », qui conserve la résistance aux plantages du style fragmenté tout en finalisant dans un fichier largement compatible, à activer si les plantages d'OBS vous ont déjà joué des tours.

Comment fonctionne la reconstruction du moov

Un plantage vous a donc laissé avec ftyp, un mdatgigantesque, et aucun index. Le reconstruire est possible parce que le bloc de données « opaque » n'est pas parfaitement opaque pour un analyseur qui connaît les codecs. À l'intérieur de mdat, les images vidéo sont stockées comme des unités préfixées de leur longueur, et le flux binaire de chaque codec présente des motifs reconnaissables : des en-têtes qui marquent le type, les dimensions et les limites d'une image. Les outils de reconstruction (le projet open source untrunca établi l'approche, et c'est la classe de réparation que réalise le moteur vidéo d'IntactFile) parcourent les données brutes octet par octet :

  1. Trouver les limites des images. Parcourirmdat, en utilisant les préfixes de longueur et les signatures de codec pour identifier où commence et où finit chaque image vidéo et audio.
  2. Classer et mesurer. Attribuer chaque image à son flux, et consigner sa taille et sa position, en reconstruisant échantillon par échantillon la matière première de stsz et stco.
  3. Reconstruire le minutage. Déduire la durée des images à partir des réglages de l'encodeur. C'est pourquoi untruncdemande un fichier de référence sain enregistré avec les mêmes réglages, afin d'apprendre à quoi ressemble le « normal » pour votre appareil.
  4. Écrire un nouveau moov et finaliser. Assembler les tables d'échantillons en un index neuf et produire un fichier conforme à la spécification.

Le résultat lit tout ce qui a physiquement survécu, s'arrêtant là où s'arrêtent les données. Les limites honnêtes découlent directement du mécanisme : les enregistrements au minutage d'images très irrégulier peuvent revenir avec un léger décalage audio/vidéo, et si mdatlui-même n'est que des zéros (c'est le stockage qui a lâché, pas l'enregistreur) il n'y a aucune image à trouver, et aucun outil ne peut les faire apparaître. Pour le tableau plus large de savoir quel dommage est lequel, voyez comment les fichiers vidéo se corrompent et ce qui est réellement réparable.

FAQ

Qu'est-ce que l'atome moov dans un fichier MP4 ?

L'atome moov est l'index du MP4 : un bloc structuré qui consigne où se situe dans le fichier chaque image vidéo et audio, la taille de chacune, le moment où elle doit s'afficher et la manière dont les flux se synchronisent. Il porte aussi la configuration du décodeur. Un lecteur lit d'abord l'atome moov et s'en sert comme carte vers les données multimédias. Sans atome moov valide, le fichier ne s'ouvre pas, même quand les séquences elles-mêmes sont intactes.

Pourquoi l'atome moov est-il à la fin du fichier ?

Parce que son contenu n'est pas connu avant la fin de l'enregistrement. L'atome moov liste la taille, la position et le minutage de chaque image, une information qui n'existe qu'une fois la dernière image écrite. Les enregistreurs ajoutent donc les images au fil de l'eau et écrivent l'index en une seule passe à la finalisation, ce qui le place après les données multimédias. Les fichiers préparés pour le streaming web ont souvent le moov déplacé au début a posteriori (« faststart »), mais c'est une étape de post-traitement, pas la façon dont le fichier naît.

Un atome moov manquant peut-il être reconstruit ?

En général oui, à condition que les données multimédias (le bloc mdat) aient survécu. Les outils de reconstruction parcourent le flux brut, détectent les limites de chaque image, mesurent tailles et positions et reconstruisent les tables d'échantillons qu'aurait contenues l'atome moov. Le résultat est un fichier lisible couvrant tout jusqu'au point d'interruption. Si le bloc mdat est absent, mis à zéro ou écrasé, il n'y a rien à indexer, et aucun outil ne peut reconstruire le fichier. Vous pouvez vérifier un fichier dans votre navigateur pour voir dans quel cas se trouve le vôtre.

Quelle est la différence entre moov et mdat ?

Le mdat contient la charge utile : les images audio et vidéo compressées, empaquetées les unes à la suite des autres, typiquement 99 % de la taille du fichier. Le moov contient les métadonnées : l'index qui décrit où commence chaque image dans mdat, sa taille, son minutage et les réglages du décodeur nécessaires à la lecture. Un mdat sans moov, ce sont des séquences sans carte : les données sont là, mais aucun lecteur ne peut y naviguer. Un moov sans mdat, c'est la carte d'un territoire qui n'existe plus.

Que fait movflags faststart ?

Dans ffmpeg, -movflags +faststart déplace l'atome moov de la fin d'un fichier terminé vers le début, juste après l'en-tête de type de fichier. Les lecteurs peuvent alors démarrer la lecture pendant que le reste du fichier se télécharge encore, ce qui en fait le standard pour la vidéo web. Cela nécessite de réécrire le fichier (ffmpeg fait une seconde passe) et ne fonctionne que sur un fichier sain et complet. Cela ne protège pas un enregistrement contre les plantages et ne peut pas réparer un fichier dont le moov n'a jamais été écrit.

Aussi dans cette série : comment les fichiers vidéo se corrompent — et ce qui est réellement réparable.