diff options
Diffstat (limited to 'common/usbc_ppc.c')
-rw-r--r-- | common/usbc_ppc.c | 358 |
1 files changed, 0 insertions, 358 deletions
diff --git a/common/usbc_ppc.c b/common/usbc_ppc.c deleted file mode 100644 index 816c53d06e..0000000000 --- a/common/usbc_ppc.c +++ /dev/null @@ -1,358 +0,0 @@ -/* Copyright 2017 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. - */ - -/* USB-C Power Path Controller Common Code */ - -#include "atomic.h" -#include "common.h" -#include "console.h" -#include "hooks.h" -#include "timer.h" -#include "usbc_ppc.h" -#include "util.h" - -#ifndef TEST_BUILD -#define CPRINTF(format, args...) cprintf(CC_USBPD, format, ## args) -#define CPRINTS(format, args...) cprints(CC_USBPD, format, ## args) -#else -#define CPRINTF(args...) -#define CPRINTS(args...) -#endif - -/* - * A per-port table that indicates how many VBUS overcurrent events have - * occurred. This table is cleared after detecting a physical disconnect of the - * sink. - */ -static uint8_t oc_event_cnt_tbl[CONFIG_USB_PD_PORT_MAX_COUNT]; - -static uint32_t connected_ports; - -/* Simple wrappers to dispatch to the drivers. */ - -int ppc_init(int port) -{ - int rv = EC_ERROR_UNIMPLEMENTED; - const struct ppc_config_t *ppc; - - if ((port < 0) || (port >= ppc_cnt)) { - CPRINTS("%s(%d) Invalid port!", __func__, port); - return EC_ERROR_INVAL; - } - - ppc = &ppc_chips[port]; - if (ppc->drv->init) { - rv = ppc->drv->init(port); - if (rv) - CPRINTS("p%d: PPC init failed! (%d)", port, rv); - else - CPRINTS("p%d: PPC init'd.", port); - } - - return rv; -} - -int ppc_add_oc_event(int port) -{ - if ((port < 0) || (port >= ppc_cnt)) { - CPRINTS("%s(%d) Invalid port!", __func__, port); - return EC_ERROR_INVAL; - } - - oc_event_cnt_tbl[port]++; - - /* The port overcurrented, so don't clear it's OC events. */ - atomic_clear(&connected_ports, 1 << port); - - if (oc_event_cnt_tbl[port] >= PPC_OC_CNT_THRESH) - CPRINTS("C%d: OC event limit reached! " - "Source path disabled until physical disconnect.", - port); - return EC_SUCCESS; -} - -static void clear_oc_tbl(void) -{ - int port; - - for (port = 0; port < ppc_cnt; port++) - /* - * Only clear the table if the port partner is no longer - * attached after debouncing. - */ - if ((!(BIT(port) & connected_ports)) && - oc_event_cnt_tbl[port]) { - oc_event_cnt_tbl[port] = 0; - CPRINTS("C%d: OC events cleared", port); - } -} -DECLARE_DEFERRED(clear_oc_tbl); - -int ppc_clear_oc_event_counter(int port) -{ - if ((port < 0) || (port >= ppc_cnt)) { - CPRINTS("%s(%d) Invalid port!", __func__, port); - return EC_ERROR_INVAL; - } - - /* - * If we are clearing our event table in quick succession, we may be in - * an overcurrent loop where we are also detecting a disconnect on the - * CC pins. Therefore, let's not clear it just yet and the let the - * limit be reached. This way, we won't send the hard reset and - * actually detect the physical disconnect. - */ - if (oc_event_cnt_tbl[port]) { - hook_call_deferred(&clear_oc_tbl_data, - PPC_OC_COOLDOWN_DELAY_US); - } - return EC_SUCCESS; -} - -int ppc_is_sourcing_vbus(int port) -{ - int rv = EC_ERROR_UNIMPLEMENTED; - const struct ppc_config_t *ppc; - - if ((port < 0) || (port >= ppc_cnt)) { - CPRINTS("%s(%d) Invalid port!", __func__, port); - return EC_ERROR_INVAL; - } - - ppc = &ppc_chips[port]; - if (ppc->drv->is_sourcing_vbus) - rv = ppc->drv->is_sourcing_vbus(port); - - return rv; -} - -#ifdef CONFIG_USBC_PPC_POLARITY -int ppc_set_polarity(int port, int polarity) -{ - int rv = EC_ERROR_UNIMPLEMENTED; - const struct ppc_config_t *ppc; - - if ((port < 0) || (port >= ppc_cnt)) { - CPRINTS("%s(%d) Invalid port!", __func__, port); - return EC_ERROR_INVAL; - } - - ppc = &ppc_chips[port]; - if (ppc->drv->set_polarity) - rv = ppc->drv->set_polarity(port, polarity); - - return rv; -} -#endif - -int ppc_set_vbus_source_current_limit(int port, enum tcpc_rp_value rp) -{ - int rv = EC_ERROR_UNIMPLEMENTED; - const struct ppc_config_t *ppc; - - if ((port < 0) || (port >= ppc_cnt)) { - CPRINTS("%s(%d) Invalid port!", __func__, port); - return EC_ERROR_INVAL; - } - - ppc = &ppc_chips[port]; - if (ppc->drv->set_vbus_source_current_limit) - rv = ppc->drv->set_vbus_source_current_limit(port, rp); - - return rv; -} - -int ppc_discharge_vbus(int port, int enable) -{ - int rv = EC_ERROR_UNIMPLEMENTED; - const struct ppc_config_t *ppc; - - if ((port < 0) || (port >= ppc_cnt)) { - CPRINTS("%s(%d) Invalid port!", __func__, port); - return EC_ERROR_INVAL; - } - - ppc = &ppc_chips[port]; - if (ppc->drv->discharge_vbus) - rv = ppc->drv->discharge_vbus(port, enable); - - return rv; -} - -int ppc_is_port_latched_off(int port) -{ - if ((port < 0) || (port >= ppc_cnt)) { - CPRINTS("%s(%d) Invalid port!", __func__, port); - return EC_ERROR_INVAL; - } - - return oc_event_cnt_tbl[port] >= PPC_OC_CNT_THRESH; -} - -#ifdef CONFIG_USBC_PPC_SBU -int ppc_set_sbu(int port, int enable) -{ - int rv = EC_ERROR_UNIMPLEMENTED; - const struct ppc_config_t *ppc; - - if ((port < 0) || (port >= ppc_cnt)) { - CPRINTS("%s(%d) Invalid port!", __func__, port); - return EC_ERROR_INVAL; - } - - ppc = &ppc_chips[port]; - if (ppc->drv->set_sbu) - rv = ppc->drv->set_sbu(port, enable); - - return rv; -} -#endif /* defined(CONFIG_USBC_PPC_SBU) */ - -#ifdef CONFIG_USBC_PPC_VCONN -int ppc_set_vconn(int port, int enable) -{ - int rv = EC_ERROR_UNIMPLEMENTED; - const struct ppc_config_t *ppc; - - if ((port < 0) || (port >= ppc_cnt)) { - CPRINTS("%s(%d) Invalid port!", __func__, port); - return EC_ERROR_INVAL; - } - - /* - * Check our OC event counter. If we've exceeded our threshold, then - * let's latch our source path off to prevent continuous cycling. When - * the PD state machine detects a disconnection on the CC lines, we will - * reset our OC event counter. - */ - if (enable && ppc_is_port_latched_off(port)) - return EC_ERROR_ACCESS_DENIED; - - ppc = &ppc_chips[port]; - if (ppc->drv->set_vconn) - rv = ppc->drv->set_vconn(port, enable); - - return rv; -} -#endif - -void ppc_sink_is_connected(int port, int is_connected) -{ - if ((port < 0) || (port >= ppc_cnt)) { - CPRINTS("%s(%d) Invalid port!", __func__, port); - return; - } - - if (is_connected) - atomic_or(&connected_ports, 1 << port); - else - atomic_clear(&connected_ports, 1 << port); -} - -int ppc_vbus_sink_enable(int port, int enable) -{ - int rv = EC_ERROR_UNIMPLEMENTED; - const struct ppc_config_t *ppc; - - if ((port < 0) || (port >= ppc_cnt)) { - CPRINTS("%s(%d) Invalid port!", __func__, port); - return EC_ERROR_INVAL; - } - - ppc = &ppc_chips[port]; - if (ppc->drv->vbus_sink_enable) - rv = ppc->drv->vbus_sink_enable(port, enable); - - return rv; -} - -int ppc_enter_low_power_mode(int port) -{ - int rv = EC_ERROR_UNIMPLEMENTED; - const struct ppc_config_t *ppc; - - if ((port < 0) || (port >= ppc_cnt)) { - CPRINTS("%s(%d) Invalid port!", __func__, port); - return EC_ERROR_INVAL; - } - - ppc = &ppc_chips[port]; - if (ppc->drv->enter_low_power_mode) - rv = ppc->drv->enter_low_power_mode(port); - - return rv; -} - -int ppc_vbus_source_enable(int port, int enable) -{ - int rv = EC_ERROR_UNIMPLEMENTED; - const struct ppc_config_t *ppc; - - if ((port < 0) || (port >= ppc_cnt)) { - CPRINTS("%s(%d) Invalid port!", __func__, port); - return EC_ERROR_INVAL; - } - - /* - * Check our OC event counter. If we've exceeded our threshold, then - * let's latch our source path off to prevent continuous cycling. When - * the PD state machine detects a disconnection on the CC lines, we will - * reset our OC event counter. - */ - if (enable && ppc_is_port_latched_off(port)) - return EC_ERROR_ACCESS_DENIED; - - ppc = &ppc_chips[port]; - if (ppc->drv->vbus_source_enable) - rv = ppc->drv->vbus_source_enable(port, enable); - - return rv; -} - -#ifdef CONFIG_USB_PD_VBUS_DETECT_PPC -int ppc_is_vbus_present(int port) -{ - int rv = EC_ERROR_UNIMPLEMENTED; - const struct ppc_config_t *ppc; - - if ((port < 0) || (port >= ppc_cnt)) { - CPRINTS("%s(%d) Invalid port!", __func__, port); - return EC_ERROR_INVAL; - } - - ppc = &ppc_chips[port]; - - if (ppc->drv->is_vbus_present) - rv = ppc->drv->is_vbus_present(port); - - return rv; -} -#endif /* defined(CONFIG_USB_PD_VBUS_DETECT_PPC) */ - -#ifdef CONFIG_CMD_PPC_DUMP -static int command_ppc_dump(int argc, char **argv) -{ - int port; - int rv = EC_ERROR_UNIMPLEMENTED; - const struct ppc_config_t *ppc; - - if (argc < 2) - return EC_ERROR_PARAM_COUNT; - - port = atoi(argv[1]); - if ((port < 0) || (port >= ppc_cnt)) { - CPRINTS("%s(%d) Invalid port!", __func__, port); - return EC_ERROR_INVAL; - } - - ppc = &ppc_chips[port]; - if (ppc->drv->reg_dump) - rv = ppc->drv->reg_dump(port); - - return rv; -} -DECLARE_CONSOLE_COMMAND(ppc_dump, command_ppc_dump, "<Type-C port>", - "dump the PPC regs"); -#endif /* defined(CONFIG_CMD_PPC_DUMP) */ |