func_config.c File Reference

A function to retrieve variables from an Asterisk configuration file. More...

#include "asterisk.h"
#include "asterisk/module.h"
#include "asterisk/channel.h"
#include "asterisk/pbx.h"
#include "asterisk/app.h"

Include dependency graph for func_config.c:

Go to the source code of this file.

Data Structures

struct  config_item
struct  configs

Functions

static void __fini_configs (void)
static void __init_configs (void)
static void __reg_module (void)
static void __unreg_module (void)
static int config_function_read (struct ast_channel *chan, const char *cmd, char *data, char *buf, size_t len)
static int load_module (void)
static int unload_module (void)

Variables

static struct ast_module_info __mod_info = { .name = AST_MODULE, .flags = AST_MODFLAG_LOAD_ORDER , .description = "Asterisk configuration file variable access" , .key = "This paragraph is copyright (c) 2006 by Digium, Inc. \In order for your module to load, it must return this \key via a function called \"key\". Any code which \includes this paragraph must be licensed under the GNU \General Public License version 2 or later (at your \option). In addition to Digium's general reservations \of rights, Digium expressly reserves the right to \allow other parties to license this paragraph under \different terms. Any use of Digium, Inc. trademarks or \logos (including \"Asterisk\" or \"Digium\") without \express written permission of Digium, Inc. is prohibited.\n" , .buildopt_sum = AST_BUILDOPT_SUM, .load = load_module, .unload = unload_module, .load_pri = AST_MODPRI_DEFAULT, .support_level = AST_MODULE_SUPPORT_CORE, }
static struct ast_module_infoast_module_info = &__mod_info
static struct ast_custom_function config_function


Detailed Description

A function to retrieve variables from an Asterisk configuration file.

Author:
Russell Bryant <russell@digium.com>

Tilghman Lesher <func_config__200803@the-tilghman.com>

Definition in file func_config.c.


Function Documentation

static void __fini_configs ( void   )  [static]

Definition at line 73 of file func_config.c.

