diff --git a/CHANGES b/CHANGES index 1753be663959a6258364b7f9d13b4cb8fca3e807..1609e506e6130f49654f45117c19b763b78114c7 100644 --- a/CHANGES +++ b/CHANGES @@ -104,6 +104,12 @@ Core for DNS functionality. Modules that use this functionality will require that a DNS resolver module is loaded and available. + * Modified processing of command-line options to first parse only what + is necessary to read asterisk.conf. Once asterisk.conf is fully loaded, + the remaining options are processed. The -X option now applies to + asterisk.conf only. To enable #exec for other config files you must + set execincludes=yes in asterisk.conf. Any other option set on the + command-line will now override the equivalent setting from asterisk.conf. Functions ------------------ diff --git a/UPGRADE.txt b/UPGRADE.txt index d9d5cec5330473687bac4327c1e785e0a0e8a1cb..91d9edc924932eaf5edbb93a79c981579cd07215 100644 --- a/UPGRADE.txt +++ b/UPGRADE.txt @@ -36,6 +36,13 @@ Core: The setting can be overridden in asterisk.conf by setting refdebug in the options category. No recompile is required to enable/disable it. + - Modified processing of command-line options to first parse only what + is necessary to read asterisk.conf. Once asterisk.conf is fully loaded, + the remaining options are processed. The -X option now applies to + asterisk.conf only. To enable #exec for other config files you must + set execincludes=yes in asterisk.conf. Any other option set on the + command-line will now override the equivalent setting from asterisk.conf. + AMI: - The 'ModuleCheck' Action's Version key will no longer show the module version. The value will always be blank. diff --git a/doc/asterisk.8 b/doc/asterisk.8 index d566480f27981eba9eb15b7b68d5403726d93b7d..3f49a3401a8024637eddf900bd0604aeaaabf94c 100644 --- a/doc/asterisk.8 +++ b/doc/asterisk.8 @@ -232,9 +232,8 @@ then terminating when the command execution completes. Implies supplied. .TP \-X -Enables executing of includes via \fB#exec\fR directive. -This can be useful if You want to do \fB#exec\fR inside -\*(T<\fIasterisk.conf\fR\*(T> +Enables executing of includes via \fB#exec\fR directive inside +\*(T<\fIasterisk.conf\fR\*(T>. .SH EXAMPLES \fBasterisk\fR - Begin Asterisk as a daemon .PP diff --git a/include/asterisk/options.h b/include/asterisk/options.h index a08b8638c3a0c0209eadb8f8385111d2ff26a7da..e2709f9188f0b3362d18146bfbaf37e38d474626 100644 --- a/include/asterisk/options.h +++ b/include/asterisk/options.h @@ -66,8 +66,6 @@ enum ast_option_flags { AST_OPT_FLAG_CACHE_RECORD_FILES = (1 << 13), /*! Display timestamp in CLI verbose output */ AST_OPT_FLAG_TIMESTAMP = (1 << 14), - /*! Override config */ - AST_OPT_FLAG_OVERRIDE_CONFIG = (1 << 15), /*! Reconnect */ AST_OPT_FLAG_RECONNECT = (1 << 16), /*! Transmit Silence during Record() and DTMF Generation */ @@ -119,7 +117,6 @@ enum ast_option_flags { #define ast_opt_dump_core ast_test_flag(&ast_options, AST_OPT_FLAG_DUMP_CORE) #define ast_opt_cache_record_files ast_test_flag(&ast_options, AST_OPT_FLAG_CACHE_RECORD_FILES) #define ast_opt_timestamp ast_test_flag(&ast_options, AST_OPT_FLAG_TIMESTAMP) -#define ast_opt_override_config ast_test_flag(&ast_options, AST_OPT_FLAG_OVERRIDE_CONFIG) #define ast_opt_reconnect ast_test_flag(&ast_options, AST_OPT_FLAG_RECONNECT) #define ast_opt_transmit_silence ast_test_flag(&ast_options, AST_OPT_FLAG_TRANSMIT_SILENCE) #define ast_opt_dont_warn ast_test_flag(&ast_options, AST_OPT_FLAG_DONT_WARN) diff --git a/main/asterisk.c b/main/asterisk.c index f4a163b8a441597c2299bd04852f56eda72f6d4a..53bceadfd66fa1db79b0ed4476aa7c9e5cd8ece5 100644 --- a/main/asterisk.c +++ b/main/asterisk.c @@ -3352,7 +3352,7 @@ static int show_cli_help(void) printf(" -G <group> Run as a group other than the caller\n"); printf(" -U <user> Run as a user other than the caller\n"); printf(" -c Provide console CLI\n"); - printf(" -d Enable extra debugging\n"); + printf(" -d Increase debugging (multiple d's = more debugging)\n"); #if HAVE_WORKING_FORK printf(" -f Do not fork\n"); printf(" -F Always fork\n"); @@ -3375,7 +3375,7 @@ static int show_cli_help(void) printf(" of output to the CLI\n"); printf(" -v Increase verbosity (multiple v's = more verbose)\n"); printf(" -x <cmd> Execute command <cmd> (implies -r)\n"); - printf(" -X Execute includes by default (allows #exec in asterisk.conf)\n"); + printf(" -X Enable use of #exec in asterisk.conf\n"); printf(" -W Adjust terminal colors to compensate for a light background\n"); printf("\n"); return 0; @@ -3385,7 +3385,6 @@ static void ast_readconfig(void) { struct ast_config *cfg; struct ast_variable *v; - char *config = DEFAULT_CONFIG_FILE; char hostname[MAXHOSTNAMELEN] = ""; struct ast_flags config_flags = { CONFIG_FLAG_NOREALTIME }; struct { @@ -3394,19 +3393,12 @@ static void ast_readconfig(void) } found = { 0, 0 }; /* Default to false for security */ int live_dangerously = 0; + int option_debug_new = 0; + int option_verbose_new = 0; /* Set default value */ option_dtmfminduration = AST_MIN_DTMF_DURATION; - if (ast_opt_override_config) { - cfg = ast_config_load2(ast_config_AST_CONFIG_FILE, "" /* core, can't reload */, config_flags); - if (cfg == CONFIG_STATUS_FILEMISSING || cfg == CONFIG_STATUS_FILEUNCHANGED || cfg == CONFIG_STATUS_FILEINVALID) { - fprintf(stderr, "Unable to open specified master config file '%s', using built-in defaults\n", ast_config_AST_CONFIG_FILE); - } - } else { - cfg = ast_config_load2(config, "" /* core, can't reload */, config_flags); - } - /* init with buildtime config */ ast_copy_string(cfg_paths.config_dir, DEFAULT_CONFIG_DIR, sizeof(cfg_paths.config_dir)); ast_copy_string(cfg_paths.spool_dir, DEFAULT_SPOOL_DIR, sizeof(cfg_paths.spool_dir)); @@ -3432,8 +3424,15 @@ static void ast_readconfig(void) ast_set_default_eid(&ast_eid_default); + cfg = ast_config_load2(ast_config_AST_CONFIG_FILE, "" /* core, can't reload */, config_flags); + + /* If AST_OPT_FLAG_EXEC_INCLUDES was previously enabled with -X turn it off now. + * Using #exec from other configs requires that it be enabled from asterisk.conf. */ + ast_clear_flag(&ast_options, AST_OPT_FLAG_EXEC_INCLUDES); + /* no asterisk.conf? no problem, use buildtime config! */ if (cfg == CONFIG_STATUS_FILEMISSING || cfg == CONFIG_STATUS_FILEUNCHANGED || cfg == CONFIG_STATUS_FILEINVALID) { + fprintf(stderr, "Unable to open specified master config file '%s', using built-in defaults\n", ast_config_AST_CONFIG_FILE); return; } @@ -3487,7 +3486,7 @@ static void ast_readconfig(void) for (v = ast_variable_browse(cfg, "options"); v; v = v->next) { /* verbose level (-v at startup) */ if (!strcasecmp(v->name, "verbose")) { - option_verbose = atoi(v->value); + option_verbose_new = atoi(v->value); /* whether or not to force timestamping in CLI verbose output. (-T at startup) */ } else if (!strcasecmp(v->name, "timestamp")) { ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_TIMESTAMP); @@ -3496,9 +3495,9 @@ static void ast_readconfig(void) ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_EXEC_INCLUDES); /* debug level (-d at startup) */ } else if (!strcasecmp(v->name, "debug")) { - option_debug = 0; - if (sscanf(v->value, "%30d", &option_debug) != 1) { - option_debug = ast_true(v->value) ? 1 : 0; + option_debug_new = 0; + if (sscanf(v->value, "%30d", &option_debug_new) != 1) { + option_debug_new = ast_true(v->value) ? 1 : 0; } } else if (!strcasecmp(v->name, "refdebug")) { ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_REF_DEBUG); @@ -3647,6 +3646,9 @@ static void ast_readconfig(void) pbx_live_dangerously(live_dangerously); } + option_debug += option_debug_new; + option_verbose += option_verbose_new; + ast_config_destroy(cfg); } @@ -3787,9 +3789,9 @@ int main(int argc, char *argv[]) int isroot = 1, rundir_exists = 0; char *buf; const char *runuser = NULL, *rungroup = NULL; - char *remotesock = NULL; int moduleresult; /*!< Result from the module load subsystem */ struct rlimit l; + static const char *getopt_settings = "BC:cde:FfG:ghIiL:M:mnpqRrs:TtU:VvWXx:"; /* Remember original args for restart */ if (argc > ARRAY_LEN(_argv) - 1) { @@ -3813,11 +3815,57 @@ int main(int argc, char *argv[]) if (getenv("HOME")) snprintf(filename, sizeof(filename), "%s/.asterisk_history", getenv("HOME")); + + /* Set config file to default before checking arguments for override. */ + ast_copy_string(cfg_paths.config_file, DEFAULT_CONFIG_FILE, sizeof(cfg_paths.config_file)); + + /* Process command-line options that effect asterisk.conf load. */ + while ((c = getopt(argc, argv, getopt_settings)) != -1) { + switch (c) { + case 'X': + ast_set_flag(&ast_options, AST_OPT_FLAG_EXEC_INCLUDES); + break; + case 'C': + ast_copy_string(cfg_paths.config_file, optarg, sizeof(cfg_paths.config_file)); + break; + case 'd': + option_debug++; + break; + case 'h': + show_cli_help(); + exit(0); + case 'R': + case 'r': + case 'x': + /* ast_opt_remote is checked during config load. This is only part of what + * these options do, see the second loop for the rest of the actions. */ + ast_set_flag(&ast_options, AST_OPT_FLAG_REMOTE); + break; + case 'V': + show_version(); + exit(0); + case 'v': + option_verbose++; + break; + case '?': + exit(1); + } + } + + /* Initialize env so it is available if #exec is used in asterisk.conf. */ + env_init(); + + ast_readconfig(); + + /* Update env to include any systemname that was set. */ + env_init(); + /*! \brief Check for options * * \todo Document these options */ - while ((c = getopt(argc, argv, "BC:cde:FfG:ghIiL:M:mnpqRrs:TtU:VvWXx:")) != -1) { + optind = 0; + while ((c = getopt(argc, argv, getopt_settings)) != -1) { /*!\note Please keep the ordering here to alphabetical, capital letters * first. This will make it easier in the future to select unused * option flags for new features. */ @@ -3827,18 +3875,16 @@ int main(int argc, char *argv[]) ast_clear_flag(&ast_options, AST_OPT_FLAG_LIGHT_BACKGROUND); break; case 'X': - ast_set_flag(&ast_options, AST_OPT_FLAG_EXEC_INCLUDES); + /* The command-line -X option enables #exec for asterisk.conf only. */ break; case 'C': - ast_copy_string(cfg_paths.config_file, optarg, sizeof(cfg_paths.config_file)); - ast_set_flag(&ast_options, AST_OPT_FLAG_OVERRIDE_CONFIG); + /* already processed. */ break; case 'c': ast_set_flag(&ast_options, AST_OPT_FLAG_NO_FORK | AST_OPT_FLAG_CONSOLE); break; case 'd': - option_debug++; - ast_set_flag(&ast_options, AST_OPT_FLAG_NO_FORK); + /* already processed. */ break; #if defined(HAVE_SYSINFO) case 'e': @@ -3862,8 +3908,8 @@ int main(int argc, char *argv[]) ast_set_flag(&ast_options, AST_OPT_FLAG_DUMP_CORE); break; case 'h': - show_cli_help(); - exit(0); + /* already processed. */ + break; case 'I': fprintf(stderr, "NOTICE: The -I option is no longer needed.\n" @@ -3901,7 +3947,9 @@ int main(int argc, char *argv[]) ast_set_flag(&ast_options, AST_OPT_FLAG_NO_FORK | AST_OPT_FLAG_REMOTE); break; case 's': - remotesock = ast_strdupa(optarg); + if (ast_opt_remote) { + ast_copy_string((char *) cfg_paths.socket_path, optarg, sizeof(cfg_paths.socket_path)); + } break; case 'T': ast_set_flag(&ast_options, AST_OPT_FLAG_TIMESTAMP); @@ -3913,11 +3961,8 @@ int main(int argc, char *argv[]) runuser = ast_strdupa(optarg); break; case 'V': - show_version(); - exit(0); case 'v': - option_verbose++; - ast_set_flag(&ast_options, AST_OPT_FLAG_NO_FORK); + /* already processed. */ break; case 'W': /* White background */ ast_set_flag(&ast_options, AST_OPT_FLAG_LIGHT_BACKGROUND); @@ -3931,7 +3976,8 @@ int main(int argc, char *argv[]) xarg = ast_strdupa(optarg); break; case '?': - exit(1); + /* already processed. */ + break; } } @@ -3945,12 +3991,6 @@ int main(int argc, char *argv[]) } } - ast_readconfig(); - env_init(); - - if (ast_opt_remote && remotesock != NULL) - ast_copy_string((char *) cfg_paths.socket_path, remotesock, sizeof(cfg_paths.socket_path)); - if (!ast_language_is_prefix && !ast_opt_remote) { fprintf(stderr, "The 'languageprefix' option in asterisk.conf is deprecated; in a future release it will be removed, and your sound files will need to be organized in the 'new style' language layout.\n"); }