diff --git a/DDG4/src/Geant4CalorimeterSD.cpp b/DDG4/src/Geant4CalorimeterSD.cpp
index a6edbda5f5a294bc71ccef0d608bf99abd1f9417..a1da7a7bead01067a90811a0bf9da58bd91ba127 100644
--- a/DDG4/src/Geant4CalorimeterSD.cpp
+++ b/DDG4/src/Geant4CalorimeterSD.cpp
@@ -49,8 +49,7 @@ namespace DD4hep {  namespace Simulation {
     
     return true;
   }
-    //typedef  Geant4GenericSD<Calorimeter> Geant4Calorimeter;
-    typedef SimpleG4SDFactory< Geant4GenericSD<Calorimeter> > Geant4Calorimeter;
+    typedef  Geant4GenericSD<Calorimeter> Geant4Calorimeter;
 }}    // End namespace DD4hep::Simulation
 
 DECLARE_GEANT4SENSITIVEDETECTOR(Geant4Calorimeter)
@@ -105,8 +104,7 @@ namespace DD4hep {  namespace Simulation {
       }
     }
   };
-    //typedef Geant4GenericSD<OpticalCalorimeter>  Geant4OpticalCalorimeter;
-    typedef SimpleG4SDFactory< Geant4GenericSD<OpticalCalorimeter> > Geant4OpticalCalorimeter;
+    typedef Geant4GenericSD<OpticalCalorimeter>  Geant4OpticalCalorimeter;
 }}    // End namespace DD4hep::Simulation
 
 DECLARE_GEANT4SENSITIVEDETECTOR(Geant4OpticalCalorimeter)
diff --git a/DDG4/src/Geant4Converter.cpp b/DDG4/src/Geant4Converter.cpp
index 003c426abb14797df25a26564d7465ff3dd60306..82ea256e651f7cf7e625eeff4b68de9c21f56679 100644
--- a/DDG4/src/Geant4Converter.cpp
+++ b/DDG4/src/Geant4Converter.cpp
@@ -8,11 +8,12 @@
 //====================================================================
 
 #include "DD4hep/LCDD.h"
+#include "DD4hep/Plugins.h"
 #include "DD4hep/Volumes.h"
 #include "DD4hep/Printout.h"
 #include "DDG4/Geant4Field.h"
 #include "DDG4/Geant4Converter.h"
-#include "DDG4/G4SDFactory.h"
+#include "DDG4/Factories.h"
 #include "DDG4/Geant4SensitiveDetector.h"
 
 // ROOT includes
@@ -36,8 +37,8 @@
 #include "TGeoShapeAssembly.h"
 #include "TClass.h"
 #include "TMath.h"
-#include "Reflex/PluginService.h"
 
+#include "G4VSensitiveDetector.hh"
 #include "G4VisAttributes.hh"
 #include "G4ProductionCuts.hh"
 #include "G4VUserRegionInformation.hh"
