GNU Radio 3.5.1 C++ API
|
00001 /* -*- c++ -*- */ 00002 /* 00003 * Copyright 2006,2008,2009,2011 Free Software Foundation, Inc. 00004 * 00005 * This file is part of GNU Radio 00006 * 00007 * GNU Radio is free software; you can redistribute it and/or modify 00008 * it under the terms of the GNU General Public License as published by 00009 * the Free Software Foundation; either version 3, or (at your option) 00010 * any later version. 00011 * 00012 * GNU Radio is distributed in the hope that it will be useful, 00013 * but WITHOUT ANY WARRANTY; without even the implied warranty of 00014 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00015 * GNU General Public License for more details. 00016 * 00017 * You should have received a copy of the GNU General Public License 00018 * along with GNU Radio; see the file COPYING. If not, write to 00019 * the Free Software Foundation, Inc., 51 Franklin Street, 00020 * Boston, MA 02110-1301, USA. 00021 */ 00022 00023 #ifndef INCLUDED_GR_BASIC_BLOCK_H 00024 #define INCLUDED_GR_BASIC_BLOCK_H 00025 00026 #include <gr_core_api.h> 00027 #include <gr_runtime_types.h> 00028 #include <gr_sptr_magic.h> 00029 #include <boost/enable_shared_from_this.hpp> 00030 #include <boost/function.hpp> 00031 #include <gr_msg_accepter.h> 00032 #include <string> 00033 00034 /*! 00035 * \brief The abstract base class for all signal processing blocks. 00036 * \ingroup internal 00037 * 00038 * Basic blocks are the bare abstraction of an entity that has a name, 00039 * a set of inputs and outputs, and a message queue. These are never instantiated 00040 * directly; rather, this is the abstract parent class of both gr_hier_block, 00041 * which is a recursive container, and gr_block, which implements actual 00042 * signal processing functions. 00043 */ 00044 00045 class GR_CORE_API gr_basic_block : public gr_msg_accepter, public boost::enable_shared_from_this<gr_basic_block> 00046 { 00047 typedef boost::function<void(pmt::pmt_t)> msg_handler_t; 00048 00049 private: 00050 /* 00051 * This function is called by the runtime system to dispatch messages. 00052 * 00053 * The thread-safety guarantees mentioned in set_msg_handler are implemented 00054 * by the callers of this method. 00055 */ 00056 void dispatch_msg(pmt::pmt_t msg) 00057 { 00058 if (d_msg_handler) // Is there a handler? 00059 d_msg_handler(msg); // Yes, invoke it. 00060 }; 00061 00062 msg_handler_t d_msg_handler; 00063 00064 protected: 00065 friend class gr_flowgraph; 00066 friend class gr_flat_flowgraph; // TODO: will be redundant 00067 friend class gr_tpb_thread_body; 00068 00069 enum vcolor { WHITE, GREY, BLACK }; 00070 00071 std::string d_name; 00072 gr_io_signature_sptr d_input_signature; 00073 gr_io_signature_sptr d_output_signature; 00074 long d_unique_id; 00075 vcolor d_color; 00076 00077 gr_basic_block(void){} //allows pure virtual interface sub-classes 00078 00079 //! Protected constructor prevents instantiation by non-derived classes 00080 gr_basic_block(const std::string &name, 00081 gr_io_signature_sptr input_signature, 00082 gr_io_signature_sptr output_signature); 00083 00084 //! may only be called during constructor 00085 void set_input_signature(gr_io_signature_sptr iosig) { 00086 d_input_signature = iosig; 00087 } 00088 00089 //! may only be called during constructor 00090 void set_output_signature(gr_io_signature_sptr iosig) { 00091 d_output_signature = iosig; 00092 } 00093 00094 /*! 00095 * \brief Allow the flowgraph to set for sorting and partitioning 00096 */ 00097 void set_color(vcolor color) { d_color = color; } 00098 vcolor color() const { return d_color; } 00099 00100 public: 00101 virtual ~gr_basic_block(); 00102 long unique_id() const { return d_unique_id; } 00103 std::string name() const { return d_name; } 00104 gr_io_signature_sptr input_signature() const { return d_input_signature; } 00105 gr_io_signature_sptr output_signature() const { return d_output_signature; } 00106 gr_basic_block_sptr to_basic_block(); // Needed for Python/Guile type coercion 00107 00108 /*! 00109 * \brief Confirm that ninputs and noutputs is an acceptable combination. 00110 * 00111 * \param ninputs number of input streams connected 00112 * \param noutputs number of output streams connected 00113 * 00114 * \returns true if this is a valid configuration for this block. 00115 * 00116 * This function is called by the runtime system whenever the 00117 * topology changes. Most classes do not need to override this. 00118 * This check is in addition to the constraints specified by the input 00119 * and output gr_io_signatures. 00120 */ 00121 virtual bool check_topology(int ninputs, int noutputs) { return true; } 00122 00123 /*! 00124 * \brief Set the callback that is fired when messages are available. 00125 * 00126 * \p msg_handler can be any kind of function pointer or function object 00127 * that has the signature: 00128 * <pre> 00129 * void msg_handler(pmt::pmt msg); 00130 * </pre> 00131 * 00132 * (You may want to use boost::bind to massage your callable into the 00133 * correct form. See gr_nop.{h,cc} for an example that sets up a class 00134 * method as the callback.) 00135 * 00136 * Blocks that desire to handle messages must call this method in their 00137 * constructors to register the handler that will be invoked when messages 00138 * are available. 00139 * 00140 * If the block inherits from gr_block, the runtime system will ensure that 00141 * msg_handler is called in a thread-safe manner, such that work and 00142 * msg_handler will never be called concurrently. This allows msg_handler 00143 * to update state variables without having to worry about thread-safety 00144 * issues with work, general_work or another invocation of msg_handler. 00145 * 00146 * If the block inherits from gr_hier_block2, the runtime system will 00147 * ensure that no reentrant calls are made to msg_handler. 00148 */ 00149 template <typename T> void set_msg_handler(T msg_handler){ 00150 d_msg_handler = msg_handler_t(msg_handler); 00151 } 00152 }; 00153 00154 inline bool operator<(gr_basic_block_sptr lhs, gr_basic_block_sptr rhs) 00155 { 00156 return lhs->unique_id() < rhs->unique_id(); 00157 } 00158 00159 typedef std::vector<gr_basic_block_sptr> gr_basic_block_vector_t; 00160 typedef std::vector<gr_basic_block_sptr>::iterator gr_basic_block_viter_t; 00161 00162 GR_CORE_API long gr_basic_block_ncurrently_allocated(); 00163 00164 inline std::ostream &operator << (std::ostream &os, gr_basic_block_sptr basic_block) 00165 { 00166 os << basic_block->name() << "(" << basic_block->unique_id() << ")"; 00167 return os; 00168 } 00169 00170 #endif /* INCLUDED_GR_BASIC_BLOCK_H */