Skip to content

SubniC/ais-sdr-receiver

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

2 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

AIS-SDR Receiver

Python-based AIS (Automatic Identification System) receiver using a Software Defined Radio.

AIS-SDR captures the maritime AIS radio signal with an SDR, demodulates and decodes the messages broadcast by nearby vessels, and exposes the decoded data through a REST API.

Overview

The receiver implements the full receive chain in software:

SDR hardware → IQ streaming → GMSK/FM demodulation → clock recovery →
HDLC framing + CRC → AIS decoding (pyais) → REST API

Both AIS channels (A at 161.975 MHz and B at 162.025 MHz) can be decoded simultaneously from a single wideband SDR.

Hardware

Device SoapySDR Driver Notes
NESDR Smart V5 / generic RTL-SDR rtlsdr 250 kHz sample rate, single channel
HackRF One hackrf 2 MHz minimum sample rate, supports dual-channel

Switching hardware requires only a change to config.yaml (sdr.driver); no code changes. The signal pipeline automatically decimates higher sample rates (e.g. HackRF's 2 MHz) down to the ~250 kHz used internally for clock recovery.

This project performs reception only. It does not transmit.

Requirements

  • Python 3.11+
  • A working SoapySDR installation plus the driver module for your hardware
  • Python dependencies listed in requirements.txt

Installation

SoapySDR and its device modules are native libraries and are easiest to install via conda-forge:

# RTL-SDR
conda install -c conda-forge soapysdr soapysdr-module-rtlsdr

# HackRF One
conda install -c conda-forge soapysdr soapysdr-module-hackrf

Then install the Python package and its dependencies:

pip install -e ".[dev]"

Configuration

All runtime parameters live in config.yaml at the project root.

RTL-SDR (single channel)

sdr:
  driver: "rtlsdr"
  sample_rate: 250000       # 250 kHz
  center_freq: 161975000    # Channel A
  gain: 30.0
  buffer_size: 16384
  clock_recovery: "multiphase"
  dual_channel: false

HackRF One (dual channel)

sdr:
  driver: "hackrf"
  sample_rate: 2000000      # 2 MHz minimum; decimated to 250 kHz internally
  center_freq: 162000000    # midpoint between Channel A and B
  buffer_size: 131072       # ~65 ms per chunk at 2 MHz
  invert_polarity: true     # required for HackRF hardware polarity
  hackrf_lna_gain: 40       # LNA: 0-40 dB (8 dB steps)
  hackrf_vga_gain: 20       # VGA: 0-62 dB (2 dB steps); keep <=20 to avoid saturation
  hackrf_amp_enable: false
  clock_recovery: "multiphase"
  dual_channel: true

clock_recovery options:

  • "multiphase" — open-loop, scans 8 clock phases in parallel, no convergence time (recommended; survives the silence gaps between AIS bursts)
  • "mueller_muller" — feedback timing-error detector that tracks timing drift within a burst; loses lock during long inter-burst silence, so it is not recommended for the intermittent AIS Class B signal

Running

python src/main.py
# or with a custom config:
python src/main.py --config /path/to/config.yaml

The REST API is then available at http://localhost:8000, with interactive documentation at http://localhost:8000/docs.

API Endpoints

Method Endpoint Description
GET /status System status
GET /metrics Runtime metrics
POST /receiver/start Start AIS reception
POST /receiver/stop Stop AIS reception
GET /receiver/state Receiver state
GET /ais/messages Decoded AIS messages (optional limit, mmsi filters)
GET /ais/messages/{mmsi} Messages for a specific MMSI
GET /ais/export Download all decoded messages as a JSON attachment

AIS Message Types Decoded

Type Description
1 Position Report Class A
2 Position Report Class A (Assigned)
3 Position Report Class A (Special)
4 Base Station Report
5 Static and Voyage Related Data
9 Standard SAR Aircraft Position Report
14 Safety Related Broadcast Message
18 Standard Class B CS Position Report
21 Aid-to-Navigation Report
24 Class B CS Static Data Report

Project Structure

src/
  ais_sdr/
    core/               # Config, logging, models, exceptions
    sdr/                # SDR device abstraction (SoapySDR)
    signal_processing/  # GMSK demodulation, filtering, clock recovery
    ais/                # HDLC framing, CRC, AIS decoding
    api/                # FastAPI server and routes
  main.py               # Entry point
tests/
  unit/                 # Unit tests (no hardware required)
  integration/
config.yaml             # Runtime configuration
docs/
  ARCHITECTURE.md       # System architecture
  SIGNAL-PIPELINE.md    # Receive-chain signal theory

Running Tests

The test suite runs entirely without hardware (all SDR access is mocked):

pytest

How It Works

For a detailed walkthrough of the receive chain — FM demodulation, DC correction, multi-phase clock recovery, HDLC framing, CRC verification, and AIS payload decoding — see docs/SIGNAL-PIPELINE.md. The overall module layout and design decisions are documented in docs/ARCHITECTURE.md.

License

MIT © 2026 mdps

Disclaimer: experimental, receive-only project provided as is, without warranty; not for navigation or safety-of-life use — operate your SDR within your local radio regulations.

Un proyecto de mdps · 2026 · desarrollado en Murcia.

About

Software-defined AIS receiver: SDR capture -> GMSK/FM demod -> clock recovery -> HDLC/CRC -> AIS decode, exposed over a REST API. Dual-channel from one wideband SDR.

Topics

Resources

License

Stars

0 stars

Watchers

0 watching

Forks

Packages

 
 
 

Contributors

Languages