Geant4-11
Public Types | Public Member Functions | Private Member Functions
G4TemplateAutoLock< _Mutex_t > Class Template Reference

#include <G4AutoLock.hh>

Inheritance diagram for G4TemplateAutoLock< _Mutex_t >:

Public Types

typedef unique_lock_t::mutex_type mutex_type
 
typedef G4TemplateAutoLock< _Mutex_t > this_type
 
typedef std::unique_lock< _Mutex_t > unique_lock_t
 

Public Member Functions

 G4TemplateAutoLock (mutex_type &_mutex)
 
template<typename Rep , typename Period >
 G4TemplateAutoLock (mutex_type &_mutex, const std::chrono::duration< Rep, Period > &_timeout_duration)
 
template<typename Clock , typename Duration >
 G4TemplateAutoLock (mutex_type &_mutex, const std::chrono::time_point< Clock, Duration > &_timeout_time)
 
 G4TemplateAutoLock (mutex_type &_mutex, std::adopt_lock_t)
 
 G4TemplateAutoLock (mutex_type &_mutex, std::defer_lock_t _lock) noexcept
 
 G4TemplateAutoLock (mutex_type &_mutex, std::try_to_lock_t)
 
 G4TemplateAutoLock (mutex_type *_mutex)
 
 G4TemplateAutoLock (mutex_type *_mutex, std::adopt_lock_t)
 
 G4TemplateAutoLock (mutex_type *_mutex, std::defer_lock_t _lock) noexcept
 
 G4TemplateAutoLock (mutex_type *_mutex, std::try_to_lock_t)
 
void lock ()
 
bool owns_lock () const noexcept
 
void swap (this_type &other) noexcept
 
bool try_lock ()
 
template<typename Rep , typename Period >
bool try_lock_for (const std::chrono::duration< Rep, Period > &)
 
template<typename Clock , typename Duration >
bool try_lock_until (const std::chrono::time_point< Clock, Duration > &)
 
void unlock ()
 

Private Member Functions

void _lock_deferred ()
 
template<typename Rep , typename Period >
void _lock_deferred (const std::chrono::duration< Rep, Period > &_timeout_duration)
 
template<typename Clock , typename Duration >
void _lock_deferred (const std::chrono::time_point< Clock, Duration > &_timeout_time)
 
template<typename _Tp = _Mutex_t, typename std::enable_if< _is_stand_mutex(_Tp), int >::type = 0>
std::string GetTypeString ()
 
template<typename _Tp = _Mutex_t, typename std::enable_if< _is_recur_mutex(_Tp), int >::type = 0>
std::string GetTypeString ()
 
template<typename _Tp = _Mutex_t, typename std::enable_if< _is_other_mutex(_Tp), int >::type = 0>
std::string GetTypeString ()
 
void PrintLockErrorMessage (std::system_error &e)
 
template<typename _Tp >
void suppress_unused_variable (const _Tp &)
 

Detailed Description

template<typename _Mutex_t>
class G4TemplateAutoLock< _Mutex_t >

============================================================================//

