HDK
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
FS_Reader.h
Go to the documentation of this file.
1 /*
2  * PROPRIETARY INFORMATION. This software is proprietary to
3  * Side Effects Software Inc., and is not to be reproduced,
4  * transmitted, or disclosed in any way without written permission.
5  *
6  * NAME: FS_Reader.h ( FS Library, C++)
7  *
8  * COMMENTS:
9  *
10  */
11 
12 #ifndef __FS_Reader__
13 #define __FS_Reader__
14 
15 #include "FS_API.h"
16 #include "FS_ReaderStream.h"
17 #include <UT/UT_NonCopyable.h>
18 #include <UT/UT_ValArray.h>
19 #include <SYS/SYS_Types.h>
20 
21 #include <time.h>
22 
23 class UT_IStream;
24 class UT_Options;
25 class UT_String;
26 class UT_StringArray;
27 class UT_StringHolder;
28 class FS_IndexFile;
29 class FS_ReaderHelper;
31 
32 /// Class for reading files
34 {
35 public:
36  FS_Reader();
37 
38  /// Use this constructor to create a new reader. The specified file is
39  /// opened immediately.
40  /// Common options:
41  /// - "string cache_mode" - Specify the "caching" pattern. This gives a
42  /// hint to the file system about how the stream will be accessed.
43  /// * "normal" - Normal caching
44  /// * "random" - Access pattern is random
45  /// * "sequential" - Access pattern is sequential
46  /// - "int buffer_size" - Specify the buffer size (see setvbuf)
47  /// - "bool ascii" - Specify whether the file should be opened in ASCII
48  /// read mode for automatically translating line-endings.
49  FS_Reader(const char *source, const UT_Options *options=0);
50 
51  /// NOTE: This new FS_Reader takes ownership of the FS_ReaderStream
52  FS_Reader(FS_ReaderStream *sourcestream);
53  virtual ~FS_Reader();
54 
55  /// Get the amount of memory owned by this FS_Reader
56  virtual int64 getMemoryUsage(bool inclusive) const;
57 
58  /// Closes the stream. After calling this function, the getStream()
59  /// function will always return @c nullptr.
60  void close();
61 
62  /// This function is used to check if the file was successfully opened
63  bool isGood()
64  { return myStream && myStream->isGood(); }
65 
66  /// This function retrieves the C++ stream object which you can interact
67  /// with in the normal ways. If this function returns @c nullptr, the file
68  /// specified in the constructor could not be found.
69  UT_IStream *getStream() const;
70 
71  // Obtains a stream reader that reads a portion of this reader's stream.
72  // Note, the underlying buffers are shared, invoking this method will
73  // advance the current read position to the subset's beginning, and any
74  // subsequent reading will further advance the read position.
75  FS_ReaderStream *shareDataAndGetSubstream(int64 stream_offset,
76  int64 sub_stream_size, int64 sub_data_size,
77  const FS_IStreamFilterFactory * f = nullptr) const;
78 
79  time_t getModTime() const;
80  int64 getLength() const;
81  const UT_StringHolder &getFilename() const;
82 
83  // Obtains filter factories that are piggyacked from another FS_IndexFile.
84  FS_IStreamFilterFactory *getSubStreamReadFilterFactory() const;
85  FS_WriteFilterFactory *getSubStreamWriteFilterFactory() const;
86 
87  // Functions for adding and removing helpers.
88  static void addReaderHelper(FS_ReaderHelper *helper);
89  static void removeReaderHelper(FS_ReaderHelper *helper);
90 
91  /// @{
92  /// Utility fuction to split the original source path into the index file
93  /// path and the section name. It asks all registered reader helpers
94  /// whether they recognize the source path protocol and can provide the
95  /// section name. If none of the helpers do, then it tries FS_IndexFile to
96  /// split the source path on '?' by default.
97  /// @param[in] source_section_path The original source path to split.
98  /// @param[out] index_file_path If the original source path refers to
99  /// an index file section, this parameter is set to the
100  /// index file path. Otherwise, it is set to the
101  /// source_section_path parameter.
102  /// @param[out] section_name If the original source path refers to
103  /// and index file section, this parameter is set to the
104  /// name of that section. Otherwise, it is set to an empty
105  /// string. If there are many nested sections in the source
106  /// path, then this argument will contain the innermost
107  /// section name, and the index_file_path will point
108  /// to the containing section (itself an index file).
109  /// @param[out] section_names If the original source path refers to
110  /// a section that is nested within other
111  /// sections (that themselves are index files), then
112  /// this parameter is set to these section names, with
113  /// the outermost section at the beginning of the array
114  /// and the innermost section (contained within the outer
115  /// sections) at the end of the array. If there is just
116  /// a single section, the array will contain just one
117  /// entry (ie, the single section name),
118  /// and the call will be equivalent to the method
119  /// that takes just the single string.
120  /// @return True if the path refered to a section name and the outgoing
121  /// parameter 'section_name' contains a non-empty string;
122  /// otherwise, returns false.
123  static bool splitIndexFileSectionPath(
124  const char *source_section_path,
125  UT_String &index_file_path,
126  UT_String &section_name);
127  static bool splitIndexFileSectionPath(
128  const char *source_section_path,
129  UT_StringHolder &index_file_path,
130  UT_StringHolder &section_name);
131  static bool splitIndexFileSectionPath(
132  const char *source_section_path,
133  UT_String &index_file_path,
134  UT_StringArray &section_names );
135  /// @}
136 
137  /// @{
138  /// Utility function to combine index file name and section name into the
139  /// section path. It asks all registered reader helpers
140  /// whether they recognize the index_file_path path protocol and can
141  /// combine it with the section name into the section full path.
142  /// If none of the helpers do, then it asks FS_IndexFile to
143  /// combine the components, joining them with '?' by default.
144  /// @param[out] source_section_path The combined section full path.
145  /// @param[in] index_file_path The base path to the index file.
146  /// @param[in] section_name The name of the section inside the index file.
147  /// @param[in] section_names The names of the nested sections in
148  /// the index file, with the outermost section at the
149  /// beginning of the array and the innermost section
150  /// (contained within the outer sections) at the end
151  /// of the array. If the array contains only one entry,
152  /// it's equivalent to the method that takes just a single
153  /// string.
154  static void combineIndexFileSectionPath(
155  UT_String &source_section_path,
156  const char *index_file_path,
157  const char *section_name);
158  static void combineIndexFileSectionPath(
159  UT_String &source_section_path,
160  const char *index_file_path,
161  const UT_StringArray &section_names );
162  /// @}
163 
164 
165 private:
166  void createStreamFromSource(const char *source,
167  const UT_Options *options);
168 
169  static UT_ValArray<FS_ReaderHelper *> &getHelpers();
170 
171  FS_ReaderStream *myStream;
172 };
173 
174 /// This class provides a plug-in method for adding a custom "file-system"
175 /// @see FS_WriterHelper, FS_InfoHelper
177 {
178 public:
180  { FS_Reader::addReaderHelper(this); }
183 
184  /// Return an FS_ReaderStream if the helper is able to open the source
185  /// filename.
186  ///
187  /// The options are passed through directly from the FS_Reader
188  /// constructor. See FS_Reader for list of options.
189  virtual FS_ReaderStream *createStream(const char *source,
190  const UT_Options *options=nullptr) = 0;
191 
192  /// Parse the source path into the index file path and the section name.
193  ///
194  /// The FS library recognizes a special source format for FS_IndexFile,
195  /// which is a file containing several sections indexed and accessible
196  /// by their name. That source format contains '?' as a separator between
197  /// the file path and the section name.
198  /// FS_Reader scans for '?' in the source path before asking helpers
199  /// to handle it. This way index files are supported for custom protoclos
200  /// automatically without them needing to implement it explicitly.
201  /// Eg, "myfiles:path/to/indexfile?section" will work automaticaly, since
202  /// FS_Reader will ask the helper for a read stream for
203  /// "myfiles:/path/to/indexfile" but will create and use the "section"
204  /// read stream itself.
205  /// The downside is that custom protocols can't use '?' in their path
206  /// format. To address this isse, this method has been added to let the
207  /// helpers decide how to handle the '?'.
208  ///
209  /// If the helper does not use '?' for any special purpose, it does not need
210  /// to override this virtual (or it can overloaded it and return false).
211  /// If the helper uses '?' for some special meaning (or if it supports some
212  /// custom syntax to refer to sections of an index file), then it should
213  /// override it and return true. Further, it can return a non-empty section
214  /// name if the protocol supports section naming and the source path indeed
215  /// refers to a section in an index file. Or, it can return an empty string
216  /// for the section name, if the source path does not refer to an index
217  /// file (or if helper does not want the automatic index file handling and
218  /// plans to handle index files explicitly by itself).
219  ///
220  /// @param[in] source_section_path Original source path to be opened for
221  /// reading.
222  /// @param[out] index_file_path If source_section_path refers to a section
223  /// in an index file, then this parameter is set to the index
224  /// file path (and method returns true).
225  /// If source_section_path does not refer to a section, then
226  /// this parameter is set to original path, ie, equal to
227  /// source_section_path (and method returns true).
228  /// If the helper does not recognize the source_section_path
229  /// (ie, it's another protocol), or if recognizes it but does
230  /// not need (nor want) custom handling for '?' separator,
231  /// then this parameter is not set (and method returns false).
232  /// @param[out] section_name This Similar to index_file_path, but this
233  /// outgoing parameter is set to the section name, if
234  /// source_section_path refers to a section and is set to
235  /// empty-string if it does not (and method returns true).
236  /// If the method returns false, it is not set.
237  ///
238  /// @return True if the source_section_path can be handled by the
239  /// helper, in which case index_file_path and section_name
240  /// are also set (though section can be an empty-string).
241  /// False if the source_code_path is not handled by helper,
242  /// or if helper wants default index file naming convention
243  /// (with '?' splitting the file and section name).
244  ///
245  virtual bool splitIndexFileSectionPath(const char *source_section_path,
246  UT_String &index_file_path,
247  UT_String &section_name)
248  {
249  return false;
250  }
251 
252  /// Utility function to combine index file name and section name into the
253  /// section path. Performs the reverse of splitIndexFileSectionPath().
254  /// If the helper does not use '?' for any special purpose in the source
255  /// path, then it does not need to override this virtual (see above).
256  /// @param[out] source_section_path The combined full section path.
257  /// @param[in] index_file_path The base path to the index file.
258  /// @param[in] section_name The name of the section inside the index file.
259  /// @return True if the helper recognizes the 'index_file_path' as its
260  /// own file protocol. False, if it does not recognize the
261  /// protocol or if it wants the default joining of file and
262  /// section names using the default convention of '?' to
263  /// join the components.
265  UT_String &source_section_path,
266  const char *index_file_path,
267  const char *section_name)
268  {
269  return false;
270  }
271 };
272 
273 #endif
274 
Class for reading files.
Definition: FS_Reader.h:33
static void addReaderHelper(FS_ReaderHelper *helper)
virtual ~FS_ReaderHelper()
Definition: FS_Reader.h:181
long long int64
Definition: SYS_Types.h:107
GLfloat f
Definition: glcorearb.h:1925
static void removeReaderHelper(FS_ReaderHelper *helper)
virtual bool splitIndexFileSectionPath(const char *source_section_path, UT_String &index_file_path, UT_String &section_name)
Definition: FS_Reader.h:245
GLsizei GLsizei GLchar * source
Definition: glcorearb.h:802
A map of string to various well defined value types.
Definition: UT_Options.h:42
virtual void close()
bool isGood()
This function is used to check if the file was successfully opened.
Definition: FS_Reader.h:63
#define FS_API
Definition: FS_API.h:10
virtual bool combineIndexFileSectionPath(UT_String &source_section_path, const char *index_file_path, const char *section_name)
Definition: FS_Reader.h:264