summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--CMakeLists.txt4
-rw-r--r--cmake/Modules/FindUHD.cmake24
-rw-r--r--docs/doxygen/Doxyfile.in27
-rw-r--r--docs/doxygen/other/pmt.dox17
-rw-r--r--docs/doxygen/other/stream_tags.dox5
-rw-r--r--gnuradio-runtime/include/gnuradio/block.h14
-rw-r--r--gnuradio-runtime/include/gnuradio/block_detail.h5
-rw-r--r--gnuradio-runtime/include/gnuradio/buffer.h10
-rw-r--r--gnuradio-runtime/include/gnuradio/logger.h.in7
-rw-r--r--gnuradio-runtime/include/gnuradio/tagged_stream_block.h2
-rw-r--r--gnuradio-runtime/include/pmt/pmt.h10
-rw-r--r--gnuradio-runtime/lib/basic_block.cc2
-rw-r--r--gnuradio-runtime/lib/block.cc12
-rw-r--r--gnuradio-runtime/lib/block_detail.cc13
-rw-r--r--gnuradio-runtime/lib/buffer.cc58
-rw-r--r--gnuradio-runtime/lib/logger.cc31
-rw-r--r--gnuradio-runtime/lib/pmt/pmt.cc12
-rw-r--r--gnuradio-runtime/lib/pmt/qa_pmt_prims.cc9
-rw-r--r--gnuradio-runtime/lib/tagged_stream_block.cc12
-rw-r--r--gnuradio-runtime/python/gnuradio/gr/hier_block2.py139
-rw-r--r--gnuradio-runtime/python/gnuradio/gr/qa_hier_block2.py91
-rw-r--r--gnuradio-runtime/python/gnuradio/gr/tag_utils.py17
-rw-r--r--gnuradio-runtime/python/gnuradio/gr/top_block.py148
-rwxr-xr-xgnuradio-runtime/python/pmt/qa_pmt.py2
-rw-r--r--gnuradio-runtime/swig/block.i1
-rw-r--r--gnuradio-runtime/swig/pmt_swig.i2
-rw-r--r--gr-analog/grc/analog_probe_avg_mag_sqrd_x.xml1
-rw-r--r--gr-analog/include/gnuradio/analog/probe_avg_mag_sqrd_c.h1
-rw-r--r--gr-analog/include/gnuradio/analog/probe_avg_mag_sqrd_cf.h1
-rw-r--r--gr-analog/include/gnuradio/analog/probe_avg_mag_sqrd_f.h1
-rw-r--r--gr-analog/lib/probe_avg_mag_sqrd_c_impl.cc6
-rw-r--r--gr-analog/lib/probe_avg_mag_sqrd_c_impl.h1
-rw-r--r--gr-analog/lib/probe_avg_mag_sqrd_cf_impl.cc6
-rw-r--r--gr-analog/lib/probe_avg_mag_sqrd_cf_impl.h1
-rw-r--r--gr-analog/lib/probe_avg_mag_sqrd_f_impl.cc6
-rw-r--r--gr-analog/lib/probe_avg_mag_sqrd_f_impl.h1
-rw-r--r--gr-blocks/examples/CMakeLists.txt8
-rw-r--r--gr-blocks/examples/msg_passing/strobe.grc182
-rw-r--r--gr-blocks/examples/vector_source_with_tags.grc698
-rw-r--r--gr-blocks/grc/blocks_abs_xx.xml19
-rw-r--r--gr-blocks/grc/blocks_repack_bits_bb.xml27
-rw-r--r--gr-blocks/grc/blocks_tagged_stream_to_pdu.xml1
-rw-r--r--gr-blocks/include/gnuradio/blocks/abs_XX.h.t2
-rw-r--r--gr-blocks/include/gnuradio/blocks/control_loop.h81
-rw-r--r--gr-blocks/include/gnuradio/blocks/pdu_to_tagged_stream.h4
-rw-r--r--gr-blocks/include/gnuradio/blocks/repack_bits_bb.h6
-rw-r--r--gr-blocks/lib/abs_XX_impl.cc.t13
-rw-r--r--gr-blocks/lib/abs_XX_impl.h.t5
-rw-r--r--gr-blocks/lib/deinterleave_impl.cc36
-rw-r--r--gr-blocks/lib/deinterleave_impl.h3
-rw-r--r--gr-blocks/lib/message_strobe_impl.cc8
-rw-r--r--gr-blocks/lib/message_strobe_impl.h2
-rw-r--r--gr-blocks/lib/message_strobe_random_impl.cc4
-rw-r--r--gr-blocks/lib/message_strobe_random_impl.h2
-rw-r--r--gr-blocks/lib/pdu_to_tagged_stream_impl.cc119
-rw-r--r--gr-blocks/lib/pdu_to_tagged_stream_impl.h15
-rw-r--r--gr-blocks/lib/qa_block_tags.cc198
-rw-r--r--gr-blocks/lib/repack_bits_bb_impl.cc115
-rw-r--r--gr-blocks/lib/repack_bits_bb_impl.h5
-rw-r--r--gr-blocks/lib/throttle_impl.cc8
-rw-r--r--gr-blocks/lib/throttle_impl.h3
-rw-r--r--gr-blocks/lib/udp_sink_impl.cc5
-rw-r--r--gr-blocks/lib/udp_source_impl.cc3
-rw-r--r--gr-blocks/lib/vector_source_X_impl.cc.t2
-rwxr-xr-xgr-blocks/python/blocks/qa_pdu.py2
-rwxr-xr-xgr-blocks/python/blocks/qa_repack_bits_bb.py53
-rw-r--r--gr-digital/grc/digital_costas_loop_cc.xml84
-rw-r--r--gr-digital/include/gnuradio/digital/costas_loop_cc.h9
-rw-r--r--gr-digital/include/gnuradio/digital/ofdm_frame_equalizer_vcvc.h17
-rw-r--r--gr-digital/lib/costas_loop_cc_impl.cc68
-rw-r--r--gr-digital/lib/costas_loop_cc_impl.h45
-rw-r--r--gr-digital/lib/header_payload_demux_impl.cc71
-rw-r--r--gr-digital/lib/ofdm_frame_equalizer_vcvc_impl.cc66
-rw-r--r--gr-digital/lib/ofdm_serializer_vcc_impl.cc80
-rwxr-xr-xgr-digital/python/digital/qa_costas_loop_cc.py22
-rwxr-xr-xgr-digital/python/digital/qa_header_payload_demux.py80
-rwxr-xr-xgr-digital/python/digital/qa_ofdm_frame_equalizer_vcvc.py2
-rw-r--r--gr-fec/lib/decoder_impl.cc8
-rw-r--r--gr-fec/lib/encoder_impl.cc13
-rw-r--r--gr-fft/include/gnuradio/fft/window.h23
-rw-r--r--gr-fft/lib/window.cc20
-rw-r--r--gr-qtgui/grc/qtgui_freq_sink_x.xml81
-rw-r--r--gr-qtgui/grc/qtgui_waterfall_sink_x.xml19
-rw-r--r--gr-qtgui/include/gnuradio/qtgui/FrequencyDisplayPlot.h3
-rw-r--r--gr-qtgui/include/gnuradio/qtgui/WaterfallDisplayPlot.h2
-rw-r--r--gr-qtgui/include/gnuradio/qtgui/freq_sink_c.h28
-rw-r--r--gr-qtgui/include/gnuradio/qtgui/freq_sink_f.h35
-rw-r--r--gr-qtgui/include/gnuradio/qtgui/freqdisplayform.h28
-rw-r--r--gr-qtgui/include/gnuradio/qtgui/waterfall_sink_f.h7
-rw-r--r--gr-qtgui/include/gnuradio/qtgui/waterfalldisplayform.h1
-rw-r--r--gr-qtgui/lib/FrequencyDisplayPlot.cc34
-rw-r--r--gr-qtgui/lib/WaterfallDisplayPlot.cc31
-rw-r--r--gr-qtgui/lib/const_sink_c_impl.cc2
-rw-r--r--gr-qtgui/lib/freq_sink_c_impl.cc225
-rw-r--r--gr-qtgui/lib/freq_sink_c_impl.h24
-rw-r--r--gr-qtgui/lib/freq_sink_f_impl.cc219
-rw-r--r--gr-qtgui/lib/freq_sink_f_impl.h27
-rw-r--r--gr-qtgui/lib/freqdisplayform.cc119
-rw-r--r--gr-qtgui/lib/waterfall_sink_f_impl.cc23
-rw-r--r--gr-qtgui/lib/waterfall_sink_f_impl.h1
-rw-r--r--gr-qtgui/lib/waterfalldisplayform.cc7
-rw-r--r--gr-trellis/doc/gr-trellis.xml8
-rw-r--r--gr-trellis/examples/grc/CMakeLists.txt26
-rw-r--r--gr-trellis/examples/grc/interference_cancellation.grc2635
-rw-r--r--gr-trellis/examples/grc/pccc.grc833
-rw-r--r--gr-trellis/examples/grc/readme.txt6
-rw-r--r--gr-trellis/examples/grc/sccc.grc690
-rw-r--r--gr-trellis/examples/grc/tcm.grc (renamed from gr-trellis/examples/grc/pccc1.grc)828
-rw-r--r--gr-trellis/examples/grc/turbo_equalization.grc2766
-rw-r--r--gr-trellis/examples/grc/viterbi_equalization.grc (renamed from gr-trellis/examples/grc/sccc1.grc)1026
-rw-r--r--gr-trellis/examples/python/CMakeLists.txt30
-rw-r--r--gr-trellis/examples/python/README10
-rw-r--r--gr-trellis/examples/python/fsm_files/awgn1o1_16rsc.fsm40
-rw-r--r--gr-trellis/examples/python/fsm_files/awgn1o1_4rsc.fsm16
-rw-r--r--gr-trellis/examples/python/fsm_files/awgn1o2_16rsc.fsm40
-rw-r--r--gr-trellis/examples/python/fsm_files/awgn1o2_4rsc.fsm14
-rw-r--r--gr-trellis/examples/python/fsm_files/awgn2o3_16ungerboeck.fsm50
-rw-r--r--gr-trellis/examples/python/fsm_files/awgn2o3_16ungerboecka.fsm48
-rw-r--r--gr-trellis/examples/python/fsm_files/awgn2o3_32ungerboeck.fsm83
-rw-r--r--gr-trellis/examples/python/fsm_files/awgn2o3_32ungerboecka.fsm84
-rw-r--r--gr-trellis/examples/python/fsm_files/awgn2o3_4_msb.fsm2
-rw-r--r--gr-trellis/examples/python/fsm_files/awgn2o3_4_msbG.fsm4
-rw-r--r--gr-trellis/examples/python/fsm_files/awgn2o3_4ungerboeck.fsm26
-rw-r--r--gr-trellis/examples/python/fsm_files/awgn2o3_4ungerboecka.fsm23
-rw-r--r--gr-trellis/examples/python/fsm_files/awgn2o3_64ungerboeck.fsm150
-rw-r--r--gr-trellis/examples/python/fsm_files/awgn2o3_64ungerboecka.fsm154
-rw-r--r--gr-trellis/examples/python/fsm_files/awgn2o3_8.fsm3
-rw-r--r--gr-trellis/examples/python/fsm_files/awgn2o3_8ungerboeck.fsm35
-rw-r--r--gr-trellis/examples/python/fsm_files/awgn2o3_8ungerboecka.fsm32
-rw-r--r--gr-trellis/examples/python/fsm_files/uncoded4.fsm7
-rwxr-xr-xgr-trellis/examples/python/test_cpm.py7
-rwxr-xr-xgr-trellis/examples/python/test_pccc_turbo1.py124
-rwxr-xr-xgr-trellis/examples/python/test_sccc_hard.py106
-rwxr-xr-xgr-trellis/examples/python/test_sccc_soft.py110
-rwxr-xr-xgr-trellis/examples/python/test_sccc_turbo.py146
-rwxr-xr-xgr-trellis/examples/python/test_sccc_turbo1.py104
-rwxr-xr-xgr-trellis/examples/python/test_sccc_turbo2.py106
-rwxr-xr-xgr-trellis/examples/python/test_tcm.py76
-rwxr-xr-xgr-trellis/examples/python/test_tcm_bit.py134
-rwxr-xr-xgr-trellis/examples/python/test_tcm_combined.py112
-rwxr-xr-xgr-trellis/examples/python/test_tcm_parallel.py118
-rwxr-xr-xgr-trellis/examples/python/test_turbo_equalization.py147
-rwxr-xr-xgr-trellis/examples/python/test_turbo_equalization1.py152
-rwxr-xr-xgr-trellis/examples/python/test_turbo_equalization2.py152
-rwxr-xr-xgr-trellis/examples/python/test_viterbi_equalization.py99
-rwxr-xr-xgr-trellis/examples/python/test_viterbi_equalization1.py108
-rw-r--r--gr-trellis/gnuradio-trellis.pc.in2
-rw-r--r--gr-trellis/grc/trellis_encoder_xx.xml26
-rw-r--r--gr-trellis/grc/trellis_metrics_x.xml3
-rw-r--r--gr-trellis/grc/trellis_pccc_decoder_combined_xx.xml2
-rw-r--r--gr-trellis/grc/trellis_permutation.xml4
-rw-r--r--gr-trellis/grc/trellis_sccc_decoder_combined_xx.xml2
-rw-r--r--gr-trellis/grc/trellis_siso_combined_f.xml16
-rw-r--r--gr-trellis/grc/trellis_siso_f.xml13
-rw-r--r--gr-trellis/grc/trellis_viterbi_combined_xx.xml8
-rw-r--r--gr-trellis/grc/trellis_viterbi_x.xml4
-rw-r--r--gr-trellis/include/gnuradio/trellis/encoder_XX.h.t6
-rw-r--r--gr-trellis/include/gnuradio/trellis/fsm.h10
-rw-r--r--gr-trellis/include/gnuradio/trellis/metrics_X.h.t5
-rw-r--r--gr-trellis/include/gnuradio/trellis/permutation.h7
-rw-r--r--gr-trellis/include/gnuradio/trellis/sccc_decoder_combined_XX.h.t1
-rw-r--r--gr-trellis/include/gnuradio/trellis/siso_combined_f.h11
-rw-r--r--gr-trellis/include/gnuradio/trellis/siso_f.h8
-rw-r--r--gr-trellis/include/gnuradio/trellis/viterbi_X.h.t13
-rw-r--r--gr-trellis/include/gnuradio/trellis/viterbi_combined_XX.h.t9
-rw-r--r--gr-trellis/lib/calc_metric.cc17
-rw-r--r--gr-trellis/lib/core_algorithms.cc47
-rw-r--r--gr-trellis/lib/encoder_XX_impl.cc.t80
-rw-r--r--gr-trellis/lib/encoder_XX_impl.h.t14
-rw-r--r--gr-trellis/lib/fsm.cc48
-rw-r--r--gr-trellis/lib/metrics_X_impl.cc.t27
-rw-r--r--gr-trellis/lib/metrics_X_impl.h.t4
-rw-r--r--gr-trellis/lib/pccc_decoder_combined_XX_impl.cc.t2
-rw-r--r--gr-trellis/lib/pccc_encoder_XX_impl.cc.t2
-rw-r--r--gr-trellis/lib/permutation_impl.cc23
-rw-r--r--gr-trellis/lib/permutation_impl.h6
-rw-r--r--gr-trellis/lib/sccc_decoder_combined_XX_impl.cc.t2
-rw-r--r--gr-trellis/lib/siso_combined_f_impl.cc109
-rw-r--r--gr-trellis/lib/siso_combined_f_impl.h12
-rw-r--r--gr-trellis/lib/siso_f_impl.cc80
-rw-r--r--gr-trellis/lib/siso_f_impl.h9
-rw-r--r--gr-trellis/lib/viterbi_X_impl.cc.t27
-rw-r--r--gr-trellis/lib/viterbi_X_impl.h.t12
-rw-r--r--gr-trellis/lib/viterbi_combined_XX_impl.cc.t45
-rw-r--r--gr-trellis/lib/viterbi_combined_XX_impl.h.t17
-rw-r--r--gr-trellis/python/trellis/CMakeLists.txt1
-rw-r--r--gr-trellis/python/trellis/__init__.py3
-rwxr-xr-xgr-trellis/python/trellis/fsm_utils.py (renamed from gr-trellis/examples/python/fsm_utils.py)61
-rw-r--r--gr-uhd/lib/usrp_sink_impl.cc15
-rw-r--r--gr-uhd/lib/usrp_source_impl.cc15
-rw-r--r--gr-utils/python/modtool/gr-newmod/cmake/Modules/FindCppUnit.cmake3
-rw-r--r--gr-utils/python/modtool/gr-newmod/cmake/Modules/GrMiscUtils.cmake321
-rw-r--r--gr-utils/python/modtool/gr-newmod/cmake/Modules/GrPlatform.cmake10
-rw-r--r--gr-utils/python/modtool/gr-newmod/cmake/Modules/GrPython.cmake25
-rw-r--r--gr-utils/python/modtool/gr-newmod/cmake/Modules/GrSwig.cmake50
-rw-r--r--gr-utils/python/modtool/gr-newmod/cmake/Modules/GrTest.cmake22
-rwxr-xr-xgr-utils/python/utils/grcc29
-rw-r--r--gr-wxgui/python/wxgui/fft_window.py6
-rw-r--r--gr-wxgui/python/wxgui/fftsink_nongl.py12
-rw-r--r--grc/CMakeLists.txt4
-rw-r--r--grc/base/CMakeLists.txt1
-rw-r--r--grc/base/Connection.py26
-rw-r--r--grc/base/Constants.py6
-rw-r--r--grc/base/Element.py3
-rw-r--r--grc/base/FlowGraph.py20
-rw-r--r--grc/base/Platform.py54
-rw-r--r--grc/base/Port.py13
-rw-r--r--grc/base/domain.dtd35
-rw-r--r--grc/blocks/gr_message_domain.xml18
-rw-r--r--grc/blocks/gr_stream_domain.xml18
-rw-r--r--grc/blocks/options.xml10
-rw-r--r--grc/blocks/pad_sink.xml4
-rw-r--r--grc/blocks/pad_source.xml4
-rw-r--r--grc/gui/ActionHandler.py15
-rw-r--r--grc/gui/Block.py18
-rw-r--r--grc/gui/Colors.py6
-rw-r--r--grc/gui/Connection.py50
-rw-r--r--grc/gui/Constants.py7
-rw-r--r--grc/gui/Element.py14
-rw-r--r--grc/gui/Messages.py8
-rw-r--r--grc/gui/Param.py5
-rw-r--r--grc/gui/Port.py13
-rw-r--r--grc/python/Block.py9
-rw-r--r--grc/python/CMakeLists.txt1
-rw-r--r--grc/python/Connection.py6
-rw-r--r--grc/python/FlowGraph.py93
-rw-r--r--grc/python/Generator.py269
-rw-r--r--grc/python/Port.py12
-rw-r--r--grc/python/block.dtd5
-rw-r--r--grc/python/convert_hier.py116
-rw-r--r--grc/python/flow_graph.tmpl59
-rw-r--r--volk/apps/volk_profile.cc83
-rw-r--r--volk/kernels/volk/volk_16i_32fc_dot_prod_32fc.h70
-rw-r--r--volk/kernels/volk/volk_16i_branch_4_state_8.h22
-rw-r--r--volk/kernels/volk/volk_16i_convert_8i.h65
-rw-r--r--volk/kernels/volk/volk_16i_max_star_16i.h24
-rw-r--r--volk/kernels/volk/volk_16i_max_star_horizontal_16i.h28
-rw-r--r--volk/kernels/volk/volk_16i_permute_and_scalar_add.h22
-rw-r--r--volk/kernels/volk/volk_16i_s32f_convert_32f.h182
-rw-r--r--volk/kernels/volk/volk_16i_x4_quad_max_star_16i.h22
-rw-r--r--volk/kernels/volk/volk_16i_x5_add_quad_16i_x4.h22
-rw-r--r--volk/kernels/volk/volk_16ic_deinterleave_16i_x2.h22
-rw-r--r--volk/kernels/volk/volk_16ic_deinterleave_real_16i.h22
-rw-r--r--volk/kernels/volk/volk_16ic_deinterleave_real_8i.h22
-rw-r--r--volk/kernels/volk/volk_16ic_magnitude_16i.h22
-rw-r--r--volk/kernels/volk/volk_16ic_s32f_deinterleave_32f_x2.h22
-rw-r--r--volk/kernels/volk/volk_16ic_s32f_deinterleave_real_32f.h22
-rw-r--r--volk/kernels/volk/volk_16ic_s32f_magnitude_32f.h22
-rw-r--r--volk/kernels/volk/volk_16u_byteswap.h74
-rw-r--r--volk/kernels/volk/volk_16u_byteswappuppet_16u.h55
-rw-r--r--volk/kernels/volk/volk_32f_accumulator_s32f.h22
-rw-r--r--volk/kernels/volk/volk_32f_acos_32f.h194
-rw-r--r--volk/kernels/volk/volk_32f_asin_32f.h189
-rw-r--r--volk/kernels/volk/volk_32f_atan_32f.h183
-rw-r--r--volk/kernels/volk/volk_32f_binary_slicer_32i.h22
-rw-r--r--volk/kernels/volk/volk_32f_binary_slicer_8i.h102
-rw-r--r--volk/kernels/volk/volk_32f_convert_64f.h94
-rw-r--r--volk/kernels/volk/volk_32f_cos_32f.h211
-rw-r--r--volk/kernels/volk/volk_32f_expfast_32f.h216
-rw-r--r--volk/kernels/volk/volk_32f_index_max_16u.h22
-rw-r--r--volk/kernels/volk/volk_32f_invsqrt_32f.h24
-rw-r--r--volk/kernels/volk/volk_32f_log2_32f.h332
-rw-r--r--volk/kernels/volk/volk_32f_s32f_32f_fm_detect_32f.h22
-rw-r--r--volk/kernels/volk/volk_32f_s32f_calc_spectral_noise_floor_32f.h22
-rw-r--r--volk/kernels/volk/volk_32f_s32f_convert_16i.h136
-rw-r--r--volk/kernels/volk/volk_32f_s32f_convert_32i.h22
-rw-r--r--volk/kernels/volk/volk_32f_s32f_convert_8i.h22
-rw-r--r--volk/kernels/volk/volk_32f_s32f_multiply_32f.h22
-rw-r--r--volk/kernels/volk/volk_32f_s32f_normalize.h22
-rw-r--r--volk/kernels/volk/volk_32f_s32f_power_32f.h22
-rw-r--r--volk/kernels/volk/volk_32f_s32f_stddev_32f.h22
-rw-r--r--volk/kernels/volk/volk_32f_sin_32f.h211
-rw-r--r--volk/kernels/volk/volk_32f_sqrt_32f.h22
-rw-r--r--volk/kernels/volk/volk_32f_stddev_and_mean_32f_x2.h22
-rw-r--r--volk/kernels/volk/volk_32f_tan_32f.h220
-rw-r--r--volk/kernels/volk/volk_32f_tanh_32f.h318
-rw-r--r--volk/kernels/volk/volk_32f_x2_add_32f.h24
-rw-r--r--volk/kernels/volk/volk_32f_x2_divide_32f.h22
-rw-r--r--volk/kernels/volk/volk_32f_x2_dot_prod_16i.h22
-rw-r--r--volk/kernels/volk/volk_32f_x2_dot_prod_32f.h22
-rw-r--r--volk/kernels/volk/volk_32f_x2_interleave_32fc.h24
-rw-r--r--volk/kernels/volk/volk_32f_x2_max_32f.h24
-rw-r--r--volk/kernels/volk/volk_32f_x2_min_32f.h22
-rw-r--r--volk/kernels/volk/volk_32f_x2_multiply_32f.h22
-rw-r--r--volk/kernels/volk/volk_32f_x2_pow_32f.h298
-rw-r--r--volk/kernels/volk/volk_32f_x2_s32f_interleave_16ic.h22
-rw-r--r--volk/kernels/volk/volk_32f_x2_subtract_32f.h22
-rw-r--r--volk/kernels/volk/volk_32f_x3_sum_of_poly_32f.h22
-rw-r--r--volk/kernels/volk/volk_32fc_32f_dot_prod_32fc.h30
-rw-r--r--volk/kernels/volk/volk_32fc_32f_multiply_32fc.h22
-rw-r--r--volk/kernels/volk/volk_32fc_conjugate_32fc.h98
-rw-r--r--volk/kernels/volk/volk_32fc_deinterleave_32f_x2.h104
-rw-r--r--volk/kernels/volk/volk_32fc_deinterleave_64f_x2.h124
-rw-r--r--volk/kernels/volk/volk_32fc_deinterleave_imag_32f.h93
-rw-r--r--volk/kernels/volk/volk_32fc_deinterleave_real_32f.h48
-rw-r--r--volk/kernels/volk/volk_32fc_deinterleave_real_64f.h22
-rw-r--r--volk/kernels/volk/volk_32fc_index_max_16u.h22
-rw-r--r--volk/kernels/volk/volk_32fc_magnitude_32f.h114
-rw-r--r--volk/kernels/volk/volk_32fc_magnitude_squared_32f.h110
-rw-r--r--volk/kernels/volk/volk_32fc_s32f_atan2_32f.h22
-rw-r--r--volk/kernels/volk/volk_32fc_s32f_deinterleave_real_16i.h22
-rw-r--r--volk/kernels/volk/volk_32fc_s32f_magnitude_16i.h22
-rw-r--r--volk/kernels/volk/volk_32fc_s32f_power_32fc.h22
-rw-r--r--volk/kernels/volk/volk_32fc_s32f_power_spectrum_32f.h22
-rw-r--r--volk/kernels/volk/volk_32fc_s32f_x2_power_spectral_density_32f.h114
-rw-r--r--volk/kernels/volk/volk_32fc_s32fc_multiply_32fc.h155
-rw-r--r--volk/kernels/volk/volk_32fc_s32fc_rotatorpuppet_32fc.h22
-rw-r--r--volk/kernels/volk/volk_32fc_s32fc_x2_rotator_32fc.h22
-rw-r--r--volk/kernels/volk/volk_32fc_x2_conjugate_dot_prod_32fc.h71
-rw-r--r--volk/kernels/volk/volk_32fc_x2_dot_prod_32fc.h139
-rw-r--r--volk/kernels/volk/volk_32fc_x2_multiply_32fc.h120
-rw-r--r--volk/kernels/volk/volk_32fc_x2_multiply_conjugate_32fc.h128
-rw-r--r--volk/kernels/volk/volk_32fc_x2_s32f_square_dist_scalar_mult_32f.h22
-rw-r--r--volk/kernels/volk/volk_32fc_x2_square_dist_32f.h22
-rw-r--r--volk/kernels/volk/volk_32i_s32f_convert_32f.h22
-rw-r--r--volk/kernels/volk/volk_32i_x2_and_32i.h56
-rw-r--r--volk/kernels/volk/volk_32i_x2_or_32i.h56
-rw-r--r--volk/kernels/volk/volk_32u_byteswap.h77
-rw-r--r--volk/kernels/volk/volk_32u_byteswappuppet_32u.h45
-rw-r--r--volk/kernels/volk/volk_32u_popcnt.h22
-rw-r--r--volk/kernels/volk/volk_32u_popcntpuppet_32u.h47
-rw-r--r--volk/kernels/volk/volk_64f_convert_32f.h22
-rw-r--r--volk/kernels/volk/volk_64f_x2_max_64f.h22
-rw-r--r--volk/kernels/volk/volk_64f_x2_min_64f.h22
-rw-r--r--volk/kernels/volk/volk_64u_byteswap.h77
-rw-r--r--volk/kernels/volk/volk_64u_byteswappuppet_64u.h46
-rw-r--r--volk/kernels/volk/volk_64u_popcnt.h42
-rw-r--r--volk/kernels/volk/volk_64u_popcntpuppet_64u.h58
-rw-r--r--volk/kernels/volk/volk_8i_convert_16i.h22
-rw-r--r--volk/kernels/volk/volk_8i_s32f_convert_32f.h22
-rw-r--r--volk/kernels/volk/volk_8ic_deinterleave_16i_x2.h103
-rw-r--r--volk/kernels/volk/volk_8ic_deinterleave_real_16i.h70
-rw-r--r--volk/kernels/volk/volk_8ic_deinterleave_real_8i.h80
-rw-r--r--volk/kernels/volk/volk_8ic_s32f_deinterleave_32f_x2.h22
-rw-r--r--volk/kernels/volk/volk_8ic_s32f_deinterleave_real_32f.h22
-rw-r--r--volk/kernels/volk/volk_8ic_x2_multiply_conjugate_16ic.h22
-rw-r--r--volk/kernels/volk/volk_8ic_x2_s32f_multiply_conjugate_32fc.h22
-rw-r--r--volk/kernels/volk/volk_8u_conv_k7_r2puppet_8u.h22
-rw-r--r--volk/kernels/volk/volk_8u_x4_conv_k7_r2_8u.h22
-rw-r--r--volk/lib/CMakeLists.txt15
-rw-r--r--volk/lib/qa_utils.cc34
-rw-r--r--volk/lib/qa_utils.h43
-rw-r--r--volk/lib/testqa.cc14
343 files changed, 18219 insertions, 6277 deletions
diff --git a/CMakeLists.txt b/CMakeLists.txt
index 7f617df901..858a7d6a2f 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -46,8 +46,8 @@ message(STATUS "Build type set to ${CMAKE_BUILD_TYPE}.")
# Set the version information here
set(VERSION_INFO_MAJOR_VERSION 3)
set(VERSION_INFO_API_COMPAT 7)
-set(VERSION_INFO_MINOR_VERSION 5)
-set(VERSION_INFO_MAINT_VERSION 1)
+set(VERSION_INFO_MINOR_VERSION 6)
+set(VERSION_INFO_MAINT_VERSION git)
include(GrVersion) #setup version info
# Append -O2 optimization flag for Debug builds
diff --git a/cmake/Modules/FindUHD.cmake b/cmake/Modules/FindUHD.cmake
index cfb89b11ce..21cb0942c3 100644
--- a/cmake/Modules/FindUHD.cmake
+++ b/cmake/Modules/FindUHD.cmake
@@ -2,7 +2,7 @@
# Find the library for the USRP Hardware Driver
########################################################################
-# make this file non-reentrant
+# make this file non-reentrant within the current context
if(__INCLUDED_FIND_UHD_CMAKE)
return()
endif()
@@ -20,6 +20,12 @@ unset(CMAKE_MODULE_PATH)
# handle REQUIRED internally later
unset(UHD_FOUND)
+# set that UHDConfig.cmake was not used. Have to use the ENV, since
+# UHDConfigVersion does not allow CACHE changes and UHDConfig might
+# not allow CACHE changes.
+set(ENV{UHD_CONFIG_USED} FALSE)
+set(ENV{UHD_CONFIG_VERSION_USED} FALSE)
+
# was the version specified?
unset(LOCAL_UHD_FIND_VERSION)
if(UHD_FIND_VERSION)
@@ -42,10 +48,10 @@ find_package(
# restore CMAKE_MODULE_PATH
set(CMAKE_MODULE_PATH ${SAVED_CMAKE_MODULE_PATH})
-# check if UHD was found above
-if(NOT UHD_FOUND)
+# check if UHDConfig was used above
+if(NOT $ENV{UHD_CONFIG_VERSION_USED})
- # Not found; try the "old" method (not as robust)
+ # Not used; try the "old" method (not as robust)
include(FindPkgConfig)
pkg_check_modules(PC_UHD uhd)
@@ -67,7 +73,7 @@ if(NOT UHD_FOUND)
PATHS /usr/local/lib
/usr/lib
)
-endif(NOT UHD_FOUND)
+endif(NOT $ENV{UHD_CONFIG_VERSION_USED})
if(UHD_LIBRARIES AND UHD_INCLUDE_DIRS)
@@ -79,7 +85,9 @@ if(UHD_LIBRARIES AND UHD_INCLUDE_DIRS)
mark_as_advanced(UHD_LIBRARIES UHD_INCLUDE_DIRS)
elseif(UHD_FIND_REQUIRED)
-
- message(FATAL_ERROR "UHD is required, but was not found.")
-
+ if($ENV{UHD_CONFIG_VERSION_USED} AND NOT $ENV{UHD_CONFIG_USED})
+ message(FATAL_ERROR "The found UHD version ($ENV{UHD_PACKAGE_VERSION}) is not compatible with the version required (${UHD_FIND_VERSION}).")
+ else()
+ message(FATAL_ERROR "UHD is required, but was not found.")
+ endif()
endif()
diff --git a/docs/doxygen/Doxyfile.in b/docs/doxygen/Doxyfile.in
index 3b82e2c40c..3f558526e7 100644
--- a/docs/doxygen/Doxyfile.in
+++ b/docs/doxygen/Doxyfile.in
@@ -142,26 +142,51 @@ STRIP_FROM_PATH =
# are normally passed to the compiler using the -I flag.
STRIP_FROM_INC_PATH = @CMAKE_SOURCE_DIR@/gnuradio-runtime/include \
+ @CMAKE_BINARY_DIR@/gnuradio-runtime/include \
@CMAKE_SOURCE_DIR@/gr-analog/include \
+ @CMAKE_BINARY_DIR@/gr-analog/include \
@CMAKE_SOURCE_DIR@/gr-atsc/include \
+ @CMAKE_BINARY_DIR@/gr-atsc/include \
@CMAKE_SOURCE_DIR@/gr-audio/include \
+ @CMAKE_BINARY_DIR@/gr-audio/include \
@CMAKE_SOURCE_DIR@/gr-blocks/include \
+ @CMAKE_BINARY_DIR@/gr-blocks/include \
@CMAKE_SOURCE_DIR@/gr-channels/include \
+ @CMAKE_BINARY_DIR@/gr-channels/include \
@CMAKE_SOURCE_DIR@/gr-comedi/include \
+ @CMAKE_BINARY_DIR@/gr-comedi/include \
@CMAKE_SOURCE_DIR@/gr-digital/include \
+ @CMAKE_BINARY_DIR@/gr-digital/include \
+ @CMAKE_SOURCE_DIR@/gr-dtv/include \
+ @CMAKE_BINARY_DIR@/gr-dtv/include \
@CMAKE_SOURCE_DIR@/gr-fcd/include \
+ @CMAKE_BINARY_DIR@/gr-fcd/include \
@CMAKE_SOURCE_DIR@/gr-fec/include \
+ @CMAKE_BINARY_DIR@/gr-fec/include \
@CMAKE_SOURCE_DIR@/gr-fft/include \
+ @CMAKE_BINARY_DIR@/gr-fft/include \
@CMAKE_SOURCE_DIR@/gr-filter/include \
+ @CMAKE_BINARY_DIR@/gr-filter/include \
@CMAKE_SOURCE_DIR@/gr-noaa/include \
+ @CMAKE_BINARY_DIR@/gr-noaa/include \
@CMAKE_SOURCE_DIR@/gr-pager/include \
+ @CMAKE_BINARY_DIR@/gr-pager/include \
@CMAKE_SOURCE_DIR@/gr-qtgui/include \
+ @CMAKE_BINARY_DIR@/gr-qtgui/include \
@CMAKE_SOURCE_DIR@/gr-trellis/include \
+ @CMAKE_BINARY_DIR@/gr-trellis/include \
@CMAKE_SOURCE_DIR@/gr-uhd/include \
+ @CMAKE_BINARY_DIR@/gr-uhd/include \
@CMAKE_SOURCE_DIR@/gr-video-sdl/include \
+ @CMAKE_BINARY_DIR@/gr-video-sdl/include \
@CMAKE_SOURCE_DIR@/gr-vocoder/include \
+ @CMAKE_BINARY_DIR@/gr-vocoder/include \
+ @CMAKE_SOURCE_DIR@/gr-wavelet/include \
+ @CMAKE_BINARY_DIR@/gr-wavelet/include \
@CMAKE_SOURCE_DIR@/gr-wxgui/include \
- @CMAKE_SOURCE_DIR@/volk/include
+ @CMAKE_BINARY_DIR@/gr-wxgui/include \
+ @CMAKE_SOURCE_DIR@/volk/include \
+ @CMAKE_BINARY_DIR@/volk/include
# If the SHORT_NAMES tag is set to YES, doxygen will generate much shorter
# (but less readable) file names. This can be useful if your file system
diff --git a/docs/doxygen/other/pmt.dox b/docs/doxygen/other/pmt.dox
index bc7f870ccd..51e1865d39 100644
--- a/docs/doxygen/other/pmt.dox
+++ b/docs/doxygen/other/pmt.dox
@@ -477,4 +477,21 @@ pmt::pmt_t a pmt::from_double(1.0);
std::cout << "The PMT a contains " << a << std::endl;
\endcode
+
+\section pmt_python Conversion between Python Objects and PMTs
+
+Although PMTs can be manipulated in Python using the Python versions
+of the C++ interfaces, there are some additional goodies that make it
+easier to work with PMTs in python. There are functions to automate
+the conversion between PMTs and Python types for booleans, strings,
+integers, longs, floats, complex numbers, dictionaries, lists, tuples
+and combinations thereof.
+
+Two functions capture most of this functionality:
+
+\code
+pmt.to_pmt # Converts a python object to a PMT.
+pmt.to_python # Converts a PMT into a python object.
+\endcode
+
*/
diff --git a/docs/doxygen/other/stream_tags.dox b/docs/doxygen/other/stream_tags.dox
index 851740984e..d48ec1ddee 100644
--- a/docs/doxygen/other/stream_tags.dox
+++ b/docs/doxygen/other/stream_tags.dox
@@ -61,7 +61,10 @@ at <em>nitems_written(0)+i</em> for the 0th output port.
\section stream_tags_api Stream Tags API
The stream tags API consists of four functions, two to add and two to
-get the stream tags. These functions are:
+get the stream tags. These functions are only meant to be accessed
+within a call to general_work/work. While they can be called elsewhere
+in time by a block, the behavior outside of work is undefined without
+exact knowledge of the item counts in the buffers.
\li gr::block::add_item_tag: Adds an item tag to a particular output port using a
gr::tag_t data type.
diff --git a/gnuradio-runtime/include/gnuradio/block.h b/gnuradio-runtime/include/gnuradio/block.h
index a033e0ac27..4a534b7f46 100644
--- a/gnuradio-runtime/include/gnuradio/block.h
+++ b/gnuradio-runtime/include/gnuradio/block.h
@@ -221,7 +221,8 @@ namespace gr {
/*!
* \brief Tell the scheduler \p how_many_items of input stream \p
- * which_input were consumed.
+ * which_input were consumed.
+ * This function should be called at the end of work() or general_work(), after all processing is finished.
*/
void consume(int which_input, int how_many_items);
@@ -503,6 +504,11 @@ namespace gr {
float pc_work_time_total();
/*!
+ * \brief Gets average throughput.
+ */
+ float pc_throughput_avg();
+
+ /*!
* \brief Resets the performance counters
*/
void reset_perf_counters();
@@ -636,7 +642,7 @@ namespace gr {
void add_item_tag(unsigned int which_output, const tag_t &tag);
/*!
- * \brief Removes a tag from the given input buffer.
+ * \brief DEPRECATED. Will be removed in 3.8.
*
* \param which_input an integer of which input stream to remove the tag from
* \param abs_offset a uint64 number of the absolute item number
@@ -662,9 +668,7 @@ namespace gr {
}
/*!
- * \brief Removes a tag from the given input buffer.
- *
- * If no such tag is found, does nothing.
+ * \brief DEPRECATED. Will be removed in 3.8.
*
* \param which_input an integer of which input stream to remove the tag from
* \param tag the tag object to remove
diff --git a/gnuradio-runtime/include/gnuradio/block_detail.h b/gnuradio-runtime/include/gnuradio/block_detail.h
index 41568c8ab3..916c0a46c1 100644
--- a/gnuradio-runtime/include/gnuradio/block_detail.h
+++ b/gnuradio-runtime/include/gnuradio/block_detail.h
@@ -219,6 +219,7 @@ namespace gr {
float pc_output_buffers_full_avg(size_t which);
std::vector<float> pc_output_buffers_full_avg();
float pc_work_time_avg();
+ float pc_throughput_avg();
float pc_noutput_items_var();
float pc_nproduced_var();
@@ -246,6 +247,9 @@ namespace gr {
float d_ins_noutput_items;
float d_avg_noutput_items;
float d_var_noutput_items;
+ float d_total_noutput_items;
+ gr::high_res_timer_type d_pc_start_time;
+ gr::high_res_timer_type d_pc_last_work_time;
float d_ins_nproduced;
float d_avg_nproduced;
float d_var_nproduced;
@@ -260,6 +264,7 @@ namespace gr {
float d_avg_work_time;
float d_var_work_time;
float d_total_work_time;
+ float d_avg_throughput;
float d_pc_counter;
block_detail(unsigned int ninputs, unsigned int noutputs);
diff --git a/gnuradio-runtime/include/gnuradio/buffer.h b/gnuradio-runtime/include/gnuradio/buffer.h
index e2d5760e59..c0c9f3d39d 100644
--- a/gnuradio-runtime/include/gnuradio/buffer.h
+++ b/gnuradio-runtime/include/gnuradio/buffer.h
@@ -28,7 +28,7 @@
#include <gnuradio/tags.h>
#include <boost/weak_ptr.hpp>
#include <gnuradio/thread/thread.h>
-#include <deque>
+#include <map>
namespace gr {
@@ -125,8 +125,10 @@ namespace gr {
*/
void prune_tags(uint64_t max_time);
- std::deque<tag_t>::iterator get_tags_begin() { return d_item_tags.begin(); }
- std::deque<tag_t>::iterator get_tags_end() { return d_item_tags.end(); }
+ std::multimap<uint64_t,tag_t>::iterator get_tags_begin() { return d_item_tags.begin(); }
+ std::multimap<uint64_t,tag_t>::iterator get_tags_end() { return d_item_tags.end(); }
+ std::multimap<uint64_t,tag_t>::iterator get_tags_lower_bound(uint64_t x) { return d_item_tags.lower_bound(x); }
+ std::multimap<uint64_t,tag_t>::iterator get_tags_upper_bound(uint64_t x) { return d_item_tags.upper_bound(x); }
// -------------------------------------------------------------------------
@@ -157,7 +159,7 @@ namespace gr {
unsigned int d_write_index; // in items [0,d_bufsize)
uint64_t d_abs_write_offset; // num items written since the start
bool d_done;
- std::deque<tag_t> d_item_tags;
+ std::multimap<uint64_t,tag_t> d_item_tags;
uint64_t d_last_min_items_read;
unsigned index_add(unsigned a, unsigned b)
diff --git a/gnuradio-runtime/include/gnuradio/logger.h.in b/gnuradio-runtime/include/gnuradio/logger.h.in
index 05367a1873..941ce75af3 100644
--- a/gnuradio-runtime/include/gnuradio/logger.h.in
+++ b/gnuradio-runtime/include/gnuradio/logger.h.in
@@ -844,8 +844,11 @@ namespace gr {
* block, we use 'alias()' for this value, and this is set up for us
* automatically in gr::block.
*/
- GR_RUNTIME_API bool configure_default_loggers(gr::logger_ptr &l, gr::logger_ptr &d,
- const std::string name);
+ GR_RUNTIME_API bool configure_default_loggers(gr::logger_ptr &l, gr::logger_ptr &d,
+ const std::string name);
+
+ GR_RUNTIME_API bool update_logger_alias(const std::string &name, const std::string &alias);
+
} /* namespace gr */
diff --git a/gnuradio-runtime/include/gnuradio/tagged_stream_block.h b/gnuradio-runtime/include/gnuradio/tagged_stream_block.h
index 1fe92ee25a..86343f281d 100644
--- a/gnuradio-runtime/include/gnuradio/tagged_stream_block.h
+++ b/gnuradio-runtime/include/gnuradio/tagged_stream_block.h
@@ -97,6 +97,8 @@ namespace gr {
*/
void /* final */ forecast (int noutput_items, gr_vector_int &ninput_items_required);
+ bool check_topology(int ninputs, int /* noutputs */);
+
/*!
* - Reads the number of input items from the tags using parse_length_tags()
* - Checks there's enough data on the input and output buffers
diff --git a/gnuradio-runtime/include/pmt/pmt.h b/gnuradio-runtime/include/pmt/pmt.h
index 3e17571b23..cb6fdf44d5 100644
--- a/gnuradio-runtime/include/pmt/pmt.h
+++ b/gnuradio-runtime/include/pmt/pmt.h
@@ -201,6 +201,7 @@ PMT_API bool is_real(pmt_t obj);
//! Return the pmt value that represents double \p x.
PMT_API pmt_t from_double(double x);
+PMT_API pmt_t from_float(float x);
/*!
* \brief Convert pmt to double if possible.
@@ -211,6 +212,15 @@ PMT_API pmt_t from_double(double x);
*/
PMT_API double to_double(pmt_t x);
+/*!
+ * \brief Convert pmt to float if possible.
+ *
+ * This basically is to_double() with a type-cast; the PMT stores
+ * the value as a double in any case. Use this when strict typing
+ * is required.
+ */
+PMT_API float to_float(pmt_t x);
+
/*
* ------------------------------------------------------------------------
* Complex
diff --git a/gnuradio-runtime/lib/basic_block.cc b/gnuradio-runtime/lib/basic_block.cc
index 686c1d6e65..09d2eb2b3a 100644
--- a/gnuradio-runtime/lib/basic_block.cc
+++ b/gnuradio-runtime/lib/basic_block.cc
@@ -26,6 +26,7 @@
#include <gnuradio/basic_block.h>
#include <gnuradio/block_registry.h>
+#include <gnuradio/logger.h>
#include <stdexcept>
#include <sstream>
#include <iostream>
@@ -82,6 +83,7 @@ namespace gr {
// set the block's alias
d_symbol_alias = name;
+ update_logger_alias(symbol_name(), d_symbol_alias);
}
// ** Message passing interface **
diff --git a/gnuradio-runtime/lib/block.cc b/gnuradio-runtime/lib/block.cc
index a15fb89c85..9173094e53 100644
--- a/gnuradio-runtime/lib/block.cc
+++ b/gnuradio-runtime/lib/block.cc
@@ -60,7 +60,7 @@ namespace gr {
message_port_register_in(pmt::mp("system"));
set_msg_handler(pmt::mp("system"), boost::bind(&block::system_handler, this, _1));
- configure_default_loggers(d_logger, d_debug_logger, alias());
+ configure_default_loggers(d_logger, d_debug_logger, symbol_name());
}
block::~block()
@@ -682,6 +682,16 @@ namespace gr {
}
}
+ float
+ block::pc_throughput_avg() {
+ if(d_detail) {
+ return d_detail->pc_throughput_avg();
+ }
+ else {
+ return 0;
+ }
+ }
+
void
block::reset_perf_counters()
{
diff --git a/gnuradio-runtime/lib/block_detail.cc b/gnuradio-runtime/lib/block_detail.cc
index 77c457cf7f..9463e8d13b 100644
--- a/gnuradio-runtime/lib/block_detail.cc
+++ b/gnuradio-runtime/lib/block_detail.cc
@@ -46,6 +46,7 @@ namespace gr {
d_ins_noutput_items(0),
d_avg_noutput_items(0),
d_var_noutput_items(0),
+ d_total_noutput_items(0),
d_ins_nproduced(0),
d_avg_nproduced(0),
d_var_nproduced(0),
@@ -58,9 +59,11 @@ namespace gr {
d_ins_work_time(0),
d_avg_work_time(0),
d_var_work_time(0),
+ d_avg_throughput(0),
d_pc_counter(0)
{
s_ncurrently_allocated++;
+ d_pc_start_time = gr::high_res_timer_now();
}
block_detail::~block_detail()
@@ -279,6 +282,8 @@ namespace gr {
d_ins_noutput_items = noutput_items;
d_avg_noutput_items = noutput_items;
d_var_noutput_items = 0;
+ d_total_noutput_items = noutput_items;
+ d_pc_start_time = (float)gr::high_res_timer_now();
for(size_t i=0; i < d_input.size(); i++) {
gr::thread::scoped_lock guard(*d_input[i]->mutex());
float pfull = static_cast<float>(d_input[i]->items_available()) /
@@ -312,6 +317,10 @@ namespace gr {
d_ins_noutput_items = noutput_items;
d_avg_noutput_items = d_avg_noutput_items + d/d_pc_counter;
d_var_noutput_items = d_var_noutput_items + d*d;
+ d_total_noutput_items += noutput_items;
+ d_pc_last_work_time = gr::high_res_timer_now();
+ float monitor_time = (float)(d_pc_last_work_time - d_pc_start_time) / (float)gr::high_res_timer_tps();
+ d_avg_throughput = d_total_noutput_items / monitor_time;
for(size_t i=0; i < d_input.size(); i++) {
gr::thread::scoped_lock guard(*d_input[i]->mutex());
@@ -501,4 +510,8 @@ namespace gr {
return d_total_work_time;
}
+ float
+ block_detail::pc_throughput_avg() {
+ return d_avg_throughput;
+ }
} /* namespace gr */
diff --git a/gnuradio-runtime/lib/buffer.cc b/gnuradio-runtime/lib/buffer.cc
index 162324e590..f00e9a04bf 100644
--- a/gnuradio-runtime/lib/buffer.cc
+++ b/gnuradio-runtime/lib/buffer.cc
@@ -23,7 +23,7 @@
#ifdef HAVE_CONFIG_H
#include "config.h"
#endif
-
+#include <algorithm>
#include <gnuradio/buffer.h>
#include <gnuradio/math.h>
#include "vmcircbuf.h"
@@ -225,16 +225,16 @@ namespace gr {
buffer::add_item_tag(const tag_t &tag)
{
gr::thread::scoped_lock guard(*mutex());
- d_item_tags.push_back(tag);
+ d_item_tags.insert(std::pair<uint64_t,tag_t>(tag.offset,tag));
}
void
buffer::remove_item_tag(const tag_t &tag, long id)
{
gr::thread::scoped_lock guard(*mutex());
- for(std::deque<tag_t>::iterator it = d_item_tags.begin(); it != d_item_tags.end(); ++it) {
- if(*it == tag) {
- (*it).marked_deleted.push_back(id);
+ for(std::multimap<uint64_t,tag_t>::iterator it = d_item_tags.lower_bound(tag.offset); it != d_item_tags.upper_bound(tag.offset); ++it) {
+ if((*it).second == tag) {
+ (*it).second.marked_deleted.push_back(id);
}
}
}
@@ -250,25 +250,9 @@ namespace gr {
If this function is used elsewhere, remember to lock the
buffer's mutex al la the scoped_lock line below.
*/
- //gr::thread::scoped_lock guard(*mutex());
- std::deque<tag_t>::iterator itr = d_item_tags.begin();
-
- uint64_t item_time;
-
- // Since tags are not guarenteed to be in any particular order, we
- // need to erase here instead of pop_front. An erase in the middle
- // invalidates all iterators; so this resets the iterator to find
- // more. Mostly, we wil be erasing from the front and
- // therefore lose little time this way.
- while(itr != d_item_tags.end()) {
- item_time = (*itr).offset;
- if(item_time+d_max_reader_delay + bufsize() < max_time) {
- d_item_tags.erase(itr);
- itr = d_item_tags.begin();
- }
- else
- itr++;
- }
+ std::multimap<uint64_t, tag_t>::iterator end_itr = d_item_tags.lower_bound(max_time);
+ std::multimap<uint64_t, tag_t>::iterator begin_itr = d_item_tags.begin();
+ d_item_tags.erase(begin_itr, end_itr);
}
long
@@ -333,30 +317,28 @@ namespace gr {
buffer_reader::get_tags_in_range(std::vector<tag_t> &v,
uint64_t abs_start,
uint64_t abs_end,
- long id)
+ long id)
{
gr::thread::scoped_lock guard(*mutex());
v.resize(0);
- std::deque<tag_t>::iterator itr = d_buffer->get_tags_begin();
+ std::multimap<uint64_t,tag_t>::iterator itr = d_buffer->get_tags_lower_bound(abs_start);
+ std::multimap<uint64_t,tag_t>::iterator itr_end = d_buffer->get_tags_upper_bound(abs_end);
uint64_t item_time;
- while(itr != d_buffer->get_tags_end()) {
- item_time = (*itr).offset + d_attr_delay;
-
+ while(itr != itr_end) {
+ item_time = (*itr).second.offset + d_attr_delay;
if((item_time >= abs_start) && (item_time < abs_end)) {
- std::vector<long>::iterator id_itr;
- id_itr = std::find(itr->marked_deleted.begin(), itr->marked_deleted.end(), id);
-
+ std::vector<long>::iterator id_itr;
+ id_itr = std::find(itr->second.marked_deleted.begin(), itr->second.marked_deleted.end(), id);
// If id is not in the vector of marked blocks
- if(id_itr == itr->marked_deleted.end()) {
- tag_t t = *itr;
+ if(id_itr == itr->second.marked_deleted.end()) {
+ tag_t t = (*itr).second;
t.offset += d_attr_delay;
- v.push_back(t);
- v.back().marked_deleted.clear();
- }
+ v.push_back(t);
+ v.back().marked_deleted.clear();
+ }
}
-
itr++;
}
}
diff --git a/gnuradio-runtime/lib/logger.cc b/gnuradio-runtime/lib/logger.cc
index bb1d4b4c33..13c8391c8e 100644
--- a/gnuradio-runtime/lib/logger.cc
+++ b/gnuradio-runtime/lib/logger.cc
@@ -417,4 +417,35 @@ namespace gr {
return false;
}
+ bool
+ update_logger_alias(const std::string &name, const std::string &alias)
+ {
+#ifdef ENABLE_GR_LOG
+#ifdef HAVE_LOG4CPP
+ prefs *p = prefs::singleton();
+ std::string log_file = p->get_string("LOG", "log_file", "");
+ std::string debug_file = p->get_string("LOG", "debug_file", "");
+
+ GR_LOG_GETLOGGER(LOG, "gr_log." + name);
+ if(log_file.size() > 0) {
+ if(log_file == "stdout") {
+ boost::format str("gr::log :%%p: %1% - %%m%%n");
+ GR_LOG_SET_CONSOLE_APPENDER(LOG, "cout", boost::str(str % alias));
+ }
+ else if(log_file == "stderr") {
+ boost::format str("gr::log :%%p: %1% - %%m%%n");
+ GR_LOG_SET_CONSOLE_APPENDER(LOG, "cerr", boost::str(str % alias));
+ }
+ else {
+ boost::format str("%%r :%%p: %1% - %%m%%n");
+ GR_LOG_SET_FILE_APPENDER(LOG, log_file, true, boost::str(str % alias));
+ }
+ }
+ return true;
+#endif /* HAVE_LOG4CPP */
+#endif /* ENABLE_GR_LOG */
+
+ return false;
+ }
+
} /* namespace gr */
diff --git a/gnuradio-runtime/lib/pmt/pmt.cc b/gnuradio-runtime/lib/pmt/pmt.cc
index 082b98a80d..da830e1aed 100644
--- a/gnuradio-runtime/lib/pmt/pmt.cc
+++ b/gnuradio-runtime/lib/pmt/pmt.cc
@@ -368,6 +368,12 @@ from_double(double x)
return pmt_t(new pmt_real(x));
}
+pmt_t
+from_float(float x)
+{
+ return pmt_t(new pmt_real(x));
+}
+
double
to_double(pmt_t x)
{
@@ -379,6 +385,12 @@ to_double(pmt_t x)
throw wrong_type("pmt_to_double", x);
}
+float
+to_float(pmt_t x)
+{
+ return float(to_double(x));
+}
+
////////////////////////////////////////////////////////////////////////////
// Complex
////////////////////////////////////////////////////////////////////////////
diff --git a/gnuradio-runtime/lib/pmt/qa_pmt_prims.cc b/gnuradio-runtime/lib/pmt/qa_pmt_prims.cc
index 2f46b014db..2b3ca32293 100644
--- a/gnuradio-runtime/lib/pmt/qa_pmt_prims.cc
+++ b/gnuradio-runtime/lib/pmt/qa_pmt_prims.cc
@@ -125,6 +125,15 @@ qa_pmt_prims::test_reals()
CPPUNIT_ASSERT_EQUAL(-1.0, pmt::to_double(m1));
CPPUNIT_ASSERT_EQUAL(1.0, pmt::to_double(p1));
CPPUNIT_ASSERT_EQUAL(1.0, pmt::to_double(pmt::from_long(1)));
+
+ pmt::pmt_t p2 = pmt::from_float(1);
+ pmt::pmt_t m2 = pmt::from_float(-1);
+ CPPUNIT_ASSERT(pmt::is_real(p2));
+ CPPUNIT_ASSERT(pmt::is_real(m2));
+ CPPUNIT_ASSERT_THROW(pmt::to_float(pmt::PMT_T), pmt::wrong_type);
+ CPPUNIT_ASSERT_EQUAL(float(-1.0), pmt::to_float(m2));
+ CPPUNIT_ASSERT_EQUAL(float(1.0), pmt::to_float(p2));
+ CPPUNIT_ASSERT_EQUAL(float(1.0), pmt::to_float(pmt::from_long(1)));
}
void
diff --git a/gnuradio-runtime/lib/tagged_stream_block.cc b/gnuradio-runtime/lib/tagged_stream_block.cc
index c6d5fc1fec..252a235fbf 100644
--- a/gnuradio-runtime/lib/tagged_stream_block.cc
+++ b/gnuradio-runtime/lib/tagged_stream_block.cc
@@ -89,6 +89,14 @@ namespace gr {
return;
}
+ bool
+ tagged_stream_block::check_topology(int ninputs, int /* noutputs */)
+ {
+ d_n_input_items_reqd.resize(ninputs, 0);
+ return true;
+ }
+
+
int
tagged_stream_block::general_work(int noutput_items,
gr_vector_int &ninput_items,
@@ -99,7 +107,9 @@ namespace gr {
return work(noutput_items, ninput_items, input_items, output_items);
}
- if(d_n_input_items_reqd[0] == 0) { // Otherwise, it's already set from a previous call
+ // Read TSB tags, unless we...
+ // ...don't have inputs or ... ... we already set it in a previous run.
+ if(!d_n_input_items_reqd.empty() && d_n_input_items_reqd[0] == 0) {
std::vector<std::vector<tag_t> > tags(input_items.size(), std::vector<tag_t>());
for(unsigned i = 0; i < input_items.size(); i++) {
get_tags_in_range(tags[i], i, nitems_read(i), nitems_read(i)+1);
diff --git a/gnuradio-runtime/python/gnuradio/gr/hier_block2.py b/gnuradio-runtime/python/gnuradio/gr/hier_block2.py
index d7cea3a9a3..3bc1e2e111 100644
--- a/gnuradio-runtime/python/gnuradio/gr/hier_block2.py
+++ b/gnuradio-runtime/python/gnuradio/gr/hier_block2.py
@@ -1,5 +1,5 @@
#
-# Copyright 2006,2007 Free Software Foundation, Inc.
+# Copyright 2006,2007,2014 Free Software Foundation, Inc.
#
# This file is part of GNU Radio
#
@@ -19,11 +19,49 @@
# Boston, MA 02110-1301, USA.
#
+from functools import wraps
+from itertools import imap
+
from runtime_swig import hier_block2_swig, dot_graph
import pmt
-#
-# This hack forces a 'has-a' relationship to look like an 'is-a' one.
+
+def _multiple_endpoints(func):
+ @wraps(func)
+ def wrapped(self, *points):
+ if not points:
+ raise ValueError("At least one block required for " + func.__name__)
+ elif len(points) == 1:
+ try:
+ block = points[0].to_basic_block()
+ except AttributeError:
+ raise ValueError("At least two endpoints required for " + func.__name__)
+ func(self, block)
+ else:
+ try:
+ endp = [(p, 0) if hasattr(p, 'to_basic_block') else p for p in points]
+ endp_pairs = imap(lambda i: endp[i:i+2], range(len(endp)-1))
+ for (src, src_port), (dst, dst_port) in endp_pairs:
+ func(self, src.to_basic_block(), src_port,
+ dst.to_basic_block(), dst_port)
+ except (ValueError, TypeError):
+ raise ValueError("Unable to coerce endpoint")
+ return wrapped
+
+
+def _optional_endpoints(func):
+ @wraps(func)
+ def wrapped(self, src, srcport, dst=None, dstport=None):
+ if dst is None and dstport is None:
+ try:
+ (src, srcport), (dst, dstport) = src, srcport
+ except (ValueError, TypeError):
+ raise ValueError("Unable to coerce endpoint")
+ func(self, src.to_basic_block(), srcport, dst.to_basic_block(), dstport)
+ return wrapped
+
+
+# This makes a 'has-a' relationship to look like an 'is-a' one.
#
# It allows Python classes to subclass this one, while passing through
# method calls to the C++ class shared pointer from SWIG.
@@ -42,17 +80,23 @@ class hier_block2(object):
"""
Create a hierarchical block with a given name and I/O signatures.
"""
- self._hb = hier_block2_swig(name, input_signature, output_signature)
+ self._impl = hier_block2_swig(name, input_signature, output_signature)
def __getattr__(self, name):
"""
Pass-through member requests to the C++ object.
"""
- if not hasattr(self, "_hb"):
- raise RuntimeError("hier_block2: invalid state--did you forget to call gr.hier_block2.__init__ in a derived class?")
- return getattr(self._hb, name)
+ if not hasattr(self, "_impl"):
+ raise RuntimeError(
+ "{0}: invalid state -- did you forget to call {0}.__init__ in "
+ "a derived class?".format(self.__class__.__name__))
+ return getattr(self._impl, name)
+
+ # FIXME: these should really be implemented
+ # in the original C++ class (gr_hier_block2), then they would all be inherited here
- def connect(self, *points):
+ @_multiple_endpoints
+ def connect(self, *args):
"""
Connect two or more block endpoints. An endpoint is either a (block, port)
tuple or a block instance. In the latter case, the port number is assumed
@@ -64,69 +108,52 @@ class hier_block2(object):
If multiple arguments are provided, connect will attempt to wire them in series,
interpreting the endpoints as inputs or outputs as appropriate.
"""
+ self.primitive_connect(*args)
- if len (points) < 1:
- raise ValueError, ("connect requires at least one endpoint; %d provided." % (len (points),))
- else:
- if len(points) == 1:
- self._hb.primitive_connect(points[0].to_basic_block())
- else:
- for i in range (1, len (points)):
- self._connect(points[i-1], points[i])
-
- def _connect(self, src, dst):
- (src_block, src_port) = self._coerce_endpoint(src)
- (dst_block, dst_port) = self._coerce_endpoint(dst)
- self._hb.primitive_connect(src_block.to_basic_block(), src_port,
- dst_block.to_basic_block(), dst_port)
-
- def _coerce_endpoint(self, endp):
- if hasattr(endp, 'to_basic_block'):
- return (endp, 0)
- else:
- if hasattr(endp, "__getitem__") and len(endp) == 2:
- return endp # Assume user put (block, port)
- else:
- raise ValueError("unable to coerce endpoint")
-
- def disconnect(self, *points):
+ @_multiple_endpoints
+ def disconnect(self, *args):
"""
- Disconnect two endpoints in the flowgraph.
+ Disconnect two or more endpoints in the flowgraph.
To disconnect the hierarchical block external inputs or outputs to internal block
inputs or outputs, use 'self' in the connect call.
If more than two arguments are provided, they are disconnected successively.
"""
+ self.primitive_disconnect(*args)
- if len (points) < 1:
- raise ValueError, ("disconnect requires at least one endpoint; %d provided." % (len (points),))
- else:
- if len (points) == 1:
- self._hb.primitive_disconnect(points[0].to_basic_block())
- else:
- for i in range (1, len (points)):
- self._disconnect(points[i-1], points[i])
+ @_optional_endpoints
+ def msg_connect(self, *args):
+ """
+ Connect two message ports in the flowgraph.
- def _disconnect(self, src, dst):
- (src_block, src_port) = self._coerce_endpoint(src)
- (dst_block, dst_port) = self._coerce_endpoint(dst)
- self._hb.primitive_disconnect(src_block.to_basic_block(), src_port,
- dst_block.to_basic_block(), dst_port)
+ If only two arguments are provided, they must be endpoints (block, port)
+ """
+ self.primitive_msg_connect(*args)
- def msg_connect(self, src, srcport, dst, dstport):
- self.primitive_msg_connect(src.to_basic_block(), srcport, dst.to_basic_block(), dstport);
+ @_optional_endpoints
+ def msg_disconnect(self, *args):
+ """
+ Disconnect two message ports in the flowgraph.
- def msg_disconnect(self, src, srcport, dst, dstport):
- self.primitive_msg_disconnect(src.to_basic_block(), srcport, dst.to_basic_block(), dstport);
+ If only two arguments are provided, they must be endpoints (block, port)
+ """
+ self.primitive_msg_disconnect(*args)
def message_port_register_hier_in(self, portname):
- self.primitive_message_port_register_hier_in(pmt.intern(portname));
+ """
+ Register a message port for this hier block
+ """
+ self.primitive_message_port_register_hier_in(pmt.intern(portname))
def message_port_register_hier_out(self, portname):
- self.primitive_message_port_register_hier_out(pmt.intern(portname));
+ """
+ Register a message port for this hier block
+ """
+ self.primitive_message_port_register_hier_out(pmt.intern(portname))
def dot_graph(self):
- '''Return graph representation in dot language'''
- return dot_graph(self._hb)
-
+ """
+ Return graph representation in dot language
+ """
+ return dot_graph(self._impl)
diff --git a/gnuradio-runtime/python/gnuradio/gr/qa_hier_block2.py b/gnuradio-runtime/python/gnuradio/gr/qa_hier_block2.py
new file mode 100644
index 0000000000..50b1562f3a
--- /dev/null
+++ b/gnuradio-runtime/python/gnuradio/gr/qa_hier_block2.py
@@ -0,0 +1,91 @@
+#
+# Copyright 2014 Free Software Foundation, Inc.
+#
+# This file is part of GNU Radio
+#
+# GNU Radio is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 3, or (at your option)
+# any later version.
+#
+# GNU Radio is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with GNU Radio; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 51 Franklin Street,
+# Boston, MA 02110-1301, USA.
+#
+
+from gnuradio import gr_unittest
+from gnuradio.gr.hier_block2 import _multiple_endpoints, _optional_endpoints
+
+
+class test_hier_block2(gr_unittest.TestCase):
+
+ def setUp(self):
+ self.call_log = []
+ self.Block = type("Block", (), {"to_basic_block": lambda bl: bl})
+
+ def test_f(self, *args):
+ """test doc"""
+ self.call_log.append(args)
+
+ multi = _multiple_endpoints(test_f)
+ opt = _optional_endpoints(test_f)
+
+ def test_000(self):
+ self.assertEqual(self.multi.__doc__, "test doc")
+ self.assertEqual(self.multi.__name__, "test_f")
+
+ def test_001(self):
+ b = self.Block()
+ self.multi(b)
+ self.assertEqual((b,), self.call_log[0])
+
+ def test_002(self):
+ b1, b2 = self.Block(), self.Block()
+ self.multi(b1, b2)
+ self.assertEqual([(b1, 0, b2, 0)], self.call_log)
+
+ def test_003(self):
+ b1, b2 = self.Block(), self.Block()
+ self.multi((b1, 1), (b2, 2))
+ self.assertEqual([(b1, 1, b2, 2)], self.call_log)
+
+ def test_004(self):
+ b1, b2, b3, b4 = [self.Block()] * 4
+ self.multi(b1, (b2, 5), b3, (b4, 0))
+ expected = [
+ (b1, 0, b2, 5),
+ (b2, 5, b3, 0),
+ (b3, 0, b4, 0),
+ ]
+ self.assertEqual(expected, self.call_log)
+
+ def test_005(self):
+ with self.assertRaises(ValueError) as c:
+ self.multi((self.Block(), 5))
+ self.assertIsInstance(c.exception, ValueError)
+
+ def test_006(self):
+ with self.assertRaises(ValueError) as c:
+ self.multi(self.Block(), (self.Block(), 5, 5))
+ self.assertIsInstance(c.exception, ValueError)
+
+ def test_007(self):
+ b1, b2 = self.Block(), self.Block()
+ self.opt(b1, "in", b2, "out")
+ self.assertEqual([(b1, "in", b2, "out")], self.call_log)
+
+ def test_008(self):
+ f, b1, b2 = self.multi, self.Block(), self.Block()
+ self.opt((b1, "in"), (b2, "out"))
+ self.assertEqual([(b1, "in", b2, "out")], self.call_log)
+
+
+if __name__ == '__main__':
+ gr_unittest.run(test_hier_block2, "test_hier_block2.xml")
+
diff --git a/gnuradio-runtime/python/gnuradio/gr/tag_utils.py b/gnuradio-runtime/python/gnuradio/gr/tag_utils.py
index cbca9d44ae..ba46e3f4d9 100644
--- a/gnuradio-runtime/python/gnuradio/gr/tag_utils.py
+++ b/gnuradio-runtime/python/gnuradio/gr/tag_utils.py
@@ -89,9 +89,22 @@ def python_to_tag(tag_struct):
tag.srcid = tag_struct[3]
good = True
+ elif(len(tag_struct) == 3):
+ if(isinstance(tag_struct[0], (int,long))):
+ tag.offset = tag_struct[0]
+ good = True
+
+ if(isinstance(tag_struct[1], pmt.pmt_swig.swig_int_ptr)):
+ tag.key = tag_struct[1]
+ good = True
+
+ if(isinstance(tag_struct[2], pmt.pmt_swig.swig_int_ptr)):
+ tag.value = tag_struct[2]
+ good = True
+
+ tag.srcid = pmt.PMT_F
+
if(good):
return tag
else:
return None
-
-
diff --git a/gnuradio-runtime/python/gnuradio/gr/top_block.py b/gnuradio-runtime/python/gnuradio/gr/top_block.py
index 58332c3421..f9872fc114 100644
--- a/gnuradio-runtime/python/gnuradio/gr/top_block.py
+++ b/gnuradio-runtime/python/gnuradio/gr/top_block.py
@@ -1,5 +1,5 @@
#
-# Copyright 2007 Free Software Foundation, Inc.
+# Copyright 2007,2014 Free Software Foundation, Inc.
#
# This file is part of GNU Radio
#
@@ -27,32 +27,31 @@ from runtime_swig import top_block_swig, \
#import gnuradio.gr.gr_threading as _threading
import gr_threading as _threading
-#
-# There is no problem that can't be solved with an additional
-# level of indirection...
-#
-# This kludge allows ^C to interrupt top_block.run and top_block.wait
-#
-# The problem that we are working around is that Python only services
-# signals (e.g., KeyboardInterrupt) in its main thread. If the main
-# thread is blocked in our C++ version of wait, even though Python's
-# SIGINT handler fires, and even though there may be other python
-# threads running, no one will know. Thus instead of directly waiting
-# in the thread that calls wait (which is likely to be the Python main
-# thread), we create a separate thread that does the blocking wait,
-# and then use the thread that called wait to do a slow poll of an
-# event queue. That thread, which is executing "wait" below is
-# interruptable, and if it sees a KeyboardInterrupt, executes a stop
-# on the top_block, then goes back to waiting for it to complete.
-# This ensures that the unlocked wait that was in progress (in the
-# _top_block_waiter thread) can complete, release its mutex and back
-# out. If we don't do that, we are never able to clean up, and nasty
-# things occur like leaving the USRP transmitter sending a carrier.
-#
-# See also top_block.wait (below), which uses this class to implement
-# the interruptable wait.
-#
+from hier_block2 import hier_block2
+
class _top_block_waiter(_threading.Thread):
+ """
+ This kludge allows ^C to interrupt top_block.run and top_block.wait
+
+ The problem that we are working around is that Python only services
+ signals (e.g., KeyboardInterrupt) in its main thread. If the main
+ thread is blocked in our C++ version of wait, even though Python's
+ SIGINT handler fires, and even though there may be other python
+ threads running, no one will know. Thus instead of directly waiting
+ in the thread that calls wait (which is likely to be the Python main
+ thread), we create a separate thread that does the blocking wait,
+ and then use the thread that called wait to do a slow poll of an
+ event queue. That thread, which is executing "wait" below is
+ interruptable, and if it sees a KeyboardInterrupt, executes a stop
+ on the top_block, then goes back to waiting for it to complete.
+ This ensures that the unlocked wait that was in progress (in the
+ _top_block_waiter thread) can complete, release its mutex and back
+ out. If we don't do that, we are never able to clean up, and nasty
+ things occur like leaving the USRP transmitter sending a carrier.
+
+ See also top_block.wait (below), which uses this class to implement
+ the interruptable wait.
+ """
def __init__(self, tb):
_threading.Thread.__init__(self)
self.setDaemon(1)
@@ -74,7 +73,7 @@ class _top_block_waiter(_threading.Thread):
#
-# This hack forces a 'has-a' relationship to look like an 'is-a' one.
+# This makes a 'has-a' relationship to look like an 'is-a' one.
#
# It allows Python classes to subclass this one, while passing through
# method calls to the C++ class shared pointer from SWIG.
@@ -85,91 +84,48 @@ class _top_block_waiter(_threading.Thread):
# to release the Python global interpreter lock before calling the actual
# method in gr_top_block
#
-class top_block(object):
+class top_block(hier_block2):
"""
Top-level hierarchical block representing a flow-graph.
This is a python wrapper around the C++ implementation to allow
python subclassing.
"""
- def __init__(self, name="top_block"):
- self._tb = top_block_swig(name)
- def __getattr__(self, name):
- if not hasattr(self, "_tb"):
- raise RuntimeError("top_block: invalid state--did you forget to call gr.top_block.__init__ in a derived class?")
- return getattr(self._tb, name)
+ def __init__(self, name="top_block"):
+ """
+ Create a top block with a given name.
+ """
+ # not calling hier_block2.__init__, we set our own _impl
+ self._impl = top_block_swig(name)
def start(self, max_noutput_items=10000000):
- top_block_start_unlocked(self._tb, max_noutput_items)
+ """
+ Start the flowgraph with the given number of output items and return.
+ """
+ top_block_start_unlocked(self._impl, max_noutput_items)
def stop(self):
- top_block_stop_unlocked(self._tb)
+ """
+ Stop the flowgraph
+ """
+ top_block_stop_unlocked(self._impl)
def run(self, max_noutput_items=10000000):
+ """
+ Start the flowgraph with the given number of output items and wait.
+ """
self.start(max_noutput_items)
self.wait()
def wait(self):
- _top_block_waiter(self._tb).wait()
-
-
- # FIXME: these are duplicated from hier_block2.py; they should really be implemented
- # in the original C++ class (gr_hier_block2), then they would all be inherited here
-
- def connect(self, *points):
- '''connect requires one or more arguments that can be coerced to endpoints.
- If more than two arguments are provided, they are connected together successively.
- '''
- if len (points) < 1:
- raise ValueError, ("connect requires at least one endpoint; %d provided." % (len (points),))
- else:
- if len(points) == 1:
- self._tb.primitive_connect(points[0].to_basic_block())
- else:
- for i in range (1, len (points)):
- self._connect(points[i-1], points[i])
-
- def msg_connect(self, src, srcport, dst, dstport):
- self.primitive_msg_connect(src.to_basic_block(), srcport, dst.to_basic_block(), dstport);
-
- def msg_disconnect(self, src, srcport, dst, dstport):
- self.primitive_msg_disconnect(src.to_basic_block(), srcport, dst.to_basic_block(), dstport);
-
- def _connect(self, src, dst):
- (src_block, src_port) = self._coerce_endpoint(src)
- (dst_block, dst_port) = self._coerce_endpoint(dst)
- self._tb.primitive_connect(src_block.to_basic_block(), src_port,
- dst_block.to_basic_block(), dst_port)
-
- def _coerce_endpoint(self, endp):
- if hasattr(endp, 'to_basic_block'):
- return (endp, 0)
- else:
- if hasattr(endp, "__getitem__") and len(endp) == 2:
- return endp # Assume user put (block, port)
- else:
- raise ValueError("unable to coerce endpoint")
-
- def disconnect(self, *points):
- '''disconnect requires one or more arguments that can be coerced to endpoints.
- If more than two arguments are provided, they are disconnected successively.
- '''
- if len (points) < 1:
- raise ValueError, ("disconnect requires at least one endpoint; %d provided." % (len (points),))
- else:
- if len(points) == 1:
- self._tb.primitive_disconnect(points[0].to_basic_block())
- else:
- for i in range (1, len (points)):
- self._disconnect(points[i-1], points[i])
-
- def _disconnect(self, src, dst):
- (src_block, src_port) = self._coerce_endpoint(src)
- (dst_block, dst_port) = self._coerce_endpoint(dst)
- self._tb.primitive_disconnect(src_block.to_basic_block(), src_port,
- dst_block.to_basic_block(), dst_port)
+ """
+ Wait for the flowgraph to finish running
+ """
+ _top_block_waiter(self._impl).wait()
def dot_graph(self):
- '''Return graph representation in dot language'''
- return dot_graph_tb(self._tb)
+ """
+ Return graph representation in dot language
+ """
+ return dot_graph_tb(self._impl)
diff --git a/gnuradio-runtime/python/pmt/qa_pmt.py b/gnuradio-runtime/python/pmt/qa_pmt.py
index 5c1af2c00e..32cff62f44 100755
--- a/gnuradio-runtime/python/pmt/qa_pmt.py
+++ b/gnuradio-runtime/python/pmt/qa_pmt.py
@@ -36,7 +36,9 @@ class test_pmt(unittest.TestCase):
const = 123765
x_pmt = pmt.from_double(const)
x_int = pmt.to_double(x_pmt)
+ x_float = pmt.to_float(x_pmt)
self.assertEqual(x_int, const)
+ self.assertEqual(x_float, const)
def test03(self):
v = pmt.init_f32vector(3, [11, -22, 33])
diff --git a/gnuradio-runtime/swig/block.i b/gnuradio-runtime/swig/block.i
index 9f3f374d78..945cea79b2 100644
--- a/gnuradio-runtime/swig/block.i
+++ b/gnuradio-runtime/swig/block.i
@@ -96,6 +96,7 @@ class gr::block : public gr::basic_block
float pc_work_time_avg();
float pc_work_time_var();
float pc_work_time_total();
+ float pc_throughput_avg();
// Methods to manage processor affinity.
void set_processor_affinity(const std::vector<int> &mask);
diff --git a/gnuradio-runtime/swig/pmt_swig.i b/gnuradio-runtime/swig/pmt_swig.i
index e54b544977..c4b678222d 100644
--- a/gnuradio-runtime/swig/pmt_swig.i
+++ b/gnuradio-runtime/swig/pmt_swig.i
@@ -111,6 +111,8 @@ namespace pmt{
bool is_real(pmt_t obj);
pmt_t from_double(double x);
double to_double(pmt_t x);
+ pmt_t from_float(double x);
+ double to_float(pmt_t x);
bool is_complex(pmt_t obj);
pmt_t make_rectangular(double re, double im);
diff --git a/gr-analog/grc/analog_probe_avg_mag_sqrd_x.xml b/gr-analog/grc/analog_probe_avg_mag_sqrd_x.xml
index b05ac6d0d1..482982b21f 100644
--- a/gr-analog/grc/analog_probe_avg_mag_sqrd_x.xml
+++ b/gr-analog/grc/analog_probe_avg_mag_sqrd_x.xml
@@ -11,6 +11,7 @@
<make>analog.probe_avg_mag_sqrd_$(type)($threshold, $alpha)</make>
<callback>set_alpha($alpha)</callback>
<callback>set_threshold($threshold)</callback>
+ <callback>reset()</callback>
<param>
<name>Type</name>
<key>type</key>
diff --git a/gr-analog/include/gnuradio/analog/probe_avg_mag_sqrd_c.h b/gr-analog/include/gnuradio/analog/probe_avg_mag_sqrd_c.h
index 781d72f742..e6816f7fb6 100644
--- a/gr-analog/include/gnuradio/analog/probe_avg_mag_sqrd_c.h
+++ b/gr-analog/include/gnuradio/analog/probe_avg_mag_sqrd_c.h
@@ -60,6 +60,7 @@ namespace gr {
virtual void set_alpha(double alpha) = 0;
virtual void set_threshold(double decibels) = 0;
+ virtual void reset() = 0;
};
} /* namespace analog */
diff --git a/gr-analog/include/gnuradio/analog/probe_avg_mag_sqrd_cf.h b/gr-analog/include/gnuradio/analog/probe_avg_mag_sqrd_cf.h
index 03f465b2c5..9aeb8761be 100644
--- a/gr-analog/include/gnuradio/analog/probe_avg_mag_sqrd_cf.h
+++ b/gr-analog/include/gnuradio/analog/probe_avg_mag_sqrd_cf.h
@@ -62,6 +62,7 @@ namespace gr {
virtual void set_alpha(double alpha) = 0;
virtual void set_threshold(double decibels) = 0;
+ virtual void reset() = 0;
};
} /* namespace analog */
diff --git a/gr-analog/include/gnuradio/analog/probe_avg_mag_sqrd_f.h b/gr-analog/include/gnuradio/analog/probe_avg_mag_sqrd_f.h
index b9424dbd96..66095c3709 100644
--- a/gr-analog/include/gnuradio/analog/probe_avg_mag_sqrd_f.h
+++ b/gr-analog/include/gnuradio/analog/probe_avg_mag_sqrd_f.h
@@ -62,6 +62,7 @@ namespace gr {
virtual void set_alpha (double alpha) = 0;
virtual void set_threshold (double decibels) = 0;
+ virtual void reset() = 0;
};
} /* namespace analog */
diff --git a/gr-analog/lib/probe_avg_mag_sqrd_c_impl.cc b/gr-analog/lib/probe_avg_mag_sqrd_c_impl.cc
index 78e0c842ed..3d04c8bc6f 100644
--- a/gr-analog/lib/probe_avg_mag_sqrd_c_impl.cc
+++ b/gr-analog/lib/probe_avg_mag_sqrd_c_impl.cc
@@ -87,5 +87,11 @@ namespace gr {
d_iir.set_taps(alpha);
}
+ void
+ probe_avg_mag_sqrd_c_impl::reset()
+ {
+ d_iir.reset();
+ }
+
} /* namespace analog */
} /* namespace gr */
diff --git a/gr-analog/lib/probe_avg_mag_sqrd_c_impl.h b/gr-analog/lib/probe_avg_mag_sqrd_c_impl.h
index cddb9a7234..0128491f9d 100644
--- a/gr-analog/lib/probe_avg_mag_sqrd_c_impl.h
+++ b/gr-analog/lib/probe_avg_mag_sqrd_c_impl.h
@@ -48,6 +48,7 @@ namespace gr {
void set_alpha(double alpha);
void set_threshold(double decibels);
+ void reset();
int work(int noutput_items,
gr_vector_const_void_star &input_items,
diff --git a/gr-analog/lib/probe_avg_mag_sqrd_cf_impl.cc b/gr-analog/lib/probe_avg_mag_sqrd_cf_impl.cc
index 76d54880d4..c57f5cefd8 100644
--- a/gr-analog/lib/probe_avg_mag_sqrd_cf_impl.cc
+++ b/gr-analog/lib/probe_avg_mag_sqrd_cf_impl.cc
@@ -89,5 +89,11 @@ namespace gr {
d_iir.set_taps(alpha);
}
+ void
+ probe_avg_mag_sqrd_cf_impl::reset()
+ {
+ d_iir.reset();
+ }
+
} /* namespace analog */
} /* namespace gr */
diff --git a/gr-analog/lib/probe_avg_mag_sqrd_cf_impl.h b/gr-analog/lib/probe_avg_mag_sqrd_cf_impl.h
index 359f7f8d53..0284981cac 100644
--- a/gr-analog/lib/probe_avg_mag_sqrd_cf_impl.h
+++ b/gr-analog/lib/probe_avg_mag_sqrd_cf_impl.h
@@ -48,6 +48,7 @@ namespace gr {
void set_alpha(double alpha);
void set_threshold(double decibels);
+ void reset();
int work(int noutput_items,
gr_vector_const_void_star &input_items,
diff --git a/gr-analog/lib/probe_avg_mag_sqrd_f_impl.cc b/gr-analog/lib/probe_avg_mag_sqrd_f_impl.cc
index 505a24a5e9..0d2ce63f7b 100644
--- a/gr-analog/lib/probe_avg_mag_sqrd_f_impl.cc
+++ b/gr-analog/lib/probe_avg_mag_sqrd_f_impl.cc
@@ -87,6 +87,12 @@ namespace gr {
d_iir.set_taps(alpha);
}
+ void
+ probe_avg_mag_sqrd_f_impl::reset()
+ {
+ d_iir.reset();
+ }
+
} /* namespace analog */
} /* namespace gr */
diff --git a/gr-analog/lib/probe_avg_mag_sqrd_f_impl.h b/gr-analog/lib/probe_avg_mag_sqrd_f_impl.h
index bdccfc7b3a..1f82f85e18 100644
--- a/gr-analog/lib/probe_avg_mag_sqrd_f_impl.h
+++ b/gr-analog/lib/probe_avg_mag_sqrd_f_impl.h
@@ -48,6 +48,7 @@ namespace gr {
void set_alpha(double alpha);
void set_threshold(double decibels);
+ void reset();
int work(int noutput_items,
gr_vector_const_void_star &input_items,
diff --git a/gr-blocks/examples/CMakeLists.txt b/gr-blocks/examples/CMakeLists.txt
index c9829661b6..bb07cdc2b5 100644
--- a/gr-blocks/examples/CMakeLists.txt
+++ b/gr-blocks/examples/CMakeLists.txt
@@ -17,6 +17,14 @@
# the Free Software Foundation, Inc., 51 Franklin Street,
# Boston, MA 02110-1301, USA.
+install(
+ FILES
+ matrix_multiplexer.grc
+ vector_source_with_tags.grc
+ DESTINATION ${GR_PKG_DATA_DIR}/examples/blocks
+ COMPONENT "runtime_python"
+)
+
add_subdirectory(metadata)
add_subdirectory(tags)
diff --git a/gr-blocks/examples/msg_passing/strobe.grc b/gr-blocks/examples/msg_passing/strobe.grc
index e5001a4262..f24887ab76 100644
--- a/gr-blocks/examples/msg_passing/strobe.grc
+++ b/gr-blocks/examples/msg_passing/strobe.grc
@@ -1,4 +1,5 @@
<?xml version='1.0' encoding='ASCII'?>
+<?grc format='1' created='3.7.6'?>
<flow_graph>
<timestamp>Sun Mar 17 20:42:59 2013</timestamp>
<block>
@@ -52,8 +53,12 @@
<value></value>
</param>
<param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
<key>_coordinate</key>
- <value>(10, 10)</value>
+ <value>(-8, -12)</value>
</param>
<param>
<key>_rotation</key>
@@ -61,41 +66,42 @@
</param>
</block>
<block>
- <key>variable</key>
+ <key>blocks_pdu_to_tagged_stream</key>
<param>
<key>id</key>
- <value>samp_rate</value>
+ <value>blocks_pdu_to_tagged_stream_0</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>value</key>
- <value>32000</value>
+ <key>type</key>
+ <value>byte</value>
</param>
<param>
- <key>_coordinate</key>
- <value>(10, 170)</value>
+ <key>tag</key>
+ <value>packet_len</value>
</param>
<param>
- <key>_rotation</key>
- <value>0</value>
+ <key>alias</key>
+ <value></value>
</param>
- </block>
- <block>
- <key>blocks_message_debug</key>
<param>
- <key>id</key>
- <value>blocks_message_debug_0</value>
+ <key>affinity</key>
+ <value></value>
</param>
<param>
- <key>_enabled</key>
- <value>True</value>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
</param>
<param>
<key>_coordinate</key>
- <value>(1049, 176)</value>
+ <value>(264, 179)</value>
</param>
<param>
<key>_rotation</key>
@@ -103,22 +109,42 @@
</param>
</block>
<block>
- <key>blocks_pdu_to_tagged_stream</key>
+ <key>blocks_message_strobe</key>
<param>
<key>id</key>
- <value>blocks_pdu_to_tagged_stream_0</value>
+ <value>blocks_message_strobe_0_0</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>type</key>
- <value>byte</value>
+ <key>msg</key>
+ <value>pmt.cons( pmt.PMT_NIL, pmt.make_u8vector(512,0) )</value>
+ </param>
+ <param>
+ <key>period</key>
+ <value>750</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
</param>
<param>
<key>_coordinate</key>
- <value>(388, 85)</value>
+ <value>(48, 172)</value>
</param>
<param>
<key>_rotation</key>
@@ -129,7 +155,7 @@
<key>blocks_message_strobe</key>
<param>
<key>id</key>
- <value>blocks_message_strobe_0_0</value>
+ <value>blocks_message_strobe_0</value>
</param>
<param>
<key>_enabled</key>
@@ -137,15 +163,31 @@
</param>
<param>
<key>msg</key>
- <value>pmt.cons( pmt.PMT_NIL, pmt.make_u8vector(512,0) )</value>
+ <value>pmt.intern("TEST")</value>
</param>
<param>
<key>period</key>
- <value>750</value>
+ <value>1000</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
</param>
<param>
<key>_coordinate</key>
- <value>(95, 95)</value>
+ <value>(56, 108)</value>
</param>
<param>
<key>_rotation</key>
@@ -175,8 +217,28 @@
<value>1</value>
</param>
<param>
+ <key>showports</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
<key>_coordinate</key>
- <value>(629, 81)</value>
+ <value>(496, 179)</value>
</param>
<param>
<key>_rotation</key>
@@ -198,8 +260,28 @@
<value>byte</value>
</param>
<param>
+ <key>tag</key>
+ <value>packet_len</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
<key>_coordinate</key>
- <value>(837, 47)</value>
+ <value>(664, 179)</value>
</param>
<param>
<key>_rotation</key>
@@ -207,26 +289,26 @@
</param>
</block>
<block>
- <key>blocks_message_strobe</key>
+ <key>blocks_message_debug</key>
<param>
<key>id</key>
- <value>blocks_message_strobe_0</value>
+ <value>blocks_message_debug_0</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>msg</key>
- <value>pmt.intern("TEST")</value>
+ <key>alias</key>
+ <value></value>
</param>
<param>
- <key>period</key>
- <value>1000</value>
+ <key>affinity</key>
+ <value></value>
</param>
<param>
<key>_coordinate</key>
- <value>(423, 164)</value>
+ <value>(944, 120)</value>
</param>
<param>
<key>_rotation</key>
@@ -234,22 +316,16 @@
</param>
</block>
<connection>
- <source_block_id>blocks_message_strobe_0</source_block_id>
- <sink_block_id>blocks_message_debug_0</sink_block_id>
- <source_key>0</source_key>
- <sink_key>0</sink_key>
- </connection>
- <connection>
<source_block_id>blocks_message_strobe_0_0</source_block_id>
<sink_block_id>blocks_pdu_to_tagged_stream_0</sink_block_id>
- <source_key>0</source_key>
- <sink_key>0</sink_key>
+ <source_key>strobe</source_key>
+ <sink_key>pdus</sink_key>
</connection>
<connection>
- <source_block_id>blocks_tagged_stream_to_pdu_0</source_block_id>
- <sink_block_id>blocks_message_debug_0</sink_block_id>
+ <source_block_id>blocks_pdu_to_tagged_stream_0</source_block_id>
+ <sink_block_id>blocks_copy_0</sink_block_id>
<source_key>0</source_key>
- <sink_key>2</sink_key>
+ <sink_key>0</sink_key>
</connection>
<connection>
<source_block_id>blocks_copy_0</source_block_id>
@@ -258,9 +334,15 @@
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_pdu_to_tagged_stream_0</source_block_id>
- <sink_block_id>blocks_copy_0</sink_block_id>
- <source_key>0</source_key>
- <sink_key>0</sink_key>
+ <source_block_id>blocks_message_strobe_0</source_block_id>
+ <sink_block_id>blocks_message_debug_0</sink_block_id>
+ <source_key>strobe</source_key>
+ <sink_key>print</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>blocks_tagged_stream_to_pdu_0</source_block_id>
+ <sink_block_id>blocks_message_debug_0</sink_block_id>
+ <source_key>pdus</source_key>
+ <sink_key>print_pdu</sink_key>
</connection>
</flow_graph>
diff --git a/gr-blocks/examples/vector_source_with_tags.grc b/gr-blocks/examples/vector_source_with_tags.grc
new file mode 100644
index 0000000000..e266b91f85
--- /dev/null
+++ b/gr-blocks/examples/vector_source_with_tags.grc
@@ -0,0 +1,698 @@
+<?xml version='1.0' encoding='ASCII'?>
+<?grc format='1' created='3.7.6'?>
+<flow_graph>
+ <timestamp>Mon Sep 22 11:59:58 2014</timestamp>
+ <block>
+ <key>options</key>
+ <param>
+ <key>id</key>
+ <value>vector_source_with_tags</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>title</key>
+ <value></value>
+ </param>
+ <param>
+ <key>author</key>
+ <value></value>
+ </param>
+ <param>
+ <key>description</key>
+ <value>Shows how to use tags in a vector_source</value>
+ </param>
+ <param>
+ <key>window_size</key>
+ <value>1280, 1024</value>
+ </param>
+ <param>
+ <key>generate_options</key>
+ <value>qt_gui</value>
+ </param>
+ <param>
+ <key>category</key>
+ <value>Custom</value>
+ </param>
+ <param>
+ <key>run_options</key>
+ <value>prompt</value>
+ </param>
+ <param>
+ <key>run</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>max_nouts</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>realtime_scheduling</key>
+ <value></value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(10, 10)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>variable</key>
+ <param>
+ <key>id</key>
+ <value>tag1</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>value</key>
+ <value>gr.tag_utils.python_to_tag((1, pmt.intern('mark'), pmt.PMT_T))</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(16, 267)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>variable</key>
+ <param>
+ <key>id</key>
+ <value>tag0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>value</key>
+ <value>gr.tag_utils.python_to_tag((0, pmt.intern('mark'), pmt.PMT_T, pmt.intern("src")))</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(16, 203)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>variable</key>
+ <param>
+ <key>id</key>
+ <value>samp_rate</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>value</key>
+ <value>32000</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(184, 11)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>import</key>
+ <param>
+ <key>id</key>
+ <value>import_pmt</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>import</key>
+ <value>import pmt</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(280, 11)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>blocks_throttle</key>
+ <param>
+ <key>id</key>
+ <value>blocks_throttle_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>type</key>
+ <value>float</value>
+ </param>
+ <param>
+ <key>samples_per_second</key>
+ <value>samp_rate</value>
+ </param>
+ <param>
+ <key>vlen</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>ignoretag</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(272, 123)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>blocks_tag_debug</key>
+ <param>
+ <key>id</key>
+ <value>blocks_tag_debug_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>type</key>
+ <value>float</value>
+ </param>
+ <param>
+ <key>name</key>
+ <value></value>
+ </param>
+ <param>
+ <key>filter</key>
+ <value>""</value>
+ </param>
+ <param>
+ <key>num_inputs</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>vlen</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>display</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(456, 195)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>blocks_vector_source_x</key>
+ <param>
+ <key>id</key>
+ <value>blocks_vector_source_x_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>type</key>
+ <value>float</value>
+ </param>
+ <param>
+ <key>vector</key>
+ <value>(-0.75, -0.5, -0.25, 0.0, 0.25, 0.5, 0.75, 0.0)</value>
+ </param>
+ <param>
+ <key>tags</key>
+ <value>[tag0, tag1]</value>
+ </param>
+ <param>
+ <key>repeat</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>vlen</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(16, 107)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>qtgui_time_sink_x</key>
+ <param>
+ <key>id</key>
+ <value>qtgui_time_sink_x_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>type</key>
+ <value>float</value>
+ </param>
+ <param>
+ <key>name</key>
+ <value>""</value>
+ </param>
+ <param>
+ <key>ylabel</key>
+ <value>Amplitude</value>
+ </param>
+ <param>
+ <key>yunit</key>
+ <value>""</value>
+ </param>
+ <param>
+ <key>size</key>
+ <value>60</value>
+ </param>
+ <param>
+ <key>srate</key>
+ <value>samp_rate</value>
+ </param>
+ <param>
+ <key>grid</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>autoscale</key>
+ <value>False</value>
+ </param>
+ <param>
+ <key>ymin</key>
+ <value>-1</value>
+ </param>
+ <param>
+ <key>ymax</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>nconnections</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>update_time</key>
+ <value>0.10</value>
+ </param>
+ <param>
+ <key>entags</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>gui_hint</key>
+ <value></value>
+ </param>
+ <param>
+ <key>tr_mode</key>
+ <value>qtgui.TRIG_MODE_TAG</value>
+ </param>
+ <param>
+ <key>tr_slope</key>
+ <value>qtgui.TRIG_SLOPE_POS</value>
+ </param>
+ <param>
+ <key>tr_level</key>
+ <value>0.0</value>
+ </param>
+ <param>
+ <key>tr_delay</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>tr_chan</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>tr_tag</key>
+ <value>mark</value>
+ </param>
+ <param>
+ <key>label1</key>
+ <value></value>
+ </param>
+ <param>
+ <key>width1</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>color1</key>
+ <value>"blue"</value>
+ </param>
+ <param>
+ <key>style1</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>marker1</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>alpha1</key>
+ <value>1.0</value>
+ </param>
+ <param>
+ <key>label2</key>
+ <value></value>
+ </param>
+ <param>
+ <key>width2</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>color2</key>
+ <value>"red"</value>
+ </param>
+ <param>
+ <key>style2</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>marker2</key>
+ <value>-1</value>
+ </param>
+ <param>
+ <key>alpha2</key>
+ <value>1.0</value>
+ </param>
+ <param>
+ <key>label3</key>
+ <value></value>
+ </param>
+ <param>
+ <key>width3</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>color3</key>
+ <value>"green"</value>
+ </param>
+ <param>
+ <key>style3</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>marker3</key>
+ <value>-1</value>
+ </param>
+ <param>
+ <key>alpha3</key>
+ <value>1.0</value>
+ </param>
+ <param>
+ <key>label4</key>
+ <value></value>
+ </param>
+ <param>
+ <key>width4</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>color4</key>
+ <value>"black"</value>
+ </param>
+ <param>
+ <key>style4</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>marker4</key>
+ <value>-1</value>
+ </param>
+ <param>
+ <key>alpha4</key>
+ <value>1.0</value>
+ </param>
+ <param>
+ <key>label5</key>
+ <value></value>
+ </param>
+ <param>
+ <key>width5</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>color5</key>
+ <value>"cyan"</value>
+ </param>
+ <param>
+ <key>style5</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>marker5</key>
+ <value>-1</value>
+ </param>
+ <param>
+ <key>alpha5</key>
+ <value>1.0</value>
+ </param>
+ <param>
+ <key>label6</key>
+ <value></value>
+ </param>
+ <param>
+ <key>width6</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>color6</key>
+ <value>"magenta"</value>
+ </param>
+ <param>
+ <key>style6</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>marker6</key>
+ <value>-1</value>
+ </param>
+ <param>
+ <key>alpha6</key>
+ <value>1.0</value>
+ </param>
+ <param>
+ <key>label7</key>
+ <value></value>
+ </param>
+ <param>
+ <key>width7</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>color7</key>
+ <value>"yellow"</value>
+ </param>
+ <param>
+ <key>style7</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>marker7</key>
+ <value>-1</value>
+ </param>
+ <param>
+ <key>alpha7</key>
+ <value>1.0</value>
+ </param>
+ <param>
+ <key>label8</key>
+ <value></value>
+ </param>
+ <param>
+ <key>width8</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>color8</key>
+ <value>"dark red"</value>
+ </param>
+ <param>
+ <key>style8</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>marker8</key>
+ <value>-1</value>
+ </param>
+ <param>
+ <key>alpha8</key>
+ <value>1.0</value>
+ </param>
+ <param>
+ <key>label9</key>
+ <value></value>
+ </param>
+ <param>
+ <key>width9</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>color9</key>
+ <value>"dark green"</value>
+ </param>
+ <param>
+ <key>style9</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>marker9</key>
+ <value>-1</value>
+ </param>
+ <param>
+ <key>alpha9</key>
+ <value>1.0</value>
+ </param>
+ <param>
+ <key>label10</key>
+ <value></value>
+ </param>
+ <param>
+ <key>width10</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>color10</key>
+ <value>"blue"</value>
+ </param>
+ <param>
+ <key>style10</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>marker10</key>
+ <value>-1</value>
+ </param>
+ <param>
+ <key>alpha10</key>
+ <value>1.0</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(456, 107)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <connection>
+ <source_block_id>blocks_throttle_0</source_block_id>
+ <sink_block_id>qtgui_time_sink_x_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>blocks_vector_source_x_0</source_block_id>
+ <sink_block_id>blocks_throttle_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>blocks_throttle_0</source_block_id>
+ <sink_block_id>blocks_tag_debug_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+</flow_graph>
diff --git a/gr-blocks/grc/blocks_abs_xx.xml b/gr-blocks/grc/blocks_abs_xx.xml
index 65ef97ddff..77298716c8 100644
--- a/gr-blocks/grc/blocks_abs_xx.xml
+++ b/gr-blocks/grc/blocks_abs_xx.xml
@@ -8,7 +8,13 @@
<name>Abs</name>
<key>blocks_abs_xx</key>
<import>from gnuradio import blocks</import>
- <make>blocks.abs_$(type.fcn)()</make>
+ <make>blocks.abs_$(type.fcn)($vlen)</make>
+ <param>
+ <name>Vec Length</name>
+ <key>vlen</key>
+ <value>1</value>
+ <type>int</type>
+ </param>
<param>
<name>IO Type</name>
<key>type</key>
@@ -29,21 +35,14 @@
<opt>fcn:ff</opt>
</option>
</param>
- <param>
- <name>Num Inputs</name>
- <key>num_inputs</key>
- <value>1</value>
- <type>int</type>
- </param>
- <check>$num_inputs &gt;= 1</check>
<sink>
<name>in</name>
<type>$type</type>
- <nports>$num_inputs</nports>
+ <vlen>$vlen</vlen>
</sink>
<source>
<name>out</name>
<type>$type</type>
- <nports>$num_inputs</nports>
+ <vlen>$vlen</vlen>
</source>
</block>
diff --git a/gr-blocks/grc/blocks_repack_bits_bb.xml b/gr-blocks/grc/blocks_repack_bits_bb.xml
index 4ad5ec631b..7931132540 100644
--- a/gr-blocks/grc/blocks_repack_bits_bb.xml
+++ b/gr-blocks/grc/blocks_repack_bits_bb.xml
@@ -2,30 +2,36 @@
<name>Repack Bits</name>
<key>blocks_repack_bits_bb</key>
<import>from gnuradio import blocks</import>
- <make>blocks.repack_bits_bb($k, $l, $len_tag_key, $align_output)</make>
+ <make>blocks.repack_bits_bb($k, $l, $len_tag_key, $align_output, $endianness)</make>
+
<param>
<name>Bits per input byte</name>
<key>k</key>
<value>1</value>
<type>int</type>
</param>
+
<param>
<name>Bits per output byte</name>
<key>l</key>
<value>8</value>
<type>int</type>
</param>
+
<param>
<name>Length Tag Key</name>
<key>len_tag_key</key>
<value>""</value>
<type>string</type>
+ <hide>part</hide>
</param>
+
<param>
<name>Packet Alignment</name>
<key>align_output</key>
<value>False</value>
<type>enum</type>
+ <hide>part</hide>
<option>
<name>Output</name>
<key>True</key>
@@ -35,10 +41,29 @@
<key>False</key>
</option>
</param>
+
+
+ <param>
+ <name>Endianness</name>
+ <key>endianness</key>
+ <value>gr.GR_LSB_FIRST</value>
+ <type>int</type>
+ <hide>part</hide>
+ <option>
+ <name>MSB</name>
+ <key>gr.GR_MSB_FIRST</key>
+ </option>
+ <option>
+ <name>LSB</name>
+ <key>gr.GR_LSB_FIRST</key>
+ </option>
+ </param>
+
<sink>
<name>in</name>
<type>byte</type>
</sink>
+
<source>
<name>out</name>
<type>byte</type>
diff --git a/gr-blocks/grc/blocks_tagged_stream_to_pdu.xml b/gr-blocks/grc/blocks_tagged_stream_to_pdu.xml
index f85b47fb19..ae8ad3b6c5 100644
--- a/gr-blocks/grc/blocks_tagged_stream_to_pdu.xml
+++ b/gr-blocks/grc/blocks_tagged_stream_to_pdu.xml
@@ -42,5 +42,6 @@
<source>
<name>pdus</name>
<type>message</type>
+ <optional>1</optional>
</source>
</block>
diff --git a/gr-blocks/include/gnuradio/blocks/abs_XX.h.t b/gr-blocks/include/gnuradio/blocks/abs_XX.h.t
index f8688edcd3..541716296f 100644
--- a/gr-blocks/include/gnuradio/blocks/abs_XX.h.t
+++ b/gr-blocks/include/gnuradio/blocks/abs_XX.h.t
@@ -49,7 +49,7 @@ namespace gr {
/*!
* \brief Create an instance of @NAME@
*/
- static sptr make();
+ static sptr make(size_t vlen=1);
};
} /* namespace blocks */
diff --git a/gr-blocks/include/gnuradio/blocks/control_loop.h b/gr-blocks/include/gnuradio/blocks/control_loop.h
index f7ff9770f9..821c3824ec 100644
--- a/gr-blocks/include/gnuradio/blocks/control_loop.h
+++ b/gr-blocks/include/gnuradio/blocks/control_loop.h
@@ -268,6 +268,87 @@ namespace gr {
float get_min_freq() const;
};
+ // This is a table of tanh(x) for x in [-2, 2] used in tanh_lut.
+ static float
+ tanh_lut_table[256] = { -0.96402758, -0.96290241, -0.96174273, -0.96054753, -0.95931576,
+ -0.95804636, -0.95673822, -0.95539023, -0.95400122, -0.95257001,
+ -0.95109539, -0.9495761 , -0.94801087, -0.94639839, -0.94473732,
+ -0.94302627, -0.94126385, -0.93944862, -0.93757908, -0.93565374,
+ -0.93367104, -0.93162941, -0.92952723, -0.92736284, -0.92513456,
+ -0.92284066, -0.92047938, -0.91804891, -0.91554743, -0.91297305,
+ -0.91032388, -0.90759795, -0.9047933 , -0.90190789, -0.89893968,
+ -0.89588656, -0.89274642, -0.88951709, -0.88619637, -0.88278203,
+ -0.87927182, -0.87566342, -0.87195453, -0.86814278, -0.86422579,
+ -0.86020115, -0.85606642, -0.85181914, -0.84745683, -0.84297699,
+ -0.83837709, -0.83365461, -0.82880699, -0.82383167, -0.81872609,
+ -0.81348767, -0.80811385, -0.80260204, -0.7969497 , -0.79115425,
+ -0.78521317, -0.77912392, -0.772884 , -0.76649093, -0.75994227,
+ -0.75323562, -0.74636859, -0.73933889, -0.73214422, -0.7247824 ,
+ -0.71725127, -0.70954876, -0.70167287, -0.6936217 , -0.68539341,
+ -0.67698629, -0.66839871, -0.65962916, -0.65067625, -0.64153871,
+ -0.6322154 , -0.62270534, -0.61300768, -0.60312171, -0.59304692,
+ -0.58278295, -0.57232959, -0.56168685, -0.55085493, -0.53983419,
+ -0.52862523, -0.51722883, -0.50564601, -0.49387799, -0.48192623,
+ -0.46979241, -0.45747844, -0.44498647, -0.4323189 , -0.41947836,
+ -0.40646773, -0.39329014, -0.37994896, -0.36644782, -0.35279057,
+ -0.33898135, -0.32502449, -0.31092459, -0.2966865 , -0.28231527,
+ -0.26781621, -0.25319481, -0.23845682, -0.22360817, -0.208655 ,
+ -0.19360362, -0.17846056, -0.16323249, -0.14792623, -0.13254879,
+ -0.11710727, -0.10160892, -0.08606109, -0.07047123, -0.05484686,
+ -0.0391956 , -0.02352507, -0.00784298, 0.00784298, 0.02352507,
+ 0.0391956 , 0.05484686, 0.07047123, 0.08606109, 0.10160892,
+ 0.11710727, 0.13254879, 0.14792623, 0.16323249, 0.17846056,
+ 0.19360362, 0.208655 , 0.22360817, 0.23845682, 0.25319481,
+ 0.26781621, 0.28231527, 0.2966865 , 0.31092459, 0.32502449,
+ 0.33898135, 0.35279057, 0.36644782, 0.37994896, 0.39329014,
+ 0.40646773, 0.41947836, 0.4323189 , 0.44498647, 0.45747844,
+ 0.46979241, 0.48192623, 0.49387799, 0.50564601, 0.51722883,
+ 0.52862523, 0.53983419, 0.55085493, 0.56168685, 0.57232959,
+ 0.58278295, 0.59304692, 0.60312171, 0.61300768, 0.62270534,
+ 0.6322154 , 0.64153871, 0.65067625, 0.65962916, 0.66839871,
+ 0.67698629, 0.68539341, 0.6936217 , 0.70167287, 0.70954876,
+ 0.71725127, 0.7247824 , 0.73214422, 0.73933889, 0.74636859,
+ 0.75323562, 0.75994227, 0.76649093, 0.772884 , 0.77912392,
+ 0.78521317, 0.79115425, 0.7969497 , 0.80260204, 0.80811385,
+ 0.81348767, 0.81872609, 0.82383167, 0.82880699, 0.83365461,
+ 0.83837709, 0.84297699, 0.84745683, 0.85181914, 0.85606642,
+ 0.86020115, 0.86422579, 0.86814278, 0.87195453, 0.87566342,
+ 0.87927182, 0.88278203, 0.88619637, 0.88951709, 0.89274642,
+ 0.89588656, 0.89893968, 0.90190789, 0.9047933 , 0.90759795,
+ 0.91032388, 0.91297305, 0.91554743, 0.91804891, 0.92047938,
+ 0.92284066, 0.92513456, 0.92736284, 0.92952723, 0.93162941,
+ 0.93367104, 0.93565374, 0.93757908, 0.93944862, 0.94126385,
+ 0.94302627, 0.94473732, 0.94639839, 0.94801087, 0.9495761 ,
+ 0.95109539, 0.95257001, 0.95400122, 0.95539023, 0.95673822,
+ 0.95804636, 0.95931576, 0.96054753, 0.96174273, 0.96290241,
+ 0.96402758 };
+
+ /*!
+ * A look-up table (LUT) tanh calcuation. This function returns an
+ * estimate to tanh(x) based on a 256-point LUT between -2 and
+ * 2. If x < -2, it returns -1; if > 2, it retursn 1.
+ *
+ * This LUT form of the tanh is "hidden" in this code because it
+ * is likely too coarse an estimate for any real uses of a
+ * tanh. It is useful, however, in certain control loop
+ * applications where the input is expected to be within these
+ * bounds and the noise will be greater than the quanitzation of
+ * this small LUT. For more accurate forms of tanh, see
+ * volk_32f_tanh_32f.
+ */
+ static inline float
+ tanhf_lut(float x)
+ {
+ if(x > 2)
+ return 1;
+ else if(x <= -2)
+ return -1;
+ else {
+ int index = 128 + 64*x;
+ return tanh_lut_table[index];
+ }
+ }
+
} /* namespace blocks */
} /* namespace gr */
diff --git a/gr-blocks/include/gnuradio/blocks/pdu_to_tagged_stream.h b/gr-blocks/include/gnuradio/blocks/pdu_to_tagged_stream.h
index 9ae2ecd297..479e367e72 100644
--- a/gr-blocks/include/gnuradio/blocks/pdu_to_tagged_stream.h
+++ b/gr-blocks/include/gnuradio/blocks/pdu_to_tagged_stream.h
@@ -25,7 +25,7 @@
#include <gnuradio/blocks/api.h>
#include <gnuradio/blocks/pdu.h>
-#include <gnuradio/sync_block.h>
+#include <gnuradio/tagged_stream_block.h>
namespace gr {
namespace blocks {
@@ -34,7 +34,7 @@ namespace gr {
* \brief Turns received PDUs into a tagged stream of items
* \ingroup message_tools_blk
*/
- class BLOCKS_API pdu_to_tagged_stream : virtual public sync_block
+ class BLOCKS_API pdu_to_tagged_stream : virtual public tagged_stream_block
{
public:
// gr::blocks::pdu_to_tagged_stream::sptr
diff --git a/gr-blocks/include/gnuradio/blocks/repack_bits_bb.h b/gr-blocks/include/gnuradio/blocks/repack_bits_bb.h
index e094e6815a..83bd771e0b 100644
--- a/gr-blocks/include/gnuradio/blocks/repack_bits_bb.h
+++ b/gr-blocks/include/gnuradio/blocks/repack_bits_bb.h
@@ -25,6 +25,7 @@
#include <gnuradio/blocks/api.h>
#include <gnuradio/tagged_stream_block.h>
+#include <gnuradio/endianness.h>
namespace gr {
namespace blocks {
@@ -75,12 +76,13 @@ namespace gr {
* \param tsb_tag_key If not empty, this is the key for the length tag.
* \param align_output If tsb_tag_key is given, this controls if the input
* or the output is aligned.
+ * \param endianness The endianness of the output data stream (LSB or MSB).
*/
- static sptr make(int k, int l=8, const std::string &tsb_tag_key="", bool align_output=false);
+ static sptr make(int k, int l=8, const std::string &tsb_tag_key="",
+ bool align_output=false, endianness_t endianness=GR_LSB_FIRST);
};
} // namespace blocks
} // namespace gr
#endif /* INCLUDED_BLOCKS_REPACK_BITS_BB_H */
-
diff --git a/gr-blocks/lib/abs_XX_impl.cc.t b/gr-blocks/lib/abs_XX_impl.cc.t
index 6bb9f149fd..195d8dff3d 100644
--- a/gr-blocks/lib/abs_XX_impl.cc.t
+++ b/gr-blocks/lib/abs_XX_impl.cc.t
@@ -32,15 +32,16 @@
namespace gr {
namespace blocks {
- @NAME@::sptr @NAME@::make()
+ @NAME@::sptr @NAME@::make(size_t vlen)
{
- return gnuradio::get_initial_sptr(new @NAME_IMPL@());
+ return gnuradio::get_initial_sptr(new @NAME_IMPL@(vlen));
}
- @NAME_IMPL@::@NAME_IMPL@()
+ @NAME_IMPL@::@NAME_IMPL@(size_t vlen)
: sync_block ("@NAME@",
- io_signature::make (1, 1, sizeof (@I_TYPE@)),
- io_signature::make (1, 1, sizeof (@O_TYPE@)))
+ io_signature::make (1, 1, sizeof (@I_TYPE@)*vlen),
+ io_signature::make (1, 1, sizeof (@O_TYPE@)*vlen)),
+ d_vlen(vlen)
{
}
@@ -52,7 +53,7 @@ namespace gr {
@I_TYPE@ *iptr = (@I_TYPE@ *) input_items[0];
@O_TYPE@ *optr = (@O_TYPE@ *) output_items[0];
- for(int i=0; i<noutput_items; i++) {
+ for(size_t i=0; i<noutput_items*d_vlen; i++) {
@I_TYPE@ val = iptr[i];
optr[i] = ((val < ((@I_TYPE@)0)) ? -val : val);
}
diff --git a/gr-blocks/lib/abs_XX_impl.h.t b/gr-blocks/lib/abs_XX_impl.h.t
index b31ef5fb31..fa96c84073 100644
--- a/gr-blocks/lib/abs_XX_impl.h.t
+++ b/gr-blocks/lib/abs_XX_impl.h.t
@@ -32,8 +32,11 @@ namespace gr {
class BLOCKS_API @NAME_IMPL@ : public @NAME@
{
+ private:
+ size_t d_vlen;
+
public:
- @NAME_IMPL@();
+ @NAME_IMPL@(size_t vlen);
int work(int noutput_items,
gr_vector_const_void_star &input_items,
diff --git a/gr-blocks/lib/deinterleave_impl.cc b/gr-blocks/lib/deinterleave_impl.cc
index c9d0e9aeda..9e18c35e58 100644
--- a/gr-blocks/lib/deinterleave_impl.cc
+++ b/gr-blocks/lib/deinterleave_impl.cc
@@ -41,13 +41,20 @@ namespace gr {
io_signature::make (1, io_signature::IO_INFINITE, itemsize)),
d_itemsize(itemsize), d_blocksize(blocksize), d_current_output(0)
{
+ d_size_bytes = d_itemsize * d_blocksize;
set_output_multiple(blocksize);
}
+ void
+ deinterleave_impl::forecast(int noutput_items, gr_vector_int &ninput_items_required)
+ {
+ ninput_items_required[0] = noutput_items * d_noutputs;
+ }
+
bool
deinterleave_impl::check_topology(int ninputs, int noutputs)
{
- set_relative_rate((double)noutputs);
+ set_relative_rate(1.0/(double)noutputs);
d_noutputs = noutputs;
return true;
}
@@ -61,10 +68,29 @@ namespace gr {
const char *in = (const char*)input_items[0];
char **out = (char**)&output_items[0];
- memcpy(out[d_current_output], in, d_itemsize * d_blocksize);
- consume_each(d_blocksize);
- produce(d_current_output, d_blocksize);
- d_current_output = (d_current_output + 1) % d_noutputs;
+ int count = 0, totalcount = noutput_items*d_noutputs;
+ unsigned int skip = 0;
+ unsigned int acc = 0;
+ while(count < totalcount) {
+ memcpy(out[d_current_output]+skip*d_size_bytes, in, d_size_bytes);
+ in += d_size_bytes;
+ produce(d_current_output, d_blocksize);
+ d_current_output = (d_current_output + 1) % d_noutputs;
+
+ // accumulate times through the loop; increment skip after a
+ // full pass over the output streams.
+ // This is separate than d_current_output since we could be in
+ // the middle of a loop when we exit.
+ acc++;
+ if(acc >= d_noutputs) {
+ skip++;
+ acc = 0;
+ }
+
+ // Keep track of our loop counter
+ count+=d_blocksize;
+ }
+ consume_each(totalcount);
return WORK_CALLED_PRODUCE;
}
diff --git a/gr-blocks/lib/deinterleave_impl.h b/gr-blocks/lib/deinterleave_impl.h
index 247ee3a018..71a551a69c 100644
--- a/gr-blocks/lib/deinterleave_impl.h
+++ b/gr-blocks/lib/deinterleave_impl.h
@@ -35,11 +35,12 @@ namespace gr {
unsigned int d_blocksize;
unsigned int d_current_output;
unsigned int d_noutputs;
-
+ unsigned int d_size_bytes; // block size in bytes
public:
deinterleave_impl(size_t itemsize, unsigned int blocksize);
+ void forecast(int noutput_items, gr_vector_int &ninput_items_required);
bool check_topology(int ninputs, int noutputs);
int general_work(int noutput_items,
diff --git a/gr-blocks/lib/message_strobe_impl.cc b/gr-blocks/lib/message_strobe_impl.cc
index bd0ad80142..b3f1782229 100644
--- a/gr-blocks/lib/message_strobe_impl.cc
+++ b/gr-blocks/lib/message_strobe_impl.cc
@@ -47,15 +47,15 @@ namespace gr {
message_strobe_impl::message_strobe_impl(pmt::pmt_t msg, float period_ms)
: block("message_strobe",
- io_signature::make(0, 0, 0),
- io_signature::make(0, 0, 0)),
+ io_signature::make(0, 0, 0),
+ io_signature::make(0, 0, 0)),
d_finished(false),
d_period_ms(period_ms),
d_msg(msg)
{
message_port_register_out(pmt::mp("strobe"));
- d_thread = boost::shared_ptr<boost::thread>
- (new boost::thread(boost::bind(&message_strobe_impl::run, this)));
+ d_thread = boost::shared_ptr<gr::thread::thread>
+ (new gr::thread::thread(boost::bind(&message_strobe_impl::run, this)));
message_port_register_in(pmt::mp("set_msg"));
set_msg_handler(pmt::mp("set_msg"),
diff --git a/gr-blocks/lib/message_strobe_impl.h b/gr-blocks/lib/message_strobe_impl.h
index 7a54680286..0f37cd2e0e 100644
--- a/gr-blocks/lib/message_strobe_impl.h
+++ b/gr-blocks/lib/message_strobe_impl.h
@@ -31,7 +31,7 @@ namespace gr {
class BLOCKS_API message_strobe_impl : public message_strobe
{
private:
- boost::shared_ptr<boost::thread> d_thread;
+ boost::shared_ptr<gr::thread::thread> d_thread;
bool d_finished;
float d_period_ms;
pmt::pmt_t d_msg;
diff --git a/gr-blocks/lib/message_strobe_random_impl.cc b/gr-blocks/lib/message_strobe_random_impl.cc
index 80819fc2fc..c62aad1c7a 100644
--- a/gr-blocks/lib/message_strobe_random_impl.cc
+++ b/gr-blocks/lib/message_strobe_random_impl.cc
@@ -61,8 +61,8 @@ namespace gr {
// set up ports
message_port_register_out(pmt::mp("strobe"));
- d_thread = boost::shared_ptr<boost::thread>
- (new boost::thread(boost::bind(&message_strobe_random_impl::run, this)));
+ d_thread = boost::shared_ptr<gr::thread::thread>
+ (new gr::thread::thread(boost::bind(&message_strobe_random_impl::run, this)));
message_port_register_in(pmt::mp("set_msg"));
set_msg_handler(pmt::mp("set_msg"),
diff --git a/gr-blocks/lib/message_strobe_random_impl.h b/gr-blocks/lib/message_strobe_random_impl.h
index 32eddb592c..2dcaa7effa 100644
--- a/gr-blocks/lib/message_strobe_random_impl.h
+++ b/gr-blocks/lib/message_strobe_random_impl.h
@@ -36,7 +36,7 @@ namespace gr {
class BLOCKS_API message_strobe_random_impl : public message_strobe_random
{
private:
- boost::shared_ptr<boost::thread> d_thread;
+ boost::shared_ptr<gr::thread::thread> d_thread;
bool d_finished;
float d_mean_ms;
float d_std_ms;
diff --git a/gr-blocks/lib/pdu_to_tagged_stream_impl.cc b/gr-blocks/lib/pdu_to_tagged_stream_impl.cc
index 8baa9773d6..a8ba5d22b9 100644
--- a/gr-blocks/lib/pdu_to_tagged_stream_impl.cc
+++ b/gr-blocks/lib/pdu_to_tagged_stream_impl.cc
@@ -32,90 +32,79 @@ namespace gr {
namespace blocks {
pdu_to_tagged_stream::sptr
- pdu_to_tagged_stream::make(pdu::vector_type type, const std::string& lengthtagname)
+ pdu_to_tagged_stream::make(pdu::vector_type type, const std::string& tsb_tag_key)
{
- return gnuradio::get_initial_sptr(new pdu_to_tagged_stream_impl(type, lengthtagname));
+ return gnuradio::get_initial_sptr(new pdu_to_tagged_stream_impl(type, tsb_tag_key));
}
- pdu_to_tagged_stream_impl::pdu_to_tagged_stream_impl(pdu::vector_type type, const std::string& lengthtagname)
- : sync_block("pdu_to_tagged_stream",
- io_signature::make(0, 0, 0),
- io_signature::make(1, 1, pdu::itemsize(type))),
- d_itemsize(pdu::itemsize(type)),
- d_type(type),
- d_tag(pmt::mp(lengthtagname))
+ pdu_to_tagged_stream_impl::pdu_to_tagged_stream_impl(pdu::vector_type type, const std::string& tsb_tag_key)
+ : tagged_stream_block("pdu_to_tagged_stream",
+ io_signature::make(0, 0, 0),
+ io_signature::make(1, 1, pdu::itemsize(type)),
+ tsb_tag_key),
+ d_itemsize(pdu::itemsize(type)),
+ d_type(type),
+ d_curr_len(0)
{
message_port_register_in(PDU_PORT_ID);
}
- int
- pdu_to_tagged_stream_impl::work(int noutput_items,
- gr_vector_const_void_star &input_items,
- gr_vector_void_star &output_items)
+ int pdu_to_tagged_stream_impl::calculate_output_stream_length(const gr_vector_int &)
{
- char *out = (char *)output_items[0];
- int nout = 0;
-
- // if we have remaining output, send it
- if (d_remain.size() > 0) {
- nout = std::min((size_t)d_remain.size()/d_itemsize, (size_t)noutput_items);
- memcpy(out, &d_remain[0], nout*d_itemsize);
- d_remain.erase(d_remain.begin(), d_remain.begin()+nout*d_itemsize);
- noutput_items -= nout;
- out += nout*d_itemsize;
- }
-
- // if we have space for at least one item output as much as we can
- if (noutput_items > 0) {
-
- // grab a message if one exists
- pmt::pmt_t msg(delete_head_nowait(PDU_PORT_ID));
- if (msg.get() == NULL)
- return nout;
-
- // make sure type is valid
- if (!pmt::is_pair(msg)) // TODO: implement pdu::is_valid()
- throw std::runtime_error("received a malformed pdu message");
-
- // grab the components of the pdu message
- pmt::pmt_t meta(pmt::car(msg));
- pmt::pmt_t vect(pmt::cdr(msg));
+ if (d_curr_len == 0) {
+ pmt::pmt_t msg(delete_head_nowait(PDU_PORT_ID));
+ if (msg.get() == NULL) {
+ return 0;
+ }
- // compute offset for output tag
- uint64_t offset = nitems_written(0) + nout;
+ if (!pmt::is_pair(msg))
+ throw std::runtime_error("received a malformed pdu message");
- // add a tag for pdu length
- add_item_tag(0, offset, d_tag, pmt::from_long(pmt::length(vect)), pmt::mp(alias()));
+ d_curr_meta = pmt::car(msg);
+ d_curr_vect = pmt::cdr(msg);
+ d_curr_len = pmt::length(d_curr_vect);
+ }
- // if we recieved metadata add it as tags
- if (!pmt::eq(meta, pmt::PMT_NIL) ) {
- pmt::pmt_t klist(pmt::dict_keys(meta));
- for(size_t i=0; i<pmt::length(klist); i++){
- pmt::pmt_t k(pmt::nth(i, klist));
- pmt::pmt_t v(pmt::dict_ref(meta, k, pmt::PMT_NIL));
- add_item_tag(0, offset, k, v, pmt::mp(alias()));
- }
+ return d_curr_len;
}
- // copy vector output
- size_t ncopy = std::min((size_t)noutput_items, (size_t)pmt::length(vect));
- size_t nsave = pmt::length(vect) - ncopy;
+ int
+ pdu_to_tagged_stream_impl::work (int noutput_items,
+ gr_vector_int &ninput_items,
+ gr_vector_const_void_star &input_items,
+ gr_vector_void_star &output_items)
+ {
+ uint8_t *out = (uint8_t*) output_items[0];
- // copy output
- size_t io(0);
- nout += ncopy;
- const uint8_t* ptr = (uint8_t*) uniform_vector_elements(vect, io);
- memcpy(out, ptr, ncopy*d_itemsize);
+ if (d_curr_len == 0) {
+ return 0;
+ }
- // save leftover items if needed for next work call
- if (nsave > 0) {
- d_remain.resize(nsave*d_itemsize, 0);
- memcpy(&d_remain[0], ptr + ncopy*d_itemsize, nsave*d_itemsize);
+ // work() should only be called if the current PDU fits entirely
+ // into the output buffer.
+ assert(noutput_items >= d_curr_len);
+
+ // Copy vector output
+ size_t nout = d_curr_len;
+ size_t io(0);
+ const uint8_t* ptr = (uint8_t*) uniform_vector_elements(d_curr_vect, io);
+ memcpy(out, ptr, d_curr_len*d_itemsize);
+
+ // Copy tags
+ if (!pmt::eq(d_curr_meta, pmt::PMT_NIL) ) {
+ pmt::pmt_t klist(pmt::dict_keys(d_curr_meta));
+ for (size_t i = 0; i < pmt::length(klist); i++) {
+ pmt::pmt_t k(pmt::nth(i, klist));
+ pmt::pmt_t v(pmt::dict_ref(d_curr_meta, k, pmt::PMT_NIL));
+ add_item_tag(0, nitems_written(0), k, v, pmt::mp(alias()));
}
}
+ // Reset state
+ d_curr_len = 0;
+
return nout;
- }
+ } /* work() */
} /* namespace blocks */
} /* namespace gr */
diff --git a/gr-blocks/lib/pdu_to_tagged_stream_impl.h b/gr-blocks/lib/pdu_to_tagged_stream_impl.h
index 4bfd9cfd4e..99f68147c8 100644
--- a/gr-blocks/lib/pdu_to_tagged_stream_impl.h
+++ b/gr-blocks/lib/pdu_to_tagged_stream_impl.h
@@ -32,18 +32,23 @@ namespace gr {
{
size_t d_itemsize;
pdu::vector_type d_type;
- std::vector<uint8_t> d_remain;
- pmt::pmt_t d_tag;
+ pmt::pmt_t d_curr_meta;
+ pmt::pmt_t d_curr_vect;
+ size_t d_curr_len;
public:
pdu_to_tagged_stream_impl(pdu::vector_type type, const std::string& lengthtagname="packet_len");
+ int calculate_output_stream_length(const gr_vector_int &ninput_items);
+
int work(int noutput_items,
- gr_vector_const_void_star &input_items,
- gr_vector_void_star &output_items);
+ gr_vector_int &ninput_items,
+ gr_vector_const_void_star &input_items,
+ gr_vector_void_star &output_items
+ );
};
} /* namespace blocks */
} /* namespace gr */
-#endif
+#endif /* INCLUDED_PDU_TO_TAGGED_STREAM_IMPL_H */
diff --git a/gr-blocks/lib/qa_block_tags.cc b/gr-blocks/lib/qa_block_tags.cc
index c554425f8e..d794f8edfe 100644
--- a/gr-blocks/lib/qa_block_tags.cc
+++ b/gr-blocks/lib/qa_block_tags.cc
@@ -33,20 +33,32 @@
#include <gnuradio/blocks/annotator_alltoall.h>
#include <gnuradio/blocks/annotator_1to1.h>
#include <gnuradio/blocks/keep_one_in_n.h>
-#include <gnuradio/tags.h>
// ----------------------------------------------------------------
// set to 1 to turn on debug output
// The debug output fully checks that the tags seen are what are expected. While
-// this behavior currently works with our implementation, there is no guarentee
+// this behavior currently works with our implementation, there is no guarantee
// that the tags will be coming in this specific order, so it's dangerous to
// rely on this as a test of the tag system working. We would really want to
// tags we know we should see and then test that they all occur once, but in no
// particular order.
#define QA_TAGS_DEBUG 0
+gr::tag_t make_tag(uint64_t offset, pmt::pmt_t key, pmt::pmt_t value, pmt::pmt_t srcid) {
+ gr::tag_t result;
+ result.offset = offset;
+ result.key = key;
+ result.value = value;
+ result.srcid = srcid;
+ return result;
+}
+
+std::ostream&
+operator << (std::ostream& os, const gr::tag_t &t) {
+ return os;
+}
void
qa_block_tags::t0()
{
@@ -59,8 +71,6 @@ qa_block_tags::t0()
tb->connect(src, 0, head, 0);
tb->connect(head, 0, snk, 0);
- //CPPUNIT_ASSERT_THROW(src->nitems_read(0), std::runtime_error);
- //CPPUNIT_ASSERT_THROW(src->nitems_written(0), std::runtime_error);
CPPUNIT_ASSERT_EQUAL(src->nitems_read(0), (uint64_t)0);
CPPUNIT_ASSERT_EQUAL(src->nitems_written(0), (uint64_t)0);
@@ -117,39 +127,39 @@ qa_block_tags::t1()
str1 << ann1->name() << ann1->unique_id();
str2 << ann2->name() << ann2->unique_id();
- pmt::pmt_t expected_tags3[8];
- expected_tags3[0] = mp(pmt::from_uint64(0), mp(str1.str()), mp("seq"), mp(0));
- expected_tags3[1] = mp(pmt::from_uint64(0), mp(str0.str()), mp("seq"), mp(0));
- expected_tags3[2] = mp(pmt::from_uint64(10000), mp(str1.str()), mp("seq"), mp(1));
- expected_tags3[3] = mp(pmt::from_uint64(10000), mp(str0.str()), mp("seq"), mp(2));
- expected_tags3[4] = mp(pmt::from_uint64(20000), mp(str1.str()), mp("seq"), mp(2));
- expected_tags3[5] = mp(pmt::from_uint64(20000), mp(str0.str()), mp("seq"), mp(4));
- expected_tags3[6] = mp(pmt::from_uint64(30000), mp(str1.str()), mp("seq"), mp(3));
- expected_tags3[7] = mp(pmt::from_uint64(30000), mp(str0.str()), mp("seq"), mp(6));
-
- pmt::pmt_t expected_tags4[8];
- expected_tags4[0] = mp(pmt::from_uint64(0), mp(str2.str()), mp("seq"), mp(0));
- expected_tags4[1] = mp(pmt::from_uint64(0), mp(str0.str()), mp("seq"), mp(1));
- expected_tags4[2] = mp(pmt::from_uint64(10000), mp(str2.str()), mp("seq"), mp(1));
- expected_tags4[3] = mp(pmt::from_uint64(10000), mp(str0.str()), mp("seq"), mp(3));
- expected_tags4[4] = mp(pmt::from_uint64(20000), mp(str2.str()), mp("seq"), mp(2));
- expected_tags4[5] = mp(pmt::from_uint64(20000), mp(str0.str()), mp("seq"), mp(5));
- expected_tags4[6] = mp(pmt::from_uint64(30000), mp(str2.str()), mp("seq"), mp(3));
- expected_tags4[7] = mp(pmt::from_uint64(30000), mp(str0.str()), mp("seq"), mp(7));
+ gr::tag_t expected_tags3[8];
+ expected_tags3[0] = make_tag(0, pmt::mp(str1.str()), pmt::mp("seq"), pmt::mp(0));
+ expected_tags3[1] = make_tag(0, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(0));
+ expected_tags3[2] = make_tag(10000, pmt::mp(str1.str()), pmt::mp("seq"), pmt::mp(1));
+ expected_tags3[3] = make_tag(10000, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(2));
+ expected_tags3[4] = make_tag(20000, pmt::mp(str1.str()), pmt::mp("seq"), pmt::mp(2));
+ expected_tags3[5] = make_tag(20000, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(4));
+ expected_tags3[6] = make_tag(30000, pmt::mp(str1.str()), pmt::mp("seq"), pmt::mp(3));
+ expected_tags3[7] = make_tag(30000, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(6));
+
+ gr::tag_t expected_tags4[8];
+ expected_tags4[0] = make_tag(0, pmt::mp(str2.str()), pmt::mp("seq"), pmt::mp(0));
+ expected_tags4[1] = make_tag(0, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(1));
+ expected_tags4[2] = make_tag(10000, pmt::mp(str2.str()), pmt::mp("seq"), pmt::mp(1));
+ expected_tags4[3] = make_tag(10000, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(3));
+ expected_tags4[4] = make_tag(20000, pmt::mp(str2.str()), pmt::mp("seq"), pmt::mp(2));
+ expected_tags4[5] = make_tag(20000, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(5));
+ expected_tags4[6] = make_tag(30000, pmt::mp(str2.str()), pmt::mp("seq"), pmt::mp(3));
+ expected_tags4[7] = make_tag(30000, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(7));
std::cout << std::endl << "qa_block_tags::t1" << std::endl;
// For annotator 3, we know it gets tags from ann0 and ann1, test this
for(size_t i = 0; i < tags3.size(); i++) {
std::cout << "tags3[" << i << "] = " << tags3[i] << "\t\t" << expected_tags3[i] << std::endl;
- CPPUNIT_ASSERT_EQUAL(pmt::write_string(tags3[i]), pmt::write_string(expected_tags3[i]));
+ CPPUNIT_ASSERT_EQUAL(tags3[i], expected_tags3[i]);
}
// For annotator 4, we know it gets tags from ann0 and ann2, test this
std::cout << std::endl;
for(size_t i = 0; i < tags4.size(); i++) {
std::cout << "tags4[" << i << "] = " << tags4[i] << "\t\t" << expected_tags4[i] << std::endl;
- CPPUNIT_ASSERT_EQUAL(pmt::write_string(tags4[i]), pmt::write_string(expected_tags4[i]));
+ CPPUNIT_ASSERT_EQUAL(tags4[i], expected_tags4[i]);
}
#endif
}
@@ -207,33 +217,33 @@ qa_block_tags::t2 ()
str0 << ann0->name() << ann0->unique_id();
str1 << ann1->name() << ann1->unique_id();
- pmt::pmt_t expected_tags2[12];
- expected_tags2[0] = mp(pmt::from_uint64(0), mp(str1.str()), mp("seq"), mp(0));
- expected_tags2[1] = mp(pmt::from_uint64(0), mp(str0.str()), mp("seq"), mp(0));
- expected_tags2[2] = mp(pmt::from_uint64(0), mp(str0.str()), mp("seq"), mp(1));
- expected_tags2[3] = mp(pmt::from_uint64(10000), mp(str1.str()), mp("seq"), mp(3));
- expected_tags2[4] = mp(pmt::from_uint64(10000), mp(str0.str()), mp("seq"), mp(2));
- expected_tags2[5] = mp(pmt::from_uint64(10000), mp(str0.str()), mp("seq"), mp(3));
- expected_tags2[6] = mp(pmt::from_uint64(20000), mp(str1.str()), mp("seq"), mp(6));
- expected_tags2[7] = mp(pmt::from_uint64(20000), mp(str0.str()), mp("seq"), mp(4));
- expected_tags2[8] = mp(pmt::from_uint64(20000), mp(str0.str()), mp("seq"), mp(5));
- expected_tags2[9] = mp(pmt::from_uint64(30000), mp(str1.str()), mp("seq"), mp(9));
- expected_tags2[10] = mp(pmt::from_uint64(30000), mp(str0.str()), mp("seq"), mp(6));
- expected_tags2[11] = mp(pmt::from_uint64(30000), mp(str0.str()), mp("seq"), mp(7));
-
- pmt::pmt_t expected_tags4[12];
- expected_tags4[0] = mp(pmt::from_uint64(0), mp(str1.str()), mp("seq"), mp(2));
- expected_tags4[1] = mp(pmt::from_uint64(0), mp(str0.str()), mp("seq"), mp(0));
- expected_tags4[2] = mp(pmt::from_uint64(0), mp(str0.str()), mp("seq"), mp(1));
- expected_tags4[3] = mp(pmt::from_uint64(10000), mp(str1.str()), mp("seq"), mp(5));
- expected_tags4[4] = mp(pmt::from_uint64(10000), mp(str0.str()), mp("seq"), mp(2));
- expected_tags4[5] = mp(pmt::from_uint64(10000), mp(str0.str()), mp("seq"), mp(3));
- expected_tags4[6] = mp(pmt::from_uint64(20000), mp(str1.str()), mp("seq"), mp(8));
- expected_tags4[7] = mp(pmt::from_uint64(20000), mp(str0.str()), mp("seq"), mp(4));
- expected_tags4[8] = mp(pmt::from_uint64(20000), mp(str0.str()), mp("seq"), mp(5));
- expected_tags4[9] = mp(pmt::from_uint64(30000), mp(str1.str()), mp("seq"), mp(11));
- expected_tags4[10] = mp(pmt::from_uint64(30000), mp(str0.str()), mp("seq"), mp(6));
- expected_tags4[11] = mp(pmt::from_uint64(30000), mp(str0.str()), mp("seq"), mp(7));
+ gr::tag_t expected_tags2[12];
+ expected_tags2[0] = make_tag(0, pmt::mp(str1.str()), pmt::mp("seq"), pmt::mp(0));
+ expected_tags2[1] = make_tag(0, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(0));
+ expected_tags2[2] = make_tag(0, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(1));
+ expected_tags2[3] = make_tag(10000, pmt::mp(str1.str()), pmt::mp("seq"), pmt::mp(3));
+ expected_tags2[4] = make_tag(10000, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(2));
+ expected_tags2[5] = make_tag(10000, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(3));
+ expected_tags2[6] = make_tag(20000, pmt::mp(str1.str()), pmt::mp("seq"), pmt::mp(6));
+ expected_tags2[7] = make_tag(20000, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(4));
+ expected_tags2[8] = make_tag(20000, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(5));
+ expected_tags2[9] = make_tag(30000, pmt::mp(str1.str()), pmt::mp("seq"), pmt::mp(9));
+ expected_tags2[10] = make_tag(30000, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(6));
+ expected_tags2[11] = make_tag(30000, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(7));
+
+ gr::tag_t expected_tags4[12];
+ expected_tags4[0] = make_tag(0, pmt::mp(str1.str()), pmt::mp("seq"), pmt::mp(2));
+ expected_tags4[1] = make_tag(0, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(0));
+ expected_tags4[2] = make_tag(0, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(1));
+ expected_tags4[3] = make_tag(10000, pmt::mp(str1.str()), pmt::mp("seq"), pmt::mp(5));
+ expected_tags4[4] = make_tag(10000, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(2));
+ expected_tags4[5] = make_tag(10000, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(3));
+ expected_tags4[6] = make_tag(20000, pmt::mp(str1.str()), pmt::mp("seq"), pmt::mp(8));
+ expected_tags4[7] = make_tag(20000, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(4));
+ expected_tags4[8] = make_tag(20000, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(5));
+ expected_tags4[9] = make_tag(30000, pmt::mp(str1.str()), pmt::mp("seq"), pmt::mp(11));
+ expected_tags4[10] = make_tag(30000, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(6));
+ expected_tags4[11] = make_tag(30000, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(7));
std::cout << std::endl << "qa_block_tags::t2" << std::endl;
@@ -243,13 +253,13 @@ qa_block_tags::t2 ()
// inconceivable for ann3 to have it wrong.
for(size_t i = 0; i < tags2.size(); i++) {
std::cout << "tags2[" << i << "] = " << tags2[i] << "\t\t" << expected_tags2[i] << std::endl;
- CPPUNIT_ASSERT_EQUAL(pmt::write_string(tags2[i]), pmt::write_string(expected_tags2[i]));
+ CPPUNIT_ASSERT_EQUAL(tags2[i], expected_tags2[i]);
}
std::cout << std::endl;
for(size_t i = 0; i < tags4.size(); i++) {
std::cout << "tags2[" << i << "] = " << tags4[i] << "\t\t" << expected_tags4[i] << std::endl;
- CPPUNIT_ASSERT_EQUAL(pmt::write_string(tags4[i]), pmt::write_string(expected_tags4[i]));
+ CPPUNIT_ASSERT_EQUAL(tags4[i], expected_tags4[i]);
}
#endif
}
@@ -301,39 +311,39 @@ qa_block_tags::t3()
str1 << ann1->name() << ann1->unique_id();
str2 << ann2->name() << ann2->unique_id();
- pmt::pmt_t expected_tags3[8];
- expected_tags3[0] = mp(pmt::from_uint64(0), mp(str1.str()), mp("seq"), mp(0));
- expected_tags3[1] = mp(pmt::from_uint64(0), mp(str0.str()), mp("seq"), mp(0));
- expected_tags3[2] = mp(pmt::from_uint64(10000), mp(str1.str()), mp("seq"), mp(1));
- expected_tags3[3] = mp(pmt::from_uint64(10000), mp(str0.str()), mp("seq"), mp(2));
- expected_tags3[4] = mp(pmt::from_uint64(20000), mp(str1.str()), mp("seq"), mp(2));
- expected_tags3[5] = mp(pmt::from_uint64(20000), mp(str0.str()), mp("seq"), mp(4));
- expected_tags3[6] = mp(pmt::from_uint64(30000), mp(str1.str()), mp("seq"), mp(3));
- expected_tags3[7] = mp(pmt::from_uint64(30000), mp(str0.str()), mp("seq"), mp(6));
-
- pmt::pmt_t expected_tags4[8];
- expected_tags4[0] = mp(pmt::from_uint64(0), mp(str2.str()), mp("seq"), mp(0));
- expected_tags4[1] = mp(pmt::from_uint64(0), mp(str0.str()), mp("seq"), mp(1));
- expected_tags4[2] = mp(pmt::from_uint64(10000), mp(str2.str()), mp("seq"), mp(1));
- expected_tags4[3] = mp(pmt::from_uint64(10000), mp(str0.str()), mp("seq"), mp(3));
- expected_tags4[4] = mp(pmt::from_uint64(20000), mp(str2.str()), mp("seq"), mp(2));
- expected_tags4[5] = mp(pmt::from_uint64(20000), mp(str0.str()), mp("seq"), mp(5));
- expected_tags4[6] = mp(pmt::from_uint64(30000), mp(str2.str()), mp("seq"), mp(3));
- expected_tags4[7] = mp(pmt::from_uint64(30000), mp(str0.str()), mp("seq"), mp(7));
+ gr::tag_t expected_tags3[8];
+ expected_tags3[0] = make_tag(0, pmt::mp(str1.str()), pmt::mp("seq"), pmt::mp(0));
+ expected_tags3[1] = make_tag(0, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(0));
+ expected_tags3[2] = make_tag(10000, pmt::mp(str1.str()), pmt::mp("seq"), pmt::mp(1));
+ expected_tags3[3] = make_tag(10000, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(2));
+ expected_tags3[4] = make_tag(20000, pmt::mp(str1.str()), pmt::mp("seq"), pmt::mp(2));
+ expected_tags3[5] = make_tag(20000, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(4));
+ expected_tags3[6] = make_tag(30000, pmt::mp(str1.str()), pmt::mp("seq"), pmt::mp(3));
+ expected_tags3[7] = make_tag(30000, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(6));
+
+ gr::tag_t expected_tags4[8];
+ expected_tags4[0] = make_tag(0, pmt::mp(str2.str()), pmt::mp("seq"), pmt::mp(0));
+ expected_tags4[1] = make_tag(0, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(1));
+ expected_tags4[2] = make_tag(10000, pmt::mp(str2.str()), pmt::mp("seq"), pmt::mp(1));
+ expected_tags4[3] = make_tag(10000, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(3));
+ expected_tags4[4] = make_tag(20000, pmt::mp(str2.str()), pmt::mp("seq"), pmt::mp(2));
+ expected_tags4[5] = make_tag(20000, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(5));
+ expected_tags4[6] = make_tag(30000, pmt::mp(str2.str()), pmt::mp("seq"), pmt::mp(3));
+ expected_tags4[7] = make_tag(30000, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(7));
std::cout << std::endl << "qa_block_tags::t3" << std::endl;
// For annotator 3, we know it gets tags from ann0 and ann1, test this
for(size_t i = 0; i < tags3.size(); i++) {
std::cout << "tags3[" << i << "] = " << tags3[i] << "\t\t" << expected_tags3[i] << std::endl;
- CPPUNIT_ASSERT_EQUAL(pmt::write_string(tags3[i]), pmt::write_string(expected_tags3[i]));
+ CPPUNIT_ASSERT_EQUAL(tags3[i], expected_tags3[i]);
}
// For annotator 4, we know it gets tags from ann0 and ann2, test this
std::cout << std::endl;
for(size_t i = 0; i < tags4.size(); i++) {
std::cout << "tags4[" << i << "] = " << tags4[i] << "\t\t" << expected_tags4[i] << std::endl;
- CPPUNIT_ASSERT_EQUAL(pmt::write_string(tags4[i]), pmt::write_string(expected_tags4[i]));
+ CPPUNIT_ASSERT_EQUAL(tags4[i], expected_tags4[i]);
}
#endif
}
@@ -409,23 +419,23 @@ qa_block_tags::t5()
str1 << ann1->name() << ann1->unique_id();
str2 << ann2->name() << ann2->unique_id();
- pmt_t expected_tags1[5];
- expected_tags1[0] = mp(pmt::from_uint64(0), mp(str0.str()), mp("seq"), mp(0));
- expected_tags1[1] = mp(pmt::from_uint64(10000), mp(str0.str()), mp("seq"), mp(1));
- expected_tags1[2] = mp(pmt::from_uint64(20000), mp(str0.str()), mp("seq"), mp(2));
- expected_tags1[3] = mp(pmt::from_uint64(30000), mp(str0.str()), mp("seq"), mp(3));
-
- pmt_t expected_tags2[10];
- expected_tags2[0] = mp(pmt::from_uint64(0), mp(str1.str()), mp("seq"), mp(0));
- expected_tags2[1] = mp(pmt::from_uint64(0), mp(str0.str()), mp("seq"), mp(0));
- expected_tags2[2] = mp(pmt::from_uint64(1000), mp(str1.str()), mp("seq"), mp(1));
- expected_tags2[3] = mp(pmt::from_uint64(1000), mp(str0.str()), mp("seq"), mp(1));
- expected_tags2[4] = mp(pmt::from_uint64(2000), mp(str1.str()), mp("seq"), mp(2));
- expected_tags2[5] = mp(pmt::from_uint64(2000), mp(str0.str()), mp("seq"), mp(2));
- expected_tags2[6] = mp(pmt::from_uint64(3000), mp(str1.str()), mp("seq"), mp(3));
- expected_tags2[7] = mp(pmt::from_uint64(3000), mp(str0.str()), mp("seq"), mp(3));
- expected_tags2[8] = mp(pmt::from_uint64(4000), mp(str1.str()), mp("seq"), mp(4));
- expected_tags2[9] = mp(pmt::from_uint64(4000), mp(str0.str()), mp("seq"), mp(4));
+ gr::tag_t expected_tags1[5];
+ expected_tags1[0] = make_tag(0, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(0));
+ expected_tags1[1] = make_tag(10000, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(1));
+ expected_tags1[2] = make_tag(20000, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(2));
+ expected_tags1[3] = make_tag(30000, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(3));
+
+ gr::tag_t expected_tags2[10];
+ expected_tags2[0] = make_tag(0, pmt::mp(str1.str()), pmt::mp("seq"), pmt::mp(0));
+ expected_tags2[1] = make_tag(0, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(0));
+ expected_tags2[2] = make_tag(1000, pmt::mp(str1.str()), pmt::mp("seq"), pmt::mp(1));
+ expected_tags2[3] = make_tag(1000, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(1));
+ expected_tags2[4] = make_tag(2000, pmt::mp(str1.str()), pmt::mp("seq"), pmt::mp(2));
+ expected_tags2[5] = make_tag(2000, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(2));
+ expected_tags2[6] = make_tag(3000, pmt::mp(str1.str()), pmt::mp("seq"), pmt::mp(3));
+ expected_tags2[7] = make_tag(3000, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(3));
+ expected_tags2[8] = make_tag(4000, pmt::mp(str1.str()), pmt::mp("seq"), pmt::mp(4));
+ expected_tags2[9] = make_tag(4000, pmt::mp(str0.str()), pmt::mp("seq"), pmt::mp(4));
std::cout << std::endl << "qa_block_tags::t5" << std::endl;
@@ -433,7 +443,7 @@ qa_block_tags::t5()
std::cout << "tags1.size(): " << tags1.size() << std::endl;
for(size_t i = 0; i < tags1.size(); i++) {
std::cout << "tags1[" << i << "] = " << tags1[i] << "\t\t" << expected_tags1[i] << std::endl;
- CPPUNIT_ASSERT_EQUAL(pmt::write_string(tags1[i]), pmt::write_string(expected_tags1[i]));
+ CPPUNIT_ASSERT_EQUAL(tags1[i], expected_tags1[i]);
}
// annotator 2 gets tags from annotators 0 and 1
@@ -441,7 +451,7 @@ qa_block_tags::t5()
std::cout << "tags2.size(): " << tags2.size() << std::endl;
for(size_t i = 0; i < tags2.size(); i++) {
std::cout << "tags2[" << i << "] = " << tags2[i] << "\t\t" << expected_tags2[i] << std::endl;
- CPPUNIT_ASSERT_EQUAL(pmt::write_string(tags2[i]), pmt::write_string(expected_tags2[i]));
+ CPPUNIT_ASSERT_EQUAL(tags2[i], expected_tags2[i]);
}
#endif
}
diff --git a/gr-blocks/lib/repack_bits_bb_impl.cc b/gr-blocks/lib/repack_bits_bb_impl.cc
index af83187e92..de61bf414f 100644
--- a/gr-blocks/lib/repack_bits_bb_impl.cc
+++ b/gr-blocks/lib/repack_bits_bb_impl.cc
@@ -31,20 +31,25 @@ namespace gr {
namespace blocks {
repack_bits_bb::sptr
- repack_bits_bb::make(int k, int l, const std::string &len_tag_key, bool align_output)
+ repack_bits_bb::make(int k, int l, const std::string &len_tag_key,
+ bool align_output, endianness_t endianness)
{
- return gnuradio::get_initial_sptr (new repack_bits_bb_impl(k, l, len_tag_key, align_output));
+ return gnuradio::get_initial_sptr
+ (new repack_bits_bb_impl(k, l, len_tag_key,
+ align_output, endianness));
}
- repack_bits_bb_impl::repack_bits_bb_impl(int k, int l, const std::string &len_tag_key, bool align_output)
+ repack_bits_bb_impl::repack_bits_bb_impl(int k, int l, const std::string &len_tag_key,
+ bool align_output, endianness_t endianness)
: tagged_stream_block("repack_bits_bb",
- io_signature::make(1, 1, sizeof (char)),
- io_signature::make(1, 1, sizeof (char)),
- len_tag_key),
- d_k(k), d_l(l),
- d_packet_mode(!len_tag_key.empty()),
- d_in_index(0), d_out_index(0),
- d_align_output(align_output)
+ io_signature::make(1, 1, sizeof(char)),
+ io_signature::make(1, 1, sizeof(char)),
+ len_tag_key),
+ d_k(k), d_l(l),
+ d_packet_mode(!len_tag_key.empty()),
+ d_in_index(0), d_out_index(0),
+ d_align_output(align_output),
+ d_endianness(endianness)
{
if (d_k > 8 || d_k < 1 || d_l > 8 || d_l < 1) {
throw std::invalid_argument("k and l must be in [1, 8]");
@@ -88,31 +93,70 @@ namespace gr {
int n_read = 0;
int n_written = 0;
- while(n_written < bytes_to_write && n_read < ninput_items[0]) {
- if (d_out_index == 0) { // Starting a fresh byte
- out[n_written] = 0;
- }
- out[n_written] |= ((in[n_read] >> d_in_index) & 0x01) << d_out_index;
-
- d_in_index = (d_in_index + 1) % d_k;
- d_out_index = (d_out_index + 1) % d_l;
- if (d_in_index == 0) {
- n_read++;
- d_in_index = 0;
- }
- if (d_out_index == 0) {
- n_written++;
- d_out_index = 0;
- }
- }
-
- if (d_packet_mode) {
- if (d_out_index) {
- n_written++;
- d_out_index = 0;
- }
- } else {
- consume_each(n_read);
+ switch(d_endianness) {
+ case GR_LSB_FIRST:
+ while(n_written < bytes_to_write && n_read < ninput_items[0]) {
+ if(d_out_index == 0) { // Starting a fresh byte
+ out[n_written] = 0;
+ }
+ out[n_written] |= ((in[n_read] >> d_in_index) & 0x01) << d_out_index;
+
+ d_in_index = (d_in_index + 1) % d_k;
+ d_out_index = (d_out_index + 1) % d_l;
+ if(d_in_index == 0) {
+ n_read++;
+ d_in_index = 0;
+ }
+ if(d_out_index == 0) {
+ n_written++;
+ d_out_index = 0;
+ }
+ }
+
+ if(d_packet_mode) {
+ if(d_out_index) {
+ n_written++;
+ d_out_index = 0;
+ }
+ }
+ else {
+ consume_each(n_read);
+ }
+ break;
+
+
+ case GR_MSB_FIRST:
+ while(n_written < bytes_to_write && n_read < ninput_items[0]) {
+ if(d_out_index == 0) { // Starting a fresh byte
+ out[n_written] = 0;
+ }
+ out[n_written] |= ((in[n_read] >> (d_k - 1 - d_in_index)) & 0x01) << (d_l - 1 - d_out_index);
+
+ d_in_index = (d_in_index + 1) % d_k;
+ d_out_index = (d_out_index + 1) % d_l;
+ if(d_in_index == 0) {
+ n_read++;
+ d_in_index = 0;
+ }
+ if(d_out_index == 0) {
+ n_written++;
+ d_out_index = 0;
+ }
+ }
+
+ if(d_packet_mode) {
+ if(d_out_index) {
+ n_written++;
+ d_out_index = 0;
+ }
+ }
+ else {
+ consume_each(n_read);
+ }
+ break;
+
+ default:
+ throw std::runtime_error("repack_bits_bb: unrecognized endianness value.");
}
return n_written;
@@ -120,4 +164,3 @@ namespace gr {
} /* namespace blocks */
} /* namespace gr */
-
diff --git a/gr-blocks/lib/repack_bits_bb_impl.h b/gr-blocks/lib/repack_bits_bb_impl.h
index ffb8349d35..8c57c74c23 100644
--- a/gr-blocks/lib/repack_bits_bb_impl.h
+++ b/gr-blocks/lib/repack_bits_bb_impl.h
@@ -37,12 +37,14 @@ namespace gr {
int d_in_index; // Current bit of input byte
int d_out_index; // Current bit of output byte
bool d_align_output; //! true if the output shall be aligned, false if the input shall be aligned
+ endianness_t d_endianness;
protected:
int calculate_output_stream_length(const gr_vector_int &ninput_items);
public:
- repack_bits_bb_impl(int k, int l, const std::string &len_tag_key, bool align_output);
+ repack_bits_bb_impl(int k, int l, const std::string &len_tag_key,
+ bool align_output, endianness_t endianness=GR_LSB_FIRST);
~repack_bits_bb_impl();
int work(int noutput_items,
@@ -55,4 +57,3 @@ namespace gr {
} // namespace gr
#endif /* INCLUDED_BLOCKS_REPACK_BITS_BB_IMPL_H */
-
diff --git a/gr-blocks/lib/throttle_impl.cc b/gr-blocks/lib/throttle_impl.cc
index f46decee11..7c24f80ae1 100644
--- a/gr-blocks/lib/throttle_impl.cc
+++ b/gr-blocks/lib/throttle_impl.cc
@@ -57,6 +57,14 @@ namespace gr {
{
}
+ bool
+ throttle_impl::start()
+ {
+ d_start = boost::get_system_time();
+ d_total_samples = 0;
+ return block::start();
+ }
+
void
throttle_impl::set_sample_rate(double rate)
{
diff --git a/gr-blocks/lib/throttle_impl.h b/gr-blocks/lib/throttle_impl.h
index c5e43d7564..6afacbba5d 100644
--- a/gr-blocks/lib/throttle_impl.h
+++ b/gr-blocks/lib/throttle_impl.h
@@ -41,6 +41,9 @@ namespace gr {
throttle_impl(size_t itemsize, double samples_per_sec, bool ignore_tags=true);
~throttle_impl();
+ // Overloading gr::block::start to reset timer
+ bool start();
+
void setup_rpc();
void set_sample_rate(double rate);
diff --git a/gr-blocks/lib/udp_sink_impl.cc b/gr-blocks/lib/udp_sink_impl.cc
index ae6488f6dd..6989fdb27c 100644
--- a/gr-blocks/lib/udp_sink_impl.cc
+++ b/gr-blocks/lib/udp_sink_impl.cc
@@ -76,13 +76,12 @@ namespace gr {
std::string s_port = (boost::format("%d")%port).str();
if(host.size() > 0) {
boost::asio::ip::udp::resolver resolver(d_io_service);
- boost::asio::ip::udp::resolver::query query(boost::asio::ip::udp::v4(),
- host, s_port,
+ boost::asio::ip::udp::resolver::query query(host, s_port,
boost::asio::ip::resolver_query_base::passive);
d_endpoint = *resolver.resolve(query);
d_socket = new boost::asio::ip::udp::socket(d_io_service);
- d_socket->open(boost::asio::ip::udp::v4());
+ d_socket->open(d_endpoint.protocol());
boost::asio::socket_base::reuse_address roption(true);
d_socket->set_option(roption);
diff --git a/gr-blocks/lib/udp_source_impl.cc b/gr-blocks/lib/udp_source_impl.cc
index c3ab8953e7..ca4018464d 100644
--- a/gr-blocks/lib/udp_source_impl.cc
+++ b/gr-blocks/lib/udp_source_impl.cc
@@ -84,8 +84,7 @@ namespace gr {
if(host.size() > 0) {
boost::asio::ip::udp::resolver resolver(d_io_service);
- boost::asio::ip::udp::resolver::query query(boost::asio::ip::udp::v4(),
- d_host, s_port,
+ boost::asio::ip::udp::resolver::query query(d_host, s_port,
boost::asio::ip::resolver_query_base::passive);
d_endpoint = *resolver.resolve(query);
diff --git a/gr-blocks/lib/vector_source_X_impl.cc.t b/gr-blocks/lib/vector_source_X_impl.cc.t
index 93f672bfb9..cb17c70d63 100644
--- a/gr-blocks/lib/vector_source_X_impl.cc.t
+++ b/gr-blocks/lib/vector_source_X_impl.cc.t
@@ -106,7 +106,7 @@ namespace gr {
optr += size;
for(unsigned t = 0; t < d_tags.size(); t++) {
add_item_tag(0, nitems_written(0)+i+d_tags[t].offset,
- d_tags[t].key, d_tags[t].value);
+ d_tags[t].key, d_tags[t].value, d_tags[t].srcid);
}
}
}
diff --git a/gr-blocks/python/blocks/qa_pdu.py b/gr-blocks/python/blocks/qa_pdu.py
index 5a29e04735..bbee3605ba 100755
--- a/gr-blocks/python/blocks/qa_pdu.py
+++ b/gr-blocks/python/blocks/qa_pdu.py
@@ -99,8 +99,6 @@ class test_pdu(gr_unittest.TestCase):
msg = pmt.cons( pmt.PMT_NIL, pmt.init_f32vector(10, src_data))
src.to_basic_block()._post(port, msg)
- src.set_max_noutput_items(5)
-
self.tb.start()
#ideally, would wait until we get ten samples
time.sleep(0.2)
diff --git a/gr-blocks/python/blocks/qa_repack_bits_bb.py b/gr-blocks/python/blocks/qa_repack_bits_bb.py
index 10880b196a..50e1506196 100755
--- a/gr-blocks/python/blocks/qa_repack_bits_bb.py
+++ b/gr-blocks/python/blocks/qa_repack_bits_bb.py
@@ -46,6 +46,19 @@ class qa_repack_bits_bb (gr_unittest.TestCase):
self.tb.run ()
self.assertEqual(sink.data(), expected_data)
+ def test_001_simple_msb (self):
+ """ Very simple test, 2 bits -> 1 with MSB set """
+ src_data = (0b11, 0b01, 0b10)
+ expected_data = (0b1, 0b1, 0b0, 0b1, 0b1, 0b0)
+ k = 2
+ l = 1
+ src = blocks.vector_source_b(src_data, False, 1)
+ repack = blocks.repack_bits_bb(k, l, "", False, gr.GR_MSB_FIRST)
+ sink = blocks.vector_sink_b()
+ self.tb.connect(src, repack, sink)
+ self.tb.run ()
+ self.assertEqual(sink.data(), expected_data)
+
def test_002_three (self):
""" 8 -> 3 """
src_data = (0b11111101, 0b11111111, 0b11111111)
@@ -59,6 +72,32 @@ class qa_repack_bits_bb (gr_unittest.TestCase):
self.tb.run ()
self.assertEqual(sink.data(), expected_data)
+ def test_002_three (self):
+ """ 8 -> 3 """
+ src_data = (0b11111101, 0b11111111, 0b11111111)
+ expected_data = (0b101,) + (0b111,) * 7
+ k = 8
+ l = 3
+ src = blocks.vector_source_b(src_data, False, 1)
+ repack = blocks.repack_bits_bb(k, l)
+ sink = blocks.vector_sink_b()
+ self.tb.connect(src, repack, sink)
+ self.tb.run ()
+ self.assertEqual(sink.data(), expected_data)
+
+ def test_002_three_msb (self):
+ """ 8 -> 3 """
+ src_data = (0b11111101, 0b11111111, 0b11111111)
+ expected_data = (0b111,) + (0b111,) + (0b011,) + (0b111,) * 5
+ k = 8
+ l = 3
+ src = blocks.vector_source_b(src_data, False, 1)
+ repack = blocks.repack_bits_bb(k, l, "", False, gr.GR_MSB_FIRST)
+ sink = blocks.vector_sink_b()
+ self.tb.connect(src, repack, sink)
+ self.tb.run ()
+ self.assertEqual(sink.data(), expected_data)
+
def test_003_lots_of_bytes (self):
""" Lots and lots of bytes, multiple packer stages """
src_data = tuple([random.randint(0, 255) for x in range(3*5*7*8 * 10)])
@@ -72,6 +111,19 @@ class qa_repack_bits_bb (gr_unittest.TestCase):
self.tb.run ()
self.assertEqual(sink.data(), src_data)
+ def test_003_lots_of_bytes_msb (self):
+ """ Lots and lots of bytes, multiple packer stages """
+ src_data = tuple([random.randint(0, 255) for x in range(3*5*7*8 * 10)])
+ src = blocks.vector_source_b(src_data, False, 1)
+ repack1 = blocks.repack_bits_bb(8, 3, "", False, gr.GR_MSB_FIRST)
+ repack2 = blocks.repack_bits_bb(3, 5, "", False, gr.GR_MSB_FIRST)
+ repack3 = blocks.repack_bits_bb(5, 7, "", False, gr.GR_MSB_FIRST)
+ repack4 = blocks.repack_bits_bb(7, 8, "", False, gr.GR_MSB_FIRST)
+ sink = blocks.vector_sink_b()
+ self.tb.connect(src, repack1, repack2, repack3, repack4, sink)
+ self.tb.run ()
+ self.assertEqual(sink.data(), src_data)
+
def test_004_three_with_tags (self):
""" 8 -> 3 """
src_data = (0b11111101, 0b11111111)
@@ -112,4 +164,3 @@ class qa_repack_bits_bb (gr_unittest.TestCase):
if __name__ == '__main__':
gr_unittest.run(qa_repack_bits_bb, "qa_repack_bits_bb.xml")
-
diff --git a/gr-digital/grc/digital_costas_loop_cc.xml b/gr-digital/grc/digital_costas_loop_cc.xml
index 668c43dec6..40db3a4a6f 100644
--- a/gr-digital/grc/digital_costas_loop_cc.xml
+++ b/gr-digital/grc/digital_costas_loop_cc.xml
@@ -5,34 +5,60 @@
###################################################
-->
<block>
- <name>Costas Loop</name>
- <key>digital_costas_loop_cc</key>
- <import>from gnuradio import digital</import>
- <make>digital.costas_loop_cc($w, $order)</make>
- <callback>set_loop_bandwidth($w)</callback>
- <param>
- <name>Loop Bandwidth</name>
- <key>w</key>
- <type>real</type>
- </param>
- <param>
- <name>Order</name>
- <key>order</key>
- <type>int</type>
- </param>
- <sink>
- <name>in</name>
- <type>complex</type>
- </sink>
- <source>
- <name>out</name>
- <type>complex</type>
- </source>
+ <name>Costas Loop</name>
+ <key>digital_costas_loop_cc</key>
+ <import>from gnuradio import digital</import>
+ <make>digital.costas_loop_cc($w, $order, $use_snr)</make>
+ <callback>set_loop_bandwidth($w)</callback>
- <!-- Optional Outputs -->
- <source>
- <name>frequency</name>
- <type>float</type>
- <optional>1</optional>
- </source>
+ <param>
+ <name>Loop Bandwidth</name>
+ <key>w</key>
+ <type>real</type>
+ </param>
+
+ <param>
+ <name>Order</name>
+ <key>order</key>
+ <type>int</type>
+ </param>
+
+ <param>
+ <name>Use SNR</name>
+ <key>use_snr</key>
+ <value>False</value>
+ <type>enum</type>
+ <hide>part</hide>
+ <option>
+ <name>Yes</name>
+ <key>True</key>
+ </option>
+ <option>
+ <name>No</name>
+ <key>False</key>
+ </option>
+ </param>
+
+ <sink>
+ <name>in</name>
+ <type>complex</type>
+ </sink>
+
+ <sink>
+ <name>noise</name>
+ <type>message</type>
+ <optional>1</optional>
+ </sink>
+
+ <source>
+ <name>out</name>
+ <type>complex</type>
+ </source>
+
+ <!-- Optional Outputs -->
+ <source>
+ <name>frequency</name>
+ <type>float</type>
+ <optional>1</optional>
+ </source>
</block>
diff --git a/gr-digital/include/gnuradio/digital/costas_loop_cc.h b/gr-digital/include/gnuradio/digital/costas_loop_cc.h
index d924d969b7..ff5b9b993a 100644
--- a/gr-digital/include/gnuradio/digital/costas_loop_cc.h
+++ b/gr-digital/include/gnuradio/digital/costas_loop_cc.h
@@ -1,6 +1,6 @@
/* -*- c++ -*- */
/*
- * Copyright 2006,2011,2012 Free Software Foundation, Inc.
+ * Copyright 2006,2011,2012,2014 Free Software Foundation, Inc.
*
* This file is part of GNU Radio
*
@@ -58,6 +58,9 @@ namespace gr {
* The Costas loop can have two output streams:
* \li stream 1 (required) is the baseband I and Q;
* \li stream 2 (optional) is the normalized frequency of the loop
+ *
+ * There is a single optional message input:
+ * \li noise: A noise floor estimate used to calculate the SNR of a sample.
*/
class DIGITAL_API costas_loop_cc
: virtual public sync_block,
@@ -72,8 +75,10 @@ namespace gr {
*
* \param loop_bw internal 2nd order loop bandwidth (~ 2pi/100)
* \param order the loop order, either 2, 4, or 8
+ * \param use_snr Use or ignore SNR estimates (from noise message port)
+ * in measurements; also uses tanh instead of slicing.
*/
- static sptr make(float loop_bw, int order);
+ static sptr make(float loop_bw, int order, bool use_snr=false);
/*!
* Returns the current value of the loop error.
diff --git a/gr-digital/include/gnuradio/digital/ofdm_frame_equalizer_vcvc.h b/gr-digital/include/gnuradio/digital/ofdm_frame_equalizer_vcvc.h
index 2715316a93..be38b6f8ae 100644
--- a/gr-digital/include/gnuradio/digital/ofdm_frame_equalizer_vcvc.h
+++ b/gr-digital/include/gnuradio/digital/ofdm_frame_equalizer_vcvc.h
@@ -58,18 +58,19 @@ namespace gr {
/*!
* \param equalizer The equalizer object that will do the actual work
* \param cp_len Length of the cyclic prefix in samples (required to correct the frequency offset)
- * \param len_tag_key Length tag key
+ * \param tsb_key TSB key
* \param propagate_channel_state If true, the channel state after the last symbol
* will be added to the first symbol as a tag
- * \param fixed_frame_len Set if the frame length is fixed throughout,
- * helps with book keeping.
+ * \param fixed_frame_len Set if the frame length is fixed. When this value is given,
+ * the TSB tag key can be left empty, but it is useful even
+ * when using tagged streams at the input.
*/
static sptr make(
- ofdm_equalizer_base::sptr equalizer,
- int cp_len,
- const std::string &len_tag_key = "frame_len",
- bool propagate_channel_state=false,
- int fixed_frame_len=0
+ ofdm_equalizer_base::sptr equalizer,
+ int cp_len,
+ const std::string &tsb_key="frame_len",
+ bool propagate_channel_state=false,
+ int fixed_frame_len=0
);
};
diff --git a/gr-digital/lib/costas_loop_cc_impl.cc b/gr-digital/lib/costas_loop_cc_impl.cc
index 36f95ac022..a53045ac55 100644
--- a/gr-digital/lib/costas_loop_cc_impl.cc
+++ b/gr-digital/lib/costas_loop_cc_impl.cc
@@ -35,37 +35,52 @@ namespace gr {
namespace digital {
costas_loop_cc::sptr
- costas_loop_cc::make(float loop_bw, int order)
+ costas_loop_cc::make(float loop_bw, int order, bool use_snr)
{
return gnuradio::get_initial_sptr
- (new costas_loop_cc_impl(loop_bw, order));
+ (new costas_loop_cc_impl(loop_bw, order, use_snr));
}
- costas_loop_cc_impl::costas_loop_cc_impl(float loop_bw, int order)
+ costas_loop_cc_impl::costas_loop_cc_impl(float loop_bw, int order, bool use_snr)
: sync_block("costas_loop_cc",
io_signature::make(1, 1, sizeof(gr_complex)),
io_signature::make2(1, 2, sizeof(gr_complex), sizeof(float))),
blocks::control_loop(loop_bw, 1.0, -1.0),
- d_order(order), d_error(0), d_phase_detector(NULL)
+ d_order(order), d_error(0), d_noise(1.0), d_phase_detector(NULL)
{
// Set up the phase detector to use based on the constellation order
switch(d_order) {
case 2:
- d_phase_detector = &costas_loop_cc_impl::phase_detector_2;
+ if(use_snr)
+ d_phase_detector = &costas_loop_cc_impl::phase_detector_snr_2;
+ else
+ d_phase_detector = &costas_loop_cc_impl::phase_detector_2;
break;
case 4:
- d_phase_detector = &costas_loop_cc_impl::phase_detector_4;
+ if(use_snr)
+ d_phase_detector = &costas_loop_cc_impl::phase_detector_snr_4;
+ else
+ d_phase_detector = &costas_loop_cc_impl::phase_detector_4;
break;
case 8:
- d_phase_detector = &costas_loop_cc_impl::phase_detector_8;
+ if(use_snr)
+ d_phase_detector = &costas_loop_cc_impl::phase_detector_snr_8;
+ else
+ d_phase_detector = &costas_loop_cc_impl::phase_detector_8;
break;
default:
throw std::invalid_argument("order must be 2, 4, or 8");
break;
}
+
+ message_port_register_in(pmt::mp("noise"));
+ set_msg_handler(
+ pmt::mp("noise"),
+ boost::bind(&costas_loop_cc_impl::handle_set_noise,
+ this, _1));
}
costas_loop_cc_impl::~costas_loop_cc_impl()
@@ -114,11 +129,50 @@ namespace gr {
}
float
+ costas_loop_cc_impl::phase_detector_snr_8(gr_complex sample) const
+ {
+ float K = (sqrt(2.0) - 1);
+ float snr = abs(sample)*abs(sample) / d_noise;
+ if(fabsf(sample.real()) >= fabsf(sample.imag())) {
+ return ((blocks::tanhf_lut(snr*sample.real()) * sample.imag()) -
+ (blocks::tanhf_lut(snr*sample.imag()) * sample.real() * K));
+ }
+ else {
+ return ((blocks::tanhf_lut(snr*sample.real()) * sample.imag() * K) -
+ (blocks::tanhf_lut(snr*sample.imag()) * sample.real()));
+ }
+ }
+
+ float
+ costas_loop_cc_impl::phase_detector_snr_4(gr_complex sample) const
+ {
+ float snr = abs(sample)*abs(sample) / d_noise;
+ return ((blocks::tanhf_lut(snr*sample.real()) * sample.imag()) -
+ (blocks::tanhf_lut(snr*sample.imag()) * sample.real()));
+ }
+
+ float
+ costas_loop_cc_impl::phase_detector_snr_2(gr_complex sample) const
+ {
+ float snr = abs(sample)*abs(sample) / d_noise;
+ return blocks::tanhf_lut(snr*sample.real()) * sample.imag();
+ }
+
+ float
costas_loop_cc_impl::error() const
{
return d_error;
}
+ void
+ costas_loop_cc_impl::handle_set_noise(pmt::pmt_t msg)
+ {
+ if(pmt::is_real(msg)) {
+ d_noise = pmt::to_double(msg);
+ d_noise = powf(10.0f, d_noise/10.0f);
+ }
+ }
+
int
costas_loop_cc_impl::work(int noutput_items,
gr_vector_const_void_star &input_items,
diff --git a/gr-digital/lib/costas_loop_cc_impl.h b/gr-digital/lib/costas_loop_cc_impl.h
index 665724236b..ebd05e2e93 100644
--- a/gr-digital/lib/costas_loop_cc_impl.h
+++ b/gr-digital/lib/costas_loop_cc_impl.h
@@ -1,6 +1,6 @@
/* -*- c++ -*- */
/*
- * Copyright 2006,2011,2012 Free Software Foundation, Inc.
+ * Copyright 2006,2011,2012,2014 Free Software Foundation, Inc.
*
* This file is part of GNU Radio
*
@@ -34,33 +34,68 @@ namespace gr {
private:
int d_order;
float d_error;
+ float d_noise;
- /*! \brief the phase detector circuit for 8th-order PSK loops
+ /*! \brief the phase detector circuit for 8th-order PSK loops.
+ *
* \param sample complex sample
* \return the phase error
*/
float phase_detector_8(gr_complex sample) const; // for 8PSK
- /*! \brief the phase detector circuit for fourth-order loops
+ /*! \brief the phase detector circuit for fourth-order loops.
+ *
* \param sample complex sample
* \return the phase error
*/
float phase_detector_4(gr_complex sample) const; // for QPSK
- /*! \brief the phase detector circuit for second-order loops
+ /*! \brief the phase detector circuit for second-order loops.
+ *
* \param sample a complex sample
* \return the phase error
*/
float phase_detector_2(gr_complex sample) const; // for BPSK
+
+ /*! \brief the phase detector circuit for 8th-order PSK
+ * loops. Uses tanh instead of slicing and the noise estimate
+ * from the message port to estimated SNR of the samples.
+ *
+ * \param sample complex sample
+ * \return the phase error
+ */
+ float phase_detector_snr_8(gr_complex sample) const; // for 8PSK
+
+ /*! \brief the phase detector circuit for fourth-order
+ * loops. Uses tanh instead of slicing and the noise estimate
+ * from the message port to estimated SNR of the samples.
+ *
+ * \param sample complex sample
+ * \return the phase error
+ */
+ float phase_detector_snr_4(gr_complex sample) const; // for QPSK
+
+ /*! \brief the phase detector circuit for second-order
+ * loops. Uses tanh instead of slicing and the noise estimate
+ * from the message port to estimated SNR of the samples.
+ *
+ * \param sample a complex sample
+ * \return the phase error
+ */
+ float phase_detector_snr_2(gr_complex sample) const; // for BPSK
+
+
float (costas_loop_cc_impl::*d_phase_detector)(gr_complex sample) const;
public:
- costas_loop_cc_impl(float loop_bw, int order);
+ costas_loop_cc_impl(float loop_bw, int order, bool use_snr=false);
~costas_loop_cc_impl();
float error() const;
+ void handle_set_noise(pmt::pmt_t msg);
+
void setup_rpc();
int work(int noutput_items,
diff --git a/gr-digital/lib/header_payload_demux_impl.cc b/gr-digital/lib/header_payload_demux_impl.cc
index 15308c0be1..160f54036d 100644
--- a/gr-digital/lib/header_payload_demux_impl.cc
+++ b/gr-digital/lib/header_payload_demux_impl.cc
@@ -1,5 +1,5 @@
/* -*- c++ -*- */
-/* Copyright 2012,2013 Free Software Foundation, Inc.
+/* Copyright 2012-2014 Free Software Foundation, Inc.
*
* This file is part of GNU Radio
*
@@ -300,20 +300,19 @@ namespace gr {
}
}
if (d_uses_trigger_tag) {
- std::vector<tag_t> tags;
- get_tags_in_range(tags, 0, nitems_read(0), nitems_read(0)+noutput_items, d_trigger_tag_key);
- uint64_t min_offset = ULLONG_MAX;
- int tag_index = -1;
- for (unsigned i = 0; i < tags.size(); i++) {
- if (tags[i].offset < min_offset) {
- tag_index = (int) i;
- min_offset = tags[i].offset;
- }
- }
- if (tag_index != -1) {
- remove_item_tag(0, tags[tag_index]);
- return min_offset - nitems_read(0);
- }
+ std::vector<tag_t> tags;
+ get_tags_in_range(tags, 0, nitems_read(0), nitems_read(0)+noutput_items, d_trigger_tag_key);
+ uint64_t min_offset = ULLONG_MAX;
+ int tag_index = -1;
+ for (unsigned i = 0; i < tags.size(); i++) {
+ if (tags[i].offset < min_offset) {
+ tag_index = (int) i;
+ min_offset = tags[i].offset;
+ }
+ }
+ if (tag_index != -1) {
+ return min_offset - nitems_read(0);
+ }
}
return -1;
} /* find_trigger_signal() */
@@ -388,26 +387,30 @@ namespace gr {
// Copy tags
std::vector<tag_t> tags;
get_tags_in_range(
- tags, 0,
- nitems_read(0),
- nitems_read(0) + n_symbols * (d_items_per_symbol + d_gi)
+ tags, 0,
+ nitems_read(0),
+ nitems_read(0) + n_symbols * (d_items_per_symbol + d_gi)
);
- for (unsigned t = 0; t < tags.size(); t++) {
- int new_offset = tags[t].offset - nitems_read(0);
- if (d_output_symbols) {
- new_offset /= (d_items_per_symbol + d_gi);
- } else if (d_gi) {
- int pos_on_symbol = (new_offset % (d_items_per_symbol + d_gi)) - d_gi;
- if (pos_on_symbol < 0) {
- pos_on_symbol = 0;
- }
- new_offset = (new_offset / (d_items_per_symbol + d_gi)) + pos_on_symbol;
- }
- add_item_tag(port,
- nitems_written(port) + new_offset,
- tags[t].key,
- tags[t].value
- );
+ for (size_t t = 0; t < tags.size(); t++) {
+ // The trigger tag is *not* propagated
+ if (tags[t].key == d_trigger_tag_key) {
+ continue;
+ }
+ int new_offset = tags[t].offset - nitems_read(0);
+ if (d_output_symbols) {
+ new_offset /= (d_items_per_symbol + d_gi);
+ } else if (d_gi) {
+ int pos_on_symbol = (new_offset % (d_items_per_symbol + d_gi)) - d_gi;
+ if (pos_on_symbol < 0) {
+ pos_on_symbol = 0;
+ }
+ new_offset = (new_offset / (d_items_per_symbol + d_gi)) + pos_on_symbol;
+ }
+ add_item_tag(port,
+ nitems_written(port) + new_offset,
+ tags[t].key,
+ tags[t].value
+ );
}
} /* copy_n_symbols() */
diff --git a/gr-digital/lib/ofdm_frame_equalizer_vcvc_impl.cc b/gr-digital/lib/ofdm_frame_equalizer_vcvc_impl.cc
index 4446306a8b..70e840d778 100644
--- a/gr-digital/lib/ofdm_frame_equalizer_vcvc_impl.cc
+++ b/gr-digital/lib/ofdm_frame_equalizer_vcvc_impl.cc
@@ -29,6 +29,9 @@
#define M_TWOPI (2*M_PI)
+static const pmt::pmt_t CARR_OFFSET_KEY = pmt::mp("ofdm_sync_carr_offset");
+static const pmt::pmt_t CHAN_TAPS_KEY = pmt::mp("ofdm_sync_chan_taps");
+
namespace gr {
namespace digital {
@@ -36,14 +39,14 @@ namespace gr {
ofdm_frame_equalizer_vcvc::make(
ofdm_equalizer_base::sptr equalizer,
int cp_len,
- const std::string &len_tag_key,
+ const std::string &tsb_key,
bool propagate_channel_state,
int fixed_frame_len
)
{
return gnuradio::get_initial_sptr (
new ofdm_frame_equalizer_vcvc_impl(
- equalizer, cp_len, len_tag_key, propagate_channel_state, fixed_frame_len
+ equalizer, cp_len, tsb_key, propagate_channel_state, fixed_frame_len
)
);
}
@@ -51,13 +54,13 @@ namespace gr {
ofdm_frame_equalizer_vcvc_impl::ofdm_frame_equalizer_vcvc_impl(
ofdm_equalizer_base::sptr equalizer,
int cp_len,
- const std::string &len_tag_key,
+ const std::string &tsb_key,
bool propagate_channel_state,
int fixed_frame_len
) : tagged_stream_block("ofdm_frame_equalizer_vcvc",
io_signature::make(1, 1, sizeof (gr_complex) * equalizer->fft_len()),
io_signature::make(1, 1, sizeof (gr_complex) * equalizer->fft_len()),
- len_tag_key),
+ tsb_key),
d_fft_len(equalizer->fft_len()),
d_cp_len(cp_len),
d_eq(equalizer),
@@ -65,16 +68,18 @@ namespace gr {
d_fixed_frame_len(fixed_frame_len),
d_channel_state(equalizer->fft_len(), gr_complex(1, 0))
{
- if (len_tag_key.empty() && fixed_frame_len == 0) {
- throw std::invalid_argument("Either specify a length tag or a frame length!");
+ if (tsb_key.empty() && fixed_frame_len == 0) {
+ throw std::invalid_argument("Either specify a TSB tag or a fixed frame length!");
}
if (d_fixed_frame_len < 0) {
- throw std::invalid_argument("Invalid frame length!");
+ throw std::invalid_argument("Invalid frame length!");
}
if (d_fixed_frame_len) {
- set_output_multiple(d_fixed_frame_len);
+ set_output_multiple(d_fixed_frame_len);
}
set_relative_rate(1.0);
+ // Really, we have TPP_ONE_TO_ONE, but the channel state is not propagated
+ set_tag_propagation_policy(TPP_DONT);
}
ofdm_frame_equalizer_vcvc_impl::~ofdm_frame_equalizer_vcvc_impl()
@@ -83,18 +88,17 @@ namespace gr {
void
ofdm_frame_equalizer_vcvc_impl::parse_length_tags(
- const std::vector<std::vector<tag_t> > &tags,
- gr_vector_int &n_input_items_reqd
- ){
+ const std::vector<std::vector<tag_t> > &tags,
+ gr_vector_int &n_input_items_reqd
+ ) {
if (d_fixed_frame_len) {
- n_input_items_reqd[0] = d_fixed_frame_len;
+ n_input_items_reqd[0] = d_fixed_frame_len;
} else {
- for (unsigned k = 0; k < tags[0].size(); k++) {
- if (tags[0][k].key == pmt::string_to_symbol(d_length_tag_key_str)) {
- n_input_items_reqd[0] = pmt::to_long(tags[0][k].value);
- remove_item_tag(0, tags[0][k]);
- }
- }
+ for (unsigned k = 0; k < tags[0].size(); k++) {
+ if (tags[0][k].key == pmt::string_to_symbol(d_length_tag_key_str)) {
+ n_input_items_reqd[0] = pmt::to_long(tags[0][k].value);
+ }
+ }
}
}
@@ -114,15 +118,14 @@ namespace gr {
}
std::vector<tag_t> tags;
- get_tags_in_range(tags, 0, nitems_read(0), nitems_read(0)+1);
+ get_tags_in_window(tags, 0, 0, 1);
for (unsigned i = 0; i < tags.size(); i++) {
- if (pmt::symbol_to_string(tags[i].key) == "ofdm_sync_chan_taps") {
- d_channel_state = pmt::c32vector_elements(tags[i].value);
- remove_item_tag(0, tags[i]);
- }
- if (pmt::symbol_to_string(tags[i].key) == "ofdm_sync_carr_offset") {
- carrier_offset = pmt::to_long(tags[i].value);
- }
+ if (pmt::symbol_to_string(tags[i].key) == "ofdm_sync_chan_taps") {
+ d_channel_state = pmt::c32vector_elements(tags[i].value);
+ }
+ if (pmt::symbol_to_string(tags[i].key) == "ofdm_sync_carr_offset") {
+ carrier_offset = pmt::to_long(tags[i].value);
+ }
}
// Copy the frame and the channel state vector such that the symbols are shifted to the correct position
@@ -157,7 +160,16 @@ namespace gr {
// Update the channel state regarding the frequency offset
phase_correction = gr_expj(M_TWOPI * carrier_offset * d_cp_len / d_fft_len * frame_len);
for (int k = 0; k < d_fft_len; k++) {
- d_channel_state[k] *= phase_correction;
+ d_channel_state[k] *= phase_correction;
+ }
+
+ // Propagate tags (except for the channel state and the TSB tag)
+ get_tags_in_window(tags, 0, 0, frame_len);
+ for (size_t i = 0; i < tags.size(); i++) {
+ if (tags[i].key != CHAN_TAPS_KEY
+ and tags[i].key != pmt::mp(d_length_tag_key_str)) {
+ add_item_tag(0, tags[i]);
+ }
}
// Housekeeping
diff --git a/gr-digital/lib/ofdm_serializer_vcc_impl.cc b/gr-digital/lib/ofdm_serializer_vcc_impl.cc
index f6c796d3c5..1398dcd2a1 100644
--- a/gr-digital/lib/ofdm_serializer_vcc_impl.cc
+++ b/gr-digital/lib/ofdm_serializer_vcc_impl.cc
@@ -1,5 +1,5 @@
/* -*- c++ -*- */
-/* Copyright 2012 Free Software Foundation, Inc.
+/* Copyright 2012,2014 Free Software Foundation, Inc.
*
* This file is part of GNU Radio
*
@@ -157,55 +157,57 @@ namespace gr {
std::vector<tag_t> tags;
// Packet mode
if (!d_length_tag_key_str.empty()) {
- get_tags_in_range(tags, 0, nitems_read(0), nitems_read(0)+1);
- for (unsigned i = 0; i < tags.size(); i++) {
- if (tags[i].key == d_carr_offset_key) {
- carr_offset = pmt::to_long(tags[i].value);
- }
- if (tags[i].key == d_packet_len_tag_key) {
- packet_length = pmt::to_long(tags[i].value);
- remove_item_tag(0, tags[i]);
- }
- }
+ get_tags_in_range(tags, 0, nitems_read(0), nitems_read(0)+1);
+ for (unsigned i = 0; i < tags.size(); i++) {
+ if (tags[i].key == d_carr_offset_key) {
+ carr_offset = pmt::to_long(tags[i].value);
+ }
+ if (tags[i].key == d_packet_len_tag_key) {
+ packet_length = pmt::to_long(tags[i].value);
+ }
+ }
} else {
- // recalc frame length from noutput_items
- frame_length = 0;
- int sym_per_frame = 0;
- while ((sym_per_frame + d_occupied_carriers[(frame_length + 1) % d_occupied_carriers.size()].size()) < (size_t)noutput_items) {
- frame_length++;
- sym_per_frame += d_occupied_carriers[(frame_length + 1) % d_occupied_carriers.size()].size();
- }
+ // recalc frame length from noutput_items
+ frame_length = 0;
+ int sym_per_frame = 0;
+ while ((sym_per_frame + d_occupied_carriers[(frame_length + 1) % d_occupied_carriers.size()].size()) < (size_t)noutput_items) {
+ frame_length++;
+ sym_per_frame += d_occupied_carriers[(frame_length + 1) % d_occupied_carriers.size()].size();
+ }
}
// Copy symbols
int n_out_symbols = 0;
for (int i = 0; i < frame_length; i++) {
- // Copy all tags associated with this input OFDM symbol onto the first output symbol
- get_tags_in_range(tags, 0,
- nitems_read(0)+i,
- nitems_read(0)+i+1
- );
- for (unsigned t = 0; t < tags.size(); t++) {
- add_item_tag(0, nitems_written(0)+n_out_symbols,
- tags[t].key,
- tags[t].value
- );
- }
- for (unsigned k = 0; k < d_occupied_carriers[d_curr_set].size(); k++) {
- out[n_out_symbols++] = in[i * d_fft_len + d_occupied_carriers[d_curr_set][k] + carr_offset];
- }
- if (packet_length && n_out_symbols > packet_length) {
- n_out_symbols = packet_length;
- break;
- }
- d_curr_set = (d_curr_set + 1) % d_occupied_carriers.size();
+ // Copy all tags associated with this input OFDM symbol onto the first output symbol
+ get_tags_in_range(tags, 0,
+ nitems_read(0)+i,
+ nitems_read(0)+i+1
+ );
+ for (size_t t = 0; t < tags.size(); t++) {
+ // The packet length tag is not propagated
+ if (tags[t].key != d_packet_len_tag_key) {
+ add_item_tag(0, nitems_written(0)+n_out_symbols,
+ tags[t].key,
+ tags[t].value
+ );
+ }
+ }
+ for (unsigned k = 0; k < d_occupied_carriers[d_curr_set].size(); k++) {
+ out[n_out_symbols++] = in[i * d_fft_len + d_occupied_carriers[d_curr_set][k] + carr_offset];
+ }
+ if (packet_length && n_out_symbols > packet_length) {
+ n_out_symbols = packet_length;
+ break;
+ }
+ d_curr_set = (d_curr_set + 1) % d_occupied_carriers.size();
}
// Housekeeping
if (d_length_tag_key_str.empty()) {
- consume_each(frame_length);
+ consume_each(frame_length);
} else {
- d_curr_set = d_symbols_skipped;
+ d_curr_set = d_symbols_skipped;
}
return n_out_symbols;
diff --git a/gr-digital/python/digital/qa_costas_loop_cc.py b/gr-digital/python/digital/qa_costas_loop_cc.py
index 9ecb017599..e48f45cc22 100755
--- a/gr-digital/python/digital/qa_costas_loop_cc.py
+++ b/gr-digital/python/digital/qa_costas_loop_cc.py
@@ -1,24 +1,24 @@
#!/usr/bin/env python
#
# Copyright 2011,2013 Free Software Foundation, Inc.
-#
+#
# This file is part of GNU Radio
-#
+#
# GNU Radio is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 3, or (at your option)
# any later version.
-#
+#
# GNU Radio is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
-#
+#
# You should have received a copy of the GNU General Public License
# along with GNU Radio; see the file COPYING. If not, write to
# the Free Software Foundation, Inc., 51 Franklin Street,
# Boston, MA 02110-1301, USA.
-#
+#
import random
import cmath
@@ -46,7 +46,7 @@ class test_costas_loop_cc(gr_unittest.TestCase):
self.tb.connect(self.src, self.test, self.snk)
self.tb.run()
-
+
expected_result = data
dst_data = self.snk.data()
self.assertComplexTuplesAlmostEqual(expected_result, dst_data, 5)
@@ -77,7 +77,7 @@ class test_costas_loop_cc(gr_unittest.TestCase):
rot = cmath.exp(0.2j) # some small rotation
data = [complex(2*random.randint(0,1)-1, 0) for i in xrange(100)]
-
+
N = 40 # settling time
expected_result = data[N:]
data = [rot*d for d in data]
@@ -89,7 +89,7 @@ class test_costas_loop_cc(gr_unittest.TestCase):
self.tb.run()
dst_data = self.snk.data()[N:]
-
+
# generously compare results; the loop will converge near to, but
# not exactly on, the target data
self.assertComplexTuplesAlmostEqual(expected_result, dst_data, 2)
@@ -103,7 +103,7 @@ class test_costas_loop_cc(gr_unittest.TestCase):
rot = cmath.exp(0.2j) # some small rotation
data = [complex(2*random.randint(0,1)-1, 2*random.randint(0,1)-1)
for i in xrange(100)]
-
+
N = 40 # settling time
expected_result = data[N:]
data = [rot*d for d in data]
@@ -130,7 +130,7 @@ class test_costas_loop_cc(gr_unittest.TestCase):
const = psk.psk_constellation(order)
data = [random.randint(0,7) for i in xrange(100)]
data = [2*rot*const.points()[d] for d in data]
-
+
N = 40 # settling time
expected_result = data[N:]
@@ -144,7 +144,7 @@ class test_costas_loop_cc(gr_unittest.TestCase):
self.tb.run()
dst_data = self.snk.data()[N:]
-
+
# generously compare results; the loop will converge near to, but
# not exactly on, the target data
self.assertComplexTuplesAlmostEqual(expected_result, dst_data, 2)
diff --git a/gr-digital/python/digital/qa_header_payload_demux.py b/gr-digital/python/digital/qa_header_payload_demux.py
index 0b754fe248..8006d4442e 100755
--- a/gr-digital/python/digital/qa_header_payload_demux.py
+++ b/gr-digital/python/digital/qa_header_payload_demux.py
@@ -113,6 +113,86 @@ class qa_header_payload_demux (gr_unittest.TestCase):
]
self.assertEqual(expected_tags_payload, ptags_payload)
+ def test_001_t_tags (self):
+ """ Like the previous test, but use a trigger tag instead of
+ a trigger signal.
+ """
+ n_zeros = 1
+ header = (1, 2, 3)
+ payload = tuple(range(5, 20))
+ data_signal = (0,) * n_zeros + header + payload
+ # Trigger tag
+ trigger_tag = gr.tag_t()
+ trigger_tag.offset = n_zeros
+ trigger_tag.key = pmt.string_to_symbol('detect')
+ trigger_tag.value = pmt.PMT_T
+ # This is dropped:
+ testtag1 = gr.tag_t()
+ testtag1.offset = 0
+ testtag1.key = pmt.string_to_symbol('tag1')
+ testtag1.value = pmt.from_long(0)
+ # This goes on output 0, item 0:
+ testtag2 = gr.tag_t()
+ testtag2.offset = n_zeros
+ testtag2.key = pmt.string_to_symbol('tag2')
+ testtag2.value = pmt.from_long(23)
+ # This goes on output 0, item 2:
+ testtag3 = gr.tag_t()
+ testtag3.offset = n_zeros + len(header) - 1
+ testtag3.key = pmt.string_to_symbol('tag3')
+ testtag3.value = pmt.from_long(42)
+ # This goes on output 1, item 3:
+ testtag4 = gr.tag_t()
+ testtag4.offset = n_zeros + len(header) + 3
+ testtag4.key = pmt.string_to_symbol('tag4')
+ testtag4.value = pmt.from_long(314)
+ data_src = blocks.vector_source_f(
+ data_signal,
+ False,
+ tags=(trigger_tag, testtag1, testtag2, testtag3, testtag4)
+ )
+ hpd = digital.header_payload_demux(
+ len(header), 1, 0, "frame_len", "detect", False, gr.sizeof_float
+ )
+ self.assertEqual(pmt.length(hpd.message_ports_in()), 2) #extra system port defined for you
+ header_sink = blocks.vector_sink_f()
+ payload_sink = blocks.vector_sink_f()
+
+ self.tb.connect(data_src, (hpd, 0))
+ self.tb.connect((hpd, 0), header_sink)
+ self.tb.connect((hpd, 1), payload_sink)
+ self.tb.start()
+ time.sleep(.2) # Need this, otherwise, the next message is ignored
+ hpd.to_basic_block()._post(
+ pmt.intern('header_data'),
+ pmt.from_long(len(payload))
+ )
+ while len(payload_sink.data()) < len(payload):
+ time.sleep(.2)
+ self.tb.stop()
+ self.tb.wait()
+
+ self.assertEqual(header_sink.data(), header)
+ self.assertEqual(payload_sink.data(), payload)
+ ptags_header = []
+ for tag in header_sink.tags():
+ ptag = gr.tag_to_python(tag)
+ ptags_header.append({'key': ptag.key, 'offset': ptag.offset})
+ expected_tags_header = [
+ {'key': 'tag2', 'offset': 0},
+ {'key': 'tag3', 'offset': 2},
+ ]
+ self.assertEqual(expected_tags_header, ptags_header)
+ ptags_payload = []
+ for tag in payload_sink.tags():
+ ptag = gr.tag_to_python(tag)
+ ptags_payload.append({'key': ptag.key, 'offset': ptag.offset})
+ expected_tags_payload = [
+ {'key': 'frame_len', 'offset': 0},
+ {'key': 'tag4', 'offset': 3},
+ ]
+ self.assertEqual(expected_tags_payload, ptags_payload)
+
def test_002_symbols (self):
"""
Same as before, but operate on symbols
diff --git a/gr-digital/python/digital/qa_ofdm_frame_equalizer_vcvc.py b/gr-digital/python/digital/qa_ofdm_frame_equalizer_vcvc.py
index c42fb2b907..1b3ffb7738 100755
--- a/gr-digital/python/digital/qa_ofdm_frame_equalizer_vcvc.py
+++ b/gr-digital/python/digital/qa_ofdm_frame_equalizer_vcvc.py
@@ -72,7 +72,7 @@ class qa_ofdm_frame_equalizer_vcvc (gr_unittest.TestCase):
ptag = gr.tag_to_python(tag)
tag_dict[ptag.key] = ptag.value
expected_dict = {
- 'foo': 42
+ 'foo': 42
}
self.assertEqual(tag_dict, expected_dict)
diff --git a/gr-fec/lib/decoder_impl.cc b/gr-fec/lib/decoder_impl.cc
index 38d564374a..d570c4077a 100644
--- a/gr-fec/lib/decoder_impl.cc
+++ b/gr-fec/lib/decoder_impl.cc
@@ -95,11 +95,6 @@ namespace gr {
noutput_items/(output_multiple() - d_decoder->get_history()) :
innum;
- /*
- GR_LOG_DEBUG(d_debug_logger, boost::format("%1%, %2%, %3%") \
- % outnum % ninput_items[0] % items);
- */
-
for(int i = 0; i < items; ++i) {
d_decoder->generic_work((void*)(in+(i*d_decoder->get_input_size()*d_input_item_size)),
(void*)(out+(i*d_decoder->get_output_size()*d_output_item_size)));
@@ -111,9 +106,6 @@ namespace gr {
int consumed = static_cast<int>(items/relative_rate()*(output_multiple() - d_decoder->get_history()) + 0.5);
int returned = items*(output_multiple() - d_decoder->get_history());
- GR_LOG_DEBUG(d_debug_logger, boost::format("consumed %1%") % consumed);
- GR_LOG_DEBUG(d_debug_logger, boost::format("returned %1%") % returned);
-
consume_each(consumed);
return returned;
}
diff --git a/gr-fec/lib/encoder_impl.cc b/gr-fec/lib/encoder_impl.cc
index 31f56eac58..dfa1f48592 100644
--- a/gr-fec/lib/encoder_impl.cc
+++ b/gr-fec/lib/encoder_impl.cc
@@ -91,24 +91,11 @@ namespace gr {
char *inbuffer = (char*)input_items[0];
char *outbuffer = (char*)output_items[0];
- /*
- GR_LOG_DEBUG(d_debug_logger, boost::format("%1%, %2%, %3%") \
- % noutput_items % ninput_items[0] % (noutput_items/output_multiple()));
- */
-
-
for(int i = 0; i < noutput_items/output_multiple(); i++) {
d_encoder->generic_work((void*)(inbuffer+(i*d_input_size)),
(void*)(outbuffer+(i*d_output_size)));
}
- /*
- GR_LOG_DEBUG(d_debug_logger, boost::format("consuming: %1%") \
- % (fixed_rate_noutput_to_ninput(noutput_items)));
- GR_LOG_DEBUG(d_debug_logger, boost::format("returning: %1%") \
- % (noutput_items));
- */
-
consume_each(fixed_rate_noutput_to_ninput(noutput_items));
return noutput_items;
}
diff --git a/gr-fft/include/gnuradio/fft/window.h b/gr-fft/include/gnuradio/fft/window.h
index c1de1814c7..4b13ddd5c3 100644
--- a/gr-fft/include/gnuradio/fft/window.h
+++ b/gr-fft/include/gnuradio/fft/window.h
@@ -179,32 +179,47 @@ namespace gr {
static std::vector<float> blackmanharris(int ntaps, int atten=92);
/*!
- * \brief Build a Nuttal (or Blackman-Nuttal) window.
+ * \brief Build a Nuttall (or Blackman-Nuttall) window.
*
* See: http://en.wikipedia.org/wiki/Window_function#Blackman.E2.80.93Nuttall_window
*
* \param ntaps Number of coefficients in the window.
*/
+ static std::vector<float> nuttall(int ntaps);
+
+ /*!
+ * Deprecated: use nuttall window instead.
+ */
static std::vector<float> nuttal(int ntaps);
/*!
- * \brief Alias to the Nuttal window.
+ * \brief Alias to the Nuttall window.
*
* \param ntaps Number of coefficients in the window.
*/
+ static std::vector<float> blackman_nuttall(int ntaps);
+
+ /*!
+ * Deprecated: use blackman_nuttall window instead.
+ */
static std::vector<float> blackman_nuttal(int ntaps);
/*!
- * \brief Build a Nuttal continuous first derivative window.
+ * \brief Build a Nuttall continuous first derivative window.
*
* See: http://en.wikipedia.org/wiki/Window_function#Nuttall_window.2C_continuous_first_derivative
*
* \param ntaps Number of coefficients in the window.
*/
+ static std::vector<float> nuttall_cfd(int ntaps);
+
+ /*!
+ * Deprecated: use nuttall_cfd window instead.
+ */
static std::vector<float> nuttal_cfd(int ntaps);
/*!
- * \brief Build a Nuttal continuous first derivative window.
+ * \brief Build a flat top window.
*
* See: http://en.wikipedia.org/wiki/Window_function#Flat_top_window
*
diff --git a/gr-fft/lib/window.cc b/gr-fft/lib/window.cc
index 965b11bf46..126b28978d 100644
--- a/gr-fft/lib/window.cc
+++ b/gr-fft/lib/window.cc
@@ -209,18 +209,36 @@ namespace gr {
std::vector<float>
window::nuttal(int ntaps)
{
+ return nuttall(ntaps);
+ }
+
+ std::vector<float>
+ window::nuttall(int ntaps)
+ {
return coswindow(ntaps, 0.3635819, 0.4891775, 0.1365995, 0.0106411);
}
std::vector<float>
window::blackman_nuttal(int ntaps)
{
- return nuttal(ntaps);
+ return nuttall(ntaps);
+ }
+
+ std::vector<float>
+ window::blackman_nuttall(int ntaps)
+ {
+ return nuttall(ntaps);
}
std::vector<float>
window::nuttal_cfd(int ntaps)
{
+ return nuttall_cfd(ntaps);
+ }
+
+ std::vector<float>
+ window::nuttall_cfd(int ntaps)
+ {
return coswindow(ntaps, 0.355768, 0.487396, 0.144232, 0.012604);
}
diff --git a/gr-qtgui/grc/qtgui_freq_sink_x.xml b/gr-qtgui/grc/qtgui_freq_sink_x.xml
index 94989f5c68..aea46ab4e3 100644
--- a/gr-qtgui/grc/qtgui_freq_sink_x.xml
+++ b/gr-qtgui/grc/qtgui_freq_sink_x.xml
@@ -22,10 +22,14 @@ qtgui.$(type.fcn)(
)
self.$(id).set_update_time($update_time)
self.$(id).set_y_axis($ymin, $ymax)
+self.$(id).set_trigger_mode($tr_mode, $tr_level, $tr_chan, $tr_tag)
self.$(id).enable_autoscale($autoscale)
self.$(id).enable_grid($grid)
self.$(id).set_fft_average($average)
+if $type == type(float()):
+ self.$(id).set_plot_pos_half(not $freqhalf)
+
labels = [$label1, $label2, $label3, $label4, $label5,
$label6, $label7, $label8, $label9, $label10]
widths = [$width1, $width2, $width3, $width4, $width5,
@@ -53,6 +57,7 @@ $(gui_hint()($win))</make>
<param_tab_order>
<tab>General</tab>
+ <tab>Trigger</tab>
<tab>Config</tab>
</param_tab_order>
@@ -80,6 +85,25 @@ $(gui_hint()($win))</make>
<type>int</type>
</param>
+
+ <param>
+ <name>Spectrum Width</name>
+ <key>freqhalf</key>
+ <value>True</value>
+ <type>enum</type>
+ <hide>#if $type() == "float" then 'part' else 'all'#</hide>
+ <option>
+ <name>Full</name>
+ <key>True</key>
+ </option>
+ <option>
+ <name>Half</name>
+ <key>False</key>
+ </option>
+ </param>
+
+
+
<param>
<name>Window Type</name>
<key>wintype</key>
@@ -237,6 +261,63 @@ $(gui_hint()($win))</make>
</option>
</param>
+
+ <!-- Begin Trigger Tab items -->
+ <param>
+ <name>Trigger Mode</name>
+ <key>tr_mode</key>
+ <value>qtgui.TRIG_MODE_FREE</value>
+ <type>enum</type>
+ <hide>part</hide>
+ <option>
+ <name>Free</name>
+ <key>qtgui.TRIG_MODE_FREE</key>
+ </option>
+ <option>
+ <name>Auto</name>
+ <key>qtgui.TRIG_MODE_AUTO</key>
+ </option>
+ <option>
+ <name>Normal</name>
+ <key>qtgui.TRIG_MODE_NORM</key>
+ </option>
+ <option>
+ <name>Tag</name>
+ <key>qtgui.TRIG_MODE_TAG</key>
+ </option>
+ <tab>Trigger</tab>
+ </param>
+
+ <param>
+ <name>Trigger Level</name>
+ <key>tr_level</key>
+ <value>0.0</value>
+ <type>float</type>
+ <hide>part</hide>
+ <tab>Trigger</tab>
+ </param>
+
+ <param>
+ <name>Trigger Channel</name>
+ <key>tr_chan</key>
+ <value>0</value>
+ <type>int</type>
+ <hide>part</hide>
+ <tab>Trigger</tab>
+ </param>
+
+ <param>
+ <name>Trigger Tag Key</name>
+ <key>tr_tag</key>
+ <value>""</value>
+ <type>string</type>
+ <hide>part</hide>
+ <tab>Trigger</tab>
+ </param>
+
+
+
+ <!-- Begin Config Tab items -->
<param>
<name>Line 1 Label</name>
<key>label1</key>
diff --git a/gr-qtgui/grc/qtgui_waterfall_sink_x.xml b/gr-qtgui/grc/qtgui_waterfall_sink_x.xml
index d6e0f5911b..3b6e37e16b 100644
--- a/gr-qtgui/grc/qtgui_waterfall_sink_x.xml
+++ b/gr-qtgui/grc/qtgui_waterfall_sink_x.xml
@@ -23,6 +23,9 @@ qtgui.$(type.fcn)(
self.$(id).set_update_time($update_time)
self.$(id).enable_grid($grid)
+if $type == type(float()):
+ self.$(id).set_plot_pos_half(not $freqhalf)
+
labels = [$label1, $label2, $label3, $label4, $label5,
$label6, $label7, $label8, $label9, $label10]
colors = [$color1, $color2, $color3, $color4, $color5,
@@ -77,6 +80,22 @@ $(gui_hint()($win))</make>
</param>
<param>
+ <name>Spectrum Width</name>
+ <key>freqhalf</key>
+ <value>True</value>
+ <type>enum</type>
+ <hide>#if $type() == "float" then 'part' else 'all'#</hide>
+ <option>
+ <name>Full</name>
+ <key>True</key>
+ </option>
+ <option>
+ <name>Half</name>
+ <key>False</key>
+ </option>
+ </param>
+
+ <param>
<name>Window Type</name>
<key>wintype</key>
<value>firdes.WIN_BLACKMAN_hARRIS</value>
diff --git a/gr-qtgui/include/gnuradio/qtgui/FrequencyDisplayPlot.h b/gr-qtgui/include/gnuradio/qtgui/FrequencyDisplayPlot.h
index ac7dfe8b6d..cb44fbe510 100644
--- a/gr-qtgui/include/gnuradio/qtgui/FrequencyDisplayPlot.h
+++ b/gr-qtgui/include/gnuradio/qtgui/FrequencyDisplayPlot.h
@@ -118,6 +118,8 @@ public slots:
void setAutoScale(bool state);
+ void setPlotPosHalf(bool half);
+
private:
void _resetXAxisPoints();
void _autoScale(double bottom, double top);
@@ -143,6 +145,7 @@ private:
double d_stop_frequency;
double d_ymax;
double d_ymin;
+ bool d_half_freq;
QwtPlotMarker* d_lower_intensity_marker;
QwtPlotMarker* d_upper_intensity_marker;
diff --git a/gr-qtgui/include/gnuradio/qtgui/WaterfallDisplayPlot.h b/gr-qtgui/include/gnuradio/qtgui/WaterfallDisplayPlot.h
index 4fdd065093..37c6183608 100644
--- a/gr-qtgui/include/gnuradio/qtgui/WaterfallDisplayPlot.h
+++ b/gr-qtgui/include/gnuradio/qtgui/WaterfallDisplayPlot.h
@@ -95,6 +95,7 @@ public slots:
void setIntensityColorMapType1(int);
void setUserDefinedLowIntensityColor(QColor);
void setUserDefinedHighIntensityColor(QColor);
+ void setPlotPosHalf(bool half);
signals:
void updatedLowerIntensityLevel(const double);
@@ -106,6 +107,7 @@ private:
double d_start_frequency;
double d_stop_frequency;
int d_xaxis_multiplier;
+ bool d_half_freq;
std::vector<WaterfallData*> d_data;
diff --git a/gr-qtgui/include/gnuradio/qtgui/freq_sink_c.h b/gr-qtgui/include/gnuradio/qtgui/freq_sink_c.h
index d02505c6f6..f49e7b062f 100644
--- a/gr-qtgui/include/gnuradio/qtgui/freq_sink_c.h
+++ b/gr-qtgui/include/gnuradio/qtgui/freq_sink_c.h
@@ -28,6 +28,7 @@
#endif
#include <gnuradio/qtgui/api.h>
+#include <gnuradio/qtgui/trigger_mode.h>
#include <gnuradio/sync_block.h>
#include <qapplication.h>
#include <gnuradio/filter/firdes.h>
@@ -118,6 +119,33 @@ namespace gr {
virtual void set_line_marker(int which, int marker) = 0;
virtual void set_line_alpha(int which, double alpha) = 0;
+ /*!
+ * Set up a trigger for the sink to know when to start
+ * plotting. Useful to isolate events and avoid noise.
+ *
+ * The trigger modes are Free, Auto, Normal, and Tag (see
+ * gr::qtgui::trigger_mode). The first three are like a normal
+ * trigger function. Free means free running with no trigger,
+ * auto will trigger if the trigger event is seen, but will
+ * still plot otherwise, and normal will hold until the trigger
+ * event is observed. The Tag trigger mode allows us to trigger
+ * off a specific stream tag. The tag trigger is based only on
+ * the name of the tag, so when a tag of the given name is seen,
+ * the trigger is activated.
+ *
+ * In auto and normal mode, we look to see if the magnitude of
+ * the any FFT point is over the set level.
+ *
+ * \param mode The trigger_mode: free, auto, normal, or tag.
+ * \param level The magnitude of the trigger even for auto or normal modes.
+ * \param channel Which input channel to use for the trigger events.
+ * \param tag_key The name (as a string) of the tag to trigger off
+ * of if using the tag mode.
+ */
+ virtual void set_trigger_mode(trigger_mode mode,
+ float level, int channel,
+ const std::string &tag_key="") = 0;
+
virtual std::string title() = 0;
virtual std::string line_label(int which) = 0;
virtual std::string line_color(int which) = 0;
diff --git a/gr-qtgui/include/gnuradio/qtgui/freq_sink_f.h b/gr-qtgui/include/gnuradio/qtgui/freq_sink_f.h
index 81f9c0c8c5..ed65d3136c 100644
--- a/gr-qtgui/include/gnuradio/qtgui/freq_sink_f.h
+++ b/gr-qtgui/include/gnuradio/qtgui/freq_sink_f.h
@@ -28,6 +28,7 @@
#endif
#include <gnuradio/qtgui/api.h>
+#include <gnuradio/qtgui/trigger_mode.h>
#include <gnuradio/sync_block.h>
#include <qapplication.h>
#include <gnuradio/filter/firdes.h>
@@ -117,6 +118,40 @@ namespace gr {
virtual void set_line_marker(int which, int marker) = 0;
virtual void set_line_alpha(int which, double alpha) = 0;
+ /*!
+ * Pass "true" to this function to only show the positive half
+ * of the spectrum. By default, this plotter shows the full
+ * spectrum (positive and negative halves).
+ */
+ virtual void set_plot_pos_half(bool half) = 0;
+
+ /*!
+ * Set up a trigger for the sink to know when to start
+ * plotting. Useful to isolate events and avoid noise.
+ *
+ * The trigger modes are Free, Auto, Normal, and Tag (see
+ * gr::qtgui::trigger_mode). The first three are like a normal
+ * trigger function. Free means free running with no trigger,
+ * auto will trigger if the trigger event is seen, but will
+ * still plot otherwise, and normal will hold until the trigger
+ * event is observed. The Tag trigger mode allows us to trigger
+ * off a specific stream tag. The tag trigger is based only on
+ * the name of the tag, so when a tag of the given name is seen,
+ * the trigger is activated.
+ *
+ * In auto and normal mode, we look to see if the magnitude of
+ * the any FFT point is over the set level.
+ *
+ * \param mode The trigger_mode: free, auto, normal, or tag.
+ * \param level The magnitude of the trigger even for auto or normal modes.
+ * \param channel Which input channel to use for the trigger events.
+ * \param tag_key The name (as a string) of the tag to trigger off
+ * of if using the tag mode.
+ */
+ virtual void set_trigger_mode(trigger_mode mode,
+ float level, int channel,
+ const std::string &tag_key="") = 0;
+
virtual std::string title() = 0;
virtual std::string line_label(int which) = 0;
virtual std::string line_color(int which) = 0;
diff --git a/gr-qtgui/include/gnuradio/qtgui/freqdisplayform.h b/gr-qtgui/include/gnuradio/qtgui/freqdisplayform.h
index 7cd077e6f8..744ac3ee90 100644
--- a/gr-qtgui/include/gnuradio/qtgui/freqdisplayform.h
+++ b/gr-qtgui/include/gnuradio/qtgui/freqdisplayform.h
@@ -49,6 +49,13 @@ class FreqDisplayForm : public DisplayForm
float getFFTAverage() const;
gr::filter::firdes::win_type getFFTWindowType() const;
+ // Trigger methods
+ gr::qtgui::trigger_mode getTriggerMode() const;
+ float getTriggerLevel() const;
+ int getTriggerChannel() const;
+ std::string getTriggerTagKey() const;
+
+
// returns the frequency that was last double-clicked on by the user
float getClickedFreq() const;
@@ -69,9 +76,19 @@ public slots:
void setYMax(const QString &m);
void setYMin(const QString &m);
void autoScale(bool en);
+ void setPlotPosHalf(bool half);
void clearMaxHold();
void clearMinHold();
+ // Trigger slots
+ void updateTrigger(gr::qtgui::trigger_mode mode);
+ void setTriggerMode(gr::qtgui::trigger_mode mode);
+ void setTriggerLevel(QString s);
+ void setTriggerLevel(float level);
+ void setTriggerChannel(int chan);
+ void setTriggerTagKey(QString s);
+ void setTriggerTagKey(const std::string &s);
+
private slots:
void newData(const QEvent *updateEvent);
void onPlotPointSelected(const QPointF p);
@@ -93,6 +110,17 @@ private:
FFTAverageMenu *d_avgmenu;
FFTWindowMenu *d_winmenu;
QAction *d_clearmin_act, *d_clearmax_act;
+
+ QMenu *d_triggermenu;
+ TriggerModeMenu *d_tr_mode_menu;
+ PopupMenu *d_tr_level_act;
+ TriggerChannelMenu *d_tr_channel_menu;
+ PopupMenu *d_tr_tag_key_act;
+
+ gr::qtgui::trigger_mode d_trig_mode;
+ float d_trig_level;
+ int d_trig_channel;
+ std::string d_trig_tag_key;
};
#endif /* FREQ_DISPLAY_FORM_H */
diff --git a/gr-qtgui/include/gnuradio/qtgui/waterfall_sink_f.h b/gr-qtgui/include/gnuradio/qtgui/waterfall_sink_f.h
index bbfcc33164..4570ef9d54 100644
--- a/gr-qtgui/include/gnuradio/qtgui/waterfall_sink_f.h
+++ b/gr-qtgui/include/gnuradio/qtgui/waterfall_sink_f.h
@@ -124,6 +124,13 @@ namespace gr {
virtual void set_line_alpha(int which, double alpha) = 0;
virtual void set_color_map(int which, const int color) = 0;
+ /*!
+ * Pass "true" to this function to only show the positive half
+ * of the spectrum. By default, this plotter shows the full
+ * spectrum (positive and negative halves).
+ */
+ virtual void set_plot_pos_half(bool half) = 0;
+
virtual std::string title() = 0;
virtual std::string line_label(int which) = 0;
virtual double line_alpha(int which) = 0;
diff --git a/gr-qtgui/include/gnuradio/qtgui/waterfalldisplayform.h b/gr-qtgui/include/gnuradio/qtgui/waterfalldisplayform.h
index 8017d5ce8f..e885a525b0 100644
--- a/gr-qtgui/include/gnuradio/qtgui/waterfalldisplayform.h
+++ b/gr-qtgui/include/gnuradio/qtgui/waterfalldisplayform.h
@@ -86,6 +86,7 @@ public slots:
const QColor highColor=QColor("white"));
void autoScale(bool en=false);
+ void setPlotPosHalf(bool half);
private slots:
void newData(const QEvent *updateEvent);
diff --git a/gr-qtgui/lib/FrequencyDisplayPlot.cc b/gr-qtgui/lib/FrequencyDisplayPlot.cc
index 12835bcd27..41050edfc2 100644
--- a/gr-qtgui/lib/FrequencyDisplayPlot.cc
+++ b/gr-qtgui/lib/FrequencyDisplayPlot.cc
@@ -1,6 +1,6 @@
/* -*- c++ -*- */
/*
- * Copyright 2008-2011 Free Software Foundation, Inc.
+ * Copyright 2008-2011,2014 Free Software Foundation, Inc.
*
* This file is part of GNU Radio
*
@@ -94,6 +94,7 @@ FrequencyDisplayPlot::FrequencyDisplayPlot(int nplots, QWidget* parent)
d_min_fft_data = new double[d_numPoints];
d_max_fft_data = new double[d_numPoints];
d_xdata = new double[d_numPoints];
+ d_half_freq = false;
setAxisTitle(QwtPlot::xBottom, "Frequency (Hz)");
setAxisScaleDraw(QwtPlot::xBottom, new FreqDisplayScaleDraw(0));
@@ -279,8 +280,13 @@ FrequencyDisplayPlot::setFrequencyRange(const double centerfreq,
const double bandwidth,
const double units, const std::string &strunits)
{
- double startFreq = (centerfreq - bandwidth/2.0f) / units;
- double stopFreq = (centerfreq + bandwidth/2.0f) / units;
+ double startFreq;
+ double stopFreq = (centerfreq + bandwidth/2.0f) / units;
+ if(d_half_freq)
+ startFreq = 0;
+ else
+ startFreq = (centerfreq - bandwidth/2.0f) / units;
+
d_xdata_multiplier = units;
@@ -346,10 +352,13 @@ FrequencyDisplayPlot::plotNewData(const std::vector<double*> dataPoints,
const double noiseFloorAmplitude, const double peakFrequency,
const double peakAmplitude, const double timeInterval)
{
+ int64_t _npoints_in = d_half_freq ? numDataPoints/2 : numDataPoints;
+ int64_t _in_index = d_half_freq ? _npoints_in : 0;
+
if(!d_stop) {
if(numDataPoints > 0) {
- if(numDataPoints != d_numPoints) {
- d_numPoints = numDataPoints;
+ if(_npoints_in != d_numPoints) {
+ d_numPoints = _npoints_in;
delete[] d_min_fft_data;
delete[] d_max_fft_data;
@@ -383,9 +392,9 @@ FrequencyDisplayPlot::plotNewData(const std::vector<double*> dataPoints,
double bottom=1e20, top=-1e20;
for(int n = 0; n < d_nplots; n++) {
- memcpy(d_ydata[n], dataPoints[n], numDataPoints*sizeof(double));
+ memcpy(d_ydata[n], &(dataPoints[n][_in_index]), _npoints_in*sizeof(double));
- for(int64_t point = 0; point < numDataPoints; point++) {
+ for(int64_t point = 0; point < _npoints_in; point++) {
if(dataPoints[n][point] < d_min_fft_data[point]) {
d_min_fft_data[point] = dataPoints[n][point];
}
@@ -462,6 +471,15 @@ FrequencyDisplayPlot::setAutoScale(bool state)
}
void
+FrequencyDisplayPlot::setPlotPosHalf(bool half)
+{
+ d_half_freq = half;
+ if(half)
+ d_start_frequency = 0;
+}
+
+
+void
FrequencyDisplayPlot::setMaxFFTVisible(const bool visibleFlag)
{
d_max_fft_visible = visibleFlag;
@@ -491,7 +509,7 @@ void
FrequencyDisplayPlot::_resetXAxisPoints()
{
double fft_bin_size = (d_stop_frequency - d_start_frequency)
- / static_cast<double>(d_numPoints-1);
+ / static_cast<double>(d_numPoints);
double freqValue = d_start_frequency;
for(int64_t loc = 0; loc < d_numPoints; loc++) {
d_xdata[loc] = freqValue;
diff --git a/gr-qtgui/lib/WaterfallDisplayPlot.cc b/gr-qtgui/lib/WaterfallDisplayPlot.cc
index eb33cba921..86724fe04d 100644
--- a/gr-qtgui/lib/WaterfallDisplayPlot.cc
+++ b/gr-qtgui/lib/WaterfallDisplayPlot.cc
@@ -1,6 +1,6 @@
/* -*- c++ -*- */
/*
- * Copyright 2008-2012 Free Software Foundation, Inc.
+ * Copyright 2008-2012,2014 Free Software Foundation, Inc.
*
* This file is part of GNU Radio
*
@@ -139,6 +139,7 @@ WaterfallDisplayPlot::WaterfallDisplayPlot(int nplots, QWidget* parent)
resize(parent->width(), parent->height());
d_numPoints = 1024;
+ d_half_freq = false;
setAxisTitle(QwtPlot::xBottom, "Frequency (Hz)");
setAxisScaleDraw(QwtPlot::xBottom, new FreqDisplayScaleDraw(0));
@@ -225,8 +226,13 @@ WaterfallDisplayPlot::setFrequencyRange(const double centerfreq,
const double bandwidth,
const double units, const std::string &strunits)
{
- double startFreq = (centerfreq - bandwidth/2.0f) / units;
- double stopFreq = (centerfreq + bandwidth/2.0f) / units;
+ double startFreq;
+ double stopFreq = (centerfreq + bandwidth/2.0f) / units;
+ if(d_half_freq)
+ startFreq = 0;
+ else
+ startFreq = (centerfreq - bandwidth/2.0f) / units;
+
d_xaxis_multiplier = units;
@@ -273,10 +279,13 @@ WaterfallDisplayPlot::plotNewData(const std::vector<double*> dataPoints,
const gr::high_res_timer_type timestamp,
const int droppedFrames)
{
+ int64_t _npoints_in = d_half_freq ? numDataPoints/2 : numDataPoints;
+ int64_t _in_index = d_half_freq ? _npoints_in : 0;
+
if(!d_stop) {
if(numDataPoints > 0){
- if(numDataPoints != d_numPoints){
- d_numPoints = numDataPoints;
+ if(_npoints_in != d_numPoints) {
+ d_numPoints = _npoints_in;
resetAxis();
@@ -298,7 +307,8 @@ WaterfallDisplayPlot::plotNewData(const std::vector<double*> dataPoints,
((WaterfallZoomer*)d_zoomer)->setZeroTime(timestamp);
for(int i = 0; i < d_nplots; i++) {
- d_data[i]->addFFTData(dataPoints[i], numDataPoints, droppedFrames);
+ d_data[i]->addFFTData(&(dataPoints[i][_in_index]),
+ _npoints_in, droppedFrames);
d_data[i]->incrementNumLinesToUpdate();
d_spectrogram[i]->invalidateCache();
d_spectrogram[i]->itemChanged();
@@ -596,4 +606,13 @@ WaterfallDisplayPlot::_updateIntensityRangeDisplay()
replot();
}
+void
+WaterfallDisplayPlot::setPlotPosHalf(bool half)
+{
+ d_half_freq = half;
+ if(half)
+ d_start_frequency = 0;
+}
+
+
#endif /* WATERFALL_DISPLAY_PLOT_C */
diff --git a/gr-qtgui/lib/const_sink_c_impl.cc b/gr-qtgui/lib/const_sink_c_impl.cc
index f7bdc01489..10b342dbf5 100644
--- a/gr-qtgui/lib/const_sink_c_impl.cc
+++ b/gr-qtgui/lib/const_sink_c_impl.cc
@@ -498,7 +498,7 @@ namespace gr {
d_index += nitems;
- // If we've have a trigger and a full d_size of items in the buffers, plot.
+ // If we have a trigger and a full d_size of items in the buffers, plot.
if((d_triggered) && (d_index == d_end)) {
// Copy data to be plotted to start of buffers.
for(n = 0; n < d_nconnections; n++) {
diff --git a/gr-qtgui/lib/freq_sink_c_impl.cc b/gr-qtgui/lib/freq_sink_c_impl.cc
index 11e8fc378f..e46b9db865 100644
--- a/gr-qtgui/lib/freq_sink_c_impl.cc
+++ b/gr-qtgui/lib/freq_sink_c_impl.cc
@@ -54,8 +54,8 @@ namespace gr {
int nconnections,
QWidget *parent)
: sync_block("freq_sink_c",
- io_signature::make(1, -1, sizeof(gr_complex)),
- io_signature::make(0, 0, 0)),
+ io_signature::make(nconnections, nconnections, sizeof(gr_complex)),
+ io_signature::make(0, 0, 0)),
d_fftsize(fftsize), d_fftavg(1.0),
d_wintype((filter::firdes::win_type)(wintype)),
d_center_freq(fc), d_bandwidth(bw), d_name(name),
@@ -87,6 +87,11 @@ namespace gr {
volk_get_alignment());
memset(d_fbuf, 0, d_fftsize*sizeof(float));
+ d_tmpbuflen = (unsigned int)(floor(d_fftsize/2.0));
+ d_tmpbuf = (float*)volk_malloc(sizeof(float)*(d_tmpbuflen + 1),
+ volk_get_alignment());
+
+
d_index = 0;
for(int i = 0; i < d_nconnections; i++) {
d_residbufs.push_back((gr_complex*)volk_malloc(d_fftsize*sizeof(gr_complex),
@@ -101,6 +106,8 @@ namespace gr {
buildwindow();
initialize();
+
+ set_trigger_mode(TRIG_MODE_FREE, 0, 0);
}
freq_sink_c_impl::~freq_sink_c_impl()
@@ -114,6 +121,7 @@ namespace gr {
}
delete d_fft;
volk_free(d_fbuf);
+ volk_free(d_tmpbuf);
delete d_argv;
}
@@ -125,15 +133,6 @@ namespace gr {
}
void
- freq_sink_c_impl::forecast(int noutput_items, gr_vector_int &ninput_items_required)
- {
- unsigned int ninputs = ninput_items_required.size();
- for (unsigned int i = 0; i < ninputs; i++) {
- ninput_items_required[i] = std::min(d_fftsize, 8191);
- }
- }
-
- void
freq_sink_c_impl::initialize()
{
if(qApp != NULL) {
@@ -162,6 +161,8 @@ namespace gr {
if(d_name.size() > 0)
set_title(d_name);
+ set_output_multiple(d_fftsize);
+
// initialize update time to 10 times a second
set_update_time(0.1);
}
@@ -303,6 +304,29 @@ namespace gr {
d_main_gui->resize(QSize(width, height));
}
+ void
+ freq_sink_c_impl::set_trigger_mode(trigger_mode mode,
+ float level,
+ int channel,
+ const std::string &tag_key)
+ {
+ gr::thread::scoped_lock lock(d_setlock);
+
+ d_trigger_mode = mode;
+ d_trigger_level = level;
+ d_trigger_channel = channel;
+ d_trigger_tag_key = pmt::intern(tag_key);
+ d_triggered = false;
+ d_trigger_count = 0;
+
+ d_main_gui->setTriggerMode(d_trigger_mode);
+ d_main_gui->setTriggerLevel(d_trigger_level);
+ d_main_gui->setTriggerChannel(d_trigger_channel);
+ d_main_gui->setTriggerTagKey(tag_key);
+
+ _reset();
+ }
+
std::string
freq_sink_c_impl::title()
{
@@ -378,10 +402,26 @@ namespace gr {
void
freq_sink_c_impl::reset()
{
- d_index = 0;
+ gr::thread::scoped_lock lock(d_setlock);
+ _reset();
}
void
+ freq_sink_c_impl::_reset()
+ {
+ d_trigger_count = 0;
+
+ // Reset the trigger.
+ if(d_trigger_mode == TRIG_MODE_FREE) {
+ d_triggered = true;
+ }
+ else {
+ d_triggered = false;
+ }
+ }
+
+
+ void
freq_sink_c_impl::fft(float *data_out, const gr_complex *data_in, int size)
{
if(d_window.size()) {
@@ -398,15 +438,12 @@ namespace gr {
size, 1.0, size);
// Perform shift operation
- unsigned int len = (unsigned int)(floor(size/2.0));
- float *tmp = (float*)malloc(sizeof(float)*len);
- memcpy(tmp, &data_out[0], sizeof(float)*len);
- memcpy(&data_out[0], &data_out[len], sizeof(float)*(size - len));
- memcpy(&data_out[size - len], tmp, sizeof(float)*len);
- free(tmp);
+ memcpy(d_tmpbuf, &data_out[0], sizeof(float)*(d_tmpbuflen + 1));
+ memcpy(&data_out[0], &data_out[size - d_tmpbuflen], sizeof(float)*(d_tmpbuflen));
+ memcpy(&data_out[d_tmpbuflen], d_tmpbuf, sizeof(float)*(d_tmpbuflen + 1));
}
- void
+ bool
freq_sink_c_impl::windowreset()
{
gr::thread::scoped_lock lock(d_setlock);
@@ -416,7 +453,9 @@ namespace gr {
if(d_wintype != newwintype) {
d_wintype = newwintype;
buildwindow();
+ return true;
}
+ return false;
}
void
@@ -428,7 +467,7 @@ namespace gr {
}
}
- void
+ bool
freq_sink_c_impl::fftresize()
{
gr::thread::scoped_lock lock(d_setlock);
@@ -467,7 +506,19 @@ namespace gr {
d_fbuf = (float*)volk_malloc(d_fftsize*sizeof(float),
volk_get_alignment());
memset(d_fbuf, 0, d_fftsize*sizeof(float));
+
+ volk_free(d_tmpbuf);
+ d_tmpbuflen = (unsigned int)(floor(d_fftsize/2.0));
+ d_tmpbuf = (float*)volk_malloc(sizeof(float)*(d_tmpbuflen + 1),
+ volk_get_alignment());
+
+ d_last_time = 0;
+
+ set_output_multiple(d_fftsize);
+
+ return true;
}
+ return false;
}
void
@@ -494,59 +545,121 @@ namespace gr {
}
}
+ void
+ freq_sink_c_impl::_gui_update_trigger()
+ {
+ trigger_mode new_trigger_mode = d_main_gui->getTriggerMode();
+ d_trigger_level = d_main_gui->getTriggerLevel();
+ d_trigger_channel = d_main_gui->getTriggerChannel();
+
+ std::string tagkey = d_main_gui->getTriggerTagKey();
+ d_trigger_tag_key = pmt::intern(tagkey);
+
+ if(new_trigger_mode != d_trigger_mode) {
+ d_trigger_mode = new_trigger_mode;
+ _reset();
+ }
+ }
+
+ void
+ freq_sink_c_impl::_test_trigger_tags(int start, int nitems)
+ {
+ uint64_t nr = nitems_read(d_trigger_channel);
+ std::vector<gr::tag_t> tags;
+ get_tags_in_range(tags, d_trigger_channel,
+ nr+start, nr+start+nitems,
+ d_trigger_tag_key);
+ if(tags.size() > 0) {
+ d_triggered = true;
+ d_index = tags[0].offset - nr;
+ d_trigger_count = 0;
+ }
+ }
+
+ void
+ freq_sink_c_impl::_test_trigger_norm(int nitems, std::vector<double*> inputs)
+ {
+ const double *in = (const double*)inputs[d_trigger_channel];
+ for(int i = 0; i < nitems; i++) {
+ d_trigger_count++;
+
+ // Test if trigger has occurred based on the FFT magnitude and
+ // channel number. Test if any value is > the level (in dBx).
+ if(in[i] > d_trigger_level) {
+ d_triggered = true;
+ d_trigger_count = 0;
+ break;
+ }
+ }
+
+ // If using auto trigger mode, trigger periodically even
+ // without a trigger event.
+ if((d_trigger_mode == TRIG_MODE_AUTO) && (d_trigger_count > d_fftsize)) {
+ d_triggered = true;
+ d_trigger_count = 0;
+ }
+ }
+
int
freq_sink_c_impl::work(int noutput_items,
gr_vector_const_void_star &input_items,
gr_vector_void_star &output_items)
{
- int j=0;
const gr_complex *in = (const gr_complex*)input_items[0];
// Update the FFT size from the application
- fftresize();
- windowreset();
- check_clicked();
+ bool updated = false;
+ updated |= fftresize();
+ updated |= windowreset();
+ if(updated)
+ return 0;
- for(int i=0; i < noutput_items; i+=d_fftsize) {
- unsigned int datasize = noutput_items - i;
- unsigned int resid = d_fftsize-d_index;
+ check_clicked();
+ _gui_update_trigger();
- // If we have enough input for one full FFT, do it
- if(datasize >= resid) {
+ gr::thread::scoped_lock lock(d_setlock);
+ for(d_index = 0; d_index < noutput_items; d_index+=d_fftsize) {
- if(gr::high_res_timer_now() - d_last_time > d_update_time) {
- for(int n = 0; n < d_nconnections; n++) {
- // Fill up residbuf with d_fftsize number of items
- in = (const gr_complex*)input_items[n];
- memcpy(d_residbufs[n]+d_index, &in[j], sizeof(gr_complex)*resid);
+ if((gr::high_res_timer_now() - d_last_time) > d_update_time) {
- fft(d_fbuf, d_residbufs[n], d_fftsize);
- for(int x = 0; x < d_fftsize; x++) {
- d_magbufs[n][x] = (double)((1.0-d_fftavg)*d_magbufs[n][x] + (d_fftavg)*d_fbuf[x]);
- }
- //volk_32f_convert_64f_a(d_magbufs[n], d_fbuf, d_fftsize);
+ // Trigger off tag, if active
+ if((d_trigger_mode == TRIG_MODE_TAG) && !d_triggered) {
+ _test_trigger_tags(d_index, d_fftsize);
+ if(d_triggered) {
+ // If not enough from tag position, early exit
+ if((d_index + d_fftsize) >= noutput_items)
+ return d_index;
}
+ }
- d_last_time = gr::high_res_timer_now();
- d_qApplication->postEvent(d_main_gui,
- new FreqUpdateEvent(d_magbufs, d_fftsize));
- }
+ // Perform FFT and shift operations into d_magbufs
+ for(int n = 0; n < d_nconnections; n++) {
+ in = (const gr_complex*)input_items[n];
+ memcpy(d_residbufs[n], &in[d_index], sizeof(gr_complex)*d_fftsize);
- d_index = 0;
- j += resid;
- }
- // Otherwise, copy what we received into the residbuf for next time
- else {
- for(int n = 0; n < d_nconnections; n++) {
- in = (const gr_complex*)input_items[n];
- memcpy(d_residbufs[n]+d_index, &in[j], sizeof(gr_complex)*datasize);
- }
- d_index += datasize;
- j += datasize;
- }
+ fft(d_fbuf, d_residbufs[n], d_fftsize);
+ for(int x = 0; x < d_fftsize; x++) {
+ d_magbufs[n][x] = (double)((1.0-d_fftavg)*d_magbufs[n][x] + (d_fftavg)*d_fbuf[x]);
+ }
+ //volk_32f_convert_64f_a(d_magbufs[n], d_fbuf, d_fftsize);
+ }
+
+ // Test trigger off signal power in d_magbufs
+ if((d_trigger_mode == TRIG_MODE_NORM) || (d_trigger_mode == TRIG_MODE_AUTO)) {
+ _test_trigger_norm(d_fftsize, d_magbufs);
+ }
+
+ // If a trigger (FREE always triggers), plot and reset state
+ if(d_triggered) {
+ d_last_time = gr::high_res_timer_now();
+ d_qApplication->postEvent(d_main_gui,
+ new FreqUpdateEvent(d_magbufs, d_fftsize));
+ _reset();
+ }
+ }
}
- return j;
+ return noutput_items;
}
} /* namespace qtgui */
diff --git a/gr-qtgui/lib/freq_sink_c_impl.h b/gr-qtgui/lib/freq_sink_c_impl.h
index dc985c1a99..b5f9cd3d4d 100644
--- a/gr-qtgui/lib/freq_sink_c_impl.h
+++ b/gr-qtgui/lib/freq_sink_c_impl.h
@@ -35,11 +35,10 @@ namespace gr {
class QTGUI_API freq_sink_c_impl : public freq_sink_c
{
private:
- void forecast(int noutput_items, gr_vector_int &ninput_items_required);
-
void initialize();
int d_fftsize;
+ int d_tmpbuflen;
float d_fftavg;
filter::firdes::win_type d_wintype;
std::vector<float> d_window;
@@ -55,6 +54,7 @@ namespace gr {
std::vector<gr_complex*> d_residbufs;
std::vector<double*> d_magbufs;
float *d_fbuf;
+ float *d_tmpbuf;
int d_argc;
char *d_argv;
@@ -64,9 +64,9 @@ namespace gr {
gr::high_res_timer_type d_update_time;
gr::high_res_timer_type d_last_time;
- void windowreset();
+ bool windowreset();
void buildwindow();
- void fftresize();
+ bool fftresize();
void check_clicked();
void fft(float *data_out, const gr_complex *data_in, int size);
@@ -74,6 +74,19 @@ namespace gr {
// The message is a PMT pair (intern('freq'), double(frequency)).
void handle_set_freq(pmt::pmt_t msg);
+ // Members used for triggering scope
+ trigger_mode d_trigger_mode;
+ float d_trigger_level;
+ int d_trigger_channel;
+ pmt::pmt_t d_trigger_tag_key;
+ bool d_triggered;
+ int d_trigger_count;
+
+ void _reset();
+ void _gui_update_trigger();
+ void _test_trigger_tags(int start, int nitems);
+ void _test_trigger_norm(int nitems, std::vector<double*> inputs);
+
public:
freq_sink_c_impl(int size, int wintype,
double fc, double bw,
@@ -112,6 +125,9 @@ namespace gr {
void set_line_style(int which, int style);
void set_line_marker(int which, int marker);
void set_line_alpha(int which, double alpha);
+ void set_trigger_mode(trigger_mode mode,
+ float level, int channel,
+ const std::string &tag_key="");
std::string title();
std::string line_label(int which);
diff --git a/gr-qtgui/lib/freq_sink_f_impl.cc b/gr-qtgui/lib/freq_sink_f_impl.cc
index c0a29becd8..200b009d79 100644
--- a/gr-qtgui/lib/freq_sink_f_impl.cc
+++ b/gr-qtgui/lib/freq_sink_f_impl.cc
@@ -54,8 +54,8 @@ namespace gr {
int nconnections,
QWidget *parent)
: sync_block("freq_sink_f",
- io_signature::make(1, -1, sizeof(float)),
- io_signature::make(0, 0, 0)),
+ io_signature::make(nconnections, nconnections, sizeof(float)),
+ io_signature::make(0, 0, 0)),
d_fftsize(fftsize), d_fftavg(1.0),
d_wintype((filter::firdes::win_type)(wintype)),
d_center_freq(fc), d_bandwidth(bw), d_name(name),
@@ -87,6 +87,10 @@ namespace gr {
volk_get_alignment());
memset(d_fbuf, 0, d_fftsize*sizeof(float));
+ d_tmpbuflen = (unsigned int)(floor(d_fftsize/2.0));
+ d_tmpbuf = (float*)volk_malloc(sizeof(float)*(d_tmpbuflen + 1),
+ volk_get_alignment());
+
d_index = 0;
for(int i = 0; i < d_nconnections; i++) {
d_residbufs.push_back((float*)volk_malloc(d_fftsize*sizeof(float),
@@ -101,6 +105,8 @@ namespace gr {
buildwindow();
initialize();
+
+ set_trigger_mode(TRIG_MODE_FREE, 0, 0);
}
freq_sink_f_impl::~freq_sink_f_impl()
@@ -114,6 +120,7 @@ namespace gr {
}
delete d_fft;
volk_free(d_fbuf);
+ volk_free(d_tmpbuf);
delete d_argv;
}
@@ -125,15 +132,6 @@ namespace gr {
}
void
- freq_sink_f_impl::forecast(int noutput_items, gr_vector_int &ninput_items_required)
- {
- unsigned int ninputs = ninput_items_required.size();
- for (unsigned int i = 0; i < ninputs; i++) {
- ninput_items_required[i] = std::min(d_fftsize, 8191);
- }
- }
-
- void
freq_sink_f_impl::initialize()
{
if(qApp != NULL) {
@@ -162,6 +160,8 @@ namespace gr {
if(d_name.size() > 0)
set_title(d_name);
+ set_output_multiple(d_fftsize);
+
// initialize update time to 10 times a second
set_update_time(0.1);
}
@@ -303,6 +303,35 @@ namespace gr {
d_main_gui->resize(QSize(width, height));
}
+ void
+ freq_sink_f_impl::set_plot_pos_half(bool half)
+ {
+ d_main_gui->setPlotPosHalf(half);
+ }
+
+ void
+ freq_sink_f_impl::set_trigger_mode(trigger_mode mode,
+ float level,
+ int channel,
+ const std::string &tag_key)
+ {
+ gr::thread::scoped_lock lock(d_setlock);
+
+ d_trigger_mode = mode;
+ d_trigger_level = level;
+ d_trigger_channel = channel;
+ d_trigger_tag_key = pmt::intern(tag_key);
+ d_triggered = false;
+ d_trigger_count = 0;
+
+ d_main_gui->setTriggerMode(d_trigger_mode);
+ d_main_gui->setTriggerLevel(d_trigger_level);
+ d_main_gui->setTriggerChannel(d_trigger_channel);
+ d_main_gui->setTriggerTagKey(tag_key);
+
+ _reset();
+ }
+
std::string
freq_sink_f_impl::title()
{
@@ -378,10 +407,25 @@ namespace gr {
void
freq_sink_f_impl::reset()
{
- d_index = 0;
+ gr::thread::scoped_lock lock(d_setlock);
+ _reset();
}
void
+ freq_sink_f_impl::_reset()
+ {
+ d_trigger_count = 0;
+
+ // Reset the trigger.
+ if(d_trigger_mode == TRIG_MODE_FREE) {
+ d_triggered = true;
+ }
+ else {
+ d_triggered = false;
+ }
+ }
+
+ void
freq_sink_f_impl::fft(float *data_out, const float *data_in, int size)
{
// float to complex conversion
@@ -399,15 +443,12 @@ namespace gr {
size, 1.0, size);
// Perform shift operation
- unsigned int len = (unsigned int)(floor(size/2.0));
- float *tmp = (float*)malloc(sizeof(float)*len);
- memcpy(tmp, &data_out[0], sizeof(float)*len);
- memcpy(&data_out[0], &data_out[len], sizeof(float)*(size - len));
- memcpy(&data_out[size - len], tmp, sizeof(float)*len);
- free(tmp);
+ memcpy(d_tmpbuf, &data_out[0], sizeof(float)*(d_tmpbuflen + 1));
+ memcpy(&data_out[0], &data_out[size - d_tmpbuflen], sizeof(float)*d_tmpbuflen);
+ memcpy(&data_out[d_tmpbuflen], d_tmpbuf, sizeof(float)*(d_tmpbuflen + 1));
}
- void
+ bool
freq_sink_f_impl::windowreset()
{
gr::thread::scoped_lock lock(d_setlock);
@@ -417,7 +458,9 @@ namespace gr {
if(d_wintype != newwintype) {
d_wintype = newwintype;
buildwindow();
+ return true;
}
+ return false;
}
void
@@ -429,7 +472,7 @@ namespace gr {
}
}
- void
+ bool
freq_sink_f_impl::fftresize()
{
gr::thread::scoped_lock lock(d_setlock);
@@ -468,7 +511,19 @@ namespace gr {
d_fbuf = (float*)volk_malloc(d_fftsize*sizeof(float),
volk_get_alignment());
memset(d_fbuf, 0, d_fftsize*sizeof(float));
+
+ volk_free(d_tmpbuf);
+ d_tmpbuflen = (unsigned int)(floor(d_fftsize/2.0));
+ d_tmpbuf = (float*)volk_malloc(sizeof(float)*(d_tmpbuflen + 1),
+ volk_get_alignment());
+
+ d_last_time = 0;
+
+ set_output_multiple(d_fftsize);
+
+ return true;
}
+ return false;
}
void
@@ -495,59 +550,121 @@ namespace gr {
}
}
+ void
+ freq_sink_f_impl::_gui_update_trigger()
+ {
+ trigger_mode new_trigger_mode = d_main_gui->getTriggerMode();
+ d_trigger_level = d_main_gui->getTriggerLevel();
+ d_trigger_channel = d_main_gui->getTriggerChannel();
+
+ std::string tagkey = d_main_gui->getTriggerTagKey();
+ d_trigger_tag_key = pmt::intern(tagkey);
+
+ if(new_trigger_mode != d_trigger_mode) {
+ d_trigger_mode = new_trigger_mode;
+ _reset();
+ }
+ }
+
+ void
+ freq_sink_f_impl::_test_trigger_tags(int start, int nitems)
+ {
+ uint64_t nr = nitems_read(d_trigger_channel);
+ std::vector<gr::tag_t> tags;
+ get_tags_in_range(tags, d_trigger_channel,
+ nr+start, nr+start+nitems,
+ d_trigger_tag_key);
+ if(tags.size() > 0) {
+ d_triggered = true;
+ d_index = tags[0].offset - nr;
+ d_trigger_count = 0;
+ }
+ }
+
+ void
+ freq_sink_f_impl::_test_trigger_norm(int nitems, std::vector<double*> inputs)
+ {
+ const double *in = (const double*)inputs[d_trigger_channel];
+ for(int i = 0; i < nitems; i++) {
+ d_trigger_count++;
+
+ // Test if trigger has occurred based on the FFT magnitude and
+ // channel number. Test if any value is > the level (in dBx).
+ if(in[i] > d_trigger_level) {
+ d_triggered = true;
+ d_trigger_count = 0;
+ break;
+ }
+ }
+
+ // If using auto trigger mode, trigger periodically even
+ // without a trigger event.
+ if((d_trigger_mode == TRIG_MODE_AUTO) && (d_trigger_count > d_fftsize)) {
+ d_triggered = true;
+ d_trigger_count = 0;
+ }
+ }
+
int
freq_sink_f_impl::work(int noutput_items,
gr_vector_const_void_star &input_items,
gr_vector_void_star &output_items)
{
- int j=0;
const float *in = (const float*)input_items[0];
// Update the FFT size from the application
- fftresize();
- windowreset();
+ bool updated = false;
+ updated |= fftresize();
+ updated |= windowreset();
+ if(updated)
+ return 0;
+
check_clicked();
+ _gui_update_trigger();
+
+ gr::thread::scoped_lock lock(d_setlock);
+ for(d_index = 0; d_index < noutput_items; d_index+=d_fftsize) {
- for(int i=0; i < noutput_items; i+=d_fftsize) {
- unsigned int datasize = noutput_items - i;
- unsigned int resid = d_fftsize-d_index;
+ if((gr::high_res_timer_now() - d_last_time) > d_update_time) {
- // If we have enough input for one full FFT, do it
- if(datasize >= resid) {
+ // Trigger off tag, if active
+ if((d_trigger_mode == TRIG_MODE_TAG) && !d_triggered) {
+ _test_trigger_tags(d_index, d_fftsize);
+ if(d_triggered) {
+ // If not enough from tag position, early exit
+ if((d_index + d_fftsize) >= noutput_items)
+ return d_index;
+ }
+ }
- if(gr::high_res_timer_now() - d_last_time > d_update_time) {
- for(int n = 0; n < d_nconnections; n++) {
- // Fill up residbuf with d_fftsize number of items
- in = (const float*)input_items[n];
- memcpy(d_residbufs[n]+d_index, &in[j], sizeof(float)*resid);
+ for(int n = 0; n < d_nconnections; n++) {
+ // Fill up residbuf with d_fftsize number of items
+ in = (const float*)input_items[n];
+ memcpy(d_residbufs[n], &in[d_index], sizeof(float)*d_fftsize);
- fft(d_fbuf, d_residbufs[n], d_fftsize);
- for(int x = 0; x < d_fftsize; x++) {
- d_magbufs[n][x] = (double)((1.0-d_fftavg)*d_magbufs[n][x] + (d_fftavg)*d_fbuf[x]);
- }
- //volk_32f_convert_64f_a(d_magbufs[n], d_fbuf, d_fftsize);
+ fft(d_fbuf, d_residbufs[n], d_fftsize);
+ for(int x = 0; x < d_fftsize; x++) {
+ d_magbufs[n][x] = (double)((1.0-d_fftavg)*d_magbufs[n][x] + (d_fftavg)*d_fbuf[x]);
}
+ //volk_32f_convert_64f_a(d_magbufs[n], d_fbuf, d_fftsize);
+ }
+ // Test trigger off signal power in d_magbufs
+ if((d_trigger_mode == TRIG_MODE_NORM) || (d_trigger_mode == TRIG_MODE_AUTO)) {
+ _test_trigger_norm(d_fftsize, d_magbufs);
+ }
+
+ // If a trigger (FREE always triggers), plot and reset state
+ if(d_triggered) {
d_last_time = gr::high_res_timer_now();
d_qApplication->postEvent(d_main_gui,
new FreqUpdateEvent(d_magbufs, d_fftsize));
+ _reset();
}
-
- d_index = 0;
- j += resid;
- }
- // Otherwise, copy what we received into the residbuf for next time
- else {
- for(int n = 0; n < d_nconnections; n++) {
- in = (const float*)input_items[n];
- memcpy(d_residbufs[n]+d_index, &in[j], sizeof(float)*datasize);
- }
- d_index += datasize;
- j += datasize;
}
}
- return j;
+ return noutput_items;
}
} /* namespace qtgui */
diff --git a/gr-qtgui/lib/freq_sink_f_impl.h b/gr-qtgui/lib/freq_sink_f_impl.h
index 9c4e1e3bcb..1463699319 100644
--- a/gr-qtgui/lib/freq_sink_f_impl.h
+++ b/gr-qtgui/lib/freq_sink_f_impl.h
@@ -1,6 +1,6 @@
/* -*- c++ -*- */
/*
- * Copyright 2012 Free Software Foundation, Inc.
+ * Copyright 2012,2014 Free Software Foundation, Inc.
*
* This file is part of GNU Radio
*
@@ -35,11 +35,10 @@ namespace gr {
class QTGUI_API freq_sink_f_impl : public freq_sink_f
{
private:
- void forecast(int noutput_items, gr_vector_int &ninput_items_required);
-
void initialize();
int d_fftsize;
+ int d_tmpbuflen;
float d_fftavg;
filter::firdes::win_type d_wintype;
std::vector<float> d_window;
@@ -55,6 +54,7 @@ namespace gr {
std::vector<float*> d_residbufs;
std::vector<double*> d_magbufs;
float *d_fbuf;
+ float *d_tmpbuf;
int d_argc;
char *d_argv;
@@ -64,9 +64,9 @@ namespace gr {
gr::high_res_timer_type d_update_time;
gr::high_res_timer_type d_last_time;
- void windowreset();
+ bool windowreset();
void buildwindow();
- void fftresize();
+ bool fftresize();
void check_clicked();
void fft(float *data_out, const float *data_in, int size);
@@ -74,6 +74,19 @@ namespace gr {
// The message is a PMT pair (intern('freq'), double(frequency)).
void handle_set_freq(pmt::pmt_t msg);
+ // Members used for triggering scope
+ trigger_mode d_trigger_mode;
+ float d_trigger_level;
+ int d_trigger_channel;
+ pmt::pmt_t d_trigger_tag_key;
+ bool d_triggered;
+ int d_trigger_count;
+
+ void _reset();
+ void _gui_update_trigger();
+ void _test_trigger_tags(int start, int nitems);
+ void _test_trigger_norm(int nitems, std::vector<double*> inputs);
+
public:
freq_sink_f_impl(int size, int wintype,
double fc, double bw,
@@ -111,6 +124,10 @@ namespace gr {
void set_line_style(int which, int style);
void set_line_marker(int which, int marker);
void set_line_alpha(int which, double alpha);
+ void set_plot_pos_half(bool half);
+ void set_trigger_mode(trigger_mode mode,
+ float level, int channel,
+ const std::string &tag_key="");
std::string title();
std::string line_label(int which);
diff --git a/gr-qtgui/lib/freqdisplayform.cc b/gr-qtgui/lib/freqdisplayform.cc
index ccc7fe9e07..d7fa1563fa 100644
--- a/gr-qtgui/lib/freqdisplayform.cc
+++ b/gr-qtgui/lib/freqdisplayform.cc
@@ -74,6 +74,37 @@ FreqDisplayForm::FreqDisplayForm(int nplots, QWidget* parent)
connect(d_clearmin_act, SIGNAL(triggered()),
this, SLOT(clearMinHold()));
+ // Set up the trigger menu
+ d_triggermenu = new QMenu("Trigger", this);
+ d_tr_mode_menu = new TriggerModeMenu(this);
+ d_tr_level_act = new PopupMenu("Level", this);
+ d_tr_channel_menu = new TriggerChannelMenu(nplots, this);
+ d_tr_tag_key_act = new PopupMenu("Tag Key", this);
+ d_triggermenu->addMenu(d_tr_mode_menu);
+ d_triggermenu->addAction(d_tr_level_act);
+ d_triggermenu->addMenu(d_tr_channel_menu);
+ d_triggermenu->addAction(d_tr_tag_key_act);
+ d_menu->addMenu(d_triggermenu);
+
+ setTriggerMode(gr::qtgui::TRIG_MODE_FREE);
+ connect(d_tr_mode_menu, SIGNAL(whichTrigger(gr::qtgui::trigger_mode)),
+ this, SLOT(setTriggerMode(gr::qtgui::trigger_mode)));
+ // updates trigger state by calling set level or set tag key.
+ connect(d_tr_mode_menu, SIGNAL(whichTrigger(gr::qtgui::trigger_mode)),
+ this, SLOT(updateTrigger(gr::qtgui::trigger_mode)));
+
+ setTriggerLevel(0);
+ connect(d_tr_level_act, SIGNAL(whichTrigger(QString)),
+ this, SLOT(setTriggerLevel(QString)));
+
+ setTriggerChannel(0);
+ connect(d_tr_channel_menu, SIGNAL(whichTrigger(int)),
+ this, SLOT(setTriggerChannel(int)));
+
+ setTriggerTagKey(std::string(""));
+ connect(d_tr_tag_key_act, SIGNAL(whichTrigger(QString)),
+ this, SLOT(setTriggerTagKey(QString)));
+
Reset();
connect(d_display_plot, SIGNAL(plotPointSelected(const QPointF)),
@@ -222,6 +253,13 @@ FreqDisplayForm::autoScale(bool en)
}
void
+FreqDisplayForm::setPlotPosHalf(bool half)
+{
+ getPlot()->setPlotPosHalf(half);
+ getPlot()->replot();
+}
+
+void
FreqDisplayForm::clearMaxHold()
{
getPlot()->clearMaxData();
@@ -257,3 +295,84 @@ FreqDisplayForm::getClickedFreq() const
{
return d_clicked_freq;
}
+
+
+/********************************************************************
+ * TRIGGER METHODS
+ *******************************************************************/
+
+void
+FreqDisplayForm::setTriggerMode(gr::qtgui::trigger_mode mode)
+{
+ d_trig_mode = mode;
+ d_tr_mode_menu->getAction(mode)->setChecked(true);
+}
+
+void
+FreqDisplayForm::updateTrigger(gr::qtgui::trigger_mode mode)
+{
+ // If auto or normal mode, popup trigger level box to set
+ if((d_trig_mode == gr::qtgui::TRIG_MODE_AUTO) || (d_trig_mode == gr::qtgui::TRIG_MODE_NORM))
+ d_tr_level_act->activate(QAction::Trigger);
+
+ // if tag mode, popup tag key box to set
+ if(d_trig_mode == gr::qtgui::TRIG_MODE_TAG)
+ d_tr_tag_key_act->activate(QAction::Trigger);
+}
+
+gr::qtgui::trigger_mode
+FreqDisplayForm::getTriggerMode() const
+{
+ return d_trig_mode;
+}
+
+void
+FreqDisplayForm::setTriggerLevel(QString s)
+{
+ d_trig_level = s.toFloat();
+}
+
+void
+FreqDisplayForm::setTriggerLevel(float level)
+{
+ d_trig_level = level;
+ d_tr_level_act->setText(QString().setNum(d_trig_level));
+}
+
+float
+FreqDisplayForm::getTriggerLevel() const
+{
+ return d_trig_level;
+}
+
+void
+FreqDisplayForm::setTriggerChannel(int channel)
+{
+ d_trig_channel = channel;
+ d_tr_channel_menu->getAction(d_trig_channel)->setChecked(true);
+}
+
+int
+FreqDisplayForm::getTriggerChannel() const
+{
+ return d_trig_channel;
+}
+
+void
+FreqDisplayForm::setTriggerTagKey(QString s)
+{
+ d_trig_tag_key = s.toStdString();
+}
+
+void
+FreqDisplayForm::setTriggerTagKey(const std::string &key)
+{
+ d_trig_tag_key = key;
+ d_tr_tag_key_act->setText(QString().fromStdString(d_trig_tag_key));
+}
+
+std::string
+FreqDisplayForm::getTriggerTagKey() const
+{
+ return d_trig_tag_key;
+}
diff --git a/gr-qtgui/lib/waterfall_sink_f_impl.cc b/gr-qtgui/lib/waterfall_sink_f_impl.cc
index 5667acf2e7..0f7f9e0437 100644
--- a/gr-qtgui/lib/waterfall_sink_f_impl.cc
+++ b/gr-qtgui/lib/waterfall_sink_f_impl.cc
@@ -53,8 +53,8 @@ namespace gr {
int nconnections,
QWidget *parent)
: sync_block("waterfall_sink_f",
- io_signature::make(1, -1, sizeof(float)),
- io_signature::make(0, 0, 0)),
+ io_signature::make(1, -1, sizeof(float)),
+ io_signature::make(0, 0, 0)),
d_fftsize(fftsize), d_fftavg(1.0),
d_wintype((filter::firdes::win_type)(wintype)),
d_center_freq(fc), d_bandwidth(bw), d_name(name),
@@ -107,8 +107,8 @@ namespace gr {
d_main_gui->close();
for(int i = 0; i < d_nconnections; i++) {
- volk_free(d_residbufs[i]);
- volk_free(d_magbufs[i]);
+ volk_free(d_residbufs[i]);
+ volk_free(d_magbufs[i]);
}
delete d_fft;
volk_free(d_fbuf);
@@ -127,7 +127,7 @@ namespace gr {
{
unsigned int ninputs = ninput_items_required.size();
for (unsigned int i = 0; i < ninputs; i++) {
- ninput_items_required[i] = std::min(d_fftsize, 8191);
+ ninput_items_required[i] = std::min(d_fftsize, 8191);
}
}
@@ -135,14 +135,14 @@ namespace gr {
waterfall_sink_f_impl::initialize()
{
if(qApp != NULL) {
- d_qApplication = qApp;
+ d_qApplication = qApp;
}
else {
#if QT_VERSION >= 0x040500
std::string style = prefs::singleton()->get_string("qtgui", "style", "raster");
QApplication::setGraphicsSystem(QString(style.c_str()));
#endif
- d_qApplication = new QApplication(d_argc, &d_argv);
+ d_qApplication = new QApplication(d_argc, &d_argv);
}
// If a style sheet is set in the prefs file, enable it here.
@@ -290,6 +290,12 @@ namespace gr {
d_main_gui->resize(QSize(width, height));
}
+ void
+ waterfall_sink_f_impl::set_plot_pos_half(bool half)
+ {
+ d_main_gui->setPlotPosHalf(half);
+ }
+
std::string
waterfall_sink_f_impl::title()
{
@@ -398,7 +404,8 @@ namespace gr {
{
gr::thread::scoped_lock lock(d_setlock);
- int newfftsize = d_fftsize;
+ int newfftsize = d_main_gui->getFFTSize();
+ d_fftavg = d_main_gui->getFFTAverage();
if(newfftsize != d_fftsize) {
diff --git a/gr-qtgui/lib/waterfall_sink_f_impl.h b/gr-qtgui/lib/waterfall_sink_f_impl.h
index d783f31d14..ca6e3f4264 100644
--- a/gr-qtgui/lib/waterfall_sink_f_impl.h
+++ b/gr-qtgui/lib/waterfall_sink_f_impl.h
@@ -110,6 +110,7 @@ namespace gr {
void set_line_label(int which, const std::string &label);
void set_line_alpha(int which, double alpha);
void set_color_map(int which, const int color);
+ void set_plot_pos_half(bool half);
std::string title();
std::string line_label(int which);
diff --git a/gr-qtgui/lib/waterfalldisplayform.cc b/gr-qtgui/lib/waterfalldisplayform.cc
index fdf09d9180..c1dd8f7aab 100644
--- a/gr-qtgui/lib/waterfalldisplayform.cc
+++ b/gr-qtgui/lib/waterfalldisplayform.cc
@@ -330,3 +330,10 @@ WaterfallDisplayForm::getClickedFreq() const
{
return d_clicked_freq;
}
+
+void
+WaterfallDisplayForm::setPlotPosHalf(bool half)
+{
+ getPlot()->setPlotPosHalf(half);
+ getPlot()->replot();
+}
diff --git a/gr-trellis/doc/gr-trellis.xml b/gr-trellis/doc/gr-trellis.xml
index 6ffbb9ec2c..aabf9ad535 100644
--- a/gr-trellis/doc/gr-trellis.xml
+++ b/gr-trellis/doc/gr-trellis.xml
@@ -176,8 +176,8 @@ private:
int d_O;
std::vector&lt;int&gt; d_NS;
std::vector&lt;int&gt; d_OS;
- std::vector&lt;int&gt; d_PS;
- std::vector&lt;int&gt; d_PI;
+ std::vector&lt; std::vector&lt; int&gt; &gt; d_PS;
+ std::vector&lt; std::vector&lt; int&gt; &gt; d_PI;
std::vector&lt;int&gt; d_TMi;
std::vector&lt;int&gt; d_TMl;
void generate_PS_PI ();
@@ -195,8 +195,8 @@ public:
int O () const { return d_O; }
const std::vector&lt;int&gt; &amp; NS () const { return d_NS; }
const std::vector&lt;int&gt; &amp; OS () const { return d_OS; }
- const std::vector&lt;int&gt; &amp; PS () const { return d_PS; }
- const std::vector&lt;int&gt; &amp; PI () const { return d_PI; }
+ const std::vector&lt; std::vector&lt; int&gt; &gt; &amp; PS () const { return d_PS; }
+ const std::vector&lt; std::vector&lt; int&gt; &gt; &amp; PI () const { return d_PI; }
const std::vector&lt;int&gt; &amp; TMi () const { return d_TMi; }
const std::vector&lt;int&gt; &amp; TMl () const { return d_TMl; }
};
diff --git a/gr-trellis/examples/grc/CMakeLists.txt b/gr-trellis/examples/grc/CMakeLists.txt
index 35280d515f..c5d4fc8965 100644
--- a/gr-trellis/examples/grc/CMakeLists.txt
+++ b/gr-trellis/examples/grc/CMakeLists.txt
@@ -20,13 +20,18 @@
## Configure GRC examples to point to the right fsm_files directory
set(FSM_FILE_INSTALL_DIR "${CMAKE_INSTALL_PREFIX}/${GR_PKG_TRELLIS_EXAMPLES_DIR}/fsm_files/")
configure_file(
- "${CMAKE_CURRENT_SOURCE_DIR}/pccc.grc"
- "${CMAKE_CURRENT_BINARY_DIR}/pccc.grc"
+ "${CMAKE_CURRENT_SOURCE_DIR}/tcm.grc"
+ "${CMAKE_CURRENT_BINARY_DIR}/tcm.grc"
+)
+
+configure_file(
+ "${CMAKE_CURRENT_SOURCE_DIR}/viterbi_equalization.grc"
+ "${CMAKE_CURRENT_BINARY_DIR}/viterbi_equalization.grc"
)
configure_file(
- "${CMAKE_CURRENT_SOURCE_DIR}/pccc1.grc"
- "${CMAKE_CURRENT_BINARY_DIR}/pccc1.grc"
+ "${CMAKE_CURRENT_SOURCE_DIR}/turbo_equalization.grc"
+ "${CMAKE_CURRENT_BINARY_DIR}/turbo_equalization.grc"
)
configure_file(
@@ -35,8 +40,8 @@ configure_file(
)
configure_file(
- "${CMAKE_CURRENT_SOURCE_DIR}/sccc1.grc"
- "${CMAKE_CURRENT_BINARY_DIR}/sccc1.grc"
+ "${CMAKE_CURRENT_SOURCE_DIR}/pccc.grc"
+ "${CMAKE_CURRENT_BINARY_DIR}/pccc.grc"
)
configure_file(
@@ -46,11 +51,12 @@ configure_file(
install(
FILES
- ${CMAKE_CURRENT_BINARY_DIR}/interference_cancellation.grc
- ${CMAKE_CURRENT_BINARY_DIR}/pccc.grc
- ${CMAKE_CURRENT_BINARY_DIR}/pccc1.grc
- ${CMAKE_CURRENT_BINARY_DIR}/sccc1.grc
+ ${CMAKE_CURRENT_BINARY_DIR}/tcm.grc
+ ${CMAKE_CURRENT_BINARY_DIR}/viterbi_equalization.grc
+ ${CMAKE_CURRENT_BINARY_DIR}/turbo_equalization.grc
${CMAKE_CURRENT_BINARY_DIR}/sccc.grc
+ ${CMAKE_CURRENT_BINARY_DIR}/pccc.grc
+ ${CMAKE_CURRENT_BINARY_DIR}/interference_cancellation.grc
readme.txt
DESTINATION ${GR_PKG_TRELLIS_EXAMPLES_DIR}
COMPONENT "trellis-examples"
diff --git a/gr-trellis/examples/grc/interference_cancellation.grc b/gr-trellis/examples/grc/interference_cancellation.grc
index 2ccc723235..1dbcf69b86 100644
--- a/gr-trellis/examples/grc/interference_cancellation.grc
+++ b/gr-trellis/examples/grc/interference_cancellation.grc
@@ -1,6 +1,6 @@
<?xml version='1.0' encoding='ASCII'?>
<flow_graph>
- <timestamp>Mon Jul 28 14:00:18 2014</timestamp>
+ <timestamp>Fri Sep 26 18:21:00 2014</timestamp>
<block>
<key>options</key>
<param>
@@ -29,7 +29,7 @@
</param>
<param>
<key>generate_options</key>
- <value>qt_gui</value>
+ <value>wx_gui</value>
</param>
<param>
<key>category</key>
@@ -52,10 +52,6 @@
<value></value>
</param>
<param>
- <key>alias</key>
- <value></value>
- </param>
- <param>
<key>_coordinate</key>
<value>(10, 10)</value>
</param>
@@ -79,12 +75,8 @@
<value>"@FSM_FILE_INSTALL_DIR@"</value>
</param>
<param>
- <key>alias</key>
- <value></value>
- </param>
- <param>
<key>_coordinate</key>
- <value>(660, 11)</value>
+ <value>(871, 14)</value>
</param>
<param>
<key>_rotation</key>
@@ -95,7 +87,7 @@
<key>variable</key>
<param>
<key>id</key>
- <value>block</value>
+ <value>R</value>
</param>
<param>
<key>_enabled</key>
@@ -103,15 +95,11 @@
</param>
<param>
<key>value</key>
- <value>1000</value>
- </param>
- <param>
- <key>alias</key>
- <value></value>
+ <value>100e3</value>
</param>
<param>
<key>_coordinate</key>
- <value>(583, 10)</value>
+ <value>(748, 12)</value>
</param>
<param>
<key>_rotation</key>
@@ -122,7 +110,7 @@
<key>variable</key>
<param>
<key>id</key>
- <value>R</value>
+ <value>noisevar</value>
</param>
<param>
<key>_enabled</key>
@@ -130,15 +118,11 @@
</param>
<param>
<key>value</key>
- <value>100e3</value>
- </param>
- <param>
- <key>alias</key>
- <value></value>
+ <value>10**(-snr_db/10)</value>
</param>
<param>
<key>_coordinate</key>
- <value>(502, 10)</value>
+ <value>(637, 13)</value>
</param>
<param>
<key>_rotation</key>
@@ -149,7 +133,7 @@
<key>variable</key>
<param>
<key>id</key>
- <value>noisevar</value>
+ <value>fsm1</value>
</param>
<param>
<key>_enabled</key>
@@ -157,15 +141,11 @@
</param>
<param>
<key>value</key>
- <value>10**(-snr_db/10)</value>
- </param>
- <param>
- <key>alias</key>
- <value></value>
+ <value>"awgn1o2_16.fsm"</value>
</param>
<param>
<key>_coordinate</key>
- <value>(428, 10)</value>
+ <value>(849, 87)</value>
</param>
<param>
<key>_rotation</key>
@@ -173,54 +153,45 @@
</param>
</block>
<block>
- <key>analog_random_source_x</key>
+ <key>variable</key>
<param>
<key>id</key>
- <value>analog_random_source_x_0</value>
+ <value>fsm2</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>type</key>
- <value>short</value>
+ <key>value</key>
+ <value>"awgn1o2_4.fsm"</value>
</param>
<param>
- <key>min</key>
- <value>0</value>
+ <key>_coordinate</key>
+ <value>(849, 153)</value>
</param>
<param>
- <key>max</key>
- <value>2</value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>variable</key>
<param>
- <key>num_samps</key>
- <value>1000</value>
+ <key>id</key>
+ <value>block</value>
</param>
<param>
- <key>repeat</key>
+ <key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>alias</key>
- <value></value>
- </param>
- <param>
- <key>affinity</key>
- <value></value>
- </param>
- <param>
- <key>minoutbuf</key>
- <value>0</value>
- </param>
- <param>
- <key>maxoutbuf</key>
- <value>0</value>
+ <key>value</key>
+ <value>1000</value>
</param>
<param>
<key>_coordinate</key>
- <value>(21, 170)</value>
+ <value>(752, 85)</value>
</param>
<param>
<key>_rotation</key>
@@ -228,38 +199,34 @@
</param>
</block>
<block>
- <key>analog_random_source_x</key>
+ <key>digital_chunks_to_symbols_xx</key>
<param>
<key>id</key>
- <value>analog_random_source_x_1</value>
+ <value>digital_chunks_to_symbols_xx_0_0_1</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>type</key>
- <value>short</value>
- </param>
- <param>
- <key>min</key>
- <value>0</value>
+ <key>in_type</key>
+ <value>byte</value>
</param>
<param>
- <key>max</key>
- <value>2</value>
+ <key>out_type</key>
+ <value>complex</value>
</param>
<param>
- <key>num_samps</key>
- <value>1000</value>
+ <key>symbol_table</key>
+ <value>1,1j,-1j,-1</value>
</param>
<param>
- <key>repeat</key>
- <value>True</value>
+ <key>dimension</key>
+ <value>1</value>
</param>
<param>
- <key>alias</key>
- <value></value>
+ <key>num_ports</key>
+ <value>1</value>
</param>
<param>
<key>affinity</key>
@@ -270,12 +237,8 @@
<value>0</value>
</param>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
- </param>
- <param>
<key>_coordinate</key>
- <value>(25, 291)</value>
+ <value>(408, 1719)</value>
</param>
<param>
<key>_rotation</key>
@@ -283,46 +246,22 @@
</param>
</block>
<block>
- <key>blocks_sub_xx</key>
+ <key>virtual_source</key>
<param>
<key>id</key>
- <value>blocks_sub_xx_0</value>
+ <value>virtual_source_0_0</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>type</key>
- <value>short</value>
- </param>
- <param>
- <key>vlen</key>
- <value>1</value>
- </param>
- <param>
- <key>num_inputs</key>
- <value>2</value>
- </param>
- <param>
- <key>alias</key>
- <value></value>
- </param>
- <param>
- <key>affinity</key>
- <value></value>
- </param>
- <param>
- <key>minoutbuf</key>
- <value>0</value>
- </param>
- <param>
- <key>maxoutbuf</key>
- <value>0</value>
+ <key>stream_id</key>
+ <value>user1</value>
</param>
<param>
<key>_coordinate</key>
- <value>(536, 529)</value>
+ <value>(356, 1844)</value>
</param>
<param>
<key>_rotation</key>
@@ -330,46 +269,22 @@
</param>
</block>
<block>
- <key>blocks_multiply_xx</key>
+ <key>virtual_source</key>
<param>
<key>id</key>
- <value>blocks_multiply_xx_0</value>
+ <value>virtual_source_0_2_0</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>type</key>
- <value>short</value>
- </param>
- <param>
- <key>num_inputs</key>
- <value>2</value>
- </param>
- <param>
- <key>vlen</key>
- <value>1</value>
- </param>
- <param>
- <key>alias</key>
- <value></value>
- </param>
- <param>
- <key>affinity</key>
- <value></value>
- </param>
- <param>
- <key>minoutbuf</key>
- <value>0</value>
- </param>
- <param>
- <key>maxoutbuf</key>
- <value>0</value>
+ <key>stream_id</key>
+ <value>user2_est</value>
</param>
<param>
<key>_coordinate</key>
- <value>(771, 525)</value>
+ <value>(10, 1649)</value>
</param>
<param>
<key>_rotation</key>
@@ -380,7 +295,7 @@
<key>blocks_sub_xx</key>
<param>
<key>id</key>
- <value>blocks_sub_xx_3</value>
+ <value>blocks_sub_xx_2_0</value>
</param>
<param>
<key>_enabled</key>
@@ -388,7 +303,7 @@
</param>
<param>
<key>type</key>
- <value>short</value>
+ <value>complex</value>
</param>
<param>
<key>vlen</key>
@@ -399,10 +314,6 @@
<value>2</value>
</param>
<param>
- <key>alias</key>
- <value></value>
- </param>
- <param>
<key>affinity</key>
<value></value>
</param>
@@ -411,12 +322,8 @@
<value>0</value>
</param>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
- </param>
- <param>
<key>_coordinate</key>
- <value>(535, 792)</value>
+ <value>(963, 1695)</value>
</param>
<param>
<key>_rotation</key>
@@ -424,46 +331,22 @@
</param>
</block>
<block>
- <key>blocks_sub_xx</key>
+ <key>virtual_source</key>
<param>
<key>id</key>
- <value>blocks_sub_xx_2</value>
+ <value>virtual_source_0_1_2</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>type</key>
- <value>complex</value>
- </param>
- <param>
- <key>vlen</key>
- <value>1</value>
- </param>
- <param>
- <key>num_inputs</key>
- <value>2</value>
- </param>
- <param>
- <key>alias</key>
- <value></value>
- </param>
- <param>
- <key>affinity</key>
- <value></value>
- </param>
- <param>
- <key>minoutbuf</key>
- <value>0</value>
- </param>
- <param>
- <key>maxoutbuf</key>
- <value>0</value>
+ <key>stream_id</key>
+ <value>observation</value>
</param>
<param>
<key>_coordinate</key>
- <value>(944, 978)</value>
+ <value>(705, 1660)</value>
</param>
<param>
<key>_rotation</key>
@@ -471,10 +354,10 @@
</param>
</block>
<block>
- <key>blocks_sub_xx</key>
+ <key>blocks_multiply_const_vxx</key>
<param>
<key>id</key>
- <value>blocks_sub_xx_1</value>
+ <value>blocks_multiply_const_vxx_2_0</value>
</param>
<param>
<key>_enabled</key>
@@ -482,19 +365,15 @@
</param>
<param>
<key>type</key>
- <value>short</value>
- </param>
- <param>
- <key>vlen</key>
- <value>1</value>
+ <value>complex</value>
</param>
<param>
- <key>num_inputs</key>
- <value>2</value>
+ <key>const</key>
+ <value>(1-alpha)**0.5</value>
</param>
<param>
- <key>alias</key>
- <value></value>
+ <key>vlen</key>
+ <value>1</value>
</param>
<param>
<key>affinity</key>
@@ -505,12 +384,8 @@
<value>0</value>
</param>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
- </param>
- <param>
<key>_coordinate</key>
- <value>(540, 1141)</value>
+ <value>(721, 1727)</value>
</param>
<param>
<key>_rotation</key>
@@ -518,30 +393,34 @@
</param>
</block>
<block>
- <key>blocks_sub_xx</key>
+ <key>digital_chunks_to_symbols_xx</key>
<param>
<key>id</key>
- <value>blocks_sub_xx_2_0</value>
+ <value>digital_chunks_to_symbols_xx_0_0_0</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>type</key>
+ <key>in_type</key>
+ <value>byte</value>
+ </param>
+ <param>
+ <key>out_type</key>
<value>complex</value>
</param>
<param>
- <key>vlen</key>
- <value>1</value>
+ <key>symbol_table</key>
+ <value>1,1j,-1j,-1</value>
</param>
<param>
- <key>num_inputs</key>
- <value>2</value>
+ <key>dimension</key>
+ <value>1</value>
</param>
<param>
- <key>alias</key>
- <value></value>
+ <key>num_ports</key>
+ <value>1</value>
</param>
<param>
<key>affinity</key>
@@ -552,12 +431,8 @@
<value>0</value>
</param>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
- </param>
- <param>
<key>_coordinate</key>
- <value>(975, 1342)</value>
+ <value>(416, 1251)</value>
</param>
<param>
<key>_rotation</key>
@@ -565,46 +440,22 @@
</param>
</block>
<block>
- <key>blocks_sub_xx</key>
+ <key>virtual_source</key>
<param>
<key>id</key>
- <value>blocks_sub_xx_1_0</value>
+ <value>virtual_source_0_4</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>type</key>
- <value>short</value>
- </param>
- <param>
- <key>vlen</key>
- <value>1</value>
- </param>
- <param>
- <key>num_inputs</key>
- <value>2</value>
- </param>
- <param>
- <key>alias</key>
- <value></value>
- </param>
- <param>
- <key>affinity</key>
- <value></value>
- </param>
- <param>
- <key>minoutbuf</key>
- <value>0</value>
- </param>
- <param>
- <key>maxoutbuf</key>
- <value>0</value>
+ <key>stream_id</key>
+ <value>user2</value>
</param>
<param>
<key>_coordinate</key>
- <value>(559, 1536)</value>
+ <value>(359, 1373)</value>
</param>
<param>
<key>_rotation</key>
@@ -612,46 +463,22 @@
</param>
</block>
<block>
- <key>blocks_add_xx</key>
+ <key>virtual_source</key>
<param>
<key>id</key>
- <value>blocks_add_xx_0</value>
+ <value>virtual_source_0_2</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>type</key>
- <value>complex</value>
- </param>
- <param>
- <key>num_inputs</key>
- <value>2</value>
- </param>
- <param>
- <key>vlen</key>
- <value>1</value>
- </param>
- <param>
- <key>alias</key>
- <value></value>
- </param>
- <param>
- <key>affinity</key>
- <value></value>
- </param>
- <param>
- <key>minoutbuf</key>
- <value>0</value>
- </param>
- <param>
- <key>maxoutbuf</key>
- <value>0</value>
+ <key>stream_id</key>
+ <value>user1_est</value>
</param>
<param>
<key>_coordinate</key>
- <value>(1224, 245)</value>
+ <value>(33, 1187)</value>
</param>
<param>
<key>_rotation</key>
@@ -659,10 +486,10 @@
</param>
</block>
<block>
- <key>analog_noise_source_x</key>
+ <key>blocks_sub_xx</key>
<param>
<key>id</key>
- <value>analog_noise_source_x_0</value>
+ <value>blocks_sub_xx_2</value>
</param>
<param>
<key>_enabled</key>
@@ -673,20 +500,12 @@
<value>complex</value>
</param>
<param>
- <key>noise_type</key>
- <value>analog.GR_GAUSSIAN</value>
- </param>
- <param>
- <key>amp</key>
- <value>noisevar</value>
- </param>
- <param>
- <key>seed</key>
- <value>-42</value>
+ <key>vlen</key>
+ <value>1</value>
</param>
<param>
- <key>alias</key>
- <value></value>
+ <key>num_inputs</key>
+ <value>2</value>
</param>
<param>
<key>affinity</key>
@@ -697,12 +516,8 @@
<value>0</value>
</param>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
- </param>
- <param>
<key>_coordinate</key>
- <value>(1178, 321)</value>
+ <value>(942, 1229)</value>
</param>
<param>
<key>_rotation</key>
@@ -710,50 +525,22 @@
</param>
</block>
<block>
- <key>blocks_throttle</key>
+ <key>virtual_source</key>
<param>
<key>id</key>
- <value>blocks_throttle_0</value>
+ <value>virtual_source_0_1_1</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>type</key>
- <value>short</value>
- </param>
- <param>
- <key>samples_per_second</key>
- <value>R</value>
- </param>
- <param>
- <key>vlen</key>
- <value>1</value>
- </param>
- <param>
- <key>ignoretag</key>
- <value>True</value>
- </param>
- <param>
- <key>alias</key>
- <value></value>
- </param>
- <param>
- <key>affinity</key>
- <value></value>
- </param>
- <param>
- <key>minoutbuf</key>
- <value>0</value>
- </param>
- <param>
- <key>maxoutbuf</key>
- <value>0</value>
+ <key>stream_id</key>
+ <value>observation</value>
</param>
<param>
<key>_coordinate</key>
- <value>(579, 143)</value>
+ <value>(698, 1198)</value>
</param>
<param>
<key>_rotation</key>
@@ -764,7 +551,7 @@
<key>blocks_multiply_const_vxx</key>
<param>
<key>id</key>
- <value>blocks_multiply_const_vxx_0</value>
+ <value>blocks_multiply_const_vxx_2</value>
</param>
<param>
<key>_enabled</key>
@@ -783,10 +570,6 @@
<value>1</value>
</param>
<param>
- <key>alias</key>
- <value></value>
- </param>
- <param>
<key>affinity</key>
<value></value>
</param>
@@ -795,12 +578,8 @@
<value>0</value>
</param>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
- </param>
- <param>
<key>_coordinate</key>
- <value>(988, 196)</value>
+ <value>(708, 1259)</value>
</param>
<param>
<key>_rotation</key>
@@ -808,54 +587,45 @@
</param>
</block>
<block>
- <key>digital_chunks_to_symbols_xx</key>
+ <key>virtual_source</key>
<param>
<key>id</key>
- <value>digital_chunks_to_symbols_xx_0</value>
+ <value>virtual_source_0_3</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>in_type</key>
- <value>short</value>
- </param>
- <param>
- <key>out_type</key>
- <value>complex</value>
- </param>
- <param>
- <key>symbol_table</key>
- <value>1,1j,-1j,-1</value>
- </param>
- <param>
- <key>dimension</key>
- <value>1</value>
+ <key>stream_id</key>
+ <value>user2</value>
</param>
<param>
- <key>num_ports</key>
- <value>1</value>
+ <key>_coordinate</key>
+ <value>(342, 928)</value>
</param>
<param>
- <key>alias</key>
- <value></value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>virtual_sink</key>
<param>
- <key>affinity</key>
- <value></value>
+ <key>id</key>
+ <value>virtual_sink_0_2_0</value>
</param>
<param>
- <key>minoutbuf</key>
- <value>0</value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
+ <key>stream_id</key>
+ <value>user2_est</value>
</param>
<param>
<key>_coordinate</key>
- <value>(703, 211)</value>
+ <value>(341, 1025)</value>
</param>
<param>
<key>_rotation</key>
@@ -863,46 +633,45 @@
</param>
</block>
<block>
- <key>blocks_multiply_const_vxx</key>
+ <key>virtual_source</key>
<param>
<key>id</key>
- <value>blocks_multiply_const_vxx_1</value>
+ <value>virtual_source_0_1_0</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>type</key>
- <value>complex</value>
- </param>
- <param>
- <key>const</key>
- <value>(1-alpha)**0.5</value>
+ <key>stream_id</key>
+ <value>observation</value>
</param>
<param>
- <key>vlen</key>
- <value>1</value>
+ <key>_coordinate</key>
+ <value>(11, 873)</value>
</param>
<param>
- <key>alias</key>
- <value></value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>virtual_source</key>
<param>
- <key>affinity</key>
- <value></value>
+ <key>id</key>
+ <value>virtual_source_0</value>
</param>
<param>
- <key>minoutbuf</key>
- <value>0</value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
+ <key>stream_id</key>
+ <value>user1</value>
</param>
<param>
<key>_coordinate</key>
- <value>(994, 319)</value>
+ <value>(348, 566)</value>
</param>
<param>
<key>_rotation</key>
@@ -910,54 +679,45 @@
</param>
</block>
<block>
- <key>digital_chunks_to_symbols_xx</key>
+ <key>virtual_sink</key>
<param>
<key>id</key>
- <value>digital_chunks_to_symbols_xx_0_0</value>
+ <value>virtual_sink_0_2</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>in_type</key>
- <value>short</value>
- </param>
- <param>
- <key>out_type</key>
- <value>complex</value>
- </param>
- <param>
- <key>symbol_table</key>
- <value>1,1j,-1j,-1</value>
+ <key>stream_id</key>
+ <value>user1_est</value>
</param>
<param>
- <key>dimension</key>
- <value>1</value>
- </param>
- <param>
- <key>num_ports</key>
- <value>1</value>
+ <key>_coordinate</key>
+ <value>(355, 687)</value>
</param>
<param>
- <key>alias</key>
- <value></value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>virtual_source</key>
<param>
- <key>affinity</key>
- <value></value>
+ <key>id</key>
+ <value>virtual_source_0_1</value>
</param>
<param>
- <key>minoutbuf</key>
- <value>0</value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
+ <key>stream_id</key>
+ <value>observation</value>
</param>
<param>
<key>_coordinate</key>
- <value>(703, 311)</value>
+ <value>(13, 530)</value>
</param>
<param>
<key>_rotation</key>
@@ -965,84 +725,81 @@
</param>
</block>
<block>
- <key>digital_chunks_to_symbols_xx</key>
+ <key>wxgui_numbersink2</key>
<param>
<key>id</key>
- <value>digital_chunks_to_symbols_xx_0_0_0</value>
+ <value>wxgui_numbersink2_0</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>in_type</key>
- <value>short</value>
+ <key>type</key>
+ <value>float</value>
</param>
<param>
- <key>out_type</key>
- <value>complex</value>
+ <key>title</key>
+ <value>BER 1 (raw)</value>
</param>
<param>
- <key>symbol_table</key>
- <value>1,1j,-1j,-1</value>
+ <key>units</key>
+ <value>BER</value>
</param>
<param>
- <key>dimension</key>
- <value>1</value>
+ <key>samp_rate</key>
+ <value>R</value>
</param>
<param>
- <key>num_ports</key>
- <value>1</value>
+ <key>min_value</key>
+ <value>0</value>
</param>
<param>
- <key>alias</key>
- <value></value>
+ <key>max_value</key>
+ <value>1</value>
</param>
<param>
- <key>affinity</key>
- <value></value>
+ <key>factor</key>
+ <value>1.0</value>
</param>
<param>
- <key>minoutbuf</key>
- <value>0</value>
+ <key>decimal_places</key>
+ <value>6</value>
</param>
<param>
- <key>maxoutbuf</key>
+ <key>ref_level</key>
<value>0</value>
</param>
<param>
- <key>_coordinate</key>
- <value>(418, 1000)</value>
+ <key>number_rate</key>
+ <value>15</value>
</param>
<param>
- <key>_rotation</key>
- <value>0</value>
+ <key>peak_hold</key>
+ <value>False</value>
</param>
- </block>
- <block>
- <key>blocks_multiply_const_vxx</key>
<param>
- <key>id</key>
- <value>blocks_multiply_const_vxx_2</value>
+ <key>average</key>
+ <value>False</value>
</param>
<param>
- <key>_enabled</key>
- <value>True</value>
+ <key>avg_alpha</key>
+ <value>0.001</value>
</param>
<param>
- <key>type</key>
- <value>complex</value>
+ <key>show_gauge</key>
+ <value>True</value>
</param>
<param>
- <key>const</key>
- <value>alpha**0.5</value>
+ <key>win_size</key>
+ <value></value>
</param>
<param>
- <key>vlen</key>
- <value>1</value>
+ <key>grid_pos</key>
+ <value>0,0,1,1</value>
</param>
<param>
- <key>alias</key>
+ <key>notebook</key>
<value></value>
</param>
<param>
@@ -1050,16 +807,8 @@
<value></value>
</param>
<param>
- <key>minoutbuf</key>
- <value>0</value>
- </param>
- <param>
- <key>maxoutbuf</key>
- <value>0</value>
- </param>
- <param>
<key>_coordinate</key>
- <value>(710, 1008)</value>
+ <value>(944, 556)</value>
</param>
<param>
<key>_rotation</key>
@@ -1067,10 +816,10 @@
</param>
</block>
<block>
- <key>blocks_multiply_const_vxx</key>
+ <key>wxgui_numbersink2</key>
<param>
<key>id</key>
- <value>blocks_multiply_const_vxx_2_0</value>
+ <value>wxgui_numbersink2_2</value>
</param>
<param>
<key>_enabled</key>
@@ -1078,73 +827,70 @@
</param>
<param>
<key>type</key>
- <value>complex</value>
+ <value>float</value>
</param>
<param>
- <key>const</key>
- <value>(1-alpha)**0.5</value>
+ <key>title</key>
+ <value>BER 2 (raw)</value>
</param>
<param>
- <key>vlen</key>
- <value>1</value>
+ <key>units</key>
+ <value>BER</value>
</param>
<param>
- <key>alias</key>
- <value></value>
+ <key>samp_rate</key>
+ <value>R</value>
</param>
<param>
- <key>affinity</key>
- <value></value>
+ <key>min_value</key>
+ <value>0</value>
</param>
<param>
- <key>minoutbuf</key>
- <value>0</value>
+ <key>max_value</key>
+ <value>1.0</value>
</param>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
+ <key>factor</key>
+ <value>1.0</value>
</param>
<param>
- <key>_coordinate</key>
- <value>(733, 1374)</value>
+ <key>decimal_places</key>
+ <value>6</value>
</param>
<param>
- <key>_rotation</key>
+ <key>ref_level</key>
<value>0</value>
</param>
- </block>
- <block>
- <key>digital_chunks_to_symbols_xx</key>
<param>
- <key>id</key>
- <value>digital_chunks_to_symbols_xx_0_0_1</value>
+ <key>number_rate</key>
+ <value>15</value>
</param>
<param>
- <key>_enabled</key>
- <value>True</value>
+ <key>peak_hold</key>
+ <value>False</value>
</param>
<param>
- <key>in_type</key>
- <value>short</value>
+ <key>average</key>
+ <value>False</value>
</param>
<param>
- <key>out_type</key>
- <value>complex</value>
+ <key>avg_alpha</key>
+ <value>0.001</value>
</param>
<param>
- <key>symbol_table</key>
- <value>1,1j,-1j,-1</value>
+ <key>show_gauge</key>
+ <value>True</value>
</param>
<param>
- <key>dimension</key>
- <value>1</value>
+ <key>win_size</key>
+ <value></value>
</param>
<param>
- <key>num_ports</key>
- <value>1</value>
+ <key>grid_pos</key>
+ <value>0,1,1,1</value>
</param>
<param>
- <key>alias</key>
+ <key>notebook</key>
<value></value>
</param>
<param>
@@ -1152,16 +898,8 @@
<value></value>
</param>
<param>
- <key>minoutbuf</key>
- <value>0</value>
- </param>
- <param>
- <key>maxoutbuf</key>
- <value>0</value>
- </param>
- <param>
<key>_coordinate</key>
- <value>(420, 1366)</value>
+ <value>(944, 886)</value>
</param>
<param>
<key>_rotation</key>
@@ -1169,128 +907,101 @@
</param>
</block>
<block>
- <key>variable_qtgui_range</key>
+ <key>wxgui_numbersink2</key>
<param>
<key>id</key>
- <value>alpha</value>
+ <value>wxgui_numbersink2_3</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>label</key>
- <value>P1/P</value>
+ <key>type</key>
+ <value>float</value>
</param>
<param>
- <key>value</key>
- <value>0.6</value>
+ <key>title</key>
+ <value>BER 2 (after cancelling user 1)</value>
</param>
<param>
- <key>start</key>
- <value>0</value>
+ <key>units</key>
+ <value>BER</value>
</param>
<param>
- <key>stop</key>
- <value>1</value>
+ <key>samp_rate</key>
+ <value>R</value>
</param>
<param>
- <key>step</key>
- <value>0.01</value>
+ <key>min_value</key>
+ <value>0</value>
</param>
<param>
- <key>widget</key>
- <value>counter_slider</value>
+ <key>max_value</key>
+ <value>1.0</value>
</param>
<param>
- <key>orient</key>
- <value>Qt.Horizontal</value>
+ <key>factor</key>
+ <value>1.0</value>
</param>
<param>
- <key>min_len</key>
- <value>200</value>
+ <key>decimal_places</key>
+ <value>6</value>
</param>
<param>
- <key>gui_hint</key>
- <value></value>
+ <key>ref_level</key>
+ <value>0</value>
</param>
<param>
- <key>alias</key>
- <value></value>
+ <key>number_rate</key>
+ <value>15</value>
</param>
<param>
- <key>_coordinate</key>
- <value>(177, 10)</value>
+ <key>peak_hold</key>
+ <value>False</value>
</param>
<param>
- <key>_rotation</key>
- <value>180</value>
+ <key>average</key>
+ <value>False</value>
</param>
- </block>
- <block>
- <key>variable_qtgui_range</key>
<param>
- <key>id</key>
- <value>snr_db</value>
+ <key>avg_alpha</key>
+ <value>0.001</value>
</param>
<param>
- <key>_enabled</key>
+ <key>show_gauge</key>
<value>True</value>
</param>
<param>
- <key>label</key>
- <value>P/sigma^2 (dB)</value>
- </param>
- <param>
- <key>value</key>
- <value>16</value>
- </param>
- <param>
- <key>start</key>
- <value>0</value>
- </param>
- <param>
- <key>stop</key>
- <value>20</value>
- </param>
- <param>
- <key>step</key>
- <value>0.01</value>
- </param>
- <param>
- <key>widget</key>
- <value>counter_slider</value>
- </param>
- <param>
- <key>orient</key>
- <value>Qt.Horizontal</value>
+ <key>win_size</key>
+ <value></value>
</param>
<param>
- <key>min_len</key>
- <value>200</value>
+ <key>grid_pos</key>
+ <value>1,1,1,1</value>
</param>
<param>
- <key>gui_hint</key>
+ <key>notebook</key>
<value></value>
</param>
<param>
- <key>alias</key>
+ <key>affinity</key>
<value></value>
</param>
<param>
<key>_coordinate</key>
- <value>(300, 10)</value>
+ <value>(945, 1351)</value>
</param>
<param>
<key>_rotation</key>
- <value>180</value>
+ <value>0</value>
</param>
</block>
<block>
- <key>blocks_add_xx</key>
+ <key>blocks_multiply_const_vxx</key>
<param>
<key>id</key>
- <value>blocks_add_xx_1</value>
+ <value>blocks_multiply_const_vxx_1</value>
</param>
<param>
<key>_enabled</key>
@@ -1301,18 +1012,14 @@
<value>complex</value>
</param>
<param>
- <key>num_inputs</key>
- <value>2</value>
+ <key>const</key>
+ <value>(1-alpha)**0.5</value>
</param>
<param>
<key>vlen</key>
<value>1</value>
</param>
<param>
- <key>alias</key>
- <value></value>
- </param>
- <param>
<key>affinity</key>
<value></value>
</param>
@@ -1321,12 +1028,8 @@
<value>0</value>
</param>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
- </param>
- <param>
<key>_coordinate</key>
- <value>(1400, 262)</value>
+ <value>(943, 402)</value>
</param>
<param>
<key>_rotation</key>
@@ -1334,10 +1037,10 @@
</param>
</block>
<block>
- <key>qtgui_const_sink_x</key>
+ <key>blocks_multiply_const_vxx</key>
<param>
<key>id</key>
- <value>qtgui_const_sink_x_0</value>
+ <value>blocks_multiply_const_vxx_0</value>
</param>
<param>
<key>_enabled</key>
@@ -1348,320 +1051,141 @@
<value>complex</value>
</param>
<param>
- <key>name</key>
- <value>Constellation</value>
- </param>
- <param>
- <key>size</key>
- <value>1024</value>
- </param>
- <param>
- <key>grid</key>
- <value>False</value>
- </param>
- <param>
- <key>autoscale</key>
- <value>False</value>
- </param>
- <param>
- <key>ymin</key>
- <value>-2</value>
- </param>
- <param>
- <key>ymax</key>
- <value>2</value>
- </param>
- <param>
- <key>xmin</key>
- <value>-2</value>
- </param>
- <param>
- <key>xmax</key>
- <value>2</value>
+ <key>const</key>
+ <value>alpha**0.5</value>
</param>
<param>
- <key>nconnections</key>
+ <key>vlen</key>
<value>1</value>
</param>
<param>
- <key>update_time</key>
- <value>0.10</value>
- </param>
- <param>
- <key>gui_hint</key>
+ <key>affinity</key>
<value></value>
</param>
<param>
- <key>tr_mode</key>
- <value>qtgui.TRIG_MODE_FREE</value>
- </param>
- <param>
- <key>tr_slope</key>
- <value>qtgui.TRIG_SLOPE_POS</value>
- </param>
- <param>
- <key>tr_level</key>
- <value>0.0</value>
- </param>
- <param>
- <key>tr_chan</key>
+ <key>minoutbuf</key>
<value>0</value>
</param>
<param>
- <key>tr_tag</key>
- <value>""</value>
- </param>
- <param>
- <key>label1</key>
- <value></value>
- </param>
- <param>
- <key>width1</key>
- <value>1</value>
- </param>
- <param>
- <key>color1</key>
- <value>"blue"</value>
- </param>
- <param>
- <key>style1</key>
- <value>0</value>
+ <key>_coordinate</key>
+ <value>(947, 301)</value>
</param>
<param>
- <key>marker1</key>
+ <key>_rotation</key>
<value>0</value>
</param>
+ </block>
+ <block>
+ <key>virtual_sink</key>
<param>
- <key>alpha1</key>
- <value>1.0</value>
- </param>
- <param>
- <key>label2</key>
- <value></value>
+ <key>id</key>
+ <value>virtual_sink_0_0</value>
</param>
<param>
- <key>width2</key>
- <value>1</value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>color2</key>
- <value>"red"</value>
+ <key>stream_id</key>
+ <value>user2</value>
</param>
<param>
- <key>style2</key>
- <value>0</value>
+ <key>_coordinate</key>
+ <value>(208, 340)</value>
</param>
<param>
- <key>marker2</key>
+ <key>_rotation</key>
<value>0</value>
</param>
+ </block>
+ <block>
+ <key>analog_random_source_x</key>
<param>
- <key>alpha2</key>
- <value>1.0</value>
- </param>
- <param>
- <key>label3</key>
- <value></value>
- </param>
- <param>
- <key>width3</key>
- <value>1</value>
+ <key>id</key>
+ <value>analog_random_source_x_1</value>
</param>
<param>
- <key>color3</key>
- <value>"red"</value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>style3</key>
- <value>0</value>
+ <key>type</key>
+ <value>byte</value>
</param>
<param>
- <key>marker3</key>
+ <key>min</key>
<value>0</value>
</param>
<param>
- <key>alpha3</key>
- <value>1.0</value>
- </param>
- <param>
- <key>label4</key>
- <value></value>
- </param>
- <param>
- <key>width4</key>
- <value>1</value>
- </param>
- <param>
- <key>color4</key>
- <value>"red"</value>
- </param>
- <param>
- <key>style4</key>
- <value>0</value>
+ <key>max</key>
+ <value>2</value>
</param>
<param>
- <key>marker4</key>
- <value>0</value>
+ <key>num_samps</key>
+ <value>block</value>
</param>
<param>
- <key>alpha4</key>
- <value>1.0</value>
+ <key>repeat</key>
+ <value>True</value>
</param>
<param>
- <key>label5</key>
+ <key>affinity</key>
<value></value>
</param>
<param>
- <key>width5</key>
- <value>1</value>
- </param>
- <param>
- <key>color5</key>
- <value>"red"</value>
- </param>
- <param>
- <key>style5</key>
- <value>0</value>
- </param>
- <param>
- <key>marker5</key>
+ <key>minoutbuf</key>
<value>0</value>
</param>
<param>
- <key>alpha5</key>
- <value>1.0</value>
- </param>
- <param>
- <key>label6</key>
- <value></value>
- </param>
- <param>
- <key>width6</key>
- <value>1</value>
- </param>
- <param>
- <key>color6</key>
- <value>"red"</value>
- </param>
- <param>
- <key>style6</key>
- <value>0</value>
+ <key>_coordinate</key>
+ <value>(22, 374)</value>
</param>
<param>
- <key>marker6</key>
+ <key>_rotation</key>
<value>0</value>
</param>
+ </block>
+ <block>
+ <key>digital_chunks_to_symbols_xx</key>
<param>
- <key>alpha6</key>
- <value>1.0</value>
- </param>
- <param>
- <key>label7</key>
- <value></value>
- </param>
- <param>
- <key>width7</key>
- <value>1</value>
- </param>
- <param>
- <key>color7</key>
- <value>"red"</value>
+ <key>id</key>
+ <value>digital_chunks_to_symbols_xx_0</value>
</param>
<param>
- <key>style7</key>
- <value>0</value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>marker7</key>
- <value>0</value>
+ <key>in_type</key>
+ <value>byte</value>
</param>
<param>
- <key>alpha7</key>
- <value>1.0</value>
+ <key>out_type</key>
+ <value>complex</value>
</param>
<param>
- <key>label8</key>
- <value></value>
+ <key>symbol_table</key>
+ <value>1,1j,-1j,-1</value>
</param>
<param>
- <key>width8</key>
+ <key>dimension</key>
<value>1</value>
</param>
<param>
- <key>color8</key>
- <value>"red"</value>
- </param>
- <param>
- <key>style8</key>
- <value>0</value>
- </param>
- <param>
- <key>marker8</key>
- <value>0</value>
- </param>
- <param>
- <key>alpha8</key>
- <value>1.0</value>
- </param>
- <param>
- <key>label9</key>
- <value></value>
- </param>
- <param>
- <key>width9</key>
+ <key>num_ports</key>
<value>1</value>
</param>
<param>
- <key>color9</key>
- <value>"red"</value>
- </param>
- <param>
- <key>style9</key>
- <value>0</value>
- </param>
- <param>
- <key>marker9</key>
- <value>0</value>
- </param>
- <param>
- <key>alpha9</key>
- <value>1.0</value>
- </param>
- <param>
- <key>label10</key>
+ <key>affinity</key>
<value></value>
</param>
<param>
- <key>width10</key>
- <value>1</value>
- </param>
- <param>
- <key>color10</key>
- <value>"red"</value>
- </param>
- <param>
- <key>style10</key>
- <value>0</value>
- </param>
- <param>
- <key>marker10</key>
+ <key>minoutbuf</key>
<value>0</value>
</param>
<param>
- <key>alpha10</key>
- <value>1.0</value>
- </param>
- <param>
- <key>alias</key>
- <value></value>
- </param>
- <param>
- <key>affinity</key>
- <value></value>
- </param>
- <param>
<key>_coordinate</key>
- <value>(0, 0)</value>
+ <value>(700, 294)</value>
</param>
<param>
<key>_rotation</key>
@@ -1669,26 +1193,26 @@
</param>
</block>
<block>
- <key>blocks_short_to_float</key>
+ <key>blocks_throttle</key>
<param>
<key>id</key>
- <value>blocks_short_to_float_0</value>
+ <value>blocks_throttle_0</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>vlen</key>
- <value>1</value>
+ <key>type</key>
+ <value>byte</value>
</param>
<param>
- <key>scale</key>
- <value>1</value>
+ <key>samples_per_second</key>
+ <value>R</value>
</param>
<param>
- <key>alias</key>
- <value></value>
+ <key>vlen</key>
+ <value>1</value>
</param>
<param>
<key>affinity</key>
@@ -1699,12 +1223,8 @@
<value>0</value>
</param>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
- </param>
- <param>
<key>_coordinate</key>
- <value>(1010, 1551)</value>
+ <value>(576, 226)</value>
</param>
<param>
<key>_rotation</key>
@@ -1712,226 +1232,194 @@
</param>
</block>
<block>
- <key>qtgui_number_sink</key>
+ <key>analog_random_source_x</key>
<param>
<key>id</key>
- <value>qtgui_number_sink_0</value>
+ <value>analog_random_source_x_0</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>name</key>
- <value>""</value>
- </param>
- <param>
<key>type</key>
- <value>float</value>
- </param>
- <param>
- <key>autoscale</key>
- <value>False</value>
- </param>
- <param>
- <key>avg</key>
- <value>0.001</value>
- </param>
- <param>
- <key>graph_type</key>
- <value>qtgui.NUM_GRAPH_HORIZ</value>
- </param>
- <param>
- <key>nconnections</key>
- <value>1</value>
+ <value>byte</value>
</param>
<param>
<key>min</key>
- <value>-1</value>
+ <value>0</value>
</param>
<param>
<key>max</key>
- <value>1</value>
- </param>
- <param>
- <key>update_time</key>
- <value>0.10</value>
+ <value>2</value>
</param>
<param>
- <key>gui_hint</key>
- <value>0,0,1,1</value>
+ <key>num_samps</key>
+ <value>block</value>
</param>
<param>
- <key>label1</key>
- <value></value>
+ <key>repeat</key>
+ <value>True</value>
</param>
<param>
- <key>unit1</key>
+ <key>affinity</key>
<value></value>
</param>
<param>
- <key>color1</key>
- <value>("black", "black")</value>
+ <key>minoutbuf</key>
+ <value>0</value>
</param>
<param>
- <key>factor1</key>
- <value>1</value>
+ <key>_coordinate</key>
+ <value>(18, 253)</value>
</param>
<param>
- <key>label2</key>
- <value></value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>virtual_sink</key>
<param>
- <key>unit2</key>
- <value></value>
+ <key>id</key>
+ <value>virtual_sink_0</value>
</param>
<param>
- <key>color2</key>
- <value>("black", "black")</value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>factor2</key>
- <value>1</value>
+ <key>stream_id</key>
+ <value>user1</value>
</param>
<param>
- <key>label3</key>
- <value></value>
+ <key>_coordinate</key>
+ <value>(208, 229)</value>
</param>
<param>
- <key>unit3</key>
- <value></value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>digital_chunks_to_symbols_xx</key>
<param>
- <key>color3</key>
- <value>("black", "black")</value>
+ <key>id</key>
+ <value>digital_chunks_to_symbols_xx_0_0</value>
</param>
<param>
- <key>factor3</key>
- <value>1</value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>label4</key>
- <value></value>
+ <key>in_type</key>
+ <value>byte</value>
</param>
<param>
- <key>unit4</key>
- <value></value>
+ <key>out_type</key>
+ <value>complex</value>
</param>
<param>
- <key>color4</key>
- <value>("black", "black")</value>
+ <key>symbol_table</key>
+ <value>1,1j,-1j,-1</value>
</param>
<param>
- <key>factor4</key>
+ <key>dimension</key>
<value>1</value>
</param>
<param>
- <key>label5</key>
- <value></value>
- </param>
- <param>
- <key>unit5</key>
- <value></value>
- </param>
- <param>
- <key>color5</key>
- <value>("black", "black")</value>
- </param>
- <param>
- <key>factor5</key>
+ <key>num_ports</key>
<value>1</value>
</param>
<param>
- <key>label6</key>
+ <key>affinity</key>
<value></value>
</param>
<param>
- <key>unit6</key>
- <value></value>
+ <key>minoutbuf</key>
+ <value>0</value>
</param>
<param>
- <key>color6</key>
- <value>("black", "black")</value>
+ <key>_coordinate</key>
+ <value>(700, 394)</value>
</param>
<param>
- <key>factor6</key>
- <value>1</value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>blocks_add_xx</key>
<param>
- <key>label7</key>
- <value></value>
+ <key>id</key>
+ <value>blocks_add_xx_1</value>
</param>
<param>
- <key>unit7</key>
- <value></value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>color7</key>
- <value>("black", "black")</value>
+ <key>type</key>
+ <value>complex</value>
</param>
<param>
- <key>factor7</key>
- <value>1</value>
+ <key>num_inputs</key>
+ <value>2</value>
</param>
<param>
- <key>label8</key>
- <value></value>
+ <key>vlen</key>
+ <value>1</value>
</param>
<param>
- <key>unit8</key>
+ <key>affinity</key>
<value></value>
</param>
<param>
- <key>color8</key>
- <value>("black", "black")</value>
- </param>
- <param>
- <key>factor8</key>
- <value>1</value>
- </param>
- <param>
- <key>label9</key>
- <value></value>
+ <key>minoutbuf</key>
+ <value>0</value>
</param>
<param>
- <key>unit9</key>
- <value></value>
+ <key>_coordinate</key>
+ <value>(1400, 341)</value>
</param>
<param>
- <key>color9</key>
- <value>("black", "black")</value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>blocks_add_xx</key>
<param>
- <key>factor9</key>
- <value>1</value>
+ <key>id</key>
+ <value>blocks_add_xx_0</value>
</param>
<param>
- <key>label10</key>
- <value></value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>unit10</key>
- <value></value>
+ <key>type</key>
+ <value>complex</value>
</param>
<param>
- <key>color10</key>
- <value>("black", "black")</value>
+ <key>num_inputs</key>
+ <value>2</value>
</param>
<param>
- <key>factor10</key>
+ <key>vlen</key>
<value>1</value>
</param>
<param>
- <key>alias</key>
+ <key>affinity</key>
<value></value>
</param>
<param>
- <key>affinity</key>
- <value></value>
+ <key>minoutbuf</key>
+ <value>0</value>
</param>
<param>
<key>_coordinate</key>
- <value>(1257, 471)</value>
+ <value>(1224, 324)</value>
</param>
<param>
<key>_rotation</key>
@@ -1939,10 +1427,10 @@
</param>
</block>
<block>
- <key>trellis_encoder_xx</key>
+ <key>analog_noise_source_x</key>
<param>
<key>id</key>
- <value>trellis_encoder_xx_1</value>
+ <value>analog_noise_source_x_0</value>
</param>
<param>
<key>_enabled</key>
@@ -1950,19 +1438,19 @@
</param>
<param>
<key>type</key>
- <value>ss</value>
+ <value>complex</value>
</param>
<param>
- <key>fsm_args</key>
- <value>prefix+"/awgn1o2_16.fsm"</value>
+ <key>noise_type</key>
+ <value>analog.GR_GAUSSIAN</value>
</param>
<param>
- <key>init_state</key>
- <value>0</value>
+ <key>amp</key>
+ <value>noisevar</value>
</param>
<param>
- <key>alias</key>
- <value></value>
+ <key>seed</key>
+ <value>-42</value>
</param>
<param>
<key>affinity</key>
@@ -1973,12 +1461,8 @@
<value>0</value>
</param>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
- </param>
- <param>
<key>_coordinate</key>
- <value>(336, 311)</value>
+ <value>(1178, 400)</value>
</param>
<param>
<key>_rotation</key>
@@ -1986,46 +1470,22 @@
</param>
</block>
<block>
- <key>trellis_encoder_xx</key>
+ <key>virtual_sink</key>
<param>
<key>id</key>
- <value>trellis_encoder_xx_0</value>
+ <value>virtual_sink_0_1</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>type</key>
- <value>ss</value>
- </param>
- <param>
- <key>fsm_args</key>
- <value>prefix+"/awgn1o2_16.fsm"</value>
- </param>
- <param>
- <key>init_state</key>
- <value>0</value>
- </param>
- <param>
- <key>alias</key>
- <value></value>
- </param>
- <param>
- <key>affinity</key>
- <value></value>
- </param>
- <param>
- <key>minoutbuf</key>
- <value>0</value>
- </param>
- <param>
- <key>maxoutbuf</key>
- <value>0</value>
+ <key>stream_id</key>
+ <value>observation</value>
</param>
<param>
<key>_coordinate</key>
- <value>(340, 187)</value>
+ <value>(1407, 453)</value>
</param>
<param>
<key>_rotation</key>
@@ -2033,10 +1493,10 @@
</param>
</block>
<block>
- <key>trellis_viterbi_combined_xx</key>
+ <key>wxgui_scopesink2</key>
<param>
<key>id</key>
- <value>trellis_viterbi_combined_xx_1</value>
+ <value>wxgui_scopesink2_0</value>
</param>
<param>
<key>_enabled</key>
@@ -2044,59 +1504,67 @@
</param>
<param>
<key>type</key>
- <value>c</value>
+ <value>complex</value>
</param>
<param>
- <key>out_type</key>
- <value>s</value>
+ <key>title</key>
+ <value>Scope Plot</value>
</param>
<param>
- <key>fsm_args</key>
- <value>prefix+"/awgn1o2_16.fsm"</value>
+ <key>samp_rate</key>
+ <value>R</value>
</param>
<param>
- <key>block_size</key>
- <value>1000</value>
+ <key>v_scale</key>
+ <value>0</value>
</param>
<param>
- <key>init_state</key>
- <value>-1</value>
+ <key>v_offset</key>
+ <value>0</value>
</param>
<param>
- <key>final_state</key>
- <value>-1</value>
+ <key>t_scale</key>
+ <value>0</value>
</param>
<param>
- <key>dim</key>
- <value>1</value>
+ <key>ac_couple</key>
+ <value>False</value>
</param>
<param>
- <key>table</key>
- <value>alpha**0.5*1,alpha**0.5*1j,alpha**0.5*(-1j),alpha**0.5*(-1)</value>
+ <key>xy_mode</key>
+ <value>True</value>
</param>
<param>
- <key>metric_type</key>
- <value>digital.TRELLIS_EUCLIDEAN</value>
+ <key>num_inputs</key>
+ <value>1</value>
</param>
<param>
- <key>alias</key>
+ <key>win_size</key>
<value></value>
</param>
<param>
- <key>affinity</key>
+ <key>grid_pos</key>
<value></value>
</param>
<param>
- <key>minoutbuf</key>
- <value>0</value>
+ <key>notebook</key>
+ <value></value>
</param>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
+ <key>trig_mode</key>
+ <value>wxgui.TRIG_MODE_AUTO</value>
+ </param>
+ <param>
+ <key>y_axis_label</key>
+ <value>Counts</value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
</param>
<param>
<key>_coordinate</key>
- <value>(79, 501)</value>
+ <value>(1383, 208)</value>
</param>
<param>
<key>_rotation</key>
@@ -2107,7 +1575,7 @@
<key>trellis_viterbi_combined_xx</key>
<param>
<key>id</key>
- <value>trellis_viterbi_combined_xx_2</value>
+ <value>trellis_viterbi_combined_xx_1</value>
</param>
<param>
<key>_enabled</key>
@@ -2119,15 +1587,15 @@
</param>
<param>
<key>out_type</key>
- <value>s</value>
+ <value>b</value>
</param>
<param>
<key>fsm_args</key>
- <value>prefix+"/awgn1o2_16.fsm"</value>
+ <value>prefix+fsm1</value>
</param>
<param>
<key>block_size</key>
- <value>1000</value>
+ <value>block</value>
</param>
<param>
<key>init_state</key>
@@ -2143,17 +1611,13 @@
</param>
<param>
<key>table</key>
- <value>(1-alpha)**0.5*1,(1-alpha)**0.5*1j,(1-alpha)**0.5*(-1j),(1-alpha)**0.5*(-1)</value>
+ <value>alpha**0.5*1,alpha**0.5*1j,alpha**0.5*(-1j),alpha**0.5*(-1)</value>
</param>
<param>
<key>metric_type</key>
<value>digital.TRELLIS_EUCLIDEAN</value>
</param>
<param>
- <key>alias</key>
- <value></value>
- </param>
- <param>
<key>affinity</key>
<value></value>
</param>
@@ -2162,12 +1626,8 @@
<value>0</value>
</param>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
- </param>
- <param>
<key>_coordinate</key>
- <value>(82, 766)</value>
+ <value>(75, 583)</value>
</param>
<param>
<key>_rotation</key>
@@ -2178,7 +1638,7 @@
<key>trellis_viterbi_combined_xx</key>
<param>
<key>id</key>
- <value>trellis_viterbi_combined_xx_0</value>
+ <value>trellis_viterbi_combined_xx_0_0</value>
</param>
<param>
<key>_enabled</key>
@@ -2190,15 +1650,15 @@
</param>
<param>
<key>out_type</key>
- <value>s</value>
+ <value>b</value>
</param>
<param>
<key>fsm_args</key>
- <value>prefix+"/awgn1o2_16.fsm"</value>
+ <value>prefix+fsm1</value>
</param>
<param>
<key>block_size</key>
- <value>1000</value>
+ <value>block</value>
</param>
<param>
<key>init_state</key>
@@ -2214,17 +1674,13 @@
</param>
<param>
<key>table</key>
- <value>(1-alpha)**0.5*1,(1-alpha)**0.5*1j,(1-alpha)**0.5*(-1j),(1-alpha)**0.5*(-1)</value>
+ <value>alpha**0.5*1,alpha**0.5*1j,alpha**0.5*(-1j),alpha**0.5*(-1)</value>
</param>
<param>
<key>metric_type</key>
<value>digital.TRELLIS_EUCLIDEAN</value>
</param>
<param>
- <key>alias</key>
- <value></value>
- </param>
- <param>
<key>affinity</key>
<value></value>
</param>
@@ -2233,12 +1689,8 @@
<value>0</value>
</param>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
- </param>
- <param>
<key>_coordinate</key>
- <value>(83, 1111)</value>
+ <value>(63, 1848)</value>
</param>
<param>
<key>_rotation</key>
@@ -2246,10 +1698,10 @@
</param>
</block>
<block>
- <key>trellis_viterbi_combined_xx</key>
+ <key>trellis_encoder_xx</key>
<param>
<key>id</key>
- <value>trellis_viterbi_combined_xx_0_0</value>
+ <value>trellis_encoder_xx_0</value>
</param>
<param>
<key>_enabled</key>
@@ -2257,43 +1709,15 @@
</param>
<param>
<key>type</key>
- <value>c</value>
- </param>
- <param>
- <key>out_type</key>
- <value>s</value>
+ <value>bb</value>
</param>
<param>
<key>fsm_args</key>
- <value>prefix+"/awgn1o2_16.fsm"</value>
- </param>
- <param>
- <key>block_size</key>
- <value>1000</value>
+ <value>prefix+fsm1</value>
</param>
<param>
<key>init_state</key>
- <value>-1</value>
- </param>
- <param>
- <key>final_state</key>
- <value>-1</value>
- </param>
- <param>
- <key>dim</key>
- <value>1</value>
- </param>
- <param>
- <key>table</key>
- <value>alpha**0.5*1,alpha**0.5*1j,alpha**0.5*(-1j),alpha**0.5*(-1)</value>
- </param>
- <param>
- <key>metric_type</key>
- <value>digital.TRELLIS_EUCLIDEAN</value>
- </param>
- <param>
- <key>alias</key>
- <value></value>
+ <value>0</value>
</param>
<param>
<key>affinity</key>
@@ -2304,12 +1728,8 @@
<value>0</value>
</param>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
- </param>
- <param>
<key>_coordinate</key>
- <value>(75, 1495)</value>
+ <value>(337, 270)</value>
</param>
<param>
<key>_rotation</key>
@@ -2317,10 +1737,10 @@
</param>
</block>
<block>
- <key>blocks_multiply_xx</key>
+ <key>trellis_encoder_xx</key>
<param>
<key>id</key>
- <value>blocks_multiply_xx_2_0</value>
+ <value>trellis_encoder_xx_2</value>
</param>
<param>
<key>_enabled</key>
@@ -2328,19 +1748,15 @@
</param>
<param>
<key>type</key>
- <value>short</value>
- </param>
- <param>
- <key>num_inputs</key>
- <value>2</value>
+ <value>bb</value>
</param>
<param>
- <key>vlen</key>
- <value>1</value>
+ <key>fsm_args</key>
+ <value>prefix+fsm1</value>
</param>
<param>
- <key>alias</key>
- <value></value>
+ <key>init_state</key>
+ <value>0</value>
</param>
<param>
<key>affinity</key>
@@ -2351,12 +1767,8 @@
<value>0</value>
</param>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
- </param>
- <param>
<key>_coordinate</key>
- <value>(771, 1530)</value>
+ <value>(87, 1251)</value>
</param>
<param>
<key>_rotation</key>
@@ -2364,26 +1776,26 @@
</param>
</block>
<block>
- <key>blocks_short_to_float</key>
+ <key>trellis_encoder_xx</key>
<param>
<key>id</key>
- <value>blocks_short_to_float_1</value>
+ <value>trellis_encoder_xx_1</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>vlen</key>
- <value>1</value>
+ <key>type</key>
+ <value>bb</value>
</param>
<param>
- <key>scale</key>
- <value>1</value>
+ <key>fsm_args</key>
+ <value>prefix+fsm2</value>
</param>
<param>
- <key>alias</key>
- <value></value>
+ <key>init_state</key>
+ <value>0</value>
</param>
<param>
<key>affinity</key>
@@ -2394,12 +1806,8 @@
<value>0</value>
</param>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
- </param>
- <param>
<key>_coordinate</key>
- <value>(985, 1608)</value>
+ <value>(376, 381)</value>
</param>
<param>
<key>_rotation</key>
@@ -2407,226 +1815,62 @@
</param>
</block>
<block>
- <key>qtgui_number_sink</key>
+ <key>trellis_viterbi_combined_xx</key>
<param>
<key>id</key>
- <value>qtgui_number_sink_0_0_0_0</value>
+ <value>trellis_viterbi_combined_xx_2</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>name</key>
- <value>""</value>
- </param>
- <param>
<key>type</key>
- <value>float</value>
- </param>
- <param>
- <key>autoscale</key>
- <value>False</value>
+ <value>c</value>
</param>
<param>
- <key>avg</key>
- <value>0.001</value>
+ <key>out_type</key>
+ <value>b</value>
</param>
<param>
- <key>graph_type</key>
- <value>qtgui.NUM_GRAPH_HORIZ</value>
+ <key>fsm_args</key>
+ <value>prefix+fsm2</value>
</param>
<param>
- <key>nconnections</key>
- <value>1</value>
+ <key>block_size</key>
+ <value>block</value>
</param>
<param>
- <key>min</key>
+ <key>init_state</key>
<value>-1</value>
</param>
<param>
- <key>max</key>
- <value>1</value>
- </param>
- <param>
- <key>update_time</key>
- <value>0.10</value>
- </param>
- <param>
- <key>gui_hint</key>
- <value>1,0,1,1</value>
- </param>
- <param>
- <key>label1</key>
- <value>BER 2 (raw)</value>
- </param>
- <param>
- <key>unit1</key>
- <value></value>
- </param>
- <param>
- <key>color1</key>
- <value>("black", "black")</value>
- </param>
- <param>
- <key>factor1</key>
- <value>1</value>
- </param>
- <param>
- <key>label2</key>
- <value></value>
- </param>
- <param>
- <key>unit2</key>
- <value></value>
- </param>
- <param>
- <key>color2</key>
- <value>("black", "black")</value>
- </param>
- <param>
- <key>factor2</key>
- <value>1</value>
- </param>
- <param>
- <key>label3</key>
- <value></value>
- </param>
- <param>
- <key>unit3</key>
- <value></value>
- </param>
- <param>
- <key>color3</key>
- <value>("black", "black")</value>
- </param>
- <param>
- <key>factor3</key>
- <value>1</value>
- </param>
- <param>
- <key>label4</key>
- <value></value>
- </param>
- <param>
- <key>unit4</key>
- <value></value>
- </param>
- <param>
- <key>color4</key>
- <value>("black", "black")</value>
- </param>
- <param>
- <key>factor4</key>
- <value>1</value>
- </param>
- <param>
- <key>label5</key>
- <value></value>
- </param>
- <param>
- <key>unit5</key>
- <value></value>
- </param>
- <param>
- <key>color5</key>
- <value>("black", "black")</value>
- </param>
- <param>
- <key>factor5</key>
- <value>1</value>
- </param>
- <param>
- <key>label6</key>
- <value></value>
- </param>
- <param>
- <key>unit6</key>
- <value></value>
- </param>
- <param>
- <key>color6</key>
- <value>("black", "black")</value>
- </param>
- <param>
- <key>factor6</key>
- <value>1</value>
- </param>
- <param>
- <key>label7</key>
- <value></value>
- </param>
- <param>
- <key>unit7</key>
- <value></value>
- </param>
- <param>
- <key>color7</key>
- <value>("black", "black")</value>
- </param>
- <param>
- <key>factor7</key>
- <value>1</value>
- </param>
- <param>
- <key>label8</key>
- <value></value>
- </param>
- <param>
- <key>unit8</key>
- <value></value>
- </param>
- <param>
- <key>color8</key>
- <value>("black", "black")</value>
- </param>
- <param>
- <key>factor8</key>
- <value>1</value>
- </param>
- <param>
- <key>label9</key>
- <value></value>
- </param>
- <param>
- <key>unit9</key>
- <value></value>
- </param>
- <param>
- <key>color9</key>
- <value>("black", "black")</value>
+ <key>final_state</key>
+ <value>-1</value>
</param>
<param>
- <key>factor9</key>
+ <key>dim</key>
<value>1</value>
</param>
<param>
- <key>label10</key>
- <value></value>
- </param>
- <param>
- <key>unit10</key>
- <value></value>
- </param>
- <param>
- <key>color10</key>
- <value>("black", "black")</value>
+ <key>table</key>
+ <value>(1-alpha)**0.5*1,(1-alpha)**0.5*1j,(1-alpha)**0.5*(-1j),(1-alpha)**0.5*(-1)</value>
</param>
<param>
- <key>factor10</key>
- <value>1</value>
+ <key>metric_type</key>
+ <value>digital.TRELLIS_EUCLIDEAN</value>
</param>
<param>
- <key>alias</key>
+ <key>affinity</key>
<value></value>
</param>
<param>
- <key>affinity</key>
- <value></value>
+ <key>minoutbuf</key>
+ <value>0</value>
</param>
<param>
<key>_coordinate</key>
- <value>(1272, 1551)</value>
+ <value>(85, 931)</value>
</param>
<param>
<key>_rotation</key>
@@ -2634,10 +1878,10 @@
</param>
</block>
<block>
- <key>blocks_multiply_xx</key>
+ <key>trellis_viterbi_combined_xx</key>
<param>
<key>id</key>
- <value>blocks_multiply_xx_1</value>
+ <value>trellis_viterbi_combined_xx_0</value>
</param>
<param>
<key>_enabled</key>
@@ -2645,62 +1889,39 @@
</param>
<param>
<key>type</key>
- <value>short</value>
- </param>
- <param>
- <key>num_inputs</key>
- <value>2</value>
- </param>
- <param>
- <key>vlen</key>
- <value>1</value>
- </param>
- <param>
- <key>alias</key>
- <value></value>
- </param>
- <param>
- <key>affinity</key>
- <value></value>
- </param>
- <param>
- <key>minoutbuf</key>
- <value>0</value>
+ <value>c</value>
</param>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
+ <key>out_type</key>
+ <value>b</value>
</param>
<param>
- <key>_coordinate</key>
- <value>(785, 779)</value>
+ <key>fsm_args</key>
+ <value>prefix+fsm2</value>
</param>
<param>
- <key>_rotation</key>
- <value>0</value>
+ <key>block_size</key>
+ <value>block</value>
</param>
- </block>
- <block>
- <key>blocks_short_to_float</key>
<param>
- <key>id</key>
- <value>blocks_short_to_float_2</value>
+ <key>init_state</key>
+ <value>-1</value>
</param>
<param>
- <key>_enabled</key>
- <value>True</value>
+ <key>final_state</key>
+ <value>-1</value>
</param>
<param>
- <key>vlen</key>
+ <key>dim</key>
<value>1</value>
</param>
<param>
- <key>scale</key>
- <value>1</value>
+ <key>table</key>
+ <value>(1-alpha)**0.5*1,(1-alpha)**0.5*1j,(1-alpha)**0.5*(-1j),(1-alpha)**0.5*(-1)</value>
</param>
<param>
- <key>alias</key>
- <value></value>
+ <key>metric_type</key>
+ <value>digital.TRELLIS_EUCLIDEAN</value>
</param>
<param>
<key>affinity</key>
@@ -2711,12 +1932,8 @@
<value>0</value>
</param>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
- </param>
- <param>
<key>_coordinate</key>
- <value>(1013, 735)</value>
+ <value>(81, 1362)</value>
</param>
<param>
<key>_rotation</key>
@@ -2724,10 +1941,10 @@
</param>
</block>
<block>
- <key>blocks_multiply_xx</key>
+ <key>trellis_encoder_xx</key>
<param>
<key>id</key>
- <value>blocks_multiply_xx_2</value>
+ <value>trellis_encoder_xx_2_0</value>
</param>
<param>
<key>_enabled</key>
@@ -2735,63 +1952,16 @@
</param>
<param>
<key>type</key>
- <value>short</value>
- </param>
- <param>
- <key>num_inputs</key>
- <value>2</value>
- </param>
- <param>
- <key>vlen</key>
- <value>1</value>
- </param>
- <param>
- <key>alias</key>
- <value></value>
- </param>
- <param>
- <key>affinity</key>
- <value></value>
- </param>
- <param>
- <key>minoutbuf</key>
- <value>0</value>
- </param>
- <param>
- <key>maxoutbuf</key>
- <value>0</value>
+ <value>bb</value>
</param>
<param>
- <key>_coordinate</key>
- <value>(796, 1136)</value>
+ <key>fsm_args</key>
+ <value>prefix+fsm2</value>
</param>
<param>
- <key>_rotation</key>
+ <key>init_state</key>
<value>0</value>
</param>
- </block>
- <block>
- <key>blocks_short_to_float</key>
- <param>
- <key>id</key>
- <value>blocks_short_to_float_3</value>
- </param>
- <param>
- <key>_enabled</key>
- <value>True</value>
- </param>
- <param>
- <key>vlen</key>
- <value>1</value>
- </param>
- <param>
- <key>scale</key>
- <value>1</value>
- </param>
- <param>
- <key>alias</key>
- <value></value>
- </param>
<param>
<key>affinity</key>
<value></value>
@@ -2801,12 +1971,8 @@
<value>0</value>
</param>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
- </param>
- <param>
<key>_coordinate</key>
- <value>(1002, 1149)</value>
+ <value>(91, 1719)</value>
</param>
<param>
<key>_rotation</key>
@@ -2814,226 +1980,200 @@
</param>
</block>
<block>
- <key>qtgui_number_sink</key>
+ <key>wxgui_numbersink2</key>
<param>
<key>id</key>
- <value>qtgui_number_sink_0_0</value>
+ <value>wxgui_numbersink2_3_0</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>name</key>
- <value>""</value>
- </param>
- <param>
<key>type</key>
<value>float</value>
</param>
<param>
- <key>autoscale</key>
- <value>False</value>
- </param>
- <param>
- <key>avg</key>
- <value>0.001</value>
- </param>
- <param>
- <key>graph_type</key>
- <value>qtgui.NUM_GRAPH_HORIZ</value>
- </param>
- <param>
- <key>nconnections</key>
- <value>1</value>
- </param>
- <param>
- <key>min</key>
- <value>-1</value>
+ <key>title</key>
+ <value>BER 1 (after cancelling user 2)</value>
</param>
<param>
- <key>max</key>
- <value>1</value>
+ <key>units</key>
+ <value>BER</value>
</param>
<param>
- <key>update_time</key>
- <value>0.10</value>
+ <key>samp_rate</key>
+ <value>R</value>
</param>
<param>
- <key>gui_hint</key>
- <value>0,1,1,1</value>
+ <key>min_value</key>
+ <value>0</value>
</param>
<param>
- <key>label1</key>
- <value>BER 2 (raw)</value>
+ <key>max_value</key>
+ <value>1.0</value>
</param>
<param>
- <key>unit1</key>
- <value></value>
+ <key>factor</key>
+ <value>1.0</value>
</param>
<param>
- <key>color1</key>
- <value>("black", "black")</value>
+ <key>decimal_places</key>
+ <value>6</value>
</param>
<param>
- <key>factor1</key>
- <value>1</value>
+ <key>ref_level</key>
+ <value>0</value>
</param>
<param>
- <key>label2</key>
- <value></value>
+ <key>number_rate</key>
+ <value>15</value>
</param>
<param>
- <key>unit2</key>
- <value></value>
+ <key>peak_hold</key>
+ <value>False</value>
</param>
<param>
- <key>color2</key>
- <value>("black", "black")</value>
+ <key>average</key>
+ <value>False</value>
</param>
<param>
- <key>factor2</key>
- <value>1</value>
+ <key>avg_alpha</key>
+ <value>0.001</value>
</param>
<param>
- <key>label3</key>
- <value></value>
+ <key>show_gauge</key>
+ <value>True</value>
</param>
<param>
- <key>unit3</key>
+ <key>win_size</key>
<value></value>
</param>
<param>
- <key>color3</key>
- <value>("black", "black")</value>
- </param>
- <param>
- <key>factor3</key>
- <value>1</value>
+ <key>grid_pos</key>
+ <value>1,0,1,1</value>
</param>
<param>
- <key>label4</key>
+ <key>notebook</key>
<value></value>
</param>
<param>
- <key>unit4</key>
+ <key>affinity</key>
<value></value>
</param>
<param>
- <key>color4</key>
- <value>("black", "black")</value>
+ <key>_coordinate</key>
+ <value>(929, 1816)</value>
</param>
<param>
- <key>factor4</key>
- <value>1</value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>variable_slider</key>
<param>
- <key>label5</key>
- <value></value>
+ <key>id</key>
+ <value>alpha</value>
</param>
<param>
- <key>unit5</key>
- <value></value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>color5</key>
- <value>("black", "black")</value>
+ <key>label</key>
+ <value>P1/P</value>
</param>
<param>
- <key>factor5</key>
- <value>1</value>
+ <key>value</key>
+ <value>0.1</value>
</param>
<param>
- <key>label6</key>
- <value></value>
+ <key>min</key>
+ <value>0</value>
</param>
<param>
- <key>unit6</key>
- <value></value>
+ <key>max</key>
+ <value>1.0</value>
</param>
<param>
- <key>color6</key>
- <value>("black", "black")</value>
+ <key>num_steps</key>
+ <value>100</value>
</param>
<param>
- <key>factor6</key>
- <value>1</value>
+ <key>style</key>
+ <value>wx.SL_HORIZONTAL</value>
</param>
<param>
- <key>label7</key>
- <value></value>
+ <key>converver</key>
+ <value>float_converter</value>
</param>
<param>
- <key>unit7</key>
+ <key>grid_pos</key>
<value></value>
</param>
<param>
- <key>color7</key>
- <value>("black", "black")</value>
- </param>
- <param>
- <key>factor7</key>
- <value>1</value>
- </param>
- <param>
- <key>label8</key>
+ <key>notebook</key>
<value></value>
</param>
<param>
- <key>unit8</key>
- <value></value>
+ <key>_coordinate</key>
+ <value>(243, 11)</value>
</param>
<param>
- <key>color8</key>
- <value>("black", "black")</value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>variable_slider</key>
<param>
- <key>factor8</key>
- <value>1</value>
+ <key>id</key>
+ <value>snr_db</value>
</param>
<param>
- <key>label9</key>
- <value></value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>unit9</key>
- <value></value>
+ <key>label</key>
+ <value>P/sigma^2 (dB)</value>
</param>
<param>
- <key>color9</key>
- <value>("black", "black")</value>
+ <key>value</key>
+ <value>10</value>
</param>
<param>
- <key>factor9</key>
- <value>1</value>
+ <key>min</key>
+ <value>0</value>
</param>
<param>
- <key>label10</key>
- <value></value>
+ <key>max</key>
+ <value>20</value>
</param>
<param>
- <key>unit10</key>
- <value></value>
+ <key>num_steps</key>
+ <value>100</value>
</param>
<param>
- <key>color10</key>
- <value>("black", "black")</value>
+ <key>style</key>
+ <value>wx.SL_HORIZONTAL</value>
</param>
<param>
- <key>factor10</key>
- <value>1</value>
+ <key>converver</key>
+ <value>float_converter</value>
</param>
<param>
- <key>alias</key>
+ <key>grid_pos</key>
<value></value>
</param>
<param>
- <key>affinity</key>
+ <key>notebook</key>
<value></value>
</param>
<param>
<key>_coordinate</key>
- <value>(1223, 1133)</value>
+ <value>(447, 14)</value>
</param>
<param>
<key>_rotation</key>
@@ -3041,10 +2181,10 @@
</param>
</block>
<block>
- <key>trellis_encoder_xx</key>
+ <key>blks2_error_rate</key>
<param>
<key>id</key>
- <value>trellis_encoder_xx_2_0</value>
+ <value>blks2_error_rate_0</value>
</param>
<param>
<key>_enabled</key>
@@ -3052,19 +2192,15 @@
</param>
<param>
<key>type</key>
- <value>ss</value>
+ <value>'BER'</value>
</param>
<param>
- <key>fsm_args</key>
- <value>prefix+"/awgn1o2_16.fsm"</value>
+ <key>win_size</key>
+ <value>block*100</value>
</param>
<param>
- <key>init_state</key>
- <value>0</value>
- </param>
- <param>
- <key>alias</key>
- <value></value>
+ <key>bits_per_symbol</key>
+ <value>2</value>
</param>
<param>
<key>affinity</key>
@@ -3075,12 +2211,8 @@
<value>0</value>
</param>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
- </param>
- <param>
<key>_coordinate</key>
- <value>(103, 1366)</value>
+ <value>(724, 613)</value>
</param>
<param>
<key>_rotation</key>
@@ -3088,10 +2220,10 @@
</param>
</block>
<block>
- <key>trellis_encoder_xx</key>
+ <key>blks2_error_rate</key>
<param>
<key>id</key>
- <value>trellis_encoder_xx_2</value>
+ <value>blks2_error_rate_0_0</value>
</param>
<param>
<key>_enabled</key>
@@ -3099,19 +2231,15 @@
</param>
<param>
<key>type</key>
- <value>ss</value>
+ <value>'BER'</value>
</param>
<param>
- <key>fsm_args</key>
- <value>prefix+"/awgn1o2_16.fsm"</value>
- </param>
- <param>
- <key>init_state</key>
- <value>0</value>
+ <key>win_size</key>
+ <value>block*100</value>
</param>
<param>
- <key>alias</key>
- <value></value>
+ <key>bits_per_symbol</key>
+ <value>2</value>
</param>
<param>
<key>affinity</key>
@@ -3122,12 +2250,8 @@
<value>0</value>
</param>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
- </param>
- <param>
<key>_coordinate</key>
- <value>(89, 1000)</value>
+ <value>(719, 943)</value>
</param>
<param>
<key>_rotation</key>
@@ -3135,226 +2259,77 @@
</param>
</block>
<block>
- <key>qtgui_number_sink</key>
+ <key>blks2_error_rate</key>
<param>
<key>id</key>
- <value>qtgui_number_sink_0_0_0</value>
+ <value>blks2_error_rate_0_0_0</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>name</key>
- <value>""</value>
- </param>
- <param>
<key>type</key>
- <value>float</value>
- </param>
- <param>
- <key>autoscale</key>
- <value>False</value>
- </param>
- <param>
- <key>avg</key>
- <value>0.001</value>
- </param>
- <param>
- <key>graph_type</key>
- <value>qtgui.NUM_GRAPH_HORIZ</value>
- </param>
- <param>
- <key>nconnections</key>
- <value>1</value>
- </param>
- <param>
- <key>min</key>
- <value>-1</value>
- </param>
- <param>
- <key>max</key>
- <value>1</value>
- </param>
- <param>
- <key>update_time</key>
- <value>0.10</value>
- </param>
- <param>
- <key>gui_hint</key>
- <value>1,1,1,1</value>
- </param>
- <param>
- <key>label1</key>
- <value></value>
- </param>
- <param>
- <key>unit1</key>
- <value></value>
- </param>
- <param>
- <key>color1</key>
- <value>("black", "black")</value>
- </param>
- <param>
- <key>factor1</key>
- <value>1</value>
- </param>
- <param>
- <key>label2</key>
- <value></value>
- </param>
- <param>
- <key>unit2</key>
- <value></value>
- </param>
- <param>
- <key>color2</key>
- <value>("black", "black")</value>
- </param>
- <param>
- <key>factor2</key>
- <value>1</value>
- </param>
- <param>
- <key>label3</key>
- <value></value>
- </param>
- <param>
- <key>unit3</key>
- <value></value>
- </param>
- <param>
- <key>color3</key>
- <value>("black", "black")</value>
- </param>
- <param>
- <key>factor3</key>
- <value>1</value>
- </param>
- <param>
- <key>label4</key>
- <value></value>
- </param>
- <param>
- <key>unit4</key>
- <value></value>
- </param>
- <param>
- <key>color4</key>
- <value>("black", "black")</value>
+ <value>'BER'</value>
</param>
<param>
- <key>factor4</key>
- <value>1</value>
- </param>
- <param>
- <key>label5</key>
- <value></value>
- </param>
- <param>
- <key>unit5</key>
- <value></value>
- </param>
- <param>
- <key>color5</key>
- <value>("black", "black")</value>
- </param>
- <param>
- <key>factor5</key>
- <value>1</value>
- </param>
- <param>
- <key>label6</key>
- <value></value>
- </param>
- <param>
- <key>unit6</key>
- <value></value>
- </param>
- <param>
- <key>color6</key>
- <value>("black", "black")</value>
- </param>
- <param>
- <key>factor6</key>
- <value>1</value>
- </param>
- <param>
- <key>label7</key>
- <value></value>
- </param>
- <param>
- <key>unit7</key>
- <value></value>
- </param>
- <param>
- <key>color7</key>
- <value>("black", "black")</value>
- </param>
- <param>
- <key>factor7</key>
- <value>1</value>
+ <key>win_size</key>
+ <value>block*100</value>
</param>
<param>
- <key>label8</key>
- <value></value>
+ <key>bits_per_symbol</key>
+ <value>2</value>
</param>
<param>
- <key>unit8</key>
+ <key>affinity</key>
<value></value>
</param>
<param>
- <key>color8</key>
- <value>("black", "black")</value>
- </param>
- <param>
- <key>factor8</key>
- <value>1</value>
- </param>
- <param>
- <key>label9</key>
- <value></value>
+ <key>minoutbuf</key>
+ <value>0</value>
</param>
<param>
- <key>unit9</key>
- <value></value>
+ <key>_coordinate</key>
+ <value>(725, 1399)</value>
</param>
<param>
- <key>color9</key>
- <value>("black", "black")</value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>blks2_error_rate</key>
<param>
- <key>factor9</key>
- <value>1</value>
+ <key>id</key>
+ <value>blks2_error_rate_0_0_0_0</value>
</param>
<param>
- <key>label10</key>
- <value></value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>unit10</key>
- <value></value>
+ <key>type</key>
+ <value>'BER'</value>
</param>
<param>
- <key>color10</key>
- <value>("black", "black")</value>
+ <key>win_size</key>
+ <value>block*100</value>
</param>
<param>
- <key>factor10</key>
- <value>1</value>
+ <key>bits_per_symbol</key>
+ <value>2</value>
</param>
<param>
- <key>alias</key>
+ <key>affinity</key>
<value></value>
</param>
<param>
- <key>affinity</key>
- <value></value>
+ <key>minoutbuf</key>
+ <value>0</value>
</param>
<param>
<key>_coordinate</key>
- <value>(1266, 720)</value>
+ <value>(724, 1880)</value>
</param>
<param>
<key>_rotation</key>
@@ -3362,218 +2337,194 @@
</param>
</block>
<connection>
- <source_block_id>analog_random_source_x_1</source_block_id>
- <sink_block_id>trellis_encoder_xx_1</sink_block_id>
- <source_key>0</source_key>
- <sink_key>0</sink_key>
- </connection>
- <connection>
- <source_block_id>blocks_multiply_const_vxx_0</source_block_id>
- <sink_block_id>blocks_add_xx_0</sink_block_id>
+ <source_block_id>blocks_add_xx_1</source_block_id>
+ <sink_block_id>wxgui_scopesink2_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_add_xx_0</source_block_id>
- <sink_block_id>blocks_add_xx_1</sink_block_id>
+ <source_block_id>blocks_add_xx_1</source_block_id>
+ <sink_block_id>virtual_sink_0_1</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_multiply_const_vxx_1</source_block_id>
- <sink_block_id>blocks_add_xx_0</sink_block_id>
+ <source_block_id>trellis_viterbi_combined_xx_0_0</source_block_id>
+ <sink_block_id>blks2_error_rate_0_0_0_0</sink_block_id>
<source_key>0</source_key>
<sink_key>1</sink_key>
</connection>
<connection>
- <source_block_id>blocks_sub_xx_0</source_block_id>
- <sink_block_id>blocks_multiply_xx_0</sink_block_id>
+ <source_block_id>virtual_source_0_0</source_block_id>
+ <sink_block_id>blks2_error_rate_0_0_0_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_sub_xx_0</source_block_id>
- <sink_block_id>blocks_multiply_xx_0</sink_block_id>
+ <source_block_id>blks2_error_rate_0_0_0_0</source_block_id>
+ <sink_block_id>wxgui_numbersink2_3_0</sink_block_id>
<source_key>0</source_key>
- <sink_key>1</sink_key>
+ <sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_multiply_xx_0</source_block_id>
- <sink_block_id>blocks_short_to_float_0</sink_block_id>
+ <source_block_id>virtual_source_0_2_0</source_block_id>
+ <sink_block_id>trellis_encoder_xx_2_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>analog_random_source_x_0</source_block_id>
- <sink_block_id>trellis_encoder_xx_0</sink_block_id>
+ <source_block_id>virtual_source_0_1_2</source_block_id>
+ <sink_block_id>blocks_sub_xx_2_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_add_xx_1</source_block_id>
- <sink_block_id>trellis_viterbi_combined_xx_1</sink_block_id>
+ <source_block_id>digital_chunks_to_symbols_xx_0_0_1</source_block_id>
+ <sink_block_id>blocks_multiply_const_vxx_2_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>analog_random_source_x_0</source_block_id>
- <sink_block_id>blocks_sub_xx_0</sink_block_id>
+ <source_block_id>trellis_encoder_xx_2_0</source_block_id>
+ <sink_block_id>digital_chunks_to_symbols_xx_0_0_1</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>trellis_viterbi_combined_xx_1</source_block_id>
- <sink_block_id>blocks_sub_xx_0</sink_block_id>
+ <source_block_id>blocks_multiply_const_vxx_2_0</source_block_id>
+ <sink_block_id>blocks_sub_xx_2_0</sink_block_id>
<source_key>0</source_key>
<sink_key>1</sink_key>
</connection>
<connection>
- <source_block_id>trellis_viterbi_combined_xx_0</source_block_id>
- <sink_block_id>blocks_sub_xx_1</sink_block_id>
+ <source_block_id>blocks_sub_xx_2_0</source_block_id>
+ <sink_block_id>trellis_viterbi_combined_xx_0_0</sink_block_id>
<source_key>0</source_key>
- <sink_key>1</sink_key>
+ <sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>analog_random_source_x_1</source_block_id>
- <sink_block_id>blocks_sub_xx_1</sink_block_id>
+ <source_block_id>trellis_viterbi_combined_xx_0</source_block_id>
+ <sink_block_id>blks2_error_rate_0_0_0</sink_block_id>
<source_key>0</source_key>
- <sink_key>0</sink_key>
+ <sink_key>1</sink_key>
</connection>
<connection>
- <source_block_id>blocks_sub_xx_1</source_block_id>
- <sink_block_id>blocks_multiply_xx_2</sink_block_id>
+ <source_block_id>virtual_source_0_4</source_block_id>
+ <sink_block_id>blks2_error_rate_0_0_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_sub_xx_1</source_block_id>
- <sink_block_id>blocks_multiply_xx_2</sink_block_id>
+ <source_block_id>blks2_error_rate_0_0_0</source_block_id>
+ <sink_block_id>wxgui_numbersink2_3</sink_block_id>
<source_key>0</source_key>
- <sink_key>1</sink_key>
+ <sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_sub_xx_2</source_block_id>
- <sink_block_id>trellis_viterbi_combined_xx_0</sink_block_id>
+ <source_block_id>virtual_source_0_2</source_block_id>
+ <sink_block_id>trellis_encoder_xx_2</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_add_xx_1</source_block_id>
+ <source_block_id>virtual_source_0_1_1</source_block_id>
<sink_block_id>blocks_sub_xx_2</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_multiply_const_vxx_2</source_block_id>
- <sink_block_id>blocks_sub_xx_2</sink_block_id>
+ <source_block_id>digital_chunks_to_symbols_xx_0_0_0</source_block_id>
+ <sink_block_id>blocks_multiply_const_vxx_2</sink_block_id>
<source_key>0</source_key>
- <sink_key>1</sink_key>
+ <sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>trellis_viterbi_combined_xx_1</source_block_id>
- <sink_block_id>trellis_encoder_xx_2</sink_block_id>
+ <source_block_id>trellis_encoder_xx_2</source_block_id>
+ <sink_block_id>digital_chunks_to_symbols_xx_0_0_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>trellis_viterbi_combined_xx_2</source_block_id>
- <sink_block_id>blocks_sub_xx_3</sink_block_id>
+ <source_block_id>blocks_multiply_const_vxx_2</source_block_id>
+ <sink_block_id>blocks_sub_xx_2</sink_block_id>
<source_key>0</source_key>
<sink_key>1</sink_key>
</connection>
<connection>
- <source_block_id>blocks_sub_xx_3</source_block_id>
- <sink_block_id>blocks_multiply_xx_1</sink_block_id>
+ <source_block_id>blocks_sub_xx_2</source_block_id>
+ <sink_block_id>trellis_viterbi_combined_xx_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_sub_xx_3</source_block_id>
- <sink_block_id>blocks_multiply_xx_1</sink_block_id>
- <source_key>0</source_key>
- <sink_key>1</sink_key>
- </connection>
- <connection>
- <source_block_id>analog_random_source_x_1</source_block_id>
- <sink_block_id>blocks_sub_xx_3</sink_block_id>
+ <source_block_id>blks2_error_rate_0_0</source_block_id>
+ <sink_block_id>wxgui_numbersink2_2</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>trellis_viterbi_combined_xx_2</source_block_id>
- <sink_block_id>trellis_encoder_xx_2_0</sink_block_id>
+ <source_block_id>virtual_source_0_3</source_block_id>
+ <sink_block_id>blks2_error_rate_0_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>trellis_viterbi_combined_xx_0_0</source_block_id>
- <sink_block_id>blocks_sub_xx_1_0</sink_block_id>
+ <source_block_id>trellis_viterbi_combined_xx_2</source_block_id>
+ <sink_block_id>blks2_error_rate_0_0</sink_block_id>
<source_key>0</source_key>
<sink_key>1</sink_key>
</connection>
<connection>
- <source_block_id>blocks_sub_xx_1_0</source_block_id>
- <sink_block_id>blocks_multiply_xx_2_0</sink_block_id>
+ <source_block_id>trellis_viterbi_combined_xx_2</source_block_id>
+ <sink_block_id>virtual_sink_0_2_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_sub_xx_1_0</source_block_id>
- <sink_block_id>blocks_multiply_xx_2_0</sink_block_id>
- <source_key>0</source_key>
- <sink_key>1</sink_key>
- </connection>
- <connection>
- <source_block_id>blocks_sub_xx_2_0</source_block_id>
- <sink_block_id>trellis_viterbi_combined_xx_0_0</sink_block_id>
+ <source_block_id>virtual_source_0_1_0</source_block_id>
+ <sink_block_id>trellis_viterbi_combined_xx_2</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_add_xx_1</source_block_id>
- <sink_block_id>blocks_sub_xx_2_0</sink_block_id>
+ <source_block_id>blks2_error_rate_0</source_block_id>
+ <sink_block_id>wxgui_numbersink2_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>analog_random_source_x_0</source_block_id>
- <sink_block_id>blocks_sub_xx_1_0</sink_block_id>
+ <source_block_id>virtual_source_0</source_block_id>
+ <sink_block_id>blks2_error_rate_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_multiply_const_vxx_2_0</source_block_id>
- <sink_block_id>blocks_sub_xx_2_0</sink_block_id>
+ <source_block_id>trellis_viterbi_combined_xx_1</source_block_id>
+ <sink_block_id>blks2_error_rate_0</sink_block_id>
<source_key>0</source_key>
<sink_key>1</sink_key>
</connection>
<connection>
- <source_block_id>trellis_encoder_xx_0</source_block_id>
- <sink_block_id>blocks_throttle_0</sink_block_id>
+ <source_block_id>trellis_viterbi_combined_xx_1</source_block_id>
+ <sink_block_id>virtual_sink_0_2</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>analog_noise_source_x_0</source_block_id>
- <sink_block_id>blocks_add_xx_1</sink_block_id>
- <source_key>0</source_key>
- <sink_key>1</sink_key>
- </connection>
- <connection>
- <source_block_id>blocks_throttle_0</source_block_id>
- <sink_block_id>digital_chunks_to_symbols_xx_0</sink_block_id>
+ <source_block_id>virtual_source_0_1</source_block_id>
+ <sink_block_id>trellis_viterbi_combined_xx_1</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>digital_chunks_to_symbols_xx_0</source_block_id>
- <sink_block_id>blocks_multiply_const_vxx_0</sink_block_id>
+ <source_block_id>analog_random_source_x_1</source_block_id>
+ <sink_block_id>virtual_sink_0_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>digital_chunks_to_symbols_xx_0_0</source_block_id>
- <sink_block_id>blocks_multiply_const_vxx_1</sink_block_id>
+ <source_block_id>analog_random_source_x_0</source_block_id>
+ <sink_block_id>virtual_sink_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
@@ -3584,80 +2535,62 @@
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>trellis_encoder_xx_2</source_block_id>
- <sink_block_id>digital_chunks_to_symbols_xx_0_0_0</sink_block_id>
- <source_key>0</source_key>
- <sink_key>0</sink_key>
- </connection>
- <connection>
- <source_block_id>digital_chunks_to_symbols_xx_0_0_0</source_block_id>
- <sink_block_id>blocks_multiply_const_vxx_2</sink_block_id>
- <source_key>0</source_key>
- <sink_key>0</sink_key>
- </connection>
- <connection>
- <source_block_id>trellis_encoder_xx_2_0</source_block_id>
- <sink_block_id>digital_chunks_to_symbols_xx_0_0_1</sink_block_id>
- <source_key>0</source_key>
- <sink_key>0</sink_key>
- </connection>
- <connection>
- <source_block_id>digital_chunks_to_symbols_xx_0_0_1</source_block_id>
- <sink_block_id>blocks_multiply_const_vxx_2_0</sink_block_id>
+ <source_block_id>digital_chunks_to_symbols_xx_0_0</source_block_id>
+ <sink_block_id>blocks_multiply_const_vxx_1</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_add_xx_1</source_block_id>
- <sink_block_id>qtgui_const_sink_x_0</sink_block_id>
+ <source_block_id>digital_chunks_to_symbols_xx_0</source_block_id>
+ <sink_block_id>blocks_multiply_const_vxx_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_add_xx_1</source_block_id>
- <sink_block_id>trellis_viterbi_combined_xx_2</sink_block_id>
+ <source_block_id>blocks_throttle_0</source_block_id>
+ <sink_block_id>digital_chunks_to_symbols_xx_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_short_to_float_0</source_block_id>
- <sink_block_id>qtgui_number_sink_0</sink_block_id>
+ <source_block_id>trellis_encoder_xx_0</source_block_id>
+ <sink_block_id>blocks_throttle_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_multiply_xx_2_0</source_block_id>
- <sink_block_id>blocks_short_to_float_1</sink_block_id>
+ <source_block_id>analog_random_source_x_0</source_block_id>
+ <sink_block_id>trellis_encoder_xx_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_short_to_float_1</source_block_id>
- <sink_block_id>qtgui_number_sink_0_0_0_0</sink_block_id>
+ <source_block_id>analog_random_source_x_1</source_block_id>
+ <sink_block_id>trellis_encoder_xx_1</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_multiply_xx_1</source_block_id>
- <sink_block_id>blocks_short_to_float_2</sink_block_id>
+ <source_block_id>analog_noise_source_x_0</source_block_id>
+ <sink_block_id>blocks_add_xx_1</sink_block_id>
<source_key>0</source_key>
- <sink_key>0</sink_key>
+ <sink_key>1</sink_key>
</connection>
<connection>
- <source_block_id>blocks_short_to_float_2</source_block_id>
- <sink_block_id>qtgui_number_sink_0_0_0</sink_block_id>
+ <source_block_id>blocks_multiply_const_vxx_1</source_block_id>
+ <sink_block_id>blocks_add_xx_0</sink_block_id>
<source_key>0</source_key>
- <sink_key>0</sink_key>
+ <sink_key>1</sink_key>
</connection>
<connection>
- <source_block_id>blocks_multiply_xx_2</source_block_id>
- <sink_block_id>blocks_short_to_float_3</sink_block_id>
+ <source_block_id>blocks_add_xx_0</source_block_id>
+ <sink_block_id>blocks_add_xx_1</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_short_to_float_3</source_block_id>
- <sink_block_id>qtgui_number_sink_0_0</sink_block_id>
+ <source_block_id>blocks_multiply_const_vxx_0</source_block_id>
+ <sink_block_id>blocks_add_xx_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
diff --git a/gr-trellis/examples/grc/pccc.grc b/gr-trellis/examples/grc/pccc.grc
index c642a71940..e10c70a614 100644
--- a/gr-trellis/examples/grc/pccc.grc
+++ b/gr-trellis/examples/grc/pccc.grc
@@ -1,6 +1,7 @@
<?xml version='1.0' encoding='ASCII'?>
+<?grc format='1' created='3.7.6'?>
<flow_graph>
- <timestamp>Mon Jul 28 14:02:43 2014</timestamp>
+ <timestamp>Fri Sep 26 12:26:16 2014</timestamp>
<block>
<key>options</key>
<param>
@@ -29,7 +30,7 @@
</param>
<param>
<key>generate_options</key>
- <value>qt_gui</value>
+ <value>wx_gui</value>
</param>
<param>
<key>category</key>
@@ -84,7 +85,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(520, 11)</value>
+ <value>(320, 21)</value>
</param>
<param>
<key>_rotation</key>
@@ -95,7 +96,7 @@
<key>variable</key>
<param>
<key>id</key>
- <value>noisevar</value>
+ <value>R</value>
</param>
<param>
<key>_enabled</key>
@@ -103,7 +104,7 @@
</param>
<param>
<key>value</key>
- <value>10**(-snr_db/10)</value>
+ <value>100e3</value>
</param>
<param>
<key>alias</key>
@@ -111,7 +112,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(279, 10)</value>
+ <value>(200, 101)</value>
</param>
<param>
<key>_rotation</key>
@@ -122,7 +123,7 @@
<key>variable</key>
<param>
<key>id</key>
- <value>R</value>
+ <value>block</value>
</param>
<param>
<key>_enabled</key>
@@ -130,7 +131,7 @@
</param>
<param>
<key>value</key>
- <value>100e3</value>
+ <value>1000</value>
</param>
<param>
<key>alias</key>
@@ -138,7 +139,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(358, 10)</value>
+ <value>(200, 37)</value>
</param>
<param>
<key>_rotation</key>
@@ -149,7 +150,7 @@
<key>variable</key>
<param>
<key>id</key>
- <value>block</value>
+ <value>dim</value>
</param>
<param>
<key>_enabled</key>
@@ -157,7 +158,7 @@
</param>
<param>
<key>value</key>
- <value>1000</value>
+ <value>mod[0]</value>
</param>
<param>
<key>alias</key>
@@ -165,7 +166,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(438, 10)</value>
+ <value>(688, 317)</value>
</param>
<param>
<key>_rotation</key>
@@ -173,54 +174,53 @@
</param>
</block>
<block>
- <key>analog_random_source_x</key>
+ <key>variable</key>
<param>
<key>id</key>
- <value>analog_random_source_x_0</value>
+ <value>constellation</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>type</key>
- <value>short</value>
- </param>
- <param>
- <key>min</key>
- <value>0</value>
+ <key>value</key>
+ <value>mod[1]</value>
</param>
<param>
- <key>max</key>
- <value>2</value>
+ <key>alias</key>
+ <value></value>
</param>
<param>
- <key>num_samps</key>
- <value>1000</value>
+ <key>_coordinate</key>
+ <value>(528, 317)</value>
</param>
<param>
- <key>repeat</key>
- <value>True</value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>variable</key>
<param>
- <key>alias</key>
- <value></value>
+ <key>id</key>
+ <value>dim</value>
</param>
<param>
- <key>affinity</key>
- <value></value>
+ <key>_enabled</key>
+ <value>False</value>
</param>
<param>
- <key>minoutbuf</key>
- <value>0</value>
+ <key>value</key>
+ <value>2</value>
</param>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
+ <key>alias</key>
+ <value></value>
</param>
<param>
<key>_coordinate</key>
- <value>(21, 170)</value>
+ <value>(688, 189)</value>
</param>
<param>
<key>_rotation</key>
@@ -228,50 +228,53 @@
</param>
</block>
<block>
- <key>blocks_throttle</key>
+ <key>variable</key>
<param>
<key>id</key>
- <value>blocks_throttle_0</value>
+ <value>constellation</value>
</param>
<param>
<key>_enabled</key>
- <value>True</value>
+ <value>False</value>
</param>
<param>
- <key>type</key>
- <value>short</value>
+ <key>value</key>
+ <value>-3,-3,-1,-3,1,-3,3,-3, -3,-1,-1,-1,1,-1,3,-1, -3,1,-1,1,1,1,3,1, -3,3,-1,3,1,3,3,3 </value>
</param>
<param>
- <key>samples_per_second</key>
- <value>R</value>
+ <key>alias</key>
+ <value></value>
</param>
<param>
- <key>vlen</key>
- <value>1</value>
+ <key>_coordinate</key>
+ <value>(528, 189)</value>
</param>
<param>
- <key>ignoretag</key>
- <value>True</value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>variable</key>
<param>
- <key>alias</key>
- <value></value>
+ <key>id</key>
+ <value>Es</value>
</param>
<param>
- <key>affinity</key>
- <value></value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>minoutbuf</key>
- <value>0</value>
+ <key>value</key>
+ <value>sum(numpy.square(constellation))/(len(constellation)/(1.0*dim))</value>
</param>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
+ <key>alias</key>
+ <value></value>
</param>
<param>
<key>_coordinate</key>
- <value>(559, 104)</value>
+ <value>(776, 141)</value>
</param>
<param>
<key>_rotation</key>
@@ -279,50 +282,45 @@
</param>
</block>
<block>
- <key>variable_qtgui_range</key>
+ <key>variable</key>
<param>
<key>id</key>
- <value>snr_db</value>
+ <value>noisevar</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>label</key>
- <value>SNR (dB)</value>
- </param>
- <param>
<key>value</key>
- <value>5</value>
- </param>
- <param>
- <key>start</key>
- <value>-10</value>
+ <value>10**(-EsN0_dB/10.0) * Es /2.0</value>
</param>
<param>
- <key>stop</key>
- <value>10</value>
+ <key>alias</key>
+ <value></value>
</param>
<param>
- <key>step</key>
- <value>0.01</value>
+ <key>_coordinate</key>
+ <value>(1032, 149)</value>
</param>
<param>
- <key>widget</key>
- <value>counter_slider</value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>variable</key>
<param>
- <key>orient</key>
- <value>Qt.Horizontal</value>
+ <key>id</key>
+ <value>interleaver</value>
</param>
<param>
- <key>min_len</key>
- <value>200</value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>gui_hint</key>
- <value></value>
+ <key>value</key>
+ <value>trellis.interleaver(block,666)</value>
</param>
<param>
<key>alias</key>
@@ -330,62 +328,61 @@
</param>
<param>
<key>_coordinate</key>
- <value>(177, 10)</value>
+ <value>(320, 213)</value>
</param>
<param>
<key>_rotation</key>
- <value>180</value>
+ <value>0</value>
</param>
</block>
<block>
- <key>digital_chunks_to_symbols_xx</key>
+ <key>variable</key>
<param>
<key>id</key>
- <value>digital_chunks_to_symbols_xx_0</value>
+ <value>fsm1</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>in_type</key>
- <value>short</value>
- </param>
- <param>
- <key>out_type</key>
- <value>complex</value>
+ <key>value</key>
+ <value>trellis.fsm(prefix+"awgn1o2_4rsc.fsm")</value>
</param>
<param>
- <key>symbol_table</key>
- <value>-7,0, -5,0, -3,0, -1,0, 1,0, 3,0, 5,0, 7,0, 0,-7,0, -5,0, -3,0, -1,0, 1,0, 3,0, 5,0, 7,0</value>
+ <key>alias</key>
+ <value></value>
</param>
<param>
- <key>dimension</key>
- <value>2</value>
+ <key>_coordinate</key>
+ <value>(320, 85)</value>
</param>
<param>
- <key>num_ports</key>
- <value>1</value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>variable</key>
<param>
- <key>alias</key>
- <value></value>
+ <key>id</key>
+ <value>fsm2</value>
</param>
<param>
- <key>affinity</key>
- <value></value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>minoutbuf</key>
- <value>0</value>
+ <key>value</key>
+ <value>trellis.fsm(prefix+"awgn1o1_4rsc.fsm")</value>
</param>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
+ <key>alias</key>
+ <value></value>
</param>
<param>
<key>_coordinate</key>
- <value>(559, 180)</value>
+ <value>(320, 149)</value>
</param>
<param>
<key>_rotation</key>
@@ -393,62 +390,72 @@
</param>
</block>
<block>
- <key>trellis_pccc_encoder_xx</key>
+ <key>variable</key>
<param>
<key>id</key>
- <value>trellis_pccc_encoder_xx_0</value>
+ <value>mod</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>type</key>
- <value>ss</value>
+ <key>value</key>
+ <value>fu.psk2x3</value>
</param>
<param>
- <key>o_fsm_args</key>
- <value>prefix + "/awgn1o2_4.fsm"</value>
+ <key>alias</key>
+ <value></value>
</param>
<param>
- <key>o_init_state</key>
+ <key>_coordinate</key>
+ <value>(576, 253)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
<value>0</value>
</param>
+ </block>
+ <block>
+ <key>virtual_source</key>
<param>
- <key>i_fsm_args</key>
- <value>prefix + "/awgn1o2_4.fsm"</value>
+ <key>id</key>
+ <value>virtual_source_0_0</value>
</param>
<param>
- <key>i_init_state</key>
- <value>0</value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>interleaver_args</key>
- <value>trellis.interleaver(block,666)</value>
+ <key>stream_id</key>
+ <value>info</value>
</param>
<param>
- <key>bl</key>
- <value>block</value>
+ <key>_coordinate</key>
+ <value>(104, 1220)</value>
</param>
<param>
- <key>alias</key>
- <value></value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>virtual_source</key>
<param>
- <key>affinity</key>
- <value></value>
+ <key>id</key>
+ <value>virtual_source_0_0_0</value>
</param>
<param>
- <key>minoutbuf</key>
- <value>0</value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
+ <key>stream_id</key>
+ <value>estimate</value>
</param>
<param>
<key>_coordinate</key>
- <value>(234, 154)</value>
+ <value>(88, 1292)</value>
</param>
<param>
<key>_rotation</key>
@@ -456,10 +463,10 @@
</param>
</block>
<block>
- <key>trellis_pccc_decoder_combined_xx</key>
+ <key>wxgui_numbersink2</key>
<param>
<key>id</key>
- <value>trellis_pccc_decoder_combined_xx_0</value>
+ <value>wxgui_numbersink2_3_0_0</value>
</param>
<param>
<key>_enabled</key>
@@ -467,67 +474,71 @@
</param>
<param>
<key>type</key>
- <value>c</value>
+ <value>float</value>
</param>
<param>
- <key>out_type</key>
- <value>s</value>
+ <key>title</key>
+ <value>BER</value>
</param>
<param>
- <key>o_fsm_args</key>
- <value>prefix + "/awgn1o2_4.fsm"</value>
+ <key>units</key>
+ <value>BER</value>
</param>
<param>
- <key>o_init_state</key>
+ <key>samp_rate</key>
+ <value>R</value>
+ </param>
+ <param>
+ <key>min_value</key>
<value>0</value>
</param>
<param>
- <key>o_final_state</key>
- <value>-1</value>
+ <key>max_value</key>
+ <value>1.0</value>
</param>
<param>
- <key>i_fsm_args</key>
- <value>prefix + "/awgn1o2_4.fsm"</value>
+ <key>factor</key>
+ <value>1.0</value>
</param>
<param>
- <key>i_init_state</key>
- <value>0</value>
+ <key>decimal_places</key>
+ <value>6</value>
</param>
<param>
- <key>i_final_state</key>
- <value>-1</value>
+ <key>ref_level</key>
+ <value>0</value>
</param>
<param>
- <key>interleaver</key>
- <value>trellis.interleaver(block,666)</value>
+ <key>number_rate</key>
+ <value>15</value>
</param>
<param>
- <key>block_size</key>
- <value>block</value>
+ <key>peak_hold</key>
+ <value>False</value>
</param>
<param>
- <key>iterations</key>
- <value>10</value>
+ <key>average</key>
+ <value>False</value>
</param>
<param>
- <key>dim</key>
- <value>2</value>
+ <key>avg_alpha</key>
+ <value>0.001</value>
</param>
<param>
- <key>table</key>
- <value>-7,0, -5,0, -3,0, -1,0, 1,0, 3,0, 5,0, 7,0, 0,-7,0, -5,0, -3,0, -1,0, 1,0, 3,0, 5,0, 7,0</value>
+ <key>show_gauge</key>
+ <value>False</value>
</param>
<param>
- <key>metric_type</key>
- <value>digital.TRELLIS_EUCLIDEAN</value>
+ <key>win_size</key>
+ <value></value>
</param>
<param>
- <key>siso_type</key>
- <value>trellis.TRELLIS_MIN_SUM</value>
+ <key>grid_pos</key>
+ <value></value>
</param>
<param>
- <key>scaling</key>
- <value>1.0</value>
+ <key>notebook</key>
+ <value></value>
</param>
<param>
<key>alias</key>
@@ -538,27 +549,19 @@
<value></value>
</param>
<param>
- <key>minoutbuf</key>
- <value>0</value>
- </param>
- <param>
- <key>maxoutbuf</key>
- <value>0</value>
- </param>
- <param>
<key>_coordinate</key>
- <value>(234, 299)</value>
+ <value>(680, 1205)</value>
</param>
<param>
<key>_rotation</key>
- <value>180</value>
+ <value>0</value>
</param>
</block>
<block>
- <key>blocks_multiply_xx</key>
+ <key>blks2_error_rate</key>
<param>
<key>id</key>
- <value>blocks_multiply_xx_2_0</value>
+ <value>blks2_error_rate_0</value>
</param>
<param>
<key>_enabled</key>
@@ -566,14 +569,14 @@
</param>
<param>
<key>type</key>
- <value>short</value>
+ <value>'SER'</value>
</param>
<param>
- <key>num_inputs</key>
- <value>2</value>
+ <key>win_size</key>
+ <value>block*100</value>
</param>
<param>
- <key>vlen</key>
+ <key>bits_per_symbol</key>
<value>1</value>
</param>
<param>
@@ -594,7 +597,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(421, 574)</value>
+ <value>(304, 1256)</value>
</param>
<param>
<key>_rotation</key>
@@ -602,46 +605,68 @@
</param>
</block>
<block>
- <key>blocks_sub_xx</key>
+ <key>virtual_sink</key>
<param>
<key>id</key>
- <value>blocks_sub_xx_0</value>
+ <value>virtual_sink_0_1</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>type</key>
- <value>short</value>
+ <key>stream_id</key>
+ <value>estimate</value>
</param>
<param>
- <key>vlen</key>
- <value>1</value>
+ <key>_coordinate</key>
+ <value>(768, 940)</value>
</param>
<param>
- <key>num_inputs</key>
- <value>2</value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>virtual_source</key>
<param>
- <key>alias</key>
- <value></value>
+ <key>id</key>
+ <value>virtual_source_0</value>
</param>
<param>
- <key>affinity</key>
- <value></value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>minoutbuf</key>
- <value>0</value>
+ <key>stream_id</key>
+ <value>observation</value>
</param>
<param>
- <key>maxoutbuf</key>
+ <key>_coordinate</key>
+ <value>(104, 940)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
<value>0</value>
</param>
+ </block>
+ <block>
+ <key>virtual_sink</key>
+ <param>
+ <key>id</key>
+ <value>virtual_sink_0_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>stream_id</key>
+ <value>info</value>
+ </param>
<param>
<key>_coordinate</key>
- <value>(246, 580)</value>
+ <value>(224, 412)</value>
</param>
<param>
<key>_rotation</key>
@@ -649,22 +674,30 @@
</param>
</block>
<block>
- <key>blocks_short_to_float</key>
+ <key>blocks_throttle</key>
<param>
<key>id</key>
- <value>blocks_short_to_float_1_0</value>
+ <value>blocks_throttle_0_0</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
+ <key>type</key>
+ <value>byte</value>
+ </param>
+ <param>
+ <key>samples_per_second</key>
+ <value>R</value>
+ </param>
+ <param>
<key>vlen</key>
<value>1</value>
</param>
<param>
- <key>scale</key>
- <value>1</value>
+ <key>ignoretag</key>
+ <value>True</value>
</param>
<param>
<key>alias</key>
@@ -684,7 +717,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(564, 592)</value>
+ <value>(208, 492)</value>
</param>
<param>
<key>_rotation</key>
@@ -703,7 +736,7 @@
</param>
<param>
<key>type</key>
- <value>complex</value>
+ <value>float</value>
</param>
<param>
<key>noise_type</key>
@@ -711,7 +744,7 @@
</param>
<param>
<key>amp</key>
- <value>noisevar</value>
+ <value>noisevar**0.5</value>
</param>
<param>
<key>seed</key>
@@ -735,7 +768,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(520, 309)</value>
+ <value>(656, 646)</value>
</param>
<param>
<key>_rotation</key>
@@ -754,7 +787,7 @@
</param>
<param>
<key>type</key>
- <value>complex</value>
+ <value>float</value>
</param>
<param>
<key>num_inputs</key>
@@ -782,7 +815,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(816, 192)</value>
+ <value>(880, 552)</value>
</param>
<param>
<key>_rotation</key>
@@ -790,214 +823,360 @@
</param>
</block>
<block>
- <key>qtgui_number_sink</key>
+ <key>virtual_sink</key>
<param>
<key>id</key>
- <value>qtgui_number_sink_0</value>
+ <value>virtual_sink_0</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>name</key>
- <value>""</value>
+ <key>stream_id</key>
+ <value>observation</value>
</param>
<param>
- <key>type</key>
- <value>float</value>
+ <key>_coordinate</key>
+ <value>(896, 676)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>import</key>
+ <param>
+ <key>id</key>
+ <value>import_0_0</value>
</param>
<param>
- <key>autoscale</key>
+ <key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>avg</key>
- <value>0.001</value>
+ <key>import</key>
+ <value>import gnuradio.trellis.fsm_utils as fu</value>
</param>
<param>
- <key>graph_type</key>
- <value>qtgui.NUM_GRAPH_HORIZ</value>
+ <key>alias</key>
+ <value></value>
</param>
<param>
- <key>nconnections</key>
- <value>1</value>
+ <key>_coordinate</key>
+ <value>(48, 132)</value>
</param>
<param>
- <key>min</key>
+ <key>_rotation</key>
<value>0</value>
</param>
+ </block>
+ <block>
+ <key>trellis_pccc_encoder_xx</key>
<param>
- <key>max</key>
- <value>1</value>
+ <key>id</key>
+ <value>trellis_pccc_encoder_xx_0</value>
</param>
<param>
- <key>update_time</key>
- <value>0.01</value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>gui_hint</key>
- <value></value>
+ <key>type</key>
+ <value>bb</value>
</param>
<param>
- <key>label1</key>
- <value></value>
+ <key>o_fsm_args</key>
+ <value>fsm1</value>
</param>
<param>
- <key>unit1</key>
- <value></value>
+ <key>o_init_state</key>
+ <value>0</value>
</param>
<param>
- <key>color1</key>
- <value>("black", "black")</value>
+ <key>i_fsm_args</key>
+ <value>fsm2</value>
</param>
<param>
- <key>factor1</key>
- <value>1</value>
+ <key>i_init_state</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>interleaver_args</key>
+ <value>interleaver</value>
</param>
<param>
- <key>label2</key>
+ <key>bl</key>
+ <value>block</value>
+ </param>
+ <param>
+ <key>alias</key>
<value></value>
</param>
<param>
- <key>unit2</key>
+ <key>affinity</key>
<value></value>
</param>
<param>
- <key>color2</key>
- <value>("black", "black")</value>
+ <key>minoutbuf</key>
+ <value>0</value>
</param>
<param>
- <key>factor2</key>
- <value>1</value>
+ <key>maxoutbuf</key>
+ <value>0</value>
</param>
<param>
- <key>label3</key>
- <value></value>
+ <key>_coordinate</key>
+ <value>(400, 457)</value>
</param>
<param>
- <key>unit3</key>
- <value></value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>digital_chunks_to_symbols_xx</key>
<param>
- <key>color3</key>
- <value>("black", "black")</value>
+ <key>id</key>
+ <value>digital_chunks_to_symbols_xx_0</value>
</param>
<param>
- <key>factor3</key>
- <value>1</value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>label4</key>
- <value></value>
+ <key>in_type</key>
+ <value>byte</value>
</param>
<param>
- <key>unit4</key>
- <value></value>
+ <key>out_type</key>
+ <value>float</value>
+ </param>
+ <param>
+ <key>symbol_table</key>
+ <value>constellation</value>
</param>
<param>
- <key>color4</key>
- <value>("black", "black")</value>
+ <key>dimension</key>
+ <value>dim</value>
</param>
<param>
- <key>factor4</key>
+ <key>num_ports</key>
<value>1</value>
</param>
<param>
- <key>label5</key>
+ <key>alias</key>
<value></value>
</param>
<param>
- <key>unit5</key>
+ <key>affinity</key>
<value></value>
</param>
<param>
- <key>color5</key>
- <value>("black", "black")</value>
+ <key>minoutbuf</key>
+ <value>0</value>
</param>
<param>
- <key>factor5</key>
- <value>1</value>
+ <key>maxoutbuf</key>
+ <value>0</value>
</param>
<param>
- <key>label6</key>
- <value></value>
+ <key>_coordinate</key>
+ <value>(632, 485)</value>
</param>
<param>
- <key>unit6</key>
- <value></value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>analog_random_source_x</key>
<param>
- <key>color6</key>
- <value>("black", "black")</value>
+ <key>id</key>
+ <value>analog_random_source_x_0_0</value>
</param>
<param>
- <key>factor6</key>
- <value>1</value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>label7</key>
- <value></value>
+ <key>type</key>
+ <value>byte</value>
</param>
<param>
- <key>unit7</key>
- <value></value>
+ <key>min</key>
+ <value>0</value>
</param>
<param>
- <key>color7</key>
- <value>("black", "black")</value>
+ <key>max</key>
+ <value>2</value>
</param>
<param>
- <key>factor7</key>
- <value>1</value>
+ <key>num_samps</key>
+ <value>block</value>
+ </param>
+ <param>
+ <key>repeat</key>
+ <value>True</value>
</param>
<param>
- <key>label8</key>
+ <key>alias</key>
<value></value>
</param>
<param>
- <key>unit8</key>
+ <key>affinity</key>
<value></value>
</param>
<param>
- <key>color8</key>
- <value>("black", "black")</value>
+ <key>minoutbuf</key>
+ <value>0</value>
</param>
<param>
- <key>factor8</key>
- <value>1</value>
+ <key>maxoutbuf</key>
+ <value>0</value>
</param>
<param>
- <key>label9</key>
- <value></value>
+ <key>_coordinate</key>
+ <value>(8, 471)</value>
</param>
<param>
- <key>unit9</key>
- <value></value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>variable_slider</key>
<param>
- <key>color9</key>
- <value>("black", "black")</value>
+ <key>id</key>
+ <value>EsN0_dB</value>
</param>
<param>
- <key>factor9</key>
- <value>1</value>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>label</key>
+ <value>EsN0 (dB)</value>
+ </param>
+ <param>
+ <key>value</key>
+ <value>2</value>
+ </param>
+ <param>
+ <key>min</key>
+ <value>-10</value>
+ </param>
+ <param>
+ <key>max</key>
+ <value>20</value>
+ </param>
+ <param>
+ <key>num_steps</key>
+ <value>1000</value>
+ </param>
+ <param>
+ <key>style</key>
+ <value>wx.SL_HORIZONTAL</value>
+ </param>
+ <param>
+ <key>converver</key>
+ <value>float_converter</value>
</param>
<param>
- <key>label10</key>
+ <key>grid_pos</key>
<value></value>
</param>
<param>
- <key>unit10</key>
+ <key>notebook</key>
<value></value>
</param>
<param>
- <key>color10</key>
- <value>("black", "black")</value>
+ <key>alias</key>
+ <value></value>
</param>
<param>
- <key>factor10</key>
- <value>1</value>
+ <key>_coordinate</key>
+ <value>(896, 129)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>trellis_pccc_decoder_combined_xx</key>
+ <param>
+ <key>id</key>
+ <value>trellis_pccc_decoder_combined_xx_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>type</key>
+ <value>f</value>
+ </param>
+ <param>
+ <key>out_type</key>
+ <value>b</value>
+ </param>
+ <param>
+ <key>o_fsm_args</key>
+ <value>fsm1</value>
+ </param>
+ <param>
+ <key>o_init_state</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>o_final_state</key>
+ <value>-1</value>
+ </param>
+ <param>
+ <key>i_fsm_args</key>
+ <value>fsm2</value>
+ </param>
+ <param>
+ <key>i_init_state</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>i_final_state</key>
+ <value>-1</value>
+ </param>
+ <param>
+ <key>interleaver</key>
+ <value>interleaver</value>
+ </param>
+ <param>
+ <key>block_size</key>
+ <value>block</value>
+ </param>
+ <param>
+ <key>iterations</key>
+ <value>10</value>
+ </param>
+ <param>
+ <key>dim</key>
+ <value>dim</value>
+ </param>
+ <param>
+ <key>table</key>
+ <value>constellation</value>
+ </param>
+ <param>
+ <key>metric_type</key>
+ <value>digital.TRELLIS_EUCLIDEAN</value>
+ </param>
+ <param>
+ <key>siso_type</key>
+ <value>trellis.TRELLIS_MIN_SUM</value>
+ </param>
+ <param>
+ <key>scaling</key>
+ <value>0.5/noisevar</value>
</param>
<param>
<key>alias</key>
@@ -1008,8 +1187,16 @@
<value></value>
</param>
<param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
<key>_coordinate</key>
- <value>(571, 477)</value>
+ <value>(400, 849)</value>
</param>
<param>
<key>_rotation</key>
@@ -1017,75 +1204,75 @@
</param>
</block>
<connection>
- <source_block_id>analog_random_source_x_0</source_block_id>
- <sink_block_id>trellis_pccc_encoder_xx_0</sink_block_id>
+ <source_block_id>digital_chunks_to_symbols_xx_0</source_block_id>
+ <sink_block_id>blocks_add_xx_1</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_add_xx_1</source_block_id>
- <sink_block_id>trellis_pccc_decoder_combined_xx_0</sink_block_id>
+ <source_block_id>blks2_error_rate_0</source_block_id>
+ <sink_block_id>wxgui_numbersink2_3_0_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>analog_noise_source_x_0</source_block_id>
- <sink_block_id>blocks_add_xx_1</sink_block_id>
+ <source_block_id>virtual_source_0_0</source_block_id>
+ <sink_block_id>blks2_error_rate_0</sink_block_id>
<source_key>0</source_key>
- <sink_key>1</sink_key>
+ <sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>digital_chunks_to_symbols_xx_0</source_block_id>
- <sink_block_id>blocks_add_xx_1</sink_block_id>
+ <source_block_id>virtual_source_0_0_0</source_block_id>
+ <sink_block_id>blks2_error_rate_0</sink_block_id>
<source_key>0</source_key>
- <sink_key>0</sink_key>
+ <sink_key>1</sink_key>
</connection>
<connection>
- <source_block_id>blocks_throttle_0</source_block_id>
- <sink_block_id>digital_chunks_to_symbols_xx_0</sink_block_id>
+ <source_block_id>blocks_add_xx_1</source_block_id>
+ <sink_block_id>virtual_sink_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>trellis_pccc_encoder_xx_0</source_block_id>
- <sink_block_id>blocks_throttle_0</sink_block_id>
+ <source_block_id>trellis_pccc_decoder_combined_xx_0</source_block_id>
+ <sink_block_id>virtual_sink_0_1</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>analog_random_source_x_0</source_block_id>
- <sink_block_id>blocks_sub_xx_0</sink_block_id>
+ <source_block_id>virtual_source_0</source_block_id>
+ <sink_block_id>trellis_pccc_decoder_combined_xx_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_short_to_float_1_0</source_block_id>
- <sink_block_id>qtgui_number_sink_0</sink_block_id>
+ <source_block_id>trellis_pccc_encoder_xx_0</source_block_id>
+ <sink_block_id>digital_chunks_to_symbols_xx_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>trellis_pccc_decoder_combined_xx_0</source_block_id>
- <sink_block_id>blocks_sub_xx_0</sink_block_id>
+ <source_block_id>blocks_throttle_0_0</source_block_id>
+ <sink_block_id>trellis_pccc_encoder_xx_0</sink_block_id>
<source_key>0</source_key>
- <sink_key>1</sink_key>
+ <sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_sub_xx_0</source_block_id>
- <sink_block_id>blocks_multiply_xx_2_0</sink_block_id>
+ <source_block_id>analog_random_source_x_0_0</source_block_id>
+ <sink_block_id>blocks_throttle_0_0</sink_block_id>
<source_key>0</source_key>
- <sink_key>1</sink_key>
+ <sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_sub_xx_0</source_block_id>
- <sink_block_id>blocks_multiply_xx_2_0</sink_block_id>
+ <source_block_id>analog_random_source_x_0_0</source_block_id>
+ <sink_block_id>virtual_sink_0_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_multiply_xx_2_0</source_block_id>
- <sink_block_id>blocks_short_to_float_1_0</sink_block_id>
+ <source_block_id>analog_noise_source_x_0</source_block_id>
+ <sink_block_id>blocks_add_xx_1</sink_block_id>
<source_key>0</source_key>
- <sink_key>0</sink_key>
+ <sink_key>1</sink_key>
</connection>
</flow_graph>
diff --git a/gr-trellis/examples/grc/readme.txt b/gr-trellis/examples/grc/readme.txt
index a5261ac0b2..3d32e046dd 100644
--- a/gr-trellis/examples/grc/readme.txt
+++ b/gr-trellis/examples/grc/readme.txt
@@ -1,6 +1,6 @@
These are examples of using gr-trellis in grc.
-INTERFERENCE CANCELLATION
+Interference Cancellation
-------------------------
Two users are transmitting simultaneously using convolutionally encoded QPSK, each with power P1=alpha*P and P2=(1-alpha)*P.
The combined signal is observed in noise and four different receivers are considered:
@@ -20,13 +20,13 @@ Serially Concatenated Convolutional Codes
-----------------------------------------
An SCCC can be defined by an outer and an inner FSM together with an interleaver
and a modulation type. You can change the SNR and observe the estimated BER.
-In sccc.grc the decoding and metric calculation are combined; in sccc1.grc they are separate.
Parallel Concatenated Convolutional Codes
-----------------------------------------
A PCCC can be defined by two FSMs together with an interleaver
and a modulation type. You can change the SNR and observe the estimated BER.
-In pccc1.grc the decoding and metric calculation are separate.
+
+...and a few other examples including turbo equalization, etc
Enjoy.
diff --git a/gr-trellis/examples/grc/sccc.grc b/gr-trellis/examples/grc/sccc.grc
index 9d516743b6..f31f3ce86d 100644
--- a/gr-trellis/examples/grc/sccc.grc
+++ b/gr-trellis/examples/grc/sccc.grc
@@ -1,6 +1,7 @@
<?xml version='1.0' encoding='ASCII'?>
+<?grc format='1' created='3.7.6'?>
<flow_graph>
- <timestamp>Mon Jul 28 14:09:50 2014</timestamp>
+ <timestamp>Wed Oct 1 11:04:18 2014</timestamp>
<block>
<key>options</key>
<param>
@@ -29,7 +30,7 @@
</param>
<param>
<key>generate_options</key>
- <value>qt_gui</value>
+ <value>wx_gui</value>
</param>
<param>
<key>category</key>
@@ -84,7 +85,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(514, 10)</value>
+ <value>(344, 13)</value>
</param>
<param>
<key>_rotation</key>
@@ -95,7 +96,7 @@
<key>variable</key>
<param>
<key>id</key>
- <value>block</value>
+ <value>mod</value>
</param>
<param>
<key>_enabled</key>
@@ -103,7 +104,7 @@
</param>
<param>
<key>value</key>
- <value>1000</value>
+ <value>fu.psk2x3</value>
</param>
<param>
<key>alias</key>
@@ -111,7 +112,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(441, 10)</value>
+ <value>(632, 101)</value>
</param>
<param>
<key>_rotation</key>
@@ -122,7 +123,7 @@
<key>variable</key>
<param>
<key>id</key>
- <value>R</value>
+ <value>interleaver</value>
</param>
<param>
<key>_enabled</key>
@@ -130,7 +131,7 @@
</param>
<param>
<key>value</key>
- <value>100e3</value>
+ <value>trellis.interleaver(block,666)</value>
</param>
<param>
<key>alias</key>
@@ -138,7 +139,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(358, 10)</value>
+ <value>(344, 205)</value>
</param>
<param>
<key>_rotation</key>
@@ -149,7 +150,7 @@
<key>variable</key>
<param>
<key>id</key>
- <value>noisevar</value>
+ <value>Es</value>
</param>
<param>
<key>_enabled</key>
@@ -157,7 +158,7 @@
</param>
<param>
<key>value</key>
- <value>10**(-snr_db/10)</value>
+ <value>sum(numpy.square(constellation))/(len(constellation)/(1.0*dim))</value>
</param>
<param>
<key>alias</key>
@@ -165,7 +166,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(279, 10)</value>
+ <value>(800, 133)</value>
</param>
<param>
<key>_rotation</key>
@@ -173,54 +174,80 @@
</param>
</block>
<block>
- <key>analog_random_source_x</key>
+ <key>variable</key>
<param>
<key>id</key>
- <value>analog_random_source_x_0</value>
+ <value>noisevar</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>type</key>
- <value>short</value>
+ <key>value</key>
+ <value>10**(-EsN0_dB/10.0) * Es /2.0</value>
</param>
<param>
- <key>min</key>
- <value>0</value>
+ <key>alias</key>
+ <value></value>
</param>
<param>
- <key>max</key>
- <value>2</value>
+ <key>_coordinate</key>
+ <value>(1056, 141)</value>
</param>
<param>
- <key>num_samps</key>
- <value>1000</value>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>variable</key>
+ <param>
+ <key>id</key>
+ <value>block</value>
</param>
<param>
- <key>repeat</key>
+ <key>_enabled</key>
<value>True</value>
</param>
<param>
+ <key>value</key>
+ <value>1000</value>
+ </param>
+ <param>
<key>alias</key>
<value></value>
</param>
<param>
- <key>affinity</key>
- <value></value>
+ <key>_coordinate</key>
+ <value>(224, 29)</value>
</param>
<param>
- <key>minoutbuf</key>
+ <key>_rotation</key>
<value>0</value>
</param>
+ </block>
+ <block>
+ <key>variable</key>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
+ <key>id</key>
+ <value>fsm_o</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>value</key>
+ <value>trellis.fsm(prefix+"awgn1o2_4.fsm")</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
</param>
<param>
<key>_coordinate</key>
- <value>(21, 170)</value>
+ <value>(344, 77)</value>
</param>
<param>
<key>_rotation</key>
@@ -228,46 +255,80 @@
</param>
</block>
<block>
- <key>blocks_add_xx</key>
+ <key>variable</key>
<param>
<key>id</key>
- <value>blocks_add_xx_1</value>
+ <value>fsm_i</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>type</key>
- <value>complex</value>
+ <key>value</key>
+ <value>trellis.fsm(prefix+"/awgn2o3_4.fsm")</value>
</param>
<param>
- <key>num_inputs</key>
- <value>2</value>
+ <key>alias</key>
+ <value></value>
</param>
<param>
- <key>vlen</key>
- <value>1</value>
+ <key>_coordinate</key>
+ <value>(344, 141)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>variable</key>
+ <param>
+ <key>id</key>
+ <value>constellation</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>value</key>
+ <value>mod[1]</value>
</param>
<param>
<key>alias</key>
<value></value>
</param>
<param>
- <key>affinity</key>
- <value></value>
+ <key>_coordinate</key>
+ <value>(568, 173)</value>
</param>
<param>
- <key>minoutbuf</key>
+ <key>_rotation</key>
<value>0</value>
</param>
+ </block>
+ <block>
+ <key>variable</key>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
+ <key>id</key>
+ <value>dim</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>value</key>
+ <value>mod[0]</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
</param>
<param>
<key>_coordinate</key>
- <value>(951, 256)</value>
+ <value>(720, 173)</value>
</param>
<param>
<key>_rotation</key>
@@ -275,50 +336,76 @@
</param>
</block>
<block>
- <key>analog_noise_source_x</key>
+ <key>variable</key>
<param>
<key>id</key>
- <value>analog_noise_source_x_0</value>
+ <value>R</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>type</key>
- <value>complex</value>
+ <key>value</key>
+ <value>100e3</value>
</param>
<param>
- <key>noise_type</key>
- <value>analog.GR_GAUSSIAN</value>
+ <key>alias</key>
+ <value></value>
</param>
<param>
- <key>amp</key>
- <value>noisevar</value>
+ <key>_coordinate</key>
+ <value>(224, 93)</value>
</param>
<param>
- <key>seed</key>
- <value>-42</value>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>import</key>
+ <param>
+ <key>id</key>
+ <value>import_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>import</key>
+ <value>import numpy</value>
</param>
<param>
<key>alias</key>
<value></value>
</param>
<param>
- <key>affinity</key>
- <value></value>
+ <key>_coordinate</key>
+ <value>(32, 148)</value>
</param>
<param>
- <key>minoutbuf</key>
+ <key>_rotation</key>
<value>0</value>
</param>
+ </block>
+ <block>
+ <key>virtual_sink</key>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
+ <key>id</key>
+ <value>virtual_sink_0_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>stream_id</key>
+ <value>info</value>
</param>
<param>
<key>_coordinate</key>
- <value>(549, 250)</value>
+ <value>(192, 332)</value>
</param>
<param>
<key>_rotation</key>
@@ -326,10 +413,10 @@
</param>
</block>
<block>
- <key>blocks_throttle</key>
+ <key>analog_random_source_x</key>
<param>
<key>id</key>
- <value>blocks_throttle_0</value>
+ <value>analog_random_source_x_0</value>
</param>
<param>
<key>_enabled</key>
@@ -337,18 +424,22 @@
</param>
<param>
<key>type</key>
- <value>short</value>
+ <value>byte</value>
</param>
<param>
- <key>samples_per_second</key>
- <value>R</value>
+ <key>min</key>
+ <value>0</value>
</param>
<param>
- <key>vlen</key>
- <value>1</value>
+ <key>max</key>
+ <value>2</value>
</param>
<param>
- <key>ignoretag</key>
+ <key>num_samps</key>
+ <value>1007</value>
+ </param>
+ <param>
+ <key>repeat</key>
<value>True</value>
</param>
<param>
@@ -369,7 +460,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(551, 116)</value>
+ <value>(5, 384)</value>
</param>
<param>
<key>_rotation</key>
@@ -377,10 +468,10 @@
</param>
</block>
<block>
- <key>blocks_sub_xx</key>
+ <key>blocks_throttle</key>
<param>
<key>id</key>
- <value>blocks_sub_xx_0</value>
+ <value>blocks_throttle_0</value>
</param>
<param>
<key>_enabled</key>
@@ -388,15 +479,19 @@
</param>
<param>
<key>type</key>
- <value>short</value>
+ <value>byte</value>
+ </param>
+ <param>
+ <key>samples_per_second</key>
+ <value>R</value>
</param>
<param>
<key>vlen</key>
<value>1</value>
</param>
<param>
- <key>num_inputs</key>
- <value>2</value>
+ <key>ignoretag</key>
+ <value>True</value>
</param>
<param>
<key>alias</key>
@@ -416,7 +511,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(239, 548)</value>
+ <value>(232, 404)</value>
</param>
<param>
<key>_rotation</key>
@@ -424,25 +519,33 @@
</param>
</block>
<block>
- <key>blocks_multiply_xx</key>
+ <key>digital_chunks_to_symbols_xx</key>
<param>
<key>id</key>
- <value>blocks_multiply_xx_2_0</value>
+ <value>digital_chunks_to_symbols_xx_0</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>type</key>
- <value>short</value>
+ <key>in_type</key>
+ <value>byte</value>
</param>
<param>
- <key>num_inputs</key>
- <value>2</value>
+ <key>out_type</key>
+ <value>float</value>
</param>
<param>
- <key>vlen</key>
+ <key>symbol_table</key>
+ <value>constellation</value>
+ </param>
+ <param>
+ <key>dimension</key>
+ <value>dim</value>
+ </param>
+ <param>
+ <key>num_ports</key>
<value>1</value>
</param>
<param>
@@ -463,7 +566,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(418, 551)</value>
+ <value>(672, 397)</value>
</param>
<param>
<key>_rotation</key>
@@ -471,21 +574,25 @@
</param>
</block>
<block>
- <key>blocks_short_to_float</key>
+ <key>blocks_add_xx</key>
<param>
<key>id</key>
- <value>blocks_short_to_float_1_0</value>
+ <value>blocks_add_xx_1</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>vlen</key>
- <value>1</value>
+ <key>type</key>
+ <value>float</value>
+ </param>
+ <param>
+ <key>num_inputs</key>
+ <value>2</value>
</param>
<param>
- <key>scale</key>
+ <key>vlen</key>
<value>1</value>
</param>
<param>
@@ -506,7 +613,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(605, 564)</value>
+ <value>(960, 472)</value>
</param>
<param>
<key>_rotation</key>
@@ -514,33 +621,25 @@
</param>
</block>
<block>
- <key>digital_chunks_to_symbols_xx</key>
+ <key>blks2_error_rate</key>
<param>
<key>id</key>
- <value>digital_chunks_to_symbols_xx_0</value>
+ <value>blks2_error_rate_0</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>in_type</key>
- <value>short</value>
- </param>
- <param>
- <key>out_type</key>
- <value>complex</value>
- </param>
- <param>
- <key>symbol_table</key>
- <value>1,0,1j,0,-1j,0,-1,0,1,0,1j,0,-1j,0,-1,0</value>
+ <key>type</key>
+ <value>'SER'</value>
</param>
<param>
- <key>dimension</key>
- <value>2</value>
+ <key>win_size</key>
+ <value>block*100</value>
</param>
<param>
- <key>num_ports</key>
+ <key>bits_per_symbol</key>
<value>1</value>
</param>
<param>
@@ -561,7 +660,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(551, 181)</value>
+ <value>(312, 1168)</value>
</param>
<param>
<key>_rotation</key>
@@ -569,226 +668,260 @@
</param>
</block>
<block>
- <key>qtgui_number_sink</key>
+ <key>virtual_source</key>
<param>
<key>id</key>
- <value>qtgui_number_sink_0</value>
+ <value>virtual_source_0_0_0</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>name</key>
- <value>""</value>
+ <key>stream_id</key>
+ <value>estimate</value>
</param>
<param>
- <key>type</key>
- <value>float</value>
+ <key>_coordinate</key>
+ <value>(96, 1204)</value>
</param>
<param>
- <key>autoscale</key>
- <value>False</value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>virtual_source</key>
<param>
- <key>avg</key>
- <value>0.001</value>
+ <key>id</key>
+ <value>virtual_source_0_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>graph_type</key>
- <value>qtgui.NUM_GRAPH_HORIZ</value>
+ <key>stream_id</key>
+ <value>info</value>
</param>
<param>
- <key>nconnections</key>
- <value>1</value>
+ <key>_coordinate</key>
+ <value>(112, 1132)</value>
</param>
<param>
- <key>min</key>
+ <key>_rotation</key>
<value>0</value>
</param>
+ </block>
+ <block>
+ <key>wxgui_numbersink2</key>
<param>
- <key>max</key>
- <value>1</value>
+ <key>id</key>
+ <value>wxgui_numbersink2_3_0_0</value>
</param>
<param>
- <key>update_time</key>
- <value>0.10</value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>gui_hint</key>
- <value>1,0,1,1</value>
+ <key>type</key>
+ <value>float</value>
</param>
<param>
- <key>label1</key>
- <value></value>
+ <key>title</key>
+ <value>BER</value>
</param>
<param>
- <key>unit1</key>
- <value></value>
+ <key>units</key>
+ <value>BER</value>
</param>
<param>
- <key>color1</key>
- <value>("black", "black")</value>
+ <key>samp_rate</key>
+ <value>R</value>
</param>
<param>
- <key>factor1</key>
- <value>1</value>
+ <key>min_value</key>
+ <value>0</value>
</param>
<param>
- <key>label2</key>
- <value></value>
+ <key>max_value</key>
+ <value>1.0</value>
</param>
<param>
- <key>unit2</key>
- <value></value>
+ <key>factor</key>
+ <value>1.0</value>
</param>
<param>
- <key>color2</key>
- <value>("black", "black")</value>
+ <key>decimal_places</key>
+ <value>6</value>
</param>
<param>
- <key>factor2</key>
- <value>1</value>
+ <key>ref_level</key>
+ <value>0</value>
</param>
<param>
- <key>label3</key>
- <value></value>
+ <key>number_rate</key>
+ <value>15</value>
</param>
<param>
- <key>unit3</key>
- <value></value>
+ <key>peak_hold</key>
+ <value>False</value>
</param>
<param>
- <key>color3</key>
- <value>("black", "black")</value>
+ <key>average</key>
+ <value>False</value>
</param>
<param>
- <key>factor3</key>
- <value>1</value>
+ <key>avg_alpha</key>
+ <value>0.001</value>
</param>
<param>
- <key>label4</key>
- <value></value>
+ <key>show_gauge</key>
+ <value>False</value>
</param>
<param>
- <key>unit4</key>
+ <key>win_size</key>
<value></value>
</param>
<param>
- <key>color4</key>
- <value>("black", "black")</value>
+ <key>grid_pos</key>
+ <value></value>
</param>
<param>
- <key>factor4</key>
- <value>1</value>
+ <key>notebook</key>
+ <value></value>
</param>
<param>
- <key>label5</key>
+ <key>alias</key>
<value></value>
</param>
<param>
- <key>unit5</key>
+ <key>affinity</key>
<value></value>
</param>
<param>
- <key>color5</key>
- <value>("black", "black")</value>
+ <key>_coordinate</key>
+ <value>(688, 1117)</value>
</param>
<param>
- <key>factor5</key>
- <value>1</value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>virtual_source</key>
<param>
- <key>label6</key>
- <value></value>
+ <key>id</key>
+ <value>virtual_source_0</value>
</param>
<param>
- <key>unit6</key>
- <value></value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>color6</key>
- <value>("black", "black")</value>
+ <key>stream_id</key>
+ <value>observation</value>
</param>
<param>
- <key>factor6</key>
- <value>1</value>
+ <key>_coordinate</key>
+ <value>(88, 836)</value>
</param>
<param>
- <key>label7</key>
- <value></value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>virtual_sink</key>
<param>
- <key>unit7</key>
- <value></value>
+ <key>id</key>
+ <value>virtual_sink_0_1</value>
</param>
<param>
- <key>color7</key>
- <value>("black", "black")</value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>factor7</key>
- <value>1</value>
+ <key>stream_id</key>
+ <value>estimate</value>
</param>
<param>
- <key>label8</key>
- <value></value>
+ <key>_coordinate</key>
+ <value>(744, 836)</value>
</param>
<param>
- <key>unit8</key>
- <value></value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>analog_noise_source_x</key>
<param>
- <key>color8</key>
- <value>("black", "black")</value>
+ <key>id</key>
+ <value>analog_noise_source_x_0</value>
</param>
<param>
- <key>factor8</key>
- <value>1</value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>label9</key>
- <value></value>
+ <key>type</key>
+ <value>float</value>
</param>
<param>
- <key>unit9</key>
- <value></value>
+ <key>noise_type</key>
+ <value>analog.GR_GAUSSIAN</value>
</param>
<param>
- <key>color9</key>
- <value>("black", "black")</value>
+ <key>amp</key>
+ <value>noisevar**0.5</value>
</param>
<param>
- <key>factor9</key>
- <value>1</value>
+ <key>seed</key>
+ <value>-42</value>
</param>
<param>
- <key>label10</key>
+ <key>alias</key>
<value></value>
</param>
<param>
- <key>unit10</key>
+ <key>affinity</key>
<value></value>
</param>
<param>
- <key>color10</key>
- <value>("black", "black")</value>
+ <key>minoutbuf</key>
+ <value>0</value>
</param>
<param>
- <key>factor10</key>
- <value>1</value>
+ <key>maxoutbuf</key>
+ <value>0</value>
</param>
<param>
- <key>alias</key>
- <value></value>
+ <key>_coordinate</key>
+ <value>(608, 510)</value>
</param>
<param>
- <key>affinity</key>
- <value></value>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>virtual_sink</key>
+ <param>
+ <key>id</key>
+ <value>virtual_sink_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>stream_id</key>
+ <value>observation</value>
</param>
<param>
<key>_coordinate</key>
- <value>(788, 548)</value>
+ <value>(1064, 484)</value>
</param>
<param>
<key>_rotation</key>
@@ -796,10 +929,10 @@
</param>
</block>
<block>
- <key>variable_qtgui_range</key>
+ <key>variable_slider</key>
<param>
<key>id</key>
- <value>snr_db</value>
+ <value>EsN0_dB</value>
</param>
<param>
<key>_enabled</key>
@@ -807,38 +940,38 @@
</param>
<param>
<key>label</key>
- <value>SNR (dB)</value>
+ <value>EsN0 (dB)</value>
</param>
<param>
<key>value</key>
- <value>5</value>
+ <value>2</value>
</param>
<param>
- <key>start</key>
+ <key>min</key>
<value>-10</value>
</param>
<param>
- <key>stop</key>
+ <key>max</key>
<value>10</value>
</param>
<param>
- <key>step</key>
- <value>0.01</value>
+ <key>num_steps</key>
+ <value>1000</value>
</param>
<param>
- <key>widget</key>
- <value>counter_slider</value>
+ <key>style</key>
+ <value>wx.SL_HORIZONTAL</value>
</param>
<param>
- <key>orient</key>
- <value>Qt.Horizontal</value>
+ <key>converver</key>
+ <value>float_converter</value>
</param>
<param>
- <key>min_len</key>
- <value>200</value>
+ <key>grid_pos</key>
+ <value></value>
</param>
<param>
- <key>gui_hint</key>
+ <key>notebook</key>
<value></value>
</param>
<param>
@@ -847,11 +980,11 @@
</param>
<param>
<key>_coordinate</key>
- <value>(177, 10)</value>
+ <value>(920, 113)</value>
</param>
<param>
<key>_rotation</key>
- <value>180</value>
+ <value>0</value>
</param>
</block>
<block>
@@ -866,11 +999,11 @@
</param>
<param>
<key>type</key>
- <value>ss</value>
+ <value>bb</value>
</param>
<param>
<key>o_fsm_args</key>
- <value>prefix+"/awgn1o2_4.fsm"</value>
+ <value>fsm_o</value>
</param>
<param>
<key>o_init_state</key>
@@ -878,7 +1011,7 @@
</param>
<param>
<key>i_fsm_args</key>
- <value>prefix+"/awgn2o3_4.fsm"</value>
+ <value>fsm_i</value>
</param>
<param>
<key>i_init_state</key>
@@ -886,7 +1019,7 @@
</param>
<param>
<key>interleaver_args</key>
- <value>trellis.interleaver(block,666)</value>
+ <value>interleaver</value>
</param>
<param>
<key>bl</key>
@@ -910,11 +1043,38 @@
</param>
<param>
<key>_coordinate</key>
- <value>(242, 154)</value>
+ <value>(416, 369)</value>
</param>
<param>
<key>_rotation</key>
- <value>180</value>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>import</key>
+ <param>
+ <key>id</key>
+ <value>import_0_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>import</key>
+ <value>import gnuradio.trellis.fsm_utils as fu</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(40, 204)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
</param>
</block>
<block>
@@ -929,15 +1089,15 @@
</param>
<param>
<key>type</key>
- <value>c</value>
+ <value>f</value>
</param>
<param>
<key>out_type</key>
- <value>s</value>
+ <value>b</value>
</param>
<param>
<key>o_fsm_args</key>
- <value>prefix+"/awgn1o2_4.fsm"</value>
+ <value>fsm_o</value>
</param>
<param>
<key>o_init_state</key>
@@ -949,7 +1109,7 @@
</param>
<param>
<key>i_fsm_args</key>
- <value>prefix+"/awgn2o3_4.fsm"</value>
+ <value>fsm_i</value>
</param>
<param>
<key>i_init_state</key>
@@ -961,7 +1121,7 @@
</param>
<param>
<key>interleaver</key>
- <value>trellis.interleaver(block,666)</value>
+ <value>interleaver</value>
</param>
<param>
<key>block_size</key>
@@ -973,11 +1133,11 @@
</param>
<param>
<key>dim</key>
- <value>2</value>
+ <value>dim</value>
</param>
<param>
<key>table</key>
- <value>1,0,1j,0,-1j,0,-1,0,1,0,1j,0,-1j,0,-1,0</value>
+ <value>constellation</value>
</param>
<param>
<key>metric_type</key>
@@ -985,11 +1145,11 @@
</param>
<param>
<key>siso_type</key>
- <value>trellis.TRELLIS_SUM_PRODUCT</value>
+ <value>trellis.TRELLIS_MIN_SUM</value>
</param>
<param>
<key>scaling</key>
- <value>1.0</value>
+ <value>1.0/noisevar</value>
</param>
<param>
<key>alias</key>
@@ -1009,7 +1169,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(241, 287)</value>
+ <value>(400, 745)</value>
</param>
<param>
<key>_rotation</key>
@@ -1017,74 +1177,74 @@
</param>
</block>
<connection>
- <source_block_id>analog_random_source_x_0</source_block_id>
- <sink_block_id>blocks_sub_xx_0</sink_block_id>
+ <source_block_id>analog_noise_source_x_0</source_block_id>
+ <sink_block_id>blocks_add_xx_1</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>1</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>digital_chunks_to_symbols_xx_0</source_block_id>
+ <sink_block_id>blocks_add_xx_1</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
<source_block_id>analog_random_source_x_0</source_block_id>
- <sink_block_id>trellis_sccc_encoder_xx_0</sink_block_id>
+ <sink_block_id>virtual_sink_0_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>trellis_sccc_encoder_xx_0</source_block_id>
+ <source_block_id>analog_random_source_x_0</source_block_id>
<sink_block_id>blocks_throttle_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_add_xx_1</source_block_id>
- <sink_block_id>trellis_sccc_decoder_combined_xx_0</sink_block_id>
+ <source_block_id>blocks_throttle_0</source_block_id>
+ <sink_block_id>trellis_sccc_encoder_xx_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>trellis_sccc_decoder_combined_xx_0</source_block_id>
- <sink_block_id>blocks_sub_xx_0</sink_block_id>
+ <source_block_id>trellis_sccc_encoder_xx_0</source_block_id>
+ <sink_block_id>digital_chunks_to_symbols_xx_0</sink_block_id>
<source_key>0</source_key>
- <sink_key>1</sink_key>
+ <sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_throttle_0</source_block_id>
- <sink_block_id>digital_chunks_to_symbols_xx_0</sink_block_id>
+ <source_block_id>blocks_add_xx_1</source_block_id>
+ <sink_block_id>virtual_sink_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>analog_noise_source_x_0</source_block_id>
- <sink_block_id>blocks_add_xx_1</sink_block_id>
+ <source_block_id>virtual_source_0_0_0</source_block_id>
+ <sink_block_id>blks2_error_rate_0</sink_block_id>
<source_key>0</source_key>
<sink_key>1</sink_key>
</connection>
<connection>
- <source_block_id>digital_chunks_to_symbols_xx_0</source_block_id>
- <sink_block_id>blocks_add_xx_1</sink_block_id>
+ <source_block_id>virtual_source_0_0</source_block_id>
+ <sink_block_id>blks2_error_rate_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_sub_xx_0</source_block_id>
- <sink_block_id>blocks_multiply_xx_2_0</sink_block_id>
- <source_key>0</source_key>
- <sink_key>1</sink_key>
- </connection>
- <connection>
- <source_block_id>blocks_sub_xx_0</source_block_id>
- <sink_block_id>blocks_multiply_xx_2_0</sink_block_id>
+ <source_block_id>blks2_error_rate_0</source_block_id>
+ <sink_block_id>wxgui_numbersink2_3_0_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_multiply_xx_2_0</source_block_id>
- <sink_block_id>blocks_short_to_float_1_0</sink_block_id>
+ <source_block_id>trellis_sccc_decoder_combined_xx_0</source_block_id>
+ <sink_block_id>virtual_sink_0_1</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_short_to_float_1_0</source_block_id>
- <sink_block_id>qtgui_number_sink_0</sink_block_id>
+ <source_block_id>virtual_source_0</source_block_id>
+ <sink_block_id>trellis_sccc_decoder_combined_xx_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
diff --git a/gr-trellis/examples/grc/pccc1.grc b/gr-trellis/examples/grc/tcm.grc
index acb112d255..451d940962 100644
--- a/gr-trellis/examples/grc/pccc1.grc
+++ b/gr-trellis/examples/grc/tcm.grc
@@ -1,11 +1,12 @@
<?xml version='1.0' encoding='ASCII'?>
+<?grc format='1' created='3.7.6'?>
<flow_graph>
- <timestamp>Mon Jul 28 14:09:00 2014</timestamp>
+ <timestamp>Wed Oct 1 11:04:18 2014</timestamp>
<block>
<key>options</key>
<param>
<key>id</key>
- <value>sccc1</value>
+ <value>tcm</value>
</param>
<param>
<key>_enabled</key>
@@ -13,7 +14,7 @@
</param>
<param>
<key>title</key>
- <value>Parallel Concatenated Convolutional Code</value>
+ <value>Trellis Coded Modulation</value>
</param>
<param>
<key>author</key>
@@ -29,7 +30,7 @@
</param>
<param>
<key>generate_options</key>
- <value>qt_gui</value>
+ <value>wx_gui</value>
</param>
<param>
<key>category</key>
@@ -84,7 +85,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(513, 10)</value>
+ <value>(320, 13)</value>
</param>
<param>
<key>_rotation</key>
@@ -95,7 +96,7 @@
<key>variable</key>
<param>
<key>id</key>
- <value>block</value>
+ <value>dim</value>
</param>
<param>
<key>_enabled</key>
@@ -103,7 +104,7 @@
</param>
<param>
<key>value</key>
- <value>1000</value>
+ <value>mod[0]</value>
</param>
<param>
<key>alias</key>
@@ -111,7 +112,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(441, 10)</value>
+ <value>(464, 229)</value>
</param>
<param>
<key>_rotation</key>
@@ -122,7 +123,7 @@
<key>variable</key>
<param>
<key>id</key>
- <value>R</value>
+ <value>constellation</value>
</param>
<param>
<key>_enabled</key>
@@ -130,7 +131,7 @@
</param>
<param>
<key>value</key>
- <value>100e3</value>
+ <value>mod[1]</value>
</param>
<param>
<key>alias</key>
@@ -138,7 +139,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(358, 10)</value>
+ <value>(312, 229)</value>
</param>
<param>
<key>_rotation</key>
@@ -149,7 +150,7 @@
<key>variable</key>
<param>
<key>id</key>
- <value>noisevar</value>
+ <value>mod</value>
</param>
<param>
<key>_enabled</key>
@@ -157,7 +158,7 @@
</param>
<param>
<key>value</key>
- <value>10**(-snr_db/10)</value>
+ <value>fu.psk4</value>
</param>
<param>
<key>alias</key>
@@ -165,7 +166,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(279, 10)</value>
+ <value>(336, 157)</value>
</param>
<param>
<key>_rotation</key>
@@ -173,54 +174,53 @@
</param>
</block>
<block>
- <key>analog_random_source_x</key>
+ <key>variable</key>
<param>
<key>id</key>
- <value>analog_random_source_x_0</value>
+ <value>fsm</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>type</key>
- <value>short</value>
- </param>
- <param>
- <key>min</key>
- <value>0</value>
+ <key>value</key>
+ <value>"awgn1o2_4.fsm"</value>
</param>
<param>
- <key>max</key>
- <value>2</value>
+ <key>alias</key>
+ <value></value>
</param>
<param>
- <key>num_samps</key>
- <value>1000</value>
+ <key>_coordinate</key>
+ <value>(320, 77)</value>
</param>
<param>
- <key>repeat</key>
- <value>True</value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>variable</key>
<param>
- <key>alias</key>
- <value></value>
+ <key>id</key>
+ <value>R</value>
</param>
<param>
- <key>affinity</key>
- <value></value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>minoutbuf</key>
- <value>0</value>
+ <key>value</key>
+ <value>100e3</value>
</param>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
+ <key>alias</key>
+ <value></value>
</param>
<param>
<key>_coordinate</key>
- <value>(21, 170)</value>
+ <value>(216, 109)</value>
</param>
<param>
<key>_rotation</key>
@@ -228,226 +228,270 @@
</param>
</block>
<block>
- <key>qtgui_number_sink</key>
+ <key>variable</key>
<param>
<key>id</key>
- <value>qtgui_number_sink_0</value>
+ <value>noisevar</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>name</key>
- <value>""</value>
+ <key>value</key>
+ <value>10**(-EsN0_dB/10.0) * Es /2.0</value>
</param>
<param>
- <key>type</key>
- <value>float</value>
+ <key>alias</key>
+ <value></value>
</param>
<param>
- <key>autoscale</key>
- <value>False</value>
+ <key>_coordinate</key>
+ <value>(728, 157)</value>
</param>
<param>
- <key>avg</key>
- <value>0.001</value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>variable</key>
<param>
- <key>graph_type</key>
- <value>qtgui.NUM_GRAPH_HORIZ</value>
+ <key>id</key>
+ <value>Es</value>
</param>
<param>
- <key>nconnections</key>
- <value>1</value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>min</key>
+ <key>value</key>
+ <value>sum(numpy.square(numpy.abs(constellation)))/(len(constellation)/(1.0*dim))</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(528, 157)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
<value>0</value>
</param>
+ </block>
+ <block>
+ <key>variable</key>
<param>
- <key>max</key>
- <value>1</value>
+ <key>id</key>
+ <value>block</value>
</param>
<param>
- <key>update_time</key>
- <value>0.10</value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>gui_hint</key>
- <value>1,0,1,1</value>
+ <key>value</key>
+ <value>500*16</value>
</param>
<param>
- <key>label1</key>
+ <key>alias</key>
<value></value>
</param>
<param>
- <key>unit1</key>
- <value></value>
+ <key>_coordinate</key>
+ <value>(216, 29)</value>
</param>
<param>
- <key>color1</key>
- <value>("black", "black")</value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>blocks_throttle</key>
<param>
- <key>factor1</key>
- <value>1</value>
+ <key>id</key>
+ <value>blocks_throttle_0</value>
</param>
<param>
- <key>label2</key>
- <value></value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>unit2</key>
- <value></value>
+ <key>type</key>
+ <value>byte</value>
</param>
<param>
- <key>color2</key>
- <value>("black", "black")</value>
+ <key>samples_per_second</key>
+ <value>R</value>
</param>
<param>
- <key>factor2</key>
+ <key>vlen</key>
<value>1</value>
</param>
<param>
- <key>label3</key>
- <value></value>
+ <key>ignoretag</key>
+ <value>True</value>
</param>
<param>
- <key>unit3</key>
+ <key>alias</key>
<value></value>
</param>
<param>
- <key>color3</key>
- <value>("black", "black")</value>
+ <key>affinity</key>
+ <value></value>
</param>
<param>
- <key>factor3</key>
- <value>1</value>
+ <key>minoutbuf</key>
+ <value>0</value>
</param>
<param>
- <key>label4</key>
- <value></value>
+ <key>maxoutbuf</key>
+ <value>0</value>
</param>
<param>
- <key>unit4</key>
- <value></value>
+ <key>_coordinate</key>
+ <value>(208, 380)</value>
</param>
<param>
- <key>color4</key>
- <value>("black", "black")</value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>blocks_add_xx</key>
<param>
- <key>factor4</key>
- <value>1</value>
+ <key>id</key>
+ <value>blocks_add_xx_1</value>
</param>
<param>
- <key>label5</key>
- <value></value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>unit5</key>
- <value></value>
+ <key>type</key>
+ <value>float</value>
</param>
<param>
- <key>color5</key>
- <value>("black", "black")</value>
+ <key>num_inputs</key>
+ <value>2</value>
</param>
<param>
- <key>factor5</key>
+ <key>vlen</key>
<value>1</value>
</param>
<param>
- <key>label6</key>
+ <key>alias</key>
<value></value>
</param>
<param>
- <key>unit6</key>
+ <key>affinity</key>
<value></value>
</param>
<param>
- <key>color6</key>
- <value>("black", "black")</value>
+ <key>minoutbuf</key>
+ <value>0</value>
</param>
<param>
- <key>factor6</key>
- <value>1</value>
+ <key>maxoutbuf</key>
+ <value>0</value>
</param>
<param>
- <key>label7</key>
- <value></value>
+ <key>_coordinate</key>
+ <value>(912, 488)</value>
</param>
<param>
- <key>unit7</key>
- <value></value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>virtual_sink</key>
<param>
- <key>color7</key>
- <value>("black", "black")</value>
+ <key>id</key>
+ <value>virtual_sink_0_0</value>
</param>
<param>
- <key>factor7</key>
- <value>1</value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>label8</key>
- <value></value>
+ <key>stream_id</key>
+ <value>info</value>
</param>
<param>
- <key>unit8</key>
- <value></value>
+ <key>_coordinate</key>
+ <value>(224, 316)</value>
</param>
<param>
- <key>color8</key>
- <value>("black", "black")</value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>virtual_sink</key>
<param>
- <key>factor8</key>
- <value>1</value>
+ <key>id</key>
+ <value>virtual_sink_0</value>
</param>
<param>
- <key>label9</key>
- <value></value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>unit9</key>
- <value></value>
+ <key>stream_id</key>
+ <value>observation</value>
</param>
<param>
- <key>color9</key>
- <value>("black", "black")</value>
+ <key>_coordinate</key>
+ <value>(832, 620)</value>
</param>
<param>
- <key>factor9</key>
- <value>1</value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>virtual_source</key>
<param>
- <key>label10</key>
- <value></value>
+ <key>id</key>
+ <value>virtual_source_0</value>
</param>
<param>
- <key>unit10</key>
- <value></value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>color10</key>
- <value>("black", "black")</value>
+ <key>stream_id</key>
+ <value>observation</value>
</param>
<param>
- <key>factor10</key>
- <value>1</value>
+ <key>_coordinate</key>
+ <value>(64, 732)</value>
</param>
<param>
- <key>alias</key>
- <value></value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>virtual_sink</key>
<param>
- <key>affinity</key>
- <value></value>
+ <key>id</key>
+ <value>virtual_sink_0_1</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>stream_id</key>
+ <value>estimate</value>
</param>
<param>
<key>_coordinate</key>
- <value>(632, 509)</value>
+ <value>(800, 732)</value>
</param>
<param>
<key>_rotation</key>
@@ -455,22 +499,30 @@
</param>
</block>
<block>
- <key>blocks_short_to_float</key>
+ <key>analog_noise_source_x</key>
<param>
<key>id</key>
- <value>blocks_short_to_float_1_0</value>
+ <value>analog_noise_source_x_0</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>vlen</key>
- <value>1</value>
+ <key>type</key>
+ <value>float</value>
</param>
<param>
- <key>scale</key>
- <value>1</value>
+ <key>noise_type</key>
+ <value>analog.GR_GAUSSIAN</value>
+ </param>
+ <param>
+ <key>amp</key>
+ <value>noisevar**0.5</value>
+ </param>
+ <param>
+ <key>seed</key>
+ <value>-42</value>
</param>
<param>
<key>alias</key>
@@ -490,7 +542,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(375, 525)</value>
+ <value>(384, 502)</value>
</param>
<param>
<key>_rotation</key>
@@ -498,46 +550,58 @@
</param>
</block>
<block>
- <key>blocks_multiply_xx</key>
+ <key>variable_slider</key>
<param>
<key>id</key>
- <value>blocks_multiply_xx_2_0</value>
+ <value>EsN0_dB</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>type</key>
- <value>short</value>
+ <key>label</key>
+ <value>Es/N0 (dB)</value>
</param>
<param>
- <key>num_inputs</key>
- <value>2</value>
+ <key>value</key>
+ <value>4.0</value>
</param>
<param>
- <key>vlen</key>
- <value>1</value>
+ <key>min</key>
+ <value>-10</value>
</param>
<param>
- <key>alias</key>
- <value></value>
+ <key>max</key>
+ <value>30</value>
</param>
<param>
- <key>affinity</key>
+ <key>num_steps</key>
+ <value>1000</value>
+ </param>
+ <param>
+ <key>style</key>
+ <value>wx.SL_HORIZONTAL</value>
+ </param>
+ <param>
+ <key>converver</key>
+ <value>float_converter</value>
+ </param>
+ <param>
+ <key>grid_pos</key>
<value></value>
</param>
<param>
- <key>minoutbuf</key>
- <value>0</value>
+ <key>notebook</key>
+ <value></value>
</param>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
+ <key>alias</key>
+ <value></value>
</param>
<param>
<key>_coordinate</key>
- <value>(232, 507)</value>
+ <value>(608, 105)</value>
</param>
<param>
<key>_rotation</key>
@@ -545,10 +609,10 @@
</param>
</block>
<block>
- <key>blocks_sub_xx</key>
+ <key>analog_random_source_x</key>
<param>
<key>id</key>
- <value>blocks_sub_xx_0</value>
+ <value>analog_random_source_x_0</value>
</param>
<param>
<key>_enabled</key>
@@ -556,17 +620,25 @@
</param>
<param>
<key>type</key>
- <value>short</value>
+ <value>byte</value>
</param>
<param>
- <key>vlen</key>
- <value>1</value>
+ <key>min</key>
+ <value>0</value>
</param>
<param>
- <key>num_inputs</key>
+ <key>max</key>
<value>2</value>
</param>
<param>
+ <key>num_samps</key>
+ <value>1007</value>
+ </param>
+ <param>
+ <key>repeat</key>
+ <value>True</value>
+ </param>
+ <param>
<key>alias</key>
<value></value>
</param>
@@ -584,7 +656,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(57, 513)</value>
+ <value>(8, 359)</value>
</param>
<param>
<key>_rotation</key>
@@ -592,49 +664,81 @@
</param>
</block>
<block>
- <key>variable_qtgui_range</key>
+ <key>wxgui_numbersink2</key>
<param>
<key>id</key>
- <value>snr_db</value>
+ <value>wxgui_numbersink2_3_0_0</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>label</key>
- <value>SNR (dB)</value>
+ <key>type</key>
+ <value>float</value>
</param>
<param>
- <key>value</key>
- <value>5</value>
+ <key>title</key>
+ <value>BER</value>
</param>
<param>
- <key>start</key>
- <value>-10</value>
+ <key>units</key>
+ <value>BER</value>
+ </param>
+ <param>
+ <key>samp_rate</key>
+ <value>R</value>
+ </param>
+ <param>
+ <key>min_value</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>max_value</key>
+ <value>1.0</value>
+ </param>
+ <param>
+ <key>factor</key>
+ <value>1.0</value>
+ </param>
+ <param>
+ <key>decimal_places</key>
+ <value>6</value>
+ </param>
+ <param>
+ <key>ref_level</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>number_rate</key>
+ <value>15</value>
+ </param>
+ <param>
+ <key>peak_hold</key>
+ <value>False</value>
</param>
<param>
- <key>stop</key>
- <value>10</value>
+ <key>average</key>
+ <value>False</value>
</param>
<param>
- <key>step</key>
- <value>0.01</value>
+ <key>avg_alpha</key>
+ <value>0.001</value>
</param>
<param>
- <key>widget</key>
- <value>counter_slider</value>
+ <key>show_gauge</key>
+ <value>False</value>
</param>
<param>
- <key>orient</key>
- <value>Qt.Horizontal</value>
+ <key>win_size</key>
+ <value></value>
</param>
<param>
- <key>min_len</key>
- <value>200</value>
+ <key>grid_pos</key>
+ <value></value>
</param>
<param>
- <key>gui_hint</key>
+ <key>notebook</key>
<value></value>
</param>
<param>
@@ -642,51 +746,85 @@
<value></value>
</param>
<param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
<key>_coordinate</key>
- <value>(177, 10)</value>
+ <value>(728, 1133)</value>
</param>
<param>
<key>_rotation</key>
- <value>180</value>
+ <value>0</value>
</param>
</block>
<block>
- <key>trellis_pccc_encoder_xx</key>
+ <key>virtual_source</key>
<param>
<key>id</key>
- <value>trellis_pccc_encoder_xx_0</value>
+ <value>virtual_source_0_0</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>type</key>
- <value>ss</value>
+ <key>stream_id</key>
+ <value>info</value>
</param>
<param>
- <key>o_fsm_args</key>
- <value>prefix+"/awgn1o2_4.fsm"</value>
+ <key>_coordinate</key>
+ <value>(80, 1148)</value>
</param>
<param>
- <key>o_init_state</key>
+ <key>_rotation</key>
<value>0</value>
</param>
+ </block>
+ <block>
+ <key>virtual_source</key>
<param>
- <key>i_fsm_args</key>
- <value>prefix+"/awgn1o2_4.fsm"</value>
+ <key>id</key>
+ <value>virtual_source_0_0_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>stream_id</key>
+ <value>estimate</value>
</param>
<param>
- <key>i_init_state</key>
+ <key>_coordinate</key>
+ <value>(72, 1244)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
<value>0</value>
</param>
+ </block>
+ <block>
+ <key>blks2_error_rate</key>
<param>
- <key>interleaver_args</key>
- <value>trellis.interleaver(block,666)</value>
+ <key>id</key>
+ <value>blks2_error_rate_0</value>
</param>
<param>
- <key>bl</key>
- <value>block</value>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>type</key>
+ <value>'SER'</value>
+ </param>
+ <param>
+ <key>win_size</key>
+ <value>block*100</value>
+ </param>
+ <param>
+ <key>bits_per_symbol</key>
+ <value>1</value>
</param>
<param>
<key>alias</key>
@@ -706,7 +844,34 @@
</param>
<param>
<key>_coordinate</key>
- <value>(235, 154)</value>
+ <value>(312, 1184)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>note</key>
+ <param>
+ <key>id</key>
+ <value>note_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>note</key>
+ <value>Substititue the metrics/Viterbi block with Viterbi_combo</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(712, 868)</value>
</param>
<param>
<key>_rotation</key>
@@ -721,7 +886,7 @@
</param>
<param>
<key>_enabled</key>
- <value>True</value>
+ <value>False</value>
</param>
<param>
<key>type</key>
@@ -729,15 +894,15 @@
</param>
<param>
<key>card</key>
- <value>16</value>
+ <value>trellis.fsm(prefix+fsm).O()</value>
</param>
<param>
<key>dim</key>
- <value>2</value>
+ <value>dim</value>
</param>
<param>
<key>table</key>
- <value>-7,0, -5,0, -3,0, -1,0, 1,0, 3,0, 5,0, 7,0, 0,-7,0, -5,0, -3,0, -1,0, 1,0, 3,0, 5,0, 7,0</value>
+ <value>constellation</value>
</param>
<param>
<key>metric_type</key>
@@ -761,7 +926,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(89, 380)</value>
+ <value>(304, 711)</value>
</param>
<param>
<key>_rotation</key>
@@ -769,58 +934,34 @@
</param>
</block>
<block>
- <key>trellis_pccc_decoder_x</key>
+ <key>trellis_viterbi_x</key>
<param>
<key>id</key>
- <value>trellis_pccc_decoder_x_0</value>
+ <value>trellis_viterbi_x_0</value>
</param>
<param>
<key>_enabled</key>
- <value>True</value>
- </param>
- <param>
- <key>out_type</key>
- <value>s</value>
- </param>
- <param>
- <key>o_fsm_args</key>
- <value>prefix+"/awgn1o2_4.fsm"</value>
- </param>
- <param>
- <key>o_init_state</key>
- <value>0</value>
- </param>
- <param>
- <key>o_final_state</key>
- <value>-1</value>
- </param>
- <param>
- <key>i_fsm_args</key>
- <value>prefix+"/awgn1o2_4.fsm"</value>
- </param>
- <param>
- <key>i_init_state</key>
- <value>0</value>
+ <value>False</value>
</param>
<param>
- <key>i_final_state</key>
- <value>-1</value>
+ <key>type</key>
+ <value>b</value>
</param>
<param>
- <key>interleaver</key>
- <value>trellis.interleaver(block,666)</value>
+ <key>fsm_args</key>
+ <value>prefix+fsm</value>
</param>
<param>
<key>block_size</key>
<value>block</value>
</param>
<param>
- <key>iterations</key>
- <value>10</value>
+ <key>init_state</key>
+ <value>-1</value>
</param>
<param>
- <key>siso_type</key>
- <value>trellis.TRELLIS_MIN_SUM</value>
+ <key>final_state</key>
+ <value>-1</value>
</param>
<param>
<key>alias</key>
@@ -840,7 +981,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(379, 332)</value>
+ <value>(544, 711)</value>
</param>
<param>
<key>_rotation</key>
@@ -848,34 +989,50 @@
</param>
</block>
<block>
- <key>digital_chunks_to_symbols_xx</key>
+ <key>trellis_viterbi_combined_xx</key>
<param>
<key>id</key>
- <value>digital_chunks_to_symbols_xx_0</value>
+ <value>trellis_viterbi_combined_xx_0</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>in_type</key>
- <value>short</value>
+ <key>type</key>
+ <value>f</value>
</param>
<param>
<key>out_type</key>
- <value>float</value>
+ <value>b</value>
</param>
<param>
- <key>symbol_table</key>
- <value>-7,0,-5,0,-3,0,-1,0,1,0,3,0,5,0,7,0,-7,0,-5,0,-3,0,-1,0,1,0,3,0,5,0,7,0</value>
+ <key>fsm_args</key>
+ <value>prefix+fsm</value>
</param>
<param>
- <key>dimension</key>
- <value>2</value>
+ <key>block_size</key>
+ <value>block</value>
</param>
<param>
- <key>num_ports</key>
- <value>1</value>
+ <key>init_state</key>
+ <value>-1</value>
+ </param>
+ <param>
+ <key>final_state</key>
+ <value>-1</value>
+ </param>
+ <param>
+ <key>dim</key>
+ <value>dim</value>
+ </param>
+ <param>
+ <key>table</key>
+ <value>constellation</value>
+ </param>
+ <param>
+ <key>metric_type</key>
+ <value>digital.TRELLIS_EUCLIDEAN</value>
</param>
<param>
<key>alias</key>
@@ -895,7 +1052,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(552, 164)</value>
+ <value>(440, 866)</value>
</param>
<param>
<key>_rotation</key>
@@ -903,50 +1060,53 @@
</param>
</block>
<block>
- <key>blocks_throttle</key>
+ <key>import</key>
<param>
<key>id</key>
- <value>blocks_throttle_0</value>
+ <value>import_0</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>type</key>
- <value>short</value>
+ <key>import</key>
+ <value>import numpy</value>
</param>
<param>
- <key>samples_per_second</key>
- <value>R</value>
+ <key>alias</key>
+ <value></value>
</param>
<param>
- <key>vlen</key>
- <value>1</value>
+ <key>_coordinate</key>
+ <value>(16, 140)</value>
</param>
<param>
- <key>ignoretag</key>
- <value>True</value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>import</key>
<param>
- <key>alias</key>
- <value></value>
+ <key>id</key>
+ <value>import_0_0</value>
</param>
<param>
- <key>affinity</key>
- <value></value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>minoutbuf</key>
- <value>0</value>
+ <key>import</key>
+ <value>import gnuradio.trellis.fsm_utils as fu</value>
</param>
<param>
- <key>maxoutbuf</key>
- <value>0</value>
+ <key>alias</key>
+ <value></value>
</param>
<param>
<key>_coordinate</key>
- <value>(553, 89)</value>
+ <value>(24, 196)</value>
</param>
<param>
<key>_rotation</key>
@@ -954,30 +1114,34 @@
</param>
</block>
<block>
- <key>analog_noise_source_x</key>
+ <key>digital_chunks_to_symbols_xx</key>
<param>
<key>id</key>
- <value>analog_noise_source_x_0</value>
+ <value>digital_chunks_to_symbols_xx_0</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>type</key>
+ <key>in_type</key>
+ <value>byte</value>
+ </param>
+ <param>
+ <key>out_type</key>
<value>float</value>
</param>
<param>
- <key>noise_type</key>
- <value>analog.GR_GAUSSIAN</value>
+ <key>symbol_table</key>
+ <value>constellation</value>
</param>
<param>
- <key>amp</key>
- <value>noisevar</value>
+ <key>dimension</key>
+ <value>dim</value>
</param>
<param>
- <key>seed</key>
- <value>-42</value>
+ <key>num_ports</key>
+ <value>1</value>
</param>
<param>
<key>alias</key>
@@ -997,7 +1161,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(551, 230)</value>
+ <value>(696, 373)</value>
</param>
<param>
<key>_rotation</key>
@@ -1005,10 +1169,10 @@
</param>
</block>
<block>
- <key>blocks_add_xx</key>
+ <key>trellis_encoder_xx</key>
<param>
<key>id</key>
- <value>blocks_add_xx_1</value>
+ <value>trellis_encoder_xx_0</value>
</param>
<param>
<key>_enabled</key>
@@ -1016,15 +1180,23 @@
</param>
<param>
<key>type</key>
- <value>float</value>
+ <value>bb</value>
</param>
<param>
- <key>num_inputs</key>
- <value>2</value>
+ <key>fsm_args</key>
+ <value>prefix+fsm</value>
</param>
<param>
- <key>vlen</key>
- <value>1</value>
+ <key>init_state</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>blockwise</key>
+ <value>False</value>
+ </param>
+ <param>
+ <key>blocklength</key>
+ <value>0</value>
</param>
<param>
<key>alias</key>
@@ -1044,7 +1216,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(839, 176)</value>
+ <value>(424, 373)</value>
</param>
<param>
<key>_rotation</key>
@@ -1052,81 +1224,93 @@
</param>
</block>
<connection>
- <source_block_id>analog_random_source_x_0</source_block_id>
- <sink_block_id>blocks_sub_xx_0</sink_block_id>
+ <source_block_id>analog_noise_source_x_0</source_block_id>
+ <sink_block_id>blocks_add_xx_1</sink_block_id>
<source_key>0</source_key>
- <sink_key>0</sink_key>
+ <sink_key>1</sink_key>
</connection>
<connection>
- <source_block_id>blocks_add_xx_1</source_block_id>
- <sink_block_id>trellis_metrics_x_0</sink_block_id>
+ <source_block_id>digital_chunks_to_symbols_xx_0</source_block_id>
+ <sink_block_id>blocks_add_xx_1</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
<source_block_id>analog_random_source_x_0</source_block_id>
- <sink_block_id>trellis_pccc_encoder_xx_0</sink_block_id>
+ <sink_block_id>blocks_throttle_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>trellis_pccc_encoder_xx_0</source_block_id>
- <sink_block_id>blocks_throttle_0</sink_block_id>
+ <source_block_id>blocks_throttle_0</source_block_id>
+ <sink_block_id>trellis_encoder_xx_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>trellis_metrics_x_0</source_block_id>
- <sink_block_id>trellis_pccc_decoder_x_0</sink_block_id>
+ <source_block_id>trellis_encoder_xx_0</source_block_id>
+ <sink_block_id>digital_chunks_to_symbols_xx_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>trellis_pccc_decoder_x_0</source_block_id>
- <sink_block_id>blocks_sub_xx_0</sink_block_id>
+ <source_block_id>blocks_add_xx_1</source_block_id>
+ <sink_block_id>virtual_sink_0</sink_block_id>
<source_key>0</source_key>
- <sink_key>1</sink_key>
+ <sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_short_to_float_1_0</source_block_id>
- <sink_block_id>qtgui_number_sink_0</sink_block_id>
+ <source_block_id>virtual_source_0</source_block_id>
+ <sink_block_id>trellis_metrics_x_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_sub_xx_0</source_block_id>
- <sink_block_id>blocks_multiply_xx_2_0</sink_block_id>
+ <source_block_id>trellis_metrics_x_0</source_block_id>
+ <sink_block_id>trellis_viterbi_x_0</sink_block_id>
<source_key>0</source_key>
- <sink_key>1</sink_key>
+ <sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_sub_xx_0</source_block_id>
- <sink_block_id>blocks_multiply_xx_2_0</sink_block_id>
+ <source_block_id>analog_random_source_x_0</source_block_id>
+ <sink_block_id>virtual_sink_0_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_multiply_xx_2_0</source_block_id>
- <sink_block_id>blocks_short_to_float_1_0</sink_block_id>
+ <source_block_id>trellis_viterbi_x_0</source_block_id>
+ <sink_block_id>virtual_sink_0_1</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>analog_noise_source_x_0</source_block_id>
- <sink_block_id>blocks_add_xx_1</sink_block_id>
+ <source_block_id>virtual_source_0</source_block_id>
+ <sink_block_id>trellis_viterbi_combined_xx_0</sink_block_id>
<source_key>0</source_key>
- <sink_key>1</sink_key>
+ <sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>digital_chunks_to_symbols_xx_0</source_block_id>
- <sink_block_id>blocks_add_xx_1</sink_block_id>
+ <source_block_id>trellis_viterbi_combined_xx_0</source_block_id>
+ <sink_block_id>virtual_sink_0_1</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_throttle_0</source_block_id>
- <sink_block_id>digital_chunks_to_symbols_xx_0</sink_block_id>
+ <source_block_id>blks2_error_rate_0</source_block_id>
+ <sink_block_id>wxgui_numbersink2_3_0_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
+ <connection>
+ <source_block_id>virtual_source_0_0</source_block_id>
+ <sink_block_id>blks2_error_rate_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>virtual_source_0_0_0</source_block_id>
+ <sink_block_id>blks2_error_rate_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>1</sink_key>
+ </connection>
</flow_graph>
diff --git a/gr-trellis/examples/grc/turbo_equalization.grc b/gr-trellis/examples/grc/turbo_equalization.grc
new file mode 100644
index 0000000000..c83c59db20
--- /dev/null
+++ b/gr-trellis/examples/grc/turbo_equalization.grc
@@ -0,0 +1,2766 @@
+<?xml version='1.0' encoding='ASCII'?>
+<?grc format='1' created='3.7.6'?>
+<flow_graph>
+ <timestamp>Wed Oct 1 11:04:18 2014</timestamp>
+ <block>
+ <key>options</key>
+ <param>
+ <key>id</key>
+ <value>turbo_equalization</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>title</key>
+ <value>Hard/Soft/Turbo Equalization</value>
+ </param>
+ <param>
+ <key>author</key>
+ <value>AA</value>
+ </param>
+ <param>
+ <key>description</key>
+ <value>gnuradio flow graph</value>
+ </param>
+ <param>
+ <key>window_size</key>
+ <value>2048, 3048</value>
+ </param>
+ <param>
+ <key>generate_options</key>
+ <value>wx_gui</value>
+ </param>
+ <param>
+ <key>category</key>
+ <value>Custom</value>
+ </param>
+ <param>
+ <key>run_options</key>
+ <value>prompt</value>
+ </param>
+ <param>
+ <key>run</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>max_nouts</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>realtime_scheduling</key>
+ <value></value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(10, 10)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>variable</key>
+ <param>
+ <key>id</key>
+ <value>fsm_o</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>value</key>
+ <value>trellis.fsm(prefix+"/awgn1o2_4.fsm")</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(344, 21)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>variable</key>
+ <param>
+ <key>id</key>
+ <value>block_b</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>value</key>
+ <value>bpsym*1000</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(216, 21)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>variable</key>
+ <param>
+ <key>id</key>
+ <value>interleaver</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>value</key>
+ <value>trellis.interleaver(block_b/bpsym,666)</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(528, 117)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>variable</key>
+ <param>
+ <key>id</key>
+ <value>Es</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>value</key>
+ <value>numpy.mean((numpy.square(numpy.abs(tot_mod[1]))))</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(776, 181)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>variable</key>
+ <param>
+ <key>id</key>
+ <value>noisevar</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>value</key>
+ <value>10**(-EsN0_dB/10.0) * Es /2.0</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(1080, 181)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>variable</key>
+ <param>
+ <key>id</key>
+ <value>bpsym</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>value</key>
+ <value>int(round(math.log(fsm_o.I())/math.log(2)))</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(528, 29)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>variable</key>
+ <param>
+ <key>id</key>
+ <value>channel</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>value</key>
+ <value>fu.c_channel</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(320, 205)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>variable</key>
+ <param>
+ <key>id</key>
+ <value>modulation</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>value</key>
+ <value>fu.pam4</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(320, 117)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>variable</key>
+ <param>
+ <key>id</key>
+ <value>R</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>value</key>
+ <value>100e3</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(216, 109)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>variable</key>
+ <param>
+ <key>id</key>
+ <value>tot_mod</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>value</key>
+ <value>fu.make_isi_lookup(modulation,channel,False)</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(320, 381)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>variable</key>
+ <param>
+ <key>id</key>
+ <value>prefix</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>value</key>
+ <value>"@FSM_FILE_INSTALL_DIR@"</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(768, 21)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>variable</key>
+ <param>
+ <key>id</key>
+ <value>fsm_i</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>value</key>
+ <value>trellis.fsm(len(modulation[1]),len(channel))</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(320, 293)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>import</key>
+ <param>
+ <key>id</key>
+ <value>import_0_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>import</key>
+ <value>import gnuradio.trellis.fsm_utils as fu</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(24, 252)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>import</key>
+ <param>
+ <key>id</key>
+ <value>import_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>import</key>
+ <value>import numpy</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(16, 140)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>import</key>
+ <param>
+ <key>id</key>
+ <value>import_0_1</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>import</key>
+ <value>import math</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(24, 188)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>virtual_sink</key>
+ <param>
+ <key>id</key>
+ <value>virtual_sink_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>stream_id</key>
+ <value>observation</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(608, 1076)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>blocks_add_xx</key>
+ <param>
+ <key>id</key>
+ <value>blocks_add_xx_1</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>type</key>
+ <value>float</value>
+ </param>
+ <param>
+ <key>num_inputs</key>
+ <value>2</value>
+ </param>
+ <param>
+ <key>vlen</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(688, 944)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>analog_noise_source_x</key>
+ <param>
+ <key>id</key>
+ <value>analog_noise_source_x_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>type</key>
+ <value>float</value>
+ </param>
+ <param>
+ <key>noise_type</key>
+ <value>analog.GR_GAUSSIAN</value>
+ </param>
+ <param>
+ <key>amp</key>
+ <value>noisevar**0.5</value>
+ </param>
+ <param>
+ <key>seed</key>
+ <value>-42</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(288, 958)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>fir_filter_xxx</key>
+ <param>
+ <key>id</key>
+ <value>fir_filter_xxx_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>type</key>
+ <value>fff</value>
+ </param>
+ <param>
+ <key>decim</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>taps</key>
+ <value>fu.c_channel</value>
+ </param>
+ <param>
+ <key>samp_delay</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(448, 861)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>digital_chunks_to_symbols_xx</key>
+ <param>
+ <key>id</key>
+ <value>digital_chunks_to_symbols_xx_0_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>in_type</key>
+ <value>byte</value>
+ </param>
+ <param>
+ <key>out_type</key>
+ <value>float</value>
+ </param>
+ <param>
+ <key>symbol_table</key>
+ <value>modulation[1]</value>
+ </param>
+ <param>
+ <key>dimension</key>
+ <value>modulation[0]</value>
+ </param>
+ <param>
+ <key>num_ports</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(480, 733)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>trellis_permutation</key>
+ <param>
+ <key>id</key>
+ <value>trellis_permutation_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>type</key>
+ <value>byte</value>
+ </param>
+ <param>
+ <key>interleaver_size</key>
+ <value>interleaver.K()</value>
+ </param>
+ <param>
+ <key>table</key>
+ <value>interleaver.INTER()</value>
+ </param>
+ <param>
+ <key>syms_per_block</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>vlen</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(208, 726)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>virtual_sink</key>
+ <param>
+ <key>id</key>
+ <value>virtual_sink_0_0_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>stream_id</key>
+ <value>info_i</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(968, 572)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>blocks_throttle</key>
+ <param>
+ <key>id</key>
+ <value>blocks_throttle_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>type</key>
+ <value>byte</value>
+ </param>
+ <param>
+ <key>samples_per_second</key>
+ <value>R</value>
+ </param>
+ <param>
+ <key>vlen</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>ignoretag</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(256, 580)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>analog_random_source_x</key>
+ <param>
+ <key>id</key>
+ <value>analog_random_source_x_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>type</key>
+ <value>byte</value>
+ </param>
+ <param>
+ <key>min</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>max</key>
+ <value>2</value>
+ </param>
+ <param>
+ <key>num_samps</key>
+ <value>1007</value>
+ </param>
+ <param>
+ <key>repeat</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(16, 559)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>blocks_pack_k_bits_bb</key>
+ <param>
+ <key>id</key>
+ <value>blocks_pack_k_bits_bb_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>k</key>
+ <value>bpsym</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(440, 580)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>trellis_encoder_xx</key>
+ <param>
+ <key>id</key>
+ <value>trellis_encoder_xx_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>type</key>
+ <value>bb</value>
+ </param>
+ <param>
+ <key>fsm_args</key>
+ <value>fsm_o</value>
+ </param>
+ <param>
+ <key>init_state</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>blockwise</key>
+ <value>False</value>
+ </param>
+ <param>
+ <key>blocklength</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(672, 573)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>virtual_sink</key>
+ <param>
+ <key>id</key>
+ <value>virtual_sink_0_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>stream_id</key>
+ <value>info</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(248, 524)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>virtual_sink</key>
+ <param>
+ <key>id</key>
+ <value>virtual_sink_0_1</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>stream_id</key>
+ <value>estimate</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(864, 1380)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>blocks_unpack_k_bits_bb</key>
+ <param>
+ <key>id</key>
+ <value>blocks_unpack_k_bits_bb_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>k</key>
+ <value>bpsym</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(552, 1380)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>blocks_char_to_float</key>
+ <param>
+ <key>id</key>
+ <value>blocks_char_to_float_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>vlen</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>scale</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(72, 1380)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>trellis_permutation</key>
+ <param>
+ <key>id</key>
+ <value>trellis_permutation_0_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>type</key>
+ <value>byte</value>
+ </param>
+ <param>
+ <key>interleaver_size</key>
+ <value>interleaver.K()</value>
+ </param>
+ <param>
+ <key>table</key>
+ <value>interleaver.DEINTER()</value>
+ </param>
+ <param>
+ <key>syms_per_block</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>vlen</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(568, 1222)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>trellis_viterbi_combined_xx</key>
+ <param>
+ <key>id</key>
+ <value>trellis_viterbi_combined_xx_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>type</key>
+ <value>f</value>
+ </param>
+ <param>
+ <key>out_type</key>
+ <value>b</value>
+ </param>
+ <param>
+ <key>fsm_args</key>
+ <value>fsm_i</value>
+ </param>
+ <param>
+ <key>block_size</key>
+ <value>interleaver.K()</value>
+ </param>
+ <param>
+ <key>init_state</key>
+ <value>-1</value>
+ </param>
+ <param>
+ <key>final_state</key>
+ <value>-1</value>
+ </param>
+ <param>
+ <key>dim</key>
+ <value>tot_mod[0]</value>
+ </param>
+ <param>
+ <key>table</key>
+ <value>tot_mod[1]</value>
+ </param>
+ <param>
+ <key>metric_type</key>
+ <value>digital.TRELLIS_EUCLIDEAN</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(288, 1194)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>virtual_sink</key>
+ <param>
+ <key>id</key>
+ <value>virtual_sink_0_1_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>stream_id</key>
+ <value>estimate_i</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(896, 1228)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>virtual_source</key>
+ <param>
+ <key>id</key>
+ <value>virtual_source_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>stream_id</key>
+ <value>observation</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(40, 1236)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>analog_const_source_x</key>
+ <param>
+ <key>id</key>
+ <value>analog_const_source_x_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>type</key>
+ <value>float</value>
+ </param>
+ <param>
+ <key>const</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(88, 1788)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>trellis_viterbi_combined_xx</key>
+ <param>
+ <key>id</key>
+ <value>trellis_viterbi_combined_xx_1</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>type</key>
+ <value>f</value>
+ </param>
+ <param>
+ <key>out_type</key>
+ <value>b</value>
+ </param>
+ <param>
+ <key>fsm_args</key>
+ <value>fsm_o</value>
+ </param>
+ <param>
+ <key>block_size</key>
+ <value>interleaver.K()</value>
+ </param>
+ <param>
+ <key>init_state</key>
+ <value>-1</value>
+ </param>
+ <param>
+ <key>final_state</key>
+ <value>-1</value>
+ </param>
+ <param>
+ <key>dim</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>table</key>
+ <value>0,1,2,3</value>
+ </param>
+ <param>
+ <key>metric_type</key>
+ <value>digital.TRELLIS_HARD_SYMBOL</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(256, 1338)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>trellis_siso_combined_f</key>
+ <param>
+ <key>id</key>
+ <value>trellis_siso_combined_f_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>fsm_args</key>
+ <value>fsm_i</value>
+ </param>
+ <param>
+ <key>block_size</key>
+ <value>interleaver.K()</value>
+ </param>
+ <param>
+ <key>init_state</key>
+ <value>-1</value>
+ </param>
+ <param>
+ <key>final_state</key>
+ <value>-1</value>
+ </param>
+ <param>
+ <key>a_post_in</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>a_post_out</key>
+ <value>False</value>
+ </param>
+ <param>
+ <key>siso_type</key>
+ <value>trellis.TRELLIS_MIN_SUM</value>
+ </param>
+ <param>
+ <key>dim</key>
+ <value>tot_mod[0]</value>
+ </param>
+ <param>
+ <key>table</key>
+ <value>tot_mod[1]</value>
+ </param>
+ <param>
+ <key>metric_type</key>
+ <value>trellis.TRELLIS_EUCLIDEAN</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(280, 1765)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>trellis_permutation</key>
+ <param>
+ <key>id</key>
+ <value>trellis_permutation_0_0_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>type</key>
+ <value>float</value>
+ </param>
+ <param>
+ <key>interleaver_size</key>
+ <value>interleaver.K()</value>
+ </param>
+ <param>
+ <key>table</key>
+ <value>interleaver.DEINTER()</value>
+ </param>
+ <param>
+ <key>syms_per_block</key>
+ <value>fsm_o.O()</value>
+ </param>
+ <param>
+ <key>vlen</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(616, 1814)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>trellis_viterbi_x</key>
+ <param>
+ <key>id</key>
+ <value>trellis_viterbi_x_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>type</key>
+ <value>b</value>
+ </param>
+ <param>
+ <key>fsm_args</key>
+ <value>fsm_o</value>
+ </param>
+ <param>
+ <key>block_size</key>
+ <value>interleaver.K()</value>
+ </param>
+ <param>
+ <key>init_state</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>final_state</key>
+ <value>-1</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(288, 2023)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>virtual_source</key>
+ <param>
+ <key>id</key>
+ <value>virtual_source_0_1</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>stream_id</key>
+ <value>observation</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(72, 1860)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>virtual_source</key>
+ <param>
+ <key>id</key>
+ <value>virtual_source_0_1_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>stream_id</key>
+ <value>observation</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(88, 2564)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>blocks_unpack_k_bits_bb</key>
+ <param>
+ <key>id</key>
+ <value>blocks_unpack_k_bits_bb_0_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>k</key>
+ <value>bpsym</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(584, 2044)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>virtual_sink</key>
+ <param>
+ <key>id</key>
+ <value>virtual_sink_0_1_1</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>stream_id</key>
+ <value>estimate1</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(896, 2044)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>virtual_source</key>
+ <param>
+ <key>id</key>
+ <value>virtual_source_0_0_0_0_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>stream_id</key>
+ <value>estimate1</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(144, 2284)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>virtual_source</key>
+ <param>
+ <key>id</key>
+ <value>virtual_source_0_0_1_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>stream_id</key>
+ <value>info</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(152, 2188)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>virtual_source</key>
+ <param>
+ <key>id</key>
+ <value>virtual_source_0_0_1_0_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>stream_id</key>
+ <value>info</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(176, 2732)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>virtual_source</key>
+ <param>
+ <key>id</key>
+ <value>virtual_source_0_0_0_0_0_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>stream_id</key>
+ <value>estimate2</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(168, 2828)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>virtual_source</key>
+ <param>
+ <key>id</key>
+ <value>virtual_source_0_0_1</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>stream_id</key>
+ <value>info</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(80, 1556)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>virtual_source</key>
+ <param>
+ <key>id</key>
+ <value>virtual_source_0_0_0_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>stream_id</key>
+ <value>estimate</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(72, 1652)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>wxgui_numbersink2</key>
+ <param>
+ <key>id</key>
+ <value>wxgui_numbersink2_3_0_0_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>type</key>
+ <value>float</value>
+ </param>
+ <param>
+ <key>title</key>
+ <value>BER_hard</value>
+ </param>
+ <param>
+ <key>units</key>
+ <value>BER</value>
+ </param>
+ <param>
+ <key>samp_rate</key>
+ <value>R</value>
+ </param>
+ <param>
+ <key>min_value</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>max_value</key>
+ <value>1.0</value>
+ </param>
+ <param>
+ <key>factor</key>
+ <value>1.0</value>
+ </param>
+ <param>
+ <key>decimal_places</key>
+ <value>6</value>
+ </param>
+ <param>
+ <key>ref_level</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>number_rate</key>
+ <value>15</value>
+ </param>
+ <param>
+ <key>peak_hold</key>
+ <value>False</value>
+ </param>
+ <param>
+ <key>average</key>
+ <value>False</value>
+ </param>
+ <param>
+ <key>avg_alpha</key>
+ <value>0.001</value>
+ </param>
+ <param>
+ <key>show_gauge</key>
+ <value>False</value>
+ </param>
+ <param>
+ <key>win_size</key>
+ <value></value>
+ </param>
+ <param>
+ <key>grid_pos</key>
+ <value></value>
+ </param>
+ <param>
+ <key>notebook</key>
+ <value></value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(504, 1549)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>wxgui_numbersink2</key>
+ <param>
+ <key>id</key>
+ <value>wxgui_numbersink2_3_0_0_0_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>type</key>
+ <value>float</value>
+ </param>
+ <param>
+ <key>title</key>
+ <value>BER_soft</value>
+ </param>
+ <param>
+ <key>units</key>
+ <value>BER</value>
+ </param>
+ <param>
+ <key>samp_rate</key>
+ <value>R</value>
+ </param>
+ <param>
+ <key>min_value</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>max_value</key>
+ <value>1.0</value>
+ </param>
+ <param>
+ <key>factor</key>
+ <value>1.0</value>
+ </param>
+ <param>
+ <key>decimal_places</key>
+ <value>6</value>
+ </param>
+ <param>
+ <key>ref_level</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>number_rate</key>
+ <value>15</value>
+ </param>
+ <param>
+ <key>peak_hold</key>
+ <value>False</value>
+ </param>
+ <param>
+ <key>average</key>
+ <value>False</value>
+ </param>
+ <param>
+ <key>avg_alpha</key>
+ <value>0.001</value>
+ </param>
+ <param>
+ <key>show_gauge</key>
+ <value>False</value>
+ </param>
+ <param>
+ <key>win_size</key>
+ <value></value>
+ </param>
+ <param>
+ <key>grid_pos</key>
+ <value></value>
+ </param>
+ <param>
+ <key>notebook</key>
+ <value></value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(576, 2181)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>wxgui_numbersink2</key>
+ <param>
+ <key>id</key>
+ <value>wxgui_numbersink2_3_0_0_0_0_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>type</key>
+ <value>float</value>
+ </param>
+ <param>
+ <key>title</key>
+ <value>BER_turbo</value>
+ </param>
+ <param>
+ <key>units</key>
+ <value>BER</value>
+ </param>
+ <param>
+ <key>samp_rate</key>
+ <value>R</value>
+ </param>
+ <param>
+ <key>min_value</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>max_value</key>
+ <value>1.0</value>
+ </param>
+ <param>
+ <key>factor</key>
+ <value>1.0</value>
+ </param>
+ <param>
+ <key>decimal_places</key>
+ <value>6</value>
+ </param>
+ <param>
+ <key>ref_level</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>number_rate</key>
+ <value>15</value>
+ </param>
+ <param>
+ <key>peak_hold</key>
+ <value>False</value>
+ </param>
+ <param>
+ <key>average</key>
+ <value>False</value>
+ </param>
+ <param>
+ <key>avg_alpha</key>
+ <value>0.001</value>
+ </param>
+ <param>
+ <key>show_gauge</key>
+ <value>False</value>
+ </param>
+ <param>
+ <key>win_size</key>
+ <value></value>
+ </param>
+ <param>
+ <key>grid_pos</key>
+ <value></value>
+ </param>
+ <param>
+ <key>notebook</key>
+ <value></value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(600, 2725)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>trellis_sccc_decoder_combined_xx</key>
+ <param>
+ <key>id</key>
+ <value>trellis_sccc_decoder_combined_xx_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>type</key>
+ <value>f</value>
+ </param>
+ <param>
+ <key>out_type</key>
+ <value>b</value>
+ </param>
+ <param>
+ <key>o_fsm_args</key>
+ <value>fsm_o</value>
+ </param>
+ <param>
+ <key>o_init_state</key>
+ <value>-1</value>
+ </param>
+ <param>
+ <key>o_final_state</key>
+ <value>-1</value>
+ </param>
+ <param>
+ <key>i_fsm_args</key>
+ <value>fsm_i</value>
+ </param>
+ <param>
+ <key>i_init_state</key>
+ <value>-1</value>
+ </param>
+ <param>
+ <key>i_final_state</key>
+ <value>-1</value>
+ </param>
+ <param>
+ <key>interleaver</key>
+ <value>interleaver</value>
+ </param>
+ <param>
+ <key>block_size</key>
+ <value>interleaver.K()</value>
+ </param>
+ <param>
+ <key>iterations</key>
+ <value>5</value>
+ </param>
+ <param>
+ <key>dim</key>
+ <value>tot_mod[0]</value>
+ </param>
+ <param>
+ <key>table</key>
+ <value>tot_mod[1]</value>
+ </param>
+ <param>
+ <key>metric_type</key>
+ <value>digital.TRELLIS_EUCLIDEAN</value>
+ </param>
+ <param>
+ <key>siso_type</key>
+ <value>trellis.TRELLIS_MIN_SUM</value>
+ </param>
+ <param>
+ <key>scaling</key>
+ <value>1.0</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(456, 2481)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>blks2_error_rate</key>
+ <param>
+ <key>id</key>
+ <value>blks2_error_rate_0_0_0_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>type</key>
+ <value>'BER'</value>
+ </param>
+ <param>
+ <key>win_size</key>
+ <value>block_b*100</value>
+ </param>
+ <param>
+ <key>bits_per_symbol</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(408, 2766)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>blks2_error_rate</key>
+ <param>
+ <key>id</key>
+ <value>blks2_error_rate_0_0_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>type</key>
+ <value>'BER'</value>
+ </param>
+ <param>
+ <key>win_size</key>
+ <value>block_b*100</value>
+ </param>
+ <param>
+ <key>bits_per_symbol</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(384, 2230)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>blks2_error_rate</key>
+ <param>
+ <key>id</key>
+ <value>blks2_error_rate_0_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>type</key>
+ <value>'BER'</value>
+ </param>
+ <param>
+ <key>win_size</key>
+ <value>block_b*100</value>
+ </param>
+ <param>
+ <key>bits_per_symbol</key>
+ <value>1</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(312, 1598)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>variable_slider</key>
+ <param>
+ <key>id</key>
+ <value>EsN0_dB</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>label</key>
+ <value>Es/N0 (dB)</value>
+ </param>
+ <param>
+ <key>value</key>
+ <value>13.0</value>
+ </param>
+ <param>
+ <key>min</key>
+ <value>-10</value>
+ </param>
+ <param>
+ <key>max</key>
+ <value>30</value>
+ </param>
+ <param>
+ <key>num_steps</key>
+ <value>1000</value>
+ </param>
+ <param>
+ <key>style</key>
+ <value>wx.SL_HORIZONTAL</value>
+ </param>
+ <param>
+ <key>converver</key>
+ <value>float_converter</value>
+ </param>
+ <param>
+ <key>grid_pos</key>
+ <value></value>
+ </param>
+ <param>
+ <key>notebook</key>
+ <value></value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(936, 129)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>blocks_unpack_k_bits_bb</key>
+ <param>
+ <key>id</key>
+ <value>blocks_unpack_k_bits_bb_0_0_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>k</key>
+ <value>bpsym</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(720, 2572)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>virtual_sink</key>
+ <param>
+ <key>id</key>
+ <value>virtual_sink_0_1_1_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>stream_id</key>
+ <value>estimate2</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(920, 2572)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>note</key>
+ <param>
+ <key>id</key>
+ <value>note_0_1</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>note</key>
+ <value>This is the full-fledged turbo equalizer/decoder</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(1144, 2572)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>note</key>
+ <param>
+ <key>id</key>
+ <value>note_0_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>note</key>
+ <value>This is a better soft-equalizer/Viterbi decoder</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(1016, 1908)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>note</key>
+ <param>
+ <key>id</key>
+ <value>note_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>note</key>
+ <value>This is the simplest hard Viterbi equalizer/hard Viterbi decoder</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(1096, 1316)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <connection>
+ <source_block_id>analog_random_source_x_0</source_block_id>
+ <sink_block_id>virtual_sink_0_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>analog_random_source_x_0</source_block_id>
+ <sink_block_id>blocks_throttle_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>analog_noise_source_x_0</source_block_id>
+ <sink_block_id>blocks_add_xx_1</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>1</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>blocks_add_xx_1</source_block_id>
+ <sink_block_id>virtual_sink_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>digital_chunks_to_symbols_xx_0_0</source_block_id>
+ <sink_block_id>fir_filter_xxx_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>fir_filter_xxx_0</source_block_id>
+ <sink_block_id>blocks_add_xx_1</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>blocks_throttle_0</source_block_id>
+ <sink_block_id>blocks_pack_k_bits_bb_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>blocks_pack_k_bits_bb_0</source_block_id>
+ <sink_block_id>trellis_encoder_xx_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>trellis_encoder_xx_0</source_block_id>
+ <sink_block_id>trellis_permutation_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>trellis_permutation_0</source_block_id>
+ <sink_block_id>digital_chunks_to_symbols_xx_0_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>trellis_encoder_xx_0</source_block_id>
+ <sink_block_id>virtual_sink_0_0_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>blocks_char_to_float_0</source_block_id>
+ <sink_block_id>trellis_viterbi_combined_xx_1</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>trellis_permutation_0_0</source_block_id>
+ <sink_block_id>blocks_char_to_float_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>trellis_permutation_0_0</source_block_id>
+ <sink_block_id>virtual_sink_0_1_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>blocks_unpack_k_bits_bb_0</source_block_id>
+ <sink_block_id>virtual_sink_0_1</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>trellis_viterbi_combined_xx_1</source_block_id>
+ <sink_block_id>blocks_unpack_k_bits_bb_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>trellis_viterbi_combined_xx_0</source_block_id>
+ <sink_block_id>trellis_permutation_0_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>virtual_source_0</source_block_id>
+ <sink_block_id>trellis_viterbi_combined_xx_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>blocks_unpack_k_bits_bb_0_0</source_block_id>
+ <sink_block_id>virtual_sink_0_1_1</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>virtual_source_0_1</source_block_id>
+ <sink_block_id>trellis_siso_combined_f_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>1</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>analog_const_source_x_0</source_block_id>
+ <sink_block_id>trellis_siso_combined_f_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>trellis_siso_combined_f_0</source_block_id>
+ <sink_block_id>trellis_permutation_0_0_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>trellis_permutation_0_0_0</source_block_id>
+ <sink_block_id>trellis_viterbi_x_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>trellis_viterbi_x_0</source_block_id>
+ <sink_block_id>blocks_unpack_k_bits_bb_0_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>virtual_source_0_1_0</source_block_id>
+ <sink_block_id>trellis_sccc_decoder_combined_xx_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>blocks_unpack_k_bits_bb_0_0_0</source_block_id>
+ <sink_block_id>virtual_sink_0_1_1_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>trellis_sccc_decoder_combined_xx_0</source_block_id>
+ <sink_block_id>blocks_unpack_k_bits_bb_0_0_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>blks2_error_rate_0_0_0</source_block_id>
+ <sink_block_id>wxgui_numbersink2_3_0_0_0_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>virtual_source_0_0_1_0</source_block_id>
+ <sink_block_id>blks2_error_rate_0_0_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>virtual_source_0_0_0_0_0</source_block_id>
+ <sink_block_id>blks2_error_rate_0_0_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>1</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>blks2_error_rate_0_0_0_0</source_block_id>
+ <sink_block_id>wxgui_numbersink2_3_0_0_0_0_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>virtual_source_0_0_1_0_0</source_block_id>
+ <sink_block_id>blks2_error_rate_0_0_0_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>virtual_source_0_0_0_0_0_0</source_block_id>
+ <sink_block_id>blks2_error_rate_0_0_0_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>1</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>blks2_error_rate_0_0</source_block_id>
+ <sink_block_id>wxgui_numbersink2_3_0_0_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>virtual_source_0_0_1</source_block_id>
+ <sink_block_id>blks2_error_rate_0_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>virtual_source_0_0_0_0</source_block_id>
+ <sink_block_id>blks2_error_rate_0_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>1</sink_key>
+ </connection>
+</flow_graph>
diff --git a/gr-trellis/examples/grc/sccc1.grc b/gr-trellis/examples/grc/viterbi_equalization.grc
index 71b3f76625..2f69ead429 100644
--- a/gr-trellis/examples/grc/sccc1.grc
+++ b/gr-trellis/examples/grc/viterbi_equalization.grc
@@ -1,11 +1,12 @@
<?xml version='1.0' encoding='ASCII'?>
+<?grc format='1' created='3.7.6'?>
<flow_graph>
- <timestamp>Mon Jul 28 14:10:35 2014</timestamp>
+ <timestamp>Wed Oct 1 11:04:18 2014</timestamp>
<block>
<key>options</key>
<param>
<key>id</key>
- <value>sccc1</value>
+ <value>viterbi_equalization</value>
</param>
<param>
<key>_enabled</key>
@@ -13,7 +14,7 @@
</param>
<param>
<key>title</key>
- <value>Serially Concatenated Convolutional Code</value>
+ <value>Viterbi Equalization</value>
</param>
<param>
<key>author</key>
@@ -29,7 +30,7 @@
</param>
<param>
<key>generate_options</key>
- <value>qt_gui</value>
+ <value>wx_gui</value>
</param>
<param>
<key>category</key>
@@ -68,7 +69,7 @@
<key>variable</key>
<param>
<key>id</key>
- <value>prefix</value>
+ <value>noisevar</value>
</param>
<param>
<key>_enabled</key>
@@ -76,7 +77,7 @@
</param>
<param>
<key>value</key>
- <value>"@FSM_FILE_INSTALL_DIR@"</value>
+ <value>10**(-EsN0_dB/10.0) * Es /2.0</value>
</param>
<param>
<key>alias</key>
@@ -84,7 +85,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(513, 10)</value>
+ <value>(872, 157)</value>
</param>
<param>
<key>_rotation</key>
@@ -95,7 +96,7 @@
<key>variable</key>
<param>
<key>id</key>
- <value>block</value>
+ <value>bpsym</value>
</param>
<param>
<key>_enabled</key>
@@ -103,7 +104,7 @@
</param>
<param>
<key>value</key>
- <value>1000</value>
+ <value>int(round(math.log(fsm.I())/math.log(2)))</value>
</param>
<param>
<key>alias</key>
@@ -111,7 +112,34 @@
</param>
<param>
<key>_coordinate</key>
- <value>(441, 10)</value>
+ <value>(528, 13)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>variable</key>
+ <param>
+ <key>id</key>
+ <value>channel</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>value</key>
+ <value>fu.c_channel</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(320, 85)</value>
</param>
<param>
<key>_rotation</key>
@@ -138,7 +166,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(358, 10)</value>
+ <value>(216, 109)</value>
</param>
<param>
<key>_rotation</key>
@@ -149,7 +177,7 @@
<key>variable</key>
<param>
<key>id</key>
- <value>noisevar</value>
+ <value>block</value>
</param>
<param>
<key>_enabled</key>
@@ -157,7 +185,7 @@
</param>
<param>
<key>value</key>
- <value>10**(-snr_db/10)</value>
+ <value>bpsym*1000</value>
</param>
<param>
<key>alias</key>
@@ -165,7 +193,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(279, 10)</value>
+ <value>(216, 21)</value>
</param>
<param>
<key>_rotation</key>
@@ -173,54 +201,161 @@
</param>
</block>
<block>
- <key>analog_random_source_x</key>
+ <key>variable</key>
<param>
<key>id</key>
- <value>analog_random_source_x_0</value>
+ <value>fsm</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>type</key>
- <value>short</value>
+ <key>value</key>
+ <value>trellis.fsm(len(modulation[1]),len(channel))</value>
</param>
<param>
- <key>min</key>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(320, 157)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
<value>0</value>
</param>
+ </block>
+ <block>
+ <key>variable</key>
<param>
- <key>max</key>
- <value>2</value>
+ <key>id</key>
+ <value>tot_mod</value>
</param>
<param>
- <key>num_samps</key>
- <value>1000</value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>repeat</key>
+ <key>value</key>
+ <value>fu.make_isi_lookup(modulation,channel,False)</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(320, 229)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>variable</key>
+ <param>
+ <key>id</key>
+ <value>modulation</value>
+ </param>
+ <param>
+ <key>_enabled</key>
<value>True</value>
</param>
<param>
+ <key>value</key>
+ <value>fu.pam4</value>
+ </param>
+ <param>
<key>alias</key>
<value></value>
</param>
<param>
- <key>affinity</key>
+ <key>_coordinate</key>
+ <value>(320, 21)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>variable</key>
+ <param>
+ <key>id</key>
+ <value>Es</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>value</key>
+ <value>numpy.mean((numpy.square(numpy.abs(tot_mod[1]))))</value>
+ </param>
+ <param>
+ <key>alias</key>
<value></value>
</param>
<param>
- <key>minoutbuf</key>
+ <key>_coordinate</key>
+ <value>(568, 157)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
<value>0</value>
</param>
+ </block>
+ <block>
+ <key>import</key>
+ <param>
+ <key>id</key>
+ <value>import_0_0</value>
+ </param>
<param>
- <key>maxoutbuf</key>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>import</key>
+ <value>import gnuradio.trellis.fsm_utils as fu</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(24, 252)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
<value>0</value>
</param>
+ </block>
+ <block>
+ <key>import</key>
+ <param>
+ <key>id</key>
+ <value>import_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>import</key>
+ <value>import numpy</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
<param>
<key>_coordinate</key>
- <value>(21, 170)</value>
+ <value>(16, 140)</value>
</param>
<param>
<key>_rotation</key>
@@ -228,32 +363,55 @@
</param>
</block>
<block>
- <key>blocks_throttle</key>
+ <key>import</key>
<param>
<key>id</key>
- <value>blocks_throttle_0</value>
+ <value>import_0_1</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>type</key>
- <value>short</value>
+ <key>import</key>
+ <value>import math</value>
</param>
<param>
- <key>samples_per_second</key>
- <value>R</value>
+ <key>alias</key>
+ <value></value>
</param>
<param>
- <key>vlen</key>
- <value>1</value>
+ <key>_coordinate</key>
+ <value>(24, 188)</value>
</param>
<param>
- <key>ignoretag</key>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>blks2_error_rate</key>
+ <param>
+ <key>id</key>
+ <value>blks2_error_rate_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
<value>True</value>
</param>
<param>
+ <key>type</key>
+ <value>'BER'</value>
+ </param>
+ <param>
+ <key>win_size</key>
+ <value>block*100</value>
+ </param>
+ <param>
+ <key>bits_per_symbol</key>
+ <value>1</value>
+ </param>
+ <param>
<key>alias</key>
<value></value>
</param>
@@ -271,7 +429,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(607, 110)</value>
+ <value>(312, 1766)</value>
</param>
<param>
<key>_rotation</key>
@@ -279,10 +437,56 @@
</param>
</block>
<block>
- <key>blocks_add_xx</key>
+ <key>virtual_source</key>
<param>
<key>id</key>
- <value>blocks_add_xx_1</value>
+ <value>virtual_source_0_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>stream_id</key>
+ <value>info</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(80, 1724)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>virtual_source</key>
+ <param>
+ <key>id</key>
+ <value>virtual_source_0_0_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>stream_id</key>
+ <value>estimate</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(72, 1820)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>wxgui_numbersink2</key>
+ <param>
+ <key>id</key>
+ <value>wxgui_numbersink2_3_0_0</value>
</param>
<param>
<key>_enabled</key>
@@ -293,12 +497,68 @@
<value>float</value>
</param>
<param>
- <key>num_inputs</key>
- <value>2</value>
+ <key>title</key>
+ <value>BER</value>
</param>
<param>
- <key>vlen</key>
- <value>1</value>
+ <key>units</key>
+ <value>BER</value>
+ </param>
+ <param>
+ <key>samp_rate</key>
+ <value>R</value>
+ </param>
+ <param>
+ <key>min_value</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>max_value</key>
+ <value>1.0</value>
+ </param>
+ <param>
+ <key>factor</key>
+ <value>1.0</value>
+ </param>
+ <param>
+ <key>decimal_places</key>
+ <value>6</value>
+ </param>
+ <param>
+ <key>ref_level</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>number_rate</key>
+ <value>15</value>
+ </param>
+ <param>
+ <key>peak_hold</key>
+ <value>False</value>
+ </param>
+ <param>
+ <key>average</key>
+ <value>False</value>
+ </param>
+ <param>
+ <key>avg_alpha</key>
+ <value>0.001</value>
+ </param>
+ <param>
+ <key>show_gauge</key>
+ <value>False</value>
+ </param>
+ <param>
+ <key>win_size</key>
+ <value></value>
+ </param>
+ <param>
+ <key>grid_pos</key>
+ <value></value>
+ </param>
+ <param>
+ <key>notebook</key>
+ <value></value>
</param>
<param>
<key>alias</key>
@@ -309,16 +569,81 @@
<value></value>
</param>
<param>
- <key>minoutbuf</key>
+ <key>_coordinate</key>
+ <value>(728, 1709)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
<value>0</value>
</param>
+ </block>
+ <block>
+ <key>note</key>
<param>
- <key>maxoutbuf</key>
+ <key>id</key>
+ <value>note_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>note</key>
+ <value>Substititue the metrics/Viterbi block with Viterbi_combo</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(704, 1468)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
<value>0</value>
</param>
+ </block>
+ <block>
+ <key>virtual_source</key>
+ <param>
+ <key>id</key>
+ <value>virtual_source_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>stream_id</key>
+ <value>observation</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(40, 1236)</value>
+ </param>
+ <param>
+ <key>_rotation</key>
+ <value>0</value>
+ </param>
+ </block>
+ <block>
+ <key>virtual_sink</key>
+ <param>
+ <key>id</key>
+ <value>virtual_sink_0_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>stream_id</key>
+ <value>info</value>
+ </param>
<param>
<key>_coordinate</key>
- <value>(932, 187)</value>
+ <value>(232, 524)</value>
</param>
<param>
<key>_rotation</key>
@@ -326,10 +651,10 @@
</param>
</block>
<block>
- <key>blocks_multiply_xx</key>
+ <key>analog_random_source_x</key>
<param>
<key>id</key>
- <value>blocks_multiply_xx_2_0</value>
+ <value>analog_random_source_x_0</value>
</param>
<param>
<key>_enabled</key>
@@ -337,15 +662,23 @@
</param>
<param>
<key>type</key>
- <value>short</value>
+ <value>byte</value>
</param>
<param>
- <key>num_inputs</key>
+ <key>min</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>max</key>
<value>2</value>
</param>
<param>
- <key>vlen</key>
- <value>1</value>
+ <key>num_samps</key>
+ <value>1007</value>
+ </param>
+ <param>
+ <key>repeat</key>
+ <value>True</value>
</param>
<param>
<key>alias</key>
@@ -365,7 +698,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(233, 480)</value>
+ <value>(16, 559)</value>
</param>
<param>
<key>_rotation</key>
@@ -373,10 +706,10 @@
</param>
</block>
<block>
- <key>blocks_sub_xx</key>
+ <key>blocks_null_sink</key>
<param>
<key>id</key>
- <value>blocks_sub_xx_0</value>
+ <value>blocks_null_sink_1</value>
</param>
<param>
<key>_enabled</key>
@@ -384,7 +717,7 @@
</param>
<param>
<key>type</key>
- <value>short</value>
+ <value>float</value>
</param>
<param>
<key>vlen</key>
@@ -392,7 +725,11 @@
</param>
<param>
<key>num_inputs</key>
- <value>2</value>
+ <value>1</value>
+ </param>
+ <param>
+ <key>bus_conns</key>
+ <value>[[0,],]</value>
</param>
<param>
<key>alias</key>
@@ -403,16 +740,31 @@
<value></value>
</param>
<param>
- <key>minoutbuf</key>
- <value>0</value>
+ <key>_coordinate</key>
+ <value>(800, 1008)</value>
</param>
<param>
- <key>maxoutbuf</key>
+ <key>_rotation</key>
<value>0</value>
</param>
+ </block>
+ <block>
+ <key>virtual_sink</key>
+ <param>
+ <key>id</key>
+ <value>virtual_sink_0</value>
+ </param>
+ <param>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>stream_id</key>
+ <value>observation</value>
+ </param>
<param>
<key>_coordinate</key>
- <value>(58, 486)</value>
+ <value>(608, 1076)</value>
</param>
<param>
<key>_rotation</key>
@@ -420,24 +772,32 @@
</param>
</block>
<block>
- <key>blocks_short_to_float</key>
+ <key>fir_filter_xxx</key>
<param>
<key>id</key>
- <value>blocks_short_to_float_1_0</value>
+ <value>fir_filter_xxx_0</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>vlen</key>
- <value>1</value>
+ <key>type</key>
+ <value>fff</value>
</param>
<param>
- <key>scale</key>
+ <key>decim</key>
<value>1</value>
</param>
<param>
+ <key>taps</key>
+ <value>fu.c_channel</value>
+ </param>
+ <param>
+ <key>samp_delay</key>
+ <value>0</value>
+ </param>
+ <param>
<key>alias</key>
<value></value>
</param>
@@ -455,7 +815,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(376, 498)</value>
+ <value>(904, 613)</value>
</param>
<param>
<key>_rotation</key>
@@ -463,10 +823,10 @@
</param>
</block>
<block>
- <key>trellis_metrics_x</key>
+ <key>blocks_add_xx</key>
<param>
<key>id</key>
- <value>trellis_metrics_x_0</value>
+ <value>blocks_add_xx_1</value>
</param>
<param>
<key>_enabled</key>
@@ -474,25 +834,17 @@
</param>
<param>
<key>type</key>
- <value>f</value>
+ <value>float</value>
</param>
<param>
- <key>card</key>
- <value>8</value>
+ <key>num_inputs</key>
+ <value>2</value>
</param>
<param>
- <key>dim</key>
+ <key>vlen</key>
<value>1</value>
</param>
<param>
- <key>table</key>
- <value>-7, -5, -3, -1, 1, 3, 5, 7</value>
- </param>
- <param>
- <key>metric_type</key>
- <value>digital.TRELLIS_EUCLIDEAN</value>
- </param>
- <param>
<key>alias</key>
<value></value>
</param>
@@ -510,7 +862,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(63, 328)</value>
+ <value>(688, 944)</value>
</param>
<param>
<key>_rotation</key>
@@ -525,7 +877,7 @@
</param>
<param>
<key>_enabled</key>
- <value>True</value>
+ <value>False</value>
</param>
<param>
<key>in_type</key>
@@ -537,11 +889,11 @@
</param>
<param>
<key>symbol_table</key>
- <value>-7,-5,-3,-1,1,3,5,7</value>
+ <value>tot_mod[1]</value>
</param>
<param>
<key>dimension</key>
- <value>1</value>
+ <value>tot_mod[0]</value>
</param>
<param>
<key>num_ports</key>
@@ -565,7 +917,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(607, 175)</value>
+ <value>(944, 461)</value>
</param>
<param>
<key>_rotation</key>
@@ -592,7 +944,7 @@
</param>
<param>
<key>amp</key>
- <value>noisevar</value>
+ <value>noisevar**0.5</value>
</param>
<param>
<key>seed</key>
@@ -616,7 +968,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(606, 242)</value>
+ <value>(288, 958)</value>
</param>
<param>
<key>_rotation</key>
@@ -624,213 +976,198 @@
</param>
</block>
<block>
- <key>qtgui_number_sink</key>
+ <key>trellis_metrics_x</key>
<param>
<key>id</key>
- <value>qtgui_number_sink_0</value>
+ <value>trellis_metrics_x_0</value>
</param>
<param>
<key>_enabled</key>
- <value>True</value>
- </param>
- <param>
- <key>name</key>
- <value>""</value>
+ <value>False</value>
</param>
<param>
<key>type</key>
- <value>float</value>
- </param>
- <param>
- <key>autoscale</key>
- <value>False</value>
+ <value>f</value>
</param>
<param>
- <key>avg</key>
- <value>0.001</value>
+ <key>card</key>
+ <value>fsm.O()</value>
</param>
<param>
- <key>graph_type</key>
- <value>qtgui.NUM_GRAPH_HORIZ</value>
+ <key>dim</key>
+ <value>tot_mod[0]</value>
</param>
<param>
- <key>nconnections</key>
- <value>1</value>
+ <key>table</key>
+ <value>tot_mod[1]</value>
</param>
<param>
- <key>min</key>
- <value>0</value>
+ <key>metric_type</key>
+ <value>digital.TRELLIS_EUCLIDEAN</value>
</param>
<param>
- <key>max</key>
- <value>1</value>
+ <key>alias</key>
+ <value></value>
</param>
<param>
- <key>update_time</key>
- <value>0.10</value>
+ <key>affinity</key>
+ <value></value>
</param>
<param>
- <key>gui_hint</key>
- <value>1,0,1,1</value>
+ <key>minoutbuf</key>
+ <value>0</value>
</param>
<param>
- <key>label1</key>
- <value></value>
+ <key>maxoutbuf</key>
+ <value>0</value>
</param>
<param>
- <key>unit1</key>
- <value></value>
+ <key>_coordinate</key>
+ <value>(272, 1271)</value>
</param>
<param>
- <key>color1</key>
- <value>("black", "black")</value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>variable_slider</key>
<param>
- <key>factor1</key>
- <value>1</value>
+ <key>id</key>
+ <value>EsN0_dB</value>
</param>
<param>
- <key>label2</key>
- <value></value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>unit2</key>
- <value></value>
+ <key>label</key>
+ <value>Es/N0 (dB)</value>
</param>
<param>
- <key>color2</key>
- <value>("black", "black")</value>
+ <key>value</key>
+ <value>20.0</value>
</param>
<param>
- <key>factor2</key>
- <value>1</value>
+ <key>min</key>
+ <value>-10</value>
</param>
<param>
- <key>label3</key>
- <value></value>
+ <key>max</key>
+ <value>30</value>
</param>
<param>
- <key>unit3</key>
- <value></value>
+ <key>num_steps</key>
+ <value>1000</value>
</param>
<param>
- <key>color3</key>
- <value>("black", "black")</value>
+ <key>style</key>
+ <value>wx.SL_HORIZONTAL</value>
</param>
<param>
- <key>factor3</key>
- <value>1</value>
+ <key>converver</key>
+ <value>float_converter</value>
</param>
<param>
- <key>label4</key>
+ <key>grid_pos</key>
<value></value>
</param>
<param>
- <key>unit4</key>
+ <key>notebook</key>
<value></value>
</param>
<param>
- <key>color4</key>
- <value>("black", "black")</value>
- </param>
- <param>
- <key>factor4</key>
- <value>1</value>
- </param>
- <param>
- <key>label5</key>
+ <key>alias</key>
<value></value>
</param>
<param>
- <key>unit5</key>
- <value></value>
+ <key>_coordinate</key>
+ <value>(728, 105)</value>
</param>
<param>
- <key>color5</key>
- <value>("black", "black")</value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>blocks_throttle</key>
<param>
- <key>factor5</key>
- <value>1</value>
+ <key>id</key>
+ <value>blocks_throttle_0</value>
</param>
<param>
- <key>label6</key>
- <value></value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>unit6</key>
- <value></value>
+ <key>type</key>
+ <value>byte</value>
</param>
<param>
- <key>color6</key>
- <value>("black", "black")</value>
+ <key>samples_per_second</key>
+ <value>R</value>
</param>
<param>
- <key>factor6</key>
+ <key>vlen</key>
<value>1</value>
</param>
<param>
- <key>label7</key>
- <value></value>
+ <key>ignoretag</key>
+ <value>True</value>
</param>
<param>
- <key>unit7</key>
+ <key>alias</key>
<value></value>
</param>
<param>
- <key>color7</key>
- <value>("black", "black")</value>
- </param>
- <param>
- <key>factor7</key>
- <value>1</value>
- </param>
- <param>
- <key>label8</key>
+ <key>affinity</key>
<value></value>
</param>
<param>
- <key>unit8</key>
- <value></value>
+ <key>minoutbuf</key>
+ <value>0</value>
</param>
<param>
- <key>color8</key>
- <value>("black", "black")</value>
+ <key>maxoutbuf</key>
+ <value>0</value>
</param>
<param>
- <key>factor8</key>
- <value>1</value>
+ <key>_coordinate</key>
+ <value>(240, 580)</value>
</param>
<param>
- <key>label9</key>
- <value></value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>digital_chunks_to_symbols_xx</key>
<param>
- <key>unit9</key>
- <value></value>
+ <key>id</key>
+ <value>digital_chunks_to_symbols_xx_0_0</value>
</param>
<param>
- <key>color9</key>
- <value>("black", "black")</value>
+ <key>_enabled</key>
+ <value>True</value>
</param>
<param>
- <key>factor9</key>
- <value>1</value>
+ <key>in_type</key>
+ <value>byte</value>
</param>
<param>
- <key>label10</key>
- <value></value>
+ <key>out_type</key>
+ <value>float</value>
</param>
<param>
- <key>unit10</key>
- <value></value>
+ <key>symbol_table</key>
+ <value>modulation[1]</value>
</param>
<param>
- <key>color10</key>
- <value>("black", "black")</value>
+ <key>dimension</key>
+ <value>modulation[0]</value>
</param>
<param>
- <key>factor10</key>
+ <key>num_ports</key>
<value>1</value>
</param>
<param>
@@ -842,8 +1179,16 @@
<value></value>
</param>
<param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
<key>_coordinate</key>
- <value>(609, 482)</value>
+ <value>(672, 613)</value>
</param>
<param>
<key>_rotation</key>
@@ -851,69 +1196,88 @@
</param>
</block>
<block>
- <key>variable_qtgui_range</key>
+ <key>virtual_sink</key>
<param>
<key>id</key>
- <value>snr_db</value>
+ <value>virtual_sink_0_1</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>label</key>
- <value>SNR (dB)</value>
+ <key>stream_id</key>
+ <value>estimate</value>
</param>
<param>
- <key>value</key>
- <value>5</value>
+ <key>_coordinate</key>
+ <value>(944, 1436)</value>
</param>
<param>
- <key>start</key>
- <value>-10</value>
+ <key>_rotation</key>
+ <value>0</value>
</param>
+ </block>
+ <block>
+ <key>trellis_viterbi_x</key>
<param>
- <key>stop</key>
- <value>10</value>
+ <key>id</key>
+ <value>trellis_viterbi_x_0</value>
</param>
<param>
- <key>step</key>
- <value>0.01</value>
+ <key>_enabled</key>
+ <value>False</value>
</param>
<param>
- <key>widget</key>
- <value>counter_slider</value>
+ <key>type</key>
+ <value>b</value>
</param>
<param>
- <key>orient</key>
- <value>Qt.Horizontal</value>
+ <key>fsm_args</key>
+ <value>fsm</value>
</param>
<param>
- <key>min_len</key>
- <value>200</value>
+ <key>block_size</key>
+ <value>block/bpsym</value>
</param>
<param>
- <key>gui_hint</key>
- <value></value>
+ <key>init_state</key>
+ <value>-1</value>
+ </param>
+ <param>
+ <key>final_state</key>
+ <value>-1</value>
</param>
<param>
<key>alias</key>
<value></value>
</param>
<param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
<key>_coordinate</key>
- <value>(177, 10)</value>
+ <value>(480, 1271)</value>
</param>
<param>
<key>_rotation</key>
- <value>180</value>
+ <value>0</value>
</param>
</block>
<block>
- <key>trellis_sccc_encoder_xx</key>
+ <key>trellis_viterbi_combined_xx</key>
<param>
<key>id</key>
- <value>trellis_sccc_encoder_xx_0</value>
+ <value>trellis_viterbi_combined_xx_0</value>
</param>
<param>
<key>_enabled</key>
@@ -921,31 +1285,78 @@
</param>
<param>
<key>type</key>
- <value>ss</value>
+ <value>f</value>
</param>
<param>
- <key>o_fsm_args</key>
- <value>prefix+"/awgn1o2_4.fsm"</value>
+ <key>out_type</key>
+ <value>b</value>
</param>
<param>
- <key>o_init_state</key>
+ <key>fsm_args</key>
+ <value>fsm</value>
+ </param>
+ <param>
+ <key>block_size</key>
+ <value>block/bpsym</value>
+ </param>
+ <param>
+ <key>init_state</key>
+ <value>-1</value>
+ </param>
+ <param>
+ <key>final_state</key>
+ <value>-1</value>
+ </param>
+ <param>
+ <key>dim</key>
+ <value>tot_mod[0]</value>
+ </param>
+ <param>
+ <key>table</key>
+ <value>tot_mod[1]</value>
+ </param>
+ <param>
+ <key>metric_type</key>
+ <value>digital.TRELLIS_EUCLIDEAN</value>
+ </param>
+ <param>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
+ </param>
+ <param>
+ <key>minoutbuf</key>
<value>0</value>
</param>
<param>
- <key>i_fsm_args</key>
- <value>prefix+"/awgn2o3_4.fsm"</value>
+ <key>maxoutbuf</key>
+ <value>0</value>
+ </param>
+ <param>
+ <key>_coordinate</key>
+ <value>(352, 1410)</value>
</param>
<param>
- <key>i_init_state</key>
+ <key>_rotation</key>
<value>0</value>
</param>
+ </block>
+ <block>
+ <key>blocks_unpack_k_bits_bb</key>
<param>
- <key>interleaver_args</key>
- <value>trellis.interleaver(block,666)</value>
+ <key>id</key>
+ <value>blocks_unpack_k_bits_bb_0</value>
</param>
<param>
- <key>bl</key>
- <value>block</value>
+ <key>_enabled</key>
+ <value>True</value>
+ </param>
+ <param>
+ <key>k</key>
+ <value>bpsym</value>
</param>
<param>
<key>alias</key>
@@ -965,7 +1376,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(294, 154)</value>
+ <value>(728, 1364)</value>
</param>
<param>
<key>_rotation</key>
@@ -973,58 +1384,65 @@
</param>
</block>
<block>
- <key>trellis_sccc_decoder_x</key>
+ <key>blocks_pack_k_bits_bb</key>
<param>
<key>id</key>
- <value>trellis_sccc_decoder_x_0</value>
+ <value>blocks_pack_k_bits_bb_0</value>
</param>
<param>
<key>_enabled</key>
<value>True</value>
</param>
<param>
- <key>out_type</key>
- <value>s</value>
+ <key>k</key>
+ <value>bpsym</value>
</param>
<param>
- <key>o_fsm_args</key>
- <value>prefix+"/awgn1o2_4.fsm"</value>
+ <key>alias</key>
+ <value></value>
+ </param>
+ <param>
+ <key>affinity</key>
+ <value></value>
</param>
<param>
- <key>o_init_state</key>
+ <key>minoutbuf</key>
<value>0</value>
</param>
<param>
- <key>o_final_state</key>
- <value>-1</value>
+ <key>maxoutbuf</key>
+ <value>0</value>
</param>
<param>
- <key>i_fsm_args</key>
- <value>prefix+"/awgn2o3_4.fsm"</value>
+ <key>_coordinate</key>
+ <value>(456, 572)</value>
</param>
<param>
- <key>i_init_state</key>
+ <key>_rotation</key>
<value>0</value>
</param>
+ </block>
+ <block>
+ <key>trellis_encoder_xx</key>
<param>
- <key>i_final_state</key>
- <value>-1</value>
+ <key>id</key>
+ <value>trellis_encoder_xx_0</value>
</param>
<param>
- <key>interleaver</key>
- <value>trellis.interleaver(block,666)</value>
+ <key>_enabled</key>
+ <value>False</value>
</param>
<param>
- <key>block_size</key>
- <value>block</value>
+ <key>type</key>
+ <value>bs</value>
</param>
<param>
- <key>iterations</key>
- <value>10</value>
+ <key>fsm_args</key>
+ <value>fsm</value>
</param>
<param>
- <key>siso_type</key>
- <value>trellis.TRELLIS_MIN_SUM</value>
+ <key>init_state</key>
+ <value>0</value>
</param>
<param>
<key>alias</key>
@@ -1044,7 +1462,7 @@
</param>
<param>
<key>_coordinate</key>
- <value>(292, 280)</value>
+ <value>(672, 461)</value>
</param>
<param>
<key>_rotation</key>
@@ -1052,44 +1470,80 @@
</param>
</block>
<connection>
- <source_block_id>analog_random_source_x_0</source_block_id>
- <sink_block_id>blocks_sub_xx_0</sink_block_id>
+ <source_block_id>blks2_error_rate_0</source_block_id>
+ <sink_block_id>wxgui_numbersink2_3_0_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>virtual_source_0_0</source_block_id>
+ <sink_block_id>blks2_error_rate_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>virtual_source_0_0_0</source_block_id>
+ <sink_block_id>blks2_error_rate_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>1</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>virtual_source_0</source_block_id>
+ <sink_block_id>trellis_metrics_x_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>trellis_metrics_x_0</source_block_id>
+ <sink_block_id>trellis_viterbi_x_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>virtual_source_0</source_block_id>
+ <sink_block_id>trellis_viterbi_combined_xx_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
<source_block_id>analog_random_source_x_0</source_block_id>
- <sink_block_id>trellis_sccc_encoder_xx_0</sink_block_id>
+ <sink_block_id>virtual_sink_0_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>trellis_sccc_encoder_xx_0</source_block_id>
+ <source_block_id>analog_random_source_x_0</source_block_id>
<sink_block_id>blocks_throttle_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
+ <source_block_id>analog_noise_source_x_0</source_block_id>
+ <sink_block_id>blocks_add_xx_1</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>1</sink_key>
+ </connection>
+ <connection>
<source_block_id>blocks_add_xx_1</source_block_id>
- <sink_block_id>trellis_metrics_x_0</sink_block_id>
+ <sink_block_id>blocks_null_sink_1</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>trellis_metrics_x_0</source_block_id>
- <sink_block_id>trellis_sccc_decoder_x_0</sink_block_id>
+ <source_block_id>blocks_add_xx_1</source_block_id>
+ <sink_block_id>virtual_sink_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>trellis_sccc_decoder_x_0</source_block_id>
- <sink_block_id>blocks_sub_xx_0</sink_block_id>
+ <source_block_id>digital_chunks_to_symbols_xx_0_0</source_block_id>
+ <sink_block_id>fir_filter_xxx_0</sink_block_id>
<source_key>0</source_key>
- <sink_key>1</sink_key>
+ <sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_throttle_0</source_block_id>
- <sink_block_id>digital_chunks_to_symbols_xx_0</sink_block_id>
+ <source_block_id>fir_filter_xxx_0</source_block_id>
+ <sink_block_id>blocks_add_xx_1</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
@@ -1100,32 +1554,44 @@
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>analog_noise_source_x_0</source_block_id>
- <sink_block_id>blocks_add_xx_1</sink_block_id>
+ <source_block_id>trellis_encoder_xx_0</source_block_id>
+ <sink_block_id>digital_chunks_to_symbols_xx_0</sink_block_id>
<source_key>0</source_key>
- <sink_key>1</sink_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>blocks_throttle_0</source_block_id>
+ <sink_block_id>blocks_pack_k_bits_bb_0</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_sub_xx_0</source_block_id>
- <sink_block_id>blocks_multiply_xx_2_0</sink_block_id>
+ <source_block_id>blocks_pack_k_bits_bb_0</source_block_id>
+ <sink_block_id>digital_chunks_to_symbols_xx_0_0</sink_block_id>
<source_key>0</source_key>
- <sink_key>1</sink_key>
+ <sink_key>0</sink_key>
+ </connection>
+ <connection>
+ <source_block_id>blocks_unpack_k_bits_bb_0</source_block_id>
+ <sink_block_id>virtual_sink_0_1</sink_block_id>
+ <source_key>0</source_key>
+ <sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_sub_xx_0</source_block_id>
- <sink_block_id>blocks_multiply_xx_2_0</sink_block_id>
+ <source_block_id>trellis_viterbi_x_0</source_block_id>
+ <sink_block_id>blocks_unpack_k_bits_bb_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_multiply_xx_2_0</source_block_id>
- <sink_block_id>blocks_short_to_float_1_0</sink_block_id>
+ <source_block_id>trellis_viterbi_combined_xx_0</source_block_id>
+ <sink_block_id>blocks_unpack_k_bits_bb_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
<connection>
- <source_block_id>blocks_short_to_float_1_0</source_block_id>
- <sink_block_id>qtgui_number_sink_0</sink_block_id>
+ <source_block_id>blocks_pack_k_bits_bb_0</source_block_id>
+ <sink_block_id>trellis_encoder_xx_0</sink_block_id>
<source_key>0</source_key>
<sink_key>0</sink_key>
</connection>
diff --git a/gr-trellis/examples/python/CMakeLists.txt b/gr-trellis/examples/python/CMakeLists.txt
index e2c7e70ff7..8a05525bc4 100644
--- a/gr-trellis/examples/python/CMakeLists.txt
+++ b/gr-trellis/examples/python/CMakeLists.txt
@@ -21,18 +21,8 @@ include(GrPython)
GR_PYTHON_INSTALL(
PROGRAMS
- fsm_utils.py
test_tcm.py
- test_tcm_parallel.py
- test_tcm_combined.py
- test_sccc_hard.py
- test_sccc_soft.py
- test_sccc_turbo.py
- test_viterbi_equalization1.py
- test_viterbi_equalization.py
- test_turbo_equalization.py
- test_turbo_equalization1.py
- test_turbo_equalization2.py
+ test_cpm.py
DESTINATION ${GR_PKG_TRELLIS_EXAMPLES_DIR}
COMPONENT "trellis_examples"
)
@@ -45,20 +35,38 @@ install(
install(
FILES
+ fsm_files/awgn1o1_16rsc.fsm
+ fsm_files/awgn1o1_4rsc.fsm
fsm_files/awgn1o2_128.fsm
fsm_files/awgn1o2_16.fsm
+ fsm_files/awgn1o2_16rsc.fsm
fsm_files/awgn1o2_4.fsm
+ fsm_files/awgn1o2_4rsc.fsm
fsm_files/awgn1o2_8.fsm
fsm_files/awgn2o3_16.fsm
+ fsm_files/awgn2o3_16ungerboecka.fsm
+ fsm_files/awgn2o3_16ungerboeck.fsm
+ fsm_files/awgn2o3_32ungerboecka.fsm
+ fsm_files/awgn2o3_32ungerboeck.fsm
fsm_files/awgn2o3_4.fsm
fsm_files/awgn2o3_4_msb.fsm
fsm_files/awgn2o3_4_msbG.fsm
+ fsm_files/awgn2o3_4ungerboecka.fsm
+ fsm_files/awgn2o3_4ungerboeck.fsm
+ fsm_files/awgn2o3_64ungerboecka.fsm
+ fsm_files/awgn2o3_64ungerboeck.fsm
fsm_files/awgn2o3_8.fsm
+ fsm_files/awgn2o3_8ungerboecka.fsm
+ fsm_files/awgn2o3_8ungerboeck.fsm
fsm_files/awgn2o4_4.fsm
fsm_files/disconnected.fsm
+ fsm_files/irregular.fsm
+ fsm_files/joint_16_16.fsm
+ fsm_files/joint_4_16.fsm
fsm_files/rep3.fsm
fsm_files/rep5.fsm
fsm_files/simple.fsm
+ fsm_files/uncoded4.fsm
DESTINATION ${GR_PKG_TRELLIS_EXAMPLES_DIR}/fsm_files
COMPONENT "trellis_examples"
)
diff --git a/gr-trellis/examples/python/README b/gr-trellis/examples/python/README
index 155b0a9416..8b4e0f0abb 100644
--- a/gr-trellis/examples/python/README
+++ b/gr-trellis/examples/python/README
@@ -2,8 +2,6 @@ Here we have several test programs for use with the gr-trellis implementation.
Documentation can be found in
http://gnuradio.org/doc/doxygen/group__trellis__coding__blk.html
-fsm_utils.py contains several useful functions.
-
fsm_files is a directory with some FSM definitions
If you just want to see what these programs do run them;
@@ -26,10 +24,12 @@ which gives you information about the:
number of transmitted packets
number of packets in error
estimated packet error rate
-number of transmitted shorts (or symbols, or bits, depending on the specific program)
-number of shorts (or symbols, or bits) in error
-estimated short (or symbol, or bit) error rate
+number of transmitted symbols, or bits, depending on the specific program
+number of symbols, or bits in error
+estimated symbol, or bit error rate
for instance, the final number 1.10e-03 is the error rate estimate by sending 1000
packets of 1024 shorts each, using an 1/2 4-state convolutional code
and QPSK modulation through an AWGN with Es/N0 = 6.0 dB
+
+There is a similar example in the ../grc/ directory
diff --git a/gr-trellis/examples/python/fsm_files/awgn1o1_16rsc.fsm b/gr-trellis/examples/python/fsm_files/awgn1o1_16rsc.fsm
new file mode 100644
index 0000000000..f82d6052c2
--- /dev/null
+++ b/gr-trellis/examples/python/fsm_files/awgn1o1_16rsc.fsm
@@ -0,0 +1,40 @@
+2 16 2
+
+0 8
+8 0
+1 9
+9 1
+2 10
+10 2
+3 11
+11 3
+12 4
+4 12
+13 5
+5 13
+14 6
+6 14
+15 7
+7 15
+
+
+0 1
+0 1
+1 0
+1 0
+1 0
+1 0
+0 1
+0 1
+1 0
+1 0
+0 1
+0 1
+0 1
+0 1
+1 0
+1 0
+
+Recursive Systematic Codes(RSC)
+GM1o2_16rsc=[1, 1+D+D^4/1+D^2+D^3+D^4] = [1, 27/31] (in decimal);
+
diff --git a/gr-trellis/examples/python/fsm_files/awgn1o1_4rsc.fsm b/gr-trellis/examples/python/fsm_files/awgn1o1_4rsc.fsm
new file mode 100644
index 0000000000..d5e7fe31ba
--- /dev/null
+++ b/gr-trellis/examples/python/fsm_files/awgn1o1_4rsc.fsm
@@ -0,0 +1,16 @@
+2 4 2
+
+0 2
+2 0
+1 3
+3 1
+
+0 1
+0 1
+1 0
+1 0
+
+
+Recursive Systematic Codes(RSC)
+GM1o2_4rsc=[1, 1+D+D^2/1+D^2] = [1, 7/5] (in decimal);
+without the systematic bit
diff --git a/gr-trellis/examples/python/fsm_files/awgn1o2_16rsc.fsm b/gr-trellis/examples/python/fsm_files/awgn1o2_16rsc.fsm
new file mode 100644
index 0000000000..ccf1f1d4b1
--- /dev/null
+++ b/gr-trellis/examples/python/fsm_files/awgn1o2_16rsc.fsm
@@ -0,0 +1,40 @@
+2 16 4
+
+0 8
+8 0
+1 9
+9 1
+2 10
+10 2
+3 11
+11 3
+12 4
+4 12
+13 5
+5 13
+14 6
+6 14
+15 7
+7 15
+
+
+0 3
+0 3
+1 2
+1 2
+1 2
+1 2
+0 3
+0 3
+1 2
+1 2
+0 3
+0 3
+0 3
+0 3
+1 2
+1 2
+
+Recursive Systematic Codes(RSC)
+GM1o2_16rsc=[1, 1+D+D^4/1+D^2+D^3+D^4] = [1, 27/31] (in decimal);
+
diff --git a/gr-trellis/examples/python/fsm_files/awgn1o2_4rsc.fsm b/gr-trellis/examples/python/fsm_files/awgn1o2_4rsc.fsm
new file mode 100644
index 0000000000..adb500a217
--- /dev/null
+++ b/gr-trellis/examples/python/fsm_files/awgn1o2_4rsc.fsm
@@ -0,0 +1,14 @@
+2 4 4
+
+0 2
+2 0
+1 3
+3 1
+
+0 3
+0 3
+1 2
+1 2
+
+Recursive Systematic Codes(RSC)
+GM1o2_4rsc=[1, 1+D+D^2/1+D^2] = [1, 7/5] (in decimal);
diff --git a/gr-trellis/examples/python/fsm_files/awgn2o3_16ungerboeck.fsm b/gr-trellis/examples/python/fsm_files/awgn2o3_16ungerboeck.fsm
new file mode 100644
index 0000000000..70ead4f17a
--- /dev/null
+++ b/gr-trellis/examples/python/fsm_files/awgn2o3_16ungerboeck.fsm
@@ -0,0 +1,50 @@
+4 16 8
+
+0 1 2 3
+4 5 6 7
+8 9 10 11
+12 13 14 15
+0 1 2 3
+4 5 6 7
+8 9 10 11
+12 13 14 15
+0 1 2 3
+4 5 6 7
+8 9 10 11
+12 13 14 15
+0 1 2 3
+4 5 6 7
+8 9 10 11
+12 13 14 15
+
+
+0 4 2 6
+1 5 3 7
+4 0 6 2
+5 1 7 3
+2 6 0 4
+3 7 1 5
+6 2 4 0
+7 3 5 1
+4 0 6 2
+5 1 7 3
+0 4 2 6
+1 5 3 7
+6 2 4 0
+7 3 5 1
+2 6 0 4
+3 7 1 5
+
+This is the rate 2/3 Ungerboeck code with 16 states for 8-PSK (natural mapping).
+The states are defined in Ungerboeck's way.
+
+d_free^2 = 2.274^2 Es --> 7.13 dB (so gain of 4.13 dB over uncoded QPSK)
+
+Parity check matrix in octal: [16 04 23]
+
+Generator Matrix:
+
+[ D 1+D+D^2 0
+ 1+D^2 D^2 D]
+
+
diff --git a/gr-trellis/examples/python/fsm_files/awgn2o3_16ungerboecka.fsm b/gr-trellis/examples/python/fsm_files/awgn2o3_16ungerboecka.fsm
new file mode 100644
index 0000000000..523384362f
--- /dev/null
+++ b/gr-trellis/examples/python/fsm_files/awgn2o3_16ungerboecka.fsm
@@ -0,0 +1,48 @@
+4 16 8
+
+0 8 2 10
+0 8 2 10
+1 9 3 11
+1 9 3 11
+0 8 2 10
+0 8 2 10
+1 9 3 11
+1 9 3 11
+4 12 6 14
+4 12 6 14
+5 13 7 15
+5 13 7 15
+4 12 6 14
+4 12 6 14
+5 13 7 15
+5 13 7 15
+
+
+0 6 2 4
+2 4 0 6
+6 0 4 2
+4 2 6 0
+4 2 6 0
+6 0 4 2
+2 4 0 6
+0 6 2 4
+1 7 3 5
+3 5 1 7
+7 1 5 3
+5 3 7 1
+5 3 7 1
+7 1 5 3
+3 5 1 7
+1 7 3 5
+
+This is the rate 2/3 Ungerboeck code with 16 states for 8-PSK (natural mapping).
+The states are defined in typical way.
+
+d_free^2 = 2.274^2Es --> 7.13 dB (so gain of 4.13 dB over uncoded QPSK)
+
+Parity check matrix in octal: [16 04 23]
+
+Generator Matrix:
+
+[ D 1+D+D^2 0
+ 1+D^2 D^2 D]
diff --git a/gr-trellis/examples/python/fsm_files/awgn2o3_32ungerboeck.fsm b/gr-trellis/examples/python/fsm_files/awgn2o3_32ungerboeck.fsm
new file mode 100644
index 0000000000..a00f9c2e8d
--- /dev/null
+++ b/gr-trellis/examples/python/fsm_files/awgn2o3_32ungerboeck.fsm
@@ -0,0 +1,83 @@
+4 32 8
+
+0 16 1 17
+0 16 1 17
+0 16 1 17
+0 16 1 17
+2 18 3 19
+2 18 3 19
+2 18 3 19
+2 18 3 19
+4 20 5 21
+4 20 5 21
+4 20 5 21
+4 20 5 21
+6 22 7 23
+6 22 7 23
+6 22 7 23
+6 22 7 23
+8 24 9 25
+8 24 9 25
+8 24 9 25
+8 24 9 25
+10 26 11 27
+10 26 11 27
+10 26 11 27
+10 26 11 27
+12 28 13 29
+12 28 13 29
+12 28 13 29
+12 28 13 29
+14 30 15 31
+14 30 15 31
+14 30 15 31
+14 30 15 31
+
+
+
+
+0 4 2 6
+4 0 6 2
+2 6 0 4
+6 2 4 0
+5 1 7 3
+1 5 3 7
+7 3 5 1
+3 7 1 5
+1 5 3 7
+5 1 7 3
+3 7 1 5
+7 3 5 1
+4 0 6 2
+0 4 2 6
+6 2 4 0
+2 6 0 4
+1 5 3 7
+5 1 7 3
+3 7 1 5
+7 3 5 1
+4 0 6 2
+0 4 2 6
+6 2 4 0
+2 6 0 4
+0 4 2 6
+4 0 6 2
+2 6 0 4
+6 2 4 0
+5 1 7 3
+1 5 3 7
+7 3 5 1
+3 7 1 5
+
+This is the rate 2/3 Ungerboeck code with 32 states for 8-PSK (natural mapping).
+The states are defined in typical way.
+
+d_free^2 = 2.405^2 Es --> 7.59 dB (so gain of 4.59 dB over uncoded QPSK)
+
+Parity check matrix in octal: [34 16 45]
+
+Generator Matrix:
+
+[ 1 D 0
+ D^4 D^2+1 D^3+D^2+D]
+
diff --git a/gr-trellis/examples/python/fsm_files/awgn2o3_32ungerboecka.fsm b/gr-trellis/examples/python/fsm_files/awgn2o3_32ungerboecka.fsm
new file mode 100644
index 0000000000..b2e6ebdf44
--- /dev/null
+++ b/gr-trellis/examples/python/fsm_files/awgn2o3_32ungerboecka.fsm
@@ -0,0 +1,84 @@
+4 32 8
+0 16 1 17
+0 16 1 17
+0 16 1 17
+0 16 1 17
+2 18 3 19
+2 18 3 19
+2 18 3 19
+2 18 3 19
+4 20 5 21
+4 20 5 21
+4 20 5 21
+4 20 5 21
+6 22 7 23
+6 22 7 23
+6 22 7 23
+6 22 7 23
+8 24 9 25
+8 24 9 25
+8 24 9 25
+8 24 9 25
+10 26 11 27
+10 26 11 27
+10 26 11 27
+10 26 11 27
+12 28 13 29
+12 28 13 29
+12 28 13 29
+12 28 13 29
+14 30 15 31
+14 30 15 31
+14 30 15 31
+14 30 15 31
+
+
+
+
+
+0 4 2 6
+4 0 6 2
+2 6 0 4
+6 2 4 0
+1 5 3 7
+5 1 7 3
+3 7 1 5
+7 3 5 1
+3 7 1 5
+7 3 5 1
+1 5 3 7
+5 1 7 3
+2 6 0 4
+6 2 4 0
+0 4 2 6
+4 0 6 2
+1 5 3 7
+5 1 7 3
+3 7 1 5
+7 3 5 1
+0 4 2 6
+4 0 6 2
+2 6 0 4
+6 2 4 0
+2 6 0 4
+6 2 4 0
+0 4 2 6
+4 0 6 2
+3 7 1 5
+7 3 5 1
+1 5 3 7
+5 1 7 3
+
+This is the rate 2/3 Ungerboeck code with 32 states for 8-PSK (natural mapping).
+The states are defined in typical way.
+
+d_free^2 = 2.405^2 Es --> 7.59 dB (so gain of 4.59 dB over uncoded QPSK)
+
+Parity check matrix in octal: [34 16 45]
+
+Generator Matrix:
+
+[ 1 D 0
+ D^4+D 1 D^3+D^2+D]
+
+
diff --git a/gr-trellis/examples/python/fsm_files/awgn2o3_4_msb.fsm b/gr-trellis/examples/python/fsm_files/awgn2o3_4_msb.fsm
index d834c52718..ff6e2a763b 100644
--- a/gr-trellis/examples/python/fsm_files/awgn2o3_4_msb.fsm
+++ b/gr-trellis/examples/python/fsm_files/awgn2o3_4_msb.fsm
@@ -12,7 +12,7 @@
This is generated by the 1/2 AWGN code (5 7) operated twice, ie,
-(xk+1 xki) [xk-1 xk-2] -> [xk+1 xki].
+(xk+1 xk) [xk-1 xk-2] -> [xk+1 xk].
We also puncture the first (MSB) bit.
This code is worse than awgn2o3_4_msbG and slightly worse than
awgn2o3_4, BUT seems to be a good innner code for sctcm (with 8PSK natural).
diff --git a/gr-trellis/examples/python/fsm_files/awgn2o3_4_msbG.fsm b/gr-trellis/examples/python/fsm_files/awgn2o3_4_msbG.fsm
index 8956c53da2..54f9cbc3cc 100644
--- a/gr-trellis/examples/python/fsm_files/awgn2o3_4_msbG.fsm
+++ b/gr-trellis/examples/python/fsm_files/awgn2o3_4_msbG.fsm
@@ -11,7 +11,7 @@
This is generated by the 1/2 AWGN code (5 7) operated twice, ie,
-(xk+1 xki) [xk-1 xk-2] -> [xk+1 xki].
+(xk+1 xk) [xk-1 xk-2] -> [xk+1 xk].
We also puncture the first (MSB) bit and Gray map the symbols.
intermediate states:
@@ -45,7 +45,7 @@ and in decimal:
After Gray mapping:
label -> phase
0 -> 0
-1 -> 0
+1 -> 1
2 -> 7
3 -> 2
4 -> 5
diff --git a/gr-trellis/examples/python/fsm_files/awgn2o3_4ungerboeck.fsm b/gr-trellis/examples/python/fsm_files/awgn2o3_4ungerboeck.fsm
new file mode 100644
index 0000000000..160f4ea30f
--- /dev/null
+++ b/gr-trellis/examples/python/fsm_files/awgn2o3_4ungerboeck.fsm
@@ -0,0 +1,26 @@
+4 4 8
+
+0 0 1 1
+2 2 3 3
+0 0 1 1
+2 2 3 3
+
+
+0 4 2 6
+1 5 3 7
+2 6 0 4
+3 7 1 5
+
+
+
+This is the Ungerboeck code for 8-PSK (natural mapping).
+The states are defined in Ungerboeck's way.
+
+d_free^2=4 Es -> 3.0 dB over uncoded QPSK
+
+Parity check matrix in octal: [0 2 5]
+
+Generator matrix:
+
+[1 0 0
+ 0 1+D^2 D]
diff --git a/gr-trellis/examples/python/fsm_files/awgn2o3_4ungerboecka.fsm b/gr-trellis/examples/python/fsm_files/awgn2o3_4ungerboecka.fsm
new file mode 100644
index 0000000000..d9c210a0e9
--- /dev/null
+++ b/gr-trellis/examples/python/fsm_files/awgn2o3_4ungerboecka.fsm
@@ -0,0 +1,23 @@
+4 4 8
+
+0 2 0 2
+0 2 0 2
+1 3 1 3
+1 3 1 3
+
+0 2 4 6
+2 0 6 4
+1 3 5 7
+3 1 7 5
+
+This is the rate 2/3 Ungerboeck's code with 4 states.
+The states are defined in typical way.
+
+d_free^2=4 Es -> 3.0 dB over uncoded QPSK
+
+Parity check matrix in octal: [0 2 5]
+
+Generator matrix:
+
+[1 0 0
+ 0 1+D^2 D]
diff --git a/gr-trellis/examples/python/fsm_files/awgn2o3_64ungerboeck.fsm b/gr-trellis/examples/python/fsm_files/awgn2o3_64ungerboeck.fsm
new file mode 100644
index 0000000000..62c75c31c1
--- /dev/null
+++ b/gr-trellis/examples/python/fsm_files/awgn2o3_64ungerboeck.fsm
@@ -0,0 +1,150 @@
+4 64 8
+
+
+0 32 1 33
+0 32 1 33
+0 32 1 33
+0 32 1 33
+2 34 3 35
+2 34 3 35
+2 34 3 35
+2 34 3 35
+4 36 5 37
+4 36 5 37
+4 36 5 37
+4 36 5 37
+6 38 7 39
+6 38 7 39
+6 38 7 39
+6 38 7 39
+8 40 9 41
+8 40 9 41
+8 40 9 41
+8 40 9 41
+10 42 11 43
+10 42 11 43
+10 42 11 43
+10 42 11 43
+12 44 13 45
+12 44 13 45
+12 44 13 45
+12 44 13 45
+14 46 15 47
+14 46 15 47
+14 46 15 47
+14 46 15 47
+16 48 17 49
+16 48 17 49
+16 48 17 49
+16 48 17 49
+18 50 19 51
+18 50 19 51
+18 50 19 51
+18 50 19 51
+20 52 21 53
+20 52 21 53
+20 52 21 53
+20 52 21 53
+22 54 23 55
+22 54 23 55
+22 54 23 55
+22 54 23 55
+24 56 25 57
+24 56 25 57
+24 56 25 57
+24 56 25 57
+26 58 27 59
+26 58 27 59
+26 58 27 59
+26 58 27 59
+28 60 29 61
+28 60 29 61
+28 60 29 61
+28 60 29 61
+30 62 31 63
+30 62 31 63
+30 62 31 63
+30 62 31 63
+
+
+
+
+0 4 2 6
+4 0 6 2
+2 6 0 4
+6 2 4 0
+1 5 3 7
+5 1 7 3
+3 7 1 5
+7 3 5 1
+3 7 1 5
+7 3 5 1
+1 5 3 7
+5 1 7 3
+2 6 0 4
+6 2 4 0
+0 4 2 6
+4 0 6 2
+1 5 3 7
+5 1 7 3
+3 7 1 5
+7 3 5 1
+0 4 2 6
+4 0 6 2
+2 6 0 4
+6 2 4 0
+2 6 0 4
+6 2 4 0
+0 4 2 6
+4 0 6 2
+3 7 1 5
+7 3 5 1
+1 5 3 7
+5 1 7 3
+1 5 3 7
+5 1 7 3
+3 7 1 5
+7 3 5 1
+0 4 2 6
+4 0 6 2
+2 6 0 4
+6 2 4 0
+2 6 0 4
+6 2 4 0
+0 4 2 6
+4 0 6 2
+3 7 1 5
+7 3 5 1
+1 5 3 7
+5 1 7 3
+0 4 2 6
+4 0 6 2
+2 6 0 4
+6 2 4 0
+1 5 3 7
+5 1 7 3
+3 7 1 5
+7 3 5 1
+3 7 1 5
+7 3 5 1
+1 5 3 7
+5 1 7 3
+2 6 0 4
+6 2 4 0
+0 4 2 6
+4 0 6 2
+
+
+This is the rate 2/3 Ungerboeck code with 64 states for 8-PSK (natural mapping).
+The states are defined in typical way.
+
+d_free^2 = 2.52^2 Es --> 8.01 dB (so gain of 5.01 dB over uncoded QPSK)
+
+parity check matrix in octal: [074 036 105]
+
+generator matrix:
+
+[1 D 0
+ D^5 D^2+1 D^4+D^3+D^2+D]
+
+
diff --git a/gr-trellis/examples/python/fsm_files/awgn2o3_64ungerboecka.fsm b/gr-trellis/examples/python/fsm_files/awgn2o3_64ungerboecka.fsm
new file mode 100644
index 0000000000..137091f1f6
--- /dev/null
+++ b/gr-trellis/examples/python/fsm_files/awgn2o3_64ungerboecka.fsm
@@ -0,0 +1,154 @@
+4 64 8
+
+
+0 32 1 33
+0 32 1 33
+0 32 1 33
+0 32 1 33
+2 34 3 35
+2 34 3 35
+2 34 3 35
+2 34 3 35
+4 36 5 37
+4 36 5 37
+4 36 5 37
+4 36 5 37
+6 38 7 39
+6 38 7 39
+6 38 7 39
+6 38 7 39
+8 40 9 41
+8 40 9 41
+8 40 9 41
+8 40 9 41
+10 42 11 43
+10 42 11 43
+10 42 11 43
+10 42 11 43
+12 44 13 45
+12 44 13 45
+12 44 13 45
+12 44 13 45
+14 46 15 47
+14 46 15 47
+14 46 15 47
+14 46 15 47
+16 48 17 49
+16 48 17 49
+16 48 17 49
+16 48 17 49
+18 50 19 51
+18 50 19 51
+18 50 19 51
+18 50 19 51
+20 52 21 53
+20 52 21 53
+20 52 21 53
+20 52 21 53
+22 54 23 55
+22 54 23 55
+22 54 23 55
+22 54 23 55
+24 56 25 57
+24 56 25 57
+24 56 25 57
+24 56 25 57
+26 58 27 59
+26 58 27 59
+26 58 27 59
+26 58 27 59
+28 60 29 61
+28 60 29 61
+28 60 29 61
+28 60 29 61
+30 62 31 63
+30 62 31 63
+30 62 31 63
+30 62 31 63
+
+
+
+
+
+0 4 2 6
+4 0 6 2
+2 6 0 4
+6 2 4 0
+5 1 7 3
+1 5 3 7
+7 3 5 1
+3 7 1 5
+1 5 3 7
+5 1 7 3
+3 7 1 5
+7 3 5 1
+4 0 6 2
+0 4 2 6
+6 2 4 0
+2 6 0 4
+1 5 3 7
+5 1 7 3
+3 7 1 5
+7 3 5 1
+4 0 6 2
+0 4 2 6
+6 2 4 0
+2 6 0 4
+0 4 2 6
+4 0 6 2
+2 6 0 4
+6 2 4 0
+5 1 7 3
+1 5 3 7
+7 3 5 1
+3 7 1 5
+1 5 3 7
+5 1 7 3
+3 7 1 5
+7 3 5 1
+4 0 6 2
+0 4 2 6
+6 2 4 0
+2 6 0 4
+0 4 2 6
+4 0 6 2
+2 6 0 4
+6 2 4 0
+5 1 7 3
+1 5 3 7
+7 3 5 1
+3 7 1 5
+0 4 2 6
+4 0 6 2
+2 6 0 4
+6 2 4 0
+5 1 7 3
+1 5 3 7
+7 3 5 1
+3 7 1 5
+1 5 3 7
+5 1 7 3
+3 7 1 5
+7 3 5 1
+4 0 6 2
+0 4 2 6
+6 2 4 0
+2 6 0 4
+
+
+
+
+
+This is the rate 2/3 Ungerboeck code with 64 states for 8-PSK (natural mapping).
+The states are defined in typical way.
+
+d_free^2 = 2.52^2 Es --> 8.01 dB (so gain of 5.01 dB over uncoded QPSK)
+
+parity check matrix in octal: [074 036 105]
+
+generator matrix:
+
+[1 D 0
+ D^5+D 1 D^4+D^3+D^2+D]
+
+
diff --git a/gr-trellis/examples/python/fsm_files/awgn2o3_8.fsm b/gr-trellis/examples/python/fsm_files/awgn2o3_8.fsm
index 34deeb68cb..6ace4f5e14 100644
--- a/gr-trellis/examples/python/fsm_files/awgn2o3_8.fsm
+++ b/gr-trellis/examples/python/fsm_files/awgn2o3_8.fsm
@@ -21,5 +21,6 @@
-This is generated by the 1/2 8-state AWGN code (15 17) by puncturing the fourth bit.
+This is generated by the 1/2 8-state AWGN code (15 17) by operating it twice and
+puncturing the fourth bit.
--> d_free=???
diff --git a/gr-trellis/examples/python/fsm_files/awgn2o3_8ungerboeck.fsm b/gr-trellis/examples/python/fsm_files/awgn2o3_8ungerboeck.fsm
new file mode 100644
index 0000000000..e2f08eba25
--- /dev/null
+++ b/gr-trellis/examples/python/fsm_files/awgn2o3_8ungerboeck.fsm
@@ -0,0 +1,35 @@
+4 8 8
+
+0 1 2 3
+4 5 6 7
+0 1 2 3
+4 5 6 7
+0 1 2 3
+4 5 6 7
+0 1 2 3
+4 5 6 7
+
+
+0 4 2 6
+1 5 3 7
+4 0 6 2
+5 1 7 3
+2 6 0 4
+3 7 1 5
+6 2 4 0
+7 3 5 1
+
+
+
+This is the rate 2/3 Ungerboeck code with 8-states for 8-PSK (natural mapping).
+The states are defined in Ungerboeck's way.
+
+d_free^2 = 4.585 Es --> 6.6 dB (so gain of 3.6 dB over uncoded QPSK)
+
+Parity check matrix in octal: [04 02 11]
+
+Generator Matrix:
+
+[ 1 D 0
+ D^2 1 D]
+
diff --git a/gr-trellis/examples/python/fsm_files/awgn2o3_8ungerboecka.fsm b/gr-trellis/examples/python/fsm_files/awgn2o3_8ungerboecka.fsm
new file mode 100644
index 0000000000..2425e6a01a
--- /dev/null
+++ b/gr-trellis/examples/python/fsm_files/awgn2o3_8ungerboecka.fsm
@@ -0,0 +1,32 @@
+4 8 8
+
+0 4 1 5
+0 4 1 5
+0 4 1 5
+0 4 1 5
+2 6 3 7
+2 6 3 7
+2 6 3 7
+2 6 3 7
+
+0 4 2 6
+4 0 6 2
+2 6 0 4
+6 2 4 0
+1 5 3 7
+5 1 7 3
+3 7 1 5
+7 3 5 1
+
+This is the rate 2/3 Ungerboeck code with 8-states for 8-PSK (natural mapping).
+The states are defined in typical way.
+
+d_free^2 = 4.585 Es --> 6.6 dB (so gain of 3.6 dB over uncoded QPSK)
+
+Parity check matrix in octal: [04 02 11]
+
+Generator Matrix:
+
+[ 1 D 0
+ D^2 1 D]
+
diff --git a/gr-trellis/examples/python/fsm_files/uncoded4.fsm b/gr-trellis/examples/python/fsm_files/uncoded4.fsm
new file mode 100644
index 0000000000..67cb12ce8f
--- /dev/null
+++ b/gr-trellis/examples/python/fsm_files/uncoded4.fsm
@@ -0,0 +1,7 @@
+4 1 4
+
+0 0 0 0
+
+0 1 2 3
+
+uncoded 4-ary transmission
diff --git a/gr-trellis/examples/python/test_cpm.py b/gr-trellis/examples/python/test_cpm.py
index 3f5cfc4587..6fe25ec68c 100755
--- a/gr-trellis/examples/python/test_cpm.py
+++ b/gr-trellis/examples/python/test_cpm.py
@@ -12,8 +12,8 @@ from gnuradio import trellis, digital, filter, blocks
from grc_gnuradio import blks2 as grc_blks2
import math
import numpy
-import fsm_utils
from gnuradio import trellis
+from gnuradio.trellis import fsm_utils
try:
from gnuradio import analog
@@ -43,8 +43,9 @@ def run_test(seed,blocksize):
f = trellis.fsm(P,M,L)
# CPFSK signals
- #p = numpy.ones(Q)/(2.0)
- #q = numpy.cumsum(p)/(1.0*Q)
+ #p = numpy.ones(L*Q)
+ #q = numpy.cumsum(p)
+ #q = q/q[-1]/2.0;
# GMSK signals
BT=0.3;
diff --git a/gr-trellis/examples/python/test_pccc_turbo1.py b/gr-trellis/examples/python/test_pccc_turbo1.py
deleted file mode 100755
index 7104aa5039..0000000000
--- a/gr-trellis/examples/python/test_pccc_turbo1.py
+++ /dev/null
@@ -1,124 +0,0 @@
-#!/usr/bin/env python
-
-from gnuradio import gr
-from gnuradio import trellis, digital, blocks
-from gnuradio import eng_notation
-import math
-import sys
-import random
-import fsm_utils
-
-try:
- from gnuradio import analog
-except ImportError:
- sys.stderr.write("Error: Program requires gr-analog.\n")
- sys.exit(1)
-
-def run_test (fo,fi,interleaver,Kb,bitspersymbol,K,dimensionality,constellation,Es,N0,IT,seed):
- tb = gr.top_block ()
-
-
- # TX
- src = blocks.lfsr_32k_source_s()
- src_head = blocks.head (gr.sizeof_short,Kb/16) # packet size in shorts
- s2fsmi = blocks.packed_to_unpacked_ss(bitspersymbol,gr.GR_MSB_FIRST) # unpack shorts to symbols compatible with the outer FSM input cardinality
- #src = blocks.vector_source_s([0,0,0,0,0,0,0,0,0,0,0,0,1,1,1,1],False)
- enc = trellis.pccc_encoder_ss(fo,0,fi,0,interleaver,K)
- code = blocks.vector_sink_s()
- mod = digital.chunks_to_symbols_sf(constellation,dimensionality)
-
- # CHANNEL
- add = blocks.add_ff()
- noise = analog.noise_source_f(analog.GR_GAUSSIAN,math.sqrt(N0/2),seed)
-
- # RX
- metrics_in = trellis.metrics_f(fi.O()*fo.O(),dimensionality,constellation,digital.TRELLIS_EUCLIDEAN) # data preprocessing to generate metrics for innner SISO
- scale = blocks.multiply_const_ff(1.0/N0)
- dec = trellis.pccc_decoder_s(fo,0,-1,fi,0,-1,interleaver,K,IT,trellis.TRELLIS_MIN_SUM)
-
- fsmi2s = blocks.unpacked_to_packed_ss(bitspersymbol,gr.GR_MSB_FIRST) # pack FSM input symbols to shorts
- dst = blocks.check_lfsr_32k_s()
-
- tb.connect (src,src_head,s2fsmi,enc,mod)
- #tb.connect (src,enc,mod)
- #tb.connect(enc,code)
- tb.connect (mod,(add,0))
- tb.connect (noise,(add,1))
- tb.connect (add,metrics_in,scale,dec,fsmi2s,dst)
-
- tb.run()
-
- #print code.data()
-
- ntotal = dst.ntotal ()
- nright = dst.nright ()
- runlength = dst.runlength ()
- return (ntotal,ntotal-nright)
-
-
-def main(args):
- nargs = len (args)
- if nargs == 5:
- fname_out=args[0]
- fname_in=args[1]
- esn0_db=float(args[2]) # Es/No in dB
- IT=int(args[3])
- rep=int(args[4]) # number of times the experiment is run to collect enough errors
- else:
- sys.stderr.write ('usage: test_pccc_turbo.py fsm_name_1 fsm_fname_2 Es/No_db iterations repetitions\n')
- sys.exit (1)
-
- # system parameters
- Kb=1024*16 # packet size in bits (make it multiple of 16 so it can be packed in a short)
- fo=trellis.fsm(fname_out) # get the outer FSM specification from a file
- fi=trellis.fsm(fname_in) # get the innner FSM specification from a file
- bitspersymbol = int(round(math.log(fo.I())/math.log(2))) # bits per FSM input symbol
- if fo.I() != fi.I():
- sys.stderr.write ('Incompatible input cardinality between two FSMs.\n')
- sys.exit (1)
- K=Kb/bitspersymbol # packet size in trellis steps
- interleaver=trellis.interleaver(K,666) # construct a random interleaver
- #modulation = fsm_utils.psk8 # see fsm_utlis.py for available predefined modulations
- dimensionality = 4
- constellation = [ 1, 0, 1, 0,\
- 1, 0,-1, 0,\
- 1, 0, 0, 1,\
- 1, 0, 0,-1,\
- -1, 0, 1, 0,\
- -1, 0,-1, 0,\
- -1, 0, 0, 1,\
- -1, 0, 0,-1,\
- 0, 1, 1, 0,\
- 0, 1,-1, 0,\
- 0, 1, 0, 1,\
- 0, 1, 0,-1,\
- 0,-1, 1, 0,\
- 0,-1,-1, 0,\
- 0,-1, 0, 1,\
- 0,-1, 0,-1,] # equivalent to 2 QPSK symbols
- if len(constellation)/dimensionality != fi.O()*fo.O():
- sys.stderr.write ('Incompatible FSM output cardinality and modulation size.\n')
- sys.exit (1)
- # calculate average symbol energy
- Es = 0
- for i in range(len(constellation)):
- Es = Es + constellation[i]**2
- Es = Es / (len(constellation)/dimensionality)
- N0=Es/pow(10.0,esn0_db/10.0); # calculate noise variance
-
- tot_s=0 # total number of transmitted shorts
- terr_s=0 # total number of shorts in error
- terr_p=0 # total number of packets in error
- for i in range(rep):
- (s,e)=run_test(fo,fi,interleaver,Kb,bitspersymbol,K,dimensionality,constellation,Es,N0,IT,-long(666+i)) # run experiment with different seed to get different noise realizations
- tot_s=tot_s+s
- terr_s=terr_s+e
- terr_p=terr_p+(terr_s!=0)
- if ((i+1)%10==0): # display progress
- print i+1,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_s,terr_s, '%.2e' % ((1.0*terr_s)/tot_s)
- # estimate of the (short or bit) error rate
- print rep,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_s,terr_s, '%.2e' % ((1.0*terr_s)/tot_s)
-
-
-if __name__ == '__main__':
- main (sys.argv[1:])
diff --git a/gr-trellis/examples/python/test_sccc_hard.py b/gr-trellis/examples/python/test_sccc_hard.py
deleted file mode 100755
index 83393df4dc..0000000000
--- a/gr-trellis/examples/python/test_sccc_hard.py
+++ /dev/null
@@ -1,106 +0,0 @@
-#!/usr/bin/env python
-
-from gnuradio import gr
-from gnuradio import trellis, digital, blocks
-from gnuradio import eng_notation
-import math
-import sys
-import random
-import fsm_utils
-
-try:
- from gnuradio import analog
-except ImportError:
- sys.stderr.write("Error: Program requires gr-analog.\n")
- sys.exit(1)
-
-def run_test (fo,fi,interleaver,Kb,bitspersymbol,K,dimensionality,constellation,N0,seed):
- tb = gr.top_block ()
-
-
- # TX
- src = blocks.lfsr_32k_source_s()
- src_head = blocks.head(gr.sizeof_short,Kb/16) # packet size in shorts
- s2fsmi = blocks.packed_to_unpacked_ss(bitspersymbol,gr.GR_MSB_FIRST) # unpack shorts to symbols compatible with the outer FSM input cardinality
- enc_out = trellis.encoder_ss(fo,0) # initial state = 0
- inter = trellis.permutation(interleaver.K(),interleaver.INTER(),1,gr.sizeof_short)
- enc_in = trellis.encoder_ss(fi,0) # initial state = 0
- mod = digital.chunks_to_symbols_sf(constellation,dimensionality)
-
- # CHANNEL
- add = blocks.add_ff()
- noise = analog.noise_source_f(analog.GR_GAUSSIAN,math.sqrt(N0/2),seed)
-
- # RX
- metrics_in = trellis.metrics_f(fi.O(),dimensionality,constellation,digital.TRELLIS_EUCLIDEAN) # data preprocessing to generate metrics for innner Viterbi
- va_in = trellis.viterbi_s(fi,K,0,-1) # Put -1 if the Initial/Final states are not set.
- deinter = trellis.permutation(interleaver.K(),interleaver.DEINTER(),1,gr.sizeof_short)
- metrics_out = trellis.metrics_s(fo.O(),1,[0,1,2,3],digital.TRELLIS_HARD_SYMBOL) # data preprocessing to generate metrics for outer Viterbi (hard decisions)
- va_out = trellis.viterbi_s(fo,K,0,-1) # Put -1 if the Initial/Final states are not set.
- fsmi2s = blocks.unpacked_to_packed_ss(bitspersymbol,gr.GR_MSB_FIRST) # pack FSM input symbols to shorts
- dst = blocks.check_lfsr_32k_s()
-
- tb.connect (src,src_head,s2fsmi,enc_out,inter,enc_in,mod)
- tb.connect (mod,(add,0))
- tb.connect (noise,(add,1))
- tb.connect (add,metrics_in)
- tb.connect (metrics_in,va_in,deinter,metrics_out,va_out,fsmi2s,dst)
-
- tb.run()
-
- ntotal = dst.ntotal ()
- nright = dst.nright ()
- runlength = dst.runlength ()
- return (ntotal,ntotal-nright)
-
-
-def main(args):
- nargs = len (args)
- if nargs == 4:
- fname_out=args[0]
- fname_in=args[1]
- esn0_db=float(args[2]) # Es/No in dB
- rep=int(args[3]) # number of times the experiment is run to collect enough errors
- else:
- sys.stderr.write ('usage: test_tcm.py fsm_name_out fsm_fname_in Es/No_db repetitions\n')
- sys.exit (1)
-
- # system parameters
- Kb=1024*16 # packet size in bits (make it multiple of 16 so it can be packed in a short)
- fo=trellis.fsm(fname_out) # get the outer FSM specification from a file
- fi=trellis.fsm(fname_in) # get the innner FSM specification from a file
- bitspersymbol = int(round(math.log(fo.I())/math.log(2))) # bits per FSM input symbol
- if fo.O() != fi.I():
- sys.stderr.write ('Incompatible cardinality between outer and inner FSM.\n')
- sys.exit (1)
- K=Kb/bitspersymbol # packet size in trellis steps
- interleaver=trellis.interleaver(K,666) # construct a random interleaver
- modulation = fsm_utils.psk8 # see fsm_utlis.py for available predefined modulations
- dimensionality = modulation[0]
- constellation = modulation[1]
- if len(constellation)/dimensionality != fi.O():
- sys.stderr.write ('Incompatible FSM output cardinality and modulation size.\n')
- sys.exit (1)
- # calculate average symbol energy
- Es = 0
- for i in range(len(constellation)):
- Es = Es + constellation[i]**2
- Es = Es / (len(constellation)/dimensionality)
- N0=Es/pow(10.0,esn0_db/10.0); # calculate noise variance
-
- tot_s=0 # total number of transmitted shorts
- terr_s=0 # total number of shorts in error
- terr_p=0 # total number of packets in error
- for i in range(rep):
- (s,e)=run_test(fo,fi,interleaver,Kb,bitspersymbol,K,dimensionality,constellation,N0,-long(666+i)) # run experiment with different seed to get different noise realizations
- tot_s=tot_s+s
- terr_s=terr_s+e
- terr_p=terr_p+(terr_s!=0)
- if ((i+1)%100==0) : # display progress
- print i+1,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_s,terr_s, '%.2e' % ((1.0*terr_s)/tot_s)
- # estimate of the (short or bit) error rate
- print rep,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_s,terr_s, '%.2e' % ((1.0*terr_s)/tot_s)
-
-
-if __name__ == '__main__':
- main (sys.argv[1:])
diff --git a/gr-trellis/examples/python/test_sccc_soft.py b/gr-trellis/examples/python/test_sccc_soft.py
deleted file mode 100755
index 25d26e0025..0000000000
--- a/gr-trellis/examples/python/test_sccc_soft.py
+++ /dev/null
@@ -1,110 +0,0 @@
-#!/usr/bin/env python
-
-from gnuradio import gr
-from gnuradio import trellis, digital, blocks
-from gnuradio import eng_notation
-import math
-import sys
-import random
-import fsm_utils
-
-try:
- from gnuradio import analog
-except ImportError:
- sys.stderr.write("Error: Program requires gr-analog.\n")
- sys.exit(1)
-
-def run_test (fo,fi,interleaver,Kb,bitspersymbol,K,dimensionality,constellation,N0,seed):
- tb = gr.top_block ()
-
-
- # TX
- src = blocks.lfsr_32k_source_s()
- src_head = blocks.head (gr.sizeof_short,Kb/16) # packet size in shorts
- s2fsmi = blocks.packed_to_unpacked_ss(bitspersymbol,gr.GR_MSB_FIRST) # unpack shorts to symbols compatible with the outer FSM input cardinality
- enc_out = trellis.encoder_ss(fo,0) # initial state = 0
- inter = trellis.permutation(interleaver.K(),interleaver.INTER(),1,gr.sizeof_short)
- enc_in = trellis.encoder_ss(fi,0) # initial state = 0
- mod = digital.chunks_to_symbols_sf(constellation,dimensionality)
-
- # CHANNEL
- add = blocks.add_ff()
- noise = analog.noise_source_f(analog.GR_GAUSSIAN,math.sqrt(N0/2),seed)
-
- # RX
- metrics_in = trellis.metrics_f(fi.O(),dimensionality,constellation,digital.TRELLIS_EUCLIDEAN) # data preprocessing to generate metrics for innner Viterbi
- gnd = blocks.vector_source_f([0],True);
- siso_in = trellis.siso_f(fi,K,0,-1,True,False,trellis.TRELLIS_MIN_SUM) # Put -1 if the Initial/Final states are not set.
- deinter = trellis.permutation(interleaver.K(),interleaver.DEINTER(),fi.I(),gr.sizeof_float)
- va_out = trellis.viterbi_s(fo,K,0,-1) # Put -1 if the Initial/Final states are not set.
- fsmi2s = blocks.unpacked_to_packed_ss(bitspersymbol,gr.GR_MSB_FIRST) # pack FSM input symbols to shorts
- dst = blocks.check_lfsr_32k_s()
-
- tb.connect (src,src_head,s2fsmi,enc_out,inter,enc_in,mod)
- tb.connect (mod,(add,0))
- tb.connect (noise,(add,1))
- tb.connect (add,metrics_in)
- tb.connect (gnd,(siso_in,0))
- tb.connect (metrics_in,(siso_in,1))
- tb.connect (siso_in,deinter,va_out,fsmi2s,dst)
-
- tb.run()
-
- ntotal = dst.ntotal ()
- nright = dst.nright ()
- runlength = dst.runlength ()
- return (ntotal,ntotal-nright)
-
-
-def main(args):
- nargs = len (args)
- if nargs == 4:
- fname_out=args[0]
- fname_in=args[1]
- esn0_db=float(args[2]) # Es/No in dB
- rep=int(args[3]) # number of times the experiment is run to collect enough errors
- else:
- sys.stderr.write ('usage: test_tcm.py fsm_name_out fsm_fname_in Es/No_db repetitions\n')
- sys.exit (1)
-
- # system parameters
- Kb=1024*16 # packet size in bits (make it multiple of 16 so it can be packed in a short)
- fo=trellis.fsm(fname_out) # get the outer FSM specification from a file
- fi=trellis.fsm(fname_in) # get the innner FSM specification from a file
- bitspersymbol = int(round(math.log(fo.I())/math.log(2))) # bits per FSM input symbol
- if fo.O() != fi.I():
- sys.stderr.write ('Incompatible cardinality between outer and inner FSM.\n')
- sys.exit (1)
- K=Kb/bitspersymbol # packet size in trellis steps
- interleaver=trellis.interleaver(K,666) # construct a random interleaver
- modulation = fsm_utils.psk8 # see fsm_utlis.py for available predefined modulations
- dimensionality = modulation[0]
- constellation = modulation[1]
- if len(constellation)/dimensionality != fi.O():
- sys.stderr.write ('Incompatible FSM output cardinality and modulation size.\n')
- sys.exit (1)
- # calculate average symbol energy
- Es = 0
- for i in range(len(constellation)):
- Es = Es + constellation[i]**2
- Es = Es / (len(constellation)/dimensionality)
- N0=Es/pow(10.0,esn0_db/10.0); # calculate noise variance
-
-
- tot_s=0 # total number of transmitted shorts
- terr_s=0 # total number of shorts in error
- terr_p=0 # total number of packets in error
- for i in range(rep):
- (s,e)=run_test(fo,fi,interleaver,Kb,bitspersymbol,K,dimensionality,constellation,N0,-long(666+i)) # run experiment with different seed to get different noise realizations
- tot_s=tot_s+s
- terr_s=terr_s+e
- terr_p=terr_p+(terr_s!=0)
- if ((i+1)%100==0) : # display progress
- print i+1,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_s,terr_s, '%.2e' % ((1.0*terr_s)/tot_s)
- # estimate of the (short or bit) error rate
- print rep,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_s,terr_s, '%.2e' % ((1.0*terr_s)/tot_s)
-
-
-
-if __name__ == '__main__':
- main (sys.argv[1:])
diff --git a/gr-trellis/examples/python/test_sccc_turbo.py b/gr-trellis/examples/python/test_sccc_turbo.py
deleted file mode 100755
index 08004e8a0d..0000000000
--- a/gr-trellis/examples/python/test_sccc_turbo.py
+++ /dev/null
@@ -1,146 +0,0 @@
-#!/usr/bin/env python
-
-from gnuradio import gr
-from gnuradio import trellis, digital, blocks
-from gnuradio import eng_notation
-import math
-import sys
-import random
-import fsm_utils
-
-try:
- from gnuradio import analog
-except ImportError:
- sys.stderr.write("Error: Program requires gr-analog.\n")
- sys.exit(1)
-
-def make_rx(tb,fo,fi,dimensionality,constellation,K,interleaver,IT,Es,N0,type):
- metrics_in = trellis.metrics_f(fi.O(),dimensionality,constellation,digital.TRELLIS_EUCLIDEAN) # data preprocessing to generate metrics for innner Viterbi
- scale = blocks.multiply_const_ff(1.0/N0)
- gnd = blocks.vector_source_f([0],True);
-
- inter=[]
- deinter=[]
- siso_in=[]
- siso_out=[]
-
- # generate all blocks
- for it in range(IT):
- inter.append( trellis.permutation(interleaver.K(),interleaver.INTER(),fi.I(),gr.sizeof_float) )
- siso_in.append( trellis.siso_f(fi,K,0,-1,True,False,type) )
- deinter.append( trellis.permutation(interleaver.K(),interleaver.DEINTER(),fi.I(),gr.sizeof_float) )
- if it < IT-1:
- siso_out.append( trellis.siso_f(fo,K,0,-1,False,True,type) )
- else:
- siso_out.append( trellis.viterbi_s(fo,K,0,-1) ) # no soft outputs needed
-
- # connect first stage
- tb.connect (gnd,inter[0])
- tb.connect (metrics_in,scale)
- tb.connect (scale,(siso_in[0],1))
-
- # connect the rest
- for it in range(IT):
- if it < IT-1:
- tb.connect (metrics_in,(siso_in[it+1],1))
- tb.connect (siso_in[it],deinter[it],(siso_out[it],1))
- tb.connect (gnd,(siso_out[it],0))
- tb.connect (siso_out[it],inter[it+1])
- tb.connect (inter[it],(siso_in[it],0))
- else:
- tb.connect (siso_in[it],deinter[it],siso_out[it])
- tb.connect (inter[it],(siso_in[it],0))
-
- return (metrics_in,siso_out[IT-1])
-
-
-def run_test (fo,fi,interleaver,Kb,bitspersymbol,K,dimensionality,constellation,Es,N0,IT,seed):
- tb = gr.top_block ()
-
-
- # TX
- src = blocks.lfsr_32k_source_s()
- src_head = blocks.head(gr.sizeof_short,Kb/16) # packet size in shorts
- s2fsmi = blocks.packed_to_unpacked_ss(bitspersymbol,gr.GR_MSB_FIRST) # unpack shorts to symbols compatible with the outer FSM input cardinality
- enc_out = trellis.encoder_ss(fo,0) # initial state = 0
- inter = trellis.permutation(interleaver.K(),interleaver.INTER(),1,gr.sizeof_short)
- enc_in = trellis.encoder_ss(fi,0) # initial state = 0
- mod = digital.chunks_to_symbols_sf(constellation,dimensionality)
-
- # CHANNEL
- add = blocks.add_ff()
- noise = analog.noise_source_f(analog.GR_GAUSSIAN,math.sqrt(N0/2),seed)
-
- # RX
- (head,tail) = make_rx(tb,fo,fi,dimensionality,constellation,K,interleaver,IT,Es,N0,trellis.TRELLIS_MIN_SUM)
- #(head,tail) = make_rx(tb,fo,fi,dimensionality,constellation,K,interleaver,IT,Es,N0,trellis.TRELLIS_SUM_PRODUCT)
- fsmi2s = blocks.unpacked_to_packed_ss(bitspersymbol,gr.GR_MSB_FIRST) # pack FSM input symbols to shorts
- dst = blocks.check_lfsr_32k_s()
-
- tb.connect (src,src_head,s2fsmi,enc_out,inter,enc_in,mod)
- tb.connect (mod,(add,0))
- tb.connect (noise,(add,1))
- tb.connect (add,head)
- tb.connect (tail,fsmi2s,dst)
-
- tb.run()
-
- #print enc_out.ST(), enc_in.ST()
-
- ntotal = dst.ntotal ()
- nright = dst.nright ()
- runlength = dst.runlength ()
- return (ntotal,ntotal-nright)
-
-
-def main(args):
- nargs = len (args)
- if nargs == 5:
- fname_out=args[0]
- fname_in=args[1]
- esn0_db=float(args[2]) # Es/No in dB
- IT=int(args[3])
- rep=int(args[4]) # number of times the experiment is run to collect enough errors
- else:
- sys.stderr.write ('usage: test_sccc_turbo.py fsm_name_out fsm_fname_in Es/No_db iterations repetitions\n')
- sys.exit (1)
-
- # system parameters
- Kb=1024*16 # packet size in bits (make it multiple of 16 so it can be packed in a short)
- fo=trellis.fsm(fname_out) # get the outer FSM specification from a file
- fi=trellis.fsm(fname_in) # get the innner FSM specification from a file
- bitspersymbol = int(round(math.log(fo.I())/math.log(2))) # bits per FSM input symbol
- if fo.O() != fi.I():
- sys.stderr.write ('Incompatible cardinality between outer and inner FSM.\n')
- sys.exit (1)
- K=Kb/bitspersymbol # packet size in trellis steps
- interleaver=trellis.interleaver(K,666) # construct a random interleaver
- modulation = fsm_utils.psk8 # see fsm_utlis.py for available predefined modulations
- dimensionality = modulation[0]
- constellation = modulation[1]
- if len(constellation)/dimensionality != fi.O():
- sys.stderr.write ('Incompatible FSM output cardinality and modulation size.\n')
- sys.exit (1)
- # calculate average symbol energy
- Es = 0
- for i in range(len(constellation)):
- Es = Es + constellation[i]**2
- Es = Es / (len(constellation)/dimensionality)
- N0=Es/pow(10.0,esn0_db/10.0); # calculate noise variance
-
- tot_s=0 # total number of transmitted shorts
- terr_s=0 # total number of shorts in error
- terr_p=0 # total number of packets in error
- for i in range(rep):
- (s,e)=run_test(fo,fi,interleaver,Kb,bitspersymbol,K,dimensionality,constellation,Es,N0,IT,-long(666+i)) # run experiment with different seed to get different noise realizations
- tot_s=tot_s+s
- terr_s=terr_s+e
- terr_p=terr_p+(terr_s!=0)
- if ((i+1)%10==0): # display progress
- print i+1,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_s,terr_s, '%.2e' % ((1.0*terr_s)/tot_s)
- # estimate of the (short or bit) error rate
- print rep,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_s,terr_s, '%.2e' % ((1.0*terr_s)/tot_s)
-
-
-if __name__ == '__main__':
- main (sys.argv[1:])
diff --git a/gr-trellis/examples/python/test_sccc_turbo1.py b/gr-trellis/examples/python/test_sccc_turbo1.py
deleted file mode 100755
index 528a79d011..0000000000
--- a/gr-trellis/examples/python/test_sccc_turbo1.py
+++ /dev/null
@@ -1,104 +0,0 @@
-#!/usr/bin/env python
-
-from gnuradio import gr
-from gnuradio import trellis, digital, blocks
-from gnuradio import eng_notation
-import math
-import sys
-import random
-import fsm_utils
-
-try:
- from gnuradio import analog
-except ImportError:
- sys.stderr.write("Error: Program requires gr-analog.\n")
- sys.exit(1)
-
-def run_test (fo,fi,interleaver,Kb,bitspersymbol,K,dimensionality,constellation,Es,N0,IT,seed):
- tb = gr.top_block ()
-
- # TX
- src = blocks.lfsr_32k_source_s()
- src_head = blocks.head(gr.sizeof_short,Kb/16) # packet size in shorts
- s2fsmi = blocks.packed_to_unpacked_ss(bitspersymbol,gr.GR_MSB_FIRST) # unpack shorts to symbols compatible with the outer FSM input cardinality
- enc = trellis.sccc_encoder_ss(fo,0,fi,0,interleaver,K)
- mod = digital.chunks_to_symbols_sf(constellation,dimensionality)
-
- # CHANNEL
- add = blocks.add_ff()
- noise = analog.noise_source_f(analog.GR_GAUSSIAN,math.sqrt(N0/2),seed)
-
- # RX
- dec = trellis.sccc_decoder_combined_fs(fo,0,-1,fi,0,-1,interleaver,K,IT,trellis.TRELLIS_MIN_SUM,dimensionality,constellation,digital.TRELLIS_EUCLIDEAN,1.0)
- fsmi2s = blocks.unpacked_to_packed_ss(bitspersymbol,gr.GR_MSB_FIRST) # pack FSM input symbols to shorts
- dst = blocks.check_lfsr_32k_s()
-
- #tb.connect (src,src_head,s2fsmi,enc_out,inter,enc_in,mod)
- tb.connect (src,src_head,s2fsmi,enc,mod)
- tb.connect (mod,(add,0))
- tb.connect (noise,(add,1))
- #tb.connect (add,head)
- #tb.connect (tail,fsmi2s,dst)
- tb.connect (add,dec,fsmi2s,dst)
-
- tb.run()
-
- #print enc_out.ST(), enc_in.ST()
-
- ntotal = dst.ntotal ()
- nright = dst.nright ()
- runlength = dst.runlength ()
- return (ntotal,ntotal-nright)
-
-
-def main(args):
- nargs = len (args)
- if nargs == 5:
- fname_out=args[0]
- fname_in=args[1]
- esn0_db=float(args[2]) # Es/No in dB
- IT=int(args[3])
- rep=int(args[4]) # number of times the experiment is run to collect enough errors
- else:
- sys.stderr.write ('usage: test_tcm.py fsm_name_out fsm_fname_in Es/No_db iterations repetitions\n')
- sys.exit (1)
-
- # system parameters
- Kb=1024*16 # packet size in bits (make it multiple of 16 so it can be packed in a short)
- fo=trellis.fsm(fname_out) # get the outer FSM specification from a file
- fi=trellis.fsm(fname_in) # get the innner FSM specification from a file
- bitspersymbol = int(round(math.log(fo.I())/math.log(2))) # bits per FSM input symbol
- if fo.O() != fi.I():
- sys.stderr.write ('Incompatible cardinality between outer and inner FSM.\n')
- sys.exit (1)
- K=Kb/bitspersymbol # packet size in trellis steps
- interleaver=trellis.interleaver(K,666) # construct a random interleaver
- modulation = fsm_utils.psk8 # see fsm_utlis.py for available predefined modulations
- dimensionality = modulation[0]
- constellation = modulation[1]
- if len(constellation)/dimensionality != fi.O():
- sys.stderr.write ('Incompatible FSM output cardinality and modulation size.\n')
- sys.exit (1)
- # calculate average symbol energy
- Es = 0
- for i in range(len(constellation)):
- Es = Es + constellation[i]**2
- Es = Es / (len(constellation)/dimensionality)
- N0=Es/pow(10.0,esn0_db/10.0); # calculate noise variance
-
- tot_s=0 # total number of transmitted shorts
- terr_s=0 # total number of shorts in error
- terr_p=0 # total number of packets in error
- for i in range(rep):
- (s,e)=run_test(fo,fi,interleaver,Kb,bitspersymbol,K,dimensionality,constellation,Es,N0,IT,-long(666+i)) # run experiment with different seed to get different noise realizations
- tot_s=tot_s+s
- terr_s=terr_s+e
- terr_p=terr_p+(terr_s!=0)
- if ((i+1)%10==0): # display progress
- print i+1,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_s,terr_s, '%.2e' % ((1.0*terr_s)/tot_s)
- # estimate of the (short or bit) error rate
- print rep,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_s,terr_s, '%.2e' % ((1.0*terr_s)/tot_s)
-
-
-if __name__ == '__main__':
- main (sys.argv[1:])
diff --git a/gr-trellis/examples/python/test_sccc_turbo2.py b/gr-trellis/examples/python/test_sccc_turbo2.py
deleted file mode 100755
index d7f26c4e13..0000000000
--- a/gr-trellis/examples/python/test_sccc_turbo2.py
+++ /dev/null
@@ -1,106 +0,0 @@
-#!/usr/bin/env python
-
-from gnuradio import gr
-from gnuradio import trellis, digital, blocks
-from gnuradio import eng_notation
-import math
-import sys
-import random
-import fsm_utils
-
-try:
- from gnuradio import analog
-except ImportError:
- sys.stderr.write("Error: Program requires gr-analog.\n")
- sys.exit(1)
-
-def run_test (fo,fi,interleaver,Kb,bitspersymbol,K,dimensionality,constellation,Es,N0,IT,seed):
- tb = gr.top_block ()
-
- # TX
- src = blocks.lfsr_32k_source_s()
- src_head = blocks.head(gr.sizeof_short,Kb/16) # packet size in shorts
- s2fsmi = blocks.packed_to_unpacked_ss(bitspersymbol,gr.GR_MSB_FIRST) # unpack shorts to symbols compatible with the outer FSM input cardinality
- enc = trellis.sccc_encoder_ss(fo,0,fi,0,interleaver,K)
- mod = digital.chunks_to_symbols_sf(constellation,dimensionality)
-
- # CHANNEL
- add = blocks.add_ff()
- noise = analog.noise_source_f(analog.GR_GAUSSIAN,math.sqrt(N0/2),seed)
-
- # RX
- metrics_in = trellis.metrics_f(fi.O(),dimensionality,constellation,digital.TRELLIS_EUCLIDEAN) # data preprocessing to generate metrics for innner SISO
- scale = blocks.multiply_const_ff(1.0/N0)
- dec = trellis.sccc_decoder_s(fo,0,-1,fi,0,-1,interleaver,K,IT,trellis.TRELLIS_MIN_SUM)
- fsmi2s = blocks.unpacked_to_packed_ss(bitspersymbol,gr.GR_MSB_FIRST) # pack FSM input symbols to shorts
- dst = blocks.check_lfsr_32k_s()
-
- #tb.connect (src,src_head,s2fsmi,enc_out,inter,enc_in,mod)
- tb.connect (src,src_head,s2fsmi,enc,mod)
- tb.connect (mod,(add,0))
- tb.connect (noise,(add,1))
- #tb.connect (add,head)
- #tb.connect (tail,fsmi2s,dst)
- tb.connect (add,metrics_in,scale,dec,fsmi2s,dst)
-
- tb.run()
-
- #print enc_out.ST(), enc_in.ST()
-
- ntotal = dst.ntotal ()
- nright = dst.nright ()
- runlength = dst.runlength ()
- return (ntotal,ntotal-nright)
-
-
-def main(args):
- nargs = len (args)
- if nargs == 5:
- fname_out=args[0]
- fname_in=args[1]
- esn0_db=float(args[2]) # Es/No in dB
- IT=int(args[3])
- rep=int(args[4]) # number of times the experiment is run to collect enough errors
- else:
- sys.stderr.write ('usage: test_tcm.py fsm_name_out fsm_fname_in Es/No_db iterations repetitions\n')
- sys.exit (1)
-
- # system parameters
- Kb=1024*16 # packet size in bits (make it multiple of 16 so it can be packed in a short)
- fo=trellis.fsm(fname_out) # get the outer FSM specification from a file
- fi=trellis.fsm(fname_in) # get the innner FSM specification from a file
- bitspersymbol = int(round(math.log(fo.I())/math.log(2))) # bits per FSM input symbol
- if fo.O() != fi.I():
- sys.stderr.write ('Incompatible cardinality between outer and inner FSM.\n')
- sys.exit (1)
- K=Kb/bitspersymbol # packet size in trellis steps
- interleaver=trellis.interleaver(K,666) # construct a random interleaver
- modulation = fsm_utils.psk8 # see fsm_utlis.py for available predefined modulations
- dimensionality = modulation[0]
- constellation = modulation[1]
- if len(constellation)/dimensionality != fi.O():
- sys.stderr.write ('Incompatible FSM output cardinality and modulation size.\n')
- sys.exit (1)
- # calculate average symbol energy
- Es = 0
- for i in range(len(constellation)):
- Es = Es + constellation[i]**2
- Es = Es / (len(constellation)/dimensionality)
- N0=Es/pow(10.0,esn0_db/10.0); # calculate noise variance
-
- tot_s=0 # total number of transmitted shorts
- terr_s=0 # total number of shorts in error
- terr_p=0 # total number of packets in error
- for i in range(rep):
- (s,e)=run_test(fo,fi,interleaver,Kb,bitspersymbol,K,dimensionality,constellation,Es,N0,IT,-long(666+i)) # run experiment with different seed to get different noise realizations
- tot_s=tot_s+s
- terr_s=terr_s+e
- terr_p=terr_p+(terr_s!=0)
- if ((i+1)%10==0): # display progress
- print i+1,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_s,terr_s, '%.2e' % ((1.0*terr_s)/tot_s)
- # estimate of the (short or bit) error rate
- print rep,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_s,terr_s, '%.2e' % ((1.0*terr_s)/tot_s)
-
-
-if __name__ == '__main__':
- main (sys.argv[1:])
diff --git a/gr-trellis/examples/python/test_tcm.py b/gr-trellis/examples/python/test_tcm.py
index bf9710aa1c..dfc565616e 100755
--- a/gr-trellis/examples/python/test_tcm.py
+++ b/gr-trellis/examples/python/test_tcm.py
@@ -6,9 +6,10 @@ from gnuradio import eng_notation
import math
import sys
import random
-import fsm_utils
+from gnuradio.trellis import fsm_utils
from gnuradio.eng_option import eng_option
from optparse import OptionParser
+import numpy
try:
from gnuradio import analog
@@ -19,39 +20,32 @@ except ImportError:
def run_test (f,Kb,bitspersymbol,K,dimensionality,constellation,N0,seed):
tb = gr.top_block ()
-
# TX
- #packet = [0]*Kb
- #for i in range(Kb-1*16): # last 16 bits = 0 to drive the final state to 0
- #packet[i] = random.randint(0, 1) # random 0s and 1s
- #src = blocks.vector_source_s(packet,False)
- src = blocks.lfsr_32k_source_s()
- src_head = blocks.head(gr.sizeof_short,Kb/16) # packet size in shorts
- #b2s = blocks.unpacked_to_packed_ss(1,gr.GR_MSB_FIRST) # pack bits in shorts
+ numpy.random.seed(-seed)
+ packet = numpy.random.randint(0,2,Kb) # create Kb random bits
+ packet[Kb-10:Kb]=0
+ packet[0:Kb]=0
+ src = blocks.vector_source_s(packet.tolist(),False)
+ b2s = blocks.unpacked_to_packed_ss(1,gr.GR_MSB_FIRST) # pack bits in shorts
s2fsmi = blocks.packed_to_unpacked_ss(bitspersymbol,gr.GR_MSB_FIRST) # unpack shorts to symbols compatible with the FSM input cardinality
enc = trellis.encoder_ss(f,0) # initial state = 0
mod = digital.chunks_to_symbols_sf(constellation,dimensionality)
# CHANNEL
add = blocks.add_ff()
- noise = analog.noise_source_f(analog.GR_GAUSSIAN,math.sqrt(N0/2),seed)
+ noise = analog.noise_source_f(analog.GR_GAUSSIAN,math.sqrt(N0/2),long(seed))
# RX
- metrics = trellis.metrics_f(f.O(),dimensionality,constellation,digital.TRELLIS_EUCLIDEAN) # data preprocessing to generate metrics for Viterbi
- va = trellis.viterbi_s(f,K,0,-1) # Put -1 if the Initial/Final states are not set.
+ va = trellis.viterbi_combined_fs(f,K,0,0,dimensionality,constellation,digital.TRELLIS_EUCLIDEAN) # Put -1 if the Initial/Final states are not set.
fsmi2s = blocks.unpacked_to_packed_ss(bitspersymbol,gr.GR_MSB_FIRST) # pack FSM input symbols to shorts
- #s2b = blocks.packed_to_unpacked_ss(1,gr.GR_MSB_FIRST) # unpack shorts to bits
- #dst = blocks.vector_sink_s();
- dst = blocks.check_lfsr_32k_s()
+ s2b = blocks.packed_to_unpacked_ss(1,gr.GR_MSB_FIRST) # unpack shorts to bits
+ dst = blocks.vector_sink_s();
- tb.connect (src,src_head,s2fsmi,enc,mod)
- #tb.connect (src,b2s,s2fsmi,enc,mod)
+ tb.connect (src,b2s,s2fsmi,enc,mod)
tb.connect (mod,(add,0))
tb.connect (noise,(add,1))
- tb.connect (add,metrics)
- tb.connect (metrics,va,fsmi2s,dst)
- #tb.connect (metrics,va,fsmi2s,s2b,dst)
+ tb.connect (add,va,fsmi2s,s2b,dst)
tb.run()
@@ -61,19 +55,11 @@ def run_test (f,Kb,bitspersymbol,K,dimensionality,constellation,N0,seed):
# Then put it as the last argument in the viterbi block
#print "final state = " , enc.ST()
- ntotal = dst.ntotal ()
- nright = dst.nright ()
- runlength = dst.runlength ()
- #ntotal = len(packet)
- #if len(dst.data()) != ntotal:
- #print "Error: not enough data\n"
- #nright = 0;
- #for i in range(ntotal):
- #if packet[i]==dst.data()[i]:
- #nright=nright+1
- #else:
- #print "Error in ", i
- return (ntotal,ntotal-nright)
+ if len(dst.data()) != len(packet):
+ print "Error: not enough data:", len(dst.data()), len(packet)
+ ntotal=len(packet)
+ nwrong = sum(abs(packet-numpy.array(dst.data())));
+ return (ntotal,nwrong,abs(packet-numpy.array(dst.data())))
@@ -113,20 +99,26 @@ def main():
Es = Es / (len(constellation)/dimensionality)
N0=Es/pow(10.0,esn0_db/10.0); # calculate noise variance
- tot_s=0 # total number of transmitted shorts
- terr_s=0 # total number of shorts in error
+ tot_b=0 # total number of transmitted bits
+ terr_b=0 # total number of bits in error
terr_p=0 # total number of packets in error
for i in range(rep):
- (s,e)=run_test(f,Kb,bitspersymbol,K,dimensionality,constellation,N0,-long(666+i)) # run experiment with different seed to get different noise realizations
- tot_s=tot_s+s
- terr_s=terr_s+e
- terr_p=terr_p+(terr_s!=0)
+ (b,e,pattern)=run_test(f,Kb,bitspersymbol,K,dimensionality,constellation,N0,-(666+i)) # run experiment with different seed to get different noise realizations
+ tot_b=tot_b+b
+ terr_b=terr_b+e
+ terr_p=terr_p+(e!=0)
if ((i+1)%100==0) : # display progress
- print i+1,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_s,terr_s, '%.2e' % ((1.0*terr_s)/tot_s)
- # estimate of the (short or bit) error rate
- print rep,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_s,terr_s, '%.2e' % ((1.0*terr_s)/tot_s)
+ print i+1,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_b,terr_b, '%.2e' % ((1.0*terr_b)/tot_b)
+ if e!=0:
+ print "rep=",i, e
+ for k in range(Kb):
+ if pattern[k]!=0:
+ print k
+ # estimate of the bit error rate
+ print rep,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_b,terr_b, '%.2e' % ((1.0*terr_b)/tot_b)
if __name__ == '__main__':
main()
+
diff --git a/gr-trellis/examples/python/test_tcm_bit.py b/gr-trellis/examples/python/test_tcm_bit.py
deleted file mode 100755
index 7880f0ea53..0000000000
--- a/gr-trellis/examples/python/test_tcm_bit.py
+++ /dev/null
@@ -1,134 +0,0 @@
-#!/usr/bin/env python
-
-from gnuradio import gr
-from gnuradio import trellis, digital, blocks
-from gnuradio import eng_notation
-import math
-import sys
-import random
-import fsm_utils
-from gnuradio.eng_option import eng_option
-from optparse import OptionParser
-
-try:
- from gnuradio import analog
-except ImportError:
- sys.stderr.write("Error: Program requires gr-analog.\n")
- sys.exit(1)
-
-def run_test (f,Kb,bitspersymbol,K,dimensionality,constellation,N0,seed):
- tb = gr.top_block ()
-
- # TX
- packet = [0]*Kb
- # this for loop is TOO slow!!!
- for i in range(Kb-1*16): # last 16 bits = 0 to drive the final state to 0
- packet[i] = random.randint(0, 1) # random 0s and 1s
- src = blocks.vector_source_s(packet,False)
- #src = blocks.lfsr_32k_source_s()
- #src_head = blocks.head (gr.sizeof_short,Kb/16) # packet size in shorts
- b2s = blocks.unpacked_to_packed_ss(1,gr.GR_MSB_FIRST) # pack bits in shorts
- s2fsmi = blocks.packed_to_unpacked_ss(bitspersymbol,gr.GR_MSB_FIRST) # unpack shorts to symbols compatible with the FSM input cardinality
- enc = trellis.encoder_ss(f,0) # initial state = 0
- mod = digital.chunks_to_symbols_sf(constellation,dimensionality)
-
-
- # CHANNEL
- add = blocks.add_ff()
- noise = analog.noise_source_f(analog.GR_GAUSSIAN,math.sqrt(N0/2),seed)
-
-
- # RX
- metrics = trellis.metrics_f(f.O(),dimensionality,constellation,digital.TRELLIS_EUCLIDEAN) # data preprocessing to generate metrics for Viterbi
- va = trellis.viterbi_s(f,K,0,-1) # Put -1 if the Initial/Final states are not set.
- fsmi2s = blocks.unpacked_to_packed_ss(bitspersymbol,gr.GR_MSB_FIRST) # pack FSM input symbols to shorts
- s2b = blocks.packed_to_unpacked_ss(1,gr.GR_MSB_FIRST) # unpack shorts to bits
- dst = blocks.vector_sink_s();
- #dst = blocks.check_lfsr_32k_s();
-
-
- #tb.connect (src,src_head,s2fsmi,enc,mod)
- tb.connect (src,b2s,s2fsmi,enc,mod)
- tb.connect (mod,(add,0))
- tb.connect (noise,(add,1))
- tb.connect (add,metrics)
- #tb.connect (metrics,va,fsmi2s,dst)
- tb.connect (metrics,va,fsmi2s,s2b,dst)
-
-
- tb.run()
-
- # A bit of cheating: run the program once and print the
- # final encoder state..
- # Then put it as the last argument in the viterbi block
- #print "final state = " , enc.ST()
-
- #ntotal = dst.ntotal ()
- #nright = dst.nright ()
- #runlength = dst.runlength ()
- ntotal = len(packet)
- if len(dst.data()) != ntotal:
- print "Error: not enough data\n"
- nright = 0;
- # this for loop is TOO slow!!!
- for i in range(ntotal):
- if packet[i]==dst.data()[i]:
- nright=nright+1
- #else:
- #print "Error in ", i
- return (ntotal,ntotal-nright)
-
-
-
-
-def main():
- parser = OptionParser(option_class=eng_option)
- parser.add_option("-f", "--fsm_file", type="string", default="fsm_files/awgn1o2_4.fsm", help="Filename containing the fsm specification, e.g. -f fsm_files/awgn1o2_4.fsm (default=fsm_files/awgn1o2_4.fsm)")
- parser.add_option("-e", "--esn0", type="eng_float", default=10.0, help="Symbol energy to noise PSD level ratio in dB, e.g., -e 10.0 (default=10.0)")
- parser.add_option("-r", "--repetitions", type="int", default=100, help="Number of packets to be generated for the simulation, e.g., -r 100 (default=100)")
-
- (options, args) = parser.parse_args ()
- if len(args) != 0:
- parser.print_help()
- raise SystemExit, 1
-
- fname=options.fsm_file
- esn0_db=float(options.esn0)
- rep=int(options.repetitions)
-
-
- # system parameters
- f=trellis.fsm(fname) # get the FSM specification from a file
- Kb=1024*16 # packet size in bits (make it multiple of 16 so it can be packed in a short)
- bitspersymbol = int(round(math.log(f.I())/math.log(2))) # bits per FSM input symbol
- K=Kb/bitspersymbol # packet size in trellis steps
- modulation = fsm_utils.psk4 # see fsm_utlis.py for available predefined modulations
- dimensionality = modulation[0]
- constellation = modulation[1]
- if len(constellation)/dimensionality != f.O():
- sys.stderr.write ('Incompatible FSM output cardinality and modulation size.\n')
- sys.exit (1)
- # calculate average symbol energy
- Es = 0
- for i in range(len(constellation)):
- Es = Es + constellation[i]**2
- Es = Es / (len(constellation)/dimensionality)
- N0=Es/pow(10.0,esn0_db/10.0); # calculate noise variance
-
- tot_s=0 # total number of transmitted shorts
- terr_s=0 # total number of shorts in error
- terr_p=0 # total number of packets in error
- for i in range(rep):
- (s,e)=run_test(f,Kb,bitspersymbol,K,dimensionality,constellation,N0,-long(666+i)) # run experiment with different seed to get different noise realizations
- tot_s=tot_s+s
- terr_s=terr_s+e
- terr_p=terr_p+(terr_s!=0)
- if ((i+1)%1==0) : # display progress
- print i+1,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_s,terr_s, '%.2e' % ((1.0*terr_s)/tot_s)
- # estimate of the (short or bit) error rate
- print rep,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_s,terr_s, '%.2e' % ((1.0*terr_s)/tot_s)
-
-
-
-if __name__ == '__main__':
- main()
diff --git a/gr-trellis/examples/python/test_tcm_combined.py b/gr-trellis/examples/python/test_tcm_combined.py
deleted file mode 100755
index 697e3cc64a..0000000000
--- a/gr-trellis/examples/python/test_tcm_combined.py
+++ /dev/null
@@ -1,112 +0,0 @@
-#!/usr/bin/env python
-
-from gnuradio import gr
-from gnuradio import trellis, digital, blocks
-from gnuradio import eng_notation
-import math
-import sys
-import fsm_utils
-from gnuradio.eng_option import eng_option
-from optparse import OptionParser
-
-try:
- from gnuradio import analog
-except ImportError:
- sys.stderr.write("Error: Program requires gr-analog.\n")
- sys.exit(1)
-
-def run_test (f,Kb,bitspersymbol,K,dimensionality,constellation,N0,seed):
- tb = gr.top_block ()
-
- # TX
- src = blocks.lfsr_32k_source_s()
- src_head = blocks.head(gr.sizeof_short,Kb/16) # packet size in shorts
- s2fsmi = blocks.packed_to_unpacked_ss(bitspersymbol,gr.GR_MSB_FIRST) # unpack shorts to symbols compatible with the FSM input cardinality
- enc = trellis.encoder_ss(f,0) # initial state = 0
- mod = digital.chunks_to_symbols_sf(constellation,dimensionality)
-
-
- # CHANNEL
- add = blocks.add_ff()
- noise = analog.noise_source_f(analog.GR_GAUSSIAN,math.sqrt(N0/2),seed)
-
-
- # RX
- va = trellis.viterbi_combined_fs(f,K,0,-1,dimensionality,constellation,digital.TRELLIS_EUCLIDEAN) # Put -1 if the Initial/Final states are not set.
- fsmi2s = blocks.unpacked_to_packed_ss(bitspersymbol,gr.GR_MSB_FIRST) # pack FSM input symbols to shorts
- dst = blocks.check_lfsr_32k_s();
-
-
- tb.connect (src,src_head,s2fsmi,enc,mod)
- tb.connect (mod,(add,0))
- tb.connect (noise,(add,1))
- tb.connect (add,va,fsmi2s,dst)
-
-
- tb.run()
-
- # A bit of cheating: run the program once and print the
- # final encoder state..
- # Then put it as the last argument in the viterbi block
- #print "final state = " , enc.ST()
-
- ntotal = dst.ntotal ()
- nright = dst.nright ()
- runlength = dst.runlength ()
-
- return (ntotal,ntotal-nright)
-
-
-
-
-def main():
- parser = OptionParser(option_class=eng_option)
- parser.add_option("-f", "--fsm_file", type="string", default="fsm_files/awgn1o2_4.fsm", help="Filename containing the fsm specification, e.g. -f fsm_files/awgn1o2_4.fsm (default=fsm_files/awgn1o2_4.fsm)")
- parser.add_option("-e", "--esn0", type="eng_float", default=10.0, help="Symbol energy to noise PSD level ratio in dB, e.g., -e 10.0 (default=10.0)")
- parser.add_option("-r", "--repetitions", type="int", default=100, help="Number of packets to be generated for the simulation, e.g., -r 100 (default=100)")
-
- (options, args) = parser.parse_args ()
- if len(args) != 0:
- parser.print_help()
- raise SystemExit, 1
-
- fname=options.fsm_file
- esn0_db=float(options.esn0)
- rep=int(options.repetitions)
-
- # system parameters
- f=trellis.fsm(fname) # get the FSM specification from a file (will hopefully be automated in the future...)
- Kb=1024*16 # packet size in bits (make it multiple of 16)
- bitspersymbol = int(round(math.log(f.I())/math.log(2))) # bits per FSM input symbol
- K=Kb/bitspersymbol # packet size in trellis steps
- modulation = fsm_utils.psk4 # see fsm_utils.py for available predefined modulations
- dimensionality = modulation[0]
- constellation = modulation[1]
- if len(constellation)/dimensionality != f.O():
- sys.stderr.write ('Incompatible FSM output cardinality and modulation size.\n')
- sys.exit (1)
- # calculate average symbol energy
- Es = 0
- for i in range(len(constellation)):
- Es = Es + constellation[i]**2
- Es = Es / (len(constellation)/dimensionality)
- N0=Es/pow(10.0,esn0_db/10.0); # noise variance
-
- tot_s=0 # total number of transmitted shorts
- terr_s=0 # total number of shorts in error
- terr_p=0 # total number of packets in error
- for i in range(rep):
- (s,e)=run_test(f,Kb,bitspersymbol,K,dimensionality,constellation,N0,-long(666+i)) # run experiment with different seed to get different noise realizations
- tot_s=tot_s+s
- terr_s=terr_s+e
- terr_p=terr_p+(terr_s!=0)
- if ((i+1)%100==0) : # display progress
- print i+1,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_s,terr_s, '%.2e' % ((1.0*terr_s)/tot_s)
- # estimate of the (short or bit) error rate
- print rep,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_s,terr_s, '%.2e' % ((1.0*terr_s)/tot_s)
-
-
-
-if __name__ == '__main__':
- main()
-
diff --git a/gr-trellis/examples/python/test_tcm_parallel.py b/gr-trellis/examples/python/test_tcm_parallel.py
deleted file mode 100755
index b30c80811f..0000000000
--- a/gr-trellis/examples/python/test_tcm_parallel.py
+++ /dev/null
@@ -1,118 +0,0 @@
-#!/usr/bin/env python
-
-from gnuradio import gr
-from gnuradio import trellis, digital, blocks
-from gnuradio import eng_notation
-import math
-import sys
-import fsm_utils
-from gnuradio.eng_option import eng_option
-from optparse import OptionParser
-
-try:
- from gnuradio import analog
-except ImportError:
- sys.stderr.write("Error: Program requires gr-analog.\n")
- sys.exit(1)
-
-def run_test (f,Kb,bitspersymbol,K,dimensionality,constellation,N0,seed,P):
- tb = gr.top_block ()
-
- # TX
- src = blocks.lfsr_32k_source_s()
- src_head = blocks.head(gr.sizeof_short,Kb/16*P) # packet size in shorts
- s2fsmi=blocks.packed_to_unpacked_ss(bitspersymbol,gr.GR_MSB_FIRST) # unpack shorts to symbols compatible with the FSM input cardinality
- s2p = blocks.stream_to_streams(gr.sizeof_short,P) # serial to parallel
- enc = trellis.encoder_ss(f,0) # initiali state = 0
- mod = digital.chunks_to_symbols_sf(constellation,dimensionality)
-
- # CHANNEL
- add=[]
- noise=[]
- for i in range(P):
- add.append(blocks.add_ff())
- noise.append(analog.noise_source_f(analog.GR_GAUSSIAN,math.sqrt(N0/2),seed))
-
- # RX
- metrics = trellis.metrics_f(f.O(),dimensionality,constellation,digital.TRELLIS_EUCLIDEAN) # data preprocessing to generate metrics for Viterbi
- va = trellis.viterbi_s(f,K,0,-1) # Put -1 if the Initial/Final states are not set.
- p2s = blocks.streams_to_stream(gr.sizeof_short,P) # parallel to serial
- fsmi2s=blocks.unpacked_to_packed_ss(bitspersymbol,gr.GR_MSB_FIRST) # pack FSM input symbols to shorts
- dst = blocks.check_lfsr_32k_s()
-
- tb.connect (src,src_head,s2fsmi,s2p)
- for i in range(P):
- tb.connect ((s2p,i),(enc,i),(mod,i))
- tb.connect ((mod,i),(add[i],0))
- tb.connect (noise[i],(add[i],1))
- tb.connect (add[i],(metrics,i))
- tb.connect ((metrics,i),(va,i),(p2s,i))
- tb.connect (p2s,fsmi2s,dst)
-
-
- tb.run()
-
- # A bit of cheating: run the program once and print the
- # final encoder state.
- # Then put it as the last argument in the viterbi block
- #print "final state = " , enc.ST()
-
- ntotal = dst.ntotal ()
- nright = dst.nright ()
- runlength = dst.runlength ()
-
- return (ntotal,ntotal-nright)
-
-
-
-def main():
- parser = OptionParser(option_class=eng_option)
- parser.add_option("-f", "--fsm_file", type="string", default="fsm_files/awgn1o2_4.fsm", help="Filename containing the fsm specification, e.g. -f fsm_files/awgn1o2_4.fsm (default=fsm_files/awgn1o2_4.fsm)")
- parser.add_option("-e", "--esn0", type="eng_float", default=10.0, help="Symbol energy to noise PSD level ratio in dB, e.g., -e 10.0 (default=10.0)")
- parser.add_option("-r", "--repetitions", type="int", default=100, help="Number of packets to be generated for the simulation, e.g., -r 100 (default=100)")
-
- (options, args) = parser.parse_args ()
- if len(args) != 0:
- parser.print_help()
- raise SystemExit, 1
-
- fname=options.fsm_file
- esn0_db=float(options.esn0)
- rep=int(options.repetitions)
-
- # system parameters
- f=trellis.fsm(fname) # get the FSM specification from a file
- P=4 # how many parallel streams?
- Kb=1024*16 # packet size in bits (make it multiple of 16 so it can be packed in a short)
- bitspersymbol = int(round(math.log(f.I())/math.log(2))) # bits per FSM input symbol
- K=Kb/bitspersymbol # packet size in trellis steps
- modulation = fsm_utils.psk4 # see fsm_utlis.py for available predefined modulations
- dimensionality = modulation[0]
- constellation = modulation[1]
- if len(constellation)/dimensionality != f.O():
- sys.stderr.write ('Incompatible FSM output cardinality and modulation size.\n')
- sys.exit (1)
- # calculate average symbol energy
- Es = 0
- for i in range(len(constellation)):
- Es = Es + constellation[i]**2
- Es = Es / (len(constellation)/dimensionality)
- N0=Es/pow(10.0,esn0_db/10.0); # calculate noise variance
-
- tot_s=0 # total number of transmitted shorts
- terr_s=0 # total number of shorts in error
- terr_p=0 # total number of packets in error
- for i in range(rep):
- (s,e)=run_test(f,Kb,bitspersymbol,K,dimensionality,constellation,N0,-long(666+i),P) # run experiment with different seed to get different noise realizations
- tot_s=tot_s+s
- terr_s=terr_s+e
- terr_p=terr_p+(terr_s!=0)
- if ((i+1)%100==0) : # display progress
- print i+1,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_s,terr_s, '%.2e' % ((1.0*terr_s)/tot_s)
- # estimate of the (short or bit) error rate
- print rep,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_s,terr_s, '%.2e' % ((1.0*terr_s)/tot_s)
-
-
-if __name__ == '__main__':
- main()
-
diff --git a/gr-trellis/examples/python/test_turbo_equalization.py b/gr-trellis/examples/python/test_turbo_equalization.py
deleted file mode 100755
index b2d58a6014..0000000000
--- a/gr-trellis/examples/python/test_turbo_equalization.py
+++ /dev/null
@@ -1,147 +0,0 @@
-#!/usr/bin/env python
-
-from gnuradio import gr
-from gnuradio import trellis, digital, blocks
-from gnuradio import eng_notation
-import math
-import sys
-import fsm_utils
-
-try:
- from gnuradio import analog
-except ImportError:
- sys.stderr.write("Error: Program requires gr-analog.\n")
- sys.exit(1)
-
-def make_rx(tb,fo,fi,dimensionality,tot_constellation,K,interleaver,IT,Es,N0,type):
- metrics_in = trellis.metrics_f(fi.O(),dimensionality,tot_constellation,digital.TRELLIS_EUCLIDEAN) # data preprocessing to generate metrics for innner SISO
- scale = blocks.multiply_const_ff(1.0/N0)
- gnd = blocks.vector_source_f([0],True);
-
- inter=[]
- deinter=[]
- siso_in=[]
- siso_out=[]
-
- # generate all blocks
- for it in range(IT):
- inter.append( trellis.permutation(interleaver.K(),interleaver.INTER(),fi.I(),gr.sizeof_float) )
- siso_in.append( trellis.siso_f(fi,K,0,-1,True,False,type) )
- deinter.append( trellis.permutation(interleaver.K(),interleaver.DEINTER(),fi.I(),gr.sizeof_float) )
- if it < IT-1:
- siso_out.append( trellis.siso_f(fo,K,0,-1,False,True,type) )
- else:
- siso_out.append( trellis.viterbi_s(fo,K,0,-1) ) # no soft outputs needed
-
- # connect first stage
- tb.connect (gnd,inter[0])
- tb.connect (metrics_in,scale)
- tb.connect (scale,(siso_in[0],1))
-
- # connect the rest
- for it in range(IT):
- if it < IT-1:
- tb.connect (metrics_in,(siso_in[it+1],1))
- tb.connect (siso_in[it],deinter[it],(siso_out[it],1))
- tb.connect (gnd,(siso_out[it],0))
- tb.connect (siso_out[it],inter[it+1])
- tb.connect (inter[it],(siso_in[it],0))
- else:
- tb.connect (siso_in[it],deinter[it],siso_out[it])
- tb.connect (inter[it],(siso_in[it],0))
-
- return (metrics_in,siso_out[IT-1])
-
-
-def run_test (fo,fi,interleaver,Kb,bitspersymbol,K,dimensionality,tot_constellation,Es,N0,IT,seed):
- tb = gr.top_block ()
-
- # TX
- src = blocks.lfsr_32k_source_s()
- src_head = blocks.head(gr.sizeof_short,Kb/16) # packet size in shorts
- s2fsmi = blocks.packed_to_unpacked_ss(bitspersymbol,gr.GR_MSB_FIRST) # unpack shorts to symbols compatible with the iouter FSM input cardinality
- enc_out = trellis.encoder_ss(fo,0) # initial state = 0
- inter = trellis.permutation(interleaver.K(),interleaver.INTER(),1,gr.sizeof_short)
- enc_in = trellis.encoder_ss(fi,0) # initial state = 0
- # essentially here we implement the combination of modulation and channel as a memoryless modulation (the memory induced by the channel is hidden in the innner FSM)
- mod = digital.chunks_to_symbols_sf(tot_constellation,dimensionality)
-
- # CHANNEL
- add = blocks.add_ff()
- noise = analog.noise_source_f(analog.GR_GAUSSIAN,math.sqrt(N0/2),seed)
-
- # RX
- (head,tail) = make_rx(tb,fo,fi,dimensionality,tot_constellation,K,interleaver,IT,Es,N0,trellis.TRELLIS_MIN_SUM)
- fsmi2s = blocks.unpacked_to_packed_ss(bitspersymbol,gr.GR_MSB_FIRST) # pack FSM input symbols to shorts
- dst = blocks.check_lfsr_32k_s();
-
- tb.connect (src,src_head,s2fsmi,enc_out,inter,enc_in,mod)
- tb.connect (mod,(add,0))
- tb.connect (noise,(add,1))
- tb.connect (add,head)
- tb.connect (tail,fsmi2s,dst)
-
- tb.run()
-
- ntotal = dst.ntotal ()
- nright = dst.nright ()
- runlength = dst.runlength ()
- #print ntotal,nright,runlength
-
- return (ntotal,ntotal-nright)
-
-
-
-
-def main(args):
- nargs = len (args)
- if nargs == 3:
- fname_out=args[0]
- esn0_db=float(args[1])
- rep=int(args[2])
- else:
- sys.stderr.write ('usage: test_turbo_equalization.py fsm_name_out Es/No_db repetitions\n')
- sys.exit (1)
-
- # system parameters
- Kb=64*16 # packet size in bits (multiple of 16)
- modulation = fsm_utils.pam4 # see fsm_utlis.py for available predefined modulations
- channel = fsm_utils.c_channel # see fsm_utlis.py for available predefined test channels
- fo=trellis.fsm(fname_out) # get the outer FSM specification from a file
- fi=trellis.fsm(len(modulation[1]),len(channel)) # generate the FSM automatically
- if fo.O() != fi.I():
- sys.stderr.write ('Incompatible cardinality between outer and inner FSM.\n')
- sys.exit (1)
- bitspersymbol = int(round(math.log(fo.I())/math.log(2))) # bits per FSM input symbol
- K=Kb/bitspersymbol # packet size in trellis steps
- print 'size = ',K
- interleaver=trellis.interleaver(K,666) # construct a random interleaver
- tot_channel = fsm_utils.make_isi_lookup(modulation,channel,True) # generate the lookup table (normalize energy to 1)
- dimensionality = tot_channel[0]
- tot_constellation = tot_channel[1]
- if len(tot_constellation)/dimensionality != fi.O():
- sys.stderr.write ('Incompatible FSM output cardinality and lookup table size.\n')
- sys.exit (1)
- N0=pow(10.0,-esn0_db/10.0); # noise variance
- IT = 3 # number of turbo iterations
-
- tot_s=0 # total number of transmitted shorts
- terr_s=0 # total number of shorts in error
- terr_p=0 # total number of packets in error
-
- for i in range(rep):
- (s,e)=run_test(fo,fi,interleaver,Kb,bitspersymbol,K,dimensionality,tot_constellation,1,N0,IT,-long(666+i)) # run experiment with different seed to get different noise realizations
- print s
- tot_s=tot_s+s
- terr_s=terr_s+e
- terr_p=terr_p+(terr_s!=0)
- if ((i+1)%10==0) : # display progress
- print i+1,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_s,terr_s, '%.2e' % ((1.0*terr_s)/tot_s)
- # estimate of the (short or bit) error rate
- print rep,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_s,terr_s, '%.2e' % ((1.0*terr_s)/tot_s)
-
-
-
-if __name__ == '__main__':
- main (sys.argv[1:])
-
diff --git a/gr-trellis/examples/python/test_turbo_equalization1.py b/gr-trellis/examples/python/test_turbo_equalization1.py
deleted file mode 100755
index 5ff21ec757..0000000000
--- a/gr-trellis/examples/python/test_turbo_equalization1.py
+++ /dev/null
@@ -1,152 +0,0 @@
-#!/usr/bin/env python
-
-from gnuradio import gr
-from gnuradio import trellis, digital, filter, blocks
-from gnuradio import eng_notation
-import math
-import sys
-import random
-import fsm_utils
-
-try:
- from gnuradio import analog
-except ImportError:
- sys.stderr.write("Error: Program requires gr-analog.\n")
- sys.exit(1)
-
-def make_rx(tb,fo,fi,dimensionality,tot_constellation,K,interleaver,IT,Es,N0,type):
- metrics_in = trellis.metrics_f(fi.O(),dimensionality,tot_constellation,digital.TRELLIS_EUCLIDEAN) # data preprocessing to generate metrics for innner SISO
- scale = blocks.multiply_const_ff(1.0/N0)
- gnd = blocks.vector_source_f([0],True);
-
- inter=[]
- deinter=[]
- siso_in=[]
- siso_out=[]
-
- # generate all blocks
- for it in range(IT):
- inter.append( trellis.permutation(interleaver.K(),interleaver.INTER(),fi.I(),gr.sizeof_float) )
- siso_in.append( trellis.siso_f(fi,K,0,-1,True,False,type) )
- deinter.append( trellis.permutation(interleaver.K(),interleaver.DEINTER(),fi.I(),gr.sizeof_float) )
- if it < IT-1:
- siso_out.append( trellis.siso_f(fo,K,0,-1,False,True,type) )
- else:
- siso_out.append( trellis.viterbi_s(fo,K,0,-1) ) # no soft outputs needed
-
- # connect first stage
- tb.connect (gnd,inter[0])
- tb.connect (metrics_in,scale)
- tb.connect (scale,(siso_in[0],1))
-
- # connect the rest
- for it in range(IT):
- if it < IT-1:
- tb.connect (scale,(siso_in[it+1],1))
- tb.connect (siso_in[it],deinter[it],(siso_out[it],1))
- tb.connect (gnd,(siso_out[it],0))
- tb.connect (siso_out[it],inter[it+1])
- tb.connect (inter[it],(siso_in[it],0))
- else:
- tb.connect (siso_in[it],deinter[it],siso_out[it])
- tb.connect (inter[it],(siso_in[it],0))
-
- return (metrics_in,siso_out[IT-1])
-
-
-def run_test (fo,fi,interleaver,Kb,bitspersymbol,K,channel,modulation,dimensionality,tot_constellation,Es,N0,IT,seed):
- tb = gr.top_block ()
- L = len(channel)
-
- # TX
- # this for loop is TOO slow in python!!!
- packet = [0]*(K)
- random.seed(seed)
- for i in range(len(packet)):
- packet[i] = random.randint(0, 2**bitspersymbol - 1) # random symbols
- src = blocks.vector_source_s(packet,False)
- enc_out = trellis.encoder_ss(fo,0) # initial state = 0
- inter = trellis.permutation(interleaver.K(),interleaver.INTER(),1,gr.sizeof_short)
- mod = digital.chunks_to_symbols_sf(modulation[1],modulation[0])
-
- # CHANNEL
- isi = filter.fir_filter_fff(1,channel)
- add = blocks.add_ff()
- noise = analog.noise_source_f(analog.GR_GAUSSIAN,math.sqrt(N0/2),seed)
-
- # RX
- (head,tail) = make_rx(tb,fo,fi,dimensionality,tot_constellation,K,interleaver,IT,Es,N0,trellis.TRELLIS_MIN_SUM)
- dst = blocks.vector_sink_s();
-
- tb.connect (src,enc_out,inter,mod)
- tb.connect (mod,isi,(add,0))
- tb.connect (noise,(add,1))
- tb.connect (add,head)
- tb.connect (tail,dst)
-
- tb.run()
-
- data = dst.data()
- ntotal = len(data)
- nright=0
- for i in range(ntotal):
- if packet[i]==data[i]:
- nright=nright+1
- #else:
- #print "Error in ", i
-
- return (ntotal,ntotal-nright)
-
-
-
-
-def main(args):
- nargs = len (args)
- if nargs == 3:
- fname_out=args[0]
- esn0_db=float(args[1])
- rep=int(args[2])
- else:
- sys.stderr.write ('usage: test_turbo_equalization.py fsm_name_out Es/No_db repetitions\n')
- sys.exit (1)
-
- # system parameters
- Kb=64*16 # packet size in bits (multiple of 16)
- modulation = fsm_utils.pam4 # see fsm_utlis.py for available predefined modulations
- channel = fsm_utils.c_channel # see fsm_utlis.py for available predefined test channels
- fo=trellis.fsm(fname_out) # get the outer FSM specification from a file
- fi=trellis.fsm(len(modulation[1]),len(channel)) # generate the FSM automatically
- if fo.O() != fi.I():
- sys.stderr.write ('Incompatible cardinality between outer and inner FSM.\n')
- sys.exit (1)
- bitspersymbol = int(round(math.log(fo.I())/math.log(2))) # bits per FSM input symbol
- K=Kb/bitspersymbol # packet size in trellis steps
- interleaver=trellis.interleaver(K,666) # construct a random interleaver
- tot_channel = fsm_utils.make_isi_lookup(modulation,channel,True) # generate the lookup table (normalize energy to 1)
- dimensionality = tot_channel[0]
- tot_constellation = tot_channel[1]
- if len(tot_constellation)/dimensionality != fi.O():
- sys.stderr.write ('Incompatible FSM output cardinality and lookup table size.\n')
- sys.exit (1)
- N0=pow(10.0,-esn0_db/10.0); # noise variance
- IT = 3 # number of turbo iterations
-
- tot_s=0 # total number of transmitted shorts
- terr_s=0 # total number of shorts in error
- terr_p=0 # total number of packets in error
-
- for i in range(rep):
- (s,e)=run_test(fo,fi,interleaver,Kb,bitspersymbol,K,channel,modulation,dimensionality,tot_constellation,1,N0,IT,-long(666+i)) # run experiment with different seed to get different noise realizations
- tot_s=tot_s+s
- terr_s=terr_s+e
- terr_p=terr_p+(terr_s!=0)
- if ((i+1)%10==0) : # display progress
- print i+1,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_s,terr_s, '%.2e' % ((1.0*terr_s)/tot_s)
- # estimate of the (short or bit) error rate
- print rep,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_s,terr_s, '%.2e' % ((1.0*terr_s)/tot_s)
-
-
-
-if __name__ == '__main__':
- main (sys.argv[1:])
-
diff --git a/gr-trellis/examples/python/test_turbo_equalization2.py b/gr-trellis/examples/python/test_turbo_equalization2.py
deleted file mode 100755
index c2af9fbfca..0000000000
--- a/gr-trellis/examples/python/test_turbo_equalization2.py
+++ /dev/null
@@ -1,152 +0,0 @@
-#!/usr/bin/env python
-
-from gnuradio import gr
-from gnuradio import trellis, digital, filter, blocks
-from gnuradio import eng_notation
-import math
-import sys
-import random
-import fsm_utils
-
-try:
- from gnuradio import analog
-except ImportError:
- sys.stderr.write("Error: Program requires gr-analog.\n")
- sys.exit(1)
-
-def make_rx(tb,fo,fi,dimensionality,tot_constellation,K,interleaver,IT,Es,N0,type):
- scale = blocks.multiply_const_ff(math.sqrt(1.0/N0))
- gnd = blocks.vector_source_f([0],True);
-
- inter=[]
- deinter=[]
- siso_in=[]
- siso_out=[]
-
- # generate all blocks
- for it in range(IT):
- inter.append( trellis.permutation(interleaver.K(),interleaver.INTER(),fi.I(),gr.sizeof_float) )
- siso_in.append( trellis.siso_combined_f(fi,K,0,-1,True,False,type,dimensionality,tot_constellation,digital.TRELLIS_EUCLIDEAN) )
- deinter.append( trellis.permutation(interleaver.K(),interleaver.DEINTER(),fi.I(),gr.sizeof_float) )
- if it < IT-1:
- siso_out.append( trellis.siso_f(fo,K,0,-1,False,True,type) )
- else:
- siso_out.append( trellis.viterbi_s(fo,K,0,-1) ) # no soft outputs needed
-
- # connect first stage
- tb.connect (gnd,inter[0])
- tb.connect (scale,(siso_in[0],1))
-
- # connect the rest
- for it in range(IT):
- if it < IT-1:
- tb.connect (scale,(siso_in[it+1],1))
- tb.connect (siso_in[it],deinter[it],(siso_out[it],1))
- tb.connect (gnd,(siso_out[it],0))
- tb.connect (siso_out[it],inter[it+1])
- tb.connect (inter[it],(siso_in[it],0))
- else:
- tb.connect (siso_in[it],deinter[it],siso_out[it])
- tb.connect (inter[it],(siso_in[it],0))
-
- return (scale,siso_out[IT-1])
-
-
-def run_test (fo,fi,interleaver,Kb,bitspersymbol,K,channel,modulation,dimensionality,tot_constellation,Es,N0,IT,seed):
- tb = gr.top_block ()
- L = len(channel)
-
- # TX
- # this for loop is TOO slow in python!!!
- packet = [0]*(K)
- random.seed(seed)
- for i in range(len(packet)):
- packet[i] = random.randint(0, 2**bitspersymbol - 1) # random symbols
- src = blocks.vector_source_s(packet,False)
- enc_out = trellis.encoder_ss(fo,0) # initial state = 0
- inter = trellis.permutation(interleaver.K(),interleaver.INTER(),1,gr.sizeof_short)
- mod = digital.chunks_to_symbols_sf(modulation[1],modulation[0])
-
- # CHANNEL
- isi = filter.fir_filter_fff(1,channel)
- add = blocks.add_ff()
- noise = analog.noise_source_f(analog.GR_GAUSSIAN,math.sqrt(N0/2),seed)
-
- # RX
- (head,tail) = make_rx(tb,fo,fi,dimensionality,tot_constellation,K,interleaver,IT,Es,N0,trellis.TRELLIS_MIN_SUM)
- dst = blocks.vector_sink_s();
-
- tb.connect (src,enc_out,inter,mod)
- tb.connect (mod,isi,(add,0))
- tb.connect (noise,(add,1))
- tb.connect (add,head)
- tb.connect (tail,dst)
-
- tb.run()
-
- data = dst.data()
- ntotal = len(data)
- nright=0
- for i in range(ntotal):
- if packet[i]==data[i]:
- nright=nright+1
- #else:
- #print "Error in ", i
-
- return (ntotal,ntotal-nright)
-
-
-
-
-def main(args):
- nargs = len (args)
- if nargs == 3:
- fname_out=args[0]
- esn0_db=float(args[1])
- rep=int(args[2])
- else:
- sys.stderr.write ('usage: test_turbo_equalization.py fsm_name_out Es/No_db repetitions\n')
- sys.exit (1)
-
- # system parameters
- Kb=64*16 # packet size in bits (multiple of 16)
- modulation = fsm_utils.pam4 # see fsm_utlis.py for available predefined modulations
- channel = fsm_utils.c_channel # see fsm_utlis.py for available predefined test channels
- fo=trellis.fsm(fname_out) # get the outer FSM specification from a file
- fi=trellis.fsm(len(modulation[1]),len(channel)) # generate the FSM automatically
- if fo.O() != fi.I():
- sys.stderr.write ('Incompatible cardinality between outer and inner FSM.\n')
- sys.exit (1)
- bitspersymbol = int(round(math.log(fo.I())/math.log(2))) # bits per FSM input symbol
- K=Kb/bitspersymbol # packet size in trellis steps
- interleaver=trellis.interleaver(K,666) # construct a random interleaver
- tot_channel = fsm_utils.make_isi_lookup(modulation,channel,True) # generate the lookup table (normalize energy to 1)
- dimensionality = tot_channel[0]
- N0=pow(10.0,-esn0_db/10.0); # noise variance
- tot_constellation =[0]*len(tot_channel[1])
- for i in range(len(tot_channel[1])):
- tot_constellation[i] = tot_channel[1][i] * math.sqrt(1.0/N0)
- if len(tot_constellation)/dimensionality != fi.O():
- sys.stderr.write ('Incompatible FSM output cardinality and lookup table size.\n')
- sys.exit (1)
- IT = 3 # number of turbo iterations
-
- tot_s=0 # total number of transmitted shorts
- terr_s=0 # total number of shorts in error
- terr_p=0 # total number of packets in error
-
- for i in range(rep):
- (s,e)=run_test(fo,fi,interleaver,Kb,bitspersymbol,K,channel,modulation,dimensionality,tot_constellation,1,N0,IT,-long(666+i)) # run experiment with different seed to get different noise realizations
- tot_s=tot_s+s
- terr_s=terr_s+e
- terr_p=terr_p+(terr_s!=0)
- if ((i+1)%10==0) : # display progress
- print i+1,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_s,terr_s, '%.2e' % ((1.0*terr_s)/tot_s)
- # estimate of the (short or bit) error rate
- print rep,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_s,terr_s, '%.2e' % ((1.0*terr_s)/tot_s)
-
-
-
-if __name__ == '__main__':
- main (sys.argv[1:])
-
diff --git a/gr-trellis/examples/python/test_viterbi_equalization.py b/gr-trellis/examples/python/test_viterbi_equalization.py
deleted file mode 100755
index 987f171b2a..0000000000
--- a/gr-trellis/examples/python/test_viterbi_equalization.py
+++ /dev/null
@@ -1,99 +0,0 @@
-#!/usr/bin/env python
-
-from gnuradio import gr
-from gnuradio import trellis, digital, blocks
-from gnuradio import eng_notation
-import math
-import sys
-import fsm_utils
-
-try:
- from gnuradio import analog
-except ImportError:
- sys.stderr.write("Error: Program requires gr-analog.\n")
- sys.exit(1)
-
-def run_test (f,Kb,bitspersymbol,K,dimensionality,tot_constellation,N0,seed):
- tb = gr.top_block ()
-
- # TX
- src = blocks.lfsr_32k_source_s()
- src_head = blocks.head (gr.sizeof_short,Kb/16) # packet size in shorts
- s2fsmi = blocks.packed_to_unpacked_ss(bitspersymbol,gr.GR_MSB_FIRST) # unpack shorts to symbols compatible with the FSM input cardinality
- enc = trellis.encoder_ss(f,0) # initial state = 0
- # essentially here we implement the combination of modulation and channel as a memoryless modulation (the memory induced by the channel is hidden in the FSM)
- mod = digital.chunks_to_symbols_sf(tot_constellation,dimensionality)
-
- # CHANNEL
- add = blocks.add_ff()
- noise = analog.noise_source_f(analog.GR_GAUSSIAN,math.sqrt(N0/2),seed)
-
- # RX
- metrics = trellis.metrics_f(f.O(),dimensionality,tot_constellation,digital.TRELLIS_EUCLIDEAN) # data preprocessing to generate metrics for Viterbi
- va = trellis.viterbi_s(f,K,0,-1) # Put -1 if the Initial/Final states are not set.
- fsmi2s = blocks.unpacked_to_packed_ss(bitspersymbol,gr.GR_MSB_FIRST) # pack FSM input symbols to shorts
- dst = blocks.check_lfsr_32k_s();
-
- tb.connect (src,src_head,s2fsmi,enc,mod)
- tb.connect (mod,(add,0))
- tb.connect (noise,(add,1))
- tb.connect (add,metrics)
- tb.connect (metrics,va,fsmi2s,dst)
-
- tb.run()
-
- ntotal = dst.ntotal ()
- nright = dst.nright ()
- runlength = dst.runlength ()
- #print ntotal,nright,runlength
-
- return (ntotal,ntotal-nright)
-
-
-
-
-def main(args):
- nargs = len (args)
- if nargs == 2:
- esn0_db=float(args[0])
- rep=int(args[1])
- else:
- sys.stderr.write ('usage: test_viterbi_equalization.py Es/No_db repetitions\n')
- sys.exit (1)
-
- # system parameters
- Kb=128*16 # packet size in bits (multiple of 16)
- modulation = fsm_utils.pam4 # see fsm_utlis.py for available predefined modulations
- channel = fsm_utils.c_channel # see fsm_utlis.py for available predefined test channels
- f=trellis.fsm(len(modulation[1]),len(channel)) # generate the FSM automatically
- bitspersymbol = int(round(math.log(f.I())/math.log(2))) # bits per FSM input symbol
- K=Kb/bitspersymbol # packet size in trellis steps
-
- tot_channel = fsm_utils.make_isi_lookup(modulation,channel,True) # generate the lookup table (normalize energy to 1)
- dimensionality = tot_channel[0]
- tot_constellation = tot_channel[1]
- N0=pow(10.0,-esn0_db/10.0); # noise variance
- if len(tot_constellation)/dimensionality != f.O():
- sys.stderr.write ('Incompatible FSM output cardinality and lookup table size.\n')
- sys.exit (1)
-
-
- tot_s=0 # total number of transmitted shorts
- terr_s=0 # total number of shorts in error
- terr_p=0 # total number of packets in error
-
- for i in range(rep):
- (s,e)=run_test(f,Kb,bitspersymbol,K,dimensionality,tot_constellation,N0,-long(666+i)) # run experiment with different seed to get different noise realizations
- tot_s=tot_s+s
- terr_s=terr_s+e
- terr_p=terr_p+(terr_s!=0)
- if ((i+1)%100==0) : # display progress
- print i+1,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_s,terr_s, '%.2e' % ((1.0*terr_s)/tot_s)
- # estimate of the (short or bit) error rate
- print rep,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_s,terr_s, '%.2e' % ((1.0*terr_s)/tot_s)
-
-
-
-if __name__ == '__main__':
- main (sys.argv[1:])
-
diff --git a/gr-trellis/examples/python/test_viterbi_equalization1.py b/gr-trellis/examples/python/test_viterbi_equalization1.py
deleted file mode 100755
index baa6a27f1b..0000000000
--- a/gr-trellis/examples/python/test_viterbi_equalization1.py
+++ /dev/null
@@ -1,108 +0,0 @@
-#!/usr/bin/env python
-
-from gnuradio import gr
-from gnuradio import trellis, digital, filter, blocks
-from gnuradio import eng_notation
-import math
-import sys
-import random
-import fsm_utils
-
-try:
- from gnuradio import analog
-except ImportError:
- sys.stderr.write("Error: Program requires gr-analog.\n")
- sys.exit(1)
-
-def run_test (f,Kb,bitspersymbol,K,channel,modulation,dimensionality,tot_constellation,N0,seed):
- tb = gr.top_block ()
- L = len(channel)
-
- # TX
- # this for loop is TOO slow in python!!!
- packet = [0]*(K+2*L)
- random.seed(seed)
- for i in range(len(packet)):
- packet[i] = random.randint(0, 2**bitspersymbol - 1) # random symbols
- for i in range(L): # first/last L symbols set to 0
- packet[i] = 0
- packet[len(packet)-i-1] = 0
- src = blocks.vector_source_s(packet,False)
- mod = digital.chunks_to_symbols_sf(modulation[1],modulation[0])
-
- # CHANNEL
- isi = filter.fir_filter_fff(1,channel)
- add = blockss.add_ff()
- noise = analog.noise_source_f(analog.GR_GAUSSIAN,math.sqrt(N0/2),seed)
-
- # RX
- skip = blocks.skiphead(gr.sizeof_float, L) # skip the first L samples since you know they are coming from the L zero symbols
- #metrics = trellis.metrics_f(f.O(),dimensionality,tot_constellation,digital.TRELLIS_EUCLIDEAN) # data preprocessing to generate metrics for Viterbi
- #va = trellis.viterbi_s(f,K+L,-1,0) # Put -1 if the Initial/Final states are not set.
- va = trellis.viterbi_combined_fs(f,K+L,0,0,dimensionality,tot_constellation,digital.TRELLIS_EUCLIDEAN) # using viterbi_combined_fs instead of metrics_f/viterbi_s allows larger packet lengths because metrics_f is complaining for not being able to allocate large buffers. This is due to the large f.O() in this application...
- dst = blocks.vector_sink_s()
-
- tb.connect (src,mod)
- tb.connect (mod,isi,(add,0))
- tb.connect (noise,(add,1))
- #tb.connect (add,metrics)
- #tb.connect (metrics,va,dst)
- tb.connect (add,skip,va,dst)
-
- tb.run()
-
- data = dst.data()
- ntotal = len(data) - L
- nright=0
- for i in range(ntotal):
- if packet[i+L]==data[i]:
- nright=nright+1
- #else:
- #print "Error in ", i
-
- return (ntotal,ntotal-nright)
-
-
-def main(args):
- nargs = len (args)
- if nargs == 2:
- esn0_db=float(args[0])
- rep=int(args[1])
- else:
- sys.stderr.write ('usage: test_viterbi_equalization1.py Es/No_db repetitions\n')
- sys.exit (1)
-
- # system parameters
- Kb=128*16 # packet size in bits (multiple of 16)
- modulation = fsm_utils.pam4 # see fsm_utlis.py for available predefined modulations
- channel = fsm_utils.c_channel # see fsm_utlis.py for available predefined test channels
- f=trellis.fsm(len(modulation[1]),len(channel)) # generate the FSM automatically
- bitspersymbol = int(round(math.log(f.I())/math.log(2))) # bits per FSM input symbol
- K=Kb/bitspersymbol # packet size in trellis steps
-
- tot_channel = fsm_utils.make_isi_lookup(modulation,channel,True) # generate the lookup table (normalize energy to 1)
- dimensionality = tot_channel[0]
- tot_constellation = tot_channel[1]
- N0=pow(10.0,-esn0_db/10.0); # noise variance
- if len(tot_constellation)/dimensionality != f.O():
- sys.stderr.write ('Incompatible FSM output cardinality and lookup table size.\n')
- sys.exit (1)
-
- tot_s=0 # total number of transmitted shorts
- terr_s=0 # total number of shorts in error
- terr_p=0 # total number of packets in error
-
- for i in range(rep):
- (s,e)=run_test(f,Kb,bitspersymbol,K,channel,modulation,dimensionality,tot_constellation,N0,-long(666+i)) # run experiment with different seed to get different noise realizations
- tot_s=tot_s+s
- terr_s=terr_s+e
- terr_p=terr_p+(terr_s!=0)
- if ((i+1)%100==0) : # display progress
- print i+1,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_s,terr_s, '%.2e' % ((1.0*terr_s)/tot_s)
- # estimate of the (short or symbol) error rate
- print rep,terr_p, '%.2e' % ((1.0*terr_p)/(i+1)),tot_s,terr_s, '%.2e' % ((1.0*terr_s)/tot_s)
-
-
-
-if __name__ == '__main__':
- main (sys.argv[1:])
diff --git a/gr-trellis/gnuradio-trellis.pc.in b/gr-trellis/gnuradio-trellis.pc.in
index df7e2e2575..8ccf65b83f 100644
--- a/gr-trellis/gnuradio-trellis.pc.in
+++ b/gr-trellis/gnuradio-trellis.pc.in
@@ -4,7 +4,7 @@ libdir=@libdir@
includedir=@includedir@
Name: gnuradio-trellis
-Description: GNU Radio blocks for trellis coded modulation
+Description: GNU Radio blocks for trellis-based processing
Requires: gnuradio-runtime
Version: @LIBVER@
Libs: -L${libdir} -lgnuradio-trellis
diff --git a/gr-trellis/grc/trellis_encoder_xx.xml b/gr-trellis/grc/trellis_encoder_xx.xml
index d877d53c53..a2ad69278d 100644
--- a/gr-trellis/grc/trellis_encoder_xx.xml
+++ b/gr-trellis/grc/trellis_encoder_xx.xml
@@ -10,7 +10,9 @@
<key>trellis_encoder_xx</key>
<category>Trellis Coding</category>
<import>from gnuradio import trellis</import>
- <make>trellis.encoder_$(type)(trellis.fsm($fsm_args), $init_state)</make>
+ <make> trellis.encoder_$(type)(trellis.fsm($fsm_args), $init_state, $blocklength) if $blockwise else trellis.encoder_$(type)(trellis.fsm($fsm_args), $init_state) </make>
+ <callback>set_FSM(trellis.fsm($fsm_args))</callback>
+ <callback>set_ST($init_state)</callback>
<param>
<name>Type</name>
<key>type</key>
@@ -63,6 +65,28 @@
<value>0</value>
<type>int</type>
</param>
+ <param>
+ <name>Blockwise</name>
+ <key>blockwise</key>
+ <value>False</value>
+ <type>enum</type>
+ <hide>part</hide>
+ <option>
+ <name>On</name>
+ <key>True</key>
+ </option>
+ <option>
+ <name>Off</name>
+ <key>False</key>
+ </option>
+ </param>
+ <param>
+ <name>Block length</name>
+ <key>blocklength</key>
+ <value>0</value>
+ <type>int</type>
+ <hide>#if $blockwise() == 'True' then 'none' else 'all'#</hide>
+ </param>
<check>(isinstance(eval(""" $fsm_args """[1:-1], locals(),globals()), str) and open($fsm_args).close()) or True</check>
<sink>
<name>in</name>
diff --git a/gr-trellis/grc/trellis_metrics_x.xml b/gr-trellis/grc/trellis_metrics_x.xml
index f551bc1521..8bb978f275 100644
--- a/gr-trellis/grc/trellis_metrics_x.xml
+++ b/gr-trellis/grc/trellis_metrics_x.xml
@@ -12,6 +12,9 @@
<category>Trellis Coding</category>
<import>from gnuradio import trellis, digital</import>
<make>trellis.metrics_$(type)($card, $dim, $table, $metric_type)</make>
+ <callback>set_O($card)</callback>
+ <callback>set_D($dim)</callback>
+ <callback>set_TYPE($metric_type)</callback>
<callback>set_TABLE($table)</callback>
<param>
<name>Type</name>
diff --git a/gr-trellis/grc/trellis_pccc_decoder_combined_xx.xml b/gr-trellis/grc/trellis_pccc_decoder_combined_xx.xml
index 9bb4b034ac..ff727fbf8b 100644
--- a/gr-trellis/grc/trellis_pccc_decoder_combined_xx.xml
+++ b/gr-trellis/grc/trellis_pccc_decoder_combined_xx.xml
@@ -21,7 +21,7 @@
$dim, $table, $metric_type,
$scaling)
</make>
- <callback>set_TABLE($table)</callback>
+ <callback>set_scaling($scaling)</callback>
<param>
<name>Input Type</name>
<key>type</key>
diff --git a/gr-trellis/grc/trellis_permutation.xml b/gr-trellis/grc/trellis_permutation.xml
index bf6fc3ff15..0f118e889f 100644
--- a/gr-trellis/grc/trellis_permutation.xml
+++ b/gr-trellis/grc/trellis_permutation.xml
@@ -12,6 +12,10 @@
<category>Trellis Coding</category>
<import>from gnuradio import trellis</import>
<make>trellis.permutation($interleaver_size, $table, $syms_per_block, $type.size*$vlen)</make>
+ <callback>set_K($interleaver_size)</callback>
+ <callback>set_TABLE($table)</callback>
+ <callback>set_SYMS_PER_BLOCK($syms_per_block)</callback>
+
<param>
<name>Type</name>
<key>type</key>
diff --git a/gr-trellis/grc/trellis_sccc_decoder_combined_xx.xml b/gr-trellis/grc/trellis_sccc_decoder_combined_xx.xml
index bacc16cf5e..4947376d94 100644
--- a/gr-trellis/grc/trellis_sccc_decoder_combined_xx.xml
+++ b/gr-trellis/grc/trellis_sccc_decoder_combined_xx.xml
@@ -21,7 +21,7 @@
$dim, $table, $metric_type,
$scaling)
</make>
- <callback>set_TABLE($table)</callback>
+ <callback>set_scaling($scaling)</callback>
<param>
<name>Input Type</name>
<key>type</key>
diff --git a/gr-trellis/grc/trellis_siso_combined_f.xml b/gr-trellis/grc/trellis_siso_combined_f.xml
index 95eceeea31..542bba6d8b 100644
--- a/gr-trellis/grc/trellis_siso_combined_f.xml
+++ b/gr-trellis/grc/trellis_siso_combined_f.xml
@@ -12,6 +12,16 @@
<category>Trellis Coding</category>
<import>from gnuradio import trellis</import>
<make>trellis.siso_combined_f(trellis.fsm($fsm_args), $block_size, $init_state, $final_state, $a_post_in, $a_post_out, $siso_type, $dim, $table, $metric_type)</make>
+ <callback>set_FSM(trellis.fsm($fsm_args))</callback>
+ <callback>set_K($block_size)</callback>
+ <callback>set_S0($init_state)</callback>
+ <callback>set_SK($final_state)</callback>
+ <callback>set_POSTI($a_post_in)</callback>
+ <callback>set_POSTO($a_post_out)</callback>
+ <callback>set_SISO_TYPE($siso_type)</callback>
+ <callback>set_D($dim)</callback>
+ <callback>set_TABLE($table)</callback>
+ <callback>set_TYPE($metric_type)</callback>
<param>
<name>FSM Args</name>
<key>fsm_args</key>
@@ -101,7 +111,11 @@
</option>
</param>
<sink>
- <name>in</name>
+ <name>in_i</name>
+ <type>float</type>
+ </sink>
+ <sink>
+ <name>in_o</name>
<type>float</type>
</sink>
<source>
diff --git a/gr-trellis/grc/trellis_siso_f.xml b/gr-trellis/grc/trellis_siso_f.xml
index 67eeb27189..30849d2723 100644
--- a/gr-trellis/grc/trellis_siso_f.xml
+++ b/gr-trellis/grc/trellis_siso_f.xml
@@ -12,6 +12,13 @@
<category>Trellis Coding</category>
<import>from gnuradio import trellis</import>
<make>trellis.siso_f(trellis.fsm($fsm_args), $block_size, $init_state, $final_state, $a_post_in, $a_post_out, $siso_type)</make>
+ <callback>set_FSM(trellis.fsm($fsm_args))</callback>
+ <callback>set_K($block_size)</callback>
+ <callback>set_S0($init_state)</callback>
+ <callback>set_SK($final_state)</callback>
+ <callback>set_POSTI($a_post_in)</callback>
+ <callback>set_POSTO($a_post_out)</callback>
+ <callback>set_SISO_TYPE($siso_type)</callback>
<param>
<name>FSM Args</name>
<key>fsm_args</key>
@@ -75,7 +82,11 @@
</param>
<check>(isinstance(eval(""" $fsm_args """[1:-1], locals(),globals()), str) and open($fsm_args).close()) or True</check>
<sink>
- <name>in</name>
+ <name>priori</name>
+ <type>float</type>
+ </sink>
+ <sink>
+ <name>prioro</name>
<type>float</type>
</sink>
<source>
diff --git a/gr-trellis/grc/trellis_viterbi_combined_xx.xml b/gr-trellis/grc/trellis_viterbi_combined_xx.xml
index 81b49860a5..9c755dc524 100644
--- a/gr-trellis/grc/trellis_viterbi_combined_xx.xml
+++ b/gr-trellis/grc/trellis_viterbi_combined_xx.xml
@@ -12,7 +12,13 @@
<category>Trellis Coding</category>
<import>from gnuradio import trellis, digital</import>
<make>trellis.viterbi_combined_$(type)$(out_type)(trellis.fsm($fsm_args), $block_size, $init_state, $final_state, $dim, $table, $metric_type)</make>
- <callback>set_TABLE($table)</callback>
+ <callback>set_FSM(trellis.fsm($fsm_args))</callback>
+ <callback>set_K($block_size)</callback>
+ <callback>set_S0($init_state)</callback>
+ <callback>set_SK($final_state)</callback>
+ <callback>set_D($dim)</callback>
+ <callback>set_TABLE($table)</callback>
+ <callback>set_TYPE($metric_type)</callback>
<param>
<name>Input Type</name>
<key>type</key>
diff --git a/gr-trellis/grc/trellis_viterbi_x.xml b/gr-trellis/grc/trellis_viterbi_x.xml
index 734bb5386a..9083061e6b 100644
--- a/gr-trellis/grc/trellis_viterbi_x.xml
+++ b/gr-trellis/grc/trellis_viterbi_x.xml
@@ -12,6 +12,10 @@
<category>Trellis Coding</category>
<import>from gnuradio import trellis</import>
<make>trellis.viterbi_$(type)(trellis.fsm($fsm_args), $block_size, $init_state, $final_state)</make>
+ <callback>set_FSM(trellis.fsm($fsm_args))</callback>
+ <callback>set_K($block_size)</callback>
+ <callback>set_S0($init_state)</callback>
+ <callback>set_SK($final_state)</callback>
<param>
<name>Type</name>
<key>type</key>
diff --git a/gr-trellis/include/gnuradio/trellis/encoder_XX.h.t b/gr-trellis/include/gnuradio/trellis/encoder_XX.h.t
index 7ece5d3f21..affd62f68b 100644
--- a/gr-trellis/include/gnuradio/trellis/encoder_XX.h.t
+++ b/gr-trellis/include/gnuradio/trellis/encoder_XX.h.t
@@ -44,8 +44,14 @@ namespace gr {
static sptr make(const fsm &FSM, int ST);
+ static sptr make(const fsm &FSM, int ST, int K);
+
virtual fsm FSM() const = 0;
virtual int ST() const = 0;
+ virtual int K() const = 0;
+ virtual void set_FSM(const fsm &FSM) =0;
+ virtual void set_ST(int ST) =0;
+ virtual void set_K(int K) =0;
};
} /* namespace trellis */
diff --git a/gr-trellis/include/gnuradio/trellis/fsm.h b/gr-trellis/include/gnuradio/trellis/fsm.h
index cc8893f1e3..5ba4483b97 100644
--- a/gr-trellis/include/gnuradio/trellis/fsm.h
+++ b/gr-trellis/include/gnuradio/trellis/fsm.h
@@ -153,6 +153,16 @@ namespace gr {
* \param FSM2 second FSMS
*/
fsm(const fsm &FSM1, const fsm &FSM2);
+
+
+ /*!
+ * \brief Creates an FSMS describing the trellis of two serially concatenated FSMs.
+ *
+ * \param FSMo outer FSMS
+ * \param FSMi inner FSMS
+ * \param serial set it to true to distinguish from the previous constructor
+ */
+ fsm(const fsm &FSMo, const fsm &FSMi, bool serial);
/*!
* \brief Creates an FSMS representing n stages through the originial FSM (AKA radix-n FSM).
diff --git a/gr-trellis/include/gnuradio/trellis/metrics_X.h.t b/gr-trellis/include/gnuradio/trellis/metrics_X.h.t
index 3f650faf0e..f463c865a9 100644
--- a/gr-trellis/include/gnuradio/trellis/metrics_X.h.t
+++ b/gr-trellis/include/gnuradio/trellis/metrics_X.h.t
@@ -49,9 +49,14 @@ namespace gr {
virtual int D() const = 0;
virtual digital::trellis_metric_type_t TYPE() const = 0;
virtual std::vector<@I_TYPE@> TABLE() const = 0;
+
+ virtual void set_O(int O) = 0;
+ virtual void set_D(int D) = 0;
+ virtual void set_TYPE(digital::trellis_metric_type_t type) = 0;
virtual void set_TABLE(const std::vector<@I_TYPE@> &table) = 0;
};
+
} /* namespace trellis */
} /* namespace gr */
diff --git a/gr-trellis/include/gnuradio/trellis/permutation.h b/gr-trellis/include/gnuradio/trellis/permutation.h
index 80b9fef641..5c86f3c9a7 100644
--- a/gr-trellis/include/gnuradio/trellis/permutation.h
+++ b/gr-trellis/include/gnuradio/trellis/permutation.h
@@ -44,9 +44,14 @@ namespace gr {
int SYMS_PER_BLOCK, size_t NBYTES);
virtual int K() const = 0;
- virtual const std::vector<int> & TABLE() const = 0;
+ virtual std::vector<int> TABLE() const = 0;
virtual int SYMS_PER_BLOCK() const = 0;
virtual size_t BYTES_PER_SYMBOL() const = 0;
+
+ virtual void set_K(int K) =0;
+ virtual void set_TABLE (const std::vector<int> &table) = 0;
+ virtual void set_SYMS_PER_BLOCK(int spb) =0;
+
};
} /* namespace trellis */
diff --git a/gr-trellis/include/gnuradio/trellis/sccc_decoder_combined_XX.h.t b/gr-trellis/include/gnuradio/trellis/sccc_decoder_combined_XX.h.t
index 699de12fd8..e1f95dff1f 100644
--- a/gr-trellis/include/gnuradio/trellis/sccc_decoder_combined_XX.h.t
+++ b/gr-trellis/include/gnuradio/trellis/sccc_decoder_combined_XX.h.t
@@ -70,6 +70,7 @@ namespace gr {
virtual digital::trellis_metric_type_t METRIC_TYPE() const = 0;
virtual siso_type_t SISO_TYPE() const = 0;
virtual float scaling() const = 0;
+
virtual void set_scaling(float scaling) = 0;
};
diff --git a/gr-trellis/include/gnuradio/trellis/siso_combined_f.h b/gr-trellis/include/gnuradio/trellis/siso_combined_f.h
index 47c34ea81e..4c37b2c68d 100644
--- a/gr-trellis/include/gnuradio/trellis/siso_combined_f.h
+++ b/gr-trellis/include/gnuradio/trellis/siso_combined_f.h
@@ -60,6 +60,17 @@ namespace gr {
virtual int D() const = 0;
virtual std::vector<float> TABLE() const = 0;
virtual digital::trellis_metric_type_t TYPE() const = 0;
+
+ virtual void set_FSM(const fsm &FSM) =0;
+ virtual void set_K(int K) =0;
+ virtual void set_S0(int S0) =0;
+ virtual void set_SK(int SK) =0;
+ virtual void set_POSTI(bool POSTI) =0;
+ virtual void set_POSTO(bool POSTO) =0;
+ virtual void set_SISO_TYPE(trellis::siso_type_t type) =0;
+ virtual void set_D(int D) =0;
+ virtual void set_TABLE(const std::vector<float> &table) =0;
+ virtual void set_TYPE(digital::trellis_metric_type_t type) =0;
};
} /* namespace trellis */
diff --git a/gr-trellis/include/gnuradio/trellis/siso_f.h b/gr-trellis/include/gnuradio/trellis/siso_f.h
index ae212cb4cf..89bcba0e82 100644
--- a/gr-trellis/include/gnuradio/trellis/siso_f.h
+++ b/gr-trellis/include/gnuradio/trellis/siso_f.h
@@ -53,6 +53,14 @@ namespace gr {
virtual bool POSTI() const = 0;
virtual bool POSTO() const = 0;
virtual siso_type_t SISO_TYPE() const = 0;
+
+ virtual void set_FSM(const fsm &FSM) =0;
+ virtual void set_K(int K) =0;
+ virtual void set_S0(int S0) =0;
+ virtual void set_SK(int SK) =0;
+ virtual void set_POSTI(bool posti) =0;
+ virtual void set_POSTO(bool posto) =0;
+ virtual void set_SISO_TYPE(trellis::siso_type_t type) = 0;
};
} /* namespace trellis */
diff --git a/gr-trellis/include/gnuradio/trellis/viterbi_X.h.t b/gr-trellis/include/gnuradio/trellis/viterbi_X.h.t
index 2d72cb5e09..252ffb715d 100644
--- a/gr-trellis/include/gnuradio/trellis/viterbi_X.h.t
+++ b/gr-trellis/include/gnuradio/trellis/viterbi_X.h.t
@@ -45,10 +45,15 @@ namespace gr {
static sptr make(const fsm &FSM, int K,
int S0, int SK);
- virtual fsm FSM() const = 0;
- virtual int K() const = 0;
- virtual int S0() const = 0;
- virtual int SK() const = 0;
+ virtual fsm FSM() const = 0;
+ virtual int K() const = 0;
+ virtual int S0() const = 0;
+ virtual int SK() const = 0;
+
+ virtual void set_FSM(const fsm &FSM) =0;
+ virtual void set_K(int K) =0;
+ virtual void set_S0(int S0) =0;
+ virtual void set_SK(int SK) =0;
};
} /* namespace trellis */
diff --git a/gr-trellis/include/gnuradio/trellis/viterbi_combined_XX.h.t b/gr-trellis/include/gnuradio/trellis/viterbi_combined_XX.h.t
index 2becf8bf18..4546e95739 100644
--- a/gr-trellis/include/gnuradio/trellis/viterbi_combined_XX.h.t
+++ b/gr-trellis/include/gnuradio/trellis/viterbi_combined_XX.h.t
@@ -50,12 +50,19 @@ namespace gr {
virtual fsm FSM() const = 0;
virtual int K() const = 0;
- virtual int S0() const = 0;
+ virtual int S0() const = 0;
virtual int SK() const = 0;
virtual int D() const = 0;
virtual std::vector<@I_TYPE@> TABLE() const = 0;
virtual digital::trellis_metric_type_t TYPE() const = 0;
+
+ virtual void set_FSM(const fsm &FSM) =0;
+ virtual void set_K(int K) =0;
+ virtual void set_S0(int S0) =0;
+ virtual void set_SK(int SK) =0;
+ virtual void set_D(int D) =0;
virtual void set_TABLE (const std::vector<@I_TYPE@> &table) = 0;
+ virtual void set_TYPE(digital::trellis_metric_type_t type) = 0;
};
} /* namespace trellis */
diff --git a/gr-trellis/lib/calc_metric.cc b/gr-trellis/lib/calc_metric.cc
index b95899940a..bdbb13ea08 100644
--- a/gr-trellis/lib/calc_metric.cc
+++ b/gr-trellis/lib/calc_metric.cc
@@ -73,19 +73,17 @@ namespace gr {
}
template
- void calc_metric<short>(int O, int D, const std::vector<short> &TABLE, const short *input,
- float *metric, digital::trellis_metric_type_t type);
+ void calc_metric<char>(int O, int D, const std::vector<char> &TABLE, const char *input, float *metric, digital::trellis_metric_type_t type);
template
- void calc_metric<int>(int O, int D, const std::vector<int> &TABLE, const int *input,
- float *metric, digital::trellis_metric_type_t type);
+ void calc_metric<short>(int O, int D, const std::vector<short> &TABLE, const short *input, float *metric, digital::trellis_metric_type_t type);
- template
- void calc_metric<float>(int O, int D, const std::vector<float> &TABLE, const float *input,
- float *metric, digital::trellis_metric_type_t type);
+ template void calc_metric<int>(int O, int D, const std::vector<int> &TABLE, const int *input, float *metric, digital::trellis_metric_type_t type);
- void calc_metric(int O, int D, const std::vector<short> &TABLE, const short *input,
- float *metric, digital::trellis_metric_type_t type)
+ template void calc_metric<float>(int O, int D, const std::vector<float> &TABLE, const float *input, float *metric, digital::trellis_metric_type_t type);
+
+ /*
+ void calc_metric(int O, int D, const std::vector<short> &TABLE, const short *input, float *metric, digital::trellis_metric_type_t type)
{
float minm = FLT_MAX;
int minmi = 0;
@@ -124,7 +122,6 @@ namespace gr {
}
}
- /*
void calc_metric(int O, int D, const std::vector<int> &TABLE, const int *input,
float *metric, digital::trellis_metric_type_t type)
{
diff --git a/gr-trellis/lib/core_algorithms.cc b/gr-trellis/lib/core_algorithms.cc
index a8a0174551..b26ee331f2 100644
--- a/gr-trellis/lib/core_algorithms.cc
+++ b/gr-trellis/lib/core_algorithms.cc
@@ -215,6 +215,19 @@ namespace gr {
//---------------
template void
+ viterbi_algorithm_combined<char,unsigned char>(int I, int S, int O,
+ const std::vector<int> &NS,
+ const std::vector<int> &OS,
+ const std::vector< std::vector<int> > &PS,
+ const std::vector< std::vector<int> > &PI,
+ int K,
+ int S0,int SK,
+ int D,
+ const std::vector<char> &TABLE,
+ digital::trellis_metric_type_t TYPE,
+ const char *in, unsigned char *out);
+
+ template void
viterbi_algorithm_combined<short,unsigned char>(int I, int S, int O,
const std::vector<int> &NS,
const std::vector<int> &OS,
@@ -269,6 +282,19 @@ namespace gr {
//---------------
template void
+ viterbi_algorithm_combined<char,short>(int I, int S, int O,
+ const std::vector<int> &NS,
+ const std::vector<int> &OS,
+ const std::vector< std::vector<int> > &PS,
+ const std::vector< std::vector<int> > &PI,
+ int K,
+ int S0,int SK,
+ int D,
+ const std::vector<char> &TABLE,
+ digital::trellis_metric_type_t TYPE,
+ const char *in, short *out);
+
+ template void
viterbi_algorithm_combined<short,short>(int I, int S, int O,
const std::vector<int> &NS,
const std::vector<int> &OS,
@@ -323,6 +349,19 @@ namespace gr {
//--------------
template void
+ viterbi_algorithm_combined<char,int>(int I, int S, int O,
+ const std::vector<int> &NS,
+ const std::vector<int> &OS,
+ const std::vector< std::vector<int> > &PS,
+ const std::vector< std::vector<int> > &PI,
+ int K,
+ int S0,int SK,
+ int D,
+ const std::vector<char> &TABLE,
+ digital::trellis_metric_type_t TYPE,
+ const char *in, int *out);
+
+ template void
viterbi_algorithm_combined<short,int>(int I, int S, int O,
const std::vector<int> &NS,
const std::vector<int> &OS,
@@ -1177,17 +1216,17 @@ namespace gr {
for(int k=0;k<blocklength;k++) {
//std::cout << k << std::endl;
for(int i=0;i<FSM1.O();i++) {
- float x=cprioro[k*FSM1.O()*FSM2.O()+i*FSM1.O()+0];
+ float x=cprioro[k*O+i*FSM2.O()+0];
for(int j=1;j<FSM2.O();j++)
- x = (*p2mymin)(x,cprioro[k*FSM1.O()*FSM2.O()+i*FSM1.O()+j]);
+ x = (*p2mymin)(x,cprioro[k*O+i*FSM2.O()+j]);
prioro1[k*FSM1.O()+i]=x;
//std::cout << prioro1[k*FSM1.O()+i] << ", ";
}
//std::cout << std::endl;
for(int i=0;i<FSM2.O();i++) {
- float x=cprioro[k*FSM1.O()*FSM2.O()+0*FSM1.O()+i];
+ float x=cprioro[k*O+0*FSM2.O()+i];
for(int j=1;j<FSM1.O();j++)
- x = (*p2mymin)(x,cprioro[k*FSM1.O()*FSM2.O()+j*FSM1.O()+i]);
+ x = (*p2mymin)(x,cprioro[k*O+j*FSM2.O()+i]);
prioro2[k*FSM2.O()+i]=x;
}
}
diff --git a/gr-trellis/lib/encoder_XX_impl.cc.t b/gr-trellis/lib/encoder_XX_impl.cc.t
index 4b11e3c06d..3a004a2f94 100644
--- a/gr-trellis/lib/encoder_XX_impl.cc.t
+++ b/gr-trellis/lib/encoder_XX_impl.cc.t
@@ -37,18 +37,45 @@ namespace gr {
@BASE_NAME@::make(const fsm &FSM, int ST)
{
return gnuradio::get_initial_sptr
- (new @IMPL_NAME@(FSM,ST));
+ (new @IMPL_NAME@(FSM,ST,0,false));
}
- @IMPL_NAME@::@IMPL_NAME@(const fsm &FSM, int ST)
+ @BASE_NAME@::sptr
+ @BASE_NAME@::make(const fsm &FSM, int ST, int K)
+ {
+ return gnuradio::get_initial_sptr
+ (new @IMPL_NAME@(FSM,ST,K,true));
+ }
+
+ @IMPL_NAME@::@IMPL_NAME@(const fsm &FSM, int ST, int K, bool B)
: sync_block("@BASE_NAME@",
- io_signature::make(1, -1, sizeof(@I_TYPE@)),
- io_signature::make(1, -1, sizeof(@O_TYPE@))),
+ io_signature::make(1, 1, sizeof(@I_TYPE@)),
+ io_signature::make(1, 1, sizeof(@O_TYPE@))),
d_FSM(FSM),
- d_ST(ST)
+ d_ST(ST),
+ d_K(K),
+ d_B(B)
{
}
+ void @IMPL_NAME@::set_FSM(const fsm &FSM)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_FSM = FSM;
+ }
+
+ void @IMPL_NAME@::set_ST(int ST)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_ST = ST;
+ }
+
+ void @IMPL_NAME@::set_K(int K)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_K = K;
+ }
+
@IMPL_NAME@::~@IMPL_NAME@()
{
}
@@ -58,25 +85,34 @@ namespace gr {
gr_vector_const_void_star &input_items,
gr_vector_void_star &output_items)
{
+ gr::thread::scoped_lock guard(d_setlock);
int ST_tmp = 0;
- int nstreams = input_items.size();
- for(int m=0;m<nstreams;m++) {
- const @I_TYPE@ *in = (const @I_TYPE@*)input_items[m];
- @O_TYPE@ *out = (@O_TYPE@ *) output_items[m];
- ST_tmp = d_ST;
-
- // per stream processing
- for(int i = 0; i < noutput_items; i++) {
- out[i] = (@O_TYPE@)d_FSM.OS()[ST_tmp*d_FSM.I()+in[i]]; // direction of time?
- ST_tmp = (int)d_FSM.NS()[ST_tmp*d_FSM.I()+in[i]];
- }
- // end per stream processing
- }
- d_ST = ST_tmp;
-
- return noutput_items;
- }
+ if (d_B){ // blockwise operation
+ int nblocks = noutput_items /d_K;
+ const @I_TYPE@ *in = (const @I_TYPE@*)input_items[0];
+ @O_TYPE@ *out = (@O_TYPE@ *) output_items[0];
+ for(int n = 0; n < nblocks; n++) {
+ ST_tmp = d_ST;
+ for(int i = 0; i < d_K; i++) {
+ out[n*d_K+i] = (@O_TYPE@)d_FSM.OS()[ST_tmp*d_FSM.I()+in[n*d_K+i]];
+ ST_tmp = (int)d_FSM.NS()[ST_tmp*d_FSM.I()+in[n*d_K+i]];
+ }
+ }
+ return nblocks*d_K;
+ } // end blockwise operation
+ else{ // streaming operation
+ const @I_TYPE@ *in = (const @I_TYPE@*)input_items[0];
+ @O_TYPE@ *out = (@O_TYPE@ *) output_items[0];
+ ST_tmp = d_ST;
+ for(int i = 0; i < noutput_items; i++) {
+ out[i] = (@O_TYPE@)d_FSM.OS()[ST_tmp*d_FSM.I()+in[i]];
+ ST_tmp = (int)d_FSM.NS()[ST_tmp*d_FSM.I()+in[i]];
+ }
+ d_ST = ST_tmp;
+ return noutput_items;
+ } // end streaming operation
+ }
} /* namespace trellis */
} /* namespace gr */
diff --git a/gr-trellis/lib/encoder_XX_impl.h.t b/gr-trellis/lib/encoder_XX_impl.h.t
index ec2f82611e..2b0ff31f4d 100644
--- a/gr-trellis/lib/encoder_XX_impl.h.t
+++ b/gr-trellis/lib/encoder_XX_impl.h.t
@@ -35,14 +35,20 @@ namespace gr {
private:
fsm d_FSM;
int d_ST;
+ int d_K;
+ bool d_B;
+
public:
- @IMPL_NAME@(const fsm &FSM, int ST);
+ @IMPL_NAME@(const fsm &FSM, int ST, int K, bool B);
~@IMPL_NAME@();
- fsm FSM() const { return d_FSM; }
- int ST() const { return d_ST; }
-
+ fsm FSM() const { return d_FSM;; }
+ int ST() const { return d_ST; }
+ int K() const { return d_K; }
+ void set_FSM(const fsm &FSM);
+ void set_ST(int ST);
+ void set_K(int K);
int work(int noutput_items,
gr_vector_const_void_star &input_items,
gr_vector_void_star &output_items);
diff --git a/gr-trellis/lib/fsm.cc b/gr-trellis/lib/fsm.cc
index 20eeed5c25..4e57949f5e 100644
--- a/gr-trellis/lib/fsm.cc
+++ b/gr-trellis/lib/fsm.cc
@@ -313,6 +313,54 @@ namespace gr {
generate_TM();
}
+
+ //######################################################################
+ //# Automatically generate an FSM specification describing the
+ //# the joint trellis of two serially concatenated fsms.
+ //######################################################################
+ fsm::fsm(const fsm &FSMo, const fsm &FSMi, bool serial)
+ {
+ if(serial==false || FSMo.O()!=FSMi.I()) {
+ d_I=0;
+ d_S=0;
+ d_O=0;
+ d_NS.resize(0);
+ d_OS.resize(0);
+ d_PS.resize(0);
+ d_PI.resize(0);
+ d_TMi.resize(0);
+ d_TMl.resize(0);
+ return;
+ }
+
+ d_I=FSMo.I();
+ d_S=FSMo.S()*FSMi.S();
+ d_O=FSMi.O();
+
+ d_NS.resize(d_I*d_S);
+ d_OS.resize(d_I*d_S);
+
+ for(int s=0;s<d_S;s++) {
+ for(int i=0;i<d_I;i++) {
+ int so=s/FSMi.S();
+ int si=s%FSMi.S();
+ int oo=FSMo.OS()[so * FSMo.I() + i];
+ int oi=FSMi.OS()[si * FSMi.I() + oo];
+ d_NS[s*d_I+i] = FSMo.NS()[so * FSMo.I() + i] * FSMo.S() + FSMi.NS()[si * FSMi.I() + oo];
+ d_OS[s*d_I+i] = oi;
+ }
+ }
+
+ generate_PS_PI();
+ generate_TM();
+ }
+
+
+
+
+
+
+
//######################################################################
//# Generate a new FSM representing n stages through the original FSM
//# AKA radix-n FSM
diff --git a/gr-trellis/lib/metrics_X_impl.cc.t b/gr-trellis/lib/metrics_X_impl.cc.t
index 499bd8b9cd..5e74e4b2fc 100644
--- a/gr-trellis/lib/metrics_X_impl.cc.t
+++ b/gr-trellis/lib/metrics_X_impl.cc.t
@@ -54,16 +54,40 @@ namespace gr {
set_output_multiple ((int)d_O);
}
- @IMPL_NAME@::~@IMPL_NAME@()
+ void @IMPL_NAME@::set_O(int O)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_O = O;
+ set_relative_rate (1.0 * d_O / ((double) d_D));
+ set_output_multiple ((int)d_O);
+ }
+
+ void @IMPL_NAME@::set_D(int D)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_D = D;
+ set_relative_rate (1.0 * d_O / ((double) d_D));
+ }
+
+ void
+ @IMPL_NAME@::set_TYPE(digital::trellis_metric_type_t type)
{
+ gr::thread::scoped_lock guard(d_setlock);
+ d_TYPE = type;
}
void
@IMPL_NAME@::set_TABLE(const std::vector<@I_TYPE@> &table)
{
+ gr::thread::scoped_lock guard(d_setlock);
d_TABLE = table;
}
+ @IMPL_NAME@::~@IMPL_NAME@()
+ {
+ }
+
+
void
@IMPL_NAME@::forecast(int noutput_items, gr_vector_int &ninput_items_required)
{
@@ -79,6 +103,7 @@ namespace gr {
gr_vector_const_void_star &input_items,
gr_vector_void_star &output_items)
{
+ gr::thread::scoped_lock guard(d_setlock);
int nstreams = input_items.size();
for(int m = 0; m < nstreams; m++) {
diff --git a/gr-trellis/lib/metrics_X_impl.h.t b/gr-trellis/lib/metrics_X_impl.h.t
index 2b4481fdb1..9323ae4645 100644
--- a/gr-trellis/lib/metrics_X_impl.h.t
+++ b/gr-trellis/lib/metrics_X_impl.h.t
@@ -47,6 +47,10 @@ namespace gr {
int D() const { return d_D; }
digital::trellis_metric_type_t TYPE() const { return d_TYPE; }
std::vector<@I_TYPE@> TABLE() const { return d_TABLE; }
+
+ void set_O(int O);
+ void set_D(int D);
+ void set_TYPE(digital::trellis_metric_type_t type);
void set_TABLE(const std::vector<@I_TYPE@> &table);
void forecast(int noutput_items,
diff --git a/gr-trellis/lib/pccc_decoder_combined_XX_impl.cc.t b/gr-trellis/lib/pccc_decoder_combined_XX_impl.cc.t
index 15ea3ceecb..5b3cdeeb62 100644
--- a/gr-trellis/lib/pccc_decoder_combined_XX_impl.cc.t
+++ b/gr-trellis/lib/pccc_decoder_combined_XX_impl.cc.t
@@ -90,6 +90,7 @@ namespace gr {
void
@IMPL_NAME@::set_scaling(float scaling)
{
+ gr::thread::scoped_lock guard(d_setlock);
d_scaling = scaling;
}
@@ -109,6 +110,7 @@ namespace gr {
gr_vector_const_void_star &input_items,
gr_vector_void_star &output_items)
{
+ gr::thread::scoped_lock guard(d_setlock);
int nblocks = noutput_items / d_blocklength;
float (*p2min)(float, float) = NULL;
diff --git a/gr-trellis/lib/pccc_encoder_XX_impl.cc.t b/gr-trellis/lib/pccc_encoder_XX_impl.cc.t
index 119bff6ddb..8fd143ca9d 100644
--- a/gr-trellis/lib/pccc_encoder_XX_impl.cc.t
+++ b/gr-trellis/lib/pccc_encoder_XX_impl.cc.t
@@ -81,7 +81,7 @@ namespace gr {
ST1_tmp = (int) d_FSM1.NS()[ST1_tmp*d_FSM1.I()+in[i]];
int o2 = d_FSM2.OS()[ST2_tmp*d_FSM2.I()+in[k]];
ST2_tmp = (int) d_FSM2.NS()[ST2_tmp*d_FSM2.I()+in[k]];
- out[i] = (@O_TYPE@) (o1*d_FSM1.O() + o2);
+ out[i] = (@O_TYPE@) (o1*d_FSM2.O() + o2);
}
}
return noutput_items;
diff --git a/gr-trellis/lib/permutation_impl.cc b/gr-trellis/lib/permutation_impl.cc
index 06bba1e11f..2fe0ea8cb8 100644
--- a/gr-trellis/lib/permutation_impl.cc
+++ b/gr-trellis/lib/permutation_impl.cc
@@ -49,10 +49,30 @@ namespace gr {
d_SYMS_PER_BLOCK(SYMS_PER_BLOCK),
d_BYTES_PER_SYMBOL(BYTES_PER_SYMBOL)
{
- set_output_multiple(d_K*SYMS_PER_BLOCK);
+ set_output_multiple(d_K*d_SYMS_PER_BLOCK);
//std::cout << d_K << "\n";
}
+ void permutation_impl::set_K(int K)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_K=K;
+ set_output_multiple(d_K*d_SYMS_PER_BLOCK);
+ }
+
+ void permutation_impl::set_TABLE (const std::vector<int> &table)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_TABLE = table;
+ }
+
+ void permutation_impl::set_SYMS_PER_BLOCK(int spb)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_SYMS_PER_BLOCK=spb;
+ set_output_multiple(d_K*d_SYMS_PER_BLOCK);
+ }
+
permutation_impl::~permutation_impl()
{
}
@@ -62,6 +82,7 @@ namespace gr {
gr_vector_const_void_star &input_items,
gr_vector_void_star &output_items)
{
+ gr::thread::scoped_lock guard(d_setlock);
int nstreams = input_items.size();
for(int m=0;m<nstreams;m++) {
diff --git a/gr-trellis/lib/permutation_impl.h b/gr-trellis/lib/permutation_impl.h
index 2c7b28d62f..e013e52a20 100644
--- a/gr-trellis/lib/permutation_impl.h
+++ b/gr-trellis/lib/permutation_impl.h
@@ -43,10 +43,14 @@ namespace gr {
~permutation_impl();
int K() const { return d_K; }
- const std::vector<int> & TABLE() const { return d_TABLE; }
+ std::vector<int> TABLE() const { return d_TABLE; }
int SYMS_PER_BLOCK() const { return d_SYMS_PER_BLOCK; }
size_t BYTES_PER_SYMBOL() const { return d_BYTES_PER_SYMBOL; }
+ void set_K(int K) ;
+ void set_TABLE (const std::vector<int> &table);
+ void set_SYMS_PER_BLOCK(int spb) ;
+
int work(int noutput_items,
gr_vector_const_void_star &input_items,
gr_vector_void_star &output_items);
diff --git a/gr-trellis/lib/sccc_decoder_combined_XX_impl.cc.t b/gr-trellis/lib/sccc_decoder_combined_XX_impl.cc.t
index 4acc560175..f66b1f37e7 100644
--- a/gr-trellis/lib/sccc_decoder_combined_XX_impl.cc.t
+++ b/gr-trellis/lib/sccc_decoder_combined_XX_impl.cc.t
@@ -89,6 +89,7 @@ namespace gr {
void
@IMPL_NAME@::set_scaling(float scaling)
{
+ gr::thread::scoped_lock guard(d_setlock);
d_scaling = scaling;
}
@@ -108,6 +109,7 @@ namespace gr {
gr_vector_const_void_star &input_items,
gr_vector_void_star &output_items)
{
+ gr::thread::scoped_lock guard(d_setlock);
int nblocks = noutput_items / d_blocklength;
float (*p2min)(float, float) = NULL;
diff --git a/gr-trellis/lib/siso_combined_f_impl.cc b/gr-trellis/lib/siso_combined_f_impl.cc
index d30f5cc4bb..3b89684bf0 100644
--- a/gr-trellis/lib/siso_combined_f_impl.cc
+++ b/gr-trellis/lib/siso_combined_f_impl.cc
@@ -48,23 +48,9 @@ namespace gr {
SISO_TYPE, D, TABLE, TYPE));
}
- siso_combined_f_impl::siso_combined_f_impl(const fsm &FSM, int K,
- int S0, int SK,
- bool POSTI, bool POSTO,
- siso_type_t SISO_TYPE,
- int D, const std::vector<float> &TABLE,
- digital::trellis_metric_type_t TYPE)
- : block("siso_combined_f",
- io_signature::make(1, -1, sizeof(float)),
- io_signature::make(1, -1, sizeof(float))),
- d_FSM(FSM), d_K(K), d_S0(S0), d_SK(SK),
- d_POSTI(POSTI), d_POSTO(POSTO),
- d_SISO_TYPE(SISO_TYPE),
- d_D(D), d_TABLE(TABLE), d_TYPE(TYPE)//,
- //d_alpha(FSM.S()*(K+1)),
- //d_beta(FSM.S()*(K+1))
+ void siso_combined_f_impl::recalculate()
{
- int multiple;
+ int multiple;
if(d_POSTI && d_POSTO)
multiple = d_FSM.I()+d_FSM.O();
else if(d_POSTI)
@@ -74,7 +60,6 @@ namespace gr {
else
throw std::runtime_error ("Not both POSTI and POSTO can be false.");
- //printf("constructor: Multiple = %d\n",multiple);
set_output_multiple(d_K*multiple);
//what is the meaning of relative rate for a block with 2 inputs?
@@ -84,9 +69,94 @@ namespace gr {
//set_relative_rate ( multiple / ((double) d_FSM.O()) );
// I am tempted to automate like this
if(d_FSM.I() <= d_D)
- set_relative_rate(multiple / ((double)d_D));
+ set_relative_rate(multiple / ((double)d_D));
else
- set_relative_rate(multiple / ((double)d_FSM.I()));
+ set_relative_rate(multiple / ((double)d_FSM.I()));
+ }
+
+
+ siso_combined_f_impl::siso_combined_f_impl(const fsm &FSM, int K,
+ int S0, int SK,
+ bool POSTI, bool POSTO,
+ siso_type_t SISO_TYPE,
+ int D, const std::vector<float> &TABLE,
+ digital::trellis_metric_type_t TYPE)
+ : block("siso_combined_f",
+ io_signature::make(1, -1, sizeof(float)),
+ io_signature::make(1, -1, sizeof(float))),
+ d_FSM(FSM), d_K(K), d_S0(S0), d_SK(SK),
+ d_POSTI(POSTI), d_POSTO(POSTO),
+ d_SISO_TYPE(SISO_TYPE),
+ d_D(D), d_TABLE(TABLE), d_TYPE(TYPE)//,
+ //d_alpha(FSM.S()*(K+1)),
+ //d_beta(FSM.S()*(K+1))
+ {
+ recalculate();
+ }
+
+ void siso_combined_f_impl::set_FSM(const fsm &FSM)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_FSM=FSM;
+ recalculate();
+ }
+
+ void siso_combined_f_impl::set_K(int K)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_K=K;
+ recalculate();
+ }
+
+ void siso_combined_f_impl::set_POSTI(bool POSTI)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_POSTI = POSTI;
+ recalculate();
+ }
+
+ void siso_combined_f_impl::set_POSTO(bool POSTO)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_POSTO = POSTO;
+ recalculate();
+ }
+
+ void siso_combined_f_impl::set_D(int D)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_D=D;
+ recalculate();
+ }
+
+ void siso_combined_f_impl::set_S0(int S0)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_S0 = S0;
+ }
+
+ void siso_combined_f_impl::set_SK(int SK)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_SK = SK;
+ }
+
+ void siso_combined_f_impl::set_SISO_TYPE(trellis::siso_type_t type)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_SISO_TYPE = type;
+ }
+
+ void siso_combined_f_impl::set_TABLE(const std::vector<float> &table)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_TABLE = table;
+ }
+
+ void siso_combined_f_impl::set_TYPE(digital::trellis_metric_type_t type)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_TYPE = type;
}
siso_combined_f_impl::~siso_combined_f_impl()
@@ -126,6 +196,7 @@ namespace gr {
gr_vector_const_void_star &input_items,
gr_vector_void_star &output_items)
{
+ gr::thread::scoped_lock guard(d_setlock);
int nstreams = output_items.size();
//printf("general_work:Streams: %d\n",nstreams);
diff --git a/gr-trellis/lib/siso_combined_f_impl.h b/gr-trellis/lib/siso_combined_f_impl.h
index 5035a0a83d..93e9aa87d2 100644
--- a/gr-trellis/lib/siso_combined_f_impl.h
+++ b/gr-trellis/lib/siso_combined_f_impl.h
@@ -41,6 +41,7 @@ namespace gr {
int d_D;
std::vector<float> d_TABLE;
digital::trellis_metric_type_t d_TYPE;
+ void recalculate();
//std::vector<float> d_alpha;
//std::vector<float> d_beta;
@@ -64,6 +65,17 @@ namespace gr {
std::vector<float> TABLE() const { return d_TABLE; }
digital::trellis_metric_type_t TYPE() const { return d_TYPE; }
+ void set_FSM(const fsm &FSM);
+ void set_K(int K);
+ void set_S0(int S0);
+ void set_SK(int SK);
+ void set_POSTI(bool POSTI);
+ void set_POSTO(bool POSTO);
+ void set_SISO_TYPE(trellis::siso_type_t type);
+ void set_D(int D);
+ void set_TABLE(const std::vector<float> &table);
+ void set_TYPE(digital::trellis_metric_type_t type);
+
void forecast(int noutput_items,
gr_vector_int &ninput_items_required);
diff --git a/gr-trellis/lib/siso_f_impl.cc b/gr-trellis/lib/siso_f_impl.cc
index d699cecaec..2af5a21710 100644
--- a/gr-trellis/lib/siso_f_impl.cc
+++ b/gr-trellis/lib/siso_f_impl.cc
@@ -45,19 +45,8 @@ namespace gr {
(new siso_f_impl(FSM, K, S0, SK, POSTI, POSTO, SISO_TYPE));
}
- siso_f_impl::siso_f_impl(const fsm &FSM, int K,
- int S0, int SK,
- bool POSTI, bool POSTO,
- siso_type_t SISO_TYPE)
- : block("siso_f",
- io_signature::make(1, -1, sizeof(float)),
- io_signature::make(1, -1, sizeof(float))),
- d_FSM(FSM), d_K(K),
- d_S0(S0),d_SK(SK),
- d_POSTI(POSTI), d_POSTO(POSTO),
- d_SISO_TYPE(SISO_TYPE)//,
- //d_alpha(FSM.S()*(K+1)),
- //d_beta(FSM.S()*(K+1))
+
+ void siso_f_impl::recalculate()
{
int multiple;
if(d_POSTI && d_POSTO)
@@ -69,7 +58,6 @@ namespace gr {
else
throw std::runtime_error ("Not both POSTI and POSTO can be false.");
- //printf("constructor: Multiple = %d\n",multiple);
set_output_multiple (d_K*multiple);
//what is the meaning of relative rate for a block with 2 inputs?
@@ -84,6 +72,69 @@ namespace gr {
set_relative_rate(multiple / ((double) d_FSM.I()));
}
+ siso_f_impl::siso_f_impl(const fsm &FSM, int K,
+ int S0, int SK,
+ bool POSTI, bool POSTO,
+ siso_type_t SISO_TYPE)
+ : block("siso_f",
+ io_signature::make(1, -1, sizeof(float)),
+ io_signature::make(1, -1, sizeof(float))),
+ d_FSM(FSM), d_K(K),
+ d_S0(S0),d_SK(SK),
+ d_POSTI(POSTI), d_POSTO(POSTO),
+ d_SISO_TYPE(SISO_TYPE)//,
+ //d_alpha(FSM.S()*(K+1)),
+ //d_beta(FSM.S()*(K+1))
+ {
+ recalculate();
+ }
+
+ void siso_f_impl::set_FSM(const fsm &FSM)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_FSM=FSM;
+ recalculate();
+ }
+
+ void siso_f_impl::set_K(int K)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_K=K;
+ recalculate();
+ }
+
+ void siso_f_impl::set_POSTI(bool POSTI)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_POSTI = POSTI;
+ recalculate();
+ }
+
+ void siso_f_impl::set_POSTO(bool POSTO)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_POSTO = POSTO;
+ recalculate();
+ }
+
+ void siso_f_impl::set_S0(int S0)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_S0 = S0;
+ }
+
+ void siso_f_impl::set_SK(int SK)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_SK = SK;
+ }
+
+ void siso_f_impl::set_SISO_TYPE(trellis::siso_type_t type)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_SISO_TYPE = type;
+ }
+
siso_f_impl::~siso_f_impl()
{
}
@@ -119,6 +170,7 @@ namespace gr {
gr_vector_const_void_star &input_items,
gr_vector_void_star &output_items)
{
+ gr::thread::scoped_lock guard(d_setlock);
int nstreams = output_items.size();
//printf("general_work:Streams: %d\n",nstreams);
int multiple;
diff --git a/gr-trellis/lib/siso_f_impl.h b/gr-trellis/lib/siso_f_impl.h
index ca8f623aaf..f92616bf0a 100644
--- a/gr-trellis/lib/siso_f_impl.h
+++ b/gr-trellis/lib/siso_f_impl.h
@@ -42,6 +42,7 @@ namespace gr {
bool d_POSTI;
bool d_POSTO;
siso_type_t d_SISO_TYPE;
+ void recalculate();
//std::vector<float> d_alpha;
//std::vector<float> d_beta;
@@ -60,6 +61,14 @@ namespace gr {
bool POSTO() const { return d_POSTO; }
siso_type_t SISO_TYPE() const { return d_SISO_TYPE; }
+ void set_FSM(const fsm &FSM);
+ void set_K(int K);
+ void set_S0(int S0);
+ void set_SK(int SK);
+ void set_POSTI(bool POSTI);
+ void set_POSTO(bool POSTO);
+ void set_SISO_TYPE(trellis::siso_type_t type);
+
void forecast(int noutput_items,
gr_vector_int &ninput_items_required);
diff --git a/gr-trellis/lib/viterbi_X_impl.cc.t b/gr-trellis/lib/viterbi_X_impl.cc.t
index 247424b3f3..1d4864596e 100644
--- a/gr-trellis/lib/viterbi_X_impl.cc.t
+++ b/gr-trellis/lib/viterbi_X_impl.cc.t
@@ -55,6 +55,32 @@ namespace gr {
set_output_multiple(d_K);
}
+ void @IMPL_NAME@::set_FSM(const fsm &FSM)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_FSM = FSM;
+ set_relative_rate(1.0 / ((double)d_FSM.O()));
+ }
+
+ void @IMPL_NAME@::set_K(int K)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_K = K;
+ set_output_multiple(d_K);
+ }
+
+ void @IMPL_NAME@::set_S0(int S0)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_S0 = S0;
+ }
+
+ void @IMPL_NAME@::set_SK(int SK)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_SK = SK;
+ }
+
@IMPL_NAME@::~@IMPL_NAME@()
{
}
@@ -76,6 +102,7 @@ namespace gr {
gr_vector_const_void_star &input_items,
gr_vector_void_star &output_items)
{
+ gr::thread::scoped_lock guard(d_setlock);
int nstreams = input_items.size();
int nblocks = noutput_items / d_K;
diff --git a/gr-trellis/lib/viterbi_X_impl.h.t b/gr-trellis/lib/viterbi_X_impl.h.t
index b9554e8c39..1479ad5a3f 100644
--- a/gr-trellis/lib/viterbi_X_impl.h.t
+++ b/gr-trellis/lib/viterbi_X_impl.h.t
@@ -44,11 +44,15 @@ namespace gr {
int S0, int SK);
~@IMPL_NAME@();
- fsm FSM() const { return d_FSM; }
- int K() const { return d_K; }
- int S0() const { return d_S0; }
- int SK() const { return d_SK; }
+ fsm FSM() const { return d_FSM; }
+ int K() const { return d_K; }
+ int S0() const { return d_S0; }
+ int SK() const { return d_SK; }
+ void set_FSM(const fsm &FSM);
+ void set_K(int K);
+ void set_S0(int S0);
+ void set_SK(int SK);
//std::vector<int> trace () const { return d_trace; }
void forecast(int noutput_items,
diff --git a/gr-trellis/lib/viterbi_combined_XX_impl.cc.t b/gr-trellis/lib/viterbi_combined_XX_impl.cc.t
index c7cf10e567..722708bcd2 100644
--- a/gr-trellis/lib/viterbi_combined_XX_impl.cc.t
+++ b/gr-trellis/lib/viterbi_combined_XX_impl.cc.t
@@ -60,16 +60,58 @@ namespace gr {
set_output_multiple(d_K);
}
- @IMPL_NAME@::~@IMPL_NAME@()
+ void
+ @IMPL_NAME@::set_K(int K)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_K = K;
+ set_output_multiple(d_K);
+ }
+
+ void
+ @IMPL_NAME@::set_D(int D)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_D = D;
+ set_relative_rate(1.0 / ((double)d_D));
+ }
+
+ void @IMPL_NAME@::set_FSM(const fsm &FSM)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_FSM = FSM;
+ }
+
+ void @IMPL_NAME@::set_S0(int S0)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_S0 = S0;
+ }
+
+ void @IMPL_NAME@::set_SK(int SK)
+ {
+ gr::thread::scoped_lock guard(d_setlock);
+ d_SK = SK;
+ }
+
+ void
+ @IMPL_NAME@::set_TYPE(digital::trellis_metric_type_t type)
{
+ gr::thread::scoped_lock guard(d_setlock);
+ d_TYPE = type;
}
void
@IMPL_NAME@::set_TABLE(const std::vector<@I_TYPE@> &table)
{
+ gr::thread::scoped_lock guard(d_setlock);
d_TABLE = table;
}
+ @IMPL_NAME@::~@IMPL_NAME@()
+ {
+ }
+
void
@IMPL_NAME@::forecast(int noutput_items,
gr_vector_int &ninput_items_required)
@@ -87,6 +129,7 @@ namespace gr {
gr_vector_const_void_star &input_items,
gr_vector_void_star &output_items)
{
+ gr::thread::scoped_lock guard(d_setlock);
int nstreams = input_items.size();
int nblocks = noutput_items / d_K;
diff --git a/gr-trellis/lib/viterbi_combined_XX_impl.h.t b/gr-trellis/lib/viterbi_combined_XX_impl.h.t
index 199e8c8e88..788e609895 100644
--- a/gr-trellis/lib/viterbi_combined_XX_impl.h.t
+++ b/gr-trellis/lib/viterbi_combined_XX_impl.h.t
@@ -49,15 +49,22 @@ namespace gr {
digital::trellis_metric_type_t TYPE);
~@IMPL_NAME@();
- fsm FSM() const { return d_FSM; }
- int K() const { return d_K; }
- int S0() const { return d_S0; }
- int SK() const { return d_SK; }
- int D() const { return d_D; }
+ fsm FSM() const { return d_FSM; }
+ int K() const { return d_K; }
+ int S0() const { return d_S0; }
+ int SK() const { return d_SK; }
+ int D() const { return d_D; }
std::vector<@I_TYPE@> TABLE() const { return d_TABLE; }
digital::trellis_metric_type_t TYPE() const { return d_TYPE; }
//std::vector<int> trace() const { return d_trace; }
+
+ void set_FSM(const fsm &FSM);
+ void set_K(int K);
+ void set_S0(int S0);
+ void set_SK(int SK);
+ void set_D(int D);
void set_TABLE(const std::vector<@I_TYPE@> &table);
+ void set_TYPE(digital::trellis_metric_type_t type);
void forecast(int noutput_items,
gr_vector_int &ninput_items_required);
diff --git a/gr-trellis/python/trellis/CMakeLists.txt b/gr-trellis/python/trellis/CMakeLists.txt
index b4223af935..5cfe927412 100644
--- a/gr-trellis/python/trellis/CMakeLists.txt
+++ b/gr-trellis/python/trellis/CMakeLists.txt
@@ -25,6 +25,7 @@ include(GrPython)
GR_PYTHON_INSTALL(
FILES
__init__.py
+ fsm_utils.py
DESTINATION ${GR_PYTHON_DIR}/gnuradio/trellis
COMPONENT "trellis_python"
)
diff --git a/gr-trellis/python/trellis/__init__.py b/gr-trellis/python/trellis/__init__.py
index 6c6d80ecdf..662aa58197 100644
--- a/gr-trellis/python/trellis/__init__.py
+++ b/gr-trellis/python/trellis/__init__.py
@@ -31,3 +31,6 @@ except ImportError:
dirname, filename = os.path.split(os.path.abspath(__file__))
__path__.append(os.path.join(dirname, "..", "..", "swig"))
from trellis_swig import *
+
+# import any pure python here
+import fsm_utils
diff --git a/gr-trellis/examples/python/fsm_utils.py b/gr-trellis/python/trellis/fsm_utils.py
index 06855ea775..72aa1d3660 100755
--- a/gr-trellis/examples/python/fsm_utils.py
+++ b/gr-trellis/python/trellis/fsm_utils.py
@@ -27,7 +27,7 @@ import sys
import operator
import numpy
-from gnuradio import trellis
+#from gnuradio import trellis
try:
import scipy.linalg
@@ -182,6 +182,7 @@ psk4=(2,[1, 0, \
0, 1, \
0, -1,\
-1, 0]) # includes Gray mapping
+
psk8=(2,[math.cos(2*math.pi*0/8), math.sin(2*math.pi*0/8), \
math.cos(2*math.pi*1/8), math.sin(2*math.pi*1/8), \
math.cos(2*math.pi*2/8), math.sin(2*math.pi*2/8), \
@@ -191,6 +192,32 @@ psk8=(2,[math.cos(2*math.pi*0/8), math.sin(2*math.pi*0/8), \
math.cos(2*math.pi*6/8), math.sin(2*math.pi*6/8), \
math.cos(2*math.pi*7/8), math.sin(2*math.pi*7/8)])
+psk2x3 = (3,[-1,-1,-1, \
+ -1,-1,1, \
+ -1,1,-1, \
+ -1,1,1, \
+ 1,-1,-1, \
+ 1,-1,1, \
+ 1,1,-1, \
+ 1,1,1])
+
+psk2x4 = (4,[-1,-1,-1,-1, \
+ -1,-1,-1,1, \
+ -1,-1,1,-1, \
+ -1,-1,1,1, \
+ -1,1,-1,-1, \
+ -1,1,-1,1, \
+ -1,1,1,-1, \
+ -1,1,1,1, \
+ 1,-1,-1,-1, \
+ 1,-1,-1,1, \
+ 1,-1,1,-1, \
+ 1,-1,1,1, \
+ 1,1,-1,-1, \
+ 1,1,-1,1, \
+ 1,1,1,-1, \
+ 1,1,1,1])
+
orth2 = (2,[1, 0, \
0, 1])
orth4=(4,[1, 0, 0, 0, \
@@ -205,35 +232,3 @@ orth4=(4,[1, 0, 0, 0, \
# C test channel (J. Proakis, Digital Communications, McGraw-Hill Inc., 2001)
c_channel = [0.227, 0.460, 0.688, 0.460, 0.227]
-
-
-
-
-
-
-
-
-
-if __name__ == '__main__':
- f1=trellis.fsm('fsm_files/awgn1o2_4.fsm')
- #f2=trellis.fsm('fsm_files/awgn2o3_4.fsm')
- #print f1.I(), f1.S(), f1.O()
- #print f1.NS()
- #print f1.OS()
- #print f2.I(), f2.S(), f2.O()
- #print f2.NS()
- #print f2.OS()
- ##f1.write_trellis_svg('f1.svg',4)
- #f2.write_trellis_svg('f2.svg',4)
- #f=fsm_concatenate(f1,f2)
- #f=fsm_radix(f1,2)
-
- #print "----------\n"
- #print f.I(), f.S(), f.O()
- #print f.NS()
- #print f.OS()
- #f.write_trellis_svg('f.svg',4)
-
- q=numpy.arange(0,8)/(2.0*8)
- (f0,SS,S,F,Sf,Ff,N) = make_cpm_signals(1,2,2,1,q,0.99)
-
diff --git a/gr-uhd/lib/usrp_sink_impl.cc b/gr-uhd/lib/usrp_sink_impl.cc
index 1a17e87775..c184f0a406 100644
--- a/gr-uhd/lib/usrp_sink_impl.cc
+++ b/gr-uhd/lib/usrp_sink_impl.cc
@@ -88,7 +88,7 @@ namespace gr {
{
bool clocks_locked = true;
- // 1) Check ref lock for all mboards
+ // Check ref lock for all mboards
for (size_t mboard_index = 0; mboard_index < _dev->get_num_mboards(); mboard_index++) {
std::string sensor_name = "ref_locked";
if (_dev->get_clock_source(mboard_index) == "internal") {
@@ -107,19 +107,6 @@ namespace gr {
}
}
- // 2) Check LO for all channels
- for (size_t i = 0; i < _nchan; i++) {
- size_t chan_index = _stream_args.channels[i];
- if (not _wait_for_locked_sensor(
- get_sensor_names(chan_index),
- "lo_locked",
- boost::bind(&usrp_sink_impl::get_sensor, this, _1, chan_index)
- )) {
- GR_LOG_WARN(d_logger, boost::format("Sensor 'lo_locked' failed to lock within timeout on channel %d.") % chan_index);
- clocks_locked = false;
- }
- }
-
return clocks_locked;
}
diff --git a/gr-uhd/lib/usrp_source_impl.cc b/gr-uhd/lib/usrp_source_impl.cc
index 6be0bac9ca..3142627952 100644
--- a/gr-uhd/lib/usrp_source_impl.cc
+++ b/gr-uhd/lib/usrp_source_impl.cc
@@ -87,7 +87,7 @@ namespace gr {
{
bool clocks_locked = true;
- // 1) Check ref lock for all mboards
+ // Check ref lock for all mboards
for (size_t mboard_index = 0; mboard_index < _dev->get_num_mboards(); mboard_index++) {
std::string sensor_name = "ref_locked";
if (_dev->get_clock_source(mboard_index) == "internal") {
@@ -106,19 +106,6 @@ namespace gr {
}
}
- // 2) Check LO for all channels
- for (size_t i = 0; i < _nchan; i++) {
- size_t chan_index = _stream_args.channels[i];
- if (not _wait_for_locked_sensor(
- get_sensor_names(chan_index),
- "lo_locked",
- boost::bind(&usrp_source_impl::get_sensor, this, _1, chan_index)
- )) {
- GR_LOG_WARN(d_logger, boost::format("Sensor 'lo_locked' failed to lock within timeout on channel %d.") % chan_index);
- clocks_locked = false;
- }
- }
-
return clocks_locked;
}
diff --git a/gr-utils/python/modtool/gr-newmod/cmake/Modules/FindCppUnit.cmake b/gr-utils/python/modtool/gr-newmod/cmake/Modules/FindCppUnit.cmake
index 9af308f84b..f93ade3412 100644
--- a/gr-utils/python/modtool/gr-newmod/cmake/Modules/FindCppUnit.cmake
+++ b/gr-utils/python/modtool/gr-newmod/cmake/Modules/FindCppUnit.cmake
@@ -15,6 +15,7 @@ PKG_CHECK_MODULES(PC_CPPUNIT "cppunit")
FIND_PATH(CPPUNIT_INCLUDE_DIRS
NAMES cppunit/TestCase.h
HINTS ${PC_CPPUNIT_INCLUDE_DIR}
+ ${CMAKE_INSTALL_PREFIX}/include
PATHS
/usr/local/include
/usr/include
@@ -23,6 +24,8 @@ FIND_PATH(CPPUNIT_INCLUDE_DIRS
FIND_LIBRARY(CPPUNIT_LIBRARIES
NAMES cppunit
HINTS ${PC_CPPUNIT_LIBDIR}
+ ${CMAKE_INSTALL_PREFIX}/lib
+ ${CMAKE_INSTALL_PREFIX}/lib64
PATHS
${CPPUNIT_INCLUDE_DIRS}/../lib
/usr/local/lib
diff --git a/gr-utils/python/modtool/gr-newmod/cmake/Modules/GrMiscUtils.cmake b/gr-utils/python/modtool/gr-newmod/cmake/Modules/GrMiscUtils.cmake
index 9331d5debc..188c40480b 100644
--- a/gr-utils/python/modtool/gr-newmod/cmake/Modules/GrMiscUtils.cmake
+++ b/gr-utils/python/modtool/gr-newmod/cmake/Modules/GrMiscUtils.cmake
@@ -1,4 +1,4 @@
-# Copyright 2010-2011 Free Software Foundation, Inc.
+# Copyright 2010-2011,2014 Free Software Foundation, Inc.
#
# This file is part of GNU Radio
#
@@ -94,7 +94,13 @@ macro(GR_ADD_CXX_COMPILER_FLAG_IF_AVAILABLE flag have)
include(CheckCXXCompilerFlag)
CHECK_CXX_COMPILER_FLAG(${flag} ${have})
if(${have})
- add_definitions(${flag})
+ if(${CMAKE_VERSION} VERSION_GREATER "2.8.4")
+ STRING(FIND "${CMAKE_CXX_FLAGS}" "${flag}" flag_dup)
+ if(${flag_dup} EQUAL -1)
+ set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${flag}")
+ set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} ${flag}")
+ endif(${flag_dup} EQUAL -1)
+ endif(${CMAKE_VERSION} VERSION_GREATER "2.8.4")
endif(${have})
endmacro(GR_ADD_CXX_COMPILER_FLAG_IF_AVAILABLE)
@@ -155,7 +161,7 @@ function(GR_LIBRARY_FOO target)
GR_LIBTOOL(TARGET ${target} DESTINATION ${GR_LIBRARY_DIR})
#give the library a special name with ultra-zero soversion
- set_target_properties(${target} PROPERTIES LIBRARY_OUTPUT_NAME ${target}-${LIBVER} SOVERSION "0.0.0")
+ set_target_properties(${target} PROPERTIES OUTPUT_NAME ${target}-${LIBVER} SOVERSION "0.0.0")
set(target_name lib${target}-${LIBVER}.so.0.0.0)
#custom command to generate symlinks
@@ -208,3 +214,312 @@ function(GR_GEN_TARGET_DEPS name var)
set(${var} "DEPENDS;${name};COMMAND;${name}" PARENT_SCOPE)
endif()
endfunction(GR_GEN_TARGET_DEPS)
+
+########################################################################
+# Control use of gr_logger
+# Usage:
+# GR_LOGGING()
+#
+# Will set ENABLE_GR_LOG to 1 by default.
+# Can manually set with -DENABLE_GR_LOG=0|1
+########################################################################
+function(GR_LOGGING)
+ find_package(Log4cpp)
+
+ OPTION(ENABLE_GR_LOG "Use gr_logger" ON)
+ if(ENABLE_GR_LOG)
+ # If gr_logger is enabled, make it usable
+ add_definitions( -DENABLE_GR_LOG )
+
+ # also test LOG4CPP; if we have it, use this version of the logger
+ # otherwise, default to the stdout/stderr model.
+ if(LOG4CPP_FOUND)
+ SET(HAVE_LOG4CPP True CACHE INTERNAL "" FORCE)
+ add_definitions( -DHAVE_LOG4CPP )
+ else(not LOG4CPP_FOUND)
+ SET(HAVE_LOG4CPP False CACHE INTERNAL "" FORCE)
+ SET(LOG4CPP_INCLUDE_DIRS "" CACHE INTERNAL "" FORCE)
+ SET(LOG4CPP_LIBRARY_DIRS "" CACHE INTERNAL "" FORCE)
+ SET(LOG4CPP_LIBRARIES "" CACHE INTERNAL "" FORCE)
+ endif(LOG4CPP_FOUND)
+
+ SET(ENABLE_GR_LOG ${ENABLE_GR_LOG} CACHE INTERNAL "" FORCE)
+
+ else(ENABLE_GR_LOG)
+ SET(HAVE_LOG4CPP False CACHE INTERNAL "" FORCE)
+ SET(LOG4CPP_INCLUDE_DIRS "" CACHE INTERNAL "" FORCE)
+ SET(LOG4CPP_LIBRARY_DIRS "" CACHE INTERNAL "" FORCE)
+ SET(LOG4CPP_LIBRARIES "" CACHE INTERNAL "" FORCE)
+ endif(ENABLE_GR_LOG)
+
+ message(STATUS "ENABLE_GR_LOG set to ${ENABLE_GR_LOG}.")
+ message(STATUS "HAVE_LOG4CPP set to ${HAVE_LOG4CPP}.")
+ message(STATUS "LOG4CPP_LIBRARIES set to ${LOG4CPP_LIBRARIES}.")
+
+endfunction(GR_LOGGING)
+
+########################################################################
+# Run GRCC to compile .grc files into .py files.
+#
+# Usage: GRCC(filename, directory)
+# - filenames: List of file name of .grc file
+# - directory: directory of built .py file - usually in
+# ${CMAKE_CURRENT_BINARY_DIR}
+# - Sets PYFILES: output converted GRC file names to Python files.
+########################################################################
+function(GRCC)
+ # Extract directory from list of args, remove it for the list of filenames.
+ list(GET ARGV -1 directory)
+ list(REMOVE_AT ARGV -1)
+ set(filenames ${ARGV})
+ file(MAKE_DIRECTORY ${directory})
+
+ SET(GRCC_COMMAND ${CMAKE_SOURCE_DIR}/gr-utils/python/grcc)
+
+ # GRCC uses some stuff in grc and gnuradio-runtime, so we force
+ # the known paths here
+ list(APPEND PYTHONPATHS
+ ${CMAKE_SOURCE_DIR}
+ ${CMAKE_SOURCE_DIR}/gnuradio-runtime/python
+ ${CMAKE_SOURCE_DIR}/gnuradio-runtime/lib/swig
+ ${CMAKE_BINARY_DIR}/gnuradio-runtime/lib/swig
+ )
+
+ if(WIN32)
+ #SWIG generates the python library files into a subdirectory.
+ #Therefore, we must append this subdirectory into PYTHONPATH.
+ #Only do this for the python directories matching the following:
+ foreach(pydir ${PYTHONPATHS})
+ get_filename_component(name ${pydir} NAME)
+ if(name MATCHES "^(swig|lib|src)$")
+ list(APPEND PYTHONPATHS ${pydir}/${CMAKE_BUILD_TYPE})
+ endif()
+ endforeach(pydir)
+ endif(WIN32)
+
+ file(TO_NATIVE_PATH "${PYTHONPATHS}" pypath)
+
+ if(UNIX)
+ list(APPEND pypath "$PYTHONPATH")
+ string(REPLACE ";" ":" pypath "${pypath}")
+ set(ENV{PYTHONPATH} ${pypath})
+ endif(UNIX)
+
+ if(WIN32)
+ list(APPEND pypath "%PYTHONPATH%")
+ string(REPLACE ";" "\\;" pypath "${pypath}")
+ #list(APPEND environs "PYTHONPATH=${pypath}")
+ set(ENV{PYTHONPATH} ${pypath})
+ endif(WIN32)
+
+ foreach(f ${filenames})
+ execute_process(
+ COMMAND ${GRCC_COMMAND} -d ${directory} ${f}
+ )
+ string(REPLACE ".grc" ".py" pyfile "${f}")
+ string(REPLACE "${CMAKE_CURRENT_SOURCE_DIR}" "${CMAKE_CURRENT_BINARY_DIR}" pyfile "${pyfile}")
+ list(APPEND pyfiles ${pyfile})
+ endforeach(f)
+
+ set(PYFILES ${pyfiles} PARENT_SCOPE)
+endfunction(GRCC)
+
+########################################################################
+# Check if HAVE_PTHREAD_SETSCHEDPARAM and HAVE_SCHED_SETSCHEDULER
+# should be defined
+########################################################################
+macro(GR_CHECK_LINUX_SCHED_AVAIL)
+set(CMAKE_REQUIRED_LIBRARIES -lpthread)
+ CHECK_CXX_SOURCE_COMPILES("
+ #include <pthread.h>
+ int main(){
+ pthread_t pthread;
+ pthread_setschedparam(pthread, 0, 0);
+ return 0;
+ } " HAVE_PTHREAD_SETSCHEDPARAM
+ )
+ GR_ADD_COND_DEF(HAVE_PTHREAD_SETSCHEDPARAM)
+
+ CHECK_CXX_SOURCE_COMPILES("
+ #include <sched.h>
+ int main(){
+ pid_t pid;
+ sched_setscheduler(pid, 0, 0);
+ return 0;
+ } " HAVE_SCHED_SETSCHEDULER
+ )
+ GR_ADD_COND_DEF(HAVE_SCHED_SETSCHEDULER)
+endmacro(GR_CHECK_LINUX_SCHED_AVAIL)
+
+########################################################################
+# Macros to generate source and header files from template
+########################################################################
+macro(GR_EXPAND_X_H component root)
+
+ include(GrPython)
+
+ file(WRITE ${CMAKE_CURRENT_BINARY_DIR}/generate_helper.py
+"#!${PYTHON_EXECUTABLE}
+
+import sys, os, re
+sys.path.append('${GR_RUNTIME_PYTHONPATH}')
+os.environ['srcdir'] = '${CMAKE_CURRENT_SOURCE_DIR}'
+os.chdir('${CMAKE_CURRENT_BINARY_DIR}')
+
+if __name__ == '__main__':
+ import build_utils
+ root, inp = sys.argv[1:3]
+ for sig in sys.argv[3:]:
+ name = re.sub ('X+', sig, root)
+ d = build_utils.standard_dict2(name, sig, '${component}')
+ build_utils.expand_template(d, inp)
+")
+
+ #make a list of all the generated headers
+ unset(expanded_files_h)
+ foreach(sig ${ARGN})
+ string(REGEX REPLACE "X+" ${sig} name ${root})
+ list(APPEND expanded_files_h ${CMAKE_CURRENT_BINARY_DIR}/${name}.h)
+ endforeach(sig)
+ unset(name)
+
+ #create a command to generate the headers
+ add_custom_command(
+ OUTPUT ${expanded_files_h}
+ DEPENDS ${CMAKE_CURRENT_SOURCE_DIR}/${root}.h.t
+ COMMAND ${PYTHON_EXECUTABLE} ${PYTHON_DASH_B}
+ ${CMAKE_CURRENT_BINARY_DIR}/generate_helper.py
+ ${root} ${root}.h.t ${ARGN}
+ )
+
+ #install rules for the generated headers
+ list(APPEND generated_includes ${expanded_files_h})
+
+endmacro(GR_EXPAND_X_H)
+
+macro(GR_EXPAND_X_CC_H component root)
+
+ include(GrPython)
+
+ file(WRITE ${CMAKE_CURRENT_BINARY_DIR}/generate_helper.py
+"#!${PYTHON_EXECUTABLE}
+
+import sys, os, re
+sys.path.append('${GR_RUNTIME_PYTHONPATH}')
+os.environ['srcdir'] = '${CMAKE_CURRENT_SOURCE_DIR}'
+os.chdir('${CMAKE_CURRENT_BINARY_DIR}')
+
+if __name__ == '__main__':
+ import build_utils
+ root, inp = sys.argv[1:3]
+ for sig in sys.argv[3:]:
+ name = re.sub ('X+', sig, root)
+ d = build_utils.standard_impl_dict2(name, sig, '${component}')
+ build_utils.expand_template(d, inp)
+")
+
+ #make a list of all the generated files
+ unset(expanded_files_cc)
+ unset(expanded_files_h)
+ foreach(sig ${ARGN})
+ string(REGEX REPLACE "X+" ${sig} name ${root})
+ list(APPEND expanded_files_cc ${CMAKE_CURRENT_BINARY_DIR}/${name}.cc)
+ list(APPEND expanded_files_h ${CMAKE_CURRENT_BINARY_DIR}/${name}.h)
+ endforeach(sig)
+ unset(name)
+
+ #create a command to generate the source files
+ add_custom_command(
+ OUTPUT ${expanded_files_cc}
+ DEPENDS ${CMAKE_CURRENT_SOURCE_DIR}/${root}.cc.t
+ COMMAND ${PYTHON_EXECUTABLE} ${PYTHON_DASH_B}
+ ${CMAKE_CURRENT_BINARY_DIR}/generate_helper.py
+ ${root} ${root}.cc.t ${ARGN}
+ )
+
+ #create a command to generate the header files
+ add_custom_command(
+ OUTPUT ${expanded_files_h}
+ DEPENDS ${CMAKE_CURRENT_SOURCE_DIR}/${root}.h.t
+ COMMAND ${PYTHON_EXECUTABLE} ${PYTHON_DASH_B}
+ ${CMAKE_CURRENT_BINARY_DIR}/generate_helper.py
+ ${root} ${root}.h.t ${ARGN}
+ )
+
+ #make source files depends on headers to force generation
+ set_source_files_properties(${expanded_files_cc}
+ PROPERTIES OBJECT_DEPENDS "${expanded_files_h}"
+ )
+
+ #install rules for the generated files
+ list(APPEND generated_sources ${expanded_files_cc})
+ list(APPEND generated_headers ${expanded_files_h})
+
+endmacro(GR_EXPAND_X_CC_H)
+
+macro(GR_EXPAND_X_CC_H_IMPL component root)
+
+ include(GrPython)
+
+ file(WRITE ${CMAKE_CURRENT_BINARY_DIR}/generate_helper.py
+"#!${PYTHON_EXECUTABLE}
+
+import sys, os, re
+sys.path.append('${GR_RUNTIME_PYTHONPATH}')
+os.environ['srcdir'] = '${CMAKE_CURRENT_SOURCE_DIR}'
+os.chdir('${CMAKE_CURRENT_BINARY_DIR}')
+
+if __name__ == '__main__':
+ import build_utils
+ root, inp = sys.argv[1:3]
+ for sig in sys.argv[3:]:
+ name = re.sub ('X+', sig, root)
+ d = build_utils.standard_dict(name, sig, '${component}')
+ build_utils.expand_template(d, inp, '_impl')
+")
+
+ #make a list of all the generated files
+ unset(expanded_files_cc_impl)
+ unset(expanded_files_h_impl)
+ unset(expanded_files_h)
+ foreach(sig ${ARGN})
+ string(REGEX REPLACE "X+" ${sig} name ${root})
+ list(APPEND expanded_files_cc_impl ${CMAKE_CURRENT_BINARY_DIR}/${name}_impl.cc)
+ list(APPEND expanded_files_h_impl ${CMAKE_CURRENT_BINARY_DIR}/${name}_impl.h)
+ list(APPEND expanded_files_h ${CMAKE_CURRENT_BINARY_DIR}/../include/gnuradio/${component}/${name}.h)
+ endforeach(sig)
+ unset(name)
+
+ #create a command to generate the _impl.cc files
+ add_custom_command(
+ OUTPUT ${expanded_files_cc_impl}
+ DEPENDS ${CMAKE_CURRENT_SOURCE_DIR}/${root}_impl.cc.t
+ COMMAND ${PYTHON_EXECUTABLE} ${PYTHON_DASH_B}
+ ${CMAKE_CURRENT_BINARY_DIR}/generate_helper.py
+ ${root} ${root}_impl.cc.t ${ARGN}
+ )
+
+ #create a command to generate the _impl.h files
+ add_custom_command(
+ OUTPUT ${expanded_files_h_impl}
+ DEPENDS ${CMAKE_CURRENT_SOURCE_DIR}/${root}_impl.h.t
+ COMMAND ${PYTHON_EXECUTABLE} ${PYTHON_DASH_B}
+ ${CMAKE_CURRENT_BINARY_DIR}/generate_helper.py
+ ${root} ${root}_impl.h.t ${ARGN}
+ )
+
+ #make _impl.cc source files depend on _impl.h to force generation
+ set_source_files_properties(${expanded_files_cc_impl}
+ PROPERTIES OBJECT_DEPENDS "${expanded_files_h_impl}"
+ )
+
+ #make _impl.h source files depend on headers to force generation
+ set_source_files_properties(${expanded_files_h_impl}
+ PROPERTIES OBJECT_DEPENDS "${expanded_files_h}"
+ )
+
+ #install rules for the generated files
+ list(APPEND generated_sources ${expanded_files_cc_impl})
+ list(APPEND generated_headers ${expanded_files_h_impl})
+
+endmacro(GR_EXPAND_X_CC_H_IMPL)
diff --git a/gr-utils/python/modtool/gr-newmod/cmake/Modules/GrPlatform.cmake b/gr-utils/python/modtool/gr-newmod/cmake/Modules/GrPlatform.cmake
index a2e4f3b34e..5b7e886f85 100644
--- a/gr-utils/python/modtool/gr-newmod/cmake/Modules/GrPlatform.cmake
+++ b/gr-utils/python/modtool/gr-newmod/cmake/Modules/GrPlatform.cmake
@@ -37,10 +37,18 @@ if(LINUX AND EXISTS "/etc/redhat-release")
set(REDHAT TRUE)
endif()
+if(LINUX AND EXISTS "/etc/slackware-version")
+ set(SLACKWARE TRUE)
+endif()
+
########################################################################
# when the library suffix should be 64 (applies to redhat linux family)
########################################################################
-if(NOT DEFINED LIB_SUFFIX AND REDHAT AND CMAKE_SYSTEM_PROCESSOR MATCHES "64$")
+if (REDHAT OR SLACKWARE)
+ set(LIB64_CONVENTION TRUE)
+endif()
+
+if(NOT DEFINED LIB_SUFFIX AND LIB64_CONVENTION AND CMAKE_SYSTEM_PROCESSOR MATCHES "64$")
set(LIB_SUFFIX 64)
endif()
set(LIB_SUFFIX ${LIB_SUFFIX} CACHE STRING "lib directory suffix")
diff --git a/gr-utils/python/modtool/gr-newmod/cmake/Modules/GrPython.cmake b/gr-utils/python/modtool/gr-newmod/cmake/Modules/GrPython.cmake
index 68ca58e996..395faffa5a 100644
--- a/gr-utils/python/modtool/gr-newmod/cmake/Modules/GrPython.cmake
+++ b/gr-utils/python/modtool/gr-newmod/cmake/Modules/GrPython.cmake
@@ -48,8 +48,15 @@ else(PYTHON_EXECUTABLE)
endif(PYTHON_EXECUTABLE)
+if (CMAKE_CROSSCOMPILING)
+ set(QA_PYTHON_EXECUTABLE "/usr/bin/python")
+else (CMAKE_CROSSCOMPILING)
+ set(QA_PYTHON_EXECUTABLE ${PYTHON_EXECUTABLE})
+endif(CMAKE_CROSSCOMPILING)
+
#make the path to the executable appear in the cmake gui
set(PYTHON_EXECUTABLE ${PYTHON_EXECUTABLE} CACHE FILEPATH "python interpreter")
+set(QA_PYTHON_EXECUTABLE ${QA_PYTHON_EXECUTABLE} CACHE FILEPATH "python interpreter for QA tests")
#make sure we can use -B with python (introduced in 2.6)
if(PYTHON_EXECUTABLE)
@@ -76,10 +83,11 @@ macro(GR_PYTHON_CHECK_MODULE desc mod cmd have)
execute_process(
COMMAND ${PYTHON_EXECUTABLE} -c "
#########################################
-try: import ${mod}
-except: exit(-1)
-try: assert ${cmd}
-except: exit(-1)
+try:
+ import ${mod}
+ assert ${cmd}
+except ImportError, AssertionError: exit(-1)
+except: pass
#########################################"
RESULT_VARIABLE ${have}
)
@@ -95,11 +103,13 @@ endmacro(GR_PYTHON_CHECK_MODULE)
########################################################################
# Sets the python installation directory GR_PYTHON_DIR
########################################################################
+if(NOT DEFINED GR_PYTHON_DIR)
execute_process(COMMAND ${PYTHON_EXECUTABLE} -c "
from distutils import sysconfig
print sysconfig.get_python_lib(plat_specific=True, prefix='')
" OUTPUT_VARIABLE GR_PYTHON_DIR OUTPUT_STRIP_TRAILING_WHITESPACE
)
+endif()
file(TO_CMAKE_PATH ${GR_PYTHON_DIR} GR_PYTHON_DIR)
########################################################################
@@ -181,6 +191,10 @@ function(GR_PYTHON_INSTALL)
####################################################################
file(TO_NATIVE_PATH ${PYTHON_EXECUTABLE} pyexe_native)
+ if (CMAKE_CROSSCOMPILING)
+ set(pyexe_native "/usr/bin/env python")
+ endif()
+
foreach(pyfile ${GR_PYTHON_INSTALL_PROGRAMS})
get_filename_component(pyfile_name ${pyfile} NAME)
get_filename_component(pyfile ${pyfile} ABSOLUTE)
@@ -193,8 +207,9 @@ function(GR_PYTHON_INSTALL)
add_custom_command(
OUTPUT ${pyexefile} DEPENDS ${pyfile}
COMMAND ${PYTHON_EXECUTABLE} -c
- \"open('${pyexefile}', 'w').write('\#!${pyexe_native}\\n'+open('${pyfile}').read())\"
+ "open('${pyexefile}','w').write('\#!${pyexe_native}\\n'+open('${pyfile}').read())"
COMMENT "Shebangin ${pyfile_name}"
+ VERBATIM
)
#on windows, python files need an extension to execute
diff --git a/gr-utils/python/modtool/gr-newmod/cmake/Modules/GrSwig.cmake b/gr-utils/python/modtool/gr-newmod/cmake/Modules/GrSwig.cmake
index 569667b0e9..abf4dc4612 100644
--- a/gr-utils/python/modtool/gr-newmod/cmake/Modules/GrSwig.cmake
+++ b/gr-utils/python/modtool/gr-newmod/cmake/Modules/GrSwig.cmake
@@ -33,14 +33,13 @@ include(GrPython)
# - GR_SWIG_DOCS_TARGET_DEPS
########################################################################
function(GR_SWIG_MAKE_DOCS output_file)
- find_package(Doxygen)
- if(DOXYGEN_FOUND)
+ if(ENABLE_DOXYGEN)
#setup the input files variable list, quote formated
set(input_files)
unset(INPUT_PATHS)
foreach(input_path ${ARGN})
- if (IS_DIRECTORY ${input_path}) #when input path is a directory
+ if(IS_DIRECTORY ${input_path}) #when input path is a directory
file(GLOB input_path_h_files ${input_path}/*.h)
else() #otherwise its just a file, no glob
set(input_path_h_files ${input_path})
@@ -76,17 +75,18 @@ function(GR_SWIG_MAKE_DOCS output_file)
#call the swig_doc script on the xml files
add_custom_command(
OUTPUT ${output_file}
- DEPENDS ${input_files} ${OUTPUT_DIRECTORY}/xml/index.xml
+ DEPENDS ${input_files} ${stamp-file} ${OUTPUT_DIRECTORY}/xml/index.xml
COMMAND ${PYTHON_EXECUTABLE} ${PYTHON_DASH_B}
${CMAKE_SOURCE_DIR}/docs/doxygen/swig_doc.py
${OUTPUT_DIRECTORY}/xml
${output_file}
+ COMMENT "Generating python docstrings for ${name}"
WORKING_DIRECTORY ${CMAKE_SOURCE_DIR}/docs/doxygen
)
- else(DOXYGEN_FOUND)
+ else(ENABLE_DOXYGEN)
file(WRITE ${output_file} "\n") #no doxygen -> empty file
- endif(DOXYGEN_FOUND)
+ endif(ENABLE_DOXYGEN)
endfunction(GR_SWIG_MAKE_DOCS)
########################################################################
@@ -105,20 +105,35 @@ endfunction(GR_SWIG_MAKE_DOCS)
macro(GR_SWIG_MAKE name)
set(ifiles ${ARGN})
+ # Shimming this in here to take care of a SWIG bug with handling
+ # vector<size_t> and vector<unsigned int> (on 32-bit machines) and
+ # vector<long unsigned int> (on 64-bit machines). Use this to test
+ # the size of size_t, then set SIZE_T_32 if it's a 32-bit machine
+ # or not if it's 64-bit. The logic in gr_type.i handles the rest.
+ INCLUDE(CheckTypeSize)
+ CHECK_TYPE_SIZE("size_t" SIZEOF_SIZE_T)
+ CHECK_TYPE_SIZE("unsigned int" SIZEOF_UINT)
+ if(${SIZEOF_SIZE_T} EQUAL ${SIZEOF_UINT})
+ list(APPEND GR_SWIG_FLAGS -DSIZE_T_32)
+ endif(${SIZEOF_SIZE_T} EQUAL ${SIZEOF_UINT})
+
#do swig doc generation if specified
- if (GR_SWIG_DOC_FILE)
+ if(GR_SWIG_DOC_FILE)
set(GR_SWIG_DOCS_SOURCE_DEPS ${GR_SWIG_SOURCE_DEPS})
- set(GR_SWIG_DOCS_TAREGT_DEPS ${GR_SWIG_TARGET_DEPS})
+ list(APPEND GR_SWIG_DOCS_TARGET_DEPS ${GR_SWIG_TARGET_DEPS})
GR_SWIG_MAKE_DOCS(${GR_SWIG_DOC_FILE} ${GR_SWIG_DOC_DIRS})
- list(APPEND GR_SWIG_SOURCE_DEPS ${GR_SWIG_DOC_FILE})
+ add_custom_target(${name}_swig_doc DEPENDS ${GR_SWIG_DOC_FILE})
+ list(APPEND GR_SWIG_TARGET_DEPS ${name}_swig_doc ${GR_RUNTIME_SWIG_DOC_FILE})
endif()
#append additional include directories
find_package(PythonLibs 2)
list(APPEND GR_SWIG_INCLUDE_DIRS ${PYTHON_INCLUDE_PATH}) #deprecated name (now dirs)
list(APPEND GR_SWIG_INCLUDE_DIRS ${PYTHON_INCLUDE_DIRS})
- list(APPEND GR_SWIG_INCLUDE_DIRS ${CMAKE_CURRENT_SOURCE_DIR})
- list(APPEND GR_SWIG_INCLUDE_DIRS ${CMAKE_CURRENT_BINARY_DIR})
+
+ #prepend local swig directories
+ list(INSERT GR_SWIG_INCLUDE_DIRS 0 ${CMAKE_CURRENT_SOURCE_DIR})
+ list(INSERT GR_SWIG_INCLUDE_DIRS 0 ${CMAKE_CURRENT_BINARY_DIR})
#determine include dependencies for swig file
execute_process(
@@ -157,6 +172,9 @@ macro(GR_SWIG_MAKE name)
include(UseSWIG)
SWIG_ADD_MODULE(${name} python ${ifiles})
SWIG_LINK_LIBRARIES(${name} ${PYTHON_LIBRARIES} ${GR_SWIG_LIBRARIES})
+ if(${name} STREQUAL "runtime_swig")
+ SET_TARGET_PROPERTIES(${SWIG_MODULE_runtime_swig_REAL_NAME} PROPERTIES DEFINE_SYMBOL "gnuradio_runtime_EXPORTS")
+ endif(${name} STREQUAL "runtime_swig")
endmacro(GR_SWIG_MAKE)
@@ -204,21 +222,25 @@ file(WRITE ${CMAKE_BINARY_DIR}/get_swig_deps.py "
import os, sys, re
-include_matcher = re.compile('[#|%]include\\s*[<|\"](.*)[>|\"]')
+i_include_matcher = re.compile('%(include|import)\\s*[<|\"](.*)[>|\"]')
+h_include_matcher = re.compile('#(include)\\s*[<|\"](.*)[>|\"]')
include_dirs = sys.argv[2].split(';')
def get_swig_incs(file_path):
+ if file_path.endswith('.i'): matcher = i_include_matcher
+ else: matcher = h_include_matcher
file_contents = open(file_path, 'r').read()
- return include_matcher.findall(file_contents, re.MULTILINE)
+ return matcher.findall(file_contents, re.MULTILINE)
def get_swig_deps(file_path, level):
deps = [file_path]
if level == 0: return deps
- for inc_file in get_swig_incs(file_path):
+ for keyword, inc_file in get_swig_incs(file_path):
for inc_dir in include_dirs:
inc_path = os.path.join(inc_dir, inc_file)
if not os.path.exists(inc_path): continue
deps.extend(get_swig_deps(inc_path, level-1))
+ break #found, we dont search in lower prio inc dirs
return deps
if __name__ == '__main__':
diff --git a/gr-utils/python/modtool/gr-newmod/cmake/Modules/GrTest.cmake b/gr-utils/python/modtool/gr-newmod/cmake/Modules/GrTest.cmake
index 6174c034e9..62caab4b51 100644
--- a/gr-utils/python/modtool/gr-newmod/cmake/Modules/GrTest.cmake
+++ b/gr-utils/python/modtool/gr-newmod/cmake/Modules/GrTest.cmake
@@ -30,10 +30,10 @@ set(__INCLUDED_GR_TEST_CMAKE TRUE)
# GR_TEST_TARGET_DEPS - built targets for the library path
# GR_TEST_LIBRARY_DIRS - directories for the library path
# GR_TEST_PYTHON_DIRS - directories for the python path
+# GR_TEST_ENVIRONS - other environment key/value pairs
########################################################################
function(GR_ADD_TEST test_name)
- if(WIN32)
#Ensure that the build exe also appears in the PATH.
list(APPEND GR_TEST_TARGET_DEPS ${ARGN})
@@ -50,6 +50,7 @@ function(GR_ADD_TEST test_name)
endif(location)
endforeach(target)
+ if(WIN32)
#SWIG generates the python library files into a subdirectory.
#Therefore, we must append this subdirectory into PYTHONPATH.
#Only do this for the python directories matching the following:
@@ -65,7 +66,8 @@ function(GR_ADD_TEST test_name)
file(TO_NATIVE_PATH "${GR_TEST_LIBRARY_DIRS}" libpath) #ok to use on dir list?
file(TO_NATIVE_PATH "${GR_TEST_PYTHON_DIRS}" pypath) #ok to use on dir list?
- set(environs "GR_DONT_LOAD_PREFS=1" "srcdir=${srcdir}")
+ set(environs "VOLK_GENERIC=1" "GR_DONT_LOAD_PREFS=1" "srcdir=${srcdir}")
+ list(APPEND environs ${GR_TEST_ENVIRONS})
#http://www.cmake.org/pipermail/cmake/2009-May/029464.html
#Replaced this add test + set environs code with the shell script generation.
@@ -74,18 +76,26 @@ function(GR_ADD_TEST test_name)
#SET_TESTS_PROPERTIES(${test_name} PROPERTIES ENVIRONMENT "${environs}")
if(UNIX)
+ set(LD_PATH_VAR "LD_LIBRARY_PATH")
+ if(APPLE)
+ set(LD_PATH_VAR "DYLD_LIBRARY_PATH")
+ endif()
+
set(binpath "${CMAKE_CURRENT_BINARY_DIR}:$PATH")
- #set both LD and DYLD paths to cover multiple UNIX OS library paths
- list(APPEND libpath "$LD_LIBRARY_PATH" "$DYLD_LIBRARY_PATH")
+ list(APPEND libpath "$${LD_PATH_VAR}")
list(APPEND pypath "$PYTHONPATH")
#replace list separator with the path separator
string(REPLACE ";" ":" libpath "${libpath}")
string(REPLACE ";" ":" pypath "${pypath}")
- list(APPEND environs "PATH=${binpath}" "LD_LIBRARY_PATH=${libpath}" "DYLD_LIBRARY_PATH=${libpath}" "PYTHONPATH=${pypath}")
+ list(APPEND environs "PATH=${binpath}" "${LD_PATH_VAR}=${libpath}" "PYTHONPATH=${pypath}")
#generate a bat file that sets the environment and runs the test
- find_program(SHELL sh)
+ if (CMAKE_CROSSCOMPILING)
+ set(SHELL "/bin/sh")
+ else(CMAKE_CROSSCOMPILING)
+ find_program(SHELL sh)
+ endif(CMAKE_CROSSCOMPILING)
set(sh_file ${CMAKE_CURRENT_BINARY_DIR}/${test_name}_test.sh)
file(WRITE ${sh_file} "#!${SHELL}\n")
#each line sets an environment variable
diff --git a/gr-utils/python/utils/grcc b/gr-utils/python/utils/grcc
index 8fb44c2c79..82db5435db 100755
--- a/gr-utils/python/utils/grcc
+++ b/gr-utils/python/utils/grcc
@@ -20,6 +20,9 @@
# Boston, MA 02110-1301, USA.
#
+import os
+import sys
+from optparse import OptionParser
import warnings
warnings.simplefilter('ignore')
@@ -28,10 +31,8 @@ try:
except ImportError:
from gnuradio.grc.python.Platform import Platform
-from optparse import OptionParser
-import os, sys
-class grcc:
+class GRCC:
def __init__(self, grcfile, out_dir):
self.out_dir = out_dir
self.platform = Platform()
@@ -43,7 +44,9 @@ class grcc:
self.fg.validate()
if not self.fg.is_valid():
- raise StandardError("Compilation error")
+ raise StandardError("\n\n".join(
+ ["Validation failed:"] + self.fg.get_error_messages()
+ ))
self.gen = self.platform.get_generator()(self.fg, out_dir)
self.gen.write()
@@ -52,7 +55,8 @@ class grcc:
progname = self.fg.get_option('id')
os.system("{0}/{1}.py".format(self.out_dir, progname))
-if __name__ == "__main__":
+
+def main():
usage="%prog: [options] filename"
description = "Compiles a GRC file (.grc) into a GNU Radio Python program. The program is stored in ~/.grc_gnuradio by default, but this location can be changed with the -d option."
@@ -63,15 +67,20 @@ if __name__ == "__main__":
help="Run the program after compiling [default=%default]")
(options, args) = parser.parse_args ()
- if(len(args) != 1):
+ if len(args) != 1:
sys.stderr.write("Please specify a GRC file name to compile.\n")
sys.exit(1)
try:
- g = grcc(args[0], options.directory+"/")
- except:
- sys.stderr.write("Error during file compilation.\n");
+ g = GRCC(args[0], options.directory + "/")
+ except Exception as e:
+ sys.stderr.write(str(e) + "\n")
+ sys.stderr.write("Error during file compilation.\n")
sys.exit(1)
- if(options.execute):
+ if options.execute:
g.exec_program()
+
+
+if __name__ == "__main__":
+ main()
diff --git a/gr-wxgui/python/wxgui/fft_window.py b/gr-wxgui/python/wxgui/fft_window.py
index 86023e3f88..024200556e 100644
--- a/gr-wxgui/python/wxgui/fft_window.py
+++ b/gr-wxgui/python/wxgui/fft_window.py
@@ -336,8 +336,8 @@ class fft_window(wx.Panel, pubsub.pubsub):
samples = numpy.fromstring(msg, numpy.float32)[:self.fft_size] #only take first frame
num_samps = len(samples)
#reorder fft
- if self.real: samples = samples[:(num_samps+1)/2]
- else: samples = numpy.concatenate((samples[num_samps/2+1:], samples[:(num_samps+1)/2]))
+ if self.real: samples = samples[:(num_samps+2)/2]
+ else: samples = numpy.concatenate((samples[(num_samps+1)/2:], samples[:(num_samps+2)/2]))
self.samples = samples
#peak hold calculation
if self[PEAK_HOLD_KEY]:
@@ -407,6 +407,6 @@ class fft_window(wx.Panel, pubsub.pubsub):
#update y grid
self.plotter.set_y_grid(ref_level-y_per_div*y_divs, ref_level, y_per_div)
#update y units
- self.plotter.set_y_label('Amplitude', 'dB')
+ self.plotter.set_y_label('Power', 'dB')
#update plotter
self.plotter.update()
diff --git a/gr-wxgui/python/wxgui/fftsink_nongl.py b/gr-wxgui/python/wxgui/fftsink_nongl.py
index be69e41578..c63f0fb268 100644
--- a/gr-wxgui/python/wxgui/fftsink_nongl.py
+++ b/gr-wxgui/python/wxgui/fftsink_nongl.py
@@ -136,17 +136,17 @@ class fft_sink_f(gr.hier_block2, fft_sink_base):
for tap in mywindow:
power += tap*tap
- self.c2mag = blocks.complex_to_mag(self.fft_size)
+ self.c2magsq = blocks.complex_to_mag_squared(self.fft_size)
self.avg = grfilter.single_pole_iir_filter_ff(1.0, self.fft_size)
# FIXME We need to add 3dB to all bins but the DC bin
- self.log = blocks.nlog10_ff(20, self.fft_size,
+ self.log = blocks.nlog10_ff(10, self.fft_size,
-20*math.log10(self.fft_size) # Adjust for number of bins
-10*math.log10(power/self.fft_size) # Adjust for windowing loss
-20*math.log10(ref_scale/2)) # Adjust for reference scale
self.sink = blocks.message_sink(gr.sizeof_float * self.fft_size, self.msgq, True)
- self.connect(self, self.s2p, self.one_in_n, self.fft, self.c2mag, self.avg, self.log, self.sink)
+ self.connect(self, self.s2p, self.one_in_n, self.fft, self.c2magsq, self.avg, self.log, self.sink)
self.win = fft_window(self, parent, size=size)
self.set_average(self.average)
@@ -183,17 +183,17 @@ class fft_sink_c(gr.hier_block2, fft_sink_base):
for tap in mywindow:
power += tap*tap
- self.c2mag = blocks.complex_to_mag(self.fft_size)
+ self.c2magsq = blocks.complex_to_mag_squared(self.fft_size)
self.avg = grfilter.single_pole_iir_filter_ff(1.0, self.fft_size)
# FIXME We need to add 3dB to all bins but the DC bin
- self.log = blocks.nlog10_ff(20, self.fft_size,
+ self.log = blocks.nlog10_ff(10, self.fft_size,
-20*math.log10(self.fft_size) # Adjust for number of bins
-10*math.log10(power/self.fft_size) # Adjust for windowing loss
-20*math.log10(ref_scale/2)) # Adjust for reference scale
self.sink = blocks.message_sink(gr.sizeof_float * self.fft_size, self.msgq, True)
- self.connect(self, self.s2p, self.one_in_n, self.fft, self.c2mag, self.avg, self.log, self.sink)
+ self.connect(self, self.s2p, self.one_in_n, self.fft, self.c2magsq, self.avg, self.log, self.sink)
self.win = fft_window(self, parent, size=size)
self.set_average(self.average)
diff --git a/grc/CMakeLists.txt b/grc/CMakeLists.txt
index cbf4c9945d..3714401bbb 100644
--- a/grc/CMakeLists.txt
+++ b/grc/CMakeLists.txt
@@ -67,6 +67,10 @@ CPACK_COMPONENT("grc"
# Create and install the grc conf file
########################################################################
file(TO_NATIVE_PATH ${CMAKE_INSTALL_PREFIX}/${GRC_BLOCKS_DIR} blocksdir)
+if(CMAKE_INSTALL_PREFIX STREQUAL "/usr")
+ # linux binary installs: append blocks dir with prefix /usr/local
+ set(blocksdir ${blocksdir}:/usr/local/${GRC_BLOCKS_DIR})
+endif(CMAKE_INSTALL_PREFIX STREQUAL "/usr")
if (APPLE)
set(GRC_XTERM_EXE "xterm")
diff --git a/grc/base/CMakeLists.txt b/grc/base/CMakeLists.txt
index 1087e842a3..bdc8a5006f 100644
--- a/grc/base/CMakeLists.txt
+++ b/grc/base/CMakeLists.txt
@@ -36,6 +36,7 @@ GR_PYTHON_INSTALL(FILES
install(FILES
block_tree.dtd
+ domain.dtd
flow_graph.dtd
DESTINATION ${GR_PYTHON_DIR}/gnuradio/grc/base
COMPONENT "grc"
diff --git a/grc/base/Connection.py b/grc/base/Connection.py
index b35ca91050..3a2de5b9a5 100644
--- a/grc/base/Connection.py
+++ b/grc/base/Connection.py
@@ -81,10 +81,28 @@ class Connection(Element):
The ports must match in type.
"""
Element.validate(self)
- source_type = self.get_source().get_type()
- sink_type = self.get_sink().get_type()
- if source_type != sink_type:
- self.add_error_message('Source type "%s" does not match sink type "%s".'%(source_type, sink_type))
+ platform = self.get_parent().get_parent()
+ source_domain = self.get_source().get_domain()
+ sink_domain = self.get_sink().get_domain()
+ if (source_domain, sink_domain) not in platform.get_connection_templates():
+ self.add_error_message('No connection known for domains "%s", "%s"'
+ % (source_domain, sink_domain))
+ too_many_other_sinks = (
+ source_domain in platform.get_domains() and
+ not platform.get_domain(key=source_domain)['multiple_sinks'] and
+ len(self.get_source().get_enabled_connections()) > 1
+ )
+ too_many_other_sources = (
+ sink_domain in platform.get_domains() and
+ not platform.get_domain(key=sink_domain)['multiple_sources'] and
+ len(self.get_sink().get_enabled_connections()) > 1
+ )
+ if too_many_other_sinks:
+ self.add_error_message(
+ 'Domain "%s" can have only one downstream block' % source_domain)
+ if too_many_other_sources:
+ self.add_error_message(
+ 'Domain "%s" can have only one upstream block' % sink_domain)
def get_enabled(self):
"""
diff --git a/grc/base/Constants.py b/grc/base/Constants.py
index 75a6560b6d..efae0ecbb5 100644
--- a/grc/base/Constants.py
+++ b/grc/base/Constants.py
@@ -32,3 +32,9 @@ FLOW_GRAPH_FILE_FORMAT_VERSION = 1
# Param tabs
DEFAULT_PARAM_TAB = "General"
ADVANCED_PARAM_TAB = "Advanced"
+
+# Port domains
+DOMAIN_DTD = os.path.join(DATA_DIR, 'domain.dtd')
+GR_STREAM_DOMAIN = "gr_stream"
+GR_MESSAGE_DOMAIN = "gr_message"
+DEFAULT_DOMAIN = GR_STREAM_DOMAIN
diff --git a/grc/base/Element.py b/grc/base/Element.py
index 9c697b6393..04a3690282 100644
--- a/grc/base/Element.py
+++ b/grc/base/Element.py
@@ -21,6 +21,7 @@ class Element(object):
def __init__(self, parent=None):
self._parent = parent
+ self._error_messages = list()
##################################################
# Element Validation API
@@ -30,7 +31,7 @@ class Element(object):
Validate this element and call validate on all children.
Call this base method before adding error messages in the subclass.
"""
- self._error_messages = list()
+ del self._error_messages[:]
for child in self.get_children(): child.validate()
def is_valid(self):
diff --git a/grc/base/FlowGraph.py b/grc/base/FlowGraph.py
index 02d1b112c4..fb25b46821 100644
--- a/grc/base/FlowGraph.py
+++ b/grc/base/FlowGraph.py
@@ -17,11 +17,13 @@ along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
"""
+import time
from . import odict
from Element import Element
from .. gui import Messages
from . Constants import FLOW_GRAPH_FILE_FORMAT_VERSION
+
class FlowGraph(Element):
def __init__(self, platform):
@@ -36,6 +38,8 @@ class FlowGraph(Element):
"""
#initialize
Element.__init__(self, platform)
+ self._elements = []
+ self._timestamp = time.ctime()
#inital blank import
self.import_data()
@@ -51,12 +55,14 @@ class FlowGraph(Element):
"""
index = 0
while True:
- id = '%s_%d'%(base_id, index)
- index = index + 1
+ id = '%s_%d' % (base_id, index)
+ index += 1
#make sure that the id is not used by another block
if not filter(lambda b: b.get_id() == id, self.get_blocks()): return id
- def __str__(self): return 'FlowGraph - %s(%s)'%(self.get_option('title'), self.get_option('id'))
+ def __str__(self):
+ return 'FlowGraph - %s(%s)' % (self.get_option('title'), self.get_option('id'))
+
def rewrite(self):
def refactor_bus_structure():
@@ -242,9 +248,8 @@ class FlowGraph(Element):
Returns:
a nested data odict
"""
- import time
n = odict()
- n['timestamp'] = time.ctime()
+ n['timestamp'] = self._timestamp
n['block'] = [block.export_data() for block in self.get_blocks()]
n['connection'] = [connection.export_data() for connection in self.get_connections()]
instructions = odict({
@@ -273,6 +278,7 @@ class FlowGraph(Element):
file_format = 0
#use blank data if none provided
fg_n = n and n.find('flow_graph') or odict()
+ self._timestamp = fg_n.find('timestamp') or time.ctime()
blocks_n = fg_n.findall('block')
connections_n = fg_n.findall('connection')
#create option block
@@ -384,7 +390,7 @@ def _initialize_dummy_block(block, block_n):
"""
block._key = block_n.find('key')
block.is_dummy_block = lambda: True
- block.is_valid = lambda: False
+ block.is_valid = lambda: False
block.get_enabled = lambda: False
for param_n in block_n.findall('param'):
if param_n['key'] not in block.get_param_keys():
@@ -393,7 +399,7 @@ def _initialize_dummy_block(block, block_n):
def _dummy_block_add_port(block, key, dir):
- """This is so ugly... Add a port to a dummy-fied block"""
+ """This is so ugly... Add a port to a dummy-field block"""
port_n = odict({'name': '?', 'key': key, 'type': ''})
port = block.get_parent().get_parent().Port(block=block, n=port_n, dir=dir)
if port.is_source():
diff --git a/grc/base/Platform.py b/grc/base/Platform.py
index 095b70cc16..9fb67329d4 100644
--- a/grc/base/Platform.py
+++ b/grc/base/Platform.py
@@ -26,7 +26,7 @@ from Connection import Connection as _Connection
from Block import Block as _Block
from Port import Port as _Port
from Param import Param as _Param
-from Constants import BLOCK_TREE_DTD, FLOW_GRAPH_DTD
+from Constants import BLOCK_TREE_DTD, FLOW_GRAPH_DTD, DOMAIN_DTD
class Platform(_Element):
@@ -74,6 +74,8 @@ class Platform(_Element):
self._blocks = None
self._blocks_n = None
self._category_trees_n = None
+ self._domains = dict()
+ self._connection_templates = dict()
self.load_blocks()
def load_blocks(self):
@@ -82,19 +84,23 @@ class Platform(_Element):
self._blocks = odict()
self._blocks_n = odict()
self._category_trees_n = list()
+ self._domains.clear()
+ self._connection_templates.clear()
ParseXML.xml_failures.clear()
# try to parse and load blocks
for xml_file in self.iter_xml_files():
try:
if xml_file.endswith("block_tree.xml"):
self.load_category_tree_xml(xml_file)
+ elif xml_file.endswith('domain.xml'):
+ self.load_domain_xml(xml_file)
else:
self.load_block_xml(xml_file)
except ParseXML.XMLSyntaxError as e:
# print >> sys.stderr, 'Warning: Block validation failed:\n\t%s\n\tIgnoring: %s' % (e, xml_file)
pass
except Exception as e:
- print >> sys.stderr, 'Warning: Block loading failed:\n\t%s\n\tIgnoring: %s' % (e, xml_file)
+ print >> sys.stderr, 'Warning: XML parsing failed:\n\t%s\n\tIgnoring: %s' % (e, xml_file)
def iter_xml_files(self):
"""Iterator for block descriptions and category trees"""
@@ -128,6 +134,46 @@ class Platform(_Element):
n = ParseXML.from_file(xml_file).find('cat')
self._category_trees_n.append(n)
+ def load_domain_xml(self, xml_file):
+ """Load a domain properties and connection templates from XML"""
+ ParseXML.validate_dtd(xml_file, DOMAIN_DTD)
+ n = ParseXML.from_file(xml_file).find('domain')
+
+ key = n.find('key')
+ if not key:
+ print >> sys.stderr, 'Warning: Domain with emtpy key.\n\tIgnoring: %s' % xml_file
+ return
+ if key in self.get_domains(): # test against repeated keys
+ print >> sys.stderr, 'Warning: Domain with key "%s" already exists.\n\tIgnoring: %s' % (key, xml_file)
+ return
+
+ to_bool = lambda s, d: d if s is None else \
+ s.lower() not in ('false', 'off', '0', '')
+
+ color = n.find('color') or ''
+ try:
+ import gtk # ugly but handy
+ gtk.gdk.color_parse(color)
+ except (ValueError, ImportError):
+ if color: # no color is okay, default set in GUI
+ print >> sys.stderr, 'Warning: Can\'t parse color code "%s" for domain "%s" ' % (color, key)
+ color = None
+
+ self._domains[key] = dict(
+ name=n.find('name') or key,
+ multiple_sinks=to_bool(n.find('multiple_sinks'), True),
+ multiple_sources=to_bool(n.find('multiple_sources'), False),
+ color=color
+ )
+ for connection_n in n.findall('connection'):
+ key = (connection_n.find('source_domain'), connection_n.find('sink_domain'))
+ if not all(key):
+ print >> sys.stderr, 'Warning: Empty domain key(s) in connection template.\n\t%s' % xml_file
+ elif key in self._connection_templates:
+ print >> sys.stderr, 'Warning: Connection template "%s" already exists.\n\t%s' % (key, xml_file)
+ else:
+ self._connection_templates[key] = connection_n.find('make') or ''
+
def parse_flow_graph(self, flow_graph_file):
"""
Parse a saved flow graph file.
@@ -197,6 +243,10 @@ class Platform(_Element):
def get_blocks(self): return self._blocks.values()
def get_new_block(self, flow_graph, key): return self.Block(flow_graph, n=self._blocks_n[key])
+ def get_domains(self): return self._domains
+ def get_domain(self, key): return self._domains.get(key)
+ def get_connection_templates(self): return self._connection_templates
+
def get_name(self): return self._name
def get_version(self): return self._version
def get_version_major(self): return self._version_major
diff --git a/grc/base/Port.py b/grc/base/Port.py
index be32d15a91..b393ba9600 100644
--- a/grc/base/Port.py
+++ b/grc/base/Port.py
@@ -18,6 +18,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
"""
from Element import Element
+from . Constants import GR_STREAM_DOMAIN, GR_MESSAGE_DOMAIN
class Port(Element):
@@ -36,6 +37,7 @@ class Port(Element):
self._name = n['name']
self._key = n['key']
self._type = n['type']
+ self._domain = n['domain']
self._hide = n.find('hide') or ''
self._dir = dir
self._type_evaluated = None # updated on rewrite()
@@ -48,7 +50,10 @@ class Port(Element):
"""
Element.validate(self)
if self.get_type() not in self.get_types():
- self.add_error_message('Type "%s" is not a possible type.'%self.get_type())
+ self.add_error_message('Type "%s" is not a possible type.' % self.get_type())
+ platform = self.get_parent().get_parent().get_parent()
+ if self.get_domain() not in platform.get_domains():
+ self.add_error_message('Domain key "%s" is not registered.' % self.get_domain())
def rewrite(self):
"""resolve dependencies in for type and hide"""
@@ -56,6 +61,11 @@ class Port(Element):
self._type_evaluated = self.get_parent().resolve_dependencies(self._type)
hide = self.get_parent().resolve_dependencies(self._hide).strip().lower()
self._hide_evaluated = False if hide in ('false', 'off', '0') else bool(hide)
+ # update domain if was deduced from (dynamic) port type
+ if self._domain == GR_STREAM_DOMAIN and self._type_evaluated == "message":
+ self._domain = GR_MESSAGE_DOMAIN
+ if self._domain == GR_MESSAGE_DOMAIN and self._type_evaluated != "message":
+ self._domain = GR_STREAM_DOMAIN
def __str__(self):
if self.is_source():
@@ -85,6 +95,7 @@ class Port(Element):
def get_type(self):
return self.get_parent().resolve_dependencies(self._type) \
if self._type_evaluated is None else self._type_evaluated
+ def get_domain(self): return self._domain
def get_hide(self): return self._hide_evaluated
def get_connections(self):
diff --git a/grc/base/domain.dtd b/grc/base/domain.dtd
new file mode 100644
index 0000000000..b5b0b8bf39
--- /dev/null
+++ b/grc/base/domain.dtd
@@ -0,0 +1,35 @@
+<!--
+Copyright 2014 Free Software Foundation, Inc.
+This file is part of GNU Radio
+
+GNU Radio Companion is free software; you can redistribute it and/or
+modify it under the terms of the GNU General Public License
+as published by the Free Software Foundation; either version 2
+of the License, or (at your option) any later version.
+
+GNU Radio Companion is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program; if not, write to the Free Software
+Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
+-->
+<!ELEMENT domain (name, key, color?, multiple_sinks?, multiple_sources?, connection*)>
+<!--
+ Sub level elements.
+ -->
+<!ELEMENT connection (source_domain, sink_domain, make)>
+<!--
+ Bottom level elements.
+ Character data only.
+ -->
+<!ELEMENT name (#PCDATA)>
+<!ELEMENT key (#PCDATA)>
+<!ELEMENT multiple_sinks (#PCDATA)>
+<!ELEMENT multiple_sources (#PCDATA)>
+<!ELEMENT color (#PCDATA)>
+<!ELEMENT make (#PCDATA)>
+<!ELEMENT source_domain (#PCDATA)>
+<!ELEMENT sink_domain (#PCDATA)>
diff --git a/grc/blocks/gr_message_domain.xml b/grc/blocks/gr_message_domain.xml
new file mode 100644
index 0000000000..c1eedb7c88
--- /dev/null
+++ b/grc/blocks/gr_message_domain.xml
@@ -0,0 +1,18 @@
+<?xml version="1.0"?>
+<!--
+###################################################
+##GNU Radio default domain 'gr_message'
+###################################################
+ -->
+ <domain>
+ <name>GR Message</name>
+ <key>gr_message</key>
+ <multiple_sources>True</multiple_sources>
+ <connection>
+ <source_domain>gr_message</source_domain>
+ <sink_domain>gr_message</sink_domain>
+ <make>#slurp
+ self.msg_connect($make_port_sig($source), $make_port_sig($sink))#slurp
+ </make>
+ </connection>
+</domain>
diff --git a/grc/blocks/gr_stream_domain.xml b/grc/blocks/gr_stream_domain.xml
new file mode 100644
index 0000000000..66026448ca
--- /dev/null
+++ b/grc/blocks/gr_stream_domain.xml
@@ -0,0 +1,18 @@
+<?xml version="1.0"?>
+<!--
+###################################################
+##GNU Radio default domain 'gr_stream'
+###################################################
+ -->
+ <domain>
+ <name>GR Stream</name>
+ <key>gr_stream</key>
+ <color>#000</color>
+ <connection>
+ <source_domain>gr_stream</source_domain>
+ <sink_domain>gr_stream</sink_domain>
+ <make>#slurp
+ self.connect($make_port_sig($source), $make_port_sig($sink))#slurp
+ </make>
+ </connection>
+</domain>
diff --git a/grc/blocks/options.xml b/grc/blocks/options.xml
index 0c3a804fd7..c1c94e4e24 100644
--- a/grc/blocks/options.xml
+++ b/grc/blocks/options.xml
@@ -58,17 +58,17 @@ else: self.stop(); self.wait()</callback>
<param>
<name>Generate Options</name>
<key>generate_options</key>
- <value>wx_gui</value>
+ <value>qt_gui</value>
<type>enum</type>
<option>
- <name>WX GUI</name>
- <key>wx_gui</key>
- </option>
- <option>
<name>QT GUI</name>
<key>qt_gui</key>
</option>
<option>
+ <name>WX GUI</name>
+ <key>wx_gui</key>
+ </option>
+ <option>
<name>No GUI</name>
<key>no_gui</key>
</option>
diff --git a/grc/blocks/pad_sink.xml b/grc/blocks/pad_sink.xml
index 37e132c34c..b022fa3d0d 100644
--- a/grc/blocks/pad_sink.xml
+++ b/grc/blocks/pad_sink.xml
@@ -7,9 +7,7 @@
<block>
<name>Pad Sink</name>
<key>pad_sink</key>
- <make>#if str($type) == "message"
-None;self.message_port_register_hier_in($label)
-#end if</make>
+ <make></make>
<param>
<name>Label</name>
<key>label</key>
diff --git a/grc/blocks/pad_source.xml b/grc/blocks/pad_source.xml
index 745e48c080..c0fb19eee7 100644
--- a/grc/blocks/pad_source.xml
+++ b/grc/blocks/pad_source.xml
@@ -7,9 +7,7 @@
<block>
<name>Pad Source</name>
<key>pad_source</key>
- <make>#if str($type) == "message"
-None;self.message_port_register_hier_out($label)
-#end if</make>
+ <make></make>
<param>
<name>Label</name>
<key>label</key>
diff --git a/grc/gui/ActionHandler.py b/grc/gui/ActionHandler.py
index f8963fa472..6c56a94e9c 100644
--- a/grc/gui/ActionHandler.py
+++ b/grc/gui/ActionHandler.py
@@ -495,9 +495,11 @@ class ActionHandler:
ExecFlowGraphThread(self)
elif action == Actions.FLOW_GRAPH_KILL:
if self.get_page().get_proc():
- try: self.get_page().get_proc().kill()
- except: print "could not kill process: %d"%self.get_page().get_proc().pid
- elif action == Actions.PAGE_CHANGE: #pass and run the global actions
+ try:
+ self.get_page().get_proc().kill()
+ except:
+ print "could not kill process: %d" % self.get_page().get_proc().pid
+ elif action == Actions.PAGE_CHANGE: # pass and run the global actions
pass
elif action == Actions.RELOAD_BLOCKS:
self.platform.load_blocks()
@@ -583,7 +585,7 @@ class ActionHandler:
sensitive = self.get_flow_graph().is_valid() and not self.get_page().get_proc()
Actions.FLOW_GRAPH_GEN.set_sensitive(sensitive)
Actions.FLOW_GRAPH_EXEC.set_sensitive(sensitive)
- Actions.FLOW_GRAPH_KILL.set_sensitive(self.get_page().get_proc() != None)
+ Actions.FLOW_GRAPH_KILL.set_sensitive(self.get_page().get_proc() is not None)
class ExecFlowGraphThread(Thread):
"""Execute the flow graph as a new process and wait on it to finish."""
@@ -619,13 +621,14 @@ class ExecFlowGraphThread(Thread):
"""
#handle completion
r = "\n"
- while(r):
+ while r:
gobject.idle_add(Messages.send_verbose_exec, r)
r = os.read(self.p.stdout.fileno(), 1024)
+ self.p.poll()
gobject.idle_add(self.done)
def done(self):
"""Perform end of execution tasks."""
- Messages.send_end_exec()
+ Messages.send_end_exec(self.p.returncode)
self.page.set_proc(None)
self.update_exec_stop()
diff --git a/grc/gui/Block.py b/grc/gui/Block.py
index 1a32f6c2ba..11c1cafc97 100644
--- a/grc/gui/Block.py
+++ b/grc/gui/Block.py
@@ -25,7 +25,7 @@ from Constants import BORDER_PROXIMITY_SENSITIVITY
from Constants import \
BLOCK_LABEL_PADDING, \
PORT_SEPARATION, LABEL_SEPARATION, \
- PORT_BORDER_SEPARATION, POSSIBLE_ROTATIONS
+ PORT_BORDER_SEPARATION, POSSIBLE_ROTATIONS, BLOCK_FONT, PARAM_FONT
import Actions
import pygtk
pygtk.require('2.0')
@@ -34,7 +34,7 @@ import pango
BLOCK_MARKUP_TMPL="""\
#set $foreground = $block.is_valid() and 'black' or 'red'
-<span foreground="$foreground" font_desc="Sans 8"><b>$encode($block.get_name())</b></span>"""
+<span foreground="$foreground" font_desc="$font"><b>$encode($block.get_name())</b></span>"""
class Block(Element):
"""The graphical signal block."""
@@ -146,11 +146,13 @@ class Block(Element):
#create the main layout
layout = gtk.DrawingArea().create_pango_layout('')
layouts.append(layout)
- layout.set_markup(Utils.parse_template(BLOCK_MARKUP_TMPL, block=self))
+ layout.set_markup(Utils.parse_template(BLOCK_MARKUP_TMPL, block=self, font=BLOCK_FONT))
self.label_width, self.label_height = layout.get_pixel_size()
#display the params
if self.is_dummy_block():
- markups = ['<span foreground="black" font_desc="Sans 7.5"><b>key: </b>{}</span>'.format(self._key)]
+ markups = [
+ '<span foreground="black" font_desc="$font"><b>key: </b>{key}</span>'.format(font=PARAM_FONT, key=self._key)
+ ]
else:
markups = [param.get_markup() for param in self.get_params() if param.get_hide() not in ('all', 'part')]
if markups:
@@ -210,8 +212,11 @@ class Block(Element):
gc: the graphics context
window: the gtk window to draw on
"""
+ # draw ports
+ for port in self.get_ports_gui():
+ port.draw(gc, window)
+ # draw main block
x, y = self.get_coordinate()
- #draw main block
Element.draw(
self, gc, window, bg_color=self._bg_color,
border_color=self.is_highlighted() and Colors.HIGHLIGHT_COLOR or
@@ -222,9 +227,6 @@ class Block(Element):
window.draw_drawable(gc, self.horizontal_label, 0, 0, x+BLOCK_LABEL_PADDING, y+(self.H-self.label_height)/2, -1, -1)
elif self.is_vertical():
window.draw_drawable(gc, self.vertical_label, 0, 0, x+(self.H-self.label_height)/2, y+BLOCK_LABEL_PADDING, -1, -1)
- #draw ports
- for port in self.get_ports_gui():
- port.draw(gc, window)
def what_is_selected(self, coor, coor_m=None):
"""
diff --git a/grc/gui/Colors.py b/grc/gui/Colors.py
index 541d8db0b2..7430705cf8 100644
--- a/grc/gui/Colors.py
+++ b/grc/gui/Colors.py
@@ -25,7 +25,7 @@ try:
def get_color(color_code): return _COLORMAP.alloc_color(color_code, True, True)
HIGHLIGHT_COLOR = get_color('#00FFFF')
- BORDER_COLOR = get_color('black')
+ BORDER_COLOR = get_color('#444444')
# missing blocks stuff
MISSING_BLOCK_BACKGROUND_COLOR = get_color('#FFF2F2')
MISSING_BLOCK_BORDER_COLOR = get_color('red')
@@ -39,7 +39,9 @@ try:
BLOCK_DISABLED_COLOR = get_color('#CCCCCC')
#connection color constants
CONNECTION_ENABLED_COLOR = get_color('black')
- CONNECTION_DISABLED_COLOR = get_color('#999999')
+ CONNECTION_DISABLED_COLOR = get_color('#BBBBBB')
CONNECTION_ERROR_COLOR = get_color('red')
except:
print 'Unable to import Colors'
+
+DEFAULT_DOMAIN_COLOR_CODE = '#777777'
diff --git a/grc/gui/Connection.py b/grc/gui/Connection.py
index 5f95c99a0b..84004f5af6 100644
--- a/grc/gui/Connection.py
+++ b/grc/gui/Connection.py
@@ -23,6 +23,8 @@ import Colors
from Constants import CONNECTOR_ARROW_BASE, CONNECTOR_ARROW_HEIGHT
import gtk
+from .. base.Constants import GR_MESSAGE_DOMAIN
+
class Connection(Element):
"""
A graphical connection for ports.
@@ -33,7 +35,10 @@ class Connection(Element):
The arrow coloring exposes the enabled and valid states.
"""
- def __init__(self): Element.__init__(self)
+ def __init__(self):
+ Element.__init__(self)
+ self._color = Colors.CONNECTION_ENABLED_COLOR
+ self._bg_color = Colors.CONNECTION_ENABLED_COLOR
def get_coordinate(self):
"""
@@ -76,10 +81,21 @@ class Connection(Element):
Utils.get_rotated_coordinate((-CONNECTOR_ARROW_HEIGHT, -CONNECTOR_ARROW_BASE/2), self.get_sink().get_rotation()),
Utils.get_rotated_coordinate((-CONNECTOR_ARROW_HEIGHT, CONNECTOR_ARROW_BASE/2), self.get_sink().get_rotation()),
]
+ source_domain = self.get_source().get_domain()
+ sink_domain = self.get_sink().get_domain()
+ if source_domain == GR_MESSAGE_DOMAIN:
+ self.line_attributes[1] = gtk.gdk.LINE_ON_OFF_DASH
+ else:
+ self.line_attributes[1] = gtk.gdk.LINE_DOUBLE_DASH
+ if source_domain != sink_domain:
+ self.line_attributes[0] = 2
+ get_domain_color = lambda d: Colors.get_color((
+ self.get_parent().get_parent().get_domain(d) or {}
+ ).get('color') or Colors.DEFAULT_DOMAIN_COLOR_CODE)
+ self._color = get_domain_color(source_domain)
+ self._bg_color = get_domain_color(sink_domain)
+
self._update_after_move()
- if not self.get_enabled(): self._arrow_color = Colors.CONNECTION_DISABLED_COLOR
- elif not self.is_valid(): self._arrow_color = Colors.CONNECTION_ERROR_COLOR
- else: self._arrow_color = Colors.CONNECTION_ENABLED_COLOR
def _update_after_move(self):
"""Calculate coordinates."""
@@ -148,17 +164,21 @@ class Connection(Element):
self._sink_coor = sink.get_coordinate()
self._source_coor = source.get_coordinate()
#draw
- if self.is_highlighted(): border_color = Colors.HIGHLIGHT_COLOR
- elif self.get_enabled(): border_color = Colors.CONNECTION_ENABLED_COLOR
- else: border_color = Colors.CONNECTION_DISABLED_COLOR
- # make message connections dashed (no areas here)
- normal_line_style = gc.line_style
- if source.get_type() == "message": gc.line_style = gtk.gdk.LINE_ON_OFF_DASH
- Element.draw(self, gc, window, bg_color=None, border_color=border_color)
- gc.line_style = normal_line_style # restore line style
- #draw arrow on sink port
+ border_color = (
+ Colors.HIGHLIGHT_COLOR if self.is_highlighted() else
+ Colors.CONNECTION_DISABLED_COLOR if not self.get_enabled() else
+ self._color
+ )
+ bg_color = (
+ Colors.HIGHLIGHT_COLOR if self.is_highlighted() else
+ Colors.CONNECTION_DISABLED_COLOR if not self.get_enabled() else
+ self._bg_color
+ )
+ Element.draw(self, gc, window, border_color, bg_color)
+ # draw arrow on sink port
try:
- gc.set_foreground(self._arrow_color)
+ gc.set_foreground(bg_color)
+ gc.set_line_attributes(0, gtk.gdk.LINE_SOLID, gtk.gdk.CAP_BUTT, gtk.gdk.JOIN_MITER)
window.draw_polygon(gc, True, self._arrow)
except:
- return
+ pass
diff --git a/grc/gui/Constants.py b/grc/gui/Constants.py
index 7db291df99..0dc6279fd2 100644
--- a/grc/gui/Constants.py
+++ b/grc/gui/Constants.py
@@ -41,6 +41,13 @@ MIN_DIALOG_HEIGHT = 500
##default sizes
DEFAULT_BLOCKS_WINDOW_WIDTH = 100
DEFAULT_REPORTS_WINDOW_WIDTH = 100
+## flow-graph canvas fonts
+FONT_FAMILY = "Sans"
+FONT_SIZE = 8
+BLOCK_FONT = "%s %f" % (FONT_FAMILY, FONT_SIZE)
+PORT_FONT = BLOCK_FONT
+PARAM_FONT = "%s %f" % (FONT_FAMILY, FONT_SIZE - 0.5)
+
##The size of the state saving cache in the flow graph (for undo/redo functionality)
STATE_CACHE_SIZE = 42
diff --git a/grc/gui/Element.py b/grc/gui/Element.py
index 95a4e2edab..18fb321929 100644
--- a/grc/gui/Element.py
+++ b/grc/gui/Element.py
@@ -20,6 +20,9 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
from Constants import LINE_SELECT_SENSITIVITY
from Constants import POSSIBLE_ROTATIONS
+import gtk
+
+
class Element(object):
"""
GraphicalElement is the base class for all graphical elements.
@@ -35,6 +38,9 @@ class Element(object):
self.set_coordinate((0, 0))
self.clear()
self.set_highlighted(False)
+ self.line_attributes = [
+ 0, gtk.gdk.LINE_SOLID, gtk.gdk.CAP_BUTT, gtk.gdk.JOIN_MITER
+ ]
def is_horizontal(self, rotation=None):
"""
@@ -89,16 +95,18 @@ class Element(object):
border_color: the color for lines and rectangle borders
bg_color: the color for the inside of the rectangle
"""
- X,Y = self.get_coordinate()
- for (rX,rY),(W,H) in self._areas_list:
+ X, Y = self.get_coordinate()
+ gc.set_line_attributes(*self.line_attributes)
+ for (rX, rY), (W, H) in self._areas_list:
aX = X + rX
aY = Y + rY
gc.set_foreground(bg_color)
window.draw_rectangle(gc, True, aX, aY, W, H)
gc.set_foreground(border_color)
window.draw_rectangle(gc, False, aX, aY, W, H)
- for (x1, y1),(x2, y2) in self._lines_list:
+ for (x1, y1), (x2, y2) in self._lines_list:
gc.set_foreground(border_color)
+ gc.set_background(bg_color)
window.draw_line(gc, X+x1, Y+y1, X+x2, Y+y2)
def rotate(self, rotation):
diff --git a/grc/gui/Messages.py b/grc/gui/Messages.py
index f220b6dd06..90f508d770 100644
--- a/grc/gui/Messages.py
+++ b/grc/gui/Messages.py
@@ -24,15 +24,17 @@ import os
## A list of functions that can receive a message.
MESSENGERS_LIST = list()
+
def register_messenger(messenger):
"""
Append the given messenger to the list of messengers.
Args:
- messenger: a method thats takes a string
+ messenger: a method that takes a string
"""
MESSENGERS_LIST.append(messenger)
+
def send(message):
"""
Give the message to each of the messengers.
@@ -102,8 +104,8 @@ def send_start_exec(file_path):
def send_verbose_exec(verbose):
send(verbose)
-def send_end_exec():
- send('\n>>> Done\n')
+def send_end_exec(returncode=0):
+ send('\n>>> Done%s\n' % (" (return code %s)" % returncode if returncode else ""))
################# functions for saving flow graphs ########################################
def send_fail_save(file_path):
diff --git a/grc/gui/Param.py b/grc/gui/Param.py
index ef1c154933..2ef8603a83 100644
--- a/grc/gui/Param.py
+++ b/grc/gui/Param.py
@@ -19,6 +19,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
import Utils
from Element import Element
+from . Constants import PARAM_FONT
import pygtk
pygtk.require('2.0')
import gtk
@@ -196,7 +197,7 @@ class FileParam(EntryParam):
PARAM_MARKUP_TMPL="""\
#set $foreground = $param.is_valid() and 'black' or 'red'
-<span foreground="$foreground" font_desc="Sans 7.5"><b>$encode($param.get_name()): </b>$encode(repr($param))</span>"""
+<span foreground="$foreground" font_desc="$font"><b>$encode($param.get_name()): </b>$encode(repr($param))</span>"""
PARAM_LABEL_MARKUP_TMPL="""\
#set $foreground = $modified and 'blue' or $param.is_valid() and 'black' or 'red'
@@ -261,4 +262,4 @@ class Param(Element):
Returns:
a pango markup string
"""
- return Utils.parse_template(PARAM_MARKUP_TMPL, param=self)
+ return Utils.parse_template(PARAM_MARKUP_TMPL, param=self, font=PARAM_FONT)
diff --git a/grc/gui/Port.py b/grc/gui/Port.py
index 364ca6a5b9..9abda878bf 100644
--- a/grc/gui/Port.py
+++ b/grc/gui/Port.py
@@ -21,7 +21,8 @@ from Element import Element
from Constants import \
PORT_SEPARATION, CONNECTOR_EXTENSION_MINIMAL, \
CONNECTOR_EXTENSION_INCREMENT, \
- PORT_LABEL_PADDING, PORT_MIN_WIDTH, PORT_LABEL_HIDDEN_WIDTH
+ PORT_LABEL_PADDING, PORT_MIN_WIDTH, PORT_LABEL_HIDDEN_WIDTH, PORT_FONT
+from .. base.Constants import DEFAULT_DOMAIN, GR_MESSAGE_DOMAIN
import Utils
import Actions
import Colors
@@ -29,10 +30,8 @@ import pygtk
pygtk.require('2.0')
import gtk
-PORT_HIDDEN_MARKUP_TMPL="""\
-<span foreground="black" font_desc="Sans 7.5"> </span>"""
PORT_MARKUP_TMPL="""\
-<span foreground="black" font_desc="Sans 7.5">$encode($port.get_name())</span>"""
+<span foreground="black" font_desc="$font">$encode($port.get_name())</span>"""
class Port(Element):
@@ -55,6 +54,10 @@ class Port(Element):
Element.create_shapes(self)
if self.get_hide():
return # this port is hidden, no need to create shapes
+ if self.get_domain() == GR_MESSAGE_DOMAIN:
+ pass
+ elif self.get_domain() != DEFAULT_DOMAIN:
+ self.line_attributes[0] = 2
#get current rotation
rotation = self.get_rotation()
#get all sibling ports
@@ -115,7 +118,7 @@ class Port(Element):
self._bg_color = Colors.get_color(self.get_color())
#create the layout
layout = gtk.DrawingArea().create_pango_layout('')
- layout.set_markup(Utils.parse_template(PORT_MARKUP_TMPL, port=self))
+ layout.set_markup(Utils.parse_template(PORT_MARKUP_TMPL, port=self, font=PORT_FONT))
self.w, self.h = layout.get_pixel_size()
self.W, self.H = 2*PORT_LABEL_PADDING + self.w, 2*PORT_LABEL_PADDING+self.h
self.H = self.modify_height(self.H)
diff --git a/grc/python/Block.py b/grc/python/Block.py
index 9556e8f061..d0cbfbfa86 100644
--- a/grc/python/Block.py
+++ b/grc/python/Block.py
@@ -17,6 +17,8 @@ along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
"""
+from collections import defaultdict
+
from .. base.Block import Block as _Block
from .. gui.Block import Block as _GUIBlock
from . FlowGraph import _variable_matcher
@@ -127,8 +129,11 @@ class Block(_Block, _GUIBlock):
self.back_ofthe_bus(ports)
# renumber non-message/-msg ports
- for i, port in enumerate(filter(lambda p: p.get_key().isdigit(), ports)):
- port._key = str(i)
+ domain_specific_port_index = defaultdict(int)
+ for port in filter(lambda p: p.get_key().isdigit(), ports):
+ domain = port.get_domain()
+ port._key = str(domain_specific_port_index[domain])
+ domain_specific_port_index[domain] += 1
def port_controller_modify(self, direction):
"""
diff --git a/grc/python/CMakeLists.txt b/grc/python/CMakeLists.txt
index 4832dd897e..41d965e89c 100644
--- a/grc/python/CMakeLists.txt
+++ b/grc/python/CMakeLists.txt
@@ -19,7 +19,6 @@
########################################################################
GR_PYTHON_INSTALL(FILES
- convert_hier.py
expr_utils.py
extract_docs.py
Block.py
diff --git a/grc/python/Connection.py b/grc/python/Connection.py
index 7f235b190b..0a6cf5fa46 100644
--- a/grc/python/Connection.py
+++ b/grc/python/Connection.py
@@ -18,7 +18,6 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
"""
import Constants
-from .. base.Element import Element
from .. base.Connection import Connection as _Connection
from .. gui.Connection import Connection as _GUIConnection
@@ -31,9 +30,6 @@ class Connection(_Connection, _GUIConnection):
def is_msg(self):
return self.get_source().get_type() == self.get_sink().get_type() == 'msg'
- def is_message(self):
- return self.get_source().get_type() == self.get_sink().get_type() == 'message'
-
def is_bus(self):
return self.get_source().get_type() == self.get_sink().get_type() == 'bus'
@@ -42,8 +38,8 @@ class Connection(_Connection, _GUIConnection):
Validate the connections.
The ports must match in io size.
"""
- Element.validate(self)
source_size = Constants.TYPE_TO_SIZEOF[self.get_source().get_type()] * self.get_source().get_vlen()
sink_size = Constants.TYPE_TO_SIZEOF[self.get_sink().get_type()] * self.get_sink().get_vlen()
if source_size != sink_size:
self.add_error_message('Source IO size "%s" does not match sink IO size "%s".'%(source_size, sink_size))
+ _Connection.validate(self)
diff --git a/grc/python/FlowGraph.py b/grc/python/FlowGraph.py
index daec2d4310..d7337b8a96 100644
--- a/grc/python/FlowGraph.py
+++ b/grc/python/FlowGraph.py
@@ -58,34 +58,62 @@ class FlowGraph(_FlowGraph, _GUIFlowGraph):
#return from cache
return self._eval_cache[my_hash]
- def get_io_signaturev(self, direction):
+ def get_hier_block_stream_io(self, direction):
"""
- Get a list of io signatures for this flow graph.
+ Get a list of stream io signatures for this flow graph.
Args:
direction: a string of 'in' or 'out'
Returns:
- a list of dicts with: type, label, vlen, size
+ a list of dicts with: type, label, vlen, size, optional
"""
- sorted_pads = {
- 'in': self.get_pad_sources(),
- 'out': self.get_pad_sinks(),
- }[direction]
- # we only want stream ports
- sorted_pads = filter(lambda b: b.get_param('type').get_evaluated() != 'message', sorted_pads);
- expanded_pads = [];
- for i in sorted_pads:
- for j in range(i.get_param('num_streams').get_evaluated()):
- expanded_pads.append(i);
- #load io signature
- return [{
- 'label': str(pad.get_param('label').get_evaluated()),
- 'type': str(pad.get_param('type').get_evaluated()),
- 'vlen': str(pad.get_param('vlen').get_value()),
- 'size': pad.get_param('type').get_opt('size'),
- 'optional': bool(pad.get_param('optional').get_evaluated()),
- } for pad in expanded_pads]
+ return filter(lambda p: p['type'] != "message",
+ self.get_hier_block_io(direction))
+
+ def get_hier_block_message_io(self, direction):
+ """
+ Get a list of message io signatures for this flow graph.
+
+ Args:
+ direction: a string of 'in' or 'out'
+
+ Returns:
+ a list of dicts with: type, label, vlen, size, optional
+ """
+ return filter(lambda p: p['type'] == "message",
+ self.get_hier_block_io(direction))
+
+ def get_hier_block_io(self, direction):
+ """
+ Get a list of io ports for this flow graph.
+
+ Args:
+ direction: a string of 'in' or 'out'
+
+ Returns:
+ a list of dicts with: type, label, vlen, size, optional
+ """
+ pads = self.get_pad_sources() if direction in ('sink', 'in') else \
+ self.get_pad_sinks() if direction in ('source', 'out') else []
+ ports = []
+ for pad in pads:
+ master = {
+ 'label': str(pad.get_param('label').get_evaluated()),
+ 'type': str(pad.get_param('type').get_evaluated()),
+ 'vlen': str(pad.get_param('vlen').get_value()),
+ 'size': pad.get_param('type').get_opt('size'),
+ 'optional': bool(pad.get_param('optional').get_evaluated()),
+ }
+ num_ports = pad.get_param('num_streams').get_evaluated()
+ if num_ports > 1:
+ for i in xrange(num_ports):
+ clone = master.copy()
+ clone['label'] += str(i)
+ ports.append(clone)
+ else:
+ ports.append(master)
+ return ports
def get_pad_sources(self):
"""
@@ -118,20 +146,21 @@ class FlowGraph(_FlowGraph, _GUIFlowGraph):
key_offset = 0
pads = self.get_pad_sources() if port.is_source() else self.get_pad_sinks()
for pad in pads:
+ # using the block param 'type' instead of the port domain here
+ # to emphasize that hier block generation is domain agnostic
+ is_message_pad = pad.get_param('type').get_evaluated() == "message"
if port.get_parent() == pad:
- return str(key_offset + int(port.get_key()))
- # assuming we have either only sources or sinks
- key_offset += len(pad.get_ports())
+ if is_message_pad:
+ key = pad.get_param('label').get_value()
+ else:
+ key = str(key_offset + int(port.get_key()))
+ return key
+ else:
+ # assuming we have either only sources or sinks
+ if not is_message_pad:
+ key_offset += len(pad.get_ports())
return -1
- def get_msg_pad_sources(self):
- ps = self.get_pad_sources();
- return filter(lambda b: b.get_param('type').get_evaluated() == 'message', ps);
-
- def get_msg_pad_sinks(self):
- ps = self.get_pad_sinks();
- return filter(lambda b: b.get_param('type').get_evaluated() == 'message', ps);
-
def get_imports(self):
"""
Get a set of all import statments in this flow graph namespace.
diff --git a/grc/python/Generator.py b/grc/python/Generator.py
index 4a496b7c0f..7512cfb633 100644
--- a/grc/python/Generator.py
+++ b/grc/python/Generator.py
@@ -23,14 +23,18 @@ import subprocess
import tempfile
from distutils.spawn import find_executable
from Cheetah.Template import Template
-import expr_utils
-from Constants import \
- TOP_BLOCK_FILE_MODE, HIER_BLOCK_FILE_MODE, HIER_BLOCKS_LIB_DIR, FLOW_GRAPH_TEMPLATE, XTERM_EXECUTABLE
-import convert_hier
+
from .. gui import Messages
+from .. base import ParseXML
+from .. base import odict
+
+from . Constants import TOP_BLOCK_FILE_MODE, FLOW_GRAPH_TEMPLATE, \
+ XTERM_EXECUTABLE, HIER_BLOCK_FILE_MODE, HIER_BLOCKS_LIB_DIR, BLOCK_DTD
+from . import expr_utils
class Generator(object):
+ """Adaptor for various generators (uses generate_options)"""
def __init__(self, flow_graph, file_path):
"""
@@ -39,44 +43,67 @@ class Generator(object):
Args:
flow_graph: the flow graph object
+ file_path: the path to the grc file
+ """
+ self._generate_options = flow_graph.get_option('generate_options')
+ if self._generate_options == 'hb':
+ self._generator = HierBlockGenerator(flow_graph, file_path)
+ else:
+ self._generator = TopBlockGenerator(flow_graph, file_path)
+
+ def get_generate_options(self):
+ return self._generate_options
+
+ def __getattr__(self, item):
+ """get all other attrib from actual generator object"""
+ return getattr(self._generator, item)
+
+
+class TopBlockGenerator(object):
+
+ def __init__(self, flow_graph, file_path):
+ """
+ Initialize the top block generator object.
+
+ Args:
+ flow_graph: the flow graph object
file_path: the path to write the file to
"""
self._flow_graph = flow_graph
self._generate_options = self._flow_graph.get_option('generate_options')
- if self._generate_options == 'hb':
- self._mode = HIER_BLOCK_FILE_MODE
- dirname = HIER_BLOCKS_LIB_DIR
- else:
- self._mode = TOP_BLOCK_FILE_MODE
- dirname = os.path.dirname(file_path)
- #handle the case where the directory is read-only
- #in this case, use the system's temp directory
- if not os.access(dirname, os.W_OK):
- dirname = tempfile.gettempdir()
+ self._mode = TOP_BLOCK_FILE_MODE
+ dirname = os.path.dirname(file_path)
+ # handle the case where the directory is read-only
+ # in this case, use the system's temp directory
+ if not os.access(dirname, os.W_OK):
+ dirname = tempfile.gettempdir()
filename = self._flow_graph.get_option('id') + '.py'
self._file_path = os.path.join(dirname, filename)
- def get_file_path(self): return self._file_path
+ def get_file_path(self):
+ return self._file_path
def write(self):
- #do throttle warning
+ """generate output and write it to files"""
+ # do throttle warning
throttling_blocks = filter(lambda b: b.throttle(), self._flow_graph.get_enabled_blocks())
if not throttling_blocks and self._generate_options != 'hb':
- Messages.send_warning('''\
-This flow graph may not have flow control: no audio or RF hardware blocks found. \
-Add a Misc->Throttle block to your flow graph to avoid CPU congestion.''')
+ Messages.send_warning("This flow graph may not have flow control: "
+ "no audio or RF hardware blocks found. "
+ "Add a Misc->Throttle block to your flow "
+ "graph to avoid CPU congestion.")
if len(throttling_blocks) > 1:
keys = set(map(lambda b: b.get_key(), throttling_blocks))
if len(keys) > 1 and 'blocks_throttle' in keys:
- Messages.send_warning('''\
-This flow graph contains a throttle block and another rate limiting block, e.g. a hardware source or sink. \
-This is usually undesired. Consider removing the throttle block.''')
- #generate
- open(self.get_file_path(), 'w').write(str(self))
- if self._generate_options == 'hb':
- #convert hier block to xml wrapper
- convert_hier.convert_hier(self._flow_graph, self.get_file_path())
- os.chmod(self.get_file_path(), self._mode)
+ Messages.send_warning("This flow graph contains a throttle "
+ "block and another rate limiting block, "
+ "e.g. a hardware source or sink. "
+ "This is usually undesired. Consider "
+ "removing the throttle block.")
+ # generate
+ open(self.get_file_path(), 'w').write(
+ self._build_python_code_from_template()
+ )
def get_popen(self):
"""
@@ -85,15 +112,15 @@ This is usually undesired. Consider removing the throttle block.''')
Returns:
a popen object
"""
- #extract the path to the python executable
+ # extract the path to the python executable
python_exe = sys.executable
- #when using wx gui on mac os, execute with pythonw
- #using pythonw is not necessary anymore, disabled below
- #if self._generate_options == 'wx_gui' and 'darwin' in sys.platform.lower():
+ # when using wx gui on mac os, execute with pythonw
+ # using pythonw is not necessary anymore, disabled below
+ # if self._generate_options == 'wx_gui' and 'darwin' in sys.platform.lower():
# python_exe = 'pythonw'
- #setup the command args to run
+ # setup the command args to run
cmds = [python_exe, '-u', self.get_file_path()] # -u is unbuffered stdio
# when in no gui mode on linux, use a graphical terminal (looks nice)
@@ -101,10 +128,12 @@ This is usually undesired. Consider removing the throttle block.''')
if self._generate_options == 'no_gui' and xterm_executable:
cmds = [xterm_executable, '-e'] + cmds
- p = subprocess.Popen(args=cmds, stdout=subprocess.PIPE, stderr=subprocess.STDOUT, shell=False, universal_newlines=True)
+ p = subprocess.Popen(
+ args=cmds, stdout=subprocess.PIPE, stderr=subprocess.STDOUT,
+ shell=False, universal_newlines=True)
return p
- def __str__(self):
+ def _build_python_code_from_template(self):
"""
Convert the flow graph to python code.
@@ -116,53 +145,175 @@ This is usually undesired. Consider removing the throttle block.''')
variables = self._flow_graph.get_variables()
parameters = self._flow_graph.get_parameters()
monitors = self._flow_graph.get_monitors()
- #list of blocks not including variables and imports and parameters and disabled
+
+ # list of blocks not including variables and imports and parameters and disabled
def _get_block_sort_text(block):
code = block.get_make().replace(block.get_id(), ' ')
- try: code += block.get_param('notebook').get_value() #older gui markup w/ wxgui
- except: pass
- try: code += block.get_param('gui_hint').get_value() #newer gui markup w/ qtgui
- except: pass
+ try:
+ code += block.get_param('notebook').get_value() # older gui markup w/ wxgui
+ except:
+ pass
+ try:
+ code += block.get_param('gui_hint').get_value() # newer gui markup w/ qtgui
+ except:
+ pass
return code
blocks = expr_utils.sort_objects(
self._flow_graph.get_enabled_blocks(),
lambda b: b.get_id(), _get_block_sort_text
)
- #list of regular blocks (all blocks minus the special ones)
+ # list of regular blocks (all blocks minus the special ones)
blocks = filter(lambda b: b not in (imports + parameters), blocks)
- #list of connections where each endpoint is enabled
- connections = filter(lambda c: not (c.is_bus() or c.is_msg() or c.is_message()), self._flow_graph.get_enabled_connections())
- messages = filter(lambda c: c.is_msg(), self._flow_graph.get_enabled_connections())
- messages2 = filter(lambda c: c.is_message(), self._flow_graph.get_enabled_connections())
- #list of variable names
+ # list of connections where each endpoint is enabled (sorted by domains, block names)
+ connections = filter(lambda c: not (c.is_bus() or c.is_msg()), self._flow_graph.get_enabled_connections())
+ connections.sort(key=lambda c: (
+ c.get_source().get_domain(), c.get_sink().get_domain(),
+ c.get_source().get_parent().get_id(), c.get_sink().get_parent().get_id()
+ ))
+ connection_templates = self._flow_graph.get_parent().get_connection_templates()
+ msgs = filter(lambda c: c.is_msg(), self._flow_graph.get_enabled_connections())
+ # list of variable names
var_ids = [var.get_id() for var in parameters + variables]
- #prepend self.
- replace_dict = dict([(var_id, 'self.%s'%var_id) for var_id in var_ids])
- #list of callbacks
+ # prepend self.
+ replace_dict = dict([(var_id, 'self.%s' % var_id) for var_id in var_ids])
+ # list of callbacks
callbacks = [
expr_utils.expr_replace(cb, replace_dict)
for cb in sum([block.get_callbacks() for block in self._flow_graph.get_enabled_blocks()], [])
]
- #map var id to callbacks
- var_id2cbs = dict(
- [(var_id, filter(lambda c: expr_utils.get_variable_dependencies(c, [var_id]), callbacks))
- for var_id in var_ids]
- )
- #load the namespace
+ # map var id to callbacks
+ var_id2cbs = dict([
+ (var_id, filter(lambda c: expr_utils.get_variable_dependencies(c, [var_id]), callbacks))
+ for var_id in var_ids
+ ])
+ # load the namespace
namespace = {
'title': title,
'imports': imports,
'flow_graph': self._flow_graph,
'variables': variables,
'parameters': parameters,
- 'monitors': monitors,
+ 'monitors': monitors,
'blocks': blocks,
'connections': connections,
- 'messages': messages,
- 'messages2': messages2,
+ 'connection_templates': connection_templates,
+ 'msgs': msgs,
'generate_options': self._generate_options,
'var_id2cbs': var_id2cbs,
}
- #build the template
+ # build the template
t = Template(open(FLOW_GRAPH_TEMPLATE, 'r').read(), namespace)
return str(t)
+
+
+class HierBlockGenerator(TopBlockGenerator):
+ """Extends the top block generator to also generate a block XML file"""
+
+ def __init__(self, flow_graph, file_path):
+ """
+ Initialize the hier block generator object.
+
+ Args:
+ flow_graph: the flow graph object
+ file_path: where to write the py file (the xml goes into HIER_BLOCK_LIB_DIR)
+ """
+ TopBlockGenerator.__init__(self, flow_graph, file_path)
+ self._mode = HIER_BLOCK_FILE_MODE
+ self._file_path = os.path.join(HIER_BLOCKS_LIB_DIR,
+ self._flow_graph.get_option('id') + '.py')
+ self._file_path_xml = self._file_path + '.xml'
+
+ def get_file_path_xml(self):
+ return self._file_path_xml
+
+ def write(self):
+ """generate output and write it to files"""
+ TopBlockGenerator.write(self)
+ ParseXML.to_file(self._build_block_n_from_flow_graph_io(), self.get_file_path_xml())
+ ParseXML.validate_dtd(self.get_file_path_xml(), BLOCK_DTD)
+
+ def _build_block_n_from_flow_graph_io(self):
+ """
+ Generate a block XML nested data from the flow graph IO
+
+ Returns:
+ a xml node tree
+ """
+ # extract info from the flow graph
+ block_key = self._flow_graph.get_option('id')
+ parameters = self._flow_graph.get_parameters()
+
+ def var_or_value(name):
+ if name in map(lambda p: p.get_id(), parameters):
+ return "$"+name
+ return name
+
+ # build the nested data
+ block_n = odict()
+ block_n['name'] = self._flow_graph.get_option('title') or \
+ self._flow_graph.get_option('id').replace('_', ' ').title()
+ block_n['key'] = block_key
+ block_n['category'] = self._flow_graph.get_option('category')
+ block_n['import'] = 'execfile("{0}")'.format(self.get_file_path())
+ # make data
+ if parameters:
+ block_n['make'] = '{cls}(\n {kwargs},\n)'.format(
+ cls=block_key,
+ kwargs=',\n '.join(
+ '{key}=${key}'.format(key=param.get_id()) for param in parameters
+ ),
+ )
+ else:
+ block_n['make'] = '{cls}()'.format(cls=block_key)
+ # callback data
+ block_n['callback'] = [
+ 'set_{key}(${key})'.format(key=param.get_id()) for param in parameters
+ ]
+
+ # Parameters
+ block_n['param'] = list()
+ for param in parameters:
+ param_n = odict()
+ param_n['name'] = param.get_param('label').get_value() or param.get_id()
+ param_n['key'] = param.get_id()
+ param_n['value'] = param.get_param('value').get_value()
+ param_n['type'] = 'raw'
+ block_n['param'].append(param_n)
+
+ # bus stuff
+ if self._flow_graph.get_bussink():
+ block_n['bus_sink'] = '1'
+ if self._flow_graph.get_bussrc():
+ block_n['bus_source'] = '1'
+
+ # sink/source ports
+ for direction in ('sink', 'source'):
+ block_n[direction] = list()
+ for port in self._flow_graph.get_hier_block_io(direction):
+ port_n = odict()
+ port_n['name'] = port['label']
+ port_n['type'] = port['type']
+ if port['type'] != "message":
+ port_n['vlen'] = var_or_value(port['vlen'])
+ if port['optional']:
+ port_n['optional'] = '1'
+ block_n[direction].append(port_n)
+
+ # more bus stuff
+ bus_struct_sink = self._flow_graph.get_bus_structure_sink()
+ if bus_struct_sink:
+ block_n['bus_structure_sink'] = bus_struct_sink[0].get_param('struct').get_value()
+ bus_struct_src = self._flow_graph.get_bus_structure_src()
+ if bus_struct_src:
+ block_n['bus_structure_source'] = bus_struct_src[0].get_param('struct').get_value()
+
+ # documentation
+ block_n['doc'] = "\n".join(field for field in (
+ self._flow_graph.get_option('author'),
+ self._flow_graph.get_option('description'),
+ self.get_file_path()
+ ) if field)
+ block_n['grc_source'] = str(self._flow_graph.grc_file_path)
+
+ n = {'block': block_n}
+ return n
diff --git a/grc/python/Port.py b/grc/python/Port.py
index cfeabf8560..4cd07a9721 100644
--- a/grc/python/Port.py
+++ b/grc/python/Port.py
@@ -18,9 +18,11 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
"""
from .. base.Port import Port as _Port
+from .. base.Constants import DEFAULT_DOMAIN, GR_MESSAGE_DOMAIN
from .. gui.Port import Port as _GUIPort
import Constants
+
def _get_source_from_virtual_sink_port(vsp):
"""
Resolve the source port that is connected to the given virtual sink port.
@@ -91,8 +93,14 @@ class Port(_Port, _GUIPort):
dir: the direction
"""
self._n = n
+ if n['type'] == 'message':
+ n['domain'] = GR_MESSAGE_DOMAIN
+ if 'domain' not in n:
+ n['domain'] = DEFAULT_DOMAIN
+ elif n['domain'] == GR_MESSAGE_DOMAIN:
+ n['key'] = n['name']
+ n['type'] = 'message' # for port color
if n['type'] == 'msg': n['key'] = 'msg'
- if n['type'] == 'message': n['key'] = n['name']
if dir == 'source' and not n.find('key'):
n['key'] = str(block._source_count)
block._source_count += 1
@@ -120,8 +128,6 @@ class Port(_Port, _GUIPort):
_Port.validate(self)
if not self.get_enabled_connections() and not self.get_optional():
self.add_error_message('Port is not connected.')
- if not self.is_source() and (not self.get_type() == "message") and len(self.get_enabled_connections()) > 1:
- self.add_error_message('Port has too many connections.')
#message port logic
if self.get_type() == 'msg':
if self.get_nports():
diff --git a/grc/python/block.dtd b/grc/python/block.dtd
index 576b428111..8cfd3dd392 100644
--- a/grc/python/block.dtd
+++ b/grc/python/block.dtd
@@ -32,8 +32,8 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
<!ELEMENT param_tab_order (tab+)>
<!ELEMENT param (base_key?, name, key, value?, type?, hide?, option*, tab?)>
<!ELEMENT option (name, key, opt*)>
-<!ELEMENT sink (name, type, vlen?, nports?, optional?, hide?)>
-<!ELEMENT source (name, type, vlen?, nports?, optional?, hide?)>
+<!ELEMENT sink (name, type, vlen?, domain?, nports?, optional?, hide?)>
+<!ELEMENT source (name, type, vlen?, domain?, nports?, optional?, hide?)>
<!--
Bottom level elements.
Character data only.
@@ -53,6 +53,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
<!ELEMENT type (#PCDATA)>
<!ELEMENT hide (#PCDATA)>
<!ELEMENT vlen (#PCDATA)>
+<!ELEMENT domain (#PCDATA)>
<!ELEMENT nports (#PCDATA)>
<!ELEMENT bus_structure_sink (#PCDATA)>
<!ELEMENT bus_structure_source (#PCDATA)>
diff --git a/grc/python/convert_hier.py b/grc/python/convert_hier.py
deleted file mode 100644
index cf4c04a149..0000000000
--- a/grc/python/convert_hier.py
+++ /dev/null
@@ -1,116 +0,0 @@
-"""
-Copyright 2008-2011 Free Software Foundation, Inc.
-This file is part of GNU Radio
-
-GNU Radio Companion is free software; you can redistribute it and/or
-modify it under the terms of the GNU General Public License
-as published by the Free Software Foundation; either version 2
-of the License, or (at your option) any later version.
-
-GNU Radio Companion is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-GNU General Public License for more details.
-
-You should have received a copy of the GNU General Public License
-along with this program; if not, write to the Free Software
-Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
-"""
-
-from Constants import BLOCK_DTD
-from .. base import ParseXML
-from .. base import odict
-
-def convert_hier(flow_graph, python_file):
- #extract info from the flow graph
- input_sigs = flow_graph.get_io_signaturev('in')
- output_sigs = flow_graph.get_io_signaturev('out')
- input_msgp = flow_graph.get_msg_pad_sources();
- output_msgp = flow_graph.get_msg_pad_sinks();
- parameters = flow_graph.get_parameters()
- bussink = flow_graph.get_bussink()
- bussrc = flow_graph.get_bussrc()
- bus_struct_sink = flow_graph.get_bus_structure_sink()
- bus_struct_src = flow_graph.get_bus_structure_src()
- block_key = flow_graph.get_option('id')
- block_name = flow_graph.get_option('title') or flow_graph.get_option('id').replace('_', ' ').title()
- block_category = flow_graph.get_option('category')
- block_desc = flow_graph.get_option('description')
- block_author = flow_graph.get_option('author')
- #build the nested data
- block_n = odict()
- block_n['name'] = block_name
- block_n['key'] = block_key
- block_n['category'] = block_category
- block_n['import'] = 'execfile("%s")'%python_file
- #make data
- if parameters: block_n['make'] = '%s(\n %s,\n)'%(
- block_key,
- ',\n '.join(['%s=$%s'%(param.get_id(), param.get_id()) for param in parameters]),
- )
- else: block_n['make'] = '%s()'%block_key
- #callback data
- block_n['callback'] = ['set_%s($%s)'%(param.get_id(), param.get_id()) for param in parameters]
- #param data
- params_n = list()
- for param in parameters:
- param_n = odict()
- param_n['name'] = param.get_param('label').get_value() or param.get_id()
- param_n['key'] = param.get_id()
- param_n['value'] = param.get_param('value').get_value()
- param_n['type'] = 'raw'
- params_n.append(param_n)
- block_n['param'] = params_n
- #sink data stream ports
- if bussink:
- block_n['bus_sink'] = '1';
- if bussrc:
- block_n['bus_source'] = '1';
- block_n['sink'] = list()
- for input_sig in input_sigs:
- sink_n = odict()
- sink_n['name'] = input_sig['label']
- sink_n['type'] = input_sig['type']
- sink_n['vlen'] = var_or_value(input_sig['vlen'], parameters)
- if input_sig['optional']: sink_n['optional'] = '1'
- block_n['sink'].append(sink_n)
- #sink data msg ports
- for input_sig in input_msgp:
- sink_n = odict()
- sink_n['name'] = input_sig.get_param("label").get_value();
- sink_n['type'] = "message"
- sink_n['optional'] = input_sig.get_param("optional").get_value();
- block_n['sink'].append(sink_n)
- #source data stream ports
- block_n['source'] = list()
- if bus_struct_sink:
- block_n['bus_structure_sink'] = bus_struct_sink[0].get_param('struct').get_value();
- if bus_struct_src:
- block_n['bus_structure_source'] = bus_struct_src[0].get_param('struct').get_value();
- for output_sig in output_sigs:
- source_n = odict()
- source_n['name'] = output_sig['label']
- source_n['type'] = output_sig['type']
- source_n['vlen'] = var_or_value(output_sig['vlen'], parameters)
- if output_sig['optional']: source_n['optional'] = '1'
- block_n['source'].append(source_n)
- #source data msg ports
- for output_sig in output_msgp:
- source_n = odict()
- source_n['name'] = output_sig.get_param("label").get_value();
- source_n['type'] = "message"
- source_n['optional'] = output_sig.get_param("optional").get_value();
- block_n['source'].append(source_n)
- #doc data
- block_n['doc'] = "%s\n%s\n%s"%(block_author, block_desc, python_file)
- block_n['grc_source'] = "%s"%(flow_graph.grc_file_path)
- #write the block_n to file
- xml_file = python_file + '.xml'
- ParseXML.to_file({'block': block_n}, xml_file)
- ParseXML.validate_dtd(xml_file, BLOCK_DTD)
-
-
-def var_or_value(name, parameters):
- if name in map(lambda p: p.get_id(), parameters):
- return "$"+name
- return name \ No newline at end of file
diff --git a/grc/python/flow_graph.tmpl b/grc/python/flow_graph.tmpl
index bee9c68af5..d66c2581de 100644
--- a/grc/python/flow_graph.tmpl
+++ b/grc/python/flow_graph.tmpl
@@ -8,7 +8,7 @@
##@param parameters the paramater blocks
##@param blocks the signal blocks
##@param connections the connections
-##@param messages the msg type connections
+##@param msgs the msg type connections
##@param generate_options the type of flow graph
##@param var_id2cbs variable id map to callback strings
########################################################
@@ -90,8 +90,8 @@ class $(class_name)(gr.top_block):
def __init__($param_str):
gr.top_block.__init__(self, "$title")
#elif $generate_options == 'hb'
- #set $in_sigs = $flow_graph.get_io_signaturev('in')
- #set $out_sigs = $flow_graph.get_io_signaturev('out')
+ #set $in_sigs = $flow_graph.get_hier_block_stream_io('in')
+ #set $out_sigs = $flow_graph.get_hier_block_stream_io('out')
class $(class_name)(gr.hier_block2):
#def make_io_sig($io_sigs)
#set $size_strs = ['%s*%s'%(io_sig['size'], io_sig['vlen']) for io_sig in $io_sigs]
@@ -110,6 +110,12 @@ gr.io_signaturev($(len($io_sigs)), $(len($io_sigs)), [$(', '.join($size_strs))])
$make_io_sig($in_sigs),
$make_io_sig($out_sigs),
)
+ #for $pad in $flow_graph.get_hier_block_message_io('in')
+ self.message_port_register_hier_out("$pad['label']")
+ #end for
+ #for $pad in $flow_graph.get_hier_block_message_io('out')
+ self.message_port_register_hier_in("$pad['label']")
+ #end for
#end if
########################################################
##Create Parameters
@@ -139,13 +145,13 @@ gr.io_signaturev($(len($io_sigs)), $(len($io_sigs)), [$(', '.join($size_strs))])
########################################################
##Create Message Queues
########################################################
-#if $messages
+#if $msgs
$DIVIDER
# Message Queues
$DIVIDER
#end if
-#for $msg in $messages
+#for $msg in $msgs
$(msg.get_source().get_parent().get_id())_msgq_out = $(msg.get_sink().get_parent().get_id())_msgq_in = gr.msg_queue(2)
#end for
########################################################
@@ -183,10 +189,16 @@ gr.io_signaturev($(len($io_sigs)), $(len($io_sigs)), [$(', '.join($size_strs))])
########################################################
#def make_port_sig($port)
#if $port.get_parent().get_key() in ('pad_source', 'pad_sink')
-(self, $flow_graph.get_pad_port_global_key($port))#slurp
+ #set block = 'self'
+ #set key = $flow_graph.get_pad_port_global_key($port)
#else
-(self.$port.get_parent().get_id(), $port.get_key())#slurp
+ #set block = 'self.' + $port.get_parent().get_id()
+ #set key = $port.get_key()
#end if
+ #if not $key.isdigit()
+ #set key = repr($key)
+ #end if
+($block, $key)#slurp
#end def
#if $connections
@@ -195,42 +207,17 @@ gr.io_signaturev($(len($io_sigs)), $(len($io_sigs)), [$(', '.join($size_strs))])
$DIVIDER
#end if
#for $con in $connections
- #set $source = $con.get_source()
- #set $sink = $con.get_sink()
+ #set global $source = $con.get_source()
+ #set global $sink = $con.get_sink()
##resolve virtual sources to the actual sources
#if $source.get_parent().is_virtual_source()
#set $source = $source.resolve_virtual_source()
#end if
##do not generate connections with virtual sinks
#if not $sink.get_parent().is_virtual_sink()
- self.connect($make_port_sig($source), $make_port_sig($sink))
- #end if
-#end for
+ #include source=$connection_templates[($source.get_domain(), $sink.get_domain())]
-########################################################
-##Create Asynch Message Connections
-########################################################
-#if $messages2
- $DIVIDER
- # Asynch Message Connections
- $DIVIDER
-#end if
-#for $msg in $messages2
- #set $sr = $msg.get_source()
- #set $source = "self.%s"%($sr.get_parent().get_id())
- #set $source_port = $sr.get_key();
- #if $sr.get_parent().get_key() == "pad_source"
- #set $source = "self"
- #set $source_port = $sr.get_parent().get_param("label").get_value();
- #end if
- #set $sk = $msg.get_sink()
- #set $sink = "self.%s"%($sk.get_parent().get_id())
- #set $sink_port = $sk.get_name();
- #if $sk.get_parent().get_key() == "pad_sink"
- #set $sink = "self"
- #set $sink_port = $sk.get_parent().get_param("label").get_value();
- #end if
- self.msg_connect($source, "$source_port", $sink, "$sink_port")
+ #end if
#end for
########################################################
diff --git a/volk/apps/volk_profile.cc b/volk/apps/volk_profile.cc
index 074d1e7be4..9bc1842c63 100644
--- a/volk/apps/volk_profile.cc
+++ b/volk/apps/volk_profile.cc
@@ -37,6 +37,49 @@
namespace fs = boost::filesystem;
+void write_json(std::ofstream &json_file, std::vector<volk_test_results_t> results) {
+ json_file << "{" << std::endl;
+ json_file << " \"volk_tests\": [" << std::endl;
+ size_t len = results.size();
+ size_t i = 0;
+ BOOST_FOREACH(volk_test_results_t &result, results) {
+ json_file << " {" << std::endl;
+ json_file << " \"name\": \"" << result.name << "\"," << std::endl;
+ json_file << " \"vlen\": " << result.vlen << "," << std::endl;
+ json_file << " \"iter\": " << result.iter << "," << std::endl;
+ json_file << " \"best_arch_a\": \"" << result.best_arch_a
+ << "\"," << std::endl;
+ json_file << " \"best_arch_u\": \"" << result.best_arch_u
+ << "\"," << std::endl;
+ json_file << " \"results\": {" << std::endl;
+ size_t results_len = result.results.size();
+ size_t ri = 0;
+ typedef std::pair<std::string, volk_test_time_t> tpair;
+ BOOST_FOREACH(tpair pair, result.results) {
+ volk_test_time_t time = pair.second;
+ json_file << " \"" << time.name << "\": {" << std::endl;
+ json_file << " \"name\": \"" << time.name << "\"," << std::endl;
+ json_file << " \"time\": " << time.time << "," << std::endl;
+ json_file << " \"units\": \"" << time.units << "\"" << std::endl;
+ json_file << " }" ;
+ if(ri+1 != results_len) {
+ json_file << ",";
+ }
+ json_file << std::endl;
+ ri++;
+ }
+ json_file << " }" << std::endl;
+ json_file << " }";
+ if(i+1 != len) {
+ json_file << ",";
+ }
+ json_file << std::endl;
+ i++;
+ }
+ json_file << " ]" << std::endl;
+ json_file << "}" << std::endl;
+}
+
int main(int argc, char *argv[]) {
// Adding program options
boost::program_options::options_description desc("Options");
@@ -49,6 +92,9 @@ int main(int argc, char *argv[]) {
("tests-regex,R",
boost::program_options::value<std::string>(),
"Run tests matching regular expression.")
+ ("json,j",
+ boost::program_options::value<std::string>(),
+ "JSON output file")
;
// Handle the options that were given
@@ -56,6 +102,8 @@ int main(int argc, char *argv[]) {
bool benchmark_mode;
std::string kernel_regex;
bool store_results = true;
+ std::ofstream json_file;
+
try {
boost::program_options::store(boost::program_options::parse_command_line(argc, argv, desc), vm);
boost::program_options::notify(vm);
@@ -83,9 +131,14 @@ int main(int argc, char *argv[]) {
return 0;
}
+ if ( vm.count("json") )
+ {
+ json_file.open( vm["json"].as<std::string>().c_str() );
+ }
+
// Run tests
- std::vector<std::string> results;
+ std::vector<volk_test_results_t> results;
//VOLK_PROFILE(volk_16i_x5_add_quad_16i_x4, 1e-4, 2046, 10000, &results, benchmark_mode, kernel_regex);
//VOLK_PROFILE(volk_16i_branch_4_state_8, 1e-4, 2046, 10000, &results, benchmark_mode, kernel_regex);
@@ -104,16 +157,25 @@ int main(int argc, char *argv[]) {
//VOLK_PROFILE(volk_16i_max_star_horizontal_16i, 0, 0, 204602, 10000, &results, benchmark_mode, kernel_regex);
//VOLK_PROFILE(volk_16i_permute_and_scalar_add, 1e-4, 0, 2046, 10000, &results, benchmark_mode, kernel_regex);
//VOLK_PROFILE(volk_16i_x4_quad_max_star_16i, 1e-4, 0, 2046, 10000, &results, benchmark_mode, kernel_regex);
- VOLK_PROFILE(volk_16u_byteswap, 0, 0, 204602, 10000, &results, benchmark_mode, kernel_regex);
+ VOLK_PUPPET_PROFILE(volk_16u_byteswappuppet_16u, volk_16u_byteswap, 0, 0, 204602, 10000, &results, benchmark_mode, kernel_regex);
VOLK_PROFILE(volk_16i_32fc_dot_prod_32fc, 1e-4, 0, 204602, 10000, &results, benchmark_mode, kernel_regex);
VOLK_PROFILE(volk_32f_accumulator_s32f, 1e-4, 0, 204602, 10000, &results, benchmark_mode, kernel_regex);
VOLK_PROFILE(volk_32f_x2_add_32f, 1e-4, 0, 204602, 10000, &results, benchmark_mode, kernel_regex);
VOLK_PROFILE(volk_32fc_32f_multiply_32fc, 1e-4, 0, 204602, 1000, &results, benchmark_mode, kernel_regex);
+ VOLK_PROFILE(volk_32f_log2_32f, 1.5e-1, 0, 204602, 1000, &results, benchmark_mode, kernel_regex);
+ VOLK_PROFILE(volk_32f_expfast_32f, 1e-1, 0, 204602, 1000, &results, benchmark_mode, kernel_regex);
+ VOLK_PROFILE(volk_32f_x2_pow_32f, 1e-2, 0, 204602, 1000, &results, benchmark_mode, kernel_regex);
+ VOLK_PROFILE(volk_32f_sin_32f, 1e-6, 0, 204602, 1000, &results, benchmark_mode, kernel_regex);
+ VOLK_PROFILE(volk_32f_cos_32f, 1e-6, 0, 204602, 1000, &results, benchmark_mode, kernel_regex);
+ VOLK_PROFILE(volk_32f_tan_32f, 1e-6, 0, 204602, 1000, &results, benchmark_mode, kernel_regex);
+ VOLK_PROFILE(volk_32f_atan_32f, 1e-3, 0, 204602, 1000, &results, benchmark_mode, kernel_regex);
+ VOLK_PROFILE(volk_32f_asin_32f, 1e-3, 0, 204602, 1000, &results, benchmark_mode, kernel_regex);
+ VOLK_PROFILE(volk_32f_acos_32f, 1e-3, 0, 204602, 1000, &results, benchmark_mode, kernel_regex);
VOLK_PROFILE(volk_32fc_s32f_power_32fc, 1e-4, 0, 204602, 50, &results, benchmark_mode, kernel_regex);
VOLK_PROFILE(volk_32f_s32f_calc_spectral_noise_floor_32f, 1e-4, 20.0, 204602, 1000, &results, benchmark_mode, kernel_regex);
VOLK_PROFILE(volk_32fc_s32f_atan2_32f, 1e-4, 10.0, 204602, 100, &results, benchmark_mode, kernel_regex);
//VOLK_PROFILE(volk_32fc_x2_conjugate_dot_prod_32fc, 1e-4, 0, 2046, 10000, &results, benchmark_mode, kernel_regex);
- VOLK_PROFILE(volk_32fc_x2_conjugate_dot_prod_32fc, 1e-4, 0, 204602, 10000, &results, benchmark_mode, kernel_regex);
+ VOLK_PROFILE(volk_32fc_x2_conjugate_dot_prod_32fc, 1e-4, 0, 204602, 100, &results, benchmark_mode, kernel_regex);
VOLK_PROFILE(volk_32fc_deinterleave_32f_x2, 1e-4, 0, 204602, 1000, &results, benchmark_mode, kernel_regex);
VOLK_PROFILE(volk_32fc_deinterleave_64f_x2, 1e-4, 0, 204602, 1000, &results, benchmark_mode, kernel_regex);
VOLK_PROFILE(volk_32fc_s32f_deinterleave_real_16i, 0, 32768, 204602, 10000, &results, benchmark_mode, kernel_regex);
@@ -157,13 +219,13 @@ int main(int argc, char *argv[]) {
VOLK_PROFILE(volk_32i_x2_and_32i, 0, 0, 204602, 10000, &results, benchmark_mode, kernel_regex);
VOLK_PROFILE(volk_32i_s32f_convert_32f, 1e-4, 100, 204602, 10000, &results, benchmark_mode, kernel_regex);
VOLK_PROFILE(volk_32i_x2_or_32i, 0, 0, 204602, 10000, &results, benchmark_mode, kernel_regex);
- VOLK_PROFILE(volk_32u_byteswap, 0, 0, 204602, 2000, &results, benchmark_mode, kernel_regex);
- //VOLK_PROFILE(volk_32u_popcnt, 0, 0, 2046, 10000, &results, benchmark_mode, kernel_regex);
+ VOLK_PUPPET_PROFILE(volk_32u_byteswappuppet_32u, volk_32u_byteswap, 0, 0, 204602, 2000, &results, benchmark_mode, kernel_regex);
+ VOLK_PUPPET_PROFILE(volk_32u_popcntpuppet_32u, volk32u_popcnt_32u, 0, 0, 2046, 10000, &results, benchmark_mode, kernel_regex);
VOLK_PROFILE(volk_64f_convert_32f, 1e-4, 0, 204602, 10000, &results, benchmark_mode, kernel_regex);
VOLK_PROFILE(volk_64f_x2_max_64f, 1e-4, 0, 204602, 1000, &results, benchmark_mode, kernel_regex);
VOLK_PROFILE(volk_64f_x2_min_64f, 1e-4, 0, 204602, 1000, &results, benchmark_mode, kernel_regex);
- VOLK_PROFILE(volk_64u_byteswap, 0, 0, 204602, 1000, &results, benchmark_mode, kernel_regex);
- //VOLK_PROFILE(volk_64u_popcnt, 0, 0, 2046, 10000, &results, benchmark_mode, kernel_regex);
+ VOLK_PUPPET_PROFILE(volk_64u_byteswappuppet_64u, volk_64u_byteswap, 0, 0, 204602, 1000, &results, benchmark_mode, kernel_regex);
+ VOLK_PUPPET_PROFILE(volk_64u_popcntpuppet_64u, volk_64u_popcnt, 0, 0, 2046, 10000, &results, benchmark_mode, kernel_regex);
VOLK_PROFILE(volk_8ic_deinterleave_16i_x2, 0, 0, 204602, 3000, &results, benchmark_mode, kernel_regex);
VOLK_PROFILE(volk_8ic_s32f_deinterleave_32f_x2, 1e-4, 100, 204602, 3000, &results, benchmark_mode, kernel_regex);
VOLK_PROFILE(volk_8ic_deinterleave_real_16i, 0, 256, 204602, 3000, &results, benchmark_mode, kernel_regex);
@@ -178,6 +240,7 @@ int main(int argc, char *argv[]) {
VOLK_PROFILE(volk_32f_s32f_multiply_32f, 1e-4, 1.0, 204602, 10000, &results, benchmark_mode, kernel_regex);
VOLK_PROFILE(volk_32f_binary_slicer_32i, 0, 1.0, 204602, 10000, &results, benchmark_mode, kernel_regex);
VOLK_PROFILE(volk_32f_binary_slicer_8i, 0, 1.0, 204602, 10000, &results, benchmark_mode, kernel_regex);
+ VOLK_PROFILE(volk_32f_tanh_32f, 1e-6, 0, 204602, 1000, &results, benchmark_mode, kernel_regex);
// Until we can update the config on a kernel by kernel basis
// do not overwrite volk_config when using a regex.
@@ -204,8 +267,10 @@ int main(int argc, char *argv[]) {
#the function name is followed by the preferred architecture.\n\
";
- BOOST_FOREACH(std::string result, results) {
- config << result << std::endl;
+ BOOST_FOREACH(volk_test_results_t result, results) {
+ config << result.config_name << " "
+ << result.best_arch_a << " "
+ << result.best_arch_u << std::endl;
}
config.close();
}
diff --git a/volk/kernels/volk/volk_16i_32fc_dot_prod_32fc.h b/volk/kernels/volk/volk_16i_32fc_dot_prod_32fc.h
index 8c66892fd9..2656d766b8 100644
--- a/volk/kernels/volk/volk_16i_32fc_dot_prod_32fc.h
+++ b/volk/kernels/volk/volk_16i_32fc_dot_prod_32fc.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_16i_32fc_dot_prod_32fc_H
#define INCLUDED_volk_16i_32fc_dot_prod_32fc_H
@@ -7,7 +29,6 @@
#ifdef LV_HAVE_GENERIC
-
static inline void volk_16i_32fc_dot_prod_32fc_generic(lv_32fc_t* result, const short* input, const lv_32fc_t * taps, unsigned int num_points) {
static const int N_UNROLL = 4;
@@ -36,7 +57,54 @@ static inline void volk_16i_32fc_dot_prod_32fc_generic(lv_32fc_t* result, const
#endif /*LV_HAVE_GENERIC*/
+#ifdef LV_HAVE_NEON
+#include <arm_neon.h>
+static inline void volk_16i_32fc_dot_prod_32fc_neon(lv_32fc_t* result, const short* input, const lv_32fc_t * taps, unsigned int num_points) {
+
+ unsigned ii;
+ unsigned quarter_points = num_points / 4;
+ lv_32fc_t* tapsPtr = (lv_32fc_t*) taps;
+ short* inputPtr = (short*) input;
+ lv_32fc_t accumulator_vec[4];
+
+ float32x4x2_t tapsVal, accumulator_val;
+ int16x4_t input16;
+ int32x4_t input32;
+ float32x4_t input_float, prod_re, prod_im;
+
+ accumulator_val.val[0] = vdupq_n_f32(0.0);
+ accumulator_val.val[1] = vdupq_n_f32(0.0);
+
+ for(ii = 0; ii < quarter_points; ++ii) {
+ tapsVal = vld2q_f32((float*)tapsPtr);
+ input16 = vld1_s16(inputPtr);
+ // widen 16-bit int to 32-bit int
+ input32 = vmovl_s16(input16);
+ // convert 32-bit int to float with scale
+ input_float = vcvtq_f32_s32(input32);
+
+ prod_re = vmulq_f32(input_float, tapsVal.val[0]);
+ prod_im = vmulq_f32(input_float, tapsVal.val[1]);
+
+ accumulator_val.val[0] = vaddq_f32(prod_re, accumulator_val.val[0]);
+ accumulator_val.val[1] = vaddq_f32(prod_im, accumulator_val.val[1]);
+
+ tapsPtr += 4;
+ inputPtr += 4;
+ }
+ vst2q_f32((float*)accumulator_vec, accumulator_val);
+ accumulator_vec[0] += accumulator_vec[1];
+ accumulator_vec[2] += accumulator_vec[3];
+ accumulator_vec[0] += accumulator_vec[2];
+
+ for(ii = quarter_points * 4; ii < num_points; ++ii) {
+ accumulator_vec[0] += *(tapsPtr++) * (float)(*(inputPtr++));
+ }
+
+ *result = accumulator_vec[0];
+}
+#endif /*LV_HAVE_NEON*/
#if LV_HAVE_SSE && LV_HAVE_MMX
diff --git a/volk/kernels/volk/volk_16i_branch_4_state_8.h b/volk/kernels/volk/volk_16i_branch_4_state_8.h
index cdfbc7ba13..4477245bbf 100644
--- a/volk/kernels/volk/volk_16i_branch_4_state_8.h
+++ b/volk/kernels/volk/volk_16i_branch_4_state_8.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_16i_branch_4_state_8_a_H
#define INCLUDED_volk_16i_branch_4_state_8_a_H
diff --git a/volk/kernels/volk/volk_16i_convert_8i.h b/volk/kernels/volk/volk_16i_convert_8i.h
index 3789b2e4ab..6f16fa45d3 100644
--- a/volk/kernels/volk/volk_16i_convert_8i.h
+++ b/volk/kernels/volk/volk_16i_convert_8i.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_16i_convert_8i_u_H
#define INCLUDED_volk_16i_convert_8i_u_H
@@ -116,6 +138,46 @@ static inline void volk_16i_convert_8i_a_sse2(int8_t* outputVector, const int16_
}
#endif /* LV_HAVE_SSE2 */
+#ifdef LV_HAVE_NEON
+#include <arm_neon.h>
+/*!
+ \brief Converts the input 16 bit integer data into 8 bit integer data
+ \param inputVector The 16 bit input data buffer
+ \param outputVector The 8 bit output data buffer
+ \param num_points The number of data values to be converted
+*/
+static inline void volk_16i_convert_8i_neon(int8_t* outputVector, const int16_t* inputVector, unsigned int num_points){
+ int8_t* outputVectorPtr = outputVector;
+ const int16_t* inputVectorPtr = inputVector;
+ unsigned int number = 0;
+ unsigned int sixteenth_points = num_points / 16;
+
+ int16x8_t inputVal0;
+ int16x8_t inputVal1;
+ int8x8_t outputVal0;
+ int8x8_t outputVal1;
+ int8x16_t outputVal;
+
+ for(number = 0; number < sixteenth_points; number++){
+ // load two input vectors
+ inputVal0 = vld1q_s16(inputVectorPtr);
+ inputVal1 = vld1q_s16(inputVectorPtr+8);
+ // shift right
+ outputVal0 = vshrn_n_s16(inputVal0, 8);
+ outputVal1 = vshrn_n_s16(inputVal1, 8);
+ // squash two vectors and write output
+ outputVal = vcombine_s8(outputVal0, outputVal1);
+ vst1q_s8(outputVectorPtr, outputVal);
+ inputVectorPtr += 16;
+ outputVectorPtr += 16;
+ }
+
+ for(number = sixteenth_points * 16; number < num_points; number++){
+ *outputVectorPtr++ = ((int8_t)(*inputVectorPtr++ >> 8));
+ }
+}
+#endif /* LV_HAVE_NEON */
+
#ifdef LV_HAVE_GENERIC
/*!
\brief Converts the input 16 bit integer data into 8 bit integer data
@@ -134,7 +196,4 @@ static inline void volk_16i_convert_8i_a_generic(int8_t* outputVector, const int
}
#endif /* LV_HAVE_GENERIC */
-
-
-
#endif /* INCLUDED_volk_16i_convert_8i_a_H */
diff --git a/volk/kernels/volk/volk_16i_max_star_16i.h b/volk/kernels/volk/volk_16i_max_star_16i.h
index d296c43cb0..e81a91a375 100644
--- a/volk/kernels/volk/volk_16i_max_star_16i.h
+++ b/volk/kernels/volk/volk_16i_max_star_16i.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_16i_max_star_16i_a_H
#define INCLUDED_volk_16i_max_star_16i_a_H
@@ -94,7 +116,7 @@ static inline void volk_16i_max_star_16i_neon(short* target, short* src0, unsign
int16x8_t diff, zeros;
uint16x8_t comp1, comp2;
zeros = veorq_s16(zeros, zeros);
-
+
int16x8x2_t tmpvec;
int16x8_t candidate_vec = vld1q_dup_s16(src0 );
diff --git a/volk/kernels/volk/volk_16i_max_star_horizontal_16i.h b/volk/kernels/volk/volk_16i_max_star_horizontal_16i.h
index 1915522947..b671929a29 100644
--- a/volk/kernels/volk/volk_16i_max_star_horizontal_16i.h
+++ b/volk/kernels/volk/volk_16i_max_star_horizontal_16i.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_16i_max_star_horizontal_16i_a_H
#define INCLUDED_volk_16i_max_star_horizontal_16i_a_H
@@ -125,17 +147,17 @@ static inline void volk_16i_max_star_horizontal_16i_neon(int16_t* target, int16_
diff = vsubq_s16(input_vec.val[0], input_vec.val[1]);
comp1 = vcgeq_s16(diff, zeros);
comp2 = vcltq_s16(diff, zeros);
-
+
input_vec.val[0] = vandq_s16(input_vec.val[0], (int16x8_t)comp1);
input_vec.val[1] = vandq_s16(input_vec.val[1], (int16x8_t)comp2);
-
+
max_vec = vaddq_s16(input_vec.val[0], input_vec.val[1]);
vst1q_s16(target, max_vec);
src0 += 16;
target += 8;
}
for(number=0; number < num_points%16; number+=2) {
- target[number >> 1] = ((int16_t)(src0[number] - src0[number + 1]) > 0) ? src0[number] : src0[number+1];
+ target[number >> 1] = ((int16_t)(src0[number] - src0[number + 1]) > 0) ? src0[number] : src0[number+1];
}
}
diff --git a/volk/kernels/volk/volk_16i_permute_and_scalar_add.h b/volk/kernels/volk/volk_16i_permute_and_scalar_add.h
index 7a01d172a3..e6f20b72bc 100644
--- a/volk/kernels/volk/volk_16i_permute_and_scalar_add.h
+++ b/volk/kernels/volk/volk_16i_permute_and_scalar_add.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_16i_permute_and_scalar_add_a_H
#define INCLUDED_volk_16i_permute_and_scalar_add_a_H
diff --git a/volk/kernels/volk/volk_16i_s32f_convert_32f.h b/volk/kernels/volk/volk_16i_s32f_convert_32f.h
index a810a601a0..6ea28f0e90 100644
--- a/volk/kernels/volk/volk_16i_s32f_convert_32f.h
+++ b/volk/kernels/volk/volk_16i_s32f_convert_32f.h
@@ -1,9 +1,88 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_16i_s32f_convert_32f_u_H
#define INCLUDED_volk_16i_s32f_convert_32f_u_H
#include <inttypes.h>
#include <stdio.h>
+#ifdef LV_HAVE_AVX
+#include <immintrin.h>
+
+ /*!
+ \brief Converts the input 16 bit integer data into floating point data, and divides the each floating point output data point by the scalar value
+ \param inputVector The 16 bit input data buffer
+ \param outputVector The floating point output data buffer
+ \param scalar The value divided against each point in the output buffer
+ \param num_points The number of data values to be converted
+ */
+static inline void volk_16i_s32f_convert_32f_u_avx(float* outputVector, const int16_t* inputVector, const float scalar, unsigned int num_points){
+ unsigned int number = 0;
+ const unsigned int eighthPoints = num_points / 8;
+
+ float* outputVectorPtr = outputVector;
+ __m128 invScalar = _mm_set_ps1(1.0/scalar);
+ int16_t* inputPtr = (int16_t*)inputVector;
+ __m128i inputVal, inputVal2;
+ __m128 ret;
+ __m256 output;
+ __m256 dummy = _mm256_setzero_ps();
+
+ for(;number < eighthPoints; number++){
+
+ // Load the 8 values
+ //inputVal = _mm_loadu_si128((__m128i*)inputPtr);
+ inputVal = _mm_loadu_si128((__m128i*)inputPtr);
+
+ // Shift the input data to the right by 64 bits ( 8 bytes )
+ inputVal2 = _mm_srli_si128(inputVal, 8);
+
+ // Convert the lower 4 values into 32 bit words
+ inputVal = _mm_cvtepi16_epi32(inputVal);
+ inputVal2 = _mm_cvtepi16_epi32(inputVal2);
+
+ ret = _mm_cvtepi32_ps(inputVal);
+ ret = _mm_mul_ps(ret, invScalar);
+ output = _mm256_insertf128_ps(dummy, ret, 0);
+
+ ret = _mm_cvtepi32_ps(inputVal2);
+ ret = _mm_mul_ps(ret, invScalar);
+ output = _mm256_insertf128_ps(output, ret, 1);
+
+ _mm256_storeu_ps(outputVectorPtr, output);
+
+ outputVectorPtr += 8;
+
+ inputPtr += 8;
+ }
+
+ number = eighthPoints * 8;
+ for(; number < num_points; number++){
+ outputVector[number] =((float)(inputVector[number])) / scalar;
+ }
+}
+#endif /* LV_HAVE_AVX */
+
#ifdef LV_HAVE_SSE4_1
#include <smmintrin.h>
@@ -116,7 +195,53 @@ static inline void volk_16i_s32f_convert_32f_generic(float* outputVector, const
}
#endif /* LV_HAVE_GENERIC */
+#ifdef LV_HAVE_NEON
+ /*!
+ \brief Converts the input 16 bit integer data into floating point data, and divides the each floating point output data point by the scalar value
+ \param inputVector The 16 bit input data buffer
+ \param outputVector The floating point output data buffer
+ \param scalar The value divided against each point in the output buffer
+ \param num_points The number of data values to be converted
+ \note Output buffer does NOT need to be properly aligned
+ */
+static inline void volk_16i_s32f_convert_32f_neon(float* outputVector, const int16_t* inputVector, const float scalar, unsigned int num_points){
+ float* outputPtr = outputVector;
+ const int16_t* inputPtr = inputVector;
+ unsigned int number = 0;
+ unsigned int eighth_points = num_points / 8;
+
+ int16x4x2_t input16;
+ int32x4_t input32_0, input32_1;
+ float32x4_t input_float_0, input_float_1;
+ float32x4x2_t output_float;
+ float32x4_t inv_scale;
+
+ inv_scale = vdupq_n_f32(1.0/scalar);
+
+ // the generic disassembles to a 128-bit load
+ // and duplicates every instruction to operate on 64-bits
+ // at a time. This is only possible with lanes, which is faster
+ // than just doing a vld1_s16, but still slower.
+ for(number = 0; number < eighth_points; number++){
+ input16 = vld2_s16(inputPtr);
+ // widen 16-bit int to 32-bit int
+ input32_0 = vmovl_s16(input16.val[0]);
+ input32_1 = vmovl_s16(input16.val[1]);
+ // convert 32-bit int to float with scale
+ input_float_0 = vcvtq_f32_s32(input32_0);
+ input_float_1 = vcvtq_f32_s32(input32_1);
+ output_float.val[0] = vmulq_f32(input_float_0, inv_scale);
+ output_float.val[1] = vmulq_f32(input_float_1, inv_scale);
+ vst2q_f32(outputPtr, output_float);
+ inputPtr += 8;
+ outputPtr += 8;
+ }
+ for(number = eighth_points*8; number < num_points; number++){
+ *outputPtr++ = ((float)(*inputPtr++)) / scalar;
+ }
+}
+#endif /* LV_HAVE_NEON */
#endif /* INCLUDED_volk_16i_s32f_convert_32f_u_H */
@@ -126,6 +251,63 @@ static inline void volk_16i_s32f_convert_32f_generic(float* outputVector, const
#include <inttypes.h>
#include <stdio.h>
+#ifdef LV_HAVE_AVX
+#include <immintrin.h>
+
+ /*!
+ \brief Converts the input 16 bit integer data into floating point data, and divides the each floating point output data point by the scalar value
+ \param inputVector The 16 bit input data buffer
+ \param outputVector The floating point output data buffer
+ \param scalar The value divided against each point in the output buffer
+ \param num_points The number of data values to be converted
+ */
+static inline void volk_16i_s32f_convert_32f_a_avx(float* outputVector, const int16_t* inputVector, const float scalar, unsigned int num_points){
+ unsigned int number = 0;
+ const unsigned int eighthPoints = num_points / 8;
+
+ float* outputVectorPtr = outputVector;
+ __m128 invScalar = _mm_set_ps1(1.0/scalar);
+ int16_t* inputPtr = (int16_t*)inputVector;
+ __m128i inputVal, inputVal2;
+ __m128 ret;
+ __m256 output;
+ __m256 dummy = _mm256_setzero_ps();
+
+ for(;number < eighthPoints; number++){
+
+ // Load the 8 values
+ //inputVal = _mm_loadu_si128((__m128i*)inputPtr);
+ inputVal = _mm_load_si128((__m128i*)inputPtr);
+
+ // Shift the input data to the right by 64 bits ( 8 bytes )
+ inputVal2 = _mm_srli_si128(inputVal, 8);
+
+ // Convert the lower 4 values into 32 bit words
+ inputVal = _mm_cvtepi16_epi32(inputVal);
+ inputVal2 = _mm_cvtepi16_epi32(inputVal2);
+
+ ret = _mm_cvtepi32_ps(inputVal);
+ ret = _mm_mul_ps(ret, invScalar);
+ output = _mm256_insertf128_ps(dummy, ret, 0);
+
+ ret = _mm_cvtepi32_ps(inputVal2);
+ ret = _mm_mul_ps(ret, invScalar);
+ output = _mm256_insertf128_ps(output, ret, 1);
+
+ _mm256_store_ps(outputVectorPtr, output);
+
+ outputVectorPtr += 8;
+
+ inputPtr += 8;
+ }
+
+ number = eighthPoints * 8;
+ for(; number < num_points; number++){
+ outputVector[number] =((float)(inputVector[number])) / scalar;
+ }
+}
+#endif /* LV_HAVE_AVX */
+
#ifdef LV_HAVE_SSE4_1
#include <smmintrin.h>
diff --git a/volk/kernels/volk/volk_16i_x4_quad_max_star_16i.h b/volk/kernels/volk/volk_16i_x4_quad_max_star_16i.h
index 8e84b6ea17..4c67ef4e7d 100644
--- a/volk/kernels/volk/volk_16i_x4_quad_max_star_16i.h
+++ b/volk/kernels/volk/volk_16i_x4_quad_max_star_16i.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_16i_x4_quad_max_star_16i_a_H
#define INCLUDED_volk_16i_x4_quad_max_star_16i_a_H
diff --git a/volk/kernels/volk/volk_16i_x5_add_quad_16i_x4.h b/volk/kernels/volk/volk_16i_x5_add_quad_16i_x4.h
index cd1952bccb..6a056ff69a 100644
--- a/volk/kernels/volk/volk_16i_x5_add_quad_16i_x4.h
+++ b/volk/kernels/volk/volk_16i_x5_add_quad_16i_x4.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_16i_x5_add_quad_16i_x4_a_H
#define INCLUDED_volk_16i_x5_add_quad_16i_x4_a_H
diff --git a/volk/kernels/volk/volk_16ic_deinterleave_16i_x2.h b/volk/kernels/volk/volk_16ic_deinterleave_16i_x2.h
index 9ce8012640..26521e215d 100644
--- a/volk/kernels/volk/volk_16ic_deinterleave_16i_x2.h
+++ b/volk/kernels/volk/volk_16ic_deinterleave_16i_x2.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_16ic_deinterleave_16i_x2_a_H
#define INCLUDED_volk_16ic_deinterleave_16i_x2_a_H
diff --git a/volk/kernels/volk/volk_16ic_deinterleave_real_16i.h b/volk/kernels/volk/volk_16ic_deinterleave_real_16i.h
index f6eccd77ee..5c2988743c 100644
--- a/volk/kernels/volk/volk_16ic_deinterleave_real_16i.h
+++ b/volk/kernels/volk/volk_16ic_deinterleave_real_16i.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_16ic_deinterleave_real_16i_a_H
#define INCLUDED_volk_16ic_deinterleave_real_16i_a_H
diff --git a/volk/kernels/volk/volk_16ic_deinterleave_real_8i.h b/volk/kernels/volk/volk_16ic_deinterleave_real_8i.h
index f3d0c83524..b2b1e2a41d 100644
--- a/volk/kernels/volk/volk_16ic_deinterleave_real_8i.h
+++ b/volk/kernels/volk/volk_16ic_deinterleave_real_8i.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_16ic_deinterleave_real_8i_a_H
#define INCLUDED_volk_16ic_deinterleave_real_8i_a_H
diff --git a/volk/kernels/volk/volk_16ic_magnitude_16i.h b/volk/kernels/volk/volk_16ic_magnitude_16i.h
index b33306a123..fb29bfdc94 100644
--- a/volk/kernels/volk/volk_16ic_magnitude_16i.h
+++ b/volk/kernels/volk/volk_16ic_magnitude_16i.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_16ic_magnitude_16i_a_H
#define INCLUDED_volk_16ic_magnitude_16i_a_H
diff --git a/volk/kernels/volk/volk_16ic_s32f_deinterleave_32f_x2.h b/volk/kernels/volk/volk_16ic_s32f_deinterleave_32f_x2.h
index 55243b4aa8..cc702de872 100644
--- a/volk/kernels/volk/volk_16ic_s32f_deinterleave_32f_x2.h
+++ b/volk/kernels/volk/volk_16ic_s32f_deinterleave_32f_x2.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_16ic_s32f_deinterleave_32f_x2_a_H
#define INCLUDED_volk_16ic_s32f_deinterleave_32f_x2_a_H
diff --git a/volk/kernels/volk/volk_16ic_s32f_deinterleave_real_32f.h b/volk/kernels/volk/volk_16ic_s32f_deinterleave_real_32f.h
index 57d078a595..2dd9188c5f 100644
--- a/volk/kernels/volk/volk_16ic_s32f_deinterleave_real_32f.h
+++ b/volk/kernels/volk/volk_16ic_s32f_deinterleave_real_32f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_16ic_s32f_deinterleave_real_32f_a_H
#define INCLUDED_volk_16ic_s32f_deinterleave_real_32f_a_H
diff --git a/volk/kernels/volk/volk_16ic_s32f_magnitude_32f.h b/volk/kernels/volk/volk_16ic_s32f_magnitude_32f.h
index 27901cb9ac..ba06450312 100644
--- a/volk/kernels/volk/volk_16ic_s32f_magnitude_32f.h
+++ b/volk/kernels/volk/volk_16ic_s32f_magnitude_32f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_16ic_s32f_magnitude_32f_a_H
#define INCLUDED_volk_16ic_s32f_magnitude_32f_a_H
diff --git a/volk/kernels/volk/volk_16u_byteswap.h b/volk/kernels/volk/volk_16u_byteswap.h
index 436caf0474..3b2f9e2c91 100644
--- a/volk/kernels/volk/volk_16u_byteswap.h
+++ b/volk/kernels/volk/volk_16u_byteswap.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_16u_byteswap_u_H
#define INCLUDED_volk_16u_byteswap_u_H
@@ -136,6 +158,58 @@ static inline void volk_16u_byteswap_neon(uint16_t* intsToSwap, unsigned int num
}
#endif /* LV_HAVE_NEON */
+#ifdef LV_HAVE_NEON
+#include <arm_neon.h>
+/*!
+ \brief Byteswaps (in-place) an aligned vector of int32_t's.
+ \param intsToSwap The vector of data to byte swap
+ \param numDataPoints The number of data points
+*/
+static inline void volk_16u_byteswap_neon_table(uint16_t* intsToSwap, unsigned int num_points){
+ uint16_t* inputPtr = intsToSwap;
+ unsigned int number = 0;
+ unsigned int n16points = num_points / 16;
+
+ uint8x8x4_t input_table;
+ uint8x8_t int_lookup01, int_lookup23, int_lookup45, int_lookup67;
+ uint8x8_t swapped_int01, swapped_int23, swapped_int45, swapped_int67;
+
+ /* these magic numbers are used as byte-indeces in the LUT.
+ they are pre-computed to save time. A simple C program
+ can calculate them; for example for lookup01:
+ uint8_t chars[8] = {24, 16, 8, 0, 25, 17, 9, 1};
+ for(ii=0; ii < 8; ++ii) {
+ index += ((uint64_t)(*(chars+ii))) << (ii*8);
+ }
+ */
+ int_lookup01 = vcreate_u8(1232017111498883080);
+ int_lookup23 = vcreate_u8(1376697457175036426);
+ int_lookup45 = vcreate_u8(1521377802851189772);
+ int_lookup67 = vcreate_u8(1666058148527343118);
+
+ for(number = 0; number < n16points; ++number){
+ input_table = vld4_u8((uint8_t*) inputPtr);
+ swapped_int01 = vtbl4_u8(input_table, int_lookup01);
+ swapped_int23 = vtbl4_u8(input_table, int_lookup23);
+ swapped_int45 = vtbl4_u8(input_table, int_lookup45);
+ swapped_int67 = vtbl4_u8(input_table, int_lookup67);
+ vst1_u8((uint8_t*)inputPtr, swapped_int01);
+ vst1_u8((uint8_t*)(inputPtr+4), swapped_int23);
+ vst1_u8((uint8_t*)(inputPtr+8), swapped_int45);
+ vst1_u8((uint8_t*)(inputPtr+12), swapped_int67);
+
+ inputPtr += 16;
+ }
+
+ for(number = n16points * 16; number < num_points; ++number){
+ uint16_t output = *inputPtr;
+ output = (((output >> 8) & 0xff) | ((output << 8) & 0xff00));
+ *inputPtr = output;
+ inputPtr++;
+ }
+}
+#endif /* LV_HAVE_NEON */
+
#ifdef LV_HAVE_GENERIC
/*!
\brief Byteswaps (in-place) an aligned vector of int16_t's.
diff --git a/volk/kernels/volk/volk_16u_byteswappuppet_16u.h b/volk/kernels/volk/volk_16u_byteswappuppet_16u.h
new file mode 100644
index 0000000000..74745d328c
--- /dev/null
+++ b/volk/kernels/volk/volk_16u_byteswappuppet_16u.h
@@ -0,0 +1,55 @@
+#ifndef INCLUDED_volk_16u_byteswappuppet_16u_H
+#define INCLUDED_volk_16u_byteswappuppet_16u_H
+
+
+#include <stdint.h>
+#include <volk/volk_16u_byteswap.h>
+#include <string.h>
+
+#ifdef LV_HAVE_GENERIC
+static inline void volk_16u_byteswappuppet_16u_generic(uint16_t*output, uint16_t* intsToSwap, unsigned int num_points){
+
+ volk_16u_byteswap_generic((uint16_t*)intsToSwap, num_points);
+ memcpy((void*)output, (void*)intsToSwap, num_points * sizeof(uint16_t));
+
+}
+#endif
+
+#ifdef LV_HAVE_NEON
+static inline void volk_16u_byteswappuppet_16u_neon(uint16_t*output, uint16_t* intsToSwap, unsigned int num_points){
+
+ volk_16u_byteswap_neon((uint16_t*)intsToSwap, num_points);
+ memcpy((void*)output, (void*)intsToSwap, num_points * sizeof(uint16_t));
+
+}
+#endif
+
+#ifdef LV_HAVE_NEON
+static inline void volk_16u_byteswappuppet_16u_neon_table(uint16_t*output, uint16_t* intsToSwap, unsigned int num_points){
+
+ volk_16u_byteswap_neon_table((uint16_t*)intsToSwap, num_points);
+ memcpy((void*)output, (void*)intsToSwap, num_points * sizeof(uint16_t));
+
+}
+#endif
+
+#ifdef LV_HAVE_SSE2
+static inline void volk_16u_byteswappuppet_16u_u_sse2(uint16_t *output, uint16_t* intsToSwap, unsigned int num_points){
+
+ volk_16u_byteswap_u_sse2((uint16_t*)intsToSwap, num_points);
+ memcpy((void*)output, (void*)intsToSwap, num_points * sizeof(uint16_t));
+
+}
+#endif
+
+#ifdef LV_HAVE_SSE2
+static inline void volk_16u_byteswappuppet_16u_a_sse2(uint16_t *output, uint16_t* intsToSwap, unsigned int num_points){
+
+ volk_16u_byteswap_a_sse2((uint16_t*)intsToSwap, num_points);
+ memcpy((void*)output, (void*)intsToSwap, num_points * sizeof(uint16_t));
+
+}
+#endif
+
+
+#endif
diff --git a/volk/kernels/volk/volk_32f_accumulator_s32f.h b/volk/kernels/volk/volk_32f_accumulator_s32f.h
index a67d10f9b5..e8995fb6c6 100644
--- a/volk/kernels/volk/volk_32f_accumulator_s32f.h
+++ b/volk/kernels/volk/volk_32f_accumulator_s32f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32f_accumulator_s32f_a_H
#define INCLUDED_volk_32f_accumulator_s32f_a_H
diff --git a/volk/kernels/volk/volk_32f_acos_32f.h b/volk/kernels/volk/volk_32f_acos_32f.h
new file mode 100644
index 0000000000..1b2b734835
--- /dev/null
+++ b/volk/kernels/volk/volk_32f_acos_32f.h
@@ -0,0 +1,194 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
+#include <stdio.h>
+#include <math.h>
+#include <inttypes.h>
+
+/* This is the number of terms of Taylor series to evaluate, increase this for more accuracy*/
+#define ACOS_TERMS 2
+
+#ifndef INCLUDED_volk_32f_acos_32f_a_H
+#define INCLUDED_volk_32f_acos_32f_a_H
+
+#ifdef LV_HAVE_SSE4_1
+#include <smmintrin.h>
+/*!
+ \brief Computes arccosine of input vector and stores results in output vector
+ \param bVector The vector where results will be stored
+ \param aVector The input vector of floats
+ \param num_points Number of points for which arccosine is to be computed
+*/
+static inline void volk_32f_acos_32f_a_sse4_1(float* bVector, const float* aVector, unsigned int num_points){
+
+ float* bPtr = bVector;
+ const float* aPtr = aVector;
+
+ unsigned int number = 0;
+ unsigned int quarterPoints = num_points / 4;
+ int i, j;
+
+ __m128 aVal, d, pi, pio2, x, y, z, arccosine;
+ __m128 fzeroes, fones, ftwos, ffours, condition;
+
+ pi = _mm_set1_ps(3.14159265358979323846);
+ pio2 = _mm_set1_ps(3.14159265358979323846/2);
+ fzeroes = _mm_setzero_ps();
+ fones = _mm_set1_ps(1.0);
+ ftwos = _mm_set1_ps(2.0);
+ ffours = _mm_set1_ps(4.0);
+
+ for(;number < quarterPoints; number++){
+ aVal = _mm_load_ps(aPtr);
+ d = aVal;
+ aVal = _mm_div_ps(_mm_sqrt_ps(_mm_mul_ps(_mm_add_ps(fones, aVal), _mm_sub_ps(fones, aVal))), aVal);
+ z = aVal;
+ condition = _mm_cmplt_ps(z, fzeroes);
+ z = _mm_sub_ps(z, _mm_and_ps(_mm_mul_ps(z, ftwos), condition));
+ x = z;
+ condition = _mm_cmplt_ps(z, fones);
+ x = _mm_add_ps(x, _mm_and_ps(_mm_sub_ps(_mm_div_ps(fones, z), z), condition));
+
+ for(i = 0; i < 2; i++)
+ x = _mm_add_ps(x, _mm_sqrt_ps(_mm_add_ps(fones, _mm_mul_ps(x, x))));
+ x = _mm_div_ps(fones, x);
+ y = fzeroes;
+ for(j = ACOS_TERMS - 1; j >=0 ; j--)
+ y = _mm_add_ps(_mm_mul_ps(y, _mm_mul_ps(x, x)), _mm_set1_ps(pow(-1,j)/(2*j+1)));
+
+ y = _mm_mul_ps(y, _mm_mul_ps(x, ffours));
+ condition = _mm_cmpgt_ps(z, fones);
+
+ y = _mm_add_ps(y, _mm_and_ps(_mm_sub_ps(pio2, _mm_mul_ps(y, ftwos)), condition));
+ arccosine = y;
+ condition = _mm_cmplt_ps(aVal, fzeroes);
+ arccosine = _mm_sub_ps(arccosine, _mm_and_ps(_mm_mul_ps(arccosine, ftwos), condition));
+ condition = _mm_cmplt_ps(d, fzeroes);
+ arccosine = _mm_add_ps(arccosine, _mm_and_ps(pi, condition));
+
+ _mm_store_ps(bPtr, arccosine);
+ aPtr += 4;
+ bPtr += 4;
+ }
+
+ number = quarterPoints * 4;
+ for(;number < num_points; number++){
+ *bPtr++ = acos(*aPtr++);
+ }
+}
+
+#endif /* LV_HAVE_SSE4_1 for aligned */
+
+#endif /* INCLUDED_volk_32f_acos_32f_a_H */
+
+
+#ifndef INCLUDED_volk_32f_acos_32f_u_H
+#define INCLUDED_volk_32f_acos_32f_u_H
+
+#ifdef LV_HAVE_SSE4_1
+#include <smmintrin.h>
+/*!
+ \brief Computes arccosine of input vector and stores results in output vector
+ \param bVector The vector where results will be stored
+ \param aVector The input vector of floats
+ \param num_points Number of points for which arccosine is to be computed
+*/
+static inline void volk_32f_acos_32f_u_sse4_1(float* bVector, const float* aVector, unsigned int num_points){
+ float* bPtr = bVector;
+ const float* aPtr = aVector;
+
+ unsigned int number = 0;
+ unsigned int quarterPoints = num_points / 4;
+ int i, j;
+
+ __m128 aVal, d, pi, pio2, x, y, z, arccosine;
+ __m128 fzeroes, fones, ftwos, ffours, condition;
+
+ pi = _mm_set1_ps(3.14159265358979323846);
+ pio2 = _mm_set1_ps(3.14159265358979323846/2);
+ fzeroes = _mm_setzero_ps();
+ fones = _mm_set1_ps(1.0);
+ ftwos = _mm_set1_ps(2.0);
+ ffours = _mm_set1_ps(4.0);
+
+ for(;number < quarterPoints; number++){
+ aVal = _mm_loadu_ps(aPtr);
+ d = aVal;
+ aVal = _mm_div_ps(_mm_sqrt_ps(_mm_mul_ps(_mm_add_ps(fones, aVal), _mm_sub_ps(fones, aVal))), aVal);
+ z = aVal;
+ condition = _mm_cmplt_ps(z, fzeroes);
+ z = _mm_sub_ps(z, _mm_and_ps(_mm_mul_ps(z, ftwos), condition));
+ x = z;
+ condition = _mm_cmplt_ps(z, fones);
+ x = _mm_add_ps(x, _mm_and_ps(_mm_sub_ps(_mm_div_ps(fones, z), z), condition));
+
+ for(i = 0; i < 2; i++)
+ x = _mm_add_ps(x, _mm_sqrt_ps(_mm_add_ps(fones, _mm_mul_ps(x, x))));
+ x = _mm_div_ps(fones, x);
+ y = fzeroes;
+
+ for(j = ACOS_TERMS - 1; j >=0 ; j--)
+ y = _mm_add_ps(_mm_mul_ps(y, _mm_mul_ps(x, x)), _mm_set1_ps(pow(-1,j)/(2*j+1)));
+
+ y = _mm_mul_ps(y, _mm_mul_ps(x, ffours));
+ condition = _mm_cmpgt_ps(z, fones);
+
+ y = _mm_add_ps(y, _mm_and_ps(_mm_sub_ps(pio2, _mm_mul_ps(y, ftwos)), condition));
+ arccosine = y;
+ condition = _mm_cmplt_ps(aVal, fzeroes);
+ arccosine = _mm_sub_ps(arccosine, _mm_and_ps(_mm_mul_ps(arccosine, ftwos), condition));
+ condition = _mm_cmplt_ps(d, fzeroes);
+ arccosine = _mm_add_ps(arccosine, _mm_and_ps(pi, condition));
+
+ _mm_storeu_ps(bPtr, arccosine);
+ aPtr += 4;
+ bPtr += 4;
+ }
+
+ number = quarterPoints * 4;
+ for(;number < num_points; number++){
+ *bPtr++ = acos(*aPtr++);
+ }
+}
+
+#endif /* LV_HAVE_SSE4_1 for aligned */
+
+#ifdef LV_HAVE_GENERIC
+/*!
+ \brief Computes arccosine of input vector and stores results in output vector
+ \param bVector The vector where results will be stored
+ \param aVector The input vector of floats
+ \param num_points Number of points for which arccosine is to be computed
+*/
+static inline void volk_32f_acos_32f_generic(float* bVector, const float* aVector, unsigned int num_points){
+ float* bPtr = bVector;
+ const float* aPtr = aVector;
+ unsigned int number = 0;
+
+ for(number = 0; number < num_points; number++){
+ *bPtr++ = acos(*aPtr++);
+ }
+
+}
+#endif /* LV_HAVE_GENERIC */
+
+#endif /* INCLUDED_volk_32f_acos_32f_u_H */
diff --git a/volk/kernels/volk/volk_32f_asin_32f.h b/volk/kernels/volk/volk_32f_asin_32f.h
new file mode 100644
index 0000000000..7b80de7ee8
--- /dev/null
+++ b/volk/kernels/volk/volk_32f_asin_32f.h
@@ -0,0 +1,189 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
+#include <stdio.h>
+#include <math.h>
+#include <inttypes.h>
+
+/* This is the number of terms of Taylor series to evaluate, increase this for more accuracy*/
+#define ASIN_TERMS 2
+
+#ifndef INCLUDED_volk_32f_asin_32f_a_H
+#define INCLUDED_volk_32f_asin_32f_a_H
+
+#ifdef LV_HAVE_SSE4_1
+#include <smmintrin.h>
+/*!
+ \brief Computes arcsine of input vector and stores results in output vector
+ \param bVector The vector where results will be stored
+ \param aVector The input vector of floats
+ \param num_points Number of points for which arcsine is to be computed
+*/
+static inline void volk_32f_asin_32f_a_sse4_1(float* bVector, const float* aVector, unsigned int num_points){
+
+ float* bPtr = bVector;
+ const float* aPtr = aVector;
+
+ unsigned int number = 0;
+ unsigned int quarterPoints = num_points / 4;
+ int i, j;
+
+ __m128 aVal, pio2, x, y, z, arcsine;
+ __m128 fzeroes, fones, ftwos, ffours, condition;
+
+ pio2 = _mm_set1_ps(3.14159265358979323846/2);
+ fzeroes = _mm_setzero_ps();
+ fones = _mm_set1_ps(1.0);
+ ftwos = _mm_set1_ps(2.0);
+ ffours = _mm_set1_ps(4.0);
+
+ for(;number < quarterPoints; number++){
+ aVal = _mm_load_ps(aPtr);
+ aVal = _mm_div_ps(aVal, _mm_sqrt_ps(_mm_mul_ps(_mm_add_ps(fones, aVal), _mm_sub_ps(fones, aVal))));
+ z = aVal;
+ condition = _mm_cmplt_ps(z, fzeroes);
+ z = _mm_sub_ps(z, _mm_and_ps(_mm_mul_ps(z, ftwos), condition));
+ x = z;
+ condition = _mm_cmplt_ps(z, fones);
+ x = _mm_add_ps(x, _mm_and_ps(_mm_sub_ps(_mm_div_ps(fones, z), z), condition));
+
+ for(i = 0; i < 2; i++){
+ x = _mm_add_ps(x, _mm_sqrt_ps(_mm_add_ps(fones, _mm_mul_ps(x, x))));
+ }
+ x = _mm_div_ps(fones, x);
+ y = fzeroes;
+ for(j = ASIN_TERMS - 1; j >=0 ; j--){
+ y = _mm_add_ps(_mm_mul_ps(y, _mm_mul_ps(x, x)), _mm_set1_ps(pow(-1,j)/(2*j+1)));
+ }
+
+ y = _mm_mul_ps(y, _mm_mul_ps(x, ffours));
+ condition = _mm_cmpgt_ps(z, fones);
+
+ y = _mm_add_ps(y, _mm_and_ps(_mm_sub_ps(pio2, _mm_mul_ps(y, ftwos)), condition));
+ arcsine = y;
+ condition = _mm_cmplt_ps(aVal, fzeroes);
+ arcsine = _mm_sub_ps(arcsine, _mm_and_ps(_mm_mul_ps(arcsine, ftwos), condition));
+
+ _mm_store_ps(bPtr, arcsine);
+ aPtr += 4;
+ bPtr += 4;
+ }
+
+ number = quarterPoints * 4;
+ for(;number < num_points; number++){
+ *bPtr++ = asin(*aPtr++);
+ }
+}
+
+#endif /* LV_HAVE_SSE4_1 for aligned */
+
+#endif /* INCLUDED_volk_32f_asin_32f_a_H */
+
+#ifndef INCLUDED_volk_32f_asin_32f_u_H
+#define INCLUDED_volk_32f_asin_32f_u_H
+
+#ifdef LV_HAVE_SSE4_1
+#include <smmintrin.h>
+/*!
+ \brief Computes arcsine of input vector and stores results in output vector
+ \param bVector The vector where results will be stored
+ \param aVector The input vector of floats
+ \param num_points Number of points for which arcsine is to be computed
+*/
+static inline void volk_32f_asin_32f_u_sse4_1(float* bVector, const float* aVector, unsigned int num_points){
+
+ float* bPtr = bVector;
+ const float* aPtr = aVector;
+
+ unsigned int number = 0;
+ unsigned int quarterPoints = num_points / 4;
+ int i, j;
+
+ __m128 aVal, pio2, x, y, z, arcsine;
+ __m128 fzeroes, fones, ftwos, ffours, condition;
+
+ pio2 = _mm_set1_ps(3.14159265358979323846/2);
+ fzeroes = _mm_setzero_ps();
+ fones = _mm_set1_ps(1.0);
+ ftwos = _mm_set1_ps(2.0);
+ ffours = _mm_set1_ps(4.0);
+
+ for(;number < quarterPoints; number++){
+ aVal = _mm_loadu_ps(aPtr);
+ aVal = _mm_div_ps(aVal, _mm_sqrt_ps(_mm_mul_ps(_mm_add_ps(fones, aVal), _mm_sub_ps(fones, aVal))));
+ z = aVal;
+ condition = _mm_cmplt_ps(z, fzeroes);
+ z = _mm_sub_ps(z, _mm_and_ps(_mm_mul_ps(z, ftwos), condition));
+ x = z;
+ condition = _mm_cmplt_ps(z, fones);
+ x = _mm_add_ps(x, _mm_and_ps(_mm_sub_ps(_mm_div_ps(fones, z), z), condition));
+
+ for(i = 0; i < 2; i++){
+ x = _mm_add_ps(x, _mm_sqrt_ps(_mm_add_ps(fones, _mm_mul_ps(x, x))));
+ }
+ x = _mm_div_ps(fones, x);
+ y = fzeroes;
+ for(j = ASIN_TERMS - 1; j >=0 ; j--){
+ y = _mm_add_ps(_mm_mul_ps(y, _mm_mul_ps(x, x)), _mm_set1_ps(pow(-1,j)/(2*j+1)));
+ }
+
+ y = _mm_mul_ps(y, _mm_mul_ps(x, ffours));
+ condition = _mm_cmpgt_ps(z, fones);
+
+ y = _mm_add_ps(y, _mm_and_ps(_mm_sub_ps(pio2, _mm_mul_ps(y, ftwos)), condition));
+ arcsine = y;
+ condition = _mm_cmplt_ps(aVal, fzeroes);
+ arcsine = _mm_sub_ps(arcsine, _mm_and_ps(_mm_mul_ps(arcsine, ftwos), condition));
+
+ _mm_storeu_ps(bPtr, arcsine);
+ aPtr += 4;
+ bPtr += 4;
+ }
+
+ number = quarterPoints * 4;
+ for(;number < num_points; number++){
+ *bPtr++ = asin(*aPtr++);
+ }
+}
+
+#endif /* LV_HAVE_SSE4_1 for unaligned */
+
+#ifdef LV_HAVE_GENERIC
+/*!
+ \brief Computes arcsine of input vector and stores results in output vector
+ \param bVector The vector where results will be stored
+ \param aVector The input vector of floats
+ \param num_points Number of points for which arcsine is to be computed
+*/
+static inline void volk_32f_asin_32f_u_generic(float* bVector, const float* aVector, unsigned int num_points){
+ float* bPtr = bVector;
+ const float* aPtr = aVector;
+ unsigned int number = 0;
+
+ for(number = 0; number < num_points; number++){
+ *bPtr++ = asin(*aPtr++);
+ }
+
+}
+#endif /* LV_HAVE_GENERIC */
+
+#endif /* INCLUDED_volk_32f_asin_32f_u_H */
diff --git a/volk/kernels/volk/volk_32f_atan_32f.h b/volk/kernels/volk/volk_32f_atan_32f.h
new file mode 100644
index 0000000000..60742bb724
--- /dev/null
+++ b/volk/kernels/volk/volk_32f_atan_32f.h
@@ -0,0 +1,183 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
+#include <stdio.h>
+#include <math.h>
+#include <inttypes.h>
+
+/* This is the number of terms of Taylor series to evaluate, increase this for more accuracy*/
+#define TERMS 2
+
+#ifndef INCLUDED_volk_32f_atan_32f_a_H
+#define INCLUDED_volk_32f_atan_32f_a_H
+
+#ifdef LV_HAVE_SSE4_1
+#include <smmintrin.h>
+/*!
+ \brief Computes arctangent of input vector and stores results in output vector
+ \param bVector The vector where results will be stored
+ \param aVector The input vector of floats
+ \param num_points Number of points for which arctangent is to be computed
+*/
+static inline void volk_32f_atan_32f_a_sse4_1(float* bVector, const float* aVector, unsigned int num_points){
+
+ float* bPtr = bVector;
+ const float* aPtr = aVector;
+
+ unsigned int number = 0;
+ unsigned int quarterPoints = num_points / 4;
+ int i, j;
+
+ __m128 aVal, pio2, x, y, z, arctangent;
+ __m128 fzeroes, fones, ftwos, ffours, condition;
+
+ pio2 = _mm_set1_ps(3.14159265358979323846/2);
+ fzeroes = _mm_setzero_ps();
+ fones = _mm_set1_ps(1.0);
+ ftwos = _mm_set1_ps(2.0);
+ ffours = _mm_set1_ps(4.0);
+
+ for(;number < quarterPoints; number++){
+ aVal = _mm_load_ps(aPtr);
+ z = aVal;
+ condition = _mm_cmplt_ps(z, fzeroes);
+ z = _mm_sub_ps(z, _mm_and_ps(_mm_mul_ps(z, ftwos), condition));
+ x = z;
+ condition = _mm_cmplt_ps(z, fones);
+ x = _mm_add_ps(x, _mm_and_ps(_mm_sub_ps(_mm_div_ps(fones, z), z), condition));
+
+ for(i = 0; i < 2; i++){
+ x = _mm_add_ps(x, _mm_sqrt_ps(_mm_add_ps(fones, _mm_mul_ps(x, x))));
+ }
+ x = _mm_div_ps(fones, x);
+ y = fzeroes;
+ for(j = TERMS - 1; j >=0 ; j--){
+ y = _mm_add_ps(_mm_mul_ps(y, _mm_mul_ps(x, x)), _mm_set1_ps(pow(-1,j)/(2*j+1)));
+ }
+
+ y = _mm_mul_ps(y, _mm_mul_ps(x, ffours));
+ condition = _mm_cmpgt_ps(z, fones);
+
+ y = _mm_add_ps(y, _mm_and_ps(_mm_sub_ps(pio2, _mm_mul_ps(y, ftwos)), condition));
+ arctangent = y;
+ condition = _mm_cmplt_ps(aVal, fzeroes);
+ arctangent = _mm_sub_ps(arctangent, _mm_and_ps(_mm_mul_ps(arctangent, ftwos), condition));
+
+ _mm_store_ps(bPtr, arctangent);
+ aPtr += 4;
+ bPtr += 4;
+ }
+
+ number = quarterPoints * 4;
+ for(;number < num_points; number++){
+ *bPtr++ = atan(*aPtr++);
+ }
+}
+
+#endif /* LV_HAVE_SSE4_1 for aligned */
+
+#endif /* INCLUDED_volk_32f_atan_32f_a_H */
+
+#ifndef INCLUDED_volk_32f_atan_32f_u_H
+#define INCLUDED_volk_32f_atan_32f_u_H
+
+#ifdef LV_HAVE_SSE4_1
+#include <smmintrin.h>
+/*!
+ \brief Computes arctangent of input vector and stores results in output vector
+ \param bVector The vector where results will be stored
+ \param aVector The input vector of floats
+ \param num_points Number of points for which arctangent is to be computed
+*/
+static inline void volk_32f_atan_32f_u_sse4_1(float* bVector, const float* aVector, unsigned int num_points){
+
+ float* bPtr = bVector;
+ const float* aPtr = aVector;
+
+ unsigned int number = 0;
+ unsigned int quarterPoints = num_points / 4;
+ int i, j;
+
+ __m128 aVal, pio2, x, y, z, arctangent;
+ __m128 fzeroes, fones, ftwos, ffours, condition;
+
+ pio2 = _mm_set1_ps(3.14159265358979323846/2);
+ fzeroes = _mm_setzero_ps();
+ fones = _mm_set1_ps(1.0);
+ ftwos = _mm_set1_ps(2.0);
+ ffours = _mm_set1_ps(4.0);
+
+ for(;number < quarterPoints; number++){
+ aVal = _mm_loadu_ps(aPtr);
+ z = aVal;
+ condition = _mm_cmplt_ps(z, fzeroes);
+ z = _mm_sub_ps(z, _mm_and_ps(_mm_mul_ps(z, ftwos), condition));
+ x = z;
+ condition = _mm_cmplt_ps(z, fones);
+ x = _mm_add_ps(x, _mm_and_ps(_mm_sub_ps(_mm_div_ps(fones, z), z), condition));
+
+ for(i = 0; i < 2; i++) x = _mm_add_ps(x, _mm_sqrt_ps(_mm_add_ps(fones, _mm_mul_ps(x, x))));
+ x = _mm_div_ps(fones, x);
+ y = fzeroes;
+ for(j = TERMS - 1; j >= 0; j--) y = _mm_add_ps(_mm_mul_ps(y, _mm_mul_ps(x, x)), _mm_set1_ps(pow(-1,j)/(2*j+1)));
+
+ y = _mm_mul_ps(y, _mm_mul_ps(x, ffours));
+ condition = _mm_cmpgt_ps(z, fones);
+
+ y = _mm_add_ps(y, _mm_and_ps(_mm_sub_ps(pio2, _mm_mul_ps(y, ftwos)), condition));
+ arctangent = y;
+ condition = _mm_cmplt_ps(aVal, fzeroes);
+ arctangent = _mm_sub_ps(arctangent, _mm_and_ps(_mm_mul_ps(arctangent, ftwos), condition));
+
+ _mm_storeu_ps(bPtr, arctangent);
+ aPtr += 4;
+ bPtr += 4;
+ }
+
+ number = quarterPoints * 4;
+ for(;number < num_points; number++){
+ *bPtr++ = atan(*aPtr++);
+ }
+}
+
+#endif /* LV_HAVE_SSE4_1 for unaligned */
+
+#ifdef LV_HAVE_GENERIC
+/*!
+ \brief Computes arctangent of input vector and stores results in output vector
+ \param bVector The vector where results will be stored
+ \param aVector The input vector of floats
+ \param num_points Number of points for which arctangent is to be computed
+*/
+static inline void volk_32f_atan_32f_generic(float* bVector, const float* aVector, unsigned int num_points){
+ float* bPtr = bVector;
+ const float* aPtr = aVector;
+ unsigned int number = 0;
+
+ for(number = 0; number < num_points; number++){
+ *bPtr++ = atan(*aPtr++);
+ }
+
+}
+#endif /* LV_HAVE_GENERIC */
+
+#endif /* INCLUDED_volk_32f_atan_32f_u_H */
diff --git a/volk/kernels/volk/volk_32f_binary_slicer_32i.h b/volk/kernels/volk/volk_32f_binary_slicer_32i.h
index f47d20fd37..41f59148c2 100644
--- a/volk/kernels/volk/volk_32f_binary_slicer_32i.h
+++ b/volk/kernels/volk/volk_32f_binary_slicer_32i.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32f_binary_slicer_32i_H
#define INCLUDED_volk_32f_binary_slicer_32i_H
diff --git a/volk/kernels/volk/volk_32f_binary_slicer_8i.h b/volk/kernels/volk/volk_32f_binary_slicer_8i.h
index e24960cab7..ae4420b6e1 100644
--- a/volk/kernels/volk/volk_32f_binary_slicer_8i.h
+++ b/volk/kernels/volk/volk_32f_binary_slicer_8i.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32f_binary_slicer_8i_H
#define INCLUDED_volk_32f_binary_slicer_8i_H
@@ -184,4 +206,84 @@ volk_32f_binary_slicer_8i_u_sse2(int8_t* cVector, const float* aVector,
#endif /* LV_HAVE_SSE2 */
+#ifdef LV_HAVE_NEON
+#include <arm_neon.h>
+/*!
+ \brief Returns integer 1 if float input is greater than or equal to 0, 1 otherwise
+ \param cVector The char (int8_t) output (either 0 or 1)
+ \param aVector The float input
+ \param num_points The number of values in aVector and stored into cVector
+*/
+static inline void
+volk_32f_binary_slicer_8i_neon(int8_t* cVector, const float* aVector,
+ unsigned int num_points)
+{
+ int8_t* cPtr = cVector;
+ const float* aPtr = aVector;
+ unsigned int number = 0;
+ unsigned int n16points = num_points / 16;
+
+ float32x4x2_t input_val0, input_val1;
+ float32x4_t zero_val;
+ uint32x4x2_t res0_u32, res1_u32;
+ uint16x4x2_t res0_u16x4, res1_u16x4;
+ uint16x8x2_t res_u16x8;
+ uint8x8x2_t res_u8;
+ uint8x8_t one;
+
+ zero_val = vdupq_n_f32(0.0);
+ one = vdup_n_u8(0x01);
+
+ // TODO: this is a good candidate for asm because the vcombines
+ // can be eliminated simply by picking dst registers that are
+ // adjacent.
+ for(number = 0; number < n16points; number++) {
+ input_val0 = vld2q_f32(aPtr);
+ input_val1 = vld2q_f32(aPtr+8);
+
+ // test against 0; return uint32
+ res0_u32.val[0] = vcgeq_f32(input_val0.val[0], zero_val);
+ res0_u32.val[1] = vcgeq_f32(input_val0.val[1], zero_val);
+ res1_u32.val[0] = vcgeq_f32(input_val1.val[0], zero_val);
+ res1_u32.val[1] = vcgeq_f32(input_val1.val[1], zero_val);
+
+ // narrow uint32 -> uint16 followed by combine to 8-element vectors
+ res0_u16x4.val[0] = vmovn_u32(res0_u32.val[0]);
+ res0_u16x4.val[1] = vmovn_u32(res0_u32.val[1]);
+ res1_u16x4.val[0] = vmovn_u32(res1_u32.val[0]);
+ res1_u16x4.val[1] = vmovn_u32(res1_u32.val[1]);
+
+ res_u16x8.val[0] = vcombine_u16(res0_u16x4.val[0], res1_u16x4.val[0]);
+ res_u16x8.val[1] = vcombine_u16(res0_u16x4.val[1], res1_u16x4.val[1]);
+
+ // narrow uint16x8 -> uint8x8
+ res_u8.val[0] = vmovn_u16(res_u16x8.val[0]);
+ res_u8.val[1] = vmovn_u16(res_u16x8.val[1]);
+ // we *could* load twice as much data and do another vcombine here
+ // to get a uint8x16x2 vector, still only do 2 vandqs and a single store
+ // but that turns out to be ~16% slower than this version on zc702
+ // it's possible register contention in GCC scheduler slows it down
+ // and a hand-written asm with quad-word u8 registers is much faster.
+
+ res_u8.val[0] = vand_u8(one, res_u8.val[0]);
+ res_u8.val[1] = vand_u8(one, res_u8.val[1]);
+
+ vst2_u8((unsigned char*)cPtr, res_u8);
+ cPtr += 16;
+ aPtr += 16;
+
+ }
+
+ for(number = n16points * 16; number < num_points; number++) {
+ if(*aPtr++ >= 0) {
+ *cPtr++ = 1;
+ }
+ else {
+ *cPtr++ = 0;
+ }
+ }
+}
+#endif /* LV_HAVE_NEON */
+
+
#endif /* INCLUDED_volk_32f_binary_slicer_8i_H */
diff --git a/volk/kernels/volk/volk_32f_convert_64f.h b/volk/kernels/volk/volk_32f_convert_64f.h
index 2f036955dd..96a411c800 100644
--- a/volk/kernels/volk/volk_32f_convert_64f.h
+++ b/volk/kernels/volk/volk_32f_convert_64f.h
@@ -1,9 +1,67 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32f_convert_64f_u_H
#define INCLUDED_volk_32f_convert_64f_u_H
#include <inttypes.h>
#include <stdio.h>
+#ifdef LV_HAVE_AVX
+#include <immintrin.h>
+ /*!
+ \brief Converts the float values into double values
+ \param dVector The converted double vector values
+ \param fVector The float vector values to be converted
+ \param num_points The number of points in the two vectors to be converted
+ */
+
+static inline void volk_32f_convert_64f_u_avx(double* outputVector, const float* inputVector, unsigned int num_points){
+ unsigned int number = 0;
+
+ const unsigned int quarterPoints = num_points / 4;
+
+ const float* inputVectorPtr = (const float*)inputVector;
+ double* outputVectorPtr = outputVector;
+ __m256d ret;
+ __m128 inputVal;
+
+ for(;number < quarterPoints; number++){
+ inputVal = _mm_loadu_ps(inputVectorPtr); inputVectorPtr += 4;
+
+ ret = _mm256_cvtps_pd(inputVal);
+ _mm256_storeu_pd(outputVectorPtr, ret);
+
+ outputVectorPtr += 4;
+ }
+
+ number = quarterPoints * 4;
+ for(; number < num_points; number++){
+ outputVector[number] = (double)(inputVector[number]);
+ }
+}
+
+#endif /* LV_HAVE_AVX */
+
#ifdef LV_HAVE_SSE2
#include <emmintrin.h>
/*!
@@ -68,12 +126,48 @@ static inline void volk_32f_convert_64f_generic(double* outputVector, const floa
#endif /* INCLUDED_volk_32f_convert_64f_u_H */
+
+
#ifndef INCLUDED_volk_32f_convert_64f_a_H
#define INCLUDED_volk_32f_convert_64f_a_H
#include <inttypes.h>
#include <stdio.h>
+#ifdef LV_HAVE_AVX
+#include <immintrin.h>
+ /*!
+ \brief Converts the float values into double values
+ \param dVector The converted double vector values
+ \param fVector The float vector values to be converted
+ \param num_points The number of points in the two vectors to be converted
+ */
+static inline void volk_32f_convert_64f_a_avx(double* outputVector, const float* inputVector, unsigned int num_points){
+ unsigned int number = 0;
+
+ const unsigned int quarterPoints = num_points / 4;
+
+ const float* inputVectorPtr = (const float*)inputVector;
+ double* outputVectorPtr = outputVector;
+ __m256d ret;
+ __m128 inputVal;
+
+ for(;number < quarterPoints; number++){
+ inputVal = _mm_load_ps(inputVectorPtr); inputVectorPtr += 4;
+
+ ret = _mm256_cvtps_pd(inputVal);
+ _mm256_store_pd(outputVectorPtr, ret);
+
+ outputVectorPtr += 4;
+ }
+
+ number = quarterPoints * 4;
+ for(; number < num_points; number++){
+ outputVector[number] = (double)(inputVector[number]);
+ }
+}
+#endif /* LV_HAVE_AVX */
+
#ifdef LV_HAVE_SSE2
#include <emmintrin.h>
/*!
diff --git a/volk/kernels/volk/volk_32f_cos_32f.h b/volk/kernels/volk/volk_32f_cos_32f.h
new file mode 100644
index 0000000000..49c56580bf
--- /dev/null
+++ b/volk/kernels/volk/volk_32f_cos_32f.h
@@ -0,0 +1,211 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
+#include <stdio.h>
+#include <math.h>
+#include <inttypes.h>
+
+#ifndef INCLUDED_volk_32f_cos_32f_a_H
+#define INCLUDED_volk_32f_cos_32f_a_H
+
+#ifdef LV_HAVE_SSE4_1
+#include <smmintrin.h>
+/*!
+ \brief Computes cosine of input vector and stores results in output vector
+ \param bVector The vector where results will be stored
+ \param aVector The input vector of floats
+ \param num_points Number of points for which cosine is to be computed
+*/
+static inline void volk_32f_cos_32f_a_sse4_1(float* bVector, const float* aVector, unsigned int num_points){
+
+ float* bPtr = bVector;
+ const float* aPtr = aVector;
+
+ unsigned int number = 0;
+ unsigned int quarterPoints = num_points / 4;
+ unsigned int i = 0;
+
+ __m128 aVal, s, m4pi, pio4A, pio4B, cp1, cp2, cp3, cp4, cp5, ffours, ftwos, fones, fzeroes;
+ __m128 sine, cosine, condition1, condition3;
+ __m128i q, r, ones, twos, fours;
+
+ m4pi = _mm_set1_ps(1.273239545);
+ pio4A = _mm_set1_ps(0.78515625);
+ pio4B = _mm_set1_ps(0.241876e-3);
+ ffours = _mm_set1_ps(4.0);
+ ftwos = _mm_set1_ps(2.0);
+ fones = _mm_set1_ps(1.0);
+ fzeroes = _mm_setzero_ps();
+ ones = _mm_set1_epi32(1);
+ twos = _mm_set1_epi32(2);
+ fours = _mm_set1_epi32(4);
+
+ cp1 = _mm_set1_ps(1.0);
+ cp2 = _mm_set1_ps(0.83333333e-1);
+ cp3 = _mm_set1_ps(0.2777778e-2);
+ cp4 = _mm_set1_ps(0.49603e-4);
+ cp5 = _mm_set1_ps(0.551e-6);
+
+ for(;number < quarterPoints; number++){
+
+ aVal = _mm_load_ps(aPtr);
+ s = _mm_sub_ps(aVal, _mm_and_ps(_mm_mul_ps(aVal, ftwos), _mm_cmplt_ps(aVal, fzeroes)));
+ q = _mm_cvtps_epi32(_mm_mul_ps(s, m4pi));
+ r = _mm_add_epi32(q, _mm_and_si128(q, ones));
+
+ s = _mm_sub_ps(s, _mm_mul_ps(_mm_cvtepi32_ps(r), pio4A));
+ s = _mm_sub_ps(s, _mm_mul_ps(_mm_cvtepi32_ps(r), pio4B));
+
+ s = _mm_div_ps(s, _mm_set1_ps(8.0)); // The constant is 2^N, for 3 times argument reduction
+ s = _mm_mul_ps(s, s);
+ // Evaluate Taylor series
+ s = _mm_mul_ps(_mm_add_ps(_mm_mul_ps(_mm_sub_ps(_mm_mul_ps(_mm_add_ps(_mm_mul_ps(_mm_sub_ps(_mm_mul_ps(s, cp5), cp4), s), cp3), s), cp2), s), cp1), s);
+
+ for(i = 0; i < 3; i++) s = _mm_mul_ps(s, _mm_sub_ps(ffours, s));
+ s = _mm_div_ps(s, ftwos);
+
+ sine = _mm_sqrt_ps(_mm_mul_ps(_mm_sub_ps(ftwos, s), s));
+ cosine = _mm_sub_ps(fones, s);
+
+ condition1 = _mm_cmpneq_ps(_mm_cvtepi32_ps(_mm_and_si128(_mm_add_epi32(q, ones), twos)), fzeroes);
+
+ condition3 = _mm_cmpneq_ps(_mm_cvtepi32_ps(_mm_and_si128(_mm_add_epi32(q, twos), fours)), fzeroes);
+
+ cosine = _mm_add_ps(cosine, _mm_and_ps(_mm_sub_ps(sine, cosine), condition1));
+ cosine = _mm_sub_ps(cosine, _mm_and_ps(_mm_mul_ps(cosine, _mm_set1_ps(2.0f)), condition3));
+ _mm_store_ps(bPtr, cosine);
+ aPtr += 4;
+ bPtr += 4;
+ }
+
+ number = quarterPoints * 4;
+ for(;number < num_points; number++){
+ *bPtr++ = cos(*aPtr++);
+ }
+}
+
+#endif /* LV_HAVE_SSE4_1 for aligned */
+
+#endif /* INCLUDED_volk_32f_cos_32f_a_H */
+
+#ifndef INCLUDED_volk_32f_cos_32f_u_H
+#define INCLUDED_volk_32f_cos_32f_u_H
+
+#ifdef LV_HAVE_SSE4_1
+#include <smmintrin.h>
+/*!
+ \brief Computes cosine of input vector and stores results in output vector
+ \param bVector The vector where results will be stored
+ \param aVector The input vector of floats
+ \param num_points Number of points for which cosine is to be computed
+*/
+static inline void volk_32f_cos_32f_u_sse4_1(float* bVector, const float* aVector, unsigned int num_points){
+
+ float* bPtr = bVector;
+ const float* aPtr = aVector;
+
+ unsigned int number = 0;
+ unsigned int quarterPoints = num_points / 4;
+ unsigned int i = 0;
+
+ __m128 aVal, s, m4pi, pio4A, pio4B, cp1, cp2, cp3, cp4, cp5, ffours, ftwos, fones, fzeroes;
+ __m128 sine, cosine, condition1, condition3;
+ __m128i q, r, ones, twos, fours;
+
+ m4pi = _mm_set1_ps(1.273239545);
+ pio4A = _mm_set1_ps(0.78515625);
+ pio4B = _mm_set1_ps(0.241876e-3);
+ ffours = _mm_set1_ps(4.0);
+ ftwos = _mm_set1_ps(2.0);
+ fones = _mm_set1_ps(1.0);
+ fzeroes = _mm_setzero_ps();
+ ones = _mm_set1_epi32(1);
+ twos = _mm_set1_epi32(2);
+ fours = _mm_set1_epi32(4);
+
+ cp1 = _mm_set1_ps(1.0);
+ cp2 = _mm_set1_ps(0.83333333e-1);
+ cp3 = _mm_set1_ps(0.2777778e-2);
+ cp4 = _mm_set1_ps(0.49603e-4);
+ cp5 = _mm_set1_ps(0.551e-6);
+
+ for(;number < quarterPoints; number++){
+ aVal = _mm_loadu_ps(aPtr);
+ s = _mm_sub_ps(aVal, _mm_and_ps(_mm_mul_ps(aVal, ftwos), _mm_cmplt_ps(aVal, fzeroes)));
+ q = _mm_cvtps_epi32(_mm_mul_ps(s, m4pi));
+ r = _mm_add_epi32(q, _mm_and_si128(q, ones));
+
+ s = _mm_sub_ps(s, _mm_mul_ps(_mm_cvtepi32_ps(r), pio4A));
+ s = _mm_sub_ps(s, _mm_mul_ps(_mm_cvtepi32_ps(r), pio4B));
+
+ s = _mm_div_ps(s, _mm_set1_ps(8.0)); // The constant is 2^N, for 3 times argument reduction
+ s = _mm_mul_ps(s, s);
+ // Evaluate Taylor series
+ s = _mm_mul_ps(_mm_add_ps(_mm_mul_ps(_mm_sub_ps(_mm_mul_ps(_mm_add_ps(_mm_mul_ps(_mm_sub_ps(_mm_mul_ps(s, cp5), cp4), s), cp3), s), cp2), s), cp1), s);
+
+ for(i = 0; i < 3; i++){
+ s = _mm_mul_ps(s, _mm_sub_ps(ffours, s));
+ }
+ s = _mm_div_ps(s, ftwos);
+
+ sine = _mm_sqrt_ps(_mm_mul_ps(_mm_sub_ps(ftwos, s), s));
+ cosine = _mm_sub_ps(fones, s);
+
+ condition1 = _mm_cmpneq_ps(_mm_cvtepi32_ps(_mm_and_si128(_mm_add_epi32(q, ones), twos)), fzeroes);
+
+ condition3 = _mm_cmpneq_ps(_mm_cvtepi32_ps(_mm_and_si128(_mm_add_epi32(q, twos), fours)), fzeroes);
+
+ cosine = _mm_add_ps(cosine, _mm_and_ps(_mm_sub_ps(sine, cosine), condition1));
+ cosine = _mm_sub_ps(cosine, _mm_and_ps(_mm_mul_ps(cosine, _mm_set1_ps(2.0f)), condition3));
+ _mm_storeu_ps(bPtr, cosine);
+ aPtr += 4;
+ bPtr += 4;
+ }
+
+ number = quarterPoints * 4;
+ for(;number < num_points; number++){
+ *bPtr++ = cos(*aPtr++);
+ }
+}
+
+#endif /* LV_HAVE_SSE4_1 for unaligned */
+
+#ifdef LV_HAVE_GENERIC
+/*!
+ \brief Computes cosine of input vector and stores results in output vector
+ \param bVector The vector where results will be stored
+ \param aVector The input vector of floats
+ \param num_points Number of points for which cosine is to be computed
+*/
+static inline void volk_32f_cos_32f_generic(float* bVector, const float* aVector, unsigned int num_points){
+ float* bPtr = bVector;
+ const float* aPtr = aVector;
+ unsigned int number = 0;
+
+ for(; number < num_points; number++){
+ *bPtr++ = cos(*aPtr++);
+ }
+
+}
+#endif /* LV_HAVE_GENERIC */
+
+#endif /* INCLUDED_volk_32f_cos_32f_u_H */
diff --git a/volk/kernels/volk/volk_32f_expfast_32f.h b/volk/kernels/volk/volk_32f_expfast_32f.h
new file mode 100644
index 0000000000..b64e45c86e
--- /dev/null
+++ b/volk/kernels/volk/volk_32f_expfast_32f.h
@@ -0,0 +1,216 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
+#include <stdio.h>
+#include <math.h>
+#include <inttypes.h>
+
+#define Mln2 0.6931471805f
+#define A 8388608.0f
+#define B 1065353216.0f
+#define C 60801.0f
+
+
+#ifndef INCLUDED_volk_32f_expfast_32f_a_H
+#define INCLUDED_volk_32f_expfast_32f_a_H
+
+#ifdef LV_HAVE_AVX
+#include <immintrin.h>
+/*!
+ \brief Computes fast exp (max 7% error) of input vector and stores results in output vector
+ \param bVector The vector where results will be stored
+ \param aVector The input vector of floats
+ \param num_points Number of points for which exp is to be computed
+*/
+static inline void volk_32f_expfast_32f_a_avx(float* bVector, const float* aVector, unsigned int num_points){
+
+ float* bPtr = bVector;
+ const float* aPtr = aVector;
+
+ unsigned int number = 0;
+ const unsigned int eighthPoints = num_points / 8;
+
+ __m256 aVal, bVal, a, b;
+ __m256i exp;
+ a = _mm256_set1_ps(A/Mln2);
+ b = _mm256_set1_ps(B-C);
+
+ for(;number < eighthPoints; number++){
+ aVal = _mm256_load_ps(aPtr);
+ exp = _mm256_cvtps_epi32(_mm256_add_ps(_mm256_mul_ps(a,aVal), b));
+ bVal = _mm256_castsi256_ps(exp);
+
+ _mm256_store_ps(bPtr, bVal);
+ aPtr += 8;
+ bPtr += 8;
+ }
+
+ number = eighthPoints * 8;
+ for(;number < num_points; number++){
+ *bPtr++ = expf(*aPtr++);
+ }
+}
+
+#endif /* LV_HAVE_AVX for aligned */
+
+#ifdef LV_HAVE_SSE4_1
+#include <smmintrin.h>
+/*!
+ \brief Computes fast exp (max 7% error) of input vector and stores results in output vector
+ \param bVector The vector where results will be stored
+ \param aVector The input vector of floats
+ \param num_points Number of points for which exp is to be computed
+*/
+static inline void volk_32f_expfast_32f_a_sse4_1(float* bVector, const float* aVector, unsigned int num_points){
+
+ float* bPtr = bVector;
+ const float* aPtr = aVector;
+
+ unsigned int number = 0;
+ const unsigned int quarterPoints = num_points / 4;
+
+ __m128 aVal, bVal, a, b;
+ __m128i exp;
+ a = _mm_set1_ps(A/Mln2);
+ b = _mm_set1_ps(B-C);
+
+ for(;number < quarterPoints; number++){
+ aVal = _mm_load_ps(aPtr);
+ exp = _mm_cvtps_epi32(_mm_add_ps(_mm_mul_ps(a,aVal), b));
+ bVal = _mm_castsi128_ps(exp);
+
+ _mm_store_ps(bPtr, bVal);
+ aPtr += 4;
+ bPtr += 4;
+ }
+
+ number = quarterPoints * 4;
+ for(;number < num_points; number++){
+ *bPtr++ = expf(*aPtr++);
+ }
+}
+
+#endif /* LV_HAVE_SSE4_1 for aligned */
+
+#endif /* INCLUDED_volk_32f_expfast_32f_a_H */
+
+#ifndef INCLUDED_volk_32f_expfast_32f_u_H
+#define INCLUDED_volk_32f_expfast_32f_u_H
+
+#ifdef LV_HAVE_AVX
+#include <immintrin.h>
+/*!
+ \brief Computes fast exp (max 7% error) of input vector and stores results in output vector
+ \param bVector The vector where results will be stored
+ \param aVector The input vector of floats
+ \param num_points Number of points for which exp is to be computed
+*/
+static inline void volk_32f_expfast_32f_u_avx(float* bVector, const float* aVector, unsigned int num_points){
+
+ float* bPtr = bVector;
+ const float* aPtr = aVector;
+
+ unsigned int number = 0;
+ const unsigned int eighthPoints = num_points / 8;
+
+ __m256 aVal, bVal, a, b;
+ __m256i exp;
+ a = _mm256_set1_ps(A/Mln2);
+ b = _mm256_set1_ps(B-C);
+
+ for(;number < eighthPoints; number++){
+ aVal = _mm256_loadu_ps(aPtr);
+ exp = _mm256_cvtps_epi32(_mm256_add_ps(_mm256_mul_ps(a,aVal), b));
+ bVal = _mm256_castsi256_ps(exp);
+
+ _mm256_storeu_ps(bPtr, bVal);
+ aPtr += 8;
+ bPtr += 8;
+ }
+
+ number = eighthPoints * 8;
+ for(;number < num_points; number++){
+ *bPtr++ = expf(*aPtr++);
+ }
+}
+
+#endif /* LV_HAVE_AVX for aligned */
+
+#ifdef LV_HAVE_SSE4_1
+#include <smmintrin.h>
+/*!
+ \brief Computes fast exp (max 7% error) of input vector and stores results in output vector
+ \param bVector The vector where results will be stored
+ \param aVector The input vector of floats
+ \param num_points Number of points for which log is to be computed
+*/
+static inline void volk_32f_expfast_32f_u_sse4_1(float* bVector, const float* aVector, unsigned int num_points){
+
+ float* bPtr = bVector;
+ const float* aPtr = aVector;
+
+ unsigned int number = 0;
+ const unsigned int quarterPoints = num_points / 4;
+
+ __m128 aVal, bVal, a, b;
+ __m128i exp;
+ a = _mm_set1_ps(A/Mln2);
+ b = _mm_set1_ps(B-C);
+
+ for(;number < quarterPoints; number++){
+ aVal = _mm_loadu_ps(aPtr);
+ exp = _mm_cvtps_epi32(_mm_add_ps(_mm_mul_ps(a,aVal), b));
+ bVal = _mm_castsi128_ps(exp);
+
+ _mm_storeu_ps(bPtr, bVal);
+ aPtr += 4;
+ bPtr += 4;
+ }
+
+ number = quarterPoints * 4;
+ for(;number < num_points; number++){
+ *bPtr++ = expf(*aPtr++);
+ }
+}
+
+#endif /* LV_HAVE_SSE4_1 for unaligned */
+
+#ifdef LV_HAVE_GENERIC
+/*!
+ \brief Computes fast exp (max 7% error) of input vector and stores results in output vector
+ \param bVector The vector where results will be stored
+ \param aVector The input vector of floats
+ \param num_points Number of points for which log is to be computed
+*/
+static inline void volk_32f_expfast_32f_generic(float* bVector, const float* aVector, unsigned int num_points){
+ float* bPtr = bVector;
+ const float* aPtr = aVector;
+ unsigned int number = 0;
+
+ for(number = 0; number < num_points; number++){
+ *bPtr++ = expf(*aPtr++);
+ }
+
+}
+#endif /* LV_HAVE_GENERIC */
+
+#endif /* INCLUDED_volk_32f_expfast_32f_u_H */
diff --git a/volk/kernels/volk/volk_32f_index_max_16u.h b/volk/kernels/volk/volk_32f_index_max_16u.h
index dd1aed2459..a5482a6a61 100644
--- a/volk/kernels/volk/volk_32f_index_max_16u.h
+++ b/volk/kernels/volk/volk_32f_index_max_16u.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32f_index_max_16u_a_H
#define INCLUDED_volk_32f_index_max_16u_a_H
diff --git a/volk/kernels/volk/volk_32f_invsqrt_32f.h b/volk/kernels/volk/volk_32f_invsqrt_32f.h
index 8ea12a73c4..21ed125053 100644
--- a/volk/kernels/volk/volk_32f_invsqrt_32f.h
+++ b/volk/kernels/volk/volk_32f_invsqrt_32f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32f_invsqrt_32f_a_H
#define INCLUDED_volk_32f_invsqrt_32f_a_H
@@ -113,7 +135,7 @@ static inline void volk_32f_invsqrt_32f_neon(float* cVector, const float* aVecto
aPtr += 4;
cPtr += 4;
}
-
+
for(number=quarter_points * 4;number < num_points; number++)
*cPtr++ = Q_rsqrt(*aPtr++);
diff --git a/volk/kernels/volk/volk_32f_log2_32f.h b/volk/kernels/volk/volk_32f_log2_32f.h
new file mode 100644
index 0000000000..892eeb1685
--- /dev/null
+++ b/volk/kernels/volk/volk_32f_log2_32f.h
@@ -0,0 +1,332 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
+/*
+ * This kernel was adapted from Jose Fonseca's Fast SSE2 log implementation
+ * http://jrfonseca.blogspot.in/2008/09/fast-sse2-pow-tables-or-polynomials.htm
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the
+ * "Software"), to deal in the Software without restriction, including
+ * without limitation the rights to use, copy, modify, merge, publish,
+ * distribute, sub license, and/or sell copies of the Software, and to
+ * permit persons to whom the Software is furnished to do so, subject to
+ * the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
+ * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT.
+ * IN NO EVENT SHALL TUNGSTEN GRAPHICS AND/OR ITS SUPPLIERS BE LIABLE FOR
+ * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
+ * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
+ * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+ * This is the MIT License (MIT)
+
+*/
+
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <inttypes.h>
+#include <math.h>
+
+#define POLY0(x, c0) _mm_set1_ps(c0)
+#define POLY1(x, c0, c1) _mm_add_ps(_mm_mul_ps(POLY0(x, c1), x), _mm_set1_ps(c0))
+#define POLY2(x, c0, c1, c2) _mm_add_ps(_mm_mul_ps(POLY1(x, c1, c2), x), _mm_set1_ps(c0))
+#define POLY3(x, c0, c1, c2, c3) _mm_add_ps(_mm_mul_ps(POLY2(x, c1, c2, c3), x), _mm_set1_ps(c0))
+#define POLY4(x, c0, c1, c2, c3, c4) _mm_add_ps(_mm_mul_ps(POLY3(x, c1, c2, c3, c4), x), _mm_set1_ps(c0))
+#define POLY5(x, c0, c1, c2, c3, c4, c5) _mm_add_ps(_mm_mul_ps(POLY4(x, c1, c2, c3, c4, c5), x), _mm_set1_ps(c0))
+
+#define LOG_POLY_DEGREE 6
+
+
+#ifndef INCLUDED_volk_32f_log2_32f_a_H
+#define INCLUDED_volk_32f_log2_32f_a_H
+
+#ifdef LV_HAVE_GENERIC
+/*!
+ \brief Computes base 2 log of input vector and stores results in output vector
+ \param bVector The vector where results will be stored
+ \param aVector The input vector of floats
+ \param num_points Number of points for which log is to be computed
+*/
+static inline void volk_32f_log2_32f_generic(float* bVector, const float* aVector, unsigned int num_points){
+ float* bPtr = bVector;
+ const float* aPtr = aVector;
+ unsigned int number = 0;
+
+ for(number = 0; number < num_points; number++){
+ *bPtr++ = log2(*aPtr++);
+ }
+
+}
+#endif /* LV_HAVE_GENERIC */
+
+
+#ifdef LV_HAVE_SSE4_1
+#include <smmintrin.h>
+/*!
+ \brief Computes base 2 log of input vector and stores results in output vector
+ \param bVector The vector where results will be stored
+ \param aVector The input vector of floats
+ \param num_points Number of points for which log is to be computed
+*/
+static inline void volk_32f_log2_32f_a_sse4_1(float* bVector, const float* aVector, unsigned int num_points){
+
+ float* bPtr = bVector;
+ const float* aPtr = aVector;
+
+ unsigned int number = 0;
+ const unsigned int quarterPoints = num_points / 4;
+
+ __m128 aVal, bVal, mantissa, frac, leadingOne;
+ __m128i bias, exp;
+
+ for(;number < quarterPoints; number++){
+
+ aVal = _mm_load_ps(aPtr);
+ bias = _mm_set1_epi32(127);
+ leadingOne = _mm_set1_ps(1.0f);
+ exp = _mm_sub_epi32(_mm_srli_epi32(_mm_and_si128(_mm_castps_si128(aVal), _mm_set1_epi32(0x7f800000)), 23), bias);
+ bVal = _mm_cvtepi32_ps(exp);
+
+ // Now to extract mantissa
+ frac = _mm_or_ps(leadingOne, _mm_and_ps(aVal, _mm_castsi128_ps(_mm_set1_epi32(0x7fffff))));
+
+ #if LOG_POLY_DEGREE == 6
+ mantissa = POLY5( frac, 3.1157899f, -3.3241990f, 2.5988452f, -1.2315303f, 3.1821337e-1f, -3.4436006e-2f);
+ #elif LOG_POLY_DEGREE == 5
+ mantissa = POLY4( frac, 2.8882704548164776201f, -2.52074962577807006663f, 1.48116647521213171641f, -0.465725644288844778798f, 0.0596515482674574969533f);
+ #elif LOG_POLY_DEGREE == 4
+ mantissa = POLY3( frac, 2.61761038894603480148f, -1.75647175389045657003f, 0.688243882994381274313f, -0.107254423828329604454f);
+ #elif LOG_POLY_DEGREE == 3
+ mantissa = POLY2( frac, 2.28330284476918490682f, -1.04913055217340124191f, 0.204446009836232697516f);
+ #else
+ #error
+ #endif
+
+ bVal = _mm_add_ps(bVal, _mm_mul_ps(mantissa, _mm_sub_ps(frac, leadingOne)));
+ _mm_store_ps(bPtr, bVal);
+
+
+ aPtr += 4;
+ bPtr += 4;
+ }
+
+ number = quarterPoints * 4;
+ for(;number < num_points; number++){
+ *bPtr++ = log2(*aPtr++);
+ }
+}
+
+#endif /* LV_HAVE_SSE4_1 for aligned */
+
+
+#ifdef LV_HAVE_NEON
+#include <arm_neon.h>
+
+/* these macros allow us to embed logs in other kernels */
+#define VLOG2Q_NEON_PREAMBLE() \
+ int32x4_t one = vdupq_n_s32(0x000800000); \
+ /* minimax polynomial */ \
+ float32x4_t p0 = vdupq_n_f32(-3.0400402727048585); \
+ float32x4_t p1 = vdupq_n_f32(6.1129631282966113); \
+ float32x4_t p2 = vdupq_n_f32(-5.3419892024633207); \
+ float32x4_t p3 = vdupq_n_f32(3.2865287703753912); \
+ float32x4_t p4 = vdupq_n_f32(-1.2669182593441635); \
+ float32x4_t p5 = vdupq_n_f32(0.2751487703421256); \
+ float32x4_t p6 = vdupq_n_f32(-0.0256910888150985); \
+ int32x4_t exp_mask = vdupq_n_s32(0x7f800000); \
+ int32x4_t sig_mask = vdupq_n_s32(0x007fffff); \
+ int32x4_t exp_bias = vdupq_n_s32(127);
+
+
+#define VLOG2Q_NEON_F32(log2_approx, aval) \
+ int32x4_t exponent_i = vandq_s32(aval, exp_mask); \
+ int32x4_t significand_i = vandq_s32(aval, sig_mask); \
+ exponent_i = vshrq_n_s32(exponent_i, 23); \
+ \
+ /* extract the exponent and significand \
+ we can treat this as fixed point to save ~9% on the \
+ conversion + float add */ \
+ significand_i = vorrq_s32(one, significand_i); \
+ float32x4_t significand_f = vcvtq_n_f32_s32(significand_i,23); \
+ /* debias the exponent and convert to float */ \
+ exponent_i = vsubq_s32(exponent_i, exp_bias); \
+ float32x4_t exponent_f = vcvtq_f32_s32(exponent_i); \
+ \
+ /* put the significand through a polynomial fit of log2(x) [1,2]\
+ add the result to the exponent */ \
+ log2_approx = vaddq_f32(exponent_f, p0); /* p0 */ \
+ float32x4_t tmp1 = vmulq_f32(significand_f, p1); /* p1 * x */ \
+ log2_approx = vaddq_f32(log2_approx, tmp1); \
+ float32x4_t sig_2 = vmulq_f32(significand_f, significand_f); /* x^2 */ \
+ tmp1 = vmulq_f32(sig_2, p2); /* p2 * x^2 */ \
+ log2_approx = vaddq_f32(log2_approx, tmp1); \
+ \
+ float32x4_t sig_3 = vmulq_f32(sig_2, significand_f); /* x^3 */ \
+ tmp1 = vmulq_f32(sig_3, p3); /* p3 * x^3 */ \
+ log2_approx = vaddq_f32(log2_approx, tmp1); \
+ float32x4_t sig_4 = vmulq_f32(sig_2, sig_2); /* x^4 */ \
+ tmp1 = vmulq_f32(sig_4, p4); /* p4 * x^4 */ \
+ log2_approx = vaddq_f32(log2_approx, tmp1); \
+ float32x4_t sig_5 = vmulq_f32(sig_3, sig_2); /* x^5 */ \
+ tmp1 = vmulq_f32(sig_5, p5); /* p5 * x^5 */ \
+ log2_approx = vaddq_f32(log2_approx, tmp1); \
+ float32x4_t sig_6 = vmulq_f32(sig_3, sig_3); /* x^6 */ \
+ tmp1 = vmulq_f32(sig_6, p6); /* p6 * x^6 */ \
+ log2_approx = vaddq_f32(log2_approx, tmp1);
+
+/*!
+ \brief Computes base 2 log of input vector and stores results in output vector
+ \param bVector The vector where results will be stored
+ \param aVector The input vector of floats
+ \param num_points Number of points for which log is to be computed
+*/
+static inline void volk_32f_log2_32f_neon(float* bVector, const float* aVector, unsigned int num_points){
+ float* bPtr = bVector;
+ const float* aPtr = aVector;
+ unsigned int number;
+ const unsigned int quarterPoints = num_points / 4;
+
+ int32x4_t aval;
+ float32x4_t log2_approx;
+
+ VLOG2Q_NEON_PREAMBLE()
+ // lms
+ //p0 = vdupq_n_f32(-1.649132280361871);
+ //p1 = vdupq_n_f32(1.995047138579499);
+ //p2 = vdupq_n_f32(-0.336914839219728);
+
+ // keep in mind a single precision float is represented as
+ // (-1)^sign * 2^exp * 1.significand, so the log2 is
+ // log2(2^exp * sig) = exponent + log2(1 + significand/(1<<23)
+ for(number = 0; number < quarterPoints; ++number){
+ // load float in to an int register without conversion
+ aval = vld1q_s32((int*)aPtr);
+
+ VLOG2Q_NEON_F32(log2_approx, aval)
+
+ vst1q_f32(bPtr, log2_approx);
+
+ aPtr += 4;
+ bPtr += 4;
+ }
+
+ for(number = quarterPoints * 4; number < num_points; number++){
+ *bPtr++ = log2(*aPtr++);
+ }
+}
+
+#endif /* LV_HAVE_NEON */
+
+
+#endif /* INCLUDED_volk_32f_log2_32f_a_H */
+
+#ifndef INCLUDED_volk_32f_log2_32f_u_H
+#define INCLUDED_volk_32f_log2_32f_u_H
+
+
+#ifdef LV_HAVE_GENERIC
+/*!
+ \brief Computes base 2 log of input vector and stores results in output vector
+ \param bVector The vector where results will be stored
+ \param aVector The input vector of floats
+ \param num_points Number of points for which log is to be computed
+*/
+static inline void volk_32f_log2_32f_u_generic(float* bVector, const float* aVector, unsigned int num_points){
+ float* bPtr = bVector;
+ const float* aPtr = aVector;
+ unsigned int number = 0;
+
+ for(number = 0; number < num_points; number++){
+ *bPtr++ = log2(*aPtr++);
+ }
+
+}
+#endif /* LV_HAVE_GENERIC */
+
+
+#ifdef LV_HAVE_SSE4_1
+#include <smmintrin.h>
+/*!
+ \brief Computes base 2 log of input vector and stores results in output vector
+ \param bVector The vector where results will be stored
+ \param aVector The input vector of floats
+ \param num_points Number of points for which log is to be computed
+*/
+static inline void volk_32f_log2_32f_u_sse4_1(float* bVector, const float* aVector, unsigned int num_points){
+
+ float* bPtr = bVector;
+ const float* aPtr = aVector;
+
+ unsigned int number = 0;
+ const unsigned int quarterPoints = num_points / 4;
+
+ __m128 aVal, bVal, mantissa, frac, leadingOne;
+ __m128i bias, exp;
+
+ for(;number < quarterPoints; number++){
+
+ aVal = _mm_loadu_ps(aPtr);
+ bias = _mm_set1_epi32(127);
+ leadingOne = _mm_set1_ps(1.0f);
+ exp = _mm_sub_epi32(_mm_srli_epi32(_mm_and_si128(_mm_castps_si128(aVal), _mm_set1_epi32(0x7f800000)), 23), bias);
+ bVal = _mm_cvtepi32_ps(exp);
+
+ // Now to extract mantissa
+ frac = _mm_or_ps(leadingOne, _mm_and_ps(aVal, _mm_castsi128_ps(_mm_set1_epi32(0x7fffff))));
+
+ #if LOG_POLY_DEGREE == 6
+ mantissa = POLY5( frac, 3.1157899f, -3.3241990f, 2.5988452f, -1.2315303f, 3.1821337e-1f, -3.4436006e-2f);
+ #elif LOG_POLY_DEGREE == 5
+ mantissa = POLY4( frac, 2.8882704548164776201f, -2.52074962577807006663f, 1.48116647521213171641f, -0.465725644288844778798f, 0.0596515482674574969533f);
+ #elif LOG_POLY_DEGREE == 4
+ mantissa = POLY3( frac, 2.61761038894603480148f, -1.75647175389045657003f, 0.688243882994381274313f, -0.107254423828329604454f);
+ #elif LOG_POLY_DEGREE == 3
+ mantissa = POLY2( frac, 2.28330284476918490682f, -1.04913055217340124191f, 0.204446009836232697516f);
+ #else
+ #error
+ #endif
+
+ bVal = _mm_add_ps(bVal, _mm_mul_ps(mantissa, _mm_sub_ps(frac, leadingOne)));
+ _mm_storeu_ps(bPtr, bVal);
+
+
+ aPtr += 4;
+ bPtr += 4;
+ }
+
+ number = quarterPoints * 4;
+ for(;number < num_points; number++){
+ *bPtr++ = log2(*aPtr++);
+ }
+}
+
+#endif /* LV_HAVE_SSE4_1 for unaligned */
+
+#endif /* INCLUDED_volk_32f_log2_32f_u_H */
diff --git a/volk/kernels/volk/volk_32f_s32f_32f_fm_detect_32f.h b/volk/kernels/volk/volk_32f_s32f_32f_fm_detect_32f.h
index 71881c2d5f..f03d80bdd6 100644
--- a/volk/kernels/volk/volk_32f_s32f_32f_fm_detect_32f.h
+++ b/volk/kernels/volk/volk_32f_s32f_32f_fm_detect_32f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32f_s32f_32f_fm_detect_32f_a_H
#define INCLUDED_volk_32f_s32f_32f_fm_detect_32f_a_H
diff --git a/volk/kernels/volk/volk_32f_s32f_calc_spectral_noise_floor_32f.h b/volk/kernels/volk/volk_32f_s32f_calc_spectral_noise_floor_32f.h
index bf05a882d5..9b9f5d3afb 100644
--- a/volk/kernels/volk/volk_32f_s32f_calc_spectral_noise_floor_32f.h
+++ b/volk/kernels/volk/volk_32f_s32f_calc_spectral_noise_floor_32f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32f_s32f_calc_spectral_noise_floor_32f_a_H
#define INCLUDED_volk_32f_s32f_calc_spectral_noise_floor_32f_a_H
diff --git a/volk/kernels/volk/volk_32f_s32f_convert_16i.h b/volk/kernels/volk/volk_32f_s32f_convert_16i.h
index 9fd758655f..c11c13b413 100644
--- a/volk/kernels/volk/volk_32f_s32f_convert_16i.h
+++ b/volk/kernels/volk/volk_32f_s32f_convert_16i.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32f_s32f_convert_16i_u_H
#define INCLUDED_volk_32f_s32f_convert_16i_u_H
@@ -5,6 +27,63 @@
#include <stdio.h>
#include <math.h>
+#ifdef LV_HAVE_AVX
+#include <immintrin.h>
+ /*!
+ \brief Multiplies each point in the input buffer by the scalar value, then converts the result into a 16 bit integer value
+ \param inputVector The floating point input data buffer
+ \param outputVector The 16 bit output data buffer
+ \param scalar The value multiplied against each point in the input buffer
+ \param num_points The number of data values to be converted
+ */
+static inline void volk_32f_s32f_convert_16i_u_avx(int16_t* outputVector, const float* inputVector, const float scalar, unsigned int num_points){
+ unsigned int number = 0;
+
+ const unsigned int eighthPoints = num_points / 8;
+
+ const float* inputVectorPtr = (const float*)inputVector;
+ int16_t* outputVectorPtr = outputVector;
+
+ float min_val = -32768;
+ float max_val = 32767;
+ float r;
+
+ __m256 vScalar = _mm256_set1_ps(scalar);
+ __m256 inputVal, ret;
+ __m256i intInputVal;
+ __m128i intInputVal1, intInputVal2;
+ __m256 vmin_val = _mm256_set1_ps(min_val);
+ __m256 vmax_val = _mm256_set1_ps(max_val);
+
+ for(;number < eighthPoints; number++){
+ inputVal = _mm256_loadu_ps(inputVectorPtr); inputVectorPtr += 8;
+
+ // Scale and clip
+ ret = _mm256_max_ps(_mm256_min_ps(_mm256_mul_ps(inputVal, vScalar), vmax_val), vmin_val);
+
+ intInputVal = _mm256_cvtps_epi32(ret);
+
+ intInputVal1 = _mm256_extractf128_si256(intInputVal, 0);
+ intInputVal2 = _mm256_extractf128_si256(intInputVal, 1);
+
+ intInputVal1 = _mm_packs_epi32(intInputVal1, intInputVal2);
+
+ _mm_storeu_si128((__m128i*)outputVectorPtr, intInputVal1);
+ outputVectorPtr += 8;
+ }
+
+ number = eighthPoints * 8;
+ for(; number < num_points; number++){
+ r = inputVector[number] * scalar;
+ if(r > max_val)
+ r = max_val;
+ else if(r < min_val)
+ r = min_val;
+ outputVector[number] = (int16_t)rintf(r);
+ }
+}
+#endif /* LV_HAVE_AVX */
+
#ifdef LV_HAVE_SSE2
#include <emmintrin.h>
/*!
@@ -158,6 +237,63 @@ static inline void volk_32f_s32f_convert_16i_generic(int16_t* outputVector, cons
#include <stdio.h>
#include <math.h>
+#ifdef LV_HAVE_AVX
+#include <immintrin.h>
+ /*!
+ \brief Multiplies each point in the input buffer by the scalar value, then converts the result into a 16 bit integer value
+ \param inputVector The floating point input data buffer
+ \param outputVector The 16 bit output data buffer
+ \param scalar The value multiplied against each point in the input buffer
+ \param num_points The number of data values to be converted
+ */
+static inline void volk_32f_s32f_convert_16i_a_avx(int16_t* outputVector, const float* inputVector, const float scalar, unsigned int num_points){
+ unsigned int number = 0;
+
+ const unsigned int eighthPoints = num_points / 8;
+
+ const float* inputVectorPtr = (const float*)inputVector;
+ int16_t* outputVectorPtr = outputVector;
+
+ float min_val = -32768;
+ float max_val = 32767;
+ float r;
+
+ __m256 vScalar = _mm256_set1_ps(scalar);
+ __m256 inputVal, ret;
+ __m256i intInputVal;
+ __m128i intInputVal1, intInputVal2;
+ __m256 vmin_val = _mm256_set1_ps(min_val);
+ __m256 vmax_val = _mm256_set1_ps(max_val);
+
+ for(;number < eighthPoints; number++){
+ inputVal = _mm256_load_ps(inputVectorPtr); inputVectorPtr += 8;
+
+ // Scale and clip
+ ret = _mm256_max_ps(_mm256_min_ps(_mm256_mul_ps(inputVal, vScalar), vmax_val), vmin_val);
+
+ intInputVal = _mm256_cvtps_epi32(ret);
+
+ intInputVal1 = _mm256_extractf128_si256(intInputVal, 0);
+ intInputVal2 = _mm256_extractf128_si256(intInputVal, 1);
+
+ intInputVal1 = _mm_packs_epi32(intInputVal1, intInputVal2);
+
+ _mm_store_si128((__m128i*)outputVectorPtr, intInputVal1);
+ outputVectorPtr += 8;
+ }
+
+ number = eighthPoints * 8;
+ for(; number < num_points; number++){
+ r = inputVector[number] * scalar;
+ if(r > max_val)
+ r = max_val;
+ else if(r < min_val)
+ r = min_val;
+ outputVector[number] = (int16_t)rintf(r);
+ }
+}
+#endif /* LV_HAVE_AVX */
+
#ifdef LV_HAVE_SSE2
#include <emmintrin.h>
/*!
diff --git a/volk/kernels/volk/volk_32f_s32f_convert_32i.h b/volk/kernels/volk/volk_32f_s32f_convert_32i.h
index 1a46093ee2..f8e804572f 100644
--- a/volk/kernels/volk/volk_32f_s32f_convert_32i.h
+++ b/volk/kernels/volk/volk_32f_s32f_convert_32i.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32f_s32f_convert_32i_u_H
#define INCLUDED_volk_32f_s32f_convert_32i_u_H
diff --git a/volk/kernels/volk/volk_32f_s32f_convert_8i.h b/volk/kernels/volk/volk_32f_s32f_convert_8i.h
index b451505221..2f0cee98dd 100644
--- a/volk/kernels/volk/volk_32f_s32f_convert_8i.h
+++ b/volk/kernels/volk/volk_32f_s32f_convert_8i.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32f_s32f_convert_8i_u_H
#define INCLUDED_volk_32f_s32f_convert_8i_u_H
diff --git a/volk/kernels/volk/volk_32f_s32f_multiply_32f.h b/volk/kernels/volk/volk_32f_s32f_multiply_32f.h
index 8665d4e90e..ee9e2b5c8b 100644
--- a/volk/kernels/volk/volk_32f_s32f_multiply_32f.h
+++ b/volk/kernels/volk/volk_32f_s32f_multiply_32f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32f_s32f_multiply_32f_u_H
#define INCLUDED_volk_32f_s32f_multiply_32f_u_H
diff --git a/volk/kernels/volk/volk_32f_s32f_normalize.h b/volk/kernels/volk/volk_32f_s32f_normalize.h
index a0bd33c7dc..95a25f53b4 100644
--- a/volk/kernels/volk/volk_32f_s32f_normalize.h
+++ b/volk/kernels/volk/volk_32f_s32f_normalize.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32f_s32f_normalize_a_H
#define INCLUDED_volk_32f_s32f_normalize_a_H
diff --git a/volk/kernels/volk/volk_32f_s32f_power_32f.h b/volk/kernels/volk/volk_32f_s32f_power_32f.h
index 2822444686..b8b441311f 100644
--- a/volk/kernels/volk/volk_32f_s32f_power_32f.h
+++ b/volk/kernels/volk/volk_32f_s32f_power_32f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32f_s32f_power_32f_a_H
#define INCLUDED_volk_32f_s32f_power_32f_a_H
diff --git a/volk/kernels/volk/volk_32f_s32f_stddev_32f.h b/volk/kernels/volk/volk_32f_s32f_stddev_32f.h
index 0622b278a6..590a7d26f1 100644
--- a/volk/kernels/volk/volk_32f_s32f_stddev_32f.h
+++ b/volk/kernels/volk/volk_32f_s32f_stddev_32f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32f_s32f_stddev_32f_a_H
#define INCLUDED_volk_32f_s32f_stddev_32f_a_H
diff --git a/volk/kernels/volk/volk_32f_sin_32f.h b/volk/kernels/volk/volk_32f_sin_32f.h
new file mode 100644
index 0000000000..48ce60c7ed
--- /dev/null
+++ b/volk/kernels/volk/volk_32f_sin_32f.h
@@ -0,0 +1,211 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
+#include <stdio.h>
+#include <math.h>
+#include <inttypes.h>
+
+#ifndef INCLUDED_volk_32f_sin_32f_a_H
+#define INCLUDED_volk_32f_sin_32f_a_H
+
+#ifdef LV_HAVE_SSE4_1
+#include <smmintrin.h>
+/*!
+ \brief Computes sine of input vector and stores results in output vector
+ \param bVector The vector where results will be stored
+ \param aVector The input vector of floats
+ \param num_points Number of points for which sine is to be computed
+*/
+static inline void volk_32f_sin_32f_a_sse4_1(float* bVector, const float* aVector, unsigned int num_points){
+
+ float* bPtr = bVector;
+ const float* aPtr = aVector;
+
+ unsigned int number = 0;
+ unsigned int quarterPoints = num_points / 4;
+ unsigned int i = 0;
+
+ __m128 aVal, s, m4pi, pio4A, pio4B, cp1, cp2, cp3, cp4, cp5, ffours, ftwos, fones, fzeroes;
+ __m128 sine, cosine, condition1, condition2;
+ __m128i q, r, ones, twos, fours;
+
+ m4pi = _mm_set1_ps(1.273239545);
+ pio4A = _mm_set1_ps(0.78515625);
+ pio4B = _mm_set1_ps(0.241876e-3);
+ ffours = _mm_set1_ps(4.0);
+ ftwos = _mm_set1_ps(2.0);
+ fones = _mm_set1_ps(1.0);
+ fzeroes = _mm_setzero_ps();
+ ones = _mm_set1_epi32(1);
+ twos = _mm_set1_epi32(2);
+ fours = _mm_set1_epi32(4);
+
+ cp1 = _mm_set1_ps(1.0);
+ cp2 = _mm_set1_ps(0.83333333e-1);
+ cp3 = _mm_set1_ps(0.2777778e-2);
+ cp4 = _mm_set1_ps(0.49603e-4);
+ cp5 = _mm_set1_ps(0.551e-6);
+
+ for(;number < quarterPoints; number++){
+ aVal = _mm_load_ps(aPtr);
+ s = _mm_sub_ps(aVal, _mm_and_ps(_mm_mul_ps(aVal, ftwos), _mm_cmplt_ps(aVal, fzeroes)));
+ q = _mm_cvtps_epi32(_mm_mul_ps(s, m4pi));
+ r = _mm_add_epi32(q, _mm_and_si128(q, ones));
+
+ s = _mm_sub_ps(s, _mm_mul_ps(_mm_cvtepi32_ps(r), pio4A));
+ s = _mm_sub_ps(s, _mm_mul_ps(_mm_cvtepi32_ps(r), pio4B));
+
+ s = _mm_div_ps(s, _mm_set1_ps(8.0)); // The constant is 2^N, for 3 times argument reduction
+ s = _mm_mul_ps(s, s);
+ // Evaluate Taylor series
+ s = _mm_mul_ps(_mm_add_ps(_mm_mul_ps(_mm_sub_ps(_mm_mul_ps(_mm_add_ps(_mm_mul_ps(_mm_sub_ps(_mm_mul_ps(s, cp5), cp4), s), cp3), s), cp2), s), cp1), s);
+
+ for(i = 0; i < 3; i++) {
+ s = _mm_mul_ps(s, _mm_sub_ps(ffours, s));
+ }
+ s = _mm_div_ps(s, ftwos);
+
+ sine = _mm_sqrt_ps(_mm_mul_ps(_mm_sub_ps(ftwos, s), s));
+ cosine = _mm_sub_ps(fones, s);
+
+ condition1 = _mm_cmpneq_ps(_mm_cvtepi32_ps(_mm_and_si128(_mm_add_epi32(q, ones), twos)), fzeroes);
+ condition2 = _mm_cmpneq_ps(_mm_cmpneq_ps(_mm_cvtepi32_ps(_mm_and_si128(q, fours)), fzeroes), _mm_cmplt_ps(aVal, fzeroes));
+ // Need this condition only for cos
+ //condition3 = _mm_cmpneq_ps(_mm_cvtepi32_ps(_mm_and_si128(_mm_add_epi32(q, twos), fours)), fzeroes);
+
+ sine = _mm_add_ps(sine, _mm_and_ps(_mm_sub_ps(cosine, sine), condition1));
+ sine = _mm_sub_ps(sine, _mm_and_ps(_mm_mul_ps(sine, _mm_set1_ps(2.0f)), condition2));
+ _mm_store_ps(bPtr, sine);
+ aPtr += 4;
+ bPtr += 4;
+ }
+
+ number = quarterPoints * 4;
+ for(;number < num_points; number++){
+ *bPtr++ = sin(*aPtr++);
+ }
+}
+#endif /* LV_HAVE_SSE4_1 for aligned */
+
+#endif /* INCLUDED_volk_32f_sin_32f_a_H */
+
+#ifndef INCLUDED_volk_32f_sin_32f_u_H
+#define INCLUDED_volk_32f_sin_32f_u_H
+
+#ifdef LV_HAVE_SSE4_1
+#include <smmintrin.h>
+/*!
+ \brief Computes sine of input vector and stores results in output vector
+ \param bVector The vector where results will be stored
+ \param aVector The input vector of floats
+ \param num_points Number of points for which sine is to be computed
+*/
+static inline void volk_32f_sin_32f_u_sse4_1(float* bVector, const float* aVector, unsigned int num_points){
+
+ float* bPtr = bVector;
+ const float* aPtr = aVector;
+
+ unsigned int number = 0;
+ unsigned int quarterPoints = num_points / 4;
+ unsigned int i = 0;
+
+ __m128 aVal, s, m4pi, pio4A, pio4B, cp1, cp2, cp3, cp4, cp5, ffours, ftwos, fones, fzeroes;
+ __m128 sine, cosine, condition1, condition2;
+ __m128i q, r, ones, twos, fours;
+
+ m4pi = _mm_set1_ps(1.273239545);
+ pio4A = _mm_set1_ps(0.78515625);
+ pio4B = _mm_set1_ps(0.241876e-3);
+ ffours = _mm_set1_ps(4.0);
+ ftwos = _mm_set1_ps(2.0);
+ fones = _mm_set1_ps(1.0);
+ fzeroes = _mm_setzero_ps();
+ ones = _mm_set1_epi32(1);
+ twos = _mm_set1_epi32(2);
+ fours = _mm_set1_epi32(4);
+
+ cp1 = _mm_set1_ps(1.0);
+ cp2 = _mm_set1_ps(0.83333333e-1);
+ cp3 = _mm_set1_ps(0.2777778e-2);
+ cp4 = _mm_set1_ps(0.49603e-4);
+ cp5 = _mm_set1_ps(0.551e-6);
+
+ for(;number < quarterPoints; number++){
+ aVal = _mm_loadu_ps(aPtr);
+ s = _mm_sub_ps(aVal, _mm_and_ps(_mm_mul_ps(aVal, ftwos), _mm_cmplt_ps(aVal, fzeroes)));
+ q = _mm_cvtps_epi32(_mm_mul_ps(s, m4pi));
+ r = _mm_add_epi32(q, _mm_and_si128(q, ones));
+
+ s = _mm_sub_ps(s, _mm_mul_ps(_mm_cvtepi32_ps(r), pio4A));
+ s = _mm_sub_ps(s, _mm_mul_ps(_mm_cvtepi32_ps(r), pio4B));
+
+ s = _mm_div_ps(s, _mm_set1_ps(8.0)); // The constant is 2^N, for 3 times argument reduction
+ s = _mm_mul_ps(s, s);
+ // Evaluate Taylor series
+ s = _mm_mul_ps(_mm_add_ps(_mm_mul_ps(_mm_sub_ps(_mm_mul_ps(_mm_add_ps(_mm_mul_ps(_mm_sub_ps(_mm_mul_ps(s, cp5), cp4), s), cp3), s), cp2), s), cp1), s);
+
+ for(i = 0; i < 3; i++) {
+ s = _mm_mul_ps(s, _mm_sub_ps(ffours, s));
+ }
+ s = _mm_div_ps(s, ftwos);
+
+ sine = _mm_sqrt_ps(_mm_mul_ps(_mm_sub_ps(ftwos, s), s));
+ cosine = _mm_sub_ps(fones, s);
+
+ condition1 = _mm_cmpneq_ps(_mm_cvtepi32_ps(_mm_and_si128(_mm_add_epi32(q, ones), twos)), fzeroes);
+ condition2 = _mm_cmpneq_ps(_mm_cmpneq_ps(_mm_cvtepi32_ps(_mm_and_si128(q, fours)), fzeroes), _mm_cmplt_ps(aVal, fzeroes));
+
+ sine = _mm_add_ps(sine, _mm_and_ps(_mm_sub_ps(cosine, sine), condition1));
+ sine = _mm_sub_ps(sine, _mm_and_ps(_mm_mul_ps(sine, _mm_set1_ps(2.0f)), condition2));
+ _mm_storeu_ps(bPtr, sine);
+ aPtr += 4;
+ bPtr += 4;
+ }
+
+ number = quarterPoints * 4;
+ for(;number < num_points; number++){
+ *bPtr++ = sin(*aPtr++);
+ }
+}
+
+#endif /* LV_HAVE_SSE4_1 for unaligned */
+
+#ifdef LV_HAVE_GENERIC
+/*!
+ \brief Computes sine of input vector and stores results in output vector
+ \param bVector The vector where results will be stored
+ \param aVector The input vector of floats
+ \param num_points Number of points for which sine is to be computed
+*/
+static inline void volk_32f_sin_32f_generic(float* bVector, const float* aVector, unsigned int num_points){
+ float* bPtr = bVector;
+ const float* aPtr = aVector;
+ unsigned int number = 0;
+
+ for(number = 0; number < num_points; number++){
+ *bPtr++ = sin(*aPtr++);
+ }
+
+}
+#endif /* LV_HAVE_GENERIC */
+
+#endif /* INCLUDED_volk_32f_sin_32f_u_H */
diff --git a/volk/kernels/volk/volk_32f_sqrt_32f.h b/volk/kernels/volk/volk_32f_sqrt_32f.h
index f8f8cbd221..fb70b29125 100644
--- a/volk/kernels/volk/volk_32f_sqrt_32f.h
+++ b/volk/kernels/volk/volk_32f_sqrt_32f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32f_sqrt_32f_a_H
#define INCLUDED_volk_32f_sqrt_32f_a_H
diff --git a/volk/kernels/volk/volk_32f_stddev_and_mean_32f_x2.h b/volk/kernels/volk/volk_32f_stddev_and_mean_32f_x2.h
index 9bded6713d..9d5f709943 100644
--- a/volk/kernels/volk/volk_32f_stddev_and_mean_32f_x2.h
+++ b/volk/kernels/volk/volk_32f_stddev_and_mean_32f_x2.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32f_stddev_and_mean_32f_x2_a_H
#define INCLUDED_volk_32f_stddev_and_mean_32f_x2_a_H
diff --git a/volk/kernels/volk/volk_32f_tan_32f.h b/volk/kernels/volk/volk_32f_tan_32f.h
new file mode 100644
index 0000000000..05e52aa809
--- /dev/null
+++ b/volk/kernels/volk/volk_32f_tan_32f.h
@@ -0,0 +1,220 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
+#include <stdio.h>
+#include <math.h>
+#include <inttypes.h>
+
+#ifndef INCLUDED_volk_32f_tan_32f_a_H
+#define INCLUDED_volk_32f_tan_32f_a_H
+
+#ifdef LV_HAVE_SSE4_1
+#include <smmintrin.h>
+/*!
+ \brief Computes tangent of input vector and stores results in output vector
+ \param bVector The vector where results will be stored
+ \param aVector The input vector of floats
+ \param num_points Number of points for which tangent is to be computed
+*/
+static inline void volk_32f_tan_32f_a_sse4_1(float* bVector, const float* aVector, unsigned int num_points){
+
+ float* bPtr = bVector;
+ const float* aPtr = aVector;
+
+ unsigned int number = 0;
+ unsigned int quarterPoints = num_points / 4;
+ unsigned int i = 0;
+
+ __m128 aVal, s, m4pi, pio4A, pio4B, cp1, cp2, cp3, cp4, cp5, ffours, ftwos, fones, fzeroes;
+ __m128 sine, cosine, tangent, condition1, condition2, condition3;
+ __m128i q, r, ones, twos, fours;
+
+ m4pi = _mm_set1_ps(1.273239545);
+ pio4A = _mm_set1_ps(0.78515625);
+ pio4B = _mm_set1_ps(0.241876e-3);
+ ffours = _mm_set1_ps(4.0);
+ ftwos = _mm_set1_ps(2.0);
+ fones = _mm_set1_ps(1.0);
+ fzeroes = _mm_setzero_ps();
+ ones = _mm_set1_epi32(1);
+ twos = _mm_set1_epi32(2);
+ fours = _mm_set1_epi32(4);
+
+ cp1 = _mm_set1_ps(1.0);
+ cp2 = _mm_set1_ps(0.83333333e-1);
+ cp3 = _mm_set1_ps(0.2777778e-2);
+ cp4 = _mm_set1_ps(0.49603e-4);
+ cp5 = _mm_set1_ps(0.551e-6);
+
+ for(;number < quarterPoints; number++){
+ aVal = _mm_load_ps(aPtr);
+ s = _mm_sub_ps(aVal, _mm_and_ps(_mm_mul_ps(aVal, ftwos), _mm_cmplt_ps(aVal, fzeroes)));
+ q = _mm_cvtps_epi32(_mm_mul_ps(s, m4pi));
+ r = _mm_add_epi32(q, _mm_and_si128(q, ones));
+
+ s = _mm_sub_ps(s, _mm_mul_ps(_mm_cvtepi32_ps(r), pio4A));
+ s = _mm_sub_ps(s, _mm_mul_ps(_mm_cvtepi32_ps(r), pio4B));
+
+ s = _mm_div_ps(s, _mm_set1_ps(8.0)); // The constant is 2^N, for 3 times argument reduction
+ s = _mm_mul_ps(s, s);
+ // Evaluate Taylor series
+ s = _mm_mul_ps(_mm_add_ps(_mm_mul_ps(_mm_sub_ps(_mm_mul_ps(_mm_add_ps(_mm_mul_ps(_mm_sub_ps(_mm_mul_ps(s, cp5), cp4), s), cp3), s), cp2), s), cp1), s);
+
+ for(i = 0; i < 3; i++){
+ s = _mm_mul_ps(s, _mm_sub_ps(ffours, s));
+ }
+ s = _mm_div_ps(s, ftwos);
+
+ sine = _mm_sqrt_ps(_mm_mul_ps(_mm_sub_ps(ftwos, s), s));
+ cosine = _mm_sub_ps(fones, s);
+
+ condition1 = _mm_cmpneq_ps(_mm_cvtepi32_ps(_mm_and_si128(_mm_add_epi32(q, ones), twos)), fzeroes);
+ condition2 = _mm_cmpneq_ps(_mm_cmpneq_ps(_mm_cvtepi32_ps(_mm_and_si128(q, fours)), fzeroes), _mm_cmplt_ps(aVal, fzeroes));
+ condition3 = _mm_cmpneq_ps(_mm_cvtepi32_ps(_mm_and_si128(_mm_add_epi32(q, twos), fours)), fzeroes);
+
+ __m128 temp = cosine;
+ cosine = _mm_add_ps(cosine, _mm_and_ps(_mm_sub_ps(sine, cosine), condition1));
+ sine = _mm_add_ps(sine, _mm_and_ps(_mm_sub_ps(temp, sine), condition1));
+ sine = _mm_sub_ps(sine, _mm_and_ps(_mm_mul_ps(sine, _mm_set1_ps(2.0f)), condition2));
+ cosine = _mm_sub_ps(cosine, _mm_and_ps(_mm_mul_ps(cosine, _mm_set1_ps(2.0f)), condition3));
+ tangent = _mm_div_ps(sine, cosine);
+ _mm_store_ps(bPtr, tangent);
+ aPtr += 4;
+ bPtr += 4;
+ }
+
+ number = quarterPoints * 4;
+ for(;number < num_points; number++){
+ *bPtr++ = tan(*aPtr++);
+ }
+}
+
+#endif /* LV_HAVE_SSE4_1 for aligned */
+
+#endif /* INCLUDED_volk_32f_tan_32f_a_H */
+
+#ifndef INCLUDED_volk_32f_tan_32f_u_H
+#define INCLUDED_volk_32f_tan_32f_u_H
+
+#ifdef LV_HAVE_SSE4_1
+#include <smmintrin.h>
+/*!
+ \brief Computes tangent of input vector and stores results in output vector
+ \param bVector The vector where results will be stored
+ \param aVector The input vector of floats
+ \param num_points Number of points for which tangent is to be computed
+*/
+static inline void volk_32f_tan_32f_u_sse4_1(float* bVector, const float* aVector, unsigned int num_points){
+
+ float* bPtr = bVector;
+ const float* aPtr = aVector;
+
+ unsigned int number = 0;
+ unsigned int quarterPoints = num_points / 4;
+ unsigned int i = 0;
+
+ __m128 aVal, s, m4pi, pio4A, pio4B, cp1, cp2, cp3, cp4, cp5, ffours, ftwos, fones, fzeroes;
+ __m128 sine, cosine, tangent, condition1, condition2, condition3;
+ __m128i q, r, ones, twos, fours;
+
+ m4pi = _mm_set1_ps(1.273239545);
+ pio4A = _mm_set1_ps(0.78515625);
+ pio4B = _mm_set1_ps(0.241876e-3);
+ ffours = _mm_set1_ps(4.0);
+ ftwos = _mm_set1_ps(2.0);
+ fones = _mm_set1_ps(1.0);
+ fzeroes = _mm_setzero_ps();
+ ones = _mm_set1_epi32(1);
+ twos = _mm_set1_epi32(2);
+ fours = _mm_set1_epi32(4);
+
+ cp1 = _mm_set1_ps(1.0);
+ cp2 = _mm_set1_ps(0.83333333e-1);
+ cp3 = _mm_set1_ps(0.2777778e-2);
+ cp4 = _mm_set1_ps(0.49603e-4);
+ cp5 = _mm_set1_ps(0.551e-6);
+
+ for(;number < quarterPoints; number++){
+ aVal = _mm_loadu_ps(aPtr);
+ s = _mm_sub_ps(aVal, _mm_and_ps(_mm_mul_ps(aVal, ftwos), _mm_cmplt_ps(aVal, fzeroes)));
+ q = _mm_cvtps_epi32(_mm_mul_ps(s, m4pi));
+ r = _mm_add_epi32(q, _mm_and_si128(q, ones));
+
+ s = _mm_sub_ps(s, _mm_mul_ps(_mm_cvtepi32_ps(r), pio4A));
+ s = _mm_sub_ps(s, _mm_mul_ps(_mm_cvtepi32_ps(r), pio4B));
+
+ s = _mm_div_ps(s, _mm_set1_ps(8.0)); // The constant is 2^N, for 3 times argument reduction
+ s = _mm_mul_ps(s, s);
+ // Evaluate Taylor series
+ s = _mm_mul_ps(_mm_add_ps(_mm_mul_ps(_mm_sub_ps(_mm_mul_ps(_mm_add_ps(_mm_mul_ps(_mm_sub_ps(_mm_mul_ps(s, cp5), cp4), s), cp3), s), cp2), s), cp1), s);
+
+ for(i = 0; i < 3; i++){
+ s = _mm_mul_ps(s, _mm_sub_ps(ffours, s));
+ }
+ s = _mm_div_ps(s, ftwos);
+
+ sine = _mm_sqrt_ps(_mm_mul_ps(_mm_sub_ps(ftwos, s), s));
+ cosine = _mm_sub_ps(fones, s);
+
+ condition1 = _mm_cmpneq_ps(_mm_cvtepi32_ps(_mm_and_si128(_mm_add_epi32(q, ones), twos)), fzeroes);
+ condition2 = _mm_cmpneq_ps(_mm_cmpneq_ps(_mm_cvtepi32_ps(_mm_and_si128(q, fours)), fzeroes), _mm_cmplt_ps(aVal, fzeroes));
+ condition3 = _mm_cmpneq_ps(_mm_cvtepi32_ps(_mm_and_si128(_mm_add_epi32(q, twos), fours)), fzeroes);
+
+ __m128 temp = cosine;
+ cosine = _mm_add_ps(cosine, _mm_and_ps(_mm_sub_ps(sine, cosine), condition1));
+ sine = _mm_add_ps(sine, _mm_and_ps(_mm_sub_ps(temp, sine), condition1));
+ sine = _mm_sub_ps(sine, _mm_and_ps(_mm_mul_ps(sine, _mm_set1_ps(2.0f)), condition2));
+ cosine = _mm_sub_ps(cosine, _mm_and_ps(_mm_mul_ps(cosine, _mm_set1_ps(2.0f)), condition3));
+ tangent = _mm_div_ps(sine, cosine);
+ _mm_storeu_ps(bPtr, tangent);
+ aPtr += 4;
+ bPtr += 4;
+ }
+
+ number = quarterPoints * 4;
+ for(;number < num_points; number++){
+ *bPtr++ = tan(*aPtr++);
+ }
+}
+
+#endif /* LV_HAVE_SSE4_1 for unaligned */
+
+#ifdef LV_HAVE_GENERIC
+/*!
+ \brief Computes tangent of input vector and stores results in output vector
+ \param bVector The vector where results will be stored
+ \param aVector The input vector of floats
+ \param num_points Number of points for which tangent is to be computed
+*/
+static inline void volk_32f_tan_32f_generic(float* bVector, const float* aVector, unsigned int num_points){
+ float* bPtr = bVector;
+ const float* aPtr = aVector;
+ unsigned int number = 0;
+
+ for(; number < num_points; number++){
+ *bPtr++ = tan(*aPtr++);
+ }
+
+}
+#endif /* LV_HAVE_GENERIC */
+
+#endif /* INCLUDED_volk_32f_tan_32f_u_H */
diff --git a/volk/kernels/volk/volk_32f_tanh_32f.h b/volk/kernels/volk/volk_32f_tanh_32f.h
new file mode 100644
index 0000000000..cdb685f811
--- /dev/null
+++ b/volk/kernels/volk/volk_32f_tanh_32f.h
@@ -0,0 +1,318 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
+#ifndef INCLUDED_volk_32f_tanh_32f_a_H
+#define INCLUDED_volk_32f_tanh_32f_a_H
+
+#include <inttypes.h>
+#include <stdio.h>
+#include <math.h>
+#include <string.h>
+
+#ifdef LV_HAVE_GENERIC
+/*!
+\brief Calculates tanh(x)
+\param cVector The vector where the results will be stored
+\param aVector Input vector
+\param num_points The number of values to calulate
+*/
+static inline void volk_32f_tanh_32f_generic(float* cVector, const float* aVector,
+ unsigned int num_points)
+{
+ unsigned int number = 0;
+ float* cPtr = cVector;
+ const float* aPtr = aVector;
+ for(; number < num_points; number++) {
+ *cPtr++ = tanh(*aPtr++);
+ }
+}
+
+#endif /* LV_HAVE_GENERIC */
+
+
+#ifdef LV_HAVE_GENERIC
+/*!
+\brief Calculates tanh(x) using a series approximation, good to within 1e-6 of the actual tanh.
+\param cVector The vector where the results will be stored
+\param aVector Input vector
+\param num_points The number of values to calulate
+*/
+static inline void volk_32f_tanh_32f_series(float* cVector, const float* aVector,
+ unsigned int num_points)
+{
+ unsigned int number = 0;
+ float* cPtr = cVector;
+ const float* aPtr = aVector;
+ for(; number < num_points; number++) {
+ if(*aPtr > 4.97)
+ *cPtr++ = 1;
+ else if(*aPtr <= -4.97)
+ *cPtr++ = -1;
+ else {
+ float x2 = (*aPtr) * (*aPtr);
+ float a = (*aPtr) * (135135.0f + x2 * (17325.0f + x2 * (378.0f + x2)));
+ float b = 135135.0f + x2 * (62370.0f + x2 * (3150.0f + x2 * 28.0f));
+ *cPtr++ = a / b;
+ aPtr++;
+ }
+ }
+}
+
+#endif /* LV_HAVE_GENERIC */
+
+
+
+#ifdef LV_HAVE_SSE
+#include <xmmintrin.h>
+/*!
+\brief Calculates tanh(x) using a series approximation, good to within 1e-6 of the actual tanh.
+\param cVector The vector where the results will be stored
+\param aVector Input vector
+\param num_points The number of values to calulate
+*/
+static inline void volk_32f_tanh_32f_a_sse(float* cVector, const float* aVector,
+ unsigned int num_points)
+{
+ unsigned int number = 0;
+ const unsigned int quarterPoints = num_points / 4;
+
+ float* cPtr = cVector;
+ const float* aPtr = aVector;
+
+ __m128 aVal, cVal, x2, a, b;
+ __m128 const1, const2, const3, const4, const5, const6;
+ const1 = _mm_set_ps1(135135.0f);
+ const2 = _mm_set_ps1(17325.0f);
+ const3 = _mm_set_ps1(378.0f);
+ const4 = _mm_set_ps1(62370.0f);
+ const5 = _mm_set_ps1(3150.0f);
+ const6 = _mm_set_ps1(28.0f);
+ for(;number < quarterPoints; number++){
+
+ aVal = _mm_load_ps(aPtr);
+ x2 = _mm_mul_ps(aVal, aVal);
+ a = _mm_mul_ps(aVal, _mm_add_ps(const1, _mm_mul_ps(x2, _mm_add_ps(const2, _mm_mul_ps(x2, _mm_add_ps(const3, x2))))));
+ b = _mm_add_ps(const1, _mm_mul_ps(x2, _mm_add_ps(const4, _mm_mul_ps(x2, _mm_add_ps(const5, _mm_mul_ps(x2, const6))))));
+
+ cVal = _mm_div_ps(a, b);
+
+ _mm_store_ps(cPtr, cVal); // Store the results back into the C container
+
+ aPtr += 4;
+ cPtr += 4;
+ }
+
+ number = quarterPoints * 4;
+ for(;number < num_points; number++) {
+ if(*aPtr > 4.97)
+ *cPtr++ = 1;
+ else if(*aPtr <= -4.97)
+ *cPtr++ = -1;
+ else {
+ float x2 = (*aPtr) * (*aPtr);
+ float a = (*aPtr) * (135135.0f + x2 * (17325.0f + x2 * (378.0f + x2)));
+ float b = 135135.0f + x2 * (62370.0f + x2 * (3150.0f + x2 * 28.0f));
+ *cPtr++ = a / b;
+ aPtr++;
+ }
+ }
+}
+#endif /* LV_HAVE_SSE */
+
+
+#ifdef LV_HAVE_AVX
+#include <immintrin.h>
+/*!
+\brief Calculates tanh(x) using a series approximation, good to within 1e-6 of the actual tanh.
+\param cVector The vector where the results will be stored
+\param aVector Input vector
+\param num_points The number of values to calulate
+*/
+static inline void volk_32f_tanh_32f_a_avx(float* cVector, const float* aVector,
+ unsigned int num_points)
+{
+ unsigned int number = 0;
+ const unsigned int eighthPoints = num_points / 8;
+
+ float* cPtr = cVector;
+ const float* aPtr = aVector;
+
+ __m256 aVal, cVal, x2, a, b;
+ __m256 const1, const2, const3, const4, const5, const6;
+ const1 = _mm256_set1_ps(135135.0f);
+ const2 = _mm256_set1_ps(17325.0f);
+ const3 = _mm256_set1_ps(378.0f);
+ const4 = _mm256_set1_ps(62370.0f);
+ const5 = _mm256_set1_ps(3150.0f);
+ const6 = _mm256_set1_ps(28.0f);
+ for(;number < eighthPoints; number++){
+
+ aVal = _mm256_load_ps(aPtr);
+ x2 = _mm256_mul_ps(aVal, aVal);
+ a = _mm256_mul_ps(aVal, _mm256_add_ps(const1, _mm256_mul_ps(x2, _mm256_add_ps(const2, _mm256_mul_ps(x2, _mm256_add_ps(const3, x2))))));
+ b = _mm256_add_ps(const1, _mm256_mul_ps(x2, _mm256_add_ps(const4, _mm256_mul_ps(x2, _mm256_add_ps(const5, _mm256_mul_ps(x2, const6))))));
+
+ cVal = _mm256_div_ps(a, b);
+
+ _mm256_store_ps(cPtr, cVal); // Store the results back into the C container
+
+ aPtr += 8;
+ cPtr += 8;
+ }
+
+ number = eighthPoints * 8;
+ for(;number < num_points; number++) {
+ if(*aPtr > 4.97)
+ *cPtr++ = 1;
+ else if(*aPtr <= -4.97)
+ *cPtr++ = -1;
+ else {
+ float x2 = (*aPtr) * (*aPtr);
+ float a = (*aPtr) * (135135.0f + x2 * (17325.0f + x2 * (378.0f + x2)));
+ float b = 135135.0f + x2 * (62370.0f + x2 * (3150.0f + x2 * 28.0f));
+ *cPtr++ = a / b;
+ aPtr++;
+ }
+ }
+}
+#endif /* LV_HAVE_AVX */
+
+
+
+
+#ifdef LV_HAVE_SSE
+#include <xmmintrin.h>
+/*!
+\brief Calculates tanh(x) using a series approximation, good to within 1e-6 of the actual tanh.
+\param cVector The vector where the results will be stored
+\param aVector Input vector
+\param num_points The number of values to calulate
+*/
+static inline void volk_32f_tanh_32f_u_sse(float* cVector, const float* aVector,
+ unsigned int num_points)
+{
+ unsigned int number = 0;
+ const unsigned int quarterPoints = num_points / 4;
+
+ float* cPtr = cVector;
+ const float* aPtr = aVector;
+
+ __m128 aVal, cVal, x2, a, b;
+ __m128 const1, const2, const3, const4, const5, const6;
+ const1 = _mm_set_ps1(135135.0f);
+ const2 = _mm_set_ps1(17325.0f);
+ const3 = _mm_set_ps1(378.0f);
+ const4 = _mm_set_ps1(62370.0f);
+ const5 = _mm_set_ps1(3150.0f);
+ const6 = _mm_set_ps1(28.0f);
+ for(;number < quarterPoints; number++){
+
+ aVal = _mm_loadu_ps(aPtr);
+ x2 = _mm_mul_ps(aVal, aVal);
+ a = _mm_mul_ps(aVal, _mm_add_ps(const1, _mm_mul_ps(x2, _mm_add_ps(const2, _mm_mul_ps(x2, _mm_add_ps(const3, x2))))));
+ b = _mm_add_ps(const1, _mm_mul_ps(x2, _mm_add_ps(const4, _mm_mul_ps(x2, _mm_add_ps(const5, _mm_mul_ps(x2, const6))))));
+
+ cVal = _mm_div_ps(a, b);
+
+ _mm_storeu_ps(cPtr, cVal); // Store the results back into the C container
+
+ aPtr += 4;
+ cPtr += 4;
+ }
+
+ number = quarterPoints * 4;
+ for(;number < num_points; number++) {
+ if(*aPtr > 4.97)
+ *cPtr++ = 1;
+ else if(*aPtr <= -4.97)
+ *cPtr++ = -1;
+ else {
+ float x2 = (*aPtr) * (*aPtr);
+ float a = (*aPtr) * (135135.0f + x2 * (17325.0f + x2 * (378.0f + x2)));
+ float b = 135135.0f + x2 * (62370.0f + x2 * (3150.0f + x2 * 28.0f));
+ *cPtr++ = a / b;
+ aPtr++;
+ }
+ }
+}
+#endif /* LV_HAVE_SSE */
+
+
+
+#ifdef LV_HAVE_AVX
+#include <immintrin.h>
+/*!
+\brief Calculates tanh(x) using a series approximation, good to within 1e-6 of the actual tanh.
+\param cVector The vector where the results will be stored
+\param aVector Input vector
+\param num_points The number of values to calulate
+*/
+static inline void volk_32f_tanh_32f_u_avx(float* cVector, const float* aVector,
+ unsigned int num_points)
+{
+ unsigned int number = 0;
+ const unsigned int eighthPoints = num_points / 8;
+
+ float* cPtr = cVector;
+ const float* aPtr = aVector;
+
+ __m256 aVal, cVal, x2, a, b;
+ __m256 const1, const2, const3, const4, const5, const6;
+ const1 = _mm256_set1_ps(135135.0f);
+ const2 = _mm256_set1_ps(17325.0f);
+ const3 = _mm256_set1_ps(378.0f);
+ const4 = _mm256_set1_ps(62370.0f);
+ const5 = _mm256_set1_ps(3150.0f);
+ const6 = _mm256_set1_ps(28.0f);
+ for(;number < eighthPoints; number++){
+
+ aVal = _mm256_loadu_ps(aPtr);
+ x2 = _mm256_mul_ps(aVal, aVal);
+ a = _mm256_mul_ps(aVal, _mm256_add_ps(const1, _mm256_mul_ps(x2, _mm256_add_ps(const2, _mm256_mul_ps(x2, _mm256_add_ps(const3, x2))))));
+ b = _mm256_add_ps(const1, _mm256_mul_ps(x2, _mm256_add_ps(const4, _mm256_mul_ps(x2, _mm256_add_ps(const5, _mm256_mul_ps(x2, const6))))));
+
+ cVal = _mm256_div_ps(a, b);
+
+ _mm256_storeu_ps(cPtr, cVal); // Store the results back into the C container
+
+ aPtr += 8;
+ cPtr += 8;
+ }
+
+ number = eighthPoints * 8;
+ for(;number < num_points; number++) {
+ if(*aPtr > 4.97)
+ *cPtr++ = 1;
+ else if(*aPtr <= -4.97)
+ *cPtr++ = -1;
+ else {
+ float x2 = (*aPtr) * (*aPtr);
+ float a = (*aPtr) * (135135.0f + x2 * (17325.0f + x2 * (378.0f + x2)));
+ float b = 135135.0f + x2 * (62370.0f + x2 * (3150.0f + x2 * 28.0f));
+ *cPtr++ = a / b;
+ aPtr++;
+ }
+ }
+}
+#endif /* LV_HAVE_AVX */
+
+#endif /* INCLUDED_volk_32f_tanh_32f_a_H */
diff --git a/volk/kernels/volk/volk_32f_x2_add_32f.h b/volk/kernels/volk/volk_32f_x2_add_32f.h
index a9a1d4fbf0..0c66b271ae 100644
--- a/volk/kernels/volk/volk_32f_x2_add_32f.h
+++ b/volk/kernels/volk/volk_32f_x2_add_32f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32f_x2_add_32f_u_H
#define INCLUDED_volk_32f_x2_add_32f_u_H
@@ -136,7 +158,7 @@ static inline void volk_32f_x2_add_32f_u_neon(float* cVector, const float* aVect
// vector add
cVal = vaddq_f32(aVal, bVal);
// Store the results back into the C container
- vst1q_f32(cPtr,cVal);
+ vst1q_f32(cPtr,cVal);
aPtr += 4; // q uses quadwords, 4 floats per vadd
bPtr += 4;
diff --git a/volk/kernels/volk/volk_32f_x2_divide_32f.h b/volk/kernels/volk/volk_32f_x2_divide_32f.h
index d5a7c7d7c0..bbb5cbc9c4 100644
--- a/volk/kernels/volk/volk_32f_x2_divide_32f.h
+++ b/volk/kernels/volk/volk_32f_x2_divide_32f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32f_x2_divide_32f_a_H
#define INCLUDED_volk_32f_x2_divide_32f_a_H
diff --git a/volk/kernels/volk/volk_32f_x2_dot_prod_16i.h b/volk/kernels/volk/volk_32f_x2_dot_prod_16i.h
index b637f17777..6e38e33dc7 100644
--- a/volk/kernels/volk/volk_32f_x2_dot_prod_16i.h
+++ b/volk/kernels/volk/volk_32f_x2_dot_prod_16i.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32f_x2_dot_prod_16i_H
#define INCLUDED_volk_32f_x2_dot_prod_16i_H
diff --git a/volk/kernels/volk/volk_32f_x2_dot_prod_32f.h b/volk/kernels/volk/volk_32f_x2_dot_prod_32f.h
index ac6f56976b..a98802b4b5 100644
--- a/volk/kernels/volk/volk_32f_x2_dot_prod_32f.h
+++ b/volk/kernels/volk/volk_32f_x2_dot_prod_32f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32f_x2_dot_prod_32f_u_H
#define INCLUDED_volk_32f_x2_dot_prod_32f_u_H
diff --git a/volk/kernels/volk/volk_32f_x2_interleave_32fc.h b/volk/kernels/volk/volk_32f_x2_interleave_32fc.h
index 3591b24d69..bf7e9250cf 100644
--- a/volk/kernels/volk/volk_32f_x2_interleave_32fc.h
+++ b/volk/kernels/volk/volk_32f_x2_interleave_32fc.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32f_x2_interleave_32fc_a_H
#define INCLUDED_volk_32f_x2_interleave_32fc_a_H
@@ -70,7 +92,7 @@ static inline void volk_32f_x2_interleave_32fc_neon(lv_32fc_t* complexVector, co
iBuffer += 4;
qBuffer += 4;
complexVectorPtr += 8;
- }
+ }
for(number=quarter_points * 4; number < num_points; ++number) {
*complexVectorPtr++ = *iBuffer++;
diff --git a/volk/kernels/volk/volk_32f_x2_max_32f.h b/volk/kernels/volk/volk_32f_x2_max_32f.h
index a1403fba18..7e4e2afc8e 100644
--- a/volk/kernels/volk/volk_32f_x2_max_32f.h
+++ b/volk/kernels/volk/volk_32f_x2_max_32f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32f_x2_max_32f_a_H
#define INCLUDED_volk_32f_x2_max_32f_a_H
@@ -60,7 +82,7 @@ static inline void volk_32f_x2_max_32f_neon(float* cVector, const float* aVector
const float* aPtr = aVector;
const float* bPtr= bVector;
unsigned int number = 0;
-
+
float32x4_t a_vec, b_vec, c_vec;
for(number = 0; number < quarter_points; number++){
a_vec = vld1q_f32(aPtr);
diff --git a/volk/kernels/volk/volk_32f_x2_min_32f.h b/volk/kernels/volk/volk_32f_x2_min_32f.h
index f7598d6354..b67c7b8471 100644
--- a/volk/kernels/volk/volk_32f_x2_min_32f.h
+++ b/volk/kernels/volk/volk_32f_x2_min_32f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32f_x2_min_32f_a_H
#define INCLUDED_volk_32f_x2_min_32f_a_H
diff --git a/volk/kernels/volk/volk_32f_x2_multiply_32f.h b/volk/kernels/volk/volk_32f_x2_multiply_32f.h
index 00b31859d6..b05421573d 100644
--- a/volk/kernels/volk/volk_32f_x2_multiply_32f.h
+++ b/volk/kernels/volk/volk_32f_x2_multiply_32f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32f_x2_multiply_32f_u_H
#define INCLUDED_volk_32f_x2_multiply_32f_u_H
diff --git a/volk/kernels/volk/volk_32f_x2_pow_32f.h b/volk/kernels/volk/volk_32f_x2_pow_32f.h
new file mode 100644
index 0000000000..431c4c7021
--- /dev/null
+++ b/volk/kernels/volk/volk_32f_x2_pow_32f.h
@@ -0,0 +1,298 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <inttypes.h>
+#include <math.h>
+
+#define POLY0(x, c0) _mm_set1_ps(c0)
+#define POLY1(x, c0, c1) _mm_add_ps(_mm_mul_ps(POLY0(x, c1), x), _mm_set1_ps(c0))
+#define POLY2(x, c0, c1, c2) _mm_add_ps(_mm_mul_ps(POLY1(x, c1, c2), x), _mm_set1_ps(c0))
+#define POLY3(x, c0, c1, c2, c3) _mm_add_ps(_mm_mul_ps(POLY2(x, c1, c2, c3), x), _mm_set1_ps(c0))
+#define POLY4(x, c0, c1, c2, c3, c4) _mm_add_ps(_mm_mul_ps(POLY3(x, c1, c2, c3, c4), x), _mm_set1_ps(c0))
+#define POLY5(x, c0, c1, c2, c3, c4, c5) _mm_add_ps(_mm_mul_ps(POLY4(x, c1, c2, c3, c4, c5), x), _mm_set1_ps(c0))
+
+#define LOG_POLY_DEGREE 3
+
+#ifndef INCLUDED_volk_32f_x2_pow_32f_a_H
+#define INCLUDED_volk_32f_x2_pow_32f_a_H
+
+#ifdef LV_HAVE_SSE4_1
+#include <smmintrin.h>
+/*!
+ \brief Computes pow(x,y) by using exp and log
+ \param cVector The vector where results will be stored
+ \param aVector The input vector of bases
+ \param bVector The input vector of indices
+ \param num_points Number of points for which pow is to be computed
+*/
+static inline void volk_32f_x2_pow_32f_a_sse4_1(float* cVector, const float* bVector, const float* aVector, unsigned int num_points){
+
+ float* cPtr = cVector;
+ const float* bPtr = bVector;
+ const float* aPtr = aVector;
+
+ unsigned int number = 0;
+ const unsigned int quarterPoints = num_points / 4;
+
+ __m128 aVal, bVal, cVal, logarithm, mantissa, frac, leadingOne;
+ __m128 tmp, fx, mask, pow2n, z, y;
+ __m128 one, exp_hi, exp_lo, ln2, log2EF, half, exp_C1, exp_C2;
+ __m128 exp_p0, exp_p1, exp_p2, exp_p3, exp_p4, exp_p5;
+ __m128i bias, exp, emm0, pi32_0x7f;
+
+ one = _mm_set1_ps(1.0);
+ exp_hi = _mm_set1_ps(88.3762626647949);
+ exp_lo = _mm_set1_ps(-88.3762626647949);
+ ln2 = _mm_set1_ps(0.6931471805);
+ log2EF = _mm_set1_ps(1.44269504088896341);
+ half = _mm_set1_ps(0.5);
+ exp_C1 = _mm_set1_ps(0.693359375);
+ exp_C2 = _mm_set1_ps(-2.12194440e-4);
+ pi32_0x7f = _mm_set1_epi32(0x7f);
+
+ exp_p0 = _mm_set1_ps(1.9875691500e-4);
+ exp_p1 = _mm_set1_ps(1.3981999507e-3);
+ exp_p2 = _mm_set1_ps(8.3334519073e-3);
+ exp_p3 = _mm_set1_ps(4.1665795894e-2);
+ exp_p4 = _mm_set1_ps(1.6666665459e-1);
+ exp_p5 = _mm_set1_ps(5.0000001201e-1);
+
+ for(;number < quarterPoints; number++){
+ // First compute the logarithm
+ aVal = _mm_load_ps(aPtr);
+ bias = _mm_set1_epi32(127);
+ leadingOne = _mm_set1_ps(1.0f);
+ exp = _mm_sub_epi32(_mm_srli_epi32(_mm_and_si128(_mm_castps_si128(aVal), _mm_set1_epi32(0x7f800000)), 23), bias);
+ logarithm = _mm_cvtepi32_ps(exp);
+
+ frac = _mm_or_ps(leadingOne, _mm_and_ps(aVal, _mm_castsi128_ps(_mm_set1_epi32(0x7fffff))));
+
+ #if LOG_POLY_DEGREE == 6
+ mantissa = POLY5( frac, 3.1157899f, -3.3241990f, 2.5988452f, -1.2315303f, 3.1821337e-1f, -3.4436006e-2f);
+ #elif LOG_POLY_DEGREE == 5
+ mantissa = POLY4( frac, 2.8882704548164776201f, -2.52074962577807006663f, 1.48116647521213171641f, -0.465725644288844778798f, 0.0596515482674574969533f);
+ #elif LOG_POLY_DEGREE == 4
+ mantissa = POLY3( frac, 2.61761038894603480148f, -1.75647175389045657003f, 0.688243882994381274313f, -0.107254423828329604454f);
+ #elif LOG_POLY_DEGREE == 3
+ mantissa = POLY2( frac, 2.28330284476918490682f, -1.04913055217340124191f, 0.204446009836232697516f);
+ #else
+ #error
+ #endif
+
+ logarithm = _mm_add_ps(logarithm, _mm_mul_ps(mantissa, _mm_sub_ps(frac, leadingOne)));
+ logarithm = _mm_mul_ps(logarithm, ln2);
+
+
+ // Now calculate b*lna
+ bVal = _mm_load_ps(bPtr);
+ bVal = _mm_mul_ps(bVal, logarithm);
+
+ // Now compute exp(b*lna)
+ tmp = _mm_setzero_ps();
+
+ bVal = _mm_max_ps(_mm_min_ps(bVal, exp_hi), exp_lo);
+
+ fx = _mm_add_ps(_mm_mul_ps(bVal, log2EF), half);
+
+ emm0 = _mm_cvttps_epi32(fx);
+ tmp = _mm_cvtepi32_ps(emm0);
+
+ mask = _mm_and_ps(_mm_cmpgt_ps(tmp, fx), one);
+ fx = _mm_sub_ps(tmp, mask);
+
+ tmp = _mm_mul_ps(fx, exp_C1);
+ z = _mm_mul_ps(fx, exp_C2);
+ bVal = _mm_sub_ps(_mm_sub_ps(bVal, tmp), z);
+ z = _mm_mul_ps(bVal, bVal);
+
+ y = _mm_mul_ps(_mm_add_ps(_mm_mul_ps(exp_p0, bVal), exp_p1), bVal);
+ y = _mm_add_ps(_mm_mul_ps(_mm_add_ps(y, exp_p2), bVal), exp_p3);
+ y = _mm_mul_ps(_mm_add_ps(_mm_mul_ps(y, bVal), exp_p4), bVal);
+ y = _mm_add_ps(_mm_mul_ps(_mm_add_ps(y, exp_p5), z), bVal);
+ y = _mm_add_ps(y, one);
+
+ emm0 = _mm_slli_epi32(_mm_add_epi32(_mm_cvttps_epi32(fx), pi32_0x7f), 23);
+
+ pow2n = _mm_castsi128_ps(emm0);
+ cVal = _mm_mul_ps(y, pow2n);
+
+ _mm_store_ps(cPtr, cVal);
+
+ aPtr += 4;
+ bPtr += 4;
+ cPtr += 4;
+ }
+
+ number = quarterPoints * 4;
+ for(;number < num_points; number++){
+ *cPtr++ = pow(*aPtr++, *bPtr++);
+ }
+}
+
+#endif /* LV_HAVE_SSE4_1 for aligned */
+
+#endif /* INCLUDED_volk_32f_x2_pow_32f_a_H */
+
+#ifndef INCLUDED_volk_32f_x2_pow_32f_u_H
+#define INCLUDED_volk_32f_x2_pow_32f_u_H
+
+#ifdef LV_HAVE_GENERIC
+/*!
+ \brief Computes pow(x,y) by using exp and log
+ \param cVector The vector where results will be stored
+ \param aVector The input vector of bases
+ \param bVector The input vector of indices
+ \param num_points Number of points for which pow is to be computed
+*/
+static inline void volk_32f_x2_pow_32f_generic(float* cVector, const float* bVector, const float* aVector, unsigned int num_points){
+ float* cPtr = cVector;
+ const float* bPtr = bVector;
+ const float* aPtr = aVector;
+ unsigned int number = 0;
+
+ for(number = 0; number < num_points; number++){
+ *cPtr++ = pow(*aPtr++, *bPtr++);
+ }
+
+}
+#endif /* LV_HAVE_GENERIC */
+
+
+#ifdef LV_HAVE_SSE4_1
+#include <smmintrin.h>
+/*!
+ \brief Computes pow(x,y) by using exp and log
+ \param cVector The vector where results will be stored
+ \param aVector The input vector of bases
+ \param bVector The input vector of indices
+ \param num_points Number of points for which pow is to be computed
+*/
+static inline void volk_32f_x2_pow_32f_u_sse4_1(float* cVector, const float* bVector, const float* aVector, unsigned int num_points){
+
+ float* cPtr = cVector;
+ const float* bPtr = bVector;
+ const float* aPtr = aVector;
+
+ unsigned int number = 0;
+ const unsigned int quarterPoints = num_points / 4;
+
+ __m128 aVal, bVal, cVal, logarithm, mantissa, frac, leadingOne;
+ __m128 tmp, fx, mask, pow2n, z, y;
+ __m128 one, exp_hi, exp_lo, ln2, log2EF, half, exp_C1, exp_C2;
+ __m128 exp_p0, exp_p1, exp_p2, exp_p3, exp_p4, exp_p5;
+ __m128i bias, exp, emm0, pi32_0x7f;
+
+ one = _mm_set1_ps(1.0);
+ exp_hi = _mm_set1_ps(88.3762626647949);
+ exp_lo = _mm_set1_ps(-88.3762626647949);
+ ln2 = _mm_set1_ps(0.6931471805);
+ log2EF = _mm_set1_ps(1.44269504088896341);
+ half = _mm_set1_ps(0.5);
+ exp_C1 = _mm_set1_ps(0.693359375);
+ exp_C2 = _mm_set1_ps(-2.12194440e-4);
+ pi32_0x7f = _mm_set1_epi32(0x7f);
+
+ exp_p0 = _mm_set1_ps(1.9875691500e-4);
+ exp_p1 = _mm_set1_ps(1.3981999507e-3);
+ exp_p2 = _mm_set1_ps(8.3334519073e-3);
+ exp_p3 = _mm_set1_ps(4.1665795894e-2);
+ exp_p4 = _mm_set1_ps(1.6666665459e-1);
+ exp_p5 = _mm_set1_ps(5.0000001201e-1);
+
+ for(;number < quarterPoints; number++){
+
+ // First compute the logarithm
+ aVal = _mm_loadu_ps(aPtr);
+ bias = _mm_set1_epi32(127);
+ leadingOne = _mm_set1_ps(1.0f);
+ exp = _mm_sub_epi32(_mm_srli_epi32(_mm_and_si128(_mm_castps_si128(aVal), _mm_set1_epi32(0x7f800000)), 23), bias);
+ logarithm = _mm_cvtepi32_ps(exp);
+
+ frac = _mm_or_ps(leadingOne, _mm_and_ps(aVal, _mm_castsi128_ps(_mm_set1_epi32(0x7fffff))));
+
+ #if LOG_POLY_DEGREE == 6
+ mantissa = POLY5( frac, 3.1157899f, -3.3241990f, 2.5988452f, -1.2315303f, 3.1821337e-1f, -3.4436006e-2f);
+ #elif LOG_POLY_DEGREE == 5
+ mantissa = POLY4( frac, 2.8882704548164776201f, -2.52074962577807006663f, 1.48116647521213171641f, -0.465725644288844778798f, 0.0596515482674574969533f);
+ #elif LOG_POLY_DEGREE == 4
+ mantissa = POLY3( frac, 2.61761038894603480148f, -1.75647175389045657003f, 0.688243882994381274313f, -0.107254423828329604454f);
+ #elif LOG_POLY_DEGREE == 3
+ mantissa = POLY2( frac, 2.28330284476918490682f, -1.04913055217340124191f, 0.204446009836232697516f);
+ #else
+ #error
+ #endif
+
+ logarithm = _mm_add_ps(logarithm, _mm_mul_ps(mantissa, _mm_sub_ps(frac, leadingOne)));
+ logarithm = _mm_mul_ps(logarithm, ln2);
+
+
+ // Now calculate b*lna
+ bVal = _mm_loadu_ps(bPtr);
+ bVal = _mm_mul_ps(bVal, logarithm);
+
+ // Now compute exp(b*lna)
+ tmp = _mm_setzero_ps();
+
+ bVal = _mm_max_ps(_mm_min_ps(bVal, exp_hi), exp_lo);
+
+ fx = _mm_add_ps(_mm_mul_ps(bVal, log2EF), half);
+
+ emm0 = _mm_cvttps_epi32(fx);
+ tmp = _mm_cvtepi32_ps(emm0);
+
+ mask = _mm_and_ps(_mm_cmpgt_ps(tmp, fx), one);
+ fx = _mm_sub_ps(tmp, mask);
+
+ tmp = _mm_mul_ps(fx, exp_C1);
+ z = _mm_mul_ps(fx, exp_C2);
+ bVal = _mm_sub_ps(_mm_sub_ps(bVal, tmp), z);
+ z = _mm_mul_ps(bVal, bVal);
+
+ y = _mm_mul_ps(_mm_add_ps(_mm_mul_ps(exp_p0, bVal), exp_p1), bVal);
+ y = _mm_add_ps(_mm_mul_ps(_mm_add_ps(y, exp_p2), bVal), exp_p3);
+ y = _mm_mul_ps(_mm_add_ps(_mm_mul_ps(y, bVal), exp_p4), bVal);
+ y = _mm_add_ps(_mm_mul_ps(_mm_add_ps(y, exp_p5), z), bVal);
+ y = _mm_add_ps(y, one);
+
+ emm0 = _mm_slli_epi32(_mm_add_epi32(_mm_cvttps_epi32(fx), pi32_0x7f), 23);
+
+ pow2n = _mm_castsi128_ps(emm0);
+ cVal = _mm_mul_ps(y, pow2n);
+
+ _mm_storeu_ps(cPtr, cVal);
+
+ aPtr += 4;
+ bPtr += 4;
+ cPtr += 4;
+ }
+
+ number = quarterPoints * 4;
+ for(;number < num_points; number++){
+ *cPtr++ = pow(*aPtr++, *bPtr++);
+ }
+}
+
+#endif /* LV_HAVE_SSE4_1 for unaligned */
+
+#endif /* INCLUDED_volk_32f_x2_log2_32f_u_H */
diff --git a/volk/kernels/volk/volk_32f_x2_s32f_interleave_16ic.h b/volk/kernels/volk/volk_32f_x2_s32f_interleave_16ic.h
index ce7b91a318..5d7eca8f4c 100644
--- a/volk/kernels/volk/volk_32f_x2_s32f_interleave_16ic.h
+++ b/volk/kernels/volk/volk_32f_x2_s32f_interleave_16ic.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32f_x2_s32f_interleave_16ic_a_H
#define INCLUDED_volk_32f_x2_s32f_interleave_16ic_a_H
diff --git a/volk/kernels/volk/volk_32f_x2_subtract_32f.h b/volk/kernels/volk/volk_32f_x2_subtract_32f.h
index c725ef8d4f..a3aa8e0d6b 100644
--- a/volk/kernels/volk/volk_32f_x2_subtract_32f.h
+++ b/volk/kernels/volk/volk_32f_x2_subtract_32f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32f_x2_subtract_32f_a_H
#define INCLUDED_volk_32f_x2_subtract_32f_a_H
diff --git a/volk/kernels/volk/volk_32f_x3_sum_of_poly_32f.h b/volk/kernels/volk/volk_32f_x3_sum_of_poly_32f.h
index 0d3c2168c7..cc40c67a66 100644
--- a/volk/kernels/volk/volk_32f_x3_sum_of_poly_32f.h
+++ b/volk/kernels/volk/volk_32f_x3_sum_of_poly_32f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32f_x3_sum_of_poly_32f_a_H
#define INCLUDED_volk_32f_x3_sum_of_poly_32f_a_H
diff --git a/volk/kernels/volk/volk_32fc_32f_dot_prod_32fc.h b/volk/kernels/volk/volk_32fc_32f_dot_prod_32fc.h
index 6d0c8480e0..0c3ef0d8b7 100644
--- a/volk/kernels/volk/volk_32fc_32f_dot_prod_32fc.h
+++ b/volk/kernels/volk/volk_32fc_32f_dot_prod_32fc.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32fc_32f_dot_prod_32fc_a_H
#define INCLUDED_volk_32fc_32f_dot_prod_32fc_a_H
@@ -296,7 +318,7 @@ static inline void volk_32fc_32f_dot_prod_32fc_neon_unroll ( lv_32fc_t* __restri
const float* inputPtr = (float*)input;
const float* tapsPtr = taps;
float zero[4] = {0.0f, 0.0f, 0.0f, 0.0f };
- float accVector_real[4];
+ float accVector_real[4];
float accVector_imag[4];
float32x4x2_t inputVector0, inputVector1;
@@ -305,14 +327,14 @@ static inline void volk_32fc_32f_dot_prod_32fc_neon_unroll ( lv_32fc_t* __restri
float32x4_t tmp_real1, tmp_imag1;
float32x4_t real_accumulator0, imag_accumulator0;
float32x4_t real_accumulator1, imag_accumulator1;
-
+
// zero out accumulators
// take a *float, return float32x4_t
real_accumulator0 = vld1q_f32( zero );
imag_accumulator0 = vld1q_f32( zero );
real_accumulator1 = vld1q_f32( zero );
imag_accumulator1 = vld1q_f32( zero );
-
+
for(number=0 ;number < quarterPoints; number++){
// load doublewords and duplicate in to second lane
tapsVector0 = vld1q_f32(tapsPtr );
@@ -338,7 +360,7 @@ static inline void volk_32fc_32f_dot_prod_32fc_neon_unroll ( lv_32fc_t* __restri
tapsPtr += 8;
inputPtr += 16;
}
-
+
real_accumulator0 = vaddq_f32( real_accumulator0, real_accumulator1);
imag_accumulator0 = vaddq_f32( imag_accumulator0, imag_accumulator1);
// void vst1q_f32( float32_t * ptr, float32x4_t val);
diff --git a/volk/kernels/volk/volk_32fc_32f_multiply_32fc.h b/volk/kernels/volk/volk_32fc_32f_multiply_32fc.h
index 21b71998c2..0f5a141107 100644
--- a/volk/kernels/volk/volk_32fc_32f_multiply_32fc.h
+++ b/volk/kernels/volk/volk_32fc_32f_multiply_32fc.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32fc_32f_multiply_32fc_a_H
#define INCLUDED_volk_32fc_32f_multiply_32fc_a_H
diff --git a/volk/kernels/volk/volk_32fc_conjugate_32fc.h b/volk/kernels/volk/volk_32fc_conjugate_32fc.h
index 0f74b01816..49d8a0fbda 100644
--- a/volk/kernels/volk/volk_32fc_conjugate_32fc.h
+++ b/volk/kernels/volk/volk_32fc_conjugate_32fc.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32fc_conjugate_32fc_u_H
#define INCLUDED_volk_32fc_conjugate_32fc_u_H
@@ -6,6 +28,44 @@
#include <volk/volk_complex.h>
#include <float.h>
+#ifdef LV_HAVE_AVX
+#include <immintrin.h>
+ /*!
+ \brief Takes the conjugate of a complex vector.
+ \param cVector The vector where the results will be stored
+ \param aVector Vector to be conjugated
+ \param num_points The number of complex values in aVector to be conjugated and stored into cVector
+ */
+static inline void volk_32fc_conjugate_32fc_u_avx(lv_32fc_t* cVector, const lv_32fc_t* aVector, unsigned int num_points){
+ unsigned int number = 0;
+ const unsigned int quarterPoints = num_points / 4;
+
+ __m256 x;
+ lv_32fc_t* c = cVector;
+ const lv_32fc_t* a = aVector;
+
+ __m256 conjugator = _mm256_setr_ps(0, -0.f, 0, -0.f, 0, -0.f, 0, -0.f);
+
+ for(;number < quarterPoints; number++){
+
+ x = _mm256_loadu_ps((float*)a); // Load the complex data as ar,ai,br,bi
+
+ x = _mm256_xor_ps(x, conjugator); // conjugate register
+
+ _mm256_storeu_ps((float*)c,x); // Store the results back into the C container
+
+ a += 4;
+ c += 4;
+ }
+
+ number = quarterPoints * 4;
+
+ for(;number < num_points; number++) {
+ *c++ = lv_conj(*a++);
+ }
+}
+#endif /* LV_HAVE_AVX */
+
#ifdef LV_HAVE_SSE3
#include <pmmintrin.h>
/*!
@@ -70,6 +130,44 @@ static inline void volk_32fc_conjugate_32fc_generic(lv_32fc_t* cVector, const lv
#include <volk/volk_complex.h>
#include <float.h>
+#ifdef LV_HAVE_AVX
+#include <immintrin.h>
+ /*!
+ \brief Takes the conjugate of a complex vector.
+ \param cVector The vector where the results will be stored
+ \param aVector Vector to be conjugated
+ \param num_points The number of complex values in aVector to be conjugated and stored into cVector
+ */
+static inline void volk_32fc_conjugate_32fc_a_avx(lv_32fc_t* cVector, const lv_32fc_t* aVector, unsigned int num_points){
+ unsigned int number = 0;
+ const unsigned int quarterPoints = num_points / 4;
+
+ __m256 x;
+ lv_32fc_t* c = cVector;
+ const lv_32fc_t* a = aVector;
+
+ __m256 conjugator = _mm256_setr_ps(0, -0.f, 0, -0.f, 0, -0.f, 0, -0.f);
+
+ for(;number < quarterPoints; number++){
+
+ x = _mm256_load_ps((float*)a); // Load the complex data as ar,ai,br,bi
+
+ x = _mm256_xor_ps(x, conjugator); // conjugate register
+
+ _mm256_store_ps((float*)c,x); // Store the results back into the C container
+
+ a += 4;
+ c += 4;
+ }
+
+ number = quarterPoints * 4;
+
+ for(;number < num_points; number++) {
+ *c++ = lv_conj(*a++);
+ }
+}
+#endif /* LV_HAVE_AVX */
+
#ifdef LV_HAVE_SSE3
#include <pmmintrin.h>
/*!
diff --git a/volk/kernels/volk/volk_32fc_deinterleave_32f_x2.h b/volk/kernels/volk/volk_32fc_deinterleave_32f_x2.h
index 0d33ed7e28..aed7f097b8 100644
--- a/volk/kernels/volk/volk_32fc_deinterleave_32f_x2.h
+++ b/volk/kernels/volk/volk_32fc_deinterleave_32f_x2.h
@@ -1,9 +1,80 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32fc_deinterleave_32f_x2_a_H
#define INCLUDED_volk_32fc_deinterleave_32f_x2_a_H
#include <inttypes.h>
#include <stdio.h>
+#ifdef LV_HAVE_AVX
+#include <immintrin.h>
+/*!
+ \brief Deinterleaves the complex vector into I & Q vector data
+ \param complexVector The complex input vector
+ \param iBuffer The I buffer output data
+ \param qBuffer The Q buffer output data
+ \param num_points The number of complex data values to be deinterleaved
+*/
+static inline void volk_32fc_deinterleave_32f_x2_a_avx(float* iBuffer, float* qBuffer, const lv_32fc_t* complexVector, unsigned int num_points){
+ const float* complexVectorPtr = (float*)complexVector;
+ float* iBufferPtr = iBuffer;
+ float* qBufferPtr = qBuffer;
+
+ unsigned int number = 0;
+ // Mask for real and imaginary parts
+ const unsigned int eighthPoints = num_points / 8;
+ __m256 cplxValue1, cplxValue2, complex1, complex2, iValue, qValue;
+ for(;number < eighthPoints; number++){
+
+ cplxValue1 = _mm256_load_ps(complexVectorPtr);
+ complexVectorPtr += 8;
+
+ cplxValue2 = _mm256_load_ps(complexVectorPtr);
+ complexVectorPtr += 8;
+
+ complex1 = _mm256_permute2f128_ps(cplxValue1, cplxValue2, 0x20);
+ complex2 = _mm256_permute2f128_ps(cplxValue1, cplxValue2, 0x31);
+
+ // Arrange in i1i2i3i4 format
+ iValue = _mm256_shuffle_ps(complex1, complex2, 0x88);
+ // Arrange in q1q2q3q4 format
+ qValue = _mm256_shuffle_ps(complex1, complex2, 0xdd);
+
+ _mm256_store_ps(iBufferPtr, iValue);
+ _mm256_store_ps(qBufferPtr, qValue);
+
+ iBufferPtr += 8;
+ qBufferPtr += 8;
+ }
+
+ number = eighthPoints * 8;
+ for(; number < num_points; number++){
+ *iBufferPtr++ = *complexVectorPtr++;
+ *qBufferPtr++ = *complexVectorPtr++;
+ }
+}
+#endif /* LV_HAVE_AVX */
+
#ifdef LV_HAVE_SSE
#include <xmmintrin.h>
/*!
@@ -49,6 +120,39 @@ static inline void volk_32fc_deinterleave_32f_x2_a_sse(float* iBuffer, float* qB
}
#endif /* LV_HAVE_SSE */
+#ifdef LV_HAVE_NEON
+#include <arm_neon.h>
+/*!
+ \brief Deinterleaves the complex vector into I & Q vector data
+ \param complexVector The complex input vector
+ \param iBuffer The I buffer output data
+ \param qBuffer The Q buffer output data
+ \param num_points The number of complex data values to be deinterleaved
+*/
+static inline void volk_32fc_deinterleave_32f_x2_neon(float* iBuffer, float* qBuffer, const lv_32fc_t* complexVector, unsigned int num_points){
+ unsigned int number = 0;
+ unsigned int quarter_points = num_points / 4;
+ const float* complexVectorPtr = (float*)complexVector;
+ float* iBufferPtr = iBuffer;
+ float* qBufferPtr = qBuffer;
+ float32x4x2_t complexInput;
+
+ for(number = 0; number < quarter_points; number++){
+ complexInput = vld2q_f32(complexVectorPtr);
+ vst1q_f32( iBufferPtr, complexInput.val[0] );
+ vst1q_f32( qBufferPtr, complexInput.val[1] );
+ complexVectorPtr += 8;
+ iBufferPtr += 4;
+ qBufferPtr += 4;
+ }
+
+ for(number = quarter_points*4; number < num_points; number++){
+ *iBufferPtr++ = *complexVectorPtr++;
+ *qBufferPtr++ = *complexVectorPtr++;
+ }
+}
+#endif /* LV_HAVE_NEON */
+
#ifdef LV_HAVE_GENERIC
/*!
\brief Deinterleaves the complex vector into I & Q vector data
diff --git a/volk/kernels/volk/volk_32fc_deinterleave_64f_x2.h b/volk/kernels/volk/volk_32fc_deinterleave_64f_x2.h
index 4a4c5509bd..9b872e05e2 100644
--- a/volk/kernels/volk/volk_32fc_deinterleave_64f_x2.h
+++ b/volk/kernels/volk/volk_32fc_deinterleave_64f_x2.h
@@ -1,9 +1,82 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32fc_deinterleave_64f_x2_u_H
#define INCLUDED_volk_32fc_deinterleave_64f_x2_u_H
#include <inttypes.h>
#include <stdio.h>
+#ifdef LV_HAVE_AVX
+#include <immintrin.h>
+/*!
+ \brief Deinterleaves the lv_32fc_t vector into double I & Q vector data
+ \param complexVector The complex input vector
+ \param iBuffer The I buffer output data
+ \param qBuffer The Q buffer output data
+ \param num_points The number of complex data values to be deinterleaved
+*/
+static inline void volk_32fc_deinterleave_64f_x2_u_avx(double* iBuffer, double* qBuffer, const lv_32fc_t* complexVector, unsigned int num_points){
+ unsigned int number = 0;
+
+ const float* complexVectorPtr = (float*)complexVector;
+ double* iBufferPtr = iBuffer;
+ double* qBufferPtr = qBuffer;
+
+ const unsigned int quarterPoints = num_points / 4;
+ __m256 cplxValue;
+ __m128 complexH, complexL, fVal;
+ __m256d dVal;
+
+ for(;number < quarterPoints; number++){
+
+ cplxValue = _mm256_loadu_ps(complexVectorPtr);
+ complexVectorPtr += 8;
+
+ complexH = _mm256_extractf128_ps(cplxValue, 1);
+ complexL = _mm256_extractf128_ps(cplxValue, 0);
+
+ // Arrange in i1i2i1i2 format
+ fVal = _mm_shuffle_ps(complexL, complexH, _MM_SHUFFLE(2,0,2,0));
+ dVal = _mm256_cvtps_pd(fVal);
+ _mm256_storeu_pd(iBufferPtr, dVal);
+
+ // Arrange in q1q2q1q2 format
+ fVal = _mm_shuffle_ps(complexL, complexH, _MM_SHUFFLE(3,1,3,1));
+ dVal = _mm256_cvtps_pd(fVal);
+ _mm256_storeu_pd(qBufferPtr, dVal);
+
+ iBufferPtr += 4;
+ qBufferPtr += 4;
+ }
+
+ number = quarterPoints * 4;
+ for(; number < num_points; number++){
+ *iBufferPtr++ = *complexVectorPtr++;
+ *qBufferPtr++ = *complexVectorPtr++;
+ }
+}
+#endif /* LV_HAVE_AVX */
+
#ifdef LV_HAVE_SSE2
#include <emmintrin.h>
/*!
@@ -82,6 +155,57 @@ static inline void volk_32fc_deinterleave_64f_x2_generic(double* iBuffer, double
#include <inttypes.h>
#include <stdio.h>
+#ifdef LV_HAVE_AVX
+#include <immintrin.h>
+/*!
+ \brief Deinterleaves the lv_32fc_t vector into double I & Q vector data
+ \param complexVector The complex input vector
+ \param iBuffer The I buffer output data
+ \param qBuffer The Q buffer output data
+ \param num_points The number of complex data values to be deinterleaved
+*/
+static inline void volk_32fc_deinterleave_64f_x2_a_avx(double* iBuffer, double* qBuffer, const lv_32fc_t* complexVector, unsigned int num_points){
+ unsigned int number = 0;
+
+ const float* complexVectorPtr = (float*)complexVector;
+ double* iBufferPtr = iBuffer;
+ double* qBufferPtr = qBuffer;
+
+ const unsigned int quarterPoints = num_points / 4;
+ __m256 cplxValue;
+ __m128 complexH, complexL, fVal;
+ __m256d dVal;
+
+ for(;number < quarterPoints; number++){
+
+ cplxValue = _mm256_load_ps(complexVectorPtr);
+ complexVectorPtr += 8;
+
+ complexH = _mm256_extractf128_ps(cplxValue, 1);
+ complexL = _mm256_extractf128_ps(cplxValue, 0);
+
+ // Arrange in i1i2i1i2 format
+ fVal = _mm_shuffle_ps(complexL, complexH, _MM_SHUFFLE(2,0,2,0));
+ dVal = _mm256_cvtps_pd(fVal);
+ _mm256_store_pd(iBufferPtr, dVal);
+
+ // Arrange in q1q2q1q2 format
+ fVal = _mm_shuffle_ps(complexL, complexH, _MM_SHUFFLE(3,1,3,1));
+ dVal = _mm256_cvtps_pd(fVal);
+ _mm256_store_pd(qBufferPtr, dVal);
+
+ iBufferPtr += 4;
+ qBufferPtr += 4;
+ }
+
+ number = quarterPoints * 4;
+ for(; number < num_points; number++){
+ *iBufferPtr++ = *complexVectorPtr++;
+ *qBufferPtr++ = *complexVectorPtr++;
+ }
+}
+#endif /* LV_HAVE_AVX */
+
#ifdef LV_HAVE_SSE2
#include <emmintrin.h>
/*!
diff --git a/volk/kernels/volk/volk_32fc_deinterleave_imag_32f.h b/volk/kernels/volk/volk_32fc_deinterleave_imag_32f.h
index b1968296f5..a590c83d7a 100644
--- a/volk/kernels/volk/volk_32fc_deinterleave_imag_32f.h
+++ b/volk/kernels/volk/volk_32fc_deinterleave_imag_32f.h
@@ -1,9 +1,73 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32fc_deinterleave_imag_32f_a_H
#define INCLUDED_volk_32fc_deinterleave_imag_32f_a_H
#include <inttypes.h>
#include <stdio.h>
+#ifdef LV_HAVE_AVX
+#include <immintrin.h>
+/*!
+ \brief Deinterleaves the complex vector into Q vector data
+ \param complexVector The complex input vector
+ \param qBuffer The Q buffer output data
+ \param num_points The number of complex data values to be deinterleaved
+*/
+static inline void volk_32fc_deinterleave_imag_32f_a_avx(float* qBuffer, const lv_32fc_t* complexVector, unsigned int num_points){
+ unsigned int number = 0;
+ const unsigned int eighthPoints = num_points / 8;
+ const float* complexVectorPtr = (const float*)complexVector;
+ float* qBufferPtr = qBuffer;
+
+ __m256 cplxValue1, cplxValue2, complex1, complex2, qValue;
+ for(;number < eighthPoints; number++){
+
+ cplxValue1 = _mm256_load_ps(complexVectorPtr);
+ complexVectorPtr += 8;
+
+ cplxValue2 = _mm256_load_ps(complexVectorPtr);
+ complexVectorPtr += 8;
+
+ complex1 = _mm256_permute2f128_ps(cplxValue1, cplxValue2, 0x20);
+ complex2 = _mm256_permute2f128_ps(cplxValue1, cplxValue2, 0x31);
+
+ // Arrange in q1q2q3q4 format
+ qValue = _mm256_shuffle_ps(complex1, complex2, 0xdd);
+
+ _mm256_store_ps(qBufferPtr, qValue);
+
+ qBufferPtr += 8;
+ }
+
+ number = eighthPoints * 8;
+ for(; number < num_points; number++){
+ complexVectorPtr++;
+ *qBufferPtr++ = *complexVectorPtr++;
+ }
+}
+#endif /* LV_HAVE_AVX */
+
#ifdef LV_HAVE_SSE
#include <xmmintrin.h>
/*!
@@ -44,6 +108,35 @@ static inline void volk_32fc_deinterleave_imag_32f_a_sse(float* qBuffer, const l
}
#endif /* LV_HAVE_SSE */
+#ifdef LV_HAVE_NEON
+#include <arm_neon.h>
+/*!
+ \brief Deinterleaves the complex vector into Q vector data
+ \param complexVector The complex input vector
+ \param qBuffer The Q buffer output data
+ \param num_points The number of complex data values to be deinterleaved
+*/
+static inline void volk_32fc_deinterleave_imag_32f_neon(float* qBuffer, const lv_32fc_t* complexVector, unsigned int num_points){
+ unsigned int number = 0;
+ unsigned int quarter_points = num_points / 4;
+ const float* complexVectorPtr = (float*)complexVector;
+ float* qBufferPtr = qBuffer;
+ float32x4x2_t complexInput;
+
+ for(number = 0; number < quarter_points; number++){
+ complexInput = vld2q_f32(complexVectorPtr);
+ vst1q_f32( qBufferPtr, complexInput.val[1] );
+ complexVectorPtr += 8;
+ qBufferPtr += 4;
+ }
+
+ for(number = quarter_points*4; number < num_points; number++){
+ complexVectorPtr++;
+ *qBufferPtr++ = *complexVectorPtr++;
+ }
+}
+#endif /* LV_HAVE_NEON */
+
#ifdef LV_HAVE_GENERIC
/*!
\brief Deinterleaves the complex vector into Q vector data
diff --git a/volk/kernels/volk/volk_32fc_deinterleave_real_32f.h b/volk/kernels/volk/volk_32fc_deinterleave_real_32f.h
index 3d57598135..c0e8d8fb34 100644
--- a/volk/kernels/volk/volk_32fc_deinterleave_real_32f.h
+++ b/volk/kernels/volk/volk_32fc_deinterleave_real_32f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32fc_deinterleave_real_32f_a_H
#define INCLUDED_volk_32fc_deinterleave_real_32f_a_H
@@ -62,7 +84,33 @@ static inline void volk_32fc_deinterleave_real_32f_generic(float* iBuffer, const
}
#endif /* LV_HAVE_GENERIC */
+#ifdef LV_HAVE_NEON
+#include <arm_neon.h>
+/*!
+ \brief Deinterleaves the complex vector into I vector data
+ \param complexVector The complex input vector
+ \param iBuffer The I buffer output data
+ \param num_points The number of complex data values to be deinterleaved
+*/
+static inline void volk_32fc_deinterleave_real_32f_neon(float* iBuffer, const lv_32fc_t* complexVector, unsigned int num_points){
+ unsigned int number = 0;
+ unsigned int quarter_points = num_points / 4;
+ const float* complexVectorPtr = (float*)complexVector;
+ float* iBufferPtr = iBuffer;
+ float32x4x2_t complexInput;
+ for(number = 0; number < quarter_points; number++){
+ complexInput = vld2q_f32(complexVectorPtr);
+ vst1q_f32( iBufferPtr, complexInput.val[0] );
+ complexVectorPtr += 8;
+ iBufferPtr += 4;
+ }
+ for(number = quarter_points*4; number < num_points; number++){
+ *iBufferPtr++ = *complexVectorPtr++;
+ complexVectorPtr++;
+ }
+}
+#endif /* LV_HAVE_NEON */
#endif /* INCLUDED_volk_32fc_deinterleave_real_32f_a_H */
diff --git a/volk/kernels/volk/volk_32fc_deinterleave_real_64f.h b/volk/kernels/volk/volk_32fc_deinterleave_real_64f.h
index 1fa66e8add..eb1df386a8 100644
--- a/volk/kernels/volk/volk_32fc_deinterleave_real_64f.h
+++ b/volk/kernels/volk/volk_32fc_deinterleave_real_64f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32fc_deinterleave_real_64f_a_H
#define INCLUDED_volk_32fc_deinterleave_real_64f_a_H
diff --git a/volk/kernels/volk/volk_32fc_index_max_16u.h b/volk/kernels/volk/volk_32fc_index_max_16u.h
index c8d7212401..bc47f7983b 100644
--- a/volk/kernels/volk/volk_32fc_index_max_16u.h
+++ b/volk/kernels/volk/volk_32fc_index_max_16u.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32fc_index_max_16u_a_H
#define INCLUDED_volk_32fc_index_max_16u_a_H
diff --git a/volk/kernels/volk/volk_32fc_magnitude_32f.h b/volk/kernels/volk/volk_32fc_magnitude_32f.h
index b6da7f3630..d057b70f5e 100644
--- a/volk/kernels/volk/volk_32fc_magnitude_32f.h
+++ b/volk/kernels/volk/volk_32fc_magnitude_32f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32fc_magnitude_32f_u_H
#define INCLUDED_volk_32fc_magnitude_32f_u_H
@@ -5,6 +27,52 @@
#include <stdio.h>
#include <math.h>
+#ifdef LV_HAVE_AVX
+#include <immintrin.h>
+ /*!
+ \brief Calculates the magnitude of the complexVector and stores the results in the magnitudeVector
+ \param complexVector The vector containing the complex input values
+ \param magnitudeVector The vector containing the real output values
+ \param num_points The number of complex values in complexVector to be calculated and stored into cVector
+ */
+static inline void volk_32fc_magnitude_32f_u_avx(float* magnitudeVector, const lv_32fc_t* complexVector, unsigned int num_points){
+ unsigned int number = 0;
+ const unsigned int eighthPoints = num_points / 8;
+
+ const float* complexVectorPtr = (float*)complexVector;
+ float* magnitudeVectorPtr = magnitudeVector;
+
+ __m256 cplxValue1, cplxValue2, complex1, complex2, result;
+ for(;number < eighthPoints; number++){
+ cplxValue1 = _mm256_loadu_ps(complexVectorPtr);
+ complexVectorPtr += 8;
+
+ cplxValue2 = _mm256_loadu_ps(complexVectorPtr);
+ complexVectorPtr += 8;
+
+ cplxValue1 = _mm256_mul_ps(cplxValue1, cplxValue1); // Square the values
+ cplxValue2 = _mm256_mul_ps(cplxValue2, cplxValue2); // Square the Values
+
+ complex1 = _mm256_permute2f128_ps(cplxValue1, cplxValue2, 0x20);
+ complex2 = _mm256_permute2f128_ps(cplxValue1, cplxValue2, 0x31);
+
+ result = _mm256_hadd_ps(complex1, complex2); // Add the I2 and Q2 values
+
+ result = _mm256_sqrt_ps(result);
+
+ _mm256_storeu_ps(magnitudeVectorPtr, result);
+ magnitudeVectorPtr += 8;
+ }
+
+ number = eighthPoints * 8;
+ for(; number < num_points; number++){
+ float val1Real = *complexVectorPtr++;
+ float val1Imag = *complexVectorPtr++;
+ *magnitudeVectorPtr++ = sqrtf((val1Real * val1Real) + (val1Imag * val1Imag));
+ }
+}
+#endif /* LV_HAVE_AVX */
+
#ifdef LV_HAVE_SSE3
#include <pmmintrin.h>
/*!
@@ -123,6 +191,52 @@ static inline void volk_32fc_magnitude_32f_generic(float* magnitudeVector, const
#include <stdio.h>
#include <math.h>
+#ifdef LV_HAVE_AVX
+#include <immintrin.h>
+ /*!
+ \brief Calculates the magnitude of the complexVector and stores the results in the magnitudeVector
+ \param complexVector The vector containing the complex input values
+ \param magnitudeVector The vector containing the real output values
+ \param num_points The number of complex values in complexVector to be calculated and stored into cVector
+ */
+static inline void volk_32fc_magnitude_32f_a_avx(float* magnitudeVector, const lv_32fc_t* complexVector, unsigned int num_points){
+ unsigned int number = 0;
+ const unsigned int eighthPoints = num_points / 8;
+
+ const float* complexVectorPtr = (float*)complexVector;
+ float* magnitudeVectorPtr = magnitudeVector;
+
+ __m256 cplxValue1, cplxValue2, complex1, complex2, result;
+ for(;number < eighthPoints; number++){
+ cplxValue1 = _mm256_load_ps(complexVectorPtr);
+ complexVectorPtr += 8;
+
+ cplxValue2 = _mm256_load_ps(complexVectorPtr);
+ complexVectorPtr += 8;
+
+ cplxValue1 = _mm256_mul_ps(cplxValue1, cplxValue1); // Square the values
+ cplxValue2 = _mm256_mul_ps(cplxValue2, cplxValue2); // Square the Values
+
+ complex1 = _mm256_permute2f128_ps(cplxValue1, cplxValue2, 0x20);
+ complex2 = _mm256_permute2f128_ps(cplxValue1, cplxValue2, 0x31);
+
+ result = _mm256_hadd_ps(complex1, complex2); // Add the I2 and Q2 values
+
+ result = _mm256_sqrt_ps(result);
+
+ _mm256_store_ps(magnitudeVectorPtr, result);
+ magnitudeVectorPtr += 8;
+ }
+
+ number = eighthPoints * 8;
+ for(; number < num_points; number++){
+ float val1Real = *complexVectorPtr++;
+ float val1Imag = *complexVectorPtr++;
+ *magnitudeVectorPtr++ = sqrtf((val1Real * val1Real) + (val1Imag * val1Imag));
+ }
+}
+#endif /* LV_HAVE_AVX */
+
#ifdef LV_HAVE_SSE3
#include <pmmintrin.h>
/*!
diff --git a/volk/kernels/volk/volk_32fc_magnitude_squared_32f.h b/volk/kernels/volk/volk_32fc_magnitude_squared_32f.h
index 878794ba79..ed8eac62d9 100644
--- a/volk/kernels/volk/volk_32fc_magnitude_squared_32f.h
+++ b/volk/kernels/volk/volk_32fc_magnitude_squared_32f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32fc_magnitude_squared_32f_u_H
#define INCLUDED_volk_32fc_magnitude_squared_32f_u_H
@@ -5,6 +27,50 @@
#include <stdio.h>
#include <math.h>
+#ifdef LV_HAVE_AVX
+#include <immintrin.h>
+ /*!
+ \brief Calculates the magnitude squared of the complexVector and stores the results in the magnitudeVector
+ \param complexVector The vector containing the complex input values
+ \param magnitudeVector The vector containing the real output values
+ \param num_points The number of complex values in complexVector to be calculated and stored into cVector
+ */
+static inline void volk_32fc_magnitude_squared_32f_u_avx(float* magnitudeVector, const lv_32fc_t* complexVector, unsigned int num_points){
+ unsigned int number = 0;
+ const unsigned int eighthPoints = num_points / 8;
+
+ const float* complexVectorPtr = (float*)complexVector;
+ float* magnitudeVectorPtr = magnitudeVector;
+
+ __m256 cplxValue1, cplxValue2, complex1, complex2, result;
+ for(;number < eighthPoints; number++){
+ cplxValue1 = _mm256_loadu_ps(complexVectorPtr);
+ complexVectorPtr += 8;
+
+ cplxValue2 = _mm256_loadu_ps(complexVectorPtr);
+ complexVectorPtr += 8;
+
+ cplxValue1 = _mm256_mul_ps(cplxValue1, cplxValue1); // Square the values
+ cplxValue2 = _mm256_mul_ps(cplxValue2, cplxValue2); // Square the Values
+
+ complex1 = _mm256_permute2f128_ps(cplxValue1, cplxValue2, 0x20);
+ complex2 = _mm256_permute2f128_ps(cplxValue1, cplxValue2, 0x31);
+
+ result = _mm256_hadd_ps(complex1, complex2); // Add the I2 and Q2 values
+
+ _mm256_storeu_ps(magnitudeVectorPtr, result);
+ magnitudeVectorPtr += 8;
+ }
+
+ number = eighthPoints * 8;
+ for(; number < num_points; number++){
+ float val1Real = *complexVectorPtr++;
+ float val1Imag = *complexVectorPtr++;
+ *magnitudeVectorPtr++ = (val1Real * val1Real) + (val1Imag * val1Imag);
+ }
+}
+#endif /* LV_HAVE_AVX */
+
#ifdef LV_HAVE_SSE3
#include <pmmintrin.h>
/*!
@@ -119,6 +185,50 @@ static inline void volk_32fc_magnitude_squared_32f_generic(float* magnitudeVecto
#include <stdio.h>
#include <math.h>
+#ifdef LV_HAVE_AVX
+#include <immintrin.h>
+ /*!
+ \brief Calculates the magnitude squared of the complexVector and stores the results in the magnitudeVector
+ \param complexVector The vector containing the complex input values
+ \param magnitudeVector The vector containing the real output values
+ \param num_points The number of complex values in complexVector to be calculated and stored into cVector
+ */
+static inline void volk_32fc_magnitude_squared_32f_a_avx(float* magnitudeVector, const lv_32fc_t* complexVector, unsigned int num_points){
+ unsigned int number = 0;
+ const unsigned int eighthPoints = num_points / 8;
+
+ const float* complexVectorPtr = (float*)complexVector;
+ float* magnitudeVectorPtr = magnitudeVector;
+
+ __m256 cplxValue1, cplxValue2, complex1, complex2, result;
+ for(;number < eighthPoints; number++){
+ cplxValue1 = _mm256_load_ps(complexVectorPtr);
+ complexVectorPtr += 8;
+
+ cplxValue2 = _mm256_load_ps(complexVectorPtr);
+ complexVectorPtr += 8;
+
+ cplxValue1 = _mm256_mul_ps(cplxValue1, cplxValue1); // Square the values
+ cplxValue2 = _mm256_mul_ps(cplxValue2, cplxValue2); // Square the Values
+
+ complex1 = _mm256_permute2f128_ps(cplxValue1, cplxValue2, 0x20);
+ complex2 = _mm256_permute2f128_ps(cplxValue1, cplxValue2, 0x31);
+
+ result = _mm256_hadd_ps(complex1, complex2); // Add the I2 and Q2 values
+
+ _mm256_store_ps(magnitudeVectorPtr, result);
+ magnitudeVectorPtr += 8;
+ }
+
+ number = eighthPoints * 8;
+ for(; number < num_points; number++){
+ float val1Real = *complexVectorPtr++;
+ float val1Imag = *complexVectorPtr++;
+ *magnitudeVectorPtr++ = (val1Real * val1Real) + (val1Imag * val1Imag);
+ }
+}
+#endif /* LV_HAVE_AVX */
+
#ifdef LV_HAVE_SSE3
#include <pmmintrin.h>
/*!
diff --git a/volk/kernels/volk/volk_32fc_s32f_atan2_32f.h b/volk/kernels/volk/volk_32fc_s32f_atan2_32f.h
index b076ab44ef..2e9221b593 100644
--- a/volk/kernels/volk/volk_32fc_s32f_atan2_32f.h
+++ b/volk/kernels/volk/volk_32fc_s32f_atan2_32f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32fc_s32f_atan2_32f_a_H
#define INCLUDED_volk_32fc_s32f_atan2_32f_a_H
diff --git a/volk/kernels/volk/volk_32fc_s32f_deinterleave_real_16i.h b/volk/kernels/volk/volk_32fc_s32f_deinterleave_real_16i.h
index 9e10217a0f..0f24512b0e 100644
--- a/volk/kernels/volk/volk_32fc_s32f_deinterleave_real_16i.h
+++ b/volk/kernels/volk/volk_32fc_s32f_deinterleave_real_16i.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32fc_s32f_deinterleave_real_16i_a_H
#define INCLUDED_volk_32fc_s32f_deinterleave_real_16i_a_H
diff --git a/volk/kernels/volk/volk_32fc_s32f_magnitude_16i.h b/volk/kernels/volk/volk_32fc_s32f_magnitude_16i.h
index 09abd967d6..b8ac93a0ec 100644
--- a/volk/kernels/volk/volk_32fc_s32f_magnitude_16i.h
+++ b/volk/kernels/volk/volk_32fc_s32f_magnitude_16i.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32fc_s32f_magnitude_16i_a_H
#define INCLUDED_volk_32fc_s32f_magnitude_16i_a_H
diff --git a/volk/kernels/volk/volk_32fc_s32f_power_32fc.h b/volk/kernels/volk/volk_32fc_s32f_power_32fc.h
index b9dd13baf0..9ecca50d5c 100644
--- a/volk/kernels/volk/volk_32fc_s32f_power_32fc.h
+++ b/volk/kernels/volk/volk_32fc_s32f_power_32fc.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32fc_s32f_power_32fc_a_H
#define INCLUDED_volk_32fc_s32f_power_32fc_a_H
diff --git a/volk/kernels/volk/volk_32fc_s32f_power_spectrum_32f.h b/volk/kernels/volk/volk_32fc_s32f_power_spectrum_32f.h
index f76d9d35e4..8927112344 100644
--- a/volk/kernels/volk/volk_32fc_s32f_power_spectrum_32f.h
+++ b/volk/kernels/volk/volk_32fc_s32f_power_spectrum_32f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32fc_s32f_power_spectrum_32f_a_H
#define INCLUDED_volk_32fc_s32f_power_spectrum_32f_a_H
diff --git a/volk/kernels/volk/volk_32fc_s32f_x2_power_spectral_density_32f.h b/volk/kernels/volk/volk_32fc_s32f_x2_power_spectral_density_32f.h
index e73eb09f8f..517ade4822 100644
--- a/volk/kernels/volk/volk_32fc_s32f_x2_power_spectral_density_32f.h
+++ b/volk/kernels/volk/volk_32fc_s32f_x2_power_spectral_density_32f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32fc_s32f_x2_power_spectral_density_32f_a_H
#define INCLUDED_volk_32fc_s32f_x2_power_spectral_density_32f_a_H
@@ -5,6 +27,98 @@
#include <stdio.h>
#include <math.h>
+#ifdef LV_HAVE_AVX
+#include <immintrin.h>
+
+#ifdef LV_HAVE_LIB_SIMDMATH
+#include <simdmath.h>
+#endif /* LV_HAVE_LIB_SIMDMATH */
+
+/*!
+ \brief Calculates the log10 power value divided by the RBW for each input point
+ \param logPowerOutput The 10.0 * log10((r*r + i*i)/RBW) for each data point
+ \param complexFFTInput The complex data output from the FFT point
+ \param normalizationFactor This value is divided against all the input values before the power is calculated
+ \param rbw The resolution bandwith of the fft spectrum
+ \param num_points The number of fft data points
+*/
+static inline void volk_32fc_s32f_x2_power_spectral_density_32f_a_avx(float* logPowerOutput, const lv_32fc_t* complexFFTInput, const float normalizationFactor, const float rbw, unsigned int num_points){
+ const float* inputPtr = (const float*)complexFFTInput;
+ float* destPtr = logPowerOutput;
+ uint64_t number = 0;
+ const float iRBW = 1.0 / rbw;
+ const float iNormalizationFactor = 1.0 / normalizationFactor;
+
+#ifdef LV_HAVE_LIB_SIMDMATH
+ __m256 magScalar = _mm256_set1_ps(10.0);
+ magScalar = _mm256_div_ps(magScalar, logf4(magScalar));
+
+ __m256 invRBW = _mm256_set1_ps(iRBW);
+
+ __m256 invNormalizationFactor = _mm256_set1_ps(iNormalizationFactor);
+
+ __m256 power;
+ __m256 input1, input2;
+ const uint64_t eighthPoints = num_points / 8;
+ for(;number < eighthPoints; number++){
+ // Load the complex values
+ input1 =_mm256_load_ps(inputPtr);
+ inputPtr += 8;
+ input2 =_mm256_load_ps(inputPtr);
+ inputPtr += 8;
+
+ // Apply the normalization factor
+ input1 = _mm256_mul_ps(input1, invNormalizationFactor);
+ input2 = _mm256_mul_ps(input2, invNormalizationFactor);
+
+ // Multiply each value by itself
+ // (r1*r1), (i1*i1), (r2*r2), (i2*i2)
+ input1 = _mm256_mul_ps(input1, input1);
+ // (r3*r3), (i3*i3), (r4*r4), (i4*i4)
+ input2 = _mm256_mul_ps(input2, input2);
+
+ // Horizontal add, to add (r*r) + (i*i) for each complex value
+ // (r1*r1)+(i1*i1), (r2*r2) + (i2*i2), (r3*r3)+(i3*i3), (r4*r4)+(i4*i4)
+ inputVal1 = _mm256_permute2f128_ps(input1, input2, 0x20);
+ inputVal2 = _mm256_permute2f128_ps(input1, input2, 0x31);
+
+ power = _mm256_hadd_ps(inputVal1, inputVal2);
+
+ // Divide by the rbw
+ power = _mm256_mul_ps(power, invRBW);
+
+ // Calculate the natural log power
+ power = logf4(power);
+
+ // Convert to log10 and multiply by 10.0
+ power = _mm256_mul_ps(power, magScalar);
+
+ // Store the floating point results
+ _mm256_store_ps(destPtr, power);
+
+ destPtr += 8;
+ }
+
+ number = eighthPoints*8;
+#endif /* LV_HAVE_LIB_SIMDMATH */
+ // Calculate the FFT for any remaining points
+ for(; number < num_points; number++){
+ // Calculate dBm
+ // 50 ohm load assumption
+ // 10 * log10 (v^2 / (2 * 50.0 * .001)) = 10 * log10( v^2 * 10)
+ // 75 ohm load assumption
+ // 10 * log10 (v^2 / (2 * 75.0 * .001)) = 10 * log10( v^2 * 15)
+
+ const float real = *inputPtr++ * iNormalizationFactor;
+ const float imag = *inputPtr++ * iNormalizationFactor;
+
+ *destPtr = 10.0*log10f((((real * real) + (imag * imag)) + 1e-20) * iRBW);
+ destPtr++;
+ }
+
+}
+#endif /* LV_HAVE_AVX */
+
#ifdef LV_HAVE_SSE3
#include <pmmintrin.h>
diff --git a/volk/kernels/volk/volk_32fc_s32fc_multiply_32fc.h b/volk/kernels/volk/volk_32fc_s32fc_multiply_32fc.h
index 668a047609..474b982887 100644
--- a/volk/kernels/volk/volk_32fc_s32fc_multiply_32fc.h
+++ b/volk/kernels/volk/volk_32fc_s32fc_multiply_32fc.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32fc_s32fc_multiply_32fc_u_H
#define INCLUDED_volk_32fc_s32fc_multiply_32fc_u_H
@@ -6,6 +28,52 @@
#include <volk/volk_complex.h>
#include <float.h>
+#ifdef LV_HAVE_AVX
+#include <immintrin.h>
+ /*!
+ \brief Multiplies the two input complex vectors and stores their results in the third vector
+ \param cVector The vector where the results will be stored
+ \param aVector One of the vectors to be multiplied
+ \param bVector One of the vectors to be multiplied
+ \param num_points The number of complex values in aVector and bVector to be multiplied together and stored into cVector
+ */
+static inline void volk_32fc_s32fc_multiply_32fc_u_avx(lv_32fc_t* cVector, const lv_32fc_t* aVector, const lv_32fc_t scalar, unsigned int num_points){
+ unsigned int number = 0;
+ unsigned int i = 0;
+ const unsigned int quarterPoints = num_points / 4;
+ unsigned int isodd = num_points & 3;
+ __m256 x, yl, yh, z, tmp1, tmp2;
+ lv_32fc_t* c = cVector;
+ const lv_32fc_t* a = aVector;
+
+ // Set up constant scalar vector
+ yl = _mm256_set1_ps(lv_creal(scalar));
+ yh = _mm256_set1_ps(lv_cimag(scalar));
+
+ for(;number < quarterPoints; number++){
+ x = _mm256_loadu_ps((float*)a); // Load the ar + ai, br + bi as ar,ai,br,bi
+
+ tmp1 = _mm256_mul_ps(x,yl); // tmp1 = ar*cr,ai*cr,br*dr,bi*dr
+
+ x = _mm256_shuffle_ps(x,x,0xB1); // Re-arrange x to be ai,ar,bi,br
+
+ tmp2 = _mm256_mul_ps(x,yh); // tmp2 = ai*ci,ar*ci,bi*di,br*di
+
+ z = _mm256_addsub_ps(tmp1,tmp2); // ar*cr-ai*ci, ai*cr+ar*ci, br*dr-bi*di, bi*dr+br*di
+
+ _mm256_storeu_ps((float*)c,z); // Store the results back into the C container
+
+ a += 4;
+ c += 4;
+ }
+
+ for(i = num_points-isodd; i < num_points; i++) {
+ *c++ = (*a++) * scalar;
+ }
+
+}
+#endif /* LV_HAVE_AVX */
+
#ifdef LV_HAVE_SSE3
#include <pmmintrin.h>
/*!
@@ -93,6 +161,52 @@ static inline void volk_32fc_s32fc_multiply_32fc_generic(lv_32fc_t* cVector, con
#include <volk/volk_complex.h>
#include <float.h>
+#ifdef LV_HAVE_AVX
+#include <immintrin.h>
+ /*!
+ \brief Multiplies the two input complex vectors and stores their results in the third vector
+ \param cVector The vector where the results will be stored
+ \param aVector One of the vectors to be multiplied
+ \param bVector One of the vectors to be multiplied
+ \param num_points The number of complex values in aVector and bVector to be multiplied together and stored into cVector
+ */
+static inline void volk_32fc_s32fc_multiply_32fc_a_avx(lv_32fc_t* cVector, const lv_32fc_t* aVector, const lv_32fc_t scalar, unsigned int num_points){
+ unsigned int number = 0;
+ unsigned int i = 0;
+ const unsigned int quarterPoints = num_points / 4;
+ unsigned int isodd = num_points & 3;
+ __m256 x, yl, yh, z, tmp1, tmp2;
+ lv_32fc_t* c = cVector;
+ const lv_32fc_t* a = aVector;
+
+ // Set up constant scalar vector
+ yl = _mm256_set1_ps(lv_creal(scalar));
+ yh = _mm256_set1_ps(lv_cimag(scalar));
+
+ for(;number < quarterPoints; number++){
+ x = _mm256_load_ps((float*)a); // Load the ar + ai, br + bi as ar,ai,br,bi
+
+ tmp1 = _mm256_mul_ps(x,yl); // tmp1 = ar*cr,ai*cr,br*dr,bi*dr
+
+ x = _mm256_shuffle_ps(x,x,0xB1); // Re-arrange x to be ai,ar,bi,br
+
+ tmp2 = _mm256_mul_ps(x,yh); // tmp2 = ai*ci,ar*ci,bi*di,br*di
+
+ z = _mm256_addsub_ps(tmp1,tmp2); // ar*cr-ai*ci, ai*cr+ar*ci, br*dr-bi*di, bi*dr+br*di
+
+ _mm256_store_ps((float*)c,z); // Store the results back into the C container
+
+ a += 4;
+ c += 4;
+ }
+
+ for(i = num_points-isodd; i < num_points; i++) {
+ *c++ = (*a++) * scalar;
+ }
+
+}
+#endif /* LV_HAVE_AVX */
+
#ifdef LV_HAVE_SSE3
#include <pmmintrin.h>
/*!
@@ -138,6 +252,43 @@ static inline void volk_32fc_s32fc_multiply_32fc_a_sse3(lv_32fc_t* cVector, cons
}
#endif /* LV_HAVE_SSE */
+#ifdef LV_HAVE_NEON
+#include <arm_neon.h>
+ /*!
+ \brief Multiplies the two input complex vectors and stores their results in the third vector
+ \param cVector The vector where the results will be stored
+ \param aVector One of the vectors to be multiplied
+ \param bVector One of the vectors to be multiplied
+ \param num_points The number of complex values in aVector and bVector to be multiplied together and stored into cVector
+ */
+static inline void volk_32fc_s32fc_multiply_32fc_neon(lv_32fc_t* cVector, const lv_32fc_t* aVector, const lv_32fc_t scalar, unsigned int num_points){
+ lv_32fc_t* cPtr = cVector;
+ const lv_32fc_t* aPtr = aVector;
+ unsigned int number = num_points;
+ unsigned int quarter_points = num_points / 4;
+
+ float32x4x2_t a_val, scalar_val;
+ float32x4x2_t tmp_imag;
+
+ scalar_val = vld2q_f32((const float*)&scalar);
+ for(number = 0; number < quarter_points; ++number) {
+ a_val = vld2q_f32((float*)aPtr);
+ tmp_imag.val[1] = vmulq_f32(a_val.val[1], scalar_val.val[0]);
+ tmp_imag.val[0] = vmulq_f32(a_val.val[0], scalar_val.val[0]);
+
+ tmp_imag.val[1] = vmlaq_f32(tmp_imag.val[1], a_val.val[0], scalar_val.val[1]);
+ tmp_imag.val[0] = vmlaq_f32(tmp_imag.val[0], a_val.val[1], scalar_val.val[1]);
+
+ vst2q_f32((float*)cVector, tmp_imag);
+ aPtr += 4;
+ cVector += 4;
+ }
+
+ for(number = quarter_points*4; number < num_points; number++){
+ *cPtr++ = *aPtr++ * scalar;
+ }
+}
+#endif /* LV_HAVE_NEON */
#ifdef LV_HAVE_GENERIC
/*!
@@ -171,8 +322,4 @@ static inline void volk_32fc_s32fc_multiply_32fc_a_generic(lv_32fc_t* cVector, c
}
#endif /* LV_HAVE_GENERIC */
-
-
-
-
#endif /* INCLUDED_volk_32fc_x2_multiply_32fc_a_H */
diff --git a/volk/kernels/volk/volk_32fc_s32fc_rotatorpuppet_32fc.h b/volk/kernels/volk/volk_32fc_s32fc_rotatorpuppet_32fc.h
index c7b46e7e99..cbbc43624b 100644
--- a/volk/kernels/volk/volk_32fc_s32fc_rotatorpuppet_32fc.h
+++ b/volk/kernels/volk/volk_32fc_s32fc_rotatorpuppet_32fc.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32fc_s32fc_rotatorpuppet_32fc_a_H
#define INCLUDED_volk_32fc_s32fc_rotatorpuppet_32fc_a_H
diff --git a/volk/kernels/volk/volk_32fc_s32fc_x2_rotator_32fc.h b/volk/kernels/volk/volk_32fc_s32fc_x2_rotator_32fc.h
index 0ed9d67cb5..06500784a1 100644
--- a/volk/kernels/volk/volk_32fc_s32fc_x2_rotator_32fc.h
+++ b/volk/kernels/volk/volk_32fc_s32fc_x2_rotator_32fc.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32fc_s32fc_rotator_32fc_a_H
#define INCLUDED_volk_32fc_s32fc_rotator_32fc_a_H
diff --git a/volk/kernels/volk/volk_32fc_x2_conjugate_dot_prod_32fc.h b/volk/kernels/volk/volk_32fc_x2_conjugate_dot_prod_32fc.h
index e6ccf5c384..8964434bef 100644
--- a/volk/kernels/volk/volk_32fc_x2_conjugate_dot_prod_32fc.h
+++ b/volk/kernels/volk/volk_32fc_x2_conjugate_dot_prod_32fc.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32fc_x2_conjugate_dot_prod_32fc_u_H
#define INCLUDED_volk_32fc_x2_conjugate_dot_prod_32fc_u_H
@@ -142,10 +164,57 @@ static inline void volk_32fc_x2_conjugate_dot_prod_32fc_u_sse3(lv_32fc_t* result
#endif /*LV_HAVE_SSE3*/
+#ifdef LV_HAVE_NEON
+#include <arm_neon.h>
+static inline void volk_32fc_x2_conjugate_dot_prod_32fc_neon(lv_32fc_t* result, const lv_32fc_t* input, const lv_32fc_t* taps, unsigned int num_points) {
+
+ unsigned int quarter_points = num_points / 4;
+ unsigned int number;
+
+ lv_32fc_t* a_ptr = (lv_32fc_t*) taps;
+ lv_32fc_t* b_ptr = (lv_32fc_t*) input;
+ // for 2-lane vectors, 1st lane holds the real part,
+ // 2nd lane holds the imaginary part
+ float32x4x2_t a_val, b_val, accumulator;
+ float32x4x2_t tmp_imag;
+ accumulator.val[0] = vdupq_n_f32(0);
+ accumulator.val[1] = vdupq_n_f32(0);
+
+ for(number = 0; number < quarter_points; ++number) {
+ a_val = vld2q_f32((float*)a_ptr); // a0r|a1r|a2r|a3r || a0i|a1i|a2i|a3i
+ b_val = vld2q_f32((float*)b_ptr); // b0r|b1r|b2r|b3r || b0i|b1i|b2i|b3i
+ __builtin_prefetch(a_ptr+8);
+ __builtin_prefetch(b_ptr+8);
+
+ // do the first multiply
+ tmp_imag.val[1] = vmulq_f32(a_val.val[1], b_val.val[0]);
+ tmp_imag.val[0] = vmulq_f32(a_val.val[0], b_val.val[0]);
+
+ // use multiply accumulate/subtract to get result
+ tmp_imag.val[1] = vmlsq_f32(tmp_imag.val[1], a_val.val[0], b_val.val[1]);
+ tmp_imag.val[0] = vmlaq_f32(tmp_imag.val[0], a_val.val[1], b_val.val[1]);
+
+ accumulator.val[0] = vaddq_f32(accumulator.val[0], tmp_imag.val[0]);
+ accumulator.val[1] = vaddq_f32(accumulator.val[1], tmp_imag.val[1]);
+
+ // increment pointers
+ a_ptr += 4;
+ b_ptr += 4;
+ }
+ lv_32fc_t accum_result[4];
+ vst2q_f32((float*)accum_result, accumulator);
+ *result = accum_result[0] + accum_result[1] + accum_result[2] + accum_result[3];
-#endif /*INCLUDED_volk_32fc_x2_conjugate_dot_prod_32fc_u_H*/
+ // tail case
+ for(number = quarter_points*4; number < num_points; ++number) {
+ *result += (*a_ptr++) * lv_conj(*b_ptr++);
+ }
+ *result = lv_conj(*result);
+}
+#endif /*LV_HAVE_NEON*/
+#endif /*INCLUDED_volk_32fc_x2_conjugate_dot_prod_32fc_u_H*/
#ifndef INCLUDED_volk_32fc_x2_conjugate_dot_prod_32fc_a_H
#define INCLUDED_volk_32fc_x2_conjugate_dot_prod_32fc_a_H
diff --git a/volk/kernels/volk/volk_32fc_x2_dot_prod_32fc.h b/volk/kernels/volk/volk_32fc_x2_dot_prod_32fc.h
index 430b747ff2..c65d0984c5 100644
--- a/volk/kernels/volk/volk_32fc_x2_dot_prod_32fc.h
+++ b/volk/kernels/volk/volk_32fc_x2_dot_prod_32fc.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32fc_x2_dot_prod_32fc_u_H
#define INCLUDED_volk_32fc_x2_dot_prod_32fc_u_H
@@ -316,10 +338,66 @@ static inline void volk_32fc_x2_dot_prod_32fc_u_sse4_1(lv_32fc_t* result, const
#endif /*LV_HAVE_SSE4_1*/
+#ifdef LV_HAVE_AVX
+
+#include <immintrin.h>
+
+static inline void volk_32fc_x2_dot_prod_32fc_u_avx(lv_32fc_t* result, const lv_32fc_t* input, const lv_32fc_t* taps, unsigned int num_points) {
+
+ unsigned int isodd = num_points & 3;
+ unsigned int i = 0;
+ lv_32fc_t dotProduct;
+ memset(&dotProduct, 0x0, 2*sizeof(float));
+
+ unsigned int number = 0;
+ const unsigned int quarterPoints = num_points / 4;
+
+ __m256 x, y, yl, yh, z, tmp1, tmp2, dotProdVal;
+
+ const lv_32fc_t* a = input;
+ const lv_32fc_t* b = taps;
+
+ dotProdVal = _mm256_setzero_ps();
+
+ for(;number < quarterPoints; number++){
+ x = _mm256_loadu_ps((float*)a); // Load a,b,e,f as ar,ai,br,bi,er,ei,fr,fi
+ y = _mm256_loadu_ps((float*)b); // Load c,d,g,h as cr,ci,dr,di,gr,gi,hr,hi
+
+ yl = _mm256_moveldup_ps(y); // Load yl with cr,cr,dr,dr,gr,gr,hr,hr
+ yh = _mm256_movehdup_ps(y); // Load yh with ci,ci,di,di,gi,gi,hi,hi
+
+ tmp1 = _mm256_mul_ps(x,yl); // tmp1 = ar*cr,ai*cr,br*dr,bi*dr ...
+
+ x = _mm256_shuffle_ps(x,x,0xB1); // Re-arrange x to be ai,ar,bi,br,ei,er,fi,fr
+ tmp2 = _mm256_mul_ps(x,yh); // tmp2 = ai*ci,ar*ci,bi*di,br*di ...
+
+ z = _mm256_addsub_ps(tmp1,tmp2); // ar*cr-ai*ci, ai*cr+ar*ci, br*dr-bi*di, bi*dr+br*di
+
+ dotProdVal = _mm256_add_ps(dotProdVal, z); // Add the complex multiplication results together
+
+ a += 4;
+ b += 4;
+ }
+
+ __VOLK_ATTR_ALIGNED(32) lv_32fc_t dotProductVector[4];
+
+ _mm256_storeu_ps((float*)dotProductVector,dotProdVal); // Store the results back into the dot product vector
+
+ dotProduct += ( dotProductVector[0] + dotProductVector[1] + dotProductVector[2] + dotProductVector[3]);
+
+ for(i = num_points-isodd; i < num_points; i++) {
+ dotProduct += input[i] * taps[i];
+ }
+
+ *result = dotProduct;
+}
+
+#endif /*LV_HAVE_AVX*/
#endif /*INCLUDED_volk_32fc_x2_dot_prod_32fc_u_H*/
+
#ifndef INCLUDED_volk_32fc_x2_dot_prod_32fc_a_H
#define INCLUDED_volk_32fc_x2_dot_prod_32fc_a_H
@@ -680,6 +758,7 @@ static inline void volk_32fc_x2_dot_prod_32fc_a_sse3(lv_32fc_t* result, const lv
#endif /*LV_HAVE_SSE3*/
+
#ifdef LV_HAVE_SSE4_1
#include <smmintrin.h>
@@ -817,7 +896,7 @@ static inline void volk_32fc_x2_dot_prod_32fc_neon(lv_32fc_t* result, const lv_3
#endif /*LV_HAVE_NEON*/
#ifdef LV_HAVE_NEON
-
+#include <arm_neon.h>
static inline void volk_32fc_x2_dot_prod_32fc_neon_opttests(lv_32fc_t* result, const lv_32fc_t* input, const lv_32fc_t* taps, unsigned int num_points) {
unsigned int quarter_points = num_points / 4;
@@ -976,4 +1055,62 @@ static inline void volk_32fc_x2_dot_prod_32fc_neon_optfmaunroll(lv_32fc_t* resul
#endif /*LV_HAVE_NEON*/
+#ifdef LV_HAVE_AVX
+
+#include <immintrin.h>
+
+static inline void volk_32fc_x2_dot_prod_32fc_a_avx(lv_32fc_t* result, const lv_32fc_t* input, const lv_32fc_t* taps, unsigned int num_points) {
+
+ unsigned int isodd = num_points & 3;
+ unsigned int i = 0;
+ lv_32fc_t dotProduct;
+ memset(&dotProduct, 0x0, 2*sizeof(float));
+
+ unsigned int number = 0;
+ const unsigned int quarterPoints = num_points / 4;
+
+ __m256 x, y, yl, yh, z, tmp1, tmp2, dotProdVal;
+
+ const lv_32fc_t* a = input;
+ const lv_32fc_t* b = taps;
+
+ dotProdVal = _mm256_setzero_ps();
+
+ for(;number < quarterPoints; number++){
+
+ x = _mm256_load_ps((float*)a); // Load a,b,e,f as ar,ai,br,bi,er,ei,fr,fi
+ y = _mm256_load_ps((float*)b); // Load c,d,g,h as cr,ci,dr,di,gr,gi,hr,hi
+
+ yl = _mm256_moveldup_ps(y); // Load yl with cr,cr,dr,dr,gr,gr,hr,hr
+ yh = _mm256_movehdup_ps(y); // Load yh with ci,ci,di,di,gi,gi,hi,hi
+
+ tmp1 = _mm256_mul_ps(x,yl); // tmp1 = ar*cr,ai*cr,br*dr,bi*dr ...
+
+ x = _mm256_shuffle_ps(x,x,0xB1); // Re-arrange x to be ai,ar,bi,br,ei,er,fi,fr
+
+ tmp2 = _mm256_mul_ps(x,yh); // tmp2 = ai*ci,ar*ci,bi*di,br*di ...
+
+ z = _mm256_addsub_ps(tmp1,tmp2); // ar*cr-ai*ci, ai*cr+ar*ci, br*dr-bi*di, bi*dr+br*di
+
+ dotProdVal = _mm256_add_ps(dotProdVal, z); // Add the complex multiplication results together
+
+ a += 4;
+ b += 4;
+ }
+
+ __VOLK_ATTR_ALIGNED(32) lv_32fc_t dotProductVector[4];
+
+ _mm256_store_ps((float*)dotProductVector,dotProdVal); // Store the results back into the dot product vector
+
+ dotProduct += ( dotProductVector[0] + dotProductVector[1] + dotProductVector[2] + dotProductVector[3]);
+
+ for(i = num_points-isodd; i < num_points; i++) {
+ dotProduct += input[i] * taps[i];
+ }
+
+ *result = dotProduct;
+}
+
+#endif /*LV_HAVE_AVX*/
+
#endif /*INCLUDED_volk_32fc_x2_dot_prod_32fc_a_H*/
diff --git a/volk/kernels/volk/volk_32fc_x2_multiply_32fc.h b/volk/kernels/volk/volk_32fc_x2_multiply_32fc.h
index 7c723bcdb6..4575439e94 100644
--- a/volk/kernels/volk/volk_32fc_x2_multiply_32fc.h
+++ b/volk/kernels/volk/volk_32fc_x2_multiply_32fc.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32fc_x2_multiply_32fc_u_H
#define INCLUDED_volk_32fc_x2_multiply_32fc_u_H
@@ -6,6 +28,55 @@
#include <volk/volk_complex.h>
#include <float.h>
+#ifdef LV_HAVE_AVX
+#include <immintrin.h>
+ /*!
+ \brief Multiplies the two input complex vectors and stores their results in the third vector
+ \param cVector The vector where the results will be stored
+ \param aVector One of the vectors to be multiplied
+ \param bVector One of the vectors to be multiplied
+ \param num_points The number of complex values in aVector and bVector to be multiplied together and stored into cVector
+ */
+static inline void volk_32fc_x2_multiply_32fc_u_avx(lv_32fc_t* cVector, const lv_32fc_t* aVector, const lv_32fc_t* bVector, unsigned int num_points){
+ unsigned int number = 0;
+ const unsigned int quarterPoints = num_points / 4;
+
+ __m256 x, y, yl, yh, z, tmp1, tmp2;
+ lv_32fc_t* c = cVector;
+ const lv_32fc_t* a = aVector;
+ const lv_32fc_t* b = bVector;
+
+ for(;number < quarterPoints; number++){
+
+ x = _mm256_loadu_ps((float*)a); // Load the ar + ai, br + bi ... as ar,ai,br,bi ...
+ y = _mm256_loadu_ps((float*)b); // Load the cr + ci, dr + di ... as cr,ci,dr,di ...
+
+ yl = _mm256_moveldup_ps(y); // Load yl with cr,cr,dr,dr ...
+ yh = _mm256_movehdup_ps(y); // Load yh with ci,ci,di,di ...
+
+ tmp1 = _mm256_mul_ps(x,yl); // tmp1 = ar*cr,ai*cr,br*dr,bi*dr ...
+
+ x = _mm256_shuffle_ps(x,x,0xB1); // Re-arrange x to be ai,ar,bi,br ...
+
+ tmp2 = _mm256_mul_ps(x,yh); // tmp2 = ai*ci,ar*ci,bi*di,br*di
+
+ z = _mm256_addsub_ps(tmp1,tmp2); // ar*cr-ai*ci, ai*cr+ar*ci, br*dr-bi*di, bi*dr+br*di
+
+ _mm256_storeu_ps((float*)c,z); // Store the results back into the C container
+
+ a += 4;
+ b += 4;
+ c += 4;
+ }
+
+ number = quarterPoints * 4;
+
+ for(; number < num_points; number++) {
+ *c++ = (*a++) * (*b++);
+ }
+}
+#endif /* LV_HAVE_AVX */
+
#ifdef LV_HAVE_SSE3
#include <pmmintrin.h>
/*!
@@ -83,6 +154,55 @@ static inline void volk_32fc_x2_multiply_32fc_generic(lv_32fc_t* cVector, const
#include <volk/volk_complex.h>
#include <float.h>
+#ifdef LV_HAVE_AVX
+#include <immintrin.h>
+ /*!
+ \brief Multiplies the two input complex vectors and stores their results in the third vector
+ \param cVector The vector where the results will be stored
+ \param aVector One of the vectors to be multiplied
+ \param bVector One of the vectors to be multiplied
+ \param num_points The number of complex values in aVector and bVector to be multiplied together and stored into cVector
+ */
+static inline void volk_32fc_x2_multiply_32fc_a_avx(lv_32fc_t* cVector, const lv_32fc_t* aVector, const lv_32fc_t* bVector, unsigned int num_points){
+ unsigned int number = 0;
+ const unsigned int quarterPoints = num_points / 4;
+
+ __m256 x, y, yl, yh, z, tmp1, tmp2;
+ lv_32fc_t* c = cVector;
+ const lv_32fc_t* a = aVector;
+ const lv_32fc_t* b = bVector;
+
+ for(;number < quarterPoints; number++){
+
+ x = _mm256_load_ps((float*)a); // Load the ar + ai, br + bi ... as ar,ai,br,bi ...
+ y = _mm256_load_ps((float*)b); // Load the cr + ci, dr + di ... as cr,ci,dr,di ...
+
+ yl = _mm256_moveldup_ps(y); // Load yl with cr,cr,dr,dr ...
+ yh = _mm256_movehdup_ps(y); // Load yh with ci,ci,di,di ...
+
+ tmp1 = _mm256_mul_ps(x,yl); // tmp1 = ar*cr,ai*cr,br*dr,bi*dr ...
+
+ x = _mm256_shuffle_ps(x,x,0xB1); // Re-arrange x to be ai,ar,bi,br ...
+
+ tmp2 = _mm256_mul_ps(x,yh); // tmp2 = ai*ci,ar*ci,bi*di,br*di
+
+ z = _mm256_addsub_ps(tmp1,tmp2); // ar*cr-ai*ci, ai*cr+ar*ci, br*dr-bi*di, bi*dr+br*di
+
+ _mm256_store_ps((float*)c,z); // Store the results back into the C container
+
+ a += 4;
+ b += 4;
+ c += 4;
+ }
+
+ number = quarterPoints * 4;
+
+ for(; number < num_points; number++) {
+ *c++ = (*a++) * (*b++);
+ }
+}
+#endif /* LV_HAVE_AVX */
+
#ifdef LV_HAVE_SSE3
#include <pmmintrin.h>
/*!
diff --git a/volk/kernels/volk/volk_32fc_x2_multiply_conjugate_32fc.h b/volk/kernels/volk/volk_32fc_x2_multiply_conjugate_32fc.h
index dbc123ff25..c9b3bbc70b 100644
--- a/volk/kernels/volk/volk_32fc_x2_multiply_conjugate_32fc.h
+++ b/volk/kernels/volk/volk_32fc_x2_multiply_conjugate_32fc.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32fc_x2_multiply_conjugate_32fc_u_H
#define INCLUDED_volk_32fc_x2_multiply_conjugate_32fc_u_H
@@ -6,6 +28,59 @@
#include <volk/volk_complex.h>
#include <float.h>
+#ifdef LV_HAVE_AVX
+#include <immintrin.h>
+ /*!
+ \brief Multiplies vector a by the conjugate of vector b and stores the results in the third vector
+ \param cVector The vector where the results will be stored
+ \param aVector First vector to be multiplied
+ \param bVector Second vector that is conjugated before being multiplied
+ \param num_points The number of complex values in aVector and bVector to be multiplied together and stored into cVector
+ */
+static inline void volk_32fc_x2_multiply_conjugate_32fc_u_avx(lv_32fc_t* cVector, const lv_32fc_t* aVector, const lv_32fc_t* bVector, unsigned int num_points){
+ unsigned int number = 0;
+ const unsigned int quarterPoints = num_points / 4;
+
+ __m256 x, y, yl, yh, z, tmp1, tmp2;
+ lv_32fc_t* c = cVector;
+ const lv_32fc_t* a = aVector;
+ const lv_32fc_t* b = bVector;
+
+ __m256 conjugator = _mm256_setr_ps(0, -0.f, 0, -0.f, 0, -0.f, 0, -0.f);
+
+ for(;number < quarterPoints; number++){
+
+ x = _mm256_loadu_ps((float*)a); // Load the ar + ai, br + bi ... as ar,ai,br,bi ...
+ y = _mm256_loadu_ps((float*)b); // Load the cr + ci, dr + di ... as cr,ci,dr,di ...
+
+ y = _mm256_xor_ps(y, conjugator); // conjugate y
+
+ yl = _mm256_moveldup_ps(y); // Load yl with cr,cr,dr,dr ...
+ yh = _mm256_movehdup_ps(y); // Load yh with ci,ci,di,di ...
+
+ tmp1 = _mm256_mul_ps(x,yl); // tmp1 = ar*cr,ai*cr,br*dr,bi*dr ...
+
+ x = _mm256_shuffle_ps(x,x,0xB1); // Re-arrange x to be ai,ar,bi,br ...
+
+ tmp2 = _mm256_mul_ps(x,yh); // tmp2 = ai*ci,ar*ci,bi*di,br*di ...
+
+ z = _mm256_addsub_ps(tmp1,tmp2); // ar*cr-ai*ci, ai*cr+ar*ci, br*dr-bi*di, bi*dr+br*di ...
+
+ _mm256_storeu_ps((float*)c,z); // Store the results back into the C container
+
+ a += 4;
+ b += 4;
+ c += 4;
+ }
+
+ number = quarterPoints * 4;
+
+ for(; number < num_points; number++) {
+ *c++ = (*a++) * lv_conj(*b++);
+ }
+}
+#endif /* LV_HAVE_AVX */
+
#ifdef LV_HAVE_SSE3
#include <pmmintrin.h>
/*!
@@ -87,6 +162,59 @@ static inline void volk_32fc_x2_multiply_conjugate_32fc_generic(lv_32fc_t* cVect
#include <volk/volk_complex.h>
#include <float.h>
+#ifdef LV_HAVE_AVX
+#include <immintrin.h>
+ /*!
+ \brief Multiplies vector a by the conjugate of vector b and stores the results in the third vector
+ \param cVector The vector where the results will be stored
+ \param aVector First vector to be multiplied
+ \param bVector Second vector that is conjugated before being multiplied
+ \param num_points The number of complex values in aVector and bVector to be multiplied together and stored into cVector
+ */
+static inline void volk_32fc_x2_multiply_conjugate_32fc_a_avx(lv_32fc_t* cVector, const lv_32fc_t* aVector, const lv_32fc_t* bVector, unsigned int num_points){
+ unsigned int number = 0;
+ const unsigned int quarterPoints = num_points / 4;
+
+ __m256 x, y, yl, yh, z, tmp1, tmp2;
+ lv_32fc_t* c = cVector;
+ const lv_32fc_t* a = aVector;
+ const lv_32fc_t* b = bVector;
+
+ __m256 conjugator = _mm256_setr_ps(0, -0.f, 0, -0.f, 0, -0.f, 0, -0.f);
+
+ for(;number < quarterPoints; number++){
+
+ x = _mm256_load_ps((float*)a); // Load the ar + ai, br + bi ... as ar,ai,br,bi ...
+ y = _mm256_load_ps((float*)b); // Load the cr + ci, dr + di ... as cr,ci,dr,di ...
+
+ y = _mm256_xor_ps(y, conjugator); // conjugate y
+
+ yl = _mm256_moveldup_ps(y); // Load yl with cr,cr,dr,dr ...
+ yh = _mm256_movehdup_ps(y); // Load yh with ci,ci,di,di ...
+
+ tmp1 = _mm256_mul_ps(x,yl); // tmp1 = ar*cr,ai*cr,br*dr,bi*dr ...
+
+ x = _mm256_shuffle_ps(x,x,0xB1); // Re-arrange x to be ai,ar,bi,br ...
+
+ tmp2 = _mm256_mul_ps(x,yh); // tmp2 = ai*ci,ar*ci,bi*di,br*di ...
+
+ z = _mm256_addsub_ps(tmp1,tmp2); // ar*cr-ai*ci, ai*cr+ar*ci, br*dr-bi*di, bi*dr+br*di ...
+
+ _mm256_store_ps((float*)c,z); // Store the results back into the C container
+
+ a += 4;
+ b += 4;
+ c += 4;
+ }
+
+ number = quarterPoints * 4;
+
+ for(; number < num_points; number++) {
+ *c++ = (*a++) * lv_conj(*b++);
+ }
+}
+#endif /* LV_HAVE_AVX */
+
#ifdef LV_HAVE_SSE3
#include <pmmintrin.h>
/*!
diff --git a/volk/kernels/volk/volk_32fc_x2_s32f_square_dist_scalar_mult_32f.h b/volk/kernels/volk/volk_32fc_x2_s32f_square_dist_scalar_mult_32f.h
index cb2e945015..a25a6866b7 100644
--- a/volk/kernels/volk/volk_32fc_x2_s32f_square_dist_scalar_mult_32f.h
+++ b/volk/kernels/volk/volk_32fc_x2_s32f_square_dist_scalar_mult_32f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32fc_x2_s32f_square_dist_scalar_mult_32f_a_H
#define INCLUDED_volk_32fc_x2_s32f_square_dist_scalar_mult_32f_a_H
diff --git a/volk/kernels/volk/volk_32fc_x2_square_dist_32f.h b/volk/kernels/volk/volk_32fc_x2_square_dist_32f.h
index 56b3d5c230..2984beaa17 100644
--- a/volk/kernels/volk/volk_32fc_x2_square_dist_32f.h
+++ b/volk/kernels/volk/volk_32fc_x2_square_dist_32f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32fc_x2_square_dist_32f_a_H
#define INCLUDED_volk_32fc_x2_square_dist_32f_a_H
diff --git a/volk/kernels/volk/volk_32i_s32f_convert_32f.h b/volk/kernels/volk/volk_32i_s32f_convert_32f.h
index 7a09883453..dd965bc9b2 100644
--- a/volk/kernels/volk/volk_32i_s32f_convert_32f.h
+++ b/volk/kernels/volk/volk_32i_s32f_convert_32f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32i_s32f_convert_32f_u_H
#define INCLUDED_volk_32i_s32f_convert_32f_u_H
diff --git a/volk/kernels/volk/volk_32i_x2_and_32i.h b/volk/kernels/volk/volk_32i_x2_and_32i.h
index 54ecb79812..c138540e69 100644
--- a/volk/kernels/volk/volk_32i_x2_and_32i.h
+++ b/volk/kernels/volk/volk_32i_x2_and_32i.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32i_x2_and_32i_a_H
#define INCLUDED_volk_32i_x2_and_32i_a_H
@@ -43,6 +65,40 @@ static inline void volk_32i_x2_and_32i_a_sse(int32_t* cVector, const int32_t* aV
}
#endif /* LV_HAVE_SSE */
+#ifdef LV_HAVE_NEON
+#include <arm_neon.h>
+/*!
+ \brief Ands the two input vectors and store their results in the third vector
+ \param cVector The vector where the results will be stored
+ \param aVector One of the vectors
+ \param bVector One of the vectors
+ \param num_points The number of values in aVector and bVector to be anded together and stored into cVector
+*/
+static inline void volk_32i_x2_and_32i_neon(int32_t* cVector, const int32_t* aVector, const int32_t* bVector, unsigned int num_points){
+ int32_t* cPtr = cVector;
+ const int32_t* aPtr = aVector;
+ const int32_t* bPtr= bVector;
+ unsigned int number = 0;
+ unsigned int quarter_points = num_points / 4;
+
+ int32x4_t a_val, b_val, c_val;
+
+ for(number = 0; number < quarter_points; number++){
+ a_val = vld1q_s32(aPtr);
+ b_val = vld1q_s32(bPtr);
+ c_val = vandq_s32(a_val, b_val);
+ vst1q_s32(cPtr, c_val);
+ aPtr += 4;
+ bPtr += 4;
+ cPtr += 4;
+ }
+
+ for(number = quarter_points * 4; number < num_points; number++){
+ *cPtr++ = (*aPtr++) & (*bPtr++);
+ }
+}
+#endif /* LV_HAVE_NEON */
+
#ifdef LV_HAVE_GENERIC
/*!
\brief Ands the two input vectors and store their results in the third vector
diff --git a/volk/kernels/volk/volk_32i_x2_or_32i.h b/volk/kernels/volk/volk_32i_x2_or_32i.h
index acadd5a57f..544a71c67c 100644
--- a/volk/kernels/volk/volk_32i_x2_or_32i.h
+++ b/volk/kernels/volk/volk_32i_x2_or_32i.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32i_x2_or_32i_a_H
#define INCLUDED_volk_32i_x2_or_32i_a_H
@@ -43,6 +65,40 @@ static inline void volk_32i_x2_or_32i_a_sse(int32_t* cVector, const int32_t* aVe
}
#endif /* LV_HAVE_SSE */
+#ifdef LV_HAVE_NEON
+#include <arm_neon.h>
+/*!
+ \brief Ands the two input vectors and store their results in the third vector
+ \param cVector The vector where the results will be stored
+ \param aVector One of the vectors
+ \param bVector One of the vectors
+ \param num_points The number of values in aVector and bVector to be anded together and stored into cVector
+*/
+static inline void volk_32i_x2_or_32i_neon(int32_t* cVector, const int32_t* aVector, const int32_t* bVector, unsigned int num_points){
+ int32_t* cPtr = cVector;
+ const int32_t* aPtr = aVector;
+ const int32_t* bPtr= bVector;
+ unsigned int number = 0;
+ unsigned int quarter_points = num_points / 4;
+
+ int32x4_t a_val, b_val, c_val;
+
+ for(number = 0; number < quarter_points; number++){
+ a_val = vld1q_s32(aPtr);
+ b_val = vld1q_s32(bPtr);
+ c_val = vorrq_s32(a_val, b_val);
+ vst1q_s32(cPtr, c_val);
+ aPtr += 4;
+ bPtr += 4;
+ cPtr += 4;
+ }
+
+ for(number = quarter_points * 4; number < num_points; number++){
+ *cPtr++ = (*aPtr++) | (*bPtr++);
+ }
+}
+#endif /* LV_HAVE_NEON */
+
#ifdef LV_HAVE_GENERIC
/*!
\brief Ors the two input vectors and store their results in the third vector
diff --git a/volk/kernels/volk/volk_32u_byteswap.h b/volk/kernels/volk/volk_32u_byteswap.h
index 8f6e3ad7b5..0194efc12c 100644
--- a/volk/kernels/volk/volk_32u_byteswap.h
+++ b/volk/kernels/volk/volk_32u_byteswap.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_32u_byteswap_u_H
#define INCLUDED_volk_32u_byteswap_u_H
@@ -51,6 +73,59 @@ static inline void volk_32u_byteswap_u_sse2(uint32_t* intsToSwap, unsigned int n
}
#endif /* LV_HAVE_SSE2 */
+#ifdef LV_HAVE_NEON
+#include <arm_neon.h>
+/*!
+ \brief Byteswaps (in-place) an aligned vector of int32_t's.
+ \param intsToSwap The vector of data to byte swap
+ \param numDataPoints The number of data points
+*/
+static inline void volk_32u_byteswap_neon(uint32_t* intsToSwap, unsigned int num_points){
+ uint32_t* inputPtr = intsToSwap;
+ unsigned int number = 0;
+ unsigned int n8points = num_points / 8;
+
+ uint8x8x4_t input_table;
+ uint8x8_t int_lookup01, int_lookup23, int_lookup45, int_lookup67;
+ uint8x8_t swapped_int01, swapped_int23, swapped_int45, swapped_int67;
+
+ /* these magic numbers are used as byte-indeces in the LUT.
+ they are pre-computed to save time. A simple C program
+ can calculate them; for example for lookup01:
+ uint8_t chars[8] = {24, 16, 8, 0, 25, 17, 9, 1};
+ for(ii=0; ii < 8; ++ii) {
+ index += ((uint64_t)(*(chars+ii))) << (ii*8);
+ }
+ */
+ int_lookup01 = vcreate_u8(74609667900706840);
+ int_lookup23 = vcreate_u8(219290013576860186);
+ int_lookup45 = vcreate_u8(363970359253013532);
+ int_lookup67 = vcreate_u8(508650704929166878);
+
+ for(number = 0; number < n8points; ++number){
+ input_table = vld4_u8((uint8_t*) inputPtr);
+ swapped_int01 = vtbl4_u8(input_table, int_lookup01);
+ swapped_int23 = vtbl4_u8(input_table, int_lookup23);
+ swapped_int45 = vtbl4_u8(input_table, int_lookup45);
+ swapped_int67 = vtbl4_u8(input_table, int_lookup67);
+ vst1_u8((uint8_t*) inputPtr, swapped_int01);
+ vst1_u8((uint8_t*) (inputPtr+2), swapped_int23);
+ vst1_u8((uint8_t*) (inputPtr+4), swapped_int45);
+ vst1_u8((uint8_t*) (inputPtr+6), swapped_int67);
+
+ inputPtr += 8;
+ }
+
+ for(number = n8points * 8; number < num_points; ++number){
+ uint32_t output = *inputPtr;
+ output = (((output >> 24) & 0xff) | ((output >> 8) & 0x0000ff00) | ((output << 8) & 0x00ff0000) | ((output << 24) & 0xff000000));
+
+ *inputPtr = output;
+ inputPtr++;
+ }
+}
+#endif /* LV_HAVE_NEON */
+
#ifdef LV_HAVE_GENERIC
/*!
\brief Byteswaps (in-place) an aligned vector of int32_t's.
@@ -72,8 +147,6 @@ static inline void volk_32u_byteswap_generic(uint32_t* intsToSwap, unsigned int
#endif /* LV_HAVE_GENERIC */
-
-
#endif /* INCLUDED_volk_32u_byteswap_u_H */
#ifndef INCLUDED_volk_32u_byteswap_a_H
#define INCLUDED_volk_32u_byteswap_a_H
diff --git a/volk/kernels/volk/volk_32u_byteswappuppet_32u.h b/volk/kernels/volk/volk_32u_byteswappuppet_32u.h
new file mode 100644
index 0000000000..bf7055e241
--- /dev/null
+++ b/volk/kernels/volk/volk_32u_byteswappuppet_32u.h
@@ -0,0 +1,45 @@
+#ifndef INCLUDED_volk_32u_byteswappuppet_32u_H
+#define INCLUDED_volk_32u_byteswappuppet_32u_H
+
+
+#include <stdint.h>
+#include <volk/volk_32u_byteswap.h>
+
+#ifdef LV_HAVE_GENERIC
+static inline void volk_32u_byteswappuppet_32u_generic(uint32_t*output, uint32_t* intsToSwap, unsigned int num_points){
+
+ volk_32u_byteswap_generic((uint32_t*)intsToSwap, num_points);
+ memcpy((void*)output, (void*)intsToSwap, num_points * sizeof(uint32_t));
+
+}
+#endif
+
+#ifdef LV_HAVE_NEON
+static inline void volk_32u_byteswappuppet_32u_neon(uint32_t*output, uint32_t* intsToSwap, unsigned int num_points){
+
+ volk_32u_byteswap_neon((uint32_t*)intsToSwap, num_points);
+ memcpy((void*)output, (void*)intsToSwap, num_points * sizeof(uint32_t));
+
+}
+#endif
+
+#ifdef LV_HAVE_SSE2
+static inline void volk_32u_byteswappuppet_32u_u_sse2(uint32_t *output, uint32_t* intsToSwap, unsigned int num_points){
+
+ volk_32u_byteswap_u_sse2((uint32_t*)intsToSwap, num_points);
+ memcpy((void*)output, (void*)intsToSwap, num_points * sizeof(uint32_t));
+
+}
+#endif
+
+#ifdef LV_HAVE_SSE2
+static inline void volk_32u_byteswappuppet_32u_a_sse2(uint32_t* output, uint32_t* intsToSwap, unsigned int num_points){
+
+ volk_32u_byteswap_a_sse2((uint32_t*)intsToSwap, num_points);
+ memcpy((void*)output, (void*)intsToSwap, num_points * sizeof(uint32_t));
+
+}
+#endif
+
+
+#endif
diff --git a/volk/kernels/volk/volk_32u_popcnt.h b/volk/kernels/volk/volk_32u_popcnt.h
index 9783569729..8d613754df 100644
--- a/volk/kernels/volk/volk_32u_popcnt.h
+++ b/volk/kernels/volk/volk_32u_popcnt.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_VOLK_32u_POPCNT_A16_H
#define INCLUDED_VOLK_32u_POPCNT_A16_H
diff --git a/volk/kernels/volk/volk_32u_popcntpuppet_32u.h b/volk/kernels/volk/volk_32u_popcntpuppet_32u.h
new file mode 100644
index 0000000000..d5edd35b81
--- /dev/null
+++ b/volk/kernels/volk/volk_32u_popcntpuppet_32u.h
@@ -0,0 +1,47 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
+#ifndef INCLUDED_volk_32u_popcntpuppet_32u_H
+#define INCLUDED_volk_32u_popcntpuppet_32u_H
+
+#include <stdint.h>
+#include <volk/volk_32u_popcnt.h>
+
+#ifdef LV_HAVE_GENERIC
+static inline void volk_32u_popcntpuppet_32u_generic(uint32_t* outVector, const uint32_t* inVector, unsigned int num_points){
+ unsigned int ii;
+ for(ii=0; ii < num_points; ++ii) {
+ volk_32u_popcnt_generic(outVector+ii, *(inVector+ii) );
+ }
+}
+#endif /* LV_HAVE_GENERIC */
+
+#ifdef LV_HAVE_SSE4_2
+static inline void volk_32u_popcntpuppet_32u_a_sse4_2(uint32_t* outVector, const uint32_t* inVector, unsigned int num_points){
+ unsigned int ii;
+ for(ii=0; ii < num_points; ++ii) {
+ volk_32u_popcnt_a_sse4_2(outVector+ii, *(inVector+ii) );
+ }
+}
+#endif /* LV_HAVE_SSE4_2 */
+
+#endif /* INCLUDED_volk_32fc_s32fc_rotatorpuppet_32fc_a_H */
diff --git a/volk/kernels/volk/volk_64f_convert_32f.h b/volk/kernels/volk/volk_64f_convert_32f.h
index c27526ffaf..39a7ae8fd0 100644
--- a/volk/kernels/volk/volk_64f_convert_32f.h
+++ b/volk/kernels/volk/volk_64f_convert_32f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_64f_convert_32f_u_H
#define INCLUDED_volk_64f_convert_32f_u_H
diff --git a/volk/kernels/volk/volk_64f_x2_max_64f.h b/volk/kernels/volk/volk_64f_x2_max_64f.h
index f9a04c2c40..7bf09e8514 100644
--- a/volk/kernels/volk/volk_64f_x2_max_64f.h
+++ b/volk/kernels/volk/volk_64f_x2_max_64f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_64f_x2_max_64f_a_H
#define INCLUDED_volk_64f_x2_max_64f_a_H
diff --git a/volk/kernels/volk/volk_64f_x2_min_64f.h b/volk/kernels/volk/volk_64f_x2_min_64f.h
index c77ca87fbd..8d8b377503 100644
--- a/volk/kernels/volk/volk_64f_x2_min_64f.h
+++ b/volk/kernels/volk/volk_64f_x2_min_64f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_64f_x2_min_64f_a_H
#define INCLUDED_volk_64f_x2_min_64f_a_H
diff --git a/volk/kernels/volk/volk_64u_byteswap.h b/volk/kernels/volk/volk_64u_byteswap.h
index e05daf6d5c..dce883278d 100644
--- a/volk/kernels/volk/volk_64u_byteswap.h
+++ b/volk/kernels/volk/volk_64u_byteswap.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_64u_byteswap_u_H
#define INCLUDED_volk_64u_byteswap_u_H
@@ -82,7 +104,62 @@ static inline void volk_64u_byteswap_generic(uint64_t* intsToSwap, unsigned int
}
#endif /* LV_HAVE_GENERIC */
+#ifdef LV_HAVE_NEON
+#include <arm_neon.h>
+/*!
+ \brief Byteswaps (in-place) a vector of int64_t's.
+ \param intsToSwap The vector of data to byte swap
+ \param numDataPoints The number of data points
+*/
+static inline void volk_64u_byteswap_neon(uint64_t* intsToSwap, unsigned int num_points){
+ uint32_t* inputPtr = (uint32_t*)intsToSwap;
+ unsigned int number = 0;
+ unsigned int n8points = num_points / 4;
+
+ uint8x8x4_t input_table;
+ uint8x8_t int_lookup01, int_lookup23, int_lookup45, int_lookup67;
+ uint8x8_t swapped_int01, swapped_int23, swapped_int45, swapped_int67;
+
+ /* these magic numbers are used as byte-indeces in the LUT.
+ they are pre-computed to save time. A simple C program
+ can calculate them; for example for lookup01:
+ uint8_t chars[8] = {24, 16, 8, 0, 25, 17, 9, 1};
+ for(ii=0; ii < 8; ++ii) {
+ index += ((uint64_t)(*(chars+ii))) << (ii*8);
+ }
+ */
+ int_lookup01 = vcreate_u8(2269495096316185);
+ int_lookup23 = vcreate_u8(146949840772469531);
+ int_lookup45 = vcreate_u8(291630186448622877);
+ int_lookup67 = vcreate_u8(436310532124776223);
+
+ for(number = 0; number < n8points; ++number){
+ input_table = vld4_u8((uint8_t*) inputPtr);
+ swapped_int01 = vtbl4_u8(input_table, int_lookup01);
+ swapped_int23 = vtbl4_u8(input_table, int_lookup23);
+ swapped_int45 = vtbl4_u8(input_table, int_lookup45);
+ swapped_int67 = vtbl4_u8(input_table, int_lookup67);
+ vst1_u8((uint8_t*) inputPtr, swapped_int01);
+ vst1_u8((uint8_t*) (inputPtr+2), swapped_int23);
+ vst1_u8((uint8_t*) (inputPtr+4), swapped_int45);
+ vst1_u8((uint8_t*) (inputPtr+6), swapped_int67);
+
+ inputPtr += 4;
+ }
+ for(number = n8points * 4; number < num_points; ++number){
+ uint32_t output1 = *inputPtr;
+ uint32_t output2 = inputPtr[1];
+
+ output1 = (((output1 >> 24) & 0xff) | ((output1 >> 8) & 0x0000ff00) | ((output1 << 8) & 0x00ff0000) | ((output1 << 24) & 0xff000000));
+ output2 = (((output2 >> 24) & 0xff) | ((output2 >> 8) & 0x0000ff00) | ((output2 << 8) & 0x00ff0000) | ((output2 << 24) & 0xff000000));
+
+ *inputPtr++ = output2;
+ *inputPtr++ = output1;
+ }
+
+}
+#endif /* LV_HAVE_NEON */
#endif /* INCLUDED_volk_64u_byteswap_u_H */
diff --git a/volk/kernels/volk/volk_64u_byteswappuppet_64u.h b/volk/kernels/volk/volk_64u_byteswappuppet_64u.h
new file mode 100644
index 0000000000..6733c5813a
--- /dev/null
+++ b/volk/kernels/volk/volk_64u_byteswappuppet_64u.h
@@ -0,0 +1,46 @@
+#ifndef INCLUDED_volk_64u_byteswappuppet_64u_H
+#define INCLUDED_volk_64u_byteswappuppet_64u_H
+
+
+#include <stdint.h>
+#include <volk/volk_64u_byteswap.h>
+#include <string.h>
+
+#ifdef LV_HAVE_GENERIC
+static inline void volk_64u_byteswappuppet_64u_generic(uint64_t*output, uint64_t* intsToSwap, unsigned int num_points){
+
+ volk_64u_byteswap_generic((uint64_t*)intsToSwap, num_points);
+ memcpy((void*)output, (void*)intsToSwap, num_points * sizeof(uint64_t));
+
+}
+#endif
+
+#ifdef LV_HAVE_NEON
+static inline void volk_64u_byteswappuppet_64u_neon(uint64_t*output, uint64_t* intsToSwap, unsigned int num_points){
+
+ volk_64u_byteswap_neon((uint64_t*)intsToSwap, num_points);
+ memcpy((void*)output, (void*)intsToSwap, num_points * sizeof(uint64_t));
+
+}
+#endif
+
+#ifdef LV_HAVE_SSE2
+static inline void volk_64u_byteswappuppet_64u_u_sse2(uint64_t* output, uint64_t* intsToSwap, unsigned int num_points){
+
+ volk_64u_byteswap_u_sse2((uint64_t*)intsToSwap, num_points);
+ memcpy((void*)output, (void*)intsToSwap, num_points * sizeof(uint64_t));
+
+}
+#endif
+
+#ifdef LV_HAVE_SSE2
+static inline void volk_64u_byteswappuppet_64u_a_sse2(uint64_t* output, uint64_t* intsToSwap, unsigned int num_points){
+
+ volk_64u_byteswap_a_sse2((uint64_t*)intsToSwap, num_points);
+ memcpy((void*)output, (void*)intsToSwap, num_points * sizeof(uint64_t));
+
+}
+#endif
+
+
+#endif
diff --git a/volk/kernels/volk/volk_64u_popcnt.h b/volk/kernels/volk/volk_64u_popcnt.h
index 466cfa5dad..0ec72e3404 100644
--- a/volk/kernels/volk/volk_64u_popcnt.h
+++ b/volk/kernels/volk/volk_64u_popcnt.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_64u_popcnt_a_H
#define INCLUDED_volk_64u_popcnt_a_H
@@ -49,4 +71,24 @@ static inline void volk_64u_popcnt_a_sse4_2(uint64_t* ret, const uint64_t value)
#endif /*LV_HAVE_SSE4_2*/
+#if LV_HAVE_NEON
+#include <arm_neon.h>
+static inline void volk_64u_popcnt_neon(uint64_t* ret, const uint64_t value) {
+ uint8x8_t input_val, count8x8_val;
+ uint16x4_t count16x4_val;
+ uint32x2_t count32x2_val;
+ uint64x1_t count64x1_val;
+
+ input_val = vld1_u8((unsigned char *) &value);
+ count8x8_val = vcnt_u8(input_val);
+ count16x4_val = vpaddl_u8(count8x8_val);
+ count32x2_val = vpaddl_u16(count16x4_val);
+ count64x1_val = vpaddl_u32(count32x2_val);
+ vst1_u64(ret, count64x1_val);
+
+ //*ret = _mm_popcnt_u64(value);
+
+}
+#endif /*LV_HAVE_NEON*/
+
#endif /*INCLUDED_volk_64u_popcnt_a_H*/
diff --git a/volk/kernels/volk/volk_64u_popcntpuppet_64u.h b/volk/kernels/volk/volk_64u_popcntpuppet_64u.h
new file mode 100644
index 0000000000..ae20ff497c
--- /dev/null
+++ b/volk/kernels/volk/volk_64u_popcntpuppet_64u.h
@@ -0,0 +1,58 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
+#ifndef INCLUDED_volk_64u_popcntpuppet_64u_H
+#define INCLUDED_volk_64u_popcntpuppet_64u_H
+
+#include <stdint.h>
+#include <volk/volk_64u_popcnt.h>
+
+#ifdef LV_HAVE_GENERIC
+static inline void volk_64u_popcntpuppet_64u_generic(uint64_t* outVector, const uint64_t* inVector, unsigned int num_points){
+ unsigned int ii;
+ for(ii=0; ii < num_points; ++ii) {
+ volk_64u_popcnt_generic(outVector+ii, num_points );
+
+ }
+}
+#endif /* LV_HAVE_GENERIC */
+
+#ifdef LV_HAVE_SSE4_2
+static inline void volk_64u_popcntpuppet_64u_a_sse4_2(uint64_t* outVector, const uint64_t* inVector, unsigned int num_points){
+ unsigned int ii;
+ for(ii=0; ii < num_points; ++ii) {
+ volk_64u_popcnt_a_sse4_2(outVector+ii, num_points );
+
+ }
+}
+#endif /* LV_HAVE_SSE4_2 */
+
+#ifdef LV_HAVE_NEON
+static inline void volk_64u_popcntpuppet_64u_neon(uint64_t* outVector, const uint64_t* inVector, unsigned int num_points){
+ unsigned int ii;
+ for(ii=0; ii < num_points; ++ii) {
+ volk_64u_popcnt_neon(outVector+ii, num_points );
+ }
+}
+#endif /* LV_HAVE_NEON */
+
+#endif /* INCLUDED_volk_32fc_s32fc_rotatorpuppet_32fc_a_H */
diff --git a/volk/kernels/volk/volk_8i_convert_16i.h b/volk/kernels/volk/volk_8i_convert_16i.h
index 9776dfdc66..549ba4e388 100644
--- a/volk/kernels/volk/volk_8i_convert_16i.h
+++ b/volk/kernels/volk/volk_8i_convert_16i.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_8i_convert_16i_u_H
#define INCLUDED_volk_8i_convert_16i_u_H
diff --git a/volk/kernels/volk/volk_8i_s32f_convert_32f.h b/volk/kernels/volk/volk_8i_s32f_convert_32f.h
index bd7ff82d9a..5e959c8692 100644
--- a/volk/kernels/volk/volk_8i_s32f_convert_32f.h
+++ b/volk/kernels/volk/volk_8i_s32f_convert_32f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_8i_s32f_convert_32f_u_H
#define INCLUDED_volk_8i_s32f_convert_32f_u_H
diff --git a/volk/kernels/volk/volk_8ic_deinterleave_16i_x2.h b/volk/kernels/volk/volk_8ic_deinterleave_16i_x2.h
index b59d22d186..818d309013 100644
--- a/volk/kernels/volk/volk_8ic_deinterleave_16i_x2.h
+++ b/volk/kernels/volk/volk_8ic_deinterleave_16i_x2.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_8ic_deinterleave_16i_x2_a_H
#define INCLUDED_volk_8ic_deinterleave_16i_x2_a_H
@@ -13,30 +35,31 @@
\param qBuffer The Q buffer output data
\param num_points The number of complex data values to be deinterleaved
*/
+
static inline void volk_8ic_deinterleave_16i_x2_a_sse4_1(int16_t* iBuffer, int16_t* qBuffer, const lv_8sc_t* complexVector, unsigned int num_points){
unsigned int number = 0;
const int8_t* complexVectorPtr = (int8_t*)complexVector;
int16_t* iBufferPtr = iBuffer;
int16_t* qBufferPtr = qBuffer;
- __m128i iMoveMask = _mm_set_epi8(0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 14, 12, 10, 8, 6, 4, 2, 0);
+ __m128i iMoveMask = _mm_set_epi8(0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 14, 12, 10, 8, 6, 4, 2, 0); // set 16 byte values
__m128i qMoveMask = _mm_set_epi8(0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 15, 13, 11, 9, 7, 5, 3, 1);
__m128i complexVal, iOutputVal, qOutputVal;
unsigned int eighthPoints = num_points / 8;
for(number = 0; number < eighthPoints; number++){
- complexVal = _mm_load_si128((__m128i*)complexVectorPtr); complexVectorPtr += 16;
+ complexVal = _mm_load_si128((__m128i*)complexVectorPtr); complexVectorPtr += 16; // aligned load
- iOutputVal = _mm_shuffle_epi8(complexVal, iMoveMask);
+ iOutputVal = _mm_shuffle_epi8(complexVal, iMoveMask); // shuffle 16 bytes of 128bit complexVal
qOutputVal = _mm_shuffle_epi8(complexVal, qMoveMask);
- iOutputVal = _mm_cvtepi8_epi16(iOutputVal);
- iOutputVal = _mm_slli_epi16(iOutputVal, 8);
+ iOutputVal = _mm_cvtepi8_epi16(iOutputVal); // fills 2-byte sign extended versions of lower 8 bytes of input to output
+ iOutputVal = _mm_slli_epi16(iOutputVal, 8); // shift in left by 8 bits, each of the 8 16-bit integers, shift in with zeros
qOutputVal = _mm_cvtepi8_epi16(qOutputVal);
qOutputVal = _mm_slli_epi16(qOutputVal, 8);
- _mm_store_si128((__m128i*)iBufferPtr, iOutputVal);
+ _mm_store_si128((__m128i*)iBufferPtr, iOutputVal); // aligned store
_mm_store_si128((__m128i*)qBufferPtr, qOutputVal);
iBufferPtr += 8;
@@ -45,12 +68,78 @@ static inline void volk_8ic_deinterleave_16i_x2_a_sse4_1(int16_t* iBuffer, int16
number = eighthPoints * 8;
for(; number < num_points; number++){
- *iBufferPtr++ = ((int16_t)*complexVectorPtr++) * 256;
+ *iBufferPtr++ = ((int16_t)*complexVectorPtr++) * 256; // load 8 bit Complexvector into 16 bit, shift left by 8 bits and store
*qBufferPtr++ = ((int16_t)*complexVectorPtr++) * 256;
}
}
#endif /* LV_HAVE_SSE4_1 */
+#ifdef LV_HAVE_AVX
+#include <immintrin.h>
+/*!
+ \brief Deinterleaves the complex 8 bit vector into I & Q 16 bit vector data
+ \param complexVector The complex input vector
+ \param iBuffer The I buffer output data
+ \param qBuffer The Q buffer output data
+ \param num_points The number of complex data values to be deinterleaved
+*/
+static inline void volk_8ic_deinterleave_16i_x2_a_avx(int16_t* iBuffer, int16_t* qBuffer, const lv_8sc_t* complexVector, unsigned int num_points){
+ unsigned int number = 0;
+ const int8_t* complexVectorPtr = (int8_t*)complexVector;
+ int16_t* iBufferPtr = iBuffer;
+ int16_t* qBufferPtr = qBuffer;
+ __m128i iMoveMask = _mm_set_epi8(0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 14, 12, 10, 8, 6, 4, 2, 0); // set 16 byte values
+ __m128i qMoveMask = _mm_set_epi8(0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 15, 13, 11, 9, 7, 5, 3, 1);
+ __m256i complexVal, iOutputVal, qOutputVal;
+ __m128i complexVal1, complexVal0;
+ __m128i iOutputVal1, iOutputVal0, qOutputVal1, qOutputVal0;
+
+ unsigned int sixteenthPoints = num_points / 16;
+
+ for(number = 0; number < sixteenthPoints; number++){
+ complexVal = _mm256_load_si256((__m256i*)complexVectorPtr); complexVectorPtr += 32; // aligned load
+
+ // Extract from complexVal to iOutputVal and qOutputVal
+ complexVal1 = _mm256_extractf128_si256(complexVal, 1);
+ complexVal0 = _mm256_extractf128_si256(complexVal, 0);
+
+ iOutputVal1 = _mm_shuffle_epi8(complexVal1, iMoveMask); // shuffle 16 bytes of 128bit complexVal
+ iOutputVal0 = _mm_shuffle_epi8(complexVal0, iMoveMask);
+ qOutputVal1 = _mm_shuffle_epi8(complexVal1, qMoveMask);
+ qOutputVal0 = _mm_shuffle_epi8(complexVal0, qMoveMask);
+
+ iOutputVal1 = _mm_cvtepi8_epi16(iOutputVal1); // fills 2-byte sign extended versions of lower 8 bytes of input to output
+ iOutputVal1 = _mm_slli_epi16(iOutputVal1, 8); // shift in left by 8 bits, each of the 8 16-bit integers, shift in with zeros
+ iOutputVal0 = _mm_cvtepi8_epi16(iOutputVal0);
+ iOutputVal0 = _mm_slli_epi16(iOutputVal0, 8);
+
+ qOutputVal1 = _mm_cvtepi8_epi16(qOutputVal1);
+ qOutputVal1 = _mm_slli_epi16(qOutputVal1, 8);
+ qOutputVal0 = _mm_cvtepi8_epi16(qOutputVal0);
+ qOutputVal0 = _mm_slli_epi16(qOutputVal0, 8);
+
+ // Pack iOutputVal0,1 to iOutputVal
+ __m256i dummy = _mm256_setzero_si256();
+ iOutputVal = _mm256_insertf128_si256(dummy, iOutputVal0, 0);
+ iOutputVal = _mm256_insertf128_si256(iOutputVal, iOutputVal1, 1);
+ qOutputVal = _mm256_insertf128_si256(dummy, qOutputVal0, 0);
+ qOutputVal = _mm256_insertf128_si256(qOutputVal, qOutputVal1, 1);
+
+ _mm256_store_si256((__m256i*)iBufferPtr, iOutputVal); // aligned store
+ _mm256_store_si256((__m256i*)qBufferPtr, qOutputVal);
+
+ iBufferPtr += 16;
+ qBufferPtr += 16;
+ }
+
+ number = sixteenthPoints * 16;
+ for(; number < num_points; number++){
+ *iBufferPtr++ = ((int16_t)*complexVectorPtr++) * 256; // load 8 bit Complexvector into 16 bit, shift left by 8 bits and store
+ *qBufferPtr++ = ((int16_t)*complexVectorPtr++) * 256;
+ }
+}
+#endif /* LV_HAVE_AVX */
+
#ifdef LV_HAVE_GENERIC
/*!
\brief Deinterleaves the complex 8 bit vector into I & Q 16 bit vector data
diff --git a/volk/kernels/volk/volk_8ic_deinterleave_real_16i.h b/volk/kernels/volk/volk_8ic_deinterleave_real_16i.h
index 82cedb2bb7..c22f828a88 100644
--- a/volk/kernels/volk/volk_8ic_deinterleave_real_16i.h
+++ b/volk/kernels/volk/volk_8ic_deinterleave_real_16i.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_8ic_deinterleave_real_16i_a_H
#define INCLUDED_volk_8ic_deinterleave_real_16i_a_H
@@ -41,6 +63,54 @@ static inline void volk_8ic_deinterleave_real_16i_a_sse4_1(int16_t* iBuffer, con
}
#endif /* LV_HAVE_SSE4_1 */
+#ifdef LV_HAVE_AVX
+#include <immintrin.h>
+/*!
+ \brief Deinterleaves the complex 8 bit vector into I 16 bit vector data
+ \param complexVector The complex input vector
+ \param iBuffer The I buffer output data
+ \param num_points The number of complex data values to be deinterleaved
+*/
+static inline void volk_8ic_deinterleave_real_16i_a_avx(int16_t* iBuffer, const lv_8sc_t* complexVector, unsigned int num_points){
+ unsigned int number = 0;
+ const int8_t* complexVectorPtr = (int8_t*)complexVector;
+ int16_t* iBufferPtr = iBuffer;
+ __m128i moveMask = _mm_set_epi8(0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 14, 12, 10, 8, 6, 4, 2, 0);
+ __m256i complexVal, outputVal;
+ __m128i complexVal1, complexVal0, outputVal1, outputVal0;
+
+ unsigned int sixteenthPoints = num_points / 16;
+
+ for(number = 0; number < sixteenthPoints; number++){
+ complexVal = _mm256_load_si256((__m256i*)complexVectorPtr); complexVectorPtr += 32;
+
+ complexVal1 = _mm256_extractf128_si256(complexVal, 1);
+ complexVal0 = _mm256_extractf128_si256(complexVal, 0);
+
+ outputVal1 = _mm_shuffle_epi8(complexVal1, moveMask);
+ outputVal0 = _mm_shuffle_epi8(complexVal0, moveMask);
+
+ outputVal1 = _mm_cvtepi8_epi16(outputVal1);
+ outputVal1 = _mm_slli_epi16(outputVal1, 7);
+ outputVal0 = _mm_cvtepi8_epi16(outputVal0);
+ outputVal0 = _mm_slli_epi16(outputVal0, 7);
+
+ __m256i dummy = _mm256_setzero_si256();
+ outputVal = _mm256_insertf128_si256(dummy, outputVal0, 0);
+ outputVal = _mm256_insertf128_si256(outputVal, outputVal1, 1);
+ _mm256_store_si256((__m256i*)iBufferPtr, outputVal);
+
+ iBufferPtr += 16;
+ }
+
+ number = sixteenthPoints * 16;
+ for(; number < num_points; number++){
+ *iBufferPtr++ = ((int16_t)*complexVectorPtr++) * 128;
+ complexVectorPtr++;
+ }
+}
+#endif /* LV_HAVE_AVX */
+
#ifdef LV_HAVE_GENERIC
/*!
diff --git a/volk/kernels/volk/volk_8ic_deinterleave_real_8i.h b/volk/kernels/volk/volk_8ic_deinterleave_real_8i.h
index 427c9abf55..e333306fac 100644
--- a/volk/kernels/volk/volk_8ic_deinterleave_real_8i.h
+++ b/volk/kernels/volk/volk_8ic_deinterleave_real_8i.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_VOLK_8sc_DEINTERLEAVE_REAL_8s_ALIGNED8_H
#define INCLUDED_VOLK_8sc_DEINTERLEAVE_REAL_8s_ALIGNED8_H
@@ -43,6 +65,64 @@ static inline void volk_8ic_deinterleave_real_8i_a_ssse3(int8_t* iBuffer, const
}
#endif /* LV_HAVE_SSSE3 */
+#ifdef LV_HAVE_AVX
+#include <immintrin.h>
+/*!
+ \brief Deinterleaves the complex 8 bit vector into I vector data
+ \param complexVector The complex input vector
+ \param iBuffer The I buffer output data
+ \param num_points The number of complex data values to be deinterleaved
+*/
+
+static inline void volk_8ic_deinterleave_real_8i_a_avx(int8_t* iBuffer, const lv_8sc_t* complexVector, unsigned int num_points){
+ unsigned int number = 0;
+ const int8_t* complexVectorPtr = (int8_t*)complexVector;
+ int8_t* iBufferPtr = iBuffer;
+ __m128i moveMaskL = _mm_set_epi8(0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 14, 12, 10, 8, 6, 4, 2, 0);
+ __m128i moveMaskH = _mm_set_epi8(14, 12, 10, 8, 6, 4, 2, 0, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80);
+ __m256i complexVal1, complexVal2, outputVal;
+ __m128i complexVal1H, complexVal1L, complexVal2H, complexVal2L, outputVal1, outputVal2;
+
+ unsigned int thirtysecondPoints = num_points / 32;
+
+ for(number = 0; number < thirtysecondPoints; number++){
+
+ complexVal1 = _mm256_load_si256((__m256i*)complexVectorPtr);
+ complexVectorPtr += 32;
+ complexVal2 = _mm256_load_si256((__m256i*)complexVectorPtr);
+ complexVectorPtr += 32;
+
+ complexVal1H = _mm256_extractf128_si256(complexVal1, 1);
+ complexVal1L = _mm256_extractf128_si256(complexVal1, 0);
+ complexVal2H = _mm256_extractf128_si256(complexVal2, 1);
+ complexVal2L = _mm256_extractf128_si256(complexVal2, 0);
+
+ complexVal1H = _mm_shuffle_epi8(complexVal1H, moveMaskH);
+ complexVal1L = _mm_shuffle_epi8(complexVal1L, moveMaskL);
+ outputVal1 = _mm_or_si128(complexVal1H, complexVal1L);
+
+
+ complexVal2H = _mm_shuffle_epi8(complexVal2H, moveMaskH);
+ complexVal2L = _mm_shuffle_epi8(complexVal2L, moveMaskL);
+ outputVal2 = _mm_or_si128(complexVal2H, complexVal2L);
+
+ __m256i dummy = _mm256_setzero_si256();
+ outputVal = _mm256_insertf128_si256(dummy, outputVal1, 0);
+ outputVal = _mm256_insertf128_si256(outputVal, outputVal2, 1);
+
+
+ _mm256_store_si256((__m256i*)iBufferPtr, outputVal);
+ iBufferPtr += 32;
+ }
+
+ number = thirtysecondPoints * 32;
+ for(; number < num_points; number++){
+ *iBufferPtr++ = *complexVectorPtr++;
+ complexVectorPtr++;
+ }
+}
+#endif /* LV_HAVE_AVX */
+
#ifdef LV_HAVE_GENERIC
/*!
\brief Deinterleaves the complex 8 bit vector into I vector data
diff --git a/volk/kernels/volk/volk_8ic_s32f_deinterleave_32f_x2.h b/volk/kernels/volk/volk_8ic_s32f_deinterleave_32f_x2.h
index 9e244c8fc2..a6115482ec 100644
--- a/volk/kernels/volk/volk_8ic_s32f_deinterleave_32f_x2.h
+++ b/volk/kernels/volk/volk_8ic_s32f_deinterleave_32f_x2.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_8ic_s32f_deinterleave_32f_x2_a_H
#define INCLUDED_volk_8ic_s32f_deinterleave_32f_x2_a_H
diff --git a/volk/kernels/volk/volk_8ic_s32f_deinterleave_real_32f.h b/volk/kernels/volk/volk_8ic_s32f_deinterleave_real_32f.h
index 56a1adcbb5..bbe2c26b70 100644
--- a/volk/kernels/volk/volk_8ic_s32f_deinterleave_real_32f.h
+++ b/volk/kernels/volk/volk_8ic_s32f_deinterleave_real_32f.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_8ic_s32f_deinterleave_real_32f_a_H
#define INCLUDED_volk_8ic_s32f_deinterleave_real_32f_a_H
diff --git a/volk/kernels/volk/volk_8ic_x2_multiply_conjugate_16ic.h b/volk/kernels/volk/volk_8ic_x2_multiply_conjugate_16ic.h
index 685a21ddcd..5b64c5218c 100644
--- a/volk/kernels/volk/volk_8ic_x2_multiply_conjugate_16ic.h
+++ b/volk/kernels/volk/volk_8ic_x2_multiply_conjugate_16ic.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_8ic_x2_multiply_conjugate_16ic_a_H
#define INCLUDED_volk_8ic_x2_multiply_conjugate_16ic_a_H
diff --git a/volk/kernels/volk/volk_8ic_x2_s32f_multiply_conjugate_32fc.h b/volk/kernels/volk/volk_8ic_x2_s32f_multiply_conjugate_32fc.h
index edb52ff509..d6cc1f09cd 100644
--- a/volk/kernels/volk/volk_8ic_x2_s32f_multiply_conjugate_32fc.h
+++ b/volk/kernels/volk/volk_8ic_x2_s32f_multiply_conjugate_32fc.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_8ic_x2_s32f_multiply_conjugate_32fc_a_H
#define INCLUDED_volk_8ic_x2_s32f_multiply_conjugate_32fc_a_H
diff --git a/volk/kernels/volk/volk_8u_conv_k7_r2puppet_8u.h b/volk/kernels/volk/volk_8u_conv_k7_r2puppet_8u.h
index 8d31e469f2..b398556ca8 100644
--- a/volk/kernels/volk/volk_8u_conv_k7_r2puppet_8u.h
+++ b/volk/kernels/volk/volk_8u_conv_k7_r2puppet_8u.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_8u_conv_k7_r2puppet_8u_H
#define INCLUDED_volk_8u_conv_k7_r2puppet_8u_H
diff --git a/volk/kernels/volk/volk_8u_x4_conv_k7_r2_8u.h b/volk/kernels/volk/volk_8u_x4_conv_k7_r2_8u.h
index ece8cf0f48..e21dfe1e01 100644
--- a/volk/kernels/volk/volk_8u_x4_conv_k7_r2_8u.h
+++ b/volk/kernels/volk/volk_8u_x4_conv_k7_r2_8u.h
@@ -1,3 +1,25 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2014 Free Software Foundation, Inc.
+ *
+ * This file is part of GNU Radio
+ *
+ * GNU Radio is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * GNU Radio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Radio; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street,
+ * Boston, MA 02110-1301, USA.
+ */
+
#ifndef INCLUDED_volk_8u_x4_conv_k7_r2_8u_H
#define INCLUDED_volk_8u_x4_conv_k7_r2_8u_H
diff --git a/volk/lib/CMakeLists.txt b/volk/lib/CMakeLists.txt
index 6cc4504cfa..37915e5552 100644
--- a/volk/lib/CMakeLists.txt
+++ b/volk/lib/CMakeLists.txt
@@ -406,10 +406,8 @@ if(${CMAKE_VERSION} VERSION_GREATER "2.8.9")
# if we find one that matches our current system architecture
# set up the assembler flags and include the source files
foreach(ARCH ${ASM_ARCHS_AVAILABLE})
- message(STATUS "--==>> -CFLAGS1: ${FULL_C_FLAGS}")
string(REGEX MATCH "${ARCH}" ASM_ARCH "${FULL_C_FLAGS}")
if( ASM_ARCH STREQUAL "armv7" )
- set(ASM-ATT $ENV{ASM})
message(STATUS "---- Adding ASM files") # we always use ATT syntax
message(STATUS "-- Detected armv7 architecture; enabling ASM")
# setup architecture specific assembler flags
@@ -422,13 +420,20 @@ if(${CMAKE_VERSION} VERSION_GREATER "2.8.9")
message(STATUS "Adding source file: ${asm_file}")
endforeach(asm_file)
endif()
- set(CMAKE_ASM-ATT_FLAGS_INIT ${ARCH_ASM_FLAGS})
- enable_language(ASM-ATT) # this must be after flags_init
- message(STATUS "asm flags: ${CMAKE_ASM-ATT_FLAGS}")
+ enable_language(ASM)
+ set(CMAKE_ASM_FLAGS ${ARCH_ASM_FLAGS})
+ message(STATUS "c flags: ${FULL_C_FLAGS}")
+ message(STATUS "asm flags: ${CMAKE_ASM_FLAGS}")
endforeach(ARCH)
else(${CMAKE_VERSION} VERSION_GREATER "2.8.9")
message(STATUS "Not enabling ASM support. CMake >= 2.8.10 required.")
+ foreach(machine_name ${available_machines})
+ string(REGEX MATCH "neon" NEON_MACHINE ${machine_name})
+ if( NEON_MACHINE STREQUAL "neon")
+ message(FATAL_ERROR "CMake >= 2.8.10 is required for ARM NEON support")
+ endif()
+ endforeach()
endif(${CMAKE_VERSION} VERSION_GREATER "2.8.9")
########################################################################
diff --git a/volk/lib/qa_utils.cc b/volk/lib/qa_utils.cc
index f30f0097ae..be20ed6585 100644
--- a/volk/lib/qa_utils.cc
+++ b/volk/lib/qa_utils.cc
@@ -5,7 +5,9 @@
#include <boost/tokenizer.hpp>
#include <boost/xpressive/xpressive.hpp>
#include <iostream>
+#include <fstream>
#include <vector>
+#include <map>
#include <list>
#include <ctime>
#include <cmath>
@@ -245,7 +247,7 @@ bool fcompare(t *in1, t *in2, unsigned int vlen, float tol) {
}
}
// the primary test is the percent different greater than given tol
- else if(fabs(((t *)(in1))[i] - ((t *)(in2))[i])/(((t *)in1)[i]) > tol) {
+ else if(fabs(((t *)(in1))[i] - ((t *)(in2))[i])/fabs(((t *)in1)[i]) > tol) {
fail=true;
if(print_max_errs-- > 0) {
std::cout << "offset " << i << " in1: " << t(((t *)(in1))[i]) << " in2: " << t(((t *)(in2))[i]) << std::endl;
@@ -328,9 +330,9 @@ bool run_volk_tests(volk_func_desc_t desc,
lv_32fc_t scalar,
int vlen,
int iter,
- std::vector<std::string> *best_arch_vector = 0,
- std::string puppet_master_name = "NULL",
- bool benchmark_mode,
+ std::vector<volk_test_results_t> *results,
+ std::string puppet_master_name,
+ bool benchmark_mode,
std::string kernel_regex
) {
boost::xpressive::sregex kernel_expression = boost::xpressive::sregex::compile(kernel_regex);
@@ -338,6 +340,12 @@ bool run_volk_tests(volk_func_desc_t desc,
// in this case we have a regex and are only looking to test one kernel
return false;
}
+ if(results) {
+ results->push_back(volk_test_results_t());
+ results->back().name = name;
+ results->back().vlen = vlen;
+ results->back().iter = iter;
+ }
std::cout << "RUN_VOLK_TESTS: " << name << "(" << vlen << "," << iter << ")" << std::endl;
// The multiply and lv_force_cast_hf are work arounds for GNU Radio bugs 582 and 583
@@ -453,6 +461,13 @@ bool run_volk_tests(volk_func_desc_t desc,
end = clock();
double arch_time = 1000.0 * (double)(end-start)/(double)CLOCKS_PER_SEC;
std::cout << arch_list[i] << " completed in " << arch_time << "ms" << std::endl;
+ if(results) {
+ volk_test_time_t result;
+ result.name = arch_list[i];
+ result.time = arch_time;
+ result.units = "ms";
+ results->back().results[result.name] = result;
+ }
profile_times.push_back(arch_time);
}
@@ -553,13 +568,14 @@ bool run_volk_tests(volk_func_desc_t desc,
std::cout << "Best aligned arch: " << best_arch_a << std::endl;
std::cout << "Best unaligned arch: " << best_arch_u << std::endl;
- if(best_arch_vector) {
+ if(results) {
if(puppet_master_name == "NULL") {
- best_arch_vector->push_back(name + " " + best_arch_a + " " + best_arch_u);
- }
- else {
- best_arch_vector->push_back(puppet_master_name + " " + best_arch_a + " " + best_arch_u);
+ results->back().config_name = name;
+ } else {
+ results->back().config_name = puppet_master_name;
}
+ results->back().best_arch_a = best_arch_a;
+ results->back().best_arch_u = best_arch_u;
}
return fail_global;
diff --git a/volk/lib/qa_utils.h b/volk/lib/qa_utils.h
index fc1a0239eb..7ca8b8d1e8 100644
--- a/volk/lib/qa_utils.h
+++ b/volk/lib/qa_utils.h
@@ -3,7 +3,10 @@
#include <cstdlib>
#include <string>
+#include <iostream>
+#include <fstream>
#include <vector>
+#include <map>
#include <volk/volk.h>
#include <volk/volk_common.h>
@@ -21,10 +24,46 @@ volk_type_t volk_type_from_string(std::string);
float uniform(void);
void random_floats(float *buf, unsigned n);
-bool run_volk_tests(volk_func_desc_t, void(*)(), std::string, float, lv_32fc_t, int, int, std::vector<std::string> *, std::string, bool benchmark_mode=false, std::string kernel_regex="");
+class volk_test_time_t {
+ public:
+ std::string name;
+ double time;
+ std::string units;
+};
+
+class volk_test_results_t {
+ public:
+ std::string name;
+ std::string config_name;
+ int vlen;
+ int iter;
+ std::map<std::string, volk_test_time_t> results;
+ std::string best_arch_a;
+ std::string best_arch_u;
+};
+
+bool run_volk_tests(
+ volk_func_desc_t,
+ void(*)(),
+ std::string,
+ float,
+ lv_32fc_t,
+ int,
+ int,
+ std::vector<volk_test_results_t> *results = NULL,
+ std::string puppet_master_name = "NULL",
+ bool benchmark_mode=false,
+ std::string kernel_regex=""
+ );
-#define VOLK_RUN_TESTS(func, tol, scalar, len, iter) BOOST_AUTO_TEST_CASE(func##_test) { BOOST_CHECK_EQUAL(run_volk_tests(func##_get_func_desc(), (void (*)())func##_manual, std::string(#func), tol, scalar, len, iter, 0, "NULL"), 0); }
+#define VOLK_RUN_TESTS(func, tol, scalar, len, iter) \
+ BOOST_AUTO_TEST_CASE(func##_test) { \
+ BOOST_CHECK_EQUAL(run_volk_tests( \
+ func##_get_func_desc(), (void (*)())func##_manual, \
+ std::string(#func), tol, scalar, len, iter, 0, "NULL"), \
+ 0); \
+ }
#define VOLK_PROFILE(func, tol, scalar, len, iter, results, bnmode, kernel_regex) run_volk_tests(func##_get_func_desc(), (void (*)())func##_manual, std::string(#func), tol, scalar, len, iter, results, "NULL", bnmode, kernel_regex)
#define VOLK_PUPPET_PROFILE(func, puppet_master_func, tol, scalar, len, iter, results, bnmode, kernel_regex) run_volk_tests(func##_get_func_desc(), (void (*)())func##_manual, std::string(#func), tol, scalar, len, iter, results, std::string(#puppet_master_func), bnmode, kernel_regex)
typedef void (*volk_fn_1arg)(void *, unsigned int, const char*); //one input, operate in place
diff --git a/volk/lib/testqa.cc b/volk/lib/testqa.cc
index bc97ad16e5..7807ce40a6 100644
--- a/volk/lib/testqa.cc
+++ b/volk/lib/testqa.cc
@@ -44,6 +44,15 @@ VOLK_RUN_TESTS(volk_16u_byteswap, 0, 0, 20462, 1);
VOLK_RUN_TESTS(volk_32f_accumulator_s32f, 1e-4, 0, 20462, 1);
VOLK_RUN_TESTS(volk_32f_x2_add_32f, 1e-4, 0, 20462, 1);
VOLK_RUN_TESTS(volk_32fc_32f_multiply_32fc, 1e-4, 0, 20462, 1);
+VOLK_RUN_TESTS(volk_32f_log2_32f, 1.5e-1, 0, 20462, 1);
+VOLK_RUN_TESTS(volk_32f_expfast_32f, 1e-1, 0, 20462, 1);
+VOLK_RUN_TESTS(volk_32f_x2_pow_32f, 1e-2, 0, 20462, 1);
+VOLK_RUN_TESTS(volk_32f_sin_32f, 1e-6, 0, 20462, 1);
+VOLK_RUN_TESTS(volk_32f_cos_32f, 1e-6, 0, 20462, 1);
+VOLK_RUN_TESTS(volk_32f_tan_32f, 1e-6, 0, 20462, 1);
+VOLK_RUN_TESTS(volk_32f_atan_32f, 1e-3, 0, 20462, 1);
+VOLK_RUN_TESTS(volk_32f_asin_32f, 1e-3, 0, 20462, 1);
+VOLK_RUN_TESTS(volk_32f_acos_32f, 1e-3, 0, 20462, 1);
VOLK_RUN_TESTS(volk_32fc_s32f_power_32fc, 1e-4, 0, 20462, 1);
VOLK_RUN_TESTS(volk_32f_s32f_calc_spectral_noise_floor_32f, 1e-4, 20.0, 20462, 1);
VOLK_RUN_TESTS(volk_32fc_s32f_atan2_32f, 1e-4, 10.0, 20462, 1);
@@ -88,12 +97,12 @@ VOLK_RUN_TESTS(volk_32i_x2_and_32i, 0, 0, 20462, 1);
VOLK_RUN_TESTS(volk_32i_s32f_convert_32f, 1e-4, 100, 20462, 1);
VOLK_RUN_TESTS(volk_32i_x2_or_32i, 0, 0, 20462, 1);
VOLK_RUN_TESTS(volk_32u_byteswap, 0, 0, 20462, 1);
-//VOLK_RUN_TESTS(volk_32u_popcnt, 0, 0, 2046, 10000);
+VOLK_RUN_TESTS(volk_32u_popcntpuppet_32u, 0, 0, 2046, 10000);
VOLK_RUN_TESTS(volk_64f_convert_32f, 1e-4, 0, 20462, 1);
VOLK_RUN_TESTS(volk_64f_x2_max_64f, 1e-4, 0, 20462, 1);
VOLK_RUN_TESTS(volk_64f_x2_min_64f, 1e-4, 0, 20462, 1);
VOLK_RUN_TESTS(volk_64u_byteswap, 0, 0, 20462, 1);
-//VOLK_RUN_TESTS(volk_64u_popcnt, 0, 0, 2046, 10000);
+VOLK_RUN_TESTS(volk_64u_popcntpuppet_64u, 0, 0, 2046, 10000);
VOLK_RUN_TESTS(volk_8ic_deinterleave_16i_x2, 0, 0, 20462, 1);
VOLK_RUN_TESTS(volk_8ic_s32f_deinterleave_32f_x2, 1e-4, 100, 20462, 1);
VOLK_RUN_TESTS(volk_8ic_deinterleave_real_16i, 0, 256, 20462, 1);
@@ -114,3 +123,4 @@ VOLK_RUN_TESTS(volk_8u_conv_k7_r2puppet_8u, 0, 0, 2060, 1);
VOLK_RUN_TESTS(volk_32f_invsqrt_32f, 1e-2, 0, 20462, 1);
VOLK_RUN_TESTS(volk_32f_binary_slicer_32i, 0, 0, 20462, 1);
VOLK_RUN_TESTS(volk_32f_binary_slicer_8i, 0, 0, 20462, 1);
+VOLK_RUN_TESTS(volk_32f_tanh_32f, 1e-6, 0, 20462, 1);