diff --git a/DDAlign/include/DDAlign/AlignmentsManager.h b/DDAlign/include/DDAlign/AlignmentsManager.h index d20de301195d0bb32607e5a46d55ca5a9849e373..feb74bcc4b5d33505b60992e24ca47d0107d70b0 100644 --- a/DDAlign/include/DDAlign/AlignmentsManager.h +++ b/DDAlign/include/DDAlign/AlignmentsManager.h @@ -1,4 +1,3 @@ -// $Id$ //========================================================================== // AIDA Detector description implementation for LCD //-------------------------------------------------------------------------- @@ -120,7 +119,7 @@ namespace DD4hep { /// Compute the transformation from the closest detector element of the alignment to the world system void to_world(AlignContext& new_alignments, UserPool& pool, DetElement det, TGeoHMatrix& mat) const; /// Compute all alignment conditions of the lower levels - void compute(AlignContext& new_alignments, UserPool& pool, DetElement child, int level) const; + void compute(AlignContext& new_alignments, UserPool& pool, DetElement child) const; public: /// Initializing constructor diff --git a/DDAlign/include/DDAlign/DDAlignForwardCall.h b/DDAlign/include/DDAlign/DDAlignForwardCall.h new file mode 100644 index 0000000000000000000000000000000000000000..ab95f1e4fe17f2a5127165f2f1c17ac01b3421e5 --- /dev/null +++ b/DDAlign/include/DDAlign/DDAlignForwardCall.h @@ -0,0 +1,44 @@ +//========================================================================== +// AIDA Detector description implementation for LCD +//-------------------------------------------------------------------------- +// Copyright (C) Organisation europeenne pour la Recherche nucleaire (CERN) +// All rights reserved. +// +// For the licensing terms see $DD4hepINSTALL/LICENSE. +// For the list of contributors see $DD4hepINSTALL/doc/CREDITS. +// +// Author : M.Frank +// +//========================================================================== +#ifndef DD4HEP_DDALIGN_DDALIGNFORWARDCALL_H +#define DD4HEP_DDALIGN_DDALIGNFORWARDCALL_H + +// Framework includes +#include "DDAlign/AlignmentUpdateCall.h" + +/// Namespace for the AIDA detector description toolkit +namespace DD4hep { + + /// Namespace of the DDAlign conversion stuff + namespace Alignments { + + /// Specialized conditions forward callback for DDAlign alignments + /** + * + * \author M.Frank + * \version 1.0 + * \ingroup DD4HEP_ALIGNMENT + */ + class DDAlignForwardCall : public AlignmentUpdateCall { + public: + /// Default constructor + DDAlignForwardCall() = default; + /// Default destructor + virtual ~DDAlignForwardCall() = default; + /// Interface to client Callback in order to forward the condition + virtual Condition operator()(const ConditionKey& key, const UpdateContext& context); + }; + + } /* End namespace Alignments */ +} /* End namespace DD4hep */ +#endif /* DD4HEP_DDALIGN_DDALIGNFORWARDCALL_H */ diff --git a/DDAlign/include/DDAlign/DDAlignTest.h b/DDAlign/include/DDAlign/DDAlignTest.h deleted file mode 100644 index 2760fb9d853726907ad52d7aa41f4a04e42fbc3b..0000000000000000000000000000000000000000 --- a/DDAlign/include/DDAlign/DDAlignTest.h +++ /dev/null @@ -1,54 +0,0 @@ -//========================================================================== -// AIDA Detector description implementation for LCD -//-------------------------------------------------------------------------- -// Copyright (C) Organisation europeenne pour la Recherche nucleaire (CERN) -// All rights reserved. -// -// For the licensing terms see $DD4hepINSTALL/LICENSE. -// For the list of contributors see $DD4hepINSTALL/doc/CREDITS. -// -// Author : M.Frank -// -//========================================================================== -#ifndef DD4HEP_DDALIGNTEST_H -#define DD4HEP_DDALIGNTEST_H - -// Framework includes -#include "DDAlign/AlignmentsManager.h" -#include "DDCond/ConditionsManager.h" - - -/// Namespace for the AIDA detector description toolkit -namespace DD4hep { - - /// Test class to chain variou test sequences for DDCond and DDAlign - /** - * - * \author M.Frank - * \version 1.0 - * \ingroup DD4HEP - */ - class DDAlignTest { - typedef Alignments::AlignmentsManager AlignmentsManager; - typedef Alignments::UserPool AlignmentsPool; - - typedef Conditions::ConditionsManager ConditionsManager; - typedef Conditions::UserPool ConditionsPool; - - public: - /// Reference to alignments manager object - AlignmentsManager alignmentsMgr; - dd4hep_ptr<ConditionsPool> alignmentsPool; - - /// Reference to conditions manager object - ConditionsManager conditionsMgr; - dd4hep_ptr<ConditionsPool> conditionsPool; - - public: - /// Default constructor - DDAlignTest() = default; - /// Default destructor - virtual ~DDAlignTest() = default; - }; -} /* End namespace DD4hep */ -#endif /* DD4HEP_DDALIGN_DDALIGNTEST_H */ diff --git a/DDAlign/src/AlignmentsManager.cpp b/DDAlign/src/AlignmentsManager.cpp index 5d189595e003285f4a804f193da154e5f7a57d44..bff4c8c4aab927c1c1f2a28b13bf00021bf4997f 100644 --- a/DDAlign/src/AlignmentsManager.cpp +++ b/DDAlign/src/AlignmentsManager.cpp @@ -1,4 +1,3 @@ -// $Id$ //========================================================================== // AIDA Detector description implementation for LCD //-------------------------------------------------------------------------- @@ -38,7 +37,7 @@ namespace DD4hep { const Dependency* dep; DetElement::Object* det; AlignmentCondition::Object* cond; - unsigned int key, top; + unsigned int key, top, valid; }; struct PathOrdering { bool operator()(const DetElement& a, const DetElement& b) const @@ -62,11 +61,12 @@ namespace DD4hep { if ( det.isValid() ) { Entry entry; unsigned int key = det.key(); - entry.top = 0; - entry.cond = con; - entry.dep = dep; - entry.det = det.ptr(); - entry.key = key; + entry.valid = 0; + entry.top = 0; + entry.cond = con; + entry.dep = dep; + entry.det = det.ptr(); + entry.key = key; detectors.insert(std::make_pair(det, entries.size())); keys.insert(std::make_pair(key, entries.size())); entries.insert(entries.end(), entry); @@ -87,6 +87,7 @@ namespace DD4hep { DD4HEP_INSTANTIATE_HANDLE_NAMED(AlignmentsManagerObject); +static PrintLevel s_PRINT = WARNING; /// Initializing constructor AlignmentsManagerObject::AlignmentsManagerObject() : NamedObject() { @@ -103,7 +104,11 @@ AlignmentsManagerObject::~AlignmentsManagerObject() { InstanceCount::decrement(this); } -void AlignmentsManagerObject::to_world(AlignContext& new_alignments, UserPool& pool, DetElement det, TGeoHMatrix& mat) const { +void AlignmentsManagerObject::to_world(AlignContext& new_alignments, + UserPool& pool, + DetElement det, + TGeoHMatrix& delta) const +{ using Conditions::Condition; DetElement par = det.parent(); while( par.isValid() ) { @@ -112,12 +117,24 @@ void AlignmentsManagerObject::to_world(AlignContext& new_alignments, UserPool& p AlignContext::Keys::const_iterator i = new_alignments.keys.find(par.key()); if ( i != new_alignments.keys.end() ) { const AlignContext::Entry& e = new_alignments.entries[(*i).second]; + // The parent entry is (not yet) valid. need to compute it first + if ( 0 == e.valid ) { + compute(new_alignments, pool, par); + } AlignmentCondition cond(e.cond); AlignmentData& align = cond.data(); - mat.MultiplyLeft(&align.worldTransformation()); + if ( s_PRINT <= INFO ) { + printf("Multiply-left ALIGNMENT %s:", det.path().c_str()); delta.Print(); + printf(" with ALIGN(world) %s :", par.path().c_str()); + align.worldDelta.Print(); + } + delta.MultiplyLeft(&align.worldDelta); + if ( s_PRINT <= INFO ) { + printf(" Result :"); delta.Print(); + } return; } - // The parent did not get updated: We have to search the the conditions pool if + // The parent did not get updated: We have to search the conditions pool if // there is a still valid condition, which we can use to build the world transformation // The parent's alignment condition by defintiion must be present in the pool, // since it got updated in the past! @@ -127,12 +144,28 @@ void AlignmentsManagerObject::to_world(AlignContext& new_alignments, UserPool& p Condition::key_type key = e.dep->target.hash; AlignmentCondition cond = pool.get(key); AlignmentData& align = cond.data(); - mat.MultiplyLeft(&align.worldTransformation()); + if ( s_PRINT <= INFO ) { + printf("Multiply-left ALIGNMENT %s:", det.path().c_str()); delta.Print(); + printf(" with ALIGN(world) %s :", par.path().c_str()); + align.worldDelta.Print(); + } + delta.MultiplyLeft(&align.worldDelta); + if ( s_PRINT <= INFO ) { + printf(" Result :"); delta.Print(); + } return; } // There is no special alignment for this detector element. // Hence to nominal (relative) transformation to the parent is valid - mat.MultiplyLeft(&par.nominal().detectorTransformation()); + if ( s_PRINT <= INFO ) { + printf("Multiply-left ALIGNMENT %s:", det.path().c_str()); delta.Print(); + printf(" with NOMINAL(det) %s :", par.path().c_str()); + par.nominal().detectorTransformation().Print(); + } + delta.MultiplyLeft(&par.nominal().detectorTransformation()); + if ( s_PRINT <= INFO ) { + printf(" Result :"); delta.Print(); + } par = par.parent(); } } @@ -144,12 +177,16 @@ void AlignmentsManagerObject::compute(UserPool& user_pool) const { /// Compute all alignment conditions of the specified dependency list void AlignmentsManagerObject::compute(UserPool& pool, const Dependencies& deps) const { - AlignContext::DetectorMap::const_iterator i; AlignContext new_alignments; new_alignments.entries.reserve(deps.size()); pool.compute(deps, &new_alignments); + for(auto i=new_alignments.entries.begin(); i != new_alignments.entries.end(); ++i) + compute(new_alignments, pool, (*i).det); + for(auto i=new_alignments.entries.begin(); i != new_alignments.entries.end(); ++i) + compute(new_alignments, pool, (*i).det); +#if 0 std::string prev = "-----"; - for(i=new_alignments.detectors.begin(); i!=new_alignments.detectors.end(); ++i) { + for(auto i=new_alignments.detectors.begin(); i!=new_alignments.detectors.end(); ++i) { AlignContext::Entry& e = new_alignments.entries[(*i).second]; DetElement det = e.det; const std::string& p = det.path(); @@ -158,25 +195,26 @@ void AlignmentsManagerObject::compute(UserPool& pool, const Dependencies& deps) continue; } prev = p; - printout(DEBUG,"Alignment","Update top Node: Lvl:%d Key:%08X: %s", det.level(), det.key(), p.c_str()); + printout(s_PRINT,"Alignment","Update top Node: Lvl:%d Key:%08X: %s", det.level(), det.key(), p.c_str()); e.top = 1; } // We got now the top nodes of the new_alignments. From the top nodes we have to // recursively calculate all changes downwards the lower levels! // Note: The upper levels are already correct and do not need to be updated! printout(INFO,"Alignment","Working down the tree...."); - for(i=new_alignments.detectors.begin(); i != new_alignments.detectors.end(); ++i) { + for(auto i=new_alignments.detectors.begin(); i != new_alignments.detectors.end(); ++i) { AlignContext::Entry& e = new_alignments.entries[(*i).second]; if ( e.top ) { - compute(new_alignments, pool, e.det, 0); + compute(new_alignments, pool, e.det); } } +#endif } + /// Compute the alignment delta for one detector element and it's alignment condition static void computeDelta(AlignmentCondition cond, TGeoHMatrix& tr_delta) { const AlignmentData& align = cond.data(); const Delta& delta = align.delta; - const TGeoHMatrix& nom = align.detectorTransformation(); const Position& pos = delta.translation; const Translation3D& piv = delta.pivot; const RotationZYX& rot = delta.rotation; @@ -200,28 +238,44 @@ static void computeDelta(AlignmentCondition cond, TGeoHMatrix& tr_delta) { default: break; } - tr_delta.MultiplyLeft(&nom); - align.detectorTrafo = tr_delta; - align.worldTrafo = tr_delta; } + /// Compute all alignment conditions of the lower levels -void AlignmentsManagerObject::compute(AlignContext& new_alignments, UserPool& pool, DetElement det, int level) const { - AlignContext::Keys::const_iterator k=new_alignments.keys.find(det.key()); - bool has_cond = k != new_alignments.keys.end(); - const AlignContext::Entry* ent = has_cond ? &new_alignments.entries[(*k).second] : 0; +void AlignmentsManagerObject::compute(AlignContext& new_alignments, UserPool& pool, DetElement det) const { + auto k=new_alignments.keys.find(det.key()); + bool has_cond = (k != new_alignments.keys.end()); + AlignContext::Entry* ent = has_cond ? &new_alignments.entries[(*k).second] : 0; - if ( ent ) { - char fmt[128]; + if ( ent && ent->valid == 1 ) { + printout(DEBUG,"ComputeAlignment","================ IGNORE %s (already valid)",det.path().c_str()); + return; + } + if ( ent && ent->valid == 0 ) { TGeoHMatrix tr_delta; - AlignmentCondition cond(ent->cond); + AlignmentCondition cond = ent->cond; AlignmentData& align = cond.data(); + printout(INFO,"ComputeAlignment", + "============================== Compute transformation of %s ============================== ", + det.path().c_str()); + + ent->valid = 1; computeDelta(cond, tr_delta); - to_world(new_alignments, pool, det, align.worldTrafo); - align.trToWorld = Geometry::_transform(&align.worldTrafo); - ::snprintf(fmt,sizeof(fmt),"%%d %%%ds %%s %%08X: %%s IOV:%%s",2*level); - printout(DEBUG,"ComputeAlignment",fmt, - det.level(), "", has_cond ? "NO " : "YES", - det.key(), det.path().c_str(), cond.iov().str().c_str()); + align.worldDelta = tr_delta; + to_world(new_alignments, pool, det, align.worldDelta); + align.worldTrafo = det.nominal().worldTransformation()*align.worldDelta; + align.detectorTrafo = det.nominal().detectorTransformation()*tr_delta; + align.trToWorld = Geometry::_transform(&align.worldDelta); + printout(INFO,"ComputeAlignment","Level:%d Path:%s DetKey:%08X: Cond:%s key:%08X IOV:%s", + det.level(), det.path().c_str(), det.key(), + yes_no(has_cond), cond.key(), cond.iov().str().c_str()); + if ( s_PRINT <= INFO ) { + printf("DetectorTrafo: '%s' -> '%s' ",det.path().c_str(), det.parent().path().c_str()); + det.nominal().detectorTransformation().Print(); + printf("Delta: '%s' ",det.path().c_str()); tr_delta.Print(); + printf("World-Delta: '%s' ",det.path().c_str()); align.worldDelta.Print(); + printf("Nominal: '%s' ",det.path().c_str()); det.nominal().worldTransformation().Print(); + printf("Result: '%s' ",det.path().c_str()); align.worldTrafo.Print(); + } } else { // DetElement 'det' has no specific alignment. If any of the children has one @@ -233,11 +287,20 @@ void AlignmentsManagerObject::compute(AlignContext& new_alignments, UserPool& po // Alternatively we could inject 'special' alignment conditions, which would depend // on the parent... // Under circumstances, this might be cheaper to re-compute. + // + // NOT HANDLED HERE! + // Solution uses derived conditions to generate AlignmentCondition + // objects with an empty Delta. + // + // Handled in the alignment plugin: DDAlign_AlignmentForward, + // to be executed AFTER DDAlign_AlignmentRegister. + // This plugin will inject the relevant dependency calls. + // } const DetElement::Children& children = det.children(); for(auto c=children.begin(); c!=children.end(); ++c) { DetElement child = (*c).second; - compute(new_alignments, pool, child, level+1); + compute(new_alignments, pool, child); } } @@ -275,12 +338,12 @@ const AlignmentsManager::Dependencies& AlignmentsManager::knownDependencies() c /// Compute all alignment conditions of the internal dependency list void AlignmentsManager::compute(dd4hep_ptr<UserPool>& user_pool) const { Object* o = access(); - o->compute(*(user_pool.get()), *(o->dependencies)); + o->compute(*user_pool, *(o->dependencies)); } /// Compute all alignment conditions of the specified dependency list void AlignmentsManager::compute(dd4hep_ptr<UserPool>& user_pool, const Dependencies& deps) const { - access()->compute(*(user_pool.get()), deps); + access()->compute(*user_pool, deps); } /// Register new updated derived alignment during the computation step diff --git a/DDAlign/src/DDAlignForwardCall.cpp b/DDAlign/src/DDAlignForwardCall.cpp new file mode 100644 index 0000000000000000000000000000000000000000..dcc558377137ab5ae14b0cbe7a2f65626b56fea9 --- /dev/null +++ b/DDAlign/src/DDAlignForwardCall.cpp @@ -0,0 +1,32 @@ +//========================================================================== +// AIDA Detector description implementation for LCD +//-------------------------------------------------------------------------- +// Copyright (C) Organisation europeenne pour la Recherche nucleaire (CERN) +// All rights reserved. +// +// For the licensing terms see $DD4hepINSTALL/LICENSE. +// For the list of contributors see $DD4hepINSTALL/doc/CREDITS. +// +// Author : M.Frank +// +//========================================================================== + +// Framework includes +#include "DDAlign/DDAlignForwardCall.h" +#include "DD4hep/ConditionsData.h" +#include "DD4hep/Printout.h" + +using namespace DD4hep; +using namespace DD4hep::Conditions; + +/// Interface to client Callback in order to update the condition +Condition +Alignments::DDAlignForwardCall::operator()(const ConditionKey& key, const UpdateContext& context) +{ + const Data::Delta delta; + DetElement det = context.dependency.detector; + Condition c = AlignmentUpdateCall::handle(key, context, delta); + printout(INFO,"DDAlignForward","++ Building child alignment condition: %s Detector [%d]: %s [%p]", + key.name.c_str(), det.level(), det.path().c_str(), c.ptr()); + return c; +} diff --git a/DDAlign/src/DDAlignUpdateCall.cpp b/DDAlign/src/DDAlignUpdateCall.cpp index 4faf638edf0eecd9b04fe58c3e46f873d1f386b5..e8a7e2a196e9e04628e1578860134601952abe5a 100644 --- a/DDAlign/src/DDAlignUpdateCall.cpp +++ b/DDAlign/src/DDAlignUpdateCall.cpp @@ -28,7 +28,7 @@ Alignments::DDAlignUpdateCall::operator()(const ConditionKey& key, const UpdateC if ( cond.typeInfo() == typeid(Data::Delta) ) { const Data::Delta& delta = cond.get<Data::Delta>(); Condition c = AlignmentUpdateCall::handle(key, context, delta); - printout(INFO,"AlignmentUpdate","++ Building dependent condition: %s Detector [%d]: %s [%p]", + printout(INFO,"DDAlignUpdate","++ Building dependent condition: %s Detector [%d]: %s [%p]", key.name.c_str(), det.level(), det.path().c_str(), c.ptr()); return c; } diff --git a/DDAlign/src/plugins/AlignmentDependencyTest.cpp b/DDAlign/src/plugins/AlignmentDependencyTest.cpp index 43adc47da435dfe46660592f72eba80aa3c3677e..f476764e8751490c329fbdf33038cb97e4d77a31 100644 --- a/DDAlign/src/plugins/AlignmentDependencyTest.cpp +++ b/DDAlign/src/plugins/AlignmentDependencyTest.cpp @@ -11,6 +11,7 @@ // Author : M.Frank // //========================================================================== +#if 0 // Framework includes #include "DD4hep/Plugins.h" @@ -38,52 +39,6 @@ using Conditions::DetConditions; using Conditions::DependencyBuilder; // ====================================================================================== -#include "DDAlign/AlignmentsManager.h" - -namespace { - /// Print alignments - /** - * - * \author M.Frank - * \version 1.0 - * \date 18/11/2016 - * \ingroup DD4HEP_DDALIGN - */ - class AlignmentPrinter : public AlignmentsProcessor { - public: - /// Initializing constructor - AlignmentPrinter() : AlignmentsProcessor(0) {} - /// Default destructor - virtual ~AlignmentPrinter() = default; - /// Callback to output conditions information - virtual int operator()(Alignment a) { - const Alignments::Delta& D = a.data().delta; - printout(INFO,"Alignment","++ (%11s-%8s-%5s) Cond:%p 'Alignment'", - D.hasTranslation() ? "Translation" : "", - D.hasRotation() ? "Rotation" : "", - D.hasPivot() ? "Pivot" : "", - a.data().hasCondition() ? a.data().condition.ptr() : 0); - return 1; - } - /// Container callback for object processing - virtual int operator()(Container container) - { return this->self_t::operator()(container); } - /// Callback to output conditions information - virtual int operator()(DetElement de) - { return this->self_t::operator()(de); } - }; -} - -/// Convert alignments conditions to alignment objects -static void* ddalign_AlignmentsPrinter(Geometry::LCDD& /* lcdd */, int /* argc */, char** /* argv */) { - return (AlignmentsProcessor*)(new AlignmentPrinter()); -} - -DECLARE_LCDD_CONSTRUCTOR(DDAlign_AlignmentsPrinter,ddalign_AlignmentsPrinter) - - - -#if 0 /// Compute dependent alignment conditions int computeDependencies(dd4hep_ptr<UserPool>& user_pool, ConditionsManager conds, diff --git a/DDAlign/src/plugins/AlignmentForward.cpp b/DDAlign/src/plugins/AlignmentForward.cpp new file mode 100644 index 0000000000000000000000000000000000000000..a684f21f6a02ef6b888599c8559489cc5f793ebd --- /dev/null +++ b/DDAlign/src/plugins/AlignmentForward.cpp @@ -0,0 +1,119 @@ +//========================================================================== +// AIDA Detector description implementation for LCD +//-------------------------------------------------------------------------- +// Copyright (C) Organisation europeenne pour la Recherche nucleaire (CERN) +// All rights reserved. +// +// For the licensing terms see $DD4hepINSTALL/LICENSE. +// For the list of contributors see $DD4hepINSTALL/doc/CREDITS. +// +// Author : M.Frank +// +//========================================================================== + +// Framework includes +#include "DD4hep/Plugins.h" +#include "DD4hep/Printout.h" +#include "DD4hep/DetAlign.h" +#include "DD4hep/DetFactoryHelper.h" +#include "DD4hep/objects/AlignmentsInterna.h" + +#include "DDAlign/AlignmentsManager.h" +#include "DDAlign/AlignmentUpdateCall.h" + +using namespace DD4hep; +using namespace DD4hep::Alignments; + +// ====================================================================================== + +/// Anonymous namespace for plugins +namespace { + + /// Create lignment dependencies from conditions + /** + * Conditions analyser to select alignments.and create the + * corresponding alignment condition dependencies. + * + * \author M.Frank + * \version 1.0 + * \date 31/03/2016 + * \ingroup DD4HEP_DDALIGN + */ + class AlignmentForward : public DetElement::Processor { + public: + LCDD& lcdd; + AlignmentsManager alignmentMgr; + AlignmentUpdateCall* updateCall; + Conditions::UserPool* user_pool; + + /// Initializing constructor + AlignmentForward(LCDD& l, AlignmentUpdateCall* c, UserPool* p) + : lcdd(l), updateCall(c), user_pool(p) + { + alignmentMgr = AlignmentsManager::from(lcdd); + } + /// Default destructor + virtual ~AlignmentForward() { + releasePtr(updateCall); + } + /// Callback to output conditions information + virtual int processElement(DetElement de) { + if ( de.isValid() ) { + DetElement parent = de.parent(); + if ( parent.isValid() && parent.hasAlignments() && !de.hasAlignments() ) { + DetAlign align(de); + Conditions::ConditionKey k(de.path()+"#alignment/Tranformations"); + // + // The alignment access through the DetElement object is optional! + // It is slow and deprecated. The access using the UserPool directly + // is highly favored. + // + align.alignments()->addKey(k.name); + align.alignments()->addKey("Alignment",k.name); + // + // Now add the dependency to the alignmant manager + Conditions::DependencyBuilder b(k, updateCall->addRef(), de); + bool result = alignmentMgr.adoptDependency(b.release()); + if ( result ) { + printout(INFO,"AlignForward", + "++ Added Alignment child dependency Cond:%s Key:%08X", + k.name.c_str(), k.hash); + return 1; + } + printout(ERROR,"AlignForward", + "++ FAILED to add Alignment dependency Cond:%s Key:%08X", + k.name.c_str(), k.hash); + } + } + return 1; + } + }; +} + +#include "DD4hep/PluginTester.h" +#include "DDCond/ConditionsPool.h" +/// Convert alignments conditions to alignment objects +static void* ddalign_AlignmentForward(Geometry::LCDD& lcdd, int argc, char** argv) { + std::vector<char*> args_prepare, args_call; + + for(int i=0; i<argc && argv[i]; ++i) { + if ( ::strcmp(argv[i],"-call") == 0 ) { + while( (++i)<argc && argv[i] && 0 != ::strcmp(argv[i],"-call-end") ) + args_call.push_back(argv[i]); + } + } + + PluginTester* test = lcdd.extension<PluginTester>(); + Conditions::UserPool* pool = test->extension<Conditions::UserPool>("ConditionsTestUserPool"); + AlignmentUpdateCall* call = (AlignmentUpdateCall*) + PluginService::Create<void*>((const char*)args_call[0],&lcdd, + int(args_call.size())-1, + (char**)&args_call[1]); + if ( 0 == call ) { + except("AlignForward","++ Failed to create update call!"); + } + AlignmentForward* obj = new AlignmentForward(lcdd, call, pool); + return obj; +} +DECLARE_LCDD_CONSTRUCTOR(DDAlign_AlignmentForward,ddalign_AlignmentForward) + diff --git a/DDAlign/src/plugins/AlignmentPlugins.cpp b/DDAlign/src/plugins/AlignmentPlugins.cpp index f36c150210215f1f51c9445b616734058df96b35..9d1329fbcb3d292217ed4ff761b1583048cd203c 100644 --- a/DDAlign/src/plugins/AlignmentPlugins.cpp +++ b/DDAlign/src/plugins/AlignmentPlugins.cpp @@ -16,6 +16,7 @@ #include "DD4hep/DetectorTools.h" #include "DD4hep/DetFactoryHelper.h" +using namespace std; using namespace DD4hep; using namespace DD4hep::Alignments; @@ -51,10 +52,10 @@ namespace { namespace DetectorTools = DD4hep::Geometry::DetectorTools; long create_global_alignment_file(Geometry::LCDD& lcdd, int argc, char** argv) { Geometry::DetElement top; - std::string output, path = "/world"; - bool enable_transactions = false; + string output, path = "/world"; + bool enable_transactions = false, arg_error = false; for(int i=1; i<argc;++i) { - if ( argv[i][0]=='-' || argv[i][0]=='/' ) { + if ( argv[i] && (argv[i][0]=='-' || argv[i][0]=='/') ) { const char* p = ::strchr(argv[i],'='); if ( p && strncmp(argv[i]+1,"-output",7)==0 ) output = p+1; @@ -63,18 +64,33 @@ namespace { else if ( strncmp(argv[i]+1,"-transactions",5)==0 ) enable_transactions = true; else - throw std::runtime_error("AlignmentWriter: Invalid argument:"+std::string(argv[i])); + arg_error = true; } } + + if ( arg_error || output.empty() || path.empty() ) { + /// Help printout describing the basic command line interface + cout << + "Usage: -plugin <name> -arg [-arg] \n" + " name: factory nameDD4hep_GlobalAlignmentWriter \n\n" + " -output <string> Path to the output file generated. \n" + " -path <string> Path to the detector element for which \n" + " the alignment file should be written. \n" + " -transactions Enable output transactions. \n" + "\tArguments given: " << arguments(argc,argv) << endl << flush; + ::_exit(EINVAL); + } + printout(ALWAYS,"AlignmentWriter", - "++++ Writing DD4hep alignment constants of the \"%s\" DetElement tree to file \"%s\"", + "++ Writing DD4hep alignment constants of the \"%s\" DetElement tree to file \"%s\"", path.c_str(), output.c_str()); top = DetectorTools::findDaughterElement(lcdd.world(),path); if ( top.isValid() ) { GlobalAlignmentWriter wr(lcdd); return wr.write(wr.dump(top,enable_transactions), output); } - throw std::runtime_error("AlignmentWriter: Invalid top level element name:"+path); + except("AlignmentWriter","++ Invalid top level detector element name: %s",path.c_str()); + return 1; } } /* End anonymous namespace */ DECLARE_APPLY(DD4hep_GlobalAlignmentWriter, create_global_alignment_file) @@ -87,10 +103,21 @@ static void* create_DDAlignUpdateCall(Geometry::LCDD& /* lcdd */, int /* argc */ DECLARE_LCDD_CONSTRUCTOR(DDAlign_UpdateCall, create_DDAlignUpdateCall) // ====================================================================================== -#include "DDAlign/DDAlignTest.h" +#include "DDAlign/DDAlignForwardCall.h" +static void* create_DDAlignForwardCall(Geometry::LCDD& /* lcdd */, int /* argc */, char** /* argv */) { + return (AlignmentUpdateCall*)(new DDAlignForwardCall()); +} +DECLARE_LCDD_CONSTRUCTOR(DDAlign_ForwardCall, create_DDAlignForwardCall) + +#include "DD4hep/PluginTester.h" +#include "DDCond/ConditionsPool.h" +// ====================================================================================== static long compute_alignments(Geometry::LCDD& lcdd, int /* argc */, char** /* argv */) { - DDAlignTest* test = lcdd.extension<DDAlignTest>(); - test->alignmentsMgr.compute(test->alignmentsPool); + AlignmentsManager mgr = AlignmentsManager::from(lcdd); + PluginTester* tst = lcdd.extension<PluginTester>(); + dd4hep_ptr<UserPool> pool(tst->extension<UserPool>("ConditionsTestUserPool")); + mgr.compute(pool); + pool.release(); return 1; } DECLARE_APPLY(DDAlign_ComputeAlignments, compute_alignments) diff --git a/DDAlign/src/plugins/Conditions2Alignments.cpp b/DDAlign/src/plugins/AlignmentRegister.cpp similarity index 72% rename from DDAlign/src/plugins/Conditions2Alignments.cpp rename to DDAlign/src/plugins/AlignmentRegister.cpp index 87efa0c4dd5b95a87aea68aa329ca2100910ddc5..995b64cc5d74ac7fa599d5d262b5f60e127d42a8 100644 --- a/DDAlign/src/plugins/Conditions2Alignments.cpp +++ b/DDAlign/src/plugins/AlignmentRegister.cpp @@ -47,7 +47,7 @@ namespace { * \date 31/03/2016 * \ingroup DD4HEP_DDALIGN */ - class Conditions2Alignments : public DetElement::Processor { + class AlignmentRegister : public DetElement::Processor { public: LCDD& lcdd; Alignments::AlignmentsManager alignmentMgr; @@ -55,32 +55,32 @@ namespace { Conditions::UserPool* user_pool; /// Initializing constructor - Conditions2Alignments(LCDD& l, AlignmentUpdateCall* c, UserPool* p) + AlignmentRegister(LCDD& l, AlignmentUpdateCall* c, UserPool* p) : lcdd(l), updateCall(c), user_pool(p) { alignmentMgr = AlignmentsManager::from(lcdd); } /// Default destructor - virtual ~Conditions2Alignments() { + virtual ~AlignmentRegister() { releasePtr(updateCall); } /// Callback to output conditions information - virtual int operator()(DetElement de) { + virtual int processElement(DetElement de) { if ( de.isValid() ) { if ( de.hasConditions() ) { DetAlign align(de); DetConditions conditions(de); Conditions::Container cont = conditions.conditions(); - printout(INFO,"Conditions2Alignments", + printout(DEBUG,"AlignRegister", "++ Processing DE %s hasConditions:%s [%d entries]", de.path().c_str(), yes_no(de.hasConditions()), int(cont.numKeys())); for ( const auto& c : cont.keys() ) { Condition cond = cont.get(c.first, *user_pool); - printout(INFO,"Conditions2Alignments", + printout(DEBUG,"AlignRegister", "++ Processing DE %s Cond:%s Key:%08X flags:%d", - de.path().c_str(), cond.name().c_str(), cond.key(), cond->flags); + de.path().c_str(), cond.name(), cond.key(), cond->flags); if ( (cond->flags&Condition::ALIGNMENT) ) { - ConditionKey k(cond.name()+"/Tranformations"); + ConditionKey k(cond->name+"/Tranformations"); // // The alignment access through the DetElement object is optional! // It is slow and deprecated. The access using the UserPool directly @@ -90,25 +90,23 @@ namespace { align.alignments()->addKey("Alignment",k.name); // // Now add the dependency to the alignmant manager - DependencyBuilder b(k, updateCall->addRef()); - b->detector = de; + DependencyBuilder b(k, updateCall->addRef(), de); b.add(ConditionKey(cond->name)); - Conditions::ConditionDependency* dep = b.release(); - bool result = alignmentMgr.adoptDependency(dep); + bool result = alignmentMgr.adoptDependency(b.release()); if ( result ) { - printout(INFO,"Conditions2Alignments", - "++ Added Alignment dependency Cond:%s Key:%08X", - k.name.c_str(), k.hash); + printout(INFO,"AlignRegister", + "++ Added Alignment dependency Cond:%s Key:%08X flags:%d", + k.name.c_str(), k.hash, cond->flags); continue; } - printout(ERROR,"Conditions2Alignments", - "++ FAILED to add Alignment dependency Cond:%s Key:%08X", - k.name.c_str(), k.hash); + printout(ERROR,"AlignRegister", + "++ FAILED to add Alignment dependency Cond:%s Key:%08X flags:%d", + k.name.c_str(), k.hash, cond->flags); } } return 1; } - printout(INFO,"Conditions2Alignments","++ Processing DE %s hasConditions:%s", + printout(DEBUG,"AlignRegister","++ Processing DE %s hasConditions:%s", de.path().c_str(), yes_no(de.hasConditions())); } return 1; @@ -116,41 +114,41 @@ namespace { }; } - -#include "DDAlign/DDAlignTest.h" - +#include "DD4hep/PluginTester.h" +#include "DDCond/ConditionsPool.h" /// Convert alignments conditions to alignment objects -static void* ddalign_Conditions2Alignments(Geometry::LCDD& lcdd, int argc, char** argv) { +static void* ddalign_AlignmentRegister(Geometry::LCDD& lcdd, int argc, char** argv) { std::vector<char*> args_prepare, args_call; for(int i=0; i<argc && argv[i]; ++i) { if ( ::strcmp(argv[i],"-prepare") == 0 ) { - while( 0 != ::strcmp(argv[++i],"-prepare-end") && i<argc ) + while( (++i)<argc && argv[i] && 0 != ::strcmp(argv[i],"-prepare-end") ) args_prepare.push_back(argv[i]); } if ( ::strcmp(argv[i],"-call") == 0 ) { - while( 0 != ::strcmp(argv[++i],"-call-end") && i<argc ) + while( (++i)<argc && argv[i] && 0 != ::strcmp(argv[i],"-call-end") ) args_call.push_back(argv[i]); } } - DDAlignTest* test = lcdd.extension<DDAlignTest>(); + PluginTester* test = lcdd.extension<PluginTester>(); Conditions::UserPool* pool = (Conditions::UserPool*) PluginService::Create<void*>((const char*)args_prepare[0],&lcdd, int(args_prepare.size())-1, (char**)&args_prepare[1]); if ( 0 == pool ) { - except("Conditions2Alignments","++ Failed to prepare conditions user-pool!"); + except("AlignRegister","++ Failed to prepare conditions user-pool!"); } - test->alignmentsPool.adopt(pool); + test->addExtension<Conditions::UserPool>(pool,"ConditionsTestUserPool"); AlignmentUpdateCall* call = (AlignmentUpdateCall*) PluginService::Create<void*>((const char*)args_call[0],&lcdd, int(args_call.size())-1, (char**)&args_call[1]); if ( 0 == call ) { - except("Conditions2Alignments","++ Failed to create update call!"); + except("AlignRegister","++ Failed to create update call!"); } - Conditions2Alignments* obj = new Conditions2Alignments(lcdd, call, pool); + AlignmentRegister* obj = new AlignmentRegister(lcdd, call, pool); return obj; } -DECLARE_LCDD_CONSTRUCTOR(DDAlign_Conditions2Alignments,ddalign_Conditions2Alignments) +DECLARE_LCDD_CONSTRUCTOR(DDAlign_AlignmentRegister,ddalign_AlignmentRegister) + diff --git a/DDAlign/src/plugins/AlignmentsPrinter.cpp b/DDAlign/src/plugins/AlignmentsPrinter.cpp deleted file mode 100644 index f7b6fdcf8ef861a8c75afe353c5649124910d2b7..0000000000000000000000000000000000000000 --- a/DDAlign/src/plugins/AlignmentsPrinter.cpp +++ /dev/null @@ -1,66 +0,0 @@ -//========================================================================== -// AIDA Detector description implementation for LCD -//-------------------------------------------------------------------------- -// Copyright (C) Organisation europeenne pour la Recherche nucleaire (CERN) -// All rights reserved. -// -// For the licensing terms see $DD4hepINSTALL/LICENSE. -// For the list of contributors see $DD4hepINSTALL/doc/CREDITS. -// -// Author : M.Frank -// -//========================================================================== - -// Framework includes -#include "DD4hep/Printout.h" -#include "DD4hep/DetFactoryHelper.h" -//#include "DD4hep/Conditions.h" -//#include "DD4hep/DetAlign.h" -#include "DD4hep/AlignmentsProcessor.h" -#include "DD4hep/objects/AlignmentsInterna.h" - -using namespace DD4hep; -using namespace DD4hep::Alignments; - -// ====================================================================================== - -namespace { - /// Print alignments - /** - * - * \author M.Frank - * \version 1.0 - * \date 18/11/2016 - * \ingroup DD4HEP_DDALIGN - */ - class AlignmentPrinter : public AlignmentsProcessor { - public: - /// Initializing constructor - AlignmentPrinter() : AlignmentsProcessor(0) {} - /// Default destructor - virtual ~AlignmentPrinter() = default; - /// Callback to output conditions information - virtual int operator()(Alignment a) { - const Alignments::Delta& D = a.data().delta; - printout(INFO,"Alignment","++ (%11s-%8s-%5s) Cond:%p 'Alignment'", - D.hasTranslation() ? "Translation" : "", - D.hasRotation() ? "Rotation" : "", - D.hasPivot() ? "Pivot" : "", - a.data().hasCondition() ? a.data().condition.ptr() : 0); - return 1; - } - /// Container callback for object processing - virtual int operator()(Container container) - { return this->self_t::operator()(container); } - /// Callback to output conditions information - virtual int operator()(DetElement de) - { return this->self_t::operator()(de); } - }; -} - -/// Convert alignments conditions to alignment objects -static void* ddalign_AlignmentsPrinter(Geometry::LCDD& /* lcdd */, int /* argc */, char** /* argv */) { - return (AlignmentsProcessor*)(new AlignmentPrinter()); -} - -DECLARE_LCDD_CONSTRUCTOR(DDAlign_AlignmentsPrinter,ddalign_AlignmentsPrinter) diff --git a/DDAlign/src/plugins/DDAlignTest.cpp b/DDAlign/src/plugins/DDAlignTest.cpp deleted file mode 100644 index 63751a3061eaac8c82565fe9ac617e98b13cad12..0000000000000000000000000000000000000000 --- a/DDAlign/src/plugins/DDAlignTest.cpp +++ /dev/null @@ -1,32 +0,0 @@ -//========================================================================== -// AIDA Detector description implementation for LCD -//-------------------------------------------------------------------------- -// Copyright (C) Organisation europeenne pour la Recherche nucleaire (CERN) -// All rights reserved. -// -// For the licensing terms see $DD4hepINSTALL/LICENSE. -// For the list of contributors see $DD4hepINSTALL/doc/CREDITS. -// -// Author : M.Frank -// -//========================================================================== - -// Framework includes -#include "DD4hep/Printout.h" -#include "DD4hep/DetectorTools.h" -#include "DD4hep/DetFactoryHelper.h" - -using namespace DD4hep; - -// ====================================================================================== -#include "DDAlign/DDAlignTest.h" -static long install_ddalign_tester(Geometry::LCDD& lcdd, int /* argc */, char** /* argv */) { - Alignments::AlignmentsManager alignMgr = Alignments::AlignmentsManager::from(lcdd); - Conditions::ConditionsManager condMgr = Conditions::ConditionsManager::from(lcdd); - DDAlignTest* test = new DDAlignTest(); - test->alignmentsMgr = alignMgr; - test->conditionsMgr = condMgr; - lcdd.addExtension<DDAlignTest>(test); - return 1; -} -DECLARE_APPLY(DDAlign_InstallTest, install_ddalign_tester) diff --git a/DDCond/src/ConditionsInterna.cpp b/DDCond/src/ConditionsInterna.cpp index 539c3fd6a4d76c94c5b249c8b87149098f473723..32150b794a0a4cda4fb530ed89b3837724474202 100644 --- a/DDCond/src/ConditionsInterna.cpp +++ b/DDCond/src/ConditionsInterna.cpp @@ -626,14 +626,14 @@ ConditionsManagerObject::get(Condition::key_type key, const Condition::iov_type& RC::const_iterator start = conditions.begin(); Condition first = *start; printout(ERROR,"ConditionsManager","+++ Condition %s [%08X] is ambiguous for IOV %s:", - first.name().c_str(), key, iov.str().c_str()); + first.name(), key, iov.str().c_str()); for(RC::const_iterator i=start; i!=conditions.end(); ++i) { Condition c = *i; printout(ERROR,"ConditionsManager","+++ %s [%s] = %s", - c.name().c_str(), c->iov->str().c_str(), c->value.c_str()); + c.name(), c->iov->str().c_str(), c->value.c_str()); } except("ConditionsManager","+++ Condition %s [%08X] is ambiguous for IOV %s:", - first.name().c_str(), key, iov.str().c_str()); + first.name(), key, iov.str().c_str()); } return Condition(); } diff --git a/DDCond/src/ConditionsRepository.cpp b/DDCond/src/ConditionsRepository.cpp index 14d9ebe4a5eb09dee812737887d07ba56f3a2256..f4b187ac73e549d0ab3c15969bd6b2c64d74a46a 100644 --- a/DDCond/src/ConditionsRepository.cpp +++ b/DDCond/src/ConditionsRepository.cpp @@ -129,7 +129,7 @@ namespace { << "." << long(siz_tot) << endl; for(AllConditions::const_iterator i=all.begin(); i!=all.end(); ++i) { Condition c = (*i).second; - ::snprintf(text, sizeof(text), fmt, c.key(), c.name().c_str(), c.address().c_str()); + ::snprintf(text, sizeof(text), fmt, c.key(), c.name(), c.address().c_str()); out << text << endl; } out.close(); diff --git a/DDCond/src/ConditionsTest.cpp b/DDCond/src/ConditionsTest.cpp index e9e8c71890af946a9613c339d72b13bdec196b16..eea73192f91d3f01831832cb3d56b634aa855d9b 100644 --- a/DDCond/src/ConditionsTest.cpp +++ b/DDCond/src/ConditionsTest.cpp @@ -49,23 +49,23 @@ namespace DD4hep { T val = _multiply(c.get<T>(),norm); ::snprintf(text_format,sizeof(text_format)," Bound value %%s : value:%s [%s] Type: %%s", Primitive<T>::default_format(),Primitive<T>::default_format()); - printout(INFO,"Cond_Value",text_format, c.name().c_str(), value, val, typeName(c.typeInfo()).c_str()); + printout(INFO,"Cond_Value",text_format, c.name(), value, val, typeName(c.typeInfo()).c_str()); return; } ::snprintf(text_format,sizeof(text_format)," Bound value %%s : value:%s Type: %%s", Primitive<T>::default_format()); - printout(INFO,"Cond_Value",text_format, c.name().c_str(), value, typeName(c.typeInfo()).c_str()); + printout(INFO,"Cond_Value",text_format, c.name(), value, typeName(c.typeInfo()).c_str()); } template <> void __print_bound_val<string>(Condition c, const char*) { const string& v = access_val<string>(c); printout(INFO,"Cond_Value"," Bound value %s : string value:%s Type: %s Ptr:%016X", - c.name().c_str(), c.get<string>().c_str(),typeName(c.typeInfo()).c_str(), + c.name(), c.get<string>().c_str(),typeName(c.typeInfo()).c_str(), (void*)&v); } template <typename T> void __print_bound_container(Condition c, const char*) { const T& v = access_val<T>(c); printout(INFO,"Cond_Value"," Bound value %s : size:%d = %s Type: %s Ptr:%016X", - c.name().c_str(), int(v.size()), c.data().str().c_str(), + c.name(), int(v.size()), c.data().str().c_str(), typeName(c.typeInfo()).c_str(), (void*)&v); } @@ -114,8 +114,8 @@ namespace DD4hep { template <> void print_condition<void>(Condition c) { string type = c.type(); printout(INFO,"Cond_Value","%-32s [%16s] : %s [%s] ", - c.name().c_str(),c.type().c_str(), - c.value().c_str(),c->validity.c_str()); + c.name(), c.type().c_str(), + c.value().c_str(), c->validity.c_str()); if ( type == "alignment" ) print_bound_value<string>(c); else if ( type == "temperature" ) diff --git a/DDCond/src/ConditionsTextRepository.cpp b/DDCond/src/ConditionsTextRepository.cpp index 4798d526cd792c99101ed4ec0e28dc68ebda4d6f..e9913f7d4e2522cd5a9042a8a4d6680f224a308e 100644 --- a/DDCond/src/ConditionsTextRepository.cpp +++ b/DDCond/src/ConditionsTextRepository.cpp @@ -129,7 +129,7 @@ namespace { << "." << long(siz_tot) << endl; for(AllConditions::const_iterator i=all.begin(); i!=all.end(); ++i) { Condition c = (*i).second; - ::snprintf(text, sizeof(text), fmt, c.key(), c.name().c_str(), c.address().c_str()); + ::snprintf(text, sizeof(text), fmt, c.key(), c.name(), c.address().c_str()); out << text << endl; } out.close(); diff --git a/DDCond/src/plugins/ConditionsPlugins.cpp b/DDCond/src/plugins/ConditionsPlugins.cpp index 5f281d4dcddd59c5e5ce3afe9e1352df2ba3007d..7e4deaf39c3991cab6ad993f3b9944c2a1b6986b 100644 --- a/DDCond/src/plugins/ConditionsPlugins.cpp +++ b/DDCond/src/plugins/ConditionsPlugins.cpp @@ -16,6 +16,7 @@ #include "DD4hep/Plugins.h" #include "DD4hep/Printout.h" #include "DD4hep/Conditions.h" +#include "DD4hep/PluginCreators.h" #include "DD4hep/DetFactoryHelper.h" #include "DD4hep/ConditionsPrinter.h" @@ -59,32 +60,6 @@ static int ddcond_install_cond_mgr (LCDD& lcdd, int argc, char** argv) { } DECLARE_APPLY(DD4hep_ConditionsManagerInstaller,ddcond_install_cond_mgr) -// ====================================================================================== -static ConditionsProcessor* create_processor(lcdd_t& lcdd, int argc, char** argv) { - class Processor {public: virtual ~Processor() {} }; - ConditionsProcessor* processor = 0; - if ( argc < 2 ) { - except("CondPoolProcessor","++ No processor creator name given!"); - } - for(int i=0; i<argc; ++i) { - if ( 0 == ::strncmp(argv[i],"-processor",3) ) { - vector<char*> args; - for(int j=2; j<argc && argv[j]; ++j) args.push_back(argv[j]); - args.push_back(0); - string fac = argv[++i]; - Condition::Processor* p = (Condition::Processor*) - PluginService::Create<void*>(fac,&lcdd,int(args.size()),&args[0]); - processor = dynamic_cast<ConditionsProcessor*>(p); - break; - } - } - if ( !processor ) { - except("CondPoolProcessor", - "++ Found arguments in plugin call, but could not make any sense of them...."); - } - return processor; -} - // ====================================================================================== /// Plugin function: Dump of all Conditions pool with or without conditions /** @@ -96,7 +71,8 @@ static ConditionsProcessor* create_processor(lcdd_t& lcdd, int argc, char** argv * \date 01/04/2016 */ static int ddcond_conditions_pool_processor(lcdd_t& lcdd, bool process_pool, bool process_conditions, int argc, char** argv) { - ConditionsProcessor* processor = create_processor(lcdd,argc,argv); + DetElement::Processor* p = createProcessor<DetElement::Processor>(lcdd,argc,argv); + ConditionsProcessor* processor = dynamic_cast<ConditionsProcessor*>(p); typedef std::vector<const IOVType*> _T; typedef ConditionsIOVPool::Elements _E; typedef RangeConditions _R; @@ -220,7 +196,7 @@ static int ddcond_detelement_dump(LCDD& lcdd, int /* argc */, char** /* argv */) (unsigned long)de.volumeID(), sens); printer.setName(string(tmp)+de.name()); if ( de.hasConditions() ) { - (printer)(de); + printer.processElement(de); } for (const auto& c : de.children() ) dump(c.second,level+1); @@ -308,7 +284,7 @@ static int ddcond_detelement_processor(LCDD& lcdd, int argc, char** argv) { /// Dump method. long dump(DetElement de) { if ( de.hasConditions() ) { - (*processor)(de); + processor->processElement(de); } for (const auto& c : de.children() ) dump(c.second); @@ -317,11 +293,11 @@ static int ddcond_detelement_processor(LCDD& lcdd, int argc, char** argv) { }; ConditionsProcessor* processor = 0; if ( argc > 0 ) { - processor = create_processor(lcdd, argc, argv); + processor = createProcessor<ConditionsProcessor>(lcdd, argc, argv); } else { const void* args[] = { "-processor", "DD4hepConditionsPrinter", 0}; - processor = create_processor(lcdd, 2, (char**)args); + processor = createProcessor<ConditionsProcessor>(lcdd, 2, (char**)args); } return Actor(processor,ConditionsManager::from(lcdd)).dump(lcdd.world()); } @@ -337,7 +313,7 @@ DECLARE_APPLY(DD4hep_DetElementConditionsProcessor,ddcond_detelement_processor) * \date 01/04/2016 */ static long ddcond_synchronize_conditions(lcdd_t& lcdd, int argc, char** argv) { - if ( argc > 0 ) { + if ( argc >= 2 ) { string iov_type = argv[0]; IOV::Key::first_type iov_key = *(IOV::Key::first_type*)argv[1]; ConditionsManager manager = ConditionsManager::from(lcdd); @@ -366,7 +342,8 @@ static long ddcond_synchronize_conditions(lcdd_t& lcdd, int argc, char** argv) { user_pool->clear(); return 1; } - except("Conditions","+++ Failed update conditions. No event time argument given!"); + except("Conditions","+++ Failed update conditions. Arguments were: '%s'", + arguments(argc,argv).c_str()); return 0; } DECLARE_APPLY(DD4hep_ConditionsSynchronize,ddcond_synchronize_conditions) @@ -407,16 +384,28 @@ DECLARE_APPLY(DD4hep_ConditionsClean,ddcond_clean_conditions) * \date 01/04/2016 */ static long ddcond_create_repository(lcdd_t& lcdd, int argc, char** argv) { - if ( argc > 0 ) { - string output = argv[0]; - printout(INFO,"Conditions", - "+++ ConditionsRepository: Creating %s",output.c_str()); - ConditionsManager manager = ConditionsManager::from(lcdd); - ConditionsRepository().save(manager,output); - return 1; + bool arg_error = false; + string output = ""; + for(int i=0; i<argc && argv[i]; ++i) { + if ( 0 == ::strncmp("-output",argv[i],4) ) + output = argv[++i]; + else + arg_error = true; } - except("Conditions","+++ Failed creating conditions repository. Insufficient arguments!"); - return 0; + if ( arg_error || output.empty() ) { + /// Help printout describing the basic command line interface + cout << + "Usage: -plugin <name> -arg [-arg] \n" + " name: factory name DD4hep_ConditionsCreateRepository \n\n" + " -output <string> Output file name. \n\n" + "\tArguments given: " << arguments(argc,argv) << endl << flush; + ::_exit(EINVAL); + } + printout(INFO,"Conditions", + "+++ ConditionsRepository: Creating %s",output.c_str()); + ConditionsManager manager = ConditionsManager::from(lcdd); + ConditionsRepository().save(manager,output); + return 1; } DECLARE_APPLY(DD4hep_ConditionsCreateRepository,ddcond_create_repository) @@ -429,31 +418,99 @@ DECLARE_APPLY(DD4hep_ConditionsCreateRepository,ddcond_create_repository) * \version 1.0 * \date 01/04/2016 */ -static long ddcond_dump_repository(lcdd_t& lcdd, int argc, char** argv) { - if ( argc > 0 ) { - typedef ConditionsRepository::Data Data; - Data data; - string input = argv[0]; - printout(INFO,"Conditions", - "+++ ConditionsRepository: Dumping %s",input.c_str()); - ConditionsManager manager = ConditionsManager::from(lcdd); - if ( ConditionsRepository().load(input, data) ) { - printout(INFO,"Repository","%-8s %-60s %-60s","Key","Name","Address"); - for(Data::const_iterator i=data.begin(); i!=data.end(); ++i) { - const ConditionsRepository::Entry& e = *i; - string add = e.address; - if ( add.length() > 80 ) add = e.address.substr(0,60) + "..."; - printout(INFO,"Repository","%08X %s",e.key,e.name.c_str()); - printout(INFO,"Repository"," -> %s",e.address.c_str()); - } +static long ddcond_dump_repository(lcdd_t& lcdd, int argc, char** argv) { + typedef ConditionsRepository::Data Data; + bool arg_error = false; + string input = ""; + Data data; + for(int i=0; i<argc && argv[i]; ++i) { + if ( 0 == ::strncmp("-input",argv[i],4) ) + input = argv[++i]; + else + arg_error = true; + } + if ( arg_error || input.empty() ) { + /// Help printout describing the basic command line interface + cout << + "Usage: -plugin <name> -arg [-arg] \n" + " name: factory name DD4hep_ConditionsDumpRepository \n\n" + " -input <string> Input file name. \n\n" + "\tArguments given: " << arguments(argc,argv) << endl << flush; + ::_exit(EINVAL); + } + printout(INFO,"Conditions", + "+++ ConditionsRepository: Dumping %s",input.c_str()); + ConditionsManager manager = ConditionsManager::from(lcdd); + if ( ConditionsRepository().load(input, data) ) { + printout(INFO,"Repository","%-8s %-60s %-60s","Key","Name","Address"); + for(Data::const_iterator i=data.begin(); i!=data.end(); ++i) { + const ConditionsRepository::Entry& e = *i; + string add = e.address; + if ( add.length() > 80 ) add = e.address.substr(0,60) + "..."; + printout(INFO,"Repository","%08X %s",e.key,e.name.c_str()); + printout(INFO,"Repository"," -> %s",e.address.c_str()); } - return 1; } - except("Conditions","+++ Failed dumping conditions repository. Insufficient arguments!"); - return 0; + return 1; } DECLARE_APPLY(DD4hep_ConditionsDumpRepository,ddcond_dump_repository) +/// Basic entry point to instantiate the basic DD4hep conditions/alignmants printer +/** + * Factory: DD4hepConditionsPrinter, DD4hepAlignmentsPrinter + * + * \author M.Frank + * \version 1.0 + * \date 17/11/2016 + */ +#include "DD4hep/PluginTester.h" +template <typename PRINTER> +static void* create_printer(Geometry::LCDD& lcdd, int argc,char** argv) { + typedef typename PRINTER::pool_type pool_t; + string prefix = "", name = ""; + int flags = 0, have_pool = 0, arg_error = false; + for(int i=0; i<argc && argv[i]; ++i) { + if ( 0 == ::strncmp("-prefix",argv[i],4) ) + prefix = argv[++i]; + else if ( 0 == ::strncmp("-name",argv[i],5) ) + name = argv[++i]; + else if ( 0 == ::strncmp("-flags",argv[i],5) ) + flags = ::atol(argv[++i]); + else if ( 0 == ::strncmp("-pool",argv[i],5) ) + have_pool = 1; + else + arg_error = true; + } + if ( arg_error ) { + /// Help printout describing the basic command line interface + cout << + "Usage: -plugin <name> -arg [-arg] \n" + " name: factory name DD4hep_ConditionsPrinter, DD4hep_AlignmentsPrinter\n\n" + " -prefix <string> Printout prefix for user customized output. \n" + " -flags <number> Printout processing flags. \n" + " -pool Attach conditions user pool from \n" + " PluginTester instance attached to LCDD. \n\n" + "\tArguments given: " << arguments(argc,argv) << endl << flush; + ::_exit(EINVAL); + } + DetElement world = lcdd.world(); + printout(INFO,"Printer","World=%s [%p]",world.path().c_str(),world.ptr()); + PRINTER* p = (flags) ? new PRINTER(prefix,flags) : new PRINTER(prefix); + if ( have_pool != 0 ) { + PluginTester* test = lcdd.extension<PluginTester>(); + pool_t* pool = test->extension<pool_t>("ConditionsTestUserPool"); + if ( !name.empty() ) p->name = name; + p->setPool(pool); + } + return (void*)dynamic_cast<DetElement::Processor*>(p); +} +#include "DD4hep/ConditionsPrinter.h" +DECLARE_LCDD_CONSTRUCTOR(DD4hep_ConditionsPrinter,create_printer<Conditions::ConditionsPrinter>) +#include "DD4hep/AlignmentsPrinter.h" +DECLARE_LCDD_CONSTRUCTOR(DD4hep_AlignmentsPrinter,create_printer<Alignments::AlignmentsPrinter>) +#include "DD4hep/AlignedVolumePrinter.h" +DECLARE_LCDD_CONSTRUCTOR(DD4hep_AlignedVolumePrinter,create_printer<Alignments::AlignedVolumePrinter>) + // ====================================================================================== /// Plugin entry point: Load conditions repository csv file into conditions manager /** diff --git a/DDCond/src/plugins/ConditionsRepositoryParser.cpp b/DDCond/src/plugins/ConditionsRepositoryParser.cpp index 616394b61ef2ced02f10aff675210fe721f49c52..f8dd4a02930b9df4ddf7d161ee6b119570a97672 100644 --- a/DDCond/src/plugins/ConditionsRepositoryParser.cpp +++ b/DDCond/src/plugins/ConditionsRepositoryParser.cpp @@ -418,6 +418,7 @@ namespace DD4hep { xml_coll_t(e,_UC(mapping)).for_each(Converter<mapping>(lcdd,param,optional)); xml_coll_t(e,_UC(sequence)).for_each(Converter<sequence>(lcdd,param,optional)); xml_coll_t(e,_UC(alignment)).for_each(Converter<alignment>(lcdd,param,optional)); + xml_coll_t(e,_UC(detelement)).for_each(Converter<detelement>(lcdd,param,optional)); } /** Convert repository objects diff --git a/DDCore/include/DD4hep/AlignedVolumePrinter.h b/DDCore/include/DD4hep/AlignedVolumePrinter.h new file mode 100644 index 0000000000000000000000000000000000000000..77759adbed0f8c2e1432ce2236d59c3c4a70e6c0 --- /dev/null +++ b/DDCore/include/DD4hep/AlignedVolumePrinter.h @@ -0,0 +1,64 @@ +//========================================================================== +// AIDA Detector description implementation for LCD +//-------------------------------------------------------------------------- +// Copyright (C) Organisation europeenne pour la Recherche nucleaire (CERN) +// All rights reserved. +// +// For the licensing terms see $DD4hepINSTALL/LICENSE. +// For the list of contributors see $DD4hepINSTALL/doc/CREDITS. +// +// Author : M.Frank +// +//========================================================================== +#ifndef DD4HEP_DDCORE_ALIGNEDVOLUMEPRINTER_H +#define DD4HEP_DDCORE_ALIGNEDVOLUMEPRINTER_H + +// Framework includes +#include "DD4hep/AlignmentsProcessor.h" + +/// Namespace for the AIDA detector description toolkit +namespace DD4hep { + + /// Namespace for the AIDA detector description toolkit supporting XML utilities + namespace Alignments { + + /// Generic Alignments data dumper. + /** + * Please note that the principle of locality applies: + * The object is designed for stack allocation and configuration. + * It may NOT be shared across threads! + * + * \author M.Frank + * \version 1.0 + * \date 31/03/2016 + * \ingroup DD4HEP_DDDB + */ + class AlignedVolumePrinter : public AlignmentsProcessor { + public: + /// Printer name. Want to know who is printing what + std::string name; + /// Printout prefix + std::string prefix; + protected: + /// Printout processing and customization flag + int m_flag; + + public: + /// Initializing constructor + AlignedVolumePrinter(const std::string& prefix="",int flags=0); + /// Default destructor + virtual ~AlignedVolumePrinter() = default; + /// Set name for printouts + void setName(const std::string& value) { name = value; } + /// Set prefix for printouts + void setPrefix(const std::string& value) { prefix = value; } + /// Callback to output alignments information + virtual int operator()(Alignment cond); + /// Container callback for object processing + virtual int operator()(Container container); + /// Callback to output alignments information of an entire DetElement + virtual int processElement(DetElement de); + }; + } /* End namespace Alignments */ +} /* End namespace DD4hep */ +#endif /* DD4HEP_DDCORE_ALIGNEDVOLUMEPRINTER_H */ diff --git a/DDCore/include/DD4hep/AlignmentData.h b/DDCore/include/DD4hep/AlignmentData.h index 7cd0fa7c9b95337931f8055b8e6497e00d637351..1c582c8a3875b33fa066321d735b6200c93ba443 100644 --- a/DDCore/include/DD4hep/AlignmentData.h +++ b/DDCore/include/DD4hep/AlignmentData.h @@ -135,6 +135,8 @@ namespace DD4hep { Delta delta; /// Intermediate buffer to store the transformation to the world coordination system mutable TGeoHMatrix worldTrafo; + /// Delta transformation to the world coordination system + mutable TGeoHMatrix worldDelta; /// Intermediate buffer to store the transformation to the parent detector element mutable TGeoHMatrix detectorTrafo; /// The list of TGeoNodes (physical placements) diff --git a/DDCore/include/DD4hep/Alignments.h b/DDCore/include/DD4hep/Alignments.h index 7a0668411a4406214066299526e7845562a6e632..f3bc6aee32851dc7a01d2eb451252b44cbfa41fb 100644 --- a/DDCore/include/DD4hep/Alignments.h +++ b/DDCore/include/DD4hep/Alignments.h @@ -176,6 +176,8 @@ namespace DD4hep { const IOVType& iovType() const; /// Access the IOV block const iov_type& iov() const; + /// Access the hash identifier + key_type key() const; /** Data block (bound type) */ /// Data accessor for the use of decorators diff --git a/DDCore/include/DD4hep/AlignmentsPrinter.h b/DDCore/include/DD4hep/AlignmentsPrinter.h index 0a9863b5e1216c7eaaf1b15a3e76f2f797914e0d..1c7a6726b44c19f46b74e656e9d857084a14368a 100644 --- a/DDCore/include/DD4hep/AlignmentsPrinter.h +++ b/DDCore/include/DD4hep/AlignmentsPrinter.h @@ -35,9 +35,12 @@ namespace DD4hep { */ class AlignmentsPrinter : public AlignmentsProcessor { public: + /// Printer name. Want to know who is printing what std::string name; + /// Printout prefix std::string prefix; protected: + /// Printout processing and customization flag int m_flag; public: @@ -54,10 +57,21 @@ namespace DD4hep { /// Container callback for object processing virtual int operator()(Container container); /// Callback to output alignments information of an entire DetElement - virtual int operator()(DetElement de) - { return this->AlignmentsProcessor::operator()(de); } + virtual int processElement(DetElement de); }; + /// Default printout of an alignment entry + void printAlignment(const std::string& prefix, Alignment alignment); + + /// Default printout of a container entry + void printContainer(const std::string& prefix, Container container, UserPool* pool); + + /// Default printout of a detector element entry + void printElement(const std::string& prefix, DetElement element, UserPool* pool); + + /// PrintElement placement with/without alignment applied + void printElementPlacement(const std::string& prefix, DetElement detector, UserPool* pool); + } /* End namespace Alignments */ } /* End namespace DD4hep */ #endif /* DD4HEP_DDCORE_ALIGNMENTSPRINTER_H */ diff --git a/DDCore/include/DD4hep/AlignmentsProcessor.h b/DDCore/include/DD4hep/AlignmentsProcessor.h index 4b1463fd6d0930b58e0aa893f97541a97fe8d582..725d0bc88cf7e451957103dd5dede1b76f742045 100644 --- a/DDCore/include/DD4hep/AlignmentsProcessor.h +++ b/DDCore/include/DD4hep/AlignmentsProcessor.h @@ -40,30 +40,33 @@ namespace DD4hep { * \ingroup DD4HEP_ALIGNMENTS */ class AlignmentsProcessor : - public Alignment::Processor, - public Container::Processor, - public Geometry::DetElement::Processor + virtual public Alignment::Processor, + virtual public Container::Processor, + virtual public Geometry::DetElement::Processor { - protected: + public: /// Self type definition - typedef AlignmentsProcessor self_t; + typedef AlignmentsProcessor self_type; + /// Pool definition + typedef UserPool pool_type; + protected: /// Make DetElement type local typedef Geometry::DetElement DetElement; /// Reference to the user pool - UserPool* m_pool; + pool_type* m_pool; public: /// Initializing constructor - AlignmentsProcessor(UserPool* p) : m_pool(p) {} + AlignmentsProcessor(pool_type* p) : m_pool(p) {} /// Default destructor virtual ~AlignmentsProcessor() = default; /// Set pool - void setPool(UserPool* value) { m_pool = value; } + void setPool(pool_type* value) { m_pool = value; } /// Callback to output alignments information virtual int operator()(Alignment cond); /// Container callback for object processing virtual int operator()(Container container); /// Callback to output alignments information of an entire DetElement - virtual int operator()(DetElement de); + virtual int processElement(DetElement de); }; /// Generic Alignment object collector @@ -72,7 +75,7 @@ namespace DD4hep { * AlignmentsProcessor base class for further information. * */ - class AlignmentsCollector : public AlignmentsProcessor { + class AlignmentsCollector : virtual public AlignmentsProcessor { public: /// Collection container std::vector<Alignment> alignments; @@ -88,10 +91,10 @@ namespace DD4hep { } /// Container callback for object processing virtual int operator()(Container container) - { return this->self_t::operator()(container); } + { return this->self_type::operator()(container); } /// Callback to output alignments information of an entire DetElement - virtual int operator()(DetElement detector) - { return this->self_t::operator()(detector); } + virtual int processElement(DetElement detector) + { return this->self_type::processElement(detector); } }; } /* End namespace Alignments */ diff --git a/DDCore/include/DD4hep/ConditionDerived.h b/DDCore/include/DD4hep/ConditionDerived.h index af5426159a44a952e313a336d2fafa21f3afc595..e7b8095a94426ec38ffd6c32a0c7336e646e8780 100644 --- a/DDCore/include/DD4hep/ConditionDerived.h +++ b/DDCore/include/DD4hep/ConditionDerived.h @@ -206,6 +206,8 @@ namespace DD4hep { public: /// Initializing constructor DependencyBuilder(const ConditionKey& target, ConditionUpdateCall* call); + /// Initializing constructor + DependencyBuilder(const ConditionKey& target, ConditionUpdateCall* call, Geometry::DetElement de); /// Default destructor virtual ~DependencyBuilder(); /// Access underlying object directly diff --git a/DDCore/include/DD4hep/Conditions.h b/DDCore/include/DD4hep/Conditions.h index bb0e9e97123ed46fe096abc65a8f2a02dd72314a..97e71a8dc0014ca0c0bfa2d45c8d7319b7bcb811 100644 --- a/DDCore/include/DD4hep/Conditions.h +++ b/DDCore/include/DD4hep/Conditions.h @@ -148,8 +148,6 @@ namespace DD4hep { const iov_type& iov() const; /** Direct data items in string form */ - /// Access the name of the condition - const std::string& name() const; /// Access the type field of the condition const std::string& type() const; /// Access the comment field of the condition diff --git a/DDCore/include/DD4hep/ConditionsPrinter.h b/DDCore/include/DD4hep/ConditionsPrinter.h index 4b7b9742f728de1580794999d1c92b51b24d8baf..24979431ab98542139c87c643e0c22b9e60be8e8 100644 --- a/DDCore/include/DD4hep/ConditionsPrinter.h +++ b/DDCore/include/DD4hep/ConditionsPrinter.h @@ -35,9 +35,12 @@ namespace DD4hep { */ class ConditionsPrinter : public ConditionsProcessor { public: + /// Printer name. Want to know who is printing what std::string name; + /// Printout prefix std::string prefix; protected: + /// Printout processing and customization flag int m_flag; public: @@ -55,8 +58,8 @@ namespace DD4hep { /// Container callback for object processing virtual int operator()(Container container); /// Callback to output conditions information of an entire DetElement - virtual int operator()(DetElement de) - { return this->ConditionsProcessor::operator()(de); } + virtual int processElement(DetElement de) + { return this->ConditionsProcessor::processElement(de); } }; } /* End namespace Conditions */ diff --git a/DDCore/include/DD4hep/ConditionsProcessor.h b/DDCore/include/DD4hep/ConditionsProcessor.h index 1a4c96e48ad538b88a2a86935a4a42b501fd6275..cc46848e6f4cd634f2fc2c01555386a8e0a5b02e 100644 --- a/DDCore/include/DD4hep/ConditionsProcessor.h +++ b/DDCore/include/DD4hep/ConditionsProcessor.h @@ -40,30 +40,33 @@ namespace DD4hep { * \ingroup DD4HEP_CONDITIONS */ class ConditionsProcessor : - public Condition::Processor, - public Container::Processor, - public Geometry::DetElement::Processor + virtual public Condition::Processor, + virtual public Container::Processor, + virtual public Geometry::DetElement::Processor { - protected: + public: /// Self type definition - typedef ConditionsProcessor self_t; + typedef ConditionsProcessor self_type; + /// Pool definition + typedef UserPool pool_type; + protected: /// Make DetElement type local typedef Geometry::DetElement DetElement; /// Reference to the user pool - UserPool* m_pool; + pool_type* m_pool; public: /// Initializing constructor - ConditionsProcessor(UserPool* p) : m_pool(p) {} + ConditionsProcessor(pool_type* p) : m_pool(p) {} /// Default destructor virtual ~ConditionsProcessor() = default; /// Set pool - void setPool(UserPool* value) { m_pool = value; } + void setPool(pool_type* value) { m_pool = value; } /// Callback to output conditions information virtual int operator()(Condition cond); /// Container callback for object processing virtual int operator()(Container container); /// Callback to output conditions information of an entire DetElement - virtual int operator()(DetElement de); + virtual int processElement(DetElement de); }; /// Generic Condition object collector @@ -72,7 +75,7 @@ namespace DD4hep { * ConditionsProcessor base class for further information. * */ - class ConditionsCollector : public ConditionsProcessor { + class ConditionsCollector : virtual public ConditionsProcessor { public: /// Collection container std::vector<Condition> conditions; @@ -88,10 +91,10 @@ namespace DD4hep { } /// Container callback for object processing virtual int operator()(Container container) - { return this->self_t::operator()(container); } + { return this->self_type::operator()(container); } /// Callback to output conditions information of an entire DetElement - virtual int operator()(DetElement detector) - { return this->self_t::operator()(detector); } + virtual int processElement(DetElement detector) + { return this->self_type::processElement(detector); } }; } /* End namespace Conditions */ } /* End namespace DD4hep */ diff --git a/DDCore/include/DD4hep/Detector.h b/DDCore/include/DD4hep/Detector.h index af37ace0cc83275151b90ac07c0b65a5e7cdef9a..b913261ab484ee66b7237f82b6929eba5f73836c 100644 --- a/DDCore/include/DD4hep/Detector.h +++ b/DDCore/include/DD4hep/Detector.h @@ -182,9 +182,9 @@ namespace DD4hep { /// Default constructor Processor(); /// Default destructor - virtual ~Processor() = default; + virtual ~Processor(); /// Container callback for object processing - virtual int operator()(DetElement detector) = 0; + virtual int processElement(DetElement detector) = 0; }; /// Internal object type diff --git a/DDCore/include/DD4hep/PluginCreators.h b/DDCore/include/DD4hep/PluginCreators.h index 0ed1af10f3d9ee713e14d2bd20d360c0920fcfa5..dcb5fced92bac1a63ad15c1409b34fefc43bfb21 100644 --- a/DDCore/include/DD4hep/PluginCreators.h +++ b/DDCore/include/DD4hep/PluginCreators.h @@ -39,6 +39,7 @@ namespace DD4hep { void* createPlugin(const std::string& factory, Geometry::LCDD& lcdd, void* (*cast)(void*)); void* createPlugin(const std::string& factory, Geometry::LCDD& lcdd, const std::string& arg, void* (*cast)(void*)); void* createPlugin(const std::string& factory, Geometry::LCDD& lcdd, int argc, char** argv, void* (*cast)(void*)); + void* createProcessor(Geometry::LCDD& lcdd, int argc, char** argv, void* (*cast)(void*)); /// Handler for factories of type: ConstructionFactory with casted return type template <typename T> T* createPlugin(const std::string& factory, Geometry::LCDD& lcdd) { @@ -59,6 +60,20 @@ namespace DD4hep { return (plugin_t*)createPlugin(factory, lcdd, argc, (char**)argv, __cast::cast); } + /// Handler for factories of type: ConstructionFactory with casted return type + template <typename T> T* createProcessor(Geometry::LCDD& lcdd, int argc, char** argv) { + typedef T plugin_t; + struct __cast{ static void* cast(void* p) { return &dynamic_cast<plugin_t&>(*(plugin_t*)p); } }; + return (plugin_t*)createProcessor(lcdd, argc, argv, __cast::cast); + } + + /// Handler for factories of type: ConstructionFactory with casted return type + template <typename T> T* createProcessor(Geometry::LCDD& lcdd, int argc, const void** argv) { + typedef T plugin_t; + struct __cast{ static void* cast(void* p) { return &dynamic_cast<plugin_t&>(*(plugin_t*)p); } }; + return (plugin_t*)createProcessor(lcdd, argc, (char**)argv, __cast::cast); + } + } /* End namespace DD4hep */ #endif // DD4HEP_PLUGINCREATORS_H diff --git a/DDCore/include/DD4hep/PluginTester.h b/DDCore/include/DD4hep/PluginTester.h new file mode 100644 index 0000000000000000000000000000000000000000..34ed9d37b17307ec69e1080d98d92ba78076df6c --- /dev/null +++ b/DDCore/include/DD4hep/PluginTester.h @@ -0,0 +1,85 @@ +//========================================================================== +// AIDA Detector description implementation for LCD +//-------------------------------------------------------------------------- +// Copyright (C) Organisation europeenne pour la Recherche nucleaire (CERN) +// All rights reserved. +// +// For the licensing terms see $DD4hepINSTALL/LICENSE. +// For the list of contributors see $DD4hepINSTALL/doc/CREDITS. +// +// \author Markus Frank +// \date 2016-02-02 +// \version 1.0 +// +//========================================================================== +#ifndef DD4HEP_PLUGINTESTER_H +#define DD4HEP_PLUGINTESTER_H 1 + +// Framework includes + +// C/C++ include files +#include <typeinfo> +#include <string> +#include <map> + + +/// Namespace for the AIDA detector description toolkit +namespace DD4hep { + class PluginTester { + public: + /// Definition of the extension type + typedef std::pair<const std::type_info*,std::string> key_type; + typedef std::map<key_type, void*> Extensions; + /// Extensions destructor type + typedef void (*destruct_t)(void*); + /// Defintiion of the extension entry + struct Entry { + destruct_t destruct; + int id; + }; + typedef std::map<const std::type_info*, Entry> ExtensionMap; + + /// The extensions object + Extensions extensions; //! + /// Pointer to the extension map + ExtensionMap* extensionMap; //! + + /// Function to be passed as dtor if object should NOT be deleted! + static void _noDelete(void*) {} + + /// Templated destructor function + template <typename T> static void _delete(void* ptr) { + delete (T*) (ptr); + } + + /// Add an extension object to the detector element + void* addExtension(void* ptr, const std::string& name, const std::type_info& info, destruct_t dtor); + /// Access an existing extension object from the detector element + void* extension(const std::string& name, const std::type_info& info, bool alert) const; + /// Remove an existing extension object from the instance + void* removeExtension(const std::string& name, const std::type_info& info, bool destroy); + + public: + /// Default constructor + PluginTester(); + /// Copy constructor + PluginTester(const PluginTester& copy) = delete; + /// Default destructor + virtual ~PluginTester(); + /// Assignment operator + PluginTester& operator=(const PluginTester& copy) = delete; + /// Clear all extensions + void clear(bool destroy=true); + template<typename Q> Q* addExtension(Q* ptr, const std::string& name) { + return (Q*)addExtension(ptr, name, typeid(Q), _delete<Q>); + } + template<typename Q> Q* extension(const std::string& name, bool alert=true) { + return (Q*)extension(name, typeid(Q), alert); + } + template<typename Q> Q* removeExtension(const std::string& name, bool destroy=true) { + return (Q*)removeExtension(name, typeid(Q), destroy); + } + }; + +} /* End namespace DD4hep */ +#endif // DD4HEP_PLUGINTESTER_H diff --git a/DDCore/include/DD4hep/Printout.h b/DDCore/include/DD4hep/Printout.h index a754e905b85d5b379bd0650bdbd44911be29a8d3..85b2369333f1f612ed76d5cba7a5df151a4d9652 100644 --- a/DDCore/include/DD4hep/Printout.h +++ b/DDCore/include/DD4hep/Printout.h @@ -59,7 +59,16 @@ namespace DD4hep { typedef size_t (*output_function1_t)(void*, PrintLevel severity, const char*, const char*); typedef size_t (*output_function2_t)(void*, PrintLevel severity, const char*, const char*, va_list& args); - /** Calls the display action + /// Helper function to serialize argument list to a single string + /** + * @arg argc [int,read-only] Number of arguments. + * @arg argv [char**,read-only] Argument strings + * @return String containing the concatenated arguments + */ + std::string arguments(int argc, char** argv); + + /// Calls the display action with a given severity level + /** * @arg severity [int,read-only] Display severity flag (see enum) * @arg src [string,read-only] Information source (component, etc.) * @arg fmt [string,read-only] Format string for ellipsis args @@ -67,7 +76,8 @@ namespace DD4hep { */ int printout(PrintLevel severity, const char* src, const char* fmt, ...); - /** Calls the display action + /// Calls the display action with a given severity level + /** * @arg severity [int,read-only] Display severity flag (see enum) * @arg src [string,read-only] Information source (component, etc.) * @arg fmt [string,read-only] Format string for ellipsis args @@ -75,7 +85,8 @@ namespace DD4hep { */ int printout(PrintLevel severity, const std::string& src, const char* fmt, ...); - /** Calls the display action + /// Calls the display action with a given severity level + /** * @arg severity [int,read-only] Display severity flag (see enum) * @arg src [string,read-only] Information source (component, etc.) * @arg fmt [string,read-only] Format string for ellipsis args @@ -83,7 +94,8 @@ namespace DD4hep { */ int printout(PrintLevel severity, const std::string& src, const std::string& fmt, ...); - /** Calls the display action + /// Calls the display action with a given severity level + /** * @arg severity [int,read-only] Display severity flag (see enum) * @arg src [string,read-only] Information source (component, etc.) * @arg fmt [string,read-only] Format string for ellipsis args @@ -91,7 +103,8 @@ namespace DD4hep { */ int printout(PrintLevel severity, const char* src, const std::string& fmt, ...); - /** Calls the display action + /// Calls the display action with a given severity level + /** * @arg severity [int,read-only] Display severity flag (see enum) * @arg src [string,read-only] Information source (component, etc.) * @arg fmt [string,read-only] Format string for ellipsis args @@ -100,7 +113,8 @@ namespace DD4hep { */ int printout(PrintLevel severity, const char* src, const char* fmt, va_list& args); - /** Calls the display action + /// Calls the display action with a given severity level + /** * @arg severity [int,read-only] Display severity flag (see enum) * @arg src [string,read-only] Information source (component, etc.) * @arg fmt [string,read-only] Format string for ellipsis args @@ -109,7 +123,8 @@ namespace DD4hep { */ int printout(PrintLevel severity, const std::string& src, const char* fmt, va_list& args); - /** Calls the display action + /// Calls the display action with a given severity level + /** * @arg severity [int,read-only] Display severity flag (see enum) * @arg src [string,read-only] Information source (component, etc.) * @arg fmt [string,read-only] Format string for ellipsis args @@ -118,7 +133,8 @@ namespace DD4hep { */ int printout(PrintLevel severity, const std::string& src, const std::string& fmt, va_list& args); - /** Calls the display action + /// Calls the display action with a given severity level + /** * @arg severity [int,read-only] Display severity flag (see enum) * @arg src [string,read-only] Information source (component, etc.) * @arg fmt [string,read-only] Format string for ellipsis args @@ -127,51 +143,58 @@ namespace DD4hep { */ int printout(PrintLevel severity, const char* src, const std::string& fmt, va_list& args); - /** Calls the display action with ERROR and throws an std::runtime_error exception + /// Calls the display action with ERROR and throws an std::runtime_error exception + /** * @arg src [string,read-only] Information source (component, etc.) * @arg fmt [string,read-only] Format string for ellipsis args * @return Status code indicating success or failure */ - void except(const std::string& src, const std::string& fmt, ...); + int except(const std::string& src, const std::string& fmt, ...); - /** Calls the display action with ERROR and throws an std::runtime_error exception + /// Calls the display action with ERROR and throws an std::runtime_error exception + /** * @arg src [string,read-only] Information source (component, etc.) * @arg fmt [string,read-only] Format string for ellipsis args * @return Status code indicating success or failure */ - void except(const char* src, const char* fmt, ...); + int except(const char* src, const char* fmt, ...); - /** Calls the display action with ERROR and throws an std::runtime_error exception + /// Calls the display action with ERROR and throws an std::runtime_error exception + /** * @arg src [string,read-only] Information source (component, etc.) * @arg fmt [string,read-only] Format string for ellipsis args * @arg args [ap_list,read-only] List with variable number of arguments to fill format string. * @return Status code indicating success or failure */ - void except(const std::string& src, const std::string& fmt, va_list& args); + int except(const std::string& src, const std::string& fmt, va_list& args); - /** Calls the display action with ERROR and throws an std::runtime_error exception + /// Calls the display action with ERROR and throws an std::runtime_error exception + /** * @arg src [string,read-only] Information source (component, etc.) * @arg fmt [string,read-only] Format string for ellipsis args * @arg args [ap_list,read-only] List with variable number of arguments to fill format string. * @return Status code indicating success or failure */ - void except(const char* src, const char* fmt, va_list& args); + int except(const char* src, const char* fmt, va_list& args); - /** Build formatted string + /// Build formatted string + /* * @arg src [string,read-only] Information source (component, etc.) * @arg fmt [string,read-only] Format string for ellipsis args * @return Status code indicating success or failure */ std::string format(const std::string& src, const std::string& fmt, ...); - /** Build exception string + /// Build exception string + /** * @arg src [string,read-only] Information source (component, etc.) * @arg fmt [string,read-only] Format string for ellipsis args * @return Status code indicating success or failure */ std::string format(const char* src, const char* fmt, ...); - /** Build formatted string + /// Build formatted string + /** * @arg src [string,read-only] Information source (component, etc.) * @arg fmt [string,read-only] Format string for ellipsis args * @arg args [ap_list,read-only] List with variable number of arguments to fill format string. @@ -179,7 +202,8 @@ namespace DD4hep { */ std::string format(const std::string& src, const std::string& fmt, va_list& args); - /** Build exception string and throw std::runtime_error + /// Build formatted string + /** * @arg src [string,read-only] Information source (component, etc.) * @arg fmt [string,read-only] Format string for ellipsis args * @arg args [ap_list,read-only] List with variable number of arguments to fill format string. diff --git a/DDCore/include/DD4hep/Shapes.h b/DDCore/include/DD4hep/Shapes.h index f416c4a3454432e4a4077aca0ff0d4a078d920ea..c0cad1cb2b01ed9cb835ce8fd4857bc4429d569e 100644 --- a/DDCore/include/DD4hep/Shapes.h +++ b/DDCore/include/DD4hep/Shapes.h @@ -90,6 +90,8 @@ namespace DD4hep { /// Access to shape name const char* name() const; + /// Access to shape type (The TClass name of the ROOT implementation) + const char* type() const; /// Auto conversion to underlying ROOT object operator T*() const { return this->m_element; diff --git a/DDCore/include/DD4hep/objects/AlignmentsInterna.h b/DDCore/include/DD4hep/objects/AlignmentsInterna.h index 4d266d70660b699e6761906bdd95416f942cdfcc..860d7b2df7a907d23d53a5fdf7eb5cd461cc6e52 100644 --- a/DDCore/include/DD4hep/objects/AlignmentsInterna.h +++ b/DDCore/include/DD4hep/objects/AlignmentsInterna.h @@ -80,7 +80,7 @@ namespace DD4hep { class AlignmentContainer; class AlignmentConditionObject; - /// The data class behind a alignments handle. + /// The data class behind an alignments handle. /** * See AlignmentsInterna.cpp for the implementation. * @@ -101,7 +101,7 @@ namespace DD4hep { void clear(); }; - /// The data class behind a alignments container handle. + /// The data class behind an alignments container handle. /** * See AlignmentsInterna.cpp for the implementation. * diff --git a/DDCore/src/AlignedVolumePrinter.cpp b/DDCore/src/AlignedVolumePrinter.cpp new file mode 100644 index 0000000000000000000000000000000000000000..8323ef3a4db3fc4b2ae81c2a8d85d5b768d85cce --- /dev/null +++ b/DDCore/src/AlignedVolumePrinter.cpp @@ -0,0 +1,44 @@ +//========================================================================== +// AIDA Detector description implementation for LCD +//-------------------------------------------------------------------------- +// Copyright (C) Organisation europeenne pour la Recherche nucleaire (CERN) +// All rights reserved. +// +// For the licensing terms see $DD4hepINSTALL/LICENSE. +// For the list of contributors see $DD4hepINSTALL/doc/CREDITS. +// +// Author : M.Frank +// +//========================================================================== + +// Framework includes +#include "DD4hep/AlignmentsPrinter.h" +#include "DD4hep/AlignedVolumePrinter.h" + +using std::string; +using namespace DD4hep; +using namespace DD4hep::Alignments; + +/// Initializing constructor +AlignedVolumePrinter::AlignedVolumePrinter(const string& pref, int flg) + : AlignmentsProcessor(0), name("Alignment"), prefix(pref), m_flag(flg) +{ +} + +/// Callback to output alignments information +int AlignedVolumePrinter::operator()(Alignment a) { + printAlignment(name, a); + return 1; +} + +/// Container callback for object processing +int AlignedVolumePrinter::operator()(Container container) { + printContainer(name, container, m_pool); + return 1; +} + +/// Callback to output alignments information of an entire DetElement +int AlignedVolumePrinter::processElement(DetElement de) { + printElementPlacement(name, de, m_pool); + return 1; +} diff --git a/DDCore/src/AlignmentData.cpp b/DDCore/src/AlignmentData.cpp index 15d9a4d05c4c82c83733cfbf62aea247aab25854..0e212b0a811977406a6aaa51c47491f7fd3a196b 100644 --- a/DDCore/src/AlignmentData.cpp +++ b/DDCore/src/AlignmentData.cpp @@ -75,7 +75,8 @@ AlignmentData::AlignmentData() /// Copy constructor AlignmentData::AlignmentData(const AlignmentData& copy) - : delta(copy.delta), worldTrafo(copy.worldTrafo), detectorTrafo(copy.detectorTrafo), + : delta(copy.delta), worldTrafo(copy.worldTrafo), worldDelta(copy.worldDelta), + detectorTrafo(copy.detectorTrafo), nodes(copy.nodes), trToWorld(copy.trToWorld), detector(copy.detector), placement(copy.placement), flag(copy.flag), magic(magic_word()) { diff --git a/DDCore/src/Alignments.cpp b/DDCore/src/Alignments.cpp index 21722e7c3d14b6d7a8924bbaf9fb9ec79fd18b34..1ef0b6afdbbd895cb3c5dab8e15672f216ef97b6 100644 --- a/DDCore/src/Alignments.cpp +++ b/DDCore/src/Alignments.cpp @@ -77,6 +77,11 @@ const DD4hep::IOV& AlignmentCondition::iov() const { return *(access()->iovData()); } +/// Access the hash identifier +AlignmentCondition::key_type AlignmentCondition::key() const { + return access()->hash; +} + /// Data accessor for the use of decorators AlignmentCondition::Data& AlignmentCondition::data() { Object* o = access(); diff --git a/DDCore/src/AlignmentsPrinter.cpp b/DDCore/src/AlignmentsPrinter.cpp index cf177feba824fedfd869fb9c8a3465012535d569..08413dbe2c00b33cfc788c495a0e7ea839abc350 100644 --- a/DDCore/src/AlignmentsPrinter.cpp +++ b/DDCore/src/AlignmentsPrinter.cpp @@ -17,57 +17,246 @@ #include "DD4hep/AlignmentsPrinter.h" #include "DD4hep/objects/AlignmentsInterna.h" +// C/C++ include files +#include <sstream> + +using std::string; +using std::stringstream; using namespace DD4hep; using namespace DD4hep::Alignments; /// Initializing constructor -AlignmentsPrinter::AlignmentsPrinter(const std::string& pref, int flg) +AlignmentsPrinter::AlignmentsPrinter(const string& pref, int flg) : AlignmentsProcessor(0), name("Alignment"), prefix(pref), m_flag(flg) { } /// Callback to output alignments information int AlignmentsPrinter::operator()(Alignment a) { + printAlignment(name, a); + return 1; +} + +/// Container callback for object processing +int AlignmentsPrinter::operator()(Container container) { + printContainer(name, container, m_pool); + return 1; +} + +/// Callback to output alignments information of an entire DetElement +int AlignmentsPrinter::processElement(DetElement de) { + printElement(name, de, m_pool); + return 1; +} + + +/// Default printout of an alignment entry +void DD4hep::Alignments::printAlignment(const string& prefix, Alignment a) { if ( a.isValid() ) { - printout(INFO,name,"++ %s%s [%p]",prefix.c_str(),a.name(),a.ptr()); - const Alignments::Delta& D = a.data().delta; - std::string new_prefix = prefix; + const Alignment::Data& data = a.data(); + Conditions::Condition cond = data.condition; + const Delta& D = data.delta; + string new_prefix = prefix; new_prefix.assign(prefix.length(),' '); - printout(INFO,name,"++ %s \tPath:%s", - new_prefix.c_str(), a.name()); - printout(INFO,name,"++ %s \tData:(%11s-%8s-%5s) Cond:%p 'Alignment'", + printout(INFO,prefix,"++ %s \tPath:%s [%p] Typ:%s", + new_prefix.c_str(), cond.name(), a.ptr(), + typeName(typeid(*(a.ptr()))).c_str()); + printout(INFO,prefix,"++ %s \tData:(%11s-%8s-%5s)", new_prefix.c_str(), D.hasTranslation() ? "Translation" : "", D.hasRotation() ? "Rotation" : "", - D.hasPivot() ? "Pivot" : "", - a.data().hasCondition() ? a.data().condition.ptr() : 0); + D.hasPivot() ? "Pivot" : ""); + printf("WorldTrafo: "); data.worldTrafo.Print(); + printf("DetTrafo: "); data.detectorTrafo.Print(); } - return 1; } -/// Container callback for object processing -int AlignmentsPrinter::operator()(Container container) { - if ( m_pool ) { - printout(INFO,name,"++ Alignments of DE %s [%d entries]", - container->detector.path().c_str(), int(container.keys().size())); +/// Default printout of an container entry +void DD4hep::Alignments::printContainer(const string& prefix, Container container, UserPool* pool) { + string tag = prefix+"Cont"; + if ( pool ) { for(const auto& k : container.keys() ) { try { - Alignment align = container.get(k.first,*m_pool); - std::string an = align.name(); - std::string cn = an.substr(an.find('#')+1); - Alignment::key_type key = hash32(cn); - printout(INFO,name,"++ %s %s %s [%08X] -> %s [%08X]", - prefix.c_str(), "Alignment:", an.c_str(), key==k.first ? key : k.first, - align.name(), k.second.first); - (*this)(align); + Alignment align = container.get(k.first,*pool); + printout(INFO,tag,"++ %s Alignment [%08X] -> [%08X] %s", + prefix.c_str(), k.first, k.second.first, k.second.second.c_str()); + printAlignment(prefix,align); } catch(...) { - printout(ERROR,name,"++ %s %s [%08X] -> [%08X]", + printout(ERROR,tag,"++ %s %s [%08X] -> [%08X]", prefix.c_str(), "FAILED Alignment:", k.first, k.second.first); } } - return 1; + return; + } + except(tag,"Cannot dump alignments container without valid user-pool."); +} + +/// Default printout of a detector element entry +void DD4hep::Alignments::printElement(const string& prefix, DetElement de, UserPool* pool) { + string tag = prefix+"Element"; + if ( de.isValid() ) { + if ( pool ) { + DetAlign a(de); + Container c = a.alignments(); + printout(INFO,tag,"++ Alignments of DE %s [%d entries]", + de.path().c_str(), int(c.keys().size())); + printContainer(prefix, c, pool); + return; + } + except(tag,"Cannot process DetElement alignments from '%s' without valid user-pool",de.name()); + } + except(tag,"Cannot process alignments of an invalid detector element"); +} + + +#include "TClass.h" +#include "DD4hep/ToStream.h" +static string replace_all(const string& in, const string& from, const string& to) { + string res = in; + size_t idx; + while( string::npos != (idx=res.find(from)) ) + res.replace(idx,from.length(),to); + return res; +} +static string _transformPoint2World(const Alignment::Data& data, const Position& local) { + char text[256]; + Position world = data.localToWorld(local); + ::snprintf(text,sizeof(text),"Local: (%7.3f , %7.3f , %7.3f ) -- > World: (%7.3f , %7.3f , %7.3f )", + local.x(), local.y(), local.z(), world.x(), world.y(), world.z()); + return text; +} + +static string _transformPoint2Detector(const Alignment::Data& data, const Position& local) { + char text[256]; + Position world = data.localToDetector(local); + ::snprintf(text,sizeof(text),"Local: (%7.3f , %7.3f , %7.3f ) -- > Parent: (%7.3f , %7.3f , %7.3f )", + local.x(), local.y(), local.z(), world.x(), world.y(), world.z()); + return text; +} + +static void printAlignmentEx(const string& prefix, const string& opt, DetElement de, Alignment alignment) { + using Geometry::Box; + DetAlign a(de); + const string& tag = prefix; + const Alignment::Data& align_data = alignment.data(); + Conditions::Condition align_cond = align_data.condition; + const Delta& align_delta = align_data.delta; + string par = de.parent().isValid() ? de.parent().path() : string(); + Box bbox = de.placement().volume().solid(); + /// The edge positions of the bounding box: + Position p1( bbox.x(), bbox.y(), bbox.z()); + Position p2( bbox.x(),-bbox.y(), bbox.z()); + Position p3(-bbox.x(), bbox.y(), bbox.z()); + Position p4(-bbox.x(),-bbox.y(), bbox.z()); + Position p5( bbox.x(), bbox.y(),-bbox.z()); + Position p6( bbox.x(),-bbox.y(),-bbox.z()); + Position p7(-bbox.x(), bbox.y(),-bbox.z()); + Position p8(-bbox.x(),-bbox.y(),-bbox.z()); + + if ( align_cond.isValid() ) { + printout(INFO,tag,"++ %s DATA: (%11s-%8s-%5s) %p IOV:%s", opt.c_str(), + align_delta.hasTranslation() ? "Translation" : "", + align_delta.hasRotation() ? "Rotation" : "", + align_delta.hasPivot() ? "Pivot" : "", + alignment.ptr(), + align_cond.iov().str().c_str()); + } + else { + printout(INFO,tag,"++ %s DATA: (%11s-%8s-%5s) %p", opt.c_str(), + align_delta.hasTranslation() ? "Translation" : "", + align_delta.hasRotation() ? "Rotation" : "", + align_delta.hasPivot() ? "Pivot" : "", + alignment.ptr()); + } + if ( align_delta.hasTranslation() ) { + stringstream str; + Utils::toStream(align_delta.translation, str); + printout(INFO,tag,"++ %s DELTA Translation: %s", opt.c_str(), replace_all(str.str(),"\n","").c_str()); + } + if ( align_delta.hasPivot() ) { + stringstream str; + Utils::toStream(align_delta.pivot, str); + string res = replace_all(str.str(),"\n",""); + res = "( "+replace_all(res," "," , ")+" )"; + printout(INFO,tag,"++ %s DELTA Pivot: %s", opt.c_str(), res.c_str()); + } + if ( align_delta.hasRotation() ) { + stringstream str; + Utils::toStream(align_delta.rotation, str); + printout(INFO,tag,"++ %s DELTA Rotation: %s", opt.c_str(), replace_all(str.str(),"\n","").c_str()); + } + printf("%s %s WorldTrafo (to %s): ",opt.c_str(), tag.c_str(), de.world().path().c_str()); + align_data.worldTrafo.Print(); + printf("%s %s DetTrafo (to %s): ",opt.c_str(), tag.c_str(), par.c_str()); + align_data.detectorTrafo.Print(); + + printout(INFO,tag,"++ %s: P1(x,y,z) %s", opt.c_str(), _transformPoint2World(align_data, p1).c_str()); + printout(INFO,tag,"++ %s: P2(x,y,z) %s", opt.c_str(), _transformPoint2World(align_data, p2).c_str()); + printout(INFO,tag,"++ %s: P3(x,y,z) %s", opt.c_str(), _transformPoint2World(align_data, p3).c_str()); + printout(INFO,tag,"++ %s: P4(x,y,z) %s", opt.c_str(), _transformPoint2World(align_data, p4).c_str()); + printout(INFO,tag,"++ %s: P5(x,y,z) %s", opt.c_str(), _transformPoint2World(align_data, p5).c_str()); + printout(INFO,tag,"++ %s: P6(x,y,z) %s", opt.c_str(), _transformPoint2World(align_data, p6).c_str()); + printout(INFO,tag,"++ %s: P7(x,y,z) %s", opt.c_str(), _transformPoint2World(align_data, p7).c_str()); + printout(INFO,tag,"++ %s: P8(x,y,z) %s", opt.c_str(), _transformPoint2World(align_data, p8).c_str()); + + printout(INFO,tag,"++ %s: P1(x,y,z) %s", opt.c_str(), _transformPoint2Detector(align_data, p1).c_str()); + printout(INFO,tag,"++ %s: P2(x,y,z) %s", opt.c_str(), _transformPoint2Detector(align_data, p2).c_str()); + printout(INFO,tag,"++ %s: P3(x,y,z) %s", opt.c_str(), _transformPoint2Detector(align_data, p3).c_str()); + printout(INFO,tag,"++ %s: P4(x,y,z) %s", opt.c_str(), _transformPoint2Detector(align_data, p4).c_str()); + printout(INFO,tag,"++ %s: P5(x,y,z) %s", opt.c_str(), _transformPoint2Detector(align_data, p5).c_str()); + printout(INFO,tag,"++ %s: P6(x,y,z) %s", opt.c_str(), _transformPoint2Detector(align_data, p6).c_str()); + printout(INFO,tag,"++ %s: P7(x,y,z) %s", opt.c_str(), _transformPoint2Detector(align_data, p7).c_str()); + printout(INFO,tag,"++ %s: P8(x,y,z) %s", opt.c_str(), _transformPoint2Detector(align_data, p8).c_str()); +} + +/// PrintElement placement with/without alignment applied +void DD4hep::Alignments::printElementPlacement(const string& prefix, DetElement de, UserPool* pool) { + using Geometry::Box; + using Geometry::Solid; + using Geometry::Volume; + using Geometry::PlacedVolume; + string tag = prefix+"Element"; + if ( de.isValid() ) { + if ( pool ) { + char text[132]; + DetAlign a(de); + Container container = a.alignments(); + Alignment nominal = de.nominal(); + Box bbox = de.placement().volume().solid(); + ::memset(text,'=',sizeof(text)); + text[sizeof(text)-1] = 0; + printout(INFO,tag,text); + printout(INFO,tag,"++ Alignments of DE %s [%d entries]", + de.path().c_str(), int(container.keys().size())); + printout(INFO,tag,"++ Volume: %s BBox: x=%7.3f y=%7.3f z=%7.3f",bbox.type(),bbox.x(),bbox.y(),bbox.z()); + printAlignmentEx(tag,"NOMINAL",de,nominal); + + for(const auto& k : container.keys() ) { + try { + Alignment align = container.get(k.first,*pool); + const Alignment::Data& align_data = align.data(); + Conditions::Condition align_cond = align_data.condition; + if ( k.first != k.second.first ) { + printout(INFO,tag,"++ Alignment %p [%08X] -> [%08X] %s (SYNONYM) ignored.", + a.ptr(), k.first, k.second.first, k.second.second.c_str()); + continue; + } + printout(INFO,tag,"++ Alignment %p [%08X] -> [%08X] %s", + a.ptr(), k.first, k.second.first, k.second.second.c_str()); + if ( k.second.second != align_cond.name() ) { + printout(INFO,prefix,"++ \tPath:%s [%p]", align_cond.name(), a.ptr()); + } + printAlignmentEx(tag,"ALIGNMENT",de,align); + } + catch(...) { + printout(ERROR,tag,"++ %s %s [%08X] -> [%08X]", + prefix.c_str(), "FAILED Alignment:", k.first, k.second.first); + } + } + return; + } + except(tag,"Cannot process DetElement alignments from '%s' without valid user-pool",de.name()); } - except(name,"Cannot dump alignments container without user-pool."); - return 0; + except(tag,"Cannot process alignments of an invalid detector element"); } diff --git a/DDCore/src/AlignmentsProcessor.cpp b/DDCore/src/AlignmentsProcessor.cpp index fde89123481908f1cb53ecf4ec6ca50ef0443f1c..78cc40a936e424ae478fc19086a5f723995cd70a 100644 --- a/DDCore/src/AlignmentsProcessor.cpp +++ b/DDCore/src/AlignmentsProcessor.cpp @@ -38,7 +38,7 @@ int AlignmentsProcessor::operator()(Container container) { } /// Callback to output alignments information of an entire DetElement -int AlignmentsProcessor::operator()(Geometry::DetElement de) { +int AlignmentsProcessor::processElement(Geometry::DetElement de) { if ( de.isValid() ) { if ( m_pool ) { DetAlign align(de); diff --git a/DDCore/src/ConditionDerived.cpp b/DDCore/src/ConditionDerived.cpp index 53fed76a5dbfc8c816cb976a8b20a59c78ab849e..5be7a996f2607e1169ad3d47c5907e8f5026cf48 100644 --- a/DDCore/src/ConditionDerived.cpp +++ b/DDCore/src/ConditionDerived.cpp @@ -87,6 +87,13 @@ DependencyBuilder::DependencyBuilder(const ConditionKey& target, ConditionUpdate { } +/// Initializing constructor +DependencyBuilder::DependencyBuilder(const ConditionKey& target, ConditionUpdateCall* call, Geometry::DetElement de) + : m_dependency(new ConditionDependency(target,call)) +{ + m_dependency->detector = de; +} + /// Default destructor DependencyBuilder::~DependencyBuilder() { releasePtr(m_dependency); diff --git a/DDCore/src/Conditions.cpp b/DDCore/src/Conditions.cpp index 90d295e2ca952e7ecc372fa74dc373f0d3bf5ada..d7f46714815573a1215cb2cc617f7062db7af9fd 100644 --- a/DDCore/src/Conditions.cpp +++ b/DDCore/src/Conditions.cpp @@ -103,11 +103,6 @@ const DD4hep::IOV& Condition::iov() const { return *(access()->iovData()); } -/// Access the name of the condition -const string& Condition::name() const { - return access()->name; -} - /// Access the type field of the condition const string& Condition::type() const { return access()->type; @@ -164,7 +159,7 @@ Condition& Condition::rebind() { #endif o->data.fromString(o->value); printout(INFO,"Condition","+++ condition:%s rebinding value:%s", - name().c_str(), o->value.c_str()); + name(), o->value.c_str()); return *this; } diff --git a/DDCore/src/ConditionsPrinter.cpp b/DDCore/src/ConditionsPrinter.cpp index 9c2d65b1bcabaf5c6cc9ae1d50f7d1d540b19aa4..1253a6d55858b52de92fd657b705e8401f94d48e 100644 --- a/DDCore/src/ConditionsPrinter.cpp +++ b/DDCore/src/ConditionsPrinter.cpp @@ -15,6 +15,7 @@ #include "DD4hep/Printout.h" #include "DD4hep/DetConditions.h" #include "DD4hep/ConditionsPrinter.h" +#include "DD4hep/objects/ConditionsInterna.h" using namespace DD4hep; using namespace DD4hep::Conditions; @@ -39,12 +40,12 @@ int ConditionsPrinter::operator()(Condition cond) { std::string new_prefix = prefix; new_prefix.assign(prefix.length(),' '); printout(INFO,name,"++ %s \tPath:%s Key:%08X Type:%s", - new_prefix.c_str(), cond.name().c_str(), cond.key(), data.dataType().c_str()); + new_prefix.c_str(), cond.name(), cond.key(), data.dataType().c_str()); printout(INFO,name,"++ %s \tData:%s", new_prefix.c_str(), values.c_str()); } return 1; } -#include "DD4hep/objects/ConditionsInterna.h" + /// Container callback for object processing int ConditionsPrinter::operator()(Container container) { if ( m_pool ) { @@ -52,11 +53,12 @@ int ConditionsPrinter::operator()(Container container) { container->detector.path().c_str(), int(container.keys().size())); for(const auto& k : container.keys() ) { Condition c = container.get(k.first,*m_pool); - std::string cn = c.name().substr(c.name().find('#')+1); + std::string nam = c.name(); + std::string cn = nam.substr(nam.find('#')+1); Condition::key_type key = ConditionKey::hashCode(cn); printout(INFO,name,"++ %s %s %s [%08X] -> %s [%08X]", prefix.c_str(), "Condition:", cn.c_str(), key==k.first ? key : k.first, - c.name().c_str(), k.second.first); + c.name(), k.second.first); (*this)(c); } return 1; diff --git a/DDCore/src/ConditionsProcessor.cpp b/DDCore/src/ConditionsProcessor.cpp index defc5c119005cea62a1144dc81fa081e995ce508..96770054b7e1fb1e49ce6c57263e17a4bac07eb1 100644 --- a/DDCore/src/ConditionsProcessor.cpp +++ b/DDCore/src/ConditionsProcessor.cpp @@ -38,7 +38,7 @@ int ConditionsProcessor::operator()(Container container) { } /// Callback to output conditions information of an entire DetElement -int ConditionsProcessor::operator()(DetElement de) { +int ConditionsProcessor::processElement(DetElement de) { if ( de.isValid() ) { if ( m_pool ) { DetConditions conds(de); diff --git a/DDCore/src/Detector.cpp b/DDCore/src/Detector.cpp index 377f2e0bcb8111764994f6e9c4a2290595d10932..3712736cc7a3c882ef1415bc66327ad6f805d200 100644 --- a/DDCore/src/Detector.cpp +++ b/DDCore/src/Detector.cpp @@ -32,6 +32,10 @@ namespace { DetElement::Processor::Processor() { } +/// Default destructor +DetElement::Processor::~Processor() { +} + /// Clone constructor DetElement::DetElement(Object* det_data, const string& det_name, const string& det_type) : RefObject(det_data) diff --git a/DDCore/src/ObjectExtensions.cpp b/DDCore/src/ObjectExtensions.cpp index 182d8cefcdbabf88ced5e9ab98748afd34c39397..d1c9b825d5fa0ffacd0cf17fb208cac0b62dfede 100644 --- a/DDCore/src/ObjectExtensions.cpp +++ b/DDCore/src/ObjectExtensions.cpp @@ -1,4 +1,3 @@ -// $Id: $ //========================================================================== // AIDA Detector description implementation for LCD //-------------------------------------------------------------------------- diff --git a/DDCore/src/PluginCreators.cpp b/DDCore/src/PluginCreators.cpp index d33a5d0beb55d0ba714ef0da020a1f1a3c5f6e54..257976c140e491e9ced633e09392b7c8ca8d383b 100644 --- a/DDCore/src/PluginCreators.cpp +++ b/DDCore/src/PluginCreators.cpp @@ -1,4 +1,3 @@ -// $Id$ //========================================================================== // AIDA Detector description implementation for LCD //-------------------------------------------------------------------------- @@ -18,19 +17,60 @@ #include "DD4hep/Printout.h" #include "DD4hep/Plugins.h" +// C/C++ include files +#include <cstring> + /// Namespace for the AIDA detector description toolkit namespace DD4hep { static inline ComponentCast* component(void* p) { return (ComponentCast*)p; } - void* createPlugin(const std::string& factory, Geometry::LCDD& lcdd, int argc, char** argv, void* (*cast)(void*)) - { + void* createProcessor(Geometry::LCDD& lcdd, int argc, char** argv, void* (*cast)(void*)) { + void* processor = 0; + if ( argc < 2 ) { + except("createProcessor","++ DD4hep-plugins: No processor creator name given!"); + } + for(int i=0; i<argc; ++i) { + if ( 0 == ::strncmp(argv[i],"-processor",4) ) { + std::vector<char*> args; + std::string fac = argv[++i]; + for(int j=++i; j<argc && argv[j] && + 0 != ::strncmp(argv[j],"-processor",4) && + 0 != ::strncmp(argv[j],"-end-processor",8); ++j) + args.push_back(argv[j]); + int num_arg = int(args.size()); + args.push_back(0); + processor = PluginService::Create<void*>(fac,&lcdd,num_arg,&args[0]); + if ( !processor ) { + PluginDebug dbg; + processor = PluginService::Create<void*>(fac, &lcdd, argc, argv); + if ( !processor ) { + except("createProcessor","DD4hep-plugins: Failed to locate plugin %s. \n%s.", + fac.c_str(), dbg.missingFactory(fac).c_str()); + } + } + if ( cast ) { + void* obj = cast(processor); + if ( obj ) return obj; + invalidHandleAssignmentError(typeid(cast),typeid(*component(processor))); + } + } + } + if ( !processor ) { + except("createProcessor", + "DD4hep-plugins: Found arguments in plugin call, but could not make any sense of them: %s", + arguments(argc,argv).c_str()); + } + return processor; + } + + void* createPlugin(const std::string& factory, Geometry::LCDD& lcdd, int argc, char** argv, void* (*cast)(void*)) { void* object = PluginService::Create<void*>(factory, &lcdd, argc, argv); if ( !object ) { PluginDebug dbg; object = PluginService::Create<void*>(factory, &lcdd, argc, argv); if ( !object ) { - except("ConditionsManager","DD4hep: plugin: Failed to locate plugin %s. [%s].", + except("ConditionsManager","DD4hep-plugins: Failed to locate plugin %s. \n%s.", factory.c_str(), dbg.missingFactory(factory).c_str()); } } @@ -43,8 +83,7 @@ namespace DD4hep { } /// Handler for factories of type: ConstructionFactory - void* createPlugin(const std::string& factory, Geometry::LCDD& lcdd, void* (*cast)(void*)) - { + void* createPlugin(const std::string& factory, Geometry::LCDD& lcdd, void* (*cast)(void*)) { char* argv[] = {0}; int argc = 0; return createPlugin(factory, lcdd, argc, argv, cast); diff --git a/DDCore/src/PluginTester.cpp b/DDCore/src/PluginTester.cpp new file mode 100644 index 0000000000000000000000000000000000000000..3810e0e50d9aea2f4009a9abfa1610ba8304d3ba --- /dev/null +++ b/DDCore/src/PluginTester.cpp @@ -0,0 +1,111 @@ +//========================================================================== +// AIDA Detector description implementation for LCD +//-------------------------------------------------------------------------- +// Copyright (C) Organisation europeenne pour la Recherche nucleaire (CERN) +// All rights reserved. +// +// For the licensing terms see $DD4hepINSTALL/LICENSE. +// For the list of contributors see $DD4hepINSTALL/doc/CREDITS. +// +// Author : M.Frank +// +//========================================================================== + +// Framework include files +#include "DD4hep/PluginTester.h" +#include "DD4hep/InstanceCount.h" +#include "DD4hep/Primitives.h" + +// C/C++ include files +#include <stdexcept> + +using namespace DD4hep; + +namespace { + static int s_extensionID = 0; + PluginTester::ExtensionMap* extensionContainer(const std::type_info& typ) { + static std::map<const std::type_info*, PluginTester::ExtensionMap> s_map; + return &s_map[&typ]; + } +} + +/// Default constructor +PluginTester::PluginTester() { + extensionMap = extensionContainer(typeid(*this)); + InstanceCount::increment(this); +} + +/// Default destructor +PluginTester::~PluginTester() { + clear(); + InstanceCount::decrement(this); +} + +/// Internal object destructor: release extension object(s) +void PluginTester::clear(bool destroy) { + for (Extensions::iterator i = extensions.begin(); i != extensions.end(); ++i) { + void* ptr = (*i).second; + if (ptr) { + ExtensionMap::iterator j = extensionMap->find((*i).first.first); + if (j != extensionMap->end()) { + Entry& e = (*j).second; + if (destroy && e.destruct) + (*(e.destruct))(ptr); + } + } + } + extensions.clear(); +} + +/// Add an extension object to the detector element +void* PluginTester::addExtension(void* ptr, const std::string& name, const std::type_info& info, destruct_t dtor) { + key_type key(&info,name); + Extensions::iterator j = extensions.find(key); + if (j == extensions.end()) { + ExtensionMap::iterator i = extensionMap->find(&info); + if (i == extensionMap->end()) { + Entry entry; + entry.destruct = dtor; + entry.id = ++s_extensionID; + extensionMap->insert(make_pair(&info, entry)); + } + return extensions[key] = ptr; + } + throw std::runtime_error("DD4hep: addExtension: Object already has an extension "+name+ + " of type:" + typeName(info) + "."); +} + +/// Remove an existing extension object from the instance +void* PluginTester::removeExtension(const std::string& name, const std::type_info& info, bool destroy) { + key_type key(&info,name); + Extensions::iterator j = extensions.find(key); + if (j != extensions.end()) { + void *ptr = (*j).second; + if ( destroy ) { + ExtensionMap::iterator i = extensionMap->find(&info); + if (i != extensionMap->end()) { + Entry& e = (*i).second; + (*e.destruct)((*j).second); + ptr = 0; + } + } + extensions.erase(j); + return ptr; + } + throw std::runtime_error("DD4hep: removeExtension: The object "+name+ + " of type " + typeName(info) + " is not present."); +} + +/// Access an existing extension object from the detector element +void* PluginTester::extension(const std::string& name, const std::type_info& info, bool alert) const { + key_type key(&info,name); + Extensions::const_iterator j = extensions.find(key); + if (j != extensions.end()) { + return (*j).second; + } + else if ( !alert ) + return 0; + throw std::runtime_error("DD4hep: extension: Object has no extension "+name+ + " of type:" + typeName(info) + "."); +} + diff --git a/DDCore/src/Plugins.cpp b/DDCore/src/Plugins.cpp index 1ef820abfec5f847a43965917d532841a104823b..3bc5de85deb93fbbd5f4f8f3c639300aa8631405 100644 --- a/DDCore/src/Plugins.cpp +++ b/DDCore/src/Plugins.cpp @@ -58,7 +58,8 @@ PluginDebug::~PluginDebug() { string PluginDebug::missingFactory(const string& name) const { ROOT::Reflex::Scope factories = ROOT::Reflex::Scope::ByName(PLUGINSVC_FACTORY_NS); string factoryname = ROOT::Reflex::PluginService::FactoryName(name); - string msg = "\n\t\tNo factory with name " + factoryname + " for type " + name + " found.\n\t\tPlease check library load path."; + string msg = "\t\tNo factory with name " + factoryname + " for type " + name + " found.\n" + "\t\tPlease check library load path and/or plugin factory name."; return msg; } @@ -144,8 +145,9 @@ PluginDebug::~PluginDebug() { /// Helper to check factory existence string PluginDebug::missingFactory(const string& name) const { - string factoryname = "??? Create("+name+")"; - string msg = "\n\t\tNo factory with name " + factoryname + " for type " + name + " found.\n\t\tPlease check library load path."; + string factoryname = "Create("+name+")"; + string msg = "\t\tNo factory with name " + factoryname + " for type " + name + " found.\n" + "\t\tPlease check library load path and/or plugin factory name."; return msg; } diff --git a/DDCore/src/Printout.cpp b/DDCore/src/Printout.cpp index 9b29dd48d454a2dafb1ceb1fab3771acb3d3a7ec..c342ba62eac741405f1f53db11911adbde58edee 100644 --- a/DDCore/src/Printout.cpp +++ b/DDCore/src/Printout.cpp @@ -17,6 +17,7 @@ // C/C++ include files #include <cstring> #include <cstdarg> +#include <sstream> #include <stdexcept> // Disable some diagnostics for ROOT dictionaries #ifdef __GNUC__ @@ -86,6 +87,21 @@ namespace { } } +/// Helper function to serialize argument list to a single string +/** + * @arg argc [int,read-only] Number of arguments. + * @arg argv [char**,read-only] Argument strings + * @return String containing the concatenated arguments + */ +string DD4hep::arguments(int argc, char** argv) { + stringstream str; + for(int i=0; i<argc;) { + str << argv[i]; + if ( ++i < argc ) str << " "; + } + return str.str(); +} + /** Calls the display action * @arg severity [int,read-only] Display severity flag * @arg src [string,read-only] Information source (component, etc.) @@ -198,10 +214,10 @@ int DD4hep::printout(PrintLevel severity, const string& src, const string& fmt, * @arg fmt [string,read-only] Format string for ellipsis args * @return Status code indicating success or failure */ -void DD4hep::except(const string& src, const string& fmt, ...) { +int DD4hep::except(const string& src, const string& fmt, ...) { va_list args; va_start(args, &fmt); - except(src.c_str(),fmt.c_str(), args); + return except(src.c_str(),fmt.c_str(), args); } /** Calls the display action with ERROR and throws an std::runtime_error exception @@ -209,10 +225,10 @@ void DD4hep::except(const string& src, const string& fmt, ...) { * @arg fmt [string,read-only] Format string for ellipsis args * @return Status code indicating success or failure */ -void DD4hep::except(const char* src, const char* fmt, ...) { +int DD4hep::except(const char* src, const char* fmt, ...) { va_list args; va_start(args, fmt); - except(src, fmt, args); + return except(src, fmt, args); } /** Calls the display action with ERROR and throws an std::runtime_error exception @@ -221,7 +237,7 @@ void DD4hep::except(const char* src, const char* fmt, ...) { * @arg args [ap_list,read-only] List with variable number of arguments to fill format string. * @return Status code indicating success or failure */ -void DD4hep::except(const string& src, const string& fmt, va_list& args) { +int DD4hep::except(const string& src, const string& fmt, va_list& args) { string msg = __format(fmt.c_str(), args); va_end(args); printout(ERROR, src.c_str(), "%s", msg.c_str()); @@ -235,8 +251,8 @@ void DD4hep::except(const string& src, const string& fmt, va_list& args) { * @arg args [ap_list,read-only] List with variable number of arguments to fill format string. * @return Status code indicating success or failure */ -void DD4hep::except(const char* src, const char* fmt, va_list& args) { - string msg = format(src, fmt, args); +int DD4hep::except(const char* src, const char* fmt, va_list& args) { + string msg = __format(fmt, args); va_end(args); printout(ERROR, src, "%s", msg.c_str()); // No return. Must call va_end here! diff --git a/DDCore/src/Shapes.cpp b/DDCore/src/Shapes.cpp index 8ef9f02e938115f3c5a8b564bb18cbc315c528de..67a5888124ad396f180ff48933e4d72c3bae30ea 100644 --- a/DDCore/src/Shapes.cpp +++ b/DDCore/src/Shapes.cpp @@ -1,4 +1,3 @@ -// $Id$ //========================================================================== // AIDA Detector description implementation for LCD //-------------------------------------------------------------------------- @@ -173,6 +172,14 @@ template <typename T> const char* Solid_type<T>::name() const { return this->ptr()->GetName(); } +/// Access to shape type (The TClass name of the ROOT implementation) +template <typename T> const char* Solid_type<T>::type() const { + if ( this->ptr() ) { + return this->ptr()->IsA()->GetName(); + } + return ""; +} + void Box::make(double x_val, double y_val, double z_val) { _assign(new TGeoBBox(x_val, y_val, z_val), "", "box", true); } diff --git a/DDCore/src/plugins/StandardPlugins.cpp b/DDCore/src/plugins/StandardPlugins.cpp index 32d993376fed9b649372584ac7c3a4f4cae2e0ed..2e546c197639d3e223dc3a70c01649f493695500 100644 --- a/DDCore/src/plugins/StandardPlugins.cpp +++ b/DDCore/src/plugins/StandardPlugins.cpp @@ -17,6 +17,7 @@ #include "DD4hep/Factories.h" #include "DD4hep/Printout.h" #include "DD4hep/DetectorTools.h" +#include "DD4hep/PluginCreators.h" #include "DD4hep/DD4hepRootPersistency.h" #include "../LCDDImp.h" @@ -392,32 +393,6 @@ static long dump_volume_tree(LCDD& lcdd, int argc, char** argv) { } DECLARE_APPLY(DD4hepVolumeDump,dump_volume_tree) -// ====================================================================================== -static DetElement::Processor* create_processor(LCDD& lcdd, int argc, char** argv) { - DetElement::Processor* processor = 0; - if ( argc < 2 ) { - except("DetectorProcessor","++ No processor creator name given!"); - } - for(int i=0; i<argc; ++i) { - if ( 0 == ::strncmp(argv[i],"-processor",4) ) { - vector<char*> args; - string fac = argv[++i]; - for(int j=++i; j<argc && argv[j] && 0 != ::strncmp(argv[j],"-processor",4); ++j) - args.push_back(argv[j]); - args.push_back(0); - DetElement::Processor* p = (DetElement::Processor*) - PluginService::Create<void*>(fac,&lcdd,int(args.size()),&args[0]); - processor = dynamic_cast<DetElement::Processor*>(p); - break; - } - } - if ( !processor ) { - except("DetectorProcessor", - "++ Found arguments in plugin call, but could not make any sense of them...."); - } - return processor; -} - // ====================================================================================== /// Plugin function: Apply arbitrary functor callback on the tree of detector elements /** @@ -443,7 +418,7 @@ static int detelement_processor(LCDD& lcdd, int argc, char** argv) { long process(DetElement de) { if ( de.isValid() ) { int result = 1; - (*processor)(de); + (*processor).processElement(de); for (const auto& c : de.children() ) { int ret = process(c.second); if ( 1 != ret ) { @@ -458,14 +433,15 @@ static int detelement_processor(LCDD& lcdd, int argc, char** argv) { } }; DetElement det = lcdd.world(); - DetElement::Processor* processor = create_processor(lcdd, argc, argv); + DetElement::Processor* proc = + DD4hep::createProcessor<DetElement::Processor>(lcdd, argc, argv); for(int i=0, num=std::min(argc,3); i<num; ++i) { if ( 0 == ::strncmp(argv[i],"-detector",4) ) { det = DetectorTools::findElement(lcdd, argv[++i]); break; } } - return Actor(processor).process(det); + return Actor(proc).process(det); } DECLARE_APPLY(DD4hep_DetElementProcessor,detelement_processor) @@ -608,31 +584,15 @@ DECLARE_APPLY(DD4hepDetectorTypes,detectortype_cache) typedef SurfaceInstaller TestSurfacesPlugin; DECLARE_SURFACE_INSTALLER(TestSurfaces,TestSurfacesPlugin) -/// Basic entry point to instantiate the basic DD4hep conditions/alignmants printer -/** - * Factory: DD4hepConditionsPrinter, DD4hepAlignmentsPrinter - * - * \author M.Frank - * \version 1.0 - * \date 17/11/2016 - */ -namespace { - template <typename PRINTER> - void* create_printer(Geometry::LCDD& /* lcdd */, int argc,char** argv) { - string prefix = ""; - int flags = 0; - for(int i=0; i<argc && argv[i]; ++i) { - if ( 0 == ::strncmp("-prefix",argv[i],4) ) - prefix = argv[++i]; - else if ( 0 == ::strncmp("-flags",argv[i],2) ) - flags = ::atol(argv[++i]); - } - if ( flags ) - return (void*)new PRINTER(prefix,flags); - return (void*)new PRINTER(prefix); +#include "DD4hep/PluginTester.h" +static long install_plugin_tester(LCDD& lcdd, int , char** ) { + PluginTester* test = lcdd.extension<PluginTester>(false); + if ( !test ) { + lcdd.addExtension<PluginTester>(new PluginTester()); + printout(INFO,"PluginTester", + "+++ Successfully installed PluginTester instance to LCDD."); } + return 1; } -#include "DD4hep/ConditionsPrinter.h" -DECLARE_LCDD_CONSTRUCTOR(DD4hepConditionsPrinter,create_printer<Conditions::ConditionsPrinter>) -#include "DD4hep/AlignmentsPrinter.h" -DECLARE_LCDD_CONSTRUCTOR(DD4hepAlignmentsPrinter,create_printer<Alignments::AlignmentsPrinter>) +DECLARE_APPLY(DD4hepPluginTester,install_plugin_tester) + diff --git a/DDDB/src/DDDBConditionPrinter.cpp b/DDDB/src/DDDBConditionPrinter.cpp index 573ee61f04e286669f1d1217b4ab3f8baeaca9c8..12dd05fa7d2b3d25e3c32d2f5eaaf93d1e8b3116 100644 --- a/DDDB/src/DDDBConditionPrinter.cpp +++ b/DDDB/src/DDDBConditionPrinter.cpp @@ -89,7 +89,7 @@ int ConditionPrinter::operator()(Condition cond) { new_prefix.assign(m_prefix.length(),' '); printout(INFO,"Condition","++ %s Path:%s Class:%d [%s]", m_prefix.c_str(), - cond.name().c_str(), + cond.name(), data.classID, cond.data().dataType().c_str()); if ( !data.params.empty() ) { diff --git a/examples/AlignDet/src/Telescope_geo.cpp b/examples/AlignDet/src/Telescope_geo.cpp index e9094a09ab82d87b81ac9e3a3a7e180e998c0f1d..a882e63000f0c93b3c48b27fb85fcab284a49e06 100644 --- a/examples/AlignDet/src/Telescope_geo.cpp +++ b/examples/AlignDet/src/Telescope_geo.cpp @@ -46,12 +46,14 @@ static Ref_t create_element(LCDD& lcdd, xml_h e, SensitiveDetector sd) { Volume modvol(_toString(mod.id(),"module_%d"), box, air); modvol.setVisAttributes(lcdd.visAttributes(mod.visStr())); + DetElement sens_det(mod_det,"sensor",x_det.id()); box = Box(pitch*noPixX/2e0, pitch*noPixY/2e0, sens.thickness()/2e0); vol = Volume(_toString(mod.id(),"sensor_%d"), box, air); vol.setSensitiveDetector(sd); vol.setVisAttributes(lcdd.visAttributes(sens.visStr())); phv = modvol.placeVolume(vol, Position(0, 0, -mod_thick/2e0+sens.thickness()/2e0)); phv.addPhysVolID("sensor",1); + sens_det.setPlacement(phv); box = Box(pitch*noPixX/2e0, pitch*noPixY/2e0, chip.thickness()/2e0); vol = Volume(_toString(mod.id(),"chip_%d"), box, air); diff --git a/examples/Conditions/data/Modules_run-1000...2000.xml b/examples/Conditions/data/Modules_run-1000...2000.xml index 4534ee872b0d82cec40a25ec16d1924cd6dfdbfb..c9f74bc0edb1e88dcdd49b9ea6e2024338d69bcf 100644 --- a/examples/Conditions/data/Modules_run-1000...2000.xml +++ b/examples/Conditions/data/Modules_run-1000...2000.xml @@ -3,6 +3,13 @@ <!--- Created : 2016-11-07 --> <conditions> + <detelement path="/world/Telescope"> + <alignment> + <position x="0" y="0" z="5*cm"/> + <rotation x="0" y="0" z="0"/> + </alignment> + </detelement> +<!-- <detelement path="/world/Telescope/module_1"> </detelement> @@ -38,13 +45,26 @@ <rotation x="0" y="pi/2" z="0"/> </alignment> </detelement> - +--> <detelement path="/world/Telescope/module_9" ref="default_module.xml"> <alignment> - <position x="0" y="0" z="290.0*mm"/> - <rotation x="0" y="pi/2" z="0"/> + <position x="0" y="0" z="10.0*mm"/> + <rotation x="0" y="0" z="0"/> <pivot x="0" y="0" z="0"/> </alignment> + <detelement path="/world/Telescope/module_9/sensor"> + <alignment> + <position x="0" y="0" z="10.0*mm"/> + <!-- This is a point symmetry of 180 degree. + Can be checked with the printer. + x,y coordinates should invert sign. + --> + <rotation x="0" y="0" z="pi"/> + <pivot x="0" y="0" z="0"/> + </alignment> + </detelement> +<!-- +--> </detelement> </conditions>