Tue Nov 4 13:20:26 2008

Asterisk developer's documentation


app_waitforsilence.c File Reference

Wait for Silence More...

#include "asterisk.h"
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <unistd.h>
#include "asterisk/file.h"
#include "asterisk/logger.h"
#include "asterisk/channel.h"
#include "asterisk/pbx.h"
#include "asterisk/dsp.h"
#include "asterisk/module.h"
#include "asterisk/options.h"

Go to the source code of this file.

Functions

 AST_MODULE_INFO_STANDARD (ASTERISK_GPL_KEY,"Wait For Silence")
static int do_waiting (struct ast_channel *chan, int silencereqd, time_t waitstart, int timeout)
static int load_module (void)
static int unload_module (void)
static int waitforsilence_exec (struct ast_channel *chan, void *data)

Variables

static char * app = "WaitForSilence"
static char * descrip
static char * synopsis = "Waits for a specified amount of silence"


Detailed Description

Wait for Silence

Author:
David C. Troy <dave@popvox.com>

Definition in file app_waitforsilence.c.


Function Documentation

AST_MODULE_INFO_STANDARD ( ASTERISK_GPL_KEY  ,
"Wait For Silence"   
)

static int do_waiting ( struct ast_channel chan,
int  silencereqd,
time_t  waitstart,
int  timeout 
) [static]

Definition at line 78 of file app_waitforsilence.c.

References ast_dsp_free(), ast_dsp_new(), ast_dsp_set_threshold(), ast_dsp_silence(), AST_FORMAT_SLINEAR, AST_FRAME_VOICE, ast_frfree, ast_getformatname(), ast_log(), ast_read(), ast_set_read_format(), ast_verbose(), ast_waitfor(), f, LOG_DEBUG, LOG_WARNING, option_verbose, pbx_builtin_setvar_helper(), ast_channel::readformat, silencethreshold, and VERBOSE_PREFIX_3.

Referenced by waitforsilence_exec().

00078                                                                                                 {
00079    struct ast_frame *f;
00080    int dspsilence = 0;
00081    static int silencethreshold = 128;
00082    int rfmt = 0;
00083    int res = 0;
00084    struct ast_dsp *sildet;  /* silence detector dsp */
00085    time_t now;
00086 
00087    rfmt = chan->readformat; /* Set to linear mode */
00088    res = ast_set_read_format(chan, AST_FORMAT_SLINEAR);
00089    if (res < 0) {
00090       ast_log(LOG_WARNING, "Unable to set channel to linear mode, giving up\n");
00091       return -1;
00092    }
00093 
00094    sildet = ast_dsp_new(); /* Create the silence detector */
00095    if (!sildet) {
00096       ast_log(LOG_WARNING, "Unable to create silence detector :(\n");
00097       return -1;
00098    }
00099    ast_dsp_set_threshold(sildet, silencethreshold);
00100 
00101    /* Await silence... */
00102    f = NULL;
00103    for(;;) {
00104       /* Start with no silence received */
00105       dspsilence = 0;
00106 
00107       res = ast_waitfor(chan, silencereqd);
00108 
00109       /* Must have gotten a hangup; let's exit */
00110       if (res <= 0) {
00111          f = NULL;
00112          break;
00113       }
00114       
00115       /* We waited and got no frame; sounds like digital silence or a muted digital channel */
00116       if (!res) {
00117          dspsilence = silencereqd;
00118       } else {
00119          /* Looks like we did get a frame, so let's check it out */
00120          f = ast_read(chan);
00121          if (!f)
00122             break;
00123          if (f && f->frametype == AST_FRAME_VOICE) {
00124             ast_dsp_silence(sildet, f, &dspsilence);
00125             ast_frfree(f);
00126          }
00127       }
00128 
00129       if (option_verbose > 6)
00130          ast_verbose(VERBOSE_PREFIX_3 "Got %dms silence< %dms required\n", dspsilence, silencereqd);
00131 
00132       if (dspsilence >= silencereqd) {
00133          if (option_verbose > 2)
00134             ast_verbose(VERBOSE_PREFIX_3 "Exiting with %dms silence >= %dms required\n", dspsilence, silencereqd);
00135          /* Ended happily with silence */
00136          res = 1;
00137          pbx_builtin_setvar_helper(chan, "WAITSTATUS", "SILENCE");
00138          ast_log(LOG_DEBUG, "WAITSTATUS was set to SILENCE\n");
00139          break;
00140       }
00141 
00142       if ( timeout && (difftime(time(&now),waitstart) >= timeout) ) {
00143          pbx_builtin_setvar_helper(chan, "WAITSTATUS", "TIMEOUT");
00144          ast_log(LOG_DEBUG, "WAITSTATUS was set to TIMEOUT\n");
00145          res = 0;
00146          break;
00147       }
00148    }
00149 
00150 
00151    if (rfmt && ast_set_read_format(chan, rfmt)) {
00152       ast_log(LOG_WARNING, "Unable to restore format %s to channel '%s'\n", ast_getformatname(rfmt), chan->name);
00153    }
00154    ast_dsp_free(sildet);
00155    return res;
00156 }

static int load_module ( void   )  [static]

Definition at line 199 of file app_waitforsilence.c.

References ast_register_application(), and waitforsilence_exec().

static int unload_module ( void   )  [static]

Definition at line 188 of file app_waitforsilence.c.

References ast_module_user_hangup_all, and ast_unregister_application().

00189 {
00190    int res;
00191 
00192    res = ast_unregister_application(app);
00193    
00194    ast_module_user_hangup_all();
00195 
00196    return res;
00197 }

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

Definition at line 158 of file app_waitforsilence.c.

References ast_answer(), ast_log(), ast_verbose(), do_waiting(), LOG_WARNING, option_verbose, and VERBOSE_PREFIX_3.

Referenced by load_module().

00159 {
00160    int res = 1;
00161    int silencereqd = 1000;
00162    int timeout = 0;
00163    int iterations = 1, i;
00164    time_t waitstart;
00165 
00166    res = ast_answer(chan); /* Answer the channel */
00167 
00168    if (!data || ( (sscanf(data, "%d|%d|%d", &silencereqd, &iterations, &timeout) != 3) &&
00169       (sscanf(data, "%d|%d", &silencereqd, &iterations) != 2) &&
00170       (sscanf(data, "%d", &silencereqd) != 1) ) ) {
00171       ast_log(LOG_WARNING, "Using default value of 1000ms, 1 iteration, no timeout\n");
00172    }
00173 
00174    if (option_verbose > 2)
00175       ast_verbose(VERBOSE_PREFIX_3 "Waiting %d time(s) for %d ms silence with %d timeout\n", iterations, silencereqd, timeout);
00176 
00177    time(&waitstart);
00178    res = 1;
00179    for (i=0; (i<iterations) && (res == 1); i++) {
00180       res = do_waiting(chan, silencereqd, waitstart, timeout);
00181    }
00182    if (res > 0)
00183       res = 0;
00184    return res;
00185 }


Variable Documentation

char* app = "WaitForSilence" [static]

Definition at line 52 of file app_waitforsilence.c.

char* descrip [static]

Definition at line 54 of file app_waitforsilence.c.

char* synopsis = "Waits for a specified amount of silence" [static]

Definition at line 53 of file app_waitforsilence.c.


Generated on Tue Nov 4 13:20:26 2008 for Asterisk - the Open Source PBX by  doxygen 1.4.7