void print_threading() { #ifdef G4MULTITHREADED std::cout << "\nUsing G4MULTITHREADED version..." << std::endl; #else std::cout << "\nUsing G4SERIAL version..." << std::endl; #endif }

============================================================================//

typedef std::unique_lock<std::mutex> unique_lock_t; functions for casting G4AutoLock to std::unique_lock to demonstrate that G4AutoLock is NOT polymorphic void as_unique_lock(unique_lock_t* lock) { lock->lock(); } void as_unique_unlock(unique_lock_t* lock) { lock->unlock(); }

============================================================================//

void run(const uint64_t& n) { sync the threads a bit std::this_thread::sleep_for(std::chrono::milliseconds(10));

get two mutexes to avoid deadlock when l32 actually locks G4AutoLock l32(G4TypeMutex<int32_t>(), std::defer_lock); G4AutoLock l64(G4TypeMutex<int64_t>(), std::defer_lock);

when serial: will not execute std::unique_lock::lock() because it overrides the member function l32.lock(); regardless of serial or MT: will execute std::unique_lock::lock() because std::unique_lock::lock() is not virtual as_unique_lock(&l64);

std::cout << "Running iteration " << n << "..." << std::endl; }

============================================================================// execute some work template <typename thread_type = std::thread>> void exec(uint64_t n) { get two mutexes to avoid deadlock when l32 actually locks G4AutoLock l32(G4TypeMutex<int32_t>(), std::defer_lock); G4AutoLock l64(G4TypeMutex<int64_t>(), std::defer_lock);

std::vector<thread_type*> threads(n, nullptr); for(uint64_t i = 0; i < n; ++i) { threads[i] = new thread_type(); (threads[i]) = std::move(thread_type(run, i)); }

when serial: will not execute std::unique_lock::lock() because it overrides the member function l32.lock(); regardless of serial or MT: will execute std::unique_lock::lock() because std::unique_lock::lock() is not virtual as_unique_lock(&l64);

std::cout << "Joining..." << std::endl;

when serial: will not execute std::unique_lock::unlock() because it overrides the member function l32.unlock(); regardless of serial or MT: will execute std::unique_lock::unlock() because std::unique_lock::unlock() is not virtual as_unique_unlock(&l64);

NOTE ABOUT UNLOCKS: in MT, commenting out either l32.unlock(); or as_unique_unlock(&l64); creates a deadlock; in serial, commenting out as_unique_unlock(&l64); creates a deadlock but commenting out l32.unlock(); does not

clean up and join for(uint64_t i = 0; i < n; ++i) { threads[i]->join(); delete threads[i]; } threads.clear(); }

============================================================================//

int main() { print_threading();

uint64_t n = 30; std::cout << "\nRunning with real threads...\n" << std::endl; exec<std::thread>(n); std::cout << "\nRunning with fake threads...\n" << std::endl; exec<G4DummyThread>(n);

}

Definition at line 273 of file G4AutoLock.hh.

Member Typedef Documentation

◆ mutex_type

template<typename _Mutex_t >
typedef unique_lock_t::mutex_type G4TemplateAutoLock< _Mutex_t >::mutex_type

Definition at line 281 of file G4AutoLock.hh.

◆ this_type

template<typename _Mutex_t >
typedef G4TemplateAutoLock<_Mutex_t> G4TemplateAutoLock< _Mutex_t >::this_type

Definition at line 280 of file G4AutoLock.hh.

◆ unique_lock_t

template<typename _Mutex_t >
typedef std::unique_lock<_Mutex_t> G4TemplateAutoLock< _Mutex_t >::unique_lock_t

Definition at line 279 of file G4AutoLock.hh.

Constructor & Destructor Documentation

◆ G4TemplateAutoLock() [1/10]

template<typename _Mutex_t >
G4TemplateAutoLock< _Mutex_t >::G4TemplateAutoLock ( mutex_type _mutex)
inline

Definition at line 292 of file G4AutoLock.hh.

293 : unique_lock_t(_mutex, std::defer_lock)
294 {
295 // call termination-safe locking. if serial, this call has no effect
297 }
std::unique_lock< _Mutex_t > unique_lock_t
Definition: G4AutoLock.hh:279

References G4TemplateAutoLock< _Mutex_t >::_lock_deferred().

◆ G4TemplateAutoLock() [2/10]

template<typename _Mutex_t >
template<typename Rep , typename Period >
G4TemplateAutoLock< _Mutex_t >::G4TemplateAutoLock ( mutex_type _mutex,
const std::chrono::duration< Rep, Period > &  _timeout_duration 
)
inline

Definition at line 304 of file G4AutoLock.hh.

