C Accept Client Socket «Недопустимый аргумент» Ошибка при добавлении сигнального потока - PullRequest
0 голосов
/ 12 декабря 2018

Я делаю проект для класса и застрял в проблеме.

Мой проект требует таймера каждые 15 секунд для печати данных.Это также требует отлова завершения программы.Для решения обеих этих задач я создал поток сигналов и перехватывал сигналы SIGINT и SIGALRM (из setitimer).У меня нет проблем здесь.

Однако, соединение с сервером-> клиентом больше не работает должным образом.Я продолжаю получать -1 в качестве идентификатора сокета с ошибкой «Недопустимый аргумент».Это не имеет никакого смысла для меня, потому что, если я отключаю сигнальный поток, все снова работает нормально.Я вставлю приведенный ниже код.

void * signal_thread(void * arg) {


while (1) {
    int caught_signal;

    sigwait(&mask, &caught_signal);

    switch(caught_signal) {
    case SIGINT:
        puts("Server manually terminated!");
        int i;
        for(i = 0; i<clientCount; i++){
            send(socketIds[i], "ServerShutDown", 255, 0);
        }
        break;
    case SIGALRM:
        printf("CAUGHT SIGALRM\n");
        break;
    default:
        break;
    }
}
}

int main(void) {
    /* do the necessary setup, i.e. bind() and listen()... */
    int rc;
    pthread_t signal_tid;
    sigemptyset(&mask);
    sigaddset(&mask, SIGINT);
    sigaddset(&mask, SIGALRM);
    rc = pthread_sigmask(SIG_BLOCK, &mask, NULL);

    if (rc != 0) 
        puts("Sig mask error");

    rc = pthread_create(&signal_tid, NULL, signal_thread, &mask);

    if (rc!= 0)
        puts("Sig thread error");




    struct itimerval timer;
    timer.it_value.tv_sec = 2;
    timer.it_value.tv_usec = 0;
    timer.it_interval.tv_sec = 2;
    timer.it_interval.tv_usec = 0;
    setitimer (ITIMER_REAL, &timer, NULL);


int socket_desc , client_sock , c;
    struct sockaddr_in server , client;
     int sockfd, newsocket, length;
     int port =  8778;
    //Create socket

    socket_desc = socket(AF_INET , SOCK_STREAM , 0);
    if (socket_desc == -1)
    {
        printf("Could not create socket");
    }

    if(setsockopt(socket_desc, SOL_SOCKET, SO_REUSEADDR, &(int) {1}, sizeof(int)) < 0){
        perror("setsockopt failed");
    }

    bzero((char*) &server, sizeof(server));
    server.sin_family = AF_INET;
    server.sin_addr.s_addr = INADDR_ANY;
    server.sin_port =  htons(port);

    //Bind
    if( bind(socket_desc,(struct sockaddr *) &server , sizeof(server)) < 0)
    {
        //print the error message
        perror("bind failed. Error");
        return 1;
    }

    //Listen
    listen(socket_desc , 5);

     length = sizeof(struct sockaddr_in);


    //Accept and incoming connection
    puts("Waiting for incoming connections...");

    pthread_t thread_id;
      while( 1 )
    {
        int * socketPtr = malloc(sizeof(int));
        newsocket = accept(socket_desc, (struct sockaddr *) &client, (socklen_t *) &c);
        if (newsocket == -1) {
            perror("Error at accept..");
        }
        printf("Accepted new client connection!\n");
        socketIds[clientCount++] = newsocket;
        if( pthread_create( &thread_id , NULL ,  handle_connection , &newsocket) < 0)
        {
            perror("could not create thread");
            return 1;
        }


        //Now join the thread , so that we dont terminate before the thread
        //pthread_join( thread_id , NULL);

    }

    if (client_sock < 0)
    {
        perror("accept failed");
        return 1;
    }

    return 0;
}

Итак, ошибка, которую я получаю, происходит здесь:

if (newsocket == -1) {
            perror("Error at accept..");
        }

Ошибка при принятии ..: Распечатан неверный аргумент.

Когда я отключаю эту строку:

rc = pthread_create(&signal_tid, NULL, signal_thread, &mask);

Ошибка прекращается.Я запутался в том, как эта неродственная нить приводит к тому, что мое клиентское соединение с сервером портится.Любая проницательность будет оценена

РЕДАКТИРОВАТЬ: Решено Ty Chris Turner.У меня было неправильное поле в длине аргумента для принятия.Странно, как это работало раньше!

1 Ответ

0 голосов
/ 12 декабря 2018

Вы никогда не присваиваете c разумное значение, поэтому вы передаете случайный мусор accept здесь:

    newsocket = accept(socket_desc, (struct sockaddr *) &client, (socklen_t *) &c);

Это может быть или не быть допустимым значением.Таким образом, последствия этого вызова будут непредсказуемыми.

...