2016-10-22 5 views
0

次のコードは、実際に別のファイルで受信する場合、同じファイル("/ tmp/frame")、 のデータを引き続き受信します。 サーバーがファイルの受信を開始し、閉じず、次のファイルのデータを引き続き受信しているようです。ソケット転送でファイルが無限のデータを受信し続ける

(コード内のコメントは、問題を解決しますが、ファイルの転送を遅らせる)

送信者:

screenshot ptr_screen; 
CHAR Block[4096], buffer[512]; 
int BytesRead, iResult; 
for (;;) { 
    memset(Block, 0, sizeof(Block)); 
    memset(buffer, 0, sizeof(buffer)); 

    ptr_screen.Start(); 

    FILE *fp = fopen("screen.jpg", "rb"); 
    if (!fp) { break; } 

    fseek(fp, 0, SEEK_END); 
    int32_t file_size = ftell(fp); 
    fseek(fp, 0, SEEK_SET); 

    iResult = send(socket_, (char*)&file_size, sizeof(file_size), 0); 
    if (iResult == SOCKET_ERROR) { fclose(fp); break; } 

    while (file_size > 0) { 
     BytesRead = fread(Block, 1, sizeof(Block), fp); 
     if (BytesRead <= 0) { break; } 

     iResult = send(socket_, Block, BytesRead, 0); 
     if (iResult != BytesRead) { break; } 

     file_size -= BytesRead; 
    } 
    fflush(fp); 
    fclose(fp); 
    //if (recv_to(socket_, buffer, sizeof(buffer), 0, 5000) <= 0) 
     //break; 
} 

受信機:

int iResult; 
char Block[512]; 
int32_t file_size; 
for(;;) { 
    FILE* fp = fopen("/tmp/frame", "wb"); 
    if(!fp) { break; } 

    memset(Block, 0, sizeof(Block)); 
    iResult = recv_to((char*)&file_size, sizeof(file_size), 10); 
    if(iResult <= 0) { break; } 

    while(file_size > 0) { 
     iResult = recv_to(Block, sizeof(Block), 10); 
     if(iResult <= 0) { break; } 

     if(fwrite(Block, 1, iResult, fp) != (unsigned)iResult) { return; } 
     file_size -= iResult; 
    } 
    fclose(fp); 
    system("mv /tmp/frame /tmp/stream.jpg"); 
    //send(socket_, "OK", strlen("OK"), 0); // response 
} 

答えて

2

TCPですストリームプロトコル。受信者は、通常、送信者が送信したデータと同じチャンクに分割されたデータを受信することはありません。チャンクは本質的に任意に分解されます。

特に、送信者がファイルの最後の部分を送信すると、すぐに新しいファイルからサイズと最初のチャンクが送信されます。受信者が最後のチャンク、サイズ、および部分を受信する可能性があります次のファイルの最初のチャンクのすべてが1つのブロックにまとめられています。 file_sizeは負になります。これはあなたを今度は内側のループから抜け出します。しかし、次に、file_sizeに次のファイルの途中からいくつかのランダムなデータを読み込みます。おそらくちょうど非常に大きな整数を形成することになります。そのため、内側のループはもう終了しないように見えます。

内側のループではmax(sizeof(Block), file_size)バイトを読み込み、ファイルの境界を越えないようにしてください。

+0

Linuxサーバーの例を教えてもらえますか? –

+0

何の例ですか? –

+0

どうすればこのコードをrecv_to(block、sizeof(Block)、10)に変更できますか? 私はこの問題を抱えていませんか? –

関連する問題