307 : unique_lock_t(_mutex, std::defer_lock)
308 {
309 // call termination-safe locking. if serial, this call has no effect
310 _lock_deferred(_timeout_duration);
311 }

References G4TemplateAutoLock< _Mutex_t >::_lock_deferred().

◆ G4TemplateAutoLock() [3/10]

template<typename _Mutex_t >
template<typename Clock , typename Duration >
G4TemplateAutoLock< _Mutex_t >::G4TemplateAutoLock ( mutex_type _mutex,
const std::chrono::time_point< Clock, Duration > &  _timeout_time 
)
inline

Definition at line 318 of file G4AutoLock.hh.

321 : unique_lock_t(_mutex, std::defer_lock)
322 {
323 // call termination-safe locking. if serial, this call has no effect
324 _lock_deferred(_timeout_time);
325 }

References G4TemplateAutoLock< _Mutex_t >::_lock_deferred().

◆ G4TemplateAutoLock() [4/10]

template<typename _Mutex_t >
G4TemplateAutoLock< _Mutex_t >::G4TemplateAutoLock ( mutex_type _mutex,
std::defer_lock_t  _lock 
)
inlinenoexcept

Definition at line 328 of file G4AutoLock.hh.

329 : unique_lock_t(_mutex, _lock)
330 {}

◆ G4TemplateAutoLock() [5/10]

template<typename _Mutex_t >
G4TemplateAutoLock< _Mutex_t >::G4TemplateAutoLock ( mutex_type _mutex,
std::try_to_lock_t   
)
inline

Definition at line 349 of file G4AutoLock.hh.

350 : unique_lock_t(_mutex, std::defer_lock)
351 {}

◆ G4TemplateAutoLock() [6/10]

template<typename _Mutex_t >
G4TemplateAutoLock< _Mutex_t >::G4TemplateAutoLock ( mutex_type _mutex,
std::adopt_lock_t   
)
inline

Definition at line 354 of file G4AutoLock.hh.

355 : unique_lock_t(_mutex, std::defer_lock)
356 {}

◆ G4TemplateAutoLock() [7/10]

template<typename _Mutex_t >
G4TemplateAutoLock< _Mutex_t >::G4TemplateAutoLock ( mutex_type _mutex)
inline

Definition at line 364 of file G4AutoLock.hh.

365 : unique_lock_t(*_mutex, std::defer_lock)
366 {
367 // call termination-safe locking. if serial, this call has no effect
369 }

References G4TemplateAutoLock< _Mutex_t >::_lock_deferred().

◆ G4TemplateAutoLock() [8/10]

template<typename _Mutex_t >
G4TemplateAutoLock< _Mutex_t >::G4TemplateAutoLock ( mutex_type _mutex,
std::defer_lock_t  _lock 
)
inlinenoexcept

Definition at line 371 of file G4AutoLock.hh.

372 : unique_lock_t(*_mutex, _lock)
373 {}

◆ G4TemplateAutoLock() [9/10]

template<typename _Mutex_t >
G4TemplateAutoLock< _Mutex_t >::G4TemplateAutoLock ( mutex_type _mutex,
std::try_to_lock_t   
)
inline

Definition at line 387 of file G4AutoLock.hh.

388 : unique_lock_t(*_mutex, std::defer_lock)
389 {}

◆ G4TemplateAutoLock() [10/10]

template<typename _Mutex_t >
G4TemplateAutoLock< _Mutex_t >::G4TemplateAutoLock ( mutex_type _mutex,
std::adopt_lock_t   
)
inline

Definition at line 391 of file G4AutoLock.hh.

392 : unique_lock_t(*_mutex, std::defer_lock)
393 {}

Member Function Documentation

◆ _lock_deferred() [1/3]

template<typename _Mutex_t >
void G4TemplateAutoLock< _Mutex_t >::_lock_deferred ( )
inlineprivate

Definition at line 494 of file G4AutoLock.hh.

