summaryrefslogtreecommitdiff
path: root/doc/rfc/rfc7016.txt
diff options
context:
space:
mode:
Diffstat (limited to 'doc/rfc/rfc7016.txt')
-rw-r--r--doc/rfc/rfc7016.txt6331
1 files changed, 6331 insertions, 0 deletions
diff --git a/doc/rfc/rfc7016.txt b/doc/rfc/rfc7016.txt
new file mode 100644
index 0000000..7a5d503
--- /dev/null
+++ b/doc/rfc/rfc7016.txt
@@ -0,0 +1,6331 @@
+
+
+
+
+
+
+Internet Engineering Task Force (IETF) M. Thornburgh
+Request for Comments: 7016 Adobe
+Category: Informational November 2013
+ISSN: 2070-1721
+
+
+ Adobe's Secure Real-Time Media Flow Protocol
+
+Abstract
+
+ This memo describes Adobe's Secure Real-Time Media Flow Protocol
+ (RTMFP), an endpoint-to-endpoint communication protocol designed to
+ securely transport parallel flows of real-time video, audio, and data
+ messages, as well as bulk data, over IP networks. RTMFP has features
+ that make it effective for peer-to-peer (P2P) as well as client-
+ server communications, even when Network Address Translators (NATs)
+ are used.
+
+Status of This Memo
+
+ This document is not an Internet Standards Track specification; it is
+ published for informational purposes.
+
+ This document is a product of the Internet Engineering Task Force
+ (IETF). It has been approved for publication by the Internet
+ Engineering Steering Group (IESG). Not all documents approved by the
+ IESG are a candidate for any level of Internet Standard; see Section
+ 2 of RFC 5741.
+
+ Information about the current status of this document, any errata,
+ and how to provide feedback on it may be obtained at
+ http://www.rfc-editor.org/info/rfc7016.
+
+IESG Note
+
+ This document represents technology developed outside the processes
+ of the IETF and the IETF community has determined that it is useful
+ to publish it as an RFC in its current form. It is a product of the
+ IETF only in that it has received public review and has been approved
+ for publication by the Internet Engineering Steering Group (IESG),
+ but the content of the document does not represent a consensus of the
+ IETF.
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 1]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+Copyright Notice
+
+ Copyright (c) 2013 IETF Trust and the persons identified as the
+ document authors. All rights reserved.
+
+ This document is subject to BCP 78 and the IETF Trust's Legal
+ Provisions Relating to IETF Documents
+ (http://trustee.ietf.org/license-info) in effect on the date of
+ publication of this document. Please review these documents
+ carefully, as they describe your rights and restrictions with respect
+ to this document. Code Components extracted from this document must
+ include Simplified BSD License text as described in Section 4.e of
+ the Trust Legal Provisions and are provided without warranty as
+ described in the Simplified BSD License.
+
+ This document may not be modified, and derivative works of it may not
+ be created, except to format it for publication as an RFC or to
+ translate it into languages other than English.
+
+Table of Contents
+
+ 1. Introduction ....................................................5
+ 1.1. Design Highlights of RTMFP .................................6
+ 1.2. Terminology ................................................7
+ 2. Syntax ..........................................................8
+ 2.1. Common Elements ............................................8
+ 2.1.1. Elementary Types and Constructs .....................8
+ 2.1.2. Variable Length Unsigned Integer (VLU) .............10
+ 2.1.3. Option .............................................10
+ 2.1.4. Option List ........................................11
+ 2.1.5. Internet Socket Address (Address) ..................12
+ 2.2. Network Layer .............................................13
+ 2.2.1. Encapsulation ......................................13
+ 2.2.2. Multiplex ..........................................13
+ 2.2.3. Encryption .........................................14
+ 2.2.4. Packet .............................................15
+ 2.3. Chunks ....................................................18
+ 2.3.1. Packet Fragment Chunk ..............................20
+ 2.3.2. Initiator Hello Chunk (IHello) .....................21
+ 2.3.3. Forwarded Initiator Hello Chunk (FIHello) ..........22
+ 2.3.4. Responder Hello Chunk (RHello) .....................23
+ 2.3.5. Responder Redirect Chunk (Redirect) ................24
+ 2.3.6. RHello Cookie Change Chunk .........................26
+ 2.3.7. Initiator Initial Keying Chunk (IIKeying) ..........27
+ 2.3.8. Responder Initial Keying Chunk (RIKeying) ..........29
+ 2.3.9. Ping Chunk .........................................31
+ 2.3.10. Ping Reply Chunk ..................................32
+
+
+
+
+Thornburgh Informational [Page 2]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ 2.3.11. User Data Chunk ...................................33
+ 2.3.11.1. Options for User Data ....................35
+ 2.3.11.1.1. User's Per-Flow Metadata ......35
+ 2.3.11.1.2. Return Flow Association .......36
+ 2.3.12. Next User Data Chunk ..............................37
+ 2.3.13. Data Acknowledgement Bitmap Chunk (Bitmap Ack) ....39
+ 2.3.14. Data Acknowledgement Ranges Chunk (Range Ack) .....41
+ 2.3.15. Buffer Probe Chunk ................................43
+ 2.3.16. Flow Exception Report Chunk .......................43
+ 2.3.17. Session Close Request Chunk (Close) ...............44
+ 2.3.18. Session Close Acknowledgement Chunk (Close Ack) ...44
+ 3. Operation ......................................................45
+ 3.1. Overview ..................................................45
+ 3.2. Endpoint Identity .........................................46
+ 3.3. Packet Multiplex ..........................................48
+ 3.4. Packet Fragmentation ......................................48
+ 3.5. Sessions ..................................................50
+ 3.5.1. Startup ............................................53
+ 3.5.1.1. Normal Handshake ..........................53
+ 3.5.1.1.1. Initiator ......................54
+ 3.5.1.1.2. Responder ......................55
+ 3.5.1.2. Cookie Change .............................57
+ 3.5.1.3. Glare .....................................59
+ 3.5.1.4. Redirector ................................60
+ 3.5.1.5. Forwarder .................................61
+ 3.5.1.6. Redirector and Forwarder with NAT .........63
+ 3.5.1.7. Load Distribution and Fault Tolerance .....66
+ 3.5.2. Congestion Control .................................67
+ 3.5.2.1. Time Critical Reverse Notification ........68
+ 3.5.2.2. Retransmission Timeout ....................68
+ 3.5.2.3. Burst Avoidance ...........................71
+ 3.5.3. Address Mobility ...................................71
+ 3.5.4. Ping ...............................................72
+ 3.5.4.1. Keepalive .................................72
+ 3.5.4.2. Address Mobility ..........................73
+ 3.5.4.3. Path MTU Discovery ........................74
+ 3.5.5. Close ..............................................74
+ 3.6. Flows .....................................................75
+ 3.6.1. Overview ...........................................75
+ 3.6.1.1. Identity ..................................75
+ 3.6.1.2. Messages and Sequencing ...................76
+ 3.6.1.3. Lifetime ..................................77
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 3]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ 3.6.2. Sender .............................................78
+ 3.6.2.1. Startup ...................................80
+ 3.6.2.2. Queuing Data ..............................80
+ 3.6.2.3. Sending Data ..............................81
+ 3.6.2.3.1. Startup Options ................83
+ 3.6.2.3.2. Send Next Data .................83
+ 3.6.2.4. Processing Acknowledgements ...............83
+ 3.6.2.5. Negative Acknowledgement and Loss .........84
+ 3.6.2.6. Timeout ...................................85
+ 3.6.2.7. Abandoning Data ...........................86
+ 3.6.2.7.1. Forward Sequence Number
+ Update .........................86
+ 3.6.2.8. Examples ..................................87
+ 3.6.2.9. Flow Control ..............................89
+ 3.6.2.9.1. Buffer Probe ...................89
+ 3.6.2.10. Exception ................................89
+ 3.6.2.11. Close ....................................90
+ 3.6.3. Receiver ...........................................90
+ 3.6.3.1. Startup ...................................93
+ 3.6.3.2. Receiving Data ............................94
+ 3.6.3.3. Buffering and Delivering Data .............95
+ 3.6.3.4. Acknowledging Data ........................97
+ 3.6.3.4.1. Timing .........................98
+ 3.6.3.4.2. Size and Truncation ............99
+ 3.6.3.4.3. Constructing ...................99
+ 3.6.3.4.4. Delayed Acknowledgement .......100
+ 3.6.3.4.5. Obligatory Acknowledgement ....100
+ 3.6.3.4.6. Opportunistic
+ Acknowledgement ...............100
+ 3.6.3.4.7. Example .......................101
+ 3.6.3.5. Flow Control .............................102
+ 3.6.3.6. Receiving a Buffer Probe .................103
+ 3.6.3.7. Rejecting a Flow .........................103
+ 3.6.3.8. Close ....................................104
+ 4. IANA Considerations ...........................................104
+ 5. Security Considerations .......................................105
+ 6. Acknowledgements ..............................................106
+ 7. References ....................................................107
+ 7.1. Normative References .....................................107
+ 7.2. Informative References ...................................107
+ Appendix A. Example Congestion Control Algorithm .................108
+ A.1. Discussion ................................................108
+ A.2. Algorithm .................................................110
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 4]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+1. Introduction
+
+ Adobe's Secure Real-Time Media Flow Protocol (RTMFP) is intended for
+ use as a general purpose endpoint-to-endpoint data transport service
+ in IP networks. It has features that make it well suited to the
+ transport of real-time media (such as low-delay video, audio, and
+ data) as well as bulk data, and for client-server as well as peer-to-
+ peer (P2P) communication. These features include independent
+ parallel message flows that may have different delivery priorities,
+ variable message reliability (from TCP-like full reliability to
+ UDP-like best effort), multi-point congestion control, and built-in
+ security. Session multiplexing and facilities to support UDP
+ hole-punching simplify Network Address Translator (NAT) traversal in
+ peer-to-peer systems.
+
+ RTMFP is implemented in Flash Player, Adobe Integrated Runtime (AIR),
+ and Adobe Media Server (AMS, formerly Flash Media Server or FMS), all
+ from Adobe Systems Incorporated, and is used as the foundation
+ transport protocol for real-time video, audio, and data
+ communication, both client-server and P2P, in those products. At the
+ time of writing, the Adobe Flash Player runtime is installed on more
+ than one billion end-user desktop computers.
+
+ RTMFP was developed by Adobe Systems Incorporated and is not the
+ product of an IETF activity.
+
+ This memo describes the syntax and operation of the Secure Real-Time
+ Media Flow Protocol.
+
+ This memo describes a general security framework that, when combined
+ with an application-specific Cryptography Profile, can be used to
+ establish a confidential and authenticated session between endpoints.
+ The application-specific Cryptography Profile, not defined herein,
+ would detail the specific cryptographic algorithms, data formats, and
+ semantics to be used within this framework. Interoperation between
+ applications of RTMFP requires common or compatible Cryptography
+ Profiles.
+
+ Note to implementers: at the time of writing, the Cryptography
+ Profile used by the above-mentioned Adobe products is not publicly
+ described by Adobe. Implementers should investigate the availability
+ of documentation of that Cryptography Profile prior to implementing
+ RTMFP for the purpose of interoperation with the above-mentioned
+ Adobe products.
+
+
+
+
+
+
+
+Thornburgh Informational [Page 5]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+1.1. Design Highlights of RTMFP
+
+ Between any pair of communicating endpoints is a single,
+ bidirectional, secured, congestion controlled session.
+ Unidirectional flows convey messages from one end to the other within
+ the session. An endpoint can have concurrent sessions with multiple
+ other far endpoints.
+
+ Design highlights of RTMFP include the following:
+
+ o The security framework is an inherent part of the basic protocol.
+ The application designer chooses the cryptographic formats and
+ algorithms to suit the needs of the application, and may update
+ them as the state of the security arts progresses.
+
+ o Cryptographic Endpoint Discriminators can resist port scanning.
+
+ o All header, control, and framing information, except for network
+ addressing information and a session identifier, is encrypted
+ according to the Cryptography Profile.
+
+ o There is a single session and associated congestion control state
+ between a pair of endpoints.
+
+ o Each session may have zero or more unidirectional message-oriented
+ flows in each direction. All of a session's sending flows share
+ the session's congestion control state.
+
+ o Return Flow Association (Section 2.3.11.1.2) generalizes
+ bidirectional communication to arbitrarily complex trees of flows.
+
+ o Messages in flows can be arbitrarily large and are fragmented for
+ transmission.
+
+ o Messages of any size may be sent with full, partial, or no
+ reliability (sender's choice). Messages may be delivered to the
+ receiving user in original queuing order or network arrival order
+ (receiver's choice).
+
+ o Flows are named with arbitrary, user-defined metadata
+ (Section 2.3.11.1.1) rather than port or stream numbers.
+
+ o The sequence numbers of each flow are independent of all other
+ flows and are not permanently bound to a session-wide transmission
+ ordering. This allows real-time priority decisions to be made at
+ transmission or retransmission time.
+
+
+
+
+
+Thornburgh Informational [Page 6]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ o Each flow has its own receive window and, therefore, independent
+ flow control.
+
+ o Round trips are expensive and are minimized or eliminated when
+ possible.
+
+ o After a session is established, flows begin by sending the flow's
+ messages with no additional handshake (and associated round
+ trips).
+
+ o Transmitting bytes on the network is much more expensive than
+ moving bytes in a CPU or memory. Wasted bytes are minimized or
+ eliminated when possible and practical, and variable length
+ encodings are used, even at the expense of breaking 32-bit
+ alignment and making the text diagrams in this specification look
+ awkward.
+
+ o P2P lookup and peer introduction (including UDP hole-punching for
+ NAT and firewall traversal) are supported directly by the session
+ startup handshake.
+
+ o Session identifiers allow an endpoint to multiplex many sessions
+ over a single local transport address while allowing sessions to
+ survive changes in transport address (as may happen in mobile or
+ wireless deployments).
+
+ The syntax of the protocol is detailed in Section 2. The operation
+ of the protocol is detailed in Section 3.
+
+1.2. Terminology
+
+ The key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT",
+ "SHOULD", "SHOULD NOT", "RECOMMENDED", "NOT RECOMMENDED", "MAY", and
+ "OPTIONAL" in this document are to be interpreted as described in
+ [RFC2119].
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 7]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+2. Syntax
+
+ Definitions of types and structures in this specification use
+ traditional text diagrams paired with procedural descriptions using a
+ C-like syntax. The C-like procedural descriptions SHALL be construed
+ as definitive.
+
+ Structures are packed to take only as many bytes as explicitly
+ indicated. There is no 32-bit alignment constraint, and fields are
+ not padded for alignment unless explicitly indicated or described.
+ Text diagrams may include a bit ruler across the top; this is a
+ convenience for counting bits in individual fields and does not
+ necessarily imply field alignment on a multiple of the ruler width.
+
+ Unless specified otherwise, reserved fields SHOULD be set to 0 by a
+ sender and MUST be ignored by a receiver.
+
+ The procedural syntax of this specification defines correct and
+ error-free encoded inputs to a parser. The procedural syntax does
+ not describe a fully featured parser, including error detection and
+ handling. Implementations MUST include means to identify error
+ circumstances, including truncations causing elementary or composed
+ types to not fit inside containing structures, fields, or elements.
+ Unless specified otherwise, an error circumstance SHALL abort the
+ parsing and processing of an element and its enclosing elements, up
+ to the containing packet.
+
+2.1. Common Elements
+
+ This section lists types and structures that are used throughout this
+ specification.
+
+2.1.1. Elementary Types and Constructs
+
+ This section lists the elementary types and constructs out of which
+ all of the following sections' definitions are built.
+
+ uint8_t var;
+
+ An unsigned integer 8 bits (one byte) in length and byte aligned.
+
+ uint16_t var;
+
+ An unsigned integer 16 bits in length, in network byte order ("big
+ endian") and byte aligned.
+
+
+
+
+
+
+Thornburgh Informational [Page 8]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ uint32_t var;
+
+ An unsigned integer 32 bits in length, in network byte order and
+ byte aligned.
+
+ uint128_t var;
+
+ An unsigned integer 128 bits in length, in network byte order and
+ byte aligned.
+
+ uintn_t var :bitsize;
+
+ An unsigned integer of any other size, potentially not byte
+ aligned. Its size in bits is specified explicitly by bitsize.
+
+ bool_t var :1;
+
+ A boolean flag having the value true (1 or set) or false (0 or
+ clear) and being one bit in length.
+
+ type var[num];
+
+ A packed array of type with length num*sizeof(type)*8 bits.
+
+ struct name_t { ... } name :bitsize;
+
+ A packed structure. Its size in bits is specified by bitsize.
+
+ remainder();
+
+ The number of bytes from the current offset to the end of the
+ enclosing structure.
+
+ type var[remainder()];
+
+ A packed array of type, its size extending to the end of the
+ enclosing structure.
+
+ Note that a bitsize of "variable" indicates that the size of the
+ structure is determined by the sizes of its interior components. A
+ bitsize of "n*8" indicates that the size of the structure is a whole
+ number of bytes and is byte aligned.
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 9]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+2.1.2. Variable Length Unsigned Integer (VLU)
+
+ A VLU encodes any finite non-negative integer into one or more bytes.
+ For each encoded byte, if the high bit is set, the next byte is also
+ part of the VLU. If the high bit is clear, this is the final byte of
+ the VLU. The remaining bits encode the number, seven bits at a time,
+ from most significant to least significant.
+
+ 0 1 2 3 4 5 6 7 0 1 2 3 4 5 6 7
+ +~+~+~+~+~+~+~+~+ +-+-+-+-+-+-+-+-+
+ |1| digit |...............|0| digit |
+ +~+~+~+~+~+~+~+~+ +-+-+-+-+-+-+-+-+
+ ^ ^
+ +--------- zero or more --------+
+
+ struct vlu_t
+ {
+ value = 0;
+ do {
+ bool_t more :1;
+ uintn_t digit :7;
+ value = (value * 128) + digit;
+ } while(more);
+ } :variable*8;
+
+
+
+ +-------------/-+
+ | \ |
+ +-------------/-+
+
+ Figure 1: VLU Depiction in Following Diagrams
+
+ Unless stated otherwise in this specification, implementations SHOULD
+ handle VLUs encoding unsigned integers at least 64 bits in length
+ (that is, encoding a maximum value of at least 2^64 - 1).
+
+2.1.3. Option
+
+ An Option is a Length-Type-Value triplet. Length and Type are
+ encoded in VLU format. Length is the number of bytes of payload
+ following the Length field. The payload comprises the Type and Value
+ fields. Type identifies the kind of option this is. The syntax of
+ the Value field is determined by the type of option.
+
+
+
+
+
+
+
+Thornburgh Informational [Page 10]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ An Option can have a length of zero, in which case it has no type and
+ no value and is empty. An empty Option is called a "Marker".
+
+ +-------------/-+~~~~~~~~~~~~~/~+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~+
+ | length \ | type \ | value |
+ +-------------/-+~~~~~~~~~~~~~/~+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~/
+ ^ ^
+ +-------- length bytes long (may be 0) ---------+
+
+ struct option_t
+ {
+ vlu_t length :variable*8; // "L"
+ if(length > 0)
+ {
+ struct {
+ vlu_t type :variable*8; // "T"
+ uint8_t value[remainder()]; // "V"
+ } payload :length*8;
+ }
+ } :variable*8;
+
+
+ +---/---/-------+
+ | L \ T \ V |
+ +---/---/-------+
+
+ Figure 2: Option Depiction in Following Diagrams
+
+2.1.4. Option List
+
+ An Option List is a sequence of zero or more non-empty Options
+ terminated by a Marker.
+
+ +~~~/~~~/~~~~~~~+ +~~~/~~~/~~~~~~~+-------------/-+
+ | L \ T \ V |...............| L \ T \ V | 0 \ |
+ +~~~/~~~/~~~~~~~+ +~~~/~~~/~~~~~~~+-------------/-+
+ ^ ^ Marker
+ +------- zero or more non-empty Options --------+ (empty Option)
+
+ struct optionList_t
+ {
+ do
+ {
+ option_t option :variable*8;
+ } while(option.length > 0);
+ } :variable*8;
+
+
+
+
+
+Thornburgh Informational [Page 11]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+2.1.5. Internet Socket Address (Address)
+
+ When communicating an Internet socket address (a combination of a
+ 32-bit IPv4 [RFC0791] or 128-bit IPv6 [RFC2460] address and a 16-bit
+ port number) to another RTMFP, this encoding is used. This encoding
+ additionally allows an address to be tagged with an origin type,
+ which an RTMFP MAY use to modify the use or disposition of the
+ address.
+
+ 1
+ 0 1 2 3 4 5 6 7 0 1 2 3 4 5 6 7|8 9 0 1 2 3 4 5
+ +-+-+-+-+-+-+-+-+-----/.../-----+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ |I| | O | Internet | |
+ |P|0 0 0 0 0| R | address | port |
+ |6| rsv | I |32 or 128 bits | |
+ +-+-+-+-+-+-+-+-+-----/.../-----+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+
+ struct address_t
+ {
+ bool_t inet6 :1; // "IP6"
+ uintn_t reserved :5 = 0; // "rsv"
+ uintn_t origin :2; // "ORI"
+ if(inet6)
+ uint128_t ipAddress;
+ else
+ uint32_t ipAddress;
+ uint16_t port;
+ } :variable*8;
+
+ inet6: If set, the Internet address is a 128-bit IPv6 address. If
+ clear, the Internet address is a 32-bit IPv4 address.
+
+ origin: The origin tag of this address. Possible values are:
+
+ 0: Unknown, unspecified, or "other"
+
+ 1: Address was reported by the origin as a local, directly
+ attached interface address
+
+ 2: Address was observed to be the source address from which a
+ packet was received (a "reflexive transport address" in the
+ terminology of [RFC5389])
+
+ 3: Address is a relay, proxy, or introducer (a Redirector
+ and/or Forwarder)
+
+
+
+
+
+
+Thornburgh Informational [Page 12]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ ipAddress: The Internet address, in network byte order.
+
+ port: The 16-bit port number, in network byte order.
+
+2.2. Network Layer
+
+2.2.1. Encapsulation
+
+ RTMFP Multiplex packets are usually carried in UDP [RFC0768]
+ datagrams so that they may transit commonly deployed NATs and
+ firewalls, and so that RTMFP may be implemented on commonly deployed
+ operating systems without special privileges or permissions.
+
+ RTMFP Multiplex packets MAY be carried by any suitable datagram
+ transport or encapsulation where endpoints are addressed by an
+ Internet socket address (that is, an IPv4 or IPv6 address and a
+ 16-bit port number).
+
+ The choice of port numbers is not mandated by this specification.
+ Higher protocol layers or the application define the port
+ numbers used.
+
+2.2.2. Multiplex
+
+ 0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ | Scrambled Session ID (SSID) |
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ | e first32[0] |
+ |- - - - - - n - - - - - - - - - - - - - - - - - - - - - - - -|
+ | c first32[1] |
+ +- - - - - - r - - - - - - - - - - - - - - - - - - - - - - - -+
+ | y |
+ | pted packet |
+ +---------------------------------------------------------------/
+
+ struct multiplex_t
+ {
+ uint32_t scrambledSessionID; // "SSID"
+ union {
+ uint32_t first32[2]; // see note
+ uint8_t encryptedPacket[remainder()];
+ } :(encapsulation.length - 4)*8;
+
+ // if encryptedPacket is less than 8 bytes long, treat it
+ // as if it were end-padded with 0s for the following:
+ sessionID = scrambledSessionID XOR first32[0] XOR first32[1];
+ } :encapsulation.length*8;
+
+
+
+Thornburgh Informational [Page 13]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ The 32-bit Scrambled Session ID is the 32-bit session ID modified by
+ performing a bitwise exclusive-or with the bitwise exclusive-or of
+ the first two 32-bit words of the encrypted packet.
+
+ The session ID is a 32-bit value that the receiver has requested to
+ be used by the sender when sending packets to this receiver
+ (Sections 2.3.7 and 2.3.8). The session ID identifies the session to
+ which this packet belongs and the decryption key to be used to
+ decrypt the encrypted packet.
+
+ Note: Session ID 0 (prior to scrambling) denotes the startup pseudo-
+ session and implies the Default Session Key.
+
+ Note: If the encrypted packet is less than 8 bytes long, then for the
+ scrambling operation, perform the exclusive-or as though the
+ encrypted packet were end-padded with enough 0-bytes to bring its
+ length to 8.
+
+2.2.3. Encryption
+
+ RTMFP packets are encrypted according to a Cryptography Profile.
+ This specification doesn't define a Cryptography Profile or mandate a
+ particular choice of cryptography. The application defines the
+ cryptographic syntax and algorithms.
+
+ Packet encryption is RECOMMENDED to be a block cipher operating in
+ Cipher Block Chaining [CBC] or similar mode. Encrypted packets MUST
+ be decipherable without inter-packet dependency, since packets may be
+ lost, duplicated, or reordered in the network.
+
+ The packet encryption layer is responsible for data integrity and
+ authenticity of packets, for example by means of a checksum or
+ cryptographic message authentication code. To mitigate replay
+ attacks, data integrity SHOULD comprise duplicate packet detection,
+ for example by means of a session-wide packet sequence number. The
+ packet encryption layer SHALL discard a received packet that does not
+ pass integrity or authenticity tests.
+
+ Note that the structures described below are of plain, unencrypted
+ packets. Encrypted packets MUST be decrypted according to the
+ Session Key associated with the Multiplex Session ID before being
+ interpreted according to this specification.
+
+ The Cryptography Profile defines a well-known Default Session Key
+ that is used at session startup, during which per-session key(s) are
+ negotiated by the two endpoints. A session ID of zero denotes use of
+ the Default Session Key. The Default Session Key is also used with
+
+
+
+
+Thornburgh Informational [Page 14]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ non-zero session IDs during the latter phases of session startup
+ (Sections 2.3.6 and 2.3.8). See Security Considerations (Section 5)
+ for more about the Default Session Key.
+
+2.2.4. Packet
+
+ An (unencrypted, plain) RTMFP packet consists of a variable sized
+ common header, zero or more chunks, and padding. Padding can be
+ inserted by the encryption layer of the sender to meet cipher block
+ size constraints and is ignored by the receiver. A sender's
+ encryption layer MAY pad the end of a packet with bytes with value
+ 0xff such that the resulting packet is a natural and appropriate size
+ for the cipher. Alternatively, the Cryptography Profile MAY define
+ its own framing and padding scheme, if needed, such that decrypted
+ packets are compatible with the syntax defined in this section.
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 15]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ 0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7
+ +-+-+-+-+-+-+-+-+
+ |T|T| r |T|T| M |
+ |C|C| s |S|S| O |
+ | |R| v | |E| D |
+ +-+-+-+-+-+-+-+-+
+ +~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+
+ | if(TS) timestamp | if(TSE) timestampEcho |
+ +~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+
+ +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~+
+ | Chunk |
+ +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~/
+ :
+ :
+ +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~+
+ | Chunk |
+ +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~/
+ +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~+
+ | padding |
+ +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~/
+
+ struct packet_t
+ {
+ bool_t timeCritical :1; // "TC"
+ bool_t timeCriticalReverse :1; // "TCR"
+ uintn_t reserved :2; // "rsv"
+ bool_t timestampPresent :1; // "TS"
+ bool_t timestampEchoPresent :1; // "TSE"
+ uintn_t mode :2; // "MOD"
+ if(0 != mode)
+ {
+ if(timestampPresent)
+ uint16_t timestamp;
+ if(timestampEchoPresent)
+ uint16_t timestampEcho;
+ while(remainder() > 2)
+ {
+ uint8_t chunkType;
+ uint16_t chunkLength;
+ if(remainder() < chunkLength)
+ break;
+ uint8_t chunkPayload[chunkLength];
+ } // chunks
+ uint8_t padding[remainder()];
+ }
+ } :plainPacket.length*8;
+
+
+
+
+
+Thornburgh Informational [Page 16]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ timeCritical: Time Critical Forward Notification. If set, indicates
+ that this packet contains real-time user data.
+
+ timeCriticalReverse: Time Critical Reverse Notification. If set,
+ indicates that the sender is currently receiving packets on other
+ sessions that have the timeCritical flag set.
+
+ timestampPresent: If set, indicates that the timestamp field is
+ present. If clear, there is no timestamp field.
+
+ timestampEchoPresent: If set, indicates that the timestamp echo
+ field is present. If clear, there is no timestamp echo field.
+
+ mode: The mode of this packet. See below for additional discussion
+ of packet modes. Possible values are:
+
+ 0: Forbidden value
+
+ 1: Initiator Mark
+
+ 2: Responder Mark
+
+ 3: Startup
+
+ timestamp: If the timestampPresent flag is set, this field is
+ present and contains the low 16 bits of the sender's 250 Hz clock
+ (4 milliseconds per tick) at transmit time. The sender's clock
+ MAY have its origin at any time in the past.
+
+ timestampEcho: If the timestampEchoPresent flag is set, this field
+ is present and contains the sender's estimate of what the
+ timestamp field of a packet received from the other end would be
+ at the time this packet was transmitted, using the method
+ described in Section 3.5.2.2.
+
+ chunks: Zero or more chunks follow the header. It is RECOMMENDED
+ that a packet contain at least one chunk.
+
+ padding: Zero or more bytes of padding follow the chunks. The
+ following conditions indicate padding:
+
+ * Fewer than three bytes (the size of a chunk header) remain in
+ the packet.
+
+ * The chunkLength field of what would be the current chunk header
+ indicates that the hypothetical chunk payload wouldn't fit in
+ the remaining bytes of the packet.
+
+
+
+
+Thornburgh Informational [Page 17]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ Packet mode 0 is not allowed. Packets marked with this mode are
+ invalid and MUST be discarded.
+
+ The original initiator of a session MUST mark all non-startup packets
+ it sends in that session with packet mode 1 ("Initiator Mark"). It
+ SHOULD ignore any packet received in that session with packet mode 1.
+
+ The original responder of a session MUST mark all non-startup packets
+ it sends in that session with packet mode 2 ("Responder Mark"). It
+ SHOULD ignore any packet received in that session with packet mode 2.
+
+ Packet mode 3 is for session startup. Session startup chunks are
+ only allowed in packets with this mode.
+
+ Chunks that are not for session startup are only allowed in packets
+ with modes 1 or 2.
+
+2.3. Chunks
+
+ 0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ | chunkType | chunkLength |
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~+
+ | chunkPayload (chunkLength bytes, may be zero) |
+ +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~/
+
+ struct chunk_t
+ {
+ uint8_t chunkType;
+ uint16_t chunkLength;
+ uint8_t chunkPayload[chunkLength];
+ } :variable*8;
+
+ chunkType: The chunk type code.
+
+ chunkLength: The size, in bytes, of the chunk payload.
+
+ chunkPayload: The type-specific payload of this chunk,
+ chunkLength bytes in length (may be empty).
+
+
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 18]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ Defined chunk types are enumerated here in the order they might be
+ encountered in the course of a typical session. The following chunk
+ type codes are defined:
+
+ 0x7f: Packet Fragment (Section 2.3.1)
+
+ 0x30: Initiator Hello (Section 2.3.2)
+
+ 0x0f: Forwarded Initiator Hello (Section 2.3.3)
+
+ 0x70: Responder Hello (Section 2.3.4)
+
+ 0x71: Responder Redirect (Section 2.3.5)
+
+ 0x79: RHello Cookie Change (Section 2.3.6)
+
+ 0x38: Initiator Initial Keying (Section 2.3.7)
+
+ 0x78: Responder Initial Keying (Section 2.3.8)
+
+ 0x01: Ping (Section 2.3.9)
+
+ 0x41: Ping Reply (Section 2.3.10)
+
+ 0x10: User Data (Section 2.3.11)
+
+ 0x11: Next User Data (Section 2.3.12)
+
+ 0x50: Data Acknowledgement Bitmap (Section 2.3.13)
+
+ 0x51: Data Acknowledgement Ranges (Section 2.3.14)
+
+ 0x18: Buffer Probe (Section 2.3.15)
+
+ 0x5e: Flow Exception Report (Section 2.3.16)
+
+ 0x0c: Session Close Request (Section 2.3.17)
+
+ 0x4c: Session Close Acknowledgement (Section 2.3.18)
+
+ 0x00: Ignore/Padding
+
+ 0xff: Ignore/Padding
+
+ A receiver MUST ignore a chunk having an unrecognized chunk type
+ code. A receiver MUST ignore a chunk appearing in a packet having a
+ mode inappropriate to that chunk type.
+
+
+
+
+Thornburgh Informational [Page 19]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ Unless specified otherwise, if a chunk has a syntax or processing
+ error (for example, the chunk's payload field is not long enough to
+ contain the specified syntax elements), the chunk SHALL be ignored as
+ though it was not present in the packet, and parsing and processing
+ SHALL commence with the next chunk in the packet, if any.
+
+2.3.1. Packet Fragment Chunk
+
+ This chunk is used to divide a plain RTMFP packet (Section 2.2.4)
+ that is unavoidably larger than the path MTU (such as session startup
+ packets containing Responder Hello (Section 2.3.4) or Initiator
+ Initial Keying (Section 2.3.7) chunks with large certificates) into
+ segments that do not exceed the path MTU, and to allow the segments
+ to be sent through the network at a moderated rate to avoid jamming
+ interfaces, links, or paths.
+
+ 0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ | 0x7f | chunkLength |
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ +-+-+-+-+-+-+-+-+-------------/-+-------------/-+
+ |M| reserved | packetID \ | fragmentNum \ |
+ +-+-+-+-+-+-+-+-+-------------/-+-------------/-+
+ +---------------------------------------------------------------+
+ | packetFragment |
+ +---------------------------------------------------------------/
+
+ struct fragmentChunkPayload_t
+ {
+ bool_t moreFragments :1; // M
+ uintn_t reserved :7;
+ vlu_t packetID :variable*8;
+ vlu_t fragmentNum :variable*8;
+ uint8_t packetFragment[remainder()];
+ } :chunkLength*8;
+
+ moreFragments: If set, the indicated packet comprises additional
+ fragments. If clear, this fragment is the final fragment of the
+ packet.
+
+ reserved: Reserved for future use.
+
+ packetID: VLU, the identifier of this segmented packet. All
+ fragments of the same packet have the same packetID.
+
+ fragmentNum: VLU, the index of this fragment of the indicated
+ packet. The first fragment of the packet MUST be index 0.
+ Fragments are numbered consecutively.
+
+
+
+Thornburgh Informational [Page 20]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ packetFragment: The bytes of the indicated segment of the indicated
+ original plain RTMFP packet. A packetFragment MUST NOT be empty.
+
+ The use of this mechanism is detailed in Section 3.4.
+
+2.3.2. Initiator Hello Chunk (IHello)
+
+ This chunk is sent by the initiator of a new session to begin the
+ startup handshake. This chunk is only allowed in a packet with
+ Session ID 0, encrypted with the Default Session Key, and having
+ packet mode 3 (Startup).
+
+ 0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ | 0x30 | chunkLength |
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ +-------------/-+-----------------------------------------------+
+ | epdLength \ | endpointDiscriminator (epdLength bytes) |
+ +-------------/-+-----------------------------------------------/
+ +---------------------------------------------------------------+
+ | tag |
+ +---------------------------------------------------------------/
+
+ struct ihelloChunkPayload_t
+ {
+ vlu_t epdLength :variable*8;
+ uint8_t endpointDiscriminator[epdLength];
+ uint8_t tag[remainder()];
+ } :chunkLength*8;
+
+ epdLength: VLU, the length of the following endpointDiscriminator
+ field in bytes.
+
+ endpointDiscriminator: The Endpoint Discriminator for the identity
+ with which the initiator wants to communicate.
+
+ tag: Initiator-provided data to be returned in a Responder Hello's
+ tagEcho field. The tag/tagEcho is used to match Responder Hellos
+ to the initiator's session startup state independent of the
+ responder's address.
+
+ The use of IHello is detailed in Section 3.5.1.
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 21]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+2.3.3. Forwarded Initiator Hello Chunk (FIHello)
+
+ This chunk is sent on behalf of an initiator by a Forwarder. It is
+ only allowed in packets of an established session having packet
+ mode 1 or 2. A receiver MAY treat this chunk as though it was an
+ Initiator Hello received directly from replyAddress. Alternatively,
+ if the receiver is selected by the Endpoint Discriminator, it MAY
+ respond to replyAddress with an Implied Redirect (Section 2.3.5).
+
+ 0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ | 0x0f | chunkLength |
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ +-------------/-+-----------------------------------------------+
+ | epdLength \ | endpointDiscriminator (epdLength bytes) |
+ +-------------/-+-----------------------------------------------/
+ +---------------------------------------------------------------+
+ | replyAddress |
+ +---------------------------------------------------------------/
+ +---------------------------------------------------------------+
+ | tag |
+ +---------------------------------------------------------------/
+
+ struct fihelloChunkPayload_t
+ {
+ vlu_t epdLength :variable*8;
+ uint8_t endpointDiscriminator[epdLength];
+ address_t replyAddress :variable*8;
+ uint8_t tag[remainder()];
+ } :chunkLength*8;
+
+ epdLength: VLU, the length of the following endpointDiscriminator
+ field in bytes.
+
+ endpointDiscriminator: The Endpoint Discriminator for the identity
+ with which the original initiator wants to communicate, copied
+ from the original Initiator Hello.
+
+ replyAddress: Address format (Section 2.1.5), the address that the
+ forwarding node derived from the received Initiator Hello, to
+ which the receiver should respond.
+
+ tag: Copied from the original Initiator Hello.
+
+ The use of FIHello is detailed in Section 3.5.1.5.
+
+
+
+
+
+
+Thornburgh Informational [Page 22]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+2.3.4. Responder Hello Chunk (RHello)
+
+ This chunk is sent by a responder in response to an Initiator Hello
+ or Forwarded Initiator Hello if the Endpoint Discriminator indicates
+ the responder's identity. This chunk is only allowed in a packet
+ with Session ID 0, encrypted with the Default Session Key, and having
+ packet mode 3 (Startup).
+
+ 0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ | 0x70 | chunkLength |
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ +-------------/-+-----------------------------------------------+
+ | tagLength \ | tagEcho (tagLength bytes) |
+ +-------------/-+-----------------------------------------------/
+ +-------------/-+-----------------------------------------------+
+ | cookieLength\ | cookie (cookieLength bytes) |
+ +-------------/-+-----------------------------------------------/
+ +---------------------------------------------------------------+
+ | responderCertificate |
+ +---------------------------------------------------------------/
+
+ struct rhelloChunkPayload_t
+ {
+ vlu_t tagLength :variable*8;
+ uint8_t tagEcho[tagLength];
+ vlu_t cookieLength :variable*8;
+ uint8_t cookie[cookieLength];
+ uint8_t responderCertificate[remainder()];
+ } :chunkLength*8;
+
+ tagLength: VLU, the length of the following tagEcho field in bytes.
+
+ tagEcho: The tag from the Initiator Hello, unaltered.
+
+ cookieLength: VLU, the length of the following cookie field
+ in bytes.
+
+ cookie: Responder-created state data to authenticate a future
+ Initiator Initial Keying message (in order to prevent denial-of-
+ service attacks).
+
+ responderCertificate: The responder's cryptographic credentials.
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 23]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ Note: This specification doesn't mandate a specific choice of
+ certificate format. The Cryptography Profile determines the syntax,
+ algorithms, and interpretation of the responderCertificate.
+
+ The use of RHello is detailed in Section 3.5.1.
+
+2.3.5. Responder Redirect Chunk (Redirect)
+
+ This chunk is sent in response to an Initiator Hello or Forwarded
+ Initiator Hello to indicate that the requested endpoint can be
+ reached at one or more of the indicated addresses. A receiver can
+ add none, some, or all of the indicated addresses to the set of
+ addresses to which it is sending Initiator Hello messages for the
+ opening session associated with tagEcho. This chunk is only allowed
+ in a packet with Session ID 0, encrypted with the Default Session
+ Key, and having packet mode 3 (Startup).
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 24]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ 0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ | 0x71 | chunkLength |
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ +-------------/-+-----------------------------------------------+
+ | tagLength \ | tagEcho (tagLength bytes) |
+ +-------------/-+-----------------------------------------------/
+ +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~+
+ | redirectDestination 1 |
+ +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~/
+ :
+ :
+ +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~+
+ | redirectDestination N |
+ +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~/
+
+ struct responderRedirectChunkPayload_t
+ {
+ vlu_t tagLength :variable*8;
+ uint8_t tagEcho[tagLength];
+ addressCount = 0;
+ while(remainder() > 0)
+ {
+ address_t redirectDestination :variable*8;
+ addressCount++;
+ }
+ if(0 == addressCount)
+ redirectDestination = packetSourceAddress();
+ } :chunkLength*8;
+
+ tagLength: VLU, the length of the following tagEcho field in bytes.
+
+ tagEcho: The tag from the Initiator Hello, unaltered.
+
+ redirectDestination: (Zero or more) Address format (Section 2.1.5)
+ addresses to add to the opening set for the indicated session.
+
+ If this chunk lists zero redirectDestination addresses, then this is
+ an Implied Redirect, and the indicated address is the address from
+ which the packet containing this chunk was received.
+
+ The use of Redirect is detailed in Sections 3.5.1.1.1, 3.5.1.1.2,
+ and 3.5.1.4.
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 25]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+2.3.6. RHello Cookie Change Chunk
+
+ This chunk SHOULD be sent by a responder to an initiator in response
+ to an Initiator Initial Keying if that chunk's cookie appears to have
+ been created by the responder but the cookie is incorrect (for
+ example, it includes a hash of the initiator's address, but the
+ initiator's address is different than the one that elicited the
+ Responder Hello containing the original cookie).
+
+ This chunk is only allowed in a packet encrypted with the Default
+ Session Key and having packet mode 3, and with the session ID
+ indicated in the initiatorSessionID field of the Initiator Initial
+ Keying to which this is a response.
+
+ 0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ | 0x79 | chunkLength |
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ +-------------/-+-----------------------------------------------+
+ | oldCookieLen\ | oldCookie (oldCookieLen bytes) |
+ +-------------/-+-----------------------------------------------/
+ +---------------------------------------------------------------+
+ | newCookie |
+ +---------------------------------------------------------------/
+
+ struct rhelloCookieChangeChunkPayload_t
+ {
+ vlu_t oldCookieLen :variable*8;
+ uint8_t oldCookie[oldCookieLen];
+ uint8_t newCookie[remainder()];
+ } :chunkLength*8;
+
+ oldCookieLen: VLU, the length of the following oldCookie field
+ in bytes.
+
+ oldCookie: The cookie that was sent in a previous Responder Hello
+ and Initiator Initial Keying.
+
+ newCookie: The new cookie that the responder would like sent (and
+ signed) in a replacement Initiator Initial Keying. The old and
+ new cookies need not have the same lengths.
+
+ On receipt of this chunk, the initiator SHOULD compute, sign, and
+ send a new Initiator Initial Keying having newCookie in place of
+ oldCookie. The use of this chunk is detailed in Section 3.5.1.2.
+
+
+
+
+
+
+Thornburgh Informational [Page 26]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+2.3.7. Initiator Initial Keying Chunk (IIKeying)
+
+ This chunk is sent by an initiator to establish a session with a
+ responder. The initiator MUST have obtained a valid cookie to use
+ with the responder, typically by receiving a Responder Hello from it.
+ This chunk is only allowed in a packet with Session ID 0, encrypted
+ with the Default Session Key, and having packet mode 3 (Startup).
+
+ 0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ | 0x38 | chunkLength |
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ | initiatorSessionID |
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ +-------------/-+-----------------------------------------------+
+ | cookieLength\ | cookieEcho |
+ +-------------/-+-----------------------------------------------/
+ +-------------/-+-----------------------------------------------+
+ | certLength \ | initiatorCertificate |
+ +-------------/-+-----------------------------------------------/
+ +-------------/-+-----------------------------------------------+
+ | skicLength \ | sessionKeyInitiatorComponent |
+ +-------------/-+-----------------------------------------------/
+ +---------------------------------------------------------------+
+ | signature |
+ +---------------------------------------------------------------/
+
+ struct iikeyingChunkPayload_t
+ {
+ struct
+ {
+ uint32_t initiatorSessionID;
+ vlu_t cookieLength :variable*8;
+ uint8_t cookieEcho[cookieLength];
+ vlu_t certLength :variable*8;
+ uint8_t initiatorCertificate[certLength];
+ vlu_t skicLength :variable*8;
+ uint8_t sessionKeyInitiatorComponent[skicLength];
+ } initiatorSignedParameters :variable*8;
+ uint8_t signature[remainder()];
+ } :chunkLength*8;
+
+ initiatorSessionID: The session ID to be used by the responder when
+ sending packets to the initiator.
+
+
+
+
+
+
+Thornburgh Informational [Page 27]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ cookieLength: VLU, the length of the following cookieEcho field
+ in bytes.
+
+ cookieEcho: The cookie from the Responder Hello, unaltered.
+
+ certLength: VLU, the length of the following initiatorCertificate
+ field in bytes.
+
+ initiatorCertificate: The initiator's identity credentials.
+
+ skicLength: VLU, the length of the following
+ sessionKeyInitiatorComponent field in bytes.
+
+ sessionKeyInitiatorComponent: The initiator's portion of the session
+ key negotiation according to the Cryptography Profile.
+
+ initiatorSignedParameters: The payload portion of this chunk up to
+ the signature field.
+
+ signature: The initiator's digital signature of the
+ initiatorSignedParameters according to the Cryptography Profile.
+
+ Note: This specification doesn't mandate a specific choice of
+ cryptography. The Cryptography Profile determines the syntax,
+ algorithms, and interpretation of the initiatorCertificate,
+ responderCertificate, sessionKeyInitiatorComponent,
+ sessionKeyResponderComponent, and signature, and how the
+ sessionKeyInitiatorComponent and sessionKeyResponderComponent are
+ combined to derive the session keys.
+
+ The use of IIKeying is detailed in Section 3.5.1.
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 28]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+2.3.8. Responder Initial Keying Chunk (RIKeying)
+
+ This chunk is sent by a responder in response to an Initiator Initial
+ Keying as the final phase of session startup. This chunk is only
+ allowed in a packet encrypted with the Default Session Key, having
+ packet mode 3 (Startup), and sent to the initiator with the
+ session ID specified by the initiatorSessionID field from the
+ Initiator Initial Keying.
+
+ 0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ | 0x78 | chunkLength |
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ | responderSessionID |
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ +-------------/-+-----------------------------------------------+
+ | skrcLength \ | sessionKeyResponderComponent |
+ +-------------/-+-----------------------------------------------/
+ +---------------------------------------------------------------+
+ | signature |
+ +---------------------------------------------------------------/
+
+ struct rikeyingChunkPayload_t
+ {
+ struct
+ {
+ uint32_t responderSessionID;
+ vlu_t skrcLength :variable*8;
+ uint8_t sessionKeyResponderComponent[skrcLength];
+ } responderSignedParametersPortion :variable*8;
+ uint8_t signature[remainder()];
+ } :chunkLength*8;
+
+ struct
+ {
+ responderSignedParametersPortion;
+ sessionKeyInitiatorComponent;
+ } responderSignedParameters;
+
+ responderSessionID: The session ID to be used by the initiator when
+ sending packets to the responder.
+
+ skrcLength: VLU, the length of the following
+ sessionKeyResponderComponent field in bytes.
+
+ sessionKeyResponderComponent: The responder's portion of the session
+ key negotiation according to the Cryptography Profile.
+
+
+
+Thornburgh Informational [Page 29]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ responderSignedParametersPortion: The payload portion of this chunk
+ up to the signature field.
+
+ signature: The responder's digital signature of the
+ responderSignedParameters (see below) according to the
+ Cryptography Profile.
+
+ responderSignedParameters: The concatenation of the
+ responderSignedParametersPortion (the payload portion of this
+ chunk up to the signature field) and the
+ sessionKeyInitiatorComponent from the Initiator Initial Keying to
+ which this chunk is a response.
+
+ Note: This specification doesn't mandate a specific choice of
+ cryptography. The Cryptography Profile determines the syntax,
+ algorithms, and interpretation of the initiatorCertificate,
+ responderCertificate, sessionKeyInitiatorComponent,
+ sessionKeyResponderComponent, and signature, and how the
+ sessionKeyInitiatorComponent and sessionKeyResponderComponent are
+ combined to derive the session keys.
+
+ Once the responder has computed the sessionKeyResponderComponent, it
+ has all of the information and state necessary for an established
+ session with the initiator. Once the responder has sent this chunk
+ to the initiator, the session is established and ready to carry flows
+ of user data.
+
+ Once the initiator receives, verifies, and processes this chunk, it
+ has all of the information and state necessary for an established
+ session with the responder. The session is established and ready to
+ carry flows of user data.
+
+ The use of RIKeying is detailed in Section 3.5.1.
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 30]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+2.3.9. Ping Chunk
+
+ This chunk is sent in order to elicit a Ping Reply from the receiver.
+ It is only allowed in a packet belonging to an established session
+ and having packet mode 1 or 2.
+
+ 0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ | 0x01 | chunkLength |
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~+
+ | message |
+ +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~/
+
+ struct pingChunkPayload_t
+ {
+ uint8_t message[chunkLength];
+ } :chunkLength*8;
+
+ message: The (potentially empty) message that is expected to be
+ returned by the other end of the session in a Ping Reply.
+
+ The receiver of this chunk SHOULD reply as immediately as is
+ practical with a Ping Reply.
+
+ Ping and the expected Ping Reply are typically used for session
+ keepalive, endpoint address change verification, and path MTU
+ discovery. See Section 3.5.4 for details.
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 31]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+2.3.10. Ping Reply Chunk
+
+ This chunk is sent in response to a Ping chunk. It is only allowed
+ in a packet belonging to an established session and having packet
+ mode 1 or 2.
+
+ 0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ | 0x41 | chunkLength |
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~+
+ | messageEcho |
+ +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~/
+
+ struct pingReplyChunkPayload_t
+ {
+ uint8_t messageEcho[chunkLength];
+ } :chunkLength*8;
+
+ messageEcho: The message from the Ping to which this is a response,
+ unaltered.
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 32]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+2.3.11. User Data Chunk
+
+ This chunk is the basic unit of transmission for the user messages of
+ a flow. A user message comprises one or more fragments. Each
+ fragment is carried in its own chunk and has a unique sequence number
+ in its flow. It is only allowed in a packet belonging to an
+ established session and having packet mode 1 or 2.
+
+ 0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ | 0x10 | chunkLength |
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ +-+-+-+-+-+-+-+-+
+ |O|r| F | r |A|F|
+ |P|s| R | s |B|I|
+ |T|v| A | v |N|N|
+ +-+-+-+-+-+-+-+-+
+ +-------------/-+-------------/-+-------------/-+
+ | flowID \ | seq# \ | fsnOffset \ |
+ +-------------/-+-------------/-+-------------/-+
+ +~~~/~~~/~~~~~~~+ +~~~/~~~/~~~~~~~+-------------/-+
+ | L \ T \ V |... options ...| L \ T \ V | 0 \ |
+ \~~~/~~~/~~~~~~~+ [if(OPT)] +~~~/~~~/~~~~~~~+-------------/-/
+ +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~+
+ | userData |
+ +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~/
+
+ struct userDataChunkPayload_t
+ {
+ bool_t optionsPresent :1; // "OPT"
+ uintn_t reserved1 :1; // "rsv"
+ uintn_t fragmentControl :2; // "FRA"
+ // 0=whole, 1=begin, 2=end, 3=middle
+ uintn_t reserved2 :2; // "rsv"
+ bool_t abandon :1; // "ABN"
+ bool_t final :1; // "FIN"
+ vlu_t flowID :variable*8;
+ vlu_t sequenceNumber :variable*8; // "seq#"
+ vlu_t fsnOffset :variable*8;
+ forwardSequenceNumber = sequenceNumber - fsnOffset;
+ if(optionsPresent)
+ optionList_t options :variable*8;
+ uint8_t userData[remainder()];
+ } :chunkLength*8;
+
+ optionsPresent: If set, indicates the presence of an option list
+ before the user data. If clear, there is no option list in this
+ chunk.
+
+
+
+Thornburgh Informational [Page 33]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ fragmentControl: Indicates how this fragment is assembled,
+ potentially with others, into a complete user message. Possible
+ values:
+
+ 0: This fragment is a complete message.
+
+ 1: This fragment is the first of a multi-fragment message.
+
+ 2: This fragment is the last of a multi-fragment message.
+
+ 3: This fragment is in the middle of a multi-fragment message.
+
+ A single-fragment user message has a fragment control of
+ "0-whole". When a message has more than one fragment, the first
+ fragment has a fragment control of "1-begin", then zero or more
+ "3-middle" fragments, and finally a "2-end" fragment. The
+ sequence numbers of a multi-fragment message MUST be contiguous.
+
+ abandon: If set, this sequence number has been abandoned by the
+ sender. The userData, if any, MUST be ignored.
+
+ final: If set, this is the last sequence number of the flow.
+
+ flowID: VLU, the flow identifier.
+
+ sequenceNumber: VLU, the sequence number of this fragment.
+ Fragments are assigned contiguous increasing sequence numbers in a
+ flow. The first sequence number of a flow SHOULD be 1. The first
+ sequence number of a flow MUST be greater than zero. Sequence
+ numbers are unbounded and do not wrap.
+
+ fsnOffset: VLU, the difference between the sequence number and the
+ Forward Sequence Number. This field MUST NOT be zero if the
+ abandon flag is not set. This field MUST NOT be greater than
+ sequenceNumber.
+
+ forwardSequenceNumber: The flow sender will not send (or resend) any
+ fragment with a sequence number less than or equal to the Forward
+ Sequence Number.
+
+ options: If the optionsPresent flag is set, a list of zero or more
+ Options terminated by a Marker is present. See Section 2.3.11.1
+ for defined options.
+
+ userData: The actual user data for this fragment.
+
+ The use of User Data is detailed in Section 3.6.2.
+
+
+
+
+Thornburgh Informational [Page 34]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+2.3.11.1. Options for User Data
+
+ This section lists options that may appear in User Data option lists.
+ A conforming implementation MUST support the options in this section.
+
+ A flow receiver MUST reject a flow containing a flow option that is
+ not understood if the option type is less than 8192 (0x2000). A flow
+ receiver MUST ignore any flow option that is not understood if the
+ option type is 8192 or greater.
+
+ The following option type codes are defined for User Data:
+
+ 0x00: User's Per-Flow Metadata (Section 2.3.11.1.1)
+
+ 0x0a: Return Flow Association (Section 2.3.11.1.2)
+
+2.3.11.1.1. User's Per-Flow Metadata
+
+ This option conveys the user's per-flow metadata for the flow to
+ which it's attached.
+
+ +-------------/-+-------------/-+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~+
+ | length \ | 0x00 \ | userMetadata |
+ +-------------/-+-------------/-+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~/
+
+ struct userMetadataOptionValue_t
+ {
+ uint8_t userMetadata[remainder()];
+ } :remainder()*8;
+
+ The user associates application-defined metadata with each flow. The
+ metadata does not change over the life of the flow. Every flow MUST
+ have metadata. A flow sender MUST send this option with the first
+ User Data chunk for this flow in each packet until an acknowledgement
+ for this flow is received. A flow sender SHOULD NOT send this option
+ more than once for each flow in any one packet. A flow sender SHOULD
+ NOT send this option for a flow once the flow has been acknowledged.
+
+ This specification doesn't mandate the encoding, syntax, or
+ interpretation of the user's per-flow metadata; this is determined by
+ the application.
+
+ The userMetadata SHOULD NOT exceed 512 bytes. The userMetadata MAY
+ be 0 bytes in length.
+
+
+
+
+
+
+
+Thornburgh Informational [Page 35]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+2.3.11.1.2. Return Flow Association
+
+ A new flow can be considered to be in return (or response) to a flow
+ sent by the other endpoint. This option encodes the receive flow
+ identifier to which this new sending flow is a response.
+
+ +-------------/-+-------------/-+-------------/-+
+ | length \ | 0x0a \ | flowID \ |
+ +-------------/-+-------------/-+-------------/-+
+
+ struct returnFlowAssociationOptionValue_t
+ {
+ vlu_t flowID :variable*8;
+ } :variable*8;
+
+ Consider endpoints A and B. Endpoint A begins a flow with
+ identifier 5 to endpoint B. A is the flow sender for A's flowID=5,
+ and B is the flow receiver for A's flowID=5. B begins a return flow
+ with identifier 7 to A in response to A's flowID=5. B is the flow
+ sender for B's flowID=7, and A is the flow receiver for B's flowID=7.
+ B sends this option with flowID set to 5 to indicate that B's
+ flowID=7 is in response to and associated with A's flowID=5.
+
+ If there is a return association, the flow sender MUST send this
+ option with the first User Data chunk for this flow in each packet
+ until an acknowledgement for this flow is received. A flow sender
+ SHOULD NOT send this option more than once for each flow in any one
+ packet. A flow sender SHOULD NOT send this option for a flow once
+ the flow has been acknowledged.
+
+ A flow MUST NOT indicate more than one return association.
+
+ A flow MUST indicate its return association, if any, upon its first
+ transmission of a User Data chunk. A return association can't be
+ added to a sending flow after it begins.
+
+ A flow receiver MUST reject a new receiving flow having a return flow
+ association that does not indicate an F_OPEN sending flow.
+
+
+
+
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 36]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+2.3.12. Next User Data Chunk
+
+ This chunk is equivalent to the User Data chunk for purposes of
+ sending the user messages of a flow. When used, it MUST follow a
+ User Data chunk or another Next User Data chunk in the same packet.
+
+ 0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ | 0x11 | chunkLength |
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ +-+-+-+-+-+-+-+-+
+ |O|r| F | r |A|F|
+ |P|s| R | s |B|I|
+ |T|v| A | v |N|N|
+ +-+-+-+-+-+-+-+-+
+ +~~~/~~~/~~~~~~~+ +~~~/~~~/~~~~~~~+-------------/-+
+ | L \ T \ V |... options ...| L \ T \ V | 0 \ |
+ \~~~/~~~/~~~~~~~+ [if(OPT)] +~~~/~~~/~~~~~~~+-------------/-/
+ +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~+
+ | userData |
+ +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~/
+
+ struct nextUserDataChunkPayload_t
+ {
+ bool_t optionsPresent :1; // "OPT"
+ uintn_t reserved1 :1; // "rsv"
+ uintn_t fragmentControl :2; // "FRA"
+ // 0=whole, 1=begin, 2=end, 3=middle
+ uintn_t reserved2 :2; // "rsv"
+ bool_t abandon :1; // "ABN"
+ bool_t final :1; // "FIN"
+ if(optionsPresent)
+ optionList_t options :variable*8;
+ uint8_t userData[remainder()];
+ } :chunkLength*8;
+
+ This chunk is considered to be for the same flowID as the most
+ recently preceding User Data or Next User Data chunk in the same
+ packet, having the same Forward Sequence Number, and having the next
+ sequence number. The optionsPresent, fragmentControl, abandon, and
+ final flags, and the options (if present), have the same
+ interpretation as for the User Data chunk.
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 37]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ ...
+ ----------+------------------------------------
+ 10 00 07 | User Data chunk, length=7
+ 00 | OPT=0, FRA=0 "whole", ABN=0, FIN=0
+ 02 05 03 | flowID=2, seq#=5, fsn=(5-3)=2
+ 00 01 02 | data 3 bytes: 00, 01, 02
+ ----------+------------------------------------
+ 11 00 04 | Next User Data chunk,length=4
+ 00 | OPT=0, FRA=0 "whole", ABN=0, FIN=0
+ | flowID=2, seq#=6, fsn=2
+ 03 04 05 | data 3 bytes: 03, 04, 05
+ ----------+------------------------------------
+ 11 00 04 | Next User Data chunk, length=4
+ 00 | OPT=0, FRA=0 "whole", ABN=0, FIN=0
+ | flowID=2, seq#=7, fsn=2
+ 06 07 08 | data 3 bytes: 06, 07, 08
+ ----------+------------------------------------
+
+ Figure 3: Sequential Messages in One Packet Using Next User Data
+
+ The use of Next User Data is detailed in Section 3.6.2.3.2.
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 38]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+2.3.13. Data Acknowledgement Bitmap Chunk (Bitmap Ack)
+
+ This chunk is sent by the flow receiver to indicate to the flow
+ sender the User Data fragment sequence numbers that have been
+ received for one flow. It is only allowed in a packet belonging to
+ an established session and having packet mode 1 or 2.
+
+ The flow receiver can choose to acknowledge User Data with this chunk
+ or with a Range Ack. It SHOULD choose whichever format has the most
+ compact encoding of the sequence numbers received.
+
+ 0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ | 0x50 | chunkLength |
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ +-------------/-+-------------/-+-------------/-+
+ | flowID \ | bufAvail \ | cumAck \ |
+ +-------------/-+-------------/-+-------------/-+
+ +~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+
+ |C|C|C|C|C|C|C|C|C|C|C|C|C|C|C|C|C|C|C|C|C|C|C|C|
+ |+|+|+|+|+|+|+|+|+|+|+|+|+|+|+|+|+|+|+|+|+|+|+|+|
+ |9|8|7|6|5|4|3|2|1|1|1|1|1|1|1|1|2|2|2|2|2|2|1|1| ....
+ | | | | | | | | |7|6|5|4|3|2|1|0|5|4|3|2|1|0|9|8|
+ +~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+~+
+
+ struct dataAckBitmapChunkPayload_t
+ {
+ vlu_t flowID :variable*8;
+ vlu_t bufferBlocksAvailable :variable*8; // "bufAvail"
+ vlu_t cumulativeAck :variable*8; // "cumAck"
+ bufferBytesAvailable = bufferBlocksAvailable * 1024;
+ acknowledge(0 through cumulativeAck);
+ ackCursor = cumulativeAck + 1;
+ while(remainder() > 0)
+ {
+ for(bitPosition = 8; bitPosition > 0; bitPosition--)
+ {
+ bool_t bit :1;
+ if(bit)
+ acknowledge(ackCursor + bitPosition);
+ }
+ ackCursor += 8;
+ }
+ } :chunkLength*8;
+
+
+
+
+
+
+
+Thornburgh Informational [Page 39]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ flowID: VLU, the flow identifier.
+
+ bufferBlocksAvailable: VLU, the number of 1024-byte blocks of User
+ Data that the receiver is currently able to accept.
+ Section 3.6.3.5 describes how to calculate this value.
+
+ cumulativeAck: VLU, the acknowledgement of every fragment sequence
+ number in this flow that is less than or equal to this value.
+ This MUST NOT be less than the highest Forward Sequence Number
+ received in this flow.
+
+ bit field: A sequence of zero or more bytes representing a bit field
+ of received fragment sequence numbers after the cumulative
+ acknowledgement, least significant bit first. A set bit indicates
+ receipt of a sequence number. A clear bit indicates that sequence
+ number was not received. The least significant bit of the first
+ byte is the second sequence number following the cumulative
+ acknowledgement, the next bit is the third sequence number
+ following, and so on.
+
+ Figure 4 shows an example Bitmap Ack indicating acknowledgement of
+ fragment sequence numbers 0 through 16, 18, 21 through 24, 27,
+ and 28.
+
+ 50 00 05 | Bitmap Ack, length=5 bytes
+ 05 7f 10 | flowID=5, bufAvail=127*1024 bytes, cumAck=0..16
+ 79 06 | 01111001 00000110 = 18, 21, 22, 23, 24, 27, 28
+
+ Figure 4: Example Bitmap Ack
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 40]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+2.3.14. Data Acknowledgement Ranges Chunk (Range Ack)
+
+ This chunk is sent by the flow receiver to indicate to the flow
+ sender the User Data fragment sequence numbers that have been
+ received for one flow. It is only allowed in a packet belonging to
+ an established session and having packet mode 1 or 2.
+
+ The flow receiver can choose to acknowledge User Data with this chunk
+ or with a Bitmap Ack. It SHOULD choose whichever format has the most
+ compact encoding of the sequence numbers received.
+
+ 0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ | 0x51 | chunkLength |
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ +-------------/-+-------------/-+-------------/-+
+ | flowID \ | bufAvail \ | cumAck \ |
+ +-------------/-+-------------/-+-------------/-+
+ +~~~~~~~~~~~~~/~+~~~~~~~~~~~~~/~+
+ | #holes-1 \ | #recv-1 \ |
+ +~~~~~~~~~~~~~/~+~~~~~~~~~~~~~/~+
+ :
+ :
+ +~~~~~~~~~~~~~/~+~~~~~~~~~~~~~/~+
+ | #holes-1 \ | #recv-1 \ |
+ +~~~~~~~~~~~~~/~+~~~~~~~~~~~~~/~+
+
+ struct dataAckRangesChunkPayload_t
+ {
+ vlu_t flowID :variable*8;
+ vlu_t bufferBlocksAvailable :variable*8; // "bufAvail"
+ vlu_t cumulativeAck :variable*8; // "cumAck"
+ bufferBytesAvailable = bufferBlocksAvailable * 1024;
+ acknowledge(0 through cumulativeAck);
+ ackCursor = cumulativeAck;
+ while(remainder() > 0)
+ {
+ vlu_t holesMinusOne :variable*8; // "#holes-1"
+ vlu_t receivedMinusOne :variable*8; // "#recv-1"
+
+ ackCursor++;
+ rangeFrom = ackCursor + holesMinusOne + 1;
+ rangeTo = rangeFrom + receivedMinusOne;
+ acknowledge(rangeFrom through rangeTo);
+
+ ackCursor = rangeTo;
+ }
+ } :chunkLength*8;
+
+
+
+Thornburgh Informational [Page 41]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ flowID: VLU, the flow identifier.
+
+ bufferBlocksAvailable: VLU, the number of 1024-byte blocks of User
+ Data that the receiver is currently able to accept.
+ Section 3.6.3.5 describes how to calculate this value.
+
+ cumulativeAck: VLU, the acknowledgement of every fragment sequence
+ number in this flow that is less than or equal to this value.
+ This MUST NOT be less than the highest Forward Sequence Number
+ received in this flow.
+
+ holesMinusOne / receivedMinusOne: Zero or more acknowledgement
+ ranges, run-length encoded. Runs are encoded as zero or more
+ pairs of VLUs indicating the number (minus one) of missing
+ sequence numbers followed by the number (minus one) of received
+ sequence numbers, starting at the cumulative acknowledgement.
+ NOTE: If a parser syntax error is encountered here (that is, if
+ the chunk is truncated such that not enough bytes remain to
+ completely encode both VLUs of the acknowledgement range), then
+ treat and process this chunk as though it was properly formed up
+ to the last completely encoded range.
+
+ Figure 5 shows an example Range Ack indicating acknowledgement of
+ fragment sequence numbers 0 through 16, 18, 21, 22, 23, and 24.
+
+ 51 00 07 | Range Ack, length=7
+ 05 7f 10 | flowID=5, bufAvail=127*1024 bytes, cumAck=0..16
+ 00 00 | holes=1, received=1 -- missing 17, received 18
+ 01 03 | holes=2, received=4 -- missing 19..20, received 21..24
+
+ Figure 5: Example Range Ack
+
+ Figure 6 shows an example Range Ack indicating acknowledgement of
+ fragment sequence numbers 0 through 16 and 18, with a truncated
+ last range. Note that the truncation and parse error does not
+ abort the entire chunk in this case.
+
+ 51 00 07 | Range Ack, length=9
+ 05 7f 10 | flowID=5, bufAvail=127*1024 bytes, cumAck=0..16
+ 00 00 | holes=1, received=1 -- missing 17, received 18
+ 01 83 | holes=2, received=VLU parse error, ignore this range
+
+ Figure 6: Example Truncated Range Ack
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 42]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+2.3.15. Buffer Probe Chunk
+
+ This chunk is sent by the flow sender in order to request the current
+ available receive buffer (in the form of a Data Acknowledgement) for
+ a flow. It is only allowed in a packet belonging to an established
+ session and having packet mode 1 or 2.
+
+ 0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ | 0x18 | chunkLength |
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ +-------------/-+
+ | flowID \ |
+ +-------------/-+
+
+ struct bufferProbeChunkPayload_t
+ {
+ vlu_t flowID :variable*8;
+ } :chunkLength*8;
+
+ flowID: VLU, the flow identifier.
+
+ The receiver of this chunk SHOULD reply as immediately as is
+ practical with a Data Acknowledgement.
+
+2.3.16. Flow Exception Report Chunk
+
+ This chunk is sent by the flow receiver to indicate that it is not
+ (or is no longer) interested in the flow and would like the flow
+ sender to close the flow. This chunk SHOULD precede every Data
+ Acknowledgement chunk for the same flow in this condition.
+
+ This chunk is only allowed in a packet belonging to an established
+ session and having packet mode 1 or 2.
+
+ 0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ | 0x5e | chunkLength |
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ +-------------/-+-------------/-+
+ | flowID \ | exception \ |
+ +-------------/-+-------------/-+
+
+ struct flowExceptionReportChunkPayload_t
+ {
+ vlu_t flowID :variable*8;
+ vlu_t exception :variable*8;
+ } :chunkLength*8;
+
+
+
+Thornburgh Informational [Page 43]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ flowID: VLU, the flow identifier.
+
+ exception: VLU, the application-defined exception code being
+ reported.
+
+ A receiving RTMFP might reject a flow automatically, for example if
+ it is missing metadata, or if an invalid return association is
+ specified. In circumstances where an RTMFP rejects a flow
+ automatically, the exception code MUST be 0. The application can
+ specify any exception code, including 0, when rejecting a flow. All
+ non-zero exception codes are reserved for the application.
+
+2.3.17. Session Close Request Chunk (Close)
+
+ This chunk is sent to cleanly terminate a session. It is only
+ allowed in a packet belonging to an established or closing session
+ and having packet mode 1 or 2.
+
+ 0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ | 0x0c | 0 |
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+
+ This chunk has no payload.
+
+ The use of Close is detailed in Section 3.5.5.
+
+2.3.18. Session Close Acknowledgement Chunk (Close Ack)
+
+ This chunk is sent in response to a Session Close Request to indicate
+ that the sender has terminated the session. It is only allowed in a
+ packet belonging to an established or closing session and having
+ packet mode 1 or 2.
+
+ 0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7|0 1 2 3 4 5 6 7
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ | 0x4c | 0 |
+ +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+
+ This chunk has no payload.
+
+ The use of Close Ack is detailed in Section 3.5.5.
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 44]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+3. Operation
+
+3.1. Overview
+
+ +--------+ +--------+
+ | Peer A | S E S S I O N | Peer B |
+ | /=============================\ |
+ | || Flows || |
+ | ||---------------------------->|| |
+ | ||---------------------------->|| |
+ | ||<----------------------------|| |
+ | ||<----------------------------|| |
+ | ||<----------------------------|| |
+ | \=============================/ |
+ | | | |
+ | | +--------+
+ | |
+ | | +--------+
+ | | S E S S I O N | Peer C |
+ | /=============================\ |
+ | || Flows || |
+ | ||---------------------------->|| |
+ | ||<----------------------------|| |
+ | ||<----------------------------|| |
+ | \=============================/ |
+ | | | |
+ +--------+ +--------+
+
+ Figure 7: Sessions between Pairs of Communicating Endpoints
+
+ Between any pair of communicating endpoints is a single,
+ bidirectional, secured, congestion controlled session.
+ Unidirectional flows convey messages from one end to the other within
+ the session.
+
+ An endpoint initiates a session to a far end when communication is
+ desired. An initiator begins with one or more candidate destination
+ socket addresses, and it may learn and try more candidate addresses
+ during startup handshaking. Eventually, a first suitable response is
+ received, and that endpoint is selected. Startup proceeds to the
+ selected endpoint. In the case of session startup glare, one
+ endpoint is the prevailing initiator and the other assumes the role
+ of responder. Encryption keys and session identifiers are negotiated
+ between the endpoints, and the session is established.
+
+ Each endpoint may begin sending message flows to the other end. For
+ each flow, the far end may accept it and deliver its messages to the
+ user, or it may reject the flow and transmit an exception to the
+
+
+
+Thornburgh Informational [Page 45]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ sender. The flow receiver may close and reject a flow at a later
+ time, after first accepting it. The flow receiver acknowledges all
+ data sent to it, regardless of whether the flow was accepted.
+ Acknowledgements drive a congestion control mechanism.
+
+ An endpoint may have concurrent sessions with other far endpoints.
+ The multiple sessions are distinguished by a session identifier
+ rather than by socket address. This allows an endpoint's address to
+ change mid-session without having to tear down and re-establish a
+ session. The existing cryptographic state for a session can be used
+ to verify a change of address while protecting against session
+ hijacking or denial of service.
+
+ A sender may indicate to a receiver that some user messages are of a
+ time critical or real-time nature. A receiver may indicate to
+ senders on concurrent sessions that it is receiving time critical
+ messages from another endpoint. The other senders SHOULD modify
+ their congestion control parameters to yield capacity to the session
+ carrying time critical messages.
+
+ A sender may close a flow. The flow is completed when the receiver
+ has no outstanding gaps before the final fragment of the flow. The
+ sender and receiver reserve a completed flow's identifier for a time
+ to allow in-flight messages to drain from the network.
+
+ Eventually, neither end will have any flows open to the other. The
+ session will be idle and quiescent. Either end may reliably close
+ the session to recover its resources.
+
+ In certain circumstances, an endpoint may be ceasing operation and
+ not have time to wait for acknowledgement of a reliable session
+ close. In this case, the halting endpoint may send an abrupt session
+ close to advise the far end that it is halting immediately.
+
+3.2. Endpoint Identity
+
+ Each RTMFP endpoint has an identity. The identity is encoded in a
+ certificate. This specification doesn't mandate any particular
+ certificate format, cryptographic algorithms, or cryptographic
+ properties for certificates.
+
+ An endpoint is named by an Endpoint Discriminator. This
+ specification doesn't mandate any particular format for Endpoint
+ Discriminators.
+
+ An Endpoint Discriminator MAY select more than one identity and MAY
+ match more than one distinct certificate.
+
+
+
+
+Thornburgh Informational [Page 46]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ Multiple distinct Endpoint Discriminators MAY match one certificate.
+
+ It is RECOMMENDED that multiple endpoints not have the same identity.
+ Entities with the same identity are indistinguishable during session
+ startup; this situation could be undesirable in some applications.
+
+ An endpoint MAY have more than one address.
+
+ The Cryptography Profile implements the following functions for
+ identities, certificates, and Endpoint Discriminators, whose
+ operation MUST be deterministic:
+
+ o Test whether a given certificate is authentic. Authenticity can
+ comprise verifying an issuer signature chain in a public key
+ infrastructure.
+
+ o Test whether a given Endpoint Discriminator selects a given
+ certificate.
+
+ o Test whether a given Endpoint Discriminator selects the local
+ endpoint.
+
+ o Generate a Canonical Endpoint Discriminator for a given
+ certificate. Canonical Endpoint Discriminators for distinct
+ identities SHOULD be distinct. If two distinct identities have
+ the same Canonical Endpoint Discriminator, an initiator might
+ abort a new opening session to the second identity
+ (Section 3.5.1.1.1); this behavior might not be desirable.
+
+ o Given a certificate, a message, and a digital signature over the
+ message, test whether the signature is valid and generated by the
+ owner of the certificate.
+
+ o Generate a digital signature for a given message corresponding to
+ the near identity.
+
+ o Given the near identity and a far certificate, determine which one
+ shall prevail as Initiator and which shall assume the Responder
+ role in the case of startup glare. The far end MUST arrive at the
+ same conclusion. A comparison function can comprise performing a
+ lexicographic ordering of the binary certificates, declaring the
+ far identity the prevailing endpoint if the far certificate is
+ ordered before the near certificate, and otherwise declaring the
+ near identity to be the prevailing endpoint.
+
+
+
+
+
+
+
+Thornburgh Informational [Page 47]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ o Given a first certificate and a second certificate, test whether a
+ new incoming session from the second shall override an existing
+ session with the first. It is RECOMMENDED that the test comprise
+ testing whether the certificates are bitwise identical.
+
+ All other semantics for certificates and Endpoint Discriminators are
+ determined by the Cryptography Profile and the application.
+
+3.3. Packet Multiplex
+
+ An RTMFP typically has one or more interfaces through which it
+ communicates with other RTMFP endpoints. RTMFP can communicate with
+ multiple distinct other RTMFP endpoints through each local interface.
+ Session multiplexing over a shared interface can facilitate peer-to-
+ peer communications through a NAT, by enabling third-party endpoints
+ such as Forwarders (Section 3.5.1.5) and Redirectors
+ (Section 3.5.1.4) to observe the translated public address and inform
+ peers of the translation.
+
+ An interface is typically a UDP socket (Section 2.2.1) but MAY be any
+ suitable datagram transport service where endpoints can be addressed
+ by IPv4 or IPv6 socket addresses.
+
+ RTMFP uses a session ID to multiplex and demultiplex communications
+ with distinct endpoints (Section 2.2.2), in addition to the endpoint
+ socket address. This allows an RTMFP to detect a far-end address
+ change (as might happen, for example, in mobile and wireless
+ scenarios) and allows communication sessions to survive address
+ changes. This also allows an RTMFP to act as a Forwarder or
+ Redirector for an endpoint with which it has an active session, by
+ distinguishing startup packets from those of the active session.
+
+ On receiving a packet, an RTMFP decodes the session ID to look up the
+ corresponding session information context and decryption key.
+ Session ID 0 is reserved for session startup and MUST NOT be used for
+ an active session. A packet for Session ID 0 uses the Default
+ Session Key as defined by the Cryptography Profile.
+
+3.4. Packet Fragmentation
+
+ When an RTMFP packet (Section 2.2.4) is unavoidably larger than the
+ path MTU (such as a startup packet containing an RHello
+ (Section 2.3.4) or IIKeying (Section 2.3.7) chunk with a large
+ certificate), it can be fragmented into segments that do not exceed
+ the path MTU by using the Packet Fragment chunk (Section 2.3.1).
+
+
+
+
+
+
+Thornburgh Informational [Page 48]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ The packet fragmentation mechanism SHOULD be used only to segment
+ unavoidably large packets. Accordingly, this mechanism SHOULD be
+ employed only during session startup with Session ID 0. This
+ mechanism MUST NOT be used instead of the natural fragmentation
+ mechanism of the User Data (Section 2.3.11) and Next User Data
+ (Section 2.3.12) chunks for dividing the messages of the user's data
+ flows into segments that do not exceed the path MTU.
+
+ A fragmented plain RTMFP packet is reassembled by concatenating the
+ packetFragment fields of the fragments for the packet in contiguous
+ ascending order, starting from index 0 through and including the
+ final fragment.
+
+ When reassembling packets for Session ID 0, a receiver SHOULD
+ identify the packets by the socket address from which the packet
+ containing the fragment was received, as well as the indicated
+ packetID.
+
+ A receiver SHOULD allow up to 60 seconds to completely receive a
+ fragmented packet for which progress is being made. A packet is
+ progressing if at least one new fragment for it was received in the
+ last second.
+
+ A receiver MUST discard a Packet Fragment chunk having an empty
+ packetFragment field.
+
+ The mode of each packet containing Packet Fragments for the same
+ fragmented packet MUST match the mode of the fragmented packet. A
+ receiver MUST discard any new Packet Fragment chunk received in a
+ packet with a mode different from the mode of the packet containing
+ the first received fragment. A receiver MUST discard any reassembled
+ packet with a mode different than the packets containing its
+ fragments.
+
+ In order to avoid jamming the network, the sender MUST rate limit
+ packet transmission. In the absence of specific path capacity
+ information (for instance, during session startup), a sender SHOULD
+ NOT send more than 4380 bytes nor more than four packets per distinct
+ endpoint every 200 ms.
+
+ To avoid resource exhaustion, a receiver SHOULD limit the number of
+ concurrent packet reassembly buffers and the size of each buffer.
+ Limits can depend, for example, on the expected size of reassembled
+ packets, on the rate at which fragmented packets are expected to be
+ received, on the expected degree of interleaving, and on the expected
+ function of the receiver. Limits can depend on the available
+ resources of the receiver. There can be different limits for packets
+ with Session ID 0 and packets for established sessions. For example,
+
+
+
+Thornburgh Informational [Page 49]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ a busy server might need to allow for several hundred concurrent
+ packet reassembly buffers to accommodate hundreds of connection
+ requests per second with potentially interleaved fragments, but a
+ client device with constrained resources could allow just a few
+ reassembly buffers. In the absence of specific information regarding
+ the expected size of reassembled packets, a receiver should set the
+ limit for each packet reassembly buffer to 65536 bytes.
+
+3.5. Sessions
+
+ A session is the protocol relationship between a pair of
+ communicating endpoints, comprising the shared and endpoint-specific
+ information context necessary to carry out the communication. The
+ session context at each end includes at least:
+
+ o TS_RX: the last timestamp received from the far end;
+
+ o TS_RX_TIME: the time at which TS_RX was first observed to be
+ different than its previous value;
+
+ o TS_ECHO_TX: the last timestamp echo sent to the far end;
+
+ o MRTO: the measured retransmission timeout;
+
+ o ERTO: the effective retransmission timeout;
+
+ o Cryptographic keys for encrypting and decrypting packets, and for
+ verifying the validity of packets, according to the Cryptography
+ Profile;
+
+ o Cryptographic near and far nonces according to the Cryptography
+ Profile, where the near nonce is the far end's far nonce, and vice
+ versa;
+
+ o The certificate of the far end;
+
+ o The receive session identifier, used by the far end when sending
+ packets to this end;
+
+ o The send session identifier to use when sending packets to the far
+ end;
+
+ o DESTADDR: the destination socket address to use when sending
+ packets to the far end;
+
+ o The set of all sending flow contexts (Section 3.6.2);
+
+ o The set of all receiving flow contexts (Section 3.6.3);
+
+
+
+Thornburgh Informational [Page 50]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ o The transmission budget, which controls the rate at which data is
+ sent into the network (for example, a congestion window);
+
+ o S_OUTSTANDING_BYTES: the total amount of user message data
+ outstanding, or in flight, in the network -- that is, the sum of
+ the F_OUTSTANDING_BYTES of each sending flow in the session;
+
+ o RX_DATA_PACKETS: a count of the number of received packets
+ containing at least one User Data chunk since the last
+ acknowledgement was sent, initially 0;
+
+ o ACK_NOW: a boolean flag indicating whether an acknowledgement
+ should be sent immediately, initially false;
+
+ o DELACK_ALARM: an alarm to trigger an acknowledgement after a
+ delay, initially unset;
+
+ o The state, at any time being one of the following values: the
+ opening states S_IHELLO_SENT and S_KEYING_SENT, the open state
+ S_OPEN, the closing states S_NEARCLOSE and S_FARCLOSE_LINGER, and
+ the closed states S_CLOSED and S_OPEN_FAILED; and
+
+ o The role -- either Initiator or Responder -- of this end of the
+ session.
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 51]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ Note: The following diagram is only a summary of state transitions
+ and their causing events, and is not a complete operational
+ specification.
+
+ rcv IIKeying Glare
+ far prevails +-------------+ ultimate open timeout
+ +--------------|S_IHELLO_SENT|-------------+
+ | +-------------+ |
+ | |rcv RHello |
+ | | v
+ | v +-------------+
+ |<-----------(duplicate session?) |S_OPEN_FAILED|
+ | yes |no +-------------+
+ | | ^
+ | rcv IIKeying Glare v |
+ | far prevails +-------------+ |
+ |<-------------|S_KEYING_SENT|-------------+
+ | +-------------+ ultimate open timeout
+ | |rcv RIKeying
+ | |
+ | rcv v
+ | +-+ IIKeying +--------+ rcv Close Request
+ | |X|---------->| S_OPEN |--------------------+
+ | +-+ +--------+ |
+ | | |ABRUPT CLOSE |
+ | ORDERLY CLOSE| |or rcv Close Ack |
+ | | |or rcv IIKeying |
+ | | | session override |
+ | | +-------+ |
+ | v | v
+ | +-----------+ | +-----------------+
+ | |S_NEARCLOSE| | |S_FARCLOSE_LINGER|
+ | +-----------+ | +-----------------+
+ | rcv Close Ack| | |rcv Close Ack
+ | or 90 seconds| v |or 19 seconds
+ | | +--------+ |
+ | +------>|S_CLOSED|<---------+
+ +-------------------------->| |
+ +--------+
+
+ Figure 8: Session State Diagram
+
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 52]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+3.5.1. Startup
+
+3.5.1.1. Normal Handshake
+
+ RTMFP sessions are established with a 4-way handshake in two round
+ trips. The initiator begins by sending an IHello to one or more
+ candidate addresses for the desired destination endpoint. A
+ responder statelessly sends an RHello in response. The first correct
+ RHello received at the initiator is selected; all others are ignored.
+ The initiator computes its half of the session keying and sends an
+ IIKeying. The responder receives the IIKeying and, if it is
+ acceptable, computes its half of the session keying, at which point
+ it can also compute the shared session keying and session nonces.
+ The responder creates a new S_OPEN session with the initiator and
+ sends an RIKeying. The initiator receives the RIKeying and, if it is
+ acceptable, computes the shared session keying and session nonces.
+ The initiator's session is now S_OPEN.
+
+ . Initiator Responder .
+ | IHello |
+ |(EPD,Tag) |
+ S_IHELLO_SENT |(SID=0) |
+ |------------------------------->|
+ | |
+ | RHello |
+ | (Tag,Cookie,RCert)|
+ | (SID=0)|
+ |<-------------------------------|
+ S_KEYING_SENT | |
+ | IIKeying |
+ |(ISID,Cookie,ICert,SKIC,ISig) |
+ |(SID=0) |
+ |------------------------------->|
+ | |
+ | RIKeying |
+ | (RSID,SKRC,RSig)|
+ | (SID=ISID,Key=Default)| S_OPEN
+ |<-------------------------------|
+ S_OPEN | |
+ | S E S S I O N |
+ |<-------------------(SID=ISID)--|
+ |--(SID=RSID)------------------->|
+
+ Figure 9: Normal Handshake
+
+ In the following sections, the handshake is detailed from the
+ perspectives of the initiator and responder.
+
+
+
+
+Thornburgh Informational [Page 53]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+3.5.1.1.1. Initiator
+
+ The initiator determines that a session is needed for an Endpoint
+ Discriminator. The initiator creates state for a new opening session
+ and begins with a candidate endpoint address set containing at least
+ one address. The new session is placed in the S_IHELLO_SENT state.
+
+ If the session does not move to the S_OPEN state before an ultimate
+ open timeout, the session has failed and moves to the S_OPEN_FAILED
+ state. The RECOMMENDED ultimate open timeout is 95 seconds.
+
+ The initiator chooses a new, unique tag not used by any currently
+ opening session. It is RECOMMENDED that the tag be cryptographically
+ pseudorandom and be at least 8 bytes in length, so that it is hard to
+ guess. The initiator constructs an IHello chunk (Section 2.3.2) with
+ the Endpoint Discriminator and the tag.
+
+ While the initiator is in the S_IHELLO_SENT state, it sends the
+ IHello to each candidate endpoint address in the set, on a backoff
+ schedule. The backoff SHOULD NOT be less than multiplicative, with
+ not less than 1.5 seconds added to the interval between each attempt.
+ The backoff SHOULD be scheduled separately for each candidate
+ address, since new candidates can be added over time.
+
+ If the initiator receives a Redirect chunk (Section 2.3.5) with a tag
+ echo matching this session, AND this session is in the S_IHELLO_SENT
+ state, then for each redirect destination indicated in the Redirect:
+ if the candidate endpoint address set contains fewer than
+ REDIRECT_THRESHOLD addresses, add the indicated redirect destination
+ to the candidate endpoint address set. REDIRECT_THRESHOLD SHOULD NOT
+ be more than 24.
+
+ If the initiator receives an RHello chunk (Section 2.3.4) with a tag
+ echo matching this session, AND this session is in the S_IHELLO_SENT
+ state, AND the responder certificate matches the desired Endpoint
+ Discriminator, AND the certificate is authentic according to the
+ Cryptography Profile, then:
+
+ 1. If the Canonical Endpoint Discriminator for the responder
+ certificate matches the Canonical Endpoint Discriminator of
+ another existing session in the S_KEYING_SENT or S_OPEN states,
+ AND the certificate of the other opening session matches the
+ desired Endpoint Discriminator, then this session is a duplicate
+ and SHOULD be aborted in favor of the other existing session;
+ otherwise,
+
+
+
+
+
+
+Thornburgh Informational [Page 54]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ 2. Move to the S_KEYING_SENT state. Set DESTADDR, the far-end
+ address for the session, to the address from which this RHello
+ was received. The initiator chooses a new, unique receive
+ session ID, not used by any other session, for the responder to
+ use when sending packets to the initiator. It computes a Session
+ Key Initiator Component appropriate to the responder's
+ certificate according to the Cryptography Profile. Using this
+ data and the cookie from the RHello, the initiator constructs and
+ signs an IIKeying chunk (Section 2.3.7).
+
+ While the initiator is in the S_KEYING_SENT state, it sends the
+ IIKeying to DESTADDR on a backoff schedule. The backoff SHOULD NOT
+ be less than multiplicative, with not less than 1.5 seconds added to
+ the interval between each attempt.
+
+ If the initiator receives an RIKeying chunk (Section 2.3.8) in a
+ packet with this session's receive session identifier, AND this
+ session is in the S_KEYING_SENT state, AND the signature in the chunk
+ is authentic according to the far end's certificate (from the
+ RHello), AND the Session Key Responder Component successfully
+ combines with the Session Key Initiator Component and the near and
+ far certificates to form the shared session keys and nonces according
+ to the Cryptography Profile, then the session has opened
+ successfully. The session moves to the S_OPEN state. The send
+ session identifier is set from the RIKeying. Packet encryption,
+ decryption, and verification now use the newly computed shared
+ session keys, and the session nonces are available for application-
+ layer cryptographic challenges.
+
+3.5.1.1.2. Responder
+
+ On receipt of an IHello chunk (Section 2.3.2) with an Endpoint
+ Discriminator that selects its identity, an endpoint SHOULD construct
+ an RHello chunk (Section 2.3.4) and send it to the address from which
+ the IHello was received. To avoid a potential resource exhaustion
+ denial of service, the endpoint SHOULD NOT create any persistent
+ state associated with the IHello. The endpoint MUST generate the
+ cookie for the RHello in such a way that it can be recognized as
+ authentic and valid when echoed in an IIKeying. The endpoint SHOULD
+ use the address from which the IHello was received as part of the
+ cookie generation formula. Cookies SHOULD be valid only for a
+ limited time; that lifetime SHOULD NOT be less than 95 seconds (the
+ recommended ultimate session open timeout).
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 55]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ On receipt of an FIHello chunk (Section 2.3.3) from a Forwarder
+ (Section 3.5.1.5) where the Endpoint Discriminator selects its
+ identity, an endpoint SHOULD do one of the following:
+
+ 1. Compute, construct, and send an RHello as though the FIHello was
+ an IHello received from the indicated reply address; or
+
+ 2. Construct and send an Implied Redirect (Section 2.3.5) to the
+ FIHello's reply address; or
+
+ 3. Ignore this FIHello.
+
+ On receipt of an IIKeying chunk (Section 2.3.7), if the cookie is not
+ authentic or if it has expired, ignore this IIKeying; otherwise,
+
+ On receipt of an IIKeying chunk, if the cookie appears authentic but
+ does not match the address from which the IIKeying's packet was
+ received, perform the special processing at Cookie Change
+ (Section 3.5.1.2); otherwise,
+
+ On receipt of an IIKeying with an authentic and valid cookie, if the
+ certificate is authentic according to the Cryptography Profile, AND
+ the signature in the chunk is authentic according to the far end's
+ certificate and the Cryptography Profile, AND the Session Key
+ Initiator Component is acceptable, then:
+
+ 1. If the address from which this IIKeying was received corresponds
+ to an opening session in the S_IHELLO_SENT or S_KEYING_SENT
+ state, perform the special processing at Glare (Section 3.5.1.3);
+ otherwise,
+
+ 2. If the address from which this IIKeying was received corresponds
+ to a session in the S_OPEN state, then:
+
+ 1. If the receiver was the Responder for the S_OPEN session and
+ the session identifier, certificate, and Session Key
+ Initiator Component are identical to those of the S_OPEN
+ session, this IIKeying is a retransmission, so resend the
+ S_OPEN session's RIKeying using the Default Session Key as
+ specified below; otherwise,
+
+ 2. If the certificate from this IIKeying does not override the
+ certificate of the S_OPEN session, ignore this IIKeying;
+ otherwise,
+
+
+
+
+
+
+
+Thornburgh Informational [Page 56]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ 3. The certificate from this IIKeying overrides the certificate
+ of the S_OPEN session; this is a new opening session from the
+ same identity, and the existing S_OPEN session is stale.
+ Move the existing S_OPEN session to S_CLOSED and abort all of
+ its flows (signaling exceptions to the user), then continue
+ processing this IIKeying.
+
+ Otherwise,
+
+ 3. Compute a Session Key Responder Component and choose a new,
+ unique receive session ID not used by any other session for the
+ initiator to use when sending packets to the responder. Using
+ this data, construct and, with the Session Key Initiator
+ Component, sign an RIKeying chunk (Section 2.3.8). Using the
+ Session Key Initiator and Responder Components and the near and
+ far certificates, the responder combines and computes the shared
+ session keys and nonces according to the Cryptography Profile.
+ The responder creates a new session in the S_OPEN state, with the
+ far-endpoint address DESTADDR taken from the source address of
+ the packet containing the IIKeying and the send session
+ identifier taken from the IIKeying. The responder sends the
+ RIKeying to the initiator using the Default Session Key and the
+ requested send session identifier. Packet encryption,
+ decryption, and verification of all future packets for this
+ session use the newly computed keys, and the session nonces are
+ available for application-layer cryptographic challenges.
+
+3.5.1.2. Cookie Change
+
+ In some circumstances, the responder may generate an RHello cookie
+ for an initiator's address that isn't the address the initiator would
+ use when sending packets directly to the responder. This can happen,
+ for example, when the initiator has multiple local addresses and uses
+ one address to reach a Forwarder (Section 3.5.1.5) but another to
+ reach the responder.
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 57]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ Consider the following example:
+
+ Initiator Forwarder Responder
+ | IHello | |
+ |(Src=Ix) | |
+ |------------------------------->| |
+ | | FIHello |
+ | |(RA=Ix) |
+ | |-------------------------------->|
+ | |
+ | RHello |
+ | (Cookie:Ix)|
+ |<-----------------------------------------------------------------|
+ | |
+ | IIKeying |
+ |(Cookie:Ix,Src=Iy) |
+ |----------------------------------------------------------------->|
+ | |
+ | RHello Cookie Change |
+ | (Cookie:Ix,Cookie:Iy)|
+ |<-----------------------------------------------------------------|
+ | |
+ | IIKeying |
+ |(Cookie:Iy) |
+ |----------------------------------------------------------------->|
+ | |
+ | RIKeying |
+ |<-----------------------------------------------------------------|
+ | |
+ |<======================== S E S S I O N =========================>|
+
+ Figure 10: Handshake with Cookie Change
+
+ The initiator has two network interfaces: a first preferred interface
+ with address Ix = 192.0.2.100:50000, and a second with address Iy =
+ 198.51.100.101:50001. The responder has one interface with address
+ Ry = 198.51.100.200:51000, on the same network as the initiator's
+ second interface. The initiator uses its first interface to reach a
+ Forwarder. The Forwarder observes the initiator's address of Ix and
+ sends a Forwarded IHello (Section 2.3.3) to the responder. The
+ responder treats this as if it were an IHello from Ix, calculates a
+ corresponding cookie, and sends an RHello to Ix. The initiator
+ receives this RHello from Ry and selects that address as the
+ destination for the session. It then sends an IIKeying, copying the
+ cookie from the RHello. However, since the source of the RHello is
+ Ry, on a network to which the initiator is directly connected, the
+ initiator uses its second interface Iy to send the IIKeying. The
+ responder, on receiving the IIKeying, will compare the cookie to the
+
+
+
+Thornburgh Informational [Page 58]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ expected value based on the source address of the packet, and since
+ the IIKeying source doesn't match the IHello source used to generate
+ the cookie, the responder will reject the IIKeying.
+
+ If the responder determines that it generated the cookie in the
+ IIKeying but the cookie doesn't match the sender's address (for
+ example, if the cookie is in two parts, with a first part generated
+ independently of the initiator's address and a second part dependent
+ on the address), the responder SHOULD generate a new cookie based on
+ the address from which the IIKeying was received and send an RHello
+ Cookie Change chunk (Section 2.3.6) to the source of the IIKeying,
+ using the session ID from the IIKeying and the Default Session Key.
+
+ If the initiator receives an RHello Cookie Change chunk for a session
+ in the S_KEYING_SENT state, AND the old cookie matches the one
+ originally sent to the responder, then the initiator adopts the new
+ cookie, constructs and signs a new IIKeying chunk, and sends the new
+ IIKeying to the responder. The initiator SHOULD NOT change the
+ cookie for a session more than once.
+
+3.5.1.3. Glare
+
+ Glare occurs when two endpoints attempt to initiate sessions to each
+ other concurrently. Glare is detected by receipt of a valid and
+ authentic IIKeying from an endpoint address that is a destination for
+ an opening session. Only one session is allowed between a pair of
+ endpoints.
+
+ Glare is resolved by comparing the certificate in the received
+ IIKeying with the near end's certificate. The Cryptography Profile
+ defines a certificate comparison function to determine the prevailing
+ endpoint when there is glare.
+
+ If the near end prevails, discard and ignore the received IIKeying.
+ The far end will abort its opening session on receipt of IIKeying
+ from the near end.
+
+ Otherwise, the far end prevails:
+
+ 1. If the certificate in the IIKeying overrides the certificate
+ associated with the near opening session according to the
+ Cryptography Profile, then abort and destroy the near opening
+ session. Then,
+
+ 2. Continue with normal Responder IIKeying processing
+ (Section 3.5.1.1.2).
+
+
+
+
+
+Thornburgh Informational [Page 59]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+3.5.1.4. Redirector
+
+ +-----------+ +------------+ +-----------+
+ | Initiator |---------->| Redirector | | Responder |
+ | |<----------| | | |
+ | | +------------+ | |
+ | |<=================================>| |
+ +-----------+ +-----------+
+
+ Figure 11: Redirector
+
+ A Redirector acts like a name server for Endpoint Discriminators.
+ An initiator MAY use a Redirector to discover additional candidate
+ endpoint addresses for a desired endpoint.
+
+ On receipt of an IHello chunk with an Endpoint Discriminator that
+ does not select the Redirector's identity, the Redirector constructs
+ and sends back to the initiator a Responder Redirect chunk
+ (Section 2.3.5) containing one or more additional candidate addresses
+ for the indicated endpoint.
+
+ Initiator Redirector Responder
+ | IHello | |
+ |------------------------------->| |
+ | | |
+ | Redirect | |
+ |<-------------------------------| |
+ | |
+ | IHello |
+ |----------------------------------------------------------------->|
+ | |
+ | RHello |
+ |<-----------------------------------------------------------------|
+ | |
+ | IIKeying |
+ |----------------------------------------------------------------->|
+ | |
+ | RIKeying |
+ |<-----------------------------------------------------------------|
+ | |
+ |<======================== S E S S I O N =========================>|
+
+ Figure 12: Handshake Using a Redirector
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 60]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ Deployment Design Note: Redirectors SHOULD NOT initiate new sessions
+ to endpoints that might use the Redirector's address as a candidate
+ for another endpoint, since the far end might interpret the
+ Redirector's IIKeying as glare for the far end's initiation to the
+ other endpoint.
+
+3.5.1.5. Forwarder
+
+ +-----------+ +-----------+ +---+ +-----------+
+ | Initiator |---->| Forwarder |<===>| N |<===>| Responder |
+ | | +-----------+ | A | | |
+ | |<=====================>| T |<===>| |
+ +-----------+ +---+ +-----------+
+
+ Figure 13: Forwarder
+
+ A responder might be behind a NAT or firewall that doesn't allow
+ inbound packets to reach the endpoint until it first sends an
+ outbound packet for a particular far-endpoint address.
+
+ A Forwarder's endpoint address MAY be a candidate address for another
+ endpoint. A responder MAY use a Forwarder to receive FIHello chunks
+ sent on behalf of an initiator.
+
+ On receipt of an IHello chunk with an Endpoint Discriminator that
+ does not select the Forwarder's identity, if the Forwarder has an
+ S_OPEN session with an endpoint whose certificate matches the desired
+ Endpoint Discriminator, the Forwarder constructs and sends an FIHello
+ chunk (Section 2.3.3) to the selected endpoint over the S_OPEN
+ session, using the tag and Endpoint Discriminator from the IHello
+ chunk and the source address of the packet containing the IHello for
+ the corresponding fields of the FIHello.
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 61]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ On receipt of an FIHello chunk, a responder might send an RHello or
+ Implied Redirect to the original source of the IHello
+ (Section 3.5.1.1.2), potentially allowing future packets to flow
+ directly between the initiator and responder through the NAT or
+ firewall.
+
+ Initiator Forwarder NAT Responder
+ | IHello | | |
+ |------------------------------->| | |
+ | | FIHello | |
+ | |--------------->|--------------->|
+ | | |
+ | | RHello |
+ | :<---------------|
+ |<------------------------------------------------: |
+ | : |
+ | IIKeying : |
+ |-------------------------------------------------:--------------->|
+ | : |
+ | : RIKeying |
+ | :<---------------|
+ |<------------------------------------------------: |
+ | : |
+ |<======================== S E S S I O N ========>:<==============>|
+
+ Figure 14: Forwarder Handshake where Responder Sends an RHello
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 62]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ Initiator Forwarder NAT Responder
+ | IHello | | |
+ |------------------------------->| | |
+ | | FIHello | |
+ | |--------------->|--------------->|
+ | | |
+ | | Redirect |
+ | | (Implied,RD={})|
+ | :<---------------|
+ |<------------------------------------------------: |
+ | : |
+ | IHello : |
+ |------------------------------------------------>:--------------->|
+ | : |
+ | : RHello |
+ | :<---------------|
+ |<------------------------------------------------: |
+ | : |
+ | IIKeying : |
+ |------------------------------------------------>:--------------->|
+ | : |
+ | : RIKeying |
+ | :<---------------|
+ |<------------------------------------------------: |
+ | : |
+ |<======================== S E S S I O N ========>:<==============>|
+
+ Figure 15: Forwarder Handshake where Responder Sends an
+ Implied Redirect
+
+3.5.1.6. Redirector and Forwarder with NAT
+
+ +---+ +---+ +---+ +---+ +---+
+ | I | | N | | I | | N | | R |
+ | n |------>| A |------>| n | | A | | e |
+ | i | | T | | t |<====>| T |<====>| s |
+ | t |<------| |<------| r | | | | p |
+ | i | | | | o | | | | o |
+ | a | | | +---+ | | | n |
+ | t | | | | | | d |
+ | o |<=====>| |<================>| |<====>| e |
+ | r | | | | | | r |
+ +---+ +---+ +---+ +---+
+
+ Figure 16: Introduction Service for Initiator and Responder
+ behind NATs
+
+
+
+
+
+Thornburgh Informational [Page 63]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ An initiator and responder might each be behind distinct NATs or
+ firewalls that don't allow inbound packets to reach the respective
+ endpoints until each first sends an outbound packet for a particular
+ far-endpoint address.
+
+ An introduction service comprising Redirector and Forwarder functions
+ may facilitate direct communication between endpoints each behind
+ a NAT.
+
+ The responder is registered with the introduction service via an
+ S_OPEN session to it. The service observes and records the
+ responder's public NAT address as the DESTADDR of the S_OPEN session.
+ The service MAY record other addresses for the responder, for example
+ addresses that the responder self-reports as being directly attached.
+
+ The initiator begins with an address of the introduction service as
+ an initial candidate. The Redirector portion of the service sends to
+ the initiator a Responder Redirect containing at least the
+ responder's public NAT address as previously recorded. The Forwarder
+ portion of the service sends to the responder a Forwarded IHello
+ containing the initiator's public NAT address as observed to be the
+ source of the IHello.
+
+ The responder sends an RHello to the initiator's public NAT address
+ in response to the FIHello. This will allow inbound packets to the
+ responder through its NAT from the initiator's public NAT address.
+
+ The initiator sends an IHello to the responder's public NAT address
+ in response to the Responder Redirect. This will allow inbound
+ packets to the initiator through its NAT from the responder's public
+ NAT address.
+
+ With transit paths created in both NATs, normal session startup can
+ proceed.
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 64]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ Initiator NAT-I Redirector+Forwarder NAT-R Responder
+ | | | | |
+ | IHello | | | |
+ |(Dst=Intro) | | | |
+ |-------------->| | | |
+ | |--------------->| | |
+ | | | FIHello | |
+ | | |(RA=NAT-I-Pub) | |
+ | | |--------------->|--------------->|
+ | | Redirect | | |
+ | | (RD={NAT-R-Pub,| | |
+ | | ...})| | |
+ |<--------------|<---------------| | |
+ | | | RHello |
+ | | | (Dst=NAT-I-Pub)|
+ | | :<---------------|
+ | | (*) <--------------------------: |
+ | IHello | : |
+ |(Dst=NAT-R-Pub)| : |
+ |-------------->: : |
+ | :-------------------------------->:--------------->|
+ | : : |
+ | : : RHello |
+ | : :<---------------|
+ |<--------------:<--------------------------------: |
+ | : : |
+ | IIKeying : : |
+ |-------------->: : |
+ | :-------------------------------->:--------------->|
+ | : : |
+ | : : RIKeying |
+ | : :<---------------|
+ |<--------------:<--------------------------------: |
+ | : : |
+ |<=============>:<======== S E S S I O N ========>:<==============>|
+
+ Figure 17: Handshake with Redirector and Forwarder
+
+ At the point in Figure 17 marked (*), the responder's RHello from the
+ FIHello might arrive at the initiator's NAT before or after the
+ initiator's IHello is sent outbound to the responder's public NAT
+ address. If it arrives before, it may be dropped by the NAT. If it
+ arrives after, it will transit the NAT and trigger keying without
+ waiting for another round-trip time. The timing of this race
+ depends, among other factors, on the relative distances of the
+ initiator and responder from each other and from the introduction
+ service.
+
+
+
+
+Thornburgh Informational [Page 65]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+3.5.1.7. Load Distribution and Fault Tolerance
+
+ +---+ IHello/RHello +-------------+
+ | I |<------------------->| Responder 1 |
+ | n | +-------------+
+ | i | SESSION +-------------+
+ | t |<=========>| Responder 2 |
+ | i | +-------------+
+ | a | IHello... +----------------+
+ | t |-------------------------> X | Dead Responder |
+ | o | +----------------+
+ | r | IHello/RHello +-------------+
+ | |<---------------->| Responder N |
+ +---+ +-------------+
+
+ Figure 18: Parallel Open to Multiple Endpoints
+
+ As specified in Section 3.2, more than one endpoint is allowed to be
+ selected by one Endpoint Discriminator. This will typically be the
+ case for a set of servers, any of which could accommodate a
+ connecting client.
+
+ As specified in Section 3.5.1.1.1, an initiator is allowed to use
+ multiple candidate endpoint addresses when starting a session, and
+ the sender of the first acceptable RHello chunk to be received is
+ selected to complete the session, with later responses ignored. An
+ initiator can start with the multiple candidate endpoint addresses,
+ or it may learn them during startup from one or more Redirectors
+ (Section 3.5.1.4).
+
+ Parallel open to multiple endpoints for the same Endpoint
+ Discriminator, combined with selection by earliest RHello, can be
+ used for load distribution and fault tolerance. The cost at each
+ endpoint that is not selected is limited to receiving and processing
+ an IHello, and generating and sending an RHello.
+
+ In one circumstance, multiple servers of similar processing and
+ networking capacity may be located in near proximity to each other,
+ such as in a data center. In this circumstance, a less heavily
+ loaded server can respond to an IHello more quickly than more heavily
+ loaded servers and will tend to be selected by a client.
+
+ In another circumstance, multiple servers may be located in different
+ physical locations, such as different data centers. In this
+ circumstance, a server that is located nearer (in terms of network
+ distance) to the client can respond earlier than more distant servers
+ and will tend to be selected by the client.
+
+
+
+
+Thornburgh Informational [Page 66]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ Multiple servers, in proximity or distant from one another, can form
+ a redundant pool of servers. A client can perform a parallel open to
+ the multiple servers. In normal operation, the multiple servers will
+ all respond, and the client will select one of them as described
+ above. If one of the multiple servers fails, other servers in the
+ pool can still respond to the client, allowing the client to succeed
+ to an S_OPEN session with one of them.
+
+3.5.2. Congestion Control
+
+ An RTMFP MUST implement congestion control and avoidance algorithms
+ that are "TCP compatible", in accordance with Internet best current
+ practice [RFC2914]. The algorithms SHOULD NOT be more aggressive in
+ sending data than those described in "TCP Congestion Control"
+ [RFC5681] and MUST NOT be more aggressive in sending data than the
+ "slow start algorithm" described in Section 3.1 of RFC 5681.
+
+ An endpoint maintains a transmission budget in the session
+ information context of each S_OPEN session (Section 3.5), controlling
+ the rate at which the endpoint sends data into the network.
+
+ For window-based congestion control and avoidance algorithms, the
+ transmission budget is the congestion window, which is the amount of
+ user data that is allowed to be outstanding, or in flight, in the
+ network. Transmission is allowed when S_OUTSTANDING_BYTES
+ (Section 3.5) is less than the congestion window (Section 3.6.2.3).
+ See Appendix A for an experimental window-based congestion control
+ algorithm for real-time and bulk data.
+
+ An endpoint avoids sending large bursts of data or packets into the
+ network (Section 3.5.2.3).
+
+ A sending endpoint increases and decreases its transmission budget in
+ response to acknowledgements (Section 3.6.2.4) and loss according to
+ the congestion control and avoidance algorithms. Loss is detected by
+ negative acknowledgement (Section 3.6.2.5) and timeout
+ (Section 3.6.2.6).
+
+ Timeout is determined by the Effective Retransmission Timeout (ERTO)
+ (Section 3.5.2.2). The ERTO is measured using the Timestamp and
+ Timestamp Echo packet header fields (Section 2.2.4).
+
+ A receiving endpoint acknowledges all received data (Section 3.6.3.4)
+ to enable the sender to measure receipt of data, or lack thereof.
+
+ A receiving endpoint may be receiving time critical (or real-time)
+ data from a first sender while receiving data from other senders.
+ The receiving endpoint can signal its other senders (Section 2.2.4)
+
+
+
+Thornburgh Informational [Page 67]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ to cause them to decrease the aggressiveness of their congestion
+ control and avoidance algorithms, in order to yield network capacity
+ to the time critical data (Section 3.5.2.1).
+
+3.5.2.1. Time Critical Reverse Notification
+
+ A sender can increase its transmission budget at a rate compatible
+ with (but not exceeding) the "slow start algorithm" specified in
+ RFC 5681 (with which the transmission rate is doubled every round
+ trip when beginning or restarting transmission, until loss is
+ detected). However, a sender MUST behave as though the slow start
+ threshold SSTHRESH is clamped to 0 (disabling the slow start
+ algorithm's exponential increase behavior) on a session where a Time
+ Critical Reverse Notification (Section 2.2.4) indication has been
+ received from the far end within the last 800 milliseconds, unless
+ the sender is itself currently sending time critical data to the
+ far end.
+
+ During each round trip, a sender SHOULD NOT increase the transmission
+ budget by more than 0.5% or by 384 bytes per round trip (whichever is
+ greater) on a session where a Time Critical Reverse Notification
+ indication has been received from the far end within the last 800
+ milliseconds, unless the sender is itself currently sending time
+ critical data to the far end.
+
+3.5.2.2. Retransmission Timeout
+
+ RTMFP uses the ERTO to detect when a user data fragment has been lost
+ in the network. The ERTO is typically calculated in a manner similar
+ to that specified in "Requirements for Internet Hosts - Communication
+ Layers" [RFC1122] and is a function of round-trip time measurements
+ and persistent timeout behavior.
+
+ The ERTO SHOULD be at least 250 milliseconds and SHOULD allow for the
+ receiver to delay sending an acknowledgement for up to 200
+ milliseconds (Section 3.6.3.4.4). The ERTO MUST NOT be less than the
+ round-trip time.
+
+ To facilitate round-trip time measurement, an endpoint MUST implement
+ the Timestamp Echo facility:
+
+ o On a session entering the S_OPEN state, initialize TS_RX_TIME to
+ negative infinity, and initialize TS_RX and TS_ECHO_TX to have no
+ value.
+
+
+
+
+
+
+
+Thornburgh Informational [Page 68]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ o On receipt of a packet in an S_OPEN session with the
+ timestampPresent (Section 2.2.4) flag set, if the timestamp field
+ in the packet is different than TS_RX, set TS_RX to the value of
+ the timestamp field in the packet, and set TS_RX_TIME to the
+ current time.
+
+ o When sending a packet to the far end in an S_OPEN session:
+
+ 1. Calculate TS_RX_ELAPSED = current time - TS_RX_TIME. If
+ TS_RX_ELAPSED is more than 128 seconds, then set TS_RX and
+ TS_ECHO_TX to have no value, and do not include a timestamp
+ echo; otherwise,
+
+ 2. Calculate TS_RX_ELAPSED_TICKS to be the number of whole
+ 4-millisecond periods in TS_RX_ELAPSED; then
+
+ 3. Calculate TS_ECHO = (TS_RX + TS_RX_ELAPSED_TICKS) MODULO
+ 65536; then
+
+ 4. If TS_ECHO is not equal to TS_ECHO_TX, then set TS_ECHO_TX to
+ TS_ECHO, set the timestampEchoPresent flag, and set the
+ timestampEcho field to TS_ECHO_TX.
+
+ The remainder of this section describes an OPTIONAL method for
+ calculating the ERTO. Real-time applications and P2P mesh
+ applications often require knowing the round-trip time and RTT
+ variance. This section additionally describes a method for measuring
+ the round-trip time and RTT variance, and calculating a smoothed
+ round-trip time.
+
+ Let the session information context contain additional variables:
+
+ o TS_TX: the last timestamp sent to the far end, initialized to have
+ no value;
+
+ o TS_ECHO_RX: the last timestamp echo received from the far end,
+ initialized to have no value;
+
+ o SRTT: the smoothed round-trip time, initialized to have no value;
+
+ o RTTVAR: the round-trip time variance, initialized to 0.
+
+ Initialize MRTO to 250 milliseconds.
+
+ Initialize ERTO to 3 seconds.
+
+
+
+
+
+
+Thornburgh Informational [Page 69]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ On sending a packet to the far end of an S_OPEN session, if the
+ current send timestamp is not equal to TS_TX, then set TS_TX to the
+ current send timestamp, set the timestampPresent flag in the packet
+ header, and set the timestamp field to TS_TX.
+
+ On receipt of a packet from the far end of an S_OPEN session, if the
+ timestampEchoPresent flag is set in the packet header, AND the
+ timestampEcho field is not equal to TS_ECHO_RX, then:
+
+ 1. Set TS_ECHO_RX to timestampEcho;
+
+ 2. Calculate RTT_TICKS = (current send timestamp - timestampEcho)
+ MODULO 65536;
+
+ 3. If RTT_TICKS is greater than 32767, the measurement is invalid,
+ so discard this measurement; otherwise,
+
+ 4. Calculate RTT = RTT_TICKS * 4 milliseconds;
+
+ 5. If SRTT has a value, then calculate new values of RTTVAR
+ and SRTT:
+
+ 1. RTT_DELTA = | SRTT - RTT |;
+
+ 2. RTTVAR = ((3 * RTTVAR) + RTT_DELTA) / 4;
+
+ 3. SRTT = ((7 * SRTT) + RTT) / 8.
+
+ 6. If SRTT has no value, then set SRTT = RTT and RTTVAR = RTT / 2;
+
+ 7. Set MRTO = SRTT + 4 * RTTVAR + 200 milliseconds;
+
+ 8. Set ERTO to MRTO or 250 milliseconds, whichever is greater.
+
+ A retransmission timeout occurs when the most recently transmitted
+ user data fragment has remained outstanding in the network for ERTO.
+ When this timeout occurs, increase ERTO on an exponential backoff
+ with an ultimate backoff cap of 10 seconds:
+
+ 1. Calculate ERTO_BACKOFF = ERTO * 1.4142;
+
+ 2. Calculate ERTO_CAPPED to be ERTO_BACKOFF or 10 seconds, whichever
+ is less;
+
+ 3. Set ERTO to ERTO_CAPPED or MRTO, whichever is greater.
+
+
+
+
+
+
+Thornburgh Informational [Page 70]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+3.5.2.3. Burst Avoidance
+
+ An application's sending patterns may cause the transmission budget
+ to grow to a large value, but at times its sending patterns will
+ result in a comparatively small amount of data outstanding in the
+ network. In this circumstance, especially with a window-based
+ congestion avoidance algorithm, if the application then has a large
+ amount of new data to send (for example, a new bulk data transfer),
+ it could send data into the network all at once to fill the window.
+ This kind of transmission burst is undesirable, however, because it
+ can jam interfaces, links, and buffers.
+
+ Accordingly, in any session, an endpoint SHOULD NOT send more than
+ six packets containing user data between receiving any
+ acknowledgements or retransmission timeouts.
+
+ The following describes an OPTIONAL method to avoid bursting large
+ numbers of packets into the network:
+
+ Let the session information context contain an additional variable
+ DATA_PACKET_COUNT, initialized to 0.
+
+ Transmission of a user data fragment on this session is not allowed
+ if DATA_PACKET_COUNT is greater than or equal to 6, regardless of any
+ other allowance of the congestion control algorithm.
+
+ On transmission of a packet containing at least one User Data chunk
+ (Section 2.3.11), set DATA_PACKET_COUNT = DATA_PACKET_COUNT + 1.
+
+ On receipt of an acknowledgement chunk (Sections 2.3.13 and 2.3.14),
+ set DATA_PACKET_COUNT to 0.
+
+ On a retransmission timeout, set DATA_PACKET_COUNT to 0.
+
+3.5.3. Address Mobility
+
+ Sessions are demultiplexed with a 32-bit session ID, rather than by
+ endpoint address. This allows an endpoint's address to change during
+ an S_OPEN session. This can happen, for example, when switching from
+ a wireless to a wired network, or when moving from one wireless base
+ station to another, or when a NAT restarts.
+
+ If the near end receives a valid packet for an S_OPEN session from a
+ source address that doesn't match DESTADDR, the far end might have
+ changed addresses. The near end SHOULD verify that the far end is
+ definitively at the new address before changing DESTADDR. A
+ suggested verification method is described in Section 3.5.4.2.
+
+
+
+
+Thornburgh Informational [Page 71]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+3.5.4. Ping
+
+ If an endpoint receives a Ping chunk (Section 2.3.9) in a session in
+ the S_OPEN state, it SHOULD construct and send a Ping Reply chunk
+ (Section 2.3.10) in response if possible, copying the message
+ unaltered. The Ping Reply SHOULD be sent as quickly as possible
+ following receipt of a Ping. The semantics of a Ping's message is
+ reserved for the sender; a receiver SHOULD NOT interpret the Ping's
+ message.
+
+ Endpoints can use the mechanism of the Ping chunk and the expected
+ Ping Reply for any purpose. This specification doesn't mandate any
+ specific constraints on the format or semantics of a Ping message. A
+ Ping Reply MUST be sent only as a response to a Ping.
+
+ Receipt of a Ping Reply implies live bidirectional connectivity.
+ This specification doesn't mandate any other semantics for a
+ Ping Reply.
+
+3.5.4.1. Keepalive
+
+ An endpoint can use a Ping to test for live bidirectional
+ connectivity, to test that the far end of a session is still in the
+ S_OPEN state, to keep NAT translations alive, and to keep firewall
+ holes open.
+
+ An endpoint can use a Ping to hasten detection of a near-end address
+ change by the far end.
+
+ An endpoint may declare a session to be defunct and dead after a
+ persistent failure by the far end to return Ping Replies in response
+ to Pings.
+
+ If used for these purposes, a Keepalive Ping SHOULD have an empty
+ message.
+
+ A Keepalive Ping SHOULD NOT be sent more often than once per ERTO.
+ If a corresponding Ping Reply is not received within ERTO of sending
+ the Ping, ERTO SHOULD be increased according to Section 3.5.2
+ ("Congestion Control").
+
+
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 72]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+3.5.4.2. Address Mobility
+
+ This section describes an OPTIONAL but suggested method for
+ processing and verifying a far-end address change.
+
+ Let the session context contain additional variables MOB_TX_TS,
+ MOB_RX_TS, and MOB_SECRET. MOB_TX_TS and MOB_RX_TS have initial
+ values of negative infinity. MOB_SECRET should be a
+ cryptographically pseudorandom value not less than 128 bits in length
+ and known only to this end.
+
+ On receipt of a packet for an S_OPEN session, after processing all
+ chunks in the packet: if the session is still in the S_OPEN state,
+ AND the source address of the packet does not match DESTADDR, AND
+ MOB_TX_TS is at least one second in the past, then:
+
+ 1. Set MOB_TX_TS to the current time;
+
+ 2. Construct a Ping message comprising the following: a marking to
+ indicate (to this end when returned in a Ping Reply) that it is a
+ mobility check (for example, the first byte being ASCII 'M' for
+ "Mobility"), a timestamp set to MOB_TX_TS, and a cryptographic
+ hash over the following: the preceding items, the address from
+ which the packet was received, and MOB_SECRET; and
+
+ 3. Send this Ping to the address from which the packet was received,
+ instead of DESTADDR.
+
+ On receipt of a Ping Reply in an S_OPEN session, if the Ping Reply's
+ message satisfies all of these conditions:
+
+ o it has this end's expected marking to indicate that it is a
+ mobility check, and
+
+ o the timestamp in the message is not more than 120 seconds in the
+ past, and
+
+ o the timestamp in the message is greater than MOB_RX_TS, and
+
+ o the cryptographic hash matches the expected value according to the
+ contents of the message plus the source address of the packet
+ containing this Ping Reply and MOB_SECRET,
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 73]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ then:
+
+ 1. Set MOB_RX_TS to the timestamp in the message; and
+
+ 2. Set DESTADDR to the source address of the packet containing this
+ Ping Reply.
+
+3.5.4.3. Path MTU Discovery
+
+ "Packetization Layer Path MTU Discovery" [RFC4821] describes a method
+ for measuring the path MTU between communicating endpoints.
+
+ An RTMFP SHOULD perform path MTU discovery.
+
+ The method described in RFC 4821 can be adapted for use in RTMFP by
+ sending a probe packet comprising one of the Padding chunk types
+ (type 0x00 or 0xff) and a Ping. The Ping chunk SHOULD come after the
+ Padding chunk, to guard against a false positive response in case the
+ probe packet is truncated.
+
+3.5.5. Close
+
+ An endpoint may close a session at any time. Typically, an endpoint
+ will close a session when there have been no open flows in either
+ direction for a time. In another circumstance, an endpoint may be
+ ceasing operation and will close all of its sessions even if they
+ have open flows.
+
+ To close an S_OPEN session in a reliable and orderly fashion, an
+ endpoint moves the session to the S_NEARCLOSE state.
+
+ On a session transitioning from S_OPEN to S_NEARCLOSE and every
+ 5 seconds thereafter while still in the S_NEARCLOSE state, send a
+ Session Close Request chunk (Section 2.3.17).
+
+ A session that has been in the S_NEARCLOSE state for at least
+ 90 seconds (allowing time to retransmit the Session Close Request
+ multiple times) SHOULD move to the S_CLOSED state.
+
+ On a session transitioning from S_OPEN to the S_NEARCLOSE,
+ S_FARCLOSE_LINGER or S_CLOSED state, immediately abort and terminate
+ all open or closing flows. Flows only exist in S_OPEN sessions.
+
+ To close an S_OPEN session abruptly, send a Session Close
+ Acknowledgement chunk (Section 2.3.18), then move to the S_CLOSED
+ state.
+
+
+
+
+
+Thornburgh Informational [Page 74]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ On receipt of a Session Close Request chunk for a session in the
+ S_OPEN, S_NEARCLOSE, or S_FARCLOSE_LINGER states, send a Session
+ Close Acknowledgement chunk; then, if the session is in the S_OPEN
+ state, move to the S_FARCLOSE_LINGER state.
+
+ A session that has been in the S_FARCLOSE_LINGER state for at least
+ 19 seconds (allowing time to answer 3 retransmissions of a Session
+ Close Request) SHOULD move to the S_CLOSED state.
+
+ On receipt of a Session Close Acknowledgement chunk for a session in
+ the S_OPEN, S_NEARCLOSE, or S_FARCLOSE_LINGER states, move to the
+ S_CLOSED state.
+
+3.6. Flows
+
+ A flow is a unidirectional communication channel in a session for
+ transporting a correlated series of user messages from a sender to a
+ receiver. Each end of a session may have zero or more sending flows
+ to the other end. Each sending flow at one end has a corresponding
+ receiving flow at the other end.
+
+3.6.1. Overview
+
+3.6.1.1. Identity
+
+ Flows are multiplexed in a session by a flow identifier. Each end of
+ a session chooses its sending flow identifiers independently of the
+ other end. The choice of similar flow identifiers by both ends does
+ not imply an association. A sender MAY choose any identifier for any
+ flow; therefore, a flow receiver MUST NOT ascribe any semantic
+ meaning, role, or name to a flow based only on its identifier. There
+ are no "well known" or reserved flow identifiers.
+
+ Bidirectional flow association is indicated at flow startup with the
+ Return Flow Association option (Section 2.3.11.1.2). An endpoint can
+ indicate that a new sending flow is in return (or response) to a
+ receiving flow from the other end. A sending flow MUST NOT indicate
+ more than one return association. A receiving flow can be specified
+ as the return association for any number of sending flows. The
+ return flow association, if any, is fixed for the lifetime of the
+ sending flow. Note: Closure of one flow in an association does not
+ automatically close other flows in the association, except as
+ specified in Section 3.6.3.1.
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 75]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ Flows are named with arbitrary user metadata. This specification
+ doesn't mandate any particular encoding, syntax, or semantics for the
+ user metadata, except for the encoded size (Section 2.3.11.1.1); the
+ user metadata is entirely reserved for the application. The user
+ metadata is fixed for the lifetime of the flow.
+
+3.6.1.2. Messages and Sequencing
+
+ Flows provide message-oriented framing. Large messages are
+ fragmented for transport in the network. Receivers reassemble
+ fragmented messages and only present complete messages to the user.
+
+ A sender queues messages on a sending flow one after another. A
+ receiver can recover the original queuing order of the messages, even
+ when they are reordered in transit by the network or as a result of
+ loss and retransmission, by means of the messages' fragment sequence
+ numbers. Flows are the basic units of message sequencing; each flow
+ is sequenced independently of all other flows; inter-flow message
+ arrival and delivery sequencing are not guaranteed.
+
+ Independent flow sequencing allows a sender to prioritize the
+ transmission or retransmission of the messages of one flow over those
+ of other flows in a session, allocating capacity from the
+ transmission budget according to priority. RTMFP is designed for
+ flows to be the basic unit of prioritization. In any flow, fragment
+ sequence numbers are unique and monotonically increasing; that is,
+ the fragment sequence numbers for any message MUST be greater than
+ the fragment sequence numbers of all messages previously queued in
+ that flow. Receipt of fragments out of sequence number order within
+ a flow creates discontiguous gaps at the receiver, causing it to send
+ an acknowledgement for every packet and also causing the size of the
+ encoded acknowledgements to grow. Therefore, for any flow, the
+ sender SHOULD send lower sequence numbers first.
+
+ A sender can abandon a queued message at any time, even if some
+ fragments of that message have been received by the other end. A
+ receiver MUST be able to detect a gap in the flow when a message is
+ abandoned; therefore, each message SHOULD take at least one sequence
+ number from the sequence space even if no fragments for that message
+ are ever sent. The sender will transmit the fragments of all
+ messages not abandoned, and retransmit any lost fragments of all
+ messages not abandoned, until all the fragments of all messages not
+ abandoned are acknowledged by the receiver. A sender indicates a
+ Forward Sequence Number (FSN) to instruct the receiver that sequence
+ numbers less than or equal to the FSN will not be transmitted or
+ retransmitted. This allows the receiver to move forward over gaps
+ and continue sequenced delivery of completely received messages to
+ the user. Any incomplete messages missing fragments with sequence
+
+
+
+Thornburgh Informational [Page 76]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ numbers less than or equal to the FSN were abandoned by the sender
+ and will never be completed. A gap indication MUST be communicated
+ to the receiving user.
+
+3.6.1.3. Lifetime
+
+ A sender begins a flow by sending user message fragments to the other
+ end, and including the user metadata and, if any, the return flow
+ association. The sender continues to include the user metadata and
+ return flow association until the flow is acknowledged by the far
+ end, at which point the sender knows that the receiver has received
+ the user metadata and, if any, the return flow association. After
+ that point, the flow identifier alone is sufficient.
+
+ Flow receivers SHOULD acknowledge all sequence numbers received for
+ any flow, whether the flow is accepted or rejected. Flow receivers
+ MUST NOT acknowledge sequence numbers higher than the FSN that were
+ not received. Acknowledgements drive the congestion control and
+ avoidance algorithms and therefore must be accurate.
+
+ An endpoint can reject a receiving flow at any time in the flow's
+ lifetime. To reject the flow, the receiving endpoint sends a Flow
+ Exception Report chunk (Section 2.3.16) immediately preceding every
+ acknowledgement chunk for the rejected receiving flow.
+
+ An endpoint may eventually conclude and close a sending flow. The
+ last sequence number of the flow is marked with the Final flag. The
+ sending flow is complete when all sequence numbers of the flow,
+ including the final sequence number, have been cumulatively
+ acknowledged by the receiver. The receiving flow is complete when
+ every sequence number from the FSN to the final sequence number has
+ been received. The sending flow and corresponding receiving flow at
+ the respective ends hold the flow identifier of a completed flow in
+ reserve for a time to allow delayed or duplicated fragments and
+ acknowledgements to drain from the network without erroneously
+ initiating a new receiving flow or erroneously acknowledging a new
+ sending flow.
+
+ If a flow sender receives a Flow Exception indication from the other
+ end, the flow sender SHOULD close the flow and abandon all of the
+ undelivered queued messages. The flow sender SHOULD indicate an
+ exception to the user.
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 77]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+3.6.2. Sender
+
+ Each sending flow comprises the flow-specific information context
+ necessary to transfer that flow's messages to the other end. Each
+ sending flow context includes at least:
+
+ o F_FLOW_ID: this flow's identifier;
+
+ o STARTUP_OPTIONS: the set of options to send to the receiver until
+ this flow is acknowledged, including the User's Per-Flow Metadata
+ and, if set, the Return Flow Association;
+
+ o SEND_QUEUE: the unacknowledged message fragments queued in this
+ flow, initially empty; each message fragment entry comprising the
+ following:
+
+ * SEQUENCE_NUMBER: the sequence number of this fragment;
+
+ * DATA: this fragment's user data;
+
+ * FRA: the fragment control value for this message fragment,
+ having one of the values enumerated for that purpose in
+ Section 2.3.11 ("User Data Chunk");
+
+ * ABANDONED: a boolean flag indicating whether this fragment has
+ been abandoned;
+
+ * SENT_ABANDONED: a boolean flag indicating whether this fragment
+ was abandoned when sent;
+
+ * EVER_SENT: a boolean flag indicating whether this fragment has
+ been sent at least once, initially false;
+
+ * NAK_COUNT: a count of the number of negative acknowledgements
+ detected for this fragment, initially 0;
+
+ * IN_FLIGHT: a boolean flag indicating whether this fragment is
+ currently outstanding, or in flight, in the network, initially
+ false;
+
+ * TRANSMIT_SIZE: the size, in bytes, of the encoded User Data
+ chunk (including the chunk header) for this fragment when it
+ was transmitted into the network.
+
+ o F_OUTSTANDING_BYTES: the sum of the TRANSMIT_SIZE of each entry in
+ SEND_QUEUE where entry.IN_FLIGHT is true;
+
+
+
+
+
+Thornburgh Informational [Page 78]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ o RX_BUFFER_SIZE: the most recent available buffer advertisement
+ from the other end (Sections 2.3.13 and 2.3.14), initially
+ 65536 bytes;
+
+ o NEXT_SN: the next sequence number to assign to a message fragment,
+ initially 1;
+
+ o F_FINAL_SN: the sequence number assigned to the final message
+ fragment of the flow, initially having no value;
+
+ o EXCEPTION: a boolean flag indicating whether an exception has been
+ reported by the receiver, initially false;
+
+ o The state, at any time being one of the following values: the open
+ state F_OPEN; the closing states F_CLOSING and F_COMPLETE_LINGER;
+ and the closed state F_CLOSED.
+
+ Note: The following diagram is only a summary of state transitions
+ and their causing events, and is not a complete operational
+ specification.
+
+ +--------+
+ | F_OPEN |
+ +--------+
+ |CLOSE or
+ |rcv Flow Exception
+ |
+ v
+ +---------+
+ |F_CLOSING|
+ +---------+
+ |rcv Data Ack
+ | 0..F_FINAL_SN
+ v
+ +-----------------+
+ |F_COMPLETE_LINGER|
+ +-----------------+
+ | 130 seconds
+ v
+ +--------+
+ |F_CLOSED|
+ +--------+
+
+ Figure 19: Sending Flow State Diagram
+
+
+
+
+
+
+
+Thornburgh Informational [Page 79]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+3.6.2.1. Startup
+
+ The application opens a new sending flow to the other end in an
+ S_OPEN session. The implementation chooses a new flow ID that is not
+ assigned to any other sending flow in that session in the F_OPEN,
+ F_CLOSING, or F_COMPLETE_LINGER states. The flow starts in the
+ F_OPEN state. The STARTUP_OPTIONS for the new flow is set with the
+ User's Per-Flow Metadata (Section 2.3.11.1.1). If this flow is in
+ return (or response) to a receiving flow from the other end, that
+ flow's ID is encoded in a Return Flow Association
+ (Section 2.3.11.1.2) option and added to STARTUP_OPTIONS. A new
+ sending flow SHOULD NOT be opened in response to a receiving flow
+ from the other end that is not in the RF_OPEN state when the sending
+ flow is opened.
+
+ At this point, the flow exists in the sender but not in the receiver.
+ The flow begins when user data fragments are transmitted to the
+ receiver. A sender can begin a flow in the absence of immediate user
+ data by sending a Forward Sequence Number Update (Section 3.6.2.7.1),
+ by queuing and transmitting a user data fragment that is already
+ abandoned.
+
+3.6.2.2. Queuing Data
+
+ The application queues messages in an F_OPEN sending flow for
+ transmission to the far end. The implementation divides each message
+ into one or more fragments for transmission in User Data chunks
+ (Section 2.3.11). Each fragment MUST be small enough so that, if
+ assembled into a packet (Section 2.2.4) with a maximum-size common
+ header, User Data chunk header, and, if not empty, this flow's
+ STARTUP_OPTIONS, the packet will not exceed the path MTU
+ (Section 3.5.4.3).
+
+ For each fragment, create a fragment entry and set
+ fragmentEntry.SEQUENCE_NUMBER to flow.NEXT_SN, and increment
+ flow.NEXT_SN by one. Set fragmentEntry.FRA according to the encoding
+ in User Data chunks:
+
+ 0: This fragment is a complete message.
+
+ 1: This fragment is the first of a multi-fragment message.
+
+ 2: This fragment is the last of a multi-fragment message.
+
+ 3: This fragment is in the middle of a multi-fragment message.
+
+ Append fragmentEntry to flow.SEND_QUEUE.
+
+
+
+
+Thornburgh Informational [Page 80]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+3.6.2.3. Sending Data
+
+ A sending flow is ready to transmit if the SEND_QUEUE contains at
+ least one entry that is eligible to send, and if either
+ RX_BUFFER_SIZE is greater than F_OUTSTANDING_BYTES or EXCEPTION is
+ set to true.
+
+ A SEND_QUEUE entry is eligible to send if it is not IN_FLIGHT, AND at
+ least one of the following conditions holds:
+
+ o The entry is not ABANDONED; or
+
+ o The entry is the first one in the SEND_QUEUE; or
+
+ o The entry's SEQUENCE_NUMBER is equal to flow.F_FINAL_SN.
+
+ If the session's transmission budget allows, a flow that is ready to
+ transmit is selected for transmission according to the
+ implementation's prioritization scheme. The manner of flow
+ prioritization is not mandated by this specification.
+
+ Trim abandoned messages from the front of the queue, and find the
+ Forward Sequence Number (FSN):
+
+ 1. While the SEND_QUEUE contains at least two entries, AND the first
+ entry is not IN_FLIGHT, AND the first entry is ABANDONED, remove
+ and discard the first entry from the SEND_QUEUE;
+
+ 2. If the first entry in the SEND_QUEUE is not abandoned, set FSN to
+ entry.SEQUENCE_NUMBER - 1; otherwise,
+
+ 3. If the first entry in the SEND_QUEUE is IN_FLIGHT, AND
+ entry.SENT_ABANDONED is false, set FSN to
+ entry.SEQUENCE_NUMBER - 1; otherwise,
+
+ 4. The first entry in the SEND_QUEUE is abandoned and either is not
+ IN_FLIGHT or was already abandoned when sent; set FSN to
+ entry.SEQUENCE_NUMBER.
+
+ The FSN MUST NOT be greater than any sequence number currently
+ outstanding. The FSN MUST NOT be equal to any sequence number
+ currently outstanding that was not abandoned when sent.
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 81]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ Assemble user data chunks for this flow into a packet to send to the
+ receiver. While enough space remains in the packet and the flow is
+ ready to transmit:
+
+ 1. Starting at the head of the SEND_QUEUE, find the first eligible
+ fragment entry;
+
+ 2. Encode the entry into a User Data chunk (Section 2.3.11) or, if
+ possible (Section 3.6.2.3.2), a Next User Data chunk
+ (Section 2.3.12);
+
+ 3. If present, set chunk.flowID to flow.F_FLOW_ID;
+
+ 4. If present, set chunk.sequenceNumber to entry.SEQUENCE_NUMBER;
+
+ 5. If present, set chunk.fsnOffset to entry.SEQUENCE_NUMBER - FSN;
+
+ 6. Set chunk.fragmentControl to entry.FRA;
+
+ 7. Set chunk.abandon to entry.ABANDONED;
+
+ 8. If entry.SEQUENCE_NUMBER equals flow.F_FINAL_SN, set chunk.final
+ to true; else set chunk.final to false;
+
+ 9. If any options are being sent with this chunk, set
+ chunk.optionsPresent to true, assemble the options into the
+ chunk, and assemble a Marker to terminate the option list;
+
+ 10. If entry.ABANDONED is true, set chunk.userData to empty;
+ otherwise, set chunk.userData to entry.DATA;
+
+ 11. If adding the assembled chunk to the packet would cause the
+ packet to exceed the path MTU, do not assemble this chunk into
+ the packet; enough space no longer remains in the packet; stop.
+ Otherwise, continue:
+
+ 12. Set entry.IN_FLIGHT to true;
+
+ 13. Set entry.EVER_SENT to true;
+
+ 14. Set entry.NAK_COUNT to 0;
+
+ 15. Set entry.SENT_ABANDONED to entry.ABANDONED;
+
+ 16. Set entry.TRANSMIT_SIZE to the size of the assembled chunk,
+ including the chunk header;
+
+
+
+
+
+Thornburgh Informational [Page 82]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ 17. Assemble this chunk into the packet; and
+
+ 18. If this flow or entry is considered Time Critical (real-time),
+ set the timeCritical flag in the packet header (Section 2.2.4).
+
+ Complete any other appropriate packet processing, and transmit the
+ packet to the far end.
+
+3.6.2.3.1. Startup Options
+
+ If STARTUP_OPTIONS is not empty, then when assembling the FIRST User
+ Data chunk for this flow into a packet, add the encoded
+ STARTUP_OPTIONS to that chunk's option list.
+
+3.6.2.3.2. Send Next Data
+
+ The Next User Data chunk (Section 2.3.12) is a compact encoding for a
+ user message fragment when multiple contiguous fragments are
+ assembled into one packet. Using this chunk where possible can
+ conserve space in a packet, potentially reducing transmission
+ overhead or allowing additional information to be sent in a packet.
+
+ If, after assembling a user message fragment of a flow into a packet
+ (Section 3.6.2.3), the next eligible fragment to be selected for
+ assembly into that packet belongs to the same flow, AND its sequence
+ number is one greater than that of the fragment just assembled, it is
+ RECOMMENDED that an implementation encode a Next User Data chunk
+ instead of a User Data chunk.
+
+ The FIRST fragment of a flow assembled into a packet MUST be encoded
+ as a User Data chunk.
+
+3.6.2.4. Processing Acknowledgements
+
+ A Data Acknowledgement Bitmap chunk (Section 2.3.13) or a Data
+ Acknowledgement Ranges chunk (Section 2.3.14) encodes the
+ acknowledgement of receipt of one or more sequence numbers of a flow,
+ as well as the receiver's current receive window advertisement.
+
+ On receipt of an acknowledgement chunk for a sending flow:
+
+ 1. Set PRE_ACK_OUTSTANDING_BYTES to flow.F_OUTSTANDING_BYTES;
+
+ 2. Set flow.STARTUP_OPTIONS to empty;
+
+ 3. Set flow.RX_BUFFER_SIZE to chunk.bufferBytesAvailable;
+
+
+
+
+
+Thornburgh Informational [Page 83]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ 4. For each sequence number encoded in the acknowledgement, if
+ there is an entry in flow.SEND_QUEUE with that sequence number
+ and its IN_FLIGHT is true, then remove the entry from
+ flow.SEND_QUEUE; and
+
+ 5. Notify the congestion control and avoidance algorithms that
+ PRE_ACK_OUTSTANDING_BYTES - flow.F_OUTSTANDING_BYTES were
+ acknowledged. Note that negative acknowledgements
+ (Section 3.6.2.5) affect "TCP friendly" congestion control.
+
+3.6.2.5. Negative Acknowledgement and Loss
+
+ A negative acknowledgement is inferred for an outstanding fragment if
+ an acknowledgement is received for any other fragments sent after it
+ in the same session.
+
+ An implementation SHOULD consider a fragment to be lost once that
+ fragment receives three negative acknowledgements. A lost fragment
+ is no longer outstanding in the network.
+
+ The following describes an OPTIONAL method for detecting negative
+ acknowledgements.
+
+ Let the session track the order in which fragments are transmitted
+ across all its sending flows by way of a monotonically increasing
+ Transmission Sequence Number (TSN) recorded with each fragment queue
+ entry each time that fragment is transmitted.
+
+ Let the session information context contain additional variables:
+
+ o NEXT_TSN: the next TSN to record with a fragment's queue entry
+ when it is transmitted, initially 1;
+
+ o MAX_TSN_ACK: the highest acknowledged TSN, initially 0.
+
+ Let each fragment queue entry contain an additional variable TSN,
+ initially 0, to track its transmission order.
+
+ On transmission of a message fragment into the network, set its
+ entry.TSN to session.NEXT_TSN, and increment session.NEXT_TSN.
+
+ On acknowledgement of an outstanding fragment, if its entry.TSN is
+ greater than session.MAX_TSN_ACK, set session.MAX_TSN_ACK to
+ entry.TSN.
+
+ After processing all acknowledgements in a packet containing at least
+ one acknowledgement, then for each sending flow in that session, for
+ each entry in that flow's SEND_QUEUE, if entry.IN_FLIGHT is true and
+
+
+
+Thornburgh Informational [Page 84]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ entry.TSN is less than session.MAX_TSN_ACK, increment entry.NAK_COUNT
+ and notify the congestion control and avoidance algorithms that a
+ negative acknowledgement was detected in this packet.
+
+ For each sending flow in that session, for each entry in that flow's
+ SEND_QUEUE, if entry.IN_FLIGHT is true and entry.NAK_COUNT is at
+ least 3, that fragment was lost in the network and is no longer
+ considered to be in flight. Set entry.IN_FLIGHT to false. Notify
+ the congestion control and avoidance algorithms of the loss.
+
+3.6.2.6. Timeout
+
+ A fragment is considered lost and no longer in flight in the network
+ if it has remained outstanding for at least ERTO.
+
+ The following describes an OPTIONAL method to manage transmission
+ timeouts. This method REQUIRES that either burst avoidance
+ (Section 3.5.2.3) is implemented or the implementation's congestion
+ control and avoidance algorithms will eventually stop sending new
+ fragments into the network if acknowledgements are persistently not
+ received.
+
+ Let the session information context contain an alarm TIMEOUT_ALARM,
+ initially unset.
+
+ On sending a packet containing at least one User Data chunk, set or
+ reset TIMEOUT_ALARM to fire in ERTO.
+
+ On receiving a packet containing at least one acknowledgement, reset
+ TIMEOUT_ALARM (if already set) to fire in ERTO.
+
+ When TIMEOUT_ALARM fires:
+
+ 1. Set WAS_LOSS = false;
+
+ 2. For each sending flow in the session, and for each entry in that
+ flow's SEND_QUEUE:
+
+ 1. If entry.IN_FLIGHT is true, set WAS_LOSS = true; and
+
+ 2. Set entry.IN_FLIGHT to false.
+
+ 3. If WAS_LOSS is true, perform ERTO backoff (Section 3.5.2.2); and
+
+ 4. Notify the congestion control and avoidance algorithms of the
+ timeout and, if WAS_LOSS is true, that there was loss.
+
+
+
+
+
+Thornburgh Informational [Page 85]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+3.6.2.7. Abandoning Data
+
+ The application can abandon queued messages at any time and for any
+ reason. Example reasons include (but are not limited to) the
+ following: one or more fragments of a message have remained in the
+ SEND_QUEUE for longer than a specified message lifetime; a fragment
+ has been retransmitted more than a specified retransmission limit; a
+ prior message on which this message depends (such as a key frame in a
+ prediction chain) was abandoned and not delivered.
+
+ To abandon a message fragment, set its SEND_QUEUE entry's ABANDON
+ flag to true. When abandoning a message fragment, abandon all
+ fragments of the message to which it belongs.
+
+ An abandoned fragment MUST NOT be un-abandoned.
+
+3.6.2.7.1. Forward Sequence Number Update
+
+ Abandoned data may leave gaps in the sequence number space of a flow.
+ Gaps may cause the receiver to hold completely received messages for
+ ordered delivery to allow for retransmission of the missing
+ fragments. User Data chunks (Section 2.3.11) encode a Forward
+ Sequence Number (FSN) to instruct the receiver that fragments with
+ sequence numbers less than or equal to the FSN will not be
+ transmitted or retransmitted.
+
+ When the receiver has gaps in the received sequence number space and
+ no non-abandoned message fragments remain in the SEND_QUEUE, the
+ sender SHOULD transmit a Forward Sequence Number Update (FSN Update)
+ comprising a User Data chunk marked abandoned, whose sequence number
+ is the FSN and whose fsnOffset is 0. An FSN Update allows the
+ receiver to skip gaps that will not be repaired and deliver received
+ messages to the user. An FSN Update may be thought of as a
+ transmission or retransmission of abandoned sequence numbers without
+ actually sending the data.
+
+ The method described in Section 3.6.2.3 ("Sending Data") generates
+ FSN Updates when appropriate.
+
+
+
+
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 86]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+3.6.2.8. Examples
+
+ Sender
+ | :
+ 1 |<--- Ack ID=2, seq:0-16
+ 2 |---> Data ID=2, seq#=25, fsnOff=9 (fsn=16)
+ 3 |---> Data ID=2, seq#=26, fsnOff=10 (fsn=16)
+ 4 |<--- Ack ID=2, seq:0-18
+ 5 |---> Data ID=2, seq#=27, fsnOff=9 (fsn=18)
+ 6 |---> Data ID=2, seq#=28, fsnOff=10 (fsn=18)
+ | :
+
+ There are 9 sequence numbers in flight with delayed acknowledgements.
+
+ Figure 20: Normal Flow with No Loss
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 87]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ Sender
+ | :
+ 1 |<--- Ack ID=3, seq:0-30
+ 2 |---> Data ID=3, seq#=45, fsnOff=15 (fsn=30)
+ 3 |<--- Ack ID=3, seq:0-30, 32 (nack 31:1)
+ 4 |---> Data ID=3, seq#=46, fsnOff=16 (fsn=30)
+ 5 |<--- Ack ID=3, seq:0-30, 32, 34 (nack 31:2, 33:1)
+ 6 |<--- Ack ID=3, seq:0-30, 32, 34-35 (nack 31:3=lost, 33:2)
+ 7 |---> Data ID=3, seq#=47, fsnOff=15 (fsn=32, abandon 31)
+ 8 |<--- Ack ID=3, seq:0-30, 32, 34-36 (nack 33:3=lost)
+ 9 |---> Data ID=3, seq#=33, fsnOff=1 (fsn=32, retransmit 33)
+ 10 |<--- Ack ID=3, seq:0-30, 32, 34-37
+ 11 |---> Data ID=3, seq#=48, fsnOff=16 (fsn=32)
+ | :
+ | (continues through seq#=59)
+ | :
+ 12 |---> Data ID=3, seq#=60, fsnOff=28(fsn=32)
+ 13 |<--- Ack ID=3, seq:0-30, 34-46
+ 14 |---> Data ID=3, seq#=61, fsnOff=29 (fsn=32)
+ 15 |<--- Ack ID=3, seq:0-32, 34-47
+ 16 |---> Data ID=3, seq#=62, fsnOff=30 (fsn=32)
+ 17 |<--- Ack ID=3, seq:0-47
+ 18 |---> Data ID=3, seq#=63, fsnOff=16 (fsn=47)
+ 19 |<--- Ack ID=3, seq:0-49
+ 20 |---> Data ID=3, seq#=64, fsnOff=15 (fsn=49)
+ | :
+ 21 |<--- Ack ID=3, seq:0-59
+ 22 |<--- Ack ID=3, seq:0-59, 61 (nack 60:1)
+ 23 |<--- Ack ID=3, seq:0-59, 61-62 (nack 60:2)
+ 24 |<--- Ack ID=3, seq:0-59, 61-63 (nack 60:3=lost)
+ 25 |---> Data ID=3, ABN=1, seq#=60, fsnOff=0 (fsn=60, abandon 60)
+ 26 |<--- Ack ID=3, seq:0-59, 61-64
+ | :
+ 27 |<--- Ack ID=3, seq:0-64
+
+ Flow with sequence numbers 31, 33, and 60 lost in transit, and a
+ pause at 64. 33 is retransmitted; 31 and 60 are abandoned. Note
+ that line 25 is a Forward Sequence Number Update (Section 3.6.2.7.1).
+
+ Figure 21: Flow with Loss
+
+
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 88]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+3.6.2.9. Flow Control
+
+ The flow receiver advertises the amount of new data it's willing to
+ accept from the flow sender with the bufferBytesAvailable derived
+ field of an acknowledgement (Sections 2.3.13 and 2.3.14).
+
+ The flow sender MUST NOT send new data into the network if
+ flow.F_OUTSTANDING_BYTES is greater than or equal to the most
+ recently received buffer advertisement, unless flow.EXCEPTION is true
+ (Section 3.6.2.3).
+
+3.6.2.9.1. Buffer Probe
+
+ The flow sender is suspended if the most recently received buffer
+ advertisement is zero and the flow hasn't been rejected by the
+ receiver -- that is, while RX_BUFFER_SIZE is zero AND EXCEPTION is
+ false. To guard against potentially lost acknowledgements that might
+ reopen the receive window, a suspended flow sender SHOULD send a
+ packet comprising a Buffer Probe chunk (Section 2.3.15) for this flow
+ from time to time.
+
+ If the receive window advertisement transitions from non-zero to
+ zero, the flow sender MAY send a Buffer Probe immediately and SHOULD
+ send a probe within one second.
+
+ The initial period between Buffer Probes SHOULD be at least
+ one second or ERTO, whichever is greater. The period between probes
+ SHOULD increase over time, but the period between probes SHOULD NOT
+ be more than one minute or ERTO, whichever is greater.
+
+ The flow sender SHOULD stop sending Buffer Probes if it is no longer
+ suspended.
+
+3.6.2.10. Exception
+
+ The flow receiver can reject the flow at any time and for any reason.
+ The flow receiver sends a Flow Exception Report (Section 2.3.16) when
+ it has rejected a flow.
+
+ On receiving a Flow Exception Report for a sending flow:
+
+ 1. If the flow is F_OPEN, close the flow (Section 3.6.2.11) and
+ notify the user that the far end reported an exception with the
+ encoded exception code;
+
+ 2. Set the EXCEPTION flag to true; and
+
+ 3. For each entry in SEND_QUEUE, set entry.ABANDONED = true.
+
+
+
+Thornburgh Informational [Page 89]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+3.6.2.11. Close
+
+ A sending flow is closed by the user or as a result of an exception.
+ To close an F_OPEN flow:
+
+ 1. Move to the F_CLOSING state;
+
+ 2. If the SEND_QUEUE is not empty, AND the tail entry of the
+ SEND_QUEUE has a sequence number of NEXT_SN - 1, AND the
+ tail entry.EVER_SENT is false, set F_FINAL_SN to
+ entry.SEQUENCE_NUMBER; else
+
+ 3. The SEND_QUEUE is empty, OR the tail entry does not have a
+ sequence number of NEXT_SN - 1, OR the tail entry.EVER_SENT is
+ true: enqueue a new SEND_QUEUE entry with entry.SEQUENCE_NUMBER =
+ flow.NEXT_SN, entry.FRA = 0, and entry.ABANDONED = true, and set
+ flow.F_FINAL_SN to entry.SEQUENCE_NUMBER.
+
+ An F_CLOSING sending flow is complete when its SEND_QUEUE transitions
+ to empty, indicating that all sequence numbers, including the
+ FINAL_SN, have been acknowledged by the other end.
+
+ When an F_CLOSING sending flow becomes complete, move to the
+ F_COMPLETE_LINGER state.
+
+ A sending flow MUST remain in the F_COMPLETE_LINGER state for at
+ least 130 seconds. After at least 130 seconds, move to the F_CLOSED
+ state. The sending flow is now closed, its resources can be
+ reclaimed, and its F_FLOW_ID MAY be used for a new sending flow.
+
+3.6.3. Receiver
+
+ Each receiving flow comprises the flow-specific information context
+ necessary to receive that flow's messages from the sending end and
+ deliver completed messages to the user. Each receiving flow context
+ includes at least:
+
+ o RF_FLOW_ID: this flow's identifier;
+
+ o SEQUENCE_SET: the set of all fragment sequence numbers seen in
+ this receiving flow, whether received or abandoned, initially
+ empty;
+
+ o RF_FINAL_SN: the final fragment sequence number of the flow,
+ initially having no value;
+
+
+
+
+
+
+Thornburgh Informational [Page 90]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ o RECV_BUFFER: the message fragments waiting to be delivered to the
+ user, sorted by sequence number in ascending order, initially
+ empty; each message fragment entry comprising the following:
+
+ * SEQUENCE_NUMBER: the sequence number of this fragment;
+
+ * DATA: this fragment's user data; and
+
+ * FRA: the fragment control value for this message fragment,
+ having one of the values enumerated for that purpose in
+ Section 2.3.11 ("User Data Chunk").
+
+ o BUFFERED_SIZE: the sum of the lengths of each fragment in
+ RECV_BUFFER plus any additional storage overhead for the fragments
+ incurred by the implementation, in bytes;
+
+ o BUFFER_CAPACITY: the desired maximum size for the receive buffer,
+ in bytes;
+
+ o PREV_RWND: the most recent receive window advertisement sent in an
+ acknowledgement, in 1024-byte blocks, initially having no value;
+
+ o SHOULD_ACK: whether or not an acknowledgement should be sent for
+ this flow, initially false;
+
+ o EXCEPTION_CODE: the exception code to report to the sender when
+ the flow has been rejected, initially 0;
+
+ o The state, at any time being one of the following values: the open
+ state RF_OPEN; the closing states RF_REJECTED and
+ RF_COMPLETE_LINGER; and the closed state RF_CLOSED.
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 91]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ Note: The following diagram is only a summary of state transitions
+ and their causing events, and is not a complete operational
+ specification.
+
+ +-+
+ |X|
+ +-+
+ |rcv User Data for
+ | no existing flow
+ v
+ +---------+
+ | RF_OPEN |
+ +---------+
+ rcv all sequence numbers| |user reject,
+ 0..RF_FINAL_SN | |rcv bad option,
+ | |no metadata at open,
+ | |association specified
+ | | but not F_OPEN at open
+ +---+ |
+ | v
+ | +-----------+
+ | |RF_REJECTED|
+ | +-----------+
+ | |rcv all sequence numbers
+ | | 0..RF_FINAL_SN
+ v v
+ +------------------+
+ |RF_COMPLETE_LINGER|
+ +------------------+
+ | 120 seconds
+ v
+ +---------+
+ |RF_CLOSED|
+ +---------+
+
+ Figure 22: Receiving Flow State Diagram
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 92]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+3.6.3.1. Startup
+
+ A new receiving flow starts on receipt of a User Data chunk
+ (Section 2.3.11) encoding a flow ID not belonging to any other
+ receiving flow in the same session in the RF_OPEN, RF_REJECTED, or
+ RF_COMPLETE_LINGER states.
+
+ On receipt of such a User Data chunk:
+
+ 1. Set temporary variables METADATA, ASSOCIATED_FLOWID, and
+ ASSOCIATION to each have no value;
+
+ 2. Create a new receiving flow context in this session, setting its
+ RF_FLOW_ID to the flow ID encoded in the opening User Data
+ chunk, and set to the RF_OPEN state;
+
+ 3. If the opening User Data chunk encodes a User's Per-Flow
+ Metadata option (Section 2.3.11.1.1), set METADATA to
+ option.userMetadata;
+
+ 4. If the opening User Data chunk encodes a Return Flow Association
+ option (Section 2.3.11.1.2), set ASSOCIATED_FLOWID to
+ option.flowID;
+
+ 5. If METADATA has no value, the receiver MUST reject the flow
+ (Section 3.6.3.7), moving it to the RF_REJECTED state;
+
+ 6. If ASSOCIATED_FLOWID has a value, then if there is no sending
+ flow in the same session with a flow ID of ASSOCIATED_FLOWID,
+ the receiver MUST reject the flow, moving it to the RF_REJECTED
+ state; otherwise, set ASSOCIATION to the indicated sending flow;
+
+ 7. If ASSOCIATION indicates a sending flow, AND that sending flow's
+ state is not F_OPEN, the receiver MUST reject this receiving
+ flow, moving it to the RF_REJECTED state;
+
+ 8. If the opening User Data chunk encodes any unrecognized option
+ with a type code less than 8192 (Section 2.3.11.1), the receiver
+ MUST reject the flow, moving it to the RF_REJECTED state;
+
+ 9. If this new receiving flow is still RF_OPEN, then notify the
+ user that a new receiving flow has opened, including the
+ METADATA and, if present, the ASSOCIATION, and set
+ flow.BUFFER_CAPACITY according to the user;
+
+
+
+
+
+
+
+Thornburgh Informational [Page 93]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ 10. Perform the normal data processing (Section 3.6.3.2) for the
+ opening User Data chunk; and
+
+ 11. Set this session's ACK_NOW to true.
+
+3.6.3.2. Receiving Data
+
+ A User Data chunk (Section 2.3.11) or a Next User Data chunk
+ (Section 2.3.12) encodes one fragment of a user data message of a
+ flow, as well as the flow's Forward Sequence Number and potentially
+ optional parameters (Section 2.3.11.1).
+
+ On receipt of a User Data or Next User Data chunk:
+
+ 1. If chunk.flowID doesn't indicate an existing receiving flow in
+ the same session in the RF_OPEN, RF_REJECTED, or
+ RF_COMPLETE_LINGER state, perform the steps of Section 3.6.3.1
+ ("Startup") to start a new receiving flow;
+
+ 2. Retrieve the receiving flow context for the flow indicated by
+ chunk.flowID;
+
+ 3. Set flow.SHOULD_ACK to true;
+
+ 4. If the flow is RF_OPEN, AND the chunk encodes any unrecognized
+ option with a type code less than 8192 (Section 2.3.11.1), the
+ flow MUST be rejected: notify the user of an exception, and
+ reject the flow (Section 3.6.3.7), moving it to the RF_REJECTED
+ state;
+
+ 5. If the flow is not in the RF_OPEN state, set session.ACK_NOW
+ to true;
+
+ 6. If flow.PREV_RWND has a value and that value is less than
+ 2 blocks, set session.ACK_NOW to true;
+
+ 7. If chunk.abandon is true, set session.ACK_NOW to true;
+
+ 8. If flow.SEQUENCE_SET has any gaps (that is, if it doesn't
+ contain every sequence number from 0 through and including the
+ highest sequence number in the set), set session.ACK_NOW
+ to true;
+
+ 9. If flow.SEQUENCE_SET contains chunk.sequenceNumber, then this
+ chunk is a duplicate: set session.ACK_NOW to true;
+
+
+
+
+
+
+Thornburgh Informational [Page 94]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ 10. If flow.SEQUENCE_SET doesn't contain chunk.sequenceNumber, AND
+ chunk.final is true, AND flow.RF_FINAL_SN has no value, then set
+ flow.RF_FINAL_SN to chunk.sequenceNumber, and set
+ session.ACK_NOW to true;
+
+ 11. If the flow is in the RF_OPEN state, AND flow.SEQUENCE_SET
+ doesn't contain chunk.sequenceNumber, AND chunk.abandon is
+ false, then create a new RECV_BUFFER entry for this chunk's data
+ and set entry.SEQUENCE_NUMBER to chunk.sequenceNumber,
+ entry.DATA to chunk.userData, and entry.FRA to
+ chunk.fragmentControl, and insert this new entry into
+ flow.RECV_BUFFER;
+
+ 12. Add to flow.SEQUENCE_SET the range of sequence numbers from 0
+ through and including the chunk.forwardSequenceNumber derived
+ field;
+
+ 13. Add chunk.sequenceNumber to flow.SEQUENCE_SET;
+
+ 14. If flow.SEQUENCE_SET now has any gaps, set session.ACK_NOW
+ to true;
+
+ 15. If session.ACK_NOW is false and session.DELACK_ALARM is not set,
+ set session.DELACK_ALARM to fire in 200 milliseconds; and
+
+ 16. Attempt delivery of completed messages in this flow's
+ RECV_BUFFER to the user (Section 3.6.3.3).
+
+ After processing all chunks in a packet containing at least one User
+ Data chunk, increment session.RX_DATA_PACKETS by one. If
+ session.RX_DATA_PACKETS is at least two, set session.ACK_NOW to true.
+
+ A receiving flow that is not in the RF_CLOSED state is ready to send
+ an acknowledgement if its SHOULD_ACK flag is set. Acknowledgements
+ for receiving flows that are ready are sent either opportunistically
+ by piggybacking on a packet that's already sending user data or an
+ acknowledgement (Section 3.6.3.4.6), or when the session's ACK_NOW
+ flag is set (Section 3.6.3.4.5).
+
+3.6.3.3. Buffering and Delivering Data
+
+ A receiving flow's information context contains a RECV_BUFFER for
+ reordering, reassembling, and holding the user data messages of the
+ flow. Only complete messages are delivered to the user; an
+ implementation MUST NOT deliver partially received messages, except
+ by special arrangement with the user.
+
+
+
+
+
+Thornburgh Informational [Page 95]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ Let the Cumulative Acknowledgement Sequence Number (CSN) be the
+ highest number in the contiguous range of numbers in SEQUENCE_SET
+ starting with 0. For example, if SEQUENCE_SET contains {0, 1, 2, 3,
+ 5, 6}, the contiguous range starting with 0 is 0..3, so the CSN is 3.
+
+ A message is complete if all of its fragments are present in the
+ RECV_BUFFER. The fragments of one message have contiguous sequence
+ numbers. A message can be either a single fragment, whose fragment
+ control value is 0-whole, or two or more fragments where the first's
+ fragment control value is 1-begin, followed by zero or more fragments
+ with control value 3-middle, and terminated by a last fragment with
+ control value 2-end.
+
+ An incomplete message segment is a contiguous sequence of one or more
+ fragments that do not form a complete message -- that is, a 1-begin
+ followed by zero or more 3-middle fragments but with no 2-end, or
+ zero or more 3-middle fragments followed by a 2-end but with no
+ 1-begin, or one or more 3-middle fragments with neither a 1-begin nor
+ a 2-end.
+
+ Incomplete message segments can either be in progress or abandoned.
+ An incomplete segment is abandoned in the following cases:
+
+ o The sequence number of the segment's first fragment is less than
+ or equal to the CSN, AND that fragment's control value is not
+ 1-begin; or
+
+ o The sequence number of the segment's last fragment is less than
+ the CSN.
+
+ Abandoned message segments will never be completed, so they SHOULD be
+ removed from the RECV_BUFFER to make room in the advertised receive
+ window and the receiver's memory for messages that can be completed.
+
+ The user can suspend delivery of a flow's messages. A suspended
+ receiving flow holds completed messages in its RECV_BUFFER until the
+ user resumes delivery. A suspended flow can cause the receive window
+ advertisement to go to zero even when the BUFFER_CAPACITY is
+ non-zero; this is described in detail in Section 3.6.3.5
+ ("Flow Control").
+
+ When the receiving flow is not suspended, the original queuing order
+ of the messages is recovered by delivering, in ascending sequence
+ number order, complete messages in the RECV_BUFFER whose sequence
+ numbers are less than or equal to the CSN.
+
+
+
+
+
+
+Thornburgh Informational [Page 96]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ The following describes a method for discarding abandoned message
+ segments and delivering complete messages in original queuing order
+ when the receiving flow is not suspended.
+
+ While the first fragment entry in the RECV_BUFFER has a sequence
+ number less than or equal to the CSN and delivery is still possible:
+
+ 1. If entry.FRA is 0-whole, deliver entry.DATA to the user, and
+ remove this entry from RECV_BUFFER; otherwise,
+
+ 2. If entry.FRA is 2-end or 3-middle, this entry belongs to an
+ abandoned segment, so remove and discard this entry from
+ RECV_BUFFER; otherwise,
+
+ 3. Entry.FRA is 1-begin. Let LAST_ENTRY be the last RECV_BUFFER
+ entry that is part of this message segment (LAST_ENTRY can be
+ entry if the segment has only one fragment so far). Then:
+
+ 1. If LAST_ENTRY.FRA is 2-end, this segment is a complete
+ message, so concatenate the DATA fields of each fragment
+ entry of this segment in ascending sequence number order and
+ deliver the complete message to the user, then remove the
+ entries for this complete message from RECV_BUFFER;
+ otherwise,
+
+ 2. If LAST_ENTRY.SEQUENCE_NUMBER is less than CSN, this segment
+ is incomplete and abandoned, so remove and discard the
+ entries for this segment from RECV_BUFFER; otherwise,
+
+ 3. LAST_ENTRY.SEQUENCE_NUMBER is equal to CSN and LAST_ENTRY.FRA
+ is not 2-end: this segment is incomplete but still in
+ progress. Ordered delivery is no longer possible until at
+ least one more fragment is received. Stop.
+
+ If flow.RF_FINAL_SN has a value and is equal to the CSN, AND
+ RECV_BUFFER is empty, all complete messages have been delivered to
+ the user, so notify the user that the flow is complete.
+
+3.6.3.4. Acknowledging Data
+
+ A flow receiver SHOULD acknowledge all user data fragment sequence
+ numbers seen in that flow. Acknowledgements drive the sender's
+ congestion control and avoidance algorithms, clear data from the
+ sender's buffers, and in some sender implementations clock new data
+ into the network; therefore, the acknowledgements must be accurate
+ and timely.
+
+
+
+
+
+Thornburgh Informational [Page 97]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+3.6.3.4.1. Timing
+
+ For reasons similar to those discussed in Section 4.2.3.2 of RFC 1122
+ [RFC1122], it is advantageous to delay sending acknowledgements for a
+ short time, so that multiple data fragments can be acknowledged in a
+ single transmission. However, it is also advantageous for a sender
+ to receive timely notification about the receiver's disposition of
+ the flow, particularly in unusual or exceptional circumstances, so
+ that the circumstances can be addressed if possible.
+
+ Therefore, a flow receiver SHOULD send an acknowledgement for a flow
+ as soon as is practical in any of the following circumstances:
+
+ o On receipt of a User Data chunk that starts a new flow;
+
+ o On receipt of a User Data or Next User Data chunk if the flow is
+ not in the RF_OPEN state;
+
+ o On receipt of a User Data chunk where, before processing the
+ chunk, the SEQUENCE_SET of the indicated flow does not contain
+ every sequence number between 0 and the highest sequence number in
+ the set (that is, if there was a sequence number gap before
+ processing the chunk);
+
+ o On receipt of a User Data chunk where, after processing the chunk,
+ the flow's SEQUENCE_SET does not contain every sequence number
+ between 0 and the highest sequence number in the set (that is, if
+ this chunk causes a sequence number gap);
+
+ o On receipt of a Buffer Probe for the flow;
+
+ o On receipt of a User Data chunk if the last acknowledgement sent
+ for the flow indicated fewer than two bufferBlocksAvailable;
+
+ o On receipt of a User Data or Next User Data chunk for the flow if,
+ after processing the chunk, the flow's BUFFER_CAPACITY is not at
+ least 1024 bytes greater than BUFFERED_SIZE;
+
+ o On receipt of a User Data or Next User Data chunk for any sequence
+ number that was already seen (that is, on receipt of a duplicate);
+
+ o On the first receipt of the final sequence number of the flow;
+
+ o On receipt of two packets in the session that contain user data
+ for any flows since an acknowledgement was last sent, the new
+ acknowledgements being for the flows having any User Data chunks
+ in the received packets (that is, for every second packet
+ containing user data);
+
+
+
+Thornburgh Informational [Page 98]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ o After receipt of a User Data chunk for the flow, if an
+ acknowledgement for any other flow is being sent (that is,
+ consolidate acknowledgements);
+
+ o After receipt of a User Data chunk for the flow, if any user data
+ for a sending flow is being sent in a packet and if there is space
+ available in the same packet (that is, attempt to piggyback an
+ acknowledgement with user data if possible);
+
+ o No longer than 200 milliseconds after receipt of a User Data chunk
+ for the flow.
+
+3.6.3.4.2. Size and Truncation
+
+ Including an encoded acknowledgement in a packet might cause the
+ packet to exceed the path MTU. In that case:
+
+ o If the packet is being sent primarily to send an acknowledgement,
+ AND this is the first acknowledgement in the packet, truncate the
+ acknowledgement so that the packet does not exceed the path MTU;
+ otherwise,
+
+ o The acknowledgement is being piggybacked in a packet with user
+ data or with an acknowledgement for another flow: do not include
+ this acknowledgement in the packet, and send it later.
+
+3.6.3.4.3. Constructing
+
+ The Data Acknowledgement Bitmap chunk (Section 2.3.13) and Data
+ Acknowledgement Ranges chunk (Section 2.3.14) encode a receiving
+ flow's SEQUENCE_SET and its receive window advertisement. The two
+ chunks are semantically equivalent; implementations SHOULD send
+ whichever provides the most compact encoding of the SEQUENCE_SET.
+
+ When assembling an acknowledgement for a receiving flow:
+
+ 1. If the flow's state is RF_REJECTED, first assemble a Flow
+ Exception Report chunk (Section 2.3.16) for flow.flowID;
+
+ 2. Choose the acknowledgement chunk type that most compactly encodes
+ flow.SEQUENCE_SET;
+
+ 3. Use the method described in Section 3.6.3.5 ("Flow Control") to
+ determine the value for the acknowledgement chunk's
+ bufferBlocksAvailable field.
+
+
+
+
+
+
+Thornburgh Informational [Page 99]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+3.6.3.4.4. Delayed Acknowledgement
+
+ As discussed in Section 3.6.3.4.1 ("Timing"), a flow receiver can
+ delay sending an acknowledgement for up to 200 milliseconds after
+ receiving user data. The method described in Section 3.6.3.2
+ ("Receiving Data") sets the session's DELACK_ALARM.
+
+ When DELACK_ALARM fires, set ACK_NOW to true.
+
+3.6.3.4.5. Obligatory Acknowledgement
+
+ One or more acknowledgements should be sent as soon as is practical
+ when the session's ACK_NOW flag is set. While the ACK_NOW flag
+ is set:
+
+ 1. Choose a receiving flow that is ready to send an acknowledgement;
+
+ 2. If there is no such flow, there is no work to do, set ACK_NOW to
+ false, set RX_DATA_PACKETS to 0, clear the DELACK_ALARM, and
+ stop; otherwise,
+
+ 3. Start a new packet;
+
+ 4. Assemble an acknowledgement for the flow and include it in the
+ packet, truncating it if necessary so that the packet doesn't
+ exceed the path MTU;
+
+ 5. Set flow.SHOULD_ACK to false;
+
+ 6. Set flow.PREV_RWND to the bufferBlocksAvailable field of the
+ included acknowledgement chunk;
+
+ 7. Attempt to piggyback acknowledgements for any other flows that
+ are ready to send an acknowledgement into the packet, as
+ described below; and
+
+ 8. Send the packet.
+
+3.6.3.4.6. Opportunistic Acknowledgement
+
+ When sending a packet with user data or an acknowledgement, any other
+ receiving flows that are ready to send an acknowledgement should
+ include their acknowledgements in the packet if possible.
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 100]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ To piggyback acknowledgements in a packet that is already being sent,
+ where the packet contains user data or an acknowledgement, while
+ there is at least one receiving flow that is ready to send an
+ acknowledgement:
+
+ 1. Assemble an acknowledgement for the flow;
+
+ 2. If the acknowledgement cannot be included in the packet without
+ exceeding the path MTU, the packet is full; stop. Otherwise,
+
+ 3. Include the acknowledgement in the packet;
+
+ 4. Set flow.SHOULD_ACK to false;
+
+ 5. Set flow.PREV_RWND to the bufferBlocksAvailable field of the
+ included acknowledgement chunk; and
+
+ 6. If there are no longer any receiving flows in the session that
+ are ready to send an acknowledgement, set session.ACK_NOW to
+ false, set session.RX_DATA_PACKETS to 0, and clear
+ session.DELACK_ALARM.
+
+3.6.3.4.7. Example
+
+ Figure 23 shows an example flow with sequence numbers 31 and 33 lost
+ in transit; 31 is abandoned, and 33 is retransmitted.
+
+ Receiver
+ 1 |<--- Data ID=3, seq#=29, fsnOff=11 (fsn=18)
+ 2 |<--- Data ID=3, seq#=30, fsnOff=12 (fsn=18)
+ 3 |---> Ack ID=3, seq:0-30
+ 4 |<--- Data ID=3, seq#=32, fsnOff=12 (fsn=20)
+ 5 |---> Ack ID=3, seq:0-30, 32
+ 6 |<--- Data ID=3, seq#=34, fsnOff=12 (fsn=22)
+ 7 |---> Ack ID=3, seq:0-30, 32, 34
+ | :
+ 8 |<--- Data ID=3, seq#=46, fsnOff=16 (fsn=30)
+ 9 |---> Ack ID=3, seq:0-30, 32, 34-46
+ 10 |<--- Data ID=3, seq#=47, fsnOff=15 (fsn=32)
+ 11 |---> Ack ID=3, seq:0-32, 34-47
+ 12 |<--- Data ID=3, seq#=33, fsnOff=1 (fsn=32)
+ 13 |---> Ack ID=3, seq#=0-47
+ 14 |<--- Data ID=3, seq#=48, fsnOff=16 (fsn=32)
+ 15 |<--- Data ID=3, seq#=49, fsnOff=17 (fsn=32)
+ 16 |---> Ack ID=3, seq#=0-49
+ | :
+
+ Figure 23: Flow Example with Loss
+
+
+
+Thornburgh Informational [Page 101]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+3.6.3.5. Flow Control
+
+ The flow receiver maintains a buffer for reassembling and reordering
+ messages for delivery to the user (Section 3.6.3.3). The
+ implementation and the user may wish to limit the amount of resources
+ (including buffer memory) that a flow is allowed to use.
+
+ RTMFP provides a means for each receiving flow to govern the amount
+ of data sent by the sender, by way of the bufferBytesAvailable
+ derived field of acknowledgement chunks (Sections 2.3.13 and 2.3.14).
+ This derived field indicates the amount of data that the sender is
+ allowed to have outstanding in the network, until instructed
+ otherwise. This amount is also called the receive window.
+
+ The flow receiver can suspend the sender by advertising a closed
+ (zero length) receive window.
+
+ The user can suspend delivery of messages from the receiving flow
+ (Section 3.6.3.3). This can cause the receive buffer to fill.
+
+ In order for progress to be made on completing a fragmented message
+ or repairing a gap for sequenced delivery in a flow, the flow
+ receiver MUST advertise at least one buffer block in an
+ acknowledgement if it is not suspended, even if the amount of data in
+ the buffer exceeds the buffer capacity, unless the buffer capacity is
+ 0. Otherwise, deadlock can occur, as the receive buffer will stay
+ full and won't drain because of a gap or incomplete message, and the
+ gap or incomplete message can't be repaired or completed because the
+ sender is suspended.
+
+ The receive window is advertised in units of 1024-byte blocks. For
+ example, advertisements for 1 byte, 1023 bytes, and 1024 bytes each
+ require one block. An advertisement for 1025 bytes requires
+ two blocks.
+
+ The following describes the RECOMMENDED method of calculating the
+ bufferBlocksAvailable field of an acknowledgement chunk for a
+ receiving flow:
+
+ 1. If BUFFERED_SIZE is greater than or equal to BUFFER_CAPACITY, set
+ ADVERTISE_BYTES to 0;
+
+ 2. If BUFFERED_SIZE is less than BUFFER_CAPACITY, set
+ ADVERTISE_BYTES to BUFFER_CAPACITY - BUFFERED_SIZE;
+
+ 3. Set ADVERTISE_BLOCKS to CEIL(ADVERTISE_BYTES / 1024);
+
+
+
+
+
+Thornburgh Informational [Page 102]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ 4. If ADVERTISE_BLOCKS is 0, AND BUFFER_CAPACITY is greater than 0,
+ AND delivery to the user is not suspended, set ADVERTISE_BLOCKS
+ to 1; and
+
+ 5. Set the acknowledgement's bufferBlocksAvailable field to
+ ADVERTISE_BLOCKS.
+
+3.6.3.6. Receiving a Buffer Probe
+
+ A Buffer Probe chunk (Section 2.3.15) is sent by the flow sender
+ (Section 3.6.2.9.1) to request the current receive window
+ advertisement (in the form of an acknowledgement) from the flow
+ receiver.
+
+ On receipt of a Buffer Probe chunk:
+
+ 1. If chunk.flowID doesn't belong to a receiving flow in the same
+ session in the RF_OPEN, RF_REJECTED, or RF_COMPLETE_LINGER state,
+ ignore this Buffer Probe; otherwise,
+
+ 2. Retrieve the receiving flow context for the flow indicated by
+ chunk.flowID; then
+
+ 3. Set flow.SHOULD_ACK to true; and
+
+ 4. Set session.ACK_NOW to true.
+
+3.6.3.7. Rejecting a Flow
+
+ A receiver can reject an RF_OPEN flow at any time and for any reason.
+ To reject a receiving flow in the RF_OPEN state:
+
+ 1. Move to the RF_REJECTED state;
+
+ 2. Discard all entries in flow.RECV_BUFFER, as they are no longer
+ relevant;
+
+ 3. If the user rejected the flow, set flow.EXCEPTION_CODE to the
+ exception code indicated by the user; otherwise, the flow was
+ rejected automatically by the implementation, so the exception
+ code is 0;
+
+ 4. Set flow.SHOULD_ACK to true; and
+
+ 5. Set session.ACK_NOW to true.
+
+
+
+
+
+
+Thornburgh Informational [Page 103]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ The receiver indicates that it has rejected a flow by sending a Flow
+ Exception Report chunk (Section 2.3.16) with every acknowledgement
+ (Section 3.6.3.4.3) for a flow in the RF_REJECTED state.
+
+3.6.3.8. Close
+
+ A receiving flow is complete when every sequence number from 0
+ through and including the final sequence number has been received --
+ that is, when flow.RF_FINAL_SN has a value and flow.SEQUENCE_SET
+ contains every sequence number from 0 through flow.RF_FINAL_SN,
+ inclusive.
+
+ When an RF_OPEN or RF_REJECTED receiving flow becomes complete, move
+ to the RF_COMPLETE_LINGER state, set flow.SHOULD_ACK to true, and set
+ session.ACK_NOW to true.
+
+ A receiving flow SHOULD remain in the RF_COMPLETE_LINGER state for
+ 120 seconds. After 120 seconds, move to the RF_CLOSED state. The
+ receiving flow is now closed, and its resources can be reclaimed once
+ all complete messages in flow.RECV_BUFFER have been delivered to the
+ user (Section 3.6.3.3). The same flow ID might be used for a new
+ flow by the sender after this point.
+
+ Discussion: The flow sender detects that the flow is complete on
+ receiving an acknowledgement of all fragment sequence numbers of the
+ flow. This can't happen until after the receiver has detected that
+ the flow is complete and acknowledged all of the sequence numbers.
+ The receiver's RF_COMPLETE_LINGER period is two minutes (one Maximum
+ Segment Lifetime (MSL)); this period allows any in-flight packets to
+ drain from the network without being misidentified and gives the
+ sender an opportunity to retransmit any sequence numbers if the
+ completing acknowledgement is lost. The sender's F_COMPLETE_LINGER
+ period is at least two minutes plus 10 seconds and doesn't begin
+ until the completing acknowledgement is received; therefore, the same
+ flow identifier won't be reused by the flow sender for a new sending
+ flow for at least 10 seconds after the flow receiver has closed the
+ receiving flow context. This ensures correct operation independent
+ of network delay, even when the sender's clock runs up to 8 percent
+ faster than the receiver's.
+
+4. IANA Considerations
+
+ This memo specifies chunk type code values (Section 2.3) and User
+ Data option type code values (Section 2.3.11.1). These type code
+ values are assigned and maintained by Adobe. Therefore, this memo
+ has no IANA actions.
+
+
+
+
+
+Thornburgh Informational [Page 104]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+5. Security Considerations
+
+ This memo specifies a general framework that can be used to establish
+ a confidential and authenticated session between endpoints. A
+ Cryptography Profile, not specified herein, defines the cryptographic
+ algorithms, data formats, and semantics as used within this
+ framework. Designing a Cryptography Profile to ensure that
+ communications are protected to the degree required by the
+ application-specific threat model is outside the scope of this
+ specification.
+
+ A block cipher in CBC mode is RECOMMENDED for packet encryption
+ (Section 2.2.3). An attacker can predict the values of some fields
+ from one plain RTMFP packet to the next or predict that some fields
+ may be the same from one packet to the next. This SHOULD be
+ considered in choosing and implementing a packet encryption cipher
+ and mode.
+
+ The well-known Default Session Key of a Cryptography Profile serves
+ multiple purposes, including the scrambling of session startup
+ packets to protect interior fields from undesirable modification by
+ middleboxes such as NATs, increasing the effort required for casual
+ passive observation of startup packets, and allowing different
+ applications of RTMFP using different Default Session Keys to
+ (intentionally or not) share network transport addresses without
+ interference. The Default Session Key, being well known, MUST NOT be
+ construed to contribute to the security of session startup; session
+ startup is essentially in the clear.
+
+ Section 3.5.4.2 describes an OPTIONAL method for processing a change
+ of network address of a communicating peer. Securely processing
+ address mobility using that method, or any substantially similar
+ method, REQUIRES at least that the packet encryption function of the
+ Cryptography Profile (Section 2.2.3) employs a cryptographic
+ verification mechanism comprising secret information known only to
+ the two endpoints. Without this constraint, that method, or any
+ substantially similar method, becomes "session hijacking support".
+
+ Flows and packet fragmentation imply semantics that could cause
+ unbounded resource utilization in receivers, causing a denial of
+ service. Implementations SHOULD guard against unbounded or excessive
+ resource use and abort sessions that appear abusive.
+
+ A rogue but popular Redirector (Section 3.5.1.4) could direct session
+ initiators to flood a victim address or network with Initiator Hello
+ packets, potentially causing a denial of service.
+
+
+
+
+
+Thornburgh Informational [Page 105]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ An attacker that can passively observe an IHello and that possesses a
+ certificate matching the Endpoint Discriminator (without having to
+ know the private key, if any, associated with it) can deny the
+ initiator access to the desired responder by sending an RHello before
+ the desired responder does, since only the first received RHello is
+ selected by the initiator. The attacker needn't forge the desired
+ responder's source address, since the RHello is selected based on the
+ tag echo and not the packet's source address. This can simplify the
+ attack in some network or host configurations.
+
+ An attacker that can passively observe and record the packets of an
+ established session can use traffic analysis techniques to infer the
+ start and completion of flows without decrypting the packets. The
+ User Data fragments of flows have unique sequence numbers, so flows
+ are immune to replay while they are open. However, once a flow has
+ completed and the linger period has concluded, the attacker could
+ replay the recorded packets, opening a new flow in the receiver and
+ duplicating the flow's data; this replay might have undesirable
+ effects on the receiver's application. The attacker could also infer
+ that a new flow has begun reusing the recorded flow's identifier and
+ replay the final sequence number or any of the other fragments in the
+ flow, potentially denying or interfering with legitimate traffic to
+ the receiver. Therefore, the data integrity aspect of packet
+ encryption SHOULD comprise anti-replay measures.
+
+6. Acknowledgements
+
+ Special thanks go to Matthew Kaufman for his contributions to the
+ creation and design of RTMFP.
+
+ Thanks to Jari Arkko, Ben Campbell, Wesley Eddy, Stephen Farrell,
+ Philipp Hancke, Bela Lubkin, Hilarie Orman, Richard Scheffenegger,
+ and Martin Stiemerling for their detailed reviews of this memo.
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 106]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+7. References
+
+7.1. Normative References
+
+ [CBC] Dworkin, M., "Recommendation for Block Cipher Modes of
+ Operation", NIST Special Publication 800-38A,
+ December 2001, <http://csrc.nist.gov/publications/
+ nistpubs/800-38a/sp800-38a.pdf>.
+
+ [RFC0768] Postel, J., "User Datagram Protocol", STD 6, RFC 768,
+ August 1980.
+
+ [RFC0791] Postel, J., "Internet Protocol", STD 5, RFC 791,
+ September 1981.
+
+ [RFC1122] Braden, R., "Requirements for Internet Hosts -
+ Communication Layers", STD 3, RFC 1122, October 1989.
+
+ [RFC2119] Bradner, S., "Key words for use in RFCs to Indicate
+ Requirement Levels", BCP 14, RFC 2119, March 1997.
+
+ [RFC2460] Deering, S. and R. Hinden, "Internet Protocol, Version 6
+ (IPv6) Specification", RFC 2460, December 1998.
+
+ [RFC2914] Floyd, S., "Congestion Control Principles", BCP 41,
+ RFC 2914, September 2000.
+
+ [RFC4821] Mathis, M. and J. Heffner, "Packetization Layer Path MTU
+ Discovery", RFC 4821, March 2007.
+
+ [RFC5681] Allman, M., Paxson, V., and E. Blanton, "TCP Congestion
+ Control", RFC 5681, September 2009.
+
+7.2. Informative References
+
+ [RFC5389] Rosenberg, J., Mahy, R., Matthews, P., and D. Wing,
+ "Session Traversal Utilities for NAT (STUN)", RFC 5389,
+ October 2008.
+
+ [ScalableTCP]
+ Kelly, T., "Scalable TCP: Improving Performance in
+ Highspeed Wide Area Networks", December 2002,
+ <http://datatag.web.cern.ch/datatag/papers/
+ pfldnet2003-ctk.pdf>.
+
+
+
+
+
+
+
+Thornburgh Informational [Page 107]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+Appendix A. Example Congestion Control Algorithm
+
+ As mandated in Section 3.5.2, an RTMFP is required to use TCP-
+ compatible congestion control, but flexibility in exact
+ implementation is allowed, within certain limits. This section
+ describes an experimental window-based congestion control algorithm
+ that is appropriate for real-time and bulk data transport in RTMFP.
+ The algorithm includes slow start and congestion avoidance phases,
+ including modified increase and decrease parameters. These
+ parameters are further adjusted according to whether real-time data
+ is being sent and whether Time Critical Reverse Notifications are
+ received.
+
+A.1. Discussion
+
+ RFC 5681 defines the standard window-based congestion control
+ algorithms for TCP. These algorithms are appropriate for delay-
+ insensitive bulk data transport but have undesirable behaviors for
+ delay- and loss-sensitive applications. Among the undesirable
+ behaviors are the cutting of the congestion window in half during a
+ loss event, and the rapidity of the slow start algorithm's
+ exponential growth. Cutting the congestion window in half requires a
+ large channel headroom to support a real-time application and can
+ cause a large amount of jitter from sender-side buffering. Doubling
+ the congestion window during the slow start phase can lead to the
+ congestion window temporarily growing to twice the size it should be,
+ causing a period of excessive loss in the path.
+
+ We found that a number of deployed TCP implementations use the method
+ of equation (3) from Section 3.1 of RFC 5681; this method, when
+ combined with the recommended behavior of acknowledging every other
+ packet, causes the congestion window to grow at approximately half
+ the rate that the recommended method specifies. In order to compete
+ fairly with these deployed TCPs, we choose 768 bytes per round trip
+ as the increment during the normal congestion avoidance phase; this
+ is approximately half of the typical maximum segment size of
+ 1500 bytes and is also easily subdivided.
+
+ The sender may be sending real-time data to the far end. When
+ sending real-time data, a smoother response to congestion is desired
+ while still competing with reasonable fairness to other flows in the
+ Internet. In order to scale the sending rate quickly, the slow start
+ algorithm is desired, but slow start's normal rate of increase can
+ cause excessive loss in the last round trip. Accordingly, slow
+ start's exponential increase rate is adjusted to double approximately
+ every 3 round trips instead of every round trip. The multiplicative
+ decrease cuts the congestion window by one eighth on loss to maintain
+ a smoother sending rate. The additive increase is done at half the
+
+
+
+Thornburgh Informational [Page 108]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ normal rate (incrementing at 384 bytes per round trip), to both
+ compensate for the less aggressive loss response and probe the path
+ capacity more gently.
+
+ The far end may report that it is receiving real-time data from other
+ peers, or the sender may be sending real-time data to other far ends.
+ In these circumstances (if not sending real-time data to this far
+ end), it is desirable to respond differently than the standard TCP
+ algorithms specify, to both yield capacity to the real-time flows and
+ avoid excessive losses while probing the path capacity. Slow start's
+ exponential increase is disabled, and the additive increase is done
+ at half the normal rate (incrementing at 384 bytes per round trip).
+ Multiplicative decrease is left at the normal rate (cutting by half)
+ to yield to other flows.
+
+ Since real-time messages may be small, and sent regularly, it is
+ advantageous to spread congestion window increases out across the
+ round-trip time instead of doing them all at once. We divide the
+ round trip into 16 segments with an additive increase of a useful
+ size (48 bytes) per segment.
+
+ Scalable TCP [ScalableTCP] describes experimental methods of
+ modifying the additive increase and multiplicative decrease of the
+ congestion window in large delay-bandwidth scenarios. The congestion
+ window is increased by 1% each round trip and decreased by one eighth
+ on loss in the congestion avoidance phase in certain circumstances
+ (specifically, when a 1% increase is larger than the normal additive-
+ increase amount). Those methods are adapted here. The scalable
+ increase amount is 48 bytes for every 4800 bytes acknowledged, to
+ spread the increase out over the round trip. The congestion window
+ is decreased by one eighth on loss when it is at least 67200 bytes
+ per round trip, which is seven eighths of 76800 (the point at which
+ 1% is greater than 768 bytes per round trip). When sending real-time
+ data to the far end, the scalable increase is 1% or 384 bytes per
+ round trip, whichever is greater. Otherwise, when notified that the
+ far end is receiving real-time data from other peers, the scaled
+ increase is adjusted to 0.5% or 384 bytes per round trip, whichever
+ is greater.
+
+
+
+
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 109]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+A.2. Algorithm
+
+ Let SMSS denote the Sender Maximum Segment Size [RFC5681], for
+ example 1460 bytes. Let CWND_INIT denote the Initial Congestion
+ Window (IW) according to Section 3.1 of RFC 5681, for example
+ 4380 bytes. Let CWND_TIMEDOUT denote the congestion window after a
+ timeout indicating lost data, being 1*SMSS (for example, 1460 bytes).
+
+ Let the session information context contain additional variables:
+
+ o CWND: the congestion window, initialized to CWND_INIT;
+
+ o SSTHRESH: the slow start threshold, initialized to positive
+ infinity;
+
+ o ACKED_BYTES_ACCUMULATOR: a count of acknowledged bytes,
+ initialized to 0;
+
+ o ACKED_BYTES_THIS_PACKET: a count of acknowledged bytes observed in
+ the current packet;
+
+ o PRE_ACK_OUTSTANDING: the number of bytes outstanding in the
+ network before processing any acknowledgements in the current
+ packet;
+
+ o ANY_LOSS: an indication of whether any loss has been detected in
+ the current packet;
+
+ o ANY_NAKS: an indication of whether any negative acknowledgements
+ have been detected in the current packet;
+
+ o ANY_ACKS: an indication of whether any acknowledgement chunks have
+ been received in the current packet.
+
+ Let FASTGROW_ALLOWED indicate whether the congestion window is
+ allowed to grow at the normal rate versus a slower rate, being false
+ if a Time Critical Reverse Notification has been received on this
+ session within the last 800 milliseconds (Sections 2.2.4 and 3.5.2.1)
+ or if a Time Critical Forward Notification has been sent on ANY
+ session in the last 800 milliseconds, and otherwise being true.
+
+ Let TC_SENT indicate whether a Time Critical Forward Notification has
+ been sent on this session within the last 800 milliseconds.
+
+ Implement the method described in Section 3.6.2.6 to manage
+ transmission timeouts, including setting the TIMEOUT_ALARM.
+
+
+
+
+
+Thornburgh Informational [Page 110]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ On being notified that the TIMEOUT_ALARM has fired, perform the
+ function shown in Figure 24:
+
+ on TimeoutNotification(WAS_LOSS):
+ set SSTHRESH to MAX(SSTHRESH, CWND * 3/4).
+ set ACKED_BYTES_ACCUMULATOR to 0.
+ if WAS_LOSS is true:
+ set CWND to CWND_TIMEDOUT.
+ else:
+ set CWND to CWND_INIT.
+
+ Figure 24: Pseudocode for Handling a Timeout Notification
+
+ Before processing each received packet in this session:
+
+ 1. Set ANY_LOSS to false;
+
+ 2. Set ANY_NAKS to false;
+
+ 3. Set ACKED_BYTES_THIS_PACKET to 0; and
+
+ 4. Set PRE_ACK_OUTSTANDING to S_OUTSTANDING_BYTES.
+
+ On notification of loss (Section 3.6.2.5), set ANY_LOSS to true.
+
+ On notification of negative acknowledgement (Section 3.6.2.5), set
+ ANY_NAKS to true.
+
+ On notification of acknowledgement of data (Section 3.6.2.4), set
+ ANY_ACKS to true, and add the count of acknowledged bytes to
+ ACKED_BYTES_THIS_PACKET.
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 111]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+ After processing all chunks in each received packet for this session,
+ perform the function shown in Figure 25:
+
+ if ANY_LOSS is true:
+ if (TC_SENT is true) OR (PRE_ACK_OUTSTANDING > 67200 AND \
+ FASTGROW_ALLOWED is true):
+ set SSTHRESH to MAX(PRE_ACK_OUTSTANDING * 7/8, CWND_INIT).
+ else:
+ set SSTHRESH to MAX(PRE_ACK_OUTSTANDING * 1/2, CWND_INIT).
+ set CWND to SSTHRESH.
+ set ACKED_BYTES_ACCUMULATOR to 0.
+ else if (ANY_ACKS is true) AND (ANY_NAKS is false) AND \
+ (PRE_ACK_OUTSTANDING >= CWND):
+ set var INCREASE to 0.
+ var AITHRESH.
+ if FASTGROW_ALLOWED is true:
+ if CWND < SSTHRESH:
+ set INCREASE to ACKED_BYTES_THIS_PACKET.
+ else:
+ add ACKED_BYTES_THIS_PACKET to ACKED_BYTES_ACCUMULATOR.
+ set AITHRESH to MIN(MAX(CWND / 16, 64), 4800).
+ while ACKED_BYTES_ACCUMULATOR >= AITHRESH:
+ subtract AITHRESH from ACKED_BYTES_ACCUMULATOR.
+ add 48 to INCREASE.
+ else FASTGROW_ALLOWED is false:
+ if CWND < SSTHRESH AND TC_SENT is true:
+ set INCREASE to CEIL(ACKED_BYTES_THIS_PACKET / 4).
+ else:
+ var AITHRESH_CAP.
+ if TC_SENT is true:
+ set AITHRESH_CAP to 2400.
+ else:
+ set AITHRESH_CAP to 4800.
+ add ACKED_BYTES_THIS_PACKET to ACKED_BYTES_ACCUMULATOR.
+ set AITHRESH to MIN(MAX(CWND / 16, 64), AITHRESH_CAP).
+ while ACKED_BYTES_ACCUMULATOR >= AITHRESH:
+ subtract AITHRESH from ACKED_BYTES_ACCUMULATOR.
+ add 24 to INCREASE.
+ set CWND to MAX(CWND + MIN(INCREASE, SMSS), CWND_INIT).
+
+ Figure 25: Pseudocode for Congestion Window Adjustment
+ after Processing a Packet
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 112]
+
+RFC 7016 Adobe RTMFP November 2013
+
+
+Author's Address
+
+ Michael C. Thornburgh
+ Adobe Systems Incorporated
+ 345 Park Avenue
+ San Jose, CA 95110-2704
+ US
+
+ Phone: +1 408 536 6000
+ EMail: mthornbu@adobe.com
+ URI: http://www.adobe.com/
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+Thornburgh Informational [Page 113]
+