C++ 从套接字读写
我制作了一个简单的tcp服务器/客户端应用程序,客户端向服务器写入一些内容,然后将其回显到客户端。然而,当我试图读取服务器在客户机中的回音时,我遇到了一些问题C++ 从套接字读写,c++,sockets,C++,Sockets,我制作了一个简单的tcp服务器/客户端应用程序,客户端向服务器写入一些内容,然后将其回显到客户端。然而,当我试图读取服务器在客户机中的回音时,我遇到了一些问题 string s; while((n = read(socketFD[0],readBuf, BUFFER_SIZE)) > 0){ cout<<"\nBytes read: "<<n<<endl; s.append(readBuf, n); } cout<<"\nTest a
string s;
while((n = read(socketFD[0],readBuf, BUFFER_SIZE)) > 0){
cout<<"\nBytes read: "<<n<<endl;
s.append(readBuf, n);
}
cout<<"\nTest after read\n";
read调用似乎在完成从套接字的读取后阻塞,并且永远不会离开循环。我怎样才能解决这个问题
编辑:这是服务器中处理连接的客户端的代码
if((childpid = fork()) == 0){
close(listenFD);
while ((n = read(connectFD, buf, BUFFSIZE)) > 0){
cout<<"\nBytes read: "<<n<<endl;
write(connectFD, buf, n);
}
cout<<"\nTest after read\n";
exit(0);
}
与客户端中的代码相比,这里有什么不同?为什么读取调用不像在客户端中那样阻塞 如果您不想将读取循环放入另一个线程中,那么您可以在不实际读取的情况下查看队列中是否存在某些内容
读取调用在完成从套接字读取后似乎会阻塞,并且永远不会离开循环。如何解决此问题?
简短回答,收到所有数据后,不要呼叫read
编写代码,以检测何时已接收到当时希望接收的所有数据,如果是,则退出循环。您必须实际实现某种协议
s+=readBuf;
那不可能是对的。它如何知道要向
s
中添加多少字节的数据?这里是一段摘自Python中一篇非常好的套接字介绍的摘录。它是Python,是的,但是它公开了C-Socket API,因此在您的上下文中编写的内容也是正确的。你可以在这里阅读:
关于“使用套接字”的部分准确地告诉您所观察到的问题是什么。它讨论的是recv
函数,但它转换为文件描述符上的read
函数
但是,如果您计划重用套接字进行进一步传输,则需要意识到套接字上没有EOT。我重复:如果套接字send或recv在处理0字节后返回,则连接已断开。如果连接没有断开,您可以永远等待recv,因为套接字不会告诉您没有更多内容可读(目前)。现在,如果您仔细考虑一下,您将认识到套接字的一个基本事实:消息必须是固定长度的(恶心),或者是分隔的(耸耸肩),或者指示它们的长度(好得多),或者通过关闭连接来结束。这完全是你的选择,(但有些方法比其他方法更正确)
什么是
readArr
?当服务器关闭连接时,循环应该退出——<代码>读()(代码)>将返回0指示EOF。它是一个键入,应该是Read BuffFe,它不能工作,因为<代码> Read Buff不是C++字符串或C字符串。C字符串需要以null结尾,read
不能这样做,因为它可以用于非字符串的数据。在阻塞套接字上,read
调用将阻塞,直到读取至少一个字节或发生错误或连接关闭。如果你想的话,你可以使套接字不阻塞。你能检查一下帖子中添加的代码吗?为什么会得到不同的结果?请查看n
的值。如果是零,那是因为另一端关闭了连接。如果是-1
,请检查errno
以了解返回read
的原因。因此,read中的返回值0始终表示连接的另一侧已关闭?read中的0表示双向连接的入站部分已正常关闭。如果你没有关闭它,那么另一边肯定有。(例如,您可以使用shutdown
功能将其关闭。)
Bytes read: 4096
Bytes read: 4096
Bytes read: 4096
Bytes read: 4046
Test after read
s+=readBuf;