URL
https://opencores.org/ocsvn/or1k/or1k/trunk
Subversion Repositories or1k
Compare Revisions
- This comparison shows the changes necessary to convert path
/
- from Rev 1504 to Rev 1505
- ↔ Reverse comparison
Rev 1504 → Rev 1505
/trunk/or1ksim/peripheral/16450.c
558,13 → 558,12
SCHED_ADD(uart_check_char, uart, UART_FGETC_SLOWDOWN * UART_CLOCK_DIVIDER); |
} |
|
/*----------------------------------------------------[ UART I/O handling ]---*/ |
/* Set a specific UART register with value. */ |
void uart_write_byte(oraddr_t addr, uint8_t value, void *dat) |
{ |
struct dev_16450 *uart = dat; |
|
TRACE("uart_write_byte(%"PRIxADDR",%02"PRIx8")\n", addr, value); |
|
if (uart->regs.lcr & UART_LCR_DLAB) { |
switch (addr) { |
case UART_DLL: |
574,6 → 573,7
uart->regs.dll, uart->regs.dlh, uart->regs.lcr); |
return; |
case UART_DLH: |
TRACE("Setting dlh with %"PRIx8"\n", value); |
uart->regs.dlh = value; |
return; |
} |
581,6 → 581,7
|
switch (addr) { |
case UART_TXBUF: |
TRACE("Adding %"PRIx8" to TX FIFO\n", value); |
uart->regs.lsr &= ~UART_LSR_TXBUFE; |
if (uart->istat.txbuf_full < uart->fifo_len) { |
uart->regs.txbuf[uart->istat.txbuf_head] = value; |
593,6 → 594,7
uart_clear_int(uart, UART_IIR_THRI); |
break; |
case UART_FCR: |
TRACE("Setting FCR reg with %"PRIx8"\n", value); |
uart->regs.fcr = value & UART_VALID_FCR; |
if ((uart->fifo_len == 1 && (value & UART_FCR_FIE)) |
|| (uart->fifo_len != 1 && !(value & UART_FCR_FIE))) |
620,9 → 622,12
break; |
case UART_IER: |
uart->regs.ier = value & UART_VALID_IER; |
TRACE("Enabling 0x%02x interrupts with 0x%x interrupts pending\n", |
value, uart->istat.ints); |
SCHED_ADD(uart_next_int, uart, 0); |
break; |
case UART_LCR: |
TRACE("Setting LCR reg with %"PRIx8"\n", value); |
if((uart->regs.lcr & UART_LCR_SBC) != (value & UART_LCR_SBC)) { |
if((value & UART_LCR_SBC) && !(uart->regs.lsr & UART_LSR_TXSERE)) { |
/* Schedule a job to send the break char */ |
640,14 → 645,16
uart->char_clks = char_clks(uart->regs.dll, uart->regs.dlh, uart->regs.lcr); |
break; |
case UART_MCR: |
TRACE("Setting MCR reg with %"PRIx8"\n", value); |
uart->regs.mcr = value & UART_VALID_MCR; |
uart_loopback(uart); |
break; |
case UART_SCR: |
TRACE("Setting SCR reg with %"PRIx8"\n", value); |
uart->regs.scr = value; |
break; |
default: |
TRACE("write out of range (addr %x)\n", addr); |
TRACE("write out of range (addr %"PRIxADDR")\n", addr); |
} |
} |
|
657,17 → 664,15
struct dev_16450 *uart = dat; |
uint8_t value = 0; |
|
TRACE("uart_read_byte(%"PRIxADDR")", addr); |
|
if (uart->regs.lcr & UART_LCR_DLAB) { |
switch (addr) { |
case UART_DLL: |
value = uart->regs.dll; |
TRACE("= %"PRIx8"\n", value); |
TRACE("reading DLL = %"PRIx8"\n", value); |
return value; |
case UART_DLH: |
value = uart->regs.dlh; |
TRACE("= %"PRIx8"\n", value); |
TRACE("reading DLH = %"PRIx8"\n", value); |
return value; |
} |
} |
679,7 → 684,8
TRACE("(%i/%i, %i, %i:", uart->istat.rxbuf_full, uart->fifo_len, |
uart->istat.rxbuf_head, uart->istat.rxbuf_tail); |
for (i = 0; i < uart->istat.rxbuf_full; i++) |
TRACE("%02x ", uart->regs.rxbuf[(uart->istat.rxbuf_tail + i) % uart->fifo_len]); |
TRACE("%02x ", |
uart->regs.rxbuf[(uart->istat.rxbuf_tail + i) % uart->fifo_len]); |
TRACE(")"); |
} |
if (uart->istat.rxbuf_full) { |
709,6 → 715,7
break; |
case UART_IER: |
value = uart->regs.ier & UART_VALID_IER; |
TRACE("reading IER = %"PRIx8"\n", value); |
break; |
case UART_IIR: |
value = (uart->regs.iir & UART_VALID_IIR) | 0xc0; |
715,12 → 722,15
/* Only clear the thri interrupt if it is the one we are repporting */ |
if(uart->regs.iir == UART_IIR_THRI) |
uart_clear_int(uart, UART_IIR_THRI); |
TRACE("reading IIR = %"PRIx8"\n", value); |
break; |
case UART_LCR: |
value = uart->regs.lcr & UART_VALID_LCR; |
TRACE("reading LCR = %"PRIx8"\n", value); |
break; |
case UART_MCR: |
value = 0; |
TRACE("reading MCR = %"PRIx8"\n", value); |
break; |
case UART_LSR: |
value = uart->regs.lsr & UART_VALID_LSR; |
729,6 → 739,7
| UART_LSR_FRAME | UART_LSR_RXERR); |
/* Clear potentially pending RLSI interrupt */ |
uart_clear_int(uart, UART_IIR_RLSI); |
TRACE("reading LSR = %"PRIx8"\n", value); |
break; |
case UART_MSR: |
value = uart->regs.msr & UART_VALID_MSR; |
735,14 → 746,15
uart->regs.msr = 0; |
uart_clear_int(uart, UART_IIR_MSI); |
uart_loopback(uart); |
TRACE("reading MSR = %"PRIx8"\n", value); |
break; |
case UART_SCR: |
value = uart->regs.scr; |
TRACE("reading SCR = %"PRIx8"\n", value); |
break; |
default: |
TRACE("read out of range (addr %"PRIxADDR")\n", addr); |
} |
TRACE(" = %"PRIx8"\n", value); |
return value; |
} |
|
846,9 → 858,10
uart_vapi_cmd(uart); |
} |
|
/*--------------------------------------------------------[ Sim callbacks ]---*/ |
/* Reset. It initializes all registers of all UART devices to zero values, |
(re)opens all RX/TX file streams and places devices in memory address |
space. */ |
* (re)opens all RX/TX file streams and places devices in memory address |
* space. */ |
void uart_reset(void *dat) |
{ |
struct dev_16450 *uart = dat; |