Project

General

Profile

Extensible PhysicsList Factory

General Overview

The C++ construct of a "factory" is generally based on a mix of the two Design Patterns [ 1 ], the "Abstract Factory" and "Singleton". The "Abstract Factory" is an interface for creating objects of a related type without the the need for caller to have knowledge (i.e. C++ headers) of individual concrete classes. A factory typically gets a request based on a string name and returns an object of that type that derives from a base class. The "Singleton" pattern is to ensure consistent access to the one-and-only instance of an class object (creating it if necessary). The addition of the "Singleton" factory is a means of allowing the factory to retain a central registry of known types (e.g. blueprints) and allowing it to be extended by registering new types with it.

Details how how this is implemented in Geant4 can be found here.

Current Issues 2018-03 here.

Goals of this Factory

The goal of the new g4alt::G4PhysListFactory is to be a drop-in replacement for the existing G4PhysListFactory that requires no code changes once the g4alt namespace is removed. When substituted in it should provide all the current functionality. In addition the goal is to allow more flexibility to the users by allowing them to extend the list of known G4VModularPhysList's and extend the paradigm presented by the EM extensions (_EMX, _EMY, etc ...) already in the old factory.

The new factory treats user generated and pre-supplied physics lists identically, which makes it extensible for the user.

New Classes

The g4alt::G4PhysListFactory is the replacement interface; it in itself does very little. In order to make it compatible with existing code it is implemented as a lightweight object that delegates the work to G4PhysListRegistry. This allows g4alt::G4PhysListFactory to be created and destroyed on the stack as it currently used in most examples.

The G4PhysListRegistry is a singleton that holds the state of registered lists and extensions.

The G4PhysListStamper (equivalent in function to G4PhysicsConstructorFactory, as G4PhysListRegistry is to G4PhysicsConstructorRegistry) is the templated class to register itself with a single physics list constructor to the G4PhysListRegistry.

The G4RegisterPhysList simply registers all existing Geant4 supplied G4VModularPhysList s.

Usage

Most usages of the factory require minimal changes at present; i.e. only those required due to concurrency of the two versions.

+ #ifdef USE_OLD
    #include "G4PhysListFactory.hh" 
+ #else
+   #include "G4PhysListFactoryAlt.hh" 
+ #endif

+ #ifdef USE_OLD
    G4PhysListFactory factory;
+ #else
+   g4alt::G4PhysListFactory factory;
+ #endif

or alternatively

-   #include "G4PhysListFactory.hh" 
+   #include "G4PhysListFactoryAlt.hh" 
+   using namespace g4alt;
+  // no further changes to the code are required

Using the new features

Declaring new physics lists

To register a new physics list one uses the construct:

  #include "G4PhysListStamper.hh" 

  #include "AnyOldPhysList.hh" 
  G4_DECLARE_PHYSLIST_FACTORY(AnyOldPhysList);

  // restrictions on cpp macros require a slightly different form in case namespaces
  #include "MyNameSpacedPhysList.hh" 
  G4_DECLARE_PHYSLIST_FACTORY_NS(myns::MyNameSpacedPhysList,myns,MyNameSpacedPhysList);

Use in conjunction with new physics constructors

Similar to adding new physics lists to it's factory, one can also add new physics constructors to it's respective factory. This allows a generalization of the EM modifiers (e.g. _EMX, _EMY ...) to include replacing or adding additional phys_ctors to any physics list available to the factory (include user additions). One must register the new phys_ctor with its factory, and (if desired) add a mapping from the long name to short (e.g. "G4EmStandarPhysics_option4" to "EMZ"). We use the convention that an underscore separator ("_") means "replace", while a plus ("+") means "add"/register).

The declaration of new physics constructors is slightly different (due to the template form of physics lists):

  #include "G4PhysicsConstructorFactory.hh" 
  G4_REFERENCE_PHYSCONSTR_FACTORY(NameOfPhysCtor);
  G4_REFERENCE_PHYSCONSTR_FACTORY_NS(myns::G4NewExoticPhysics,myns,G4NewExoticPhysics)

