From 96122ae5a9487bab1d5d1d631565c289f2cdb075 Mon Sep 17 00:00:00 2001 From: Raja Das Date: Thu, 9 Jun 2016 02:08:03 -0500 Subject: Synchronization of Command Handling Change-Id: Iefec280c27f432c9624e8fd3abf78f6bb0ee3adb RTC: 150470 Reviewed-on: http://ralgit01.raleigh.ibm.com/gerrit1/25538 Tested-by: Jenkins Server Reviewed-by: Shakeeb A. Pasha B K Reviewed-by: Sachin Gupta --- sbe/sbefw/sbeSpMsg.H | 22 ++++++ sbe/sbefw/sbecmdprocessor.C | 134 ++++++++++++++++--------------- sbe/sbefw/sbecmdreceiver.C | 187 ++++++++++++++++++++++++++------------------ sbe/sbefw/sbeexeintf.H | 80 +++++++++++++++++-- sbe/sbefw/sbeirq.C | 9 ++- sbe/sbefw/sbemain.C | 7 +- 6 files changed, 287 insertions(+), 152 deletions(-) (limited to 'sbe') diff --git a/sbe/sbefw/sbeSpMsg.H b/sbe/sbefw/sbeSpMsg.H index be0d26e3..07c25c53 100644 --- a/sbe/sbefw/sbeSpMsg.H +++ b/sbe/sbefw/sbeSpMsg.H @@ -481,6 +481,28 @@ typedef struct { uint32_t prim_status:16 ; // Primary Response Status uint32_t sec_status:16 ; // Secondary Response Status + + /** + * @brief initialize the response status + **/ + void init() + { + prim_status = SBE_PRI_OPERATION_SUCCESSFUL; + sec_status = SBE_SEC_OPERATION_SUCCESSFUL; + } + + /** + * @brief set the primary and secondary status + * + * @param[in] i_prim Primary status + * @param[in] i_sec Secondary status + * + **/ + void setStatus(const uint16_t i_prim, const uint16_t i_sec) + { + prim_status = i_prim; + sec_status = i_sec; + } } sbeCmdRespHdr_t; extern sbeCmdRespHdr_t g_sbeCmdRespHdr; diff --git a/sbe/sbefw/sbecmdprocessor.C b/sbe/sbefw/sbecmdprocessor.C index f5fb0f90..7c525f56 100644 --- a/sbe/sbefw/sbecmdprocessor.C +++ b/sbe/sbefw/sbecmdprocessor.C @@ -1,3 +1,27 @@ +/* IBM_PROLOG_BEGIN_TAG */ +/* This is an automatically generated prolog. */ +/* */ +/* $Source: sbe/sbefw/sbecmdprocessor.C $ */ +/* */ +/* OpenPOWER sbe Project */ +/* */ +/* Contributors Listed Below - COPYRIGHT 2015,2016 */ +/* [+] International Business Machines Corp. */ +/* */ +/* */ +/* Licensed under the Apache License, Version 2.0 (the "License"); */ +/* you may not use this file except in compliance with the License. */ +/* You may obtain a copy of the License at */ +/* */ +/* http://www.apache.org/licenses/LICENSE-2.0 */ +/* */ +/* Unless required by applicable law or agreed to in writing, software */ +/* distributed under the License is distributed on an "AS IS" BASIS, */ +/* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or */ +/* implied. See the License for the specific language governing */ +/* permissions and limitations under the License. */ +/* */ +/* IBM_PROLOG_END_TAG */ /* * @file: ppe/sbe/sbefw/sbecmdprocessor.C * @@ -32,7 +56,7 @@ void sbeHandlePsuResponse (const uint32_t i_rc) do { - uint8_t l_count = 0; + uint8_t l_cnt = 0; switch (i_rc) { case SBE_SEC_COMMAND_CLASS_NOT_SUPPORTED: @@ -48,31 +72,24 @@ void sbeHandlePsuResponse (const uint32_t i_rc) g_sbeSbe2PsuRespHdr.setStatus(SBE_PRI_INVALID_COMMAND, i_rc); // Now Update SBE->PSU Mbx Reg4 with response - l_count = sizeof(g_sbeSbe2PsuRespHdr)/ + l_cnt = sizeof(g_sbeSbe2PsuRespHdr)/ sizeof(uint64_t); l_rc = sbeWriteSbe2PsuMbxReg(SBE_HOST_PSU_MBOX_REG4, reinterpret_cast( - &g_sbeSbe2PsuRespHdr), l_count, true); - if (SBE_SEC_OPERATION_SUCCESSFUL != l_rc) - { - break; - } + &g_sbeSbe2PsuRespHdr), l_cnt, true); break; case SBE_SEC_OS_FAILURE: // Set primary and secondary status - g_sbeSbe2PsuRespHdr.setStatus(SBE_PRI_GENERIC_EXECUTION_FAILURE, i_rc); + g_sbeSbe2PsuRespHdr.setStatus(SBE_PRI_GENERIC_EXECUTION_FAILURE, + i_rc); // Now Update SBE->PSU Mbx Reg4 with response - l_count = sizeof(g_sbeSbe2PsuRespHdr)/ + l_cnt = sizeof(g_sbeSbe2PsuRespHdr)/ sizeof(uint64_t); l_rc = sbeWriteSbe2PsuMbxReg(SBE_HOST_PSU_MBOX_REG4, reinterpret_cast( - &g_sbeSbe2PsuRespHdr), l_count, true); - if (SBE_SEC_OPERATION_SUCCESSFUL != l_rc) - { - break; - } + &g_sbeSbe2PsuRespHdr), l_cnt, true); break; case SBE_SEC_OPERATION_SUCCESSFUL: @@ -89,7 +106,6 @@ void sbeHandlePsuResponse (const uint32_t i_rc) } while(false); SBE_DEBUG(SBE_FUNC"l_rc[0x0%08X]", l_rc); - #undef SBE_FUNC } @@ -206,13 +222,13 @@ void sbeSyncCommandProcessor_routine(void *i_pArg) SBE_ENTER(SBE_FUNC); // Check the destination bit at the start - if(true == SbeRegAccess::theSbeRegAccess().isDestBitRuntime()) + if(SbeRegAccess::theSbeRegAccess().isDestBitRuntime()) { SBE_DEBUG(SBE_FUNC"Destination bit tells us to go to runtime"); (void)SbeRegAccess::theSbeRegAccess(). updateSbeState(SBE_STATE_RUNTIME); } - else if(true == SbeRegAccess::theSbeRegAccess().isIstepMode()) + else if(SbeRegAccess::theSbeRegAccess().isIstepMode()) { SBE_DEBUG(SBE_FUNC"Continuous IPL mode not set, will wait for " "commands..."); @@ -235,27 +251,47 @@ void sbeSyncCommandProcessor_routine(void *i_pArg) do { - if ( g_sbeIntrSource.isSet(SBE_INTERFACE_PSU) ) + // Local Variables + uint8_t l_cmdClass = 0; + uint8_t l_cmdOpCode = 0; + + // Check on the Rx Thread Interrupt Bits for Interrupt Status + if ( g_sbeIntrSource.isSet(SBE_RX_ROUTINE, + SBE_INTERFACE_PSU) ) { - l_primStatus = g_sbeSbe2PsuRespHdr.primStatus; l_rc = g_sbeSbe2PsuRespHdr.secStatus; + l_cmdClass = g_sbePsu2SbeCmdReqHdr.cmdClass; + l_cmdOpCode = g_sbePsu2SbeCmdReqHdr.command; + // Set this here, so that during response handling we know which + // interrupt we are processing, need not check for + // g_sbeIntrSource again + g_sbeIntrSource.setIntrSource(SBE_PROC_ROUTINE, + SBE_INTERFACE_PSU); } - else if ( g_sbeIntrSource.isSet(SBE_INTERFACE_FIFO) ) + else if ( g_sbeIntrSource.isSet(SBE_RX_ROUTINE, + SBE_INTERFACE_FIFO) ) { - l_primStatus = g_sbeCmdRespHdr.prim_status; l_rc = g_sbeCmdRespHdr.sec_status; + l_cmdClass = g_sbeFifoCmdHdr.cmdClass; + l_cmdOpCode = g_sbeFifoCmdHdr.command; + // Set this here, so that during response handling we know which + // interrupt we are processing, need not check for + // g_sbeIntrSource again + g_sbeIntrSource.setIntrSource(SBE_PROC_ROUTINE, + SBE_INTERFACE_FIFO); } else // SBE_INTERFACE_FIFO_RESET or SBE_INTERFACE_UNKNOWN { SBE_ERROR(SBE_FUNC"Unexpected interrupt communicated to the " - "processor thread. Interrupt source: 0x%02X", - g_sbeIntrSource.l_intrSource); + "processor thread. Interrupt source: 0x%02X 0x%02X", + g_sbeIntrSource.intrSource, g_sbeIntrSource.rxThrIntrSource); assert(false); break; } - SBE_DEBUG (SBE_FUNC"l_primStatus=[0x%04X], l_rc=[0x%04X]", - l_primStatus, l_rc); + SBE_DEBUG (SBE_FUNC"New cmd arrived, g_sbeSemCmdProcess.count=%d " + "l_primStatus=[0x%04X], l_rc=[0x%04X]", + g_sbeSemCmdProcess.count, l_primStatus, l_rc); // PK API failure if (l_rcPk != PK_OK) @@ -264,46 +300,19 @@ void sbeSyncCommandProcessor_routine(void *i_pArg) "l_rcPk=%d, g_sbeSemCmdRecv.count=%d", l_rcPk, g_sbeSemCmdRecv.count); - // if the command receiver thread already updated - // the response status codes, don't override them. - if (l_primStatus == SBE_PRI_OPERATION_SUCCESSFUL) - { - l_primStatus = SBE_PRI_INTERNAL_ERROR; - l_rc = SBE_SEC_OS_FAILURE; - } + // If it's a semphore_pend error then update the same to show + // internal failure + l_rc = SBE_SEC_OS_FAILURE; } - SBE_DEBUG(SBE_FUNC"unblocked"); - + // Check for error which Receiver thread might have set if (l_rc != SBE_SEC_OPERATION_SUCCESSFUL) { break; } - SBE_DEBUG(SBE_FUNC"New cmd arrived, g_sbeSemCmdProcess.count=%d", - g_sbeSemCmdProcess.count); - - uint8_t l_cmdClass = 0; - uint8_t l_cmdOpCode = 0; - - // @TODO via RTC: 128658 - // Review if Mutex protection is required - // for all the globals used between threads - - if ( g_sbeIntrSource.isSet(SBE_INTERFACE_PSU) ) - { - l_cmdClass = g_sbePsu2SbeCmdReqHdr.cmdClass; - l_cmdOpCode = g_sbePsu2SbeCmdReqHdr.command; - } - else if ( g_sbeIntrSource.isSet(SBE_INTERFACE_FIFO) ) - { - l_cmdClass = g_sbeFifoCmdHdr.cmdClass; - l_cmdOpCode = g_sbeFifoCmdHdr.command; - } - // Get the command function - sbeCmdFunc_t l_pFuncP = sbeFindCmdFunc (l_cmdClass, l_cmdOpCode) ; - + sbeCmdFunc_t l_pFuncP = sbeFindCmdFunc (l_cmdClass, l_cmdOpCode); assert( l_pFuncP ) // Call the ChipOp function @@ -312,23 +321,20 @@ void sbeSyncCommandProcessor_routine(void *i_pArg) } while(false); // Inner do..while loop ends here SBE_DEBUG(SBE_FUNC"l_rc=[0x%08X]", l_rc); - if ( g_sbeIntrSource.isSet(SBE_INTERFACE_PSU) ) + if ( g_sbeIntrSource.isSet(SBE_PROC_ROUTINE, SBE_INTERFACE_PSU) ) { sbeHandlePsuResponse (l_rc); // Enable Host interrupt - g_sbeIntrSource.clearIntrSource(SBE_INTERFACE_PSU); + g_sbeIntrSource.clearIntrSource(SBE_ALL_HANDLER,SBE_INTERFACE_PSU); pk_irq_enable(SBE_IRQ_HOST_PSU_INTR); } - else if ( g_sbeIntrSource.isSet(SBE_INTERFACE_FIFO) ) + else if ( g_sbeIntrSource.isSet(SBE_PROC_ROUTINE, SBE_INTERFACE_FIFO) ) { sbeHandleFifoResponse (l_rc); - // @TODO via RTC : 126147 - // Review all the scenarios - // Enable the new data available interrupt - g_sbeIntrSource.clearIntrSource(SBE_INTERFACE_FIFO); + g_sbeIntrSource.clearIntrSource(SBE_ALL_HANDLER,SBE_INTERFACE_FIFO); pk_irq_enable(SBE_IRQ_SBEFIFO_DATA); pk_irq_enable(SBE_IRQ_SBEFIFO_RESET); } diff --git a/sbe/sbefw/sbecmdreceiver.C b/sbe/sbefw/sbecmdreceiver.C index 94a44ce1..dd99da50 100644 --- a/sbe/sbefw/sbecmdreceiver.C +++ b/sbe/sbefw/sbecmdreceiver.C @@ -1,3 +1,27 @@ +/* IBM_PROLOG_BEGIN_TAG */ +/* This is an automatically generated prolog. */ +/* */ +/* $Source: sbe/sbefw/sbecmdreceiver.C $ */ +/* */ +/* OpenPOWER sbe Project */ +/* */ +/* Contributors Listed Below - COPYRIGHT 2015,2016 */ +/* [+] International Business Machines Corp. */ +/* */ +/* */ +/* Licensed under the Apache License, Version 2.0 (the "License"); */ +/* you may not use this file except in compliance with the License. */ +/* You may obtain a copy of the License at */ +/* */ +/* http://www.apache.org/licenses/LICENSE-2.0 */ +/* */ +/* Unless required by applicable law or agreed to in writing, software */ +/* distributed under the License is distributed on an "AS IS" BASIS, */ +/* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or */ +/* implied. See the License for the specific language governing */ +/* permissions and limitations under the License. */ +/* */ +/* IBM_PROLOG_END_TAG */ /* * @file: ppe/sbe/sbefw/sbecmdreceiver.C * @@ -22,7 +46,7 @@ sbeFifoCmdReqBuf_t g_sbeFifoCmdHdr; sbeCmdRespHdr_t g_sbeCmdRespHdr; sbePsu2SbeCmdReqHdr_t g_sbePsu2SbeCmdReqHdr; sbeSbe2PsuRespHdr_t g_sbeSbe2PsuRespHdr; -sbeIntrHandle_t g_sbeIntrSource ; +sbeIntrHandle_t g_sbeIntrSource; ////////////////////////////////////////////////////// ////////////////////////////////////////////////////// @@ -30,6 +54,7 @@ void sbeCommandReceiver_routine(void *i_pArg) { #define SBE_FUNC " sbeCommandReceiver_routine " SBE_ENTER(SBE_FUNC); + uint32_t l_rc = SBE_SEC_OPERATION_SUCCESSFUL; // Update SBE msgg reg to indicate that control loop // is ready now to receive data on its interfaces @@ -37,23 +62,11 @@ void sbeCommandReceiver_routine(void *i_pArg) do { - uint32_t l_rc = SBE_SEC_OPERATION_SUCCESSFUL; - // @TODO via RTC: 128944 // Read Scratchpad - // Wait for new data in FIFO or FIFO reset interrupt or PSU interrupt int l_rcPk = pk_semaphore_pend (&g_sbeSemCmdRecv, PK_WAIT_FOREVER); - // @TODO via RTC: 128658 - // Review if Mutex protection is required - // for all the globals used between threads - g_sbeCmdRespHdr.prim_status = SBE_PRI_OPERATION_SUCCESSFUL; - g_sbeCmdRespHdr.sec_status = SBE_SEC_OPERATION_SUCCESSFUL; - g_sbeFifoCmdHdr.cmdClass = SBE_CMD_CLASS_UNKNOWN; - g_sbePsu2SbeCmdReqHdr.init(); - - // inner loop for command handling do { uint8_t l_cmdClass = SBE_CMD_CLASS_UNKNOWN; @@ -65,14 +78,15 @@ void sbeCommandReceiver_routine(void *i_pArg) break; } - SBE_DEBUG(SBE_FUNC"unblocked"); + SBE_DEBUG(SBE_FUNC"Receiver unblocked"); // The responsibility of this thread is limited to reading off // the FIFO or PSU interfaces to be able to decode the command // class and the command opcode parameters. // Received FIFO Reset interrupt - if ( g_sbeIntrSource.isSet(SBE_INTERFACE_FIFO_RESET) ) + if ( g_sbeIntrSource.isSet(SBE_INTERRUPT_ROUTINE, + SBE_INTERFACE_FIFO_RESET) ) { SBE_ERROR(SBE_FUNC"FIFO reset received"); l_rc = SBE_FIFO_RESET_RECEIVED; @@ -80,71 +94,85 @@ void sbeCommandReceiver_routine(void *i_pArg) } // Received PSU interrupt - if ( g_sbeIntrSource.isSet(SBE_INTERFACE_PSU) ) + if ( g_sbeIntrSource.isSet(SBE_INTERRUPT_ROUTINE, + SBE_INTERFACE_PSU) ) { + //Clear the Interrupt Source bit for PSU + g_sbeIntrSource.clearIntrSource(SBE_INTERRUPT_ROUTINE, + SBE_INTERFACE_PSU); + g_sbeIntrSource.setIntrSource(SBE_RX_ROUTINE, + SBE_INTERFACE_PSU); // First clear PSU->SBE DB bit 0 l_rc = sbeClearPsu2SbeDbBitX(SBE_PSU2SBE_DOORBELL_CLEAR_BIT0); - if (SBE_SEC_OPERATION_SUCCESSFUL != l_rc) + if (l_rc) { break; } + // Initialize the g_sbePsu2SbeCmdReqHdr + g_sbePsu2SbeCmdReqHdr.init(); // Read the request field from PSU->SBE Mbx Reg0 - uint8_t l_count = sizeof(g_sbePsu2SbeCmdReqHdr)/ - sizeof(uint64_t); - l_rc = sbeReadPsu2SbeMbxReg (SBE_HOST_PSU_MBOX_REG0, - l_count, (uint64_t *)&g_sbePsu2SbeCmdReqHdr); + uint8_t l_cnt = sizeof(g_sbePsu2SbeCmdReqHdr)/sizeof(uint64_t); + + l_rc = sbeReadPsu2SbeMbxReg(SBE_HOST_PSU_MBOX_REG0, l_cnt, + (uint64_t *)&g_sbePsu2SbeCmdReqHdr); + g_sbeSbe2PsuRespHdr.init(); l_cmdClass = g_sbePsu2SbeCmdReqHdr.cmdClass; l_command = g_sbePsu2SbeCmdReqHdr.command; } // end if loop for PSU interface chipOp handling // Received FIFO New Data interrupt - else if ( g_sbeIntrSource.isSet(SBE_INTERFACE_FIFO) ) { - - // This thread will attempt to unblock the command processor - // thread on the following scenarios: - // - Normal scenarios where SBE would need to respond to FSP - // via downstream FIFO. This includes SUCCESS cases as well as - // the cases for Invalid Data sequence or Command validation - // failure. - // - if there is a need to handle FIFO reset - - // Accordingly, this will update g_sbeCmdRespHdr.prim_status - // and g_sbeCmdRespHdr.sec_status for command processor thread - // to handle them later in the sequence. - - l_cmdClass = SBE_CMD_CLASS_UNKNOWN; - uint32_t len = sizeof(g_sbeFifoCmdHdr)/sizeof(uint32_t); - l_rc = sbeUpFifoDeq_mult ( len, (uint32_t *)&g_sbeFifoCmdHdr, - false ); - - // If FIFO reset is requested, - if (l_rc == SBE_FIFO_RESET_RECEIVED) + else if ( g_sbeIntrSource.isSet(SBE_INTERRUPT_ROUTINE, + SBE_INTERFACE_FIFO) ) { - SBE_ERROR(SBE_FUNC"FIFO reset received"); - break; - } - - // If we received EOT out-of-sequence - if ( (l_rc == SBE_SEC_UNEXPECTED_EOT_INSUFFICIENT_DATA) || - (l_rc == SBE_SEC_UNEXPECTED_EOT_EXCESS_DATA) ) - { - SBE_ERROR(SBE_FUNC"sbeUpFifoDeq_mult failure, " - " l_rc=[0x%08X]", l_rc); - g_sbeCmdRespHdr.prim_status = - SBE_PRI_INVALID_DATA; - g_sbeCmdRespHdr.sec_status = l_rc; + //Clear the Interrupt Source bit for FIFO + g_sbeIntrSource.clearIntrSource(SBE_INTERRUPT_ROUTINE, + SBE_INTERFACE_FIFO); + g_sbeIntrSource.setIntrSource(SBE_RX_ROUTINE, + SBE_INTERFACE_FIFO); + + // This thread will attempt to unblock the command processor + // thread on the following scenarios: + // - Normal scenarios where SBE would need to respond to FSP + // via downstream FIFO. This includes SUCCESS cases as well + // as the cases for Invalid Data sequence or Command + // validation failure. + // - if there is a need to handle FIFO reset + + // Accordingly, this will update g_sbeCmdRespHdr.prim_status + // and g_sbeCmdRespHdr.sec_status for command processor thread + // to handle them later in the sequence. + + g_sbeFifoCmdHdr.cmdClass = SBE_CMD_CLASS_UNKNOWN; + g_sbeCmdRespHdr.init(); + uint32_t len = sizeof(g_sbeFifoCmdHdr)/sizeof(uint32_t); + l_rc = sbeUpFifoDeq_mult ( len, (uint32_t *)&g_sbeFifoCmdHdr, + false ); + + // If FIFO reset is requested, + if (l_rc == SBE_FIFO_RESET_RECEIVED) + { + SBE_ERROR(SBE_FUNC"FIFO reset received"); + break; + } - // Reassign l_rc to Success to Unblock command processor - // thread and let that take the necessary action. - l_rc = SBE_SEC_OPERATION_SUCCESSFUL; - break; - } + // If we received EOT out-of-sequence + if ( (l_rc == SBE_SEC_UNEXPECTED_EOT_INSUFFICIENT_DATA) || + (l_rc == SBE_SEC_UNEXPECTED_EOT_EXCESS_DATA) ) + { + SBE_ERROR(SBE_FUNC"sbeUpFifoDeq_mult failure, " + " l_rc=[0x%08X]", l_rc); + g_sbeCmdRespHdr.setStatus(SBE_PRI_INVALID_DATA, l_rc); - l_cmdClass = g_sbeFifoCmdHdr.cmdClass; - l_command = g_sbeFifoCmdHdr.command; + // Reassign l_rc to Success to Unblock command processor + // thread and let that take the necessary action. + l_rc = SBE_SEC_OPERATION_SUCCESSFUL; + break; + } + l_cmdClass = g_sbeFifoCmdHdr.cmdClass; + l_command = g_sbeFifoCmdHdr.command; } // end else if loop for FIFO interface chipOp handling // Any other FIFO access issue @@ -160,15 +188,15 @@ void sbeCommandReceiver_routine(void *i_pArg) { // Command Validation failed; SBE_ERROR(SBE_FUNC"Command validation failed"); - if ( g_sbeIntrSource.isSet(SBE_INTERFACE_PSU) ) + if ( g_sbeIntrSource.isSet(SBE_RX_ROUTINE, + SBE_INTERFACE_PSU) ) { - g_sbeSbe2PsuRespHdr.primStatus = SBE_PRI_INVALID_COMMAND; - g_sbeSbe2PsuRespHdr.secStatus = l_rc; + g_sbeSbe2PsuRespHdr.setStatus(SBE_PRI_INVALID_COMMAND,l_rc); } - else if ( g_sbeIntrSource.isSet(SBE_INTERFACE_FIFO) ) + else if ( g_sbeIntrSource.isSet(SBE_RX_ROUTINE, + SBE_INTERFACE_FIFO) ) { - g_sbeCmdRespHdr.prim_status = SBE_PRI_INVALID_COMMAND; - g_sbeCmdRespHdr.sec_status = l_rc; + g_sbeCmdRespHdr.setStatus(SBE_PRI_INVALID_COMMAND, l_rc); } // Reassign l_rc to Success to Unblock command processor @@ -195,14 +223,17 @@ void sbeCommandReceiver_routine(void *i_pArg) // Collect FFDC? } - if ( g_sbeIntrSource.isSet(SBE_INTERFACE_FIFO) ) + if ( g_sbeIntrSource.isSet(SBE_RX_ROUTINE, SBE_INTERFACE_FIFO) ) { - g_sbeIntrSource.clearIntrSource(SBE_INTERFACE_FIFO); + g_sbeIntrSource.clearIntrSource(SBE_ALL_HANDLER, + SBE_INTERFACE_FIFO); } - if ( g_sbeIntrSource.isSet(SBE_INTERFACE_FIFO_RESET) ) + if ( g_sbeIntrSource.isSet(SBE_INTERRUPT_ROUTINE, + SBE_INTERFACE_FIFO_RESET) ) { - g_sbeIntrSource.clearIntrSource(SBE_INTERFACE_FIFO_RESET); + g_sbeIntrSource.clearIntrSource(SBE_ALL_HANDLER, + SBE_INTERFACE_FIFO_RESET); } pk_irq_enable(SBE_IRQ_SBEFIFO_DATA); @@ -231,14 +262,18 @@ void sbeCommandReceiver_routine(void *i_pArg) "l_rcPk=[%d], g_sbeSemCmdProcess.count=[%d], l_rc=[%d]", l_rcPk, g_sbeSemCmdProcess.count, l_rc); - if ( g_sbeIntrSource.isSet(SBE_INTERFACE_PSU) ) + if ( g_sbeIntrSource.isSet(SBE_RX_ROUTINE, + SBE_INTERFACE_PSU) ) { - g_sbeIntrSource.clearIntrSource(SBE_INTERFACE_PSU); + g_sbeIntrSource.clearIntrSource(SBE_ALL_HANDLER, + SBE_INTERFACE_PSU); pk_irq_enable(SBE_IRQ_HOST_PSU_INTR); } - else if ( g_sbeIntrSource.isSet(SBE_INTERFACE_FIFO) ) + else if ( g_sbeIntrSource.isSet(SBE_RX_ROUTINE, + SBE_INTERFACE_FIFO) ) { - g_sbeIntrSource.clearIntrSource(SBE_INTERFACE_FIFO); + g_sbeIntrSource.clearIntrSource(SBE_ALL_HANDLER, + SBE_INTERFACE_FIFO); pk_irq_enable(SBE_IRQ_SBEFIFO_DATA); } continue; diff --git a/sbe/sbefw/sbeexeintf.H b/sbe/sbefw/sbeexeintf.H index 6f43784d..e871632a 100644 --- a/sbe/sbefw/sbeexeintf.H +++ b/sbe/sbefw/sbeexeintf.H @@ -1,3 +1,27 @@ +/* IBM_PROLOG_BEGIN_TAG */ +/* This is an automatically generated prolog. */ +/* */ +/* $Source: sbe/sbefw/sbeexeintf.H $ */ +/* */ +/* OpenPOWER sbe Project */ +/* */ +/* Contributors Listed Below - COPYRIGHT 2015,2016 */ +/* [+] International Business Machines Corp. */ +/* */ +/* */ +/* Licensed under the Apache License, Version 2.0 (the "License"); */ +/* you may not use this file except in compliance with the License. */ +/* You may obtain a copy of the License at */ +/* */ +/* http://www.apache.org/licenses/LICENSE-2.0 */ +/* */ +/* Unless required by applicable law or agreed to in writing, software */ +/* distributed under the License is distributed on an "AS IS" BASIS, */ +/* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or */ +/* implied. See the License for the specific language governing */ +/* permissions and limitations under the License. */ +/* */ +/* IBM_PROLOG_END_TAG */ /* * @file: ppe/sbe/sbefw/sbeexeintf.H * @@ -89,27 +113,69 @@ typedef enum SBE_INTERFACE_FIFO_RESET = 0x04, } sbeInterfaceSrc_t; +/* + * @brief Enum for Handler, handling the interrupt and setting/clearing the + * interrupt variable + */ +typedef enum +{ + SBE_ALL_HANDLER = 0x0, + SBE_INTERRUPT_ROUTINE = 0x1, + SBE_RX_ROUTINE = 0x2, + SBE_PROC_ROUTINE = 0x3, +} sbeHandler_t; + /** * @brief structure for SBE external Interrupt handling * */ typedef struct { - uint8_t l_intrSource; + uint8_t intrSource; + uint8_t rxThrIntrSource; + uint8_t procThrIntrSource; - void setIntrSource(const sbeInterfaceSrc_t i_val) + void setIntrSource(const sbeHandler_t i_handler, + const sbeInterfaceSrc_t i_val) { - l_intrSource |= i_val; + switch(i_handler) + { + case SBE_INTERRUPT_ROUTINE: intrSource |= i_val; break; + case SBE_RX_ROUTINE: rxThrIntrSource |= i_val; break; + case SBE_PROC_ROUTINE: procThrIntrSource |= i_val; break; + case SBE_ALL_HANDLER: break; + } } - void clearIntrSource(const sbeInterfaceSrc_t i_val) + void clearIntrSource(const sbeHandler_t i_handler, + const sbeInterfaceSrc_t i_val) { - l_intrSource &= ~i_val; + switch(i_handler) + { + case SBE_INTERRUPT_ROUTINE: intrSource &= ~i_val; break; + case SBE_RX_ROUTINE: rxThrIntrSource &= ~i_val; break; + case SBE_PROC_ROUTINE: procThrIntrSource &= ~i_val; break; + case SBE_ALL_HANDLER: + { + intrSource &= ~i_val; + rxThrIntrSource &= ~i_val; + procThrIntrSource &= ~i_val; + break; + } + } } - bool isSet (const sbeInterfaceSrc_t i_val) + bool isSet (const sbeHandler_t i_handler, const sbeInterfaceSrc_t i_val) { - return (l_intrSource & i_val); + bool l_ret = false; + switch(i_handler) + { + case SBE_INTERRUPT_ROUTINE: l_ret = (intrSource & i_val); break; + case SBE_RX_ROUTINE: l_ret = (rxThrIntrSource & i_val); break; + case SBE_PROC_ROUTINE: l_ret = (procThrIntrSource & i_val); break; + case SBE_ALL_HANDLER: break; + } + return l_ret; } } sbeIntrHandle_t; extern sbeIntrHandle_t g_sbeIntrSource ; diff --git a/sbe/sbefw/sbeirq.C b/sbe/sbefw/sbeirq.C index efcb210b..33c63761 100644 --- a/sbe/sbefw/sbeirq.C +++ b/sbe/sbefw/sbeirq.C @@ -56,16 +56,19 @@ void sbe_interrupt_handler (void *i_pArg, PkIrqId i_irq) switch (i_irq) { case SBE_IRQ_HOST_PSU_INTR: - g_sbeIntrSource.setIntrSource(SBE_INTERFACE_PSU); + g_sbeIntrSource.setIntrSource(SBE_INTERRUPT_ROUTINE, + SBE_INTERFACE_PSU); break; case SBE_IRQ_SBEFIFO_DATA: - g_sbeIntrSource.setIntrSource(SBE_INTERFACE_FIFO); + g_sbeIntrSource.setIntrSource(SBE_INTERRUPT_ROUTINE, + SBE_INTERFACE_FIFO); pk_irq_disable(SBE_IRQ_SBEFIFO_RESET); break; case SBE_IRQ_SBEFIFO_RESET: - g_sbeIntrSource.setIntrSource(SBE_INTERFACE_FIFO_RESET); + g_sbeIntrSource.setIntrSource(SBE_INTERRUPT_ROUTINE, + SBE_INTERFACE_FIFO_RESET); pk_irq_disable(SBE_IRQ_SBEFIFO_DATA); break; diff --git a/sbe/sbefw/sbemain.C b/sbe/sbefw/sbemain.C index 201e6ad4..accf5e98 100644 --- a/sbe/sbefw/sbemain.C +++ b/sbe/sbefw/sbemain.C @@ -49,6 +49,9 @@ PkSemaphore g_sbeSemCmdRecv; PkSemaphore g_sbeSemCmdProcess; +// Max defines for Semaphores +static uint32_t MAX_SEMAPHORE_COUNT = 3; + //////////////////////////////////////////////////////////////// // @brief Stacks for Non-critical Interrupts and Threads //////////////////////////////////////////////////////////////// @@ -126,12 +129,12 @@ uint32_t sbeInitSems(void) do { - l_rc = pk_semaphore_create(&g_sbeSemCmdRecv, 0, 1); + l_rc = pk_semaphore_create(&g_sbeSemCmdRecv, 0, MAX_SEMAPHORE_COUNT); if (l_rc) { break; } - l_rc = pk_semaphore_create(&g_sbeSemCmdProcess, 0, 1); + l_rc = pk_semaphore_create(&g_sbeSemCmdProcess, 0, MAX_SEMAPHORE_COUNT); if (l_rc) { break; -- cgit v1.2.1