SIGINT при выполнении std :: thread :: join () - PullRequest
0 голосов
/ 01 февраля 2012

У меня есть main(), который порождает поток, а затем присоединяется к нему. Я хочу иметь возможность CTRL-C программы, поэтому я установил бы обработчик SIGINT в main (поток порождения игнорирует этот сигнал). Когда я нахожусь в sig-handler, я отменю порожденный поток с cancel(), но что происходит с текущим 'join ()', который был активен во время вызова сигнала. Я предполагаю, что я получу EAGAIN или EINTR, и мне придется сделать join() в цикле. Я прав? Спасибо.

Вопрос в том, законно ли это с многопоточностью. Я не против установить флаг с помощью ручки SIGINT, но что происходит с вызовом join()?

Ответы [ 2 ]

2 голосов
/ 01 февраля 2012

Сигналы и темы? Здесь будут драконы! Вы должны полностью указать маски , иначе любой поток может получить сигнал .

Обработчик сигнала обычно не должен предполагать, что он работает в "основном" потоке. Скорее, он должен опубликовать сообщение и вернуть, аналогично прерыванию потока . Основной поток может забрать это позже в цикле событий или в любом другом месте и затем присоединиться.

1 голос
/ 01 февраля 2012

std::thread::join() имеет тип возврата void, поэтому не может вернуть EINTR. На платформах POSIX это, вероятно, обертка вокруг pthread_join, которая не возвращает EINTR. Присоединение к потоку не должно возвращать или выбрасывать до тех пор, пока поток не будет успешно присоединен к нему, при условии, что он вызывается для присоединяемого потока.

Кроме того, может быть небезопасно отменить поток из обработчика сигнала. std::thread не имеет cancel() функции-члена, поэтому я предполагаю, что вы написали свою собственную. Поэтому вам необходимо убедиться, что это безопасно для использования в обработчике сигналов --- pthread_cancel() не указан в качестве функции, которую можно безопасно вызывать из обработчика сигналов , например.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...