23 #include "G4EventManager.hh"
24 #include "G4GDMLParser.hh"
25 #include "G4Navigator.hh"
26 #include "G4ParallelWorldPhysics.hh"
27 #include "G4PropagatorInField.hh"
28 #include "G4RunManagerKernel.hh"
29 #include "G4ScoringManager.hh"
30 #include "G4StackManager.hh"
31 #include "G4StateManager.hh"
32 #include "G4TrackingManager.hh"
33 #include "G4TransportationManager.hh"
34 #include "G4UImanager.hh"
35 #include "G4VModularPhysicsList.hh"
36 #include "G4VUserPhysicsList.hh"
39 #include "CLHEP/Random/RandomEngine.h"
42 #include "GaudiKernel/IThreadInitTool.h"
55 static std::once_flag initializeOnceFlag;
56 static std::once_flag finalizeOnceFlag;
57 static std::once_flag releaseGeoModelOnceFlag;
77 if(!m_simplifiedGeoPath.empty()) {
80 if (geoFile.empty()) {
81 ATH_MSG_FATAL(
"Could not find simplified geometry file: " << m_simplifiedGeoPath);
82 return StatusCode::FAILURE;
86 parser.Read(geoFile,
false);
90 if (m_recordFlux) G4ScoringManager::GetScoringManager();
98 ATH_MSG_ERROR(
"Failure in G4AtlasAlg::initializeOnce: " <<
e.what());
99 return StatusCode::FAILURE;
109 ATH_CHECK( m_truthRecordSvc.retrieve() );
110 ATH_MSG_INFO(
"- Using ISF TruthRecordSvc : " << m_truthRecordSvc.typeAndName() );
112 ATH_MSG_INFO(
"- Using ISF GeoIDSvc : " << m_geoIDSvc.typeAndName() );
119 ATH_CHECK( m_inputTruthCollectionKey.initialize());
120 ATH_CHECK( m_outputTruthCollectionKey.initialize());
121 ATH_CHECK( m_eventInfoKey.initialize() );
124 if ( not m_truthPreselectionTool.empty() ) {
125 ATH_CHECK(m_truthPreselectionTool.retrieve());
128 if ( not m_qspatcher.empty() ) {
133 return StatusCode::SUCCESS;
141 throw std::runtime_error(
"Could not initialize ATLAS PhysicsListSvc!");
145 throw std::runtime_error(
"Failed to add action tool "+action_tool.name());
149 ATH_MSG_INFO(
"retrieving the Detector Construction tool" );
151 throw std::runtime_error(
"Could not initialize ATLAS DetectorConstruction!");
156 #ifdef G4MULTITHREADED
158 G4AtlasMTRunManager::GetG4AtlasMTRunManager();
164 std::unique_ptr<G4AtlasUserWorkerThreadInitialization> workerInit =
165 std::make_unique<G4AtlasUserWorkerThreadInitialization>();
167 runMgr->SetUserInitialization( workerInit.release() );
168 std::unique_ptr<G4AtlasActionInitialization> actionInitialization =
170 runMgr->SetUserInitialization(actionInitialization.release());
173 throw std::runtime_error(
"Trying to use multi-threading in non-MT build!");
179 G4AtlasRunManager::GetG4AtlasRunManager();
181 runMgr->SetRecordFlux(
m_recordFlux, std::make_unique<G4AtlasFluxRecorder>() );
182 runMgr->SetLogLevel(
int(
msg().
level()) );
186 std::unique_ptr<G4AtlasActionInitialization> actionInitialization =
188 runMgr->SetUserInitialization(actionInitialization.release());
193 G4UImanager *ui = G4UImanager::GetUIpointer();
197 ATH_MSG_INFO(
"G4AtlasAlg specific libraries requested ");
199 ui->ApplyCommand(temp);
204 std::string temp=
"/Physics/GetPhysicsList "+
m_physList;
205 ui->ApplyCommand(temp);
211 std::string temp=
"/MagneticField/Select "+
m_fieldMap;
212 ui->ApplyCommand(temp);
213 ui->ApplyCommand(
"/MagneticField/Initialize");
217 ATH_MSG_DEBUG(
"G4 Command: Trying at the end of initializeOnce()");
219 int returnCode = ui->ApplyCommand( g4command );
224 auto* rm = G4RunManager::GetRunManager();
226 throw std::runtime_error(
"Run manager retrieval has failed");
230 if(!
m_useMT && rm->ConfirmBeamOnCondition()) {
231 rm->RunInitialization();
236 if (physicsTool->initializePhysics().isFailure()) {
237 throw std::runtime_error(
"Failed to initialize physics with tool " + physicsTool.name());
242 throw std::runtime_error(
"Could not initialize ATLAS UserLimitsSvc!");
246 G4VModularPhysicsList* thePhysicsList=
dynamic_cast<G4VModularPhysicsList*
>(
m_physListSvc->GetPhysicsList());
247 if (!thePhysicsList) {
248 throw std::runtime_error(
"Failed dynamic_cast!! this is not a G4VModularPhysicsList!");
250 #if G4VERSION_NUMBER >= 1010
251 std::vector<std::string>& parallelWorldNames=
m_detConstruction->GetParallelWorldNames();
252 for (
auto&
it: parallelWorldNames) {
253 thePhysicsList->RegisterPhysics(
new G4ParallelWorldPhysics(
it,
true));
264 G4TransportationManager *tm = G4TransportationManager::GetTransportationManager();
265 G4RunManagerKernel *rmk = G4RunManagerKernel::GetRunManagerKernel();
266 G4EventManager *em = G4EventManager::GetEventManager();
270 tm->GetNavigatorForTracking()->SetVerboseLevel(
atof(itr->second.data()) );
273 tm->GetPropagatorInField()->SetVerboseLevel(
atof(itr->second.data()) );
276 rmk->GetTrackingManager()->SetVerboseLevel(
atof(itr->second.data()) );
279 rmk->GetTrackingManager()->GetSteppingManager()->
280 SetVerboseLevel(
atof(itr->second.data()) );
283 rmk->GetStackManager()->SetVerboseLevel(
atof(itr->second.data()) );
286 em->SetVerboseLevel(
atof(itr->second.data()) );
297 ATH_MSG_DEBUG(
"++++++++++++ G4AtlasAlg finalized ++++++++++++" <<std::endl<<std::endl);
304 ATH_MSG_ERROR(
"Failure in G4AtlasAlg::finalizeOnce: " <<
e.what());
305 return StatusCode::FAILURE;
308 return StatusCode::SUCCESS;
315 auto runMgr = G4RunManager::GetRunManager();
316 runMgr->RunTermination();
323 static std::atomic<unsigned int> n_Event=0;
324 ATH_MSG_DEBUG(
"++++++++++++ G4AtlasAlg execute ++++++++++++");
328 if (n_Event<=10 || (n_Event%100) == 0) {
329 ATH_MSG_ALWAYS(
"G4AtlasAlg: Event num. " << n_Event <<
" start processing");
338 ATH_MSG_ERROR(
"Failure in G4AtlasAlg::releaseGeoModel: " <<
e.what());
339 return StatusCode::FAILURE;
343 const EventContext& ctx = Gaudi::Hive::currentContext();
348 G4Random::setTheEngine(*rngWrapper);
352 auto eventInfo = std::make_unique<AtlasG4EventUserInfo>();
354 std::shared_ptr<HitCollectionMap> hitCollections = eventInfo->GetHitCollectionMap();
360 if (!inputTruthCollection.
isValid()) {
361 ATH_MSG_FATAL(
"Unable to read input GenEvent collection " << inputTruthCollection.
name() <<
" in store " << inputTruthCollection.
store());
362 return StatusCode::FAILURE;
364 ATH_MSG_DEBUG(
"Found input GenEvent collection " << inputTruthCollection.
name() <<
" in store " << inputTruthCollection.
store());
367 std::unique_ptr<McEventCollection> shadowTruth{};
369 outputTruthCollection = std::make_unique<McEventCollection>();
371 shadowTruth = std::make_unique<McEventCollection>(*inputTruthCollection);
372 for (HepMC::GenEvent* currentGenEvent : *shadowTruth ) {
379 outputTruthCollection->
push_back(outputEvent.release());
384 outputTruthCollection = std::make_unique<McEventCollection>(*inputTruthCollection);
386 shadowTruth = std::make_unique<McEventCollection>();
389 for (HepMC::GenEvent* currentGenEvent : *outputTruthCollection ) {
395 ATH_MSG_DEBUG(
"Recorded output GenEvent collection " << outputTruthCollection.
name() <<
" in store " << outputTruthCollection.
store());
408 auto inputEvent = std::make_unique<G4Event>(ctx.eventID().event_number());
409 inputEvent->SetUserInformation(eventInfo.release());
412 *outputTruthCollection, *inputEvent, *shadowTruth));
418 #ifdef G4MULTITHREADED
419 auto* workerRM = G4AtlasWorkerRunManager::GetG4AtlasWorkerRunManager();
420 abort = workerRM->ProcessEvent(inputEvent.release());
422 ATH_MSG_ERROR(
"Trying to use multi-threading in non-MT build!");
423 return StatusCode::FAILURE;
427 G4AtlasRunManager::GetG4AtlasRunManager();
428 abort = workerRM->ProcessEvent(inputEvent.release());
436 setFilterPassed(
false);
442 "Failed to retrieve xAOD::EventInfo while trying to update the "
444 return StatusCode::FAILURE;
460 for (HepMC::GenEvent* currentGenEvent : *outputTruthCollection ) {
465 return StatusCode::SUCCESS;
472 SmartIF<IGeoModelSvc> geoModel{Gaudi::svcLocator()->service(
"GeoModelSvc")};
477 if (geoModel->clear().isFailure()) {
481 ATH_MSG_INFO(
" ----> GeoModelSvc::clear() succeeded " );
491 case 0: {
ATH_MSG_DEBUG(
"G4 Command: " << commandString <<
" - Command Succeeded"); }
break;
492 case 100: {
ATH_MSG_ERROR(
"G4 Command: " << commandString <<
" - Command Not Found!"); }
break;
494 auto* stateManager = G4StateManager::GetStateManager();
495 ATH_MSG_DEBUG(
"G4 Command: " << commandString <<
" - Illegal Application State (" <<
496 stateManager->GetStateString(stateManager->GetCurrentState()) <<
")!");
498 case 300: {
ATH_MSG_ERROR(
"G4 Command: " << commandString <<
" - Parameter Out of Range!"); }
break;
499 case 400: {
ATH_MSG_ERROR(
"G4 Command: " << commandString <<
" - Parameter Unreadable!"); }
break;
500 case 500: {
ATH_MSG_ERROR(
"G4 Command: " << commandString <<
" - Parameter Out of Candidates!"); }
break;
501 case 600: {
ATH_MSG_ERROR(
"G4 Command: " << commandString <<
" - Alias Not Found!"); }
break;
502 default: {
ATH_MSG_ERROR(
"G4 Command: " << commandString <<
" - Unknown Status!"); }
break;