процесс fork + exec с поврежденными потоками на macOS?- процесс детей застрял в _atfork_child - PullRequest
0 голосов
/ 24 сентября 2019

У нас есть несколько большее C ++ приложение для macOS.Это приложение в какой-то момент имеет несколько потоков, которые вызывают fork и почти сразу после этого exec.Между fork и exec нет ничего особенного, только некоторые dup2 и close труб, без блокировок, без динамического выделения.Другие потоки родительского процесса могут выполнять некоторое динамическое распределение при вызове fork, но я подумал, что это не должно иметь значения.

Иногда мы видим, что после fork дочерний процесс даже не просыпается отfork, он долго зависает, и когда мы подключаем к нему отладчик, мы видим следующую трассировку стека:

* thread #1, stop reason = signal SIGSTOP
  * frame #0: 0x00007fff79e0234a libsystem_kernel.dylib`syscall_thread_switch + 10
    frame #1: 0x00007fff79e7926a libsystem_malloc.dylib`tiny_malloc_should_clear + 547
    frame #2: 0x00007fff79e78f96 libsystem_malloc.dylib`szone_malloc_should_clear + 66
    frame #3: 0x00007fff79e7a188 libsystem_malloc.dylib`malloc_zone_calloc + 99
    frame #4: 0x00007fff79e7a108 libsystem_malloc.dylib`calloc + 30
    frame #5: 0x00007fff79da4a62 libsystem_coreservices.dylib`_dirhelper_init + 460
    frame #6: 0x00007fff79eafacb libsystem_platform.dylib`_os_once_callout + 18
    frame #7: 0x00007fff79da5ebb libsystem_coreservices.dylib`_libcoreservices_fork_child + 52
    frame #8: 0x00007fff76a1bb09 libSystem.B.dylib`libSystem_atfork_child + 39
    frame #9: 0x00007fff79d26d97 libsystem_c.dylib`fork + 40
...

Так что, если я правильно понимаю, дочерний процесс даже не вернулся изfork.

AFAIK наше приложение не делает ничего особенного, например, установку пользовательских обработчиков atfork и тому подобное.Мы не используем Objective C.Я думал, что это новое поведение форка для Objective C может быть причиной, поэтому мы попытались отключить это (добавив раздел __DATA,__objc_fork_ok), но проблема все еще появляется.

Есть ли здесь кто-нибудьидея, что может быть причиной?

Пока что кажется, что fork в многопоточной среде просто сломан на macOS.Эта проблема не случается слишком часто, просто иногда - чем больше это раздражает.Я не уверен, что может быть не так с нашей стороны - когда дочерний процесс продолжает зависать в системном коде, он даже не может выполнить наш код.

Одна идея - возможно, что fork получитвызывается одновременно из нескольких потоков.Может ли это вызвать проблемы, может только один поток за один раз позвонить fork?

Спасибо за любые мысли.

...