1 /*
2 * Copyright (c) 2020 - 2024 Renesas Electronics Corporation and/or its affiliates
3 *
4 * SPDX-License-Identifier: BSD-3-Clause
5 */
6 
7 /***********************************************************************************************************************
8  * Includes
9  **********************************************************************************************************************/
10 #include "r_iic_master.h"
11 #if IIC_MASTER_CFG_DTC_ENABLE
12  #include "r_dtc.h"
13 #endif
14 
15 /***********************************************************************************************************************
16  * Macro definitions
17  **********************************************************************************************************************/
18 
19 /* "IIC" in ASCII, used to determine if channel is open. */
20 #define IIC_MASTER_OPEN                             (0x52494943U)
21 
22 #define I2C_CODE_READ                               (0x01U)
23 #define I2C_CODE_10BIT                              (0xF0U)
24 
25 /* The timeout interrupt enable bit */
26 #define IIC_MASTER_TMO_EN_BIT                       (0x01)
27 
28 /* The arbitration loss detection interrupt enable bit */
29 #define IIC_MASTER_ALD_EN_BIT                       (0x02)
30 
31 /* The start condition detection interrupt enable bit */
32 #define IIC_MASTER_STR_EN_BIT                       (0x04)
33 
34 /* The stop condition detection interrupt enable bit */
35 #define IIC_MASTER_STP_EN_BIT                       (0x08)
36 
37 /* The NAK reception interrupt enable bit */
38 #define IIC_MASTER_NAK_EN_BIT                       (0x10)
39 
40 /* The receive data full interrupt enable bit */
41 #define IIC_MASTER_RXI_EN_BIT                       (0x20)
42 
43 /* The transmit end interrupt enable bit */
44 #define IIC_MASTER_TEI_EN_BIT                       (0x40)
45 
46 /* The transmit data empty interrupt enable bit */
47 #define IIC_MASTER_TXI_EN_BIT                       (0x80)
48 
49 /* Bit position for STOP condition flag in ICSR2 */
50 #define IIC_MASTER_ICSR2_STOP_BIT                   (0x08U)
51 
52 #define IIC_MASTER_BUS_RATE_REG_RESERVED_BITS       (0xE0U)
53 #define IIC_MASTER_INTERNAL_REF_CLOCK_SELECT_MAX    (0x07U)
54 
55 #define IIC_MASTER_SLAVE_10_BIT_ADDR_LEN_ADJUST     (2U)
56 
57 #define IIC_MASTER_DTC_RX_TRANSFER_SETTINGS         ((TRANSFER_MODE_NORMAL << TRANSFER_SETTINGS_MODE_BITS) |         \
58                                                      (TRANSFER_SIZE_1_BYTE << TRANSFER_SETTINGS_SIZE_BITS) |         \
59                                                      (TRANSFER_ADDR_MODE_FIXED << TRANSFER_SETTINGS_SRC_ADDR_BITS) | \
60                                                      (TRANSFER_IRQ_END << TRANSFER_SETTINGS_IRQ_BITS) |              \
61                                                      (TRANSFER_ADDR_MODE_INCREMENTED <<                              \
62                                                       TRANSFER_SETTINGS_DEST_ADDR_BITS))
63 #define IIC_MASTER_DTC_TX_TRANSFER_SETTINGS         ((TRANSFER_MODE_NORMAL << TRANSFER_SETTINGS_MODE_BITS) | \
64                                                      (TRANSFER_SIZE_1_BYTE << TRANSFER_SETTINGS_SIZE_BITS) | \
65                                                      (TRANSFER_ADDR_MODE_INCREMENTED <<                      \
66                                                       TRANSFER_SETTINGS_SRC_ADDR_BITS) |                     \
67                                                      (TRANSFER_IRQ_END << TRANSFER_SETTINGS_IRQ_BITS) |      \
68                                                      (TRANSFER_ADDR_MODE_FIXED << TRANSFER_SETTINGS_DEST_ADDR_BITS))
69 #define IIC_MASTER_FUNCTION_ENABLE_REG_VAL          (0x02U)
70 #define IIC_MASTER_INTERRUPT_ENABLE_INIT_MASK       (0xB3U)
71 #define IIC_MASTER_FUNCTION_ENABLE_INIT_SETTINGS    (0x77U)
72 #define IIC_MASTER_STATUS_REGISTER_2_ERR_MASK       (0x1FU)
73 #define IIC_MASTER_BUS_MODE_REGISTER_1_MASK         (0x08U)
74 #define IIC_MASTER_BUS_MODE_REGISTER_2_MASK         (0x04U)
75 #define IIC_MASTER_SYSDIVCK_ICLK_MASK               (0x0F000000U)
76 #define IIC_MASTER_SYSDIVCK_PCLKB_MASK              (0x00000F00U)
77 #define IIC_MASTER_PRV_SCL_SDA_NOT_DRIVEN           (0x1FU)
78 #define IIC_MASTER_ICCR1_ICE_BIT_MASK               (0x80)
79 #define IIC_MASTER_ICCR1_IICRST_BIT_MASK            (0x40)
80 #define IIC_MASTER_ICCR2_SP_BIT_MASK                (0x08)
81 #define IIC_MASTER_ICCR2_RS_BIT_MASK                (0x04)
82 #define IIC_MASTER_ICCR2_ST_BIT_MASK                (0x02)
83 
84 /* Worst case ratio of (ICLK/PCLKB) = 64 bytes approximately.
85  * 3 PCLKB cycles is the number of cycles to wait for IICn.
86  * Refer "Table 3.2 Access cycles (1 of 2)" of the RA6M3 manual R01UH0886EJ0100)
87  */
88 #define IIC_MASTER_PERIPHERAL_REG_MAX_WAIT          (0x40U * 0x03U)
89 
90 #define IIC_MASTER_HARDWARE_REGISTER_WAIT(reg, required_value, timeout) \
91     while ((timeout))                                                   \
92     {                                                                   \
93         if ((required_value) == (reg))                                  \
94         {                                                               \
95             break;                                                      \
96         }                                                               \
97         (timeout)--;                                                    \
98     }
99 
100 /***********************************************************************************************************************
101  * Typedef definitions
102  **********************************************************************************************************************/
103 
104 /* Hardware errors and events that can occur on the IIC */
105 typedef enum e_iic_master_err_event
106 {
107     IIC_MASTER_ERR_EVENT_NONE             = 0,
108     IIC_MASTER_ERR_EVENT_TIMEOUT          = 1,
109     IIC_MASTER_ERR_EVENT_ARBITRATION_LOSS = 2,
110     IIC_MASTER_ERR_EVENT_START            = 4,
111     IIC_MASTER_ERR_EVENT_STOP             = 8,
112     IIC_MASTER_ERR_EVENT_NACK             = 16
113 } iic_master_err_t;
114 
115 /* IIC read/write enumeration */
116 typedef enum e_iic_master_transfer_dir_option
117 {
118     IIC_MASTER_TRANSFER_DIR_WRITE = 0x0,
119     IIC_MASTER_TRANSFER_DIR_READ  = 0x1
120 } iic_master_transfer_dir_t;
121 
122 #if defined(__ARMCC_VERSION) || defined(__ICCARM__)
123 typedef void (BSP_CMSE_NONSECURE_CALL * iic_master_prv_ns_callback)(i2c_master_callback_args_t * p_args);
124 #elif defined(__GNUC__)
125 typedef BSP_CMSE_NONSECURE_CALL void (*volatile iic_master_prv_ns_callback)(i2c_master_callback_args_t * p_args);
126 #endif
127 
128 /***********************************************************************************************************************
129  * Private function prototypes
130  **********************************************************************************************************************/
131 
132 void iic_master_rxi_isr(void);
133 void iic_master_txi_isr(void);
134 void iic_master_tei_isr(void);
135 void iic_master_eri_isr(void);
136 
137 /* Internal helper functions */
138 static void      iic_master_abort_seq_master(iic_master_instance_ctrl_t * const p_ctrl, bool iic_reset);
139 static fsp_err_t iic_master_read_write(i2c_master_ctrl_t * const p_api_ctrl,
140                                        uint8_t * const           p_buffer,
141                                        uint32_t const            bytes,
142                                        iic_master_transfer_dir_t direction);
143 static void iic_master_notify(iic_master_instance_ctrl_t * const p_ctrl, i2c_master_event_t const event);
144 
145 #if IIC_MASTER_CFG_DTC_ENABLE
146 static fsp_err_t iic_master_transfer_open(i2c_master_cfg_t const * const p_cfg);
147 static fsp_err_t iic_master_transfer_configure(transfer_instance_t const * p_transfer,
148                                                iic_master_transfer_dir_t   direction);
149 
150 #endif
151 
152 /* Interrupt handlers */
153 static void iic_master_rxi_master(iic_master_instance_ctrl_t * p_ctrl);
154 static void iic_master_txi_master(iic_master_instance_ctrl_t * p_ctrl);
155 static void iic_master_tei_master(iic_master_instance_ctrl_t * p_ctrl);
156 static void iic_master_err_master(iic_master_instance_ctrl_t * p_ctrl);
157 
158 /* Functions that manipulate hardware */
159 static void iic_master_open_hw_master(iic_master_instance_ctrl_t * const p_ctrl,
160                                       i2c_master_cfg_t const * const     p_cfg);
161 static fsp_err_t iic_master_run_hw_master(iic_master_instance_ctrl_t * const p_ctrl);
162 static void      iic_master_rxi_read_data(iic_master_instance_ctrl_t * const p_ctrl);
163 static void      iic_master_txi_send_address(iic_master_instance_ctrl_t * const p_ctrl);
164 
165 /***********************************************************************************************************************
166  * Private global variables
167  **********************************************************************************************************************/
168 
169 /***********************************************************************************************************************
170  * Global variables
171  **********************************************************************************************************************/
172 
173 /* IIC Implementation of I2C device master interface */
174 i2c_master_api_t const g_i2c_master_on_iic =
175 {
176     .open            = R_IIC_MASTER_Open,
177     .read            = R_IIC_MASTER_Read,
178     .write           = R_IIC_MASTER_Write,
179     .abort           = R_IIC_MASTER_Abort,
180     .slaveAddressSet = R_IIC_MASTER_SlaveAddressSet,
181     .close           = R_IIC_MASTER_Close,
182     .statusGet       = R_IIC_MASTER_StatusGet,
183     .callbackSet     = R_IIC_MASTER_CallbackSet
184 };
185 
186 /*******************************************************************************************************************//**
187  * @addtogroup IIC_MASTER
188  * @{
189  **********************************************************************************************************************/
190 
191 /***********************************************************************************************************************
192  * Functions
193  **********************************************************************************************************************/
194 
195 /*******************************************************************************************************************//**
196  * Opens the I2C device.
197  *
198  * @retval  FSP_SUCCESS                       Requested clock rate was set exactly.
199  * @retval  FSP_ERR_ALREADY_OPEN              Module is already open.
200  * @retval  FSP_ERR_IP_CHANNEL_NOT_PRESENT    Channel is not available on this MCU.
201  * @retval  FSP_ERR_ASSERTION                 Parameter check failure due to one or more reasons below:
202  *                                            1. p_api_ctrl or p_cfg is NULL.
203  *                                            2. extended parameter is NULL.
204  *                                            3. Callback parameter is NULL.
205  *                                            4. Set the rate to fast mode plus on a channel which does not support it.
206  *                                            5. Invalid IRQ number assigned
207  **********************************************************************************************************************/
R_IIC_MASTER_Open(i2c_master_ctrl_t * const p_api_ctrl,i2c_master_cfg_t const * const p_cfg)208 fsp_err_t R_IIC_MASTER_Open (i2c_master_ctrl_t * const p_api_ctrl, i2c_master_cfg_t const * const p_cfg)
209 {
210     iic_master_instance_ctrl_t * p_ctrl = (iic_master_instance_ctrl_t *) p_api_ctrl;
211 #if IIC_MASTER_CFG_PARAM_CHECKING_ENABLE
212     FSP_ASSERT(p_api_ctrl != NULL);
213     FSP_ASSERT(p_cfg != NULL);
214     FSP_ASSERT(p_cfg->p_extend != NULL);
215     FSP_ASSERT(p_cfg->rxi_irq >= (IRQn_Type) 0);
216     FSP_ASSERT(p_cfg->txi_irq >= (IRQn_Type) 0);
217     FSP_ASSERT(p_cfg->tei_irq >= (IRQn_Type) 0);
218     FSP_ASSERT(p_cfg->eri_irq >= (IRQn_Type) 0);
219     FSP_ERROR_RETURN(IIC_MASTER_OPEN != p_ctrl->open, FSP_ERR_ALREADY_OPEN);
220 
221     FSP_ERROR_RETURN(BSP_FEATURE_IIC_VALID_CHANNEL_MASK & (1 << p_cfg->channel), FSP_ERR_IP_CHANNEL_NOT_PRESENT);
222 
223     /* If rate is configured as Fast mode plus, check whether the channel supports it */
224     if (I2C_MASTER_RATE_FASTPLUS == p_cfg->rate)
225     {
226         FSP_ASSERT((BSP_FEATURE_IIC_FAST_MODE_PLUS & (1U << p_cfg->channel)));
227     }
228 #endif
229 #if IIC_MASTER_CFG_DTC_ENABLE
230     fsp_err_t err = FSP_SUCCESS;
231 #endif
232 
233     p_ctrl->p_reg = (R_IIC0_Type *) ((uint32_t) R_IIC0 + (p_cfg->channel * ((uint32_t) R_IIC1 - (uint32_t) R_IIC0)));
234 
235     /* Record the pointer to the configuration structure for later use */
236     p_ctrl->p_cfg             = p_cfg;
237     p_ctrl->slave             = p_cfg->slave;
238     p_ctrl->addr_mode         = p_cfg->addr_mode;
239     p_ctrl->p_callback        = p_cfg->p_callback;
240     p_ctrl->p_context         = p_cfg->p_context;
241     p_ctrl->p_callback_memory = NULL;
242 
243     R_BSP_MODULE_START(FSP_IP_IIC, p_cfg->channel);
244 
245     /* Open the hardware in master mode. Performs IIC initialization as described in hardware manual (see Section 36.3.2
246      * 'Initial Settings' of the RA6M3 manual R01UH0886EJ0100). */
247     iic_master_open_hw_master(p_ctrl, p_cfg);
248 
249 #if IIC_MASTER_CFG_DTC_ENABLE
250 
251     /* Open the IIC transfer interface if available */
252     err = iic_master_transfer_open(p_cfg);
253     if (FSP_SUCCESS != err)
254     {
255         R_BSP_MODULE_STOP(FSP_IP_IIC, p_cfg->channel);
256 
257         return err;
258     }
259 #endif
260 
261     p_ctrl->p_buff    = NULL;
262     p_ctrl->total     = 0U;
263     p_ctrl->remain    = 0U;
264     p_ctrl->loaded    = 0U;
265     p_ctrl->read      = false;
266     p_ctrl->restart   = false;
267     p_ctrl->err       = false;
268     p_ctrl->restarted = false;
269     p_ctrl->open      = IIC_MASTER_OPEN;
270 
271     return FSP_SUCCESS;
272 }
273 
274 /*******************************************************************************************************************//**
275  * Performs a read from the I2C device.
276  * The caller will be notified when the operation has completed (successfully) by an
277  * I2C_MASTER_EVENT_RX_COMPLETE in the callback.
278  *
279  * @retval  FSP_SUCCESS             Function executed without issue.
280  * @retval  FSP_ERR_ASSERTION       p_api_ctrl, p_dest or bytes is NULL.
281  * @retval  FSP_ERR_INVALID_SIZE    Provided number of bytes more than uint16_t size (65535) while DTC is used
282  *                                  for data transfer.
283  * @retval  FSP_ERR_IN_USE          Bus busy condition. Another transfer was in progress.
284  * @retval  FSP_ERR_NOT_OPEN        Handle is not initialized.  Call R_IIC_MASTER_Open to initialize the control block.
285  **********************************************************************************************************************/
R_IIC_MASTER_Read(i2c_master_ctrl_t * const p_api_ctrl,uint8_t * const p_dest,uint32_t const bytes,bool const restart)286 fsp_err_t R_IIC_MASTER_Read (i2c_master_ctrl_t * const p_api_ctrl,
287                              uint8_t * const           p_dest,
288                              uint32_t const            bytes,
289                              bool const                restart)
290 {
291 #if IIC_MASTER_CFG_PARAM_CHECKING_ENABLE
292     FSP_ASSERT(p_api_ctrl != NULL);
293     FSP_ASSERT(bytes != 0U);
294 #endif
295     fsp_err_t err = FSP_SUCCESS;
296 
297     /* Record the restart information about this transfer.
298      * This is done here to keep the parameter (argument) list of iic_master_read_write to 4. */
299     ((iic_master_instance_ctrl_t *) p_api_ctrl)->restart = restart;
300 
301     /* Call the common helper function to perform I2C Read operation.*/
302     err = iic_master_read_write(p_api_ctrl, p_dest, bytes, IIC_MASTER_TRANSFER_DIR_READ);
303 
304     return err;
305 }
306 
307 /*******************************************************************************************************************//**
308  * Performs a write to the I2C device.
309  * The caller will be notified when the operation has completed (successfully) by an
310  * I2C_MASTER_EVENT_TX_COMPLETE in the callback.
311  *
312  * @retval  FSP_SUCCESS           Function executed without issue.
313  * @retval  FSP_ERR_ASSERTION     p_api_ctrl or p_src is NULL.
314  * @retval  FSP_ERR_INVALID_SIZE  Provided number of bytes more than uint16_t size (65535) while DTC is used
315  *                                for data transfer.
316  * @retval  FSP_ERR_IN_USE        Bus busy condition. Another transfer was in progress.
317  * @retval  FSP_ERR_NOT_OPEN      Handle is not initialized.  Call R_IIC_MASTER_Open to initialize the control block.
318  **********************************************************************************************************************/
R_IIC_MASTER_Write(i2c_master_ctrl_t * const p_api_ctrl,uint8_t * const p_src,uint32_t const bytes,bool const restart)319 fsp_err_t R_IIC_MASTER_Write (i2c_master_ctrl_t * const p_api_ctrl,
320                               uint8_t * const           p_src,
321                               uint32_t const            bytes,
322                               bool const                restart)
323 {
324 #if IIC_MASTER_CFG_PARAM_CHECKING_ENABLE
325     FSP_ASSERT(p_api_ctrl != NULL);
326 #endif
327     fsp_err_t err = FSP_SUCCESS;
328 
329     /* Record the restart information about this transfer.
330      * This is done here to keep the parameter (argument) list of iic_master_read_write to 4. */
331     ((iic_master_instance_ctrl_t *) p_api_ctrl)->restart = restart;
332 
333     /* Call the common helper function to perform I2C Write operation.*/
334     err = iic_master_read_write(p_api_ctrl, p_src, bytes, IIC_MASTER_TRANSFER_DIR_WRITE);
335 
336     return err;
337 }
338 
339 /*******************************************************************************************************************//**
340  * Safely aborts any in-progress transfer and forces the IIC peripheral into ready state.
341  *
342  *
343  * @retval  FSP_SUCCESS             Channel was reset successfully.
344  * @retval  FSP_ERR_ASSERTION       p_api_ctrl is NULL.
345  * @retval  FSP_ERR_NOT_OPEN        Handle is not initialized.  Call R_IIC_MASTER_Open to initialize the control block.
346  *
347  * @note A callback will not be invoked in case an in-progress transfer gets aborted by calling this API.
348  **********************************************************************************************************************/
R_IIC_MASTER_Abort(i2c_master_ctrl_t * const p_api_ctrl)349 fsp_err_t R_IIC_MASTER_Abort (i2c_master_ctrl_t * const p_api_ctrl)
350 {
351     iic_master_instance_ctrl_t * p_ctrl = (iic_master_instance_ctrl_t *) p_api_ctrl;
352 
353 #if IIC_MASTER_CFG_PARAM_CHECKING_ENABLE
354     FSP_ASSERT(p_ctrl != NULL);
355     FSP_ERROR_RETURN(IIC_MASTER_OPEN == p_ctrl->open, FSP_ERR_NOT_OPEN);
356 #endif
357 
358     /* Abort any transfer happening on the channel */
359     iic_master_abort_seq_master(p_ctrl, true);
360 
361     return FSP_SUCCESS;
362 }
363 
364 /*******************************************************************************************************************//**
365  * Sets address and addressing mode of the slave device.
366  * This function is used to set the device address and addressing mode of the slave
367  * without reconfiguring the entire bus.
368  *
369  * @retval  FSP_SUCCESS             Address of the slave is set correctly.
370  * @retval  FSP_ERR_ASSERTION       Pointer to control structure is NULL.
371  * @retval  FSP_ERR_IN_USE          Another transfer was in-progress.
372  * @retval  FSP_ERR_NOT_OPEN        Handle is not initialized.  Call R_IIC_MASTER_Open to initialize the control block.
373  **********************************************************************************************************************/
R_IIC_MASTER_SlaveAddressSet(i2c_master_ctrl_t * const p_api_ctrl,uint32_t const slave,i2c_master_addr_mode_t const addr_mode)374 fsp_err_t R_IIC_MASTER_SlaveAddressSet (i2c_master_ctrl_t * const    p_api_ctrl,
375                                         uint32_t const               slave,
376                                         i2c_master_addr_mode_t const addr_mode)
377 {
378     iic_master_instance_ctrl_t * p_ctrl = (iic_master_instance_ctrl_t *) p_api_ctrl;
379 
380     fsp_err_t err = FSP_SUCCESS;
381 
382 #if IIC_MASTER_CFG_PARAM_CHECKING_ENABLE
383     FSP_ASSERT(p_ctrl != NULL);
384     FSP_ERROR_RETURN(IIC_MASTER_OPEN == p_ctrl->open, FSP_ERR_NOT_OPEN);
385 
386     /* Fail if there is already a transfer in progress */
387     FSP_ERROR_RETURN(((0 == p_ctrl->remain) && (false == p_ctrl->restart)), FSP_ERR_IN_USE);
388 #endif
389 
390     /* Sets the address of the slave device */
391     p_ctrl->slave = slave;
392 
393     /* Sets the mode of addressing */
394     p_ctrl->addr_mode = addr_mode;
395 
396     return err;
397 }
398 
399 /*******************************************************************************************************************//**
400  * Updates the user callback and has option of providing memory for callback structure.
401  * Implements i2c_master_api_t::callbackSet
402  *
403  * @retval  FSP_SUCCESS                  Callback updated successfully.
404  * @retval  FSP_ERR_ASSERTION            A required pointer is NULL.
405  * @retval  FSP_ERR_NOT_OPEN             The control block has not been opened.
406  * @retval  FSP_ERR_NO_CALLBACK_MEMORY   p_callback is non-secure and p_callback_memory is either secure or NULL.
407  **********************************************************************************************************************/
R_IIC_MASTER_CallbackSet(i2c_master_ctrl_t * const p_api_ctrl,void (* p_callback)(i2c_master_callback_args_t *),void const * const p_context,i2c_master_callback_args_t * const p_callback_memory)408 fsp_err_t R_IIC_MASTER_CallbackSet (i2c_master_ctrl_t * const          p_api_ctrl,
409                                     void (                           * p_callback)(i2c_master_callback_args_t *),
410                                     void const * const                 p_context,
411                                     i2c_master_callback_args_t * const p_callback_memory)
412 {
413     iic_master_instance_ctrl_t * p_ctrl = (iic_master_instance_ctrl_t *) p_api_ctrl;
414 
415 #if (IIC_MASTER_CFG_PARAM_CHECKING_ENABLE)
416     FSP_ASSERT(p_ctrl);
417     FSP_ASSERT(p_callback);
418     FSP_ERROR_RETURN(IIC_MASTER_OPEN == p_ctrl->open, FSP_ERR_NOT_OPEN);
419 #endif
420 
421 #if BSP_TZ_SECURE_BUILD
422 
423     /* Get security state of p_callback */
424     bool callback_is_secure =
425         (NULL == cmse_check_address_range((void *) p_callback, sizeof(void *), CMSE_AU_NONSECURE));
426 
427  #if IIC_MASTER_CFG_PARAM_CHECKING_ENABLE
428 
429     /* In secure projects, p_callback_memory must be provided in non-secure space if p_callback is non-secure */
430     i2c_master_callback_args_t * const p_callback_memory_checked = cmse_check_pointed_object(p_callback_memory,
431                                                                                              CMSE_AU_NONSECURE);
432     FSP_ERROR_RETURN(callback_is_secure || (NULL != p_callback_memory_checked), FSP_ERR_NO_CALLBACK_MEMORY);
433  #endif
434 #endif
435 
436     /* Store callback and context */
437 #if BSP_TZ_SECURE_BUILD
438     p_ctrl->p_callback = callback_is_secure ? p_callback :
439                          (void (*)(i2c_master_callback_args_t *))cmse_nsfptr_create(p_callback);
440 #else
441     p_ctrl->p_callback = p_callback;
442 #endif
443     p_ctrl->p_context         = p_context;
444     p_ctrl->p_callback_memory = p_callback_memory;
445 
446     return FSP_SUCCESS;
447 }
448 
449 /*******************************************************************************************************************//**
450  * Provides driver status.
451  *
452  * @retval     FSP_SUCCESS                   Status stored in p_status.
453  * @retval     FSP_ERR_ASSERTION             NULL pointer.
454  **********************************************************************************************************************/
R_IIC_MASTER_StatusGet(i2c_master_ctrl_t * const p_api_ctrl,i2c_master_status_t * p_status)455 fsp_err_t R_IIC_MASTER_StatusGet (i2c_master_ctrl_t * const p_api_ctrl, i2c_master_status_t * p_status)
456 {
457     iic_master_instance_ctrl_t * p_ctrl = (iic_master_instance_ctrl_t *) p_api_ctrl;
458 
459 #if IIC_MASTER_CFG_PARAM_CHECKING_ENABLE
460     FSP_ASSERT(p_ctrl != NULL);
461     FSP_ASSERT(p_status != NULL);
462 #endif
463 
464     p_status->open = (IIC_MASTER_OPEN == p_ctrl->open);
465 
466     return FSP_SUCCESS;
467 }
468 
469 /*******************************************************************************************************************//**
470  * Closes the I2C device. May power down IIC peripheral.
471  * This function will safely terminate any in-progress I2C transfers.
472  *
473  * @retval  FSP_SUCCESS         Device closed without issue.
474  * @retval  FSP_ERR_ASSERTION   p_api_ctrl is NULL.
475  * @retval  FSP_ERR_NOT_OPEN    Handle is not initialized.  Call R_IIC_MASTER_Open to initialize the control block.
476  *
477  * @note A callback will not be invoked in case an in-progress transfer gets aborted by calling this API.
478  **********************************************************************************************************************/
R_IIC_MASTER_Close(i2c_master_ctrl_t * const p_api_ctrl)479 fsp_err_t R_IIC_MASTER_Close (i2c_master_ctrl_t * const p_api_ctrl)
480 {
481     iic_master_instance_ctrl_t * p_ctrl = (iic_master_instance_ctrl_t *) p_api_ctrl;
482 
483 #if IIC_MASTER_CFG_PARAM_CHECKING_ENABLE
484     FSP_ASSERT(p_ctrl != NULL);
485     FSP_ERROR_RETURN(IIC_MASTER_OPEN == p_ctrl->open, FSP_ERR_NOT_OPEN);
486 #endif
487 
488     /* Abort an in-progress transfer with this device only */
489     iic_master_abort_seq_master(p_ctrl, true);
490 
491     /* Disable I2C interrupts. Described in hardware manual (see Section 36.2.8
492      * 'I2C Bus Interrupt Enable Register (ICIER)' of the RA6M3 manual R01UH0886EJ0100). */
493     p_ctrl->p_reg->ICIER = 0x00;
494 
495     /* The device is now considered closed */
496     p_ctrl->open = 0U;
497 
498 #if IIC_MASTER_CFG_DTC_ENABLE
499 
500     /* Close the handles for the transfer interfaces */
501     if (NULL != p_ctrl->p_cfg->p_transfer_rx)
502     {
503         p_ctrl->p_cfg->p_transfer_rx->p_api->close(p_ctrl->p_cfg->p_transfer_rx->p_ctrl);
504     }
505 
506     if (NULL != p_ctrl->p_cfg->p_transfer_tx)
507     {
508         p_ctrl->p_cfg->p_transfer_tx->p_api->close(p_ctrl->p_cfg->p_transfer_tx->p_ctrl);
509     }
510 #endif
511 
512     R_BSP_IrqDisable(p_ctrl->p_cfg->eri_irq);
513     R_BSP_IrqDisable(p_ctrl->p_cfg->rxi_irq);
514     R_BSP_IrqDisable(p_ctrl->p_cfg->tei_irq);
515     R_BSP_IrqDisable(p_ctrl->p_cfg->txi_irq);
516 
517     R_BSP_MODULE_STOP(FSP_IP_IIC, p_ctrl->p_cfg->channel);
518 
519     return FSP_SUCCESS;
520 }
521 
522 /*******************************************************************************************************************//**
523  * @} (end addtogroup IIC_MASTER)
524  **********************************************************************************************************************/
525 
526 /***********************************************************************************************************************
527  * Private Functions
528  **********************************************************************************************************************/
529 
530 /*******************************************************************************************************************//**
531  * Helper function for handling I2C Read or Write.
532  *
533  * @param      p_api_ctrl      Pointer to control block
534  * @param      p_buffer        Pointer to the buffer to store read/write data.
535  * @param[in]  bytes           Number of bytes to be read/written.
536  * @param[in]  direction       Read or Write
537  *
538  * @retval  FSP_SUCCESS           Function executed successfully.
539  * @retval  FSP_ERR_ASSERTION     p_api_ctrl or p_buffer is NULL.
540  * @retval  FSP_ERR_INVALID_SIZE  Provided number of bytes more than UINT16_MAX(= 65535) while DTC is used
541  *                                for data transfer.
542  * @retval  FSP_ERR_IN_USE        Another transfer was in progress.
543  * @retval  FSP_ERR_NOT_OPEN      Handle is not initialized. Call R_IIC_MASTER_Open to initialize the control block.
544  **********************************************************************************************************************/
iic_master_read_write(i2c_master_ctrl_t * const p_api_ctrl,uint8_t * const p_buffer,uint32_t const bytes,iic_master_transfer_dir_t direction)545 static fsp_err_t iic_master_read_write (i2c_master_ctrl_t * const p_api_ctrl,
546                                         uint8_t * const           p_buffer,
547                                         uint32_t const            bytes,
548                                         iic_master_transfer_dir_t direction)
549 {
550     iic_master_instance_ctrl_t * p_ctrl = (iic_master_instance_ctrl_t *) p_api_ctrl;
551 
552 #if IIC_MASTER_CFG_PARAM_CHECKING_ENABLE
553     FSP_ASSERT(p_buffer != NULL);
554     FSP_ERROR_RETURN((p_ctrl->open == IIC_MASTER_OPEN), FSP_ERR_NOT_OPEN);
555     FSP_ASSERT(((iic_master_instance_ctrl_t *) p_api_ctrl)->p_callback != NULL);
556  #if IIC_MASTER_CFG_DTC_ENABLE
557 
558     /* DTC on RX could actually receive 65535+3 = 65538 bytes as 3 bytes are handled separately.
559      * Forcing to 65535 to keep TX and RX uniform with respect to max transaction length via DTC.
560      */
561     FSP_ERROR_RETURN((bytes <= UINT16_MAX), FSP_ERR_INVALID_SIZE);
562  #endif
563 #endif
564 
565     fsp_err_t err = FSP_SUCCESS;
566 
567     p_ctrl->p_buff = p_buffer;
568     p_ctrl->total  = bytes;
569 
570     /* Handle the (different) addressing mode(s) */
571     if (p_ctrl->addr_mode == I2C_MASTER_ADDR_MODE_7BIT)
572     {
573         /* Set the address bytes according to a 7-bit slave read command */
574         p_ctrl->addr_high  = 0U;
575         p_ctrl->addr_low   = (uint8_t) ((p_ctrl->slave << 1U) | (uint8_t) direction);
576         p_ctrl->addr_total = 1U;
577     }
578 
579 #if IIC_MASTER_CFG_ADDR_MODE_10_BIT_ENABLE
580     else
581     {
582         /* Set the address bytes according to a 10-bit slave read command */
583         p_ctrl->addr_high = (uint8_t) (((p_ctrl->slave >> 7U) | I2C_CODE_10BIT) & (uint8_t) ~(I2C_CODE_READ));
584         p_ctrl->addr_low  = (uint8_t) p_ctrl->slave;
585 
586         /* Addr total = 3 for Read and 2 for Write.
587          * See Section 36.3.1 "Communication Data Format" of the RA6M3 manual R01UH0886EJ0100
588          */
589         p_ctrl->addr_total = (uint8_t) ((uint8_t) direction + IIC_MASTER_SLAVE_10_BIT_ADDR_LEN_ADJUST);
590     }
591 #endif
592 
593     p_ctrl->read = (bool) direction;
594 
595     /* Kickoff the read operation as a master */
596     err = iic_master_run_hw_master(p_ctrl);
597 
598     FSP_ERROR_RETURN(FSP_SUCCESS == err, err);
599 
600     return FSP_SUCCESS;
601 }
602 
603 /*******************************************************************************************************************//**
604  * Single point for managing the logic around notifying a transfer has finished.
605  *
606  * @param[in]       p_ctrl      Pointer to transfer that is ending.
607  * @param[in]       event       The event code to pass to the callback.
608  **********************************************************************************************************************/
iic_master_notify(iic_master_instance_ctrl_t * const p_ctrl,i2c_master_event_t const event)609 static void iic_master_notify (iic_master_instance_ctrl_t * const p_ctrl, i2c_master_event_t const event)
610 {
611     i2c_master_callback_args_t args;
612 
613     /* Store callback arguments in memory provided by user if available.  This allows callback arguments to be
614      * stored in non-secure memory so they can be accessed by a non-secure callback function. */
615     i2c_master_callback_args_t * p_args = p_ctrl->p_callback_memory;
616     if (NULL == p_args)
617     {
618         /* Store on stack */
619         p_args = &args;
620     }
621     else
622     {
623         /* Save current arguments on the stack in case this is a nested interrupt. */
624         args = *p_args;
625     }
626 
627     p_args->p_context = p_ctrl->p_context;
628     p_args->event     = event;
629 
630 #if IIC_MASTER_CFG_DTC_ENABLE
631 
632     /* Stop any DTC assisted transfer for tx */
633     const transfer_instance_t * p_transfer_tx = p_ctrl->p_cfg->p_transfer_tx;
634     if ((NULL != p_transfer_tx) && (!p_ctrl->read))
635     {
636         p_transfer_tx->p_api->disable(p_transfer_tx->p_ctrl);
637     }
638 
639     /* Stop any DTC assisted transfer for rx */
640     const transfer_instance_t * p_transfer_rx = p_ctrl->p_cfg->p_transfer_rx;
641     if ((NULL != p_transfer_rx) && (p_ctrl->read))
642     {
643         p_transfer_rx->p_api->disable(p_transfer_rx->p_ctrl);
644     }
645 #endif
646 
647     /* Now do the callback here */
648 #if BSP_TZ_SECURE_BUILD
649 
650     /* p_callback can point to a secure function or a non-secure function. */
651     if (!cmse_is_nsfptr(p_ctrl->p_callback))
652     {
653         /* If p_callback is secure, then the project does not need to change security state. */
654         p_ctrl->p_callback(p_args);
655     }
656     else
657     {
658         /* If p_callback is Non-secure, then the project must change to Non-secure state in order to call the callback. */
659         iic_master_prv_ns_callback p_callback = (iic_master_prv_ns_callback) (p_ctrl->p_callback);
660         p_callback(p_args);
661     }
662 
663 #else
664 
665     /* If the project is not Trustzone Secure, then it will never need to change security state in order to call the callback. */
666     p_ctrl->p_callback(p_args);
667 #endif
668 
669     if (NULL != p_ctrl->p_callback_memory)
670     {
671         /* Restore callback memory in case this is a nested interrupt. */
672         *p_ctrl->p_callback_memory = args;
673     }
674 
675     /* Clear the err flags */
676     p_ctrl->err = false;
677 }
678 
679 /*******************************************************************************************************************//**
680  * Single point for managing the logic around aborting a transfer when operating as a master.
681  *
682  * @param[in]       p_ctrl  Pointer to control structure of specific device.
683  * @param[in]       iic_reset  Flag to enable IIC reset
684  **********************************************************************************************************************/
iic_master_abort_seq_master(iic_master_instance_ctrl_t * const p_ctrl,bool iic_reset)685 static void iic_master_abort_seq_master (iic_master_instance_ctrl_t * const p_ctrl, bool iic_reset)
686 {
687     /* Safely stop the hardware from operating. */
688 
689     /* Reset the peripheral */
690     if (true == iic_reset)
691     {
692         /* Disable channel interrupts */
693         p_ctrl->p_reg->ICIER = 0x00;
694 
695         /* This helper function would do a full IIC reset
696          * followed by re-initializing the required peripheral registers. */
697         iic_master_open_hw_master(p_ctrl, p_ctrl->p_cfg);
698     }
699 
700     /* Update the transfer descriptor to show no longer in-progress and an error */
701     p_ctrl->remain = 0U;
702 
703     /* Update the transfer descriptor to make sure interrupts no longer process */
704     p_ctrl->addr_loaded = p_ctrl->addr_total;
705     p_ctrl->loaded      = p_ctrl->total;
706     p_ctrl->restarted   = false;
707     p_ctrl->restart     = false;
708 
709     /* Enable Interrupts: TMOIE, ALIE, NAKIE, RIE, TIE.
710      * Disable Interrupt: TEIE, STIE, SPIE
711      * (see Section 36.2.8 'I2C Bus Interrupt Enable Register (ICIER)' of the RA6M3 manual R01UH0886EJ0100).
712      */
713     p_ctrl->p_reg->ICIER = IIC_MASTER_INTERRUPT_ENABLE_INIT_MASK;
714 }
715 
716 /*******************************************************************************************************************//**
717  * Performs the hardware initialization sequence when operating as a master (see Section 36.3.2
718  * 'Initial Settings' of the RA6M3 manual R01UH0886EJ0100).
719  *
720  * @param[in]  p_ctrl                Pointer to IIC specific control structure
721  * @param[in]  p_cfg                 Pointer to IIC specific configuration structure.
722  **********************************************************************************************************************/
iic_master_open_hw_master(iic_master_instance_ctrl_t * const p_ctrl,i2c_master_cfg_t const * const p_cfg)723 static void iic_master_open_hw_master (iic_master_instance_ctrl_t * const p_ctrl, i2c_master_cfg_t const * const p_cfg)
724 {
725     /* Perform IIC reset */
726     p_ctrl->p_reg->ICCR1 = (uint8_t) IIC_MASTER_PRV_SCL_SDA_NOT_DRIVEN;
727 
728     /* Reset */
729     p_ctrl->p_reg->ICCR1 = (uint8_t) (IIC_MASTER_ICCR1_IICRST_BIT_MASK | IIC_MASTER_PRV_SCL_SDA_NOT_DRIVEN);
730 
731     /* Come out of IIC reset to internal reset */
732     p_ctrl->p_reg->ICCR1 =
733         (uint8_t) (IIC_MASTER_ICCR1_ICE_BIT_MASK | IIC_MASTER_ICCR1_IICRST_BIT_MASK |
734                    IIC_MASTER_PRV_SCL_SDA_NOT_DRIVEN);
735 
736     /* Configure the clock settings. This is set in the configuration structure by the tooling. */
737     /* Set the number of counts that the clock remains low, bit 7 to 5 should be written as 1 */
738     p_ctrl->p_reg->ICBRL =
739         (uint8_t) (IIC_MASTER_BUS_RATE_REG_RESERVED_BITS |
740                    ((iic_master_extended_cfg_t *) p_ctrl->p_cfg->p_extend)->clock_settings.brl_value);
741 
742     /* Set the number of counts that the clock remains high, bit 7 to 5 should be written as 1 */
743     p_ctrl->p_reg->ICBRH = (uint8_t) (IIC_MASTER_BUS_RATE_REG_RESERVED_BITS |
744                                       ((iic_master_extended_cfg_t *) p_ctrl->p_cfg->p_extend)->clock_settings.brh_value);
745 
746     /* Set the internal reference clock source for generating IIC clock */
747     p_ctrl->p_reg->ICMR1 = (uint8_t) (IIC_MASTER_BUS_MODE_REGISTER_1_MASK |
748                                       (uint8_t) ((((iic_master_extended_cfg_t *) p_ctrl->p_cfg->p_extend)->
749                                                   clock_settings.
750                                                   cks_value &
751                                                   IIC_MASTER_INTERNAL_REF_CLOCK_SELECT_MAX) << 4U));
752 
753     /* Allow timeouts to be generated on the low value of SCL using either long or short mode */
754 
755     /* TMOL 'Timeout L Count Control' and TMOH 'Timeout H Count Control' will be set at the time of I2C reset.
756      * This will enable time out detection for both SCLn high and low.
757      * Only Set/Clear TMOS here to select long or short mode.
758      * (see Section 36.2.4 'I2C Bus Mode Register 2 (ICMR2)' of the RA6M3 manual R01UH0886EJ0100).
759      */
760     p_ctrl->p_reg->ICMR2 = (uint8_t) (IIC_MASTER_BUS_MODE_REGISTER_2_MASK |
761                                       (uint8_t) (IIC_MASTER_TIMEOUT_MODE_SHORT ==
762                                                  ((iic_master_extended_cfg_t *) p_ctrl->p_cfg->p_extend)->timeout_mode)
763                                       |
764                                       (uint8_t) (((iic_master_extended_cfg_t *) p_ctrl->p_cfg->p_extend)->
765                                                  timeout_scl_low << R_IIC0_ICMR2_TMOL_Pos));
766 
767     /* ICFER Register Settings:
768      * 1. Enable timeout function.
769      * 2. Enable master arbitration loss detection.
770      * 3. Enable NACK arbitration loss detection.
771      * 4. Disable Slave arbitration loss detection.
772      * 5. Enable NACK reception transfer suspension.
773      * 6. Use the digital noise filter circuit. Upon I2C reset, 'NF[1:0] Noise Filter Stage Select' will be set to 0x00
774      * This would imply  'Filter out noise of up to 1 IIC cycle (single-stage filter)'
775      * (see Section 36.2.5 'I2C Bus Mode Register 3 (ICMR3)' of the RA6M3 manual R01UH0886EJ0100)
776      * 7. Do not use the SCL synchronous circuit.
777      * 8. Enable FM+ slope circuit if fast mode plus is enabled.
778      * (see Section 36.2.6 'I2C Bus Function Enable Register' of the RA6M3 manual R01UH0886EJ0100 for more details)
779      */
780     p_ctrl->p_reg->ICFER =
781         (uint8_t) ((uint8_t) (I2C_MASTER_RATE_FASTPLUS ==
782                               p_ctrl->p_cfg->rate) << 7U) | IIC_MASTER_FUNCTION_ENABLE_INIT_SETTINGS;
783 
784     /* Ensure the HW is in master mode and does not behave as a slave to another master on the same channel. */
785     p_ctrl->p_reg->ICSER = 0x00;
786 
787     /* Enable Interrupts: TMOIE, ALIE, NAKIE, RIE, TIE.
788      * Disable Interrupt: TEIE, STIE, SPIE
789      * (see Section 36.2.8 'I2C Bus Interrupt Enable Register (ICIER)' of the RA6M3 manual R01UH0886EJ0100).
790      */
791     p_ctrl->p_reg->ICIER = IIC_MASTER_INTERRUPT_ENABLE_INIT_MASK;
792 
793     /* Set valid interrupt contexts and user provided priority. Enable the interrupts at the NVIC  */
794     R_BSP_IrqCfgEnable(p_cfg->eri_irq, p_cfg->ipl, p_ctrl);
795     R_BSP_IrqCfgEnable(p_cfg->txi_irq, p_cfg->ipl, p_ctrl);
796     R_BSP_IrqCfgEnable(p_cfg->tei_irq, p_cfg->ipl, p_ctrl);
797     R_BSP_IrqCfgEnable(p_cfg->rxi_irq, p_cfg->ipl, p_ctrl);
798 
799     /* Release IIC from internal reset */
800 
801     /* Reset */
802     p_ctrl->p_reg->ICCR1 = (uint8_t) (IIC_MASTER_ICCR1_ICE_BIT_MASK | IIC_MASTER_PRV_SCL_SDA_NOT_DRIVEN);
803 }
804 
805 /*******************************************************************************************************************//**
806  * Performs the data transfer described by the parameters when operating as a master.
807  * See 36.3.3 "Master Transmit Operation" and section 36.3.4 "Master Receive Operation"
808  * of the RA6M3 manual R01UH0886EJ0100
809  *
810  * @param[in]       p_ctrl  Pointer to control structure of specific device.
811  *
812  * @retval  FSP_SUCCESS       Data transfer success.
813  * @retval  FSP_ERR_IN_USE    If data transfer is in progress.
814  **********************************************************************************************************************/
iic_master_run_hw_master(iic_master_instance_ctrl_t * const p_ctrl)815 static fsp_err_t iic_master_run_hw_master (iic_master_instance_ctrl_t * const p_ctrl)
816 {
817     /* IICn operates using PCLKB. The ratio ICLK (System Clock)/PCLKB gives the CPU cycles for 1 ICBRL count.
818      * (ICLK/PCLKB)*ICBRL gives the CPU cycles for entire ICBRL count.
819      * Since each time we loop the timeout count will be decremented by 1 this would require at least 4 CPU clocks,
820      * making the final timeout count as:
821      * Timeout = ((ICLK/PCLKB)*ICBRL)/4.
822      */
823     volatile uint32_t sysdiccr = FSP_STYPE3_REG8_READ(R_SYSTEM->SCKDIVCR, BSP_CFG_CLOCKS_SECURE);
824     sysdiccr &= (IIC_MASTER_SYSDIVCK_ICLK_MASK | IIC_MASTER_SYSDIVCK_PCLKB_MASK);
825     uint32_t pclkb         = (IIC_MASTER_SYSDIVCK_PCLKB_MASK & sysdiccr) >> 8U;
826     uint32_t iclk          = sysdiccr >> 24U;
827     uint32_t timeout_count = ((1U << (pclkb - iclk)) * p_ctrl->p_reg->ICBRL) >> 2U;
828 
829     /* Check if this is a new transaction or a continuation */
830     if (!p_ctrl->restarted)
831     {
832         /* As per BBSY clearing conditions in section 36.2.2 of the RA6M3 manual R01UH0886EJ0100,
833          * the BBSY bit is 0 after the bus free time (ICBRL setting)
834          * if a start condition is not detected after a stop condition detection.
835          */
836         IIC_MASTER_HARDWARE_REGISTER_WAIT(p_ctrl->p_reg->ICCR2_b.BBSY, 0U, timeout_count);
837 
838         /* If bus is busy, return error */
839         FSP_ERROR_RETURN((0U != timeout_count), FSP_ERR_IN_USE);
840 
841         /* This is not a restarted transaction. Enable TXI for the next transfer.
842          * This had been disabled at the end of TXI interrupt.
843          * The intention is to only enable IIC_MASTER_TXI_EN_BIT.
844          * Writing the whole mask - IIC_MASTER_INTERRUPT_ENABLE_INIT_MASK saves cycles.
845          */
846         p_ctrl->p_reg->ICIER = IIC_MASTER_INTERRUPT_ENABLE_INIT_MASK;
847     }
848 
849     /* Initialize fields used during transfer */
850     p_ctrl->addr_loaded          = 0U;
851     p_ctrl->loaded               = 0U;
852     p_ctrl->remain               = p_ctrl->total;
853     p_ctrl->addr_remain          = p_ctrl->addr_total;
854     p_ctrl->err                  = false;
855     p_ctrl->dummy_read_completed = false;
856     p_ctrl->activation_on_rxi    = false;
857     p_ctrl->activation_on_txi    = false;
858     p_ctrl->address_restarted    = false;
859 
860     /* Allow timeouts to be generated on the low value of SCL using either short or long mode.
861      * This gets disabled in case the previous transaction issues a restart.
862      */
863 
864     /* TMOL 'Timeout L Count Control' and TMOH 'Timeout H Count Control' will be set at the time of I2C reset.
865      * This will enable time out detection for both SCLn high and low.
866      * Only Set/Clear TMOS here to select long or short mode.
867      * (see Section 36.2.4 'I2C Bus Mode Register 2 (ICMR2)' of the RA6M3 manual R01UH0886EJ0100).
868      */
869     p_ctrl->p_reg->ICMR2 = (uint8_t) (IIC_MASTER_BUS_MODE_REGISTER_2_MASK |
870                                       (uint8_t) (IIC_MASTER_TIMEOUT_MODE_SHORT ==
871                                                  ((iic_master_extended_cfg_t *) p_ctrl->p_cfg->p_extend)->timeout_mode)
872                                       |
873                                       (uint8_t) (((iic_master_extended_cfg_t *) p_ctrl->p_cfg->p_extend)->
874                                                  timeout_scl_low << R_IIC0_ICMR2_TMOL_Pos));
875 
876     /* Set the response as ACK */
877     p_ctrl->p_reg->ICMR3_b.ACKWP = 1;  /* Write Enable */
878     p_ctrl->p_reg->ICMR3_b.ACKBT = 0;  /* Write */
879     p_ctrl->p_reg->ICMR3_b.ACKWP = 0;
880 
881     /* Enable timeout function */
882     p_ctrl->p_reg->ICFER_b.TMOE = 1U;
883 
884     /* Enable TXI. This is treated differently to support restart functionality.
885      * In case the previous IIC master transaction enabled restart, the queued TXI will fire a this point.
886      *
887      * The TXI had been NVIC-disabled (but Peripheral enabled) before setting the
888      * RS bit by the previous restart enabled transaction.
889      * The RS bit mimics a "stop" followed by a "start" and keeps the bus busy.
890      * As a part of the previous transaction, TXI fires at the peripheral level and is queued at the CPU.
891      *
892      * If the previous transaction was not restart enabled -
893      * NVIC-enable TXI which will fire after the start condition below.
894      */
895     NVIC_EnableIRQ(p_ctrl->p_cfg->txi_irq);
896 
897     /* Enable SPIE to detect unexpected STOP condition. This is disabled between communication events as it can lead
898      * to undesired interrupts in multi-master setups. */
899     p_ctrl->p_reg->ICIER = IIC_MASTER_INTERRUPT_ENABLE_INIT_MASK | R_IIC0_ICIER_STIE_Msk | R_IIC0_ICIER_SPIE_Msk;
900 
901     /* If previous transaction did not end with restart, send a start condition */
902     if (!p_ctrl->restarted)
903     {
904         /* Request IIC to issue the start condition */
905         p_ctrl->p_reg->ICCR2 = (uint8_t) IIC_MASTER_ICCR2_ST_BIT_MASK;
906     }
907     else
908     {
909         p_ctrl->restarted = false;
910     }
911 
912     /*
913      * The Flowchart under 36.3.3 "Master Transmit Operation" and section 36.3.4 "Master Receive Operation"
914      * of the RA6M3 manual R01UH0886EJ0100 is covered in the interrupts:
915      *
916      * 1. NACKF processing is handled in the ERI interrupt.
917      *    For receive, dummy reading ICDRR is not required because the NACK processing in this driver resets the IIC peripheral.
918      * 2. Data is written to ICDRT in the transmit interrupt (TDRE is set when a transmit interrupt fires).
919      * 3. For transmit, stop is issued in the transmit end interrupt (TEND is set when a transmit end interrupt fires).
920      * 4. For transmit, ICSR2 is cleared in the transmit end interrupt.
921      * 5. For receive, remaining processing including reading ICDRR happens in the receive interrupt (RDRF is set when a receive interrupt fires).
922      */
923     return FSP_SUCCESS;
924 }
925 
926 /*******************************************************************************************************************//**
927  * Handles the receive data full interrupt when operating as a master.
928  *
929  * @param[in]       p_ctrl     The target IIC block's control block.
930  **********************************************************************************************************************/
iic_master_rxi_master(iic_master_instance_ctrl_t * p_ctrl)931 static void iic_master_rxi_master (iic_master_instance_ctrl_t * p_ctrl)
932 {
933     volatile uint8_t dummy_read;
934 
935     /* First receive interrupt: Handle the special case of 1 or 2 byte read here */
936     if (false == p_ctrl->dummy_read_completed)
937     {
938         /* Enable WAIT for 1 or 2 byte read */
939         if (2U >= p_ctrl->total)
940         {
941             p_ctrl->p_reg->ICMR3_b.WAIT = 1;
942         }
943 
944         /* Enable NACK for 1 byte read */
945         if (1U == p_ctrl->remain)
946         {
947             /* Writes to be done separately.
948              * See Note 1 in Section 36.2.5 'I2C Bus Mode Register 3 (ICMR3)' of the RA6M3 manual R01UH0886EJ0100
949              */
950             p_ctrl->p_reg->ICMR3_b.ACKWP = 1; /* Write enable ACKBT */
951             p_ctrl->p_reg->ICMR3_b.ACKBT = 1;
952             p_ctrl->p_reg->ICMR3_b.ACKWP = 0;
953         }
954 
955 #if IIC_MASTER_CFG_DTC_ENABLE
956         uint8_t volatile const * p_iic_master_rx_buffer = &(p_ctrl->p_reg->ICDRR);
957 
958         /* Enable transfer support if possible */
959         if ((NULL != p_ctrl->p_cfg->p_transfer_rx) && (p_ctrl->read) && (p_ctrl->total > 3U))
960         {
961             p_ctrl->p_cfg->p_transfer_rx->p_api->reset(p_ctrl->p_cfg->p_transfer_rx->p_ctrl,
962                                                        (uint8_t *) (p_iic_master_rx_buffer),
963                                                        (void *) (p_ctrl->p_buff),
964                                                        (uint16_t) (p_ctrl->total - 3U));
965 
966             p_ctrl->remain            = 3U;
967             p_ctrl->loaded            = p_ctrl->total - 3U;
968             p_ctrl->activation_on_rxi = true;
969         }
970 #endif
971 
972         /* Do a dummy read to clock the data into the ICDRR. */
973         dummy_read = p_ctrl->p_reg->ICDRR;
974         FSP_PARAMETER_NOT_USED(dummy_read);
975 
976         /* Update the counter */
977         p_ctrl->dummy_read_completed = true;
978     }
979 
980 #if IIC_MASTER_CFG_DTC_ENABLE
981 
982     /* If this is the interrupt that got fired after DTC transfer,
983      * ignore it as the DTC has already taken care of the data transfer */
984     else if (true == p_ctrl->activation_on_rxi)
985     {
986         p_ctrl->activation_on_rxi = false;
987     }
988 #endif
989 
990     /* ICDRR contain valid received data */
991     else if (0U < p_ctrl->remain)
992     {
993         iic_master_rxi_read_data(p_ctrl);
994     }
995     else
996     {
997         /* Do nothing */
998     }
999 }
1000 
1001 /*******************************************************************************************************************//**
1002  * Handles the transmit data empty interrupt when operating as a master.
1003  *
1004  * @param[in]       p_ctrl     The target IIC block's control block.
1005  **********************************************************************************************************************/
iic_master_txi_master(iic_master_instance_ctrl_t * p_ctrl)1006 static void iic_master_txi_master (iic_master_instance_ctrl_t * p_ctrl)
1007 {
1008     uint32_t timeout_count = IIC_MASTER_PERIPHERAL_REG_MAX_WAIT;
1009 
1010     /* Check if we are issuing the slave address */
1011     if (0U < p_ctrl->addr_remain)
1012     {
1013         iic_master_txi_send_address(p_ctrl);
1014     }
1015     else if (!p_ctrl->read)
1016     {
1017 #if IIC_MASTER_CFG_DTC_ENABLE
1018 
1019         /* If this is the interrupt that got fired after DTC transfer,
1020          * ignore it as the DTC has already taken care of the data transfer */
1021         if (true == p_ctrl->activation_on_txi)
1022         {
1023             p_ctrl->activation_on_txi = false;
1024         }
1025         else if (p_ctrl->remain > 0U)
1026 #else
1027         if (p_ctrl->remain > 0U)
1028 #endif
1029         {
1030             /* Write the data to ICDRT register */
1031             p_ctrl->p_reg->ICDRT = p_ctrl->p_buff[p_ctrl->loaded];
1032 
1033             /* Update the number of bytes remaining for next pass */
1034             p_ctrl->loaded++;
1035             p_ctrl->remain--;
1036         }
1037         else
1038         {
1039             /* Do nothing */
1040         }
1041 
1042         /* We are done loading ICDRT, wait for TEND to send a stop/restart */
1043         if (0U == p_ctrl->remain)
1044         {
1045             p_ctrl->p_reg->ICIER_b.TIE = 0U;
1046 
1047             /* Wait for the value to reflect at the peripheral.
1048              * See 'Note' under Table 36.10 "Interrupt sources" of the RA6M3 manual R01UH0886EJ0100 */
1049             IIC_MASTER_HARDWARE_REGISTER_WAIT(p_ctrl->p_reg->ICIER_b.TIE, 0U, timeout_count);
1050 
1051             /* Enable the transmit end IRQ, to issue a STOP or RESTART */
1052             /* Clear any pending TEND interrupts */
1053             R_BSP_IrqStatusClear(p_ctrl->p_cfg->tei_irq);
1054             NVIC_ClearPendingIRQ(p_ctrl->p_cfg->tei_irq);
1055 
1056             /* Enable the TXEND interrupt */
1057             p_ctrl->p_reg->ICIER_b.TEIE = 1U;
1058 
1059             /* No need to wait to check TEIE has actually become 1U; because if that's not the case,
1060              * no other operation can occur at this point */
1061         }
1062     }
1063     else
1064     {
1065         /* Do nothing */
1066     }
1067 }
1068 
1069 /*******************************************************************************************************************//**
1070  * Handles the transmit end interrupt when operating as a master.
1071  * @note This interrupt is configured to be generated at the end of last byte of the requested transfer.
1072  *
1073  * @param[in]       p_ctrl     The target IIC block's control block.
1074  **********************************************************************************************************************/
iic_master_tei_master(iic_master_instance_ctrl_t * p_ctrl)1075 static void iic_master_tei_master (iic_master_instance_ctrl_t * p_ctrl)
1076 {
1077     uint32_t timeout_count = IIC_MASTER_PERIPHERAL_REG_MAX_WAIT;
1078 
1079     /* This is a 10 bit address read, issue a restart prior to the last address byte transmission  */
1080     if ((p_ctrl->read) && (p_ctrl->addr_remain == 1U) && (false == p_ctrl->address_restarted))
1081     {
1082 #if IIC_MASTER_CFG_ADDR_MODE_10_BIT_ENABLE
1083 
1084         /* Enable TXI so that it fires after restart condition. */
1085         p_ctrl->p_reg->ICIER_b.TIE = 1U;
1086 
1087         /* Request IIC to issue the restart condition */
1088         p_ctrl->p_reg->ICCR2      = (uint8_t) IIC_MASTER_ICCR2_RS_BIT_MASK;
1089         p_ctrl->address_restarted = true;
1090 #endif
1091     }
1092     /* We are done with the transfer, send STOP or RESTART */
1093     else if (0U == p_ctrl->remain)
1094     {
1095         /* Send RESTART */
1096         if (p_ctrl->restart)
1097         {
1098             /* NOTE:Only disable in NVIC, disabling in I2C would cause the
1099              * restart condition to fail because we are using the buffered
1100              * interrupt to start the next sequence */
1101             R_BSP_IrqDisable(p_ctrl->p_cfg->txi_irq);
1102             p_ctrl->p_reg->ICIER_b.TIE = 1U;
1103 
1104             /* Request IIC to issue the restart condition. At this point we will queue a TXI at the NVIC level. */
1105             p_ctrl->p_reg->ICCR2 = (uint8_t) IIC_MASTER_ICCR2_RS_BIT_MASK;
1106 
1107             /* Disable timeout function */
1108             p_ctrl->p_reg->ICFER_b.TMOE = 0;
1109 
1110             /* Remember that we issued a restart for the next transfer */
1111             p_ctrl->restarted = true;
1112         }
1113         /* Send STOP */
1114         else
1115         {
1116             /* Clear STOP flag and set SP.
1117              * It is ok to clear other status' as this transaction is over.
1118              */
1119             p_ctrl->p_reg->ICSR2 &= (uint8_t) ~(IIC_MASTER_ICSR2_STOP_BIT);;
1120 
1121             /* Request IIC to issue the stop condition */
1122             p_ctrl->p_reg->ICCR2 = (uint8_t) IIC_MASTER_ICCR2_SP_BIT_MASK; /* It is safe to write 0's to other bits. */
1123         }
1124     }
1125     else
1126     {
1127         /* Do nothing */
1128     }
1129 
1130     /* Disable the interrupt as we are done with the transfer */
1131     p_ctrl->p_reg->ICIER_b.TEIE = 0U;
1132 
1133     /* Wait for the value to reflect at the peripheral.
1134      * See 'Note' under Table 36.10 "Interrupt sources" of the RA6M3 manual R01UH0886EJ0100 */
1135     IIC_MASTER_HARDWARE_REGISTER_WAIT(p_ctrl->p_reg->ICIER_b.TEIE, 0U, timeout_count);
1136 }
1137 
1138 /*******************************************************************************************************************//**
1139  * Handles the error interrupts when operating as a master.
1140  *
1141  * @param[in]       p_ctrl  Pointer to transfer control block
1142  **********************************************************************************************************************/
iic_master_err_master(iic_master_instance_ctrl_t * p_ctrl)1143 static void iic_master_err_master (iic_master_instance_ctrl_t * p_ctrl)
1144 {
1145     /* Clear all the event flags except the receive data full, transmit end and transmit data empty flags*/
1146     uint8_t errs_events = IIC_MASTER_STATUS_REGISTER_2_ERR_MASK & p_ctrl->p_reg->ICSR2;
1147     p_ctrl->p_reg->ICSR2 &= (uint8_t) ~IIC_MASTER_STATUS_REGISTER_2_ERR_MASK;
1148 
1149     /* If the event was an error event, then handle it */
1150     if ((errs_events &
1151          (uint8_t) ((uint8_t) (IIC_MASTER_ERR_EVENT_TIMEOUT) | (uint8_t) (IIC_MASTER_ERR_EVENT_ARBITRATION_LOSS))) |
1152         ((errs_events & (uint8_t) (IIC_MASTER_ERR_EVENT_NACK)) && (1U != p_ctrl->p_reg->ICCR2_b.MST)))
1153     {
1154         /* Conditions to get here:
1155          * 1. This is Timeout and/or arbitration loss error during an ongoing transaction
1156          * 2. This is a NACK error and this device is no longer the active master on the bus.
1157          *    The MST bit here can get cleared:
1158          *     a. In case of an arbitration loss error.also occurs.
1159          *     b. If the slave timeout is lesser than master timeout and the slave releases
1160          *        the bus by performing an internal reset.
1161          *        Refer Section "I2C Bus Control Register 2 (ICCR2) - Clearing conditions for MST"
1162          *        of the RA6M3 manual R01UH0886EJ0100
1163          * 3. This is a Timeout error after attempting to issue a stop after detecting a NACK previously.
1164          *//* Set the error flag when an error event occurred */
1165         p_ctrl->err = true;
1166 
1167         /* Abort an in-progress transfer with the current device */
1168         iic_master_abort_seq_master(p_ctrl, true); /* This will reset the IIC Master driver */
1169         /* Notify anyone waiting that the transfer is Aborted due to error. */
1170         iic_master_notify(p_ctrl, I2C_MASTER_EVENT_ABORTED);
1171     }
1172     else if ((errs_events & (uint8_t) (IIC_MASTER_ERR_EVENT_NACK)) && (1U == p_ctrl->p_reg->ICCR2_b.MST))
1173     {
1174         /* MST bit must be set to issue a stop condition.
1175          * Refer Section "36.11.3 Issuing a Stop Condition" of the RA6M3 manual R01UH0886EJ0100
1176          */
1177 
1178         /* Set the error flag when an error event occurred
1179          * This will be checked after the stop condition is detected from the request below. */
1180         p_ctrl->err = true;
1181 
1182         /* The sequence below is to handle a NACK received from slave in the middle of a write.
1183          * See item '[4]' under 'Figure 36.6 Example master transmission flow' of the RA6M3 manual R01UH0886EJ0100 */
1184 
1185         /* Request IIC to issue the stop condition */
1186         p_ctrl->p_reg->ICCR2 = (uint8_t) IIC_MASTER_ICCR2_SP_BIT_MASK; /* It is safe to write 0's to other bits. */
1187         /* Allow timeouts to be generated on the low value of SCL using either long or short mode */
1188         p_ctrl->p_reg->ICMR2 = (uint8_t) 0x02U |
1189                                (uint8_t) (IIC_MASTER_TIMEOUT_MODE_SHORT ==
1190                                           ((iic_master_extended_cfg_t *) p_ctrl->p_cfg->p_extend)->timeout_mode);
1191         p_ctrl->p_reg->ICFER_b.TMOE = 1;
1192 
1193         /* This interrupt will be fired again when wither stop condition is sent
1194          * or the hardware detects the line is stuck low causing a timeout */
1195     }
1196     /* This is a STOP, START or RESTART event. We need to process these events only at the
1197      * end of the requisite transfers.
1198      * NOTE: Do not use p_transfer->loaded or p_transfer->remain to check whether the transfer is
1199      * completed, since using them would lead to a race condition between txi and eri interrupts in case
1200      * of one byte transfer which will result in BUS arbitration loss error */
1201     else if ((errs_events & (uint8_t) IIC_MASTER_ERR_EVENT_STOP) ||
1202              ((p_ctrl->restarted) && (errs_events & (uint8_t) IIC_MASTER_ERR_EVENT_START)))
1203     {
1204         i2c_master_event_t event = I2C_MASTER_EVENT_ABORTED;
1205         if (false == p_ctrl->err)      /* Successful transaction */
1206         {
1207             /* Get the correct event to notify the user */
1208             event = (p_ctrl->read) ? I2C_MASTER_EVENT_RX_COMPLETE : I2C_MASTER_EVENT_TX_COMPLETE;
1209 
1210             /* Disable STIE/SPIE to prevent errant interrupts in multi-master scenarios */
1211             p_ctrl->p_reg->ICIER = IIC_MASTER_INTERRUPT_ENABLE_INIT_MASK;
1212         }
1213         else if ((errs_events & (uint8_t) IIC_MASTER_ERR_EVENT_STOP))
1214         {
1215             /* This is the STOP condition requested due to a NACK error earlier.
1216              * Since the stop condition is successfully issued there is no need to reset the driver.
1217              */
1218             iic_master_abort_seq_master(p_ctrl, false); /* Clear the transaction flags only */
1219         }
1220         else
1221         {
1222             /* Do nothing */
1223         }
1224 
1225         /* Notify anyone waiting */
1226         iic_master_notify(p_ctrl, event);
1227     }
1228     else
1229     {
1230         /* Do nothing */
1231     }
1232 }
1233 
1234 /*******************************************************************************************************************//**
1235  * Check valid receive data and set WAIT, NACK and STOP/RESTART bit in RXI handler.
1236  *
1237  * @param[in]       p_ctrl  Pointer to transfer control block
1238  **********************************************************************************************************************/
iic_master_rxi_read_data(iic_master_instance_ctrl_t * const p_ctrl)1239 static void iic_master_rxi_read_data (iic_master_instance_ctrl_t * const p_ctrl)
1240 {
1241     /* If next data = (final byte - 2), enable WAIT */
1242     if (3U == p_ctrl->remain)
1243     {
1244         p_ctrl->p_reg->ICMR3_b.WAIT = 1;
1245     }
1246     /* If next data = (final byte - 1), enable NACK  */
1247     else if (2U == p_ctrl->remain)
1248     {
1249         /* Writes to be done separately.
1250          * See Note 1 in Section 36.2.5 'I2C Bus Mode Register 3 (ICMR3)' of the RA6M3 manual R01UH0886EJ0100
1251          */
1252         p_ctrl->p_reg->ICMR3_b.ACKWP = 1; /* Write enable ACKBT */
1253         p_ctrl->p_reg->ICMR3_b.ACKBT = 1;
1254         p_ctrl->p_reg->ICMR3_b.ACKWP = 0;
1255     }
1256     /* If next data = final byte, send STOP or RESTART */
1257     else if (1U == p_ctrl->remain)
1258     {
1259         if (p_ctrl->restart)
1260         {
1261             /* NOTE:Only disable in NVIC, disabling in I2C would cause the
1262              * restart condition to fail because we are using the buffered
1263              * interrupt to start the next sequence */
1264             R_BSP_IrqDisable(p_ctrl->p_cfg->txi_irq);
1265             p_ctrl->p_reg->ICIER_b.TIE = 1U;
1266 
1267             p_ctrl->p_reg->ICMR3_b.ACKWP = 1; /* Write enable ACKBT */
1268 
1269             /* This bit clears to 0 automatically by issuing stop condition.
1270              * For restart condition, clear bit by software.
1271              */
1272             p_ctrl->p_reg->ICMR3_b.ACKBT = 0;
1273             p_ctrl->p_reg->ICMR3_b.ACKWP = 0;
1274 
1275             /* Request IIC to issue the restart condition */
1276             p_ctrl->p_reg->ICCR2 = (uint8_t) IIC_MASTER_ICCR2_RS_BIT_MASK;
1277 
1278             /* Disable timeout function */
1279             p_ctrl->p_reg->ICFER_b.TMOE = 0;
1280 
1281             /* Remember that we issued a restart when doing the next transfer */
1282             p_ctrl->restarted = true;
1283         }
1284         else
1285         {
1286             /* Clear STOP flag and set SP.
1287              * It is ok to clear other status' as this transaction is over.
1288              */
1289             p_ctrl->p_reg->ICSR2 &= (uint8_t) ~(IIC_MASTER_ICSR2_STOP_BIT);;
1290 
1291             /* Request IIC to issue the stop condition */
1292             p_ctrl->p_reg->ICCR2 = (uint8_t) IIC_MASTER_ICCR2_SP_BIT_MASK; /* It is safe to write 0's to other bits. */
1293 
1294             /* STOP flag will not be set just yet. STOP will be set only after reading the last byte from ICDRR and clearing the WAIT.
1295              * See Point #7 under '36.3.4 Master Receive Operation' of the RA6M3 manual R01UH0886EJ0100.
1296              */
1297         }
1298     }
1299     else
1300     {
1301         /* Do nothing */
1302     }
1303 
1304     p_ctrl->p_buff[p_ctrl->loaded] = p_ctrl->p_reg->ICDRR;
1305 
1306     /* Update the counter values */
1307     p_ctrl->loaded++;
1308     p_ctrl->remain--;
1309 
1310     /* If we are done with the reception, clear the WAIT bit */
1311     if (0U == p_ctrl->remain)
1312     {
1313         p_ctrl->p_reg->ICMR3_b.WAIT = 0;
1314 
1315         /* If this transaction does not have the restart flag set to true,
1316          * last byte has been read and WAIT has been cleared.
1317          * Callback will be issued by the ERI once the stop condition is detected
1318          * In case of restart flag set to true a callback will be issued by the ERI once the start
1319          * (from restart) condition is detected
1320          */
1321     }
1322 }
1323 
1324 /*******************************************************************************************************************//**
1325  * Write the address byte to the iic bus
1326  *
1327  * @param[in]       p_ctrl  Pointer to transfer control block
1328  **********************************************************************************************************************/
iic_master_txi_send_address(iic_master_instance_ctrl_t * const p_ctrl)1329 static void iic_master_txi_send_address (iic_master_instance_ctrl_t * const p_ctrl)
1330 {
1331     /* This is a 10 bit read and we have transmitted the low byte, next is restart */
1332     if ((3U == p_ctrl->addr_total) && (2U == p_ctrl->addr_loaded) && (false == p_ctrl->address_restarted))
1333     {
1334 #if IIC_MASTER_CFG_ADDR_MODE_10_BIT_ENABLE
1335         uint32_t timeout_count = IIC_MASTER_PERIPHERAL_REG_MAX_WAIT;
1336 
1337         /* For Read operation an extra address byte needs to be sent after issuing restart.
1338          * At this point we have sent the first 2 address bytes. Disable TXI.
1339          */
1340         p_ctrl->p_reg->ICIER_b.TIE = 0U;
1341 
1342         /* Wait for the value to reflect at the peripheral.
1343          * See 'Note' under Table 36.10 "Interrupt sources" of the RA6M3 manual R01UH0886EJ0100 */
1344         IIC_MASTER_HARDWARE_REGISTER_WAIT(p_ctrl->p_reg->ICIER_b.TIE, 0U, timeout_count);
1345 
1346         /* Enable the transmit end IRQ, so that we can generate a RESTART condition */
1347         /* Clear any pending TEND interrupts */
1348         R_BSP_IrqStatusClear(p_ctrl->p_cfg->tei_irq);
1349         NVIC_ClearPendingIRQ(p_ctrl->p_cfg->tei_irq);
1350 
1351         /* Enable the TXEND interrupt */
1352         p_ctrl->p_reg->ICIER_b.TEIE = 1U;
1353 
1354         /* No need to wait to check TEIE has actually become 1U; because if that's not the case,
1355          * no other operation can occur at this point */
1356 #endif
1357     }
1358     else
1359     {
1360         /* Address low byte, this could either be a 7 bit address or low byte of 10 bit address */
1361         uint8_t address_byte = p_ctrl->addr_low;
1362 #if IIC_MASTER_CFG_ADDR_MODE_10_BIT_ENABLE
1363 
1364         /* 10 bit address, handle accordingly */
1365         if (p_ctrl->addr_total > 1U)
1366         {
1367             /* MSB transfer, send address high byte with with R/W set to 0 */
1368             if (0U == p_ctrl->addr_loaded)
1369             {
1370                 address_byte = p_ctrl->addr_high;
1371             }
1372             /* MSB transfer after restart of 10 bit read, send high byte with R/W set to 1 */
1373             else if ((2U == p_ctrl->addr_loaded) && (3U == p_ctrl->addr_total))
1374             {
1375                 address_byte = p_ctrl->addr_high | (uint8_t) I2C_CODE_READ;
1376             }
1377             /* Low byte transfer */
1378             else
1379             {
1380                 address_byte = p_ctrl->addr_low;
1381             }
1382         }
1383 #endif
1384 
1385 #if IIC_MASTER_CFG_DTC_ENABLE
1386         uint8_t volatile const * p_iic_master_tx_buffer = &(p_ctrl->p_reg->ICDRT);
1387 
1388         /* If this is the last address byte, enable transfer */
1389         if (1U == p_ctrl->addr_remain)
1390         {
1391             if ((NULL != p_ctrl->p_cfg->p_transfer_tx) && !(p_ctrl->read) && (p_ctrl->total > 0U))
1392             {
1393                 p_ctrl->p_cfg->p_transfer_tx->p_api->reset(p_ctrl->p_cfg->p_transfer_tx->p_ctrl,
1394                                                            (void *) (p_ctrl->p_buff),
1395                                                            (uint8_t *) (p_iic_master_tx_buffer),
1396                                                            (uint16_t) (p_ctrl->remain));
1397                 p_ctrl->remain            = 0U;
1398                 p_ctrl->loaded            = p_ctrl->total;
1399                 p_ctrl->activation_on_txi = true;
1400             }
1401         }
1402 #endif
1403 
1404         /* Write the address byte */
1405         p_ctrl->p_reg->ICDRT = address_byte;
1406 
1407         /* Update the number of address bytes loaded for next pass */
1408         p_ctrl->addr_loaded++;
1409         p_ctrl->addr_remain--;
1410     }
1411 }
1412 
1413 #if IIC_MASTER_CFG_DTC_ENABLE
1414 
1415 /*******************************************************************************************************************//**
1416  * Configures IIC related transfer drivers (if enabled).
1417  *
1418  * @param[in]   p_ctrl    Pointer to IIC specific control structure
1419  * @param[in]   p_cfg     Pointer to IIC specific configuration structure
1420  *
1421  * @retval      FSP_SUCCESS                Transfer interface initialized successfully.
1422  * @retval      FSP_ERR_ASSERTION          Pointer to transfer instance for I2C receive in p_cfg is NULL.
1423  **********************************************************************************************************************/
iic_master_transfer_open(i2c_master_cfg_t const * const p_cfg)1424 static fsp_err_t iic_master_transfer_open (i2c_master_cfg_t const * const p_cfg)
1425 {
1426     fsp_err_t err = FSP_SUCCESS;
1427 
1428     if (NULL != p_cfg->p_transfer_rx)
1429     {
1430         err = iic_master_transfer_configure(p_cfg->p_transfer_rx, IIC_MASTER_TRANSFER_DIR_READ);
1431         FSP_ERROR_RETURN(FSP_SUCCESS == err, err);
1432     }
1433 
1434     if (NULL != p_cfg->p_transfer_tx)
1435     {
1436         err = iic_master_transfer_configure(p_cfg->p_transfer_tx, IIC_MASTER_TRANSFER_DIR_WRITE);
1437         if (FSP_SUCCESS != err)
1438         {
1439             if (NULL != p_cfg->p_transfer_rx)
1440             {
1441                 p_cfg->p_transfer_rx->p_api->close(p_cfg->p_transfer_rx->p_ctrl);
1442             }
1443 
1444             return err;
1445         }
1446     }
1447 
1448     return FSP_SUCCESS;
1449 }
1450 
1451 /*******************************************************************************************************************//**
1452  * Configures  IIC RX related transfer.
1453  * @param[in]     p_ctrl                     Pointer to IIC specific control structure
1454  * @param[in]     p_cfg                      Pointer to IIC specific configuration structure
1455  *
1456  * @retval        FSP_SUCCESS                Transfer interface is configured with valid parameters.
1457  * @retval        FSP_ERR_ASSERTION          Pointer to transfer instance for I2C receive in p_cfg is NULL.
1458  **********************************************************************************************************************/
iic_master_transfer_configure(transfer_instance_t const * p_transfer,iic_master_transfer_dir_t direction)1459 static fsp_err_t iic_master_transfer_configure (transfer_instance_t const * p_transfer,
1460                                                 iic_master_transfer_dir_t   direction)
1461 {
1462     fsp_err_t err;
1463 
1464     /* Set default transfer info and open receive transfer module, if enabled. */
1465  #if (IIC_MASTER_CFG_PARAM_CHECKING_ENABLE)
1466     FSP_ASSERT(NULL != p_transfer->p_api);
1467     FSP_ASSERT(NULL != p_transfer->p_cfg);
1468     FSP_ASSERT(NULL != p_transfer->p_cfg->p_info);
1469  #endif
1470     transfer_info_t * p_cfg = p_transfer->p_cfg->p_info;
1471     if (IIC_MASTER_TRANSFER_DIR_READ == direction)
1472     {
1473         p_cfg->transfer_settings_word = IIC_MASTER_DTC_RX_TRANSFER_SETTINGS;
1474     }
1475     else
1476     {
1477         p_cfg->transfer_settings_word = IIC_MASTER_DTC_TX_TRANSFER_SETTINGS;
1478     }
1479 
1480     err = p_transfer->p_api->open(p_transfer->p_ctrl, p_transfer->p_cfg);
1481     FSP_ERROR_RETURN((FSP_SUCCESS == err), err);
1482 
1483     return FSP_SUCCESS;
1484 }
1485 
1486 #endif
1487 
1488 /***********************************************************************************************************************
1489  * Interrupt Vectors
1490  **********************************************************************************************************************/
1491 
1492 /*******************************************************************************************************************//**
1493  * Receive data full interrupt routine.
1494  *
1495  * This function implements the IIC Receive buffer full ISR routine.
1496  *
1497  **********************************************************************************************************************/
iic_master_rxi_isr(void)1498 void iic_master_rxi_isr (void)
1499 {
1500     /* Save context if RTOS is used */
1501     FSP_CONTEXT_SAVE
1502     /* Clear the IR flag */
1503     R_BSP_IrqStatusClear(R_FSP_CurrentIrqGet());
1504 
1505     IRQn_Type irq = R_FSP_CurrentIrqGet();
1506     iic_master_instance_ctrl_t * p_ctrl = (iic_master_instance_ctrl_t *) R_FSP_IsrContextGet(irq);
1507     iic_master_rxi_master(p_ctrl);
1508 
1509     /* Restore context if RTOS is used */
1510     FSP_CONTEXT_RESTORE
1511 }
1512 
1513 /*******************************************************************************************************************//**
1514  * Transmit data empty interrupt routine.
1515  *
1516  * This function implements the Transmit buffer empty ISR routine.
1517  *
1518  **********************************************************************************************************************/
iic_master_txi_isr(void)1519 void iic_master_txi_isr (void)
1520 {
1521     /* Save context if RTOS is used */
1522     FSP_CONTEXT_SAVE
1523     /* Clear the IR flag */
1524     R_BSP_IrqStatusClear(R_FSP_CurrentIrqGet());
1525 
1526     IRQn_Type irq = R_FSP_CurrentIrqGet();
1527     iic_master_instance_ctrl_t * p_ctrl = (iic_master_instance_ctrl_t *) R_FSP_IsrContextGet(irq);
1528     iic_master_txi_master(p_ctrl);
1529 
1530     /* Restore context if RTOS is used */
1531     FSP_CONTEXT_RESTORE
1532 }
1533 
1534 /*******************************************************************************************************************//**
1535  * Transmit end interrupt routine.
1536  *
1537  * This function implements the IIC Transmission End ISR routine.
1538  *
1539  **********************************************************************************************************************/
iic_master_tei_isr(void)1540 void iic_master_tei_isr (void)
1541 {
1542     /* Save context if RTOS is used */
1543     FSP_CONTEXT_SAVE
1544 
1545     IRQn_Type irq = R_FSP_CurrentIrqGet();
1546     iic_master_instance_ctrl_t * p_ctrl = (iic_master_instance_ctrl_t *) R_FSP_IsrContextGet(irq);
1547     iic_master_tei_master(p_ctrl);
1548 
1549     /* Clear the IR flag */
1550     R_BSP_IrqStatusClear(R_FSP_CurrentIrqGet());
1551 
1552     /* Restore context if RTOS is used */
1553     FSP_CONTEXT_RESTORE
1554 }
1555 
1556 /*******************************************************************************************************************//**
1557  * Error and event interrupt routine.
1558  *
1559  * This function implements the IIC Event/Error.
1560  *
1561  **********************************************************************************************************************/
iic_master_eri_isr(void)1562 void iic_master_eri_isr (void)
1563 {
1564     /* Save context if RTOS is used */
1565     FSP_CONTEXT_SAVE
1566 
1567     IRQn_Type irq = R_FSP_CurrentIrqGet();
1568     iic_master_instance_ctrl_t * p_ctrl = (iic_master_instance_ctrl_t *) R_FSP_IsrContextGet(irq);
1569     iic_master_err_master(p_ctrl);
1570 
1571     /* Clear the IR flag */
1572     R_BSP_IrqStatusClear(R_FSP_CurrentIrqGet());
1573 
1574     /* Restore context if RTOS is used */
1575     FSP_CONTEXT_RESTORE
1576 }
1577