Enforce CW decode processing only when mode is CW/CWR and decoder
is enabled, even within the receive loop, and remove CW path RMS
zero-gating to preserve weak tone decoding.
Co-authored-by: Codex <codex@openai.com>
Signed-off-by: Stan Grams <sjg@haxx.space>
Expand server-side CW tone command clamping to 100-10000 Hz to match
frontend controls and picker behavior.
Co-authored-by: Codex <codex@openai.com>
Signed-off-by: Stan Grams <sjg@haxx.space>
Apply an RMS gate to near-silent decoder input frames and zero them
before APRS/CW/FT8/WSPR processing to avoid false decodes from
unsquelched/no-signal noise.
Co-authored-by: Codex <codex@openai.com>
Signed-off-by: Stan Grams <sjg@haxx.space>
Gate the CW decoder task on cw_decode_enabled in both startup and state changes.
This restores the UI toggle and prevents decode activity when CW decode is off.
Co-authored-by: OpenAI Codex <codex@openai.com>
Signed-off-by: Stan Grams <sjg@haxx.space>
Make FT-817 mode setting fail for unsupported modes instead of silently mapping SDR-only modes onto FM.
Co-authored-by: Stan Grams <sjg@haxx.space>
Signed-off-by: Stan Grams <sjg@haxx.space>
Remove SDR-only decoder modes from the FT-817 supported mode list so they are not shown in that rig's mode picker.
Co-authored-by: Stan Grams <sjg@haxx.space>
Signed-off-by: Stan Grams <sjg@haxx.space>
Raise the AM audio AGC target and headroom again so the restored envelope demod path plays at a stronger level.
Co-authored-by: Stan Grams <sjg@haxx.space>
Signed-off-by: Stan Grams <sjg@haxx.space>
Retune the AM audio AGC target, timing, and headroom so the restored envelope demod path plays back at a stronger level.
Co-authored-by: Stan Grams <sjg@haxx.space>
Signed-off-by: Stan Grams <sjg@haxx.space>
Revert the recent AM coherent detector experiment and restore the original envelope detector path.
Co-authored-by: Stan Grams <sjg@haxx.space>
Signed-off-by: Stan Grams <sjg@haxx.space>
Remove half-wave clipping from the AM coherent detector output and slow the carrier-reference tracking to reduce audible distortion.
Co-authored-by: Stan Grams <sjg@haxx.space>
Signed-off-by: Stan Grams <sjg@haxx.space>
Replace the raw AM envelope detector with a limiter-derived coherent detector and update backend tests for the current channel DSP constructor.
Co-authored-by: Stan Grams <sjg@haxx.space>
Signed-off-by: Stan Grams <sjg@haxx.space>
Finish the pending MARINE frontend and decoder activation wiring, and lower the VDES detector power floors so weak signals are eligible for burst detection in the same power domain used by the IQ path.
Co-authored-by: OpenAI Codex <codex@openai.com>
Signed-off-by: Stanislaw Grams <stanislawgrams@gmail.com>
Keep the SoapySDR VDES and MARINE IQ path at a much higher channel sample rate instead of collapsing toward the normal audio rate, so the decoder receives usable complex baseband for the 76.8 ksps VDES signal.
Co-authored-by: OpenAI Codex <codex@openai.com>
Signed-off-by: Stanislaw Grams <stanislawgrams@gmail.com>
Add an FT8 live overlay bar, align APRS top controls with the other decoder tabs, advertise MARINE in the SoapySDR mode list, and make the VDES decoder emit raw unsynced diagnostic frames instead of dropping weak bursts outright.
Co-authored-by: OpenAI Codex <codex@openai.com>
Signed-off-by: Stanislaw Grams <stanislawgrams@gmail.com>
Keep weak VDES bursts visible by emitting unsynced diagnostic frames instead of dropping them, remove receiver badges from FT8 and WSPR history rows, and carry the current MARINE composite-mode scaffolding through the shared mode enums and backend mappings.
Co-authored-by: OpenAI Codex <codex@openai.com>
Signed-off-by: Stanislaw Grams <stanislawgrams@gmail.com>
Improve the VDES decoder with sync/rotation metadata and a first hard-decision rate-1/2 Viterbi stage after deinterleaving, then surface the extra lock state in the VDES frontend. Also fix the strict clippy findings in AIS, frontend bookmarks, and the server audio stack signature.
Co-authored-by: OpenAI Codex <codex@openai.com>
Signed-off-by: Stanislaw Grams <stanislawgrams@gmail.com>
Add a dedicated VDES plugin tab and live bar, stop reusing the AIS vessel UI, and serve a separate VDES frontend script. Rework the SDR backend so VDES receives a single 100 kHz IQ tap, then replace the fake AIS-clone decoder path with an early M.2092-1 oriented complex-baseband scaffold using burst detection, coarse pi/4-QPSK slicing, and TER-MCS-1.100 frame heuristics.
Co-authored-by: OpenAI Codex <codex@openai.com>
Signed-off-by: Stanislaw Grams <stanislawgrams@gmail.com>
Add a new trx-vdes decoder path alongside AIS, wire VDES through the server/frontend decode pipeline, and fix the web map so AIS vessel symbols load correctly and the TRX receiver marker appears when location data arrives.
Co-authored-by: OpenAI Codex <codex@openai.com>
Signed-off-by: Stan Grams <sjg@haxx.space>
Add dual-channel AIS decode support across the SoapySDR backend, server decode pipeline, and frontend plugins, including the new AIS tab, live bar, and map filtering.
Co-authored-by: OpenAI Codex <codex@openai.com>
Signed-off-by: Stan Grams <sjg@haxx.space>
Attach replay timestamps to APRS history and filter the APRS live bar
so it only shows the last hour of valid entries.
Co-authored-by: OpenAI Codex <codex@openai.com>
Signed-off-by: Stan Grams <sjg@haxx.space>
Guard both the live broadcast (decode_tx.send) and the history store
(record_aprs_packet) so CRC-failed packets are never forwarded to
connected clients or replayed on reconnect. The decode logger still
receives all frames for debugging.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Signed-off-by: Stan Grams <sjg@haxx.space>
Move the spectrum FFT snapshot logic into a dedicated dsp module so dsp.rs stays focused on pipeline orchestration.
Co-authored-by: OpenAI Codex <codex@openai.com>
Signed-off-by: Stan Grams <sjg@haxx.space>
Split the SoapySDR backend demod and dsp code into focused modules while keeping behavior stable, and include the resulting formatting updates.
Co-authored-by: OpenAI Codex <codex@openai.com>
Signed-off-by: Stan Grams <sjg@haxx.space>
Wire the StereoDenoise processor through the full stack:
- Add SetWfmDenoise command variant and RigCat trait method (trx-core)
- Add wfm_denoise field to RigFilterState with default true
- Add protocol command and bidirectional mapping (trx-protocol)
- Add rig_task command handler (trx-server)
- Implement set_wfm_denoise in SoapySdrRig backend
- Add /set_wfm_denoise API endpoint (trx-frontend-http)
- Add denoise checkbox in WFM controls with SSE sync and
localStorage persistence
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Signed-off-by: Stan Grams <sjg@haxx.space>
Clean up the workspace so cargo clippy passes across all targets and features.
Co-authored-by: OpenAI Codex <codex@openai.com>
Signed-off-by: Stan Grams <sjg@haxx.space>
Add frequency-selective attenuation of the L-R difference signal to
reduce stereo hiss on weak FM broadcasts. Uses the quadrature component
(diff_q) as a noise reference per US7292694B2 (Wildhagen/Sony).
The algorithm splits sum, diff_i, and diff_q into 6 overlapping subbands,
estimates per-band SNR from smoothed |diff_q|² noise power, and applies
an energy-weighted broadband gain to the original diff signal. This
preserves clean stereo content (<4 dB loss) while attenuating noise-only
diff channels (>6 dB reduction).
Enabled by default; toggled via set_denoise_enabled() / set_wfm_denoise().
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Signed-off-by: Stan Grams <sjg@haxx.space>
Increase the stereo matrix gain to 1.2 and trim the WFM output gain slightly to rebalance the decoded audio path.
Co-authored-by: OpenAI Codex <codex@openai.com>
Signed-off-by: Stan Grams <sjg@haxx.space>
Output gain clamp catches any peaks from full-deviation signals.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Signed-off-by: Stan Grams <sjg@haxx.space>
More stereo headroom for broadcast audio. With WFM_OUTPUT_GAIN at 0.35
the effective output is 0.28 peak, well within clipping margin.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Signed-off-by: Stan Grams <sjg@haxx.space>
Replace both IQ AGC and audio AGC in the WFM path with a fixed output
gain of 0.35. AGC pumping on broadcast audio degrades stereo separation
and introduces audible artifacts. The IQ hard limiter already normalizes
input magnitude, and the WFM decoder's internal deemphasis + matrix gain
provides consistent output levels.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Signed-off-by: Stan Grams <sjg@haxx.space>
Set opus encoder complexity from default (9-10) to 5 for both cpal and
SDR audio paths, significantly reducing encoding CPU usage with minimal
quality impact at these bitrates. Raise default bitrate from 192 kbps to
256 kbps for higher fidelity stereo audio.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Signed-off-by: Stan Grams <sjg@haxx.space>
Replace per-sample sin_cos(pilot_phase) with a quadrature NCO that
advances via complex rotation (4 muls + 2 adds vs transcendental).
Renormalize every 1024 samples to prevent magnitude drift.
Decimate stereo detection logic (pilot coherence, lock, drive,
hysteresis) to run every 16 composite samples instead of every sample.
Accumulate pilot_mag and pilot_abs over the window and process averaged
values, scaling the IIR coefficients accordingly.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Signed-off-by: Stan Grams <sjg@haxx.space>