Geant4 Cross Reference |
1 // 1 // 2 // ******************************************* 2 // ******************************************************************** 3 // * License and Disclaimer 3 // * License and Disclaimer * 4 // * 4 // * * 5 // * The Geant4 software is copyright of th 5 // * The Geant4 software is copyright of the Copyright Holders of * 6 // * the Geant4 Collaboration. It is provided 6 // * the Geant4 Collaboration. It is provided under the terms and * 7 // * conditions of the Geant4 Software License 7 // * conditions of the Geant4 Software License, included in the file * 8 // * LICENSE and available at http://cern.ch/ 8 // * LICENSE and available at http://cern.ch/geant4/license . These * 9 // * include a list of copyright holders. 9 // * include a list of copyright holders. * 10 // * 10 // * * 11 // * Neither the authors of this software syst 11 // * Neither the authors of this software system, nor their employing * 12 // * institutes,nor the agencies providing fin 12 // * institutes,nor the agencies providing financial support for this * 13 // * work make any representation or warran 13 // * work make any representation or warranty, express or implied, * 14 // * regarding this software system or assum 14 // * regarding this software system or assume any liability for its * 15 // * use. Please see the license in the file 15 // * use. Please see the license in the file LICENSE and URL above * 16 // * for the full disclaimer and the limitatio 16 // * for the full disclaimer and the limitation of liability. * 17 // * 17 // * * 18 // * This code implementation is the result 18 // * This code implementation is the result of the scientific and * 19 // * technical work of the GEANT4 collaboratio 19 // * technical work of the GEANT4 collaboration. * 20 // * By using, copying, modifying or distri 20 // * By using, copying, modifying or distributing the software (or * 21 // * any work based on the software) you ag 21 // * any work based on the software) you agree to acknowledge its * 22 // * use in resulting scientific publicati 22 // * use in resulting scientific publications, and indicate your * 23 // * acceptance of all terms of the Geant4 Sof 23 // * acceptance of all terms of the Geant4 Software license. * 24 // ******************************************* 24 // ******************************************************************** 25 // 25 // >> 26 // $Id: G4LossTableManager.cc 76333 2013-11-08 14:31:50Z gcosmo $ >> 27 // 26 // ------------------------------------------- 28 // ------------------------------------------------------------------- 27 // 29 // 28 // GEANT4 Class file 30 // GEANT4 Class file 29 // 31 // 30 // 32 // 31 // File name: G4LossTableManager 33 // File name: G4LossTableManager 32 // 34 // 33 // Author: Vladimir Ivanchenko 35 // Author: Vladimir Ivanchenko 34 // 36 // 35 // Creation date: 03.01.2002 37 // Creation date: 03.01.2002 36 // 38 // 37 // Modifications: by V.Ivanchenko << 39 // Modifications: 38 // 40 // >> 41 // 20-01-03 Migrade to cut per region (V.Ivanchenko) >> 42 // 15-02-03 Lambda table can be scaled (V.Ivanchenko) >> 43 // 17-02-03 Fix problem of store/restore tables (V.Ivanchenko) >> 44 // 10-03-03 Add Ion registration (V.Ivanchenko) >> 45 // 25-03-03 Add deregistration (V.Ivanchenko) >> 46 // 02-04-03 Change messenger (V.Ivanchenko) >> 47 // 26-04-03 Fix retrieve tables (V.Ivanchenko) >> 48 // 13-05-03 Add calculation of precise range (V.Ivanchenko) >> 49 // 23-07-03 Add exchange with G4EnergyLossTables (V.Ivanchenko) >> 50 // 05-10-03 Add G4VEmProcesses registration and Verbose command (V.Ivanchenko) >> 51 // 17-10-03 Add SetParameters method (V.Ivanchenko) >> 52 // 23-10-03 Add control on inactive processes (V.Ivanchenko) >> 53 // 04-11-03 Add checks in RetrievePhysicsTable (V.Ivanchenko) >> 54 // 12-11-03 G4EnergyLossSTD -> G4EnergyLossProcess (V.Ivanchenko) >> 55 // 14-01-04 Activate precise range calculation (V.Ivanchenko) >> 56 // 10-03-04 Fix a problem of Precise Range table (V.Ivanchenko) >> 57 // 08-11-04 Migration to new interface of Store/Retrieve tables (V.Ivanchenko) >> 58 // 13-01-04 Fix problem which takes place for inactivate eIoni (V.Ivanchenko) >> 59 // 25-01-04 Fix initialisation problem for ions (V.Ivanchenko) >> 60 // 11-03-05 Shift verbose level by 1 (V.Ivantchenko) >> 61 // 10-01-06 PreciseRange -> CSDARange (V.Ivantchenko) >> 62 // 20-01-06 Introduce G4EmTableType to remove repeating code (VI) >> 63 // 23-03-06 Set flag isIonisation (VI) >> 64 // 10-05-06 Add methods SetMscStepLimitation, FacRange and MscFlag (VI) >> 65 // 22-05-06 Add methods Set/Get bremsTh (VI) >> 66 // 05-06-06 Do not clear loss_table map between runs (VI) >> 67 // 16-01-07 Create new energy loss table for e+,e-,mu+,mu- and >> 68 // left ionisation table for further usage (VI) >> 69 // 12-02-07 Add SetSkin, SetLinearLossLimit (V.Ivanchenko) >> 70 // 18-06-07 Move definition of msc parameters to G4EmProcessOptions (V.Ivanchenko) >> 71 // 21-02-08 Added G4EmSaturation (V.Ivanchenko) >> 72 // 12-04-10 Added PreparePhysicsTables and BuildPhysicsTables entries (V.Ivanchenko) >> 73 // 04-06-13 (V.Ivanchenko) Adaptation for MT mode; new method LocalPhysicsTables; >> 74 // ions expect G4GenericIon are not included in the map of energy loss >> 75 // processes for performnc reasons 39 // 76 // 40 // Class Description: 77 // Class Description: 41 // 78 // 42 // ------------------------------------------- 79 // ------------------------------------------------------------------- 43 // 80 // 44 //....oooOO0OOooo........oooOO0OOooo........oo 81 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo.... 45 //....oooOO0OOooo........oooOO0OOooo........oo 82 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo.... 46 83 47 #include "G4LossTableManager.hh" 84 #include "G4LossTableManager.hh" 48 #include "G4SystemOfUnits.hh" 85 #include "G4SystemOfUnits.hh" 49 << 86 #include "G4EnergyLossMessenger.hh" 50 #include "G4VMultipleScattering.hh" << 51 #include "G4VEmProcess.hh" << 52 << 53 #include "G4EmParameters.hh" << 54 #include "G4EmSaturation.hh" << 55 #include "G4EmConfigurator.hh" << 56 #include "G4ElectronIonPair.hh" << 57 #include "G4NIELCalculator.hh" << 58 #include "G4EmCorrections.hh" << 59 #include "G4LossTableBuilder.hh" << 60 #include "G4VAtomDeexcitation.hh" << 61 #include "G4VSubCutProducer.hh" << 62 << 63 #include "G4PhysicsTable.hh" 87 #include "G4PhysicsTable.hh" 64 #include "G4ParticleDefinition.hh" 88 #include "G4ParticleDefinition.hh" 65 #include "G4MaterialCutsCouple.hh" 89 #include "G4MaterialCutsCouple.hh" 66 #include "G4ProcessManager.hh" 90 #include "G4ProcessManager.hh" 67 #include "G4Electron.hh" 91 #include "G4Electron.hh" 68 #include "G4Proton.hh" 92 #include "G4Proton.hh" >> 93 #include "G4VMultipleScattering.hh" >> 94 #include "G4VEmProcess.hh" 69 #include "G4ProductionCutsTable.hh" 95 #include "G4ProductionCutsTable.hh" 70 #include "G4PhysicsTableHelper.hh" 96 #include "G4PhysicsTableHelper.hh" >> 97 #include "G4EmCorrections.hh" >> 98 #include "G4EmSaturation.hh" >> 99 #include "G4EmConfigurator.hh" >> 100 #include "G4ElectronIonPair.hh" 71 #include "G4EmTableType.hh" 101 #include "G4EmTableType.hh" >> 102 #include "G4LossTableBuilder.hh" >> 103 #include "G4VAtomDeexcitation.hh" 72 #include "G4Region.hh" 104 #include "G4Region.hh" 73 #include "G4PhysicalConstants.hh" 105 #include "G4PhysicalConstants.hh" 74 106 75 #include "G4Gamma.hh" << 107 //G4ThreadLocal G4LossTableManager* G4LossTableManager::theInstance = 0; 76 #include "G4Positron.hh" << 77 #include "G4OpticalPhoton.hh" << 78 #include "G4Neutron.hh" << 79 #include "G4MuonPlus.hh" << 80 #include "G4MuonMinus.hh" << 81 #include "G4GenericIon.hh" << 82 108 83 //....oooOO0OOooo........oooOO0OOooo........oo 109 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 84 110 85 static std::once_flag applyOnce; << 86 G4ThreadLocal G4LossTableManager* G4LossTableM << 87 << 88 G4LossTableManager* G4LossTableManager::Instan 111 G4LossTableManager* G4LossTableManager::Instance() 89 { 112 { 90 if(nullptr == instance) { << 113 /* 91 static G4ThreadLocalSingleton<G4LossTableM << 114 if(!theInstance) { 92 instance = inst.Instance(); << 115 theInstance = new G4LossTableManager; 93 } 116 } 94 return instance; << 117 return theInstance; >> 118 */ >> 119 static G4ThreadLocalSingleton<G4LossTableManager> instance; >> 120 return instance.Instance(); 95 } 121 } 96 122 97 //....oooOO0OOooo........oooOO0OOooo........oo 123 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 98 124 99 G4LossTableManager::~G4LossTableManager() 125 G4LossTableManager::~G4LossTableManager() 100 { 126 { 101 for (auto const & p : loss_vector) { delete << 127 //G4cout << "### G4LossTableManager::~G4LossTableManager()" << G4endl; 102 for (auto const & p : msc_vector) { delete p << 128 for (G4int i=0; i<n_loss; ++i) { 103 for (auto const & p : emp_vector) { delete p << 129 if( loss_vector[i] ) { delete loss_vector[i]; } 104 for (auto const & p : p_vector) { delete p; << 130 } 105 << 131 size_t msc = msc_vector.size(); 106 std::size_t mod = mod_vector.size(); << 132 for (size_t j=0; j<msc; ++j) { 107 std::size_t fmod = fmod_vector.size(); << 133 if( msc_vector[j] ) { delete msc_vector[j]; } 108 for (std::size_t a=0; a<mod; ++a) { << 134 } 109 if( nullptr != mod_vector[a] ) { << 135 size_t emp = emp_vector.size(); 110 for (std::size_t b=0; b<fmod; ++b) { << 136 for (size_t k=0; k<emp; ++k) { 111 if((G4VEmModel*)(fmod_vector[b]) == mo << 137 if( emp_vector[k] ) { delete emp_vector[k]; } 112 fmod_vector[b] = nullptr; << 138 } 113 } << 139 size_t mod = mod_vector.size(); >> 140 size_t fmod = fmod_vector.size(); >> 141 for (size_t a=0; a<mod; ++a) { >> 142 if( mod_vector[a] ) { >> 143 for (size_t b=0; b<fmod; ++b) { >> 144 if((G4VEmModel*)(fmod_vector[b]) == mod_vector[a]) { >> 145 fmod_vector[b] = 0; >> 146 } 114 } 147 } 115 delete mod_vector[a]; 148 delete mod_vector[a]; 116 mod_vector[a] = nullptr; << 117 } 149 } 118 } 150 } 119 for (auto const & p : fmod_vector) { delete << 151 for (size_t b=0; b<fmod; ++b) { 120 << 152 if( fmod_vector[b] ) { delete fmod_vector[b]; } >> 153 } 121 Clear(); 154 Clear(); >> 155 delete theMessenger; 122 delete tableBuilder; 156 delete tableBuilder; 123 delete emCorrections; 157 delete emCorrections; >> 158 delete emSaturation; 124 delete emConfigurator; 159 delete emConfigurator; 125 delete emElectronIonPair; 160 delete emElectronIonPair; 126 delete nielCalculator; << 127 delete atomDeexcitation; 161 delete atomDeexcitation; 128 delete subcutProducer; << 129 } 162 } 130 163 131 //....oooOO0OOooo........oooOO0OOooo........oo 164 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 132 165 133 G4LossTableManager::G4LossTableManager() 166 G4LossTableManager::G4LossTableManager() 134 { 167 { 135 theParameters = G4EmParameters::Instance(); << 168 n_loss = 0; 136 theElectron = G4Electron::Electron(); << 169 run = -1; 137 << 170 startInitialisation = false; 138 // only one thread is the master << 171 all_tables_are_built = false; 139 std::call_once(applyOnce, [this]() { isMaste << 172 currentLoss = 0; 140 verbose = isMaster ? theParameters->Verbose( << 173 currentParticle = 0; 141 << 174 firstParticle = 0; 142 tableBuilder = new G4LossTableBuilder(isMast << 175 lossFluctuationFlag = true; 143 emCorrections = new G4EmCorrections(verbose) << 176 subCutoffFlag = false; 144 << 177 rndmStepFlag = false; 145 std::size_t n = 70; << 178 minSubRange = 0.0; 146 loss_vector.reserve(n); << 179 maxRangeVariation = 1.0; 147 part_vector.reserve(n); << 180 maxFinalStep = 0.0; 148 base_part_vector.reserve(n); << 181 minKinEnergy = 0.1*keV; 149 dedx_vector.reserve(n); << 182 maxKinEnergy = 10.0*TeV; 150 range_vector.reserve(n); << 183 nbinsLambda = 77; 151 inv_range_vector.reserve(n); << 184 nbinsPerDecade = 7; 152 tables_are_built.reserve(n); << 185 maxKinEnergyForMuons = 10.*TeV; 153 isActive.reserve(n); << 186 integral = true; 154 msc_vector.reserve(10); << 187 integralActive = false; 155 emp_vector.reserve(16); << 188 buildCSDARange = false; 156 mod_vector.reserve(150); << 189 minEnergyActive = false; 157 fmod_vector.reserve(60); << 190 maxEnergyActive = false; >> 191 maxEnergyForMuonsActive = false; >> 192 stepFunctionActive = false; >> 193 flagLPM = true; >> 194 splineFlag = true; >> 195 isMaster = false; >> 196 bremsTh = DBL_MAX; >> 197 factorForAngleLimit = 1.0; >> 198 verbose = 1; >> 199 theMessenger = new G4EnergyLossMessenger(); >> 200 theElectron = G4Electron::Electron(); >> 201 theGenericIon= 0; >> 202 tableBuilder = new G4LossTableBuilder(); >> 203 emCorrections= new G4EmCorrections(); >> 204 emSaturation = new G4EmSaturation(); >> 205 emConfigurator = new G4EmConfigurator(verbose); >> 206 emElectronIonPair = new G4ElectronIonPair(); >> 207 tableBuilder->SetSplineFlag(splineFlag); >> 208 atomDeexcitation = 0; 158 } 209 } 159 210 160 //....oooOO0OOooo........oooOO0OOooo........oo 211 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 161 212 162 void G4LossTableManager::Clear() 213 void G4LossTableManager::Clear() 163 { 214 { 164 all_tables_are_built = false; 215 all_tables_are_built = false; 165 currentLoss = nullptr; << 216 currentLoss = 0; 166 currentParticle = nullptr; << 217 currentParticle = 0; 167 if(n_loss) { << 218 if(n_loss) 168 dedx_vector.clear(); << 219 { 169 range_vector.clear(); << 220 dedx_vector.clear(); 170 inv_range_vector.clear(); << 221 range_vector.clear(); 171 loss_map.clear(); << 222 inv_range_vector.clear(); 172 loss_vector.clear(); << 223 loss_map.clear(); 173 part_vector.clear(); << 224 loss_vector.clear(); 174 base_part_vector.clear(); << 225 part_vector.clear(); 175 tables_are_built.clear(); << 226 base_part_vector.clear(); 176 isActive.clear(); << 227 tables_are_built.clear(); 177 n_loss = 0; << 228 isActive.clear(); 178 } << 229 n_loss = 0; >> 230 } 179 } 231 } 180 232 181 //....oooOO0OOooo........oooOO0OOooo........oo 233 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 182 234 183 void G4LossTableManager::Register(G4VEnergyLos 235 void G4LossTableManager::Register(G4VEnergyLossProcess* p) 184 { 236 { 185 if (nullptr == p) { return; } << 237 if(!p) { return; } 186 for (G4int i=0; i<n_loss; ++i) { 238 for (G4int i=0; i<n_loss; ++i) { 187 if(loss_vector[i] == p) { return; } 239 if(loss_vector[i] == p) { return; } 188 } 240 } 189 if(verbose > 1) { 241 if(verbose > 1) { 190 G4cout << "G4LossTableManager::Register G4 242 G4cout << "G4LossTableManager::Register G4VEnergyLossProcess : " 191 << p->GetProcessName() << " idx= " << 243 << p->GetProcessName() << " idx= " << n_loss << G4endl; 192 } 244 } 193 ++n_loss; 245 ++n_loss; 194 loss_vector.push_back(p); 246 loss_vector.push_back(p); 195 part_vector.push_back(nullptr); << 247 part_vector.push_back(0); 196 base_part_vector.push_back(nullptr); << 248 base_part_vector.push_back(0); 197 dedx_vector.push_back(nullptr); << 249 dedx_vector.push_back(0); 198 range_vector.push_back(nullptr); << 250 range_vector.push_back(0); 199 inv_range_vector.push_back(nullptr); << 251 inv_range_vector.push_back(0); 200 tables_are_built.push_back(false); 252 tables_are_built.push_back(false); 201 isActive.push_back(true); 253 isActive.push_back(true); 202 all_tables_are_built = false; 254 all_tables_are_built = false; 203 } << 255 if(!lossFluctuationFlag) { p->SetLossFluctuations(false); } 204 << 256 if(subCutoffFlag) { p->ActivateSubCutoff(true); } 205 //....oooOO0OOooo........oooOO0OOooo........oo << 257 if(rndmStepFlag) { p->SetRandomStep(true); } 206 << 258 if(stepFunctionActive) { p->SetStepFunction(maxRangeVariation, 207 void G4LossTableManager::ResetParameters() << 259 maxFinalStep); } 208 { << 260 if(integralActive) { p->SetIntegral(integral); } 209 // initialisation once per run << 261 if(minEnergyActive) { p->SetMinKinEnergy(minKinEnergy); } 210 if (!resetParam) { return; } << 262 if(maxEnergyActive) { p->SetMaxKinEnergy(maxKinEnergy); } 211 resetParam = false; << 212 startInitialisation = true; << 213 verbose = theParameters->Verbose(); << 214 if(!isMaster) { << 215 verbose = theParameters->WorkerVerbose(); << 216 } else { << 217 if(verbose > 0) { theParameters->Dump(); } << 218 } << 219 << 220 tableBuilder->InitialiseBaseMaterials(); << 221 if (nullptr != nielCalculator) { nielCalcula << 222 << 223 emCorrections->SetVerbose(verbose); << 224 if(nullptr != emConfigurator) { emConfigurat << 225 if(nullptr != emElectronIonPair) { emElectro << 226 if(nullptr != atomDeexcitation) { << 227 atomDeexcitation->SetVerboseLevel(verbose) << 228 atomDeexcitation->InitialiseAtomicDeexcita << 229 } << 230 if (1 < verbose) { << 231 G4cout << "====== G4LossTableManager::Rese << 232 << " Nloss=" << loss_vector.size() << 233 << " run=" << run << " master=" << isMast << 234 << G4endl; << 235 } << 236 } 263 } 237 264 238 //....oooOO0OOooo........oooOO0OOooo........oo 265 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 239 266 240 void G4LossTableManager::DeRegister(G4VEnergyL 267 void G4LossTableManager::DeRegister(G4VEnergyLossProcess* p) 241 { 268 { 242 if (nullptr == p) { return; } << 269 if(!p) { return; } 243 for (G4int i=0; i<n_loss; ++i) { 270 for (G4int i=0; i<n_loss; ++i) { 244 if(loss_vector[i] == p) { << 271 if(loss_vector[i] == p) { loss_vector[i] = 0; } 245 loss_vector[i] = nullptr; << 246 break; << 247 } << 248 } 272 } 249 } 273 } 250 274 251 //....oooOO0OOooo........oooOO0OOooo........oo 275 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 252 276 253 void G4LossTableManager::Register(G4VMultipleS 277 void G4LossTableManager::Register(G4VMultipleScattering* p) 254 { 278 { 255 if (nullptr == p) { return; } << 279 if(!p) { return; } 256 std::size_t n = msc_vector.size(); << 280 G4int n = msc_vector.size(); 257 for (std::size_t i=0; i<n; ++i) { << 281 for (G4int i=0; i<n; ++i) { 258 if(msc_vector[i] == p) { return; } 282 if(msc_vector[i] == p) { return; } 259 } 283 } 260 if(verbose > 1) { 284 if(verbose > 1) { 261 G4cout << "G4LossTableManager::Register G4 285 G4cout << "G4LossTableManager::Register G4VMultipleScattering : " 262 << p->GetProcessName() << " idx= " << 286 << p->GetProcessName() << " idx= " << msc_vector.size() << G4endl; 263 } 287 } 264 msc_vector.push_back(p); 288 msc_vector.push_back(p); 265 } 289 } 266 290 267 //....oooOO0OOooo........oooOO0OOooo........oo 291 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 268 292 269 void G4LossTableManager::DeRegister(G4VMultipl 293 void G4LossTableManager::DeRegister(G4VMultipleScattering* p) 270 { 294 { 271 if (nullptr == p) { return; } << 295 if(!p) { return; } 272 std::size_t msc = msc_vector.size(); << 296 size_t msc = msc_vector.size(); 273 for (std::size_t i=0; i<msc; ++i) { << 297 for (size_t i=0; i<msc; ++i) { 274 if(msc_vector[i] == p) { << 298 if(msc_vector[i] == p) { msc_vector[i] = 0; } 275 msc_vector[i] = nullptr; << 276 break; << 277 } << 278 } 299 } 279 } 300 } 280 301 281 //....oooOO0OOooo........oooOO0OOooo........oo 302 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 282 303 283 void G4LossTableManager::Register(G4VEmProcess 304 void G4LossTableManager::Register(G4VEmProcess* p) 284 { 305 { 285 if (nullptr == p) { return; } << 306 if(!p) { return; } 286 std::size_t n = emp_vector.size(); << 307 G4int n = emp_vector.size(); 287 for (std::size_t i=0; i<n; ++i) { << 308 for (G4int i=0; i<n; ++i) { 288 if(emp_vector[i] == p) { return; } 309 if(emp_vector[i] == p) { return; } 289 } 310 } 290 if(verbose > 1) { 311 if(verbose > 1) { 291 G4cout << "G4LossTableManager::Register G4 312 G4cout << "G4LossTableManager::Register G4VEmProcess : " 292 << p->GetProcessName() << " idx= " << 313 << p->GetProcessName() << " idx= " << emp_vector.size() << G4endl; 293 } 314 } 294 emp_vector.push_back(p); 315 emp_vector.push_back(p); 295 } 316 } 296 317 297 //....oooOO0OOooo........oooOO0OOooo........oo 318 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 298 319 299 void G4LossTableManager::DeRegister(G4VEmProce 320 void G4LossTableManager::DeRegister(G4VEmProcess* p) 300 { 321 { 301 if (nullptr == p) { return; } << 322 if(!p) { return; } 302 std::size_t emp = emp_vector.size(); << 323 size_t emp = emp_vector.size(); 303 for (std::size_t i=0; i<emp; ++i) { << 324 for (size_t i=0; i<emp; ++i) { 304 if(emp_vector[i] == p) { << 325 if(emp_vector[i] == p) { emp_vector[i] = 0; } 305 emp_vector[i] = nullptr; << 306 break; << 307 } << 308 } << 309 } << 310 << 311 //....oooOO0OOooo........oooOO0OOooo........oo << 312 << 313 void G4LossTableManager::Register(G4VProcess* << 314 { << 315 if (nullptr == p) { return; } << 316 std::size_t n = p_vector.size(); << 317 for (std::size_t i=0; i<n; ++i) { << 318 if(p_vector[i] == p) { return; } << 319 } << 320 if(verbose > 1) { << 321 G4cout << "G4LossTableManager::Register G4 << 322 << p->GetProcessName() << " idx= " << 323 } << 324 p_vector.push_back(p); << 325 } << 326 << 327 //....oooOO0OOooo........oooOO0OOooo........oo << 328 << 329 void G4LossTableManager::DeRegister(G4VProcess << 330 { << 331 if (nullptr == p) { return; } << 332 std::size_t emp = p_vector.size(); << 333 for (std::size_t i=0; i<emp; ++i) { << 334 if(p_vector[i] == p) { << 335 p_vector[i] = nullptr; << 336 break; << 337 } << 338 } 326 } 339 } 327 } 340 328 341 //....oooOO0OOooo........oooOO0OOooo........oo 329 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 342 330 343 void G4LossTableManager::Register(G4VEmModel* 331 void G4LossTableManager::Register(G4VEmModel* p) 344 { 332 { 345 mod_vector.push_back(p); 333 mod_vector.push_back(p); 346 if(verbose > 1) { 334 if(verbose > 1) { 347 G4cout << "G4LossTableManager::Register G4 335 G4cout << "G4LossTableManager::Register G4VEmModel : " 348 << p->GetName() << " " << p << " << 336 << p->GetName() << G4endl; 349 } 337 } 350 } 338 } 351 339 352 //....oooOO0OOooo........oooOO0OOooo........oo 340 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 353 341 354 void G4LossTableManager::DeRegister(G4VEmModel 342 void G4LossTableManager::DeRegister(G4VEmModel* p) 355 { 343 { 356 //G4cout << "G4LossTableManager::DeRegister << 344 size_t n = mod_vector.size(); 357 std::size_t n = mod_vector.size(); << 345 for (size_t i=0; i<n; ++i) { 358 for (std::size_t i=0; i<n; ++i) { << 346 if(mod_vector[i] == p) { mod_vector[i] = 0; } 359 if(mod_vector[i] == p) { << 360 mod_vector[i] = nullptr; << 361 break; << 362 } << 363 } 347 } 364 } 348 } 365 349 366 //....oooOO0OOooo........oooOO0OOooo........oo 350 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 367 351 368 void G4LossTableManager::Register(G4VEmFluctua 352 void G4LossTableManager::Register(G4VEmFluctuationModel* p) 369 { 353 { 370 fmod_vector.push_back(p); 354 fmod_vector.push_back(p); 371 if(verbose > 1) { 355 if(verbose > 1) { 372 G4cout << "G4LossTableManager::Register G4 356 G4cout << "G4LossTableManager::Register G4VEmFluctuationModel : " 373 << p->GetName() << " " << fmod_vec << 357 << p->GetName() << G4endl; 374 } 358 } 375 } 359 } 376 360 377 //....oooOO0OOooo........oooOO0OOooo........oo 361 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 378 362 379 void G4LossTableManager::DeRegister(G4VEmFluct 363 void G4LossTableManager::DeRegister(G4VEmFluctuationModel* p) 380 { 364 { 381 std::size_t n = fmod_vector.size(); << 365 size_t n = fmod_vector.size(); 382 for (std::size_t i=0; i<n; ++i) { << 366 for (size_t i=0; i<n; ++i) { 383 if(fmod_vector[i] == p) { fmod_vector[i] = << 367 if(fmod_vector[i] == p) { fmod_vector[i] = 0; } 384 } 368 } 385 } 369 } 386 370 387 //....oooOO0OOooo........oooOO0OOooo........oo 371 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 388 372 389 void G4LossTableManager::RegisterExtraParticle 373 void G4LossTableManager::RegisterExtraParticle( 390 const G4ParticleDefinition* part, 374 const G4ParticleDefinition* part, 391 G4VEnergyLossProcess* p) 375 G4VEnergyLossProcess* p) 392 { 376 { 393 if (nullptr == p || nullptr == part) { retur << 377 if(!p || !part) { return; } 394 for (G4int i=0; i<n_loss; ++i) { 378 for (G4int i=0; i<n_loss; ++i) { 395 if(loss_vector[i] == p) { return; } 379 if(loss_vector[i] == p) { return; } 396 } 380 } 397 if(verbose > 1) { 381 if(verbose > 1) { 398 G4cout << "G4LossTableManager::RegisterExt 382 G4cout << "G4LossTableManager::RegisterExtraParticle " 399 << part->GetParticleName() << " G4 << 383 << part->GetParticleName() << " G4VEnergyLossProcess : " 400 << p->GetProcessName() << " idx= " << 384 << p->GetProcessName() << " idx= " << n_loss << G4endl; 401 } 385 } 402 ++n_loss; 386 ++n_loss; 403 loss_vector.push_back(p); 387 loss_vector.push_back(p); 404 part_vector.push_back(part); 388 part_vector.push_back(part); 405 base_part_vector.push_back(p->BaseParticle() 389 base_part_vector.push_back(p->BaseParticle()); 406 dedx_vector.push_back(nullptr); << 390 dedx_vector.push_back(0); 407 range_vector.push_back(nullptr); << 391 range_vector.push_back(0); 408 inv_range_vector.push_back(nullptr); << 392 inv_range_vector.push_back(0); 409 tables_are_built.push_back(false); 393 tables_are_built.push_back(false); 410 all_tables_are_built = false; 394 all_tables_are_built = false; 411 } 395 } 412 396 413 //....oooOO0OOooo........oooOO0OOooo........oo << 414 << 415 G4VEnergyLossProcess* << 416 G4LossTableManager::GetEnergyLossProcess(const << 417 { << 418 if(aParticle != currentParticle) { << 419 currentParticle = aParticle; << 420 std::map<PD,G4VEnergyLossProcess*,std::les << 421 if ((pos = loss_map.find(aParticle)) != lo << 422 currentLoss = (*pos).second; << 423 } else { << 424 currentLoss = nullptr; << 425 if(0.0 != aParticle->GetPDGCharge() && << 426 (pos = loss_map.find(theGenericIon)) != los << 427 currentLoss = (*pos).second; << 428 } << 429 } << 430 } << 431 return currentLoss; << 432 } << 433 << 434 //....oooOO0OOooo........oooOO0OOooo........oo 397 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 435 398 436 void 399 void 437 G4LossTableManager::PreparePhysicsTable(const 400 G4LossTableManager::PreparePhysicsTable(const G4ParticleDefinition* particle, 438 G4VEne << 401 G4VEnergyLossProcess* p, >> 402 G4bool theMaster) 439 { 403 { 440 if (1 < verbose) { 404 if (1 < verbose) { 441 G4cout << "G4LossTableManager::PreparePhys 405 G4cout << "G4LossTableManager::PreparePhysicsTable for " 442 << particle->GetParticleName() << 406 << particle->GetParticleName() 443 << " and " << p->GetProcessName() < << 407 << " and " << p->GetProcessName() << " run= " << run 444 << " loss_vector " << loss_vector << 408 << " loss_vector " << loss_vector.size() << G4endl; 445 << " run=" << run << " master=" << isMast << 409 } 446 << G4endl; << 410 >> 411 isMaster = theMaster; >> 412 >> 413 if(!startInitialisation) { >> 414 tableBuilder->SetInitialisationFlag(false); >> 415 if (1 < verbose) { >> 416 G4cout << "====== G4LossTableManager::PreparePhysicsTable start =====" >> 417 << G4endl; >> 418 } 447 } 419 } 448 420 449 // start initialisation for the first run 421 // start initialisation for the first run 450 if( -1 == run ) { 422 if( -1 == run ) { 451 if (nullptr != emConfigurator) { emConfigu << 423 emConfigurator->PrepareModels(particle, p); 452 424 453 // initialise particles for given process 425 // initialise particles for given process 454 for (G4int j=0; j<n_loss; ++j) { 426 for (G4int j=0; j<n_loss; ++j) { 455 if (p == loss_vector[j] && nullptr == pa << 427 if (p == loss_vector[j] && !part_vector[j]) { 456 part_vector[j] = particle; << 428 part_vector[j] = particle; 457 if (particle->GetParticleName() == "Ge << 429 if(particle->GetParticleName() == "GenericIon") { 458 theGenericIon = particle; << 430 theGenericIon = particle; 459 } << 431 } 460 } 432 } 461 } 433 } 462 } 434 } 463 ResetParameters(); << 435 startInitialisation = true; 464 } 436 } 465 437 466 //....oooOO0OOooo........oooOO0OOooo........oo 438 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 467 439 468 void 440 void 469 G4LossTableManager::PreparePhysicsTable(const 441 G4LossTableManager::PreparePhysicsTable(const G4ParticleDefinition* particle, 470 G4VEmP << 442 G4VEmProcess* p, G4bool theMaster) 471 { 443 { 472 if (1 < verbose) { 444 if (1 < verbose) { 473 G4cout << "G4LossTableManager::PreparePhys 445 G4cout << "G4LossTableManager::PreparePhysicsTable for " 474 << particle->GetParticleName() << 446 << particle->GetParticleName() 475 << " and " << p->GetProcessName() << 447 << " and " << p->GetProcessName() << G4endl; 476 << " run=" << run << " master=" << isMast << 448 } 477 << G4endl; << 449 isMaster = theMaster; >> 450 >> 451 if(!startInitialisation) { >> 452 tableBuilder->SetInitialisationFlag(false); >> 453 if (1 < verbose) { >> 454 G4cout << "====== G4LossTableManager::PreparePhysicsTable start =====" >> 455 << G4endl; >> 456 } 478 } 457 } 479 458 480 // start initialisation for the first run 459 // start initialisation for the first run 481 if( -1 == run ) { 460 if( -1 == run ) { 482 if (nullptr != emConfigurator) { emConfigu << 461 emConfigurator->PrepareModels(particle, p); 483 } 462 } 484 << 463 startInitialisation = true; 485 ResetParameters(); << 486 } 464 } 487 465 488 //....oooOO0OOooo........oooOO0OOooo........oo 466 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 489 467 490 void 468 void 491 G4LossTableManager::PreparePhysicsTable(const 469 G4LossTableManager::PreparePhysicsTable(const G4ParticleDefinition* particle, 492 G4VMul << 470 G4VMultipleScattering* p, >> 471 G4bool theMaster) 493 { 472 { 494 if (1 < verbose) { 473 if (1 < verbose) { 495 G4cout << "G4LossTableManager::PreparePhys 474 G4cout << "G4LossTableManager::PreparePhysicsTable for " 496 << particle->GetParticleName() << 475 << particle->GetParticleName() 497 << " and " << p->GetProcessName() << 476 << " and " << p->GetProcessName() << G4endl; 498 << " run=" << run << " master=" << isMast << 477 } 499 << G4endl; << 478 >> 479 isMaster = theMaster; >> 480 >> 481 if(!startInitialisation) { >> 482 tableBuilder->SetInitialisationFlag(false); >> 483 if (1 < verbose) { >> 484 G4cout << "====== G4LossTableManager::PreparePhysicsTable start =====" >> 485 << G4endl; >> 486 } 500 } 487 } 501 488 502 // start initialisation for the first run 489 // start initialisation for the first run 503 if ( -1 == run ) { << 490 if( -1 == run ) { 504 if (nullptr != emConfigurator) { emConfigu << 491 emConfigurator->PrepareModels(particle, p); 505 } 492 } 506 << 493 startInitialisation = true; 507 ResetParameters(); << 508 } 494 } 509 495 510 //....oooOO0OOooo........oooOO0OOooo........oo 496 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 511 497 512 void 498 void 513 G4LossTableManager::BuildPhysicsTable(const G4 499 G4LossTableManager::BuildPhysicsTable(const G4ParticleDefinition*) 514 { 500 { 515 if(-1 == run && startInitialisation) { 501 if(-1 == run && startInitialisation) { 516 if (nullptr != emConfigurator) { emConfigu << 502 emConfigurator->Clear(); 517 } 503 } 518 if (startInitialisation) { resetParam = true << 519 } 504 } 520 505 521 //....oooOO0OOooo........oooOO0OOooo........oo 506 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 522 507 523 void G4LossTableManager::LocalPhysicsTables( 508 void G4LossTableManager::LocalPhysicsTables( 524 const G4ParticleDefinition* aParticle, 509 const G4ParticleDefinition* aParticle, 525 G4VEnergyLossProcess* p) 510 G4VEnergyLossProcess* p) 526 { 511 { 527 if (1 < verbose) { << 512 if(1 < verbose) { 528 G4cout << "### G4LossTableManager::LocalPh << 513 G4cout << "### G4LossTableManager::SlavePhysicsTable() for " 529 << aParticle->GetParticleName() << 514 << aParticle->GetParticleName() 530 << " and process " << p->GetProcess << 515 << " and process " << p->GetProcessName() 531 << G4endl; << 516 << G4endl; 532 } 517 } 533 518 534 if(-1 == run && startInitialisation) { 519 if(-1 == run && startInitialisation) { 535 if (nullptr != emConfigurator) { emConfigu << 520 emConfigurator->Clear(); 536 firstParticle = aParticle; 521 firstParticle = aParticle; 537 } 522 } 538 523 539 if (startInitialisation) { << 524 if(startInitialisation) { 540 ++run; 525 ++run; 541 if (1 < verbose) { << 526 if(1 < verbose) { 542 G4cout << "===== G4LossTableManager::Loc << 527 G4cout << "===== G4LossTableManager::SlavePhysicsTable() for run " 543 << run << " =====" << G4endl; << 528 << run << " =====" << G4endl; 544 } 529 } 545 currentParticle = nullptr; << 530 if(atomDeexcitation) { >> 531 atomDeexcitation->InitialiseAtomicDeexcitation(); >> 532 } >> 533 currentParticle = 0; 546 startInitialisation = false; 534 startInitialisation = false; 547 resetParam = true; << 548 for (G4int i=0; i<n_loss; ++i) { 535 for (G4int i=0; i<n_loss; ++i) { 549 if (nullptr != loss_vector[i]) { << 536 if(loss_vector[i]) { 550 tables_are_built[i] = false; << 537 tables_are_built[i] = false; 551 } else { 538 } else { 552 tables_are_built[i] = true; << 539 tables_are_built[i] = true; 553 part_vector[i] = nullptr; << 540 part_vector[i] = 0; 554 } 541 } 555 } 542 } 556 } 543 } 557 544 558 all_tables_are_built= true; 545 all_tables_are_built= true; 559 for (G4int i=0; i<n_loss; ++i) { 546 for (G4int i=0; i<n_loss; ++i) { 560 if(p == loss_vector[i]) { 547 if(p == loss_vector[i]) { 561 tables_are_built[i] = true; 548 tables_are_built[i] = true; 562 isActive[i] = true; 549 isActive[i] = true; >> 550 /* >> 551 const G4ProcessManager* pm = p->GetProcessManager(); >> 552 isActive[i] = false; >> 553 if(pm) { isActive[i] = pm->GetProcessActivation(p); } >> 554 */ 563 part_vector[i] = p->Particle(); 555 part_vector[i] = p->Particle(); 564 base_part_vector[i] = p->BaseParticle(); 556 base_part_vector[i] = p->BaseParticle(); 565 dedx_vector[i] = p->DEDXTable(); 557 dedx_vector[i] = p->DEDXTable(); 566 range_vector[i] = p->RangeTableForLoss() 558 range_vector[i] = p->RangeTableForLoss(); 567 inv_range_vector[i] = p->InverseRangeTab 559 inv_range_vector[i] = p->InverseRangeTable(); 568 if(0 == run && p->IsIonisationProcess()) 560 if(0 == run && p->IsIonisationProcess()) { 569 loss_map[part_vector[i]] = p; << 561 loss_map[part_vector[i]] = loss_vector[i]; 570 } 562 } 571 563 572 if(1 < verbose) { 564 if(1 < verbose) { 573 G4cout << i <<". "<< p->GetProcessNa << 565 G4cout << i <<". "<< p->GetProcessName(); 574 if(part_vector[i]) { << 566 if(part_vector[i]) { 575 G4cout << " for " << part_vector[i << 567 G4cout << " for " << part_vector[i]->GetParticleName(); 576 } << 568 } 577 G4cout << " active= " << isActive[i] << 569 G4cout << " active= " << isActive[i] 578 << " table= " << tables_are_bu << 570 << " table= " << tables_are_built[i] 579 << " isIonisation= " << p->IsI << 571 << " isIonisation= " << p->IsIonisationProcess() 580 << G4endl; << 572 << G4endl; 581 } 573 } 582 break; 574 break; 583 } else if(!tables_are_built[i]) { 575 } else if(!tables_are_built[i]) { 584 all_tables_are_built = false; 576 all_tables_are_built = false; 585 } 577 } 586 } 578 } 587 579 >> 580 // Set run time parameters >> 581 SetParameters(aParticle, p); >> 582 588 if(1 < verbose) { 583 if(1 < verbose) { 589 G4cout << "### G4LossTableManager::LocalPh << 584 G4cout << "### G4LossTableManager::SlavePhysicsTable end" 590 << G4endl; << 585 << G4endl; 591 } 586 } 592 if(all_tables_are_built) { 587 if(all_tables_are_built) { 593 if(1 < verbose) { 588 if(1 < verbose) { 594 G4cout << "%%%%% All dEdx and Range tabl 589 G4cout << "%%%%% All dEdx and Range tables for worker are ready for run " 595 << run << " %%%%%" << G4endl; << 590 << run << " %%%%%" << G4endl; 596 } 591 } 597 } 592 } 598 } 593 } 599 594 600 //....oooOO0OOooo........oooOO0OOooo........oo 595 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 601 596 602 void G4LossTableManager::BuildPhysicsTable( 597 void G4LossTableManager::BuildPhysicsTable( 603 const G4ParticleDefinition* aParticle, 598 const G4ParticleDefinition* aParticle, 604 G4VEnergyLossProcess* p) 599 G4VEnergyLossProcess* p) 605 { 600 { 606 if(1 < verbose) { 601 if(1 < verbose) { 607 G4cout << "### G4LossTableManager::BuildPh 602 G4cout << "### G4LossTableManager::BuildPhysicsTable() for " 608 << aParticle->GetParticleName() 603 << aParticle->GetParticleName() 609 << " and process " << p->GetProcess << 604 << " and process " << p->GetProcessName() << G4endl; 610 } 605 } 611 // clear configurator 606 // clear configurator 612 if(-1 == run && startInitialisation) { 607 if(-1 == run && startInitialisation) { 613 if( nullptr != emConfigurator) { emConfigu << 608 emConfigurator->Clear(); 614 firstParticle = aParticle; 609 firstParticle = aParticle; 615 } 610 } 616 if(startInitialisation) { 611 if(startInitialisation) { 617 ++run; 612 ++run; 618 resetParam = true; << 619 startInitialisation = false; << 620 if(1 < verbose) { 613 if(1 < verbose) { 621 G4cout << "===== G4LossTableManager::Bui 614 G4cout << "===== G4LossTableManager::BuildPhysicsTable() for run " 622 << run << " ===== " << atomDeexci << 615 << run << " =====" << G4endl; >> 616 } >> 617 if(atomDeexcitation) { >> 618 atomDeexcitation->InitialiseAtomicDeexcitation(); 623 } 619 } 624 currentParticle = nullptr; << 620 currentParticle = 0; 625 all_tables_are_built = false; << 621 startInitialisation = false; >> 622 all_tables_are_built= true; >> 623 } >> 624 >> 625 // initialisation before any table is built >> 626 if ( aParticle == firstParticle ) { 626 627 >> 628 if(1 < verbose) { >> 629 G4cout << "### G4LossTableManager start initilisation for first particle " >> 630 << firstParticle->GetParticleName() >> 631 << G4endl; >> 632 } 627 for (G4int i=0; i<n_loss; ++i) { 633 for (G4int i=0; i<n_loss; ++i) { 628 G4VEnergyLossProcess* el = loss_vector[i 634 G4VEnergyLossProcess* el = loss_vector[i]; 629 635 630 if(nullptr != el) { << 636 if(el) { 631 isActive[i] = true; 637 isActive[i] = true; 632 part_vector[i] = el->Particle(); << 638 /* 633 base_part_vector[i] = el->BaseParticle << 639 const G4ProcessManager* pm = el->GetProcessManager(); 634 tables_are_built[i] = false; << 640 isActive[i] = false; 635 if(1 < verbose) { << 641 if(pm) { isActive[i] = pm->GetProcessActivation(el); } 636 G4cout << i <<". "<< el->GetProces << 642 */ >> 643 base_part_vector[i] = el->BaseParticle(); >> 644 tables_are_built[i] = false; >> 645 all_tables_are_built= false; >> 646 if(!isActive[i]) { >> 647 el->SetIonisation(false); >> 648 tables_are_built[i] = true; >> 649 } >> 650 >> 651 if(1 < verbose) { >> 652 G4cout << i <<". "<< el->GetProcessName(); 637 if(el->Particle()) { 653 if(el->Particle()) { 638 G4cout << " for " << el->Particl << 654 G4cout << " for " << el->Particle()->GetParticleName(); 639 } << 655 } 640 G4cout << " active= " << isActive[i << 656 G4cout << " active= " << isActive[i] 641 << " table= " << tables_are_ 657 << " table= " << tables_are_built[i] 642 << " isIonisation= " << el-> << 658 << " isIonisation= " << el->IsIonisationProcess(); 643 if(base_part_vector[i]) { << 659 if(base_part_vector[i]) { 644 G4cout << " base particle " << 660 G4cout << " base particle " 645 << base_part_vector[i]->Get << 661 << base_part_vector[i]->GetParticleName(); 646 } << 662 } 647 G4cout << G4endl; << 663 G4cout << G4endl; 648 } << 664 } 649 } else { 665 } else { 650 tables_are_built[i] = true; 666 tables_are_built[i] = true; 651 part_vector[i] = nullptr; << 667 part_vector[i] = 0; 652 isActive[i] = false; << 668 isActive[i] = false; 653 } 669 } 654 } 670 } 655 } 671 } 656 672 657 if (all_tables_are_built) { << 673 // Set run time parameters 658 theParameters->SetIsPrintedFlag(true); << 674 SetParameters(aParticle, p); 659 return; << 675 660 } << 676 if (all_tables_are_built) { return; } 661 677 662 // Build tables for given particle 678 // Build tables for given particle 663 all_tables_are_built = true; 679 all_tables_are_built = true; 664 680 665 for(G4int i=0; i<n_loss; ++i) { 681 for(G4int i=0; i<n_loss; ++i) { 666 if(p == loss_vector[i] && !tables_are_buil << 682 if(p == loss_vector[i] && !tables_are_built[i] && !base_part_vector[i]) { 667 const G4ParticleDefinition* curr_part = 683 const G4ParticleDefinition* curr_part = part_vector[i]; 668 if(1 < verbose) { 684 if(1 < verbose) { 669 G4cout << "### Build Table for " << p- 685 G4cout << "### Build Table for " << p->GetProcessName() 670 << " and " << curr_part->GetPar << 686 << " and " << curr_part->GetParticleName() << G4endl; 671 << " " << tables_are_built[i] << 672 << G4endl; << 673 } 687 } 674 G4VEnergyLossProcess* curr_proc = BuildT 688 G4VEnergyLossProcess* curr_proc = BuildTables(curr_part); 675 if(curr_proc) { << 689 if(curr_proc) { CopyTables(curr_part, curr_proc); } 676 CopyTables(curr_part, curr_proc); << 677 if(p == curr_proc && 0 == run && p->Is << 678 loss_map[aParticle] = p; << 679 //G4cout << "G4LossTableManager::Bui << 680 // << aParticle->GetParticleName << 681 // << " added to map " << p << 682 } << 683 } << 684 } 690 } 685 if ( !tables_are_built[i] ) { all_tables_a 691 if ( !tables_are_built[i] ) { all_tables_are_built = false; } 686 } 692 } >> 693 if(0 == run && p->IsIonisationProcess()) { loss_map[aParticle] = p; } >> 694 687 if(1 < verbose) { 695 if(1 < verbose) { 688 G4cout << "### G4LossTableManager::BuildPh 696 G4cout << "### G4LossTableManager::BuildPhysicsTable end: " 689 << "all_tables_are_built= " << all_ << 697 << "all_tables_are_built= " << all_tables_are_built 690 << aParticle->GetParticleName() << << 698 << G4endl; >> 699 } >> 700 if(all_tables_are_built) { >> 701 if(1 < verbose) { >> 702 G4cout << "%%%%% All dEdx and Range tables are built for master run= " >> 703 << run << " %%%%%" << G4endl; >> 704 } 691 } 705 } 692 } 706 } 693 707 694 //....oooOO0OOooo........oooOO0OOooo........oo 708 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 695 709 696 void G4LossTableManager::CopyTables(const G4Pa 710 void G4LossTableManager::CopyTables(const G4ParticleDefinition* part, 697 G4VEnergyL << 711 G4VEnergyLossProcess* base_proc) 698 { 712 { 699 for (G4int j=0; j<n_loss; ++j) { 713 for (G4int j=0; j<n_loss; ++j) { 700 714 701 G4VEnergyLossProcess* proc = loss_vector[j 715 G4VEnergyLossProcess* proc = loss_vector[j]; 702 716 703 if (!tables_are_built[j] && part == base_p 717 if (!tables_are_built[j] && part == base_part_vector[j]) { 704 tables_are_built[j] = true; 718 tables_are_built[j] = true; 705 // for base particle approach only ionis << 719 proc->SetDEDXTable(base_proc->DEDXTable(),fRestricted); 706 proc->SetDEDXTable(base_proc->Ionisation << 720 proc->SetDEDXTable(base_proc->DEDXTableForSubsec(),fSubRestricted); 707 proc->SetDEDXTable(base_proc->DEDXunRest 721 proc->SetDEDXTable(base_proc->DEDXunRestrictedTable(),fTotal); 708 proc->SetCSDARangeTable(base_proc->CSDAR 722 proc->SetCSDARangeTable(base_proc->CSDARangeTable()); 709 proc->SetRangeTableForLoss(base_proc->Ra 723 proc->SetRangeTableForLoss(base_proc->RangeTableForLoss()); 710 proc->SetInverseRangeTable(base_proc->In 724 proc->SetInverseRangeTable(base_proc->InverseRangeTable()); 711 proc->SetLambdaTable(base_proc->LambdaTa 725 proc->SetLambdaTable(base_proc->LambdaTable()); >> 726 proc->SetSubLambdaTable(base_proc->SubLambdaTable()); >> 727 proc->SetIonisation(base_proc->IsIonisationProcess()); 712 if(proc->IsIonisationProcess()) { 728 if(proc->IsIonisationProcess()) { 713 range_vector[j] = base_proc->RangeTabl << 729 range_vector[j] = base_proc->RangeTableForLoss(); 714 inv_range_vector[j] = base_proc->Inver << 730 inv_range_vector[j] = base_proc->InverseRangeTable(); 715 loss_map[part_vector[j]] = proc; << 731 loss_map[part_vector[j]] = proc; 716 //G4cout << "G4LossTableManager::CopyT << 717 // << part_vector[j]->GetParticl << 718 // << " added to map " << proc < << 719 } 732 } 720 if (1 < verbose) { 733 if (1 < verbose) { 721 G4cout << " CopyTables for " << pro << 734 G4cout << "For " << proc->GetProcessName() 722 << " for " << part_vector[j]-> 735 << " for " << part_vector[j]->GetParticleName() 723 << " base_part= " << part->Get 736 << " base_part= " << part->GetParticleName() 724 << " tables are assigned" << 737 << " tables are assigned " 725 << G4endl; 738 << G4endl; 726 } 739 } 727 } 740 } >> 741 >> 742 if (theElectron == part && theElectron == proc->SecondaryParticle() ) { >> 743 proc->SetSecondaryRangeTable(base_proc->RangeTableForLoss()); >> 744 } 728 } 745 } 729 } 746 } 730 747 731 //....oooOO0OOooo........oooOO0OOooo........oo 748 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 732 749 733 G4VEnergyLossProcess* G4LossTableManager::Buil 750 G4VEnergyLossProcess* G4LossTableManager::BuildTables( 734 const G4ParticleDefiniti 751 const G4ParticleDefinition* aParticle) 735 { 752 { 736 if(1 < verbose) { 753 if(1 < verbose) { 737 G4cout << " G4LossTableManager::BuildTab << 754 G4cout << "G4LossTableManager::BuildTables() for " 738 << aParticle->GetParticleName() << 755 << aParticle->GetParticleName() << G4endl; 739 } 756 } 740 757 741 std::vector<G4PhysicsTable*> t_list; 758 std::vector<G4PhysicsTable*> t_list; 742 std::vector<G4VEnergyLossProcess*> loss_list 759 std::vector<G4VEnergyLossProcess*> loss_list; 743 std::vector<G4bool> build_flags; << 760 loss_list.clear(); 744 G4VEnergyLossProcess* em = nullptr; << 761 G4VEnergyLossProcess* em = 0; 745 G4VEnergyLossProcess* p = nullptr; << 762 G4VEnergyLossProcess* p = 0; 746 G4int iem = 0; 763 G4int iem = 0; 747 G4PhysicsTable* dedx = nullptr; << 764 G4PhysicsTable* dedx = 0; 748 G4int i; 765 G4int i; 749 766 750 G4ProcessVector* pvec = << 751 aParticle->GetProcessManager()->GetProcess << 752 G4int nvec = (G4int)pvec->size(); << 753 << 754 for (i=0; i<n_loss; ++i) { 767 for (i=0; i<n_loss; ++i) { 755 p = loss_vector[i]; 768 p = loss_vector[i]; 756 if (nullptr != p) { << 769 if (p && aParticle == part_vector[i] && !tables_are_built[i]) { 757 G4bool yes = (aParticle == part_vector[i << 770 if ((p->IsIonisationProcess() && isActive[i]) || !em) { 758 << 771 em = p; 759 // possible case of process sharing betw << 772 iem= i; 760 if(!yes) { << 761 auto ptr = static_cast<G4VProcess*>(p) << 762 for(G4int j=0; j<nvec; ++j) { << 763 //G4cout << "j= " << j << " " << (*p << 764 if(ptr == (*pvec)[j]) { << 765 yes = true; << 766 break; << 767 } << 768 } << 769 } << 770 // process belong to this particle << 771 if(yes && isActive[i]) { << 772 if (p->IsIonisationProcess() || !em) { << 773 em = p; << 774 iem= i; << 775 } << 776 // tables may be shared between partic << 777 G4bool val = false; << 778 if (!tables_are_built[i]) { << 779 val = true; << 780 dedx = p->BuildDEDXTable(fRestricted << 781 //G4cout << "===Build DEDX table for << 782 // << " idx= " << i << " dedx:" << d << 783 p->SetDEDXTable(dedx,fRestricted); << 784 tables_are_built[i] = true; << 785 } else { << 786 dedx = p->DEDXTable(); << 787 } << 788 t_list.push_back(dedx); << 789 loss_list.push_back(p); << 790 build_flags.push_back(val); << 791 } 773 } >> 774 dedx = p->BuildDEDXTable(fRestricted); >> 775 //G4cout << "Build DEDX table for " << aParticle->GetParticleName() >> 776 // << " " << dedx << " " << dedx->length() << G4endl; >> 777 p->SetDEDXTable(dedx,fRestricted); >> 778 t_list.push_back(dedx); >> 779 loss_list.push_back(p); >> 780 tables_are_built[i] = true; 792 } 781 } 793 } 782 } 794 783 795 G4int n_dedx = (G4int)t_list.size(); << 784 G4int n_dedx = t_list.size(); 796 if (0 == n_dedx || !em) { 785 if (0 == n_dedx || !em) { 797 G4cout << "G4LossTableManager WARNING: no 786 G4cout << "G4LossTableManager WARNING: no DEDX processes for " 798 << aParticle->GetParticleName() << << 787 << aParticle->GetParticleName() << G4endl; 799 return nullptr; << 788 return 0; 800 } 789 } 801 G4int nSubRegions = em->NumberOfSubCutoffReg 790 G4int nSubRegions = em->NumberOfSubCutoffRegions(); 802 791 803 if (1 < verbose) { 792 if (1 < verbose) { 804 G4cout << " Start to build the sum of << 793 G4cout << "G4LossTableManager::BuildTables() start to build range tables" >> 794 << " and the sum of " << n_dedx << " processes" 805 << " iem= " << iem << " em= " << em 795 << " iem= " << iem << " em= " << em->GetProcessName() 806 << " buildCSDARange= " << theParame << 796 << " buildCSDARange= " << buildCSDARange 807 << " nSubRegions= " << nSubRegions; << 797 << " nSubRegions= " << nSubRegions 808 if(subcutProducer) { << 798 << G4endl; 809 G4cout << " SubCutProducer " << subcutPr << 810 } << 811 G4cout << G4endl; << 812 } 799 } 813 // do not build tables if producer class is << 814 if(subcutProducer) { nSubRegions = 0; } << 815 800 816 dedx = em->DEDXTable(); << 801 dedx = em->DEDXTable(); 817 em->SetDEDXTable(dedx, fIsIonisation); << 802 em->SetIonisation(true); 818 803 819 if (1 < n_dedx) { 804 if (1 < n_dedx) { 820 dedx = nullptr; << 805 em->SetDEDXTable(dedx, fIsIonisation); >> 806 dedx = 0; 821 dedx = G4PhysicsTableHelper::PreparePhysic 807 dedx = G4PhysicsTableHelper::PreparePhysicsTable(dedx); 822 tableBuilder->BuildDEDXTable(dedx, t_list) 808 tableBuilder->BuildDEDXTable(dedx, t_list); 823 em->SetDEDXTable(dedx, fRestricted); 809 em->SetDEDXTable(dedx, fRestricted); 824 } 810 } 825 << 811 /* >> 812 if(2==run && "e-" == aParticle->GetParticleName()) { >> 813 G4cout << "G4LossTableManager::BuildTables for e- " << dedx << G4endl; >> 814 G4cout << (*dedx) << G4endl; >> 815 G4cout << "%%%%% Instance ID= " << (*dedx)[0]->GetInstanceID() << G4endl; >> 816 G4cout << "%%%%% LastValue= " << (*dedx)[0]->GetLastValue() << G4endl; >> 817 G4cout << "%%%%% 1.2 " << (*(dedx))[0]->Value(1.2) << G4endl; >> 818 } >> 819 */ 826 dedx_vector[iem] = dedx; 820 dedx_vector[iem] = dedx; 827 821 828 G4PhysicsTable* range = em->RangeTableForLos 822 G4PhysicsTable* range = em->RangeTableForLoss(); 829 if(!range) range = G4PhysicsTableHelper::Pr 823 if(!range) range = G4PhysicsTableHelper::PreparePhysicsTable(range); 830 range_vector[iem] = range; 824 range_vector[iem] = range; 831 825 832 G4PhysicsTable* invrange = em->InverseRangeT 826 G4PhysicsTable* invrange = em->InverseRangeTable(); 833 if(!invrange) invrange = G4PhysicsTableHelpe 827 if(!invrange) invrange = G4PhysicsTableHelper::PreparePhysicsTable(invrange); 834 inv_range_vector[iem] = invrange; 828 inv_range_vector[iem] = invrange; 835 829 836 tableBuilder->BuildRangeTable(dedx, range); << 830 tableBuilder->BuildRangeTable(dedx, range, true); 837 tableBuilder->BuildInverseRangeTable(range, << 831 tableBuilder->BuildInverseRangeTable(range, invrange, true); >> 832 >> 833 // if(1<verbose) G4cout << *dedx << G4endl; 838 834 839 em->SetRangeTableForLoss(range); 835 em->SetRangeTableForLoss(range); 840 em->SetInverseRangeTable(invrange); 836 em->SetInverseRangeTable(invrange); 841 837 >> 838 // if(1<verbose) G4cout << *range << G4endl; >> 839 >> 840 std::vector<G4PhysicsTable*> listSub; 842 std::vector<G4PhysicsTable*> listCSDA; 841 std::vector<G4PhysicsTable*> listCSDA; 843 842 844 for (i=0; i<n_dedx; ++i) { 843 for (i=0; i<n_dedx; ++i) { 845 p = loss_list[i]; 844 p = loss_list[i]; 846 if(build_flags[i]) { << 845 if(p != em) { p->SetIonisation(false); } 847 p->SetLambdaTable(p->BuildLambdaTable(fR << 846 p->SetLambdaTable(p->BuildLambdaTable(fRestricted)); >> 847 if (0 < nSubRegions) { >> 848 dedx = p->BuildDEDXTable(fSubRestricted); >> 849 p->SetDEDXTable(dedx,fSubRestricted); >> 850 listSub.push_back(dedx); >> 851 p->SetSubLambdaTable(p->BuildLambdaTable(fSubRestricted)); >> 852 if(p != em) { em->AddCollaborativeProcess(p); } 848 } 853 } 849 if(theParameters->BuildCSDARange()) { << 854 if(buildCSDARange) { 850 dedx = p->BuildDEDXTable(fTotal); 855 dedx = p->BuildDEDXTable(fTotal); 851 p->SetDEDXTable(dedx,fTotal); 856 p->SetDEDXTable(dedx,fTotal); 852 listCSDA.push_back(dedx); 857 listCSDA.push_back(dedx); 853 } 858 } 854 } 859 } 855 860 856 if(theParameters->BuildCSDARange()) { << 861 if (0 < nSubRegions) { >> 862 G4PhysicsTable* dedxSub = em->IonisationTableForSubsec(); >> 863 if (1 < listSub.size()) { >> 864 em->SetDEDXTable(dedxSub, fIsSubIonisation); >> 865 dedxSub = 0; >> 866 dedxSub = G4PhysicsTableHelper::PreparePhysicsTable(dedxSub); >> 867 tableBuilder->BuildDEDXTable(dedxSub, listSub); >> 868 em->SetDEDXTable(dedxSub, fSubRestricted); >> 869 } >> 870 } >> 871 if(buildCSDARange) { 857 G4PhysicsTable* dedxCSDA = em->DEDXunRestr 872 G4PhysicsTable* dedxCSDA = em->DEDXunRestrictedTable(); 858 if (1 < n_dedx) { 873 if (1 < n_dedx) { 859 dedxCSDA = G4PhysicsTableHelper::Prepare << 874 dedxCSDA = 0; >> 875 dedxCSDA = G4PhysicsTableHelper::PreparePhysicsTable(dedxCSDA); 860 tableBuilder->BuildDEDXTable(dedxCSDA, l 876 tableBuilder->BuildDEDXTable(dedxCSDA, listCSDA); 861 em->SetDEDXTable(dedxCSDA,fTotal); 877 em->SetDEDXTable(dedxCSDA,fTotal); 862 } 878 } 863 G4PhysicsTable* rCSDA = em->CSDARangeTable 879 G4PhysicsTable* rCSDA = em->CSDARangeTable(); 864 if(!rCSDA) { rCSDA = G4PhysicsTableHelper: 880 if(!rCSDA) { rCSDA = G4PhysicsTableHelper::PreparePhysicsTable(rCSDA); } 865 tableBuilder->BuildRangeTable(dedxCSDA, rC << 881 tableBuilder->BuildRangeTable(dedxCSDA, rCSDA, true); 866 em->SetCSDARangeTable(rCSDA); 882 em->SetCSDARangeTable(rCSDA); 867 } 883 } 868 884 869 if (1 < verbose) { 885 if (1 < verbose) { 870 G4cout << "G4LossTableManager::BuildTables 886 G4cout << "G4LossTableManager::BuildTables: Tables are built for " 871 << aParticle->GetParticleName() 887 << aParticle->GetParticleName() 872 << "; ionisation process: " << em-> << 888 << "; ionisation process: " << em->GetProcessName() 873 << " " << em << 874 << G4endl; 889 << G4endl; 875 } 890 } 876 return em; 891 return em; 877 } 892 } 878 893 879 //....oooOO0OOooo........oooOO0OOooo........oo 894 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 880 895 >> 896 G4EnergyLossMessenger* G4LossTableManager::GetMessenger() >> 897 { >> 898 return theMessenger; >> 899 } >> 900 >> 901 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... >> 902 881 void G4LossTableManager::ParticleHaveNoLoss( 903 void G4LossTableManager::ParticleHaveNoLoss( 882 const G4ParticleDefinition* aParticle) 904 const G4ParticleDefinition* aParticle) 883 { 905 { 884 G4ExceptionDescription ed; 906 G4ExceptionDescription ed; 885 ed << "Energy loss process not found for " < 907 ed << "Energy loss process not found for " << aParticle->GetParticleName() 886 << " !"; 908 << " !"; 887 G4Exception("G4LossTableManager::ParticleHav 909 G4Exception("G4LossTableManager::ParticleHaveNoLoss", "em0001", 888 FatalException, ed); << 910 FatalException, ed); >> 911 >> 912 } >> 913 >> 914 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... >> 915 >> 916 G4bool G4LossTableManager::BuildCSDARange() const >> 917 { >> 918 return buildCSDARange; >> 919 } >> 920 >> 921 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... >> 922 >> 923 void G4LossTableManager::SetLossFluctuations(G4bool val) >> 924 { >> 925 lossFluctuationFlag = val; >> 926 for(G4int i=0; i<n_loss; ++i) { >> 927 if(loss_vector[i]) { loss_vector[i]->SetLossFluctuations(val); } >> 928 } >> 929 } >> 930 >> 931 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... >> 932 >> 933 void G4LossTableManager::SetSubCutoff(G4bool val, const G4Region* r) >> 934 { >> 935 subCutoffFlag = val; >> 936 for(G4int i=0; i<n_loss; ++i) { >> 937 if(loss_vector[i]) { loss_vector[i]->ActivateSubCutoff(val, r); } >> 938 } >> 939 } >> 940 >> 941 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... >> 942 >> 943 void G4LossTableManager::SetIntegral(G4bool val) >> 944 { >> 945 integral = val; >> 946 integralActive = true; >> 947 for(G4int i=0; i<n_loss; ++i) { >> 948 if(loss_vector[i]) { loss_vector[i]->SetIntegral(val); } >> 949 } >> 950 size_t emp = emp_vector.size(); >> 951 for (size_t k=0; k<emp; ++k) { >> 952 if(emp_vector[k]) { emp_vector[k]->SetIntegral(val); } >> 953 } >> 954 } >> 955 >> 956 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... >> 957 >> 958 void G4LossTableManager::SetMinSubRange(G4double val) >> 959 { >> 960 minSubRange = val; >> 961 for(G4int i=0; i<n_loss; ++i) { >> 962 if(loss_vector[i]) { loss_vector[i]->SetMinSubRange(val); } >> 963 } >> 964 } >> 965 >> 966 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... >> 967 >> 968 void G4LossTableManager::SetRandomStep(G4bool val) >> 969 { >> 970 rndmStepFlag = val; >> 971 for(G4int i=0; i<n_loss; ++i) { >> 972 if(loss_vector[i]) { loss_vector[i]->SetRandomStep(val); } >> 973 } >> 974 } >> 975 >> 976 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... >> 977 >> 978 void G4LossTableManager::SetMinEnergy(G4double val) >> 979 { >> 980 minEnergyActive = true; >> 981 minKinEnergy = val; >> 982 for(G4int i=0; i<n_loss; ++i) { >> 983 if(loss_vector[i]) { loss_vector[i]->SetMinKinEnergy(val); } >> 984 } >> 985 size_t emp = emp_vector.size(); >> 986 for (size_t k=0; k<emp; ++k) { >> 987 if(emp_vector[k]) { emp_vector[k]->SetMinKinEnergy(val); } >> 988 } >> 989 } >> 990 >> 991 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... >> 992 >> 993 void G4LossTableManager::SetMaxEnergy(G4double val) >> 994 { >> 995 maxEnergyActive = true; >> 996 maxKinEnergy = val; >> 997 for(G4int i=0; i<n_loss; ++i) { >> 998 if(loss_vector[i]) { loss_vector[i]->SetMaxKinEnergy(val); } >> 999 } >> 1000 size_t emp = emp_vector.size(); >> 1001 for (size_t k=0; k<emp; ++k) { >> 1002 if(emp_vector[k]) { emp_vector[k]->SetMaxKinEnergy(val); } >> 1003 } >> 1004 } >> 1005 >> 1006 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... >> 1007 >> 1008 void G4LossTableManager::SetMaxEnergyForCSDARange(G4double val) >> 1009 { >> 1010 for(G4int i=0; i<n_loss; ++i) { >> 1011 if(loss_vector[i]) { loss_vector[i]->SetMaxKinEnergyForCSDARange(val); } >> 1012 } >> 1013 } >> 1014 >> 1015 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... >> 1016 >> 1017 void G4LossTableManager::SetMaxEnergyForMuons(G4double val) >> 1018 { >> 1019 maxEnergyForMuonsActive = true; >> 1020 maxKinEnergyForMuons = val; >> 1021 } >> 1022 >> 1023 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... >> 1024 >> 1025 void G4LossTableManager::SetDEDXBinning(G4int val) >> 1026 { >> 1027 for(G4int i=0; i<n_loss; ++i) { >> 1028 if(loss_vector[i]) { loss_vector[i]->SetDEDXBinning(val); } >> 1029 } >> 1030 } >> 1031 >> 1032 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... >> 1033 >> 1034 void G4LossTableManager::SetDEDXBinningForCSDARange(G4int val) >> 1035 { >> 1036 for(G4int i=0; i<n_loss; ++i) { >> 1037 if(loss_vector[i]) { loss_vector[i]->SetDEDXBinningForCSDARange(val); } >> 1038 } >> 1039 } >> 1040 >> 1041 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... >> 1042 >> 1043 void G4LossTableManager::SetLambdaBinning(G4int val) >> 1044 { >> 1045 G4int n = val/G4int(std::log10(maxKinEnergy/minKinEnergy) + 0.5); >> 1046 if(n < 5) { >> 1047 G4cout << "G4LossTableManager::SetLambdaBinning WARNING " >> 1048 << "too small number of bins " << val << " ignored" >> 1049 << G4endl; >> 1050 return; >> 1051 } >> 1052 nbinsLambda = val; >> 1053 nbinsPerDecade = n; >> 1054 size_t emp = emp_vector.size(); >> 1055 for (size_t k=0; k<emp; ++k) { >> 1056 if(emp_vector[k]) { emp_vector[k]->SetLambdaBinning(val); } >> 1057 } >> 1058 } >> 1059 >> 1060 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... >> 1061 >> 1062 G4int G4LossTableManager::GetNumberOfBinsPerDecade() const >> 1063 { >> 1064 return nbinsPerDecade; 889 } 1065 } 890 1066 891 //....oooOO0OOooo........oooOO0OOooo........oo 1067 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 892 1068 893 void G4LossTableManager::SetVerbose(G4int val) 1069 void G4LossTableManager::SetVerbose(G4int val) 894 { 1070 { 895 verbose = val; 1071 verbose = val; >> 1072 for(G4int i=0; i<n_loss; ++i) { >> 1073 if(loss_vector[i]) { loss_vector[i]->SetVerboseLevel(val); } >> 1074 } >> 1075 size_t msc = msc_vector.size(); >> 1076 for (size_t j=0; j<msc; ++j) { >> 1077 if(msc_vector[j]) { msc_vector[j]->SetVerboseLevel(val); } >> 1078 } >> 1079 size_t emp = emp_vector.size(); >> 1080 for (size_t k=0; k<emp; ++k) { >> 1081 if(emp_vector[k]) { emp_vector[k]->SetVerboseLevel(val); } >> 1082 } >> 1083 emConfigurator->SetVerbose(val); >> 1084 //tableBuilder->SetVerbose(val); >> 1085 //emCorrections->SetVerbose(val); >> 1086 emSaturation->SetVerbose(val); >> 1087 emElectronIonPair->SetVerbose(val); >> 1088 if(atomDeexcitation) { atomDeexcitation->SetVerboseLevel(val); } >> 1089 } >> 1090 >> 1091 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... >> 1092 >> 1093 void G4LossTableManager::SetStepFunction(G4double v1, G4double v2) >> 1094 { >> 1095 stepFunctionActive = true; >> 1096 maxRangeVariation = v1; >> 1097 maxFinalStep = v2; >> 1098 for(G4int i=0; i<n_loss; ++i) { >> 1099 if(loss_vector[i]) { loss_vector[i]->SetStepFunction(v1, v2); } >> 1100 } >> 1101 } >> 1102 >> 1103 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... >> 1104 >> 1105 void G4LossTableManager::SetLinearLossLimit(G4double val) >> 1106 { >> 1107 for(G4int i=0; i<n_loss; ++i) { >> 1108 if(loss_vector[i]) { loss_vector[i]->SetLinearLossLimit(val); } >> 1109 } >> 1110 } >> 1111 >> 1112 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... >> 1113 >> 1114 void G4LossTableManager::SetBuildCSDARange(G4bool val) >> 1115 { >> 1116 buildCSDARange = val; >> 1117 } >> 1118 >> 1119 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... >> 1120 >> 1121 void >> 1122 G4LossTableManager::SetParameters(const G4ParticleDefinition* aParticle, >> 1123 G4VEnergyLossProcess* p) >> 1124 { >> 1125 if(stepFunctionActive) { >> 1126 p->SetStepFunction(maxRangeVariation, maxFinalStep); >> 1127 } >> 1128 if(integralActive) { p->SetIntegral(integral); } >> 1129 if(minEnergyActive) { p->SetMinKinEnergy(minKinEnergy); } >> 1130 if(maxEnergyActive) { p->SetMaxKinEnergy(maxKinEnergy); } >> 1131 p->SetVerboseLevel(verbose); >> 1132 if(maxEnergyForMuonsActive) { >> 1133 G4double dm = std::abs(aParticle->GetPDGMass() - 105.7*MeV); >> 1134 if(dm < 5.*MeV) { p->SetMaxKinEnergy(maxKinEnergyForMuons); } >> 1135 } 896 } 1136 } 897 1137 898 //....oooOO0OOooo........oooOO0OOooo........oo 1138 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 899 1139 900 const std::vector<G4VEnergyLossProcess*>& 1140 const std::vector<G4VEnergyLossProcess*>& 901 G4LossTableManager::GetEnergyLossProcessVector 1141 G4LossTableManager::GetEnergyLossProcessVector() 902 { 1142 { 903 return loss_vector; 1143 return loss_vector; 904 } 1144 } 905 1145 906 //....oooOO0OOooo........oooOO0OOooo........oo 1146 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 907 1147 908 const std::vector<G4VEmProcess*>& G4LossTableM 1148 const std::vector<G4VEmProcess*>& G4LossTableManager::GetEmProcessVector() 909 { 1149 { 910 return emp_vector; 1150 return emp_vector; 911 } 1151 } 912 1152 913 //....oooOO0OOooo........oooOO0OOooo........oo 1153 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 914 1154 915 const std::vector<G4VMultipleScattering*>& 1155 const std::vector<G4VMultipleScattering*>& 916 G4LossTableManager::GetMultipleScatteringVecto 1156 G4LossTableManager::GetMultipleScatteringVector() 917 { 1157 { 918 return msc_vector; 1158 return msc_vector; 919 } 1159 } 920 1160 >> 1161 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... >> 1162 >> 1163 void G4LossTableManager::SetLPMFlag(G4bool val) >> 1164 { >> 1165 flagLPM = val; >> 1166 } >> 1167 >> 1168 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... >> 1169 >> 1170 G4bool G4LossTableManager::LPMFlag() const >> 1171 { >> 1172 return flagLPM; >> 1173 } >> 1174 >> 1175 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... >> 1176 >> 1177 void G4LossTableManager::SetSplineFlag(G4bool val) >> 1178 { >> 1179 splineFlag = val; >> 1180 tableBuilder->SetSplineFlag(splineFlag); >> 1181 } >> 1182 >> 1183 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... >> 1184 >> 1185 G4bool G4LossTableManager::SplineFlag() const >> 1186 { >> 1187 return splineFlag; >> 1188 } >> 1189 >> 1190 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... >> 1191 >> 1192 G4bool G4LossTableManager::IsMaster() const >> 1193 { >> 1194 return isMaster; >> 1195 } >> 1196 >> 1197 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo.... >> 1198 >> 1199 void G4LossTableManager::SetBremsstrahlungTh(G4double val) >> 1200 { >> 1201 bremsTh = val; >> 1202 } >> 1203 >> 1204 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo.... >> 1205 >> 1206 G4double G4LossTableManager::BremsstrahlungTh() const >> 1207 { >> 1208 return bremsTh; >> 1209 } >> 1210 >> 1211 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo.... >> 1212 >> 1213 void G4LossTableManager::SetFactorForAngleLimit(G4double val) >> 1214 { >> 1215 if(val > 0.0) { factorForAngleLimit = val; } >> 1216 } >> 1217 >> 1218 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo.... >> 1219 >> 1220 G4double G4LossTableManager::FactorForAngleLimit() const >> 1221 { >> 1222 return factorForAngleLimit; >> 1223 } >> 1224 >> 1225 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo...... >> 1226 >> 1227 G4double G4LossTableManager::MinKinEnergy() const >> 1228 { >> 1229 return minKinEnergy; >> 1230 } >> 1231 >> 1232 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo...... >> 1233 >> 1234 G4double G4LossTableManager::MaxKinEnergy() const >> 1235 { >> 1236 return maxKinEnergy; >> 1237 } >> 1238 >> 1239 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo...... >> 1240 >> 1241 G4EmCorrections* G4LossTableManager::EmCorrections() >> 1242 { >> 1243 return emCorrections; >> 1244 } >> 1245 921 //....oooOO0OOooo........oooOO0OOooo........oo 1246 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo...... 922 1247 923 G4EmSaturation* G4LossTableManager::EmSaturati 1248 G4EmSaturation* G4LossTableManager::EmSaturation() 924 { 1249 { 925 return theParameters->GetEmSaturation(); << 1250 return emSaturation; 926 } 1251 } 927 1252 928 //....oooOO0OOooo........oooOO0OOooo........oo 1253 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo...... 929 1254 930 G4EmConfigurator* G4LossTableManager::EmConfig 1255 G4EmConfigurator* G4LossTableManager::EmConfigurator() 931 { 1256 { 932 if(!emConfigurator) { << 933 emConfigurator = new G4EmConfigurator(verb << 934 } << 935 return emConfigurator; 1257 return emConfigurator; 936 } 1258 } 937 1259 938 //....oooOO0OOooo........oooOO0OOooo........oo 1260 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo...... 939 1261 940 G4ElectronIonPair* G4LossTableManager::Electro 1262 G4ElectronIonPair* G4LossTableManager::ElectronIonPair() 941 { 1263 { 942 if(!emElectronIonPair) { << 943 emElectronIonPair = new G4ElectronIonPair( << 944 } << 945 return emElectronIonPair; 1264 return emElectronIonPair; 946 } 1265 } 947 1266 948 //....oooOO0OOooo........oooOO0OOooo........oo << 1267 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo.... 949 1268 950 void G4LossTableManager::SetNIELCalculator(G4N << 1269 G4VAtomDeexcitation* G4LossTableManager::AtomDeexcitation() 951 { 1270 { 952 if(nullptr != ptr && ptr != nielCalculator) << 1271 return atomDeexcitation; 953 delete nielCalculator; << 954 nielCalculator = ptr; << 955 } << 956 } 1272 } 957 1273 958 //....oooOO0OOooo........oooOO0OOooo........oo << 1274 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo.... 959 1275 960 G4NIELCalculator* G4LossTableManager::NIELCalc << 1276 G4LossTableBuilder* G4LossTableManager::GetTableBuilder() 961 { 1277 { 962 if(!nielCalculator) { << 1278 return tableBuilder; 963 nielCalculator = new G4NIELCalculator(null << 964 } << 965 return nielCalculator; << 966 } 1279 } 967 1280 968 //....oooOO0OOooo........oooOO0OOooo........oo 1281 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo.... 969 1282 970 void G4LossTableManager::SetAtomDeexcitation(G 1283 void G4LossTableManager::SetAtomDeexcitation(G4VAtomDeexcitation* p) 971 { 1284 { 972 if(atomDeexcitation != p) { << 1285 atomDeexcitation = p; 973 delete atomDeexcitation; << 974 atomDeexcitation = p; << 975 } << 976 } 1286 } 977 1287 978 //....oooOO0OOooo........oooOO0OOooo........oo 1288 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 979 1289 980 void G4LossTableManager::SetSubCutProducer(G4V << 1290 G4VEnergyLossProcess* >> 1291 G4LossTableManager::GetEnergyLossProcess(const G4ParticleDefinition *aParticle) 981 { 1292 { 982 if(subcutProducer != p) { << 1293 if(aParticle != currentParticle) { 983 delete subcutProducer; << 1294 currentParticle = aParticle; 984 subcutProducer = p; << 1295 std::map<PD,G4VEnergyLossProcess*,std::less<PD> >::const_iterator pos; >> 1296 if ((pos = loss_map.find(aParticle)) != loss_map.end()) { >> 1297 currentLoss = (*pos).second; >> 1298 } else { >> 1299 currentLoss = 0; >> 1300 if(aParticle->GetParticleType() == "nucleus") { >> 1301 if ((pos = loss_map.find(theGenericIon)) != loss_map.end()) { >> 1302 currentLoss = (*pos).second; >> 1303 } >> 1304 } >> 1305 } 985 } 1306 } >> 1307 return currentLoss; 986 } 1308 } 987 1309 988 //....oooOO0OOooo........oooOO0OOooo........oo << 1310 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo...... 989 1311 990 void G4LossTableManager::PrintEWarning(G4Strin << 1312 G4double G4LossTableManager::GetDEDX(const G4ParticleDefinition *aParticle, >> 1313 G4double kineticEnergy, >> 1314 const G4MaterialCutsCouple *couple) 991 { 1315 { 992 G4String ss = "G4LossTableManager::" + tit; << 1316 if(aParticle != currentParticle) { GetEnergyLossProcess(aParticle); } 993 G4ExceptionDescription ed; << 1317 G4double x = 0.0; 994 /* << 1318 if(currentLoss) { x = currentLoss->GetDEDX(kineticEnergy, couple); } 995 ed << "Parameter is out of range: " << val << 1319 return x; 996 << " it will have no effect!\n" << " ## " << 997 << " nbins= " << nbinsLambda << 998 << " nbinsPerDecade= " << nbinsPerDecade << 999 << " Emin(keV)= " << minKinEnergy/keV << 1000 << " Emax(GeV)= " << maxKinEnergy/GeV; << 1001 */ << 1002 G4Exception(ss, "em0044", JustWarning, ed); << 1003 } 1320 } 1004 1321 1005 //....oooOO0OOooo........oooOO0OOooo........o << 1322 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 1006 1323 1007 void G4LossTableManager::DumpHtml() << 1324 G4double G4LossTableManager::GetSubDEDX(const G4ParticleDefinition *aParticle, >> 1325 G4double kineticEnergy, >> 1326 const G4MaterialCutsCouple *couple) 1008 { 1327 { 1009 // Automatic generation of html documentati << 1328 if(aParticle != currentParticle) { GetEnergyLossProcess(aParticle); } 1010 // List processes and models for the most i << 1329 G4double x = 0.0; 1011 // particles in descending order of importa << 1330 if(currentLoss) { x = currentLoss->GetDEDXForSubsec(kineticEnergy, couple); } 1012 // NB. for model names with length > 18 cha << 1331 return x; 1013 // to be edited by hand. Or modify G4EmMod << 1332 } 1014 << 1015 char* dirName = std::getenv("G4PhysListDocD << 1016 char* physList = std::getenv("G4PhysListNam << 1017 if (dirName && physList) { << 1018 G4String physListName = G4String(physList << 1019 G4String pathName = G4String(dirName) + " << 1020 << 1021 std::ofstream outFile; << 1022 outFile.open(pathName); << 1023 << 1024 outFile << physListName << G4endl; << 1025 outFile << std::string(physListName.lengt << 1026 << 1027 std::vector<G4ParticleDefinition*> partic << 1028 G4Gamma::Gamma(), << 1029 G4Electron::Electron(), << 1030 G4Positron::Positron(), << 1031 G4Proton::ProtonDefinition(), << 1032 G4MuonPlus::MuonPlusDefinition(), << 1033 G4MuonMinus::MuonMinusDefinition(), << 1034 }; << 1035 << 1036 std::vector<G4VEmProcess*> emproc_vector << 1037 std::vector<G4VEnergyLossProcess*> enloss << 1038 GetEnergyLossProcessVector(); << 1039 std::vector<G4VMultipleScattering*> mscat << 1040 GetMultipleScatteringVector(); << 1041 << 1042 for (auto theParticle : particles) { << 1043 outFile << G4endl << "**" << theParticl << 1044 << "**" << G4endl << G4endl << << 1045 << 1046 G4ProcessManager* pm = theParticle->Get << 1047 G4ProcessVector* pv = pm->GetProcessLi << 1048 G4int plen = pm->GetProcessListLength() << 1049 << 1050 for (auto emproc : emproc_vector) { << 1051 for (G4int i = 0; i < plen; ++i) { << 1052 G4VProcess* proc = (*pv)[i]; << 1053 if (proc == emproc) { << 1054 outFile << G4endl; << 1055 proc->ProcessDescription(outFile) << 1056 break; << 1057 } << 1058 } << 1059 } << 1060 1333 1061 for (auto mscproc : mscat_vector) { << 1334 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 1062 for (G4int i = 0; i < plen; ++i) { << 1063 G4VProcess* proc = (*pv)[i]; << 1064 if (proc == mscproc) { << 1065 outFile << G4endl; << 1066 proc->ProcessDescription(outFile) << 1067 break; << 1068 } << 1069 } << 1070 } << 1071 1335 1072 for (auto enlossproc : enloss_vector) { << 1336 G4double G4LossTableManager::GetCSDARange(const G4ParticleDefinition *aParticle, 1073 for (G4int i = 0; i < plen; ++i) { << 1337 G4double kineticEnergy, 1074 G4VProcess* proc = (*pv)[i]; << 1338 const G4MaterialCutsCouple *couple) 1075 if (proc == enlossproc) { << 1339 { 1076 outFile << G4endl; << 1340 if(aParticle != currentParticle) { GetEnergyLossProcess(aParticle); } 1077 proc->ProcessDescription(outFile) << 1341 G4double x = DBL_MAX; 1078 break; << 1342 if(currentLoss) { x = currentLoss->GetCSDARange(kineticEnergy, couple); } 1079 } << 1343 return x; 1080 } << 1344 } 1081 } << 1345 1082 } << 1346 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 1083 outFile.close(); << 1347 1084 } << 1348 G4double G4LossTableManager::GetRangeFromRestricteDEDX( >> 1349 const G4ParticleDefinition *aParticle, >> 1350 G4double kineticEnergy, >> 1351 const G4MaterialCutsCouple *couple) >> 1352 { >> 1353 if(aParticle != currentParticle) { GetEnergyLossProcess(aParticle); } >> 1354 G4double x = DBL_MAX; >> 1355 if(currentLoss) { x = currentLoss->GetRangeForLoss(kineticEnergy, couple); } >> 1356 return x; 1085 } 1357 } 1086 1358 1087 //....oooOO0OOooo........oooOO0OOooo........o 1359 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo..... 1088 1360 >> 1361 G4double G4LossTableManager::GetRange(const G4ParticleDefinition *aParticle, >> 1362 G4double kineticEnergy, >> 1363 const G4MaterialCutsCouple *couple) >> 1364 { >> 1365 if(aParticle != currentParticle) { GetEnergyLossProcess(aParticle); } >> 1366 G4double x = DBL_MAX; >> 1367 if(currentLoss) { x = currentLoss->GetRange(kineticEnergy, couple); } >> 1368 return x; >> 1369 } >> 1370 >> 1371 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo...... >> 1372 >> 1373 G4double G4LossTableManager::GetEnergy(const G4ParticleDefinition *aParticle, >> 1374 G4double range, >> 1375 const G4MaterialCutsCouple *couple) >> 1376 { >> 1377 if(aParticle != currentParticle) { GetEnergyLossProcess(aParticle); } >> 1378 G4double x = 0; >> 1379 if(currentLoss) { x = currentLoss->GetKineticEnergy(range, couple); } >> 1380 return x; >> 1381 } >> 1382 >> 1383 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo...... >> 1384 >> 1385 G4double G4LossTableManager::GetDEDXDispersion( >> 1386 const G4MaterialCutsCouple *couple, >> 1387 const G4DynamicParticle* dp, >> 1388 G4double& length) >> 1389 { >> 1390 const G4ParticleDefinition* aParticle = dp->GetParticleDefinition(); >> 1391 if(aParticle != currentParticle) { GetEnergyLossProcess(aParticle); } >> 1392 G4double x = 0.0; >> 1393 if(currentLoss) { currentLoss->GetDEDXDispersion(couple, dp, length); } >> 1394 return x; >> 1395 } >> 1396 >> 1397 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo.... 1089 1398