One way of controlling the framework is by writing shell scripts containing special macros. These scripts are supplied as an argument to the tool dynamos_run_commands. This tool will translate the macros and produce a new script with the postfix ".translated.sh" containing the actual calls to the Control Tool.
![]() | The current method of issuing control commands is weak. It does not support retrieving the return value of the control commands to react appropriately (e.g. abort the update on error). It also lacks a macro of defining a group of function updates that should be applied atomically. There are plans to replace this method with a Perl-based library of calls. Control programs will then be written in a more reliable way and in a more powerful language. |
The list of the existing control command macros follows:
DYNREPLACE_REGISTER_INTUITIVELY(update_name, id, function_name)
This macro is used to register updates with the version manager.
By convention, the id is a number indicating the number of parameters the function accepts. Multiple updates may be registered in the version manager with the same update_name but different ids. Such updates would correspond to different routines. And for each <update_name, id> pair, multiple function_names could be registered as the alternate versions of this update. update_names must be enclosed in double(") quotes.
DYNREPLACE_DEREGISTER_FUNCTION(update_name, id, version)
This macro is used to unregister specific versions of updates.
Attempting to unregister version 0 will unregister all versions for the particular <update_name, id> pair.
DYNREPLACE_ACTIVATE_FUNCTION(update_name, id, version)
This macro is used to activate specific versions of updates.
By convention, the original version of an update is version number 1. To deactivate an update, activate version number 1.
DYNREPLACE_SET_PREACTIVATION_HOOK_BY_NAME(update_name, id, version, function_name)
This macro is used to set a hook that will be executed before a particular version of a specific <update_name, id> pair is activated.
DYNREPLACE_SET_POSTACTIVATION_HOOK_BY_NAME(update_name, id, version, function_name)
This macro is used to set a hook that will be executed after a particular version of a specific <update_name, id> pair is activated.
DYNREPLACE_SET_PREREMOVAL_HOOK_BY_NAME(update_name, id, version, function_name)
This macro is used to set a hook that will be executed before a <update_name, id> pair is removed from the version manager.
DYNREPLACE_SET_POSTREMOVAL_HOOK_BY_NAME(update_name, id, version, function_name)
This macro is used to set a hook that will be executed after a <update_name, id> pair is removed from the version manager.
DYNREPLACE_SET_RULE_EVALUATION_FUNCTION_BY_NAME(update_name, id, version, function_name)
This macro is used to define an adaptation handler. There can be only one adaptation handler per <update_name, id> pair.
DYNREPLACE_SET_RULE_EVALUATION_FUNCTION_BY_ADDRESS(update_name, id, version, memory_address)
This macro is also used to define an adaptation handler. Supplying a memory_address of 0 will remove an existing adaptation handler.
DYNREPLACE_CALL(function_name)
This macro is used to invoke an initialization function.
Figure 4-3 shows parts of actual control commands used to enable the Linger-Longer system, adaptive updating of the pipefs implementation, and enable EPCKPT process checkpointing.
Figure 4-3. Example control commands.
# Linger-Longer -- Update the kswapd thread DYNREPLACE_REGISTER_INTUITIVELY("interruptible_sleep_on", 1, interruptible_sleep_on) DYNREPLACE_REGISTER_INTUITIVELY("interruptible_sleep_on", 1, interruptible_sleep_on_v2) DYNREPLACE_ACTIVATE_FUNCTION("interruptible_sleep_on", 1, 2) DYNREPLACE_REGISTER_INTUITIVELY("kswapd", 1, kswapd) DYNREPLACE_REGISTER_INTUITIVELY("kswapd", 1, kswapd_ll) DYNREPLACE_SET_PREACTIVATION_HOOK_BY_NAME("kswapd", 1, 1, kswapd_pre_activation_hook) DYNREPLACE_SET_POSTACTIVATION_HOOK_BY_NAME("kswapd", 1, 1, kswapd_post_activation_hook) DYNREPLACE_SET_PREACTIVATION_HOOK_BY_NAME("kswapd", 1, 2, kswapd_ll_pre_activation_hook) DYNREPLACE_SET_POSTACTIVATION_HOOK_BY_NAME("kswapd", 1, 2, kswapd_ll_post_activation_hook) DYNREPLACE_ACTIVATE_FUNCTION("kswapd", 1, 2) # pipefs -- create an adaptation handler DYNREPLACE_REGISTER_INTUITIVELY("pipe_read", 4, pipe_read) DYNREPLACE_REGISTER_INTUITIVELY("pipe_read", 4, pipe_read_v2) DYNREPLACE_REGISTER_INTUITIVELY("pipe_read", 4, pipe_read_v3) DYNREPLACE_ACTIVATE_FUNCTION("pipe_read", 4, 2) DYNREPLACE_SET_RULE_EVALUATION_FUNCTION_BY_NAME("pipe_read", 4, pipe_adaptation_handler_read_or_write) # Disable the adaptation handler DYNREPLACE_SET_RULE_EVALUATION_FUNCTION_BY_ADDRESS("pipe_write", 4, 0) DYNREPLACE_SET_RULE_EVALUATION_FUNCTION_BY_ADDRESS("pipe_read", 4, 0) # Unregister some functions DYNREPLACE_DEREGISTER_FUNCTION("pipe_write", 4, 0) DYNREPLACE_DEREGISTER_FUNCTION("pipe_read", 4, 0) DYNREPLACE_DEREGISTER_FUNCTION("pipe_release", 3, 0) # EPCKPT -- Set a preremoval hook DYNREPLACE_SET_PREREMOVAL_HOOK_BY_NAME("restart_binary", 2, epckpt_cleanup) # Invoke an initialization function DYNREPLACE_CALL(epckpt_init)