summaryrefslogtreecommitdiffstats
path: root/src/usr
diff options
context:
space:
mode:
Diffstat (limited to 'src/usr')
-rw-r--r--src/usr/ipmi/ipmifruinv.C205
-rw-r--r--src/usr/ipmi/ipmifruinvprvt.H47
-rw-r--r--src/usr/targeting/common/xmltohb/attribute_types.xml8
-rw-r--r--src/usr/targeting/common/xmltohb/target_types.xml1
4 files changed, 261 insertions, 0 deletions
diff --git a/src/usr/ipmi/ipmifruinv.C b/src/usr/ipmi/ipmifruinv.C
index 4f0d7d709..cc2f06ad9 100644
--- a/src/usr/ipmi/ipmifruinv.C
+++ b/src/usr/ipmi/ipmifruinv.C
@@ -37,6 +37,7 @@
#include "ipmifruinvprvt.H"
#include <stdio.h>
#include <assert.h>
+#include <pnor/pnorif.H>
extern trace_desc_t * g_trac_ipmi;
@@ -84,6 +85,10 @@ IpmiFruInv *IpmiFruInv::Factory(TARGETING::TargetHandleList i_targets,
// @todo-RTC:117702
l_fru = new backplaneIpmiFruInv(l_target, i_targets, i_updateData);
break;
+ case TARGETING::TYPE_SYS:
+ // Use sys target for setting System Firmware Info
+ l_fru = new systemFwIpmiFruInv(l_target);
+ break;
default:
assert(false,
"IpmiFruInv::Factory: No support for target type given: [%08x]",
@@ -927,6 +932,197 @@ errlHndl_t backplaneIpmiFruInv::addVpdData(std::vector<uint8_t> &io_data,
return l_errl;
}
+//##############################################################################
+systemFwIpmiFruInv::systemFwIpmiFruInv( TARGETING::TargetHandle_t i_target )
+ :IpmiFruInv(i_target)
+{
+
+};
+
+errlHndl_t systemFwIpmiFruInv::buildInternalUseArea(std::vector<uint8_t>
+ &io_data)
+{
+ //This section not needed for system firmware type
+ return IpmiFruInv::buildEmptyArea(io_data);
+}
+
+errlHndl_t systemFwIpmiFruInv::buildChassisInfoArea(std::vector<uint8_t>
+ &io_data)
+{
+ //This section not needed for system firmware type
+ return IpmiFruInv::buildEmptyArea(io_data);
+}
+
+errlHndl_t systemFwIpmiFruInv::buildBoardInfoArea(std::vector<uint8_t> &io_data)
+{
+ //This section not needed for system firmware type
+ return IpmiFruInv::buildEmptyArea(io_data);
+}
+
+errlHndl_t systemFwIpmiFruInv::buildProductInfoArea(std::vector<uint8_t>
+ &io_data)
+{
+ errlHndl_t l_errl = NULL;
+
+ do {
+ //Set formatting data that goes at the beginning of the record
+ preFormatProcessing(io_data, true);
+
+ uint8_t l_data[] = {IPMIFRUINV::TYPELENGTH_BYTE_NULL,
+ IPMIFRUINV::TYPELENGTH_BYTE_ASCII + 18, 'O','p','e',
+ 'n','P','O','W','E','R',' ','F','i','r','m','w','a',
+ 'r','e', IPMIFRUINV::TYPELENGTH_BYTE_NULL};
+
+ io_data.insert( io_data.end(),
+ &l_data[0],
+ &l_data[0] + (uint8_t(sizeof(l_data) / sizeof(uint8_t))));
+
+ //Get PNOR Version Here
+ PNOR::SectionInfo_t l_pnorInfo;
+ l_errl = getSectionInfo( PNOR::VERSION , l_pnorInfo);
+ if (l_errl) { break; }
+
+ uint8_t* l_versionData = reinterpret_cast<uint8_t*>( l_pnorInfo.vaddr );
+ //Total Bytes in PNOR Version String
+ uint8_t l_numBytes = 0;
+ uint8_t l_curOffset = 0;
+
+ //Total Number of fields needed to print PNOR Version String
+ uint8_t l_numFields = 0;
+ bool l_clearStandardFields = true;
+
+ //First determine number of bytes in PNOR Version string
+ // with the caveat there is a max record size allowed, so
+ // the string will be cut off if too long
+ //Also, remove newline chars
+ while ((l_numBytes < IPMIFRUINV::MAX_RECORD_SIZE -
+ (uint8_t(sizeof(l_data) / sizeof(uint8_t))) -
+ IPMIFRUINV::COMMON_HEADER_FORMAT_SIZE - 8)
+ && (((char)(l_versionData[l_numBytes])) != '\0'))
+ {
+
+ if (((char)(l_versionData[l_numBytes])) == '\n')
+ {
+
+ if (l_numBytes > l_curOffset)
+ {
+ //Add on size of this field to the data buffer
+ io_data.push_back(
+ IPMIFRUINV::TYPELENGTH_BYTE_ASCII
+ + (l_numBytes-l_curOffset));
+
+ io_data.insert(io_data.end(),
+ &l_versionData[0]+(l_curOffset),
+ &l_versionData[0]+(l_numBytes));
+ }
+
+ //Null data for standard fields needs to be indicated once after
+ // the first segment of data is displayed to match the
+ // ipmi fru spec
+ if (l_clearStandardFields)
+ {
+ //Add Empty Asset Tag
+ io_data.push_back(uint8_t(0));
+ //FRU File ID - Empty
+ io_data.push_back(IPMIFRUINV::TYPELENGTH_BYTE_NULL);
+ io_data.push_back(uint8_t(0)); // Empty FRU File ID bytes
+ l_clearStandardFields = false;
+ }
+
+ //Increment past the newline char
+ l_curOffset = l_numBytes + 1;
+ }
+ l_numBytes++;
+ }
+
+ if (l_curOffset == 0)
+ {
+ //Calculate the number of fields required to display this data
+ // given only MAX_ASCII_FIELD_SIZE bytes can be in any one given
+ // IPMI fru inventory field
+ l_numFields = l_numBytes / IPMIFRUINV::MAX_ASCII_FIELD_SIZE;
+ if (l_numBytes % IPMIFRUINV::MAX_ASCII_FIELD_SIZE)
+ {
+ l_numFields += 1;
+ }
+
+ //Count by number of fields, adding the data to the buffer as
+ // we go.
+ for (uint8_t i=0; i < l_numFields; i++)
+ {
+ //Determine the data size for this particular field
+ uint8_t l_dataSize=IPMIFRUINV::MAX_ASCII_FIELD_SIZE;
+ if (i == l_numFields - 1)
+ {
+ l_dataSize = l_numBytes -
+ (i * IPMIFRUINV::MAX_ASCII_FIELD_SIZE);
+ }
+
+ //Add on size of this field to the data buffer
+ io_data.push_back(IPMIFRUINV::TYPELENGTH_BYTE_ASCII
+ + l_dataSize);
+
+ //Insert this segment of version string data
+ io_data.insert(io_data.end(),
+ &l_versionData[0]+(i * IPMIFRUINV::MAX_ASCII_FIELD_SIZE),
+ &l_versionData[0]+(i * IPMIFRUINV::MAX_ASCII_FIELD_SIZE)
+ +l_dataSize);
+
+ //Null data for standard fields needs to be indicated once after
+ // the first segment of data is displayed to match the
+ // ipmi fru spec
+ if (l_clearStandardFields)
+ {
+ //Add Empty Asset Tag
+ io_data.push_back(uint8_t(0));
+ //FRU File ID - Empty
+ io_data.push_back(IPMIFRUINV::TYPELENGTH_BYTE_NULL);
+ l_clearStandardFields = false;
+ }
+
+ }
+ }
+ else
+ {
+ if (l_numBytes > l_curOffset)
+ {
+ io_data.push_back( IPMIFRUINV::TYPELENGTH_BYTE_ASCII
+ + (l_numBytes-l_curOffset));
+
+ io_data.insert(io_data.end(),
+ &l_versionData[0]+(l_curOffset),
+ &l_versionData[0]+(l_numBytes));
+ }
+
+ }
+
+ if (l_clearStandardFields)
+ {
+ //Add Asset Tag
+ io_data.push_back(uint8_t(0)); //No Asset Tag needed - O bytes
+ //FRU File ID - Empty
+ io_data.push_back(IPMIFRUINV::TYPELENGTH_BYTE_NULL);
+ }
+
+ io_data.push_back(IPMIFRUINV::END_OF_CUSTOM_FIELDS);
+
+ //Finalize section formatting
+ postFormatProcessing(io_data);
+
+ } while(0);
+
+ return l_errl;
+}
+
+errlHndl_t systemFwIpmiFruInv::buildMultiRecordInfoArea(std::vector<uint8_t>
+ &io_data)
+{
+ //This section not needed for system firmware type
+ return IpmiFruInv::buildEmptyArea(io_data);
+}
+
+
+
void IpmiFruInv::addEcidData(const TARGETING::TargetHandle_t& i_target,
const TARGETING::ATTR_ECID_type& i_ecidInfo,
std::vector<uint8_t> &io_data)
@@ -997,6 +1193,15 @@ void IPMIFRUINV::setData(bool i_updateData)
IPMIFRUINV::gatherClearData(pSys, frusToClear);
}
+ //Get System FW FRU_ID if available
+ uint32_t l_systemFwFruId;
+ bool hasSystemFwFruId =
+ pSys->tryGetAttr<TARGETING::ATTR_BMC_FRU_ID>(l_systemFwFruId);
+ if (hasSystemFwFruId)
+ {
+ l_potentialFrus.push_back(std::make_pair(pSys, l_systemFwFruId));
+ }
+
// Find list of all target types that may need a fru inv. record set
IPMIFRUINV::gatherSetData(pSys, frusToClear,
l_potentialFrus, i_updateData);
diff --git a/src/usr/ipmi/ipmifruinvprvt.H b/src/usr/ipmi/ipmifruinvprvt.H
index 2573a84cf..468a47f80 100644
--- a/src/usr/ipmi/ipmifruinvprvt.H
+++ b/src/usr/ipmi/ipmifruinvprvt.H
@@ -42,6 +42,8 @@ namespace IPMIFRUINV
COMMON_HEADER_FORMAT_SIZE = 8, //size in bytes
DEFAULT_CHASSIS_TYPE = 0x05,
DEFAULT_FRU_OFFSET = 0,
+ MAX_ASCII_FIELD_SIZE = 0x3F, //size in bytes
+ MAX_RECORD_SIZE = 0xFF, //size in bytes
};
};
@@ -460,4 +462,49 @@ class backplaneIpmiFruInv : public IpmiFruInv
};
+//Child class for building up System Firwmare Fru Inventory Record Data
+class systemFwIpmiFruInv : public IpmiFruInv
+{
+
+ public:
+ /**
+ * @brief Constructor
+ *
+ * @param[in] TargetHandle_t, Handle to target for which
+ * to get relevant IPMI FRU Data from
+ */
+ systemFwIpmiFruInv( TARGETING::TargetHandle_t i_target);
+
+ /**
+ * @brief Builds the Internal Use Area Data Section
+ * @param[in/out] data, The container to put internal use area data in
+ */
+ errlHndl_t buildInternalUseArea(std::vector<uint8_t> &io_data);
+
+ /**
+ * @brief Builds the Chassis Info Area Data Section
+ * @param[in/out] data, The container to put chassis info area data in
+ */
+ errlHndl_t buildChassisInfoArea(std::vector<uint8_t> &io_data);
+
+ /**
+ * @brief Builds the Board Info Area Data Section
+ * @param[in/out] data, The container to put board info area data in
+ */
+ errlHndl_t buildBoardInfoArea(std::vector<uint8_t> &io_data);
+
+ /**
+ * @brief Builds the Product Info Area Data Section
+ * @param[in/out] data, The container to put product info area data in
+ */
+ errlHndl_t buildProductInfoArea(std::vector<uint8_t> &io_data);
+
+ /**
+ * @brief Builds the MultiRecord Info Area Data Section
+ * @param[in/out] data, The container to put multirecord info area data in
+ */
+ errlHndl_t buildMultiRecordInfoArea(std::vector<uint8_t> &io_data);
+
+};
+
#endif
diff --git a/src/usr/targeting/common/xmltohb/attribute_types.xml b/src/usr/targeting/common/xmltohb/attribute_types.xml
index ec256dedd..17729cdb2 100644
--- a/src/usr/targeting/common/xmltohb/attribute_types.xml
+++ b/src/usr/targeting/common/xmltohb/attribute_types.xml
@@ -11659,6 +11659,14 @@ firmware notes: Platforms should initialize this attribute to AUTO (0)</descript
</attribute>
<attribute>
+ <id>BMC_FRU_ID</id>
+ <description>BMC FRU ID attribute for node class</description>
+ <simpleType><uint32_t><default>0</default></uint32_t></simpleType>
+ <persistency>non-volatile</persistency>
+ <readable/>
+</attribute>
+
+<attribute>
<id>PLCK_IPL_ATTR_OVERRIDES_EXIST</id>
<description>
Set to 1 by HWSV to indicate that attribute overrides exist in a PLCK IPL
diff --git a/src/usr/targeting/common/xmltohb/target_types.xml b/src/usr/targeting/common/xmltohb/target_types.xml
index 15d7921d1..82ec014be 100644
--- a/src/usr/targeting/common/xmltohb/target_types.xml
+++ b/src/usr/targeting/common/xmltohb/target_types.xml
@@ -300,6 +300,7 @@
<attribute><id>MNFG_TH_CEN_L4_CACHE_CES</id></attribute>
<attribute><id>OPT_MEMMAP_GROUP_POLICY</id></attribute>
<attribute><id>FRU_ID</id></attribute>
+ <attribute><id>BMC_FRU_ID</id></attribute>
</targetType>
<targetType>
OpenPOWER on IntegriCloud