LINUX.ORG.RU

Interrupted system call


0

0

Проблема с созданием потоков: в программе время от времени требуется создать поток, потоковая функция имеет линейный алгоритм и поток завершается по выходу из неё. Для создания потока использую pthread_create:

pthread_t child; if (pthread_create(&child,NULL,&Child,&params)!=0) { perror ("pthread error"); } Простой тест: запускаю создание потока в цикле с интервалом в треть секунды. Потоковая функция выводит одну строку на stdout и завершается. Поначалу всё идёт хорошо, но на 1020 попытке pthread_create возвращает ошибку: "Interrupted system call"!!! Что это и как это обойти? Очень буду признателен за помощь! : )

anonymous

Забыл уточнить: компилятор - gcc 2.96, ядро - 2.4.18.-3, дистриб - Red Hat Linux 7.3 Помогите,очень нужно!

anonymous
()

В том примере, который приведен, есть один не очень хороший момент. По-умолчанию (когда указатель на атрибуты NULL), поток создается JOINABLE, т.е. часть его ресурсов не освобождается после завершения, пока какой-нибудь другой поток не сделает pthread_join. Не уверен, что описанная проблема связана именно с этим, но данный момент, в любом случае, нельзя оставлять без внимания.

AVI
()

можешь попробовать перед созданием нитки игнорировать все сигналы

lg ★★
()

Вообще-то странно, ни одна функция типа pthread_* не устанавливает errno, поэтому perror печатает не то, что относится к pthread_create. Правильнее делать: if (( retError = pthread_create(&child,NULL,&Child,&params) )!=0) { fprintf( stderr, "pthread error: ", strerror( retError )); }

AVI
()

Попробуй поэкспериментировать с ulimit -u.

Ну и ловить все сигналы - в обработчике, скажем, открывать отладочный терминал и писать туда номер (FILE *f = fopen ("/dev/tty12", "w+"); fprintf (f, ...);) - хоть узнаешь что за сигнал.

Murr ★★
()

Сделал ,как мне предложил AVI и на 1020 цикле прочитал такое сообщение: Operation not Permitted. Даже и не знаю ,что подумать... А с NULL сейчас пока экспериментирую...

anonymous
()

Это значит, что pthread_create вернул код ошибки 1 (EPERM - The caller does not have appropriate permission to set the required scheduling parameters or scheduling policy). Странно как-то, усли указатель на атрибуты NULL. А если ps посмотреть, сколько потоков он показывает?

AVI
()

Ура!!! Получилось!!! Дело действительно оказалось в атрибутах ! PTHREAD_CREATE_JOINABLE не прёт. Перед вызовом pthread_create я проинициализировал атрибуты потока:

pthread_attr_t attr; patt=pthread_attr_init(&attr); pthread_attr_setdetachstate(&attr,PTHREAD_CREATE_DETACHED);

потом запустил цикл и всё замечательно. Спасибо всем!

anonymous
()

Значит они у тебя завершаются очень быстро. В первом случае просто срабатывало ограничение PTHREAD_MAX_THREADS=1024.

Murr ★★
()

Честно говоря,не совсем понял, что это значит. В списке процессов одновременно висело не более одного потока этой проги, но тем не менее в 1024- ый раз он не создавался.Получается, что это ограничеие действует вообще на количество вызовов pthread_create, я его просто обнулил при инициализации атрибутов, и PTHREAD_CREATE_JOINABLE тут ни при чём?

anonymous
()

Прошу прощения, я только что сморозил полную херню, я совсем не то хотел сказать!

anonymous
()

Если поток JOINABLE, то после его завершения остается часть ресурсов, в частности возвращаемое значение. Эти ресурсы высвобождаются после вызова pthread_join, которая принимает в качестве параметра id уже "завершенного" потока, т.е. система его хранит в списке и это, по-моему, приводит к "мнимому" превышению количества потоков.

AVI
()
Ответ на: комментарий от anonymous

У тебя есть пул нитей в 1024. Больше нельзя. Пока ты не ждешь joinable - они занимают слот. Если ты создаешь detached, то после выхода слот освобождается.

P.S. тем не менее, если ты в цикле создаешь 1024 нити и к созданию последней ни одна не завершится, то ты опять получить ошибку...

Murr ★★
()
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.