LCOV - code coverage report
Current view: top level - include/linux - irqdomain.h (source / functions) Hit Total Coverage
Test: coverage.info Lines: 0 16 0.0 %
Date: 2022-12-09 01:23:36 Functions: 0 0 -

          Line data    Source code
       1             : /* SPDX-License-Identifier: GPL-2.0 */
       2             : /*
       3             :  * irq_domain - IRQ translation domains
       4             :  *
       5             :  * Translation infrastructure between hw and linux irq numbers.  This is
       6             :  * helpful for interrupt controllers to implement mapping between hardware
       7             :  * irq numbers and the Linux irq number space.
       8             :  *
       9             :  * irq_domains also have hooks for translating device tree or other
      10             :  * firmware interrupt representations into a hardware irq number that
      11             :  * can be mapped back to a Linux irq number without any extra platform
      12             :  * support code.
      13             :  *
      14             :  * Interrupt controller "domain" data structure. This could be defined as a
      15             :  * irq domain controller. That is, it handles the mapping between hardware
      16             :  * and virtual interrupt numbers for a given interrupt domain. The domain
      17             :  * structure is generally created by the PIC code for a given PIC instance
      18             :  * (though a domain can cover more than one PIC if they have a flat number
      19             :  * model). It's the domain callbacks that are responsible for setting the
      20             :  * irq_chip on a given irq_desc after it's been mapped.
      21             :  *
      22             :  * The host code and data structures use a fwnode_handle pointer to
      23             :  * identify the domain. In some cases, and in order to preserve source
      24             :  * code compatibility, this fwnode pointer is "upgraded" to a DT
      25             :  * device_node. For those firmware infrastructures that do not provide
      26             :  * a unique identifier for an interrupt controller, the irq_domain
      27             :  * code offers a fwnode allocator.
      28             :  */
      29             : 
      30             : #ifndef _LINUX_IRQDOMAIN_H
      31             : #define _LINUX_IRQDOMAIN_H
      32             : 
      33             : #include <linux/types.h>
      34             : #include <linux/irqhandler.h>
      35             : #include <linux/of.h>
      36             : #include <linux/mutex.h>
      37             : #include <linux/radix-tree.h>
      38             : 
      39             : struct device_node;
      40             : struct fwnode_handle;
      41             : struct irq_domain;
      42             : struct irq_chip;
      43             : struct irq_data;
      44             : struct irq_desc;
      45             : struct cpumask;
      46             : struct seq_file;
      47             : struct irq_affinity_desc;
      48             : 
      49             : #define IRQ_DOMAIN_IRQ_SPEC_PARAMS 16
      50             : 
      51             : /**
      52             :  * struct irq_fwspec - generic IRQ specifier structure
      53             :  *
      54             :  * @fwnode:             Pointer to a firmware-specific descriptor
      55             :  * @param_count:        Number of device-specific parameters
      56             :  * @param:              Device-specific parameters
      57             :  *
      58             :  * This structure, directly modeled after of_phandle_args, is used to
      59             :  * pass a device-specific description of an interrupt.
      60             :  */
      61             : struct irq_fwspec {
      62             :         struct fwnode_handle *fwnode;
      63             :         int param_count;
      64             :         u32 param[IRQ_DOMAIN_IRQ_SPEC_PARAMS];
      65             : };
      66             : 
      67             : /* Conversion function from of_phandle_args fields to fwspec  */
      68             : void of_phandle_args_to_fwspec(struct device_node *np, const u32 *args,
      69             :                                unsigned int count, struct irq_fwspec *fwspec);
      70             : 
      71             : /*
      72             :  * Should several domains have the same device node, but serve
      73             :  * different purposes (for example one domain is for PCI/MSI, and the
      74             :  * other for wired IRQs), they can be distinguished using a
      75             :  * bus-specific token. Most domains are expected to only carry
      76             :  * DOMAIN_BUS_ANY.
      77             :  */
      78             : enum irq_domain_bus_token {
      79             :         DOMAIN_BUS_ANY          = 0,
      80             :         DOMAIN_BUS_WIRED,
      81             :         DOMAIN_BUS_GENERIC_MSI,
      82             :         DOMAIN_BUS_PCI_MSI,
      83             :         DOMAIN_BUS_PLATFORM_MSI,
      84             :         DOMAIN_BUS_NEXUS,
      85             :         DOMAIN_BUS_IPI,
      86             :         DOMAIN_BUS_FSL_MC_MSI,
      87             :         DOMAIN_BUS_TI_SCI_INTA_MSI,
      88             :         DOMAIN_BUS_WAKEUP,
      89             :         DOMAIN_BUS_VMD_MSI,
      90             : };
      91             : 
      92             : /**
      93             :  * struct irq_domain_ops - Methods for irq_domain objects
      94             :  * @match: Match an interrupt controller device node to a host, returns
      95             :  *         1 on a match
      96             :  * @map: Create or update a mapping between a virtual irq number and a hw
      97             :  *       irq number. This is called only once for a given mapping.
      98             :  * @unmap: Dispose of such a mapping
      99             :  * @xlate: Given a device tree node and interrupt specifier, decode
     100             :  *         the hardware irq number and linux irq type value.
     101             :  *
     102             :  * Functions below are provided by the driver and called whenever a new mapping
     103             :  * is created or an old mapping is disposed. The driver can then proceed to
     104             :  * whatever internal data structures management is required. It also needs
     105             :  * to setup the irq_desc when returning from map().
     106             :  */
     107             : struct irq_domain_ops {
     108             :         int (*match)(struct irq_domain *d, struct device_node *node,
     109             :                      enum irq_domain_bus_token bus_token);
     110             :         int (*select)(struct irq_domain *d, struct irq_fwspec *fwspec,
     111             :                       enum irq_domain_bus_token bus_token);
     112             :         int (*map)(struct irq_domain *d, unsigned int virq, irq_hw_number_t hw);
     113             :         void (*unmap)(struct irq_domain *d, unsigned int virq);
     114             :         int (*xlate)(struct irq_domain *d, struct device_node *node,
     115             :                      const u32 *intspec, unsigned int intsize,
     116             :                      unsigned long *out_hwirq, unsigned int *out_type);
     117             : #ifdef  CONFIG_IRQ_DOMAIN_HIERARCHY
     118             :         /* extended V2 interfaces to support hierarchy irq_domains */
     119             :         int (*alloc)(struct irq_domain *d, unsigned int virq,
     120             :                      unsigned int nr_irqs, void *arg);
     121             :         void (*free)(struct irq_domain *d, unsigned int virq,
     122             :                      unsigned int nr_irqs);
     123             :         int (*activate)(struct irq_domain *d, struct irq_data *irqd, bool reserve);
     124             :         void (*deactivate)(struct irq_domain *d, struct irq_data *irq_data);
     125             :         int (*translate)(struct irq_domain *d, struct irq_fwspec *fwspec,
     126             :                          unsigned long *out_hwirq, unsigned int *out_type);
     127             : #endif
     128             : #ifdef CONFIG_GENERIC_IRQ_DEBUGFS
     129             :         void (*debug_show)(struct seq_file *m, struct irq_domain *d,
     130             :                            struct irq_data *irqd, int ind);
     131             : #endif
     132             : };
     133             : 
     134             : extern const struct irq_domain_ops irq_generic_chip_ops;
     135             : 
     136             : struct irq_domain_chip_generic;
     137             : 
     138             : /**
     139             :  * struct irq_domain - Hardware interrupt number translation object
     140             :  * @link: Element in global irq_domain list.
     141             :  * @name: Name of interrupt domain
     142             :  * @ops: pointer to irq_domain methods
     143             :  * @host_data: private data pointer for use by owner.  Not touched by irq_domain
     144             :  *             core code.
     145             :  * @flags: host per irq_domain flags
     146             :  * @mapcount: The number of mapped interrupts
     147             :  *
     148             :  * Optional elements
     149             :  * @fwnode: Pointer to firmware node associated with the irq_domain. Pretty easy
     150             :  *          to swap it for the of_node via the irq_domain_get_of_node accessor
     151             :  * @gc: Pointer to a list of generic chips. There is a helper function for
     152             :  *      setting up one or more generic chips for interrupt controllers
     153             :  *      drivers using the generic chip library which uses this pointer.
     154             :  * @dev: Pointer to a device that the domain represent, and that will be
     155             :  *       used for power management purposes.
     156             :  * @parent: Pointer to parent irq_domain to support hierarchy irq_domains
     157             :  *
     158             :  * Revmap data, used internally by irq_domain
     159             :  * @revmap_size: Size of the linear map table @revmap[]
     160             :  * @revmap_tree: Radix map tree for hwirqs that don't fit in the linear map
     161             :  * @revmap_mutex: Lock for the revmap
     162             :  * @revmap: Linear table of irq_data pointers
     163             :  */
     164             : struct irq_domain {
     165             :         struct list_head link;
     166             :         const char *name;
     167             :         const struct irq_domain_ops *ops;
     168             :         void *host_data;
     169             :         unsigned int flags;
     170             :         unsigned int mapcount;
     171             : 
     172             :         /* Optional data */
     173             :         struct fwnode_handle *fwnode;
     174             :         enum irq_domain_bus_token bus_token;
     175             :         struct irq_domain_chip_generic *gc;
     176             :         struct device *dev;
     177             : #ifdef  CONFIG_IRQ_DOMAIN_HIERARCHY
     178             :         struct irq_domain *parent;
     179             : #endif
     180             : 
     181             :         /* reverse map data. The linear map gets appended to the irq_domain */
     182             :         irq_hw_number_t hwirq_max;
     183             :         unsigned int revmap_size;
     184             :         struct radix_tree_root revmap_tree;
     185             :         struct mutex revmap_mutex;
     186             :         struct irq_data __rcu *revmap[];
     187             : };
     188             : 
     189             : /* Irq domain flags */
     190             : enum {
     191             :         /* Irq domain is hierarchical */
     192             :         IRQ_DOMAIN_FLAG_HIERARCHY       = (1 << 0),
     193             : 
     194             :         /* Irq domain name was allocated in __irq_domain_add() */
     195             :         IRQ_DOMAIN_NAME_ALLOCATED       = (1 << 1),
     196             : 
     197             :         /* Irq domain is an IPI domain with virq per cpu */
     198             :         IRQ_DOMAIN_FLAG_IPI_PER_CPU     = (1 << 2),
     199             : 
     200             :         /* Irq domain is an IPI domain with single virq */
     201             :         IRQ_DOMAIN_FLAG_IPI_SINGLE      = (1 << 3),
     202             : 
     203             :         /* Irq domain implements MSIs */
     204             :         IRQ_DOMAIN_FLAG_MSI             = (1 << 4),
     205             : 
     206             :         /* Irq domain implements MSI remapping */
     207             :         IRQ_DOMAIN_FLAG_MSI_REMAP       = (1 << 5),
     208             : 
     209             :         /*
     210             :          * Quirk to handle MSI implementations which do not provide
     211             :          * masking. Currently known to affect x86, but partially
     212             :          * handled in core code.
     213             :          */
     214             :         IRQ_DOMAIN_MSI_NOMASK_QUIRK     = (1 << 6),
     215             : 
     216             :         /* Irq domain doesn't translate anything */
     217             :         IRQ_DOMAIN_FLAG_NO_MAP          = (1 << 7),
     218             : 
     219             :         /*
     220             :          * Flags starting from IRQ_DOMAIN_FLAG_NONCORE are reserved
     221             :          * for implementation specific purposes and ignored by the
     222             :          * core code.
     223             :          */
     224             :         IRQ_DOMAIN_FLAG_NONCORE         = (1 << 16),
     225             : };
     226             : 
     227             : static inline struct device_node *irq_domain_get_of_node(struct irq_domain *d)
     228             : {
     229           0 :         return to_of_node(d->fwnode);
     230             : }
     231             : 
     232             : static inline void irq_domain_set_pm_device(struct irq_domain *d,
     233             :                                             struct device *dev)
     234             : {
     235             :         if (d)
     236             :                 d->dev = dev;
     237             : }
     238             : 
     239             : #ifdef CONFIG_IRQ_DOMAIN
     240             : struct fwnode_handle *__irq_domain_alloc_fwnode(unsigned int type, int id,
     241             :                                                 const char *name, phys_addr_t *pa);
     242             : 
     243             : enum {
     244             :         IRQCHIP_FWNODE_REAL,
     245             :         IRQCHIP_FWNODE_NAMED,
     246             :         IRQCHIP_FWNODE_NAMED_ID,
     247             : };
     248             : 
     249             : static inline
     250             : struct fwnode_handle *irq_domain_alloc_named_fwnode(const char *name)
     251             : {
     252             :         return __irq_domain_alloc_fwnode(IRQCHIP_FWNODE_NAMED, 0, name, NULL);
     253             : }
     254             : 
     255             : static inline
     256             : struct fwnode_handle *irq_domain_alloc_named_id_fwnode(const char *name, int id)
     257             : {
     258             :         return __irq_domain_alloc_fwnode(IRQCHIP_FWNODE_NAMED_ID, id, name,
     259             :                                          NULL);
     260             : }
     261             : 
     262             : static inline struct fwnode_handle *irq_domain_alloc_fwnode(phys_addr_t *pa)
     263             : {
     264             :         return __irq_domain_alloc_fwnode(IRQCHIP_FWNODE_REAL, 0, NULL, pa);
     265             : }
     266             : 
     267             : void irq_domain_free_fwnode(struct fwnode_handle *fwnode);
     268             : struct irq_domain *__irq_domain_add(struct fwnode_handle *fwnode, unsigned int size,
     269             :                                     irq_hw_number_t hwirq_max, int direct_max,
     270             :                                     const struct irq_domain_ops *ops,
     271             :                                     void *host_data);
     272             : struct irq_domain *irq_domain_create_simple(struct fwnode_handle *fwnode,
     273             :                                             unsigned int size,
     274             :                                             unsigned int first_irq,
     275             :                                             const struct irq_domain_ops *ops,
     276             :                                             void *host_data);
     277             : struct irq_domain *irq_domain_add_legacy(struct device_node *of_node,
     278             :                                          unsigned int size,
     279             :                                          unsigned int first_irq,
     280             :                                          irq_hw_number_t first_hwirq,
     281             :                                          const struct irq_domain_ops *ops,
     282             :                                          void *host_data);
     283             : struct irq_domain *irq_domain_create_legacy(struct fwnode_handle *fwnode,
     284             :                                             unsigned int size,
     285             :                                             unsigned int first_irq,
     286             :                                             irq_hw_number_t first_hwirq,
     287             :                                             const struct irq_domain_ops *ops,
     288             :                                             void *host_data);
     289             : extern struct irq_domain *irq_find_matching_fwspec(struct irq_fwspec *fwspec,
     290             :                                                    enum irq_domain_bus_token bus_token);
     291             : extern bool irq_domain_check_msi_remap(void);
     292             : extern void irq_set_default_host(struct irq_domain *host);
     293             : extern struct irq_domain *irq_get_default_host(void);
     294             : extern int irq_domain_alloc_descs(int virq, unsigned int nr_irqs,
     295             :                                   irq_hw_number_t hwirq, int node,
     296             :                                   const struct irq_affinity_desc *affinity);
     297             : 
     298             : static inline struct fwnode_handle *of_node_to_fwnode(struct device_node *node)
     299             : {
     300           0 :         return node ? &node->fwnode : NULL;
     301             : }
     302             : 
     303             : extern const struct fwnode_operations irqchip_fwnode_ops;
     304             : 
     305             : static inline bool is_fwnode_irqchip(struct fwnode_handle *fwnode)
     306             : {
     307           0 :         return fwnode && fwnode->ops == &irqchip_fwnode_ops;
     308             : }
     309             : 
     310             : extern void irq_domain_update_bus_token(struct irq_domain *domain,
     311             :                                         enum irq_domain_bus_token bus_token);
     312             : 
     313             : static inline
     314             : struct irq_domain *irq_find_matching_fwnode(struct fwnode_handle *fwnode,
     315             :                                             enum irq_domain_bus_token bus_token)
     316             : {
     317           0 :         struct irq_fwspec fwspec = {
     318             :                 .fwnode = fwnode,
     319             :         };
     320             : 
     321           0 :         return irq_find_matching_fwspec(&fwspec, bus_token);
     322             : }
     323             : 
     324             : static inline struct irq_domain *irq_find_matching_host(struct device_node *node,
     325             :                                                         enum irq_domain_bus_token bus_token)
     326             : {
     327             :         return irq_find_matching_fwnode(of_node_to_fwnode(node), bus_token);
     328             : }
     329             : 
     330             : static inline struct irq_domain *irq_find_host(struct device_node *node)
     331             : {
     332             :         struct irq_domain *d;
     333             : 
     334             :         d = irq_find_matching_host(node, DOMAIN_BUS_WIRED);
     335             :         if (!d)
     336             :                 d = irq_find_matching_host(node, DOMAIN_BUS_ANY);
     337             : 
     338             :         return d;
     339             : }
     340             : 
     341             : static inline struct irq_domain *irq_domain_add_simple(struct device_node *of_node,
     342             :                                                        unsigned int size,
     343             :                                                        unsigned int first_irq,
     344             :                                                        const struct irq_domain_ops *ops,
     345             :                                                        void *host_data)
     346             : {
     347             :         return irq_domain_create_simple(of_node_to_fwnode(of_node), size, first_irq, ops, host_data);
     348             : }
     349             : 
     350             : /**
     351             :  * irq_domain_add_linear() - Allocate and register a linear revmap irq_domain.
     352             :  * @of_node: pointer to interrupt controller's device tree node.
     353             :  * @size: Number of interrupts in the domain.
     354             :  * @ops: map/unmap domain callbacks
     355             :  * @host_data: Controller private data pointer
     356             :  */
     357             : static inline struct irq_domain *irq_domain_add_linear(struct device_node *of_node,
     358             :                                          unsigned int size,
     359             :                                          const struct irq_domain_ops *ops,
     360             :                                          void *host_data)
     361             : {
     362           0 :         return __irq_domain_add(of_node_to_fwnode(of_node), size, size, 0, ops, host_data);
     363             : }
     364             : 
     365             : #ifdef CONFIG_IRQ_DOMAIN_NOMAP
     366             : static inline struct irq_domain *irq_domain_add_nomap(struct device_node *of_node,
     367             :                                          unsigned int max_irq,
     368             :                                          const struct irq_domain_ops *ops,
     369             :                                          void *host_data)
     370             : {
     371             :         return __irq_domain_add(of_node_to_fwnode(of_node), 0, max_irq, max_irq, ops, host_data);
     372             : }
     373             : 
     374             : extern unsigned int irq_create_direct_mapping(struct irq_domain *host);
     375             : #endif
     376             : 
     377             : static inline struct irq_domain *irq_domain_add_tree(struct device_node *of_node,
     378             :                                          const struct irq_domain_ops *ops,
     379             :                                          void *host_data)
     380             : {
     381             :         return __irq_domain_add(of_node_to_fwnode(of_node), 0, ~0, 0, ops, host_data);
     382             : }
     383             : 
     384             : static inline struct irq_domain *irq_domain_create_linear(struct fwnode_handle *fwnode,
     385             :                                          unsigned int size,
     386             :                                          const struct irq_domain_ops *ops,
     387             :                                          void *host_data)
     388             : {
     389           0 :         return __irq_domain_add(fwnode, size, size, 0, ops, host_data);
     390             : }
     391             : 
     392             : static inline struct irq_domain *irq_domain_create_tree(struct fwnode_handle *fwnode,
     393             :                                          const struct irq_domain_ops *ops,
     394             :                                          void *host_data)
     395             : {
     396           0 :         return __irq_domain_add(fwnode, 0, ~0, 0, ops, host_data);
     397             : }
     398             : 
     399             : extern void irq_domain_remove(struct irq_domain *host);
     400             : 
     401             : extern int irq_domain_associate(struct irq_domain *domain, unsigned int irq,
     402             :                                         irq_hw_number_t hwirq);
     403             : extern void irq_domain_associate_many(struct irq_domain *domain,
     404             :                                       unsigned int irq_base,
     405             :                                       irq_hw_number_t hwirq_base, int count);
     406             : 
     407             : extern unsigned int irq_create_mapping_affinity(struct irq_domain *host,
     408             :                                       irq_hw_number_t hwirq,
     409             :                                       const struct irq_affinity_desc *affinity);
     410             : extern unsigned int irq_create_fwspec_mapping(struct irq_fwspec *fwspec);
     411             : extern void irq_dispose_mapping(unsigned int virq);
     412             : 
     413             : static inline unsigned int irq_create_mapping(struct irq_domain *host,
     414             :                                               irq_hw_number_t hwirq)
     415             : {
     416           0 :         return irq_create_mapping_affinity(host, hwirq, NULL);
     417             : }
     418             : 
     419             : extern struct irq_desc *__irq_resolve_mapping(struct irq_domain *domain,
     420             :                                               irq_hw_number_t hwirq,
     421             :                                               unsigned int *irq);
     422             : 
     423             : static inline struct irq_desc *irq_resolve_mapping(struct irq_domain *domain,
     424             :                                                    irq_hw_number_t hwirq)
     425             : {
     426           0 :         return __irq_resolve_mapping(domain, hwirq, NULL);
     427             : }
     428             : 
     429             : /**
     430             :  * irq_find_mapping() - Find a linux irq from a hw irq number.
     431             :  * @domain: domain owning this hardware interrupt
     432             :  * @hwirq: hardware irq number in that domain space
     433             :  */
     434             : static inline unsigned int irq_find_mapping(struct irq_domain *domain,
     435             :                                             irq_hw_number_t hwirq)
     436             : {
     437             :         unsigned int irq;
     438             : 
     439           0 :         if (__irq_resolve_mapping(domain, hwirq, &irq))
     440           0 :                 return irq;
     441             : 
     442             :         return 0;
     443             : }
     444             : 
     445             : static inline unsigned int irq_linear_revmap(struct irq_domain *domain,
     446             :                                              irq_hw_number_t hwirq)
     447             : {
     448             :         return irq_find_mapping(domain, hwirq);
     449             : }
     450             : 
     451             : extern const struct irq_domain_ops irq_domain_simple_ops;
     452             : 
     453             : /* stock xlate functions */
     454             : int irq_domain_xlate_onecell(struct irq_domain *d, struct device_node *ctrlr,
     455             :                         const u32 *intspec, unsigned int intsize,
     456             :                         irq_hw_number_t *out_hwirq, unsigned int *out_type);
     457             : int irq_domain_xlate_twocell(struct irq_domain *d, struct device_node *ctrlr,
     458             :                         const u32 *intspec, unsigned int intsize,
     459             :                         irq_hw_number_t *out_hwirq, unsigned int *out_type);
     460             : int irq_domain_xlate_onetwocell(struct irq_domain *d, struct device_node *ctrlr,
     461             :                         const u32 *intspec, unsigned int intsize,
     462             :                         irq_hw_number_t *out_hwirq, unsigned int *out_type);
     463             : 
     464             : int irq_domain_translate_twocell(struct irq_domain *d,
     465             :                                  struct irq_fwspec *fwspec,
     466             :                                  unsigned long *out_hwirq,
     467             :                                  unsigned int *out_type);
     468             : 
     469             : int irq_domain_translate_onecell(struct irq_domain *d,
     470             :                                  struct irq_fwspec *fwspec,
     471             :                                  unsigned long *out_hwirq,
     472             :                                  unsigned int *out_type);
     473             : 
     474             : /* IPI functions */
     475             : int irq_reserve_ipi(struct irq_domain *domain, const struct cpumask *dest);
     476             : int irq_destroy_ipi(unsigned int irq, const struct cpumask *dest);
     477             : 
     478             : /* V2 interfaces to support hierarchy IRQ domains. */
     479             : extern struct irq_data *irq_domain_get_irq_data(struct irq_domain *domain,
     480             :                                                 unsigned int virq);
     481             : extern void irq_domain_set_info(struct irq_domain *domain, unsigned int virq,
     482             :                                 irq_hw_number_t hwirq,
     483             :                                 const struct irq_chip *chip,
     484             :                                 void *chip_data, irq_flow_handler_t handler,
     485             :                                 void *handler_data, const char *handler_name);
     486             : extern void irq_domain_reset_irq_data(struct irq_data *irq_data);
     487             : #ifdef  CONFIG_IRQ_DOMAIN_HIERARCHY
     488             : extern struct irq_domain *irq_domain_create_hierarchy(struct irq_domain *parent,
     489             :                         unsigned int flags, unsigned int size,
     490             :                         struct fwnode_handle *fwnode,
     491             :                         const struct irq_domain_ops *ops, void *host_data);
     492             : 
     493             : static inline struct irq_domain *irq_domain_add_hierarchy(struct irq_domain *parent,
     494             :                                             unsigned int flags,
     495             :                                             unsigned int size,
     496             :                                             struct device_node *node,
     497             :                                             const struct irq_domain_ops *ops,
     498             :                                             void *host_data)
     499             : {
     500             :         return irq_domain_create_hierarchy(parent, flags, size,
     501             :                                            of_node_to_fwnode(node),
     502             :                                            ops, host_data);
     503             : }
     504             : 
     505             : extern int __irq_domain_alloc_irqs(struct irq_domain *domain, int irq_base,
     506             :                                    unsigned int nr_irqs, int node, void *arg,
     507             :                                    bool realloc,
     508             :                                    const struct irq_affinity_desc *affinity);
     509             : extern void irq_domain_free_irqs(unsigned int virq, unsigned int nr_irqs);
     510             : extern int irq_domain_activate_irq(struct irq_data *irq_data, bool early);
     511             : extern void irq_domain_deactivate_irq(struct irq_data *irq_data);
     512             : 
     513             : static inline int irq_domain_alloc_irqs(struct irq_domain *domain,
     514             :                         unsigned int nr_irqs, int node, void *arg)
     515             : {
     516           0 :         return __irq_domain_alloc_irqs(domain, -1, nr_irqs, node, arg, false,
     517             :                                        NULL);
     518             : }
     519             : 
     520             : extern int irq_domain_alloc_irqs_hierarchy(struct irq_domain *domain,
     521             :                                            unsigned int irq_base,
     522             :                                            unsigned int nr_irqs, void *arg);
     523             : extern int irq_domain_set_hwirq_and_chip(struct irq_domain *domain,
     524             :                                          unsigned int virq,
     525             :                                          irq_hw_number_t hwirq,
     526             :                                          const struct irq_chip *chip,
     527             :                                          void *chip_data);
     528             : extern void irq_domain_free_irqs_common(struct irq_domain *domain,
     529             :                                         unsigned int virq,
     530             :                                         unsigned int nr_irqs);
     531             : extern void irq_domain_free_irqs_top(struct irq_domain *domain,
     532             :                                      unsigned int virq, unsigned int nr_irqs);
     533             : 
     534             : extern int irq_domain_push_irq(struct irq_domain *domain, int virq, void *arg);
     535             : extern int irq_domain_pop_irq(struct irq_domain *domain, int virq);
     536             : 
     537             : extern int irq_domain_alloc_irqs_parent(struct irq_domain *domain,
     538             :                                         unsigned int irq_base,
     539             :                                         unsigned int nr_irqs, void *arg);
     540             : 
     541             : extern void irq_domain_free_irqs_parent(struct irq_domain *domain,
     542             :                                         unsigned int irq_base,
     543             :                                         unsigned int nr_irqs);
     544             : 
     545             : extern int irq_domain_disconnect_hierarchy(struct irq_domain *domain,
     546             :                                            unsigned int virq);
     547             : 
     548             : static inline bool irq_domain_is_hierarchy(struct irq_domain *domain)
     549             : {
     550           0 :         return domain->flags & IRQ_DOMAIN_FLAG_HIERARCHY;
     551             : }
     552             : 
     553             : static inline bool irq_domain_is_ipi(struct irq_domain *domain)
     554             : {
     555             :         return domain->flags &
     556             :                 (IRQ_DOMAIN_FLAG_IPI_PER_CPU | IRQ_DOMAIN_FLAG_IPI_SINGLE);
     557             : }
     558             : 
     559             : static inline bool irq_domain_is_ipi_per_cpu(struct irq_domain *domain)
     560             : {
     561             :         return domain->flags & IRQ_DOMAIN_FLAG_IPI_PER_CPU;
     562             : }
     563             : 
     564             : static inline bool irq_domain_is_ipi_single(struct irq_domain *domain)
     565             : {
     566             :         return domain->flags & IRQ_DOMAIN_FLAG_IPI_SINGLE;
     567             : }
     568             : 
     569             : static inline bool irq_domain_is_msi(struct irq_domain *domain)
     570             : {
     571           0 :         return domain->flags & IRQ_DOMAIN_FLAG_MSI;
     572             : }
     573             : 
     574             : static inline bool irq_domain_is_msi_remap(struct irq_domain *domain)
     575             : {
     576           0 :         return domain->flags & IRQ_DOMAIN_FLAG_MSI_REMAP;
     577             : }
     578             : 
     579             : extern bool irq_domain_hierarchical_is_msi_remap(struct irq_domain *domain);
     580             : 
     581             : #else   /* CONFIG_IRQ_DOMAIN_HIERARCHY */
     582             : static inline int irq_domain_alloc_irqs(struct irq_domain *domain,
     583             :                         unsigned int nr_irqs, int node, void *arg)
     584             : {
     585             :         return -1;
     586             : }
     587             : 
     588             : static inline void irq_domain_free_irqs(unsigned int virq,
     589             :                                         unsigned int nr_irqs) { }
     590             : 
     591             : static inline bool irq_domain_is_hierarchy(struct irq_domain *domain)
     592             : {
     593             :         return false;
     594             : }
     595             : 
     596             : static inline bool irq_domain_is_ipi(struct irq_domain *domain)
     597             : {
     598             :         return false;
     599             : }
     600             : 
     601             : static inline bool irq_domain_is_ipi_per_cpu(struct irq_domain *domain)
     602             : {
     603             :         return false;
     604             : }
     605             : 
     606             : static inline bool irq_domain_is_ipi_single(struct irq_domain *domain)
     607             : {
     608             :         return false;
     609             : }
     610             : 
     611             : static inline bool irq_domain_is_msi(struct irq_domain *domain)
     612             : {
     613             :         return false;
     614             : }
     615             : 
     616             : static inline bool irq_domain_is_msi_remap(struct irq_domain *domain)
     617             : {
     618             :         return false;
     619             : }
     620             : 
     621             : static inline bool
     622             : irq_domain_hierarchical_is_msi_remap(struct irq_domain *domain)
     623             : {
     624             :         return false;
     625             : }
     626             : #endif  /* CONFIG_IRQ_DOMAIN_HIERARCHY */
     627             : 
     628             : #else /* CONFIG_IRQ_DOMAIN */
     629             : static inline void irq_dispose_mapping(unsigned int virq) { }
     630             : static inline struct irq_domain *irq_find_matching_fwnode(
     631             :         struct fwnode_handle *fwnode, enum irq_domain_bus_token bus_token)
     632             : {
     633             :         return NULL;
     634             : }
     635             : static inline bool irq_domain_check_msi_remap(void)
     636             : {
     637             :         return false;
     638             : }
     639             : #endif /* !CONFIG_IRQ_DOMAIN */
     640             : 
     641             : #endif /* _LINUX_IRQDOMAIN_H */

Generated by: LCOV version 1.14