如何停止从套接字C / C ++接收数据

时间:2012-10-02 19:25:35

标签: c++ c sockets tcp

关键是我发送了4096个字节但只有119个字节的aprox。携带有用的信息。

100个字节以\ r \ n \ n \ n \ n结尾,所以在客户端,当我读到\ r \ n \ r \ n时,我想停止从该字符串接收信息,然后重新开始。

我不知道是否需要冲洗,关闭插座,或其他什么......

它们是套接字TCP。

客户端中,我这样做:

 buf details[4096];
 strcpy(details,"1");
 strcat(details,"10/04/12");
 strcat(details,"Kevin Fire");
 strcat(detils,"abcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcde\r\n\r\n");
 nbytes_sent = send(sock,(char *)details,sizeof(details),0);

另一方面,服务器 ...

char buf[20];
memset(buf,'\0',20);

while(!end){
 nbytes_read=recv(sclient,(char *)ress,sizeof(ress),0);

 if(strcmp(ress,"1")==0){
   printf("Details: %s (%i)\n",buf,nbytes_read);
   while(strcmp(buf,"\r\n\r\n") != 0){
     nbytes_read=recv(sclient,(char *)buf,sizeof(buf),0);
     cout.flush();
     printf("Details: %s (%i)\n",buf,nbytes_read);
   }                                     }
   if(strcmp(buf,"\r\n\r\n")==0) printf("The End\n");
   cout.flush();
 }
}

我只想阅读一个新的“ress”,而不是检索其余无效的字节。

提前致谢。

4 个答案:

答案 0 :(得分:1)

如果你的意思是想要丢弃剩余的数据并读取一个新的块你不能用TCP做,因为它是面向流的,没有消息的概念,也不知道你的其余信息想要忽略。如果你的意思是别的,请描述一下。

但除此之外,为什么只在nbytes_sent = send(sock,(char *)details,sizeof(details),0); nbytes_sent = send(sock,(char *)details,strlen(details),0)之前的数据时使用\r\n' is important. you can use;`只发送有效数据和减少你通过网络发送的垃圾,你不需要在服务器上重新开始?

答案 1 :(得分:0)

我不确定我是否完全关注了您的问题,但只要您检测到您收到的邮件结束时,您就可以设置end=true

char buf[20];
memset(buf,'\0',20);
while(!end)
{
    nbytes_read=recv(sclient,(char *)ress,sizeof(ress),0);
    if(strcmp(ress,"1")==0)
    {
        printf("Details: %s (%i)\n",buf,nbytes_read);
        while(strcmp(buf,"\r\n\r\n") != 0)
        {
            nbytes_read=recv(sclient,(char *)buf,sizeof(buf),0);
            cout.flush();
            printf("Details: %s (%i)\n",buf,nbytes_read);
        }
    }
    if(strcmp(buf,"\r\n\r\n")==0)
    {
        end = true; // <--- This should do it for you, right?
        printf("The End\n");
    }
    cout.flush();
}

但是,如果客户端仍然连接并将下一条消息写入套接字,那么您只需要开始阅读下一条消息。那么一旦写入消息,客户端会发生什么?它是开始编写下一条消息还是关闭套接字连接?

此外:您需要获取缓冲区中的内容并从中创建消息。当前消息完成后,请考虑使用下一条消息中的缓冲区内容创建一条新消息。

答案 2 :(得分:0)

如果您设计的协议如HTTP 1.0,每个请求都会打开一个新套接字,那么在您阅读足够的内容后关闭套接字。

否则,您需要继续阅读,直到跳过整个4096字节为止。最简单的方法是继续读取,直到你首先得到4096个字节(你需要在循环中调用recv),然后解析缓冲区的内容。再说一遍,你可能最好重新设计你的协议。

答案 3 :(得分:0)

我的想法只是偷看第一个x字符。 4个字符可能是预期缓冲区的大小。

例如,如果您的消息是: abcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcde \ r \ n \ r \ n

这是(使用你的原理图)100字节加上\ r \ n \ r \ n。所以它是100 + 4,所以104。

我会在字符串的开头发送char(104)作为sentinal值 然后是它后面的字符串,所以它看起来类似于

炭(104)abcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcde \ r \ n \ r \ n

然后使用recv的peek_MSG能力来获取第一个字符串,设置字符串大小,只读取该值以及通过套接字刷新调用丢弃的任何内容。