Come funziona internamente un reflector digitale: dal pacchetto UDP alla voce di centinaia di radio.

Premiamo il PTT.

Parliamo nel microfono.

Il nostro hotspot riceve il segnale e pochi istanti dopo la nostra voce viene ascoltata da radioamatori che si trovano a centinaia o migliaia di chilometri di distanza.

In mezzo a tutto questo spesso compare una parola:

reflector.

Ma che cos’è realmente?

Un reflector non è semplicemente “un server al quale si collegano le radio”.

È un sistema che mantiene informazioni sui client collegati, riceve flussi digital voice, interpreta il protocollo, decide dove debbano essere inoltrati e distribuisce i pacchetti alle destinazioni appropriate.

A seconda del software può inoltre gestire moduli, gateway, keepalive, dashboard, interlink, autenticazione o validazione, logging e perfino transcoding.

Progetti reali mostrano bene quanto il concetto possa diventare sofisticato: mrefd, per esempio, è un reflector open source M17 che gestisce Stream e Packet Mode e fino a 26 moduli; URF estende invece il concetto a diversi protocolli digital voice e può essere abbinato a un transcoder.

Vediamo quindi cosa accade realmente dentro un reflector.


Prima distinzione: repeater, gateway e reflector

Sono tre componenti differenti.

Ripetitore

Il ripetitore lavora principalmente sul lato RF:

RADIO
 ↓ RF
RIPETITORE
 ↓ RF
ALTRE RADIO

Può naturalmente essere collegato alla rete, ma la sua funzione fondamentale rimane quella di ricevere e ritrasmettere RF.


Gateway

Il gateway collega il mondo RF o un sistema locale alla rete.

Per esempio:

RADIO
 ↓
HOTSPOT / RIPETITORE
 ↓
GATEWAY
 ↓
INTERNET

Il software M17Gateway, per esempio, permette a un sistema M17 di collegarsi ai reflector e gestisce comandi quali collegamento, scollegamento, echo e informazioni sullo stato del link.


Reflector

Il reflector sta dall’altra parte.

Riceve connessioni da:

Gateway A
Gateway B
Gateway C
Hotspot D
Ripetitore E
...

e crea un punto comune nel quale i flussi vengono distribuiti.

Possiamo immaginarlo come una grande sala virtuale.


Una metafora utile: la conferenza telefonica

Immaginiamo dieci persone in una conference call.

Quando parla A:

A
 ↓
SERVER
 ├── B
 ├── C
 ├── D
 ├── E
 └── ...

Il server non deve necessariamente trasformare la voce.

Può semplicemente ricevere il flusso dati e replicarlo verso gli altri partecipanti.

Il reflector digitale segue spesso una filosofia simile.


Primo passo: collegamento del client

Supponiamo di avere:

HOTSPOT IZ1ABC

che vuole collegarsi:

REFLECTOR XYZ
MODULO A

Il gateway conosce normalmente:

  • hostname o IP;
  • porta;
  • protocollo;
  • identificativo/callsign;
  • modulo desiderato.

Nel mondo M17, per esempio, un reflector può possedere moduli distinti indicati da lettere; mrefd supporta fino a 26 canali/moduli, mentre gli host file utilizzati nell’ecosistema possono includere callsign del reflector, indirizzi IPv4/IPv6, moduli configurati e porta UDP.


Che cos’è un modulo?

Possiamo immaginare:

REFLECTOR D2ALP
│
├── MODULO A
├── MODULO B
├── MODULO C
└── MODULO D

Ogni modulo rappresenta una sala logica separata.

Client collegati ad A ascoltano normalmente il traffico di A.

Client collegati a B ascoltano B.

Non abbiamo necessariamente quattro server.

Abbiamo quattro gruppi logici gestiti dallo stesso processo reflector.


La tabella dei client

Il reflector deve sapere chi è collegato.

Concettualmente potrebbe mantenere una struttura simile:

CALLSIGN   IP             PORTA   MODULO   LAST SEEN
IZ1AAA     1.2.3.4        17000   A        10:21:03
IZ1BBB     5.6.7.8        23001   A        10:21:04
IW1CCC     9.8.7.6        41000   B        10:21:02

Non è necessariamente la struttura interna esatta di ogni software, ma rappresenta bene ciò che un reflector deve conoscere:

a quali endpoint deve inviare i pacchetti?

mrefd è esplicitamente progettato come reflector M17 con più moduli e gestione dei client Stream/Packet; applicazioni come M17Web dimostrano inoltre che il traffico di un reflector può essere osservato da software esterno via UDP e successivamente elaborato.


