Gentoo Websites Logo
Go to: Gentoo Home Documentation Forums Lists Bugs Planet Store Wiki Get Gentoo!
View | Details | Raw Unified | Return to bug 298328
Collapse All | Expand All

(-)asterisk-1.6.2.0-beta2/apps/app_nv_backgrounddetect.c (+325 lines)
Line 0 Link Here
1
/*
2
 * Asterisk -- A telephony toolkit for Linux.
3
 *
4
 * Playback a file with audio detect
5
 * 
6
 * Copyright (C) 2004-2005, Newman Telecom, Inc. and Newman Ventures, Inc.
7
 *
8
 * Justin Newman <jnewman@newmantelecom.com>
9
 *
10
 * We would like to thank Newman Ventures, Inc. for funding this
11
 * Asterisk project.
12
 *
13
 * Newman Ventures <info@newmanventures.com>
14
 *
15
 * Portions Copyright:
16
 * Copyright (C) 2001, Linux Support Services, Inc.
17
 * Copyright (C) 2004, Digium, Inc.
18
 *
19
 * Matthew Fredrickson <creslin@linux-support.net>
20
 * Mark Spencer <markster@digium.com>
21
 *
22
 * This program is free software, distributed under the terms of
23
 * the GNU General Public License
24
 */
25
 
