Как установить тайм-аут сервера TCP при приеме нескольких клиентских подключений - PullRequest
0 голосов
/ 18 мая 2019

Я работаю над функцией на моем TCP-сервере, которая принимает предварительно определенное количество клиентских подключений в течение определенного периода времени (сейчас я установил его на 10 секунд) и возвращает, когда достигнуто предварительно определенное количество подключений.Я использую функцию выбора, чтобы установить тайм-аут сервера, но по какой-то причине тайм-аут сбрасывается каждый раз, когда клиент присоединяется.например, если клиент присоединяется к серверу через 5 секунд, то время ожидания сбрасывается и начинается обратный отсчет с 10. Помощь будет очень признательна, спасибо.

Я использую Mac и думаю, что в этой ОС FD_ISSET используется для проверки подключения клиента (что, я уверен, не требуется в Linux).Таким образом, вы можете просто обработать возвращаемое значение этой функции так же, как и возвращаемое значение функции select в linux.

while (num_conn < NO_OF_CLIENTS) {

    // Listen for clients
    err = listen(server_fd, 128);
    if (err < 0) {
        fprintf(stderr, "Could not listen on socket\n");
        exit(EXIT_FAILURE);
    }
    // Zero out memory for the client information
    memset( & client, 0, sizeof(client));

    socklen_t client_len = sizeof(client);
    FD_ZERO( & set);
    FD_SET(server_fd, & set);

    select(server_fd + 1, & set, NULL, NULL, & timeout);

    // server times out after allowing 30 seconds for clients to join.
    // If no clients join function returns 0. Otherwise returns no_clients
    nready = FD_ISSET(server_fd, & set);
    printf("nready is: %d\n", nready);

    if (nready == 0) {
        return num_conn; // returns number of connections if a time out occurs. 
    }

    // Accept the connection from the client
    client_fd[num_conn] = accept(server_fd, (struct sockaddr * ) & client, & client_len);
    if (client_fd < 0) {
        fprintf(stderr, "Could not establish new connection\n");
        // SEND REJECT??
        exit(EXIT_FAILURE);
    }

    // Assign value to number of clients here and let it set after a time out
    // more work to  be done here
    printf("Accepted connection from client %d\n", num_conn);
    num_conn++;
}

1 Ответ

1 голос
/ 18 мая 2019
select(server_fd + 1, & set, NULL, NULL, & timeout);

Ваш код зависит от выбора, изменяющего timeout, установленный вне цикла, так что timeout отражает оставшееся время.Но вы не можете полагаться на это поведение, поскольку оно относится только к некоторым платформам, таким как Linux.

Примечательно, что на вашей платформе MacOS справочная страница для select четко заявляет, что время ожидания не изменяется вЕсли вы полагаетесь на:

... Для проведения опроса аргумент тайм-аута должен быть не нулевым, указывая на нулевую временную структуру. Тайм-аут не изменяется с помощью select () и может использоваться повторно при последующих вызовах, однако рекомендуется повторно инициализировать его перед каждым вызовом select ().

Это означает, что вам нужно самостоятельно определить время, потраченное на select, и соответственно настроить timeout при повторном вызове select.

...