Поток не создан, несмотря на успех при возврате из pthread_create()

#c #linux #pthreads #posix

#c #linux #pthreads #posix

Вопрос:

Я написал довольно много многопоточного кода на HP-UX и даже SUSE, и это работает отлично. Но это не работает на Red Hat. Это моя машина:

Версия Linux 3.10.0-1062.18.1.el7.x86_64 (Red Hat 4.8.5-39)

Red_Hat_Enterprise_Linux-Release_Notes-7-en-US-7-2.el7.noarch

redhat-release-server-7.7-10.el7.x86_64

Я написал простую тестовую программу thr_ex.c:

 #include <pthread.h>
#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <string.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>



void *funny(void *);



void *funny(s)
void *s;

{ 
    int fd;


    fd = creat("/tmp/funny_func", 0600);

    write(fd, s, strlen((char *) s));

    close(fd);
}



int main()

{
    int                 return_value;
    pthread_t           thread_id;
    pthread_attr_t      thread_attr;


    pthread_attr_init(amp;thread_attr);
    pthread_attr_setscope(amp;thread_attr, PTHREAD_SCOPE_SYSTEM);
    pthread_attr_setdetachstate(amp;thread_attr, PTHREAD_CREATE_DETACHED);

    return_value = pthread_create(amp;thread_id, amp;thread_attr, funny, (void *) "Here I amn");

    printf("Return value == %dn", return_value);
    printf("Thread id    == %hun", thread_id);

    exit(0);
} /* End main. */
  

Компиляция, сборка:

gcc -pthread -s -o thr_ex thr_ex.c

Выполняется:

./thr_ex

Возвращаемое значение == 0

Идентификатор потока == 5888

Но ни один файл не создается в /tmp. strace -f не показывает creat() или write() (кроме как из printf в main () ) .

Однако strace -f показывает, например: strace: выход неизвестного pid 64574 игнорируется

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

Комментарии:

1. Где вы нашли этот пример с древним определением аргумента функции K amp; R?

2. Что касается вашей проблемы, вы никогда не ждете завершения потока. Вместо этого вы завершаете процесс сразу после создания потока (что означает, что у него может даже не быть времени для запуска).

3. @Anders Вставьте pthread_exit( NULL); перед возвратом.

4. Чтобы уточнить, когда процесс завершается (с exit(0) ), все потоки процесса заканчиваются с ним. Чтобы отдельные потоки (и сам процесс) выполнялись в «фоновом режиме», выйдите только из «основного потока» (используя pthread_exit вместо exit ).

5. В качестве альтернативы, оставьте второй поток присоединяемым и присоединитесь к нему перед exit() запуском программы.

Ответ №1:

Вставить перед оператором return или exit( 0) в main

 pthread_exit( NULL );
  

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

Комментарии:

1. Другими словами, в программе есть условия гонки между всем, что выполняется вторым потоком, и exit(0) тем, что выполняется основным потоком.

2. @JohnBollinger Точно, спасибо. Я просто подумал, что у второго потока будет время выполнить хотя бы несколько раз из всех выполненных мной тестов.