pm: power: npcx: add console expired mechanism.

This CL adds support for console expired mechanism. It implements the
notification to power management module that the module for console is
in use. If the interval that module doesn't receive any input message
exceeds CONFIG_SOC_POWER_CONSOLE_EXPIRED_TIMEOUT, the power management
module is allowed to enter deep sleep mode. This mechanism gives a
window in which the users can organize console input.

Signed-off-by: Mulin Chao <mlchao@nuvoton.com>
This commit is contained in:
Mulin Chao 2021-02-25 23:15:58 -08:00 committed by Anas Nashif
commit 105af6f357
4 changed files with 97 additions and 11 deletions

View file

@ -34,6 +34,7 @@ struct uart_npcx_config {
struct uart_npcx_data {
/* Baud rate */
uint32_t baud_rate;
struct miwu_dev_callback uart_rx_cb;
#ifdef CONFIG_UART_INTERRUPT_DRIVEN
uart_irq_callback_user_data_t user_cb;
void *user_data;
@ -209,6 +210,12 @@ static void uart_npcx_isr(const struct device *dev)
{
struct uart_npcx_data *data = DRV_DATA(dev);
/* Refresh console expired time if got UART Rx event */
if (IS_ENABLED(CONFIG_UART_CONSOLE_INPUT_EXPIRED) &&
uart_npcx_irq_rx_ready(dev)) {
npcx_power_console_is_in_use_refresh();
}
if (data->user_cb) {
data->user_cb(dev, data->user_data);
}
@ -285,6 +292,15 @@ static int uart_npcx_err_check(const struct device *dev)
return err;
}
static __unused void uart_npcx_rx_wk_isr(const struct device *dev,
struct npcx_wui *wui)
{
/* Refresh console expired time if got UART Rx wake-up event */
if (IS_ENABLED(CONFIG_UART_CONSOLE_INPUT_EXPIRED)) {
npcx_power_console_is_in_use_refresh();
}
}
/* UART driver registration */
static const struct uart_driver_api uart_npcx_driver_api = {
.poll_in = uart_npcx_poll_in,
@ -311,7 +327,7 @@ static const struct uart_driver_api uart_npcx_driver_api = {
static int uart_npcx_init(const struct device *dev)
{
const struct uart_npcx_config *const config = DRV_CONFIG(dev);
const struct uart_npcx_data *const data = DRV_DATA(dev);
struct uart_npcx_data *const data = DRV_DATA(dev);
struct uart_reg *const inst = HAL_INSTANCE(dev);
const struct device *const clk_dev =
device_get_binding(NPCX_CLK_CTRL_NAME);
@ -366,17 +382,22 @@ static int uart_npcx_init(const struct device *dev)
config->uconf.irq_config_func(dev);
#endif
#if defined(CONFIG_PM)
/*
* Configure the UART wake-up event triggered from a falling edge
* on CR_SIN pin. No need for callback function.
*/
npcx_miwu_interrupt_configure(&config->uart_rx_wui,
NPCX_MIWU_MODE_EDGE, NPCX_MIWU_TRIG_LOW);
if (IS_ENABLED(CONFIG_PM)) {
/* Initialize a miwu device input and its callback function */
npcx_miwu_init_dev_callback(&data->uart_rx_cb,
&config->uart_rx_wui,
uart_npcx_rx_wk_isr, dev);
npcx_miwu_manage_dev_callback(&data->uart_rx_cb, true);
/*
* Configure the UART wake-up event triggered from a falling
* edge on CR_SIN pin. No need for callback function.
*/
npcx_miwu_interrupt_configure(&config->uart_rx_wui,
NPCX_MIWU_MODE_EDGE, NPCX_MIWU_TRIG_LOW);
/* Enable irq of interrupt-input module */
npcx_miwu_irq_enable(&config->uart_rx_wui);
#endif
/* Enable irq of interrupt-input module */
npcx_miwu_irq_enable(&config->uart_rx_wui);
}
/* Configure pin-mux for uart device */
npcx_pinctrl_mux_configure(config->alts_list, config->alts_size, 1);

View file

@ -0,0 +1,43 @@
/*
* Copyright (c) 2021 Nuvoton Technology Corporation.
*
* SPDX-License-Identifier: Apache-2.0
*/
#ifndef _NUVOTON_NPCX_SOC_POWER_H_
#define _NUVOTON_NPCX_SOC_POWER_H_
#ifdef __cplusplus
extern "C" {
#endif
/**
* @brief Receive whether the module for the console is in use.
*
* @return 1 if console is in use. Otherwise
* @return
* - True if the console is in use.
* - False otherwise, the module for console is reday to enter low power mode.
*/
bool npcx_power_console_is_in_use(void);
/**
* @brief Notify the power module that the module for the console is in use.
*
* Notify the power module that the module for the console is in use. It also
* extends expired time by CONFIG_UART_CONSOLE_INPUT_EXPIRED_TIMEOUT.
*/
void npcx_power_console_is_in_use_refresh(void);
/**
* @brief Set expired time-out directly for the console is in use.
*
* @param timeout Expired time-out for the console is in use.
*/
void npcx_power_set_console_in_use_timeout(int64_t timeout);
#ifdef __cplusplus
}
#endif
#endif /* _NUVOTON_NPCX_SOC_POWER_H_ */

View file

@ -82,6 +82,27 @@ enum {
NPCX_STANDARD_WAKE_UP,
};
#ifdef CONFIG_UART_CONSOLE_INPUT_EXPIRED
static int64_t expired_timeout = CONFIG_UART_CONSOLE_INPUT_EXPIRED_TIMEOUT;
static int64_t console_expired_time = CONFIG_UART_CONSOLE_INPUT_EXPIRED_TIMEOUT;
/* Platform specific power control functions */
bool npcx_power_console_is_in_use(void)
{
return (k_uptime_get() < console_expired_time);
}
void npcx_power_console_is_in_use_refresh(void)
{
console_expired_time = k_uptime_get() + expired_timeout;
}
void npcx_power_set_console_in_use_timeout(int64_t timeout)
{
expired_timeout = timeout;
}
#endif
static void npcx_power_enter_system_sleep(int slp_mode, int wk_mode)
{
/* Disable interrupts */

View file

@ -19,5 +19,6 @@
#include <soc_dt.h>
#include <soc_clock.h>
#include <soc_pins.h>
#include <soc_power.h>
#endif /* _NUVOTON_NPCX_SOC_H_ */