как в Erlang организовать "заморозку" процессов и буферов сообщений?
встроенных средств в Erlang для этого нет, библиотеки для выгрузки буфера сообщений по процессу нет — или я просто их не нашел?
тогда единственное, что приходит в голову — это обертка над отправкой/получением сообщений для занесения/удаления их в mnesia...
насколько я понимаю, полная "заморозка"(по типу ООП в clos) процессов и сообщений невозможна, но по крайней мере сообщения, число процессов?
Re: [Erlang]заморозка процессов?
От:
Аноним
Дата:
25.05.07 06:01
Оценка:
заморозка — т.е. сохранение состояния на жесткий диск с последующим восстановлением(насколько это возможно, полным)
Здравствуйте, Аноним, Вы писали:
А>как в Erlang организовать "заморозку" процессов и буферов сообщений? А>встроенных средств в Erlang для этого нет, библиотеки для выгрузки буфера сообщений по процессу нет — или я просто их не нашел? А>тогда единственное, что приходит в голову — это обертка над отправкой/получением сообщений для занесения/удаления их в mnesia... А>насколько я понимаю, полная "заморозка"(по типу ООП в clos) процессов и сообщений невозможна, но по крайней мере сообщения, число процессов?
Есть функция erlang:hibernate(Mod,Fun,Arg). Как раз освобождает место в памяти занимаемое процессом. Используется при большом количестве долгоживущих процессов. При получении первого сообщения процесс возобновляется с вызовом указанной функции и параметров. Правда, если есть необработанные сообщения, то процесс проснется тут же, так что может потребоваться какая-то очистка или сохранение сообщений в очереди.
--
Mikl
Re[2]: [Erlang]заморозка процессов?
От:
Аноним
Дата:
25.05.07 07:23
Оценка:
MK>Есть функция erlang:hibernate(Mod,Fun,Arg). Как раз освобождает место в памяти занимаемое процессом.
нет, нужно сбрасывать состояние процессов на жесткий диск с последующим восстановлением. такая возможность есть для с++(sl, кажется), есть для clos, есть и в eiffel. хочется того же и в erlang.
Здравствуйте, Аноним, Вы писали:
А>как в Erlang организовать "заморозку" процессов и буферов сообщений? А>встроенных средств в Erlang для этого нет, библиотеки для выгрузки буфера сообщений по процессу нет — или я просто их не нашел? А>тогда единственное, что приходит в голову — это обертка над отправкой/получением сообщений для занесения/удаления их в mnesia...
Можно сделать примерно так. Псевдокод — для иллюстрации идеи:
так сохраняем очередь сообщений
freeze() ->
receive
M -> save_to_disk( M ),
freeze();
after 0 -> done;
end.
а так восстанавливаем
restore() ->
case read_from_disk() of
{ message, M } -> self() ! M;
eof -> done;
end.
А>насколько я понимаю, полная "заморозка"(по типу ООП в clos) процессов и сообщений невозможна, но по крайней мере сообщения, число процессов?
Возможна — но тебе надо кроме очереди сообщений сохранить состояние процесса, которое он передает себе в бесконечной рекурсии.
process_loop( State ) ->
...
process_loop( State ).
А еще — тебе надо остановить все процессы перед процедурой, чтобы они перестали посылать новые сообщения. То есть, надо всем процессам послать сообщение freeze, при получении которого они войдут в режим сохранения (перестав посылать рабочие сообщения), и только после того, как все процессы вошли в этот режим, можно инициировать сохранение процессов отдельным сообщением.
Здравствуйте, Gaperton, Вы писали:
G>А еще — тебе надо остановить все процессы перед процедурой, чтобы они перестали посылать новые сообщения. То есть, надо всем процессам послать сообщение freeze, при получении которого они войдут в режим сохранения (перестав посылать рабочие сообщения), и только после того, как все процессы вошли в этот режим, можно инициировать сохранение процессов отдельным сообщением.
И это еще не все. Боюсь, что в распределенной системе нельзя будет пи этой схеме гарантировать, что нет сообщений, затерявшихся в пути. Здесь надо как следует подумать, как не потерять сообщений при записи. Для частного случая эти задачи решаемы. В общем случае — тяжело.
Re[3]: [Erlang]заморозка процессов?
От:
Аноним
Дата:
25.05.07 13:40
Оценка:
G>И это еще не все. Боюсь, что в распределенной системе нельзя будет пи этой схеме гарантировать, что нет сообщений, затерявшихся в пути.
типа transactions in Limbo.. Мда..
а насчет остановки — м.б. самое простое сделать это через обновление кода на лету ?
Меняем function (x,y,z) -> do something на "обновленную" версию function (x,y,z) -> save_xyz, halt; ?
Здравствуйте, Аноним, Вы писали:
G>>И это еще не все. Боюсь, что в распределенной системе нельзя будет пи этой схеме гарантировать, что нет сообщений, затерявшихся в пути.
А>типа transactions in Limbo.. Мда..
А>а насчет остановки — м.б. самое простое сделать это через обновление кода на лету ? А>Меняем function (x,y,z) -> do something на "обновленную" версию function (x,y,z) -> save_xyz, halt; ?
Не, это как-то жестко. Вообще — разумно написать behaviour для процесса, который может сохраняться. Тогда всю логику по остановке, сохранению, и восстановлению можно спрятать туда. За основу имеет смысл взять gen_server — в него вполне можно добавить нужную логику. Например, потому, что при реализации этого бехэвиора не принято крутить рекурсивные функции — надо возвращать управление. Во-вторых, там уже сделаны обертки для приема и посылки сообщений. Короче, изучи gen_server повнимательнее, и дальше разберешься, как делать.
Здравствуйте, Gaperton, Вы писали:
G>Здравствуйте, Gaperton, Вы писали:
G>>А еще — тебе надо остановить все процессы перед процедурой, чтобы они перестали посылать новые сообщения. То есть, надо всем процессам послать сообщение freeze, при получении которого они войдут в режим сохранения (перестав посылать рабочие сообщения), и только после того, как все процессы вошли в этот режим, можно инициировать сохранение процессов отдельным сообщением.
G>И это еще не все. Боюсь, что в распределенной системе нельзя будет пи этой схеме гарантировать, что нет сообщений, затерявшихся в пути. Здесь надо как следует подумать, как не потерять сообщений при записи. Для частного случая эти задачи решаемы. В общем случае — тяжело.
Это еще далеко не все. Кроме состояния, которое болтается в хвостовой рекурсии нашего процесса и майлбокса с сообщениями, есть еще много чего: данные в словаре процесса — ну, их можно сохранить, если не забыть; данные в ets-таблицах — надо не забыть тоже; сами ets-таблицы, которыми владеет процесс — тут сложнее, при "разморозке" надо как-то восстанавливать идентификатор таблицы, что не всегда возможно; есть линки и мониторы — что с ними делать, ума не приложу.
Думаю, что надо наложить какие-то разумные ограничения и решать задачу для частного случая.
Здравствуйте, Изя Рнет, Вы писали:
ИР>Здравствуйте, Gaperton, Вы писали:
G>>Здравствуйте, Gaperton, Вы писали:
G>>>А еще — тебе надо остановить все процессы перед процедурой, чтобы они перестали посылать новые сообщения. То есть, надо всем процессам послать сообщение freeze, при получении которого они войдут в режим сохранения (перестав посылать рабочие сообщения), и только после того, как все процессы вошли в этот режим, можно инициировать сохранение процессов отдельным сообщением.
G>>И это еще не все. Боюсь, что в распределенной системе нельзя будет пи этой схеме гарантировать, что нет сообщений, затерявшихся в пути. Здесь надо как следует подумать, как не потерять сообщений при записи. Для частного случая эти задачи решаемы. В общем случае — тяжело.
ИР>Это еще далеко не все. Кроме состояния, которое болтается в хвостовой рекурсии нашего процесса и майлбокса с сообщениями, есть еще много чего: данные в словаре процесса — ну, их можно сохранить, если не забыть; данные в ets-таблицах — надо не забыть тоже; сами ets-таблицы, которыми владеет процесс — тут сложнее, при "разморозке" надо как-то восстанавливать идентификатор таблицы, что не всегда возможно; есть линки и мониторы — что с ними делать, ума не приложу.
Кстати, да. Это можно обобщить как "ресурсы процесса" — ну, типа, добавить сюда же открытые файлы, сокеты, и прочее. Чтоб жизнь совсем медом не казалась, и стало ясно, что в общем случае задача не решаема.
ИР>Думаю, что надо наложить какие-то разумные ограничения и решать задачу для частного случая.
Именно так. Я бы модифицировал бехавиорс gen_server и добавил туда два коллбка save/restore, в которых пользователь может обраоботать ручками сам любую "грязь" — такую как ets-таблицы и прочее.
Здравствуйте, Gaperton, Вы писали:
G>Здравствуйте, Изя Рнет, Вы писали:
ИР>>Здравствуйте, Gaperton, Вы писали:
G>>>Здравствуйте, Gaperton, Вы писали:
G>>>>А еще — тебе надо остановить все процессы перед процедурой, чтобы они перестали посылать новые сообщения. То есть, надо всем процессам послать сообщение freeze, при получении которого они войдут в режим сохранения (перестав посылать рабочие сообщения), и только после того, как все процессы вошли в этот режим, можно инициировать сохранение процессов отдельным сообщением.
...
ИР>>Думаю, что надо наложить какие-то разумные ограничения и решать задачу для частного случая. G>Именно так. Я бы модифицировал бехавиорс gen_server и добавил туда два коллбка save/restore, в которых пользователь может обраоботать ручками сам любую "грязь" — такую как ets-таблицы и прочее.
Угу. Начинать от gen_server'а — разумный шаг хотя бы потому, что gen_server уже умеет suspend/resume для целей смены кода. На самом деле это умеют все OTP процессы (см. модуль sys).