aboutsummaryrefslogtreecommitdiffstats
path: root/host/tests/actions_test.cpp
blob: 20e2bdf6e47fe2011543b077f6f5b2a916b99b32 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
//
// Copyright 2019 Ettus Research, a National Instruments Brand
//
// SPDX-License-Identifier: GPL-3.0-or-later
//

#include <uhd/rfnoc/node.hpp>
#include <uhd/rfnoc/actions.hpp>
#include <uhd/utils/log.hpp>
#include <uhdlib/rfnoc/node_accessor.hpp>
#include <uhdlib/rfnoc/prop_accessor.hpp>
#include <uhdlib/rfnoc/graph.hpp>
#include <boost/test/unit_test.hpp>
#include <iostream>

#include "rfnoc_graph_mock_nodes.hpp"


const std::string STREAM_CMD_KEY = "stream_cmd";

BOOST_AUTO_TEST_CASE(test_actions_single_node)
{
    node_accessor_t node_accessor{};

    // Define some mock nodes:
    mock_radio_node_t mock_radio(0);

    auto stream_cmd =
        stream_cmd_action_info::make(uhd::stream_cmd_t::STREAM_MODE_START_CONTINUOUS);
    auto other_cmd = action_info::make("FOO");

    node_accessor.send_action(&mock_radio, {res_source_info::INPUT_EDGE, 0}, stream_cmd);
    node_accessor.send_action(&mock_radio, {res_source_info::INPUT_EDGE, 0}, other_cmd);

    mock_radio.update_fwd_policy(node_t::forwarding_policy_t::ONE_TO_ONE);
    node_accessor.send_action(&mock_radio, {res_source_info::INPUT_EDGE, 0}, other_cmd);
    mock_radio.update_fwd_policy(node_t::forwarding_policy_t::ONE_TO_FAN);
    node_accessor.send_action(&mock_radio, {res_source_info::INPUT_EDGE, 0}, other_cmd);
    mock_radio.update_fwd_policy(node_t::forwarding_policy_t::ONE_TO_ALL);
    node_accessor.send_action(&mock_radio, {res_source_info::INPUT_EDGE, 0}, other_cmd);
    mock_radio.update_fwd_policy(node_t::forwarding_policy_t::ONE_TO_ALL_IN);
    node_accessor.send_action(&mock_radio, {res_source_info::INPUT_EDGE, 0}, other_cmd);
    mock_radio.update_fwd_policy(node_t::forwarding_policy_t::ONE_TO_ALL_OUT);
    node_accessor.send_action(&mock_radio, {res_source_info::INPUT_EDGE, 0}, other_cmd);

    uhd::rfnoc::detail::graph_t graph{};
    graph.connect(&mock_radio, &mock_radio, {0, 0, graph_edge_t::DYNAMIC, false});
    graph.commit();
    stream_cmd =
        stream_cmd_action_info::make(uhd::stream_cmd_t::STREAM_MODE_NUM_SAMPS_AND_DONE);
    stream_cmd->stream_cmd.num_samps = 37;
    node_accessor.post_action(&mock_radio, {res_source_info::USER, 0}, stream_cmd);
    BOOST_REQUIRE_EQUAL(mock_radio.last_num_samps, 37);
}

BOOST_AUTO_TEST_CASE(test_actions_simple_graph)
{
    node_accessor_t node_accessor{};
    uhd::rfnoc::detail::graph_t graph{};

    // Define some mock nodes:
    mock_radio_node_t mock_rx_radio{0};
    mock_ddc_node_t mock_ddc{};
    mock_fifo_t mock_fifo{1};
    mock_streamer_t mock_streamer{1};

    // These init calls would normally be done by the framework
    node_accessor.init_props(&mock_rx_radio);
    node_accessor.init_props(&mock_ddc);
    node_accessor.init_props(&mock_fifo);
    node_accessor.init_props(&mock_streamer);

    graph.connect(&mock_rx_radio, &mock_ddc, {0, 0, graph_edge_t::DYNAMIC, true});
    graph.connect(&mock_ddc, &mock_fifo, {0, 0, graph_edge_t::DYNAMIC, true});
    graph.connect(&mock_fifo, &mock_streamer, {0, 0, graph_edge_t::DYNAMIC, true});
    graph.commit();

    // Force the DDC to actually set a decimation rate != 1
    mock_streamer.set_property<double>("samp_rate", 10e6, 0);

    uhd::stream_cmd_t num_samps_cmd(uhd::stream_cmd_t::STREAM_MODE_NUM_SAMPS_AND_DONE);
    constexpr size_t NUM_SAMPS = 100;
    num_samps_cmd.num_samps = NUM_SAMPS;

    mock_streamer.issue_stream_cmd(num_samps_cmd, 0);
    BOOST_CHECK_EQUAL(NUM_SAMPS * mock_ddc.get_property<int>("decim", 0),
            mock_rx_radio.last_num_samps);
}