Skip to content

Commit e6f67ce

Browse files
hcodinaKAGA-KOKO
authored andcommitted
irqdomain: Add support for generic irq chips creation before publishing a domain
The current API functions create an irq_domain and also publish this newly created to domain. Once an irq_domain is published, consumers can request IRQ in order to use them. Some interrupt controller drivers have to perform some more operations with the created irq_domain in order to have it ready to be used. For instance: - Allocate generic irq chips with irq_alloc_domain_generic_chips() - Retrieve the generic irq chips with irq_get_domain_generic_chip() - Initialize retrieved chips: set register base address and offsets, set several hooks such as irq_mask, irq_unmask, ... With the newly introduced irq_domain_alloc_generic_chips(), an interrupt controller driver can use the irq_domain_chip_generic_info structure and set the init() hook to perform its generic chips initialization. In order to avoid a window where the domain is published but not yet ready to be used, handle the generic chip creation (i.e the irq_domain_alloc_generic_chips() call) before the domain is published. Suggested-by: Thomas Gleixner <[email protected]> Signed-off-by: Herve Codina <[email protected]> Signed-off-by: Thomas Gleixner <[email protected]> Link: https://lore.kernel.org/r/[email protected]
1 parent fea922e commit e6f67ce

File tree

2 files changed

+22
-1
lines changed

2 files changed

+22
-1
lines changed

include/linux/irqdomain.h

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -210,6 +210,9 @@ enum {
210210
/* Irq domain is a MSI device domain */
211211
IRQ_DOMAIN_FLAG_MSI_DEVICE = (1 << 9),
212212

213+
/* Irq domain must destroy generic chips when removed */
214+
IRQ_DOMAIN_FLAG_DESTROY_GC = (1 << 10),
215+
213216
/*
214217
* Flags starting from IRQ_DOMAIN_FLAG_NONCORE are reserved
215218
* for implementation specific purposes and ignored by the
@@ -259,6 +262,9 @@ static inline struct fwnode_handle *irq_domain_alloc_fwnode(phys_addr_t *pa)
259262
}
260263

261264
void irq_domain_free_fwnode(struct fwnode_handle *fwnode);
265+
266+
struct irq_domain_chip_generic_info;
267+
262268
/**
263269
* struct irq_domain_info - Domain information structure
264270
* @fwnode: firmware node for the interrupt controller
@@ -270,6 +276,8 @@ void irq_domain_free_fwnode(struct fwnode_handle *fwnode);
270276
* @bus_token: Domain bus token
271277
* @ops: Domain operation callbacks
272278
* @host_data: Controller private data pointer
279+
* @dgc_info: Geneneric chip information structure pointer used to
280+
* create generic chips for the domain if not NULL.
273281
* @init: Function called when the domain is created.
274282
* Allow to do some additional domain initialisation.
275283
* @exit: Function called when the domain is destroyed.
@@ -290,6 +298,7 @@ struct irq_domain_info {
290298
*/
291299
struct irq_domain *parent;
292300
#endif
301+
struct irq_domain_chip_generic_info *dgc_info;
293302
int (*init)(struct irq_domain *d);
294303
void (*exit)(struct irq_domain *d);
295304
};

kernel/irq/irqdomain.c

Lines changed: 13 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -292,16 +292,25 @@ struct irq_domain *irq_domain_instantiate(const struct irq_domain_info *info)
292292
}
293293
#endif
294294

295+
if (info->dgc_info) {
296+
err = irq_domain_alloc_generic_chips(domain, info->dgc_info);
297+
if (err)
298+
goto err_domain_free;
299+
}
300+
295301
if (info->init) {
296302
err = info->init(domain);
297303
if (err)
298-
goto err_domain_free;
304+
goto err_domain_gc_remove;
299305
}
300306

301307
__irq_domain_publish(domain);
302308

303309
return domain;
304310

311+
err_domain_gc_remove:
312+
if (info->dgc_info)
313+
irq_domain_remove_generic_chips(domain);
305314
err_domain_free:
306315
irq_domain_free(domain);
307316
return ERR_PTR(err);
@@ -369,6 +378,9 @@ void irq_domain_remove(struct irq_domain *domain)
369378

370379
mutex_unlock(&irq_domain_mutex);
371380

381+
if (domain->flags & IRQ_DOMAIN_FLAG_DESTROY_GC)
382+
irq_domain_remove_generic_chips(domain);
383+
372384
pr_debug("Removed domain %s\n", domain->name);
373385
irq_domain_free(domain);
374386
}

0 commit comments

Comments
 (0)