[erlang-questions] how to _cause_ a code_change in a gen_fsm

Robert Virding robert.virding@REDACTED
Sun Nov 27 02:25:28 CET 2011


That is basically how it is done internally as well. You would need to load in the new version of the module *after* you have suspended the FSM and before you call sys:change_code/4. If you have many FSMs using the same module then the would have to:

- suspend all the FSM processes with sys:suspend/1
- reload the module
- call sys:change_code/4 on all the FSM processes
- resume all the FSM processes with sys:resume/1

You could do change_code/resume per process to get some of the FSMs back and running faster.

Robert

----- Original Message -----
> Hi Daniel,
> 
> I had to solve a similar problem some time ago. I needed a way to
> force supervisors to reload the child specifications, which it does
> in
> supervisor:code_change/3. It is possible to fake what the reltool
> does, by manually suspending, forcing code change and then resuming
> the process.
> 
> I use the following hack:
> 
>     ok = sys:suspend(Pid),
>     ok = sys:change_code(Pid, Mod, Vsn, []),
>     ok = sys:resume(Pid),
> 
> Which I admit is very naive as it doesn't take into account something
> going wrong in sys:change_code/4.
> 
> Regards
> Knut
> 
> On Sat, Nov 26, 2011 at 6:01 PM, Daniel Dormont
> <dan@REDACTED> wrote:
> > Ok. So what is the "right" way to get my code_change callback to
> > fire?
> > I see some reference to "appup" and I have looked over that part of
> > the manual but don't really understand how it applies to my case.
> > Literally all I have is a .beam file I want to install in a running
> > system.
> >
> > dan
> >
> > On Sat, Nov 26, 2011 at 10:28 AM, Bob Ippolito <bob@REDACTED>
> > wrote:
> >> I don't know how ejabberd likes to do things but l() is the lower
> >> level
> >> non-OTP way to do things and will immediately purge the old code
> >> and load
> >> the new code. Nothing else will happen, no magic.
> >>
> >> On Friday, November 25, 2011, Daniel Dormont
> >> <dan@REDACTED>
> >> wrote:
> >>> This is a follow-up to my earlier question but the topic is a
> >>> little
> >>> different. Having put together a nice piece of code for handling
> >>> the
> >>> change in my gen_fsm's state record, I discovered to my chagrin
> >>> that
> >>> when I loaded the new code (using l() at first and then using the
> >>> "update" command that comes with ejabberd) it did not call the
> >>> code_change callback; neither immediately nor before processing
> >>> the
> >>> next message sent to that process. I admit that the details of
> >>> things
> >>> like proc_lib and sys are a little opaque to me, but I had
> >>> understood
> >>> that as long as the module implemented a standard OTP behavior,
> >>> code
> >>> upgrades would "just work" in some sense. I suppose I was wrong
> >>> :)
> >>> This module is fairly self-contained, so I'm not too worried
> >>> about
> >>> having to synchronize other modules, notify supervisors or
> >>> anything
> >>> like that. How do I proceed from here?
> >>>
> >>> thanks,
> >>> dan
> >>>
> >>>
> >>> ---------- Forwarded message ----------
> >>> From: Daniel Dormont <dan@REDACTED>
> >>> Date: Mon, Nov 21, 2011 at 10:51 AM
> >>> Subject: code_change for gen_fsm: how to actually handle a state
> >>> change
> >>> To: erlang-questions <erlang-questions@REDACTED>
> >>>
> >>>
> >>> Hello all,
> >>>
> >>> I have a gen_fsm module and would like to take advantage of hot
> >>> code
> >>> deploy. The module uses a record (called "state") and the new
> >>> version
> >>> of the module includes some new fields in the record. What is a
> >>> nice
> >>> clean way to code the my_module:code_change function to deal with
> >>> this? Are there any good examples out there on the web?
> >>>
> >>> Note: for my purposes it would be sufficient to detect that the
> >>> state
> >>> record is out of date, and terminate cleanly. BUT the correct
> >>> functionality of the terminate/3 function in my module depends on
> >>> the
> >>> state data, and I would need it to complete cleanly and not crash
> >>> in
> >>> this instance because there are other processes that depend on
> >>> this
> >>> one and need to be notified properly of its exit. The issue is
> >>> that
> >>> the state itself contains the data of which processes those are.
> >>>
> >>> What's the best approach here?
> >>>
> >>> thanks,
> >>> Dan
> >>> _______________________________________________
> >>> erlang-questions mailing list
> >>> erlang-questions@REDACTED
> >>> http://erlang.org/mailman/listinfo/erlang-questions
> >>>
> > _______________________________________________
> > erlang-questions mailing list
> > erlang-questions@REDACTED
> > http://erlang.org/mailman/listinfo/erlang-questions
> >
> _______________________________________________
> erlang-questions mailing list
> erlang-questions@REDACTED
> http://erlang.org/mailman/listinfo/erlang-questions
> 



More information about the erlang-questions mailing list