• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /**
2  * Copyright (c) 2020 HiSilicon (Shanghai) Technologies CO., LIMITED.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  *     http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  *
15  * Description: Provides i2c driver source \n
16  *
17  * History: \n
18  * 2022-08-15, Create file. \n
19  */
20 
21 #include <stdbool.h>
22 #include "soc_osal.h"
23 #include "securec.h"
24 #include "common_def.h"
25 #include "tcxo.h"
26 #include "i2c.h"
27 #if defined(CONFIG_I2C_SUPPORT_DMA) && (CONFIG_I2C_SUPPORT_DMA == 1)
28 #include "dma.h"
29 #include "hal_dma.h"
30 #endif  /* CONFIG_I2C_SUPPORT_DMA */
31 
32 #define I2C_DEFAULT_DEV_ADDRESS  0x0
33 
34 typedef struct i2c_ctrl_block_info {
35     bool init_flag;              /* When the I2C bus is initialized, the flag is true. */
36     bool master_flag;            /* when init_flag is True, the flag can be valid. */
37     uint8_t hscode;              /* High speeed mode master code. */
38     uint8_t operate_type;        /* I2C data operation type. */
39     uint16_t addr;               /* I2C slave address, valid for slave mode. */
40 #if defined(CONFIG_I2C_SUPPORT_INT) && (CONFIG_I2C_SUPPORT_INT == 1)
41     i2c_irq_callback_t  callback;
42 #endif
43 } i2c_ctrl_block_info_t;
44 
45 static i2c_ctrl_block_info_t g_i2c_ctrl[I2C_BUS_MAX_NUM];
46 
47 #if defined(CONFIG_I2C_SUPPORT_DMA) && (CONFIG_I2C_SUPPORT_DMA == 1)
48 typedef struct i2c_dma_trans_inf {
49     bool trans_succ;
50     uint8_t read_channel;
51     uint8_t write_channel;
52     osal_semaphore dma_sem;
53 } i2c_dma_trans_inf_t;
54 
55 static i2c_dma_trans_inf_t g_dma_trans[I2C_BUS_NONE] = { 0 };
56 #endif  /* CONFIG_I2C_SUPPORT_DMA */
57 
58 #if defined(CONFIG_I2C_SUPPORT_CONCURRENCY) && (CONFIG_I2C_SUPPORT_CONCURRENCY == 1)
59 static osal_mutex g_i2c_mutex[I2C_BUS_NONE];
60 #endif  /* CONFIG_I2C_SUPPORT_CONCURRENCY */
61 
62 #if defined(CONFIG_I2C_SUPPORT_INT) && (CONFIG_I2C_SUPPORT_INT == 1)
63 static osal_semaphore g_i2c_int_sem[I2C_BUS_MAX_NUM];
64 static hal_i2c_buffer_wrap_t g_i2c_buffer_wrap[I2C_BUS_MAX_NUM];
65 #endif  /* CONFIG_I2C_SUPPORT_INT */
66 
i2c_bus_init_check(i2c_bus_t bus)67 static errcode_t i2c_bus_init_check(i2c_bus_t bus)
68 {
69     if (bus >= I2C_BUS_MAX_NUMBER) {
70         return ERRCODE_I2C_INVALID_PARAMETER;
71     }
72 
73     i2c_ctrl_block_info_t *i2c_ctrl = &g_i2c_ctrl[bus];
74     if (i2c_ctrl->init_flag == false) {
75         return ERRCODE_I2C_NOT_INIT;
76     }
77     return ERRCODE_SUCC;
78 }
79 
i2c_write_pre_check(i2c_bus_t bus,const i2c_data_t * data)80 static errcode_t i2c_write_pre_check(i2c_bus_t bus, const i2c_data_t *data)
81 {
82     if ((data == NULL) || (data->send_buf == NULL) || (data->send_len == 0)) {
83         return ERRCODE_I2C_SEND_PARAM_INVALID;
84     }
85 
86     errcode_t ret = i2c_bus_init_check(bus);
87     if (ret != ERRCODE_SUCC) {
88         return ret;
89     }
90     return ERRCODE_SUCC;
91 }
92 
i2c_read_pre_check(i2c_bus_t bus,const i2c_data_t * data)93 static errcode_t i2c_read_pre_check(i2c_bus_t bus, const i2c_data_t *data)
94 {
95     if ((data == NULL) || (data->receive_buf == NULL) || (data->receive_len == 0)) {
96         return ERRCODE_I2C_RECEIVE_PARAM_INVALID;
97     }
98 
99     errcode_t ret = i2c_bus_init_check(bus);
100     if (ret != ERRCODE_SUCC) {
101         return ret;
102     }
103     return ERRCODE_SUCC;
104 }
105 
i2c_event_get_mask(hal_i2c_evt_id_t evt_id)106 static inline uint32_t i2c_event_get_mask(hal_i2c_evt_id_t evt_id)
107 {
108     return (1 << (uint32_t)evt_id);
109 }
110 
i2c_ctrl_get_mask(hal_i2c_ctrl_id_t ctrl_id)111 static inline uint32_t i2c_ctrl_get_mask(hal_i2c_ctrl_id_t ctrl_id)
112 {
113     return (1 << (uint32_t)ctrl_id);
114 }
115 
i2c_ctrl_get_id(uint32_t ctrl_mask,hal_i2c_ctrl_id_t ctrl_id)116 static inline bool i2c_ctrl_get_id(uint32_t ctrl_mask, hal_i2c_ctrl_id_t ctrl_id)
117 {
118     return (ctrl_mask >> (uint32_t)ctrl_id) & 1;
119 }
120 
i2c_comm_ctrl_check(i2c_bus_t bus,hal_i2c_ctrl_id_t id)121 static errcode_t i2c_comm_ctrl_check(i2c_bus_t bus, hal_i2c_ctrl_id_t id)
122 {
123     uint32_t flag = false;
124     errcode_t ret = hal_i2c_ctrl(bus, id, (uintptr_t)&flag);
125     if (ret != ERRCODE_SUCC) {
126         return ret;
127     }
128     if (flag == true) {
129         return ERRCODE_SUCC;
130     }
131     return ERRCODE_I2C_WAIT_CONTINUE;
132 }
133 
i2c_ctrl_wait(i2c_bus_t bus,uint32_t ctrl_mask,uint32_t timeout)134 static errcode_t i2c_ctrl_wait(i2c_bus_t bus, uint32_t ctrl_mask, uint32_t timeout)
135 {
136     errcode_t ret;
137     uint32_t tmp_ctrl_mask = ctrl_mask;
138     uint64_t start_time = uapi_tcxo_get_ms();
139 
140     do {
141         for (uint32_t loop = 0; loop <= (uint32_t)I2C_CTRL_NORMAL_MAX; loop++) {
142             if (i2c_ctrl_get_id(tmp_ctrl_mask, loop) == false) {
143                 continue;
144             }
145             ret = i2c_comm_ctrl_check(bus, loop);
146             if (ret == ERRCODE_SUCC) {
147                 tmp_ctrl_mask &= ~(1 << loop);
148             } else if (ret == ERRCODE_I2C_WAIT_CONTINUE) {
149                 continue;
150             }
151         }
152 
153         ret = i2c_comm_ctrl_check(bus, I2C_CTRL_CHECK_TRANSMIT_ABRT);
154         if (ret == ERRCODE_SUCC) {
155             return ERRCODE_I2C_WAIT_EXCEPTION;
156         }
157 
158         if ((uapi_tcxo_get_ms() - start_time) > timeout) {
159             return ERRCODE_I2C_TIMEOUT;
160         }
161     } while (tmp_ctrl_mask != 0);
162     return ERRCODE_SUCC;
163 }
164 
i2c_wait(i2c_bus_t bus,i2c_wait_condition_t * condition,uint32_t timeout)165 static errcode_t i2c_wait(i2c_bus_t bus, i2c_wait_condition_t *condition, uint32_t timeout)
166 {
167     errcode_t ret = ERRCODE_SUCC;
168     i2c_ctrl_block_info_t *i2c_ctrl = &g_i2c_ctrl[bus];
169 
170     if (i2c_ctrl->operate_type == I2C_DATA_OPERATION_TYPE_POLL) {
171         ret = i2c_ctrl_wait(bus, condition->ctrl_mask, timeout);
172     }
173     return ret;
174 }
175 
i2c_write(i2c_bus_t bus,hal_i2c_buffer_wrap_t * buffer_wrap)176 static errcode_t i2c_write(i2c_bus_t bus, hal_i2c_buffer_wrap_t *buffer_wrap)
177 {
178     errcode_t ret = ERRCODE_SUCC;
179     uint32_t real_write_num = 0;
180     uint8_t *buffer = buffer_wrap->buffer;
181     uint32_t len = buffer_wrap->len;
182     i2c_wait_condition_t condition = { 0 };
183 
184     uint32_t burst_num = 0;
185     hal_i2c_ctrl(bus, I2C_CTRL_GET_WRITE_NUM, (uintptr_t)&burst_num);
186     if (burst_num == 0) {
187         return ret;
188     }
189 
190     while (real_write_num < len) {
191         condition.ctrl_mask = i2c_ctrl_get_mask(I2C_CTRL_CHECK_TX_AVAILABLE);
192         condition.evt_mask = i2c_event_get_mask(I2C_EVT_TX_AVAILABLE) | i2c_event_get_mask(I2C_EVT_TX_READY);
193         ret = i2c_wait(bus, &condition, CONFIG_I2C_WAIT_CONDITION_TIMEOUT);
194         if (ret != ERRCODE_SUCC) {
195             break;
196         }
197 
198         uint32_t remain_num = len - real_write_num;
199         hal_i2c_buffer_wrap_t write_data = { 0 };
200         if (remain_num > burst_num) {
201             write_data.len = burst_num;
202         } else {
203             write_data.len = remain_num;
204             write_data.stop_flag = buffer_wrap->stop_flag;
205         }
206 
207         if (real_write_num == 0) {
208             write_data.restart_flag = buffer_wrap->restart_flag;
209         }
210 
211         write_data.buffer = &buffer[real_write_num];
212         unsigned int irq_sts = i2c_porting_lock(bus);
213         ret = hal_i2c_write(bus, &write_data);
214         i2c_porting_unlock(bus, irq_sts);
215         if (ret != ERRCODE_SUCC) {
216             break;
217         }
218 
219         real_write_num += write_data.len;
220     }
221 
222     return ret;
223 }
224 
i2c_read(i2c_bus_t bus,hal_i2c_buffer_wrap_t * buffer_wrap)225 static errcode_t i2c_read(i2c_bus_t bus, hal_i2c_buffer_wrap_t *buffer_wrap)
226 {
227     uint8_t *buffer = buffer_wrap->buffer;
228     uint32_t len = buffer_wrap->len;
229     uint32_t real_read_num = 0;
230     i2c_wait_condition_t condition = { 0 };
231     errcode_t ret = ERRCODE_SUCC;
232 
233     while (real_read_num < len) {
234         uint32_t burst_num = 0;
235         hal_i2c_ctrl(bus, I2C_CTRL_GET_READ_NUM, (uintptr_t)&burst_num);
236 
237         uint32_t remain_num = len - real_read_num;
238         hal_i2c_buffer_wrap_t read_data = { 0 };
239         if (remain_num > burst_num) {
240             read_data.len = burst_num;
241         } else {
242             read_data.len = remain_num;
243             read_data.stop_flag = buffer_wrap->stop_flag;
244         }
245 
246         if (real_read_num == 0) {
247             read_data.restart_flag = buffer_wrap->restart_flag;
248         }
249 
250         ret = hal_i2c_ctrl(bus, I2C_CTRL_FLUSH_RX_FIFO, (uintptr_t)&read_data);
251         if (ret == ERRCODE_SUCC) {
252             condition.ctrl_mask = i2c_ctrl_get_mask(I2C_CTRL_CHECK_RX_AVAILABLE);
253             condition.evt_mask = i2c_event_get_mask(I2C_EVT_RX_READY);
254             (void)i2c_wait(bus, &condition, CONFIG_I2C_WAIT_CONDITION_TIMEOUT);
255         }
256 
257         read_data.buffer = &buffer[real_read_num];
258         unsigned int irq_sts = i2c_porting_lock(bus);
259         ret = hal_i2c_read(bus, &read_data);
260         i2c_porting_unlock(bus, irq_sts);
261         if (ret != ERRCODE_SUCC) {
262             break;
263         }
264         real_read_num += read_data.len;
265     }
266     return ret;
267 }
268 
i2c_poll_write(i2c_bus_t bus,uint16_t dev_addr,hal_i2c_buffer_wrap_t * data_cfg,bool end_flag)269 static errcode_t i2c_poll_write(i2c_bus_t bus, uint16_t dev_addr, hal_i2c_buffer_wrap_t *data_cfg, bool end_flag)
270 {
271     hal_i2c_prepare_config_t cfg = { 0 };
272     i2c_ctrl_block_info_t *i2c_ctrl = &g_i2c_ctrl[bus];
273 
274     cfg.addr = dev_addr;
275     cfg.operation_type = I2C_DATA_OPERATION_TYPE_POLL;
276     i2c_ctrl->operate_type = cfg.operation_type;
277 
278     errcode_t ret = hal_i2c_ctrl(bus, I2C_CTRL_WRITE_PREPARE, (uintptr_t)&cfg);
279     if (ret != ERRCODE_SUCC) {
280         return ret;
281     }
282 
283     ret = i2c_write(bus, data_cfg);
284     if (ret != ERRCODE_SUCC) {
285         (void)hal_i2c_ctrl(bus, I2C_CTRL_WRITE_RESTORE, (uintptr_t)NULL);
286         return ret;
287     }
288 
289     i2c_wait_condition_t condition = { 0 };
290     if (end_flag) {
291         condition.ctrl_mask = i2c_ctrl_get_mask(I2C_CTRL_CHECK_TX_PROCESS_DONE);
292     }
293     ret = i2c_wait(bus, &condition, CONFIG_I2C_WAIT_CONDITION_TIMEOUT);
294 
295     (void)hal_i2c_ctrl(bus, I2C_CTRL_WRITE_RESTORE, (uintptr_t)NULL);
296     return ret;
297 }
298 
i2c_poll_read(i2c_bus_t bus,uint16_t dev_addr,hal_i2c_buffer_wrap_t * data_cfg,bool end_flag)299 static errcode_t i2c_poll_read(i2c_bus_t bus, uint16_t dev_addr, hal_i2c_buffer_wrap_t *data_cfg, bool end_flag)
300 {
301     unused(end_flag);
302     hal_i2c_prepare_config_t cfg = { 0 };
303     i2c_ctrl_block_info_t *i2c_ctrl = &g_i2c_ctrl[bus];
304 
305     cfg.addr = dev_addr;
306     cfg.operation_type = I2C_DATA_OPERATION_TYPE_POLL;
307     i2c_ctrl->operate_type = cfg.operation_type;
308 
309     errcode_t ret = hal_i2c_ctrl(bus, I2C_CTRL_READ_PREPARE, (uintptr_t)&cfg);
310     if (ret != ERRCODE_SUCC) {
311         return ret;
312     }
313 
314     ret = i2c_read(bus, data_cfg);
315     if (ret != ERRCODE_SUCC) {
316         (void)hal_i2c_ctrl(bus, I2C_CTRL_READ_RESTORE, (uintptr_t)NULL);
317         return ret;
318     }
319 
320     i2c_wait_condition_t condition = { 0 };
321     condition.ctrl_mask = i2c_ctrl_get_mask(I2C_CTRL_CHECK_RX_PROCESS_DONE);
322 
323     ret = i2c_wait(bus, &condition, CONFIG_I2C_WAIT_CONDITION_TIMEOUT);
324 
325     (void)hal_i2c_ctrl(bus, I2C_CTRL_READ_RESTORE, (uintptr_t)NULL);
326     return ret;
327 }
328 
329 #if (defined(CONFIG_I2C_SUPPORT_DMA) || defined(CONFIG_I2C_SUPPORT_INT))
i2c_int_mode_down(osal_semaphore * sem)330 static int i2c_int_mode_down(osal_semaphore *sem)
331 {
332     unused(sem);
333     int osal_value = OSAL_SUCCESS;
334 #if !defined(CONFIG_I2C_SUPPORT_IN_CHIP_LOOPBACK)
335     osal_value = osal_sem_down(sem);
336 #endif
337     return osal_value;
338 }
339 
i2c_int_mode_up(osal_semaphore * sem)340 static void i2c_int_mode_up(osal_semaphore *sem)
341 {
342     unused(sem);
343 #if !defined(CONFIG_I2C_SUPPORT_IN_CHIP_LOOPBACK)
344     osal_sem_up(sem);
345 #endif
346 }
347 #endif
348 
349 #if defined(CONFIG_I2C_SUPPORT_DMA) && (CONFIG_I2C_SUPPORT_DMA == 1)
i2c_dma_isr(uint8_t int_type,uint8_t ch,uintptr_t arg)350 static void i2c_dma_isr(uint8_t int_type, uint8_t ch, uintptr_t arg)
351 {
352     unused(arg);
353     uint8_t bus = I2C_BUS_NONE;
354     for (uint8_t i = I2C_BUS_0; i < I2C_BUS_NONE; i++) {
355         /* channel default value is 0, means not used. channel > 0 means used.
356            So ch + 1 will not misjudgment with channel value 0. */
357         if (g_dma_trans[i].read_channel == ch + 1) {
358             bus = i;
359             break;
360         }
361         if (g_dma_trans[i].write_channel == ch + 1) {
362             bus = i;
363             break;
364         }
365     }
366 
367     if (bus != I2C_BUS_NONE) {
368         if (int_type == 0) {
369             g_dma_trans[bus].trans_succ = true;
370         }
371         i2c_int_mode_up(&(g_dma_trans[bus].dma_sem));
372     }
373 }
374 
i2c_write_by_dma_config(i2c_bus_t bus,uint16_t * buffer,uint32_t length,dma_ch_user_peripheral_config_t * user_cfg)375 static void i2c_write_by_dma_config(i2c_bus_t bus, uint16_t *buffer,
376                                     uint32_t length,
377                                     dma_ch_user_peripheral_config_t *user_cfg)
378 {
379     uint32_t data_addr = 0;
380     hal_i2c_ctrl(bus, I2C_CTRL_GET_DMA_DATA_ADDR, (uintptr_t)(&data_addr));
381 
382     user_cfg->src = (uint32_t)(uintptr_t)buffer;
383     user_cfg->dest = (uint32_t)data_addr;
384     user_cfg->transfer_num = (uint16_t)length;
385     user_cfg->src_handshaking = 0;
386     user_cfg->trans_type = HAL_DMA_TRANS_MEMORY_TO_PERIPHERAL_DMA;
387     user_cfg->trans_dir = HAL_DMA_TRANSFER_DIR_MEM_TO_PERIPHERAL;
388     user_cfg->priority = HAL_DMA_CH_PRIORITY_0;
389     user_cfg->src_width = HAL_DMA_TRANSFER_WIDTH_8;
390     user_cfg->dest_width = HAL_DMA_TRANSFER_WIDTH_8;
391     user_cfg->burst_length = HAL_DMA_BURST_TRANSACTION_LENGTH_4;
392     user_cfg->src_increment = HAL_DMA_ADDRESS_INC_INCREMENT;
393     user_cfg->dest_increment = HAL_DMA_ADDRESS_INC_NO_CHANGE;
394     user_cfg->protection = HAL_DMA_PROTECTION_CONTROL_PRIVILEGED;
395     user_cfg->dest_handshaking = (uint16_t)i2c_port_get_dma_trans_dest_handshaking(bus);
396 }
397 
i2c_read_by_dma_config(i2c_bus_t bus,uint8_t * buffer,uint32_t length,dma_ch_user_peripheral_config_t * user_cfg)398 static void i2c_read_by_dma_config(i2c_bus_t bus,
399                                    uint8_t *buffer,
400                                    uint32_t length,
401                                    dma_ch_user_peripheral_config_t *user_cfg)
402 {
403     uint32_t data_addr = 0;
404     hal_i2c_ctrl(bus, I2C_CTRL_GET_DMA_DATA_ADDR, (uintptr_t)(&data_addr));
405 
406     user_cfg->src = (uint32_t)data_addr;
407     user_cfg->dest = (uint32_t)(uintptr_t)buffer;
408     user_cfg->transfer_num = (uint16_t)length;
409     user_cfg->src_handshaking = (uint16_t)i2c_port_get_dma_trans_src_handshaking(bus);
410     user_cfg->trans_type = HAL_DMA_TRANS_PERIPHERAL_TO_MEMORY_DMA;
411     user_cfg->trans_dir = HAL_DMA_TRANSFER_DIR_PERIPHERAL_TO_MEM;
412     user_cfg->priority = HAL_DMA_CH_PRIORITY_0;
413     user_cfg->src_width = HAL_DMA_TRANSFER_WIDTH_8;
414     user_cfg->dest_width = HAL_DMA_TRANSFER_WIDTH_8;
415     user_cfg->burst_length = HAL_DMA_BURST_TRANSACTION_LENGTH_4;
416     user_cfg->src_increment = HAL_DMA_ADDRESS_INC_NO_CHANGE;
417     user_cfg->dest_increment = HAL_DMA_ADDRESS_INC_INCREMENT;
418     user_cfg->protection = HAL_DMA_PROTECTION_CONTROL_BUFFERABLE;
419     user_cfg->dest_handshaking = 0;
420 }
421 
i2c_start_transmit_dma(i2c_bus_t bus,uint8_t dma_ch)422 static errcode_t i2c_start_transmit_dma(i2c_bus_t bus, uint8_t dma_ch)
423 {
424     g_dma_trans[bus].write_channel = dma_ch + 1;
425     g_dma_trans[bus].trans_succ = false;
426     if (uapi_dma_start_transfer(dma_ch) != ERRCODE_SUCC) {
427         g_dma_trans[bus].write_channel = 0;
428         return ERRCODE_I2C_DMA_CONFIG_ERROR;
429     }
430     return ERRCODE_SUCC;
431 }
432 
i2c_transmit_dma(i2c_bus_t bus,hal_i2c_buffer_wrap_t * data_cfg)433 static errcode_t i2c_transmit_dma(i2c_bus_t bus, hal_i2c_buffer_wrap_t *data_cfg)
434 {
435     uint8_t dma_ch;
436     dma_ch_user_peripheral_config_t user_cfg = {0};
437 
438     i2c_write_by_dma_config(bus, (uint16_t*)data_cfg->buffer, (uint16_t)data_cfg->len, &user_cfg);
439 
440     if (uapi_dma_configure_peripheral_transfer_single(&user_cfg, &dma_ch,
441         i2c_dma_isr, (uintptr_t)NULL) != ERRCODE_SUCC) {
442         return ERRCODE_I2C_DMA_CONFIG_ERROR;
443     }
444 
445     return i2c_start_transmit_dma(bus, dma_ch);
446 }
447 
i2c_transmit_read_cmd_by_dma(i2c_bus_t bus,hal_i2c_buffer_wrap_t * data_cfg)448 static errcode_t i2c_transmit_read_cmd_by_dma(i2c_bus_t bus, hal_i2c_buffer_wrap_t *data_cfg)
449 {
450     uint8_t dma_ch;
451     static uint16_t read_cmd = 0x100;
452     dma_ch_user_peripheral_config_t user_cfg = {0};
453 
454     i2c_write_by_dma_config(bus, &read_cmd, data_cfg->len, &user_cfg);
455     user_cfg.src_width = HAL_DMA_TRANSFER_WIDTH_16;
456     user_cfg.dest_width = HAL_DMA_TRANSFER_WIDTH_16;
457     user_cfg.src_increment = HAL_DMA_ADDRESS_INC_NO_CHANGE;
458 
459     if (uapi_dma_configure_peripheral_transfer_single(&user_cfg, &dma_ch,
460         i2c_dma_isr, (uintptr_t)NULL) != ERRCODE_SUCC) {
461         return ERRCODE_I2C_DMA_CONFIG_ERROR;
462     }
463 
464     return i2c_start_transmit_dma(bus, dma_ch);
465 }
466 
i2c_start_recv_dma(i2c_bus_t bus,hal_i2c_buffer_wrap_t * data_cfg)467 static errcode_t i2c_start_recv_dma(i2c_bus_t bus, hal_i2c_buffer_wrap_t *data_cfg)
468 {
469     uint8_t dma_ch;
470     dma_ch_user_peripheral_config_t user_cfg = {0};
471 
472     i2c_read_by_dma_config(bus, data_cfg->buffer, data_cfg->len, &user_cfg);
473 
474     if (uapi_dma_configure_peripheral_transfer_single(&user_cfg, &dma_ch,
475         i2c_dma_isr, (uintptr_t)NULL) != ERRCODE_SUCC) {
476         return ERRCODE_I2C_DMA_CONFIG_ERROR;
477     }
478 
479     g_dma_trans[bus].read_channel = dma_ch + 1;
480     g_dma_trans[bus].trans_succ = false;
481     if (uapi_dma_start_transfer(dma_ch) != ERRCODE_SUCC) {
482         g_dma_trans[bus].read_channel = 0;
483         return ERRCODE_I2C_DMA_CONFIG_ERROR;
484     }
485     return ERRCODE_SUCC;
486 }
487 
i2c_write_by_dma(i2c_bus_t bus,uint16_t dev_addr,hal_i2c_buffer_wrap_t * data)488 static errcode_t i2c_write_by_dma(i2c_bus_t bus, uint16_t dev_addr, hal_i2c_buffer_wrap_t *data)
489 {
490     hal_i2c_prepare_config_t cfg = { 0 };
491     hal_i2c_buffer_wrap_t buffer_wrap;
492     i2c_ctrl_block_info_t *i2c_ctrl = &g_i2c_ctrl[bus];
493 
494     cfg.addr = dev_addr;
495     cfg.operation_type = I2C_DATA_OPERATION_TYPE_DMA;
496     i2c_ctrl->operate_type = cfg.operation_type;
497     errcode_t ret = hal_i2c_ctrl(bus, I2C_CTRL_WRITE_PREPARE, (uintptr_t)&cfg);
498     if (ret != ERRCODE_SUCC) {
499         return ret;
500     }
501 
502     buffer_wrap.buffer = data->buffer;
503     buffer_wrap.len = data->stop_flag ? data->len - 1 : data->len;
504 
505     /* if the lenth is 0 here, send stop byte straightforward */
506     if (buffer_wrap.len != 0) {
507         ret = i2c_transmit_dma(bus, &buffer_wrap);
508         if (ret != ERRCODE_SUCC) {
509             return ret;
510         }
511 
512         /* wait for trans */
513         if (i2c_int_mode_down(&(g_dma_trans[bus].dma_sem)) != OSAL_SUCCESS) {
514             g_dma_trans[bus].write_channel = 0;
515             return ERRCODE_I2C_DMA_TRANSFER_ERROR;
516         }
517         g_dma_trans[bus].write_channel = 0;
518         if (!g_dma_trans[bus].trans_succ) {
519             return ERRCODE_I2C_DMA_TRANSFER_ERROR;
520         }
521     }
522 
523     if (data->stop_flag) {
524         buffer_wrap.buffer = data->buffer + data->len - 1;
525         buffer_wrap.len = 1;
526         buffer_wrap.restart_flag = false;
527         buffer_wrap.stop_flag = true;
528 
529         ret = i2c_write(bus, &buffer_wrap);
530         if (ret != ERRCODE_SUCC) {
531             (void)hal_i2c_ctrl(bus, I2C_CTRL_WRITE_RESTORE, (uintptr_t)NULL);
532             return ret;
533         }
534 
535         i2c_wait_condition_t condition = { 0 };
536         condition.ctrl_mask = i2c_ctrl_get_mask(I2C_CTRL_CHECK_TX_PROCESS_DONE);
537         ret = i2c_wait(bus, &condition, CONFIG_I2C_WAIT_CONDITION_TIMEOUT);
538     }
539 
540     (void)hal_i2c_ctrl(bus, I2C_CTRL_WRITE_RESTORE, (uintptr_t)NULL);
541 
542     return ret;
543 }
544 
i2c_read_by_dma(i2c_bus_t bus,uint16_t dev_addr,hal_i2c_buffer_wrap_t * data)545 static errcode_t i2c_read_by_dma(i2c_bus_t bus, uint16_t dev_addr, hal_i2c_buffer_wrap_t *data)
546 {
547     hal_i2c_prepare_config_t cfg = { 0 };
548     i2c_ctrl_block_info_t *i2c_ctrl = &g_i2c_ctrl[bus];
549     cfg.addr = dev_addr;
550     cfg.operation_type = I2C_DATA_OPERATION_TYPE_DMA;
551     i2c_ctrl->operate_type = cfg.operation_type;
552     /* 读准备 */
553     errcode_t ret = hal_i2c_ctrl(bus, I2C_CTRL_READ_PREPARE, (uintptr_t)&cfg);
554     if (ret != ERRCODE_SUCC) {
555         return ret;
556     }
557 
558     hal_i2c_buffer_wrap_t buffer_wrap;
559 
560     buffer_wrap.len = data->len;
561     buffer_wrap.buffer = data->buffer;
562 
563     /* 开启一个dma接收传输 */
564     ret = i2c_start_recv_dma(bus, &buffer_wrap);
565     if (ret != ERRCODE_SUCC) {
566         return ret;
567     }
568 
569     /* 从模式在这里接收信号量,主模式在发送读命令之后接收信号量 */
570     if (!i2c_ctrl->master_flag) {
571         if (i2c_int_mode_down(&(g_dma_trans[bus].dma_sem)) != OSAL_SUCCESS) {
572             g_dma_trans[bus].write_channel = 0;
573             return ERRCODE_I2C_DMA_TRANSFER_ERROR;
574         }
575 
576         g_dma_trans[bus].write_channel = 0;
577         if (!g_dma_trans[bus].trans_succ) {
578             return ERRCODE_I2C_DMA_TRANSFER_ERROR;
579         }
580 
581         (void)hal_i2c_ctrl(bus, I2C_CTRL_READ_RESTORE, (uintptr_t)NULL);
582     }
583 
584     return ERRCODE_SUCC;
585 }
586 
i2c_read_do_send_cmd(i2c_bus_t bus,hal_i2c_buffer_wrap_t * data)587 static errcode_t i2c_read_do_send_cmd(i2c_bus_t bus, hal_i2c_buffer_wrap_t *data)
588 {
589     errcode_t ret;
590     hal_i2c_buffer_wrap_t buffer_wrap;
591 
592     buffer_wrap.buffer = data->buffer;
593     buffer_wrap.len = data->len - 1;
594     buffer_wrap.stop_flag = data->stop_flag;
595 
596     /* 先通过dma发送len - 1个没有停止位的读命令 */
597     if (buffer_wrap.len != 0) {
598         ret = i2c_transmit_read_cmd_by_dma(bus, &buffer_wrap);
599         if (ret != ERRCODE_SUCC) {
600             return ret;
601         }
602 
603         /* 发送len - 1个命令的dma中断 */
604         if (i2c_int_mode_down(&(g_dma_trans[bus].dma_sem)) != OSAL_SUCCESS) {
605             g_dma_trans[bus].write_channel = 0;
606             g_dma_trans[bus].read_channel = 0;
607             return ERRCODE_I2C_DMA_TRANSFER_ERROR;
608         }
609     }
610 
611     /* 单独发送最后一个cmd,会包含停止位,触发数据接收流程 */
612     buffer_wrap.len = 1;
613     hal_i2c_ctrl(bus, I2C_CTRL_FLUSH_RX_FIFO, (uintptr_t)&buffer_wrap);
614     /* 等待接收数据的dma中断释放信号量 */
615     if (i2c_int_mode_down(&(g_dma_trans[bus].dma_sem)) != OSAL_SUCCESS) {
616         g_dma_trans[bus].read_channel = 0;
617         (void)hal_i2c_ctrl(bus, I2C_CTRL_READ_RESTORE, (uintptr_t)NULL);
618         return ERRCODE_I2C_DMA_TRANSFER_ERROR;
619     }
620 
621     (void)hal_i2c_ctrl(bus, I2C_CTRL_READ_RESTORE, (uintptr_t)NULL);
622 
623     return ERRCODE_SUCC;
624 }
625 #endif  /* CONFIG_I2C_SUPPORT_DMA */
626 
627 #if defined(CONFIG_I2C_SUPPORT_INT) && (CONFIG_I2C_SUPPORT_INT == 1)
i2c_evt_busy_callback(i2c_bus_t bus)628 static void i2c_evt_busy_callback(i2c_bus_t bus)
629 {
630     if (g_i2c_ctrl[bus].callback != NULL) {
631         g_i2c_ctrl[bus].callback(bus, I2C_IRQ_EVT_I2C_BUSY);
632     }
633 }
634 
i2c_evt_err_callback(i2c_bus_t bus)635 static void i2c_evt_err_callback(i2c_bus_t bus)
636 {
637     if (g_i2c_ctrl[bus].callback != NULL) {
638         g_i2c_ctrl[bus].callback(bus, I2C_IRQ_EVT_I2C_ERR);
639     }
640 }
641 
i2c_evt_tx_callback(i2c_bus_t bus)642 static void i2c_evt_tx_callback(i2c_bus_t bus)
643 {
644     hal_i2c_buffer_wrap_t hal_wrap;
645     uint32_t burst_len;
646 
647     /* 如果没有要写的数据了,就退出 */
648     if (g_i2c_buffer_wrap[bus].len == 0) {
649         (void)hal_i2c_ctrl(bus, I2C_CTRL_WRITE_RESTORE, (uintptr_t)NULL);
650         if (g_i2c_ctrl[bus].callback != NULL) {
651             g_i2c_ctrl[bus].callback(bus, I2C_IRQ_EVT_TX_DONE);
652         }
653         return;
654     }
655 
656     hal_i2c_ctrl(bus, I2C_CTRL_GET_WRITE_NUM, (uintptr_t)&burst_len);
657     uint32_t remain_len = g_i2c_buffer_wrap[bus].len;
658 
659     burst_len = burst_len < remain_len ? burst_len : remain_len;
660     hal_wrap.len = burst_len;
661     hal_wrap.buffer = g_i2c_buffer_wrap[bus].buffer;
662     hal_wrap.restart_flag = g_i2c_buffer_wrap[bus].restart_flag;
663     /* 只有在发送到末尾时,才发送停止位 */
664     if (burst_len == g_i2c_buffer_wrap[bus].len) {
665         hal_wrap.stop_flag = g_i2c_buffer_wrap[bus].stop_flag;
666     } else {
667         hal_wrap.stop_flag = false;
668     }
669 
670     g_i2c_buffer_wrap[bus].len -= burst_len;
671     g_i2c_buffer_wrap[bus].buffer += burst_len;
672 
673     hal_i2c_write(bus, &hal_wrap);
674 }
675 
i2c_evt_rx_callback(i2c_bus_t bus)676 static void i2c_evt_rx_callback(i2c_bus_t bus)
677 {
678     uint32_t burst_len;
679     uint32_t read_len;
680     uint32_t cmd_len;
681     hal_i2c_buffer_wrap_t read_wrap;
682     hal_i2c_buffer_wrap_t cmd_wrap;
683 
684     hal_i2c_ctrl(bus, I2C_CTRL_GET_READ_NUM, (uintptr_t)&burst_len);
685 
686     read_len = g_i2c_buffer_wrap[bus].len;
687     read_len = burst_len < read_len ? burst_len : read_len;
688 
689     read_wrap.len = read_len;
690     read_wrap.buffer = g_i2c_buffer_wrap[bus].buffer;
691     read_wrap.restart_flag = g_i2c_buffer_wrap[bus].restart_flag;
692     read_wrap.stop_flag = g_i2c_buffer_wrap[bus].stop_flag;
693 
694     hal_i2c_read(bus, &read_wrap);
695 
696     g_i2c_buffer_wrap[bus].buffer += read_len;
697     g_i2c_buffer_wrap[bus].len -= read_len;
698 
699     /* 先是读取已有的数据,接下来发送读取之后的数据的命令 */
700     if (g_i2c_buffer_wrap[bus].len == 0) {
701         hal_i2c_ctrl(bus, I2C_CTRL_READ_RESTORE, (uintptr_t)NULL);
702         i2c_int_mode_up(&g_i2c_int_sem[bus]);
703         if (g_i2c_ctrl[bus].callback != NULL) {
704             g_i2c_ctrl[bus].callback(bus, I2C_IRQ_EVT_RX_DONE);
705         }
706         return;
707     }
708 
709     hal_i2c_ctrl(bus, I2C_CTRL_GET_READ_NUM, (uintptr_t)&burst_len);
710     cmd_len = g_i2c_buffer_wrap[bus].len;
711     cmd_len = burst_len < cmd_len ? burst_len : cmd_len;
712 
713     cmd_wrap.buffer = g_i2c_buffer_wrap[bus].buffer;
714     cmd_wrap.len = cmd_len;
715     cmd_wrap.restart_flag = g_i2c_buffer_wrap[bus].restart_flag;
716     /* 只有在发送到末尾时,才发送停止位 */
717     if (cmd_len < g_i2c_buffer_wrap[bus].len) {
718         cmd_wrap.stop_flag = false;
719     } else {
720         cmd_wrap.stop_flag = g_i2c_buffer_wrap[bus].stop_flag;
721     }
722 
723     hal_i2c_ctrl(bus, I2C_CTRL_FLUSH_RX_FIFO, (uintptr_t)&cmd_wrap);
724 }
725 
i2c_write_int(i2c_bus_t bus,uint16_t dev_addr,hal_i2c_buffer_wrap_t * data_cfg)726 static errcode_t i2c_write_int(i2c_bus_t bus, uint16_t dev_addr, hal_i2c_buffer_wrap_t *data_cfg)
727 {
728     hal_i2c_prepare_config_t cfg = { 0 };
729     i2c_ctrl_block_info_t *i2c_ctrl = &g_i2c_ctrl[bus];
730 
731     cfg.addr = dev_addr;
732     cfg.operation_type = I2C_DATA_OPERATION_TYPE_INT;
733     cfg.total_len = data_cfg->len;
734     i2c_ctrl->operate_type = cfg.operation_type;
735 
736     g_i2c_buffer_wrap[bus].buffer = data_cfg->buffer;
737     g_i2c_buffer_wrap[bus].len = data_cfg->len;
738     g_i2c_buffer_wrap[bus].restart_flag = data_cfg->restart_flag;
739     g_i2c_buffer_wrap[bus].stop_flag = data_cfg->stop_flag;
740 
741     errcode_t ret = hal_i2c_ctrl(bus, I2C_CTRL_WRITE_PREPARE, (uintptr_t)&cfg);
742     if (ret != ERRCODE_SUCC) {
743         return ret;
744     }
745 
746     if (i2c_int_mode_down(&g_i2c_int_sem[bus]) != OSAL_SUCCESS) {
747         return ERRCODE_I2C_DMA_TRANSFER_ERROR;
748     }
749 
750     return ret;
751 }
752 
i2c_read_int(i2c_bus_t bus,uint16_t dev_addr,hal_i2c_buffer_wrap_t * data_cfg)753 static errcode_t i2c_read_int(i2c_bus_t bus, uint16_t dev_addr, hal_i2c_buffer_wrap_t *data_cfg)
754 {
755     hal_i2c_prepare_config_t cfg = { 0 };
756     i2c_ctrl_block_info_t *i2c_ctrl = &g_i2c_ctrl[bus];
757 
758     cfg.addr = dev_addr;
759     cfg.operation_type = I2C_DATA_OPERATION_TYPE_INT;
760     cfg.total_len = data_cfg->len;
761     i2c_ctrl->operate_type = cfg.operation_type;
762 
763     errcode_t ret = hal_i2c_ctrl(bus, I2C_CTRL_READ_PREPARE, (uintptr_t)&cfg);
764     if (ret != ERRCODE_SUCC) {
765         return ret;
766     }
767 
768     uint32_t burst_num;
769     uint32_t len = data_cfg->len;
770     hal_i2c_buffer_wrap_t hal_read_cmd;
771 
772     hal_i2c_ctrl(bus, I2C_CTRL_GET_READ_NUM, (uintptr_t)&burst_num);
773     burst_num = burst_num < len ? burst_num : len;
774     g_i2c_buffer_wrap[bus].len = data_cfg->len;
775     g_i2c_buffer_wrap[bus].buffer = data_cfg->buffer;
776     g_i2c_buffer_wrap[bus].restart_flag = data_cfg->restart_flag;
777     g_i2c_buffer_wrap[bus].stop_flag = data_cfg->stop_flag;
778 
779     hal_read_cmd.len = burst_num;
780     hal_read_cmd.buffer = data_cfg->buffer;
781     hal_read_cmd.restart_flag = data_cfg->restart_flag;
782     if (burst_num == g_i2c_buffer_wrap[bus].len) {
783         hal_read_cmd.stop_flag = data_cfg->stop_flag;
784     } else {
785         hal_read_cmd.stop_flag = false;
786     }
787     hal_i2c_ctrl(bus, I2C_CTRL_FLUSH_RX_FIFO, (uintptr_t)&hal_read_cmd);
788 
789     if (i2c_int_mode_down(&g_i2c_int_sem[bus]) != OSAL_SUCCESS) {
790         return ERRCODE_I2C_DMA_TRANSFER_ERROR;
791     }
792 
793     return ret;
794 }
795 
796 #endif  /* CONFIG_I2C_SUPPORT_INT */
797 
i2c_evt_callback(i2c_bus_t bus,hal_i2c_evt_id_t evt,uintptr_t param)798 static errcode_t i2c_evt_callback(i2c_bus_t bus, hal_i2c_evt_id_t evt, uintptr_t param)
799 {
800     unused(param);
801     unused(evt);
802     if (g_i2c_ctrl[bus].operate_type == I2C_DATA_OPERATION_TYPE_POLL) {
803         return ERRCODE_SUCC;
804     }
805 
806 #if defined(CONFIG_I2C_SUPPORT_INT) && (CONFIG_I2C_SUPPORT_INT == 1)
807     if (evt == I2C_EVT_TX_READY) {
808         i2c_evt_tx_callback(bus);
809     } else if (evt == I2C_EVT_RX_READY) {
810         i2c_evt_rx_callback(bus);
811     } else if (evt == I2C_EVT_TRANSMITION_DONE) {
812         i2c_int_mode_up(&g_i2c_int_sem[bus]);
813     } else if (evt == I2C_EVT_TRANSMITION_ABRT) {
814         i2c_evt_err_callback(bus);
815     } else if (evt == I2C_EVT_TRANSMITION_BUSY) {
816         i2c_evt_busy_callback(bus);
817     }
818 
819 #endif  /* CONFIG_I2C_SUPPORT_INT */
820     return ERRCODE_SUCC;
821 }
822 
823 #if defined(CONFIG_I2C_SUPPORT_INT) && (CONFIG_I2C_SUPPORT_INT == 1)
uapi_i2c_set_irq_mode(i2c_bus_t bus,bool irq_en)824 errcode_t uapi_i2c_set_irq_mode(i2c_bus_t bus, bool irq_en)
825 {
826     if (bus >= I2C_BUS_NONE) {
827         return ERRCODE_I2C_INVALID_PARAMETER;
828     }
829     if (irq_en) {
830         g_i2c_ctrl[bus].operate_type = I2C_DATA_OPERATION_TYPE_INT;
831     } else {
832         g_i2c_ctrl[bus].operate_type = I2C_DATA_OPERATION_TYPE_POLL;
833     }
834 
835     return ERRCODE_SUCC;
836 }
837 
uapi_i2c_register_irq_callback(i2c_bus_t bus,i2c_irq_callback_t callback)838 errcode_t uapi_i2c_register_irq_callback(i2c_bus_t bus, i2c_irq_callback_t callback)
839 {
840     g_i2c_ctrl[bus].callback = callback;
841     return ERRCODE_SUCC;
842 }
843 
uapi_i2c_unregister_irq_callback(i2c_bus_t bus)844 errcode_t uapi_i2c_unregister_irq_callback(i2c_bus_t bus)
845 {
846     g_i2c_ctrl[bus].callback = NULL;
847     return ERRCODE_SUCC;
848 }
849 #endif  /* CONFIG_I2C_SUPPORT_INT */
850 
i2c_int_mode_init(i2c_bus_t bus)851 static void i2c_int_mode_init(i2c_bus_t bus)
852 {
853     unused(bus);
854 #if defined(CONFIG_I2C_SUPPORT_INT) && (CONFIG_I2C_SUPPORT_INT == 1)
855     (void)memset_s(&g_i2c_int_sem[bus], sizeof(g_i2c_int_sem[bus]),
856                    0, sizeof(g_i2c_int_sem[bus]));
857 #if !defined(CONFIG_I2C_SUPPORT_IN_CHIP_LOOPBACK)
858     (void)osal_sem_init(&g_i2c_int_sem[bus], 0);
859 #endif
860 #endif  /* CONFIG_I2C_SUPPORT_INT */
861 }
862 
i2c_int_mode_sem_deinit(i2c_bus_t bus)863 static void i2c_int_mode_sem_deinit(i2c_bus_t bus)
864 {
865     unused(bus);
866 #if defined(CONFIG_I2C_SUPPORT_INT) && (CONFIG_I2C_SUPPORT_INT == 1)
867 #if !defined(CONFIG_I2C_SUPPORT_IN_CHIP_LOOPBACK)
868     osal_sem_destroy(&g_i2c_int_sem[bus]);
869 #endif
870 #endif  /* CONFIG_I2C_SUPPORT_INT */
871 }
872 
873 #if defined(CONFIG_I2C_SUPPORT_DMA) && (CONFIG_I2C_SUPPORT_DMA == 1)
uapi_i2c_set_dma_mode(i2c_bus_t bus,bool dma_en)874 errcode_t uapi_i2c_set_dma_mode(i2c_bus_t bus, bool dma_en)
875 {
876     if (bus >= I2C_BUS_NONE) {
877         return ERRCODE_I2C_INVALID_PARAMETER;
878     }
879     if (dma_en) {
880         g_i2c_ctrl[bus].operate_type = I2C_DATA_OPERATION_TYPE_DMA;
881     } else {
882         g_i2c_ctrl[bus].operate_type = I2C_DATA_OPERATION_TYPE_POLL;
883     }
884     return ERRCODE_SUCC;
885 }
886 #endif  /* CONFIG_I2C_SUPPORT_DMA */
887 
i2c_dma_mode_init(i2c_bus_t bus)888 static void i2c_dma_mode_init(i2c_bus_t bus)
889 {
890     unused(bus);
891 #if defined(CONFIG_I2C_SUPPORT_DMA) && (CONFIG_I2C_SUPPORT_DMA == 1)
892     (void)memset_s(&(g_dma_trans[bus].dma_sem), sizeof(g_dma_trans[bus].dma_sem),
893                    0, sizeof(g_dma_trans[bus].dma_sem));
894     (void)osal_sem_init(&(g_dma_trans[bus].dma_sem), 0);
895 #endif  /* CONFIG_I2C_SUPPORT_DMA */
896 }
897 
i2c_dma_mode_sem_deinit(i2c_bus_t bus)898 static void i2c_dma_mode_sem_deinit(i2c_bus_t bus)
899 {
900     unused(bus);
901 #if defined(CONFIG_I2C_SUPPORT_DMA) && (CONFIG_I2C_SUPPORT_DMA == 1)
902     osal_sem_destroy(&(g_dma_trans[bus].dma_sem));
903 #endif  /* CONFIG_I2C_SUPPORT_DMA */
904 }
905 
i2c_mutex_init(i2c_bus_t bus)906 static void i2c_mutex_init(i2c_bus_t bus)
907 {
908     unused(bus);
909 #if defined(CONFIG_I2C_SUPPORT_CONCURRENCY) && (CONFIG_I2C_SUPPORT_CONCURRENCY == 1)
910     (void)memset_s(&g_i2c_mutex[bus], sizeof(g_i2c_mutex[bus]), 0, sizeof(g_i2c_mutex[bus]));
911     (void)osal_mutex_init(&g_i2c_mutex[bus]);
912 #endif  /* CONFIG_I2C_SUPPORT_CONCURRENCY */
913 }
914 
i2c_mutex_destroy(i2c_bus_t bus)915 static void i2c_mutex_destroy(i2c_bus_t bus)
916 {
917     unused(bus);
918 #if defined(CONFIG_I2C_SUPPORT_CONCURRENCY) && (CONFIG_I2C_SUPPORT_CONCURRENCY == 1)
919     osal_mutex_destroy(&g_i2c_mutex[bus]);
920 #endif  /* CONFIG_I2C_SUPPORT_CONCURRENCY */
921 }
922 
i2c_mutex_lock(i2c_bus_t bus)923 static void i2c_mutex_lock(i2c_bus_t bus)
924 {
925     unused(bus);
926 #if defined(CONFIG_I2C_SUPPORT_CONCURRENCY) && (CONFIG_I2C_SUPPORT_CONCURRENCY == 1)
927     osal_mutex_lock(&g_i2c_mutex[bus]);
928 #endif  /* CONFIG_I2C_SUPPORT_CONCURRENCY */
929 }
930 
i2c_mutex_unlock(i2c_bus_t bus)931 static void i2c_mutex_unlock(i2c_bus_t bus)
932 {
933     unused(bus);
934 #if defined(CONFIG_I2C_SUPPORT_CONCURRENCY) && (CONFIG_I2C_SUPPORT_CONCURRENCY == 1)
935     osal_mutex_unlock(&g_i2c_mutex[bus]);
936 #endif  /* CONFIG_I2C_SUPPORT_CONCURRENCY */
937 }
938 
i2c_init_check(i2c_bus_t bus,uint32_t baudrate)939 static errcode_t i2c_init_check(i2c_bus_t bus, uint32_t baudrate)
940 {
941     if (unlikely(bus >= I2C_BUS_MAX_NUM)) {
942         return ERRCODE_I2C_INVALID_PARAMETER;
943     }
944     if (unlikely(baudrate > I2C_HS_MODE_BAUDRATE_HIGH_LIMIT || baudrate == 0)) {
945         return ERRCODE_I2C_RATE_INVALID;
946     }
947     if (g_i2c_ctrl[bus].init_flag == true) {
948         return ERRCODE_I2C_ALREADY_INIT;
949     }
950     return ERRCODE_SUCC;
951 }
952 
953 #if defined(CONFIG_I2C_SUPPORT_MASTER) && (CONFIG_I2C_SUPPORT_MASTER == 1)
i2c_master_init_check(i2c_bus_t bus,uint32_t baudrate,uint8_t hscode)954 static errcode_t i2c_master_init_check(i2c_bus_t bus, uint32_t baudrate, uint8_t hscode)
955 {
956     errcode_t ret = i2c_init_check(bus, baudrate);
957     if (ret != ERRCODE_SUCC) {
958         return ret;
959     }
960 
961     if (unlikely(hscode > I2C_HS_MODE_MASTER_CODE_MAX)) {
962         return ERRCODE_I2C_INVALID_PARAMETER;
963     }
964     return ERRCODE_SUCC;
965 }
966 
uapi_i2c_master_init(i2c_bus_t bus,uint32_t baudrate,uint8_t hscode)967 errcode_t uapi_i2c_master_init(i2c_bus_t bus, uint32_t baudrate, uint8_t hscode)
968 {
969     errcode_t ret = i2c_master_init_check(bus, baudrate, hscode);
970     if (ret != ERRCODE_SUCC) {
971         return ret;
972     }
973 
974 #if defined(CONFIG_I2C_SUPPORT_LPC)
975     i2c_port_clock_enable(bus, true);
976 #endif
977 
978     i2c_mutex_init(bus);
979     i2c_int_mode_init(bus);
980     i2c_dma_mode_init(bus);
981 
982     ret = hal_i2c_master_init(bus, baudrate, hscode, i2c_evt_callback);
983     if (ret != ERRCODE_SUCC) {
984         i2c_int_mode_sem_deinit(bus);
985         i2c_dma_mode_sem_deinit(bus);
986         i2c_mutex_destroy(bus);
987         return ret;
988     }
989 
990 #if defined(CONFIG_I2C_SUPPORT_INT) && (CONFIG_I2C_SUPPORT_INT == 1)
991     i2c_port_register_irq(bus);
992 #endif
993 
994     i2c_ctrl_block_info_t *i2c_ctrl = &g_i2c_ctrl[bus];
995     i2c_ctrl->init_flag = true;
996     i2c_ctrl->master_flag = true;
997     i2c_ctrl->hscode = hscode;
998     return ERRCODE_SUCC;
999 }
1000 
i2c_fifo_check(i2c_bus_t bus)1001 static errcode_t i2c_fifo_check(i2c_bus_t bus)
1002 {
1003     if (hal_i2c_ctrl(bus, I2C_CTRL_CHECK_TX_FIFO_EMPTY, (uintptr_t)CONFIG_I2C_WAIT_CONDITION_TIMEOUT) != ERRCODE_SUCC) {
1004         return ERRCODE_I2C_TIMEOUT;
1005     }
1006     return ERRCODE_SUCC;
1007 }
1008 
uapi_i2c_master_write(i2c_bus_t bus,uint16_t dev_addr,i2c_data_t * data)1009 errcode_t uapi_i2c_master_write(i2c_bus_t bus, uint16_t dev_addr, i2c_data_t *data)
1010 {
1011     errcode_t ret = i2c_write_pre_check(bus, data);
1012     if (ret != ERRCODE_SUCC) {
1013         return ret;
1014     }
1015 
1016     ret = i2c_fifo_check(bus);
1017     if (ret != ERRCODE_SUCC) {
1018         return ret;
1019     }
1020 
1021     hal_i2c_buffer_wrap_t buffer_wrap = { 0 };
1022     buffer_wrap.buffer = data->send_buf;
1023     buffer_wrap.len = data->send_len;
1024     buffer_wrap.stop_flag = true;
1025     buffer_wrap.restart_flag = false;
1026 
1027     i2c_mutex_lock(bus);
1028 #if defined(CONFIG_I2C_SUPPORT_DMA) && (CONFIG_I2C_SUPPORT_DMA == 1)
1029 #if defined(CONFIG_I2C_SUPPORT_POLL_AND_DMA_AUTO_SWITCH) && (CONFIG_I2C_SUPPORT_POLL_AND_DMA_AUTO_SWITCH == 1)
1030     if (buffer_wrap.len > CONFIG_I2C_POLL_AND_DMA_AUTO_SWITCH_THRESHOLD) {
1031         uapi_i2c_set_dma_mode(bus, true);
1032         ret = i2c_write_by_dma(bus, dev_addr, &buffer_wrap);
1033         i2c_mutex_unlock(bus);
1034         return ret;
1035     }
1036     uapi_i2c_set_dma_mode(bus, false);
1037 #else
1038     if (g_i2c_ctrl[bus].operate_type == I2C_DATA_OPERATION_TYPE_DMA) {
1039         ret = i2c_write_by_dma(bus, dev_addr, &buffer_wrap);
1040         i2c_mutex_unlock(bus);
1041         return ret;
1042     }
1043 #endif  /* CONFIG_I2C_SUPPORT_POLL_AND_DMA_AUTO_SWITCH */
1044 #endif  /* CONFIG_I2C_SUPPORT_DMA */
1045 #if defined(CONFIG_I2C_SUPPORT_INT) && (CONFIG_I2C_SUPPORT_INT == 1)
1046     if (g_i2c_ctrl[bus].operate_type == I2C_DATA_OPERATION_TYPE_INT) {
1047         ret = i2c_write_int(bus, dev_addr, &buffer_wrap);
1048         i2c_mutex_unlock(bus);
1049         return ret;
1050     }
1051 #endif  /* CONFIG_I2C_SUPPORT_INT */
1052     ret = i2c_poll_write(bus, dev_addr, &buffer_wrap, true);
1053     i2c_mutex_unlock(bus);
1054     return ret;
1055 }
1056 
uapi_i2c_master_read(i2c_bus_t bus,uint16_t dev_addr,i2c_data_t * data)1057 errcode_t uapi_i2c_master_read(i2c_bus_t bus, uint16_t dev_addr, i2c_data_t *data)
1058 {
1059     errcode_t ret = i2c_read_pre_check(bus, data);
1060     if (ret != ERRCODE_SUCC) {
1061         return ret;
1062     }
1063 
1064     hal_i2c_buffer_wrap_t buffer_wrap = { 0 };
1065     buffer_wrap.buffer = data->receive_buf;
1066     buffer_wrap.len = data->receive_len;
1067     buffer_wrap.stop_flag = true;
1068     buffer_wrap.restart_flag = false;
1069 
1070     i2c_mutex_lock(bus);
1071 #if defined(CONFIG_I2C_SUPPORT_DMA) && (CONFIG_I2C_SUPPORT_DMA == 1)
1072 #if defined(CONFIG_I2C_SUPPORT_POLL_AND_DMA_AUTO_SWITCH) && (CONFIG_I2C_SUPPORT_POLL_AND_DMA_AUTO_SWITCH == 1)
1073     if (buffer_wrap.len > CONFIG_I2C_POLL_AND_DMA_AUTO_SWITCH_THRESHOLD) {
1074         uapi_i2c_set_dma_mode(bus, true);
1075         errcode_t ret = i2c_read_by_dma(bus, dev_addr, &buffer_wrap);
1076         if (ret != ERRCODE_SUCC) {
1077             i2c_mutex_unlock(bus);
1078             return ret;
1079         }
1080         ret = i2c_read_do_send_cmd(bus, &buffer_wrap);
1081         i2c_mutex_unlock(bus);
1082         return ret;
1083     }
1084     uapi_i2c_set_dma_mode(bus, false);
1085 #else
1086     if (g_i2c_ctrl[bus].operate_type == I2C_DATA_OPERATION_TYPE_DMA) {
1087         errcode_t ret = i2c_read_by_dma(bus, dev_addr, &buffer_wrap);
1088         if (ret != ERRCODE_SUCC) {
1089             i2c_mutex_unlock(bus);
1090             return ret;
1091         }
1092         ret = i2c_read_do_send_cmd(bus, &buffer_wrap);
1093         i2c_mutex_unlock(bus);
1094         return ret;
1095     }
1096 #endif  /* CONFIG_I2C_SUPPORT_POLL_AND_DMA_AUTO_SWITCH */
1097 #endif  /* CONFIG_I2C_SUPPORT_DMA */
1098 #if defined(CONFIG_I2C_SUPPORT_INT) && (CONFIG_I2C_SUPPORT_INT == 1)
1099     if (g_i2c_ctrl[bus].operate_type == I2C_DATA_OPERATION_TYPE_INT) {
1100         ret = i2c_read_int(bus, dev_addr, &buffer_wrap);
1101         i2c_mutex_unlock(bus);
1102         return ret;
1103     }
1104 #endif  /* CONFIG_I2C_SUPPORT_INT */
1105     ret = i2c_poll_read(bus, dev_addr, &buffer_wrap, true);
1106     i2c_mutex_unlock(bus);
1107     return ret;
1108 }
1109 
uapi_i2c_master_writeread(i2c_bus_t bus,uint16_t dev_addr,i2c_data_t * data)1110 errcode_t uapi_i2c_master_writeread(i2c_bus_t bus, uint16_t dev_addr, i2c_data_t *data)
1111 {
1112     errcode_t ret = i2c_write_pre_check(bus, data);
1113     if (ret != ERRCODE_SUCC) {
1114         return ret;
1115     }
1116     ret = i2c_read_pre_check(bus, data);
1117     if (ret != ERRCODE_SUCC) {
1118         return ret;
1119     }
1120     ret = i2c_fifo_check(bus);
1121     if (ret != ERRCODE_SUCC) {
1122         return ret;
1123     }
1124 
1125     i2c_mutex_lock(bus);
1126     ret = uapi_i2c_master_write(bus, dev_addr, data);
1127     if (ret != ERRCODE_SUCC) {
1128         i2c_mutex_unlock(bus);
1129         return ret;
1130     }
1131 
1132     i2c_wait_condition_t condition = { 0 };
1133     condition.ctrl_mask = i2c_ctrl_get_mask(I2C_CTRL_CHECK_RESTART_READY);
1134     (void)i2c_wait(bus, &condition, CONFIG_I2C_WAIT_CONDITION_TIMEOUT);
1135 
1136     ret = uapi_i2c_master_read(bus, dev_addr, data);
1137     i2c_mutex_unlock(bus);
1138     return ret;
1139 }
1140 #endif  /* CONFIG_I2C_SUPPORT_MASTER */
1141 
1142 #if defined(CONFIG_I2C_SUPPORT_SLAVE) && (CONFIG_I2C_SUPPORT_SLAVE == 1)
uapi_i2c_slave_init(i2c_bus_t bus,uint32_t baudrate,uint16_t addr)1143 errcode_t uapi_i2c_slave_init(i2c_bus_t bus, uint32_t baudrate, uint16_t addr)
1144 {
1145     errcode_t ret = i2c_init_check(bus, baudrate);
1146     if (ret != ERRCODE_SUCC) {
1147         return ret;
1148     }
1149 
1150 #if defined(CONFIG_I2C_SUPPORT_LPC)
1151     i2c_port_clock_enable(bus, true);
1152 #endif
1153 
1154     i2c_mutex_init(bus);
1155     i2c_int_mode_init(bus);
1156     i2c_dma_mode_init(bus);
1157 
1158     ret = hal_i2c_slave_init(bus, baudrate, addr, i2c_evt_callback);
1159     if (ret != ERRCODE_SUCC) {
1160         i2c_int_mode_sem_deinit(bus);
1161         i2c_dma_mode_sem_deinit(bus);
1162         i2c_mutex_destroy(bus);
1163         return ret;
1164     }
1165 
1166 #if defined(CONFIG_I2C_SUPPORT_INT) && (CONFIG_I2C_SUPPORT_INT == 1)
1167     i2c_port_register_irq(bus);
1168 #endif
1169 
1170     i2c_ctrl_block_info_t *i2c_ctrl = &g_i2c_ctrl[bus];
1171     i2c_ctrl->init_flag = true;
1172     i2c_ctrl->master_flag = false;
1173     i2c_ctrl->addr = addr;
1174     return ERRCODE_SUCC;
1175 }
1176 
uapi_i2c_slave_write(i2c_bus_t bus,i2c_data_t * data)1177 errcode_t uapi_i2c_slave_write(i2c_bus_t bus, i2c_data_t *data)
1178 {
1179     errcode_t ret = i2c_write_pre_check(bus, data);
1180     if (ret != ERRCODE_SUCC) {
1181         return ret;
1182     }
1183 
1184     ret = i2c_fifo_check(bus);
1185     if (ret != ERRCODE_SUCC) {
1186         return ret;
1187     }
1188 
1189     hal_i2c_buffer_wrap_t buffer_wrap = { 0 };
1190     buffer_wrap.buffer = data->send_buf;
1191     buffer_wrap.len = data->send_len;
1192     buffer_wrap.stop_flag = false;
1193 
1194     i2c_mutex_lock(bus);
1195 #if defined(CONFIG_I2C_SUPPORT_DMA) && (CONFIG_I2C_SUPPORT_DMA == 1)
1196 #if defined(CONFIG_I2C_SUPPORT_POLL_AND_DMA_AUTO_SWITCH) && (CONFIG_I2C_SUPPORT_POLL_AND_DMA_AUTO_SWITCH == 1)
1197     if (buffer_wrap.len > CONFIG_I2C_POLL_AND_DMA_AUTO_SWITCH_THRESHOLD) {
1198         uapi_i2c_set_dma_mode(bus, true);
1199         ret = i2c_write_by_dma(bus, I2C_DEFAULT_DEV_ADDRESS, &buffer_wrap);
1200         i2c_mutex_unlock(bus);
1201         return ret;
1202     }
1203     uapi_i2c_set_dma_mode(bus, false);
1204 #else
1205     if (g_i2c_ctrl[bus].operate_type == I2C_DATA_OPERATION_TYPE_DMA) {
1206         ret = i2c_write_by_dma(bus, I2C_DEFAULT_DEV_ADDRESS, &buffer_wrap);
1207         i2c_mutex_unlock(bus);
1208         return ret;
1209     }
1210 #endif  /* CONFIG_I2C_SUPPORT_POLL_AND_DMA_AUTO_SWITCH */
1211 #endif  /* CONFIG_I2C_SUPPORT_DMA */
1212 #if defined(CONFIG_I2C_SUPPORT_INT) && (CONFIG_I2C_SUPPORT_INT == 1)
1213     if (g_i2c_ctrl[bus].operate_type == I2C_DATA_OPERATION_TYPE_INT) {
1214         ret = i2c_write_int(bus, I2C_DEFAULT_DEV_ADDRESS, &buffer_wrap);
1215         i2c_mutex_unlock(bus);
1216         return ret;
1217     }
1218 #endif  /* CONFIG_I2C_SUPPORT_INT */
1219     ret = i2c_poll_write(bus, I2C_DEFAULT_DEV_ADDRESS, &buffer_wrap, true);
1220     i2c_mutex_unlock(bus);
1221     return ret;
1222 }
1223 
uapi_i2c_slave_read(i2c_bus_t bus,i2c_data_t * data)1224 errcode_t uapi_i2c_slave_read(i2c_bus_t bus, i2c_data_t *data)
1225 {
1226     errcode_t ret = i2c_read_pre_check(bus, data);
1227     if (ret != ERRCODE_SUCC) {
1228         return ret;
1229     }
1230 
1231     hal_i2c_buffer_wrap_t buffer_wrap;
1232     buffer_wrap.buffer = data->receive_buf;
1233     buffer_wrap.len = data->receive_len;
1234     buffer_wrap.stop_flag = false;
1235     buffer_wrap.restart_flag = false;
1236 
1237     i2c_mutex_lock(bus);
1238 #if defined(CONFIG_I2C_SUPPORT_DMA) && (CONFIG_I2C_SUPPORT_DMA == 1)
1239 #if defined(CONFIG_I2C_SUPPORT_POLL_AND_DMA_AUTO_SWITCH) && (CONFIG_I2C_SUPPORT_POLL_AND_DMA_AUTO_SWITCH == 1)
1240     if (buffer_wrap.len > CONFIG_I2C_POLL_AND_DMA_AUTO_SWITCH_THRESHOLD) {
1241         uapi_i2c_set_dma_mode(bus, true);
1242         ret = i2c_read_by_dma(bus, I2C_DEFAULT_DEV_ADDRESS, &buffer_wrap);
1243         i2c_mutex_unlock(bus);
1244         return ret;
1245     }
1246     uapi_i2c_set_dma_mode(bus, false);
1247 #else
1248     if (g_i2c_ctrl[bus].operate_type == I2C_DATA_OPERATION_TYPE_DMA) {
1249         ret = i2c_read_by_dma(bus, I2C_DEFAULT_DEV_ADDRESS, &buffer_wrap);
1250         i2c_mutex_unlock(bus);
1251         return ret;
1252     }
1253 #endif  /* CONFIG_I2C_SUPPORT_POLL_AND_DMA_AUTO_SWITCH */
1254 #endif  /* CONFIG_I2C_SUPPORT_DMA */
1255 
1256 #if defined(CONFIG_I2C_SUPPORT_INT) && (CONFIG_I2C_SUPPORT_INT == 1)
1257     if (g_i2c_ctrl[bus].operate_type == I2C_DATA_OPERATION_TYPE_INT) {
1258         ret = i2c_read_int(bus, I2C_DEFAULT_DEV_ADDRESS, &buffer_wrap);
1259         i2c_mutex_unlock(bus);
1260         return ret;
1261     }
1262 #endif  /* CONFIG_I2C_SUPPORT_INT */
1263     ret = i2c_poll_read(bus, I2C_DEFAULT_DEV_ADDRESS, &buffer_wrap, true);
1264     i2c_mutex_unlock(bus);
1265     return ret;
1266 }
1267 #endif  /* CONFIG_I2C_SUPPORT_SLAVE */
1268 
uapi_i2c_deinit(i2c_bus_t bus)1269 errcode_t uapi_i2c_deinit(i2c_bus_t bus)
1270 {
1271     errcode_t ret = i2c_bus_init_check(bus);
1272     if (ret != ERRCODE_SUCC) {
1273         return ret;
1274     }
1275     i2c_ctrl_block_info_t *i2c_ctrl = &g_i2c_ctrl[bus];
1276 
1277     hal_i2c_deinit(bus);
1278     i2c_int_mode_sem_deinit(bus);
1279     i2c_dma_mode_sem_deinit(bus);
1280     i2c_mutex_destroy(bus);
1281 #if defined(CONFIG_I2C_SUPPORT_INT) && (CONFIG_I2C_SUPPORT_INT == 1)
1282     i2c_port_unregister_irq(bus);
1283 #endif
1284 #if defined(CONFIG_I2C_SUPPORT_LPC)
1285     i2c_port_clock_enable(bus, false);
1286 #endif
1287 
1288     i2c_ctrl->init_flag = false;
1289     i2c_ctrl->master_flag = false;
1290     return ERRCODE_SUCC;
1291 }
1292 
uapi_i2c_set_baudrate(i2c_bus_t bus,uint32_t baudrate)1293 errcode_t uapi_i2c_set_baudrate(i2c_bus_t bus, uint32_t baudrate)
1294 {
1295     if (baudrate > I2C_HS_MODE_BAUDRATE_HIGH_LIMIT || baudrate == 0) {
1296         return ERRCODE_I2C_RATE_INVALID;
1297     }
1298     errcode_t ret = i2c_bus_init_check(bus);
1299     if (ret != ERRCODE_SUCC) {
1300         return ret;
1301     }
1302 
1303     i2c_ctrl_block_info_t *i2c_ctrl = &g_i2c_ctrl[bus];
1304     i2c_mutex_lock(bus);
1305     if (i2c_ctrl->master_flag == true) {
1306         ret = hal_i2c_master_init(bus, baudrate, i2c_ctrl->hscode, i2c_evt_callback);
1307     } else {
1308         ret = hal_i2c_slave_init(bus, baudrate, i2c_ctrl->addr, i2c_evt_callback);
1309     }
1310     i2c_mutex_unlock(bus);
1311     return ret;
1312 }
1313 
1314 #if defined(CONFIG_I2C_SUPPORT_LPM)
uapi_i2c_suspend(uintptr_t arg)1315 errcode_t uapi_i2c_suspend(uintptr_t arg)
1316 {
1317     unused(arg);
1318     return ERRCODE_SUCC;
1319 }
1320 
uapi_i2c_resume(uintptr_t arg)1321 errcode_t uapi_i2c_resume(uintptr_t arg)
1322 {
1323     unused(arg);
1324     return ERRCODE_SUCC;
1325 }
1326 #endif