UAT Translation from Dump978-fa

So I have been trying to pipe UAT data into Virtual Radar Server (VRS) and found it doesn’t like UAT data and only likes ADS-B, Mode-S or MLAT data. When connecting to dump978-fa’s Basestation port of 30978, it would get messages, but not decode any messages from it. If it told to to connect to JSON output at 30979, i would get nothing but a connection.

I saw the mutability fork of dump978 had a program called uat2esnt bundled with it, which dump978-fa seems to not include. It has a simple operation on how to pipe dump978’s output into it, and use nc to pipe it to your local dump1090 instance, but not in PiAware’s SD Card image. So I dug and figure out how to get this working.

1. Build Dump978 (You will only be using uat2esnt from it so it wont mess up your current install. It clones github repo and builds the program. It also gives permission to execute the newly build uat2esnt program).

cd ~
mkdir builds
git clone GitHub - mutability/dump978: Experimental demodulator/decoder for UAT on 978MHz
cd dump978
make
chmod +x uat2esnt

2. Modify Dump978 Setup Script (This was the hard part, finding how dump978 is started. We are making a backup copy first just in case) (THIS CAN BE DONE A LOT EASIER SKIP TO END TO SEE)

sudo cp /usr/share/dump978-fa/start-dump978-fa /usr/share/dump978-fa/start-dump978-fa.bac
sudo nano /usr/share/dump978-fa/start-dump978-fa
Change From:


To:
exec /usr/bin/dump978-fa
$RECEIVER_OPTIONS $DECODER_OPTIONS $NET_OPTIONS |
./home/pi/builds/dump978/uat2esnt |
nc -l -k -p 30977
“$@”

CTRL-O to write the file, then CTRL-X to exit Nano.

sudo systemctl restart dump978-fa.service
This restarts the service, or just reboot the system with:
sudo reboot

That’s it!!

Note, you can change the options for nc. I have it outputting the AVR / BEAST output to port 30977. You can change this to any port you want. There’s other fancier stuff you can do with nc like push the data to your server, but for most software you want to just serve it from your Pi.

I haven’t 100% tested this yet but it should do it. There’s a local flight school nearby that usually has a lot of UAT (10-30 flights a day) traffic, but with the holiday (Mothers Day) and a lot of rain, I have not received any UAT data to verify this.

EDIT
After Step 1, it is MUCH MUCH easier to simply just ran this one-liner rather than modify PiAware’s settings. Do this instead of step 2.

nc -q -1 127.0.0.1 30978 | exec /home/pi/builds/dump978/uat2esnt | nc -l -k -p 30977

This listens to your Pi’s 30978 port output, feeds it to uat2esnt, then outputs AVR format on port 30977. I will try and make a more elegant solution with some loops and whiles incase of disconnects but down and dirty it does the simple trick.

1 Like

Not quite gonna work as dump978-fa by default does not output messages on stdout.
You want this option so it prints to console/stdout:
--raw-stdout

Also i’m not sure dump978-fa will start correctly without nc also having a connection on the listen port.

Personally i would rather make a script that basically connects to dump978-fa on port 30978, pipes its output to uat2esnt and then provides output again on another port like you are doing now.

That way you don’t need to mess with the dump978-fa feeding flightaware and displaying in skyview.
(It doesn’t care who connects via network or if that program is unresponsive for example)

You would need to create your own service optimally which for example starts a bash script.

Maybe have a look at this:
GitHub - wiedehopf/combine1090: Combine data from multiple ADS-B receivers into one readsb decoder / tar1090 webinterface

You could modify the bash script and the service to fit your needs or make something along those lines.

1 Like

Oh interesting. I didn’t know it didn’t give a verbose output by default.

In theory, this can be done MUCH simpler, like you said with a simple batch script listening on port 30978…

nc 127.0.0.1 30978 | exec /home/pi/builds/dump978/uat2esnt | nc -l -k -p 30977

Simply setting this to run on startup, perhaps on delay, should work just find. MUCH cleaner.

Testing now. Thanks!!!

1 Like

nc is kinda tricky with broken connections and stuff like that.
You might need a while loop and some timeouts for the nc sprinkled in there.

Edit: And seriously have a little look at how easy the service file is.
You basically just place it in the correct directory and point it at your script.
Then you go systemctl enable whatever and it starts on boot.
Logs to journalctl and so on, very useful.

1 Like

Yeah that’s what I’m finding out… -k option helps on the output nc command. I just need to modify the input incase of dump978 restarts. -q -1 may do it I think. But a While/Loop should work better.

1 Like

If i knew you had a clue i would’ve pointed you in the right direction earlier :slight_smile:
But i didn’t feel like actually writing a script and testing it.

You could just delete most from the combine1090.sh script in my the github repository i linked.

socat has a mode to connect to stdout and the timeouts should already be in place, the while loop as well.

3 Likes

Works! :slight_smile: MUCH MUCH simpler.

3 Likes

Is it possible to make this simple enough for a noob like me to install? I have VRS running on the same Pi as 3.7.1 operates from.
Thanks,
Glenn

1 Like

socat -u tcp4-connect:127.0.0.1:30978,forever,interval=5,fork STDOUT | exec /home/pi/builds/dump978/uat2esnt | socat -u STDIN tcp4-listen:30977,forever,interval=5,fork

This should do it a bit better with socat like you said. Like Rick Astly it will never give up, not let you down, and will keep listening forever, retrying every 5 seconds until it reconnects. Tested running it against my dump1090 message log, restarting the Pi and Dump1090.

while true
do
socat -v -u tcp4-connect:127.0.0.1:30978,forever,interval=5,fork STDOUT | exec /home/pi/builds/dump978/uat2esnt | socat -v -u STDIN tcp4-listen:30977,forever,interval=5,fork
sleep 5
done

This looks right? Maybe.

And to others interesting I will try and make this easier to setup soon…

2 Likes

30978 doesn’t produce Basestation format output, 30978 emits the raw UAT messages.

More generally, the reason why dump978-fa doesn’t include uat2esnt is that I’m trying to get away from that translation step - it will cause some minor problems if the data ever gets looped back to a feeder (either piaware or another feeder) and it naturally loses information.

Ideally what would happen is that more software like VRS would start adding native UAT support. But I appreciate that this doesn’t help you right away!

A middle ground might be to produce a kinda-like-Basestation format output on a separate port (i.e. decoded data) as that is less likely to be misinterpreted as “real” 1090MHz data further downstream. I just don’t want to patch this up so much that it becomes the expected way of doing things and so nobody builds proper support for UAT. It’s way better if you can use software that directly understands UAT, because UAT’s message layouts are fundamentally different to 1090MHz ADS-B and you’re always going to lose information converting between them.

4 Likes

Ah yes I meant raw. Sorry about that! Everything else is perfectly understandable. If UAT is going to be used, programs like VRS and such should understand UAT data as it does contain a lot more info than most ADS-B and 1090mhz data generally, and like you said you lose info in the translation down to the most common level. However I see this as coming very slow, as UAT is only supported in the United States for now. For now, this translation works to just get the planes on my VRS map… a basestation output would be VERY helpful so custom scripting wouldn’t be needed, not that running one command is hard for now.

FYI, this is the final command you want to run. The other one I had I slipped “fork” option in accidentally, which ran a new socat process. After a few days I had a hundred or so socat processes, which sent my Pi’s CPU close to 70C :slight_smile: I also added a loop. Simply follow Step #1 above to compile uat2esnt, then write this file somewhere. chmod u+x it, and you’re good! It will output AVR Beast data on port 30977 in this example.

#!/bin/bash
while true
do
socat -u tcp4-connect:127.0.0.1:30978,forever,interval=5 STDOUT | /home/pi/builds/dump978/uat2esnt | socat -u STDIN tcp4-listen:30977,forever,interval=5
sleep 1
done

1 Like

Using the script, i can get VRS to connect to it, but it never sees any messages or planes.
Very weird.
I’ve run the first part of the command with the pipe to uat2esnt or uat2text and it spews tons of lines, for some reason VRS doesn’t like the data I guess.
I have the receiver in VRS set to AVR or Beast, and it does show connected.
Only difference is my VRS is on a different host, but it connects to the pi fine for 1090 or MLAT, so not sure why the 978 connection isn’t working.

Can you post a sample output?

$ socat -u tcp4-connect:127.0.0.1:30978,forever,interval=5 STDOUT |  uat2esnt

