| /* Copyright 2012 The Chromium OS Authors. All rights reserved. |
| * Use of this source code is governed by a BSD-style license that can be |
| * found in the LICENSE file. |
| */ |
| |
| /* |
| * Chipset module for Chrome EC. |
| * |
| * This is intended to be a platform/chipset-neutral interface, implemented by |
| * all main chipsets (x86, gaia, etc.). |
| */ |
| |
| #ifndef __CROS_EC_CHIPSET_H |
| #define __CROS_EC_CHIPSET_H |
| |
| #include "common.h" |
| #include "compile_time_macros.h" |
| #include "ec_commands.h" |
| #include "gpio.h" |
| #include "stddef.h" |
| |
| /* |
| * Chipset state mask |
| * |
| * Note that this is a non-exhaustive list of states which the main chipset can |
| * be in, and is potentially one-to-many for real, underlying chipset states. |
| * That's why chipset_in_state() asks "Is the chipset in something |
| * approximating this state?" and not "Tell me what state the chipset is in and |
| * I'll compare it myself with the state(s) I want." |
| */ |
| enum chipset_state_mask { |
| CHIPSET_STATE_HARD_OFF = 0x01, /* Hard off (G3) */ |
| CHIPSET_STATE_SOFT_OFF = 0x02, /* Soft off (S5) */ |
| CHIPSET_STATE_SUSPEND = 0x04, /* Suspend (S3) */ |
| CHIPSET_STATE_ON = 0x08, /* On (S0) */ |
| CHIPSET_STATE_STANDBY = 0x10, /* Standby (S0ix) */ |
| /* Common combinations */ |
| CHIPSET_STATE_ANY_OFF = (CHIPSET_STATE_HARD_OFF | |
| CHIPSET_STATE_SOFT_OFF), /* Any off state */ |
| /* This combination covers any kind of suspend i.e. S3 or S0ix. */ |
| CHIPSET_STATE_ANY_SUSPEND = (CHIPSET_STATE_SUSPEND | |
| CHIPSET_STATE_STANDBY), |
| }; |
| |
| /* |
| * Reason codes used by the AP after a shutdown to figure out why it was reset |
| * by the EC. These are sent in EC commands. Therefore, to maintain protocol |
| * compatibility: |
| * - New entries must be inserted prior to the _COUNT field |
| * - If an existing entry is no longer in service, it must be replaced with a |
| * RESERVED entry instead. |
| * - The semantic meaning of an entry should not change. |
| * - Do not exceed 2^15 - 1 for reset reasons or 2^16 - 1 for shutdown reasons. |
| */ |
| enum chipset_reset_reason { |
| CHIPSET_RESET_BEGIN = 0, |
| CHIPSET_RESET_UNKNOWN = CHIPSET_RESET_BEGIN, |
| /* Custom reason defined by a board.c or baseboard.c file */ |
| CHIPSET_RESET_BOARD_CUSTOM, |
| /* Believe that the AP has hung */ |
| CHIPSET_RESET_HANG_REBOOT, |
| /* Reset by EC console command */ |
| CHIPSET_RESET_CONSOLE_CMD, |
| /* Reset by EC host command */ |
| CHIPSET_RESET_HOST_CMD, |
| /* Keyboard module reset key combination */ |
| CHIPSET_RESET_KB_SYSRESET, |
| /* Keyboard module warm reboot */ |
| CHIPSET_RESET_KB_WARM_REBOOT, |
| /* Debug module warm reboot */ |
| CHIPSET_RESET_DBG_WARM_REBOOT, |
| /* I cannot self-terminate. You must lower me into the steel. */ |
| CHIPSET_RESET_AP_REQ, |
| /* Reset as side-effect of startup sequence */ |
| CHIPSET_RESET_INIT, |
| /* EC detected an AP watchdog event. */ |
| CHIPSET_RESET_AP_WATCHDOG, |
| CHIPSET_RESET_COUNT, |
| }; |
| |
| /* |
| * Hard shutdowns are logged on the same path as resets. |
| */ |
| enum chipset_shutdown_reason { |
| CHIPSET_SHUTDOWN_BEGIN = BIT(15), |
| CHIPSET_SHUTDOWN_POWERFAIL = CHIPSET_SHUTDOWN_BEGIN, |
| /* Forcing a shutdown as part of EC initialization */ |
| CHIPSET_SHUTDOWN_INIT, |
| /* Custom reason on a per-board basis. */ |
| CHIPSET_SHUTDOWN_BOARD_CUSTOM, |
| /* This is a reason to inhibit startup, not cause shut down. */ |
| CHIPSET_SHUTDOWN_BATTERY_INHIBIT, |
| /* A power_wait_signal is being asserted */ |
| CHIPSET_SHUTDOWN_WAIT, |
| /* Critical battery level. */ |
| CHIPSET_SHUTDOWN_BATTERY_CRIT, |
| /* Because you told me to. */ |
| CHIPSET_SHUTDOWN_CONSOLE_CMD, |
| /* Forcing a shutdown to effect entry to G3. */ |
| CHIPSET_SHUTDOWN_G3, |
| /* Force shutdown due to over-temperature. */ |
| CHIPSET_SHUTDOWN_THERMAL, |
| /* Force a chipset shutdown from the power button through EC */ |
| CHIPSET_SHUTDOWN_BUTTON, |
| |
| CHIPSET_SHUTDOWN_COUNT, |
| }; |
| |
| enum critical_shutdown { |
| CRITICAL_SHUTDOWN_IGNORE, |
| CRITICAL_SHUTDOWN_HIBERNATE, |
| CRITICAL_SHUTDOWN_CUTOFF, |
| }; |
| |
| #ifdef HAS_TASK_CHIPSET |
| |
| /** |
| * Check if chipset is in a given state. |
| * |
| * @param state_mask Combination of one or more CHIPSET_STATE_* flags. |
| * |
| * @return non-zero if the chipset is in one of the states specified in the |
| * mask. |
| */ |
| int chipset_in_state(int state_mask); |
| |
| /** |
| * Check if chipset is in a given state or if the chipset task is currently |
| * transitioning to that state. For example, G3S5, S5, and S3S5 would all count |
| * as the S5 state. |
| * |
| * @param state_mask Combination of one or more CHIPSET_STATE_* flags. |
| * |
| * @return non-zero if the chipset is in one of the states specified in the |
| * mask. |
| */ |
| int chipset_in_or_transitioning_to_state(int state_mask); |
| |
| /** |
| * Ask the chipset to exit the hard off state. |
| * |
| * Does nothing if the chipset has already left the state, or was not in the |
| * state to begin with. |
| */ |
| void chipset_exit_hard_off(void); |
| |
| /* This is a private chipset-specific implementation for use only by |
| * throttle_ap() . Don't call this directly! |
| */ |
| void chipset_throttle_cpu(int throttle); |
| |
| /** |
| * Immediately shut off power to main processor and chipset. |
| * |
| * This is intended for use when the system is too hot or battery power is |
| * critical. |
| */ |
| void chipset_force_shutdown(enum chipset_shutdown_reason reason); |
| |
| /** |
| * Reset the CPU and/or chipset. |
| */ |
| void chipset_reset(enum chipset_reset_reason reason); |
| |
| /** |
| * Interrupt handler to power GPIO inputs. |
| */ |
| void power_interrupt(enum gpio_signal signal); |
| |
| /** |
| * Handle assert of eSPI_Reset# pin. |
| */ |
| void chipset_handle_espi_reset_assert(void); |
| |
| /** |
| * Perform chipset pre-initialization work within the context of chipset task. |
| */ |
| void chipset_pre_init_callback(void); |
| |
| /** |
| * Initialize reset logs and next reset log. |
| */ |
| void init_reset_log(void); |
| |
| #else /* !HAS_TASK_CHIPSET */ |
| |
| /* When no chipset is present, assume it is always off. */ |
| static inline int chipset_in_state(int state_mask) |
| { |
| return state_mask & CHIPSET_STATE_ANY_OFF; |
| } |
| |
| static inline int chipset_in_or_transitioning_to_state(int state_mask) |
| { |
| return state_mask & CHIPSET_STATE_ANY_OFF; |
| } |
| |
| static inline void chipset_exit_hard_off(void) { } |
| static inline void chipset_throttle_cpu(int throttle) { } |
| static inline void chipset_force_shutdown(enum chipset_shutdown_reason reason) |
| { |
| } |
| |
| static inline void chipset_reset(enum chipset_reset_reason reason) { } |
| static inline void power_interrupt(enum gpio_signal signal) { } |
| static inline void chipset_handle_espi_reset_assert(void) { } |
| static inline void chipset_handle_reboot(void) { } |
| static inline void chipset_reset_request_interrupt(enum gpio_signal signal) { } |
| static inline void chipset_warm_reset_interrupt(enum gpio_signal signal) { } |
| static inline void chipset_ap_rst_interrupt(enum gpio_signal signal) { } |
| static inline void chipset_power_good_interrupt(enum gpio_signal signal) { } |
| static inline void chipset_watchdog_interrupt(enum gpio_signal signal) { } |
| |
| static inline void init_reset_log(void) { } |
| |
| #endif /* !HAS_TASK_CHIPSET */ |
| |
| /** |
| * Optional chipset check if PLTRST# is valid. |
| * |
| * @return non-zero if PLTRST# is valid, 0 if invalid. |
| */ |
| int chipset_pltrst_is_valid(void) __attribute__((weak)); |
| |
| /** |
| * Execute chipset-specific reboot. |
| */ |
| void chipset_handle_reboot(void); |
| |
| /** |
| * GPIO interrupt handler of reset request from AP. |
| * |
| * It is used in SDM845/MT8183 chipset power sequence. |
| */ |
| void chipset_reset_request_interrupt(enum gpio_signal signal); |
| |
| /** |
| * GPIO interrupt handler of AP_RST_L signal from PMIC. |
| * PMIC uses this signal to notify AP reset. |
| * |
| * It is used in Qualcomm chipset power sequence. |
| */ |
| void chipset_ap_rst_interrupt(enum gpio_signal signal); |
| |
| /** |
| * GPIO interrupt handler of warm reset signal from servo or H1. |
| * |
| * It is used in Qualcomm chipset power sequence. |
| */ |
| void chipset_warm_reset_interrupt(enum gpio_signal signal); |
| |
| /** |
| * GPIO interrupt handler of the power good signal (pull rail of warm reset). |
| * |
| * It is used in Qualcomm chipset power sequence. |
| */ |
| void chipset_power_good_interrupt(enum gpio_signal signal); |
| |
| /** |
| * GPIO interrupt handler of watchdog from AP. |
| * |
| * It is used in MT8183 chipset, where it must be setup to trigger on falling |
| * edge only. |
| */ |
| void chipset_watchdog_interrupt(enum gpio_signal signal); |
| |
| /** |
| * Callback which allows board to take custom action on G3 timer expiration |
| * |
| * @param last_shutdown_time Last shutdown time |
| * @param target Expiration time. Can be modified by board. |
| * @param now Current time |
| * @return Action to take |
| */ |
| __override_proto enum critical_shutdown board_system_is_idle( |
| uint64_t last_shutdown_time, uint64_t *target, uint64_t now); |
| |
| #ifdef CONFIG_CMD_AP_RESET_LOG |
| |
| /** |
| * Report that the AP is being reset to the reset log. |
| */ |
| void report_ap_reset(enum chipset_shutdown_reason reason); |
| |
| /** |
| * Get statistics about AP resets. |
| * |
| * @param reset_log_entries Pointer to array of log entries. |
| * @param num_reset_log_entries Number of items in reset_log_entries. |
| * @param resets_since_ec_boot Number of AP resets since EC boot. |
| */ |
| test_mockable enum ec_error_list |
| get_ap_reset_stats(struct ap_reset_log_entry *reset_log_entries, |
| size_t num_reset_log_entries, |
| uint32_t *resets_since_ec_boot); |
| |
| #else |
| |
| static inline void report_ap_reset(enum chipset_shutdown_reason reason) { } |
| |
| test_mockable_static_inline enum ec_error_list |
| get_ap_reset_stats(struct ap_reset_log_entry *reset_log_entries, |
| size_t num_reset_log_entries, uint32_t *resets_since_ec_boot) |
| { |
| return EC_SUCCESS; |
| } |
| |
| #endif /* !CONFIG_CMD_AP_RESET_LOG */ |
| |
| #endif /* __CROS_EC_CHIPSET_H */ |