2016-09-04 4 views
1

Я пытаюсь разрешить имя хоста, а затем открыть/закрыть сокет с хостом.Подключиться к соединениям сокетов в состояниях TIME_WAIT

Код ниже работает нормально. Проблема, с которой я сталкиваюсь, - это, похоже, не корректно закрывать соединения. Я остался с кучей TIME_WAITS:

tcp  0  0 192.168.142.139:44475 172.217.23.14:443  TIME_WAIT 
tcp  0  0 192.168.142.139:44362 45.79.5.162:80   TIME_WAIT 
tcp  0  0 192.168.142.139:44373 45.79.5.162:80   TIME_WAIT 
tcp  0  0 192.168.142.139:44461 172.217.23.14:443  TIME_WAIT 
tcp  0  0 192.168.142.139:44468 172.217.23.14:443  TIME_WAIT 
tcp  0  0 192.168.142.139:44472 172.217.23.14:443  TIME_WAIT 
tcp  0  0 192.168.142.139:44474 172.217.23.14:443  TIME_WAIT 
tcp  0  0 192.168.142.139:44459 172.217.23.14:443  TIME_WAIT 
tcp  0  0 192.168.142.139:44470 172.217.23.14:443  TIME_WAIT 
tcp  0  0 192.168.142.139:44463 172.217.23.14:443  TIME_WAIT 
tcp  0  0 192.168.142.139:44464 172.217.23.14:443  TIME_WAIT 

Я особо не нужно послать что-нибудь конкретное для хозяина, это больше общей проверки Интернет. Я также пробовал то же самое с использованием неблокирующего соединения, за которым следует выбор. Тот же результат.

int port = 443; 
    char *hostname = "google.com"; 

    int open_socket(char *ip) 
    { 
    int error = 0; // Socket error 
    struct sockaddr_in address; 
    short int sock = -1; 
    fd_set fdset; 
    struct timeval tv; 
    int so_keepalive = 0; 

    sock = socket(PF_INET, SOCK_STREAM , 0); 
    if (sock < 0) 
     return 150; 

    address.sin_family = AF_INET; 
    address.sin_addr.s_addr = inet_addr(ip); 
    address.sin_port = htons(port); 
    /* address.sin_addr.s_addr = INADDR_ANY; */ 

    FD_ZERO(&fdset); 
    FD_SET(sock, &fdset); 
    tv.tv_sec = 3; 
    tv.tv_usec = 0; 

    int yes = 1; 
    // setsockopt(sock,SOL_SOCKET,SO_REUSEADDR,&yes,sizeof(int)); 
    // setsockopt(sock, SOL_SOCKET, SO_RCVTIMEO, (char *)&tv, sizeof(struct timeval)); 
    setsockopt(sock, SOL_SOCKET, SO_SNDTIMEO, (char *)&tv, sizeof(struct timeval)); 
    setsockopt(sock, SOL_SOCKET, SO_KEEPALIVE, &so_keepalive, sizeof(so_keepalive)); 

    if (connect(sock, (struct sockaddr *)&address , sizeof(address)) < 0) 
     error = 150; 

    if (error == 0) { 
     char *message = "HELLO"; 
     if (send(sock , message , strlen(message) , 0) < 0) 
     error = 180; 

     char server_reply[2000]; 
     if(recv(sock, server_reply , 2000 , 0) < 0) 
     error = 190; 
    } 

    /* shutdown(sock, SHUT_RDWR); */ 
    close(sock); 
    return error; 
    } 

    int connection_check() 
    { 
    struct addrinfo *result; 
    struct in_addr addr; 

    int error; 

    error = getaddrinfo(hostname, NULL, NULL, &result); 
    if (error != 0) 
    { 
     fprintf(stderr, "DNS Lookup Failed: %s\n", gai_strerror(error)); 
     return 100; 
    } 

    addr.s_addr = ((struct sockaddr_in *)(result->ai_addr))->sin_addr.s_addr; 
    printf("\nUsing %s for internet check\n", inet_ntoa(addr)); 
    freeaddrinfo(result); 
    return(open_socket(inet_ntoa(addr))); 
    } 

Может кто-нибудь предложить, как я должен правильно это обработать.

+2

Вы правильно обработки: или, по крайней мере, нет никаких проблем здесь, чтобы решить. Состояние TIME_WAIT является нормальной частью TCP. Это длится пару минут. – EJP

+0

Хорошо, меня вообще беспокоило, что я не закрываю что-то должным образом. Я проигнорирую и продолжаю. Спасибо –

ответ

0

TCP требует, чтобы конечная точка, которая закрывает соединение блоков дополнительно контакты на одной и той же пары хост/порт, пока нет никаких пакетов от , что подключение оставшихся в сети.

Чтобы временно заблокировать соединения, один конечный пункт хранит копию блока управления TCP (TCB), указывающий, что соединение было окончательно завершено . Такое соединение находится в состоянии TIME-WAIT. Соединения в TIME-WAIT перемещаются в CLOSED, и их TCB отбрасывается после того, как прошло достаточно времени , что все пакеты из того же соединения оставили сети. Пакеты покидают сеть, выйдя на одну из конечных точек и отклоняясь или прибывая с полем времени с проживанием (TTL) с истечением срока действия на маршрутизаторе и удаляясь.

http://www.isi.edu/touch/pubs/infocomm99/infocomm99-web/

+0

Это ответ ?. –

+0

Если это вам поможет, это, если нет, это не так;) –

Смежные вопросы