Sat Mar 24 22:57:14 2007

Asterisk developer's documentation


pbx_config.c File Reference

Populate and remember extensions from static config file. More...

#include <sys/types.h>
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <ctype.h>
#include <errno.h>
#include "asterisk.h"
#include "asterisk/pbx.h"
#include "asterisk/config.h"
#include "asterisk/options.h"
#include "asterisk/module.h"
#include "asterisk/logger.h"
#include "asterisk/cli.h"
#include "asterisk/callerid.h"

Include dependency graph for pbx_config.c:

Go to the source code of this file.

Defines

#define BROKEN_READLINE   1
#define FREE   free

Functions

 AST_MUTEX_DEFINE_STATIC (save_dialplan_lock)
static char * complete_context_add_extension (char *line, char *word, int pos, int state)
static char * complete_context_add_ignorepat (char *line, char *word, int pos, int state)
static char * complete_context_add_include (char *line, char *word, int pos, int state)
static char * complete_context_dont_include (char *line, char *word, int pos, int state)
static char * complete_context_remove_extension (char *line, char *word, int pos, int state)
static char * complete_context_remove_ignorepat (char *line, char *word, int pos, int state)
char * description (void)
 Provides a description of the module.
static int fix_complete_args (char *line, char **word, int *pos)
static int handle_context_add_extension (int fd, int argc, char *argv[])
 ADD EXTENSION command stuff.
static int handle_context_add_ignorepat (int fd, int argc, char *argv[])
static int handle_context_add_include (int fd, int argc, char *argv[])
static int handle_context_dont_include (int fd, int argc, char *argv[])
static int handle_context_remove_extension (int fd, int argc, char *argv[])
static int handle_context_remove_ignorepat (int fd, int argc, char *argv[])
static int handle_reload_extensions (int fd, int argc, char *argv[])
static int handle_save_dialplan (int fd, int argc, char *argv[])
 'save dialplan' CLI command implementation functions ...
char * key (void)
 Returns the ASTERISK_GPL_KEY.
int load_module (void)
 Initialize the module.
static int pbx_load_module (void)
int reload (void)
 Reload stuff.
int unload_module (void)
 Cleanup all module structures, sockets, etc.
int usecount (void)
 Provides a usecount.

Variables

static int autofallthrough_config = 0
static int clearglobalvars_config = 0
static char * config = "extensions.conf"
static struct ast_cli_entry context_add_extension_cli
static char context_add_extension_help []
static struct ast_cli_entry context_add_ignorepat_cli
static char context_add_ignorepat_help []
static struct ast_cli_entry context_add_include_cli
static char context_add_include_help []
static struct ast_cli_entry context_dont_include_cli
static char context_dont_include_help []
static struct ast_cli_entry context_remove_extension_cli
static char context_remove_extension_help []
static struct ast_cli_entry context_remove_ignorepat_cli
static char context_remove_ignorepat_help []
static char * dtext = "Text Extension Configuration"
static struct ast_contextlocal_contexts = NULL
static char * registrar = "pbx_config"
static struct ast_cli_entry reload_extensions_cli
static char reload_extensions_help []
static struct ast_cli_entry save_dialplan_cli
static char save_dialplan_help []
static int static_config = 0
static int write_protect_config = 1


Detailed Description

Populate and remember extensions from static config file.

Definition in file pbx_config.c.


Define Documentation

#define BROKEN_READLINE   1

Definition at line 437 of file pbx_config.c.

#define FREE   free

Definition at line 51 of file pbx_config.c.


Function Documentation

AST_MUTEX_DEFINE_STATIC ( save_dialplan_lock   ) 

static char* complete_context_add_extension ( char *  line,
char *  word,
int  pos,
int  state 
) [static]

add extension 6123,1,Dial,IAX/212.71.138.13/6123 into local

Definition at line 1255 of file pbx_config.c.

References ast_get_context_name(), ast_lock_contexts(), ast_log(), ast_unlock_contexts(), ast_walk_contexts(), LOG_WARNING, and strdup.

01257 {
01258    int which = 0;
01259 
01260    /* complete 'into' word ... */
01261    if (pos == 3) {
01262       if (state == 0) return strdup("into");
01263       return NULL;
01264    }
01265 
01266    /* complete context */
01267    if (pos == 4) {
01268       struct ast_context *c;
01269 
01270       /* try to lock contexts list ... */
01271       if (ast_lock_contexts()) {
01272          ast_log(LOG_WARNING, "Failed to lock contexts list\n");
01273          return NULL;
01274       }
01275 
01276       /* walk through all contexts */
01277       c = ast_walk_contexts(NULL);
01278       while (c) {
01279          /* matching context? */
01280          if (!strncmp(ast_get_context_name(c), word, strlen(word))) {
01281             if (++which > state) {
01282                char *res = strdup(ast_get_context_name(c));
01283                ast_unlock_contexts();
01284                return res;
01285             }
01286          }
01287          c = ast_walk_contexts(c);
01288       }
01289 
01290       ast_unlock_contexts();
01291       return NULL;
01292    }
01293 
01294    if (pos == 5) return state == 0 ? strdup("replace") : NULL;
01295 
01296    return NULL;
01297 }

static char* complete_context_add_ignorepat ( char *  line,
char *  word,
int  pos,
int  state 
) [static]

Definition at line 1338 of file pbx_config.c.

References ast_get_context_name(), ast_get_ignorepat_name(), ast_lock_context(), ast_lock_contexts(), ast_log(), ast_unlock_context(), ast_unlock_contexts(), ast_walk_context_ignorepats(), ast_walk_contexts(), context, free, LOG_ERROR, strdup, and strsep().

01340 {
01341    if (pos == 3) return state == 0 ? strdup("into") : NULL;
01342 
01343    if (pos == 4) {
01344       struct ast_context *c;
01345       int which = 0;
01346       char *dupline, *duplinet, *ignorepat = NULL;
01347 
01348       dupline = strdup(line);
01349       duplinet = dupline;
01350 
01351       if (duplinet) {
01352          strsep(&duplinet, " "); /* skip 'add' */
01353          strsep(&duplinet, " "); /* skip 'ignorepat' */
01354          ignorepat = strsep(&duplinet, " ");
01355       }
01356 
01357       if (ast_lock_contexts()) {
01358          ast_log(LOG_ERROR, "Failed to lock contexts list\n");
01359          return NULL;
01360       }
01361 
01362       c = ast_walk_contexts(NULL);
01363       while (c) {
01364          if (!strncmp(ast_get_context_name(c), word, strlen(word))) {
01365             int serve_context = 1;
01366             if (ignorepat) {
01367                if (!ast_lock_context(c)) {
01368                   struct ast_ignorepat *ip;
01369                   ip = ast_walk_context_ignorepats(c, NULL);
01370                   while (ip && serve_context) {
01371                      if (!strcmp(ast_get_ignorepat_name(ip), ignorepat))
01372                         serve_context = 0;
01373                      ip = ast_walk_context_ignorepats(c, ip);
01374                   }
01375                   ast_unlock_context(c);
01376                }
01377             }
01378             if (serve_context) {
01379                if (++which > state) {
01380                   char *context = strdup(ast_get_context_name(c));
01381                   if (dupline) free(dupline);
01382                   ast_unlock_contexts();
01383                   return context;
01384                }
01385             }
01386          }
01387          c = ast_walk_contexts(c);
01388       }
01389 
01390       if (dupline) free(dupline);
01391       ast_unlock_contexts();
01392       return NULL;
01393    }
01394 
01395    return NULL;
01396 }

static char* complete_context_add_include ( char *  line,
char *  word,
int  pos,
int  state 
) [static]

Definition at line 748 of file pbx_config.c.

References ast_get_context_name(), ast_get_include_name(), ast_lock_context(), ast_lock_contexts(), ast_log(), ast_unlock_context(), ast_unlock_contexts(), ast_walk_context_includes(), ast_walk_contexts(), context, free, LOG_ERROR, strdup, and strsep().

