Vivek V K
Vivek V K

Reputation: 1148

C - send multiple messages over a single socket - Data not transferred until I close the socket

I am attempting to have a TCP communication from my laptop to a SoC board where I send one message to initiate a process and It sends me a series of status messages until it has completed the process. This means that I would call send() multiple times over the socket from the SoC. The problem is that my laptop does not receive any status message unless the socket connection is closed by the SoC. As soon as the socket closes, I get a burst of all the data that the SoC sent. Is there a way to make this communication realtime so that I get the status messages immediately as it sends?

Code on the SoC that sends the data: This function is called multiple times:

INT16 upload(INT16* socket, INT8 HOB, INT8 LOB, INT8 msg_type, INT8* data) {
    INT8* Tx_Data= NULL;
    INT8 size = 0;
    INT16 num= 0;
    int temp = 0;
    size = 256*HOB + LOB + NAME_SIZE + 3;
    Tx_Data = (INT8*) malloc(size*sizeof(INT8));
    for (num=0;num<NAME_SIZE ;num++) {
            Tx_Data[num] = NAME[num];   
    }   
    Tx_Data[num++] = HOB;
    Tx_Data[num++] = LOB;
    Tx_Data[num++] = msg_type; // 11 byte header ends here
    for(temp = 0;num<size;num++,temp++) {
        Tx_Data[num] = data[temp]; // data
    }
    send(*socket, (INT8*)Tx_Data,num,0);
    return PASS;
}

Code on my Laptop:

for(;;) {
            printf("Start of for loop socket id: %d \n",socket_id);
            RX_Data = (unsigned char*)malloc(2048);
            unsigned char Command;
            int No_of_Data_Bytes=0;
            printf("Before read.... \n");
            nbytes = read(socket_id,RX_Data,11);    // get 11 bytes from EZ80
            printf("Received %d bytes from socket\n",nbytes);
            No_of_Data_Bytes = RX_Data[8]*256 + RX_Data[9];
            Command = RX_Data[10];
            printf("\n command:%c %d \n",Command,No_of_Data_Bytes);
            if(Command=='I' || Command=='E'|| Command=='V') {
                    //read and analyse data
            }
            else {
                    break;
            }
            Command = '\0';
            free(RX_Data);
        }

Upvotes: 0

Views: 1006

Answers (2)

wick
wick

Reputation: 2234

The reason for this behaviour is Nagel algorithm that is enabled on a socket by default. You can disable it via setsockopt() call.

You can use fflush() or just add '\n' character to the end of string being writen into the socket, but this will flush only stdio buffers in userland, which is not what you aim at.

Upvotes: 0

Cantfindname
Cantfindname

Reputation: 2148

In Linux you could just use fdopen, write and flush the stream. Not sure if it's applicable in your case however. Example:

FILE *f = fdopen(socketdescriptor, "w+");
. . .
n = write(socketdescriptor, "this is a message", 17);
fflush(f);
...

Upvotes: 1

Related Questions