26
#include "asterisk.h"
27
28
#include <asterisk/lock.h>
29
#include <asterisk/file.h>
30
#include <asterisk/logger.h>
31
#include <asterisk/channel.h>
32
#include <asterisk/pbx.h>
33
#include <asterisk/module.h>
34
#include <asterisk/translate.h>
35
#include <asterisk/utils.h>
36
#include <asterisk/dsp.h>
37
38
static char *app = "NVBackgroundDetect";
39
40
static char *synopsis = "Background a file with talk and fax detect (IAX and SIP too)";
41
42
static char *descrip = 
43
"  NVBackgroundDetect(filename[|options[|sildur[|mindur|[maxdur]]]]):\n"
44
"Plays filename, waiting for interruption from fax tones (on IAX and SIP too),\n"
45
"a digit, or non-silence. Audio is monitored in the receive direction. If\n"
46
"digits interrupt, they must be the start of a valid extension unless the\n"
47
"option is included to ignore. If fax is detected, it will jump to the\n"
48
"'fax' extension. If a period of non-silence is greater than 'mindur' ms,\n"
49
"yet less than 'maxdur' ms is followed by silence at least 'sildur' ms\n"
50
"then the app is aborted and processing jumps to the 'talk' extension.\n"
51
"If all undetected, control will continue at the next priority.\n"
52
"      options:\n"
53
"        'n':  Attempt on-hook if unanswered (default=no)\n"
54
"        'x':  DTMF digits terminate without extension (default=no)\n"
55
"        'd':  Ignore DTMF digit detection (default=no)\n"
56
"        'f':  Ignore fax detection (default=no)\n"
57
"        't':  Ignore talk detection (default=no)\n"
58
"      sildur:  Silence ms after mindur/maxdur before aborting (default=1000)\n"
59
"      mindur:  Minimum non-silence ms needed (default=100)\n"
60
"      maxdur:  Maximum non-silence ms allowed (default=0/forever)\n"
61
"Returns -1 on hangup, and 0 on successful completion with no exit conditions.\n\n"
62
"For questions or comments, please e-mail support@newmantelecom.com.\n";
63
64
// Use the second one for recent Asterisk releases
65
#define CALLERID_FIELD cid.cid_num
66
//#define CALLERID_FIELD callerid
67
68
static int nv_background_detect_exec(struct ast_channel *chan, void *data)
69
{
70
	int res = 0;
71
	char tmp[256] = "\0";
72
	char *p = NULL;
73
	char *filename = NULL;
74
	char *options = NULL;
75
	char *silstr = NULL;
76
	char *minstr = NULL;
77
	char *maxstr = NULL;
78
	struct ast_frame *fr = NULL;
79
	struct ast_frame *fr2 = NULL;
80
	int notsilent = 0;
81
	struct timeval start = {0, 0}, end = {0, 0};
82
	int sildur = 1000;
83
	int mindur = 100;
84
	int maxdur = -1;
85
	int skipanswer = 0;
86
	int noextneeded = 0;
87
	int ignoredtmf = 0;
88
	int ignorefax = 0;
89
	int ignoretalk = 0;
90
	int x = 0;
91
	int origrformat = 0;
92
	int features = 0;
93
	struct ast_dsp *dsp = NULL;
94
	
95
	pbx_builtin_setvar_helper(chan, "FAX_DETECTED", "");
96
	pbx_builtin_setvar_helper(chan, "FAXEXTEN", "");
97
	pbx_builtin_setvar_helper(chan, "DTMF_DETECTED", "");
98
	pbx_builtin_setvar_helper(chan, "TALK_DETECTED", "");
99
	
100
	if (!data || ast_strlen_zero((char *)data)) {
101
		ast_log(LOG_WARNING, "NVBackgroundDetect requires an argument (filename)\n");
102
		return -1;
103
	}	
104
	
105
	strncpy(tmp, (char *)data, sizeof(tmp)-1);
106
	p = tmp;
107
	
108
	filename = strsep(&p, "|");
109
	options = strsep(&p, "|");
110
	silstr = strsep(&p, "|");
111
	minstr = strsep(&p, "|");	
112
	maxstr = strsep(&p, "|");	
113
	
114
	if (options) {
115
		if (strchr(options, 'n'))
116
			skipanswer = 1;
117
		if (strchr(options, 'x'))
118
			noextneeded = 1;
119
		if (strchr(options, 'd'))
120
			ignoredtmf = 1;
121
		if (strchr(options, 'f'))
122
			ignorefax = 1;
123
		if (strchr(options, 't'))
124
			ignoretalk = 1;
125
	}
126
	
127
	if (silstr) {
128
		if ((sscanf(silstr, "%d", &x) == 1) && (x > 0))
129
			sildur = x;
130
	}
131
	
132
	if (minstr) {
133
		if ((sscanf(minstr, "%d", &x) == 1) && (x > 0))
134
			mindur = x;
135
	}
136
	
137
	if (maxstr) {
138
		if ((sscanf(maxstr, "%d", &x) == 1) && (x > 0))
139
			maxdur = x;
140
	}
141
	
142
	ast_log(LOG_DEBUG, "Preparing detect of '%s' (sildur=%dms, mindur=%dms, maxdur=%dms)\n", 
143
						tmp, sildur, mindur, maxdur);
144
						
145
	//	LOCAL_USER_ADD(u);
146
	if (chan->_state != AST_STATE_UP && !skipanswer) {
147
		/* Otherwise answer unless we're supposed to send this while on-hook */
148
		res = ast_answer(chan);
149
	}
150
	if (!res) {
151
		origrformat = chan->readformat;
152
		if ((res = ast_set_read_format(chan, AST_FORMAT_SLINEAR))) 
153
			ast_log(LOG_WARNING, "Unable to set read format to linear!\n");
154
	}
155
	if (!(dsp = ast_dsp_new())) {
156
		ast_log(LOG_WARNING, "Unable to allocate DSP!\n");
157
		res = -1;
158
	}
159
160
	if (dsp) {	
161
		if (!ignoretalk)
162
			; /* features |= DSP_FEATURE_SILENCE_SUPPRESS; */
163
		if (!ignorefax)
164
			features |= DSP_FEATURE_FAX_DETECT;
165
		//if (!ignoredtmf)
166
			features |= DSP_FEATURE_DIGIT_DETECT;
167
			
168
		ast_dsp_set_threshold(dsp, 256);
169
		ast_dsp_set_features(dsp, features | DSP_DIGITMODE_RELAXDTMF);
170
		ast_dsp_set_digitmode(dsp, DSP_DIGITMODE_DTMF);
171
	}
172
	
173
	if (!res) {
174
		ast_stopstream(chan);
175
		res = ast_streamfile(chan, tmp, chan->language);
176
		if (!res) {
177
			while(chan->stream) {
178
				res = ast_sched_wait(chan->sched);
179
				if ((res < 0) && !chan->timingfunc) {
180
					res = 0;
181
					break;
182
				}
183
				if (res < 0)
184
					res = 1000;
185
				res = ast_waitfor(chan, res);
186
				if (res < 0) {
187
					ast_log(LOG_WARNING, "Waitfor failed on %s\n", chan->name);
188
					break;
189
				} else if (res > 0) {
190
					fr = ast_read(chan);
191
					if (!fr) {
192
						ast_log(LOG_DEBUG, "Got hangup\n");
193
						res = -1;
194
						break;
195
					}
196
					
197
					fr2 = ast_dsp_process(chan, dsp, fr);
198
					if (!fr2) {
199
						ast_log(LOG_WARNING, "Bad DSP received (what happened!!)\n");
200
						fr2 = fr;
201
					} 
202
					
203
					if (fr2->frametype == AST_FRAME_DTMF) {
204
						if (fr2->subclass == 'f' && !ignorefax) {
205
							/* Fax tone -- Handle and return NULL */
206
							ast_log(LOG_DEBUG, "Fax detected on %s\n", chan->name);
207
							if (strcmp(chan->exten, "fax")) {
208
								ast_log(LOG_NOTICE, "Redirecting %s to fax extension\n", chan->name);
209
								pbx_builtin_setvar_helper(chan, "FAX_DETECTED", "1");
210
								pbx_builtin_setvar_helper(chan,"FAXEXTEN",chan->exten);								
211
								if (ast_exists_extension(chan, chan->context, "fax", 1, chan->CALLERID_FIELD)) {
212
									/* Save the DID/DNIS when we transfer the fax call to a "fax" extension */
213
									strncpy(chan->exten, "fax", sizeof(chan->exten)-1);
214
									chan->priority = 0;									
215
								} else
216
									ast_log(LOG_WARNING, "Fax detected, but no fax extension\n");
217
							} else
218
								ast_log(LOG_WARNING, "Already in a fax extension, not redirecting\n");
219
220
							res = 0;
221
							ast_frfree(fr);
222
							break;
223
						} else if (!ignoredtmf) {
224
							ast_log(LOG_DEBUG, "DTMF detected on %s\n", chan->name);
225
							char t[2];
226
							t[0] = fr2->subclass;
227
							t[1] = '\0';
228
							if (noextneeded || ast_canmatch_extension(chan, chan->context, t, 1, chan->CALLERID_FIELD)) {
229
								pbx_builtin_setvar_helper(chan, "DTMF_DETECTED", "1");
230
								/* They entered a valid extension, or might be anyhow */
231
								if (noextneeded) {
232
									ast_log(LOG_NOTICE, "DTMF received (not matching to exten)\n");
233
									res = 0;
234
								} else {
235
									ast_log(LOG_NOTICE, "DTMF received (matching to exten)\n");
236
									res = fr2->subclass;
237
								}
238
								ast_frfree(fr);
239
								break;
240
							} else
241
								ast_log(LOG_DEBUG, "Valid extension requested and DTMF did not match\n");
242
						}
243
					} else if ((fr->frametype == AST_FRAME_VOICE) && (fr->subclass == AST_FORMAT_SLINEAR) && !ignoretalk) {
244
						int totalsilence;
245
						int ms;
246
						res = ast_dsp_silence(dsp, fr, &totalsilence);
247
						if (res && (totalsilence > sildur)) {
248
							/* We've been quiet a little while */
249
							if (notsilent) {
250
								/* We had heard some talking */
251
								gettimeofday(&end, NULL);
252
								ms = (end.tv_sec - start.tv_sec) * 1000;
253
								ms += (end.tv_usec - start.tv_usec) / 1000;
254
								ms -= sildur;
255
								if (ms < 0)
256
									ms = 0;
257
								if ((ms > mindur) && ((maxdur < 0) || (ms < maxdur))) {
258
									char ms_str[10];
259
									ast_log(LOG_DEBUG, "Found qualified token of %d ms\n", ms);
260
									ast_log(LOG_NOTICE, "Redirecting %s to talk extension\n", chan->name);
261
262
									/* Save detected talk time (in milliseconds) */ 
263
									sprintf(ms_str, "%d", ms);	
264
									pbx_builtin_setvar_helper(chan, "TALK_DETECTED", ms_str);
265
									
266
									if (ast_exists_extension(chan, chan->context, "talk", 1, chan->CALLERID_FIELD)) {
267
										strncpy(chan->exten, "talk", sizeof(chan->exten) - 1);
268
										chan->priority = 0;
269
									} else
270
										ast_log(LOG_WARNING, "Talk detected, but no talk extension\n");
271
									res = 0;
272
									ast_frfree(fr);
273
									break;
274
								} else
275
									ast_log(LOG_DEBUG, "Found unqualified token of %d ms\n", ms);
276
								notsilent = 0;
277
							}
278
						} else {
279
							if (!notsilent) {
280
								/* Heard some audio, mark the begining of the token */
281
								gettimeofday(&start, NULL);
282
								ast_log(LOG_DEBUG, "Start of voice token!\n");
283
								notsilent = 1;
284
							}
285
						}						
286
					}
287
					ast_frfree(fr);
288
				}
289
				ast_sched_runq(chan->sched);
290
			}
291
			ast_stopstream(chan);
292
		} else {
293
			ast_log(LOG_WARNING, "ast_streamfile failed on %s for %s\n", chan->name, (char *)data);
294
			res = 0;
295
		}
296
	} else
297
		ast_log(LOG_WARNING, "Could not answer channel '%s'\n", chan->name);
298
	
299
	if (res > -1) {
300
		if (origrformat && ast_set_read_format(chan, origrformat)) {
301
			ast_log(LOG_WARNING, "Failed to restore read format for %s to %s\n", 
302
				chan->name, ast_getformatname(origrformat));
303
		}
304
	}
305
	
306
	if (dsp)
307
		ast_dsp_free(dsp);
308
	
309
	//	LOCAL_USER_REMOVE(u);
310
	
311
	return res;
312
}
313
314
static int unload_module(void)
315
{
316
  //	STANDARD_HANGUP_LOCALUSERS;
317
	return ast_unregister_application(app);
318
}
319
320
static int load_module(void)
321
{
322
	return ast_register_application(app, nv_background_detect_exec, synopsis, descrip);
323
}
324
325
AST_MODULE_INFO_STANDARD(ASTERISK_GPL_KEY, "Fax playing Background Music Detection Application");
(-)asterisk-1.6.2.0-beta2/apps/app_nv_faxdetect.c (+317 lines)
Line 0 Link Here
1
/*
2
 * Asterisk -- A telephony toolkit for Linux.
3
 *
4
 * Fax detection application for all channel types.
5
 * 
6
 * Copyright (C) 2004-2005, Newman Telecom, Inc. and Newman Ventures, Inc.
7
 *
8
 * Justin Newman <jnewman@newmantelecom.com>
9
 *
10
 * We would like to thank Newman Ventures, Inc. for funding this
11
 * Asterisk project.
12
 *
13
 * Newman Ventures <info@newmanventures.com>
14
 *
15
 * Portions Copyright:
16
 * Copyright (C) 2001, Linux Support Services, Inc.
17
 * Copyright (C) 2004, Digium, Inc.
18
 *
19
 * Matthew Fredrickson <creslin@linux-support.net>
20
 * Mark Spencer <markster@digium.com>
21
 *
22
 * This program is free software, distributed under the terms of
23
 * the GNU General Public License
24
 */
25
 
26
#include "asterisk.h"
27
28
#include <asterisk/lock.h>
29
#include <asterisk/file.h>
30
#include <asterisk/logger.h>
31
#include <asterisk/channel.h>
32
#include <asterisk/pbx.h>
33
#include <asterisk/module.h>
34
#include <asterisk/translate.h>
35
#include <asterisk/dsp.h>
36
#include <asterisk/utils.h>
37
38
static char *app = "NVFaxDetect";
39
40
static char *synopsis = "Detects fax sounds on all channel types (IAX and SIP too)";
41
42
static char *descrip = 
43
"  NVFaxDetect([waitdur[|options[|sildur[|mindur[|maxdur]]]]]):\n"
44
"This application listens for fax tones (on IAX and SIP channels too)\n"
45
"for waitdur seconds of time. In addition, it can be interrupted by digits,\n"
46
"or non-silence. Audio is only monitored in the receive direction. If\n"
47
"digits interrupt, they must be the start of a valid extension unless the\n"
48
"option is included to ignore. If fax is detected, it will jump to the\n"
49
"'fax' extension. If a period of non-silence greater than 'mindur' ms,\n"
50
"yet less than 'maxdur' ms is followed by silence at least 'sildur' ms\n"
51
"then the app is aborted and processing jumps to the 'talk' extension.\n"
52
"If all undetected, control will continue at the next priority.\n"
53
"      waitdur:  Maximum number of seconds to wait (default=4)\n"
54
"      options:\n"
55
"        'n':  Attempt on-hook if unanswered (default=no)\n"
56
"        'x':  DTMF digits terminate without extension (default=no)\n"
57
"        'd':  Ignore DTMF digit detection (default=no)\n"
58
"        'f':  Ignore fax detection (default=no)\n"
59
"        't':  Ignore talk detection (default=no)\n"
60
"      sildur:  Silence ms after mindur/maxdur before aborting (default=1000)\n"
61
"      mindur:  Minimum non-silence ms needed (default=100)\n"
62
"      maxdur:  Maximum non-silence ms allowed (default=0/forever)\n"
63
"Returns -1 on hangup, and 0 on successful completion with no exit conditions.\n\n"
64
"For questions or comments, please e-mail support@newmantelecom.com.\n";
65
66
// Use the second one for recent Asterisk releases
67
#define CALLERID_FIELD cid.cid_num
68
//#define CALLERID_FIELD callerid
69
70
static int nv_detectfax_exec(struct ast_channel *chan, void *data)
71
{
72
	int res = 0;
73
	char tmp[256] = "\0";
74
	char *p = NULL;
75
	char *waitstr = NULL;
76
	char *options = NULL;
77
	char *silstr = NULL;
78
	char *minstr = NULL;
79
	char *maxstr = NULL;
80
	struct ast_frame *fr = NULL;
81
	struct ast_frame *fr2 = NULL;
82
	int notsilent = 0;
83
	struct timeval start = {0, 0}, end = {0, 0};
84
	int waitdur = 4;
85
	int sildur = 1000;
86
	int mindur = 100;
87
	int maxdur = -1;
88
	int skipanswer = 0;
89
	int noextneeded = 0;
90
	int ignoredtmf = 0;
91
	int ignorefax = 0;
92
	int ignoretalk = 0;
93
	int x = 0;
94
	int origrformat = 0;
95
	int features = 0;
96
	time_t timeout = 0;
97
	struct ast_dsp *dsp = NULL;
98
	
99
	pbx_builtin_setvar_helper(chan, "FAX_DETECTED", "");
100
	pbx_builtin_setvar_helper(chan, "FAXEXTEN", "");
101
	pbx_builtin_setvar_helper(chan, "DTMF_DETECTED", "");
102
	pbx_builtin_setvar_helper(chan, "TALK_DETECTED", "");
103
	
104
	if (data || !ast_strlen_zero((char *)data)) {
105
		strncpy(tmp, (char *)data, sizeof(tmp)-1);
106
	}	
107
	
108
	p = tmp;
109
	
110
	waitstr = strsep(&p, "|");
111
	options = strsep(&p, "|");
112
	silstr = strsep(&p, "|");
113
	minstr = strsep(&p, "|");	
114
	maxstr = strsep(&p, "|");	
115
	
116
	if (waitstr) {
117
		if ((sscanf(waitstr, "%d", &x) == 1) && (x > 0))
118
			waitdur = x;
119
	}
120
	
121
	if (options) {
122
		if (strchr(options, 'n'))
123
			skipanswer = 1;
124
		if (strchr(options, 'x'))
125
			noextneeded = 1;
126
		if (strchr(options, 'd'))
127
			ignoredtmf = 1;
128
		if (strchr(options, 'f'))
129
			ignorefax = 1;
130
		if (strchr(options, 't'))
131
			ignoretalk = 1;
132
	}
133
	
134
	if (silstr) {
135
		if ((sscanf(silstr, "%d", &x) == 1) && (x > 0))
136
			sildur = x;
137
	}
138
	
139
	if (minstr) {
140
		if ((sscanf(minstr, "%d", &x) == 1) && (x > 0))
141
			mindur = x;
142
	}
143
	
144
	if (maxstr) {
145
		if ((sscanf(maxstr, "%d", &x) == 1) && (x > 0))
146
			maxdur = x;
147
	}
148
	
149
	ast_log(LOG_DEBUG, "Preparing detect of fax (waitdur=%dms, sildur=%dms, mindur=%dms, maxdur=%dms)\n", 
150
						waitdur, sildur, mindur, maxdur);
151
						
152
	//	LOCAL_USER_ADD(u);
153
	if (chan->_state != AST_STATE_UP && !skipanswer) {
154
		/* Otherwise answer unless we're supposed to send this while on-hook */
155
		res = ast_answer(chan);
156
	}
157
	if (!res) {
158
		origrformat = chan->readformat;
159
		if ((res = ast_set_read_format(chan, AST_FORMAT_SLINEAR))) 
160
			ast_log(LOG_WARNING, "Unable to set read format to linear!\n");
161
	}
162
	if (!(dsp = ast_dsp_new())) {
163
		ast_log(LOG_WARNING, "Unable to allocate DSP!\n");
164
		res = -1;
165
	}
166
	
167
	if (dsp) {	
168
		if (!ignoretalk)
169
			; /* features |= DSP_FEATURE_SILENCE_SUPPRESS; */
170
		if (!ignorefax)
171
			features |= DSP_FEATURE_FAX_DETECT;
172
		//if (!ignoredtmf)
173
			features |= DSP_FEATURE_DIGIT_DETECT;
174
			
175
		ast_dsp_set_threshold(dsp, 256); 
176
		ast_dsp_set_features(dsp, features | DSP_DIGITMODE_RELAXDTMF);
177
		ast_dsp_set_digitmode(dsp, DSP_DIGITMODE_DTMF);
178
	}
179
180
	if (!res) {
181
		if (waitdur > 0)
182
			timeout = time(NULL) + (time_t)waitdur;
183
184
		while(ast_waitfor(chan, -1) > -1) {
185
			if (waitdur > 0 && time(NULL) > timeout) {
186
				res = 0;
187
				break;
188
			}
189
190
			fr = ast_read(chan);
191
			if (!fr) {
192
				ast_log(LOG_DEBUG, "Got hangup\n");
193
				res = -1;
194
				break;
195
			}
196
197
			fr2 = ast_dsp_process(chan, dsp, fr);
198
			if (!fr2) {
199
				ast_log(LOG_WARNING, "Bad DSP received (what happened?)\n");
200
				fr2 = fr;
201
			} 
202
203
			if (fr2->frametype == AST_FRAME_DTMF) {
204
				if (fr2->subclass == 'f' && !ignorefax) {
205
					/* Fax tone -- Handle and return NULL */
206
					ast_log(LOG_DEBUG, "Fax detected on %s\n", chan->name);
207
					if (strcmp(chan->exten, "fax")) {
208
						ast_log(LOG_NOTICE, "Redirecting %s to fax extension\n", chan->name);
209
						pbx_builtin_setvar_helper(chan, "FAX_DETECTED", "1");
210
						pbx_builtin_setvar_helper(chan,"FAXEXTEN",chan->exten);								
211
						if (ast_exists_extension(chan, chan->context, "fax", 1, chan->CALLERID_FIELD)) {
212
							/* Save the DID/DNIS when we transfer the fax call to a "fax" extension */
213
							strncpy(chan->exten, "fax", sizeof(chan->exten)-1);
214
							chan->priority = 0;									
215
						} else
216
							ast_log(LOG_WARNING, "Fax detected, but no fax extension\n");
217
					} else
218
						ast_log(LOG_WARNING, "Already in a fax extension, not redirecting\n");
219
220
					res = 0;
221
					ast_frfree(fr);
222
					break;
223
				} else if (!ignoredtmf) {
224
					ast_log(LOG_DEBUG, "DTMF detected on %s\n", chan->name);
225
					char t[2];
226
					t[0] = fr2->subclass;
227
					t[1] = '\0';
228
					if (noextneeded || ast_canmatch_extension(chan, chan->context, t, 1, chan->CALLERID_FIELD)) {
229
						pbx_builtin_setvar_helper(chan, "DTMF_DETECTED", "1");
230
						/* They entered a valid extension, or might be anyhow */
231
						if (noextneeded) {
232
							ast_log(LOG_NOTICE, "DTMF received (not matching to exten)\n");
233
							res = 0;
234
						} else {
235
							ast_log(LOG_NOTICE, "DTMF received (matching to exten)\n");
236
							res = fr2->subclass;
237
						}
238
						ast_frfree(fr);
239
						break;
240
					} else
241
						ast_log(LOG_DEBUG, "Valid extension requested and DTMF did not match\n");
242
				}
243
			} else if ((fr->frametype == AST_FRAME_VOICE) && (fr->subclass == AST_FORMAT_SLINEAR) && !ignoretalk) {
244
				int totalsilence;
245
				int ms;
246
				res = ast_dsp_silence(dsp, fr, &totalsilence);
247
				if (res && (totalsilence > sildur)) {
248
					/* We've been quiet a little while */
249
					if (notsilent) {
250
						/* We had heard some talking */
251
						gettimeofday(&end, NULL);
252
						ms = (end.tv_sec - start.tv_sec) * 1000;
253
						ms += (end.tv_usec - start.tv_usec) / 1000;
254
						ms -= sildur;
255
						if (ms < 0)
256
							ms = 0;
257
						if ((ms > mindur) && ((maxdur < 0) || (ms < maxdur))) {
258
							char ms_str[10];
259
							ast_log(LOG_DEBUG, "Found qualified token of %d ms\n", ms);
260
							ast_log(LOG_NOTICE, "Redirecting %s to talk extension\n", chan->name);
261
262
							/* Save detected talk time (in milliseconds) */ 
263
							sprintf(ms_str, "%d", ms);	
264
							pbx_builtin_setvar_helper(chan, "TALK_DETECTED", ms_str);
265
266
							if (ast_exists_extension(chan, chan->context, "talk", 1, chan->CALLERID_FIELD)) {
267
								strncpy(chan->exten, "talk", sizeof(chan->exten) - 1);
268
								chan->priority = 0;
269
							} else
270
								ast_log(LOG_WARNING, "Talk detected, but no talk extension\n");
271
							res = 0;
272
							ast_frfree(fr);
273
							break;
274
						} else
275
							ast_log(LOG_DEBUG, "Found unqualified token of %d ms\n", ms);
276
						notsilent = 0;
277
					}
278
				} else {
279
					if (!notsilent) {
280
						/* Heard some audio, mark the begining of the token */
281
						gettimeofday(&start, NULL);
282
						ast_log(LOG_DEBUG, "Start of voice token!\n");
283
						notsilent = 1;
284
					}
285
				}						
286
			}
287
			ast_frfree(fr);
288
		}
289
	} else
290
		ast_log(LOG_WARNING, "Could not answer channel '%s'\n", chan->name);
291
	
292
	if (res > -1) {
293
		if (origrformat && ast_set_read_format(chan, origrformat)) {
294
			ast_log(LOG_WARNING, "Failed to restore read format for %s to %s\n", 
295
				chan->name, ast_getformatname(origrformat));
296
		}
297
	}
298
	
299
	if (dsp)
300
		ast_dsp_free(dsp);
301
	
302
	//	LOCAL_USER_REMOVE(u);
303
	
304
	return res;
305
}
306
307
static int unload_module(void)
308
{
309
  return ast_unregister_application(app);
310
}
311
312
static int load_module(void)
313
{
314
  return ast_register_application(app, nv_detectfax_exec, synopsis, descrip);
315
}
316
317
AST_MODULE_INFO_STANDARD(ASTERISK_GPL_KEY, "Fax Detection Application");

Return to bug 298328