Fix a few things I missed to ensure zt_chan_conf structure is not modified in mkintf
[asterisk-bristuff.git] / apps / app_test.c
blobb38fe4ca76394ec2aa33c9c10b4f4efc8da4575c
1 /*
2 * Asterisk -- An open source telephony toolkit.
4 * Copyright (C) 1999 - 2005, Digium, Inc.
6 * Mark Spencer <markster@digium.com>
7 * Russell Bryant <russelb@clemson.edu>
9 * See http://www.asterisk.org for more information about
10 * the Asterisk project. Please do not directly contact
11 * any of the maintainers of this project for assistance;
12 * the project provides a web site, mailing lists and IRC
13 * channels for your use.
15 * This program is free software, distributed under the terms of
16 * the GNU General Public License Version 2. See the LICENSE file
17 * at the top of the source tree.
20 /*! \file
22 * \brief Applications to test connection and produce report in text file
24 * \author Mark Spencer <markster@digium.com>
25 * \author Russell Bryant <russelb@clemson.edu>
27 * \ingroup applications
30 #include "asterisk.h"
32 ASTERISK_FILE_VERSION(__FILE__, "$Revision$")
34 #include <stdlib.h>
35 #include <stdio.h>
36 #include <string.h>
37 #include <unistd.h>
38 #include <fcntl.h>
39 #include <sys/types.h>
40 #include <sys/stat.h>
42 #include "asterisk/channel.h"
43 #include "asterisk/options.h"
44 #include "asterisk/module.h"
45 #include "asterisk/logger.h"
46 #include "asterisk/lock.h"
47 #include "asterisk/app.h"
48 #include "asterisk/pbx.h"
49 #include "asterisk/utils.h"
51 static char *tests_descrip =
52 "TestServer(): Perform test server function and write call report.\n"
53 "Results stored in /var/log/asterisk/testreports/<testid>-server.txt";
54 static char *tests_app = "TestServer";
55 static char *tests_synopsis = "Execute Interface Test Server";
57 static char *testc_descrip =
58 "TestClient(testid): Executes test client with given testid.\n"
59 "Results stored in /var/log/asterisk/testreports/<testid>-client.txt";
61 static char *testc_app = "TestClient";
62 static char *testc_synopsis = "Execute Interface Test Client";
64 static int measurenoise(struct ast_channel *chan, int ms, char *who)
66 int res=0;
67 int mssofar;
68 int noise=0;
69 int samples=0;
70 int x;
71 short *foo;
72 struct timeval start;
73 struct ast_frame *f;
74 int rformat;
75 rformat = chan->readformat;
76 if (ast_set_read_format(chan, AST_FORMAT_SLINEAR)) {
77 ast_log(LOG_NOTICE, "Unable to set to linear mode!\n");
78 return -1;
80 start = ast_tvnow();
81 for(;;) {
82 mssofar = ast_tvdiff_ms(ast_tvnow(), start);
83 if (mssofar > ms)
84 break;
85 res = ast_waitfor(chan, ms - mssofar);
86 if (res < 1)
87 break;
88 f = ast_read(chan);
89 if (!f) {
90 res = -1;
91 break;
93 if ((f->frametype == AST_FRAME_VOICE) && (f->subclass == AST_FORMAT_SLINEAR)) {
94 foo = (short *)f->data;
95 for (x=0;x<f->samples;x++) {
96 noise += abs(foo[x]);
97 samples++;
100 ast_frfree(f);
103 if (rformat) {
104 if (ast_set_read_format(chan, rformat)) {
105 ast_log(LOG_NOTICE, "Unable to restore original format!\n");
106 return -1;
109 if (res < 0)
110 return res;
111 if (!samples) {
112 ast_log(LOG_NOTICE, "No samples were received from the other side!\n");
113 return -1;
115 ast_log(LOG_DEBUG, "%s: Noise: %d, samples: %d, avg: %d\n", who, noise, samples, noise / samples);
116 return (noise / samples);
119 static int sendnoise(struct ast_channel *chan, int ms)
121 int res;
122 res = ast_tonepair_start(chan, 1537, 2195, ms, 8192);
123 if (!res) {
124 res = ast_waitfordigit(chan, ms);
125 ast_tonepair_stop(chan);
127 return res;
130 static int testclient_exec(struct ast_channel *chan, void *data)
132 struct ast_module_user *u;
133 int res = 0;
134 char *testid=data;
135 char fn[80];
136 char serverver[80];
137 FILE *f;
139 /* Check for test id */
140 if (ast_strlen_zero(testid)) {
141 ast_log(LOG_WARNING, "TestClient requires an argument - the test id\n");
142 return -1;
145 u = ast_module_user_add(chan);
147 if (chan->_state != AST_STATE_UP)
148 res = ast_answer(chan);
150 /* Wait a few just to be sure things get started */
151 res = ast_safe_sleep(chan, 3000);
152 /* Transmit client version */
153 if (!res)
154 res = ast_dtmf_stream(chan, NULL, "8378*1#", 0);
155 if (option_debug)
156 ast_log(LOG_DEBUG, "Transmit client version\n");
158 /* Read server version */
159 if (option_debug)
160 ast_log(LOG_DEBUG, "Read server version\n");
161 if (!res)
162 res = ast_app_getdata(chan, NULL, serverver, sizeof(serverver) - 1, 0);
163 if (res > 0)
164 res = 0;
165 if (option_debug)
166 ast_log(LOG_DEBUG, "server version: %s\n", serverver);
168 if (res > 0)
169 res = 0;
171 if (!res)
172 res = ast_safe_sleep(chan, 1000);
173 /* Send test id */
174 if (!res)
175 res = ast_dtmf_stream(chan, NULL, testid, 0);
176 if (!res)
177 res = ast_dtmf_stream(chan, NULL, "#", 0);
178 if (option_debug)
179 ast_log(LOG_DEBUG, "send test identifier: %s\n", testid);
181 if ((res >=0) && (!ast_strlen_zero(testid))) {
182 /* Make the directory to hold the test results in case it's not there */
183 snprintf(fn, sizeof(fn), "%s/testresults", ast_config_AST_LOG_DIR);
184 mkdir(fn, 0777);
185 snprintf(fn, sizeof(fn), "%s/testresults/%s-client.txt", ast_config_AST_LOG_DIR, testid);
186 if ((f = fopen(fn, "w+"))) {
187 setlinebuf(f);
188 fprintf(f, "CLIENTCHAN: %s\n", chan->name);
189 fprintf(f, "CLIENTTEST ID: %s\n", testid);
190 fprintf(f, "ANSWER: PASS\n");
191 res = 0;
193 if (!res) {
194 /* Step 1: Wait for "1" */
195 if (option_debug)
196 ast_log(LOG_DEBUG, "TestClient: 2. Wait DTMF 1\n");
197 res = ast_waitfordigit(chan, 3000);
198 fprintf(f, "WAIT DTMF 1: %s\n", (res != '1') ? "FAIL" : "PASS");
199 if (res == '1')
200 res = 0;
201 else
202 res = -1;
204 if (!res)
205 res = ast_safe_sleep(chan, 1000);
206 if (!res) {
207 /* Step 2: Send "2" */
208 if (option_debug)
209 ast_log(LOG_DEBUG, "TestClient: 2. Send DTMF 2\n");
210 res = ast_dtmf_stream(chan, NULL, "2", 0);
211 fprintf(f, "SEND DTMF 2: %s\n", (res < 0) ? "FAIL" : "PASS");
212 if (res > 0)
213 res = 0;
215 if (!res) {
216 /* Step 3: Wait one second */
217 if (option_debug)
218 ast_log(LOG_DEBUG, "TestClient: 3. Wait one second\n");
219 res = ast_safe_sleep(chan, 1000);
220 fprintf(f, "WAIT 1 SEC: %s\n", (res < 0) ? "FAIL" : "PASS");
221 if (res > 0)
222 res = 0;
224 if (!res) {
225 /* Step 4: Measure noise */
226 if (option_debug)
227 ast_log(LOG_DEBUG, "TestClient: 4. Measure noise\n");
228 res = measurenoise(chan, 5000, "TestClient");
229 fprintf(f, "MEASURENOISE: %s (%d)\n", (res < 0) ? "FAIL" : "PASS", res);
230 if (res > 0)
231 res = 0;
233 if (!res) {
234 /* Step 5: Wait for "4" */
235 if (option_debug)
236 ast_log(LOG_DEBUG, "TestClient: 5. Wait DTMF 4\n");
237 res = ast_waitfordigit(chan, 3000);
238 fprintf(f, "WAIT DTMF 4: %s\n", (res != '4') ? "FAIL" : "PASS");
239 if (res == '4')
240 res = 0;
241 else
242 res = -1;
244 if (!res) {
245 /* Step 6: Transmit tone noise */
246 if (option_debug)
247 ast_log(LOG_DEBUG, "TestClient: 6. Transmit tone\n");
248 res = sendnoise(chan, 6000);
249 fprintf(f, "SENDTONE: %s\n", (res < 0) ? "FAIL" : "PASS");
251 if (!res || (res == '5')) {
252 /* Step 7: Wait for "5" */
253 if (option_debug)
254 ast_log(LOG_DEBUG, "TestClient: 7. Wait DTMF 5\n");
255 if (!res)
256 res = ast_waitfordigit(chan, 3000);
257 fprintf(f, "WAIT DTMF 5: %s\n", (res != '5') ? "FAIL" : "PASS");
258 if (res == '5')
259 res = 0;
260 else
261 res = -1;
263 if (!res) {
264 /* Step 8: Wait one second */
265 if (option_debug)
266 ast_log(LOG_DEBUG, "TestClient: 8. Wait one second\n");
267 res = ast_safe_sleep(chan, 1000);
268 fprintf(f, "WAIT 1 SEC: %s\n", (res < 0) ? "FAIL" : "PASS");
269 if (res > 0)
270 res = 0;
272 if (!res) {
273 /* Step 9: Measure noise */
274 if (option_debug)
275 ast_log(LOG_DEBUG, "TestClient: 6. Measure tone\n");
276 res = measurenoise(chan, 4000, "TestClient");
277 fprintf(f, "MEASURETONE: %s (%d)\n", (res < 0) ? "FAIL" : "PASS", res);
278 if (res > 0)
279 res = 0;
281 if (!res) {
282 /* Step 10: Send "7" */
283 if (option_debug)
284 ast_log(LOG_DEBUG, "TestClient: 7. Send DTMF 7\n");
285 res = ast_dtmf_stream(chan, NULL, "7", 0);
286 fprintf(f, "SEND DTMF 7: %s\n", (res < 0) ? "FAIL" : "PASS");
287 if (res > 0)
288 res =0;
290 if (!res) {
291 /* Step 11: Wait for "8" */
292 if (option_debug)
293 ast_log(LOG_DEBUG, "TestClient: 11. Wait DTMF 8\n");
294 res = ast_waitfordigit(chan, 3000);
295 fprintf(f, "WAIT DTMF 8: %s\n", (res != '8') ? "FAIL" : "PASS");
296 if (res == '8')
297 res = 0;
298 else
299 res = -1;
301 if (option_debug && !res ) {
302 /* Step 12: Hangup! */
303 ast_log(LOG_DEBUG, "TestClient: 12. Hangup\n");
306 if (option_debug)
307 ast_log(LOG_DEBUG, "-- TEST COMPLETE--\n");
308 fprintf(f, "-- END TEST--\n");
309 fclose(f);
310 res = -1;
311 } else
312 res = -1;
313 } else {
314 ast_log(LOG_NOTICE, "Did not read a test ID on '%s'\n", chan->name);
315 res = -1;
317 ast_module_user_remove(u);
318 return res;
321 static int testserver_exec(struct ast_channel *chan, void *data)
323 struct ast_module_user *u;
324 int res = 0;
325 char testid[80]="";
326 char fn[80];
327 FILE *f;
328 u = ast_module_user_add(chan);
329 if (chan->_state != AST_STATE_UP)
330 res = ast_answer(chan);
331 /* Read version */
332 if (option_debug)
333 ast_log(LOG_DEBUG, "Read client version\n");
334 if (!res)
335 res = ast_app_getdata(chan, NULL, testid, sizeof(testid) - 1, 0);
336 if (res > 0)
337 res = 0;
338 if (option_debug) {
339 ast_log(LOG_DEBUG, "client version: %s\n", testid);
340 ast_log(LOG_DEBUG, "Transmit server version\n");
342 res = ast_safe_sleep(chan, 1000);
343 if (!res)
344 res = ast_dtmf_stream(chan, NULL, "8378*1#", 0);
345 if (res > 0)
346 res = 0;
348 if (!res)
349 res = ast_app_getdata(chan, NULL, testid, sizeof(testid) - 1, 0);
350 if (option_debug)
351 ast_log(LOG_DEBUG, "read test identifier: %s\n", testid);
352 /* Check for sneakyness */
353 if (strchr(testid, '/'))
354 res = -1;
355 if ((res >=0) && (!ast_strlen_zero(testid))) {
356 /* Got a Test ID! Whoo hoo! */
357 /* Make the directory to hold the test results in case it's not there */
358 snprintf(fn, sizeof(fn), "%s/testresults", ast_config_AST_LOG_DIR);
359 mkdir(fn, 0777);
360 snprintf(fn, sizeof(fn), "%s/testresults/%s-server.txt", ast_config_AST_LOG_DIR, testid);
361 if ((f = fopen(fn, "w+"))) {
362 setlinebuf(f);
363 fprintf(f, "SERVERCHAN: %s\n", chan->name);
364 fprintf(f, "SERVERTEST ID: %s\n", testid);
365 fprintf(f, "ANSWER: PASS\n");
366 ast_log(LOG_DEBUG, "Processing Test ID '%s'\n", testid);
367 res = ast_safe_sleep(chan, 1000);
368 if (!res) {
369 /* Step 1: Send "1" */
370 if (option_debug)
371 ast_log(LOG_DEBUG, "TestServer: 1. Send DTMF 1\n");
372 res = ast_dtmf_stream(chan, NULL, "1", 0);
373 fprintf(f, "SEND DTMF 1: %s\n", (res < 0) ? "FAIL" : "PASS");
374 if (res > 0)
375 res = 0;
377 if (!res) {
378 /* Step 2: Wait for "2" */
379 if (option_debug)
380 ast_log(LOG_DEBUG, "TestServer: 2. Wait DTMF 2\n");
381 res = ast_waitfordigit(chan, 3000);
382 fprintf(f, "WAIT DTMF 2: %s\n", (res != '2') ? "FAIL" : "PASS");
383 if (res == '2')
384 res = 0;
385 else
386 res = -1;
388 if (!res) {
389 /* Step 3: Measure noise */
390 if (option_debug)
391 ast_log(LOG_DEBUG, "TestServer: 3. Measure noise\n");
392 res = measurenoise(chan, 6000, "TestServer");
393 fprintf(f, "MEASURENOISE: %s (%d)\n", (res < 0) ? "FAIL" : "PASS", res);
394 if (res > 0)
395 res = 0;
397 if (!res) {
398 /* Step 4: Send "4" */
399 if (option_debug)
400 ast_log(LOG_DEBUG, "TestServer: 4. Send DTMF 4\n");
401 res = ast_dtmf_stream(chan, NULL, "4", 0);
402 fprintf(f, "SEND DTMF 4: %s\n", (res < 0) ? "FAIL" : "PASS");
403 if (res > 0)
404 res = 0;
407 if (!res) {
408 /* Step 5: Wait one second */
409 if (option_debug)
410 ast_log(LOG_DEBUG, "TestServer: 5. Wait one second\n");
411 res = ast_safe_sleep(chan, 1000);
412 fprintf(f, "WAIT 1 SEC: %s\n", (res < 0) ? "FAIL" : "PASS");
413 if (res > 0)
414 res = 0;
417 if (!res) {
418 /* Step 6: Measure noise */
419 if (option_debug)
420 ast_log(LOG_DEBUG, "TestServer: 6. Measure tone\n");
421 res = measurenoise(chan, 4000, "TestServer");
422 fprintf(f, "MEASURETONE: %s (%d)\n", (res < 0) ? "FAIL" : "PASS", res);
423 if (res > 0)
424 res = 0;
427 if (!res) {
428 /* Step 7: Send "5" */
429 if (option_debug)
430 ast_log(LOG_DEBUG, "TestServer: 7. Send DTMF 5\n");
431 res = ast_dtmf_stream(chan, NULL, "5", 0);
432 fprintf(f, "SEND DTMF 5: %s\n", (res < 0) ? "FAIL" : "PASS");
433 if (res > 0)
434 res = 0;
437 if (!res) {
438 /* Step 8: Transmit tone noise */
439 if (option_debug)
440 ast_log(LOG_DEBUG, "TestServer: 8. Transmit tone\n");
441 res = sendnoise(chan, 6000);
442 fprintf(f, "SENDTONE: %s\n", (res < 0) ? "FAIL" : "PASS");
445 if (!res || (res == '7')) {
446 /* Step 9: Wait for "7" */
447 if (option_debug)
448 ast_log(LOG_DEBUG, "TestServer: 9. Wait DTMF 7\n");
449 if (!res)
450 res = ast_waitfordigit(chan, 3000);
451 fprintf(f, "WAIT DTMF 7: %s\n", (res != '7') ? "FAIL" : "PASS");
452 if (res == '7')
453 res = 0;
454 else
455 res = -1;
457 if (!res)
458 res = ast_safe_sleep(chan, 1000);
459 if (!res) {
460 /* Step 10: Send "8" */
461 if (option_debug)
462 ast_log(LOG_DEBUG, "TestServer: 10. Send DTMF 8\n");
463 res = ast_dtmf_stream(chan, NULL, "8", 0);
464 fprintf(f, "SEND DTMF 8: %s\n", (res < 0) ? "FAIL" : "PASS");
465 if (res > 0)
466 res = 0;
468 if (!res) {
469 /* Step 11: Wait for hangup to arrive! */
470 if (option_debug)
471 ast_log(LOG_DEBUG, "TestServer: 11. Waiting for hangup\n");
472 res = ast_safe_sleep(chan, 10000);
473 fprintf(f, "WAIT HANGUP: %s\n", (res < 0) ? "PASS" : "FAIL");
476 ast_log(LOG_NOTICE, "-- TEST COMPLETE--\n");
477 fprintf(f, "-- END TEST--\n");
478 fclose(f);
479 res = -1;
480 } else
481 res = -1;
482 } else {
483 ast_log(LOG_NOTICE, "Did not read a test ID on '%s'\n", chan->name);
484 res = -1;
486 ast_module_user_remove(u);
487 return res;
490 static int unload_module(void)
492 int res;
494 res = ast_unregister_application(testc_app);
495 res |= ast_unregister_application(tests_app);
497 ast_module_user_hangup_all();
499 return res;
502 static int load_module(void)
504 int res;
506 res = ast_register_application(testc_app, testclient_exec, testc_synopsis, testc_descrip);
507 res |= ast_register_application(tests_app, testserver_exec, tests_synopsis, tests_descrip);
509 return res;
512 AST_MODULE_INFO_STANDARD(ASTERISK_GPL_KEY, "Interface Test Application");