Wed Aug 15 01:25:27 2007

Asterisk developer's documentation


res_agi.c File Reference

AGI - the Asterisk Gateway Interface. More...

#include "asterisk.h"
#include <sys/types.h>
#include <netdb.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <netinet/tcp.h>
#include <arpa/inet.h>
#include <math.h>
#include <stdlib.h>
#include <unistd.h>
#include <string.h>
#include <signal.h>
#include <sys/time.h>
#include <stdio.h>
#include <fcntl.h>
#include <errno.h>
#include <sys/wait.h>
#include "asterisk/file.h"
#include "asterisk/logger.h"
#include "asterisk/channel.h"
#include "asterisk/pbx.h"
#include "asterisk/module.h"
#include "asterisk/astdb.h"
#include "asterisk/callerid.h"
#include "asterisk/cli.h"
#include "asterisk/options.h"
#include "asterisk/image.h"
#include "asterisk/say.h"
#include "asterisk/app.h"
#include "asterisk/dsp.h"
#include "asterisk/musiconhold.h"
#include "asterisk/utils.h"
#include "asterisk/lock.h"
#include "asterisk/strings.h"
#include "asterisk/agi.h"

Include dependency graph for res_agi.c:

Go to the source code of this file.

Defines

#define AGI_PORT   4573
#define fdprintf   agi_debug_cli
#define MAX_AGI_CONNECT   2000
#define MAX_ARGS   128
#define MAX_COMMANDS   128
#define RETRY   3
#define TONE_BLOCK_SIZE   200

Enumerations

enum  agi_result { AGI_RESULT_SUCCESS, AGI_RESULT_FAILURE, AGI_RESULT_HANGUP }

Functions

static int agi_debug_cli (int fd, char *fmt,...)
static int agi_do_debug (int fd, int argc, char *argv[])
static int agi_exec (struct ast_channel *chan, void *data)
static int agi_exec_full (struct ast_channel *chan, void *data, int enhanced, int dead)
static int agi_handle_command (struct ast_channel *chan, AGI *agi, char *buf)
static int agi_no_debug (int fd, int argc, char *argv[])
static int agi_no_debug_deprecated (int fd, int argc, char *argv[])
int ast_agi_register (agi_command *agi)
void ast_agi_unregister (agi_command *agi)
 AST_MODULE_INFO (ASTERISK_GPL_KEY, AST_MODFLAG_GLOBAL_SYMBOLS,"Asterisk Gateway Interface (AGI)",.load=load_module,.unload=unload_module,)
static int deadagi_exec (struct ast_channel *chan, void *data)
static int eagi_exec (struct ast_channel *chan, void *data)
static agi_commandfind_command (char *cmds[], int exact)
static int handle_agidumphtml (int fd, int argc, char *argv[])
static int handle_answer (struct ast_channel *chan, AGI *agi, int argc, char *argv[])
static int handle_autohangup (struct ast_channel *chan, AGI *agi, int argc, char *argv[])
static int handle_channelstatus (struct ast_channel *chan, AGI *agi, int argc, char **argv)
static int handle_controlstreamfile (struct ast_channel *chan, AGI *agi, int argc, char *argv[])
static int handle_dbdel (struct ast_channel *chan, AGI *agi, int argc, char **argv)
static int handle_dbdeltree (struct ast_channel *chan, AGI *agi, int argc, char **argv)
static int handle_dbget (struct ast_channel *chan, AGI *agi, int argc, char **argv)
static int handle_dbput (struct ast_channel *chan, AGI *agi, int argc, char **argv)
static int handle_exec (struct ast_channel *chan, AGI *agi, int argc, char **argv)
static int handle_getdata (struct ast_channel *chan, AGI *agi, int argc, char *argv[])
static int handle_getoption (struct ast_channel *chan, AGI *agi, int argc, char *argv[])
static int handle_getvariable (struct ast_channel *chan, AGI *agi, int argc, char **argv)
static int handle_getvariablefull (struct ast_channel *chan, AGI *agi, int argc, char **argv)
static int handle_hangup (struct ast_channel *chan, AGI *agi, int argc, char **argv)
static int handle_noop (struct ast_channel *chan, AGI *agi, int arg, char *argv[])
static int handle_recordfile (struct ast_channel *chan, AGI *agi, int argc, char *argv[])
static int handle_recvchar (struct ast_channel *chan, AGI *agi, int argc, char *argv[])
static int handle_recvtext (struct ast_channel *chan, AGI *agi, int argc, char *argv[])
static int handle_sayalpha (struct ast_channel *chan, AGI *agi, int argc, char *argv[])
static int handle_saydate (struct ast_channel *chan, AGI *agi, int argc, char *argv[])
static int handle_saydatetime (struct ast_channel *chan, AGI *agi, int argc, char *argv[])
static int handle_saydigits (struct ast_channel *chan, AGI *agi, int argc, char *argv[])
static int handle_saynumber (struct ast_channel *chan, AGI *agi, int argc, char *argv[])
static int handle_sayphonetic (struct ast_channel *chan, AGI *agi, int argc, char *argv[])
static int handle_saytime (struct ast_channel *chan, AGI *agi, int argc, char *argv[])
static int handle_sendimage (struct ast_channel *chan, AGI *agi, int argc, char *argv[])
static int handle_sendtext (struct ast_channel *chan, AGI *agi, int argc, char *argv[])
static int handle_setcallerid (struct ast_channel *chan, AGI *agi, int argc, char **argv)
static int handle_setcontext (struct ast_channel *chan, AGI *agi, int argc, char *argv[])
static int handle_setextension (struct ast_channel *chan, AGI *agi, int argc, char **argv)
static int handle_setmusic (struct ast_channel *chan, AGI *agi, int argc, char *argv[])
static int handle_setpriority (struct ast_channel *chan, AGI *agi, int argc, char **argv)
static int handle_setvariable (struct ast_channel *chan, AGI *agi, int argc, char **argv)
static int handle_showagi (int fd, int argc, char *argv[])
static int handle_streamfile (struct ast_channel *chan, AGI *agi, int argc, char *argv[])
static int handle_tddmode (struct ast_channel *chan, AGI *agi, int argc, char *argv[])
static int handle_verbose (struct ast_channel *chan, AGI *agi, int argc, char **argv)
static int handle_waitfordigit (struct ast_channel *chan, AGI *agi, int argc, char *argv[])
static int help_workhorse (int fd, char *match[])
static enum agi_result launch_netscript (char *agiurl, char *argv[], int *fds, int *efd, int *opid)
static enum agi_result launch_script (char *script, char *argv[], int *fds, int *efd, int *opid)
static int load_module (void)
static int parse_args (char *s, int *max, char *argv[])
static enum agi_result run_agi (struct ast_channel *chan, char *request, AGI *agi, int pid, int *status, int dead)
static void setup_env (struct ast_channel *chan, char *request, int fd, int enhanced)
static int unload_module (void)

Variables

static int agidebug = 0
static char * app = "AGI"
static struct
ast_cli_entry 
cli_agi []
static struct
ast_cli_entry 
cli_agi_no_debug_deprecated
static struct
ast_cli_entry 
cli_dump_agihtml_deprecated
static struct
ast_cli_entry 
cli_show_agi_deprecated
static agi_command commands [MAX_COMMANDS]
static char * deadapp = "DeadAGI"
static char * deadsynopsis = "Executes AGI on a hungup channel"
static char debug_usage []
static char * descrip
static char dumpagihtml_help []
static char * eapp = "EAGI"
static char * esynopsis = "Executes an EAGI compliant application"
static char no_debug_usage []
static char showagi_help []
static char * synopsis = "Executes an AGI compliant application"
static char usage_answer []
static char usage_autohangup []
static char usage_channelstatus []
static char usage_controlstreamfile []
static char usage_dbdel []
static char usage_dbdeltree []
static char usage_dbget []
static char usage_dbput []
static char usage_exec []
static char usage_getdata []
static char usage_getoption []
static char usage_getvariable []
static char usage_getvariablefull []
static char usage_hangup []
static char usage_noop []
static char usage_recordfile []
static char usage_recvchar []
static char usage_recvtext []
static char usage_sayalpha []
static char usage_saydate []
static char usage_saydatetime []
static char usage_saydigits []
static char usage_saynumber []
static char usage_sayphonetic []
static char usage_saytime []
static char usage_sendimage []
static char usage_sendtext []
static char usage_setcallerid []
static char usage_setcontext []
static char usage_setextension []
static char usage_setmusic []
static char usage_setpriority []
static char usage_setvariable []
static char usage_streamfile []
static char usage_tddmode []
static char usage_verbose []
static char usage_waitfordigit []


Detailed Description

AGI - the Asterisk Gateway Interface.

Author:
Mark Spencer <markster@digium.com>

Definition in file res_agi.c.


Define Documentation

#define AGI_PORT   4573

Definition at line 110 of file res_agi.c.

Referenced by launch_netscript().

#define fdprintf   agi_debug_cli

Definition at line 72 of file res_agi.c.

Referenced by agi_handle_command(), handle_answer(), handle_autohangup(), handle_channelstatus(), handle_controlstreamfile(), handle_dbdel(), handle_dbdeltree(), handle_dbget(), handle_dbput(), handle_exec(), handle_getdata(), handle_getoption(), handle_getvariable(), handle_getvariablefull(), handle_hangup(), handle_noop(), handle_recordfile(), handle_recvchar(), handle_recvtext(), handle_sayalpha(), handle_saydate(), handle_saydatetime(), handle_saydigits(), handle_saynumber(), handle_sayphonetic(), handle_saytime(), handle_sendimage(), handle_sendtext(), handle_setcallerid(), handle_setcontext(), handle_setextension(), handle_setmusic(), handle_setpriority(), handle_setvariable(), handle_streamfile(), handle_tddmode(), handle_verbose(), handle_waitfordigit(), launch_netscript(), and setup_env().

#define MAX_AGI_CONNECT   2000

Definition at line 108 of file res_agi.c.

Referenced by launch_netscript().

#define MAX_ARGS   128

Definition at line 68 of file res_agi.c.

#define MAX_COMMANDS   128

Definition at line 69 of file res_agi.c.

Referenced by ast_agi_register(), and ast_agi_unregister().

#define RETRY   3

Definition at line 1826 of file res_agi.c.

Referenced by run_agi().

#define TONE_BLOCK_SIZE   200

Definition at line 105 of file res_agi.c.


Enumeration Type Documentation

enum agi_result

Enumerator:
AGI_RESULT_SUCCESS 
AGI_RESULT_FAILURE 
AGI_RESULT_HANGUP 

Definition at line 112 of file res_agi.c.

00112                 {
00113    AGI_RESULT_SUCCESS,
00114    AGI_RESULT_FAILURE,
00115    AGI_RESULT_HANGUP
00116 };


Function Documentation

static int agi_debug_cli ( int  fd,
char *  fmt,
  ... 
) [static]

Definition at line 118 of file res_agi.c.

References ast_carefulwrite(), ast_log(), ast_verbose(), free, LOG_ERROR, ast_variable::stuff, and vasprintf.

00119 {
00120    char *stuff;
00121    int res = 0;
00122 
00123    va_list ap;
00124    va_start(ap, fmt);
00125    res = vasprintf(&stuff, fmt, ap);
00126    va_end(ap);
00127    if (res == -1) {
00128       ast_log(LOG_ERROR, "Out of memory\n");
00129    } else {
00130       if (agidebug)
00131          ast_verbose("AGI Tx >> %s", stuff); /* \n provided by caller */
00132       res = ast_carefulwrite(fd, stuff, strlen(stuff), 100);
00133       free(stuff);
00134    }
00135 
00136    return res;
00137 }

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

Definition at line 1313 of file res_agi.c.

References ast_cli(), RESULT_SHOWUSAGE, and RESULT_SUCCESS.

01314 {
01315    if (argc != 2)
01316       return RESULT_SHOWUSAGE;
01317    agidebug = 1;
01318    ast_cli(fd, "AGI Debugging Enabled\n");
01319    return RESULT_SUCCESS;
01320 }

static int agi_exec ( struct ast_channel chan,
void *  data 
) [static]

Definition at line 2058 of file res_agi.c.

References ast_channel::_softhangup, agi_exec_full(), ast_log(), and LOG_WARNING.

Referenced by load_module().

02059 {
02060    if (chan->_softhangup)
02061       ast_log(LOG_WARNING, "If you want to run AGI on hungup channels you should use DeadAGI!\n");
02062    return agi_exec_full(chan, data, 0, 0);
02063 }

static int agi_exec_full ( struct ast_channel chan,
void *  data,
int  enhanced,
int  dead 
) [static]

Definition at line 1990 of file res_agi.c.

References ast_channel::_state, AGI_RESULT_FAILURE, AGI_RESULT_HANGUP, AGI_RESULT_SUCCESS, ast_answer(), ast_log(), ast_module_user_add, ast_module_user_remove, AST_STATE_UP, ast_strlen_zero(), ast_unreplace_sigchld(), AGI::audio, AGI::ctrl, AGI::fd, launch_script(), LOG_WARNING, MAX_ARGS, pbx_builtin_setvar_helper(), run_agi(), and strsep().