00750 {
00751    struct ast_context *c;
00752    int which = 0;
00753 
00754    /* server context for inclusion ... */
00755    if (pos == 1)
00756    {
00757       if (ast_lock_contexts()) {
00758          ast_log(LOG_ERROR, "Failed to lock context list\n");
00759          return NULL;
00760       }
00761 
00762       /* server all contexts */ 
00763       c = ast_walk_contexts(NULL); 
00764       while (c) {
00765          if ((!strlen(word) || 
00766              !strncmp(ast_get_context_name(c), word, strlen(word))) &&
00767             ++which > state)
00768          {
00769             char *context = strdup(ast_get_context_name(c));
00770             ast_unlock_contexts();
00771             return context;
00772          }
00773          c = ast_walk_contexts(c);
00774       }
00775 
00776       ast_unlock_contexts();
00777    }
00778 
00779    /* complete 'in' only if context exist ... */
00780    if (pos == 2)
00781    {
00782       char *context, *dupline, *duplinet;
00783 
00784       if (state != 0) return NULL;
00785 
00786       /* parse context from line ... */
00787       if (!(dupline = strdup(line))) {
00788          ast_log(LOG_ERROR, "Out of free memory\n");
00789          if (state == 0) return strdup("in");
00790          return NULL;
00791       }
00792 
00793       duplinet = dupline;
00794 
00795       strsep(&duplinet, " ");
00796       context = strsep(&duplinet, " ");
00797       if (context) {
00798          struct ast_context *c;
00799          int context_existence = 0;
00800 
00801          /* check for context existence ... */
00802          if (ast_lock_contexts()) {
00803             ast_log(LOG_ERROR, "Failed to lock context list\n");
00804             free(dupline);
00805             /* our fault, we can't check, so complete 'in' ... */
00806             return strdup("in");
00807          }
00808 
00809          c = ast_walk_contexts(NULL);
00810          while (c && !context_existence) {
00811             if (!strcmp(context, ast_get_context_name(c))) {
00812                context_existence = 1;
00813                continue;
00814             }
00815             c = ast_walk_contexts(c);
00816          }
00817 
00818          /* if context exists, return 'into' ... */
00819          if (context_existence) {
00820             free(dupline);
00821             ast_unlock_contexts();
00822             return strdup("into");
00823          }
00824 
00825          ast_unlock_contexts();
00826       }  
00827 
00828       free(dupline);
00829       return NULL;
00830    }
00831 
00832    /* serve context into which we include another context */
00833    if (pos == 3)
00834    {
00835       char *context, *dupline, *duplinet, *in;
00836       int context_existence = 0;
00837 
00838       if (!(dupline = strdup(line))) {
00839          ast_log(LOG_ERROR, "Out of free memory\n");
00840          return NULL;
00841       }
00842 
00843       duplinet = dupline;
00844 
00845       strsep(&duplinet, " "); /* skip 'include' */
00846       context = strsep(&duplinet, " ");
00847       in = strsep(&duplinet, " ");
00848 
00849       /* given some context and third word is in? */
00850       if (!strlen(context) || strcmp(in, "in")) {
00851          free(dupline);
00852          return NULL;
00853       }
00854 
00855       if (ast_lock_contexts()) {
00856          ast_log(LOG_ERROR, "Failed to lock context list\n");
00857          free(dupline);
00858          return NULL;
00859       }
00860 
00861       /* check for context existence ... */
00862       c = ast_walk_contexts(NULL);
00863       while (c && !context_existence) {
00864          if (!strcmp(context, ast_get_context_name(c))) {
00865             context_existence = 1;
00866             continue;
00867          }
00868          c = ast_walk_contexts(c);
00869       }
00870 
00871       if (!context_existence) {
00872          free(dupline);
00873          ast_unlock_contexts();
00874          return NULL;
00875       }
00876 
00877       /* go through all contexts ... */
00878       c = ast_walk_contexts(NULL);
00879       while (c) {
00880          /* must be different contexts ... */
00881          if (strcmp(context, ast_get_context_name(c))) {
00882             if (!ast_lock_context(c)) {
00883                struct ast_include *i;
00884                int included = 0;
00885 
00886                /* check for duplicity inclusion ... */
00887                i = ast_walk_context_includes(c, NULL);
00888                while (i && !included) {
00889                   if (!strcmp(ast_get_include_name(i), context))
00890                      included = 1;
00891                   i = ast_walk_context_includes(c, i);
00892                }
00893                ast_unlock_context(c);
00894 
00895                /* not included yet, so show possibility ... */
00896                if (!included &&
00897                   !strncmp(ast_get_context_name(c), word, strlen(word))){
00898                   
00899                   if (++which > state) {
00900                      char *res = strdup(ast_get_context_name(c));
00901                      free(dupline);
00902                      ast_unlock_contexts();
00903                      return res;
00904                   }
00905                }  
00906             }
00907          }
00908          c = ast_walk_contexts(c);
00909       }
00910 
00911       ast_unlock_contexts();
00912       free(dupline);
00913       return NULL;
00914    }
00915 
00916    return NULL;
00917 }

static char* complete_context_dont_include ( char *  line,
char *  word,
int  pos,
int  state 
) [static]

Definition at line 146 of file pbx_config.c.

References ast_get_context_name(), ast_get_include_name(), ast_lock_context(), ast_lock_contexts(), ast_log(), ast_unlock_context(), ast_unlock_contexts(), ast_walk_context_includes(), ast_walk_contexts(), context, free, LOG_ERROR, LOG_WARNING, strdup, and strsep().

00148 {
00149    int which = 0;
00150 
00151    /*
00152     * Context completion ...
00153     */
00154    if (pos == 2) {
00155       struct ast_context *c;
00156 
00157       if (ast_lock_contexts()) {
00158          ast_log(LOG_ERROR, "Failed to lock context list\n");
00159          return NULL;
00160       }
00161 
00162       /* walk pbx_get_contexts ... */
00163       c = ast_walk_contexts(NULL); 
00164       while (c) {
00165          struct ast_include *i;
00166 
00167          if (ast_lock_context(c)) {
00168             c = ast_walk_contexts(c);
00169             continue;
00170          }
00171 
00172          i = ast_walk_context_includes(c, NULL);
00173          while (i) {
00174             if (!strlen(word) ||
00175                !strncmp(ast_get_include_name(i), word, strlen(word))) {
00176                struct ast_context *nc;
00177                int already_served = 0;
00178 
00179                /* check if this include is already served or not */
00180 
00181                /* go through all contexts again till we reach actuall
00182                 * context or already_served = 1
00183                 */
00184                nc = ast_walk_contexts(NULL);
00185                while (nc && nc != c && !already_served) {
00186                   if (!ast_lock_context(nc)) {
00187                      struct ast_include *ni;
00188 
00189                      ni = ast_walk_context_includes(nc, NULL);
00190                      while (ni && !already_served) {
00191                         if (!strcmp(ast_get_include_name(i),
00192                            ast_get_include_name(ni)))
00193                            already_served = 1;
00194                         ni = ast_walk_context_includes(nc, ni);
00195                      }  
00196                      
00197                      ast_unlock_context(nc);
00198                   }
00199                   nc = ast_walk_contexts(nc);
00200                }
00201 
00202                if (!already_served) {
00203                   if (++which > state) {
00204                      char *res =
00205                         strdup(ast_get_include_name(i));
00206                      ast_unlock_context(c);
00207                      ast_unlock_contexts();
00208                      return res;
00209                   }
00210                }
00211             }
00212             i = ast_walk_context_includes(c, i);
00213          }
00214 
00215          ast_unlock_context(c);
00216          c = ast_walk_contexts(c);
00217       }
00218 
00219       ast_unlock_contexts();
00220       return NULL;
00221    }
00222 
00223    /*
00224     * 'in' completion ... (complete only if previous context is really
00225     * included somewhere)
00226     */
00227    if (pos == 3) {
00228       struct ast_context *c;
00229       char *context, *dupline, *duplinet;
00230 
00231       if (state > 0) return NULL;
00232 
00233       /* take 'context' from line ... */
00234       if (!(dupline = strdup(line))) {
00235          ast_log(LOG_ERROR, "Out of free memory\n");
00236          return NULL;
00237       }
00238 
00239       duplinet = dupline;
00240       strsep(&duplinet, " "); /* skip 'dont' */
00241       strsep(&duplinet, " "); /* skip 'include' */
00242       context = strsep(&duplinet, " ");
00243 
00244       if (!context) {
00245          free(dupline);
00246          return NULL;
00247       }
00248 
00249       if (ast_lock_contexts()) {
00250          ast_log(LOG_WARNING, "Failed to lock contexts list\n");
00251          free(dupline);
00252          return NULL;
00253       }
00254 
00255       /* go through all contexts and check if is included ... */
00256       c = ast_walk_contexts(NULL);
00257       while (c) {
00258          struct ast_include *i;
00259          if (ast_lock_context(c)) {
00260             free(dupline);
00261             ast_unlock_contexts();
00262             return NULL;
00263          }
00264 
00265          i = ast_walk_context_includes(c, NULL);
00266          while (i) {
00267             /* is it our context? */
00268             if (!strcmp(ast_get_include_name(i), context)) {
00269                /* yes, it is, context is really included, so
00270                 * complete "in" command
00271                 */
00272                free(dupline);
00273                ast_unlock_context(c);
00274                ast_unlock_contexts();
00275                return strdup("in");
00276             }
00277             i = ast_walk_context_includes(c, i);
00278          }
00279          ast_unlock_context(c);
00280          c = ast_walk_contexts(c);
00281       }
00282       free(dupline);
00283       ast_unlock_contexts();
00284       return NULL;
00285    }
00286 
00287    /*
00288     * Context from which we removing include ... 
00289     */
00290    if (pos == 4) {
00291       struct ast_context *c;
00292       char *context, *dupline, *duplinet, *in;
00293 
00294       if (!(dupline = strdup(line))) {
00295          ast_log(LOG_ERROR, "Out of free memory\n");
00296          return NULL;
00297       }
00298 
00299       duplinet = dupline;
00300 
00301       strsep(&duplinet, " "); /* skip 'dont' */
00302       strsep(&duplinet, " "); /* skip 'include' */
00303 
00304       if (!(context = strsep(&duplinet, " "))) {
00305          free(dupline);
00306          return NULL;
00307       }
00308 
00309       /* third word must be in */
00310       in = strsep(&duplinet, " ");
00311       if (!in ||
00312          strcmp(in, "in")) {
00313          free(dupline);
00314          return NULL;
00315       }
00316 
00317       if (ast_lock_contexts()) {
00318          ast_log(LOG_ERROR, "Failed to lock context list\n");
00319          free(dupline);
00320          return NULL;
00321       }
00322 
00323       /* walk through all contexts ... */
00324       c = ast_walk_contexts(NULL);
00325       while (c) {
00326          struct ast_include *i;
00327          if (ast_lock_context(c)) {
00328             free(dupline);
00329             return NULL;
00330          }
00331    
00332          /* walk through all includes and check if it is our context */ 
00333          i = ast_walk_context_includes(c, NULL);
00334          while (i) {
00335             /* is in this context included another on which we want to
00336              * remove?
00337              */
00338             if (!strcmp(context, ast_get_include_name(i))) {
00339                /* yes, it's included, is matching our word too? */
00340                if (!strncmp(ast_get_context_name(c),
00341                      word, strlen(word))) {
00342                   /* check state for completion */
00343                   if (++which > state) {
00344                      char *res = strdup(ast_get_context_name(c));
00345                      free(dupline);
00346                      ast_unlock_context(c);
00347                      ast_unlock_contexts();
00348                      return res;
00349                   }
00350                }
00351                break;
00352             }
00353             i = ast_walk_context_includes(c, i);
00354          }  
00355          ast_unlock_context(c);
00356          c = ast_walk_contexts(c);
00357       }
00358 
00359       free(dupline);
00360       ast_unlock_contexts();
00361       return NULL;
00362    }
00363 
00364    return NULL;
00365 }

