From c0b2e69fb1d10e3b53a97e56070634cc92da8fa2 Mon Sep 17 00:00:00 2001 From: Martin Braun Date: Thu, 7 Apr 2022 10:09:08 +0200 Subject: tests: rfnoc: Add another loop graph test This test mimics the Radio <-> Replay loop graph. Because we need one back-edge in this graph, this test makes sure the atomic item sizes still resolve. --- host/tests/rfnoc_propprop_test.cpp | 110 +++++++++++++++++++++++++++++++++++++ 1 file changed, 110 insertions(+) (limited to 'host/tests/rfnoc_propprop_test.cpp') diff --git a/host/tests/rfnoc_propprop_test.cpp b/host/tests/rfnoc_propprop_test.cpp index 130137a28..c4693418d 100644 --- a/host/tests/rfnoc_propprop_test.cpp +++ b/host/tests/rfnoc_propprop_test.cpp @@ -15,6 +15,7 @@ #include #include #include +#include /*! Mock invalid node * @@ -654,3 +655,112 @@ BOOST_AUTO_TEST_CASE(test_graph_node_deletion_resolver_fix) BOOST_CHECK_EQUAL(mock_ddc._samp_rate_in.get() / disconnected_interp_ratio, mock_ddc._samp_rate_out.get()); } + + +BOOST_AUTO_TEST_CASE(test_graph_node_loop_resolve) +{ + // Mock the radio with only the AIS property. It will keep AIS at a multiple + // of 4. + class mock_radio_ais_node_t : public node_t + { + public: + mock_radio_ais_node_t() + { + register_property(&_ais_in); + register_property(&_ais_out); + + add_property_resolver({&_ais_in}, {&_ais_in}, [this]() { + _ais_in = std::max(4, (_ais_in.get() / 4) * 4); + }); + add_property_resolver({&_ais_out}, {&_ais_out}, [this]() { + _ais_out = std::max(4, (_ais_out.get() / 4) * 4); + }); + } + + std::string get_unique_id() const override + { + return "MOCK_RADIO_AIS_NODE"; + } + + size_t get_num_input_ports() const override + { + return 1; + } + + size_t get_num_output_ports() const override + { + return 1; + } + + private: + property_t _ais_in{ + PROP_KEY_ATOMIC_ITEM_SIZE, 4, {res_source_info::INPUT_EDGE}}; + property_t _ais_out{ + PROP_KEY_ATOMIC_ITEM_SIZE, 8, {res_source_info::OUTPUT_EDGE}}; + }; + + // Mock the replay with only the AIS property. It will keep AIS at exactly 8. + class mock_replay_ais_node_t : public node_t + { + public: + mock_replay_ais_node_t() + { + register_property(&_ais_in); + register_property(&_ais_out); + + add_property_resolver({&_ais_in}, {&_ais_in}, [this]() { + _ais_in = 8; + }); + add_property_resolver({&_ais_out}, {&_ais_out}, [this]() { + _ais_out = 8; + }); + } + + std::string get_unique_id() const override + { + return "MOCK_REPLAY_AIS_NODE"; + } + + size_t get_num_input_ports() const override + { + return 1; + } + + size_t get_num_output_ports() const override + { + return 1; + } + + private: + property_t _ais_in{ + PROP_KEY_ATOMIC_ITEM_SIZE, 4, {res_source_info::INPUT_EDGE}}; + property_t _ais_out{ + PROP_KEY_ATOMIC_ITEM_SIZE, 8, {res_source_info::OUTPUT_EDGE}}; + }; + + // Now let's define things + node_accessor_t node_accessor{}; + uhd::rfnoc::detail::graph_t graph{}; + + // Create mock blocks + mock_radio_ais_node_t mock_radio_ais_node{}; + mock_replay_ais_node_t mock_replay_ais_node{}; + + // These init calls would normally be done by the framework + node_accessor.init_props(&mock_radio_ais_node); + node_accessor.init_props(&mock_replay_ais_node); + + // Connect the radio to the replay in a simple graph + uhd::rfnoc::detail::graph_t::graph_edge_t edge_info; + edge_info.src_port = 0; + edge_info.dst_port = 0; + edge_info.property_propagation_active = true; + edge_info.edge = uhd::rfnoc::detail::graph_t::graph_edge_t::DYNAMIC; + + graph.connect(&mock_radio_ais_node, &mock_replay_ais_node, edge_info); + // Declare back-edge + edge_info.property_propagation_active = false; + graph.connect(&mock_replay_ais_node, &mock_radio_ais_node, edge_info); + UHD_LOG_INFO("TEST", "Committing replay/radio loop graph"); + BOOST_CHECK_NO_THROW(graph.commit();); +} -- cgit v1.2.3