ASoC: SOF: ipc4-loader/topology: Query the CPC value from manifest
The manifest's firmware module configuration section contains the measured CPC values along with a matching IBS/OBS values. The CPC can be looked up by looking for a matching IBS/OBS entry. In case of multiple matches we will use the highest CPC value. If there is no mod_cfg or no CPC value (all 0) or no match was found then print warning message and use 0 as CPC value. Signed-off-by: Peter Ujfalusi <peter.ujfalusi@linux.intel.com> Reviewed-by: Kai Vehmanen <kai.vehmanen@linux.intel.com> Reviewed-by: Pierre-Louis Bossart <pierre-louis.bossart@linux.intel.com> Reviewed-by: Ranjani Sridharan <ranjani.sridharan@linux.intel.com> Link: https://lore.kernel.org/r/20230522101313.12519-6-peter.ujfalusi@linux.intel.com Signed-off-by: Mark Brown <broonie@kernel.org>
This commit is contained in:
parent
9caa901805
commit
d8a2c98793
@ -423,6 +423,71 @@ int sof_ipc4_reload_fw_libraries(struct snd_sof_dev *sdev)
|
||||
return ret;
|
||||
}
|
||||
|
||||
/**
|
||||
* sof_ipc4_update_cpc_from_manifest - Update the cpc in base config from manifest
|
||||
* @sdev: SOF device
|
||||
* @fw_module: pointer struct sof_ipc4_fw_module to parse
|
||||
* @basecfg: Pointer to the base_config to update
|
||||
*/
|
||||
void sof_ipc4_update_cpc_from_manifest(struct snd_sof_dev *sdev,
|
||||
struct sof_ipc4_fw_module *fw_module,
|
||||
struct sof_ipc4_base_module_cfg *basecfg)
|
||||
{
|
||||
const struct sof_man4_module_config *fw_mod_cfg;
|
||||
u32 cpc_pick = 0;
|
||||
u32 max_cpc = 0;
|
||||
const char *msg;
|
||||
int i;
|
||||
|
||||
if (!fw_module->fw_mod_cfg) {
|
||||
msg = "No mod_cfg available for CPC lookup in the firmware file's manifest";
|
||||
goto no_cpc;
|
||||
}
|
||||
|
||||
/*
|
||||
* Find the best matching (highest) CPC value based on the module's
|
||||
* IBS/OBS configuration inferred from the audio format selection.
|
||||
*
|
||||
* The CPC value in each module config entry has been measured and
|
||||
* recorded as a IBS/OBS/CPC triplet and stored in the firmware file's
|
||||
* manifest
|
||||
*/
|
||||
fw_mod_cfg = fw_module->fw_mod_cfg;
|
||||
for (i = 0; i < fw_module->man4_module_entry.cfg_count; i++) {
|
||||
if (basecfg->obs == fw_mod_cfg[i].obs &&
|
||||
basecfg->ibs == fw_mod_cfg[i].ibs &&
|
||||
cpc_pick < fw_mod_cfg[i].cpc)
|
||||
cpc_pick = fw_mod_cfg[i].cpc;
|
||||
|
||||
if (max_cpc < fw_mod_cfg[i].cpc)
|
||||
max_cpc = fw_mod_cfg[i].cpc;
|
||||
}
|
||||
|
||||
basecfg->cpc = cpc_pick;
|
||||
|
||||
/* We have a matching configuration for CPC */
|
||||
if (basecfg->cpc)
|
||||
return;
|
||||
|
||||
/*
|
||||
* No matching IBS/OBS found, the firmware manifest is missing
|
||||
* information in the module's module configuration table.
|
||||
*/
|
||||
if (!max_cpc)
|
||||
msg = "No CPC value available in the firmware file's manifest";
|
||||
else if (!cpc_pick)
|
||||
msg = "No CPC match in the firmware file's manifest";
|
||||
|
||||
no_cpc:
|
||||
dev_warn(sdev->dev, "%s (UUID: %pUL): %s (ibs/obs: %u/%u)\n",
|
||||
fw_module->man4_module_entry.name,
|
||||
&fw_module->man4_module_entry.uuid, msg, basecfg->ibs,
|
||||
basecfg->obs);
|
||||
dev_warn_once(sdev->dev, "Please try to update the firmware.\n");
|
||||
dev_warn_once(sdev->dev, "If the issue persists, file a bug at\n");
|
||||
dev_warn_once(sdev->dev, "https://github.com/thesofproject/sof/issues/\n");
|
||||
}
|
||||
|
||||
const struct sof_ipc_fw_loader_ops ipc4_loader_ops = {
|
||||
.validate = sof_ipc4_validate_firmware,
|
||||
.parse_ext_manifest = sof_ipc4_fw_parse_basefw_ext_man,
|
||||
|
@ -114,4 +114,10 @@ int sof_ipc4_query_fw_configuration(struct snd_sof_dev *sdev);
|
||||
int sof_ipc4_reload_fw_libraries(struct snd_sof_dev *sdev);
|
||||
struct sof_ipc4_fw_module *sof_ipc4_find_module_by_uuid(struct snd_sof_dev *sdev,
|
||||
const guid_t *uuid);
|
||||
|
||||
struct sof_ipc4_base_module_cfg;
|
||||
void sof_ipc4_update_cpc_from_manifest(struct snd_sof_dev *sdev,
|
||||
struct sof_ipc4_fw_module *fw_module,
|
||||
struct sof_ipc4_base_module_cfg *basecfg);
|
||||
|
||||
#endif
|
||||
|
@ -966,6 +966,13 @@ sof_ipc4_update_resource_usage(struct snd_sof_dev *sdev, struct snd_sof_widget *
|
||||
pipe_widget = swidget->spipe->pipe_widget;
|
||||
pipeline = pipe_widget->private;
|
||||
pipeline->mem_usage += total;
|
||||
|
||||
/* Update base_config->cpc from the module manifest */
|
||||
sof_ipc4_update_cpc_from_manifest(sdev, fw_module, base_config);
|
||||
|
||||
dev_dbg(sdev->dev, "%s: ibs / obs / cpc: %u / %u / %u\n",
|
||||
swidget->widget->name, base_config->ibs, base_config->obs,
|
||||
base_config->cpc);
|
||||
}
|
||||
|
||||
static int sof_ipc4_widget_assign_instance_id(struct snd_sof_dev *sdev,
|
||||
|
Loading…
Reference in New Issue
Block a user