Perché spesso viene usato UDP?

Nelle applicazioni digital voice in tempo reale incontriamo frequentemente UDP.

Il motivo concettuale è semplice:

la voce ha bisogno soprattutto di arrivare in tempo.

Immaginiamo un pacchetto vocale appartenente alla parola:

buongiorno

che viene perso.

Dopo 500 ms non sarebbe molto utile ritrasmetterlo quando la conversazione è già andata avanti.

In sistemi real-time si preferisce spesso accettare una piccola perdita e proseguire.

M17Web, ad esempio, documenta esplicitamente un’architettura nella quale il sistema ascolta traffico UDP proveniente dai reflector M17, lo inoltra attraverso un proxy e decodifica l’audio nel browser. Anche implementazioni M17 relay descrivono esplicitamente connessioni e interlink gestiti tramite UDP.

Questo non significa che ogni protocollo digital voice utilizzi esclusivamente UDP: dipende dal sistema.


Premiamo il PTT

A questo punto iniziamo una trasmissione.

La catena potrebbe essere:

MICROFONO
    ↓
RADIO
    ↓ RF
MMDVM
    ↓
GATEWAY
    ↓ IP
REFLECTOR

La voce è già stata trasformata in dati digitali prima di raggiungere il reflector.

Questo punto è essenziale.


Il reflector normalmente non riceve “audio WAV”

Riceve frame del protocollo.

Concettualmente potremmo avere qualcosa del tipo:

HEADER
SOURCE
DESTINATION
STREAM ID
SEQUENCE
VOICE DATA
CONTROL

La struttura reale dipende dal protocollo.

Il server deve quindi analizzare i campi necessari per capire:

  • chi trasmette;
  • a quale flusso appartiene il pacchetto;
  • quale modulo è interessato;
  • dove deve essere inoltrato.

Lo Stream ID

Immaginiamo che due stazioni inizino trasmissioni quasi contemporaneamente.

Il reflector deve distinguere:

STREAM 0x1234

da:

STREAM 0xABCD

Un identificatore di flusso permette al software di associare pacchetti successivi alla stessa trasmissione.

Il concetto è analogo a mettere un’etichetta su ogni pacchetto:

“Io appartengo alla trasmissione di IZ1ABC iniziata poco fa.”


I pacchetti arrivano in sequenza

La voce viene suddivisa in piccoli blocchi.

Possiamo rappresentarla così:

P1
P2
P3
P4
P5
P6
...

Il network li trasporta attraverso Internet.

Idealmente arrivano:

1 2 3 4 5 6

ma una rete IP reale può produrre:

1 2 4 3 5 6

oppure:

1 2 X 4 5 6

dove X rappresenta un pacchetto perso.

È qui che diventano importanti:

  • sequence number;
  • buffering;
  • jitter management;
  • gestione delle perdite.

Il reflector riceve il primo frame

Supponiamo:

SOURCE = IZ1ABC
MODULE = A
STREAM = 1234

Il reflector verifica il contesto della connessione e determina:

questa trasmissione appartiene al modulo A.

A questo punto consulta l’elenco dei client associati ad A.


Fan-out: una copia diventa cento copie

Supponiamo che sul modulo A ci siano:

100 client

Il reflector riceve:

1 pacchetto

e deve distribuirlo ai client interessati.

Concettualmente:

                ┌→ CLIENT 1
                ├→ CLIENT 2
                ├→ CLIENT 3
PACCHETTO → REF ├→ CLIENT 4
                ├→ ...
                └→ CLIENT 100

Questo processo può essere chiamato fan-out.

Il reflector diventa quindi un moltiplicatore di traffico.


Un semplice conto

Supponiamo, solo come esempio didattico, che il flusso IP complessivo di una trasmissione sia:

10 kbit/s

con 100 destinatari.

In ingresso il server riceve circa:

10 kbit/s

in uscita potrebbe dover inviare, nell’ordine di grandezza:

10 × 100 = 1000 kbit/s

cioè circa 1 Mbit/s, trascurando overhead e traffico di controllo.

Con:

500 client

il traffico cresce ulteriormente.

Per questo un reflector molto frequentato necessita non tanto di enormi capacità CPU quanto di:

  • rete affidabile;
  • banda;
  • packet processing efficiente;
  • kernel/network stack ben configurato.

Il server deve decodificare la voce?

Non necessariamente.

Questa è probabilmente la parte più importante dell’articolo.

Se:

CLIENT A → codec X
CLIENT B → codec X

il reflector può spesso distribuire direttamente il frame codificato.

CODEC X DATA
     ↓
REFLECTOR
     ↓
CODEC X DATA

Non serve:

decode → PCM → encode

Il server non deve quindi necessariamente sapere “cosa stiamo dicendo”.

Deve sapere dove deve mandare quei dati.


Routing non significa transcoding

Ecco la differenza fondamentale.

Routing/reflecting

AMBE
 ↓
AMBE

oppure:

Codec2
 ↓
Codec2

Il payload vocale resta essenzialmente nello stesso formato.

Transcoding

AMBE
 ↓
DECODER
 ↓
PCM
 ↓
ENCODER
 ↓
CODEC2

Qui il server deve realmente convertire l’audio.

Un progetto come URF chiarisce bene la distinzione: può supportare diversi protocolli, ma senza il componente transcoder gli utenti che impiegano codec differenti possono ascoltare soltanto gli altri client compatibili con il proprio codec.


Reflector multiprotocollo

Qui la faccenda diventa molto più interessante.

Supponiamo:

DMR
  \
YSF ---- REFLECTOR
  /
D-STAR

Il server deve comprendere diversi protocolli di rete.

Non significa però automaticamente che sappia convertire anche i codec.

Possiamo avere:

PROTOCOL TRANSLATION

senza:

VOICE TRANSCODING

Sono due operazioni differenti.


Prendiamo XLX come esempio concettuale

Software della famiglia XLX sono nati come reflector/gateway multiprotocollo per reti digital voice.

DMRGateway, per esempio, può collegare un sistema MMDVM fino a più reti DMR e prevede specificamente una rete XLX tra quelle configurabili.

Questo dimostra come nel mondo digital voice i ruoli possano concatenarsi:

MMDVM
 ↓
DMRGateway
 ↓
XLX
 ↓
altri gateway/client

Il transcoder

Se due lati utilizzano codifiche vocali incompatibili occorre aggiungere:

TRANSCODER

L’architettura può diventare:

PROTOCOLLO A
     ↓
REFLECTOR
     ↓
TRANSCODER
     ↓
PROTOCOLLO B

Esistono implementazioni multiprotocollo che utilizzano proprio un componente transcoder separato. URF, ad esempio, supporta la possibilità di transcoding locale o remoto mediante un componente dedicato.


Perché il transcoder è separato?

Perché svolge un lavoro completamente differente.

Il reflector deve principalmente:

ricevere
identificare
decidere
replicare
trasmettere

Il transcoder deve:

decodificare codec A
 ↓
produrre audio intermedio
 ↓
codificare codec B

Può quindi richiedere:

  • maggiore CPU;
  • hardware vocoder;
  • software aggiuntivo;
  • buffering;
  • gestione della latenza.

Separare le due funzioni permette di scalare il sistema meglio.


La latenza si accumula

Seguiamo una QSO:

RADIO
 ↓
RF
 ↓
HOTSPOT
 ↓
INTERNET
 ↓
REFLECTOR
 ↓
TRANSCODER
 ↓
INTERNET
 ↓
HOTSPOT
 ↓
RF
 ↓
RADIO

Ogni freccia richiede tempo.

Abbiamo:

  • codifica;
  • buffering;
  • RF;
  • gateway;
  • uplink Internet;
  • routing;
  • reflector;
  • eventuale transcoding;
  • downlink;
  • decodifica.

È così che due radio poste a pochi metri l’una dall’altra possono avere centinaia di millisecondi di ritardo se stanno comunicando attraverso un server a migliaia di chilometri.


Perché a volte due persone si parlano sopra?

Immaginiamo:

IZ1AAA termina di parlare

ma il pacchetto finale deve ancora attraversare:

Internet → reflector → Internet → hotspot

Il secondo operatore sente la fine della trasmissione leggermente dopo.

Se risponde istantaneamente, la rete potrebbe ancora avere code o stati di stream in fase di chiusura.

Ecco perché nelle reti digitali è buona pratica lasciare una piccola pausa tra un passaggio e l’altro.

Non serve aspettare cinque secondi.

Ma neppure schiacciare il PTT nello stesso istante in cui scompare l’audio.


Keepalive: “sei ancora lì?”

Il reflector deve anche capire se un client è ancora collegato.

Supponiamo che un hotspot venga spento senza inviare correttamente un messaggio di disconnessione.

Il server potrebbe continuare a considerarlo online.

Per questo molti protocolli utilizzano meccanismi di:

PING
PONG
KEEPALIVE
TIMEOUT

Concettualmente:

REFLECTOR → sei vivo?
CLIENT    → sì

REFLECTOR → sei vivo?
CLIENT    → sì

REFLECTOR → sei vivo?
CLIENT    → ...

