mirror of https://github.com/thesofproject/sof.git
component: add set of helper functions for large config configuration
This commit rewrites functions responsible for large config configuration from detect_test component and puts them in component.c file as generic ones - as a result they can be used by other components. Signed-off-by: Bartosz Kokoszko <bartoszx.kokoszko@linux.intel.com>
This commit is contained in:
parent
4f1090d083
commit
a2d1e1efdc
|
@ -5,6 +5,7 @@ add_subdirectory(arch)
|
|||
add_subdirectory(ipc)
|
||||
add_subdirectory(audio)
|
||||
add_subdirectory(lib)
|
||||
add_subdirectory(math)
|
||||
add_local_sources(sof spinlock.c)
|
||||
|
||||
if(CONFIG_LIBRARY)
|
||||
|
@ -14,7 +15,6 @@ endif()
|
|||
add_subdirectory(debug)
|
||||
add_subdirectory(drivers)
|
||||
add_subdirectory(init)
|
||||
add_subdirectory(math)
|
||||
add_subdirectory(schedule)
|
||||
|
||||
if (CONFIG_TRACE)
|
||||
|
|
|
@ -326,6 +326,158 @@ int comp_verify_params(struct comp_dev *dev, uint32_t flag,
|
|||
return 0;
|
||||
}
|
||||
|
||||
void comp_free_model_data(struct comp_dev *dev, struct comp_model_data *model)
|
||||
{
|
||||
if (!model->data)
|
||||
return;
|
||||
|
||||
rfree(model->data);
|
||||
model->data = NULL;
|
||||
model->data_size = 0;
|
||||
model->crc = 0;
|
||||
model->data_pos = 0;
|
||||
}
|
||||
|
||||
int comp_alloc_model_data(struct comp_dev *dev, struct comp_model_data *model,
|
||||
uint32_t size)
|
||||
{
|
||||
if (!size)
|
||||
return 0;
|
||||
|
||||
comp_free_model_data(dev, model);
|
||||
|
||||
model->data = rballoc(0, SOF_MEM_CAPS_RAM, size);
|
||||
|
||||
if (!model->data) {
|
||||
comp_err(dev, "comp_alloc_model_data(): model->data rballoc failed");
|
||||
return -ENOMEM;
|
||||
}
|
||||
|
||||
bzero(model->data, size);
|
||||
model->data_size = size;
|
||||
model->data_pos = 0;
|
||||
model->crc = 0;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int comp_set_model(struct comp_dev *dev, struct comp_model_data *model,
|
||||
struct sof_ipc_ctrl_data *cdata)
|
||||
{
|
||||
bool done = false;
|
||||
int ret = 0;
|
||||
|
||||
comp_dbg(dev, "comp_set_model() msg_index = %d, num_elems = %d, remaining = %d ",
|
||||
cdata->msg_index, cdata->num_elems,
|
||||
cdata->elems_remaining);
|
||||
|
||||
/* in case when the current package is the first, we should allocate
|
||||
* memory for whole model data
|
||||
*/
|
||||
if (!cdata->msg_index) {
|
||||
ret = comp_alloc_model_data(dev, model, cdata->data->size);
|
||||
if (ret < 0)
|
||||
return ret;
|
||||
}
|
||||
|
||||
/* return an error in case when we do not have allocated memory for
|
||||
* model data
|
||||
*/
|
||||
if (!model->data) {
|
||||
comp_err(dev, "comp_set_model(): buffer not allocated");
|
||||
return -ENOMEM;
|
||||
}
|
||||
|
||||
if (!cdata->elems_remaining) {
|
||||
/* when we receive the last package and do not fill the whole
|
||||
* allocated buffer, we return an error
|
||||
*/
|
||||
if (cdata->num_elems + model->data_pos < model->data_size) {
|
||||
comp_err(dev, "comp_set_model(): not enough data to fill the buffer");
|
||||
// TODO: handle this situation
|
||||
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
/* the whole data were received properly */
|
||||
done = true;
|
||||
comp_dbg(dev, "comp_set_model(): final package received");
|
||||
}
|
||||
|
||||
/* return an error in case when received data exceed allocated
|
||||
* memory
|
||||
*/
|
||||
if (cdata->num_elems > model->data_size - model->data_pos) {
|
||||
comp_err(dev, "comp_set_model(): too much data");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
ret = memcpy_s((char *)model->data + model->data_pos,
|
||||
model->data_size - model->data_pos,
|
||||
cdata->data->data, cdata->num_elems);
|
||||
assert(!ret);
|
||||
|
||||
/* update data_pos variable with received number of elements (num_elem)
|
||||
*/
|
||||
model->data_pos += cdata->num_elems;
|
||||
|
||||
/* Update crc value when done */
|
||||
if (done) {
|
||||
model->crc = crc32(0, model->data, model->data_size);
|
||||
comp_dbg(dev, "comp_set_model() done, memory_size = 0x%x, crc = 0x%08x",
|
||||
model->data_size, model->crc);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int comp_get_model(struct comp_dev *dev, struct comp_model_data *model,
|
||||
struct sof_ipc_ctrl_data *cdata, int size)
|
||||
{
|
||||
size_t bs;
|
||||
int ret = 0;
|
||||
|
||||
comp_dbg(dev, "comp_get_model() msg_index = %d, num_elems = %d, remaining = %d ",
|
||||
cdata->msg_index, cdata->num_elems,
|
||||
cdata->elems_remaining);
|
||||
|
||||
/* Copy back to user space */
|
||||
if (model->data) {
|
||||
/* reset data_pos variable in case of copying first element */
|
||||
if (!cdata->msg_index) {
|
||||
model->data_pos = 0;
|
||||
comp_dbg(dev, "comp_get_model() model data_size = 0x%x",
|
||||
model->data_size);
|
||||
}
|
||||
|
||||
bs = cdata->num_elems;
|
||||
|
||||
/* return an error in case of mismatch between num_elems and
|
||||
* required size
|
||||
*/
|
||||
if (bs > size) {
|
||||
comp_err(dev, "comp_get_model(): invalid size %d", bs);
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
/* copy required size of data */
|
||||
ret = memcpy_s(cdata->data->data, size,
|
||||
(char *)model->data + model->data_pos,
|
||||
bs);
|
||||
assert(!ret);
|
||||
|
||||
cdata->data->abi = SOF_ABI_VERSION;
|
||||
cdata->data->size = model->data_size;
|
||||
model->data_pos += bs;
|
||||
|
||||
} else {
|
||||
comp_err(dev, "comp_get_model(): !model->data");
|
||||
ret = -EINVAL;
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
struct comp_dev *comp_make_shared(struct comp_dev *dev)
|
||||
{
|
||||
struct list_item *old_bsource_list = &dev->bsource_list;
|
||||
|
|
|
@ -472,6 +472,16 @@ struct comp_copy_limits {
|
|||
int sink_frame_bytes;
|
||||
};
|
||||
|
||||
/** \brief Struct for large component configs */
|
||||
struct comp_model_data {
|
||||
uint32_t data_size; /**< size of component's model data */
|
||||
void *data; /**< pointer to model data */
|
||||
uint32_t crc; /**< crc value of model data */
|
||||
uint32_t data_pos; /**< indicates a data position in data
|
||||
* sending/receiving process
|
||||
*/
|
||||
};
|
||||
|
||||
/** \brief Computes size of the component device including ipc config. */
|
||||
#define COMP_SIZE(x) \
|
||||
(sizeof(struct comp_dev) - sizeof(struct sof_ipc_comp) + sizeof(x))
|
||||
|
@ -725,6 +735,45 @@ void comp_get_copy_limits_with_lock(struct comp_buffer *source,
|
|||
buffer_unlock(source, source_flags);
|
||||
}
|
||||
|
||||
/**
|
||||
* Frees data for large component configurations.
|
||||
*
|
||||
* @param dev Component device
|
||||
* @param model Component model struct
|
||||
*/
|
||||
void comp_free_model_data(struct comp_dev *dev, struct comp_model_data *model);
|
||||
|
||||
/**
|
||||
* Allocates data for large component configurations.
|
||||
*
|
||||
* @param dev Component device
|
||||
* @param model Component model struct
|
||||
* @param size Required size.
|
||||
*/
|
||||
int comp_alloc_model_data(struct comp_dev *dev, struct comp_model_data *model,
|
||||
uint32_t size);
|
||||
|
||||
/**
|
||||
* Gets model data for large component configurations.
|
||||
*
|
||||
* @param dev Component device
|
||||
* @param model Component model struct
|
||||
* @param cdata IPC ctrl data
|
||||
*/
|
||||
int comp_set_model(struct comp_dev *dev, struct comp_model_data *model,
|
||||
struct sof_ipc_ctrl_data *cdata);
|
||||
/**
|
||||
*
|
||||
* Set model data for large component configurations.
|
||||
*
|
||||
* @param dev Component device
|
||||
* @param model Component model struct
|
||||
* @param cdata IPC ctrl data
|
||||
* @param size Required size
|
||||
*/
|
||||
int comp_get_model(struct comp_dev *dev, struct comp_model_data *model,
|
||||
struct sof_ipc_ctrl_data *cdata, int size);
|
||||
|
||||
/**
|
||||
* Called by component in params() function in order to set and update some of
|
||||
* downstream (playback) or upstream (capture) buffer parameters with pcm
|
||||
|
|
|
@ -1,3 +1,9 @@
|
|||
# SPDX-License-Identifier: BSD-3-Clause
|
||||
|
||||
add_local_sources(sof numbers.c trig.c decibels.c)
|
||||
|
||||
if(BUILD_LIBRARY)
|
||||
return()
|
||||
endif()
|
||||
|
||||
add_local_sources(sof trig.c decibels.c)
|
|
@ -38,6 +38,11 @@ void pipeline_xrun(struct pipeline *p, struct comp_dev *dev, int32_t bytes)
|
|||
{
|
||||
}
|
||||
|
||||
uint32_t crc32(uint32_t base, const void *data, uint32_t bytes)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
struct sof *sof_get(void)
|
||||
{
|
||||
return &sof;
|
||||
|
|
|
@ -12,6 +12,7 @@
|
|||
#include <stdio.h>
|
||||
#include <sof/sof.h>
|
||||
#include <sof/audio/component_ext.h>
|
||||
#include <sof/math/numbers.h>
|
||||
#include <sof/audio/format.h>
|
||||
|
||||
#define DEBUG_MSG_LEN 256
|
||||
|
|
Loading…
Reference in New Issue