Referenced by agi_exec(), deadagi_exec(), and eagi_exec().

01991 {
01992    enum agi_result res;
01993    struct ast_module_user *u;
01994    char *argv[MAX_ARGS];
01995    char buf[2048]="";
01996    char *tmp = (char *)buf;
01997    int argc = 0;
01998    int fds[2];
01999    int efd = -1;
02000    int pid;
02001         char *stringp;
02002    AGI agi;
02003 
02004    if (ast_strlen_zero(data)) {
02005       ast_log(LOG_WARNING, "AGI requires an argument (script)\n");
02006       return -1;
02007    }
02008    ast_copy_string(buf, data, sizeof(buf));
02009 
02010    memset(&agi, 0, sizeof(agi));
02011         while ((stringp = strsep(&tmp, "|")) && argc < MAX_ARGS-1)
02012       argv[argc++] = stringp;
02013    argv[argc] = NULL;
02014 
02015    u = ast_module_user_add(chan);
02016 #if 0
02017     /* Answer if need be */
02018         if (chan->_state != AST_STATE_UP) {
02019       if (ast_answer(chan)) {
02020          LOCAL_USER_REMOVE(u);
02021          return -1;
02022       }
02023    }
02024 #endif
02025    res = launch_script(argv[0], argv, fds, enhanced ? &efd : NULL, &pid);
02026    if (res == AGI_RESULT_SUCCESS) {
02027       int status = 0;
02028       agi.fd = fds[1];
02029       agi.ctrl = fds[0];
02030       agi.audio = efd;
02031       res = run_agi(chan, argv[0], &agi, pid, &status, dead);
02032       /* If the fork'd process returns non-zero, set AGISTATUS to FAILURE */
02033       if (res == AGI_RESULT_SUCCESS && status)
02034          res = AGI_RESULT_FAILURE;
02035       if (fds[1] != fds[0])
02036          close(fds[1]);
02037       if (efd > -1)
02038          close(efd);
02039       ast_unreplace_sigchld();
02040    }
02041    ast_module_user_remove(u);
02042 
02043    switch (res) {
02044    case AGI_RESULT_SUCCESS:
02045       pbx_builtin_setvar_helper(chan, "AGISTATUS", "SUCCESS");
02046       break;
02047    case AGI_RESULT_FAILURE:
02048       pbx_builtin_setvar_helper(chan, "AGISTATUS", "FAILURE");
02049       break;
02050    case AGI_RESULT_HANGUP:
02051       pbx_builtin_setvar_helper(chan, "AGISTATUS", "HANGUP");
02052       return -1;
02053    }
02054 
02055    return 0;
02056 }

static int agi_handle_command ( struct ast_channel chan,
AGI agi,
char *  buf 
) [static]

Definition at line 1795 of file res_agi.c.

References AST_PBX_KEEPALIVE, AGI::fd, fdprintf, find_command(), agi_command::handler, MAX_ARGS, parse_args(), RESULT_FAILURE, RESULT_SHOWUSAGE, and agi_command::usage.

Referenced by run_agi().

01796 {
01797    char *argv[MAX_ARGS];
01798    int argc = MAX_ARGS;
01799    int res;
01800    agi_command *c;
01801 
01802    parse_args(buf, &argc, argv);
01803    c = find_command(argv, 0);
01804    if (c) {
01805       res = c->handler(chan, agi, argc, argv);
01806       switch(res) {
01807       case RESULT_SHOWUSAGE:
01808          fdprintf(agi->fd, "520-Invalid command syntax.  Proper usage follows:\n");
01809          fdprintf(agi->fd, c->usage);
01810          fdprintf(agi->fd, "520 End of proper usage.\n");
01811          break;
01812       case AST_PBX_KEEPALIVE:
01813          /* We've been asked to keep alive, so do so */
01814          return AST_PBX_KEEPALIVE;
01815          break;
01816       case RESULT_FAILURE:
01817          /* They've already given the failure.  We've been hung up on so handle this
01818             appropriately */
01819          return -1;
01820       }
01821    } else {
01822       fdprintf(agi->fd, "510 Invalid or unknown command\n");
01823    }
01824    return 0;
01825 }

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

Definition at line 1331 of file res_agi.c.

References ast_cli(), RESULT_SHOWUSAGE, and RESULT_SUCCESS.

01332 {
01333    if (argc != 3)
01334       return RESULT_SHOWUSAGE;
01335    agidebug = 0;
01336    ast_cli(fd, "AGI Debugging Disabled\n");
01337    return RESULT_SUCCESS;
01338 }

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

Definition at line 1322 of file res_agi.c.

References ast_cli(), RESULT_SHOWUSAGE, and RESULT_SUCCESS.

01323 {
01324    if (argc != 3)
01325       return RESULT_SHOWUSAGE;
01326    agidebug = 0;
01327    ast_cli(fd, "AGI Debugging Disabled\n");
01328    return RESULT_SUCCESS;
01329 }

int ast_agi_register ( agi_command agi  ) 

Definition at line 1666 of file res_agi.c.

References ast_log(), agi_command::cmda, LOG_WARNING, and MAX_COMMANDS.

01667 {
01668    int x;
01669    for (x=0; x<MAX_COMMANDS - 1; x++) {
01670       if (commands[x].cmda[0] == agi->cmda[0]) {
01671          ast_log(LOG_WARNING, "Command already registered!\n");
01672          return -1;
01673       }
01674    }
01675    for (x=0; x<MAX_COMMANDS - 1; x++) {
01676       if (!commands[x].cmda[0]) {
01677          commands[x] = *agi;
01678          return 0;
01679       }
01680    }
01681    ast_log(LOG_WARNING, "No more room for new commands!\n");
01682    return -1;
01683 }

void ast_agi_unregister ( agi_command agi  ) 

Definition at line 1685 of file res_agi.c.

References agi_command::cmda, and MAX_COMMANDS.

01686 {
01687    int x;
01688    for (x=0; x<MAX_COMMANDS - 1; x++) {
01689       if (commands[x].cmda[0] == agi->cmda[0]) {
01690          memset(&commands[x], 0, sizeof(agi_command));
01691       }
01692    }
01693 }

AST_MODULE_INFO ( ASTERISK_GPL_KEY  ,
AST_MODFLAG_GLOBAL_SYMBOLS  ,
"Asterisk Gateway Interface (AGI)"  ,
load = load_module,
unload = unload_module 
)

static int deadagi_exec ( struct ast_channel chan,
void *  data 
) [static]

Definition at line 2086 of file res_agi.c.

References agi_exec_full(), ast_check_hangup(), ast_log(), and LOG_WARNING.

Referenced by load_module().

02087 {
02088    if (!ast_check_hangup(chan))
02089       ast_log(LOG_WARNING,"Running DeadAGI on a live channel will cause problems, please use AGI\n");
02090    return agi_exec_full(chan, data, 0, 1);
02091 }

static int eagi_exec ( struct ast_channel chan,
void *  data 
) [static]

Definition at line 2065 of file res_agi.c.

References ast_channel::_softhangup, agi_exec_full(), AST_FORMAT_SLINEAR, ast_getformatname(), ast_log(), ast_set_read_format(), LOG_WARNING, and ast_channel::readformat.

Referenced by load_module().

02066 {
02067    int readformat;
02068    int res;
02069 
02070    if (chan->_softhangup)
02071       ast_log(LOG_WARNING, "If you want to run AGI on hungup channels you should use DeadAGI!\n");
02072    readformat = chan->readformat;
02073    if (ast_set_read_format(chan, AST_FORMAT_SLINEAR)) {
02074       ast_log(LOG_WARNING, "Unable to set channel '%s' to linear mode\n", chan->name);
02075       return -1;
02076    }
02077    res = agi_exec_full(chan, data, 1, 0);
02078    if (!res) {
02079       if (ast_set_read_format(chan, readformat)) {
02080          ast_log(LOG_WARNING, "Unable to restore channel '%s' to format %s\n", chan->name, ast_getformatname(readformat));
02081       }
02082    }
02083    return res;
02084 }

static agi_command* find_command ( char *  cmds[],
int  exact 
) [static]

Definition at line 1695 of file res_agi.c.

References agi_command::cmda, and match().

01696 {
01697    int x;
01698    int y;
01699    int match;
01700 
01701    for (x=0; x < sizeof(commands) / sizeof(commands[0]); x++) {
01702       if (!commands[x].cmda[0])
01703          break;
01704       /* start optimistic */
01705       match = 1;
01706       for (y=0; match && cmds[y]; y++) {
01707          /* If there are no more words in the command (and we're looking for
01708             an exact match) or there is a difference between the two words,
01709             then this is not a match */
01710          if (!commands[x].cmda[y] && !exact)
01711             break;
01712          /* don't segfault if the next part of a command doesn't exist */
01713          if (!commands[x].cmda[y])
01714             return NULL;
01715          if (strcasecmp(commands[x].cmda[y], cmds[y]))
01716             match = 0;
01717       }
01718       /* If more words are needed to complete the command then this is not
01719          a candidate (unless we're looking for a really inexact answer  */
01720       if ((exact > -1) && commands[x].cmda[y])
01721          match = 0;
01722       if (match)
01723          return &commands[x];
01724    }
01725    return NULL;
01726 }

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

Definition at line 1936 of file res_agi.c.

References ast_cli(), ast_join(), agi_command::cmda, RESULT_SHOWUSAGE, RESULT_SUCCESS, strsep(), agi_command::summary, and agi_command::usage.

01937 {
01938    struct agi_command *e;
01939    char fullcmd[80];
01940    int x;
01941    FILE *htmlfile;
01942 
01943    if ((argc < 3))
01944       return RESULT_SHOWUSAGE;
01945 
01946    if (!(htmlfile = fopen(argv[2], "wt"))) {
01947       ast_cli(fd, "Could not create file '%s'\n", argv[2]);
01948       return RESULT_SHOWUSAGE;
01949    }
01950 
01951    fprintf(htmlfile, "<HTML>\n<HEAD>\n<TITLE>AGI Commands</TITLE>\n</HEAD>\n");
01952    fprintf(htmlfile, "<BODY>\n<CENTER><B><H1>AGI Commands</H1></B></CENTER>\n\n");
01953 
01954 
01955    fprintf(htmlfile, "<TABLE BORDER=\"0\" CELLSPACING=\"10\">\n");
01956 
01957    for (x=0;x<sizeof(commands)/sizeof(commands[0]);x++) {
01958       char *stringp, *tempstr;
01959 
01960       e = &commands[x]; 
01961       if (!e->cmda[0])  /* end ? */
01962          break;
01963       /* Hide commands that start with '_' */
01964       if ((e->cmda[0])[0] == '_')
01965          continue;
01966       ast_join(fullcmd, sizeof(fullcmd), e->cmda);
01967 
01968       fprintf(htmlfile, "<TR><TD><TABLE BORDER=\"1\" CELLPADDING=\"5\" WIDTH=\"100%%\">\n");
01969       fprintf(htmlfile, "<TR><TH ALIGN=\"CENTER\"><B>%s - %s</B></TH></TR>\n", fullcmd,e->summary);
01970 
01971       stringp=e->usage;
01972       tempstr = strsep(&stringp, "\n");
01973 
01974       fprintf(htmlfile, "<TR><TD ALIGN=\"CENTER\">%s</TD></TR>\n", tempstr);
01975       
01976       fprintf(htmlfile, "<TR><TD ALIGN=\"CENTER\">\n");
01977       while ((tempstr = strsep(&stringp, "\n")) != NULL)
01978          fprintf(htmlfile, "%s<BR>\n",tempstr);
01979       fprintf(htmlfile, "</TD></TR>\n");
01980       fprintf(htmlfile, "</TABLE></TD></TR>\n\n");
01981 
01982    }
01983 
01984    fprintf(htmlfile, "</TABLE>\n</BODY>\n</HTML>\n");
01985    fclose(htmlfile);
01986    ast_cli(fd, "AGI HTML Commands Dumped to: %s\n", argv[2]);
01987    return RESULT_SUCCESS;
01988 }

static int handle_answer ( struct ast_channel chan,
AGI agi,
int  argc,
char *  argv[] 
) [static]

Definition at line 401 of file res_agi.c.

References ast_channel::_state, ast_answer(), AST_STATE_UP, AGI::fd, fdprintf, RESULT_FAILURE, and RESULT_SUCCESS.

00402 {
00403    int res;
00404    res = 0;
00405    if (chan->_state != AST_STATE_UP) {
00406       /* Answer the chan */
00407       res = ast_answer(chan);
00408    }
00409    fdprintf(agi->fd, "200 result=%d\n", res);
00410    return (res >= 0) ? RESULT_SUCCESS : RESULT_FAILURE;
00411 }

static int handle_autohangup ( struct ast_channel chan,
AGI agi,
int  argc,
char *  argv[] 
) [static]

Definition at line 1050 of file res_agi.c.

