RTL-SDR + readsb + tar1090 + watchdog

J’ai réinstallé ma réception ADS-B sur une VM (Machine Virtuelle) Ubuntu serveur hébergée sur Proxmox avec la configuration suivante :

Configuration de la VM :

OS : Ubuntu serveur 25.04
Taille du disque (disk size) : 24 Go
Cœurs (cores) : 1
Processeur (cpu) : x86-64-v2-AES
Mémoire (memory) : 2048 Mo (2 Go)
Nom (name) : ADSB

Je rencontrais des problèmes de déconnexion lors de la réception des données ADS-B. Pour y remédier, j’ai donc ajouté un watchdog.

Mémo prêt à l’emploi pour (ré)installer et dépanner la chaîne complète.


1) Préparer la clé RTL-SDR

Vérifier la détection et installer les outils de test.

lsusb | grep -i realtek
sudo apt-get update
sudo apt-get install -y rtl-sdr
sudo rtl_test -t

2) Désactiver le driver DVB du noyau (évite les conflits)

echo -e "blacklist dvb_usb_rtl28xxu\nblacklist rtl2832\nblacklist rtl2830" | sudo tee /etc/modprobe.d/blacklist-rtlsdr.conf
sudo update-initramfs -u
sudo modprobe -r dvb_usb_rtl28xxu rtl2832 rtl2830 2>/dev/null || true

3) Installer et configurer readsb

Éditer /etc/default/readsb :

RECEIVER_OPTIONS="--device 0 --device-type rtlsdr --gain auto"
DECODER_OPTIONS="--fix --aggressive"
NET_OPTIONS="--net --net-heartbeat 60 --net-ro-size 1250 --net-ro-interval 0.05 --net-ri-port 30001 --net-ro-port 30002 --net-sbs-port 30003 --net-bi-port 30004,30104 --net-bo-port 30005"
JSON_OPTIONS="--write-json /run/readsb --write-interval 1"

Puis démarrer et vérifier :

sudo systemctl daemon-reload
sudo systemctl enable --now readsb
systemctl status readsb --no-pager
ls -l /run/readsb/aircraft.json

4) Installer le serveur web lighttpd pour tar1090

sudo apt-get install -y lighttpd
sudo systemctl enable --now lighttpd

Créer /etc/lighttpd/conf-available/89-tar1090.conf :

alias.url += ( "/tar1090/" => "/usr/share/tar1090/html/" )
$HTTP["url"] =~ "^/tar1090/data/" {
  alias.url += ( "/tar1090/data/" => "/run/readsb/" )
}

Activer et tester :

sudo lighttpd-enable-mod tar1090
sudo systemctl reload lighttpd
curl -I http://localhost/tar1090/
curl -I http://localhost/tar1090/data/aircraft.json

5) Ajouter un watchdog (redémarrage auto si le flux se fige)

Script /usr/local/bin/readsb-watchdog.sh :

#!/usr/bin/env bash
JSON_FILE="/run/readsb/aircraft.json"
SERVICE="readsb.service"
THRESHOLD_MIN=3
STATE_FILE="/run/readsb-watchdog.state"

messages=$(jq -r '.messages // empty' "$JSON_FILE" 2>/dev/null || true)
[[ -z "$messages" ]] && exit 0

now=$(date +%s)
last_messages=0
last_change=$now
[[ -f "$STATE_FILE" ]] && read -r last_messages last_change < "$STATE_FILE"

if [[ "$messages" -gt "$last_messages" ]]; then
  echo "$messages $now" > "$STATE_FILE"
  exit 0
fi

elapsed=$(( now - last_change ))
limit=$(( THRESHOLD_MIN * 60 ))

if [[ "$elapsed" -ge "$limit" ]]; then
  logger -t readsb-watchdog "No new messages for ${elapsed}s, restarting $SERVICE"
  systemctl restart "$SERVICE"
  echo "$messages $now" > "$STATE_FILE"
fi

Rendre exécutable :

sudo chmod +x /usr/local/bin/readsb-watchdog.sh

Unit systemd /etc/systemd/system/readsb-watchdog.service

[Unit]
Description=Watchdog readsb - restart if stalled
After=readsb.service

[Service]
Type=oneshot
ExecStart=/usr/local/bin/readsb-watchdog.sh

Timer /etc/systemd/system/readsb-watchdog.timer

[Unit]
Description=Run readsb watchdog every minute

[Timer]
OnBootSec=1min
OnUnitActiveSec=1min
AccuracySec=10s
Unit=readsb-watchdog.service

[Install]
WantedBy=timers.target

Activer :

sudo systemctl daemon-reload
sudo systemctl enable --now readsb-watchdog.timer
systemctl list-timers | grep readsb-watchdog

6) Vérifications rapides

head -c 200 /run/readsb/aircraft.json
curl -I http://localhost/tar1090/
journalctl -t readsb-watchdog -n 20 --no-pager

Astuce stabilité : désactiver l’autosuspend USB, utiliser un hub USB alimenté, et ventilater légèrement le dongle.

🛠️ Astuces de stabilité RTL-SDR

Réduisez les pertes de réception aléatoires en désactivant l’autosuspend USB, en utilisant un hub USB alimenté et en ajoutant un refroidissement léger au dongle.

1) Désactiver l’autosuspend USB (règle udev, recommandé)

  1. Trouver l’ID de la clé :
    lsusb | grep -i -E 'realtek|rtl|2832|2838'
    # Ex. : ID 0bda:2832 Realtek RTL2832U
  2. Créer la règle udev (remplacez idVendor/idProduct si besoin) :
    sudo tee /etc/udev/rules.d/99-rtlsdr-autosuspend.rules >/dev/null <<'EOF'
    ACTION=="add", SUBSYSTEM=="usb", ATTR{idVendor}=="0bda", ATTR{idProduct}=="2832", TEST=="power/control", ATTR{power/control}="on"
    EOF
    
    sudo udevadm control --reload
    sudo udevadm trigger
  3. Vérifier l’état (on = autosuspend désactivé) :
    # Remplacer 002/002 par votre bus/device réel
    sudo cat /dev/bus/usb/002/002/../power/control 2>/dev/null || \
    for f in /sys/bus/usb/devices/*/power/control; do echo "$f: $(cat "$f" 2>/dev/null)"; done | grep -iE 'on|auto'
Alternative globale (optionnelle) : désactiver l’autosuspend pour tout l’USB

Ajoutez le paramètre noyau (affecte toute la machine) :

sudo sed -i 's/GRUB_CMDLINE_LINUX="/GRUB_CMDLINE_LINUX="usbcore.autosuspend=-1 /' /etc/default/grub
sudo update-grub
sudo reboot

2) Hub USB alimenté

  • Privilégiez un hub alimenté (5V/2A+), surtout si le dongle chauffe ou si d’autres périphériques sont branchés.
  • Évitez les rallonges de mauvaise qualité ; câble court et blindé recommandé.

3) Refroidissement léger

  • Collez un radiateur (petit dissipateur) sur le tuner/boîtier du dongle.
  • Ajoutez un flux d’air (mini-ventilateur 5V silencieux) si l’enceinte est fermée.
  • Éloignez la clé de sources de chaleur (boîtier, alim, CPU).

Bonus : votre watchdog et la politique Restart=on-failure de systemd couvrent les blocages logiciels ; ces astuces USB réduisent les blocages matériels.