This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

No UART TX interrupts and undefined interrupts on C6424

Other Parts Discussed in Thread: TMS320C6424

Hi, All!

 

I'm implementing the UART driver for TMS320C6424 DSP using IOM + class-driver model.

 

Driver code was developed using DDK recommendations.

IOM model looks to be working (I use SIO/DIO class-driver for now) - at least all the IOM_Fxns calls are invoked when necessary.

Nevertheless I've got an issue which I cannot resolve using TI's documentation and samples.

Due to documentation if UART's Tx interrupts are enabled, an interrupt should be generated once Tx FIFO or THR is empty (depending on mode used), and the corresponding interrupt ID bit in IIR should be unset only if anything is written to THR.

UART's interrupts are multiplexed to the single hardware interrupt, and the actual interrupt reason should be read from IIR register.

 

The issue is I have no interrupts, though Tx interrupts are enabled and Tx FIFO is empty.

More than that, sometimes I get interrupt with "interrupt source = None" due to IIR.

 

Below are the UART registers contents which I've got in my UART interrupt service routine:

 

regs      0x01C20000   CSL_UartRegsOvly

RBR    0x00000000    unsigned int

IER      0x00000002    unsigned int

IIR       0x000000C1   unsigned int

LCR    0x00000003    unsigned int

MCR   0x00000000    unsigned int

LSR     0x00000060    unsigned int

MSR    0x000000B0   unsigned int

SCR    0x00000000    unsigned int

DLL     0x0000002C   unsigned int

DLH    0x00000000    unsigned int

PID1    0x00000103    unsigned int

PID2    0x00000004    unsigned int

PWREMU_MGMT    0x00006003    unsigned int

 

Here:

bit0 in IIR = 1, which means no pending interrupts (0xC0 bits - FIFO enabled).

bit5 and bit6 in LSR = 1, which means that both THR/FIFO and TSR are empty.

bit1 in IER = 1, which means that TX interrupts are enabled, and interrupt should be generated on empty TX.

 

My driver enables Tx interrupts (in IER) only when Tx data are ready.

Once data are available, I enable Tx interrupts, and fill THR.

I've tried filling THR with both a single character and a multiple (16 characters - FIFO size).

The result was the same in all cases: there're no Tx interrupts, though LSR shows that Tx is empty.

 

May anyone kindly advice what's the reason for such a behaviour?

 

// below is the interrupt service routine source-code.

// uart_handle_rx_/tx_/err_ routines aren't executed for now because of missing pending and reason bit :(

===============================================

static void

uart_isr_(Ptr * devp)

{

  t_uart_iom_obj * uart = (t_uart_iom_obj *)devp;

  uint32 iir_reg = uart->regs->IIR;

  uint32 int_id = iir_reg >> CSL_UART_IIR_INTID_SHIFT;

 

  isr_cnt++;

 

  // process all incoming requests

  // IPEND bit is 0 while there're interrupts pending

  while (CSL_UART_IIR_IPEND_PEND == (iir_reg & CSL_UART_IIR_IPEND_MASK))

  {

    // check actual interrupt reason

 

    if (int_id & CSL_UART_IIR_INTID_RLS)  // receiver line error

      uart_isr_handle_err_ (uart, int_id);

   

    if (int_id & CSL_UART_IIR_INTID_THRE) // Tx Holding Register or Tx FIFO empty

      uart_isr_handle_tx_ (uart);

   

    // Rx data ready (either FIFO threshold achieved or RBR is filled)

    // or receiver time-out

    if (int_id & (CSL_UART_IIR_INTID_RDA | CSL_UART_IIR_INTID_CTI) )

      uart_isr_handle_rx_ (uart);

 

    // read register

    iir_reg = uart->regs->IIR;

    int_id = iir_reg >> CSL_UART_IIR_INTID_SHIFT;

  }

}

  • Hi,

    Have you tried a simple CCS testcase (no bios) that does interrupt based UART tx? It sounds to me you cannot even receive a tx interrupt. 

  • Hello Paul,

    I have simple driver (not using any dsp bios driver model) working at the same system.
    I've just found at some of the UART-related threads of this forum that IIR register may be cleared by reading it.
    This wasn't mentioned in the following documentation. 

    I've used register reading in my code, and it can be a reason for my issue.
    In addition I debug the code using emulator which in its turn reads registers too. 

    I'm going to check if using single IIR access instead of multiple helps.

  • I just want to tell, that reading IIR resets pending interrupt identification bits.
    Once I've replaced IIR register reading with temporary variable storing IIR value, mini-driver works.

    Unfortunately, it isn't mentioned in TI's UART description (at least for TMS320C642x) that reading IIR resets its interrupt status bits.

    P.S. Now I have another problem which is related to interaction of a class-driver (SIO/DIO) and my mini-driver.
    SIO_reclaim() related to the input stream receives ETIMEOUT for the first received packet, though data in the packet are correct and the packet's bufsize field isn't changed by IOM.
    Other packets receive correct results (equal to filled data size).

    I think it's better to post this question in a separate thread because the problem is different... 

  • Vladislav,

    Thanks for the update. You are correct. I just checked with the spec owner, and IIR is cleared upon reading. I will put a request to update these docs soon.

    If it is BIOS (even IO mini) related, you will get a faster response in the BIOS forum.

  • Could somebody please fix the documentation (it's been five years and people, like me, still needlessly run into the same problem)? This seems to affect all CPUs with a PC16550D UART (in my case, a DM6435). Interestingly, the ancient PC16550D documentation (from 1995) still says that a THRE interrupt is cleared by "Reading the IIR Register (if source of interrupt) or Writing into the Transmitter Holding Register". The C6424 and DM6435 documentation only says it's cleared when "A character is written to the transmitter holding register (THR)".

    What's worse: at least the PSP drivers 1.11.0 for DM6437 follow the newer documentation and therefore miss THRE events when handling RXFIFOE events, effectively freezing the transmitter. I wouldn't be surprised at all if that's also the cause of the problems described in https://e2e.ti.com/support/dsp/davinci_digital_media_processors/f/99/t/5795


    Regards

    Markus