|
Open Model Railroad Network (OpenMRN)
|
This class helps waiting for traction responses. More...
#include <TractionClient.hxx>
Public Member Functions | |
| TractionResponseHandler (openlcb::If *iface, openlcb::Node *local_node) | |
| void | wait_for_response (NodeHandle target_node, uint8_t expected_type, ::Timer *trigger) |
| Starts waiting for a traction control reply from a given node with the first byte 'expected_type'. | |
| Buffer< GenMessage > * | response () |
| Caller must unref this buffer when done with it. | |
| void | wait_timeout () |
| Call this if the timeout has expired. | |
Public Member Functions inherited from openlcb::IncomingMessageStateFlow | |
| IncomingMessageStateFlow (If *iface) | |
| If * | iface () |
| GenMessage * | nmsg () |
| Returns the NMRAnet message we received. | |
Public Member Functions inherited from StateFlow< Buffer< GenMessage >, QList< 4 > > | |
| StateFlow (Service *service) | |
| Constructor. | |
Public Member Functions inherited from TypedStateFlow< MessageType, Base > | |
| TypedStateFlow (Service *service) | |
| Constructor. | |
| virtual | ~TypedStateFlow () |
| Destructor. | |
| void | send (MessageType *msg, unsigned priority=UINT_MAX) OVERRIDE |
| Sends a message to the state flow for processing. | |
Public Member Functions inherited from FlowInterface< MessageType > | |
| virtual Pool * | pool () |
| virtual MessageType * | type_helper () |
| This function is never user in the code, but GDB can use it to infer the correct message types. | |
| MessageType * | alloc () |
| Synchronously allocates a message buffer from the pool of this flow. | |
| void | alloc_async (Executable *target) |
| Asynchronously allocates a message buffer from the pool of this flow. | |
Private Member Functions | |
| void | start_listening () |
| void | stop_listening () |
| Action | entry () OVERRIDE |
| Entry into the StateFlow activity. | |
Private Attributes | |
| openlcb::NodeHandle | expectedSrc_ |
| openlcb::Node * | expectedDst_ |
| uint8_t | expectedType_ |
| ::Timer * | trigger_ |
| Buffer< GenMessage > * | response_ |
Additional Inherited Members | |
Public Types inherited from TypedStateFlow< MessageType, Base > | |
| typedef Base::Action | Action |
| Allows using Action without having StateFlowBase:: prefix in front of it. | |
Public Types inherited from FlowInterface< MessageType > | |
| typedef MessageType | message_type |
| Stores the message template type for external reference. | |
Static Public Member Functions inherited from FlowInterface< MessageType > | |
| static MessageType * | cast_alloc (QMember *entry) |
| Down casts and initializes an asynchronous allocation result to the appropriate flow's buffer type. | |
Protected Member Functions inherited from TypedStateFlow< MessageType, Base > | |
| void | release () OVERRIDE |
| Unrefs the current buffer. | |
| void | return_buffer () |
| For state flows that are operated using invoke_subflow_and_wait this is a way to hand back the buffer to the caller. | |
| MessageType * | message () |
| MessageType * | transfer_message () |
| Releases ownership of the current message. | |
This class helps waiting for traction responses.
It listens for traction control response messages, matches them to an expected destination/responsetype pair, and triggers a timeout when the matching response arrives.
Synchronous usage: auto* b = ... // allocate and fill reuqest buffer. SyncTimeout t(g_executor.active_timers()); t.start(MSEC_TO_NSEC(300)); response_handler.wait_for_response(b->data()->dst, b->data()->payload[0], &t); iface->addressed_message_write_flow()->send(b); t.wait_for_notification(); response_handler.wait_timeout(); // Stops listening. if (response_handler.response()) { // we have a response – use it from response_handler->response() response_handler.response()->unref(); } else { // timeout }
Asynchronous usage:
FlowClass : public StateFlow... {
Action send_request() { auto* b = get_allocation_result(iface->addressed_message_write_flow()); // fill b responseHandler_.wait_for_response(b->data()->dst, b->data()->payload[0], &t_); iface->addressed_message_write_flow()->send(b); return sleep_and_call(&t_, MSEC_TO_NSEC(), STATE(parse_response)); }
Action parse_response() { responseHandler_.wait_timeout(); if (response_handler.response()) { // parse response ... do useful stuff. responseHandler_.response()->unref(); } else { return gone_to_error(); } }
TractionResponseHandler responseHandler_; StateFlowTimer t_; };
Definition at line 95 of file TractionClient.hxx.
|
inline |
Definition at line 98 of file TractionClient.hxx.
|
inlineprivatevirtual |
Entry into the StateFlow activity.
Pure virtual which must be defined by derived class.
@TODO(balazs.racz) factor out this code into a helper function that allows matching an incoming response frame to an expected NodeHandle.
@TODO(balazs.racz) we should start an alias resolution process here.
Implements TypedStateFlow< MessageType, Base >.
Definition at line 154 of file TractionClient.hxx.
|
inline |
Caller must unref this buffer when done with it.
Definition at line 121 of file TractionClient.hxx.
|
inlineprivate |
Definition at line 140 of file TractionClient.hxx.
|
inlineprivate |
Definition at line 147 of file TractionClient.hxx.
|
inline |
Starts waiting for a traction control reply from a given node with the first byte 'expected_type'.
Will wake up the given timer if a reply arrives.
Definition at line 110 of file TractionClient.hxx.
|
inline |
Call this if the timeout has expired.
Call only on the service executor. If the caller got notified due to a response, it is still okay to call this. @TODO(balazs.racz) rename to something like wait_done_or_timeout()
Definition at line 130 of file TractionClient.hxx.
|
private |
Definition at line 213 of file TractionClient.hxx.
|
private |
Definition at line 212 of file TractionClient.hxx.
|
private |
Definition at line 215 of file TractionClient.hxx.
|
private |
Definition at line 217 of file TractionClient.hxx.
|
private |
Definition at line 216 of file TractionClient.hxx.