diff options
author | Tom Hughes <tomhughes@chromium.org> | 2022-09-21 14:10:01 -0700 |
---|---|---|
committer | Tom Hughes <tomhughes@chromium.org> | 2022-09-22 12:49:33 -0700 |
commit | 2bcf863b492fe7ed8105c853814dba6ed32ba719 (patch) | |
tree | fcf6ce5810f9ff9e3c8cce434812dd75492269ed /board/gaelin/led.c | |
parent | e5fb0b9ba488614b5684e640530f00821ab7b943 (diff) | |
parent | 28712dae9d7ed1e694f7622cc083afa71090d4d5 (diff) | |
download | chrome-ec-firmware-fpmcu-bloonchipper-release.tar.gz |
Merge remote-tracking branch cros/main into firmware-fpmcu-bloonchipper-releasefirmware-fpmcu-bloonchipper-release
Generated by: ./util/update_release_branch.py --board bloonchipper
--relevant_paths_file ./util/fingerprint-relevant-paths.txt firmware-
fpmcu-bloonchipper-release
Relevant changes:
git log --oneline e5fb0b9ba4..28712dae9d -- board/hatch_fp
board/bloonchipper common/fpsensor docs/fingerprint driver/fingerprint
util/getversion.sh
ded9307b79 util/getversion.sh: Fix version when not in a git repo
956055e692 board: change Google USB vendor info
71b2ef709d Update license boilerplate text in source code files
33e11afda0 Revert "fpsensor: Build fpsensor source file with C++"
c8d0360723 fpsensor: Build fpsensor source file with C++
bc113abd53 fpsensor: Fix g++ compiler error
150a58a0dc fpsensor: Fix fp_set_sensor_mode return type
b33b5ce85b fpsensor: Remove nested designators for C++ compatibility
2e864b2539 tree-wide: const-ify argv for console commands
56d8b360f9 test: Add test for get ikm failure when seed not set
3a3d6c3690 test: Add test for fpsensor trivial key failure
233e6bbd08 fpsensor_crypto: Abstract calls to hmac_SHA256
0a041b285b docs/fingerprint: Typo correction
c03fab67e2 docs/fingerprint: Fix the path of fputils.py
0b5d4baf5a util/getversion.sh: Fix empty file list handling
6e128fe760 FPMCU dev board environment with Satlab
3eb29b6aa5 builtin: Move ssize_t to sys/types.h
345d62ebd1 docs/fingerprint: Update power numbers for latest dartmonkey release
c25ffdb316 common: Conditionally support printf %l and %i modifiers
9a3c514b45 test: Add a test to check if the debugger is connected
54e603413f Move standard library tests to their own file
43fa6b4bf8 docs/fingerprint: Update power numbers for latest bloonchipper release
25536f9a84 driver/fingerprint/fpc/bep/fpc_sensor_spi.c: Format with clang-format
4face99efd driver/fingerprint/fpc/libfp/fpc_sensor_pal.h: Format with clang-format
738de2b575 trng: Rename rand to trng_rand
14b8270edd docs/fingerprint: Update dragonclaw power numbers
0b268f93d1 driver/fingerprint/fpc/libfp/fpc_private.c: Format with clang-format
f80da163f2 driver/fingerprint/fpc/libfp/fpc_private.h: Format with clang-format
5e9c85c9b1 driver/fingerprint/fpc/libfp/fpc_sensor_pal.c: Format with clang-format
c1f9dd3cf8 driver/fingerprint/fpc/libfp/fpc_bio_algorithm.h: Format with clang-format
eb1e1bed8d driver/fingerprint/fpc/libfp/fpc1145_private.h: Format with clang-format
6e7b611821 driver/fingerprint/fpc/bep/fpc_bio_algorithm.h: Format with clang-format
e0589cd5e2 driver/fingerprint/fpc/bep/fpc1035_private.h: Format with clang-format
7905e556a0 common/fpsensor/fpsensor_crypto.c: Format with clang-format
21289d170c driver/fingerprint/fpc/bep/fpc1025_private.h: Format with clang-format
98a20f937e common/fpsensor/fpsensor_state.c: Format with clang-format
a2d255d8af common/fpsensor/fpsensor.c: Format with clang-format
73055eeb3f driver/fingerprint/fpc/bep/fpc_private.c: Format with clang-format
0f7b5cb509 common/fpsensor/fpsensor_private.h: Format with clang-format
1ceade6e65 driver/fingerprint/fpc/bep/fpc_private.h: Format with clang-format
dc3e9008b8 board/hatch_fp/board.h: Format with clang-format
dca9d74321 Revert "trng: Rename rand to trng_rand"
a6b0b3554f trng: Rename rand to trng_rand
28d0b75b70 third_party/boringssl: Remove unused header
BRANCH=None
BUG=b:246424843 b:234181908 b:244781166 b:234181908 b:244387210
BUG=b:242720240 chromium:1098010 b:180945056 b:236025198 b:234181908
BUG=b:234181908 b:237344361 b:131913998 b:236386294 b:234143158
BUG=b:234781655 b:215613183 b:242720910
TEST=`make -j buildall`
TEST=./test/run_device_tests.py --board bloonchipper
Test "aes": PASSED
Test "cec": PASSED
Test "cortexm_fpu": PASSED
Test "crc": PASSED
Test "flash_physical": PASSED
Test "flash_write_protect": PASSED
Test "fpsensor_hw": PASSED
Test "fpsensor_spi_ro": PASSED
Test "fpsensor_spi_rw": PASSED
Test "fpsensor_uart_ro": PASSED
Test "fpsensor_uart_rw": PASSED
Test "mpu_ro": PASSED
Test "mpu_rw": PASSED
Test "mutex": PASSED
Test "pingpong": PASSED
Test "printf": PASSED
Test "queue": PASSED
Test "rollback_region0": PASSED
Test "rollback_region1": PASSED
Test "rollback_entropy": PASSED
Test "rtc": PASSED
Test "sha256": PASSED
Test "sha256_unrolled": PASSED
Test "static_if": PASSED
Test "stdlib": PASSED
Test "system_is_locked_wp_on": PASSED
Test "system_is_locked_wp_off": PASSED
Test "timer_dos": PASSED
Test "utils": PASSED
Test "utils_str": PASSED
Test "stm32f_rtc": PASSED
Test "panic_data_bloonchipper_v2.0.4277": PASSED
Test "panic_data_bloonchipper_v2.0.5938": PASSED
Force-Relevant-Builds: all
Signed-off-by: Tom Hughes <tomhughes@chromium.org>
Change-Id: I264ad0ffe7afcd507a1e483c6e934a9c4fea47c3
Diffstat (limited to 'board/gaelin/led.c')
-rw-r--r-- | board/gaelin/led.c | 260 |
1 files changed, 260 insertions, 0 deletions
diff --git a/board/gaelin/led.c b/board/gaelin/led.c new file mode 100644 index 0000000000..842cee0530 --- /dev/null +++ b/board/gaelin/led.c @@ -0,0 +1,260 @@ +/* Copyright 2022 The ChromiumOS Authors + * Use of this source code is governed by a BSD-style license that can be + * found in the LICENSE file. + * + * Power LED control for Brask. + * Solid green - active power + * Green flashing - suspended + * Red flashing - alert + * Solid red - critical + */ + +#include "chipset.h" +#include "console.h" +#include "ec_commands.h" +#include "gpio.h" +#include "hooks.h" +#include "led_common.h" +#include "pwm.h" +#include "timer.h" +#include "util.h" + +#define CPRINTS(format, args...) cprints(CC_GPIO, format, ##args) + +/* + * Due to the CSME-Lite processing, upon startup the CPU transitions through + * S0->S3->S5->S3->S0, causing the LED to turn on/off/on, so + * delay turning off the LED during suspend/shutdown. + */ +#define LED_CPU_DELAY_MS (2000 * MSEC) + +const enum ec_led_id supported_led_ids[] = { EC_LED_ID_POWER_LED }; +const int supported_led_ids_count = ARRAY_SIZE(supported_led_ids); + +enum led_color { + LED_OFF = 0, + LED_RED, + LED_GREEN, + + /* Number of colors, not a color itself */ + LED_COLOR_COUNT +}; + +static int set_color_power(enum led_color color, int duty) +{ + int green = 0; + int red = 0; + + if (duty < 0 || 100 < duty) + return EC_ERROR_UNKNOWN; + + switch (color) { + case LED_OFF: + break; + case LED_GREEN: + green = 1; + break; + case LED_RED: + red = 1; + break; + default: + return EC_ERROR_UNKNOWN; + } + + if (red) + pwm_set_duty(PWM_CH_LED_RED, duty); + else + pwm_set_duty(PWM_CH_LED_RED, 0); + + if (green) + pwm_set_duty(PWM_CH_LED_GREEN, duty); + else + pwm_set_duty(PWM_CH_LED_GREEN, 0); + + return EC_SUCCESS; +} + +static int set_color(enum ec_led_id id, enum led_color color, int duty) +{ + switch (id) { + case EC_LED_ID_POWER_LED: + return set_color_power(color, duty); + default: + return EC_ERROR_UNKNOWN; + } +} + +#define LED_PULSE_US (2 * SECOND) +/* 40 msec for nice and smooth transition. */ +#define LED_PULSE_TICK_US (40 * MSEC) + +/* + * When pulsing is enabled, brightness is incremented by <duty_inc> every + * <interval> usec from 0 to 100% in LED_PULSE_US usec. Then it's decremented + * likewise in LED_PULSE_US usec. + */ +static struct { + uint32_t interval; + int duty_inc; + enum led_color color; + int duty; +} led_pulse; + +#define CONFIG_TICK(interval, color) \ + config_tick((interval), 100 / (LED_PULSE_US / (interval)), (color)) + +static void config_tick(uint32_t interval, int duty_inc, enum led_color color) +{ + led_pulse.interval = interval; + led_pulse.duty_inc = duty_inc; + led_pulse.color = color; + led_pulse.duty = 0; +} + +static void pulse_power_led(enum led_color color) +{ + set_color(EC_LED_ID_POWER_LED, color, led_pulse.duty); + if (led_pulse.duty + led_pulse.duty_inc > 100) + led_pulse.duty_inc = led_pulse.duty_inc * -1; + else if (led_pulse.duty + led_pulse.duty_inc < 0) + led_pulse.duty_inc = led_pulse.duty_inc * -1; + led_pulse.duty += led_pulse.duty_inc; +} + +static void led_tick(void); +DECLARE_DEFERRED(led_tick); +static void led_tick(void) +{ + uint32_t elapsed; + uint32_t next = 0; + uint32_t start = get_time().le.lo; + + if (led_auto_control_is_enabled(EC_LED_ID_POWER_LED)) + pulse_power_led(led_pulse.color); + elapsed = get_time().le.lo - start; + next = led_pulse.interval > elapsed ? led_pulse.interval - elapsed : 0; + hook_call_deferred(&led_tick_data, next); +} + +static void led_suspend(void) +{ + CONFIG_TICK(LED_PULSE_TICK_US, LED_GREEN); + led_tick(); +} +DECLARE_DEFERRED(led_suspend); + +static void led_shutdown(void) +{ + if (led_auto_control_is_enabled(EC_LED_ID_POWER_LED)) + set_color(EC_LED_ID_POWER_LED, LED_OFF, 0); +} +DECLARE_DEFERRED(led_shutdown); + +static void led_shutdown_hook(void) +{ + hook_call_deferred(&led_tick_data, -1); + hook_call_deferred(&led_suspend_data, -1); + hook_call_deferred(&led_shutdown_data, LED_CPU_DELAY_MS); +} +DECLARE_HOOK(HOOK_CHIPSET_SHUTDOWN, led_shutdown_hook, HOOK_PRIO_DEFAULT); + +static void led_suspend_hook(void) +{ + hook_call_deferred(&led_shutdown_data, -1); + hook_call_deferred(&led_suspend_data, LED_CPU_DELAY_MS); +} +DECLARE_HOOK(HOOK_CHIPSET_SUSPEND, led_suspend_hook, HOOK_PRIO_DEFAULT); + +static void led_resume(void) +{ + /* + * Assume there is no race condition with led_tick, which also + * runs in hook_task. + */ + hook_call_deferred(&led_tick_data, -1); + /* + * Avoid invoking the suspend/shutdown delayed hooks. + */ + hook_call_deferred(&led_suspend_data, -1); + hook_call_deferred(&led_shutdown_data, -1); + if (led_auto_control_is_enabled(EC_LED_ID_POWER_LED)) + set_color(EC_LED_ID_POWER_LED, LED_GREEN, 100); +} +DECLARE_HOOK(HOOK_CHIPSET_RESUME, led_resume, HOOK_PRIO_DEFAULT); + +void led_alert(int enable) +{ + if (enable) { + /* Overwrite the current signal */ + config_tick(1 * SECOND, 100, LED_RED); + led_tick(); + } else { + /* Restore the previous signal */ + if (chipset_in_state(CHIPSET_STATE_ON)) + led_resume(); + else if (chipset_in_state(CHIPSET_STATE_SUSPEND)) + led_suspend_hook(); + else if (chipset_in_state(CHIPSET_STATE_ANY_OFF)) + led_shutdown_hook(); + } +} + +void show_critical_error(void) +{ + hook_call_deferred(&led_tick_data, -1); + if (led_auto_control_is_enabled(EC_LED_ID_POWER_LED)) + set_color(EC_LED_ID_POWER_LED, LED_RED, 100); +} + +static int command_led(int argc, const char **argv) +{ + enum ec_led_id id = EC_LED_ID_POWER_LED; + + if (argc < 2) + return EC_ERROR_PARAM_COUNT; + + if (!strcasecmp(argv[1], "debug")) { + led_auto_control(id, !led_auto_control_is_enabled(id)); + ccprintf("o%s\n", led_auto_control_is_enabled(id) ? "ff" : "n"); + } else if (!strcasecmp(argv[1], "off")) { + set_color(id, LED_OFF, 0); + } else if (!strcasecmp(argv[1], "red")) { + set_color(id, LED_RED, 100); + } else if (!strcasecmp(argv[1], "green")) { + set_color(id, LED_GREEN, 100); + } else if (!strcasecmp(argv[1], "alert")) { + led_alert(1); + } else if (!strcasecmp(argv[1], "crit")) { + show_critical_error(); + } else { + return EC_ERROR_PARAM1; + } + return EC_SUCCESS; +} +DECLARE_CONSOLE_COMMAND(led, command_led, "[debug|red|green|off|alert|crit]", + "Turn on/off LED."); + +void led_get_brightness_range(enum ec_led_id led_id, uint8_t *brightness_range) +{ + brightness_range[EC_LED_COLOR_RED] = 100; + brightness_range[EC_LED_COLOR_GREEN] = 100; +} + +int led_set_brightness(enum ec_led_id id, const uint8_t *brightness) +{ + if (brightness[EC_LED_COLOR_RED]) + return set_color(id, LED_RED, brightness[EC_LED_COLOR_RED]); + else if (brightness[EC_LED_COLOR_GREEN]) + return set_color(id, LED_GREEN, brightness[EC_LED_COLOR_GREEN]); + else + return set_color(id, LED_OFF, 0); +} +void board_set_charge_limit(int port, int supplier, int charge_ma, int max_ma, + int charge_mv) +{ + /* Blink alert if insufficient power per system_can_boot_ap(). */ + int insufficient_power = + (charge_ma * charge_mv) < + (CONFIG_CHARGER_MIN_POWER_MW_FOR_POWER_ON * 1000); + led_alert(insufficient_power); +} |