static char* complete_context_remove_extension ( char *  line,
char *  word,
int  pos,
int  state 
) [static]

Definition at line 484 of file pbx_config.c.

References ast_get_context_name(), ast_get_extension_name(), ast_get_extension_priority(), ast_lock_contexts(), ast_log(), ast_unlock_contexts(), ast_walk_context_extensions(), ast_walk_contexts(), ast_walk_extension_priorities(), context, exten, fix_complete_args(), free, LOG_ERROR, malloc, ast_exten::priority, strdup, and strsep().

00486 {
00487    char *ret = NULL;
00488    int which = 0;
00489 
00490 #ifdef BROKEN_READLINE
00491    /*
00492     * Fix arguments, *word is a new allocated structure, REMEMBER to
00493     * free *word when you want to return from this function ...
00494     */
00495    if (fix_complete_args(line, &word, &pos)) {
00496       ast_log(LOG_ERROR, "Out of free memory\n");
00497       return NULL;
00498    }
00499 #endif
00500 
00501    /*
00502     * exten@context completion ... 
00503     */
00504    if (pos == 2) {
00505       struct ast_context *c;
00506       struct ast_exten *e;
00507       char *context = NULL, *exten = NULL, *delim = NULL;
00508 
00509       /* now, parse values from word = exten@context */
00510       if ((delim = strchr(word, (int)'@'))) {
00511          /* check for duplicity ... */
00512          if (delim != strrchr(word, (int)'@')) {
00513 #ifdef BROKEN_READLINE
00514             free(word);
00515 #endif
00516             return NULL;
00517          }
00518 
00519          *delim = '\0';
00520          exten = strdup(word);
00521          context = strdup(delim + 1);
00522          *delim = '@';
00523       } else {
00524          exten = strdup(word);
00525       }
00526 #ifdef BROKEN_READLINE
00527       free(word);
00528 #endif
00529 
00530       if (ast_lock_contexts()) {
00531          ast_log(LOG_ERROR, "Failed to lock context list\n");
00532          free(context); free(exten);
00533          return NULL;
00534       }
00535 
00536       /* find our context ... */
00537       c = ast_walk_contexts(NULL); 
00538       while (c) {
00539          /* our context? */
00540          if ( (!context || !strlen(context)) ||                            /* if no input, all contexts ... */
00541              (context && !strncmp(ast_get_context_name(c),
00542                           context, strlen(context))) ) {                  /* if input, compare ... */
00543             /* try to complete extensions ... */
00544             e = ast_walk_context_extensions(c, NULL);
00545             while (e) {
00546                /* our extension? */
00547                if ( (!exten || !strlen(exten)) ||                           /* if not input, all extensions ... */
00548                    (exten && !strncmp(ast_get_extension_name(e), exten,
00549                                       strlen(exten))) ) { /* if input, compare ... */
00550                   if (++which > state) {
00551                      /* If there is an extension then return
00552                       * exten@context.
00553                       */
00554                      if (exten) {
00555                         ret = malloc(strlen(ast_get_extension_name(e)) +
00556                            strlen(ast_get_context_name(c)) + 2);
00557                         if (ret)
00558                            sprintf(ret, "%s@%s", ast_get_extension_name(e),
00559                               ast_get_context_name(c));
00560                      }
00561                      free(exten); free(context);
00562 
00563                      ast_unlock_contexts();
00564    
00565                      return ret;
00566                   }
00567                }
00568                e = ast_walk_context_extensions(c, e);
00569             }
00570          }
00571          c = ast_walk_contexts(c);
00572       }
00573 
00574       ast_unlock_contexts();
00575 
00576       free(exten); free(context);
00577 
00578       return NULL;
00579    }
00580 
00581    /*
00582     * Complete priority ...
00583     */
00584    if (pos == 3) {
00585       char *delim, *exten, *context, *dupline, *duplinet, *ec;
00586       struct ast_context *c;
00587 
00588       dupline = strdup(line);
00589       if (!dupline) {
00590 #ifdef BROKEN_READLINE
00591          free(word);
00592 #endif
00593          return NULL;
00594       }
00595       duplinet = dupline;
00596 
00597       strsep(&duplinet, " "); /* skip 'remove' */
00598       strsep(&duplinet, " "); /* skip 'extension */
00599 
00600       if (!(ec = strsep(&duplinet, " "))) {
00601          free(dupline);
00602 #ifdef BROKEN_READLINE
00603          free(word);
00604 #endif
00605          return NULL;
00606       }
00607 
00608       /* wrong exten@context format? */
00609       if (!(delim = strchr(ec, (int)'@')) ||
00610          (strchr(ec, (int)'@') != strrchr(ec, (int)'@'))) {
00611 #ifdef BROKEN_READLINE
00612          free(word);
00613 #endif
00614          free(dupline);
00615          return NULL;
00616       }
00617 
00618       /* check if there is exten and context too ... */
00619       *delim = '\0';
00620       if ((!strlen(ec)) || (!strlen(delim + 1))) {
00621 #ifdef BROKEN_READLINE
00622          free(word);
00623 #endif
00624          free(dupline);
00625          return NULL;
00626       }
00627 
00628       exten = strdup(ec);
00629       context = strdup(delim + 1);
00630       free(dupline);
00631 
00632       if (ast_lock_contexts()) {
00633          ast_log(LOG_ERROR, "Failed to lock context list\n");
00634 #ifdef BROKEN_READLINE
00635          free(word);
00636 #endif
00637          free(exten); free(context);
00638          return NULL;
00639       }
00640 
00641       /* walk contexts */
00642       c = ast_walk_contexts(NULL); 
00643       while (c) {
00644          if (!strcmp(ast_get_context_name(c), context)) {
00645             struct ast_exten *e;
00646 
00647             /* walk extensions */
00648             free(context);
00649             e = ast_walk_context_extensions(c, NULL); 
00650             while (e) {
00651                if (!strcmp(ast_get_extension_name(e), exten)) {
00652                   struct ast_exten *priority;
00653                   char buffer[10];
00654                
00655                   free(exten);
00656                   priority = ast_walk_extension_priorities(e, NULL);
00657                   /* serve priorities */
00658                   do {
00659                      snprintf(buffer, 10, "%u",
00660                         ast_get_extension_priority(priority));
00661                      if (!strncmp(word, buffer, strlen(word))) {
00662                         if (++which > state) {
00663 #ifdef BROKEN_READLINE
00664                            free(word);
00665 #endif
00666                            ast_unlock_contexts();
00667                            return strdup(buffer);
00668                         }
00669                      }
00670                      priority = ast_walk_extension_priorities(e,
00671                         priority);
00672                   } while (priority);
00673 
00674 #ifdef BROKEN_READLINE
00675                   free(word);
00676 #endif
00677                   ast_unlock_contexts();
00678                   return NULL;         
00679                }
00680                e = ast_walk_context_extensions(c, e);
00681             }
00682 #ifdef BROKEN_READLINE
00683             free(word);
00684 #endif
00685             free(exten);
00686             ast_unlock_contexts();
00687             return NULL;
00688          }
00689          c = ast_walk_contexts(c);
00690       }
00691 
00692 #ifdef BROKEN_READLINE
00693       free(word);
00694 #endif
00695       free(exten); free(context);
00696 
00697       ast_unlock_contexts();
00698       return NULL;
00699    }
00700 
00701 #ifdef BROKEN_READLINE
00702    free(word);
00703 #endif
00704    return NULL; 
00705 }

