TCP Convergence Layer

The TCP Convergence Layer connects DTN nodes via a TCP channel. As with all TCP connections, it is reliable (meaning the underlying layers attempt to deliver all the data sent, in the order it was sent). In the context of a DTN, however, a TCP connection is only reliable while it is up. The DTN components (each endpoint of the TCP connection) are ready and willing to invoke various types of recovery mechanisms if the transfer of a bundle is interrupted by a broken TCP connection.

The TCP session between two DTN nodes only moves bundles in one direction. The TCP session itself is two directional, so that the TCP convergence layer on the bundle receiver can send feedback to the sender. In a case where bundles need to move both directions between two nodes, there will be two TCP connections, each one initiated by one of the sides. The side that initiates the connection sends bundles over it.

Interfaces and Links

Each TCP link needs to be configured on both sides. On one side, it is configured as a passive listener (called an interface by dtnd), and on the other side as an active session initiator (called a link). But take note of the receiver_connect option, which reverses things.

Passive Listener

The interface add command creates the passive listener side of the session. It always takes at least one argument, which is the local address. This is specified with either the IP or Host address families. For more information about address families, see the interface add documentation. After the local address, you may include optional arguments which are detailed below.

Active Initiator

The link add command creates an object in the system that is capable of initiating a connection outbound to other DTN nodes. Depending on the state of the link, as managed by the various options to the link command, it may or may not actually be actively opening or maintaining a TCP connection at a given time.

Options

These options can appear after the link add command, or after the interface add command.

NameTypeDefaultComment
bundle_ack_enabledbooleantrue Should we send an ACK when we have received the entire bundle?
connect_timeoutinteger miliseconds10000 (10 seconds) Number of milliseconds to wait for a TCP connection to be established.
idle_close_timeinteger seconds30 Number of seconds after which to close the connection if no data other than keepalives arrives.
keepalive_intervalinteger seconds2 The number of seconds between keepalives requested for both directions on this link. The actual value of this parameter for a connection will be decided during parameter negotiation.
local_addrIP address or a DNS hostname0.0.0.0 (interface), -1 (link) In the case of an interface, this is the IP address that the server will listen on. In the case of a link, the default ensures that the operating system choses the appropriate source address for the connection before it is initiated.
local_portIP port number5000 (interface), 0 (link) In the case of an interface, this is the TCP port that the server will listen on. In the case of a link, changing this setting from the default of 0 instructs the operating system to use the given port. In general, it is better to allow the OS to choose the source port itself.
partial_ack_leninteger bytes1024 If dtnd has read at least this much data without sending an acknowledgement, send one.
reactive_frag_enabledbooleantrue If the servers loses the connection while sending, should it fragment the bundle so that when the connection is working again the it can start sending from the last ack, instead of from the beginning?
readbuf_leninteger bytes32768 The maximum number of bytes to read from the network before flushing them to the local copy of the bundle. Recall that the local copy of the bundle might be in memory, and not on disk. See param set payload_mem_threshold command.
receiver_connectbooleanfalse This option reverses the direction of dataflow, making the initiator receive bundles. (Not yet implemented.)
rtt_timeoutinteger miliseconds5000 (5 seconds) Number of milliseconds to wait for an expected response from the other side. RTT means Round Trip Time.
test_fragment_sizeinteger bytes-1 (disabled) Artifically close the connection, simulating a link failure, after this many bytes. This feature is probably only useful while testing the fragmentation system. (No longer implemented.)
writebuf_leninteger bytes32768 The maximum number of bytes to read from the on-disk bundle at a time for buffering before it is sent across the connection.

Parameter Negotiation

Some parameters take effect solely inside one daemon or the other. Other paramaters are sent across the link at the beginning during a negotiation phase. The following table summarizes which parameters are subject to negotiation, and how the negotiation works.

NameNegotiation
partial_ack_lenMinimum of near side and far side.
keepalive_intervalMinimum of near side and far side.
idle_close_timeMinimum of near side and far side.
bundle_ack_enabledLogical AND of near and far side.
reactive_frag_enabledLogical AND of near and far side.
receiver_connect_Logical OR of near and far side.