diff options
Diffstat (limited to 'board/reef/usb_pd_policy.c')
-rw-r--r-- | board/reef/usb_pd_policy.c | 53 |
1 files changed, 45 insertions, 8 deletions
diff --git a/board/reef/usb_pd_policy.c b/board/reef/usb_pd_policy.c index 693bd6e2e4..bc530687bd 100644 --- a/board/reef/usb_pd_policy.c +++ b/board/reef/usb_pd_policy.c @@ -21,6 +21,7 @@ #include "util.h" #include "usb_mux.h" #include "usb_pd.h" +#include "usb_pd_tcpm.h" #define CPRINTF(format, args...) cprintf(CC_USBPD, format, ## args) #define CPRINTS(format, args...) cprints(CC_USBPD, format, ## args) @@ -33,6 +34,10 @@ const uint32_t pd_src_pdo[] = { PDO_FIXED(5000, 1500, PDO_FIXED_FLAGS), }; const int pd_src_pdo_cnt = ARRAY_SIZE(pd_src_pdo); +const uint32_t pd_src_pdo_max[] = { + PDO_FIXED(5000, 3000, PDO_FIXED_FLAGS), +}; +const int pd_src_pdo_max_cnt = ARRAY_SIZE(pd_src_pdo_max); const uint32_t pd_snk_pdo[] = { PDO_FIXED(5000, 500, PDO_FIXED_FLAGS), @@ -51,9 +56,37 @@ void pd_transition_voltage(int idx) /* No-operation: we are always 5V */ } +static uint8_t vbus_en[CONFIG_USB_PD_PORT_COUNT]; +static uint8_t vbus_rp[CONFIG_USB_PD_PORT_COUNT] = {TYPEC_RP_1A5, TYPEC_RP_1A5}; + int board_vbus_source_enabled(int port) { - return gpio_get_level(port ? GPIO_USB_C1_5V_EN : GPIO_USB_C0_5V_EN); + return vbus_en[port]; +} + +static void board_vbus_update_source_current(int port) +{ + enum gpio_signal gpio = port ? GPIO_USB_C1_5V_EN : GPIO_USB_C0_5V_EN; + int flags = (vbus_rp[port] == TYPEC_RP_1A5 && vbus_en[port]) ? + (GPIO_INPUT | GPIO_PULL_UP) : (GPIO_OUTPUT | GPIO_PULL_UP); + + /* + * Driving USB_Cx_5V_EN high, actually put a 16.5k resistance + * (2x 33k in parallel) on the NX5P3290 load switch ILIM pin, + * setting a minimum OCP current of 3186 mA. + * Putting an internal pull-up on USB_Cx_5V_EN, effectively put a 33k + * resistor on ILIM, setting a minimum OCP current of 1505 mA. + */ + gpio_set_level(gpio, vbus_en[port]); + gpio_set_flags(gpio, flags); +} + +void typec_set_source_current_limit(int port, int rp) +{ + vbus_rp[port] = rp; + + /* change the GPIO driving the load switch if needed */ + board_vbus_update_source_current(port); } int pd_set_power_supply_ready(int port) @@ -61,11 +94,13 @@ int pd_set_power_supply_ready(int port) /* Ensure we're not charging from this port */ bd9995x_select_input_port(bd9995x_pd_port_to_chg_port(port), 0); - /* Provide VBUS */ - gpio_set_level(port ? GPIO_USB_C1_5V_EN : - GPIO_USB_C0_5V_EN, 1); + /* Ensure we advertise the proper available current quota */ + charge_manager_source_port(port, 1); pd_set_vbus_discharge(port, 0); + /* Provide VBUS */ + vbus_en[port] = 1; + board_vbus_update_source_current(port); /* notify host of power info change */ pd_send_host_event(PD_EVENT_POWER_CHANGE); @@ -75,19 +110,21 @@ int pd_set_power_supply_ready(int port) void pd_power_supply_reset(int port) { - enum gpio_signal gpio; int prev_en; - gpio = port ? GPIO_USB_C1_5V_EN : GPIO_USB_C0_5V_EN; - prev_en = gpio_get_level(gpio); + prev_en = vbus_en[port]; /* Disable VBUS */ - gpio_set_level(gpio, 0); + vbus_en[port] = 0; + board_vbus_update_source_current(port); /* Enable discharge if we were previously sourcing 5V */ if (prev_en) pd_set_vbus_discharge(port, 1); + /* Give back the current quota we are no longer using */ + charge_manager_source_port(port, 0); + /* notify host of power info change */ pd_send_host_event(PD_EVENT_POWER_CHANGE); } |