This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

TI AER - Algorithm details

I have a few questions regarding the TI AER algorithm :

1) We are currently getting into an issue where TI AER algorithm switches to bypass mode and does not cancel any echo. We have set tail length to 200ms and y2x_delay to 20ms. We do see number of underruns happening in our system (issue under investigation) however these underruns causing TI AER algorithm to switch to bypass mode. We compare this algorithm with another open source SPEEX algorithm does diverge at those underruns but converges quickly after some time. Our understanding is this is primarily due to variable tap adaptive filter delay implementation of TI AER comapred to fixed tap adaptive filter on SPEEX. AER sets initial tail length to 60ms and only increases it by additional 20ms if there is significant energy in those segments? Our question is there a way to set that initial tail length to > 60ms on TI AER algorithm. Attached is bypass.png file in ZIP File that shows waveforms of receiveinref (-6dBm random noise), receiveout (speaker output), sendin (capture signal) and sendout( AER processed signal). As you can see AER switches to bypass mode around 4second.

2) Another issue we are seeing is slow convergence of TI AER algorithm compared to SPEEX. This happens not everytime but only certain runs. Attached is slowconvergence.png file where the top waveform shows sendout signal of TI AER processed signal and the bottom waveform shows sendout signal of SPEEX (open source AEC) processed signal. As you can see TI AER converges very slowly for divergence happening around 750ms while TI SPEEX converges very quickly. Any pointers on what could cause such behavior? IF TI AER tail lenght is set to 60ms initially compared to SPEEX which has fixed tap implementation, we would expect TI AER to converge much faster than SPEEX.

Please note we are using minimal AER configuration with all other components disabled (NLP, DRC, etc).

Thanks in advance for your inputs. 

AERsnapshots.zip
  • Hi,

    Yes, there is a way to set the initial tail length to be the same as the total length. Please refer to aer.h and search for aer_CTL1_INCREASE_MIN_HVEC. However, this would slow down the convergence.

    To have good convergence, you'll need to understand your system delay from Rx out to Send in, and then configure y2x_delay properly. Since you set y2x_delay to 20ms, is it possible for the system to become non-causal when underruns/overruns happen? Do you have a rough idea how much your system delay is?

    If system remains causal when underruns/overruns happen, AER will lose convergence but will reconverge. The speed of reconvergence depends on coherence detection. When AER sees poor cancellation, it will look for coherence between Rx and Tx signals. If it decides there is coherence, it will reconverge from 60msec and the reconvergence should be fast. The parameters for coherence detection are: coh_ratio_thresh and coh_cnt_thresh. Please refer to aer.h for more information.

    The best way to maintain stable convergence is to prevent overruns or underruns. AER is designed to run in a deterministic and synchronized framework.

    Regards,

    Jianzhong

  • Hi Jianzhong,

     

    Thanks a ton for your response.

     

    We are having an issue with the alsa driver in our system, where in the y2x delay is changing by ~5 samples (@16KHz) at specific time of 720/1440 ms for 16/8KHz sampling rates randomly after starting the input and output streams. AER is diverging and re converging very slowly after this event. We measured the change in y2x delay using the method you described, i.e., dumping the first 20msec of the filter coefficients before divergence (@600ms) and after re-convergence (@ 40 seconds)  and finding the peak filter coefficient position using optdl tool. 

    We understand that the right solution would be to fix the issue in the alsa driver, but we've not been able to find out the root cause yet. And on the workaround, the right thing would be to adjust the y2x delay if it's occurring always, but it is not, it's highly random. So, for now, we're thinking of protecting aer from diverging as a workarouund. Towards this, we found that AER is re converging quickly, similar to the initial convergence if everything is cleared (aer_CTL0_CLEAR_ALL) just after the change in y2x delay . We believe the right approach here is to clear only the filter coefficients and delay line. But we're not finding any option to clear the delay line.  Please let us know if there's a better way to handle this scenario. 

    Do you think we should work around the above issue either by increasing the minimum tail to total tail length, which effectively increases the convergence time (and reduces the divergence severity) or modifying the coherence detection parameters, some how the latter does not seem to be the right approach for us. Please let us know your thoughts on this. 

    On the minimum tail length, we tried changing it to total tail length as you described, but it's not working. Here's the control code that we used for the same. 

        memset (&aer_ctl, 0x0, sizeof(aer_ctl));
        aer_ctl.valid_bitfield_0 =   aer_CTL_VALID0_MODES_CTL1;
        aer_ctl.modes_1.mask  = aer_CTL1_INCREASE_MIN_HVEC; 
        aer_ctl.modes_1.value = aer_CTL1_INCREASE_MIN_HVEC; 
        if (aerControl (haerObject->hHf.aer, &aer_ctl) != aer_NOERR) {
            printf("AER parameters configuration error!\n");
            exit(0);
        }      

    But somehow, the min hvec length continues to be at 3 vectors only, verified it by using the following code 

            aerGetFilter(haerObject->hHf.aer, &tail_model, coeff, 0, 0);
            {
                static int num_H_vec = 0;
                if (tail_model.num_H_vec != num_H_vec) {
                    printf("Frame No: %d num_H_vec %d \n", frameNo, tail_model.num_H_vec);
                    num_H_vec = tail_model.num_H_vec;
                }
            }   

    Please let us know if you find any mistake in the above control code. We came across a note in the aer.h that this is applicable only for non-handsfree modes, please confirm. 

     

    Prateek

     

  • Hi Prateek,

    Does the delay change only once at 720/1440 ms after starting the input and output streams? If that's the case, issuing aer_CTL0_CLEAR_ALL after 720/1440 ms is okay. However on the other hand, if the delay changes randomly at any time, then no workaround would be sufficient to ensure good AER performance.

    Yes, you can just reset the filter and delay line instead of doing CLEAR_ALL. Filter can be reset by aer_CTL0_CLEAR_FILTER. Delay line can be cleared by aer_CTL1_PARTIAL_RESET. However, doing this doesn't give you the same reconvergence speed since convergence control is not reset.

    If your delay only changes by 5 samples, then there is no need to increase your minimum tail length. I inspected the code and identified a bug that made the aer_CTL1_INCREASE_MIN_HVEC API broken. That's why you didn't see num_H_vec changing. But anyways, you don't have to continue on this road.

    Regards,

    Jianzhong

  • Thanks Jianzhong. We see this issue only once and we were able to use CLEAR_ALL to address the same.

    TI AEC is working fine except for one issue that we constantly come across - here are the details:

    We are observing a very strange issue with TI AER , our application quits randomly with "Floating point exception" message printed on the terminal and nothing else. The issue seems to occur with the TI AER only and we've never seen this occurring with Speex echo canceller. 

    We did try several experiments and found a way to consistently reproduce the issue within 30 to 40 seconds from the beginning of a call. The issue is observed quickly when the far end (Rin) is silent and the near end active from the beginning of a call. We used an audio player to keep the near end always active. 

    We're just wondering if there's any operation inside aer that would cause the floating point exception for the scenario described above. 

    We're very close to our product production schedule, would appreciate very much if you could help us to resolve this issue soon.

  • What version of AER are you using? There was a bug that caused this kind of problem in AER 16.0.0.1 and it was fixed in latest release - 16.1.0.3. Please download the latest AER and give it a try. There are some minor changes in API from 16.0.x to 16.1.x, so you'll need to change your source code.

    Regards,

    Jianzhong

  • Hi Jianzhong,

    Thanks a ton for your quick reply. Yes, we are using older version 16.0.0.1. We will go ahead and download latest AER release version 16.1.0.3. I put in approval request for the same and would appreciate if you can help with expediting the same. Thanks again.

    Regards,

    Prateek