root/drivers/dma/ipu/ipu_irq.c

/* [<][>][^][v][top][bottom][index][help] */

DEFINITIONS

This source file includes following definitions.
  1. ipu_read_reg
  2. ipu_write_reg
  3. src2map
  4. ipu_irq_unmask
  5. ipu_irq_mask
  6. ipu_irq_ack
  7. ipu_irq_status
  8. ipu_irq_map
  9. ipu_irq_unmap
  10. ipu_irq_handler
  11. ipu_irq_attach_irq
  12. ipu_irq_detach_irq

   1 // SPDX-License-Identifier: GPL-2.0-only
   2 /*
   3  * Copyright (C) 2008
   4  * Guennadi Liakhovetski, DENX Software Engineering, <lg@denx.de>
   5  */
   6 
   7 #include <linux/init.h>
   8 #include <linux/err.h>
   9 #include <linux/spinlock.h>
  10 #include <linux/delay.h>
  11 #include <linux/clk.h>
  12 #include <linux/irq.h>
  13 #include <linux/io.h>
  14 #include <linux/module.h>
  15 #include <linux/dma/ipu-dma.h>
  16 
  17 #include "ipu_intern.h"
  18 
  19 /*
  20  * Register read / write - shall be inlined by the compiler
  21  */
  22 static u32 ipu_read_reg(struct ipu *ipu, unsigned long reg)
  23 {
  24         return __raw_readl(ipu->reg_ipu + reg);
  25 }
  26 
  27 static void ipu_write_reg(struct ipu *ipu, u32 value, unsigned long reg)
  28 {
  29         __raw_writel(value, ipu->reg_ipu + reg);
  30 }
  31 
  32 
  33 /*
  34  * IPU IRQ chip driver
  35  */
  36 
  37 #define IPU_IRQ_NR_FN_BANKS 3
  38 #define IPU_IRQ_NR_ERR_BANKS 2
  39 #define IPU_IRQ_NR_BANKS (IPU_IRQ_NR_FN_BANKS + IPU_IRQ_NR_ERR_BANKS)
  40 
  41 struct ipu_irq_bank {
  42         unsigned int    control;
  43         unsigned int    status;
  44         struct ipu      *ipu;
  45 };
  46 
  47 static struct ipu_irq_bank irq_bank[IPU_IRQ_NR_BANKS] = {
  48         /* 3 groups of functional interrupts */
  49         {
  50                 .control        = IPU_INT_CTRL_1,
  51                 .status         = IPU_INT_STAT_1,
  52         }, {
  53                 .control        = IPU_INT_CTRL_2,
  54                 .status         = IPU_INT_STAT_2,
  55         }, {
  56                 .control        = IPU_INT_CTRL_3,
  57                 .status         = IPU_INT_STAT_3,
  58         },
  59         /* 2 groups of error interrupts */
  60         {
  61                 .control        = IPU_INT_CTRL_4,
  62                 .status         = IPU_INT_STAT_4,
  63         }, {
  64                 .control        = IPU_INT_CTRL_5,
  65                 .status         = IPU_INT_STAT_5,
  66         },
  67 };
  68 
  69 struct ipu_irq_map {
  70         unsigned int            irq;
  71         int                     source;
  72         struct ipu_irq_bank     *bank;
  73         struct ipu              *ipu;
  74 };
  75 
  76 static struct ipu_irq_map irq_map[CONFIG_MX3_IPU_IRQS];
  77 /* Protects allocations from the above array of maps */
  78 static DEFINE_MUTEX(map_lock);
  79 /* Protects register accesses and individual mappings */
  80 static DEFINE_RAW_SPINLOCK(bank_lock);
  81 
  82 static struct ipu_irq_map *src2map(unsigned int src)
  83 {
  84         int i;
  85 
  86         for (i = 0; i < CONFIG_MX3_IPU_IRQS; i++)
  87                 if (irq_map[i].source == src)
  88                         return irq_map + i;
  89 
  90         return NULL;
  91 }
  92 
  93 static void ipu_irq_unmask(struct irq_data *d)
  94 {
  95         struct ipu_irq_map *map = irq_data_get_irq_chip_data(d);
  96         struct ipu_irq_bank *bank;
  97         uint32_t reg;
  98         unsigned long lock_flags;
  99 
 100         raw_spin_lock_irqsave(&bank_lock, lock_flags);
 101 
 102         bank = map->bank;
 103         if (!bank) {
 104                 raw_spin_unlock_irqrestore(&bank_lock, lock_flags);
 105                 pr_err("IPU: %s(%u) - unmapped!\n", __func__, d->irq);
 106                 return;
 107         }
 108 
 109         reg = ipu_read_reg(bank->ipu, bank->control);
 110         reg |= (1UL << (map->source & 31));
 111         ipu_write_reg(bank->ipu, reg, bank->control);
 112 
 113         raw_spin_unlock_irqrestore(&bank_lock, lock_flags);
 114 }
 115 
 116 static void ipu_irq_mask(struct irq_data *d)
 117 {
 118         struct ipu_irq_map *map = irq_data_get_irq_chip_data(d);
 119         struct ipu_irq_bank *bank;
 120         uint32_t reg;
 121         unsigned long lock_flags;
 122 
 123         raw_spin_lock_irqsave(&bank_lock, lock_flags);
 124 
 125         bank = map->bank;
 126         if (!bank) {
 127                 raw_spin_unlock_irqrestore(&bank_lock, lock_flags);
 128                 pr_err("IPU: %s(%u) - unmapped!\n", __func__, d->irq);
 129                 return;
 130         }
 131 
 132         reg = ipu_read_reg(bank->ipu, bank->control);
 133         reg &= ~(1UL << (map->source & 31));
 134         ipu_write_reg(bank->ipu, reg, bank->control);
 135 
 136         raw_spin_unlock_irqrestore(&bank_lock, lock_flags);
 137 }
 138 
 139 static void ipu_irq_ack(struct irq_data *d)
 140 {
 141         struct ipu_irq_map *map = irq_data_get_irq_chip_data(d);
 142         struct ipu_irq_bank *bank;
 143         unsigned long lock_flags;
 144 
 145         raw_spin_lock_irqsave(&bank_lock, lock_flags);
 146 
 147         bank = map->bank;
 148         if (!bank) {
 149                 raw_spin_unlock_irqrestore(&bank_lock, lock_flags);
 150                 pr_err("IPU: %s(%u) - unmapped!\n", __func__, d->irq);
 151                 return;
 152         }
 153 
 154         ipu_write_reg(bank->ipu, 1UL << (map->source & 31), bank->status);
 155         raw_spin_unlock_irqrestore(&bank_lock, lock_flags);
 156 }
 157 
 158 /**
 159  * ipu_irq_status() - returns the current interrupt status of the specified IRQ.
 160  * @irq:        interrupt line to get status for.
 161  * @return:     true if the interrupt is pending/asserted or false if the
 162  *              interrupt is not pending.
 163  */
 164 bool ipu_irq_status(unsigned int irq)
 165 {
 166         struct ipu_irq_map *map = irq_get_chip_data(irq);
 167         struct ipu_irq_bank *bank;
 168         unsigned long lock_flags;
 169         bool ret;
 170 
 171         raw_spin_lock_irqsave(&bank_lock, lock_flags);
 172         bank = map->bank;
 173         ret = bank && ipu_read_reg(bank->ipu, bank->status) &
 174                 (1UL << (map->source & 31));
 175         raw_spin_unlock_irqrestore(&bank_lock, lock_flags);
 176 
 177         return ret;
 178 }
 179 
 180 /**
 181  * ipu_irq_map() - map an IPU interrupt source to an IRQ number
 182  * @source:     interrupt source bit position (see below)
 183  * @return:     mapped IRQ number or negative error code
 184  *
 185  * The source parameter has to be explained further. On i.MX31 IPU has 137 IRQ
 186  * sources, they are broken down in 5 32-bit registers, like 32, 32, 24, 32, 17.
 187  * However, the source argument of this function is not the sequence number of
 188  * the possible IRQ, but rather its bit position. So, first interrupt in fourth
 189  * register has source number 96, and not 88. This makes calculations easier,
 190  * and also provides forward compatibility with any future IPU implementations
 191  * with any interrupt bit assignments.
 192  */
 193 int ipu_irq_map(unsigned int source)
 194 {
 195         int i, ret = -ENOMEM;
 196         struct ipu_irq_map *map;
 197 
 198         might_sleep();
 199 
 200         mutex_lock(&map_lock);
 201         map = src2map(source);
 202         if (map) {
 203                 pr_err("IPU: Source %u already mapped to IRQ %u\n", source, map->irq);
 204                 ret = -EBUSY;
 205                 goto out;
 206         }
 207 
 208         for (i = 0; i < CONFIG_MX3_IPU_IRQS; i++) {
 209                 if (irq_map[i].source < 0) {
 210                         unsigned long lock_flags;
 211 
 212                         raw_spin_lock_irqsave(&bank_lock, lock_flags);
 213                         irq_map[i].source = source;
 214                         irq_map[i].bank = irq_bank + source / 32;
 215                         raw_spin_unlock_irqrestore(&bank_lock, lock_flags);
 216 
 217                         ret = irq_map[i].irq;
 218                         pr_debug("IPU: mapped source %u to IRQ %u\n",
 219                                  source, ret);
 220                         break;
 221                 }
 222         }
 223 out:
 224         mutex_unlock(&map_lock);
 225 
 226         if (ret < 0)
 227                 pr_err("IPU: couldn't map source %u: %d\n", source, ret);
 228 
 229         return ret;
 230 }
 231 
 232 /**
 233  * ipu_irq_map() - map an IPU interrupt source to an IRQ number
 234  * @source:     interrupt source bit position (see ipu_irq_map())
 235  * @return:     0 or negative error code
 236  */
 237 int ipu_irq_unmap(unsigned int source)
 238 {
 239         int i, ret = -EINVAL;
 240 
 241         might_sleep();
 242 
 243         mutex_lock(&map_lock);
 244         for (i = 0; i < CONFIG_MX3_IPU_IRQS; i++) {
 245                 if (irq_map[i].source == source) {
 246                         unsigned long lock_flags;
 247 
 248                         pr_debug("IPU: unmapped source %u from IRQ %u\n",
 249                                  source, irq_map[i].irq);
 250 
 251                         raw_spin_lock_irqsave(&bank_lock, lock_flags);
 252                         irq_map[i].source = -EINVAL;
 253                         irq_map[i].bank = NULL;
 254                         raw_spin_unlock_irqrestore(&bank_lock, lock_flags);
 255 
 256                         ret = 0;
 257                         break;
 258                 }
 259         }
 260         mutex_unlock(&map_lock);
 261 
 262         return ret;
 263 }
 264 
 265 /* Chained IRQ handler for IPU function and error interrupt */
 266 static void ipu_irq_handler(struct irq_desc *desc)
 267 {
 268         struct ipu *ipu = irq_desc_get_handler_data(desc);
 269         u32 status;
 270         int i, line;
 271 
 272         for (i = 0; i < IPU_IRQ_NR_BANKS; i++) {
 273                 struct ipu_irq_bank *bank = irq_bank + i;
 274 
 275                 raw_spin_lock(&bank_lock);
 276                 status = ipu_read_reg(ipu, bank->status);
 277                 /*
 278                  * Don't think we have to clear all interrupts here, they will
 279                  * be acked by ->handle_irq() (handle_level_irq). However, we
 280                  * might want to clear unhandled interrupts after the loop...
 281                  */
 282                 status &= ipu_read_reg(ipu, bank->control);
 283                 raw_spin_unlock(&bank_lock);
 284                 while ((line = ffs(status))) {
 285                         struct ipu_irq_map *map;
 286                         unsigned int irq;
 287 
 288                         line--;
 289                         status &= ~(1UL << line);
 290 
 291                         raw_spin_lock(&bank_lock);
 292                         map = src2map(32 * i + line);
 293                         if (!map) {
 294                                 raw_spin_unlock(&bank_lock);
 295                                 pr_err("IPU: Interrupt on unmapped source %u bank %d\n",
 296                                        line, i);
 297                                 continue;
 298                         }
 299                         irq = map->irq;
 300                         raw_spin_unlock(&bank_lock);
 301                         generic_handle_irq(irq);
 302                 }
 303         }
 304 }
 305 
 306 static struct irq_chip ipu_irq_chip = {
 307         .name           = "ipu_irq",
 308         .irq_ack        = ipu_irq_ack,
 309         .irq_mask       = ipu_irq_mask,
 310         .irq_unmask     = ipu_irq_unmask,
 311 };
 312 
 313 /* Install the IRQ handler */
 314 int __init ipu_irq_attach_irq(struct ipu *ipu, struct platform_device *dev)
 315 {
 316         unsigned int irq, i;
 317         int irq_base = irq_alloc_descs(-1, 0, CONFIG_MX3_IPU_IRQS,
 318                                        numa_node_id());
 319 
 320         if (irq_base < 0)
 321                 return irq_base;
 322 
 323         for (i = 0; i < IPU_IRQ_NR_BANKS; i++)
 324                 irq_bank[i].ipu = ipu;
 325 
 326         for (i = 0; i < CONFIG_MX3_IPU_IRQS; i++) {
 327                 int ret;
 328 
 329                 irq = irq_base + i;
 330                 ret = irq_set_chip(irq, &ipu_irq_chip);
 331                 if (ret < 0)
 332                         return ret;
 333                 ret = irq_set_chip_data(irq, irq_map + i);
 334                 if (ret < 0)
 335                         return ret;
 336                 irq_map[i].ipu = ipu;
 337                 irq_map[i].irq = irq;
 338                 irq_map[i].source = -EINVAL;
 339                 irq_set_handler(irq, handle_level_irq);
 340                 irq_clear_status_flags(irq, IRQ_NOREQUEST | IRQ_NOPROBE);
 341         }
 342 
 343         irq_set_chained_handler_and_data(ipu->irq_fn, ipu_irq_handler, ipu);
 344 
 345         irq_set_chained_handler_and_data(ipu->irq_err, ipu_irq_handler, ipu);
 346 
 347         ipu->irq_base = irq_base;
 348 
 349         return 0;
 350 }
 351 
 352 void ipu_irq_detach_irq(struct ipu *ipu, struct platform_device *dev)
 353 {
 354         unsigned int irq, irq_base;
 355 
 356         irq_base = ipu->irq_base;
 357 
 358         irq_set_chained_handler_and_data(ipu->irq_fn, NULL, NULL);
 359 
 360         irq_set_chained_handler_and_data(ipu->irq_err, NULL, NULL);
 361 
 362         for (irq = irq_base; irq < irq_base + CONFIG_MX3_IPU_IRQS; irq++) {
 363                 irq_set_status_flags(irq, IRQ_NOREQUEST);
 364                 irq_set_chip(irq, NULL);
 365                 irq_set_chip_data(irq, NULL);
 366         }
 367 }

/* [<][>][^][v][top][bottom][index][help] */