UDT Tutorial

### User-defined Congestion Control Algorithm

You can add your own congestion control algorithm into UDT. It is as simple as to define several callback functions that will be triggered on certain events, e.g, when an ACK is received.

All the congestion control callback functions are collected in a C++ class CCC. You have to inherit this class to define your own congestion control algorithm. That is, UDT/CCC uses an object-oriented design. CCC in defined in ccc.h, which you have to include in your files in order to enable this feature.

The CCC class contains two control variables: m_dPktSndPeriod, and m_dCWndSize. m_dPktSndPeriod is a double float number representing the packet sending period (as to be used in rate control), in microseconds. m_dCWndSize is a double float number representing the size of the congestion window (cwnd), in number of packets. The congestion control algorithm will need to update at least one of them. For example, for pure window based approach, m_dPktSndPeriod should always be zero.

The fast way to learn CCC is to use the examples in ./app/cc.h. The file cc.h also includes many more advanced control mechanisms that your control classes can be derived from. For example, if you are designing a new TCP variant, you can implement the new control class directly from CTCP.

Here we demonstrate the usage of UDT/CCC by writing a reliable UDP blast control mechanism.

class CUDPBlast: public CCC
{
public:
CUDPBlast() {m_dCWndSize = 83333.0;}
public:
void setRate(int mbps)
{
m_dPktSndPeriod = (m_iMSS * 8.0) / mbps;
}
};

In this example, CUDPBlast inherits from the base class CCC. In the constructor, it sets the congestion window size to a large value so that it will not affect the packet sending. (This is pure rate based method to blast UDP packets.) The method SetRate() can be used to set a fixed packet sending rate at any time.

The application can use setsockopt/getsockopt to assign this control class to a UDT instance, and/or set its parameters.

UDT::setsockopt(usock, 0, UDT_CC, new CCCFactory<CUDPBlast> <CUDPBlast> , sizeof(CCCFactory<CUDPBlast> <CUDPBlast>));

The above code assigns the CUDPBlast control algorthm to a UDT socket usock. Note that CCCFactory<CUDPBlast> is using the Abstract Factory design pattern.

To set a specific data sending rate, the application needs to obtain a handle to the concrete CCC class instance used by the UDT socket usock.

CUDPBlast* cchandle = NULL;
int temp;
UDT::getsockopt(usock, 0, UDT_CC, &cchandle, &temp);

The application can then call the method of setRate() to set a 500Mbps data rate.

if (NULL != cchandle)
cchandle->setRate(500);

The UDT/CCC can be used to implement most control mechanims, including but not limited to rate-based approaches, TCP variants (e.g., TCP, Scalable, HighSpeed, BiC, Vegas, FAST), and group-based approaches (e.g., GTP, CM).

##### Note

1. Do NOT call regular UDT API inside CCC or its derived classes. Unknown error could happen.

2. CCCFactory<...> is a C++ template class. You do not need to derive any classes from it.

3. UDT will not release the CCCFactory<...> instance. The application should release it, at anywhere after the setsockopt() call.

##### See Also

Congestion Control Class