HDK
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
GA_ATIBlobArray.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: GA_ATIBlobArray.h ( GA Library, C++)
7  *
8  * COMMENTS: Blob Array ATI (Attribute Type Implementation)
9  */
10 
11 #pragma once
12 
13 #ifndef __GA_ATIBlobArray__
14 #define __GA_ATIBlobArray__
15 
16 #include "GA_API.h"
17 #include "GA_Attribute.h"
18 #include "GA_BlobContainer.h"
19 #include "GA_ATIBlob.h"
20 #include "GA_BlobData.h"
21 #include "GA_ArrayDataArray.h"
22 #include "GA_Types.h"
23 
24 #include <UT/UT_StringHolder.h>
25 #include <UT/UT_VectorTypes.h>
26 
27 #include <SYS/SYS_Types.h>
28 
29 #include <stddef.h>
30 
31 
32 class GA_AIFBlobArray;
33 class GA_AIFCompare;
34 class GA_AIFCopyData;
35 class GA_AIFInterp;
36 class GA_AIFMerge;
37 class GA_AttributeType;
38 class GA_Defragment;
39 class GA_IndexMap;
40 class GA_LoadMap;
41 class GA_MergeMap;
42 class GA_SaveMap;
43 class GA_Range;
44 
45 class UT_JSONParser;
46 class UT_JSONWriter;
47 class UT_Options;
48 template <typename T> class UT_Array;
49 
50 
51 /// @brief A simple ATI to store aribtrary "blobs" of data in an attribute
52 ///
53 /// The blob attribute type stores arbitrary blobs (GA_Blob) of data for each
54 /// element in the attribute array. The blobs are stored as reference counted
55 /// shared objects, meaning the blobs may be shared between multiple elements
56 /// of the array. Each blob is referenced by a unique integer handle.
57 ///
58 /// It's also possible to get a list of all the blobs stored by the attribute
59 ///
60 /// By default, the array is filled with NULL pointers.
61 ///
62 /// This class is very simple and only provides a minimal interface. Blob
63 /// attributes are not saved/loaded, and there is minimal access to the blobs.
64 ///
65 /// Users may sub-class from this ATI to create more complicated classes which
66 /// provide alternate interfaces.
67 ///
68 /// This attribute looks for options (GA_Attribute::getOptions())
69 /// - bool blob:stringset (default: true)@n
70 /// This option is queried when merging detail attributes. When true,
71 /// the @b unique blobs from both details will be merged into the resulting
72 /// detail. When false, the resulting detail will only have the blobs from
73 /// the first detail in the merge.
74 ///
76 {
77 public:
78  static void registerType();
80  static const UT_StringHolder &getTypeName()
81  { return theAttributeType->getTypeName(); }
83  static const GA_AttributeType &getType() { return *theAttributeType; }
84 
86  static bool isType(const GA_Attribute *attrib);
88  static GA_ATIBlobArray *cast(GA_Attribute *attrib);
90  static const GA_ATIBlobArray *cast(const GA_Attribute *attrib);
91 
92  static GA_Attribute *create(const GA_IndexMap &index_map,
93  GA_AttributeScope scope,
94  const UT_StringHolder &name,
95  const GA_AttributeOptions *attribute_options=NULL);
96  static GA_Attribute *create(const GA_IndexMap &index_map,
97  const UT_StringHolder &name)
98  {
99  return create(index_map, GA_SCOPE_PUBLIC, name);
100  }
101 
103  const GA_IndexMap &index_map,
104  GA_AttributeScope scope,
105  const UT_StringHolder &name,
106  int tuple_size);
107  ~GA_ATIBlobArray() override;
108 
109  /// Report approximate memory usage
110  int64 getMemoryUsage(bool inclusive) const override;
111 
112  void countMemory(UT_MemoryCounter &counter, bool inclusive) const override;
113 
114  /// @{
115  /// Interface for defragmentation
116  void defragment(const GA_Defragment &defrag) override
117  { myHandles.defragment(defrag); }
118  /// @}
119 
121  GA_Offset nelements) override;
122 
124  { return myHandles.findMaximumArrayLength(); }
125 
126  /// Get the tuple size
127  int getTupleSize() const
128  { return myHandles.getTupleSize(); }
129  bool setTupleSize(int size)
130  { myHandles.setTupleSize(size); return true; }
131 
132 
133  /// Return the entries in the blob container
134  int entries() const
135  { return myBlobs.entries(); }
136 
137  /// Return the maximum index of any blob in the container. This may be
138  /// more than the number of blobs in the container. If the maximum index
139  /// is less than 0, there are no blobs in the container.
141  { return myBlobs.getMaximumIndex(); }
142 
143  /// Return the capacity of the blob container
144  int capacity() const
145  { return myBlobs.capacity(); }
146 
147  /// Look up a blob handle by offset.
148  void getBlobIndex(UT_Array<GA_BlobIndex> &indices, GA_Offset offset) const;
149 
150  /// Store a new blob_index at the given offset
151  bool setBlobIndex(const UT_Array<GA_BlobIndex> &indices,
152  GA_Offset offset);
153 
154  /// Get the blob associated with a given offset into the array
156  GA_Offset offset) const
157  {
159  getBlobIndex(indices, offset);
160 
161  blobs.clear();
162  blobs.setCapacityIfNeeded(indices.entries());
163  for (int i = 0; i < indices.entries(); i++)
164  blobs.append(lookupBlob(indices(i)));
165  }
166 
167  /// Store a new blob at the given offset
168  bool setBlob(const UT_Array<GA_BlobRef> &blobs,
169  GA_Offset offset);
170 
171  /// Replace a blob in the blob container with a new blob value
172  bool replaceBlob(GA_BlobIndex handle,
173  const GA_BlobRef &blob);
174 
175 
176  /// Look up a blob given its handle
178  { return myBlobs.getBlob(handle); }
179 
180  /// Lookup a blob given an ordered index
182  { return myBlobs.getOrderedBlob(idx); }
183 
184  /// This method will "compact" the attribute container, possibly changing
185  /// all the handles in the attribute data.
186  void compactStorage() override;
187 
188  /// Get a measure of the vacancy entropy of the storage container. This
190  { return myBlobs.getOccupancy(); }
191 
192  /// Adding blobs is thread-safe, so we're only subject to GA_DataArray
193  /// limitations.
195  { return WRITE_CONCURRENCE_PAGE; }
196 
197  const GA_AIFBlobArray *getAIFBlobArray() const override
198  { return myAIFBlobArray; }
199  const GA_AIFMerge *getAIFMerge() const override
200  { return myAIFMerge; }
201  const GA_AIFCompare *getAIFCompare() const override
202  { return myAIFCompare;}
203  const GA_AIFCopyData *getAIFCopyData() const override
204  { return myAIFCopyData;}
205  const GA_AIFInterp *getAIFInterp() const override
206  { return nullptr; }
207 
208  /// Save blobs to a JSON stream.
209  /// This method can be called by sub-classes to save blob data to a JSON
210  /// stream. Since the GA_ATIBlob class doesn't provide an GA_AIFJSON
211  /// interface, data is not saved/loaded by default.
212  ///
213  /// @param w The JSON writer
214  /// @param s The save map options
215  /// @param blobtoken The token used to identify the blob data
216  bool jsonSave(UT_JSONWriter &w,
217  const GA_SaveMap &s,
218  const char *blobtoken = "data") const;
219 
220  /// Load blobs from a JSON stream. This method can be called by
221  /// sub-classes to load their data from a JSON stream. The class must
222  /// provide a GA_BlobDataLoader class which is used to create and load new
223  /// blob data.
224  ///
225  /// @param p The JSON parser
226  /// @param blobloader A class to create and load blobs
227  /// @param load Load options
228  /// @param blobtoken The token used to identify the blob data
229  bool jsonLoad(UT_JSONParser &p,
230  const GA_BlobDataLoader &blobloader,
231  const GA_LoadMap &load,
232  const char *blobtoken = "data");
233 
234  /// Convenience function to extract all the blobs (and their handles)
235  /// The string handles are guaranteed to be in ascending order, but
236  /// may or may not be contiguous.
238  UT_IntArray &handles) const
239  {
240  return myBlobs.extractBlobs(blobs, handles);
241  }
242 
243  /// Grow or shrink the array size
244  bool setArraySize(GA_Offset new_size) override;
245 
246  /// Return the array size for a given offset
247  virtual exint arraySize(GA_Offset item) const;
248 
249  /// Try to compress data pages
250  void tryCompressAllPages(
251  GA_Offset start_offset = GA_Offset(0),
252  GA_Offset end_offset = GA_INVALID_OFFSET) override;
253  /// Harden data pages
254  void hardenAllPages(
255  GA_Offset start_offset = GA_Offset(0),
256  GA_Offset end_offset = GA_INVALID_OFFSET) override;
257 
258  /// Returns true iff that is an attribute whose content can be copied
259  /// from this without any type conversions. This is important to
260  /// avoid reallocation of an attribute if its storage type,
261  /// including tuple size, matches the source attribute exactly.
262  bool matchesStorage(const GA_Attribute *that) const override
263  {
264  if (!GA_Attribute::matchesStorage(that))
265  return false;
266  const GA_ATIBlobArray *thatn = UTverify_cast<const GA_ATIBlobArray *>(that);
267  if (getTupleSize() != thatn->getTupleSize())
268  return false;
269  return true;
270  }
271 
272  /// This replaces the entirety of this attribute's content and non-
273  /// storage metadata (except the name) with that of the src attribute.
274  /// matchesStorage(src) should already return true.
275  /// This is primarily for use by GA_AttributeSet::replace().
276  /// NOTE: The internal content sizes may not match exactly if the
277  /// attribute type may overallocate, but the sizes should be such
278  /// that any real data will fit in the destination, so be careful
279  /// and deal with the myTailInitialize flag appropriately if
280  /// any extra elements aren't equal to the default.
281  void replace(const GA_Attribute &src) override;
282 
283 protected: // Methods
284  /// Blob attributes need each element to properly destruct for accurate
285  /// reference counting.
286  bool needDestruction() const override;
287 
288  /// Callback method to destruct an offset.
289  void destructElement(GA_Offset offset) override;
290 
291  /// Create a new ATIBlob attribute. Sub-classes must implement this.
292  GA_Attribute *doClone(const GA_IndexMap &index_map,
293  const UT_StringHolder &name) const override;
294 
295  /// @{ GA_AIFMerge
296  /// Base class implementation of GA_AIFMerge::destroyDestination()
297  void mergeDestroyDestination(const GA_MergeMap &map,
298  GA_Attribute *dattrib) const;
299  /// Base class implementation of GA_AIFMerge::addDestination()
300  GA_Attribute *mergeAddDestination(const GA_MergeMap &map,
301  GA_Attribute *dattrib) const;
302  /// Base class implementation of GA_AIFMerge::growArray()
303  void mergeGrowArray(const GA_MergeMap &map, const GA_ATIBlobArray &s);
304 
305  /// Base class implementation of GA_AIFMerge::copyArray()
306  bool mergeAppendData(const GA_MergeMap &map,
307  const GA_Attribute *sattrib);
308  /// @}
309 
310  /// @{
311  /// Methods to implement copying of data for AIFCopyData
312  bool copyData(GA_Offset di,
313  const GA_ATIBlobArray *s,
314  GA_Offset si);
315  bool copyData(const GA_Range &di,
316  const GA_ATIBlobArray *s,
317  const GA_Range &si);
318  bool fillData(const GA_Range &di,
319  const GA_ATIBlobArray *s,
320  GA_Offset si);
321  /// @}
322 
323  /// @{
324  /// The addBlobBuffer()/delBlobBuffer() methods are added solely for the
325  /// corresponding methods in GA_AIFBlob.
326  GA_BlobIndex addBlobReference(const GA_BlobRef &blob);
327  void delBlobReference(GA_BlobIndex handle);
328  /// @}
329 
330  /// @{
331  /// Interface used by AIFCompare. By default, this will use the blob key
332  /// comparison to determine equality.
333  virtual bool isEqual(GA_Offset offset,
334  const GA_ATIBlobArray &b, GA_Offset b_offset) const;
335  virtual bool isEqual(const GA_Range & range,
336  const GA_ATIBlobArray &b, const GA_Range &b_range) const;
337  /// @}
338 
339 protected: // Data
340  /// Array of handles. The default value is []
341  /// This is protected for convenience to sub-classes.
343 
344  /// Blob references. This is protected for convenience to sub-classes.
346 
347 private:
348  /// Load up an array of blob
349  bool jsonLoadBlobs(UT_JSONParser &p,
350  const GA_LoadMap &load,
351  UT_Array<GA_BlobRef> &blobs,
352  const GA_BlobDataLoader &blobloader);
353 
354  /// AIF Merge interface
355  static GA_AIFBlobArray *myAIFBlobArray;
356  static GA_AIFMerge *myAIFMerge;
357  static GA_AIFCopyData *myAIFCopyData;
358  static GA_AIFCompare *myAIFCompare;
359 
360  static const GA_AttributeType *theAttributeType;
361 
362  /// @cond INTERNAL_DOX
363  friend class ga_BlobArrayBlob;
364  friend class ga_BlobArrayMerge;
365  friend class ga_BlobArrayCopyData;
366  friend class ga_BlobArrayCompare;
367  /// @endcond
368 };
369 
370 // NOTE: It may seem strange to include GA_ATIStringArray.h here,
371 // but GA_ATIBlobArray::isType() and cast() need GA_ATIStringArray::isType(),
372 // and GA_ATIStringArray inherits from GA_ATIBlobArray, so
373 // GA_ATIBlobArray::isType() and cast() are defined in GA_ATIStringArray.h
374 // below the class.
375 #include "GA_ATIStringArray.h"
376 
377 #endif
static SYS_FORCE_INLINE const UT_StringHolder & getTypeName()
bool setTupleSize(int size)
A class to manage an ordered array which has fixed offset handles.
Definition: GA_IndexMap.h:63
GA_BlobContainer myBlobs
Blob references. This is protected for convenience to sub-classes.
Definition of a geometry attribute.
Definition: GA_Attribute.h:198
int entries() const
Return the entries in the blob container.
GLsizei GLenum const void * indices
Definition: glcorearb.h:406
GLenum GLint * range
Definition: glcorearb.h:1925
Used to pass options and map offset values during saving.
Definition: GA_SaveMap.h:48
int capacity() const
Return the capacity of the blob container.
WriteConcurrence getSupportedWriteConcurrence() const override
int getTupleSize() const
Size of the AIFTuple, if it exists. If it doesn't, 1.
GA_BlobIndex getMaximumIndex() const
GA_ArrayDataArray myHandles
Attribute Interface for accessing generic blob data.
The merge map keeps track of information when merging details.
Definition: GA_MergeMap.h:53
int64 exint
Definition: SYS_Types.h:125
virtual void reconstructElementBlock(GA_Offset offset, GA_Offset nelements)=0
GLdouble s
Definition: glad.h:3009
void defragment(const GA_Defragment &defrag) override
JSON reader class which handles parsing of JSON or bJSON files.
Definition: UT_JSONParser.h:87
virtual bool setArraySize(GA_Offset size)=0
#define GA_API
Definition: GA_API.h:14
Class which writes ASCII or binary JSON streams.
Definition: UT_JSONWriter.h:37
SYS_FORCE_INLINE TO_T UTverify_cast(FROM_T from)
Definition: UT_Assert.h:229
virtual void countMemory(UT_MemoryCounter &counter, bool inclusive) const =0
Standard user attribute level.
Definition: GA_Types.h:149
virtual int64 getMemoryUsage(bool inclusive) const =0
virtual bool matchesStorage(const GA_Attribute *that) const
Definition: GA_Attribute.h:751
static SYS_FORCE_INLINE const GA_AttributeType & getType()
virtual void tryCompressAllPages(GA_Offset start_offset=GA_Offset(0), GA_Offset end_offset=GA_INVALID_OFFSET)=0
An array of array of numbers with various storage types.
#define GA_INVALID_OFFSET
Definition: GA_Types.h:687
A range of elements in an index-map.
Definition: GA_Range.h:42
GA_Size GA_Offset
Definition: GA_Types.h:646
GA_AttributeScope
Definition: GA_Types.h:143
virtual bool needDestruction() const
Methods which can be overridden from GA_Attribute.
exint findMaximumArrayLength() const
GLintptr offset
Definition: glcorearb.h:665
SYS_FORCE_INLINE const X * cast(const InstancablePtr *o)
Utility class to load blob data from a JSON stream.
Definition: GA_ATIBlob.h:56
virtual void replace(const GA_Attribute &src)=0
Attribute Interface for merging attribute data between details.
Definition: GA_AIFMerge.h:56
UT_IndexedHashMapItemId GA_BlobIndex
#define SYS_FORCE_INLINE
Definition: SYS_Inline.h:45
fpreal getStorageOccupancy()
Get a measure of the vacancy entropy of the storage container. This.
const GA_AIFInterp * getAIFInterp() const override
Return the attribute's interpolation interface or NULL.
long long int64
Definition: SYS_Types.h:116
Attribute Interface class to perform comparisons on attributes.
Definition: GA_AIFCompare.h:27
Options during loading.
Definition: GA_LoadMap.h:42
const GA_AIFCompare * getAIFCompare() const override
Return the attribute's comparison interface or NULL.
Defragmentation of IndexMaps.
Definition: GA_Defragment.h:45
void setCapacityIfNeeded(exint min_capacity)
Definition: UT_Array.h:603
GLuint const GLchar * name
Definition: glcorearb.h:786
GA_BlobRef getOrderedBlob(exint idx) const
Lookup a blob given an ordered index.
GLboolean GLboolean GLboolean b
Definition: glcorearb.h:1222
exint append()
Definition: UT_Array.h:142
exint entries() const
Alias of size(). size() is preferred.
Definition: UT_Array.h:648
GLsizeiptr size
Definition: glcorearb.h:664
A map of string to various well defined value types.
Definition: UT_Options.h:84
GA_BlobRef lookupBlob(GA_BlobIndex handle) const
Look up a blob given its handle.
void getBlob(UT_Array< GA_BlobRef > &blobs, GA_Offset offset) const
Get the blob associated with a given offset into the array.
A simple ATI to store aribtrary "blobs" of data in an attribute.
fpreal64 fpreal
Definition: SYS_Types.h:277
static GA_Attribute * create(const GA_IndexMap &index_map, const UT_StringHolder &name)
Concurrent writes to separate pages supported.
Definition: GA_Attribute.h:367
virtual void compactStorage()
const GA_AIFCopyData * getAIFCopyData() const override
Return the attribute's copy interface or NULL.
virtual void destructElement(GA_Offset offset)
Callback invoked if needsDestruction() returns true.
Attribute Interface class to copy attribute data.
GLubyte GLubyte GLubyte GLubyte w
Definition: glcorearb.h:857
bool matchesStorage(const GA_Attribute *that) const override
const GA_AIFMerge * getAIFMerge() const override
Return the attribute's merge interface or NULL.
void clear()
Resets list to an empty list.
Definition: UT_Array.h:729
type
Definition: core.h:1059
virtual void hardenAllPages(GA_Offset start_offset=GA_Offset(0), GA_Offset end_offset=GA_INVALID_OFFSET)=0
const GA_AIFBlobArray * getAIFBlobArray() const override
Return the attribute's blob array interface or NULL.
int getTupleSize() const
Get the tuple size.
int extractBlobs(UT_Array< GA_BlobRef > &blobs, UT_IntArray &handles) const
Container to store blobs of arbitrary data for attributes.
GLenum src
Definition: glcorearb.h:1793