References AGI::fd, fdprintf, RESULT_SHOWUSAGE, RESULT_SUCCESS, and ast_channel::whentohangup.

01051 {
01052    int timeout;
01053 
01054    if (argc != 3)
01055       return RESULT_SHOWUSAGE;
01056    if (sscanf(argv[2], "%d", &timeout) != 1)
01057       return RESULT_SHOWUSAGE;
01058    if (timeout < 0)
01059       timeout = 0;
01060    if (timeout)
01061       chan->whentohangup = time(NULL) + timeout;
01062    else
01063       chan->whentohangup = 0;
01064    fdprintf(agi->fd, "200 result=0\n");
01065    return RESULT_SUCCESS;
01066 }

static int handle_channelstatus ( struct ast_channel chan,
AGI agi,
int  argc,
char **  argv 
) [static]

Definition at line 1140 of file res_agi.c.

References ast_channel::_state, ast_channel_unlock, ast_get_channel_by_name_locked(), AGI::fd, fdprintf, RESULT_SHOWUSAGE, and RESULT_SUCCESS.

01141 {
01142    struct ast_channel *c;
01143    if (argc == 2) {
01144       /* no argument: supply info on the current channel */
01145       fdprintf(agi->fd, "200 result=%d\n", chan->_state);
01146       return RESULT_SUCCESS;
01147    } else if (argc == 3) {
01148       /* one argument: look for info on the specified channel */
01149       c = ast_get_channel_by_name_locked(argv[2]);
01150       if (c) {
01151          fdprintf(agi->fd, "200 result=%d\n", c->_state);
01152          ast_channel_unlock(c);
01153          return RESULT_SUCCESS;
01154       }
01155       /* if we get this far no channel name matched the argument given */
01156       fdprintf(agi->fd, "200 result=-1\n");
01157       return RESULT_SUCCESS;
01158    } else {
01159       return RESULT_SHOWUSAGE;
01160    }
01161 }

static int handle_controlstreamfile ( struct ast_channel chan,
AGI agi,
int  argc,
char *  argv[] 
) [static]

Definition at line 512 of file res_agi.c.

References ast_control_streamfile(), ast_strlen_zero(), AGI::fd, fdprintf, RESULT_FAILURE, RESULT_SHOWUSAGE, RESULT_SUCCESS, and skipms.

00513 {
00514    int res = 0;
00515    int skipms = 3000;
00516    char *fwd = NULL;
00517    char *rev = NULL;
00518    char *pause = NULL;
00519    char *stop = NULL;
00520 
00521    if (argc < 5 || argc > 9)
00522       return RESULT_SHOWUSAGE;
00523 
00524    if (!ast_strlen_zero(argv[4]))
00525       stop = argv[4];
00526    else
00527       stop = NULL;
00528    
00529    if ((argc > 5) && (sscanf(argv[5], "%d", &skipms) != 1))
00530       return RESULT_SHOWUSAGE;
00531 
00532    if (argc > 6 && !ast_strlen_zero(argv[6]))
00533       fwd = argv[6];
00534    else
00535       fwd = "#";
00536 
00537    if (argc > 7 && !ast_strlen_zero(argv[7]))
00538       rev = argv[7];
00539    else
00540       rev = "*";
00541    
00542    if (argc > 8 && !ast_strlen_zero(argv[8]))
00543       pause = argv[8];
00544    else
00545       pause = NULL;
00546    
00547    res = ast_control_streamfile(chan, argv[3], fwd, rev, stop, pause, NULL, skipms);
00548    
00549    fdprintf(agi->fd, "200 result=%d\n", res);
00550 
00551    return (res >= 0) ? RESULT_SUCCESS : RESULT_FAILURE;
00552 }

static int handle_dbdel ( struct ast_channel chan,
AGI agi,
int  argc,
char **  argv 
) [static]

Definition at line 1280 of file res_agi.c.

References ast_db_del(), AGI::fd, fdprintf, RESULT_SHOWUSAGE, and RESULT_SUCCESS.

01281 {
01282    int res;
01283 
01284    if (argc != 4)
01285       return RESULT_SHOWUSAGE;
01286    res = ast_db_del(argv[2], argv[3]);
01287    fdprintf(agi->fd, "200 result=%c\n", res ? '0' : '1');
01288    return RESULT_SUCCESS;
01289 }

static int handle_dbdeltree ( struct ast_channel chan,
AGI agi,
int  argc,
char **  argv 
) [static]

Definition at line 1291 of file res_agi.c.

References ast_db_deltree(), AGI::fd, fdprintf, RESULT_SHOWUSAGE, and RESULT_SUCCESS.

01292 {
01293    int res;
01294    if ((argc < 3) || (argc > 4))
01295       return RESULT_SHOWUSAGE;
01296    if (argc == 4)
01297       res = ast_db_deltree(argv[2], argv[3]);
01298    else
01299       res = ast_db_deltree(argv[2], NULL);
01300 
01301    fdprintf(agi->fd, "200 result=%c\n", res ? '0' : '1');
01302    return RESULT_SUCCESS;
01303 }

static int handle_dbget ( struct ast_channel chan,
AGI agi,
int  argc,
char **  argv 
) [static]

Definition at line 1253 of file res_agi.c.

References ast_db_get(), AGI::fd, fdprintf, RESULT_SHOWUSAGE, and RESULT_SUCCESS.

01254 {
01255    int res;
01256    char tmp[256];
01257 
01258    if (argc != 4)
01259       return RESULT_SHOWUSAGE;
01260    res = ast_db_get(argv[2], argv[3], tmp, sizeof(tmp));
01261    if (res) 
01262       fdprintf(agi->fd, "200 result=0\n");
01263    else
01264       fdprintf(agi->fd, "200 result=1 (%s)\n", tmp);
01265 
01266    return RESULT_SUCCESS;
01267 }

static int handle_dbput ( struct ast_channel chan,
AGI agi,
int  argc,
char **  argv 
) [static]

Definition at line 1269 of file res_agi.c.

References ast_db_put(), AGI::fd, fdprintf, RESULT_SHOWUSAGE, and RESULT_SUCCESS.

01270 {
01271    int res;
01272 
01273    if (argc != 5)
01274       return RESULT_SHOWUSAGE;
01275    res = ast_db_put(argv[2], argv[3], argv[4]);
01276    fdprintf(agi->fd, "200 result=%c\n", res ? '0' : '1');
01277    return RESULT_SUCCESS;
01278 }

static int handle_exec ( struct ast_channel chan,
AGI agi,
int  argc,
char **  argv 
) [static]

Definition at line 1094 of file res_agi.c.

References ast_log(), ast_verbose(), AGI::fd, fdprintf, LOG_WARNING, option_verbose, pbx_exec(), pbx_findapp(), RESULT_SHOWUSAGE, and VERBOSE_PREFIX_3.

01095 {
01096    int res;
01097    struct ast_app *app;
01098 
01099    if (argc < 2)
01100       return RESULT_SHOWUSAGE;
01101 
01102    if (option_verbose > 2)
01103       ast_verbose(VERBOSE_PREFIX_3 "AGI Script Executing Application: (%s) Options: (%s)\n", argv[1], argv[2]);
01104 
01105    app = pbx_findapp(argv[1]);
01106 
01107    if (app) {
01108       res = pbx_exec(chan, app, argv[2]);
01109    } else {
01110       ast_log(LOG_WARNING, "Could not find application (%s)\n", argv[1]);
01111       res = -2;
01112    }
01113    fdprintf(agi->fd, "200 result=%d\n", res);
01114 
01115    /* Even though this is wrong, users are depending upon this result. */
01116    return res;
01117 }

static int handle_getdata ( struct ast_channel chan,
AGI agi,
int  argc,
char *  argv[] 
) [static]

Definition at line 809 of file res_agi.c.

References ast_app_getdata_full(), AGI::audio, AGI::ctrl, AGI::fd, fdprintf, RESULT_SHOWUSAGE, and RESULT_SUCCESS.

00810 {
00811    int res;
00812    char data[1024];
00813    int max;
00814    int timeout;
00815 
00816    if (argc < 3)
00817       return RESULT_SHOWUSAGE;
00818    if (argc >= 4)
00819       timeout = atoi(argv[3]); 
00820    else
00821       timeout = 0;
00822    if (argc >= 5) 
00823       max = atoi(argv[4]); 
00824    else
00825       max = 1024;
00826    res = ast_app_getdata_full(chan, argv[2], data, max, timeout, agi->audio, agi->ctrl);
00827    if (res == 2)        /* New command */
00828       return RESULT_SUCCESS;
00829    else if (res == 1)
00830       fdprintf(agi->fd, "200 result=%s (timeout)\n", data);
00831    else if (res < 0 )
00832       fdprintf(agi->fd, "200 result=-1\n");
00833    else
00834       fdprintf(agi->fd, "200 result=%s\n", data);
00835    return RESULT_SUCCESS;
00836 }

static int handle_getoption ( struct ast_channel chan,
AGI agi,
int  argc,
char *  argv[] 
) [static]

Definition at line 610 of file res_agi.c.

References ast_applystream(), ast_log(), ast_openstream(), ast_openvstream(), ast_playstream(), ast_seekstream(), ast_stopstream(), ast_tellstream(), ast_verbose(), ast_waitfordigit_full(), ast_waitstream_full(), AGI::audio, AGI::ctrl, ast_pbx::dtimeout, AGI::fd, fdprintf, LOG_DEBUG, LOG_WARNING, option_verbose, ast_channel::pbx, RESULT_FAILURE, RESULT_SHOWUSAGE, RESULT_SUCCESS, ast_channel::stream, VERBOSE_PREFIX_3, and ast_filestream::vfs.

00611 {
00612    int res;
00613    int vres;   
00614    struct ast_filestream *fs;
00615    struct ast_filestream *vfs;
00616    long sample_offset = 0;
00617    long max_length;
00618    int timeout = 0;
00619    char *edigits = "";
00620 
00621    if ( argc < 4 || argc > 5 )
00622       return RESULT_SHOWUSAGE;
00623 
00624    if ( argv[3] ) 
00625       edigits = argv[3];
00626 
00627    if ( argc == 5 )
00628       timeout = atoi(argv[4]);
00629    else if (chan->pbx->dtimeout) {
00630       /* by default dtimeout is set to 5sec */
00631       timeout = chan->pbx->dtimeout * 1000; /* in msec */
00632    }
00633 
00634    fs = ast_openstream(chan, argv[2], chan->language);
00635    if (!fs) {
00636       fdprintf(agi->fd, "200 result=%d endpos=%ld\n", 0, sample_offset);
00637       ast_log(LOG_WARNING, "Unable to open %s\n", argv[2]);
00638       return RESULT_SUCCESS;
00639    }
00640    vfs = ast_openvstream(chan, argv[2], chan->language);
00641    if (vfs)
00642       ast_log(LOG_DEBUG, "Ooh, found a video stream, too\n");
00643    
00644    if (option_verbose > 2)
00645       ast_verbose(VERBOSE_PREFIX_3 "Playing '%s' (escape_digits=%s) (timeout %d)\n", argv[2], edigits, timeout);
00646 
00647    ast_seekstream(fs, 0, SEEK_END);
00648    max_length = ast_tellstream(fs);
00649    ast_seekstream(fs, sample_offset, SEEK_SET);
00650    res = ast_applystream(chan, fs);
00651    if (vfs)
00652       vres = ast_applystream(chan, vfs);
00653    ast_playstream(fs);
00654    if (vfs)
00655       ast_playstream(vfs);
00656 
00657    res = ast_waitstream_full(chan, argv[3], agi->audio, agi->ctrl);
00658    /* this is to check for if ast_waitstream closed the stream, we probably are at
00659     * the end of the stream, return that amount, else check for the amount */
00660    sample_offset = (chan->stream)?ast_tellstream(fs):max_length;
00661    ast_stopstream(chan);
00662    if (res == 1) {
00663       /* Stop this command, don't print a result line, as there is a new command */
00664       return RESULT_SUCCESS;
00665    }
00666 
00667    /* If the user didnt press a key, wait for digitTimeout*/
00668    if (res == 0 ) {
00669       res = ast_waitfordigit_full(chan, timeout, agi->audio, agi->ctrl);
00670       /* Make sure the new result is in the escape digits of the GET OPTION */
00671       if ( !strchr(edigits,res) )
00672          res=0;
00673    }
00674 
00675         fdprintf(agi->fd, "200 result=%d endpos=%ld\n", res, sample_offset);
00676    return (res >= 0) ? RESULT_SUCCESS : RESULT_FAILURE;
00677 }

static int handle_getvariable ( struct ast_channel chan,
AGI agi,
int  argc,
char **  argv 
) [static]

Definition at line 1172 of file res_agi.c.

References ast_func_read(), ast_strlen_zero(), AGI::fd, fdprintf, pbx_retrieve_variable(), RESULT_SHOWUSAGE, and RESULT_SUCCESS.

