Commit 516d0312 authored by Sifan Naeem's avatar Sifan Naeem Committed by Kamal Mostafa

i2c: img-scb: fix LOW and HIGH period values for the SCL clock

commit 987008db upstream.

Currently, after determining the minimum value for the High period
(TCKH) the remainder of the internal clock pulses is set as the Low
period (TCKL). This causes the i2c clock duty cycle to be much less
than 50%.

Modify the starting position to TCKH and TCKL at 50% of the internal
clock, and adjusts the TCKH and TCKL values from there should the
minimum value for TCKL not be met. This results in duty cycles closer
to 50%.

Fixes: commit 27bce457 ("i2c: img-scb: Add Imagination Technologies I2C SCB driver")
Signed-off-by: default avatarSifan Naeem <sifan.naeem@imgtec.com>
Acked-by: default avatarJames Hogan <james.hogan@imgtec.com>
Reviewed-by: default avatarJames Hartley <james.hartley@imgtec.com>
Signed-off-by: default avatarWolfram Sang <wsa@the-dreams.de>
Signed-off-by: default avatarKamal Mostafa <kamal@canonical.com>
parent 9c6cf03d
...@@ -1176,25 +1176,29 @@ static int img_i2c_init(struct img_i2c *i2c) ...@@ -1176,25 +1176,29 @@ static int img_i2c_init(struct img_i2c *i2c)
((bitrate_khz * clk_period) / 2)) ((bitrate_khz * clk_period) / 2))
int_bitrate++; int_bitrate++;
/* Setup TCKH value */ /*
tckh = DIV_ROUND_UP(timing.tckh, clk_period); * Setup clock duty cycle, start with 50% and adjust TCKH and TCKL
* values from there if they don't meet minimum timing requirements
*/
tckh = int_bitrate / 2;
tckl = int_bitrate - tckh;
if (tckh > 0) /* Adjust TCKH and TCKL values */
data = tckh - 1; data = DIV_ROUND_UP(timing.tckl, clk_period);
else
data = 0;
img_i2c_writel(i2c, SCB_TIME_TCKH_REG, data); if (tckl < data) {
tckl = data;
tckh = int_bitrate - tckl;
}
/* Setup TCKL value */ if (tckh > 0)
tckl = int_bitrate - tckh; --tckh;
if (tckl > 0) if (tckl > 0)
data = tckl - 1; --tckl;
else
data = 0;
img_i2c_writel(i2c, SCB_TIME_TCKL_REG, data); img_i2c_writel(i2c, SCB_TIME_TCKH_REG, tckh);
img_i2c_writel(i2c, SCB_TIME_TCKL_REG, tckl);
/* Setup TSDH value */ /* Setup TSDH value */
tsdh = DIV_ROUND_UP(timing.tsdh, clk_period); tsdh = DIV_ROUND_UP(timing.tsdh, clk_period);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment