PMUFW: PM: Adjusting PM function return values to use XStatus type

-Using int type for returns
-Error statuses are common Xilinx XST_* codes
-Additional power management status errors are defined in pm_defs.h

Signed-off-by: Mirela Simonovic <mirela.simonovic@aggios.com>
Signed-off-by: Davorin Mista <davorin.mista@aggios.com>
Acked-by: Jyotheeswar Reddy Mutthareddyvari <jyothee@xilinx.com>
Signed-off-by: Sören Brinkmann <soren.brinkmann@xilinx.com>
This commit is contained in:
Davorin Mista 2015-05-28 09:28:11 -07:00 committed by Nava kishore Manne
parent 8703e57a32
commit a25049cb0d
16 changed files with 354 additions and 300 deletions

View file

@ -67,6 +67,13 @@ void XPfw_PmInit(void)
* @apiId PM API id that was read from master's IPI buffer and validated as
* existing
*
* @return Status of the processing IPI
* - XST_INVALID_PARAM if isrMask parameter has invalid value
* - XST_SUCCESS otherwise
* - Note that if request is processed, firmware is not receiving any
* status of processing information. Processing status is returned to
* the master which initiated communication through IPI.
*
* @note Call from IPI#0 interrupt routine. IPI's #0 interrupt can be used
* for some other purposes, not only for PM, and in #0 interrupt
* routine must :
@ -79,9 +86,10 @@ void XPfw_PmInit(void)
* be cleared after this function returns to make PM API call
* atomic.
*/
void XPfw_PmIpiHandler(const u32 isrMask,
const u32 apiId)
int XPfw_PmIpiHandler(const u32 isrMask,
const u32 apiId)
{
int status = XST_SUCCESS;
u32 i;
u32 payload[PAYLOAD_ELEM_CNT];
u32 bufferBase;
@ -91,6 +99,7 @@ void XPfw_PmIpiHandler(const u32 isrMask,
if (NULL == master) {
/* Never happens if IPI interrupt routine is implemented correctly */
PmDbg("ERROR: IPI source not supported %d\n", isrMask);
status = XST_INVALID_PARAM;
goto done;
}
@ -105,7 +114,7 @@ void XPfw_PmIpiHandler(const u32 isrMask,
PmProcessRequest(master, payload);
done:
return;
return status;
}
/**
@ -115,17 +124,20 @@ done:
* @note Call from GPI2 interrupt routine to process sleep request. Must not
* clear GPI2 interrupt before this function returns.
*/
void XPfw_PmWfiHandler(const u32 srcMask)
int XPfw_PmWfiHandler(const u32 srcMask)
{
int status;
PmProc *proc = PmGetProcByWfiStatus(srcMask);
if (NULL == proc) {
PmDbg("ERROR: Unknown processor %d\n", srcMask);
status = XST_INVALID_PARAM;
goto done;
}
PmProcFsm(proc, PM_PROC_EVENT_SLEEP);
if ((true == proc->isPrimary) && (true == IS_OFF(&proc->node))) {
status = PmProcFsm(proc, PM_PROC_EVENT_SLEEP);
if ((XST_SUCCESS == status) && (true == proc->isPrimary) &&
(true == IS_OFF(&proc->node))) {
/*
* We've just powered down a primary processor, now use opportunistic
* suspend to power down its parent(s)
@ -134,7 +146,7 @@ void XPfw_PmWfiHandler(const u32 srcMask)
}
done:
return;
return status;
}
/**
@ -153,21 +165,21 @@ done:
* slave it is determined which processor should be woken-up (always
* wake the primary processor, owner of the master channel).
*/
u32 XPfw_PmWakeHandler(const u32 srcMask)
int XPfw_PmWakeHandler(const u32 srcMask)
{
u32 status = PM_RET_SUCCESS;
int status = XST_SUCCESS;
if (PMU_IOMODULE_GPI1_GIC_WAKES_ALL_MASK & srcMask) {
/* Processor GIC wake */
PmProc* proc = PmGetProcByWakeStatus(srcMask);
if (NULL != proc) {
PmProcFsm(proc, PM_PROC_EVENT_WAKE);
status = PmProcFsm(proc, PM_PROC_EVENT_WAKE);
} else {
status = PM_RET_ERROR_PROC;
status = XST_INVALID_PARAM;
}
} else {
/* Slave wake */
PmSlaveProcessWake(srcMask);
status = PmSlaveProcessWake(srcMask);
}
return status;
@ -188,7 +200,7 @@ u32 XPfw_PmWakeHandler(const u32 srcMask)
XPfw_PmIpiStatus XPfw_PmCheckIpiRequest(const u32 isrVal,
u32* const apiId)
{
u32 status;
XPfw_PmIpiStatus status;
bool isValid;
const PmMaster *master = PmGetMasterByIpiMask(isrVal);

View file

@ -36,6 +36,7 @@
#define PM_BINDING_H_
#include "xil_types.h"
#include "xstatus.h"
/*********************************************************************
* Enum definitions
@ -57,12 +58,12 @@ void XPfw_PmInit(void);
XPfw_PmIpiStatus XPfw_PmCheckIpiRequest(const u32 isrVal, u32* const apiId);
/* Call from IPI interrupt routine to handle PM API request */
void XPfw_PmIpiHandler(const u32 isrMask, const u32 apiId);
int XPfw_PmIpiHandler(const u32 isrMask, const u32 apiId);
/* Call from GPI2 interrupt routine to handle processor sleep request */
void XPfw_PmWfiHandler(const u32 srcMask);
int XPfw_PmWfiHandler(const u32 srcMask);
/* Call from GPI1 interrupt routine to handle wake request */
u32 XPfw_PmWakeHandler(const u32 srcMask);
int XPfw_PmWakeHandler(const u32 srcMask);
#endif

View file

@ -55,15 +55,16 @@ static void PmProcessAckRequest(const u32 ack,
const u32 status,
const u32 oppoint)
{
if (status != PM_RET_SUCCESS) {
#ifdef DEBUG_PM
if (status != XST_SUCCESS) {
PmDbg("ERROR PM operation failed - code %d\n", status);
}
#endif
if (REQUEST_ACK_BLOCKING == ack) {
/* Return status immediately */
XPfw_Write32(master->buffer + IPI_BUFFER_RESP_OFFSET, status);
} else if ((REQUEST_ACK_CB_STANDARD == ack) ||
((REQUEST_ACK_CB_ERROR == ack) && (PM_RET_SUCCESS != status))) {
((REQUEST_ACK_CB_ERROR == ack) && (XST_SUCCESS != status))) {
/* Return acknowledge through callback */
PmAcknowledgeCb(master, nodeId, status, oppoint);
} else {
@ -87,6 +88,7 @@ static void PmSelfSuspend(const PmMaster *const master,
const u32 latency,
const u32 state)
{
int status;
/* the node ID must refer to a processor belonging to this master */
PmProc* proc = PmGetProcOfThisMaster(master, node);
@ -95,13 +97,14 @@ static void PmSelfSuspend(const PmMaster *const master,
if (NULL == proc) {
PmDbg("ERROR node ID %s(=%d) does not refer to a processor of "
"this master channel\n", PmStrNode(node), node);
status = XST_INVALID_PARAM;
goto done;
}
PmProcFsm(proc, PM_PROC_EVENT_SELF_SUSPEND);
status = PmProcFsm(proc, PM_PROC_EVENT_SELF_SUSPEND);
done:
return;
XPfw_Write32(master->buffer + IPI_BUFFER_RESP_OFFSET, status);
}
/**
@ -125,7 +128,7 @@ static void PmRequestSuspend(const PmMaster *const master,
if (NULL == proc) {
PmDbg("ERROR processor not found by node %d\n", node);
PmProcessAckRequest(ack, master, node, PM_RET_ERROR_ARGS, 0);
PmProcessAckRequest(ack, master, node, XST_INVALID_PARAM, 0);
goto done;
}
@ -151,27 +154,28 @@ static void PmForcePowerdown(const PmMaster *const master,
const u32 node,
const u32 ack)
{
u32 status;
int status;
u32 oppoint = 0U;
PmNode* nodePtr = PmGetNodeById(node);
PmDbg("(%s, %s)\n", PmStrNode(node), PmStrAck(ack));
if (NULL == nodePtr) {
status = PM_RET_ERROR_ARGS;
status = XST_INVALID_PARAM;
goto done;
}
switch (nodePtr->typeId) {
case PM_TYPE_PROC:
status = PmProcFsm((PmProc*)nodePtr->derived, PM_PROC_EVENT_FORCE_PWRDN);
status = PmProcFsm((PmProc*)nodePtr->derived,
PM_PROC_EVENT_FORCE_PWRDN);
break;
case PM_TYPE_PWR_ISLAND:
case PM_TYPE_PWR_DOMAIN:
status = PmForceDownTree((PmPower*)nodePtr->derived);
break;
default:
status = PM_RET_ERROR_OTHER;
status = XST_INVALID_PARAM;
break;
}
@ -181,7 +185,7 @@ static void PmForcePowerdown(const PmMaster *const master,
* Successfully powered down a node, now trigger opportunistic
* suspend to power down its parent(s) if possible
*/
if (PM_RET_SUCCESS == status && NULL != nodePtr->parent) {
if ((XST_SUCCESS == status) && (NULL != nodePtr->parent)) {
PmOpportunisticSuspend(nodePtr->parent);
}
@ -202,6 +206,7 @@ static void PmAbortSuspend(const PmMaster *const master,
const u32 reason,
const u32 node)
{
int status;
PmProc* proc = PmGetProcOfThisMaster(master, node);
PmDbg("(%s, %s)\n", PmStrNode(node), PmStrReason(reason));
@ -209,13 +214,14 @@ static void PmAbortSuspend(const PmMaster *const master,
if (NULL == proc) {
PmDbg("ERROR processor access for node %s not allowed\n",
PmStrNode(node));
status = XST_PM_INVALID_NODE;
goto done;
}
PmProcFsm(proc, PM_PROC_EVENT_ABORT_SUSPEND);
status = PmProcFsm(proc, PM_PROC_EVENT_ABORT_SUSPEND);
done:
return;
XPfw_Write32(master->buffer + IPI_BUFFER_RESP_OFFSET, status);
}
/**
@ -227,14 +233,14 @@ done:
static void PmRequestWakeup(const PmMaster *const master, const u32 node,
const u32 ack)
{
u32 status;
int status;
u32 oppoint = 0U;
PmProc* proc = PmGetProcByNodeId(node);
PmDbg("(%s, %s)\n", PmStrNode(node), PmStrAck(ack));
if (NULL == proc) {
status = PM_RET_ERROR_PROC;
status = XST_PM_INVALID_NODE;
goto done;
}
@ -256,21 +262,30 @@ static void PmReleaseNode(const PmMaster *master,
const u32 node,
const u32 latency)
{
u32 status;
int status;
/* Get static requirements structure for this master/slave pair */
PmRequirement* masterReq = PmGetRequirementForSlave(master, node);
if (NULL == masterReq) {
status = XST_PM_NO_ACCESS;
PmDbg("ERROR Can't find requirement for slave %s of master %s\n",
PmStrNode(node), PmStrNode(master->procs[0].node.nodeId));
goto done;
}
if (0U == (masterReq->info & PM_MASTER_USING_SLAVE_MASK)) {
status = XST_FAILURE;
PmDbg("WARNING %s attempt to release %s without previous "
"request\n", PmStrNode(master->procs[0].node.nodeId),
PmStrNode(node));
goto done;
}
/* Release requirements */
status = PmRequirementUpdate(masterReq, 0U);
masterReq->info &= ~PM_MASTER_USING_SLAVE_MASK;
if (PM_RET_SUCCESS != status) {
if (XST_SUCCESS != status) {
PmDbg("ERROR PmRequirementUpdate status = %d\n", status);
goto done;
}
@ -283,7 +298,7 @@ static void PmReleaseNode(const PmMaster *master,
done:
PmDbg("(%s, %d)\n", PmStrNode(node), latency);
return;
XPfw_Write32(master->buffer + IPI_BUFFER_RESP_OFFSET, status);
}
/**
@ -300,7 +315,7 @@ static void PmRequestNode(const PmMaster *master,
const u32 qos,
const u32 ack)
{
u32 status;
int status;
u32 oppoint = 0U;
/*
* Each legal master/slave pair will have one static PmRequirement data
@ -315,12 +330,12 @@ static void PmRequestNode(const PmMaster *master,
if (NULL == masterReq) {
/* Master is not allowed to use the slave with given node */
PmDbg("ERROR Master can't use the slave\n");
status = PM_RET_ERROR_ACCESS;
status = XST_PM_NO_ACCESS;
goto done;
}
if (PM_MASTER_USING_SLAVE_MASK & masterReq->info) {
status = PM_RET_ERROR_DOUBLEREQ;
status = XST_PM_DOUBLE_REQ;
goto done;
}
@ -351,7 +366,7 @@ static void PmSetRequirement(const PmMaster *master,
const u32 qos,
const u32 ack)
{
u32 status;
int status;
u32 oppoint = 0U;
PmRequirement* masterReq = PmGetRequirementForSlave(master, node);
@ -360,13 +375,13 @@ static void PmSetRequirement(const PmMaster *master,
/* Is there a provision for the master to use the given slave node */
if (NULL == masterReq) {
status = PM_RET_ERROR_ACCESS;
status = XST_PM_NO_ACCESS;
goto done;
}
/* Does master have the privilege to request settings for the node? */
/* Check if master has previously requested the node */
if (0U == (PM_MASTER_USING_SLAVE_MASK & masterReq->info)) {
status = PM_RET_ERROR_ACCESS;
status = XST_PM_NO_ACCESS;
goto done;
}
@ -381,8 +396,11 @@ static void PmSetRequirement(const PmMaster *master,
status = PmRequirementUpdate(masterReq, capabilities);
break;
default:
/* Should never happen */
status = PM_RET_ERROR_COMMUNIC;
/*
* Should never happen as processor cannot call this API while
* powered down.
*/
status = XST_FAILURE;
break;
}
oppoint = masterReq->slave->node.currState;
@ -401,7 +419,7 @@ static void PmGetApiVersion(const PmMaster *const master)
PmDbg("version %d.%d\n", PM_VERSION_MAJOR, PM_VERSION_MINOR);
XPfw_Write32(master->buffer + IPI_BUFFER_RESP_OFFSET, PM_RET_SUCCESS);
XPfw_Write32(master->buffer + IPI_BUFFER_RESP_OFFSET, XST_SUCCESS);
XPfw_Write32(master->buffer + IPI_BUFFER_RESP_OFFSET + PAYLOAD_ELEM_SIZE,
version);
}
@ -422,7 +440,7 @@ static void PmMmioWrite(const PmMaster *const master, const u32 address,
PmDbg("(0x%x, 0x%x, 0x%x)\n", address, mask, value);
XPfw_Write32(address, mask & value);
XPfw_Write32(master->buffer + IPI_BUFFER_RESP_OFFSET, PM_RET_SUCCESS);
XPfw_Write32(master->buffer + IPI_BUFFER_RESP_OFFSET, XST_SUCCESS);
}
/**
@ -442,7 +460,7 @@ static void PmMmioRead(const PmMaster *const master, const u32 address,
PmDbg("addr=0x%x, mask=0x%x\n", address, mask);
value = XPfw_Read32(address) & mask;
XPfw_Write32(master->buffer + IPI_BUFFER_RESP_OFFSET, PM_RET_SUCCESS);
XPfw_Write32(master->buffer + IPI_BUFFER_RESP_OFFSET, XST_SUCCESS);
XPfw_Write32(master->buffer + IPI_BUFFER_RESP_OFFSET + PAYLOAD_ELEM_SIZE,
value);
}
@ -462,9 +480,16 @@ static void PmSetWakeupSource(const PmMaster *const master,
const u32 sourceNode,
const u32 enable)
{
int status = XST_SUCCESS;
PmRequirement* req = PmGetRequirementForSlave(master, sourceNode);
if ((NULL == req) || (NULL == req->slave->wake)) {
if (NULL == req) {
status = XST_PM_NO_ACCESS;
goto done;
}
if (NULL == req->slave->wake) {
status = XST_NO_FEATURE;
goto done;
}
@ -477,6 +502,8 @@ static void PmSetWakeupSource(const PmMaster *const master,
done:
PmDbg("(%s, %s, %d)\n", PmStrNode(master->procs->node.nodeId),
PmStrNode(sourceNode), enable);
XPfw_Write32(master->buffer + IPI_BUFFER_RESP_OFFSET, status);
}
/**
@ -647,7 +674,7 @@ void PmProcessApiCall(const PmMaster *const master,
default:
PmDbg("ERROR unsupported PM API #%d\n", pload[0]);
PmProcessAckRequest(PmRequestAcknowledge(pload), master,
NODE_UNKNOWN, PM_RET_ERROR_NOTSUPPORTED, 0);
NODE_UNKNOWN, XST_INVALID_VERSION, 0);
break;
}
}
@ -675,7 +702,7 @@ void PmProcessRequest(const PmMaster *const master,
u32 ack = PmRequestAcknowledge(pload);
if (REQUEST_ACK_NO != ack) {
PmAcknowledgeCb(master, NODE_UNKNOWN,
PM_RET_ERROR_API_ID, 0);
XST_INVALID_PARAM, 0);
}
}
}

View file

@ -151,18 +151,11 @@
#define PM_OPCHAR_TYPE_ENERGY 2U
#define PM_OPCHAR_TYPE_TEMP 3U
/* PM API call return status */
#define PM_RET_SUCCESS 0U
#define PM_RET_ERROR_ARGS 1U
#define PM_RET_ERROR_ACCESS 2U
#define PM_RET_ERROR_TIMEOUT 3U
#define PM_RET_ERROR_NOTSUPPORTED 4U
#define PM_RET_ERROR_PROC 5U
#define PM_RET_ERROR_API_ID 6U
#define PM_RET_ERROR_FAILURE 7U
#define PM_RET_ERROR_COMMUNIC 8U
#define PM_RET_ERROR_DOUBLEREQ 9U
#define PM_RET_ERROR_INTERNAL 24U
#define PM_RET_ERROR_OTHER 25U
/* Power management specific return error statuses */
#define XST_PM_INTERNAL 2000L
#define XST_PM_CONFLICT 2001L
#define XST_PM_NO_ACCESS 2002L
#define XST_PM_INVALID_NODE 2003L
#define XST_PM_DOUBLE_REQ 2004L
#endif

View file

@ -267,15 +267,17 @@ static const PmMaster *const pmAllMasters[] = {
* goes to sleep.
*
* @return Status of the operation
* - XST_SUCCESS if requirement is successfully scheduled
* - XST_NO_FEATURE if there is no state with requested
* capabilities
*/
u32 PmRequirementSchedule(PmRequirement* const masterReq, const u32 caps)
int PmRequirementSchedule(PmRequirement* const masterReq, const u32 caps)
{
u32 status;
int status;
/* Check if slave has a state with requested capabilities */
status = PmCheckCapabilities(masterReq->slave, caps);
if (PM_RET_SUCCESS != status) {
status = PM_RET_ERROR_NOTSUPPORTED;
if (XST_SUCCESS != status) {
goto done;
}
@ -295,15 +297,15 @@ done:
*
* @return Status of the operation
*/
u32 PmRequirementUpdate(PmRequirement* const masterReq, const u32 caps)
int PmRequirementUpdate(PmRequirement* const masterReq, const u32 caps)
{
u32 status;
int status;
u32 tmpCaps;
/* Check if slave has a state with requested capabilities */
status = PmCheckCapabilities(masterReq->slave, caps);
if (PM_RET_SUCCESS != status) {
if (XST_SUCCESS != status) {
goto done;
}
@ -312,7 +314,7 @@ u32 PmRequirementUpdate(PmRequirement* const masterReq, const u32 caps)
masterReq->currReq = caps;
status = PmUpdateSlave(masterReq->slave);
if (PM_RET_SUCCESS == status) {
if (XST_SUCCESS == status) {
/* All capabilities requested in active state are constant */
masterReq->nextReq = masterReq->currReq;
} else {
@ -344,10 +346,10 @@ done:
* current requirements. Default requirements has priority over current
* requirements.
*/
static void PmRequirementUpdateScheduled(const PmMaster* const master,
const bool swap)
static int PmRequirementUpdateScheduled(const PmMaster* const master,
const bool swap)
{
u32 status;
int status;
PmRequirementId i;
PmDbg("%s\n", PmStrNode(master->procs[0].node.nodeId));
@ -376,12 +378,15 @@ static void PmRequirementUpdateScheduled(const PmMaster* const master,
/* Update slave setting */
status = PmUpdateSlave(master->reqs[i].slave);
/* if rom works correctly, status should be always ok */
if (PM_RET_SUCCESS != status) {
if (XST_SUCCESS != status) {
PmDbg("ERROR setting slave node %s\n",
PmStrNode(master->reqs[i].slave->node.nodeId));
break;
}
}
}
return status;
}
/**
@ -431,10 +436,13 @@ static void PmRequirementRequestDefault(const PmMaster* const master)
* power down, so all requirements of the processor
* are automatically released.
* @master Master whose primary processor was forced to power down
*
* @return Status of the operation of releasing all slaves used by the master
* and changing their state to the lowest possible.
*/
static void PmRequirementReleaseAll(const PmMaster* const master)
static int PmRequirementReleaseAll(const PmMaster* const master)
{
u32 status;
int status;
PmRequirementId i;
for (i = 0; i < master->reqsCnt; i++) {
@ -447,12 +455,15 @@ static void PmRequirementReleaseAll(const PmMaster* const master)
/* Update slave setting */
status = PmUpdateSlave(master->reqs[i].slave);
/* if pmu rom works correctly, status should be always ok */
if (PM_RET_SUCCESS != status) {
if (XST_SUCCESS != status) {
PmDbg("ERROR setting slave node %s\n",
PmStrNode(master->reqs[i].slave->node.nodeId));
break;
}
}
}
return status;
}
/**
@ -746,14 +757,18 @@ static void PmWakeUpDisableAll(PmMaster* const master)
* @master Pointer to master object which needs to be notified
* @event Processor Event to notify the master about
*
* @return Status of potential changing of slave states or success.
*
* Primary processor has changed its state, notify master to update its requirements
* accordingly.
*/
void PmMasterNotify(PmMaster* const master, const PmProcEvent event)
int PmMasterNotify(PmMaster* const master, const PmProcEvent event)
{
int status = XST_SUCCESS;
switch (event) {
case PM_PROC_EVENT_SLEEP:
PmRequirementUpdateScheduled(master, true);
status = PmRequirementUpdateScheduled(master, true);
break;
case PM_PROC_EVENT_ABORT_SUSPEND:
PmRequirementCancelScheduled(master);
@ -767,14 +782,17 @@ void PmMasterNotify(PmMaster* const master, const PmProcEvent event)
PmRequirementRequestDefault(master);
} else {
}
PmRequirementUpdateScheduled(master, false);
status = PmRequirementUpdateScheduled(master, false);
break;
case PM_PROC_EVENT_FORCE_PWRDN:
PmRequirementReleaseAll(master);
status = PmRequirementReleaseAll(master);
PmWakeUpCancelScheduled(master);
break;
default:
status = XST_PM_INTERNAL;
PmDbg("ERROR: undefined event #%d\n", event);
break;
}
return status;
}

View file

@ -168,15 +168,14 @@ PmRequirement* PmGetRequirementForSlave(const PmMaster* const master,
const PmNodeId nodeId);
/* Requirements related functions */
u32 PmRequirementSchedule(PmRequirement* const masterReq, const u32 caps);
u32 PmRequirementUpdate(PmRequirement* const masterReq, const u32 caps);
int PmRequirementSchedule(PmRequirement* const masterReq, const u32 caps);
int PmRequirementUpdate(PmRequirement* const masterReq, const u32 caps);
/* Notify master by a primary core when changing state */
int PmMasterNotify(PmMaster* const master, const PmProcEvent event);
/* Call at initialization to enable all masters' IPI interrupts */
void PmEnableAllMasterIpis(void);
/* Notify master by a primary core when changing state */
void PmMasterNotify(PmMaster* const master, const PmProcEvent event);
/* Call when FPD goes down to enable GIC Proxy interrupts */
void PmEnableProxyWake(PmMaster* const master);

View file

@ -38,6 +38,7 @@
#include "pm_defs.h"
#include "pm_common.h"
#include "xil_types.h"
#include "xstatus.h"
typedef u8 PmNodeId;
typedef u8 PmStateId;
@ -49,7 +50,7 @@ typedef struct PmPower PmPower;
typedef struct PmNode PmNode;
/* Function pointer for wake/sleep transition functions */
typedef u32 (*const PmNodeTranHandler)(PmNode* const nodePtr);
typedef int (*const PmNodeTranHandler)(PmNode* const nodePtr);
/*********************************************************************
* Macros

View file

@ -41,42 +41,52 @@
#include "pm_periph.h"
#include "xpfw_rom_interface.h"
/**
* PmPowerDownFpd() - Power down FPD domain
*
* @return Status of the pmu-rom operations
*/
static int PmPowerDownFpd(void)
{
int status = XpbrRstFpdHandler();
if (XST_SUCCESS == status) {
status = XpbrPwrDnFpdHandler();
/*
* When FPD is powered off, the APU-GIC will be affected too.
* GIC Proxy has to take over for all wake-up sources for
* the APU.
*/
PmEnableProxyWake(&pmMasterApu_g);
}
return status;
}
/**
* PmPwrDnHandler() - Power down island/domain
* @nodePtr Pointer to node-structure of power island/dom to be powered off
*
* @return Operation status
* - PM_RET_SUCCESS if transition succeeded
* - PM_RET_ERROR_FAILURE if pmu rom failed to set the state
* @return Operation status of power down procedure (done by pmu-rom)
*/
static u32 PmPwrDnHandler(PmNode* const nodePtr)
static int PmPwrDnHandler(PmNode* const nodePtr)
{
u32 ret = PM_RET_ERROR_FAILURE;
int status = XST_PM_INTERNAL;
if (NULL == nodePtr) {
ret = PM_RET_ERROR_FAILURE;
goto done;
}
/* Call proper PMU-ROM handler as needed */
switch (nodePtr->nodeId) {
case NODE_FPD:
ret = XpbrRstFpdHandler();
if (ret == XST_SUCCESS) {
ret = XpbrPwrDnFpdHandler();
/*
* When FPD is powered off, the APU-GIC will be affected too.
* GIC Proxy has to take over for all wake-up sources for
* the APU.
*/
PmEnableProxyWake(&pmMasterApu_g);
}
status = PmPowerDownFpd();
break;
case NODE_APU:
ret = XST_SUCCESS;
status = XST_SUCCESS;
break;
case NODE_RPU:
ret = XpbrPwrDnRpuHandler();
status = XpbrPwrDnRpuHandler();
break;
default:
PmDbg("unsupported node %s(%d)\n",
@ -84,30 +94,24 @@ static u32 PmPwrDnHandler(PmNode* const nodePtr)
break;
}
if (XST_SUCCESS != ret) {
ret = PM_RET_ERROR_FAILURE;
goto done;
if (XST_SUCCESS == status) {
nodePtr->currState = PM_PWR_STATE_OFF;
}
nodePtr->currState = PM_PWR_STATE_OFF;
ret = PM_RET_SUCCESS;
done:
PmDbg("%s\n", PmStrNode(nodePtr->nodeId));
return ret;
return status;
}
/**
* PmPwrUpHandler() - Power up island/domain
* @nodePtr Pointer to node-structure of power island/dom to be powered on
*
* @return Operation status
* - PM_RET_SUCCESS if transition succeeded
* - PM_RET_ERROR_FAILURE if pmu rom failed to set the state
* @return Operation status of power up procedure (done by pmu-rom)
*/
static u32 PmPwrUpHandler(PmNode* const nodePtr)
static int PmPwrUpHandler(PmNode* const nodePtr)
{
u32 ret = PM_RET_ERROR_FAILURE;
int status = XST_PM_INTERNAL;
PmDbg("%s\n", PmStrNode(nodePtr->nodeId));
@ -118,20 +122,24 @@ static u32 PmPwrUpHandler(PmNode* const nodePtr)
/* Call proper PMU-ROM handler as needed */
switch (nodePtr->nodeId) {
case NODE_FPD:
ret = XpbrPwrUpFpdHandler();
PmDbg("XpbrPwrUpFpdHandler return code #%d\n", ret);
status = XpbrPwrUpFpdHandler();
#ifdef DEBUG_PM
/* FIXME workaround for old version of pmu-rom */
PmDbg("ignoring error\n");
ret = XST_SUCCESS;
if (XST_SUCCESS != status) {
PmDbg("XpbrPwrUpFpdHandler returned #%d."
"Ignoring error\n", status);
status = XST_SUCCESS;
}
#endif
break;
case NODE_APU:
ret = XST_SUCCESS;
status = XST_SUCCESS;
break;
case NODE_RPU:
{
u32 reg;
ret = XpbrPwrUpRpuHandler();
status = XpbrPwrUpRpuHandler();
/* release RPU island reset */
reg = Xil_In32(CRL_APB_RST_LPD_TOP);
@ -144,19 +152,12 @@ static u32 PmPwrUpHandler(PmNode* const nodePtr)
PmStrNode(nodePtr->nodeId), nodePtr->nodeId);
break;
}
if (XST_SUCCESS != ret) {
PmDbg("failed to power up %s PBR ERROR #%d\n",
PmStrNode(nodePtr->nodeId), ret);
ret = PM_RET_ERROR_FAILURE;
goto done;
if (XST_SUCCESS == status) {
nodePtr->currState = PM_PWR_STATE_ON;
}
nodePtr->currState = PM_PWR_STATE_ON;
ret = PM_RET_SUCCESS;
done:
return ret;
return status;
}
/* Children array definitions */
@ -334,8 +335,8 @@ done:
* PmPowerUpTopParent() - Power up top parent in hierarchy that's currently off
* @powerChild Power child whose power parent has to be powered up
*
* @return Status of the power up operation (always PM_RET_SUCCESS if all
* power parents are already powered on)
* @return Status of the power up operation (XST_SUCCESS if all power
* parents are already powered on)
*
* This function turns on exactly one power parent, starting with the highest
* level parent that's currently off. If all power parents are on, it will
@ -345,13 +346,13 @@ done:
* PmTriggerPowerUp that calls this function iteratively until all power
* nodes in the hierarchy are powered up.
*/
static u32 PmPowerUpTopParent(PmPower* const powerChild)
static int PmPowerUpTopParent(PmPower* const powerChild)
{
u32 status = PM_RET_SUCCESS;
int status = XST_SUCCESS;
PmPower* powerParent = powerChild;
if (NULL == powerParent) {
status = PM_RET_ERROR_INTERNAL;
status = XST_PM_INTERNAL;
goto done;
}
@ -377,9 +378,9 @@ done:
*
* @return Status of the power up operation.
*/
u32 PmTriggerPowerUp(PmPower* const power)
int PmTriggerPowerUp(PmPower* const power)
{
u32 status = PM_RET_SUCCESS;
int status = XST_SUCCESS;
if (NULL == power) {
goto done;
@ -390,14 +391,16 @@ u32 PmTriggerPowerUp(PmPower* const power)
* turned on (always top-down).
* Use iterative approach for MISRA-C compliance
*/
while ((true == IS_OFF(&power->node)) && (PM_RET_SUCCESS == status)) {
while ((true == IS_OFF(&power->node)) && (XST_SUCCESS == status)) {
status = PmPowerUpTopParent(power);
}
done:
if (PM_RET_SUCCESS != status) {
PmDbg("failed to power up: ERROR #%d\n", status);
#ifdef DEBUG_PM
if (XST_SUCCESS != status) {
PmDbg("ERROR #%d failed to power up\n", status);
}
#endif
return status;
}
@ -485,16 +488,18 @@ static void PmForcePowerDownChildren(const PmPower* const parent)
* PmForceDownTree() - Force power down node and all its children
* @root power node (island/domain) to turn off
*
* @return Operation status of power down procedure
*
* This is a power island or power domain, power it off from the bottom up:
* find out if this parent has children which themselves have children.
* Note: using iterative algorithm for MISRA-C compliance
* (instead of recursion)
*
*/
u32 PmForceDownTree(PmPower* const root)
int PmForceDownTree(PmPower* const root)
{
int status = XST_PM_INTERNAL;
PmPower* lowestParent;
u32 status = PM_RET_SUCCESS;
if (NULL == root) {
goto done;
@ -506,7 +511,7 @@ u32 PmForceDownTree(PmPower* const root)
if (true == HAS_SLEEP(lowestParent->node.ops)) {
status = lowestParent->node.ops->sleep(&lowestParent->node);
}
} while ((lowestParent != root) && (status == PM_RET_SUCCESS));
} while ((lowestParent != root) && (XST_SUCCESS == status));
done:
return status;

View file

@ -77,7 +77,7 @@ extern PmPower pmPowerDomainFpd_g;
* Function declarations
********************************************************************/
void PmOpportunisticSuspend(PmPower* const power);
u32 PmTriggerPowerUp(PmPower* const power);
u32 PmForceDownTree(PmPower* const root);
int PmTriggerPowerUp(PmPower* const power);
int PmForceDownTree(PmPower* const root);
#endif

View file

@ -58,59 +58,54 @@
* @nodePtr Pointer to node-structure of processor to be put to sleep
*
* @return Operation status
* - PM_RET_SUCCESS if transition succeeded
* - PM_RET_ERROR_FAILURE if pmu rom failed to set the state
* - XST_PM_INTERNAL if processor cannot be identified
* - XST_SUCCESS if processor has no sleep handler (example Rpu0)
* - Returned status by pmu-rom if processor sleep handler is called
*/
u32 PmProcSleep(PmNode* const nodePtr)
int PmProcSleep(PmNode* const nodePtr)
{
u32 ret;
int status = XST_PM_INTERNAL;
if (NULL == nodePtr) {
ret = PM_RET_ERROR_FAILURE;
goto done;
}
/* Call proper PMU-ROM handler as needed */
switch (nodePtr->nodeId) {
case NODE_APU_0:
ret = XpbrACPU0SleepHandler();
status = XpbrACPU0SleepHandler();
break;
case NODE_APU_1:
ret = XpbrACPU1SleepHandler();
status = XpbrACPU1SleepHandler();
break;
case NODE_APU_2:
ret = XpbrACPU2SleepHandler();
status = XpbrACPU2SleepHandler();
break;
case NODE_APU_3:
ret = XpbrACPU3SleepHandler();
status = XpbrACPU3SleepHandler();
break;
case NODE_RPU_0:
XPfw_RMW32(CRL_APB_RST_LPD_TOP,
CRL_APB_RST_LPD_TOP_RPU_R50_RESET_MASK,
CRL_APB_RST_LPD_TOP_RPU_R50_RESET_MASK);
ret = PM_RET_SUCCESS;
status = XST_SUCCESS;
break;
case NODE_RPU_1:
XPfw_RMW32(CRL_APB_RST_LPD_TOP,
CRL_APB_RST_LPD_TOP_RPU_R51_RESET_MASK,
CRL_APB_RST_LPD_TOP_RPU_R51_RESET_MASK);
ret = PM_RET_SUCCESS;
status = XST_SUCCESS;
break;
default:
ret = PM_RET_ERROR_INTERNAL;
break;
}
if (XST_SUCCESS != ret) {
ret = PM_RET_ERROR_FAILURE;
goto done;
if (XST_SUCCESS == status) {
nodePtr->currState = PM_PROC_STATE_SLEEP;
}
nodePtr->currState = PM_PROC_STATE_SLEEP;
ret = PM_RET_SUCCESS;
done:
return ret;
return status;
}
/**
@ -118,62 +113,59 @@ done:
* @nodePtr Pointer to node-structure of processor to be woken-up
*
* @return Operation status
* - PM_RET_SUCCESS if transition succeeded
* - PM_RET_ERROR_FAILURE if pmu rom failed to set the state
* - XST_PM_INTERNAL if processor cannot be identified
* - Returned status of power up function if something goes wrong
* - Returned status by pmu-rom if processor wake handler is called
*/
u32 PmProcWake(PmNode* const nodePtr)
int PmProcWake(PmNode* const nodePtr)
{
u32 ret = PM_RET_SUCCESS;
int status = XST_SUCCESS;
if (NULL == nodePtr) {
ret = PM_RET_ERROR_INTERNAL;
status = XST_PM_INTERNAL;
goto done;
}
if (PM_PWR_STATE_OFF == nodePtr->parent->node.currState) {
/* Power parent is down, trigger its powering up */
ret = PmTriggerPowerUp(nodePtr->parent);
status = PmTriggerPowerUp(nodePtr->parent);
}
if (PM_RET_SUCCESS != ret) {
if (XST_SUCCESS != status) {
goto done;
}
/* Call proper PMU-ROM handler as needed */
switch (nodePtr->nodeId) {
case NODE_APU_0:
ret = XpbrACPU0WakeHandler();
status = XpbrACPU0WakeHandler();
break;
case NODE_APU_1:
ret = XpbrACPU1WakeHandler();
status = XpbrACPU1WakeHandler();
break;
case NODE_APU_2:
ret = XpbrACPU2WakeHandler();
status = XpbrACPU2WakeHandler();
break;
case NODE_APU_3:
ret = XpbrACPU3WakeHandler();
status = XpbrACPU3WakeHandler();
break;
case NODE_RPU_0:
ret = XpbrRstR50Handler();
status = XpbrRstR50Handler();
break;
case NODE_RPU_1:
ret = XpbrRstR51Handler();
status = XpbrRstR51Handler();
break;
default:
ret = XST_SUCCESS;
status = XST_PM_INTERNAL;
break;
}
if (XST_SUCCESS != ret) {
ret = PM_RET_ERROR_FAILURE;
goto done;
if (XST_SUCCESS == status) {
nodePtr->currState = PM_PROC_STATE_ACTIVE;
}
nodePtr->currState = PM_PROC_STATE_ACTIVE;
ret = PM_RET_SUCCESS;
done:
return ret;
return status;
}
/**
@ -181,18 +173,18 @@ done:
* @proc Pointer to processor whose FSM is changing state
*
* @return Operation status
* - PM_RET_SUCCESS is always returned as this transition cannot fail
* - XST_SUCCESS is always returned as this transition cannot fail
*
* @note Executes when processor's request for self suspend gets processed.
*/
static u32 PmProcTrActiveToSuspend(PmProc* const proc)
static int PmProcTrActiveToSuspend(PmProc* const proc)
{
PmDbg("ACTIVE->SUSPENDING %s\n", PmStrNode(proc->node.nodeId));
ENABLE_WFI(proc->wfiEnableMask);
proc->node.currState = PM_PROC_STATE_SUSPENDING;
return PM_RET_SUCCESS;
return XST_SUCCESS;
}
/**
@ -201,10 +193,6 @@ static u32 PmProcTrActiveToSuspend(PmProc* const proc)
* @proc Pointer to processor whose FSM is changing state
*
* @return Operation status
* - PM_RET_SUCCESS if transition succeeded
* - PM_RET_ERROR_FAILURE if pmu rom failed to set the state
* - PM_RET_ERROR_INTERNAL if processor structures are incorrectly
* initialized
*
* @note Executes when some other processor authorized to do so requests
* through PM API the PMU to powered down this processor. This
@ -213,7 +201,7 @@ static u32 PmProcTrActiveToSuspend(PmProc* const proc)
* no implemented sleep function it will continue executing
* instructions.
*/
static u32 PmProcTrToForcedOff(PmProc* const proc)
static int PmProcTrToForcedOff(PmProc* const proc)
{
u32 status;
@ -222,9 +210,9 @@ static u32 PmProcTrToForcedOff(PmProc* const proc)
status = PmProcSleep(&proc->node);
/* Override the state set in PmProcSleep to indicate FORCED OFF */
proc->node.currState = PM_PROC_STATE_FORCEDOFF;
if (true == proc->isPrimary) {
if ((true == proc->isPrimary) && (XST_SUCCESS == status)) {
/* Notify master to release all requirements of this processor */
PmMasterNotify(proc->master, PM_PROC_EVENT_FORCE_PWRDN);
status = PmMasterNotify(proc->master, PM_PROC_EVENT_FORCE_PWRDN);
}
return status;
@ -234,23 +222,24 @@ static u32 PmProcTrToForcedOff(PmProc* const proc)
* PmProcTrSuspendToActive() - FSM transition from suspend to active state
* @proc Pointer to processor whose FSM is changing state
*
* @return Operation status
* - PM_RET_SUCCESS is always returned as this transition cannot fail
* @return Operation status (should be always success)
*
* @note Executes when processor requests abort suspend through PM API.
*/
static u32 PmProcTrSuspendToActive(PmProc* const proc)
static int PmProcTrSuspendToActive(PmProc* const proc)
{
int status;
PmDbg("SUSPENDING->ACTIVE %s\n", PmStrNode(proc->node.nodeId));
DISABLE_WFI(proc->wfiEnableMask);
DISABLE_WAKE(proc->wakeEnableMask);
/* Notify master to cancel scheduled requests */
PmMasterNotify(proc->master, PM_PROC_EVENT_ABORT_SUSPEND);
status = PmMasterNotify(proc->master, PM_PROC_EVENT_ABORT_SUSPEND);
proc->node.currState = PM_PROC_STATE_ACTIVE;
return PM_RET_SUCCESS;
return status;
}
/**
@ -258,27 +247,23 @@ static u32 PmProcTrSuspendToActive(PmProc* const proc)
* @proc Pointer to processor whose FSM is changing state
*
* @return Operation status
* - PM_RET_SUCCESS if transition succeeded
* - PM_RET_ERROR_FAILURE if pmu rom failed to set the state
* - PM_RET_ERROR_INTERNAL if processor structures are incorrectly
* initialized
*
* @note Processor had previously called self suspend and now PMU has
* received processor's wfi interrupt.
*/
static u32 PmProcTrSuspendToSleep(PmProc* const proc)
static int PmProcTrSuspendToSleep(PmProc* const proc)
{
u32 status;
int status;
PmDbg("SUSPENDING->SLEEP %s\n", PmStrNode(proc->node.nodeId));
status = PmProcSleep(&proc->node);
if (true == proc->isPrimary) {
if ((true == proc->isPrimary) && (XST_SUCCESS == status)) {
/*
* Notify master to update slave capabilities according to the
* scheduled requests for after primary processor goes to sleep.
*/
PmMasterNotify(proc->master, PM_PROC_EVENT_SLEEP);
status = PmMasterNotify(proc->master, PM_PROC_EVENT_SLEEP);
}
DISABLE_WFI(proc->wfiEnableMask);
ENABLE_WAKE(proc->wakeEnableMask);
@ -291,36 +276,31 @@ static u32 PmProcTrSuspendToSleep(PmProc* const proc)
* @proc Pointer to processor whose FSM is changing state
*
* @return Operation status
* - PM_RET_SUCCESS if transition succeeded
* - PM_RET_ERROR_FAILURE if pmu rom failed to set the state
* - PM_RET_ERROR_INTERNAL if processor structures are incorrectly
* initialized
*
* @note Processor had previously called self suspend and before it had
* executed wfi PMU has received PM API request to force power down
* of this processor. Therefore, PMU does not wait for wfi interrupt
* from this processor to come, but puts it to sleep.
*/
static u32 PmProcTrSleepToActive(PmProc* const proc)
static int PmProcTrSleepToActive(PmProc* const proc)
{
u32 status;
int status = XST_SUCCESS;
if (true == proc->isPrimary) {
/*
* Notify master to update slave capabilities according to the
* scheduled requests for before the primary processor
* gets woken-up.
* scheduled requests for before the primary processor gets
* woken-up.
*/
PmMasterNotify(proc->master, PM_PROC_EVENT_WAKE);
status = PmMasterNotify(proc->master, PM_PROC_EVENT_WAKE);
}
if (XST_SUCCESS == status) {
PmDbg("SLEEP->ACTIVE %s\n", PmStrNode(proc->node.nodeId));
status = PmProcWake(&proc->node);
/* Keep wfi interrupt disabled while processor is active */
DISABLE_WFI(proc->wfiEnableMask);
DISABLE_WAKE(proc->wakeEnableMask);
}
PmDbg("SLEEP->ACTIVE %s\n", PmStrNode(proc->node.nodeId));
status = PmProcWake(&proc->node);
/* Keep wfi interrupt disabled while processor is active */
DISABLE_WFI(proc->wfiEnableMask);
DISABLE_WAKE(proc->wakeEnableMask);
return status;
}
@ -331,17 +311,15 @@ static u32 PmProcTrSleepToActive(PmProc* const proc)
* @proc Pointer to processor whose FSM is changing state
*
* @return Operation status
* - PM_RET_SUCCESS if transition succeeded
* - PM_RET_ERROR_FAILURE if pmu rom failed to set the state
* - PM_RET_ERROR_INTERNAL if processor does not have wake function
*
* @note Processor had previously called self suspend and before it had
* executed wfi PMU has received PM API request to force power down
* of this processor. Therefore, PMU does not wait for wfi interrupt
* from this processor to come, but puts it to sleep.
*/
static u32 PmProcTrForcePwrdnToActive(PmProc* const proc)
static int PmProcTrForcePwrdnToActive(PmProc* const proc)
{
int status = XST_SUCCESS;
PmDbg("FORCED_PWRDN->ACTIVE %s\n", PmStrNode(proc->node.nodeId));
if (true == proc->isPrimary) {
@ -350,10 +328,13 @@ static u32 PmProcTrForcePwrdnToActive(PmProc* const proc)
* scheduled requests. For waking-up from forced powerdown,
* these requirements are always only default requirements.
*/
PmMasterNotify(proc->master, PM_PROC_EVENT_WAKE);
status = PmMasterNotify(proc->master, PM_PROC_EVENT_WAKE);
}
if (XST_SUCCESS == status) {
status = PmProcWake(&proc->node);
}
return PmProcWake(&proc->node);
return status;
}
/**
@ -361,22 +342,20 @@ static u32 PmProcTrForcePwrdnToActive(PmProc* const proc)
* @proc Pointer to the processor the event is for
* @event Processor-specific event to act upon
*
* @return Status of the processor state change operation
*
* @note This FSM coordinates the state transitions for an individual
* processor.
*/
u32 PmProcFsm(PmProc* const proc, const PmProcEvent event)
int PmProcFsm(PmProc* const proc, const PmProcEvent event)
{
u32 status = PM_RET_SUCCESS;
u32 currState = proc->node.currState;
int status = XST_PM_INTERNAL;
PmStateId currState = proc->node.currState;
switch (event) {
case PM_PROC_EVENT_SELF_SUSPEND:
if (PM_PROC_STATE_ACTIVE == currState) {
status = PmProcTrActiveToSuspend(proc);
} else {
PmDbg("ERROR: illegal state %d for SUSPEND event\n",
currState);
status = PM_RET_ERROR_INTERNAL;
}
break;
case PM_PROC_EVENT_FORCE_PWRDN:
@ -388,19 +367,11 @@ u32 PmProcFsm(PmProc* const proc, const PmProcEvent event)
case PM_PROC_EVENT_ABORT_SUSPEND:
if (PM_PROC_STATE_SUSPENDING == currState) {
status = PmProcTrSuspendToActive(proc);
} else {
PmDbg("ERROR: illegal state %d for ABORT event\n",
currState);
status = PM_RET_ERROR_INTERNAL;
}
break;
case PM_PROC_EVENT_SLEEP:
if (PM_PROC_STATE_SUSPENDING == currState) {
status = PmProcTrSuspendToSleep(proc);
} else {
PmDbg("ERROR: illegal state %d for SLEEP event\n",
currState);
status = PM_RET_ERROR_INTERNAL;
}
break;
case PM_PROC_EVENT_WAKE:
@ -409,16 +380,17 @@ u32 PmProcFsm(PmProc* const proc, const PmProcEvent event)
} else if (PM_PROC_STATE_FORCEDOFF == currState) {
status = PmProcTrForcePwrdnToActive(proc);
} else {
PmDbg("ERROR: illegal state %d for WAKE event\n",
currState);
status = PM_RET_ERROR_INTERNAL;
}
break;
default:
PmDbg("ERROR: unrecognized event %d\n", event);
status = PM_RET_ERROR_INTERNAL;
break;
}
#ifdef DEBUG_PM
if (status == XST_PM_INTERNAL) {
PmDbg("ERROR: state #%d event #%d\n", currState, event);
}
#endif
return status;
}

View file

@ -135,6 +135,6 @@ extern PmProc pmRpuProcs_g[PM_PROC_RPU_MAX];
/*********************************************************************
* Function declarations
********************************************************************/
u32 PmProcFsm(PmProc* const proc, const PmProcEvent event);
int PmProcFsm(PmProc* const proc, const PmProcEvent event);
#endif

View file

@ -130,23 +130,24 @@ static u32 PmGetMaxCapabilities(const PmSlave* const slave)
}
/**
* PmCheckCapabilities() - Check whether the slave has given capabilities
* PmCheckCapabilities() - Check whether the slave has state with specified
* capabilities
* @slave Slave pointer whose capabilities/states should be checked
* @cap Check for these capabilities
*
* @return Status does slave have a state with given capabilities.
* - PM_RET_SUCCESS - slave has state with given capabilities
* - PM_RET_ERROR_NOTSUPPORTED - slave does not have such state
* @return Status wheter slave has a state with given capabilities
* - XST_SUCCESS if slave has state with given capabilities
* - XST_NO_FEATURE if slave does not have such state
*/
u32 PmCheckCapabilities(PmSlave* const slave, const u32 cap)
int PmCheckCapabilities(PmSlave* const slave, const u32 cap)
{
PmStateId i;
u32 status = PM_RET_ERROR_NOTSUPPORTED;
int status = XST_NO_FEATURE;
for (i = 0; i < slave->slvFsm->statesCnt; i++) {
/* Find the first state that contains all capabilities */
if ((cap & slave->slvFsm->states[i]) == cap) {
status = PM_RET_SUCCESS;
status = XST_SUCCESS;
break;
}
}
@ -159,13 +160,13 @@ u32 PmCheckCapabilities(PmSlave* const slave, const u32 cap)
* @slave Slave pointer whose state should be changed
* @state New state
*
* @return PM_RET_SUCCESS if transition was performed successfully
* error otherwise
* @return XST_SUCCESS if transition was performed successfully.
* Error otherwise.
*/
static u32 PmSlaveChangeState(PmSlave* const slave, const PmStateId state)
static int PmSlaveChangeState(PmSlave* const slave, const PmStateId state)
{
u32 t;
u32 status;
int status;
const PmSlaveFsm* fsm = slave->slvFsm;
#ifdef DEBUG_PM
PmStateId oldState = slave->node.currState;
@ -173,13 +174,13 @@ static u32 PmSlaveChangeState(PmSlave* const slave, const PmStateId state)
if (0U == fsm->transCnt) {
/* Slave's FSM has no transitions when it has only one state */
status = PM_RET_SUCCESS;
status = XST_SUCCESS;
} else {
/*
* Slave has transitions to change the state. Assume the failure
* and change status if state is changed correctly.
*/
status = PM_RET_ERROR_FAILURE;
status = XST_FAILURE;
}
for (t = 0U; t < fsm->transCnt; t++) {
@ -197,13 +198,13 @@ static u32 PmSlaveChangeState(PmSlave* const slave, const PmStateId state)
* Slave's FSM has no actions, because it has no private
* properties to be controlled here.
*/
status = PM_RET_SUCCESS;
status = XST_SUCCESS;
}
break;
}
#ifdef DEBUG_PM
if (PM_RET_SUCCESS == status) {
if (XST_SUCCESS == status) {
PmDbg("%s %d->%d\n", PmStrNode(slave->node.nodeId), oldState,
slave->node.currState);
} else {
@ -221,11 +222,11 @@ static u32 PmSlaveChangeState(PmSlave* const slave, const PmStateId state)
*
* @return Status of operation
*/
u32 PmUpdateSlave(PmSlave* const slave)
int PmUpdateSlave(PmSlave* const slave)
{
PmStateId s;
const PmSlaveFsm* fsm = slave->slvFsm;
u32 status = PM_RET_ERROR_NOTSUPPORTED;
int status = XST_FAILURE;
u32 capsToSet = PmGetMaxCapabilities(slave);
if (0U != capsToSet) {
@ -234,7 +235,7 @@ u32 PmUpdateSlave(PmSlave* const slave)
if ((capsToSet & fsm->states[s]) == capsToSet) {
if (s == slave->node.currState) {
/* Slave is already in right state */
status = PM_RET_SUCCESS;
status = XST_SUCCESS;
} else {
status = PmSlaveChangeState(slave, s);
}
@ -259,22 +260,37 @@ u32 PmUpdateSlave(PmSlave* const slave)
* @slave Pointer to a slave whose masters has to be woken-up (if master has
* requested this slave as wake-up source before going to sleep)
*
* @return Return status of waking up processors
*
* @note: Wake event of this slave is disabled together with all other slaves
* as part of the wake-up sequence.
*/
static void PmSlaveWakeMasters(PmSlave* const slave)
static int PmSlaveWakeMasters(PmSlave* const slave)
{
PmMasterId i;
int status;
int totalSt = XST_SUCCESS;
for (i = 0U; i < slave->reqsCnt; i++) {
if (slave->reqs[i]->info & PM_MASTER_WAKEUP_REQ_MASK) {
slave->reqs[i]->info &= ~PM_MASTER_WAKEUP_REQ_MASK;
PmDbg("%s->%s\n", PmStrNode(slave->node.nodeId),
PmStrNode(slave->reqs[i]->requestor->procs->node.nodeId));
PmProcFsm(slave->reqs[i]->requestor->procs, PM_PROC_EVENT_WAKE);
slave->reqs[i]->info &= ~PM_MASTER_WAKEUP_REQ_MASK;
status = PmProcFsm(slave->reqs[i]->requestor->procs,
PM_PROC_EVENT_WAKE);
if (XST_SUCCESS != status) {
/*
* Failed waking up processor, remember
* failure and try to wake-up others
*/
totalSt = status;
}
}
}
PmSlaveWakeDisable(slave);
return totalSt;
}
/**
@ -290,9 +306,10 @@ static void PmSlaveWakeMasters(PmSlave* const slave)
* clears the interrupt, meaning that there could be up to 31 irqs
* that would be lost if not handled immediately.
*/
void PmSlaveProcessWake(const u32 wakeMask)
int PmSlaveProcessWake(const u32 wakeMask)
{
u32 g;
int status = XST_SUCCESS;
u32 g, s, irqStatus;
if (!(PMU_LOCAL_GPI1_ENABLE_FPD_WAKE_GIC_PROX_MASK & wakeMask)) {
goto done;
@ -300,21 +317,21 @@ void PmSlaveProcessWake(const u32 wakeMask)
for (g = 0U; g < ARRAY_SIZE(gicProxyGroups_g); g++) {
/* Reading status register clears interrupts */
u32 s;
u32 irqStatus = XPfw_Read32(gicProxyGroups_g[g].baseAddr +
FPD_GICP_STATUS_OFFSET);
irqStatus = XPfw_Read32(gicProxyGroups_g[g].baseAddr +
FPD_GICP_STATUS_OFFSET);
for (s = 0U; (0U != irqStatus) && (s < ARRAY_SIZE(pmSlaves)); s++) {
if ((NULL != pmSlaves[s]->wake) &&
(pmSlaves[s]->wake->proxyIrqMask & irqStatus)) {
PmSlaveWakeMasters(pmSlaves[s]);
status = PmSlaveWakeMasters(pmSlaves[s]);
irqStatus &= ~pmSlaves[s]->wake->proxyIrqMask;
}
}
}
done:
return;
return status;
}
/**

View file

@ -45,8 +45,8 @@ typedef struct PmMaster PmMaster;
typedef struct PmRequirement PmRequirement;
typedef struct PmSlave PmSlave;
typedef u32 (*const PmSlaveFsmHandler)(PmSlave* const slave,
const PmStateId nextState);
typedef int (*const PmSlaveFsmHandler)(PmSlave* const slave,
const PmStateId nextState);
/*********************************************************************
* Macros
@ -165,12 +165,12 @@ extern PmGicProxyProperties gicProxyGroups_g[FPD_GICP_GROUP_MAX];
/*********************************************************************
* Function declarations
********************************************************************/
u32 PmUpdateSlave(PmSlave* const slave);
u32 PmCheckCapabilities(PmSlave* const slave, const u32 capabilities);
int PmUpdateSlave(PmSlave* const slave);
int PmCheckCapabilities(PmSlave* const slave, const u32 capabilities);
bool PmSlaveHasCapRequests(const PmSlave* const slave);
void PmSlaveProcessWake(const u32 wakeMask);
int PmSlaveProcessWake(const u32 wakeMask);
void PmSlaveWakeEnable(PmSlave* const slave);
void PmSlaveWakeDisable(PmSlave* const slave);

View file

@ -68,9 +68,9 @@ static const PmStateTran pmSramTransitions[] = {
*
* @return Status of performing transition action
*/
static u32 PmSramFsmHandler(PmSlave* const slave, const PmStateId nextState)
static int PmSramFsmHandler(PmSlave* const slave, const PmStateId nextState)
{
u32 status = PM_RET_ERROR_INTERNAL;
int status = XST_PM_INTERNAL;
PmSlaveSram* sram = (PmSlaveSram*)slave->node.derived;
switch (slave->node.currState) {
@ -84,6 +84,7 @@ static u32 PmSramFsmHandler(PmSlave* const slave, const PmStateId nextState)
/* ON -> OFF*/
status = sram->PwrDn();
} else {
status = XST_NO_FEATURE;
}
break;
case PM_SRAM_STATE_RET:
@ -96,24 +97,27 @@ static u32 PmSramFsmHandler(PmSlave* const slave, const PmStateId nextState)
/* RET -> OFF */
status = sram->PwrDn();
} else {
status = XST_NO_FEATURE;
}
break;
case PM_SRAM_STATE_OFF:
if (PM_SRAM_STATE_ON == nextState) {
/* OFF -> ON */
status = sram->PwrUp();
} else {
status = XST_NO_FEATURE;
}
break;
default:
status = XST_PM_INTERNAL;
PmDbg("ERROR: Unknown SRAM state #%d\n", slave->node.currState);
break;
}
if (status == XST_SUCCESS) {
if (XST_SUCCESS == status) {
slave->node.currState = nextState;
status = PM_RET_SUCCESS;
} else {
status = PM_RET_ERROR_FAILURE;
}
return status;
}

View file

@ -61,32 +61,37 @@ static const PmStateTran pmUsbTransitions[] = {
*
* @return Status of performing transition action
*/
static u32 PmUsbFsmHandler(PmSlave* const slave, const PmStateId nextState)
static int PmUsbFsmHandler(PmSlave* const slave, const PmStateId nextState)
{
u32 status = PM_RET_ERROR_INTERNAL;
int status = XST_PM_INTERNAL;
PmSlaveUsb* usb = (PmSlaveUsb*)slave->node.derived;
switch (slave->node.currState) {
case PM_USB_STATE_ON:
if (PM_USB_STATE_OFF == nextState) {
/* ON -> OFF*/
status = usb->PwrDn();
} else {
status = XST_NO_FEATURE;
}
break;
case PM_USB_STATE_OFF:
if (PM_USB_STATE_ON == nextState) {
/* OFF -> ON */
status = usb->PwrUp();
} else {
status = XST_NO_FEATURE;
}
break;
default:
status = XST_PM_INTERNAL;
PmDbg("ERROR: Unknown USB state #%d\n", slave->node.currState);
break;
}
if (status == XST_SUCCESS) {
if (XST_SUCCESS == status) {
slave->node.currState = nextState;
status = PM_RET_SUCCESS;
} else {
status = PM_RET_ERROR_FAILURE;
}
return status;
}

View file

@ -1,4 +1,4 @@
#ifndef ZYNQMP_XPFW_VERSION__H_
#define ZYNQMP_XPFW_VERSION__H_
#define ZYNQMP_XPFW_VERSION "2015.1-swbeta2-29-g7f18eaf0130e"
#define ZYNQMP_XPFW_VERSION "2015.1-swbeta2-30-g61a804cc37eb"
#endif