<000000000000FF922B0E599107715EB01459019FAE;
<000000000000FF922B0E59910774F272C236476D6E;
<000000000000FF922B0E5999800580A00400FF36F4;
<000000000000FF922B01E9911B7163061A5456FE3E;
<000000000000FF922B01E9911B74F6B4C81070EFED;
<000000000000FF922B01E999805E0200040080D65E;
<000000000000FF922B01E9911B8163061A60BE32C9;
<000000000000FF922B01E9911B84F6B4C81C99721E;
<000000000000FF922B01E999805E01C004009C2D54;
<000000000000FF922B0C469109F102F622A0284B2F;
<000000000000FF922B0C469109F49840D02F8FBE07;
<000000000000FF922B0C4699845602600400C720D8;
<000000000000FF922B0E38911D60E4104034F0787A;
<000000000000FF922B0E38911D6479DCED23213522;
<000000000000FF922B0E3899805B8D200400C2A559;
<000000000000FF922B0947912951322E4228044F46;
<000000000000FF922B0947912954C6AEEF0C0F77DE;
<000000000000FF922B09479980549348E000ED7742;
<000000000000FF922B09479127E131EA42346C0320;
<000000000000FF922B09479127E4C66AEF17E4EC69;
<000000000000FF922B094799803E9468E400FE667E;
<000000000000FF922B09F4910BB119BE20DA7AC0FF;
<000000000000FF922B09F4910BB4AEA6CE74C2D1B5;
<000000000000FF922B09F499843688482000A3D8F7;
<000000000000FF922B0E38911D70E3CE4052EEA3BF;
<000000000000FF922B0E38911D74799CED4066CB52;
<000000000000FF922B0E3899805C8CE0040080909F;
<000000000000FF922B0E38911D60E3B2405D6A9C70;
<000000000000FF922B0E38911D647980ED4B2D48D0;
<000000000000FF922B0E3899805B8D00040087D970;
<000000000000FF922B09479127C131D842537358AF;
<000000000000FF922B09479127C4C658EF36F810AB;
<000000000000FF922B094799805C9228E80061341A;
<000000000000FF922B0782910F419379F6FB2298FA;
<000000000000FF922B0782910F452658A578AA91E6;
<000000000000FF922B0782998442080004004D0D4A;
<000000000000FF922B0947912721316A425A3C3195;
<000000000000FF922B0947912724C5EEEF3C03C772;
<000000000000FF922B09479980329468F00032F536;
<000000000000FF922B09F4910B91197820C2570CF2;
<000000000000FF922B09F4910B94AE60CE5CEE3CD0;
<000000000000FF922B09F499843588682400DB8D8C;
<000000000000FF922B094791272131504256D14B7C;
<000000000000FF922B0947912724C5D4EF391139FE;
<000000000000FF922B09479980289468F0001C1A3A;
<000000000000FF922B0DF59113412B8E2532493589;
<000000000000FF922B0DF5911344C02AD2B3F52962;
<000000000000FF922B0DF599804C09402000A314C9;
<000000000000FF922B09F4910B81196820B0B85A11;
<000000000000FF922B09F4910B84AE50CE4A466CFC;
<000000000000FF922B09F499843887E828001D488F;
<000000000000FF922B0C46910B010396225C35B311;
<000000000000FF922B0C46910B0498DCCFEDA36D09;
<000000000000FF922B0C4699844106600400514D1E;
<000000000000FF922B09479125C1310C425BEC7905;
<000000000000FF922B09479125C4C590EF3E9F81E8;
<000000000000FF922B094799801B94A8F000280CB7;
<000000000000FF922B094791257130E8425DFE1780;
<000000000000FF922B0947912574C56CEF40172642;
<000000000000FF922B094799800F94C8F000DB0F14;
<000000000000FF922B09F4910B71194C20A7DC9269;
<000000000000FF922B09F4910B74AE36CE424CB4C4;
<000000000000FF922B09F499843788282400576042;
<000000000000FF922B0C46910B0103AC2250D8C9F8;
<000000000000FF922B0C46910B0498F2CFE1A402F4;
<000000000000FF922B0C469984410680040074CDC8;
<000000000000FF922B0947912501308A426647C4CF;
<000000000000FF922B0947912504C510EF48CF23E9;
<000000000000FF922B094799800A9488EC00F654B0;

That looks strange for an AVR type message.

Which version for uat2esnt are you using?

Can you try using this switch:
uat2esnt -t
(it excludes tis-b messages, those are not recognized by VRS)

uat2esnt is the current version from git - up to date ( the -t option was the last add) 9aea4f4a2a5acf07e3d428e365ae330676bed8b9

$ socat -u tcp4-connect:127.0.0.1:30978,forever,interval=5 STDOUT | uat2esnt -t

