TCP open socket and remain open

frankthetank34 wrote on Wednesday, May 11, 2016:

Hello,

Following this example:
http://www.freertos.org/FreeRTOS-Plus/FreeRTOS_Plus_TCP/TCP_Networking_Tutorial_Sending_TCP_Data.html

I have successfully opened a TCP socket, sent some data and closed it.

What I would like to do next is open a socket, send some data, check if there is data to receive, leave it open. Periodically checking if there is something to receive and if I have something new to send. Are there any examples that do something similar? I also have a hard time find exmaples online. Possibly a dumb question, but I can’t seem to find examples that are referenced in posts such as this one:
http://www.freertos.org/FreeRTOS-Plus/FreeRTOS_Plus_TCP/TCP_Echo_Clients.html

Where are these examples?

heinbali01 wrote on Wednesday, May 11, 2016:

… Are there any examples that do something similar?

This is more a general question about how to program TCP.

A TCP server is maybe the simplest:

Task-1 waits for a new client connection while calling FreeRTOS_accept() in a blocking way.

For every client, a new task will be created, which will call FreeRTOS_recv() in a blocking way.

Checking the result codes is very important:

    xResult = FreeRTOS_recv( socket, buf, len, flags );
    if( ( xResult < 0 ) && ( xResult != -pdFREERTOS_ERRNO_EWOULDBLOCK ) )
    {
        FreeRTOS_closesocket( socket );
        /* break from the main loop and terminate this task. */
        break;
    }

    /* The result of FreeRTOS_send() must be checked in the same way: */
    xResult = FreeRTOS_send( socket, buf, len, flags );
    if( ( xResult < 0 ) && ( xResult != -pdFREERTOS_ERRNO_EWOULDBLOCK ) )
    {
        FreeRTOS_closesocket( socket );
        /* break from the main loop and terminate this task. */
    }

Normally a TCP server will not actively close a connection. But if it does want to actively close a connection, you can do it like this:

    for( ;; )
    {
        /* Read and write from socket as shown above. */
        if( xDoSendShutdown != pdFALSE )
        {
            xDoSendShutdown = pdFALSE;
            FreeRTOS_shutdown( socket, FREERTOS_SHUT_RDWR );
        }
        /* Continue normal processing and wait for the closure. */
    }

and continue the normal loop that calls FreeRTOS_recv() for this socket. After some time FreeRTOS_recv() will return an error like -pdFREERTOS_ERRNO_ENOTCONN.

The above scheme is maybe the easiest to start with.

Have a look at these files:

FreeRTOS-Plus-TCP\protocols\Common\FreeRTOS_TCP_server.c
FreeRTOS-Plus-TCP\protocols\FTP\FreeRTOS_FTP_server.c
FreeRTOS-Plus-TCP\protocols\HTTP\FreeRTOS_HTTP_server.c

This is an advanced example of a TCP server that only uses one single task. At one point it calls select() in a blocking way:

    xRc = FreeRTOS_select( pxServer->xSocketSet, xBlockingTime );

All other network calls in these source files are non-blocking.

Another +TCP specific method of handling many socket within a single task is with the use of socket semaphores
That allow you to block on a semaphore. The IP-task will give to that semaphore as soon as anything of interest has happened (data arrival, new connection, connection lost etc).

Where are these examples?

When you look at the labs download, you will find the source code of the examples in the directory FreeRTOS-Plus/Demo/Common.

Regards

rtel wrote on Wednesday, May 11, 2016:

When you look at the labs download, you will find the source code of the examples in the directory FreeRTOS-Plus/Demo/Common.

I will make a note to update the relevant web pages (such as the one referenced in the first post in this thread) to say where the code actually is.