The World Institute for Mental Health recommends switching to the new
authorjm <jm@0101bb08-14d6-0310-b084-bc0e0c8e3800>
Thu, 26 Oct 2006 00:13:14 +0000 (00:13 +0000)
committerjm <jm@0101bb08-14d6-0310-b084-bc0e0c8e3800>
Thu, 26 Oct 2006 00:13:14 +0000 (00:13 +0000)
echo/preprocess API.

git-svn-id: http://svn.xiph.org/trunk/speex@11948 0101bb08-14d6-0310-b084-bc0e0c8e3800

include/speex/speex_preprocess.h
libspeex/mdf.c
libspeex/preprocess.c
libspeex/testdenoise.c
libspeex/testecho.c

index 2c76204..11888ba 100644 (file)
@@ -53,6 +53,9 @@ SpeexPreprocessState *speex_preprocess_state_init(int frame_size, int sampling_r
 void speex_preprocess_state_destroy(SpeexPreprocessState *st);
 
 /** Preprocess a frame */
+int speex_preprocess_run(SpeexPreprocessState *st, spx_int16_t *x);
+
+/** Preprocess a frame (deprecated) */
 int speex_preprocess(SpeexPreprocessState *st, spx_int16_t *x, spx_int32_t *echo);
 
 /** Preprocess a frame */
@@ -113,6 +116,9 @@ int speex_preprocess_ctl(SpeexPreprocessState *st, int request, void *ptr);
 #define SPEEX_PREPROCESS_SET_ECHO_SUPPRESS_ACTIVE 22
 #define SPEEX_PREPROCESS_GET_ECHO_SUPPRESS_ACTIVE 23
 
+#define SPEEX_PREPROCESS_SET_ECHO_STATE 24
+#define SPEEX_PREPROCESS_GET_ECHO_STATE 25
+
 #ifdef __cplusplus
 }
 #endif
index e62787f..fd7a4f0 100644 (file)
@@ -102,7 +102,7 @@ static const spx_float_t MIN_LEAK = .032f;
 #define TOP16(x) (x)
 #endif
 
-void speex_echo_get_residual(SpeexEchoState *st, spx_int32_t *Yout, int len);
+void speex_echo_get_residual(SpeexEchoState *st, spx_word32_t *Yout, int len);
 
 
 /** Speex echo cancellation state. */