495 {
496#if defined(G4MULTITHREADED)
497 try
498 {
499 this->unique_lock_t::lock();
500 } catch(std::system_error& e)
501 {
503 }
504#endif
505 }
void PrintLockErrorMessage(std::system_error &e)
Definition: G4AutoLock.hh:554

References G4TemplateAutoLock< _Mutex_t >::PrintLockErrorMessage().

Referenced by G4TemplateAutoLock< _Mutex_t >::G4TemplateAutoLock().

◆ _lock_deferred() [2/3]

template<typename _Mutex_t >
template<typename Rep , typename Period >
void G4TemplateAutoLock< _Mutex_t >::_lock_deferred ( const std::chrono::duration< Rep, Period > &  _timeout_duration)
inlineprivate

Definition at line 513 of file G4AutoLock.hh.

515 {
516#if defined(G4MULTITHREADED)
517 try
518 {
519 this->unique_lock_t::try_lock_for(_timeout_duration);
520 } catch(std::system_error& e)
521 {
523 }
524#else
525 suppress_unused_variable(_timeout_duration);
526#endif
527 }
void suppress_unused_variable(const _Tp &)
Definition: G4AutoLock.hh:471

References G4TemplateAutoLock< _Mutex_t >::PrintLockErrorMessage(), and G4TemplateAutoLock< _Mutex_t >::suppress_unused_variable().

◆ _lock_deferred() [3/3]

template<typename _Mutex_t >
template<typename Clock , typename Duration >
void G4TemplateAutoLock< _Mutex_t >::_lock_deferred ( const std::chrono::time_point< Clock, Duration > &  _timeout_time)
inlineprivate

Definition at line 535 of file G4AutoLock.hh.

537 {
538#if defined(G4MULTITHREADED)
539 try
540 {
541 this->unique_lock_t::try_lock_until(_timeout_time);
542 } catch(std::system_error& e)
543 {
545 }
546#else
547 suppress_unused_variable(_timeout_time);
548#endif
549 }

References G4TemplateAutoLock< _Mutex_t >::PrintLockErrorMessage(), and G4TemplateAutoLock< _Mutex_t >::suppress_unused_variable().

◆ GetTypeString() [1/3]

template<typename _Mutex_t >
template<typename _Tp = _Mutex_t, typename std::enable_if< _is_stand_mutex(_Tp), int >::type = 0>
std::string G4TemplateAutoLock< _Mutex_t >::GetTypeString ( )
inlineprivate

Definition at line 445 of file G4AutoLock.hh.

446 {
447 return "G4AutoLock<G4Mutex>";
448 }

◆ GetTypeString() [2/3]

template<typename _Mutex_t >
template<typename _Tp = _Mutex_t, typename std::enable_if< _is_recur_mutex(_Tp), int >::type = 0>
std::string G4TemplateAutoLock< _Mutex_t >::GetTypeString ( )
inlineprivate

Definition at line 452 of file G4AutoLock.hh.

453 {
454 return "G4AutoLock<G4RecursiveMutex>";
455 }

◆ GetTypeString() [3/3]

template<typename _Mutex_t >
template<typename _Tp = _Mutex_t, typename std::enable_if< _is_other_mutex(_Tp), int >::type = 0>
std::string G4TemplateAutoLock< _Mutex_t >::GetTypeString ( )
inlineprivate

Definition at line 459 of file G4AutoLock.hh.

460 {
461 return "G4AutoLock<UNKNOWN_MUTEX>";
462 }

◆ lock()

template<typename _Mutex_t >
void G4TemplateAutoLock< _Mutex_t >::lock ( )
inline

◆ owns_lock()

template<typename _Mutex_t >
bool G4TemplateAutoLock< _Mutex_t >::owns_lock ( ) const
inlinenoexcept

Definition at line 427 of file G4AutoLock.hh.

427{ return false; }

◆ PrintLockErrorMessage()

