336 lines
12 KiB
C
336 lines
12 KiB
C
/*
|
|
* Copyright 2019-2021 NXP
|
|
* All rights reserved.
|
|
*
|
|
*
|
|
* SPDX-License-Identifier: BSD-3-Clause
|
|
*/
|
|
|
|
#include "fsl_gpc.h"
|
|
|
|
/*******************************************************************************
|
|
* Definitions
|
|
******************************************************************************/
|
|
|
|
/* Component ID definition, used by tools. */
|
|
#ifndef FSL_COMPONENT_ID
|
|
#define FSL_COMPONENT_ID "platform.drivers.gpc_3"
|
|
#endif
|
|
|
|
/*******************************************************************************
|
|
* Variables
|
|
******************************************************************************/
|
|
/*! @brief GPC submodule step registers offset */
|
|
static uint32_t const s_cmRegOffset[] = GPC_CM_STEP_REG_OFFSET;
|
|
|
|
static uint32_t const s_spRegOffset[] = GPC_SP_STEP_REG_OFFSET;
|
|
|
|
static uint32_t const s_stbyRegOffset[] = GPC_STBY_STEP_REG_OFFSET;
|
|
|
|
/*******************************************************************************
|
|
* Code
|
|
******************************************************************************/
|
|
|
|
/*!
|
|
* brief Enable IRQ wakeup request.
|
|
*
|
|
* This function enables the IRQ request which can wakeup the CPU platform.
|
|
*
|
|
* param base GPC CPU module base address.
|
|
* param irqId ID of the IRQ, accessible range is 0-255.
|
|
* param enable Enable the IRQ request or not.
|
|
*/
|
|
void GPC_CM_EnableIrqWakeup(GPC_CPU_MODE_CTRL_Type *base, uint32_t irqId, bool enable)
|
|
{
|
|
assert(irqId < (GPC_CPU_MODE_CTRL_CM_IRQ_WAKEUP_MASK_COUNT * 32UL));
|
|
|
|
uint32_t irqGroup = irqId / 32UL;
|
|
uint32_t irqMask = irqId % 32UL;
|
|
|
|
if (true == enable)
|
|
{
|
|
base->CM_IRQ_WAKEUP_MASK[irqGroup] &= ~(1UL << irqMask);
|
|
}
|
|
else
|
|
{
|
|
base->CM_IRQ_WAKEUP_MASK[irqGroup] |= (1UL << irqMask);
|
|
}
|
|
}
|
|
|
|
/*!
|
|
* brief Get the status of the IRQ wakeup request.
|
|
*
|
|
* param base GPC CPU module base address.
|
|
* param irqId ID of the IRQ, accessible range is 0-255.
|
|
* return Indicate the IRQ request is asserted or not.
|
|
*/
|
|
bool GPC_CM_GetIrqWakeupStatus(GPC_CPU_MODE_CTRL_Type *base, uint32_t irqId)
|
|
{
|
|
assert(irqId < (GPC_CPU_MODE_CTRL_CM_IRQ_WAKEUP_MASK_COUNT * 32UL));
|
|
|
|
uint32_t irqGroup = irqId / 32UL;
|
|
uint32_t irqMask = irqId % 32UL;
|
|
bool irqStatus = false;
|
|
|
|
irqStatus = (((base->CM_IRQ_WAKEUP_STAT[irqGroup] >> irqMask) & 0x1UL) == 0x1UL) ? true : false;
|
|
return irqStatus;
|
|
}
|
|
|
|
/*!
|
|
* brief Config the cpu mode transition step.
|
|
*
|
|
* note This function can not config the setpoint sleep/wakeup operation for those
|
|
* operation is controlled by setpoint control. This funcion can not config the standby
|
|
* sleep/wakeup too, because those operation is controlled by standby controlled.
|
|
*
|
|
* param base GPC CPU module base address.
|
|
* param step step type, refer to "gpc_cm_tran_step_t".
|
|
* param config transition step configuration, refer to "gpc_tran_step_config_t".
|
|
*/
|
|
void GPC_CM_ConfigCpuModeTransitionStep(GPC_CPU_MODE_CTRL_Type *base,
|
|
gpc_cm_tran_step_t step,
|
|
const gpc_tran_step_config_t *config)
|
|
{
|
|
if (!((step >= kGPC_CM_SleepSP) && (step <= kGPC_CM_WakeupSP)))
|
|
{
|
|
uint32_t tmp32 = *(uint32_t *)((uint32_t)base + s_cmRegOffset[step]);
|
|
|
|
if (config->enableStep)
|
|
{
|
|
tmp32 &= ~(GPC_CPU_MODE_CTRL_CM_SLEEP_SSAR_CTRL_STEP_CNT_MASK |
|
|
GPC_CPU_MODE_CTRL_CM_SLEEP_SSAR_CTRL_CNT_MODE_MASK);
|
|
tmp32 |= GPC_CPU_MODE_CTRL_CM_SLEEP_SSAR_CTRL_CNT_MODE(config->cntMode);
|
|
if (config->cntMode != kGPC_StepCounterDisableMode)
|
|
{
|
|
tmp32 |= GPC_CPU_MODE_CTRL_CM_SLEEP_SSAR_CTRL_STEP_CNT(config->stepCount);
|
|
}
|
|
tmp32 &= ~GPC_CPU_MODE_CTRL_CM_SLEEP_SSAR_CTRL_DISABLE_MASK;
|
|
}
|
|
else
|
|
{
|
|
tmp32 |= GPC_CPU_MODE_CTRL_CM_SLEEP_SSAR_CTRL_DISABLE_MASK;
|
|
}
|
|
*(uint32_t *)((uint32_t)base + s_cmRegOffset[step]) = tmp32;
|
|
}
|
|
}
|
|
|
|
/*!
|
|
* brief Request a set point transition before the CPU transfers into a sleep mode.
|
|
*
|
|
* This function triggers the set point transition during a CPU Sleep/wakeup event and selects which one the CMC want
|
|
* to transfer to.
|
|
*
|
|
* param base GPC CPU module base address.
|
|
* param setPointSleep The set point CPU want the system to transit to on next CPU platform sleep sequence.
|
|
* param setPointWakeup The set point CPU want the system to transit to on next CPU platform wakeup sequence.
|
|
* param wakeupSel Select the set point transition on the next CPU platform wakeup sequence.
|
|
*/
|
|
void GPC_CM_RequestSleepModeSetPointTransition(GPC_CPU_MODE_CTRL_Type *base,
|
|
uint8_t setPointSleep,
|
|
uint8_t setPointWakeup,
|
|
gpc_cm_wakeup_sp_sel_t wakeupSel)
|
|
{
|
|
uint32_t tmp32 = base->CM_SP_CTRL;
|
|
|
|
tmp32 &= ~(GPC_CPU_MODE_CTRL_CM_SP_CTRL_CPU_SP_RUN_EN_MASK | GPC_CPU_MODE_CTRL_CM_SP_CTRL_CPU_SP_SLEEP_MASK |
|
|
GPC_CPU_MODE_CTRL_CM_SP_CTRL_CPU_SP_WAKEUP_MASK | GPC_CPU_MODE_CTRL_CM_SP_CTRL_CPU_SP_WAKEUP_SEL_MASK);
|
|
/* Config set point transition in the next sleep sequence. */
|
|
tmp32 |=
|
|
GPC_CPU_MODE_CTRL_CM_SP_CTRL_CPU_SP_SLEEP_EN_MASK | GPC_CPU_MODE_CTRL_CM_SP_CTRL_CPU_SP_SLEEP(setPointSleep);
|
|
/* Config set point transition in the next wakeup sequence. */
|
|
tmp32 |= GPC_CPU_MODE_CTRL_CM_SP_CTRL_CPU_SP_WAKEUP_EN_MASK |
|
|
GPC_CPU_MODE_CTRL_CM_SP_CTRL_CPU_SP_WAKEUP(setPointWakeup) |
|
|
GPC_CPU_MODE_CTRL_CM_SP_CTRL_CPU_SP_WAKEUP_SEL(wakeupSel);
|
|
|
|
base->CM_SP_CTRL = tmp32;
|
|
}
|
|
|
|
/*!
|
|
* brief Request a set point transition during run mode.
|
|
*
|
|
* This function triggers the set point transition and selects which one the CMC want to transfer to.
|
|
*
|
|
* param base GPC CPU module base address.
|
|
* param setPointRun The set point CPU want the system to transit in the run mode.
|
|
*/
|
|
void GPC_CM_RequestRunModeSetPointTransition(GPC_CPU_MODE_CTRL_Type *base, uint8_t setPointRun)
|
|
{
|
|
uint32_t tmp32 = base->CM_SP_CTRL;
|
|
|
|
tmp32 &= ~(GPC_CPU_MODE_CTRL_CM_SP_CTRL_CPU_SP_RUN_MASK);
|
|
tmp32 |= GPC_CPU_MODE_CTRL_CM_SP_CTRL_CPU_SP_RUN_EN_MASK | GPC_CPU_MODE_CTRL_CM_SP_CTRL_CPU_SP_RUN(setPointRun);
|
|
|
|
base->CM_SP_CTRL = tmp32;
|
|
while ((base->CM_SP_CTRL & GPC_CPU_MODE_CTRL_CM_SP_CTRL_CPU_SP_RUN_EN_MASK) != 0UL)
|
|
{
|
|
}
|
|
}
|
|
|
|
/*
|
|
* brief Set the set point mapping value for each cpu mode.
|
|
*
|
|
* This function configures which set point is allowed when CPU enters RUN/WAIT/STOP/SUSPEND. If there are multiple
|
|
* setpoints, use:
|
|
* code
|
|
* map = kkGPC_SetPoint0 | kGPC_SetPoint1 | ... | kGPC_SetPoint15;
|
|
* encode
|
|
*
|
|
* param base GPC CPU module base address.
|
|
* param mode CPU mode. Refer to "gpc_cpu_mode_t".
|
|
* param map Map value of the set point. Refer to "_gpc_setpoint_map".
|
|
*/
|
|
void GPC_CM_SetCpuModeSetPointMapping(GPC_CPU_MODE_CTRL_Type *base, gpc_cpu_mode_t mode, uint32_t map)
|
|
{
|
|
/* Ensure the allowed set point is in the accessible range (0-15). */
|
|
map = map & 0xFFFFUL;
|
|
|
|
switch (mode)
|
|
{
|
|
case kGPC_RunMode:
|
|
base->CM_RUN_MODE_MAPPING = map;
|
|
break;
|
|
case kGPC_WaitMode:
|
|
base->CM_WAIT_MODE_MAPPING = map;
|
|
break;
|
|
case kGPC_StopMode:
|
|
base->CM_STOP_MODE_MAPPING = map;
|
|
break;
|
|
case kGPC_SuspendMode:
|
|
base->CM_SUSPEND_MODE_MAPPING = map;
|
|
break;
|
|
default:
|
|
assert(false);
|
|
break;
|
|
}
|
|
}
|
|
|
|
/*
|
|
* brief Request the chip into standby mode.
|
|
*
|
|
* param base GPC CPU module base address.
|
|
* param mode CPU mode. Refer to "gpc_cpu_mode_t".
|
|
*/
|
|
void GPC_CM_RequestStandbyMode(GPC_CPU_MODE_CTRL_Type *base, const gpc_cpu_mode_t mode)
|
|
{
|
|
assert(mode != kGPC_RunMode);
|
|
|
|
switch (mode)
|
|
{
|
|
case kGPC_WaitMode:
|
|
base->CM_STBY_CTRL |= GPC_CPU_MODE_CTRL_CM_STBY_CTRL_STBY_WAIT_MASK;
|
|
break;
|
|
case kGPC_StopMode:
|
|
base->CM_STBY_CTRL |= GPC_CPU_MODE_CTRL_CM_STBY_CTRL_STBY_STOP_MASK;
|
|
break;
|
|
case kGPC_SuspendMode:
|
|
base->CM_STBY_CTRL |= GPC_CPU_MODE_CTRL_CM_STBY_CTRL_STBY_SUSPEND_MASK;
|
|
break;
|
|
default:
|
|
/* This branch should never be hit. */
|
|
break;
|
|
}
|
|
}
|
|
|
|
/*
|
|
* brief Clear the standby mode request.
|
|
*
|
|
* param base GPC CPU module base address.
|
|
* param mode CPU mode. Refer to "gpc_cpu_mode_t".
|
|
*/
|
|
void GPC_CM_ClearStandbyModeRequest(GPC_CPU_MODE_CTRL_Type *base, const gpc_cpu_mode_t mode)
|
|
{
|
|
assert(mode != kGPC_RunMode);
|
|
|
|
switch (mode)
|
|
{
|
|
case kGPC_WaitMode:
|
|
base->CM_STBY_CTRL &= ~GPC_CPU_MODE_CTRL_CM_STBY_CTRL_STBY_WAIT_MASK;
|
|
break;
|
|
case kGPC_StopMode:
|
|
base->CM_STBY_CTRL &= ~GPC_CPU_MODE_CTRL_CM_STBY_CTRL_STBY_STOP_MASK;
|
|
break;
|
|
case kGPC_SuspendMode:
|
|
base->CM_STBY_CTRL &= ~GPC_CPU_MODE_CTRL_CM_STBY_CTRL_STBY_SUSPEND_MASK;
|
|
break;
|
|
default:
|
|
/* This branch should never be hit. */
|
|
break;
|
|
}
|
|
}
|
|
|
|
/*!
|
|
* brief Clears CPU module interrut status flags.
|
|
*
|
|
* param base GPC CPU module base address.
|
|
* param mask The interrupt status flags to be cleared. Should be the OR'ed value of _gpc_cm_interrupt_status_flag.
|
|
*/
|
|
void GPC_CM_ClearInterruptStatusFlags(GPC_CPU_MODE_CTRL_Type *base, uint32_t mask)
|
|
{
|
|
uint32_t temp32;
|
|
|
|
temp32 = base->CM_INT_CTRL;
|
|
temp32 &= ~(GPC_CM_ALL_INTERRUPT_STATUS);
|
|
base->CM_INT_CTRL = (mask | temp32);
|
|
}
|
|
|
|
/*!
|
|
* brief Config the set point transition step.
|
|
*
|
|
* param base GPC Setpoint controller base address.
|
|
* param step step type, refer to "gpc_sp_tran_step_t".
|
|
* param config transition step configuration, refer to "gpc_tran_step_config_t".
|
|
*/
|
|
void GPC_SP_ConfigSetPointTransitionStep(GPC_SET_POINT_CTRL_Type *base,
|
|
gpc_sp_tran_step_t step,
|
|
const gpc_tran_step_config_t *config)
|
|
{
|
|
uint32_t tmp32 = *(uint32_t *)((uint32_t)base + s_spRegOffset[step]);
|
|
|
|
if (config->enableStep)
|
|
{
|
|
tmp32 &=
|
|
~(GPC_SET_POINT_CTRL_SP_SSAR_SAVE_CTRL_STEP_CNT_MASK | GPC_SET_POINT_CTRL_SP_SSAR_SAVE_CTRL_CNT_MODE_MASK);
|
|
tmp32 |= GPC_SET_POINT_CTRL_SP_SSAR_SAVE_CTRL_CNT_MODE(config->cntMode);
|
|
if (config->cntMode != kGPC_StepCounterDisableMode)
|
|
{
|
|
tmp32 |= GPC_SET_POINT_CTRL_SP_SSAR_SAVE_CTRL_STEP_CNT(config->stepCount);
|
|
}
|
|
tmp32 &= ~GPC_SET_POINT_CTRL_SP_SSAR_SAVE_CTRL_DISABLE_MASK;
|
|
}
|
|
else
|
|
{
|
|
tmp32 |= GPC_SET_POINT_CTRL_SP_SSAR_SAVE_CTRL_DISABLE_MASK;
|
|
}
|
|
*(uint32_t *)((uint32_t)base + s_spRegOffset[step]) = tmp32;
|
|
}
|
|
|
|
/*!
|
|
* brief Config the standby transition step.
|
|
*
|
|
* param base GPC Setpoint controller base address.
|
|
* param step step type, refer to "gpc_stby_tran_step_t".
|
|
* param config transition step configuration, refer to "gpc_tran_step_config_t".
|
|
*/
|
|
void GPC_STBY_ConfigStandbyTransitionStep(GPC_STBY_CTRL_Type *base,
|
|
gpc_stby_tran_step_t step,
|
|
const gpc_tran_step_config_t *config)
|
|
{
|
|
uint32_t tmp32 = *(uint32_t *)((uint32_t)base + s_stbyRegOffset[step]);
|
|
|
|
if (config->enableStep)
|
|
{
|
|
tmp32 &= ~(GPC_STBY_CTRL_STBY_LPCG_IN_CTRL_STEP_CNT_MASK | GPC_STBY_CTRL_STBY_LPCG_IN_CTRL_CNT_MODE_MASK);
|
|
tmp32 |= GPC_STBY_CTRL_STBY_LPCG_IN_CTRL_CNT_MODE(config->cntMode);
|
|
if (config->cntMode != kGPC_StepCounterDisableMode)
|
|
{
|
|
tmp32 |= GPC_STBY_CTRL_STBY_LPCG_IN_CTRL_STEP_CNT(config->stepCount);
|
|
}
|
|
tmp32 &= ~GPC_STBY_CTRL_STBY_LPCG_IN_CTRL_DISABLE_MASK;
|
|
}
|
|
else
|
|
{
|
|
tmp32 |= GPC_STBY_CTRL_STBY_LPCG_IN_CTRL_DISABLE_MASK;
|
|
}
|
|
*(uint32_t *)((uint32_t)base + s_stbyRegOffset[step]) = tmp32;
|
|
}
|