<000000000000FF96ACA651902B00F7120770E7F560;

<000000000000FF96ACA651902B048C8EB594A70845;

<000000000000FF96ACA65199005C8EB80800E5FEFF;

<000000000000FF96ACA651902B00F6FA077978AE88;

<000000000000FF96ACA651902B048C76B59DCEEAEE;

<000000000000FF96ACA65199005C8EB808091A7A9A;

Blockquote

And

$ socat -u tcp4-connect:127.0.0.1:30978,forever,interval=5 STDOUT | uat2text
HDR:
MDB Type: 0
Address: ACA651 (ICAO address via ADS-B)
SV:
NIC: 9
Latitude: +37.4383
Longitude: -122.4326
Altitude: 7400 ft (barometric)
N/S velocity: -112 kt
E/W velocity: 88 kt
Track: 141
Speed: 142 kt
Vertical rate: 192 ft/min (from geometric altitude)
UTC coupling: yes
TIS-B site ID: 0
RSSI: 0.0 dBFS

HDR:
MDB Type: 1
Address: ACA651 (ICAO address via ADS-B)
SV:
NIC: 9
Latitude: +37.4379
Longitude: -122.4322
Altitude: 7400 ft (barometric)
N/S velocity: -111 kt
E/W velocity: 88 kt
Track: 141
Speed: 141 kt
Vertical rate: 192 ft/min (from geometric altitude)
UTC coupling: yes
TIS-B site ID: 0
MS:
Emitter category: Light <= 7000kg
Callsign: squawk 3354
Emergency status: No emergency
UAT version: 2
SIL: 3
Transmit MSO: 62
NACp: 10
NACv: 2
NICbaro: 0
Capabilities: CDTI
Active modes:
Target track type: true heading
AUXSV:
Sec. altitude: 7625 ft (geometric)
RSSI: 0.0 dBFS

HDR:
MDB Type: 1
Address: ACA651 (ICAO address via ADS-B)
SV:
NIC: 9
Latitude: +37.4369
Longitude: -122.4313
Altitude: 7400 ft (barometric)
N/S velocity: -111 kt
E/W velocity: 88 kt
Track: 141
Speed: 141 kt
Vertical rate: 192 ft/min (from geometric altitude)
UTC coupling: yes
TIS-B site ID: 0
MS:
Emitter category: Light <= 7000kg
Callsign: N914JB
Emergency status: No emergency
UAT version: 2
SIL: 3
Transmit MSO: 34
NACp: 10
NACv: 2
NICbaro: 0
Capabilities: CDTI
Active modes:
Target track type: true heading
AUXSV:
Sec. altitude: 7625 ft (geometric)
RSSI: 0.0 dBFS

HDR:
MDB Type: 2
Address: ACA651 (ICAO address via ADS-B)
SV:
NIC: 9
Latitude: +37.4362
Longitude: -122.4306
Altitude: 7400 ft (barometric)
N/S velocity: -111 kt
E/W velocity: 88 kt
Track: 141
Speed: 141 kt
Vertical rate: 128 ft/min (from geometric altitude)
UTC coupling: yes
TIS-B site ID: 0
AUXSV:
Sec. altitude: 7625 ft (geometric)
RSSI: 0.0 dBFS

Can you provide a sample output for this part of the command?

$ socat -u tcp4-connect:127.0.0.1:30978,forever,interval=5 STDOUT
-80b7970335c96d4cc13cfa47ae2f1df19f29297378370c80f9b3e2b3dc887329ab99;rs=7;rssi=-20.3;t=1563142073.269;
-eb1e6d2152ee0002ff00fbdd7a61012fe6f2db775c59268aebce6df34e60700aec24;rs=6;rssi=-20.2;t=1563142935.181;

echo '-80b7970335c96d4cc13cfa47ae2f1df19f29297378370c80f9b3e2b3dc887329ab99;rs=7;rssi=-20.3;t=1563142073.269;' | ./uat2esnt 
*96B79703000000000000001077F0;

This is my output for feeding that into uat2esnt.

I’m not sure where that <0000000 comes from.
It seems to be an error.

Which git do you get the uat2esnt from?
(Mine is from GitHub - mutability/dump978: Experimental demodulator/decoder for UAT on 978MHz and i just typed make to compile it)

built it on the pi.
Looks like unicode support of some type is messing with it to me.

I can rebuilt it and play with thing.

Ironically, I just finally got FlightAirMap working hosted on my mac, so probably going to drop VRS now.