1031ed2faSVipin KUMAR /* 2031ed2faSVipin KUMAR * (C) Copyright 2009 3031ed2faSVipin KUMAR * Vipin Kumar, ST Micoelectronics, vipin.kumar@st.com. 4031ed2faSVipin KUMAR * 51a459660SWolfgang Denk * SPDX-License-Identifier: GPL-2.0+ 6031ed2faSVipin KUMAR */ 7031ed2faSVipin KUMAR 8031ed2faSVipin KUMAR #include <common.h> 9334b9b00SStefan Roese #include <dm.h> 10678398b1SStefan Roese #include <i2c.h> 11ba5da550SStefan Roese #include <pci.h> 12031ed2faSVipin KUMAR #include <asm/io.h> 13031ed2faSVipin KUMAR #include "designware_i2c.h" 14031ed2faSVipin KUMAR 15ba5da550SStefan Roese struct dw_scl_sda_cfg { 16ba5da550SStefan Roese u32 ss_hcnt; 17ba5da550SStefan Roese u32 fs_hcnt; 18ba5da550SStefan Roese u32 ss_lcnt; 19ba5da550SStefan Roese u32 fs_lcnt; 20ba5da550SStefan Roese u32 sda_hold; 21ba5da550SStefan Roese }; 22ba5da550SStefan Roese 23ba5da550SStefan Roese #ifdef CONFIG_X86 24ba5da550SStefan Roese /* BayTrail HCNT/LCNT/SDA hold time */ 25ba5da550SStefan Roese static struct dw_scl_sda_cfg byt_config = { 26ba5da550SStefan Roese .ss_hcnt = 0x200, 27ba5da550SStefan Roese .fs_hcnt = 0x55, 28ba5da550SStefan Roese .ss_lcnt = 0x200, 29ba5da550SStefan Roese .fs_lcnt = 0x99, 30ba5da550SStefan Roese .sda_hold = 0x6, 31ba5da550SStefan Roese }; 32ba5da550SStefan Roese #endif 33ba5da550SStefan Roese 34334b9b00SStefan Roese struct dw_i2c { 35334b9b00SStefan Roese struct i2c_regs *regs; 36ba5da550SStefan Roese struct dw_scl_sda_cfg *scl_sda_cfg; 37334b9b00SStefan Roese }; 38334b9b00SStefan Roese 39b6a77b0cSStefan Roese #ifdef CONFIG_SYS_I2C_DW_ENABLE_STATUS_UNSUPPORTED 40b6a77b0cSStefan Roese static void dw_i2c_enable(struct i2c_regs *i2c_base, bool enable) 41b6a77b0cSStefan Roese { 42b6a77b0cSStefan Roese u32 ena = enable ? IC_ENABLE_0B : 0; 43b6a77b0cSStefan Roese 44b6a77b0cSStefan Roese writel(ena, &i2c_base->ic_enable); 45b6a77b0cSStefan Roese } 46b6a77b0cSStefan Roese #else 471c8b089bSStefan Roese static void dw_i2c_enable(struct i2c_regs *i2c_base, bool enable) 481c8b089bSStefan Roese { 491c8b089bSStefan Roese u32 ena = enable ? IC_ENABLE_0B : 0; 501c8b089bSStefan Roese int timeout = 100; 511c8b089bSStefan Roese 521c8b089bSStefan Roese do { 531c8b089bSStefan Roese writel(ena, &i2c_base->ic_enable); 541c8b089bSStefan Roese if ((readl(&i2c_base->ic_enable_status) & IC_ENABLE_0B) == ena) 551c8b089bSStefan Roese return; 561c8b089bSStefan Roese 571c8b089bSStefan Roese /* 581c8b089bSStefan Roese * Wait 10 times the signaling period of the highest I2C 591c8b089bSStefan Roese * transfer supported by the driver (for 400KHz this is 601c8b089bSStefan Roese * 25us) as described in the DesignWare I2C databook. 611c8b089bSStefan Roese */ 621c8b089bSStefan Roese udelay(25); 631c8b089bSStefan Roese } while (timeout--); 641c8b089bSStefan Roese 651c8b089bSStefan Roese printf("timeout in %sabling I2C adapter\n", enable ? "en" : "dis"); 661c8b089bSStefan Roese } 67b6a77b0cSStefan Roese #endif 681c8b089bSStefan Roese 69031ed2faSVipin KUMAR /* 7011b544abSStefan Roese * i2c_set_bus_speed - Set the i2c speed 7111b544abSStefan Roese * @speed: required i2c speed 72031ed2faSVipin KUMAR * 7311b544abSStefan Roese * Set the i2c speed. 74031ed2faSVipin KUMAR */ 753f4358daSStefan Roese static unsigned int __dw_i2c_set_bus_speed(struct i2c_regs *i2c_base, 76ba5da550SStefan Roese struct dw_scl_sda_cfg *scl_sda_cfg, 7711b544abSStefan Roese unsigned int speed) 78031ed2faSVipin KUMAR { 79031ed2faSVipin KUMAR unsigned int cntl; 80031ed2faSVipin KUMAR unsigned int hcnt, lcnt; 8111b544abSStefan Roese int i2c_spd; 8211b544abSStefan Roese 8311b544abSStefan Roese if (speed >= I2C_MAX_SPEED) 8411b544abSStefan Roese i2c_spd = IC_SPEED_MODE_MAX; 8511b544abSStefan Roese else if (speed >= I2C_FAST_SPEED) 8611b544abSStefan Roese i2c_spd = IC_SPEED_MODE_FAST; 8711b544abSStefan Roese else 8811b544abSStefan Roese i2c_spd = IC_SPEED_MODE_STANDARD; 895e3e8ddaSArmando Visconti 905e3e8ddaSArmando Visconti /* to set speed cltr must be disabled */ 911c8b089bSStefan Roese dw_i2c_enable(i2c_base, false); 925e3e8ddaSArmando Visconti 93678398b1SStefan Roese cntl = (readl(&i2c_base->ic_con) & (~IC_CON_SPD_MSK)); 94031ed2faSVipin KUMAR 95031ed2faSVipin KUMAR switch (i2c_spd) { 96ba5da550SStefan Roese #ifndef CONFIG_X86 /* No High-speed for BayTrail yet */ 97031ed2faSVipin KUMAR case IC_SPEED_MODE_MAX: 98ba5da550SStefan Roese cntl |= IC_CON_SPD_SS; 99ba5da550SStefan Roese if (scl_sda_cfg) { 100ba5da550SStefan Roese hcnt = scl_sda_cfg->fs_hcnt; 101ba5da550SStefan Roese lcnt = scl_sda_cfg->fs_lcnt; 102ba5da550SStefan Roese } else { 1035b8439bbSArmando Visconti hcnt = (IC_CLK * MIN_HS_SCL_HIGHTIME) / NANO_TO_MICRO; 1045b8439bbSArmando Visconti lcnt = (IC_CLK * MIN_HS_SCL_LOWTIME) / NANO_TO_MICRO; 105ba5da550SStefan Roese } 106ba5da550SStefan Roese writel(hcnt, &i2c_base->ic_hs_scl_hcnt); 107678398b1SStefan Roese writel(lcnt, &i2c_base->ic_hs_scl_lcnt); 108031ed2faSVipin KUMAR break; 109ba5da550SStefan Roese #endif 110031ed2faSVipin KUMAR 111031ed2faSVipin KUMAR case IC_SPEED_MODE_STANDARD: 112031ed2faSVipin KUMAR cntl |= IC_CON_SPD_SS; 113ba5da550SStefan Roese if (scl_sda_cfg) { 114ba5da550SStefan Roese hcnt = scl_sda_cfg->ss_hcnt; 115ba5da550SStefan Roese lcnt = scl_sda_cfg->ss_lcnt; 116ba5da550SStefan Roese } else { 1175b8439bbSArmando Visconti hcnt = (IC_CLK * MIN_SS_SCL_HIGHTIME) / NANO_TO_MICRO; 1185b8439bbSArmando Visconti lcnt = (IC_CLK * MIN_SS_SCL_LOWTIME) / NANO_TO_MICRO; 119ba5da550SStefan Roese } 120ba5da550SStefan Roese writel(hcnt, &i2c_base->ic_ss_scl_hcnt); 121678398b1SStefan Roese writel(lcnt, &i2c_base->ic_ss_scl_lcnt); 122031ed2faSVipin KUMAR break; 123031ed2faSVipin KUMAR 124031ed2faSVipin KUMAR case IC_SPEED_MODE_FAST: 125031ed2faSVipin KUMAR default: 126031ed2faSVipin KUMAR cntl |= IC_CON_SPD_FS; 127ba5da550SStefan Roese if (scl_sda_cfg) { 128ba5da550SStefan Roese hcnt = scl_sda_cfg->fs_hcnt; 129ba5da550SStefan Roese lcnt = scl_sda_cfg->fs_lcnt; 130ba5da550SStefan Roese } else { 1315b8439bbSArmando Visconti hcnt = (IC_CLK * MIN_FS_SCL_HIGHTIME) / NANO_TO_MICRO; 1325b8439bbSArmando Visconti lcnt = (IC_CLK * MIN_FS_SCL_LOWTIME) / NANO_TO_MICRO; 133ba5da550SStefan Roese } 134ba5da550SStefan Roese writel(hcnt, &i2c_base->ic_fs_scl_hcnt); 135678398b1SStefan Roese writel(lcnt, &i2c_base->ic_fs_scl_lcnt); 136031ed2faSVipin KUMAR break; 137031ed2faSVipin KUMAR } 138031ed2faSVipin KUMAR 139678398b1SStefan Roese writel(cntl, &i2c_base->ic_con); 140031ed2faSVipin KUMAR 141ba5da550SStefan Roese /* Configure SDA Hold Time if required */ 142ba5da550SStefan Roese if (scl_sda_cfg) 143ba5da550SStefan Roese writel(scl_sda_cfg->sda_hold, &i2c_base->ic_sda_hold); 144ba5da550SStefan Roese 1455b8439bbSArmando Visconti /* Enable back i2c now speed set */ 1461c8b089bSStefan Roese dw_i2c_enable(i2c_base, true); 147031ed2faSVipin KUMAR 1483f4358daSStefan Roese return 0; 1493f4358daSStefan Roese } 1503f4358daSStefan Roese 1513f4358daSStefan Roese /* 1523f4358daSStefan Roese * i2c_setaddress - Sets the target slave address 1533f4358daSStefan Roese * @i2c_addr: target i2c address 1543f4358daSStefan Roese * 1553f4358daSStefan Roese * Sets the target slave address. 1563f4358daSStefan Roese */ 1573f4358daSStefan Roese static void i2c_setaddress(struct i2c_regs *i2c_base, unsigned int i2c_addr) 1583f4358daSStefan Roese { 1593f4358daSStefan Roese /* Disable i2c */ 1603f4358daSStefan Roese dw_i2c_enable(i2c_base, false); 1613f4358daSStefan Roese 1623f4358daSStefan Roese writel(i2c_addr, &i2c_base->ic_tar); 1633f4358daSStefan Roese 1643f4358daSStefan Roese /* Enable i2c */ 1653f4358daSStefan Roese dw_i2c_enable(i2c_base, true); 1663f4358daSStefan Roese } 1673f4358daSStefan Roese 1683f4358daSStefan Roese /* 1693f4358daSStefan Roese * i2c_flush_rxfifo - Flushes the i2c RX FIFO 1703f4358daSStefan Roese * 1713f4358daSStefan Roese * Flushes the i2c RX FIFO 1723f4358daSStefan Roese */ 1733f4358daSStefan Roese static void i2c_flush_rxfifo(struct i2c_regs *i2c_base) 1743f4358daSStefan Roese { 1753f4358daSStefan Roese while (readl(&i2c_base->ic_status) & IC_STATUS_RFNE) 1763f4358daSStefan Roese readl(&i2c_base->ic_cmd_data); 1773f4358daSStefan Roese } 1783f4358daSStefan Roese 1793f4358daSStefan Roese /* 1803f4358daSStefan Roese * i2c_wait_for_bb - Waits for bus busy 1813f4358daSStefan Roese * 1823f4358daSStefan Roese * Waits for bus busy 1833f4358daSStefan Roese */ 1843f4358daSStefan Roese static int i2c_wait_for_bb(struct i2c_regs *i2c_base) 1853f4358daSStefan Roese { 1863f4358daSStefan Roese unsigned long start_time_bb = get_timer(0); 1873f4358daSStefan Roese 1883f4358daSStefan Roese while ((readl(&i2c_base->ic_status) & IC_STATUS_MA) || 1893f4358daSStefan Roese !(readl(&i2c_base->ic_status) & IC_STATUS_TFE)) { 1903f4358daSStefan Roese 1913f4358daSStefan Roese /* Evaluate timeout */ 1923f4358daSStefan Roese if (get_timer(start_time_bb) > (unsigned long)(I2C_BYTE_TO_BB)) 1933f4358daSStefan Roese return 1; 1943f4358daSStefan Roese } 195031ed2faSVipin KUMAR 196031ed2faSVipin KUMAR return 0; 197031ed2faSVipin KUMAR } 198031ed2faSVipin KUMAR 1993f4358daSStefan Roese static int i2c_xfer_init(struct i2c_regs *i2c_base, uchar chip, uint addr, 2003f4358daSStefan Roese int alen) 2013f4358daSStefan Roese { 2023f4358daSStefan Roese if (i2c_wait_for_bb(i2c_base)) 2033f4358daSStefan Roese return 1; 2043f4358daSStefan Roese 2053f4358daSStefan Roese i2c_setaddress(i2c_base, chip); 2063f4358daSStefan Roese while (alen) { 2073f4358daSStefan Roese alen--; 2083f4358daSStefan Roese /* high byte address going out first */ 2093f4358daSStefan Roese writel((addr >> (alen * 8)) & 0xff, 2103f4358daSStefan Roese &i2c_base->ic_cmd_data); 2113f4358daSStefan Roese } 2123f4358daSStefan Roese return 0; 2133f4358daSStefan Roese } 2143f4358daSStefan Roese 2153f4358daSStefan Roese static int i2c_xfer_finish(struct i2c_regs *i2c_base) 2163f4358daSStefan Roese { 2173f4358daSStefan Roese ulong start_stop_det = get_timer(0); 2183f4358daSStefan Roese 2193f4358daSStefan Roese while (1) { 2203f4358daSStefan Roese if ((readl(&i2c_base->ic_raw_intr_stat) & IC_STOP_DET)) { 2213f4358daSStefan Roese readl(&i2c_base->ic_clr_stop_det); 2223f4358daSStefan Roese break; 2233f4358daSStefan Roese } else if (get_timer(start_stop_det) > I2C_STOPDET_TO) { 2243f4358daSStefan Roese break; 2253f4358daSStefan Roese } 2263f4358daSStefan Roese } 2273f4358daSStefan Roese 2283f4358daSStefan Roese if (i2c_wait_for_bb(i2c_base)) { 2293f4358daSStefan Roese printf("Timed out waiting for bus\n"); 2303f4358daSStefan Roese return 1; 2313f4358daSStefan Roese } 2323f4358daSStefan Roese 2333f4358daSStefan Roese i2c_flush_rxfifo(i2c_base); 2343f4358daSStefan Roese 2353f4358daSStefan Roese return 0; 2363f4358daSStefan Roese } 2373f4358daSStefan Roese 2383f4358daSStefan Roese /* 2393f4358daSStefan Roese * i2c_read - Read from i2c memory 2403f4358daSStefan Roese * @chip: target i2c address 2413f4358daSStefan Roese * @addr: address to read from 2423f4358daSStefan Roese * @alen: 2433f4358daSStefan Roese * @buffer: buffer for read data 2443f4358daSStefan Roese * @len: no of bytes to be read 2453f4358daSStefan Roese * 2463f4358daSStefan Roese * Read from i2c memory. 2473f4358daSStefan Roese */ 2483f4358daSStefan Roese static int __dw_i2c_read(struct i2c_regs *i2c_base, u8 dev, uint addr, 2493f4358daSStefan Roese int alen, u8 *buffer, int len) 2503f4358daSStefan Roese { 2513f4358daSStefan Roese unsigned long start_time_rx; 252b0338080SMarek Vasut unsigned int active = 0; 2533f4358daSStefan Roese 2543f4358daSStefan Roese #ifdef CONFIG_SYS_I2C_EEPROM_ADDR_OVERFLOW 2553f4358daSStefan Roese /* 2563f4358daSStefan Roese * EEPROM chips that implement "address overflow" are ones 2573f4358daSStefan Roese * like Catalyst 24WC04/08/16 which has 9/10/11 bits of 2583f4358daSStefan Roese * address and the extra bits end up in the "chip address" 2593f4358daSStefan Roese * bit slots. This makes a 24WC08 (1Kbyte) chip look like 2603f4358daSStefan Roese * four 256 byte chips. 2613f4358daSStefan Roese * 2623f4358daSStefan Roese * Note that we consider the length of the address field to 2633f4358daSStefan Roese * still be one byte because the extra address bits are 2643f4358daSStefan Roese * hidden in the chip address. 2653f4358daSStefan Roese */ 2663f4358daSStefan Roese dev |= ((addr >> (alen * 8)) & CONFIG_SYS_I2C_EEPROM_ADDR_OVERFLOW); 2673f4358daSStefan Roese addr &= ~(CONFIG_SYS_I2C_EEPROM_ADDR_OVERFLOW << (alen * 8)); 2683f4358daSStefan Roese 2693f4358daSStefan Roese debug("%s: fix addr_overflow: dev %02x addr %02x\n", __func__, dev, 2703f4358daSStefan Roese addr); 2713f4358daSStefan Roese #endif 2723f4358daSStefan Roese 2733f4358daSStefan Roese if (i2c_xfer_init(i2c_base, dev, addr, alen)) 2743f4358daSStefan Roese return 1; 2753f4358daSStefan Roese 2763f4358daSStefan Roese start_time_rx = get_timer(0); 2773f4358daSStefan Roese while (len) { 278b0338080SMarek Vasut if (!active) { 279b0338080SMarek Vasut /* 280b0338080SMarek Vasut * Avoid writing to ic_cmd_data multiple times 281b0338080SMarek Vasut * in case this loop spins too quickly and the 282b0338080SMarek Vasut * ic_status RFNE bit isn't set after the first 283b0338080SMarek Vasut * write. Subsequent writes to ic_cmd_data can 284b0338080SMarek Vasut * trigger spurious i2c transfer. 285b0338080SMarek Vasut */ 2863f4358daSStefan Roese if (len == 1) 2873f4358daSStefan Roese writel(IC_CMD | IC_STOP, &i2c_base->ic_cmd_data); 2883f4358daSStefan Roese else 2893f4358daSStefan Roese writel(IC_CMD, &i2c_base->ic_cmd_data); 290b0338080SMarek Vasut active = 1; 291b0338080SMarek Vasut } 2923f4358daSStefan Roese 2933f4358daSStefan Roese if (readl(&i2c_base->ic_status) & IC_STATUS_RFNE) { 2943f4358daSStefan Roese *buffer++ = (uchar)readl(&i2c_base->ic_cmd_data); 2953f4358daSStefan Roese len--; 2963f4358daSStefan Roese start_time_rx = get_timer(0); 297b0338080SMarek Vasut active = 0; 2983f4358daSStefan Roese } else if (get_timer(start_time_rx) > I2C_BYTE_TO) { 2993f4358daSStefan Roese return 1; 3003f4358daSStefan Roese } 3013f4358daSStefan Roese } 3023f4358daSStefan Roese 3033f4358daSStefan Roese return i2c_xfer_finish(i2c_base); 3043f4358daSStefan Roese } 3053f4358daSStefan Roese 3063f4358daSStefan Roese /* 3073f4358daSStefan Roese * i2c_write - Write to i2c memory 3083f4358daSStefan Roese * @chip: target i2c address 3093f4358daSStefan Roese * @addr: address to read from 3103f4358daSStefan Roese * @alen: 3113f4358daSStefan Roese * @buffer: buffer for read data 3123f4358daSStefan Roese * @len: no of bytes to be read 3133f4358daSStefan Roese * 3143f4358daSStefan Roese * Write to i2c memory. 3153f4358daSStefan Roese */ 3163f4358daSStefan Roese static int __dw_i2c_write(struct i2c_regs *i2c_base, u8 dev, uint addr, 3173f4358daSStefan Roese int alen, u8 *buffer, int len) 3183f4358daSStefan Roese { 3193f4358daSStefan Roese int nb = len; 3203f4358daSStefan Roese unsigned long start_time_tx; 3213f4358daSStefan Roese 3223f4358daSStefan Roese #ifdef CONFIG_SYS_I2C_EEPROM_ADDR_OVERFLOW 3233f4358daSStefan Roese /* 3243f4358daSStefan Roese * EEPROM chips that implement "address overflow" are ones 3253f4358daSStefan Roese * like Catalyst 24WC04/08/16 which has 9/10/11 bits of 3263f4358daSStefan Roese * address and the extra bits end up in the "chip address" 3273f4358daSStefan Roese * bit slots. This makes a 24WC08 (1Kbyte) chip look like 3283f4358daSStefan Roese * four 256 byte chips. 3293f4358daSStefan Roese * 3303f4358daSStefan Roese * Note that we consider the length of the address field to 3313f4358daSStefan Roese * still be one byte because the extra address bits are 3323f4358daSStefan Roese * hidden in the chip address. 3333f4358daSStefan Roese */ 3343f4358daSStefan Roese dev |= ((addr >> (alen * 8)) & CONFIG_SYS_I2C_EEPROM_ADDR_OVERFLOW); 3353f4358daSStefan Roese addr &= ~(CONFIG_SYS_I2C_EEPROM_ADDR_OVERFLOW << (alen * 8)); 3363f4358daSStefan Roese 3373f4358daSStefan Roese debug("%s: fix addr_overflow: dev %02x addr %02x\n", __func__, dev, 3383f4358daSStefan Roese addr); 3393f4358daSStefan Roese #endif 3403f4358daSStefan Roese 3413f4358daSStefan Roese if (i2c_xfer_init(i2c_base, dev, addr, alen)) 3423f4358daSStefan Roese return 1; 3433f4358daSStefan Roese 3443f4358daSStefan Roese start_time_tx = get_timer(0); 3453f4358daSStefan Roese while (len) { 3463f4358daSStefan Roese if (readl(&i2c_base->ic_status) & IC_STATUS_TFNF) { 3473f4358daSStefan Roese if (--len == 0) { 3483f4358daSStefan Roese writel(*buffer | IC_STOP, 3493f4358daSStefan Roese &i2c_base->ic_cmd_data); 3503f4358daSStefan Roese } else { 3513f4358daSStefan Roese writel(*buffer, &i2c_base->ic_cmd_data); 3523f4358daSStefan Roese } 3533f4358daSStefan Roese buffer++; 3543f4358daSStefan Roese start_time_tx = get_timer(0); 3553f4358daSStefan Roese 3563f4358daSStefan Roese } else if (get_timer(start_time_tx) > (nb * I2C_BYTE_TO)) { 3573f4358daSStefan Roese printf("Timed out. i2c write Failed\n"); 3583f4358daSStefan Roese return 1; 3593f4358daSStefan Roese } 3603f4358daSStefan Roese } 3613f4358daSStefan Roese 3623f4358daSStefan Roese return i2c_xfer_finish(i2c_base); 3633f4358daSStefan Roese } 3643f4358daSStefan Roese 365334b9b00SStefan Roese /* 366334b9b00SStefan Roese * __dw_i2c_init - Init function 367334b9b00SStefan Roese * @speed: required i2c speed 368334b9b00SStefan Roese * @slaveaddr: slave address for the device 369334b9b00SStefan Roese * 370334b9b00SStefan Roese * Initialization function. 371334b9b00SStefan Roese */ 372334b9b00SStefan Roese static void __dw_i2c_init(struct i2c_regs *i2c_base, int speed, int slaveaddr) 373334b9b00SStefan Roese { 374334b9b00SStefan Roese /* Disable i2c */ 375334b9b00SStefan Roese dw_i2c_enable(i2c_base, false); 376334b9b00SStefan Roese 377*014e47f0SMarek Vasut writel(IC_CON_SD | IC_CON_RE | IC_CON_SPD_FS | IC_CON_MM, 378*014e47f0SMarek Vasut &i2c_base->ic_con); 379334b9b00SStefan Roese writel(IC_RX_TL, &i2c_base->ic_rx_tl); 380334b9b00SStefan Roese writel(IC_TX_TL, &i2c_base->ic_tx_tl); 381334b9b00SStefan Roese writel(IC_STOP_DET, &i2c_base->ic_intr_mask); 382334b9b00SStefan Roese #ifndef CONFIG_DM_I2C 383ba5da550SStefan Roese __dw_i2c_set_bus_speed(i2c_base, NULL, speed); 384334b9b00SStefan Roese writel(slaveaddr, &i2c_base->ic_sar); 385334b9b00SStefan Roese #endif 386334b9b00SStefan Roese 387334b9b00SStefan Roese /* Enable i2c */ 388334b9b00SStefan Roese dw_i2c_enable(i2c_base, true); 389334b9b00SStefan Roese } 390334b9b00SStefan Roese 391334b9b00SStefan Roese #ifndef CONFIG_DM_I2C 392334b9b00SStefan Roese /* 393334b9b00SStefan Roese * The legacy I2C functions. These need to get removed once 394334b9b00SStefan Roese * all users of this driver are converted to DM. 395334b9b00SStefan Roese */ 3963f4358daSStefan Roese static struct i2c_regs *i2c_get_base(struct i2c_adapter *adap) 3973f4358daSStefan Roese { 3983f4358daSStefan Roese switch (adap->hwadapnr) { 3993f4358daSStefan Roese #if CONFIG_SYS_I2C_BUS_MAX >= 4 4003f4358daSStefan Roese case 3: 4013f4358daSStefan Roese return (struct i2c_regs *)CONFIG_SYS_I2C_BASE3; 4023f4358daSStefan Roese #endif 4033f4358daSStefan Roese #if CONFIG_SYS_I2C_BUS_MAX >= 3 4043f4358daSStefan Roese case 2: 4053f4358daSStefan Roese return (struct i2c_regs *)CONFIG_SYS_I2C_BASE2; 4063f4358daSStefan Roese #endif 4073f4358daSStefan Roese #if CONFIG_SYS_I2C_BUS_MAX >= 2 4083f4358daSStefan Roese case 1: 4093f4358daSStefan Roese return (struct i2c_regs *)CONFIG_SYS_I2C_BASE1; 4103f4358daSStefan Roese #endif 4113f4358daSStefan Roese case 0: 4123f4358daSStefan Roese return (struct i2c_regs *)CONFIG_SYS_I2C_BASE; 4133f4358daSStefan Roese default: 4143f4358daSStefan Roese printf("Wrong I2C-adapter number %d\n", adap->hwadapnr); 4153f4358daSStefan Roese } 4163f4358daSStefan Roese 4173f4358daSStefan Roese return NULL; 4183f4358daSStefan Roese } 4193f4358daSStefan Roese 4203f4358daSStefan Roese static unsigned int dw_i2c_set_bus_speed(struct i2c_adapter *adap, 4213f4358daSStefan Roese unsigned int speed) 4223f4358daSStefan Roese { 4233f4358daSStefan Roese adap->speed = speed; 424ba5da550SStefan Roese return __dw_i2c_set_bus_speed(i2c_get_base(adap), NULL, speed); 4253f4358daSStefan Roese } 4263f4358daSStefan Roese 427334b9b00SStefan Roese static void dw_i2c_init(struct i2c_adapter *adap, int speed, int slaveaddr) 428031ed2faSVipin KUMAR { 429334b9b00SStefan Roese __dw_i2c_init(i2c_get_base(adap), speed, slaveaddr); 430031ed2faSVipin KUMAR } 431031ed2faSVipin KUMAR 432678398b1SStefan Roese static int dw_i2c_read(struct i2c_adapter *adap, u8 dev, uint addr, 433678398b1SStefan Roese int alen, u8 *buffer, int len) 434031ed2faSVipin KUMAR { 4353f4358daSStefan Roese return __dw_i2c_read(i2c_get_base(adap), dev, addr, alen, buffer, len); 436031ed2faSVipin KUMAR } 437031ed2faSVipin KUMAR 438678398b1SStefan Roese static int dw_i2c_write(struct i2c_adapter *adap, u8 dev, uint addr, 439678398b1SStefan Roese int alen, u8 *buffer, int len) 440031ed2faSVipin KUMAR { 4413f4358daSStefan Roese return __dw_i2c_write(i2c_get_base(adap), dev, addr, alen, buffer, len); 442031ed2faSVipin KUMAR } 443031ed2faSVipin KUMAR 444334b9b00SStefan Roese /* dw_i2c_probe - Probe the i2c chip */ 445678398b1SStefan Roese static int dw_i2c_probe(struct i2c_adapter *adap, u8 dev) 446031ed2faSVipin KUMAR { 4473f4358daSStefan Roese struct i2c_regs *i2c_base = i2c_get_base(adap); 448031ed2faSVipin KUMAR u32 tmp; 449496ba48fSStefan Roese int ret; 450031ed2faSVipin KUMAR 451031ed2faSVipin KUMAR /* 452031ed2faSVipin KUMAR * Try to read the first location of the chip. 453031ed2faSVipin KUMAR */ 4543f4358daSStefan Roese ret = __dw_i2c_read(i2c_base, dev, 0, 1, (uchar *)&tmp, 1); 455496ba48fSStefan Roese if (ret) 456678398b1SStefan Roese dw_i2c_init(adap, adap->speed, adap->slaveaddr); 457496ba48fSStefan Roese 458496ba48fSStefan Roese return ret; 459031ed2faSVipin KUMAR } 460ac6e2fe6SArmando Visconti 461678398b1SStefan Roese U_BOOT_I2C_ADAP_COMPLETE(dw_0, dw_i2c_init, dw_i2c_probe, dw_i2c_read, 462678398b1SStefan Roese dw_i2c_write, dw_i2c_set_bus_speed, 463678398b1SStefan Roese CONFIG_SYS_I2C_SPEED, CONFIG_SYS_I2C_SLAVE, 0) 464ac6e2fe6SArmando Visconti 465678398b1SStefan Roese #if CONFIG_SYS_I2C_BUS_MAX >= 2 466678398b1SStefan Roese U_BOOT_I2C_ADAP_COMPLETE(dw_1, dw_i2c_init, dw_i2c_probe, dw_i2c_read, 467678398b1SStefan Roese dw_i2c_write, dw_i2c_set_bus_speed, 468678398b1SStefan Roese CONFIG_SYS_I2C_SPEED1, CONFIG_SYS_I2C_SLAVE1, 1) 469678398b1SStefan Roese #endif 470ac6e2fe6SArmando Visconti 471678398b1SStefan Roese #if CONFIG_SYS_I2C_BUS_MAX >= 3 472678398b1SStefan Roese U_BOOT_I2C_ADAP_COMPLETE(dw_2, dw_i2c_init, dw_i2c_probe, dw_i2c_read, 473678398b1SStefan Roese dw_i2c_write, dw_i2c_set_bus_speed, 474678398b1SStefan Roese CONFIG_SYS_I2C_SPEED2, CONFIG_SYS_I2C_SLAVE2, 2) 475678398b1SStefan Roese #endif 476ac6e2fe6SArmando Visconti 477678398b1SStefan Roese #if CONFIG_SYS_I2C_BUS_MAX >= 4 478678398b1SStefan Roese U_BOOT_I2C_ADAP_COMPLETE(dw_3, dw_i2c_init, dw_i2c_probe, dw_i2c_read, 479678398b1SStefan Roese dw_i2c_write, dw_i2c_set_bus_speed, 480678398b1SStefan Roese CONFIG_SYS_I2C_SPEED3, CONFIG_SYS_I2C_SLAVE3, 3) 481ac6e2fe6SArmando Visconti #endif 482334b9b00SStefan Roese 483334b9b00SStefan Roese #else /* CONFIG_DM_I2C */ 484334b9b00SStefan Roese /* The DM I2C functions */ 485334b9b00SStefan Roese 486334b9b00SStefan Roese static int designware_i2c_xfer(struct udevice *bus, struct i2c_msg *msg, 487334b9b00SStefan Roese int nmsgs) 488334b9b00SStefan Roese { 489334b9b00SStefan Roese struct dw_i2c *i2c = dev_get_priv(bus); 490334b9b00SStefan Roese int ret; 491334b9b00SStefan Roese 492334b9b00SStefan Roese debug("i2c_xfer: %d messages\n", nmsgs); 493334b9b00SStefan Roese for (; nmsgs > 0; nmsgs--, msg++) { 494334b9b00SStefan Roese debug("i2c_xfer: chip=0x%x, len=0x%x\n", msg->addr, msg->len); 495334b9b00SStefan Roese if (msg->flags & I2C_M_RD) { 496334b9b00SStefan Roese ret = __dw_i2c_read(i2c->regs, msg->addr, 0, 0, 497334b9b00SStefan Roese msg->buf, msg->len); 498334b9b00SStefan Roese } else { 499334b9b00SStefan Roese ret = __dw_i2c_write(i2c->regs, msg->addr, 0, 0, 500334b9b00SStefan Roese msg->buf, msg->len); 501334b9b00SStefan Roese } 502334b9b00SStefan Roese if (ret) { 503334b9b00SStefan Roese debug("i2c_write: error sending\n"); 504334b9b00SStefan Roese return -EREMOTEIO; 505334b9b00SStefan Roese } 506334b9b00SStefan Roese } 507334b9b00SStefan Roese 508334b9b00SStefan Roese return 0; 509334b9b00SStefan Roese } 510334b9b00SStefan Roese 511334b9b00SStefan Roese static int designware_i2c_set_bus_speed(struct udevice *bus, unsigned int speed) 512334b9b00SStefan Roese { 513334b9b00SStefan Roese struct dw_i2c *i2c = dev_get_priv(bus); 514334b9b00SStefan Roese 515ba5da550SStefan Roese return __dw_i2c_set_bus_speed(i2c->regs, i2c->scl_sda_cfg, speed); 516334b9b00SStefan Roese } 517334b9b00SStefan Roese 518334b9b00SStefan Roese static int designware_i2c_probe_chip(struct udevice *bus, uint chip_addr, 519334b9b00SStefan Roese uint chip_flags) 520334b9b00SStefan Roese { 521334b9b00SStefan Roese struct dw_i2c *i2c = dev_get_priv(bus); 522334b9b00SStefan Roese struct i2c_regs *i2c_base = i2c->regs; 523334b9b00SStefan Roese u32 tmp; 524334b9b00SStefan Roese int ret; 525334b9b00SStefan Roese 526334b9b00SStefan Roese /* Try to read the first location of the chip */ 527334b9b00SStefan Roese ret = __dw_i2c_read(i2c_base, chip_addr, 0, 1, (uchar *)&tmp, 1); 528334b9b00SStefan Roese if (ret) 529334b9b00SStefan Roese __dw_i2c_init(i2c_base, 0, 0); 530334b9b00SStefan Roese 531334b9b00SStefan Roese return ret; 532334b9b00SStefan Roese } 533334b9b00SStefan Roese 534334b9b00SStefan Roese static int designware_i2c_probe(struct udevice *bus) 535334b9b00SStefan Roese { 536334b9b00SStefan Roese struct dw_i2c *priv = dev_get_priv(bus); 537334b9b00SStefan Roese 538ba5da550SStefan Roese if (device_is_on_pci_bus(bus)) { 539ba5da550SStefan Roese #ifdef CONFIG_DM_PCI 540ba5da550SStefan Roese /* Save base address from PCI BAR */ 541ba5da550SStefan Roese priv->regs = (struct i2c_regs *) 542ba5da550SStefan Roese dm_pci_map_bar(bus, PCI_BASE_ADDRESS_0, PCI_REGION_MEM); 543ba5da550SStefan Roese #ifdef CONFIG_X86 544ba5da550SStefan Roese /* Use BayTrail specific timing values */ 545ba5da550SStefan Roese priv->scl_sda_cfg = &byt_config; 546ba5da550SStefan Roese #endif 547ba5da550SStefan Roese #endif 548ba5da550SStefan Roese } else { 549a821c4afSSimon Glass priv->regs = (struct i2c_regs *)devfdt_get_addr_ptr(bus); 550ba5da550SStefan Roese } 551334b9b00SStefan Roese 552334b9b00SStefan Roese __dw_i2c_init(priv->regs, 0, 0); 553334b9b00SStefan Roese 554334b9b00SStefan Roese return 0; 555334b9b00SStefan Roese } 556334b9b00SStefan Roese 557ba5da550SStefan Roese static int designware_i2c_bind(struct udevice *dev) 558ba5da550SStefan Roese { 559ba5da550SStefan Roese static int num_cards; 560ba5da550SStefan Roese char name[20]; 561ba5da550SStefan Roese 562ba5da550SStefan Roese /* Create a unique device name for PCI type devices */ 563ba5da550SStefan Roese if (device_is_on_pci_bus(dev)) { 564ba5da550SStefan Roese /* 565ba5da550SStefan Roese * ToDo: 566ba5da550SStefan Roese * Setting req_seq in the driver is probably not recommended. 567ba5da550SStefan Roese * But without a DT alias the number is not configured. And 568ba5da550SStefan Roese * using this driver is impossible for PCIe I2C devices. 569ba5da550SStefan Roese * This can be removed, once a better (correct) way for this 570ba5da550SStefan Roese * is found and implemented. 571ba5da550SStefan Roese */ 572ba5da550SStefan Roese dev->req_seq = num_cards; 573ba5da550SStefan Roese sprintf(name, "i2c_designware#%u", num_cards++); 574ba5da550SStefan Roese device_set_name(dev, name); 575ba5da550SStefan Roese } 576ba5da550SStefan Roese 577ba5da550SStefan Roese return 0; 578ba5da550SStefan Roese } 579ba5da550SStefan Roese 580334b9b00SStefan Roese static const struct dm_i2c_ops designware_i2c_ops = { 581334b9b00SStefan Roese .xfer = designware_i2c_xfer, 582334b9b00SStefan Roese .probe_chip = designware_i2c_probe_chip, 583334b9b00SStefan Roese .set_bus_speed = designware_i2c_set_bus_speed, 584334b9b00SStefan Roese }; 585334b9b00SStefan Roese 586334b9b00SStefan Roese static const struct udevice_id designware_i2c_ids[] = { 587334b9b00SStefan Roese { .compatible = "snps,designware-i2c" }, 588334b9b00SStefan Roese { } 589334b9b00SStefan Roese }; 590334b9b00SStefan Roese 591334b9b00SStefan Roese U_BOOT_DRIVER(i2c_designware) = { 592334b9b00SStefan Roese .name = "i2c_designware", 593334b9b00SStefan Roese .id = UCLASS_I2C, 594334b9b00SStefan Roese .of_match = designware_i2c_ids, 595ba5da550SStefan Roese .bind = designware_i2c_bind, 596334b9b00SStefan Roese .probe = designware_i2c_probe, 597334b9b00SStefan Roese .priv_auto_alloc_size = sizeof(struct dw_i2c), 598334b9b00SStefan Roese .ops = &designware_i2c_ops, 599334b9b00SStefan Roese }; 600334b9b00SStefan Roese 601ba5da550SStefan Roese #ifdef CONFIG_X86 602ba5da550SStefan Roese static struct pci_device_id designware_pci_supported[] = { 603ba5da550SStefan Roese /* Intel BayTrail has 7 I2C controller located on the PCI bus */ 604ba5da550SStefan Roese { PCI_VDEVICE(INTEL, 0x0f41) }, 605ba5da550SStefan Roese { PCI_VDEVICE(INTEL, 0x0f42) }, 606ba5da550SStefan Roese { PCI_VDEVICE(INTEL, 0x0f43) }, 607ba5da550SStefan Roese { PCI_VDEVICE(INTEL, 0x0f44) }, 608ba5da550SStefan Roese { PCI_VDEVICE(INTEL, 0x0f45) }, 609ba5da550SStefan Roese { PCI_VDEVICE(INTEL, 0x0f46) }, 610ba5da550SStefan Roese { PCI_VDEVICE(INTEL, 0x0f47) }, 611ba5da550SStefan Roese {}, 612ba5da550SStefan Roese }; 613ba5da550SStefan Roese 614ba5da550SStefan Roese U_BOOT_PCI_DEVICE(i2c_designware, designware_pci_supported); 615ba5da550SStefan Roese #endif 616ba5da550SStefan Roese 617334b9b00SStefan Roese #endif /* CONFIG_DM_I2C */ 618