linuxsocketstcpsetsockoptcongestion-control

How to change TCP Congestion Control algorithm using setsockopt() call from C++ code


Is it possible to change TCP congestion control algorithm from Cubic to Reno or vice versa using setsockopt call from C++ code in linux?
I am looking for an example code of doing so.


Solution

  • You can use the TCP_CONGESTION socket option to get or set the congestion control algorithm for a socket to one of the values listed in /proc/sys/net/ipv4/tcp_allowed_congestion_control or to any one of the values in /proc/sys/net/ipv4/tcp_available_congestion_control if your process is privileged.

    C example:

    #include <sys/socket.h>
    #include <netinet/in.h>
    #include <netinet/tcp.h>
    #include <stdio.h>
    #include <string.h>
    #include <unistd.h>
    
    int main(int argc, char **argv)
    {
        char buf[256];
        socklen_t len;
        int sock = socket(AF_INET, SOCK_STREAM, 0);
    
        if (sock == -1)
        {
            perror("socket");
            return -1;
        }
    
        len = sizeof(buf);
    
        if (getsockopt(sock, IPPROTO_TCP, TCP_CONGESTION, buf, &len) != 0)
        {
            perror("getsockopt");
            return -1;
        }
    
        printf("Current: %s\n", buf);
    
        strcpy(buf, "reno");
    
        len = strlen(buf);
    
        if (setsockopt(sock, IPPROTO_TCP, TCP_CONGESTION, buf, len) != 0)
        {
            perror("setsockopt");
            return -1;
        }
    
        len = sizeof(buf);
    
        if (getsockopt(sock, IPPROTO_TCP, TCP_CONGESTION, buf, &len) != 0)
        {
            perror("getsockopt");
            return -1;
        }
    
        printf("New: %s\n", buf);
    
        close(sock);
        return 0;
    }
    

    For me outputs:

    Current: cubic
    New: reno