1 /*
2 * Copyright (c) 2021-2022-2024 HPMicro
3 *
4 * SPDX-License-Identifier: BSD-3-Clause
5 *
6 */
7
8 #ifndef HPM_UART_DRV_H
9 #define HPM_UART_DRV_H
10 #include "hpm_common.h"
11 #include "hpm_uart_regs.h"
12 #include "hpm_soc_feature.h"
13
14 /**
15 *
16 * @brief UART driver APIs
17 * @defgroup uart_interface UART driver APIs
18 * @ingroup io_interfaces
19 * @{
20 */
21
22 /**
23 * @brief UART status
24 */
25 enum {
26 status_uart_no_suitable_baudrate_parameter_found = MAKE_STATUS(status_group_uart, 1),
27 };
28
29 /* @brief Parity */
30 typedef enum parity {
31 parity_none = 0,
32 parity_odd,
33 parity_even,
34 parity_always_1,
35 parity_always_0,
36 } parity_setting_t;
37
38 /* @brief Stop bits */
39 typedef enum num_of_stop_bits {
40 stop_bits_1 = 0,
41 stop_bits_1_5,
42 stop_bits_2,
43 } num_of_stop_bits_t;
44
45 /* @brief Word length */
46 typedef enum word_length {
47 word_length_5_bits = 0,
48 word_length_6_bits,
49 word_length_7_bits,
50 word_length_8_bits,
51 } word_length_t;
52
53 /* @brief UART fifo trigger levels */
54 typedef enum uart_fifo_trg_lvl {
55 #if defined(HPM_IP_FEATURE_UART_FINE_FIFO_THRLD) && (HPM_IP_FEATURE_UART_FINE_FIFO_THRLD == 1)
56 uart_fifo_1_byte = 0,
57 uart_fifo_2_bytes = 1,
58 uart_fifo_3_bytes = 2,
59 uart_fifo_4_bytes = 3,
60 uart_fifo_5_bytes = 4,
61 uart_fifo_6_bytes = 5,
62 uart_fifo_7_bytes = 6,
63 uart_fifo_8_bytes = 7,
64 uart_fifo_9_bytes = 8,
65 uart_fifo_10_bytes = 9,
66 uart_fifo_11_bytes = 10,
67 uart_fifo_12_bytes = 11,
68 uart_fifo_13_bytes = 12,
69 uart_fifo_14_bytes = 13,
70 uart_fifo_15_bytes = 14,
71 uart_fifo_16_bytes = 15,
72
73 uart_rx_fifo_trg_not_empty = uart_fifo_1_byte,
74 uart_rx_fifo_trg_gt_one_quarter = uart_fifo_4_bytes,
75 uart_rx_fifo_trg_gt_half = uart_fifo_8_bytes,
76 uart_rx_fifo_trg_gt_three_quarters = uart_fifo_12_bytes,
77
78 uart_tx_fifo_trg_not_full = uart_fifo_16_bytes,
79 uart_tx_fifo_trg_lt_three_quarters = uart_fifo_12_bytes,
80 uart_tx_fifo_trg_lt_half = uart_fifo_8_bytes,
81 uart_tx_fifo_trg_lt_one_quarter = uart_fifo_4_bytes,
82 #else
83 uart_rx_fifo_trg_not_empty = 0,
84 uart_rx_fifo_trg_gt_one_quarter = 1,
85 uart_rx_fifo_trg_gt_half = 2,
86 uart_rx_fifo_trg_gt_three_quarters = 3,
87
88 uart_tx_fifo_trg_not_full = 0,
89 uart_tx_fifo_trg_lt_three_quarters = 1,
90 uart_tx_fifo_trg_lt_half = 2,
91 uart_tx_fifo_trg_lt_one_quarter = 3,
92 #endif
93 } uart_fifo_trg_lvl_t;
94
95 /* @brief UART signals */
96 typedef enum uart_signal {
97 uart_signal_rts = UART_MCR_RTS_MASK,
98 } uart_signal_t;
99
100 /* @brief UART signal levels */
101 typedef enum uart_signal_level {
102 uart_signal_level_high,
103 uart_signal_level_low,
104 } uart_signal_level_t;
105
106 /* @brief UART modem status */
107 typedef enum uart_modem_stat {
108 uart_modem_stat_cts = UART_MSR_CTS_MASK,
109 uart_modem_stat_dcts_changed = UART_MSR_DCTS_MASK,
110 } uart_modem_stat_t;
111
112 /* @brief UART interrupt enable masks */
113 typedef enum uart_intr_enable {
114 uart_intr_rx_data_avail_or_timeout = UART_IER_ERBI_MASK,
115 uart_intr_tx_slot_avail = UART_IER_ETHEI_MASK,
116 uart_intr_rx_line_stat = UART_IER_ELSI_MASK,
117 uart_intr_modem_stat = UART_IER_EMSI_MASK,
118 #if defined(HPM_IP_FEATURE_UART_RX_IDLE_DETECT) && (HPM_IP_FEATURE_UART_RX_IDLE_DETECT == 1)
119 uart_intr_rx_line_idle = UART_IER_ERXIDLE_MASK,
120 #endif
121 #if defined(HPM_IP_FEATURE_UART_9BIT_MODE) && (HPM_IP_FEATURE_UART_9BIT_MODE == 1)
122 uart_intr_tx_line_idle = UART_IER_ETXIDLE_MASK,
123 #endif
124 #if defined(HPM_IP_FEATURE_UART_ADDR_MATCH) && (HPM_IP_FEATURE_UART_ADDR_MATCH == 1)
125 uart_intr_addr_match = UART_IER_EADDRM_MASK,
126 uart_intr_addr_match_and_rxidle = UART_IER_EADDRM_IDLE_MASK,
127 uart_intr_addr_datalost = UART_IER_EDATLOST_MASK,
128 #endif
129 } uart_intr_enable_t;
130
131 /* @brief UART interrupt IDs */
132 typedef enum uart_intr_id {
133 uart_intr_id_modem_stat = 0x0,
134 uart_intr_id_tx_slot_avail = 0x2,
135 uart_intr_id_rx_data_avail = 0x4,
136 uart_intr_id_rx_line_stat = 0x6,
137 uart_intr_id_rx_timeout = 0xc,
138 } uart_intr_id_t;
139
140 /* @brief UART status */
141 typedef enum uart_stat {
142 uart_stat_data_ready = UART_LSR_DR_MASK, /* rx data ready in fifo */
143 uart_stat_overrun_error = UART_LSR_OE_MASK,
144 uart_stat_parity_error = UART_LSR_PE_MASK,
145 uart_stat_framing_error = UART_LSR_FE_MASK,
146 uart_stat_line_break = UART_LSR_LBREAK_MASK,
147 uart_stat_tx_slot_avail = UART_LSR_THRE_MASK,
148 uart_stat_transmitter_empty = UART_LSR_TEMT_MASK,
149 uart_stat_rx_fifo_error = UART_LSR_ERRF_MASK,
150 } uart_stat_t;
151
152 /**
153 * @brief UART modem config
154 */
155 typedef struct uart_modem_config {
156 bool auto_flow_ctrl_en; /**< Auto flow control enable flag */
157 bool loop_back_en; /**< Loop back enable flag */
158 bool set_rts_high; /**< Set signal RTS level high flag */
159 } uart_modem_config_t;
160
161 #if defined(HPM_IP_FEATURE_UART_RX_IDLE_DETECT) && (HPM_IP_FEATURE_UART_RX_IDLE_DETECT == 1)
162 /**
163 * @brief UART Idle detection conditions, suitable for RX and TX
164 */
165 typedef enum hpm_uart_rxline_idle_cond {
166 uart_rxline_idle_cond_rxline_logic_one = 0, /**< Treat as idle if the RX Line high duration exceeds threshold */
167 uart_rxline_idle_cond_state_machine_idle = 1 /**< Treat as idle if the RX state machine idle state duration exceeds threshold */
168 } uart_rxline_idle_cond_t;
169
170 /**
171 * @brief UART Idle config, suitable for RX and TX
172 */
173 typedef struct hpm_uart_rxline_idle_detect_config {
174 bool detect_enable; /**< RX Line Idle detection flag */
175 bool detect_irq_enable; /**< Enable RX Line Idle detection interrupt */
176 uart_rxline_idle_cond_t idle_cond; /**< RX Line Idle detection condition */
177 uint8_t threshold; /**< UART RX Line Idle detection threshold, in terms of bits */
178 } uart_rxline_idle_config_t;
179 #endif
180
181 /**
182 * @brief UART config
183 */
184 typedef struct hpm_uart_config {
185 uint32_t src_freq_in_hz; /**< Source clock frequency in Hz */
186 uint32_t baudrate; /**< Baudrate */
187 uint8_t num_of_stop_bits; /**< Number of stop bits */
188 uint8_t word_length; /**< Word length */
189 uint8_t parity; /**< Parity */
190 uint8_t tx_fifo_level; /**< TX Fifo level */
191 uint8_t rx_fifo_level; /**< RX Fifo level */
192 bool dma_enable; /**< DMA Enable flag */
193 bool fifo_enable; /**< Fifo Enable flag */
194 uart_modem_config_t modem_config; /**< Modem config */
195 #if defined(HPM_IP_FEATURE_UART_RX_IDLE_DETECT) && (HPM_IP_FEATURE_UART_RX_IDLE_DETECT == 1)
196 uart_rxline_idle_config_t rxidle_config; /**< RX Idle configuration */
197 #endif
198 #if defined(HPM_IP_FEATURE_UART_9BIT_MODE) && (HPM_IP_FEATURE_UART_9BIT_MODE == 1)
199 uart_rxline_idle_config_t txidle_config; /**< TX Idle configuration */
200 #endif
201 #if defined(HPM_IP_FEATURE_UART_RX_EN) && (HPM_IP_FEATURE_UART_RX_EN == 1)
202 bool rx_enable; /**< RX Enable configuration */
203 #endif
204 } uart_config_t;
205
206 #if defined(HPM_IP_FEATURE_UART_TRIG_MODE) && (HPM_IP_FEATURE_UART_TRIG_MODE == 1)
207 typedef struct {
208 uint16_t stop_bit_len;
209 bool en_stop_bit_insert;
210 bool hardware_trig;
211 bool trig_mode;
212 bool trig_clr_rxfifo;
213 } uart_trig_config_t;
214 #endif
215
216 typedef struct {
217 uint8_t tx_fifo_level; /**< TX Fifo level */
218 uint8_t rx_fifo_level; /**< RX Fifo level */
219 bool reset_tx_fifo; /**< reset tx Fifo */
220 bool reset_rx_fifo; /**< reset rx Fifo */
221 bool dma_enable; /**< DMA Enable flag */
222 bool fifo_enable; /**< Fifo Enable flag */
223 } uart_fifo_ctrl_t;
224
225 #ifdef __cplusplus
226 extern "C" {
227 #endif
228
229 /**
230 * @brief Get fifo size
231 *
232 * @param [in] ptr UART base address
233 * @retval size of Fifo
234 */
uart_get_fifo_size(UART_Type * ptr)235 static inline uint8_t uart_get_fifo_size(UART_Type *ptr)
236 {
237 return 16 << ((ptr->CFG & UART_CFG_FIFOSIZE_MASK) >> UART_CFG_FIFOSIZE_SHIFT);
238 }
239
240 /**
241 * @brief uart config fifo control
242 *
243 * @note fifo control register(FCR) is WO access, if support FCCR register, it is RW access.
244 *
245 * @param [in] ptr UART base address
246 * @param [in] ctrl uart_fifo_ctrl_t
247 */
248 void uart_config_fifo_ctrl(UART_Type *ptr, uart_fifo_ctrl_t *ctrl);
249
250 /**
251 * @brief uart clear rx fifo by reading data
252 *
253 * @note read out all data in rx fifo, the uart_intr_rx_data_avail_or_timeout is cleared
254 * when RBR register is read
255 *
256 * @param [in] ptr UART base address
257 */
uart_clear_rx_fifo(UART_Type * ptr)258 static inline void uart_clear_rx_fifo(UART_Type *ptr)
259 {
260 while (ptr->LSR & UART_LSR_DR_MASK) {
261 ptr->RBR;
262 }
263 }
264
265 /**
266 * @brief Reset TX Fifo
267 *
268 * @param [in] ptr UART base address
269 */
uart_reset_tx_fifo(UART_Type * ptr)270 static inline void uart_reset_tx_fifo(UART_Type *ptr)
271 {
272 #if defined(HPM_IP_FEATURE_UART_FCRR) && (HPM_IP_FEATURE_UART_FCRR == 1)
273 ptr->FCRR |= UART_FCRR_TFIFORST_MASK;
274 #else
275 ptr->FCR = UART_FCR_TFIFORST_MASK | (ptr->GPR);
276 #endif
277 }
278
279 /**
280 * @brief Reset RX Fifo
281 *
282 * @param [in] ptr UART base address
283 */
uart_reset_rx_fifo(UART_Type * ptr)284 static inline void uart_reset_rx_fifo(UART_Type *ptr)
285 {
286 #if defined(HPM_IP_FEATURE_UART_FCRR) && (HPM_IP_FEATURE_UART_FCRR == 1)
287 ptr->FCRR |= UART_FCRR_RFIFORST_MASK;
288 #else
289 ptr->FCR = UART_FCR_RFIFORST_MASK | (ptr->GPR);
290 #endif
291 }
292
293 /**
294 * @brief [in] Reset both TX and RX Fifo
295 *
296 * @param [in] ptr UART base address
297 */
uart_reset_all_fifo(UART_Type * ptr)298 static inline void uart_reset_all_fifo(UART_Type *ptr)
299 {
300 #if defined(HPM_IP_FEATURE_UART_FCRR) && (HPM_IP_FEATURE_UART_FCRR == 1)
301 ptr->FCRR |= UART_FCRR_TFIFORST_MASK | UART_FCRR_RFIFORST_MASK;
302 #else
303 ptr->FCR = UART_FCR_RFIFORST_MASK | UART_FCR_TFIFORST_MASK | (ptr->GPR);
304 #endif
305 }
306
307 /**
308 * @brief Enable modem loopback
309 *
310 * @param [in] ptr UART base address
311 */
uart_modem_enable_loopback(UART_Type * ptr)312 static inline void uart_modem_enable_loopback(UART_Type *ptr)
313 {
314 ptr->MCR |= UART_MCR_LOOP_MASK;
315 }
316
317 /**
318 * @brief Disable modem loopback
319 *
320 * @param [in] ptr UART base address
321 */
uart_modem_disable_loopback(UART_Type * ptr)322 static inline void uart_modem_disable_loopback(UART_Type *ptr)
323 {
324 ptr->MCR &= ~UART_MCR_LOOP_MASK;
325 }
326
327 /**
328 * @brief Disable modem auto flow control
329 *
330 * @param [in] ptr UART base address
331 */
332
uart_modem_disable_auto_flow_control(UART_Type * ptr)333 static inline void uart_modem_disable_auto_flow_control(UART_Type *ptr)
334 {
335 ptr->MCR &= ~UART_MCR_AFE_MASK;
336 }
337
338 /**
339 * @brief Enable modem auto flow control
340 *
341 * @param [in] ptr UART base address
342 */
uart_modem_enable_auto_flow_control(UART_Type * ptr)343 static inline void uart_modem_enable_auto_flow_control(UART_Type *ptr)
344 {
345 ptr->MCR |= UART_MCR_AFE_MASK;
346 }
347
348 /**
349 * @brief Configure modem
350 *
351 * @param [in] ptr UART base address
352 * @param config Pointer to modem config struct
353 */
uart_modem_config(UART_Type * ptr,uart_modem_config_t * config)354 static inline void uart_modem_config(UART_Type *ptr, uart_modem_config_t *config)
355 {
356 ptr->MCR = UART_MCR_AFE_SET(config->auto_flow_ctrl_en)
357 | UART_MCR_LOOP_SET(config->loop_back_en)
358 | UART_MCR_RTS_SET(!config->set_rts_high);
359 }
360
361 /**
362 * @brief Get modem status
363 *
364 * @param [in] ptr UART base address
365 * @retval Current modem status
366 */
uart_get_modem_status(UART_Type * ptr)367 static inline uint8_t uart_get_modem_status(UART_Type *ptr)
368 {
369 return ptr->MSR;
370 }
371
372 /**
373 * @brief Write byte to TX
374 *
375 * @param ptr UART base address
376 * @param c data to be sent
377 */
uart_write_byte(UART_Type * ptr,uint8_t c)378 static inline void uart_write_byte(UART_Type *ptr, uint8_t c)
379 {
380 ptr->THR = UART_THR_THR_SET(c);
381 }
382
383
384 /**
385 * @brief Read byte from RX
386 *
387 * @param ptr UART base address
388 * @retval RX byte
389 */
uart_read_byte(UART_Type * ptr)390 static inline uint8_t uart_read_byte(UART_Type *ptr)
391 {
392 return (ptr->RBR & UART_RBR_RBR_MASK);
393 }
394
395 /**
396 * @brief Check modem status with given mask
397 *
398 * @param [in] ptr UART base address
399 * @param mask Status mask value to be checked against
400 * @retval true if any bit in given mask is set
401 * @retval false if none of any bit in given mask is set
402 */
uart_check_modem_status(UART_Type * ptr,uart_modem_stat_t mask)403 static inline bool uart_check_modem_status(UART_Type *ptr, uart_modem_stat_t mask)
404 {
405 return ((ptr->MSR & mask) != 0U) ? true : false;
406 }
407
408 /**
409 * @brief Disable IRQ with mask
410 *
411 * @param [in] ptr UART base address
412 * @param irq_mask IRQ mask value to be disabled
413 */
uart_disable_irq(UART_Type * ptr,uart_intr_enable_t irq_mask)414 static inline void uart_disable_irq(UART_Type *ptr, uart_intr_enable_t irq_mask)
415 {
416 ptr->IER &= ~irq_mask;
417 }
418
419 /**
420 * @brief Enable IRQ with mask
421 *
422 * @param [in] ptr UART base address
423 * @param irq_mask IRQ mask value to be enabled
424 */
uart_enable_irq(UART_Type * ptr,uart_intr_enable_t irq_mask)425 static inline void uart_enable_irq(UART_Type *ptr, uart_intr_enable_t irq_mask)
426 {
427 ptr->IER |= irq_mask;
428 }
429
430 /**
431 * @brief Get Enabled IRQ
432 *
433 * @param [in] ptr UART base address
434 * @return enabled irq
435 */
uart_get_enabled_irq(UART_Type * ptr)436 static inline uint32_t uart_get_enabled_irq(UART_Type *ptr)
437 {
438 return ptr->IER;
439 }
440
441 /**
442 * @brief Get interrupt identification
443 *
444 * @param [in] ptr UART base address
445 * @retval interrupt id
446 */
uart_get_irq_id(UART_Type * ptr)447 static inline uint8_t uart_get_irq_id(UART_Type *ptr)
448 {
449 return (ptr->IIR & UART_IIR_INTRID_MASK);
450 }
451
452 #if defined(HPM_IP_FEATURE_UART_RX_IDLE_DETECT) && (HPM_IP_FEATURE_UART_RX_IDLE_DETECT == 1)
453
454 /* if HPM_IP_FEATURE_UART_E00018_FIX = 1, the IIR2 register exists, should use IIR2 to get/clear rx idle status */
455 #if !defined(HPM_IP_FEATURE_UART_E00018_FIX) || (HPM_IP_FEATURE_UART_E00018_FIX == 0)
456 /**
457 * @brief Determine whether UART RX Line is idle
458 * @param [in] ptr UART base address
459 * @retval false if uart RX line is not idle
460 */
uart_is_rxline_idle(UART_Type * ptr)461 static inline bool uart_is_rxline_idle(UART_Type *ptr)
462 {
463 return ((ptr->IIR & UART_IIR_RXIDLE_FLAG_MASK) != 0U) ? true : false;
464 }
465
466 /**
467 * @brief Clear UART RX Line Idle Flag
468 * @param [in] ptr UART base address
469 */
uart_clear_rxline_idle_flag(UART_Type * ptr)470 static inline void uart_clear_rxline_idle_flag(UART_Type *ptr)
471 {
472 ptr->IIR = UART_IIR_RXIDLE_FLAG_MASK; /* Write-1-Clear Logic */
473 ptr->FCR = ptr->GPR;
474 }
475 #endif
476
477 /**
478 * @brief Enable UART RX Idle Line detection logic
479 * @param [in] ptr UART base address
480 */
uart_enable_rxline_idle_detection(UART_Type * ptr)481 static inline void uart_enable_rxline_idle_detection(UART_Type *ptr)
482 {
483 ptr->IDLE_CFG |= UART_IDLE_CFG_RX_IDLE_EN_MASK;
484 }
485
486 /**
487 * @brief Disable UART RX Idle Line detection logic
488 *
489 * @param [in] ptr UART base address
490 */
uart_disable_rxline_idle_detection(UART_Type * ptr)491 static inline void uart_disable_rxline_idle_detection(UART_Type *ptr)
492 {
493 ptr->IDLE_CFG &= ~UART_IDLE_CFG_RX_IDLE_EN_MASK;
494 }
495
496 /**
497 * @brief Configure UART RX Line detection
498 * @param [in] ptr UART base address
499 * @param [in] rxidle_config RXLine IDLE detection configuration
500 * @retval status_success if no error occurs
501 */
502 hpm_stat_t uart_init_rxline_idle_detection(UART_Type *ptr, uart_rxline_idle_config_t rxidle_config);
503
504 #endif
505
506 #if defined(HPM_IP_FEATURE_UART_E00018_FIX) && (HPM_IP_FEATURE_UART_E00018_FIX == 1)
507 /**
508 * @brief Determine whether UART TX Line is idle
509 * @param [in] ptr UART base address
510 * @retval false if uart TX line is not idle
511 */
uart_is_txline_idle(UART_Type * ptr)512 static inline bool uart_is_txline_idle(UART_Type *ptr)
513 {
514 return ((ptr->IIR2 & UART_IIR2_TXIDLE_FLAG_MASK) != 0U) ? true : false;
515 }
516
517 /**
518 * @brief Clear UART TX Line Idle Flag
519 * @param [in] ptr UART base address
520 */
uart_clear_txline_idle_flag(UART_Type * ptr)521 static inline void uart_clear_txline_idle_flag(UART_Type *ptr)
522 {
523 ptr->IIR2 = UART_IIR2_TXIDLE_FLAG_MASK; /* Write-1-Clear Logic */
524 }
525
526 /**
527 * @brief Determine whether UART RX Line is idle
528 * @param [in] ptr UART base address
529 * @retval false if uart RX line is not idle
530 */
uart_is_rxline_idle(UART_Type * ptr)531 static inline bool uart_is_rxline_idle(UART_Type *ptr)
532 {
533 return ((ptr->IIR2 & UART_IIR2_RXIDLE_FLAG_MASK) != 0U) ? true : false;
534 }
535
536 /**
537 * @brief Clear UART RX Line Idle Flag
538 * @param [in] ptr UART base address
539 */
uart_clear_rxline_idle_flag(UART_Type * ptr)540 static inline void uart_clear_rxline_idle_flag(UART_Type *ptr)
541 {
542 ptr->IIR2 = UART_IIR2_RXIDLE_FLAG_MASK; /* Write-1-Clear Logic */
543 }
544 #endif
545
546 #if defined(HPM_IP_FEATURE_UART_9BIT_MODE) && (HPM_IP_FEATURE_UART_9BIT_MODE == 1)
547 /**
548 * @brief Enable UART TX Idle Line detection logic
549 * @param [in] ptr UART base address
550 */
uart_enable_txline_idle_detection(UART_Type * ptr)551 static inline void uart_enable_txline_idle_detection(UART_Type *ptr)
552 {
553 ptr->IDLE_CFG |= UART_IDLE_CFG_TX_IDLE_EN_MASK;
554 }
555
556 /**
557 * @brief Disable UART TX Idle Line detection logic
558 *
559 * @param [in] ptr UART base address
560 */
uart_disable_txline_idle_detection(UART_Type * ptr)561 static inline void uart_disable_txline_idle_detection(UART_Type *ptr)
562 {
563 ptr->IDLE_CFG &= ~UART_IDLE_CFG_TX_IDLE_EN_MASK;
564 }
565
566 /**
567 * @brief Configure UART TX Line detection
568 * @param [in] ptr UART base address
569 * @param [in] txidle_config TXLine IDLE detection configuration
570 * @retval status_success if no error occurs
571 */
572 hpm_stat_t uart_init_txline_idle_detection(UART_Type *ptr, uart_rxline_idle_config_t txidle_config);
573
574 #endif
575
576
577
578 /**
579 * @brief Get status
580 *
581 * @param [in] ptr UART base address
582 * @retval current status
583 */
uart_get_status(UART_Type * ptr)584 static inline uint32_t uart_get_status(UART_Type *ptr)
585 {
586 return ptr->LSR;
587 }
588
589 /**
590 * @brief Check uart status according to the given status mask
591 *
592 * @note maybe clear other bits, such as PE/OE/LBREAK/ERRF bit. use uart_get_status API if you need to get these bits
593 * @param [in] ptr UART base address
594 * @param mask Status mask value to be checked against
595 * @retval true if any bit in given mask is set
596 * @retval false if none of any bit in given mask is set
597 */
uart_check_status(UART_Type * ptr,uart_stat_t mask)598 static inline bool uart_check_status(UART_Type *ptr, uart_stat_t mask)
599 {
600 return ((ptr->LSR & mask) != 0U) ? true : false;
601 }
602
603 /**
604 * @brief Get default config
605 *
606 * @param [in] ptr UART base address
607 * @param config Pointer to the buffer to save default values
608 */
609 void uart_default_config(UART_Type *ptr, uart_config_t *config);
610
611 /**
612 * @brief Initialization
613 *
614 * @param [in] ptr UART base address
615 * @param config Pointer to config struct
616 * @retval status_success only if it succeeds
617 */
618 hpm_stat_t uart_init(UART_Type *ptr, uart_config_t *config);
619
620 /**
621 * @brief Send one byte after checking thresh hold status
622 *
623 * @param [in] ptr UART base address
624 * @param c Byte to be sent
625 * @retval status_success only if it succeeds
626 */
627 hpm_stat_t uart_send_byte(UART_Type *ptr, uint8_t c);
628
629 /**
630 * @brief Receive one byte after checking data ready status
631 *
632 * @param [in] ptr UART base address
633 * @param c Pointer to buffer to save the byte received on UART
634 * @retval status_success only if it succeeds
635 */
636 hpm_stat_t uart_receive_byte(UART_Type *ptr, uint8_t *c);
637
638 /**
639 * @brief Try to receive one byte without checking data ready status
640 *
641 * @param [in] ptr UART base address
642 * @param c Pointer to buffer to save the byte received on UART
643 * @retval status_success only if it succeeds
644 */
645 hpm_stat_t uart_try_receive_byte(UART_Type *ptr, uint8_t *c);
646
647 /**
648 * @brief Set uart signal output level
649 *
650 * @param [in] ptr UART base address
651 * @param signal Target signal
652 * @param level Target signal level
653 */
654 void uart_set_signal_level(UART_Type *ptr,
655 uart_signal_t signal,
656 uart_signal_level_t level);
657
658 /**
659 * @brief Flush sending buffer/fifo
660 *
661 * @param [in] ptr UART base address
662 * @retval status_success only if it succeeds
663 */
664 hpm_stat_t uart_flush(UART_Type *ptr);
665
666 /**
667 * @brief Receive bytes blocking
668 *
669 * @param [in] ptr UART base address
670 * @param buf Pointer to the buffer to save received data
671 * @param size_in_byte Size in byte to be sent
672 * @retval status_success only if it succeeds
673 */
674 hpm_stat_t uart_receive_data(UART_Type *ptr, uint8_t *buf, uint32_t size_in_byte);
675
676 /**
677 * @brief Send bytes blocking
678 *
679 * @param [in] ptr UART base address
680 * @param buf Pointer to the buffer to be sent
681 * @param size_in_byte Size in byte to be sent
682 * @retval status_success only if it succeeds
683 */
684 hpm_stat_t uart_send_data(UART_Type *ptr, uint8_t *buf, uint32_t size_in_byte);
685
686 /**
687 * @brief Sets UART baudrate.
688 *
689 * This function configures the UART module baud rate. This function is used to update
690 * the UART module baud rate after the UART module is initialized by the uart_init.
691 *
692 * @param ptr UART base address
693 * @param baudrate UART baudrate to be set
694 * @param src_clock_hz UART clock source frequency in Hz.
695 * @retval status_uart_no_suitable_baudrate_parameter_found Baudrate is not supported in the current clock source
696 * @retval status_success Set baudrate succeeded.
697 */
698 hpm_stat_t uart_set_baudrate(UART_Type *ptr, uint32_t baudrate, uint32_t src_clock_hz);
699
700
701 #if defined(HPM_IP_FEATURE_UART_TRIG_MODE) && (HPM_IP_FEATURE_UART_TRIG_MODE == 1)
702 /**
703 * @brief uart configure transfer trigger mode
704 *
705 * This function can configure uart to send data in fifo after being triggered
706 *
707 * @param ptr UART base address
708 * @param config uart_trig_config_t config
709 */
710 void uart_config_transfer_trig_mode(UART_Type *ptr, uart_trig_config_t *config);
711
712 /**
713 * @brief uart software trigger transmit
714 *
715 * This function immediately triggers the transfer, the transfer configed by uart_config_transfer_trig_mode()
716 *
717 * @param ptr UART base address
718 */
uart_software_trig_transfer(UART_Type * ptr)719 static inline void uart_software_trig_transfer(UART_Type *ptr)
720 {
721 ptr->MOTO_CFG &= ~UART_MOTO_CFG_HWTRG_EN_MASK;
722 ptr->MOTO_CFG |= UART_MOTO_CFG_SWTRG_MASK;
723 }
724
725 /**
726 * @brief uart enable hardware trigger mode
727 *
728 * This function enable hardware trigger the transfer, the transfer start when hardware event occured
729 *
730 * @param ptr UART base address
731 * @param enable true for enable, false for disable
732 */
uart_enable_hardware_trig_transfer(UART_Type * ptr,bool enable)733 static inline void uart_enable_hardware_trig_transfer(UART_Type *ptr, bool enable)
734 {
735 if (enable) {
736 ptr->MOTO_CFG |= UART_MOTO_CFG_HWTRG_EN_MASK;
737 } else {
738 ptr->MOTO_CFG &= ~UART_MOTO_CFG_HWTRG_EN_MASK;
739 }
740 }
741
742 /**
743 * @brief UART get data count in rx fifo
744 *
745 * @param ptr UART base address
746 * @retval data count
747 */
uart_get_data_count_in_rx_fifo(UART_Type * ptr)748 static inline uint8_t uart_get_data_count_in_rx_fifo(UART_Type *ptr)
749 {
750 return UART_LSR_RFIFO_NUM_GET(ptr->LSR);
751 }
752
753 /**
754 * @brief UART get data count in tx fifo
755 *
756 * @param ptr UART base address
757 * @retval data count
758 */
uart_get_data_count_in_tx_fifo(UART_Type * ptr)759 static inline uint8_t uart_get_data_count_in_tx_fifo(UART_Type *ptr)
760 {
761 return UART_LSR_TFIFO_NUM_GET(ptr->LSR);
762 }
763 #endif
764
765 #if defined(HPM_IP_FEATURE_UART_ADDR_MATCH) && (HPM_IP_FEATURE_UART_ADDR_MATCH == 1)
766 /**
767 * @brief uart enable 9bit transmit mode
768 *
769 * @param ptr UART base address
770 * @param enable true for enable, false for disable
771 */
uart_enable_9bit_transmit_mode(UART_Type * ptr,bool enable)772 static inline void uart_enable_9bit_transmit_mode(UART_Type *ptr, bool enable)
773 {
774 if (enable) {
775 ptr->ADDR_CFG |= UART_ADDR_CFG_TXEN_9BIT_MASK
776 | UART_ADDR_CFG_RXEN_ADDR_MSB_MASK
777 | UART_ADDR_CFG_RXEN_9BIT_MASK;
778 } else {
779 ptr->ADDR_CFG &= ~(UART_ADDR_CFG_TXEN_9BIT_MASK
780 | UART_ADDR_CFG_RXEN_ADDR_MSB_MASK
781 | UART_ADDR_CFG_RXEN_9BIT_MASK);
782 }
783 }
784
785 /**
786 * @brief uart enable address0 match
787 *
788 * @param ptr UART base address
789 * @param addr address value
790 */
uart_enable_address0_match(UART_Type * ptr,uint8_t addr)791 static inline void uart_enable_address0_match(UART_Type *ptr, uint8_t addr)
792 {
793 ptr->ADDR_CFG &= ~UART_ADDR_CFG_ADDR0_MASK;
794 ptr->ADDR_CFG |= UART_ADDR_CFG_A0_EN_MASK | UART_ADDR_CFG_ADDR0_SET(addr);
795 }
796
797 /**
798 * @brief uart enable address1 match
799 *
800 * @param ptr UART base address
801 * @param addr address value
802 */
uart_enable_address1_match(UART_Type * ptr,uint8_t addr)803 static inline void uart_enable_address1_match(UART_Type *ptr, uint8_t addr)
804 {
805 ptr->ADDR_CFG &= ~UART_ADDR_CFG_ADDR1_MASK;
806 ptr->ADDR_CFG |= UART_ADDR_CFG_A1_EN_MASK | UART_ADDR_CFG_ADDR1_SET(addr);
807 }
808
809 /**
810 * @brief uart disable address0 match
811 *
812 * @param ptr UART base address
813 */
uart_disable_address0_match(UART_Type * ptr)814 static inline void uart_disable_address0_match(UART_Type *ptr)
815 {
816 ptr->ADDR_CFG &= ~UART_ADDR_CFG_A0_EN_MASK;
817 }
818
819 /**
820 * @brief uart disable address1 match
821 *
822 * @param ptr UART base address
823 */
uart_disable_address1_match(UART_Type * ptr)824 static inline void uart_disable_address1_match(UART_Type *ptr)
825 {
826 ptr->ADDR_CFG &= ~UART_ADDR_CFG_A1_EN_MASK;
827 }
828
829 /**
830 * @brief uart disable address match(address0 and address1)
831 *
832 * @param ptr UART base address
833 */
uart_disable_address_match(UART_Type * ptr)834 static inline void uart_disable_address_match(UART_Type *ptr)
835 {
836 ptr->ADDR_CFG &= ~(UART_ADDR_CFG_A0_EN_MASK | UART_ADDR_CFG_A1_EN_MASK);
837 }
838
839 /**
840 * @brief Determine whether address match for 9bit mode
841 * @param [in] ptr UART base address
842 * @retval false if uart address is not match
843 */
uart_is_addr_match(UART_Type * ptr)844 static inline bool uart_is_addr_match(UART_Type *ptr)
845 {
846 return ((ptr->IIR2 & UART_IIR2_ADDR_MATCH_MASK) != 0U) ? true : false;
847 }
848
849 /**
850 * @brief Clear UART address match Flag
851 * @param [in] ptr UART base address
852 */
uart_clear_addr_match_flag(UART_Type * ptr)853 static inline void uart_clear_addr_match_flag(UART_Type *ptr)
854 {
855 ptr->IIR2 = UART_IIR2_ADDR_MATCH_MASK; /* Write-1-Clear Logic */
856 }
857
858 /**
859 * @brief Determine whether address match and rx idle for 9bit mode
860 * @param [in] ptr UART base address
861 * @retval false if uart address is not match and not rx idle
862 */
uart_is_addr_match_and_rxidle(UART_Type * ptr)863 static inline bool uart_is_addr_match_and_rxidle(UART_Type *ptr)
864 {
865 return ((ptr->IIR2 & UART_IIR2_ADDR_MATCH_IDLE_MASK) != 0U) ? true : false;
866 }
867
868 /**
869 * @brief Clear UART address match and rxidle Flag
870 * @param [in] ptr UART base address
871 */
uart_clear_addr_match_and_rxidle_flag(UART_Type * ptr)872 static inline void uart_clear_addr_match_and_rxidle_flag(UART_Type *ptr)
873 {
874 ptr->IIR2 = UART_IIR2_ADDR_MATCH_IDLE_MASK; /* Write-1-Clear Logic */
875 }
876
877 /**
878 * @brief Determine whether data lost for 9bit mode
879 * @param [in] ptr UART base address
880 * @retval false if uart data is not lost
881 */
uart_is_data_lost(UART_Type * ptr)882 static inline bool uart_is_data_lost(UART_Type *ptr)
883 {
884 return ((ptr->IIR2 & UART_IIR2_DATA_LOST_MASK) != 0U) ? true : false;
885 }
886
887 /**
888 * @brief Clear UART data lost Flag
889 * @param [in] ptr UART base address
890 */
uart_clear_data_lost_flag(UART_Type * ptr)891 static inline void uart_clear_data_lost_flag(UART_Type *ptr)
892 {
893 ptr->IIR2 = UART_IIR2_DATA_LOST_MASK; /* Write-1-Clear Logic */
894 }
895 #endif
896
897 /**
898 * @brief Write RTS level for uart modem mode
899 *
900 * @param [in] ptr UART base address
901 * @param high RTS set to high when it is set to true
902 */
uart_modem_write_rts_pin(UART_Type * ptr,uint8_t high)903 static inline void uart_modem_write_rts_pin(UART_Type *ptr, uint8_t high)
904 {
905 if (high == true) {
906 ptr->MCR &= ~UART_MCR_RTS_MASK;
907 } else {
908 ptr->MCR |= UART_MCR_RTS_MASK;
909 }
910 }
911
912 #ifdef __cplusplus
913 }
914 #endif
915 /**
916 * @}
917 */
918
919 #endif /* HPM_UART_DRV_H */
920