template<typename _Mutex_t >
void G4TemplateAutoLock< _Mutex_t >::PrintLockErrorMessage ( std::system_error &  e)
inlineprivate

Definition at line 554 of file G4AutoLock.hh.

555 {
556 // use std::cout/std::endl to avoid include dependencies
557 using std::cout;
558 using std::endl;
559 // the error that comes from locking an unavailable mutex
560#if defined(G4VERBOSE)
561 cout << "Non-critical error: mutex lock failure in "
562 << GetTypeString<mutex_type>() << ". "
563 << "If the app is terminating, Geant4 failed to "
564 << "delete an allocated resource and a Geant4 destructor is "
565 << "being called after the statics were destroyed. \n\t--> "
566 << "Exception: [code: " << e.code() << "] caught: " << e.what()
567 << endl;
568#else
570#endif
571 }

References G4TemplateAutoLock< _Mutex_t >::suppress_unused_variable().

Referenced by G4TemplateAutoLock< _Mutex_t >::_lock_deferred().

◆ suppress_unused_variable()

template<typename _Mutex_t >
template<typename _Tp >
void G4TemplateAutoLock< _Mutex_t >::suppress_unused_variable ( const _Tp &  )
inlineprivate

◆ swap()

template<typename _Mutex_t >
void G4TemplateAutoLock< _Mutex_t >::swap ( this_type other)
inlinenoexcept

Definition at line 426 of file G4AutoLock.hh.

426{ std::swap(*this, other); }

◆ try_lock()

template<typename _Mutex_t >
bool G4TemplateAutoLock< _Mutex_t >::try_lock ( )
inline

Definition at line 412 of file G4AutoLock.hh.

412{ return true; }

◆ try_lock_for()

template<typename _Mutex_t >
template<typename Rep , typename Period >
bool G4TemplateAutoLock< _Mutex_t >::try_lock_for ( const std::chrono::duration< Rep, Period > &  )
inline

Definition at line 415 of file G4AutoLock.hh.

416 {
417 return true;
418 }

◆ try_lock_until()

template<typename _Mutex_t >
template<typename Clock , typename Duration >
bool G4TemplateAutoLock< _Mutex_t >::try_lock_until ( const std::chrono::time_point< Clock, Duration > &  )
inline

Definition at line 421 of file G4AutoLock.hh.

422 {
423 return true;
424 }

◆ unlock()

template<typename _Mutex_t >
void G4TemplateAutoLock< _Mutex_t >::unlock ( )
inline

Definition at line 411 of file G4AutoLock.hh.

411{}

