diff options
-rw-r--r-- | common/usb_pd_host_cmd.c | 33 | ||||
-rw-r--r-- | common/usb_pd_policy.c | 64 | ||||
-rw-r--r-- | common/usbc/usb_pe_drp_sm.c | 67 | ||||
-rw-r--r-- | include/usb_pd.h | 37 |
4 files changed, 119 insertions, 82 deletions
diff --git a/common/usb_pd_host_cmd.c b/common/usb_pd_host_cmd.c index 0a4f756e58..170482e10b 100644 --- a/common/usb_pd_host_cmd.c +++ b/common/usb_pd_host_cmd.c @@ -158,6 +158,39 @@ static enum ec_status hc_remote_pd_discovery(struct host_cmd_handler_args *args) DECLARE_HOST_COMMAND(EC_CMD_USB_PD_DISCOVERY, hc_remote_pd_discovery, EC_VER_MASK(0)); + +static enum ec_status hc_remote_pd_get_amode(struct host_cmd_handler_args *args) +{ + struct svdm_amode_data *modep; + const struct ec_params_usb_pd_get_mode_request *p = args->params; + struct ec_params_usb_pd_get_mode_response *r = args->response; + + if (p->port >= board_get_usb_pd_port_count()) + return EC_RES_INVALID_PARAM; + + /* no more to send */ + if (p->svid_idx >= pd_get_svid_count(p->port)) { + r->svid = 0; + args->response_size = sizeof(r->svid); + return EC_RES_SUCCESS; + } + + r->svid = pd_get_svid(p->port, p->svid_idx); + r->opos = 0; + memcpy(r->vdo, pd_get_mode_vdo(p->port, p->svid_idx), + sizeof(uint32_t) * PDO_MODES); + modep = pd_get_amode_data(p->port, r->svid); + + if (modep) + r->opos = pd_alt_mode(p->port, r->svid); + + args->response_size = sizeof(*r); + return EC_RES_SUCCESS; +} +DECLARE_HOST_COMMAND(EC_CMD_USB_PD_GET_AMODE, + hc_remote_pd_get_amode, + EC_VER_MASK(0)); + #endif /* CONFIG_USB_PD_ALT_MODE_DFP */ #ifdef CONFIG_COMMON_RUNTIME diff --git a/common/usb_pd_policy.c b/common/usb_pd_policy.c index fbe7910442..db878d2ce7 100644 --- a/common/usb_pd_policy.c +++ b/common/usb_pd_policy.c @@ -520,7 +520,7 @@ static int get_mode_idx(int port, uint16_t svid) return -1; } -static struct svdm_amode_data *get_modep(int port, uint16_t svid) +struct svdm_amode_data *pd_get_amode_data(int port, uint16_t svid) { int idx = get_mode_idx(port, svid); @@ -529,7 +529,7 @@ static struct svdm_amode_data *get_modep(int port, uint16_t svid) int pd_alt_mode(int port, uint16_t svid) { - struct svdm_amode_data *modep = get_modep(port, svid); + struct svdm_amode_data *modep = pd_get_amode_data(port, svid); return (modep) ? modep->opos : -1; } @@ -677,7 +677,7 @@ static void dfp_consume_attention(int port, uint32_t *payload) { uint16_t svid = PD_VDO_VID(payload[0]); int opos = PD_VDO_OPOS(payload[0]); - struct svdm_amode_data *modep = get_modep(port, svid); + struct svdm_amode_data *modep = pd_get_amode_data(port, svid); if (!modep || !validate_mode_request(modep, svid, opos)) return; @@ -707,7 +707,8 @@ static void dfp_consume_attention(int port, uint32_t *payload) */ int pd_dfp_dp_get_pin_mode(int port, uint32_t status) { - struct svdm_amode_data *modep = get_modep(port, USB_SID_DISPLAYPORT); + struct svdm_amode_data *modep = + pd_get_amode_data(port, USB_SID_DISPLAYPORT); uint32_t mode_caps; uint32_t pin_caps; if (!modep) @@ -761,7 +762,7 @@ int pd_dfp_exit_mode(int port, uint16_t svid, int opos) * to exit all modes. We currently don't have any UFPs that support * multiple modes on one SVID. */ - modep = get_modep(port, svid); + modep = pd_get_amode_data(port, svid); if (!modep || !validate_mode_request(modep, svid, opos)) return 0; @@ -787,6 +788,21 @@ uint8_t pd_get_product_type(int port) return PD_IDH_PTYPE(pe[port].identity[0]); } +int pd_get_svid_count(int port) +{ + return pe[port].svid_cnt; +} + +uint16_t pd_get_svid(int port, uint16_t svid_idx) +{ + return pe[port].svids[svid_idx].svid; +} + +uint32_t *pd_get_mode_vdo(int port, uint16_t svid_idx) +{ + return pe[port].svids[svid_idx].mode_vdo; +} + #ifdef CONFIG_CMD_USB_PD_PE static void dump_pe(int port) { @@ -825,7 +841,7 @@ static void dump_pe(int port) ccprintf(" [%d] %08x", j + 1, pe[port].svids[i].mode_vdo[j]); ccprintf("\n"); - modep = get_modep(port, pe[port].svids[i].svid); + modep = pd_get_amode_data(port, pe[port].svids[i].svid); if (modep) { mode_caps = modep->data->mode_vdo[modep->opos - 1]; ccprintf("MODE[%d]: svid:%04x caps:%08x\n", modep->opos, @@ -999,7 +1015,7 @@ int pd_svdm(int port, int cnt, uint32_t *payload, uint32_t **rpayload, #ifdef CONFIG_USB_PD_ALT_MODE_DFP struct svdm_amode_data *modep; - modep = get_modep(port, PD_VDO_VID(payload[0])); + modep = pd_get_amode_data(port, PD_VDO_VID(payload[0])); #endif switch (cmd) { #ifdef CONFIG_USB_PD_ALT_MODE_DFP @@ -1318,40 +1334,6 @@ static void pd_usb_billboard_deferred(void) } DECLARE_DEFERRED(pd_usb_billboard_deferred); -#ifdef CONFIG_USB_PD_ALT_MODE_DFP -static enum ec_status hc_remote_pd_get_amode(struct host_cmd_handler_args *args) -{ - struct svdm_amode_data *modep; - const struct ec_params_usb_pd_get_mode_request *p = args->params; - struct ec_params_usb_pd_get_mode_response *r = args->response; - - if (p->port >= board_get_usb_pd_port_count()) - return EC_RES_INVALID_PARAM; - - /* no more to send */ - if (p->svid_idx >= pe[p->port].svid_cnt) { - r->svid = 0; - args->response_size = sizeof(r->svid); - return EC_RES_SUCCESS; - } - - r->svid = pe[p->port].svids[p->svid_idx].svid; - r->opos = 0; - memcpy(r->vdo, pe[p->port].svids[p->svid_idx].mode_vdo, 24); - modep = get_modep(p->port, r->svid); - - if (modep) - r->opos = pd_alt_mode(p->port, r->svid); - - args->response_size = sizeof(*r); - return EC_RES_SUCCESS; -} -DECLARE_HOST_COMMAND(EC_CMD_USB_PD_GET_AMODE, - hc_remote_pd_get_amode, - EC_VER_MASK(0)); - -#endif - #define FW_RW_END (CONFIG_EC_WRITABLE_STORAGE_OFF + \ CONFIG_RW_STORAGE_OFF + CONFIG_RW_SIZE) diff --git a/common/usbc/usb_pe_drp_sm.c b/common/usbc/usb_pe_drp_sm.c index e5208f4269..33c303797c 100644 --- a/common/usbc/usb_pe_drp_sm.c +++ b/common/usbc/usb_pe_drp_sm.c @@ -498,7 +498,6 @@ static void dfp_consume_svids(int port, int cnt, uint32_t *payload); static int dfp_discover_modes(int port, uint32_t *payload); static void dfp_consume_modes(int port, int cnt, uint32_t *payload); static int get_mode_idx(int port, uint16_t svid); -static struct svdm_amode_data *get_modep(int port, uint16_t svid); #endif test_export_static enum usb_pe_state get_state_pe(const int port); @@ -3624,7 +3623,8 @@ static void pe_do_port_discovery_run(int port) { #ifdef CONFIG_USB_PD_ALT_MODE_DFP uint32_t *payload = (uint32_t *)emsg[port].buf; - struct svdm_amode_data *modep = get_modep(port, PD_VDO_VID(payload[0])); + struct svdm_amode_data *modep = + pd_get_amode_data(port, PD_VDO_VID(payload[0])); int ret = 0; if (!PE_CHK_FLAG(port, @@ -3869,7 +3869,7 @@ static void pe_vdm_acked_entry(int port) int cnt = PD_HEADER_CNT(emsg[port].header); struct svdm_amode_data *modep; - modep = get_modep(port, PD_VDO_VID(payload[0])); + modep = pd_get_amode_data(port, PD_VDO_VID(payload[0])); #endif switch (vdo_cmd) { @@ -4721,7 +4721,7 @@ static int get_mode_idx(int port, uint16_t svid) return -1; } -static struct svdm_amode_data *get_modep(int port, uint16_t svid) +struct svdm_amode_data *pd_get_amode_data(int port, uint16_t svid) { int idx = get_mode_idx(port, svid); @@ -4730,7 +4730,7 @@ static struct svdm_amode_data *get_modep(int port, uint16_t svid) int pd_alt_mode(int port, uint16_t svid) { - struct svdm_amode_data *modep = get_modep(port, svid); + struct svdm_amode_data *modep = pd_get_amode_data(port, svid); return (modep) ? modep->opos : -1; } @@ -4830,7 +4830,7 @@ static void dfp_consume_attention(int port, uint32_t *payload) { uint16_t svid = PD_VDO_VID(payload[0]); int opos = PD_VDO_OPOS(payload[0]); - struct svdm_amode_data *modep = get_modep(port, svid); + struct svdm_amode_data *modep = pd_get_amode_data(port, svid); if (!modep || !validate_mode_request(modep, svid, opos)) return; @@ -4860,7 +4860,8 @@ static void dfp_consume_attention(int port, uint32_t *payload) */ int pd_dfp_dp_get_pin_mode(int port, uint32_t status) { - struct svdm_amode_data *modep = get_modep(port, USB_SID_DISPLAYPORT); + struct svdm_amode_data *modep = + pd_get_amode_data(port, USB_SID_DISPLAYPORT); uint32_t mode_caps; uint32_t pin_caps; @@ -4916,7 +4917,7 @@ int pd_dfp_exit_mode(int port, uint16_t svid, int opos) * to exit all modes. We currently don't have any UFPs that support * multiple modes on one SVID. */ - modep = get_modep(port, svid); + modep = pd_get_amode_data(port, svid); if (!modep || !validate_mode_request(modep, svid, opos)) return 0; @@ -4946,6 +4947,21 @@ uint8_t pd_get_product_type(int port) return PD_IDH_PTYPE(pe[port].am_policy.identity[0]); } +int pd_get_svid_count(int port) +{ + return pe[port].am_policy.svid_cnt; +} + +uint16_t pd_get_svid(int port, uint16_t svid_idx) +{ + return pe[port].am_policy.svids[svid_idx].svid; +} + +uint32_t *pd_get_mode_vdo(int port, uint16_t svid_idx) +{ + return pe[port].am_policy.svids[svid_idx].mode_vdo; +} + #ifdef CONFIG_CMD_USB_PD_PE static void dump_pe(int port) { @@ -4988,7 +5004,8 @@ static void dump_pe(int port) ccprintf(" [%d] %08x", j + 1, pe[port].am_policy.svids[i].mode_vdo[j]); ccprintf("\n"); - modep = get_modep(port, pe[port].am_policy.svids[i].svid); + modep = pd_get_amode_data(port, + pe[port].am_policy.svids[i].svid); if (modep) { mode_caps = modep->data->mode_vdo[modep->opos - 1]; ccprintf("MODE[%d]: svid:%04x caps:%08x\n", modep->opos, @@ -5019,38 +5036,6 @@ DECLARE_CONSOLE_COMMAND(pe, command_pe, "<port> dump", "USB PE"); #endif /* CONFIG_CMD_USB_PD_PE */ - -static enum ec_status hc_remote_pd_get_amode(struct host_cmd_handler_args *args) -{ - struct svdm_amode_data *modep; - const struct ec_params_usb_pd_get_mode_request *p = args->params; - struct ec_params_usb_pd_get_mode_response *r = args->response; - - if (p->port >= board_get_usb_pd_port_count()) - return EC_RES_INVALID_PARAM; - - /* no more to send */ - if (p->svid_idx >= pe[p->port].am_policy.svid_cnt) { - r->svid = 0; - args->response_size = sizeof(r->svid); - return EC_RES_SUCCESS; - } - - r->svid = pe[p->port].am_policy.svids[p->svid_idx].svid; - r->opos = 0; - memcpy(r->vdo, pe[p->port].am_policy.svids[p->svid_idx].mode_vdo, 24); - modep = get_modep(p->port, r->svid); - - if (modep) - r->opos = pd_alt_mode(p->port, r->svid); - - args->response_size = sizeof(*r); - return EC_RES_SUCCESS; -} -DECLARE_HOST_COMMAND(EC_CMD_USB_PD_GET_AMODE, - hc_remote_pd_get_amode, - EC_VER_MASK(0)); - #endif /* CONFIG_USB_PD_ALT_MODE_DFP */ static const struct usb_state pe_states[] = { diff --git a/include/usb_pd.h b/include/usb_pd.h index c27310484e..b14cf8b241 100644 --- a/include/usb_pd.h +++ b/include/usb_pd.h @@ -1563,6 +1563,43 @@ uint16_t pd_get_identity_pid(int port); uint8_t pd_get_product_type(int port); /** + * Return the SVID count of port partner connected to a specified port + * + * @param port USB-C port number + * @return SVID count + */ +int pd_get_svid_count(int port); + +/** + * Return the SVID of given SVID index of port partner connected + * to a specified port + * + * @param port USB-C port number + * @param svid_idx SVID Index + * @return SVID + */ +uint16_t pd_get_svid(int port, uint16_t svid_idx); + +/** + * Return the pointer to modes of VDO of port partner connected + * to a specified port + * + * @param port USB-C port number + * @param svid_idx SVID Index + * @return Pointer to modes of VDO + */ +uint32_t *pd_get_mode_vdo(int port, uint16_t svid_idx); + +/** + * Return the alternate mode entry and exit data + * + * @param port USB-C port number + * @param svid SVID + * @return pointer to SVDM mode data + */ +struct svdm_amode_data *pd_get_amode_data(int port, uint16_t svid); + +/** * Returns the status of cable flag - CABLE_FLAGS_SOP_PRIME_ENABLE * * @param port USB-C port number |