xref: /rk3399_rockchip-uboot/drivers/i2c/sh_sh7734_i2c.c (revision f2465934b46235287e07473fa4919035ba1a2b68)
12d344a2aSNobuhiro Iwamatsu /*
22d344a2aSNobuhiro Iwamatsu  * Copyright (C) 2012 Nobuhiro Iwamatsu <nobuhiro.iwamatsu.yj@renesas.com>
32d344a2aSNobuhiro Iwamatsu  * Copyright (C) 2012 Renesas Solutions Corp.
42d344a2aSNobuhiro Iwamatsu  *
51a459660SWolfgang Denk  * SPDX-License-Identifier:	GPL-2.0+
6*28527096SSimon Glass  *
7*28527096SSimon Glass  * NOTE: This driver should be converted to driver model before June 2017.
8*28527096SSimon Glass  * Please see doc/driver-model/i2c-howto.txt for instructions.
92d344a2aSNobuhiro Iwamatsu  */
102d344a2aSNobuhiro Iwamatsu 
112d344a2aSNobuhiro Iwamatsu #include <common.h>
122d344a2aSNobuhiro Iwamatsu #include <i2c.h>
132d344a2aSNobuhiro Iwamatsu #include <asm/io.h>
142d344a2aSNobuhiro Iwamatsu 
152d344a2aSNobuhiro Iwamatsu struct sh_i2c {
162d344a2aSNobuhiro Iwamatsu 	u8 iccr1;
172d344a2aSNobuhiro Iwamatsu 	u8 iccr2;
182d344a2aSNobuhiro Iwamatsu 	u8 icmr;
192d344a2aSNobuhiro Iwamatsu 	u8 icier;
202d344a2aSNobuhiro Iwamatsu 	u8 icsr;
212d344a2aSNobuhiro Iwamatsu 	u8 sar;
222d344a2aSNobuhiro Iwamatsu 	u8 icdrt;
232d344a2aSNobuhiro Iwamatsu 	u8 icdrr;
242d344a2aSNobuhiro Iwamatsu 	u8 nf2cyc;
252d344a2aSNobuhiro Iwamatsu 	u8 __pad0;
262d344a2aSNobuhiro Iwamatsu 	u8 __pad1;
272d344a2aSNobuhiro Iwamatsu };
282d344a2aSNobuhiro Iwamatsu 
292d344a2aSNobuhiro Iwamatsu static struct sh_i2c *base;
302d344a2aSNobuhiro Iwamatsu static u8 iccr1_cks, nf2cyc;
312d344a2aSNobuhiro Iwamatsu 
322d344a2aSNobuhiro Iwamatsu /* ICCR1 */
332d344a2aSNobuhiro Iwamatsu #define SH_I2C_ICCR1_ICE	(1 << 7)
342d344a2aSNobuhiro Iwamatsu #define SH_I2C_ICCR1_RCVD	(1 << 6)
352d344a2aSNobuhiro Iwamatsu #define SH_I2C_ICCR1_MST	(1 << 5)
362d344a2aSNobuhiro Iwamatsu #define SH_I2C_ICCR1_TRS	(1 << 4)
372d344a2aSNobuhiro Iwamatsu #define SH_I2C_ICCR1_MTRS	\
382d344a2aSNobuhiro Iwamatsu 	(SH_I2C_ICCR1_MST | SH_I2C_ICCR1_TRS)
392d344a2aSNobuhiro Iwamatsu 
402d344a2aSNobuhiro Iwamatsu /* ICCR1 */
412d344a2aSNobuhiro Iwamatsu #define SH_I2C_ICCR2_BBSY	(1 << 7)
422d344a2aSNobuhiro Iwamatsu #define SH_I2C_ICCR2_SCP	(1 << 6)
432d344a2aSNobuhiro Iwamatsu #define SH_I2C_ICCR2_SDAO	(1 << 5)
442d344a2aSNobuhiro Iwamatsu #define SH_I2C_ICCR2_SDAOP	(1 << 4)
452d344a2aSNobuhiro Iwamatsu #define SH_I2C_ICCR2_SCLO	(1 << 3)
462d344a2aSNobuhiro Iwamatsu #define SH_I2C_ICCR2_IICRST	(1 << 1)
472d344a2aSNobuhiro Iwamatsu 
482d344a2aSNobuhiro Iwamatsu #define SH_I2C_ICIER_TIE	(1 << 7)
492d344a2aSNobuhiro Iwamatsu #define SH_I2C_ICIER_TEIE	(1 << 6)
502d344a2aSNobuhiro Iwamatsu #define SH_I2C_ICIER_RIE	(1 << 5)
512d344a2aSNobuhiro Iwamatsu #define SH_I2C_ICIER_NAKIE	(1 << 4)
522d344a2aSNobuhiro Iwamatsu #define SH_I2C_ICIER_STIE	(1 << 3)
532d344a2aSNobuhiro Iwamatsu #define SH_I2C_ICIER_ACKE	(1 << 2)
542d344a2aSNobuhiro Iwamatsu #define SH_I2C_ICIER_ACKBR	(1 << 1)
552d344a2aSNobuhiro Iwamatsu #define SH_I2C_ICIER_ACKBT	(1 << 0)
562d344a2aSNobuhiro Iwamatsu 
572d344a2aSNobuhiro Iwamatsu #define SH_I2C_ICSR_TDRE	(1 << 7)
582d344a2aSNobuhiro Iwamatsu #define SH_I2C_ICSR_TEND	(1 << 6)
592d344a2aSNobuhiro Iwamatsu #define SH_I2C_ICSR_RDRF	(1 << 5)
602d344a2aSNobuhiro Iwamatsu #define SH_I2C_ICSR_NACKF	(1 << 4)
612d344a2aSNobuhiro Iwamatsu #define SH_I2C_ICSR_STOP	(1 << 3)
622d344a2aSNobuhiro Iwamatsu #define SH_I2C_ICSR_ALOVE	(1 << 2)
632d344a2aSNobuhiro Iwamatsu #define SH_I2C_ICSR_AAS		(1 << 1)
642d344a2aSNobuhiro Iwamatsu #define SH_I2C_ICSR_ADZ		(1 << 0)
652d344a2aSNobuhiro Iwamatsu 
662d344a2aSNobuhiro Iwamatsu #define IRQ_WAIT 1000
672d344a2aSNobuhiro Iwamatsu 
sh_i2c_send_stop(struct sh_i2c * base)682d344a2aSNobuhiro Iwamatsu static void sh_i2c_send_stop(struct sh_i2c *base)
692d344a2aSNobuhiro Iwamatsu {
702d344a2aSNobuhiro Iwamatsu 	clrbits_8(&base->iccr2, SH_I2C_ICCR2_BBSY | SH_I2C_ICCR2_SCP);
712d344a2aSNobuhiro Iwamatsu }
722d344a2aSNobuhiro Iwamatsu 
check_icsr_bits(struct sh_i2c * base,u8 bits)732d344a2aSNobuhiro Iwamatsu static int check_icsr_bits(struct sh_i2c *base, u8 bits)
742d344a2aSNobuhiro Iwamatsu {
752d344a2aSNobuhiro Iwamatsu 	int i;
762d344a2aSNobuhiro Iwamatsu 
772d344a2aSNobuhiro Iwamatsu 	for (i = 0; i < IRQ_WAIT; i++) {
782d344a2aSNobuhiro Iwamatsu 		if (bits & readb(&base->icsr))
792d344a2aSNobuhiro Iwamatsu 			return 0;
802d344a2aSNobuhiro Iwamatsu 		udelay(10);
812d344a2aSNobuhiro Iwamatsu 	}
822d344a2aSNobuhiro Iwamatsu 
832d344a2aSNobuhiro Iwamatsu 	return 1;
842d344a2aSNobuhiro Iwamatsu }
852d344a2aSNobuhiro Iwamatsu 
check_stop(struct sh_i2c * base)862d344a2aSNobuhiro Iwamatsu static int check_stop(struct sh_i2c *base)
872d344a2aSNobuhiro Iwamatsu {
882d344a2aSNobuhiro Iwamatsu 	int ret = check_icsr_bits(base, SH_I2C_ICSR_STOP);
892d344a2aSNobuhiro Iwamatsu 	clrbits_8(&base->icsr, SH_I2C_ICSR_STOP);
902d344a2aSNobuhiro Iwamatsu 
912d344a2aSNobuhiro Iwamatsu 	return ret;
922d344a2aSNobuhiro Iwamatsu }
932d344a2aSNobuhiro Iwamatsu 
check_tend(struct sh_i2c * base,int stop)942d344a2aSNobuhiro Iwamatsu static int check_tend(struct sh_i2c *base, int stop)
952d344a2aSNobuhiro Iwamatsu {
962d344a2aSNobuhiro Iwamatsu 	int ret = check_icsr_bits(base, SH_I2C_ICSR_TEND);
972d344a2aSNobuhiro Iwamatsu 
982d344a2aSNobuhiro Iwamatsu 	if (stop) {
992d344a2aSNobuhiro Iwamatsu 		clrbits_8(&base->icsr, SH_I2C_ICSR_STOP);
1002d344a2aSNobuhiro Iwamatsu 		sh_i2c_send_stop(base);
1012d344a2aSNobuhiro Iwamatsu 	}
1022d344a2aSNobuhiro Iwamatsu 
1032d344a2aSNobuhiro Iwamatsu 	clrbits_8(&base->icsr, SH_I2C_ICSR_TEND);
1042d344a2aSNobuhiro Iwamatsu 	return ret;
1052d344a2aSNobuhiro Iwamatsu }
1062d344a2aSNobuhiro Iwamatsu 
check_tdre(struct sh_i2c * base)1072d344a2aSNobuhiro Iwamatsu static int check_tdre(struct sh_i2c *base)
1082d344a2aSNobuhiro Iwamatsu {
1092d344a2aSNobuhiro Iwamatsu 	return check_icsr_bits(base, SH_I2C_ICSR_TDRE);
1102d344a2aSNobuhiro Iwamatsu }
1112d344a2aSNobuhiro Iwamatsu 
check_rdrf(struct sh_i2c * base)1122d344a2aSNobuhiro Iwamatsu static int check_rdrf(struct sh_i2c *base)
1132d344a2aSNobuhiro Iwamatsu {
1142d344a2aSNobuhiro Iwamatsu 	return check_icsr_bits(base, SH_I2C_ICSR_RDRF);
1152d344a2aSNobuhiro Iwamatsu }
1162d344a2aSNobuhiro Iwamatsu 
check_bbsy(struct sh_i2c * base)1172d344a2aSNobuhiro Iwamatsu static int check_bbsy(struct sh_i2c *base)
1182d344a2aSNobuhiro Iwamatsu {
1192d344a2aSNobuhiro Iwamatsu 	int i;
1202d344a2aSNobuhiro Iwamatsu 
1212d344a2aSNobuhiro Iwamatsu 	for (i = 0 ; i < IRQ_WAIT ; i++) {
1222d344a2aSNobuhiro Iwamatsu 		if (!(SH_I2C_ICCR2_BBSY & readb(&base->iccr2)))
1232d344a2aSNobuhiro Iwamatsu 			return 0;
1242d344a2aSNobuhiro Iwamatsu 		udelay(10);
1252d344a2aSNobuhiro Iwamatsu 	}
1262d344a2aSNobuhiro Iwamatsu 	return 1;
1272d344a2aSNobuhiro Iwamatsu }
1282d344a2aSNobuhiro Iwamatsu 
check_ackbr(struct sh_i2c * base)1292d344a2aSNobuhiro Iwamatsu static int check_ackbr(struct sh_i2c *base)
1302d344a2aSNobuhiro Iwamatsu {
1312d344a2aSNobuhiro Iwamatsu 	int i;
1322d344a2aSNobuhiro Iwamatsu 
1332d344a2aSNobuhiro Iwamatsu 	for (i = 0 ; i < IRQ_WAIT ; i++) {
1342d344a2aSNobuhiro Iwamatsu 		if (!(SH_I2C_ICIER_ACKBR & readb(&base->icier)))
1352d344a2aSNobuhiro Iwamatsu 			return 0;
1362d344a2aSNobuhiro Iwamatsu 		udelay(10);
1372d344a2aSNobuhiro Iwamatsu 	}
1382d344a2aSNobuhiro Iwamatsu 
1392d344a2aSNobuhiro Iwamatsu 	return 1;
1402d344a2aSNobuhiro Iwamatsu }
1412d344a2aSNobuhiro Iwamatsu 
sh_i2c_reset(struct sh_i2c * base)1422d344a2aSNobuhiro Iwamatsu static void sh_i2c_reset(struct sh_i2c *base)
1432d344a2aSNobuhiro Iwamatsu {
1442d344a2aSNobuhiro Iwamatsu 	setbits_8(&base->iccr2, SH_I2C_ICCR2_IICRST);
1452d344a2aSNobuhiro Iwamatsu 
1462d344a2aSNobuhiro Iwamatsu 	udelay(100);
1472d344a2aSNobuhiro Iwamatsu 
1482d344a2aSNobuhiro Iwamatsu 	clrbits_8(&base->iccr2, SH_I2C_ICCR2_IICRST);
1492d344a2aSNobuhiro Iwamatsu }
1502d344a2aSNobuhiro Iwamatsu 
i2c_set_addr(struct sh_i2c * base,u8 id,u8 reg)1512d344a2aSNobuhiro Iwamatsu static int i2c_set_addr(struct sh_i2c *base, u8 id, u8 reg)
1522d344a2aSNobuhiro Iwamatsu {
1532d344a2aSNobuhiro Iwamatsu 	if (check_bbsy(base)) {
1542d344a2aSNobuhiro Iwamatsu 		puts("i2c bus busy\n");
1552d344a2aSNobuhiro Iwamatsu 		goto fail;
1562d344a2aSNobuhiro Iwamatsu 	}
1572d344a2aSNobuhiro Iwamatsu 
1582d344a2aSNobuhiro Iwamatsu 	setbits_8(&base->iccr1, SH_I2C_ICCR1_MTRS);
1592d344a2aSNobuhiro Iwamatsu 	clrsetbits_8(&base->iccr2, SH_I2C_ICCR2_SCP, SH_I2C_ICCR2_BBSY);
1602d344a2aSNobuhiro Iwamatsu 
1612d344a2aSNobuhiro Iwamatsu 	writeb((id << 1), &base->icdrt);
1622d344a2aSNobuhiro Iwamatsu 
1632d344a2aSNobuhiro Iwamatsu 	if (check_tend(base, 0)) {
1642d344a2aSNobuhiro Iwamatsu 		puts("TEND check fail...\n");
1652d344a2aSNobuhiro Iwamatsu 		goto fail;
1662d344a2aSNobuhiro Iwamatsu 	}
1672d344a2aSNobuhiro Iwamatsu 
1682d344a2aSNobuhiro Iwamatsu 	if (check_ackbr(base)) {
1692d344a2aSNobuhiro Iwamatsu 		check_tend(base, 0);
1702d344a2aSNobuhiro Iwamatsu 		sh_i2c_send_stop(base);
1712d344a2aSNobuhiro Iwamatsu 		goto fail;
1722d344a2aSNobuhiro Iwamatsu 	}
1732d344a2aSNobuhiro Iwamatsu 
1742d344a2aSNobuhiro Iwamatsu 	writeb(reg, &base->icdrt);
1752d344a2aSNobuhiro Iwamatsu 
1762d344a2aSNobuhiro Iwamatsu 	if (check_tdre(base)) {
1772d344a2aSNobuhiro Iwamatsu 		puts("TDRE check fail...\n");
1782d344a2aSNobuhiro Iwamatsu 		goto fail;
1792d344a2aSNobuhiro Iwamatsu 	}
1802d344a2aSNobuhiro Iwamatsu 
1812d344a2aSNobuhiro Iwamatsu 	if (check_tend(base, 0)) {
1822d344a2aSNobuhiro Iwamatsu 		puts("TEND check fail...\n");
1832d344a2aSNobuhiro Iwamatsu 		goto fail;
1842d344a2aSNobuhiro Iwamatsu 	}
1852d344a2aSNobuhiro Iwamatsu 
1862d344a2aSNobuhiro Iwamatsu 	return 0;
1872d344a2aSNobuhiro Iwamatsu fail:
1882d344a2aSNobuhiro Iwamatsu 
1892d344a2aSNobuhiro Iwamatsu 	return 1;
1902d344a2aSNobuhiro Iwamatsu }
1912d344a2aSNobuhiro Iwamatsu 
1922d344a2aSNobuhiro Iwamatsu static int
i2c_raw_write(struct sh_i2c * base,u8 id,u8 reg,u8 * val,int size)1932d344a2aSNobuhiro Iwamatsu i2c_raw_write(struct sh_i2c *base, u8 id, u8 reg, u8 *val, int size)
1942d344a2aSNobuhiro Iwamatsu {
1952d344a2aSNobuhiro Iwamatsu 	int i;
1962d344a2aSNobuhiro Iwamatsu 
1972d344a2aSNobuhiro Iwamatsu 	if (i2c_set_addr(base, id, reg)) {
1982d344a2aSNobuhiro Iwamatsu 		puts("Fail set slave address\n");
1992d344a2aSNobuhiro Iwamatsu 		return 1;
2002d344a2aSNobuhiro Iwamatsu 	}
2012d344a2aSNobuhiro Iwamatsu 
2022d344a2aSNobuhiro Iwamatsu 	for (i = 0; i < size; i++) {
2032d344a2aSNobuhiro Iwamatsu 		writeb(val[i], &base->icdrt);
2042d344a2aSNobuhiro Iwamatsu 		check_tdre(base);
2052d344a2aSNobuhiro Iwamatsu 	}
2062d344a2aSNobuhiro Iwamatsu 
2072d344a2aSNobuhiro Iwamatsu 	check_tend(base, 1);
2082d344a2aSNobuhiro Iwamatsu 	check_stop(base);
2092d344a2aSNobuhiro Iwamatsu 
2102d344a2aSNobuhiro Iwamatsu 	udelay(100);
2112d344a2aSNobuhiro Iwamatsu 
2122d344a2aSNobuhiro Iwamatsu 	clrbits_8(&base->iccr1, SH_I2C_ICCR1_MTRS);
2132d344a2aSNobuhiro Iwamatsu 	clrbits_8(&base->icsr, SH_I2C_ICSR_TDRE);
2142d344a2aSNobuhiro Iwamatsu 	sh_i2c_reset(base);
2152d344a2aSNobuhiro Iwamatsu 
2162d344a2aSNobuhiro Iwamatsu 	return 0;
2172d344a2aSNobuhiro Iwamatsu }
2182d344a2aSNobuhiro Iwamatsu 
i2c_raw_read(struct sh_i2c * base,u8 id,u8 reg)2192d344a2aSNobuhiro Iwamatsu static u8 i2c_raw_read(struct sh_i2c *base, u8 id, u8 reg)
2202d344a2aSNobuhiro Iwamatsu {
2212d344a2aSNobuhiro Iwamatsu 	u8 ret = 0;
2222d344a2aSNobuhiro Iwamatsu 
2232d344a2aSNobuhiro Iwamatsu 	if (i2c_set_addr(base, id, reg)) {
2242d344a2aSNobuhiro Iwamatsu 		puts("Fail set slave address\n");
2252d344a2aSNobuhiro Iwamatsu 		goto fail;
2262d344a2aSNobuhiro Iwamatsu 	}
2272d344a2aSNobuhiro Iwamatsu 
2282d344a2aSNobuhiro Iwamatsu 	clrsetbits_8(&base->iccr2, SH_I2C_ICCR2_SCP, SH_I2C_ICCR2_BBSY);
2292d344a2aSNobuhiro Iwamatsu 	writeb((id << 1) | 1, &base->icdrt);
2302d344a2aSNobuhiro Iwamatsu 
2312d344a2aSNobuhiro Iwamatsu 	if (check_tend(base, 0))
2322d344a2aSNobuhiro Iwamatsu 		puts("TDRE check fail...\n");
2332d344a2aSNobuhiro Iwamatsu 
2342d344a2aSNobuhiro Iwamatsu 	clrsetbits_8(&base->iccr1, SH_I2C_ICCR1_TRS, SH_I2C_ICCR1_MST);
2352d344a2aSNobuhiro Iwamatsu 	clrbits_8(&base->icsr, SH_I2C_ICSR_TDRE);
2362d344a2aSNobuhiro Iwamatsu 	setbits_8(&base->icier, SH_I2C_ICIER_ACKBT);
2372d344a2aSNobuhiro Iwamatsu 	setbits_8(&base->iccr1, SH_I2C_ICCR1_RCVD);
2382d344a2aSNobuhiro Iwamatsu 
2392d344a2aSNobuhiro Iwamatsu 	/* read data (dummy) */
2402d344a2aSNobuhiro Iwamatsu 	ret = readb(&base->icdrr);
2412d344a2aSNobuhiro Iwamatsu 
2422d344a2aSNobuhiro Iwamatsu 	if (check_rdrf(base)) {
2432d344a2aSNobuhiro Iwamatsu 		puts("check RDRF error\n");
2442d344a2aSNobuhiro Iwamatsu 		goto fail;
2452d344a2aSNobuhiro Iwamatsu 	}
2462d344a2aSNobuhiro Iwamatsu 
2472d344a2aSNobuhiro Iwamatsu 	clrbits_8(&base->icsr, SH_I2C_ICSR_STOP);
2482d344a2aSNobuhiro Iwamatsu 	udelay(1000);
2492d344a2aSNobuhiro Iwamatsu 
2502d344a2aSNobuhiro Iwamatsu 	sh_i2c_send_stop(base);
2512d344a2aSNobuhiro Iwamatsu 
2522d344a2aSNobuhiro Iwamatsu 	if (check_stop(base)) {
2532d344a2aSNobuhiro Iwamatsu 		puts("check STOP error\n");
2542d344a2aSNobuhiro Iwamatsu 		goto fail;
2552d344a2aSNobuhiro Iwamatsu 	}
2562d344a2aSNobuhiro Iwamatsu 
2572d344a2aSNobuhiro Iwamatsu 	clrbits_8(&base->iccr1, SH_I2C_ICCR1_MTRS);
2582d344a2aSNobuhiro Iwamatsu 	clrbits_8(&base->icsr, SH_I2C_ICSR_TDRE);
2592d344a2aSNobuhiro Iwamatsu 
2602d344a2aSNobuhiro Iwamatsu 	/* data read */
2612d344a2aSNobuhiro Iwamatsu 	ret = readb(&base->icdrr);
2622d344a2aSNobuhiro Iwamatsu 
2632d344a2aSNobuhiro Iwamatsu fail:
2642d344a2aSNobuhiro Iwamatsu 	clrbits_8(&base->iccr1, SH_I2C_ICCR1_RCVD);
2652d344a2aSNobuhiro Iwamatsu 
2662d344a2aSNobuhiro Iwamatsu 	return ret;
2672d344a2aSNobuhiro Iwamatsu }
2682d344a2aSNobuhiro Iwamatsu 
2692d344a2aSNobuhiro Iwamatsu #ifdef CONFIG_I2C_MULTI_BUS
2702d344a2aSNobuhiro Iwamatsu static unsigned int current_bus;
2712d344a2aSNobuhiro Iwamatsu 
2722d344a2aSNobuhiro Iwamatsu /**
2732d344a2aSNobuhiro Iwamatsu  * i2c_set_bus_num - change active I2C bus
2742d344a2aSNobuhiro Iwamatsu  *	@bus: bus index, zero based
2752d344a2aSNobuhiro Iwamatsu  *	@returns: 0 on success, non-0 on failure
2762d344a2aSNobuhiro Iwamatsu  */
i2c_set_bus_num(unsigned int bus)2772d344a2aSNobuhiro Iwamatsu int i2c_set_bus_num(unsigned int bus)
2782d344a2aSNobuhiro Iwamatsu {
2792d344a2aSNobuhiro Iwamatsu 	switch (bus) {
2802d344a2aSNobuhiro Iwamatsu 	case 0:
2812d344a2aSNobuhiro Iwamatsu 		base = (void *)CONFIG_SH_I2C_BASE0;
2822d344a2aSNobuhiro Iwamatsu 		break;
2832d344a2aSNobuhiro Iwamatsu 	case 1:
2842d344a2aSNobuhiro Iwamatsu 		base = (void *)CONFIG_SH_I2C_BASE1;
2852d344a2aSNobuhiro Iwamatsu 		break;
2862d344a2aSNobuhiro Iwamatsu 	default:
2872d344a2aSNobuhiro Iwamatsu 		printf("Bad bus: %d\n", bus);
2882d344a2aSNobuhiro Iwamatsu 		return -1;
2892d344a2aSNobuhiro Iwamatsu 	}
2902d344a2aSNobuhiro Iwamatsu 
2912d344a2aSNobuhiro Iwamatsu 	current_bus = bus;
2922d344a2aSNobuhiro Iwamatsu 
2932d344a2aSNobuhiro Iwamatsu 	return 0;
2942d344a2aSNobuhiro Iwamatsu }
2952d344a2aSNobuhiro Iwamatsu 
2962d344a2aSNobuhiro Iwamatsu /**
2972d344a2aSNobuhiro Iwamatsu  * i2c_get_bus_num - returns index of active I2C bus
2982d344a2aSNobuhiro Iwamatsu  */
i2c_get_bus_num(void)2992d344a2aSNobuhiro Iwamatsu unsigned int i2c_get_bus_num(void)
3002d344a2aSNobuhiro Iwamatsu {
3012d344a2aSNobuhiro Iwamatsu 	return current_bus;
3022d344a2aSNobuhiro Iwamatsu }
3032d344a2aSNobuhiro Iwamatsu #endif
3042d344a2aSNobuhiro Iwamatsu 
i2c_init(int speed,int slaveaddr)3052d344a2aSNobuhiro Iwamatsu void i2c_init(int speed, int slaveaddr)
3062d344a2aSNobuhiro Iwamatsu {
3072d344a2aSNobuhiro Iwamatsu #ifdef CONFIG_I2C_MULTI_BUS
3082d344a2aSNobuhiro Iwamatsu 	current_bus = 0;
3092d344a2aSNobuhiro Iwamatsu #endif
3102d344a2aSNobuhiro Iwamatsu 	base = (struct sh_i2c *)CONFIG_SH_I2C_BASE0;
3112d344a2aSNobuhiro Iwamatsu 
3122d344a2aSNobuhiro Iwamatsu 	if (speed == 400000)
3132d344a2aSNobuhiro Iwamatsu 		iccr1_cks = 0x07;
3142d344a2aSNobuhiro Iwamatsu 	else
3152d344a2aSNobuhiro Iwamatsu 		iccr1_cks = 0x0F;
3162d344a2aSNobuhiro Iwamatsu 
3172d344a2aSNobuhiro Iwamatsu 	nf2cyc = 1;
3182d344a2aSNobuhiro Iwamatsu 
3192d344a2aSNobuhiro Iwamatsu 	/* Reset */
3202d344a2aSNobuhiro Iwamatsu 	sh_i2c_reset(base);
3212d344a2aSNobuhiro Iwamatsu 
3222d344a2aSNobuhiro Iwamatsu 	/* ICE enable and set clock */
3232d344a2aSNobuhiro Iwamatsu 	writeb(SH_I2C_ICCR1_ICE | iccr1_cks, &base->iccr1);
3242d344a2aSNobuhiro Iwamatsu 	writeb(nf2cyc, &base->nf2cyc);
3252d344a2aSNobuhiro Iwamatsu }
3262d344a2aSNobuhiro Iwamatsu 
3272d344a2aSNobuhiro Iwamatsu /*
3282d344a2aSNobuhiro Iwamatsu  * i2c_read: - Read multiple bytes from an i2c device
3292d344a2aSNobuhiro Iwamatsu  *
3302d344a2aSNobuhiro Iwamatsu  * The higher level routines take into account that this function is only
3312d344a2aSNobuhiro Iwamatsu  * called with len < page length of the device (see configuration file)
3322d344a2aSNobuhiro Iwamatsu  *
3332d344a2aSNobuhiro Iwamatsu  * @chip:   address of the chip which is to be read
3342d344a2aSNobuhiro Iwamatsu  * @addr:   i2c data address within the chip
3352d344a2aSNobuhiro Iwamatsu  * @alen:   length of the i2c data address (1..2 bytes)
3362d344a2aSNobuhiro Iwamatsu  * @buffer: where to write the data
3372d344a2aSNobuhiro Iwamatsu  * @len:    how much byte do we want to read
3382d344a2aSNobuhiro Iwamatsu  * @return: 0 in case of success
3392d344a2aSNobuhiro Iwamatsu  */
i2c_read(u8 chip,u32 addr,int alen,u8 * buffer,int len)3402d344a2aSNobuhiro Iwamatsu int i2c_read(u8 chip, u32 addr, int alen, u8 *buffer, int len)
3412d344a2aSNobuhiro Iwamatsu {
3422d344a2aSNobuhiro Iwamatsu 	int i = 0;
3432d344a2aSNobuhiro Iwamatsu 	for (i = 0; i < len; i++)
3442d344a2aSNobuhiro Iwamatsu 		buffer[i] = i2c_raw_read(base, chip, addr + i);
3452d344a2aSNobuhiro Iwamatsu 
3462d344a2aSNobuhiro Iwamatsu 	return 0;
3472d344a2aSNobuhiro Iwamatsu }
3482d344a2aSNobuhiro Iwamatsu 
3492d344a2aSNobuhiro Iwamatsu /*
3502d344a2aSNobuhiro Iwamatsu  * i2c_write: -  Write multiple bytes to an i2c device
3512d344a2aSNobuhiro Iwamatsu  *
3522d344a2aSNobuhiro Iwamatsu  * The higher level routines take into account that this function is only
3532d344a2aSNobuhiro Iwamatsu  * called with len < page length of the device (see configuration file)
3542d344a2aSNobuhiro Iwamatsu  *
3552d344a2aSNobuhiro Iwamatsu  * @chip:   address of the chip which is to be written
3562d344a2aSNobuhiro Iwamatsu  * @addr:   i2c data address within the chip
3572d344a2aSNobuhiro Iwamatsu  * @alen:   length of the i2c data address (1..2 bytes)
3582d344a2aSNobuhiro Iwamatsu  * @buffer: where to find the data to be written
3592d344a2aSNobuhiro Iwamatsu  * @len:    how much byte do we want to read
3602d344a2aSNobuhiro Iwamatsu  * @return: 0 in case of success
3612d344a2aSNobuhiro Iwamatsu  */
i2c_write(u8 chip,u32 addr,int alen,u8 * buffer,int len)3622d344a2aSNobuhiro Iwamatsu int i2c_write(u8 chip, u32 addr, int alen, u8 *buffer, int len)
3632d344a2aSNobuhiro Iwamatsu {
3642d344a2aSNobuhiro Iwamatsu 	return i2c_raw_write(base, chip, addr, buffer, len);
3652d344a2aSNobuhiro Iwamatsu }
3662d344a2aSNobuhiro Iwamatsu 
3672d344a2aSNobuhiro Iwamatsu /*
3682d344a2aSNobuhiro Iwamatsu  * i2c_probe: - Test if a chip answers for a given i2c address
3692d344a2aSNobuhiro Iwamatsu  *
3702d344a2aSNobuhiro Iwamatsu  * @chip:   address of the chip which is searched for
3712d344a2aSNobuhiro Iwamatsu  * @return: 0 if a chip was found, -1 otherwhise
3722d344a2aSNobuhiro Iwamatsu  */
i2c_probe(u8 chip)3732d344a2aSNobuhiro Iwamatsu int i2c_probe(u8 chip)
3742d344a2aSNobuhiro Iwamatsu {
3752d344a2aSNobuhiro Iwamatsu 	u8 byte;
3762d344a2aSNobuhiro Iwamatsu 	return i2c_read(chip, 0, 0, &byte, 1);
3772d344a2aSNobuhiro Iwamatsu }
378