APRS packet radio demodulator

This is a receive-only software modem capable of demodulating the APRS service, and probably many other packet radio services based on AX.25 over Bell 202 over Narrow-band FM. This program is part of SigPlay my signal playground apps, and may be downloaded from that page.

The program reads a data stream (or file) containing 48kHz real-valued samples from the audio output of a scanner or radio receiver tuned appropriately. For my experiments I use a AOR AR8600Mk2 radio receiver connected to the sound-card of my computer.

The signal is resampled to 9600Hz using a polyphase decimator with a hard-coded FIR filter. 9600Hz was chosen because it is exactly 8 times the baudrate (8 * 1200Hz) and exactly a fifth of the incoming sample rate (48000 / 5). This speeds up the modem since it doesn't need to deal with as many samples while still keeping things simple by making sure the baud length is an integral number of samples.

The demodulator uses two complex correlators to detect the 1200Hz and 2200Hz tones respectively. A user-configured gain factor is applied to the output of the correlators. This was needed for my radio at least, since the 2200Hz tone was always weaker. In the future an auto-gain feature might be implemented.

Carrier is detected by comparing the total energy in the tones matched by the correlators with the total signal energy, and checking that both are above a threshhold. This works out great if you have a radio with sqelch, but might have some problems if you don't have sqelch. For my AR8600Mk2 that means I cannot use the demodulator with the detector output from the radio but must use the audio output.

The output of the correlators is compared as close to the middle of the baud as we can come to determine the bit transmitted. The bit is then differentially decoded and sent to the deframer. The baud tracking is achieved using a very simple PLL-like device. We assume that the actual baud length is always the same and just adjust the position. The baud sync needs a bit more work since it has problems with some signals.

The deframer is very simple, implementing only a minimum of functions needed to cut the bitstream up into frames. The deframer looks for AX.25 FLAG sequences (01111110) to delimit frames. It also does bit-unstuffing and detection of framing-errors (too many 1's in a row) and frame aborts (15 or more 1's in a row). The frames are then output to "stdout". No further processing is done in this program.

Example captures

The capture file below is a text representation of 364 frames captured on 2009-05-24 using my AR8600Mk2 radio connected to my servers soundcard and tuned to 144.8MHz. The command-line used to create the file was:
arecord -r 48000 -c 1 -t raw -f U16_LE | ./aprs - --noempty --noshort --2200gain=4


The aprs demodulator is part if SigPlay and is found in the "apps" subdirectory.

  • SigPlay
  • aprs.c - The main program source code. It won't compile without SigPlay.
  • aprs_debug.py - A python script to aid in debugging the demodulator. Won't work without SigPlay.
  • aprs-20090524-1.txt - A capture-file containing 364 received frames.


This code is licensed under the GNU General Public License version 2.

Page: /radio/aprs.php Last Modified: 2009-05-27 07:47:26