#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/module.h"
#include "asterisk/logger.h"
#include "asterisk/cli.h"
#include "asterisk/callerid.h"
Include dependency graph for pbx_ael.c:

Go to the source code of this file.
Data Structures | |
| struct | fillin |
| struct | stringlink |
Defines | |
| #define | DEBUG_CONTEXTS (1 << 3) |
| #define | DEBUG_MACROS (1 << 2) |
| #define | DEBUG_READ (1 << 0) |
| #define | DEBUG_TOKENS (1 << 1) |
| #define | FILLIN_BREAK 1 |
| #define | FILLIN_CONTINUE 2 |
| #define | FREE free |
Functions | |
| static int | __build_step (const char *what, const char *name, const char *filename, int lineno, struct ast_context *con, char *exten, int *pos, char *data, struct fillin **fillout, char **label) |
| static char * | __grab_token (char *src, const char *filename, int lineno, int link) |
| static int | ael_debug_contexts (int fd, int argc, char *argv[]) |
| static int | ael_debug_macros (int fd, int argc, char *argv[]) |
| static int | ael_debug_read (int fd, int argc, char *argv[]) |
| static int | ael_debug_tokens (int fd, int argc, char *argv[]) |
| static int | ael_no_debug (int fd, int argc, char *argv[]) |
| static int | ael_reload (int fd, int argc, char *argv[]) |
| static void | arg_free (struct stringlink *cur) |
| static struct stringlink * | arg_parse (char *args, const char *filename, int lineno) |
| static char * | argument_end (char *str) |
| static int | ast_ael_compile (struct ast_context **local_contexts, const char *filename) |
| static int | build_step (const char *what, const char *name, const char *filename, int lineno, struct ast_context *con, char *exten, int *pos, char *data, struct fillin **fillout, char **label) |
| char * | description (void) |
| Provides a description of the module. | |
| static void | fillin_free (struct fillin *fillin) |
| static void | fillin_process (struct ast_context *con, struct fillin *fillin, const char *filename, int lineno, const char *breakexten, int breakprio, const char *contexten, int contprio) |
| static void | gen_match_to_pattern (const char *pattern, char *result) |
| static const char * | get_case (char *s, char **restout, int *pattern) |
| static char * | grab_else (char *args, const char *filename, int lineno) |
| static char * | grab_token (char *src, const char *filename, int lineno) |
| static void | handle_context (struct ast_context **local_contexts, struct stringlink *vars, const char *filename, int lineno) |
| static void | handle_globals (struct stringlink *vars) |
| static void | handle_macro (struct ast_context **local_contexts, struct stringlink *vars, const char *filename, int lineno) |
| static int | handle_root_token (struct ast_context **local_contexts, char *token, int level, const char *filename, int lineno) |
| char * | key (void) |
| Returns the ASTERISK_GPL_KEY. | |
| int | load_module (void) |
| Initialize the module. | |
| static int | match_assignment (char *variable, char **value) |
| static int | matches_extension (char *exten, char **extout) |
| static int | matches_keyword (const char *data, const char *keyword) |
| static int | matches_label (char *data, char **rest) |
| static struct stringlink * | param_parse (char *parms, const char *macro, const char *filename, int lineno) |
| static int | parse_catch (char *data, char **catch, char **rest) |
| static void | parse_keyword (char *s, char **o) |
| static int | pbx_load_module (void) |
| int | reload (void) |
| Reload stuff. | |
| static struct stringlink * | split_params (char *token, const char *filename, int lineno) |
| static struct stringlink * | split_token (char *token, const char *filename, int lineno) |
| int | unload_module (void) |
| Cleanup all module structures, sockets, etc. | |
| int | usecount (void) |
| Provides a usecount. | |
Variables | |
| static struct ast_cli_entry | ael_cli [] |
| static int | aeldebug = 0 |
| static char * | config = "extensions.ael" |
| static char * | dtext = "Asterisk Extension Language Compiler" |
| static char * | registrar = "pbx_ael" |
Definition in file pbx_ael.c.
| #define DEBUG_CONTEXTS (1 << 3) |
| #define DEBUG_MACROS (1 << 2) |
| #define DEBUG_TOKENS (1 << 1) |
Definition at line 68 of file pbx_ael.c.
Referenced by __build_step(), __grab_token(), ael_debug_tokens(), arg_parse(), get_case(), grab_else(), and handle_root_token().
| #define FILLIN_BREAK 1 |
| #define FILLIN_CONTINUE 2 |
| static int __build_step | ( | const char * | what, | |
| const char * | name, | |||
| const char * | filename, | |||
| int | lineno, | |||
| struct ast_context * | con, | |||
| char * | exten, | |||
| int * | pos, | |||
| char * | data, | |||
| struct fillin ** | fillout, | |||
| char ** | label | |||
| ) | [static] |
Definition at line 501 of file pbx_ael.c.
References app, arg_free(), arg_parse(), argument_end(), ast_add_extension2(), ast_log(), ast_process_quotes_and_slashes(), ast_strlen_zero(), ast_verbose(), build_step(), stringlink::data, DEBUG_TOKENS, FILLIN_BREAK, FILLIN_CONTINUE, fillin_free(), fillin_process(), FREE, gen_match_to_pattern(), get_case(), grab_else(), ifend, LOG_NOTICE, LOG_WARNING, malloc, match_assignment(), matches_keyword(), matches_label(), stringlink::next, and strdup.
Referenced by build_step().
00502 { 00503 char *app; 00504 char *args; 00505 char *c; 00506 char *margs=NULL; 00507 char *oargs; 00508 char *rest; 00509 const char *curcase, *newcase; 00510 struct stringlink *swargs, *cur; 00511 int cpos; 00512 int mlen; 00513 int pattern = 0; 00514 struct fillin *fillin; 00515 00516 data = ast_skip_blanks(data); 00517 if (matches_label(data, &c)) { 00518 *label = data; 00519 data = c; 00520 data = ast_skip_blanks(data); 00521 } 00522 if (ast_strlen_zero(data)) 00523 return 0; 00524 if (matches_keyword(data, "switch")) { 00525 fillin = NULL; 00526 /* Switch */ 00527 args = data + strlen("switch"); 00528 while ((*args < 33) && (*args != '(')) args++; 00529 if ((*args == '(') && (c = argument_end(args))) { 00530 args++; 00531 *c = '\0'; 00532 c++; 00533 if (aeldebug & DEBUG_TOKENS) 00534 ast_verbose("--SWITCH on : %s\n", args); 00535 mlen = strlen(exten) + 128 + strlen(args) + strlen(name); 00536 margs = alloca(mlen); 00537 app = "Goto"; 00538 sprintf(margs, "sw-%d-%s|1", *pos, args); 00539 ast_process_quotes_and_slashes(margs, ',', '|'); 00540 oargs = args; 00541 args = margs; 00542 if (ast_add_extension2(con, 0, exten, *pos, *label, NULL, app, strdup(args), FREE, registrar)) 00543 ast_log(LOG_WARNING, "Unable to add step at priority '%d' of %s '%s'\n", *pos, what, name); 00544 else { 00545 *label = NULL; 00546 (*pos)++; 00547 } 00548 app = "NoOp"; 00549 sprintf(margs, "Finish switch-%d", *pos - 1); 00550 if (ast_add_extension2(con, 0, exten, *pos, *label, NULL, app, strdup(args), FREE, registrar)) 00551 ast_log(LOG_WARNING, "Unable to add step at priority '%d' of %s '%s'\n", *pos, what, name); 00552 else { 00553 *label = NULL; 00554 (*pos)++; 00555 } 00556 c = ast_skip_blanks(c); 00557 if (aeldebug & DEBUG_TOKENS) 00558 ast_verbose("ARG Parsing '%s'\n", c); 00559 swargs = arg_parse(c, filename, lineno); 00560 cur = swargs; 00561 curcase = NULL; 00562 while(cur) { 00563 if ((newcase = get_case(cur->data, &rest, &pattern))) { 00564 if (aeldebug & DEBUG_TOKENS) 00565 ast_verbose("--NEWCASE: '%s'!\n", newcase); 00566 if (curcase) { 00567 char zbuf[256]; 00568 00569 /* Handle fall through */ 00570 char tmp[strlen(newcase) + strlen(name) + 40]; 00571 gen_match_to_pattern(newcase,zbuf); 00572 sprintf(tmp, "sw-%d-%s|%d", *pos - 2, zbuf, 1); 00573 ast_add_extension2(con, 0, margs, cpos, NULL, NULL, "Goto", strdup(tmp), FREE, registrar); 00574 } 00575 curcase = newcase; 00576 cpos = 1; 00577 if (pattern) 00578 snprintf(margs, mlen, "_sw-%d-%s", *pos - 2, curcase); 00579 else 00580 snprintf(margs, mlen, "sw-%d-%s", *pos - 2, curcase); 00581 if (!strcasecmp(rest, "break")) { 00582 char tmp[strlen(exten) + 10]; 00583 sprintf(tmp, "%s|%d", exten, *pos - 1); 00584 ast_add_extension2(con, 0, exten, cpos, *label, NULL, "Goto", strdup(tmp), FREE, registrar); 00585 curcase = NULL; 00586 *label = NULL; 00587 } else 00588 build_step("switch", margs, filename, lineno, con, margs, &cpos, rest, &fillin, label); 00589 } else if (curcase) { 00590 if (aeldebug & DEBUG_TOKENS) 00591 ast_verbose("Building statement from '%s'\n", rest); 00592 if (!strcasecmp(rest, "break")) { 00593 char tmp[strlen(exten) + 10]; 00594 sprintf(tmp, "%s|%d", exten, *pos - 1); 00595 ast_add_extension2(con, 0, margs, cpos, *label, NULL, "Goto", strdup(tmp), FREE, registrar); 00596 curcase = NULL; 00597 *label = NULL; 00598 } else 00599 build_step("switch", margs, filename, lineno, con, margs, &cpos, rest, &fillin, label); 00600 } else 00601 ast_log(LOG_WARNING, "Unreachable code in switch at about line %d of %s\n", lineno, filename); 00602 if (aeldebug & DEBUG_TOKENS) 00603 ast_verbose("--SWARG: %s\n", cur->data); 00604 cur = cur->next; 00605 } 00606 /* Can't do anything with these */ 00607 fillin_process(con, fillin, filename, lineno, NULL, 0, NULL, 0); 00608 fillin_free(fillin); 00609 arg_free(swargs); 00610 } else 00611 ast_log(LOG_WARNING, "Syntax error in switch declaration in %s around line %d!\n", filename, lineno); 00612 00613 } else if (matches_keyword(data, "if")) { 00614 /* If... */ 00615 args = data + strlen("if"); 00616 while ((*args < 33) && (*args != '(')) args++; 00617 if ((*args == '(') && (c = argument_end(args))) { 00618 int ifblock; 00619 int ifstart; 00620 int elsestart; 00621 int ifend; 00622 int ifskip; 00623 char *elses; 00624 char *iflabel; 00625 args++; 00626 *c = '\0'; 00627 c++; 00628 c = ast_skip_blanks(c); 00629 if (aeldebug & DEBUG_TOKENS) 00630 ast_verbose("--IF on : '%s' : '%s'\n", args, c); 00631 mlen = strlen(exten) + 128 + strlen(args) + strlen(name); 00632 margs = alloca(mlen); 00633 /* Remember where the ifblock starts, and skip over */ 00634 ifblock = (*pos)++; 00635 iflabel = *label; 00636 *label = NULL; 00637 /* Remember where the start of the ifblock is */ 00638 ifstart = *pos; 00639 snprintf(margs, mlen, "if-%s-%d", name, ifblock); 00640 /* Now process the block of the if */ 00641 if (aeldebug & DEBUG_TOKENS) 00642 ast_verbose("Searching for elses in '%s'\n", c); 00643 elses = grab_else(c, filename, lineno); 00644 build_step("if", margs, filename, lineno, con, exten, pos, c, fillout, label); 00645 if (elses) { 00646 /* Reserve a goto to exit the if */ 00647 ifskip = *pos; 00648 (*pos)++; 00649 elsestart = *pos; 00650 build_step("else", margs, filename, lineno, con, exten, pos, elses, fillout, label); 00651 } else { 00652 elsestart = *pos; 00653 ifskip = 0; 00654 } 00655 ifend = *pos; 00656 (*pos)++; 00657 app = "NoOp"; 00658 snprintf(margs, mlen, "Finish if-%s-%d", name, ifblock); 00659 if (ast_add_extension2(con, 0, exten, ifend, *label, NULL, app, strdup(margs), FREE, registrar)) 00660 ast_log(LOG_WARNING, "Unable to add step at priority '%d' of %s '%s'\n", *pos, what, name); 00661 *label = NULL; 00662 app = "GotoIf"; 00663 snprintf(margs, mlen, "$[ %s ]?%d:%d", args, ifstart, elsestart); 00664 if (ast_add_extension2(con, 0, exten, ifblock, iflabel, NULL, app, strdup(margs), FREE, registrar)) 00665 ast_log(LOG_WARNING, "Unable to add step at priority '%d' of %s '%s'\n", *pos, what, name); 00666 if (ifskip) { 00667 /* Skip as appropriate around else clause */ 00668 snprintf(margs, mlen, "%d", ifend); 00669 if (ast_add_extension2(con, 0, exten, ifskip, NULL, NULL, "Goto", strdup(margs), FREE, registrar)) 00670 ast_log(LOG_WARNING, "Unable to add step at priority '%d' of %s '%s'\n", *pos, what, name); 00671 } 00672 } else 00673 ast_log(LOG_WARNING, "Syntax error in if declaration in %s around line %d!\n", filename, lineno); 00674 } else if (matches_keyword(data, "while")) { 00675 /* While... */ 00676 fillin = NULL; 00677 args = data + strlen("while"); 00678 while ((*args < 33) && (*args != '(')) args++; 00679 if ((*args == '(') && (c = argument_end(args))) { 00680 int whileblock; 00681 int whilestart; 00682 int whileend; 00683 char *whilelabel; 00684 args++; 00685 *c = '\0'; 00686 c++; 00687 c = ast_skip_blanks(c); 00688 if (aeldebug & DEBUG_TOKENS) 00689 ast_verbose("--WHILE on : '%s' : '%s'\n", args, c); 00690 mlen = strlen(exten) + 128 + strlen(args) + strlen(name); 00691 margs = alloca(mlen); 00692 /* Remember where to put the conditional, and keep its position */ 00693 whilestart = (*pos); 00694 whilelabel = *label; 00695 *label = NULL; 00696 (*pos)++; 00697 /* Remember where the whileblock starts */ 00698 whileblock = (*pos); 00699 snprintf(margs, mlen, "while-%s-%d", name, whilestart); 00700 build_step("while", margs, filename, lineno, con, exten, pos, c, &fillin, label); 00701 /* Close the loop */ 00702 app = "Goto"; 00703 snprintf(margs, mlen, "%d", whilestart); 00704 if (ast_add_extension2(con, 0, exten, (*pos)++, *label, NULL, app, strdup(margs), FREE, registrar)) 00705 ast_log(LOG_WARNING, "Unable to add step at priority '%d' of %s '%s'\n", *pos, what, name); 00706 *label = NULL; 00707 whileend = (*pos); 00708 /* Place trailer */ 00709 app = "NoOp"; 00710 snprintf(margs, mlen, "Finish while-%s-%d", name, whilestart); 00711 if (ast_add_extension2(con, 0, exten, (*pos)++, *label, NULL, app, strdup(margs), FREE, registrar)) 00712 ast_log(LOG_WARNING, "Unable to add step at priority '%d' of %s '%s'\n", *pos, what, name); 00713 *label = NULL; 00714 app = "GotoIf"; 00715 snprintf(margs, mlen, "$[ %s ]?%d:%d", args, whileblock, whileend); 00716 if (ast_add_extension2(con, 0, exten, whilestart, whilelabel, NULL, app, strdup(margs), FREE, registrar)) 00717 ast_log(LOG_WARNING, "Unable to add step at priority '%d' of %s '%s'\n", *pos, what, name); 00718 fillin_process(con, fillin, filename, lineno, exten, whileend, exten, whilestart); 00719 fillin_free(fillin); 00720 } else 00721 ast_log(LOG_WARNING, "Syntax error in while declaration in %s around line %d!\n", filename, lineno); 00722 } else if (matches_keyword(data, "jump")) { 00723 char *p; 00724 /* Jump... */ 00725 fillin = NULL; 00726 args = data + strlen("jump"); 00727 args = ast_skip_blanks(args); 00728 if (aeldebug & DEBUG_TOKENS) 00729 ast_verbose("--JUMP to : '%s'\n", args); 00730 p = strchr(args, ','); 00731 if (p) { 00732 *p = '\0'; 00733 p++; 00734 } else 00735 p = "1"; 00736 c = strchr(args, '@'); 00737 if (c) { 00738 *c = '\0'; 00739 c++; 00740 } 00741 mlen = strlen(exten) + 128 + strlen(args) + strlen(name) + (c ? strlen(c) : 0); 00742 margs = alloca(mlen); 00743 if (c) 00744 snprintf(margs, mlen, "%s|%s|%s", c,args, p); 00745 else 00746 snprintf(margs, mlen, "%s|%s", args, p); 00747 app = "Goto"; 00748 if (ast_add_extension2(con, 0, exten, (*pos)++, *label, NULL, app, strdup(margs), FREE, registrar)) 00749 ast_log(LOG_WARNING, "Unable to add step at priority '%d' of %s '%s'\n", *pos, what, name); 00750 *label = NULL; 00751 } else if (matches_keyword(data, "goto")) { 00752 /* Jump... */ 00753 fillin = NULL; 00754 args = data + strlen("goto"); 00755 args = ast_skip_blanks(args); 00756 if (aeldebug & DEBUG_TOKENS) 00757 ast_verbose("--GOTO to : '%s'\n", args); 00758 app = "Goto"; 00759 if (args[0] == '(' && args[strlen(args) - 1] == ')') { 00760 args[0] = '\0'; 00761 args++; 00762 args[strlen(args) - 1] = '\0'; 00763 } 00764 if (ast_add_extension2(con, 0, exten, (*pos)++, *label, NULL, app, strdup(args), FREE, registrar)) 00765 ast_log(LOG_WARNING, "Unable to add step at priority '%d' of %s '%s'\n", *pos, what, name); 00766 *label = NULL; 00767 } else if (matches_keyword(data, "for")) { 00768 /* While... */ 00769 fillin = NULL; 00770 args = data + strlen("for"); 00771 while ((*args < 33) && (*args != '(')) args++; 00772 if ((*args == '(') && (c = argument_end(args))) { 00773 int forblock; 00774 int forprep; 00775 int forstart; 00776 int forend; 00777 struct stringlink *fields; 00778 char *tmp; 00779 char *forlabel = NULL; 00780 args++; 00781 *c = '\0'; 00782 c++; 00783 c = ast_skip_blanks(c); 00784 /* Parse arguments first */ 00785 tmp = alloca(strlen(args) + 10); 00786 if (tmp) { 00787 snprintf(tmp, strlen(args) + 10, "{%s;}", args); 00788 fields = arg_parse(tmp, filename, lineno); 00789 } else 00790 fields = NULL; 00791 if (fields && fields->next && fields->next->next) { 00792 if (aeldebug & DEBUG_TOKENS) 00793 ast_verbose("--FOR ('%s' ; '%s' ; '%s') : '%s'\n", fields->data, fields->next->data, fields->next->next->data, c); 00794 mlen = strlen(exten) + 128 + strlen(args) + strlen(name); 00795 margs = alloca(mlen); 00796 forprep = *pos; 00797 snprintf(margs, mlen, "for-%s-%d", name, forprep); 00798 fillin = NULL; 00799 build_step("while", margs, filename, lineno, con, exten, pos, fields->data, &fillin, label); 00800 /* Remember where to put the conditional, and keep its position */ 00801 forstart = (*pos); 00802 forlabel = *label; 00803 (*pos)++; 00804 *label = NULL; 00805 /* Remember where the whileblock starts */ 00806 forblock = (*pos); 00807 build_step("for", margs, filename, lineno, con, exten, pos, c, &fillin, label); 00808 build_step("for", margs, filename, lineno, con, exten, pos, fields->next->next->data, &fillin, label); 00809 /* Close the loop */ 00810 app = "Goto"; 00811 snprintf(margs, mlen, "%d", forstart); 00812 if (ast_add_extension2(con, 0, exten, (*pos)++, *label, NULL, app, strdup(margs), FREE, registrar)) 00813 ast_log(LOG_WARNING, "Unable to add step at priority '%d' of %s '%s'\n", *pos, what, name); 00814 *label = NULL; 00815 forend = (*pos); 00816 /* Place trailer */ 00817 app = "NoOp"; 00818 snprintf(margs, mlen, "Finish for-%s-%d", name, forprep); 00819 if (ast_add_extension2(con, 0, exten, (*pos)++, *label, NULL, app, strdup(margs), FREE, registrar)) 00820 ast_log(LOG_WARNING, "Unable to add step at priority '%d' of %s '%s'\n", *pos, what, name); 00821 *label = NULL; 00822 app = "GotoIf"; 00823 snprintf(margs, mlen, "$[ %s ]?%d:%d", fields->next->data, forblock, forend); 00824 if (ast_add_extension2(con, 0, exten, forstart, forlabel, NULL, app, strdup(margs), FREE, registrar)) 00825 ast_log(LOG_WARNING, "Unable to add step at priority '%d' of %s '%s'\n", forstart, what, name); 00826 fillin_process(con, fillin, filename, lineno, exten, forend, exten, forstart); 00827 fillin_free(fillin); 00828 } else 00829 ast_log(LOG_NOTICE, "Improper for declaration in %s around line %d!\n", filename, lineno); 00830 arg_free(fields); 00831 } else 00832 ast_log(LOG_WARNING, "Syntax error in for declaration in %s around line %d!\n", filename, lineno); 00833 00834 } else if (!strcasecmp(data, "break") || !strcasecmp(data, "continue")) { 00835 struct fillin *fi; 00836 fi = malloc(sizeof(struct fillin)); 00837 if (fi) { 00838 memset(fi, 0, sizeof(struct fillin)); 00839 if (!strcasecmp(data, "break")) 00840 fi->type = FILLIN_BREAK; 00841 else 00842 fi->type = FILLIN_CONTINUE; 00843 ast_copy_string(fi->exten, exten, sizeof(fi->exten)); 00844 fi->priority = (*pos)++; 00845 fi->next = *fillout; 00846 *fillout = fi; 00847 } 00848 } else if (match_assignment(data, &rest)) { 00849 if (aeldebug & DEBUG_TOKENS) 00850 ast_verbose("ASSIGN '%s' = '%s'\n", data, rest); 00851 mlen = strlen(rest) + strlen(data) + 20; 00852 margs = alloca(mlen); 00853 snprintf(margs, mlen, "%s=$[ %s ]", data, rest); 00854 app = "Set"; 00855 if (ast_add_extension2(con, 0, exten, *pos, *label, NULL, app, strdup(margs), FREE, registrar)) 00856 ast_log(LOG_WARNING, "Unable to add assignment at priority '%d' of %s '%s'\n", *pos, what, name); 00857 else { 00858 *label = NULL; 00859 (*pos)++; 00860 } 00861 } else { 00862 app = data; 00863 args = app; 00864 while (*args && (*args > 32) && (*args != '(')) args++; 00865 if (*args != '(') { 00866 while(*args && (*args != '(')) { *args = '\0'; args++; }; 00867 } 00868 if (*args == '(') { 00869 *args = '\0'; 00870 args++; 00871 /* Got arguments, trim trailing ')' */ 00872 c = args + strlen(args) - 1; 00873 while((c >= args) && (*c < 33) && (*c != ')')) { *c = '\0'; c--; }; 00874 if ((c >= args) && (*c == ')')) *c = '\0'; 00875 } else 00876 args = ""; 00877 ast_process_quotes_and_slashes(args, ',', '|'); 00878 if (app[0] == '&') { 00879 app++; 00880 margs = alloca(strlen(args) + strlen(app) + 10); 00881 sprintf(margs, "%s|%s", app, args); 00882 args = margs; 00883 app = "Macro"; 00884 } 00885 if (aeldebug & DEBUG_TOKENS) 00886 ast_verbose("-- APP: '%s', ARGS: '%s'\n", app, args); 00887 if (ast_add_extension2(con, 0, exten, *pos, *label, NULL, app, strdup(args), FREE, registrar)) 00888 ast_log(LOG_WARNING, "Unable to add step at priority '%d' of %s '%s'\n", *pos, what, name); 00889 else { 00890 (*pos)++; 00891 *label = NULL; 00892 } 00893 } 00894 return 0; 00895 }
| static char* __grab_token | ( | char * | src, | |
| const char * | filename, | |||
| int | lineno, | |||
| int | link | |||
| ) | [static] |
Definition at line 78 of file pbx_ael.c.
References ast_log(), ast_verbose(), DEBUG_TOKENS, LOG_WARNING, malloc, and strdup.
Referenced by arg_parse(), and grab_token().
00079 { 00080 char *c; 00081 char *b; 00082 char *a; 00083 int level = 0; 00084 char *ret; 00085 #if 0 00086 if (aeldebug || DEBUG_TOKENS) 00087 ast_verbose("Searching for token in '%s'!\n", src); 00088 #endif 00089 c = src; 00090 while(*c) { 00091 if ((*c == '\\')) { 00092 c++; 00093 if (!*c) 00094 c--; 00095 } else { 00096 if ((*c == '{') || (*c == '(')) { 00097 level++; 00098 } else if ((*c == '}') || (*c == ')')) { 00099 if (level) 00100 level--; 00101 else 00102 ast_log(LOG_WARNING, "Syntax error at line %d of '%s', too many closing braces!\n", lineno, filename); 00103 } else if ((*c == ';') && !level) { 00104 /* Got a token! */ 00105 *c = '\0'; 00106 b = c; 00107 b--; 00108 c++; 00109 while((b > src) && (*b < 33)) { 00110 *b = '\0'; 00111 b--; 00112 } 00113 a = ast_skip_blanks(src); 00114 if (link) { 00115 ret = malloc(strlen(a) + sizeof(struct stringlink) + 1); 00116 if (ret) 00117 strcpy(ret + sizeof(struct stringlink), a); 00118 } else 00119 ret = strdup(a); 00120 /* Save remainder */ 00121 memmove(src, c, strlen(c) + 1); 00122 return ret; 00123 } 00124 } 00125 c++; 00126 } 00127 return NULL; 00128 }
| static int ael_debug_contexts | ( | int | fd, | |
| int | argc, | |||
| char * | argv[] | |||
| ) | [static] |
Definition at line 1247 of file pbx_ael.c.
References DEBUG_CONTEXTS.
01248 { 01249 aeldebug |= DEBUG_CONTEXTS; 01250 return 0; 01251 }
| static int ael_debug_macros | ( | int | fd, | |
| int | argc, | |||
| char * | argv[] | |||
| ) | [static] |
Definition at line 1241 of file pbx_ael.c.
References DEBUG_MACROS.
01242 { 01243 aeldebug |= DEBUG_MACROS; 01244 return 0; 01245 }
| static int ael_debug_read | ( | int | fd, | |
| int | argc, | |||
| char * | argv[] | |||
| ) | [static] |
Definition at line 1229 of file pbx_ael.c.
References DEBUG_READ.
01230 { 01231 aeldebug |= DEBUG_READ; 01232 return 0; 01233 }
| static int ael_debug_tokens | ( | int | fd, | |
| int | argc, | |||
| char * | argv[] | |||
| ) | [static] |
Definition at line 1235 of file pbx_ael.c.
References DEBUG_TOKENS.
01236 { 01237 aeldebug |= DEBUG_TOKENS; 01238 return 0; 01239 }
| static int ael_no_debug | ( | int | fd, | |
| int | argc, | |||
| char * | argv[] | |||
| ) | [static] |
| static int ael_reload | ( | int | fd, | |
| int | argc, | |||
| char * | argv[] | |||
| ) | [static] |
Definition at line 1259 of file pbx_ael.c.
References ast_context_destroy(), and pbx_load_module().
01260 { 01261 ast_context_destroy(NULL, registrar); 01262 return (pbx_load_module()); 01263 }
| static void arg_free | ( | struct stringlink * | cur | ) | [static] |
Definition at line 241 of file pbx_ael.c.
References free, last, and stringlink::next.
Referenced by __build_step(), build_step(), handle_context(), handle_macro(), and handle_root_token().
00242 { 00243 struct stringlink *last; 00244 while(cur) { 00245 last = cur; 00246 cur = cur->next; 00247 free(last); 00248 } 00249 }
| static struct stringlink* arg_parse | ( | char * | args, | |
| const char * | filename, | |||
| int | lineno | |||
| ) | [static] |
Definition at line 135 of file pbx_ael.c.
References __grab_token(), ast_verbose(), DEBUG_TOKENS, malloc, and stringlink::next.
Referenced by __build_step(), build_step(), handle_context(), and split_token().
00136 { 00137 struct stringlink *cur, *prev=NULL, *root=NULL; 00138 if (args) { 00139 if (aeldebug & DEBUG_TOKENS) 00140 ast_verbose("Parsing args '%s'!\n", args); 00141 if (args[0] == '{') { 00142 /* Strip mandatory '}' from end */ 00143 args[strlen(args) - 1] = '\0'; 00144 while ((cur = (struct stringlink *)__grab_token(args + 1, filename, lineno, 1))) { 00145 cur->next = NULL; 00146 if (prev) 00147 prev->next = cur; 00148 else 00149 root = cur; 00150 prev = cur; 00151 } 00152 } else if (*args) { 00153 root = malloc(sizeof(struct stringlink) + strlen(args) + 1); 00154 if (root) { 00155 strcpy(root->data, args); 00156 root->next = NULL; 00157 } 00158 } 00159 } 00160 return root; 00161 }
| static char* argument_end | ( | char * | str | ) | [static] |
Definition at line 456 of file pbx_ael.c.
Referenced by __build_step().
00457 { 00458 int level=0; 00459 while(*++str) { 00460 switch(*str) { 00461 case '(': 00462 level++; 00463 break; 00464 case ')': 00465 if(level) 00466 level--; 00467 else 00468 return str; 00469 break; 00470 default: 00471 break; 00472 } 00473 } 00474 return NULL; 00475 }
| static int ast_ael_compile | ( | struct ast_context ** | local_contexts, | |
| const char * | filename | |||
| ) | [static] |
Definition at line 1153 of file pbx_ael.c.
References ast_config_AST_CONFIG_DIR, ast_log(), ast_verbose(), DEBUG_READ, free, grab_token(), handle_root_token(), local_contexts, LOG_WARNING, malloc, and realloc.
Referenced by pbx_load_module().
01154 { 01155 char *rfilename; 01156 char *buf, *tbuf; 01157 int bufsiz; 01158 FILE *f; 01159 char *c; 01160 char *token; 01161 int lineno=0; 01162 01163 if (filename[0] == '/') 01164 rfilename = (char *)filename; 01165 else { 01166 rfilename = alloca(strlen(filename) + strlen(ast_config_AST_CONFIG_DIR) + 2); 01167 sprintf(rfilename, "%s/%s", ast_config_AST_CONFIG_DIR, filename); 01168 } 01169 01170 f = fopen(rfilename, "r"); 01171 if (!f) { 01172 ast_log(LOG_WARNING, "Unable to open '%s': %s\n", rfilename, strerror(errno)); 01173 return -1; 01174 } 01175 buf = malloc(4096); 01176 if (!buf) { 01177 ast_log(LOG_WARNING, "Out of memory!\n"); 01178 fclose(f); 01179 return -1; 01180 } 01181 buf[0] = 0; 01182 bufsiz = 4096; 01183 while(!feof(f)) { 01184 if (bufsiz - strlen(buf) < 2048) { 01185 bufsiz += 4096; 01186 tbuf = realloc(buf, bufsiz); 01187 if (tbuf) { 01188 buf = tbuf; 01189 } else { 01190 free(buf); 01191 ast_log(LOG_WARNING, "Out of memory!\n"); 01192 fclose(f); 01193 } 01194 } 01195 if (fgets(buf + strlen(buf), bufsiz - strlen(buf), f)) { 01196 lineno++; 01197 while(*buf && buf[strlen(buf) - 1] < 33) 01198 buf[strlen(buf) - 1] = '\0'; 01199 c = strstr(buf, "//"); 01200 if (c) 01201 *c = '\0'; 01202 if (*buf) { 01203 if (aeldebug & DEBUG_READ) 01204 ast_verbose("Newly composed line '%s'\n", buf); 01205 while((token = grab_token(buf, filename, lineno))) { 01206 handle_root_token(local_contexts, token, 0, filename, lineno); 01207 free(token); 01208 } 01209 } 01210 } 01211 }; 01212 free(buf); 01213 fclose(f); 01214 return 0; 01215 }
| static int build_step | ( | const char * | what, | |
| const char * | name, | |||
| const char * | filename, | |||
| int | lineno, | |||
| struct ast_context * | con, | |||
| char * | exten, | |||
| int * | pos, | |||
| char * | data, | |||
| struct fillin ** | fillout, | |||
| char ** | label | |||
| ) | [static] |
Definition at line 897 of file pbx_ael.c.
References __build_step(), arg_free(), arg_parse(), stringlink::data, fillin_free(), fillin_process(), and stringlink::next.
Referenced by __build_step(), handle_context(), and handle_macro().
00898 { 00899 struct stringlink *args, *cur; 00900 int res=0; 00901 struct fillin *fillin=NULL; 00902 int dropfill = 0; 00903 char *labelin = NULL; 00904 if (!fillout) { 00905 fillout = &fillin; 00906 dropfill = 1; 00907 } 00908 if (!label) { 00909 label = &labelin; 00910 }; 00911 args = arg_parse(data, filename, lineno); 00912 cur = args; 00913 while(cur) { 00914 res |= __build_step(what, name, filename, lineno, con, exten, pos, cur->data, fillout, label); 00915 cur = cur->next; 00916 } 00917 arg_free(args); 00918 if (dropfill) { 00919 fillin_process(con, fillin, filename, lineno, NULL, 0, NULL, 0); 00920 fillin_free(fillin); 00921 } 00922 return res; 00923 }
| char* description | ( | void | ) |
| static void fillin_free | ( | stru |