1/*
2 * Copyright (c) 2015-2016, Freescale Semiconductor, Inc.
3 * Copyright 2016-2021 NXP
4 * All rights reserved.
5 *
6 * SPDX-License-Identifier: BSD-3-Clause
7 */
8
9#include "fsl_lpuart.h"
10
11/*******************************************************************************
12 * Definitions
13 ******************************************************************************/
14
15/* Component ID definition, used by tools. */
16#ifndef FSL_COMPONENT_ID
17#define FSL_COMPONENT_ID "platform.drivers.lpuart"
18#endif
19
20/* LPUART transfer state. */
21enum
22{
23 kLPUART_TxIdle, /*!< TX idle. */
24 kLPUART_TxBusy, /*!< TX busy. */
25 kLPUART_RxIdle, /*!< RX idle. */
26 kLPUART_RxBusy /*!< RX busy. */
27};
28
29/*******************************************************************************
30 * Prototypes
31 ******************************************************************************/
32/*!
33 * @brief Check whether the RX ring buffer is full.
34 *
35 * @userData handle LPUART handle pointer.
36 * @retval true RX ring buffer is full.
37 * @retval false RX ring buffer is not full.
38 */
39static bool LPUART_TransferIsRxRingBufferFull(LPUART_Type *base, lpuart_handle_t *handle);
40
41/*!
42 * @brief Write to TX register using non-blocking method.
43 *
44 * This function writes data to the TX register directly, upper layer must make
45 * sure the TX register is empty or TX FIFO has empty room before calling this function.
46 *
47 * @note This function does not check whether all the data has been sent out to bus,
48 * so before disable TX, check kLPUART_TransmissionCompleteFlag to ensure the TX is
49 * finished.
50 *
51 * @param base LPUART peripheral base address.
52 * @param data Start address of the data to write.
53 * @param length Size of the buffer to be sent.
54 */
55static void LPUART_WriteNonBlocking(LPUART_Type *base, const uint8_t *data, size_t length);
56
57/*!
58 * @brief Read RX register using non-blocking method.
59 *
60 * This function reads data from the TX register directly, upper layer must make
61 * sure the RX register is full or TX FIFO has data before calling this function.
62 *
63 * @param base LPUART peripheral base address.
64 * @param data Start address of the buffer to store the received data.
65 * @param length Size of the buffer.
66 */
67static void LPUART_ReadNonBlocking(LPUART_Type *base, uint8_t *data, size_t length);
68
69/*******************************************************************************
70 * Variables
71 ******************************************************************************/
72/* Array of LPUART peripheral base address. */
73static LPUART_Type *const s_lpuartBases[] = LPUART_BASE_PTRS;
74/* Array of LPUART handle. */
75void *s_lpuartHandle[ARRAY_SIZE(s_lpuartBases)];
76/* Array of LPUART IRQ number. */
77#if defined(FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ) && FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ
78static const IRQn_Type s_lpuartRxIRQ[] = LPUART_RX_IRQS;
79const IRQn_Type s_lpuartTxIRQ[] = LPUART_TX_IRQS;
80#else
81const IRQn_Type s_lpuartIRQ[] = LPUART_RX_TX_IRQS;
82#endif
83#if !(defined(FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL) && FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL)
84/* Array of LPUART clock name. */
85static const clock_ip_name_t s_lpuartClock[] = LPUART_CLOCKS;
86
87#if defined(LPUART_PERIPH_CLOCKS)
88/* Array of LPUART functional clock name. */
89static const clock_ip_name_t s_lpuartPeriphClocks[] = LPUART_PERIPH_CLOCKS;
90#endif
91
92#endif /* FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL */
93
94/* LPUART ISR for transactional APIs. */
95#if defined(__ARMCC_VERSION) && (__ARMCC_VERSION >= 6010050)
96lpuart_isr_t s_lpuartIsr = (lpuart_isr_t)DefaultISR;
97#else
98lpuart_isr_t s_lpuartIsr;
99#endif
100
101/*******************************************************************************
102 * Code
103 ******************************************************************************/
104/*!
105 * brief Get the LPUART instance from peripheral base address.
106 *
107 * param base LPUART peripheral base address.
108 * return LPUART instance.
109 */
110uint32_t LPUART_GetInstance(LPUART_Type *base)
111{
112 uint32_t instance;
113
114 /* Find the instance index from base address mappings. */
115 for (instance = 0U; instance < ARRAY_SIZE(s_lpuartBases); instance++)
116 {
117 if (s_lpuartBases[instance] == base)
118 {
119 break;
120 }
121 }
122
123 assert(instance < ARRAY_SIZE(s_lpuartBases));
124
125 return instance;
126}
127
128/*!
129 * brief Get the length of received data in RX ring buffer.
130 *
131 * userData handle LPUART handle pointer.
132 * return Length of received data in RX ring buffer.
133 */
134size_t LPUART_TransferGetRxRingBufferLength(LPUART_Type *base, lpuart_handle_t *handle)
135{
136 assert(NULL != handle);
137
138 size_t size;
139 size_t tmpRxRingBufferSize = handle->rxRingBufferSize;
140 uint16_t tmpRxRingBufferTail = handle->rxRingBufferTail;
141 uint16_t tmpRxRingBufferHead = handle->rxRingBufferHead;
142
143 if (tmpRxRingBufferTail > tmpRxRingBufferHead)
144 {
145 size = ((size_t)tmpRxRingBufferHead + tmpRxRingBufferSize - (size_t)tmpRxRingBufferTail);
146 }
147 else
148 {
149 size = ((size_t)tmpRxRingBufferHead - (size_t)tmpRxRingBufferTail);
150 }
151
152 return size;
153}
154
155static bool LPUART_TransferIsRxRingBufferFull(LPUART_Type *base, lpuart_handle_t *handle)
156{
157 assert(NULL != handle);
158
159 bool full;
160
161 if (LPUART_TransferGetRxRingBufferLength(base, handle) == (handle->rxRingBufferSize - 1U))
162 {
163 full = true;
164 }
165 else
166 {
167 full = false;
168 }
169 return full;
170}
171
172static void LPUART_WriteNonBlocking(LPUART_Type *base, const uint8_t *data, size_t length)
173{
174 assert(NULL != data);
175
176 size_t i;
177
178 /* The Non Blocking write data API assume user have ensured there is enough space in
179 peripheral to write. */
180 for (i = 0; i < length; i++)
181 {
182 base->DATA = data[i];
183 }
184}
185
186static void LPUART_ReadNonBlocking(LPUART_Type *base, uint8_t *data, size_t length)
187{
188 assert(NULL != data);
189
190 size_t i;
191#if defined(FSL_FEATURE_LPUART_HAS_7BIT_DATA_SUPPORT) && FSL_FEATURE_LPUART_HAS_7BIT_DATA_SUPPORT
192 uint32_t ctrl = base->CTRL;
193 bool isSevenDataBits = (((ctrl & LPUART_CTRL_M7_MASK) != 0U) ||
194 (((ctrl & LPUART_CTRL_M_MASK) == 0U) && ((ctrl & LPUART_CTRL_PE_MASK) != 0U)));
195#endif
196
197 /* The Non Blocking read data API assume user have ensured there is enough space in
198 peripheral to write. */
199 for (i = 0; i < length; i++)
200 {
201#if defined(FSL_FEATURE_LPUART_HAS_7BIT_DATA_SUPPORT) && FSL_FEATURE_LPUART_HAS_7BIT_DATA_SUPPORT
202 if (isSevenDataBits)
203 {
204 data[i] = (uint8_t)(base->DATA & 0x7FU);
205 }
206 else
207 {
208 data[i] = (uint8_t)base->DATA;
209 }
210#else
211 data[i] = (uint8_t)(base->DATA);
212#endif
213 }
214}
215
216/*!
217 * brief Initializes an LPUART instance with the user configuration structure and the peripheral clock.
218 *
219 * This function configures the LPUART module with user-defined settings. Call the LPUART_GetDefaultConfig() function
220 * to configure the configuration structure and get the default configuration.
221 * The example below shows how to use this API to configure the LPUART.
222 * code
223 * lpuart_config_t lpuartConfig;
224 * lpuartConfig.baudRate_Bps = 115200U;
225 * lpuartConfig.parityMode = kLPUART_ParityDisabled;
226 * lpuartConfig.dataBitsCount = kLPUART_EightDataBits;
227 * lpuartConfig.isMsb = false;
228 * lpuartConfig.stopBitCount = kLPUART_OneStopBit;
229 * lpuartConfig.txFifoWatermark = 0;
230 * lpuartConfig.rxFifoWatermark = 1;
231 * LPUART_Init(LPUART1, &lpuartConfig, 20000000U);
232 * endcode
233 *
234 * param base LPUART peripheral base address.
235 * param config Pointer to a user-defined configuration structure.
236 * param srcClock_Hz LPUART clock source frequency in HZ.
237 * retval kStatus_LPUART_BaudrateNotSupport Baudrate is not support in current clock source.
238 * retval kStatus_Success LPUART initialize succeed
239 */
240status_t LPUART_Init(LPUART_Type *base, const lpuart_config_t *config, uint32_t srcClock_Hz)
241{
242 assert(NULL != config);
243 assert(0U < config->baudRate_Bps);
244#if defined(FSL_FEATURE_LPUART_HAS_FIFO) && FSL_FEATURE_LPUART_HAS_FIFO
245 assert((uint8_t)FSL_FEATURE_LPUART_FIFO_SIZEn(base) > config->txFifoWatermark);
246 assert((uint8_t)FSL_FEATURE_LPUART_FIFO_SIZEn(base) > config->rxFifoWatermark);
247#endif
248
249 status_t status = kStatus_Success;
250 uint32_t temp;
251 uint16_t sbr, sbrTemp;
252 uint8_t osr, osrTemp;
253 uint32_t tempDiff, calculatedBaud, baudDiff;
254
255 /* This LPUART instantiation uses a slightly different baud rate calculation
256 * The idea is to use the best OSR (over-sampling rate) possible
257 * Note, OSR is typically hard-set to 16 in other LPUART instantiations
258 * loop to find the best OSR value possible, one that generates minimum baudDiff
259 * iterate through the rest of the supported values of OSR */
260
261 baudDiff = config->baudRate_Bps;
262 osr = 0U;
263 sbr = 0U;
264 for (osrTemp = 4U; osrTemp <= 32U; osrTemp++)
265 {
266 /* calculate the temporary sbr value */
267 sbrTemp = (uint16_t)((srcClock_Hz * 10U / (config->baudRate_Bps * (uint32_t)osrTemp) + 5U) / 10U);
268 /*set sbrTemp to 1 if the sourceClockInHz can not satisfy the desired baud rate*/
269 if (sbrTemp == 0U)
270 {
271 sbrTemp = 1U;
272 }
273 /* Calculate the baud rate based on the temporary OSR and SBR values */
274 calculatedBaud = (srcClock_Hz / ((uint32_t)osrTemp * (uint32_t)sbrTemp));
275 tempDiff = calculatedBaud > config->baudRate_Bps ? (calculatedBaud - config->baudRate_Bps) :
276 (config->baudRate_Bps - calculatedBaud);
277
278 if (tempDiff <= baudDiff)
279 {
280 baudDiff = tempDiff;
281 osr = osrTemp; /* update and store the best OSR value calculated */
282 sbr = sbrTemp; /* update store the best SBR value calculated */
283 }
284 }
285
286 /* Check to see if actual baud rate is within 3% of desired baud rate
287 * based on the best calculate OSR value */
288 if (baudDiff > ((config->baudRate_Bps / 100U) * 3U))
289 {
290 /* Unacceptable baud rate difference of more than 3%*/
291 status = kStatus_LPUART_BaudrateNotSupport;
292 }
293 else
294 {
295#if !(defined(FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL) && FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL)
296
297 uint32_t instance = LPUART_GetInstance(base);
298
299 /* Enable lpuart clock */
300 (void)CLOCK_EnableClock(s_lpuartClock[instance]);
301#if defined(LPUART_PERIPH_CLOCKS)
302 (void)CLOCK_EnableClock(s_lpuartPeriphClocks[instance]);
303#endif
304
305#endif /* FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL */
306
307#if defined(FSL_FEATURE_LPUART_HAS_GLOBAL) && FSL_FEATURE_LPUART_HAS_GLOBAL
308 /*Reset all internal logic and registers, except the Global Register */
309 LPUART_SoftwareReset(base);
310#else
311 /* Disable LPUART TX RX before setting. */
312 base->CTRL &= ~(LPUART_CTRL_TE_MASK | LPUART_CTRL_RE_MASK);
313#endif
314
315 temp = base->BAUD;
316
317 /* Acceptable baud rate, check if OSR is between 4x and 7x oversampling.
318 * If so, then "BOTHEDGE" sampling must be turned on */
319 if ((osr > 3U) && (osr < 8U))
320 {
321 temp |= LPUART_BAUD_BOTHEDGE_MASK;
322 }
323
324 /* program the osr value (bit value is one less than actual value) */
325 temp &= ~LPUART_BAUD_OSR_MASK;
326 temp |= LPUART_BAUD_OSR((uint32_t)osr - 1UL);
327
328 /* write the sbr value to the BAUD registers */
329 temp &= ~LPUART_BAUD_SBR_MASK;
330 base->BAUD = temp | LPUART_BAUD_SBR(sbr);
331
332 /* Set bit count and parity mode. */
333 base->BAUD &= ~LPUART_BAUD_M10_MASK;
334
335 temp = base->CTRL & ~(LPUART_CTRL_PE_MASK | LPUART_CTRL_PT_MASK | LPUART_CTRL_M_MASK | LPUART_CTRL_ILT_MASK |
336 LPUART_CTRL_IDLECFG_MASK);
337
338 temp |= (uint8_t)config->parityMode | LPUART_CTRL_IDLECFG(config->rxIdleConfig) |
339 LPUART_CTRL_ILT(config->rxIdleType);
340
341#if defined(FSL_FEATURE_LPUART_HAS_7BIT_DATA_SUPPORT) && FSL_FEATURE_LPUART_HAS_7BIT_DATA_SUPPORT
342 if (kLPUART_SevenDataBits == config->dataBitsCount)
343 {
344 if (kLPUART_ParityDisabled != config->parityMode)
345 {
346 temp &= ~LPUART_CTRL_M7_MASK; /* Seven data bits and one parity bit */
347 }
348 else
349 {
350 temp |= LPUART_CTRL_M7_MASK;
351 }
352 }
353 else
354#endif
355 {
356 if (kLPUART_ParityDisabled != config->parityMode)
357 {
358 temp |= LPUART_CTRL_M_MASK; /* Eight data bits and one parity bit */
359 }
360 }
361
362 base->CTRL = temp;
363
364#if defined(FSL_FEATURE_LPUART_HAS_STOP_BIT_CONFIG_SUPPORT) && FSL_FEATURE_LPUART_HAS_STOP_BIT_CONFIG_SUPPORT
365 /* set stop bit per char */
366 temp = base->BAUD & ~LPUART_BAUD_SBNS_MASK;
367 base->BAUD = temp | LPUART_BAUD_SBNS((uint8_t)config->stopBitCount);
368#endif
369
370#if defined(FSL_FEATURE_LPUART_HAS_FIFO) && FSL_FEATURE_LPUART_HAS_FIFO
371 /* Set tx/rx WATER watermark
372 Note:
373 Take care of the RX FIFO, RX interrupt request only assert when received bytes
374 equal or more than RX water mark, there is potential issue if RX water
375 mark larger than 1.
376 For example, if RX FIFO water mark is 2, upper layer needs 5 bytes and
377 5 bytes are received. the last byte will be saved in FIFO but not trigger
378 RX interrupt because the water mark is 2.
379 */
380 base->WATER = (((uint32_t)(config->rxFifoWatermark) << 16U) | config->txFifoWatermark);
381
382 /* Enable tx/rx FIFO */
383 base->FIFO |= (LPUART_FIFO_TXFE_MASK | LPUART_FIFO_RXFE_MASK);
384
385 /* Flush FIFO */
386 base->FIFO |= (LPUART_FIFO_TXFLUSH_MASK | LPUART_FIFO_RXFLUSH_MASK);
387#endif
388
389 /* Clear all status flags */
390 temp = (LPUART_STAT_RXEDGIF_MASK | LPUART_STAT_IDLE_MASK | LPUART_STAT_OR_MASK | LPUART_STAT_NF_MASK |
391 LPUART_STAT_FE_MASK | LPUART_STAT_PF_MASK);
392
393#if defined(FSL_FEATURE_LPUART_HAS_LIN_BREAK_DETECT) && FSL_FEATURE_LPUART_HAS_LIN_BREAK_DETECT
394 temp |= LPUART_STAT_LBKDIF_MASK;
395#endif
396
397#if defined(FSL_FEATURE_LPUART_HAS_ADDRESS_MATCHING) && FSL_FEATURE_LPUART_HAS_ADDRESS_MATCHING
398 temp |= (LPUART_STAT_MA1F_MASK | LPUART_STAT_MA2F_MASK);
399#endif
400
401#if defined(FSL_FEATURE_LPUART_HAS_MODEM_SUPPORT) && FSL_FEATURE_LPUART_HAS_MODEM_SUPPORT
402 /* Set the CTS configuration/TX CTS source. */
403 base->MODIR |= LPUART_MODIR_TXCTSC(config->txCtsConfig) | LPUART_MODIR_TXCTSSRC(config->txCtsSource);
404 if (true == config->enableRxRTS)
405 {
406 /* Enable the receiver RTS(request-to-send) function. */
407 base->MODIR |= LPUART_MODIR_RXRTSE_MASK;
408 }
409 if (true == config->enableTxCTS)
410 {
411 /* Enable the CTS(clear-to-send) function. */
412 base->MODIR |= LPUART_MODIR_TXCTSE_MASK;
413 }
414#endif
415
416 /* Set data bits order. */
417 if (true == config->isMsb)
418 {
419 temp |= LPUART_STAT_MSBF_MASK;
420 }
421 else
422 {
423 temp &= ~LPUART_STAT_MSBF_MASK;
424 }
425
426 base->STAT |= temp;
427
428 /* Enable TX/RX base on configure structure. */
429 temp = base->CTRL;
430 if (true == config->enableTx)
431 {
432 temp |= LPUART_CTRL_TE_MASK;
433 }
434
435 if (true == config->enableRx)
436 {
437 temp |= LPUART_CTRL_RE_MASK;
438 }
439
440 base->CTRL = temp;
441 }
442
443 return status;
444}
445/*!
446 * brief Deinitializes a LPUART instance.
447 *
448 * This function waits for transmit to complete, disables TX and RX, and disables the LPUART clock.
449 *
450 * param base LPUART peripheral base address.
451 */
452void LPUART_Deinit(LPUART_Type *base)
453{
454 uint32_t temp;
455
456#if defined(FSL_FEATURE_LPUART_HAS_FIFO) && FSL_FEATURE_LPUART_HAS_FIFO
457 /* Wait tx FIFO send out*/
458 while (0U != ((base->WATER & LPUART_WATER_TXCOUNT_MASK) >> LPUART_WATER_TXWATER_SHIFT))
459 {
460 }
461#endif
462 /* Wait last char shift out */
463 while (0U == (base->STAT & LPUART_STAT_TC_MASK))
464 {
465 }
466
467 /* Clear all status flags */
468 temp = (LPUART_STAT_RXEDGIF_MASK | LPUART_STAT_IDLE_MASK | LPUART_STAT_OR_MASK | LPUART_STAT_NF_MASK |
469 LPUART_STAT_FE_MASK | LPUART_STAT_PF_MASK);
470
471#if defined(FSL_FEATURE_LPUART_HAS_LIN_BREAK_DETECT) && FSL_FEATURE_LPUART_HAS_LIN_BREAK_DETECT
472 temp |= LPUART_STAT_LBKDIF_MASK;
473#endif
474
475#if defined(FSL_FEATURE_LPUART_HAS_ADDRESS_MATCHING) && FSL_FEATURE_LPUART_HAS_ADDRESS_MATCHING
476 temp |= (LPUART_STAT_MA1F_MASK | LPUART_STAT_MA2F_MASK);
477#endif
478
479 base->STAT |= temp;
480
481 /* Disable the module. */
482 base->CTRL = 0U;
483
484#if !(defined(FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL) && FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL)
485 uint32_t instance = LPUART_GetInstance(base);
486
487 /* Disable lpuart clock */
488 (void)CLOCK_DisableClock(s_lpuartClock[instance]);
489
490#if defined(LPUART_PERIPH_CLOCKS)
491 (void)CLOCK_DisableClock(s_lpuartPeriphClocks[instance]);
492#endif
493
494#endif /* FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL */
495}
496
497/*!
498 * brief Gets the default configuration structure.
499 *
500 * This function initializes the LPUART configuration structure to a default value. The default
501 * values are:
502 * lpuartConfig->baudRate_Bps = 115200U;
503 * lpuartConfig->parityMode = kLPUART_ParityDisabled;
504 * lpuartConfig->dataBitsCount = kLPUART_EightDataBits;
505 * lpuartConfig->isMsb = false;
506 * lpuartConfig->stopBitCount = kLPUART_OneStopBit;
507 * lpuartConfig->txFifoWatermark = 0;
508 * lpuartConfig->rxFifoWatermark = 1;
509 * lpuartConfig->rxIdleType = kLPUART_IdleTypeStartBit;
510 * lpuartConfig->rxIdleConfig = kLPUART_IdleCharacter1;
511 * lpuartConfig->enableTx = false;
512 * lpuartConfig->enableRx = false;
513 *
514 * param config Pointer to a configuration structure.
515 */
516void LPUART_GetDefaultConfig(lpuart_config_t *config)
517{
518 assert(NULL != config);
519
520 /* Initializes the configure structure to zero. */
521 (void)memset(config, 0, sizeof(*config));
522
523 config->baudRate_Bps = 115200U;
524 config->parityMode = kLPUART_ParityDisabled;
525 config->dataBitsCount = kLPUART_EightDataBits;
526 config->isMsb = false;
527#if defined(FSL_FEATURE_LPUART_HAS_STOP_BIT_CONFIG_SUPPORT) && FSL_FEATURE_LPUART_HAS_STOP_BIT_CONFIG_SUPPORT
528 config->stopBitCount = kLPUART_OneStopBit;
529#endif
530#if defined(FSL_FEATURE_LPUART_HAS_FIFO) && FSL_FEATURE_LPUART_HAS_FIFO
531 config->txFifoWatermark = 0U;
532 config->rxFifoWatermark = 0U;
533#endif
534#if defined(FSL_FEATURE_LPUART_HAS_MODEM_SUPPORT) && FSL_FEATURE_LPUART_HAS_MODEM_SUPPORT
535 config->enableRxRTS = false;
536 config->enableTxCTS = false;
537 config->txCtsConfig = kLPUART_CtsSampleAtStart;
538 config->txCtsSource = kLPUART_CtsSourcePin;
539#endif
540 config->rxIdleType = kLPUART_IdleTypeStartBit;
541 config->rxIdleConfig = kLPUART_IdleCharacter1;
542 config->enableTx = false;
543 config->enableRx = false;
544}
545
546/*!
547 * brief Sets the LPUART instance baudrate.
548 *
549 * This function configures the LPUART module baudrate. This function is used to update
550 * the LPUART module baudrate after the LPUART module is initialized by the LPUART_Init.
551 * code
552 * LPUART_SetBaudRate(LPUART1, 115200U, 20000000U);
553 * endcode
554 *
555 * param base LPUART peripheral base address.
556 * param baudRate_Bps LPUART baudrate to be set.
557 * param srcClock_Hz LPUART clock source frequency in HZ.
558 * retval kStatus_LPUART_BaudrateNotSupport Baudrate is not supported in the current clock source.
559 * retval kStatus_Success Set baudrate succeeded.
560 */
561status_t LPUART_SetBaudRate(LPUART_Type *base, uint32_t baudRate_Bps, uint32_t srcClock_Hz)
562{
563 assert(0U < baudRate_Bps);
564
565 status_t status = kStatus_Success;
566 uint32_t temp, oldCtrl;
567 uint16_t sbr, sbrTemp;
568 uint8_t osr, osrTemp;
569 uint32_t tempDiff, calculatedBaud, baudDiff;
570
571 /* This LPUART instantiation uses a slightly different baud rate calculation
572 * The idea is to use the best OSR (over-sampling rate) possible
573 * Note, OSR is typically hard-set to 16 in other LPUART instantiations
574 * loop to find the best OSR value possible, one that generates minimum baudDiff
575 * iterate through the rest of the supported values of OSR */
576
577 baudDiff = baudRate_Bps;
578 osr = 0U;
579 sbr = 0U;
580 for (osrTemp = 4U; osrTemp <= 32U; osrTemp++)
581 {
582 /* calculate the temporary sbr value */
583 sbrTemp = (uint16_t)((srcClock_Hz * 10U / (baudRate_Bps * (uint32_t)osrTemp) + 5U) / 10U);
584 /*set sbrTemp to 1 if the sourceClockInHz can not satisfy the desired baud rate*/
585 if (sbrTemp == 0U)
586 {
587 sbrTemp = 1U;
588 }
589 /* Calculate the baud rate based on the temporary OSR and SBR values */
590 calculatedBaud = srcClock_Hz / ((uint32_t)osrTemp * (uint32_t)sbrTemp);
591
592 tempDiff = calculatedBaud > baudRate_Bps ? (calculatedBaud - baudRate_Bps) : (baudRate_Bps - calculatedBaud);
593
594 if (tempDiff <= baudDiff)
595 {
596 baudDiff = tempDiff;
597 osr = osrTemp; /* update and store the best OSR value calculated */
598 sbr = sbrTemp; /* update store the best SBR value calculated */
599 }
600 }
601
602 /* Check to see if actual baud rate is within 3% of desired baud rate
603 * based on the best calculate OSR value */
604 if (baudDiff < (uint32_t)((baudRate_Bps / 100U) * 3U))
605 {
606 /* Store CTRL before disable Tx and Rx */
607 oldCtrl = base->CTRL;
608
609 /* Disable LPUART TX RX before setting. */
610 base->CTRL &= ~(LPUART_CTRL_TE_MASK | LPUART_CTRL_RE_MASK);
611
612 temp = base->BAUD;
613
614 /* Acceptable baud rate, check if OSR is between 4x and 7x oversampling.
615 * If so, then "BOTHEDGE" sampling must be turned on */
616 if ((osr > 3U) && (osr < 8U))
617 {
618 temp |= LPUART_BAUD_BOTHEDGE_MASK;
619 }
620
621 /* program the osr value (bit value is one less than actual value) */
622 temp &= ~LPUART_BAUD_OSR_MASK;
623 temp |= LPUART_BAUD_OSR((uint32_t)osr - 1UL);
624
625 /* write the sbr value to the BAUD registers */
626 temp &= ~LPUART_BAUD_SBR_MASK;
627 base->BAUD = temp | LPUART_BAUD_SBR(sbr);
628
629 /* Restore CTRL. */
630 base->CTRL = oldCtrl;
631 }
632 else
633 {
634 /* Unacceptable baud rate difference of more than 3%*/
635 status = kStatus_LPUART_BaudrateNotSupport;
636 }
637
638 return status;
639}
640
641/*!
642 * brief Enable 9-bit data mode for LPUART.
643 *
644 * This function set the 9-bit mode for LPUART module. The 9th bit is not used for parity thus can be modified by user.
645 *
646 * param base LPUART peripheral base address.
647 * param enable true to enable, flase to disable.
648 */
649void LPUART_Enable9bitMode(LPUART_Type *base, bool enable)
650{
651 assert(base != NULL);
652
653 uint32_t temp = 0U;
654
655 if (enable)
656 {
657 /* Set LPUART_CTRL_M for 9-bit mode, clear LPUART_CTRL_PE to disable parity. */
658 temp = base->CTRL & ~((uint32_t)LPUART_CTRL_PE_MASK | (uint32_t)LPUART_CTRL_M_MASK);
659 temp |= (uint32_t)LPUART_CTRL_M_MASK;
660 base->CTRL = temp;
661 }
662 else
663 {
664 /* Clear LPUART_CTRL_M. */
665 base->CTRL &= ~(uint32_t)LPUART_CTRL_M_MASK;
666 }
667#if defined(FSL_FEATURE_LPUART_HAS_7BIT_DATA_SUPPORT) && FSL_FEATURE_LPUART_HAS_7BIT_DATA_SUPPORT
668 /* Clear LPUART_CTRL_M7 to disable 7-bit mode. */
669 base->CTRL &= ~(uint32_t)LPUART_CTRL_M7_MASK;
670#endif
671#if defined(FSL_FEATURE_LPUART_HAS_10BIT_DATA_SUPPORT) && FSL_FEATURE_LPUART_HAS_10BIT_DATA_SUPPORT
672 /* Clear LPUART_BAUD_M10 to disable 10-bit mode. */
673 base->BAUD &= ~(uint32_t)LPUART_BAUD_M10_MASK;
674#endif
675}
676
677/*!
678 * brief Transmit an address frame in 9-bit data mode.
679 *
680 * param base LPUART peripheral base address.
681 * param address LPUART slave address.
682 */
683void LPUART_SendAddress(LPUART_Type *base, uint8_t address)
684{
685 assert(base != NULL);
686
687 uint32_t temp = base->DATA & 0xFFFFFC00UL;
688 temp |= ((uint32_t)address | (1UL << LPUART_DATA_R8T8_SHIFT));
689 base->DATA = temp;
690}
691
692/*!
693 * brief Enables LPUART interrupts according to a provided mask.
694 *
695 * This function enables the LPUART interrupts according to a provided mask. The mask
696 * is a logical OR of enumeration members. See the ref _lpuart_interrupt_enable.
697 * This examples shows how to enable TX empty interrupt and RX full interrupt:
698 * code
699 * LPUART_EnableInterrupts(LPUART1,kLPUART_TxDataRegEmptyInterruptEnable | kLPUART_RxDataRegFullInterruptEnable);
700 * endcode
701 *
702 * param base LPUART peripheral base address.
703 * param mask The interrupts to enable. Logical OR of ref _uart_interrupt_enable.
704 */
705void LPUART_EnableInterrupts(LPUART_Type *base, uint32_t mask)
706{
707 /* Only consider the real interrupt enable bits. */
708 mask &= (uint32_t)kLPUART_AllInterruptEnable;
709
710 /* Check int enable bits in base->BAUD */
711 uint32_t tempReg = base->BAUD;
712#if defined(FSL_FEATURE_LPUART_HAS_LIN_BREAK_DETECT) && FSL_FEATURE_LPUART_HAS_LIN_BREAK_DETECT
713 tempReg |= ((mask << 8U) & LPUART_BAUD_LBKDIE_MASK);
714 /* Clear bit 7 from mask */
715 mask &= ~(uint32_t)kLPUART_LinBreakInterruptEnable;
716#endif
717 tempReg |= ((mask << 8U) & LPUART_BAUD_RXEDGIE_MASK);
718 /* Clear bit 6 from mask */
719 mask &= ~(uint32_t)kLPUART_RxActiveEdgeInterruptEnable;
720 base->BAUD = tempReg;
721
722#if defined(FSL_FEATURE_LPUART_HAS_FIFO) && FSL_FEATURE_LPUART_HAS_FIFO
723 /* Check int enable bits in base->FIFO */
724 base->FIFO = (base->FIFO & ~(LPUART_FIFO_TXOF_MASK | LPUART_FIFO_RXUF_MASK)) |
725 (mask & (LPUART_FIFO_TXOFE_MASK | LPUART_FIFO_RXUFE_MASK));
726 /* Clear bit 9 and bit 8 from mask */
727 mask &= ~((uint32_t)kLPUART_TxFifoOverflowInterruptEnable | (uint32_t)kLPUART_RxFifoUnderflowInterruptEnable);
728#endif
729
730 /* Check int enable bits in base->CTRL */
731 base->CTRL |= mask;
732}
733
734/*!
735 * brief Disables LPUART interrupts according to a provided mask.
736 *
737 * This function disables the LPUART interrupts according to a provided mask. The mask
738 * is a logical OR of enumeration members. See ref _lpuart_interrupt_enable.
739 * This example shows how to disable the TX empty interrupt and RX full interrupt:
740 * code
741 * LPUART_DisableInterrupts(LPUART1,kLPUART_TxDataRegEmptyInterruptEnable | kLPUART_RxDataRegFullInterruptEnable);
742 * endcode
743 *
744 * param base LPUART peripheral base address.
745 * param mask The interrupts to disable. Logical OR of ref _lpuart_interrupt_enable.
746 */
747void LPUART_DisableInterrupts(LPUART_Type *base, uint32_t mask)
748{
749 /* Only consider the real interrupt enable bits. */
750 mask &= (uint32_t)kLPUART_AllInterruptEnable;
751 /* Check int enable bits in base->BAUD */
752 uint32_t tempReg = base->BAUD;
753#if defined(FSL_FEATURE_LPUART_HAS_LIN_BREAK_DETECT) && FSL_FEATURE_LPUART_HAS_LIN_BREAK_DETECT
754 tempReg &= ~((mask << 8U) & LPUART_BAUD_LBKDIE_MASK);
755 /* Clear bit 7 from mask */
756 mask &= ~(uint32_t)kLPUART_LinBreakInterruptEnable;
757#endif
758 tempReg &= ~((mask << 8U) & LPUART_BAUD_RXEDGIE_MASK);
759 /* Clear bit 6 from mask */
760 mask &= ~(uint32_t)kLPUART_RxActiveEdgeInterruptEnable;
761 base->BAUD = tempReg;
762
763#if defined(FSL_FEATURE_LPUART_HAS_FIFO) && FSL_FEATURE_LPUART_HAS_FIFO
764 /* Check int enable bits in base->FIFO */
765 base->FIFO = (base->FIFO & ~(LPUART_FIFO_TXOF_MASK | LPUART_FIFO_RXUF_MASK)) &
766 ~(mask & (LPUART_FIFO_TXOFE_MASK | LPUART_FIFO_RXUFE_MASK));
767 /* Clear bit 9 and bit 8 from mask */
768 mask &= ~((uint32_t)kLPUART_TxFifoOverflowInterruptEnable | (uint32_t)kLPUART_RxFifoUnderflowInterruptEnable);
769#endif
770
771 /* Check int enable bits in base->CTRL */
772 base->CTRL &= ~mask;
773}
774
775/*!
776 * brief Gets enabled LPUART interrupts.
777 *
778 * This function gets the enabled LPUART interrupts. The enabled interrupts are returned
779 * as the logical OR value of the enumerators ref _lpuart_interrupt_enable. To check
780 * a specific interrupt enable status, compare the return value with enumerators
781 * in ref _lpuart_interrupt_enable.
782 * For example, to check whether the TX empty interrupt is enabled:
783 * code
784 * uint32_t enabledInterrupts = LPUART_GetEnabledInterrupts(LPUART1);
785 *
786 * if (kLPUART_TxDataRegEmptyInterruptEnable & enabledInterrupts)
787 * {
788 * ...
789 * }
790 * endcode
791 *
792 * param base LPUART peripheral base address.
793 * return LPUART interrupt flags which are logical OR of the enumerators in ref _lpuart_interrupt_enable.
794 */
795uint32_t LPUART_GetEnabledInterrupts(LPUART_Type *base)
796{
797 /* Check int enable bits in base->CTRL */
798 uint32_t temp = (uint32_t)(base->CTRL & (uint32_t)kLPUART_AllInterruptEnable);
799
800 /* Check int enable bits in base->BAUD */
801 temp = (temp & ~(uint32_t)kLPUART_RxActiveEdgeInterruptEnable) | ((base->BAUD & LPUART_BAUD_RXEDGIE_MASK) >> 8U);
802#if defined(FSL_FEATURE_LPUART_HAS_LIN_BREAK_DETECT) && FSL_FEATURE_LPUART_HAS_LIN_BREAK_DETECT
803 temp = (temp & ~(uint32_t)kLPUART_LinBreakInterruptEnable) | ((base->BAUD & LPUART_BAUD_LBKDIE_MASK) >> 8U);
804#endif
805
806#if defined(FSL_FEATURE_LPUART_HAS_FIFO) && FSL_FEATURE_LPUART_HAS_FIFO
807 /* Check int enable bits in base->FIFO */
808 temp =
809 (temp & ~((uint32_t)kLPUART_TxFifoOverflowInterruptEnable | (uint32_t)kLPUART_RxFifoUnderflowInterruptEnable)) |
810 (base->FIFO & (LPUART_FIFO_TXOFE_MASK | LPUART_FIFO_RXUFE_MASK));
811#endif
812
813 return temp;
814}
815
816/*!
817 * brief Gets LPUART status flags.
818 *
819 * This function gets all LPUART status flags. The flags are returned as the logical
820 * OR value of the enumerators ref _lpuart_flags. To check for a specific status,
821 * compare the return value with enumerators in the ref _lpuart_flags.
822 * For example, to check whether the TX is empty:
823 * code
824 * if (kLPUART_TxDataRegEmptyFlag & LPUART_GetStatusFlags(LPUART1))
825 * {
826 * ...
827 * }
828 * endcode
829 *
830 * param base LPUART peripheral base address.
831 * return LPUART status flags which are ORed by the enumerators in the _lpuart_flags.
832 */
833uint32_t LPUART_GetStatusFlags(LPUART_Type *base)
834{
835 uint32_t temp;
836 temp = base->STAT;
837#if defined(FSL_FEATURE_LPUART_HAS_FIFO) && FSL_FEATURE_LPUART_HAS_FIFO
838 temp |= (base->FIFO &
839 (LPUART_FIFO_TXEMPT_MASK | LPUART_FIFO_RXEMPT_MASK | LPUART_FIFO_TXOF_MASK | LPUART_FIFO_RXUF_MASK)) >>
840 16U;
841#endif
842 /* Only keeps the status bits */
843 temp &= (uint32_t)kLPUART_AllFlags;
844 return temp;
845}
846
847/*!
848 * brief Clears status flags with a provided mask.
849 *
850 * This function clears LPUART status flags with a provided mask. Automatically cleared flags
851 * can't be cleared by this function.
852 * Flags that can only cleared or set by hardware are:
853 * kLPUART_TxDataRegEmptyFlag, kLPUART_TransmissionCompleteFlag, kLPUART_RxDataRegFullFlag,
854 * kLPUART_RxActiveFlag, kLPUART_NoiseErrorInRxDataRegFlag, kLPUART_ParityErrorInRxDataRegFlag,
855 * kLPUART_TxFifoEmptyFlag,kLPUART_RxFifoEmptyFlag
856 * Note: This API should be called when the Tx/Rx is idle, otherwise it takes no effects.
857 *
858 * param base LPUART peripheral base address.
859 * param mask the status flags to be cleared. The user can use the enumerators in the
860 * _lpuart_status_flag_t to do the OR operation and get the mask.
861 * return 0 succeed, others failed.
862 * retval kStatus_LPUART_FlagCannotClearManually The flag can't be cleared by this function but
863 * it is cleared automatically by hardware.
864 * retval kStatus_Success Status in the mask are cleared.
865 */
866status_t LPUART_ClearStatusFlags(LPUART_Type *base, uint32_t mask)
867{
868 uint32_t temp;
869 status_t status;
870
871 /* Only deal with the clearable flags */
872 mask &= (uint32_t)kLPUART_AllClearFlags;
873#if defined(FSL_FEATURE_LPUART_HAS_FIFO) && FSL_FEATURE_LPUART_HAS_FIFO
874 /* Status bits in FIFO register */
875 if ((mask & ((uint32_t)kLPUART_TxFifoOverflowFlag | (uint32_t)kLPUART_RxFifoUnderflowFlag)) != 0U)
876 {
877 /* Get the FIFO register value and mask the rx/tx FIFO flush bits and the status bits that can be W1C in case
878 they are written 1 accidentally. */
879 temp = (uint32_t)base->FIFO;
880 temp &= (uint32_t)(
881 ~(LPUART_FIFO_TXFLUSH_MASK | LPUART_FIFO_RXFLUSH_MASK | LPUART_FIFO_TXOF_MASK | LPUART_FIFO_RXUF_MASK));
882 temp |= (mask << 16U) & (LPUART_FIFO_TXOF_MASK | LPUART_FIFO_RXUF_MASK);
883 base->FIFO = temp;
884 }
885#endif
886 /* Status bits in STAT register */
887 /* First get the STAT register value and mask all the bits that not represent status, then OR with the status bit
888 * that is to be W1C */
889 temp = (base->STAT & 0x3E000000UL) | mask;
890 base->STAT = temp;
891 /* If some flags still pending. */
892 if (0U != (mask & LPUART_GetStatusFlags(base)))
893 {
894 status = kStatus_LPUART_FlagCannotClearManually;
895 }
896 else
897 {
898 status = kStatus_Success;
899 }
900
901 return status;
902}
903
904/*!
905 * brief Writes to the transmitter register using a blocking method.
906 *
907 * This function polls the transmitter register, first waits for the register to be empty or TX FIFO to have room,
908 * and writes data to the transmitter buffer, then waits for the data to be sent out to bus.
909 *
910 * param base LPUART peripheral base address.
911 * param data Start address of the data to write.
912 * param length Size of the data to write.
913 * retval kStatus_LPUART_Timeout Transmission timed out and was aborted.
914 * retval kStatus_Success Successfully wrote all data.
915 */
916status_t LPUART_WriteBlocking(LPUART_Type *base, const uint8_t *data, size_t length)
917{
918 assert(NULL != data);
919
920 const uint8_t *dataAddress = data;
921 size_t transferSize = length;
922
923#if UART_RETRY_TIMES
924 uint32_t waitTimes;
925#endif
926
927 while (0U != transferSize)
928 {
929#if UART_RETRY_TIMES
930 waitTimes = UART_RETRY_TIMES;
931 while ((0U == (base->STAT & LPUART_STAT_TDRE_MASK)) && (0U != --waitTimes))
932#else
933 while (0U == (base->STAT & LPUART_STAT_TDRE_MASK))
934#endif
935 {
936 }
937#if UART_RETRY_TIMES
938 if (0U == waitTimes)
939 {
940 return kStatus_LPUART_Timeout;
941 }
942#endif
943 base->DATA = *(dataAddress);
944 dataAddress++;
945 transferSize--;
946 }
947 /* Ensure all the data in the transmit buffer are sent out to bus. */
948#if UART_RETRY_TIMES
949 waitTimes = UART_RETRY_TIMES;
950 while ((0U == (base->STAT & LPUART_STAT_TC_MASK)) && (0U != --waitTimes))
951#else
952 while (0U == (base->STAT & LPUART_STAT_TC_MASK))
953#endif
954 {
955 }
956#if UART_RETRY_TIMES
957 if (0U == waitTimes)
958 {
959 return kStatus_LPUART_Timeout;
960 }
961#endif
962 return kStatus_Success;
963}
964
965/*!
966 * brief Reads the receiver data register using a blocking method.
967 *
968 * This function polls the receiver register, waits for the receiver register full or receiver FIFO
969 * has data, and reads data from the TX register.
970 *
971 * param base LPUART peripheral base address.
972 * param data Start address of the buffer to store the received data.
973 * param length Size of the buffer.
974 * retval kStatus_LPUART_RxHardwareOverrun Receiver overrun happened while receiving data.
975 * retval kStatus_LPUART_NoiseError Noise error happened while receiving data.
976 * retval kStatus_LPUART_FramingError Framing error happened while receiving data.
977 * retval kStatus_LPUART_ParityError Parity error happened while receiving data.
978 * retval kStatus_LPUART_Timeout Transmission timed out and was aborted.
979 * retval kStatus_Success Successfully received all data.
980 */
981status_t LPUART_ReadBlocking(LPUART_Type *base, uint8_t *data, size_t length)
982{
983 assert(NULL != data);
984
985 status_t status = kStatus_Success;
986 uint32_t statusFlag;
987 uint8_t *dataAddress = data;
988
989#if defined(FSL_FEATURE_LPUART_HAS_7BIT_DATA_SUPPORT) && FSL_FEATURE_LPUART_HAS_7BIT_DATA_SUPPORT
990 uint32_t ctrl = base->CTRL;
991 bool isSevenDataBits = (((ctrl & LPUART_CTRL_M7_MASK) != 0U) ||
992 (((ctrl & LPUART_CTRL_M_MASK) == 0U) && ((ctrl & LPUART_CTRL_PE_MASK) != 0U)));
993#endif
994
995#if UART_RETRY_TIMES
996 uint32_t waitTimes;
997#endif
998
999 while (0U != (length--))
1000 {
1001#if UART_RETRY_TIMES
1002 waitTimes = UART_RETRY_TIMES;
1003#endif
1004#if defined(FSL_FEATURE_LPUART_HAS_FIFO) && FSL_FEATURE_LPUART_HAS_FIFO
1005 while (0U == ((base->WATER & LPUART_WATER_RXCOUNT_MASK) >> LPUART_WATER_RXCOUNT_SHIFT))
1006#else
1007 while (0U == (base->STAT & LPUART_STAT_RDRF_MASK))
1008#endif
1009 {
1010#if UART_RETRY_TIMES
1011 if (0U == --waitTimes)
1012 {
1013 status = kStatus_LPUART_Timeout;
1014 break;
1015 }
1016#endif
1017 statusFlag = LPUART_GetStatusFlags(base);
1018
1019 if (0U != (statusFlag & (uint32_t)kLPUART_RxOverrunFlag))
1020 {
1021 status = ((kStatus_Success == LPUART_ClearStatusFlags(base, (uint32_t)kLPUART_RxOverrunFlag)) ?
1022 (kStatus_LPUART_RxHardwareOverrun) :
1023 (kStatus_LPUART_FlagCannotClearManually));
1024 /* Other error flags(FE, NF, and PF) are prevented from setting once OR is set, no need to check other
1025 * error flags*/
1026 break;
1027 }
1028
1029 if (0U != (statusFlag & (uint32_t)kLPUART_ParityErrorFlag))
1030 {
1031 status = ((kStatus_Success == LPUART_ClearStatusFlags(base, (uint32_t)kLPUART_ParityErrorFlag)) ?
1032 (kStatus_LPUART_ParityError) :
1033 (kStatus_LPUART_FlagCannotClearManually));
1034 }
1035
1036 if (0U != (statusFlag & (uint32_t)kLPUART_FramingErrorFlag))
1037 {
1038 status = ((kStatus_Success == LPUART_ClearStatusFlags(base, (uint32_t)kLPUART_FramingErrorFlag)) ?
1039 (kStatus_LPUART_FramingError) :
1040 (kStatus_LPUART_FlagCannotClearManually));
1041 }
1042
1043 if (0U != (statusFlag & (uint32_t)kLPUART_NoiseErrorFlag))
1044 {
1045 status = ((kStatus_Success == LPUART_ClearStatusFlags(base, (uint32_t)kLPUART_NoiseErrorFlag)) ?
1046 (kStatus_LPUART_NoiseError) :
1047 (kStatus_LPUART_FlagCannotClearManually));
1048 }
1049 if (kStatus_Success != status)
1050 {
1051 break;
1052 }
1053 }
1054
1055 if (kStatus_Success == status)
1056 {
1057#if defined(FSL_FEATURE_LPUART_HAS_7BIT_DATA_SUPPORT) && FSL_FEATURE_LPUART_HAS_7BIT_DATA_SUPPORT
1058 if (isSevenDataBits)
1059 {
1060 *(dataAddress) = (uint8_t)(base->DATA & 0x7FU);
1061 dataAddress++;
1062 }
1063 else
1064 {
1065 *(dataAddress) = (uint8_t)base->DATA;
1066 dataAddress++;
1067 }
1068#else
1069 *(dataAddress) = (uint8_t)base->DATA;
1070 dataAddress++;
1071#endif
1072 }
1073 else
1074 {
1075 break;
1076 }
1077 }
1078
1079 return status;
1080}
1081
1082/*!
1083 * brief Initializes the LPUART handle.
1084 *
1085 * This function initializes the LPUART handle, which can be used for other LPUART
1086 * transactional APIs. Usually, for a specified LPUART instance,
1087 * call this API once to get the initialized handle.
1088 *
1089 * The LPUART driver supports the "background" receiving, which means that user can set up
1090 * an RX ring buffer optionally. Data received is stored into the ring buffer even when the
1091 * user doesn't call the LPUART_TransferReceiveNonBlocking() API. If there is already data received
1092 * in the ring buffer, the user can get the received data from the ring buffer directly.
1093 * The ring buffer is disabled if passing NULL as p ringBuffer.
1094 *
1095 * param base LPUART peripheral base address.
1096 * param handle LPUART handle pointer.
1097 * param callback Callback function.
1098 * param userData User data.
1099 */
1100void LPUART_TransferCreateHandle(LPUART_Type *base,
1101 lpuart_handle_t *handle,
1102 lpuart_transfer_callback_t callback,
1103 void *userData)
1104{
1105 assert(NULL != handle);
1106
1107 uint32_t instance;
1108
1109#if defined(FSL_FEATURE_LPUART_HAS_7BIT_DATA_SUPPORT) && FSL_FEATURE_LPUART_HAS_7BIT_DATA_SUPPORT
1110 uint32_t ctrl = base->CTRL;
1111 bool isSevenDataBits = (((ctrl & LPUART_CTRL_M7_MASK) != 0U) ||
1112 (((ctrl & LPUART_CTRL_M_MASK) == 0U) && ((ctrl & LPUART_CTRL_PE_MASK) != 0U)));
1113#endif
1114
1115 /* Zero the handle. */
1116 (void)memset(handle, 0, sizeof(lpuart_handle_t));
1117
1118 /* Set the TX/RX state. */
1119 handle->rxState = (uint8_t)kLPUART_RxIdle;
1120 handle->txState = (uint8_t)kLPUART_TxIdle;
1121
1122 /* Set the callback and user data. */
1123 handle->callback = callback;
1124 handle->userData = userData;
1125
1126#if defined(FSL_FEATURE_LPUART_HAS_7BIT_DATA_SUPPORT) && FSL_FEATURE_LPUART_HAS_7BIT_DATA_SUPPORT
1127 /* Initial seven data bits flag */
1128 handle->isSevenDataBits = isSevenDataBits;
1129#endif
1130
1131 /* Get instance from peripheral base address. */
1132 instance = LPUART_GetInstance(base);
1133
1134 /* Save the handle in global variables to support the double weak mechanism. */
1135 s_lpuartHandle[instance] = handle;
1136
1137 s_lpuartIsr = LPUART_TransferHandleIRQ;
1138
1139/* Enable interrupt in NVIC. */
1140#if defined(FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ) && FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ
1141 (void)EnableIRQ(s_lpuartRxIRQ[instance]);
1142 (void)EnableIRQ(s_lpuartTxIRQ[instance]);
1143#else
1144 (void)EnableIRQ(s_lpuartIRQ[instance]);
1145#endif
1146}
1147
1148/*!
1149 * brief Sets up the RX ring buffer.
1150 *
1151 * This function sets up the RX ring buffer to a specific UART handle.
1152 *
1153 * When the RX ring buffer is used, data received is stored into the ring buffer even when
1154 * the user doesn't call the UART_TransferReceiveNonBlocking() API. If there is already data received
1155 * in the ring buffer, the user can get the received data from the ring buffer directly.
1156 *
1157 * note When using RX ring buffer, one byte is reserved for internal use. In other
1158 * words, if p ringBufferSize is 32, then only 31 bytes are used for saving data.
1159 *
1160 * param base LPUART peripheral base address.
1161 * param handle LPUART handle pointer.
1162 * param ringBuffer Start address of ring buffer for background receiving. Pass NULL to disable the ring buffer.
1163 * param ringBufferSize size of the ring buffer.
1164 */
1165void LPUART_TransferStartRingBuffer(LPUART_Type *base,
1166 lpuart_handle_t *handle,
1167 uint8_t *ringBuffer,
1168 size_t ringBufferSize)
1169{
1170 assert(NULL != handle);
1171 assert(NULL != ringBuffer);
1172
1173 /* Setup the ring buffer address */
1174 handle->rxRingBuffer = ringBuffer;
1175 handle->rxRingBufferSize = ringBufferSize;
1176 handle->rxRingBufferHead = 0U;
1177 handle->rxRingBufferTail = 0U;
1178
1179 /* Disable and re-enable the global interrupt to protect the interrupt enable register during read-modify-wrte. */
1180 uint32_t irqMask = DisableGlobalIRQ();
1181 /* Enable the interrupt to accept the data when user need the ring buffer. */
1182 base->CTRL |= (uint32_t)(LPUART_CTRL_RIE_MASK | LPUART_CTRL_ORIE_MASK);
1183 EnableGlobalIRQ(irqMask);
1184}
1185
1186/*!
1187 * brief Aborts the background transfer and uninstalls the ring buffer.
1188 *
1189 * This function aborts the background transfer and uninstalls the ring buffer.
1190 *
1191 * param base LPUART peripheral base address.
1192 * param handle LPUART handle pointer.
1193 */
1194void LPUART_TransferStopRingBuffer(LPUART_Type *base, lpuart_handle_t *handle)
1195{
1196 assert(NULL != handle);
1197
1198 if (handle->rxState == (uint8_t)kLPUART_RxIdle)
1199 {
1200 /* Disable and re-enable the global interrupt to protect the interrupt enable register during read-modify-wrte.
1201 */
1202 uint32_t irqMask = DisableGlobalIRQ();
1203 base->CTRL &= ~(uint32_t)(LPUART_CTRL_RIE_MASK | LPUART_CTRL_ORIE_MASK);
1204 EnableGlobalIRQ(irqMask);
1205 }
1206
1207 handle->rxRingBuffer = NULL;
1208 handle->rxRingBufferSize = 0U;
1209 handle->rxRingBufferHead = 0U;
1210 handle->rxRingBufferTail = 0U;
1211}
1212
1213/*!
1214 * brief Transmits a buffer of data using the interrupt method.
1215 *
1216 * This function send data using an interrupt method. This is a non-blocking function, which
1217 * returns directly without waiting for all data written to the transmitter register. When
1218 * all data is written to the TX register in the ISR, the LPUART driver calls the callback
1219 * function and passes the ref kStatus_LPUART_TxIdle as status parameter.
1220 *
1221 * note The kStatus_LPUART_TxIdle is passed to the upper layer when all data are written
1222 * to the TX register. However, there is no check to ensure that all the data sent out. Before disabling the TX,
1223 * check the kLPUART_TransmissionCompleteFlag to ensure that the transmit is finished.
1224 *
1225 * param base LPUART peripheral base address.
1226 * param handle LPUART handle pointer.
1227 * param xfer LPUART transfer structure, see #lpuart_transfer_t.
1228 * retval kStatus_Success Successfully start the data transmission.
1229 * retval kStatus_LPUART_TxBusy Previous transmission still not finished, data not all written to the TX register.
1230 * retval kStatus_InvalidArgument Invalid argument.
1231 */
1232status_t LPUART_TransferSendNonBlocking(LPUART_Type *base, lpuart_handle_t *handle, lpuart_transfer_t *xfer)
1233{
1234 assert(NULL != handle);
1235 assert(NULL != xfer);
1236 assert(NULL != xfer->txData);
1237 assert(0U != xfer->dataSize);
1238
1239 status_t status;
1240
1241 /* Return error if current TX busy. */
1242 if ((uint8_t)kLPUART_TxBusy == handle->txState)
1243 {
1244 status = kStatus_LPUART_TxBusy;
1245 }
1246 else
1247 {
1248 handle->txData = xfer->txData;
1249 handle->txDataSize = xfer->dataSize;
1250 handle->txDataSizeAll = xfer->dataSize;
1251 handle->txState = (uint8_t)kLPUART_TxBusy;
1252
1253 /* Disable and re-enable the global interrupt to protect the interrupt enable register during read-modify-wrte.
1254 */
1255 uint32_t irqMask = DisableGlobalIRQ();
1256 /* Enable transmitter interrupt. */
1257 base->CTRL |= (uint32_t)LPUART_CTRL_TIE_MASK;
1258 EnableGlobalIRQ(irqMask);
1259
1260 status = kStatus_Success;
1261 }
1262
1263 return status;
1264}
1265
1266/*!
1267 * brief Aborts the interrupt-driven data transmit.
1268 *
1269 * This function aborts the interrupt driven data sending. The user can get the remainBtyes to find out
1270 * how many bytes are not sent out.
1271 *
1272 * param base LPUART peripheral base address.
1273 * param handle LPUART handle pointer.
1274 */
1275void LPUART_TransferAbortSend(LPUART_Type *base, lpuart_handle_t *handle)
1276{
1277 assert(NULL != handle);
1278
1279 /* Disable and re-enable the global interrupt to protect the interrupt enable register during read-modify-wrte. */
1280 uint32_t irqMask = DisableGlobalIRQ();
1281 base->CTRL &= ~(uint32_t)(LPUART_CTRL_TIE_MASK | LPUART_CTRL_TCIE_MASK);
1282 EnableGlobalIRQ(irqMask);
1283
1284 handle->txDataSize = 0;
1285 handle->txState = (uint8_t)kLPUART_TxIdle;
1286}
1287
1288/*!
1289 * brief Gets the number of bytes that have been sent out to bus.
1290 *
1291 * This function gets the number of bytes that have been sent out to bus by an interrupt method.
1292 *
1293 * param base LPUART peripheral base address.
1294 * param handle LPUART handle pointer.
1295 * param count Send bytes count.
1296 * retval kStatus_NoTransferInProgress No send in progress.
1297 * retval kStatus_InvalidArgument Parameter is invalid.
1298 * retval kStatus_Success Get successfully through the parameter \p count;
1299 */
1300status_t LPUART_TransferGetSendCount(LPUART_Type *base, lpuart_handle_t *handle, uint32_t *count)
1301{
1302 assert(NULL != handle);
1303 assert(NULL != count);
1304
1305 status_t status = kStatus_Success;
1306 size_t tmptxDataSize = handle->txDataSize;
1307
1308 if ((uint8_t)kLPUART_TxIdle == handle->txState)
1309 {
1310 status = kStatus_NoTransferInProgress;
1311 }
1312 else
1313 {
1314#if defined(FSL_FEATURE_LPUART_HAS_FIFO) && FSL_FEATURE_LPUART_HAS_FIFO
1315 *count = handle->txDataSizeAll - tmptxDataSize -
1316 ((base->WATER & LPUART_WATER_TXCOUNT_MASK) >> LPUART_WATER_TXCOUNT_SHIFT);
1317#else
1318 if ((base->STAT & (uint32_t)kLPUART_TxDataRegEmptyFlag) != 0U)
1319 {
1320 *count = handle->txDataSizeAll - tmptxDataSize;
1321 }
1322 else
1323 {
1324 *count = handle->txDataSizeAll - tmptxDataSize - 1U;
1325 }
1326#endif
1327 }
1328
1329 return status;
1330}
1331
1332/*!
1333 * brief Receives a buffer of data using the interrupt method.
1334 *
1335 * This function receives data using an interrupt method. This is a non-blocking function
1336 * which returns without waiting to ensure that all data are received.
1337 * If the RX ring buffer is used and not empty, the data in the ring buffer is copied and
1338 * the parameter p receivedBytes shows how many bytes are copied from the ring buffer.
1339 * After copying, if the data in the ring buffer is not enough for read, the receive
1340 * request is saved by the LPUART driver. When the new data arrives, the receive request
1341 * is serviced first. When all data is received, the LPUART driver notifies the upper layer
1342 * through a callback function and passes a status parameter ref kStatus_UART_RxIdle.
1343 * For example, the upper layer needs 10 bytes but there are only 5 bytes in ring buffer.
1344 * The 5 bytes are copied to xfer->data, which returns with the
1345 * parameter p receivedBytes set to 5. For the remaining 5 bytes, the newly arrived data is
1346 * saved from xfer->data[5]. When 5 bytes are received, the LPUART driver notifies the upper layer.
1347 * If the RX ring buffer is not enabled, this function enables the RX and RX interrupt
1348 * to receive data to xfer->data. When all data is received, the upper layer is notified.
1349 *
1350 * param base LPUART peripheral base address.
1351 * param handle LPUART handle pointer.
1352 * param xfer LPUART transfer structure, see #uart_transfer_t.
1353 * param receivedBytes Bytes received from the ring buffer directly.
1354 * retval kStatus_Success Successfully queue the transfer into the transmit queue.
1355 * retval kStatus_LPUART_RxBusy Previous receive request is not finished.
1356 * retval kStatus_InvalidArgument Invalid argument.
1357 */
1358status_t LPUART_TransferReceiveNonBlocking(LPUART_Type *base,
1359 lpuart_handle_t *handle,
1360 lpuart_transfer_t *xfer,
1361 size_t *receivedBytes)
1362{
1363 assert(NULL != handle);
1364 assert(NULL != xfer);
1365 assert(NULL != xfer->rxData);
1366 assert(0U != xfer->dataSize);
1367
1368 uint32_t i;
1369 status_t status;
1370 uint32_t irqMask;
1371 /* How many bytes to copy from ring buffer to user memory. */
1372 size_t bytesToCopy = 0U;
1373 /* How many bytes to receive. */
1374 size_t bytesToReceive;
1375 /* How many bytes currently have received. */
1376 size_t bytesCurrentReceived;
1377
1378 /* How to get data:
1379 1. If RX ring buffer is not enabled, then save xfer->data and xfer->dataSize
1380 to lpuart handle, enable interrupt to store received data to xfer->data. When
1381 all data received, trigger callback.
1382 2. If RX ring buffer is enabled and not empty, get data from ring buffer first.
1383 If there are enough data in ring buffer, copy them to xfer->data and return.
1384 If there are not enough data in ring buffer, copy all of them to xfer->data,
1385 save the xfer->data remained empty space to lpuart handle, receive data
1386 to this empty space and trigger callback when finished. */
1387
1388 if ((uint8_t)kLPUART_RxBusy == handle->rxState)
1389 {
1390 status = kStatus_LPUART_RxBusy;
1391 }
1392 else
1393 {
1394 bytesToReceive = xfer->dataSize;
1395 bytesCurrentReceived = 0;
1396
1397 /* If RX ring buffer is used. */
1398 if (NULL != handle->rxRingBuffer)
1399 {
1400 /* Disable and re-enable the global interrupt to protect the interrupt enable register during
1401 * read-modify-wrte. */
1402 irqMask = DisableGlobalIRQ();
1403 /* Disable LPUART RX IRQ, protect ring buffer. */
1404 base->CTRL &= ~(uint32_t)(LPUART_CTRL_RIE_MASK | LPUART_CTRL_ORIE_MASK);
1405 EnableGlobalIRQ(irqMask);
1406
1407 /* How many bytes in RX ring buffer currently. */
1408 bytesToCopy = LPUART_TransferGetRxRingBufferLength(base, handle);
1409
1410 if (0U != bytesToCopy)
1411 {
1412 bytesToCopy = MIN(bytesToReceive, bytesToCopy);
1413
1414 bytesToReceive -= bytesToCopy;
1415
1416 /* Copy data from ring buffer to user memory. */
1417 for (i = 0U; i < bytesToCopy; i++)
1418 {
1419 xfer->rxData[bytesCurrentReceived] = handle->rxRingBuffer[handle->rxRingBufferTail];
1420 bytesCurrentReceived++;
1421
1422 /* Wrap to 0. Not use modulo (%) because it might be large and slow. */
1423 if (((uint32_t)handle->rxRingBufferTail + 1U) == handle->rxRingBufferSize)
1424 {
1425 handle->rxRingBufferTail = 0U;
1426 }
1427 else
1428 {
1429 handle->rxRingBufferTail++;
1430 }
1431 }
1432 }
1433
1434 /* If ring buffer does not have enough data, still need to read more data. */
1435 if (0U != bytesToReceive)
1436 {
1437 /* No data in ring buffer, save the request to LPUART handle. */
1438 handle->rxData = &xfer->rxData[bytesCurrentReceived];
1439 handle->rxDataSize = bytesToReceive;
1440 handle->rxDataSizeAll = xfer->dataSize;
1441 handle->rxState = (uint8_t)kLPUART_RxBusy;
1442 }
1443
1444 /* Disable and re-enable the global interrupt to protect the interrupt enable register during
1445 * read-modify-wrte. */
1446 irqMask = DisableGlobalIRQ();
1447 /* Re-enable LPUART RX IRQ. */
1448 base->CTRL |= (uint32_t)(LPUART_CTRL_RIE_MASK | LPUART_CTRL_ORIE_MASK);
1449 EnableGlobalIRQ(irqMask);
1450
1451 /* Call user callback since all data are received. */
1452 if (0U == bytesToReceive)
1453 {
1454 if (NULL != handle->callback)
1455 {
1456 handle->callback(base, handle, kStatus_LPUART_RxIdle, handle->userData);
1457 }
1458 }
1459 }
1460 /* Ring buffer not used. */
1461 else
1462 {
1463 handle->rxData = &xfer->rxData[bytesCurrentReceived];
1464 handle->rxDataSize = bytesToReceive;
1465 handle->rxDataSizeAll = bytesToReceive;
1466 handle->rxState = (uint8_t)kLPUART_RxBusy;
1467
1468 /* Disable and re-enable the global interrupt to protect the interrupt enable register during
1469 * read-modify-wrte. */
1470 irqMask = DisableGlobalIRQ();
1471 /* Enable RX interrupt. */
1472 base->CTRL |= (uint32_t)(LPUART_CTRL_RIE_MASK | LPUART_CTRL_ILIE_MASK | LPUART_CTRL_ORIE_MASK);
1473 EnableGlobalIRQ(irqMask);
1474 }
1475
1476 /* Return the how many bytes have read. */
1477 if (NULL != receivedBytes)
1478 {
1479 *receivedBytes = bytesCurrentReceived;
1480 }
1481
1482 status = kStatus_Success;
1483 }
1484
1485 return status;
1486}
1487
1488/*!
1489 * brief Aborts the interrupt-driven data receiving.
1490 *
1491 * This function aborts the interrupt-driven data receiving. The user can get the remainBytes to find out
1492 * how many bytes not received yet.
1493 *
1494 * param base LPUART peripheral base address.
1495 * param handle LPUART handle pointer.
1496 */
1497void LPUART_TransferAbortReceive(LPUART_Type *base, lpuart_handle_t *handle)
1498{
1499 assert(NULL != handle);
1500
1501 /* Only abort the receive to handle->rxData, the RX ring buffer is still working. */
1502 if (NULL == handle->rxRingBuffer)
1503 {
1504 /* Disable and re-enable the global interrupt to protect the interrupt enable register during read-modify-wrte.
1505 */
1506 uint32_t irqMask = DisableGlobalIRQ();
1507 /* Disable RX interrupt. */
1508 base->CTRL &= ~(uint32_t)(LPUART_CTRL_RIE_MASK | LPUART_CTRL_ILIE_MASK | LPUART_CTRL_ORIE_MASK);
1509 EnableGlobalIRQ(irqMask);
1510 }
1511
1512 handle->rxDataSize = 0U;
1513 handle->rxState = (uint8_t)kLPUART_RxIdle;
1514}
1515
1516/*!
1517 * brief Gets the number of bytes that have been received.
1518 *
1519 * This function gets the number of bytes that have been received.
1520 *
1521 * param base LPUART peripheral base address.
1522 * param handle LPUART handle pointer.
1523 * param count Receive bytes count.
1524 * retval kStatus_NoTransferInProgress No receive in progress.
1525 * retval kStatus_InvalidArgument Parameter is invalid.
1526 * retval kStatus_Success Get successfully through the parameter \p count;
1527 */
1528status_t LPUART_TransferGetReceiveCount(LPUART_Type *base, lpuart_handle_t *handle, uint32_t *count)
1529{
1530 assert(NULL != handle);
1531 assert(NULL != count);
1532
1533 status_t status = kStatus_Success;
1534 size_t tmprxDataSize = handle->rxDataSize;
1535
1536 if ((uint8_t)kLPUART_RxIdle == handle->rxState)
1537 {
1538 status = kStatus_NoTransferInProgress;
1539 }
1540 else
1541 {
1542 *count = handle->rxDataSizeAll - tmprxDataSize;
1543 }
1544
1545 return status;
1546}
1547
1548/*!
1549 * brief LPUART IRQ handle function.
1550 *
1551 * This function handles the LPUART transmit and receive IRQ request.
1552 *
1553 * param base LPUART peripheral base address.
1554 * param irqHandle LPUART handle pointer.
1555 */
1556void LPUART_TransferHandleIRQ(LPUART_Type *base, void *irqHandle)
1557{
1558 assert(NULL != irqHandle);
1559
1560 uint8_t count;
1561 uint8_t tempCount;
1562 uint32_t status = LPUART_GetStatusFlags(base);
1563 uint32_t enabledInterrupts = LPUART_GetEnabledInterrupts(base);
1564 uint16_t tpmRxRingBufferHead;
1565 uint32_t tpmData;
1566 uint32_t irqMask;
1567 lpuart_handle_t *handle = (lpuart_handle_t *)irqHandle;
1568
1569 /* If RX overrun. */
1570 if ((uint32_t)kLPUART_RxOverrunFlag == ((uint32_t)kLPUART_RxOverrunFlag & status))
1571 {
1572 /* Clear overrun flag, otherwise the RX does not work. */
1573 base->STAT = ((base->STAT & 0x3FE00000U) | LPUART_STAT_OR_MASK);
1574
1575 /* Trigger callback. */
1576 if (NULL != (handle->callback))
1577 {
1578 handle->callback(base, handle, kStatus_LPUART_RxHardwareOverrun, handle->userData);
1579 }
1580 }
1581
1582 /* If IDLE flag is set and the IDLE interrupt is enabled. */
1583 if ((0U != ((uint32_t)kLPUART_IdleLineFlag & status)) &&
1584 (0U != ((uint32_t)kLPUART_IdleLineInterruptEnable & enabledInterrupts)))
1585 {
1586#if defined(FSL_FEATURE_LPUART_HAS_FIFO) && FSL_FEATURE_LPUART_HAS_FIFO
1587 count = ((uint8_t)((base->WATER & LPUART_WATER_RXCOUNT_MASK) >> LPUART_WATER_RXCOUNT_SHIFT));
1588
1589 while ((0U != handle->rxDataSize) && (0U != count))
1590 {
1591 tempCount = (uint8_t)MIN(handle->rxDataSize, count);
1592
1593 /* Using non block API to read the data from the registers. */
1594 LPUART_ReadNonBlocking(base, handle->rxData, tempCount);
1595 handle->rxData = &handle->rxData[tempCount];
1596 handle->rxDataSize -= tempCount;
1597 count -= tempCount;
1598
1599 /* If rxDataSize is 0, invoke rx idle callback.*/
1600 if (0U == (handle->rxDataSize))
1601 {
1602 handle->rxState = (uint8_t)kLPUART_RxIdle;
1603
1604 if (NULL != handle->callback)
1605 {
1606 handle->callback(base, handle, kStatus_LPUART_RxIdle, handle->userData);
1607 }
1608 }
1609 }
1610#endif
1611 /* Clear IDLE flag.*/
1612 base->STAT = ((base->STAT & 0x3FE00000U) | LPUART_STAT_IDLE_MASK);
1613
1614 /* If rxDataSize is 0, disable rx ready, overrun and idle line interrupt.*/
1615 if (0U == handle->rxDataSize)
1616 {
1617 /* Disable and re-enable the global interrupt to protect the interrupt enable register during
1618 * read-modify-wrte. */
1619 irqMask = DisableGlobalIRQ();
1620 base->CTRL &= ~(uint32_t)(LPUART_CTRL_RIE_MASK | LPUART_CTRL_ILIE_MASK | LPUART_CTRL_ORIE_MASK);
1621 EnableGlobalIRQ(irqMask);
1622 }
1623 /* Invoke callback if callback is not NULL and rxDataSize is not 0. */
1624 else if (NULL != handle->callback)
1625 {
1626 handle->callback(base, handle, kStatus_LPUART_IdleLineDetected, handle->userData);
1627 }
1628 else
1629 {
1630 /* Avoid MISRA 15.7 */
1631 }
1632 }
1633 /* Receive data register full */
1634 if ((0U != ((uint32_t)kLPUART_RxDataRegFullFlag & status)) &&
1635 (0U != ((uint32_t)kLPUART_RxDataRegFullInterruptEnable & enabledInterrupts)))
1636 {
1637 /* Get the size that can be stored into buffer for this interrupt. */
1638#if defined(FSL_FEATURE_LPUART_HAS_FIFO) && FSL_FEATURE_LPUART_HAS_FIFO
1639 count = ((uint8_t)((base->WATER & LPUART_WATER_RXCOUNT_MASK) >> LPUART_WATER_RXCOUNT_SHIFT));
1640#else
1641 count = 1;
1642#endif
1643
1644 /* If handle->rxDataSize is not 0, first save data to handle->rxData. */
1645 while ((0U != handle->rxDataSize) && (0U != count))
1646 {
1647#if defined(FSL_FEATURE_LPUART_HAS_FIFO) && FSL_FEATURE_LPUART_HAS_FIFO
1648 tempCount = (uint8_t)MIN(handle->rxDataSize, count);
1649#else
1650 tempCount = 1;
1651#endif
1652
1653 /* Using non block API to read the data from the registers. */
1654 LPUART_ReadNonBlocking(base, handle->rxData, tempCount);
1655 handle->rxData = &handle->rxData[tempCount];
1656 handle->rxDataSize -= tempCount;
1657 count -= tempCount;
1658
1659 /* If all the data required for upper layer is ready, trigger callback. */
1660 if (0U == handle->rxDataSize)
1661 {
1662 handle->rxState = (uint8_t)kLPUART_RxIdle;
1663
1664 if (NULL != handle->callback)
1665 {
1666 handle->callback(base, handle, kStatus_LPUART_RxIdle, handle->userData);
1667 }
1668 }
1669 }
1670
1671 /* If use RX ring buffer, receive data to ring buffer. */
1672 if (NULL != handle->rxRingBuffer)
1673 {
1674 while (0U != count--)
1675 {
1676 /* If RX ring buffer is full, trigger callback to notify over run. */
1677 if (LPUART_TransferIsRxRingBufferFull(base, handle))
1678 {
1679 if (NULL != handle->callback)
1680 {
1681 handle->callback(base, handle, kStatus_LPUART_RxRingBufferOverrun, handle->userData);
1682 }
1683 }
1684
1685 /* If ring buffer is still full after callback function, the oldest data is overridden. */
1686 if (LPUART_TransferIsRxRingBufferFull(base, handle))
1687 {
1688 /* Increase handle->rxRingBufferTail to make room for new data. */
1689 if (((uint32_t)handle->rxRingBufferTail + 1U) == handle->rxRingBufferSize)
1690 {
1691 handle->rxRingBufferTail = 0U;
1692 }
1693 else
1694 {
1695 handle->rxRingBufferTail++;
1696 }
1697 }
1698
1699 /* Read data. */
1700 tpmRxRingBufferHead = handle->rxRingBufferHead;
1701 tpmData = base->DATA;
1702#if defined(FSL_FEATURE_LPUART_HAS_7BIT_DATA_SUPPORT) && FSL_FEATURE_LPUART_HAS_7BIT_DATA_SUPPORT
1703 if (handle->isSevenDataBits)
1704 {
1705 handle->rxRingBuffer[tpmRxRingBufferHead] = (uint8_t)(tpmData & 0x7FU);
1706 }
1707 else
1708 {
1709 handle->rxRingBuffer[tpmRxRingBufferHead] = (uint8_t)tpmData;
1710 }
1711#else
1712 handle->rxRingBuffer[tpmRxRingBufferHead] = (uint8_t)tpmData;
1713#endif
1714
1715 /* Increase handle->rxRingBufferHead. */
1716 if (((uint32_t)handle->rxRingBufferHead + 1U) == handle->rxRingBufferSize)
1717 {
1718 handle->rxRingBufferHead = 0U;
1719 }
1720 else
1721 {
1722 handle->rxRingBufferHead++;
1723 }
1724 }
1725 }
1726 /* If no receive requst pending, stop RX interrupt. */
1727 else if (0U == handle->rxDataSize)
1728 {
1729 /* Disable and re-enable the global interrupt to protect the interrupt enable register during
1730 * read-modify-wrte. */
1731 irqMask = DisableGlobalIRQ();
1732 base->CTRL &= ~(uint32_t)(LPUART_CTRL_RIE_MASK | LPUART_CTRL_ORIE_MASK | LPUART_CTRL_ILIE_MASK);
1733 EnableGlobalIRQ(irqMask);
1734 }
1735 else
1736 {
1737 }
1738 }
1739
1740 /* Send data register empty and the interrupt is enabled. */
1741 if ((0U != ((uint32_t)kLPUART_TxDataRegEmptyFlag & status)) &&
1742 (0U != ((uint32_t)kLPUART_TxDataRegEmptyInterruptEnable & enabledInterrupts)))
1743 {
1744/* Get the bytes that available at this moment. */
1745#if defined(FSL_FEATURE_LPUART_HAS_FIFO) && FSL_FEATURE_LPUART_HAS_FIFO
1746 count = (uint8_t)FSL_FEATURE_LPUART_FIFO_SIZEn(base) -
1747 (uint8_t)((base->WATER & LPUART_WATER_TXCOUNT_MASK) >> LPUART_WATER_TXCOUNT_SHIFT);
1748#else
1749 count = 1;
1750#endif
1751
1752 while ((0U != handle->txDataSize) && (0U != count))
1753 {
1754#if defined(FSL_FEATURE_LPUART_HAS_FIFO) && FSL_FEATURE_LPUART_HAS_FIFO
1755 tempCount = (uint8_t)MIN(handle->txDataSize, count);
1756#else
1757 tempCount = 1;
1758#endif
1759
1760 /* Using non block API to write the data to the registers. */
1761 LPUART_WriteNonBlocking(base, handle->txData, tempCount);
1762 handle->txData = &handle->txData[tempCount];
1763 handle->txDataSize -= tempCount;
1764 count -= tempCount;
1765
1766 /* If all the data are written to data register, notify user with the callback, then TX finished. */
1767 if (0U == handle->txDataSize)
1768 {
1769 /* Disable and re-enable the global interrupt to protect the interrupt enable register during
1770 * read-modify-wrte. */
1771 irqMask = DisableGlobalIRQ();
1772 /* Disable TX register empty interrupt and enable transmission completion interrupt. */
1773 base->CTRL = (base->CTRL & ~LPUART_CTRL_TIE_MASK) | LPUART_CTRL_TCIE_MASK;
1774 EnableGlobalIRQ(irqMask);
1775 }
1776 }
1777 }
1778
1779 /* Transmission complete and the interrupt is enabled. */
1780 if ((0U != ((uint32_t)kLPUART_TransmissionCompleteFlag & status)) &&
1781 (0U != ((uint32_t)kLPUART_TransmissionCompleteInterruptEnable & enabledInterrupts)))
1782 {
1783 /* Set txState to idle only when all data has been sent out to bus. */
1784 handle->txState = (uint8_t)kLPUART_TxIdle;
1785
1786 /* Disable and re-enable the global interrupt to protect the interrupt enable register during read-modify-wrte.
1787 */
1788 irqMask = DisableGlobalIRQ();
1789 /* Disable transmission complete interrupt. */
1790 base->CTRL &= ~(uint32_t)LPUART_CTRL_TCIE_MASK;
1791 EnableGlobalIRQ(irqMask);
1792
1793 /* Trigger callback. */
1794 if (NULL != handle->callback)
1795 {
1796 handle->callback(base, handle, kStatus_LPUART_TxIdle, handle->userData);
1797 }
1798 }
1799}
1800
1801/*!
1802 * brief LPUART Error IRQ handle function.
1803 *
1804 * This function handles the LPUART error IRQ request.
1805 *
1806 * param base LPUART peripheral base address.
1807 * param irqHandle LPUART handle pointer.
1808 */
1809void LPUART_TransferHandleErrorIRQ(LPUART_Type *base, void *irqHandle)
1810{
1811 /* To be implemented by User. */
1812}
1813#if defined(FSL_FEATURE_LPUART_HAS_SHARED_IRQ0_IRQ1) && FSL_FEATURE_LPUART_HAS_SHARED_IRQ0_IRQ1
1814#if defined(FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ) && FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ
1815void LPUART0_LPUART1_RX_DriverIRQHandler(void);
1816void LPUART0_LPUART1_RX_DriverIRQHandler(void)
1817{
1818 /* If handle is registered, treat the transfer function is enabled. */
1819 if (NULL != s_lpuartHandle[0])
1820 {
1821 s_lpuartIsr(LPUART0, s_lpuartHandle[0]);
1822 }
1823 if (NULL != s_lpuartHandle[1])
1824 {
1825 s_lpuartIsr(LPUART1, s_lpuartHandle[1]);
1826 }
1827 SDK_ISR_EXIT_BARRIER;
1828}
1829void LPUART0_LPUART1_TX_DriverIRQHandler(void);
1830void LPUART0_LPUART1_TX_DriverIRQHandler(void)
1831{
1832 /* If handle is registered, treat the transfer function is enabled. */
1833 if (NULL != s_lpuartHandle[0])
1834 {
1835 s_lpuartIsr(LPUART0, s_lpuartHandle[0]);
1836 }
1837 if (NULL != s_lpuartHandle[1])
1838 {
1839 s_lpuartIsr(LPUART1, s_lpuartHandle[1]);
1840 }
1841 SDK_ISR_EXIT_BARRIER;
1842}
1843#else
1844void LPUART0_LPUART1_DriverIRQHandler(void);
1845void LPUART0_LPUART1_DriverIRQHandler(void)
1846{
1847 /* If handle is registered, treat the transfer function is enabled. */
1848 if (NULL != s_lpuartHandle[0])
1849 {
1850 s_lpuartIsr(LPUART0, s_lpuartHandle[0]);
1851 }
1852 if (NULL != s_lpuartHandle[1])
1853 {
1854 s_lpuartIsr(LPUART1, s_lpuartHandle[1]);
1855 }
1856 SDK_ISR_EXIT_BARRIER;
1857}
1858#endif
1859#endif
1860
1861#if defined(LPUART0)
1862#if !(defined(FSL_FEATURE_LPUART_HAS_SHARED_IRQ0_IRQ1) && FSL_FEATURE_LPUART_HAS_SHARED_IRQ0_IRQ1)
1863#if defined(FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ) && FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ
1864void LPUART0_TX_DriverIRQHandler(void);
1865void LPUART0_TX_DriverIRQHandler(void)
1866{
1867 s_lpuartIsr(LPUART0, s_lpuartHandle[0]);
1868 SDK_ISR_EXIT_BARRIER;
1869}
1870void LPUART0_RX_DriverIRQHandler(void);
1871void LPUART0_RX_DriverIRQHandler(void)
1872{
1873 s_lpuartIsr(LPUART0, s_lpuartHandle[0]);
1874 SDK_ISR_EXIT_BARRIER;
1875}
1876#else
1877void LPUART0_DriverIRQHandler(void);
1878void LPUART0_DriverIRQHandler(void)
1879{
1880 s_lpuartIsr(LPUART0, s_lpuartHandle[0]);
1881 SDK_ISR_EXIT_BARRIER;
1882}
1883#endif
1884#endif
1885#endif
1886
1887#if defined(LPUART1)
1888#if !(defined(FSL_FEATURE_LPUART_HAS_SHARED_IRQ0_IRQ1) && FSL_FEATURE_LPUART_HAS_SHARED_IRQ0_IRQ1)
1889#if defined(FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ) && FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ
1890void LPUART1_TX_DriverIRQHandler(void);
1891void LPUART1_TX_DriverIRQHandler(void)
1892{
1893 s_lpuartIsr(LPUART1, s_lpuartHandle[1]);
1894 SDK_ISR_EXIT_BARRIER;
1895}
1896void LPUART1_RX_DriverIRQHandler(void);
1897void LPUART1_RX_DriverIRQHandler(void)
1898{
1899 s_lpuartIsr(LPUART1, s_lpuartHandle[1]);
1900 SDK_ISR_EXIT_BARRIER;
1901}
1902#else
1903void LPUART1_DriverIRQHandler(void);
1904void LPUART1_DriverIRQHandler(void)
1905{
1906 s_lpuartIsr(LPUART1, s_lpuartHandle[1]);
1907 SDK_ISR_EXIT_BARRIER;
1908}
1909#endif
1910#endif
1911#endif
1912
1913#if defined(LPUART2)
1914#if defined(FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ) && FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ
1915void LPUART2_TX_DriverIRQHandler(void);
1916void LPUART2_TX_DriverIRQHandler(void)
1917{
1918 s_lpuartIsr(LPUART2, s_lpuartHandle[2]);
1919 SDK_ISR_EXIT_BARRIER;
1920}
1921void LPUART2_RX_DriverIRQHandler(void);
1922void LPUART2_RX_DriverIRQHandler(void)
1923{
1924 s_lpuartIsr(LPUART2, s_lpuartHandle[2]);
1925 SDK_ISR_EXIT_BARRIER;
1926}
1927#else
1928void LPUART2_DriverIRQHandler(void);
1929void LPUART2_DriverIRQHandler(void)
1930{
1931 s_lpuartIsr(LPUART2, s_lpuartHandle[2]);
1932 SDK_ISR_EXIT_BARRIER;
1933}
1934#endif
1935#endif
1936
1937#if defined(LPUART3)
1938#if defined(FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ) && FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ
1939void LPUART3_TX_DriverIRQHandler(void);
1940void LPUART3_TX_DriverIRQHandler(void)
1941{
1942 s_lpuartIsr(LPUART3, s_lpuartHandle[3]);
1943 SDK_ISR_EXIT_BARRIER;
1944}
1945void LPUART3_RX_DriverIRQHandler(void);
1946void LPUART3_RX_DriverIRQHandler(void)
1947{
1948 s_lpuartIsr(LPUART3, s_lpuartHandle[3]);
1949 SDK_ISR_EXIT_BARRIER;
1950}
1951#else
1952void LPUART3_DriverIRQHandler(void);
1953void LPUART3_DriverIRQHandler(void)
1954{
1955 s_lpuartIsr(LPUART3, s_lpuartHandle[3]);
1956 SDK_ISR_EXIT_BARRIER;
1957}
1958#endif
1959#endif
1960
1961#if defined(LPUART4)
1962#if defined(FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ) && FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ
1963void LPUART4_TX_DriverIRQHandler(void);
1964void LPUART4_TX_DriverIRQHandler(void)
1965{
1966 s_lpuartIsr(LPUART4, s_lpuartHandle[4]);
1967 SDK_ISR_EXIT_BARRIER;
1968}
1969void LPUART4_RX_DriverIRQHandler(void);
1970void LPUART4_RX_DriverIRQHandler(void)
1971{
1972 s_lpuartIsr(LPUART4, s_lpuartHandle[4]);
1973 SDK_ISR_EXIT_BARRIER;
1974}
1975#else
1976void LPUART4_DriverIRQHandler(void);
1977void LPUART4_DriverIRQHandler(void)
1978{
1979 s_lpuartIsr(LPUART4, s_lpuartHandle[4]);
1980 SDK_ISR_EXIT_BARRIER;
1981}
1982#endif
1983#endif
1984
1985#if defined(LPUART5)
1986#if defined(FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ) && FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ
1987void LPUART5_TX_DriverIRQHandler(void);
1988void LPUART5_TX_DriverIRQHandler(void)
1989{
1990 s_lpuartIsr(LPUART5, s_lpuartHandle[5]);
1991 SDK_ISR_EXIT_BARRIER;
1992}
1993void LPUART5_RX_DriverIRQHandler(void);
1994void LPUART5_RX_DriverIRQHandler(void)
1995{
1996 s_lpuartIsr(LPUART5, s_lpuartHandle[5]);
1997 SDK_ISR_EXIT_BARRIER;
1998}
1999#else
2000void LPUART5_DriverIRQHandler(void);
2001void LPUART5_DriverIRQHandler(void)
2002{
2003 s_lpuartIsr(LPUART5, s_lpuartHandle[5]);
2004 SDK_ISR_EXIT_BARRIER;
2005}
2006#endif
2007#endif
2008
2009#if defined(LPUART6)
2010#if defined(FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ) && FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ
2011void LPUART6_TX_DriverIRQHandler(void);
2012void LPUART6_TX_DriverIRQHandler(void)
2013{
2014 s_lpuartIsr(LPUART6, s_lpuartHandle[6]);
2015 SDK_ISR_EXIT_BARRIER;
2016}
2017void LPUART6_RX_DriverIRQHandler(void);
2018void LPUART6_RX_DriverIRQHandler(void)
2019{
2020 s_lpuartIsr(LPUART6, s_lpuartHandle[6]);
2021 SDK_ISR_EXIT_BARRIER;
2022}
2023#else
2024void LPUART6_DriverIRQHandler(void);
2025void LPUART6_DriverIRQHandler(void)
2026{
2027 s_lpuartIsr(LPUART6, s_lpuartHandle[6]);
2028 SDK_ISR_EXIT_BARRIER;
2029}
2030#endif
2031#endif
2032
2033#if defined(LPUART7)
2034#if defined(FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ) && FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ
2035void LPUART7_TX_DriverIRQHandler(void);
2036void LPUART7_TX_DriverIRQHandler(void)
2037{
2038 s_lpuartIsr(LPUART7, s_lpuartHandle[7]);
2039 SDK_ISR_EXIT_BARRIER;
2040}
2041void LPUART7_RX_DriverIRQHandler(void);
2042void LPUART7_RX_DriverIRQHandler(void)
2043{
2044 s_lpuartIsr(LPUART7, s_lpuartHandle[7]);
2045 SDK_ISR_EXIT_BARRIER;
2046}
2047#else
2048void LPUART7_DriverIRQHandler(void);
2049void LPUART7_DriverIRQHandler(void)
2050{
2051 s_lpuartIsr(LPUART7, s_lpuartHandle[7]);
2052 SDK_ISR_EXIT_BARRIER;
2053}
2054#endif
2055#endif
2056
2057#if defined(LPUART8)
2058#if defined(FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ) && FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ
2059void LPUART8_TX_DriverIRQHandler(void);
2060void LPUART8_TX_DriverIRQHandler(void)
2061{
2062 s_lpuartIsr(LPUART8, s_lpuartHandle[8]);
2063 SDK_ISR_EXIT_BARRIER;
2064}
2065void LPUART8_RX_DriverIRQHandler(void);
2066void LPUART8_RX_DriverIRQHandler(void)
2067{
2068 s_lpuartIsr(LPUART8, s_lpuartHandle[8]);
2069 SDK_ISR_EXIT_BARRIER;
2070}
2071#else
2072void LPUART8_DriverIRQHandler(void);
2073void LPUART8_DriverIRQHandler(void)
2074{
2075 s_lpuartIsr(LPUART8, s_lpuartHandle[8]);
2076 SDK_ISR_EXIT_BARRIER;
2077}
2078#endif
2079#endif
2080
2081#if defined(LPUART9)
2082#if defined(FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ) && FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ
2083void LPUART9_TX_DriverIRQHandler(void);
2084void LPUART9_TX_DriverIRQHandler(void)
2085{
2086 s_lpuartIsr(LPUART9, s_lpuartHandle[9]);
2087 SDK_ISR_EXIT_BARRIER;
2088}
2089void LPUART9_RX_DriverIRQHandler(void);
2090void LPUART9_RX_DriverIRQHandler(void)
2091{
2092 s_lpuartIsr(LPUART9, s_lpuartHandle[9]);
2093 SDK_ISR_EXIT_BARRIER;
2094}
2095#else
2096void LPUART9_DriverIRQHandler(void);
2097void LPUART9_DriverIRQHandler(void)
2098{
2099 s_lpuartIsr(LPUART9, s_lpuartHandle[9]);
2100 SDK_ISR_EXIT_BARRIER;
2101}
2102#endif
2103#endif
2104
2105#if defined(LPUART10)
2106#if defined(FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ) && FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ
2107void LPUART10_TX_DriverIRQHandler(void);
2108void LPUART10_TX_DriverIRQHandler(void)
2109{
2110 s_lpuartIsr(LPUART10, s_lpuartHandle[10]);
2111 SDK_ISR_EXIT_BARRIER;
2112}
2113void LPUART10_RX_DriverIRQHandler(void);
2114void LPUART10_RX_DriverIRQHandler(void)
2115{
2116 s_lpuartIsr(LPUART10, s_lpuartHandle[10]);
2117 SDK_ISR_EXIT_BARRIER;
2118}
2119#else
2120void LPUART10_DriverIRQHandler(void);
2121void LPUART10_DriverIRQHandler(void)
2122{
2123 s_lpuartIsr(LPUART10, s_lpuartHandle[10]);
2124 SDK_ISR_EXIT_BARRIER;
2125}
2126#endif
2127#endif
2128
2129#if defined(LPUART11)
2130#if defined(FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ) && FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ
2131void LPUART11_TX_DriverIRQHandler(void);
2132void LPUART11_TX_DriverIRQHandler(void)
2133{
2134 s_lpuartIsr(LPUART11, s_lpuartHandle[11]);
2135 SDK_ISR_EXIT_BARRIER;
2136}
2137void LPUART11_RX_DriverIRQHandler(void);
2138void LPUART11_RX_DriverIRQHandler(void)
2139{
2140 s_lpuartIsr(LPUART11, s_lpuartHandle[11]);
2141 SDK_ISR_EXIT_BARRIER;
2142}
2143#else
2144void LPUART11_DriverIRQHandler(void);
2145void LPUART11_DriverIRQHandler(void)
2146{
2147 s_lpuartIsr(LPUART11, s_lpuartHandle[11]);
2148 SDK_ISR_EXIT_BARRIER;
2149}
2150#endif
2151#endif
2152
2153#if defined(LPUART12)
2154#if defined(FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ) && FSL_FEATURE_LPUART_HAS_SEPARATE_RX_TX_IRQ
2155void LPUART12_TX_DriverIRQHandler(void);
2156void LPUART12_TX_DriverIRQHandler(void)
2157{
2158 s_lpuartIsr(LPUART12, s_lpuartHandle[12]);
2159 SDK_ISR_EXIT_BARRIER;
2160}
2161void LPUART12_RX_DriverIRQHandler(void);
2162void LPUART12_RX_DriverIRQHandler(void)
2163{
2164 s_lpuartIsr(LPUART12, s_lpuartHandle[12]);
2165 SDK_ISR_EXIT_BARRIER;
2166}
2167#else
2168void LPUART12_DriverIRQHandler(void);
2169void LPUART12_DriverIRQHandler(void)
2170{
2171 s_lpuartIsr(LPUART12, s_lpuartHandle[12]);
2172 SDK_ISR_EXIT_BARRIER;
2173}
2174#endif
2175#endif
2176
2177#if defined(CM4_0__LPUART)
2178void M4_0_LPUART_DriverIRQHandler(void);
2179void M4_0_LPUART_DriverIRQHandler(void)
2180{
2181 s_lpuartIsr(CM4_0__LPUART, s_lpuartHandle[LPUART_GetInstance(CM4_0__LPUART)]);
2182 SDK_ISR_EXIT_BARRIER;
2183}
2184#endif
2185
2186#if defined(CM4_1__LPUART)
2187void M4_1_LPUART_DriverIRQHandler(void);
2188void M4_1_LPUART_DriverIRQHandler(void)
2189{
2190 s_lpuartIsr(CM4_1__LPUART, s_lpuartHandle[LPUART_GetInstance(CM4_1__LPUART)]);
2191 SDK_ISR_EXIT_BARRIER;
2192}
2193#endif
2194
2195#if defined(CM4__LPUART)
2196void M4_LPUART_DriverIRQHandler(void);
2197void M4_LPUART_DriverIRQHandler(void)
2198{
2199 s_lpuartIsr(CM4__LPUART, s_lpuartHandle[LPUART_GetInstance(CM4__LPUART)]);
2200 SDK_ISR_EXIT_BARRIER;
2201}
2202#endif
2203
2204#if defined(DMA__LPUART0)
2205void DMA_UART0_INT_DriverIRQHandler(void);
2206void DMA_UART0_INT_DriverIRQHandler(void)
2207{
2208 s_lpuartIsr(DMA__LPUART0, s_lpuartHandle[LPUART_GetInstance(DMA__LPUART0)]);
2209 SDK_ISR_EXIT_BARRIER;
2210}
2211#endif
2212
2213#if defined(DMA__LPUART1)
2214void DMA_UART1_INT_DriverIRQHandler(void);
2215void DMA_UART1_INT_DriverIRQHandler(void)
2216{
2217 s_lpuartIsr(DMA__LPUART1, s_lpuartHandle[LPUART_GetInstance(DMA__LPUART1)]);
2218 SDK_ISR_EXIT_BARRIER;
2219}
2220#endif
2221
2222#if defined(DMA__LPUART2)
2223void DMA_UART2_INT_DriverIRQHandler(void);
2224void DMA_UART2_INT_DriverIRQHandler(void)
2225{
2226 s_lpuartIsr(DMA__LPUART2, s_lpuartHandle[LPUART_GetInstance(DMA__LPUART2)]);
2227 SDK_ISR_EXIT_BARRIER;
2228}
2229#endif
2230
2231#if defined(DMA__LPUART3)
2232void DMA_UART3_INT_DriverIRQHandler(void);
2233void DMA_UART3_INT_DriverIRQHandler(void)
2234{
2235 s_lpuartIsr(DMA__LPUART3, s_lpuartHandle[LPUART_GetInstance(DMA__LPUART3)]);
2236 SDK_ISR_EXIT_BARRIER;
2237}
2238#endif
2239
2240#if defined(DMA__LPUART4)
2241void DMA_UART4_INT_DriverIRQHandler(void);
2242void DMA_UART4_INT_DriverIRQHandler(void)
2243{
2244 s_lpuartIsr(DMA__LPUART4, s_lpuartHandle[LPUART_GetInstance(DMA__LPUART4)]);
2245 SDK_ISR_EXIT_BARRIER;
2246}
2247#endif
2248
2249#if defined(ADMA__LPUART0)
2250void ADMA_UART0_INT_DriverIRQHandler(void);
2251void ADMA_UART0_INT_DriverIRQHandler(void)
2252{
2253 s_lpuartIsr(ADMA__LPUART0, s_lpuartHandle[LPUART_GetInstance(ADMA__LPUART0)]);
2254 SDK_ISR_EXIT_BARRIER;
2255}
2256#endif
2257
2258#if defined(ADMA__LPUART1)
2259void ADMA_UART1_INT_DriverIRQHandler(void);
2260void ADMA_UART1_INT_DriverIRQHandler(void)
2261{
2262 s_lpuartIsr(ADMA__LPUART1, s_lpuartHandle[LPUART_GetInstance(ADMA__LPUART1)]);
2263 SDK_ISR_EXIT_BARRIER;
2264}
2265#endif
2266
2267#if defined(ADMA__LPUART2)
2268void ADMA_UART2_INT_DriverIRQHandler(void);
2269void ADMA_UART2_INT_DriverIRQHandler(void)
2270{
2271 s_lpuartIsr(ADMA__LPUART2, s_lpuartHandle[LPUART_GetInstance(ADMA__LPUART2)]);
2272 SDK_ISR_EXIT_BARRIER;
2273}
2274#endif
2275
2276#if defined(ADMA__LPUART3)
2277void ADMA_UART3_INT_DriverIRQHandler(void);
2278void ADMA_UART3_INT_DriverIRQHandler(void)
2279{
2280 s_lpuartIsr(ADMA__LPUART3, s_lpuartHandle[LPUART_GetInstance(ADMA__LPUART3)]);
2281 SDK_ISR_EXIT_BARRIER;
2282}
2283#endif
2284