From d2f79c07281604c1b48ec81f1cdb2754e97bbe65 Mon Sep 17 00:00:00 2001 From: Josh Blum Date: Tue, 28 Jun 2011 21:26:28 -0700 Subject: uhd: added properties unit tests, use shared ptr in tree --- host/include/uhd/property_tree.hpp | 9 +--- host/include/uhd/property_tree.ipp | 22 +++------- host/lib/property_tree.cpp | 7 ++-- host/tests/property_test.cpp | 86 ++++++++++++++++++++++++++++++-------- 4 files changed, 79 insertions(+), 45 deletions(-) diff --git a/host/include/uhd/property_tree.hpp b/host/include/uhd/property_tree.hpp index 630e86bba..63cd76a56 100644 --- a/host/include/uhd/property_tree.hpp +++ b/host/include/uhd/property_tree.hpp @@ -19,7 +19,6 @@ #define INCLUDED_UHD_PROPERTY_TREE_HPP #include -#include #include #include #include @@ -34,14 +33,10 @@ namespace uhd{ */ template class UHD_API property : boost::noncopyable{ public: - typedef boost::shared_ptr sptr; typedef boost::function subscriber_type; typedef boost::function publisher_type; typedef boost::function master_type; - //! Make a new property object - static sptr make(void); - /*! * Register a master subscriber into the property. * A master is a special subscriber that coerces the value. @@ -107,10 +102,10 @@ public: protected: //! Internal create property with wild-card type - virtual void _create(const path_type &path, const boost::any &prop) = 0; + virtual void _create(const path_type &path, const boost::shared_ptr &prop) = 0; //! Internal access property with wild-card type - virtual boost::any &_access(const path_type &path) = 0; + virtual boost::shared_ptr &_access(const path_type &path) = 0; }; diff --git a/host/include/uhd/property_tree.ipp b/host/include/uhd/property_tree.ipp index e4520df58..1c61d4937 100644 --- a/host/include/uhd/property_tree.ipp +++ b/host/include/uhd/property_tree.ipp @@ -18,15 +18,14 @@ #ifndef INCLUDED_UHD_PROPERTY_TREE_IPP #define INCLUDED_UHD_PROPERTY_TREE_IPP -#include #include +#include #include /*********************************************************************** * Implement templated property impl **********************************************************************/ -namespace uhd{ -namespace /*anon*/{ +namespace uhd{ namespace /*anon*/{ template class UHD_API property_impl : public property{ public: @@ -71,13 +70,7 @@ private: boost::any _value; //any type so we can assign structs w/ const members }; -} //namespace /*anon*/ - -template typename property::sptr property::make(void){ - return sptr(new property_impl()); -} - -} //namespace uhd +}} //namespace uhd::/*anon*/ /*********************************************************************** * Implement templated methods for the property tree @@ -85,17 +78,12 @@ template typename property::sptr property::make(void){ namespace uhd{ template property &property_tree::create(const path_type &path){ - this->_create(path, property::make()); + this->_create(path, typename boost::shared_ptr >(new property_impl())); return this->access(path); } template property &property_tree::access(const path_type &path){ - try{ - return *boost::any_cast::sptr>(this->_access(path)); - } - catch(const boost::bad_any_cast &){ - throw uhd::type_error("Cannot cast the property at: " + path.string()); - } + return *boost::static_pointer_cast >(this->_access(path)); } } //namespace uhd diff --git a/host/lib/property_tree.cpp b/host/lib/property_tree.cpp index 4fbdbad12..4a0b1b061 100644 --- a/host/lib/property_tree.cpp +++ b/host/lib/property_tree.cpp @@ -61,7 +61,7 @@ public: return node->keys(); } - void _create(const path_type &path, const boost::any &prop){ + void _create(const path_type &path, const boost::shared_ptr &prop){ boost::mutex::scoped_lock lock(_mutex); node_type *node = &_root; @@ -72,7 +72,7 @@ public: node->prop = prop; } - boost::any &_access(const path_type &path){ + boost::shared_ptr &_access(const path_type &path){ boost::mutex::scoped_lock lock(_mutex); node_type *node = &_root; @@ -80,6 +80,7 @@ public: if (not node->has_key(leaf)) throw_path_not_found(path); node = &(*node)[leaf]; } + if (node->prop.get() == NULL) throw uhd::type_error("Uninitialized property at: " + path.string()); return node->prop; } @@ -89,7 +90,7 @@ private: } struct node_type : uhd::dict{ - boost::any prop; + boost::shared_ptr prop; } _root; boost::mutex _mutex; diff --git a/host/tests/property_test.cpp b/host/tests/property_test.cpp index 6c80cea70..cd9691dca 100644 --- a/host/tests/property_test.cpp +++ b/host/tests/property_test.cpp @@ -18,6 +18,7 @@ #include #include #include +#include #include struct coercer_type{ @@ -34,44 +35,92 @@ struct setter_type{ int _x; }; +struct getter_type{ + int doit(void){ + return _x; + } + + int _x; +}; + BOOST_AUTO_TEST_CASE(test_prop_simple){ - uhd::property::sptr prop = uhd::property::make(); - prop->set(42); - BOOST_CHECK_EQUAL(prop->get(), 42); - prop->set(34); - BOOST_CHECK_EQUAL(prop->get(), 34); + uhd::property_tree::sptr tree = uhd::property_tree::make(); + uhd::property &prop = tree->create("/"); + prop.set(42); + BOOST_CHECK_EQUAL(prop.get(), 42); + prop.set(34); + BOOST_CHECK_EQUAL(prop.get(), 34); } BOOST_AUTO_TEST_CASE(test_prop_with_subscriber){ - uhd::property::sptr prop = uhd::property::make(); + uhd::property_tree::sptr tree = uhd::property_tree::make(); + uhd::property &prop = tree->create("/"); setter_type setter; - prop->subscribe(boost::bind(&setter_type::doit, &setter, _1)); + prop.subscribe(boost::bind(&setter_type::doit, &setter, _1)); - prop->set(42); - BOOST_CHECK_EQUAL(prop->get(), 42); + prop.set(42); + BOOST_CHECK_EQUAL(prop.get(), 42); BOOST_CHECK_EQUAL(setter._x, 42); - prop->set(34); - BOOST_CHECK_EQUAL(prop->get(), 34); + prop.set(34); + BOOST_CHECK_EQUAL(prop.get(), 34); BOOST_CHECK_EQUAL(setter._x, 34); } +BOOST_AUTO_TEST_CASE(test_prop_with_publisher){ + uhd::property_tree::sptr tree = uhd::property_tree::make(); + uhd::property &prop = tree->create("/"); + + getter_type getter; + prop.publish(boost::bind(&getter_type::doit, &getter)); + + getter._x = 42; + prop.set(0); //should not change + BOOST_CHECK_EQUAL(prop.get(), 42); + + getter._x = 34; + prop.set(0); //should not change + BOOST_CHECK_EQUAL(prop.get(), 34); +} + +BOOST_AUTO_TEST_CASE(test_prop_with_publisher_and_subscriber){ + uhd::property_tree::sptr tree = uhd::property_tree::make(); + uhd::property &prop = tree->create("/"); + + getter_type getter; + prop.publish(boost::bind(&getter_type::doit, &getter)); + + setter_type setter; + prop.subscribe(boost::bind(&setter_type::doit, &setter, _1)); + + getter._x = 42; + prop.set(0); + BOOST_CHECK_EQUAL(prop.get(), 42); + BOOST_CHECK_EQUAL(setter._x, 0); + + getter._x = 34; + prop.set(1); + BOOST_CHECK_EQUAL(prop.get(), 34); + BOOST_CHECK_EQUAL(setter._x, 1); +} + BOOST_AUTO_TEST_CASE(test_prop_with_coercion){ - uhd::property::sptr prop = uhd::property::make(); + uhd::property_tree::sptr tree = uhd::property_tree::make(); + uhd::property &prop = tree->create("/"); setter_type setter; - prop->subscribe(boost::bind(&setter_type::doit, &setter, _1)); + prop.subscribe(boost::bind(&setter_type::doit, &setter, _1)); coercer_type coercer; - prop->subscribe_master(boost::bind(&coercer_type::doit, &coercer, _1)); + prop.subscribe_master(boost::bind(&coercer_type::doit, &coercer, _1)); - prop->set(42); - BOOST_CHECK_EQUAL(prop->get(), 40); + prop.set(42); + BOOST_CHECK_EQUAL(prop.get(), 40); BOOST_CHECK_EQUAL(setter._x, 40); - prop->set(34); - BOOST_CHECK_EQUAL(prop->get(), 32); + prop.set(34); + BOOST_CHECK_EQUAL(prop.get(), 32); BOOST_CHECK_EQUAL(setter._x, 32); } @@ -82,6 +131,7 @@ BOOST_AUTO_TEST_CASE(test_prop_tree){ tree->create("/test/prop1"); BOOST_CHECK(tree->exists("/test")); + BOOST_CHECK_THROW(tree->access("/test"), std::exception); BOOST_CHECK(tree->exists("/test/prop0")); BOOST_CHECK(tree->exists("/test/prop1")); -- cgit v1.2.3