Geant4 Cross Reference

Cross-Referencing   Geant4
Geant4/analysis/hdf5/src/G4Hdf5FileManager.cc

Version: [ ReleaseNotes ] [ 1.0 ] [ 1.1 ] [ 2.0 ] [ 3.0 ] [ 3.1 ] [ 3.2 ] [ 4.0 ] [ 4.0.p1 ] [ 4.0.p2 ] [ 4.1 ] [ 4.1.p1 ] [ 5.0 ] [ 5.0.p1 ] [ 5.1 ] [ 5.1.p1 ] [ 5.2 ] [ 5.2.p1 ] [ 5.2.p2 ] [ 6.0 ] [ 6.0.p1 ] [ 6.1 ] [ 6.2 ] [ 6.2.p1 ] [ 6.2.p2 ] [ 7.0 ] [ 7.0.p1 ] [ 7.1 ] [ 7.1.p1 ] [ 8.0 ] [ 8.0.p1 ] [ 8.1 ] [ 8.1.p1 ] [ 8.1.p2 ] [ 8.2 ] [ 8.2.p1 ] [ 8.3 ] [ 8.3.p1 ] [ 8.3.p2 ] [ 9.0 ] [ 9.0.p1 ] [ 9.0.p2 ] [ 9.1 ] [ 9.1.p1 ] [ 9.1.p2 ] [ 9.1.p3 ] [ 9.2 ] [ 9.2.p1 ] [ 9.2.p2 ] [ 9.2.p3 ] [ 9.2.p4 ] [ 9.3 ] [ 9.3.p1 ] [ 9.3.p2 ] [ 9.4 ] [ 9.4.p1 ] [ 9.4.p2 ] [ 9.4.p3 ] [ 9.4.p4 ] [ 9.5 ] [ 9.5.p1 ] [ 9.5.p2 ] [ 9.6 ] [ 9.6.p1 ] [ 9.6.p2 ] [ 9.6.p3 ] [ 9.6.p4 ] [ 10.0 ] [ 10.0.p1 ] [ 10.0.p2 ] [ 10.0.p3 ] [ 10.0.p4 ] [ 10.1 ] [ 10.1.p1 ] [ 10.1.p2 ] [ 10.1.p3 ] [ 10.2 ] [ 10.2.p1 ] [ 10.2.p2 ] [ 10.2.p3 ] [ 10.3 ] [ 10.3.p1 ] [ 10.3.p2 ] [ 10.3.p3 ] [ 10.4 ] [ 10.4.p1 ] [ 10.4.p2 ] [ 10.4.p3 ] [ 10.5 ] [ 10.5.p1 ] [ 10.6 ] [ 10.6.p1 ] [ 10.6.p2 ] [ 10.6.p3 ] [ 10.7 ] [ 10.7.p1 ] [ 10.7.p2 ] [ 10.7.p3 ] [ 10.7.p4 ] [ 11.0 ] [ 11.0.p1 ] [ 11.0.p2 ] [ 11.0.p3, ] [ 11.0.p4 ] [ 11.1 ] [ 11.1.1 ] [ 11.1.2 ] [ 11.1.3 ] [ 11.2 ] [ 11.2.1 ] [ 11.2.2 ] [ 11.3.0 ]

  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 
 27 // Author: Ivana Hrivnacova, 20/07/2017 (ivana@ipno.in2p3.fr)
 28 
 29 #include "G4Hdf5FileManager.hh"
 30 #include "G4Hdf5HnFileManager.hh"
 31 #include "G4AnalysisManagerState.hh"
 32 #include "G4AnalysisUtilities.hh"
 33 #include "G4AutoLock.hh"
 34 
 35 #include "toolx/hdf5/h2file"
 36 
 37 using namespace G4Analysis;
 38 using namespace tools;
 39 
 40 //using namespace G4Analysis;
 41 
 42 namespace {
 43   //Mutex to lock master manager when closing a file
 44   G4Mutex closeFileMutex = G4MUTEX_INITIALIZER;
 45 }
 46 
 47 //_____________________________________________________________________________
 48 G4Hdf5FileManager::G4Hdf5FileManager(const G4AnalysisManagerState& state)
 49  : G4VTFileManager<G4Hdf5File>(state)
 50 {
 51   // Create helpers defined in the base class
 52   fH1FileManager = std::make_shared<G4Hdf5HnFileManager<histo::h1d>>(this);
 53   fH2FileManager = std::make_shared<G4Hdf5HnFileManager<histo::h2d>>(this);
 54   fH3FileManager = std::make_shared<G4Hdf5HnFileManager<histo::h3d>>(this);
 55   fP1FileManager = std::make_shared<G4Hdf5HnFileManager<histo::p1d>>(this);
 56   fP2FileManager = std::make_shared<G4Hdf5HnFileManager<histo::p2d>>(this);
 57 }
 58 
 59 //
 60 // private methods
 61 //
 62 
 63 //_____________________________________________________________________________
 64 hid_t G4Hdf5FileManager::CreateDirectory(hid_t& file,
 65   const G4String& directoryName, const G4String& objectType)
 66 {
 67 // Method for both histograms and ntuples directories.
 68 
 69   // return if no file provided
 70   if (file < 0) return kInvalidId;
 71 
 72   // use default directory name if not provided
 73   auto newDirectoryName = directoryName;
 74   if ( newDirectoryName == "" ) {
 75       newDirectoryName = fgkDefaultDirectoryName;
 76       newDirectoryName += "_";
 77       newDirectoryName += objectType;
 78   }
 79 
 80   Message(kVL4, "create", "directory for " + objectType, newDirectoryName);
 81 
 82   auto success = true;
 83 
 84   // create directory
 85   auto directory = toolx_H5Gcreate(file, newDirectoryName, 0);
 86        // 0 seems to be an optional parameter. The web doc does not say what should
 87        // be the default value but 0 is what is found in examples, and in the code, if we pass 0, clearly some
 88        // default value is taken.
 89   if ( directory < 0 ) {
 90     Warn("Cannot create directory " + directoryName,
 91       fkClass, "CreateDirectory");
 92     success = false;
 93   }
 94   else {
 95     // write atb (header?)
 96     auto result = toolx::hdf5::write_atb(directory, "type", "directory");
 97     if ( !result) {
 98       Warn("Write_atb class failed for " + directoryName,
 99         fkClass, "CreateDirectory");
100       success = false;
101     }
102   }
103 
104   Message(kVL2, "create", "directory for " + objectType, newDirectoryName, success);
105 
106   return directory;
107 }
108 
109 //_____________________________________________________________________________
110 G4String G4Hdf5FileManager::GetNtupleFileName(Hdf5NtupleDescription* ntupleDescription)
111 {
112   // get ntuple file name
113   auto ntupleFileName = ntupleDescription->GetFileName();
114   if (ntupleFileName.size() != 0u) {
115     // update filename per object per thread
116     ntupleFileName = GetTnFileName(ntupleFileName, GetFileType());
117   }
118   else {
119     // get default file name
120     ntupleFileName = GetFullFileName();
121   }
122   return ntupleFileName;
123 }
124 
125 //
126 // protected methods
127 //
128 
129 //_____________________________________________________________________________
130 std::shared_ptr<G4Hdf5File> G4Hdf5FileManager::CreateFileImpl(const G4String& fileName)
131 {
132   // create a new file
133   hid_t file = ::H5Fcreate(fileName, H5F_ACC_TRUNC, H5P_DEFAULT, H5P_DEFAULT);
134 
135   // Do nothing if there is no file
136   // (the error should be handled by caller)
137   if ( file < 0 ) {
138     Warn("::H5Fcreate failed " + fileName, fkClass, "CreateFileImpl");
139     return std::make_shared<G4Hdf5File>(-1, -1, -1);
140   }
141 
142   // create a header with general infos
143   if(!toolx::hdf5::write_header(file)) {
144     Warn("toolx::hdf5::write_header() failed for " + fileName,
145       fkClass, "CreateFileImpl");
146     return std::make_shared<G4Hdf5File>(-1, -1, -1);
147   }
148 
149   // create histo directory
150   auto hdirectory
151     = CreateDirectory(file, fHistoDirectoryName, "histograms");
152   if ( hdirectory < 0 ) {
153     // Warning is issued in CreateDirectory
154     return std::make_shared<G4Hdf5File>(-1, -1, -1);
155   }
156 
157   // create ntuple directory
158   auto ndirectory
159     = CreateDirectory(file, fNtupleDirectoryName, "ntuples");
160   if ( ndirectory < 0 ) {
161     // Warnin is issued in CreateDirectory
162     return std::make_shared<G4Hdf5File>(-1, -1, -1);
163   }
164 
165   return std::make_shared<G4Hdf5File>(file, hdirectory, ndirectory);
166 }
167 
168 //_____________________________________________________________________________
169 G4bool G4Hdf5FileManager::WriteFileImpl(std::shared_ptr<G4Hdf5File> /*file*/)
170 {
171   // Nothing to be done here
172   return true;
173 }
174 
175 //_____________________________________________________________________________
176 G4bool G4Hdf5FileManager::CloseFileImpl(std::shared_ptr<G4Hdf5File> file)
177 {
178   if ( ! file ) return false;
179 
180   G4AutoLock lock(&closeFileMutex);
181 
182   ::H5Gclose(std::get<1>(*file));
183   ::H5Gclose(std::get<2>(*file));
184   ::H5Fclose(std::get<0>(*file));
185 
186   lock.unlock();
187 
188   return true;
189 }
190 
191 //
192 // public methods
193 //
194 
195 //_____________________________________________________________________________
196 G4bool G4Hdf5FileManager::OpenFile(const G4String& fileName)
197 {
198   // Keep file name
199   fFileName = fileName;
200   auto name = GetFullFileName();
201 
202   if ( fFile ) {
203     Warn("File " + fileName + " already exists.", fkClass, "OpenFile");
204     fFile.reset();
205   }
206 
207   // create new file
208   fFile = CreateTFile(name);
209   if ( ! fFile ) {
210     Warn("Failed to create file " + fileName, fkClass, "OpenFile");
211     return false;
212   }
213 
214   LockDirectoryNames();
215   fIsOpenFile = true;
216 
217   return true;
218 }
219 
220 //_____________________________________________________________________________
221 G4bool G4Hdf5FileManager::CreateNtupleFile(
222   Hdf5NtupleDescription* ntupleDescription)
223 {
224   // get ntuple file name per object
225   auto ntupleFileName = GetNtupleFileName(ntupleDescription);
226 
227   auto file = GetTFile(ntupleFileName, false);
228   if (! file) {
229     file = CreateTFile(ntupleFileName);
230   }
231   ntupleDescription->SetFile(file);
232 
233   return (ntupleDescription->GetFile() != nullptr);
234 }
235 
236 //_____________________________________________________________________________
237 G4bool G4Hdf5FileManager::CloseNtupleFile(
238   Hdf5NtupleDescription* ntupleDescription)
239 {
240   // Notify not empty file
241   auto ntupleFileName = GetNtupleFileName(ntupleDescription);
242   auto result = SetIsEmpty(ntupleFileName, ! ntupleDescription->GetHasFill());
243 
244   // Ntuple files are registered in file manager map.
245   // they will be closed with CloseFiles() calls
246   ntupleDescription->GetFile().reset();
247 
248   return result;
249 }
250 
251 //_____________________________________________________________________________
252 hid_t G4Hdf5FileManager::GetHistoDirectory() const
253 {
254   if ( ! fFile ) return kInvalidId;
255 
256   return std::get<1>(*fFile);
257 }
258 
259 //_____________________________________________________________________________
260 hid_t G4Hdf5FileManager::GetNtupleDirectory() const
261 {
262   if ( ! fFile ) return kInvalidId;
263 
264   return std::get<2>(*fFile);
265 }
266