From 6fcf9d0a375c65db1dc06c317e2d60f4d26ed289 Mon Sep 17 00:00:00 2001 From: scott snyder <sss@karma> Date: Fri, 21 Aug 2020 23:41:36 -0400 Subject: [PATCH] TRT_RawDataByteStreamCnv: threading fixes Rework to avoid calling naughtyRetrieve. Remove ATLAS_NOT_THREAD_SAFE annotations --- just need to avoid a (needless!) AttributeList copy. Make sure to protect TRTRawDataProviderTool::m_cache with a lock. Not safe to omit it. Note that the original code was sometimes unpacking the same channel multiple times into the same collection. This behavior is fixed by the change, but it results in RootComp differences for a couple TriggerTest ART tests. --- .../src/TRTRawDataProviderTool.cxx | 4 +- .../src/TRT_RodDecoder.cxx | 79 +++++++++++-------- 2 files changed, 46 insertions(+), 37 deletions(-) diff --git a/InnerDetector/InDetEventCnv/TRT_RawDataByteStreamCnv/src/TRTRawDataProviderTool.cxx b/InnerDetector/InDetEventCnv/TRT_RawDataByteStreamCnv/src/TRTRawDataProviderTool.cxx index dbf8dcf4b699..a8b820d2dace 100644 --- a/InnerDetector/InDetEventCnv/TRT_RawDataByteStreamCnv/src/TRTRawDataProviderTool.cxx +++ b/InnerDetector/InDetEventCnv/TRT_RawDataByteStreamCnv/src/TRTRawDataProviderTool.cxx @@ -99,9 +99,7 @@ StatusCode TRTRawDataProviderTool::convert(const std::vector<const ROBFragment*> std::vector<const ROBFragment*>::const_iterator rob_it = vecRobs.begin(); const EventContext& ctx{Gaudi::Hive::currentContext()}; - // std::lock_guard<std::mutex> lock{m_mutex}; - // Do not lock mutex because this convert method is non-const. - // But we should make this method const. + std::lock_guard<std::mutex> lock{m_mutex}; CacheEntry* ent{m_cache.get(ctx)}; if (ent->m_evt!=ctx.evt()) { // New event in this slot ent->m_LastLvl1ID = 0xffffffff; diff --git a/InnerDetector/InDetEventCnv/TRT_RawDataByteStreamCnv/src/TRT_RodDecoder.cxx b/InnerDetector/InDetEventCnv/TRT_RawDataByteStreamCnv/src/TRT_RodDecoder.cxx index e4ef27f56482..09bf2cd292cd 100644 --- a/InnerDetector/InDetEventCnv/TRT_RawDataByteStreamCnv/src/TRT_RodDecoder.cxx +++ b/InnerDetector/InDetEventCnv/TRT_RawDataByteStreamCnv/src/TRT_RodDecoder.cxx @@ -557,11 +557,12 @@ TRT_RodDecoder::int_fillExpanded( const ROBFragment* robFrag, const Identifier NULLId(0); TRT_RDORawData* rdo = 0; - TRT_RDO_Collection* theColl = 0; // get the data of the fragment OFFLINE_FRAGMENTS_NAMESPACE::PointerType vint; robFrag->rod_data( vint ); + + std::unordered_map<IdentifierHash, std::unique_ptr<TRT_RDO_Collection> > colls; // loop over the data in the fragment unsigned int i; @@ -633,30 +634,28 @@ TRT_RodDecoder::int_fillExpanded( const ROBFragment* robFrag, } } + // Skip if this collection has already been done. + if (rdoIdc->indexFindPtr (idHash)) { + continue; + } + // get the collection - ATH_CHECK(rdoIdc->naughtyRetrieve( idHash, theColl )); + std::unique_ptr<TRT_RDO_Collection>& theColl = colls[idHash]; // Check if the Collection is already created. - if ( theColl == nullptr ) + if ( !theColl ) { #ifdef TRT_BSC_DEBUG ATH_MSG_DEBUG( " Collection ID = " << idHash \ << " does not exist, create it " ); #endif // create new collection - theColl = new TRT_RDO_Collection ( idHash ); + theColl = std::make_unique<TRT_RDO_Collection> ( idHash ); // get identifier from the hash, this is not nice Identifier ident; m_trt_id->get_id(idHash,ident,&m_straw_layer_context); // get the Identifier to be nice to downstream clients theColl->setIdentifier(ident); - // add collection into IDC - StatusCode sc = rdoIdc->addCollection(theColl, idHash); - if ( sc.isFailure() ) - { - ATH_MSG_WARNING ( "Failed to add TRT RDO collection to container" ); - return sc; - } } // Now the Collection is there for sure. Create RDO and push it @@ -675,6 +674,11 @@ TRT_RodDecoder::int_fillExpanded( const ROBFragment* robFrag, theColl->push_back( rdo ); } // End of loop over all words in ROD + + // add collections into IDC + for (auto& p : colls) { + ATH_CHECK( rdoIdc->addCollection (p.second.release(), p.first) ); + } return StatusCode::SUCCESS; } @@ -731,13 +735,14 @@ TRT_RodDecoder::int_fillMinimalCompress( const ROBFragment *robFrag, const Identifier NULLId(0); TRT_RDORawData* rdo = 0; - TRT_RDO_Collection* theColl = 0; // get the data of the fragment OFFLINE_FRAGMENTS_NAMESPACE::PointerType vint; robFrag->rod_data( vint ); + std::unordered_map<IdentifierHash, std::unique_ptr<TRT_RDO_Collection> > colls; + int bit=0; int v; @@ -810,7 +815,7 @@ TRT_RodDecoder::int_fillMinimalCompress( const ROBFragment *robFrag, // Make an Identifier for the RDO and get the IdHash idStraw = m_CablingSvc->getIdentifier( (eformat::SubDetector) 0 /*unused*/, robid, bufferOffset, idHash ); - + if ( NULLId == idStraw ) { #ifdef TRT_BSC_DEBUG @@ -854,30 +859,28 @@ TRT_RodDecoder::int_fillMinimalCompress( const ROBFragment *robFrag, } } + // Skip if this collection has already been done. + if (rdoIdc->indexFindPtr (idHash)) { + continue; + } + // get the collection - ATH_CHECK(rdoIdc->naughtyRetrieve( idHash, theColl )); + std::unique_ptr<TRT_RDO_Collection>& theColl = colls[idHash]; // Check if the Collection is already created. - if ( theColl==nullptr ) + if ( !theColl ) { #ifdef TRT_BSC_DEBUG ATH_MSG_DEBUG( " Collection ID = " << idHash \ << " does not exist, create it " ); #endif // create new collection - theColl = new TRT_RDO_Collection ( idHash ); + theColl = std::make_unique<TRT_RDO_Collection> ( idHash ); // get identifier from the hash, this is not nice Identifier ident; m_trt_id->get_id( idHash, ident, &m_straw_layer_context ); // get the Identifier to be nice to downstream clients theColl->setIdentifier(ident); - // add collection into IDC - StatusCode sc = rdoIdc->addCollection(theColl, idHash); - if ( sc.isFailure() ) - { - ATH_MSG_WARNING ( "Failed to add TRT RDO collection to container" ); - return sc; - } } // Now the Collection is there for sure. Create RDO and push it @@ -908,6 +911,11 @@ TRT_RodDecoder::int_fillMinimalCompress( const ROBFragment *robFrag, } // End of loop over all words in ROD + // add collections into IDC + for (auto& p : colls) { + ATH_CHECK( rdoIdc->addCollection (p.second.release(), p.first) ); + } + return StatusCode::SUCCESS; } @@ -964,12 +972,13 @@ TRT_RodDecoder::int_fillFullCompress( const ROBFragment *robFrag, const Identifier NULLId(0); TRT_RDORawData* rdo = 0; - TRT_RDO_Collection* theColl = 0; // get the data of the fragment OFFLINE_FRAGMENTS_NAMESPACE::PointerType vint; robFrag->rod_data( vint ); + std::unordered_map<IdentifierHash, std::unique_ptr<TRT_RDO_Collection> > colls; + int bit=0; int v,l; int i; @@ -1130,30 +1139,28 @@ TRT_RodDecoder::int_fillFullCompress( const ROBFragment *robFrag, } } + // Skip if this collection has already been done. + if (rdoIdc->indexFindPtr (idHash)) { + continue; + } + // get the collection - ATH_CHECK(rdoIdc->naughtyRetrieve( idHash, theColl )); + std::unique_ptr<TRT_RDO_Collection>& theColl = colls[idHash]; // Check if the Collection is already created. - if ( theColl == nullptr ) + if ( !theColl ) { #ifdef TRT_BSC_DEBUG ATH_MSG_DEBUG( " Collection ID = " << idHash \ << " does not exist, create it " ); #endif // create new collection - theColl = new TRT_RDO_Collection ( idHash ); + theColl = std::make_unique<TRT_RDO_Collection> ( idHash ); // get identifier from the hash, this is not nice Identifier ident; m_trt_id->get_id( idHash, ident, &m_straw_layer_context ); // get the Identifier to be nice to downstream clients theColl->setIdentifier(ident); - // add collection into IDC - StatusCode sc = rdoIdc->addCollection(theColl, idHash); - if ( sc.isFailure() ) - { - ATH_MSG_WARNING ( "Failed to add TRT RDO collection to container" ); - return sc; - } } // Now the Collection is there for sure. Create RDO and push it @@ -1185,6 +1192,10 @@ TRT_RodDecoder::int_fillFullCompress( const ROBFragment *robFrag, } // if phase == 1 } // End of loop over all words in ROD + // add collections into IDC + for (auto& p : colls) { + ATH_CHECK( rdoIdc->addCollection (p.second.release(), p.first) ); + } // ATH_MSG_INFO( "Input: " << in_ptr << " / " << v_size << " Output: " << out_ptr << " / 1920" ); -- GitLab