GCC Code Coverage Report


Directory: ./
File: openvdb/openvdb/points/PointDataGrid.h
Date: 2022-07-25 17:40:05
Exec Total Coverage
Lines: 419 440 95.2%
Functions: 77 101 76.2%
Branches: 718 4129 17.4%

Line Branch Exec Source
1 // Copyright Contributors to the OpenVDB Project
2 // SPDX-License-Identifier: MPL-2.0
3
4 /// @author Dan Bailey
5 ///
6 /// @file points/PointDataGrid.h
7 ///
8 /// @brief Attribute-owned data structure for points. Point attributes are
9 /// stored in leaf nodes and ordered by voxel for fast random and
10 /// sequential access.
11
12 #ifndef OPENVDB_POINTS_POINT_DATA_GRID_HAS_BEEN_INCLUDED
13 #define OPENVDB_POINTS_POINT_DATA_GRID_HAS_BEEN_INCLUDED
14
15 #include <openvdb/version.h>
16 #include <openvdb/Grid.h>
17 #include <openvdb/tree/Tree.h>
18 #include <openvdb/tree/LeafNode.h>
19 #include <openvdb/tools/PointIndexGrid.h>
20 #include "AttributeArray.h"
21 #include "AttributeArrayString.h"
22 #include "AttributeGroup.h"
23 #include "AttributeSet.h"
24 #include "StreamCompression.h"
25 #include <cstring> // std::memcpy
26 #include <iostream>
27 #include <limits>
28 #include <memory>
29 #include <type_traits> // std::is_same
30 #include <utility> // std::pair, std::make_pair
31 #include <vector>
32
33 class TestPointDataLeaf;
34
35 namespace openvdb {
36 OPENVDB_USE_VERSION_NAMESPACE
37 namespace OPENVDB_VERSION_NAME {
38
39 namespace io
40 {
41
42 /// @brief openvdb::io::readCompressedValues specialized on PointDataIndex32 arrays to
43 /// ignore the value mask, use a larger block size and use 16-bit size instead of 64-bit
44 template<>
45 inline void
46 25662 readCompressedValues( std::istream& is, PointDataIndex32* destBuf, Index destCount,
47 const util::NodeMask<3>& /*valueMask*/, bool /*fromHalf*/)
48 {
49 using compression::bloscDecompress;
50
51 const bool seek = destBuf == nullptr;
52
53 25662 const size_t destBytes = destCount*sizeof(PointDataIndex32);
54 const size_t maximumBytes = std::numeric_limits<uint16_t>::max();
55
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 25661 times.
25662 if (destBytes >= maximumBytes) {
56
2/6
✓ Branch 1 taken 1 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 1 times.
✗ Branch 5 not taken.
✗ Branch 12 not taken.
✗ Branch 13 not taken.
5 OPENVDB_THROW(openvdb::IoError, "Cannot read more than " <<
57 maximumBytes << " bytes in voxel values.")
58 }
59
60 uint16_t bytes16;
61
62 25661 const io::StreamMetadata::Ptr meta = io::getStreamMetadataPtr(is);
63
64
4/4
✓ Branch 0 taken 10221 times.
✓ Branch 1 taken 15440 times.
✓ Branch 2 taken 10220 times.
✓ Branch 3 taken 1 times.
25661 if (seek && meta) {
65 // buffer size temporarily stored in the StreamMetadata pass
66 // to avoid having to perform an expensive disk read for 2-bytes
67
1/2
✓ Branch 1 taken 10220 times.
✗ Branch 2 not taken.
10220 bytes16 = static_cast<uint16_t>(meta->pass());
68 // seek over size of the compressed buffer
69
1/2
✓ Branch 1 taken 10220 times.
✗ Branch 2 not taken.
10220 is.seekg(sizeof(uint16_t), std::ios_base::cur);
70 }
71 else {
72 // otherwise read from disk
73
1/2
✓ Branch 1 taken 15441 times.
✗ Branch 2 not taken.
15441 is.read(reinterpret_cast<char*>(&bytes16), sizeof(uint16_t));
74 }
75
76
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 25660 times.
25661 if (bytes16 == std::numeric_limits<uint16_t>::max()) {
77 // read or seek uncompressed data
78
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 1 times.
1 if (seek) {
79 is.seekg(destBytes, std::ios_base::cur);
80 }
81 else {
82
1/2
✓ Branch 1 taken 1 times.
✗ Branch 2 not taken.
1 is.read(reinterpret_cast<char*>(destBuf), destBytes);
83 }
84 }
85 else {
86 // read or seek uncompressed data
87
2/2
✓ Branch 0 taken 10221 times.
✓ Branch 1 taken 15439 times.
25660 if (seek) {
88
1/2
✓ Branch 1 taken 10221 times.
✗ Branch 2 not taken.
10221 is.seekg(int(bytes16), std::ios_base::cur);
89 }
90 else {
91 // decompress into the destination buffer
92
1/2
✓ Branch 1 taken 15439 times.
✗ Branch 2 not taken.
15439 std::unique_ptr<char[]> bloscBuffer(new char[int(bytes16)]);
93
1/2
✓ Branch 1 taken 15439 times.
✗ Branch 2 not taken.
15439 is.read(bloscBuffer.get(), bytes16);
94 std::unique_ptr<char[]> buffer = bloscDecompress( bloscBuffer.get(),
95 destBytes,
96
2/2
✓ Branch 1 taken 15437 times.
✓ Branch 2 taken 2 times.
15439 /*resize=*/false);
97
1/2
✓ Branch 0 taken 15437 times.
✗ Branch 1 not taken.
15437 std::memcpy(destBuf, buffer.get(), destBytes);
98 }
99 }
100 25659 }
101
102 /// @brief openvdb::io::writeCompressedValues specialized on PointDataIndex32 arrays to
103 /// ignore the value mask, use a larger block size and use 16-bit size instead of 64-bit
104 template<>
105 inline void
106 3967 writeCompressedValues( std::ostream& os, PointDataIndex32* srcBuf, Index srcCount,
107 const util::NodeMask<3>& /*valueMask*/,
108 const util::NodeMask<3>& /*childMask*/, bool /*toHalf*/)
109 {
110 using compression::bloscCompress;
111
112 3967 const size_t srcBytes = srcCount*sizeof(PointDataIndex32);
113 const size_t maximumBytes = std::numeric_limits<uint16_t>::max();
114
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 3966 times.
3967 if (srcBytes >= maximumBytes) {
115
2/6
✓ Branch 1 taken 1 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 1 times.
✗ Branch 5 not taken.
✗ Branch 12 not taken.
✗ Branch 13 not taken.
5 OPENVDB_THROW(openvdb::IoError, "Cannot write more than " <<
116 maximumBytes << " bytes in voxel values.")
117 }
118
119 const char* charBuffer = reinterpret_cast<const char*>(srcBuf);
120
121 size_t compressedBytes;
122 std::unique_ptr<char[]> buffer = bloscCompress( charBuffer, srcBytes,
123 3966 compressedBytes, /*resize=*/false);
124
125
2/2
✓ Branch 0 taken 3965 times.
✓ Branch 1 taken 1 times.
3966 if (compressedBytes > 0) {
126 3965 auto bytes16 = static_cast<uint16_t>(compressedBytes); // clamp to 16-bit unsigned integer
127
1/2
✓ Branch 1 taken 3965 times.
✗ Branch 2 not taken.
3965 os.write(reinterpret_cast<const char*>(&bytes16), sizeof(uint16_t));
128
1/2
✓ Branch 1 taken 3965 times.
✗ Branch 2 not taken.
3965 os.write(reinterpret_cast<const char*>(buffer.get()), compressedBytes);
129 }
130 else {
131 1 auto bytes16 = static_cast<uint16_t>(maximumBytes); // max value indicates uncompressed
132
1/2
✓ Branch 1 taken 1 times.
✗ Branch 2 not taken.
1 os.write(reinterpret_cast<const char*>(&bytes16), sizeof(uint16_t));
133
1/2
✓ Branch 1 taken 1 times.
✗ Branch 2 not taken.
1 os.write(reinterpret_cast<const char*>(srcBuf), srcBytes);
134 }
135 3966 }
136
137 template <typename T>
138 inline void
139 3961 writeCompressedValuesSize(std::ostream& os, const T* srcBuf, Index srcCount)
140 {
141 using compression::bloscCompressedSize;
142
143 3961 const size_t srcBytes = srcCount*sizeof(T);
144 const size_t maximumBytes = std::numeric_limits<uint16_t>::max();
145
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 3961 times.
3961 if (srcBytes >= maximumBytes) {
146 OPENVDB_THROW(openvdb::IoError, "Cannot write more than " <<
147 maximumBytes << " bytes in voxel values.")
148 }
149
150 const char* charBuffer = reinterpret_cast<const char*>(srcBuf);
151
152 // calculate voxel buffer size after compression
153 3961 size_t compressedBytes = bloscCompressedSize(charBuffer, srcBytes);
154
155
1/2
✓ Branch 0 taken 3961 times.
✗ Branch 1 not taken.
3961 if (compressedBytes > 0) {
156 3961 auto bytes16 = static_cast<uint16_t>(compressedBytes); // clamp to 16-bit unsigned integer
157 3961 os.write(reinterpret_cast<const char*>(&bytes16), sizeof(uint16_t));
158 }
159 else {
160 auto bytes16 = static_cast<uint16_t>(maximumBytes); // max value indicates uncompressed
161 os.write(reinterpret_cast<const char*>(&bytes16), sizeof(uint16_t));
162 }
163 3961 }
164
165 } // namespace io
166
167
168 // forward declaration
169 namespace tree {
170 template<Index, typename> struct SameLeafConfig;
171 }
172
173
174 ////////////////////////////////////////
175
176
177 namespace points {
178
179
180 // forward declaration
181 template<typename T, Index Log2Dim> class PointDataLeafNode;
182
183 // these aliases are disabled in one of the unit tests to ensure that
184 // they are not used by the Point headers
185
186 #ifndef OPENVDB_DISABLE_POINT_DATA_TREE_ALIAS
187
188 /// @brief Point index tree configured to match the default VDB configurations.
189 using PointDataTree = tree::Tree<tree::RootNode<tree::InternalNode<tree::InternalNode
190 <PointDataLeafNode<PointDataIndex32, 3>, 4>, 5>>>;
191
192
193 /// @brief Point data grid.
194 using PointDataGrid = Grid<PointDataTree>;
195
196 #endif
197
198 /// @brief Deep copy the descriptor across all leaf nodes.
199 ///
200 /// @param tree the PointDataTree.
201 ///
202 /// @return the new descriptor.
203 ///
204 /// @note This method will fail if the Descriptors in the tree are not all identical.
205 template <typename PointDataTreeT>
206 inline AttributeSet::Descriptor::Ptr
207 makeDescriptorUnique(PointDataTreeT& tree);
208
209
210 /// @brief Toggle the streaming mode on all attributes in the tree to collapse the attributes
211 /// after deconstructing a bound AttributeHandle to each array. This results in better
212 /// memory efficiency when the data is streamed into another data structure
213 /// (typically for rendering).
214 ///
215 /// @param tree the PointDataTree.
216 /// @param on @c true to enable streaming
217 ///
218 /// @note Multiple threads cannot safely access the same AttributeArray when using streaming.
219 template <typename PointDataTreeT>
220 inline void
221 setStreamingMode(PointDataTreeT& tree, bool on = true);
222
223
224 /// @brief Sequentially pre-fetch all delayed-load voxel and attribute data from disk in order
225 /// to accelerate subsequent random access.
226 ///
227 /// @param tree the PointDataTree.
228 /// @param position if enabled, prefetch the position attribute (default is on)
229 /// @param otherAttributes if enabled, prefetch all other attributes (default is on)
230 template <typename PointDataTreeT>
231 inline void
232 prefetch(PointDataTreeT& tree, bool position = true, bool otherAttributes = true);
233
234
235 ////////////////////////////////////////
236
237
238 template <typename T, Index Log2Dim>
239 class PointDataLeafNode : public tree::LeafNode<T, Log2Dim>, io::MultiPass {
240
241 public:
242 using LeafNodeType = PointDataLeafNode<T, Log2Dim>;
243 using Ptr = std::shared_ptr<PointDataLeafNode>;
244
245 using ValueType = T;
246 using ValueTypePair = std::pair<ValueType, ValueType>;
247 using IndexArray = std::vector<ValueType>;
248
249 using Descriptor = AttributeSet::Descriptor;
250
251 ////////////////////////////////////////
252
253 // The following methods had to be copied from the LeafNode class
254 // to make the derived PointDataLeafNode class compatible with the tree structure.
255
256 using BaseLeaf = tree::LeafNode<T, Log2Dim>;
257 using NodeMaskType = util::NodeMask<Log2Dim>;
258
259 using BaseLeaf::LOG2DIM;
260 using BaseLeaf::TOTAL;
261 using BaseLeaf::DIM;
262 using BaseLeaf::NUM_VALUES;
263 using BaseLeaf::NUM_VOXELS;
264 using BaseLeaf::SIZE;
265 using BaseLeaf::LEVEL;
266
267 /// Default constructor
268 12 PointDataLeafNode()
269
2/4
✓ Branch 1 taken 12 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 12 times.
✗ Branch 5 not taken.
12 : mAttributeSet(new AttributeSet) { }
270
271
9/18
✓ Branch 14 taken 1 times.
✗ Branch 15 not taken.
✓ Branch 19 taken 1 times.
✗ Branch 20 not taken.
✓ Branch 27 taken 1 times.
✗ Branch 28 not taken.
✓ Branch 30 taken 1 times.
✗ Branch 31 not taken.
✓ Branch 37 taken 1 times.
✗ Branch 38 not taken.
✓ Branch 44 taken 1 times.
✗ Branch 45 not taken.
✓ Branch 60 taken 1 times.
✗ Branch 61 not taken.
✓ Branch 64 taken 1 times.
✗ Branch 65 not taken.
✓ Branch 90 taken 1 times.
✗ Branch 91 not taken.
121407 ~PointDataLeafNode() = default;
272
273 /// Construct using deep copy of other PointDataLeafNode
274 11489 explicit PointDataLeafNode(const PointDataLeafNode& other)
275 : BaseLeaf(other)
276
2/4
✓ Branch 2 taken 11489 times.
✗ Branch 3 not taken.
✓ Branch 5 taken 11489 times.
✗ Branch 6 not taken.
11489 , mAttributeSet(new AttributeSet(*other.mAttributeSet)) { }
277
278 /// Construct using supplied origin, value and active status
279 explicit
280
13/42
✓ Branch 1 taken 1 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 6 taken 1 times.
✗ Branch 7 not taken.
✗ Branch 8 not taken.
✗ Branch 9 not taken.
✓ Branch 11 taken 1 times.
✗ Branch 12 not taken.
✓ Branch 14 taken 1 times.
✗ Branch 15 not taken.
✓ Branch 17 taken 1 times.
✗ Branch 18 not taken.
✓ Branch 20 taken 1 times.
✗ Branch 21 not taken.
✓ Branch 23 taken 1 times.
✗ Branch 24 not taken.
✓ Branch 26 taken 1 times.
✗ Branch 27 not taken.
✗ Branch 30 not taken.
✗ Branch 31 not taken.
✗ Branch 33 not taken.
✗ Branch 34 not taken.
✓ Branch 36 taken 1 times.
✗ Branch 37 not taken.
✗ Branch 38 not taken.
✗ Branch 39 not taken.
✓ Branch 41 taken 1 times.
✗ Branch 42 not taken.
✗ Branch 43 not taken.
✗ Branch 44 not taken.
✓ Branch 47 taken 1 times.
✗ Branch 48 not taken.
✗ Branch 49 not taken.
✗ Branch 50 not taken.
✓ Branch 52 taken 1 times.
✗ Branch 53 not taken.
✗ Branch 54 not taken.
✗ Branch 55 not taken.
✗ Branch 56 not taken.
✓ Branch 57 taken 1 times.
2676 PointDataLeafNode(const Coord& coords, const T& value = zeroVal<T>(), bool active = false)
281 2664 : BaseLeaf(coords, zeroVal<T>(), active)
282
3/6
✓ Branch 2 taken 2664 times.
✗ Branch 3 not taken.
✓ Branch 5 taken 2664 times.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
✓ Branch 8 taken 2664 times.
2664 , mAttributeSet(new AttributeSet) { assertNonModifiableUnlessZero(value); }
283
284 /// Construct using supplied origin, value and active status
285 /// use attribute map from another PointDataLeafNode
286 PointDataLeafNode(const PointDataLeafNode& other, const Coord& coords,
287 const T& value = zeroVal<T>(), bool active = false)
288 : BaseLeaf(coords, zeroVal<T>(), active)
289 , mAttributeSet(new AttributeSet(*other.mAttributeSet))
290 {
291 assertNonModifiableUnlessZero(value);
292 }
293
294 // Copy-construct from a PointIndexLeafNode with the same configuration but a different ValueType.
295 template<typename OtherValueType>
296 33617 PointDataLeafNode(const tools::PointIndexLeafNode<OtherValueType, Log2Dim>& other)
297 : BaseLeaf(other)
298
2/4
✓ Branch 2 taken 33617 times.
✗ Branch 3 not taken.
✓ Branch 5 taken 33617 times.
✗ Branch 6 not taken.
33617 , mAttributeSet(new AttributeSet) { }
299
300 // Copy-construct from a LeafNode with the same configuration but a different ValueType.
301 // Used for topology copies - explicitly sets the value (background) to zeroVal
302 template <typename ValueType>
303 4506 PointDataLeafNode(const tree::LeafNode<ValueType, Log2Dim>& other, const T& value, TopologyCopy)
304 4506 : BaseLeaf(other, zeroVal<T>(), TopologyCopy())
305
3/6
✓ Branch 1 taken 4057 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 4057 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✓ Branch 7 taken 4057 times.
4506 , mAttributeSet(new AttributeSet) { assertNonModifiableUnlessZero(value); }
306
307 // Copy-construct from a LeafNode with the same configuration but a different ValueType.
308 // Used for topology copies - explicitly sets the on and off value (background) to zeroVal
309 template <typename ValueType>
310 1 PointDataLeafNode(const tree::LeafNode<ValueType, Log2Dim>& other, const T& /*offValue*/, const T& /*onValue*/, TopologyCopy)
311 1 : BaseLeaf(other, zeroVal<T>(), zeroVal<T>(), TopologyCopy())
312
2/4
✓ Branch 2 taken 1 times.
✗ Branch 3 not taken.
✓ Branch 5 taken 1 times.
✗ Branch 6 not taken.
1 , mAttributeSet(new AttributeSet) { }
313
314 10219 PointDataLeafNode(PartialCreate, const Coord& coords,
315 const T& value = zeroVal<T>(), bool active = false)
316 : BaseLeaf(PartialCreate(), coords, value, active)
317
3/6
✓ Branch 2 taken 10219 times.
✗ Branch 3 not taken.
✓ Branch 5 taken 10219 times.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
✓ Branch 8 taken 10219 times.
10219 , mAttributeSet(new AttributeSet) { assertNonModifiableUnlessZero(value); }
318
319 public:
320
321 /// Retrieve the attribute set.
322 const AttributeSet& attributeSet() const { return *mAttributeSet; }
323
324 /// @brief Steal the attribute set, a new, empty attribute set is inserted in it's place.
325 AttributeSet::UniquePtr stealAttributeSet();
326
327 /// @brief Create a new attribute set. Existing attributes will be removed.
328 void initializeAttributes(const Descriptor::Ptr& descriptor, const Index arrayLength,
329 const AttributeArray::ScopedRegistryLock* lock = nullptr);
330 /// @brief Clear the attribute set.
331 void clearAttributes(const bool updateValueMask = true,
332 const AttributeArray::ScopedRegistryLock* lock = nullptr);
333
334 /// @brief Returns @c true if an attribute with this index exists.
335 /// @param pos Index of the attribute
336 bool hasAttribute(const size_t pos) const;
337 /// @brief Returns @c true if an attribute with this name exists.
338 /// @param attributeName Name of the attribute
339 bool hasAttribute(const Name& attributeName) const;
340
341 /// @brief Append an attribute to the leaf.
342 /// @param expected Existing descriptor is expected to match this parameter.
343 /// @param replacement New descriptor to replace the existing one.
344 /// @param pos Index of the new attribute in the descriptor replacement.
345 /// @param strideOrTotalSize Stride of the attribute array (if constantStride), total size otherwise
346 /// @param constantStride if @c false, stride is interpreted as total size of the array
347 /// @param metadata optional default value metadata
348 /// @param lock an optional scoped registry lock to avoid contention
349 AttributeArray::Ptr appendAttribute(const Descriptor& expected, Descriptor::Ptr& replacement,
350 const size_t pos, const Index strideOrTotalSize = 1,
351 const bool constantStride = true,
352 const Metadata* metadata = nullptr,
353 const AttributeArray::ScopedRegistryLock* lock = nullptr);
354
355 /// @brief Drop list of attributes.
356 /// @param pos vector of attribute indices to drop
357 /// @param expected Existing descriptor is expected to match this parameter.
358 /// @param replacement New descriptor to replace the existing one.
359 void dropAttributes(const std::vector<size_t>& pos,
360 const Descriptor& expected, Descriptor::Ptr& replacement);
361 /// @brief Reorder attribute set.
362 /// @param replacement New descriptor to replace the existing one.
363 void reorderAttributes(const Descriptor::Ptr& replacement);
364 /// @brief Rename attributes in attribute set (order must remain the same).
365 /// @param expected Existing descriptor is expected to match this parameter.
366 /// @param replacement New descriptor to replace the existing one.
367 void renameAttributes(const Descriptor& expected, Descriptor::Ptr& replacement);
368 /// @brief Compact all attributes in attribute set.
369 void compactAttributes();
370
371 /// @brief Replace the underlying attribute set with the given @a attributeSet.
372 /// @details This leaf will assume ownership of the given attribute set. The descriptors must
373 /// match and the voxel offsets values will need updating if the point order is different.
374 /// @throws ValueError if @a allowMismatchingDescriptors is @c false and the descriptors
375 /// do not match
376 void replaceAttributeSet(AttributeSet* attributeSet, bool allowMismatchingDescriptors = false);
377
378 /// @brief Replace the descriptor with a new one
379 /// The new Descriptor must exactly match the old one
380 void resetDescriptor(const Descriptor::Ptr& replacement);
381
382 /// @brief Sets all of the voxel offset values on this leaf, from the given vector
383 /// of @a offsets. If @a updateValueMask is true, then the active value mask will
384 /// be updated so voxels with points are active and empty voxels are inactive.
385 void setOffsets(const std::vector<ValueType>& offsets, const bool updateValueMask = true);
386
387 /// @brief Throws an error if the voxel values on this leaf are not monotonically
388 /// increasing or within the bounds of the attribute arrays
389 void validateOffsets() const;
390
391 /// @brief Read-write attribute array reference from index
392 /// @details Attribute arrays can be shared across leaf nodes, so non-const
393 /// access will deep-copy the array to make it unique. Always prefer
394 /// accessing const arrays where possible to eliminate this copying.
395 /// {
396 AttributeArray& attributeArray(const size_t pos);
397 const AttributeArray& attributeArray(const size_t pos) const;
398 const AttributeArray& constAttributeArray(const size_t pos) const;
399 /// }
400 /// @brief Read-write attribute array reference from name
401 /// @details Attribute arrays can be shared across leaf nodes, so non-const
402 /// access will deep-copy the array to make it unique. Always prefer
403 /// accessing const arrays where possible to eliminate this copying.
404 /// {
405 AttributeArray& attributeArray(const Name& attributeName);
406 const AttributeArray& attributeArray(const Name& attributeName) const;
407 const AttributeArray& constAttributeArray(const Name& attributeName) const;
408 /// }
409
410 /// @brief Read-only group handle from group index
411 GroupHandle groupHandle(const AttributeSet::Descriptor::GroupIndex& index) const;
412 /// @brief Read-only group handle from group name
413 GroupHandle groupHandle(const Name& group) const;
414 /// @brief Read-write group handle from group index
415 GroupWriteHandle groupWriteHandle(const AttributeSet::Descriptor::GroupIndex& index);
416 /// @brief Read-write group handle from group name
417 GroupWriteHandle groupWriteHandle(const Name& name);
418
419 /// @brief Compute the total point count for the leaf
420 Index64 pointCount() const;
421 /// @brief Compute the total active (on) point count for the leaf
422 Index64 onPointCount() const;
423 /// @brief Compute the total inactive (off) point count for the leaf
424 Index64 offPointCount() const;
425 /// @brief Compute the point count in a specific group for the leaf
426 Index64 groupPointCount(const Name& groupName) const;
427
428 /// @brief Activate voxels with non-zero points, deactivate voxels with zero points.
429 void updateValueMask();
430
431 ////////////////////////////////////////
432
433 void setOffsetOn(Index offset, const ValueType& val);
434 void setOffsetOnly(Index offset, const ValueType& val);
435
436 /// @brief Return @c true if the given node (which may have a different @c ValueType
437 /// than this node) has the same active value topology as this node.
438 template<typename OtherType, Index OtherLog2Dim>
439 bool hasSameTopology(const PointDataLeafNode<OtherType, OtherLog2Dim>* other) const {
440 1443 return BaseLeaf::hasSameTopology(other);
441 }
442
443 /// Check for buffer, state and origin equivalence first.
444 /// If this returns true, do a deeper comparison on the attribute set to check
445 8 bool operator==(const PointDataLeafNode& other) const {
446
2/2
✓ Branch 1 taken 6 times.
✓ Branch 2 taken 2 times.
8 if(BaseLeaf::operator==(other) != true) return false;
447 6 return (*this->mAttributeSet == *other.mAttributeSet);
448 }
449
450
4/8
✓ Branch 1 taken 1 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✓ Branch 4 taken 1 times.
✓ Branch 6 taken 1 times.
✗ Branch 7 not taken.
✗ Branch 8 not taken.
✓ Branch 9 taken 1 times.
2 bool operator!=(const PointDataLeafNode& other) const { return !(other == *this); }
451
452 void addLeaf(PointDataLeafNode*) {}
453 template<typename AccessorT>
454 void addLeafAndCache(PointDataLeafNode*, AccessorT&) {}
455
456 //@{
457 /// @brief Return a pointer to this node.
458 PointDataLeafNode* touchLeaf(const Coord&) { return this; }
459 template<typename AccessorT>
460 PointDataLeafNode* touchLeafAndCache(const Coord&, AccessorT&) { return this; }
461
462 template<typename NodeT, typename AccessorT>
463 NodeT* probeNodeAndCache(const Coord&, AccessorT&)
464 {
465 OPENVDB_NO_UNREACHABLE_CODE_WARNING_BEGIN
466 if (!(std::is_same<NodeT,PointDataLeafNode>::value)) return nullptr;
467 return reinterpret_cast<NodeT*>(this);
468 OPENVDB_NO_UNREACHABLE_CODE_WARNING_END
469 }
470 PointDataLeafNode* probeLeaf(const Coord&) { return this; }
471 template<typename AccessorT>
472 PointDataLeafNode* probeLeafAndCache(const Coord&, AccessorT&) { return this; }
473 //@}
474
475 //@{
476 /// @brief Return a @const pointer to this node.
477 const PointDataLeafNode* probeConstLeaf(const Coord&) const { return this; }
478 template<typename AccessorT>
479 const PointDataLeafNode* probeConstLeafAndCache(const Coord&, AccessorT&) const { return this; }
480 template<typename AccessorT>
481 const PointDataLeafNode* probeLeafAndCache(const Coord&, AccessorT&) const { return this; }
482 const PointDataLeafNode* probeLeaf(const Coord&) const { return this; }
483 template<typename NodeT, typename AccessorT>
484 const NodeT* probeConstNodeAndCache(const Coord&, AccessorT&) const
485 {
486 OPENVDB_NO_UNREACHABLE_CODE_WARNING_BEGIN
487 if (!(std::is_same<NodeT,PointDataLeafNode>::value)) return nullptr;
488 return reinterpret_cast<const NodeT*>(this);
489 OPENVDB_NO_UNREACHABLE_CODE_WARNING_END
490 }
491 //@}
492
493 // I/O methods
494
495 void readTopology(std::istream& is, bool fromHalf = false);
496 void writeTopology(std::ostream& os, bool toHalf = false) const;
497
498 Index buffers() const;
499
500 void readBuffers(std::istream& is, bool fromHalf = false);
501 void readBuffers(std::istream& is, const CoordBBox&, bool fromHalf = false);
502 void writeBuffers(std::ostream& os, bool toHalf = false) const;
503
504
505 Index64 memUsage() const;
506 #if OPENVDB_ABI_VERSION_NUMBER >= 10
507 Index64 memUsageIfLoaded() const;
508 #endif
509
510 void evalActiveBoundingBox(CoordBBox& bbox, bool visitVoxels = true) const;
511
512 /// @brief Return the bounding box of this node, i.e., the full index space
513 /// spanned by this leaf node.
514 CoordBBox getNodeBoundingBox() const;
515
516 ////////////////////////////////////////
517
518 // Disable all write methods to avoid unintentional changes
519 // to the point-array offsets.
520
521 void assertNonmodifiable() {
522 assert(false && "Cannot modify voxel values in a PointDataTree.");
523 }
524
525 // some methods silently ignore attempts to modify the
526 // point-array offsets if a zero value is used
527
528 void assertNonModifiableUnlessZero(const ValueType& value) {
529
8/28
✗ Branch 0 not taken.
✓ Branch 1 taken 3863 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 10259 times.
✗ Branch 6 not taken.
✓ Branch 7 taken 16 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 2673 times.
✗ Branch 12 not taken.
✗ Branch 13 not taken.
✗ Branch 15 not taken.
✓ Branch 16 taken 24 times.
✗ Branch 18 not taken.
✓ Branch 19 taken 25 times.
✗ Branch 21 not taken.
✗ Branch 22 not taken.
✗ Branch 24 not taken.
✓ Branch 25 taken 24 times.
✗ Branch 27 not taken.
✓ Branch 28 taken 72 times.
✗ Branch 30 not taken.
✗ Branch 31 not taken.
✗ Branch 33 not taken.
✗ Branch 34 not taken.
✗ Branch 36 not taken.
✗ Branch 37 not taken.
✗ Branch 39 not taken.
✗ Branch 40 not taken.
16956 if (value != zeroVal<T>()) this->assertNonmodifiable();
530 }
531
532 void setActiveState(const Coord& xyz, bool on) { BaseLeaf::setActiveState(xyz, on); }
533 void setActiveState(Index offset, bool on) { BaseLeaf::setActiveState(offset, on); }
534
535 void setValueOnly(const Coord&, const ValueType&) { assertNonmodifiable(); }
536 void setValueOnly(Index, const ValueType&) { assertNonmodifiable(); }
537
538 void setValueOff(const Coord& xyz) { BaseLeaf::setValueOff(xyz); }
539 2669 void setValueOff(Index offset) { BaseLeaf::setValueOff(offset); }
540
541 void setValueOff(const Coord&, const ValueType&) { assertNonmodifiable(); }
542 void setValueOff(Index, const ValueType&) { assertNonmodifiable(); }
543
544 void setValueOn(const Coord& xyz) { BaseLeaf::setValueOn(xyz); }
545 5 void setValueOn(Index offset) { BaseLeaf::setValueOn(offset); }
546
547 void setValueOn(const Coord&, const ValueType&) { assertNonmodifiable(); }
548 void setValueOn(Index, const ValueType&) { assertNonmodifiable(); }
549
550 void setValue(const Coord&, const ValueType&) { assertNonmodifiable(); }
551
552 void setValuesOn() { BaseLeaf::setValuesOn(); }
553 void setValuesOff() { BaseLeaf::setValuesOff(); }
554
555 template<typename ModifyOp>
556 void modifyValue(Index, const ModifyOp&) { assertNonmodifiable(); }
557
558 template<typename ModifyOp>
559 void modifyValue(const Coord&, const ModifyOp&) { assertNonmodifiable(); }
560
561 template<typename ModifyOp>
562 void modifyValueAndActiveState(const Coord&, const ModifyOp&) { assertNonmodifiable(); }
563
564 // clipping is not yet supported
565 void clip(const CoordBBox&, const ValueType& value) { assertNonModifiableUnlessZero(value); }
566
567 void fill(const CoordBBox&, const ValueType&, bool);
568 void fill(const ValueType& value) { assertNonModifiableUnlessZero(value); }
569 void fill(const ValueType&, bool);
570
571 template<typename AccessorT>
572 void setValueOnlyAndCache(const Coord&, const ValueType&, AccessorT&) {assertNonmodifiable();}
573
574 template<typename ModifyOp, typename AccessorT>
575 void modifyValueAndActiveStateAndCache(const Coord&, const ModifyOp&, AccessorT&) {
576 assertNonmodifiable();
577 }
578
579 template<typename AccessorT>
580 void setValueOffAndCache(const Coord&, const ValueType&, AccessorT&) { assertNonmodifiable(); }
581
582 template<typename AccessorT>
583 void setActiveStateAndCache(const Coord& xyz, bool on, AccessorT& parent) {
584 BaseLeaf::setActiveStateAndCache(xyz, on, parent);
585 }
586
587 void resetBackground(const ValueType&, const ValueType& newBackground) {
588 assertNonModifiableUnlessZero(newBackground);
589 }
590
591 void signedFloodFill(const ValueType&) { assertNonmodifiable(); }
592 void signedFloodFill(const ValueType&, const ValueType&) { assertNonmodifiable(); }
593
594 void negate() { assertNonmodifiable(); }
595
596 friend class ::TestPointDataLeaf;
597
598 using ValueOn = typename BaseLeaf::ValueOn;
599 using ValueOff = typename BaseLeaf::ValueOff;
600 using ValueAll = typename BaseLeaf::ValueAll;
601
602 private:
603 AttributeSet::UniquePtr mAttributeSet;
604 uint16_t mVoxelBufferSize = 0;
605
606 protected:
607 using ChildOn = typename BaseLeaf::ChildOn;
608 using ChildOff = typename BaseLeaf::ChildOff;
609 using ChildAll = typename BaseLeaf::ChildAll;
610
611 using MaskOnIterator = typename NodeMaskType::OnIterator;
612 using MaskOffIterator = typename NodeMaskType::OffIterator;
613 using MaskDenseIterator = typename NodeMaskType::DenseIterator;
614
615 // During topology-only construction, access is needed
616 // to protected/private members of other template instances.
617 template<typename, Index> friend class PointDataLeafNode;
618
619 friend class tree::IteratorBase<MaskOnIterator, PointDataLeafNode>;
620 friend class tree::IteratorBase<MaskOffIterator, PointDataLeafNode>;
621 friend class tree::IteratorBase<MaskDenseIterator, PointDataLeafNode>;
622
623 public:
624 /// @brief Leaf value voxel iterator
625 ValueVoxelCIter beginValueVoxel(const Coord& ijk) const;
626
627 public:
628
629 using ValueOnIter = typename BaseLeaf::template ValueIter<
630 MaskOnIterator, PointDataLeafNode, const ValueType, ValueOn>;
631 using ValueOnCIter = typename BaseLeaf::template ValueIter<
632 MaskOnIterator, const PointDataLeafNode, const ValueType, ValueOn>;
633 using ValueOffIter = typename BaseLeaf::template ValueIter<
634 MaskOffIterator, PointDataLeafNode, const ValueType, ValueOff>;
635 using ValueOffCIter = typename BaseLeaf::template ValueIter<
636 MaskOffIterator,const PointDataLeafNode,const ValueType,ValueOff>;
637 using ValueAllIter = typename BaseLeaf::template ValueIter<
638 MaskDenseIterator, PointDataLeafNode, const ValueType, ValueAll>;
639 using ValueAllCIter = typename BaseLeaf::template ValueIter<
640 MaskDenseIterator,const PointDataLeafNode,const ValueType,ValueAll>;
641 using ChildOnIter = typename BaseLeaf::template ChildIter<
642 MaskOnIterator, PointDataLeafNode, ChildOn>;
643 using ChildOnCIter = typename BaseLeaf::template ChildIter<
644 MaskOnIterator, const PointDataLeafNode, ChildOn>;
645 using ChildOffIter = typename BaseLeaf::template ChildIter<
646 MaskOffIterator, PointDataLeafNode, ChildOff>;
647 using ChildOffCIter = typename BaseLeaf::template ChildIter<
648 MaskOffIterator, const PointDataLeafNode, ChildOff>;
649 using ChildAllIter = typename BaseLeaf::template DenseIter<
650 PointDataLeafNode, ValueType, ChildAll>;
651 using ChildAllCIter = typename BaseLeaf::template DenseIter<
652 const PointDataLeafNode, const ValueType, ChildAll>;
653
654 using IndexVoxelIter = IndexIter<ValueVoxelCIter, NullFilter>;
655 using IndexAllIter = IndexIter<ValueAllCIter, NullFilter>;
656 using IndexOnIter = IndexIter<ValueOnCIter, NullFilter>;
657 using IndexOffIter = IndexIter<ValueOffCIter, NullFilter>;
658
659 /// @brief Leaf index iterator
660 IndexAllIter beginIndexAll() const
661 {
662 NullFilter filter;
663 62 return this->beginIndex<ValueAllCIter, NullFilter>(filter);
664 }
665 29764 IndexOnIter beginIndexOn() const
666 {
667 NullFilter filter;
668 29764 return this->beginIndex<ValueOnCIter, NullFilter>(filter);
669 }
670 4 IndexOffIter beginIndexOff() const
671 {
672 NullFilter filter;
673 4 return this->beginIndex<ValueOffCIter, NullFilter>(filter);
674 }
675
676 template<typename IterT, typename FilterT>
677 IndexIter<IterT, FilterT> beginIndex(const FilterT& filter) const;
678
679 /// @brief Filtered leaf index iterator
680 template<typename FilterT>
681 IndexIter<ValueAllCIter, FilterT> beginIndexAll(const FilterT& filter) const
682 {
683
2/5
✓ Branch 1 taken 2 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✓ Branch 4 taken 6 times.
✗ Branch 5 not taken.
5919 return this->beginIndex<ValueAllCIter, FilterT>(filter);
684 }
685 template<typename FilterT>
686 IndexIter<ValueOnCIter, FilterT> beginIndexOn(const FilterT& filter) const
687 {
688
14/120
✓ Branch 1 taken 2976 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 2908 times.
✗ Branch 5 not taken.
✓ Branch 7 taken 2918 times.
✗ Branch 8 not taken.
✓ Branch 10 taken 2912 times.
✗ Branch 11 not taken.
✓ Branch 13 taken 10 times.
✗ Branch 14 not taken.
✓ Branch 16 taken 13 times.
✗ Branch 17 not taken.
✓ Branch 19 taken 56 times.
✗ Branch 20 not taken.
✓ Branch 22 taken 10 times.
✗ Branch 23 not taken.
✓ Branch 25 taken 8 times.
✗ Branch 26 not taken.
✗ Branch 28 not taken.
✗ Branch 29 not taken.
✗ Branch 31 not taken.
✗ Branch 32 not taken.
✗ Branch 34 not taken.
✗ Branch 35 not taken.
✗ Branch 37 not taken.
✗ Branch 38 not taken.
✗ Branch 40 not taken.
✗ Branch 41 not taken.
✗ Branch 43 not taken.
✗ Branch 44 not taken.
✗ Branch 46 not taken.
✗ Branch 47 not taken.
✓ Branch 49 taken 6 times.
✗ Branch 50 not taken.
✓ Branch 52 taken 3 times.
✗ Branch 53 not taken.
✗ Branch 55 not taken.
✗ Branch 56 not taken.
✗ Branch 58 not taken.
✗ Branch 59 not taken.
✗ Branch 61 not taken.
✗ Branch 62 not taken.
✗ Branch 64 not taken.
✗ Branch 65 not taken.
✗ Branch 67 not taken.
✗ Branch 68 not taken.
✗ Branch 70 not taken.
✗ Branch 71 not taken.
✗ Branch 73 not taken.
✗ Branch 74 not taken.
✗ Branch 76 not taken.
✗ Branch 77 not taken.
✗ Branch 79 not taken.
✗ Branch 80 not taken.
✗ Branch 82 not taken.
✗ Branch 83 not taken.
✗ Branch 85 not taken.
✗ Branch 86 not taken.
✗ Branch 88 not taken.
✗ Branch 89 not taken.
✗ Branch 91 not taken.
✗ Branch 92 not taken.
✗ Branch 94 not taken.
✗ Branch 95 not taken.
✗ Branch 97 not taken.
✗ Branch 98 not taken.
✓ Branch 100 taken 6 times.
✗ Branch 101 not taken.
✓ Branch 103 taken 9 times.
✗ Branch 104 not taken.
✗ Branch 106 not taken.
✗ Branch 107 not taken.
✗ Branch 109 not taken.
✗ Branch 110 not taken.
✗ Branch 112 not taken.
✗ Branch 113 not taken.
✗ Branch 115 not taken.
✗ Branch 116 not taken.
✗ Branch 118 not taken.
✗ Branch 119 not taken.
✗ Branch 121 not taken.
✗ Branch 122 not taken.
✗ Branch 124 not taken.
✗ Branch 125 not taken.
✗ Branch 127 not taken.
✗ Branch 128 not taken.
✗ Branch 130 not taken.
✗ Branch 131 not taken.
✗ Branch 133 not taken.
✗ Branch 134 not taken.
✗ Branch 136 not taken.
✗ Branch 137 not taken.
✗ Branch 139 not taken.
✗ Branch 140 not taken.
✗ Branch 142 not taken.
✗ Branch 143 not taken.
✗ Branch 145 not taken.
✗ Branch 146 not taken.
✗ Branch 148 not taken.
✗ Branch 149 not taken.
✗ Branch 151 not taken.
✗ Branch 152 not taken.
✗ Branch 154 not taken.
✗ Branch 155 not taken.
✗ Branch 157 not taken.
✗ Branch 158 not taken.
✗ Branch 160 not taken.
✗ Branch 161 not taken.
✗ Branch 163 not taken.
✗ Branch 164 not taken.
✗ Branch 166 not taken.
✗ Branch 167 not taken.
✗ Branch 169 not taken.
✗ Branch 170 not taken.
✓ Branch 172 taken 2 times.
✗ Branch 173 not taken.
✗ Branch 175 not taken.
✗ Branch 176 not taken.
✗ Branch 178 not taken.
✗ Branch 179 not taken.
49287 return this->beginIndex<ValueOnCIter, FilterT>(filter);
689 }
690 template<typename FilterT>
691 IndexIter<ValueOffCIter, FilterT> beginIndexOff(const FilterT& filter) const
692 {
693 return this->beginIndex<ValueOffCIter, FilterT>(filter);
694 }
695
696 /// @brief Leaf index iterator from voxel
697 IndexVoxelIter beginIndexVoxel(const Coord& ijk) const;
698
699 /// @brief Filtered leaf index iterator from voxel
700 template<typename FilterT>
701 IndexIter<ValueVoxelCIter, FilterT> beginIndexVoxel(const Coord& ijk, const FilterT& filter) const;
702
703 #define VMASK_ this->getValueMask()
704
1/4
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 5 taken 1 times.
✗ Branch 6 not taken.
79184 ValueOnCIter cbeginValueOn() const { return ValueOnCIter(VMASK_.beginOn(), this); }
705 ValueOnCIter beginValueOn() const { return ValueOnCIter(VMASK_.beginOn(), this); }
706 92 ValueOnIter beginValueOn() { return ValueOnIter(VMASK_.beginOn(), this); }
707 4 ValueOffCIter cbeginValueOff() const { return ValueOffCIter(VMASK_.beginOff(), this); }
708 ValueOffCIter beginValueOff() const { return ValueOffCIter(VMASK_.beginOff(), this); }
709 ValueOffIter beginValueOff() { return ValueOffIter(VMASK_.beginOff(), this); }
710 6041 ValueAllCIter cbeginValueAll() const { return ValueAllCIter(VMASK_.beginDense(), this); }
711 ValueAllCIter beginValueAll() const { return ValueAllCIter(VMASK_.beginDense(), this); }
712 4054 ValueAllIter beginValueAll() { return ValueAllIter(VMASK_.beginDense(), this); }
713
714 ValueOnCIter cendValueOn() const { return ValueOnCIter(VMASK_.endOn(), this); }
715 ValueOnCIter endValueOn() const { return ValueOnCIter(VMASK_.endOn(), this); }
716 ValueOnIter endValueOn() { return ValueOnIter(VMASK_.endOn(), this); }
717 ValueOffCIter cendValueOff() const { return ValueOffCIter(VMASK_.endOff(), this); }
718 ValueOffCIter endValueOff() const { return ValueOffCIter(VMASK_.endOff(), this); }
719 ValueOffIter endValueOff() { return ValueOffIter(VMASK_.endOff(), this); }
720 ValueAllCIter cendValueAll() const { return ValueAllCIter(VMASK_.endDense(), this); }
721 ValueAllCIter endValueAll() const { return ValueAllCIter(VMASK_.endDense(), this); }
722 ValueAllIter endValueAll() { return ValueAllIter(VMASK_.endDense(), this); }
723
724 19508 ChildOnCIter cbeginChildOn() const { return ChildOnCIter(VMASK_.endOn(), this); }
725 ChildOnCIter beginChildOn() const { return ChildOnCIter(VMASK_.endOn(), this); }
726 12454 ChildOnIter beginChildOn() { return ChildOnIter(VMASK_.endOn(), this); }
727 ChildOffCIter cbeginChildOff() const { return ChildOffCIter(VMASK_.endOff(), this); }
728 ChildOffCIter beginChildOff() const { return ChildOffCIter(VMASK_.endOff(), this); }
729 ChildOffIter beginChildOff() { return ChildOffIter(VMASK_.endOff(), this); }
730 ChildAllCIter cbeginChildAll() const { return ChildAllCIter(VMASK_.beginDense(), this); }
731 ChildAllCIter beginChildAll() const { return ChildAllCIter(VMASK_.beginDense(), this); }
732 ChildAllIter beginChildAll() { return ChildAllIter(VMASK_.beginDense(), this); }
733
734 ChildOnCIter cendChildOn() const { return ChildOnCIter(VMASK_.endOn(), this); }
735 ChildOnCIter endChildOn() const { return ChildOnCIter(VMASK_.endOn(), this); }
736 ChildOnIter endChildOn() { return ChildOnIter(VMASK_.endOn(), this); }
737 ChildOffCIter cendChildOff() const { return ChildOffCIter(VMASK_.endOff(), this); }
738 ChildOffCIter endChildOff() const { return ChildOffCIter(VMASK_.endOff(), this); }
739 ChildOffIter endChildOff() { return ChildOffIter(VMASK_.endOff(), this); }
740 ChildAllCIter cendChildAll() const { return ChildAllCIter(VMASK_.endDense(), this); }
741 ChildAllCIter endChildAll() const { return ChildAllCIter(VMASK_.endDense(), this); }
742 ChildAllIter endChildAll() { return ChildAllIter(VMASK_.endDense(), this); }
743 #undef VMASK_
744 }; // struct PointDataLeafNode
745
746 ////////////////////////////////////////
747
748 // PointDataLeafNode implementation
749
750 template<typename T, Index Log2Dim>
751 inline AttributeSet::UniquePtr
752 PointDataLeafNode<T, Log2Dim>::stealAttributeSet()
753 {
754
1/2
✓ Branch 1 taken 1 times.
✗ Branch 2 not taken.
1 AttributeSet::UniquePtr ptr = std::make_unique<AttributeSet>();
755 std::swap(ptr, mAttributeSet);
756 return ptr;
757 }
758
759 template<typename T, Index Log2Dim>
760 inline void
761
2/2
✓ Branch 0 taken 34972 times.
✓ Branch 1 taken 1 times.
34973 PointDataLeafNode<T, Log2Dim>::initializeAttributes(const Descriptor::Ptr& descriptor, const Index arrayLength,
762 const AttributeArray::ScopedRegistryLock* lock)
763 {
764
1/2
✓ Branch 0 taken 34972 times.
✗ Branch 1 not taken.
34972 if (descriptor->size() != 1 ||
765
8/10
✓ Branch 0 taken 34972 times.
✓ Branch 1 taken 1 times.
✓ Branch 4 taken 34972 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✓ Branch 7 taken 34972 times.
✓ Branch 8 taken 34972 times.
✓ Branch 9 taken 1 times.
✓ Branch 10 taken 1 times.
✓ Branch 11 taken 34972 times.
104917 descriptor->find("P") == AttributeSet::INVALID_POS ||
766
1/2
✓ Branch 1 taken 34972 times.
✗ Branch 2 not taken.
34972 descriptor->valueType(0) != typeNameAsString<Vec3f>())
767 {
768
2/6
✓ Branch 1 taken 1 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 1 times.
✗ Branch 5 not taken.
✗ Branch 12 not taken.
✗ Branch 13 not taken.
4 OPENVDB_THROW(IndexError, "Initializing attributes only allowed with one Vec3f position attribute.");
769 }
770
771
1/2
✓ Branch 2 taken 34972 times.
✗ Branch 3 not taken.
34972 mAttributeSet.reset(new AttributeSet(descriptor, arrayLength, lock));
772 34972 }
773
774 template<typename T, Index Log2Dim>
775 inline void
776 6 PointDataLeafNode<T, Log2Dim>::clearAttributes(const bool updateValueMask,
777 const AttributeArray::ScopedRegistryLock* lock)
778 {
779
1/2
✓ Branch 2 taken 6 times.
✗ Branch 3 not taken.
6 mAttributeSet.reset(new AttributeSet(*mAttributeSet, 0, lock));
780
781 // zero voxel values
782
783 6 this->buffer().fill(ValueType(0));
784
785 // if updateValueMask, also de-activate all voxels
786
787
2/2
✓ Branch 0 taken 5 times.
✓ Branch 1 taken 1 times.
6 if (updateValueMask) this->setValuesOff();
788 6 }
789
790 template<typename T, Index Log2Dim>
791 inline bool
792 PointDataLeafNode<T, Log2Dim>::hasAttribute(const size_t pos) const
793 {
794
2/4
✗ Branch 0 not taken.
✓ Branch 1 taken 1 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 1 times.
2 return pos < mAttributeSet->size();
795 }
796
797 template<typename T, Index Log2Dim>
798 inline bool
799 PointDataLeafNode<T, Log2Dim>::hasAttribute(const Name& attributeName) const
800 {
801
3/6
✓ Branch 1 taken 3 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 3 times.
✗ Branch 5 not taken.
✓ Branch 7 taken 2 times.
✗ Branch 8 not taken.
8 const size_t pos = mAttributeSet->find(attributeName);
802 6 return pos != AttributeSet::INVALID_POS;
803 }
804
805 template<typename T, Index Log2Dim>
806 inline AttributeArray::Ptr
807 PointDataLeafNode<T, Log2Dim>::appendAttribute( const Descriptor& expected, Descriptor::Ptr& replacement,
808 const size_t pos, const Index strideOrTotalSize,
809 const bool constantStride,
810 const Metadata* metadata,
811 const AttributeArray::ScopedRegistryLock* lock)
812 {
813 return mAttributeSet->appendAttribute(
814
14/28
✓ Branch 1 taken 34892 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 3137 times.
✗ Branch 5 not taken.
✓ Branch 7 taken 1 times.
✗ Branch 8 not taken.
✓ Branch 10 taken 1 times.
✗ Branch 11 not taken.
✓ Branch 13 taken 1 times.
✗ Branch 14 not taken.
✓ Branch 16 taken 1 times.
✗ Branch 17 not taken.
✓ Branch 19 taken 1 times.
✗ Branch 20 not taken.
✓ Branch 22 taken 1 times.
✗ Branch 23 not taken.
✓ Branch 25 taken 1 times.
✗ Branch 26 not taken.
✓ Branch 28 taken 1 times.
✗ Branch 29 not taken.
✓ Branch 31 taken 1 times.
✗ Branch 32 not taken.
✓ Branch 34 taken 1 times.
✗ Branch 35 not taken.
✓ Branch 37 taken 1 times.
✗ Branch 38 not taken.
✓ Branch 40 taken 1 times.
✗ Branch 41 not taken.
38041 expected, replacement, pos, strideOrTotalSize, constantStride, metadata, lock);
815 }
816
817 template<typename T, Index Log2Dim>
818 inline void
819 PointDataLeafNode<T, Log2Dim>::dropAttributes(const std::vector<size_t>& pos,
820 const Descriptor& expected, Descriptor::Ptr& replacement)
821 {
822
1/2
✓ Branch 1 taken 78 times.
✗ Branch 2 not taken.
78 mAttributeSet->dropAttributes(pos, expected, replacement);
823 78 }
824
825 template<typename T, Index Log2Dim>
826 inline void
827 PointDataLeafNode<T, Log2Dim>::reorderAttributes(const Descriptor::Ptr& replacement)
828 {
829 mAttributeSet->reorderAttributes(replacement);
830 }
831
832 template<typename T, Index Log2Dim>
833 inline void
834 PointDataLeafNode<T, Log2Dim>::renameAttributes(const Descriptor& expected, Descriptor::Ptr& replacement)
835 {
836
1/2
✓ Branch 1 taken 24 times.
✗ Branch 2 not taken.
24 mAttributeSet->renameAttributes(expected, replacement);
837 24 }
838
839 template<typename T, Index Log2Dim>
840 inline void
841 2 PointDataLeafNode<T, Log2Dim>::compactAttributes()
842 {
843
2/2
✓ Branch 0 taken 8 times.
✓ Branch 1 taken 2 times.
10 for (size_t i = 0; i < mAttributeSet->size(); i++) {
844 8 AttributeArray* array = mAttributeSet->get(i);
845 8 array->compact();
846 }
847 2 }
848
849 template<typename T, Index Log2Dim>
850 inline void
851 2501 PointDataLeafNode<T, Log2Dim>::replaceAttributeSet(AttributeSet* attributeSet, bool allowMismatchingDescriptors)
852 {
853
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 2500 times.
2501 if (!attributeSet) {
854
2/6
✓ Branch 1 taken 1 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 1 times.
✗ Branch 5 not taken.
✗ Branch 12 not taken.
✗ Branch 13 not taken.
4 OPENVDB_THROW(ValueError, "Cannot replace with a null attribute set");
855 }
856
857
4/4
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 2490 times.
✓ Branch 2 taken 1 times.
✓ Branch 3 taken 9 times.
2510 if (!allowMismatchingDescriptors && mAttributeSet->descriptor() != attributeSet->descriptor()) {
858
2/6
✓ Branch 1 taken 1 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 1 times.
✗ Branch 5 not taken.
✗ Branch 12 not taken.
✗ Branch 13 not taken.
4 OPENVDB_THROW(ValueError, "Attribute set descriptors are not equal.");
859 }
860
861 2499 mAttributeSet.reset(attributeSet);
862 2499 }
863
864 template<typename T, Index Log2Dim>
865 inline void
866 PointDataLeafNode<T, Log2Dim>::resetDescriptor(const Descriptor::Ptr& replacement)
867 {
868
2/4
✓ Branch 1 taken 3289 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 2900 times.
✗ Branch 5 not taken.
6189 mAttributeSet->resetDescriptor(replacement);
869 6189 }
870
871 template<typename T, Index Log2Dim>
872 inline void
873
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 16 times.
17 PointDataLeafNode<T, Log2Dim>::setOffsets(const std::vector<ValueType>& offsets, const bool updateValueMask)
874 {
875
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 16 times.
17 if (offsets.size() != LeafNodeType::NUM_VALUES) {
876
2/6
✓ Branch 1 taken 1 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 1 times.
✗ Branch 5 not taken.
✗ Branch 12 not taken.
✗ Branch 13 not taken.
4 OPENVDB_THROW(ValueError, "Offset vector size doesn't match number of voxels.")
877 }
878
879
2/2
✓ Branch 0 taken 8192 times.
✓ Branch 1 taken 16 times.
8208 for (Index index = 0; index < offsets.size(); ++index) {
880 setOffsetOnly(index, offsets[index]);
881 }
882
883
2/2
✓ Branch 0 taken 14 times.
✓ Branch 1 taken 2 times.
16 if (updateValueMask) this->updateValueMask();
884 16 }
885
886 template<typename T, Index Log2Dim>
887 inline void
888 9 PointDataLeafNode<T, Log2Dim>::validateOffsets() const
889 {
890 // Ensure all of the offset values are monotonically increasing
891
2/2
✓ Branch 0 taken 4089 times.
✓ Branch 1 taken 8 times.
4097 for (Index index = 1; index < BaseLeaf::SIZE; ++index) {
892
2/2
✓ Branch 2 taken 1 times.
✓ Branch 3 taken 4088 times.
4089 if (this->getValue(index-1) > this->getValue(index)) {
893
2/6
✓ Branch 1 taken 1 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 1 times.
✗ Branch 5 not taken.
✗ Branch 12 not taken.
✗ Branch 13 not taken.
4 OPENVDB_THROW(ValueError, "Voxel offset values are not monotonically increasing");
894 }
895 }
896
897 // Ensure all attribute arrays are of equal length
898
2/2
✓ Branch 0 taken 8 times.
✓ Branch 1 taken 7 times.
15 for (size_t attributeIndex = 1; attributeIndex < mAttributeSet->size(); ++attributeIndex ) {
899
2/2
✓ Branch 4 taken 1 times.
✓ Branch 5 taken 7 times.
8 if (mAttributeSet->getConst(attributeIndex-1)->size() != mAttributeSet->getConst(attributeIndex)->size()) {
900
2/6
✓ Branch 1 taken 1 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 1 times.
✗ Branch 5 not taken.
✗ Branch 12 not taken.
✗ Branch 13 not taken.
4 OPENVDB_THROW(ValueError, "Attribute arrays have inconsistent length");
901 }
902 }
903
904 // Ensure the last voxel's offset value matches the size of each attribute array
905
3/4
✓ Branch 0 taken 7 times.
✗ Branch 1 not taken.
✓ Branch 4 taken 3 times.
✓ Branch 5 taken 4 times.
14 if (mAttributeSet->size() > 0 && this->getValue(BaseLeaf::SIZE-1) != mAttributeSet->getConst(0)->size()) {
906
2/6
✓ Branch 1 taken 3 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 3 times.
✗ Branch 5 not taken.
✗ Branch 12 not taken.
✗ Branch 13 not taken.
12 OPENVDB_THROW(ValueError, "Last voxel offset value does not match attribute array length");
907 }
908 4 }
909
910 template<typename T, Index Log2Dim>
911 inline AttributeArray&
912
2/2
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 97320 times.
97322 PointDataLeafNode<T, Log2Dim>::attributeArray(const size_t pos)
913 {
914
3/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 97320 times.
✓ Branch 3 taken 2 times.
✗ Branch 4 not taken.
✗ Branch 11 not taken.
✗ Branch 12 not taken.
97328 if (pos >= mAttributeSet->size()) OPENVDB_THROW(LookupError, "Attribute Out Of Range - " << pos);
915 97320 return *mAttributeSet->get(pos);
916 }
917
918 template<typename T, Index Log2Dim>
919 inline const AttributeArray&
920
2/2
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 149865 times.
149867 PointDataLeafNode<T, Log2Dim>::attributeArray(const size_t pos) const
921 {
922
3/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 149865 times.
✓ Branch 3 taken 2 times.
✗ Branch 4 not taken.
✗ Branch 11 not taken.
✗ Branch 12 not taken.
149873 if (pos >= mAttributeSet->size()) OPENVDB_THROW(LookupError, "Attribute Out Of Range - " << pos);
923 149865 return *mAttributeSet->getConst(pos);
924 }
925
926 template<typename T, Index Log2Dim>
927 inline const AttributeArray&
928 PointDataLeafNode<T, Log2Dim>::constAttributeArray(const size_t pos) const
929 {
930
35/130
✓ Branch 1 taken 2 times.
✓ Branch 2 taken 5800 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 6 times.
✓ Branch 5 taken 5800 times.
✗ Branch 6 not taken.
✓ Branch 7 taken 4 times.
✓ Branch 8 taken 5800 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 2 times.
✗ Branch 11 not taken.
✓ Branch 12 taken 2707 times.
✓ Branch 13 taken 8 times.
✗ Branch 14 not taken.
✓ Branch 15 taken 5407 times.
✓ Branch 16 taken 11 times.
✗ Branch 17 not taken.
✓ Branch 18 taken 7 times.
✓ Branch 19 taken 4 times.
✗ Branch 20 not taken.
✗ Branch 21 not taken.
✓ Branch 22 taken 1 times.
✓ Branch 23 taken 1 times.
✗ Branch 24 not taken.
✓ Branch 25 taken 1 times.
✓ Branch 26 taken 1 times.
✗ Branch 27 not taken.
✗ Branch 28 not taken.
✗ Branch 29 not taken.
✗ Branch 30 not taken.
✗ Branch 31 not taken.
✗ Branch 32 not taken.
✗ Branch 34 not taken.
✗ Branch 35 not taken.
✓ Branch 37 taken 2 times.
✗ Branch 38 not taken.
✗ Branch 39 not taken.
✓ Branch 40 taken 2 times.
✗ Branch 41 not taken.
✗ Branch 42 not taken.
✓ Branch 43 taken 2 times.
✗ Branch 44 not taken.
✗ Branch 46 not taken.
✗ Branch 47 not taken.
✗ Branch 49 not taken.
✗ Branch 50 not taken.
✗ Branch 51 not taken.
✗ Branch 52 not taken.
✗ Branch 53 not taken.
✗ Branch 54 not taken.
✗ Branch 55 not taken.
✗ Branch 56 not taken.
✗ Branch 58 not taken.
✗ Branch 59 not taken.
✗ Branch 61 not taken.
✗ Branch 62 not taken.
✗ Branch 63 not taken.
✗ Branch 64 not taken.
✗ Branch 65 not taken.
✗ Branch 66 not taken.
✗ Branch 67 not taken.
✗ Branch 68 not taken.
✗ Branch 70 not taken.
✗ Branch 71 not taken.
✗ Branch 73 not taken.
✗ Branch 74 not taken.
✗ Branch 75 not taken.
✗ Branch 76 not taken.
✗ Branch 77 not taken.
✗ Branch 78 not taken.
✗ Branch 79 not taken.
✗ Branch 80 not taken.
✗ Branch 82 not taken.
✗ Branch 83 not taken.
✗ Branch 85 not taken.
✗ Branch 86 not taken.
✗ Branch 88 not taken.
✗ Branch 89 not taken.
✗ Branch 91 not taken.
✗ Branch 92 not taken.
✗ Branch 94 not taken.
✗ Branch 95 not taken.
✗ Branch 97 not taken.
✗ Branch 98 not taken.
✓ Branch 100 taken 4 times.
✗ Branch 101 not taken.
✓ Branch 103 taken 2 times.
✗ Branch 104 not taken.
✗ Branch 106 not taken.
✗ Branch 107 not taken.
✓ Branch 109 taken 2 times.
✗ Branch 110 not taken.
✓ Branch 112 taken 2 times.
✗ Branch 113 not taken.
✗ Branch 115 not taken.
✗ Branch 116 not taken.
✗ Branch 118 not taken.
✗ Branch 119 not taken.
✓ Branch 121 taken 8360 times.
✗ Branch 122 not taken.
✓ Branch 124 taken 8360 times.
✗ Branch 125 not taken.
✓ Branch 127 taken 6258 times.
✗ Branch 128 not taken.
✗ Branch 130 not taken.
✗ Branch 131 not taken.
✓ Branch 133 taken 2 times.
✗ Branch 134 not taken.
✓ Branch 136 taken 2 times.
✗ Branch 137 not taken.
✗ Branch 139 not taken.
✗ Branch 140 not taken.
✗ Branch 142 not taken.
✗ Branch 143 not taken.
✓ Branch 145 taken 2 times.
✗ Branch 146 not taken.
✓ Branch 148 taken 2 times.
✗ Branch 149 not taken.
✗ Branch 151 not taken.
✗ Branch 152 not taken.
✗ Branch 154 not taken.
✗ Branch 155 not taken.
✓ Branch 157 taken 7337 times.
✗ Branch 158 not taken.
✓ Branch 160 taken 14916 times.
✗ Branch 161 not taken.
✓ Branch 163 taken 10208 times.
✗ Branch 164 not taken.
✓ Branch 166 taken 1482 times.
✗ Branch 167 not taken.
121027 return this->attributeArray(pos);
931 }
932
933 template<typename T, Index Log2Dim>
934 inline AttributeArray&
935 6318 PointDataLeafNode<T, Log2Dim>::attributeArray(const Name& attributeName)
936 {
937 6318 const size_t pos = mAttributeSet->find(attributeName);
938
3/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 6316 times.
✓ Branch 3 taken 2 times.
✗ Branch 4 not taken.
✗ Branch 11 not taken.
✗ Branch 12 not taken.
6324 if (pos == AttributeSet::INVALID_POS) OPENVDB_THROW(LookupError, "Attribute Not Found - " << attributeName);
939 6316 return *mAttributeSet->get(pos);
940 }
941
942 template<typename T, Index Log2Dim>
943 inline const AttributeArray&
944 15653 PointDataLeafNode<T, Log2Dim>::attributeArray(const Name& attributeName) const
945 {
946 15653 const size_t pos = mAttributeSet->find(attributeName);
947
3/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 15651 times.
✓ Branch 3 taken 2 times.
✗ Branch 4 not taken.
✗ Branch 11 not taken.
✗ Branch 12 not taken.
15659 if (pos == AttributeSet::INVALID_POS) OPENVDB_THROW(LookupError, "Attribute Not Found - " << attributeName);
948 15651 return *mAttributeSet->getConst(pos);
949 }
950
951 template<typename T, Index Log2Dim>
952 inline const AttributeArray&
953 PointDataLeafNode<T, Log2Dim>::constAttributeArray(const Name& attributeName) const
954 {
955
88/1496
✓ Branch 1 taken 2858 times.
✓ Branch 2 taken 10 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 25 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✓ Branch 7 taken 11 times.
✗ Branch 8 not taken.
✓ Branch 9 taken 12 times.
✓ Branch 10 taken 8 times.
✗ Branch 11 not taken.
✗ Branch 12 not taken.
✓ Branch 13 taken 15 times.
✗ Branch 14 not taken.
✓ Branch 16 taken 12 times.
✗ Branch 17 not taken.
✓ Branch 19 taken 7 times.
✗ Branch 20 not taken.
✓ Branch 22 taken 12 times.
✗ Branch 23 not taken.
✓ Branch 25 taken 10 times.
✗ Branch 26 not taken.
✓ Branch 28 taken 650 times.
✗ Branch 29 not taken.
✓ Branch 31 taken 34 times.
✗ Branch 32 not taken.
✓ Branch 34 taken 4 times.
✗ Branch 35 not taken.
✓ Branch 37 taken 4 times.
✗ Branch 38 not taken.
✓ Branch 40 taken 4 times.
✗ Branch 41 not taken.
✓ Branch 43 taken 4 times.
✗ Branch 44 not taken.
✓ Branch 46 taken 25 times.
✗ Branch 47 not taken.
✓ Branch 49 taken 4 times.
✗ Branch 50 not taken.
✓ Branch 52 taken 4 times.
✗ Branch 53 not taken.
✓ Branch 55 taken 33 times.
✗ Branch 56 not taken.
✓ Branch 58 taken 49 times.
✗ Branch 59 not taken.
✓ Branch 61 taken 5 times.
✗ Branch 62 not taken.
✓ Branch 64 taken 5 times.
✗ Branch 65 not taken.
✓ Branch 67 taken 5 times.
✗ Branch 68 not taken.
✓ Branch 70 taken 38 times.
✗ Branch 71 not taken.
✓ Branch 73 taken 7 times.
✗ Branch 74 not taken.
✓ Branch 76 taken 4 times.
✗ Branch 77 not taken.
✓ Branch 79 taken 1 times.
✗ Branch 80 not taken.
✓ Branch 82 taken 1 times.
✗ Branch 83 not taken.
✓ Branch 85 taken 1 times.
✗ Branch 86 not taken.
✓ Branch 88 taken 1 times.
✗ Branch 89 not taken.
✓ Branch 91 taken 1 times.
✗ Branch 92 not taken.
✓ Branch 94 taken 1 times.
✗ Branch 95 not taken.
✓ Branch 97 taken 1 times.
✗ Branch 98 not taken.
✓ Branch 100 taken 2351 times.
✗ Branch 101 not taken.
✓ Branch 103 taken 10 times.
✗ Branch 104 not taken.
✓ Branch 106 taken 1 times.
✗ Branch 107 not taken.
✓ Branch 109 taken 1 times.
✗ Branch 110 not taken.
✓ Branch 112 taken 1 times.
✗ Branch 113 not taken.
✓ Branch 115 taken 1 times.
✗ Branch 116 not taken.
✓ Branch 118 taken 1 times.
✗ Branch 119 not taken.
✓ Branch 121 taken 1 times.
✗ Branch 122 not taken.
✓ Branch 124 taken 1 times.
✗ Branch 125 not taken.
✓ Branch 127 taken 2303 times.
✗ Branch 128 not taken.
✓ Branch 130 taken 3 times.
✗ Branch 131 not taken.
✓ Branch 133 taken 3 times.
✗ Branch 134 not taken.
✓ Branch 136 taken 3 times.
✗ Branch 137 not taken.
✗ Branch 139 not taken.
✗ Branch 140 not taken.
✗ Branch 142 not taken.
✗ Branch 143 not taken.
✗ Branch 145 not taken.
✗ Branch 146 not taken.
✗ Branch 148 not taken.
✗ Branch 149 not taken.
✓ Branch 151 taken 1127 times.
✗ Branch 152 not taken.
✓ Branch 154 taken 1127 times.
✗ Branch 155 not taken.
✓ Branch 157 taken 1170 times.
✗ Branch 158 not taken.
✓ Branch 160 taken 1170 times.
✗ Branch 161 not taken.
✓ Branch 163 taken 1178 times.
✗ Branch 164 not taken.
✓ Branch 166 taken 1178 times.
✗ Branch 167 not taken.
✓ Branch 169 taken 15 times.
✗ Branch 170 not taken.
✓ Branch 172 taken 15 times.
✗ Branch 173 not taken.
✓ Branch 175 taken 4 times.
✗ Branch 176 not taken.
✓ Branch 178 taken 4 times.
✗ Branch 179 not taken.
✓ Branch 181 taken 3 times.
✗ Branch 182 not taken.
✓ Branch 184 taken 3 times.
✗ Branch 185 not taken.
✓ Branch 187 taken 1 times.
✗ Branch 188 not taken.
✓ Branch 190 taken 1 times.
✗ Branch 191 not taken.
✓ Branch 193 taken 2 times.
✗ Branch 194 not taken.
✓ Branch 196 taken 2 times.
✗ Branch 197 not taken.
✓ Branch 199 taken 3 times.
✗ Branch 200 not taken.
✓ Branch 202 taken 3 times.
✗ Branch 203 not taken.
✓ Branch 205 taken 2 times.
✗ Branch 206 not taken.
✓ Branch 208 taken 2 times.
✗ Branch 209 not taken.
✗ Branch 211 not taken.
✗ Branch 212 not taken.
✗ Branch 214 not taken.
✗ Branch 215 not taken.
✗ Branch 217 not taken.
✗ Branch 218 not taken.
✗ Branch 220 not taken.
✗ Branch 221 not taken.
✗ Branch 223 not taken.
✗ Branch 224 not taken.
✗ Branch 226 not taken.
✗ Branch 227 not taken.
✗ Branch 229 not taken.
✗ Branch 230 not taken.
✗ Branch 232 not taken.
✗ Branch 233 not taken.
✗ Branch 235 not taken.
✗ Branch 236 not taken.
✗ Branch 238 not taken.
✗ Branch 239 not taken.
✗ Branch 241 not taken.
✗ Branch 242 not taken.
✗ Branch 244 not taken.
✗ Branch 245 not taken.
✗ Branch 247 not taken.
✗ Branch 248 not taken.
✗ Branch 250 not taken.
✗ Branch 251 not taken.
✗ Branch 253 not taken.
✗ Branch 254 not taken.
✗ Branch 256 not taken.
✗ Branch 257 not taken.
✗ Branch 259 not taken.
✗ Branch 260 not taken.
✗ Branch 262 not taken.
✗ Branch 263 not taken.
✗ Branch 265 not taken.
✗ Branch 266 not taken.
✗ Branch 268 not taken.
✗ Branch 269 not taken.
✗ Branch 271 not taken.
✗ Branch 272 not taken.
✗ Branch 274 not taken.
✗ Branch 275 not taken.
✗ Branch 277 not taken.
✗ Branch 278 not taken.
✗ Branch 280 not taken.
✗ Branch 281 not taken.
✗ Branch 283 not taken.
✗ Branch 284 not taken.
✗ Branch 286 not taken.
✗ Branch 287 not taken.
✗ Branch 289 not taken.
✗ Branch 290 not taken.
✗ Branch 292 not taken.
✗ Branch 293 not taken.
✗ Branch 295 not taken.
✗ Branch 296 not taken.
✗ Branch 298 not taken.
✗ Branch 299 not taken.
✗ Branch 301 not taken.
✗ Branch 302 not taken.
✗ Branch 304 not taken.
✗ Branch 305 not taken.
✗ Branch 307 not taken.
✗ Branch 308 not taken.
✗ Branch 310 not taken.
✗ Branch 311 not taken.
✗ Branch 313 not taken.
✗ Branch 314 not taken.
✗ Branch 316 not taken.
✗ Branch 317 not taken.
✗ Branch 319 not taken.
✗ Branch 320 not taken.
✗ Branch 322 not taken.
✗ Branch 323 not taken.
✗ Branch 325 not taken.
✗ Branch 326 not taken.
✗ Branch 328 not taken.
✗ Branch 329 not taken.
✗ Branch 331 not taken.
✗ Branch 332 not taken.
✗ Branch 334 not taken.
✗ Branch 335 not taken.
✗ Branch 337 not taken.
✗ Branch 338 not taken.
✓ Branch 340 taken 1 times.
✗ Branch 341 not taken.
✗ Branch 343 not taken.
✗ Branch 344 not taken.
✗ Branch 346 not taken.
✗ Branch 347 not taken.
✗ Branch 349 not taken.
✗ Branch 350 not taken.
✗ Branch 352 not taken.
✗ Branch 353 not taken.
✗ Branch 355 not taken.
✗ Branch 356 not taken.
✗ Branch 358 not taken.
✗ Branch 359 not taken.
✗ Branch 361 not taken.
✗ Branch 362 not taken.
✗ Branch 364 not taken.
✗ Branch 365 not taken.
✗ Branch 367 not taken.
✗ Branch 368 not taken.
✗ Branch 370 not taken.
✗ Branch 371 not taken.
✗ Branch 373 not taken.
✗ Branch 374 not taken.
✗ Branch 376 not taken.
✗ Branch 377 not taken.
✗ Branch 379 not taken.
✗ Branch 380 not taken.
✗ Branch 382 not taken.
✗ Branch 383 not taken.
✗ Branch 385 not taken.
✗ Branch 386 not taken.
✗ Branch 388 not taken.
✗ Branch 389 not taken.
✗ Branch 391 not taken.
✗ Branch 392 not taken.
✗ Branch 394 not taken.
✗ Branch 395 not taken.
✗ Branch 397 not taken.
✗ Branch 398 not taken.
✗ Branch 400 not taken.
✗ Branch 401 not taken.
✗ Branch 403 not taken.
✗ Branch 404 not taken.
✗ Branch 406 not taken.
✗ Branch 407 not taken.
✗ Branch 409 not taken.
✗ Branch 410 not taken.
✗ Branch 412 not taken.
✗ Branch 413 not taken.
✗ Branch 415 not taken.
✗ Branch 416 not taken.
✗ Branch 418 not taken.
✗ Branch 419 not taken.
✗ Branch 421 not taken.
✗ Branch 422 not taken.
✗ Branch 424 not taken.
✗ Branch 425 not taken.
✗ Branch 427 not taken.
✗ Branch 428 not taken.
✗ Branch 430 not taken.
✗ Branch 431 not taken.
✗ Branch 433 not taken.
✗ Branch 434 not taken.
✗ Branch 436 not taken.
✗ Branch 437 not taken.
✗ Branch 439 not taken.
✗ Branch 440 not taken.
✗ Branch 442 not taken.
✗ Branch 443 not taken.
✗ Branch 445 not taken.
✗ Branch 446 not taken.
✗ Branch 448 not taken.
✗ Branch 449 not taken.
✗ Branch 451 not taken.
✗ Branch 452 not taken.
✗ Branch 454 not taken.
✗ Branch 455 not taken.
✗ Branch 457 not taken.
✗ Branch 458 not taken.
✗ Branch 460 not taken.
✗ Branch 461 not taken.
✗ Branch 463 not taken.
✗ Branch 464 not taken.
✗ Branch 466 not taken.
✗ Branch 467 not taken.
✗ Branch 469 not taken.
✗ Branch 470 not taken.
✗ Branch 472 not taken.
✗ Branch 473 not taken.
✗ Branch 475 not taken.
✗ Branch 476 not taken.
✗ Branch 478 not taken.
✗ Branch 479 not taken.
✗ Branch 481 not taken.
✗ Branch 482 not taken.
✗ Branch 484 not taken.
✗ Branch 485 not taken.
✗ Branch 487 not taken.
✗ Branch 488 not taken.
✗ Branch 490 not taken.
✗ Branch 491 not taken.
✗ Branch 493 not taken.
✗ Branch 494 not taken.
✗ Branch 496 not taken.
✗ Branch 497 not taken.
✗ Branch 499 not taken.
✗ Branch 500 not taken.
✗ Branch 502 not taken.
✗ Branch 503 not taken.
✗ Branch 505 not taken.
✗ Branch 506 not taken.
✗ Branch 508 not taken.
✗ Branch 509 not taken.
✗ Branch 511 not taken.
✗ Branch 512 not taken.
✗ Branch 514 not taken.
✗ Branch 515 not taken.
✗ Branch 517 not taken.
✗ Branch 518 not taken.
✗ Branch 520 not taken.
✗ Branch 521 not taken.
✗ Branch 523 not taken.
✗ Branch 524 not taken.
✗ Branch 526 not taken.
✗ Branch 527 not taken.
✗ Branch 529 not taken.
✗ Branch 530 not taken.
✗ Branch 532 not taken.
✗ Branch 533 not taken.
✗ Branch 535 not taken.
✗ Branch 536 not taken.
✗ Branch 538 not taken.
✗ Branch 539 not taken.
✗ Branch 541 not taken.
✗ Branch 542 not taken.
✗ Branch 544 not taken.
✗ Branch 545 not taken.
✗ Branch 547 not taken.
✗ Branch 548 not taken.
✗ Branch 550 not taken.
✗ Branch 551 not taken.
✗ Branch 553 not taken.
✗ Branch 554 not taken.
✗ Branch 556 not taken.
✗ Branch 557 not taken.
✗ Branch 559 not taken.
✗ Branch 560 not taken.
✗ Branch 562 not taken.
✗ Branch 563 not taken.
✗ Branch 565 not taken.
✗ Branch 566 not taken.
✗ Branch 568 not taken.
✗ Branch 569 not taken.
✗ Branch 571 not taken.
✗ Branch 572 not taken.
✗ Branch 574 not taken.
✗ Branch 575 not taken.
✗ Branch 577 not taken.
✗ Branch 578 not taken.
✗ Branch 580 not taken.
✗ Branch 581 not taken.
✗ Branch 583 not taken.
✗ Branch 584 not taken.
✗ Branch 586 not taken.
✗ Branch 587 not taken.
✗ Branch 589 not taken.
✗ Branch 590 not taken.
✗ Branch 592 not taken.
✗ Branch 593 not taken.
✗ Branch 595 not taken.
✗ Branch 596 not taken.
✗ Branch 598 not taken.
✗ Branch 599 not taken.
✗ Branch 601 not taken.
✗ Branch 602 not taken.
✗ Branch 604 not taken.
✗ Branch 605 not taken.
✗ Branch 607 not taken.
✗ Branch 608 not taken.
✗ Branch 610 not taken.
✗ Branch 611 not taken.
✗ Branch 613 not taken.
✗ Branch 614 not taken.
✗ Branch 616 not taken.
✗ Branch 617 not taken.
✗ Branch 619 not taken.
✗ Branch 620 not taken.
✗ Branch 622 not taken.
✗ Branch 623 not taken.
✗ Branch 625 not taken.
✗ Branch 626 not taken.
✗ Branch 628 not taken.
✗ Branch 629 not taken.
✗ Branch 631 not taken.
✗ Branch 632 not taken.
✗ Branch 634 not taken.
✗ Branch 635 not taken.
✗ Branch 637 not taken.
✗ Branch 638 not taken.
✗ Branch 640 not taken.
✗ Branch 641 not taken.
✗ Branch 643 not taken.
✗ Branch 644 not taken.
✗ Branch 646 not taken.
✗ Branch 647 not taken.
✗ Branch 649 not taken.
✗ Branch 650 not taken.
✗ Branch 652 not taken.
✗ Branch 653 not taken.
✗ Branch 655 not taken.
✗ Branch 656 not taken.
✗ Branch 658 not taken.
✗ Branch 659 not taken.
✗ Branch 661 not taken.
✗ Branch 662 not taken.
✗ Branch 664 not taken.
✗ Branch 665 not taken.
✗ Branch 667 not taken.
✗ Branch 668 not taken.
✗ Branch 670 not taken.
✗ Branch 671 not taken.
✗ Branch 673 not taken.
✗ Branch 674 not taken.
✗ Branch 676 not taken.
✗ Branch 677 not taken.
✗ Branch 679 not taken.
✗ Branch 680 not taken.
✗ Branch 682 not taken.
✗ Branch 683 not taken.
✗ Branch 685 not taken.
✗ Branch 686 not taken.
✗ Branch 688 not taken.
✗ Branch 689 not taken.
✗ Branch 691 not taken.
✗ Branch 692 not taken.
✗ Branch 694 not taken.
✗ Branch 695 not taken.
✗ Branch 697 not taken.
✗ Branch 698 not taken.
✓ Branch 700 taken 1 times.
✗ Branch 701 not taken.
✗ Branch 703 not taken.
✗ Branch 704 not taken.
✗ Branch 706 not taken.
✗ Branch 707 not taken.
✗ Branch 709 not taken.
✗ Branch 710 not taken.
✗ Branch 712 not taken.
✗ Branch 713 not taken.
✗ Branch 715 not taken.
✗ Branch 716 not taken.
✗ Branch 718 not taken.
✗ Branch 719 not taken.
✗ Branch 721 not taken.
✗ Branch 722 not taken.
✗ Branch 724 not taken.
✗ Branch 725 not taken.
✗ Branch 727 not taken.
✗ Branch 728 not taken.
✗ Branch 730 not taken.
✗ Branch 731 not taken.
✗ Branch 733 not taken.
✗ Branch 734 not taken.
✗ Branch 736 not taken.
✗ Branch 737 not taken.
✗ Branch 739 not taken.
✗ Branch 740 not taken.
✗ Branch 742 not taken.
✗ Branch 743 not taken.
✗ Branch 745 not taken.
✗ Branch 746 not taken.
✗ Branch 748 not taken.
✗ Branch 749 not taken.
✗ Branch 751 not taken.
✗ Branch 752 not taken.
✗ Branch 754 not taken.
✗ Branch 755 not taken.
✗ Branch 757 not taken.
✗ Branch 758 not taken.
✗ Branch 760 not taken.
✗ Branch 761 not taken.
✗ Branch 763 not taken.
✗ Branch 764 not taken.
✗ Branch 766 not taken.
✗ Branch 767 not taken.
✗ Branch 769 not taken.
✗ Branch 770 not taken.
✗ Branch 772 not taken.
✗ Branch 773 not taken.
✗ Branch 775 not taken.
✗ Branch 776 not taken.
✗ Branch 778 not taken.
✗ Branch 779 not taken.
✗ Branch 781 not taken.
✗ Branch 782 not taken.
✗ Branch 784 not taken.
✗ Branch 785 not taken.
✗ Branch 787 not taken.
✗ Branch 788 not taken.
✗ Branch 790 not taken.
✗ Branch 791 not taken.
✗ Branch 793 not taken.
✗ Branch 794 not taken.
✗ Branch 796 not taken.
✗ Branch 797 not taken.
✗ Branch 799 not taken.
✗ Branch 800 not taken.
✗ Branch 802 not taken.
✗ Branch 803 not taken.
✗ Branch 805 not taken.
✗ Branch 806 not taken.
✗ Branch 808 not taken.
✗ Branch 809 not taken.
✗ Branch 811 not taken.
✗ Branch 812 not taken.
✗ Branch 814 not taken.
✗ Branch 815 not taken.
✗ Branch 817 not taken.
✗ Branch 818 not taken.
✗ Branch 820 not taken.
✗ Branch 821 not taken.
✗ Branch 823 not taken.
✗ Branch 824 not taken.
✗ Branch 826 not taken.
✗ Branch 827 not taken.
✗ Branch 829 not taken.
✗ Branch 830 not taken.
✗ Branch 832 not taken.
✗ Branch 833 not taken.
✗ Branch 835 not taken.
✗ Branch 836 not taken.
✗ Branch 838 not taken.
✗ Branch 839 not taken.
✗ Branch 841 not taken.
✗ Branch 842 not taken.
✗ Branch 844 not taken.
✗ Branch 845 not taken.
✗ Branch 847 not taken.
✗ Branch 848 not taken.
✗ Branch 850 not taken.
✗ Branch 851 not taken.
✗ Branch 853 not taken.
✗ Branch 854 not taken.
✗ Branch 856 not taken.
✗ Branch 857 not taken.
✗ Branch 859 not taken.
✗ Branch 860 not taken.
✗ Branch 862 not taken.
✗ Branch 863 not taken.
✗ Branch 865 not taken.
✗ Branch 866 not taken.
✗ Branch 868 not taken.
✗ Branch 869 not taken.
✗ Branch 871 not taken.
✗ Branch 872 not taken.
✗ Branch 874 not taken.
✗ Branch 875 not taken.
✗ Branch 877 not taken.
✗ Branch 878 not taken.
✗ Branch 880 not taken.
✗ Branch 881 not taken.
✗ Branch 883 not taken.
✗ Branch 884 not taken.
✗ Branch 886 not taken.
✗ Branch 887 not taken.
✗ Branch 889 not taken.
✗ Branch 890 not taken.
✓ Branch 892 taken 1 times.
✗ Branch 893 not taken.
✗ Branch 895 not taken.
✗ Branch 896 not taken.
✗ Branch 898 not taken.
✗ Branch 899 not taken.
✗ Branch 901 not taken.
✗ Branch 902 not taken.
✗ Branch 904 not taken.
✗ Branch 905 not taken.
✗ Branch 907 not taken.
✗ Branch 908 not taken.
✗ Branch 910 not taken.
✗ Branch 911 not taken.
✗ Branch 913 not taken.
✗ Branch 914 not taken.
✗ Branch 916 not taken.
✗ Branch 917 not taken.
✗ Branch 919 not taken.
✗ Branch 920 not taken.
✗ Branch 922 not taken.
✗ Branch 923 not taken.
✗ Branch 925 not taken.
✗ Branch 926 not taken.
✗ Branch 928 not taken.
✗ Branch 929 not taken.
✗ Branch 931 not taken.
✗ Branch 932 not taken.
✗ Branch 934 not taken.
✗ Branch 935 not taken.
✗ Branch 937 not taken.
✗ Branch 938 not taken.
✗ Branch 940 not taken.
✗ Branch 941 not taken.
✗ Branch 943 not taken.
✗ Branch 944 not taken.
✗ Branch 946 not taken.
✗ Branch 947 not taken.
✗ Branch 949 not taken.
✗ Branch 950 not taken.
✗ Branch 952 not taken.
✗ Branch 953 not taken.
✗ Branch 955 not taken.
✗ Branch 956 not taken.
✗ Branch 958 not taken.
✗ Branch 959 not taken.
✗ Branch 961 not taken.
✗ Branch 962 not taken.
✗ Branch 964 not taken.
✗ Branch 965 not taken.
✗ Branch 967 not taken.
✗ Branch 968 not taken.
✗ Branch 970 not taken.
✗ Branch 971 not taken.
✗ Branch 973 not taken.
✗ Branch 974 not taken.
✗ Branch 976 not taken.
✗ Branch 977 not taken.
✗ Branch 979 not taken.
✗ Branch 980 not taken.
✗ Branch 982 not taken.
✗ Branch 983 not taken.
✗ Branch 985 not taken.
✗ Branch 986 not taken.
✗ Branch 988 not taken.
✗ Branch 989 not taken.
✗ Branch 991 not taken.
✗ Branch 992 not taken.
✗ Branch 994 not taken.
✗ Branch 995 not taken.
✗ Branch 997 not taken.
✗ Branch 998 not taken.
✗ Branch 1000 not taken.
✗ Branch 1001 not taken.
✗ Branch 1003 not taken.
✗ Branch 1004 not taken.
✗ Branch 1006 not taken.
✗ Branch 1007 not taken.
✗ Branch 1009 not taken.
✗ Branch 1010 not taken.
✗ Branch 1012 not taken.
✗ Branch 1013 not taken.
✗ Branch 1015 not taken.
✗ Branch 1016 not taken.
✗ Branch 1018 not taken.
✗ Branch 1019 not taken.
✗ Branch 1021 not taken.
✗ Branch 1022 not taken.
✗ Branch 1024 not taken.
✗ Branch 1025 not taken.
✗ Branch 1027 not taken.
✗ Branch 1028 not taken.
✗ Branch 1030 not taken.
✗ Branch 1031 not taken.
✗ Branch 1033 not taken.
✗ Branch 1034 not taken.
✗ Branch 1036 not taken.
✗ Branch 1037 not taken.
✗ Branch 1039 not taken.
✗ Branch 1040 not taken.
✗ Branch 1042 not taken.
✗ Branch 1043 not taken.
✗ Branch 1045 not taken.
✗ Branch 1046 not taken.
✗ Branch 1048 not taken.
✗ Branch 1049 not taken.
✗ Branch 1051 not taken.
✗ Branch 1052 not taken.
✗ Branch 1054 not taken.
✗ Branch 1055 not taken.
✗ Branch 1057 not taken.
✗ Branch 1058 not taken.
✗ Branch 1060 not taken.
✗ Branch 1061 not taken.
✗ Branch 1063 not taken.
✗ Branch 1064 not taken.
✗ Branch 1066 not taken.
✗ Branch 1067 not taken.
✗ Branch 1069 not taken.
✗ Branch 1070 not taken.
✓ Branch 1072 taken 1 times.
✗ Branch 1073 not taken.
✗ Branch 1075 not taken.
✗ Branch 1076 not taken.
✗ Branch 1078 not taken.
✗ Branch 1079 not taken.
✗ Branch 1081 not taken.
✗ Branch 1082 not taken.
✗ Branch 1084 not taken.
✗ Branch 1085 not taken.
✗ Branch 1087 not taken.
✗ Branch 1088 not taken.
✗ Branch 1090 not taken.
✗ Branch 1091 not taken.
✗ Branch 1093 not taken.
✗ Branch 1094 not taken.
✗ Branch 1096 not taken.
✗ Branch 1097 not taken.
✗ Branch 1099 not taken.
✗ Branch 1100 not taken.
✗ Branch 1102 not taken.
✗ Branch 1103 not taken.
✗ Branch 1105 not taken.
✗ Branch 1106 not taken.
✗ Branch 1108 not taken.
✗ Branch 1109 not taken.
✗ Branch 1111 not taken.
✗ Branch 1112 not taken.
✗ Branch 1114 not taken.
✗ Branch 1115 not taken.
✗ Branch 1117 not taken.
✗ Branch 1118 not taken.
✗ Branch 1120 not taken.
✗ Branch 1121 not taken.
✗ Branch 1123 not taken.
✗ Branch 1124 not taken.
✗ Branch 1126 not taken.
✗ Branch 1127 not taken.
✗ Branch 1129 not taken.
✗ Branch 1130 not taken.
✗ Branch 1132 not taken.
✗ Branch 1133 not taken.
✗ Branch 1135 not taken.
✗ Branch 1136 not taken.
✗ Branch 1138 not taken.
✗ Branch 1139 not taken.
✗ Branch 1141 not taken.
✗ Branch 1142 not taken.
✗ Branch 1144 not taken.
✗ Branch 1145 not taken.
✗ Branch 1147 not taken.
✗ Branch 1148 not taken.
✗ Branch 1150 not taken.
✗ Branch 1151 not taken.
✗ Branch 1153 not taken.
✗ Branch 1154 not taken.
✗ Branch 1156 not taken.
✗ Branch 1157 not taken.
✗ Branch 1159 not taken.
✗ Branch 1160 not taken.
✗ Branch 1162 not taken.
✗ Branch 1163 not taken.
✗ Branch 1165 not taken.
✗ Branch 1166 not taken.
✗ Branch 1168 not taken.
✗ Branch 1169 not taken.
✗ Branch 1171 not taken.
✗ Branch 1172 not taken.
✗ Branch 1174 not taken.
✗ Branch 1175 not taken.
✗ Branch 1177 not taken.
✗ Branch 1178 not taken.
✗ Branch 1180 not taken.
✗ Branch 1181 not taken.
✗ Branch 1183 not taken.
✗ Branch 1184 not taken.
✗ Branch 1186 not taken.
✗ Branch 1187 not taken.
✗ Branch 1189 not taken.
✗ Branch 1190 not taken.
✗ Branch 1192 not taken.
✗ Branch 1193 not taken.
✗ Branch 1195 not taken.
✗ Branch 1196 not taken.
✗ Branch 1198 not taken.
✗ Branch 1199 not taken.
✗ Branch 1201 not taken.
✗ Branch 1202 not taken.
✗ Branch 1204 not taken.
✗ Branch 1205 not taken.
✗ Branch 1207 not taken.
✗ Branch 1208 not taken.
✗ Branch 1210 not taken.
✗ Branch 1211 not taken.
✗ Branch 1213 not taken.
✗ Branch 1214 not taken.
✗ Branch 1216 not taken.
✗ Branch 1217 not taken.
✗ Branch 1219 not taken.
✗ Branch 1220 not taken.
✗ Branch 1222 not taken.
✗ Branch 1223 not taken.
✗ Branch 1225 not taken.
✗ Branch 1226 not taken.
✗ Branch 1228 not taken.
✗ Branch 1229 not taken.
✗ Branch 1231 not taken.
✗ Branch 1232 not taken.
✗ Branch 1234 not taken.
✗ Branch 1235 not taken.
✗ Branch 1237 not taken.
✗ Branch 1238 not taken.
✗ Branch 1240 not taken.
✗ Branch 1241 not taken.
✗ Branch 1243 not taken.
✗ Branch 1244 not taken.
✗ Branch 1246 not taken.
✗ Branch 1247 not taken.
✗ Branch 1249 not taken.
✗ Branch 1250 not taken.
✓ Branch 1252 taken 1 times.
✗ Branch 1253 not taken.
✗ Branch 1255 not taken.
✗ Branch 1256 not taken.
✗ Branch 1258 not taken.
✗ Branch 1259 not taken.
✗ Branch 1261 not taken.
✗ Branch 1262 not taken.
✗ Branch 1264 not taken.
✗ Branch 1265 not taken.
✗ Branch 1267 not taken.
✗ Branch 1268 not taken.
✗ Branch 1270 not taken.
✗ Branch 1271 not taken.
✗ Branch 1273 not taken.
✗ Branch 1274 not taken.
✗ Branch 1276 not taken.
✗ Branch 1277 not taken.
✗ Branch 1279 not taken.
✗ Branch 1280 not taken.
✗ Branch 1282 not taken.
✗ Branch 1283 not taken.
✗ Branch 1285 not taken.
✗ Branch 1286 not taken.
✗ Branch 1288 not taken.
✗ Branch 1289 not taken.
✗ Branch 1291 not taken.
✗ Branch 1292 not taken.
✗ Branch 1294 not taken.
✗ Branch 1295 not taken.
✗ Branch 1297 not taken.
✗ Branch 1298 not taken.
✗ Branch 1300 not taken.
✗ Branch 1301 not taken.
✗ Branch 1303 not taken.
✗ Branch 1304 not taken.
✗ Branch 1306 not taken.
✗ Branch 1307 not taken.
✗ Branch 1309 not taken.
✗ Branch 1310 not taken.
✗ Branch 1312 not taken.
✗ Branch 1313 not taken.
✗ Branch 1315 not taken.
✗ Branch 1316 not taken.
✓ Branch 1318 taken 1 times.
✗ Branch 1319 not taken.
✗ Branch 1321 not taken.
✗ Branch 1322 not taken.
✗ Branch 1324 not taken.
✗ Branch 1325 not taken.
✗ Branch 1327 not taken.
✗ Branch 1328 not taken.
✗ Branch 1330 not taken.
✗ Branch 1331 not taken.
✗ Branch 1333 not taken.
✗ Branch 1334 not taken.
✗ Branch 1336 not taken.
✗ Branch 1337 not taken.
✗ Branch 1339 not taken.
✗ Branch 1340 not taken.
✗ Branch 1342 not taken.
✗ Branch 1343 not taken.
✗ Branch 1345 not taken.
✗ Branch 1346 not taken.
✗ Branch 1348 not taken.
✗ Branch 1349 not taken.
✗ Branch 1351 not taken.
✗ Branch 1352 not taken.
✗ Branch 1354 not taken.
✗ Branch 1355 not taken.
✗ Branch 1357 not taken.
✗ Branch 1358 not taken.
✗ Branch 1360 not taken.
✗ Branch 1361 not taken.
✗ Branch 1363 not taken.
✗ Branch 1364 not taken.
✗ Branch 1366 not taken.
✗ Branch 1367 not taken.
✗ Branch 1369 not taken.
✗ Branch 1370 not taken.
✗ Branch 1372 not taken.
✗ Branch 1373 not taken.
✗ Branch 1375 not taken.
✗ Branch 1376 not taken.
✗ Branch 1378 not taken.
✗ Branch 1379 not taken.
✗ Branch 1381 not taken.
✗ Branch 1382 not taken.
✗ Branch 1384 not taken.
✗ Branch 1385 not taken.
✗ Branch 1387 not taken.
✗ Branch 1388 not taken.
✗ Branch 1390 not taken.
✗ Branch 1391 not taken.
✗ Branch 1393 not taken.
✗ Branch 1394 not taken.
✗ Branch 1396 not taken.
✗ Branch 1397 not taken.
✗ Branch 1399 not taken.
✗ Branch 1400 not taken.
✗ Branch 1402 not taken.
✗ Branch 1403 not taken.
✗ Branch 1405 not taken.
✗ Branch 1406 not taken.
✗ Branch 1408 not taken.
✗ Branch 1409 not taken.
✗ Branch 1411 not taken.
✗ Branch 1412 not taken.
✗ Branch 1414 not taken.
✗ Branch 1415 not taken.
✗ Branch 1417 not taken.
✗ Branch 1418 not taken.
✗ Branch 1420 not taken.
✗ Branch 1421 not taken.
✗ Branch 1423 not taken.
✗ Branch 1424 not taken.
✗ Branch 1426 not taken.
✗ Branch 1427 not taken.
✗ Branch 1429 not taken.
✗ Branch 1430 not taken.
✗ Branch 1432 not taken.
✗ Branch 1433 not taken.
✗ Branch 1435 not taken.
✗ Branch 1436 not taken.
✗ Branch 1438 not taken.
✗ Branch 1439 not taken.
✗ Branch 1441 not taken.
✗ Branch 1442 not taken.
✗ Branch 1444 not taken.
✗ Branch 1445 not taken.
✗ Branch 1447 not taken.
✗ Branch 1448 not taken.
✗ Branch 1450 not taken.
✗ Branch 1451 not taken.
✗ Branch 1453 not taken.
✗ Branch 1454 not taken.
✗ Branch 1456 not taken.
✗ Branch 1457 not taken.
✗ Branch 1459 not taken.
✗ Branch 1460 not taken.
✗ Branch 1462 not taken.
✗ Branch 1463 not taken.
✗ Branch 1465 not taken.
✗ Branch 1466 not taken.
✗ Branch 1468 not taken.
✗ Branch 1469 not taken.
✗ Branch 1471 not taken.
✗ Branch 1472 not taken.
✗ Branch 1474 not taken.
✗ Branch 1475 not taken.
✗ Branch 1477 not taken.
✗ Branch 1478 not taken.
✗ Branch 1480 not taken.
✗ Branch 1481 not taken.
✗ Branch 1483 not taken.
✗ Branch 1484 not taken.
✗ Branch 1486 not taken.
✗ Branch 1487 not taken.
✗ Branch 1489 not taken.
✗ Branch 1490 not taken.
✓ Branch 1492 taken 2 times.
✗ Branch 1493 not taken.
✗ Branch 1495 not taken.
✗ Branch 1496 not taken.
✗ Branch 1498 not taken.
✗ Branch 1499 not taken.
✗ Branch 1501 not taken.
✗ Branch 1502 not taken.
✗ Branch 1504 not taken.
✗ Branch 1505 not taken.
✗ Branch 1507 not taken.
✗ Branch 1508 not taken.
✗ Branch 1510 not taken.
✗ Branch 1511 not taken.
✗ Branch 1513 not taken.
✗ Branch 1514 not taken.
✗ Branch 1516 not taken.
✗ Branch 1517 not taken.
✗ Branch 1519 not taken.
✗ Branch 1520 not taken.
✗ Branch 1522 not taken.
✗ Branch 1523 not taken.
✗ Branch 1525 not taken.
✗ Branch 1526 not taken.
✗ Branch 1528 not taken.
✗ Branch 1529 not taken.
✗ Branch 1531 not taken.
✗ Branch 1532 not taken.
✗ Branch 1534 not taken.
✗ Branch 1535 not taken.
✗ Branch 1537 not taken.
✗ Branch 1538 not taken.
✗ Branch 1540 not taken.
✗ Branch 1541 not taken.
✗ Branch 1543 not taken.
✗ Branch 1544 not taken.
✗ Branch 1546 not taken.
✗ Branch 1547 not taken.
✗ Branch 1549 not taken.
✗ Branch 1550 not taken.
✗ Branch 1552 not taken.
✗ Branch 1553 not taken.
✗ Branch 1555 not taken.
✗ Branch 1556 not taken.
✗ Branch 1558 not taken.
✗ Branch 1559 not taken.
✗ Branch 1561 not taken.
✗ Branch 1562 not taken.
✗ Branch 1564 not taken.
✗ Branch 1565 not taken.
✗ Branch 1567 not taken.
✗ Branch 1568 not taken.
✗ Branch 1570 not taken.
✗ Branch 1571 not taken.
✗ Branch 1573 not taken.
✗ Branch 1574 not taken.
✗ Branch 1576 not taken.
✗ Branch 1577 not taken.
✗ Branch 1579 not taken.
✗ Branch 1580 not taken.
✗ Branch 1582 not taken.
✗ Branch 1583 not taken.
✗ Branch 1585 not taken.
✗ Branch 1586 not taken.
✗ Branch 1588 not taken.
✗ Branch 1589 not taken.
✗ Branch 1591 not taken.
✗ Branch 1592 not taken.
✗ Branch 1594 not taken.
✗ Branch 1595 not taken.
✗ Branch 1597 not taken.
✗ Branch 1598 not taken.
✗ Branch 1600 not taken.
✗ Branch 1601 not taken.
✗ Branch 1603 not taken.
✗ Branch 1604 not taken.
✗ Branch 1606 not taken.
✗ Branch 1607 not taken.
✗ Branch 1609 not taken.
✗ Branch 1610 not taken.
✗ Branch 1612 not taken.
✗ Branch 1613 not taken.
✗ Branch 1615 not taken.
✗ Branch 1616 not taken.
✗ Branch 1618 not taken.
✗ Branch 1619 not taken.
✗ Branch 1621 not taken.
✗ Branch 1622 not taken.
✗ Branch 1624 not taken.
✗ Branch 1625 not taken.
✗ Branch 1627 not taken.
✗ Branch 1628 not taken.
✗ Branch 1630 not taken.
✗ Branch 1631 not taken.
✗ Branch 1633 not taken.
✗ Branch 1634 not taken.
✗ Branch 1636 not taken.
✗ Branch 1637 not taken.
✗ Branch 1639 not taken.
✗ Branch 1640 not taken.
✗ Branch 1642 not taken.
✗ Branch 1643 not taken.
✗ Branch 1645 not taken.
✗ Branch 1646 not taken.
✗ Branch 1648 not taken.
✗ Branch 1649 not taken.
✗ Branch 1651 not taken.
✗ Branch 1652 not taken.
✗ Branch 1654 not taken.
✗ Branch 1655 not taken.
✗ Branch 1657 not taken.
✗ Branch 1658 not taken.
✗ Branch 1660 not taken.
✗ Branch 1661 not taken.
✗ Branch 1663 not taken.
✗ Branch 1664 not taken.
✗ Branch 1666 not taken.
✗ Branch 1667 not taken.
✗ Branch 1669 not taken.
✗ Branch 1670 not taken.
✗ Branch 1672 not taken.
✗ Branch 1673 not taken.
✗ Branch 1675 not taken.
✗ Branch 1676 not taken.
✗ Branch 1678 not taken.
✗ Branch 1679 not taken.
✗ Branch 1681 not taken.
✗ Branch 1682 not taken.
✗ Branch 1684 not taken.
✗ Branch 1685 not taken.
✗ Branch 1687 not taken.
✗ Branch 1688 not taken.
✓ Branch 1690 taken 1 times.
✗ Branch 1691 not taken.
✗ Branch 1693 not taken.
✗ Branch 1694 not taken.
✗ Branch 1696 not taken.
✗ Branch 1697 not taken.
✗ Branch 1699 not taken.
✗ Branch 1700 not taken.
✗ Branch 1702 not taken.
✗ Branch 1703 not taken.
✗ Branch 1705 not taken.
✗ Branch 1706 not taken.
✗ Branch 1708 not taken.
✗ Branch 1709 not taken.
✗ Branch 1711 not taken.
✗ Branch 1712 not taken.
✗ Branch 1714 not taken.
✗ Branch 1715 not taken.
✗ Branch 1717 not taken.
✗ Branch 1718 not taken.
✗ Branch 1720 not taken.
✗ Branch 1721 not taken.
✗ Branch 1723 not taken.
✗ Branch 1724 not taken.
✗ Branch 1726 not taken.
✗ Branch 1727 not taken.
✗ Branch 1729 not taken.
✗ Branch 1730 not taken.
✗ Branch 1732 not taken.
✗ Branch 1733 not taken.
✗ Branch 1735 not taken.
✗ Branch 1736 not taken.
✗ Branch 1738 not taken.
✗ Branch 1739 not taken.
✗ Branch 1741 not taken.
✗ Branch 1742 not taken.
✗ Branch 1744 not taken.
✗ Branch 1745 not taken.
✗ Branch 1747 not taken.
✗ Branch 1748 not taken.
✗ Branch 1750 not taken.
✗ Branch 1751 not taken.
✗ Branch 1753 not taken.
✗ Branch 1754 not taken.
✗ Branch 1756 not taken.
✗ Branch 1757 not taken.
✗ Branch 1759 not taken.
✗ Branch 1760 not taken.
✓ Branch 1762 taken 1 times.
✗ Branch 1763 not taken.
✗ Branch 1765 not taken.
✗ Branch 1766 not taken.
✗ Branch 1768 not taken.
✗ Branch 1769 not taken.
✗ Branch 1771 not taken.
✗ Branch 1772 not taken.
✗ Branch 1774 not taken.
✗ Branch 1775 not taken.
✗ Branch 1777 not taken.
✗ Branch 1778 not taken.
✗ Branch 1780 not taken.
✗ Branch 1781 not taken.
✗ Branch 1783 not taken.
✗ Branch 1784 not taken.
✗ Branch 1786 not taken.
✗ Branch 1787 not taken.
✗ Branch 1789 not taken.
✗ Branch 1790 not taken.
✗ Branch 1792 not taken.
✗ Branch 1793 not taken.
✗ Branch 1795 not taken.
✗ Branch 1796 not taken.
✗ Branch 1798 not taken.
✗ Branch 1799 not taken.
✗ Branch 1801 not taken.
✗ Branch 1802 not taken.
✗ Branch 1804 not taken.
✗ Branch 1805 not taken.
✗ Branch 1807 not taken.
✗ Branch 1808 not taken.
✗ Branch 1810 not taken.
✗ Branch 1811 not taken.
✗ Branch 1813 not taken.
✗ Branch 1814 not taken.
✗ Branch 1816 not taken.
✗ Branch 1817 not taken.
✗ Branch 1819 not taken.
✗ Branch 1820 not taken.
✗ Branch 1822 not taken.
✗ Branch 1823 not taken.
✗ Branch 1825 not taken.
✗ Branch 1826 not taken.
✗ Branch 1828 not taken.
✗ Branch 1829 not taken.
✗ Branch 1831 not taken.
✗ Branch 1832 not taken.
✗ Branch 1834 not taken.
✗ Branch 1835 not taken.
✗ Branch 1837 not taken.
✗ Branch 1838 not taken.
✗ Branch 1840 not taken.
✗ Branch 1841 not taken.
✗ Branch 1843 not taken.
✗ Branch 1844 not taken.
✗ Branch 1846 not taken.
✗ Branch 1847 not taken.
✗ Branch 1849 not taken.
✗ Branch 1850 not taken.
✗ Branch 1852 not taken.
✗ Branch 1853 not taken.
✗ Branch 1855 not taken.
✗ Branch 1856 not taken.
✗ Branch 1858 not taken.
✗ Branch 1859 not taken.
✗ Branch 1861 not taken.
✗ Branch 1862 not taken.
✓ Branch 1864 taken 1 times.
✗ Branch 1865 not taken.
✓ Branch 1867 taken 1 times.
✗ Branch 1868 not taken.
✓ Branch 1870 taken 1 times.
✗ Branch 1871 not taken.
✗ Branch 1873 not taken.
✗ Branch 1874 not taken.
✓ Branch 1876 taken 1 times.
✗ Branch 1877 not taken.
✗ Branch 1879 not taken.
✗ Branch 1880 not taken.
✗ Branch 1882 not taken.
✗ Branch 1883 not taken.
✗ Branch 1885 not taken.
✗ Branch 1886 not taken.
✗ Branch 1888 not taken.
✗ Branch 1889 not taken.
✗ Branch 1891 not taken.
✗ Branch 1892 not taken.
✗ Branch 1894 not taken.
✗ Branch 1895 not taken.
✗ Branch 1897 not taken.
✗ Branch 1898 not taken.
✗ Branch 1900 not taken.
✗ Branch 1901 not taken.
✗ Branch 1903 not taken.
✗ Branch 1904 not taken.
✗ Branch 1906 not taken.
✗ Branch 1907 not taken.
✗ Branch 1909 not taken.
✗ Branch 1910 not taken.
✗ Branch 1912 not taken.
✗ Branch 1913 not taken.
✗ Branch 1915 not taken.
✗ Branch 1916 not taken.
✗ Branch 1918 not taken.
✗ Branch 1919 not taken.
✗ Branch 1921 not taken.
✗ Branch 1922 not taken.
✗ Branch 1924 not taken.
✗ Branch 1925 not taken.
✗ Branch 1927 not taken.
✗ Branch 1928 not taken.
✗ Branch 1930 not taken.
✗ Branch 1931 not taken.
✗ Branch 1933 not taken.
✗ Branch 1934 not taken.
✗ Branch 1936 not taken.
✗ Branch 1937 not taken.
✗ Branch 1939 not taken.
✗ Branch 1940 not taken.
✗ Branch 1942 not taken.
✗ Branch 1943 not taken.
✗ Branch 1945 not taken.
✗ Branch 1946 not taken.
✗ Branch 1948 not taken.
✗ Branch 1949 not taken.
✗ Branch 1951 not taken.
✗ Branch 1952 not taken.
✗ Branch 1954 not taken.
✗ Branch 1955 not taken.
✗ Branch 1957 not taken.
✗ Branch 1958 not taken.
✗ Branch 1960 not taken.
✗ Branch 1961 not taken.
✗ Branch 1963 not taken.
✗ Branch 1964 not taken.
✓ Branch 1966 taken 1 times.
✗ Branch 1967 not taken.
✗ Branch 1969 not taken.
✗ Branch 1970 not taken.
✗ Branch 1972 not taken.
✗ Branch 1973 not taken.
✗ Branch 1975 not taken.
✗ Branch 1976 not taken.
✗ Branch 1978 not taken.
✗ Branch 1979 not taken.
✗ Branch 1981 not taken.
✗ Branch 1982 not taken.
✗ Branch 1984 not taken.
✗ Branch 1985 not taken.
✗ Branch 1987 not taken.
✗ Branch 1988 not taken.
✗ Branch 1990 not taken.
✗ Branch 1991 not taken.
✗ Branch 1993 not taken.
✗ Branch 1994 not taken.
✗ Branch 1996 not taken.
✗ Branch 1997 not taken.
✗ Branch 1999 not taken.
✗ Branch 2000 not taken.
✗ Branch 2002 not taken.
✗ Branch 2003 not taken.
✗ Branch 2005 not taken.
✗ Branch 2006 not taken.
✗ Branch 2008 not taken.
✗ Branch 2009 not taken.
✗ Branch 2011 not taken.
✗ Branch 2012 not taken.
✗ Branch 2014 not taken.
✗ Branch 2015 not taken.
✗ Branch 2017 not taken.
✗ Branch 2018 not taken.
✗ Branch 2020 not taken.
✗ Branch 2021 not taken.
✗ Branch 2023 not taken.
✗ Branch 2024 not taken.
✗ Branch 2026 not taken.
✗ Branch 2027 not taken.
✗ Branch 2029 not taken.
✗ Branch 2030 not taken.
✗ Branch 2032 not taken.
✗ Branch 2033 not taken.
✗ Branch 2035 not taken.
✗ Branch 2036 not taken.
✗ Branch 2038 not taken.
✗ Branch 2039 not taken.
✗ Branch 2041 not taken.
✗ Branch 2042 not taken.
✗ Branch 2044 not taken.
✗ Branch 2045 not taken.
✗ Branch 2047 not taken.
✗ Branch 2048 not taken.
✗ Branch 2050 not taken.
✗ Branch 2051 not taken.
✗ Branch 2053 not taken.
✗ Branch 2054 not taken.
✗ Branch 2056 not taken.
✗ Branch 2057 not taken.
✗ Branch 2059 not taken.
✗ Branch 2060 not taken.
✗ Branch 2062 not taken.
✗ Branch 2063 not taken.
✗ Branch 2065 not taken.
✗ Branch 2066 not taken.
✗ Branch 2068 not taken.
✗ Branch 2069 not taken.
✗ Branch 2071 not taken.
✗ Branch 2072 not taken.
✗ Branch 2074 not taken.
✗ Branch 2075 not taken.
✗ Branch 2077 not taken.
✗ Branch 2078 not taken.
✗ Branch 2080 not taken.
✗ Branch 2081 not taken.
✗ Branch 2083 not taken.
✗ Branch 2084 not taken.
✗ Branch 2086 not taken.
✗ Branch 2087 not taken.
✗ Branch 2089 not taken.
✗ Branch 2090 not taken.
✗ Branch 2092 not taken.
✗ Branch 2093 not taken.
✗ Branch 2095 not taken.
✗ Branch 2096 not taken.
✗ Branch 2098 not taken.
✗ Branch 2099 not taken.
✗ Branch 2101 not taken.
✗ Branch 2102 not taken.
✗ Branch 2104 not taken.
✗ Branch 2105 not taken.
✗ Branch 2107 not taken.
✗ Branch 2108 not taken.
✗ Branch 2110 not taken.
✗ Branch 2111 not taken.
✗ Branch 2113 not taken.
✗ Branch 2114 not taken.
✗ Branch 2116 not taken.
✗ Branch 2117 not taken.
✗ Branch 2119 not taken.
✗ Branch 2120 not taken.
✗ Branch 2122 not taken.
✗ Branch 2123 not taken.
✗ Branch 2125 not taken.
✗ Branch 2126 not taken.
✗ Branch 2128 not taken.
✗ Branch 2129 not taken.
✗ Branch 2131 not taken.
✗ Branch 2132 not taken.
✗ Branch 2134 not taken.
✗ Branch 2135 not taken.
✗ Branch 2137 not taken.
✗ Branch 2138 not taken.
✗ Branch 2140 not taken.
✗ Branch 2141 not taken.
✗ Branch 2143 not taken.
✗ Branch 2144 not taken.
✗ Branch 2146 not taken.
✗ Branch 2147 not taken.
✗ Branch 2149 not taken.
✗ Branch 2150 not taken.
✗ Branch 2152 not taken.
✗ Branch 2153 not taken.
✗ Branch 2155 not taken.
✗ Branch 2156 not taken.
✗ Branch 2158 not taken.
✗ Branch 2159 not taken.
✗ Branch 2161 not taken.
✗ Branch 2162 not taken.
✗ Branch 2164 not taken.
✗ Branch 2165 not taken.
✗ Branch 2167 not taken.
✗ Branch 2168 not taken.
✗ Branch 2170 not taken.
✗ Branch 2171 not taken.
✗ Branch 2173 not taken.
✗ Branch 2174 not taken.
✗ Branch 2176 not taken.
✗ Branch 2177 not taken.
✗ Branch 2179 not taken.
✗ Branch 2180 not taken.
✓ Branch 2182 taken 3 times.
✗ Branch 2183 not taken.
✗ Branch 2185 not taken.
✗ Branch 2186 not taken.
✗ Branch 2188 not taken.
✗ Branch 2189 not taken.
✗ Branch 2191 not taken.
✗ Branch 2192 not taken.
✗ Branch 2194 not taken.
✗ Branch 2195 not taken.
✗ Branch 2197 not taken.
✗ Branch 2198 not taken.
✗ Branch 2200 not taken.
✗ Branch 2201 not taken.
✗ Branch 2203 not taken.
✗ Branch 2204 not taken.
✗ Branch 2206 not taken.
✗ Branch 2207 not taken.
✓ Branch 2209 taken 1 times.
✗ Branch 2210 not taken.
✗ Branch 2212 not taken.
✗ Branch 2213 not taken.
✓ Branch 2215 taken 1 times.
✗ Branch 2216 not taken.
✓ Branch 2218 taken 1 times.
✗ Branch 2219 not taken.
✓ Branch 2221 taken 1 times.
✗ Branch 2222 not taken.
✗ Branch 2224 not taken.
✗ Branch 2225 not taken.
✗ Branch 2227 not taken.
✗ Branch 2228 not taken.
✗ Branch 2230 not taken.
✗ Branch 2231 not taken.
✓ Branch 2233 taken 1 times.
✗ Branch 2234 not taken.
✗ Branch 2236 not taken.
✗ Branch 2237 not taken.
15599 return this->attributeArray(attributeName);
956 }
957
958 template<typename T, Index Log2Dim>
959 inline GroupHandle
960 28833 PointDataLeafNode<T, Log2Dim>::groupHandle(const AttributeSet::Descriptor::GroupIndex& index) const
961 {
962 28833 const AttributeArray& array = this->attributeArray(index.first);
963
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 28833 times.
28833 assert(isGroup(array));
964
965 28833 const GroupAttributeArray& groupArray = GroupAttributeArray::cast(array);
966
967 28833 return GroupHandle(groupArray, index.second);
968 }
969
970 template<typename T, Index Log2Dim>
971 inline GroupHandle
972 20 PointDataLeafNode<T, Log2Dim>::groupHandle(const Name& name) const
973 {
974 20 const AttributeSet::Descriptor::GroupIndex index = this->attributeSet().groupIndex(name);
975 20 return this->groupHandle(index);
976 }
977
978 template<typename T, Index Log2Dim>
979 inline GroupWriteHandle
980 3340 PointDataLeafNode<T, Log2Dim>::groupWriteHandle(const AttributeSet::Descriptor::GroupIndex& index)
981 {
982 3340 AttributeArray& array = this->attributeArray(index.first);
983
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 3340 times.
3340 assert(isGroup(array));
984
985 3340 GroupAttributeArray& groupArray = GroupAttributeArray::cast(array);
986
987 3340 return GroupWriteHandle(groupArray, index.second);
988 }
989
990 template<typename T, Index Log2Dim>
991 inline GroupWriteHandle
992 58 PointDataLeafNode<T, Log2Dim>::groupWriteHandle(const Name& name)
993 {
994 58 const AttributeSet::Descriptor::GroupIndex index = this->attributeSet().groupIndex(name);
995 58 return this->groupWriteHandle(index);
996 }
997
998 template<typename T, Index Log2Dim>
999 template<typename ValueIterT, typename FilterT>
1000 inline IndexIter<ValueIterT, FilterT>
1001
1/2
✓ Branch 0 taken 4 times.
✗ Branch 1 not taken.
41186 PointDataLeafNode<T, Log2Dim>::beginIndex(const FilterT& filter) const
1002 {
1003 // generate no-op iterator if filter evaluates no indices
1004
1005
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 9 times.
18 if (filter.state() == index::NONE) {
1006 return IndexIter<ValueIterT, FilterT>(ValueIterT(), filter);
1007 }
1008
1009 // copy filter to ensure thread-safety
1010
1011 81760 FilterT newFilter(filter);
1012
1/2
✓ Branch 1 taken 20643 times.
✗ Branch 2 not taken.
41148 newFilter.reset(*this);
1013
1014 using IterTraitsT = tree::IterTraits<LeafNodeType, ValueIterT>;
1015
1016 // construct the value iterator and reset the filter to use this leaf
1017
1018 ValueIterT valueIter = IterTraitsT::begin(*this);
1019
1020
59/1389
✓ Branch 1 taken 23497 times.
✓ Branch 2 taken 11 times.
✓ Branch 3 taken 1 times.
✓ Branch 4 taken 10 times.
✓ Branch 5 taken 1 times.
✗ Branch 6 not taken.
✓ Branch 7 taken 6 times.
✓ Branch 8 taken 11 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 11 times.
✓ Branch 11 taken 1 times.
✗ Branch 12 not taken.
✓ Branch 13 taken 9 times.
✓ Branch 14 taken 13 times.
✗ Branch 15 not taken.
✓ Branch 16 taken 8 times.
✓ Branch 17 taken 49 times.
✗ Branch 18 not taken.
✓ Branch 19 taken 648 times.
✓ Branch 20 taken 1 times.
✗ Branch 21 not taken.
✓ Branch 22 taken 10 times.
✓ Branch 23 taken 1 times.
✗ Branch 24 not taken.
✓ Branch 25 taken 8 times.
✓ Branch 26 taken 2 times.
✗ Branch 27 not taken.
✓ Branch 28 taken 8360 times.
✓ Branch 29 taken 1 times.
✗ Branch 30 not taken.
✓ Branch 31 taken 5 times.
✓ Branch 32 taken 1 times.
✗ Branch 33 not taken.
✓ Branch 34 taken 7 times.
✓ Branch 35 taken 1 times.
✗ Branch 36 not taken.
✓ Branch 37 taken 14924 times.
✓ Branch 38 taken 1 times.
✗ Branch 39 not taken.
✓ Branch 40 taken 648 times.
✓ Branch 41 taken 1 times.
✗ Branch 42 not taken.
✗ Branch 43 not taken.
✓ Branch 44 taken 1 times.
✗ Branch 45 not taken.
✓ Branch 46 taken 3 times.
✗ Branch 47 not taken.
✓ Branch 49 taken 2353 times.
✗ Branch 50 not taken.
✓ Branch 52 taken 3 times.
✗ Branch 53 not taken.
✓ Branch 55 taken 3 times.
✗ Branch 56 not taken.
✗ Branch 58 not taken.
✗ Branch 59 not taken.
✗ Branch 61 not taken.
✗ Branch 62 not taken.
✗ Branch 64 not taken.
✗ Branch 65 not taken.
✗ Branch 67 not taken.
✗ Branch 68 not taken.
✗ Branch 70 not taken.
✗ Branch 71 not taken.
✗ Branch 73 not taken.
✗ Branch 74 not taken.
✓ Branch 76 taken 3 times.
✗ Branch 77 not taken.
✗ Branch 79 not taken.
✗ Branch 80 not taken.
✗ Branch 82 not taken.
✗ Branch 83 not taken.
✗ Branch 85 not taken.
✗ Branch 86 not taken.
✗ Branch 88 not taken.
✗ Branch 89 not taken.
✗ Branch 91 not taken.
✗ Branch 92 not taken.
✗ Branch 94 not taken.
✗ Branch 95 not taken.
✗ Branch 97 not taken.
✗ Branch 98 not taken.
✓ Branch 100 taken 2350 times.
✗ Branch 101 not taken.
✓ Branch 103 taken 2303 times.
✗ Branch 104 not taken.
✓ Branch 106 taken 3 times.
✗ Branch 107 not taken.
✓ Branch 109 taken 3 times.
✗ Branch 110 not taken.
✓ Branch 112 taken 3 times.
✗ Branch 113 not taken.
✗ Branch 115 not taken.
✗ Branch 116 not taken.
✗ Branch 118 not taken.
✗ Branch 119 not taken.
✗ Branch 121 not taken.
✗ Branch 122 not taken.
✗ Branch 124 not taken.
✗ Branch 125 not taken.
✗ Branch 127 not taken.
✗ Branch 128 not taken.
✗ Branch 130 not taken.
✗ Branch 131 not taken.
✗ Branch 133 not taken.
✗ Branch 134 not taken.
✗ Branch 136 not taken.
✗ Branch 137 not taken.
✗ Branch 139 not taken.
✗ Branch 140 not taken.
✗ Branch 142 not taken.
✗ Branch 143 not taken.
✗ Branch 145 not taken.
✗ Branch 146 not taken.
✗ Branch 148 not taken.
✗ Branch 149 not taken.
✗ Branch 151 not taken.
✗ Branch 152 not taken.
✗ Branch 154 not taken.
✗ Branch 155 not taken.
✗ Branch 157 not taken.
✗ Branch 158 not taken.
✗ Branch 160 not taken.
✗ Branch 161 not taken.
✗ Branch 163 not taken.
✗ Branch 164 not taken.
✗ Branch 166 not taken.
✗ Branch 167 not taken.
✗ Branch 169 not taken.
✗ Branch 170 not taken.
✗ Branch 172 not taken.
✗ Branch 173 not taken.
✗ Branch 175 not taken.
✗ Branch 176 not taken.
✗ Branch 178 not taken.
✗ Branch 179 not taken.
✗ Branch 181 not taken.
✗ Branch 182 not taken.
✗ Branch 184 not taken.
✗ Branch 185 not taken.
✗ Branch 187 not taken.
✗ Branch 188 not taken.
✗ Branch 190 not taken.
✗ Branch 191 not taken.
✗ Branch 193 not taken.
✗ Branch 194 not taken.
✗ Branch 196 not taken.
✗ Branch 197 not taken.
✗ Branch 199 not taken.
✗ Branch 200 not taken.
✗ Branch 202 not taken.
✗ Branch 203 not taken.
✗ Branch 205 not taken.
✗ Branch 206 not taken.
✗ Branch 208 not taken.
✗ Branch 209 not taken.
✗ Branch 211 not taken.
✗ Branch 212 not taken.
✗ Branch 214 not taken.
✗ Branch 215 not taken.
✗ Branch 217 not taken.
✗ Branch 218 not taken.
✗ Branch 220 not taken.
✗ Branch 221 not taken.
✗ Branch 223 not taken.
✗ Branch 224 not taken.
✗ Branch 226 not taken.
✗ Branch 227 not taken.
✗ Branch 229 not taken.
✗ Branch 230 not taken.
✗ Branch 232 not taken.
✗ Branch 233 not taken.
✗ Branch 235 not taken.
✗ Branch 236 not taken.
✗ Branch 238 not taken.
✗ Branch 239 not taken.
✗ Branch 241 not taken.
✗ Branch 242 not taken.
✗ Branch 244 not taken.
✗ Branch 245 not taken.
✗ Branch 247 not taken.
✗ Branch 248 not taken.
✗ Branch 250 not taken.
✗ Branch 251 not taken.
✗ Branch 253 not taken.
✗ Branch 254 not taken.
✗ Branch 256 not taken.
✗ Branch 257 not taken.
✗ Branch 259 not taken.
✗ Branch 260 not taken.
✗ Branch 262 not taken.
✗ Branch 263 not taken.
✗ Branch 265 not taken.
✗ Branch 266 not taken.
✗ Branch 268 not taken.
✗ Branch 269 not taken.
✗ Branch 271 not taken.
✗ Branch 272 not taken.
✗ Branch 274 not taken.
✗ Branch 275 not taken.
✗ Branch 277 not taken.
✗ Branch 278 not taken.
✗ Branch 280 not taken.
✗ Branch 281 not taken.
✗ Branch 283 not taken.
✗ Branch 284 not taken.
✗ Branch 286 not taken.
✗ Branch 287 not taken.
✗ Branch 289 not taken.
✗ Branch 290 not taken.
✗ Branch 292 not taken.
✗ Branch 293 not taken.
✗ Branch 295 not taken.
✗ Branch 296 not taken.
✗ Branch 298 not taken.
✗ Branch 299 not taken.
✗ Branch 301 not taken.
✗ Branch 302 not taken.
✗ Branch 304 not taken.
✗ Branch 305 not taken.
✗ Branch 307 not taken.
✗ Branch 308 not taken.
✗ Branch 310 not taken.
✗ Branch 311 not taken.
✗ Branch 313 not taken.
✗ Branch 314 not taken.
✗ Branch 316 not taken.
✗ Branch 317 not taken.
✗ Branch 319 not taken.
✗ Branch 320 not taken.
✗ Branch 322 not taken.
✗ Branch 323 not taken.
✗ Branch 325 not taken.
✗ Branch 326 not taken.
✗ Branch 328 not taken.
✗ Branch 329 not taken.
✗ Branch 331 not taken.
✗ Branch 332 not taken.
✗ Branch 334 not taken.
✗ Branch 335 not taken.
✗ Branch 337 not taken.
✗ Branch 338 not taken.
✗ Branch 340 not taken.
✗ Branch 341 not taken.
✓ Branch 343 taken 1 times.
✗ Branch 344 not taken.
✗ Branch 346 not taken.
✗ Branch 347 not taken.
✗ Branch 349 not taken.
✗ Branch 350 not taken.
✗ Branch 352 not taken.
✗ Branch 353 not taken.
✗ Branch 355 not taken.
✗ Branch 356 not taken.
✗ Branch 358 not taken.
✗ Branch 359 not taken.
✗ Branch 361 not taken.
✗ Branch 362 not taken.
✗ Branch 364 not taken.
✗ Branch 365 not taken.
✗ Branch 367 not taken.
✗ Branch 368 not taken.
✗ Branch 370 not taken.
✗ Branch 371 not taken.
✗ Branch 373 not taken.
✗ Branch 374 not taken.
✗ Branch 376 not taken.
✗ Branch 377 not taken.
✗ Branch 379 not taken.
✗ Branch 380 not taken.
✗ Branch 382 not taken.
✗ Branch 383 not taken.
✗ Branch 385 not taken.
✗ Branch 386 not taken.
✗ Branch 388 not taken.
✗ Branch 389 not taken.
✗ Branch 391 not taken.
✗ Branch 392 not taken.
✗ Branch 394 not taken.
✗ Branch 395 not taken.
✗ Branch 397 not taken.
✗ Branch 398 not taken.
✗ Branch 400 not taken.
✗ Branch 401 not taken.
✗ Branch 403 not taken.
✗ Branch 404 not taken.
✗ Branch 406 not taken.
✗ Branch 407 not taken.
✗ Branch 409 not taken.
✗ Branch 410 not taken.
✗ Branch 412 not taken.
✗ Branch 413 not taken.
✗ Branch 415 not taken.
✗ Branch 416 not taken.
✗ Branch 418 not taken.
✗ Branch 419 not taken.
✗ Branch 421 not taken.
✗ Branch 422 not taken.
✗ Branch 424 not taken.
✗ Branch 425 not taken.
✗ Branch 427 not taken.
✗ Branch 428 not taken.
✗ Branch 430 not taken.
✗ Branch 431 not taken.
✗ Branch 433 not taken.
✗ Branch 434 not taken.
✗ Branch 436 not taken.
✗ Branch 437 not taken.
✗ Branch 439 not taken.
✗ Branch 440 not taken.
✗ Branch 442 not taken.
✗ Branch 443 not taken.
✗ Branch 445 not taken.
✗ Branch 446 not taken.
✗ Branch 448 not taken.
✗ Branch 449 not taken.
✗ Branch 451 not taken.
✗ Branch 452 not taken.
✗ Branch 454 not taken.
✗ Branch 455 not taken.
✗ Branch 457 not taken.
✗ Branch 458 not taken.
✗ Branch 460 not taken.
✗ Branch 461 not taken.
✗ Branch 463 not taken.
✗ Branch 464 not taken.
✗ Branch 466 not taken.
✗ Branch 467 not taken.
✗ Branch 469 not taken.
✗ Branch 470 not taken.
✗ Branch 472 not taken.
✗ Branch 473 not taken.
✗ Branch 475 not taken.
✗ Branch 476 not taken.
✗ Branch 478 not taken.
✗ Branch 479 not taken.
✗ Branch 481 not taken.
✗ Branch 482 not taken.
✗ Branch 484 not taken.
✗ Branch 485 not taken.
✗ Branch 487 not taken.
✗ Branch 488 not taken.
✗ Branch 490 not taken.
✗ Branch 491 not taken.
✗ Branch 493 not taken.
✗ Branch 494 not taken.
✗ Branch 496 not taken.
✗ Branch 497 not taken.
✗ Branch 499 not taken.
✗ Branch 500 not taken.
✗ Branch 502 not taken.
✗ Branch 503 not taken.
✗ Branch 505 not taken.
✗ Branch 506 not taken.
✗ Branch 508 not taken.
✗ Branch 509 not taken.
✗ Branch 511 not taken.
✗ Branch 512 not taken.
✗ Branch 514 not taken.
✗ Branch 515 not taken.
✗ Branch 517 not taken.
✗ Branch 518 not taken.
✗ Branch 520 not taken.
✗ Branch 521 not taken.
✗ Branch 523 not taken.
✗ Branch 524 not taken.
✗ Branch 526 not taken.
✗ Branch 527 not taken.
✗ Branch 529 not taken.
✗ Branch 530 not taken.
✗ Branch 532 not taken.
✗ Branch 533 not taken.
✗ Branch 535 not taken.
✗ Branch 536 not taken.
✗ Branch 538 not taken.
✗ Branch 539 not taken.
✗ Branch 541 not taken.
✗ Branch 542 not taken.
✗ Branch 544 not taken.
✗ Branch 545 not taken.
✗ Branch 547 not taken.
✗ Branch 548 not taken.
✗ Branch 550 not taken.
✗ Branch 551 not taken.
✗ Branch 553 not taken.
✗ Branch 554 not taken.
✗ Branch 556 not taken.
✗ Branch 557 not taken.
✗ Branch 559 not taken.
✗ Branch 560 not taken.
✗ Branch 562 not taken.
✗ Branch 563 not taken.
✗ Branch 565 not taken.
✗ Branch 566 not taken.
✗ Branch 568 not taken.
✗ Branch 569 not taken.
✗ Branch 571 not taken.
✗ Branch 572 not taken.
✗ Branch 574 not taken.
✗ Branch 575 not taken.
✗ Branch 577 not taken.
✗ Branch 578 not taken.
✗ Branch 580 not taken.
✗ Branch 581 not taken.
✗ Branch 583 not taken.
✗ Branch 584 not taken.
✗ Branch 586 not taken.
✗ Branch 587 not taken.
✗ Branch 589 not taken.
✗ Branch 590 not taken.
✗ Branch 592 not taken.
✗ Branch 593 not taken.
✗ Branch 595 not taken.
✗ Branch 596 not taken.
✗ Branch 598 not taken.
✗ Branch 599 not taken.
✗ Branch 601 not taken.
✗ Branch 602 not taken.
✗ Branch 604 not taken.
✗ Branch 605 not taken.
✗ Branch 607 not taken.
✗ Branch 608 not taken.
✗ Branch 610 not taken.
✗ Branch 611 not taken.
✗ Branch 613 not taken.
✗ Branch 614 not taken.
✗ Branch 616 not taken.
✗ Branch 617 not taken.
✗ Branch 619 not taken.
✗ Branch 620 not taken.
✗ Branch 622 not taken.
✗ Branch 623 not taken.
✗ Branch 625 not taken.
✗ Branch 626 not taken.
✗ Branch 628 not taken.
✗ Branch 629 not taken.
✗ Branch 631 not taken.
✗ Branch 632 not taken.
✗ Branch 634 not taken.
✗ Branch 635 not taken.
✗ Branch 637 not taken.
✗ Branch 638 not taken.
✗ Branch 640 not taken.
✗ Branch 641 not taken.
✗ Branch 643 not taken.
✗ Branch 644 not taken.
✗ Branch 646 not taken.
✗ Branch 647 not taken.
✗ Branch 649 not taken.
✗ Branch 650 not taken.
✗ Branch 652 not taken.
✗ Branch 653 not taken.
✗ Branch 655 not taken.
✗ Branch 656 not taken.
✗ Branch 658 not taken.
✗ Branch 659 not taken.
✗ Branch 661 not taken.
✗ Branch 662 not taken.
✗ Branch 664 not taken.
✗ Branch 665 not taken.
✗ Branch 667 not taken.
✗ Branch 668 not taken.
✗ Branch 670 not taken.
✗ Branch 671 not taken.
✗ Branch 673 not taken.
✗ Branch 674 not taken.
✗ Branch 676 not taken.
✗ Branch 677 not taken.
✗ Branch 679 not taken.
✗ Branch 680 not taken.
✗ Branch 682 not taken.
✗ Branch 683 not taken.
✗ Branch 685 not taken.
✗ Branch 686 not taken.
✗ Branch 688 not taken.
✗ Branch 689 not taken.
✗ Branch 691 not taken.
✗ Branch 692 not taken.
✗ Branch 694 not taken.
✗ Branch 695 not taken.
✗ Branch 697 not taken.
✗ Branch 698 not taken.
✗ Branch 700 not taken.
✗ Branch 701 not taken.
✓ Branch 703 taken 1 times.
✗ Branch 704 not taken.
✗ Branch 706 not taken.
✗ Branch 707 not taken.
✗ Branch 709 not taken.
✗ Branch 710 not taken.
✗ Branch 712 not taken.
✗ Branch 713 not taken.
✗ Branch 715 not taken.
✗ Branch 716 not taken.
✗ Branch 718 not taken.
✗ Branch 719 not taken.
✗ Branch 721 not taken.
✗ Branch 722 not taken.
✗ Branch 724 not taken.
✗ Branch 725 not taken.
✗ Branch 727 not taken.
✗ Branch 728 not taken.
✗ Branch 730 not taken.
✗ Branch 731 not taken.
✗ Branch 733 not taken.
✗ Branch 734 not taken.
✗ Branch 736 not taken.
✗ Branch 737 not taken.
✗ Branch 739 not taken.
✗ Branch 740 not taken.
✗ Branch 742 not taken.
✗ Branch 743 not taken.
✗ Branch 745 not taken.
✗ Branch 746 not taken.
✗ Branch 748 not taken.
✗ Branch 749 not taken.
✗ Branch 751 not taken.
✗ Branch 752 not taken.
✗ Branch 754 not taken.
✗ Branch 755 not taken.
✗ Branch 757 not taken.
✗ Branch 758 not taken.
✗ Branch 760 not taken.
✗ Branch 761 not taken.
✗ Branch 763 not taken.
✗ Branch 764 not taken.
✗ Branch 766 not taken.
✗ Branch 767 not taken.
✗ Branch 769 not taken.
✗ Branch 770 not taken.
✗ Branch 772 not taken.
✗ Branch 773 not taken.
✗ Branch 775 not taken.
✗ Branch 776 not taken.
✗ Branch 778 not taken.
✗ Branch 779 not taken.
✗ Branch 781 not taken.
✗ Branch 782 not taken.
✗ Branch 784 not taken.
✗ Branch 785 not taken.
✗ Branch 787 not taken.
✗ Branch 788 not taken.
✗ Branch 790 not taken.
✗ Branch 791 not taken.
✗ Branch 793 not taken.
✗ Branch 794 not taken.
✗ Branch 796 not taken.
✗ Branch 797 not taken.
✗ Branch 799 not taken.
✗ Branch 800 not taken.
✗ Branch 802 not taken.
✗ Branch 803 not taken.
✗ Branch 805 not taken.
✗ Branch 806 not taken.
✗ Branch 808 not taken.
✗ Branch 809 not taken.
✗ Branch 811 not taken.
✗ Branch 812 not taken.
✗ Branch 814 not taken.
✗ Branch 815 not taken.
✗ Branch 817 not taken.
✗ Branch 818 not taken.
✗ Branch 820 not taken.
✗ Branch 821 not taken.
✗ Branch 823 not taken.
✗ Branch 824 not taken.
✗ Branch 826 not taken.
✗ Branch 827 not taken.
✗ Branch 829 not taken.
✗ Branch 830 not taken.
✗ Branch 832 not taken.
✗ Branch 833 not taken.
✗ Branch 835 not taken.
✗ Branch 836 not taken.
✗ Branch 838 not taken.
✗ Branch 839 not taken.
✗ Branch 841 not taken.
✗ Branch 842 not taken.
✗ Branch 844 not taken.
✗ Branch 845 not taken.
✗ Branch 847 not taken.
✗ Branch 848 not taken.
✗ Branch 850 not taken.
✗ Branch 851 not taken.
✗ Branch 853 not taken.
✗ Branch 854 not taken.
✗ Branch 856 not taken.
✗ Branch 857 not taken.
✗ Branch 859 not taken.
✗ Branch 860 not taken.
✗ Branch 862 not taken.
✗ Branch 863 not taken.
✗ Branch 865 not taken.
✗ Branch 866 not taken.
✗ Branch 868 not taken.
✗ Branch 869 not taken.
✗ Branch 871 not taken.
✗ Branch 872 not taken.
✗ Branch 874 not taken.
✗ Branch 875 not taken.
✗ Branch 877 not taken.
✗ Branch 878 not taken.
✗ Branch 880 not taken.
✗ Branch 881 not taken.
✗ Branch 883 not taken.
✗ Branch 884 not taken.
✗ Branch 886 not taken.
✗ Branch 887 not taken.
✗ Branch 889 not taken.
✗ Branch 890 not taken.
✗ Branch 892 not taken.
✗ Branch 893 not taken.
✓ Branch 895 taken 1 times.
✗ Branch 896 not taken.
✗ Branch 898 not taken.
✗ Branch 899 not taken.
✗ Branch 901 not taken.
✗ Branch 902 not taken.
✗ Branch 904 not taken.
✗ Branch 905 not taken.
✗ Branch 907 not taken.
✗ Branch 908 not taken.
✗ Branch 910 not taken.
✗ Branch 911 not taken.
✗ Branch 913 not taken.
✗ Branch 914 not taken.
✗ Branch 916 not taken.
✗ Branch 917 not taken.
✗ Branch 919 not taken.
✗ Branch 920 not taken.
✗ Branch 922 not taken.
✗ Branch 923 not taken.
✗ Branch 925 not taken.
✗ Branch 926 not taken.
✗ Branch 928 not taken.
✗ Branch 929 not taken.
✗ Branch 931 not taken.
✗ Branch 932 not taken.
✗ Branch 934 not taken.
✗ Branch 935 not taken.
✗ Branch 937 not taken.
✗ Branch 938 not taken.
✗ Branch 940 not taken.
✗ Branch 941 not taken.
✗ Branch 943 not taken.
✗ Branch 944 not taken.
✗ Branch 946 not taken.
✗ Branch 947 not taken.
✗ Branch 949 not taken.
✗ Branch 950 not taken.
✗ Branch 952 not taken.
✗ Branch 953 not taken.
✗ Branch 955 not taken.
✗ Branch 956 not taken.
✗ Branch 958 not taken.
✗ Branch 959 not taken.
✗ Branch 961 not taken.
✗ Branch 962 not taken.
✗ Branch 964 not taken.
✗ Branch 965 not taken.
✗ Branch 967 not taken.
✗ Branch 968 not taken.
✗ Branch 970 not taken.
✗ Branch 971 not taken.
✗ Branch 973 not taken.
✗ Branch 974 not taken.
✗ Branch 976 not taken.
✗ Branch 977 not taken.
✗ Branch 979 not taken.
✗ Branch 980 not taken.
✗ Branch 982 not taken.
✗ Branch 983 not taken.
✗ Branch 985 not taken.
✗ Branch 986 not taken.
✗ Branch 988 not taken.
✗ Branch 989 not taken.
✗ Branch 991 not taken.
✗ Branch 992 not taken.
✗ Branch 994 not taken.
✗ Branch 995 not taken.
✗ Branch 997 not taken.
✗ Branch 998 not taken.
✗ Branch 1000 not taken.
✗ Branch 1001 not taken.
✗ Branch 1003 not taken.
✗ Branch 1004 not taken.
✗ Branch 1006 not taken.
✗ Branch 1007 not taken.
✗ Branch 1009 not taken.
✗ Branch 1010 not taken.
✗ Branch 1012 not taken.
✗ Branch 1013 not taken.
✗ Branch 1015 not taken.
✗ Branch 1016 not taken.
✗ Branch 1018 not taken.
✗ Branch 1019 not taken.
✗ Branch 1021 not taken.
✗ Branch 1022 not taken.
✗ Branch 1024 not taken.
✗ Branch 1025 not taken.
✗ Branch 1027 not taken.
✗ Branch 1028 not taken.
✗ Branch 1030 not taken.
✗ Branch 1031 not taken.
✗ Branch 1033 not taken.
✗ Branch 1034 not taken.
✗ Branch 1036 not taken.
✗ Branch 1037 not taken.
✗ Branch 1039 not taken.
✗ Branch 1040 not taken.
✗ Branch 1042 not taken.
✗ Branch 1043 not taken.
✗ Branch 1045 not taken.
✗ Branch 1046 not taken.
✗ Branch 1048 not taken.
✗ Branch 1049 not taken.
✗ Branch 1051 not taken.
✗ Branch 1052 not taken.
✗ Branch 1054 not taken.
✗ Branch 1055 not taken.
✗ Branch 1057 not taken.
✗ Branch 1058 not taken.
✗ Branch 1060 not taken.
✗ Branch 1061 not taken.
✗ Branch 1063 not taken.
✗ Branch 1064 not taken.
✗ Branch 1066 not taken.
✗ Branch 1067 not taken.
✗ Branch 1069 not taken.
✗ Branch 1070 not taken.
✗ Branch 1072 not taken.
✗ Branch 1073 not taken.
✓ Branch 1075 taken 1 times.
✗ Branch 1076 not taken.
✗ Branch 1078 not taken.
✗ Branch 1079 not taken.
✗ Branch 1081 not taken.
✗ Branch 1082 not taken.
✗ Branch 1084 not taken.
✗ Branch 1085 not taken.
✗ Branch 1087 not taken.
✗ Branch 1088 not taken.
✗ Branch 1090 not taken.
✗ Branch 1091 not taken.
✗ Branch 1093 not taken.
✗ Branch 1094 not taken.
✗ Branch 1096 not taken.
✗ Branch 1097 not taken.
✗ Branch 1099 not taken.
✗ Branch 1100 not taken.
✗ Branch 1102 not taken.
✗ Branch 1103 not taken.
✗ Branch 1105 not taken.
✗ Branch 1106 not taken.
✗ Branch 1108 not taken.
✗ Branch 1109 not taken.
✗ Branch 1111 not taken.
✗ Branch 1112 not taken.
✗ Branch 1114 not taken.
✗ Branch 1115 not taken.
✗ Branch 1117 not taken.
✗ Branch 1118 not taken.
✗ Branch 1120 not taken.
✗ Branch 1121 not taken.
✗ Branch 1123 not taken.
✗ Branch 1124 not taken.
✗ Branch 1126 not taken.
✗ Branch 1127 not taken.
✗ Branch 1129 not taken.
✗ Branch 1130 not taken.
✗ Branch 1132 not taken.
✗ Branch 1133 not taken.
✗ Branch 1135 not taken.
✗ Branch 1136 not taken.
✗ Branch 1138 not taken.
✗ Branch 1139 not taken.
✗ Branch 1141 not taken.
✗ Branch 1142 not taken.
✗ Branch 1144 not taken.
✗ Branch 1145 not taken.
✗ Branch 1147 not taken.
✗ Branch 1148 not taken.
✗ Branch 1150 not taken.
✗ Branch 1151 not taken.
✗ Branch 1153 not taken.
✗ Branch 1154 not taken.
✗ Branch 1156 not taken.
✗ Branch 1157 not taken.
✗ Branch 1159 not taken.
✗ Branch 1160 not taken.
✗ Branch 1162 not taken.
✗ Branch 1163 not taken.
✗ Branch 1165 not taken.
✗ Branch 1166 not taken.
✗ Branch 1168 not taken.
✗ Branch 1169 not taken.
✗ Branch 1171 not taken.
✗ Branch 1172 not taken.
✗ Branch 1174 not taken.
✗ Branch 1175 not taken.
✗ Branch 1177 not taken.
✗ Branch 1178 not taken.
✗ Branch 1180 not taken.
✗ Branch 1181 not taken.
✗ Branch 1183 not taken.
✗ Branch 1184 not taken.
✗ Branch 1186 not taken.
✗ Branch 1187 not taken.
✗ Branch 1189 not taken.
✗ Branch 1190 not taken.
✗ Branch 1192 not taken.
✗ Branch 1193 not taken.
✗ Branch 1195 not taken.
✗ Branch 1196 not taken.
✗ Branch 1198 not taken.
✗ Branch 1199 not taken.
✗ Branch 1201 not taken.
✗ Branch 1202 not taken.
✗ Branch 1204 not taken.
✗ Branch 1205 not taken.
✗ Branch 1207 not taken.
✗ Branch 1208 not taken.
✗ Branch 1210 not taken.
✗ Branch 1211 not taken.
✗ Branch 1213 not taken.
✗ Branch 1214 not taken.
✗ Branch 1216 not taken.
✗ Branch 1217 not taken.
✗ Branch 1219 not taken.
✗ Branch 1220 not taken.
✗ Branch 1222 not taken.
✗ Branch 1223 not taken.
✗ Branch 1225 not taken.
✗ Branch 1226 not taken.
✗ Branch 1228 not taken.
✗ Branch 1229 not taken.
✗ Branch 1231 not taken.
✗ Branch 1232 not taken.
✗ Branch 1234 not taken.
✗ Branch 1235 not taken.
✗ Branch 1237 not taken.
✗ Branch 1238 not taken.
✗ Branch 1240 not taken.
✗ Branch 1241 not taken.
✗ Branch 1243 not taken.
✗ Branch 1244 not taken.
✗ Branch 1246 not taken.
✗ Branch 1247 not taken.
✗ Branch 1249 not taken.
✗ Branch 1250 not taken.
✗ Branch 1252 not taken.
✗ Branch 1253 not taken.
✓ Branch 1255 taken 1 times.
✗ Branch 1256 not taken.
✗ Branch 1258 not taken.
✗ Branch 1259 not taken.
✗ Branch 1261 not taken.
✗ Branch 1262 not taken.
✗ Branch 1264 not taken.
✗ Branch 1265 not taken.
✗ Branch 1267 not taken.
✗ Branch 1268 not taken.
✗ Branch 1270 not taken.
✗ Branch 1271 not taken.
✗ Branch 1273 not taken.
✗ Branch 1274 not taken.
✗ Branch 1276 not taken.
✗ Branch 1277 not taken.
✗ Branch 1279 not taken.
✗ Branch 1280 not taken.
✗ Branch 1282 not taken.
✗ Branch 1283 not taken.
✗ Branch 1285 not taken.
✗ Branch 1286 not taken.
✗ Branch 1288 not taken.
✗ Branch 1289 not taken.
✗ Branch 1291 not taken.
✗ Branch 1292 not taken.
✗ Branch 1294 not taken.
✗ Branch 1295 not taken.
✗ Branch 1297 not taken.
✗ Branch 1298 not taken.
✗ Branch 1300 not taken.
✗ Branch 1301 not taken.
✗ Branch 1303 not taken.
✗ Branch 1304 not taken.
✗ Branch 1306 not taken.
✗ Branch 1307 not taken.
✗ Branch 1309 not taken.
✗ Branch 1310 not taken.
✗ Branch 1312 not taken.
✗ Branch 1313 not taken.
✗ Branch 1315 not taken.
✗ Branch 1316 not taken.
✗ Branch 1318 not taken.
✗ Branch 1319 not taken.
✓ Branch 1321 taken 1 times.
✗ Branch 1322 not taken.
✗ Branch 1324 not taken.
✗ Branch 1325 not taken.
✗ Branch 1327 not taken.
✗ Branch 1328 not taken.
✗ Branch 1330 not taken.
✗ Branch 1331 not taken.
✗ Branch 1333 not taken.
✗ Branch 1334 not taken.
✗ Branch 1336 not taken.
✗ Branch 1337 not taken.
✗ Branch 1339 not taken.
✗ Branch 1340 not taken.
✗ Branch 1342 not taken.
✗ Branch 1343 not taken.
✗ Branch 1345 not taken.
✗ Branch 1346 not taken.
✗ Branch 1348 not taken.
✗ Branch 1349 not taken.
✗ Branch 1351 not taken.
✗ Branch 1352 not taken.
✗ Branch 1354 not taken.
✗ Branch 1355 not taken.
✗ Branch 1357 not taken.
✗ Branch 1358 not taken.
✗ Branch 1360 not taken.
✗ Branch 1361 not taken.
✗ Branch 1363 not taken.
✗ Branch 1364 not taken.
✗ Branch 1366 not taken.
✗ Branch 1367 not taken.
✗ Branch 1369 not taken.
✗ Branch 1370 not taken.
✗ Branch 1372 not taken.
✗ Branch 1373 not taken.
✗ Branch 1375 not taken.
✗ Branch 1376 not taken.
✗ Branch 1378 not taken.
✗ Branch 1379 not taken.
✗ Branch 1381 not taken.
✗ Branch 1382 not taken.
✗ Branch 1384 not taken.
✗ Branch 1385 not taken.
✗ Branch 1387 not taken.
✗ Branch 1388 not taken.
✗ Branch 1390 not taken.
✗ Branch 1391 not taken.
✗ Branch 1393 not taken.
✗ Branch 1394 not taken.
✗ Branch 1396 not taken.
✗ Branch 1397 not taken.
✗ Branch 1399 not taken.
✗ Branch 1400 not taken.
✗ Branch 1402 not taken.
✗ Branch 1403 not taken.
✗ Branch 1405 not taken.
✗ Branch 1406 not taken.
✗ Branch 1408 not taken.
✗ Branch 1409 not taken.
✗ Branch 1411 not taken.
✗ Branch 1412 not taken.
✗ Branch 1414 not taken.
✗ Branch 1415 not taken.
✗ Branch 1417 not taken.
✗ Branch 1418 not taken.
✗ Branch 1420 not taken.
✗ Branch 1421 not taken.
✗ Branch 1423 not taken.
✗ Branch 1424 not taken.
✗ Branch 1426 not taken.
✗ Branch 1427 not taken.
✗ Branch 1429 not taken.
✗ Branch 1430 not taken.
✗ Branch 1432 not taken.
✗ Branch 1433 not taken.
✗ Branch 1435 not taken.
✗ Branch 1436 not taken.
✗ Branch 1438 not taken.
✗ Branch 1439 not taken.
✗ Branch 1441 not taken.
✗ Branch 1442 not taken.
✗ Branch 1444 not taken.
✗ Branch 1445 not taken.
✗ Branch 1447 not taken.
✗ Branch 1448 not taken.
✗ Branch 1450 not taken.
✗ Branch 1451 not taken.
✗ Branch 1453 not taken.
✗ Branch 1454 not taken.
✗ Branch 1456 not taken.
✗ Branch 1457 not taken.
✗ Branch 1459 not taken.
✗ Branch 1460 not taken.
✗ Branch 1462 not taken.
✗ Branch 1463 not taken.
✗ Branch 1465 not taken.
✗ Branch 1466 not taken.
✗ Branch 1468 not taken.
✗ Branch 1469 not taken.
✗ Branch 1471 not taken.
✗ Branch 1472 not taken.
✗ Branch 1474 not taken.
✗ Branch 1475 not taken.
✗ Branch 1477 not taken.
✗ Branch 1478 not taken.
✗ Branch 1480 not taken.
✗ Branch 1481 not taken.
✗ Branch 1483 not taken.
✗ Branch 1484 not taken.
✗ Branch 1486 not taken.
✗ Branch 1487 not taken.
✗ Branch 1489 not taken.
✗ Branch 1490 not taken.
✗ Branch 1492 not taken.
✗ Branch 1493 not taken.
✗ Branch 1495 not taken.
✗ Branch 1496 not taken.
✗ Branch 1498 not taken.
✗ Branch 1499 not taken.
✗ Branch 1501 not taken.
✗ Branch 1502 not taken.
✗ Branch 1504 not taken.
✗ Branch 1505 not taken.
✗ Branch 1507 not taken.
✗ Branch 1508 not taken.
✗ Branch 1510 not taken.
✗ Branch 1511 not taken.
✓ Branch 1513 taken 1 times.
✗ Branch 1514 not taken.
✗ Branch 1516 not taken.
✗ Branch 1517 not taken.
✗ Branch 1519 not taken.
✗ Branch 1520 not taken.
✗ Branch 1522 not taken.
✗ Branch 1523 not taken.
✗ Branch 1525 not taken.
✗ Branch 1526 not taken.
✗ Branch 1528 not taken.
✗ Branch 1529 not taken.
✗ Branch 1531 not taken.
✗ Branch 1532 not taken.
✗ Branch 1534 not taken.
✗ Branch 1535 not taken.
✗ Branch 1537 not taken.
✗ Branch 1538 not taken.
✗ Branch 1540 not taken.
✗ Branch 1541 not taken.
✗ Branch 1543 not taken.
✗ Branch 1544 not taken.
✗ Branch 1546 not taken.
✗ Branch 1547 not taken.
✗ Branch 1549 not taken.
✗ Branch 1550 not taken.
✗ Branch 1552 not taken.
✗ Branch 1553 not taken.
✗ Branch 1555 not taken.
✗ Branch 1556 not taken.
✗ Branch 1558 not taken.
✗ Branch 1559 not taken.
✗ Branch 1561 not taken.
✗ Branch 1562 not taken.
✗ Branch 1564 not taken.
✗ Branch 1565 not taken.
✗ Branch 1567 not taken.
✗ Branch 1568 not taken.
✗ Branch 1570 not taken.
✗ Branch 1571 not taken.
✗ Branch 1573 not taken.
✗ Branch 1574 not taken.
✗ Branch 1576 not taken.
✗ Branch 1577 not taken.
✗ Branch 1579 not taken.
✗ Branch 1580 not taken.
✗ Branch 1582 not taken.
✗ Branch 1583 not taken.
✓ Branch 1585 taken 1 times.
✗ Branch 1586 not taken.
✗ Branch 1588 not taken.
✗ Branch 1589 not taken.
✗ Branch 1591 not taken.
✗ Branch 1592 not taken.
✗ Branch 1594 not taken.
✗ Branch 1595 not taken.
✗ Branch 1597 not taken.
✗ Branch 1598 not taken.
✗ Branch 1600 not taken.
✗ Branch 1601 not taken.
✗ Branch 1603 not taken.
✗ Branch 1604 not taken.
✗ Branch 1606 not taken.
✗ Branch 1607 not taken.
✗ Branch 1609 not taken.
✗ Branch 1610 not taken.
✗ Branch 1612 not taken.
✗ Branch 1613 not taken.
✗ Branch 1615 not taken.
✗ Branch 1616 not taken.
✗ Branch 1618 not taken.
✗ Branch 1619 not taken.
✗ Branch 1621 not taken.
✗ Branch 1622 not taken.
✗ Branch 1624 not taken.
✗ Branch 1625 not taken.
✗ Branch 1627 not taken.
✗ Branch 1628 not taken.
✗ Branch 1630 not taken.
✗ Branch 1631 not taken.
✗ Branch 1633 not taken.
✗ Branch 1634 not taken.
✗ Branch 1636 not taken.
✗ Branch 1637 not taken.
✗ Branch 1639 not taken.
✗ Branch 1640 not taken.
✗ Branch 1642 not taken.
✗ Branch 1643 not taken.
✗ Branch 1645 not taken.
✗ Branch 1646 not taken.
✗ Branch 1648 not taken.
✗ Branch 1649 not taken.
✗ Branch 1651 not taken.
✗ Branch 1652 not taken.
✗ Branch 1654 not taken.
✗ Branch 1655 not taken.
✗ Branch 1657 not taken.
✗ Branch 1658 not taken.
✗ Branch 1660 not taken.
✗ Branch 1661 not taken.
✗ Branch 1663 not taken.
✗ Branch 1664 not taken.
✗ Branch 1666 not taken.
✗ Branch 1667 not taken.
✗ Branch 1669 not taken.
✗ Branch 1670 not taken.
✗ Branch 1672 not taken.
✗ Branch 1673 not taken.
✗ Branch 1675 not taken.
✗ Branch 1676 not taken.
✗ Branch 1678 not taken.
✗ Branch 1679 not taken.
✗ Branch 1681 not taken.
✗ Branch 1682 not taken.
✗ Branch 1684 not taken.
✗ Branch 1685 not taken.
✓ Branch 1687 taken 1 times.
✗ Branch 1688 not taken.
✓ Branch 1690 taken 1 times.
✗ Branch 1691 not taken.
✓ Branch 1693 taken 1 times.
✗ Branch 1694 not taken.
✗ Branch 1696 not taken.
✗ Branch 1697 not taken.
✓ Branch 1699 taken 1 times.
✗ Branch 1700 not taken.
✗ Branch 1702 not taken.
✗ Branch 1703 not taken.
✗ Branch 1705 not taken.
✗ Branch 1706 not taken.
✗ Branch 1708 not taken.
✗ Branch 1709 not taken.
✗ Branch 1711 not taken.
✗ Branch 1712 not taken.
✗ Branch 1714 not taken.
✗ Branch 1715 not taken.
✗ Branch 1717 not taken.
✗ Branch 1718 not taken.
✗ Branch 1720 not taken.
✗ Branch 1721 not taken.
✗ Branch 1723 not taken.
✗ Branch 1724 not taken.
✗ Branch 1726 not taken.
✗ Branch 1727 not taken.
✗ Branch 1729 not taken.
✗ Branch 1730 not taken.
✗ Branch 1732 not taken.
✗ Branch 1733 not taken.
✗ Branch 1735 not taken.
✗ Branch 1736 not taken.
✗ Branch 1738 not taken.
✗ Branch 1739 not taken.
✗ Branch 1741 not taken.
✗ Branch 1742 not taken.
✗ Branch 1744 not taken.
✗ Branch 1745 not taken.
✗ Branch 1747 not taken.
✗ Branch 1748 not taken.
✗ Branch 1750 not taken.
✗ Branch 1751 not taken.
✗ Branch 1753 not taken.
✗ Branch 1754 not taken.
✗ Branch 1756 not taken.
✗ Branch 1757 not taken.
✗ Branch 1759 not taken.
✗ Branch 1760 not taken.
✗ Branch 1762 not taken.
✗ Branch 1763 not taken.
✗ Branch 1765 not taken.
✗ Branch 1766 not taken.
✗ Branch 1768 not taken.
✗ Branch 1769 not taken.
✗ Branch 1771 not taken.
✗ Branch 1772 not taken.
✗ Branch 1774 not taken.
✗ Branch 1775 not taken.
✗ Branch 1777 not taken.
✗ Branch 1778 not taken.
✗ Branch 1780 not taken.
✗ Branch 1781 not taken.
✗ Branch 1783 not taken.
✗ Branch 1784 not taken.
✗ Branch 1786 not taken.
✗ Branch 1787 not taken.
✓ Branch 1789 taken 1 times.
✗ Branch 1790 not taken.
✗ Branch 1792 not taken.
✗ Branch 1793 not taken.
✗ Branch 1795 not taken.
✗ Branch 1796 not taken.
✗ Branch 1798 not taken.
✗ Branch 1799 not taken.
✗ Branch 1801 not taken.
✗ Branch 1802 not taken.
✗ Branch 1804 not taken.
✗ Branch 1805 not taken.
✗ Branch 1807 not taken.
✗ Branch 1808 not taken.
✗ Branch 1810 not taken.
✗ Branch 1811 not taken.
✗ Branch 1813 not taken.
✗ Branch 1814 not taken.
✗ Branch 1816 not taken.
✗ Branch 1817 not taken.
✗ Branch 1819 not taken.
✗ Branch 1820 not taken.
✗ Branch 1822 not taken.
✗ Branch 1823 not taken.
✗ Branch 1825 not taken.
✗ Branch 1826 not taken.
✗ Branch 1828 not taken.
✗ Branch 1829 not taken.
✗ Branch 1831 not taken.
✗ Branch 1832 not taken.
✗ Branch 1834 not taken.
✗ Branch 1835 not taken.
✗ Branch 1837 not taken.
✗ Branch 1838 not taken.
✗ Branch 1840 not taken.
✗ Branch 1841 not taken.
✗ Branch 1843 not taken.
✗ Branch 1844 not taken.
✗ Branch 1846 not taken.
✗ Branch 1847 not taken.
✗ Branch 1849 not taken.
✗ Branch 1850 not taken.
✗ Branch 1852 not taken.
✗ Branch 1853 not taken.
✗ Branch 1855 not taken.
✗ Branch 1856 not taken.
✗ Branch 1858 not taken.
✗ Branch 1859 not taken.
✗ Branch 1861 not taken.
✗ Branch 1862 not taken.
✗ Branch 1864 not taken.
✗ Branch 1865 not taken.
✗ Branch 1867 not taken.
✗ Branch 1868 not taken.
✗ Branch 1870 not taken.
✗ Branch 1871 not taken.
✗ Branch 1873 not taken.
✗ Branch 1874 not taken.
✗ Branch 1876 not taken.
✗ Branch 1877 not taken.
✗ Branch 1879 not taken.
✗ Branch 1880 not taken.
✗ Branch 1882 not taken.
✗ Branch 1883 not taken.
✗ Branch 1885 not taken.
✗ Branch 1886 not taken.
✗ Branch 1888 not taken.
✗ Branch 1889 not taken.
✗ Branch 1891 not taken.
✗ Branch 1892 not taken.
✗ Branch 1894 not taken.
✗ Branch 1895 not taken.
✗ Branch 1897 not taken.
✗ Branch 1898 not taken.
✗ Branch 1900 not taken.
✗ Branch 1901 not taken.
✗ Branch 1903 not taken.
✗ Branch 1904 not taken.
✗ Branch 1906 not taken.
✗ Branch 1907 not taken.
✗ Branch 1909 not taken.
✗ Branch 1910 not taken.
✗ Branch 1912 not taken.
✗ Branch 1913 not taken.
✗ Branch 1915 not taken.
✗ Branch 1916 not taken.
✗ Branch 1918 not taken.
✗ Branch 1919 not taken.
✗ Branch 1921 not taken.
✗ Branch 1922 not taken.
✗ Branch 1924 not taken.
✗ Branch 1925 not taken.
✗ Branch 1927 not taken.
✗ Branch 1928 not taken.
✗ Branch 1930 not taken.
✗ Branch 1931 not taken.
✗ Branch 1933 not taken.
✗ Branch 1934 not taken.
✗ Branch 1936 not taken.
✗ Branch 1937 not taken.
✗ Branch 1939 not taken.
✗ Branch 1940 not taken.
✗ Branch 1942 not taken.
✗ Branch 1943 not taken.
✗ Branch 1945 not taken.
✗ Branch 1946 not taken.
✗ Branch 1948 not taken.
✗ Branch 1949 not taken.
✗ Branch 1951 not taken.
✗ Branch 1952 not taken.
✗ Branch 1954 not taken.
✗ Branch 1955 not taken.
✗ Branch 1957 not taken.
✗ Branch 1958 not taken.
✗ Branch 1960 not taken.
✗ Branch 1961 not taken.
✗ Branch 1963 not taken.
✗ Branch 1964 not taken.
✗ Branch 1966 not taken.
✗ Branch 1967 not taken.
✗ Branch 1969 not taken.
✗ Branch 1970 not taken.
✗ Branch 1972 not taken.
✗ Branch 1973 not taken.
✗ Branch 1975 not taken.
✗ Branch 1976 not taken.
✗ Branch 1978 not taken.
✗ Branch 1979 not taken.
✗ Branch 1981 not taken.
✗ Branch 1982 not taken.
✗ Branch 1984 not taken.
✗ Branch 1985 not taken.
✗ Branch 1987 not taken.
✗ Branch 1988 not taken.
✗ Branch 1990 not taken.
✗ Branch 1991 not taken.
✗ Branch 1993 not taken.
✗ Branch 1994 not taken.
✗ Branch 1996 not taken.
✗ Branch 1997 not taken.
✗ Branch 1999 not taken.
✗ Branch 2000 not taken.
✗ Branch 2002 not taken.
✗ Branch 2003 not taken.
✓ Branch 2005 taken 3 times.
✗ Branch 2006 not taken.
✗ Branch 2008 not taken.
✗ Branch 2009 not taken.
✗ Branch 2011 not taken.
✗ Branch 2012 not taken.
✗ Branch 2014 not taken.
✗ Branch 2015 not taken.
✗ Branch 2017 not taken.
✗ Branch 2018 not taken.
✗ Branch 2020 not taken.
✗ Branch 2021 not taken.
✗ Branch 2023 not taken.
✗ Branch 2024 not taken.
✗ Branch 2026 not taken.
✗ Branch 2027 not taken.
✗ Branch 2029 not taken.
✗ Branch 2030 not taken.
✓ Branch 2032 taken 1 times.
✗ Branch 2033 not taken.
✗ Branch 2035 not taken.
✗ Branch 2036 not taken.
✓ Branch 2038 taken 1 times.
✗ Branch 2039 not taken.
✓ Branch 2041 taken 1 times.
✗ Branch 2042 not taken.
✓ Branch 2044 taken 1 times.
✗ Branch 2045 not taken.
✗ Branch 2047 not taken.
✗ Branch 2048 not taken.
✗ Branch 2050 not taken.
✗ Branch 2051 not taken.
✗ Branch 2053 not taken.
✗ Branch 2054 not taken.
✓ Branch 2056 taken 1 times.
✗ Branch 2057 not taken.
✗ Branch 2059 not taken.
✗ Branch 2060 not taken.
105610 return IndexIter<ValueIterT, FilterT>(valueIter, newFilter);
1021 }
1022
1023 template<typename T, Index Log2Dim>
1024 inline ValueVoxelCIter
1025
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 46984 times.
46984 PointDataLeafNode<T, Log2Dim>::beginValueVoxel(const Coord& ijk) const
1026 {
1027 const Index index = LeafNodeType::coordToOffset(ijk);
1028
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 46984 times.
46984 assert(index < BaseLeaf::SIZE);
1029 46984 const ValueType end = this->getValue(index);
1030
2/2
✓ Branch 0 taken 101 times.
✓ Branch 1 taken 46883 times.
46984 const ValueType start = (index == 0) ? ValueType(0) : this->getValue(index - 1);
1031 46984 return ValueVoxelCIter(start, end);
1032 }
1033
1034 template<typename T, Index Log2Dim>
1035 inline typename PointDataLeafNode<T, Log2Dim>::IndexVoxelIter
1036 PointDataLeafNode<T, Log2Dim>::beginIndexVoxel(const Coord& ijk) const
1037 {
1038
8/16
✓ Branch 1 taken 513 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 1025 times.
✗ Branch 5 not taken.
✓ Branch 7 taken 513 times.
✗ Branch 8 not taken.
✓ Branch 10 taken 1 times.
✗ Branch 11 not taken.
✓ Branch 13 taken 1 times.
✗ Branch 14 not taken.
✓ Branch 16 taken 1 times.
✗ Branch 17 not taken.
✓ Branch 19 taken 1 times.
✗ Branch 20 not taken.
✓ Branch 22 taken 1 times.
✗ Branch 23 not taken.
2056 ValueVoxelCIter iter = this->beginValueVoxel(ijk);
1039 2048 return IndexVoxelIter(iter, NullFilter());
1040 }
1041
1042 template<typename T, Index Log2Dim>
1043 template<typename FilterT>
1044 inline IndexIter<ValueVoxelCIter, FilterT>
1045 3600 PointDataLeafNode<T, Log2Dim>::beginIndexVoxel(const Coord& ijk, const FilterT& filter) const
1046 {
1047
2/4
✓ Branch 5 taken 1 times.
✗ Branch 6 not taken.
✓ Branch 8 taken 1 times.
✗ Branch 9 not taken.
44927 ValueVoxelCIter iter = this->beginValueVoxel(ijk);
1048 7200 FilterT newFilter(filter);
1049
1/2
✓ Branch 1 taken 3600 times.
✗ Branch 2 not taken.
3600 newFilter.reset(*this);
1050
1/2
✓ Branch 1 taken 3600 times.
✗ Branch 2 not taken.
7202 return IndexIter<ValueVoxelCIter, FilterT>(iter, newFilter);
1051 }
1052
1053 template<typename T, Index Log2Dim>
1054 inline Index64
1055 PointDataLeafNode<T, Log2Dim>::pointCount() const
1056 {
1057
17/64
✗ Branch 0 not taken.
✓ Branch 1 taken 48 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✓ Branch 4 taken 1 times.
✓ Branch 5 taken 3 times.
✓ Branch 6 taken 3 times.
✓ Branch 7 taken 1 times.
✗ Branch 8 not taken.
✓ Branch 9 taken 3 times.
✓ Branch 10 taken 4 times.
✗ Branch 11 not taken.
✗ Branch 12 not taken.
✓ Branch 13 taken 3 times.
✓ Branch 14 taken 3 times.
✗ Branch 15 not taken.
✗ Branch 16 not taken.
✗ Branch 17 not taken.
✗ Branch 18 not taken.
✗ Branch 19 not taken.
✗ Branch 20 not taken.
✗ Branch 21 not taken.
✗ Branch 22 not taken.
✗ Branch 23 not taken.
✗ Branch 24 not taken.
✗ Branch 25 not taken.
✗ Branch 26 not taken.
✗ Branch 27 not taken.
✗ Branch 28 not taken.
✗ Branch 29 not taken.
✗ Branch 30 not taken.
✗ Branch 31 not taken.
✗ Branch 32 not taken.
✓ Branch 33 taken 2303 times.
✓ Branch 34 taken 2303 times.
✗ Branch 35 not taken.
✗ Branch 36 not taken.
✓ Branch 37 taken 3 times.
✓ Branch 38 taken 3 times.
✗ Branch 39 not taken.
✗ Branch 40 not taken.
✓ Branch 41 taken 3 times.
✓ Branch 42 taken 3 times.
✗ Branch 43 not taken.
✗ Branch 44 not taken.
✓ Branch 45 taken 3 times.
✓ Branch 46 taken 3 times.
✗ Branch 47 not taken.
✗ Branch 48 not taken.
✗ Branch 49 not taken.
✗ Branch 50 not taken.
✗ Branch 51 not taken.
✗ Branch 52 not taken.
✗ Branch 53 not taken.
✗ Branch 54 not taken.
✗ Branch 55 not taken.
✗ Branch 56 not taken.
✗ Branch 57 not taken.
✗ Branch 58 not taken.
✗ Branch 59 not taken.
✗ Branch 60 not taken.
✗ Branch 61 not taken.
✗ Branch 62 not taken.
✗ Branch 63 not taken.
37429 return this->getLastValue();
1058 }
1059
1060 template<typename T, Index Log2Dim>
1061 inline Index64
1062 2325 PointDataLeafNode<T, Log2Dim>::onPointCount() const
1063 {
1064
1/2
✓ Branch 0 taken 2325 times.
✗ Branch 1 not taken.
2325 if (this->isEmpty()) return 0;
1065
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 2324 times.
2326 else if (this->isDense()) return this->pointCount();
1066 2324 return iterCount(this->beginIndexOn());
1067 }
1068
1069 template<typename T, Index Log2Dim>
1070 inline Index64
1071 4 PointDataLeafNode<T, Log2Dim>::offPointCount() const
1072 {
1073
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 4 times.
4 if (this->isEmpty()) return this->pointCount();
1074
2/2
✓ Branch 0 taken 3 times.
✓ Branch 1 taken 1 times.
4 else if (this->isDense()) return 0;
1075 3 return iterCount(this->beginIndexOff());
1076 }
1077
1078 template<typename T, Index Log2Dim>
1079 inline Index64
1080 8 PointDataLeafNode<T, Log2Dim>::groupPointCount(const Name& groupName) const
1081 {
1082
1/2
✓ Branch 1 taken 8 times.
✗ Branch 2 not taken.
8 if (!this->attributeSet().descriptor().hasGroup(groupName)) {
1083 return Index64(0);
1084 }
1085 GroupFilter filter(groupName, this->attributeSet());
1086 if (filter.state() == index::ALL) {
1087 return this->pointCount();
1088 } else {
1089
2/6
✓ Branch 1 taken 8 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✓ Branch 4 taken 8 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
16 return iterCount(this->beginIndexAll(filter));
1090 }
1091 }
1092
1093 template<typename T, Index Log2Dim>
1094 inline void
1095 16 PointDataLeafNode<T, Log2Dim>::updateValueMask()
1096 {
1097 ValueType start = 0, end = 0;
1098
2/2
✓ Branch 0 taken 8192 times.
✓ Branch 1 taken 16 times.
8208 for (Index n = 0; n < LeafNodeType::NUM_VALUES; n++) {
1099
2/2
✓ Branch 1 taken 278 times.
✓ Branch 2 taken 7914 times.
8192 end = this->getValue(n);
1100 this->setValueMask(n, (end - start) > 0);
1101 8192 start = end;
1102 }
1103 16 }
1104
1105 template<typename T, Index Log2Dim>
1106 inline void
1107 PointDataLeafNode<T, Log2Dim>::setOffsetOn(Index offset, const ValueType& val)
1108 {
1109
7/14
✓ Branch 1 taken 2 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✓ Branch 7 taken 513 times.
✗ Branch 8 not taken.
✓ Branch 10 taken 768 times.
✗ Branch 11 not taken.
✓ Branch 13 taken 513 times.
✗ Branch 14 not taken.
✓ Branch 16 taken 256 times.
✗ Branch 17 not taken.
✓ Branch 19 taken 1 times.
✗ Branch 20 not taken.
5498740 this->buffer().setValue(offset, val);
1110 this->setValueMaskOn(offset);
1111 }
1112
1113 template<typename T, Index Log2Dim>
1114 inline void
1115 PointDataLeafNode<T, Log2Dim>::setOffsetOnly(Index offset, const ValueType& val)
1116 {
1117
28/59
✓ Branch 1 taken 1954304 times.
✓ Branch 2 taken 256 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 4096 times.
✗ Branch 5 not taken.
✓ Branch 7 taken 4096 times.
✗ Branch 8 not taken.
✓ Branch 10 taken 4608 times.
✗ Branch 11 not taken.
✓ Branch 13 taken 4096 times.
✗ Branch 14 not taken.
✓ Branch 16 taken 4096 times.
✗ Branch 17 not taken.
✓ Branch 19 taken 7168 times.
✗ Branch 20 not taken.
✓ Branch 22 taken 1024 times.
✗ Branch 23 not taken.
✓ Branch 25 taken 4096 times.
✗ Branch 26 not taken.
✓ Branch 28 taken 4096 times.
✗ Branch 29 not taken.
✓ Branch 31 taken 4096 times.
✗ Branch 32 not taken.
✓ Branch 34 taken 4096 times.
✗ Branch 35 not taken.
✗ Branch 37 not taken.
✗ Branch 38 not taken.
✓ Branch 40 taken 4096 times.
✗ Branch 41 not taken.
✓ Branch 43 taken 4096 times.
✗ Branch 44 not taken.
✗ Branch 46 not taken.
✗ Branch 47 not taken.
✓ Branch 49 taken 4096 times.
✗ Branch 50 not taken.
✓ Branch 52 taken 19968 times.
✗ Branch 53 not taken.
✓ Branch 55 taken 512 times.
✗ Branch 56 not taken.
✓ Branch 58 taken 4096 times.
✗ Branch 59 not taken.
✓ Branch 61 taken 4096 times.
✗ Branch 62 not taken.
✓ Branch 64 taken 4096 times.
✗ Branch 65 not taken.
✓ Branch 67 taken 4096 times.
✗ Branch 68 not taken.
✓ Branch 70 taken 4096 times.
✗ Branch 71 not taken.
✓ Branch 73 taken 4096 times.
✗ Branch 74 not taken.
✓ Branch 76 taken 4096 times.
✗ Branch 77 not taken.
✓ Branch 79 taken 4096 times.
✗ Branch 80 not taken.
✓ Branch 82 taken 4096 times.
✗ Branch 83 not taken.
✓ Branch 85 taken 6144 times.
✗ Branch 86 not taken.
2084608 this->buffer().setValue(offset, val);
1118 2075904 }
1119
1120 template<typename T, Index Log2Dim>
1121 inline void
1122 PointDataLeafNode<T, Log2Dim>::readTopology(std::istream& is, bool fromHalf)
1123 {
1124 BaseLeaf::readTopology(is, fromHalf);
1125 2 }
1126
1127 template<typename T, Index Log2Dim>
1128 inline void
1129 PointDataLeafNode<T, Log2Dim>::writeTopology(std::ostream& os, bool toHalf) const
1130 {
1131 BaseLeaf::writeTopology(os, toHalf);
1132 2 }
1133
1134 template<typename T, Index Log2Dim>
1135 inline Index
1136 PointDataLeafNode<T, Log2Dim>::buffers() const
1137 {
1138 return Index( /*voxel buffer sizes*/ 1 +
1139 /*voxel buffers*/ 1 +
1140 /*attribute metadata*/ 1 +
1141 18155 /*attribute uniform values*/ mAttributeSet->size() +
1142 /*attribute buffers*/ mAttributeSet->size() +
1143
4/4
✓ Branch 0 taken 8 times.
✓ Branch 1 taken 1 times.
✓ Branch 2 taken 8 times.
✓ Branch 3 taken 1 times.
18155 /*cleanup*/ 1);
1144 }
1145
1146 template<typename T, Index Log2Dim>
1147 inline void
1148 PointDataLeafNode<T, Log2Dim>::readBuffers(std::istream& is, bool fromHalf)
1149 {
1150
1/2
✓ Branch 5 taken 8 times.
✗ Branch 6 not taken.
113754 this->readBuffers(is, CoordBBox::inf(), fromHalf);
1151 }
1152
1153 template<typename T, Index Log2Dim>
1154 inline void
1155 113754 PointDataLeafNode<T, Log2Dim>::readBuffers(std::istream& is, const CoordBBox& /*bbox*/, bool fromHalf)
1156 {
1157 struct Local
1158 {
1159 36436 static void destroyPagedStream(const io::StreamMetadata::AuxDataMap& auxData, const Index index)
1160 {
1161 // if paged stream exists, delete it
1162
1/2
✓ Branch 1 taken 36436 times.
✗ Branch 2 not taken.
72872 std::string key("paged:" + std::to_string(index));
1163
2/2
✓ Branch 0 taken 46 times.
✓ Branch 1 taken 36390 times.
36436 auto it = auxData.find(key);
1164
2/2
✓ Branch 0 taken 46 times.
✓ Branch 1 taken 36390 times.
36436 if (it != auxData.end()) {
1165 46 (const_cast<io::StreamMetadata::AuxDataMap&>(auxData)).erase(it);
1166 }
1167 36436 }
1168
1169 72872 static compression::PagedInputStream& getOrInsertPagedStream( const io::StreamMetadata::AuxDataMap& auxData,
1170 const Index index)
1171 {
1172
1/2
✓ Branch 1 taken 72872 times.
✗ Branch 2 not taken.
145744 std::string key("paged:" + std::to_string(index));
1173
2/2
✓ Branch 0 taken 72826 times.
✓ Branch 1 taken 46 times.
72872 auto it = auxData.find(key);
1174
2/2
✓ Branch 0 taken 72826 times.
✓ Branch 1 taken 46 times.
72872 if (it != auxData.end()) {
1175
1/2
✓ Branch 1 taken 72826 times.
✗ Branch 2 not taken.
145652 return *(boost::any_cast<compression::PagedInputStream::Ptr>(it->second));
1176 }
1177 else {
1178
1/2
✓ Branch 1 taken 46 times.
✗ Branch 2 not taken.
46 compression::PagedInputStream::Ptr pagedStream = std::make_shared<compression::PagedInputStream>();
1179
2/4
✓ Branch 1 taken 46 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 46 times.
✗ Branch 5 not taken.
46 (const_cast<io::StreamMetadata::AuxDataMap&>(auxData))[key] = pagedStream;
1180 return *pagedStream;
1181 }
1182 }
1183
1184 10220 static bool hasMatchingDescriptor(const io::StreamMetadata::AuxDataMap& auxData)
1185 {
1186 10220 std::string matchingKey("hasMatchingDescriptor");
1187 10220 auto itMatching = auxData.find(matchingKey);
1188 10220 return itMatching != auxData.end();
1189 }
1190
1191 10220 static void clearMatchingDescriptor(const io::StreamMetadata::AuxDataMap& auxData)
1192 {
1193 10220 std::string matchingKey("hasMatchingDescriptor");
1194
1/2
✓ Branch 1 taken 10220 times.
✗ Branch 2 not taken.
10220 std::string descriptorKey("descriptorPtr");
1195 10220 auto itMatching = auxData.find(matchingKey);
1196
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 10220 times.
10220 auto itDescriptor = auxData.find(descriptorKey);
1197
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 10220 times.
10220 if (itMatching != auxData.end()) (const_cast<io::StreamMetadata::AuxDataMap&>(auxData)).erase(itMatching);
1198
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 10220 times.
10220 if (itDescriptor != auxData.end()) (const_cast<io::StreamMetadata::AuxDataMap&>(auxData)).erase(itDescriptor);
1199 10220 }
1200
1201 18 static void insertDescriptor( const io::StreamMetadata::AuxDataMap& auxData,
1202 const Descriptor::Ptr descriptor)
1203 {
1204 18 std::string descriptorKey("descriptorPtr");
1205
1/2
✓ Branch 1 taken 18 times.
✗ Branch 2 not taken.
18 std::string matchingKey("hasMatchingDescriptor");
1206
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 auto itMatching = auxData.find(matchingKey);
1207
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 if (itMatching == auxData.end()) {
1208 // if matching bool is not found, insert "true" and the descriptor
1209
2/4
✓ Branch 1 taken 18 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 18 times.
✗ Branch 5 not taken.
18 (const_cast<io::StreamMetadata::AuxDataMap&>(auxData))[matchingKey] = true;
1210
2/4
✓ Branch 1 taken 18 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 18 times.
✗ Branch 5 not taken.
18 (const_cast<io::StreamMetadata::AuxDataMap&>(auxData))[descriptorKey] = descriptor;
1211 }
1212 18 }
1213
1214 10199 static AttributeSet::Descriptor::Ptr retrieveMatchingDescriptor(const io::StreamMetadata::AuxDataMap& auxData)
1215 {
1216 10199 std::string descriptorKey("descriptorPtr");
1217
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 10199 times.
10199 auto itDescriptor = auxData.find(descriptorKey);
1218
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 10199 times.
10199 assert(itDescriptor != auxData.end());
1219
1/2
✓ Branch 1 taken 10199 times.
✗ Branch 2 not taken.
10199 const Descriptor::Ptr descriptor = boost::any_cast<AttributeSet::Descriptor::Ptr>(itDescriptor->second);
1220 10199 return descriptor;
1221 }
1222 };
1223
1224 113754 const io::StreamMetadata::Ptr meta = io::getStreamMetadataPtr(is);
1225
1226
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 113754 times.
113754 if (!meta) {
1227 OPENVDB_THROW(IoError, "Cannot read in a PointDataLeaf without StreamMetadata.");
1228 }
1229
1230
1/2
✓ Branch 1 taken 113754 times.
✗ Branch 2 not taken.
113754 const Index pass(static_cast<uint16_t>(meta->pass()));
1231
1/2
✓ Branch 1 taken 113754 times.
✗ Branch 2 not taken.
113754 const Index maximumPass(static_cast<uint16_t>(meta->pass() >> 16));
1232
1233 113754 const Index attributes = (maximumPass - 4) / 2;
1234
1235
2/2
✓ Branch 0 taken 10220 times.
✓ Branch 1 taken 103534 times.
113754 if (pass == 0) {
1236 // pass 0 - voxel data sizes
1237
1/2
✓ Branch 1 taken 10220 times.
✗ Branch 2 not taken.
10220 is.read(reinterpret_cast<char*>(&mVoxelBufferSize), sizeof(uint16_t));
1238
2/4
✓ Branch 1 taken 10220 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 10220 times.
✗ Branch 5 not taken.
10220 Local::clearMatchingDescriptor(meta->auxData());
1239 }
1240
2/2
✓ Branch 0 taken 10220 times.
✓ Branch 1 taken 93314 times.
103534 else if (pass == 1) {
1241 // pass 1 - descriptor and attribute metadata
1242
4/6
✓ Branch 1 taken 10220 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 10220 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 10199 times.
✓ Branch 7 taken 21 times.
10220 if (Local::hasMatchingDescriptor(meta->auxData())) {
1243
2/4
✓ Branch 1 taken 10199 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 10199 times.
✗ Branch 5 not taken.
10199 AttributeSet::Descriptor::Ptr descriptor = Local::retrieveMatchingDescriptor(meta->auxData());
1244
1/2
✓ Branch 1 taken 10199 times.
✗ Branch 2 not taken.
10199 mAttributeSet->resetDescriptor(descriptor, /*allowMismatchingDescriptors=*/true);
1245 }
1246 else {
1247 uint8_t header;
1248
1/2
✓ Branch 1 taken 21 times.
✗ Branch 2 not taken.
21 is.read(reinterpret_cast<char*>(&header), sizeof(uint8_t));
1249
1/2
✓ Branch 1 taken 21 times.
✗ Branch 2 not taken.
21 mAttributeSet->readDescriptor(is);
1250
2/2
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 3 times.
21 if (header & uint8_t(1)) {
1251 AttributeSet::DescriptorPtr descriptor = mAttributeSet->descriptorPtr();
1252
3/8
✓ Branch 1 taken 18 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 18 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 18 times.
✗ Branch 7 not taken.
✗ Branch 8 not taken.
✗ Branch 9 not taken.
36 Local::insertDescriptor(meta->auxData(), descriptor);
1253 }
1254 // a forwards-compatibility mechanism for future use,
1255 // if a 0x2 bit is set, read and skip over a specific number of bytes
1256
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 21 times.
21 if (header & uint8_t(2)) {
1257 uint64_t bytesToSkip;
1258 is.read(reinterpret_cast<char*>(&bytesToSkip), sizeof(uint64_t));
1259 if (bytesToSkip > uint64_t(0)) {
1260 auto metadata = io::getStreamMetadataPtr(is);
1261 if (metadata && metadata->seekable()) {
1262 is.seekg(bytesToSkip, std::ios_base::cur);
1263 }
1264 else {
1265 std::vector<uint8_t> tempData(bytesToSkip);
1266 is.read(reinterpret_cast<char*>(&tempData[0]), bytesToSkip);
1267 }
1268 }
1269 }
1270 // this reader is only able to read headers with 0x1 and 0x2 bits set
1271
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 21 times.
21 if (header > uint8_t(3)) {
1272 OPENVDB_THROW(IoError, "Unrecognised header flags in PointDataLeafNode");
1273 }
1274 }
1275
1/2
✓ Branch 1 taken 10220 times.
✗ Branch 2 not taken.
10220 mAttributeSet->readMetadata(is);
1276 }
1277
2/2
✓ Branch 0 taken 36437 times.
✓ Branch 1 taken 56877 times.
93314 else if (pass < (attributes + 2)) {
1278 // pass 2...n+2 - attribute uniform values
1279
2/2
✓ Branch 0 taken 36436 times.
✓ Branch 1 taken 1 times.
36437 const size_t attributeIndex = pass - 2;
1280
2/2
✓ Branch 0 taken 36436 times.
✓ Branch 1 taken 1 times.
36437 AttributeArray* array = attributeIndex < mAttributeSet->size() ?
1281
1/2
✓ Branch 1 taken 36436 times.
✗ Branch 2 not taken.
36436 mAttributeSet->get(attributeIndex) : nullptr;
1282
1/2
✓ Branch 0 taken 36436 times.
✗ Branch 1 not taken.
36436 if (array) {
1283 compression::PagedInputStream& pagedStream =
1284
2/4
✓ Branch 1 taken 36436 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 36436 times.
✗ Branch 5 not taken.
36436 Local::getOrInsertPagedStream(meta->auxData(), static_cast<Index>(attributeIndex));
1285 pagedStream.setInputStream(is);
1286 pagedStream.setSizeOnly(true);
1287
1/2
✓ Branch 1 taken 36436 times.
✗ Branch 2 not taken.
36436 array->readPagedBuffers(pagedStream);
1288 }
1289 }
1290
2/2
✓ Branch 0 taken 10220 times.
✓ Branch 1 taken 46657 times.
56877 else if (pass == attributes + 2) {
1291 // pass n+2 - voxel data
1292
1293
1/2
✓ Branch 1 taken 10220 times.
✗ Branch 2 not taken.
10220 const Index passValue(meta->pass());
1294
1295 // StreamMetadata pass variable used to temporarily store voxel buffer size
1296 io::StreamMetadata& nonConstMeta = const_cast<io::StreamMetadata&>(*meta);
1297
1/2
✓ Branch 1 taken 10220 times.
✗ Branch 2 not taken.
10220 nonConstMeta.setPass(mVoxelBufferSize);
1298
1299 // readBuffers() calls readCompressedValues specialization above
1300 10220 BaseLeaf::readBuffers(is, fromHalf);
1301
1302 // pass now reset to original value
1303
1/2
✓ Branch 1 taken 10220 times.
✗ Branch 2 not taken.
10220 nonConstMeta.setPass(passValue);
1304 }
1305
2/2
✓ Branch 0 taken 36437 times.
✓ Branch 1 taken 10220 times.
46657 else if (pass < (attributes*2 + 3)) {
1306 // pass n+2..2n+2 - attribute buffers
1307 36437 const Index attributeIndex = pass - attributes - 3;
1308
2/2
✓ Branch 0 taken 36436 times.
✓ Branch 1 taken 1 times.
36437 AttributeArray* array = attributeIndex < mAttributeSet->size() ?
1309
1/2
✓ Branch 1 taken 36436 times.
✗ Branch 2 not taken.
36436 mAttributeSet->get(attributeIndex) : nullptr;
1310
1/2
✓ Branch 0 taken 36436 times.
✗ Branch 1 not taken.
36436 if (array) {
1311 compression::PagedInputStream& pagedStream =
1312
2/4
✓ Branch 1 taken 36436 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 36436 times.
✗ Branch 5 not taken.
36436 Local::getOrInsertPagedStream(meta->auxData(), attributeIndex);
1313 pagedStream.setInputStream(is);
1314 pagedStream.setSizeOnly(false);
1315
1/2
✓ Branch 1 taken 36436 times.
✗ Branch 2 not taken.
36436 array->readPagedBuffers(pagedStream);
1316 }
1317 // cleanup paged stream reference in auxiliary metadata
1318
2/2
✓ Branch 0 taken 26217 times.
✓ Branch 1 taken 10220 times.
36437 if (pass > attributes + 3) {
1319
2/4
✓ Branch 1 taken 26217 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 26217 times.
✗ Branch 5 not taken.
26217 Local::destroyPagedStream(meta->auxData(), attributeIndex-1);
1320 }
1321 }
1322
2/2
✓ Branch 0 taken 10219 times.
✓ Branch 1 taken 1 times.
10220 else if (pass < buffers()) {
1323 // pass 2n+3 - cleanup last paged stream
1324
1/2
✓ Branch 1 taken 10219 times.
✗ Branch 2 not taken.
10219 const Index attributeIndex = pass - attributes - 4;
1325
2/4
✓ Branch 1 taken 10219 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 10219 times.
✗ Branch 5 not taken.
10219 Local::destroyPagedStream(meta->auxData(), attributeIndex);
1326 }
1327 113754 }
1328
1329 template<typename T, Index Log2Dim>
1330 inline void
1331 55110 PointDataLeafNode<T, Log2Dim>::writeBuffers(std::ostream& os, bool toHalf) const
1332 {
1333 struct Local
1334 {
1335 39273 static void destroyPagedStream(const io::StreamMetadata::AuxDataMap& auxData, const Index index)
1336 {
1337 // if paged stream exists, flush and delete it
1338
1/2
✓ Branch 1 taken 39273 times.
✗ Branch 2 not taken.
78546 std::string key("paged:" + std::to_string(index));
1339
2/2
✓ Branch 0 taken 44 times.
✓ Branch 1 taken 39229 times.
39273 auto it = auxData.find(key);
1340
2/2
✓ Branch 0 taken 44 times.
✓ Branch 1 taken 39229 times.
39273 if (it != auxData.end()) {
1341
1/2
✓ Branch 1 taken 44 times.
✗ Branch 2 not taken.
44 compression::PagedOutputStream& stream = *(boost::any_cast<compression::PagedOutputStream::Ptr>(it->second));
1342
1/2
✓ Branch 1 taken 44 times.
✗ Branch 2 not taken.
44 stream.flush();
1343 44 (const_cast<io::StreamMetadata::AuxDataMap&>(auxData)).erase(it);
1344 }
1345 39273 }
1346
1347 35312 static compression::PagedOutputStream& getOrInsertPagedStream( const io::StreamMetadata::AuxDataMap& auxData,
1348 const Index index)
1349 {
1350
1/2
✓ Branch 1 taken 35312 times.
✗ Branch 2 not taken.
70624 std::string key("paged:" + std::to_string(index));
1351
2/2
✓ Branch 0 taken 35268 times.
✓ Branch 1 taken 44 times.
35312 auto it = auxData.find(key);
1352
2/2
✓ Branch 0 taken 35268 times.
✓ Branch 1 taken 44 times.
35312 if (it != auxData.end()) {
1353
1/2
✓ Branch 1 taken 35268 times.
✗ Branch 2 not taken.
70536 return *(boost::any_cast<compression::PagedOutputStream::Ptr>(it->second));
1354 }
1355 else {
1356
1/2
✓ Branch 1 taken 44 times.
✗ Branch 2 not taken.
44 compression::PagedOutputStream::Ptr pagedStream = std::make_shared<compression::PagedOutputStream>();
1357
2/4
✓ Branch 1 taken 44 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 44 times.
✗ Branch 5 not taken.
44 (const_cast<io::StreamMetadata::AuxDataMap&>(auxData))[key] = pagedStream;
1358 return *pagedStream;
1359 }
1360 }
1361
1362 3959 static void insertDescriptor( const io::StreamMetadata::AuxDataMap& auxData,
1363 const Descriptor::Ptr descriptor)
1364 {
1365 3959 std::string descriptorKey("descriptorPtr");
1366
1/2
✓ Branch 1 taken 3959 times.
✗ Branch 2 not taken.
3959 std::string matchingKey("hasMatchingDescriptor");
1367 3959 auto itMatching = auxData.find(matchingKey);
1368
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 3949 times.
3959 auto itDescriptor = auxData.find(descriptorKey);
1369
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 3949 times.
3959 if (itMatching == auxData.end()) {
1370 // if matching bool is not found, insert "true" and the descriptor
1371
3/6
✓ Branch 1 taken 10 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 10 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✓ Branch 7 taken 10 times.
10 (const_cast<io::StreamMetadata::AuxDataMap&>(auxData))[matchingKey] = true;
1372
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 10 times.
10 assert(itDescriptor == auxData.end());
1373
2/4
✓ Branch 1 taken 10 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 10 times.
✗ Branch 5 not taken.
10 (const_cast<io::StreamMetadata::AuxDataMap&>(auxData))[descriptorKey] = descriptor;
1374 }
1375 else {
1376 // if matching bool is found and is false, early exit (a previous descriptor did not match)
1377
1/2
✓ Branch 1 taken 3949 times.
✗ Branch 2 not taken.
3949 bool matching = boost::any_cast<bool>(itMatching->second);
1378
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 3949 times.
3949 if (!matching) return;
1379
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 3949 times.
3949 assert(itDescriptor != auxData.end());
1380 // if matching bool is true, check whether the existing descriptor matches the current one and set
1381 // matching bool to false if not
1382
1/2
✓ Branch 1 taken 3949 times.
✗ Branch 2 not taken.
3949 const Descriptor::Ptr existingDescriptor = boost::any_cast<AttributeSet::Descriptor::Ptr>(itDescriptor->second);
1383
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 3948 times.
3949 if (*existingDescriptor != *descriptor) {
1384
2/6
✓ Branch 1 taken 1 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 1 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
1 (const_cast<io::StreamMetadata::AuxDataMap&>(auxData))[matchingKey] = false;
1385 }
1386 }
1387 }
1388
1389 3959 static bool hasMatchingDescriptor(const io::StreamMetadata::AuxDataMap& auxData)
1390 {
1391 3959 std::string matchingKey("hasMatchingDescriptor");
1392
1/2
✓ Branch 0 taken 3959 times.
✗ Branch 1 not taken.
3959 auto itMatching = auxData.find(matchingKey);
1393 // if matching key is not found, no matching descriptor
1394
1/2
✓ Branch 0 taken 3959 times.
✗ Branch 1 not taken.
3959 if (itMatching == auxData.end()) return false;
1395 // if matching key is found and is false, no matching descriptor
1396
3/4
✓ Branch 1 taken 3959 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 3 times.
✓ Branch 4 taken 3956 times.
3959 if (!boost::any_cast<bool>(itMatching->second)) return false;
1397 return true;
1398 }
1399
1400 3956 static AttributeSet::Descriptor::Ptr retrieveMatchingDescriptor(const io::StreamMetadata::AuxDataMap& auxData)
1401 {
1402 3956 std::string descriptorKey("descriptorPtr");
1403
2/2
✓ Branch 0 taken 3947 times.
✓ Branch 1 taken 9 times.
3956 auto itDescriptor = auxData.find(descriptorKey);
1404 // if matching key is true, however descriptor is not found, it has already been retrieved
1405
2/2
✓ Branch 0 taken 3947 times.
✓ Branch 1 taken 9 times.
3956 if (itDescriptor == auxData.end()) return nullptr;
1406 // otherwise remove it and return it
1407
1/2
✓ Branch 1 taken 9 times.
✗ Branch 2 not taken.
9 const Descriptor::Ptr descriptor = boost::any_cast<AttributeSet::Descriptor::Ptr>(itDescriptor->second);
1408 9 (const_cast<io::StreamMetadata::AuxDataMap&>(auxData)).erase(itDescriptor);
1409 return descriptor;
1410 }
1411
1412 3958 static void clearMatchingDescriptor(const io::StreamMetadata::AuxDataMap& auxData)
1413 {
1414 3958 std::string matchingKey("hasMatchingDescriptor");
1415
1/2
✓ Branch 1 taken 3958 times.
✗ Branch 2 not taken.
3958 std::string descriptorKey("descriptorPtr");
1416 3958 auto itMatching = auxData.find(matchingKey);
1417
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 3948 times.
3958 auto itDescriptor = auxData.find(descriptorKey);
1418
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 3948 times.
3968 if (itMatching != auxData.end()) (const_cast<io::StreamMetadata::AuxDataMap&>(auxData)).erase(itMatching);
1419
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 3957 times.
3959 if (itDescriptor != auxData.end()) (const_cast<io::StreamMetadata::AuxDataMap&>(auxData)).erase(itDescriptor);
1420 3958 }
1421 };
1422
1423 55110 const io::StreamMetadata::Ptr meta = io::getStreamMetadataPtr(os);
1424
1425
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 55109 times.
55110 if (!meta) {
1426
2/6
✓ Branch 1 taken 1 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 1 times.
✗ Branch 5 not taken.
✗ Branch 12 not taken.
✗ Branch 13 not taken.
4 OPENVDB_THROW(IoError, "Cannot write out a PointDataLeaf without StreamMetadata.");
1427 }
1428
1429
1/2
✓ Branch 1 taken 55109 times.
✗ Branch 2 not taken.
55109 const Index pass(static_cast<uint16_t>(meta->pass()));
1430
1431 // leaf traversal analysis deduces the number of passes to perform for this leaf
1432 // then updates the leaf traversal value to ensure all passes will be written
1433
1434
3/4
✓ Branch 1 taken 55109 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 3958 times.
✓ Branch 4 taken 51151 times.
55109 if (meta->countingPasses()) {
1435 const Index requiredPasses = this->buffers();
1436
2/2
✓ Branch 0 taken 9 times.
✓ Branch 1 taken 3949 times.
3958 if (requiredPasses > pass) {
1437
1/2
✓ Branch 1 taken 9 times.
✗ Branch 2 not taken.
9 meta->setPass(requiredPasses);
1438 }
1439 return;
1440 }
1441
1442
1/2
✓ Branch 1 taken 51151 times.
✗ Branch 2 not taken.
51151 const Index maximumPass(static_cast<uint16_t>(meta->pass() >> 16));
1443 51151 const Index attributes = (maximumPass - 4) / 2;
1444
1445
2/2
✓ Branch 0 taken 3959 times.
✓ Branch 1 taken 47192 times.
51151 if (pass == 0) {
1446 // pass 0 - voxel data sizes
1447
2/4
✓ Branch 1 taken 3959 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 3959 times.
✗ Branch 5 not taken.
3959 io::writeCompressedValuesSize(os, this->buffer().data(), SIZE);
1448 // track if descriptor is shared or not
1449
3/6
✓ Branch 1 taken 3959 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 3959 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✓ Branch 7 taken 1 times.
7919 Local::insertDescriptor(meta->auxData(), mAttributeSet->descriptorPtr());
1450 }
1451
2/2
✓ Branch 0 taken 3959 times.
✓ Branch 1 taken 43233 times.
47192 else if (pass == 1) {
1452 // pass 1 - descriptor and attribute metadata
1453
2/4
✓ Branch 1 taken 3959 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 3959 times.
✗ Branch 5 not taken.
3959 bool matchingDescriptor = Local::hasMatchingDescriptor(meta->auxData());
1454
2/2
✓ Branch 0 taken 3956 times.
✓ Branch 1 taken 3 times.
3959 if (matchingDescriptor) {
1455
2/4
✓ Branch 1 taken 3956 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 3956 times.
✗ Branch 5 not taken.
3956 AttributeSet::Descriptor::Ptr descriptor = Local::retrieveMatchingDescriptor(meta->auxData());
1456
2/2
✓ Branch 0 taken 9 times.
✓ Branch 1 taken 3947 times.
3956 if (descriptor) {
1457 // write a header to indicate a shared descriptor
1458 9 uint8_t header(1);
1459
1/2
✓ Branch 1 taken 9 times.
✗ Branch 2 not taken.
9 os.write(reinterpret_cast<const char*>(&header), sizeof(uint8_t));
1460
1/2
✓ Branch 1 taken 9 times.
✗ Branch 2 not taken.
9 mAttributeSet->writeDescriptor(os, /*transient=*/false);
1461 }
1462 }
1463 else {
1464 // write a header to indicate a non-shared descriptor
1465 3 uint8_t header(0);
1466
1/2
✓ Branch 1 taken 3 times.
✗ Branch 2 not taken.
3 os.write(reinterpret_cast<const char*>(&header), sizeof(uint8_t));
1467
1/2
✓ Branch 1 taken 3 times.
✗ Branch 2 not taken.
3 mAttributeSet->writeDescriptor(os, /*transient=*/false);
1468 }
1469
1/2
✓ Branch 1 taken 3959 times.
✗ Branch 2 not taken.
3959 mAttributeSet->writeMetadata(os, /*transient=*/false, /*paged=*/true);
1470 }
1471
2/2
✓ Branch 0 taken 17658 times.
✓ Branch 1 taken 25575 times.
43233 else if (pass < attributes + 2) {
1472 // pass 2...n+2 - attribute buffer sizes
1473 17658 const Index attributeIndex = pass - 2;
1474 // destroy previous paged stream
1475
2/2
✓ Branch 0 taken 13699 times.
✓ Branch 1 taken 3959 times.
17658 if (pass > 2) {
1476
2/4
✓ Branch 1 taken 13699 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 13699 times.
✗ Branch 5 not taken.
13699 Local::destroyPagedStream(meta->auxData(), attributeIndex-1);
1477 }
1478
2/2
✓ Branch 0 taken 17656 times.
✓ Branch 1 taken 2 times.
17658 const AttributeArray* array = attributeIndex < mAttributeSet->size() ?
1479
1/2
✓ Branch 1 taken 17656 times.
✗ Branch 2 not taken.
17656 mAttributeSet->getConst(attributeIndex) : nullptr;
1480
1/2
✓ Branch 0 taken 17656 times.
✗ Branch 1 not taken.
17656 if (array) {
1481 compression::PagedOutputStream& pagedStream =
1482
2/4
✓ Branch 1 taken 17656 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 17656 times.
✗ Branch 5 not taken.
17656 Local::getOrInsertPagedStream(meta->auxData(), attributeIndex);
1483 pagedStream.setOutputStream(os);
1484 pagedStream.setSizeOnly(true);
1485
1/2
✓ Branch 1 taken 17656 times.
✗ Branch 2 not taken.
17656 array->writePagedBuffers(pagedStream, /*outputTransient*/false);
1486 }
1487 }
1488
2/2
✓ Branch 0 taken 3959 times.
✓ Branch 1 taken 21616 times.
25575 else if (pass == attributes + 2) {
1489
1/2
✓ Branch 1 taken 3959 times.
✗ Branch 2 not taken.
3959 const Index attributeIndex = pass - 3;
1490
2/4
✓ Branch 1 taken 3959 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 3959 times.
✗ Branch 5 not taken.
3959 Local::destroyPagedStream(meta->auxData(), attributeIndex);
1491 // pass n+2 - voxel data
1492
1/2
✓ Branch 1 taken 3959 times.
✗ Branch 2 not taken.
3959 BaseLeaf::writeBuffers(os, toHalf);
1493 }
1494
2/2
✓ Branch 0 taken 17657 times.
✓ Branch 1 taken 3959 times.
21616 else if (pass < (attributes*2 + 3)) {
1495 // pass n+3...2n+3 - attribute buffers
1496 17657 const Index attributeIndex = pass - attributes - 3;
1497 // destroy previous paged stream
1498
1/2
✓ Branch 0 taken 17657 times.
✗ Branch 1 not taken.
17657 if (pass > attributes + 2) {
1499
2/4
✓ Branch 1 taken 17657 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 17657 times.
✗ Branch 5 not taken.
17657 Local::destroyPagedStream(meta->auxData(), attributeIndex-1);
1500 }
1501
2/2
✓ Branch 0 taken 17656 times.
✓ Branch 1 taken 1 times.
17657 const AttributeArray* array = attributeIndex < mAttributeSet->size() ?
1502
1/2
✓ Branch 1 taken 17656 times.
✗ Branch 2 not taken.
17656 mAttributeSet->getConst(attributeIndex) : nullptr;
1503
1/2
✓ Branch 0 taken 17656 times.
✗ Branch 1 not taken.
17656 if (array) {
1504 compression::PagedOutputStream& pagedStream =
1505
2/4
✓ Branch 1 taken 17656 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 17656 times.
✗ Branch 5 not taken.
17656 Local::getOrInsertPagedStream(meta->auxData(), attributeIndex);
1506 pagedStream.setOutputStream(os);
1507 pagedStream.setSizeOnly(false);
1508
1/2
✓ Branch 1 taken 17656 times.
✗ Branch 2 not taken.
17656 array->writePagedBuffers(pagedStream, /*outputTransient*/false);
1509 }
1510 }
1511
2/2
✓ Branch 0 taken 3958 times.
✓ Branch 1 taken 1 times.
3959 else if (pass < buffers()) {
1512
2/4
✓ Branch 1 taken 3958 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 3958 times.
✗ Branch 5 not taken.
3958 Local::clearMatchingDescriptor(meta->auxData());
1513 // pass 2n+3 - cleanup last paged stream
1514
1/2
✓ Branch 1 taken 3958 times.
✗ Branch 2 not taken.
3958 const Index attributeIndex = pass - attributes - 4;
1515
2/4
✓ Branch 1 taken 3958 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 3958 times.
✗ Branch 5 not taken.
3958 Local::destroyPagedStream(meta->auxData(), attributeIndex);
1516 }
1517 }
1518
1519 template<typename T, Index Log2Dim>
1520 inline Index64
1521 26905 PointDataLeafNode<T, Log2Dim>::memUsage() const
1522 {
1523 26905 return BaseLeaf::memUsage() + mAttributeSet->memUsage();
1524 }
1525
1526 #if OPENVDB_ABI_VERSION_NUMBER >= 10
1527 template<typename T, Index Log2Dim>
1528 inline Index64
1529 PointDataLeafNode<T, Log2Dim>::memUsageIfLoaded() const
1530 {
1531 return BaseLeaf::memUsageIfLoaded() + mAttributeSet->memUsageIfLoaded();
1532 }
1533 #endif
1534
1535 template<typename T, Index Log2Dim>
1536 inline void
1537 PointDataLeafNode<T, Log2Dim>::evalActiveBoundingBox(CoordBBox& bbox, bool visitVoxels) const
1538 {
1539 12441 BaseLeaf::evalActiveBoundingBox(bbox, visitVoxels);
1540 }
1541
1542 template<typename T, Index Log2Dim>
1543 inline CoordBBox
1544 PointDataLeafNode<T, Log2Dim>::getNodeBoundingBox() const
1545 {
1546 return BaseLeaf::getNodeBoundingBox();
1547 }
1548
1549 template<typename T, Index Log2Dim>
1550 inline void
1551 16 PointDataLeafNode<T, Log2Dim>::fill(const CoordBBox& bbox, const ValueType& value, bool active)
1552 {
1553
1/2
✓ Branch 0 taken 16 times.
✗ Branch 1 not taken.
16 if (!this->allocate()) return;
1554
1555 this->assertNonModifiableUnlessZero(value);
1556
1557 // active state is permitted to be updated
1558
1559
2/2
✓ Branch 0 taken 24 times.
✓ Branch 1 taken 16 times.
40 for (Int32 x = bbox.min().x(); x <= bbox.max().x(); ++x) {
1560 24 const Index offsetX = (x & (DIM-1u)) << 2*Log2Dim;
1561
2/2
✓ Branch 0 taken 36 times.
✓ Branch 1 taken 24 times.
60 for (Int32 y = bbox.min().y(); y <= bbox.max().y(); ++y) {
1562 36 const Index offsetXY = offsetX + ((y & (DIM-1u)) << Log2Dim);
1563
2/2
✓ Branch 0 taken 54 times.
✓ Branch 1 taken 36 times.
90 for (Int32 z = bbox.min().z(); z <= bbox.max().z(); ++z) {
1564
1/2
✓ Branch 0 taken 54 times.
✗ Branch 1 not taken.
54 const Index offset = offsetXY + (z & (DIM-1u));
1565 this->setValueMask(offset, active);
1566 }
1567 }
1568 }
1569 }
1570
1571 template<typename T, Index Log2Dim>
1572 inline void
1573 PointDataLeafNode<T, Log2Dim>::fill(const ValueType& value, bool active)
1574 {
1575 this->assertNonModifiableUnlessZero(value);
1576
1577 // active state is permitted to be updated
1578
1579 if (active) this->setValuesOn();
1580 else this->setValuesOff();
1581 }
1582
1583
1584 ////////////////////////////////////////
1585
1586
1587 template <typename PointDataTreeT>
1588 inline AttributeSet::Descriptor::Ptr
1589 197 makeDescriptorUnique(PointDataTreeT& tree)
1590 {
1591 auto leafIter = tree.beginLeaf();
1592
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 197 times.
197 if (!leafIter) return nullptr;
1593
1594 const AttributeSet::Descriptor& descriptor = leafIter->attributeSet().descriptor();
1595 197 auto newDescriptor = std::make_shared<AttributeSet::Descriptor>(descriptor);
1596
2/2
✓ Branch 0 taken 3289 times.
✓ Branch 1 taken 197 times.
3486 for (; leafIter; ++leafIter) {
1597 leafIter->resetDescriptor(newDescriptor);
1598 }
1599
1600 return newDescriptor;
1601 }
1602
1603
1604 template <typename PointDataTreeT>
1605 inline void
1606 setStreamingMode(PointDataTreeT& tree, bool on)
1607 {
1608 auto leafIter = tree.beginLeaf();
1609 for (; leafIter; ++leafIter) {
1610 for (size_t i = 0; i < leafIter->attributeSet().size(); i++) {
1611 leafIter->attributeArray(i).setStreaming(on);
1612 }
1613 }
1614 }
1615
1616
1617 template <typename PointDataTreeT>
1618 inline void
1619 3 prefetch(PointDataTreeT& tree, bool position, bool otherAttributes)
1620 {
1621 // NOTE: the following is intentionally not multi-threaded, as the I/O
1622 // is faster if done in the order in which it is stored in the file
1623
1624 auto leaf = tree.cbeginLeaf();
1625
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 3 times.
3 if (!leaf) return;
1626
1627 const auto& attributeSet = leaf->attributeSet();
1628
1629 // pre-fetch leaf data
1630
1631
2/2
✓ Branch 0 taken 3 times.
✓ Branch 1 taken 3 times.
6 for ( ; leaf; ++leaf) {
1632 3 leaf->buffer().data();
1633 }
1634
1635 // pre-fetch position attribute data (position will typically have index 0)
1636
1637
2/4
✓ Branch 1 taken 3 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 3 times.
✗ Branch 5 not taken.
3 size_t positionIndex = attributeSet.find("P");
1638
1639
2/2
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 1 times.
3 if (position && positionIndex != AttributeSet::INVALID_POS) {
1640
2/2
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 2 times.
6 for (leaf = tree.cbeginLeaf(); leaf; ++leaf) {
1641
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 2 times.
2 assert(leaf->hasAttribute(positionIndex));
1642 2 leaf->constAttributeArray(positionIndex).loadData();
1643 }
1644 }
1645
1646 // pre-fetch other attribute data
1647
1648
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 2 times.
3 if (otherAttributes) {
1649 const size_t attributes = attributeSet.size();
1650
2/2
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 1 times.
3 for (size_t attributeIndex = 0; attributeIndex < attributes; attributeIndex++) {
1651
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 1 times.
2 if (attributeIndex == positionIndex) continue;
1652
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 1 times.
3 for (leaf = tree.cbeginLeaf(); leaf; ++leaf) {
1653
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 1 times.
1 assert(leaf->hasAttribute(attributeIndex));
1654 1 leaf->constAttributeArray(attributeIndex).loadData();
1655 }
1656 }
1657 }
1658 }
1659
1660
1661 namespace internal {
1662
1663 /// @brief Global registration of point data-related types
1664 /// @note This is called from @c openvdb::initialize, so there is
1665 /// no need to call it directly.
1666 void initialize();
1667
1668 /// @brief Global deregistration of point data-related types
1669 /// @note This is called from @c openvdb::uninitialize, so there is
1670 /// no need to call it directly.
1671 void uninitialize();
1672
1673
1674 /// @brief Recursive node chain which generates a openvdb::TypeList value
1675 /// converted types of nodes to PointDataGrid nodes of the same configuration,
1676 /// rooted at RootNodeType in reverse order, from LeafNode to RootNode.
1677 /// See also TreeConverter<>.
1678 template<typename HeadT, int HeadLevel>
1679 struct PointDataNodeChain
1680 {
1681 using SubtreeT = typename PointDataNodeChain<typename HeadT::ChildNodeType, HeadLevel-1>::Type;
1682 using RootNodeT = tree::RootNode<typename SubtreeT::Back>;
1683 using Type = typename SubtreeT::template Append<RootNodeT>;
1684 };
1685
1686 // Specialization for internal nodes which require their embedded child type to
1687 // be switched
1688 template <typename ChildT, Index Log2Dim, int HeadLevel>
1689 struct PointDataNodeChain<tree::InternalNode<ChildT, Log2Dim>, HeadLevel>
1690 {
1691 using SubtreeT = typename PointDataNodeChain<ChildT, HeadLevel-1>::Type;
1692 using InternalNodeT = tree::InternalNode<typename SubtreeT::Back, Log2Dim>;
1693 using Type = typename SubtreeT::template Append<InternalNodeT>;
1694 };
1695
1696 // Specialization for the last internal node of a node chain, expected
1697 // to be templated on a leaf node
1698 template <typename ChildT, Index Log2Dim>
1699 struct PointDataNodeChain<tree::InternalNode<ChildT, Log2Dim>, /*HeadLevel=*/1>
1700 {
1701 using LeafNodeT = PointDataLeafNode<PointDataIndex32, ChildT::LOG2DIM>;
1702 using InternalNodeT = tree::InternalNode<LeafNodeT, Log2Dim>;
1703 using Type = TypeList<LeafNodeT, InternalNodeT>;
1704 };
1705
1706 } // namespace internal
1707
1708
1709 /// @brief Similiar to ValueConverter, but allows for tree configuration conversion
1710 /// to a PointDataTree. ValueConverter<PointDataIndex32> cannot be used as a
1711 /// PointDataLeafNode is not a specialization of LeafNode
1712 template <typename TreeType>
1713 struct TreeConverter {
1714 using RootNodeT = typename TreeType::RootNodeType;
1715 using NodeChainT = typename internal::PointDataNodeChain<RootNodeT, RootNodeT::LEVEL>::Type;
1716 using Type = tree::Tree<typename NodeChainT::Back>;
1717 };
1718
1719
1720 } // namespace points
1721
1722
1723 ////////////////////////////////////////
1724
1725
1726 namespace tree
1727 {
1728
1729 /// Helper metafunction used to implement LeafNode::SameConfiguration
1730 /// (which, as an inner class, can't be independently specialized)
1731 template<Index Dim1, typename T2>
1732 struct SameLeafConfig<Dim1, points::PointDataLeafNode<T2, Dim1>> { static const bool value = true; };
1733
1734 } // namespace tree
1735 } // namespace OPENVDB_VERSION_NAME
1736 } // namespace openvdb
1737
1738 #endif // OPENVDB_POINTS_POINT_DATA_GRID_HAS_BEEN_INCLUDED
1739