diff options
author | Alec Berg <alecaberg@chromium.org> | 2015-06-15 12:12:57 -0700 |
---|---|---|
committer | ChromeOS Commit Bot <chromeos-commit-bot@chromium.org> | 2015-06-17 10:03:52 +0000 |
commit | 859f4d50adf6f5732970239fb72fd521eb693c16 (patch) | |
tree | 625c4317c7ee5d74a049ec1ab463d03575388f49 /common | |
parent | bdf1dca078adee4717015c5583d77582b85692c3 (diff) | |
download | chrome-ec-859f4d50adf6f5732970239fb72fd521eb693c16.tar.gz |
tcpc: use vendor ID register to signal TCPC readiness
Add TCPC support for USB VID register and use that register
from the TCPM side to know when the TCPC is ready. TCPC is
ready when phy layer is initialized and CC ADC channels have
been read.
BUG=chrome-os-partner:40920, chrome-os-partner:41258
BRANCH=none
TEST=load and run glados. verify that glados EC doesn't
start sending TCPC commands until it can successfully
read TCPC VID. verify that we can boot with zinger and no
battery.
Change-Id: Iafbab529a16ff904cdb817901baac5e72e3d7220
Signed-off-by: Alec Berg <alecaberg@chromium.org>
Reviewed-on: https://chromium-review.googlesource.com/277710
Reviewed-by: Vincent Palatin <vpalatin@chromium.org>
Diffstat (limited to 'common')
-rw-r--r-- | common/usb_pd_protocol.c | 7 | ||||
-rw-r--r-- | common/usb_pd_tcpc.c | 9 | ||||
-rw-r--r-- | common/usb_pd_tcpm.c | 18 | ||||
-rw-r--r-- | common/usb_pd_tcpm_stub.c | 6 |
4 files changed, 36 insertions, 4 deletions
diff --git a/common/usb_pd_protocol.c b/common/usb_pd_protocol.c index 52b046328a..f87e5010a5 100644 --- a/common/usb_pd_protocol.c +++ b/common/usb_pd_protocol.c @@ -1326,10 +1326,9 @@ void pd_task(void) /* Ensure the power supply is in the default state */ pd_power_supply_reset(port); -#ifdef CONFIG_USB_PD_TCPC - /* Initialize port controller */ - tcpc_init(port); -#endif + /* Initialize TCPM driver and wait for TCPC to be ready */ + tcpm_init(port); + CPRINTF("[%T TCPC p%d ready]\n", port); /* Disable TCPC RX until connection is established */ tcpm_set_rx_enable(port, 0); diff --git a/common/usb_pd_tcpc.c b/common/usb_pd_tcpc.c index 0a5d60d95c..c9cbf03896 100644 --- a/common/usb_pd_tcpc.c +++ b/common/usb_pd_tcpc.c @@ -40,6 +40,9 @@ static struct mutex pd_crc_lock; static const int debug_level; #endif +/* USB Vendor ID, initialized to 0, written to actual VID when TCPC is ready */ +static int tcpc_vid; + /* Encode 5 bits using Biphase Mark Coding */ #define BMC(x) ((x & 1 ? 0x001 : 0x3FF) \ ^ (x & 2 ? 0x004 : 0x3FC) \ @@ -785,6 +788,9 @@ int tcpc_run(int port, int evt) if (pd[port].rx_enabled) pd_rx_enable_monitoring(port); + /* write our TCPC VID to notify TCPM that we are ready */ + tcpc_vid = USB_VID_GOOGLE; + /* TODO: adjust timeout based on how often to sample CC */ return 10*MSEC; } @@ -963,6 +969,9 @@ static int tcpc_i2c_read(int port, int reg, uint8_t *payload) int cc1, cc2; switch (reg) { + case TCPC_REG_VENDOR_ID: + *(uint16_t *)payload = tcpc_vid; + return 2; case TCPC_REG_CC1_STATUS: tcpc_get_cc(port, &cc1, &cc2); payload[0] = TCPC_REG_CC_STATUS_SET( diff --git a/common/usb_pd_tcpm.c b/common/usb_pd_tcpm.c index d24931e692..d7458fabfe 100644 --- a/common/usb_pd_tcpm.c +++ b/common/usb_pd_tcpm.c @@ -6,6 +6,7 @@ /* Type-C port manager */ #include "i2c.h" +#include "timer.h" #include "usb_pd.h" #include "usb_pd_tcpc.h" #include "usb_pd_tcpm.h" @@ -19,6 +20,23 @@ static int tcpc_polarity, tcpc_vconn; +int tcpm_init(int port) +{ + int rv, vid = 0; + + while (1) { + rv = i2c_read16(I2C_PORT_TCPC, I2C_ADDR_TCPC(port), + TCPC_REG_VENDOR_ID, &vid); + /* + * If i2c succeeds and VID is non-zero, then initialization + * is complete + */ + if (rv == EC_SUCCESS && vid) + return rv; + msleep(10); + } +} + int tcpm_get_cc(int port, int *cc1, int *cc2) { int status; diff --git a/common/usb_pd_tcpm_stub.c b/common/usb_pd_tcpm_stub.c index bb8ba57045..dc0843fa10 100644 --- a/common/usb_pd_tcpm_stub.c +++ b/common/usb_pd_tcpm_stub.c @@ -20,6 +20,12 @@ extern int tcpc_get_message(int port, uint32_t *payload, int *head); extern int tcpc_transmit(int port, enum tcpm_transmit_type type, uint16_t header, const uint32_t *data); +int tcpm_init(int port) +{ + tcpc_init(port); + return EC_SUCCESS; +} + int tcpm_get_cc(int port, int *cc1, int *cc2) { return tcpc_get_cc(port, cc1, cc2); |