我正在编写一个程序,用C中的套接字检查传统TCP / IP的潜在吞吐量。目前,客户端和服务器之间传输的数据内容现在无关紧要。唯一重要的是数据传输成功。客户端假设从服务器请求大量(例如10,000对)读/写操作。我遇到了一些阻塞问题,其中客户端和服务器在前几次操作后都停止了。
client.c
#include <sys/types.h>
#include <sys/socket.h>
#include <netdb.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <arpa/inet.h>
int main(int argc,char **argv)
{
int sockfd,n;
struct sockaddr_in servaddr;
sockfd=socket(AF_INET,SOCK_STREAM,0);
bzero(&servaddr,sizeof servaddr);
servaddr.sin_family=AF_INET;
servaddr.sin_port=htons(8080);
inet_pton(AF_INET,"192.168.0.3", &(servaddr.sin_addr));
connect(sockfd,(struct sockaddr *)&servaddr,sizeof(servaddr));
char sendline[100];
char recvline[100];
memset(sendline, 0, 100);
memset(recvline, 0, 100);
/*Send 10,000 read/write operations to the server*/
for(int i = 0; i<10000; i++){
write(sockfd, "read\0", 5);
read(sockfd, sendline, 100);
write(sockfd, "write\0", 6);
write(sockfd, recvline, 100);
}
}
server.c
#include <sys/types.h>
#include <sys/socket.h>
#include <netdb.h>
#include <stdio.h>
#include <string.h>
#include <unistd.h>
#include <arpa/inet.h>
int main()
{
int listen_fd, comm_fd;
struct sockaddr_in servaddr;
listen_fd = socket(AF_INET, SOCK_STREAM, 0);
memset(&servaddr, 0, sizeof(servaddr));
servaddr.sin_family = AF_INET;
servaddr.sin_addr.s_addr = htons(INADDR_ANY);
servaddr.sin_port = htons(8080);
bind(listen_fd, (struct sockaddr *) &servaddr, sizeof(servaddr));
listen(listen_fd, 10);
comm_fd = accept(listen_fd, (struct sockaddr*) NULL, NULL);
int readCount = 0;
int writeCount = 0;
char str[100];
char msg[100];
/*Server listens for client requests.*/
while(1)
{
read(comm_fd, str, 10);
if(strncmp(str, "read", 10) == 0){
printf("Recieved a read request\n");
write(comm_fd, msg, 100);
readCount++;
}else if(strncmp(str, "write", 10) == 0){
printf("Recieved a write request\n");
memset(str, 0, 100);
read(comm_fd, str, 100);
writeCount++;
}
memset(str, 0, 100);
printf("read count: %d. write count: %d\n", readCount, writeCount);
}
}
我的怀疑是,其中一个正在等待另一个相反的I / O操作,即客户端想要读取,但服务器也想要读取而不是写入。所以我添加了一个初始写操作,可以是read
或write
,告诉服务器在传输实际内容之前将要发生什么。但是这不能解决这个障碍?有人可以指出我正确的方向是什么导致阻止,以及如何解决它?
答案 0 :(得分:1)
您未检查read
和write
系统调用的返回值。任何读取或写入调用可能读取或写入的数据少于请求的数据,或者读取的数据可能比单次写入中读取的数据少,因此您需要检查调用的返回值,以查看实际传输或接收的数据量。 / p>
可能发生的事情是您的客户端发送一个6字节&#34;写&#34;字符串后跟一个100字节的缓冲区,然后是另一个请求。服务器读取一个10字节的缓冲区,得到&#34; write&#34;然后缓冲区的前4个字节,然后读取100个字节(获取缓冲区的剩余96个字节和下一个请求的前4个字节)。然后它尝试读取另一个10字节的块来解码下一个请求,但它的前4个字节已经丢失......