KL82 LPURT Interrupt Stuck

cancel
Showing results for 
Show  only  | Search instead for 
Did you mean: 

KL82 LPURT Interrupt Stuck

2,296 Views
mldevw
Contributor I

Hello,

I have a KL82 which I attached a modem to it. It communicates via UART.
If the bus is busy (message every second) everything works fine. But if there is rarely any activity (about once a minute) the interrupt for UART RX does not fire when the modem sends data.

This is resolved by reinitializing the UART.

Do you know why this occurs or how I can debug more deeply? Thanks a lot in advance.

Here is my ISR code for reference

void MODEM_LPUART_IRQHandler(void)
{
#ifdef TRACE_SYSVIEW_LPUART_CALLBACK
SEGGER_SYSVIEW_RecordEnterISR();
#endif
interfaceModem_hasWoken = pdFALSE;

/** if new data is in buffer */
if ((kLPUART_RxDataRegFullFlag)&LPUART_GetStatusFlags(MODEM_LPUART))
{
TPM_StopTimer(TPM0); /** stop timer for timeout detection */
interfaceModem_data = LPUART_ReadByte(MODEM_LPUART); /** read data from buffer */
if (uxQueueMessagesWaitingFromISR(InterfaceModem::rxQueue)<INTERFACE_MODEM_RX_QUEUE_SIZE-3)
{ /** Submit to queue */
xQueueSendFromISR(InterfaceModem::rxQueue,&interfaceModem_data,&interfaceModem_hasWoken);
if (interfaceModem_data=='\n')
{ /** if this char is a line ending, activate the timer. Every Message of SIM808 ends with */
TPM_SetTimerPeriod(TPM0,TIMER_MESSAGETIMEOUT_RELOAD_VALUE);
TPM_StartTimer(TPM0,kTPM_SystemClock);
TPM0->CNT=0;
}
}
else
{ /** If data could not be submitted, set overflow occured, clear queues and stop timeout timer */
InterfaceModem::rxOverflowOccured=1;
TPM_StopTimer(TPM0);
xQueueReceiveFromISR(InterfaceModem::rxMessageTimeoutSignalQueue,&interfaceModem_data,&interfaceModem_hasWoken);
while (xQueueReceiveFromISR(InterfaceModem::rxQueue,&interfaceModem_data,&interfaceModem_hasWoken)==pdTRUE);
InterfaceModem::rxOverflowOccured=1;
}
}
/* Add for ARM errata 838869, affects Cortex-M4, Cortex-M4F Store immediate overlapping
exception return operation might vector to incorrect interrupt */
#if defined __CORTEX_M && (__CORTEX_M == 4U)
__DSB();
#endif

#ifdef TRACE_SYSVIEW_LPUART_CALLBACK
SEGGER_SYSVIEW_RecordExitISR();
#endif
portYIELD_FROM_ISR(interfaceModem_hasWoken);
}

0 Kudos
Reply
10 Replies

2,278 Views
jingpan
NXP TechSupport
NXP TechSupport

Hi mldevw,

Could it because the lpuart is deactived by your OS, for example the clock source is changed? If lpuart is configured properly, waiting time does not affect lpuart's work.

 

Regards,

Jing

0 Kudos
Reply

2,271 Views
mldevw
Contributor I

Hello,

I am only doing one clock switch right at the start of the application. When the modem is running, no clock switch is taking place.

I am using FreeRTOS, I don't know if this could be the issue.

Strangely this occurs only when communication is rare. Once I keep the channel busy, I do not experience the problem anymore.

Edit: I am using the LPUART_Driver from the MCUXpresso SDK, not the FreeRTOS Driver.
I make sure that only one process is accessing the UART at a time.

0 Kudos
Reply

2,266 Views
jingpan
NXP TechSupport
NXP TechSupport

Hi,

You can compare LPUART register settings and its clock source setting to see what is changed when it not work.

 

Regards,

Jing

0 Kudos
Reply

2,248 Views
mldevw
Contributor I

Hello,

so I could reproduce the error and have the following finding:

EDIT2:

I made a mistake reading out, actually the STAT-Register changed
It changed from 00 80 00 00 to 00 D8 00 00 (error)
This means:
OR from 0 to 1
IDLE from 0 to 1
TC from 0 to 1

In the other error case (00 D0 00 00):
OR = 0
IDLE = 1
TC = 1

I have seen there is an overrun and I will concentrate on getting rid of that for now.
I'll get back to you if that solves the problem

LPUART->MODIR has changed from 00 D8 00 00 to 00 80 00 00
(Value was printed out with printf("%" PRIu32,LPUART->MODIR); and then converted to hex)

EDIT: Now I have also seen a case where MODIR is 00 D0 00 00 both before the error and when it occured

For my Init I use the defaults, but change the baudrate and enable tx and rx.

LPUART_GetDefaultConfig(&config);
config.baudRate_Bps = currentBaudrate;
config.enableTx = true;
config.enableRx = true;

Reading the datasheet (see below) it's not clear to me what this means.
Also I did not find any use of MODIR in the lpuart driver from the SDK but for initialisation.

Can you please help me on finding out
a) what the flags in the MODIR mean, which are changed
b) why MODIR changes

Thanks a lot in advance.

mldevw_0-1622142872970.png

Sub-Family Reference Manual Rev. 3, 08/2016, p. 1493

0 Kudos
Reply

2,230 Views
mldevw
Contributor I

Hello,

the overrun issue occurs although I am sure my ISR reads the byte in time.
The ringbuffer is not an option for me, as I need to use the RxBufFull Interrupt for timing and detecting the end of frame.

I have also tried to reset the flags register (STAT) before every sending, but this didn't help either.

any ideas?

0 Kudos
Reply

2,207 Views
jingpan
NXP TechSupport
NXP TechSupport

Hi,

RDRF is set when the number of datawords in the receive buffer is greater than the number indicated by LPUART_WATER[RXWATER]. You can set a smaller RXWATER value to have enough time to read out data before overflow. You can enable ORIE bit to enable overflow interrupt to observe when overflow happen.

 

Regards,

 

0 Kudos
Reply

2,196 Views
mldevw
Contributor I

Hi,

thanks for your feedback, I'll be watching the ORIE now.

I didn't quite understand why you pointed out RDRF, as this is never set in my case. Could you please elaborate?

Thanks in advance.

Kind regards.

0 Kudos
Reply

2,181 Views
mldevw
Contributor I

Hello,

with an oscilloscope I figured the hardware is not sending the message in the first place. It turns out this is not a fault at the receiving end (as I suspected) but actually the message is not sent out.

Workaround currently in use: Reinitialize UART (only INIT not DEINIT) before sending any message. This is working fine.

0 Kudos
Reply

2,149 Views
mldevw
Contributor I

Hello,

it turned out to provoke the same kind of error.

I am currently not sure what to do anymore, as I am taking care to fetch the data in a manner no OR occurs.

0 Kudos
Reply

2,260 Views
mldevw
Contributor I

Hello, thanks for your reply.

I have already checked the interrupts, but the config is the same before the error and when the error occurs. It can take some time to reproduce the error, but I will feedback on the setting of the UART registers once it does.

0 Kudos
Reply