QUERY: How to handle sharing of interrupt between different peripherals.
Hello everybody,
In our SOC (SPEArxxx), we have few peripherals which share common interrupt line. For example we can have GPIO (PL061), SPI (PL022) and SDIO (Arasan) sharing same physical IRQ line. Now there is a register in SOC which can give status of this interrupt line (i.e. source of interrupt). We have standard drivers for all of these, and these drivers don't request IRQ in shared mode.
How should we handle these IRQs now. One way i have been thinking of is to write a wrapper layer for this type of IRQs for our SOC, which will register actual IRQ numbers. Standard drivers can be provided virtual IRQ numbers for registration. Now this wrapper, based on source of interrupt can call the irq_handler for standard drivers.
Is this approach correct? Or is there any standard way to resolve these issues.
regards,
viresh kumar.
Quoted 2 lines · Viresh KUMAR
In our SOC (SPEArxxx), we have few peripherals which share common interrupt line.
how about set_irq_chained_handler ?
Quoted 4 lines · jassi brar
Quoted 2 lines · Viresh KUMAR
In our SOC (SPEArxxx), we have few peripherals which share common interrupt line.
how about
set_irq_chained_handler?
How about making drivers deal with shared irqs properly... most will, with a small amount of TLC support the usage of one interrupt line shared between more than one peripheral. PCs often share interrupts if the IRQ controller hasn't been put into an extended mode.
Signature · 4 lines
Ben Q: What's a light-year? A: One-third less calories than a regular year.
Quoted 11 lines · Ben Dooks
Quoted 4 lines · jassi brar
Quoted 2 lines · Viresh KUMAR
In our SOC (SPEArxxx), we have few peripherals which share common interrupt line.
how about
set_irq_chained_handler?How about making drivers deal with shared irqs properly... most will, with a small amount of TLC support the usage of one interrupt line shared between more than one peripheral. PCs often share interrupts if the IRQ controller hasn't been put into an extended mode.
I feel that is the correct way. Just need to send some patchs for exiting drivers.
Quoted 4 lines · jassi brar
Quoted 2 lines · Viresh KUMAR
In our SOC (SPEArxxx), we have few peripherals which share common interrupt line.
how about
set_irq_chained_handler?
I think it is not for this purpose. Better to use IRQF_SHARED in normal request_irq. what do you say?
Quoted 8 lines · Viresh KUMAR
Quoted 4 lines · jassi brar
Quoted 2 lines · Viresh KUMAR
In our SOC (SPEArxxx), we have few peripherals which share common interrupt line.
how about
set_irq_chained_handler?I think it is not for this purpose. Better to use
IRQF_SHAREDin normalrequest_irq. what do you say?
Of course, that is preferred if possible, as Ben already suggested. Btw, is your case not similar to having a common UART interrupt for Uart-Rx,Tx,Err irq ?
Quoted 5 lines · jassi brar
Quoted 4 lines · Viresh KUMAR
Quoted 3 lines · jassi brar
Quoted 2 lines · Viresh KUMAR
In our SOC (SPEArxxx), we have few peripherals which share common interrupt line.
Quoted 8 lines
Quoted 4 lines
Quoted 1 line
how about
set_irq_chained_handler?I think it is not for this purpose. Better to use
IRQF_SHAREDin normalrequest_irq. what do you say?Of course, that is preferred if possible, as Ben already suggested. Btw, is your case not similar to having a common UART interrupt for Uart-Rx,Tx,Err irq ?
We are now discussing two different things i suppose.
First: We have a common line for all type interrupts on UART.
This is handled well by the drivers (say - amba-pl011.c), and so we don't really have a issue here.
Second: Now UART, SDIO, SPI, I2S all have a common interrupt line, this is what we need to handle. For this IRQF_SHARED is a better way.
Quoted 2 lines · Viresh KUMAR
Second: Now UART, SDIO, SPI, I2S all have a common interrupt line, this is what we need to handle. For this
IRQF_SHAREDis a better way.
ok, I misunderstood.
Quoted 3 lines · Viresh KUMAR
Second: Now UART, SDIO, SPI, I2S all have a common interrupt line, this is what we need to handle. For this
IRQF_SHAREDis a better way.
No, chained handlers are the better way.
For example, your UARTs might be 16550-compatible. But you won't be able to use the already well-tested 16550 driver if it doesn't already use IRQF_SHARED. I haven't looked to see if it does, but that would be just one example...
b.g.
Signature · 4 lines
Bill Gatliff Embedded systems training and consulting http://billgatliff.com bgat at billgatliff.com
Quoted 4 lines · Viresh KUMAR
Quoted 2 lines · jassi brar
On Mon, Mar 15, 2010 at 1:37 PM, Viresh KUMAR <[email protected]> wrote:
Quoted 9 lines
Quoted 5 lines
Quoted 3 lines
In our SOC (SPEArxxx), we have few peripherals which share common interrupt line.
how about
set_irq_chained_handler?I think it is not for this purpose. Better to use
IRQF_SHAREDin normalrequest_irq. what do you say?
Actually, set_irq_chained_handler() is designed specifically for demultiplexing interrupt lines into independent descriptors, which is exactly what you want here. Otherwise, your drivers must know that they're sharing interrupts, which is a platform-specific assumption. You don't want that.
Take a look at how AT91 is handing their GPIO. Each bank has 32 pins, but only one shared interrupt signal. By demultiplexing that into 32 separate descriptors with set_irq_chained_handler(), drivers can all uniformly call request_irq() when one of their interrupt sources is tied to a GPIO--- same as if their interrupt source is a true IRQ line, an internal source, or whatever. That's what you want.
b.g.
Signature · 4 lines
Bill Gatliff Embedded systems training and consulting http://billgatliff.com bgat at billgatliff.com
Quoted 5 lines · Viresh KUMAR
In our SOC (SPEArxxx), we have few peripherals which share common interrupt line. For example we can have GPIO (PL061), SPI (PL022) and SDIO (Arasan) sharing same physical IRQ line. Now there is a register in SOC which can give status of this interrupt line (i.e. source of interrupt). We have standard drivers for all of these, and these drivers don't request IRQ in shared mode.
Ultimately, we have all ARM peripherals sharing one interrupt line - because the CPU only has one IRQ-level interrupt signal. That doesn't mean that we hang all interrupt handlers off the same IRQ number though.
Quoted 5 lines
How should we handle these IRQs now. One way i have been thinking of is to write a wrapper layer for this type of IRQs for our SOC, which will register actual IRQ numbers. Standard drivers can be provided virtual IRQ numbers for registration. Now this wrapper, based on source of interrupt can call the
irq_handlerfor standard drivers.
We do have a system for having a multi-level approach to interrupt decoding. Since you have a register which allows you to identify the source of the interrupt, I'd recommend for maximum system performance that you use it.
Shared interrupts have the disadvantage that you need to run each handler every time a device on the shared interrupt signals, which can be very wasteful both in terms of instruction cache lines and IO accesses.
Search arch/arm/ for set_irq_chained_handler to find examples of who to deal with multi-level handling of IRQs.
Quoted 10 lines · Russell King - ARM Linux
We do have a system for having a multi-level approach to interrupt decoding. Since you have a register which allows you to identify the source of the interrupt, I'd recommend for maximum system performance that you use it.
Shared interrupts have the disadvantage that you need to run each handler every time a device on the shared interrupt signals, which can be very wasteful both in terms of instruction cache lines and IO accesses.
Search
arch/arm/forset_irq_chained_handlerto find examples of who to deal with multi-level handling of IRQs.
OK. So we need to create virtual irqs (defined by s/w), for shared irqs which are mapped on to the real irq (defined by the H/W) through set_irq_chained_handler, right?
thanks for your help.
regards
Shiraz