00077 {

static void __init_configs ( void   )  [static]

Definition at line 73 of file func_config.c.

00077 {

static void __reg_module ( void   )  [static]

Definition at line 239 of file func_config.c.

static void __unreg_module ( void   )  [static]

Definition at line 239 of file func_config.c.

static int config_function_read ( struct ast_channel chan,
const char *  cmd,
char *  data,
char *  buf,
size_t  len 
) [static]

Definition at line 75 of file func_config.c.

References args, AST_APP_ARG, ast_calloc, ast_category_root(), ast_clear_flag, ast_config_destroy(), ast_config_load, ast_copy_string(), ast_debug, AST_DECLARE_APP_ARGS, ast_free, ast_log, AST_RWLIST_INSERT_TAIL, AST_RWLIST_RDLOCK, AST_RWLIST_TRAVERSE, AST_RWLIST_UNLOCK, AST_RWLIST_WRLOCK, AST_STANDARD_APP_ARGS, ast_strdupa, ast_strlen_zero, config_item::cfg, CONFIG_FLAG_FILEUNCHANGED, CONFIG_STATUS_FILEINVALID, CONFIG_STATUS_FILEUNCHANGED, config_item::filename, LOG_ERROR, ast_variable::name, ast_variable::next, NULL, parse(), ast_variable::value, and var.

00077 {
00078    struct ast_config *cfg;
00079    struct ast_flags cfg_flags = { CONFIG_FLAG_FILEUNCHANGED };
00080    char *parse;
00081    struct config_item *cur;
00082    int index = 0;
00083    struct ast_variable *var;
00084    struct ast_variable *found = NULL;
00085    int ix = 0;
00086    AST_DECLARE_APP_ARGS(args,
00087       AST_APP_ARG(filename);
00088       AST_APP_ARG(category);
00089       AST_APP_ARG(variable);
00090       AST_APP_ARG(index);
00091    );
00092 
00093    if (ast_strlen_zero(data)) {
00094       ast_log(LOG_ERROR, "AST_CONFIG() requires an argument\n");
00095       return -1;
00096    }
00097 
00098    parse = ast_strdupa(data);
00099    AST_STANDARD_APP_ARGS(args, parse);
00100 
00101    if (ast_strlen_zero(args.filename)) {
00102       ast_log(LOG_ERROR, "AST_CONFIG() requires a filename\n");
00103       return -1;
00104    }
00105 
00106    if (ast_strlen_zero(args.category)) {
00107       ast_log(LOG_ERROR, "AST_CONFIG() requires a category\n");
00108       return -1;
00109    }
00110    
00111    if (ast_strlen_zero(args.variable)) {
00112       ast_log(LOG_ERROR, "AST_CONFIG() requires a variable\n");
00113       return -1;
00114    }
00115 
00116    if (!ast_strlen_zero(args.index)) {
00117       if (!sscanf(args.index, "%d", &index)) {
00118          ast_log(LOG_ERROR, "AST_CONFIG() index must be an integer\n");
00119          return -1;
00120       }
00121    }
00122 
00123    if (!(cfg = ast_config_load(args.filename, cfg_flags)) || cfg == CONFIG_STATUS_FILEINVALID) {
00124       return -1;
00125    }
00126 
00127    if (cfg == CONFIG_STATUS_FILEUNCHANGED) {
00128       /* Retrieve cfg from list */
00129       AST_RWLIST_RDLOCK(&configs);
00130       AST_RWLIST_TRAVERSE(&configs, cur, entry) {
00131          if (!strcmp(cur->filename, args.filename)) {
00132             break;
00133          }
00134       }
00135 
00136       if (!cur) {
00137          /* At worst, we might leak an entry while upgrading locks */
00138          AST_RWLIST_UNLOCK(&configs);
00139          AST_RWLIST_WRLOCK(&configs);
00140          if (!(cur = ast_calloc(1, sizeof(*cur) + strlen(args.filename) + 1))) {
00141             AST_RWLIST_UNLOCK(&configs);
00142             return -1;
00143          }
00144 
00145          strcpy(cur->filename, args.filename);
00146 
00147          ast_clear_flag(&cfg_flags, CONFIG_FLAG_FILEUNCHANGED);
00148          if (!(cfg = ast_config_load(args.filename, cfg_flags)) || cfg == CONFIG_STATUS_FILEINVALID) {
00149             ast_free(cur);
00150             AST_RWLIST_UNLOCK(&configs);
00151             return -1;
00152          }
00153 
00154          cur->cfg = cfg;
00155          AST_RWLIST_INSERT_TAIL(&configs, cur, entry);
00156       }
00157 
00158       cfg = cur->cfg;
00159    } else {
00160       /* Replace cfg in list */
00161       AST_RWLIST_WRLOCK(&configs);
00162       AST_RWLIST_TRAVERSE(&configs, cur, entry) {
00163          if (!strcmp(cur->filename, args.filename)) {
00164             break;
00165          }
00166       }
00167 
00168       if (!cur) {
00169          if (!(cur = ast_calloc(1, sizeof(*cur) + strlen(args.filename) + 1))) {
00170             AST_RWLIST_UNLOCK(&configs);
00171             return -1;
00172          }
00173 
00174          strcpy(cur->filename, args.filename);
00175          cur->cfg = cfg;
00176 
00177          AST_RWLIST_INSERT_TAIL(&configs, cur, entry);
00178       } else {
00179          ast_config_destroy(cur->cfg);
00180          cur->cfg = cfg;
00181       }
00182    }
00183 
00184    for (var = ast_category_root(cfg, args.category); var; var = var->next) {
00185       if (strcasecmp(args.variable, var->name)) {
00186          continue;
00187       }
00188       found = var;
00189       if (index == -1) {
00190          continue;
00191       }
00192       if (ix == index) {
00193          break;
00194       }
00195       found = NULL;
00196       ix++;
00197    }
00198 
00199    if (!found) {
00200       ast_debug(1, "'%s' not found at index %d in [%s] of '%s'.  Maximum index found: %d\n",
00201          args.variable, index, args.category, args.filename, ix);
00202       AST_RWLIST_UNLOCK(&configs);
00203       return -1;
00204    }
00205 
00206    ast_copy_string(buf, found->value, len);
00207 
00208    /* Unlock down here, so there's no chance the struct goes away while we're using it. */
00209    AST_RWLIST_UNLOCK(&configs);
00210 
00211    return 0;
00212 }

static int load_module ( void   )  [static]

Definition at line 234 of file func_config.c.

References ast_custom_function_register, and config_function.

00235 {
00236    return ast_custom_function_register(&config_function);
00237 }

static int unload_module ( void   )  [static]

Definition at line 219 of file func_config.c.

References ast_config_destroy(), ast_custom_function_unregister(), ast_free, AST_RWLIST_REMOVE_HEAD, AST_RWLIST_UNLOCK, AST_RWLIST_WRLOCK, config_item::cfg, and config_function.

00220 {
00221    struct config_item *current;
00222    int res = ast_custom_function_unregister(&config_function);
00223 
00224    AST_RWLIST_WRLOCK(&configs);
00225    while ((current = AST_RWLIST_REMOVE_HEAD(&configs, entry))) {
00226       ast_config_destroy(current->cfg);
00227       ast_free(current);
00228    }
00229    AST_RWLIST_UNLOCK(&configs);
00230 
00231    return res;
00232 }


Variable Documentation

struct ast_module_info __mod_info = { .name = AST_MODULE, .flags = AST_MODFLAG_LOAD_ORDER , .description = "Asterisk configuration file variable access" , .key = "This paragraph is copyright (c) 2006 by Digium, Inc. \In order for your module to load, it must return this \key via a function called \"key\". Any code which \includes this paragraph must be licensed under the GNU \General Public License version 2 or later (at your \option). In addition to Digium's general reservations \of rights, Digium expressly reserves the right to \allow other parties to license this paragraph under \different terms. Any use of Digium, Inc. trademarks or \logos (including \"Asterisk\" or \"Digium\") without \express written permission of Digium, Inc. is prohibited.\n" , .buildopt_sum = AST_BUILDOPT_SUM, .load = load_module, .unload = unload_module, .load_pri = AST_MODPRI_DEFAULT, .support_level = AST_MODULE_SUPPORT_CORE, } [static]

Definition at line 239 of file func_config.c.

Definition at line 239 of file func_config.c.

Initial value:

 {
   .name = "AST_CONFIG",
   .read = config_function_read,
}

Definition at line 214 of file func_config.c.

Referenced by load_module(), and unload_module().


Generated on Thu Apr 16 06:31:13 2015 for Asterisk - The Open Source Telephony Project by  doxygen 1.5.6