static char* complete_context_remove_ignorepat ( char *  line,
char *  word,
int  pos,
int  state 
) [static]

Definition at line 1439 of file pbx_config.c.

References ast_get_context_name(), ast_get_ignorepat_name(), ast_lock_context(), ast_lock_contexts(), ast_log(), ast_unlock_context(), ast_unlock_contexts(), ast_walk_context_ignorepats(), ast_walk_contexts(), free, LOG_WARNING, strdup, and strsep().

01441 {
01442    struct ast_context *c;
01443    int which = 0;
01444 
01445    if (pos == 2) {
01446       if (ast_lock_contexts()) {
01447          ast_log(LOG_WARNING, "Failed to lock contexts list\n");
01448          return NULL;
01449       }
01450 
01451       c = ast_walk_contexts(NULL);
01452       while (c) {
01453          if (!ast_lock_context(c)) {
01454             struct ast_ignorepat *ip;
01455          
01456             ip = ast_walk_context_ignorepats(c, NULL);
01457             while (ip) {
01458                if (!strncmp(ast_get_ignorepat_name(ip), word, strlen(word))) {
01459                   if (which + 1 > state) {
01460                      struct ast_context *cw;
01461                      int already_served = 0;
01462                      cw = ast_walk_contexts(NULL);
01463                      while (cw && cw != c && !already_served) {
01464                         if (!ast_lock_context(cw)) {
01465                            struct ast_ignorepat *ipw;
01466                            ipw = ast_walk_context_ignorepats(cw, NULL);
01467                            while (ipw) {
01468                               if (!strcmp(ast_get_ignorepat_name(ipw),
01469                                  ast_get_ignorepat_name(ip))) already_served = 1;
01470                               ipw = ast_walk_context_ignorepats(cw, ipw);
01471                            }
01472                            ast_unlock_context(cw);
01473                         }
01474                         cw = ast_walk_contexts(cw);
01475                      }
01476                      if (!already_served) {
01477                         char *ret = strdup(ast_get_ignorepat_name(ip));
01478                         ast_unlock_context(c);
01479                         ast_unlock_contexts();
01480                         return ret;
01481                      }
01482                   } else
01483                      which++;
01484                }
01485                ip = ast_walk_context_ignorepats(c, ip);
01486             }
01487 
01488             ast_unlock_context(c);
01489          }
01490          c = ast_walk_contexts(c);
01491       }
01492 
01493       ast_unlock_contexts();
01494       return NULL;
01495    }
01496  
01497    if (pos == 3) return state == 0 ? strdup("from") : NULL;
01498 
01499    if (pos == 4) {
01500       char *dupline, *duplinet, *ignorepat;
01501 
01502       dupline = strdup(line);
01503       if (!dupline) {
01504          ast_log(LOG_WARNING, "Out of free memory\n");
01505          return NULL;
01506       }
01507 
01508       duplinet = dupline;
01509       strsep(&duplinet, " ");
01510       strsep(&duplinet, " ");
01511       ignorepat = strsep(&duplinet, " ");
01512 
01513       if (!ignorepat) {
01514          free(dupline);
01515          return NULL;
01516       }
01517 
01518       if (ast_lock_contexts()) {
01519          ast_log(LOG_WARNING, "Failed to lock contexts list\n");
01520          free(dupline);
01521          return NULL;
01522       }
01523 
01524       c = ast_walk_contexts(NULL);
01525       while (c) {
01526          if (!ast_lock_context(c)) {
01527             struct ast_ignorepat *ip;
01528             ip = ast_walk_context_ignorepats(c, NULL);
01529             while (ip) {
01530                if (!strcmp(ast_get_ignorepat_name(ip), ignorepat)) {
01531                   if (!strncmp(ast_get_context_name(c), word, strlen(word))) {
01532                      if (++which > state) {
01533                         char *ret = strdup(ast_get_context_name(c));
01534                         free(dupline);
01535                         ast_unlock_context(c);
01536                         ast_unlock_contexts();
01537                         return ret;
01538                      }
01539                   }
01540                }
01541                ip = ast_walk_context_ignorepats(c, ip);
01542             }
01543 
01544             ast_unlock_context(c);
01545          }
01546          c = ast_walk_contexts(c);
01547       }
01548 
01549       free(dupline);
01550       ast_unlock_contexts();
01551       return NULL;
01552    }
01553 
01554    return NULL;
01555 }

char* description ( void   ) 

Provides a description of the module.

Returns:
a short description of your module

Definition at line 1833 of file pbx_config.c.

01834 {
01835    return dtext;
01836 }

static int fix_complete_args ( char *  line,
char **  word,
int *  pos 
) [static]

Definition at line 452 of file pbx_config.c.

References free, strdup, and strsep().

Referenced by complete_context_remove_extension().

00453 {
00454    char *_line, *_strsep_line, *_previous_word = NULL, *_word = NULL;
00455    int words = 0;
00456 
00457    _line = strdup(line);
00458 
00459    _strsep_line = _line;
00460    while (_strsep_line) {
00461       _previous_word = _word;
00462       _word = strsep(&_strsep_line, " ");
00463 
00464       if (_word && strlen(_word)) words++;
00465    }
00466 
00467 
00468    if (_word || _previous_word) {
00469       if (_word) {
00470          if (!strlen(_word)) words++;
00471          *word = strdup(_word);
00472       } else
00473          *word = strdup(_previous_word);
00474       *pos = words - 1;
00475       free(_line);
00476       return 0;
00477    }
00478 
00479    free(_line);
00480    return -1;
00481 }

static int handle_context_add_extension ( int  fd,
int  argc,
char *  argv[] 
) [static]

ADD EXTENSION command stuff.

Definition at line 1169 of file pbx_config.c.

References app, ast_add_extension(), ast_cli(), ast_process_quotes_and_slashes(), ast_exten::cidmatch, exten, free, PRIORITY_HINT, RESULT_FAILURE, RESULT_SHOWUSAGE, RESULT_SUCCESS, strdup, and strsep().

01170 {
01171    char *whole_exten;
01172    char *exten, *prior;
01173    int iprior = -2;
01174    char *cidmatch, *app, *app_data;
01175    char *start, *end;
01176 
01177    /* check for arguments at first */
01178    if (argc != 5 && argc != 6) return RESULT_SHOWUSAGE;
01179    if (strcmp(argv[3], "into")) return RESULT_SHOWUSAGE;
01180    if (argc == 6) if (strcmp(argv[5], "replace")) return RESULT_SHOWUSAGE;
01181 
01182    whole_exten = argv[2];
01183    exten       = strsep(&whole_exten,",");
01184    if (strchr(exten, '/')) {
01185       cidmatch = exten;
01186       strsep(&cidmatch,"/");
01187    } else {
01188       cidmatch = NULL;
01189    }
01190    prior       = strsep(&whole_exten,",");
01191    if (prior) {
01192       if (!strcmp(prior, "hint")) {
01193          iprior = PRIORITY_HINT;
01194       } else {
01195          if (sscanf(prior, "%d", &iprior) != 1) {
01196             ast_cli(fd, "'%s' is not a valid priority\n", prior);
01197             prior = NULL;
01198          }
01199       }
01200    }
01201    app = whole_exten;
01202    if (app && (start = strchr(app, '(')) && (end = strrchr(app, ')'))) {
01203       *start = *end = '\0';
01204       app_data = start + 1;
01205       ast_process_quotes_and_slashes(app_data, ',', '|');
01206    } else {
01207       if (app) {
01208          app_data = strchr(app, ',');
01209          if (app_data) {
01210             *app_data = '\0';
01211             app_data++;
01212          }
01213       } else   
01214          app_data = NULL;
01215    }
01216 
01217    if (!exten || !prior || !app || (!app_data && iprior != PRIORITY_HINT)) return RESULT_SHOWUSAGE;
01218 
01219    if (!app_data)
01220       app_data="";
01221    if (ast_add_extension(argv[4], argc == 6 ? 1 : 0, exten, iprior, NULL, cidmatch, app,
01222       (void *)strdup(app_data), free, registrar)) {
01223       switch (errno) {
01224          case ENOMEM:
01225             ast_cli(fd, "Out of free memory\n"); break;
01226 
01227          case EBUSY:
01228             ast_cli(fd, "Failed to lock context(s) list, please try again later\n"); break;
01229 
01230          case ENOENT:
01231             ast_cli(fd, "No existence of '%s' context\n", argv[4]); break;
01232 
01233          case EEXIST:
01234             ast_cli(fd, "Extension %s@%s with priority %s already exists\n",
01235                exten, argv[4], prior); break;
01236 
01237          default:
01238             ast_cli(fd, "Failed to add '%s,%s,%s,%s' extension into '%s' context\n",
01239                exten, prior, app, app_data, argv[4]); break;
01240       }
01241       return RESULT_FAILURE;
01242    }
01243 
01244    if (argc == 6) 
01245       ast_cli(fd, "Extension %s@%s (%s) replace by '%s,%s,%s,%s'\n",
01246          exten, argv[4], prior, exten, prior, app, app_data);
01247    else
01248       ast_cli(fd, "Extension '%s,%s,%s,%s' added into '%s' context\n",
01249          exten, prior, app, app_data, argv[4]);
01250 
01251    return RESULT_SUCCESS;
01252 }

