Rate Control Packets

 
CU-SeeMe Development Group                                                     
Document Draft:  003
Protocol Feature Designer: Tim Dorcey, td11@cornell.edu
Document Author: Richard Kennerly, rbk1@cornell.edu
Revised: August 24, 1995

Protocol Specification - Rate Control and Rate Reply Packets
                
Status:
-------
Implemented in Mac CU-SeeMe 0.83b1
Implemented in Windows CU-SeeMe 0.71t1


Abstract:
---------

   With the RateReportData feature, the reflector is able to determine
the rate at which a client is able to receive data.  PacketLoss reports
indicate the loss on the whole path between our local workstation and
a remote client.  It would be useful to know the packet loss characteristics
on our local link as well.
   Rate Control Packets include the total number of bytes sent since the
connection started.  Rate Reply Packets include this number and the total
number of packets received since the connection started.  The reflector
can learn, by looking at RateReply Packets, what fraction of bytes are
being lost on the local link and adjust its send cap accordingly.  Rate
Control Packets can be sent by either the reflector or client independently
to achieve the same goals.


Implementation:
---------------

   Periodically, the reflector sends a RateControlPacket to the client.
The client is expected to immediately return a RateReplyPacket.


Definitions:
------------

#define kOldRateControlType     108
#define kOldRateReplyType       109
#define kRateControlType        110
#define kRateReplyType          111


Packet Format:
--------------

   The format of the RateControlData structure is:
   
#typedef struct {
   unsigned short       curSendCap;
   unsigned long        totalBytesSent;
   unsigned long        timeSent;
} RateControlData;


   The format of the RateControl Packet is:

#typedef struct {
   VideoPacketHeader    header;
   RateControlData      rateControl;
} RateControlPacket;


   The format of the RateReplyData structure is:
   
#typedef struct {
   unsigned int         maxRecvKbps;
   unsigned long        recvSeqNum;
   unsigned long        totalBytesSent;
   unsigned long        totalBytesRecv;
   unsigned long        timeSentToMe;
   unsigned long        timeRecvByMe;
} RateReplyData;


   The format of the RateReply Packet is:
   
#typedef struct {
   VideoPacketHeader    header;
   RateReplyData        rateReply;
} RateReplyPacket;


Sending RateControl Packets:
----------------------------

The reflector periodically sends a RateControl Packet to the client.  This 
packet informs the client of the reflector's curSendCap which tells them 
the rate at which they should expect to receive data in the next interval.
This number should be displayed to the user.

   The packet fields are filled out as follows:
   
header.routing.src_family = kReflector;
header.routing.src_addr = 0;
header.routing.src_port = 7648;

header.routing.dest_family = kClient;
header.routing.dest_addr = ;
header.routing.dest_port = 7648;

header.seqNum = ++LastSeqNum;
header.dataType = kRateControlType;
header.message = 0;
header.len = (packet length);

rateControl.curSendCap -     curSendCap currently being used by Reflector
                             for that client.
                         
rateControl.totalBytesSent - Cumulative total of all bytes sent on this
                             connection up to, and including, the
                             RateControl Packet currently being written.
                             
rateControl.timeSent -       Time in milliseconds that the packet was sent.
                             
                             

Received RateControl Packets / Sending RateReply Packets:
---------------------------------------------------------

   The client, upon receipt of a RateControl Packet uses the following
values for its own purposes:

curSendCap - Used for display on local video window.
timeSent   - Future versions could use this to detect lateness and respond
             in some way.
             
   The client responds to the RateControl Packet by immediately sending
back a RateReply Packet.  It is important that this be sent as promptly
as possible because the reflector will be modifying its behavior based
on the round-trip time.
                            
   The packet fields are filled out as follows:
   
header.routing.src_family = kClient;
header.routing.src_addr = (my IP address);
header.routing.src_port = 7648;

header.routing.dest_family = kReflector;
header.routing.dest_addr = 0;   // This should be changed to real IP (RBK)
header.routing.dest_port = 7648;

header.seqNum = 0;
header.dataType = KRateReplyType;
header.message = 0;
header.len = (packet length);

rateReply.maxRecvKbps= Value set as MaxCap in the Reception control panel.

RateReply.recvSeqNum = header.seqNum of RateControlPacket to which we
                       are responding.
rateReply.totalBytesSent = rateControl.totalBytesSent from packet to which we
                       are responding.  (cummulative bytes sent to me on
                       this connection).
rateReply.totalBytesRecv = cummulative bytes received on this connect
                       up to, and including, the ratecontrolpacket which
                       triggered this reply.  Note, we have to be careful
                       to exclude any data received from other sources
                       while we're connected.
rateReply.timeSentToMe Copied from RateControl packet rateControl.timeSent
rateReply.timeRecvByMe Time in milliseconds the packet was received by
                       me.