No description
Find a file
2025-07-28 17:54:47 +00:00
README.md Update README.md 2025-07-28 17:54:47 +00:00

AMD Radeon + Jellyfin + Docker: Enable GPU Hardware Acceleration for Encoding

Overview

from a networking perspective it looks like this (put inside mermaid.live)

graph TD
    User(User Browser)

    subgraph fedora HOST
    Caddy[Caddy Container: 80/443]
    
    Jellyfin[Jellyfin Container: 8096]
    end

    User --> |http request --> your.domain | Caddy
    Caddy -->|Proxy to port 8096| Jellyfin

The file structure looks like this

.
├── docker-compose.yml
└── volume-bindings
    ├── caddy
    │   ├── Caddyfile
    │   └── data
    └── jellyfin
        ├── cache
        └── config

docker-compose.yml

version: '3.5'

networks:
  caddy:

services:

  caddy:
    image: caddy:latest
    container_name: my-caddy
    restart: always
    ports:
      - "80:80"
      - "443:443"
    volumes:
      - ./volume-bindings/caddy/Caddyfile:/etc/caddy/Caddyfile # !ADJUST
      - caddy-data:/data # remember ssl certificates
    networks:
      - caddy

  jellyfin:
    image: jellyfin/jellyfin:latest
    container_name: my-jellyfin
    user: 1000:1000

    group_add:
      - "105" # !ADJUST Change this to match your "render" host group id and remove this comment

    networks:
      - caddy

    volumes: # !ADJUST
      - ./volume-bindings/jellyfin/config:/config
      - ./volume-bindings/jellyfin/cache:/cache
      - /mnt/QVO8TB-A/:/media:ro
      - /mnt/QVO8TB-B/:/media2:ro
      - /mnt/QVO8TB-C/:/media3:ro

    devices:
      - /dev/dri:/dev/dri

    restart: 'always'
    # Optional - alternative address used for autodiscovery
    ports:
      - 8096:8096
    environment:
      - JELLYFIN_PublishedServerUrl=http://entertain.ramboe.io # !ADJUST
    extra_hosts:
      - "host.docker.internal:host-gateway"

volumes:
  caddy-data: # create volume for caddy (to remember ssl certificates)
    driver: local
    driver_opts:
      type: none
      device: /mnt/QVO4TB/volume-bindings/caddy/data # !ADJUST
      o: bind

Caddyfile

your.domain {
  reverse_proxy my-jellyfin:8096
}

docker-compose.yml - the imporant parts for our scenario

version: '3.5'

networks:
  caddy:

services:
  
  # ...

  jellyfin:
  # ...

    group_add:
      - "105" # Change this to match your "render" host group id and remove this comment

    devices:
      - /dev/dri:/dev/dri # makes the host's GPU available for the container

Prerequisites

Check VAAPI Support on Host

vainfo

faulty output

Trying display: wayland
Trying display: x11
error: can't connect to X server!
Trying display: drm
libva info: VA-API version 1.22.0
libva info: Trying to open /usr/lib64/dri-nonfree/radeonsi_drv_video.so
libva info: Trying to open /usr/lib64/dri-freeworld/radeonsi_drv_video.so
libva info: Trying to open /usr/lib64/dri/radeonsi_drv_video.so
libva info: Found init function __vaDriverInit_1_22
libva info: va_openDriver() returns 0
vainfo: VA-API version: 1.22 (libva 2.22.0)
vainfo: Driver version: Mesa Gallium driver 25.0.7 for AMD Radeon RX 6700 XT (radeonsi, navi22, LLVM 19.1.7, DRM 3.63, 6.15.6-100.fc41.x86_64)
vainfo: Supported profile and entrypoints

      VAProfileMPEG2Simple            : VAEntrypointVLD
      VAProfileMPEG2Main              : VAEntrypointVLD
      VAProfileJPEGBaseline           : VAEntrypointVLD
      VAProfileVP9Profile0            : VAEntrypointVLD
      VAProfileVP9Profile2            : VAEntrypointVLD
      VAProfileAV1Profile0            : VAEntrypointVLD
      VAProfileNone                   : VAEntrypointVideoProc

expected output