static int handle_context_add_ignorepat ( int  fd,
int  argc,
char *  argv[] 
) [static]

IGNOREPAT CLI stuff

Definition at line 1302 of file pbx_config.c.

References ast_cli(), ast_context_add_ignorepat(), RESULT_FAILURE, RESULT_SHOWUSAGE, and RESULT_SUCCESS.

01303 {
01304    if (argc != 5) return RESULT_SHOWUSAGE;
01305    if (strcmp(argv[3], "into")) return RESULT_SHOWUSAGE;
01306 
01307    if (ast_context_add_ignorepat(argv[4], argv[2], registrar)) {
01308       switch (errno) {
01309          case ENOMEM:
01310             ast_cli(fd, "Out of free memory\n"); break;
01311 
01312          case ENOENT:
01313             ast_cli(fd, "There is no existence of '%s' context\n", argv[4]);
01314             break;
01315 
01316          case EEXIST:
01317             ast_cli(fd, "Ignore pattern '%s' already included in '%s' context\n",
01318                argv[2], argv[4]);
01319             break;
01320 
01321          case EBUSY:
01322             ast_cli(fd, "Failed to lock context(s) list, please, try again later\n");
01323             break;
01324 
01325          default:
01326             ast_cli(fd, "Failed to add ingore pattern '%s' into '%s' context\n",
01327                argv[2], argv[4]);
01328             break;
01329       }
01330       return RESULT_FAILURE;
01331    }
01332 
01333    ast_cli(fd, "Ignore pattern '%s' added into '%s' context\n",
01334       argv[2], argv[4]);
01335    return RESULT_SUCCESS;
01336 }

static int handle_context_add_include ( int  fd,
int  argc,
char *  argv[] 
) [static]

Include context ...

Definition at line 710 of file pbx_config.c.

References ast_cli(), ast_context_add_include(), RESULT_FAILURE, RESULT_SHOWUSAGE, and RESULT_SUCCESS.

00711 {
00712    if (argc != 5) return RESULT_SHOWUSAGE;
00713 
00714    /* third arg must be 'in' ... */
00715    if (strcmp(argv[3], "in") && strcmp(argv[3], "into")) return RESULT_SHOWUSAGE;
00716 
00717    if (ast_context_add_include(argv[4], argv[2], registrar)) {
00718       switch (errno) {
00719          case ENOMEM:
00720             ast_cli(fd, "Out of memory for context addition\n"); break;
00721 
00722          case EBUSY:
00723             ast_cli(fd, "Failed to lock context(s) list, please try again later\n"); break;
00724 
00725          case EEXIST:
00726             ast_cli(fd, "Context '%s' already included in '%s' context\n",
00727                argv[2], argv[4]); break;
00728 
00729          case ENOENT:
00730          case EINVAL:
00731             ast_cli(fd, "There is no existence of context '%s'\n",
00732                errno == ENOENT ? argv[4] : argv[2]); break;
00733 
00734          default:
00735             ast_cli(fd, "Failed to include '%s' in '%s' context\n",
00736                argv[2], argv[4]); break;
00737       }
00738       return RESULT_FAILURE;
00739    }
00740 
00741    /* show some info ... */
00742    ast_cli(fd, "Context '%s' included in '%s' context\n",
00743       argv[2], argv[4]);
00744 
00745    return RESULT_SUCCESS;
00746 }

static int handle_context_dont_include ( int  fd,
int  argc,
char *  argv[] 
) [static]

REMOVE INCLUDE command stuff

Definition at line 127 of file pbx_config.c.

References ast_cli(), ast_context_remove_include(), RESULT_FAILURE, RESULT_SHOWUSAGE, and RESULT_SUCCESS.

00128 {
00129    if (argc != 5)
00130       return RESULT_SHOWUSAGE;
00131 
00132    if (strcmp(argv[3], "in"))
00133       return RESULT_SHOWUSAGE;
00134 
00135    if (!ast_context_remove_include(argv[4], argv[2], registrar)) {
00136       ast_cli(fd, "We are not including '%s' in '%s' now\n",
00137          argv[2], argv[4]);
00138       return RESULT_SUCCESS;
00139    }
00140 
00141    ast_cli(fd, "Failed to remove '%s' include from '%s' context\n",
00142       argv[2], argv[4]);
00143    return RESULT_FAILURE;
00144 }

static int handle_context_remove_extension ( int  fd,
int  argc,
char *  argv[] 
) [static]

REMOVE EXTENSION command stuff

Definition at line 370 of file pbx_config.c.

References ast_cli(), ast_context_remove_extension(), context, exten, PRIORITY_HINT, RESULT_FAILURE, RESULT_SHOWUSAGE, and RESULT_SUCCESS.

00371 {
00372    int removing_priority = 0;
00373    char *exten, *context;
00374 
00375    if (argc != 4 && argc != 3) return RESULT_SHOWUSAGE;
00376 
00377    /*
00378     * Priority input checking ...
00379     */
00380    if (argc == 4) {
00381       char *c = argv[3];
00382 
00383       /* check for digits in whole parameter for right priority ...
00384        * why? because atoi (strtol) returns 0 if any characters in
00385        * string and whole extension will be removed, it's not good
00386        */
00387       if (strcmp("hint", c)) {
00388              while (*c != '\0') {
00389          if (!isdigit(*c++)) {
00390             ast_cli(fd, "Invalid priority '%s'\n", argv[3]);
00391             return RESULT_FAILURE;
00392          }
00393           }
00394           removing_priority = atoi(argv[3]);
00395       } else
00396           removing_priority = PRIORITY_HINT;
00397 
00398       if (removing_priority == 0) {
00399          ast_cli(fd, "If you want to remove whole extension, please " \
00400             "omit priority argument\n");
00401          return RESULT_FAILURE;
00402       }
00403    }
00404 
00405    /*
00406     * Format exten@context checking ...
00407     */
00408    if (!(context = strchr(argv[2], (int)'@'))) {
00409       ast_cli(fd, "First argument must be in exten@context format\n");
00410       return RESULT_FAILURE;
00411    }
00412 
00413    *context++ = '\0';
00414    exten = argv[2];
00415    if ((!strlen(exten)) || (!(strlen(context)))) {
00416       ast_cli(fd, "Missing extension or context name in second argument '%s@%s'\n",
00417          exten == NULL ? "?" : exten, context == NULL ? "?" : context);
00418       return RESULT_FAILURE;
00419    }
00420 
00421    if (!ast_context_remove_extension(context, exten, removing_priority, registrar)) {
00422       if (!removing_priority)
00423          ast_cli(fd, "Whole extension %s@%s removed\n",
00424             exten, context);
00425       else
00426          ast_cli(fd, "Extension %s@%s with priority %d removed\n",
00427             exten, context, removing_priority);
00428          
00429       return RESULT_SUCCESS;
00430    }
00431 
00432    ast_cli(fd, "Failed to remove extension %s@%s\n", exten, context);
00433 
00434    return RESULT_FAILURE;
00435 }

static int handle_context_remove_ignorepat ( int  fd,
int  argc,
char *  argv[] 
) [static]

Definition at line 1398 of file pbx_config.c.

References ast_cli(), ast_context_remove_ignorepat(), RESULT_FAILURE, RESULT_SHOWUSAGE, and RESULT_SUCCESS.

01399 {
01400    if (argc != 5) return RESULT_SHOWUSAGE;
01401    if (strcmp(argv[3], "from")) return RESULT_SHOWUSAGE;
01402 
01403    if (ast_context_remove_ignorepat(argv[4], argv[2], registrar)) {
01404       switch (errno) {
01405          case EBUSY:
01406             ast_cli(fd, "Failed to lock context(s) list, please try again later\n");
01407             break;
01408 
01409          case ENOENT:
01410             ast_cli(fd, "There is no existence of '%s' context\n", argv[4]);
01411             break;
01412 
01413          case EINVAL:
01414             ast_cli(fd, "There is no existence of '%s' ignore pattern in '%s' context\n",
01415                argv[2], argv[4]);
01416             break;
01417 
01418          default:
01419             ast_cli(fd, "Failed to remove ignore pattern '%s' from '%s' context\n", argv[2], argv[4]);
01420             break;
01421       }
01422       return RESULT_FAILURE;
01423    }
01424 
01425    ast_cli(fd, "Ignore pattern '%s' removed from '%s' context\n",
01426       argv[2], argv[4]);
01427    return RESULT_SUCCESS;
01428 }

static int handle_reload_extensions ( int  fd,
int  argc,
char *  argv[] 
) [static]

Definition at line 1432 of file pbx_config.c.

References pbx_load_module(), RESULT_SHOWUSAGE, and RESULT_SUCCESS.

01433 {
01434    if (argc!=2) return RESULT_SHOWUSAGE;
01435    pbx_load_module();
01436    return RESULT_SUCCESS;
01437 }

static int handle_save_dialplan ( int  fd,
int  argc,
char *  argv[] 
) [static]

'save dialplan' CLI command implementation functions ...

Definition at line 922 of file pbx_config.c.

