Владение глобальными ресурсами после форка - PullRequest
2 голосов
/ 16 октября 2019

Рассмотрим Foo, который содержит некоторый ресурс

struct Foo
    {
    ~Foo();
    };

и глобальный std::vector<Foo>. Возможно, глупый пример, но он хорошо иллюстрирует проблему.

std::vector<Foo> bar;

Теперь процессы fork s.

Если bar изменяется толькодочерний процесс, а затем вызов exit должен быть правильным в дочернем процессе. При вызове _exit любой Foo: s в баре будет просачиваться. Если родитель добавил некоторые вещи в bar до разветвления, эти объекты могут быть уничтожены дважды. Или, может быть, это не проблема, потому что они должны рассматриваться как разные объекты.

Как правильно обращаться с временем жизни объекта вместе с fork. Является ли единственным разумным способом решения этих проблем позволить ребенку exec и начать все сначала?

Я должен заметить, что на этом этапе в программе гарантированно будет только один поток.

Ответы [ 2 ]

1 голос
/ 16 октября 2019

Как правильно обращаться с временем жизни объекта вместе с fork?

Правильный способ обработки общих ресурсов при разветвлении зависит от того, что это за объекты или ресурсы.

Для любого объекта или переменной в памяти процесса вы автоматически получаете копию его после разветвления. Каждый процесс сможет затем изменить или уничтожить любую переменную , не затрагивая другой процесс. Это также означает, что каждый процесс отвечает за очистку своей уникальной копии ресурса.


Для других ресурсов, которые существуют вне процесса, таких как файл, веб-сокет илиОбщая память;Лучший способ справиться с ними будет зависеть от того, что это за ресурс. Обычно эти рекомендации будут описаны в библиотеке / API, которые вы используете для первоначального создания этих ресурсов.

0 голосов
/ 16 октября 2019

Как только вы fork отредактируете, ваши переменные будут иметь семантику copy-on-write , поэтому любые изменения дочернего процесса приводят к уникальным переменным для дочернего элемента, который не используется совместно с родителем. Аналогичным образом, изменения в родительском процессе приведут к тому, что дочерний объект получит новые копии и не будет размножаться, поэтому родительский процесс может пойти до exit, не прерывая дочерний процесс. Я сделал это для реализации самообновляющейся программы.

Обратите внимание, что, как указано в других ответах, «глобальные ресурсы» следует обрабатывать в каждом конкретном случае, но переменные не являются глобальными ресурсами.

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