I'm trying to use interrupts to see if there are errors in an UART 16550D and when a character is available to be read.
The UART configurations is as follows:
#define UART 0x03f8 // Endereço da Porta Serial - I (com1)
#define UART_IER 1
#define UART_LCR 3
#define UART_LSR 5
#define UART_DLL 0 /* Out: Divisor Latch Low */
#define UART_DLM 1 /* Out: Divisor Latch High */
#define UART_LSR_THRE 0x20 /* Transmit-hold-register empty */
#define UART_LSR_DR 0x01 /* Receiver data ready */
#define UART_RX 0 /* In: Receive buffer */
#define UART_TX 0 /* Out: Transmit buffer */
void UART_init(void){
outb( 0x80 , UART + UART_LCR );
outb( 0x00 , UART + UART_DLM );
outb( 0x60 , UART + UART_DLL );
outb( 0x1f , UART + UART_LCR );
outb( 0x07 , UART + UART_IER );
return;
}
And the interrupt
irqreturn_t short_interrupt(int irq, void *dev_id){
printk("INTERRUPT HAPPENED. WILL NOW RETURN\n");
return 0;
}
static int seri_init(void){
int result, i;
UART_init();
request_irq(4, short_interrupt, SA_SHIRQ, "seri", NULL);
....
So for now I just want to see if the handler is called or not. 4 is defined as the IRQ in the virtual box settings I'm using.
What I want to know is, is there something wrong about this setup? When testing, I have no problem reading and processing what I'm reading. Thing is, the handler is never called.
The return from request_irq() is -22. There are no problems during compilation.
Change
To
I know this is an old post, but thought I would throw up an answer. use gpio_to_irq to get interrupt number. The third parameter determines when the interrupt occurs.
-22 is
EINVAL
and I think it's because of NULL last argument. This page: http://www.makelinux.net/books/lkd2/ch06lev1sec3 says:So requesting a shared irq wiht NULLed dev_id won't work.
My analysis on why the interrupt handler is not triggered:
(1) Make sure the first parameter passed to request_irq(virq,...) is hardware irq number or virtual irq number. On some platform, there is a mapping between the hardware irq and the number which used by request_irq(...). If there is a mapping on your box, then you connect your handler to other interrupt source mistakenly;
(2) Make sure the interrupt mask register on 16550D is set correctly. I think there should be an interrupt mask register on 16550D which can mask/unmask the interrupt events;
(3) Check the return value of request_irq(...) to make sure the interrupt is connected successfully.
Hope the above help you.