summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAlec Berg <alecaberg@chromium.org>2014-12-15 16:03:36 -0800
committerchrome-internal-fetch <chrome-internal-fetch@google.com>2014-12-16 20:30:07 +0000
commitcf2883afe0ee144029582b62c005c79217905bf3 (patch)
tree6c5f48b9605fa44c0b369d5151571e7c98c582b8
parent2666ce13c96779b5b2977b365ef33e85c3868863 (diff)
downloadchrome-ec-cf2883afe0ee144029582b62c005c79217905bf3.tar.gz
samus: change backboosting workaround into a new task
Change backboosting workaround into a new extpower task. This new task runs exactly what used to be run in a deferred function, but at higher priority than charger task, which means that i2c transactions from this new task will occur before charger task i2c transactions. This fixes the EC watchdog when writing PD device firmware because the hooks task is no longer blocked on trying to grab the i2c mutex for talking to BQ. BUG=chrome-os-partner:33905 BRANCH=samus TEST=loaded onto samus and tested remote update of zinger 10 times. Change-Id: I01d259857aefc6bf456ab217bf46536237bc4008 Signed-off-by: Alec Berg <alecaberg@chromium.org> Reviewed-on: https://chromium-review.googlesource.com/235862 Reviewed-by: Vincent Palatin <vpalatin@chromium.org>
-rw-r--r--board/samus/ec.tasklist1
-rw-r--r--board/samus/extpower.c97
2 files changed, 59 insertions, 39 deletions
diff --git a/board/samus/ec.tasklist b/board/samus/ec.tasklist
index f59ca73403..815da6dbb9 100644
--- a/board/samus/ec.tasklist
+++ b/board/samus/ec.tasklist
@@ -21,6 +21,7 @@
TASK_NOTEST(ALS, als_task, NULL, TASK_STACK_SIZE) \
TASK_NOTEST(LIGHTBAR, lightbar_task, NULL, LARGER_TASK_STACK_SIZE) \
TASK_ALWAYS(CHARGER, charger_task, NULL, LARGER_TASK_STACK_SIZE) \
+ TASK_ALWAYS(EXTPOWER, extpower_task, NULL, SMALLER_TASK_STACK_SIZE) \
TASK_NOTEST(MOTIONSENSE, motion_sense_task, NULL, LARGER_TASK_STACK_SIZE) \
TASK_NOTEST(CHIPSET, chipset_task, NULL, TASK_STACK_SIZE) \
TASK_NOTEST(KEYPROTO, keyboard_protocol_task, NULL, TASK_STACK_SIZE) \
diff --git a/board/samus/extpower.c b/board/samus/extpower.c
index 9262c06d17..d8269efba2 100644
--- a/board/samus/extpower.c
+++ b/board/samus/extpower.c
@@ -15,47 +15,13 @@
#include "gpio.h"
#include "hooks.h"
#include "host_command.h"
+#include "task.h"
int extpower_is_present(void)
{
return gpio_get_level(GPIO_AC_PRESENT);
}
-/**
- * Deferred function to handle external power change
- */
-static void extpower_deferred(void)
-{
- static int extpower_prev;
- int extpower = extpower_is_present();
-
- if (extpower && !extpower_prev) {
- charger_discharge_on_ac(0);
- /* If in G3, enable PP5000 for accurate sensing of CC */
- if (chipset_in_state(CHIPSET_STATE_HARD_OFF))
- gpio_set_level(GPIO_PP5000_EN, 1);
- } else if (extpower && extpower_prev) {
- /* glitch on AC_PRESENT, attempt to recover from backboost */
- charger_discharge_on_ac(1);
- charger_discharge_on_ac(0);
- } else {
- charger_discharge_on_ac(1);
- /* If in G3, make sure PP5000 is off when no AC */
- if (chipset_in_state(CHIPSET_STATE_HARD_OFF))
- gpio_set_level(GPIO_PP5000_EN, 0);
- }
- extpower_prev = extpower;
-
- hook_notify(HOOK_AC_CHANGE);
-
- /* Forward notification to host */
- if (extpower)
- host_set_single_event(EC_HOST_EVENT_AC_CONNECTED);
- else
- host_set_single_event(EC_HOST_EVENT_AC_DISCONNECTED);
-}
-DECLARE_DEFERRED(extpower_deferred);
-
static void extpower_buffer_to_pch(void)
{
if (chipset_in_state(CHIPSET_STATE_HARD_OFF)) {
@@ -79,17 +45,70 @@ void extpower_interrupt(enum gpio_signal signal)
{
extpower_buffer_to_pch();
- /* Trigger deferred notification of external power change */
- hook_call_deferred(extpower_deferred, 0);
+ /* Trigger notification of external power change */
+ task_wake(TASK_ID_EXTPOWER);
}
static void extpower_init(void)
{
extpower_buffer_to_pch();
- hook_call_deferred(extpower_deferred, 0);
-
/* Enable interrupts, now that we've initialized */
gpio_enable_interrupt(GPIO_AC_PRESENT);
}
DECLARE_HOOK(HOOK_INIT, extpower_init, HOOK_PRIO_DEFAULT);
+
+static void extpower_board_hacks(int extpower)
+{
+ static int extpower_prev;
+
+ /*
+ * Use discharge_on_ac() to workaround hardware backboosting
+ * charge circuit problems.
+ *
+ * When in G3, PP5000 needs to be enabled to accurately sense
+ * CC voltage when AC is attached. When AC is disconnceted
+ * it needs to be off to save power.
+ */
+ if (extpower && !extpower_prev) {
+ charger_discharge_on_ac(0);
+ if (chipset_in_state(CHIPSET_STATE_HARD_OFF))
+ gpio_set_level(GPIO_PP5000_EN, 1);
+ } else if (extpower && extpower_prev) {
+ /* Glitch on AC_PRESENT, attempt to recover from backboost */
+ charger_discharge_on_ac(1);
+ charger_discharge_on_ac(0);
+ } else {
+ charger_discharge_on_ac(1);
+ if (chipset_in_state(CHIPSET_STATE_HARD_OFF))
+ gpio_set_level(GPIO_PP5000_EN, 0);
+ }
+ extpower_prev = extpower;
+}
+
+/**
+ * Task to handle external power change
+ */
+void extpower_task(void)
+{
+ int extpower = extpower_is_present();
+ extpower_board_hacks(extpower);
+
+ while (1) {
+ /* Wait until next extpower interrupt */
+ task_wait_event(-1);
+
+ extpower = extpower_is_present();
+
+ /* Various board hacks to run on extpower change */
+ extpower_board_hacks(extpower);
+
+ hook_notify(HOOK_AC_CHANGE);
+
+ /* Forward notification to host */
+ if (extpower)
+ host_set_single_event(EC_HOST_EVENT_AC_CONNECTED);
+ else
+ host_set_single_event(EC_HOST_EVENT_AC_DISCONNECTED);
+ }
+}