mirror of https://github.com/torvalds/linux.git
ASoC: SDCA: Add early IRQ handling
Some IRQs (FDL) require processing before the primary soundcard is brought up, as the downloaded files could be firmware required for operation of the audio functions of the device. Add a new helper function which registers the required IRQs. Reviewed-by: Bard Liao <yung-chuan.liao@linux.intel.com> Signed-off-by: Charles Keepax <ckeepax@opensource.cirrus.com> Reviewed-by: Pierre-Louis Bossart <pierre-louis.bossart@linux.dev> Link: https://patch.msgid.link/20251020155512.353774-19-ckeepax@opensource.cirrus.com Signed-off-by: Mark Brown <broonie@kernel.org>
This commit is contained in:
parent
e92e25f777
commit
12aa3160c1
|
|
@ -75,6 +75,9 @@ int sdca_irq_data_populate(struct device *dev, struct regmap *function_regmap,
|
|||
struct sdca_entity *entity,
|
||||
struct sdca_control *control,
|
||||
struct sdca_interrupt *interrupt);
|
||||
int sdca_irq_populate_early(struct device *dev, struct regmap *function_regmap,
|
||||
struct sdca_function_data *function,
|
||||
struct sdca_interrupt_info *info);
|
||||
int sdca_irq_populate(struct sdca_function_data *function,
|
||||
struct snd_soc_component *component,
|
||||
struct sdca_interrupt_info *info);
|
||||
|
|
|
|||
|
|
@ -396,6 +396,77 @@ static struct sdca_interrupt *get_interrupt_data(struct device *dev, int irq,
|
|||
return &info->irqs[irq];
|
||||
}
|
||||
|
||||
/**
|
||||
* sdca_irq_populate_early - process pre-audio card IRQ registrations
|
||||
* @dev: Device pointer for SDCA Function.
|
||||
* @regmap: Regmap pointer for the SDCA Function.
|
||||
* @function: Pointer to the SDCA Function.
|
||||
* @info: Pointer to the SDCA interrupt info for this device.
|
||||
*
|
||||
* This is intended to be used as part of the Function boot process. It
|
||||
* can be called before the soundcard is registered (ie. doesn't depend
|
||||
* on component) and will register the FDL interrupts.
|
||||
*
|
||||
* Return: Zero on success, and a negative error code on failure.
|
||||
*/
|
||||
int sdca_irq_populate_early(struct device *dev, struct regmap *regmap,
|
||||
struct sdca_function_data *function,
|
||||
struct sdca_interrupt_info *info)
|
||||
{
|
||||
int i, j;
|
||||
|
||||
guard(mutex)(&info->irq_lock);
|
||||
|
||||
for (i = 0; i < function->num_entities; i++) {
|
||||
struct sdca_entity *entity = &function->entities[i];
|
||||
|
||||
for (j = 0; j < entity->num_controls; j++) {
|
||||
struct sdca_control *control = &entity->controls[j];
|
||||
int irq = control->interrupt_position;
|
||||
struct sdca_interrupt *interrupt;
|
||||
int ret;
|
||||
|
||||
interrupt = get_interrupt_data(dev, irq, info);
|
||||
if (IS_ERR(interrupt))
|
||||
return PTR_ERR(interrupt);
|
||||
else if (!interrupt)
|
||||
continue;
|
||||
|
||||
switch (entity->type) {
|
||||
case SDCA_ENTITY_TYPE_XU:
|
||||
if (control->sel != SDCA_CTL_XU_FDL_CURRENTOWNER)
|
||||
break;
|
||||
|
||||
ret = sdca_irq_data_populate(dev, regmap, NULL,
|
||||
function, entity,
|
||||
control, interrupt);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
ret = sdca_fdl_alloc_state(interrupt);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
ret = sdca_irq_request_locked(dev, info, irq,
|
||||
interrupt->name,
|
||||
fdl_owner_handler,
|
||||
interrupt);
|
||||
if (ret) {
|
||||
dev_err(dev, "failed to request irq %s: %d\n",
|
||||
interrupt->name, ret);
|
||||
return ret;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
EXPORT_SYMBOL_NS_GPL(sdca_irq_populate_early, "SND_SOC_SDCA");
|
||||
|
||||
/**
|
||||
* sdca_irq_populate - Request all the individual IRQs for an SDCA Function
|
||||
* @function: Pointer to the SDCA Function.
|
||||
|
|
|
|||
Loading…
Reference in New Issue