Commit 8f986fd7 authored by Thomas Gleixner's avatar Thomas Gleixner

genirq/msi: Provide msi_domain_ops:: Prepare_desc()

The existing MSI domain ops msi_prepare() and set_desc() turned out to be
unsuitable for implementing IMS support.

msi_prepare() does not operate on the MSI descriptors. set_desc() lacks
an irq_domain pointer and has a completely different purpose.

Introduce a prepare_desc() op which allows IMS implementations to amend an
MSI descriptor which was allocated by the core code, e.g. by adjusting the
iomem base or adding some data based on the allocated index. This is way
better than requiring that all IMS domain implementations preallocate the
MSI descriptor and then allocate the interrupt.
Signed-off-by: default avatarThomas Gleixner <tglx@linutronix.de>
Reviewed-by: default avatarKevin Tian <kevin.tian@intel.com>
Acked-by: default avatarMarc Zyngier <maz@kernel.org>
Link: https://lore.kernel.org/r/20221124232326.444560717@linutronix.de
parent efd42049
...@@ -410,6 +410,8 @@ struct msi_domain_info; ...@@ -410,6 +410,8 @@ struct msi_domain_info;
* @msi_init: Domain specific init function for MSI interrupts * @msi_init: Domain specific init function for MSI interrupts
* @msi_free: Domain specific function to free a MSI interrupts * @msi_free: Domain specific function to free a MSI interrupts
* @msi_prepare: Prepare the allocation of the interrupts in the domain * @msi_prepare: Prepare the allocation of the interrupts in the domain
* @prepare_desc: Optional function to prepare the allocated MSI descriptor
* in the domain
* @set_desc: Set the msi descriptor for an interrupt * @set_desc: Set the msi descriptor for an interrupt
* @domain_alloc_irqs: Optional function to override the default allocation * @domain_alloc_irqs: Optional function to override the default allocation
* function. * function.
...@@ -421,7 +423,7 @@ struct msi_domain_info; ...@@ -421,7 +423,7 @@ struct msi_domain_info;
* @get_hwirq, @msi_init and @msi_free are callbacks used by the underlying * @get_hwirq, @msi_init and @msi_free are callbacks used by the underlying
* irqdomain. * irqdomain.
* *
* @msi_check, @msi_prepare and @set_desc are callbacks used by the * @msi_check, @msi_prepare, @prepare_desc and @set_desc are callbacks used by the
* msi_domain_alloc/free_irqs*() variants. * msi_domain_alloc/free_irqs*() variants.
* *
* @domain_alloc_irqs, @domain_free_irqs can be used to override the * @domain_alloc_irqs, @domain_free_irqs can be used to override the
...@@ -444,6 +446,8 @@ struct msi_domain_ops { ...@@ -444,6 +446,8 @@ struct msi_domain_ops {
int (*msi_prepare)(struct irq_domain *domain, int (*msi_prepare)(struct irq_domain *domain,
struct device *dev, int nvec, struct device *dev, int nvec,
msi_alloc_info_t *arg); msi_alloc_info_t *arg);
void (*prepare_desc)(struct irq_domain *domain, msi_alloc_info_t *arg,
struct msi_desc *desc);
void (*set_desc)(msi_alloc_info_t *arg, void (*set_desc)(msi_alloc_info_t *arg,
struct msi_desc *desc); struct msi_desc *desc);
int (*domain_alloc_irqs)(struct irq_domain *domain, int (*domain_alloc_irqs)(struct irq_domain *domain,
......
...@@ -1254,6 +1254,9 @@ static int __msi_domain_alloc_irqs(struct device *dev, struct irq_domain *domain ...@@ -1254,6 +1254,9 @@ static int __msi_domain_alloc_irqs(struct device *dev, struct irq_domain *domain
if (WARN_ON_ONCE(allocated >= ctrl->nirqs)) if (WARN_ON_ONCE(allocated >= ctrl->nirqs))
return -EINVAL; return -EINVAL;
if (ops->prepare_desc)
ops->prepare_desc(domain, &arg, desc);
ops->set_desc(&arg, desc); ops->set_desc(&arg, desc);
virq = __irq_domain_alloc_irqs(domain, -1, desc->nvec_used, virq = __irq_domain_alloc_irqs(domain, -1, desc->nvec_used,
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment