5

ストリーミングストックティックデータを受信して​​いるソケットがあります。ただし、切り捨てられたメッセージ、または切り捨てられたメッセージのように見えるものがたくさん表示されるようです。これが私がデータを受け取る方法です:

if((numbytes = recv(sockfd, buf, MAXDATASIZE-1, 0)) == -1) {
    perror("recv()");
    exit(1);
}
else {
    buf[numbytes] = '\0';
    // Process data
}

recv()送信されたものの一部のメッセージだけを受信できますか?

私の気持ちはrecv()、完全なメッセージが送信されるまで受信する呼び出しの周りに別のループが必要になる可能性があるということです。私が持っているlibcurl実装(ここではlibcurlを使用できないと思います)には外部ループがあることを知っています:

// Read the response (sum total bytes read in tot_bytes)
for(tot_bytes=0; ; tot_bytes += iolen)
{  
    wait_on_socket(sockfd, 1, 60000L);
    res = curl_easy_recv(curl, buf + tot_bytes, sizeof_buf - tot_bytes, &iolen);

    if(CURLE_OK != res) {
        // printf( "## %d", res );
        break;
    }
}

recv()libcurlの例に似たループが必要ですか(検証可能に機能します)?

4

4 に答える 4

8

recvすべてのメッセージが到着するまで待機するためにフラグを渡すこともできます。受信するバイト数がわかっている場合に機能します。このようにコマンドを渡すことができます。

numbytes =  recv(sockfd, buf, MAXDATASIZE-1, MSG_WAITALL);
于 2014-12-22T20:35:39.597 に答える
7

そうです、ループが必要です。 recv現在利用可能なデータのみを取得します。データが読み取られると、データが返される前にさらに表示されるのを待ちません。

マニュアルページには、「受信コールは通常、要求された全額の受信を待つのではなく、要求された量までの利用可能なデータを返します」と書かれています。

于 2012-04-20T17:20:55.607 に答える
3

TCPはメッセージ境界を尊重しません。つまりrecv()、あなたが仮定したとおりに、メッセージ全体を取得できるとは限りません。そしてそれは確かにあなたがあなたの周りにループが必要な理由ですrecv()。(これが、HTTPなどの上位層プロトコルがソケットを閉じるか長さインジケーターを付加する理由でもあるため、受信者はソケットからの読み取りをいつ停止するかを正確に知ることができます。)

于 2012-04-20T17:20:59.180 に答える
1

recv()は、送信されたメッセージの一部だけを受信できますか?

はい、確かに、TCPを使用している場合。これはあなたを助けることができると思います。 Cでのrecv()TCPからの部分的な戻りの処理

于 2012-04-20T17:20:17.680 に答える