01173 {
01174    char *ret;
01175    char tempstr[1024];
01176 
01177    if (argc != 3)
01178       return RESULT_SHOWUSAGE;
01179 
01180    /* check if we want to execute an ast_custom_function */
01181    if (!ast_strlen_zero(argv[2]) && (argv[2][strlen(argv[2]) - 1] == ')')) {
01182       ret = ast_func_read(chan, argv[2], tempstr, sizeof(tempstr)) ? NULL : tempstr;
01183    } else {
01184       pbx_retrieve_variable(chan, argv[2], &ret, tempstr, sizeof(tempstr), NULL);
01185    }
01186 
01187    if (ret)
01188       fdprintf(agi->fd, "200 result=1 (%s)\n", ret);
01189    else
01190       fdprintf(agi->fd, "200 result=0\n");
01191 
01192    return RESULT_SUCCESS;
01193 }

static int handle_getvariablefull ( struct ast_channel chan,
AGI agi,
int  argc,
char **  argv 
) [static]

Definition at line 1195 of file res_agi.c.

References ast_channel_unlock, ast_get_channel_by_name_locked(), AGI::fd, fdprintf, pbx_substitute_variables_helper(), RESULT_SHOWUSAGE, and RESULT_SUCCESS.

01196 {
01197    char tmp[4096] = "";
01198    struct ast_channel *chan2=NULL;
01199 
01200    if ((argc != 4) && (argc != 5))
01201       return RESULT_SHOWUSAGE;
01202    if (argc == 5) {
01203       chan2 = ast_get_channel_by_name_locked(argv[4]);
01204    } else {
01205       chan2 = chan;
01206    }
01207    if (chan) { /* XXX isn't this chan2 ? */
01208       pbx_substitute_variables_helper(chan2, argv[3], tmp, sizeof(tmp) - 1);
01209       fdprintf(agi->fd, "200 result=1 (%s)\n", tmp);
01210    } else {
01211       fdprintf(agi->fd, "200 result=0\n");
01212    }
01213    if (chan2 && (chan2 != chan))
01214       ast_channel_unlock(chan2);
01215    return RESULT_SUCCESS;
01216 }

static int handle_hangup ( struct ast_channel chan,
AGI agi,
int  argc,
char **  argv 
) [static]

Definition at line 1068 of file res_agi.c.

References ast_channel_unlock, ast_get_channel_by_name_locked(), ast_softhangup(), AST_SOFTHANGUP_EXPLICIT, AGI::fd, fdprintf, RESULT_SHOWUSAGE, and RESULT_SUCCESS.

01069 {
01070    struct ast_channel *c;
01071    if (argc == 1) {
01072       /* no argument: hangup the current channel */
01073       ast_softhangup(chan,AST_SOFTHANGUP_EXPLICIT);
01074       fdprintf(agi->fd, "200 result=1\n");
01075       return RESULT_SUCCESS;
01076    } else if (argc == 2) {
01077       /* one argument: look for info on the specified channel */
01078       c = ast_get_channel_by_name_locked(argv[1]);
01079       if (c) {
01080          /* we have a matching channel */
01081          ast_softhangup(c,AST_SOFTHANGUP_EXPLICIT);
01082          fdprintf(agi->fd, "200 result=1\n");
01083          ast_channel_unlock(c);
01084          return RESULT_SUCCESS;
01085       }
01086       /* if we get this far no channel name matched the argument given */
01087       fdprintf(agi->fd, "200 result=-1\n");
01088       return RESULT_SUCCESS;
01089    } else {
01090       return RESULT_SHOWUSAGE;
01091    }
01092 }

static int handle_noop ( struct ast_channel chan,
AGI agi,
int  arg,
char *  argv[] 
) [static]

Definition at line 1340 of file res_agi.c.

References AGI::fd, fdprintf, and RESULT_SUCCESS.

01341 {
01342    fdprintf(agi->fd, "200 result=0\n");
01343    return RESULT_SUCCESS;
01344 }

static int handle_recordfile ( struct ast_channel chan,
AGI agi,
int  argc,
char *  argv[] 
) [static]

Definition at line 873 of file res_agi.c.

References ast_applystream(), ast_closestream(), AST_CONTROL_VIDUPDATE, ast_dsp_free(), ast_dsp_new(), ast_dsp_set_threshold(), ast_dsp_silence(), AST_FORMAT_SLINEAR, AST_FRAME_DTMF, AST_FRAME_VIDEO, AST_FRAME_VOICE, ast_frfree(), ast_indicate(), ast_log(), ast_read(), ast_seekstream(), ast_set_read_format(), ast_stream_rewind(), ast_streamfile(), ast_tellstream(), ast_truncstream(), ast_waitfor(), ast_waitstream(), ast_writefile(), ast_writestream(), f, AGI::fd, fdprintf, ast_frame::frametype, LOG_WARNING, ast_channel::readformat, RESULT_FAILURE, RESULT_SHOWUSAGE, RESULT_SUCCESS, silence, ast_channel::stream, ast_frame::subclass, and ast_dsp::totalsilence.

00874 {
00875    struct ast_filestream *fs;
00876    struct ast_frame *f;
00877    struct timeval start;
00878    long sample_offset = 0;
00879    int res = 0;
00880    int ms;
00881 
00882         struct ast_dsp *sildet=NULL;         /* silence detector dsp */
00883         int totalsilence = 0;
00884         int dspsilence = 0;
00885         int silence = 0;                /* amount of silence to allow */
00886         int gotsilence = 0;             /* did we timeout for silence? */
00887         char *silencestr=NULL;
00888         int rfmt=0;
00889 
00890 
00891    /* XXX EAGI FIXME XXX */
00892 
00893    if (argc < 6)
00894       return RESULT_SHOWUSAGE;
00895    if (sscanf(argv[5], "%d", &ms) != 1)
00896       return RESULT_SHOWUSAGE;
00897 
00898    if (argc > 6)
00899       silencestr = strchr(argv[6],'s');
00900    if ((argc > 7) && (!silencestr))
00901       silencestr = strchr(argv[7],'s');
00902    if ((argc > 8) && (!silencestr))
00903       silencestr = strchr(argv[8],'s');
00904 
00905    if (silencestr) {
00906       if (strlen(silencestr) > 2) {
00907          if ((silencestr[0] == 's') && (silencestr[1] == '=')) {
00908             silencestr++;
00909             silencestr++;
00910             if (silencestr)
00911                         silence = atoi(silencestr);
00912                if (silence > 0)
00913                         silence *= 1000;
00914             }
00915       }
00916    }
00917 
00918         if (silence > 0) {
00919          rfmt = chan->readformat;
00920                 res = ast_set_read_format(chan, AST_FORMAT_SLINEAR);
00921                 if (res < 0) {
00922                   ast_log(LOG_WARNING, "Unable to set to linear mode, giving up\n");
00923                         return -1;
00924                 }
00925                   sildet = ast_dsp_new();
00926                 if (!sildet) {
00927                   ast_log(LOG_WARNING, "Unable to create silence detector :(\n");
00928                         return -1;
00929                 }
00930                   ast_dsp_set_threshold(sildet, 256);
00931          }
00932 
00933    /* backward compatibility, if no offset given, arg[6] would have been
00934     * caught below and taken to be a beep, else if it is a digit then it is a
00935     * offset */
00936    if ((argc >6) && (sscanf(argv[6], "%ld", &sample_offset) != 1) && (!strchr(argv[6], '=')))
00937       res = ast_streamfile(chan, "beep", chan->language);
00938 
00939    if ((argc > 7) && (!strchr(argv[7], '=')))
00940       res = ast_streamfile(chan, "beep", chan->language);
00941 
00942    if (!res)
00943       res = ast_waitstream(chan, argv[4]);
00944    if (res) {
00945       fdprintf(agi->fd, "200 result=%d (randomerror) endpos=%ld\n", res, sample_offset);
00946    } else {
00947       fs = ast_writefile(argv[2], argv[3], NULL, O_CREAT | O_WRONLY | (sample_offset ? O_APPEND : 0), 0, 0644);
00948       if (!fs) {
00949          res = -1;
00950          fdprintf(agi->fd, "200 result=%d (writefile)\n", res);
00951          if (sildet)
00952             ast_dsp_free(sildet);
00953          return RESULT_FAILURE;
00954       }
00955       
00956       /* Request a video update */
00957       ast_indicate(chan, AST_CONTROL_VIDUPDATE);
00958    
00959       chan->stream = fs;
00960       ast_applystream(chan,fs);
00961       /* really should have checks */
00962       ast_seekstream(fs, sample_offset, SEEK_SET);
00963       ast_truncstream(fs);
00964       
00965       start = ast_tvnow();
00966       while ((ms < 0) || ast_tvdiff_ms(ast_tvnow(), start) < ms) {
00967          res = ast_waitfor(chan, -1);
00968          if (res < 0) {
00969             ast_closestream(fs);
00970             fdprintf(agi->fd, "200 result=%d (waitfor) endpos=%ld\n", res,sample_offset);
00971             if (sildet)
00972                ast_dsp_free(sildet);
00973             return RESULT_FAILURE;
00974          }
00975          f = ast_read(chan);
00976          if (!f) {
00977             fdprintf(agi->fd, "200 result=%d (hangup) endpos=%ld\n", 0, sample_offset);
00978             ast_closestream(fs);
00979             if (sildet)
00980                ast_dsp_free(sildet);
00981             return RESULT_FAILURE;
00982          }
00983          switch(f->frametype) {
00984          case AST_FRAME_DTMF:
00985             if (strchr(argv[4], f->subclass)) {
00986                /* This is an interrupting chracter, so rewind to chop off any small
00987                   amount of DTMF that may have been recorded
00988                */
00989                ast_stream_rewind(fs, 200);
00990                ast_truncstream(fs);
00991                sample_offset = ast_tellstream(fs);
00992                fdprintf(agi->fd, "200 result=%d (dtmf) endpos=%ld\n", f->subclass, sample_offset);
00993                ast_closestream(fs);
00994                ast_frfree(f);
00995                if (sildet)
00996                   ast_dsp_free(sildet);
00997                return RESULT_SUCCESS;
00998             }
00999             break;
01000          case AST_FRAME_VOICE:
01001             ast_writestream(fs, f);
01002             /* this is a safe place to check progress since we know that fs
01003              * is valid after a write, and it will then have our current
01004              * location */
01005             sample_offset = ast_tellstream(fs);
01006                                 if (silence > 0) {
01007                                  dspsilence = 0;
01008                                         ast_dsp_silence(sildet, f, &dspsilence);
01009                                         if (dspsilence) {
01010                                              totalsilence = dspsilence;
01011                                         } else {
01012                                                 totalsilence = 0;
01013                                         }
01014                                         if (totalsilence > silence) {
01015                                              /* Ended happily with silence */
01016                                                 gotsilence = 1;
01017                                                 break;
01018                                         }
01019                               }
01020             break;
01021          case AST_FRAME_VIDEO:
01022             ast_writestream(fs, f);
01023          default:
01024             /* Ignore all other frames */
01025             break;
01026          }
01027          ast_frfree(f);
01028          if (gotsilence)
01029             break;
01030          }
01031 
01032                if (gotsilence) {
01033                         ast_stream_rewind(fs, silence-1000);
01034                   ast_truncstream(fs);
01035          sample_offset = ast_tellstream(fs);
01036       }     
01037       fdprintf(agi->fd, "200 result=%d (timeout) endpos=%ld\n", res, sample_offset);
01038       ast_closestream(fs);
01039    }
01040 
01041         if (silence > 0) {
01042                 res = ast_set_read_format(chan, rfmt);
01043                 if (res)
01044                         ast_log(LOG_WARNING, "Unable to restore read format on '%s'\n", chan->name);
01045                 ast_dsp_free(sildet);
01046         }
01047    return RESULT_SUCCESS;
01048 }

static int handle_recvchar ( struct ast_channel chan,
AGI agi,
int  argc,
char *  argv[] 
) [static]

Definition at line 443 of file res_agi.c.

References ast_recvchar(), AGI::fd, fdprintf, RESULT_FAILURE, RESULT_SHOWUSAGE, and RESULT_SUCCESS.

00444 {
00445    int res;
00446    if (argc != 3)
00447       return RESULT_SHOWUSAGE;
00448    res = ast_recvchar(chan,atoi(argv[2]));
00449    if (res == 0) {
00450       fdprintf(agi->fd, "200 result=%d (timeout)\n", res);
00451       return RESULT_SUCCESS;
00452    }
00453    if (res > 0) {
00454       fdprintf(agi->fd, "200 result=%d\n", res);
00455       return RESULT_SUCCESS;
00456    }
00457    else {
00458       fdprintf(agi->fd, "200 result=%d (hangup)\n", res);
00459       return RESULT_FAILURE;
00460    }
00461 }

static int handle_recvtext ( struct ast_channel chan,
AGI agi,
int  argc,
char *  argv[] 
) [static]

Definition at line 463 of file res_agi.c.

References ast_recvtext(), ast_hostent::buf, AGI::fd, fdprintf, free, RESULT_SHOWUSAGE, and RESULT_SUCCESS.

00464 {
00465    char *buf;
00466    
00467    if (argc != 3)
00468       return RESULT_SHOWUSAGE;
00469    buf = ast_recvtext(chan,atoi(argv[2]));
00470    if (buf) {
00471       fdprintf(agi->fd, "200 result=1 (%s)\n", buf);
00472       free(buf);
00473    } else { 
00474       fdprintf(agi->fd, "200 result=-1\n");
00475    }
00476    return RESULT_SUCCESS;
00477 }

static int handle_sayalpha ( struct ast_channel chan,
AGI agi,
int  argc,
char *  argv[] 
) [static]

Definition at line 717 of file res_agi.c.

References ast_say_character_str_full, AGI::audio, AGI::ctrl, AGI::fd, fdprintf, RESULT_FAILURE, RESULT_SHOWUSAGE, and RESULT_SUCCESS.

00718 {
00719    int res;
00720 
00721    if (argc != 4)
00722       return RESULT_SHOWUSAGE;
00723 
00724    res = ast_say_character_str_full(chan, argv[2], argv[3], chan->language, agi->audio, agi->ctrl);
00725    if (res == 1) /* New command */
00726       return RESULT_SUCCESS;
00727    fdprintf(agi->fd, "200 result=%d\n", res);
00728    return (res >= 0) ? RESULT_SUCCESS : RESULT_FAILURE;
00729 }

static int handle_saydate ( struct ast_channel chan,
AGI agi,
int  argc,
char *  argv[] 
) [static]

Definition at line 731 of file res_agi.c.

References ast_say_date, AGI::fd, fdprintf, RESULT_FAILURE, RESULT_SHOWUSAGE, and RESULT_SUCCESS.

00732 {
00733    int res;
00734    int num;
00735    if (argc != 4)
00736       return RESULT_SHOWUSAGE;
00737    if (sscanf(argv[2], "%d", &num) != 1)
00738       return RESULT_SHOWUSAGE;
00739    res = ast_say_date(chan, num, argv[3], chan->language);
00740    if (res == 1)
00741       return RESULT_SUCCESS;
00742    fdprintf(agi->fd, "200 result=%d\n", res);
00743    return (res >= 0) ? RESULT_SUCCESS : RESULT_FAILURE;
00744 }

static int handle_saydatetime ( struct ast_channel chan,
AGI agi,
int  argc,
char *  argv[] 
) [static]

Definition at line 761 of file res_agi.c.

References ast_get_time_t(), ast_say_date_with_format, ast_strlen_zero(), AGI::fd, fdprintf, format, RESULT_FAILURE, RESULT_SHOWUSAGE, and RESULT_SUCCESS.

00762 {
00763    int res=0;
00764    time_t unixtime;
00765    char *format, *zone=NULL;
00766    
00767    if (argc < 4)
00768       return RESULT_SHOWUSAGE;
00769 
00770    if (argc > 4) {
00771       format = argv[4];
00772    } else {
00773       /* XXX this doesn't belong here, but in the 'say' module */
00774       if (!strcasecmp(chan->language, "de")) {
00775          format = "A dBY HMS";
00776       } else {
00777          format = "ABdY 'digits/at' IMp"; 
00778       }
00779    }
00780 
00781    if (argc > 5 && !ast_strlen_zero(argv[5]))
00782       zone = argv[5];
00783 
00784    if (ast_get_time_t(argv[2], &unixtime, 0, NULL))
00785       return RESULT_SHOWUSAGE;
00786 
00787    res = ast_say_date_with_format(chan, unixtime, argv[3], chan->language, format, zone);
00788    if (res == 1)
00789       return RESULT_SUCCESS;
00790 
00791    fdprintf(agi->fd, "200 result=%d\n", res);
00792    return (res >= 0) ? RESULT_SUCCESS : RESULT_FAILURE;
00793 }

static int handle_saydigits ( struct ast_channel chan,
AGI agi,
int  argc,
char *  argv[] 
) [static]

Definition at line 700 of file res_agi.c.

References ast_say_digit_str_full, AGI::audio, AGI::ctrl, AGI::fd, fdprintf, RESULT_FAILURE, RESULT_SHOWUSAGE, and RESULT_SUCCESS.

00701 {
00702    int res;
00703    int num;
00704 
00705    if (argc != 4)
00706       return RESULT_SHOWUSAGE;
00707    if (sscanf(argv[2], "%d", &num) != 1)
00708       return RESULT_SHOWUSAGE;
00709 
00710    res = ast_say_digit_str_full(chan, argv[2], argv[3], chan->language, agi->audio, agi->ctrl);
00711    if (res == 1) /* New command */
00712       return RESULT_SUCCESS;
00713    fdprintf(agi->fd, "200 result=%d\n", res);
00714    return (res >= 0) ? RESULT_SUCCESS : RESULT_FAILURE;
00715 }

static int handle_saynumber ( struct ast_channel chan,
AGI agi,
int  argc,
char *  argv[] 
) [static]

Definition at line 685 of file res_agi.c.

References ast_say_number_full, AGI::audio, AGI::ctrl, AGI::fd, fdprintf, RESULT_FAILURE, RESULT_SHOWUSAGE, and RESULT_SUCCESS.

00686 {
00687    int res;
00688    int num;
00689    if (argc != 4)
00690       return RESULT_SHOWUSAGE;
00691    if (sscanf(argv[2], "%d", &num) != 1)
00692       return RESULT_SHOWUSAGE;
00693    res = ast_say_number_full(chan, num, argv[3], chan->language, (char *) NULL, agi->audio, agi->ctrl);
00694    if (res == 1)
00695       return RESULT_SUCCESS;
00696    fdprintf(agi->fd, "200 result=%d\n", res);
00697    return (res >= 0) ? RESULT_SUCCESS : RESULT_FAILURE;
00698 }

static int handle_sayphonetic ( struct ast_channel chan,
AGI agi,
int  argc,
char *  argv[] 
) [static]

Definition at line 795 of file res_agi.c.

References ast_say_phonetic_str_full, AGI::audio, AGI::ctrl, AGI::fd, fdprintf, RESULT_FAILURE, RESULT_SHOWUSAGE, and RESULT_SUCCESS.

00796 {
00797    int res;
00798 
00799    if (argc != 4)
00800       return RESULT_SHOWUSAGE;
00801 
00802    res = ast_say_phonetic_str_full(chan, argv[2], argv[3], chan->language, agi->audio, agi->ctrl);
00803    if (res == 1) /* New command */
00804       return RESULT_SUCCESS;
00805    fdprintf(agi->fd, "200 result=%d\n", res);
00806    return (res >= 0) ? RESULT_SUCCESS : RESULT_FAILURE;
00807 }

static int handle_saytime ( struct ast_channel chan,
AGI agi,
int  argc,
char *  argv[] 
) [static]

Definition at line 746 of file res_agi.c.

References ast_say_time, AGI::fd, fdprintf, RESULT_FAILURE, RESULT_SHOWUSAGE, and RESULT_SUCCESS.

00747 {
00748    int res;
00749    int num;
00750    if (argc != 4)
00751       return RESULT_SHOWUSAGE;
00752    if (sscanf(argv[2], "%d", &num) != 1)
00753       return RESULT_SHOWUSAGE;
00754    res = ast_say_time(chan, num, argv[3], chan->language);
00755    if (res == 1)
00756       return RESULT_SUCCESS;
00757    fdprintf(agi->fd, "200 result=%d\n", res);
00758    return (res >= 0) ? RESULT_SUCCESS : RESULT_FAILURE;
00759 }

static int handle_sendimage ( struct ast_channel chan,
AGI agi,
int  argc,
char *  argv[] 
) [static]

Definition at line 500 of file res_agi.c.

References ast_check_hangup(), ast_send_image(), AGI::fd, fdprintf, RESULT_FAILURE, RESULT_SHOWUSAGE, and RESULT_SUCCESS.

00501 {
00502    int res;
00503    if (argc != 3)
00504       return RESULT_SHOWUSAGE;
00505    res = ast_send_image(chan, argv[2]);
00506    if (!ast_check_hangup(chan))
00507       res = 0;
00508    fdprintf(agi->fd, "200 result=%d\n", res);
00509    return (res >= 0) ? RESULT_SUCCESS : RESULT_FAILURE;
00510 }

static int handle_sendtext ( struct ast_channel chan,
AGI agi,
int  argc,
char *  argv[] 
) [static]

Definition at line 426 of file res_agi.c.

References ast_sendtext(), AGI::fd, fdprintf, RESULT_FAILURE, RESULT_SHOWUSAGE, and RESULT_SUCCESS.

00427 {
00428    int res;
00429    if (argc != 3)
00430       return RESULT_SHOWUSAGE;
00431    /* At the moment, the parser (perhaps broken) returns with
00432       the last argument PLUS the newline at the end of the input
00433       buffer. This probably needs to be fixed, but I wont do that
00434       because other stuff may break as a result. The right way
00435       would probably be to strip off the trailing newline before
00436       parsing, then here, add a newline at the end of the string
00437       before sending it to ast_sendtext --DUDE */
00438    res = ast_sendtext(chan, argv[2]);
00439    fdprintf(agi->fd, "200 result=%d\n", res);
00440    return (res >= 0) ? RESULT_SUCCESS : RESULT_FAILURE;
00441 }

static int handle_setcallerid ( struct ast_channel chan,
AGI agi,
int  argc,
char **  argv 
) [static]

Definition at line 1119 of file res_agi.c.

References ast_callerid_parse(), ast_set_callerid(), ast_shrink_phone_number(), AGI::fd, fdprintf, and RESULT_SUCCESS.

01120 {
01121    char tmp[256]="";
01122    char *l = NULL, *n = NULL;
01123 
01124    if (argv[2]) {
01125       ast_copy_string(tmp, argv[2], sizeof(tmp));
01126       ast_callerid_parse(tmp, &n, &l);
01127       if (l)
01128          ast_shrink_phone_number(l);
01129       else
01130          l = "";
01131       if (!n)
01132          n = "";
01133       ast_set_callerid(chan, l, n, NULL);
01134    }
01135 
01136    fdprintf(agi->fd, "200 result=1\n");
01137    return RESULT_SUCCESS;
01138 }

static int handle_setcontext ( struct ast_channel chan,
AGI agi,
int  argc,
char *  argv[] 
) [static]

Definition at line 838 of file res_agi.c.

References ast_channel::context, AGI::fd, fdprintf, RESULT_SHOWUSAGE, and RESULT_SUCCESS.

00839 {
00840 
00841    if (argc != 3)
00842       return RESULT_SHOWUSAGE;
00843    ast_copy_string(chan->context, argv[2], sizeof(chan->context));
00844    fdprintf(agi->fd, "200 result=0\n");
00845    return RESULT_SUCCESS;
00846 }

static int handle_setextension ( struct ast_channel chan,
AGI agi,
int  argc,
char **  argv 
) [static]

Definition at line 848 of file res_agi.c.

References ast_channel::exten, AGI::fd, fdprintf, RESULT_SHOWUSAGE, and RESULT_SUCCESS.

00849 {
00850    if (argc != 3)
00851       return RESULT_SHOWUSAGE;
00852    ast_copy_string(chan->exten, argv[2], sizeof(chan->exten));
00853    fdprintf(agi->fd, "200 result=0\n");
00854    return RESULT_SUCCESS;
00855 }

static int handle_setmusic ( struct ast_channel chan,
AGI agi,
int  argc,
char *  argv[] 
) [static]

Definition at line 1346 of file res_agi.c.

References ast_moh_start(), ast_moh_stop(), AGI::fd, fdprintf, and RESULT_SUCCESS.

01347 {
01348    if (!strncasecmp(argv[2], "on", 2))
01349       ast_moh_start(chan, argc > 3 ? argv[3] : NULL, NULL);
01350    else if (!strncasecmp(argv[2], "off", 3))
01351       ast_moh_stop(chan);
01352    fdprintf(agi->fd, "200 result=0\n");
01353    return RESULT_SUCCESS;
01354 }

static int handle_setpriority ( struct ast_channel chan,
AGI agi,
int  argc,
char **  argv 
) [static]

Definition at line 857 of file res_agi.c.

References ast_explicit_goto(), ast_findlabel_extension(), ast_channel::cid, ast_callerid::cid_num, ast_channel::context, ast_channel::exten, AGI::fd, fdprintf, RESULT_SHOWUSAGE, and RESULT_SUCCESS.

00858 {
00859    int pri;
00860    if (argc != 3)
00861       return RESULT_SHOWUSAGE;   
00862 
00863    if (sscanf(argv[2], "%d", &pri) != 1) {
00864       if ((pri = ast_findlabel_extension(chan, chan->context, chan->exten, argv[2], chan->cid.cid_num)) < 1)
00865          return RESULT_SHOWUSAGE;
00866    }
00867 
00868    ast_explicit_goto(chan, NULL, NULL, pri);
00869    fdprintf(agi->fd, "200 result=0\n");
00870    return RESULT_SUCCESS;
00871 }

