mirror of
https://github.com/asterisk/asterisk.git
synced 2025-09-03 11:25:35 +00:00
loader.c: Allow dependent modules to be unloaded recursively.
Because of the (often recursive) nature of module dependencies in Asterisk, hot swapping a module on the fly is cumbersome if a module is depended on by other modules. Currently, dependencies must be popped manually by unloading dependents, unloading the module of interest, and then loading modules again in reverse order. To make this easier, the ability to do this recursively in certain circumstances has been added, as an optional extension to the "module refresh" command. If requested, Asterisk will check if a module that has a positive usecount could be unloaded safely if anything recursively dependent on it were unloaded. If so, it will go ahead and unload all these modules and load them back again. This makes hot swapping modules that provide dependencies much easier. Resolves: #474 UserNote: In certain circumstances, modules with dependency relations can have their dependents automatically recursively unloaded and loaded again using the "module refresh" CLI command or the ModuleLoad AMI command.
This commit is contained in:
committed by
asterisk-org-access-app[bot]
parent
b267629b77
commit
01ff5c8140
29
main/cli.c
29
main/cli.c
@@ -807,30 +807,35 @@ static char *handle_logger_mute(struct ast_cli_entry *e, int cmd, struct ast_cli
|
||||
|
||||
static char *handle_refresh(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
|
||||
{
|
||||
static const char * const completions[] = { "recursively", NULL };
|
||||
int res;
|
||||
/* "module refresh <mod>" */
|
||||
switch (cmd) {
|
||||
case CLI_INIT:
|
||||
e->command = "module refresh";
|
||||
e->usage =
|
||||
"Usage: module refresh <module name>\n"
|
||||
" Unloads and loads the specified module into Asterisk.\n";
|
||||
"Usage: module refresh <module name> [recursively]\n"
|
||||
" Unloads and loads the specified module into Asterisk.\n"
|
||||
" 'recursively' will attempt to unload any modules with\n"
|
||||
" dependencies on this module for you and load them again\n"
|
||||
" afterwards.\n";
|
||||
return NULL;
|
||||
|
||||
case CLI_GENERATE:
|
||||
if (a->pos != e->args) {
|
||||
return NULL;
|
||||
if (a->pos == e->args) {
|
||||
return ast_module_helper(a->line, a->word, a->pos, a->n, a->pos, AST_MODULE_HELPER_UNLOAD);
|
||||
} else if (a->pos == e->args + 1) {
|
||||
return ast_cli_complete(a->word, completions, a->n);
|
||||
}
|
||||
return ast_module_helper(a->line, a->word, a->pos, a->n, a->pos, AST_MODULE_HELPER_UNLOAD);
|
||||
return NULL;
|
||||
}
|
||||
if (a->argc != e->args + 1) {
|
||||
if (a->argc < 3 || a->argc > 4) {
|
||||
return CLI_SHOWUSAGE;
|
||||
}
|
||||
if (ast_unload_resource(a->argv[e->args], AST_FORCE_SOFT)) {
|
||||
ast_cli(a->fd, "Unable to unload resource %s\n", a->argv[e->args]);
|
||||
return CLI_FAILURE;
|
||||
}
|
||||
if (ast_load_resource(a->argv[e->args])) {
|
||||
ast_cli(a->fd, "Unable to load module %s\n", a->argv[e->args]);
|
||||
|
||||
res = ast_refresh_resource(a->argv[e->args], AST_FORCE_SOFT, a->argc == 4 && !strcasecmp(a->argv[3], "recursively"));
|
||||
if (res) {
|
||||
ast_cli(a->fd, "Unable to %s resource %s\n", res > 0 ? "unload" : "load", a->argv[e->args]);
|
||||
return CLI_FAILURE;
|
||||
}
|
||||
ast_cli(a->fd, "Unloaded and loaded %s\n", a->argv[e->args]);
|
||||
|
Reference in New Issue
Block a user