From 53e0db48d6f0d420c6925f5de0f6e92db078b56d Mon Sep 17 00:00:00 2001 From: Manolis Surligas Date: Sat, 4 Nov 2017 12:19:07 +0200 Subject: [PATCH 1/2] Add AFSK1200 decoder * AFSK1200 decoder with AX.25 frame support * Fix issue with the AX.25 decoder when the frame has only one AX.25 SYNC flag * Fix clear text debug output to print each one of the characters and not the string, so that the payload can be partially be printed even if it contains non-printable characters * Add AFSK1200 decoder example that can decode frames from an .ogg file retrieved by the satnogs-network --- apps/CMakeLists.txt | 1 + apps/flowgraphs/afsk1200_ax25.grc | 3688 ++++++++++++++++++++++ apps/flowgraphs/satnogs_afsk1200_ax25.py | 401 +++ examples/afsk1200_example.grc | 1278 ++++++++ lib/ax25_decoder_bm_impl.cc | 22 +- lib/multi_format_msg_sink_impl.cc | 5 +- 6 files changed, 5392 insertions(+), 3 deletions(-) create mode 100644 apps/flowgraphs/afsk1200_ax25.grc create mode 100755 apps/flowgraphs/satnogs_afsk1200_ax25.py create mode 100644 examples/afsk1200_example.grc diff --git a/apps/CMakeLists.txt b/apps/CMakeLists.txt index 9464297..3de9f53 100644 --- a/apps/CMakeLists.txt +++ b/apps/CMakeLists.txt @@ -32,5 +32,6 @@ GR_PYTHON_INSTALL( flowgraphs/satnogs_apt_demod.py flowgraphs/satnogs_fsk9600_ax25.py flowgraphs/satnogs_fsk9600_g3ruh_ax25.py + flowgraphs/satnogs_afsk1200_ax25.py DESTINATION bin ) diff --git a/apps/flowgraphs/afsk1200_ax25.grc b/apps/flowgraphs/afsk1200_ax25.grc new file mode 100644 index 0000000..9307e63 --- /dev/null +++ b/apps/flowgraphs/afsk1200_ax25.grc @@ -0,0 +1,3688 @@ + + + + Thu May 5 00:22:45 2016 + + options + + author + Manolis Surligas (surligas@gmail.com), Vardakis Giorgos (vardakis.grg@gmail.com) + + + window_size + 3000, 3000 + + + category + Custom + + + comment + + + + description + AFSK1200 AX.25 decoder + + + _enabled + True + + + _coordinate + (8, 8) + + + _rotation + 0 + + + generate_options + no_gui + + + hier_block_src_path + .: + + + id + satnogs_afsk1200_ax25 + + + max_nouts + 0 + + + qt_qss_theme + + + + realtime_scheduling + + + + run_command + {python} -u {filename} + + + run_options + run + + + run + True + + + thread_safe_setters + + + + title + AFSK1200 AX.25 decoder + + + + variable + + comment + Decimation factor +for the RX after the +SDR received samples + + + _enabled + True + + + _coordinate + (590, 761) + + + _rotation + 0 + + + id + audio_gain + + + value + satnogs.fm_demod_settings[rx_sdr_device]['audio_gain'] + + + + variable + + comment + + + + _enabled + True + + + _coordinate + (462, 546) + + + _rotation + 0 + + + id + audio_samp_rate + + + value + 48000 + + + + variable + + comment + + + + _enabled + 1 + + + _coordinate + (111, 769) + + + _rotation + 0 + + + id + baud_rate + + + value + 9600 + + + + variable + + comment + + + + _enabled + 1 + + + _coordinate + (31, 769) + + + _rotation + 0 + + + id + deviation + + + value + 5000 + + + + variable + + comment + + + + _enabled + True + + + _coordinate + (750, 706) + + + _rotation + 0 + + + id + filter_rate + + + value + 250000 + + + + variable + + comment + + + + _enabled + True + + + _coordinate + (207, 769) + + + _rotation + 0 + + + id + modulation_index + + + value + deviation / (baud_rate / 2.0) + + + + variable + + comment + SDR device +TX sampling rate + + + _enabled + True + + + _coordinate + (351, 546) + + + _rotation + 0 + + + id + samp_rate_rx + + + value + satnogs.hw_rx_settings[rx_sdr_device]['samp_rate'] + + + + variable_low_pass_filter_taps + + beta + 6.76 + + + comment + + + + cutoff_freq + 100e3 + + + _enabled + 1 + + + _coordinate + (31, 542) + + + _rotation + 0 + + + gain + 12.0 + + + id + taps + + + samp_rate + samp_rate_rx + + + width + 60000 + + + win + firdes.WIN_HAMMING + + + + variable + + comment + + + + _enabled + True + + + _coordinate + (590, 698) + + + _rotation + 0 + + + id + xlate_filter_taps + + + value + firdes.low_pass(1, samp_rate_rx, 125000, 25000, firdes.WIN_HAMMING, 6.76) + + + + analog_quadrature_demod_cf + + alias + + + + comment + + + + affinity + + + + _enabled + True + + + _coordinate + (1460, 426) + + + _rotation + 0 + + + gain + 1.0 + + + id + analog_quadrature_demod_cf_0 + + + maxoutbuf + 0 + + + minoutbuf + 0 + + + + analog_quadrature_demod_cf + + alias + + + + comment + + + + affinity + + + + _enabled + True + + + _coordinate + (1046, 339) + + + _rotation + 180 + + + gain + ((audio_samp_rate) / baud_rate)/(math.pi*modulation_index) + + + id + analog_quadrature_demod_cf_0_0 + + + maxoutbuf + 0 + + + minoutbuf + 0 + + + + parameter + + alias + + + + comment + + + + _enabled + True + + + _coordinate + (263, 865) + + + _rotation + 0 + + + id + antenna + + + label + + + + short_id + + + + type + string + + + value + satnogs.not_set_antenna + + + + parameter + + alias + + + + comment + + + + _enabled + True + + + _coordinate + (175, 865) + + + _rotation + 0 + + + id + bb_gain + + + label + + + + short_id + + + + type + eng_float + + + value + satnogs.not_set_rx_bb_gain + + + + rational_resampler_xxx + + alias + + + + comment + + + + affinity + + + + decim + int(samp_rate_rx / (int(samp_rate_rx/filter_rate))) + + + _enabled + True + + + fbw + 0 + + + _coordinate + (1272, 268) + + + _rotation + 0 + + + id + blks2_rational_resampler_xxx_1 + + + interp + 48000 + + + maxoutbuf + 0 + + + minoutbuf + 0 + + + taps + [] + + + type + ccc + + + + blocks_float_to_complex + + alias + + + + comment + + + + affinity + + + + _enabled + True + + + _coordinate + (805, 414) + + + _rotation + 0 + + + id + blocks_float_to_complex_0 + + + maxoutbuf + 0 + + + minoutbuf + 0 + + + vlen + 1 + + + + blocks_rotator_cc + + alias + + + + comment + + + + affinity + + + + _enabled + True + + + _coordinate + (997, 426) + + + _rotation + 0 + + + id + blocks_rotator_cc_0 + + + maxoutbuf + 0 + + + minoutbuf + 0 + + + phase_inc + -2.0 * math.pi * ((mark_frequency + space_frequency) / 2.0) / (audio_samp_rate / 4.0) + + + + dc_blocker_xx + + alias + + + + comment + + + + affinity + + + + _enabled + True + + + _coordinate + (414, 402) + + + _rotation + 0 + + + id + dc_blocker_xx_0 + + + length + 1024 + + + long_form + True + + + maxoutbuf + 0 + + + minoutbuf + 0 + + + type + ff + + + + parameter + + alias + + + + comment + + + + _enabled + True + + + _coordinate + (175, 586) + + + _rotation + 0 + + + id + decoded_data_file_path + + + label + + + + short_id + + + + type + string + + + value + /tmp/.satnogs/data/data + + + + parameter + + alias + + + + comment + + + + _enabled + True + + + _coordinate + (470, 690) + + + _rotation + 0 + + + id + dev_args + + + label + + + + short_id + + + + type + string + + + value + satnogs.not_set_dev_args + + + + digital_binary_slicer_fb + + alias + + + + comment + + + + affinity + + + + _enabled + 1 + + + _coordinate + (1914, 430) + + + _rotation + 0 + + + id + digital_binary_slicer_fb_0 + + + maxoutbuf + 0 + + + minoutbuf + 0 + + + + digital_clock_recovery_mm_xx + + alias + + + + comment + + + + affinity + + + + _enabled + 1 + + + _coordinate + (1699, 398) + + + _rotation + 0 + + + gain_mu + 0.175 + + + gain_omega + 0.25*0.175*0.175 + + + id + digital_clock_recovery_mm_xx_0 + + + maxoutbuf + 0 + + + minoutbuf + 0 + + + mu + 0.5 + + + omega_relative_limit + 0.005 + + + omega + 48e3/9600 + + + type + float + + + + digital_costas_loop_cc + + alias + + + + comment + + + + affinity + + + + _enabled + True + + + _coordinate + (1022, 255) + + + _rotation + 0 + + + id + digital_costas_loop_cc_0 + + + w + 2.0 * math.pi / 100.0 + + + maxoutbuf + 0 + + + minoutbuf + 0 + + + order + 2 + + + use_snr + False + + + + parameter + + alias + + + + comment + + + + _enabled + True + + + _coordinate + (31, 690) + + + _rotation + 0 + + + id + doppler_correction_per_sec + + + label + + + + short_id + + + + type + intx + + + value + 1000 + + + + parameter + + alias + + + + comment + + + + _enabled + True + + + _coordinate + (343, 865) + + + _rotation + 0 + + + id + enable_iq_dump + + + label + + + + short_id + + + + type + intx + + + value + 0 + + + + parameter + + alias + + + + comment + + + + _enabled + True + + + _coordinate + (167, 945) + + + _rotation + 180 + + + id + file_path + + + label + + + + short_id + + + + type + string + + + value + test.wav + + + + freq_xlating_fir_filter_xxx + + alias + + + + center_freq + lo_offset + + + comment + + + + affinity + + + + decim + int(samp_rate_rx/filter_rate) + + + _enabled + 1 + + + _coordinate + (680, 268) + + + _rotation + 0 + + + id + freq_xlating_fir_filter_xxx_0 + + + maxoutbuf + 0 + + + minoutbuf + 0 + + + samp_rate + samp_rate_rx + + + taps + xlate_filter_taps + + + type + ccc + + + + parameter + + alias + + + + comment + + + + _enabled + True + + + _coordinate + (95, 865) + + + _rotation + 0 + + + id + if_gain + + + label + + + + short_id + + + + type + eng_float + + + value + satnogs.not_set_rx_if_gain + + + + parameter + + alias + + + + comment + + + + _enabled + True + + + _coordinate + (470, 865) + + + _rotation + 0 + + + id + iq_file_path + + + label + + + + short_id + + + + type + string + + + value + /tmp/iq.dat + + + + parameter + + alias + + + + comment + To avoid the SDR carrier at the DC +we shift the LO a little further + + + _enabled + True + + + _coordinate + (263, 945) + + + _rotation + 0 + + + id + lo_offset + + + label + + + + short_id + + + + type + eng_float + + + value + 100e3 + + + + low_pass_filter + + beta + 6.76 + + + alias + + + + comment + + + + affinity + + + + cutoff_freq + mark_frequency + 1000.0 + + + decim + 4 + + + _enabled + True + + + type + fir_filter_fff + + + _coordinate + (622, 367) + + + _rotation + 0 + + + gain + 1 + + + id + low_pass_filter_0 + + + interp + 1 + + + maxoutbuf + 0 + + + minoutbuf + 0 + + + samp_rate + audio_samp_rate + + + width + audio_samp_rate * 0.1 + + + win + firdes.WIN_HAMMING + + + + low_pass_filter + + beta + 6.76 + + + alias + + + + comment + + + + affinity + + + + cutoff_freq + (mark_frequency - space_frequency)/2.0 + 200.0 + + + decim + 2 + + + _enabled + True + + + type + fir_filter_ccf + + + _coordinate + (1252, 382) + + + _rotation + 0 + + + gain + 1 + + + id + low_pass_filter_1 + + + interp + 1 + + + maxoutbuf + 0 + + + minoutbuf + 0 + + + samp_rate + audio_samp_rate/4 + + + width + 200 + + + win + firdes.WIN_HAMMING + + + + parameter + + alias + + + + comment + + + + _enabled + True + + + _coordinate + (23, 1113) + + + _rotation + 0 + + + id + mark_frequency + + + label + + + + short_id + + + + type + eng_float + + + value + 2200.0 + + + + osmosdr_source + + alias + + + + ant0 + satnogs.handle_rx_antenna(rx_sdr_device, antenna) + + + bb_gain0 + satnogs.handle_rx_bb_gain(rx_sdr_device, bb_gain) + + + bw0 + samp_rate_rx + + + dc_offset_mode0 + 2 + + + corr0 + ppm + + + freq0 + rx_freq - lo_offset + + + gain_mode0 + False + + + if_gain0 + satnogs.handle_rx_if_gain(rx_sdr_device, if_gain) + + + iq_balance_mode0 + 0 + + + gain0 + satnogs.handle_rx_rf_gain(rx_sdr_device, rf_gain) + + + ant10 + + + + bb_gain10 + 20 + + + bw10 + 0 + + + dc_offset_mode10 + 0 + + + corr10 + 0 + + + freq10 + 100e6 + + + gain_mode10 + False + + + if_gain10 + 20 + + + iq_balance_mode10 + 0 + + + gain10 + 10 + + + ant11 + + + + bb_gain11 + 20 + + + bw11 + 0 + + + dc_offset_mode11 + 0 + + + corr11 + 0 + + + freq11 + 100e6 + + + gain_mode11 + False + + + if_gain11 + 20 + + + iq_balance_mode11 + 0 + + + gain11 + 10 + + + ant12 + + + + bb_gain12 + 20 + + + bw12 + 0 + + + dc_offset_mode12 + 0 + + + corr12 + 0 + + + freq12 + 100e6 + + + gain_mode12 + False + + + if_gain12 + 20 + + + iq_balance_mode12 + 0 + + + gain12 + 10 + + + ant13 + + + + bb_gain13 + 20 + + + bw13 + 0 + + + dc_offset_mode13 + 0 + + + corr13 + 0 + + + freq13 + 100e6 + + + gain_mode13 + False + + + if_gain13 + 20 + + + iq_balance_mode13 + 0 + + + gain13 + 10 + + + ant14 + + + + bb_gain14 + 20 + + + bw14 + 0 + + + dc_offset_mode14 + 0 + + + corr14 + 0 + + + freq14 + 100e6 + + + gain_mode14 + False + + + if_gain14 + 20 + + + iq_balance_mode14 + 0 + + + gain14 + 10 + + + ant15 + + + + bb_gain15 + 20 + + + bw15 + 0 + + + dc_offset_mode15 + 0 + + + corr15 + 0 + + + freq15 + 100e6 + + + gain_mode15 + False + + + if_gain15 + 20 + + + iq_balance_mode15 + 0 + + + gain15 + 10 + + + ant16 + + + + bb_gain16 + 20 + + + bw16 + 0 + + + dc_offset_mode16 + 0 + + + corr16 + 0 + + + freq16 + 100e6 + + + gain_mode16 + False + + + if_gain16 + 20 + + + iq_balance_mode16 + 0 + + + gain16 + 10 + + + ant17 + + + + bb_gain17 + 20 + + + bw17 + 0 + + + dc_offset_mode17 + 0 + + + corr17 + 0 + + + freq17 + 100e6 + + + gain_mode17 + False + + + if_gain17 + 20 + + + iq_balance_mode17 + 0 + + + gain17 + 10 + + + ant18 + + + + bb_gain18 + 20 + + + bw18 + 0 + + + dc_offset_mode18 + 0 + + + corr18 + 0 + + + freq18 + 100e6 + + + gain_mode18 + False + + + if_gain18 + 20 + + + iq_balance_mode18 + 0 + + + gain18 + 10 + + + ant19 + + + + bb_gain19 + 20 + + + bw19 + 0 + + + dc_offset_mode19 + 0 + + + corr19 + 0 + + + freq19 + 100e6 + + + gain_mode19 + False + + + if_gain19 + 20 + + + iq_balance_mode19 + 0 + + + gain19 + 10 + + + ant1 + + + + bb_gain1 + 20 + + + bw1 + 0 + + + dc_offset_mode1 + 0 + + + corr1 + 0 + + + freq1 + 100e6 + + + gain_mode1 + False + + + if_gain1 + 20 + + + iq_balance_mode1 + 0 + + + gain1 + 10 + + + ant20 + + + + bb_gain20 + 20 + + + bw20 + 0 + + + dc_offset_mode20 + 0 + + + corr20 + 0 + + + freq20 + 100e6 + + + gain_mode20 + False + + + if_gain20 + 20 + + + iq_balance_mode20 + 0 + + + gain20 + 10 + + + ant21 + + + + bb_gain21 + 20 + + + bw21 + 0 + + + dc_offset_mode21 + 0 + + + corr21 + 0 + + + freq21 + 100e6 + + + gain_mode21 + False + + + if_gain21 + 20 + + + iq_balance_mode21 + 0 + + + gain21 + 10 + + + ant22 + + + + bb_gain22 + 20 + + + bw22 + 0 + + + dc_offset_mode22 + 0 + + + corr22 + 0 + + + freq22 + 100e6 + + + gain_mode22 + False + + + if_gain22 + 20 + + + iq_balance_mode22 + 0 + + + gain22 + 10 + + + ant23 + + + + bb_gain23 + 20 + + + bw23 + 0 + + + dc_offset_mode23 + 0 + + + corr23 + 0 + + + freq23 + 100e6 + + + gain_mode23 + False + + + if_gain23 + 20 + + + iq_balance_mode23 + 0 + + + gain23 + 10 + + + ant24 + + + + bb_gain24 + 20 + + + bw24 + 0 + + + dc_offset_mode24 + 0 + + + corr24 + 0 + + + freq24 + 100e6 + + + gain_mode24 + False + + + if_gain24 + 20 + + + iq_balance_mode24 + 0 + + + gain24 + 10 + + + ant25 + + + + bb_gain25 + 20 + + + bw25 + 0 + + + dc_offset_mode25 + 0 + + + corr25 + 0 + + + freq25 + 100e6 + + + gain_mode25 + False + + + if_gain25 + 20 + + + iq_balance_mode25 + 0 + + + gain25 + 10 + + + ant26 + + + + bb_gain26 + 20 + + + bw26 + 0 + + + dc_offset_mode26 + 0 + + + corr26 + 0 + + + freq26 + 100e6 + + + gain_mode26 + False + + + if_gain26 + 20 + + + iq_balance_mode26 + 0 + + + gain26 + 10 + + + ant27 + + + + bb_gain27 + 20 + + + bw27 + 0 + + + dc_offset_mode27 + 0 + + + corr27 + 0 + + + freq27 + 100e6 + + + gain_mode27 + False + + + if_gain27 + 20 + + + iq_balance_mode27 + 0 + + + gain27 + 10 + + + ant28 + + + + bb_gain28 + 20 + + + bw28 + 0 + + + dc_offset_mode28 + 0 + + + corr28 + 0 + + + freq28 + 100e6 + + + gain_mode28 + False + + + if_gain28 + 20 + + + iq_balance_mode28 + 0 + + + gain28 + 10 + + + ant29 + + + + bb_gain29 + 20 + + + bw29 + 0 + + + dc_offset_mode29 + 0 + + + corr29 + 0 + + + freq29 + 100e6 + + + gain_mode29 + False + + + if_gain29 + 20 + + + iq_balance_mode29 + 0 + + + gain29 + 10 + + + ant2 + + + + bb_gain2 + 20 + + + bw2 + 0 + + + dc_offset_mode2 + 0 + + + corr2 + 0 + + + freq2 + 100e6 + + + gain_mode2 + False + + + if_gain2 + 20 + + + iq_balance_mode2 + 0 + + + gain2 + 10 + + + ant30 + + + + bb_gain30 + 20 + + + bw30 + 0 + + + dc_offset_mode30 + 0 + + + corr30 + 0 + + + freq30 + 100e6 + + + gain_mode30 + False + + + if_gain30 + 20 + + + iq_balance_mode30 + 0 + + + gain30 + 10 + + + ant31 + + + + bb_gain31 + 20 + + + bw31 + 0 + + + dc_offset_mode31 + 0 + + + corr31 + 0 + + + freq31 + 100e6 + + + gain_mode31 + False + + + if_gain31 + 20 + + + iq_balance_mode31 + 0 + + + gain31 + 10 + + + ant3 + + + + bb_gain3 + 20 + + + bw3 + 0 + + + dc_offset_mode3 + 0 + + + corr3 + 0 + + + freq3 + 100e6 + + + gain_mode3 + False + + + if_gain3 + 20 + + + iq_balance_mode3 + 0 + + + gain3 + 10 + + + ant4 + + + + bb_gain4 + 20 + + + bw4 + 0 + + + dc_offset_mode4 + 0 + + + corr4 + 0 + + + freq4 + 100e6 + + + gain_mode4 + False + + + if_gain4 + 20 + + + iq_balance_mode4 + 0 + + + gain4 + 10 + + + ant5 + + + + bb_gain5 + 20 + + + bw5 + 0 + + + dc_offset_mode5 + 0 + + + corr5 + 0 + + + freq5 + 100e6 + + + gain_mode5 + False + + + if_gain5 + 20 + + + iq_balance_mode5 + 0 + + + gain5 + 10 + + + ant6 + + + + bb_gain6 + 20 + + + bw6 + 0 + + + dc_offset_mode6 + 0 + + + corr6 + 0 + + + freq6 + 100e6 + + + gain_mode6 + False + + + if_gain6 + 20 + + + iq_balance_mode6 + 0 + + + gain6 + 10 + + + ant7 + + + + bb_gain7 + 20 + + + bw7 + 0 + + + dc_offset_mode7 + 0 + + + corr7 + 0 + + + freq7 + 100e6 + + + gain_mode7 + False + + + if_gain7 + 20 + + + iq_balance_mode7 + 0 + + + gain7 + 10 + + + ant8 + + + + bb_gain8 + 20 + + + bw8 + 0 + + + dc_offset_mode8 + 0 + + + corr8 + 0 + + + freq8 + 100e6 + + + gain_mode8 + False + + + if_gain8 + 20 + + + iq_balance_mode8 + 0 + + + gain8 + 10 + + + ant9 + + + + bb_gain9 + 20 + + + bw9 + 0 + + + dc_offset_mode9 + 0 + + + corr9 + 0 + + + freq9 + 100e6 + + + gain_mode9 + False + + + if_gain9 + 20 + + + iq_balance_mode9 + 0 + + + gain9 + 10 + + + comment + + + + affinity + + + + args + satnogs.handle_rx_dev_args(rx_sdr_device, dev_args) + + + _enabled + 1 + + + _coordinate + (15, 319) + + + _rotation + 0 + + + id + osmosdr_source_0 + + + maxoutbuf + 0 + + + clock_source0 + + + + time_source0 + + + + clock_source1 + + + + time_source1 + + + + clock_source2 + + + + time_source2 + + + + clock_source3 + + + + time_source3 + + + + clock_source4 + + + + time_source4 + + + + clock_source5 + + + + time_source5 + + + + clock_source6 + + + + time_source6 + + + + clock_source7 + + + + time_source7 + + + + minoutbuf + 0 + + + nchan + 1 + + + num_mboards + 1 + + + type + fc32 + + + sample_rate + samp_rate_rx + + + sync + + + + + parameter + + alias + + + + comment + + + + _enabled + True + + + _coordinate + (470, 945) + + + _rotation + 0 + + + id + ppm + + + label + + + + short_id + + + + type + intx + + + value + 0 + + + + parameter + + alias + + + + comment + + + + _enabled + True + + + _coordinate + (23, 865) + + + _rotation + 0 + + + id + rf_gain + + + label + + + + short_id + + + + type + eng_float + + + value + satnogs.not_set_rx_rf_gain + + + + parameter + + alias + + + + comment + + + + _enabled + True + + + _coordinate + (382, 690) + + + _rotation + 0 + + + id + rigctl_port + + + label + + + + short_id + + + + type + intx + + + value + 4532 + + + + parameter + + alias + + + + comment + + + + _enabled + True + + + _coordinate + (303, 690) + + + _rotation + 0 + + + id + rx_freq + + + label + + + + short_id + + + + type + eng_float + + + value + 100e6 + + + + parameter + + alias + + + + comment + + + + _enabled + True + + + _coordinate + (191, 690) + + + _rotation + 0 + + + id + rx_sdr_device + + + label + + + + short_id + + + + type + string + + + value + usrpb200 + + + + satnogs_ax25_decoder_bm + + n_sync_flags + 1 + + + alias + + + + comment + + + + affinity + + + + _enabled + True + + + descrambling + False + + + _coordinate + (1374, 543) + + + _rotation + 180 + + + id + satnogs_ax25_decoder_bm_0 + + + maxoutbuf + 0 + + + max_frame_len + 1024 + + + minoutbuf + 0 + + + promisc + True + + + addr + 'GND' + + + ssid + 0 + + + + satnogs_coarse_doppler_correction_cc + + alias + + + + comment + + + + affinity + + + + _enabled + True + + + _coordinate + (352, 276) + + + _rotation + 0 + + + id + satnogs_coarse_doppler_correction_cc_0 + + + maxoutbuf + 0 + + + minoutbuf + 0 + + + sampling_rate + samp_rate_rx + + + target_freq + rx_freq + + + + satnogs_frame_file_sink + + alias + + + + comment + + + + affinity + + + + _enabled + True + + + _coordinate + (1045, 538) + + + _rotation + 180 + + + id + satnogs_frame_file_sink_0_0 + + + output_type + 0 + + + prefix_name + /tmp/afsk1200_crc_ok + + + + satnogs_frame_file_sink + + alias + + + + comment + + + + affinity + + + + _enabled + True + + + _coordinate + (1045, 602) + + + _rotation + 180 + + + id + satnogs_frame_file_sink_0_1_0 + + + output_type + 1 + + + prefix_name + /tmp/afsk1200_crc_ok + + + + satnogs_iq_sink + + append + False + + + alias + + + + comment + + + + affinity + + + + _enabled + True + + + filename + /tmp/iq.bin + + + _coordinate + (1286, 139) + + + _rotation + 0 + + + id + satnogs_iq_sink_0 + + + scale + 16768 + + + status + enable_iq_dump + + + + satnogs_ogg_encoder + + alias + + + + comment + + + + affinity + + + + _enabled + True + + + filename + file_path + + + _coordinate + (263, 466) + + + _rotation + 180 + + + id + satnogs_ogg_encoder_0 + + + quality + 1.0 + + + samp_rate + audio_samp_rate + + + + satnogs_tcp_rigctl_msg_source + + alias + + + + comment + + + + affinity + + + + _enabled + 1 + + + _coordinate + (16, 204) + + + _rotation + 0 + + + id + satnogs_tcp_rigctl_msg_source_0 + + + addr + "127.0.0.1" + + + mtu + 1500 + + + maxoutbuf + 0 + + + minoutbuf + 0 + + + mode + False + + + port + rigctl_port + + + interval + 1000 + + + + satnogs_waterfall_sink + + alias + + + + center_freq + 0.0 + + + comment + + + + affinity + + + + _enabled + True + + + fft_size + 1024 + + + filename + waterfall_file_path + + + _coordinate + (1486, 255) + + + _rotation + 0 + + + id + satnogs_waterfall_sink_0 + + + mode + 1 + + + pps + 10 + + + samp_rate + audio_samp_rate + + + + parameter + + alias + + + + comment + + + + _enabled + True + + + _coordinate + (23, 1033) + + + _rotation + 0 + + + id + space_frequency + + + label + + + + short_id + + + + type + eng_float + + + value + 1200.0 + + + + parameter + + alias + + + + comment + + + + _enabled + True + + + _coordinate + (23, 945) + + + _rotation + 0 + + + id + waterfall_file_path + + + label + + + + short_id + + + + type + string + + + value + /tmp/waterfall.dat + + + + analog_quadrature_demod_cf_0 + digital_clock_recovery_mm_xx_0 + 0 + 0 + + + analog_quadrature_demod_cf_0_0 + dc_blocker_xx_0 + 0 + 0 + + + blks2_rational_resampler_xxx_1 + analog_quadrature_demod_cf_0_0 + 0 + 0 + + + blks2_rational_resampler_xxx_1 + satnogs_iq_sink_0 + 0 + 0 + + + blks2_rational_resampler_xxx_1 + satnogs_waterfall_sink_0 + 0 + 0 + + + blocks_float_to_complex_0 + blocks_rotator_cc_0 + 0 + 0 + + + blocks_rotator_cc_0 + low_pass_filter_1 + 0 + 0 + + + dc_blocker_xx_0 + low_pass_filter_0 + 0 + 0 + + + digital_binary_slicer_fb_0 + satnogs_ax25_decoder_bm_0 + 0 + 0 + + + digital_clock_recovery_mm_xx_0 + digital_binary_slicer_fb_0 + 0 + 0 + + + digital_costas_loop_cc_0 + blks2_rational_resampler_xxx_1 + 0 + 0 + + + freq_xlating_fir_filter_xxx_0 + digital_costas_loop_cc_0 + 0 + 0 + + + low_pass_filter_0 + blocks_float_to_complex_0 + 0 + 0 + + + low_pass_filter_0 + satnogs_ogg_encoder_0 + 0 + 0 + + + low_pass_filter_1 + analog_quadrature_demod_cf_0 + 0 + 0 + + + osmosdr_source_0 + satnogs_coarse_doppler_correction_cc_0 + 0 + 0 + + + satnogs_ax25_decoder_bm_0 + satnogs_frame_file_sink_0_0 + pdu + frame + + + satnogs_ax25_decoder_bm_0 + satnogs_frame_file_sink_0_1_0 + pdu + frame + + + satnogs_coarse_doppler_correction_cc_0 + freq_xlating_fir_filter_xxx_0 + 0 + 0 + + + satnogs_tcp_rigctl_msg_source_0 + satnogs_coarse_doppler_correction_cc_0 + freq + freq + + diff --git a/apps/flowgraphs/satnogs_afsk1200_ax25.py b/apps/flowgraphs/satnogs_afsk1200_ax25.py new file mode 100755 index 0000000..729df65 --- /dev/null +++ b/apps/flowgraphs/satnogs_afsk1200_ax25.py @@ -0,0 +1,401 @@ +#!/usr/bin/env python2 +# -*- coding: utf-8 -*- +################################################## +# GNU Radio Python Flow Graph +# Title: AFSK1200 AX.25 decoder +# Author: Manolis Surligas (surligas@gmail.com), Vardakis Giorgos (vardakis.grg@gmail.com) +# Description: AFSK1200 AX.25 decoder +# Generated: Sat Nov 4 12:10:15 2017 +################################################## + +from gnuradio import analog +from gnuradio import blocks +from gnuradio import digital +from gnuradio import eng_notation +from gnuradio import filter +from gnuradio import gr +from gnuradio.eng_option import eng_option +from gnuradio.filter import firdes +from optparse import OptionParser +import math +import osmosdr +import satnogs +import time + + +class satnogs_afsk1200_ax25(gr.top_block): + + def __init__(self, antenna=satnogs.not_set_antenna, bb_gain=satnogs.not_set_rx_bb_gain, decoded_data_file_path='/tmp/.satnogs/data/data', dev_args=satnogs.not_set_dev_args, doppler_correction_per_sec=1000, enable_iq_dump=0, file_path='test.wav', if_gain=satnogs.not_set_rx_if_gain, iq_file_path='/tmp/iq.dat', lo_offset=100e3, mark_frequency=2200.0, ppm=0, rf_gain=satnogs.not_set_rx_rf_gain, rigctl_port=4532, rx_freq=100e6, rx_sdr_device='usrpb200', space_frequency=1200.0, waterfall_file_path='/tmp/waterfall.dat'): + gr.top_block.__init__(self, "AFSK1200 AX.25 decoder ") + + ################################################## + # Parameters + ################################################## + self.antenna = antenna + self.bb_gain = bb_gain + self.decoded_data_file_path = decoded_data_file_path + self.dev_args = dev_args + self.doppler_correction_per_sec = doppler_correction_per_sec + self.enable_iq_dump = enable_iq_dump + self.file_path = file_path + self.if_gain = if_gain + self.iq_file_path = iq_file_path + self.lo_offset = lo_offset + self.mark_frequency = mark_frequency + self.ppm = ppm + self.rf_gain = rf_gain + self.rigctl_port = rigctl_port + self.rx_freq = rx_freq + self.rx_sdr_device = rx_sdr_device + self.space_frequency = space_frequency + self.waterfall_file_path = waterfall_file_path + + ################################################## + # Variables + ################################################## + self.samp_rate_rx = samp_rate_rx = satnogs.hw_rx_settings[rx_sdr_device]['samp_rate'] + self.deviation = deviation = 5000 + self.baud_rate = baud_rate = 9600 + self.xlate_filter_taps = xlate_filter_taps = firdes.low_pass(1, samp_rate_rx, 125000, 25000, firdes.WIN_HAMMING, 6.76) + + self.taps = taps = firdes.low_pass(12.0, samp_rate_rx, 100e3, 60000, firdes.WIN_HAMMING, 6.76) + + self.modulation_index = modulation_index = deviation / (baud_rate / 2.0) + self.filter_rate = filter_rate = 250000 + self.audio_samp_rate = audio_samp_rate = 48000 + self.audio_gain = audio_gain = satnogs.fm_demod_settings[rx_sdr_device]['audio_gain'] + + ################################################## + # Blocks + ################################################## + self.satnogs_waterfall_sink_0 = satnogs.waterfall_sink(audio_samp_rate, 0.0, 10, 1024, waterfall_file_path, 1) + self.satnogs_tcp_rigctl_msg_source_0 = satnogs.tcp_rigctl_msg_source("127.0.0.1", rigctl_port, False, 1000, 1500) + self.satnogs_ogg_encoder_0 = satnogs.ogg_encoder(file_path, audio_samp_rate, 1.0) + self.satnogs_iq_sink_0 = satnogs.iq_sink(16768, '/tmp/iq.bin', False, enable_iq_dump) + self.satnogs_frame_file_sink_0_1_0 = satnogs.frame_file_sink('/tmp/afsk1200_crc_ok', 1) + self.satnogs_frame_file_sink_0_0 = satnogs.frame_file_sink('/tmp/afsk1200_crc_ok', 0) + self.satnogs_coarse_doppler_correction_cc_0 = satnogs.coarse_doppler_correction_cc(rx_freq, samp_rate_rx) + self.satnogs_ax25_decoder_bm_0 = satnogs.ax25_decoder_bm('GND', 0, True, False, 1024, 1) + self.osmosdr_source_0 = osmosdr.source( args="numchan=" + str(1) + " " + satnogs.handle_rx_dev_args(rx_sdr_device, dev_args) ) + self.osmosdr_source_0.set_sample_rate(samp_rate_rx) + self.osmosdr_source_0.set_center_freq(rx_freq - lo_offset, 0) + self.osmosdr_source_0.set_freq_corr(ppm, 0) + self.osmosdr_source_0.set_dc_offset_mode(2, 0) + self.osmosdr_source_0.set_iq_balance_mode(0, 0) + self.osmosdr_source_0.set_gain_mode(False, 0) + self.osmosdr_source_0.set_gain(satnogs.handle_rx_rf_gain(rx_sdr_device, rf_gain), 0) + self.osmosdr_source_0.set_if_gain(satnogs.handle_rx_if_gain(rx_sdr_device, if_gain), 0) + self.osmosdr_source_0.set_bb_gain(satnogs.handle_rx_bb_gain(rx_sdr_device, bb_gain), 0) + self.osmosdr_source_0.set_antenna(satnogs.handle_rx_antenna(rx_sdr_device, antenna), 0) + self.osmosdr_source_0.set_bandwidth(samp_rate_rx, 0) + + self.low_pass_filter_1 = filter.fir_filter_ccf(2, firdes.low_pass( + 1, audio_samp_rate/4, (mark_frequency - space_frequency)/2.0 + 200.0, 200, firdes.WIN_HAMMING, 6.76)) + self.low_pass_filter_0 = filter.fir_filter_fff(4, firdes.low_pass( + 1, audio_samp_rate, mark_frequency + 1000.0, audio_samp_rate * 0.1, firdes.WIN_HAMMING, 6.76)) + self.freq_xlating_fir_filter_xxx_0 = filter.freq_xlating_fir_filter_ccc(int(samp_rate_rx/filter_rate), (xlate_filter_taps), lo_offset, samp_rate_rx) + self.digital_costas_loop_cc_0 = digital.costas_loop_cc(2.0 * math.pi / 100.0, 2, False) + self.digital_clock_recovery_mm_xx_0 = digital.clock_recovery_mm_ff(48e3/9600, 0.25*0.175*0.175, 0.5, 0.175, 0.005) + self.digital_binary_slicer_fb_0 = digital.binary_slicer_fb() + self.dc_blocker_xx_0 = filter.dc_blocker_ff(1024, True) + self.blocks_rotator_cc_0 = blocks.rotator_cc(-2.0 * math.pi * ((mark_frequency + space_frequency) / 2.0) / (audio_samp_rate / 4.0)) + self.blocks_float_to_complex_0 = blocks.float_to_complex(1) + self.blks2_rational_resampler_xxx_1 = filter.rational_resampler_ccc( + interpolation=48000, + decimation=int(samp_rate_rx / (int(samp_rate_rx/filter_rate))), + taps=None, + fractional_bw=None, + ) + self.analog_quadrature_demod_cf_0_0 = analog.quadrature_demod_cf(((audio_samp_rate) / baud_rate)/(math.pi*modulation_index)) + self.analog_quadrature_demod_cf_0 = analog.quadrature_demod_cf(1.0) + + ################################################## + # Connections + ################################################## + self.msg_connect((self.satnogs_ax25_decoder_bm_0, 'pdu'), (self.satnogs_frame_file_sink_0_0, 'frame')) + self.msg_connect((self.satnogs_ax25_decoder_bm_0, 'pdu'), (self.satnogs_frame_file_sink_0_1_0, 'frame')) + self.msg_connect((self.satnogs_tcp_rigctl_msg_source_0, 'freq'), (self.satnogs_coarse_doppler_correction_cc_0, 'freq')) + self.connect((self.analog_quadrature_demod_cf_0, 0), (self.digital_clock_recovery_mm_xx_0, 0)) + self.connect((self.analog_quadrature_demod_cf_0_0, 0), (self.dc_blocker_xx_0, 0)) + self.connect((self.blks2_rational_resampler_xxx_1, 0), (self.analog_quadrature_demod_cf_0_0, 0)) + self.connect((self.blks2_rational_resampler_xxx_1, 0), (self.satnogs_iq_sink_0, 0)) + self.connect((self.blks2_rational_resampler_xxx_1, 0), (self.satnogs_waterfall_sink_0, 0)) + self.connect((self.blocks_float_to_complex_0, 0), (self.blocks_rotator_cc_0, 0)) + self.connect((self.blocks_rotator_cc_0, 0), (self.low_pass_filter_1, 0)) + self.connect((self.dc_blocker_xx_0, 0), (self.low_pass_filter_0, 0)) + self.connect((self.digital_binary_slicer_fb_0, 0), (self.satnogs_ax25_decoder_bm_0, 0)) + self.connect((self.digital_clock_recovery_mm_xx_0, 0), (self.digital_binary_slicer_fb_0, 0)) + self.connect((self.digital_costas_loop_cc_0, 0), (self.blks2_rational_resampler_xxx_1, 0)) + self.connect((self.freq_xlating_fir_filter_xxx_0, 0), (self.digital_costas_loop_cc_0, 0)) + self.connect((self.low_pass_filter_0, 0), (self.blocks_float_to_complex_0, 0)) + self.connect((self.low_pass_filter_0, 0), (self.satnogs_ogg_encoder_0, 0)) + self.connect((self.low_pass_filter_1, 0), (self.analog_quadrature_demod_cf_0, 0)) + self.connect((self.osmosdr_source_0, 0), (self.satnogs_coarse_doppler_correction_cc_0, 0)) + self.connect((self.satnogs_coarse_doppler_correction_cc_0, 0), (self.freq_xlating_fir_filter_xxx_0, 0)) + + def get_antenna(self): + return self.antenna + + def set_antenna(self, antenna): + self.antenna = antenna + self.osmosdr_source_0.set_antenna(satnogs.handle_rx_antenna(self.rx_sdr_device, self.antenna), 0) + + def get_bb_gain(self): + return self.bb_gain + + def set_bb_gain(self, bb_gain): + self.bb_gain = bb_gain + self.osmosdr_source_0.set_bb_gain(satnogs.handle_rx_bb_gain(self.rx_sdr_device, self.bb_gain), 0) + + def get_decoded_data_file_path(self): + return self.decoded_data_file_path + + def set_decoded_data_file_path(self, decoded_data_file_path): + self.decoded_data_file_path = decoded_data_file_path + + def get_dev_args(self): + return self.dev_args + + def set_dev_args(self, dev_args): + self.dev_args = dev_args + + def get_doppler_correction_per_sec(self): + return self.doppler_correction_per_sec + + def set_doppler_correction_per_sec(self, doppler_correction_per_sec): + self.doppler_correction_per_sec = doppler_correction_per_sec + + def get_enable_iq_dump(self): + return self.enable_iq_dump + + def set_enable_iq_dump(self, enable_iq_dump): + self.enable_iq_dump = enable_iq_dump + + def get_file_path(self): + return self.file_path + + def set_file_path(self, file_path): + self.file_path = file_path + + def get_if_gain(self): + return self.if_gain + + def set_if_gain(self, if_gain): + self.if_gain = if_gain + self.osmosdr_source_0.set_if_gain(satnogs.handle_rx_if_gain(self.rx_sdr_device, self.if_gain), 0) + + def get_iq_file_path(self): + return self.iq_file_path + + def set_iq_file_path(self, iq_file_path): + self.iq_file_path = iq_file_path + + def get_lo_offset(self): + return self.lo_offset + + def set_lo_offset(self, lo_offset): + self.lo_offset = lo_offset + self.osmosdr_source_0.set_center_freq(self.rx_freq - self.lo_offset, 0) + self.freq_xlating_fir_filter_xxx_0.set_center_freq(self.lo_offset) + + def get_mark_frequency(self): + return self.mark_frequency + + def set_mark_frequency(self, mark_frequency): + self.mark_frequency = mark_frequency + self.low_pass_filter_1.set_taps(firdes.low_pass(1, self.audio_samp_rate/4, (self.mark_frequency - self.space_frequency)/2.0 + 200.0, 200, firdes.WIN_HAMMING, 6.76)) + self.low_pass_filter_0.set_taps(firdes.low_pass(1, self.audio_samp_rate, self.mark_frequency + 1000.0, self.audio_samp_rate * 0.1, firdes.WIN_HAMMING, 6.76)) + self.blocks_rotator_cc_0.set_phase_inc(-2.0 * math.pi * ((self.mark_frequency + self.space_frequency) / 2.0) / (self.audio_samp_rate / 4.0)) + + def get_ppm(self): + return self.ppm + + def set_ppm(self, ppm): + self.ppm = ppm + self.osmosdr_source_0.set_freq_corr(self.ppm, 0) + + def get_rf_gain(self): + return self.rf_gain + + def set_rf_gain(self, rf_gain): + self.rf_gain = rf_gain + self.osmosdr_source_0.set_gain(satnogs.handle_rx_rf_gain(self.rx_sdr_device, self.rf_gain), 0) + + def get_rigctl_port(self): + return self.rigctl_port + + def set_rigctl_port(self, rigctl_port): + self.rigctl_port = rigctl_port + + def get_rx_freq(self): + return self.rx_freq + + def set_rx_freq(self, rx_freq): + self.rx_freq = rx_freq + self.satnogs_coarse_doppler_correction_cc_0.set_new_freq_locked(self.rx_freq) + self.osmosdr_source_0.set_center_freq(self.rx_freq - self.lo_offset, 0) + + def get_rx_sdr_device(self): + return self.rx_sdr_device + + def set_rx_sdr_device(self, rx_sdr_device): + self.rx_sdr_device = rx_sdr_device + self.set_samp_rate_rx(satnogs.hw_rx_settings[self.rx_sdr_device]['samp_rate']) + self.osmosdr_source_0.set_gain(satnogs.handle_rx_rf_gain(self.rx_sdr_device, self.rf_gain), 0) + self.osmosdr_source_0.set_if_gain(satnogs.handle_rx_if_gain(self.rx_sdr_device, self.if_gain), 0) + self.osmosdr_source_0.set_bb_gain(satnogs.handle_rx_bb_gain(self.rx_sdr_device, self.bb_gain), 0) + self.osmosdr_source_0.set_antenna(satnogs.handle_rx_antenna(self.rx_sdr_device, self.antenna), 0) + self.set_audio_gain(satnogs.fm_demod_settings[self.rx_sdr_device]['audio_gain']) + + def get_space_frequency(self): + return self.space_frequency + + def set_space_frequency(self, space_frequency): + self.space_frequency = space_frequency + self.low_pass_filter_1.set_taps(firdes.low_pass(1, self.audio_samp_rate/4, (self.mark_frequency - self.space_frequency)/2.0 + 200.0, 200, firdes.WIN_HAMMING, 6.76)) + self.blocks_rotator_cc_0.set_phase_inc(-2.0 * math.pi * ((self.mark_frequency + self.space_frequency) / 2.0) / (self.audio_samp_rate / 4.0)) + + def get_waterfall_file_path(self): + return self.waterfall_file_path + + def set_waterfall_file_path(self, waterfall_file_path): + self.waterfall_file_path = waterfall_file_path + + def get_samp_rate_rx(self): + return self.samp_rate_rx + + def set_samp_rate_rx(self, samp_rate_rx): + self.samp_rate_rx = samp_rate_rx + self.set_xlate_filter_taps(firdes.low_pass(1, self.samp_rate_rx, 125000, 25000, firdes.WIN_HAMMING, 6.76)) + self.osmosdr_source_0.set_sample_rate(self.samp_rate_rx) + self.osmosdr_source_0.set_bandwidth(self.samp_rate_rx, 0) + + def get_deviation(self): + return self.deviation + + def set_deviation(self, deviation): + self.deviation = deviation + self.set_modulation_index(self.deviation / (self.baud_rate / 2.0)) + + def get_baud_rate(self): + return self.baud_rate + + def set_baud_rate(self, baud_rate): + self.baud_rate = baud_rate + self.set_modulation_index(self.deviation / (self.baud_rate / 2.0)) + self.analog_quadrature_demod_cf_0_0.set_gain(((self.audio_samp_rate) / self.baud_rate)/(math.pi*self.modulation_index)) + + def get_xlate_filter_taps(self): + return self.xlate_filter_taps + + def set_xlate_filter_taps(self, xlate_filter_taps): + self.xlate_filter_taps = xlate_filter_taps + self.freq_xlating_fir_filter_xxx_0.set_taps((self.xlate_filter_taps)) + + def get_taps(self): + return self.taps + + def set_taps(self, taps): + self.taps = taps + + def get_modulation_index(self): + return self.modulation_index + + def set_modulation_index(self, modulation_index): + self.modulation_index = modulation_index + self.analog_quadrature_demod_cf_0_0.set_gain(((self.audio_samp_rate) / self.baud_rate)/(math.pi*self.modulation_index)) + + def get_filter_rate(self): + return self.filter_rate + + def set_filter_rate(self, filter_rate): + self.filter_rate = filter_rate + + def get_audio_samp_rate(self): + return self.audio_samp_rate + + def set_audio_samp_rate(self, audio_samp_rate): + self.audio_samp_rate = audio_samp_rate + self.low_pass_filter_1.set_taps(firdes.low_pass(1, self.audio_samp_rate/4, (self.mark_frequency - self.space_frequency)/2.0 + 200.0, 200, firdes.WIN_HAMMING, 6.76)) + self.low_pass_filter_0.set_taps(firdes.low_pass(1, self.audio_samp_rate, self.mark_frequency + 1000.0, self.audio_samp_rate * 0.1, firdes.WIN_HAMMING, 6.76)) + self.blocks_rotator_cc_0.set_phase_inc(-2.0 * math.pi * ((self.mark_frequency + self.space_frequency) / 2.0) / (self.audio_samp_rate / 4.0)) + self.analog_quadrature_demod_cf_0_0.set_gain(((self.audio_samp_rate) / self.baud_rate)/(math.pi*self.modulation_index)) + + def get_audio_gain(self): + return self.audio_gain + + def set_audio_gain(self, audio_gain): + self.audio_gain = audio_gain + + +def argument_parser(): + description = 'AFSK1200 AX.25 decoder' + parser = OptionParser(usage="%prog: [options]", option_class=eng_option, description=description) + parser.add_option( + "", "--antenna", dest="antenna", type="string", default=satnogs.not_set_antenna, + help="Set antenna [default=%default]") + parser.add_option( + "", "--bb-gain", dest="bb_gain", type="eng_float", default=eng_notation.num_to_str(satnogs.not_set_rx_bb_gain), + help="Set bb_gain [default=%default]") + parser.add_option( + "", "--decoded-data-file-path", dest="decoded_data_file_path", type="string", default='/tmp/.satnogs/data/data', + help="Set decoded_data_file_path [default=%default]") + parser.add_option( + "", "--dev-args", dest="dev_args", type="string", default=satnogs.not_set_dev_args, + help="Set dev_args [default=%default]") + parser.add_option( + "", "--doppler-correction-per-sec", dest="doppler_correction_per_sec", type="intx", default=1000, + help="Set doppler_correction_per_sec [default=%default]") + parser.add_option( + "", "--enable-iq-dump", dest="enable_iq_dump", type="intx", default=0, + help="Set enable_iq_dump [default=%default]") + parser.add_option( + "", "--file-path", dest="file_path", type="string", default='test.wav', + help="Set file_path [default=%default]") + parser.add_option( + "", "--if-gain", dest="if_gain", type="eng_float", default=eng_notation.num_to_str(satnogs.not_set_rx_if_gain), + help="Set if_gain [default=%default]") + parser.add_option( + "", "--iq-file-path", dest="iq_file_path", type="string", default='/tmp/iq.dat', + help="Set iq_file_path [default=%default]") + parser.add_option( + "", "--lo-offset", dest="lo_offset", type="eng_float", default=eng_notation.num_to_str(100e3), + help="Set lo_offset [default=%default]") + parser.add_option( + "", "--mark-frequency", dest="mark_frequency", type="eng_float", default=eng_notation.num_to_str(2200.0), + help="Set mark_frequency [default=%default]") + parser.add_option( + "", "--ppm", dest="ppm", type="intx", default=0, + help="Set ppm [default=%default]") + parser.add_option( + "", "--rf-gain", dest="rf_gain", type="eng_float", default=eng_notation.num_to_str(satnogs.not_set_rx_rf_gain), + help="Set rf_gain [default=%default]") + parser.add_option( + "", "--rigctl-port", dest="rigctl_port", type="intx", default=4532, + help="Set rigctl_port [default=%default]") + parser.add_option( + "", "--rx-freq", dest="rx_freq", type="eng_float", default=eng_notation.num_to_str(100e6), + help="Set rx_freq [default=%default]") + parser.add_option( + "", "--rx-sdr-device", dest="rx_sdr_device", type="string", default='usrpb200', + help="Set rx_sdr_device [default=%default]") + parser.add_option( + "", "--space-frequency", dest="space_frequency", type="eng_float", default=eng_notation.num_to_str(1200.0), + help="Set space_frequency [default=%default]") + parser.add_option( + "", "--waterfall-file-path", dest="waterfall_file_path", type="string", default='/tmp/waterfall.dat', + help="Set waterfall_file_path [default=%default]") + return parser + + +def main(top_block_cls=satnogs_afsk1200_ax25, options=None): + if options is None: + options, _ = argument_parser().parse_args() + + tb = top_block_cls(antenna=options.antenna, bb_gain=options.bb_gain, decoded_data_file_path=options.decoded_data_file_path, dev_args=options.dev_args, doppler_correction_per_sec=options.doppler_correction_per_sec, enable_iq_dump=options.enable_iq_dump, file_path=options.file_path, if_gain=options.if_gain, iq_file_path=options.iq_file_path, lo_offset=options.lo_offset, mark_frequency=options.mark_frequency, ppm=options.ppm, rf_gain=options.rf_gain, rigctl_port=options.rigctl_port, rx_freq=options.rx_freq, rx_sdr_device=options.rx_sdr_device, space_frequency=options.space_frequency, waterfall_file_path=options.waterfall_file_path) + tb.start() + tb.wait() + + +if __name__ == '__main__': + main() diff --git a/examples/afsk1200_example.grc b/examples/afsk1200_example.grc new file mode 100644 index 0000000..209cac4 --- /dev/null +++ b/examples/afsk1200_example.grc @@ -0,0 +1,1278 @@ + + + + Thu Nov 2 16:30:33 2017 + + options + + author + Manolis Surligas (surligas@gmail.com) + + + window_size + + + + category + [GRC Hier Blocks] + + + comment + + + + description + An AFSK1200 decoder + + + _enabled + True + + + _coordinate + (8, 8) + + + _rotation + 0 + + + generate_options + qt_gui + + + hier_block_src_path + .: + + + id + afsk1200_example + + + max_nouts + 0 + + + qt_qss_theme + + + + realtime_scheduling + + + + run_command + {python} -u {filename} + + + run_options + prompt + + + run + True + + + thread_safe_setters + + + + title + + + + + variable + + comment + + + + _enabled + True + + + _coordinate + (8, 160) + + + _rotation + 0 + + + id + samp_rate + + + value + 48000 + + + + analog_quadrature_demod_cf + + alias + + + + comment + + + + affinity + + + + _enabled + 1 + + + _coordinate + (813, 179) + + + _rotation + 0 + + + gain + 1.0 + + + id + analog_quadrature_demod_cf_0 + + + maxoutbuf + 0 + + + minoutbuf + 0 + + + + analog_sig_source_x + + amp + 1 + + + alias + + + + comment + + + + affinity + + + + _enabled + True + + + freq + -(1200 + 2200) / 2 + + + _coordinate + (191, 167) + + + _rotation + 0 + + + id + analog_sig_source_x_0 + + + maxoutbuf + 0 + + + minoutbuf + 0 + + + offset + 0 + + + type + complex + + + samp_rate + samp_rate + + + waveform + analog.GR_COS_WAVE + + + + blocks_float_to_complex + + alias + + + + comment + + + + affinity + + + + _enabled + True + + + _coordinate + (686, 47) + + + _rotation + 0 + + + id + blocks_float_to_complex_0 + + + maxoutbuf + 0 + + + minoutbuf + 0 + + + vlen + 1 + + + + blocks_multiply_xx + + alias + + + + comment + + + + affinity + + + + _enabled + True + + + _coordinate + (414, 167) + + + _rotation + 0 + + + id + blocks_multiply_xx_0 + + + type + complex + + + maxoutbuf + 0 + + + minoutbuf + 0 + + + num_inputs + 2 + + + vlen + 1 + + + + blocks_throttle + + alias + + + + comment + + + + affinity + + + + _enabled + 1 + + + _coordinate + (494, 43) + + + _rotation + 0 + + + id + blocks_throttle_0 + + + ignoretag + True + + + maxoutbuf + 0 + + + minoutbuf + 0 + + + samples_per_second + samp_rate*100 + + + type + float + + + vlen + 1 + + + + dc_blocker_xx + + alias + + + + comment + + + + affinity + + + + _enabled + True + + + _coordinate + (869, 299) + + + _rotation + 180 + + + id + dc_blocker_xx_0 + + + length + 1024 + + + long_form + True + + + maxoutbuf + 0 + + + minoutbuf + 0 + + + type + ff + + + + digital_binary_slicer_fb + + alias + + + + comment + + + + affinity + + + + _enabled + 1 + + + _coordinate + (398, 311) + + + _rotation + 180 + + + id + digital_binary_slicer_fb_0 + + + maxoutbuf + 0 + + + minoutbuf + 0 + + + + digital_clock_recovery_mm_xx + + alias + + + + comment + + + + affinity + + + + _enabled + True + + + _coordinate + (638, 279) + + + _rotation + 180 + + + gain_mu + 0.175 + + + gain_omega + 0.25*0.175*0.175 + + + id + digital_clock_recovery_mm_xx_1 + + + maxoutbuf + 0 + + + minoutbuf + 0 + + + mu + 0.5 + + + omega_relative_limit + 0.005 + + + omega + 4 + + + type + float + + + + digital_costas_loop_cc + + alias + + + + comment + + + + affinity + + + + _enabled + True + + + _coordinate + (885, 63) + + + _rotation + 0 + + + id + digital_costas_loop_cc_0 + + + w + 2*math.pi/100.0 + + + maxoutbuf + 0 + + + minoutbuf + 0 + + + order + 2 + + + use_snr + False + + + + import + + alias + + + + comment + + + + _enabled + True + + + _coordinate + (7, 227) + + + _rotation + 0 + + + id + import_0 + + + import + import math + + + + low_pass_filter + + beta + 6.76 + + + alias + + + + comment + + + + affinity + + + + cutoff_freq + 1000/2.0 + + + decim + 10 + + + _enabled + True + + + type + fir_filter_ccf + + + _coordinate + (590, 135) + + + _rotation + 0 + + + gain + 1 + + + id + low_pass_filter_0 + + + interp + 1 + + + maxoutbuf + 0 + + + minoutbuf + 0 + + + samp_rate + samp_rate + + + width + 1000 + + + win + firdes.WIN_HAMMING + + + + qtgui_time_sink_x + + autoscale + False + + + axislabels + True + + + alias + + + + comment + + + + ctrlpanel + True + + + affinity + + + + entags + True + + + _enabled + 1 + + + _coordinate + (1077, 163) + + + gui_hint + + + + _rotation + 0 + + + grid + False + + + id + qtgui_time_sink_x_0 + + + legend + True + + + alpha1 + 1.0 + + + color1 + "blue" + + + label1 + + + + marker1 + -1 + + + style1 + 1 + + + width1 + 1 + + + alpha10 + 1.0 + + + color10 + "blue" + + + label10 + + + + marker10 + -1 + + + style10 + 1 + + + width10 + 1 + + + alpha2 + 1.0 + + + color2 + "red" + + + label2 + + + + marker2 + -1 + + + style2 + 1 + + + width2 + 1 + + + alpha3 + 1.0 + + + color3 + "green" + + + label3 + + + + marker3 + -1 + + + style3 + 1 + + + width3 + 1 + + + alpha4 + 1.0 + + + color4 + "black" + + + label4 + + + + marker4 + -1 + + + style4 + 1 + + + width4 + 1 + + + alpha5 + 1.0 + + + color5 + "cyan" + + + label5 + + + + marker5 + -1 + + + style5 + 1 + + + width5 + 1 + + + alpha6 + 1.0 + + + color6 + "magenta" + + + label6 + + + + marker6 + -1 + + + style6 + 1 + + + width6 + 1 + + + alpha7 + 1.0 + + + color7 + "yellow" + + + label7 + + + + marker7 + -1 + + + style7 + 1 + + + width7 + 1 + + + alpha8 + 1.0 + + + color8 + "dark red" + + + label8 + + + + marker8 + -1 + + + style8 + 1 + + + width8 + 1 + + + alpha9 + 1.0 + + + color9 + "dark green" + + + label9 + + + + marker9 + -1 + + + style9 + 1 + + + width9 + 1 + + + name + "" + + + nconnections + 1 + + + size + 8192 + + + srate + samp_rate + + + tr_chan + 0 + + + tr_delay + 0 + + + tr_level + 0.0 + + + tr_mode + qtgui.TRIG_MODE_FREE + + + tr_slope + qtgui.TRIG_SLOPE_POS + + + tr_tag + "" + + + type + float + + + update_time + 0.10 + + + ylabel + Amplitude + + + yunit + "" + + + ymax + 1 + + + ymin + -1 + + + + satnogs_ax25_decoder_bm + + n_sync_flags + 1 + + + alias + + + + comment + + + + affinity + + + + _enabled + 1 + + + descrambling + False + + + _coordinate + (159, 406) + + + _rotation + 0 + + + id + satnogs_ax25_decoder_bm_0 + + + maxoutbuf + 0 + + + max_frame_len + 256 + + + minoutbuf + 0 + + + promisc + True + + + addr + 'GND' + + + ssid + 0 + + + + satnogs_multi_format_msg_sink + + alias + + + + comment + + + + affinity + + + + _enabled + 1 + + + filename + + + + _coordinate + (718, 410) + + + _rotation + 0 + + + id + satnogs_multi_format_msg_sink_0 + + + outstream + True + + + timestamp + True + + + format + 0 + + + + satnogs_ogg_source + + alias + + + + channels + 1 + + + comment + + + + affinity + + + + _enabled + 1 + + + filename + /home/surligas/Dropbox/job/satnogs/afsk1200/satnogs_24717_2017-10-28T19-14-22.ogg + + + _coordinate + (223, 35) + + + _rotation + 0 + + + id + satnogs_ogg_source_0 + + + maxoutbuf + 0 + + + minoutbuf + 0 + + + repeat + False + + + + analog_quadrature_demod_cf_0 + dc_blocker_xx_0 + 0 + 0 + + + analog_quadrature_demod_cf_0 + qtgui_time_sink_x_0 + 0 + 0 + + + analog_sig_source_x_0 + blocks_multiply_xx_0 + 0 + 1 + + + blocks_float_to_complex_0 + digital_costas_loop_cc_0 + 0 + 0 + + + blocks_multiply_xx_0 + low_pass_filter_0 + 0 + 0 + + + blocks_throttle_0 + blocks_float_to_complex_0 + 0 + 0 + + + dc_blocker_xx_0 + digital_clock_recovery_mm_xx_1 + 0 + 0 + + + digital_binary_slicer_fb_0 + satnogs_ax25_decoder_bm_0 + 0 + 0 + + + digital_clock_recovery_mm_xx_1 + digital_binary_slicer_fb_0 + 0 + 0 + + + digital_costas_loop_cc_0 + blocks_multiply_xx_0 + 0 + 0 + + + low_pass_filter_0 + analog_quadrature_demod_cf_0 + 0 + 0 + + + satnogs_ax25_decoder_bm_0 + satnogs_multi_format_msg_sink_0 + pdu + in + + + satnogs_ogg_source_0 + blocks_throttle_0 + 0 + 0 + + diff --git a/lib/ax25_decoder_bm_impl.cc b/lib/ax25_decoder_bm_impl.cc index a154eea..5a7a466 100644 --- a/lib/ax25_decoder_bm_impl.cc +++ b/lib/ax25_decoder_bm_impl.cc @@ -103,7 +103,16 @@ namespace gr { case NO_SYNC: if (d_shift_reg == AX25_SYNC_FLAG) { - enter_sync_state (); + /* + * If the user asked for only one leading AX.25 SYNC flag + * start immediately the decoding + */ + if (d_sync_flags_thr == 0) { + enter_decoding_state (); + } + else { + enter_sync_state (); + } } break; case IN_SYNC: @@ -211,7 +220,16 @@ namespace gr { case NO_SYNC: if (d_shift_reg == AX25_SYNC_FLAG) { - enter_sync_state (); + /* + * If the user asked for only one leading AX.25 SYNC flag + * start immediately the decoding + */ + if(d_sync_flags_thr == 0) { + enter_decoding_state (); + } + else { + enter_sync_state (); + } } break; case IN_SYNC: diff --git a/lib/multi_format_msg_sink_impl.cc b/lib/multi_format_msg_sink_impl.cc index 64c97dd..9c9b039 100644 --- a/lib/multi_format_msg_sink_impl.cc +++ b/lib/multi_format_msg_sink_impl.cc @@ -98,7 +98,10 @@ namespace gr switch (d_format) { case 0: - std::cout << s << std::endl; + for (size_t i = 0; i < pmt::blob_length (msg); i++) { + std::cout << s[i]; + } + std::cout << std::endl; break; case 1: su = (uint8_t *) pmt::blob_data (msg); From d951fa929218f137ad95f60b9c2e20c3091172c4 Mon Sep 17 00:00:00 2001 From: Manolis Surligas Date: Sun, 26 Nov 2017 22:46:29 +0200 Subject: [PATCH 2/2] Fix clock recovery issue on AFSK 1200 decoder * Fix clock recovery issue on AFSK 1200 decoder * Improve performance of AFSK 1200 * Make AFSK 1200 decoder to produce waterfall and audio file with the same characteristics as the generic FM demodulator flowgraph for a unified output experience in the SatNOGS network --- apps/flowgraphs/afsk1200_ax25.grc | 290 +++++++++++------------ apps/flowgraphs/satnogs_afsk1200_ax25.py | 101 ++++---- 2 files changed, 183 insertions(+), 208 deletions(-) diff --git a/apps/flowgraphs/afsk1200_ax25.grc b/apps/flowgraphs/afsk1200_ax25.grc index 9307e63..0006626 100644 --- a/apps/flowgraphs/afsk1200_ax25.grc +++ b/apps/flowgraphs/afsk1200_ax25.grc @@ -95,7 +95,7 @@ SDR received samples _coordinate - (590, 761) + (550, 690) _rotation @@ -122,7 +122,7 @@ SDR received samples _coordinate - (462, 546) + (686, 873) _rotation @@ -161,7 +161,7 @@ SDR received samples value - 9600 + 1200 @@ -203,7 +203,7 @@ SDR received samples _coordinate - (750, 706) + (327, 1073) _rotation @@ -230,7 +230,7 @@ SDR received samples _coordinate - (207, 769) + (343, 769) _rotation @@ -238,11 +238,11 @@ SDR received samples id - modulation_index + max_modulation_freq value - deviation / (baud_rate / 2.0) + 3000 @@ -250,7 +250,7 @@ SDR received samples comment SDR device -TX sampling rate +RX sampling rate _enabled @@ -258,7 +258,7 @@ TX sampling rate _coordinate - (351, 546) + (574, 873) _rotation @@ -332,7 +332,7 @@ TX sampling rate _coordinate - (590, 698) + (167, 1073) _rotation @@ -367,7 +367,7 @@ TX sampling rate _coordinate - (1460, 426) + (1364, 578) _rotation @@ -375,7 +375,7 @@ TX sampling rate gain - 1.0 + ((audio_samp_rate/10) / baud_rate)/(math.pi*1) id @@ -410,7 +410,7 @@ TX sampling rate _coordinate - (1046, 339) + (574, 394) _rotation @@ -418,7 +418,7 @@ TX sampling rate gain - ((audio_samp_rate) / baud_rate)/(math.pi*modulation_index) + (2*math.pi*deviation)/audio_samp_rate id @@ -433,6 +433,69 @@ TX sampling rate 0 + + analog_sig_source_x + + amp + 1 + + + alias + + + + comment + + + + affinity + + + + _enabled + True + + + freq + -(1200 + 2200) / 2 + + + _coordinate + (750, 646) + + + _rotation + 0 + + + id + analog_sig_source_x_0 + + + maxoutbuf + 0 + + + minoutbuf + 0 + + + offset + 0 + + + type + complex + + + samp_rate + audio_samp_rate + + + waveform + analog.GR_COS_WAVE + + parameter @@ -547,7 +610,7 @@ TX sampling rate _coordinate - (1272, 268) + (1125, 271) _rotation @@ -598,7 +661,7 @@ TX sampling rate _coordinate - (805, 414) + (686, 550) _rotation @@ -622,7 +685,7 @@ TX sampling rate - blocks_rotator_cc + blocks_multiply_xx alias @@ -641,7 +704,7 @@ TX sampling rate _coordinate - (997, 426) + (957, 566) _rotation @@ -649,7 +712,11 @@ TX sampling rate id - blocks_rotator_cc_0 + blocks_multiply_xx_0 + + + type + complex maxoutbuf @@ -660,8 +727,12 @@ TX sampling rate 0 - phase_inc - -2.0 * math.pi * ((mark_frequency + space_frequency) / 2.0) / (audio_samp_rate / 4.0) + num_inputs + 2 + + + vlen + 1 @@ -684,7 +755,7 @@ TX sampling rate _coordinate - (414, 402) + (534, 538) _rotation @@ -821,7 +892,7 @@ TX sampling rate _coordinate - (1914, 430) + (1771, 582) _rotation @@ -860,7 +931,7 @@ TX sampling rate _coordinate - (1699, 398) + (1563, 550) _rotation @@ -896,64 +967,13 @@ TX sampling rate omega - 48e3/9600 + (48e3/10)/baud_rate type float - - digital_costas_loop_cc - - alias - - - - comment - - - - affinity - - - - _enabled - True - - - _coordinate - (1022, 255) - - - _rotation - 0 - - - id - digital_costas_loop_cc_0 - - - w - 2.0 * math.pi / 100.0 - - - maxoutbuf - 0 - - - minoutbuf - 0 - - - order - 2 - - - use_snr - False - - parameter @@ -1284,7 +1304,10 @@ we shift the LO a little further comment - + Using the Carson bandwidth rule for filter width: +width = 2*(deviation + max_modulation_freq). +For the majority of FM transmissions we can expect +max_modulation_freq = 3000 affinity @@ -1292,11 +1315,11 @@ we shift the LO a little further cutoff_freq - mark_frequency + 1000.0 + deviation+max_modulation_freq decim - 4 + 1 _enabled @@ -1304,15 +1327,15 @@ we shift the LO a little further type - fir_filter_fff + fir_filter_ccf _coordinate - (622, 367) + (861, 351) _rotation - 0 + 180 gain @@ -1340,7 +1363,7 @@ we shift the LO a little further width - audio_samp_rate * 0.1 + 3000 win @@ -1367,11 +1390,11 @@ we shift the LO a little further cutoff_freq - (mark_frequency - space_frequency)/2.0 + 200.0 + (mark_frequency - space_frequency)/2.0 decim - 2 + 10 _enabled @@ -1383,7 +1406,7 @@ we shift the LO a little further _coordinate - (1252, 382) + (1148, 534) _rotation @@ -1391,7 +1414,7 @@ we shift the LO a little further gain - 1 + 10 id @@ -1411,11 +1434,11 @@ we shift the LO a little further samp_rate - audio_samp_rate/4 + audio_samp_rate width - 200 + 1000 win @@ -3115,7 +3138,7 @@ we shift the LO a little further _coordinate - (1374, 543) + (1563, 662) _rotation @@ -3217,46 +3240,7 @@ we shift the LO a little further _coordinate - (1045, 538) - - - _rotation - 180 - - - id - satnogs_frame_file_sink_0_0 - - - output_type - 0 - - - prefix_name - /tmp/afsk1200_crc_ok - - - - satnogs_frame_file_sink - - alias - - - - comment - - - - affinity - - - - _enabled - True - - - _coordinate - (1045, 602) + (1332, 706) _rotation @@ -3346,11 +3330,11 @@ we shift the LO a little further _coordinate - (263, 466) + (630, 99) _rotation - 180 + 0 id @@ -3577,9 +3561,21 @@ we shift the LO a little further 0 0 + + analog_quadrature_demod_cf_0_0 + satnogs_ogg_encoder_0 + 0 + 0 + + + analog_sig_source_x_0 + blocks_multiply_xx_0 + 0 + 1 + blks2_rational_resampler_xxx_1 - analog_quadrature_demod_cf_0_0 + low_pass_filter_0 0 0 @@ -3597,19 +3593,19 @@ we shift the LO a little further blocks_float_to_complex_0 - blocks_rotator_cc_0 + blocks_multiply_xx_0 0 0 - blocks_rotator_cc_0 + blocks_multiply_xx_0 low_pass_filter_1 0 0 dc_blocker_xx_0 - low_pass_filter_0 + blocks_float_to_complex_0 0 0 @@ -3626,26 +3622,14 @@ we shift the LO a little further 0 - digital_costas_loop_cc_0 + freq_xlating_fir_filter_xxx_0 blks2_rational_resampler_xxx_1 0 0 - - freq_xlating_fir_filter_xxx_0 - digital_costas_loop_cc_0 - 0 - 0 - low_pass_filter_0 - blocks_float_to_complex_0 - 0 - 0 - - - low_pass_filter_0 - satnogs_ogg_encoder_0 + analog_quadrature_demod_cf_0_0 0 0 @@ -3661,12 +3645,6 @@ we shift the LO a little further 0 0 - - satnogs_ax25_decoder_bm_0 - satnogs_frame_file_sink_0_0 - pdu - frame - satnogs_ax25_decoder_bm_0 satnogs_frame_file_sink_0_1_0 diff --git a/apps/flowgraphs/satnogs_afsk1200_ax25.py b/apps/flowgraphs/satnogs_afsk1200_ax25.py index 729df65..dc1c71b 100755 --- a/apps/flowgraphs/satnogs_afsk1200_ax25.py +++ b/apps/flowgraphs/satnogs_afsk1200_ax25.py @@ -5,7 +5,7 @@ # Title: AFSK1200 AX.25 decoder # Author: Manolis Surligas (surligas@gmail.com), Vardakis Giorgos (vardakis.grg@gmail.com) # Description: AFSK1200 AX.25 decoder -# Generated: Sat Nov 4 12:10:15 2017 +# Generated: Sun Nov 26 22:43:03 2017 ################################################## from gnuradio import analog @@ -54,14 +54,14 @@ class satnogs_afsk1200_ax25(gr.top_block): # Variables ################################################## self.samp_rate_rx = samp_rate_rx = satnogs.hw_rx_settings[rx_sdr_device]['samp_rate'] - self.deviation = deviation = 5000 - self.baud_rate = baud_rate = 9600 self.xlate_filter_taps = xlate_filter_taps = firdes.low_pass(1, samp_rate_rx, 125000, 25000, firdes.WIN_HAMMING, 6.76) self.taps = taps = firdes.low_pass(12.0, samp_rate_rx, 100e3, 60000, firdes.WIN_HAMMING, 6.76) - self.modulation_index = modulation_index = deviation / (baud_rate / 2.0) + self.max_modulation_freq = max_modulation_freq = 3000 self.filter_rate = filter_rate = 250000 + self.deviation = deviation = 5000 + self.baud_rate = baud_rate = 1200 self.audio_samp_rate = audio_samp_rate = 48000 self.audio_gain = audio_gain = satnogs.fm_demod_settings[rx_sdr_device]['audio_gain'] @@ -73,7 +73,6 @@ class satnogs_afsk1200_ax25(gr.top_block): self.satnogs_ogg_encoder_0 = satnogs.ogg_encoder(file_path, audio_samp_rate, 1.0) self.satnogs_iq_sink_0 = satnogs.iq_sink(16768, '/tmp/iq.bin', False, enable_iq_dump) self.satnogs_frame_file_sink_0_1_0 = satnogs.frame_file_sink('/tmp/afsk1200_crc_ok', 1) - self.satnogs_frame_file_sink_0_0 = satnogs.frame_file_sink('/tmp/afsk1200_crc_ok', 0) self.satnogs_coarse_doppler_correction_cc_0 = satnogs.coarse_doppler_correction_cc(rx_freq, samp_rate_rx) self.satnogs_ax25_decoder_bm_0 = satnogs.ax25_decoder_bm('GND', 0, True, False, 1024, 1) self.osmosdr_source_0 = osmosdr.source( args="numchan=" + str(1) + " " + satnogs.handle_rx_dev_args(rx_sdr_device, dev_args) ) @@ -89,16 +88,15 @@ class satnogs_afsk1200_ax25(gr.top_block): self.osmosdr_source_0.set_antenna(satnogs.handle_rx_antenna(rx_sdr_device, antenna), 0) self.osmosdr_source_0.set_bandwidth(samp_rate_rx, 0) - self.low_pass_filter_1 = filter.fir_filter_ccf(2, firdes.low_pass( - 1, audio_samp_rate/4, (mark_frequency - space_frequency)/2.0 + 200.0, 200, firdes.WIN_HAMMING, 6.76)) - self.low_pass_filter_0 = filter.fir_filter_fff(4, firdes.low_pass( - 1, audio_samp_rate, mark_frequency + 1000.0, audio_samp_rate * 0.1, firdes.WIN_HAMMING, 6.76)) + self.low_pass_filter_1 = filter.fir_filter_ccf(10, firdes.low_pass( + 10, audio_samp_rate, (mark_frequency - space_frequency)/2.0, 1000, firdes.WIN_HAMMING, 6.76)) + self.low_pass_filter_0 = filter.fir_filter_ccf(1, firdes.low_pass( + 1, audio_samp_rate, deviation+max_modulation_freq, 3000, firdes.WIN_HAMMING, 6.76)) self.freq_xlating_fir_filter_xxx_0 = filter.freq_xlating_fir_filter_ccc(int(samp_rate_rx/filter_rate), (xlate_filter_taps), lo_offset, samp_rate_rx) - self.digital_costas_loop_cc_0 = digital.costas_loop_cc(2.0 * math.pi / 100.0, 2, False) - self.digital_clock_recovery_mm_xx_0 = digital.clock_recovery_mm_ff(48e3/9600, 0.25*0.175*0.175, 0.5, 0.175, 0.005) + self.digital_clock_recovery_mm_xx_0 = digital.clock_recovery_mm_ff((48e3/10)/baud_rate, 0.25*0.175*0.175, 0.5, 0.175, 0.005) self.digital_binary_slicer_fb_0 = digital.binary_slicer_fb() self.dc_blocker_xx_0 = filter.dc_blocker_ff(1024, True) - self.blocks_rotator_cc_0 = blocks.rotator_cc(-2.0 * math.pi * ((mark_frequency + space_frequency) / 2.0) / (audio_samp_rate / 4.0)) + self.blocks_multiply_xx_0 = blocks.multiply_vcc(1) self.blocks_float_to_complex_0 = blocks.float_to_complex(1) self.blks2_rational_resampler_xxx_1 = filter.rational_resampler_ccc( interpolation=48000, @@ -106,29 +104,29 @@ class satnogs_afsk1200_ax25(gr.top_block): taps=None, fractional_bw=None, ) - self.analog_quadrature_demod_cf_0_0 = analog.quadrature_demod_cf(((audio_samp_rate) / baud_rate)/(math.pi*modulation_index)) - self.analog_quadrature_demod_cf_0 = analog.quadrature_demod_cf(1.0) + self.analog_sig_source_x_0 = analog.sig_source_c(audio_samp_rate, analog.GR_COS_WAVE, -(1200 + 2200) / 2, 1, 0) + self.analog_quadrature_demod_cf_0_0 = analog.quadrature_demod_cf((2*math.pi*deviation)/audio_samp_rate) + self.analog_quadrature_demod_cf_0 = analog.quadrature_demod_cf(((audio_samp_rate/10) / baud_rate)/(math.pi*1)) ################################################## # Connections ################################################## - self.msg_connect((self.satnogs_ax25_decoder_bm_0, 'pdu'), (self.satnogs_frame_file_sink_0_0, 'frame')) self.msg_connect((self.satnogs_ax25_decoder_bm_0, 'pdu'), (self.satnogs_frame_file_sink_0_1_0, 'frame')) self.msg_connect((self.satnogs_tcp_rigctl_msg_source_0, 'freq'), (self.satnogs_coarse_doppler_correction_cc_0, 'freq')) self.connect((self.analog_quadrature_demod_cf_0, 0), (self.digital_clock_recovery_mm_xx_0, 0)) self.connect((self.analog_quadrature_demod_cf_0_0, 0), (self.dc_blocker_xx_0, 0)) - self.connect((self.blks2_rational_resampler_xxx_1, 0), (self.analog_quadrature_demod_cf_0_0, 0)) + self.connect((self.analog_quadrature_demod_cf_0_0, 0), (self.satnogs_ogg_encoder_0, 0)) + self.connect((self.analog_sig_source_x_0, 0), (self.blocks_multiply_xx_0, 1)) + self.connect((self.blks2_rational_resampler_xxx_1, 0), (self.low_pass_filter_0, 0)) self.connect((self.blks2_rational_resampler_xxx_1, 0), (self.satnogs_iq_sink_0, 0)) self.connect((self.blks2_rational_resampler_xxx_1, 0), (self.satnogs_waterfall_sink_0, 0)) - self.connect((self.blocks_float_to_complex_0, 0), (self.blocks_rotator_cc_0, 0)) - self.connect((self.blocks_rotator_cc_0, 0), (self.low_pass_filter_1, 0)) - self.connect((self.dc_blocker_xx_0, 0), (self.low_pass_filter_0, 0)) + self.connect((self.blocks_float_to_complex_0, 0), (self.blocks_multiply_xx_0, 0)) + self.connect((self.blocks_multiply_xx_0, 0), (self.low_pass_filter_1, 0)) + self.connect((self.dc_blocker_xx_0, 0), (self.blocks_float_to_complex_0, 0)) self.connect((self.digital_binary_slicer_fb_0, 0), (self.satnogs_ax25_decoder_bm_0, 0)) self.connect((self.digital_clock_recovery_mm_xx_0, 0), (self.digital_binary_slicer_fb_0, 0)) - self.connect((self.digital_costas_loop_cc_0, 0), (self.blks2_rational_resampler_xxx_1, 0)) - self.connect((self.freq_xlating_fir_filter_xxx_0, 0), (self.digital_costas_loop_cc_0, 0)) - self.connect((self.low_pass_filter_0, 0), (self.blocks_float_to_complex_0, 0)) - self.connect((self.low_pass_filter_0, 0), (self.satnogs_ogg_encoder_0, 0)) + self.connect((self.freq_xlating_fir_filter_xxx_0, 0), (self.blks2_rational_resampler_xxx_1, 0)) + self.connect((self.low_pass_filter_0, 0), (self.analog_quadrature_demod_cf_0_0, 0)) self.connect((self.low_pass_filter_1, 0), (self.analog_quadrature_demod_cf_0, 0)) self.connect((self.osmosdr_source_0, 0), (self.satnogs_coarse_doppler_correction_cc_0, 0)) self.connect((self.satnogs_coarse_doppler_correction_cc_0, 0), (self.freq_xlating_fir_filter_xxx_0, 0)) @@ -203,9 +201,7 @@ class satnogs_afsk1200_ax25(gr.top_block): def set_mark_frequency(self, mark_frequency): self.mark_frequency = mark_frequency - self.low_pass_filter_1.set_taps(firdes.low_pass(1, self.audio_samp_rate/4, (self.mark_frequency - self.space_frequency)/2.0 + 200.0, 200, firdes.WIN_HAMMING, 6.76)) - self.low_pass_filter_0.set_taps(firdes.low_pass(1, self.audio_samp_rate, self.mark_frequency + 1000.0, self.audio_samp_rate * 0.1, firdes.WIN_HAMMING, 6.76)) - self.blocks_rotator_cc_0.set_phase_inc(-2.0 * math.pi * ((self.mark_frequency + self.space_frequency) / 2.0) / (self.audio_samp_rate / 4.0)) + self.low_pass_filter_1.set_taps(firdes.low_pass(10, self.audio_samp_rate, (self.mark_frequency - self.space_frequency)/2.0, 1000, firdes.WIN_HAMMING, 6.76)) def get_ppm(self): return self.ppm @@ -252,8 +248,7 @@ class satnogs_afsk1200_ax25(gr.top_block): def set_space_frequency(self, space_frequency): self.space_frequency = space_frequency - self.low_pass_filter_1.set_taps(firdes.low_pass(1, self.audio_samp_rate/4, (self.mark_frequency - self.space_frequency)/2.0 + 200.0, 200, firdes.WIN_HAMMING, 6.76)) - self.blocks_rotator_cc_0.set_phase_inc(-2.0 * math.pi * ((self.mark_frequency + self.space_frequency) / 2.0) / (self.audio_samp_rate / 4.0)) + self.low_pass_filter_1.set_taps(firdes.low_pass(10, self.audio_samp_rate, (self.mark_frequency - self.space_frequency)/2.0, 1000, firdes.WIN_HAMMING, 6.76)) def get_waterfall_file_path(self): return self.waterfall_file_path @@ -270,21 +265,6 @@ class satnogs_afsk1200_ax25(gr.top_block): self.osmosdr_source_0.set_sample_rate(self.samp_rate_rx) self.osmosdr_source_0.set_bandwidth(self.samp_rate_rx, 0) - def get_deviation(self): - return self.deviation - - def set_deviation(self, deviation): - self.deviation = deviation - self.set_modulation_index(self.deviation / (self.baud_rate / 2.0)) - - def get_baud_rate(self): - return self.baud_rate - - def set_baud_rate(self, baud_rate): - self.baud_rate = baud_rate - self.set_modulation_index(self.deviation / (self.baud_rate / 2.0)) - self.analog_quadrature_demod_cf_0_0.set_gain(((self.audio_samp_rate) / self.baud_rate)/(math.pi*self.modulation_index)) - def get_xlate_filter_taps(self): return self.xlate_filter_taps @@ -298,12 +278,12 @@ class satnogs_afsk1200_ax25(gr.top_block): def set_taps(self, taps): self.taps = taps - def get_modulation_index(self): - return self.modulation_index + def get_max_modulation_freq(self): + return self.max_modulation_freq - def set_modulation_index(self, modulation_index): - self.modulation_index = modulation_index - self.analog_quadrature_demod_cf_0_0.set_gain(((self.audio_samp_rate) / self.baud_rate)/(math.pi*self.modulation_index)) + def set_max_modulation_freq(self, max_modulation_freq): + self.max_modulation_freq = max_modulation_freq + self.low_pass_filter_0.set_taps(firdes.low_pass(1, self.audio_samp_rate, self.deviation+self.max_modulation_freq, 3000, firdes.WIN_HAMMING, 6.76)) def get_filter_rate(self): return self.filter_rate @@ -311,15 +291,32 @@ class satnogs_afsk1200_ax25(gr.top_block): def set_filter_rate(self, filter_rate): self.filter_rate = filter_rate + def get_deviation(self): + return self.deviation + + def set_deviation(self, deviation): + self.deviation = deviation + self.low_pass_filter_0.set_taps(firdes.low_pass(1, self.audio_samp_rate, self.deviation+self.max_modulation_freq, 3000, firdes.WIN_HAMMING, 6.76)) + self.analog_quadrature_demod_cf_0_0.set_gain((2*math.pi*self.deviation)/self.audio_samp_rate) + + def get_baud_rate(self): + return self.baud_rate + + def set_baud_rate(self, baud_rate): + self.baud_rate = baud_rate + self.digital_clock_recovery_mm_xx_0.set_omega((48e3/10)/self.baud_rate) + self.analog_quadrature_demod_cf_0.set_gain(((self.audio_samp_rate/10) / self.baud_rate)/(math.pi*1)) + def get_audio_samp_rate(self): return self.audio_samp_rate def set_audio_samp_rate(self, audio_samp_rate): self.audio_samp_rate = audio_samp_rate - self.low_pass_filter_1.set_taps(firdes.low_pass(1, self.audio_samp_rate/4, (self.mark_frequency - self.space_frequency)/2.0 + 200.0, 200, firdes.WIN_HAMMING, 6.76)) - self.low_pass_filter_0.set_taps(firdes.low_pass(1, self.audio_samp_rate, self.mark_frequency + 1000.0, self.audio_samp_rate * 0.1, firdes.WIN_HAMMING, 6.76)) - self.blocks_rotator_cc_0.set_phase_inc(-2.0 * math.pi * ((self.mark_frequency + self.space_frequency) / 2.0) / (self.audio_samp_rate / 4.0)) - self.analog_quadrature_demod_cf_0_0.set_gain(((self.audio_samp_rate) / self.baud_rate)/(math.pi*self.modulation_index)) + self.low_pass_filter_1.set_taps(firdes.low_pass(10, self.audio_samp_rate, (self.mark_frequency - self.space_frequency)/2.0, 1000, firdes.WIN_HAMMING, 6.76)) + self.low_pass_filter_0.set_taps(firdes.low_pass(1, self.audio_samp_rate, self.deviation+self.max_modulation_freq, 3000, firdes.WIN_HAMMING, 6.76)) + self.analog_sig_source_x_0.set_sampling_freq(self.audio_samp_rate) + self.analog_quadrature_demod_cf_0_0.set_gain((2*math.pi*self.deviation)/self.audio_samp_rate) + self.analog_quadrature_demod_cf_0.set_gain(((self.audio_samp_rate/10) / self.baud_rate)/(math.pi*1)) def get_audio_gain(self): return self.audio_gain