#include <StreamConvergenceLayer.h>
TCP, SCTP, and Bluetooth RFCOMM). The goal is to share as much functionality as possible between protocols that have in-order, reliable, delivery semantics.
For the protocol, bundles are broken up into configurable-sized segments that are sent sequentially. Only a single bundle is inflight on the wire at one time (i.e. we don't interleave segments from different bundles). When segment acknowledgements are enabled (the default behavior), the receiving node sends an acknowledgement for each segment of the bundle that was received.
Keepalive messages are sent back and forth to ensure that the connection remains open. In the case of on demand links, a configurable idle timer is maintained to close the link when no bundle traffic has been sent or received. Links that are expected to be open but have broken due to underlying network conditions (i.e. always on and on demand links) are reopened by a timer that is managed by the contact manager.
Flow control is managed through the poll callbacks given by the base class CLConnection. In send_pending_data, we check if there are any acks that need to be sent, then check if there are bundle segments to be sent (i.e. acks are given priority). The only exception to this is that the connection might be write blocked in the middle of sending a data segment. In that case, we must first finish transmitting the current segment before sending any other acks (or the shutdown message), otherwise those messages will be consumed as part of the payload.
To make sure that we don't deadlock with the other side, we always drain any data that is ready on the channel. All incoming messages mark state in the appropriate data structures (i.e. InFlightList and IncomingList), then rely on send_pending_data to send the appropriate responses.
The InflightBundle is used to record state about bundle transmissions. To record the segments that have been sent, we fill in the sent_data_ sparse bitmap with the range of bytes as we send segments out. As acks arrive, we extend the ack_data_ field to match. Once the whole bundle is acked, the entry is removed from the InFlightList.
The IncomingBundle is used to record state about bundle reception. The rcvd_data_ bitmap is extended contiguously with the amount of data that has been received, including partially received segments. To track segments that we have received but haven't yet acked, we set a single bit for the offset of the end of the segment in the ack_data_ bitmap. We also separately record the total range of acks that have been previously sent in acked_length_. As we send acks out, we clear away the bits in ack_data_
Definition at line 79 of file StreamConvergenceLayer.h.
Public Member Functions | |
StreamConvergenceLayer (const char *logpath, const char *cl_name, u_int8_t cl_version) | |
Constructor. | |
Protected Types | |
enum | contact_header_flags_t { SEGMENT_ACK_ENABLED = 1 << 0, REACTIVE_FRAG_ENABLED = 1 << 1, NEGATIVE_ACK_ENABLED = 1 << 2 } |
Values for ContactHeader flags. More... | |
enum | msg_type_t { DATA_SEGMENT = 0x1 << 4, ACK_SEGMENT = 0x2 << 4, REFUSE_BUNDLE = 0x3 << 4, KEEPALIVE = 0x4 << 4, SHUTDOWN = 0x5 << 4 } |
Valid type codes for the protocol messages, shifted into the high-order four bits of the byte. More... | |
enum | data_segment_flags_t { BUNDLE_START = 0x1 << 1, BUNDLE_END = 0x1 << 0 } |
Valid flags for the DATA_SEGMENT message. More... | |
enum | shutdown_flags_t { SHUTDOWN_HAS_REASON = 0x1 << 1, SHUTDOWN_HAS_DELAY = 0x1 << 0 } |
Valid flags for the SHUTDOWN message. More... | |
enum | shutdown_reason_t { SHUTDOWN_NO_REASON = 0xff, SHUTDOWN_IDLE_TIMEOUT = 0x0, SHUTDOWN_VERSION_MISMATCH = 0x1, SHUTDOWN_BUSY = 0x2 } |
Values for the SHUTDOWN reason codes. More... | |
typedef ConnectionConvergenceLayer::LinkParams | LinkParams |
For some gcc variants, this typedef seems to be needed. | |
Protected Member Functions | |
void | dump_link (Link *link, oasys::StringBuffer *buf) |
Virtual from ConvergenceLayer. | |
bool | parse_link_params (LinkParams *params, int argc, const char **argv, const char **invalidp) |
Virtual from ConnectionConvergenceLayer. | |
bool | finish_init_link (Link *link, LinkParams *params) |
Virtual from ConnectionConvergenceLayer. | |
Static Protected Member Functions | |
static const char * | shutdown_reason_to_str (shutdown_reason_t reason) |
Convert a reason code to a string. | |
Protected Attributes | |
struct dtn::StreamConvergenceLayer::ContactHeader | packed |
Contact initiation header. | |
u_int8_t | cl_version_ |
Version of the actual CL protocol. | |
Classes | |
class | Connection |
Stream connection class. More... | |
struct | ContactHeader |
Contact initiation header. More... | |
class | StreamLinkParams |
Link parameters shared among all stream based convergence layers. More... |
typedef ConnectionConvergenceLayer::LinkParams dtn::StreamConvergenceLayer::LinkParams [protected] |
For some gcc variants, this typedef seems to be needed.
Definition at line 264 of file StreamConvergenceLayer.h.
enum dtn::StreamConvergenceLayer::contact_header_flags_t [protected] |
Values for ContactHeader flags.
SEGMENT_ACK_ENABLED | segment acks requested |
REACTIVE_FRAG_ENABLED | reactive fragmentation enabled |
NEGATIVE_ACK_ENABLED | refuse bundle enabled |
Definition at line 91 of file StreamConvergenceLayer.h.
enum dtn::StreamConvergenceLayer::msg_type_t [protected] |
Valid type codes for the protocol messages, shifted into the high-order four bits of the byte.
The lower four bits are used for per-message flags, defined below.
Definition at line 114 of file StreamConvergenceLayer.h.
enum dtn::StreamConvergenceLayer::data_segment_flags_t [protected] |
enum dtn::StreamConvergenceLayer::shutdown_flags_t [protected] |
enum dtn::StreamConvergenceLayer::shutdown_reason_t [protected] |
Values for the SHUTDOWN reason codes.
SHUTDOWN_NO_REASON | no reason code (never sent) |
SHUTDOWN_IDLE_TIMEOUT | idle connection |
SHUTDOWN_VERSION_MISMATCH | version mismatch |
SHUTDOWN_BUSY | node is busy |
Definition at line 143 of file StreamConvergenceLayer.h.
dtn::StreamConvergenceLayer::StreamConvergenceLayer | ( | const char * | logpath, | |
const char * | cl_name, | |||
u_int8_t | cl_version | |||
) |
static const char* dtn::StreamConvergenceLayer::shutdown_reason_to_str | ( | shutdown_reason_t | reason | ) | [inline, static, protected] |
Convert a reason code to a string.
Definition at line 153 of file StreamConvergenceLayer.h.
References NOTREACHED, SHUTDOWN_BUSY, SHUTDOWN_IDLE_TIMEOUT, SHUTDOWN_NO_REASON, and SHUTDOWN_VERSION_MISMATCH.
Referenced by dtn::StreamConvergenceLayer::Connection::handle_shutdown().
void dtn::StreamConvergenceLayer::dump_link | ( | Link * | link, | |
oasys::StringBuffer * | buf | |||
) | [protected, virtual] |
Virtual from ConvergenceLayer.
Reimplemented from dtn::ConnectionConvergenceLayer.
Reimplemented in dtn::BluetoothConvergenceLayer, and dtn::TCPConvergenceLayer.
Definition at line 102 of file StreamConvergenceLayer.cc.
References oasys::StringBuffer::appendf(), ASSERT, dtn::Link::cl_info(), dtn::ConnectionConvergenceLayer::dump_link(), dtn::StreamConvergenceLayer::StreamLinkParams::keepalive_interval_, dtn::StreamConvergenceLayer::StreamLinkParams::negative_ack_enabled_, dtn::StreamConvergenceLayer::StreamLinkParams::segment_ack_enabled_, and dtn::StreamConvergenceLayer::StreamLinkParams::segment_length_.
Referenced by dtn::TCPConvergenceLayer::dump_link(), and dtn::BluetoothConvergenceLayer::dump_link().
bool dtn::StreamConvergenceLayer::parse_link_params | ( | LinkParams * | params, | |
int | argc, | |||
const char ** | argv, | |||
const char ** | invalidp | |||
) | [protected, virtual] |
Virtual from ConnectionConvergenceLayer.
Reimplemented from dtn::ConnectionConvergenceLayer.
Reimplemented in dtn::BluetoothConvergenceLayer, and dtn::TCPConvergenceLayer.
Definition at line 49 of file StreamConvergenceLayer.cc.
References oasys::OptParser::addopt(), ASSERT, cl_version_, count, dtn::StreamConvergenceLayer::StreamLinkParams::keepalive_interval_, dtn::StreamConvergenceLayer::StreamLinkParams::negative_ack_enabled_, oasys::OptParser::parse_and_shift(), dtn::ConnectionConvergenceLayer::parse_link_params(), dtn::StreamConvergenceLayer::StreamLinkParams::segment_ack_enabled_, and dtn::StreamConvergenceLayer::StreamLinkParams::segment_length_.
Referenced by dtn::TCPConvergenceLayer::parse_link_params(), and dtn::BluetoothConvergenceLayer::parse_link_params().
bool dtn::StreamConvergenceLayer::finish_init_link | ( | Link * | link, | |
LinkParams * | params | |||
) | [protected, virtual] |
Virtual from ConnectionConvergenceLayer.
Reimplemented from dtn::ConnectionConvergenceLayer.
Definition at line 87 of file StreamConvergenceLayer.cc.
References ASSERT, dtn::StreamConvergenceLayer::StreamLinkParams::segment_ack_enabled_, and dtn::Link::set_reliable().
struct dtn::StreamConvergenceLayer::ContactHeader dtn::StreamConvergenceLayer::packed [protected] |
Contact initiation header.
Sent at the beginning of a contact.
u_int8_t dtn::StreamConvergenceLayer::cl_version_ [protected] |
Version of the actual CL protocol.
Definition at line 182 of file StreamConvergenceLayer.h.
Referenced by parse_link_params().