static int handle_setvariable ( struct ast_channel chan,
AGI agi,
int  argc,
char **  argv 
) [static]

Definition at line 1163 of file res_agi.c.

References AGI::fd, fdprintf, pbx_builtin_setvar_helper(), and RESULT_SUCCESS.

01164 {
01165    if (argv[3])
01166       pbx_builtin_setvar_helper(chan, argv[2], argv[3]);
01167 
01168    fdprintf(agi->fd, "200 result=1\n");
01169    return RESULT_SUCCESS;
01170 }

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

Definition at line 1912 of file res_agi.c.

References ast_cli(), ast_join(), find_command(), help_workhorse(), RESULT_SHOWUSAGE, RESULT_SUCCESS, and agi_command::usage.

01913 {
01914    struct agi_command *e;
01915    char fullcmd[80];
01916    if ((argc < 2))
01917       return RESULT_SHOWUSAGE;
01918    if (argc > 2) {
01919       e = find_command(argv + 2, 1);
01920       if (e) 
01921          ast_cli(fd, e->usage);
01922       else {
01923          if (find_command(argv + 2, -1)) {
01924             return help_workhorse(fd, argv + 1);
01925          } else {
01926             ast_join(fullcmd, sizeof(fullcmd), argv+1);
01927             ast_cli(fd, "No such command '%s'.\n", fullcmd);
01928          }
01929       }
01930    } else {
01931       return help_workhorse(fd, NULL);
01932    }
01933    return RESULT_SUCCESS;
01934 }

static int handle_streamfile ( struct ast_channel chan,
AGI agi,
int  argc,
char *  argv[] 
) [static]

Definition at line 554 of file res_agi.c.

References ast_applystream(), ast_log(), ast_openstream(), ast_openvstream(), ast_playstream(), ast_seekstream(), ast_stopstream(), ast_tellstream(), ast_verbose(), ast_waitstream_full(), AGI::audio, AGI::ctrl, AGI::fd, fdprintf, LOG_DEBUG, option_verbose, RESULT_FAILURE, RESULT_SHOWUSAGE, RESULT_SUCCESS, ast_channel::stream, VERBOSE_PREFIX_3, and ast_filestream::vfs.

00555 {
00556    int res;
00557    int vres;   
00558    struct ast_filestream *fs;
00559    struct ast_filestream *vfs;
00560    long sample_offset = 0;
00561    long max_length;
00562    char *edigits = "";
00563 
00564    if (argc < 4 || argc > 5)
00565       return RESULT_SHOWUSAGE;
00566 
00567    if (argv[3]) 
00568       edigits = argv[3];
00569 
00570    if ((argc > 4) && (sscanf(argv[4], "%ld", &sample_offset) != 1))
00571       return RESULT_SHOWUSAGE;
00572    
00573    fs = ast_openstream(chan, argv[2], chan->language);   
00574    
00575    if (!fs) {
00576       fdprintf(agi->fd, "200 result=%d endpos=%ld\n", 0, sample_offset);
00577       return RESULT_SUCCESS;
00578    }  
00579    vfs = ast_openvstream(chan, argv[2], chan->language);
00580    if (vfs)
00581       ast_log(LOG_DEBUG, "Ooh, found a video stream, too\n");
00582       
00583    if (option_verbose > 2)
00584       ast_verbose(VERBOSE_PREFIX_3 "Playing '%s' (escape_digits=%s) (sample_offset %ld)\n", argv[2], edigits, sample_offset);
00585 
00586    ast_seekstream(fs, 0, SEEK_END);
00587    max_length = ast_tellstream(fs);
00588    ast_seekstream(fs, sample_offset, SEEK_SET);
00589    res = ast_applystream(chan, fs);
00590    if (vfs)
00591       vres = ast_applystream(chan, vfs);
00592    ast_playstream(fs);
00593    if (vfs)
00594       ast_playstream(vfs);
00595    
00596    res = ast_waitstream_full(chan, argv[3], agi->audio, agi->ctrl);
00597    /* this is to check for if ast_waitstream closed the stream, we probably are at
00598     * the end of the stream, return that amount, else check for the amount */
00599    sample_offset = (chan->stream) ? ast_tellstream(fs) : max_length;
00600    ast_stopstream(chan);
00601    if (res == 1) {
00602       /* Stop this command, don't print a result line, as there is a new command */
00603       return RESULT_SUCCESS;
00604    }
00605    fdprintf(agi->fd, "200 result=%d endpos=%ld\n", res, sample_offset);
00606    return (res >= 0) ? RESULT_SUCCESS : RESULT_FAILURE;
00607 }

static int handle_tddmode ( struct ast_channel chan,
AGI agi,
int  argc,
char *  argv[] 
) [static]

Definition at line 479 of file res_agi.c.

References ast_channel_setoption(), AST_OPTION_TDD, AGI::fd, fdprintf, RESULT_SHOWUSAGE, and RESULT_SUCCESS.

00480 {
00481    int res,x;
00482    if (argc != 3)
00483       return RESULT_SHOWUSAGE;
00484    if (!strncasecmp(argv[2],"on",2)) 
00485       x = 1; 
00486    else 
00487       x = 0;
00488    if (!strncasecmp(argv[2],"mate",4)) 
00489       x = 2;
00490    if (!strncasecmp(argv[2],"tdd",3))
00491       x = 1;
00492    res = ast_channel_setoption(chan, AST_OPTION_TDD, &x, sizeof(char), 0);
00493    if (res != RESULT_SUCCESS)
00494       fdprintf(agi->fd, "200 result=0\n");
00495    else
00496       fdprintf(agi->fd, "200 result=1\n");
00497    return RESULT_SUCCESS;
00498 }

static int handle_verbose ( struct ast_channel chan,
AGI agi,
int  argc,
char **  argv 
) [static]

Definition at line 1218 of file res_agi.c.

References ast_verbose(), ast_channel::data, AGI::fd, fdprintf, option_verbose, prefix, RESULT_SHOWUSAGE, RESULT_SUCCESS, VERBOSE_PREFIX_1, VERBOSE_PREFIX_2, VERBOSE_PREFIX_3, and VERBOSE_PREFIX_4.

01219 {
01220    int level = 0;
01221    char *prefix;
01222 
01223    if (argc < 2)
01224       return RESULT_SHOWUSAGE;
01225 
01226    if (argv[2])
01227       sscanf(argv[2], "%d", &level);
01228 
01229    switch (level) {
01230       case 4:
01231          prefix = VERBOSE_PREFIX_4;
01232          break;
01233       case 3:
01234          prefix = VERBOSE_PREFIX_3;
01235          break;
01236       case 2:
01237          prefix = VERBOSE_PREFIX_2;
01238          break;
01239       case 1:
01240       default:
01241          prefix = VERBOSE_PREFIX_1;
01242          break;
01243    }
01244 
01245    if (level <= option_verbose)
01246       ast_verbose("%s %s: %s\n", prefix, chan->data, argv[1]);
01247    
01248    fdprintf(agi->fd, "200 result=1\n");
01249    
01250    return RESULT_SUCCESS;
01251 }

static int handle_waitfordigit ( struct ast_channel chan,
AGI agi,
int  argc,
char *  argv[] 
) [static]

Definition at line 413 of file res_agi.c.

References ast_waitfordigit_full(), AGI::audio, AGI::ctrl, AGI::fd, fdprintf, RESULT_FAILURE, RESULT_SHOWUSAGE, and RESULT_SUCCESS.

00414 {
00415    int res;
00416    int to;
00417    if (argc != 4)
00418       return RESULT_SHOWUSAGE;
00419    if (sscanf(argv[3], "%d", &to) != 1)
00420       return RESULT_SHOWUSAGE;
00421    res = ast_waitfordigit_full(chan, to, agi->audio, agi->ctrl);
00422    fdprintf(agi->fd, "200 result=%d\n", res);
00423    return (res >= 0) ? RESULT_SUCCESS : RESULT_FAILURE;
00424 }

static int help_workhorse ( int  fd,
char *  match[] 
) [static]

Definition at line 1643 of file res_agi.c.

References ast_cli(), ast_join(), agi_command::cmda, and agi_command::summary.

01644 {
01645    char fullcmd[80];
01646    char matchstr[80];
01647    int x;
01648    struct agi_command *e;
01649    if (match)
01650       ast_join(matchstr, sizeof(matchstr), match);
01651    for (x=0;x<sizeof(commands)/sizeof(commands[0]);x++) {
01652       e = &commands[x]; 
01653       if (!e->cmda[0])
01654          break;
01655       /* Hide commands that start with '_' */
01656       if ((e->cmda[0])[0] == '_')
01657          continue;
01658       ast_join(fullcmd, sizeof(fullcmd), e->cmda);
01659       if (match && strncasecmp(matchstr, fullcmd, strlen(matchstr)))
01660          continue;
01661       ast_cli(fd, "%20.20s   %s\n", fullcmd, e->summary);
01662    }
01663    return 0;
01664 }

static enum agi_result launch_netscript ( char *  agiurl,
char *  argv[],
int *  fds,
int *  efd,
int *  opid 
) [static]

Definition at line 141 of file res_agi.c.

References AGI_PORT, AGI_RESULT_FAILURE, AGI_RESULT_SUCCESS, ast_gethostbyname(), ast_log(), ast_strdupa, ast_strlen_zero(), pollfd::events, pollfd::fd, fdprintf, hp, LOG_DEBUG, LOG_WARNING, MAX_AGI_CONNECT, option_debug, poll(), POLLOUT, and s.

Referenced by launch_script().

00142 {
00143    int s;
00144    int flags;
00145    struct pollfd pfds[1];
00146    char *host;
00147    char *c; int port = AGI_PORT;
00148    char *script="";
00149    struct sockaddr_in sin;
00150    struct hostent *hp;
00151    struct ast_hostent ahp;
00152    int res;
00153 
00154    /* agiusl is "agi://host.domain[:port][/script/name]" */
00155    host = ast_strdupa(agiurl + 6);  /* Remove agi:// */
00156    /* Strip off any script name */
00157    if ((c = strchr(host, '/'))) {
00158       *c = '\0';
00159       c++;
00160       script = c;
00161    }
00162    if ((c = strchr(host, ':'))) {
00163       *c = '\0';
00164       c++;
00165       port = atoi(c);
00166    }
00167    if (efd) {
00168       ast_log(LOG_WARNING, "AGI URI's don't support Enhanced AGI yet\n");
00169       return -1;
00170    }
00171    hp = ast_gethostbyname(host, &ahp);
00172    if (!hp) {
00173       ast_log(LOG_WARNING, "Unable to locate host '%s'\n", host);
00174       return -1;
00175    }
00176    s = socket(AF_INET, SOCK_STREAM, 0);
00177    if (s < 0) {
00178       ast_log(LOG_WARNING, "Unable to create socket: %s\n", strerror(errno));
00179       return -1;
00180    }
00181    flags = fcntl(s, F_GETFL);
00182    if (flags < 0) {
00183       ast_log(LOG_WARNING, "Fcntl(F_GETFL) failed: %s\n", strerror(errno));
00184       close(s);
00185       return -1;
00186    }
00187    if (fcntl(s, F_SETFL, flags | O_NONBLOCK) < 0) {
00188       ast_log(LOG_WARNING, "Fnctl(F_SETFL) failed: %s\n", strerror(errno));
00189       close(s);
00190       return -1;
00191    }
00192    memset(&sin, 0, sizeof(sin));
00193    sin.sin_family = AF_INET;
00194    sin.sin_port = htons(port);
00195    memcpy(&sin.sin_addr, hp->h_addr, sizeof(sin.sin_addr));
00196    if (connect(s, (struct sockaddr *)&sin, sizeof(sin)) && (errno != EINPROGRESS)) {
00197       ast_log(LOG_WARNING, "Connect failed with unexpected error: %s\n", strerror(errno));
00198       close(s);
00199       return AGI_RESULT_FAILURE;
00200    }
00201 
00202    pfds[0].fd = s;
00203    pfds[0].events = POLLOUT;
00204    while ((res = poll(pfds, 1, MAX_AGI_CONNECT)) != 1) {
00205       if (errno != EINTR) {
00206          if (!res) {
00207             ast_log(LOG_WARNING, "FastAGI connection to '%s' timed out after MAX_AGI_CONNECT (%d) milliseconds.\n",
00208                agiurl, MAX_AGI_CONNECT);
00209          } else
00210             ast_log(LOG_WARNING, "Connect to '%s' failed: %s\n", agiurl, strerror(errno));
00211          close(s);
00212          return AGI_RESULT_FAILURE;
00213       }
00214    }
00215 
00216    if (fdprintf(s, "agi_network: yes\n") < 0) {
00217       if (errno != EINTR) {
00218          ast_log(LOG_WARNING, "Connect to '%s' failed: %s\n", agiurl, strerror(errno));
00219          close(s);
00220          return AGI_RESULT_FAILURE;
00221       }
00222    }
00223 
00224    /* If we have a script parameter, relay it to the fastagi server */
00225    if (!ast_strlen_zero(script))
00226       fdprintf(s, "agi_network_script: %s\n", script);
00227 
00228    if (option_debug > 3)
00229       ast_log(LOG_DEBUG, "Wow, connected!\n");
00230    fds[0] = s;
00231    fds[1] = s;
00232    *opid = -1;
00233    return AGI_RESULT_SUCCESS;
00234 }

static enum agi_result launch_script ( char *  script,
char *  argv[],
int *  fds,
int *  efd,
int *  opid 
) [static]

Definition at line 236 of file res_agi.c.

References AGI_RESULT_FAILURE, AGI_RESULT_SUCCESS, ast_config_AST_AGI_DIR, ast_config_AST_CONFIG_DIR, ast_config_AST_CONFIG_FILE, ast_config_AST_DATA_DIR, ast_config_AST_KEY_DIR, ast_config_AST_LOG_DIR, ast_config_AST_MODULE_DIR, ast_config_AST_MONITOR_DIR, ast_config_AST_RUN_DIR, ast_config_AST_SPOOL_DIR, ast_config_AST_VAR_DIR, ast_log(), ast_set_priority(), ast_verbose(), launch_netscript(), LOG_WARNING, option_verbose, setenv(), and VERBOSE_PREFIX_3.

Referenced by agi_exec_full().

00237 {
00238    char tmp[256];
00239    int pid;
00240    int toast[2];
00241    int fromast[2];
00242    int audio[2];
00243    int x;
00244    int res;
00245    sigset_t signal_set, old_set;
00246    
00247    if (!strncasecmp(script, "agi://", 6))
00248       return launch_netscript(script, argv, fds, efd, opid);
00249    
00250    if (script[0] != '/') {
00251       snprintf(tmp, sizeof(tmp), "%s/%s", (char *)ast_config_AST_AGI_DIR, script);
00252       script = tmp;
00253    }
00254    if (pipe(toast)) {
00255       ast_log(LOG_WARNING, "Unable to create toast pipe: %s\n",strerror(errno));
00256       return AGI_RESULT_FAILURE;
00257    }
00258    if (pipe(fromast)) {
00259       ast_log(LOG_WARNING, "unable to create fromast pipe: %s\n", strerror(errno));
00260       close(toast[0]);
00261       close(toast[1]);
00262       return AGI_RESULT_FAILURE;
00263    }
00264    if (efd) {
00265       if (pipe(audio)) {
00266          ast_log(LOG_WARNING, "unable to create audio pipe: %s\n", strerror(errno));
00267          close(fromast[0]);
00268          close(fromast[1]);
00269          close(toast[0]);
00270          close(toast[1]);
00271          return AGI_RESULT_FAILURE;
00272       }
00273       res = fcntl(audio[1], F_GETFL);
00274       if (res > -1) 
00275          res = fcntl(audio[1], F_SETFL, res | O_NONBLOCK);
00276       if (res < 0) {
00277          ast_log(LOG_WARNING, "unable to set audio pipe parameters: %s\n", strerror(errno));
00278          close(fromast[0]);
00279          close(fromast[1]);
00280          close(toast[0]);
00281          close(toast[1]);
00282          close(audio[0]);
00283          close(audio[1]);
00284          return AGI_RESULT_FAILURE;
00285       }
00286    }
00287 
00288    /* Block SIGHUP during the fork - prevents a race */
00289    sigfillset(&signal_set);
00290    pthread_sigmask(SIG_BLOCK, &signal_set, &old_set);
00291    pid = fork();
00292    if (pid < 0) {
00293       ast_log(LOG_WARNING, "Failed to fork(): %s\n", strerror(errno));
00294       pthread_sigmask(SIG_SETMASK, &old_set, NULL);
00295       return AGI_RESULT_FAILURE;
00296    }
00297    if (!pid) {
00298       /* Pass paths to AGI via environmental variables */
00299       setenv("AST_CONFIG_DIR", ast_config_AST_CONFIG_DIR, 1);
00300       setenv("AST_CONFIG_FILE", ast_config_AST_CONFIG_FILE, 1);
00301       setenv("AST_MODULE_DIR", ast_config_AST_MODULE_DIR, 1);
00302       setenv("AST_SPOOL_DIR", ast_config_AST_SPOOL_DIR, 1);
00303       setenv("AST_MONITOR_DIR", ast_config_AST_MONITOR_DIR, 1);
00304       setenv("AST_VAR_DIR", ast_config_AST_VAR_DIR, 1);
00305       setenv("AST_DATA_DIR", ast_config_AST_DATA_DIR, 1);
00306       setenv("AST_LOG_DIR", ast_config_AST_LOG_DIR, 1);
00307       setenv("AST_AGI_DIR", ast_config_AST_AGI_DIR, 1);
00308       setenv("AST_KEY_DIR", ast_config_AST_KEY_DIR, 1);
00309       setenv("AST_RUN_DIR", ast_config_AST_RUN_DIR, 1);
00310 
00311       /* Don't run AGI scripts with realtime priority -- it causes audio stutter */
00312       ast_set_priority(0);
00313 
00314       /* Redirect stdin and out, provide enhanced audio channel if desired */
00315       dup2(fromast[0], STDIN_FILENO);
00316       dup2(toast[1], STDOUT_FILENO);
00317       if (efd) {
00318          dup2(audio[0], STDERR_FILENO + 1);
00319       } else {
00320          close(STDERR_FILENO + 1);
00321       }
00322 
00323       /* Before we unblock our signals, return our trapped signals back to the defaults */
00324       signal(SIGHUP, SIG_DFL);
00325       signal(SIGCHLD, SIG_DFL);
00326       signal(SIGINT, SIG_DFL);
00327       signal(SIGURG, SIG_DFL);
00328       signal(SIGTERM, SIG_DFL);
00329       signal(SIGPIPE, SIG_DFL);
00330       signal(SIGXFSZ, SIG_DFL);
00331 
00332       /* unblock important signal handlers */
00333       if (pthread_sigmask(SIG_UNBLOCK, &signal_set, NULL)) {
00334          ast_log(LOG_WARNING, "unable to unblock signals for AGI script: %s\n", strerror(errno));
00335          _exit(1);
00336       }
00337 
00338       /* Close everything but stdin/out/error */
00339       for (x=STDERR_FILENO + 2;x<1024;x++) 
00340          close(x);
00341 
00342       /* Execute script */
00343       execv(script, argv);
00344       /* Can't use ast_log since FD's are closed */
00345       fprintf(stdout, "verbose \"Failed to execute '%s': %s\" 2\n", script, strerror(errno));
00346       fflush(stdout);
00347       _exit(1);
00348    }
00349    pthread_sigmask(SIG_SETMASK, &old_set, NULL);
00350    if (option_verbose > 2) 
00351       ast_verbose(VERBOSE_PREFIX_3 "Launched AGI Script %s\n", script);
00352    fds[0] = toast[0];
00353    fds[1] = fromast[1];
00354    if (efd) {
00355       *efd = audio[1];
00356    }
00357    /* close what we're not using in the parent */
00358    close(toast[1]);
00359    close(fromast[0]);
00360 
00361    if (efd)
00362       close(audio[0]);
00363 
00364    *opid = pid;
00365    return AGI_RESULT_SUCCESS;
00366 }

static int load_module ( void   )  [static]

Definition at line 2146 of file res_agi.c.

References agi_exec(), ast_cli_register_multiple(), ast_register_application(), deadagi_exec(), and eagi_exec().

static int parse_args ( char *  s,
int *  max,
char *  argv[] 
) [static]

Definition at line 1729 of file res_agi.c.

References ast_log(), LOG_WARNING, and MAX_ARGS.

01730 {
01731    int x=0;
01732    int quoted=0;
01733    int escaped=0;
01734    int whitespace=1;
01735    char *cur;
01736 
01737    cur = s;
01738    while(*s) {
01739       switch(*s) {
01740       case '"':
01741          /* If it's escaped, put a literal quote */
01742          if (escaped) 
01743             goto normal;
01744          else 
01745             quoted = !quoted;
01746          if (quoted && whitespace) {
01747             /* If we're starting a quote, coming off white space start a new word, too */
01748             argv[x++] = cur;
01749             whitespace=0;
01750          }
01751          escaped = 0;
01752       break;
01753       case ' ':
01754       case '\t':
01755          if (!quoted && !escaped) {
01756             /* If we're not quoted, mark this as whitespace, and
01757                end the previous argument */
01758             whitespace = 1;
01759             *(cur++) = '\0';
01760          } else
01761             /* Otherwise, just treat it as anything else */ 
01762             goto normal;
01763          break;
01764       case '\\':
01765          /* If we're escaped, print a literal, otherwise enable escaping */
01766          if (escaped) {
01767             goto normal;
01768          } else {
01769             escaped=1;
01770          }
01771          break;
01772       default:
01773 normal:
01774          if (whitespace) {
01775             if (x >= MAX_ARGS -1) {
01776                ast_log(LOG_WARNING, "Too many arguments, truncating\n");
01777                break;
01778             }
01779             /* Coming off of whitespace, start the next argument */
01780             argv[x++] = cur;
01781             whitespace=0;
01782          }
01783          *(cur++) = *s;
01784          escaped=0;
01785       }
01786       s++;
01787    }
01788    /* Null terminate */
01789    *(cur++) = '\0';
01790    argv[x] = NULL;
01791    *max = x;
01792    return 0;
01793 }

static enum agi_result run_agi ( struct ast_channel chan,
char *  request,
AGI agi,
int  pid,
int *  status,
int  dead 
) [static]

Definition at line 1827 of file res_agi.c.

References agi_handle_command(), AGI_RESULT_FAILURE, AGI_RESULT_HANGUP, AGI_RESULT_SUCCESS, ast_false(), AST_FRAME_VOICE, ast_frfree(), ast_log(), AST_PBX_KEEPALIVE, ast_read(), ast_strlen_zero(), ast_verbose(), ast_waitfor_nandfds(), AGI::audio, AGI::ctrl, ast_frame::data, ast_frame::datalen, f, AGI::fd, ast_frame::frametype, LOG_DEBUG, LOG_WARNING, option_verbose, pbx_builtin_getvar_helper(), RETRY, setup_env(), and VERBOSE_PREFIX_3.

Referenced by agi_exec_full().

01828 {
01829    struct ast_channel *c;
01830    int outfd;
01831    int ms;
01832    enum agi_result returnstatus = AGI_RESULT_SUCCESS;
01833    struct ast_frame *f;
01834    char buf[2048];
01835    FILE *readf;
01836    /* how many times we'll retry if ast_waitfor_nandfs will return without either 
01837      channel or file descriptor in case select is interrupted by a system call (EINTR) */
01838    int retry = RETRY;
01839 
01840    if (!(readf = fdopen(agi->ctrl, "r"))) {
01841       ast_log(LOG_WARNING, "Unable to fdopen file descriptor\n");
01842       if (pid > -1)
01843          kill(pid, SIGHUP);
01844       close(agi->ctrl);
01845       return AGI_RESULT_FAILURE;
01846    }
01847    setlinebuf(readf);
01848    setup_env(chan, request, agi->fd, (agi->audio > -1));
01849    for (;;) {
01850       ms = -1;
01851       c = ast_waitfor_nandfds(&chan, dead ? 0 : 1, &agi->ctrl, 1, NULL, &outfd, &ms);
01852       if (c) {
01853          retry = RETRY;
01854          /* Idle the channel until we get a command */
01855          f = ast_read(c);
01856          if (!f) {
01857             ast_log(LOG_DEBUG, "%s hungup\n", chan->name);
01858             returnstatus = AGI_RESULT_HANGUP;
01859             break;
01860          } else {
01861             /* If it's voice, write it to the audio pipe */
01862             if ((agi->audio > -1) && (f->frametype == AST_FRAME_VOICE)) {
01863                /* Write, ignoring errors */
01864                write(agi->audio, f->data, f->datalen);
01865             }
01866             ast_frfree(f);
01867          }
01868       } else if (outfd > -1) {
01869          retry = RETRY;
01870          if (!fgets(buf, sizeof(buf), readf)) {
01871             /* Program terminated */
01872             if (returnstatus)
01873                returnstatus = -1;
01874             if (option_verbose > 2) 
01875                ast_verbose(VERBOSE_PREFIX_3 "AGI Script %s completed, returning %d\n", request, returnstatus);
01876             if (pid > 0)
01877                waitpid(pid, status, 0);
01878             /* No need to kill the pid anymore, since they closed us */
01879             pid = -1;
01880             break;
01881          }
01882          /* get rid of trailing newline, if any */
01883          if (*buf && buf[strlen(buf) - 1] == '\n')
01884             buf[strlen(buf) - 1] = 0;
01885          if (agidebug)
01886             ast_verbose("AGI Rx << %s\n", buf);
01887          returnstatus |= agi_handle_command(chan, agi, buf);
01888          /* If the handle_command returns -1, we need to stop */
01889          if ((returnstatus < 0) || (returnstatus == AST_PBX_KEEPALIVE)) {
01890             break;
01891          }
01892       } else {
01893          if (--retry <= 0) {
01894             ast_log(LOG_WARNING, "No channel, no fd?\n");
01895             returnstatus = AGI_RESULT_FAILURE;
01896             break;
01897          }
01898       }
01899    }
01900    /* Notify process */
01901    if (pid > -1) {
01902       const char *sighup = pbx_builtin_getvar_helper(chan, "AGISIGHUP");
01903       if (ast_strlen_zero(sighup) || !ast_false(sighup)) {
01904          if (kill(pid, SIGHUP))
01905             ast_log(LOG_WARNING, "unable to send SIGHUP to AGI process %d: %s\n", pid, strerror(errno));
01906       }
01907    }
01908    fclose(readf);
01909    return returnstatus;
01910 }