References ast_cli(), ast_config_AST_CONFIG_DIR, ast_config_destroy(), ast_config_load(), ast_get_context_name(), ast_get_context_registrar(), ast_get_extension_app(), ast_get_extension_app_data(), ast_get_extension_cidmatch(), ast_get_extension_label(), ast_get_extension_matchcid(), ast_get_extension_name(), ast_get_extension_priority(), ast_get_extension_registrar(), ast_get_ignorepat_name(), ast_get_ignorepat_registrar(), ast_get_include_name(), ast_get_include_registrar(), ast_get_switch_data(), ast_get_switch_name(), ast_get_switch_registrar(), ast_lock_context(), ast_lock_contexts(), ast_mutex_lock(), ast_mutex_unlock(), ast_strdupa, ast_unlock_context(), ast_unlock_contexts(), ast_variable_browse(), ast_walk_context_extensions(), ast_walk_context_ignorepats(), ast_walk_context_includes(), ast_walk_context_switches(), ast_walk_contexts(), ast_walk_extension_priorities(), cfg, el, ast_exten::label, ast_variable::name, ast_variable::next, option_priority_jumping, PRIORITY_HINT, RESULT_FAILURE, RESULT_SHOWUSAGE, RESULT_SUCCESS, and ast_variable::value.

00923 {
00924    char filename[256];
00925    struct ast_context *c;
00926    struct ast_config *cfg;
00927    struct ast_variable *v;
00928    int context_header_written;
00929    int incomplete = 0; /* incomplete config write? */
00930    FILE *output;
00931 
00932    if (! (static_config && !write_protect_config)) {
00933       ast_cli(fd,
00934          "I can't save dialplan now, see '%s' example file.\n",
00935          config);
00936       return RESULT_FAILURE;
00937    }
00938 
00939    if (argc != 2 && argc != 3) return RESULT_SHOWUSAGE;
00940 
00941    if (ast_mutex_lock(&save_dialplan_lock)) {
00942       ast_cli(fd,
00943          "Failed to lock dialplan saving (another proccess saving?)\n");
00944       return RESULT_FAILURE;
00945    }
00946 
00947    /* have config path? */
00948    if (argc == 3) {
00949       /* is there extension.conf too? */
00950       if (!strstr(argv[2], ".conf")) {
00951          /* no, only directory path, check for last '/' occurence */
00952          if (*(argv[2] + strlen(argv[2]) -1) == '/')
00953             snprintf(filename, sizeof(filename), "%s%s",
00954                argv[2], config);
00955          else
00956             /* without config extensions.conf, add it */
00957             snprintf(filename, sizeof(filename), "%s/%s",
00958                argv[2], config);
00959       } else
00960          /* there is an .conf */
00961          snprintf(filename, sizeof(filename), argv[2]);
00962    } else
00963       /* no config file, default one */
00964       snprintf(filename, sizeof(filename), "%s/%s",
00965          (char *)ast_config_AST_CONFIG_DIR, config);
00966 
00967    cfg = ast_config_load("extensions.conf");
00968 
00969    /* try to lock contexts list */
00970    if (ast_lock_contexts()) {
00971       ast_cli(fd, "Failed to lock contexts list\n");
00972       ast_mutex_unlock(&save_dialplan_lock);
00973       ast_config_destroy(cfg);
00974       return RESULT_FAILURE;
00975    }
00976 
00977    /* create new file ... */
00978    if (!(output = fopen(filename, "wt"))) {
00979       ast_cli(fd, "Failed to create file '%s'\n",
00980          filename);
00981       ast_unlock_contexts();
00982       ast_mutex_unlock(&save_dialplan_lock);
00983       ast_config_destroy(cfg);
00984       return RESULT_FAILURE;
00985    }
00986 
00987    /* fireout general info */
00988    fprintf(output, "[general]\nstatic=%s\nwriteprotect=%s\nautofallthrough=%s\nclearglobalvars=%s\npriorityjumping=%s\n\n",
00989       static_config ? "yes" : "no",
00990       write_protect_config ? "yes" : "no",
00991       autofallthrough_config ? "yes" : "no",
00992       clearglobalvars_config ? "yes" : "no",
00993       option_priority_jumping ? "yes" : "no");
00994 
00995    if ((v = ast_variable_browse(cfg, "globals"))) {
00996       fprintf(output, "[globals]\n");
00997       while(v) {
00998          fprintf(output, "%s => %s\n", v->name, v->value);
00999          v = v->next;
01000       }
01001       fprintf(output, "\n");
01002    }
01003 
01004    ast_config_destroy(cfg);
01005    
01006    /* walk all contexts */
01007    c = ast_walk_contexts(NULL);
01008    while (c) {
01009       context_header_written = 0;
01010    
01011       /* try to lock context and fireout all info */  
01012       if (!ast_lock_context(c)) {
01013          struct ast_exten *e, *last_written_e = NULL;
01014          struct ast_include *i;
01015          struct ast_ignorepat *ip;
01016          struct ast_sw *sw;
01017 
01018          /* registered by this module? */
01019          if (!strcmp(ast_get_context_registrar(c), registrar)) {
01020             fprintf(output, "[%s]\n", ast_get_context_name(c));
01021             context_header_written = 1;
01022          }
01023 
01024          /* walk extensions ... */
01025          e = ast_walk_context_extensions(c, NULL);
01026          while (e) {
01027             struct ast_exten *p;
01028 
01029             /* fireout priorities */
01030             p = ast_walk_extension_priorities(e, NULL);
01031             while (p) {
01032                if (!strcmp(ast_get_extension_registrar(p),
01033                   registrar)) {
01034          
01035                   /* make empty line between different extensions */ 
01036                   if (last_written_e != NULL &&
01037                      strcmp(ast_get_extension_name(last_written_e),
01038                         ast_get_extension_name(p)))
01039                      fprintf(output, "\n");
01040                   last_written_e = p;
01041             
01042                   if (!context_header_written) {
01043                      fprintf(output, "[%s]\n", ast_get_context_name(c));
01044                      context_header_written = 1;
01045                   }
01046 
01047                   if (ast_get_extension_priority(p)!=PRIORITY_HINT) {
01048                      char *tempdata, *startdata;
01049                      const char *el = ast_get_extension_label(p);
01050                      char label[128] = "";
01051 
01052                      tempdata = ast_strdupa(ast_get_extension_app_data(p));
01053 
01054                      startdata = tempdata;
01055                      while (*tempdata) {
01056                         if (*tempdata == '|')
01057                            *tempdata = ',';
01058                         tempdata++;
01059                      }
01060                      tempdata = startdata;
01061                      
01062                      if (el && (snprintf(label, sizeof(label), "(%s)", el) != (strlen(el) + 2)))
01063                         incomplete = 1; // error encountered or label is > 125 chars
01064 
01065                      if (ast_get_extension_matchcid(p)) {
01066                         fprintf(output, "exten => %s/%s,%d%s,%s(%s)\n",
01067                             ast_get_extension_name(p),
01068                             ast_get_extension_cidmatch(p),
01069                             ast_get_extension_priority(p), label,
01070                             ast_get_extension_app(p),
01071                             tempdata);
01072                      } else {
01073                         fprintf(output, "exten => %s,%d%s,%s(%s)\n",
01074                             ast_get_extension_name(p),
01075                             ast_get_extension_priority(p), label,
01076                             ast_get_extension_app(p),
01077                             tempdata);
01078                      }
01079                   } else {
01080                      fprintf(output, "exten => %s,hint,%s\n",
01081                          ast_get_extension_name(p),
01082                          ast_get_extension_app(p));
01083                   }
01084                   
01085                }
01086                p = ast_walk_extension_priorities(e, p);
01087             }
01088 
01089             e = ast_walk_context_extensions(c, e);
01090          }
01091 
01092          /* written any extensions? ok, write space between exten & inc */
01093          if (last_written_e) fprintf(output, "\n");
01094 
01095          /* walk through includes */
01096          i = ast_walk_context_includes(c, NULL);
01097          while (i) {
01098             if (!strcmp(ast_get_include_registrar(i), registrar)) {
01099                if (!context_header_written) {
01100                   fprintf(output, "[%s]\n", ast_get_context_name(c));
01101                   context_header_written = 1;
01102                }
01103                fprintf(output, "include => %s\n",
01104                   ast_get_include_name(i));
01105             }
01106             i = ast_walk_context_includes(c, i);
01107          }
01108 
01109          if (ast_walk_context_includes(c, NULL))
01110             fprintf(output, "\n");
01111 
01112          /* walk through switches */
01113          sw = ast_walk_context_switches(c, NULL);
01114          while (sw) {
01115             if (!strcmp(ast_get_switch_registrar(sw), registrar)) {
01116                if (!context_header_written) {
01117                   fprintf(output, "[%s]\n", ast_get_context_name(c));
01118                   context_header_written = 1;
01119                }
01120                fprintf(output, "switch => %s/%s\n",
01121                   ast_get_switch_name(sw),
01122                   ast_get_switch_data(sw));
01123             }
01124             sw = ast_walk_context_switches(c, sw);
01125          }
01126 
01127          if (ast_walk_context_switches(c, NULL))
01128             fprintf(output, "\n");
01129 
01130          /* fireout ignorepats ... */
01131          ip = ast_walk_context_ignorepats(c, NULL);
01132          while (ip) {
01133             if (!strcmp(ast_get_ignorepat_registrar(ip), registrar)) {
01134                if (!context_header_written) {
01135                   fprintf(output, "[%s]\n", ast_get_context_name(c));
01136                   context_header_written = 1;
01137                }
01138 
01139                fprintf(output, "ignorepat => %s\n",
01140                   ast_get_ignorepat_name(ip));
01141             }
01142             ip = ast_walk_context_ignorepats(c, ip);
01143          }
01144 
01145          ast_unlock_context(c);
01146       } else
01147          incomplete = 1;
01148 
01149       c = ast_walk_contexts(c);
01150    }  
01151 
01152    ast_unlock_contexts();
01153    ast_mutex_unlock(&save_dialplan_lock);
01154    fclose(output);
01155 
01156    if (incomplete) {
01157       ast_cli(fd, "Saved dialplan is incomplete\n");
01158       return RESULT_FAILURE;
01159    }
01160 
01161    ast_cli(fd, "Dialplan successfully saved into '%s'\n",
01162       filename);
01163    return RESULT_SUCCESS;
01164 }

