summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--gnuradio-runtime/include/gnuradio/basic_block.h6
-rw-r--r--gnuradio-runtime/include/gnuradio/block.h24
-rw-r--r--gnuradio-runtime/include/gnuradio/hier_block2.h25
-rw-r--r--gnuradio-runtime/lib/block.cc14
-rw-r--r--gnuradio-runtime/lib/hier_block2.cc12
-rw-r--r--gnuradio-runtime/lib/hier_block2_detail.cc18
-rw-r--r--gnuradio-runtime/lib/hier_block2_detail.h3
-rw-r--r--gnuradio-runtime/swig/block.i3
-rw-r--r--gnuradio-runtime/swig/hier_block2.i3
-rw-r--r--gr-blocks/python/blocks/qa_logger.py96
10 files changed, 204 insertions, 0 deletions
diff --git a/gnuradio-runtime/include/gnuradio/basic_block.h b/gnuradio-runtime/include/gnuradio/basic_block.h
index fa454c95ed..8d7308efe2 100644
--- a/gnuradio-runtime/include/gnuradio/basic_block.h
+++ b/gnuradio-runtime/include/gnuradio/basic_block.h
@@ -377,6 +377,12 @@ namespace gr {
virtual std::vector<int> processor_affinity()
{ throw std::runtime_error("processor_affinity not overloaded in child class."); }
+
+ virtual void set_log_level(std::string level)
+ { throw std::runtime_error("set_log_level not overloaded in child class."); }
+
+ virtual std::string log_level()
+ { throw std::runtime_error("log_level not overloaded in child class."); }
};
inline bool operator<(basic_block_sptr lhs, basic_block_sptr rhs)
diff --git a/gnuradio-runtime/include/gnuradio/block.h b/gnuradio-runtime/include/gnuradio/block.h
index 3e85f22823..21d41c0b63 100644
--- a/gnuradio-runtime/include/gnuradio/block.h
+++ b/gnuradio-runtime/include/gnuradio/block.h
@@ -633,6 +633,30 @@ namespace gr {
*/
void system_handler(pmt::pmt_t msg);
+ /*!
+ * \brief Set the logger's output level.
+ *
+ * Sets the level of the logger. This takes a string that is
+ * translated to the standard levels and can be (case insensitive):
+ *
+ * \li off , notset
+ * \li debug
+ * \li info
+ * \li notice
+ * \li warn
+ * \li error
+ * \li crit
+ * \li alert
+ * \li fatal
+ * \li emerg
+ */
+ void set_log_level(std::string level);
+
+ /*!
+ * \brief Get the logger's output level
+ */
+ std::string log_level();
+
/*!
* \brief returns true when execution has completed due to a message connection
*/
diff --git a/gnuradio-runtime/include/gnuradio/hier_block2.h b/gnuradio-runtime/include/gnuradio/hier_block2.h
index 08a5389e96..b7c6be2441 100644
--- a/gnuradio-runtime/include/gnuradio/hier_block2.h
+++ b/gnuradio-runtime/include/gnuradio/hier_block2.h
@@ -267,6 +267,31 @@ namespace gr {
std::vector<int> processor_affinity();
/*!
+ * \brief Set the logger's output level.
+ *
+ * Sets the level of the logger for all connected blocks. This takes
+ * a string that is translated to the standard levels and can be
+ * (case insensitive):
+ *
+ * \li off , notset
+ * \li debug
+ * \li info
+ * \li notice
+ * \li warn
+ * \li error
+ * \li crit
+ * \li alert
+ * \li fatal
+ * \li emerg
+ */
+ void set_log_level(std::string level);
+
+ /*!
+ * \brief Get the logger's output level
+ */
+ std::string log_level();
+
+ /*!
* \brief Get if all block min buffers should be set.
*
* \details this returns whether all the block min output buffers
diff --git a/gnuradio-runtime/lib/block.cc b/gnuradio-runtime/lib/block.cc
index e329e0657a..4c408ab7ed 100644
--- a/gnuradio-runtime/lib/block.cc
+++ b/gnuradio-runtime/lib/block.cc
@@ -715,6 +715,20 @@ namespace gr {
}
void
+ block::set_log_level(std::string level)
+ {
+ logger_set_level(d_logger, level);
+ }
+
+ std::string
+ block::log_level()
+ {
+ std::string level;
+ logger_get_level(d_logger, level);
+ return level;
+ }
+
+ void
block::notify_msg_neighbors()
{
size_t len = pmt::length(d_message_subscribers);
diff --git a/gnuradio-runtime/lib/hier_block2.cc b/gnuradio-runtime/lib/hier_block2.cc
index 597ae032ec..8ebbbda587 100644
--- a/gnuradio-runtime/lib/hier_block2.cc
+++ b/gnuradio-runtime/lib/hier_block2.cc
@@ -178,6 +178,18 @@ namespace gr {
return d_detail->processor_affinity();
}
+ void
+ hier_block2::set_log_level(std::string level)
+ {
+ d_detail->set_log_level(level);
+ }
+
+ std::string
+ hier_block2::log_level()
+ {
+ return d_detail->log_level();
+ }
+
std::string
dot_graph(hier_block2_sptr hierblock2)
{
diff --git a/gnuradio-runtime/lib/hier_block2_detail.cc b/gnuradio-runtime/lib/hier_block2_detail.cc
index 0d0ddf55ba..e6d867b269 100644
--- a/gnuradio-runtime/lib/hier_block2_detail.cc
+++ b/gnuradio-runtime/lib/hier_block2_detail.cc
@@ -956,4 +956,22 @@ namespace gr {
return tmp[0]->processor_affinity();
}
+ void
+ hier_block2_detail::set_log_level(std::string level)
+ {
+ basic_block_vector_t tmp = d_fg->calc_used_blocks();
+ for(basic_block_viter_t p = tmp.begin(); p != tmp.end(); p++) {
+ (*p)->set_log_level(level);
+ }
+ }
+
+ std::string
+ hier_block2_detail::log_level()
+ {
+ // Assume that log_level was set for all hier_block2 blocks
+ basic_block_vector_t tmp = d_fg->calc_used_blocks();
+ return tmp[0]->log_level();
+ }
+
+
} /* namespace gr */
diff --git a/gnuradio-runtime/lib/hier_block2_detail.h b/gnuradio-runtime/lib/hier_block2_detail.h
index a5584fe92a..aa419c49bd 100644
--- a/gnuradio-runtime/lib/hier_block2_detail.h
+++ b/gnuradio-runtime/lib/hier_block2_detail.h
@@ -57,6 +57,9 @@ namespace gr {
void set_processor_affinity(const std::vector<int> &mask);
void unset_processor_affinity();
std::vector<int> processor_affinity();
+
+ void set_log_level(std::string level);
+ std::string log_level();
// Track output buffer min/max settings
std::vector<size_t> d_max_output_buffer;
diff --git a/gnuradio-runtime/swig/block.i b/gnuradio-runtime/swig/block.i
index 945cea79b2..64500575fb 100644
--- a/gnuradio-runtime/swig/block.i
+++ b/gnuradio-runtime/swig/block.i
@@ -57,6 +57,9 @@ class gr::block : public gr::basic_block
uint64_t nitems_read(unsigned int which_input);
uint64_t nitems_written(unsigned int which_output);
+ void set_log_level(std::string level);
+ std::string log_level();
+
// Methods to manage the block's max_noutput_items size.
int max_noutput_items();
void set_max_noutput_items(int m);
diff --git a/gnuradio-runtime/swig/hier_block2.i b/gnuradio-runtime/swig/hier_block2.i
index 12190d0452..6e964db8a1 100644
--- a/gnuradio-runtime/swig/hier_block2.i
+++ b/gnuradio-runtime/swig/hier_block2.i
@@ -91,6 +91,9 @@ namespace gr {
void unset_processor_affinity();
std::vector<int> processor_affinity();
+ void set_log_level(std::string level);
+ std::string log_level();
+
// Methods to manage block's min/max buffer sizes.
size_t max_output_buffer(int i);
void set_max_output_buffer(size_t max_output_buffer);
diff --git a/gr-blocks/python/blocks/qa_logger.py b/gr-blocks/python/blocks/qa_logger.py
new file mode 100644
index 0000000000..d2b6b3ee5e
--- /dev/null
+++ b/gr-blocks/python/blocks/qa_logger.py
@@ -0,0 +1,96 @@
+#!/usr/bin/env python
+#
+# Copyright 2016 Free Software Foundation, Inc.
+#
+# This file is part of GNU Radio
+#
+# GNU Radio is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 3, or (at your option)
+# any later version.
+#
+# GNU Radio is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with GNU Radio; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 51 Franklin Street,
+# Boston, MA 02110-1301, USA.
+#
+
+from gnuradio import gr, gr_unittest, blocks
+
+class test_logger (gr_unittest.TestCase):
+
+ def setUp(self):
+ pass
+
+ def tearDown(self):
+ pass
+
+ def set_and_assert_log_level(self, block, level):
+ block.set_log_level(level)
+ self.assertEqual(block.log_level(), level)
+
+ def test_log_level_for_block(self):
+ # Test the python API for getting and setting log levels of individual block
+ # go through all of the documented log_levels
+ ns = blocks.null_source(1)
+ self.set_and_assert_log_level(ns, "notset")
+ self.set_and_assert_log_level(ns, "debug")
+ self.set_and_assert_log_level(ns, "info")
+ self.set_and_assert_log_level(ns, "notice")
+ self.set_and_assert_log_level(ns, "warn")
+ self.set_and_assert_log_level(ns, "error")
+ self.set_and_assert_log_level(ns, "crit")
+ self.set_and_assert_log_level(ns, "alert")
+ self.set_and_assert_log_level(ns, "emerg")
+ # There's a couple of special cases. "off" == "notset" (specific to gr)
+ # and "fatal" == "emerg" (built in to log4cpp)
+ ns.set_log_level("off")
+ self.assertEqual(ns.log_level(), "notset")
+ ns.set_log_level("fatal")
+ self.assertEqual(ns.log_level(), "emerg")
+ # Make sure exception is throw on bogus data
+ self.assertRaises(RuntimeError, ns.set_log_level, "11")
+
+
+ def test_log_level_for_tb(self):
+ # Test the python API for getting and setting log levels for a top_block
+ nsrc = blocks.null_source(4)
+ nsnk = blocks.null_sink(4)
+ # Set all log levels to a known state
+ nsrc.set_log_level("debug")
+ nsnk.set_log_level("debug")
+ tb = gr.top_block()
+ tb.connect(nsrc, nsnk)
+ # confirm that the tb has log_level of first block
+ self.assertEqual(tb.log_level(), "debug")
+ # confirm that changing tb log_level propagates to connected blocks
+ tb.set_log_level("alert")
+ self.assertEqual(tb.log_level(), "alert")
+ self.assertEqual(nsrc.log_level(), "alert")
+ self.assertEqual(nsnk.log_level(), "alert")
+
+ def test_log_level_for_hier_block(self):
+ # Test the python API for getting and setting log levels for hier blocks
+ nsrc = blocks.null_source(4)
+ nsnk = blocks.null_sink(4)
+ b = blocks.stream_to_vector_decimator(4, 1, 1, 1) # just a random hier block that exists
+ tb = gr.top_block()
+ tb.connect(nsrc, b, nsnk)
+ tb.set_log_level("debug")
+ self.assertEqual(tb.log_level(), "debug")
+ self.assertEqual(nsrc.log_level(), "debug")
+ self.assertEqual(nsnk.log_level(), "debug")
+ self.assertEqual(b.one_in_n.log_level(), "debug")
+ tb.set_log_level("alert")
+ self.assertEqual(tb.log_level(), "alert")
+ self.assertEqual(nsrc.log_level(), "alert")
+ self.assertEqual(nsnk.log_level(), "alert")
+ self.assertEqual(b.one_in_n.log_level(), "alert")
+
+if __name__ == '__main__':
+ gr_unittest.run(test_logger, "test_logger.xml")