Commit 09aa34fe authored by Dominik Muller's avatar Dominik Muller Committed by Rosen Matev
Browse files

Dynamic writing of main DD4hep xml, sensitive detector from DD4hep, Bls...

Dynamic writing of main DD4hep xml, sensitive detector from DD4hep, Bls support from dd4hep and monitor
parent 9385290e
This diff is collapsed.
......@@ -11,76 +11,4 @@
// $Id: BlsHitChecker.h,v 1.1.1.2 2010-03-10 17:38:47 vtalanov Exp $
#ifndef BLSHITCHECKER_H
#define BLSHITCHECKER_H 1
// Include files
// from Gaudi
#include "GaudiAlg/GaudiTupleAlg.h"
#include "Event/MCHit.h"
// from STL
#include <map>
/** @class BlsHitChecker BlsHitChecker.h
*
*
* @author Vadim Talanov
* @date 2010-02-06
*/
class BlsHitChecker : public GaudiTupleAlg {
public:
/// Standard constructor
BlsHitChecker( const std::string& name, ISvcLocator* pSvcLocator );
virtual ~BlsHitChecker( ); ///< Destructor
StatusCode initialize() override; ///< Algorithm initialization
StatusCode execute () override; ///< Algorithm execution
StatusCode finalize () override; ///< Algorithm finalization
protected:
private:
LHCb::MCHits* m_blsMCHits;
std::string m_blsHitsLocation;
bool m_blsAOn;
bool m_blsCOn;
std::string m_blsHTitlePrefix;
double m_blsHEntryXMin;
double m_blsHEntryXMax;
unsigned long m_blsHEntryXNbins;
double m_blsHEntryYMin;
double m_blsHEntryYMax;
unsigned long m_blsHEntryYNbins;
double m_blsHEntryZMin;
double m_blsHEntryZMax;
unsigned long m_blsHEntryZNbins;
double m_blsHEntryTimeOffset;
double m_blsHEntryTimeMin;
double m_blsHEntryTimeMax;
unsigned long m_blsHEntryTimeNbins;
double m_blsHTrackEnDepMin;
double m_blsHTrackEnDepMax;
unsigned long m_blsHTrackEnDepNbins;
double m_blsHTrackLengthMin;
double m_blsHTrackLengthMax;
unsigned long m_blsHTrackLengthNbins;
double m_blsHEventNumTracksMin;
double m_blsHEventNumTracksMax;
unsigned long m_blsHEventNumTracksNbins;
double m_blsHEventNumMin;
double m_blsHEventNumMax;
unsigned long m_blsHEventNumNbins;
unsigned long m_blsHits;
unsigned long m_blsTracks;
typedef std::multimap < const LHCb::MCParticle*,
LHCb::MCHit* >
t_blsMCParticle2MCHitMultimap;
};
#endif // BLSHITCHECKER_H
#endif // BLSHITCHECKER_H
......@@ -19,6 +19,7 @@ gaudi_depends_on_subdirs(Sim/GiGaMTFactories
Sim/GiGaMTGeo
DD4hepDDG4Ext
Sim/GiGaMTDD4hep
Sim/GaussTracker
Det/LbDD4hep)
find_package(Boost)
......@@ -45,4 +46,4 @@ message(STATUS "DD4hepDDG4_LIBRARIES: ${DD4hepDDG4_LIBRARIES}")
gaudi_add_module(DD4hepCnv
src/component/*.cpp
INCLUDE_DIRS Tools/ClhepTools GiGaMTGeo LbDD4hep DD4hep
LINK_LIBRARIES ${GEANT4_LIBS} DD4hep ${DD4hep_COMPONENT_LIBRARIES} ROOT GiGaMTCoreRunLib GiGaMTDD4hepLib)
LINK_LIBRARIES ${GEANT4_LIBS} DD4hep ${DD4hep_COMPONENT_LIBRARIES} ROOT GiGaMTCoreRunLib GiGaMTDD4hepLib GaussTrackerLib)
......@@ -120,13 +120,6 @@ StatusCode DD4hepCnvSvc::initialize() {
auto& g4map = dd4hep::sim::Geant4Mapping::instance();
dd4hep::setPrintLevel(DD4hepGaudiMessaging::Convert(msgLevel()));
dd4hep::DetElement world = m_dd4Svc->getDetector().world();
if ( msgLevel( MSG::DEBUG ) ) {
auto & children =world.children();
debug() << "Children of DD4hep world DetElement:" << endmsg;
for(auto & child: children){
debug() << " --- " << child.first << " ::: " << child.second.name() << endmsg;
}
}
dd4hep::sim::Geant4Converter conv(dd4hep::Detector::getInstance(), DD4hepGaudiMessaging::Convert(msgLevel()));
conv.debugMaterials = m_debugMaterials.value();
conv.debugElements = m_debugElements.value();
......@@ -143,6 +136,27 @@ StatusCode DD4hepCnvSvc::initialize() {
m_world_root = geoinfo->world();
// Create Geant4 volume manager only if not yet available
g4map.volumeManager();
// Printout all active volumes and assigned sensitive detectors from dd4hep
if (msgLevel(MSG::DEBUG)) {
debug() << "Stored paths in volume manager: " << endmsg;
for(auto & pp: g4map.volumeManager()->g4Paths){
debug() << "/";
for(auto & pv:pp.first){
debug() << pv->GetName() << "/";
}
debug() << " ID:" << pp.second << endmsg;
}
for (auto& [dd4hep_volume, g4_volume] : g4map.data().g4Volumes) {
if (!dd4hep_volume.isValid() || !dd4hep_volume.isSensitive()) {
continue;
}
auto dd4hep_sensdet_name = dd4hep_volume.sensitiveDetector().name();
debug() << "Active volume '" << dd4hep_volume.name() << "' SensDet: '"
<< dd4hep_sensdet_name << "'" << endmsg;
if (dd4hep_volume.isSensitive()) {
}
}
}
// We now loop over the existing logical volume mappings and extract the sensitive detector knowledge
// from the DD4hep volumes and map them to the requested Gaussino factories
......
......@@ -14,10 +14,30 @@ from Gauss.Geometry.Helpers import subdetector
@subdetector
class BCM(det_base):
class BLS(det_base):
__slots__ = {}
def ApplyDetectorDD4hep(self, basePieces, detPieces):
# Configuring the DD4hep detector conversion.
# 1. Add the mapping to have the DD4hepCnvSvc instrument
# the G4 volume with the correct sensdet factory if marked with a
# dd4hep sensitive detector named VP
from Configurables import DD4hepCnvSvc
mappings = DD4hepCnvSvc().getProp('SensDetMappings')
mappings['Bls'] = 'GiGaSensDetTrackerDD4hep/BlsSDet'
DD4hepCnvSvc().SensDetMappings = mappings
# Add the necessary dd4hep includes for the VP. Also added all the
# dependencies for material definitions that were identified using
# trial and error. As the list is made unique before being added to
# the xml this should be fine if they appear in multiple places
from Gauss.Geometry import LHCbGeo
go = LHCbGeo._listOfXMLIncludes_
go += ["Bls/parameters.xml"]
go += ["Bls/detector.xml"]
def ApplyDetectorDetDesc(self, basePieces, detPieces):
from Gauss.Geometry import LHCbGeo
# Add the non-standard pieces of the BeforeMagnet region.
......@@ -38,3 +58,68 @@ class BCM(det_base):
if piece in detPieces[region]:
continue
detPieces[region] += [piece]
def SetupExtractionImpl(self, slot=''):
from Configurables import GetTrackerHitsAlg
self.simconf_name = 'Bls'
region = "BeforeMagnetRegion"
det = "Bls"
alg = GetTrackerHitsAlg(
'Get'+det+'Hits'+slot,
MCHitsLocation='MC/'+det+'/Hits',
CollectionName=det + 'SDet/Hits',
)
# Only add the detectors if we are not using DD4hep so that the ID is
# looked up using DetDesc
if not self.getProp('UseDD4hep'):
alg.Detectors = ['/dd/Structure/LHCb/' + region + '/' + det]
from Configurables import ApplicationMgr
ApplicationMgr().TopAlg += [alg]
def SetupMonitor(self, slot=''):
from GaudiKernel import SystemOfUnits
from Configurables import BlsHitChecker
moni = BlsHitChecker("BlsHitCheckerAll"+slot)
from Configurables import ApplicationMgr
moni.HistoDir = "BlsHitChecker/BlsHitCheckerAll"
moni.BlsAOn = True
moni.BlsCOn = True
moni.HistogramTitlePrefix = "BlsA+C: "
moni.EntryXMin = -150.0 * SystemOfUnits.mm
moni.EntryXMax = +150.0 * SystemOfUnits.mm
moni.EntryXNbins = 300
moni.EntryYMin = -150.0 * SystemOfUnits.mm
moni.EntryYMax = +150.0 * SystemOfUnits.mm
moni.EntryYNbins = 300
moni.EntryZMin = -2200.0 * SystemOfUnits.mm
moni.EntryZMax = -1900.0 * SystemOfUnits.mm
moni.EntryZNbins = 300
moni.EntryTimeOffset = +0.0 * SystemOfUnits.ns
moni.EntryTimeMin = -50.0 * SystemOfUnits.ns
moni.EntryTimeMax = +50.0 * SystemOfUnits.ns
moni.EntryTimeNbins = 100
moni.EventNumMin = 0.0
moni.EventNumMax = 1000.0
moni.EventNumNbins = 1000
moni.EventNumTracksMin = 0.0
moni.EventNumTracksMax = 50.0
moni.EventNumTracksNbins = 50
moni.TrackEnDepMin = 0.0
moni.TrackEnDepMax = 50.0
moni.TrackEnDepNbins = 50
moni.TrackLengthMin = 0.0
moni.TrackLengthMax = 7.0
moni.TrackLengthNbins = 70
ApplicationMgr().TopAlg += [moni]
moni = BlsHitChecker("BlsHitCheckerBlsA"+slot)
moni.HistoDir = "BlsHitChecker/BlsHitCheckerBlsA"
moni.BlsAOn = True
moni.HistogramTitlePrefix = "BlsA: "
ApplicationMgr().TopAlg += [moni]
moni = BlsHitChecker("BlsHitCheckerBlsC"+slot)
moni.HistoDir = "BlsHitChecker/BlsHitCheckerBlsC"
moni.BlsCOn = True
moni.HistogramTitlePrefix = "BlsC: "
ApplicationMgr().TopAlg += [moni]
......@@ -41,8 +41,8 @@ class LHCbGeo(LHCbConfigurableUser):
"Debug": False,
"DD4hep": False,
"SaveGDMLFile": "",
"SensDetMap":{},
"ExtraGeoTools":[]
"SensDetMap": {},
"ExtraGeoTools": []
}
_detectorsDefaults = {
......@@ -64,6 +64,8 @@ class LHCbGeo(LHCbConfigurableUser):
# List of geometry objects which will be converted, it's content is used in
# GaussGeo or in GiGaInputStream if GiGaGeo is used for conversion
_listOfGeoObjects_ = []
# List of DD4hep XML includes
_listOfXMLIncludes_ = []
def __init__(self, name=Configurable.DefaultName, **kwargs):
kwargs["name"] = name
......@@ -107,7 +109,6 @@ class LHCbGeo(LHCbConfigurableUser):
checkIncompatibleDetectors()
defineGeoBasePieces(basePieces)
from Gauss.Geometry.Helpers import getsubdetector
detectors_geo = self.getProp("DetectorGeo")["Detectors"]
detectors_sim = self.getProp("DetectorSim")["Detectors"]
......@@ -121,7 +122,7 @@ class LHCbGeo(LHCbConfigurableUser):
getsubdetector(det).Monitor = True
# BeamPipe
# getsubdetector('BeamPipe').ApplyDetector(basePieces, detPieces)
getsubdetector('BeamPipe').ApplyDetector(basePieces, detPieces)
for det in detectors_geo:
getsubdetector(det).ApplyDetector(basePieces, detPieces)
......@@ -134,19 +135,7 @@ class LHCbGeo(LHCbConfigurableUser):
for det in detectors_geo:
getsubdetector(det).ApplyStream()
# getsubdetector("Magnet").defineMagnetGeoField()
# FIXME: those calo option files
# Seperate Calo opts
# Returns a list containing all the elments common to both lists
# if self.getProp('UseGaussGeo'):
# if [det for det in ['Spd', 'Prs', 'Ecal', 'Hcal'] if det in
# self.getProp('DetectorGeo')['Detectors']]: # NOQA
# importOptions("$GAUSSCALOROOT/options/GaussGeo-Calo.py")
# else:
# if [det for det in ['Spd', 'Prs', 'Ecal', 'Hcal'] if det in
# self.getProp('DetectorGeo')['Detectors']]: # NOQA
# importOptions("$GAUSSCALOROOT/options/Calo.opts")
getsubdetector("Magnet").defineMagnetGeoField()
self.PrintDebugDump(detPieces, basePieces)
......@@ -167,6 +156,11 @@ class LHCbGeo(LHCbConfigurableUser):
gaussgeo.AlignAllDetectors = True
for el in self._listOfGeoObjects_:
gaussgeo.GeoItemsNames.append(el)
else:
from Gauss.Geometry import xml_writer
from Configurables import LHCb__Det__LbDD4hep__DD4hepSvc
LHCb__Det__LbDD4hep__DD4hepSvc().DescriptionLocation = \
xml_writer.create_xml(self._listOfXMLIncludes_)
self.MakeItTalkToGaussino()
......@@ -213,7 +207,7 @@ class LHCbGeo(LHCbConfigurableUser):
svc.RegionsDefinitionDbLocation = xmlfile
def PrintDebugDump(self, detPieces, basePieces):
if self.getProp("Debug"):
if self.getProp("Debug") and not self.getProp("DD4hep"):
print "\nDEBUG Detector Geometry Elements:"
print "\nkey : detPieces[key]"
for key in detPieces.keys():
......
......@@ -19,11 +19,29 @@ class VP(det_base):
__slots__ = {}
def ApplyDetectorDD4hep(self, basePieces, detPieces):
# Configuring the DD4hep detector conversion.
# 1. Add the mapping to have the DD4hepCnvSvc instrument
# the G4 volume with the correct sensdet factory if marked with a
# dd4hep sensitive detector named VP
from Configurables import DD4hepCnvSvc
mappings = DD4hepCnvSvc().getProp('SensDetMappings')
mappings['VP'] = 'GiGaSensDetTracker/VPSDet'
mappings['VP'] = 'GiGaSensDetTrackerDD4hep/VPSDet'
DD4hepCnvSvc().SensDetMappings = mappings
# Add the necessary dd4hep includes for the VP. Also added all the
# dependencies for material definitions that were identified using
# trial and error. As the list is made unique before being added to
# the xml this should be fine if they appear in multiple places
from Gauss.Geometry import LHCbGeo
go = LHCbGeo._listOfXMLIncludes_
go += ["Pipe/parameters.xml"]
go += ["Rich1/materials.xml"]
go += ["VP/parameters.xml"]
go += ["VP/visualization.xml"]
go += ["VP/detector.xml"]
go += ["VP/conditions.xml"]
def ApplyDetectorDetDesc(self, basePieces, detPieces):
BeamPipe.removeBeamPipeElements("velo")
if 'BeforeMagnetRegion' in detPieces:
......@@ -38,8 +56,9 @@ class VP(det_base):
'Get'+det+'Hits'+slot,
MCHitsLocation='MC/'+det+'/Hits',
CollectionName=det + 'SDet/Hits',
Detectors=['/dd/Structure/LHCb/' + region + '/' + det]
)
if not self.getProp('UseDD4hep'):
alg.Detectors = ['/dd/Structure/LHCb/' + region + '/' + det]
from Configurables import ApplicationMgr
ApplicationMgr().TopAlg += [alg]
......
......@@ -24,6 +24,8 @@ from Gauss.Geometry.UT import *
from Gauss.Geometry.Magnet import *
from Gauss.Geometry.Muon import *
from Gauss.Geometry.HC import *
from Gauss.Geometry.BLS import *
from Gauss.Geometry.BCM import *
__all__ = [
'LHCbGeo', 'BeamPipe'
......
###############################################################################
# (c) Copyright 2000-2020 CERN for the benefit of the LHCb Collaboration #
# #
# This software is distributed under the terms of the GNU General Public #
# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING". #
# #
# In applying this licence, CERN does not waive the privileges and immunities #
# granted to it by virtue of its status as an Intergovernmental Organization #
# or submit itself to any jurisdiction. #
###############################################################################
import xml.etree.ElementTree as ET
from xml.dom import minidom
from collections import OrderedDict
from Gaudi.Configuration import log
import tempfile
import os
# Combine the includes into a valid LHCb DD4hep xml and return name of temporary
# file
def create_xml(includesfiles):
unique_includes = list(OrderedDict.fromkeys(includesfiles))
detectorroot = os.path.join(os.environ['DETECTOR_PROJECT_ROOT'], 'compact/')
def addroot(p):
if p[0] != '.' and p[0] != '/':
return detectorroot + p
return p
root = ET.Element("lccdd")
ET.SubElement(root, "std_conditions", type="STP")
debug = ET.SubElement(root, "debug")
ET.SubElement(debug, "type", name="includes", value="0")
ET.SubElement(debug, "type", name="materials", value="0")
includes = ET.SubElement(root, "includes")
ET.SubElement(includes, "gdmlFile", ref=addroot("defaults.xml"))
define = ET.SubElement(root, "define")
ET.SubElement(define, "constant", name="Bls:parent",
value="/world/BeforeMagnetRegion/BeforeVelo", type="string")
ET.SubElement(define, "constant", name="BcmUp:parent",
value="/world/BeforeMagnetRegion/BeforeVelo", type="string")
ET.SubElement(define, "constant", name="BcmDown:parent",
value="/world/DownstreamRegion/AfterMuon", type="string")
ET.SubElement(define, "constant", name="GValve:parent",
value="/world/BeforeMagnetRegion/BeforeVelo", type="string")
ET.SubElement(define, "constant", name="MBXWUp:parent",
value="/world/UpstreamRegion", type="string")
ET.SubElement(define, "constant", name="Cavern:parent",
value="/world/Infrastructure", type="string")
ET.SubElement(define, "constant", name="Tunnel:parent",
value="/world/Infrastructure", type="string")
ET.SubElement(define, "constant", name="Bunker:parent",
value="/world/Infrastructure", type="string")
ET.SubElement(define, "constant", name="VP:parent",
value="/world/BeforeMagnetRegion", type="string")
ET.SubElement(define, "constant", name="UT:parent",
value="/world/BeforeMagnetRegion", type="string")
ET.SubElement(define, "constant", name="FT:parent",
value="/world/AfterMagnetRegion/T", type="string")
ET.SubElement(define, "constant", name="Magnet:ignore", value="0")
ET.SubElement(define, "constant", name="UpstreamRegion:ignore", value="0")
ET.SubElement(define, "constant", name="BeforeMagnetRegion:ignore", value="0") # NOQA
ET.SubElement(define, "constant", name="MagnetRegion:ignore", value="0")
ET.SubElement(define, "constant", name="AfterMagnetRegion:ignore", value="0") # NOQA
ET.SubElement(define, "constant", name="DownstreamRegion:ignore", value="0")
ET.SubElement(root, "include", ref=addroot("global/conditions.xml"))
# FIXME: Regions need something from this file
ET.SubElement(root, "include", ref=addroot("T/parameters.xml"))
ET.SubElement(root, "include", ref=addroot("Regions/detector.xml"))
for inc in unique_includes:
ET.SubElement(root, "include", ref=addroot(inc))
_, tmpfile = tempfile.mkstemp('.xml')
xmlstr = minidom.parseString(ET.tostring(root)).toprettyxml(indent=" ")
with open(tmpfile, "w") as f:
f.write(xmlstr)
log.info('Wrote xml file to {}'.format(tmpfile))
return tmpfile
......@@ -173,6 +173,8 @@ class G4Physics(LHCbConfigurableUser):
for hp in _all[hadronPhys]:
addConstructor(pl, *hp)
return True
elif hadronPhys == '':
log.warning("No hadron physics list")
else:
raise RuntimeError("Unknown Hadron PhysicsList "
"chosen ('%s')" % hadronPhys)
......@@ -188,8 +190,8 @@ class G4Physics(LHCbConfigurableUser):
else:
self.defineRichPhys(pl)
else:
log.warning("The lhcb-related physics (RICH processed,"
"UnknownParticles) is disabled")
log.warning("The lhcb-related physics (RICH processed)"
"is disabled")
def AddOtherPhysics(self, pl):
otherPhys = self.getProp('Other')
......
Supports Markdown
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment