Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Audio: multiband_drc: multiband drc code re-organize and split #8526

Merged
merged 3 commits into from
Dec 4, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions src/audio/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -178,12 +178,14 @@ if(CONFIG_IPC_MAJOR_3)
set(eq-iir_sources eq_iir/eq_iir_ipc3.c eq_iir/eq_iir_generic.c)
set(eq-fir_sources eq_fir/eq_fir_ipc3.c)
set(tdfb_sources tdfb/tdfb_ipc3.c)
set(tdfb_sources multiband_drc/multiband_drc_ipc3.c)
elseif(CONFIG_IPC_MAJOR_4)
set(volume_sources volume/volume.c volume/volume_generic.c volume/volume_ipc4.c)
set(src_sources src/src.c src/src_ipc4.c src/src_generic.c)
set(eq-iir_sources eq_iir/eq_iir_ipc4.c eq_iir/eq_iir_generic.c)
set(eq-fir_sources eq_fir/eq_fir_ipc4.c)
set(tdfb_sources tdfb/tdfb_ipc4.c)
set(tdfb_sources multiband_drc/multiband_drc_ipc4.c)
endif()
set(mixer_sources ${mixer_src})
set(asrc_sources asrc/asrc.c asrc/asrc_farrow.c asrc/asrc_farrow_generic.c)
Expand Down
6 changes: 6 additions & 0 deletions src/audio/multiband_drc/CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -1,2 +1,8 @@
add_local_sources(sof multiband_drc.c)
add_local_sources(sof multiband_drc_generic.c)

if(CONFIG_IPC_MAJOR_3)
add_local_sources(sof multiband_drc_ipc3.c)
elseif(CONFIG_IPC_MAJOR_4)
add_local_sources(sof multiband_drc_ipc4.c)
endif()
151 changes: 6 additions & 145 deletions src/audio/multiband_drc/multiband_drc.c
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,6 @@
#include <sof/audio/module_adapter/module/generic.h>
#include <sof/audio/crossover/crossover_algorithm.h>
#include <sof/audio/drc/drc_algorithm.h>
#include <sof/audio/multiband_drc/multiband_drc.h>
#include <sof/audio/buffer.h>
#include <sof/audio/format.h>
#include <sof/audio/ipc-config.h>
Expand All @@ -33,6 +32,7 @@
#include <errno.h>
#include <stddef.h>
#include <stdint.h>
#include "multiband_drc.h"

LOG_MODULE_REGISTER(multiband_drc, CONFIG_SOF_LOG_LEVEL);

Expand All @@ -42,16 +42,7 @@ DECLARE_SOF_RT_UUID("multiband_drc", multiband_drc_uuid, 0x0d9f2256, 0x8e4f, 0x4

DECLARE_TR_CTX(multiband_drc_tr, SOF_UUID(multiband_drc_uuid), LOG_LEVEL_INFO);

static inline void multiband_drc_iir_reset_state_ch(struct iir_state_df2t *iir)
{
rfree(iir->coef);
rfree(iir->delay);

iir->coef = NULL;
iir->delay = NULL;
}

static inline void multiband_drc_reset_state(struct multiband_drc_state *state)
static void multiband_drc_reset_state(struct multiband_drc_state *state)
{
int i;

Expand Down Expand Up @@ -250,16 +241,12 @@ static int multiband_drc_init(struct processing_module *mod)
md->private = cd;
cd->multiband_drc_func = NULL;
cd->crossover_split = NULL;
#if CONFIG_IPC_MAJOR_4
/* Initialize to enabled is a workaround for IPC4 kernel version 6.6 and
* before where the processing is never enabled via switch control. New
* kernel sends the IPC4 switch control and sets this to desired state
* before prepare.
*/
cd->process_enabled = true;
#else
cd->process_enabled = false;
#endif
multiband_drc_process_enable(&cd->process_enabled);

/* Handler for configuration data */
cd->model_handler = comp_data_blob_handler_new(dev);
Expand Down Expand Up @@ -297,118 +284,29 @@ static int multiband_drc_free(struct processing_module *mod)
return 0;
}

#if CONFIG_IPC_MAJOR_3
static int multiband_drc_cmd_set_value(struct processing_module *mod,
struct sof_ipc_ctrl_data *cdata)
{
struct comp_dev *dev = mod->dev;
struct multiband_drc_comp_data *cd = module_get_private_data(mod);

switch (cdata->cmd) {
case SOF_CTRL_CMD_SWITCH:
comp_dbg(dev, "multiband_drc_multiband_drc_cmd_set_value(), SOF_CTRL_CMD_SWITCH");
if (cdata->num_elems == 1) {
cd->process_enabled = cdata->chanv[0].value;
comp_info(dev, "multiband_drc_cmd_set_value(), process_enabled = %d",
cd->process_enabled);
return 0;
}
}

comp_err(mod->dev, "cmd_set_value() error: invalid cdata->cmd");
return -EINVAL;
}
#endif

static int multiband_drc_set_config(struct processing_module *mod, uint32_t param_id,
enum module_cfg_fragment_position pos,
uint32_t data_offset_size, const uint8_t *fragment,
size_t fragment_size, uint8_t *response,
size_t response_size)
{
struct multiband_drc_comp_data *cd = module_get_private_data(mod);
struct comp_dev *dev = mod->dev;

comp_dbg(dev, "multiband_drc_set_config()");

#if CONFIG_IPC_MAJOR_4
struct sof_ipc4_control_msg_payload *ctl = (struct sof_ipc4_control_msg_payload *)fragment;

switch (param_id) {
case SOF_IPC4_SWITCH_CONTROL_PARAM_ID:
comp_dbg(dev, "SOF_IPC4_SWITCH_CONTROL_PARAM_ID id = %d, num_elems = %d",
ctl->id, ctl->num_elems);

if (ctl->id == 0 && ctl->num_elems == 1) {
cd->process_enabled = ctl->chanv[0].value;
comp_info(dev, "process_enabled = %d", cd->process_enabled);
} else {
comp_err(dev, "Illegal control id = %d, num_elems = %d",
ctl->id, ctl->num_elems);
return -EINVAL;
}

return 0;

case SOF_IPC4_ENUM_CONTROL_PARAM_ID:
comp_err(dev, "multiband_drc_set_config(), illegal control.");
return -EINVAL;
}

#elif CONFIG_IPC_MAJOR_3
struct sof_ipc_ctrl_data *cdata = (struct sof_ipc_ctrl_data *)fragment;

if (cdata->cmd != SOF_CTRL_CMD_BINARY)
return multiband_drc_cmd_set_value(mod, cdata);
#endif

comp_dbg(mod->dev, "multiband_drc_set_config(), SOF_CTRL_CMD_BINARY");
return comp_data_blob_set(cd->model_handler, pos, data_offset_size, fragment,
fragment_size);
}

#if CONFIG_IPC_MAJOR_3
static int multiband_drc_cmd_get_value(struct processing_module *mod,
struct sof_ipc_ctrl_data *cdata)
{
struct comp_dev *dev = mod->dev;
struct multiband_drc_comp_data *cd = module_get_private_data(mod);
int j;

switch (cdata->cmd) {
case SOF_CTRL_CMD_SWITCH:
comp_dbg(dev, "multiband_drc_cmd_get_value(), SOF_CTRL_CMD_SWITCH");
for (j = 0; j < cdata->num_elems; j++)
cdata->chanv[j].value = cd->process_enabled;
if (cdata->num_elems == 1)
return 0;

comp_warn(dev, "multiband_drc_cmd_get_value() warn: num_elems should be 1, got %d",
cdata->num_elems);
return 0;
}

comp_err(dev, "tdfb_cmd_get_value() error: invalid cdata->cmd");
return -EINVAL;
return multiband_drc_set_ipc_config(mod, param_id,
fragment, pos, data_offset_size, fragment_size);
}
#endif

static int multiband_drc_get_config(struct processing_module *mod,
uint32_t config_id, uint32_t *data_offset_size,
uint8_t *fragment, size_t fragment_size)
{
struct multiband_drc_comp_data *cd = module_get_private_data(mod);
struct sof_ipc_ctrl_data *cdata = (struct sof_ipc_ctrl_data *)fragment;

comp_dbg(mod->dev, "multiband_drc_get_config()");

#if CONFIG_IPC_MAJOR_3
if (cdata->cmd != SOF_CTRL_CMD_BINARY)
return multiband_drc_cmd_get_value(mod, cdata);
#endif

comp_dbg(mod->dev, "multiband_drc_get_config(), SOF_CTRL_CMD_BINARY");
return comp_data_blob_get_cmd(cd->model_handler, cdata, fragment_size);
return multiband_drc_get_ipc_config(mod, cdata, fragment_size);
}

static void multiband_drc_set_alignment(struct audio_stream *source,
Expand Down Expand Up @@ -451,41 +349,6 @@ static int multiband_drc_process(struct processing_module *mod,
return 0;
}

#if CONFIG_IPC_MAJOR_4
static int multiband_drc_params(struct processing_module *mod)
{
struct sof_ipc_stream_params *params = mod->stream_params;
struct sof_ipc_stream_params comp_params;
struct comp_dev *dev = mod->dev;
struct comp_buffer *sinkb;
enum sof_ipc_frame valid_fmt, frame_fmt;
int i, ret;

comp_dbg(dev, "multiband_drc_params()");

comp_params = *params;
comp_params.channels = mod->priv.cfg.base_cfg.audio_fmt.channels_count;
comp_params.rate = mod->priv.cfg.base_cfg.audio_fmt.sampling_frequency;
comp_params.buffer_fmt = mod->priv.cfg.base_cfg.audio_fmt.interleaving_style;

audio_stream_fmt_conversion(mod->priv.cfg.base_cfg.audio_fmt.depth,
mod->priv.cfg.base_cfg.audio_fmt.valid_bit_depth,
&frame_fmt, &valid_fmt,
mod->priv.cfg.base_cfg.audio_fmt.s_type);

comp_params.frame_fmt = frame_fmt;

for (i = 0; i < SOF_IPC_MAX_CHANNELS; i++)
comp_params.chmap[i] = (mod->priv.cfg.base_cfg.audio_fmt.ch_map >> i * 4) & 0xf;

component_set_nearest_period_frames(dev, comp_params.rate);
sinkb = list_first_item(&dev->bsink_list, struct comp_buffer, source_list);
ret = buffer_set_params(sinkb, &comp_params, true);

return ret;
}
#endif /* CONFIG_IPC_MAJOR_4 */

static int multiband_drc_prepare(struct processing_module *mod,
struct sof_source **sources, int num_of_sources,
struct sof_sink **sinks, int num_of_sinks)
Expand All @@ -499,11 +362,9 @@ static int multiband_drc_prepare(struct processing_module *mod,

comp_info(dev, "multiband_drc_prepare()");

#if CONFIG_IPC_MAJOR_4
ret = multiband_drc_params(mod);
if (ret < 0)
return ret;
#endif

/* DRC component will only ever have 1 source and 1 sink buffer */
sourceb = list_first_item(&dev->bsource_list, struct comp_buffer, sink_list);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -14,8 +14,8 @@
#include <sof/audio/component.h>
#include <sof/audio/data_blob.h>
#include <sof/platform.h>
#include <user/multiband_drc.h>
#include <stdint.h>
#include "user/multiband_drc.h"

/**
* Stores the state of the sub-components in Multiband DRC
Expand Down Expand Up @@ -83,6 +83,23 @@ static inline multiband_drc_func multiband_drc_find_proc_func_pass(enum sof_ipc_
return NULL;
}

static inline void multiband_drc_iir_reset_state_ch(struct iir_state_df2t *iir)
{
rfree(iir->coef);
rfree(iir->delay);

iir->coef = NULL;
iir->delay = NULL;
}

void multiband_drc_process_enable(bool *process_enabled);
int multiband_drc_set_ipc_config(struct processing_module *mod, uint32_t param_id,
const uint8_t *fragment, enum module_cfg_fragment_position pos,
uint32_t data_offset_size, size_t fragment_size);
int multiband_drc_get_ipc_config(struct processing_module *mod, struct sof_ipc_ctrl_data *cdata,
size_t fragment_size);
int multiband_drc_params(struct processing_module *mod);

#ifdef UNIT_TEST
void sys_comp_module_multiband_drc_interface_init(void);
#endif
Expand Down
2 changes: 1 addition & 1 deletion src/audio/multiband_drc/multiband_drc_generic.c
Original file line number Diff line number Diff line change
Expand Up @@ -7,8 +7,8 @@
#include <stdint.h>
#include <sof/audio/drc/drc_algorithm.h>
#include <sof/audio/format.h>
#include <sof/audio/multiband_drc/multiband_drc.h>
#include <sof/math/iir_df2t.h>
#include "multiband_drc.h"

static void multiband_drc_default_pass(const struct processing_module *mod,
const struct audio_stream *source,
Expand Down
102 changes: 102 additions & 0 deletions src/audio/multiband_drc/multiband_drc_ipc3.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,102 @@
// SPDX-License-Identifier: BSD-3-Clause
//
// Copyright(c) 2020 Google LLC. All rights reserved.
//
// Author: Pin-chih Lin <[email protected]>

#include <sof/audio/module_adapter/module/generic.h>
#include <sof/audio/module_adapter/module/module_interface.h>
#include <module/module/base.h>
#include <ipc/control.h>
#include <sof/trace/trace.h>
#include <sof/audio/component.h>
#include <module/module/interface.h>
#include <sof/audio/data_blob.h>

#include "multiband_drc.h"

LOG_MODULE_DECLARE(multiband_drc, CONFIG_SOF_LOG_LEVEL);

void multiband_drc_process_enable(bool *process_enabled)
{
*process_enabled = false;
}

static int multiband_drc_cmd_set_value(struct processing_module *mod,
struct sof_ipc_ctrl_data *cdata)
{
struct comp_dev *dev = mod->dev;
struct multiband_drc_comp_data *cd = module_get_private_data(mod);

switch (cdata->cmd) {
case SOF_CTRL_CMD_SWITCH:
comp_dbg(dev, "multiband_drc_multiband_drc_cmd_set_value(), SOF_CTRL_CMD_SWITCH");
if (cdata->num_elems == 1) {
cd->process_enabled = cdata->chanv[0].value;
comp_info(dev, "multiband_drc_cmd_set_value(), process_enabled = %d",
cd->process_enabled);
return 0;
}
}

comp_err(mod->dev, "cmd_set_value() error: invalid cdata->cmd");
return -EINVAL;
}

int multiband_drc_set_ipc_config(struct processing_module *mod, uint32_t param_id,
const uint8_t *fragment, enum module_cfg_fragment_position pos,
uint32_t data_offset_size, size_t fragment_size)
{
struct sof_ipc_ctrl_data *cdata = (struct sof_ipc_ctrl_data *)fragment;
struct multiband_drc_comp_data *cd = module_get_private_data(mod);
struct comp_dev *dev = mod->dev;

if (cdata->cmd != SOF_CTRL_CMD_BINARY)
return multiband_drc_cmd_set_value(mod, cdata);

comp_dbg(dev, "multiband_drc_set_config(), SOF_CTRL_CMD_BINARY");
return comp_data_blob_set(cd->model_handler, pos, data_offset_size, fragment,
fragment_size);
}

static int multiband_drc_cmd_get_value(struct processing_module *mod,
struct sof_ipc_ctrl_data *cdata)
{
struct comp_dev *dev = mod->dev;
struct multiband_drc_comp_data *cd = module_get_private_data(mod);
int j;

switch (cdata->cmd) {
case SOF_CTRL_CMD_SWITCH:
comp_dbg(dev, "multiband_drc_cmd_get_value(), SOF_CTRL_CMD_SWITCH");
for (j = 0; j < cdata->num_elems; j++)
cdata->chanv[j].value = cd->process_enabled;
if (cdata->num_elems == 1)
return 0;

comp_warn(dev, "multiband_drc_cmd_get_value() warn: num_elems should be 1, got %d",
cdata->num_elems);
return 0;
}

comp_err(dev, "tdfb_cmd_get_value() error: invalid cdata->cmd");
return -EINVAL;
}

int multiband_drc_get_ipc_config(struct processing_module *mod, struct sof_ipc_ctrl_data *cdata,
size_t fragment_size)
{
struct multiband_drc_comp_data *cd = module_get_private_data(mod);

if (cdata->cmd != SOF_CTRL_CMD_BINARY)
return multiband_drc_cmd_get_value(mod, cdata);

comp_dbg(mod->dev, "multiband_drc_get_ipc_config(), SOF_CTRL_CMD_BINARY");
return comp_data_blob_get_cmd(cd->model_handler, cdata, fragment_size);
}

int multiband_drc_params(struct processing_module *mod)
{
return 0;
}

Loading
Loading