--- app_amd.c.orig 2019-11-05 12:25:39.314658000 -0500 +++ app_amd.c 2019-11-05 12:34:20.578154550 -0500 @@ -277,6 +277,9 @@ /* Set silence threshold to specified value */ ast_dsp_set_threshold(silenceDetector, silenceThreshold); + /* Set our start time so we can tie the loop to real world time and not RTP updates */ + struct timeval amd_tvstart = ast_tvnow(); + /* Now we go into a loop waiting for frames from the channel */ while ((res = ast_waitfor(chan, 2 * maxWaitTimeForFrame)) > -1) { int ms = 0; @@ -295,7 +298,21 @@ break; } - if (f->frametype == AST_FRAME_VOICE || f->frametype == AST_FRAME_NULL || f->frametype == AST_FRAME_CNG) { + /* Check to make sure we haven't gone over our real-world timeout in case frames get stalled for whatever reason */ + if ( (ast_tvdiff_ms(ast_tvnow(), amd_tvstart)) > totalAnalysisTime ) { + ast_frfree(f); + strcpy(amdStatus , "NOTSURE"); + if ( audioFrameCount == 0 ) { + ast_verb(3, "AMD: Channel [%s]. No audio date recieved in [%d] seconds.\n", ast_channel_name(chan), totalAnalysisTime); + sprintf(amdCause , "NOAUDIODATA-%d", iTotalTime); + break; + } + ast_verb(3, "AMD: Channel [%s]. Timeout...\n", ast_channel_name(chan)); + sprintf(amdCause , "TOOLONG-%d", iTotalTime); + break; + } + + if (f->frametype == AST_FRAME_VOICE || f->frametype == AST_FRAME_CNG) { /* Figure out how long the frame is in milliseconds */ if (f->frametype == AST_FRAME_VOICE) { framelength = (ast_codec_samples_count(f) / DEFAULT_SAMPLES_PER_MS);