Hi, i'm developing a bootloader on a pxa255 based board.
I have a problem using stuart RX interrupt.
When I enter a character on a console, it receives the correct
character when I read the STRBR register, but no jump to my IRQ
function.
Below is a function initializing stuart.
void serial_init(unsigned long baudrate)
{
unsigned int rate;
rate = UART_CLOCK/(16*baudrate);
_bl_disable_irq();
CKEN |= CKEN5_STUART;
STFCR = 0; /* disable TX/RX FIFO */
/* set baud rate */
STLCR = LCR_DLAB; /* DLAB on */
STDLL = rate & 0xFF;
STDLH = rate >> 8;
STLCR = LCR_WLS0 | LCR_WLS1;
/* enable and reset TX/RX FIFO(1-byte rx threshold
FIFO) */
STFCR |= FCR_TRFIFOE|FCR_RESETRF|FCR_RESETTF;
__asm{ nop }
STLCR &= ~LCR_DLAB; /* DLAB off */
STIER = IER_UUE | IER_RAVIE; /* enable UART, RX interrupt */
ICMR = 0xFFFFFFFF;
_bl_enable_irq();
}
Below is the hexadecimal register values I print
when a character is received(STLSR & LSR_DR).
STIER=41, STLSR=21, STIIR=c4, ICIP=0, ICMR=ffffff80, ICPR=0
[
STIER=41 => 0x40:uart enabled,
0x01:Receiver Data Available Interrupt Enable.
STLSR=21 => 0x20:Transmit FIFO has half or less than half data,
0x01:Data is available in RBR or the FIFO
STIIR=c4 => 0xc0:FIFO mode is selected
0x04:Received Data Available
ICIP=0 => IRQ Pending Register
ICMR=FFFFFF80
ICPR=0 => no interrupt pending (why ?????????)
]
Below is the part I print above register values.
(void)itoa(rcv_char, buffer, 16);
serial_puts("\r\nc started, cpsr=");
serial_puts(buffer);
serial_puts(", STIER=");
rcv_char = STIER;
(void)itoa(rcv_char, buffer, 16);
serial_puts(buffer);
serial_puts(", ICMR=");
rcv_char = ICMR;
(void)itoa(rcv_char, buffer, 16);
serial_puts(buffer);
serial_puts("\r\n\n");
while(1) {
if(STLSR & LSR_DR) {
serial_puts("STIER=");
rcv_char = STIER;
(void)itoa(rcv_char, buffer, 16);
serial_puts(buffer);
serial_puts(", STLSR=");
rcv_char = STLSR;
(void)itoa(rcv_char, buffer, 16);
serial_puts(buffer);
serial_puts(", STIIR=");
rcv_char = STIIR;
(void)itoa(rcv_char, buffer, 16);
serial_puts(buffer);
serial_puts(", ICIP=");
rcv_char = ICIP;
(void)itoa(rcv_char, buffer, 16);
serial_puts(buffer);
serial_puts(", ICMR=");
rcv_char = ICMR;
(void)itoa(rcv_char, buffer, 16);
serial_puts(buffer);
serial_puts(", ICPR=");
rcv_char = ICPR;
(void)itoa(rcv_char, buffer, 16);
serial_puts(buffer);
//serial_puts(", char=");
//rcv_char = serial_tstc();
//serial_putc((char)rcv_char);
serial_puts("\r\n");
rcv_char = STRBR;
}
}
The global interrupt in CPSR is enabled.
And when I tested using OS timer, the coresponding interrupt was
generated correctly.
Any help will be greatly appreciated.
Thanks.
Terry.