i2c: meson: add configurable divider factors
authorGuillaume La Roque <glaroque@baylibre.com>
Fri, 22 Mar 2019 13:49:32 +0000 (14:49 +0100)
committerNeil Armstrong <narmstrong@baylibre.com>
Wed, 10 Apr 2019 14:50:02 +0000 (16:50 +0200)
This patch add support for I2C controller in Meson-AXG SoC,
Due to the IP changes between I2C controller, we need to introduce
a compatible data to make the divider factor configurable.

backport from linux:
931b18e92cd0 ("2c: meson: add configurable divider factors")

Signed-off-by: Guillaume La Roque <glaroque@baylibre.com>
Signed-off-by: Neil Armstrong <narmstrong@baylibre.com>
drivers/i2c/meson_i2c.c

index 7d06d95cf38876092b982e3e4422eff2b446ee4f..ee59bac123628c6e2cb21a7a62d0d368d3791264 100644 (file)
@@ -41,7 +41,12 @@ struct i2c_regs {
        u32 tok_rdata1;
 };
 
+struct meson_i2c_data {
+       unsigned char div_factor;
+};
+
 struct meson_i2c {
+       const struct meson_i2c_data *data;
        struct clk clk;
        struct i2c_regs *regs;
        struct i2c_msg *msg;    /* Current I2C message */
@@ -229,7 +234,7 @@ static int meson_i2c_set_bus_speed(struct udevice *bus, unsigned int speed)
        if (IS_ERR_VALUE(clk_rate))
                return -EINVAL;
 
-       div = DIV_ROUND_UP(clk_rate, speed * 4);
+       div = DIV_ROUND_UP(clk_rate, speed * i2c->data->div_factor);
 
        /* clock divider has 12 bits */
        if (div >= (1 << 12)) {
@@ -253,6 +258,8 @@ static int meson_i2c_probe(struct udevice *bus)
        struct meson_i2c *i2c = dev_get_priv(bus);
        int ret;
 
+       i2c->data = (const struct meson_i2c_data *)dev_get_driver_data(bus);
+
        ret = clk_get_by_index(bus, 0, &i2c->clk);
        if (ret < 0)
                return ret;
@@ -272,11 +279,24 @@ static const struct dm_i2c_ops meson_i2c_ops = {
        .set_bus_speed = meson_i2c_set_bus_speed,
 };
 
+static const struct meson_i2c_data i2c_meson6_data = {
+       .div_factor = 4,
+};
+
+static const struct meson_i2c_data i2c_gxbb_data = {
+       .div_factor = 4,
+};
+
+static const struct meson_i2c_data i2c_axg_data = {
+       .div_factor = 3,
+};
+
 static const struct udevice_id meson_i2c_ids[] = {
-       { .compatible = "amlogic,meson6-i2c" },
-       { .compatible = "amlogic,meson-gx-i2c" },
-       { .compatible = "amlogic,meson-gxbb-i2c" },
-       { }
+       {.compatible = "amlogic,meson6-i2c", .data = (ulong)&i2c_meson6_data},
+       {.compatible = "amlogic,meson-gx-i2c", .data = (ulong)&i2c_gxbb_data},
+       {.compatible = "amlogic,meson-gxbb-i2c", .data = (ulong)&i2c_gxbb_data},
+       {.compatible = "amlogic,meson-axg-i2c", .data = (ulong)&i2c_axg_data},
+       {}
 };
 
 U_BOOT_DRIVER(i2c_meson) = {