summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorvanlee <vanlee@us.ibm.com>2013-05-14 14:54:27 -0500
committerA. Patrick Williams III <iawillia@us.ibm.com>2013-06-12 09:27:05 -0500
commit36a701ad9bcbcb3a997d76d11fe38d7726d1c4e7 (patch)
tree56c3c21170fe54032aa0cb4ed720f653d5e207a8
parentd2a31c241a1a8221bc3932bdfacfc949fb6ec70c (diff)
downloadblackbird-hostboot-36a701ad9bcbcb3a997d76d11fe38d7726d1c4e7.tar.gz
blackbird-hostboot-36a701ad9bcbcb3a997d76d11fe38d7726d1c4e7.zip
Add interface to do bus callout in Hostboot
Change-Id: If169d997a0aba49a81ef834d7806e1e589dc3bff RTC: 69459 Reviewed-on: http://gfw160.austin.ibm.com:8080/gerrit/4503 Tested-by: Jenkins Server Reviewed-by: Brian H. Horton <brianh@linux.ibm.com> Reviewed-by: A. Patrick Williams III <iawillia@us.ibm.com>
-rw-r--r--src/include/usr/errl/errlentry.H15
-rw-r--r--src/include/usr/errl/errludcallout.H20
-rw-r--r--src/include/usr/hwas/common/hwasCallout.H34
-rw-r--r--src/usr/errl/errlentry.C50
-rw-r--r--src/usr/errl/errludcallout.C33
-rw-r--r--src/usr/errl/plugins/errludcallout.H62
-rw-r--r--src/usr/hwas/common/hwasCallout.C131
-rw-r--r--src/usr/hwas/hwasPlatCallout.C16
8 files changed, 306 insertions, 55 deletions
diff --git a/src/include/usr/errl/errlentry.H b/src/include/usr/errl/errlentry.H
index a34633df9..96598e03a 100644
--- a/src/include/usr/errl/errlentry.H
+++ b/src/include/usr/errl/errlentry.H
@@ -423,6 +423,21 @@ public:
void removeBackTrace();
/**
+ * @brief Add a bus callout
+ *
+ * @param[in] i_target1 The hardware bus endpoint target1
+ * @param[in] i_target2 The hardware bus endpoint target2
+ * @param[in] i_busType The hardware bus type
+ * @param[in] i_priority Priority of the callout
+ *
+ * @return void
+ */
+ void addBusCallout(const TARGETING::Target *i_target1,
+ const TARGETING::Target *i_target2,
+ const HWAS::busTypeEnum i_busType,
+ const HWAS::callOutPriority i_priority);
+
+ /**
* @brief Add a hardware callout
*
* @param[in] i_target The hardware target
diff --git a/src/include/usr/errl/errludcallout.H b/src/include/usr/errl/errludcallout.H
index 9357baa3f..80530edd2 100644
--- a/src/include/usr/errl/errludcallout.H
+++ b/src/include/usr/errl/errludcallout.H
@@ -52,6 +52,26 @@ class ErrlUserDetailsCallout : public ErrlUserDetails
public:
/**
+ * @brief Construct a bus callout user detail
+ *
+ * @param[in] i_pTarget1Data The hardware target1 data
+ * @param[in] i_target1DataLength length of i_pTarget1Data
+ * @param[in] i_pTarget2Data The hardware target2 data
+ * @param[in] i_target2DataLength length of i_pTarget2Data
+ * @param[in] i_busType bus type Enum
+ * @param[in] i_priority Priority of the callout
+ *
+ * @return void
+ */
+ ErrlUserDetailsCallout(
+ const void *i_pTarget1Data,
+ uint32_t i_target1DataLength,
+ const void *i_pTarget2Data,
+ uint32_t i_target2DataLength,
+ const HWAS::busTypeEnum i_busType,
+ const HWAS::callOutPriority i_priority);
+
+ /**
* @brief Construct a hardware callout user detail
*
* @param[in] i_pTargetData The hardware target data
diff --git a/src/include/usr/hwas/common/hwasCallout.H b/src/include/usr/hwas/common/hwasCallout.H
index 674dc5d34..c82e3e218 100644
--- a/src/include/usr/hwas/common/hwasCallout.H
+++ b/src/include/usr/hwas/common/hwasCallout.H
@@ -122,9 +122,20 @@ enum callOutPriority
SRCI_PRIORITY_HIGH = 6
};
+enum busTypeEnum
+{
+ FSI_BUS_TYPE = 1,
+ DMI_BUS_TYPE = 2,
+ A_BUS_TYPE = 3,
+ X_BUS_TYPE = 4,
+ I2C_BUS_TYPE = 5,
+ PSI_BUS_TYPE = 6
+};
+
//
const uint8_t HW_CALLOUT = 0x01;
const uint8_t PROCEDURE_CALLOUT = 0x02;
+const uint8_t BUS_CALLOUT = 0x03;
const uint8_t TARGET_IS_SENTINEL = 0xF0;
@@ -142,6 +153,9 @@ typedef struct callout_ud
struct { // callout
epubProcedureID procedure; // uint32_t
};
+ struct {
+ busTypeEnum busType;
+ };
};
} callout_ud_t;
@@ -199,6 +213,26 @@ errlHndl_t platHandleHWCallout(
errlHndl_t i_errl,
GARD_ErrorType i_gardErrorType);
+/**
+ * @brief platform specific code to handle a bus callout that has been
+ * found in an errlog
+ *
+ * @param[in] i_pTarget1 target endpoint1
+ * @param[in] i_pTarget2 target endpoint2
+ * @param[in] i_busType bus type Enum
+ * @param[in] i_priority Enum indicating the priority of the callout
+ * @param[in] i_errl errlHnld for this errlog
+ *
+ * @return errlHndl_t valid errlHndl_t handle if there was an error,
+ * NULL if no errors;
+ */
+errlHndl_t platHandleBusCallout(
+ TARGETING::Target *i_pTarget1,
+ TARGETING::Target *i_pTarget2,
+ busTypeEnum i_busType,
+ callOutPriority i_priority,
+ errlHndl_t i_errl);
+
#endif // not PARSER
}; // end namespace
diff --git a/src/usr/errl/errlentry.C b/src/usr/errl/errlentry.C
index 62d47e598..fd9d76857 100644
--- a/src/usr/errl/errlentry.C
+++ b/src/usr/errl/errlentry.C
@@ -299,6 +299,56 @@ void ErrlEntry::removeBackTrace()
////////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////
+void ErrlEntry::addBusCallout(const TARGETING::Target *i_target_endp1,
+ const TARGETING::Target *i_target_endp2,
+ const HWAS::busTypeEnum i_busType,
+ const HWAS::callOutPriority i_priority)
+{
+ TRACFCOMP(g_trac_errl, ENTER_MRK"addBusCallout(%p, %p, %d, 0x%x)",
+ i_target_endp1, i_target_endp2, i_busType, i_priority);
+
+ TARGETING::EntityPath ep1, ep2;
+ const void *pData1, *pData2;
+ uint32_t size1, size2;
+
+ if (i_target_endp1 == TARGETING::MASTER_PROCESSOR_CHIP_TARGET_SENTINEL)
+ {
+ size1 = sizeof(HWAS::TARGET_IS_SENTINEL);
+ pData1 = &HWAS::TARGET_IS_SENTINEL;
+ }
+ else
+ { // we got a non MASTER_SENTINEL target, therefore the targeting
+ // module is loaded, therefore we can make this call.
+ ep1 = i_target_endp1->getAttr<TARGETING::ATTR_PHYS_PATH>();
+ size1 = TARGETING::EntityPath::MAX_PATH_ELEMENTS - ep1.size();
+ size1 *= sizeof(TARGETING::EntityPath::PathElement);
+ size1 = sizeof(ep1) - size1;
+ pData1 = &ep1;
+ }
+
+ if (i_target_endp2 == TARGETING::MASTER_PROCESSOR_CHIP_TARGET_SENTINEL)
+ {
+ size2 = sizeof(HWAS::TARGET_IS_SENTINEL);
+ pData2 = &HWAS::TARGET_IS_SENTINEL;
+ }
+ else
+ { // we got a non MASTER_SENTINEL target, therefore the targeting
+ // module is loaded, therefore we can make this call.
+ ep2 = i_target_endp2->getAttr<TARGETING::ATTR_PHYS_PATH>();
+ size2 = TARGETING::EntityPath::MAX_PATH_ELEMENTS - ep2.size();
+ size2 *= sizeof(TARGETING::EntityPath::PathElement);
+ size2 = sizeof(ep2) - size2;
+ pData2 = &ep2;
+ }
+
+ ErrlUserDetailsCallout( pData1, size1, pData2, size2, i_busType,
+ i_priority).addToLog(this);
+
+} // addBusCallout
+
+
+////////////////////////////////////////////////////////////////////////////
+////////////////////////////////////////////////////////////////////////////
void ErrlEntry::addHwCallout(const TARGETING::Target *i_target,
const HWAS::callOutPriority i_priority,
const HWAS::DeconfigEnum i_deconfigState,
diff --git a/src/usr/errl/errludcallout.C b/src/usr/errl/errludcallout.C
index 3fa43078e..c206a628a 100644
--- a/src/usr/errl/errludcallout.C
+++ b/src/usr/errl/errludcallout.C
@@ -38,6 +38,39 @@ namespace ERRORLOG
extern TARGETING::TARG_TD_t g_trac_errl;
//------------------------------------------------------------------------------
+// Bus callout
+ErrlUserDetailsCallout::ErrlUserDetailsCallout(
+ const void *i_pTarget1Data,
+ uint32_t i_target1DataLength,
+ const void *i_pTarget2Data,
+ uint32_t i_target2DataLength,
+ const HWAS::busTypeEnum i_busType,
+ const HWAS::callOutPriority i_priority)
+{
+ TRACDCOMP(g_trac_errl, "BusCallout entry");
+
+ // Set up ErrlUserDetails instance variables
+ iv_CompId = ERRL_COMP_ID;
+ iv_Version = 1;
+ iv_SubSection = ERRL_UDT_CALLOUT;
+
+ uint32_t pDataLength = sizeof(HWAS::callout_ud_t) +
+ i_target1DataLength + i_target2DataLength;
+ HWAS::callout_ud_t *pData;
+ pData = reinterpret_cast<HWAS::callout_ud_t *>
+ (reallocUsrBuf(pDataLength));
+ pData->type = HWAS::BUS_CALLOUT;
+ pData->busType = i_busType;
+ pData->priority = i_priority;
+ char * l_ptr = (char *)(++pData);
+ memcpy(l_ptr, i_pTarget1Data, i_target1DataLength);
+ memcpy(l_ptr + i_target1DataLength, i_pTarget2Data, i_target2DataLength);
+
+ TRACDCOMP(g_trac_errl, "BusCallout exit; pDataLength %d", pDataLength);
+
+} // Bus callout
+
+//------------------------------------------------------------------------------
// Hardware callout
ErrlUserDetailsCallout::ErrlUserDetailsCallout(
const void *i_pTargetData,
diff --git a/src/usr/errl/plugins/errludcallout.H b/src/usr/errl/plugins/errludcallout.H
index a4d7590a8..6d27391a9 100644
--- a/src/usr/errl/plugins/errludcallout.H
+++ b/src/usr/errl/plugins/errludcallout.H
@@ -73,6 +73,37 @@ public:
switch (pData->type)
{
+ case HWAS::BUS_CALLOUT:
+ {
+ char * l_busType;
+ switch (ntohl(pData->busType))
+ {
+ case HWAS::FSI_BUS_TYPE: l_busType = "FSI BUS";
+ break;
+ case HWAS::DMI_BUS_TYPE: l_busType = "DMI BUS";
+ break;
+ case HWAS::A_BUS_TYPE: l_busType = "A BUS";
+ break;
+ case HWAS::X_BUS_TYPE: l_busType = "X BUS";
+ break;
+ case HWAS::I2C_BUS_TYPE: l_busType = "I2C BUS";
+ break;
+ case HWAS::PSI_BUS_TYPE: l_busType = "PSI BUS";
+ break;
+ default: l_busType = "UNKNOWN BUS";
+ break;
+ }
+
+ i_parser.PrintString( "Callout Bus type", l_busType );
+
+ // what follows the pData structure is Two entity paths
+ // print them out
+ uint8_t *l_ptr = reinterpret_cast<uint8_t *>(pData+1);
+ printEntityPath(l_ptr, i_parser, "Target1");
+ printEntityPath(l_ptr, i_parser, "Target2");
+
+ break; // BUS_CALLOUT
+ }
case HWAS::HW_CALLOUT:
{
i_parser.PrintString( "Callout type", "Hardware Callout");
@@ -80,17 +111,7 @@ public:
// what follows the pData structure is an entity path
// print it first
uint8_t *l_ptr = reinterpret_cast<uint8_t *>(pData+1);
- if (*l_ptr == 0xF0)
- {
- i_parser.PrintString("Target",
- "MASTER_PROCESSOR_CHIP_TARGET_SENTINEL");
- }
- else
- {
- char outString[128];
- l_ptr = errlud_parse_entity_path(l_ptr, outString);
- i_parser.PrintString("Target", outString);
- }
+ printEntityPath(l_ptr, i_parser, "Target");
i_parser.PrintNumber( "CPU id", "0x%X", ntohl(pData->cpuid) );
@@ -209,6 +230,25 @@ private:
ErrlUserDetailsParserCallout(const ErrlUserDetailsParserCallout &);
ErrlUserDetailsParserCallout & operator=(
const ErrlUserDetailsParserCallout &);
+
+ void printEntityPath(uint8_t * & io_ptr,
+ ErrlUsrParser & i_parser,
+ const char * i_label) const
+ {
+ if (*io_ptr == HWAS::TARGET_IS_SENTINEL)
+ {
+ i_parser.PrintString( i_label,
+ "MASTER_PROCESSOR_CHIP_TARGET_SENTINEL");
+ ++io_ptr;
+ }
+ else
+ {
+ char outString[128];
+ io_ptr = errlud_parse_entity_path(io_ptr, outString);
+ i_parser.PrintString(i_label, outString);
+ }
+ }
+
};
}
diff --git a/src/usr/hwas/common/hwasCallout.C b/src/usr/hwas/common/hwasCallout.C
index 64cc7b92c..f82130a94 100644
--- a/src/usr/hwas/common/hwasCallout.C
+++ b/src/usr/hwas/common/hwasCallout.C
@@ -45,6 +45,56 @@ namespace HWAS
using namespace HWAS::COMMON;
+bool retrieveTarget(uint8_t * & io_uData,
+ TARGETING::Target * & o_pTarget, errlHndl_t i_errl)
+{
+ bool l_err = false;
+
+ // data is either a token indicating it's the
+ // MASTER_PROCESSOR_CHIP_TARGET_SENTINEL
+ // or it's the EntityPath - getAttr<TARGETING::ATTR_PHYS_PATH>()
+ if (*io_uData != TARGET_IS_SENTINEL)
+ {
+ // convert the EntityPath to a Target pointer
+ TARGETING::EntityPath ep, *ep_ptr;
+ uint32_t size;
+ ep_ptr = (TARGETING::EntityPath *)io_uData;
+ size = TARGETING::EntityPath::MAX_PATH_ELEMENTS - ep_ptr->size();
+ size *= sizeof(TARGETING::EntityPath::PathElement);
+ size = sizeof(ep) - size;
+ memcpy(&ep, io_uData, size);
+ o_pTarget = TARGETING::targetService().toTarget(ep);
+ io_uData += size;
+
+ if (unlikely(o_pTarget == NULL))
+ { // only happen if we have a corrupt errlog or targeting.
+ HWAS_ERR("HW callout; o_pTarget was NULL!!!");
+
+ /*@
+ * @errortype
+ * @moduleid HWAS::MOD_PROCESS_CALLOUT
+ * @reasoncode HWAS::RC_INVALID_TARGET
+ * @devdesc Invalid Target encountered in
+ * processing of HW callout
+ * @userdata1 callout errlog PLID
+ */
+ errlHndl_t errl = hwasError(
+ ERRL_SEV_INFORMATIONAL,
+ HWAS::MOD_PROCESS_CALLOUT,
+ HWAS::RC_INVALID_TARGET,
+ i_errl->plid());
+ errlCommit(errl, HWAS_COMP_ID);
+ l_err = true;
+ }
+ }
+ else
+ { // convert this to the real master processor
+ TARGETING::targetService().masterProcChipTargetHandle(o_pTarget);
+ io_uData += sizeof(HWAS::TARGET_IS_SENTINEL);
+ }
+ return l_err;
+}
+
void processCallout(errlHndl_t i_errl,
uint8_t *i_pData,
uint64_t i_Size)
@@ -58,55 +108,24 @@ void processCallout(errlHndl_t i_errl,
{
case (HW_CALLOUT):
{
- TARGETING::Target *pTarget;
+ TARGETING::Target *pTarget = NULL;
+ uint8_t * l_uData = (uint8_t *)(pCalloutUD + 1);
+ bool l_err = retrieveTarget(l_uData, pTarget, i_errl);
- // data after the pCalloutUD structure is either a token
- // indicating it's the MASTER_PROCESSOR_CHIP_TARGET_SENTINEL
- // or it's the EntityPath - getAttr<TARGETING::ATTR_PHYS_PATH>()
- if (*((uint8_t *)(pCalloutUD + 1)) != TARGET_IS_SENTINEL)
+ if (!l_err)
{
- // convert the EntityPath to a Target pointer
- TARGETING::EntityPath ep;
- memcpy(&ep, (pCalloutUD + 1), sizeof(ep));
- pTarget = TARGETING::targetService().toTarget(ep);
-
- if (unlikely(pTarget == NULL))
- { // only happen if we have a corrupt errlog or targeting.
- HWAS_ERR("HW callout; pTarget was NULL!!!");
-
- /*@
- * @errortype
- * @moduleid HWAS::MOD_PROCESS_CALLOUT
- * @reasoncode HWAS::RC_INVALID_TARGET
- * @devdesc Invalid Target encountered in
- * processing of HW callout
- * @userdata1 callout errlog PLID
- */
- errlHndl_t errl = hwasError(
- ERRL_SEV_INFORMATIONAL,
- HWAS::MOD_PROCESS_CALLOUT,
- HWAS::RC_INVALID_TARGET,
- i_errl->plid());
+ errlHndl_t errl = platHandleHWCallout(
+ pTarget,
+ pCalloutUD->priority,
+ pCalloutUD->deconfigState,
+ i_errl,
+ pCalloutUD->gardErrorType);
+ if (errl)
+ {
+ HWAS_ERR("HW callout: error from platHandlHWCallout");
errlCommit(errl, HWAS_COMP_ID);
- break;
}
}
- else
- { // convert this to the real master processor
- TARGETING::targetService().masterProcChipTargetHandle(pTarget);
- }
-
- errlHndl_t errl = platHandleHWCallout(
- pTarget,
- pCalloutUD->priority,
- pCalloutUD->deconfigState,
- i_errl,
- pCalloutUD->gardErrorType);
- if (errl)
- {
- HWAS_ERR("HW callout: error from platHandlHWCallout");
- errlCommit(errl, HWAS_COMP_ID);
- }
break;
} // HW_CALLOUT
case (PROCEDURE_CALLOUT):
@@ -123,6 +142,30 @@ void processCallout(errlHndl_t i_errl,
}
break;
}
+ case (BUS_CALLOUT):
+ {
+ TARGETING::Target *pTarget1 = NULL;
+ TARGETING::Target *pTarget2 = NULL;
+
+ uint8_t * l_targetData = (uint8_t *)(pCalloutUD + 1);
+ bool l_err1 = retrieveTarget(l_targetData, pTarget1, i_errl);
+ bool l_err2 = retrieveTarget(l_targetData, pTarget2, i_errl);
+
+ if (!l_err1 && !l_err2)
+ {
+ errlHndl_t errl = platHandleBusCallout(
+ pTarget1, pTarget2,
+ pCalloutUD->busType,
+ pCalloutUD->priority,
+ i_errl);
+ if (errl)
+ {
+ HWAS_ERR("HW callout: error from platHandlBusCallout");
+ errlCommit(errl, HWAS_COMP_ID);
+ }
+ }
+ break;
+ } // BUS_CALLOUT
default:
{
HWAS_ERR("bad data in Callout UD %x", pCalloutUD->type);
diff --git a/src/usr/hwas/hwasPlatCallout.C b/src/usr/hwas/hwasPlatCallout.C
index 10d84e877..1b91c4e5e 100644
--- a/src/usr/hwas/hwasPlatCallout.C
+++ b/src/usr/hwas/hwasPlatCallout.C
@@ -116,4 +116,20 @@ errlHndl_t platHandleHWCallout(
return errl;
}
+//******************************************************************************
+// platHandleBusCallout
+//******************************************************************************
+errlHndl_t platHandleBusCallout(
+ TARGETING::Target *i_pTarget1,
+ TARGETING::Target *i_pTarget2,
+ busTypeEnum i_busType,
+ callOutPriority i_priority,
+ errlHndl_t i_errl)
+{
+ errlHndl_t errl = NULL;
+
+ // hostboot does not handle or do any action for bus callouts
+ return errl;
+}
+
} // namespace HWAS
OpenPOWER on IntegriCloud