Geant4 11.4.0
Toolkit for the simulation of the passage of particles through matter
Loading...
Searching...
No Matches
G4GeomSplitter.hh
Go to the documentation of this file.
1//
2// ********************************************************************
3// * License and Disclaimer *
4// * *
5// * The Geant4 software is copyright of the Copyright Holders of *
6// * the Geant4 Collaboration. It is provided under the terms and *
7// * conditions of the Geant4 Software License, included in the file *
8// * LICENSE and available at http://cern.ch/geant4/license . These *
9// * include a list of copyright holders. *
10// * *
11// * Neither the authors of this software system, nor their employing *
12// * institutes,nor the agencies providing financial support for this *
13// * work make any representation or warranty, express or implied, *
14// * regarding this software system or assume any liability for its *
15// * use. Please see the license in the file LICENSE and URL above *
16// * for the full disclaimer and the limitation of liability. *
17// * *
18// * This code implementation is the result of the scientific and *
19// * technical work of the GEANT4 collaboration. *
20// * By using, copying, modifying or distributing the software (or *
21// * any work based on the software) you agree to acknowledge its *
22// * use in resulting scientific publications, and indicate your *
23// * acceptance of all terms of the Geant4 Software license. *
24// ********************************************************************
25//
26// G4GeomSplitter
27//
28// Class description:
29//
30// Utility template class for splitting of RW data for thread-safety from
31// classes: G4LogicalVolume, G4Region, G4VPhysicalVolume, G4PolyconeSide
32// G4PolyhedraSide, G4PVReplica.
33
34// Author: Xin Dong (Northeastern Univ.), 01.25.2009 - Initial version
35// ------------------------------------------------------------------------
36#ifndef G4GEOMSPLITTER_HH
37#define G4GEOMSPLITTER_HH
38
39#include "globals.hh"
40#include "geomwdefs.hh"
41#include "G4AutoLock.hh"
42
43/**
44 * @brief G4GeomSplitter is an utility class for splitting of R/W data
45 * for thread-safety from geometry classes.
46 * T is the private data from the object to be split
47 */
48
49template <class T>
51{
52 public:
53
54 /**
55 * Constructor.
56 */
58 : sharedOffset(nullptr)
59 {
60 G4MUTEXINIT(mutex);
61 }
62
63 /**
64 * Reallocates data for a given 'size'.
65 */
67 {
68 totalspace = size;
69 return (T *) std::realloc(offset, totalspace * sizeof(T));
70 }
71
72 /**
73 * Invoked by the master or work thread to create a new subinstance
74 * whenever a new split class instance is created.
75 */
77 {
78 G4AutoLock l(&mutex);
79 ++totalobj;
80 if (totalobj > totalspace)
81 {
82 offset = Reallocate(totalspace+512);
83 if (offset == nullptr)
84 {
85 G4Exception("G4GeomSPlitter::CreateSubInstance()",
86 "OutOfMemory", FatalException, "Cannot malloc space!");
87 }
88 sharedOffset = offset;
89 }
90 return (totalobj - 1);
91 }
92
93 /**
94 * Utility to copy data from master in memory.
95 */
97 {
98 G4AutoLock l(&mutex);
99 std::memcpy(offset, sharedOffset, totalspace * sizeof(T));
100 }
101
102 /**
103 * Invoked by each worker thread to copy all the subinstance array
104 * from the master thread.
105 */
107 {
108 G4AutoLock l(&mutex);
109 if (offset != nullptr) { return; }
110 offset = Reallocate(totalspace);
111 if (offset == nullptr)
112 {
113 G4Exception("G4GeomSplitter::SlaveCopySubInstanceArray()",
114 "OutOfMemory", FatalException, "Cannot malloc space!");
115 }
116 l.unlock();
118 }
119
120 /**
121 * Invoked by each worker thread to create the subinstance array and
122 * initialize each subinstance using a particular method defined by
123 * the subclass.
124 */
126 {
127 G4AutoLock l(&mutex);
128 if (offset != nullptr) { return; }
129 offset = Reallocate(totalspace);
130
131 if (offset == nullptr)
132 {
133 G4Exception("G4GeomSplitter::SlaveInitializeSubInstance()",
134 "OutOfMemory", FatalException, "Cannot malloc space!");
135 }
136
137 for (G4int i=0 ; i<totalspace; ++i)
138 {
139 offset[i].initialize();
140 }
141 }
142
143 /**
144 * Invoked by each worker thread at start of a run (2nd or later)
145 * to copy again all the subinstance array from the master thread.
146 * To cope with user's changes in Geometry - e.g. change of material
147 * in a volume.
148 */
150 {
151 if (offset == nullptr)
152 {
154 G4Exception("G4GeomSPlitter::SlaveReCopySubInstance()",
155 "MissingInitialisation", JustWarning,
156 "Must be called after Initialisation or first Copy.");
157 }
159 }
160
161 /**
162 * Invoked by all threads to free the subinstance array.
163 */
165 {
166 if (offset == nullptr) { return; }
167 std::free( offset );
168 offset = nullptr;
169 }
170
171 // Extension - to allow sharing of workspaces
172
173 /**
174 * Returns a pointer to the split data.
175 */
176 T* GetOffset() { return offset; }
177
178 /**
179 * Uses recycled work area - which was created previously.
180 */
181 void UseWorkArea( T* newOffset )
182 {
183 if( (offset!=nullptr) && (offset!=newOffset) )
184 {
185 G4Exception("G4GeomSplitter::UseWorkspace()",
186 "TwoWorkspaces", FatalException,
187 "Thread already has workspace - cannot use another.");
188 }
189 offset = newOffset;
190 }
191
192 /**
193 * Detaches the current thread from this location.
194 * The object which calls this method is responsible for it.
195 */
197 {
198 T* offsetRet = offset;
199 offset = nullptr;
200 return offsetRet;
201 }
202
203 public:
204
206
207 private:
208
209 G4int totalobj{0};
210 G4int totalspace{0};
211 T* sharedOffset;
212 G4Mutex mutex;
213};
214
215template <typename T> G4ThreadLocal T* G4GeomSplitter<T>::offset = nullptr;
216
217#endif
G4TemplateAutoLock< G4Mutex > G4AutoLock
@ JustWarning
@ FatalException
void G4Exception(const char *originOfException, const char *exceptionCode, G4ExceptionSeverity severity, const char *description)
std::mutex G4Mutex
#define G4MUTEXINIT(mutex)
int G4int
Definition G4Types.hh:85
void SlaveReCopySubInstanceArray()
void SlaveInitializeSubInstance()
static G4GEOM_DLL G4ThreadLocal G4LVData * offset
G4int CreateSubInstance()
void SlaveCopySubInstanceArray()
T * Reallocate(G4int size)
void CopyMasterContents()
void UseWorkArea(T *newOffset)
#define G4GEOM_DLL
Definition geomwdefs.hh:45
#define G4ThreadLocal
Definition tls.hh:77