diff options
46 files changed, 2297 insertions, 713 deletions
diff --git a/cmake/Modules/FindPortaudio.cmake b/cmake/Modules/FindPortaudio.cmake index 20145ea8df..8aa17d4448 100644 --- a/cmake/Modules/FindPortaudio.cmake +++ b/cmake/Modules/FindPortaudio.cmake @@ -34,13 +34,13 @@ mark_as_advanced(PORTAUDIO_INCLUDE_DIRS PORTAUDIO_LIBRARIES) # Found PORTAUDIO, but it may be version 18 which is not acceptable. if(EXISTS ${PORTAUDIO_INCLUDE_DIRS}/portaudio.h) include(CheckCXXSourceCompiles) - include(CMakePushCheckState) - cmake_push_check_state() + set(CMAKE_REQUIRED_INCLUDES_SAVED ${CMAKE_REQUIRED_INCLUDES}) set(CMAKE_REQUIRED_INCLUDES ${PORTAUDIO_INCLUDE_DIRS}) CHECK_CXX_SOURCE_COMPILES( "#include <portaudio.h>\nPaDeviceIndex pa_find_device_by_name(const char *name); int main () {return 0;}" PORTAUDIO2_FOUND) - cmake_pop_check_state() + set(CMAKE_REQUIRED_INCLUDES ${CMAKE_REQUIRED_INCLUDES_SAVED}) + unset(CMAKE_REQUIRED_INCLUDES_SAVED) if(PORTAUDIO2_FOUND) INCLUDE(FindPackageHandleStandardArgs) FIND_PACKAGE_HANDLE_STANDARD_ARGS(PORTAUDIO DEFAULT_MSG PORTAUDIO_INCLUDE_DIRS PORTAUDIO_LIBRARIES) diff --git a/cmake/Modules/GrBuildTypes.cmake b/cmake/Modules/GrBuildTypes.cmake index aa59d0089f..8d6f08b7af 100644 --- a/cmake/Modules/GrBuildTypes.cmake +++ b/cmake/Modules/GrBuildTypes.cmake @@ -53,10 +53,12 @@ list(APPEND AVAIL_BUILDTYPES # the avialable build types. ######################################################################## function(GR_CHECK_BUILD_TYPE settype) + STRING(TOUPPER ${settype} _settype) foreach(btype ${AVAIL_BUILDTYPES}) - if(${settype} STREQUAL ${btype}) + STRING(TOUPPER ${btype} _btype) + if(${_settype} STREQUAL ${_btype}) return() # found it; exit cleanly - endif(${settype} STREQUAL ${btype}) + endif(${_settype} STREQUAL ${_btype}) endforeach(btype) # Build type not found; error out message(FATAL_ERROR "Build type '${settype}' not valid, must be one of: ${AVAIL_BUILDTYPES}") diff --git a/cmake/Modules/GrComponent.cmake b/cmake/Modules/GrComponent.cmake index f802cdcb41..5be3e8125d 100644 --- a/cmake/Modules/GrComponent.cmake +++ b/cmake/Modules/GrComponent.cmake @@ -46,9 +46,8 @@ function(GR_REGISTER_COMPONENT name var) message(STATUS " Dependency ${dep} = ${${dep}}") endforeach(dep) - #if the user set the var to force, we note this - if("${${var}}" STREQUAL "FORCE") - set(${var} ON) + #if the user set the var to force on, we note this + if("${${var}}" STREQUAL "ON") set(var_force TRUE) else() set(var_force FALSE) diff --git a/cmake/Modules/GrMiscUtils.cmake b/cmake/Modules/GrMiscUtils.cmake index 3d9a5f519b..747eb1a3d1 100644 --- a/cmake/Modules/GrMiscUtils.cmake +++ b/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 # @@ -345,3 +345,175 @@ set(CMAKE_REQUIRED_LIBRARIES -lpthread) 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/gnuradio-runtime/lib/pmt/test_pmt.cc b/gnuradio-runtime/lib/pmt/test_pmt.cc index 49700b5928..403bf64cd0 100644 --- a/gnuradio-runtime/lib/pmt/test_pmt.cc +++ b/gnuradio-runtime/lib/pmt/test_pmt.cc @@ -29,6 +29,7 @@ #include <gnuradio/unittests.h> #include <qa_pmt.h> +#include <fstream> int main (int argc, char **argv) diff --git a/gnuradio-runtime/lib/test_runtime.cc b/gnuradio-runtime/lib/test_runtime.cc index 1285302eb4..6f75bcc1b1 100644 --- a/gnuradio-runtime/lib/test_runtime.cc +++ b/gnuradio-runtime/lib/test_runtime.cc @@ -29,6 +29,7 @@ #include <gnuradio/unittests.h> #include <qa_runtime.h> +#include <fstream> int main (int argc, char **argv) diff --git a/gr-analog/include/gnuradio/analog/CMakeLists.txt b/gr-analog/include/gnuradio/analog/CMakeLists.txt index 01c0518f0b..5812cb28ad 100644 --- a/gr-analog/include/gnuradio/analog/CMakeLists.txt +++ b/gr-analog/include/gnuradio/analog/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright 2012 Free Software Foundation, Inc. +# Copyright 2012,2014 Free Software Foundation, Inc. # # This file is part of GNU Radio # @@ -18,55 +18,12 @@ # Boston, MA 02110-1301, USA. ######################################################################## -# generate helper scripts to expand templated files +# Invoke macro to generate various headers ######################################################################## -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, 'analog') - build_utils.expand_template(d, inp) - -") - -macro(expand_h root) - #make a list of all the generated files - 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) - - #create a command to generate the 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} - ) - - #install rules for the generated h files - list(APPEND generated_includes ${expanded_files_h}) -endmacro(expand_h) - -######################################################################## -# Invoke macro to generate various sources -####################################################################### -expand_h(noise_source_X s i f c) -expand_h(fastnoise_source_X s i f c) -expand_h(sig_source_X s i f c) +include(GrMiscUtils) +GR_EXPAND_X_H(analog noise_source_X s i f c) +GR_EXPAND_X_H(analog fastnoise_source_X s i f c) +GR_EXPAND_X_H(analog sig_source_X s i f c) add_custom_target(analog_generated_includes DEPENDS ${generated_includes} diff --git a/gr-analog/lib/CMakeLists.txt b/gr-analog/lib/CMakeLists.txt index 451233174b..6aa2299792 100644 --- a/gr-analog/lib/CMakeLists.txt +++ b/gr-analog/lib/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright 2012-2013 Free Software Foundation, Inc. +# Copyright 2012-2014 Free Software Foundation, Inc. # # This file is part of GNU Radio # @@ -41,72 +41,12 @@ if(ENABLE_GR_CTRLPORT) endif(ENABLE_GR_CTRLPORT) ######################################################################## -# generate helper scripts to expand templated files +# Invoke macro to generate various sources and headers ######################################################################## -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, 'analog') - build_utils.expand_template(d, inp) -") - -macro(expand_cc root) - #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) - - #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 file - 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 cc files - list(APPEND generated_sources ${expanded_files_cc}) - list(APPEND generated_headers ${expanded_files_h}) -endmacro(expand_cc) - - -######################################################################## -# Invoke macro to generate various sources -######################################################################## -expand_cc(noise_source_X_impl s i f c) -expand_cc(fastnoise_source_X_impl s i f c) -expand_cc(sig_source_X_impl s i f c) +include(GrMiscUtils) +GR_EXPAND_X_CC_H(analog noise_source_X_impl s i f c) +GR_EXPAND_X_CC_H(analog fastnoise_source_X_impl s i f c) +GR_EXPAND_X_CC_H(analog sig_source_X_impl s i f c) ######################################################################## # Setup library diff --git a/gr-analog/lib/test_gr_analog.cc b/gr-analog/lib/test_gr_analog.cc index e621f9d395..228a99e347 100644 --- a/gr-analog/lib/test_gr_analog.cc +++ b/gr-analog/lib/test_gr_analog.cc @@ -30,6 +30,7 @@ #include <gnuradio/unittests.h> #include "qa_analog.h" #include <iostream> +#include <fstream> int main (int argc, char **argv) diff --git a/gr-atsc/lib/test_atsci.cc b/gr-atsc/lib/test_atsci.cc index acea17a7ab..edbe24f0b6 100644 --- a/gr-atsc/lib/test_atsci.cc +++ b/gr-atsc/lib/test_atsci.cc @@ -28,6 +28,7 @@ #include <cppunit/TextTestRunner.h> #include <cppunit/XmlOutputter.h> #include "qa_atsci.h" +#include <fstream> int main (int argc, char **argv) diff --git a/gr-blocks/examples/matrix_multiplexer.grc b/gr-blocks/examples/matrix_multiplexer.grc new file mode 100644 index 0000000000..724c53428a --- /dev/null +++ b/gr-blocks/examples/matrix_multiplexer.grc @@ -0,0 +1,1110 @@ +<?xml version='1.0' encoding='ASCII'?> +<flow_graph> + <timestamp>Tue Jun 3 11:35:32 2014</timestamp> + <block> + <key>options</key> + <param> + <key>id</key> + <value>matrix_multiply_demo</value> + </param> + <param> + <key>_enabled</key> + <value>True</value> + </param> + <param> + <key>title</key> + <value>Matrix Multiply/Multiplex Demo</value> + </param> + <param> + <key>author</key> + <value>Martin Braun</value> + </param> + <param> + <key>description</key> + <value>A demonstration of multiply_matrix_ff to demonstrate how to use it for stream selection</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>_coordinate</key> + <value>(-2, -6)</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>_coordinate</key> + <value>(183, 5)</value> + </param> + <param> + <key>_rotation</key> + <value>0</value> + </param> + </block> + <block> + <key>blocks_null_source</key> + <param> + <key>id</key> + <value>blocks_null_source_0</value> + </param> + <param> + <key>_enabled</key> + <value>True</value> + </param> + <param> + <key>type</key> + <value>float</value> + </param> + <param> + <key>vlen</key> + <value>1</value> + </param> + <param> + <key>num_outputs</key> + <value>1</value> + </param> + <param> + <key>bus_conns</key> + <value>[[0,],]</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>(-1, 298)</value> + </param> + <param> + <key>_rotation</key> + <value>0</value> + </param> + </block> + <block> + <key>analog_sig_source_x</key> + <param> + <key>id</key> + <value>analog_sig_source_x_0</value> + </param> + <param> + <key>_enabled</key> + <value>True</value> + </param> + <param> + <key>type</key> + <value>float</value> + </param> + <param> + <key>samp_rate</key> + <value>samp_rate</value> + </param> + <param> + <key>waveform</key> + <value>analog.GR_COS_WAVE</value> + </param> + <param> + <key>freq</key> + <value>1000</value> + </param> + <param> + <key>amp</key> + <value>1</value> + </param> + <param> + <key>offset</key> + <value>0</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>(0, 136)</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>QT GUI Plot</value> + </param> + <param> + <key>size</key> + <value>1024</value> + </param> + <param> + <key>srate</key> + <value>samp_rate</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_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_delay</key> + <value>0</value> + </param> + <param> + <key>tr_chan</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>1</value> + </param> + <param> + <key>marker1</key> + <value>-1</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>affinity</key> + <value></value> + </param> + <param> + <key>_coordinate</key> + <value>(899, 106)</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_1</value> + </param> + <param> + <key>_enabled</key> + <value>True</value> + </param> + <param> + <key>type</key> + <value>float</value> + </param> + <param> + <key>name</key> + <value>QT GUI Plot</value> + </param> + <param> + <key>size</key> + <value>1024</value> + </param> + <param> + <key>srate</key> + <value>samp_rate</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_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_delay</key> + <value>0</value> + </param> + <param> + <key>tr_chan</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>1</value> + </param> + <param> + <key>marker1</key> + <value>-1</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>affinity</key> + <value></value> + </param> + <param> + <key>_coordinate</key> + <value>(904, 233)</value> + </param> + <param> + <key>_rotation</key> + <value>0</value> + </param> + </block> + <block> + <key>blocks_multiply_matrix_xx</key> + <param> + <key>id</key> + <value>blocks_multiply_matrix_xx_0</value> + </param> + <param> + <key>_enabled</key> + <value>True</value> + </param> + <param> + <key>type</key> + <value>float</value> + </param> + <param> + <key>A</key> + <value>((1, 0), (0, 1))</value> + </param> + <param> + <key>tag_propagation_policy</key> + <value>999</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>(499, 172)</value> + </param> + <param> + <key>_rotation</key> + <value>0</value> + </param> + </block> + <block> + <key>blocks_stream_to_tagged_stream</key> + <param> + <key>id</key> + <value>blocks_stream_to_tagged_stream_0</value> + </param> + <param> + <key>_enabled</key> + <value>True</value> + </param> + <param> + <key>type</key> + <value>float</value> + </param> + <param> + <key>vlen</key> + <value>1</value> + </param> + <param> + <key>packet_len</key> + <value>100</value> + </param> + <param> + <key>len_tag_key</key> + <value>"packet_len"</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>(160, 286)</value> + </param> + <param> + <key>_rotation</key> + <value>0</value> + </param> + </block> + <block> + <key>blocks_message_strobe</key> + <param> + <key>id</key> + <value>blocks_message_strobe_0</value> + </param> + <param> + <key>_enabled</key> + <value>True</value> + </param> + <param> + <key>msg</key> + <value>pmt.to_pmt(new_A)</value> + </param> + <param> + <key>period</key> + <value>1000</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>(204, 376)</value> + </param> + <param> + <key>_rotation</key> + <value>0</value> + </param> + </block> + <block> + <key>variable_qtgui_chooser</key> + <param> + <key>id</key> + <value>new_A</value> + </param> + <param> + <key>_enabled</key> + <value>True</value> + </param> + <param> + <key>label</key> + <value>Mode</value> + </param> + <param> + <key>type</key> + <value>raw</value> + </param> + <param> + <key>num_opts</key> + <value>3</value> + </param> + <param> + <key>value</key> + <value>((1, 0), (0, 1))</value> + </param> + <param> + <key>options</key> + <value>[0, 1, 2]</value> + </param> + <param> + <key>labels</key> + <value>[]</value> + </param> + <param> + <key>option0</key> + <value>((1, 0), (0, 1))</value> + </param> + <param> + <key>label0</key> + <value>Default</value> + </param> + <param> + <key>option1</key> + <value>((0, 1), (1, 0))</value> + </param> + <param> + <key>label1</key> + <value>Flip</value> + </param> + <param> + <key>option2</key> + <value>((.5, .5), (.5, .5))</value> + </param> + <param> + <key>label2</key> + <value>Mix</value> + </param> + <param> + <key>option3</key> + <value>3</value> + </param> + <param> + <key>label3</key> + <value></value> + </param> + <param> + <key>option4</key> + <value>4</value> + </param> + <param> + <key>label4</key> + <value></value> + </param> + <param> + <key>widget</key> + <value>combo_box</value> + </param> + <param> + <key>orient</key> + <value>Qt.QVBoxLayout</value> + </param> + <param> + <key>gui_hint</key> + <value></value> + </param> + <param> + <key>_coordinate</key> + <value>(277, 0)</value> + </param> + <param> + <key>_rotation</key> + <value>0</value> + </param> + </block> + <connection> + <source_block_id>blocks_null_source_0</source_block_id> + <sink_block_id>blocks_stream_to_tagged_stream_0</sink_block_id> + <source_key>0</source_key> + <sink_key>0</sink_key> + </connection> + <connection> + <source_block_id>analog_sig_source_x_0</source_block_id> + <sink_block_id>blocks_multiply_matrix_xx_0</sink_block_id> + <source_key>0</source_key> + <sink_key>0</sink_key> + </connection> + <connection> + <source_block_id>blocks_stream_to_tagged_stream_0</source_block_id> + <sink_block_id>blocks_multiply_matrix_xx_0</sink_block_id> + <source_key>0</source_key> + <sink_key>1</sink_key> + </connection> + <connection> + <source_block_id>blocks_multiply_matrix_xx_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_multiply_matrix_xx_0</source_block_id> + <sink_block_id>qtgui_time_sink_x_1</sink_block_id> + <source_key>1</source_key> + <sink_key>0</sink_key> + </connection> + <connection> + <source_block_id>blocks_message_strobe_0</source_block_id> + <sink_block_id>blocks_multiply_matrix_xx_0</sink_block_id> + <source_key>strobe</source_key> + <sink_key>set_A</sink_key> + </connection> +</flow_graph> diff --git a/gr-blocks/grc/blocks_block_tree.xml b/gr-blocks/grc/blocks_block_tree.xml index b0d7ff0687..c2910930e4 100644 --- a/gr-blocks/grc/blocks_block_tree.xml +++ b/gr-blocks/grc/blocks_block_tree.xml @@ -94,6 +94,7 @@ <block>blocks_multiply_xx</block> <block>blocks_multiply_const_vxx</block> <block>blocks_multiply_conjugate_cc</block> + <block>blocks_multiply_matrix_xx</block> <block>blocks_sub_xx</block> <block>blocks_conjugate_cc</block> <block>blocks_integrate_xx</block> diff --git a/gr-blocks/grc/blocks_multiply_matrix_xx.xml b/gr-blocks/grc/blocks_multiply_matrix_xx.xml new file mode 100644 index 0000000000..070221446e --- /dev/null +++ b/gr-blocks/grc/blocks_multiply_matrix_xx.xml @@ -0,0 +1,68 @@ +<?xml version="1.0"?> +<block> + <name>Multiply by Matrix</name> + <key>blocks_multiply_matrix_xx</key> + <import>from gnuradio import blocks</import> + <make>blocks.multiply_matrix_$(type.fcn)($A, $tag_propagation_policy)</make> + <callback>set_A($A)</callback> + <param> + <name>IO Type</name> + <key>type</key> + <type>enum</type> + <option> + <name>Float</name> + <key>float</key> + <opt>fcn:ff</opt> + </option> + <option> + <name>Complex</name> + <key>complex</key> + <opt>fcn:cc</opt> + </option> + </param> + <param> + <name>Matrix A</name> + <key>A</key> + <value>((1, 0), (0, 1))</value> + <type>raw</type> + </param> + <param> + <name>TPP</name> + <key>tag_propagation_policy</key> + <type>enum</type> + <option> + <name>All to All</name> + <key>gr.TPP_ALL_TO_ALL</key> + </option> + <option> + <name>One to One</name> + <key>gr.TPP_ONE_TO_ONE</key> + </option> + <option> + <name>No Propagation</name> + <key>gr.TPP_DONT</key> + </option> + <option> + <name>Matrix-Defined</name> + <key>999</key> + </option> + </param> + <check>len($A) > 0</check> + <check>len(${A}[0]) > 0</check> + <check>$tag_propagation_policy != gr.TPP_ONE_TO_ONE or (len($A) == len(${A}[0]))</check> + <sink> + <name>in</name> + <type>$type</type> + <nports>len(${A}[0])</nports> + </sink> + <sink> + <name>set_A</name> + <type>message</type> + <optional>1</optional> + </sink> + <source> + <name>out</name> + <type>$type</type> + <nports>len($A)</nports> + </source> +</block> diff --git a/gr-blocks/include/gnuradio/blocks/CMakeLists.txt b/gr-blocks/include/gnuradio/blocks/CMakeLists.txt index fa3c354d97..96e86078f3 100644 --- a/gr-blocks/include/gnuradio/blocks/CMakeLists.txt +++ b/gr-blocks/include/gnuradio/blocks/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright 2013 Free Software Foundation, Inc. +# Copyright 2013-2014 Free Software Foundation, Inc. # # This file is part of GNU Radio # @@ -18,81 +18,39 @@ # Boston, MA 02110-1301, USA. ######################################################################## -# generate helper scripts to expand templated files +# Invoke macro to generate various headers ######################################################################## -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, 'blocks') - build_utils.expand_template(d, inp) - -") - -macro(expand_h root) - #make a list of all the generated files - 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) - - #create a command to generate the 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} - ) - - #install rules for the generated h files - list(APPEND generated_includes ${expanded_files_h}) -endmacro(expand_h) - -######################################################################## -# Invoke macro to generate various sources -######################################################################## -expand_h(abs_XX ss ii ff) -expand_h(add_XX ss ii cc) -expand_h(add_const_XX bb ss ii ff cc) -expand_h(add_const_vXX bb ss ii ff cc) -expand_h(and_XX bb ss ii) -expand_h(and_const_XX bb ss ii) -expand_h(argmax_XX fs is ss) -expand_h(divide_XX ss ii ff cc) -expand_h(integrate_XX ss ii ff cc) -expand_h(max_XX ff ii ss) -expand_h(moving_average_XX ss ii ff cc) -expand_h(multiply_XX ss ii) -expand_h(multiply_const_XX ss ii) -expand_h(multiply_const_vXX ss ii ff cc) -expand_h(mute_XX ss ii ff cc) -expand_h(not_XX bb ss ii) -expand_h(or_XX bb ss ii) -expand_h(peak_detector_XX fb ib sb) -expand_h(probe_signal_X b s i f c) -expand_h(probe_signal_vX b s i f c) -expand_h(sample_and_hold_XX bb ss ii ff) -expand_h(sub_XX ss ii ff cc) -expand_h(tsb_vector_sink_X b s i f c) -expand_h(xor_XX bb ss ii) -expand_h(packed_to_unpacked_XX bb ss ii) -expand_h(unpacked_to_packed_XX bb ss ii) -expand_h(vector_insert_X b s i f c) -expand_h(vector_sink_X b s i f c) -expand_h(vector_source_X b s i f c) +include(GrMiscUtils) +GR_EXPAND_X_H(blocks abs_XX ss ii ff) +GR_EXPAND_X_H(blocks add_XX ss ii cc) +GR_EXPAND_X_H(blocks add_const_XX bb ss ii ff cc) +GR_EXPAND_X_H(blocks add_const_vXX bb ss ii ff cc) +GR_EXPAND_X_H(blocks and_XX bb ss ii) +GR_EXPAND_X_H(blocks and_const_XX bb ss ii) +GR_EXPAND_X_H(blocks argmax_XX fs is ss) +GR_EXPAND_X_H(blocks divide_XX ss ii ff cc) +GR_EXPAND_X_H(blocks integrate_XX ss ii ff cc) +GR_EXPAND_X_H(blocks max_XX ff ii ss) +GR_EXPAND_X_H(blocks moving_average_XX ss ii ff cc) +GR_EXPAND_X_H(blocks multiply_XX ss ii) +GR_EXPAND_X_H(blocks multiply_const_XX ss ii) +GR_EXPAND_X_H(blocks multiply_const_vXX ss ii ff cc) +GR_EXPAND_X_H(blocks multiply_matrix_XX ff cc) +GR_EXPAND_X_H(blocks mute_XX ss ii ff cc) +GR_EXPAND_X_H(blocks not_XX bb ss ii) +GR_EXPAND_X_H(blocks or_XX bb ss ii) +GR_EXPAND_X_H(blocks peak_detector_XX fb ib sb) +GR_EXPAND_X_H(blocks probe_signal_X b s i f c) +GR_EXPAND_X_H(blocks probe_signal_vX b s i f c) +GR_EXPAND_X_H(blocks sample_and_hold_XX bb ss ii ff) +GR_EXPAND_X_H(blocks sub_XX ss ii ff cc) +GR_EXPAND_X_H(blocks tsb_vector_sink_X b s i f c) +GR_EXPAND_X_H(blocks xor_XX bb ss ii) +GR_EXPAND_X_H(blocks packed_to_unpacked_XX bb ss ii) +GR_EXPAND_X_H(blocks unpacked_to_packed_XX bb ss ii) +GR_EXPAND_X_H(blocks vector_insert_X b s i f c) +GR_EXPAND_X_H(blocks vector_sink_X b s i f c) +GR_EXPAND_X_H(blocks vector_source_X b s i f c) add_custom_target(blocks_generated_includes DEPENDS ${generated_includes} diff --git a/gr-blocks/include/gnuradio/blocks/multiply_matrix_XX.h.t b/gr-blocks/include/gnuradio/blocks/multiply_matrix_XX.h.t new file mode 100644 index 0000000000..25e7212105 --- /dev/null +++ b/gr-blocks/include/gnuradio/blocks/multiply_matrix_XX.h.t @@ -0,0 +1,94 @@ +/* -*- 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. + */ + +// @WARNING@ + +#ifndef @GUARD_NAME@ +#define @GUARD_NAME@ + +#include <gnuradio/blocks/api.h> +#include <gnuradio/sync_block.h> + +namespace gr { + namespace blocks { + + /*! + * \brief Matrix multiplexer/multiplier: y(k) = A * x(k) + * \ingroup blocks + * + * This block is similar to gr::blocks::multiply_const_ff, the difference + * being it can handle several inputs and outputs, and the input-to-output + * relation can be described by the following mathematical equation: + * \f[ + * y(k) = A x(k) \, , \, y \in \mathbb{R}^N, x \in \mathbb{R}^M, A \in \mathbb{R}^{N \times M} + * \f] + * \$y(k)\$ and \$x(i)\$ are column-vectors describing the elements on the input port + * at time step \$k\$ (this is a sync block with no memory). + * + * Examples for where to use this block include: + * - Switch matrices (i.e. switch which ports go where) + * - Simulation of static MIMO-Channels (in that case, \$A\$ is the channel matrix) + * + * This block features a special tag propagation mode: When setting the tag propagation policy + * to gr::blocks::@NAME@::TPP_SELECT_BY_MATRIX, a tag is propagated from input k + * to output l if \f$(A)_{l,k} \neq 0\f$. + * + * A message port (\p set_A) allows to set the matrix. *Note*: It is not possible to change + * the dimension of the matrix after initialization, as this affects the I/O signature! + */ + class BLOCKS_API @NAME@ : virtual public gr::sync_block + { + public: + typedef boost::shared_ptr<@NAME@> sptr; + + /*! + * \param A The matrix + * \param tag_propagation_policy The tag propagation policy. + * Note this can be any gr::block::tag_propagation_policy_t value, or TPP_SELECT_BY_MATRIX. + */ + static sptr make( + std::vector<std::vector<@O_TYPE@> > A, + gr::block::tag_propagation_policy_t tag_propagation_policy=gr::block::TPP_ALL_TO_ALL + ); + + //! Returns the current matrix + virtual const std::vector<std::vector<@O_TYPE@> >& get_A() const = 0; + //! Sets the matrix to a new value \p new_A. Returns true if the new matrix was valid and could be changed. + virtual bool set_A(const std::vector<std::vector<@O_TYPE@> > &new_A) = 0; + + /*! + * \brief Set the policy by the scheduler to determine how tags are moved downstream. + * + * This will also accept the value TPP_SELECT_BY_MATRIX. + */ + virtual void set_tag_propagation_policy(gr::block::tag_propagation_policy_t p) = 0; + + static const int TPP_SELECT_BY_MATRIX = 999; + static const std::string MSG_PORT_NAME_SET_A; + }; + const std::string @NAME@::MSG_PORT_NAME_SET_A = "set_A"; + + } // namespace blocks +} // namespace gr + +#endif /* @GUARD_NAME */ + diff --git a/gr-blocks/lib/CMakeLists.txt b/gr-blocks/lib/CMakeLists.txt index 1b0227c549..b3892ce64e 100644 --- a/gr-blocks/lib/CMakeLists.txt +++ b/gr-blocks/lib/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright 2012-2013 Free Software Foundation, Inc. +# Copyright 2012-2014 Free Software Foundation, Inc. # # This file is part of GNU Radio # @@ -23,102 +23,38 @@ include(${CMAKE_CURRENT_SOURCE_DIR}/ConfigChecks.cmake) ######################################################################## -# generate helper scripts to expand templated files -######################################################################## -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, 'blocks') - build_utils.expand_template(d, inp, '_impl') -") - -macro(expand_cc_h_impl root) - #make a list of all the generated files - unset(expanded_files_cc_impl) - unset(expanded_files_h_impl) - 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/${name}.h) - endforeach(sig) - - #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 headers 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 cc files - list(APPEND generated_sources ${expanded_files_cc_impl}) -endmacro(expand_cc_h_impl) - -######################################################################## # Invoke macro to generate various sources ######################################################################## -expand_cc_h_impl(abs_XX ss ii ff) -expand_cc_h_impl(add_XX ss ii cc) -expand_cc_h_impl(add_const_XX bb ss ii ff cc) -expand_cc_h_impl(add_const_vXX bb ss ii ff cc) -expand_cc_h_impl(and_XX bb ss ii) -expand_cc_h_impl(and_const_XX bb ss ii) -expand_cc_h_impl(argmax_XX fs is ss) -expand_cc_h_impl(divide_XX ss ii ff cc) -expand_cc_h_impl(integrate_XX ss ii ff cc) -expand_cc_h_impl(max_XX ff ii ss) -expand_cc_h_impl(moving_average_XX ss ii ff cc) -expand_cc_h_impl(multiply_XX ss ii) -expand_cc_h_impl(multiply_const_XX ss ii) -expand_cc_h_impl(multiply_const_vXX ss ii ff cc) -expand_cc_h_impl(mute_XX ss ii ff cc) -expand_cc_h_impl(not_XX bb ss ii) -expand_cc_h_impl(or_XX bb ss ii) -expand_cc_h_impl(peak_detector_XX fb ib sb) -expand_cc_h_impl(probe_signal_X b s i f c) -expand_cc_h_impl(probe_signal_vX b s i f c) -expand_cc_h_impl(sample_and_hold_XX bb ss ii ff) -expand_cc_h_impl(tsb_vector_sink_X b s i f c) -expand_cc_h_impl(sub_XX ss ii ff cc) -expand_cc_h_impl(xor_XX bb ss ii) -expand_cc_h_impl(packed_to_unpacked_XX bb ss ii) -expand_cc_h_impl(unpacked_to_packed_XX bb ss ii) -expand_cc_h_impl(vector_insert_X b s i f c) -expand_cc_h_impl(vector_sink_X b s i f c) -expand_cc_h_impl(vector_source_X b s i f c) +include(GrMiscUtils) +GR_EXPAND_X_CC_H_IMPL(blocks abs_XX ss ii ff) +GR_EXPAND_X_CC_H_IMPL(blocks add_XX ss ii cc) +GR_EXPAND_X_CC_H_IMPL(blocks add_const_XX bb ss ii ff cc) +GR_EXPAND_X_CC_H_IMPL(blocks add_const_vXX bb ss ii ff cc) +GR_EXPAND_X_CC_H_IMPL(blocks and_XX bb ss ii) +GR_EXPAND_X_CC_H_IMPL(blocks and_const_XX bb ss ii) +GR_EXPAND_X_CC_H_IMPL(blocks argmax_XX fs is ss) +GR_EXPAND_X_CC_H_IMPL(blocks divide_XX ss ii ff cc) +GR_EXPAND_X_CC_H_IMPL(blocks integrate_XX ss ii ff cc) +GR_EXPAND_X_CC_H_IMPL(blocks max_XX ff ii ss) +GR_EXPAND_X_CC_H_IMPL(blocks moving_average_XX ss ii ff cc) +GR_EXPAND_X_CC_H_IMPL(blocks multiply_XX ss ii) +GR_EXPAND_X_CC_H_IMPL(blocks multiply_const_XX ss ii) +GR_EXPAND_X_CC_H_IMPL(blocks multiply_const_vXX ss ii ff cc) +GR_EXPAND_X_CC_H_IMPL(blocks mute_XX ss ii ff cc) +GR_EXPAND_X_CC_H_IMPL(blocks not_XX bb ss ii) +GR_EXPAND_X_CC_H_IMPL(blocks or_XX bb ss ii) +GR_EXPAND_X_CC_H_IMPL(blocks peak_detector_XX fb ib sb) +GR_EXPAND_X_CC_H_IMPL(blocks probe_signal_X b s i f c) +GR_EXPAND_X_CC_H_IMPL(blocks probe_signal_vX b s i f c) +GR_EXPAND_X_CC_H_IMPL(blocks sample_and_hold_XX bb ss ii ff) +GR_EXPAND_X_CC_H_IMPL(blocks sub_XX ss ii ff cc) +GR_EXPAND_X_CC_H_IMPL(blocks tsb_vector_sink_X b s i f c) +GR_EXPAND_X_CC_H_IMPL(blocks xor_XX bb ss ii) +GR_EXPAND_X_CC_H_IMPL(blocks packed_to_unpacked_XX bb ss ii) +GR_EXPAND_X_CC_H_IMPL(blocks unpacked_to_packed_XX bb ss ii) +GR_EXPAND_X_CC_H_IMPL(blocks vector_insert_X b s i f c) +GR_EXPAND_X_CC_H_IMPL(blocks vector_sink_X b s i f c) +GR_EXPAND_X_CC_H_IMPL(blocks vector_source_X b s i f c) ######################################################################## # Setup the include and linker paths @@ -262,6 +198,7 @@ list(APPEND gr_blocks_sources vector_to_streams_impl.cc wavfile_sink_impl.cc wavfile_source_impl.cc + multiply_matrix_ff_impl.cc ) if(ENABLE_GR_CTRLPORT) diff --git a/gr-blocks/lib/multiply_matrix_cc_impl.cc b/gr-blocks/lib/multiply_matrix_cc_impl.cc new file mode 100644 index 0000000000..f9fc30ee6d --- /dev/null +++ b/gr-blocks/lib/multiply_matrix_cc_impl.cc @@ -0,0 +1,192 @@ +/* -*- 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. + */ + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +#include <gnuradio/io_signature.h> +#include <volk/volk.h> +#include "multiply_matrix_cc_impl.h" + +namespace gr { + namespace blocks { + + multiply_matrix_cc::sptr + multiply_matrix_cc::make(std::vector<std::vector<gr_complex> > A, gr::block::tag_propagation_policy_t tag_propagation_policy) + { + if (A.empty() or A[0].size() == 0) { + throw std::invalid_argument("matrix A has invalid dimensions."); + } + return gnuradio::get_initial_sptr + (new multiply_matrix_cc_impl(A, tag_propagation_policy)); + } + + multiply_matrix_cc_impl::multiply_matrix_cc_impl(std::vector<std::vector<gr_complex> > A, gr::block::tag_propagation_policy_t tag_propagation_policy) + : gr::sync_block("multiply_matrix_cc", + gr::io_signature::make(A[0].size(), A[0].size(), sizeof(gr_complex)), + gr::io_signature::make(A.size(), A.size(), sizeof(gr_complex))), + d_A(A) + { + this->set_tag_propagation_policy(tag_propagation_policy); + const int alignment_multiple = volk_get_alignment() / sizeof(gr_complex); + set_alignment(std::max(1, alignment_multiple)); + + pmt::pmt_t port_name = pmt::string_to_symbol("set_A"); + message_port_register_in(port_name); + set_msg_handler( + port_name, + boost::bind(&multiply_matrix_cc_impl::msg_handler_A, this, _1) + ); + } + + multiply_matrix_cc_impl::~multiply_matrix_cc_impl() + { + } + + int + multiply_matrix_cc_impl::work(int noutput_items, + gr_vector_const_void_star &input_items, + gr_vector_void_star &output_items) + { + for (size_t out_idx = 0; out_idx < output_items.size(); out_idx++) { + gr_complex *out = reinterpret_cast<gr_complex *>(output_items[out_idx]); + // Do input 0 first, this saves a memset + const gr_complex *in = reinterpret_cast<const gr_complex *>(input_items[0]); + volk_32fc_s32fc_multiply_32fc(out, in, d_A[out_idx][0], noutput_items); + // Then do inputs 1 through N + for (size_t in_idx = 1; in_idx < input_items.size(); in_idx++) { + in = reinterpret_cast<const gr_complex *>(input_items[in_idx]); + // Yeah, this needs VOLK-ifying (TODO) + for (int i = 0; i < noutput_items; i++) { + out[i] += in[i] * d_A[out_idx][in_idx]; + } + } + } + if (d_tag_prop_select) { + propagate_tags_by_A(noutput_items, input_items.size(), output_items.size()); + } + return noutput_items; + } + + + // Copy tags from input k to output l if A[l][k] is not zero + void + multiply_matrix_cc_impl::propagate_tags_by_A(int noutput_items, size_t ninput_ports, size_t noutput_ports) + { + std::vector<gr::tag_t> tags; + for (size_t in_idx = 0; in_idx < ninput_ports; in_idx++) { + get_tags_in_window( + tags, + in_idx, + 0, + noutput_items + ); + + for (size_t out_idx = 0; out_idx < noutput_ports; out_idx++) { + if (d_A[out_idx][in_idx] == 0) { + continue; + } + for (size_t i = 0; i < tags.size(); i++) { + add_item_tag(out_idx, tags[i]); + } + } + } + } + + // Check dimensions before copying + bool + multiply_matrix_cc_impl::set_A(const std::vector<std::vector<gr_complex> > &new_A) + { + if (d_A.size() != new_A.size()) { + GR_LOG_ALERT(d_logger, "Attempted to set matrix with invalid dimensions."); + return false; + } + for (size_t i = 0; i < d_A.size(); i++) { + if (d_A[i].size() != new_A[i].size()) { + GR_LOG_ALERT(d_logger, "Attempted to set matrix with invalid dimensions."); + return false; + } + } + d_A = new_A; + return true; + } + + void + multiply_matrix_cc_impl::msg_handler_A(pmt::pmt_t A) + { + if (not pmt::is_vector(A) and not pmt::is_tuple(A)) { + GR_LOG_ALERT(d_logger, "Invalid message to set A (wrong type)."); + return; + } + if (not pmt::length(A) == d_A.size()) { + GR_LOG_ALERT(d_logger, "Invalid message to set A (wrong size)."); + return; + } + + std::vector<std::vector<gr_complex> > new_A(d_A); + for (size_t i = 0; i < pmt::length(A); i++) { + pmt::pmt_t row; + if (pmt::is_vector(A)) { + row = pmt::vector_ref(A, i); + } else if (pmt::is_tuple(A)) { + row = pmt::tuple_ref(A, i); + } + if (pmt::is_vector(row) or pmt::is_tuple(row)) { + if (pmt::length(row) != d_A[0].size()) { + GR_LOG_ALERT(d_logger, "Invalid message to set A (wrong number of columns)."); + return; + } + for (size_t k = 0; k < pmt::length(row); k++) { + new_A[i][k] = pmt::to_double(pmt::is_vector(row) ? pmt::vector_ref(row, k) : pmt::tuple_ref(row, k)); + } + } else if (pmt::is_c32vector(row)) { + size_t row_len = 0; + const gr_complex *elements = pmt::c32vector_elements(row, row_len); + if (row_len != d_A[0].size()) { + GR_LOG_ALERT(d_logger, "Invalid message to set A (wrong number of columns)."); + return; + } + new_A[i].assign(elements, elements + row_len); + } + } + + if (not set_A(new_A)) { + GR_LOG_ALERT(d_logger, "Invalid message to set A."); + } + } + + void + multiply_matrix_cc_impl::set_tag_propagation_policy(gr::block::tag_propagation_policy_t tpp) + { + if (tpp == TPP_SELECT_BY_MATRIX) { + set_tag_propagation_policy(TPP_DONT); + d_tag_prop_select = true; + } else { + gr::block::set_tag_propagation_policy(tpp); + d_tag_prop_select = false; + } + } + + } /* namespace blocks */ +} /* namespace gr */ + diff --git a/gr-blocks/lib/multiply_matrix_cc_impl.h b/gr-blocks/lib/multiply_matrix_cc_impl.h new file mode 100644 index 0000000000..b357dde2cb --- /dev/null +++ b/gr-blocks/lib/multiply_matrix_cc_impl.h @@ -0,0 +1,59 @@ +/* -*- 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_BLOCKS_MULTIPLY_matrix_cc_IMPL_H +#define INCLUDED_BLOCKS_MULTIPLY_matrix_cc_IMPL_H + +#include <gnuradio/blocks/multiply_matrix_cc.h> + +namespace gr { + namespace blocks { + + class multiply_matrix_cc_impl : public multiply_matrix_cc + { + private: + std::vector<std::vector<gr_complex> > d_A; + bool d_tag_prop_select; //!< If true, handle the tag propagation ourselves + + void propagate_tags_by_A(int noutput_items, size_t ninput_ports, size_t noutput_ports); + + void msg_handler_A(pmt::pmt_t A); + + public: + multiply_matrix_cc_impl(std::vector<std::vector<gr_complex> > A, gr::block::tag_propagation_policy_t tag_propagation_policy); + ~multiply_matrix_cc_impl(); + + const std::vector<std::vector<gr_complex> >& get_A() const { return d_A; }; + bool set_A(const std::vector<std::vector<gr_complex> > &new_A); + + void set_tag_propagation_policy(gr::block::tag_propagation_policy_t p); + + int work(int noutput_items, + gr_vector_const_void_star &input_items, + gr_vector_void_star &output_items); + }; + + } // namespace blocks +} // namespace gr + +#endif /* INCLUDED_BLOCKS_MULTIPLY_matrix_cc_IMPL_H */ + diff --git a/gr-blocks/lib/multiply_matrix_ff_impl.cc b/gr-blocks/lib/multiply_matrix_ff_impl.cc new file mode 100644 index 0000000000..564e673233 --- /dev/null +++ b/gr-blocks/lib/multiply_matrix_ff_impl.cc @@ -0,0 +1,192 @@ +/* -*- 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. + */ + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +#include <gnuradio/io_signature.h> +#include <volk/volk.h> +#include "multiply_matrix_ff_impl.h" + +namespace gr { + namespace blocks { + + multiply_matrix_ff::sptr + multiply_matrix_ff::make(std::vector<std::vector<float> > A, gr::block::tag_propagation_policy_t tag_propagation_policy) + { + if (A.empty() or A[0].size() == 0) { + throw std::invalid_argument("matrix A has invalid dimensions."); + } + return gnuradio::get_initial_sptr + (new multiply_matrix_ff_impl(A, tag_propagation_policy)); + } + + multiply_matrix_ff_impl::multiply_matrix_ff_impl(std::vector<std::vector<float> > A, gr::block::tag_propagation_policy_t tag_propagation_policy) + : gr::sync_block("multiply_matrix_ff", + gr::io_signature::make(A[0].size(), A[0].size(), sizeof(float)), + gr::io_signature::make(A.size(), A.size(), sizeof(float))), + d_A(A) + { + this->set_tag_propagation_policy(tag_propagation_policy); + const int alignment_multiple = volk_get_alignment() / sizeof(float); + set_alignment(std::max(1, alignment_multiple)); + + pmt::pmt_t port_name = pmt::string_to_symbol("set_A"); + message_port_register_in(port_name); + set_msg_handler( + port_name, + boost::bind(&multiply_matrix_ff_impl::msg_handler_A, this, _1) + ); + } + + multiply_matrix_ff_impl::~multiply_matrix_ff_impl() + { + } + + int + multiply_matrix_ff_impl::work(int noutput_items, + gr_vector_const_void_star &input_items, + gr_vector_void_star &output_items) + { + for (size_t out_idx = 0; out_idx < output_items.size(); out_idx++) { + float *out = reinterpret_cast<float *>(output_items[out_idx]); + // Do input 0 first, this saves a memset + const float *in = reinterpret_cast<const float *>(input_items[0]); + volk_32f_s32f_multiply_32f(out, in, d_A[out_idx][0], noutput_items); + // Then do inputs 1 through N + for (size_t in_idx = 1; in_idx < input_items.size(); in_idx++) { + in = reinterpret_cast<const float *>(input_items[in_idx]); + // Yeah, this needs VOLK-ifying (TODO) + for (int i = 0; i < noutput_items; i++) { + out[i] += in[i] * d_A[out_idx][in_idx]; + } + } + } + if (d_tag_prop_select) { + propagate_tags_by_A(noutput_items, input_items.size(), output_items.size()); + } + return noutput_items; + } + + + // Copy tags from input k to output l if A[l][k] is not zero + void + multiply_matrix_ff_impl::propagate_tags_by_A(int noutput_items, size_t ninput_ports, size_t noutput_ports) + { + std::vector<gr::tag_t> tags; + for (size_t in_idx = 0; in_idx < ninput_ports; in_idx++) { + get_tags_in_window( + tags, + in_idx, + 0, + noutput_items + ); + + for (size_t out_idx = 0; out_idx < noutput_ports; out_idx++) { + if (d_A[out_idx][in_idx] == 0) { + continue; + } + for (size_t i = 0; i < tags.size(); i++) { + add_item_tag(out_idx, tags[i]); + } + } + } + } + + // Check dimensions before copying + bool + multiply_matrix_ff_impl::set_A(const std::vector<std::vector<float> > &new_A) + { + if (d_A.size() != new_A.size()) { + GR_LOG_ALERT(d_logger, "Attempted to set matrix with invalid dimensions."); + return false; + } + for (size_t i = 0; i < d_A.size(); i++) { + if (d_A[i].size() != new_A[i].size()) { + GR_LOG_ALERT(d_logger, "Attempted to set matrix with invalid dimensions."); + return false; + } + } + d_A = new_A; + return true; + } + + void + multiply_matrix_ff_impl::msg_handler_A(pmt::pmt_t A) + { + if (not pmt::is_vector(A) and not pmt::is_tuple(A)) { + GR_LOG_ALERT(d_logger, "Invalid message to set A (wrong type)."); + return; + } + if (not pmt::length(A) == d_A.size()) { + GR_LOG_ALERT(d_logger, "Invalid message to set A (wrong size)."); + return; + } + + std::vector<std::vector<float> > new_A(d_A); + for (size_t i = 0; i < pmt::length(A); i++) { + pmt::pmt_t row; + if (pmt::is_vector(A)) { + row = pmt::vector_ref(A, i); + } else if (pmt::is_tuple(A)) { + row = pmt::tuple_ref(A, i); + } + if (pmt::is_vector(row) or pmt::is_tuple(row)) { + if (pmt::length(row) != d_A[0].size()) { + GR_LOG_ALERT(d_logger, "Invalid message to set A (wrong number of columns)."); + return; + } + for (size_t k = 0; k < pmt::length(row); k++) { + new_A[i][k] = pmt::to_double(pmt::is_vector(row) ? pmt::vector_ref(row, k) : pmt::tuple_ref(row, k)); + } + } else if (pmt::is_f32vector(row)) { + size_t row_len = 0; + const float *elements = pmt::f32vector_elements(row, row_len); + if (row_len != d_A[0].size()) { + GR_LOG_ALERT(d_logger, "Invalid message to set A (wrong number of columns)."); + return; + } + new_A[i].assign(elements, elements + row_len); + } + } + + if (not set_A(new_A)) { + GR_LOG_ALERT(d_logger, "Invalid message to set A."); + } + } + + void + multiply_matrix_ff_impl::set_tag_propagation_policy(gr::block::tag_propagation_policy_t tpp) + { + if (tpp == TPP_SELECT_BY_MATRIX) { + set_tag_propagation_policy(TPP_DONT); + d_tag_prop_select = true; + } else { + gr::block::set_tag_propagation_policy(tpp); + d_tag_prop_select = false; + } + } + + } /* namespace blocks */ +} /* namespace gr */ + diff --git a/gr-blocks/lib/multiply_matrix_ff_impl.h b/gr-blocks/lib/multiply_matrix_ff_impl.h new file mode 100644 index 0000000000..c9476bc8d1 --- /dev/null +++ b/gr-blocks/lib/multiply_matrix_ff_impl.h @@ -0,0 +1,59 @@ +/* -*- 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_BLOCKS_MULTIPLY_MATRIX_FF_IMPL_H +#define INCLUDED_BLOCKS_MULTIPLY_MATRIX_FF_IMPL_H + +#include <gnuradio/blocks/multiply_matrix_ff.h> + +namespace gr { + namespace blocks { + + class multiply_matrix_ff_impl : public multiply_matrix_ff + { + private: + std::vector<std::vector<float> > d_A; + bool d_tag_prop_select; //!< If true, handle the tag propagation ourselves + + void propagate_tags_by_A(int noutput_items, size_t ninput_ports, size_t noutput_ports); + + void msg_handler_A(pmt::pmt_t A); + + public: + multiply_matrix_ff_impl(std::vector<std::vector<float> > A, gr::block::tag_propagation_policy_t tag_propagation_policy); + ~multiply_matrix_ff_impl(); + + const std::vector<std::vector<float> >& get_A() const { return d_A; }; + bool set_A(const std::vector<std::vector<float> > &new_A); + + void set_tag_propagation_policy(gr::block::tag_propagation_policy_t p); + + int work(int noutput_items, + gr_vector_const_void_star &input_items, + gr_vector_void_star &output_items); + }; + + } // namespace blocks +} // namespace gr + +#endif /* INCLUDED_BLOCKS_MULTIPLY_MATRIX_FF_IMPL_H */ + diff --git a/gr-blocks/lib/test_gr_blocks.cc b/gr-blocks/lib/test_gr_blocks.cc index 2d8f0d6d2a..bc3901dac3 100644 --- a/gr-blocks/lib/test_gr_blocks.cc +++ b/gr-blocks/lib/test_gr_blocks.cc @@ -30,6 +30,7 @@ #include <gnuradio/unittests.h> #include <qa_blocks.h> #include <iostream> +#include <fstream> int main(int argc, char **argv) diff --git a/gr-blocks/python/blocks/qa_multiply_matrix_ff.py b/gr-blocks/python/blocks/qa_multiply_matrix_ff.py new file mode 100755 index 0000000000..fdf020552a --- /dev/null +++ b/gr-blocks/python/blocks/qa_multiply_matrix_ff.py @@ -0,0 +1,172 @@ +#!/usr/bin/env python +# -*- coding: utf-8 -*- +# +# 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. +# + +import time +import numpy +import os +import pmt +from gnuradio import gr, gr_unittest +from gnuradio import blocks + +class test_multiply_matrix_ff (gr_unittest.TestCase): + + def setUp (self): + self.tb = gr.top_block () + self.multiplier = None + + def tearDown (self): + self.tb = None + self.multiplier = None + + def run_once(self, X_in, A, tpp=gr.TPP_DONT, A2=None, tags=None, msg_A=None): + """ Run the test for given input-, output- and matrix values. + Every row from X_in is considered an input signal on a port. """ + X_in = numpy.matrix(X_in) + A_matrix = numpy.matrix(A) + (N, M) = A_matrix.shape + self.assertTrue(N == X_in.shape[0]) + # Calc expected + Y_out_exp = numpy.matrix(numpy.zeros((M, X_in.shape[1]))) + self.multiplier = blocks.multiply_matrix_ff(A, tpp) + if A2 is not None: + self.multiplier.set_A(A2) + A = A2 + A_matrix = numpy.matrix(A) + for i in xrange(N): + if tags is None: + these_tags = () + else: + these_tags = (tags[i],) + self.tb.connect(blocks.vector_source_f(X_in[i].tolist()[0], tags=these_tags), (self.multiplier, i)) + sinks = [] + for i in xrange(M): + sinks.append(blocks.vector_sink_f()) + self.tb.connect((self.multiplier, i), sinks[i]) + # Run and check + self.tb.run() + for i in xrange(X_in.shape[1]): + Y_out_exp[:,i] = A_matrix * X_in[:,i] + Y_out = [list(x.data()) for x in sinks] + if tags is not None: + self.the_tags = [] + for i in xrange(M): + self.the_tags.append(sinks[i].tags()) + self.assertEqual(list(Y_out), Y_out_exp.tolist()) + + + def test_001_t (self): + """ Simplest possible check: N==M, unit matrix """ + X_in = ( + (1, 2, 3, 4), + (5, 6, 7, 8), + ) + A = ( + (1, 0), + (0, 1), + ) + self.run_once(X_in, A) + + def test_002_t (self): + """ Switch check: N==M, flipped unit matrix """ + X_in = ( + (1, 2, 3, 4), + (5, 6, 7, 8), + ) + A = ( + (0, 1), + (1, 0), + ) + self.run_once(X_in, A) + + def test_003_t (self): + """ Average """ + X_in = ( + (1, 1, 1, 1), + (2, 2, 2, 2), + ) + A = ( + (0.5, 0.5), + (0.5, 0.5), + ) + self.run_once(X_in, A) + + def test_004_t (self): + """ Set """ + X_in = ( + (1, 2, 3, 4), + (5, 6, 7, 8), + ) + A1 = ( + (1, 0), + (0, 1), + ) + A2 = ( + (0, 1), + (1, 0), + ) + self.run_once(X_in, A1, A2=A2) + + def test_005_t (self): + """ Tags """ + X_in = ( + (1, 2, 3, 4), + (5, 6, 7, 8), + ) + A = ( + (0, 1), # Flip them round + (1, 0), + ) + tag1 = gr.tag_t() + tag1.offset = 0 + tag1.key = pmt.intern("in1") + tag1.value = pmt.PMT_T + tag2 = gr.tag_t() + tag2.offset = 0 + tag2.key = pmt.intern("in2") + tag2.value = pmt.PMT_T + self.run_once(X_in, A, tpp=999, tags=(tag1, tag2)) + self.assertTrue(pmt.equal(tag1.key, self.the_tags[1][0].key)) + self.assertTrue(pmt.equal(tag2.key, self.the_tags[0][0].key)) + + #def test_006_t (self): + #""" Message passing """ + #X_in = ( + #(1, 2, 3, 4), + #(5, 6, 7, 8), + #) + #A1 = ( + #(1, 0), + #(0, 1), + #) + #msg_A = ( + #(0, 1), + #(1, 0), + #) + #self.run_once(X_in, A1, msg_A=msg_A) + + + +if __name__ == '__main__': + #gr_unittest.run(test_multiply_matrix_ff, "test_multiply_matrix_ff.xml") + gr_unittest.run(test_multiply_matrix_ff) + diff --git a/gr-blocks/swig/blocks_swig3.i b/gr-blocks/swig/blocks_swig3.i index ab921a559a..43cc78a4a6 100644 --- a/gr-blocks/swig/blocks_swig3.i +++ b/gr-blocks/swig/blocks_swig3.i @@ -64,6 +64,7 @@ #include "gnuradio/blocks/multiply_const_vii.h" #include "gnuradio/blocks/multiply_const_vff.h" #include "gnuradio/blocks/multiply_const_vcc.h" +#include "gnuradio/blocks/multiply_matrix_ff.h" #include "gnuradio/blocks/mute_ss.h" #include "gnuradio/blocks/mute_ii.h" #include "gnuradio/blocks/mute_ff.h" @@ -106,6 +107,7 @@ %include "gnuradio/blocks/multiply_const_vii.h" %include "gnuradio/blocks/multiply_const_vff.h" %include "gnuradio/blocks/multiply_const_vcc.h" +%include "gnuradio/blocks/multiply_matrix_ff.h" %include "gnuradio/blocks/mute_ss.h" %include "gnuradio/blocks/mute_ii.h" %include "gnuradio/blocks/mute_ff.h" @@ -147,6 +149,7 @@ GR_SWIG_BLOCK_MAGIC2(blocks, multiply_const_vss); GR_SWIG_BLOCK_MAGIC2(blocks, multiply_const_vii); GR_SWIG_BLOCK_MAGIC2(blocks, multiply_const_vff); GR_SWIG_BLOCK_MAGIC2(blocks, multiply_const_vcc); +GR_SWIG_BLOCK_MAGIC2(blocks, multiply_matrix_ff); GR_SWIG_BLOCK_MAGIC2(blocks, mute_ss); GR_SWIG_BLOCK_MAGIC2(blocks, mute_ii); GR_SWIG_BLOCK_MAGIC2(blocks, mute_ff); diff --git a/gr-digital/include/gnuradio/digital/CMakeLists.txt b/gr-digital/include/gnuradio/digital/CMakeLists.txt index 0d958e867f..c39b12bed2 100644 --- a/gr-digital/include/gnuradio/digital/CMakeLists.txt +++ b/gr-digital/include/gnuradio/digital/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright 2011-2013 Free Software Foundation, Inc. +# Copyright 2011-2014 Free Software Foundation, Inc. # # This file is part of GNU Radio # @@ -18,53 +18,10 @@ # Boston, MA 02110-1301, USA. ######################################################################## -# generate helper scripts to expand templated files -######################################################################## -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, 'digital') - build_utils.expand_template(d, inp) - -") - -macro(expand_h root) - #make a list of all the generated files - 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) - - #create a command to generate the 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} - ) - - #install rules for the generated h files - list(APPEND generated_includes ${expanded_files_h}) -endmacro(expand_h) - -######################################################################## -# Invoke macro to generate various sources +# Invoke macro to generate various headers ####################################################################### -expand_h(chunks_to_symbols_XX bf bc sf sc if ic) +include(GrMiscUtils) +GR_EXPAND_X_H(digital chunks_to_symbols_XX bf bc sf sc if ic) add_custom_target(digital_generated_includes DEPENDS ${generated_includes} diff --git a/gr-digital/lib/CMakeLists.txt b/gr-digital/lib/CMakeLists.txt index 7f9448f8e7..f9830fbbf2 100644 --- a/gr-digital/lib/CMakeLists.txt +++ b/gr-digital/lib/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright 2011-2013 Free Software Foundation, Inc. +# Copyright 2011-2014 Free Software Foundation, Inc. # # This file is part of GNU Radio # @@ -42,70 +42,10 @@ if(ENABLE_GR_CTRLPORT) endif(ENABLE_GR_CTRLPORT) ######################################################################## -# generate helper scripts to expand templated files -######################################################################## -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, 'digital') - build_utils.expand_template(d, inp) -") - -macro(expand_cc root) - #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) - - #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 file - 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 cc files - list(APPEND generated_sources ${expanded_files_cc}) - list(APPEND generated_headers ${expanded_files_h}) -endmacro(expand_cc) - - -######################################################################## # Invoke macro to generate various sources ######################################################################## -expand_cc(chunks_to_symbols_XX_impl bf bc sf sc if ic) +include(GrMiscUtils) +GR_EXPAND_X_CC_H(digital chunks_to_symbols_XX_impl bf bc sf sc if ic) ######################################################################## # Setup library @@ -176,7 +116,6 @@ list(APPEND digital_sources scrambler_bb_impl.cc simple_correlator_impl.cc simple_framer_impl.cc - header_payload_demux_impl.cc ) #Add Windows DLL resource file if using MSVC @@ -203,7 +142,6 @@ list(APPEND digital_libs ${LOG4CPP_LIBRARIES} ) - add_library(gnuradio-digital SHARED ${digital_sources}) target_link_libraries(gnuradio-digital ${digital_libs}) GR_LIBRARY_FOO(gnuradio-digital RUNTIME_COMPONENT "digital_runtime" DEVEL_COMPONENT "digital_devel") diff --git a/gr-fec/include/gnuradio/fec/CMakeLists.txt b/gr-fec/include/gnuradio/fec/CMakeLists.txt index a91a68a996..63bc32ced9 100644 --- a/gr-fec/include/gnuradio/fec/CMakeLists.txt +++ b/gr-fec/include/gnuradio/fec/CMakeLists.txt @@ -18,63 +18,9 @@ # Boston, MA 02110-1301, USA. ######################################################################## -# generate helper scripts to expand templated files -######################################################################## -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, 'fec') - build_utils.expand_template(d, inp) - -") - -macro(expand_h root) - #make a list of all the generated files - 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) - - #create a command to generate the 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} - ) - - #install rules for the generated h files - list(APPEND generated_includes ${expanded_files_h}) -endmacro(expand_h) - -######################################################################## -# Invoke macro to generate various sources -######################################################################## -#expand_h(foo_XX ss ii cc) - -add_custom_target(fec_generated_includes DEPENDS - ${generated_includes} -) - -######################################################################## # Install header files ######################################################################## install(FILES - ${generated_includes} api.h generic_decoder.h generic_encoder.h diff --git a/gr-filter/include/gnuradio/filter/CMakeLists.txt b/gr-filter/include/gnuradio/filter/CMakeLists.txt index b5cc432c6a..e75f02b7a2 100644 --- a/gr-filter/include/gnuradio/filter/CMakeLists.txt +++ b/gr-filter/include/gnuradio/filter/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright 2012 Free Software Foundation, Inc. +# Copyright 2012,2014 Free Software Foundation, Inc. # # This file is part of GNU Radio # @@ -18,56 +18,13 @@ # Boston, MA 02110-1301, USA. ######################################################################## -# generate helper scripts to expand templated files -######################################################################## -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, 'filter') - build_utils.expand_template(d, inp) - -") - -macro(expand_h root) - #make a list of all the generated files - 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) - - #create a command to generate the 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} - ) - - #install rules for the generated h files - list(APPEND generated_includes ${expanded_files_h}) -endmacro(expand_h) - -######################################################################## -# Invoke macro to generate various sources +# Invoke macro to generate various headers ####################################################################### -expand_h(fir_filter_XXX ccc ccf fcc fff fsf scc) -expand_h(freq_xlating_fir_filter_XXX ccc ccf fcc fcf scf scc) -expand_h(interp_fir_filter_XXX ccc ccf fcc fff fsf scc) -expand_h(rational_resampler_base_XXX ccc ccf fcc fff fsf scc) +include(GrMiscUtils) +GR_EXPAND_X_H(filter fir_filter_XXX ccc ccf fcc fff fsf scc) +GR_EXPAND_X_H(filter freq_xlating_fir_filter_XXX ccc ccf fcc fcf scf scc) +GR_EXPAND_X_H(filter interp_fir_filter_XXX ccc ccf fcc fff fsf scc) +GR_EXPAND_X_H(filter rational_resampler_base_XXX ccc ccf fcc fff fsf scc) add_custom_target(filter_generated_includes DEPENDS ${generated_includes} diff --git a/gr-filter/lib/CMakeLists.txt b/gr-filter/lib/CMakeLists.txt index 75e403267b..5505f514a5 100644 --- a/gr-filter/lib/CMakeLists.txt +++ b/gr-filter/lib/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright 2012-2013 Free Software Foundation, Inc. +# Copyright 2012-2014 Free Software Foundation, Inc. # # This file is part of GNU Radio # @@ -18,73 +18,13 @@ # Boston, MA 02110-1301, USA. ######################################################################## -# generate helper scripts to expand templated files +# Invoke macro to generate various sources and headers ######################################################################## -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, 'filter') - build_utils.expand_template(d, inp) -") - -macro(expand_cc root) - #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) - - #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 file - 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 cc files - list(APPEND generated_sources ${expanded_files_cc}) - list(APPEND generated_headers ${expanded_files_h}) -endmacro(expand_cc) - -######################################################################## -# Invoke macro to generate various sources -######################################################################## -expand_cc(fir_filter_XXX_impl ccc ccf fcc fff fsf scc) -expand_cc(freq_xlating_fir_filter_XXX_impl ccc ccf fcc fcf scf scc) -expand_cc(interp_fir_filter_XXX_impl ccc ccf fcc fff fsf scc) -expand_cc(rational_resampler_base_XXX_impl ccc ccf fcc fff fsf scc) - +include(GrMiscUtils) +GR_EXPAND_X_CC_H(filter fir_filter_XXX_impl ccc ccf fcc fff fsf scc) +GR_EXPAND_X_CC_H(filter freq_xlating_fir_filter_XXX_impl ccc ccf fcc fcf scf scc) +GR_EXPAND_X_CC_H(filter interp_fir_filter_XXX_impl ccc ccf fcc fff fsf scc) +GR_EXPAND_X_CC_H(filter rational_resampler_base_XXX_impl ccc ccf fcc fff fsf scc) ######################################################################## # Setup the include and linker paths diff --git a/gr-filter/lib/test_gr_filter.cc b/gr-filter/lib/test_gr_filter.cc index b713aafaf7..f43b781490 100644 --- a/gr-filter/lib/test_gr_filter.cc +++ b/gr-filter/lib/test_gr_filter.cc @@ -30,6 +30,7 @@ #include <gnuradio/unittests.h> #include <qa_filter.h> #include <iostream> +#include <fstream> int main (int argc, char **argv) diff --git a/gr-qtgui/lib/const_sink_c_impl.cc b/gr-qtgui/lib/const_sink_c_impl.cc index 2da1c213b4..029014045f 100644 --- a/gr-qtgui/lib/const_sink_c_impl.cc +++ b/gr-qtgui/lib/const_sink_c_impl.cc @@ -115,8 +115,10 @@ namespace gr { 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); } diff --git a/gr-qtgui/lib/freq_sink_c_impl.cc b/gr-qtgui/lib/freq_sink_c_impl.cc index 4b43967f32..9f4a86f0bd 100644 --- a/gr-qtgui/lib/freq_sink_c_impl.cc +++ b/gr-qtgui/lib/freq_sink_c_impl.cc @@ -140,8 +140,10 @@ namespace gr { 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); } diff --git a/gr-qtgui/lib/freq_sink_f_impl.cc b/gr-qtgui/lib/freq_sink_f_impl.cc index ab6167d10a..77eede0040 100644 --- a/gr-qtgui/lib/freq_sink_f_impl.cc +++ b/gr-qtgui/lib/freq_sink_f_impl.cc @@ -140,8 +140,10 @@ namespace gr { 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); } diff --git a/gr-qtgui/lib/histogram_sink_f_impl.cc b/gr-qtgui/lib/histogram_sink_f_impl.cc index bd43f8645c..923ea73cc4 100644 --- a/gr-qtgui/lib/histogram_sink_f_impl.cc +++ b/gr-qtgui/lib/histogram_sink_f_impl.cc @@ -109,8 +109,10 @@ namespace gr { 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); } diff --git a/gr-qtgui/lib/sink_c_impl.cc b/gr-qtgui/lib/sink_c_impl.cc index bcd2c4468c..ed2512b00c 100644 --- a/gr-qtgui/lib/sink_c_impl.cc +++ b/gr-qtgui/lib/sink_c_impl.cc @@ -130,8 +130,10 @@ namespace gr { 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); } diff --git a/gr-qtgui/lib/sink_f_impl.cc b/gr-qtgui/lib/sink_f_impl.cc index 67896b71df..e2263f7150 100644 --- a/gr-qtgui/lib/sink_f_impl.cc +++ b/gr-qtgui/lib/sink_f_impl.cc @@ -130,8 +130,10 @@ namespace gr { 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); } diff --git a/gr-qtgui/lib/time_raster_sink_b_impl.cc b/gr-qtgui/lib/time_raster_sink_b_impl.cc index ecd8ac319a..afc5e90e2d 100644 --- a/gr-qtgui/lib/time_raster_sink_b_impl.cc +++ b/gr-qtgui/lib/time_raster_sink_b_impl.cc @@ -124,8 +124,10 @@ namespace gr { 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); } diff --git a/gr-qtgui/lib/time_raster_sink_f_impl.cc b/gr-qtgui/lib/time_raster_sink_f_impl.cc index 3a18985b2d..7d271abb20 100644 --- a/gr-qtgui/lib/time_raster_sink_f_impl.cc +++ b/gr-qtgui/lib/time_raster_sink_f_impl.cc @@ -122,8 +122,10 @@ namespace gr { 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); } diff --git a/gr-qtgui/lib/time_sink_c_impl.cc b/gr-qtgui/lib/time_sink_c_impl.cc index 8653f7179a..9cc9269eb6 100644 --- a/gr-qtgui/lib/time_sink_c_impl.cc +++ b/gr-qtgui/lib/time_sink_c_impl.cc @@ -113,8 +113,10 @@ namespace gr { 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); } diff --git a/gr-qtgui/lib/time_sink_f_impl.cc b/gr-qtgui/lib/time_sink_f_impl.cc index 30e6df1c2a..16a22b8703 100644 --- a/gr-qtgui/lib/time_sink_f_impl.cc +++ b/gr-qtgui/lib/time_sink_f_impl.cc @@ -115,8 +115,10 @@ namespace gr { 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); } diff --git a/gr-qtgui/lib/waterfall_sink_c_impl.cc b/gr-qtgui/lib/waterfall_sink_c_impl.cc index 8cb3f1a7bf..6c1583b805 100644 --- a/gr-qtgui/lib/waterfall_sink_c_impl.cc +++ b/gr-qtgui/lib/waterfall_sink_c_impl.cc @@ -139,8 +139,10 @@ namespace gr { 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); } diff --git a/gr-qtgui/lib/waterfall_sink_f_impl.cc b/gr-qtgui/lib/waterfall_sink_f_impl.cc index 1c1453c1d1..22771e155f 100644 --- a/gr-qtgui/lib/waterfall_sink_f_impl.cc +++ b/gr-qtgui/lib/waterfall_sink_f_impl.cc @@ -138,8 +138,10 @@ namespace gr { 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); } diff --git a/gr-trellis/include/gnuradio/trellis/CMakeLists.txt b/gr-trellis/include/gnuradio/trellis/CMakeLists.txt index 5f30cc8e4e..ef60ce7370 100644 --- a/gr-trellis/include/gnuradio/trellis/CMakeLists.txt +++ b/gr-trellis/include/gnuradio/trellis/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright 2012 Free Software Foundation, Inc. +# Copyright 2012,2014 Free Software Foundation, Inc. # # This file is part of GNU Radio # @@ -18,62 +18,19 @@ # Boston, MA 02110-1301, USA. ######################################################################## -# generate helper scripts to expand templated files +# Invoke macro to generate various headers ######################################################################## -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, 'trellis') - build_utils.expand_template(d, inp) - -") - -macro(expand_h root) - #make a list of all the generated files - 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) - - #create a command to generate the 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} - ) - - #install rules for the generated h files - list(APPEND generated_includes ${expanded_files_h}) -endmacro(expand_h) - -######################################################################## -# Invoke macro to generate various sources -####################################################################### -expand_h(encoder_XX bb bs bi ss si ii) -expand_h(sccc_encoder_XX bb bs bi ss si ii) -expand_h(pccc_encoder_XX bb bs bi ss si ii) -expand_h(metrics_X s i f c) -expand_h(viterbi_X b s i) -expand_h(viterbi_combined_XX sb ss si ib is ii fb fs fi cb cs ci) -expand_h(sccc_decoder_X b s i) -expand_h(sccc_decoder_combined_XX fb fs fi cb cs ci) -expand_h(pccc_decoder_X b s i) -expand_h(pccc_decoder_combined_XX fb fs fi cb cs ci) +include(GrMiscUtils) +GR_EXPAND_X_H(trellis encoder_XX bb bs bi ss si ii) +GR_EXPAND_X_H(trellis sccc_encoder_XX bb bs bi ss si ii) +GR_EXPAND_X_H(trellis pccc_encoder_XX bb bs bi ss si ii) +GR_EXPAND_X_H(trellis metrics_X s i f c) +GR_EXPAND_X_H(trellis viterbi_X b s i) +GR_EXPAND_X_H(trellis viterbi_combined_XX sb ss si ib is ii fb fs fi cb cs ci) +GR_EXPAND_X_H(trellis sccc_decoder_X b s i) +GR_EXPAND_X_H(trellis sccc_decoder_combined_XX fb fs fi cb cs ci) +GR_EXPAND_X_H(trellis pccc_decoder_X b s i) +GR_EXPAND_X_H(trellis pccc_decoder_combined_XX fb fs fi cb cs ci) add_custom_target(trellis_generated_includes DEPENDS ${generated_includes} diff --git a/gr-trellis/lib/CMakeLists.txt b/gr-trellis/lib/CMakeLists.txt index 0bb400b40c..2dfc7019dc 100644 --- a/gr-trellis/lib/CMakeLists.txt +++ b/gr-trellis/lib/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright 2012 Free Software Foundation, Inc. +# Copyright 2012,2014 Free Software Foundation, Inc. # # This file is part of GNU Radio # @@ -38,78 +38,19 @@ if(ENABLE_GR_CTRLPORT) endif(ENABLE_GR_CTRLPORT) ####################################################################### -# generate the python helper script which calls into the build utils +# Invoke macro to generate various sources and headers ######################################################################## -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, 'trellis') - build_utils.expand_template(d, inp) -") - -macro(expand_cc root) - #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) - - #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 file - 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 cc files - list(APPEND generated_sources ${expanded_files_cc}) - list(APPEND generated_headers ${expanded_files_h}) -endmacro(expand_cc) - -######################################################################## -# Invoke macro to generate various sources -######################################################################## -expand_cc(encoder_XX_impl bb bs bi ss si ii) -expand_cc(sccc_encoder_XX_impl bb bs bi ss si ii) -expand_cc(pccc_encoder_XX_impl bb bs bi ss si ii) -expand_cc(metrics_X_impl s i f c) -expand_cc(viterbi_X_impl b s i) -expand_cc(viterbi_combined_XX_impl sb ss si ib is ii fb fs fi cb cs ci) -expand_cc(sccc_decoder_X_impl b s i) -expand_cc(sccc_decoder_combined_XX_impl fb fs fi cb cs ci) -expand_cc(pccc_decoder_X_impl b s i) -expand_cc(pccc_decoder_combined_XX_impl fb fs fi cb cs ci) +include(GrMiscUtils) +GR_EXPAND_X_CC_H(trellis encoder_XX_impl bb bs bi ss si ii) +GR_EXPAND_X_CC_H(trellis sccc_encoder_XX_impl bb bs bi ss si ii) +GR_EXPAND_X_CC_H(trellis pccc_encoder_XX_impl bb bs bi ss si ii) +GR_EXPAND_X_CC_H(trellis metrics_X_impl s i f c) +GR_EXPAND_X_CC_H(trellis viterbi_X_impl b s i) +GR_EXPAND_X_CC_H(trellis viterbi_combined_XX_impl sb ss si ib is ii fb fs fi cb cs ci) +GR_EXPAND_X_CC_H(trellis sccc_decoder_X_impl b s i) +GR_EXPAND_X_CC_H(trellis sccc_decoder_combined_XX_impl fb fs fi cb cs ci) +GR_EXPAND_X_CC_H(trellis pccc_decoder_X_impl b s i) +GR_EXPAND_X_CC_H(trellis pccc_decoder_combined_XX_impl fb fs fi cb cs ci) ######################################################################## # Setup library diff --git a/gr-utils/python/modtool/gr-newmod/lib/test_howto.cc b/gr-utils/python/modtool/gr-newmod/lib/test_howto.cc index f01bd5a064..cc89dc90f3 100644 --- a/gr-utils/python/modtool/gr-newmod/lib/test_howto.cc +++ b/gr-utils/python/modtool/gr-newmod/lib/test_howto.cc @@ -30,6 +30,7 @@ #include <gnuradio/unittests.h> #include "qa_howto.h" #include <iostream> +#include <fstream> int main (int argc, char **argv) diff --git a/gr-vocoder/lib/codec2/quantise.c b/gr-vocoder/lib/codec2/quantise.c index 6423dc83df..f7326c4fcd 100644 --- a/gr-vocoder/lib/codec2/quantise.c +++ b/gr-vocoder/lib/codec2/quantise.c @@ -153,7 +153,7 @@ void encode_lspds_scalar( float dlsp_[LPC_MAX]; float wt[LPC_MAX]; const float *cb; - float se; + float se = 0.0f; assert(order == LPC_ORD); @@ -245,7 +245,7 @@ void lspvq_quantise( int i,k,m,ncb, nlsp; float wt[LPC_ORD], lsp_hz[LPC_ORD]; const float *cb; - float se; + float se = 0.0f; int index; for(i=0; i<LPC_ORD; i++) { @@ -301,7 +301,7 @@ void lspjnd_quantise(float lsps[], float lsps_[], int order) int i,k,m; float wt[LPC_ORD], lsps_hz[LPC_ORD]; const float *cb; - float se = 0.0; + float se = 0.0f; int index; for(i=0; i<LPC_ORD; i++) { @@ -369,7 +369,7 @@ void lspdt_quantise(float lsps[], float lsps_[], float lsps__prev[], int mode) int k,m; int index; const float *cb; - float se = 0.0; + float se = 0.0f; #endif // TRY_LSPDT_VQ //compute_weights(lsps, wt, LPC_ORD); @@ -1225,7 +1225,7 @@ void encode_lsps_scalar(int indexes[], float lsp[], int order) float wt[1]; float lsp_hz[LPC_MAX]; const float * cb; - float se; + float se = 0.0f; /* convert from radians to Hz so we can use human readable frequencies */ @@ -1298,7 +1298,7 @@ void encode_lsps_diff_freq_vq(int indexes[], float lsp[], int order) float dlsp_[LPC_MAX]; float wt[LPC_MAX]; const float * cb; - float se; + float se = 0.0f; for(i=0; i<LPC_ORD; i++) { wt[i] = 1.0; @@ -1404,7 +1404,7 @@ void encode_lsps_diff_time(int indexes[], float lsps_dt[LPC_ORD]; float wt[LPC_MAX]; const float * cb; - float se; + float se = 0.0f; /* Determine difference in time and convert from radians to Hz so we can use human readable frequencies */ diff --git a/grc/python/flow_graph.tmpl b/grc/python/flow_graph.tmpl index 52582384aa..ace217c967 100644 --- a/grc/python/flow_graph.tmpl +++ b/grc/python/flow_graph.tmpl @@ -58,6 +58,7 @@ class $(class_name)(grc_wxgui.top_block_gui): self.SetIcon(wx.Icon(_icon_path, wx.BITMAP_TYPE_ANY)) #end if #elif $generate_options == 'qt_gui' +from distutils.version import StrictVersion class $(class_name)(gr.top_block, Qt.QWidget): def __init__($param_str): @@ -316,7 +317,8 @@ if __name__ == '__main__': tb.Wait() #end if #elif $generate_options == 'qt_gui' - Qt.QApplication.setGraphicsSystem(gr.prefs().get_string('qtgui','style','raster')) + if(StrictVersion(Qt.qVersion()) >= StrictVersion("4.5.0")): + Qt.QApplication.setGraphicsSystem(gr.prefs().get_string('qtgui','style','raster')) qapp = Qt.QApplication(sys.argv) tb = $(class_name)($(', '.join($params_eq_list))) #if $flow_graph.get_option('run') |