DiscordDMRLink

DMR to Discord voice bridge - monitors DMR networks and streams audio to Discord voice channels

DiscordDMRLink - DMR to Discord Voice Bridge

DiscordDMRLink is a DSD-based monitor that connects to a DMR network server and pipes decoded audio directly into a Discord voice channel. This allows real-time monitoring of DMR talkgroups through Discord.

Overview

This application:

  • Connects to a DMR network server using the Homebrew/MMDVM protocol
  • Authenticates with the server
  • Receives DMR frames from the network
  • Decodes AMBE+2 (3600x2450) voice frames using mbelib-neo
  • Resamples audio from 8kHz to 48kHz
  • Encodes to Opus and streams to Discord voice channel

Important Notes

⚠️ This tool MUST be used with a static talkgroup only.

Tested with PrideDMR.net - confirmed working ❓ May work with other DMR networks - untested but should work with any network using the Homebrew/MMDVM protocol

Requirements

All dependencies are now vendored in this repository. You only need:

  • Go 1.24 or later with CGO enabled
  • A C compiler (gcc)
  • A Discord bot with voice permissions
  • Access to a DMR network with a static talkgroup assignment

Building

# Build DiscordDMRLink (all dependencies are vendored)
cd ~/Compiled/DiscordDMRLink
go build -o discorddmrlink

The build process will use the vendored mbelib-neo library and opus source included in the vendor/ directory.

Configuration

Edit the config.json file with your credentials:

{
    "server_address": "pridedmr.net",
    "server_port": 62031,
    "password": "YOUR_DMR_PASSWORD_HERE",
    "client_id": 1234567890,
    "discord_token": "YOUR_DISCORD_BOT_TOKEN_HERE",
    "discord_guild_id": "YOUR_DISCORD_GUILD_ID_HERE",
    "discord_channel_id": "YOUR_DISCORD_CHANNEL_ID_HERE"
}
Field Description
server_address IP or hostname of DMR network server (e.g., pridedmr.net)
server_port UDP port of the server (default: 62031)
password Your DMR hotspot/repeater authentication password
client_id Your DMR ID for Homebrew protocol
discord_token Discord bot token from Discord Developer Portal
discord_guild_id Discord server (guild) ID where the bot will operate
discord_channel_id Voice channel ID where audio will be streamed

Getting Discord Bot Token and IDs

  1. Create a Discord Bot:

  2. Get Permission and Invite Bot:

    • Go to OAuth2 → URL Generator
    • Select scopes: bot
    • Select bot permissions: Connect, Speak, Use Voice Activity
    • Use the generated URL to invite the bot to your server
  3. Get Discord IDs:

    • Enable Developer Mode in Discord (User Settings → App Settings → Advanced → Developer Mode)
    • Right-click your server name → "Copy Server ID" (this is discord_guild_id)
    • Right-click the voice channel → "Copy Channel ID" (this is discord_channel_id)

DMR Network Configuration

For PrideDMR.net users:

  • Server address: pridedmr.net
  • Server port: 62031 (default)
  • Use your hotspot/repeater password
  • Use your DMR ID as the client_id
  • Ensure your hotspot/repeater is configured with a static talkgroup

For other DMR networks:

  • Contact your network administrator for connection details
  • Ensure you have a static talkgroup assignment
  • You may need different port numbers depending on the network

Usage

./discorddmrlink

The bot will:

  1. Connect to Discord and join the configured voice channel
  2. Connect to the DMR network server
  3. Authenticate using your credentials
  4. Stream any received DMR audio to the Discord channel in real-time

Press Ctrl+C to gracefully stop the application.

How It Works

DMR Radio → DMR Network → DiscordDMRLink → Discord Voice Channel
                              ↓
                         mbelib-neo (AMBE+2 decode)
                              ↓
                         8kHz → 48kHz resample
                              ↓
                         Opus encode → Discord
  1. Your DMR hotspot/repeater sends traffic to the network server on your static talkgroup
  2. DiscordDMRLink receives the DMR frames via UDP
  3. AMBE+2 voice frames are decoded using mbelib-neo
  4. Audio is resampled from 8kHz (DMR) to 48kHz (Discord)
  5. Audio is encoded to Opus format
  6. Opus packets are streamed to Discord voice channel

Troubleshooting

Connection fails:

  • Verify your DMR credentials are correct
  • Check that the server address and port are correct
  • Ensure your firewall allows UDP traffic

No audio in Discord:

  • Verify the bot has "Connect" and "Speak" permissions in the voice channel
  • Check that your static talkgroup is active and receiving traffic
  • Look for error messages in the console output

Discord bot won't join channel:

  • Verify the guild_id and channel_id are correct
  • Ensure the bot was invited with proper permissions
  • Check that the bot token is valid

Technical Details

  • DMR Protocol: Homebrew/MMDVM
  • Voice Codec: AMBE+2 (3600x2450)
  • Audio Sample Rate: 8kHz (DMR) → 48kHz (Discord)
  • Discord Codec: Opus
  • Frame Size: 960 samples (20ms at 48kHz)

Related Projects