summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDaisuke Nojiri <dnojiri@chromium.org>2018-01-25 12:47:33 -0800
committerchrome-bot <chrome-bot@chromium.org>2018-02-03 02:38:10 -0800
commit044cc724967fbb424dd4f686a67abce5a67cfdec (patch)
tree4d57676879db285b665f121d77851d43c0c70a74
parentcd5173dfe0e80ad2ca622e64aeb9d14b82ef494f (diff)
downloadchrome-ec-044cc724967fbb424dd4f686a67abce5a67cfdec.tar.gz
Enable PD communication in RO for external display
This patch makes EC enable PD communication if it's running in manual recovery mode. This is required to show recovery screen on a type-c monitor. This patch also makes EC-EFS ignore power availability. It will make EC verify & jump to RW even if power is sourced by a barrel jack adapter. This should allow depthcharge to show screens (e.g. broken, warning) on a type-c monitor. BUG=b:72387533 BRANCH=none TEST=On Fizz with type-c monitor, verify - Recovery screen is displayed in manual recovery mode. - Critical update screen is displayed in normal mode. - Warning screen is displayed in developer mode. Monitors tested: Dingdong, Dell S2718D Change-Id: Ib53e02d1e5c0f5b2d96d9a02fd33022f92e52b04 Signed-off-by: Daisuke Nojiri <dnojiri@chromium.org> Reviewed-on: https://chromium-review.googlesource.com/898346 Reviewed-by: Randall Spangler <rspangler@chromium.org>
-rw-r--r--board/fizz/board.c7
-rw-r--r--board/fizz/usb_pd_policy.c21
-rw-r--r--common/main.c12
-rw-r--r--common/usb_pd_protocol.c5
-rw-r--r--common/vboot/vboot.c54
-rw-r--r--include/vboot.h12
6 files changed, 57 insertions, 54 deletions
diff --git a/board/fizz/board.c b/board/fizz/board.c
index ee0cd4fe2b..2861ee5fbe 100644
--- a/board/fizz/board.c
+++ b/board/fizz/board.c
@@ -236,9 +236,10 @@ void board_tcpc_init(void)
{
int port, reg;
- /* Only reset TCPC in RO boot. */
- if (!system_jumped_to_this_image())
- board_reset_pd_mcu();
+ /* This needs to be executed only once per boot. It could be run by RO
+ * if we boot in recovery mode. It could be run by RW if we boot in
+ * normal or dev mode. Note EFS makes RO jump to RW before HOOK_INIT. */
+ board_reset_pd_mcu();
/*
* Wake up PS8751. If PS8751 remains in low power mode after sysjump,
diff --git a/board/fizz/usb_pd_policy.c b/board/fizz/usb_pd_policy.c
index e1a0e307af..1d87c7eb75 100644
--- a/board/fizz/usb_pd_policy.c
+++ b/board/fizz/usb_pd_policy.c
@@ -3,7 +3,6 @@
* found in the LICENSE file.
*/
-#include "adc.h"
#include "atomic.h"
#include "extpower.h"
#include "charge_manager.h"
@@ -254,10 +253,9 @@ static int restore_active_charge_port(struct charge_port_info *cpi)
*/
static void board_charge_manager_init(void)
{
- int input_voltage;
- enum charge_port input_port;
- int i, j;
+ enum charge_port port;
struct charge_port_info cpi = { 0 };
+ int i, j;
/* Initialize all charge suppliers to 0 */
for (i = 0; i < CHARGE_PORT_COUNT; i++) {
@@ -265,17 +263,19 @@ static void board_charge_manager_init(void)
charge_manager_update_charge(j, i, &cpi);
}
- input_voltage = adc_read_channel(ADC_VBUS);
- input_port = gpio_get_level(GPIO_ADP_IN_L) ?
+ port = gpio_get_level(GPIO_ADP_IN_L) ?
CHARGE_PORT_TYPEC0 : CHARGE_PORT_BARRELJACK;
- CPRINTS("Power Source: p%d (%dmV)", input_port, input_voltage);
+ CPRINTS("Power source is p%d (%s)", port,
+ port == CHARGE_PORT_TYPEC0 ? "USB-C" : "BJ");
/* Initialize the power source supplier */
- switch (input_port) {
+ switch (port) {
case CHARGE_PORT_TYPEC0:
- typec_set_input_current_limit(input_port, 3000, input_voltage);
+ typec_set_input_current_limit(port, 3000, 5000);
break;
case CHARGE_PORT_BARRELJACK:
+ /* TODO: Once transition from GPIO to CBI completes, get BJ
+ * adapter info locally. No need to save & restore it. */
if (restore_active_charge_port(&cpi)) {
/* Set it to the default. Will be updated by AP. */
CPRINTS("Previous charge info not found. Use default.");
@@ -287,7 +287,8 @@ static void board_charge_manager_init(void)
break;
}
}
-DECLARE_HOOK(HOOK_INIT, board_charge_manager_init, HOOK_PRIO_INIT_ADC + 1);
+DECLARE_HOOK(HOOK_INIT, board_charge_manager_init,
+ HOOK_PRIO_CHARGE_MANAGER_INIT + 1);
static void preserve_active_charge_port(void)
{
diff --git a/common/main.c b/common/main.c
index fe3424b67f..90d4a640c3 100644
--- a/common/main.c
+++ b/common/main.c
@@ -27,6 +27,7 @@
#include "timer.h"
#include "uart.h"
#include "util.h"
+#include "vboot.h"
#include "watchdog.h"
/* Console output macros */
@@ -168,8 +169,15 @@ test_mockable __keep int main(void)
button_init();
#endif /* defined(CONFIG_DEDICATED_RECOVERY_BUTTON | CONFIG_VOLUME_BUTTONS) */
-#if !defined(CONFIG_VBOOT_EFS) && \
- defined(CONFIG_RWSIG) && !defined(HAS_TASK_RWSIG)
+#if defined(CONFIG_VBOOT_EFS)
+ /*
+ * For RO, it behaves as follows:
+ * In recovery, it enables PD communication and returns.
+ * In normal boot, it verifies and jumps to RW.
+ * For RW, it returns immediately.
+ */
+ vboot_main();
+#elif defined(CONFIG_RWSIG) && !defined(HAS_TASK_RWSIG)
/*
* Check the RW firmware signature and jump to it if it is good.
*
diff --git a/common/usb_pd_protocol.c b/common/usb_pd_protocol.c
index c7a7bbe6e9..6d82557c31 100644
--- a/common/usb_pd_protocol.c
+++ b/common/usb_pd_protocol.c
@@ -27,6 +27,7 @@
#include "usbc_ppc.h"
#include "tcpm.h"
#include "version.h"
+#include "vboot.h"
#ifdef CONFIG_COMMON_RUNTIME
#define CPRINTF(format, args...) cprintf(CC_USBPD, format, ## args)
@@ -2010,6 +2011,10 @@ static void pd_init_tasks(void)
/* Disable PD communication at init if we're in RO and locked. */
if (!system_is_in_rw() && system_is_locked())
enable = 0;
+#ifdef CONFIG_VBOOT_EFS
+ if (vboot_need_pd_comm())
+ enable = 1;
+#endif
#endif
for (i = 0; i < CONFIG_USB_PD_PORT_COUNT; i++)
pd_comm_enabled[i] = enable;
diff --git a/common/vboot/vboot.c b/common/vboot/vboot.c
index 47cf1aa10a..b1961ad6f7 100644
--- a/common/vboot/vboot.c
+++ b/common/vboot/vboot.c
@@ -182,33 +182,16 @@ static int is_manual_recovery(void)
return host_is_event_set(EC_HOST_EVENT_KEYBOARD_RECOVERY);
}
-static void vboot_main(void);
-DECLARE_DEFERRED(vboot_main);
-static void vboot_main(void)
-{
- const int check_charge_manager_frequency_usec = 10 * MSEC;
- int port = charge_manager_get_active_charge_port();
-
- if (port == CHARGE_PORT_NONE) {
- /* We loop here until charge manager is ready */
- hook_call_deferred(&vboot_main_data,
- check_charge_manager_frequency_usec);
- return;
- }
+static int pd_comm_enabled;
- CPRINTS("Checking power");
+int vboot_need_pd_comm(void)
+{
+ return pd_comm_enabled;
+}
- if (system_can_boot_ap()) {
- /*
- * We are here for the two cases:
- * 1. Booting on RO with a barrel jack adapter. We can continue
- * to boot AP with EC-RO. We'll jump later in softsync.
- * 2. Booting on RW with a type-c charger. PD negotiation is
- * done and we can boot AP.
- */
- CPRINTS("Got enough power");
- return;
- }
+void vboot_main(void)
+{
+ CPRINTS("Main");
if (system_is_in_rw() || !system_is_locked()) {
/*
@@ -217,23 +200,18 @@ static void vboot_main(void)
* or unlocked RO.
*
* This could be caused by a weak type-c charger. If that's
- * the case, users need to plug a better charger. We could
- * also be here because PD negotiation is still taking place.
- * If so, we'll briefly show request power sign but it will
- * be immediately corrected.
+ * the case, users need to plug a better charger.
*
- * We can also get here because we called system_can_boot_ap too
- * early. Power will be requested but it should be cancelled by
- * board_set_charge_limit as soon as a PD contract is made.
+ * We could also be here because PD negotiation is still taking
+ * place. If so, we'll end up showing request power signal but
+ * it will be immediately corrected.
*/
request_power();
return;
}
- CPRINTS("Booting RO on weak battery/charger");
-
if (is_manual_recovery()) {
- CPRINTS("Manual recovery requested");
+ CPRINTS("Manual recovery");
if (battery_is_present() || has_matrix_keyboard()) {
request_power();
return;
@@ -243,8 +221,8 @@ static void vboot_main(void)
* hole by allowing EC-RO to do PD negotiation but attackers
* don't gain meaningful advantage on devices without a matrix
* keyboard */
- CPRINTS("Enable C%d PD comm", port);
- pd_comm_enable(port, 1);
+ CPRINTS("Enable PD comm");
+ pd_comm_enabled = 1;
return;
}
@@ -264,5 +242,3 @@ static void vboot_main(void)
/* Failed to jump. Need recovery. */
request_recovery();
}
-
-DECLARE_HOOK(HOOK_INIT, vboot_main, HOOK_PRIO_DEFAULT);
diff --git a/include/vboot.h b/include/vboot.h
index b9f03c6423..d757d0a3e7 100644
--- a/include/vboot.h
+++ b/include/vboot.h
@@ -46,3 +46,15 @@ int vboot_is_padding_valid(const uint8_t *data, uint32_t start, uint32_t end);
*/
int vboot_verify(const uint8_t *data, int len,
const struct rsa_public_key *key, const uint8_t *sig);
+
+/**
+ * Entry point of EC EFS
+ */
+void vboot_main(void);
+
+/**
+ * Get if vboot requires PD comm to be enabled or not
+ *
+ * @return 1: need PD communication. 0: PD communication is not needed.
+ */
+int vboot_need_pd_comm(void);