@@ -126,7 +126,6 @@ struct SpeexEchoState_ {
    spx_word16_t *d;
    spx_word16_t *y;
    spx_word16_t *last_y;
-   spx_word32_t *Yps;
    spx_word16_t *Y;
    spx_word16_t *E;
    spx_word32_t *PHI;
@@ -303,7 +302,6 @@ SpeexEchoState *speex_echo_state_init(int frame_size, int filter_length)
    st->x = (spx_word16_t*)speex_alloc(N*sizeof(spx_word16_t));
    st->d = (spx_word16_t*)speex_alloc(N*sizeof(spx_word16_t));
    st->y = (spx_word16_t*)speex_alloc(N*sizeof(spx_word16_t));
-   st->Yps = (spx_word32_t*)speex_alloc(N*sizeof(spx_word32_t));
    st->last_y = (spx_word16_t*)speex_alloc(N*sizeof(spx_word16_t));
    st->Yf = (spx_word32_t*)speex_alloc((st->frame_size+1)*sizeof(spx_word32_t));
    st->Rf = (spx_word32_t*)speex_alloc((st->frame_size+1)*sizeof(spx_word32_t));
@@ -409,7 +407,6 @@ void speex_echo_state_destroy(SpeexEchoState *st)
    speex_free(st->d);
    speex_free(st->y);
    speex_free(st->last_y);
-   speex_free(st->Yps);
    speex_free(st->Yf);
    speex_free(st->Rf);
    speex_free(st->Xf);
@@ -471,7 +468,6 @@ void speex_echo_playback(SpeexEchoState *st, const spx_int16_t *play)
 void speex_echo_cancel(SpeexEchoState *st, const spx_int16_t *in, const spx_int16_t *far_end, spx_int16_t *out, spx_int32_t *Yout)
 {
    speex_echo_cancellation(st, in, far_end, out);
-   speex_echo_get_residual(st, Yout, 0);
 }
 
 /** Performs echo cancellation on a frame (deprecated, last arg now ignored) */
@@ -815,7 +811,7 @@ void speex_echo_cancellation(SpeexEchoState *st, const spx_int16_t *in, const sp
 }
 
 /* Compute spectrum of estimated echo for use in an echo post-filter */
-void speex_echo_get_residual(SpeexEchoState *st, spx_int32_t *Yout, int len)
+void speex_echo_get_residual(SpeexEchoState *st, spx_word32_t *residual_echo, int len)
 {
    int i;
    spx_word16_t leak2;
@@ -829,7 +825,7 @@ void speex_echo_get_residual(SpeexEchoState *st, spx_int32_t *Yout, int len)
       
    /* Compute power spectrum of the echo */
    spx_fft(st->fft_table, st->y, st->Y);
-   power_spectrum(st->Y, st->Yps, N);
+   power_spectrum(st->Y, residual_echo, N);
       
 #ifdef FIXED_POINT
    if (st->leak_estimate > 16383)
@@ -844,7 +840,7 @@ void speex_echo_get_residual(SpeexEchoState *st, spx_int32_t *Yout, int len)
 #endif
    /* Estimate residual echo */
    for (i=0;i<=st->frame_size;i++)
-      Yout[i] = (spx_int32_t)MULT16_32_Q15(leak2,st->Yps[i]);
+      residual_echo[i] = (spx_int32_t)MULT16_32_Q15(leak2,residual_echo[i]);
    
 }
 
index a1e7a6e..b79e3c0 100644 (file)
@@ -61,6 +61,7 @@
 
 #include <math.h>
 #include "speex/speex_preprocess.h"
+#include "speex/speex_echo.h"
 #include "misc.h"
 #include "fftwrap.h"
 #include "filterbank.h"
 #define ECHO_SUPPRESS_DEFAULT        -45
 #define ECHO_SUPPRESS_ACTIVE_DEFAULT -15
 
+#ifndef NULL
+#define NULL 0
+#endif
+
 /** Speex pre-processor state. */
 struct SpeexPreprocessState_ {
    /* Basic info */
@@ -104,6 +109,7 @@ struct SpeexPreprocessState_ {
    int    noise_suppress;
    int    echo_suppress;
    int    echo_suppress_active;
+   SpeexEchoState *echo_state;
    
    /* DSP-related arrays */
    float *frame;             /**< Processing frame (2*ps_size) */
@@ -129,6 +135,7 @@ struct SpeexPreprocessState_ {
    float *loudness_weight;   /**< Perceptual loudness curve */
 
    float *echo_noise;
+   spx_word32_t *residual_echo;
 
    /* Misc */
    float *inbuf;             /**< Input buffer (overlapped analysis) */
@@ -251,6 +258,8 @@ SpeexPreprocessState *speex_preprocess_state_init(int frame_size, int sampling_r
    st->speech_prob_start = SPEEX_PROB_START_DEFAULT;
    st->speech_prob_continue = SPEEX_PROB_CONTINUE_DEFAULT;
 
+   st->echo_state = NULL;
+   
    st->nbands = NB_BANDS;
    M = st->nbands;
    st->bank = filterbank_new(M, sampling_rate, N, 1);
@@ -262,6 +271,7 @@ SpeexPreprocessState *speex_preprocess_state_init(int frame_size, int sampling_r
    st->ps = (float*)speex_alloc((N+M)*sizeof(float));
    st->noise = (float*)speex_alloc((N+M)*sizeof(float));
    st->echo_noise = (float*)speex_alloc((N+M)*sizeof(float));
+   st->residual_echo = (spx_word32_t*)speex_alloc((N+M)*sizeof(float));
    st->reverb_estimate = (float*)speex_alloc((N+M)*sizeof(float));
    st->old_ps = (float*)speex_alloc((N+M)*sizeof(float));
    st->prior = (float*)speex_alloc((N+M)*sizeof(float));
@@ -347,6 +357,7 @@ void speex_preprocess_state_destroy(SpeexPreprocessState *st)
    speex_free(st->post);
    speex_free(st->loudness_weight);
    speex_free(st->echo_noise);
+   speex_free(st->residual_echo);
 
    speex_free(st->S);
    speex_free(st->Smin);
@@ -507,8 +518,15 @@ static void update_noise_prob(SpeexPreprocessState *st)
 
 #define NOISE_OVERCOMPENS 1.
 
+void speex_echo_get_residual(SpeexEchoState *st, spx_word32_t *Yout, int len);
+
 int speex_preprocess(SpeexPreprocessState *st, spx_int16_t *x, spx_int32_t *echo)
 {
+   return speex_preprocess_run(st, x);
+}
+
+int speex_preprocess_run(SpeexPreprocessState *st, spx_int16_t *x)
+{
    int i;
    int M;
    int N = st->ps_size;
@@ -529,10 +547,11 @@ int speex_preprocess(SpeexPreprocessState *st, spx_int16_t *x, spx_int32_t *echo
    beta_1 = 1.0f-beta;
    M = st->nbands;
    /* Deal with residual echo if provided */
-   if (echo)
+   if (st->echo_state)
    {
+      speex_echo_get_residual(st->echo_state, st->residual_echo, N);
       for (i=0;i<N;i++)
-         st->echo_noise[i] = MAX32(.6f*st->echo_noise[i], echo[i]);
+         st->echo_noise[i] = MAX32(.6f*st->echo_noise[i], st->residual_echo[i]);
       filterbank_compute_bank(st->bank, st->echo_noise, st->echo_noise+N);
    } else {
       for (i=0;i<N+M;i++)
@@ -891,6 +910,12 @@ int speex_preprocess_ctl(SpeexPreprocessState *state, int request, void *ptr)
    case SPEEX_PREPROCESS_GET_ECHO_SUPPRESS_ACTIVE:
       (*(spx_int32_t*)ptr) = st->echo_suppress_active;
       break;
+   case SPEEX_PREPROCESS_SET_ECHO_STATE:
+      st->echo_state = (SpeexEchoState*)ptr;
+      break;
+   case SPEEX_PREPROCESS_GET_ECHO_STATE:
+      ptr = (void*)st->echo_state;
+      break;
 
    default:
       speex_warning_int("Unknown speex_preprocess_ctl request: ", request);
index 177227d..42644cb 100644 (file)
@@ -24,9 +24,9 @@ int main()
    speex_preprocess_ctl(st, SPEEX_PREPROCESS_SET_AGC_LEVEL, &f);
    i=0;
    speex_preprocess_ctl(st, SPEEX_PREPROCESS_SET_DEREVERB, &i);
-   f=.4;
+   f=.0;
    speex_preprocess_ctl(st, SPEEX_PREPROCESS_SET_DEREVERB_DECAY, &f);
-   f=.3;
+   f=.0;
    speex_preprocess_ctl(st, SPEEX_PREPROCESS_SET_DEREVERB_LEVEL, &f);
    while (1)
    {
@@ -34,7 +34,7 @@ int main()
       fread(in, sizeof(short), NN, stdin);
       if (feof(stdin))
          break;
-      vad = speex_preprocess(st, in, NULL);
+      vad = speex_preprocess_run(st, in);
       /*fprintf (stderr, "%d\n", vad);*/
       fwrite(in, sizeof(short), NN, stdout);
       count++;
index f78499e..7c32c8f 100644 (file)
@@ -18,7 +18,6 @@
 int main(int argc, char **argv)
 {
    int echo_fd, ref_fd, e_fd;
-   spx_int32_t noise[NN+1];
    short echo_buf[NN], ref_buf[NN], e_buf[NN];
    SpeexEchoState *st;
    SpeexPreprocessState *den;
@@ -36,12 +35,13 @@ int main(int argc, char **argv)
    den = speex_preprocess_state_init(NN, 8000);
    int tmp = 8000;
    speex_echo_ctl(st, SPEEX_ECHO_SET_SAMPLING_RATE, &tmp);
+   speex_preprocess_ctl(den, SPEEX_PREPROCESS_SET_ECHO_STATE, st);
 
    while (read(ref_fd, ref_buf, NN*2))
    {
       read(echo_fd, echo_buf, NN*2);
-      speex_echo_cancel(st, ref_buf, echo_buf, e_buf, noise);
-      /*speex_preprocess(den, e_buf, noise);*/
+      speex_echo_cancellation(st, ref_buf, echo_buf, e_buf);
+      speex_preprocess_run(den, e_buf);
       write(e_fd, e_buf, NN*2);
    }
    speex_echo_state_destroy(st);