# gr-rylr998 GNU Radio Out-of-Tree Module for RYLR998 LoRa Modems ## Overview gr-rylr998 provides complete TX/RX blocks for RYLR998 LoRa modems, implementing the full PHY layer compatible with the Semtech LoRa standard. ### Key Features - **Complete TX/RX chains** for LoRa modulation/demodulation - **NETWORKID support** - Extracts and encodes RYLR998 NETWORKID from sync word - **gr-lora_sdr compatible** - Uses the same signal processing chain - **Python-only** - No C++ compilation required (GNU Radio 3.10+) - **Well-documented** - Educational comments throughout ## Installation ### From Source (Development) ```bash cd gr-rylr998 pip install -e . ``` ### With CMake (GNU Radio Integration) ```bash mkdir build && cd build cmake .. make sudo make install ``` ## Quick Start ### Python API ```python from rylr998 import PHYEncode, PHYDecode, FrameGen, FrameSync import numpy as np # === Transmit === encoder = PHYEncode(sf=9, cr=1, has_crc=True) frame_gen = FrameGen(sf=9, networkid=18) payload = b"Hello, LoRa!" bins = encoder.encode(payload) iq = frame_gen.generate_frame(bins) # === Receive (loopback) === sync = FrameSync(sf=9) result = sync.sync_from_samples(iq) decoder = PHYDecode(sf=9) # For loopback: use_grlora_gray=False, soft_decoding=True # For real SDR captures: use defaults (True, False) frame = decoder.decode( result.data_symbols, cfo_bin=int(result.cfo_bin), use_grlora_gray=False, soft_decoding=True ) print(f"NETWORKID: {result.networkid}") print(f"Payload: {frame.payload}") print(f"CRC OK: {frame.crc_ok}") ``` ### Command Line ```bash # Run loopback test python examples/loopback_test.py # Test all SF/CR combinations python examples/loopback_test.py --all # Generate TX frame python examples/bladerf_tx.py --payload "Test" --output frame.raw # Decode from file python examples/bladerf_rx.py --input capture.raw --verbose ``` ## Block Inventory | Block | Type | Description | |-------|------|-------------| | `css_demod` | Demod | FFT-based CSS demodulator | | `css_mod` | Mod | Chirp generator | | `frame_sync` | Sync | Preamble + NETWORKID detection | | `frame_gen` | Framing | Preamble + sync word + SFD | | `phy_decode` | PHY | Gray → deinterleave → Hamming → dewhiten | | `phy_encode` | PHY | Whiten → Hamming → interleave → Gray | | `rylr998_rx` | Hier | Complete RX chain | | `rylr998_tx` | Hier | Complete TX chain | ## NETWORKID Mapping The RYLR998 NETWORKID (0-255) maps directly to the LoRa sync word: ```python sync_bin_1 = (NETWORKID >> 4) * 8 # High nibble × 8 sync_bin_2 = (NETWORKID & 0x0F) * 8 # Low nibble × 8 ``` | NETWORKID | Sync Bins | Use | |-----------|-----------|-----| | 18 (0x12) | [8, 16] | Private networks | | 52 (0x34) | [24, 32] | LoRaWAN public | ## Directory Structure ``` gr-rylr998/ ├── python/rylr998/ # Python module │ ├── __init__.py │ ├── networkid.py # NETWORKID utilities │ ├── css_demod.py # CSS demodulator │ ├── css_mod.py # CSS modulator │ ├── phy_decode.py # PHY RX chain │ ├── phy_encode.py # PHY TX chain │ ├── frame_sync.py # Frame synchronization │ └── frame_gen.py # Frame generation ├── grc/ # GRC block definitions (.yml) ├── examples/ # Example scripts and flowgraphs │ ├── loopback_test.py │ ├── bladerf_rx.py │ ├── bladerf_tx.py │ ├── rylr998_loopback.grc │ ├── rylr998_bladerf_rx.grc │ └── rylr998_bladerf_tx.grc ├── docs/ # Documentation │ ├── BLOCK_REFERENCE.md │ ├── NETWORKID_MAPPING.md │ └── GRC_FLOWGRAPHS.md ├── CMakeLists.txt # CMake build └── pyproject.toml # Python packaging ``` ## Documentation | Document | Description | |----------|-------------| | [BLOCK_REFERENCE.md](docs/BLOCK_REFERENCE.md) | All blocks, parameters, troubleshooting | | [NETWORKID_MAPPING.md](docs/NETWORKID_MAPPING.md) | RYLR998 NETWORKID ↔ sync word mapping | | [GRC_FLOWGRAPHS.md](docs/GRC_FLOWGRAPHS.md) | GNU Radio Companion usage guide | ## Dependencies - Python 3.10+ - NumPy - GNU Radio 3.10+ (optional, for GRC integration) ## References - [LoRa Patent EP2763321](https://patents.google.com/patent/EP2763321A1) - [gr-lora_sdr](https://github.com/tapparelj/gr-lora_sdr) - [Matt Knight, "Decoding LoRa" (DEF CON 24)](https://media.defcon.org/DEF%20CON%2024/DEF%20CON%2024%20presentations/) ## License GPL-3.0-or-later