summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorScott Collyer <scollyer@google.com>2020-06-04 23:17:09 -0700
committerCommit Bot <commit-bot@chromium.org>2021-02-09 21:55:51 +0000
commitacdeee0e728c5b67ac495ccc9bf1afd746dd8a74 (patch)
treed20a8c05ff9c04ff77dfe2e3f2130bf4a3415fc3
parentb76b012a2410c4d0e9cb679f921fec80fb6dcae2 (diff)
downloadchrome-ec-acdeee0e728c5b67ac495ccc9bf1afd746dd8a74.tar.gz
usb_mux: ps8822: Initial version of driver
This CL adds the driver for the PS8822 usb demux. Currently, the driver only supports the expected usb mux driver methods. It is expected that any EQ setting functions would be board specific, though more register definitions would need to be added to the .h file. BUG=b:175660576 BRANCH=None TEST=Connect on host port and then read back mode register to confirm that it's been set as expected. Signed-off-by: Scott Collyer <scollyer@google.com> Change-Id: Ic425ffe41f4653cee7f5500b081d7b5f6ad1a3df Reviewed-on: https://chromium-review.googlesource.com/c/chromiumos/platform/ec/+/2247361 Commit-Queue: Scott Collyer <scollyer@chromium.org> Tested-by: Scott Collyer <scollyer@chromium.org> Reviewed-by: Aseda Aboagye <aaboagye@chromium.org> Reviewed-by: Diana Z <dzigterman@chromium.org>
-rw-r--r--driver/build.mk1
-rw-r--r--driver/usb_mux/ps8822.c100
-rw-r--r--driver/usb_mux/ps8822.h39
-rw-r--r--include/config.h3
-rw-r--r--include/usb_mux.h1
5 files changed, 144 insertions, 0 deletions
diff --git a/driver/build.mk b/driver/build.mk
index 405f775c52..fb9525f4dc 100644
--- a/driver/build.mk
+++ b/driver/build.mk
@@ -175,6 +175,7 @@ driver-$(CONFIG_USB_MUX_PS8740)+=usb_mux/ps8740.o
driver-$(CONFIG_USB_MUX_PS8742)+=usb_mux/ps8740.o
driver-$(CONFIG_USB_MUX_PS8743)+=usb_mux/ps8743.o
driver-$(CONFIG_USB_MUX_TUSB1064)+=usb_mux/tusb1064.o
+driver-$(CONFIG_USB_MUX_PS8822)+=usb_mux/ps8822.o
driver-$(CONFIG_USB_MUX_VIRTUAL)+=usb_mux/virtual.o
# USB Hub with I2C interface
diff --git a/driver/usb_mux/ps8822.c b/driver/usb_mux/ps8822.c
new file mode 100644
index 0000000000..43ea22de3d
--- /dev/null
+++ b/driver/usb_mux/ps8822.c
@@ -0,0 +1,100 @@
+/* Copyright 2021 The Chromium OS Authors. All rights reserved.
+ * Use of this source code is governed by a BSD-style license that can be
+ * found in the LICENSE file.
+ *
+ * Parade PS8822
+ * USB Type-C Redriving Switch for USB Host / DisplayPort.
+ */
+
+#include "common.h"
+#include "i2c.h"
+#include "ps8822.h"
+#include "usb_mux.h"
+#include "util.h"
+
+static int ps8822_read(const struct usb_mux *me, uint8_t reg, int *val)
+{
+ return i2c_read8(me->i2c_port, me->i2c_addr_flags,
+ reg, val);
+}
+
+static int ps8822_write(const struct usb_mux *me, uint8_t reg, uint8_t val)
+{
+ return i2c_write8(me->i2c_port, me->i2c_addr_flags,
+ reg, val);
+}
+
+static int ps8822_init(const struct usb_mux *me)
+{
+ char id[PS8822_ID_LEN + 1];
+ int reg;
+ int i;
+ int rv = 0;
+
+ /* Read ID registers */
+ for (i = 0; i < PS8822_ID_LEN; i++) {
+ rv |= ps8822_read(me, PS8822_REG_DEV_ID1 + i, &reg);
+ if (!rv)
+ id[i] = reg;
+ }
+
+ if (!rv) {
+ id[PS8822_ID_LEN] = '\0';
+ /* Set mode register to default value */
+ rv = ps8822_write(me, PS8822_REG_MODE, 0);
+ rv |= strcasecmp("PS8822", id);
+ }
+
+ return rv;
+}
+
+/* Writes control register to set switch mode */
+static int ps8822_set_mux(const struct usb_mux *me, mux_state_t mux_state)
+{
+ int reg;
+ int rv;
+
+ rv = ps8822_read(me, PS8822_REG_MODE, &reg);
+ if (rv)
+ return rv;
+
+ /* Assume standby, preserve PIN_E config bit */
+ reg &= ~(PS8822_MODE_ALT_DP_EN | PS8822_MODE_USB_EN | PS8822_MODE_FLIP);
+
+ if (mux_state & USB_PD_MUX_USB_ENABLED)
+ reg |= PS8822_MODE_USB_EN;
+ if (mux_state & USB_PD_MUX_DP_ENABLED)
+ reg |= PS8822_MODE_ALT_DP_EN;
+ if (mux_state & USB_PD_MUX_POLARITY_INVERTED)
+ reg |= PS8822_MODE_FLIP;
+
+ return ps8822_write(me, PS8822_REG_MODE, reg);
+}
+
+/* Reads control register and updates mux_state accordingly */
+static int ps8822_get_mux(const struct usb_mux *me, mux_state_t *mux_state)
+{
+ int reg;
+ int res;
+
+ res = ps8822_read(me, PS8822_REG_MODE, &reg);
+ if (res)
+ return res;
+
+ *mux_state = 0;
+ if (reg & PS8822_MODE_USB_EN)
+ *mux_state |= USB_PD_MUX_USB_ENABLED;
+ if (reg & PS8822_MODE_ALT_DP_EN)
+ *mux_state |= USB_PD_MUX_DP_ENABLED;
+ if (reg & PS8822_MODE_FLIP)
+ *mux_state |= USB_PD_MUX_POLARITY_INVERTED;
+
+ return EC_SUCCESS;
+}
+
+
+const struct usb_mux_driver ps8822_usb_mux_driver = {
+ .init = ps8822_init,
+ .set = ps8822_set_mux,
+ .get = ps8822_get_mux,
+};
diff --git a/driver/usb_mux/ps8822.h b/driver/usb_mux/ps8822.h
new file mode 100644
index 0000000000..d37e0600f5
--- /dev/null
+++ b/driver/usb_mux/ps8822.h
@@ -0,0 +1,39 @@
+/* Copyright 2021 The Chromium OS Authors. All rights reserved.
+ * Use of this source code is governed by a BSD-style license that can be
+ * found in the LICENSE file.
+ *
+ * Parade PS8822
+ * USB Type-C Retiming Switch for USB Device / DisplayPort Sink
+ */
+
+#ifndef __CROS_EC_PS8822_H
+#define __CROS_EC_PS8822_H
+
+#include "usb_mux.h"
+
+#define PS8822_I2C_ADDR0_FLAG 0x10
+#define PS8822_I2C_ADDR1_FLAG 0x18
+#define PS8822_I2C_ADDR2_FLAG 0x58
+#define PS8822_I2C_ADDR3_FLAG 0x60
+
+/* Mode register for setting mux */
+#define PS8822_REG_MODE 0x01
+#define PS8822_MODE_ALT_DP_EN BIT(7)
+#define PS8822_MODE_USB_EN BIT(6)
+#define PS8822_MODE_FLIP BIT(5)
+#define PS8822_MODE_PIN_E BIT(4)
+
+#define PS8822_REG_CONFIG 0x02
+#define PS8822_CONFIG_HPD_IN_DIS BIT(7)
+#define PS8822_CONFIG_DP_PLUG BIT(6)
+
+#define PS8822_REG_DEV_ID1 0x06
+#define PS8822_REG_DEV_ID2 0x07
+#define PS8822_REG_DEV_ID3 0x08
+#define PS8822_REG_DEV_ID4 0x09
+#define PS8822_REG_DEV_ID5 0x0A
+#define PS8822_REG_DEV_ID6 0x0B
+
+#define PS8822_ID_LEN 6
+
+#endif /* __CROS_EC_PS8822_H */
diff --git a/include/config.h b/include/config.h
index df235e91f3..ddf4778841 100644
--- a/include/config.h
+++ b/include/config.h
@@ -4762,6 +4762,9 @@
/* Support the Texas Instrument TUSB1064 Type-C Redriving Switch (UFP) */
#undef CONFIG_USB_MUX_TUSB1064
+/* Support the Parade PS8822 Type-C Redriving Demux Switch */
+#undef CONFIG_USB_MUX_PS8822
+
/* 'Virtual' USB mux under host (not EC) control */
#undef CONFIG_USB_MUX_VIRTUAL
diff --git a/include/usb_mux.h b/include/usb_mux.h
index 4391eed1e8..f3d18a7874 100644
--- a/include/usb_mux.h
+++ b/include/usb_mux.h
@@ -153,6 +153,7 @@ extern const struct usb_mux_driver it5205_usb_mux_driver;
extern const struct usb_mux_driver pi3usb3x532_usb_mux_driver;
extern const struct usb_mux_driver ps8740_usb_mux_driver;
extern const struct usb_mux_driver ps8743_usb_mux_driver;
+extern const struct usb_mux_driver ps8822_usb_mux_driver;
extern const struct usb_mux_driver tcpm_usb_mux_driver;
extern const struct usb_mux_driver tusb1064_usb_mux_driver;
extern const struct usb_mux_driver virtual_usb_mux_driver;