There is a fairly large binary file (approx. 1mb), it is transmitted over the network to write to the file on the receiving computer (under windows). But when you start it, just part of the file from Explorer (exactly the end of the file) is lost. When running from cmd, everything works as it should.

snippet code:

//s - сокет int n; int l = 1195520; char b[l]; puts("Getting..."); n = recv(s, b, l, 0); if(n < 0) return 1; puts("Got file"); n = send(s, "got the file!\n", 14, 0); if(n < 0) return 1; FILE * f; f = fopen("file1", "wb"); fwrite(&b, sizeof(b), 1, f); fclose(f); close(s); puts("Wrote"); 
  • 3
    recv is not required to read everything. It must read at least one byte (and return this number in the variable n) .. If you need more, read more and more. - KoVadim
  • @KoVadim, is there any restriction on the number of bytes read? - clay
  • No more than is in the buffer. - KoVadim

1 answer 1

According to man recv(2) (the important part is highlighted by me):

If you don’t have any messages ... amount requested.

For convenience, we need a function that takes all the data from the socket to the end (since we know the exact size). Something like this (the code was not checked):

 int recv_all(int socket, void *data, size_t size) { size_t received_total = 0; ssize_t received_now = 0; size_t bytes_left = size; while(1) { received_now = recv(socket, data + received_total, bytes_left, 0); if (received_now < 0) { // как-нибудь обработать ошибку break; } received_total += received_now; bytes_left -= received_now; } return received_total; } 

Use this:

 size_t received; int data_size = 1195520; char buffer[data_size]; size_t received = recv_all(sock, buffer, data_size); if (received < data_size) { return 1; } FILE *f = fopen("file1", "wb"); ... 
  • and unless with a flag 0 after reading the data from a socket are not deleted? - clay
  • Slightly corrected the function: if (bytes_left <= 0) instead of if (received_now < 0) - clay