Import Geant4 10.7.0.beta source tree

This commit is contained in:
Gabriele Cosmo
2020-06-26 10:23:25 +02:00
parent c02c370437
commit 67ba86d073
1871 changed files with 174422 additions and 131884 deletions
@@ -36,6 +36,7 @@
#include "G4GeometryManager.hh"
#include "G4VPhysicalVolume.hh"
#include "G4Navigator.hh"
#include "G4PropagatorInField.hh"
#include "G4UIdirectory.hh"
#include "G4UIcommand.hh"
@@ -317,6 +318,8 @@ G4GeometryMessenger::SetCheckMode(G4String input)
G4bool mode = chkCmd->GetNewBoolValue(input);
G4Navigator* navigator = tmanager->GetNavigatorForTracking();
navigator->CheckMode(mode);
G4PropagatorInField* pField = tmanager->GetPropagatorInField();
if (pField != nullptr) { pField->CheckMode(mode); }
}
//
@@ -0,0 +1,207 @@
//
// ********************************************************************
// * License and Disclaimer *
// * *
// * The Geant4 software is copyright of the Copyright Holders of *
// * the Geant4 Collaboration. It is provided under the terms and *
// * conditions of the Geant4 Software License, included in the file *
// * LICENSE and available at http://cern.ch/geant4/license . These *
// * include a list of copyright holders. *
// * *
// * Neither the authors of this software system, nor their employing *
// * institutes,nor the agencies providing financial support for this *
// * work make any representation or warranty, express or implied, *
// * regarding this software system or assume any liability for its *
// * use. Please see the license in the file LICENSE and URL above *
// * for the full disclaimer and the limitation of liability. *
// * *
// * This code implementation is the result of the scientific and *
// * technical work of the GEANT4 collaboration. *
// * By using, copying, modifying or distributing the software (or *
// * any work based on the software) you agree to acknowledge its *
// * use in resulting scientific publications, and indicate your *
// * acceptance of all terms of the Geant4 Software license. *
// ********************************************************************
//
// G4LocatorChangeLogger class implementation
//
// Author: John Apostolakis, 04.09.19 - First version
// --------------------------------------------------------------------
#include <iostream>
#include <iomanip>
#include <locale>
// #include <cassert>
#include "G4LocatorChangeLogger.hh"
// --------------------------------------------------------------------
// Streaming operator dumping record
//
std::ostream& operator<< ( std::ostream& os,
const G4LocatorChangeLogger& logger )
{
return logger.StreamInfo(os);
}
// --------------------------------------------------------------------
// Stream object contents to an output stream
//
std::ostream& G4LocatorChangeLogger::StreamInfo(std::ostream& os) const
{
G4int oldprc = os.precision(16);
G4LocatorChangeRecord::ReportVector( os, this->fName, *this );
os.precision(oldprc);
return os;
}
// --------------------------------------------------------------------
// Print the changes in start, end points in columns -- one event per row
//
std::ostream& G4LocatorChangeLogger::ReportEndChanges( std::ostream& os,
const G4LocatorChangeLogger & startA,
const G4LocatorChangeLogger & endB )
{
using std::setw;
G4int prec= 16;
const G4bool confirm = true;
G4int oldprc = os.precision(prec);
auto itrecA= startA.cbegin();
auto itrecB= endB.cbegin();
os << "====================================================================="
<< G4endl;
os << " Size of individual change record: startA : " << startA.size()
<< " endB : " << endB.size() << G4endl;
os << "====================================================================="
<< G4endl;
os << setw( 7 ) << "Change#" << " "
<< setw( 4 ) << "Iter" << " "
<< setw( 20 ) << "CodeLocation" << " "
<< setw( prec+9 ) << "Length-A (start)" << " "
<< setw( prec+9 ) << "Length-B (end)" << " "
<< G4endl;
os << "=====================================================================";
auto eventA = (*itrecA).GetCount();
auto eventB = (*itrecB).GetCount();
G4bool isLastA= false;
G4bool isLastB= false;
G4int jA=0, jB=0;
G4int maxEvent = std::max( startA[ startA.size() - 1 ].GetCount() ,
endB[ endB.size() - 1 ].GetCount() );
G4int prevA = -1;
G4int prevB = -1;
G4bool advanceA= false, advanceB= false;
do
{
advanceA= false;
advanceB= false;
if( ((G4int)eventA>prevA) && ((G4int)eventB>prevB) )
{
auto codeLocA= (*itrecA).GetLocation();
os << G4endl;
os << setw( 7 ) << eventA << " "
<< setw( 4 ) << (*itrecA).GetIteration() << " "
<< setw( 3 ) << codeLocA << " "
<< setw( 15 )
<< G4LocatorChangeRecord::GetNameChangeLocation( codeLocA ) << " "
<< setw( prec+9 ) << (*itrecA).GetLength() << " "
<< setw( prec+9 ) << (*itrecB).GetLength() << " ";
if( confirm )
{
os << setw( 4 ) << (*itrecB).GetIteration() << " "
<< setw( 15 ) << (*itrecB).GetLocation();
}
}
else
{
if ( (G4int)eventA > prevA )
{
auto codeLocA= (*itrecA).GetLocation();
os << G4endl;
os << setw( 7 ) << (*itrecA).GetCount() << " "
<< setw( 4 ) << (*itrecA).GetIteration() << " "
<< setw( 3 ) << codeLocA << " "
<< setw( 15 )
<< G4LocatorChangeRecord::GetNameChangeLocation( codeLocA ) << " "
<< setw( prec+9 ) << (*itrecA).GetLength() << " "
<< setw( prec+9 ) << " " << " ";
}
else
{
// assert( (G4int)eventB > prevB );
auto codeLocB= (*itrecB).GetLocation();
os << G4endl;
os << setw( 7 ) << eventB << " "
<< setw( 4 ) << (*itrecB).GetIteration() << " "
<< setw( 3 ) << codeLocB << " "
<< setw( 15 )
<< G4LocatorChangeRecord::GetNameChangeLocation( codeLocB ) << " "
<< setw( prec+9 ) << " " << " "
<< setw( prec+9 ) << (*itrecB).GetLength() << " " ;
}
}
prevA= eventA;
prevB= eventB;
auto nextA= itrecA;
auto nextB= itrecB;
G4int nextAct = maxEvent, nextBct = maxEvent;
++nextA;
++nextB;
if ( nextA != startA.end() ) { nextAct = (*nextA).GetCount(); }
if ( nextB != endB.end() ) { nextBct = (*nextB).GetCount(); }
isLastA= ( nextA >= startA.end() );
isLastB= ( nextB >= endB.end() );
advanceA= ( nextAct <= nextBct ) && !isLastA;
advanceB= ( nextBct <= nextAct ) && !isLastB;
if( advanceA )
{
++itrecA;
if( !isLastA ) { ++jA; }
eventA = isLastA ? maxEvent : (*itrecA).GetCount();
}
if( advanceB )
{
++itrecB;
if( !isLastB ) { ++jB; }
eventB = isLastB ? maxEvent : (*itrecB).GetCount();
}
// Checks
if( isLastA != ( nextA == startA.end() ) )
{
os << G4endl;
os << " Checking isLastA= " << isLastA
<< " vs expected : " << ( itrecA == startA.end() );
os << " BAD --- ERROR " << G4endl;
}
if( isLastB != ( nextB == endB.end() ) )
{
os << G4endl;
os << " Checking isLastB= " << isLastB
<< " vs expected : " << ( itrecB == endB.end() );
os << " BAD --- ERROR " << G4endl;
}
} while ( ! ( isLastA && isLastB ) );
os << G4endl;
os.precision(oldprc);
return os;
}
@@ -0,0 +1,285 @@
//
// ********************************************************************
// * License and Disclaimer *
// * *
// * The Geant4 software is copyright of the Copyright Holders of *
// * the Geant4 Collaboration. It is provided under the terms and *
// * conditions of the Geant4 Software License, included in the file *
// * LICENSE and available at http://cern.ch/geant4/license . These *
// * include a list of copyright holders. *
// * *
// * Neither the authors of this software system, nor their employing *
// * institutes,nor the agencies providing financial support for this *
// * work make any representation or warranty, express or implied, *
// * regarding this software system or assume any liability for its *
// * use. Please see the license in the file LICENSE and URL above *
// * for the full disclaimer and the limitation of liability. *
// * *
// * This code implementation is the result of the scientific and *
// * technical work of the GEANT4 collaboration. *
// * By using, copying, modifying or distributing the software (or *
// * any work based on the software) you agree to acknowledge its *
// * use in resulting scientific publications, and indicate your *
// * acceptance of all terms of the Geant4 Software license. *
// ********************************************************************
//
// G4LocatorChangeRecord class implementation
//
// Author: John Apostolakis, 28.08.19 - First version
// --------------------------------------------------------------------
#include <iostream>
#include <iomanip>
#include <locale>
// #include <cassert>
#include "G4LocatorChangeRecord.hh"
// Must correspond exactly with the count of the enum EChangeLocation
//
const char * G4LocatorChangeRecord::fNameChangeLocation[] =
{ "Invalid", "Unknown", "Initialising", "IntersectsAF", "IntersectsFB", // 5
"NoIntersections-AForFB", "RecalculatedB", // 2
"InsertingMidPoint", "RecalculatedB-2ndHalf", // 2
"Level Pop" };
// --------------------------------------------------------------------
//
std::ostream& G4LocatorChangeRecord::ReportVector ( std::ostream& os,
const std::string & name,
const std::vector<G4LocatorChangeRecord> & vecRec )
{
using std::setw;
G4int prec= 16;
if( vecRec.size() == 0 )
{
os << "Locator Change Record for " << name << " is empty" << G4endl;
return os;
}
G4int oldprc = os.precision(prec);
// std::vector<G4LocatorChangeRecord>::const_iterator
auto itRec
= std::vector<G4LocatorChangeRecord>::const_iterator(vecRec.cbegin());
os << setw( 7 ) << "Change#" << " "
<< setw( 4 ) << "Iter" << " "
<< std::left
<< setw( prec+9 ) << "Length" << " "
<< setw( 15 ) << "Code-Location" << " "
<< G4endl;
os << "====================================================================="
<< G4endl;
do
{
auto locationCode= (*itRec).GetLocation();
os << std::internal
<< setw( 7 ) << (*itRec).GetCount() << " " // Event Count
<< setw( 4 ) << (*itRec).GetIteration() << " "
<< std::left
<< setw( prec+9 ) << (*itRec).GetLength() << " "
<< setw( 2 ) << locationCode << " " // location enum
<< setw( 15 ) << fNameChangeLocation[ locationCode ]
<< std::internal
;
os << G4endl;
++itRec;
} while ( itRec != vecRec.cend() );
os.precision(oldprc);
return os;
}
// --------------------------------------------------------------------
//
std::ostream&
G4LocatorChangeRecord::ReportEndChanges (
std::ostream& os,
const std::vector<G4LocatorChangeRecord> & startA,
const std::vector<G4LocatorChangeRecord> & endB )
{
using std::setw;
G4int prec= 16;
const G4bool confirm = true;
G4int oldprc = os.precision(prec);
std::vector<G4LocatorChangeRecord>::const_iterator itrecA, itrecB;
itrecA= startA.begin();
itrecB= endB.begin();
os << "====================================================================="
<< G4endl;
os << " Size of individual change record: startA : " << startA.size()
<< " endB : " << endB.size() << G4endl;
os << "====================================================================="
<< G4endl;
os << setw( 7 ) << "Change#" << " "
<< setw( 4 ) << "Iter" << " "
<< setw( 20 ) << "CodeLocation" << " "
<< setw( prec+9 ) << "Length-A (start)" << " "
<< setw( prec+9 ) << "Length-B (end)" << " "
<< G4endl;
os << "=====================================================================";
auto eventA = (*itrecA).GetCount();
auto eventB = (*itrecB).GetCount();
G4bool isLastA= false;
G4bool isLastB= false;
G4int jA=0, jB=0;
G4int maxEvent = std::max( startA[ startA.size() - 1 ].GetCount() ,
endB[ endB.size() - 1 ].GetCount() );
G4int prevA = -1;
G4int prevB = -1;
G4bool advanceA= false, advanceB= false;
do
{
advanceA= false;
advanceB= false;
if( ((G4int)eventA>prevA) && ((G4int)eventB>prevB) )
{
auto codeLocA= (*itrecA).GetLocation();
os << G4endl;
os << setw( 7 ) << eventA << " "
<< setw( 4 ) << (*itrecA).GetIteration() << " "
<< setw( 3 ) << codeLocA << " "
<< setw( 15 ) << fNameChangeLocation[ codeLocA ] << " "
<< setw( prec+9 ) << (*itrecA).GetLength() << " "
<< setw( prec+9 ) << (*itrecB).GetLength() << " ";
if( confirm )
{
os << setw( 4 ) << (*itrecB).GetIteration() << " "
<< setw( 15 ) << (*itrecB).GetLocation();
}
}
else
{
if ( (G4int)eventA > prevA )
{
auto codeLocA = (*itrecA).GetLocation();
os << G4endl;
os << setw( 7 ) << (*itrecA).GetCount() << " "
<< setw( 4 ) << (*itrecA).GetIteration() << " "
<< setw( 3 ) << codeLocA << " "
<< setw( 15 ) << fNameChangeLocation[ codeLocA ] << " "
<< setw( prec+9 ) << (*itrecA).GetLength() << " "
<< setw( prec+9 ) << " " << " ";
}
else
{
// assert( (G4int)eventB > prevB );
auto codeLocB = (*itrecB).GetLocation();
os << G4endl;
os << setw( 7 ) << eventB << " "
<< setw( 4 ) << (*itrecB).GetIteration() << " "
<< setw( 3 ) << codeLocB << " "
<< setw( 15 ) << fNameChangeLocation[ codeLocB ] << " "
<< setw( prec+9 ) << " " << " "
<< setw( prec+9 ) << (*itrecB).GetLength() << " " ;
}
}
prevA= eventA;
prevB= eventB;
auto nextA= itrecA;
auto nextB= itrecB;
G4int nextAct = maxEvent, nextBct = maxEvent;
++nextA;
++nextB;
if ( nextA != startA.end() ) { nextAct = (*nextA).GetCount(); }
if ( nextB != endB.end() ) { nextBct = (*nextB).GetCount(); }
isLastA= ( nextA >= startA.end() );
isLastB= ( nextB >= endB.end() );
advanceA= ( nextAct <= nextBct ) && !isLastA;
advanceB= ( nextBct <= nextAct ) && !isLastB;
if( advanceA )
{
++itrecA;
if( !isLastA ) { ++jA; eventA = (*itrecA).GetCount(); }
else { eventA = maxEvent; }
}
if( advanceB )
{
++itrecB;
if( !isLastB ) { ++jB; eventB = (*itrecB).GetCount(); }
else { eventB = maxEvent; }
}
// Checks
if( isLastA != ( nextA == startA.end() ) )
{
os << G4endl;
os << " Checking isLastA= " << isLastA << " vs expected : "
<< ( itrecA == startA.end() );
os << " BAD --- ERROR " << G4endl;
}
if( isLastB != ( nextB == endB.end() ) )
{
os << G4endl;
os << " Checking isLastB= " << isLastB << " vs expected : "
<< ( itrecB == endB.end() );
os << " BAD --- ERROR " << G4endl;
}
} while ( ! ( isLastA && isLastB ) );
os << G4endl;
os.precision(oldprc);
return os;
}
// --------------------------------------------------------------------
// Streaming operator dumping record
//
std::ostream& operator<< ( std::ostream& os, const G4LocatorChangeRecord& e )
{
return e.StreamInfo(os);
}
// --------------------------------------------------------------------
// Stream object contents to an output stream
//
std::ostream& G4LocatorChangeRecord::StreamInfo(std::ostream& os) const
{
G4int oldprc = os.precision(16);
os << " count = " << fEventCount
<< " iter= " << fIteration
<< " Location code = " << fCodeLocation
<< " Length = " << GetLength() << G4endl;
os.precision(oldprc);
return os;
}
// --------------------------------------------------------------------
// Streaming operator
//
std::ostream& operator << ( std::ostream& os,
const std::vector<G4LocatorChangeRecord> & vecR )
{
G4LocatorChangeRecord::ReportVector( os, "", vecR );
return os;
}
// --------------------------------------------------------------------
//
const char *G4LocatorChangeRecord::GetNameChangeLocation( EChangeLocation loc )
{
return fNameChangeLocation[loc];
}
@@ -33,6 +33,8 @@
#include "G4ios.hh"
#include "G4MultiLevelLocator.hh"
#include "G4LocatorChangeRecord.hh"
#include "G4LocatorChangeLogger.hh"
G4MultiLevelLocator::G4MultiLevelLocator(G4Navigator *theNavigator)
: G4VIntersectionLocator(theNavigator)
@@ -47,12 +49,13 @@ G4MultiLevelLocator::G4MultiLevelLocator(G4Navigator *theNavigator)
ptrInterMedFT[ idepth ] = new G4FieldTrack( zeroV, zeroV, 0., 0., 0., 0.);
}
#ifdef G4DEBUG_FIELD
// Trial values Loose Tight
// To happen: Infrequent Often
SetMaxSteps(50); // 300 25
SetWarnSteps(40); // 250 15
#endif
if (fCheckMode)
{
// Trial values Loose Medium Tight
// To happen: Infrequent Occasional Often
SetMaxSteps(150); // 300 85 25
SetWarnSteps(80); // 250 60 15
}
}
G4MultiLevelLocator::~G4MultiLevelLocator()
@@ -123,7 +126,7 @@ G4bool G4MultiLevelLocator::EstimateIntersectionPoint(
G4bool found_approximate_intersection = false;
G4bool there_is_no_intersection = false;
G4FieldTrack CurrentA_PointVelocity = CurveStartPointVelocity;
G4FieldTrack CurrentB_PointVelocity = CurveEndPointVelocity;
G4ThreeVector CurrentE_Point = TrialPoint;
@@ -138,8 +141,6 @@ G4bool G4MultiLevelLocator::EstimateIntersectionPoint(
auto integrDriver = GetChordFinderFor()->GetIntegrationDriver();
G4bool driverReIntegrates = integrDriver->DoesReIntegrate();
// G4bool final_section= true; // Shows whether current section is last
// (i.e. B=full end)
G4bool first_section = true;
recalculatedEndPoint = false;
G4bool restoredFullEndpoint = false;
@@ -147,8 +148,37 @@ G4bool G4MultiLevelLocator::EstimateIntersectionPoint(
unsigned int substep_no = 0;
// Statistics for substeps
//
static G4ThreadLocal unsigned int max_no_seen= 0;
static G4ThreadLocal unsigned int max_no_seen= 0;
#ifdef G4DEBUG_FIELD
unsigned int trigger_substepno_print = 0;
const G4double tolerance = 1.0e-8 * CLHEP::mm;
unsigned int biggest_depth = 0;
// using kInitialisingCL = G4LocatorChangeRecord::kInitialisingCL;
#endif
// Log the location, iteration of changes in A,B
//----------------------------------------------
static G4ThreadLocal G4LocatorChangeLogger endChangeA("StartPointA"),
endChangeB("EndPointB"), recApproxPoint("ApproxPoint"),
pointH_logger("Trial points 'E': position, normal");
unsigned int eventCount = 0;
if (fCheckMode)
{
// Clear previous call's data
endChangeA.clear();
endChangeB.clear();
recApproxPoint.clear();
pointH_logger.clear();
// Record the initialisation
++eventCount;
endChangeA.AddRecord( G4LocatorChangeRecord::kInitialisingCL, substep_no,
eventCount, CurrentA_PointVelocity );
endChangeB.AddRecord( G4LocatorChangeRecord::kInitialisingCL, substep_no,
eventCount, CurrentB_PointVelocity );
}
//--------------------------------------------------------------------------
// Algorithm for the case if progress in founding intersection is too slow.
@@ -175,22 +205,23 @@ G4bool G4MultiLevelLocator::EstimateIntersectionPoint(
unsigned int depth = 0; // Depth counts subdivisions of initial step made
++fNumCalls;
#ifdef G4DEBUG_FIELD
unsigned int trigger_substepno_print = 0;
const G4double tolerance = 1.0e-8 * CLHEP::mm;
unsigned int biggest_depth = 0;
NormalAtEntry = GetSurfaceNormal(CurrentE_Point, validNormalAtE);
#if (G4DEBUG_FIELD>1)
G4ThreeVector StartPosition = CurveStartPointVelocity.GetPosition();
if( (TrialPoint - StartPosition).mag2() < sqr(tolerance))
if (fCheckMode)
{
ReportImmediateHit( MethodName, StartPosition, TrialPoint,
tolerance, fNumCalls);
pointH_logger.AddRecord( G4LocatorChangeRecord::kInitialisingCL,
substep_no, eventCount,
G4FieldTrack( CurrentE_Point,0.,NormalAtEntry,0.,
0., 1.,G4ThreeVector(0.),0.,0.) );
#if (G4DEBUG_FIELD>1)
G4ThreeVector StartPosition = CurveStartPointVelocity.GetPosition();
if( (TrialPoint - StartPosition).mag2() < sqr(tolerance))
{
ReportImmediateHit( MethodName, StartPosition, TrialPoint,
tolerance, fNumCalls);
}
#endif
}
#endif
#endif
NormalAtEntry = GetSurfaceNormal(CurrentE_Point, validNormalAtE);
// Intermediates Points on the Track = Subdivided Points must be stored.
// Give the initial values to 'InterMedFt'
@@ -222,9 +253,21 @@ G4bool G4MultiLevelLocator::EstimateIntersectionPoint(
do // Loop checking, 07.10.2016, J.Apostolakis
{ // REPEAT param
#ifdef G4DEBUG_FIELD
if( CurrentA_PointVelocity.GetCurveLength() >=
CurrentB_PointVelocity.GetCurveLength() )
{
G4cerr << "ERROR> (Start) Point A coincides with or has gone past (end) point B"
<< "MLL: iters = " << substep_no << G4endl;
// G4LocatorChangeRecord::ReportVector(G4cerr, "endPointB", endChangeB );
// G4cerr<<"EndPoints A(start) and B(end): combined changes " << G4endl;
G4LocatorChangeLogger::ReportEndChanges(G4cerr, endChangeA, endChangeB);
}
#endif
G4ThreeVector Point_A = CurrentA_PointVelocity.GetPosition();
G4ThreeVector Point_B = CurrentB_PointVelocity.GetPosition();
// F = a point on true AB path close to point E
// (the closest if possible)
//
@@ -232,15 +275,33 @@ G4bool G4MultiLevelLocator::EstimateIntersectionPoint(
->ApproxCurvePointV( CurrentA_PointVelocity,
CurrentB_PointVelocity,
CurrentE_Point,
GetEpsilonStepFor());
GetEpsilonStepFor() );
// The above method is the key & most intuitive part ...
#ifdef G4DEBUG_FIELD
if( ApproxIntersecPointV.GetCurveLength() >
CurrentB_PointVelocity.GetCurveLength() * (1.0 + tolerance) )
#ifdef G4DEBUG_FIELD
recApproxPoint.push_back(G4LocatorChangeRecord(G4LocatorChangeRecord::kInvalidCL,
substep_no, eventCount, ApproxIntersecPointV ) );
G4double lenIntsc= ApproxIntersecPointV.GetCurveLength();
G4double lenB = CurrentB_PointVelocity.GetCurveLength();
G4double checkVsEnd= lenB - lenIntsc;
if( lenIntsc > lenB )
{
G4Exception(MethodName, "GeomNav0003", FatalException,
"Intermediate F point is past end B point" );
std::ostringstream errmsg;
errmsg.precision(17);
G4double ratio = checkVsEnd / lenB;
G4double ratioTol = std::fabs(ratio) / tolerance;
errmsg << "Intermediate F point is past end B point" << G4endl
<< " l( intersection ) = " << lenIntsc << G4endl
<< " l( endpoint ) = " << lenB << G4endl;
errmsg.precision(8);
errmsg << " l_end - l_inters = " << checkVsEnd << G4endl
<< " / l_end = " << ratio << G4endl
<< " ratio / tolerance = " << ratioTol << G4endl;
if( ratioTol < 1.0 )
G4Exception(MethodName, "GeomNav0003", JustWarning, errmsg );
else
G4Exception(MethodName, "GeomNav0003", FatalException, errmsg );
}
#endif
@@ -253,7 +314,7 @@ G4bool G4MultiLevelLocator::EstimateIntersectionPoint(
G4ThreeVector NewMomentumDir = ApproxIntersecPointV.GetMomentumDir();
G4double MomDir_dot_Norm = NewMomentumDir.dot( NormalAtEntry );
#ifdef G4DEBUG_FIELD
if( fVerboseLevel > 3 )
{
@@ -316,6 +377,7 @@ G4bool G4MultiLevelLocator::EstimateIntersectionPoint(
G4ThreeVector PointG; // Candidate intersection point
G4double stepLengthAF;
G4bool Intersects_FB = false;
G4bool Intersects_AF = IntersectChord( Point_A, CurrentF_Point,
NewSafety, previousSafety,
previousSftOrigin,
@@ -325,13 +387,9 @@ G4bool G4MultiLevelLocator::EstimateIntersectionPoint(
if( Intersects_AF )
{
// G is our new Candidate for the intersection point.
// It replaces "E" and we will repeat the test to see if
// it is a good enough approximate point for us.
// B <- F
// E <- G
//
CurrentB_PointVelocity = ApproxIntersecPointV;
CurrentE_Point = PointG;
// It replaces "E" and we will see if it's good enough.
CurrentB_PointVelocity = ApproxIntersecPointV; // B <- F
CurrentE_Point = PointG; // E <- G
validIntersectP = true; // 'E' has been updated.
@@ -339,11 +397,17 @@ G4bool G4MultiLevelLocator::EstimateIntersectionPoint(
NormalAtEntry = GetSurfaceNormal( PointG, validNormalLast );
validNormalAtE = validNormalLast;
// By moving point B, must take care if current
// As we move point B, must take care in case the current
// AF has no intersection to try current FB!!
//
fin_section_depth[depth] = false;
if (fCheckMode)
{
++eventCount;
endChangeB.push_back(
G4LocatorChangeRecord(G4LocatorChangeRecord::kIntersectsAF,
substep_no, eventCount, CurrentB_PointVelocity) );
}
#ifdef G4VERBOSE
if( fVerboseLevel > 3 )
{
@@ -368,11 +432,11 @@ G4bool G4MultiLevelLocator::EstimateIntersectionPoint(
// Check whether any volumes are encountered by the chord FB
// ---------------------------------------------------------
G4bool Intersects_FB = IntersectChord( CurrentF_Point, Point_B,
NewSafety, previousSafety,
previousSftOrigin,
stepLengthFB,
PointH );
Intersects_FB = IntersectChord( CurrentF_Point, Point_B,
NewSafety, previousSafety,
previousSftOrigin,
stepLengthFB,
PointH );
if( Intersects_FB )
{
// There is an intersection of FB with a volume boundary
@@ -394,7 +458,21 @@ G4bool G4MultiLevelLocator::EstimateIntersectionPoint(
G4bool validNormalH;
NormalAtEntry = GetSurfaceNormal( PointH, validNormalH );
validNormalAtE = validNormalH;
validNormalAtE = validNormalH;
if (fCheckMode)
{
++eventCount;
endChangeA.push_back(
G4LocatorChangeRecord(G4LocatorChangeRecord::kIntersectsFB,
substep_no, eventCount, CurrentA_PointVelocity) );
G4FieldTrack intersectH_pn('0'); // Point and normal
// nothing else will be valid
intersectH_pn.SetPosition( PointH );
intersectH_pn.SetMomentum( NormalAtEntry );
pointH_logger.AddRecord(G4LocatorChangeRecord::kIntersectsFB,
substep_no, eventCount, intersectH_pn );
}
}
else // not Intersects_FB
{
@@ -433,6 +511,19 @@ G4bool G4MultiLevelLocator::EstimateIntersectionPoint(
restoredFullEndpoint = true;
validIntersectP = false; // 'E' has NOT been updated.
if (fCheckMode)
{
++eventCount;
endChangeA.push_back(
G4LocatorChangeRecord(
G4LocatorChangeRecord::kNoIntersectAForFB,
substep_no, eventCount, CurrentA_PointVelocity) );
endChangeB.push_back(
G4LocatorChangeRecord (
G4LocatorChangeRecord::kNoIntersectAForFB,
substep_no, eventCount, CurrentB_PointVelocity) );
}
}
} // Endif (Intersects_FB)
} // Endif (Intersects_AF)
@@ -469,6 +560,18 @@ G4bool G4MultiLevelLocator::EstimateIntersectionPoint(
// [ Implementation: a counter for # of recomputations
// => avoids extra work]
}
// else
// Move forward the other points
// - or better flag it, so that they are re-computed when next used
// [ Implementation: a counter for # of recomputations
// => avoids extra work]
if (fCheckMode)
{
++eventCount;
endChangeB.push_back(
G4LocatorChangeRecord( G4LocatorChangeRecord::kRecalculatedB,
substep_no, eventCount, RevisedB_FT ) );
}
}
else
{
@@ -479,15 +582,19 @@ G4bool G4MultiLevelLocator::EstimateIntersectionPoint(
if( errorEndPt > 1 ) // errorEndPt = 1 is milder, just: len(B)=len(A)
{
std::ostringstream errmsg;
errmsg << "Location: " << MethodName
<< "- After EndIf(Intersects_AF)" << G4endl;
ReportReversedPoints(errmsg,
CurveStartPointVelocity, CurveEndPointVelocity,
NewSafety, fiEpsilonStep,
CurrentA_PointVelocity, CurrentB_PointVelocity,
SubStart_PointVelocity, CurrentE_Point,
ApproxIntersecPointV, substep_no, substep_no_p, depth);
G4Exception(MethodName, "GeomNav0003", FatalException, errmsg);
errmsg << G4endl << " * Location: " << MethodName
<< "- After EndIf(Intersects_AF)" << G4endl;
errmsg << " * Bool flags: Recalculated = " << recalculatedB
<< " Intersects_AF = " << Intersects_AF
<< " Intersects_FB = " << Intersects_FB << G4endl;
errmsg << " * Number of calls to MLL:EIP= " << fNumCalls << G4endl;
G4Exception(MethodName, "GeomNav0003", FatalException, errmsg);
}
if( restoredFullEndpoint )
{
@@ -506,17 +613,21 @@ G4bool G4MultiLevelLocator::EstimateIntersectionPoint(
if( substep_no >= trigger_substepno_print )
{
G4cout << "Difficulty in converging in " << MethodName
<< G4endl
<< " Substep no = " << substep_no << G4endl;
if( substep_no == trigger_substepno_print )
{
G4cout << " Start: ";
printStatus( CurveStartPointVelocity, CurveEndPointVelocity,
-1.0, NewSafety, 0 );
G4cout << " ** Change records: " << G4endl;
G4cout << "endPoints A (start) and B (end): combined changes of AB intervals" << G4endl;
G4LocatorChangeRecord::ReportEndChanges(G4cout, endChangeA, endChangeB );
}
G4cout << " State of point A: ";
G4cout << " Point A: ";
printStatus( CurrentA_PointVelocity, CurrentA_PointVelocity,
-1.0, NewSafety, substep_no-1 );
G4cout << " State of point B: ";
G4cout << " Point B: ";
printStatus( CurrentA_PointVelocity, CurrentB_PointVelocity,
-1.0, NewSafety, substep_no );
}
@@ -537,7 +648,6 @@ G4bool G4MultiLevelLocator::EstimateIntersectionPoint(
- SubStart_PointVelocity.GetCurveLength());
G4double distAB = -1;
G4ThreeVector PointGe;
//
// Is progress is too slow, and is it possible to go deeper?
// If so, then *halve the step*
@@ -605,6 +715,14 @@ G4bool G4MultiLevelLocator::EstimateIntersectionPoint(
*ptrInterMedFT[depth] = midPoint;
CurrentB_PointVelocity = midPoint;
if (fCheckMode)
{
++eventCount;
endChangeB.push_back(
G4LocatorChangeRecord( G4LocatorChangeRecord::kInsertingMidPoint,
substep_no, eventCount, midPoint) );
}
// Adjust 'SubStartPoint' to calculate the 'did_length' in next loop
//
SubStart_PointVelocity = CurrentA_PointVelocity;
@@ -613,7 +731,8 @@ G4bool G4MultiLevelLocator::EstimateIntersectionPoint(
//
G4ThreeVector Point_A = CurrentA_PointVelocity.GetPosition();
G4ThreeVector Point_B = CurrentB_PointVelocity.GetPosition();
G4ThreeVector PointGe;
GetNavigatorFor()->LocateGlobalPointWithinVolume(Point_A);
G4bool Intersects_AB = IntersectChord(Point_A, Point_B,
NewSafety, previousSafety,
@@ -658,8 +777,21 @@ G4bool G4MultiLevelLocator::EstimateIntersectionPoint(
CurrentA_PointVelocity = *ptrInterMedFT[depth];
CurrentB_PointVelocity = *ptrInterMedFT[depth-1];
G4int errorEndPt = 0; // Default: no error (if not calling CheckAnd...
if (fCheckMode)
{
++eventCount;
G4LocatorChangeRecord chngPop_a( G4LocatorChangeRecord::kLevelPop,
substep_no, eventCount, CurrentA_PointVelocity);
endChangeA.push_back( chngPop_a );
G4LocatorChangeRecord chngPop_b( G4LocatorChangeRecord::kLevelPop,
substep_no, eventCount, CurrentB_PointVelocity);
endChangeB.push_back( chngPop_b );
}
// Ensure that the new endpoints are not further apart in space
// than on the curve due to different errors in the integration
//
G4int errorEndPt = -1;
G4bool recalculatedB= false;
if( driverReIntegrates )
{
@@ -688,45 +820,53 @@ G4bool G4MultiLevelLocator::EstimateIntersectionPoint(
if( CurrentB_PointVelocity.GetCurveLength() < CurrentA_PointVelocity.GetCurveLength() )
errorEndPt = 2;
}
if (fCheckMode)
{
++eventCount;
endChangeB.push_back(
G4LocatorChangeRecord(G4LocatorChangeRecord::kRecalculatedBagn,
substep_no, eventCount, RevisedEndPointFT));
}
}
if( errorEndPt > 1 ) // errorEndPt = 1 is milder, just: len(B)=len(A)
{
std::ostringstream errmsg;
errmsg << "Location: " << MethodName << "- Second-Half" << G4endl;
ReportReversedPoints(errmsg,
CurveStartPointVelocity, CurveEndPointVelocity,
NewSafety, fiEpsilonStep,
CurrentA_PointVelocity, CurrentB_PointVelocity,
SubStart_PointVelocity, CurrentE_Point,
ApproxIntersecPointV, substep_no, substep_no_p, depth);
errmsg << " * Location: " << MethodName << "- Second-Half" << G4endl;
errmsg << " * Recalculated = " << recalculatedB << G4endl; // false
G4Exception(MethodName, "GeomNav0003", FatalException, errmsg);
}
G4ThreeVector Point_A = CurrentA_PointVelocity.GetPosition();
G4ThreeVector Point_B = CurrentB_PointVelocity.GetPosition();
G4ThreeVector Point_B = CurrentB_PointVelocity.GetPosition();
G4ThreeVector PointGi;
GetNavigatorFor()->LocateGlobalPointWithinVolume(Point_A);
G4bool Intersects_AB = IntersectChord(Point_A, Point_B, NewSafety,
previousSafety,
previousSftOrigin, distAB,
PointGe);
PointGi);
if( Intersects_AB )
{
last_AF_intersection = Intersects_AB;
CurrentE_Point = PointGe;
CurrentE_Point = PointGi;
validIntersectP = true; // 'E' has been updated.
G4bool validNormalAB;
NormalAtEntry = GetSurfaceNormal( PointGe, validNormalAB );
validNormalAtE = validNormalAB;
NormalAtEntry = GetSurfaceNormal( PointGi, validNormalAtE );
}
else
{
validIntersectP = false; // No new 'E' chord intersection found
if( depth == 1)
{
{
there_is_no_intersection = true;
}
}
}
depth--;
fin_section_depth[depth] = true;
unfinished = !validIntersectP;
@@ -678,6 +678,9 @@ void G4PropagatorInField::ClearPropagatorState()
fParticleIsLooping = false;
fNoZeroStep = 0;
fSetFieldMgr = false; // Has field-manager been set for the current step?
fEpsilonStep= 1.0e-5; // Relative accuracy of current Step
End_PointAndTangent= G4FieldTrack( G4ThreeVector(0.,0.,0.),
G4ThreeVector(0.,0.,0.),
0.0,0.0,0.0,0.0,0.0);
@@ -686,6 +689,8 @@ void G4PropagatorInField::ClearPropagatorState()
fPreviousSftOrigin= G4ThreeVector(0.,0.,0.);
fPreviousSafety= 0.0;
fNewTrack = true;
}
// ---------------------------------------------------------------------------
@@ -210,16 +210,16 @@ G4double G4RegularNavigation::ComputeStepSkippingEqualMaterials(
.InverseTransformPoint(localPoint);
std::ostringstream message;
message << "G4RegularNavigation::ComputeStepSkippingEqualMaterials()"
<< "Stuck Track: potential geometry or navigation problem."
<< G4endl
<< " Track stuck, moving for more than "
<< ii << " steps" << G4endl
<< "- at point " << pGlobalpoint << G4endl
<< " local direction: " << localDirection << G4endl;
<< "Stuck Track: potential geometry or navigation problem."
<< G4endl
<< " Track stuck, moving for more than "
<< ii << " steps" << G4endl
<< "- at point " << pGlobalpoint << G4endl
<< " local direction: " << localDirection << G4endl;
G4Exception("G4RegularNavigation::ComputeStepSkippingEqualMaterials()",
"GeomRegNav1001",
EventMustBeAborted,
message);
"GeomRegNav1001",
EventMustBeAborted,
message);
}
newStep = voxelBox->DistanceToOut( localPoint, localDirection );
fLastStepWasZero = (newStep<fMinStep);
@@ -231,65 +231,64 @@ G4double G4RegularNavigation::ComputeStepSkippingEqualMaterials(
{
G4ThreeVector pGlobalpoint = history.GetTransform(ide)
.InverseTransformPoint(localPoint);
G4cout << "G4RegularNavigation::ComputeStepSkippingEqualMaterials():"
<< " another 'zero' step, # "
<< fNumberZeroSteps
<< ", at " << pGlobalpoint
<< ", nav-comp-step calls # " << ii
<< ", Step= " << newStep
<< G4endl;
G4cout << "G4RegularNavigation::ComputeStepSkippingEqualMaterials(): another 'zero' step, # "
<< fNumberZeroSteps
<< ", at " << pGlobalpoint
<< ", nav-comp-step calls # " << ii
<< ", Step= " << newStep
<< G4endl;
}
//#endif
if( fNumberZeroSteps > fActionThreshold_NoZeroSteps-1 )
{
// Act to recover this stuck track. Pushing it along direction
//
newStep = std::min(101*kCarTolerance*pow(10,fNumberZeroSteps-2),0.1);
// Act to recover this stuck track. Pushing it along direction
//
newStep = std::min(101*kCarTolerance*std::pow(10,fNumberZeroSteps-2),0.1);
#ifdef G4VERBOSE
if (fWarnPush)
{
if (fWarnPush)
{
G4ThreeVector pGlobalpoint = history.GetTransform(ide)
.InverseTransformPoint(localPoint);
std::ostringstream message;
message.precision(16);
message << "Track stuck or not moving." << G4endl
<< " Track stuck, not moving for "
<< fNumberZeroSteps << " steps" << G4endl
<< "- at point " << pGlobalpoint
<< " (local point " << localPoint << ")" << G4endl
<< " local direction: " << localDirection
<< " Potential geometry or navigation problem !"
<< G4endl
<< " Trying pushing it of " << newStep << " mm ...";
G4Exception("G4RegularNavigation::ComputeStepSkippingEqualMaterials()",
"GeomRegNav1002",
JustWarning,
message,
"Potential overlap in geometry!");
}
std::ostringstream message;
message.precision(16);
message << "Track stuck or not moving." << G4endl
<< " Track stuck, not moving for "
<< fNumberZeroSteps << " steps" << G4endl
<< "- at point " << pGlobalpoint
<< " (local point " << localPoint << ")" << G4endl
<< " local direction: " << localDirection
<< " Potential geometry or navigation problem !"
<< G4endl
<< " Trying pushing it of " << newStep << " mm ...";
G4Exception("G4RegularNavigation::ComputeStepSkippingEqualMaterials()",
"GeomRegNav1002",
JustWarning,
message,
"Potential overlap in geometry!");
}
#endif
}
if( fNumberZeroSteps > fAbandonThreshold_NoZeroSteps-1 )
{
// Must kill this stuck track
//
G4ThreeVector pGlobalpoint = history.GetTransform(ide)
// Must kill this stuck track
//
G4ThreeVector pGlobalpoint = history.GetTransform(ide)
.InverseTransformPoint(localPoint);
std::ostringstream message;
message << "G4RegularNavigation::ComputeStepSkippingEqualMaterials()"
<< "Stuck Track: potential geometry or navigation problem."
<< G4endl
<< " Track stuck, not moving for "
<< fNumberZeroSteps << " steps" << G4endl
<< "- at point " << pGlobalpoint << G4endl
<< " local direction: " << localDirection << G4endl;
G4Exception("G4RegularNavigation::ComputeStepSkippingEqualMaterials()",
"GeomRegNav1003",
EventMustBeAborted,
message);
std::ostringstream message;
message << "G4RegularNavigation::ComputeStepSkippingEqualMaterials()"
<< "Stuck Track: potential geometry or navigation problem."
<< G4endl
<< " Track stuck, not moving for "
<< fNumberZeroSteps << " steps" << G4endl
<< "- at point " << pGlobalpoint << G4endl
<< " local direction: " << localDirection << G4endl;
G4Exception("G4RegularNavigation::ComputeStepSkippingEqualMaterials()",
"GeomRegNav1003",
EventMustBeAborted,
message);
}
}
if( (bFirstStep) && (newStep < currentProposedStepLength) )
{
exiting = true;
@@ -777,26 +777,30 @@ ReportReversedPoints( std::ostringstream& msg,
G4VIntersectionLocator::printStatus( A_PtVel, B_PtVel,
-1.0, NewSafety, substep_no, msg, verboseLevel );
msg << "Error in advancing propagation." << G4endl
<< " Point A (start) is " << A_PtVel << G4endl
<< " Point B (end) is " << B_PtVel << G4endl
<< " Curve distance is " << curveDist << G4endl
<< " The final curve point is NOT further along"
<< " than the original!" << G4endl
<< " Going *backwards* from len(A) = " << A_PtVel.GetCurveLength()
<< " to len(B) = " << B_PtVel.GetCurveLength() << G4endl
<< " Curve distance is " << curveDist / CLHEP::millimeter << " mm "
<< G4endl
<< "The final curve point is not further along"
<< " than the original!" << G4endl;
msg << " Value of fEpsStep= " << epsStep << G4endl;
<< " Point A' (start) is " << A_PtVel << G4endl
<< " Point B' (end) is " << B_PtVel << G4endl;
msg << " fEpsStep= " << epsStep << G4endl << G4endl;
G4int oldprc = msg.precision(20);
msg << " Point A (Curve start) is " << StartPointVel << G4endl
<< " Point B (Curve end) is " << EndPointVel << G4endl
<< " Point A (Current start) is " << A_PtVel << G4endl
<< " Point B (Current end) is " << B_PtVel << G4endl
<< " Point S (Sub start) is " << SubStart_PtVel
<< " Point E (Trial Point) is " << E_Point << G4endl
<< " Point F (Intersection) is " << ApproxIntersecPointV
msg << " In full precision, the position, momentum, E_kin, length, rest mass "
<< " ... are: " << G4endl;
msg << " Point A[0] (Curve start) is " << StartPointVel << G4endl
<< " Point S (Sub start) is " << SubStart_PtVel
<< " Point A' (Current start) is " << A_PtVel << G4endl
<< " Point E (Trial Point) is " << E_Point << G4endl
<< " Point F (Intersection) is " << ApproxIntersecPointV << G4endl
<< " Point B' (Current end) is " << B_PtVel << G4endl
<< " Point B[0] (Curve end) is " << EndPointVel << G4endl
<< G4endl
<< " LocateIntersection parameters are : " << G4endl
<< " Substep no (total) = " << substep_no << G4endl
<< " Substep (depth= " << depth << substep_no_p;
<< " Substep no = " << substep_no_p << " at depth= " << depth;
msg.precision(oldprc);
}