timeout

CLIENT RIMOSSO

Questo mantiene pulita la tabella delle connessioni.


NAT: perché complica tutto

Molti hotspot si trovano dietro:

router domestico
NAT
CGNAT
firewall

Il reflector non può necessariamente aprire spontaneamente una connessione verso quel dispositivo.

È quindi il client che generalmente avvia la comunicazione verso il server.

HOTSPOT
   │
   └────────→ REFLECTOR

Una volta creata la mappatura NAT, i pacchetti di risposta possono tornare verso il client finché quella associazione rimane valida.

Anche questo spiega l’utilità dei keepalive.


La dashboard non è il reflector

Altro errore comune.

Apriamo:

https://reflector.example

e vediamo:

  • last heard;
  • client;
  • moduli;
  • callsign;
  • uptime.

Quella pagina non è necessariamente il reflector stesso.

È una dashboard.

Il backend reflector può essere:

processo C/C++
 ↓
log/XML/database/stato
 ↓
dashboard PHP/Go/web
 ↓
browser

Il progetto ufficiale ref-dash di M17, per esempio, è esplicitamente una dashboard separata progettata per essere utilizzata insieme a mrefd.


Last Heard

Quando arriva una trasmissione il reflector può aggiornare informazioni come:

CALLSIGN
MODULO
ORA
SORGENTE

La dashboard legge questi dati e costruisce il classico:

LAST HEARD

Il Last Heard è quindi principalmente un sistema di reporting.

Non è ciò che trasporta la voce.


Il reflector può anche registrare statistiche

Un Sysop può voler sapere:

quanti client?
quanti stream?
quale modulo?
quanta banda?
quanti pacchetti?
quali errori?
uptime?

Queste informazioni possono essere esportate verso:

  • dashboard;
  • log;
  • Prometheus;
  • Grafana;
  • sistemi di alert.

A quel punto possiamo trasformare un reflector in un servizio realmente monitorato.


Interlink tra reflector

Supponiamo ora di avere:

REFLECTOR A

e:

REFLECTOR B

Possiamo collegarli.

CLIENT
 ↓
REF A
 ↓
INTERLINK
 ↓
REF B
 ↓
CLIENT

Il server A diventa, dal punto di vista di B, una sorta di ulteriore endpoint o relay.

Progetti moderni di relay M17 prevedono espressamente gestione sia dei client sia degli interlink tra relay.


Attenzione ai loop

Il problema diventa evidente.

A → B
B → C
C → A

Un pacchetto potrebbe iniziare a circolare.

Serve quindi una logica capace di impedire:

  • duplicazioni;
  • loop;
  • riverberi;
  • stream replicati più volte.

Più una rete multiprotocollo diventa grande, più la progettazione del routing diventa importante.


Ecco perché i bridge possono diventare pericolosi

Immaginiamo:

DMR TG 123
 ↓
YSF ROOM A
 ↓
M17 MODULE B
 ↓
DMR TG 123

Abbiamo creato potenzialmente un percorso circolare.

Da qui possono nascere:

  • loop audio;
  • stream bloccati;
  • PTT continuo;
  • duplicazioni;
  • enorme traffico inutile.

Il Sysop deve quindi disegnare la rete prima di collegare tutto con tutto.


Una buona topologia

Molto meglio:

              MASTER/HUB
             /    |     \
            /     |      \
         DMR     M17     YSF

con regole chiare di conversione.

Piuttosto che:

DMR ↔ YSF
 ↕     ↕
M17 ↔ DSTAR
 ↖_____↗

senza sapere più chi genera cosa.


Il reflector può avere più processi

In una struttura più complessa potremmo avere:

          NGINX / WEB
              │
          DASHBOARD
              │
        ┌─────┴─────┐
        │ REFLECTOR │
        └─────┬─────┘
              │
       TRANSCODER
              │
        DATABASE/LOG
              │
         MONITORING

Non è obbligatorio che tutto sia un unico programma.

Anzi, separare le funzioni spesso rende l’infrastruttura più facile da mantenere.


Quanto potente deve essere il server?

Per un piccolo reflector senza transcoding non è necessariamente necessaria una macchina potentissima.

Il lavoro principale consiste infatti spesso nel:

  • ricevere pacchetti;
  • analizzare piccoli header;
  • mantenere stati;
  • replicare pacchetti.

Quando introduciamo:

  • molti utenti;
  • numerosi moduli;
  • transcoding;
  • dashboard;
  • database;
  • bridge multiprotocollo;

le esigenze aumentano.

Spesso però il vero requisito critico rimane la qualità della connettività.


Cosa preferire?

