00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043 #include "asterisk.h"
00044
00045 ASTERISK_FILE_VERSION(__FILE__, "$Revision: 211569 $")
00046
00047 #include <math.h>
00048
00049 #include "asterisk/frame.h"
00050 #include "asterisk/channel.h"
00051 #include "asterisk/dsp.h"
00052 #include "asterisk/ulaw.h"
00053 #include "asterisk/alaw.h"
00054 #include "asterisk/utils.h"
00055 #include "asterisk/options.h"
00056 #include "asterisk/config.h"
00057
00058
00059 enum gsamp_size {
00060 GSAMP_SIZE_NA = 183,
00061 GSAMP_SIZE_CR = 188,
00062 GSAMP_SIZE_UK = 160
00063 };
00064
00065 enum prog_mode {
00066 PROG_MODE_NA = 0,
00067 PROG_MODE_CR,
00068 PROG_MODE_UK
00069 };
00070
00071 enum freq_index {
00072
00073 HZ_350 = 0,
00074 HZ_440,
00075 HZ_480,
00076 HZ_620,
00077 HZ_950,
00078 HZ_1400,
00079 HZ_1800,
00080
00081
00082 HZ_425 = 0,
00083
00084
00085 HZ_400 = 0
00086 };
00087
00088 static struct progalias {
00089 char *name;
00090 enum prog_mode mode;
00091 } aliases[] = {
00092 { "us", PROG_MODE_NA },
00093 { "ca", PROG_MODE_NA },
00094 { "cr", PROG_MODE_CR },
00095 { "br", PROG_MODE_CR },
00096 { "uk", PROG_MODE_UK },
00097 };
00098
00099 static struct progress {
00100 enum gsamp_size size;
00101 int freqs[7];
00102 } modes[] = {
00103 { GSAMP_SIZE_NA, { 350, 440, 480, 620, 950, 1400, 1800 } },
00104 { GSAMP_SIZE_CR, { 425 } },
00105 { GSAMP_SIZE_UK, { 400 } },
00106 };
00107
00108
00109
00110
00111
00112
00113
00114
00115 #define DEFAULT_THRESHOLD 512
00116
00117 enum busy_detect {
00118 BUSY_PERCENT = 10,
00119 BUSY_PAT_PERCENT = 7,
00120 BUSY_THRESHOLD = 100,
00121 BUSY_MIN = 75,
00122 BUSY_MAX =3100
00123 };
00124
00125
00126 #define DSP_HISTORY 15
00127
00128 #define TONE_THRESH 10.0
00129 #define TONE_MIN_THRESH 1e8
00130
00131
00132 enum gsamp_thresh {
00133 THRESH_RING = 8,
00134 THRESH_TALK = 2,
00135 THRESH_BUSY = 4,
00136 THRESH_CONGESTION = 4,
00137 THRESH_HANGUP = 60,
00138 THRESH_RING2ANSWER = 300
00139 };
00140
00141 #define MAX_DTMF_DIGITS 128
00142
00143
00144
00145
00146
00147
00148
00149
00150
00151
00152
00153
00154
00155 #define DTMF_THRESHOLD 8.0e7
00156 #define FAX_THRESHOLD 8.0e7
00157 #define FAX_2ND_HARMONIC 2.0
00158 #define DTMF_NORMAL_TWIST 6.3
00159 #ifdef RADIO_RELAX
00160 #define DTMF_REVERSE_TWIST (relax ? 6.5 : 2.5)
00161 #else
00162 #define DTMF_REVERSE_TWIST (relax ? 4.0 : 2.5)
00163 #endif
00164 #define DTMF_RELATIVE_PEAK_ROW 6.3
00165 #define DTMF_RELATIVE_PEAK_COL 6.3
00166 #define DTMF_2ND_HARMONIC_ROW (relax ? 1.7 : 2.5)
00167 #define DTMF_2ND_HARMONIC_COL 63.1
00168 #define DTMF_TO_TOTAL_ENERGY 42.0
00169
00170 #define BELL_MF_THRESHOLD 1.6e9
00171 #define BELL_MF_TWIST 4.0
00172 #define BELL_MF_RELATIVE_PEAK 12.6
00173
00174 #if defined(BUSYDETECT_TONEONLY) && defined(BUSYDETECT_COMPARE_TONE_AND_SILENCE)
00175 #error You cant use BUSYDETECT_TONEONLY together with BUSYDETECT_COMPARE_TONE_AND_SILENCE
00176 #endif
00177
00178
00179
00180
00181 #define FAX_TONE_CNG_FREQ 1100
00182 #define FAX_TONE_CNG_DURATION 500
00183 #define FAX_TONE_CNG_DB 16
00184
00185
00186
00187
00188
00189 #define FAX_TONE_CED_FREQ 2100
00190 #define FAX_TONE_CED_DURATION 2600
00191 #define FAX_TONE_CED_DB 16
00192
00193 #define SAMPLE_RATE 8000
00194
00195
00196
00197
00198
00199
00200
00201 #define SAMPLES_IN_FRAME 160
00202
00203
00204 #define MF_GSIZE 120
00205
00206
00207 #define DTMF_GSIZE 102
00208
00209
00210 #define DTMF_HITS_TO_BEGIN 2
00211
00212 #define DTMF_MISSES_TO_END 3
00213
00214 #define CONFIG_FILE_NAME "dsp.conf"
00215
00216 typedef struct {
00217 int v2;
00218 int v3;
00219 int chunky;
00220 int fac;
00221 int samples;
00222 } goertzel_state_t;
00223
00224 typedef struct {
00225 int value;
00226 int power;
00227 } goertzel_result_t;
00228
00229 typedef struct
00230 {
00231 int freq;
00232 int block_size;
00233 int squelch;
00234 goertzel_state_t tone;
00235 float energy;
00236 int samples_pending;
00237 int mute_samples;
00238
00239 int hits_required;
00240 float threshold;
00241
00242 int hit_count;
00243 int last_hit;
00244
00245 } tone_detect_state_t;
00246
00247 typedef struct
00248 {
00249 goertzel_state_t row_out[4];
00250 goertzel_state_t col_out[4];
00251 int hits_to_begin;
00252 int misses_to_end;
00253 int hits;
00254 int misses;
00255 int lasthit;
00256 int current_hit;
00257 float energy;
00258 int current_sample;
00259 int mute_samples;
00260 } dtmf_detect_state_t;
00261
00262 typedef struct
00263 {
00264 goertzel_state_t tone_out[6];
00265 int current_hit;
00266 int hits[5];
00267 int current_sample;
00268 int mute_samples;
00269 } mf_detect_state_t;
00270
00271 typedef struct
00272 {
00273 char digits[MAX_DTMF_DIGITS + 1];
00274 int current_digits;
00275 int detected_digits;
00276 int lost_digits;
00277
00278 union {
00279 dtmf_detect_state_t dtmf;
00280 mf_detect_state_t mf;
00281 } td;
00282 } digit_detect_state_t;
00283
00284 static float dtmf_row[] =
00285 {
00286 697.0, 770.0, 852.0, 941.0
00287 };
00288 static float dtmf_col[] =
00289 {
00290 1209.0, 1336.0, 1477.0, 1633.0
00291 };
00292
00293 static float mf_tones[] =
00294 {
00295 700.0, 900.0, 1100.0, 1300.0, 1500.0, 1700.0
00296 };
00297
00298 static char dtmf_positions[] = "123A" "456B" "789C" "*0#D";
00299
00300 static char bell_mf_positions[] = "1247C-358A--69*---0B----#";
00301
00302 static int thresholds[THRESHOLD_MAX];
00303
00304 static inline void goertzel_sample(goertzel_state_t *s, short sample)
00305 {
00306 int v1;
00307
00308 v1 = s->v2;
00309 s->v2 = s->v3;
00310
00311 s->v3 = (s->fac * s->v2) >> 15;
00312 s->v3 = s->v3 - v1 + (sample >> s->chunky);
00313 if (abs(s->v3) > 32768) {
00314 s->chunky++;
00315 s->v3 = s->v3 >> 1;
00316 s->v2 = s->v2 >> 1;
00317 v1 = v1 >> 1;
00318 }
00319 }
00320
00321 static inline void goertzel_update(goertzel_state_t *s, short *samps, int count)
00322 {
00323 int i;
00324
00325 for (i=0;i<count;i++)
00326 goertzel_sample(s, samps[i]);
00327 }
00328
00329
00330 static inline float goertzel_result(goertzel_state_t *s)
00331 {
00332 goertzel_result_t r;
00333 r.value = (s->v3 * s->v3) + (s->v2 * s->v2);
00334 r.value -= ((s->v2 * s->v3) >> 15) * s->fac;
00335 r.power = s->chunky * 2;
00336 return (float)r.value * (float)(1 << r.power);
00337 }
00338
00339 static inline void goertzel_init(goertzel_state_t *s, float freq, int samples)
00340 {
00341 s->v2 = s->v3 = s->chunky = 0.0;
00342 s->fac = (int)(32768.0 * 2.0 * cos(2.0 * M_PI * freq / SAMPLE_RATE));
00343 s->samples = samples;
00344 }
00345
00346 static inline void goertzel_reset(goertzel_state_t *s)
00347 {
00348 s->v2 = s->v3 = s->chunky = 0.0;
00349 }
00350
00351 typedef struct {
00352 int start;
00353 int end;
00354 } fragment_t;
00355
00356
00357
00358
00359
00360
00361
00362
00363
00364
00365
00366
00367
00368
00369 struct ast_dsp {
00370 struct ast_frame f;
00371 int threshold;
00372 int totalsilence;
00373 int totalnoise;
00374 int features;
00375 int ringtimeout;
00376 int busymaybe;
00377 int busycount;
00378 int busy_tonelength;
00379 int busy_quietlength;
00380 int historicnoise[DSP_HISTORY];
00381 int historicsilence[DSP_HISTORY];
00382 goertzel_state_t freqs[7];
00383 int freqcount;
00384 int gsamps;
00385 enum gsamp_size gsamp_size;
00386 enum prog_mode progmode;
00387 int tstate;
00388 int tcount;
00389 int digitmode;
00390 int faxmode;
00391 int dtmf_began;
00392 float genergy;
00393 int mute_fragments;
00394 fragment_t mute_data[5];
00395 digit_detect_state_t digit_state;
00396 tone_detect_state_t cng_tone_state;
00397 tone_detect_state_t ced_tone_state;
00398 int destroy;
00399 };
00400
00401 static void mute_fragment(struct ast_dsp *dsp, fragment_t *fragment)
00402 {
00403 if (dsp->mute_fragments >= ARRAY_LEN(dsp->mute_data)) {
00404 ast_log(LOG_ERROR, "Too many fragments to mute. Ignoring\n");
00405 return;
00406 }
00407
00408 dsp->mute_data[dsp->mute_fragments++] = *fragment;
00409 }
00410
00411 static void ast_tone_detect_init(tone_detect_state_t *s, int freq, int duration, int amp)
00412 {
00413 int duration_samples;
00414 float x;
00415 int periods_in_block;
00416
00417 s->freq = freq;
00418
00419
00420 duration_samples = duration * SAMPLE_RATE / 1000;
00421
00422 duration_samples = duration_samples * 9 / 10;
00423
00424
00425
00426
00427 s->block_size = SAMPLES_IN_FRAME;
00428
00429 periods_in_block = s->block_size * freq / SAMPLE_RATE;
00430
00431
00432
00433
00434 if (periods_in_block < 5)
00435 periods_in_block = 5;
00436
00437
00438 s->block_size = periods_in_block * SAMPLE_RATE / freq;
00439
00440
00441
00442 s->squelch = 0;
00443
00444
00445
00446 s->hits_required = (duration_samples - (s->block_size - 1)) / s->block_size;
00447
00448 goertzel_init(&s->tone, freq, s->block_size);
00449
00450 s->samples_pending = s->block_size;
00451 s->hit_count = 0;
00452 s->last_hit = 0;
00453 s->energy = 0.0;
00454
00455
00456
00457
00458
00459
00460
00461
00462
00463
00464
00465 x = pow(10.0, amp / 10.0);
00466 s->threshold = x / (x + 1);
00467
00468 ast_debug(1, "Setup tone %d Hz, %d ms, block_size=%d, hits_required=%d\n", freq, duration, s->block_size, s->hits_required);
00469 }
00470
00471 static void ast_fax_detect_init(struct ast_dsp *s)
00472 {
00473 ast_tone_detect_init(&s->cng_tone_state, FAX_TONE_CNG_FREQ, FAX_TONE_CNG_DURATION, FAX_TONE_CNG_DB);
00474 ast_tone_detect_init(&s->ced_tone_state, FAX_TONE_CED_FREQ, FAX_TONE_CED_DURATION, FAX_TONE_CED_DB);
00475 }
00476
00477 static void ast_dtmf_detect_init (dtmf_detect_state_t *s)
00478 {
00479 int i;
00480
00481 s->lasthit = 0;
00482 s->current_hit = 0;
00483 for (i = 0; i < 4; i++) {
00484 goertzel_init (&s->row_out[i], dtmf_row[i], DTMF_GSIZE);
00485 goertzel_init (&s->col_out[i], dtmf_col[i], DTMF_GSIZE);
00486 s->energy = 0.0;
00487 }
00488 s->current_sample = 0;
00489 s->hits = 0;
00490 s->misses = 0;
00491
00492 s->hits_to_begin = DTMF_HITS_TO_BEGIN;
00493 s->misses_to_end = DTMF_MISSES_TO_END;
00494 }
00495
00496 static void ast_mf_detect_init (mf_detect_state_t *s)
00497 {
00498 int i;
00499 s->hits[0] = s->hits[1] = s->hits[2] = s->hits[3] = s->hits[4] = 0;
00500 for (i = 0; i < 6; i++) {
00501 goertzel_init (&s->tone_out[i], mf_tones[i], 160);
00502 }
00503 s->current_sample = 0;
00504 s->current_hit = 0;
00505 }
00506
00507 static void ast_digit_detect_init(digit_detect_state_t *s, int mf)
00508 {
00509 s->current_digits = 0;
00510 s->detected_digits = 0;
00511 s->lost_digits = 0;
00512 s->digits[0] = '\0';
00513
00514 if (mf)
00515 ast_mf_detect_init(&s->td.mf);
00516 else
00517 ast_dtmf_detect_init(&s->td.dtmf);
00518 }
00519
00520 static int tone_detect(struct ast_dsp *dsp, tone_detect_state_t *s, int16_t *amp, int samples)
00521 {
00522 float tone_energy;
00523 int i;
00524 int hit = 0;
00525 int limit;
00526 int res = 0;
00527 int16_t *ptr;
00528 int start, end;
00529 fragment_t mute = {0, 0};
00530
00531 if (s->squelch && s->mute_samples > 0) {
00532 mute.end = (s->mute_samples < samples) ? s->mute_samples : samples;
00533 s->mute_samples -= mute.end;
00534 }
00535
00536 for (start = 0; start < samples; start = end) {
00537
00538 limit = samples - start;
00539 if (limit > s->samples_pending)
00540 limit = s->samples_pending;
00541 end = start + limit;
00542
00543 for (i = limit, ptr = amp ; i > 0; i--, ptr++) {
00544
00545 s->energy += (int32_t) *ptr * (int32_t) *ptr;
00546
00547 goertzel_sample(&s->tone, *ptr);
00548 }
00549
00550 s->samples_pending -= limit;
00551
00552 if (s->samples_pending) {
00553
00554 break;
00555 }
00556
00557 tone_energy = goertzel_result(&s->tone);
00558
00559
00560 tone_energy *= 2.0;
00561 s->energy *= s->block_size;
00562
00563 ast_debug(10, "tone %d, Ew=%.2E, Et=%.2E, s/n=%10.2f\n", s->freq, tone_energy, s->energy, tone_energy / (s->energy - tone_energy));
00564 hit = 0;
00565 if (tone_energy > s->energy * s->threshold) {
00566 ast_debug(10, "Hit! count=%d\n", s->hit_count);
00567 hit = 1;
00568 }
00569
00570 if (s->hit_count)
00571 s->hit_count++;
00572
00573 if (hit == s->last_hit) {
00574 if (!hit) {
00575
00576 s->hit_count = 0;
00577 } else if (!s->hit_count) {
00578 s->hit_count++;
00579 }
00580
00581 }
00582
00583 if (s->hit_count == s->hits_required) {
00584 ast_debug(1, "%d Hz done detected\n", s->freq);
00585 res = 1;
00586 }
00587
00588 s->last_hit = hit;
00589
00590
00591 if (s->squelch && hit) {
00592 if (mute.end < start - s->block_size) {
00593
00594 mute_fragment(dsp, &mute);
00595 mute.start = (start > s->block_size) ? (start - s->block_size) : 0;
00596 }
00597 mute.end = end + s->block_size;
00598 }
00599
00600
00601
00602 goertzel_reset(&s->tone);
00603
00604
00605 s->energy = 0.0;
00606 s->samples_pending = s->block_size;
00607
00608 amp += limit;
00609 }
00610
00611 if (s->squelch && mute.end) {
00612 if (mute.end > samples) {
00613 s->mute_samples = mute.end - samples;
00614 mute.end = samples;
00615 }
00616 mute_fragment(dsp, &mute);
00617 }
00618
00619 return res;
00620 }
00621
00622 static void store_digit(digit_detect_state_t *s, char digit)
00623 {
00624 s->detected_digits++;
00625 if (s->current_digits < MAX_DTMF_DIGITS) {
00626 s->digits[s->current_digits++] = digit;
00627 s->digits[s->current_digits] = '\0';
00628 } else {
00629 ast_log(LOG_WARNING, "Digit lost due to full buffer\n");
00630 s->lost_digits++;
00631 }
00632 }
00633
00634 static int dtmf_detect(struct ast_dsp *dsp, digit_detect_state_t *s, int16_t amp[], int samples, int squelch, int relax)
00635 {
00636 float row_energy[4];
00637 float col_energy[4];
00638 float famp;
00639 int i;
00640 int j;
00641 int sample;
00642 int best_row;
00643 int best_col;
00644 int hit;
00645 int limit;
00646 fragment_t mute = {0, 0};
00647
00648 if (squelch && s->td.dtmf.mute_samples > 0) {
00649 mute.end = (s->td.dtmf.mute_samples < samples) ? s->td.dtmf.mute_samples : samples;
00650 s->td.dtmf.mute_samples -= mute.end;
00651 }
00652
00653 hit = 0;
00654 for (sample = 0; sample < samples; sample = limit) {
00655
00656 if ((samples - sample) >= (DTMF_GSIZE - s->td.dtmf.current_sample))
00657 limit = sample + (DTMF_GSIZE - s->td.dtmf.current_sample);
00658 else
00659 limit = samples;
00660
00661
00662 for (j = sample; j < limit; j++) {
00663 famp = amp[j];
00664 s->td.dtmf.energy += famp*famp;
00665
00666
00667 goertzel_sample(s->td.dtmf.row_out, amp[j]);
00668 goertzel_sample(s->td.dtmf.col_out, amp[j]);
00669 goertzel_sample(s->td.dtmf.row_out + 1, amp[j]);
00670 goertzel_sample(s->td.dtmf.col_out + 1, amp[j]);
00671 goertzel_sample(s->td.dtmf.row_out + 2, amp[j]);
00672 goertzel_sample(s->td.dtmf.col_out + 2, amp[j]);
00673 goertzel_sample(s->td.dtmf.row_out + 3, amp[j]);
00674 goertzel_sample(s->td.dtmf.col_out + 3, amp[j]);
00675 }
00676 s->td.dtmf.current_sample += (limit - sample);
00677 if (s->td.dtmf.current_sample < DTMF_GSIZE) {
00678 continue;
00679 }
00680
00681
00682 row_energy[0] = goertzel_result (&s->td.dtmf.row_out[0]);
00683 col_energy[0] = goertzel_result (&s->td.dtmf.col_out[0]);
00684
00685 for (best_row = best_col = 0, i = 1; i < 4; i++) {
00686 row_energy[i] = goertzel_result (&s->td.dtmf.row_out[i]);
00687 if (row_energy[i] > row_energy[best_row])
00688 best_row = i;
00689 col_energy[i] = goertzel_result (&s->td.dtmf.col_out[i]);
00690 if (col_energy[i] > col_energy[best_col])
00691 best_col = i;
00692 }
00693 hit = 0;
00694
00695 if (row_energy[best_row] >= DTMF_THRESHOLD &&
00696 col_energy[best_col] >= DTMF_THRESHOLD &&
00697 col_energy[best_col] < row_energy[best_row]*DTMF_REVERSE_TWIST &&
00698 col_energy[best_col]*DTMF_NORMAL_TWIST > row_energy[best_row]) {
00699
00700 for (i = 0; i < 4; i++) {
00701 if ((i != best_col &&
00702 col_energy[i]*DTMF_RELATIVE_PEAK_COL > col_energy[best_col]) ||
00703 (i != best_row
00704 && row_energy[i]*DTMF_RELATIVE_PEAK_ROW > row_energy[best_row])) {
00705 break;
00706 }
00707 }
00708
00709 if (i >= 4 &&
00710 (row_energy[best_row] + col_energy[best_col]) > DTMF_TO_TOTAL_ENERGY*s->td.dtmf.energy) {
00711
00712 hit = dtmf_positions[(best_row << 2) + best_col];
00713 }
00714 }
00715
00716 if (s->td.dtmf.current_hit) {
00717
00718 if (hit != s->td.dtmf.current_hit) {
00719 s->td.dtmf.misses++;
00720 if (s->td.dtmf.misses == s->td.dtmf.misses_to_end) {
00721
00722 s->td.dtmf.current_hit = 0;
00723 }
00724 } else {
00725 s->td.dtmf.misses = 0;
00726 }
00727 }
00728
00729
00730
00731
00732 if (hit) {
00733 if (hit == s->td.dtmf.lasthit) {
00734 s->td.dtmf.hits++;
00735 } else {
00736 s->td.dtmf.hits = 1;
00737 }
00738
00739 if (s->td.dtmf.hits == s->td.dtmf.hits_to_begin && hit != s->td.dtmf.current_hit) {
00740 store_digit(s, hit);
00741 s->td.dtmf.current_hit = hit;
00742 s->td.dtmf.misses = 0;
00743 }
00744 } else {
00745 s->td.dtmf.hits = 0;
00746 }
00747
00748 s->td.dtmf.lasthit = hit;
00749
00750
00751 if (squelch && hit) {
00752 if (mute.end < sample - DTMF_GSIZE) {
00753
00754 mute_fragment(dsp, &mute);
00755 mute.start = (sample > DTMF_GSIZE) ? (sample - DTMF_GSIZE) : 0;
00756 }
00757 mute.end = limit + DTMF_GSIZE;
00758 }
00759
00760
00761 for (i = 0; i < 4; i++) {
00762 goertzel_reset(&s->td.dtmf.row_out[i]);
00763 goertzel_reset(&s->td.dtmf.col_out[i]);
00764 }
00765 s->td.dtmf.energy = 0.0;
00766 s->td.dtmf.current_sample = 0;
00767 }
00768
00769 if (squelch && mute.end) {
00770 if (mute.end > samples) {
00771 s->td.dtmf.mute_samples = mute.end - samples;
00772 mute.end = samples;
00773 }
00774 mute_fragment(dsp, &mute);
00775 }
00776
00777 return (s->td.dtmf.current_hit);
00778 }
00779
00780 static int mf_detect(struct ast_dsp *dsp, digit_detect_state_t *s, int16_t amp[],
00781 int samples, int squelch, int relax)
00782 {
00783 float energy[6];
00784 int best;
00785 int second_best;
00786 float famp;
00787 int i;
00788 int j;
00789 int sample;
00790 int hit;
00791 int limit;
00792 fragment_t mute = {0, 0};
00793
00794 if (squelch && s->td.mf.mute_samples > 0) {
00795 mute.end = (s->td.mf.mute_samples < samples) ? s->td.mf.mute_samples : samples;
00796 s->td.mf.mute_samples -= mute.end;
00797 }
00798
00799 hit = 0;
00800 for (sample = 0; sample < samples; sample = limit) {
00801
00802
00803 if ((samples - sample) >= (MF_GSIZE - s->td.mf.current_sample))
00804 limit = sample + (MF_GSIZE - s->td.mf.current_sample);
00805 else
00806 limit = samples;
00807
00808
00809 for (j = sample; j < limit; j++) {
00810 famp = amp[j];
00811
00812
00813 goertzel_sample(s->td.mf.tone_out, amp[j]);
00814 goertzel_sample(s->td.mf.tone_out + 1, amp[j]);
00815 goertzel_sample(s->td.mf.tone_out + 2, amp[j]);
00816 goertzel_sample(s->td.mf.tone_out + 3, amp[j]);
00817 goertzel_sample(s->td.mf.tone_out + 4, amp[j]);
00818 goertzel_sample(s->td.mf.tone_out + 5, amp[j]);
00819 }
00820 s->td.mf.current_sample += (limit - sample);
00821 if (s->td.mf.current_sample < MF_GSIZE) {
00822 continue;
00823 }
00824
00825
00826
00827
00828
00829
00830
00831 energy[0] = goertzel_result(&s->td.mf.tone_out[0]);
00832 energy[1] = goertzel_result(&s->td.mf.tone_out[1]);
00833 if (energy[0] > energy[1]) {
00834 best = 0;
00835 second_best = 1;
00836 } else {
00837 best = 1;
00838 second_best = 0;
00839 }
00840
00841 for (i=2;i<6;i++) {
00842 energy[i] = goertzel_result(&s->td.mf.tone_out[i]);
00843 if (energy[i] >= energy[best]) {
00844 second_best = best;
00845 best = i;
00846 } else if (energy[i] >= energy[second_best]) {
00847 second_best = i;
00848 }
00849 }
00850
00851 hit = 0;
00852 if (energy[best] >= BELL_MF_THRESHOLD && energy[second_best] >= BELL_MF_THRESHOLD
00853 && energy[best] < energy[second_best]*BELL_MF_TWIST
00854 && energy[best]*BELL_MF_TWIST > energy[second_best]) {
00855
00856 hit = -1;
00857 for (i=0;i<6;i++) {
00858 if (i != best && i != second_best) {
00859 if (energy[i]*BELL_MF_RELATIVE_PEAK >= energy[second_best]) {
00860
00861 hit = 0;
00862 break;
00863 }
00864 }
00865 }
00866 }
00867 if (hit) {
00868
00869 if (second_best < best) {
00870 i = best;
00871 best = second_best;
00872 second_best = i;
00873 }
00874 best = best*5 + second_best - 1;
00875 hit = bell_mf_positions[best];
00876
00877
00878
00879
00880
00881
00882 if (hit == s->td.mf.hits[4] && hit == s->td.mf.hits[3] &&
00883 ((hit != '*' && hit != s->td.mf.hits[2] && hit != s->td.mf.hits[1])||
00884 (hit == '*' && hit == s->td.mf.hits[2] && hit != s->td.mf.hits[1] &&
00885 hit != s->td.mf.hits[0]))) {
00886 store_digit(s, hit);
00887 }
00888 }
00889
00890
00891 if (hit != s->td.mf.hits[4] && hit != s->td.mf.hits[3]) {
00892
00893 s->td.mf.current_hit = 0;
00894 }
00895
00896 s->td.mf.hits[0] = s->td.mf.hits[1];
00897 s->td.mf.hits[1] = s->td.mf.hits[2];
00898 s->td.mf.hits[2] = s->td.mf.hits[3];
00899 s->td.mf.hits[3] = s->td.mf.hits[4];
00900 s->td.mf.hits[4] = hit;
00901
00902
00903 if (squelch && hit) {
00904 if (mute.end < sample - MF_GSIZE) {
00905
00906 mute_fragment(dsp, &mute);
00907 mute.start = (sample > MF_GSIZE) ? (sample - MF_GSIZE) : 0;
00908 }
00909 mute.end = limit + DTMF_GSIZE;
00910 }
00911
00912
00913 for (i = 0; i < 6; i++)
00914 goertzel_reset(&s->td.mf.tone_out[i]);
00915 s->td.mf.current_sample = 0;
00916 }
00917
00918 if (squelch && mute.end) {
00919 if (mute.end > samples) {
00920 s->td.mf.mute_samples = mute.end - samples;
00921 mute.end = samples;
00922 }
00923 mute_fragment(dsp, &mute);
00924 }
00925
00926 return (s->td.mf.current_hit);
00927 }
00928
00929 static inline int pair_there(float p1, float p2, float i1, float i2, float e)
00930 {
00931
00932
00933 if ((p1 < TONE_MIN_THRESH) || (p2 < TONE_MIN_THRESH))
00934 return 0;
00935
00936 i2 *= TONE_THRESH;
00937 i1 *= TONE_THRESH;
00938 e *= TONE_THRESH;
00939
00940 if ((p1 < i1) || (p1 < i2) || (p1 < e))
00941 return 0;
00942
00943 if ((p2 < i1) || (p2 < i2) || (p2 < e))
00944 return 0;
00945
00946 return 1;
00947 }
00948
00949 static int __ast_dsp_call_progress(struct ast_dsp *dsp, short *s, int len)
00950 {
00951 int x;
00952 int y;
00953 int pass;
00954 int newstate = DSP_TONE_STATE_SILENCE;
00955 int res = 0;
00956 while (len) {
00957
00958 pass = len;
00959 if (pass > dsp->gsamp_size - dsp->gsamps)
00960 pass = dsp->gsamp_size - dsp->gsamps;
00961 for (x=0;x<pass;x++) {
00962 for (y=0;y<dsp->freqcount;y++)
00963 goertzel_sample(&dsp->freqs[y], s[x]);
00964 dsp->genergy += s[x] * s[x];
00965 }
00966 s += pass;
00967 dsp->gsamps += pass;
00968 len -= pass;
00969 if (dsp->gsamps == dsp->gsamp_size) {
00970 float hz[7];
00971 for (y=0;y<7;y++)
00972 hz[y] = goertzel_result(&dsp->freqs[y]);
00973 switch (dsp->progmode) {
00974 case PROG_MODE_NA:
00975 if (pair_there(hz[HZ_480], hz[HZ_620], hz[HZ_350], hz[HZ_440], dsp->genergy)) {
00976 newstate = DSP_TONE_STATE_BUSY;
00977 } else if (pair_there(hz[HZ_440], hz[HZ_480], hz[HZ_350], hz[HZ_620], dsp->genergy)) {
00978 newstate = DSP_TONE_STATE_RINGING;
00979 } else if (pair_there(hz[HZ_350], hz[HZ_440], hz[HZ_480], hz[HZ_620], dsp->genergy)) {
00980 newstate = DSP_TONE_STATE_DIALTONE;
00981 } else if (hz[HZ_950] > TONE_MIN_THRESH * TONE_THRESH) {
00982 newstate = DSP_TONE_STATE_SPECIAL1;
00983 } else if (hz[HZ_1400] > TONE_MIN_THRESH * TONE_THRESH) {
00984 if (dsp->tstate == DSP_TONE_STATE_SPECIAL1)
00985 newstate = DSP_TONE_STATE_SPECIAL2;
00986 } else if (hz[HZ_1800] > TONE_MIN_THRESH * TONE_THRESH) {
00987 if (dsp->tstate == DSP_TONE_STATE_SPECIAL2)
00988 newstate = DSP_TONE_STATE_SPECIAL3;
00989 } else if (dsp->genergy > TONE_MIN_THRESH * TONE_THRESH) {
00990 newstate = DSP_TONE_STATE_TALKING;
00991 } else
00992 newstate = DSP_TONE_STATE_SILENCE;
00993 break;
00994 case PROG_MODE_CR:
00995 if (hz[HZ_425] > TONE_MIN_THRESH * TONE_THRESH) {
00996 newstate = DSP_TONE_STATE_RINGING;
00997 } else if (dsp->genergy > TONE_MIN_THRESH * TONE_THRESH) {
00998 newstate = DSP_TONE_STATE_TALKING;
00999 } else
01000 newstate = DSP_TONE_STATE_SILENCE;
01001 break;
01002 case PROG_MODE_UK:
01003 if (hz[HZ_400] > TONE_MIN_THRESH * TONE_THRESH) {
01004 newstate = DSP_TONE_STATE_HUNGUP;
01005 }
01006 break;
01007 default:
01008 ast_log(LOG_WARNING, "Can't process in unknown prog mode '%d'\n", dsp->progmode);
01009 }
01010 if (newstate == dsp->tstate) {
01011 dsp->tcount++;
01012 if (dsp->ringtimeout)
01013 dsp->ringtimeout++;
01014 switch (dsp->tstate) {
01015 case DSP_TONE_STATE_RINGING:
01016 if ((dsp->features & DSP_PROGRESS_RINGING) &&
01017 (dsp->tcount==THRESH_RING)) {
01018 res = AST_CONTROL_RINGING;
01019 dsp->ringtimeout= 1;
01020 }
01021 break;
01022 case DSP_TONE_STATE_BUSY:
01023 if ((dsp->features & DSP_PROGRESS_BUSY) &&
01024 (dsp->tcount==THRESH_BUSY)) {
01025 res = AST_CONTROL_BUSY;
01026 dsp->features &= ~DSP_FEATURE_CALL_PROGRESS;
01027 }
01028 break;
01029 case DSP_TONE_STATE_TALKING:
01030 if ((dsp->features & DSP_PROGRESS_TALK) &&
01031 (dsp->tcount==THRESH_TALK)) {
01032 res = AST_CONTROL_ANSWER;
01033 dsp->features &= ~DSP_FEATURE_CALL_PROGRESS;
01034 }
01035 break;
01036 case DSP_TONE_STATE_SPECIAL3:
01037 if ((dsp->features & DSP_PROGRESS_CONGESTION) &&
01038 (dsp->tcount==THRESH_CONGESTION)) {
01039 res = AST_CONTROL_CONGESTION;
01040 dsp->features &= ~DSP_FEATURE_CALL_PROGRESS;
01041 }
01042 break;
01043 case DSP_TONE_STATE_HUNGUP:
01044 if ((dsp->features & DSP_FEATURE_CALL_PROGRESS) &&
01045 (dsp->tcount==THRESH_HANGUP)) {
01046 res = AST_CONTROL_HANGUP;
01047 dsp->features &= ~DSP_FEATURE_CALL_PROGRESS;
01048 }
01049 break;
01050 }
01051 if (dsp->ringtimeout==THRESH_RING2ANSWER) {
01052 ast_debug(1, "Consider call as answered because of timeout after last ring\n");
01053 res = AST_CONTROL_ANSWER;
01054 dsp->features &= ~DSP_FEATURE_CALL_PROGRESS;
01055 }
01056 } else {
01057 ast_debug(5, "Stop state %d with duration %d\n", dsp->tstate, dsp->tcount);
01058 ast_debug(5, "Start state %d\n", newstate);
01059 dsp->tstate = newstate;
01060 dsp->tcount = 1;
01061 }
01062
01063
01064 for (x=0;x<7;x++)
01065 dsp->freqs[x].v2 = dsp->freqs[x].v3 = 0.0;
01066 dsp->gsamps = 0;
01067 dsp->genergy = 0.0;
01068 }
01069 }
01070
01071 return res;
01072 }
01073
01074 int ast_dsp_call_progress(struct ast_dsp *dsp, struct ast_frame *inf)
01075 {
01076 if (inf->frametype != AST_FRAME_VOICE) {
01077 ast_log(LOG_WARNING, "Can't check call progress of non-voice frames\n");
01078 return 0;
01079 }
01080 if (inf->subclass != AST_FORMAT_SLINEAR) {
01081 ast_log(LOG_WARNING, "Can only check call progress in signed-linear frames\n");
01082 return 0;
01083 }
01084 return __ast_dsp_call_progress(dsp, inf->data.ptr, inf->datalen / 2);
01085 }
01086
01087 static int __ast_dsp_silence_noise(struct ast_dsp *dsp, short *s, int len, int *totalsilence, int *totalnoise)
01088 {
01089 int accum;
01090 int x;
01091 int res = 0;
01092
01093 if (!len)
01094 return 0;
01095 accum = 0;
01096 for (x=0;x<len; x++)
01097 accum += abs(s[x]);
01098 accum /= len;
01099 if (accum < dsp->threshold) {
01100
01101 dsp->totalsilence += len/8;
01102 if (dsp->totalnoise) {
01103
01104 memmove(dsp->historicnoise + DSP_HISTORY - dsp->busycount, dsp->historicnoise + DSP_HISTORY - dsp->busycount +1, dsp->busycount*sizeof(dsp->historicnoise[0]));
01105 dsp->historicnoise[DSP_HISTORY - 1] = dsp->totalnoise;
01106
01107 #if 0
01108 dsp->busymaybe = 1;
01109 #endif
01110 }
01111 dsp->totalnoise = 0;
01112 res = 1;
01113 } else {
01114
01115 dsp->totalnoise += len/8;
01116 if (dsp->totalsilence) {
01117 int silence1 = dsp->historicsilence[DSP_HISTORY - 1];
01118 int silence2 = dsp->historicsilence[DSP_HISTORY - 2];
01119
01120 memmove(dsp->historicsilence + DSP_HISTORY - dsp->busycount, dsp->historicsilence + DSP_HISTORY - dsp->busycount + 1, dsp->busycount*sizeof(dsp->historicsilence[0]));
01121 dsp->historicsilence[DSP_HISTORY - 1] = dsp->totalsilence;
01122
01123 if (silence1 < silence2) {
01124 if (silence1 + silence1*BUSY_PERCENT/100 >= silence2)
01125 dsp->busymaybe = 1;
01126 else
01127 dsp->busymaybe = 0;
01128 } else {
01129 if (silence1 - silence1*BUSY_PERCENT/100 <= silence2)
01130 dsp->busymaybe = 1;
01131 else
01132 dsp->busymaybe = 0;
01133 }
01134 }
01135 dsp->totalsilence = 0;
01136 }
01137 if (totalsilence)
01138 *totalsilence = dsp->totalsilence;
01139 if (totalnoise)
01140 *totalnoise = dsp->totalnoise;
01141 return res;
01142 }
01143
01144 int ast_dsp_busydetect(struct ast_dsp *dsp)
01145 {
01146 int res = 0, x;
01147 #ifndef BUSYDETECT_TONEONLY
01148 int avgsilence = 0, hitsilence = 0;
01149 #endif
01150 int avgtone = 0, hittone = 0;
01151 if (!dsp->busymaybe)
01152 return res;
01153 for (x=DSP_HISTORY - dsp->busycount;x<DSP_HISTORY;x++) {
01154 #ifndef BUSYDETECT_TONEONLY
01155 avgsilence += dsp->historicsilence[x];
01156 #endif
01157 avgtone += dsp->historicnoise[x];
01158 }
01159 #ifndef BUSYDETECT_TONEONLY
01160 avgsilence /= dsp->busycount;
01161 #endif
01162 avgtone /= dsp->busycount;
01163 for (x=DSP_HISTORY - dsp->busycount;x<DSP_HISTORY;x++) {
01164 #ifndef BUSYDETECT_TONEONLY
01165 if (avgsilence > dsp->historicsilence[x]) {
01166 if (avgsilence - (avgsilence*BUSY_PERCENT/100) <= dsp->historicsilence[x])
01167 hitsilence++;
01168 } else {
01169 if (avgsilence + (avgsilence*BUSY_PERCENT/100) >= dsp->historicsilence[x])
01170 hitsilence++;
01171 }
01172 #endif
01173 if (avgtone > dsp->historicnoise[x]) {
01174 if (avgtone - (avgtone*BUSY_PERCENT/100) <= dsp->historicnoise[x])
01175 hittone++;
01176 } else {
01177 if (avgtone + (avgtone*BUSY_PERCENT/100) >= dsp->historicnoise[x])
01178 hittone++;
01179 }
01180 }
01181 #ifndef BUSYDETECT_TONEONLY
01182 if ((hittone >= dsp->busycount - 1) && (hitsilence >= dsp->busycount - 1) &&
01183 (avgtone >= BUSY_MIN && avgtone <= BUSY_MAX) &&
01184 (avgsilence >= BUSY_MIN && avgsilence <= BUSY_MAX)) {
01185 #else
01186 if ((hittone >= dsp->busycount - 1) && (avgtone >= BUSY_MIN && avgtone <= BUSY_MAX)) {
01187 #endif
01188 #ifdef BUSYDETECT_COMPARE_TONE_AND_SILENCE
01189 if (avgtone > avgsilence) {
01190 if (avgtone - avgtone*BUSY_PERCENT/100 <= avgsilence)
01191 res = 1;
01192 } else {
01193 if (avgtone + avgtone*BUSY_PERCENT/100 >= avgsilence)
01194 res = 1;
01195 }
01196 #else
01197 res = 1;
01198 #endif
01199 }
01200
01201 if (res && (dsp->busy_tonelength > 0)) {
01202 if (abs(avgtone - dsp->busy_tonelength) > (dsp->busy_tonelength*BUSY_PAT_PERCENT/100)) {
01203 #ifdef BUSYDETECT_DEBUG
01204 ast_debug(5, "busy detector: avgtone of %d not close enough to desired %d\n",
01205 avgtone, dsp->busy_tonelength);
01206 #endif
01207 res = 0;
01208 }
01209 }
01210 #ifndef BUSYDETECT_TONEONLY
01211
01212 if (res && (dsp->busy_quietlength > 0)) {
01213 if (abs(avgsilence - dsp->busy_quietlength) > (dsp->busy_quietlength*BUSY_PAT_PERCENT/100)) {
01214 #ifdef BUSYDETECT_DEBUG
01215 ast_debug(5, "busy detector: avgsilence of %d not close enough to desired %d\n",
01216 avgsilence, dsp->busy_quietlength);
01217 #endif
01218 res = 0;
01219 }
01220 }
01221 #endif
01222 #if !defined(BUSYDETECT_TONEONLY) && defined(BUSYDETECT_DEBUG)
01223 if (res) {
01224 ast_debug(5, "ast_dsp_busydetect detected busy, avgtone: %d, avgsilence %d\n", avgtone, avgsilence);
01225 } else {
01226 ast_debug(5, "busy detector: FAILED with avgtone: %d, avgsilence %d\n", avgtone, avgsilence);
01227 }
01228 #endif
01229 return res;
01230 }
01231
01232 int ast_dsp_silence(struct ast_dsp *dsp, struct ast_frame *f, int *totalsilence)
01233 {
01234 short *s;
01235 int len;
01236
01237 if (f->frametype != AST_FRAME_VOICE) {
01238 ast_log(LOG_WARNING, "Can't calculate silence on a non-voice frame\n");
01239 return 0;
01240 }
01241 if (f->subclass != AST_FORMAT_SLINEAR) {
01242 ast_log(LOG_WARNING, "Can only calculate silence on signed-linear frames :(\n");
01243 return 0;
01244 }
01245 s = f->data.ptr;
01246 len = f->datalen/2;
01247 return __ast_dsp_silence_noise(dsp, s, len, totalsilence, NULL);
01248 }
01249
01250 int ast_dsp_noise(struct ast_dsp *dsp, struct ast_frame *f, int *totalnoise)
01251 {
01252 short *s;
01253 int len;
01254
01255 if (f->frametype != AST_FRAME_VOICE) {
01256 ast_log(LOG_WARNING, "Can't calculate noise on a non-voice frame\n");
01257 return 0;
01258 }
01259 if (f->subclass != AST_FORMAT_SLINEAR) {
01260 ast_log(LOG_WARNING, "Can only calculate noise on signed-linear frames :(\n");
01261 return 0;
01262 }
01263 s = f->data.ptr;
01264 len = f->datalen/2;
01265 return __ast_dsp_silence_noise(dsp, s, len, NULL, totalnoise);
01266 }
01267
01268
01269 struct ast_frame *ast_dsp_process(struct ast_channel *chan, struct ast_dsp *dsp, struct ast_frame *af)
01270 {
01271 int silence;
01272 int res;
01273 int digit = 0, fax_digit = 0;
01274 int x;
01275 short *shortdata;
01276 unsigned char *odata;
01277 int len;
01278 struct ast_frame *outf = NULL;
01279
01280 if (!af)
01281 return NULL;
01282 if (af->frametype != AST_FRAME_VOICE)
01283 return af;
01284
01285 odata = af->data.ptr;
01286 len = af->datalen;
01287
01288 switch (af->subclass) {
01289 case AST_FORMAT_SLINEAR:
01290 shortdata = af->data.ptr;
01291 len = af->datalen / 2;
01292 break;
01293 case AST_FORMAT_ULAW:
01294 shortdata = alloca(af->datalen * 2);
01295 for (x = 0;x < len; x++)
01296 shortdata[x] = AST_MULAW(odata[x]);
01297 break;
01298 case AST_FORMAT_ALAW:
01299 shortdata = alloca(af->datalen * 2);
01300 for (x = 0; x < len; x++)
01301 shortdata[x] = AST_ALAW(odata[x]);
01302 break;
01303 default:
01304 ast_log(LOG_WARNING, "Inband DTMF is not supported on codec %s. Use RFC2833\n", ast_getformatname(af->subclass));
01305 return af;
01306 }
01307
01308
01309 dsp->mute_fragments = 0;
01310
01311
01312 if ((dsp->features & DSP_FEATURE_SILENCE_SUPPRESS) || (dsp->features & DSP_FEATURE_BUSY_DETECT)) {
01313 res = __ast_dsp_silence_noise(dsp, shortdata, len, &silence, NULL);
01314 }
01315
01316 if ((dsp->features & DSP_FEATURE_SILENCE_SUPPRESS) && silence) {
01317 memset(&dsp->f, 0, sizeof(dsp->f));
01318 dsp->f.frametype = AST_FRAME_NULL;
01319 ast_frfree(af);
01320 ast_set_flag(&dsp->f, AST_FRFLAG_FROM_DSP);
01321 return &dsp->f;
01322 }
01323 if ((dsp->features & DSP_FEATURE_BUSY_DETECT) && ast_dsp_busydetect(dsp)) {
01324 chan->_softhangup |= AST_SOFTHANGUP_DEV;
01325 memset(&dsp->f, 0, sizeof(dsp->f));
01326 dsp->f.frametype = AST_FRAME_CONTROL;
01327 dsp->f.subclass = AST_CONTROL_BUSY;
01328 ast_frfree(af);
01329 ast_debug(1, "Requesting Hangup because the busy tone was detected on channel %s\n", chan->name);
01330 ast_set_flag(&dsp->f, AST_FRFLAG_FROM_DSP);
01331 return &dsp->f;
01332 }
01333
01334 if ((dsp->features & DSP_FEATURE_FAX_DETECT)) {
01335 if ((dsp->faxmode & DSP_FAXMODE_DETECT_CNG) && tone_detect(dsp, &dsp->cng_tone_state, shortdata, len)) {
01336 fax_digit = 'f';
01337 }
01338
01339 if ((dsp->faxmode & DSP_FAXMODE_DETECT_CED) && tone_detect(dsp, &dsp->ced_tone_state, shortdata, len)) {
01340 fax_digit = 'e';
01341 }
01342 }
01343
01344 if ((dsp->features & DSP_FEATURE_DIGIT_DETECT)) {
01345 if ((dsp->digitmode & DSP_DIGITMODE_MF))
01346 digit = mf_detect(dsp, &dsp->digit_state, shortdata, len, (dsp->digitmode & DSP_DIGITMODE_NOQUELCH) == 0, (dsp->digitmode & DSP_DIGITMODE_RELAXDTMF));
01347 else
01348 digit = dtmf_detect(dsp, &dsp->digit_state, shortdata, len, (dsp->digitmode & DSP_DIGITMODE_NOQUELCH) == 0, (dsp->digitmode & DSP_DIGITMODE_RELAXDTMF));
01349
01350 if (dsp->digit_state.current_digits) {
01351 int event = 0;
01352 char event_digit = 0;
01353
01354 if (!dsp->dtmf_began) {
01355
01356
01357 event = AST_FRAME_DTMF_BEGIN;
01358 event_digit = dsp->digit_state.digits[0];
01359 dsp->dtmf_began = 1;
01360
01361 } else if (dsp->digit_state.current_digits > 1 || digit != dsp->digit_state.digits[0]) {
01362
01363
01364 event = AST_FRAME_DTMF_END;
01365 event_digit = dsp->digit_state.digits[0];
01366 memmove(dsp->digit_state.digits, dsp->digit_state.digits + 1, dsp->digit_state.current_digits);
01367 dsp->digit_state.current_digits--;
01368 dsp->dtmf_began = 0;
01369 }
01370
01371 if (event) {
01372 memset(&dsp->f, 0, sizeof(dsp->f));
01373 dsp->f.frametype = event;
01374 dsp->f.subclass = event_digit;
01375 outf = &dsp->f;
01376 goto done;
01377 }
01378 }
01379 }
01380
01381 if (fax_digit) {
01382
01383
01384 memset(&dsp->f, 0, sizeof(dsp->f));
01385 dsp->f.frametype = AST_FRAME_DTMF;
01386 dsp->f.subclass = fax_digit;
01387 outf = &dsp->f;
01388 goto done;
01389 }
01390
01391 if ((dsp->features & DSP_FEATURE_CALL_PROGRESS)) {
01392 res = __ast_dsp_call_progress(dsp, shortdata, len);
01393 if (res) {
01394 switch (res) {
01395 case AST_CONTROL_ANSWER:
01396 case AST_CONTROL_BUSY:
01397 case AST_CONTROL_RINGING:
01398 case AST_CONTROL_CONGESTION:
01399 case AST_CONTROL_HANGUP:
01400 memset(&dsp->f, 0, sizeof(dsp->f));
01401 dsp->f.frametype = AST_FRAME_CONTROL;
01402 dsp->f.subclass = res;
01403 dsp->f.src = "dsp_progress";
01404 if (chan)
01405 ast_queue_frame(chan, &dsp->f);
01406 break;
01407 default:
01408 ast_log(LOG_WARNING, "Don't know how to represent call progress message %d\n", res);
01409 }
01410 }
01411 }
01412
01413 done:
01414
01415 for (x = 0; x < dsp->mute_fragments; x++) {
01416 memset(shortdata + dsp->mute_data[x].start, 0, sizeof(int16_t) * (dsp->mute_data[x].end - dsp->mute_data[x].start));
01417 }
01418
01419 switch (af->subclass) {
01420 case AST_FORMAT_SLINEAR:
01421 break;
01422 case AST_FORMAT_ULAW:
01423 for (x = 0; x < len; x++)
01424 odata[x] = AST_LIN2MU((unsigned short) shortdata[x]);
01425 break;
01426 case AST_FORMAT_ALAW:
01427 for (x = 0; x < len; x++)
01428 odata[x] = AST_LIN2A((unsigned short) shortdata[x]);
01429 break;
01430 }
01431
01432 if (outf) {
01433 if (chan)
01434 ast_queue_frame(chan, af);
01435 ast_frfree(af);
01436 ast_set_flag(outf, AST_FRFLAG_FROM_DSP);
01437 return outf;
01438 } else {
01439 return af;
01440 }
01441 }
01442
01443 static void ast_dsp_prog_reset(struct ast_dsp *dsp)
01444 {
01445 int max = 0;
01446 int x;
01447
01448 dsp->gsamp_size = modes[dsp->progmode].size;
01449 dsp->gsamps = 0;
01450 for (x = 0; x < ARRAY_LEN(modes[dsp->progmode].freqs); x++) {
01451 if (modes[dsp->progmode].freqs[x]) {
01452 goertzel_init(&dsp->freqs[x], (float)modes[dsp->progmode].freqs[x], dsp->gsamp_size);
01453 max = x + 1;
01454 }
01455 }
01456 dsp->freqcount = max;
01457 dsp->ringtimeout= 0;
01458 }
01459
01460 struct ast_dsp *ast_dsp_new(void)
01461 {
01462 struct ast_dsp *dsp;
01463
01464 if ((dsp = ast_calloc(1, sizeof(*dsp)))) {
01465 dsp->threshold = DEFAULT_THRESHOLD;
01466 dsp->features = DSP_FEATURE_SILENCE_SUPPRESS;
01467 dsp->busycount = DSP_HISTORY;
01468 dsp->digitmode = DSP_DIGITMODE_DTMF;
01469 dsp->faxmode = DSP_FAXMODE_DETECT_CNG;
01470
01471 ast_digit_detect_init(&dsp->digit_state, dsp->digitmode & DSP_DIGITMODE_MF);
01472
01473 ast_dsp_prog_reset(dsp);
01474
01475 ast_fax_detect_init(dsp);
01476 }
01477 return dsp;
01478 }
01479
01480 void ast_dsp_set_features(struct ast_dsp *dsp, int features)
01481 {
01482 dsp->features = features;
01483 }
01484
01485 void ast_dsp_free(struct ast_dsp *dsp)
01486 {
01487 if (ast_test_flag(&dsp->f, AST_FRFLAG_FROM_DSP)) {
01488
01489
01490
01491
01492
01493 dsp->destroy = 1;
01494
01495 return;
01496 }
01497 ast_free(dsp);
01498 }
01499
01500 void ast_dsp_set_threshold(struct ast_dsp *dsp, int threshold)
01501 {
01502 dsp->threshold = threshold;
01503 }
01504
01505 void ast_dsp_set_busy_count(struct ast_dsp *dsp, int cadences)
01506 {
01507 if (cadences < 4)
01508 cadences = 4;
01509 if (cadences > DSP_HISTORY)
01510 cadences = DSP_HISTORY;
01511 dsp->busycount = cadences;
01512 }
01513
01514 void ast_dsp_set_busy_pattern(struct ast_dsp *dsp, int tonelength, int quietlength)
01515 {
01516 dsp->busy_tonelength = tonelength;
01517 dsp->busy_quietlength = quietlength;
01518 ast_debug(1, "dsp busy pattern set to %d,%d\n", tonelength, quietlength);
01519 }
01520
01521 void ast_dsp_digitreset(struct ast_dsp *dsp)
01522 {
01523 int i;
01524
01525 dsp->dtmf_began = 0;
01526 if (dsp->digitmode & DSP_DIGITMODE_MF) {
01527 mf_detect_state_t *s = &dsp->digit_state.td.mf;
01528
01529 for (i = 0; i < 6; i++) {
01530 goertzel_reset(&s->tone_out[i]);
01531 }
01532 s->hits[4] = s->hits[3] = s->hits[2] = s->hits[1] = s->hits[0] = s->current_hit = 0;
01533 s->current_sample = 0;
01534 } else {
01535 dtmf_detect_state_t *s = &dsp->digit_state.td.dtmf;
01536
01537 for (i = 0; i < 4; i++) {
01538 goertzel_reset(&s->row_out[i]);
01539 goertzel_reset(&s->col_out[i]);
01540 }
01541 s->lasthit = s->current_hit = 0;
01542 s->energy = 0.0;
01543 s->current_sample = 0;
01544 s->hits = 0;
01545 s->misses = 0;
01546 }
01547
01548 dsp->digit_state.digits[0] = '\0';
01549 dsp->digit_state.current_digits = 0;
01550 }
01551
01552 void ast_dsp_reset(struct ast_dsp *dsp)
01553 {
01554 int x;
01555
01556 dsp->totalsilence = 0;
01557 dsp->gsamps = 0;
01558 for (x=0;x<4;x++)
01559 dsp->freqs[x].v2 = dsp->freqs[x].v3 = 0.0;
01560 memset(dsp->historicsilence, 0, sizeof(dsp->historicsilence));
01561 memset(dsp->historicnoise, 0, sizeof(dsp->historicnoise));
01562 dsp->ringtimeout= 0;
01563 }
01564
01565 int ast_dsp_set_digitmode(struct ast_dsp *dsp, int digitmode)
01566 {
01567 int new;
01568 int old;
01569
01570 old = dsp->digitmode & (DSP_DIGITMODE_DTMF | DSP_DIGITMODE_MF | DSP_DIGITMODE_MUTECONF | DSP_DIGITMODE_MUTEMAX);
01571 new = digitmode & (DSP_DIGITMODE_DTMF | DSP_DIGITMODE_MF | DSP_DIGITMODE_MUTECONF | DSP_DIGITMODE_MUTEMAX);
01572 if (old != new) {
01573
01574 ast_digit_detect_init(&dsp->digit_state, new & DSP_DIGITMODE_MF);
01575 }
01576 dsp->digitmode = digitmode;
01577 return 0;
01578 }
01579
01580 int ast_dsp_set_faxmode(struct ast_dsp *dsp, int faxmode)
01581 {
01582 if (dsp->faxmode != faxmode) {
01583 ast_fax_detect_init(dsp);
01584 }
01585 dsp->faxmode = faxmode;
01586 return 0;
01587 }
01588
01589 int ast_dsp_set_call_progress_zone(struct ast_dsp *dsp, char *zone)
01590 {
01591 int x;
01592
01593 for (x = 0; x < ARRAY_LEN(aliases); x++) {
01594 if (!strcasecmp(aliases[x].name, zone)) {
01595 dsp->progmode = aliases[x].mode;
01596 ast_dsp_prog_reset(dsp);
01597 return 0;
01598 }
01599 }
01600 return -1;
01601 }
01602
01603 int ast_dsp_was_muted(struct ast_dsp *dsp)
01604 {
01605 return (dsp->mute_fragments > 0);
01606 }
01607
01608 int ast_dsp_get_tstate(struct ast_dsp *dsp)
01609 {
01610 return dsp->tstate;
01611 }
01612
01613 int ast_dsp_get_tcount(struct ast_dsp *dsp)
01614 {
01615 return dsp->tcount;
01616 }
01617
01618 static int _dsp_init(int reload)
01619 {
01620 struct ast_flags config_flags = { reload ? CONFIG_FLAG_FILEUNCHANGED : 0 };
01621 struct ast_config *cfg;
01622
01623 cfg = ast_config_load2(CONFIG_FILE_NAME, "dsp", config_flags);
01624
01625 if (cfg && cfg != CONFIG_STATUS_FILEUNCHANGED) {
01626 const char *value;
01627
01628 value = ast_variable_retrieve(cfg, "default", "silencethreshold");
01629 if (value && sscanf(value, "%30d", &thresholds[THRESHOLD_SILENCE]) != 1) {
01630 ast_log(LOG_WARNING, "%s: '%s' is not a valid silencethreshold value\n", CONFIG_FILE_NAME, value);
01631 thresholds[THRESHOLD_SILENCE] = 256;
01632 } else if (!value)
01633 thresholds[THRESHOLD_SILENCE] = 256;
01634
01635 ast_config_destroy(cfg);
01636 }
01637 return 0;
01638 }
01639
01640 int ast_dsp_get_threshold_from_settings(enum threshold which)
01641 {
01642 return thresholds[which];
01643 }
01644
01645 int ast_dsp_init(void)
01646 {
01647 return _dsp_init(0);
01648 }
01649
01650 int ast_dsp_reload(void)
01651 {
01652 return _dsp_init(1);
01653 }
01654
01655 void ast_dsp_frame_freed(struct ast_frame *fr)
01656 {
01657 struct ast_dsp *dsp;
01658
01659 ast_clear_flag(fr, AST_FRFLAG_FROM_DSP);
01660
01661 dsp = (struct ast_dsp *) (((char *) fr) - offsetof(struct ast_dsp, f));
01662
01663 if (!dsp->destroy)
01664 return;
01665
01666 ast_dsp_free(dsp);
01667 }