xref: /btstack/port/renesas-ek-ra6m4a-da14531/e2-project/ra/fsp/src/r_sci_uart/r_sci_uart.c (revision c30869498fb8e98c1408c9db0e7624f02f483b73)
1 /***********************************************************************************************************************
2  * Copyright [2020-2022] Renesas Electronics Corporation and/or its affiliates.  All Rights Reserved.
3  *
4  * This software and documentation are supplied by Renesas Electronics America Inc. and may only be used with products
5  * of Renesas Electronics Corp. and its affiliates ("Renesas").  No other uses are authorized.  Renesas products are
6  * sold pursuant to Renesas terms and conditions of sale.  Purchasers are solely responsible for the selection and use
7  * of Renesas products and Renesas assumes no liability.  No license, express or implied, to any intellectual property
8  * right is granted by Renesas. This software is protected under all applicable laws, including copyright laws. Renesas
9  * reserves the right to change or discontinue this software and/or this documentation. THE SOFTWARE AND DOCUMENTATION
10  * IS DELIVERED TO YOU "AS IS," AND RENESAS MAKES NO REPRESENTATIONS OR WARRANTIES, AND TO THE FULLEST EXTENT
11  * PERMISSIBLE UNDER APPLICABLE LAW, DISCLAIMS ALL WARRANTIES, WHETHER EXPLICITLY OR IMPLICITLY, INCLUDING WARRANTIES
12  * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, AND NONINFRINGEMENT, WITH RESPECT TO THE SOFTWARE OR
13  * DOCUMENTATION.  RENESAS SHALL HAVE NO LIABILITY ARISING OUT OF ANY SECURITY VULNERABILITY OR BREACH.  TO THE MAXIMUM
14  * EXTENT PERMITTED BY LAW, IN NO EVENT WILL RENESAS BE LIABLE TO YOU IN CONNECTION WITH THE SOFTWARE OR DOCUMENTATION
15  * (OR ANY PERSON OR ENTITY CLAIMING RIGHTS DERIVED FROM YOU) FOR ANY LOSS, DAMAGES, OR CLAIMS WHATSOEVER, INCLUDING,
16  * WITHOUT LIMITATION, ANY DIRECT, CONSEQUENTIAL, SPECIAL, INDIRECT, PUNITIVE, OR INCIDENTAL DAMAGES; ANY LOST PROFITS,
17  * OTHER ECONOMIC DAMAGE, PROPERTY DAMAGE, OR PERSONAL INJURY; AND EVEN IF RENESAS HAS BEEN ADVISED OF THE POSSIBILITY
18  * OF SUCH LOSS, DAMAGES, CLAIMS OR COSTS.
19  **********************************************************************************************************************/
20 
21 /***********************************************************************************************************************
22  * Includes
23  **********************************************************************************************************************/
24 #include "bsp_api.h"
25 #include "r_sci_uart.h"
26 #include <string.h>
27 
28 /***********************************************************************************************************************
29  * Macro definitions
30  **********************************************************************************************************************/
31 #ifndef SCI_UART_CFG_RX_ENABLE
32  #define SCI_UART_CFG_RX_ENABLE                 1
33 #endif
34 #ifndef SCI_UART_CFG_TX_ENABLE
35  #define SCI_UART_CFG_TX_ENABLE                 1
36 #endif
37 
38 /* Number of divisors in the data table used for baud rate calculation. */
39 #define SCI_UART_NUM_DIVISORS_ASYNC             (13U)
40 
41 /* Valid range of values for the modulation duty register is 128 - 256 (256 = modulation disabled). */
42 #define SCI_UART_MDDR_MIN                       (128U)
43 #define SCI_UART_MDDR_MAX                       (256U)
44 
45 /* The bit rate register is 8-bits, so the maximum value is 255. */
46 #define SCI_UART_BRR_MAX                        (255U)
47 
48 /* No limit to the number of bytes to read or write if DTC is not used. */
49 #define SCI_UART_MAX_READ_WRITE_NO_DTC          (0xFFFFFFFFU)
50 
51 /* Mask of invalid data bits in 9-bit mode. */
52 #define SCI_UART_ALIGN_2_BYTES                  (0x1U)
53 
54 /* "SCIU" in ASCII.  Used to determine if the control block is open. */
55 #define SCI_UART_OPEN                           (0x53434955U)
56 
57 #define SCI_UART_SCMR_DEFAULT_VALUE             (0xF2U)
58 #define SCI_UART_BRR_DEFAULT_VALUE              (0xFFU)
59 #define SCI_UART_MDDR_DEFAULT_VALUE             (0xFFU)
60 #define SCI_UART_FCR_DEFAULT_VALUE              (0xF800)
61 #define SCI_UART_DCCR_DEFAULT_VALUE             (0x40U)
62 
63 #define SCI_UART_FIFO_DAT_MASK                  (0x1FFU)
64 
65 #define FRDR_TDAT_MASK_9BITS                    (0x01FFU)
66 #define SPTR_SPB2D_BIT                          (1U)
67 #define SPTR_OUTPUT_ENABLE_MASK                 (0x04U)
68 
69 #define SCI_UART_SSR_FIFO_DR_RDF                (0x41)
70 
71 #define SCI_UART_SPMR_CTSE_OFFSET               (1U)
72 
73 /* SCI SCR register bit masks */
74 #define SCI_SCR_TEIE_MASK                       (0x04U) ///< Transmit End Interrupt Enable
75 #define SCI_SCR_RE_MASK                         (0x10U) ///< Receive Enable
76 #define SCI_SCR_TE_MASK                         (0x20U) ///< Transmit Enable
77 #define SCI_SCR_RIE_MASK                        (0x40U) ///< Receive Interrupt Enable
78 #define SCI_SCR_TIE_MASK                        (0x80U) ///< Transmit Interrupt Enable
79 
80 /* SCI SEMR register bit offsets */
81 #define SCI_UART_SEMR_BRME_OFFSET               (2U)
82 #define SCI_UART_SEMR_ABCSE_OFFSET              (3U)
83 #define SCI_UART_SEMR_ABCS_OFFSET               (4U)
84 #define SCI_UART_SEMR_BGDM_OFFSET               (6U)
85 #define SCI_UART_SEMR_BAUD_SETTING_MASK         ((1U << SCI_UART_SEMR_BRME_OFFSET) |  \
86                                                  (1U << SCI_UART_SEMR_ABCSE_OFFSET) | \
87                                                  (1U << SCI_UART_SEMR_ABCS_OFFSET) | (1U << SCI_UART_SEMR_BGDM_OFFSET))
88 
89 /* SCI SMR register bit masks */
90 #define SCI_SMR_CKS_VALUE_MASK                  (0x03U) ///< CKS: 2 bits
91 
92 /* SCI SSR register receiver error bit masks */
93 #define SCI_SSR_ORER_MASK                       (0x20U) ///< overflow error
94 #define SCI_SSR_FER_MASK                        (0x10U) ///< framing error
95 #define SCI_SSR_PER_MASK                        (0x08U) ///< parity err
96 #define SCI_RCVR_ERR_MASK                       (SCI_SSR_ORER_MASK | SCI_SSR_FER_MASK | SCI_SSR_PER_MASK)
97 
98 #define SCI_REG_SIZE                            (R_SCI1_BASE - R_SCI0_BASE)
99 
100 #define SCI_UART_INVALID_8BIT_PARAM             (0xFFU)
101 #define SCI_UART_INVALID_16BIT_PARAM            (0xFFFFU)
102 
103 #define SCI_UART_DTC_MAX_TRANSFER               (0x10000U)
104 
105 #define SCI_UART_FCR_TRIGGER_MASK               (0xF)
106 #define SCI_UART_FCR_RSTRG_OFFSET               (12)
107 #define SCI_UART_FCR_RTRG_OFFSET                (8)
108 #define SCI_UART_FCR_TTRG_OFFSET                (4)
109 #define SCI_UART_FCR_RESET_TX_RX                (0x6)
110 
111 #define SCI_UART_9BIT_TRANSFER_BUFFER_OFFSET    (0xB)
112 #define SCI_UART_FIFO_TRANSFER_BUFFER_OFFSET    (0xC)
113 
114 #define SCI_UART_DTC_RX_TRANSFER_SETTINGS       ((TRANSFER_MODE_NORMAL << TRANSFER_SETTINGS_MODE_BITS) |         \
115                                                  (TRANSFER_SIZE_1_BYTE << TRANSFER_SETTINGS_SIZE_BITS) |         \
116                                                  (TRANSFER_ADDR_MODE_FIXED << TRANSFER_SETTINGS_SRC_ADDR_BITS) | \
117                                                  (TRANSFER_IRQ_END << TRANSFER_SETTINGS_IRQ_BITS) |              \
118                                                  (TRANSFER_ADDR_MODE_INCREMENTED << TRANSFER_SETTINGS_DEST_ADDR_BITS))
119 #define SCI_UART_DTC_TX_TRANSFER_SETTINGS       ((TRANSFER_MODE_NORMAL << TRANSFER_SETTINGS_MODE_BITS) |               \
120                                                  (TRANSFER_SIZE_1_BYTE << TRANSFER_SETTINGS_SIZE_BITS) |               \
121                                                  (TRANSFER_ADDR_MODE_INCREMENTED << TRANSFER_SETTINGS_SRC_ADDR_BITS) | \
122                                                  (TRANSFER_IRQ_END << TRANSFER_SETTINGS_IRQ_BITS) |                    \
123                                                  (TRANSFER_ADDR_MODE_FIXED << TRANSFER_SETTINGS_DEST_ADDR_BITS))
124 #ifndef SCI_UART_FLOW_CONTROL_ACTIVE
125  #define SCI_UART_FLOW_CONTROL_ACTIVE           BSP_IO_LEVEL_HIGH
126 #endif
127 
128 #ifndef SCI_UART_FLOW_CONTROL_INACTIVE
129  #define SCI_UART_FLOW_CONTROL_INACTIVE         BSP_IO_LEVEL_LOW
130 #endif
131 
132 /***********************************************************************************************************************
133  * Private constants
134  **********************************************************************************************************************/
135 static const int32_t SCI_UART_100_PERCENT_X_1000 = 100000;
136 static const int32_t SCI_UART_MDDR_DIVISOR       = 256;
137 
138 #if (SCI_UART_CFG_PARAM_CHECKING_ENABLE)
139 static const uint32_t SCI_UART_MAX_BAUD_RATE_ERROR_X_1000 = 15000;
140 #endif
141 
142 /***********************************************************************************************************************
143  * Typedef definitions
144  **********************************************************************************************************************/
145 typedef struct st_baud_setting_const_t
146 {
147     uint8_t bgdm  : 1;                 /**< BGDM value to get divisor */
148     uint8_t abcs  : 1;                 /**< ABCS value to get divisor */
149     uint8_t abcse : 1;                 /**< ABCSE value to get divisor */
150     uint8_t cks   : 2;                 /**< CKS  value to get divisor (CKS = N) */
151 } baud_setting_const_t;
152 
153 /* Noise filter setting definition */
154 typedef enum e_noise_cancel_lvl
155 {
156     NOISE_CANCEL_LVL1,                 /**< Noise filter level 1(weak) */
157     NOISE_CANCEL_LVL2,                 /**< Noise filter level 2 */
158     NOISE_CANCEL_LVL3,                 /**< Noise filter level 3 */
159     NOISE_CANCEL_LVL4                  /**< Noise filter level 4(strong) */
160 } noise_cancel_lvl_t;
161 
162 #if defined(__ARMCC_VERSION) || defined(__ICCARM__)
163 typedef void (BSP_CMSE_NONSECURE_CALL * sci_uart_prv_ns_callback)(uart_callback_args_t * p_args);
164 #elif defined(__GNUC__)
165 typedef BSP_CMSE_NONSECURE_CALL void (*volatile sci_uart_prv_ns_callback)(uart_callback_args_t * p_args);
166 #endif
167 
168 /***********************************************************************************************************************
169  * Private function prototypes
170  **********************************************************************************************************************/
171 
172 static void r_sci_negate_de_pin(sci_uart_instance_ctrl_t const * const p_ctrl);
173 
174 #if (SCI_UART_CFG_PARAM_CHECKING_ENABLE)
175 
176 static fsp_err_t r_sci_read_write_param_check(sci_uart_instance_ctrl_t const * const p_ctrl,
177                                               uint8_t const * const                  addr,
178                                               uint32_t const                         bytes);
179 
180 #endif
181 
182 static void r_sci_uart_config_set(sci_uart_instance_ctrl_t * const p_ctrl, uart_cfg_t const * const p_cfg);
183 
184 #if SCI_UART_CFG_DTC_SUPPORTED
185 static fsp_err_t r_sci_uart_transfer_configure(sci_uart_instance_ctrl_t * const p_ctrl,
186                                                transfer_instance_t const      * p_transfer,
187                                                uint32_t                       * p_transfer_reg,
188                                                uint32_t                         address);
189 
190 static fsp_err_t r_sci_uart_transfer_open(sci_uart_instance_ctrl_t * const p_ctrl, uart_cfg_t const * const p_cfg);
191 
192 static void r_sci_uart_transfer_close(sci_uart_instance_ctrl_t * p_ctrl);
193 
194 #endif
195 
196 static void r_sci_uart_baud_set(R_SCI0_Type * p_sci_reg, baud_setting_t const * const p_baud_setting);
197 static void r_sci_uart_call_callback(sci_uart_instance_ctrl_t * p_ctrl, uint32_t data, uart_event_t event);
198 
199 #if SCI_UART_CFG_FIFO_SUPPORT
200 static void r_sci_uart_fifo_cfg(sci_uart_instance_ctrl_t * const p_ctrl);
201 
202 #endif
203 
204 static void r_sci_irq_cfg(sci_uart_instance_ctrl_t * const p_ctrl, uint8_t const ipl, IRQn_Type const p_irq);
205 
206 static void r_sci_irqs_cfg(sci_uart_instance_ctrl_t * const p_ctrl, uart_cfg_t const * const p_cfg);
207 
208 #if (SCI_UART_CFG_TX_ENABLE)
209 void r_sci_uart_write_no_transfer(sci_uart_instance_ctrl_t * const p_ctrl);
210 
211 #endif
212 
213 #if (SCI_UART_CFG_RX_ENABLE)
214 void r_sci_uart_rxi_read_no_transfer(sci_uart_instance_ctrl_t * const p_ctrl);
215 
216 void sci_uart_rxi_isr(void);
217 
218 void r_sci_uart_read_data(sci_uart_instance_ctrl_t * const p_ctrl, uint32_t * const p_data);
219 
220 void sci_uart_eri_isr(void);
221 
222 #endif
223 
224 #if (SCI_UART_CFG_TX_ENABLE)
225 void sci_uart_txi_isr(void);
226 void sci_uart_tei_isr(void);
227 
228 #endif
229 
230 /***********************************************************************************************************************
231  * Private global variables
232  **********************************************************************************************************************/
233 
234 /* Name of module used by error logger macro */
235 #if BSP_CFG_ERROR_LOG != 0
236 static const char g_module_name[] = "sci_uart";
237 #endif
238 
239 /* Baud rate divisor information (UART mode) */
240 static const baud_setting_const_t g_async_baud[SCI_UART_NUM_DIVISORS_ASYNC] =
241 {
242     {0U, 0U, 1U, 0U},                  /* BGDM, ABCS, ABCSE, n */
243     {1U, 1U, 0U, 0U},
244     {1U, 0U, 0U, 0U},
245     {0U, 0U, 1U, 1U},
246     {0U, 0U, 0U, 0U},
247     {1U, 0U, 0U, 1U},
248     {0U, 0U, 1U, 2U},
249     {0U, 0U, 0U, 1U},
250     {1U, 0U, 0U, 2U},
251     {0U, 0U, 1U, 3U},
252     {0U, 0U, 0U, 2U},
253     {1U, 0U, 0U, 3U},
254     {0U, 0U, 0U, 3U}
255 };
256 
257 static const uint16_t g_div_coefficient[SCI_UART_NUM_DIVISORS_ASYNC] =
258 {
259     6U,
260     8U,
261     16U,
262     24U,
263     32U,
264     64U,
265     96U,
266     128U,
267     256U,
268     384U,
269     512U,
270     1024U,
271     2048U,
272 };
273 
274 /* UART on SCI HAL API mapping for UART interface */
275 const uart_api_t g_uart_on_sci =
276 {
277     .open               = R_SCI_UART_Open,
278     .close              = R_SCI_UART_Close,
279     .write              = R_SCI_UART_Write,
280     .read               = R_SCI_UART_Read,
281     .infoGet            = R_SCI_UART_InfoGet,
282     .baudSet            = R_SCI_UART_BaudSet,
283     .communicationAbort = R_SCI_UART_Abort,
284     .callbackSet        = R_SCI_UART_CallbackSet,
285     .readStop           = R_SCI_UART_ReadStop,
286 };
287 
288 /*******************************************************************************************************************//**
289  * @addtogroup SCI_UART
290  * @{
291  **********************************************************************************************************************/
292 
293 /***********************************************************************************************************************
294  * Functions
295  **********************************************************************************************************************/
296 
297 /*******************************************************************************************************************//**
298  * Configures the UART driver based on the input configurations.  If reception is enabled at compile time, reception is
299  * enabled at the end of this function. Implements @ref uart_api_t::open
300  *
301  * @retval  FSP_SUCCESS                    Channel opened successfully.
302  * @retval  FSP_ERR_ASSERTION              Pointer to UART control block or configuration structure is NULL.
303  * @retval  FSP_ERR_IP_CHANNEL_NOT_PRESENT The requested channel does not exist on this MCU.
304  * @retval  FSP_ERR_INVALID_ARGUMENT       Flow control is enabled but flow control pin is not defined or selected channel
305  *                                         does not support "Hardware CTS and Hardware RTS" flow control.
306  * @retval  FSP_ERR_ALREADY_OPEN           Control block has already been opened or channel is being used by another
307  *                                         instance. Call close() then open() to reconfigure.
308  *
309  * @return                       See @ref RENESAS_ERROR_CODES or functions called by this function for other possible
310  *                               return codes. This function calls:
311  *                                   * @ref transfer_api_t::open
312  **********************************************************************************************************************/
R_SCI_UART_Open(uart_ctrl_t * const p_api_ctrl,uart_cfg_t const * const p_cfg)313 fsp_err_t R_SCI_UART_Open (uart_ctrl_t * const p_api_ctrl, uart_cfg_t const * const p_cfg)
314 {
315     sci_uart_instance_ctrl_t * p_ctrl = (sci_uart_instance_ctrl_t *) p_api_ctrl;
316 
317 #if (SCI_UART_CFG_PARAM_CHECKING_ENABLE)
318 
319     /* Check parameters. */
320     FSP_ASSERT(p_ctrl);
321     FSP_ASSERT(p_cfg);
322 
323     FSP_ASSERT(p_cfg->p_extend);
324     FSP_ASSERT(((sci_uart_extended_cfg_t *) p_cfg->p_extend)->p_baud_setting);
325     FSP_ERROR_RETURN(SCI_UART_OPEN != p_ctrl->open, FSP_ERR_ALREADY_OPEN);
326 
327     /* Make sure this channel exists. */
328     FSP_ERROR_RETURN(BSP_FEATURE_SCI_CHANNELS & (1U << p_cfg->channel), FSP_ERR_IP_CHANNEL_NOT_PRESENT);
329 
330     if (((sci_uart_extended_cfg_t *) p_cfg->p_extend)->flow_control == SCI_UART_FLOW_CONTROL_CTSRTS)
331     {
332         FSP_ERROR_RETURN(
333             ((sci_uart_extended_cfg_t *) p_cfg->p_extend)->flow_control_pin != SCI_UART_INVALID_16BIT_PARAM,
334             FSP_ERR_INVALID_ARGUMENT);
335     }
336 
337     if (((sci_uart_extended_cfg_t *) p_cfg->p_extend)->flow_control == SCI_UART_FLOW_CONTROL_HARDWARE_CTSRTS)
338     {
339         FSP_ERROR_RETURN((0U != (((1U << (p_cfg->channel)) & BSP_FEATURE_SCI_UART_CSTPEN_CHANNELS))),
340                          FSP_ERR_INVALID_ARGUMENT);
341     }
342 
343  #if (SCI_UART_CFG_RS485_SUPPORT)
344     if (((sci_uart_extended_cfg_t *) p_cfg->p_extend)->rs485_setting.enable == SCI_UART_RS485_ENABLE)
345     {
346         FSP_ERROR_RETURN(
347             ((sci_uart_extended_cfg_t *) p_cfg->p_extend)->rs485_setting.de_control_pin != SCI_UART_INVALID_16BIT_PARAM,
348             FSP_ERR_INVALID_ARGUMENT);
349     }
350  #endif
351 
352     FSP_ASSERT(p_cfg->rxi_irq >= 0);
353     FSP_ASSERT(p_cfg->txi_irq >= 0);
354     FSP_ASSERT(p_cfg->tei_irq >= 0);
355     FSP_ASSERT(p_cfg->eri_irq >= 0);
356 #endif
357 
358     p_ctrl->p_reg = ((R_SCI0_Type *) (R_SCI0_BASE + (SCI_REG_SIZE * p_cfg->channel)));
359 
360     p_ctrl->fifo_depth = 0U;
361 #if SCI_UART_CFG_FIFO_SUPPORT
362 
363     /* Check if the channel supports fifo */
364     if (BSP_FEATURE_SCI_UART_FIFO_CHANNELS & (1U << p_cfg->channel))
365     {
366         p_ctrl->fifo_depth = BSP_FEATURE_SCI_UART_FIFO_DEPTH;
367     }
368 #endif
369 
370     p_ctrl->p_cfg = p_cfg;
371 
372     p_ctrl->p_callback        = p_cfg->p_callback;
373     p_ctrl->p_context         = p_cfg->p_context;
374     p_ctrl->p_callback_memory = NULL;
375 
376     p_ctrl->data_bytes = 1U;
377     if (UART_DATA_BITS_9 == p_cfg->data_bits)
378     {
379         p_ctrl->data_bytes = 2U;
380     }
381 
382     /* Configure the interrupts. */
383     r_sci_irqs_cfg(p_ctrl, p_cfg);
384 
385 #if SCI_UART_CFG_DTC_SUPPORTED
386 
387     /* Configure the transfer interface for transmission and reception if provided. */
388     fsp_err_t err = r_sci_uart_transfer_open(p_ctrl, p_cfg);
389 
390     FSP_ERROR_RETURN(FSP_SUCCESS == err, err);
391 #endif
392 
393     /* Negate driver enable if RS-485 mode is enabled. */
394     r_sci_negate_de_pin(p_ctrl);
395 
396     /* Enable the SCI channel and reset the registers to their initial state. */
397     R_BSP_MODULE_START(FSP_IP_SCI, p_cfg->channel);
398 
399     /* Initialize registers as defined in section 34.3.7 "SCI Initialization in Asynchronous Mode" in the RA6M3 manual
400      * R01UH0886EJ0100 or the relevant section for the MCU being used. */
401     p_ctrl->p_reg->SCR   = 0U;
402     p_ctrl->p_reg->SSR   = 0U;
403     p_ctrl->p_reg->SIMR1 = 0U;
404     p_ctrl->p_reg->SIMR2 = 0U;
405     p_ctrl->p_reg->SIMR3 = 0U;
406     p_ctrl->p_reg->CDR   = 0U;
407 
408     /* Check if the channel supports address matching */
409     if (BSP_FEATURE_SCI_ADDRESS_MATCH_CHANNELS & (1U << p_cfg->channel))
410     {
411         p_ctrl->p_reg->DCCR = SCI_UART_DCCR_DEFAULT_VALUE;
412     }
413 
414     /* Set the default level of the TX pin to 1. */
415     p_ctrl->p_reg->SPTR = (uint8_t) (1U << SPTR_SPB2D_BIT) | SPTR_OUTPUT_ENABLE_MASK;
416 
417     /* Set the UART configuration settings provided in ::uart_cfg_t and ::sci_uart_extended_cfg_t. */
418     r_sci_uart_config_set(p_ctrl, p_cfg);
419 
420     p_ctrl->p_tx_src      = NULL;
421     p_ctrl->tx_src_bytes  = 0U;
422     p_ctrl->p_rx_dest     = NULL;
423     p_ctrl->rx_dest_bytes = 0;
424 
425     sci_uart_extended_cfg_t * p_extend = (sci_uart_extended_cfg_t *) p_cfg->p_extend;
426 
427     uint32_t scr = ((uint8_t) p_extend->clock) & 0x3U;
428 #if (SCI_UART_CFG_RX_ENABLE)
429 
430     /* If reception is enabled at build time, enable reception. */
431     /* NOTE: Transmitter and its interrupt are enabled in R_SCI_UART_Write(). */
432     scr |= SCI_SCR_RE_MASK;
433     R_BSP_IrqEnable(p_ctrl->p_cfg->rxi_irq);
434     R_BSP_IrqEnable(p_ctrl->p_cfg->eri_irq);
435 
436     scr |= SCI_SCR_RIE_MASK;
437 #endif
438 
439 #if (SCI_UART_CFG_TX_ENABLE)
440     R_BSP_IrqEnable(p_ctrl->p_cfg->txi_irq);
441     R_BSP_IrqEnable(p_ctrl->p_cfg->tei_irq);
442     scr |= SCI_SCR_TE_MASK;
443 #endif
444     p_ctrl->p_reg->SCR = (uint8_t) scr;
445 
446     p_ctrl->flow_pin = p_extend->flow_control_pin;
447 
448 #if SCI_UART_CFG_FLOW_CONTROL_SUPPORT
449     if (p_ctrl->flow_pin != SCI_UART_INVALID_16BIT_PARAM)
450     {
451         R_BSP_PinAccessEnable();
452         R_BSP_PinWrite(p_ctrl->flow_pin, SCI_UART_FLOW_CONTROL_INACTIVE);
453         R_BSP_PinAccessDisable();
454     }
455 #endif
456 
457     p_ctrl->open = SCI_UART_OPEN;
458 
459     return FSP_SUCCESS;
460 }
461 
462 /*******************************************************************************************************************//**
463  * Aborts any in progress transfers. Disables interrupts, receiver, and transmitter.  Closes lower level transfer
464  * drivers if used. Removes power. Implements @ref uart_api_t::close
465  *
466  * @retval  FSP_SUCCESS              Channel successfully closed.
467  * @retval  FSP_ERR_ASSERTION        Pointer to UART control block is NULL.
468  * @retval  FSP_ERR_NOT_OPEN         The control block has not been opened
469  **********************************************************************************************************************/
R_SCI_UART_Close(uart_ctrl_t * const p_api_ctrl)470 fsp_err_t R_SCI_UART_Close (uart_ctrl_t * const p_api_ctrl)
471 {
472     sci_uart_instance_ctrl_t * p_ctrl = (sci_uart_instance_ctrl_t *) p_api_ctrl;
473 #if (SCI_UART_CFG_PARAM_CHECKING_ENABLE)
474     FSP_ASSERT(p_ctrl);
475     FSP_ERROR_RETURN(SCI_UART_OPEN == p_ctrl->open, FSP_ERR_NOT_OPEN);
476 #endif
477 
478     /* Mark the channel not open so other APIs cannot use it. */
479     p_ctrl->open = 0U;
480 
481     /* Disable interrupts, receiver, and transmitter. Disable baud clock output.*/
482     p_ctrl->p_reg->SCR = 0U;
483 
484 #if (SCI_UART_CFG_RX_ENABLE)
485 
486     /* If reception is enabled at build time, disable reception irqs. */
487     R_BSP_IrqDisable(p_ctrl->p_cfg->rxi_irq);
488     R_BSP_IrqDisable(p_ctrl->p_cfg->eri_irq);
489 #endif
490 #if (SCI_UART_CFG_TX_ENABLE)
491 
492     /* If transmission is enabled at build time, disable transmission irqs. */
493     R_BSP_IrqDisable(p_ctrl->p_cfg->txi_irq);
494     R_BSP_IrqDisable(p_ctrl->p_cfg->tei_irq);
495 #endif
496 
497 #if SCI_UART_CFG_DTC_SUPPORTED
498 
499     /* Close the lower level transfer instances. */
500     r_sci_uart_transfer_close(p_ctrl);
501 #endif
502 
503     /* Remove power to the channel. */
504     R_BSP_MODULE_STOP(FSP_IP_SCI, p_ctrl->p_cfg->channel);
505 
506     /* Negate driver enable if RS-485 mode is enabled. */
507     r_sci_negate_de_pin(p_ctrl);
508 
509     return FSP_SUCCESS;
510 }
511 
512 /*******************************************************************************************************************//**
513  * Receives user specified number of bytes into destination buffer pointer. Implements @ref uart_api_t::read
514  *
515  * @retval  FSP_SUCCESS                  Data reception successfully ends.
516  * @retval  FSP_ERR_ASSERTION            Pointer to UART control block is NULL.
517  *                                       Number of transfers outside the max or min boundary when transfer instance used
518  * @retval  FSP_ERR_INVALID_ARGUMENT     Destination address or data size is not valid for 9-bit mode.
519  * @retval  FSP_ERR_NOT_OPEN             The control block has not been opened
520  * @retval  FSP_ERR_IN_USE               A previous read operation is still in progress.
521  * @retval  FSP_ERR_UNSUPPORTED          SCI_UART_CFG_RX_ENABLE is set to 0
522  *
523  * @return                       See @ref RENESAS_ERROR_CODES or functions called by this function for other possible
524  *                               return codes. This function calls:
525  *                                   * @ref transfer_api_t::reset
526  *
527  * @note If 9-bit data length is specified at R_SCI_UART_Open call, p_dest must be aligned 16-bit boundary.
528  **********************************************************************************************************************/
R_SCI_UART_Read(uart_ctrl_t * const p_api_ctrl,uint8_t * const p_dest,uint32_t const bytes)529 fsp_err_t R_SCI_UART_Read (uart_ctrl_t * const p_api_ctrl, uint8_t * const p_dest, uint32_t const bytes)
530 {
531 #if (SCI_UART_CFG_RX_ENABLE)
532     sci_uart_instance_ctrl_t * p_ctrl = (sci_uart_instance_ctrl_t *) p_api_ctrl;
533     fsp_err_t err = FSP_SUCCESS;
534 
535  #if (SCI_UART_CFG_PARAM_CHECKING_ENABLE)
536     err = r_sci_read_write_param_check(p_ctrl, p_dest, bytes);
537     FSP_ERROR_RETURN(FSP_SUCCESS == err, err);
538     FSP_ERROR_RETURN(0U == p_ctrl->rx_dest_bytes, FSP_ERR_IN_USE);
539  #endif
540 
541  #if SCI_UART_CFG_DTC_SUPPORTED
542 
543     /* Configure transfer instance to receive the requested number of bytes if transfer is used for reception. */
544     if (NULL != p_ctrl->p_cfg->p_transfer_rx)
545     {
546         uint32_t size = bytes >> (p_ctrl->data_bytes - 1);
547   #if (SCI_UART_CFG_PARAM_CHECKING_ENABLE)
548 
549         /* Check that the number of transfers is within the 16-bit limit. */
550         FSP_ASSERT(size <= SCI_UART_DTC_MAX_TRANSFER);
551   #endif
552         err =
553             p_ctrl->p_cfg->p_transfer_rx->p_api->reset(p_ctrl->p_cfg->p_transfer_rx->p_ctrl, NULL, (void *) p_dest,
554                                                        (uint16_t) size);
555         FSP_ERROR_RETURN(FSP_SUCCESS == err, err);
556     }
557  #endif
558 
559     /* Save the destination address and size for use in rxi_isr. */
560     p_ctrl->p_rx_dest     = p_dest;
561     p_ctrl->rx_dest_bytes = bytes;
562 
563     return err;
564 #else
565     FSP_PARAMETER_NOT_USED(p_api_ctrl);
566     FSP_PARAMETER_NOT_USED(p_dest);
567     FSP_PARAMETER_NOT_USED(bytes);
568 
569     return FSP_ERR_UNSUPPORTED;
570 #endif
571 }
572 
573 /*******************************************************************************************************************//**
574  * Transmits user specified number of bytes from the source buffer pointer. Implements @ref uart_api_t::write
575  *
576  * @retval  FSP_SUCCESS                  Data transmission finished successfully.
577  * @retval  FSP_ERR_ASSERTION            Pointer to UART control block is NULL.
578  *                                       Number of transfers outside the max or min boundary when transfer instance used
579  * @retval  FSP_ERR_INVALID_ARGUMENT     Source address or data size is not valid for 9-bit mode.
580  * @retval  FSP_ERR_NOT_OPEN             The control block has not been opened
581  * @retval  FSP_ERR_IN_USE               A UART transmission is in progress
582  * @retval  FSP_ERR_UNSUPPORTED          SCI_UART_CFG_TX_ENABLE is set to 0
583  *
584  * @return                       See @ref RENESAS_ERROR_CODES or functions called by this function for other possible
585  *                               return codes. This function calls:
586  *                                   * @ref transfer_api_t::reset
587  *
588  * @note If 9-bit data length is specified at R_SCI_UART_Open call, p_src must be aligned on a 16-bit boundary.
589  **********************************************************************************************************************/
R_SCI_UART_Write(uart_ctrl_t * const p_api_ctrl,uint8_t const * const p_src,uint32_t const bytes)590 fsp_err_t R_SCI_UART_Write (uart_ctrl_t * const p_api_ctrl, uint8_t const * const p_src, uint32_t const bytes)
591 {
592 #if (SCI_UART_CFG_TX_ENABLE)
593     sci_uart_instance_ctrl_t * p_ctrl = (sci_uart_instance_ctrl_t *) p_api_ctrl;
594  #if SCI_UART_CFG_PARAM_CHECKING_ENABLE || SCI_UART_CFG_DTC_SUPPORTED
595     fsp_err_t err = FSP_SUCCESS;
596  #endif
597 
598  #if (SCI_UART_CFG_PARAM_CHECKING_ENABLE)
599     err = r_sci_read_write_param_check(p_ctrl, p_src, bytes);
600     FSP_ERROR_RETURN(FSP_SUCCESS == err, err);
601     FSP_ERROR_RETURN(0U == p_ctrl->tx_src_bytes, FSP_ERR_IN_USE);
602  #endif
603 
604  #if (SCI_UART_CFG_RS485_SUPPORT)
605     sci_uart_extended_cfg_t * p_extend = (sci_uart_extended_cfg_t *) p_ctrl->p_cfg->p_extend;
606 
607     /* If RS-485 is enabled, then assert the driver enable pin at the start of a write transfer. */
608     if (p_extend->rs485_setting.enable)
609     {
610         R_BSP_PinAccessEnable();
611 
612         bsp_io_level_t level = SCI_UART_RS485_DE_POLARITY_HIGH ==
613                                p_extend->rs485_setting.polarity ? BSP_IO_LEVEL_HIGH : BSP_IO_LEVEL_LOW;
614         R_BSP_PinWrite(p_extend->rs485_setting.de_control_pin, level);
615 
616         R_BSP_PinAccessDisable();
617     }
618  #endif
619 
620     /* Transmit interrupts must be disabled to start with. */
621     p_ctrl->p_reg->SCR &= (uint8_t) ~(SCI_SCR_TIE_MASK | SCI_SCR_TEIE_MASK);
622 
623     /* If the fifo is not used the first write will be done from this function. Subsequent writes will be done
624      * from txi_isr. */
625  #if SCI_UART_CFG_FIFO_SUPPORT
626     if (p_ctrl->fifo_depth > 0U)
627     {
628         p_ctrl->tx_src_bytes = bytes;
629         p_ctrl->p_tx_src     = p_src;
630     }
631     else
632  #endif
633     {
634         p_ctrl->tx_src_bytes = bytes - p_ctrl->data_bytes;
635         p_ctrl->p_tx_src     = p_src + p_ctrl->data_bytes;
636     }
637 
638  #if SCI_UART_CFG_DTC_SUPPORTED
639 
640     /* If a transfer instance is used for transmission, reset the transfer instance to transmit the requested
641      * data. */
642     if ((NULL != p_ctrl->p_cfg->p_transfer_tx) && p_ctrl->tx_src_bytes)
643     {
644         uint32_t data_bytes    = p_ctrl->data_bytes;
645         uint32_t num_transfers = p_ctrl->tx_src_bytes >> (data_bytes - 1);
646         p_ctrl->tx_src_bytes = 0U;
647   #if (SCI_UART_CFG_PARAM_CHECKING_ENABLE)
648 
649         /* Check that the number of transfers is within the 16-bit limit. */
650         FSP_ASSERT(num_transfers <= SCI_UART_DTC_MAX_TRANSFER);
651   #endif
652 
653         err = p_ctrl->p_cfg->p_transfer_tx->p_api->reset(p_ctrl->p_cfg->p_transfer_tx->p_ctrl,
654                                                          (void const *) p_ctrl->p_tx_src,
655                                                          NULL,
656                                                          (uint16_t) num_transfers);
657         FSP_ERROR_RETURN(FSP_SUCCESS == err, err);
658     }
659  #endif
660 
661     /* Trigger a TXI interrupt. This triggers the transfer instance or a TXI interrupt if the transfer instance is
662      * not used. */
663     p_ctrl->p_reg->SCR |= SCI_SCR_TIE_MASK;
664  #if SCI_UART_CFG_FIFO_SUPPORT
665     if (p_ctrl->fifo_depth == 0U)
666  #endif
667     {
668         /* On channels with no FIFO, the first byte is sent from this function to trigger the first TXI event.  This
669          * method is used instead of setting TE and TIE at the same time as recommended in the hardware manual to avoid
670          * the one frame delay that occurs when the TE bit is set. */
671         if (2U == p_ctrl->data_bytes)
672         {
673             p_ctrl->p_reg->FTDRHL = *((uint16_t *) (p_src)) | (uint16_t) ~(SCI_UART_FIFO_DAT_MASK);
674         }
675         else
676         {
677             p_ctrl->p_reg->TDR = *(p_src);
678         }
679     }
680 
681     return FSP_SUCCESS;
682 #else
683     FSP_PARAMETER_NOT_USED(p_api_ctrl);
684     FSP_PARAMETER_NOT_USED(p_src);
685     FSP_PARAMETER_NOT_USED(bytes);
686 
687     return FSP_ERR_UNSUPPORTED;
688 #endif
689 }
690 
691 /*******************************************************************************************************************//**
692  * Updates the user callback and has option of providing memory for callback structure.
693  * Implements uart_api_t::callbackSet
694  *
695  * @retval  FSP_SUCCESS                  Callback updated successfully.
696  * @retval  FSP_ERR_ASSERTION            A required pointer is NULL.
697  * @retval  FSP_ERR_NOT_OPEN             The control block has not been opened.
698  * @retval  FSP_ERR_NO_CALLBACK_MEMORY   p_callback is non-secure and p_callback_memory is either secure or NULL.
699  **********************************************************************************************************************/
R_SCI_UART_CallbackSet(uart_ctrl_t * const p_api_ctrl,void (* p_callback)(uart_callback_args_t *),void const * const p_context,uart_callback_args_t * const p_callback_memory)700 fsp_err_t R_SCI_UART_CallbackSet (uart_ctrl_t * const          p_api_ctrl,
701                                   void (                     * p_callback)(uart_callback_args_t *),
702                                   void const * const           p_context,
703                                   uart_callback_args_t * const p_callback_memory)
704 {
705     sci_uart_instance_ctrl_t * p_ctrl = (sci_uart_instance_ctrl_t *) p_api_ctrl;
706 
707 #if (SCI_UART_CFG_PARAM_CHECKING_ENABLE)
708     FSP_ASSERT(p_ctrl);
709     FSP_ASSERT(p_callback);
710     FSP_ERROR_RETURN(SCI_UART_OPEN == p_ctrl->open, FSP_ERR_NOT_OPEN);
711 #endif
712 
713 #if BSP_TZ_SECURE_BUILD
714 
715     /* Get security state of p_callback */
716     bool callback_is_secure =
717         (NULL == cmse_check_address_range((void *) p_callback, sizeof(void *), CMSE_AU_NONSECURE));
718 
719  #if SCI_UART_CFG_PARAM_CHECKING_ENABLE
720 
721     /* In secure projects, p_callback_memory must be provided in non-secure space if p_callback is non-secure */
722     uart_callback_args_t * const p_callback_memory_checked = cmse_check_pointed_object(p_callback_memory,
723                                                                                        CMSE_AU_NONSECURE);
724     FSP_ERROR_RETURN(callback_is_secure || (NULL != p_callback_memory_checked), FSP_ERR_NO_CALLBACK_MEMORY);
725  #endif
726 #endif
727 
728     /* Store callback and context */
729 #if BSP_TZ_SECURE_BUILD
730     p_ctrl->p_callback = callback_is_secure ? p_callback :
731                          (void (*)(uart_callback_args_t *))cmse_nsfptr_create(p_callback);
732 #else
733     p_ctrl->p_callback = p_callback;
734 #endif
735     p_ctrl->p_context         = p_context;
736     p_ctrl->p_callback_memory = p_callback_memory;
737 
738     return FSP_SUCCESS;
739 }
740 
741 /*******************************************************************************************************************//**
742  * Updates the baud rate using the clock selected in Open. p_baud_setting is a pointer to a baud_setting_t structure.
743  * Implements @ref uart_api_t::baudSet
744  *
745  * @warning This terminates any in-progress transmission.
746  *
747  * @retval  FSP_SUCCESS                  Baud rate was successfully changed.
748  * @retval  FSP_ERR_ASSERTION            Pointer to UART control block is NULL or the UART is not configured to use the
749  *                                       internal clock.
750  * @retval  FSP_ERR_NOT_OPEN             The control block has not been opened
751  **********************************************************************************************************************/
R_SCI_UART_BaudSet(uart_ctrl_t * const p_api_ctrl,void const * const p_baud_setting)752 fsp_err_t R_SCI_UART_BaudSet (uart_ctrl_t * const p_api_ctrl, void const * const p_baud_setting)
753 {
754     sci_uart_instance_ctrl_t * p_ctrl = (sci_uart_instance_ctrl_t *) p_api_ctrl;
755 
756 #if (SCI_UART_CFG_PARAM_CHECKING_ENABLE)
757     FSP_ASSERT(p_ctrl);
758     FSP_ERROR_RETURN(SCI_UART_OPEN == p_ctrl->open, FSP_ERR_NOT_OPEN);
759 
760     /* Verify that the On-Chip baud rate generator is currently selected. */
761     FSP_ASSERT((p_ctrl->p_reg->SCR_b.CKE & 0x2) == 0U);
762 #endif
763 
764     /* Save SCR configurations except transmit interrupts. Resuming transmission after reconfiguring baud settings is
765      * not supported. */
766     uint8_t preserved_scr = p_ctrl->p_reg->SCR & (uint8_t) ~(SCI_SCR_TIE_MASK | SCI_SCR_TEIE_MASK);
767 
768     /* Disables transmitter and receiver. This terminates any in-progress transmission. */
769     p_ctrl->p_reg->SCR = preserved_scr & (uint8_t) ~(SCI_SCR_TE_MASK | SCI_SCR_RE_MASK | SCI_SCR_RIE_MASK);
770     p_ctrl->p_tx_src   = NULL;
771 
772     /* Apply new baud rate register settings. */
773     r_sci_uart_baud_set(p_ctrl->p_reg, p_baud_setting);
774 
775     /* Restore all settings except transmit interrupts. */
776     p_ctrl->p_reg->SCR = preserved_scr;
777 
778     return FSP_SUCCESS;
779 }
780 
781 /*******************************************************************************************************************//**
782  * Provides the driver information, including the maximum number of bytes that can be received or transmitted at a time.
783  * Implements @ref uart_api_t::infoGet
784  *
785  * @retval  FSP_SUCCESS                  Information stored in provided p_info.
786  * @retval  FSP_ERR_ASSERTION            Pointer to UART control block is NULL.
787  * @retval  FSP_ERR_NOT_OPEN             The control block has not been opened
788  **********************************************************************************************************************/
R_SCI_UART_InfoGet(uart_ctrl_t * const p_api_ctrl,uart_info_t * const p_info)789 fsp_err_t R_SCI_UART_InfoGet (uart_ctrl_t * const p_api_ctrl, uart_info_t * const p_info)
790 {
791 #if SCI_UART_CFG_PARAM_CHECKING_ENABLE || SCI_UART_CFG_DTC_SUPPORTED
792     sci_uart_instance_ctrl_t * p_ctrl = (sci_uart_instance_ctrl_t *) p_api_ctrl;
793 #else
794     FSP_PARAMETER_NOT_USED(p_api_ctrl);
795 #endif
796 
797 #if (SCI_UART_CFG_PARAM_CHECKING_ENABLE)
798     FSP_ASSERT(p_ctrl);
799     FSP_ASSERT(p_info);
800     FSP_ERROR_RETURN(SCI_UART_OPEN == p_ctrl->open, FSP_ERR_NOT_OPEN);
801 #endif
802 
803     p_info->read_bytes_max  = SCI_UART_MAX_READ_WRITE_NO_DTC;
804     p_info->write_bytes_max = SCI_UART_MAX_READ_WRITE_NO_DTC;
805 
806 #if (SCI_UART_CFG_RX_ENABLE)
807 
808     /* Store number of bytes that can be read at a time. */
809  #if SCI_UART_CFG_DTC_SUPPORTED
810     if (NULL != p_ctrl->p_cfg->p_transfer_rx)
811     {
812         p_info->read_bytes_max = SCI_UART_DTC_MAX_TRANSFER;
813     }
814  #endif
815 #endif
816 
817 #if (SCI_UART_CFG_TX_ENABLE)
818 
819     /* Store number of bytes that can be written at a time. */
820  #if SCI_UART_CFG_DTC_SUPPORTED
821     if (NULL != p_ctrl->p_cfg->p_transfer_tx)
822     {
823         p_info->write_bytes_max = SCI_UART_DTC_MAX_TRANSFER;
824     }
825  #endif
826 #endif
827 
828     return FSP_SUCCESS;
829 }
830 
831 /*******************************************************************************************************************//**
832  * Provides API to abort ongoing transfer. Transmission is aborted after the current character is transmitted.
833  * Reception is still enabled after abort(). Any characters received after abort() and before the transfer
834  * is reset in the next call to read(), will arrive via the callback function with event UART_EVENT_RX_CHAR.
835  * Implements @ref uart_api_t::communicationAbort
836  *
837  * @retval  FSP_SUCCESS                  UART transaction aborted successfully.
838  * @retval  FSP_ERR_ASSERTION            Pointer to UART control block is NULL.
839  * @retval  FSP_ERR_NOT_OPEN             The control block has not been opened.
840  * @retval  FSP_ERR_UNSUPPORTED          The requested Abort direction is unsupported.
841  *
842  * @return                       See @ref RENESAS_ERROR_CODES or functions called by this function for other possible
843  *                               return codes. This function calls:
844  *                                   * @ref transfer_api_t::disable
845  **********************************************************************************************************************/
R_SCI_UART_Abort(uart_ctrl_t * const p_api_ctrl,uart_dir_t communication_to_abort)846 fsp_err_t R_SCI_UART_Abort (uart_ctrl_t * const p_api_ctrl, uart_dir_t communication_to_abort)
847 {
848     sci_uart_instance_ctrl_t * p_ctrl = (sci_uart_instance_ctrl_t *) p_api_ctrl;
849     fsp_err_t err = FSP_ERR_UNSUPPORTED;
850 
851 #if (SCI_UART_CFG_PARAM_CHECKING_ENABLE)
852     FSP_ASSERT(p_ctrl);
853     FSP_ERROR_RETURN(SCI_UART_OPEN == p_ctrl->open, FSP_ERR_NOT_OPEN);
854 #endif
855 
856 #if (SCI_UART_CFG_TX_ENABLE)
857     if (UART_DIR_TX & communication_to_abort)
858     {
859         err                 = FSP_SUCCESS;
860         p_ctrl->p_reg->SCR &= (uint8_t) ~(SCI_SCR_TIE_MASK | SCI_SCR_TEIE_MASK);
861  #if SCI_UART_CFG_DTC_SUPPORTED
862         if (NULL != p_ctrl->p_cfg->p_transfer_tx)
863         {
864             err = p_ctrl->p_cfg->p_transfer_tx->p_api->disable(p_ctrl->p_cfg->p_transfer_tx->p_ctrl);
865         }
866  #endif
867 
868  #if SCI_UART_CFG_FIFO_SUPPORT
869         if (0U != p_ctrl->fifo_depth)
870         {
871             /* Reset the transmit fifo */
872             p_ctrl->p_reg->FCR_b.TFRST = 1U;
873 
874             /* Wait until TFRST cleared after 1 PCLK according to section 34.2.26 "FIFO Control Register (FCR) in the
875              * RA6M3 manual R01UH0886EJ0100 or the relevant section for the MCU being used.*/
876             FSP_HARDWARE_REGISTER_WAIT(p_ctrl->p_reg->FCR_b.TFRST, 0U);
877         }
878  #endif
879         p_ctrl->tx_src_bytes = 0U;
880 
881         /* Negate driver enable if RS-485 mode is enabled. */
882         r_sci_negate_de_pin(p_ctrl);
883 
884         FSP_ERROR_RETURN(FSP_SUCCESS == err, err);
885     }
886 #endif
887 #if (SCI_UART_CFG_RX_ENABLE)
888     if (UART_DIR_RX & communication_to_abort)
889     {
890         err = FSP_SUCCESS;
891 
892         p_ctrl->rx_dest_bytes = 0U;
893  #if SCI_UART_CFG_DTC_SUPPORTED
894         if (NULL != p_ctrl->p_cfg->p_transfer_rx)
895         {
896             err = p_ctrl->p_cfg->p_transfer_rx->p_api->disable(p_ctrl->p_cfg->p_transfer_rx->p_ctrl);
897         }
898  #endif
899  #if SCI_UART_CFG_FIFO_SUPPORT
900         if (0U != p_ctrl->fifo_depth)
901         {
902             /* Reset the receive fifo */
903             p_ctrl->p_reg->FCR_b.RFRST = 1U;
904 
905             /* Wait until RFRST cleared after 1 PCLK according to section 34.2.26 "FIFO Control Register (FCR) in the
906              * RA6M3 manual R01UH0886EJ0100 or the relevant section for the MCU being used.*/
907             FSP_HARDWARE_REGISTER_WAIT(p_ctrl->p_reg->FCR_b.RFRST, 0U);
908         }
909  #endif
910     }
911 #endif
912 
913     return err;
914 }
915 
916 /*******************************************************************************************************************//**
917  * Provides API to abort ongoing read. Reception is still enabled after abort(). Any characters received after abort()
918  * and before the transfer is reset in the next call to read(), will arrive via the callback function with event
919  * UART_EVENT_RX_CHAR.
920  * Implements @ref uart_api_t::readStop
921  *
922  * @retval  FSP_SUCCESS                  UART transaction aborted successfully.
923  * @retval  FSP_ERR_ASSERTION            Pointer to UART control block is NULL.
924  * @retval  FSP_ERR_NOT_OPEN             The control block has not been opened.
925  * @retval  FSP_ERR_UNSUPPORTED          The requested Abort direction is unsupported.
926  *
927  * @return                       See @ref RENESAS_ERROR_CODES or functions called by this function for other possible
928  *                               return codes. This function calls:
929  *                                   * @ref transfer_api_t::disable
930  **********************************************************************************************************************/
R_SCI_UART_ReadStop(uart_ctrl_t * const p_api_ctrl,uint32_t * remaining_bytes)931 fsp_err_t R_SCI_UART_ReadStop (uart_ctrl_t * const p_api_ctrl, uint32_t * remaining_bytes)
932 {
933     sci_uart_instance_ctrl_t * p_ctrl = (sci_uart_instance_ctrl_t *) p_api_ctrl;
934 
935 #if (SCI_UART_CFG_PARAM_CHECKING_ENABLE)
936     FSP_ASSERT(p_ctrl);
937     FSP_ERROR_RETURN(SCI_UART_OPEN == p_ctrl->open, FSP_ERR_NOT_OPEN);
938 #endif
939 
940 #if (SCI_UART_CFG_RX_ENABLE)
941     *remaining_bytes      = p_ctrl->rx_dest_bytes;
942     p_ctrl->rx_dest_bytes = 0U;
943  #if SCI_UART_CFG_DTC_SUPPORTED
944     if (NULL != p_ctrl->p_cfg->p_transfer_rx)
945     {
946         fsp_err_t err = p_ctrl->p_cfg->p_transfer_rx->p_api->disable(p_ctrl->p_cfg->p_transfer_rx->p_ctrl);
947         FSP_ERROR_RETURN(FSP_SUCCESS == err, err);
948 
949         transfer_properties_t transfer_info;
950         err = p_ctrl->p_cfg->p_transfer_rx->p_api->infoGet(p_ctrl->p_cfg->p_transfer_rx->p_ctrl, &transfer_info);
951         FSP_ERROR_RETURN(FSP_SUCCESS == err, err);
952         *remaining_bytes = transfer_info.transfer_length_remaining;
953     }
954  #endif
955 #else
956 
957     return FSP_ERR_UNSUPPORTED;
958 #endif
959 
960     return FSP_SUCCESS;
961 }
962 
963 /*******************************************************************************************************************//**
964  * Calculates baud rate register settings. Evaluates and determines the best possible settings set to the baud rate
965  * related registers.
966  *
967  * @param[in]  baudrate                  Baud rate [bps]. For example, 19200, 57600, 115200, etc.
968  * @param[in]  bitrate_modulation        Enable bitrate modulation
969  * @param[in]  baud_rate_error_x_1000    Max baud rate error. At most &lt;baud_rate_percent_error&gt; x 1000 required
970  *                                       for module to function. Absolute max baud_rate_error is 15000 (15%).
971  * @param[out] p_baud_setting            Baud setting information stored here if successful
972  *
973  * @retval     FSP_SUCCESS               Baud rate is set successfully
974  * @retval     FSP_ERR_ASSERTION         Null pointer
975  * @retval     FSP_ERR_INVALID_ARGUMENT  Baud rate is '0', error in calculated baud rate is larger than requested
976  *                                       max error, or requested max error in baud rate is larger than 15%.
977  **********************************************************************************************************************/
R_SCI_UART_BaudCalculate(uint32_t baudrate,bool bitrate_modulation,uint32_t baud_rate_error_x_1000,baud_setting_t * const p_baud_setting)978 fsp_err_t R_SCI_UART_BaudCalculate (uint32_t               baudrate,
979                                     bool                   bitrate_modulation,
980                                     uint32_t               baud_rate_error_x_1000,
981                                     baud_setting_t * const p_baud_setting)
982 {
983 #if (SCI_UART_CFG_PARAM_CHECKING_ENABLE)
984     FSP_ASSERT(p_baud_setting);
985     FSP_ERROR_RETURN(SCI_UART_MAX_BAUD_RATE_ERROR_X_1000 >= baud_rate_error_x_1000, FSP_ERR_INVALID_ARGUMENT);
986     FSP_ERROR_RETURN((0U != baudrate), FSP_ERR_INVALID_ARGUMENT);
987 #endif
988 
989     p_baud_setting->brr = SCI_UART_BRR_MAX;
990     p_baud_setting->semr_baudrate_bits_b.brme = 0U;
991     p_baud_setting->mddr = SCI_UART_MDDR_MIN;
992 
993     /* Find the best BRR (bit rate register) value.
994      *  In table g_async_baud, divisor values are stored for BGDM, ABCS, ABCSE and N values.  Each set of divisors
995      *  is tried, and the settings with the lowest bit rate error are stored. The formula to calculate BRR is as
996      *  follows and it must be 255 or less:
997      *  BRR = (PCLK / (div_coefficient * baud)) - 1
998      */
999     int32_t  hit_bit_err = SCI_UART_100_PERCENT_X_1000;
1000     uint32_t hit_mddr    = 0U;
1001     uint32_t divisor     = 0U;
1002 
1003     uint32_t freq_hz = R_FSP_SystemClockHzGet(BSP_FEATURE_SCI_CLOCK);
1004 
1005     for (uint32_t select_16_base_clk_cycles = 0U;
1006          select_16_base_clk_cycles <= 1U && (hit_bit_err > ((int32_t) baud_rate_error_x_1000));
1007          select_16_base_clk_cycles++)
1008     {
1009         for (uint32_t i = 0U; i < SCI_UART_NUM_DIVISORS_ASYNC; i++)
1010         {
1011             /* if select_16_base_clk_cycles == true:  Skip this calculation for divisors that are not acheivable with 16 base clk cycles per bit.
1012              *  if select_16_base_clk_cycles == false: Skip this calculation for divisors that are only acheivable without 16 base clk cycles per bit.
1013              */
1014             if (((uint8_t) select_16_base_clk_cycles) ^ (g_async_baud[i].abcs | g_async_baud[i].abcse))
1015             {
1016                 continue;
1017             }
1018 
1019             divisor = (uint32_t) g_div_coefficient[i] * baudrate;
1020             uint32_t temp_brr = freq_hz / divisor;
1021 
1022             if (temp_brr <= (SCI_UART_BRR_MAX + 1U))
1023             {
1024                 while (temp_brr > 0U)
1025                 {
1026                     temp_brr -= 1U;
1027 
1028                     /* Calculate the bit rate error. The formula is as follows:
1029                      *  bit rate error[%] = {(PCLK / (baud * div_coefficient * (BRR + 1)) - 1} x 100
1030                      *  calculates bit rate error[%] to three decimal places
1031                      */
1032                     int32_t err_divisor = (int32_t) (divisor * (temp_brr + 1U));
1033 
1034                     /* Promoting to 64 bits for calculation, but the final value can never be more than 32 bits, as
1035                      * described below, so this cast is safe.
1036                      *    1. (temp_brr + 1) can be off by an upper limit of 1 due to rounding from the calculation:
1037                      *       freq_hz / divisor, or:
1038                      *       freq_hz / divisor <= (temp_brr + 1) < (freq_hz / divisor) + 1
1039                      *    2. Solving for err_divisor:
1040                      *       freq_hz <= err_divisor < freq_hz + divisor
1041                      *    3. Solving for bit_err:
1042                      *       0 >= bit_err >= (freq_hz * 100000 / (freq_hz + divisor)) - 100000
1043                      *    4. freq_hz >= divisor (or temp_brr would be -1 and we would never enter this while loop), so:
1044                      *       0 >= bit_err >= 100000 / freq_hz - 100000
1045                      *    5. Larger frequencies yield larger bit errors (absolute value).  As the frequency grows,
1046                      *       the bit_err approaches -100000, so:
1047                      *       0 >= bit_err >= -100000
1048                      *    6. bit_err is between -100000 and 0.  This entire range fits in an int32_t type, so the cast
1049                      *       to (int32_t) is safe.
1050                      */
1051                     int32_t bit_err = (int32_t) (((((int64_t) freq_hz) * SCI_UART_100_PERCENT_X_1000) /
1052                                                   err_divisor) - SCI_UART_100_PERCENT_X_1000);
1053 
1054                     uint32_t mddr = 0U;
1055                     if (bitrate_modulation)
1056                     {
1057                         /* Calculate the MDDR (M) value if bit rate modulation is enabled,
1058                          * The formula to calculate MBBR (from the M and N relationship given in the hardware manual) is as follows
1059                          * and it must be between 128 and 256.
1060                          * MDDR = ((div_coefficient * baud * 256) * (BRR + 1)) / PCLK */
1061                         mddr = (uint32_t) err_divisor / (freq_hz / SCI_UART_MDDR_MAX);
1062 
1063                         /* The maximum value that could result from the calculation above is 256, which is a valid MDDR
1064                          * value, so only the lower bound is checked. */
1065                         if (mddr < SCI_UART_MDDR_MIN)
1066                         {
1067                             break;
1068                         }
1069 
1070                         /* Adjust bit rate error for bit rate modulation. The following formula is used:
1071                          *  bit rate error [%] = ((bit rate error [%, no modulation] + 100) * MDDR / 256) - 100
1072                          */
1073                         bit_err = (((bit_err + SCI_UART_100_PERCENT_X_1000) * (int32_t) mddr) /
1074                                    SCI_UART_MDDR_DIVISOR) - SCI_UART_100_PERCENT_X_1000;
1075                     }
1076 
1077                     /* Take the absolute value of the bit rate error. */
1078                     if (bit_err < 0)
1079                     {
1080                         bit_err = -bit_err;
1081                     }
1082 
1083                     /* If the absolute value of the bit rate error is less than the previous lowest absolute value of
1084                      *  bit rate error, then store these settings as the best value.
1085                      */
1086                     if (bit_err < hit_bit_err)
1087                     {
1088                         p_baud_setting->semr_baudrate_bits_b.bgdm  = g_async_baud[i].bgdm;
1089                         p_baud_setting->semr_baudrate_bits_b.abcs  = g_async_baud[i].abcs;
1090                         p_baud_setting->semr_baudrate_bits_b.abcse = g_async_baud[i].abcse;
1091                         p_baud_setting->cks = g_async_baud[i].cks;
1092                         p_baud_setting->brr = (uint8_t) temp_brr;
1093                         hit_bit_err         = bit_err;
1094                         hit_mddr            = mddr;
1095                     }
1096 
1097                     if (bitrate_modulation)
1098                     {
1099                         p_baud_setting->semr_baudrate_bits_b.brme = 1U;
1100                         p_baud_setting->mddr = (uint8_t) hit_mddr;
1101                     }
1102                     else
1103                     {
1104                         break;
1105                     }
1106                 }
1107             }
1108         }
1109     }
1110 
1111     /* Return an error if the percent error is larger than the maximum percent error allowed for this instance */
1112     FSP_ERROR_RETURN((hit_bit_err <= (int32_t) baud_rate_error_x_1000), FSP_ERR_INVALID_ARGUMENT);
1113 
1114     return FSP_SUCCESS;
1115 }
1116 
1117 /*******************************************************************************************************************//**
1118  * @} (end addtogroup SCI_UART)
1119  **********************************************************************************************************************/
1120 
1121 /***********************************************************************************************************************
1122  * Private Functions
1123  **********************************************************************************************************************/
1124 
1125 /*******************************************************************************************************************//**
1126  * Negate the DE pin if it is enabled.
1127  *
1128  * @param[in] p_ctrl Pointer to the control block for the channel.
1129  **********************************************************************************************************************/
r_sci_negate_de_pin(sci_uart_instance_ctrl_t const * const p_ctrl)1130 static void r_sci_negate_de_pin (sci_uart_instance_ctrl_t const * const p_ctrl)
1131 {
1132 #if (SCI_UART_CFG_RS485_SUPPORT)
1133     sci_uart_extended_cfg_t * p_extend = (sci_uart_extended_cfg_t *) p_ctrl->p_cfg->p_extend;
1134 
1135     /* If RS-485 is enabled, then negate the driver enable pin at the end of a write transfer. */
1136     if (p_extend->rs485_setting.enable)
1137     {
1138         R_BSP_PinAccessEnable();
1139 
1140         bsp_io_level_t level = SCI_UART_RS485_DE_POLARITY_HIGH ==
1141                                p_extend->rs485_setting.polarity ? BSP_IO_LEVEL_LOW : BSP_IO_LEVEL_HIGH;
1142         R_BSP_PinWrite(p_extend->rs485_setting.de_control_pin, level);
1143 
1144         R_BSP_PinAccessDisable();
1145     }
1146 
1147 #else
1148     FSP_PARAMETER_NOT_USED(p_ctrl);
1149 #endif
1150 }
1151 
1152 #if (SCI_UART_CFG_PARAM_CHECKING_ENABLE)
1153 
1154 /*******************************************************************************************************************//**
1155  * Parameter error check function for read/write.
1156  *
1157  * @param[in] p_ctrl Pointer to the control block for the channel
1158  * @param[in] addr   Pointer to the buffer
1159  * @param[in] bytes  Number of bytes to read or write
1160  *
1161  * @retval  FSP_SUCCESS              No parameter error found
1162  * @retval  FSP_ERR_NOT_OPEN         The control block has not been opened
1163  * @retval  FSP_ERR_ASSERTION        Pointer to UART control block or configuration structure is NULL
1164  * @retval  FSP_ERR_INVALID_ARGUMENT Address is not aligned to 2-byte boundary or size is the odd number when the data
1165  *                                   length is 9-bit
1166  **********************************************************************************************************************/
r_sci_read_write_param_check(sci_uart_instance_ctrl_t const * const p_ctrl,uint8_t const * const addr,uint32_t const bytes)1167 static fsp_err_t r_sci_read_write_param_check (sci_uart_instance_ctrl_t const * const p_ctrl,
1168                                                uint8_t const * const                  addr,
1169                                                uint32_t const                         bytes)
1170 {
1171     FSP_ASSERT(p_ctrl);
1172     FSP_ASSERT(addr);
1173     FSP_ASSERT(0U != bytes);
1174     FSP_ERROR_RETURN(SCI_UART_OPEN == p_ctrl->open, FSP_ERR_NOT_OPEN);
1175 
1176     if (2U == p_ctrl->data_bytes)
1177     {
1178         /* Do not allow odd buffer address if data length is 9 bits. */
1179         FSP_ERROR_RETURN((0U == ((uint32_t) addr & SCI_UART_ALIGN_2_BYTES)), FSP_ERR_INVALID_ARGUMENT);
1180 
1181         /* Do not allow odd number of data bytes if data length is 9 bits. */
1182         FSP_ERROR_RETURN(0U == (bytes % 2U), FSP_ERR_INVALID_ARGUMENT);
1183     }
1184 
1185     return FSP_SUCCESS;
1186 }
1187 
1188 #endif
1189 #if SCI_UART_CFG_DTC_SUPPORTED
1190 
1191 /*******************************************************************************************************************//**
1192  * Subroutine to apply common UART transfer settings.
1193  *
1194  * @param[in]  p_cfg              Pointer to UART specific configuration structure
1195  * @param[in]  p_transfer         Pointer to transfer instance to configure
1196  *
1197  * @retval     FSP_SUCCESS        UART transfer drivers successfully configured
1198  * @retval     FSP_ERR_ASSERTION  Invalid pointer
1199  **********************************************************************************************************************/
r_sci_uart_transfer_configure(sci_uart_instance_ctrl_t * const p_ctrl,transfer_instance_t const * p_transfer,uint32_t * p_transfer_reg,uint32_t sci_buffer_address)1200 static fsp_err_t r_sci_uart_transfer_configure (sci_uart_instance_ctrl_t * const p_ctrl,
1201                                                 transfer_instance_t const      * p_transfer,
1202                                                 uint32_t                       * p_transfer_reg,
1203                                                 uint32_t                         sci_buffer_address)
1204 {
1205     /* Configure the transfer instance, if enabled. */
1206  #if (SCI_UART_CFG_PARAM_CHECKING_ENABLE)
1207     FSP_ASSERT(NULL != p_transfer->p_api);
1208     FSP_ASSERT(NULL != p_transfer->p_ctrl);
1209     FSP_ASSERT(NULL != p_transfer->p_cfg);
1210     FSP_ASSERT(NULL != p_transfer->p_cfg->p_info);
1211     FSP_ASSERT(NULL != p_transfer->p_cfg->p_extend);
1212  #endif
1213     transfer_info_t * p_info = p_transfer->p_cfg->p_info;
1214 
1215     /* Casting for compatibility with 7 or 8 bit mode. */
1216     *p_transfer_reg = sci_buffer_address;
1217 
1218  #if SCI_UART_CFG_FIFO_SUPPORT
1219     if (p_ctrl->fifo_depth > 0U)
1220     {
1221         /* Casting for compatibility with 7 or 8 bit mode. */
1222         *p_transfer_reg = sci_buffer_address + SCI_UART_FIFO_TRANSFER_BUFFER_OFFSET;
1223     }
1224  #endif
1225 
1226     if (UART_DATA_BITS_9 == p_ctrl->p_cfg->data_bits)
1227     {
1228         p_info->transfer_settings_word_b.size = TRANSFER_SIZE_2_BYTE;
1229 
1230         /* Casting for compatibility with 7 or 8 bit mode. */
1231         *p_transfer_reg = sci_buffer_address + SCI_UART_9BIT_TRANSFER_BUFFER_OFFSET;
1232     }
1233 
1234     fsp_err_t err = p_transfer->p_api->open(p_transfer->p_ctrl, p_transfer->p_cfg);
1235     FSP_ERROR_RETURN(FSP_SUCCESS == err, err);
1236 
1237     return FSP_SUCCESS;
1238 }
1239 
1240 #endif
1241 
1242 #if SCI_UART_CFG_DTC_SUPPORTED
1243 
1244 /*******************************************************************************************************************//**
1245  * Configures UART related transfer drivers (if enabled).
1246  *
1247  * @param[in]     p_ctrl  Pointer to UART control structure
1248  * @param[in]     p_cfg   Pointer to UART specific configuration structure
1249  *
1250  * @retval        FSP_SUCCESS        UART transfer drivers successfully configured
1251  * @retval        FSP_ERR_ASSERTION  Invalid pointer or required interrupt not enabled in vector table
1252  *
1253  * @return                       See @ref RENESAS_ERROR_CODES or functions called by this function for other possible
1254  *                               return codes. This function calls:
1255  *                                   * @ref transfer_api_t::open
1256  **********************************************************************************************************************/
r_sci_uart_transfer_open(sci_uart_instance_ctrl_t * const p_ctrl,uart_cfg_t const * const p_cfg)1257 static fsp_err_t r_sci_uart_transfer_open (sci_uart_instance_ctrl_t * const p_ctrl, uart_cfg_t const * const p_cfg)
1258 {
1259     fsp_err_t err = FSP_SUCCESS;
1260 
1261  #if (SCI_UART_CFG_RX_ENABLE)
1262 
1263     /* If a transfer instance is used for reception, apply UART specific settings and open the transfer instance. */
1264     if (NULL != p_cfg->p_transfer_rx)
1265     {
1266         transfer_info_t * p_info = p_cfg->p_transfer_rx->p_cfg->p_info;
1267 
1268         p_info->transfer_settings_word = SCI_UART_DTC_RX_TRANSFER_SETTINGS;
1269 
1270         err =
1271             r_sci_uart_transfer_configure(p_ctrl, p_cfg->p_transfer_rx, (uint32_t *) &p_info->p_src,
1272                                           (uint32_t) &(p_ctrl->p_reg->RDR));
1273         FSP_ERROR_RETURN(FSP_SUCCESS == err, err);
1274     }
1275  #endif
1276  #if (SCI_UART_CFG_TX_ENABLE)
1277 
1278     /* If a transfer instance is used for transmission, apply UART specific settings and open the transfer instance. */
1279     if (NULL != p_cfg->p_transfer_tx)
1280     {
1281         transfer_info_t * p_info = p_cfg->p_transfer_tx->p_cfg->p_info;
1282 
1283         p_info->transfer_settings_word = SCI_UART_DTC_TX_TRANSFER_SETTINGS;
1284 
1285         err = r_sci_uart_transfer_configure(p_ctrl,
1286                                             p_cfg->p_transfer_tx,
1287                                             (uint32_t *) &p_info->p_dest,
1288                                             (uint32_t) &p_ctrl->p_reg->TDR);
1289 
1290   #if (SCI_UART_CFG_RX_ENABLE)
1291         if ((err != FSP_SUCCESS) && (NULL != p_cfg->p_transfer_rx))
1292         {
1293             p_cfg->p_transfer_rx->p_api->close(p_cfg->p_transfer_rx->p_ctrl);
1294         }
1295   #endif
1296         FSP_ERROR_RETURN(FSP_SUCCESS == err, err);
1297     }
1298  #endif
1299 
1300     return err;
1301 }
1302 
1303 #endif
1304 
1305 /*******************************************************************************************************************//**
1306  * Configures UART related registers based on user configurations.
1307  *
1308  * @param[in]     p_ctrl  Pointer to UART control structure
1309  * @param[in]     p_cfg   Pointer to UART specific configuration structure
1310  **********************************************************************************************************************/
r_sci_uart_config_set(sci_uart_instance_ctrl_t * const p_ctrl,uart_cfg_t const * const p_cfg)1311 static void r_sci_uart_config_set (sci_uart_instance_ctrl_t * const p_ctrl, uart_cfg_t const * const p_cfg)
1312 {
1313 #if SCI_UART_CFG_FIFO_SUPPORT
1314 
1315     /* Configure FIFO related registers. */
1316     r_sci_uart_fifo_cfg(p_ctrl);
1317 #else
1318 
1319     /* If fifo support is disabled and the current channel supports fifo make sure it's disabled. */
1320     if (BSP_FEATURE_SCI_UART_FIFO_CHANNELS & (1U << p_cfg->channel))
1321     {
1322         p_ctrl->p_reg->FCR = SCI_UART_FCR_DEFAULT_VALUE;
1323     }
1324 #endif
1325 
1326     /* Configure parity and stop bits. */
1327     uint32_t smr  = (((uint32_t) p_cfg->parity << 4U) | ((uint32_t) p_cfg->stop_bits << 3U));
1328     uint32_t scmr = SCI_UART_SCMR_DEFAULT_VALUE;
1329 
1330     /* Configure data size. */
1331     if (UART_DATA_BITS_7 == p_cfg->data_bits)
1332     {
1333         /* Set the SMR.CHR bit & SCMR.CHR1 bit as selected (Character Length)
1334          *  Character Length
1335          *  (CHR1,CHR)
1336          *  (1, 1) Transmit/receive in 7-bit data length*3
1337          */
1338         smr |= (1U << 6);
1339     }
1340     else if (UART_DATA_BITS_9 == p_cfg->data_bits)
1341     {
1342         /* Set the SMR.CHR bit & SCMR.CHR1 bit as selected (Character Length)
1343          *  Character Length
1344          *  (CHR1,CHR)
1345          *  (0, 0) Transmit/receive in 9-bit data length
1346          */
1347         scmr &= ~(1U << 4);
1348     }
1349     else
1350     {
1351         /* Do nothing.  Default is 8-bit mode. */
1352     }
1353 
1354     /* Write to the SMR register. */
1355     p_ctrl->p_reg->SMR = (uint8_t) smr;
1356 
1357     /* Write to the SCMR register. */
1358     p_ctrl->p_reg->SCMR = (uint8_t) scmr;
1359 
1360     sci_uart_extended_cfg_t * p_extend = (sci_uart_extended_cfg_t *) p_cfg->p_extend;
1361 
1362     /* Configure flow control if CTS/RTS flow control is enabled. */
1363 #if BSP_FEATURE_SCI_UART_CSTPEN_CHANNELS
1364     if (p_extend->flow_control == SCI_UART_FLOW_CONTROL_HARDWARE_CTSRTS)
1365     {
1366         p_ctrl->p_reg->SPMR = R_SCI0_SPMR_CSTPEN_Msk | R_SCI0_SPMR_CTSE_Msk;
1367     }
1368     else
1369 #endif
1370     {
1371         p_ctrl->p_reg->SPMR = ((uint8_t) (p_extend->flow_control << R_SCI0_SPMR_CTSE_Pos) & R_SCI0_SPMR_CTSE_Msk);
1372     }
1373 
1374     uint32_t semr = 0;
1375 
1376     /* Starts reception on falling edge of RXD if enabled in extension (otherwise reception starts at low level
1377      * of RXD). */
1378     semr |= (p_extend->rx_edge_start & 1U) << 7;
1379 
1380     /* Enables the noise cancellation, fixed to the minimum level, if enabled in the extension. */
1381     semr |= (p_extend->noise_cancel & 1U) << 5;
1382 
1383     p_ctrl->p_reg->SNFR = NOISE_CANCEL_LVL1;
1384 
1385     if ((SCI_UART_CLOCK_EXT8X == p_extend->clock) || (SCI_UART_CLOCK_EXT16X == p_extend->clock))
1386     {
1387         /* Use external clock for baud rate */
1388         p_ctrl->p_reg->BRR = SCI_UART_BRR_DEFAULT_VALUE;
1389 
1390         if (SCI_UART_CLOCK_EXT8X == p_extend->clock)
1391         {
1392             /* Set baud rate as (external clock / 8) */
1393             semr |= 1U << SCI_UART_SEMR_ABCS_OFFSET;
1394         }
1395 
1396         p_ctrl->p_reg->SEMR = (uint8_t) semr;
1397     }
1398     else
1399     {
1400         p_ctrl->p_reg->SEMR = (uint8_t) semr;
1401 
1402         /* Set the baud rate settings for the internal baud rate generator. */
1403         r_sci_uart_baud_set(p_ctrl->p_reg, p_extend->p_baud_setting);
1404     }
1405 }
1406 
1407 #if SCI_UART_CFG_FIFO_SUPPORT
1408 
1409 /*******************************************************************************************************************//**
1410  * Resets FIFO related registers.
1411  *
1412  * @param[in] p_ctrl  Pointer to UART instance control
1413  * @param[in] p_cfg   Pointer to UART configuration structure
1414  **********************************************************************************************************************/
r_sci_uart_fifo_cfg(sci_uart_instance_ctrl_t * const p_ctrl)1415 static void r_sci_uart_fifo_cfg (sci_uart_instance_ctrl_t * const p_ctrl)
1416 {
1417     if (0U != p_ctrl->fifo_depth)
1418     {
1419         /* Enable the fifo and set the tx and rx reset bits */
1420         uint32_t fcr = 1U;
1421 
1422  #if (SCI_UART_CFG_RX_ENABLE)
1423   #if SCI_UART_CFG_DTC_SUPPORTED
1424 
1425         /* If DTC is used keep the receive trigger at the default level of 0. */
1426         if (NULL == p_ctrl->p_cfg->p_transfer_rx)
1427   #endif
1428         {
1429             /* Otherwise, set receive trigger number as configured by the user. */
1430             sci_uart_extended_cfg_t const * p_extend = p_ctrl->p_cfg->p_extend;
1431 
1432             /* RTRG(Receive FIFO Data Trigger Number) controls when the RXI interrupt will be generated. If data is
1433              * received but the trigger number is not met the RXI interrupt will be generated after 15 ETUs from
1434              * the last stop bit in asynchronous mode. For more information see the FIFO Selected section of "Serial
1435              * Data Reception in Asynchronous Mode" in the RA6M3 manual R01UH0886EJ0100 or the relevant section for
1436              * the MCU being used. */
1437             fcr |= (((p_ctrl->fifo_depth - 1U) & p_extend->rx_fifo_trigger) & SCI_UART_FCR_TRIGGER_MASK) <<
1438                    SCI_UART_FCR_RTRG_OFFSET;
1439         }
1440 
1441         /* RTS asserts when the amount of received data stored in the fifo is equal or less than this value. */
1442         fcr |= ((p_ctrl->fifo_depth - 1U) & SCI_UART_FCR_TRIGGER_MASK) << SCI_UART_FCR_RSTRG_OFFSET;
1443  #endif
1444 
1445         /* Set the FCR and reset the fifos. */
1446         p_ctrl->p_reg->FCR = (uint16_t) (fcr | SCI_UART_FCR_RESET_TX_RX);
1447 
1448         /* Wait for the fifo reset to complete after 1 PCLK according to section 34.2.26 "FIFO Control Register (FCR)
1449          * in the RA6M3 manual R01UH0886EJ0100 or the relevant section for the MCU being used.*/
1450         FSP_HARDWARE_REGISTER_WAIT(p_ctrl->p_reg->FCR, fcr);
1451     }
1452 }
1453 
1454 #endif
1455 
1456 /*******************************************************************************************************************//**
1457  * Sets interrupt priority and initializes vector info.
1458  *
1459  * @param[in]  p_ctrl                    Pointer to driver control block
1460  * @param[in]  ipl                       Interrupt priority level
1461  * @param[in]  irq                       IRQ number for this interrupt
1462  **********************************************************************************************************************/
r_sci_irq_cfg(sci_uart_instance_ctrl_t * const p_ctrl,uint8_t const ipl,IRQn_Type const irq)1463 static void r_sci_irq_cfg (sci_uart_instance_ctrl_t * const p_ctrl, uint8_t const ipl, IRQn_Type const irq)
1464 {
1465     /* Disable interrupts, set priority, and store control block in the vector information so it can be accessed
1466      * from the callback. */
1467     R_BSP_IrqDisable(irq);
1468     R_BSP_IrqStatusClear(irq);
1469     R_BSP_IrqCfg(irq, ipl, p_ctrl);
1470 }
1471 
1472 /*******************************************************************************************************************//**
1473  * Sets interrupt priority and initializes vector info for all interrupts.
1474  *
1475  * @param[in]  p_ctrl                    Pointer to UART instance control block
1476  * @param[in]  p_cfg                     Pointer to UART specific configuration structure
1477  **********************************************************************************************************************/
r_sci_irqs_cfg(sci_uart_instance_ctrl_t * const p_ctrl,uart_cfg_t const * const p_cfg)1478 static void r_sci_irqs_cfg (sci_uart_instance_ctrl_t * const p_ctrl, uart_cfg_t const * const p_cfg)
1479 {
1480 #if (SCI_UART_CFG_RX_ENABLE)
1481 
1482     /* ERI is optional. */
1483     r_sci_irq_cfg(p_ctrl, p_cfg->eri_ipl, p_cfg->eri_irq);
1484     r_sci_irq_cfg(p_ctrl, p_cfg->rxi_ipl, p_cfg->rxi_irq);
1485 #endif
1486 #if (SCI_UART_CFG_TX_ENABLE)
1487     r_sci_irq_cfg(p_ctrl, p_cfg->txi_ipl, p_cfg->txi_irq);
1488 
1489     r_sci_irq_cfg(p_ctrl, p_cfg->tei_ipl, p_cfg->tei_irq);
1490 #endif
1491 }
1492 
1493 #if SCI_UART_CFG_DTC_SUPPORTED
1494 
1495 /*******************************************************************************************************************//**
1496  * Closes transfer interfaces.
1497  *
1498  * @param[in]     p_ctrl     Pointer to UART instance control block
1499  **********************************************************************************************************************/
r_sci_uart_transfer_close(sci_uart_instance_ctrl_t * p_ctrl)1500 static void r_sci_uart_transfer_close (sci_uart_instance_ctrl_t * p_ctrl)
1501 {
1502  #if (SCI_UART_CFG_RX_ENABLE)
1503     if (NULL != p_ctrl->p_cfg->p_transfer_rx)
1504     {
1505         p_ctrl->p_cfg->p_transfer_rx->p_api->close(p_ctrl->p_cfg->p_transfer_rx->p_ctrl);
1506     }
1507  #endif
1508  #if (SCI_UART_CFG_TX_ENABLE)
1509     if (NULL != p_ctrl->p_cfg->p_transfer_tx)
1510     {
1511         p_ctrl->p_cfg->p_transfer_tx->p_api->close(p_ctrl->p_cfg->p_transfer_tx->p_ctrl);
1512     }
1513  #endif
1514 }
1515 
1516 #endif
1517 
1518 /*******************************************************************************************************************//**
1519  * Changes baud rate based on predetermined register settings.
1520  *
1521  * @param[in]  p_sci_reg       Base pointer for SCI registers
1522  * @param[in]  p_baud_setting  Pointer to other divisor related settings
1523  *
1524  * @note       The transmitter and receiver (TE and RE bits in SCR) must be disabled prior to calling this function.
1525  **********************************************************************************************************************/
r_sci_uart_baud_set(R_SCI0_Type * p_sci_reg,baud_setting_t const * const p_baud_setting)1526 static void r_sci_uart_baud_set (R_SCI0_Type * p_sci_reg, baud_setting_t const * const p_baud_setting)
1527 {
1528     /* Set BRR register value. */
1529     p_sci_reg->BRR = p_baud_setting->brr;
1530 
1531     /* Set clock source for the on-chip baud rate generator. */
1532     p_sci_reg->SMR_b.CKS = (uint8_t) (SCI_SMR_CKS_VALUE_MASK & p_baud_setting->cks);
1533 
1534     /* Set MDDR register value. */
1535     p_sci_reg->MDDR = p_baud_setting->mddr;
1536 
1537     /* Set clock divisor settings. */
1538     p_sci_reg->SEMR = (uint8_t) ((p_sci_reg->SEMR & ~(SCI_UART_SEMR_BAUD_SETTING_MASK)) |
1539                                  (p_baud_setting->semr_baudrate_bits & SCI_UART_SEMR_BAUD_SETTING_MASK));
1540 }
1541 
1542 /*******************************************************************************************************************//**
1543  * Calls user callback.
1544  *
1545  * @param[in]     p_ctrl     Pointer to UART instance control block
1546  * @param[in]     data       See uart_callback_args_t in r_uart_api.h
1547  * @param[in]     event      Event code
1548  **********************************************************************************************************************/
r_sci_uart_call_callback(sci_uart_instance_ctrl_t * p_ctrl,uint32_t data,uart_event_t event)1549 static void r_sci_uart_call_callback (sci_uart_instance_ctrl_t * p_ctrl, uint32_t data, uart_event_t event)
1550 {
1551     uart_callback_args_t args;
1552 
1553     /* Store callback arguments in memory provided by user if available.  This allows callback arguments to be
1554      * stored in non-secure memory so they can be accessed by a non-secure callback function. */
1555     uart_callback_args_t * p_args = p_ctrl->p_callback_memory;
1556     if (NULL == p_args)
1557     {
1558         /* Store on stack */
1559         p_args = &args;
1560     }
1561     else
1562     {
1563         /* Save current arguments on the stack in case this is a nested interrupt. */
1564         args = *p_args;
1565     }
1566 
1567     p_args->channel   = p_ctrl->p_cfg->channel;
1568     p_args->data      = data;
1569     p_args->event     = event;
1570     p_args->p_context = p_ctrl->p_context;
1571 
1572 #if BSP_TZ_SECURE_BUILD
1573 
1574     /* p_callback can point to a secure function or a non-secure function. */
1575     if (!cmse_is_nsfptr(p_ctrl->p_callback))
1576     {
1577         /* If p_callback is secure, then the project does not need to change security state. */
1578         p_ctrl->p_callback(p_args);
1579     }
1580     else
1581     {
1582         /* If p_callback is Non-secure, then the project must change to Non-secure state in order to call the callback. */
1583         sci_uart_prv_ns_callback p_callback = (sci_uart_prv_ns_callback) (p_ctrl->p_callback);
1584         p_callback(p_args);
1585     }
1586 
1587 #else
1588 
1589     /* If the project is not Trustzone Secure, then it will never need to change security state in order to call the callback. */
1590     p_ctrl->p_callback(p_args);
1591 #endif
1592     if (NULL != p_ctrl->p_callback_memory)
1593     {
1594         /* Restore callback memory in case this is a nested interrupt. */
1595         *p_ctrl->p_callback_memory = args;
1596     }
1597 }
1598 
1599 #if (SCI_UART_CFG_TX_ENABLE)
1600 
1601 /*******************************************************************************************************************//**
1602  * TXI interrupt processing for UART mode. TXI interrupt fires when the data in the data register or FIFO register has
1603  * been transferred to the data shift register, and the next data can be written.  This interrupt writes the next data.
1604  * After the last data byte is written, this interrupt disables the TXI interrupt and enables the TEI (transmit end)
1605  * interrupt.
1606  **********************************************************************************************************************/
sci_uart_txi_isr(void)1607 void sci_uart_txi_isr (void)
1608 {
1609     /* Save context if RTOS is used */
1610     FSP_CONTEXT_SAVE;
1611 
1612     IRQn_Type irq = R_FSP_CurrentIrqGet();
1613 
1614     /* Clear pending IRQ to make sure it doesn't fire again after exiting */
1615     R_BSP_IrqStatusClear(irq);
1616 
1617     /* Recover ISR context saved in open. */
1618     sci_uart_instance_ctrl_t * p_ctrl = (sci_uart_instance_ctrl_t *) R_FSP_IsrContextGet(irq);
1619 
1620     if ((NULL == p_ctrl->p_cfg->p_transfer_tx) && (0U != p_ctrl->tx_src_bytes))
1621     {
1622         /* Write the data to the FIFO if the channel has a FIFO.  Otherwise write data based on size to the transmit
1623          * register.  Write to 16-bit TDRHL for 9-bit data, or 8-bit TDR otherwise. */
1624  #if SCI_UART_CFG_FIFO_SUPPORT
1625         if (0U != p_ctrl->fifo_depth)
1626         {
1627             uint32_t fifo_count = (uint32_t) p_ctrl->p_reg->FDR_b.T;
1628             for (uint32_t cnt = fifo_count; (cnt < p_ctrl->fifo_depth) && p_ctrl->tx_src_bytes; cnt++)
1629             {
1630                 if (2U == p_ctrl->data_bytes)
1631                 {
1632                     p_ctrl->p_reg->FTDRHL =
1633                         (uint16_t) (*((uint16_t *) p_ctrl->p_tx_src) | (uint16_t) ~(SCI_UART_FIFO_DAT_MASK));
1634                 }
1635                 else
1636                 {
1637                     p_ctrl->p_reg->FTDRL = *p_ctrl->p_tx_src;
1638                 }
1639 
1640                 p_ctrl->tx_src_bytes -= p_ctrl->data_bytes;
1641                 p_ctrl->p_tx_src     += p_ctrl->data_bytes;
1642             }
1643 
1644             /* Clear TDFE flag */
1645             p_ctrl->p_reg->SSR_FIFO_b.TDFE = 0U;
1646         }
1647         else
1648  #endif
1649         {
1650             if ((2U == p_ctrl->data_bytes))
1651             {
1652                 /* Write 16-bit data to TDRHL register */
1653                 p_ctrl->p_reg->TDRHL = *((uint16_t *) (p_ctrl->p_tx_src)) | (uint16_t) ~(SCI_UART_FIFO_DAT_MASK);
1654             }
1655             else
1656             {
1657                 /* Write 1byte (uint8_t) data to (uint8_t) data register */
1658                 p_ctrl->p_reg->TDR = *(p_ctrl->p_tx_src);
1659             }
1660 
1661             /* Update pointer to the next data and number of remaining bytes in the control block. */
1662             p_ctrl->tx_src_bytes -= p_ctrl->data_bytes;
1663             p_ctrl->p_tx_src     += p_ctrl->data_bytes;
1664         }
1665     }
1666 
1667     if (0U == p_ctrl->tx_src_bytes)
1668     {
1669         /* After all data has been transmitted, disable transmit interrupts and enable the transmit end interrupt. */
1670         uint8_t scr_temp = p_ctrl->p_reg->SCR;
1671         scr_temp          |= SCI_SCR_TEIE_MASK;
1672         scr_temp          &= (uint8_t) ~SCI_SCR_TIE_MASK;
1673         p_ctrl->p_reg->SCR = scr_temp;
1674 
1675         p_ctrl->p_tx_src = NULL;
1676 
1677         /* If a callback was provided, call it with the argument */
1678         if (NULL != p_ctrl->p_callback)
1679         {
1680             r_sci_uart_call_callback(p_ctrl, 0U, UART_EVENT_TX_DATA_EMPTY);
1681         }
1682     }
1683 
1684     /* Restore context if RTOS is used */
1685     FSP_CONTEXT_RESTORE;
1686 }
1687 
1688 #endif
1689 
1690 #if (SCI_UART_CFG_RX_ENABLE)
1691 
1692 /*******************************************************************************************************************//**
1693  * RXI interrupt processing for UART mode. RXI interrupt happens when data arrives to the data register or the FIFO
1694  * register.  This function calls callback function when it meets conditions below.
1695  *  - UART_EVENT_RX_COMPLETE: The number of data which has been read reaches to the number specified in R_SCI_UART_Read()
1696  *    if a transfer instance is used for reception.
1697  *  - UART_EVENT_RX_CHAR: Data is received asynchronously (read has not been called)
1698  *
1699  * This interrupt also calls the callback function for RTS pin control if it is registered in R_SCI_UART_Open(). This is
1700  * special functionality to expand SCI hardware capability and make RTS/CTS hardware flow control possible. If macro
1701  * 'SCI_UART_CFG_FLOW_CONTROL_SUPPORT' is set, it is called at the beginning in this function to set the RTS pin high,
1702  * then it is called again just before leaving this function to set the RTS pin low.
1703  * @retval    none
1704  **********************************************************************************************************************/
sci_uart_rxi_isr(void)1705 void sci_uart_rxi_isr (void)
1706 {
1707     /* Save context if RTOS is used */
1708     FSP_CONTEXT_SAVE;
1709 
1710     IRQn_Type irq = R_FSP_CurrentIrqGet();
1711 
1712     /* Clear pending IRQ to make sure it doesn't fire again after exiting */
1713     R_BSP_IrqStatusClear(irq);
1714 
1715     /* Recover ISR context saved in open. */
1716     sci_uart_instance_ctrl_t * p_ctrl = (sci_uart_instance_ctrl_t *) R_FSP_IsrContextGet(irq);
1717 
1718  #if SCI_UART_CFG_DTC_SUPPORTED
1719     if ((p_ctrl->p_cfg->p_transfer_rx == NULL) || (0 == p_ctrl->rx_dest_bytes))
1720  #endif
1721     {
1722  #if (SCI_UART_CFG_FLOW_CONTROL_SUPPORT)
1723         if (p_ctrl->flow_pin != SCI_UART_INVALID_16BIT_PARAM)
1724         {
1725             R_BSP_PinAccessEnable();
1726 
1727             /* Pause the transmission of data from the other device. */
1728             R_BSP_PinWrite(p_ctrl->flow_pin, SCI_UART_FLOW_CONTROL_ACTIVE);
1729         }
1730  #endif
1731 
1732         uint32_t data;
1733  #if SCI_UART_CFG_FIFO_SUPPORT
1734         do
1735         {
1736             if ((p_ctrl->fifo_depth > 0U))
1737             {
1738                 if (p_ctrl->p_reg->FDR_b.R > 0U)
1739                 {
1740                     data = p_ctrl->p_reg->FRDRHL & FRDR_TDAT_MASK_9BITS;
1741                 }
1742                 else
1743                 {
1744                     break;
1745                 }
1746             }
1747             else if (2U == p_ctrl->data_bytes)
1748  #else
1749         {
1750             if (2U == p_ctrl->data_bytes)
1751  #endif
1752             {
1753                 data = p_ctrl->p_reg->RDRHL & FRDR_TDAT_MASK_9BITS;
1754             }
1755             else
1756             {
1757                 data = p_ctrl->p_reg->RDR;
1758             }
1759 
1760             if (0 == p_ctrl->rx_dest_bytes)
1761             {
1762                 /* If a callback was provided, call it with the argument */
1763                 if (NULL != p_ctrl->p_callback)
1764                 {
1765                     /* Call user callback with the data. */
1766                     r_sci_uart_call_callback(p_ctrl, data, UART_EVENT_RX_CHAR);
1767                 }
1768             }
1769             else
1770             {
1771                 memcpy((void *) p_ctrl->p_rx_dest, &data, p_ctrl->data_bytes);
1772                 p_ctrl->p_rx_dest     += p_ctrl->data_bytes;
1773                 p_ctrl->rx_dest_bytes -= p_ctrl->data_bytes;
1774 
1775                 if (0 == p_ctrl->rx_dest_bytes)
1776                 {
1777                     /* If a callback was provided, call it with the argument */
1778                     if (NULL != p_ctrl->p_callback)
1779                     {
1780                         r_sci_uart_call_callback(p_ctrl, 0U, UART_EVENT_RX_COMPLETE);
1781                     }
1782                 }
1783             }
1784 
1785  #if SCI_UART_CFG_FIFO_SUPPORT
1786         } while ((p_ctrl->fifo_depth > 0U) && ((p_ctrl->p_reg->FDR_b.R) > 0U));
1787 
1788         if (p_ctrl->fifo_depth > 0U)
1789         {
1790             p_ctrl->p_reg->SSR_FIFO = (uint8_t) ~(SCI_UART_SSR_FIFO_DR_RDF);
1791         }
1792 
1793  #else
1794         }
1795  #endif
1796  #if (SCI_UART_CFG_FLOW_CONTROL_SUPPORT)
1797         if (p_ctrl->flow_pin != SCI_UART_INVALID_16BIT_PARAM)
1798         {
1799             /* Resume the transmission of data from the other device. */
1800             R_BSP_PinWrite(p_ctrl->flow_pin, SCI_UART_FLOW_CONTROL_INACTIVE);
1801             R_BSP_PinAccessDisable();
1802         }
1803  #endif
1804     }
1805 
1806  #if SCI_UART_CFG_DTC_SUPPORTED
1807     else
1808     {
1809         p_ctrl->rx_dest_bytes = 0;
1810 
1811         p_ctrl->p_rx_dest = NULL;
1812 
1813         /* If a callback was provided, call it with the argument */
1814         if (NULL != p_ctrl->p_callback)
1815         {
1816             /* Call callback */
1817             r_sci_uart_call_callback(p_ctrl, 0U, UART_EVENT_RX_COMPLETE);
1818         }
1819     }
1820  #endif
1821 
1822     /* Restore context if RTOS is used */
1823     FSP_CONTEXT_RESTORE;
1824 }
1825 
1826 #endif
1827 
1828 #if (SCI_UART_CFG_TX_ENABLE)
1829 
1830 /*******************************************************************************************************************//**
1831  * TEI interrupt processing for UART mode. The TEI interrupt fires after the last byte is transmitted on the TX pin.
1832  * The user callback function is called with the UART_EVENT_TX_COMPLETE event code (if it is registered in
1833  * R_SCI_UART_Open()).
1834  **********************************************************************************************************************/
sci_uart_tei_isr(void)1835 void sci_uart_tei_isr (void)
1836 {
1837     /* Save context if RTOS is used */
1838     FSP_CONTEXT_SAVE;
1839 
1840     IRQn_Type irq = R_FSP_CurrentIrqGet();
1841 
1842     /* Recover ISR context saved in open. */
1843     sci_uart_instance_ctrl_t * p_ctrl = (sci_uart_instance_ctrl_t *) R_FSP_IsrContextGet(irq);
1844 
1845     /* Receiving TEI(transmit end interrupt) means the completion of transmission, so call callback function here. */
1846     p_ctrl->p_reg->SCR &= (uint8_t) ~(SCI_SCR_TIE_MASK | SCI_SCR_TEIE_MASK);
1847 
1848     /* Negate driver enable if RS-485 mode is enabled. */
1849     r_sci_negate_de_pin(p_ctrl);
1850 
1851     /* If a callback was provided, call it with the argument */
1852     if (NULL != p_ctrl->p_callback)
1853     {
1854         r_sci_uart_call_callback(p_ctrl, 0U, UART_EVENT_TX_COMPLETE);
1855     }
1856 
1857     /* Clear pending IRQ to make sure it doesn't fire again after exiting */
1858     R_BSP_IrqStatusClear(irq);
1859 
1860     /* Restore context if RTOS is used */
1861     FSP_CONTEXT_RESTORE;
1862 }
1863 
1864 #endif
1865 
1866 #if (SCI_UART_CFG_RX_ENABLE)
1867 
1868 /*******************************************************************************************************************//**
1869  * ERI interrupt processing for UART mode. When an ERI interrupt fires, the user callback function is called if it is
1870  * registered in R_SCI_UART_Open() with the event code that triggered the interrupt.
1871  **********************************************************************************************************************/
sci_uart_eri_isr(void)1872 void sci_uart_eri_isr (void)
1873 {
1874     /* Save context if RTOS is used */
1875     FSP_CONTEXT_SAVE;
1876 
1877     IRQn_Type irq = R_FSP_CurrentIrqGet();
1878 
1879     /* Recover ISR context saved in open. */
1880     sci_uart_instance_ctrl_t * p_ctrl = (sci_uart_instance_ctrl_t *) R_FSP_IsrContextGet(irq);
1881 
1882     uint32_t     data = 0U;
1883     uart_event_t event;
1884 
1885     /* Read data. */
1886     if (
1887  #if SCI_UART_CFG_FIFO_SUPPORT
1888         (p_ctrl->fifo_depth > 0U) ||
1889  #endif
1890         (2U == p_ctrl->data_bytes))
1891     {
1892         {
1893             data = p_ctrl->p_reg->RDRHL & SCI_UART_FIFO_DAT_MASK;
1894         }
1895     }
1896     else
1897     {
1898         data = p_ctrl->p_reg->RDR;
1899     }
1900 
1901     /* Determine cause of error. */
1902     event = (uart_event_t) (p_ctrl->p_reg->SSR & SCI_RCVR_ERR_MASK);
1903 
1904     /* Check if there is a break detected. */
1905     if ((UART_EVENT_ERR_FRAMING == (event & UART_EVENT_ERR_FRAMING)) && (0U == p_ctrl->p_reg->SPTR_b.RXDMON))
1906     {
1907         event |= UART_EVENT_BREAK_DETECT;
1908     }
1909 
1910     /* Clear error condition. */
1911     p_ctrl->p_reg->SSR &= (uint8_t) (~SCI_RCVR_ERR_MASK);
1912 
1913     /* Negate driver enable if RS-485 mode is enabled. */
1914     r_sci_negate_de_pin(p_ctrl);
1915 
1916     /* If a callback was provided, call it with the argument */
1917     if (NULL != p_ctrl->p_callback)
1918     {
1919         /* Call callback. */
1920         r_sci_uart_call_callback(p_ctrl, data, event);
1921     }
1922 
1923     /* Clear pending IRQ to make sure it doesn't fire again after exiting */
1924     R_BSP_IrqStatusClear(irq);
1925 
1926     /* Restore context if RTOS is used */
1927     FSP_CONTEXT_RESTORE;
1928 }
1929 
1930 #endif
1931