diff --git a/src/audio/google/Kconfig b/src/audio/google/Kconfig index 67d9a29171ac..f5bdfe033a1b 100644 --- a/src/audio/google/Kconfig +++ b/src/audio/google/Kconfig @@ -15,7 +15,6 @@ config COMP_GOOGLE_HOTWORD_DETECT config COMP_GOOGLE_RTC_AUDIO_PROCESSING bool "Google Real Time Communication Audio processing" select COMP_BLOB - select GOOGLE_RTC_AUDIO_PROCESSING_MOCK if COMP_STUBS default n help Select for Google real-time communication audio processing. It @@ -24,13 +23,7 @@ config COMP_GOOGLE_RTC_AUDIO_PROCESSING This component takes raw microphones input and playback reference and outputs an echo-free microphone signal. -config COMP_GOOGLE_RTC_USE_32_BIT_FLOAT_API - depends on COMP_GOOGLE_RTC_AUDIO_PROCESSING - bool "Use 32bit API in Google Audio processing" - default n - help - Selects an API to be used in communication with the Google real-time - communication audio processing: 32bit float or 16bit integer +if COMP_GOOGLE_RTC_AUDIO_PROCESSING config COMP_GOOGLE_RTC_AUDIO_PROCESSING_SAMPLE_RATE_HZ depends on COMP_GOOGLE_RTC_AUDIO_PROCESSING @@ -61,10 +54,10 @@ config COMP_GOOGLE_RTC_AUDIO_REFERENCE_CHANNEL_MAX retrieved at runtime, but channels higher than this number are ignored -config COMP_GOOGLE_RTC_AUDIO_PROCESSING_MEMORY_BUFFER_SIZE_BYTES +config COMP_GOOGLE_RTC_AUDIO_PROCESSING_MEMORY_BUFFER_SIZE_KB depends on COMP_GOOGLE_RTC_AUDIO_PROCESSING int "Memory buffer size for Google Real Time Communication Audio processing" - default 200000 + default 200 help Sets the size of the memory buffer for the Google real-time communication audio processing. @@ -87,10 +80,12 @@ config COMP_GOOGLE_RTC_AUDIO_PROCESSING_MIC_HEADROOM_LINEAR config GOOGLE_RTC_AUDIO_PROCESSING_MOCK bool "Google Real Time Communication Audio processing mock" - default n + default y if COMP_STUBS depends on COMP_GOOGLE_RTC_AUDIO_PROCESSING help Mock Google real-time communication audio processing. It allows for compilation check and basic audio flow checking. +endif # COMP_GOOGLE_RTC_AUDIO_PROCESSING + endmenu diff --git a/src/audio/google/google_rtc_audio_processing.c b/src/audio/google/google_rtc_audio_processing.c index e1121c253e10..0817ed4a8aa9 100644 --- a/src/audio/google/google_rtc_audio_processing.c +++ b/src/audio/google/google_rtc_audio_processing.c @@ -35,13 +35,23 @@ #include #include +/* Zephyr provides uncached memory for static variables on SMP, but we + * are single-core component and know we can safely use the cache for + * AEC work. XTOS SOF is cached by default, so stub the Zephyr API. + */ +#ifdef __ZEPHYR__ +#include +#else +#define sys_cache_cached_ptr_get(p) (p) +#define ALWAYS_INLINE inline __attribute__((always_inline)) +#endif + #include #include #include #define GOOGLE_RTC_AUDIO_PROCESSING_FREQENCY_TO_PERIOD_FRAMES 100 #define GOOGLE_RTC_NUM_INPUT_PINS 2 -#define GOOGLE_RTC_NUM_OUTPUT_PINS 1 LOG_MODULE_REGISTER(google_rtc_audio_processing, CONFIG_SOF_LOG_LEVEL); @@ -53,38 +63,41 @@ DECLARE_SOF_RT_UUID("google-rtc-audio-processing", google_rtc_audio_processing_u DECLARE_TR_CTX(google_rtc_audio_processing_tr, SOF_UUID(google_rtc_audio_processing_uuid), LOG_LEVEL_INFO); -struct google_rtc_audio_processing_comp_data { -#if CONFIG_IPC_MAJOR_4 - struct sof_ipc4_aec_config config; -#if CONFIG_COMP_GOOGLE_RTC_USE_32_BIT_FLOAT_API - float *aec_reference_buffer; - float *process_buffer; - float *aec_reference_buffer_ptrs[SOF_IPC_MAX_CHANNELS]; - float *process_buffer_ptrs[SOF_IPC_MAX_CHANNELS]; -#else /* CONFIG_COMP_GOOGLE_RTC_USE_32_BIT_FLOAT_API */ - int16_t *aec_reference_buffer; - int16_t *process_buffer; -#endif /* CONFIG_COMP_GOOGLE_RTC_USE_32_BIT_FLOAT_API */ +static __aligned(PLATFORM_DCACHE_ALIGN) +uint8_t aec_mem_blob[CONFIG_COMP_GOOGLE_RTC_AUDIO_PROCESSING_MEMORY_BUFFER_SIZE_KB * 1024]; -#else - int16_t *aec_reference_buffer; - int aec_reference_frame_index; - int16_t *raw_mic_buffer; - int raw_mic_buffer_frame_index; - int16_t *output_buffer; - int output_buffer_frame_index; -#endif +#define NUM_FRAMES (CONFIG_COMP_GOOGLE_RTC_AUDIO_PROCESSING_SAMPLE_RATE_HZ \ + / GOOGLE_RTC_AUDIO_PROCESSING_FREQENCY_TO_PERIOD_FRAMES) +#define CHAN_MAX CONFIG_COMP_GOOGLE_RTC_AUDIO_REFERENCE_CHANNEL_MAX + +static __aligned(PLATFORM_DCACHE_ALIGN) +float refoutbuf[CHAN_MAX][NUM_FRAMES]; + +static __aligned(PLATFORM_DCACHE_ALIGN) +float micbuf[CHAN_MAX][NUM_FRAMES]; + +struct google_rtc_audio_processing_comp_data { uint32_t num_frames; int num_aec_reference_channels; int num_capture_channels; GoogleRtcAudioProcessingState *state; - - uint8_t *memory_buffer; + float *raw_mic_buffers[CHAN_MAX]; + float *refout_buffers[CHAN_MAX]; + int buffered_frames; struct comp_data_blob_handler *tuning_handler; bool reconfigure; + bool last_ref_ok; int aec_reference_source; int raw_microphone_source; +#ifdef CONFIG_IPC_MAJOR_3 + struct comp_buffer *ref_comp_buffer; +#endif + int ref_framesz; + int cap_framesz; + void (*mic_copy)(struct sof_source *src, int frames, float **dst_bufs, int frame0); + void (*ref_copy)(struct sof_source *src, int frames, float **dst_bufs, int frame0); + void (*out_copy)(struct sof_sink *dst, int frames, float **src_bufs); }; void *GoogleRtcMalloc(size_t size) @@ -97,6 +110,130 @@ void GoogleRtcFree(void *ptr) return rfree(ptr); } +static ALWAYS_INLINE float clamp_rescale(float max_val, float x) +{ + float min = -1.0f; + float max = 1.0f - 1.0f / max_val; + + return max_val * (x < min ? min : (x > max ? max : x)); +} + +static ALWAYS_INLINE float s16_to_float(const char *ptr) +{ + float scale = -(float)SHRT_MIN; + float x = *(int16_t *)ptr; + + return (1.0f / scale) * x; +} + +static ALWAYS_INLINE void float_to_s16(float x, char *dst) +{ + *(int16_t *)dst = (int16_t)clamp_rescale(-(float)SHRT_MIN, x); +} + +static ALWAYS_INLINE float s32_to_float(const char *ptr) +{ + float scale = -(float)INT_MIN; + float x = *(int32_t *)ptr; + + return (1.0f / scale) * x; +} + +static ALWAYS_INLINE void float_to_s32(float x, char *dst) +{ + *(int32_t *)dst = (int16_t)clamp_rescale(-(float)INT_MIN, x); +} + +static ALWAYS_INLINE void source_to_float(struct sof_source *src, float **dst_bufs, + float (*cvt_fn)(const char *), + int sample_sz, int frame0, int frames) +{ + size_t chan = source_get_channels(src); + size_t bytes = frames * chan * sample_sz; + int i, c, err, ndst = MIN(chan, CHAN_MAX); + const char *buf, *bufstart, *bufend; + float *dst[CHAN_MAX]; + size_t bufsz; + + for (i = 0; i < ndst; i++) + dst[i] = &dst_bufs[i][frame0]; + + err = source_get_data(src, bytes, (void *)&buf, (void *)&bufstart, &bufsz); + assert(err == 0); + bufend = &bufstart[bufsz]; + + while (frames) { + size_t n = MIN(frames, (bufsz - (buf - bufstart)) / (chan * sample_sz)); + + for (i = 0; i < n; i++) { + for (c = 0; c < ndst; c++) { + *dst[c]++ = cvt_fn(buf); + buf += sample_sz; + } + buf += sample_sz * (chan - ndst); /* skip unused channels */ + } + frames -= n; + if (buf >= bufend) + buf = bufstart; + } + source_release_data(src, bytes); +} + +static ALWAYS_INLINE void float_to_sink(struct sof_sink *dst, float **src_bufs, + void (*cvt_fn)(float, char *), + int sample_sz, int frames) +{ + size_t chan = sink_get_channels(dst); + size_t bytes = frames * chan * sample_sz; + int i, c, err, nsrc = MIN(chan, CHAN_MAX); + char *buf, *bufstart, *bufend; + float *src[CHAN_MAX]; + size_t bufsz; + + for (i = 0; i < nsrc; i++) + src[i] = &src_bufs[i][0]; + + err = sink_get_buffer(dst, bytes, (void *)&buf, (void *)&bufstart, &bufsz); + assert(err == 0); + bufend = &bufstart[bufsz]; + + while (frames) { + size_t n = MIN(frames, (bufsz - (buf - bufstart)) / (chan * sample_sz)); + + for (i = 0; i < n; i++) { + for (c = 0; c < nsrc; c++) { + cvt_fn(*src[c]++, buf); + buf += sample_sz; + } + buf += sample_sz * (chan - nsrc); /* skip unused channels */ + } + frames -= n; + if (buf >= bufend) + buf = bufstart; + } + sink_commit_buffer(dst, bytes); +} + +static void source_copy16(struct sof_source *src, int frames, float **dst_bufs, int frame0) +{ + source_to_float(src, dst_bufs, s16_to_float, sizeof(int16_t), frame0, frames); +} + +static void source_copy32(struct sof_source *src, int frames, float **dst_bufs, int frame0) +{ + source_to_float(src, dst_bufs, s32_to_float, sizeof(int32_t), frame0, frames); +} + +static void sink_copy16(struct sof_sink *dst, int frames, float **src_bufs) +{ + float_to_sink(dst, src_bufs, float_to_s16, sizeof(int16_t), frames); +} + +static void sink_copy32(struct sof_sink *dst, int frames, float **src_bufs) +{ + float_to_sink(dst, src_bufs, float_to_s32, sizeof(int32_t), frames); +} + static int google_rtc_audio_processing_reconfigure(struct processing_module *mod) { struct google_rtc_audio_processing_comp_data *cd = module_get_private_data(mod); @@ -365,7 +502,8 @@ static int google_rtc_audio_processing_init(struct processing_module *mod) struct module_data *md = &mod->priv; struct comp_dev *dev = mod->dev; struct google_rtc_audio_processing_comp_data *cd; - int ret; + int ret, i; + comp_info(dev, "google_rtc_audio_processing_init()"); /* Create private component data */ @@ -377,54 +515,19 @@ static int google_rtc_audio_processing_init(struct processing_module *mod) md->private = cd; -#if CONFIG_IPC_MAJOR_4 - if (mod->priv.cfg.nb_input_pins != GOOGLE_RTC_NUM_INPUT_PINS) { - comp_err(dev, "Expecting %u sources, got %u", - GOOGLE_RTC_NUM_INPUT_PINS, mod->priv.cfg.nb_input_pins); - return -EINVAL; - } - if (mod->priv.cfg.nb_output_pins != GOOGLE_RTC_NUM_OUTPUT_PINS) { - comp_err(dev, "Expecting %u sink, got %u", - GOOGLE_RTC_NUM_OUTPUT_PINS, mod->priv.cfg.nb_output_pins); - return -EINVAL; - } - - cd->config.output_fmt = mod->priv.cfg.input_pins[SOF_AEC_DMIC_QUEUE_ID].audio_fmt; - cd->config.reference_fmt = mod->priv.cfg.input_pins[SOF_AEC_FEEDBACK_QUEUE_ID].audio_fmt; - - cd->num_aec_reference_channels = cd->config.reference_fmt.channels_count; - cd->num_capture_channels = cd->config.output_fmt.channels_count; - if (cd->num_capture_channels > CONFIG_COMP_GOOGLE_RTC_AUDIO_PROCESSING_CHANNEL_MAX) - cd->num_capture_channels = CONFIG_COMP_GOOGLE_RTC_AUDIO_PROCESSING_CHANNEL_MAX; - if (cd->num_aec_reference_channels > CONFIG_COMP_GOOGLE_RTC_AUDIO_REFERENCE_CHANNEL_MAX) - cd->num_aec_reference_channels = CONFIG_COMP_GOOGLE_RTC_AUDIO_REFERENCE_CHANNEL_MAX; - -#else - cd->num_aec_reference_channels = CONFIG_COMP_GOOGLE_RTC_AUDIO_REFERENCE_CHANNEL_MAX; - cd->num_capture_channels = CONFIG_COMP_GOOGLE_RTC_AUDIO_PROCESSING_CHANNEL_MAX; -#endif - cd->tuning_handler = comp_data_blob_handler_new(dev); if (!cd->tuning_handler) { ret = -ENOMEM; goto fail; } - cd->num_frames = CONFIG_COMP_GOOGLE_RTC_AUDIO_PROCESSING_SAMPLE_RATE_HZ / - GOOGLE_RTC_AUDIO_PROCESSING_FREQENCY_TO_PERIOD_FRAMES; - - if (CONFIG_COMP_GOOGLE_RTC_AUDIO_PROCESSING_MEMORY_BUFFER_SIZE_BYTES > 0) { - cd->memory_buffer = rballoc(0, SOF_MEM_CAPS_RAM, - CONFIG_COMP_GOOGLE_RTC_AUDIO_PROCESSING_MEMORY_BUFFER_SIZE_BYTES * - sizeof(cd->memory_buffer[0])); - if (!cd->memory_buffer) { - comp_err(dev, "google_rtc_audio_processing_init: failed to allocate memory buffer"); - ret = -ENOMEM; - goto fail; - } + cd->num_aec_reference_channels = CONFIG_COMP_GOOGLE_RTC_AUDIO_REFERENCE_CHANNEL_MAX; + cd->num_capture_channels = CONFIG_COMP_GOOGLE_RTC_AUDIO_REFERENCE_CHANNEL_MAX; + cd->num_frames = NUM_FRAMES; - GoogleRtcAudioProcessingAttachMemoryBuffer(cd->memory_buffer, CONFIG_COMP_GOOGLE_RTC_AUDIO_PROCESSING_MEMORY_BUFFER_SIZE_BYTES); - } + /* Giant blob of scratch memory. */ + GoogleRtcAudioProcessingAttachMemoryBuffer(sys_cache_cached_ptr_get(&aec_mem_blob[0]), + sizeof(aec_mem_blob)); cd->state = GoogleRtcAudioProcessingCreateWithConfig(CONFIG_COMP_GOOGLE_RTC_AUDIO_PROCESSING_SAMPLE_RATE_HZ, cd->num_capture_channels, @@ -449,67 +552,14 @@ static int google_rtc_audio_processing_init(struct processing_module *mod) comp_err(dev, "Failed to apply GoogleRtcAudioProcessingParameters"); goto fail; } -#if CONFIG_IPC_MAJOR_4 - size_t buf_size = cd->num_frames * cd->num_capture_channels * sizeof(cd->process_buffer[0]); - comp_dbg(dev, "Allocating process_buffer of size %u", buf_size); - cd->process_buffer = rballoc(0, SOF_MEM_CAPS_RAM, buf_size); - if (!cd->process_buffer) { - comp_err(dev, "Allocating process_buffer failure"); - ret = -EINVAL; - goto fail; + for (i = 0; i < CHAN_MAX; i++) { + cd->raw_mic_buffers[i] = sys_cache_cached_ptr_get(&micbuf[i][0]); + cd->refout_buffers[i] = sys_cache_cached_ptr_get(&refoutbuf[i][0]); } - bzero(cd->process_buffer, buf_size); - buf_size = cd->num_frames * sizeof(cd->aec_reference_buffer[0]) * - cd->num_aec_reference_channels; - comp_dbg(dev, "Allocating aec_reference_buffer of size %u", buf_size); - cd->aec_reference_buffer = rballoc(0, SOF_MEM_CAPS_RAM, buf_size); - if (!cd->aec_reference_buffer) { - comp_err(dev, "Allocating aec_reference_buffer failure"); - ret = -ENOMEM; - goto fail; - } - bzero(cd->aec_reference_buffer, buf_size); -#if CONFIG_COMP_GOOGLE_RTC_USE_32_BIT_FLOAT_API - for (size_t channel = 0; channel < cd->num_capture_channels; channel++) - cd->process_buffer_ptrs[channel] = &cd->process_buffer[channel * cd->num_frames]; - - for (size_t channel = 0; channel < cd->num_aec_reference_channels; channel++) - cd->aec_reference_buffer_ptrs[channel] = - &cd->aec_reference_buffer[channel * cd->num_frames]; -#endif /* CONFIG_COMP_GOOGLE_RTC_USE_32_BIT_FLOAT_API */ -#else - cd->raw_mic_buffer = rballoc( - 0, SOF_MEM_CAPS_RAM, - cd->num_frames * cd->num_capture_channels * sizeof(cd->raw_mic_buffer[0])); - if (!cd->raw_mic_buffer) { - ret = -EINVAL; - goto fail; - } - bzero(cd->raw_mic_buffer, cd->num_frames * cd->num_capture_channels * sizeof(cd->raw_mic_buffer[0])); - cd->raw_mic_buffer_frame_index = 0; - - cd->aec_reference_buffer = rballoc( - 0, SOF_MEM_CAPS_RAM, - cd->num_frames * sizeof(cd->aec_reference_buffer[0]) * - cd->num_aec_reference_channels); - if (!cd->aec_reference_buffer) { - ret = -ENOMEM; - goto fail; - } - bzero(cd->aec_reference_buffer, cd->num_frames * cd->num_aec_reference_channels * sizeof(cd->aec_reference_buffer[0])); - cd->aec_reference_frame_index = 0; - cd->output_buffer = rballoc( - 0, SOF_MEM_CAPS_RAM, - cd->num_frames * cd->num_capture_channels * sizeof(cd->output_buffer[0])); - if (!cd->output_buffer) { - ret = -ENOMEM; - goto fail; - } - bzero(cd->output_buffer, cd->num_frames * sizeof(cd->output_buffer[0])); - cd->output_buffer_frame_index = 0; -#endif + cd->buffered_frames = 0; + /* comp_is_new_data_blob_available always returns false for the first * control write with non-empty config. The first non-empty write may * happen after prepare (e.g. during copy). Default to true so that @@ -526,21 +576,10 @@ static int google_rtc_audio_processing_init(struct processing_module *mod) fail: comp_err(dev, "google_rtc_audio_processing_init(): Failed"); if (cd) { -#if !CONFIG_IPC_MAJOR_4 - rfree(cd->output_buffer); -#endif - rfree(cd->aec_reference_buffer); - if (cd->state) { GoogleRtcAudioProcessingFree(cd->state); } GoogleRtcAudioProcessingDetachMemoryBuffer(); - rfree(cd->memory_buffer); -#if CONFIG_IPC_MAJOR_4 - rfree(cd->process_buffer); -#else - rfree(cd->raw_mic_buffer); -#endif comp_data_blob_handler_free(cd->tuning_handler); rfree(cd); } @@ -556,17 +595,7 @@ static int google_rtc_audio_processing_free(struct processing_module *mod) GoogleRtcAudioProcessingFree(cd->state); cd->state = NULL; -#if !CONFIG_IPC_MAJOR_4 - rfree(cd->output_buffer); -#endif - rfree(cd->aec_reference_buffer); GoogleRtcAudioProcessingDetachMemoryBuffer(); - rfree(cd->memory_buffer); -#if CONFIG_IPC_MAJOR_4 - rfree(cd->process_buffer); -#else - rfree(cd->raw_mic_buffer); -#endif comp_data_blob_handler_free(cd->tuning_handler); rfree(cd); return 0; @@ -580,467 +609,240 @@ static int google_rtc_audio_processing_prepare(struct processing_module *mod, { struct comp_dev *dev = mod->dev; struct google_rtc_audio_processing_comp_data *cd = module_get_private_data(mod); -#if !CONFIG_IPC_MAJOR_4 - struct list_item *source_buffer_list_item; - struct comp_buffer *output; -#endif - unsigned int aec_channels = 0, frame_fmt, rate; - int microphone_stream_channels = 0; - int output_stream_channels; - int ret; - int i = 0; + int ret = 0; comp_info(dev, "google_rtc_audio_processing_prepare()"); -#if CONFIG_IPC_MAJOR_4 - if (num_of_sources != GOOGLE_RTC_NUM_INPUT_PINS) { - comp_err(dev, "Expecting %u sources, got %u", - GOOGLE_RTC_NUM_INPUT_PINS, num_of_sources); - return -EINVAL; - } - if (num_of_sinks != GOOGLE_RTC_NUM_OUTPUT_PINS) { - comp_err(dev, "Expecting %u sink, got %u", - GOOGLE_RTC_NUM_OUTPUT_PINS, num_of_sinks); + + if (num_of_sources != 2 || num_of_sinks != 1) { + comp_err(dev, "Invalid source/sink count"); return -EINVAL; } - /* searching for stream and feedback source buffers */ - for (i = 0; i < num_of_sources; i++) { - if (IPC4_SINK_QUEUE_ID(source_get_id(sources[i])) == SOF_AEC_FEEDBACK_QUEUE_ID) { - cd->aec_reference_source = i; - aec_channels = source_get_channels(sources[i]); - comp_dbg(dev, "reference index = %d, channels = %d", i, aec_channels); - } else { - cd->raw_microphone_source = i; - microphone_stream_channels = source_get_channels(sources[i]); - comp_dbg(dev, "microphone index = %d, channels = %d", i, - microphone_stream_channels); - } - source_set_alignment_constants(sources[i], 1, 1); - } + /* The mic is the source that is on the same pipeline as the sink */ + cd->aec_reference_source = + source_get_pipeline_id(sources[0]) == sink_get_pipeline_id(sinks[0]); + cd->raw_microphone_source = cd->aec_reference_source ? 0 : 1; - /* enforce format on pins */ - ipc4_update_source_format(sources[cd->aec_reference_source], &cd->config.reference_fmt); - ipc4_update_source_format(sources[cd->raw_microphone_source], &cd->config.output_fmt); - ipc4_update_sink_format(sinks[0], &cd->config.output_fmt); -#else /* CONFIG_IPC_MAJOR_4 */ - /* searching for stream and feedback source buffers */ - list_for_item(source_buffer_list_item, &dev->bsource_list) { - struct comp_buffer *source = container_of(source_buffer_list_item, - struct comp_buffer, sink_list); - if (source->source->pipeline->pipeline_id != dev->pipeline->pipeline_id) { - cd->aec_reference_source = i; - aec_channels = audio_stream_get_channels(&source->stream); - comp_dbg(dev, "reference index = %d, channels = %d", i, aec_channels); - } else { - cd->raw_microphone_source = i; - microphone_stream_channels = audio_stream_get_channels(&source->stream); - comp_dbg(dev, "microphone index = %d, channels = %d", i, - microphone_stream_channels); - } +#ifdef CONFIG_IPC_MAJOR_3 + /* Don't need the ref buffer on IPC4 as pipelines are always + * activated in tandem; also the API is deprecated + */ + cd->ref_comp_buffer = list_first_item(&dev->bsource_list, + struct comp_buffer, sink_list); + if (cd->aec_reference_source == 1) + cd->ref_comp_buffer = list_next_item(cd->ref_comp_buffer, sink_list); +#endif - i++; - } +#ifdef CONFIG_IPC_MAJOR_4 + /* Workaround: nothing in the framework sets up the stream for + * the reference source correctly from topology input, so we + * have to do it here. Input pin "1" is just a magic number + * that must match the input_pin_index token in a format + * record from our topology. + */ + ipc4_update_source_format(sources[cd->aec_reference_source], + &mod->priv.cfg.input_pins[1].audio_fmt); +#endif - output = list_first_item(&dev->bsink_list, struct comp_buffer, source_list); -#endif /* CONFIG_IPC_MAJOR_4 */ + /* Validate channel, format and rate on each of our three inputs */ + int ref_fmt = source_get_frm_fmt(sources[cd->aec_reference_source]); + int ref_chan = source_get_channels(sources[cd->aec_reference_source]); + int ref_rate = source_get_rate(sources[cd->aec_reference_source]); - /* On some platform the playback output is left right left right due to a crossover - * later on the signal processing chain. That makes the aec_reference be 4 channels - * and the AEC should only use the 2 first. - */ - if (cd->num_aec_reference_channels > aec_channels) { - comp_err(dev, "unsupported number of AEC reference channels: %d", - aec_channels); - return -EINVAL; - } -#if CONFIG_IPC_MAJOR_4 - sink_set_alignment_constants(sinks[0], 1, 1); - frame_fmt = sink_get_frm_fmt(sinks[0]); - rate = sink_get_rate(sinks[0]); - output_stream_channels = sink_get_channels(sinks[0]); -#else /* CONFIG_IPC_MAJOR_4 */ - frame_fmt = audio_stream_get_frm_fmt(&output->stream); - rate = audio_stream_get_rate(&output->stream); - output_stream_channels = audio_stream_get_channels(&output->stream); -#endif /* CONFIG_IPC_MAJOR_4 */ - - if (cd->num_capture_channels > microphone_stream_channels) { - comp_err(dev, "unsupported number of microphone channels: %d", - microphone_stream_channels); - return -EINVAL; + int mic_fmt = source_get_frm_fmt(sources[cd->raw_microphone_source]); + int mic_chan = source_get_channels(sources[cd->raw_microphone_source]); + int mic_rate = source_get_rate(sources[cd->raw_microphone_source]); + + int out_fmt = sink_get_frm_fmt(sinks[0]); + int out_chan = sink_get_channels(sinks[0]); + int out_rate = sink_get_rate(sinks[0]); + + cd->ref_framesz = source_get_frame_bytes(sources[cd->aec_reference_source]); + cd->cap_framesz = sink_get_frame_bytes(sinks[0]); + + cd->num_aec_reference_channels = MIN(ref_chan, CHAN_MAX); + cd->num_capture_channels = MIN(mic_chan, CHAN_MAX); + + /* Too many channels is a soft failure, AEC treats only the first N */ + if (mic_chan > CHAN_MAX) + comp_warn(dev, "Too many mic channels: %d, truncating to %d", + mic_chan, CHAN_MAX); + if (ref_chan > CHAN_MAX) + comp_warn(dev, "Too many ref channels: %d, truncating to %d", + ref_chan, CHAN_MAX); + + if (out_chan != mic_chan) { + comp_err(dev, "Input/output mic channel mismatch"); + ret = -EINVAL; } - if (cd->num_capture_channels > output_stream_channels) { - comp_err(dev, "unsupported number of output channels: %d", - output_stream_channels); - return -EINVAL; + if (ref_rate != mic_rate || ref_rate != out_rate || + ref_rate != CONFIG_COMP_GOOGLE_RTC_AUDIO_PROCESSING_SAMPLE_RATE_HZ) { + comp_err(dev, "Incorrect source/sink sample rate, expect %d\n", + CONFIG_COMP_GOOGLE_RTC_AUDIO_PROCESSING_SAMPLE_RATE_HZ); + ret = -EINVAL; } - switch (frame_fmt) { -#if CONFIG_FORMAT_S16LE - case SOF_IPC_FRAME_S16_LE: - break; -#endif /* CONFIG_FORMAT_S16LE */ - default: - comp_err(dev, "unsupported data format: %d", frame_fmt); - return -EINVAL; + if (mic_fmt != out_fmt) { + comp_err(dev, "Mismatched in/out frame format"); + ret = -EINVAL; } - if (rate != CONFIG_COMP_GOOGLE_RTC_AUDIO_PROCESSING_SAMPLE_RATE_HZ) { - comp_err(dev, "unsupported samplerate: %d", rate); - return -EINVAL; + if ((mic_fmt != SOF_IPC_FRAME_S32_LE && mic_fmt != SOF_IPC_FRAME_S16_LE) || + (ref_fmt != SOF_IPC_FRAME_S32_LE && ref_fmt != SOF_IPC_FRAME_S16_LE)) { + comp_err(dev, "Unsupported sample format"); + ret = -EINVAL; } -#if CONFIG_IPC_MAJOR_4 - /* check IBS/OBS in streams */ - if (cd->num_frames * source_get_frame_bytes(sources[cd->raw_microphone_source]) != - source_get_min_available(sources[cd->raw_microphone_source])) { - comp_err(dev, "Incorrect IBS on microphone source: %d, expected %u", - source_get_min_available(sources[cd->raw_microphone_source]), - cd->num_frames * - source_get_frame_bytes(sources[cd->raw_microphone_source])); - return -EINVAL; + +#ifdef CONFIG_IPC_MAJOR_4 + int ref_bufsz = source_get_min_available(sources[cd->aec_reference_source]); + int mic_bufsz = source_get_min_available(sources[cd->raw_microphone_source]); + int out_bufsz = sink_get_min_free_space(sinks[0]); + + if (mic_bufsz > cd->num_frames * cd->cap_framesz) { + comp_err(dev, "Mic IBS %d >1 AEC block, needless delay!", mic_bufsz); + ret = -EINVAL; } - if (cd->num_frames * sink_get_frame_bytes(sinks[0]) != - sink_get_min_free_space(sinks[0])) { - comp_err(dev, "Incorrect OBS on sink :%d, expected %u", - sink_get_min_free_space(sinks[0]), - cd->num_frames * sink_get_frame_bytes(sinks[0])); - return -EINVAL; + + if (ref_bufsz > cd->num_frames * cd->ref_framesz) { + comp_err(dev, "Ref IBS %d >1 one AEC block, needless delay!", ref_bufsz); + ret = -EINVAL; } - if (cd->num_frames * source_get_frame_bytes(sources[cd->aec_reference_source]) != - source_get_min_available(sources[cd->aec_reference_source])) { - comp_err(dev, "Incorrect IBS on reference source: %d, expected %u", - source_get_min_available(sources[cd->aec_reference_source]), - cd->num_frames * - source_get_frame_bytes(sources[cd->aec_reference_source])); - return -EINVAL; + + if (out_bufsz < cd->num_frames * cd->cap_framesz) { + comp_err(dev, "Capture OBS %d too small, must fit 1 AEC block", out_bufsz); + ret = -EINVAL; } -#endif /* CONFIG_IPC_MAJOR_4 */ +#endif - /* Blobs sent during COMP_STATE_READY is assigned to blob_handler->data - * directly, so comp_is_new_data_blob_available always returns false. - */ - ret = google_rtc_audio_processing_reconfigure(mod); - if (ret) + if (ret < 0) return ret; - return 0; -} - -static int google_rtc_audio_processing_reset(struct processing_module *mod) -{ - comp_dbg(mod->dev, "google_rtc_audio_processing_reset()"); - - return 0; -} + cd->mic_copy = mic_fmt == SOF_IPC_FRAME_S16_LE ? source_copy16 : source_copy32; + cd->ref_copy = ref_fmt == SOF_IPC_FRAME_S16_LE ? source_copy16 : source_copy32; + cd->out_copy = out_fmt == SOF_IPC_FRAME_S16_LE ? sink_copy16 : sink_copy32; -#if CONFIG_IPC_MAJOR_4 -#if CONFIG_COMP_GOOGLE_RTC_USE_32_BIT_FLOAT_API -static inline int16_t convert_float_to_int16(float data) -{ -#if XCHAL_HAVE_HIFI3 - const xtfloat ratio = 2 << 15; - xtfloat x0 = data; - xtfloat x1; - int16_t x; - - x1 = XT_MUL_S(x0, ratio); - x = XT_TRUNC_S(x1, 0); - - return x; -#else /* XCHAL_HAVE_HIFI3 */ - return Q_CONVERT_FLOAT(data, 15); -#endif /* XCHAL_HAVE_HIFI3 */ -} + cd->last_ref_ok = false; -static inline float convert_int16_to_float(int16_t data) -{ -#if XCHAL_HAVE_HIFI3 - const xtfloat ratio = 2 << 15; - xtfloat x0 = data; - float x; + ret = GoogleRtcAudioProcessingSetStreamFormats(cd->state, mic_rate, + cd->num_capture_channels, + cd->num_capture_channels, + ref_rate, cd->num_aec_reference_channels); - x = XT_DIV_S(x0, ratio); + /* Blobs sent during COMP_STATE_READY is assigned to blob_handler->data + * directly, so comp_is_new_data_blob_available always returns false. + */ + if (ret == 0) + ret = google_rtc_audio_processing_reconfigure(mod); - return x; -#else /* XCHAL_HAVE_HIFI3 */ - return Q_CONVERT_QTOF(data, 15); -#endif /* XCHAL_HAVE_HIFI3 */ + return ret; } -#endif /* CONFIG_COMP_GOOGLE_RTC_USE_32_BIT_FLOAT_API */ -/* todo CONFIG_FORMAT_S32LE */ -static int google_rtc_audio_processing_process(struct processing_module *mod, - struct sof_source **sources, int num_of_sources, - struct sof_sink **sinks, int num_of_sinks) +static int trigger_handler(struct processing_module *mod, int cmd) { - int ret; - int16_t const *src; - int8_t const *src_buf_start; - int8_t const *src_buf_end; - size_t src_buf_size; - - int16_t const *ref; - int8_t const *ref_buf_start; - int8_t const *ref_buf_end; - size_t ref_buf_size; - - int16_t *dst; - int8_t *dst_buf_start; - int8_t *dst_buf_end; - size_t dst_buf_size; - - size_t num_of_bytes_to_process; - size_t channel; - size_t buffer_offset; - - struct sof_source *ref_stream, *src_stream; - struct sof_sink *dst_stream; - +#ifdef CONFIG_IPC_MAJOR_3 struct google_rtc_audio_processing_comp_data *cd = module_get_private_data(mod); - if (cd->reconfigure) { - ret = google_rtc_audio_processing_reconfigure(mod); - if (ret) - return ret; - } - - src_stream = sources[cd->raw_microphone_source]; - ref_stream = sources[cd->aec_reference_source]; - dst_stream = sinks[0]; - - num_of_bytes_to_process = cd->num_frames * source_get_frame_bytes(ref_stream); - ret = source_get_data(ref_stream, num_of_bytes_to_process, (const void **)&ref, - (const void **)&ref_buf_start, &ref_buf_size); - - /* problems here are extremely unlikely, as it has been checked that - * the buffer contains enough data + /* Ignore and halt propagation if we get a trigger from the + * playback pipeline: not for us. (Never happens on IPC4) */ - assert(!ret); - ref_buf_end = ref_buf_start + ref_buf_size; + if (cd->ref_comp_buffer->walking) + return PPL_STATUS_PATH_STOP; +#endif - /* 32float: de-interlace ref buffer, convert it to float, skip channels if > Max - * 16int: linearize buffer, skip channels if > Max + /* Note: not module_adapter_set_state(). With IPC4 those are + * identical, but IPC3 has some odd-looking logic that + * validates that no sources are active when receiving a + * PRE_START command, which obviously breaks for our reference + * stream if playback was already running when our pipeline + * started */ - buffer_offset = 0; - for (int i = 0; i < cd->num_frames; i++) { - for (channel = 0; channel < cd->num_aec_reference_channels; ++channel) { -#if CONFIG_COMP_GOOGLE_RTC_USE_32_BIT_FLOAT_API - cd->aec_reference_buffer_ptrs[channel][i] = - convert_int16_to_float(ref[channel]); -#else /* CONFIG_COMP_GOOGLE_RTC_USE_32_BIT_FLOAT_API */ - cd->aec_reference_buffer[buffer_offset++] = ref[channel]; -#endif /* CONFIG_COMP_GOOGLE_RTC_USE_32_BIT_FLOAT_API */ - - } + return comp_set_state(mod->dev, cmd); +} - ref += cd->num_aec_reference_channels; - if ((void *)ref >= (void *)ref_buf_end) - ref = (void *)ref_buf_start; - } +static int google_rtc_audio_processing_reset(struct processing_module *mod) +{ + comp_dbg(mod->dev, "google_rtc_audio_processing_reset()"); + return 0; +} -#if CONFIG_COMP_GOOGLE_RTC_USE_32_BIT_FLOAT_API +static inline void execute_aec(struct google_rtc_audio_processing_comp_data *cd) +{ + /* Note that reference input and mic output share the same + * buffer for efficiency + */ GoogleRtcAudioProcessingAnalyzeRender_float32(cd->state, - (const float **) - cd->aec_reference_buffer_ptrs); -#else /* CONFIG_COMP_GOOGLE_RTC_USE_32_BIT_FLOAT_API */ - GoogleRtcAudioProcessingAnalyzeRender_int16(cd->state, - (const int16_t *)cd->aec_reference_buffer); -#endif /* CONFIG_COMP_GOOGLE_RTC_USE_32_BIT_FLOAT_API */ - source_release_data(ref_stream, num_of_bytes_to_process); - - /* process main stream - same as reference */ - num_of_bytes_to_process = cd->num_frames * source_get_frame_bytes(src_stream); - ret = source_get_data(src_stream, num_of_bytes_to_process, (const void **)&src, - (const void **)&src_buf_start, &src_buf_size); - assert(!ret); - src_buf_end = src_buf_start + src_buf_size; - - buffer_offset = 0; - for (int i = 0; i < cd->num_frames; i++) { - for (channel = 0; channel < cd->num_capture_channels; channel++) -#if CONFIG_COMP_GOOGLE_RTC_USE_32_BIT_FLOAT_API - cd->process_buffer_ptrs[channel][i] = convert_int16_to_float(src[channel]); -#else /* CONFIG_COMP_GOOGLE_RTC_USE_32_BIT_FLOAT_API */ - cd->process_buffer[buffer_offset++] = src[channel]; -#endif /* CONFIG_COMP_GOOGLE_RTC_USE_32_BIT_FLOAT_API */ - - /* move pointer to next frame - * number of incoming channels may be < cd->num_capture_channels - */ - src += cd->config.output_fmt.channels_count; - if ((void *)src >= (void *)src_buf_end) - src = (void *)src_buf_start; - } - - source_release_data(src_stream, num_of_bytes_to_process); - - /* call the library, use same in/out buffers */ -#if CONFIG_COMP_GOOGLE_RTC_USE_32_BIT_FLOAT_API + (const float **)cd->refout_buffers); GoogleRtcAudioProcessingProcessCapture_float32(cd->state, - (const float **)cd->process_buffer_ptrs, - cd->process_buffer_ptrs); -#else /* CONFIG_COMP_GOOGLE_RTC_USE_32_BIT_FLOAT_API */ - GoogleRtcAudioProcessingProcessCapture_int16(cd->state, - (const int16_t *)cd->process_buffer, - cd->process_buffer); -#endif /* CONFIG_COMP_GOOGLE_RTC_USE_32_BIT_FLOAT_API */ - - /* same number of bytes to process for output stream as for mic stream */ - ret = sink_get_buffer(dst_stream, num_of_bytes_to_process, (void **)&dst, - (void **)&dst_buf_start, &dst_buf_size); - assert(!ret); - dst_buf_end = dst_buf_start + dst_buf_size; - - /* process all channels in output stream */ - buffer_offset = 0; - for (int i = 0; i < cd->num_frames; i++) { - for (channel = 0; channel < cd->config.output_fmt.channels_count; channel++) { - /* set data in processed channels, zeroize not processed */ - if (channel < cd->num_capture_channels) -#if CONFIG_COMP_GOOGLE_RTC_USE_32_BIT_FLOAT_API - dst[channel] = convert_float_to_int16( - cd->process_buffer_ptrs[channel][i]); -#else /* CONFIG_COMP_GOOGLE_RTC_USE_32_BIT_FLOAT_API */ - dst[channel] = cd->process_buffer[buffer_offset++]; -#endif /* CONFIG_COMP_GOOGLE_RTC_USE_32_BIT_FLOAT_API */ - else - dst[channel] = 0; - } - - dst += cd->config.output_fmt.channels_count; - if ((void *)dst >= (void *)dst_buf_end) - dst = (void *)dst_buf_start; - } - - sink_commit_buffer(dst_stream, num_of_bytes_to_process); + (const float **)cd->raw_mic_buffers, + cd->refout_buffers); + cd->buffered_frames = 0; +} - return 0; +static bool ref_stream_active(struct google_rtc_audio_processing_comp_data *cd) +{ +#ifdef CONFIG_IPC_MAJOR_3 + return cd->ref_comp_buffer->source && + cd->ref_comp_buffer->source->state == COMP_STATE_ACTIVE; +#else + return true; +#endif } -#else /* CONFIG_IPC_MAJOR_4 */ -static int google_rtc_audio_processing_process(struct processing_module *mod, - struct input_stream_buffer *input_buffers, - int num_input_buffers, - struct output_stream_buffer *output_buffers, - int num_output_buffers) + +static int mod_process(struct processing_module *mod, struct sof_source **sources, + int num_of_sources, struct sof_sink **sinks, int num_of_sinks) { struct google_rtc_audio_processing_comp_data *cd = module_get_private_data(mod); - int16_t *src, *dst, *ref; - uint32_t num_aec_reference_frames; - uint32_t num_aec_reference_bytes; - int num_samples_remaining; - int num_frames_remaining; - int channel; - int frames; - int nmax; - int ret; - int i, j, n; - struct input_stream_buffer *ref_streamb, *mic_streamb; - struct output_stream_buffer *out_streamb; - struct audio_stream *ref_stream, *mic_stream, *out_stream; + if (cd->reconfigure) + google_rtc_audio_processing_reconfigure(mod); - if (cd->reconfigure) { - ret = google_rtc_audio_processing_reconfigure(mod); - if (ret) - return ret; - } + struct sof_source *mic = sources[cd->raw_microphone_source]; + struct sof_source *ref = sources[cd->aec_reference_source]; + struct sof_sink *out = sinks[0]; + bool ref_ok = ref_stream_active(cd); - ref_streamb = &input_buffers[cd->aec_reference_source]; - ref_stream = ref_streamb->data; - ref = audio_stream_get_rptr(ref_stream); - - num_aec_reference_frames = input_buffers[cd->aec_reference_source].size; - num_aec_reference_bytes = audio_stream_frame_bytes(ref_stream) * num_aec_reference_frames; - - num_samples_remaining = num_aec_reference_frames * audio_stream_get_channels(ref_stream); - while (num_samples_remaining) { - nmax = audio_stream_samples_without_wrap_s16(ref_stream, ref); - n = MIN(num_samples_remaining, nmax); - for (i = 0; i < n; i += cd->num_aec_reference_channels) { - j = cd->num_aec_reference_channels * cd->aec_reference_frame_index; - for (channel = 0; channel < cd->num_aec_reference_channels; ++channel) - cd->aec_reference_buffer[j++] = ref[channel]; - - ref += audio_stream_get_channels(ref_stream); - ++cd->aec_reference_frame_index; - - if (cd->aec_reference_frame_index == cd->num_frames) { - GoogleRtcAudioProcessingAnalyzeRender_int16(cd->state, - cd->aec_reference_buffer); - cd->aec_reference_frame_index = 0; - } - } - num_samples_remaining -= n; - ref = audio_stream_wrap(ref_stream, ref); - } - input_buffers[cd->aec_reference_source].consumed = num_aec_reference_bytes; + /* Clear the buffer if the reference pipeline shuts off */ + if (!ref_ok && cd->last_ref_ok) + bzero(sys_cache_cached_ptr_get(refoutbuf), sizeof(refoutbuf)); - mic_streamb = &input_buffers[cd->raw_microphone_source]; - mic_stream = mic_streamb->data; - out_streamb = &output_buffers[0]; - out_stream = out_streamb->data; + int fmic = source_get_data_frames_available(mic); + int fref = source_get_data_frames_available(ref); + int frames = ref_ok ? MIN(fmic, fref) : fmic; + int n, frames_rem; - src = audio_stream_get_rptr(mic_stream); - dst = audio_stream_get_wptr(out_stream); + for (frames_rem = frames; frames_rem; frames_rem -= n) { + n = MIN(frames_rem, cd->num_frames - cd->buffered_frames); - frames = input_buffers[cd->raw_microphone_source].size; - num_frames_remaining = frames; + cd->mic_copy(mic, n, cd->raw_mic_buffers, cd->buffered_frames); - while (num_frames_remaining) { - nmax = audio_stream_frames_without_wrap(mic_stream, src); - n = MIN(num_frames_remaining, nmax); - nmax = audio_stream_frames_without_wrap(out_stream, dst); - n = MIN(n, nmax); - for (i = 0; i < n; i++) { - memcpy_s(&(cd->raw_mic_buffer[cd->raw_mic_buffer_frame_index * - cd->num_capture_channels]), - cd->num_frames * cd->num_capture_channels * - sizeof(cd->raw_mic_buffer[0]), src, - sizeof(int16_t) * cd->num_capture_channels); - ++cd->raw_mic_buffer_frame_index; - - memcpy_s(dst, cd->num_frames * cd->num_capture_channels * - sizeof(cd->output_buffer[0]), - &(cd->output_buffer[cd->output_buffer_frame_index * - cd->num_capture_channels]), - sizeof(int16_t) * cd->num_capture_channels); - ++cd->output_buffer_frame_index; - - if (cd->raw_mic_buffer_frame_index == cd->num_frames) { - GoogleRtcAudioProcessingProcessCapture_int16(cd->state, - cd->raw_mic_buffer, - cd->output_buffer); - cd->output_buffer_frame_index = 0; - cd->raw_mic_buffer_frame_index = 0; + if (ref_ok) + cd->ref_copy(ref, n, cd->refout_buffers, cd->buffered_frames); + + cd->buffered_frames += n; + + if (cd->buffered_frames >= cd->num_frames) { + if (sink_get_free_size(out) < cd->num_frames * cd->cap_framesz) { + comp_warn(mod->dev, "AEC sink backed up!"); + break; } - src += audio_stream_get_channels(mic_stream); - dst += audio_stream_get_channels(out_stream); + execute_aec(cd); + cd->out_copy(out, cd->num_frames, cd->refout_buffers); } - num_frames_remaining -= n; - src = audio_stream_wrap(mic_stream, src); - dst = audio_stream_wrap(out_stream, dst); } - - module_update_buffer_position(&input_buffers[cd->raw_microphone_source], - &output_buffers[0], frames); - + cd->last_ref_ok = ref_ok; return 0; } -#endif /* CONFIG_IPC_MAJOR_4 */ static struct module_interface google_rtc_audio_processing_interface = { .init = google_rtc_audio_processing_init, .free = google_rtc_audio_processing_free, -#if CONFIG_IPC_MAJOR_4 - .process = google_rtc_audio_processing_process, -#else /* CONFIG_IPC_MAJOR_4 */ - .process_audio_stream = google_rtc_audio_processing_process, -#endif /* CONFIG_IPC_MAJOR_4 */ + .process = mod_process, .prepare = google_rtc_audio_processing_prepare, .set_configuration = google_rtc_audio_processing_set_config, .get_configuration = google_rtc_audio_processing_get_config, + .trigger = trigger_handler, .reset = google_rtc_audio_processing_reset, }; diff --git a/src/audio/google/google_rtc_audio_processing_mock.c b/src/audio/google/google_rtc_audio_processing_mock.c index e208885ebf34..7d5d12f5bd88 100644 --- a/src/audio/google/google_rtc_audio_processing_mock.c +++ b/src/audio/google/google_rtc_audio_processing_mock.c @@ -24,11 +24,7 @@ struct GoogleRtcAudioProcessingState { int num_aec_reference_channels; int num_output_channels; int num_frames; -#if CONFIG_COMP_GOOGLE_RTC_USE_32_BIT_FLOAT_API float *aec_reference; -#else - int16_t *aec_reference; -#endif }; static void SetFormats(GoogleRtcAudioProcessingState *const state, @@ -145,7 +141,6 @@ int GoogleRtcAudioProcessingReconfigure(GoogleRtcAudioProcessingState *const sta return 0; } -#if CONFIG_COMP_GOOGLE_RTC_USE_32_BIT_FLOAT_API int GoogleRtcAudioProcessingProcessCapture_float32(GoogleRtcAudioProcessingState *const state, const float *const *src, float * const *dest) @@ -182,42 +177,6 @@ int GoogleRtcAudioProcessingAnalyzeRender_float32(GoogleRtcAudioProcessingState return 0; } -#else /* CONFIG_COMP_GOOGLE_RTC_USE_32_BIT_FLOAT_API */ -int GoogleRtcAudioProcessingProcessCapture_int16(GoogleRtcAudioProcessingState *const state, - const int16_t *const src, - int16_t *const dest) -{ - int16_t *ref = state->aec_reference; - int n, chan; - - for (chan = 0; chan < state->num_output_channels; chan++) { - for (n = 0; n < state->num_frames; ++n) { - int16_t mic_save = src[(n * state->num_capture_channels) + chan]; - - if (chan < state->num_aec_reference_channels) - dest[(n * state->num_capture_channels) + chan] = - mic_save + ref[(n * state->num_aec_reference_channels) + chan]; - else - dest[(n * state->num_capture_channels) + chan] = mic_save; - } - } - - return 0; -} - -int GoogleRtcAudioProcessingAnalyzeRender_int16(GoogleRtcAudioProcessingState *const state, - const int16_t *const data) -{ - const size_t buffer_size = - sizeof(state->aec_reference[0]) - * state->num_frames - * state->num_aec_reference_channels; - memcpy_s(state->aec_reference, buffer_size, - data, buffer_size); - return 0; -} - -#endif /* CONFIG_COMP_GOOGLE_RTC_USE_32_BIT_FLOAT_API */ void GoogleRtcAudioProcessingParseSofConfigMessage(uint8_t *message, size_t message_size, diff --git a/src/include/ipc4/aec.h b/src/include/ipc4/aec.h index 93922a57b534..9456f86bcdf8 100644 --- a/src/include/ipc4/aec.h +++ b/src/include/ipc4/aec.h @@ -38,7 +38,4 @@ enum sof_ipc4_aec_config_params { IPC4_AEC_SET_EXT_FMT, }; -#define SOF_AEC_DMIC_QUEUE_ID 0 -#define SOF_AEC_FEEDBACK_QUEUE_ID 1 - #endif