1 /*
2 * Copyright (c) 2022 ASR Microelectronics (Shanghai) Co., Ltd. All rights reserved.
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
16 #ifndef _DUET_I2C_H_
17 #define _DUET_I2C_H_
18 #include <stdint.h>
19 #include <errno.h>
20
21 #define I2C_MASTER (0)
22 #define I2C_SLAVE (1)
23 #define I2C_ROLE_MODE I2C_MASTER
24 #define I2C_ADDRESS 0x66
25
26 #define I2C_SCL_STATUS_BIT (1)
27 #define I2C_SDA_STATUS_BIT (0)
28
29 // TWSI_NEW
30 #define I2C_INTERRUPT_RX_FIFO_OVERRUN_EN (1 << 31)
31 #define I2C_INTERRUPT_RX_FIFO_FULL_EN (1 << 30)
32 #define I2C_INTERRUPT_TX_FIFO_EMPTY_EN (1 << 28)
33 #define I2C_INTERRUPT_RX_FIFO_HALF_FULL_EN (1 << 29)
34 #define I2C_INTERRUPT_TRANS_DONE_EN (1 << 27)
35 #define I2C_INTERRUPT_SLAVE_ADDR_DET_EN (1 << 23)
36 #define I2C_INTERRUPT_ARBT_LOSS_DET_EN (1 << 18)
37 #define I2C_INTERRUPT_MASTER_STOP_DET_EN (1 << 25)
38 #define I2C_INTERRUPT_SLAVE_STOP_DET_EN (1 << 24)
39 #define I2C_INTERRUPT_BUS_ERROR_DET_EN (1 << 22)
40 #define I2C_INTERRUPT_RX_BUFER_FULL_EN (1 << 20)
41 #define I2C_INTERRUPT_TX_BUFFER_EMPTY_EN (1 << 19)
42
43 #define I2C_STATUS_RX_FIFO_OVERRUN (1 << 31)
44 #define I2C_STATUS_RX_FIFO_FULL (1 << 30)
45 #define I2C_STATUS_TX_FIFO_EMPTY (1 << 28)
46 #define I2C_STATUS_TX_FIFO_FULL (0xffff)
47 #define I2C_STATUS_RX_FIFO_HALF_FULL (1 << 29)
48 #define I2C_STATUS_TRANS_DONE (1 << 27)
49 #define I2C_STATUS_MASTER_STOP_DET (1 << 26)
50 #define I2C_STATUS_SLAVE_STOP_DET (1 << 24)
51 #define I2C_STATUS_SLAVE_ADDR_DET (1 << 23)
52 #define I2C_STATUS_BUS_ERROR_DET (1 << 22)
53 #define I2C_STATUS_RX_BUFER_FULL (1 << 20)
54 #define I2C_STATUS_TX_BUFFER_EMPTY (1 << 19)
55 #define I2C_STATUS_UNIT_BUSY (1 << 15)
56 #define I2C_STATUS_BUS_BUSY (1 << 16)
57 #define I2C_STATUS_ACK_NACK (1 << 14)
58 #define I2C_STATUS_RW_MODE (1 << 13)
59
60 #define I2C_TRANS_BEGIN (1 << 4)
61 #define I2C_MST_FIFO_MODE_ENABLE (1 << 5)
62 #define I2C_MST_FIFO_MODE_DISABLE (0)
63
64 #define I2C_MODE_STANDARD (0)
65 #define I2C_MODE_FAST (1)
66 #define I2C_MODE_HIGH_SPEED_0 (2) // not supported in sonata
67 #define I2C_MODE_HIGH_SPEED_1 (3) // not supported in sonata
68 #define I2C_MODE_SET_POS (8)
69 #define I2C_MODE_SET_MASK (3 << I2C_MODE_SET_POS)
70 #define I2C_HS_MASTER_CODE (0x0A)
71
72 #define I2C_UNIT_RESET (1 << 10)
73 #define I2C_DMA_ENABLE (1 << 7)
74 #define I2C_UNIT_ENABLE (1 << 14)
75 #define I2C_SCL_ENABLE (1 << 13)
76
77 /* fifo mode control */
78 #define I2C_TB (1 << 11)
79 #define I2C_SEND_NACK (1 << 10)
80 #define I2C_SEND_STOP (1 << 9)
81 #define I2C_SEND_START (1 << 8)
82 #define I2C_MASTER_ABORT (1 << 12)
83
84 /* non fifo mode control */
85 #define I2C_CR_TB (I2C_TB >> 8)
86 #define I2C_CR_SEND_NACK (I2C_SEND_NACK >> 8)
87 #define I2C_CR_SEND_STOP (I2C_SEND_STOP >> 8)
88 #define I2C_CR_SEND_START (I2C_SEND_START >> 8)
89
90 #define I2C_DEVICE0 0
91 #define I2C_DEVICE1 1
92 #define DUET_I2C_NUM 2
93
94 #define I2C_READ (1)
95 #define I2C_WRITE (0)
96
97 #define I2C_TX_FIFO_DEPTH (8)
98 #define I2C_RX_FIFO_DEPTH (16)
99
100 #define I2C_MEM_ADDR_SIZE_8 (0)
101 #define I2C_MEM_ADDR_SIZE_16 (1)
102 #define I2C_MEM_ADDR_SIZE_32 (3)
103
104 #define DUMMY_BYTE (0x5a)
105 #define MAX_RX_SIZE (100)
106 #define TIME_OUT (1000)
107 #define I2C_WAIT_FOREVER (0xffffffff)
108
109 #define I2C_CLK (52000000)
110 #define I2C_STANDARD_SPEED (100000)
111 #define I2C_FAST_SPEED (400000)
112 #define I2C_HIGH_SPEED (1700000)
113
114 // error number
115 #define I2C_SUCCESS 0 // success
116 #define EI2CNUMERR 1 // I2C port number error
117 #define ETIMEOUT 2 // I2C timeout
118 #define EBUSERR 3 // I2C bus error
119
120 // I2C0 pad group 0: pad 2,3
121 // I2C0 pad group 1: pad 20, 21
122 // I2C1 pad group 0: pad 8, 9
123 // I2C1 pad group 1: pad 22, 23
124 #define I2C0_PAD_GROUP0_ENABLE 1
125 #define I2C0_PAD_GROUP1_ENABLE 0
126 #define I2C1_PAD_GROUP0_ENABLE 1
127 #define I2C1_PAD_GROUP1_ENABLE 0
128
129 typedef void (*duet_i2c_slv_tx_callback_func)(void);
130 typedef void (*duet_i2c_slv_rx_callback_func)(uint8_t);
131 typedef struct {
132 duet_i2c_slv_tx_callback_func tx_func;
133 duet_i2c_slv_rx_callback_func rx_func;
134 } duet_i2c_slv_callback_t;
135
136 typedef struct {
137 uint32_t address_width;
138 uint32_t freq;
139 uint8_t mode;
140 uint16_t dev_addr;
141 } duet_i2c_config_t;
142
143 typedef struct {
144 uint8_t speed_mode;
145 uint8_t fifo_mode;
146 uint8_t dma_mode;
147 uint8_t reserved;
148 } duet_i2c_priv_cfg_t;
149
150 typedef struct {
151 uint8_t port; /* i2c port */
152 duet_i2c_config_t config; /* i2c config */
153 void *priv; /* priv data */
154 } duet_i2c_dev_t;
155
156 int32_t duet_i2c_init(duet_i2c_dev_t *i2c);
157 int32_t duet_i2c_master_send(duet_i2c_dev_t *i2c, uint16_t dev_addr, const uint8_t *data, uint16_t size,
158 uint32_t timeout);
159 int32_t duet_i2c_master_recv(duet_i2c_dev_t *i2c, uint16_t dev_addr, uint8_t *data, uint16_t size, uint32_t timeout);
160 int8_t duet_i2c_master_repeated_write_read(I2C_TypeDef *I2Cx, uint8_t slave_addr,
161 const uint8_t *pwdata, uint8_t *rdata,
162 uint32_t wlen, uint32_t rlen);
163 int32_t duet_i2c_mem_write(duet_i2c_dev_t *i2c, uint16_t dev_addr, uint16_t mem_addr,
164 uint16_t mem_addr_size, const uint8_t *data, uint16_t len,
165 uint32_t timeout);
166
167 int32_t duet_i2c_mem_read(duet_i2c_dev_t *i2c, uint16_t dev_addr, uint16_t mem_addr,
168 uint16_t mem_addr_size, uint8_t *data, uint16_t len,
169 uint32_t timeout);
170 int32_t duet_i2c_finalize(duet_i2c_dev_t *i2c);
171 void duet_i2c_master_dma_send(uint8_t iic_idx, uint32_t *data, uint16_t len);
172 void duet_i2c_master_dma_recv(uint8_t iic_idx, uint32_t *data, uint16_t len);
i2c_write_byte_cmd(I2C_TypeDef * I2Cx,uint8_t data)173 __STATIC_INLINE void i2c_write_byte_cmd(I2C_TypeDef *I2Cx, uint8_t data)
174 {
175 I2Cx->WFIFO = data | I2C_WRITE | I2C_TB;
176 }
177
i2c_read_byte_cmd(I2C_TypeDef * I2Cx)178 __STATIC_INLINE void i2c_read_byte_cmd(I2C_TypeDef *I2Cx)
179 {
180 I2Cx->WFIFO = I2C_TB;
181 }
182
183 /* read one byte from fifo or buffer register */
i2c_receive_byte(I2C_TypeDef * I2Cx)184 __STATIC_INLINE uint8_t i2c_receive_byte(I2C_TypeDef *I2Cx)
185 {
186 if (I2Cx->CR & I2C_MST_FIFO_MODE_ENABLE) {
187 return I2Cx->RFIFO;
188 } else {
189 return I2Cx->DBR;
190 }
191 }
192
193 /* write one byte to fifo or buffer reigster */
i2c_write_byte(I2C_TypeDef * I2Cx,uint16_t data)194 __STATIC_INLINE void i2c_write_byte(I2C_TypeDef *I2Cx, uint16_t data)
195 {
196 // data = data_to_write | any_conrol_bit
197 if (I2Cx->CR & I2C_MST_FIFO_MODE_ENABLE) {
198 I2Cx->WFIFO = data;
199 } else {
200 I2Cx->DBR = data;
201 }
202 }
203
i2c_clear_interrupt(I2C_TypeDef * I2Cx,uint32_t I2C_INTR)204 __STATIC_INLINE void i2c_clear_interrupt(I2C_TypeDef *I2Cx, uint32_t I2C_INTR)
205 {
206 I2Cx->SR |= I2C_INTR;
207 }
208
209 /* I2C needs to set TB for transmitting and receiving a byte
210 this function is mainly for when I2C is used as a slave
211 */
i2c_set_tb(I2C_TypeDef * I2Cx)212 __STATIC_INLINE void i2c_set_tb(I2C_TypeDef *I2Cx)
213 {
214 I2Cx->CR |= I2C_CR_TB;
215 }
216
217 #endif // _DUET_I2C_H_