xref: /optee_os/core/drivers/imx_i2c.c (revision 8e58c34a279d5f2fea3f92e6505288d48a2059b9)
1 // SPDX-License-Identifier: BSD-2-Clause
2 /*
3  * (c) 2020 Jorge Ramirez <jorge@foundries.io>, Foundries Ltd.
4  */
5 #include <arm.h>
6 #include <drivers/imx_i2c.h>
7 #include <initcall.h>
8 #include <io.h>
9 #include <kernel/delay.h>
10 #include <mm/core_memprot.h>
11 #include <mm/core_mmu.h>
12 #include <platform_config.h>
13 #include <stdlib.h>
14 #include <trace.h>
15 #include <util.h>
16 
17 #define I2C_CLK_RATE	24000000 /* Bits per second */
18 
19 /* SoC optional: iomuxc daisy configuration register */
20 #ifndef I2C_INP_SCL
21 #define I2C_INP_SCL(__x) 0
22 #define I2C_INP_SDA(__x) 0
23 #define I2C_INP_VAL(__x) 0
24 #endif
25 
26 /* SoC optional: clock gate bitmask */
27 #ifndef I2C_CLK_CGRBM
28 #define I2C_CLK_CGRBM(__x) 0
29 #endif
30 
31 static struct io_pa_va i2c_bus[3] = {
32 #if defined(I2C1_BASE)
33 	[0] = { .pa = I2C1_BASE, },
34 #endif
35 #if defined(I2C2_BASE)
36 	[1] = { .pa = I2C2_BASE, },
37 #endif
38 #if defined(I2C3_BASE)
39 	[2] = { .pa = I2C3_BASE, },
40 #endif
41 };
42 
43 static struct imx_i2c_clk {
44 	struct io_pa_va base;
45 	uint32_t i2c[ARRAY_SIZE(i2c_bus)];
46 	uint32_t cgrbm[ARRAY_SIZE(i2c_bus)];
47 } i2c_clk = {
48 	.base.pa = CCM_BASE,
49 	.i2c = { I2C_CLK_CGR(1), I2C_CLK_CGR(2), I2C_CLK_CGR(3), },
50 	.cgrbm = { I2C_CLK_CGRBM(1), I2C_CLK_CGRBM(2), I2C_CLK_CGRBM(3), },
51 };
52 
53 static struct imx_i2c_mux {
54 	struct io_pa_va base;
55 	struct imx_i2c_mux_regs {
56 		uint32_t scl_mux;
57 		uint32_t scl_cfg;
58 		uint32_t scl_inp;
59 		uint32_t sda_mux;
60 		uint32_t sda_cfg;
61 		uint32_t sda_inp;
62 	} i2c[ARRAY_SIZE(i2c_bus)];
63 } i2c_mux = {
64 	.base.pa = IOMUXC_BASE,
65 	.i2c = {{ .scl_mux = I2C_MUX_SCL(1), .scl_cfg = I2C_CFG_SCL(1),
66 		.scl_inp = I2C_INP_SCL(1), .sda_mux = I2C_MUX_SDA(1),
67 		.sda_cfg = I2C_CFG_SDA(1), .sda_inp = I2C_INP_SDA(1), },
68 		{ .scl_mux = I2C_MUX_SCL(2), .scl_cfg = I2C_CFG_SCL(2),
69 		.scl_inp = I2C_INP_SCL(2), .sda_mux = I2C_MUX_SDA(2),
70 		.sda_cfg = I2C_CFG_SDA(2), .sda_inp = I2C_INP_SDA(2), },
71 		{ .scl_mux = I2C_MUX_SCL(3), .scl_cfg = I2C_CFG_SCL(3),
72 		.scl_inp = I2C_INP_SCL(3), .sda_mux = I2C_MUX_SDA(3),
73 		.sda_cfg = I2C_CFG_SDA(3), .sda_inp = I2C_INP_SDA(3), },},
74 };
75 
76 #define I2DR				0x10
77 #define I2SR				0x0C
78 #define I2CR				0x08
79 #define IFDR				0x04
80 
81 #define I2CR_IEN			BIT(7)
82 #define I2CR_IIEN			BIT(6)
83 #define I2CR_MSTA			BIT(5)
84 #define I2CR_MTX			BIT(4)
85 #define I2CR_TX_NO_AK			BIT(3)
86 #define I2CR_RSTA			BIT(2)
87 
88 #define I2SR_ICF			BIT(7)
89 #define I2SR_IBB			BIT(5)
90 #define I2SR_IAL			BIT(4)
91 #define I2SR_IIF			BIT(1)
92 #define I2SR_RX_NO_AK			BIT(0)
93 
94 static uint8_t i2c_io_read8(uint8_t bid, uint32_t address)
95 {
96 	return io_read8(i2c_bus[bid].va + address);
97 }
98 
99 static void i2c_io_write8(uint8_t bid, uint32_t address, uint8_t data)
100 {
101 	return io_write8(i2c_bus[bid].va + address, data);
102 }
103 
104 static bool bus_is_idle(uint32_t sr)
105 {
106 	return (sr & I2SR_IBB) == 0;
107 }
108 
109 static bool bus_is_busy(uint32_t sr)
110 {
111 	return !bus_is_idle(sr);
112 }
113 
114 static bool isr_active(uint32_t sr)
115 {
116 	return (sr & I2SR_IIF) == I2SR_IIF;
117 }
118 
119 static struct ifdr_pair {
120 	uint32_t divider;
121 	uint8_t prescaler;
122 } ifdr_table[] = {
123 	{ 22,	0x20 }, { 24,	0x21 }, { 26,	0x22 }, { 28,	0x23 },
124 	{ 30,	0x00 }, { 32,	0x24 }, { 36,	0x25 }, { 40,	0x26 },
125 	{ 42,	0x03 }, { 44,	0x27 }, { 48,	0x28 }, { 52,	0x05 },
126 	{ 56,	0x29 }, { 60,	0x06 }, { 64,	0x2A }, { 72,	0x2B },
127 	{ 80,	0x2C }, { 88,	0x09 }, { 96,	0x2D }, { 104,	0x0A },
128 	{ 112,	0x2E }, { 128,	0x2F }, { 144,	0x0C }, { 160,	0x30 },
129 	{ 192,	0x31 }, { 224,	0x32 }, { 240,	0x0F }, { 256,	0x33 },
130 	{ 288,	0x10 }, { 320,	0x34 }, { 384,	0x35 }, { 448,	0x36 },
131 	{ 480,	0x13 }, { 512,	0x37 }, { 576,	0x14 }, { 640,	0x38 },
132 	{ 768,	0x39 }, { 896,	0x3A }, { 960,	0x17 }, { 1024,	0x3B },
133 	{ 1152,	0x18 }, { 1280,	0x3C }, { 1536,	0x3D }, { 1792,	0x3E },
134 	{ 1920,	0x1B }, { 2048,	0x3F }, { 2304,	0x1C }, { 2560,	0x1D },
135 	{ 3072,	0x1E }, { 3840,	0x1F }
136 };
137 
138 static void i2c_set_prescaler(uint8_t bid, uint32_t bps)
139 {
140 	struct ifdr_pair *p = ifdr_table;
141 	struct ifdr_pair *q = p + ARRAY_SIZE(ifdr_table) - 1;
142 	uint32_t div = (I2C_CLK_RATE + bps - 1) / bps;
143 
144 	if (div < p->divider)
145 		q = p;
146 	else if (div > q->divider)
147 		p = q;
148 
149 	while (p != q) {
150 		if (div <= p->divider)
151 			break;
152 		p++;
153 	}
154 
155 	i2c_io_write8(bid, IFDR, p->prescaler);
156 }
157 
158 static void i2c_set_bus_speed(uint8_t bid, int bps)
159 {
160 	vaddr_t addr = i2c_clk.base.va;
161 	uint32_t val = 0;
162 
163 #if defined(CFG_MX8MM)
164 	addr += CCM_CCGRx_SET(i2c_clk.i2c[bid]);
165 	val = CCM_CCGRx_ALWAYS_ON(0);
166 #elif defined(CFG_MX6ULL)
167 	addr += i2c_clk.i2c[bid];
168 	val = i2c_clk.cgrbm[bid] | io_read32(addr);
169 #endif
170 	io_write32(addr, val);
171 	i2c_set_prescaler(bid, bps);
172 }
173 
174 static TEE_Result i2c_sync_bus(uint8_t bid, bool (*match)(uint32_t),
175 			       uint32_t *status)
176 {
177 	uint64_t tref = timeout_init_us(100000);
178 	uint32_t sr = 0;
179 
180 	while (!timeout_elapsed(tref)) {
181 		sr = i2c_io_read8(bid, I2SR);
182 		if (sr & I2SR_IAL) {
183 			EMSG("bus arbitration lost");
184 			i2c_io_write8(bid, I2SR, sr & ~I2SR_IAL);
185 			return TEE_ERROR_COMMUNICATION;
186 		}
187 		if ((*match)(sr)) {
188 			if (status)
189 				*status = sr;
190 			return TEE_SUCCESS;
191 		}
192 	}
193 
194 	return TEE_ERROR_BUSY;
195 }
196 
197 static TEE_Result i2c_idle_bus(uint8_t bid)
198 {
199 	uint8_t tmp = i2c_io_read8(bid, I2CR) & ~I2CR_MSTA;
200 	TEE_Result ret = TEE_SUCCESS;
201 
202 	i2c_io_write8(bid, I2CR, tmp);
203 	ret = i2c_sync_bus(bid, &bus_is_idle, NULL);
204 	i2c_io_write8(bid, I2SR, 0);
205 
206 	return ret;
207 }
208 
209 static TEE_Result i2c_write_byte(uint8_t bid, uint8_t byte)
210 {
211 	TEE_Result ret = TEE_SUCCESS;
212 	uint32_t status = 0;
213 
214 	i2c_io_write8(bid, I2DR, byte);
215 	ret = i2c_sync_bus(bid, &isr_active, &status);
216 	i2c_io_write8(bid, I2SR, 0);
217 
218 	if (!ret && (status & I2SR_RX_NO_AK))
219 		return TEE_ERROR_BAD_STATE;
220 
221 	return ret;
222 }
223 
224 static TEE_Result i2c_read_byte(uint8_t bid, uint8_t *p)
225 {
226 	TEE_Result ret = TEE_SUCCESS;
227 
228 	*p = i2c_io_read8(bid, I2DR);
229 	ret = i2c_sync_bus(bid, &isr_active, NULL);
230 	i2c_io_write8(bid, I2SR, 0);
231 
232 	return ret;
233 }
234 
235 static TEE_Result i2c_write_data(uint8_t bid, const uint8_t *buf, int len)
236 {
237 	TEE_Result ret = TEE_SUCCESS;
238 	uint32_t tmp = 0;
239 
240 	if (!len)
241 		return TEE_SUCCESS;
242 
243 	tmp = i2c_io_read8(bid, I2CR) | I2CR_MTX | I2CR_TX_NO_AK;
244 	i2c_io_write8(bid, I2CR, tmp);
245 
246 	while (len--) {
247 		ret = i2c_write_byte(bid, *buf++);
248 		if (ret)
249 			return ret;
250 	}
251 
252 	return ret;
253 }
254 
255 static TEE_Result i2c_read_data(uint8_t bid, uint8_t *buf, int len)
256 {
257 	TEE_Result ret = TEE_SUCCESS;
258 	uint8_t dummy = 0;
259 	uint32_t tmp = 0;
260 
261 	if (!len)
262 		return TEE_SUCCESS;
263 
264 	tmp = i2c_io_read8(bid, I2CR) & ~I2CR_MTX;
265 	tmp = (len == 1) ? tmp | I2CR_TX_NO_AK : tmp & ~I2CR_TX_NO_AK;
266 	i2c_io_write8(bid, I2CR, tmp);
267 	i2c_io_read8(bid, I2DR);
268 
269 	ret = i2c_read_byte(bid, &dummy);
270 	if (ret)
271 		return ret;
272 
273 	/*
274 	 * A data transfer ends when the master signals a stop; for a master
275 	 * receiver to terminate a transfer it must inform the slave transmiter
276 	 * by not acknowledging the last data byte. This is done by setting the
277 	 * transmit acknowledge bit before reading the next-to-last byte.
278 	 */
279 	do {
280 		if (len == 2) {
281 			tmp = i2c_io_read8(bid, I2CR) | I2CR_TX_NO_AK;
282 			i2c_io_write8(bid, I2CR, tmp);
283 		}
284 
285 		ret = i2c_read_byte(bid, buf++);
286 		if (ret)
287 			return ret;
288 	} while (len--);
289 
290 	return ret;
291 }
292 
293 static TEE_Result i2c_init_transfer(uint8_t bid, uint8_t chip)
294 {
295 	TEE_Result ret = TEE_SUCCESS;
296 	uint32_t tmp = 0;
297 
298 	ret = i2c_idle_bus(bid);
299 	if (ret)
300 		return ret;
301 
302 	/* Enable the interface */
303 	i2c_io_write8(bid, I2CR, I2CR_IEN);
304 
305 	tmp = i2c_io_read8(bid, I2CR) | I2CR_MSTA;
306 	i2c_io_write8(bid, I2CR, tmp);
307 
308 	/* Wait until the bus is active */
309 	ret = i2c_sync_bus(bid, &bus_is_busy, NULL);
310 	if (ret)
311 		return ret;
312 
313 	/* Slave address on the bus */
314 	return i2c_write_data(bid, &chip, 1);
315 }
316 
317 TEE_Result imx_i2c_read(uint8_t bid, uint8_t chip, uint8_t *buf, int len)
318 {
319 	TEE_Result ret = TEE_SUCCESS;
320 
321 	if (bid >= ARRAY_SIZE(i2c_bus))
322 		return TEE_ERROR_BAD_PARAMETERS;
323 
324 	if ((len && !buf) || chip > 0x7F)
325 		return TEE_ERROR_BAD_PARAMETERS;
326 
327 	if (!i2c_bus[bid].va)
328 		return TEE_ERROR_BAD_PARAMETERS;
329 
330 	ret = i2c_init_transfer(bid, chip << 1 | BIT(0));
331 	if (!ret)
332 		ret = i2c_read_data(bid, buf, len);
333 
334 	if (i2c_idle_bus(bid))
335 		IMSG("bus not idle");
336 
337 	return ret;
338 }
339 
340 TEE_Result imx_i2c_write(uint8_t bid, uint8_t chip, const uint8_t *buf, int len)
341 {
342 	TEE_Result ret = TEE_SUCCESS;
343 
344 	if (bid >= ARRAY_SIZE(i2c_bus))
345 		return TEE_ERROR_BAD_PARAMETERS;
346 
347 	if ((len && !buf) || chip > 0x7F)
348 		return TEE_ERROR_BAD_PARAMETERS;
349 
350 	if (!i2c_bus[bid].va)
351 		return TEE_ERROR_BAD_PARAMETERS;
352 
353 	ret = i2c_init_transfer(bid, chip << 1);
354 	if (!ret)
355 		ret = i2c_write_data(bid, buf, len);
356 
357 	if (i2c_idle_bus(bid))
358 		IMSG("bus not idle");
359 
360 	return ret;
361 }
362 
363 TEE_Result imx_i2c_probe(uint8_t bid, uint8_t chip)
364 {
365 	if (bid >= ARRAY_SIZE(i2c_bus))
366 		return TEE_ERROR_BAD_PARAMETERS;
367 
368 	if (!i2c_bus[bid].va)
369 		return TEE_ERROR_BAD_PARAMETERS;
370 
371 	if (chip > 0x7F)
372 		return TEE_ERROR_BAD_PARAMETERS;
373 
374 	return imx_i2c_write(bid, chip, NULL, 0);
375 }
376 
377 /*
378  * I2C bus initialization: configure the IOMUX and enable the clock.
379  * @bid: Bus ID: (0=I2C1), (1=I2C2), (2=I2C3).
380  * @bps: Bus baud rate, in bits per second.
381  */
382 TEE_Result imx_i2c_init(uint8_t bid, int bps)
383 {
384 	struct imx_i2c_mux *mux = &i2c_mux;
385 
386 	if (bid >= ARRAY_SIZE(i2c_bus))
387 		return TEE_ERROR_BAD_PARAMETERS;
388 
389 	if (!bps)
390 		return TEE_ERROR_BAD_PARAMETERS;
391 
392 	if (!i2c_bus[bid].va)
393 		return TEE_ERROR_BAD_PARAMETERS;
394 
395 	io_write32(mux->base.va + mux->i2c[bid].scl_mux, I2C_MUX_VAL(bid));
396 	io_write32(mux->base.va + mux->i2c[bid].scl_cfg, I2C_CFG_VAL(bid));
397 	if (mux->i2c[bid].scl_inp)
398 		io_write32(mux->base.va + mux->i2c[bid].scl_inp,
399 			   I2C_INP_VAL(mux->i2c[bid].scl_inp));
400 
401 	io_write32(mux->base.va + mux->i2c[bid].sda_mux, I2C_MUX_VAL(bid));
402 	io_write32(mux->base.va + mux->i2c[bid].sda_cfg, I2C_CFG_VAL(bid));
403 	if (mux->i2c[bid].sda_inp)
404 		io_write32(mux->base.va + mux->i2c[bid].sda_inp,
405 			   I2C_INP_VAL(mux->i2c[bid].sda_inp));
406 
407 	/* Baud rate in bits per second */
408 	i2c_set_bus_speed(bid, bps);
409 
410 	return TEE_SUCCESS;
411 }
412 
413 static TEE_Result get_va(paddr_t pa, vaddr_t *va)
414 {
415 	if (!core_mmu_add_mapping(MEM_AREA_IO_SEC, pa, 0x10000))
416 		return TEE_ERROR_GENERIC;
417 
418 	*va = (vaddr_t)phys_to_virt(pa, MEM_AREA_IO_SEC);
419 	if (*va)
420 		return TEE_SUCCESS;
421 
422 	return TEE_ERROR_GENERIC;
423 }
424 
425 static TEE_Result i2c_init(void)
426 {
427 	size_t n = 0;
428 
429 	if (get_va(i2c_clk.base.pa, &i2c_clk.base.va))
430 		return TEE_ERROR_GENERIC;
431 
432 	if (get_va(i2c_mux.base.pa, &i2c_mux.base.va))
433 		return TEE_ERROR_GENERIC;
434 
435 	for (n = 0; n < ARRAY_SIZE(i2c_bus); n++) {
436 		if (get_va(i2c_bus[n].pa, &i2c_bus[n].va))
437 			EMSG("i2c%zu not available", n + 1);
438 	}
439 
440 	return TEE_SUCCESS;
441 }
442 
443 early_init(i2c_init);
444