static void setup_env ( struct ast_channel chan,
char *  request,
int  fd,
int  enhanced 
) [static]

Definition at line 368 of file res_agi.c.

References ast_channel::cid, ast_callerid::cid_ani2, ast_callerid::cid_dnid, ast_callerid::cid_name, ast_callerid::cid_num, ast_callerid::cid_pres, ast_callerid::cid_rdnis, ast_callerid::cid_tns, ast_callerid::cid_ton, ast_channel::context, ast_channel::exten, fdprintf, ast_channel::priority, S_OR, ast_channel::tech, and ast_channel_tech::type.

Referenced by run_agi().

00369 {
00370    /* Print initial environment, with agi_request always being the first
00371       thing */
00372    fdprintf(fd, "agi_request: %s\n", request);
00373    fdprintf(fd, "agi_channel: %s\n", chan->name);
00374    fdprintf(fd, "agi_language: %s\n", chan->language);
00375    fdprintf(fd, "agi_type: %s\n", chan->tech->type);
00376    fdprintf(fd, "agi_uniqueid: %s\n", chan->uniqueid);
00377 
00378    /* ANI/DNIS */
00379    fdprintf(fd, "agi_callerid: %s\n", S_OR(chan->cid.cid_num, "unknown"));
00380    fdprintf(fd, "agi_calleridname: %s\n", S_OR(chan->cid.cid_name, "unknown"));
00381    fdprintf(fd, "agi_callingpres: %d\n", chan->cid.cid_pres);
00382    fdprintf(fd, "agi_callingani2: %d\n", chan->cid.cid_ani2);
00383    fdprintf(fd, "agi_callington: %d\n", chan->cid.cid_ton);
00384    fdprintf(fd, "agi_callingtns: %d\n", chan->cid.cid_tns);
00385    fdprintf(fd, "agi_dnid: %s\n", S_OR(chan->cid.cid_dnid, "unknown"));
00386    fdprintf(fd, "agi_rdnis: %s\n", S_OR(chan->cid.cid_rdnis, "unknown"));
00387 
00388    /* Context information */
00389    fdprintf(fd, "agi_context: %s\n", chan->context);
00390    fdprintf(fd, "agi_extension: %s\n", chan->exten);
00391    fdprintf(fd, "agi_priority: %d\n", chan->priority);
00392    fdprintf(fd, "agi_enhanced: %s\n", enhanced ? "1.0" : "0.0");
00393 
00394    /* User information */
00395    fdprintf(fd, "agi_accountcode: %s\n", chan->accountcode ? chan->accountcode : "");
00396     
00397    /* End with empty return */
00398    fdprintf(fd, "\n");
00399 }

static int unload_module ( void   )  [static]

Definition at line 2137 of file res_agi.c.

References ast_cli_unregister_multiple(), ast_module_user_hangup_all, and ast_unregister_application().


Variable Documentation

int agidebug = 0 [static]

Definition at line 103 of file res_agi.c.

char* app = "AGI" [static]

Definition at line 74 of file res_agi.c.

struct ast_cli_entry cli_agi[] [static]

Definition at line 2119 of file res_agi.c.

struct ast_cli_entry cli_agi_no_debug_deprecated [static]

Initial value:

 {
   { "agi", "no", "debug", NULL },
   agi_no_debug_deprecated, NULL,
   NULL }

Definition at line 2114 of file res_agi.c.

struct ast_cli_entry cli_dump_agihtml_deprecated [static]

Initial value:

 {
   { "dump", "agihtml", NULL },
   handle_agidumphtml, NULL,
   NULL }

Definition at line 2109 of file res_agi.c.

struct ast_cli_entry cli_show_agi_deprecated [static]

Initial value:

 {
   { "show", "agi", NULL },
   handle_showagi, NULL,
   NULL }

Definition at line 2104 of file res_agi.c.

agi_command commands[MAX_COMMANDS] [static]

Definition at line 1603 of file res_agi.c.

Referenced by aji_dinfo_handler(), and dundi_showframe().

char* deadapp = "DeadAGI" [static]

Definition at line 78 of file res_agi.c.

char* deadsynopsis = "Executes AGI on a hungup channel" [static]

Definition at line 82 of file res_agi.c.

char debug_usage[] [static]

Initial value:

 
"Usage: agi debug\n"
"       Enables dumping of AGI transactions for debugging purposes\n"

Definition at line 1305 of file res_agi.c.

char* descrip [static]

Definition at line 84 of file res_agi.c.

char dumpagihtml_help[] [static]

Initial value:

"Usage: agi dumphtml <filename>\n"
"  Dumps the agi command list in html format to given filename\n"

Definition at line 2100 of file res_agi.c.

char* eapp = "EAGI" [static]

Definition at line 76 of file res_agi.c.

char* esynopsis = "Executes an EAGI compliant application" [static]

Definition at line 81 of file res_agi.c.

char no_debug_usage[] [static]

Initial value:

 
"Usage: agi debug off\n"
"       Disables dumping of AGI transactions for debugging purposes\n"

Definition at line 1309 of file res_agi.c.

char showagi_help[] [static]

Initial value:

"Usage: agi show [topic]\n"
"       When called with a topic as an argument, displays usage\n"
"       information on the given command.  If called without a\n"
"       topic, it provides a list of AGI commands.\n"

Definition at line 2093 of file res_agi.c.

char* synopsis = "Executes an AGI compliant application" [static]

Definition at line 80 of file res_agi.c.

char usage_answer[] [static]

Initial value:

 
" Usage: ANSWER\n"
"  Answers channel if not already in answer state. Returns -1 on\n"
" channel failure, or 0 if successful.\n"

Definition at line 1438 of file res_agi.c.

char usage_autohangup[] [static]

Initial value:

" Usage: SET AUTOHANGUP <time>\n"
"  Cause the channel to automatically hangup at <time> seconds in the\n"
" future.  Of course it can be hungup before then as well. Setting to 0 will\n"
" cause the autohangup feature to be disabled on this channel.\n"

Definition at line 1593 of file res_agi.c.

char usage_channelstatus[] [static]

Definition at line 1410 of file res_agi.c.

char usage_controlstreamfile[] [static]

Definition at line 1494 of file res_agi.c.

char usage_dbdel[] [static]

Initial value:

" Usage: DATABASE DEL <family> <key>\n"
"  Deletes an entry in the Asterisk database for a\n"
" given family and key.\n"
" Returns 1 if successful, 0 otherwise.\n"

Definition at line 1376 of file res_agi.c.

char usage_dbdeltree[] [static]

Initial value:

" Usage: DATABASE DELTREE <family> [keytree]\n"
"  Deletes a family or specific keytree within a family\n"
" in the Asterisk database.\n"
" Returns 1 if successful, 0 otherwise.\n"

Definition at line 1382 of file res_agi.c.

char usage_dbget[] [static]

Definition at line 1368 of file res_agi.c.

char usage_dbput[] [static]

Initial value:

" Usage: DATABASE PUT <family> <key> <value>\n"
"  Adds or updates an entry in the Asterisk database for a\n"
" given family, key, and value.\n"
" Returns 1 if successful, 0 otherwise.\n"

Definition at line 1362 of file res_agi.c.

char usage_exec[] [static]

Initial value:

" Usage: EXEC <application> <options>\n"
"  Executes <application> with given <options>.\n"
" Returns whatever the application returns, or -2 on failure to find application\n"

Definition at line 1428 of file res_agi.c.

char usage_getdata[] [static]

Initial value:

" Usage: GET DATA <file to be streamed> [timeout] [max digits]\n"
"  Stream the given file, and recieve DTMF data. Returns the digits received\n"
"from the channel at the other end.\n"

Definition at line 1563 of file res_agi.c.

char usage_getoption[] [static]

Initial value:

 
" Usage: GET OPTION <filename> <escape_digits> [timeout]\n"
"  Behaves similar to STREAM FILE but used with a timeout option.\n"

Definition at line 1504 of file res_agi.c.

char usage_getvariable[] [static]

Initial value:

" Usage: GET VARIABLE <variablename>\n"
"  Returns 0 if <variablename> is not set.  Returns 1 if <variablename>\n"
" is set and returns the variable in parentheses.\n"
" example return code: 200 result=1 (testvariable)\n"

Definition at line 1394 of file res_agi.c.

char usage_getvariablefull[] [static]

Definition at line 1400 of file res_agi.c.

char usage_hangup[] [static]

Initial value:

" Usage: HANGUP [<channelname>]\n"
"  Hangs up the specified channel.\n"
" If no channel name is given, hangs up the current channel\n"

Definition at line 1433 of file res_agi.c.

char usage_noop[] [static]

Initial value:

" Usage: NoOp\n"
"  Does nothing.\n"

Definition at line 1599 of file res_agi.c.

char usage_recordfile[] [static]

Definition at line 1581 of file res_agi.c.

char usage_recvchar[] [static]

Definition at line 1458 of file res_agi.c.

char usage_recvtext[] [static]

Initial value:

" Usage: RECEIVE TEXT <timeout>\n"
"  Receives a string of text on a channel. Specify timeout to be the\n"
" maximum time to wait for input in milliseconds, or 0 for infinite. Most channels\n"
" do not support the reception of text. Returns -1 for failure or 1 for success, and the string in parentheses.\n"

Definition at line 1466 of file res_agi.c.

char usage_sayalpha[] [static]

Definition at line 1522 of file res_agi.c.

char usage_saydate[] [static]

Definition at line 1529 of file res_agi.c.

char usage_saydatetime[] [static]

Definition at line 1545 of file res_agi.c.

char usage_saydigits[] [static]

Definition at line 1515 of file res_agi.c.

char usage_saynumber[] [static]

Definition at line 1508 of file res_agi.c.

char usage_sayphonetic[] [static]

Definition at line 1556 of file res_agi.c.

char usage_saytime[] [static]

Definition at line 1537 of file res_agi.c.

char usage_sendimage[] [static]

Definition at line 1477 of file res_agi.c.

char usage_sendtext[] [static]

Definition at line 1450 of file res_agi.c.

char usage_setcallerid[] [static]

Initial value:

" Usage: SET CALLERID <number>\n"
"  Changes the callerid of the current channel.\n"

Definition at line 1424 of file res_agi.c.

char usage_setcontext[] [static]

Initial value:

" Usage: SET CONTEXT <desired context>\n"
"  Sets the context for continuation upon exiting the application.\n"

Definition at line 1568 of file res_agi.c.

char usage_setextension[] [static]

Initial value:

" Usage: SET EXTENSION <new extension>\n"
"  Changes the extension for continuation upon exiting the application.\n"

Definition at line 1572 of file res_agi.c.

char usage_setmusic[] [static]

Initial value:

" Usage: SET MUSIC ON <on|off> <class>\n"
"  Enables/Disables the music on hold generator.  If <class> is\n"
" not specified, then the default music on hold class will be used.\n"
" Always returns 0.\n"

Definition at line 1356 of file res_agi.c.

char usage_setpriority[] [static]

Initial value:

" Usage: SET PRIORITY <priority>\n"
"  Changes the priority for continuation upon exiting the application.\n"
" The priority must be a valid priority or label.\n"

Definition at line 1576 of file res_agi.c.

char usage_setvariable[] [static]

Initial value:

" Usage: SET VARIABLE <variablename> <value>\n"

Definition at line 1407 of file res_agi.c.

char usage_streamfile[] [static]

Definition at line 1484 of file res_agi.c.

char usage_tddmode[] [static]

Initial value:

" Usage: TDD MODE <on|off>\n"
"  Enable/Disable TDD transmission/reception on a channel. Returns 1 if\n"
" successful, or 0 if channel is not TDD-capable.\n"

Definition at line 1472 of file res_agi.c.

char usage_verbose[] [static]

Initial value:

" Usage: VERBOSE <message> <level>\n"
"  Sends <message> to the console via verbose message system.\n"
" <level> is the the verbose level (1-4)\n"
" Always returns 1.\n"

Definition at line 1388 of file res_agi.c.

char usage_waitfordigit[] [static]

Definition at line 1443 of file res_agi.c.


Generated on Wed Aug 15 01:25:27 2007 for Asterisk - the Open Source PBX by  doxygen 1.5.3