@@ -465,7 +466,8 @@ void* Geant4Converter::handleVolume(const string& name, const TGeoVolume* volume
     bool                     assembly = s->IsA() == TGeoShapeAssembly::Class();
 
     SensitiveDetector        det = _v.sensitiveDetector();
-    G4VSensitiveDetector* sd  = 0;
+    G4VSensitiveDetector*    sd  = 0;
+
     if ( det.isValid() )   {
       sd = info.g4SensDets[det.ptr()];
       if ( !sd ) {
@@ -704,34 +706,6 @@ void* Geant4Converter::handleLimitSet(const TNamed* limitset, const set<const TG
   return g4;
 }
 
-// /// Convert the geometry type SensitiveDetector into the corresponding Geant4 object(s).
-// void* Geant4Converter::handleSensitive(const TNamed* sens_det, const set<const TGeoVolume*>& /* volumes */) const  {
-//   Geant4GeometryInfo& info = data();
-//   G4VSensitiveDetector* g4 = info.g4SensDets[sens_det];
-//   if ( !g4 )   {
-//     SensitiveDetector sd = Ref_t(sens_det);
-//     string type = sd.type(), name = sd.name();
-
-//     g4 = ROOT::Reflex::PluginService::Create<G4VSensitiveDetector*>(type,name,&m_lcdd);
-//     if ( !g4 ) {
-//       string tmp = type;
-//       tmp[0] = ::toupper(tmp[0]);
-//       type = "Geant4"+tmp;
-//       g4 = ROOT::Reflex::PluginService::Create<G4VSensitiveDetector*>(type,name,&m_lcdd);
-//       if ( !g4 )  {
-// 	throw runtime_error("Geant4Converter<SensitiveDetector>: FATAL Failed to "
-// 			    "create Geant4 sensitive detector "+name+" of type "+type+".");
-//       }
-//     }
-//     g4->Activate(true);
-//     g4->defineCollection(sd.hitsCollection());
-//     G4SDManager::GetSDMpointer()->AddNewDetector(g4);
-//     info.g4SensDets[sens_det] = g4;
-//   }
-//   return g4;
-// }
-
-
 /// Convert the geometry type SensitiveDetector into the corresponding Geant4 object(s).
 void* Geant4Converter::handleSensitive(const TNamed* sens_det, const set<const TGeoVolume*>& /* volumes */) const  {
   Geant4GeometryInfo& info = data();
@@ -739,38 +713,20 @@ void* Geant4Converter::handleSensitive(const TNamed* sens_det, const set<const T
   if ( !g4 )   {
     SensitiveDetector sd = Ref_t(sens_det);
     string type = sd.type(), name = sd.name();
-
-    //    g4 = ROOT::Reflex::PluginService::Create<G4VSensitiveDetector*>(type,name,&m_lcdd);
-    G4SDFactory* sdf = ROOT::Reflex::PluginService::Create<G4SDFactory*>(type) ;
-    
-    if ( !sdf ) {
+    g4 = PluginService::Create<G4VSensitiveDetector*>(type,name,&m_lcdd);
+    if ( !g4 ) {
       string tmp = type;
       tmp[0] = ::toupper(tmp[0]);
       type = "Geant4"+tmp;
-
-      // g4 = ROOT::Reflex::PluginService::Create<G4VSensitiveDetector*>(type,name,&m_lcdd);
-      sdf = ROOT::Reflex::PluginService::Create<G4SDFactory*>(type) ;
-
-      if ( !sdf )  {
+      g4 = PluginService::Create<G4VSensitiveDetector*>(type,name,&m_lcdd);
+      if ( !g4 )  {
+	PluginDebug dbg;
+	g4 = ROOT::Reflex::PluginService::Create<G4VSensitiveDetector*>(type,name,&m_lcdd);
 	throw runtime_error("Geant4Converter<SensitiveDetector>: FATAL Failed to "
 			    "create Geant4 sensitive detector factory "+name+" of type "+type+".");
       }
     }
-    g4 = sdf->createSD(  name , m_lcdd ) ;
-
-    if ( !g4 ) {
-	throw runtime_error("Geant4Converter<SensitiveDetector>: FATAL Failed to "
-			    "create SD from factory "+name+" of type "+type+".");
-    }
-
     g4->Activate(true);
-
-    // fg: don't know if this is needed ...
-    Geant4SensitiveDetector* g4sd =  dynamic_cast<Geant4SensitiveDetector*>( g4 ) ;
-    if( g4sd) 
-      g4sd->defineCollection(sd.hitsCollection());
-    // ...but to be save we treat old Geant4SensitiveDetectors as before ...
-
     G4SDManager::GetSDMpointer()->AddNewDetector(g4);
     info.g4SensDets[sens_det] = g4;
   }
@@ -847,8 +803,8 @@ void Geant4Converter::handleProperties(LCDD::Properties& prp)   const {
 
 /// Convert the geometry type SensitiveDetector into the corresponding Geant4 object(s).
 void* Geant4Converter::printSensitive(const TNamed* sens_det, const set<const TGeoVolume*>& /* volumes */) const  {
-  Geant4GeometryInfo& info = data();
-  G4VSensitiveDetector* g4 = info.g4SensDets[sens_det];
+  Geant4GeometryInfo&   info = data();
+  G4VSensitiveDetector* g4   = info.g4SensDets[sens_det];
   ConstVolumeSet& volset = info.sensitives[sens_det];
   SensitiveDetector   sd = Ref_t(sens_det);
   stringstream str;
diff --git a/DDG4/src/Geant4SensitiveDetector.cpp b/DDG4/src/Geant4SensitiveDetector.cpp
index bc411403ae387aba98bcae507ce361e284e73d57..fc669bffb9486f273567f07898d28420619cbdbe 100644
--- a/DDG4/src/Geant4SensitiveDetector.cpp
+++ b/DDG4/src/Geant4SensitiveDetector.cpp
@@ -174,7 +174,7 @@ void Geant4SensitiveDetector::dumpStep(G4Step* st, G4TouchableHistory* /* histor
 
 long long Geant4SensitiveDetector::getVolumeID(G4Step* aStep ){
   
-  Geant4Mapping&  mapping = Geant4Mapping::instance();
+  //Geant4Mapping&  mapping = Geant4Mapping::instance();
   
   Geant4StepHandler step(aStep);
 
diff --git a/DDG4/src/Geant4Setup.cpp b/DDG4/src/Geant4Setup.cpp
index 8928d38c7d07e8eed808eb9f12825350c2a6fedb..6aae7297b07ba262f6eaa35d7a9ee4a780c51cf4 100644
--- a/DDG4/src/Geant4Setup.cpp
+++ b/DDG4/src/Geant4Setup.cpp
@@ -6,88 +6,188 @@
 //  Author     : M.Frank
 //
 //====================================================================
+
 // Framework include files
-#include "DDG4/Factories.h"
-#include "DDG4/Geant4Field.h"
-#include "DDG4/Geant4Converter.h"
-#include "DD4hep/Fields.h"
+#include "DD4hep/LCDD.h"
+#include "DD4hep/Plugins.h"
+#include "DD4hep/Printout.h"
 
+#include "DDG4/Geant4Setup.h"
+#include "DDG4/Geant4Kernel.h"
+#include "DDG4/Geant4GeneratorAction.h"
+#include "DDG4/Geant4RunAction.h"
+#include "DDG4/Geant4EventAction.h"
+#include "DDG4/Geant4TrackingAction.h"
+#include "DDG4/Geant4SteppingAction.h"
+#include "DDG4/Geant4StackingAction.h"
+#include "DDG4/Geant4SensDetAction.h"
+#include "DDG4/Geant4ActionPhase.h"
 
-#include "G4TransportationManager.hh"
-#include "G4MagIntegratorStepper.hh"
-#include "G4Mag_EqRhs.hh"
-#include "G4ChordFinder.hh"
-#include "G4PropagatorInField.hh"
 
-using namespace DD4hep::Simulation;
-using namespace DD4hep::Geometry;
-using namespace std;
-typedef DD4hep::Geometry::LCDD lcdd_t;
+// C/C++ include files
+#include <stdexcept>
 
-struct PropertyMap {
-  const map<string,string>& vals;
-  PropertyMap(const map<string,string>& v) : vals(v) {}
-  string value(const string& key) const;
-  double toDouble(const string& key) const;
-  bool operator[](const string& key) const  { return vals.find(key) != vals.end(); }
-};
+using namespace std;
+using namespace DD4hep;
+using namespace DD4hep::Simulation;
 
-string PropertyMap::value(const string& key) const {
-  lcdd_t::PropertyValues::const_iterator iV = vals.find(key);
-  return iV == vals.end() ? "" : (*iV).second;
+/// Standard constructor
+Geant4SetupFactory<CINT>::Geant4SetupFactory(Geometry::LCDD& lcdd) : m_lcdd(lcdd)  {
 }
 
-double PropertyMap::toDouble(const string& key) const {
-  return _toDouble(value(key));
+/// Default destructor
+Geant4SetupFactory<CINT>::~Geant4SetupFactory()   {
 }
 
-static long setup_fields(lcdd_t& lcdd, const Geant4Converter& /* cnv */, const map<string,string>& vals) {
-  PropertyMap pm(vals);
-  DD4hep::Geometry::OverlayedField fld  = lcdd.field();
-  G4MagIntegratorStepper*  stepper = 0;
-  G4MagneticField*         field = 0;
-  G4FieldManager*          fieldMgr = 0;
-  G4TransportationManager* tr = 0;
-  G4PropagatorInField*     propagator = 0;
-  G4ChordFinder*           chordFinder = 0;  
-
-  lcdd_t::PropertyValues::const_iterator iV;
+/// Create the Geant4 Kernel object
+Geant4Kernel& Geant4SetupFactory<CINT>::kernel()  {
+  static Geant4Kernel* k = new Geant4Kernel(m_lcdd);
+  return *k;
+}
 
-  string eq_typ      = pm.value("equation");
-  string stepper_typ = pm.value("stepper");
-  double value;
+typedef pair<string,string> TypeName;
+static TypeName splitName(const string& type_name)  {
+  size_t idx = type_name.find("/");
+  string typ=type_name, nam=type_name;
+  if ( idx != string::npos )  {
+    typ = type_name.substr(0,idx);
+    nam = type_name.substr(idx+1);
+  }
+  return make_pair(typ,nam);
+}
 
-  field    = new Geant4Field(fld);
-  tr       = G4TransportationManager::GetTransportationManager();
-  fieldMgr = tr->GetFieldManager();
+template <typename TYPE> static inline TYPE* checked_value(TYPE* p)    {
+  if ( p )  {
+    return p;
+  }
+  throw runtime_error(format("Geant4Handle","Attempt to access an invalid object of type:%s!",
+			     typeinfoName(typeid(TYPE)).c_str()));
+}
 
-  fieldMgr->SetFieldChangesEnergy(fld.changesEnergy());
-  fieldMgr->SetDetectorField(field);
+template <typename TYPE> Geant4Handle<TYPE>::Geant4Handle() : value(0) 
+{
+}
 
-  G4Mag_EqRhs* equation = ROOT::Reflex::PluginService::Create<G4Mag_EqRhs*>(eq_typ,field);
-  stepper = ROOT::Reflex::PluginService::Create<G4MagIntegratorStepper*>(stepper_typ,equation);
+template <typename TYPE> Geant4Handle<TYPE>::Geant4Handle(TYPE* typ) : value(typ) 
+{
+}
 
-  iV = vals.find("min_chord_step");
-  value = _toDouble((iV == vals.end()) ? string("1.0e-2 * mm") : (*iV).second);
-  chordFinder  = new G4ChordFinder(field,value,stepper);
-  propagator   = tr->GetPropagatorInField();
-  fieldMgr->SetChordFinder(chordFinder);
+template <typename TYPE> Geant4Handle<TYPE>::Geant4Handle(Geant4Handle<TYPE>& handle)
+: value(0) 
+{
+  value = handle.release();
+}
 
-  if ( pm["delta_chord"] ) {
-    chordFinder->SetDeltaChord(pm.toDouble("delta_chord"));
-  }
-  if ( pm["delta_one_step"] ) {
-    fieldMgr->SetAccuraciesWithDeltaOneStep(pm.toDouble("delta_one_step"));
+template <typename TYPE> Geant4Handle<TYPE>::Geant4Handle(const Geant4Kernel& kernel,const string& type_name)
+: value(0) 
+{
+  TypeName typ = splitName(type_name);
+  Geant4Context* ctxt = kernel.context();
+  Geant4Action* object = PluginService::Create<Geant4Action*>(typ.first,ctxt,typ.second);
+  if ( !object && typ.first == typ.second )  {
+    typ.first = typeinfoName(typeid(TYPE));
+    printout(DEBUG,"Geant4Handle<Geant4Sensitive>",
+	     "Object factory for %s not found. Try out %s",
+	     typ.second.c_str(),typ.first.c_str());
+    object = PluginService::Create<Geant4Action*>(typ.first,ctxt,typ.second);
+    if ( !object )  {
+      size_t idx = typ.first.rfind(':');
+      if ( idx != string::npos ) typ.first = string(typ.first.substr(idx+1));
+      printout(DEBUG,"Geant4Handle<Geant4Sensitive>",
+	       "Try out object factory for %s",typ.first.c_str());
+      object = PluginService::Create<Geant4Action*>(typ.first,ctxt,typ.second);
+    }
   }
-  if ( pm["delta_intersection"] ) {
-    fieldMgr->SetDeltaIntersection(pm.toDouble("delta_intersection"));
+  if ( object )  {
+    TYPE* ptr = dynamic_cast<TYPE*>(object);
+    if ( ptr )  {
+      value = ptr;
+      return;
+    }
+    throw runtime_error(format("Geant4Handle",
+			       "Failed to convert object of type %s to handle of type %s!",
+			       type_name.c_str(),typeinfoName(typeid(TYPE)).c_str()));
   }
-  if ( pm["eps_min"] ) {
-    propagator->SetMinimumEpsilonStep(pm.toDouble("eps_min"));
-  }
-  if ( pm["eps_max"] ) {
-    propagator->SetMaximumEpsilonStep(pm.toDouble("eps_max"));
-  }
-  return 1;
+  throw runtime_error(format("Geant4Handle","Failed to create object of type %s!",type_name.c_str()));
+}
+
+template <typename TYPE> Geant4Handle<TYPE>::~Geant4Handle()  {
+  value = 0;
 }
-DECLARE_GEANT4_SETUP(Geant4FieldSetup,setup_fields)
+
+template <typename TYPE> Property& Geant4Handle<TYPE>::operator[](const string& property_name) const  {
+  PropertyManager& pm = checked_value(value)->properties();
+  return pm[property_name];
+}
+
+template <typename TYPE> Geant4Handle<TYPE>::operator TYPE*() const   {
+  return checked_value(value);
+}
+
+template <typename TYPE> TYPE* Geant4Handle<TYPE>::release()   {
+  TYPE* ptr = checked_value(value);
+  value = 0;
+  return ptr;
+}
+
+template <typename TYPE> TYPE* Geant4Handle<TYPE>::get() const   {
+  return checked_value(value);
+}
+template <typename TYPE> TYPE* Geant4Handle<TYPE>::operator->() const   {
+  return checked_value(value);
+}
+
+
+template <typename TYPE> Geant4Handle<TYPE>& Geant4Handle<TYPE>::operator=(Geant4Handle& handle)  {
+  value = handle.release();
+  return *this;
+}
+
+template <typename TYPE> Geant4Handle<TYPE>& Geant4Handle<TYPE>::operator=(TYPE* typ)   {
+  value = typ;
+  return *this;
+}
+
+namespace DD4hep {  namespace Simulation   {
+
+    template <> Geant4Handle<Geant4Sensitive>::Geant4Handle(const Geant4Kernel& kernel, const string& type_name, const string& detector)  {
+      try  {
+	Geant4Context*       ctxt = kernel.context();
+	TypeName             typ  = splitName(type_name);
+	Geometry::LCDD&      lcdd = kernel.lcdd();
+	Geometry::DetElement det  = lcdd.detector(detector);
+	Geant4Sensitive* object = PluginService::Create<Geant4Sensitive*>(typ.first,ctxt,typ.second,&det,&lcdd);
+	if ( object )  {
+	  value = object;
+	  return;
+	}
+      }
+      catch(const std::exception& e)   {
+	printout(ERROR,"Geant4Handle<Geant4Sensitive>","Exception: %s",e.what());
+      }
+      catch(...)   {
+	printout(ERROR,"Geant4Handle<Geant4Sensitive>","Exception: Unknown exception");
+      }
+      throw runtime_error(format("Geant4Handle<Geant4Sensitive>",
+				 "Failed to create sensitive object of type %s for detector %s!",
+				 type_name.c_str(),detector.c_str()));
+    }
+  }}
+
+template class Geant4Handle<Geant4Action>;
+template class Geant4Handle<Geant4Sensitive>;
+template class Geant4Handle<Geant4ActionPhase>;
+template class Geant4Handle<Geant4GeneratorAction>;
+template class Geant4Handle<Geant4RunAction>;
+template class Geant4Handle<Geant4EventAction>;
+template class Geant4Handle<Geant4TrackingAction>;
+template class Geant4Handle<Geant4SteppingAction>;
+template class Geant4Handle<Geant4StackingAction>;
+
+template class Geant4Handle<Geant4GeneratorActionSequence>;
+template class Geant4Handle<Geant4RunActionSequence>;
+template class Geant4Handle<Geant4EventActionSequence>;
+template class Geant4Handle<Geant4TrackingActionSequence>;
+template class Geant4Handle<Geant4SteppingActionSequence>;
+template class Geant4Handle<Geant4StackingActionSequence>;
+template class Geant4Handle<Geant4SensDetActionSequence>;
diff --git a/DDG4/src/Geant4TrackerCombineSD.cpp b/DDG4/src/Geant4TrackerCombineSD.cpp
index 51c1dbc416dc4a1ce293ff2ed11127c4c4ddfc56..573f1814b65df46c9e05513d6231847b252c74e3 100644
--- a/DDG4/src/Geant4TrackerCombineSD.cpp
+++ b/DDG4/src/Geant4TrackerCombineSD.cpp
@@ -107,8 +107,7 @@ namespace DD4hep {  namespace Simulation {
       }
       return return_code;
     }
-    //    typedef Geant4GenericSD<TrackerCombine>  Geant4TrackerCombine;
-    typedef SimpleG4SDFactory< Geant4GenericSD<TrackerCombine> >  Geant4TrackerCombine;
+    typedef Geant4GenericSD<TrackerCombine>  Geant4TrackerCombine;
 }}    // End namespace DD4hep::Simulation
 
 DECLARE_GEANT4SENSITIVEDETECTOR(Geant4TrackerCombine)
diff --git a/DDG4/src/Geant4TrackerSD.cpp b/DDG4/src/Geant4TrackerSD.cpp
index a0884980871e8dde4b4a43b25fb8abcd22ae3f64..91b0de3ff96648d1c338664ef251e5c03d39f39d 100644
--- a/DDG4/src/Geant4TrackerSD.cpp
+++ b/DDG4/src/Geant4TrackerSD.cpp
@@ -56,8 +56,7 @@ namespace DD4hep {  namespace Simulation {
       collection(0)->insert(hit);
       return hit != 0;
     }
-    //typedef Geant4GenericSD<Tracker> Geant4Tracker;
-     typedef SimpleG4SDFactory< Geant4GenericSD<Tracker> > Geant4Tracker;
+    typedef Geant4GenericSD<Tracker> Geant4Tracker;
   }}    // End namespace DD4hep::Simulation
 
 DECLARE_GEANT4SENSITIVEDETECTOR(Geant4Tracker)
diff --git a/DDG4/src/Geant4VolumeManager.cpp b/DDG4/src/Geant4VolumeManager.cpp
index 57fdb518a3dbe642c23f28e15c1da11b875cac39..53cdbd35daba2412b912c231991e73790a17a748 100644
--- a/DDG4/src/Geant4VolumeManager.cpp
+++ b/DDG4/src/Geant4VolumeManager.cpp
@@ -80,7 +80,7 @@ namespace {
 	}
 	else  {
 	  printout(WARNING,"VolumeManager",
-		   "Strange constellation volume %s is sensitive, but has no readout! sd:%p",
+		   "populate: Strange constellation volume %s is sensitive, but has no readout! sd:%p",
 		   pv.volume().name(), sd.ptr());
 	}
       }
@@ -109,13 +109,13 @@ namespace {
 	  }
 	}
 	if ( m_geo.g4Paths.find(path) != m_geo.g4Paths.end() )  {
-	  cout <<  "Severe error: Duplicated Geant4 path!!!!" << endl;
+	  printout(ERROR,"VolumeManager","populate: Severe error: Duplicated Geant4 path!!!!");
 	}
 	m_geo.g4Paths[path] = code;
 	m_entries.insert(code);
       }
       else   {
-	cout <<  "Severe error: Duplicated Volume entry:" << (void*)code << endl;
+	printout(ERROR,"VolumeManager","populate: Severe error: Duplicated Volume entry: %X",code);
       }
     }
   };