These are notes. I tried something called a recording server. Since I already had a Docker environment, it was easy to create. I also tried hardware encoding, but it was not stable, so these notes only cover building the normal setup. This is amateur work, so if you use it as a reference, do so at your own risk.
Update: In a separate article, I wrote about operating it with H/W encoding.
[Raspberry Pi 4] [Redo] Four-channel simultaneous terrestrial digital TV recording server on Raspberry Pi
Environment Tested
Raspberry Pi 4 8GB
Ubuntu Server 21.04 (notes)
I used docker-mirakurun-epgstation.
Docker is already installed (Docker installation notes)
$ docker --version
Docker version 20.10.7, build f0df350
$ docker-compose --version
docker-compose version 1.29.2, build unknown
Additional Equipment
PLEX USB-connected full-seg terrestrial digital TV tuner PX-Q1UD
B-CAS card
Connect the additional equipment to the Raspberry Pi.
# チューナによってはファームウェアが必要となるらしい。PX-Q1UD の場合は下記が必要。
$ sudo apt-get install -y unzip
$ wget http://plex-net.co.jp/plex/px-s1ud/PX-S1UD_driver_Ver.1.0.1.zip
$ unzip PX-S1UD_driver_Ver.1.0.1.zip
$ sudo cp PX-S1UD_driver_Ver.1.0.1/x86/i386/isdbt_rio.inp /lib/firmware/
再起動する
$ sudo reboot
ホスト側でも B-CAS カードが認識されるか確認しておく。(同じラズパイ4なのに、B-CASを認識しないボードがあってハマったため)
$ sudo apt install -y pcsc-tools pcscd
$ pcsc_scan
Japanese Chijou Digital B-CAS Card (pay TV)
pcscd は止めておく
$ sudo systemctl stop pcscd.socket
$ sudo systemctl disable pcscd.socket
Run the Mirakurun and EPGStation Containers
Without overthinking it, follow the official procedure.
# 公式サイトの手順を順番に実行していく
$ git clone https://github.com/l3tnun/docker-mirakurun-epgstation.git
$ cd docker-mirakurun-epgstation
$ cp docker-compose-sample.yml docker-compose.yml
$ cp epgstation/config/config.yml.template epgstation/config/config.yml
$ cp epgstation/config/operatorLogConfig.sample.yml epgstation/config/operatorLogConfig.yml
$ cp epgstation/config/epgUpdaterLogConfig.sample.yml epgstation/config/epgUpdaterLogConfig.yml
$ cp epgstation/config/serviceLogConfig.sample.yml epgstation/config/serviceLogConfig.yml
$ docker-compose run --rm -e SETUP=true mirakurunModify docker-compose.yml as needed. If logs keep being written to the SD card, the SD card will wear out quickly, so I set the logging driver to none.
# 各コンテナの定義に下記を追加
logging:
driver: noneStart the Containers
Start the containers. The first time, container images are built, so it takes a while. Relax and wait patiently.
$ docker-compose up -d
Building epgstation
...
(それなりにビルドに時間がかかります。20分ぐらい)
After the containers start, you can access EPGStation at http://<Raspberry Pi address>:8888. It also takes a little time to retrieve the program guide and related data, but recording worked without problems. 👍

At first I was building this with a 4 GB Pi 4, but I got stuck because it would not recognize the B-CAS card. Other Pi 4 and Pi 3 boards recognized it normally, so I moved the SD card to a Pi 4 8 GB partway through and continued the work. Did I draw a bad board? It is a mystery. 🍣
Bonus: I Tried Hardware Encoding, but... TBC
Even though the Pi 4 has more CPU power, it seems difficult to watch a program currently being broadcast by streaming it. There is no problem watching recorded video, but when watching a currently airing program in real time, the video stops every few seconds, making it basically unwatchable. Encoding after recording also takes quite a long time.
So I also looked into hardware encoding. However, I have not been able to run it stably at this point, so I will not write the details and will only leave notes on the items I tried.
Sites I Used as References
[Hardware Encoding] Hardware encoding in a Raspberry Pi 64-bit environment [Raspberry Pi]
I built ffmpeg on a Raspberry Pi 4 64-bit environment and tried hardware encoding
Checking the load when hardware-encoding MPEG-2 TS video to H.264 on a Raspberry Pi 4
Settings Needed for H/W Encoding
What I found by searching was that doing the following should make H/W encoding possible even from a container.
- Allow the container to access the host H/W.
- With ffmpeg 4.2.x, the video turns green, so it seems you need to use a different version.
- It seems you need to use a codec called h264_v4l2m2m.
- Change the settings so EPGStation encodes using h264_v4l2m2m.
Trying It
Allow the Container Side to Access the Host H/W
# /dev/vchiq にアクセスする必要があるらしい。そのパーミッションを変える。ラズパイもリブートしておく。
$ echo 'SUBSYSTEM=="vchiq",GROUP="video",MODE="0666"' | sudo tee /etc/udev/rules.d/10-vchiq-permissions.rules# docker-compose.yml を編集して epgstationのコンテナから /dev 周りを見れるようにする
# /dev/video* が本当に必要かどうかがよくわかっていない。
# ホストのH/Wをいじれるように privileged: true にする
$ vi docker-compose.yml
epgstation:
build: epgstation
volumes:
- /etc/localtime:/etc/localtime:ro
- ./epgstation/config:/app/config
- ./epgstation/data:/app/data
- ./epgstation/thumbnail:/app/thumbnail
- ./epgstation/logs:/app/logs
- ./recorded:/app/recorded
- /dev/vchiq:/dev/vchiq
- /dev/video10:/dev/video10
- /dev/video11:/dev/video11
- /dev/video12:/dev/video12
- /dev/video13:/dev/video13
- /dev/video14:/dev/video14
- /dev/video15:/dev/video15
- /dev/video16:/dev/video16
privileged: true
Change the ffmpeg Version
If I use the container built as-is, ffmpeg 4.2.4 is built. The latest release was 4.4, so I tried that for now. In the 4.3 series, 4.3.2 seems to be the latest. I did not change the configure options. As others have shown, when encoding with h264_v4l2m2m specified in 4.2.x, a wonderfully green video was generated. That phenomenon did not occur with 4.4, so it seems to be working.
# Dockerfile を編集
$ vi epgstation/Dockerfile
ENV FFMPEG_VERSION=4.2.4
ENV FFMPEG_VERSION=4.4
コンテナをビルドし直す
$ docker-compose build
I do not really understand it, but I tried something like a benchmark. This is an example of entering the container, running the command, and encoding a video of about three minutes.
# CPUでエンコードした場合。0.3倍速?なので10分以上かかった。エンコード中のCPU使用率は 380% 程度。
$ time ffmpeg -i test.m2ts -c:v libx264 -b:v 3M -y test.libx264.mp4
frame= 5631 fps=9.1 q=-1.0 Lsize= 75349kB time=00:03:07.78 bitrate=3287.0kbits/s dup=26 drop=0 speed=0.302x
real 10m21.868s
user 37m52.953s
sys 1m15.214s
# H/Wエンコードした場合。2.3倍速?なので1分ちょいで終わった。速い。エンコード中のCPU使用率は 180% 程度。
$ time ffmpeg -i test.m2ts -c:v h264_v4l2m2m -b:v 3M -num_capture_buffers 64 -y test.host.h264_v4l2m2m.mp4
frame= 5631 fps= 72 q=-0.0 Lsize= 71658kB time=00:03:07.55 bitrate=3129.9kbits/s dup=26 drop=0 speed=2.39
real 1m18.752s
user 2m14.459s
sys 0m14.174s
It seems to be working. The encoded video also plays properly. The CPU-encoded video is cleaner. The H/W-encoded video looked jagged. This might be adjustable with options.
Change the EPGStation Settings
Change the configuration files so encoding uses h264_v4l2m2m.
# libx264 が指定されているところを h264_v4l2m2m に置換する
$ emacs epgstation/config/config.yml
# 置換
# replace-string libx264 to h264_v4l2m2m
こっちも適当に修正
$ emacs epgstation/config/enc.js
// コーデックを変更
//const codec = ’libx264’;
const codec = ‘h264_v4l2m2m’;
// その他設定
Array.prototype.push.apply(args,[
‘-preset’, preset,
‘-aspect’, ‘16:9’,
‘-c:v’, codec,
‘-crf’, crf,
‘-b:v’, ‘3M’, // ビットレートの指定が必要らしいので追加。
‘-f’, ‘mp4’,
‘-c:a’, ‘aac’,
‘-ar’, ‘48000’,
‘-ab’, audioBitrate,
‘-ac’, ‘2’,
output
]);
For now, this changes post-recording encoding to H/W encoding. However, from the second time onward, encoding would not finish, recording itself would stop working, and it was too unstable for actual operation. This is as far as I got for now.

It would be great if I could get H/W encoding working properly, but I do not watch that much TV anyway. 🍣
More importantly, worrying about the SD card lifespan is getting tiresome, so maybe I should move the environment from the SD card to an SSD.