FFmpeg and dav1d source
Astrape uses FFmpeg and dav1d. This page has their exact source code, the build script and the licence texts, and tells you how to rebuild the framework and put your own in the app.
What Astrape uses
- FFmpeg 7.1, under the GNU Lesser General Public License, version 2.1 or later. It is built with
--disable-gpland--disable-nonfree, so no GPL code is in it. - dav1d 1.5.1, under the BSD 2-Clause licence. It decodes AV1 inside the FFmpeg framework.
FFmpeg is a separate dynamic framework, FFmpeg.framework, embedded in the app. FFmpeg and dav1d are built as static libraries and linked into that one framework, so you can replace it with your own build. It has a tvOS device slice and a simulator slice, both arm64, for tvOS 18.0 and later.
No patches. The two archives below are the upstream releases, unchanged, and the build script applies no patch to them.
Files
Everything is here, with its size and SHA-256. Check the files with shasum -a 256 -c SHA256SUMS.
| File | Bytes | SHA-256 |
|---|---|---|
| ffmpeg-7.1.tar.bz2 FFmpeg 7.1 source, as released by ffmpeg.org | 13,260,188 | fd59e6160476095082e94150ada5a6032d7dcc282fe38ce682a00c18e7820528 |
| dav1d-1.5.1.tar.xz dav1d 1.5.1 source, as released by VideoLAN | 1,020,760 | 401813f1f89fa8fd4295805aa5284d9aed9bc7fc1fdbe554af4292f64cbabe21 |
| build_ffmpeg.sh The build script, exactly as used | 23,477 | 32b76494eaec11f22951679d6d1f5575e0660477e1eaaf2867bc40d86f766203 |
| FFmpeg.PrivacyInfo.xcprivacy The Apple privacy manifest the build script copies into the framework | 817 | 8f564a0be42e1bd1c0f9b2b89c5a72dbdbeaadb1e284bce8b855fa5bb99a1881 |
| COPYING.LGPLv2.1 FFmpeg's licence, LGPL version 2.1 | 26,526 | b634ab5640e258563c536e658cad87080553df6f34f62269a21d554844e58bfe |
| dav1d-COPYING dav1d's licence, BSD 2-Clause | 1,317 | b327887de263238deaa80c34cdd2ff3e0ba1d35db585ce14a37ce3e74ee389e9 |
| README.txt The same facts as this page, as plain text | 13,034 | 212338cf779ff431f5a15d53650bccd04a23a65773e7cf8da89042b26787f06c |
| SHA256SUMS The SHA-256 of every file above except itself | 587 | 6bf64fee9f4470f05164acb26bbd82565cb89c3f0bac099d21176db1f73e65ac |
Configure flags
build_ffmpeg.sh passes these flags to FFmpeg's configure for both slices. They are the script's COMMON_FLAGS array, copied from it; --disable-gpl and --disable-nonfree are in the list.
--disable-everything --disable-programs --disable-doc --disable-avdevice --enable-avfilter # only the deinterlacer, below --disable-postproc --disable-network --disable-gpl --disable-nonfree --enable-pic --enable-cross-compile --target-os=darwin --arch=arm64 # Containers we need to demux --enable-demuxer=matroska # MKV / WebM --enable-demuxer=mov # MP4 / MOV / M4V --enable-demuxer=mpegts # TS --enable-demuxer=mpegps # PS / VOB --enable-demuxer=avi --enable-demuxer=flv --enable-demuxer=ogg --enable-demuxer=asf --enable-demuxer=rm --enable-demuxer=concat # virtual concat for segmented files # Raw elementary-stream probes: MPEG-PS (VOB/MPG) identifies an H.264 / # HEVC video stream only by probing its payload with these demuxers. --enable-demuxer=h264 --enable-demuxer=hevc --enable-demuxer=mpegvideo --enable-demuxer=ivf # raw AV1 / VP9 / VP8 --enable-demuxer=obu # raw AV1 # Video the Apple TV can't decode in hardware: decoded here, encoded to # HEVC by VideoToolbox (Core/Engine/Transcode). --enable-libdav1d --enable-decoder=libdav1d # AV1 --enable-decoder=vp9 --enable-decoder=vp8 --enable-decoder=mpeg1video --enable-decoder=mpeg2video --enable-decoder=mpeg4 # MPEG-4 Part 2 (Xvid, DivX 4+) --enable-decoder=msmpeg4v1 --enable-decoder=msmpeg4v2 --enable-decoder=msmpeg4v3 # DivX 3 --enable-decoder=h263 --enable-decoder=flv # Sorenson H.263 --enable-decoder=vc1 --enable-decoder=wmv1 --enable-decoder=wmv2 --enable-decoder=wmv3 --enable-decoder=vp3 --enable-decoder=theora --enable-decoder=mjpeg --enable-decoder=prores --enable-parser=av1 --enable-parser=vp9 --enable-parser=vp8 --enable-parser=mpegvideo --enable-parser=mpeg4video --enable-parser=h263 --enable-parser=vc1 --enable-parser=mjpeg --enable-bsf=vp9_superframe_split # the VP9 decoder needs it # Audio decoders --enable-decoder=ac3 # Dolby Digital --enable-decoder=eac3 # Dolby Digital Plus (E-AC-3 + JOC/Atmos) --enable-decoder=truehd # TrueHD / MLP (see §8 license note) --enable-decoder=mlp --enable-decoder=dca # DTS (see §8 license note — defer for App Store) --enable-decoder=aac --enable-decoder=aac_latm --enable-decoder=mp3 --enable-decoder=mp2 # MPEG-1 Layer II: DVB recordings, VOB/MPG --enable-decoder=mp2float --enable-decoder=mp1 --enable-decoder=flac --enable-decoder=opus --enable-decoder=vorbis --enable-decoder=alac --enable-decoder=pcm_s16le --enable-decoder=pcm_s16be --enable-decoder=pcm_s24le --enable-decoder=pcm_s24be --enable-decoder=pcm_s32le --enable-decoder=pcm_bluray # lpcm in remux MKVs --enable-decoder=pcm_dvd # lpcm in VOB --enable-decoder=pcm_u8 # old AVI --enable-decoder=pcm_f32le --enable-decoder=pcm_alaw --enable-decoder=pcm_mulaw --enable-decoder=adpcm_ms # old AVI --enable-decoder=adpcm_ima_wav --enable-decoder=wmav1 # ASF / WMV audio --enable-decoder=wmav2 --enable-decoder=wmapro # Subtitle decoders --enable-decoder=pgssub # PGS (Blu-ray) — ubiquitous in remux MKVs --enable-decoder=dvdsub # VOBSUB --enable-decoder=dvbsub --enable-decoder=ass --enable-decoder=ssa --enable-decoder=srt --enable-decoder=subrip --enable-decoder=webvtt --enable-decoder=mov_text --enable-decoder=microdvd --enable-decoder=text # Parsers for audio + HEVC bitstream (NAL boundary detection, DTS detect) --enable-parser=hevc # HEVC NAL splitter — needed for RPU work --enable-parser=h264 --enable-parser=ac3 --enable-parser=eac3 --enable-parser=dca --enable-parser=aac --enable-parser=aac_latm --enable-parser=flac --enable-parser=opus --enable-parser=vorbis --enable-parser=mpegaudio --enable-parser=mlp # Muxers — Path B remuxes demuxed packets into fragmented MP4 via movenc # (DEMUX_ENGINE_PLAN.md §6.2 / Revision 2). Without these, the # avformat_alloc_output_context2(..., "mp4") call returns NULL and the whole # Path B muxer fails to initialise. movenc is LGPL-clean. --enable-muxer=mov # shared movenc core --enable-muxer=mp4 # fragmented MP4 output (dvcC / dec3 / dac3) # Bitstream filters. # hevc_mp4toannexb / h264_mp4toannexb — Path A's VTDecompressionSession # needs Annex-B; Path B keeps the native length-prefixed (MP4) framing. # extract_extradata — pull in-band VPS/SPS/PPS into codecpar->extradata. --enable-bsf=hevc_mp4toannexb --enable-bsf=h264_mp4toannexb --enable-bsf=extract_extradata # Encoders — TrueHD / DTS have no Apple TV passthrough path, so Path B # decodes them to PCM and re-encodes to E-AC-3 (Revision 2 audio decision), # which movenc then muxes with a dec3 box like native Dolby Digital Plus. # Both encoders are FFmpeg-native and LGPL-clean (no GPL/libfdk dependency). --enable-encoder=ac3 --enable-encoder=eac3 # Protocols — only file + custom (AVIOBridge). No network stacks from FFmpeg. --enable-protocol=file --enable-protocol=pipe --enable-protocol=custom # avio_alloc_context (our AVIOBridge) # swresample for audio decode → PCM conversion --enable-swresample # Disable bitcode (dead since Xcode 14) --disable-bzlib # avoid dependency; unused # Interlaced sources (DVD, broadcast MPEG-2 and VC-1) are deinterlaced # before they are encoded: bwdif, one frame out per frame in. --enable-filter=buffer --enable-filter=buffersink --enable-filter=bwdif
Each slice also passes the following (build_slice in build_ffmpeg.sh). SLICE_DIR is the slice's build folder, CC and AR are the SDK's clang and ar, SYSROOT is the SDK, and CFLAGS and LDFLAGS are "-arch arm64 -target TARGET_TRIPLE -isysroot SYSROOT". TARGET_TRIPLE is arm64-apple-tvos18.0 for the device and arm64-apple-tvos18.0-simulator for the simulator.
./configure \
"${COMMON_FLAGS[@]}" \
--pkg-config-flags="--static" \
--prefix="${SLICE_DIR}/install" \
--cc="${CC}" \
--ar="${AR}" \
--sysroot="${SYSROOT}" \
--extra-cflags="${CFLAGS}" \
--extra-ldflags="${LDFLAGS}" \
--enable-static \
--disable-shared \
2>&1 | tail -20
dav1d is built as a static library with meson, using the options that build_dav1d in build_ffmpeg.sh passes. The same function writes the meson cross file, which sets the C compiler to clang with the same -arch, -target and -isysroot flags.
meson setup "${BUILD_DIR}/${SLICE}/dav1d-build" "${BUILD_DIR}/src/${DAV1D_SRC}" \
--cross-file "${CROSS}" --prefix "${PREFIX}" --libdir lib \
--buildtype release -Ddebug=true --default-library static \
-Denable_tools=false -Denable_tests=false -Denable_examples=false
How to rebuild the framework
You need a Mac with Xcode 15 or later, the tvOS platform and SDK, the Command Line Tools, and four Homebrew packages:
brew install nasm pkg-config meson ninja
- Make a folder called
Scripts, putbuild_ffmpeg.shandFFmpeg.PrivacyInfo.xcprivacyin it, and run the script from the folder above it:bash Scripts/build_ffmpeg.sh. It downloads both archives (the dav1d one is checked against its SHA-256), builds the device and simulator slices, and writesbuild/xcframeworks/FFmpeg.xcframework. - To build from the archives on this page instead of downloading them, extract them first into
$TMPDIR/HDP_FFmpeg_Build/src/, so thatffmpeg-7.1/anddav1d-1.5.1/are there. The script uses a folder that already exists and skips the download. To change FFmpeg, change the extractedffmpeg-7.1/folder before you run the script.
How to replace the framework in the app
- Build your
FFmpeg.frameworkas above, from FFmpeg 7.1 and with the same ABI: the same library versions as in the framework'sHeadersfolder, the install name@rpath/FFmpeg.framework/FFmpeg, and a minimum tvOS of 18.0. - Replace
Astrape.app/Frameworks/FFmpeg.frameworkwith your framework. - Re-sign the framework, then the app, with your own signing identity, because the app's signature covers the framework:
codesign --force --sign "<your identity>" Astrape.app/Frameworks/FFmpeg.framework codesign --force --sign "<your identity>" --preserve-metadata=entitlements Astrape.app
- Install the re-signed app on your Apple TV with your own provisioning.
Written offer
For FFmpeg and dav1d as built into FFmpeg.framework, we will give you the object files of those two libraries on request (the .o files of the static FFmpeg and dav1d libraries that the framework is linked from), for at least three years from the release of the Astrape version that contains this framework. The source, the build script and the licence texts are already on this page.
To ask, write to [email protected], and say which Astrape version you have (Settings, About). The licence texts of everything else in the app are in the app, under Acknowledgements.