Trying display: wayland
Trying display: x11
error: can't connect to X server!
Trying display: drm
libva info: VA-API version 1.22.0
libva info: Trying to open /usr/lib64/dri-nonfree/radeonsi_drv_video.so
libva info: Trying to open /usr/lib64/dri-freeworld/radeonsi_drv_video.so
libva info: Found init function __vaDriverInit_1_22
libva info: va_openDriver() returns 0
vainfo: VA-API version: 1.22 (libva 2.22.0)
vainfo: Driver version: Mesa Gallium driver 25.0.7 for AMD Radeon RX 6700 XT (radeonsi, navi22, LLVM 19.1.7, DRM 3.63, 6.15.6-100.fc41.x86_64)
vainfo: Supported profile and entrypoints

      VAProfileMPEG2Simple            : VAEntrypointVLD
      VAProfileMPEG2Main              : VAEntrypointVLD
      VAProfileVC1Simple              : VAEntrypointVLD
      VAProfileVC1Main                : VAEntrypointVLD
      VAProfileVC1Advanced            : VAEntrypointVLD
      
      VAProfileH264ConstrainedBaseline: VAEntrypointVLD
      VAProfileH264ConstrainedBaseline: VAEntrypointEncSlice
      VAProfileH264Main               : VAEntrypointVLD
      VAProfileH264Main               : VAEntrypointEncSlice
      VAProfileH264High               : VAEntrypointVLD
      VAProfileH264High               : VAEntrypointEncSlice
      VAProfileHEVCMain               : VAEntrypointVLD
      VAProfileHEVCMain               : VAEntrypointEncSlice
      VAProfileHEVCMain10             : VAEntrypointVLD
      VAProfileHEVCMain10             : VAEntrypointEncSlice
      
      VAProfileJPEGBaseline           : VAEntrypointVLD
      VAProfileVP9Profile0            : VAEntrypointVLD
      VAProfileVP9Profile2            : VAEntrypointVLD
      VAProfileAV1Profile0            : VAEntrypointVLD
      VAProfileNone                   : VAEntrypointVideoProc

expected output (simplified)

libva info: VA-API version ...
...
VAProfileH264Main : VAEntrypointVLD
VAProfileHEVCMain : VAEntrypointVLD
...

this means that hardware decoding of H.264 or HEVC via VAAPI is enabled.

If machine has no VAAPI support yet

Fedora: Install vainfo

sudo dnf install libva-utils mesa-va-drivers

Fedora: Install Mesa With Codec Support

On Fedora 41, and by default, Fedora ships a "free" Mesa stack — which intentionally disables H.264 and HEVC support for licensing reasons.

Enable RPM Fusion (if not already):

sudo dnf install \
  https://download1.rpmfusion.org/free/fedora/rpmfusion-free-release-$(rpm -E %fedora).noarch.rpm \
  https://download1.rpmfusion.org/nonfree/fedora/rpmfusion-nonfree-release-$(rpm -E %fedora).noarch.rpm

RPM Fusion is a third-party software repository for Fedora and RHEL-based Linux distributions. It provides software that Is not included in Fedora by default.

Install freeworld drivers:

sudo dnf swap mesa-va-drivers mesa-va-drivers-freeworld

reboot your system afterwards

Ubuntu: Install Mesa With Codec Support

untested, please give feedback if this works for you if you're host is Ubuntu

Install the VAAPI drivers

sudo apt update
sudo apt install i965-va-driver intel-media-va-driver libva-drm2 libva-x11-2 vainfo mesa-va-drivers

Install multimedia codecs (H.264, HEVC, etc.)

sudo apt install ubuntu-restricted-extras

Settings explained

renderD128

renderD128 is a device file on the filesystem.

This is created by the Linux kernel when it detects a GPU that supports DRM (Direct Rendering Manager) and rendering functions like VAAPI or OpenCL.

To find out if you have a renderD128 file, do this on the host:

# execute on host
ls -l /dev/dri

expected output

  total 0                                                                                                                                                    
  drwxr-xr-x. 2 root root         80 Jul 27 11:01 by-path                                                                                                    
  crw-rw----+ 1 root video  226,   1 Jul 27 11:09 card1                                                                                                      
  crw-rw-rw-. 1 root render 226, 128 Jul 27 11:01 renderD128

group_add

105 is the GID (group ID) of the render group on your machine, and that number can vary from system to system.

To find out your group ID, do this on the host:

# execute on host
getent group render

expected output

render:x:105:

Summary

the part

devices:
      - /dev/dri:/dev/dri

maps the path where the renderD128 file resides so the host can access it. and group 105 makes sure the container has the right to access it. Drivers have to be installed correctly, see "If machine has no VAAPI support yet "

If it still doesn't work

Make sure there are no missing VAAPI libraries inside the container. jellyfin/jellyfin:latest runs on Ubuntu.

Enter the container

docker exec -u 0 -it my-jellyfin bash

install packages

apt update
apt install i965-va-driver intel-media-va-driver libva-drm2 libva-x11-2 vainfo mesa-va-drivers

restart container

docker compose stop
docker compose down
docker compose up