Per un reflector serio cercherei:

datacenter affidabile
IP pubblico
buon peering
latenza contenuta
packet loss minimo
banda sufficiente
monitoring
backup

piuttosto che:

64 core CPU
+
connessione instabile

Un digital voice reflector vive di pacchetti.

Se quei pacchetti arrivano male, una CPU enorme non risolve il problema.


Un esempio completo

Seguiamo IZ1ABC.

Premiamo il PTT.

1. IZ1ABC parla

2. La radio codifica la voce

3. Trasmette RF

4. Hotspot/MMDVM riceve

5. Gateway crea i pacchetti di rete

6. Internet trasporta UDP/IP

7. Reflector identifica:
   source
   stream
   module

8. Cerca tutti i client del modulo

9. Replica il frame

10. Ogni gateway riceve la copia

11. Il payload torna verso RF

12. Ogni radio decodifica la voce

Tutto questo avviene in una frazione di secondo.


Se c’è un altro codec

Aggiungiamo:

13. Il client B usa codec differente

allora può entrare in gioco:

TRANSCODER

e il percorso diventa:

codec A
 ↓
decode
 ↓
PCM
 ↓
encode
 ↓
codec B

È esattamente per questo che dobbiamo distinguere sempre:

reflector

da

transcoder.


Reflector o master server?

Sono concetti che possono sovrapporsi in alcuni ecosistemi ma non sono necessariamente sinonimi.

Un reflector viene tipicamente pensato come una risorsa alla quale più nodi si collegano per condividere un flusso o un modulo.

Un master DMR, per esempio, può implementare logiche più ampie:

  • autenticazione;
  • routing Talkgroup;
  • policy;
  • gestione ripetitori;
  • networking con altri server.

Il principio della distribuzione dei pacchetti rimane simile, ma l’architettura complessiva può essere molto più sofisticata.


Reflector e Talkgroup non sono la stessa cosa

Anche qui attenzione.

Un:

MODULO A

di un reflector e un:

TG 22215

DMR possono produrre un’esperienza apparentemente simile:

“parlo e tutti quelli collegati mi sentono.”

Ma dal punto di vista tecnico sono concetti appartenenti ad architetture differenti.

Un bridge può associare:

TG 22215
        ↕
Modulo A

ma quell’associazione è una decisione del gateway/bridge.

Non significa che modulo e Talkgroup siano nativamente la stessa entità.


Un reflector open source è una scuola di networking

Ed è forse questo l’aspetto più bello.

Installare e studiare un reflector permette di imparare contemporaneamente:

  • Linux;
  • UDP;
  • socket;
  • NAT;
  • DNS;
  • firewall;
  • protocolli digital voice;
  • C/C++;
  • routing;
  • monitoring;
  • cybersecurity.

Progetti come mrefd, M17Gateway, URF e gli strumenti G4KLX sono disponibili come sorgenti e rappresentano un laboratorio formidabile per chi voglia comprendere davvero cosa accade dietro una rete digital voice.


Conclusioni

Quando premiamo il PTT su un hotspot collegato a un reflector, dietro la nostra voce non c’è magia.

C’è una sequenza estremamente precisa:

VOCE
 ↓
VOCODER
 ↓
RF
 ↓
GATEWAY
 ↓
PACCHETTI IP
 ↓
REFLECTOR
 ↓
ROUTING / FAN-OUT
 ↓
PACCHETTI IP
 ↓
GATEWAY
 ↓
RF
 ↓
VOCODER
 ↓
VOCE

E solo quando vogliamo mettere in comunicazione sistemi incompatibili aggiungiamo eventualmente:

TRANSCODER

Il reflector quindi non è semplicemente “un server che ripete l’audio”.

È un router specializzato per flussi digital voice, capace di mantenere lo stato dei client e distribuire rapidamente piccoli pacchetti verso decine, centinaia o migliaia di endpoint.

Capire questo significa anche capire perché:

  • la latenza conta;
  • il packet loss conta;
  • il jitter conta;
  • una buona connessione conta;
  • i loop nei bridge sono pericolosi;
  • il transcoding degrada potenzialmente l’audio;
  • un server ben progettato può gestire moltissimo traffico con risorse relativamente modeste.

La prossima volta che colleghiamo un hotspot a un reflector possiamo quindi immaginare il vero percorso della nostra voce:

non una voce che attraversa Internet, ma migliaia di piccoli pacchetti che il reflector riceve, riconosce, instrada e moltiplica in tempo reale.

Lascia un commento

Il tuo indirizzo email non sarà pubblicato. I campi obbligatori sono contrassegnati *