Crate gwr_components

Crate gwr_components 

Source
Expand description

§gwr-components

Simulation components are the basic building blocks of any GWR model.

The GWR Engine runs components that are connected together using ports.

The gwr_components library provides a collection of connectable component primitives to be used when building models.

§Testing

Components can be tested by connecting them into a small simulation and driving their ports directly. For simple cases this can be done by hand with OutPort/InPort, but most component tests need the same testbench structure:

  1. Create an engine and the device under test (DUT).
  2. Connect driver ports to DUT input ports.
  3. Connect receiver ports to DUT output ports.
  4. Run a sequence of sends, expects, delays, and no-traffic checks.

The build_component_harness! macro will generate the repeated testbench code. It generates the harness struct, Port/Step enums, helper macros, etc.

Harnesses are usually declared inside a small test module. This keeps generated names such as Port, Step, and the helper macros local to the harness and avoids clashes with other harnesses in the same test file.

For example, the harness around a Delay component is created and used below:

mod delay_harness {
    use std::rc::Rc;

    use gwr_components::build_component_harness;
    use gwr_components::delay::Delay;
    use gwr_engine::test_helpers::start_test;

    build_component_harness! {
        harness DelayHarness<T> {
            component: delay: Rc<Delay<T>>,
            rx ports: {
                Rx<T> => rx,
            },
            tx ports: {
                Tx<T> => tx,
            },
        }
    }

    #[test]
    fn delay_forwards_values() {
        let mut engine = start_test(file!());
        let clock = engine.default_clock();
        let delay = Delay::new_and_register(&engine, &clock, engine.top(), "delay", 5).unwrap();
        let mut harness = DelayHarness::new(engine, delay);

        harness.run_steps([
            send_rx!(10),
            expect_no_traffic!(&[Port::Tx], 4),
            expect_tx!(10),
        ]);
    }
}

The macro supports scalar RX/TX ports and RX/TX port arrays. Each port section is optional, so a source-only component can define only tx ports and a sink-only component can define only rx ports.

Step can be a send, expect, delay, no-traffic check, Seq(Vec<Step<...>>) that runs child steps in order, or Par(Vec<Step<...>>) that runs child steps concurrently and waits for all of them before moving on. The generated seq! and par! helper macros build those recursive control structures and record their source location, so tests can express parallel sequences on different ports while keeping error messages tied to the call site.

The harness checks that each step is used on a compatible port; for example, using an expect step on an RX port or a send step on a TX port will fail the test.

Use run_steps([Step<...>]) for fixed test sequences and run_step_generator(iterator) for stateful generators that yield steps as the test progresses.

§Further reading

The components chapter of the gwr-developer-guide contains details on the creation and use of new components.

Modules§

arbiter
Perform arbitration between a number of interfaces.
connect
Helper connection macros
delay
A component that adds delay_ticks between receiving anything and sending it on to its output.
flow_controls
Components used for flow-control.
queue
Generic queues.
router
Perform routing between an input interface and a number number of outputs.
sink
A data sink.
source
A data source.
store
A data store.
test_helpers
types
Shared types.

Macros§

borrow_option
Get a reference to a variable stored in a RefCell<Option<>>.
borrow_option_mut
Get a mutable reference to a variable stored in a RefCell<Option<>>.
build_component_harness
Build a simulation test harness around a component.
connect_dummy_rx
Create and connect a dummy RX port
connect_dummy_tx
Create and connect a dummy TX port
connect_port
Connect an OutPort port to an InPort
connect_tx
Connect a tx port for a subcomponent.
connect_tx_i
Connect a tx port for a subcomponent where the port is one of an array.
option_box_chain
option_box_repeat
option_rc_limiter
port_rx
Access rx port for a subcomponent.
port_rx_i
Access an individual index of an rx port array for a subcomponent.
rc_limiter
Create a RateLimiter wrapped in an Rc.
take_option
Take a variable out of a RefCell<Option<>>.