FFV1
37c3317fd058; modified for Encode Wiki · CC BY-SA 4.0FFV1 is a lossless video codec designed by Michael Niedermayer and developed in FFmpeg. Versions 0, 1 and 3 are specified in IETF RFC 9043, and it is one of the standard preservation formats in film and video archives, usually in Matroska. It compresses much better than fast lossless codecs such as Ut Video, at the cost of speed.
It handles YCbCr (4:2:0, 4:2:2, 4:4:4 and others), RGB, grayscale and alpha at 8 to 16 bits per sample, interlaced material, and in version 3 per-slice CRCs for error detection.
Archival encode
Section titled “Archival encode”ffmpeg -i input.mov -c:v ffv1 -level 3 -g 1 -coder 1 -slicecrc 1 -c:a copy output.mkv| Option | Why |
|---|---|
-level 3 | FFV1 version 3: slices, multithreaded decoding and CRCs. FFmpeg 8.0 and later default to it; older builds could pick version 0 or 1 for SD sources, so archival recipes pin it. Version 4 is experimental in FFmpeg and its IETF draft has expired. |
-g 1 | Every frame is a keyframe. See below. |
-coder 1 | Range coder instead of the default Golomb-Rice coder; noticeably smaller files for 8-bit sources. Above 8 bits FFmpeg switches to it automatically. -coder 2 selects the same mode. |
-slicecrc 1 | A CRC in every slice so damage can be detected and located. Already the default in version 3; set it to make the intent explicit on older builds. |
-slices N | Number of slices per frame, which sets how many threads can decode it. FFmpeg picks a count from the frame size (20 at 1080p); many archives set 16 or 24. The count has little effect on file size. FFmpeg rejects counts it cannot lay out for the frame size. |
-context 1 | Larger context model. The size difference is small and can go either way depending on content. |
FFV1 keeps its entropy-coder state from frame to frame until the next keyframe resets it, so with a GOP larger than one, damage in one frame can spoil every frame up to the next keyframe. -g 1 makes FFV1 truly intra-only: the file gets slightly bigger, and a damaged frame stays a single lost frame.
FFmpeg maps only one video and one audio stream by default. Add -map 0 to keep every track. Matroska cannot hold a MOV timecode track, so also add -dn for such sources; the start timecode is still kept as a tag.
FFV1 stores the pixel format you give it. Do not convert RGB to YUV or reduce bit depth on the way in.
Check the encode is lossless
Section titled “Check the encode is lossless”Compare per-frame hashes of the source and the FFV1 file:
ffmpeg -i input.mov -f framemd5 input.framemd5ffmpeg -i output.mkv -f framemd5 output.framemd5diff input.framemd5 output.framemd5FFmpeg decodes 8-bit RGB FFV1 as bgr0. For a gbrp source, add -pix_fmt gbrp to the second command so both sides are hashed in the same format.
Versions and playback
Section titled “Versions and playback”- Version 0 was marked stable in 2006, version 1 (more bit depths) in 2009 and version 3 (slices, CRCs) in 2013. Version 2 only ever existed in experimental form.
- FFmpeg also has a Vulkan encoder,
ffv1_vulkan, for GPU encoding. - Browsers and dedicated hardware decoders do not play FFV1. Keep it as the preservation master and make an AVC, VP9 or AV1 copy for viewing; see video codec support.