Physics constructors that are registered with the G4PhysicsConstructorFactory are mapped to an shorter extension name with:

  #include "G4PhysListRegistryAlt.hh" 

  g4alt::G4PhysListRegistry::Instance()->AddPhysicsExtension("EMZ","G4EmStandardPhysics_option4");
  g4alt::G4PhysListRegistry::Instance()->AddPhysicsExtension("NEWPHY","myns::G4NewExoticPhysics");

The latest tagged version of the physics_lists subpackage also allows extending an individual list by using the full physics constructor name, e.g. "FTFP_BERT+myns::G4NewExoticPhysics", when a request is made to the physics list factory.

Restrictions

Linking / Loading concerns for offical code

Because of restrictions on how the MS Windows linker works for static libraries these lines must be included in a code object that will be explicitly linked. For dynamically loaded libraries they only must simply be part of a loaded library.

To standardize this the declaration of all the standard Geant4 reference physics lists are collected into: source/physics_lists/lists/include/G4RegisterPhysLists.icc. This is compiled into the G4PhysListRegistry.cc object which is directly referenced by the g4alt::G4PhysListFactory class.

Similarly the declaration of all the standard Geant4 physics constructors are all collected into: source/physics_lists/constructors/factory/src/G4PhysicsConstructorRegistry.cc.

Linking / Loading concerns for user supplied code

Any user code wanting to make use of extending the factories must have the code object (.o) either included in a dynamically loaded shared object library (generally the case for non-MS Windows builds) or have the .0 file explicitly linked into the executable.

old vs. new factory restrictions

Because the old and new factories currently co-exist they are kept separate by an alternative header G4PhysListFactoryAlt.hh and the new class exists in a namespace g4alt.

test38 demonstrator

The Geant4 test test38 was written as a demonstration program to test the backward compatibility and examine the new functionality.

Details of the test38 demonstrator

Changes to Tests that use the G4PhysListFactory

Other than test38 (G4PhysListFactory demonstrator) the complete list of "tests" that use the factory are:

test status commited changes notes
27 done no Changes to test27 can't add Tst27PhysicsList to the factory because it derives
from G4VUserPhysicsList and not G4VModularPhysicsList
45 done no Changes to test45 tests use of $PHYLIST
.
46 done no Changes to test46 makes use of extensibility functionality & alternative default
existing code compares user string to name that is not class name;
handle this with typedef to mimic old functionality
69 untried - Changes to test69 .
.
73 untried - Changes to test73 .
.

The later two tests (69 and 73) have no "stand-alone" build/run procedure and can only be built in the context of the full test suite.
This complicates doing comparisons.

Changes to Examples that reference G4PhysListFactory

Changes to these haven't yet started; only identified potential candidates.

$ find . -name '*.cc' -exec grep -H G4PhysListFactory {} \; | cut -d':' -f1 | sort -u
file notes
advanced/composite_calorimeter/CompositeCalorimeter.cc
advanced/gammaknife/gammaknife.cc
advanced/gammaknife/src/GammaKnifePhysicsList.cc
advanced/gammaray_telescope/src/GammaRayTelPhysicsList.cc
advanced/hadrontherapy/hadrontherapy.cc
advanced/hadrontherapy/src/HadrontherapyPhysicsList.cc
advanced/iort_therapy/iort_therapy.cc
advanced/iort_therapy/src/IORTPhysicsList.cc
advanced/lAr_calorimeter/lArCal.cc
advanced/medical_linac/src/ML2PhysicsList.cc
advanced/radioprotection/src/PhysicsList.cc
extended/exoticphysics/monopole/monopole.cc
extended/field/field04/src/F04PhysicsList.cc
extended/hadronic/Hadr00/Hadr00.cc
extended/hadronic/Hadr01/Hadr01.cc src/PhysicsList.cc (+ Messenger.cc) G4VModularPhysicsList
extended/hadronic/Hadr02/Hadr02.cc
extended/hadronic/Hadr05/Hadr05.cc
(Hadr03 & Hadr04 & Hadr06) src/PhysicsList G4VModularPhysicsList
extended/optical/wls/src/WLSPhysicsList.cc

Test Studies

Test Study of examples/extended/hadronic/Hadr01


References

[1] Design Patterns: Elements of Reusable Object-Oriented Software -- E. Gamma, R. Helm, R. Johnson, J. Vlissides
[2] https://twiki.cern.ch/twiki/bin/view/Geant4/PhysicsValidationTaskForce