char* key ( void   ) 

Returns the ASTERISK_GPL_KEY.

This returns the ASTERISK_GPL_KEY, signifiying that you agree to the terms of the GPL stated in the ASTERISK_GPL_KEY. Your module will not load if it does not return the EXACT message:

 char *key(void) {
         return ASTERISK_GPL_KEY;
 }

Returns:
ASTERISK_GPL_KEY

Definition at line 1838 of file pbx_config.c.

References ASTERISK_GPL_KEY.

01839 {
01840    return ASTERISK_GPL_KEY;
01841 }

int load_module ( void   ) 

Initialize the module.

Initialize the Agents module. This function is being called by Asterisk when loading the module. Among other thing it registers applications, cli commands and reads the cofiguration file.

Returns:
int Always 0.

Definition at line 1803 of file pbx_config.c.

References ast_cli_register(), context_add_extension_cli, context_add_ignorepat_cli, context_add_include_cli, context_dont_include_cli, context_remove_extension_cli, context_remove_ignorepat_cli, pbx_load_module(), reload_extensions_cli, and save_dialplan_cli.

static int pbx_load_module ( void   )  [static]

Definition at line 1616 of file pbx_config.c.

References ast_add_extension2(), ast_category_browse(), ast_config_destroy(), ast_config_load(), ast_context_add_ignorepat2(), ast_context_add_include2(), ast_context_add_switch2(), ast_context_create(), ast_context_verify_includes(), ast_false(), ast_findlabel_extension2(), ast_log(), ast_merge_contexts_and_delete(), ast_process_quotes_and_slashes(), ast_shrink_phone_number(), ast_true(), ast_variable_browse(), ast_variable_retrieve(), ast_walk_contexts(), cfg, free, FREE, ast_variable::lineno, local_contexts, LOG_ERROR, LOG_WARNING, ast_variable::name, ast_variable::next, option_dontwarn, option_priority_jumping, pbx_builtin_setvar_helper(), pbx_set_autofallthrough(), pbx_substitute_variables_helper(), PRIORITY_HINT, strdup, strsep(), and ast_variable::value.

01617 {
01618    struct ast_config *cfg;
01619    struct ast_variable *v;
01620    char *cxt, *ext, *pri, *appl, *data, *tc, *cidmatch;
01621    struct ast_context *con;
01622    char *end;
01623    char *label;
01624    char realvalue[256];
01625    int lastpri = -2;
01626 
01627    cfg = ast_config_load(config);
01628    if (cfg) {
01629       /* Use existing config to populate the PBX table */
01630       static_config = ast_true(ast_variable_retrieve(cfg, "general",
01631                             "static"));
01632       write_protect_config = ast_true(ast_variable_retrieve(cfg, "general",
01633                               "writeprotect"));
01634       autofallthrough_config = ast_true(ast_variable_retrieve(cfg, "general",
01635                            "autofallthrough"));
01636       clearglobalvars_config = ast_true(ast_variable_retrieve(cfg, "general", 
01637                            "clearglobalvars"));
01638       option_priority_jumping = !ast_false(ast_variable_retrieve(cfg, "general",
01639                               "priorityjumping"));
01640 
01641       v = ast_variable_browse(cfg, "globals");
01642       while(v) {
01643          memset(realvalue, 0, sizeof(realvalue));
01644          pbx_substitute_variables_helper(NULL, v->value, realvalue, sizeof(realvalue) - 1);
01645          pbx_builtin_setvar_helper(NULL, v->name, realvalue);
01646          v = v->next;
01647       }
01648       cxt = ast_category_browse(cfg, NULL);
01649       while(cxt) {
01650          /* All categories but "general" or "globals" are considered contexts */
01651          if (!strcasecmp(cxt, "general") || !strcasecmp(cxt, "globals")) {
01652             cxt = ast_category_browse(cfg, cxt);
01653             continue;
01654          }
01655          if ((con=ast_context_create(&local_contexts,cxt, registrar))) {
01656             v = ast_variable_browse(cfg, cxt);
01657             while(v) {
01658                if (!strcasecmp(v->name, "exten")) {
01659                   char *stringp=NULL;
01660                   int ipri = -2;
01661                   char realext[256]="";
01662                   char *plus, *firstp, *firstc;
01663                   tc = strdup(v->value);
01664                   if(tc!=NULL){
01665                      stringp=tc;
01666                      ext = strsep(&stringp, ",");
01667                      if (!ext)
01668                         ext="";
01669                      pbx_substitute_variables_helper(NULL, ext, realext, sizeof(realext) - 1);
01670                      cidmatch = strchr(realext, '/');
01671                      if (cidmatch) {
01672                         *cidmatch = '\0';
01673                         cidmatch++;
01674                         ast_shrink_phone_number(cidmatch);
01675                      }
01676                      pri = strsep(&stringp, ",");
01677                      if (!pri)
01678                         pri="";
01679                      label = strchr(pri, '(');
01680                      if (label) {
01681                         *label = '\0';
01682                         label++;
01683                         end = strchr(label, ')');
01684                         if (end)
01685                            *end = '\0';
01686                         else
01687                            ast_log(LOG_WARNING, "Label missing trailing ')' at line %d\n", v->lineno);
01688                      }
01689                      plus = strchr(pri, '+');
01690                      if (plus) {
01691                         *plus = '\0';
01692                         plus++;
01693                      }
01694                      if (!strcmp(pri,"hint"))
01695                         ipri=PRIORITY_HINT;
01696                      else if (!strcmp(pri, "next") || !strcmp(pri, "n")) {
01697                         if (lastpri > -2)
01698                            ipri = lastpri + 1;
01699                         else
01700                            ast_log(LOG_WARNING, "Can't use 'next' priority on the first entry!\n");
01701                      } else if (!strcmp(pri, "same") || !strcmp(pri, "s")) {
01702                         if (lastpri > -2)
01703                            ipri = lastpri;
01704                         else
01705                            ast_log(LOG_WARNING, "Can't use 'same' priority on the first entry!\n");
01706                      } else  {
01707                         if (sscanf(pri, "%d", &ipri) != 1) {
01708                            if ((ipri = ast_findlabel_extension2(NULL, con, realext, pri, cidmatch)) < 1) {
01709                               ast_log(LOG_WARNING, "Invalid priority/label '%s' at line %d\n", pri, v->lineno);
01710                               ipri = 0;
01711                            }
01712                         }
01713                      }
01714                      appl = stringp;
01715                      if (!appl)
01716                         appl="";
01717                      /* Find the first occurrence of either '(' or ',' */
01718                      firstc = strchr(appl, ',');
01719                      firstp = strchr(appl, '(');
01720                      if (firstc && ((!firstp) || (firstc < firstp))) {
01721                         /* comma found, no parenthesis */
01722                         /* or both found, but comma found first */
01723                         appl = strsep(&stringp, ",");
01724                         data = stringp;
01725                      } else if ((!firstc) && (!firstp)) {
01726                         /* Neither found */
01727                         data = "";
01728                      } else {
01729                         /* Final remaining case is parenthesis found first */
01730                         appl = strsep(&stringp, "(");
01731                         data = stringp;
01732                         end = strrchr(data, ')');
01733                         if ((end = strrchr(data, ')'))) {
01734                            *end = '\0';
01735                         } else {
01736                            ast_log(LOG_WARNING, "No closing parenthesis found? '%s(%s'\n", appl, data);
01737                         }
01738                         ast_process_quotes_and_slashes(data, ',', '|');
01739                      }
01740 
01741                      if (!data)
01742                         data="";
01743                      while(*appl && (*appl < 33)) appl++;
01744                      if (ipri) {
01745                         if (plus)
01746                            ipri += atoi(plus);
01747                         lastpri = ipri;
01748                         if(!option_dontwarn) {
01749                            if (!strcmp(realext, "_."))
01750                               ast_log(LOG_WARNING, "The use of '_.' for an extension is strongly discouraged and can have unexpected behavior.  Please use '_X.' instead at line %d\n", v->lineno);
01751                         }
01752                         if (ast_add_extension2(con, 0, realext, ipri, label, cidmatch, appl, strdup(data), FREE, registrar)) {
01753                            ast_log(LOG_WARNING, "Unable to register extension at line %d\n", v->lineno);
01754                         }
01755                      }
01756                      free(tc);
01757                   } else {
01758                      ast_log(LOG_ERROR, "Memory allocation failure\n");
01759                   }
01760                } else if(!strcasecmp(v->name, "include")) {
01761                   memset(realvalue, 0, sizeof(realvalue));
01762                   pbx_substitute_variables_helper(NULL, v->value, realvalue, sizeof(realvalue) - 1);
01763                   if (ast_context_add_include2(con, realvalue, registrar))
01764                      ast_log(LOG_WARNING, "Unable to include context '%s' in context '%s'\n", v->value, cxt);
01765                } else if(!strcasecmp(v->name, "ignorepat")) {
01766                   memset(realvalue, 0, sizeof(realvalue));
01767                   pbx_substitute_variables_helper(NULL, v->value, realvalue, sizeof(realvalue) - 1);
01768                   if (ast_context_add_ignorepat2(con, realvalue, registrar))
01769                      ast_log(LOG_WARNING, "Unable to include ignorepat '%s' in context '%s'\n", v->value, cxt);
01770                } else if (!strcasecmp(v->name, "switch") || !strcasecmp(v->name, "lswitch") || !strcasecmp(v->name, "eswitch")) {
01771                   char *stringp=NULL;
01772                   memset(realvalue, 0, sizeof(realvalue));
01773                   if (!strcasecmp(v->name, "switch"))
01774                      pbx_substitute_variables_helper(NULL, v->value, realvalue, sizeof(realvalue) - 1);
01775                   else
01776                      strncpy(realvalue, v->value, sizeof(realvalue) - 1);
01777                   tc = realvalue;
01778                   stringp=tc;
01779                   appl = strsep(&stringp, "/");
01780                   data = strsep(&stringp, "");
01781                   if (!data)
01782                      data = "";
01783                   if (ast_context_add_switch2(con, appl, data, !strcasecmp(v->name, "eswitch"), registrar))
01784                      ast_log(LOG_WARNING, "Unable to include switch '%s' in context '%s'\n", v->value, cxt);
01785                }
01786                v = v->next;
01787             }
01788          }
01789          cxt = ast_category_browse(cfg, cxt);
01790       }
01791       ast_config_destroy(cfg);
01792    }
01793    ast_merge_contexts_and_delete(&local_contexts,registrar);
01794 
01795    for (con = ast_walk_contexts(NULL); con; con = ast_walk_contexts(con))
01796       ast_context_verify_includes(con);
01797 
01798    pbx_set_autofallthrough(autofallthrough_config);
01799 
01800    return 0;
01801 }

int reload ( void   ) 

Reload stuff.

This function is where any reload routines take place. Re-read config files, change signalling, whatever is appropriate on a reload.

Returns:
The return value is not used.

Definition at line 1820 of file pbx_config.c.

References pbx_builtin_clear_globals(), and pbx_load_module().

01821 {
01822    if (clearglobalvars_config)
01823       pbx_builtin_clear_globals();
01824    pbx_load_module();
01825    return 0;
01826 }

int unload_module ( void   ) 

Cleanup all module structures, sockets, etc.

Standard module functions ...

Definition at line 1601 of file pbx_config.c.

References ast_cli_unregister(), ast_context_destroy(), context_add_extension_cli, context_add_ignorepat_cli, context_add_include_cli, context_dont_include_cli, context_remove_extension_cli, context_remove_ignorepat_cli, reload_extensions_cli, and save_dialplan_cli.

int usecount ( void   ) 

Provides a usecount.

This function will be called by various parts of asterisk. Basically, all it has to do is to return a usecount when called. You will need to maintain your usecount within the module somewhere. The usecount should be how many channels provided by this module are in use.

Returns:
The module's usecount.

Definition at line 1828 of file pbx_config.c.

01829 {
01830    return 0;
01831 }


Variable Documentation

int autofallthrough_config = 0 [static]

Definition at line 60 of file pbx_config.c.

int clearglobalvars_config = 0 [static]

Definition at line 61 of file pbx_config.c.

char* config = "extensions.conf" [static]

Definition at line 55 of file pbx_config.c.

struct ast_cli_entry context_add_extension_cli [static]

Initial value:

   { { "add", "extension", NULL }, handle_context_add_extension,
      "Add new extension into context", context_add_extension_help,
      complete_context_add_extension }

Definition at line 1579 of file pbx_config.c.

Referenced by load_module(), and unload_module().

char context_add_extension_help[] [static]

Definition at line 91 of file pbx_config.c.

struct ast_cli_entry context_add_ignorepat_cli [static]

Initial value:

   { { "add", "ignorepat", NULL }, handle_context_add_ignorepat,
      "Add new ignore pattern", context_add_ignorepat_help,
      complete_context_add_ignorepat }

Definition at line 1584 of file pbx_config.c.

Referenced by load_module(), and unload_module().

char context_add_ignorepat_help[] [static]

Initial value:

"Usage: add ignorepat <pattern> into <context>\n"
"       This command adds a new ignore pattern into context <context>\n"
"\n"
"Example: add ignorepat _3XX into local\n"

Definition at line 101 of file pbx_config.c.

struct ast_cli_entry context_add_include_cli [static]

Initial value:

   { { "include", "context", NULL }, handle_context_add_include,
      "Include context in other context", context_add_include_help,
      complete_context_add_include }

Definition at line 1570 of file pbx_config.c.

Referenced by load_module(), and unload_module().

char context_add_include_help[] [static]

Initial value:

"Usage: include <context> in <context>\n"
"       Include a context in another context.\n"

Definition at line 80 of file pbx_config.c.

struct ast_cli_entry context_dont_include_cli [static]

Initial value:

   { { "dont", "include", NULL }, handle_context_dont_include,
      "Remove a specified include from context", context_dont_include_help,
      complete_context_dont_include }
CLI entries for commands provided by this module

Definition at line 1560 of file pbx_config.c.

Referenced by load_module(), and unload_module().

char context_dont_include_help[] [static]

Initial value:

"Usage: dont include <context> in <context>\n"
"       Remove an included context from another context.\n"

Definition at line 70 of file pbx_config.c.

struct ast_cli_entry context_remove_extension_cli [static]

Initial value:

   { { "remove", "extension", NULL }, handle_context_remove_extension,
      "Remove a specified extension", context_remove_extension_help,
      complete_context_remove_extension }

Definition at line 1565 of file pbx_config.c.

Referenced by load_module(), and unload_module().

char context_remove_extension_help[] [static]

Initial value:

"Usage: remove extension exten@context [priority]\n"
"       Remove an extension from a given context. If a priority\n"
"       is given, only that specific priority from the given extension\n"
"       will be removed.\n"

Definition at line 74 of file pbx_config.c.

struct ast_cli_entry context_remove_ignorepat_cli [static]

Initial value:

   { { "remove", "ignorepat", NULL }, handle_context_remove_ignorepat,
      "Remove ignore pattern from context", context_remove_ignorepat_help,
      complete_context_remove_ignorepat }

Definition at line 1589 of file pbx_config.c.

Referenced by load_module(), and unload_module().

char context_remove_ignorepat_help[] [static]

Initial value:

"Usage: remove ignorepat <pattern> from <context>\n"
"       This command removes an ignore pattern from context <context>\n"
"\n"
"Example: remove ignorepat _3XX from local\n"

Definition at line 107 of file pbx_config.c.

char* dtext = "Text Extension Configuration" [static]

Definition at line 54 of file pbx_config.c.

struct ast_context* local_contexts = NULL [static]

Definition at line 65 of file pbx_config.c.

Referenced by ast_ael_compile(), ast_context_create(), handle_context(), handle_macro(), handle_root_token(), and pbx_load_module().

char* registrar = "pbx_config" [static]

Definition at line 56 of file pbx_config.c.

struct ast_cli_entry reload_extensions_cli [static]

Initial value:

 
   { { "extensions", "reload", NULL}, handle_reload_extensions,
      "Reload extensions and *only* extensions", reload_extensions_help }

Definition at line 1594 of file pbx_config.c.

Referenced by load_module(), and unload_module().

char reload_extensions_help[] [static]

Definition at line 113 of file pbx_config.c.

struct ast_cli_entry save_dialplan_cli [static]

Initial value:

   { { "save", "dialplan", NULL }, handle_save_dialplan,
      "Save dialplan", save_dialplan_help }

Definition at line 1575 of file pbx_config.c.

Referenced by load_module(), and unload_module().

char save_dialplan_help[] [static]

Definition at line 84 of file pbx_config.c.

int static_config = 0 [static]

Definition at line 58 of file pbx_config.c.

int write_protect_config = 1 [static]

Definition at line 59 of file pbx_config.c.


Generated on Sat Mar 24 22:57:15 2007 for Asterisk - the Open Source PBX by  doxygen 1.4.7