Referenced by G4RootPNtupleManager::AddNtupleRow(), G4ConvergenceTester::AddScore(), G4VDecayChannel::CheckAndFillDaughters(), G4VDecayChannel::CheckAndFillParent(), G4DNAMolecularMaterial::Clear(), G4GeometryWorkspace::CloneReplicaSolid(), G4Hdf5AnalysisManager::CloseFileImpl(), G4Hdf5FileManager::CloseFileImpl(), G4PenelopeGammaConversionModel::ComputeCrossSectionPerAtom(), G4PenelopePhotoElectricModel::ComputeCrossSectionPerAtom(), G4PenelopeRayleighModel::ComputeCrossSectionPerAtom(), G4PenelopeRayleighModelMI::ComputeCrossSectionPerAtom(), G4PenelopeIonisationModel::ComputeDEDXPerVolume(), G4ImportanceConfigurator::Configure(), G4WorkerRunManager::ConstructScoringWorlds(), G4PDefManager::CreateSubInstance(), G4VUPLSplitter< T >::CreateSubInstance(), G4PenelopeIonisationModel::CrossSectionPerVolume(), G4DNAChemistryManager::DeleteInstance(), G4MolecularConfiguration::DeleteManager(), G4GeometryWorkspace::DestroyWorkspace(), G4ChipsKaonMinusElasticXS::G4ChipsKaonMinusElasticXS(), G4ChipsKaonPlusElasticXS::G4ChipsKaonPlusElasticXS(), G4ChipsKaonPlusInelasticXS::G4ChipsKaonPlusInelasticXS(), G4MTRunManagerKernel::G4MTRunManagerKernel(), G4SPSEneDistribution::GenEpnHistEnergies(), G4SPSEneDistribution::GenerateBbodyEnergies(), G4SPSEneDistribution::GenerateCPowEnergies(), G4SPSAngDistribution::GenerateUserDefPhi(), G4SPSAngDistribution::GenerateUserDefTheta(), G4SPSEneDistribution::GenUserHistEnergies(), G4PenelopeBremsstrahlungModel::GetCrossSectionTableForCouple(), G4LatticeManager::GetLatticeManager(), G4MolecularConfiguration::GetManager(), G4CutTubs::GetPointOnSurface(), G4Ellipsoid::GetPointOnSurface(), G4GenericPolycone::GetPointOnSurface(), G4Polycone::GetPointOnSurface(), G4Polyhedra::GetPointOnSurface(), G4BooleanSolid::GetPolyhedron(), G4MultiUnion::GetPolyhedron(), G4CSGSolid::GetPolyhedron(), G4Ellipsoid::GetPolyhedron(), G4EllipticalCone::GetPolyhedron(), G4EllipticalTube::GetPolyhedron(), G4GenericTrap::GetPolyhedron(), G4Hype::GetPolyhedron(), G4Paraboloid::GetPolyhedron(), G4TessellatedSolid::GetPolyhedron(), G4Tet::GetPolyhedron(), G4TwistedTubs::GetPolyhedron(), G4VCSGfaceted::GetPolyhedron(), G4VTwistedFaceted::GetPolyhedron(), G4UrbanMscModel::Initialise(), G4BoldyshevTripletModel::InitialiseForElement(), G4JAEAElasticScatteringModel::InitialiseForElement(), G4JAEAPolarizedElasticScatteringModel::InitialiseForElement(), G4LivermoreBremsstrahlungModel::InitialiseForElement(), G4LivermoreComptonModel::InitialiseForElement(), G4LivermoreGammaConversion5DModel::InitialiseForElement(), G4LivermoreGammaConversionModel::InitialiseForElement(), G4LivermoreNuclearGammaConversionModel::InitialiseForElement(), G4LivermorePolarizedComptonModel::InitialiseForElement(), G4LivermorePolarizedGammaConversionModel::InitialiseForElement(), G4LivermorePolarizedRayleighModel::InitialiseForElement(), G4LivermoreRayleighModel::InitialiseForElement(), G4LowEPComptonModel::InitialiseForElement(), G4LowEPPolarizedComptonModel::InitialiseForElement(), G4DNAMolecularMaterial::Initialize(), G4RunManagerKernel::InitializePhysics(), G4MolecularConfiguration::G4MolecularConfigurationManager::Insert(), G4DNAChemistryManager::Instance(), G4InuclNuclei::makeNuclearFragment(), G4ITTrackHolder::MasterInstance(), G4AccumulableManager::Merge(), G4RootPNtupleManager::Merge(), G4Hdf5AnalysisManager::OpenFileImpl(), G4ITTrackHolder::PushToMaster(), G4LatticeManager::RegisterLattice(), G4PenelopeGammaConversionModel::SampleSecondaries(), G4PenelopeRayleighModel::SampleSecondaries(), G4PenelopeRayleighModelMI::SampleSecondaries(), G4ScoringProbe::SetupGeometry(), G4GeomSplitter< T >::SlaveCopySubInstanceArray(), G4MTRunManagerKernel::StartThread(), mutex::unlock(), G4LogicalVolumeStore::UpdateMap(), G4PhysicalVolumeStore::UpdateMap(), G4RegionStore::UpdateMap(), and G4SolidStore::UpdateMap().


The documentation for this class was generated from the following file: