|
||||
File indexing completed on 2025-01-18 10:10:43
0001 /// \file ROOT/RFile.hxx 0002 /// \ingroup Base ROOT7 0003 /// \author Axel Naumann <axel@cern.ch> 0004 /// \date 2015-07-31 0005 /// \warning This is part of the ROOT 7 prototype! It will change without notice. It might trigger earthquakes. Feedback 0006 /// is welcome! 0007 0008 /************************************************************************* 0009 * Copyright (C) 1995-2016, Rene Brun and Fons Rademakers. * 0010 * All rights reserved. * 0011 * * 0012 * For the licensing terms see $ROOTSYS/LICENSE. * 0013 * For the list of contributors see $ROOTSYS/README/CREDITS. * 0014 *************************************************************************/ 0015 0016 #ifndef ROOT7_RFile 0017 #define ROOT7_RFile 0018 0019 #include "ROOT/RDirectory.hxx" 0020 #include <string_view> 0021 0022 #include "TClass.h" 0023 #include <memory> 0024 0025 namespace ROOT { 0026 namespace Experimental { 0027 0028 class RFilePtr; 0029 0030 namespace Internal { 0031 class RFileStorageInterface; 0032 class RFileSharedPtrCtor; 0033 } // namespace Internal 0034 0035 /** \class ROOT::Experimental::RFile 0036 A ROOT file. 0037 0038 A ROOT file is an object store: it can serialize any 0039 object for which ROOT I/O is available (generally: an object which has a 0040 dictionary), and it stores the object's data under a key name. 0041 0042 */ 0043 class RFile: public RDirectory { 0044 private: 0045 std::unique_ptr<Internal::RFileStorageInterface> fStorage; ///< Storage backend. 0046 0047 RFile(std::unique_ptr<Internal::RFileStorageInterface> &&storage); 0048 0049 /// Serialize the object at address, using the object's TClass. 0050 // FIXME: what about `cl` "pointing" to a base class? 0051 void WriteMemoryWithType(std::string_view name, const void *address, TClass *cl); 0052 0053 friend Internal::RFileSharedPtrCtor; 0054 0055 public: 0056 /// Options for RFile construction. 0057 struct Options_t { 0058 /// Default constructor needed for member inits. 0059 Options_t() {} 0060 0061 /// Whether the file should be opened asynchronously, if available. 0062 bool fAsynchronousOpen = false; 0063 0064 /// Timeout for asynchronous opening. 0065 int fAsyncTimeout = 0; 0066 0067 /// Whether the file should be cached before reading. Only available for 0068 /// "remote" file protocols. If the download fails, the file will be opened 0069 /// remotely. 0070 bool fCachedRead = false; 0071 0072 /// Where to cache the file. If empty, defaults to RFilePtr::GetCacheDir(). 0073 std::string fCacheDir; 0074 }; 0075 0076 ///\name Generator functions 0077 ///\{ 0078 0079 /// Open a file with `name` for reading. 0080 /// 0081 /// \note: Synchronizes multi-threaded accesses through locks. 0082 static RFilePtr Open(std::string_view name, const Options_t &opts = Options_t()); 0083 0084 /// Open an existing file with `name` for reading and writing. If a file with 0085 /// that name does not exist, an invalid RFilePtr will be returned. 0086 /// 0087 /// \note: Synchronizes multi-threaded accesses through locks. 0088 static RFilePtr OpenForUpdate(std::string_view name, const Options_t &opts = Options_t()); 0089 0090 /// Open a file with `name` for reading and writing. Fail (return an invalid 0091 /// `RFilePtr`) if a file with this name already exists. 0092 /// 0093 /// \note: Synchronizes multi-threaded accesses through locks. 0094 static RFilePtr Create(std::string_view name, const Options_t &opts = Options_t()); 0095 0096 /// Open a file with `name` for reading and writing. If a file with this name 0097 /// already exists, delete it and create a new one. Else simply create a new file. 0098 /// 0099 /// \note: Synchronizes multi-threaded accesses through locks. 0100 static RFilePtr Recreate(std::string_view name, const Options_t &opts = Options_t()); 0101 0102 ///\} 0103 0104 /// Set the new directory used for cached reads, returns the old directory. 0105 /// 0106 /// \note: Synchronizes multi-threaded accesses through locks. 0107 static std::string SetCacheDir(std::string_view path); 0108 0109 /// Get the directory used for cached reads. 0110 static std::string GetCacheDir(); 0111 0112 /// Must not call Write() of all attached objects: 0113 /// some might not be needed to be written or writing might be aborted due to 0114 /// an exception; require explicit Write(). 0115 ~RFile(); 0116 0117 /// Save all objects associated with this directory (including file header) to 0118 /// the storage medium. 0119 void Flush(); 0120 0121 /// Flush() and make the file non-writable: close it. 0122 void Close(); 0123 0124 /// Read the object for a key. `T` must be the object's type. 0125 /// This will re-read the object for each call, returning a new copy; whether 0126 /// the `RDirectory` is managing an object attached to this key or not. 0127 /// \returns a `unique_ptr` to the object. 0128 /// \throws RDirectoryUnknownKey if no object is stored under this name. 0129 /// \throws RDirectoryTypeMismatch if the object stored under this name is of 0130 /// a type different from `T`. 0131 template <class T> 0132 std::unique_ptr<T> Read(std::string_view name) 0133 { 0134 // FIXME: need separate collections for a RDirectory's key/value and registered objects. Here, we want to emit a 0135 // read and must look through the key/values without attaching an object to the RDirectory. 0136 // FIXME: do not register read object in RDirectory 0137 // FIXME: implement actual read 0138 // FIXME: for now, copy out of whatever the RDirectory manages. 0139 return std::make_unique<T>(*Get<T>(name)); 0140 } 0141 0142 /// Write an object that is not lifetime managed by this RFileImplBase. 0143 template <class T> 0144 void Write(std::string_view name, const T &obj) 0145 { 0146 WriteMemoryWithType(name, &obj, TClass::GetClass<T>()); 0147 } 0148 0149 /// Write an object that is not lifetime managed by this RFileImplBase. 0150 template <class T> 0151 void Write(std::string_view name, const T *obj) 0152 { 0153 WriteMemoryWithType(name, obj, TClass::GetClass<T>()); 0154 } 0155 0156 /// Write an object that is already lifetime managed by this RFileImplBase. 0157 void Write(std::string_view name) 0158 { 0159 auto dep = Find(name); 0160 WriteMemoryWithType(name, dep.GetPointer().get(), dep.GetType()); 0161 } 0162 0163 /// Hand over lifetime management of an object to this RFileImplBase, and 0164 /// write it. 0165 template <class T> 0166 void Write(std::string_view name, std::shared_ptr<T> &&obj) 0167 { 0168 Add(name, obj); 0169 // FIXME: use an iterator from the insertion to write instead of a second name lookup. 0170 Write(name); 0171 } 0172 }; 0173 0174 /** 0175 \class RFilePtr 0176 \brief Points to an object that stores or reads objects in ROOT's binary 0177 format. 0178 0179 FIXME: implement async open; likely using std::future, possibly removing the 0180 Option_t element. 0181 0182 */ 0183 0184 class RFilePtr { 0185 private: 0186 std::shared_ptr<RFile> fFile; 0187 0188 /// Constructed by Open etc. 0189 RFilePtr(std::shared_ptr<RFile> &&); 0190 0191 friend class RFile; 0192 0193 public: 0194 /// Dereference the file pointer, giving access to the RFileImplBase object. 0195 RFile *operator->() { return fFile.get(); } 0196 0197 /// Dereference the file pointer, giving access to the RFileImplBase object. 0198 /// const overload. 0199 const RFile *operator->() const { return fFile.get(); } 0200 0201 /// Check the validity of the file pointer. 0202 operator bool() const { return fFile.get(); } 0203 }; 0204 0205 } // namespace Experimental 0206 } // namespace ROOT 0207 #endif
[ Source navigation ] | [ Diff markup ] | [ Identifier search ] | [ general search ] |
This page was automatically generated by the 2.3.7 LXR engine. The LXR team |