我是C ++的新手,我正在从事套接字编程。在这种情况下,服务器应用程序充当HTTP服务器。
有一个客户端应用程序请求数据,该数据作为HTTP响应返回。在响应返回期间,客户端关闭连接。我看到套接字在服务器中移到了CLOSE_WAIT状态。
套接字连接中有很多CLOSE_WAIT状态。我在下面附加了我的代码和netstat命令结果,请提供更好的解决方案以克服CLOSE_WAIT状态。
server.cpp
int server_fd, new_socket, valread;
struct sockaddr_in address,clntAdd;
int opt = 1;
int addrlen = sizeof(address);
int getopt_ret=0;
int long_index=0;
string key_u,key_v;
int iteration_count=10;
socklen_t len;
const char *hash_key_u;
const char *hash_key_v;
char type[1024] = {0};
if ((server_fd = socket(AF_INET, SOCK_STREAM, 0)) == 0)
{
logger("socket failed");
exit(EXIT_FAILURE);
}
bzero((char*) &address, sizeof(address));
address.sin_family = AF_INET;
address.sin_addr.s_addr = INADDR_ANY;
address.sin_addr.s_addr = inet_addr("192.168.0.4");
address.sin_port = htons( PORT );
// Forcefully attaching socket to the port 8080
if (bind(server_fd, (struct sockaddr *)&address,
sizeof(address))<0)
{
logger("bind failed");
exit(EXIT_FAILURE);
}
if (listen(server_fd, 3) < 0)
{
logger("listen");
exit(EXIT_FAILURE);
}
while (true)
{
if ((new_socket = accept(server_fd, (struct sockaddr *)&address,
(socklen_t*)&addrlen))<0)
{
logger("socket not accept");
exit(EXIT_FAILURE);
}
valread = read( new_socket , type, 1024);
//printf("%s\n",type );
send(new_socket , hash_key_u , strlen(hash_key_u) , 0 );
//send(new_socket , hash_key , strlen(hash_key) , 0 );
//printf("Hello message sent\n");
}
return 0;
client.cpp
int sock = 0, valread;
struct sockaddr_in serv_addr;
char buffer[1024] = {0};
long arg;
fd_set myset;
struct timeval tv;
int valopt,i;
const int ASCIICON[2]={6,2};
socklen_t lon;
string ack="he";
string desc,newkey;
if ((sock = socket(AF_INET, SOCK_STREAM, 0)) < 0)
{
logger("Socket creation error ");
return string("-1");
}
serv_addr.sin_family = AF_INET;
serv_addr.sin_port = htons(PORT);
if(inet_pton(AF_INET, address, &serv_addr.sin_addr)<=0)
{
logger("Invalid address/ Address not supported ");
return string("-1");
}
if( (arg = fcntl(sock, F_GETFL, NULL)) < 0) {
fprintf(stderr, "Error fcntl(..., F_GETFL) (%s)\n", strerror(errno));
exit(0);
}
int res;
res = connect(sock, (struct sockaddr *)&serv_addr, sizeof(serv_addr));
if (res < 0) {
if (errno == EINPROGRESS) {
fprintf(stderr, "EINPROGRESS in connect() - selecting\n");
do {
tv.tv_sec =300;
tv.tv_usec = 0;
FD_ZERO(&myset);
FD_SET(sock, &myset);
res = select(sock+1, NULL, &myset, NULL, &tv);
if (res < 0 && errno != EINTR) {
fprintf(stderr, "Error connecting %d - %s\n", errno, strerror(errno));
exit(0);
}
else if (res > 0) {
// Socket selected for write
lon = sizeof(int);
if (getsockopt(sock, SOL_SOCKET, SO_ERROR, (void*)(&valopt), &lon) < 0) {
fprintf(stderr, "Error in getsockopt() %d - %s\n", errno, strerror(errno));
exit(0);
}
if (valopt) {
fprintf(stderr, "Error in delayed connection() %d - %s\n", valopt, strerror(valopt));
exit(0);
}
break;
}
else {
fprintf(stderr, "Timeout in select() - Cancelling!\n");
exit(0);
}
} while (1);
}
else {
fprintf(stderr, "Error connecting %d - %s\n", errno, strerror(errno));
exit(0);
}
}
char s[300];
strcpy(s,ack.c_str());
write(sock, type, strlen(type));
read( sock , buffer, 1024);
netstat结果
Proto Recv-Q Send-Q Local Address Foreign Address State PID/Program name
tcp 0 0 0.0.0.0:22 0.0.0.0:* LISTEN -
tcp 0 0 192.168.0.4:5000 0.0.0.0:* LISTEN 11546/key_send
tcp 0 0 127.0.0.1:3310 0.0.0.0:* LISTEN -
tcp 1 0 192.168.0.4:5000 192.168.0.3:46528 CLOSE_WAIT 11546/key_send
tcp 1 0 192.168.0.4:5000 192.168.0.3:45112 CLOSE_WAIT 11546/key_send
tcp 0 0 192.168.0.4:5000 192.168.0.3:47296 ESTABLISHED 11546/key_send
tcp 1 0 192.168.0.4:5000 192.168.0.3:45766 CLOSE_WAIT 11546/key_send
tcp 1 0 192.168.0.4:5000 192.168.0.3:45734 CLOSE_WAIT 11546/key_send
tcp 0 0 192.168.0.4:5000 192.168.0.3:47544 ESTABLISHED 11546/key_send
tcp 1 0 192.168.0.4:5000 192.168.0.3:46072 CLOSE_WAIT 11546/key_send
tcp 0 0 192.168.0.4:5000 192.168.0.3:47926 ESTABLISHED 11546/key_send
tcp 1 0 192.168.0.4:5000 192.168.0.3:47168 CLOSE_WAIT 11546/key_send
tcp 0 0 192.168.0.4:5000 192.168.0.3:48158 ESTABLISHED 11546/key_send
tcp 0 0 192.168.0.4:5000 192.168.0.3:47376 ESTABLISHED 11546/key_send
tcp 1 0 192.168.0.4:5000 192.168.0.3:45274 CLOSE_WAIT 11546/key_send
tcp 1 0 192.168.0.4:5000 192.168.0.3:46756 CLOSE_WAIT 11546/key_send
tcp 1 0 192.168.0.4:5000 192.168.0.3:45614 CLOSE_WAIT 11546/key_send
tcp 0 0 192.168.0.4:5000 192.168.0.3:48030 ESTABLISHED 11546/key_send
tcp 1 0 192.168.0.4:5000 192.168.0.3:44970 CLOSE_WAIT 11546/key_send
tcp 0 0 192.168.0.4:5000 192.168.0.3:47328 ESTABLISHED 11546/key_send
tcp 1 0 192.168.0.4:5000 192.168.0.3:45152 CLOSE_WAIT 11546/key_send
tcp 0 0 192.168.0.4:5000 192.168.0.3:48258 ESTABLISHED 11546/key_send
tcp 1 0 192.168.0.4:5000 192.168.0.3:46824 CLOSE_WAIT 11546/key_send
tcp 1 0 192.168.0.4:5000 192.168.0.3:46440 CLOSE_WAIT 11546/key_send
tcp 0 0 192.168.0.4:5000 192.168.0.3:48010 ESTABLISHED 11546/key_send
tcp 1 0 192.168.0.4:5000 192.168.0.3:46832 CLOSE_WAIT 11546/key_send
tcp 1 0 192.168.0.4:5000 192.168.0.3:46856 CLOSE_WAIT 11546/key_send
tcp 1 0 192.168.0.4:5000 192.168.0.3:44810 CLOSE_WAIT 11546/key_send
tcp 1 0 192.168.0.4:5000 192.168.0.3:46880 CLOSE_WAIT 11546/key_send
tcp 1 0 192.168.0.4:5000 192.168.0.3:45574 CLOSE_WAIT 11546/key_send
tcp 1 0 192.168.0.4:5000 192.168.0.3:47128 CLOSE_WAIT 11546/key_send
tcp 1 0 192.168.0.4:5000 192.168.0.3:44710 CLOSE_WAIT 11546/key_send
tcp 0 0 192.168.0.4:5000 192.168.0.3:48202 ESTABLISHED 11546/key_send
tcp 1 0 192.168.0.4:5000 192.168.0.3:45908 CLOSE_WAIT 11546/key_send
tcp 1 0 192.168.0.4:5000 192.168.0.3:44458 CLOSE_WAIT 11546/key_send