diff options
author | Jan Dabros <jsd@semihalf.com> | 2021-01-27 22:08:24 +0100 |
---|---|---|
committer | Commit Bot <commit-bot@chromium.org> | 2021-02-09 10:34:38 +0000 |
commit | b4fcacdda8df6b738025361d3edea337129594e9 (patch) | |
tree | c5246fe399bc5611d35540b7d6463ad2bebb6a54 | |
parent | 7852f10868a7cbbb3ae496ff3af82c7cab95e7f1 (diff) | |
download | chrome-ec-b4fcacdda8df6b738025361d3edea337129594e9.tar.gz |
gl3590: Add retry algorithm for port enabling procedure
To improve reliability of gl3590 driver, add verification for success of
previous enable/disable port command.
BUG=b:178125550
BRANCH=main
TEST=Flash FW6410 to GL3590 hub, verify error messages correctness on
port enable/disable events.
Flash FW6411 to GL3590 hub, verify that all commands executed silently
which means success.
Signed-off-by: Jan Dabros <jsd@semihalf.com>
Change-Id: I5599c350c88c2596a4bb2a2ba310d44c08e0717f
Reviewed-on: https://chromium-review.googlesource.com/c/chromiumos/platform/ec/+/2674002
Reviewed-by: Aseda Aboagye <aaboagye@chromium.org>
-rw-r--r-- | driver/gl3590.c | 36 | ||||
-rw-r--r-- | driver/gl3590.h | 1 |
2 files changed, 33 insertions, 4 deletions
diff --git a/driver/gl3590.c b/driver/gl3590.c index ae0d36159b..2a73f44aad 100644 --- a/driver/gl3590.c +++ b/driver/gl3590.c @@ -247,11 +247,14 @@ enum ec_error_list gl3590_ufp_pwr(int hub, struct pwr_con_t *pwr) } } +#define GL3590_EN_PORT_MAX_RETRY_COUNT 10 + int gl3590_enable_ports(int hub, uint8_t port_mask, bool enable) { uint8_t buf[4] = {0}; uint8_t en_mask = 0; - int rv; + uint8_t tmp; + int rv, i; struct uhub_i2c_iface_t *uhub_p = &uhub_config[hub]; if (!uhub_p->initialized) @@ -263,11 +266,36 @@ int gl3590_enable_ports(int hub, uint8_t port_mask, bool enable) buf[0] = en_mask; buf[2] = port_mask; - rv = gl3590_write(hub, GL3590_PORT_DISABLED_REG, buf, sizeof(buf)); + for (i = 1; i <= GL3590_EN_PORT_MAX_RETRY_COUNT; i++) { + rv = gl3590_write(hub, GL3590_PORT_DISABLED_REG, buf, + sizeof(buf)); + if (rv) + return rv; - usleep(200 * MSEC); + usleep(200 * MSEC); - return rv; + /* Verify whether port is enabled/disabled */ + rv = gl3590_read(hub, GL3590_PORT_EN_STS_REG, &tmp, 1); + if (rv) + return rv; + + if (enable && ((tmp & port_mask) == port_mask)) + break; + if (!enable && ((tmp & port_mask) == 0)) + break; + + if (i > GL3590_EN_PORT_MAX_RETRY_COUNT) { + CPRINTF("GL3590: Failed to %s port 0x%x\n", + enable ? "enable" : "disable", port_mask); + return EC_ERROR_HW_INTERNAL; + } + + CPRINTF("GL3590: Port %s retrying.. %d/%d\n" + "Port status is 0x%x\n", enable ? "enable" : "disable", + i, GL3590_EN_PORT_MAX_RETRY_COUNT, tmp); + } + + return EC_SUCCESS; } #ifdef CONFIG_CMD_GL3590 diff --git a/driver/gl3590.h b/driver/gl3590.h index a9d8735029..931035d95e 100644 --- a/driver/gl3590.h +++ b/driver/gl3590.h @@ -17,6 +17,7 @@ #define GL3590_RESPONSE_REG 0x2 #define GL3590_RESPONSE_REG_SYNC_MASK 0x80 #define GL3590_PORT_DISABLED_REG 0x4 +#define GL3590_PORT_EN_STS_REG 0x8 #define GL3590_HUB_STS_REG 0xA #define GL3590_HUB_STS_HOST_PWR_MASK 0x30 #define GL3590_HUB_STS_HOST_PWR_SHIFT 4 |