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