From 0a1b60c34e55018e233c64b292e16c3479d2145c Mon Sep 17 00:00:00 2001 From: Marty Gloff Date: Tue, 17 Oct 2017 08:23:52 -0500 Subject: Concurrent code update of HBRT - Update Structure Update Hostboot targeting data in the new targeting structure from the current targeting data. It will have the logic to save and restore values as appropriate. Change-Id: I7ae4a0c2e58548f6f1a6229f40b9fda833670e86 RTC: 180908 Reviewed-on: http://ralgit01.raleigh.ibm.com/gerrit1/48504 Reviewed-by: Roland Veloz Reviewed-by: Matt Derksen Reviewed-by: Brian E. Bakke Tested-by: Jenkins Server Tested-by: Jenkins OP Build CI Tested-by: Jenkins OP HW Tested-by: FSP CI Jenkins Reviewed-by: Daniel M. Crowell --- src/usr/targeting/runtime/attrrp_rt.C | 94 ++++++ src/usr/targeting/runtime/makefile | 1 + src/usr/targeting/runtime/rt_targeting.C | 532 +++++++++++++++++++++++++++++++ 3 files changed, 627 insertions(+) (limited to 'src/usr/targeting/runtime') diff --git a/src/usr/targeting/runtime/attrrp_rt.C b/src/usr/targeting/runtime/attrrp_rt.C index 7262c0f5a..f0557fd64 100644 --- a/src/usr/targeting/runtime/attrrp_rt.C +++ b/src/usr/targeting/runtime/attrrp_rt.C @@ -29,6 +29,7 @@ #include #include #include +#include #include #include "../attrrp_common.C" @@ -37,6 +38,98 @@ using namespace ERRORLOG; namespace TARGETING { + void AttrRP::fillInAttrRP(TargetingHeader* i_header) + { + TRACFCOMP(g_trac_targeting, ENTER_MRK"AttrRP::fillInAttrRP"); + + do + { + // Create AttributeSync + AttributeSync l_attributeSync = AttributeSync(); + + // Allocate section structures based on section count in header. + iv_sectionCount = i_header->numSections; + iv_sections = new AttrRP_Section[iv_sectionCount](); + + // Find start to the first section: + // (header address + size of header + offset in header) + TargetingSection* l_section = + reinterpret_cast( + reinterpret_cast(i_header) + + sizeof(TargetingHeader) + i_header->offsetToSections + ); + + uint64_t l_offset = 0; + + for (size_t i = 0; i < iv_sectionCount; ++i, ++l_section) + { + iv_sections[i].type = l_section->sectionType; + iv_sections[i].size = l_section->sectionSize; + + iv_sections[i].vmmAddress = + static_cast( + TARG_TO_PLAT_PTR(i_header->vmmBaseAddress)) + + i_header->vmmSectionOffset*i; + iv_sections[i].pnorAddress = + reinterpret_cast(i_header) + l_offset; + + l_offset += ALIGN_PAGE(iv_sections[i].size); + + TRACFCOMP(g_trac_targeting, + "Decoded Attribute Section: %d, 0x%lx, 0x%lx, 0x%lx", + iv_sections[i].type, + iv_sections[i].vmmAddress, + iv_sections[i].pnorAddress, + iv_sections[i].size); + } + + for (size_t i = 0; i < iv_sectionCount; ++i) + { + // get section data from current AttrRP + std::vector l_pages; + l_pages = + l_attributeSync.syncSectionFromAttrRP(iv_sections[i].type); + + // write section data to new AttrRP + uint8_t * l_dataPtr = nullptr; // ptr to Attribute address space + bool l_rc = true; // true if write is successful + + // for each page + for(std::vector::const_iterator + pageIter = l_pages.begin(); + (pageIter != l_pages.end()) && (true == l_rc); + ++pageIter) + { + // check that page number is within range + uint64_t l_pageOffset = (*pageIter).pageNumber * PAGESIZE; + if ( iv_sections[i].size < (l_pageOffset + PAGESIZE) ) + { + TARG_ERR("page offset 0x%lx is greater than " + "size 0x%lx of section %u", + l_pageOffset, + iv_sections[i].size, + iv_sections[i].type); + + l_rc = false; + break; + } + + // adjust the pointer out by page size * page number + l_dataPtr = + reinterpret_cast(iv_sections[i].pnorAddress) + + l_pageOffset; + + memcpy( l_dataPtr, (*pageIter).dataPtr, PAGESIZE ); + + } + } + } while(false); + + TRACFCOMP(g_trac_targeting, EXIT_MRK"AttrRP::fillInAttrRP"); + + return; + } + void AttrRP::startup(errlHndl_t& io_taskRetErrl, bool isMpipl) { TRACFCOMP(g_trac_targeting, "AttrRP::startup"); @@ -49,6 +142,7 @@ namespace TARGETING reinterpret_cast( hb_get_rt_rsvd_mem(Util::HBRT_MEM_LABEL_ATTR,0,attr_size)); + if ((NULL == l_header) || (l_header->eyeCatcher != PNOR_TARG_EYE_CATCHER)) { diff --git a/src/usr/targeting/runtime/makefile b/src/usr/targeting/runtime/makefile index b453a1f99..c2279f8b2 100644 --- a/src/usr/targeting/runtime/makefile +++ b/src/usr/targeting/runtime/makefile @@ -40,6 +40,7 @@ HOSTBOOT_RUNTIME_SPECIFIC_OBJS += rt_targeting.o HOSTBOOT_RUNTIME_SPECIFIC_OBJS += attrPlatOverride_rt.o HOSTBOOT_RUNTIME_SPECIFIC_OBJS += errludattribute.o HOSTBOOT_RUNTIME_SPECIFIC_OBJS += attributestrings.o +HOSTBOOT_RUNTIME_SPECIFIC_OBJS += attrsync.o OBJS += ${COMMON_TARGETING_OBJS} OBJS += ${HOSTBOOT_RT_IPL_COMMON_OBJS} diff --git a/src/usr/targeting/runtime/rt_targeting.C b/src/usr/targeting/runtime/rt_targeting.C index 96a024ffe..3b2d64ecd 100644 --- a/src/usr/targeting/runtime/rt_targeting.C +++ b/src/usr/targeting/runtime/rt_targeting.C @@ -34,12 +34,16 @@ #include #include #include +#include +#include #include #include #include #include #include #include +#include +#include using namespace TARGETING; @@ -172,9 +176,537 @@ errlHndl_t getHbTarget( return Util::Memoize::memoize(_getHbTarget,i_rtTargetId,o_target); } +/** + * @brief Validate LID Structure against Reserved Memory. Check that the + * TargetingHeader eyecatchers are valid, that the TargetingHeader number of + * sections match, and that the types and sizes of each TargetingSection match. + * @param[in] Pointer to new LID Structure targeting binary data + * @param[in] Pointer to current Reserved Memory targeting binary data + * @return 0 on success, else return code + */ +int validateData(void *i_lidStructPtr, + void *i_rsvdMemPtr) +{ + TRACFCOMP(g_trac_targeting,ENTER_MRK"validateData"); + + int rc = 0; + + do + { + // Get pointers to TargetingHeader areas of each buffer + TargetingHeader* l_headerLid = + reinterpret_cast(i_lidStructPtr); + TargetingHeader* l_headerRsvd = + reinterpret_cast(i_rsvdMemPtr); + + // Find start to the first section in each buffer: + // (header address + size of header + offset in header) + TargetingSection* l_sectionLid = + reinterpret_cast( + reinterpret_cast(l_headerLid) + + sizeof(TargetingHeader) + + l_headerLid->offsetToSections); + TargetingSection* l_sectionRsvd = + reinterpret_cast( + reinterpret_cast(l_headerRsvd) + + sizeof(TargetingHeader) + + l_headerRsvd->offsetToSections); + + // Validate LID Structure TargetingHeader eyecatcher + if (l_headerLid->eyeCatcher != PNOR_TARG_EYE_CATCHER) + { + TRACFCOMP(g_trac_targeting, + "validateData: bad eyecatcher 0x%.8x found in " + "LID Structure TargetingHeader", + l_headerLid->eyeCatcher); + + rc = 1; + + break; + } + + // Validate Reserved Memory TargetingHeader eyecatcher + if (l_headerRsvd->eyeCatcher != PNOR_TARG_EYE_CATCHER) + { + TRACFCOMP(g_trac_targeting, + "validateData: bad eyecatcher 0x%.8x found in " + "Reserved Memory TargetingHeader", + l_headerRsvd->eyeCatcher); + + rc = 1; + + break; + } + + // Validate TargetingHeader number of sections + if (l_headerLid->numSections != l_headerRsvd->numSections) + { + TRACFCOMP(g_trac_targeting, + "validateData: TargetingHeader number of sections " + "miscompare, %d LID Structure sections,%d Reserved " + "Memory sections", + l_headerLid->numSections, + l_headerRsvd->numSections); + + rc = 1; + + break; + } + + // Count of attribute sections + size_t l_sectionCount = l_headerLid->numSections; + + // Loop on each TargetingSection + for (size_t i = 0; + i < l_sectionCount; + ++i, ++l_sectionLid, ++l_sectionRsvd) + { + // Validate TargetingSection type + if (l_sectionLid->sectionType != l_sectionRsvd->sectionType) + { + TRACFCOMP(g_trac_targeting, + "validateData: TargetingSection types miscompare, " + "LID Struct type 0x%0.4x, Rsvd Memory type 0x%0.4x", + l_sectionLid->sectionType, + l_sectionRsvd->sectionType); + + rc = 1; + + break; + } + + // Validate TargetingSection size + if (l_sectionLid->sectionSize != l_sectionRsvd->sectionSize) + { + TRACFCOMP(g_trac_targeting, + "validateData: TargetingSection sizes miscompare, " + "LID Struct size 0x%0.4x, Rsvd Memory size 0x%0.4x", + l_sectionLid->sectionSize, + l_sectionRsvd->sectionSize); + + // Just trace the size mismatch; Don't set rc or break + } + } + // *** Could check if rc was set in for loop and break from do loop + } while(false); + + TRACFCOMP(g_trac_targeting,EXIT_MRK"validateData"); + + return rc; +} + +/** + * @brief Save/Restore attribute values from current Reserved Memory data + * into new LID Structure data + * @param[in] Pointer to current Reserved Memory targeting binary data + * @param[in/out] Pointer to new LID Structure targeting binary data + * @return 0 on success, else return code + */ +int saveRestoreAttrs(void *i_rsvdMemPtr, + void *io_lidStructPtr) +{ + TRACFCOMP( g_trac_targeting, + ENTER_MRK"saveRestoreAttrs: %p %p", + i_rsvdMemPtr, io_lidStructPtr); + + int rc = 0; + AttrRP *l_attrRPLid = nullptr; + + do + { + // Node ID + NODE_ID l_nodeId = 0; + + // Locate current Reserved Memory data via TargetService + TARGETING::TargetService l_targSrv; + (void)l_targSrv.init(); + AttrRP *l_attrRPRsvd = &TARG_GET_SINGLETON(TARGETING::theAttrRP); + + // Create temporary AttrRP instance for new LID Structure targeting data + l_attrRPLid = + new AttrRP(reinterpret_cast(io_lidStructPtr)); + + // Create TargetRangeFilter for LID Structure targeting data + uint32_t l_maxTargetsLid = 0; + TargetRangeFilter l_allTargetsLid = + l_targSrv.getTargetRangeFilter(io_lidStructPtr, + l_attrRPLid, + l_maxTargetsLid, + l_nodeId); + + // Set up variables for getting attribute information for a target + uint32_t l_attrCountRsvd = 0; + ATTRIBUTE_ID* l_pAttrIdRsvd = nullptr; + AbstractPointer* l_ppAttrAddrRsvd = nullptr; + uint32_t l_attrCountLid = 0; + ATTRIBUTE_ID* l_pAttrIdLid = nullptr; + AbstractPointer* l_ppAttrAddrLid = nullptr; + uint32_t l_huidLid = 0; + EntityPath l_physPathLid; + + // Walk through new LID Structure Targets + for(uint32_t l_targetNum = 1; + (l_targetNum <= l_maxTargetsLid) && (rc == 0); + ++l_allTargetsLid, ++l_targetNum) + { + // Get attribute information for a target in LID Structure (new) + l_attrCountLid = l_targSrv.getTargetAttributes(*l_allTargetsLid, + l_attrRPLid, + l_pAttrIdLid, + l_ppAttrAddrLid); + + // Make sure that attributes were found + if(l_attrCountLid == 0) + { + // Continue to next target if there were no attributes + continue; + } + + l_huidLid = l_allTargetsLid->getAttr(); + if(l_huidLid != 0) + { + TRACFCOMP( g_trac_targeting, + "saveRestoreAttrs: target %3d has %3d attrs, " + "class %0.8x, type %0.8x, ordinal ID %0.8x, HUID " + "0x%0.8x", + l_targetNum, + l_attrCountLid, + l_allTargetsLid->getAttr(), + l_allTargetsLid->getAttr(), + l_allTargetsLid->getAttr(), + l_huidLid); + } + else + { + l_physPathLid = l_allTargetsLid->getAttr(); + TRACFCOMP( g_trac_targeting, + "saveRestoreAttrs: target %3d has %3d attrs, " + "class %0.8x, type %0.8x, ordinal ID %0.8x, %s", + l_targetNum, + l_attrCountLid, + l_allTargetsLid->getAttr(), + l_allTargetsLid->getAttr(), + l_allTargetsLid->getAttr(), + l_physPathLid.toString()); + } + + // Create bool used while checking if target exists in current data + bool targetMatched = false; + + // Create TargetRangeFilter for current Reserved Memory data + TargetRangeFilter l_allTargetsRsvd(l_targSrv.begin(), + l_targSrv.end(), + NULL); + + // Walk through current Reserved Memory Targets + for(; + l_allTargetsRsvd; + ++l_allTargetsRsvd) + { + if((l_huidLid != 0) && + (l_allTargetsLid->getAttr() == + l_allTargetsRsvd->getAttr()) && + (l_allTargetsLid->getAttr() == + l_allTargetsRsvd->getAttr()) && + (l_allTargetsLid->getAttr() == + l_allTargetsRsvd->getAttr()) && + (l_huidLid == l_allTargetsRsvd->getAttr())) + { + // Flag the match + targetMatched = true; + + break; + } + else if((l_huidLid == 0) && + (l_allTargetsLid->getAttr() == + l_allTargetsRsvd->getAttr()) && + (l_allTargetsLid->getAttr() == + l_allTargetsRsvd->getAttr()) && + (l_allTargetsLid->getAttr() == + l_allTargetsRsvd->getAttr()) && + (l_physPathLid == + l_allTargetsRsvd->getAttr())) + { + // Flag the match + targetMatched = true; + + break; + } + } + + // Check if target was matched up + if(!targetMatched) + { + if(l_huidLid != 0) + { + TRACFCOMP( g_trac_targeting, + "saveRestoreAttrs: Did not find target " + "HUID 0x%0.8x in Reserved Memory, " + "Keeping targeting data from LID Structure", + l_huidLid); + } + else + { + TRACFCOMP( g_trac_targeting, + "saveRestoreAttrs: Did not find target " + "%s in Reserved Memory, " + "Keeping targeting data from LID Structure", + l_physPathLid.toString()); + } + + // rc should not be changed + + // Go to next new LID Structure target + continue; + } + + // Get attribute information for a target in Reserved Memory (cur) + l_attrCountRsvd = l_targSrv.getTargetAttributes(*l_allTargetsRsvd, + l_attrRPRsvd, + l_pAttrIdRsvd, + l_ppAttrAddrRsvd); + TRACDCOMP( g_trac_targeting, + "Rsvd Memory: " + "HUID 0x%0.8x, attr cnt %d, AttrRP %p, pAttrId %p, " + "ppAttrAddr %p", + l_allTargetsRsvd->getAttr(), + l_attrCountRsvd, + l_attrRPRsvd, + l_pAttrIdRsvd, + l_ppAttrAddrRsvd); + + // Compare attribute counts for new LID Structure target and current + // Reserved Memory target to see if they differ or not + if(l_attrCountLid != l_attrCountRsvd) + { + // Trace when the attribute counts differ + TRACFCOMP( g_trac_targeting, + "saveRestoreAttrs: Attribute counts for target with " + "huid 0x%0.8x differ, LID Structure count %d, " + "Reserved Memory count %d", + l_huidLid, + l_attrCountLid, + l_attrCountRsvd); + } + + // Walk through Attributes for the new LID Structure target + for(uint32_t l_attrNumLid = 0; + (l_attrNumLid < l_attrCountLid) && (rc == 0); + ++l_attrNumLid) + { + // Get ID for attribute on this pass through loop + ATTRIBUTE_ID* l_pAttrId = l_pAttrIdLid + l_attrNumLid; + + // Get the Reserved Memory attribute value pointer + void* l_pAttrRsvd = nullptr; + l_allTargetsRsvd->_getAttrPtr(*l_pAttrId, + l_attrRPRsvd, + l_pAttrIdRsvd, + l_ppAttrAddrRsvd, + l_pAttrRsvd); + + // Check if attribute is in Reserved Memory data + if(l_pAttrRsvd != nullptr) + { + // Get the LID Structure attribute value pointer + void* l_pAttrLid = nullptr; + l_allTargetsLid->_getAttrPtr(*l_pAttrId, + l_attrRPLid, + l_pAttrIdLid, + l_ppAttrAddrLid, + l_pAttrLid); + + // Look up the size of the attribute + uint32_t l_attrSize = attrSizeLookup(*l_pAttrId); + + // Check that attribute has a valid size + if(l_attrSize == 0) + { + TRACFCOMP( g_trac_targeting, + "saveRestoreAttrs: Did not find size of " + "attribute for attribute ID 0x%.8x, target " + "huid 0x%0.8x in Reserved Memory", + *l_pAttrId, + l_allTargetsRsvd->getAttr()); + + rc = 1; + + break; + } + + // Check if new attribute value differs from current value + if(memcmp(l_pAttrRsvd, l_pAttrLid, l_attrSize) != 0) + { + TRACFCOMP( g_trac_targeting, + "saveRestoreAttrs: Found differing values " + "for attribute ID 0x%.8x, huid 0x%0.8x", + *l_pAttrId, + l_huidLid); + + TRACFBIN( g_trac_targeting, + "saveRestoreAttrs: Reserved Memory value", + l_pAttrRsvd, + l_attrSize); + + TRACFBIN( g_trac_targeting, + "saveRestoreAttrs: LID Structure value", + l_pAttrLid, + l_attrSize); + + // Copy attribute value from current Reserved Memory + // attribute to new LID Structure attribute + memcpy(l_pAttrRsvd, l_pAttrLid, l_attrSize); + } + } + else + { + TRACFCOMP( g_trac_targeting, + "saveRestoreAttrs: Did not find attribute ID " + "0x%.8x, target huid 0x%0.8x in Reserved " + "Memory, Keeping value from LID Structure", + *l_pAttrId, + l_huidLid); + + // rc should not be changed + } + } // for attributes + } // for targets + } while(false); + + delete l_attrRPLid; + l_attrRPLid = nullptr; + + TRACFCOMP( g_trac_targeting, EXIT_MRK"saveRestoreAttrs"); + + return rc; +} + int hbrt_update_prep(void) { int rc = 0; + errlHndl_t pError = nullptr; + UtilLidMgr l_lidMgr(Util::TARGETING_BINARY_LIDID); + void *l_lidStructPtr = nullptr; + + bool l_usingRealLID = false; + + do + { + // Get size and location of attributes in reserved memory + uint64_t l_attr_size = 0; + uint64_t l_rsvdMem = hb_get_rt_rsvd_mem(Util::HBRT_MEM_LABEL_ATTR, + 0, l_attr_size); + + // Set pointer to reserved memory targeting data + void *l_rsvdMemPtr = reinterpret_cast(l_rsvdMem); + + // Create lidMgr and get size of Targeting Binary LID + size_t l_lidSize = 0; + pError = l_lidMgr.getLidSize(l_lidSize); + if(pError) + { + pError->collectTrace(TARG_COMP_NAME); + errlCommit(pError,TARG_COMP_ID); + + rc = 1; + + // break; @TODO RTC: 181285 uncomment + l_lidSize = l_attr_size; // @TODO RTC: 181285 remove + } + + if(!rc) // @TODO RTC: 181285 remove + { // @TODO RTC: 181285 remove + if(l_lidSize > l_attr_size) + { + TRACFCOMP( g_trac_targeting, + ERR_MRK"hbrt_update_prep: Sizes of targeting data, " + "LID Structure(New) 0x%0.8x is too large for Rsvd " + "Memory(Current) 0x%0.8x", + l_lidSize, + l_attr_size); + + rc = 1; + + break; + } + + // Get new structure from LID + pError = l_lidMgr.getStoredLidImage(l_lidStructPtr, l_lidSize); + if(pError) + { + pError->collectTrace(TARG_COMP_NAME); + errlCommit(pError,TARG_COMP_ID); + + rc = 1; + + // break; @TODO RTC: 181285 uncomment + } + } // @TODO RTC: 181285 remove + + if(rc) // @TODO RTC: 181285 remove if(rc){...}else{...} start + { + l_lidStructPtr = malloc(l_attr_size); + memcpy(l_lidStructPtr, + l_rsvdMemPtr, + l_attr_size); + + rc = 0; + } + else + { + l_usingRealLID = true; + } // @TODO RTC: 181285 remove if(rc){...}else{...} end + + // Validate LID Structure against Reserved Memory + rc = validateData(l_lidStructPtr, + l_rsvdMemPtr); + if(rc) + { + break; + } + + // Save/Restore attribute values from current Reserved Memory data into + // new LID Structure data + rc = saveRestoreAttrs(l_rsvdMemPtr, + l_lidStructPtr); + if(rc) + { + break; + } + + // Copy new LID Structure data over current Reserved Memory data + size_t l_copySize = std::min(l_lidSize, l_attr_size); + TRACFCOMP( g_trac_targeting, + "hbrt_update_prep: Copy 0x%0.8x bytes of targeting data", + l_copySize); + memcpy(l_rsvdMemPtr, + l_lidStructPtr, + l_copySize); + TRACFCOMP( g_trac_targeting, + "hbrt_update_prep: Set 0x%0.8x bytes to 0", + l_attr_size - l_copySize); + memset(reinterpret_cast( + reinterpret_cast(l_rsvdMemPtr) + l_copySize), + 0, + l_attr_size - l_copySize); + } while(false); + + if(l_usingRealLID) // @TODO RTC: 181285 remove + { // @TODO RTC: 181285 remove + pError = l_lidMgr.releaseLidImage(); + if(pError) + { + pError->collectTrace(TARG_COMP_NAME); + errlCommit(pError,TARG_COMP_ID); + + rc = 1; + } + } // @TODO RTC: 181285 remove + else // @TODO RTC: 181285 remove + { // @TODO RTC: 181285 remove + free(l_lidStructPtr); // @TODO RTC: 181285 remove + l_lidStructPtr = nullptr; // @TODO RTC: 181285 remove + } // @TODO RTC: 181285 remove return rc; } -- cgit v1.2.1