Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
godotengine
GitHub Repository: godotengine/godot
Path: blob/master/thirdparty/embree/kernels/bvh/bvh.h
9912 views
1
// Copyright 2009-2021 Intel Corporation
2
// SPDX-License-Identifier: Apache-2.0
3
4
#pragma once
5
6
/* include all node types */
7
#include "bvh_node_aabb.h"
8
#include "bvh_node_aabb_mb.h"
9
#include "bvh_node_aabb_mb4d.h"
10
#include "bvh_node_obb.h"
11
#include "bvh_node_obb_mb.h"
12
#include "bvh_node_qaabb.h"
13
14
namespace embree
15
{
16
/*! flags used to enable specific node types in intersectors */
17
enum BVHNodeFlags
18
{
19
BVH_FLAG_ALIGNED_NODE = 0x00001,
20
BVH_FLAG_ALIGNED_NODE_MB = 0x00010,
21
BVH_FLAG_UNALIGNED_NODE = 0x00100,
22
BVH_FLAG_UNALIGNED_NODE_MB = 0x01000,
23
BVH_FLAG_QUANTIZED_NODE = 0x100000,
24
BVH_FLAG_ALIGNED_NODE_MB4D = 0x1000000,
25
26
/* short versions */
27
BVH_AN1 = BVH_FLAG_ALIGNED_NODE,
28
BVH_AN2 = BVH_FLAG_ALIGNED_NODE_MB,
29
BVH_AN2_AN4D = BVH_FLAG_ALIGNED_NODE_MB | BVH_FLAG_ALIGNED_NODE_MB4D,
30
BVH_UN1 = BVH_FLAG_UNALIGNED_NODE,
31
BVH_UN2 = BVH_FLAG_UNALIGNED_NODE_MB,
32
BVH_MB = BVH_FLAG_ALIGNED_NODE_MB | BVH_FLAG_UNALIGNED_NODE_MB | BVH_FLAG_ALIGNED_NODE_MB4D,
33
BVH_AN1_UN1 = BVH_FLAG_ALIGNED_NODE | BVH_FLAG_UNALIGNED_NODE,
34
BVH_AN2_UN2 = BVH_FLAG_ALIGNED_NODE_MB | BVH_FLAG_UNALIGNED_NODE_MB,
35
BVH_AN2_AN4D_UN2 = BVH_FLAG_ALIGNED_NODE_MB | BVH_FLAG_ALIGNED_NODE_MB4D | BVH_FLAG_UNALIGNED_NODE_MB,
36
BVH_QN1 = BVH_FLAG_QUANTIZED_NODE
37
};
38
39
/*! Multi BVH with N children. Each node stores the bounding box of
40
* it's N children as well as N child references. */
41
template<int N>
42
class BVHN : public AccelData
43
{
44
ALIGNED_CLASS_(16);
45
public:
46
47
/*! forward declaration of node ref type */
48
typedef NodeRefPtr<N> NodeRef;
49
typedef BaseNode_t<NodeRef,N> BaseNode;
50
typedef AABBNode_t<NodeRef,N> AABBNode;
51
typedef AABBNodeMB_t<NodeRef,N> AABBNodeMB;
52
typedef AABBNodeMB4D_t<NodeRef,N> AABBNodeMB4D;
53
typedef OBBNode_t<NodeRef,N> OBBNode;
54
typedef OBBNodeMB_t<NodeRef,N> OBBNodeMB;
55
typedef QuantizedBaseNode_t<N> QuantizedBaseNode;
56
typedef QuantizedBaseNodeMB_t<N> QuantizedBaseNodeMB;
57
typedef QuantizedNode_t<NodeRef,N> QuantizedNode;
58
59
/*! Number of bytes the nodes and primitives are minimally aligned to.*/
60
static const size_t byteAlignment = 16;
61
static const size_t byteNodeAlignment = 4*N;
62
63
/*! Empty node */
64
static const size_t emptyNode = NodeRef::emptyNode;
65
66
/*! Invalid node, used as marker in traversal */
67
static const size_t invalidNode = NodeRef::invalidNode;
68
static const size_t popRay = NodeRef::popRay;
69
70
/*! Maximum depth of the BVH. */
71
static const size_t maxBuildDepth = 32;
72
static const size_t maxBuildDepthLeaf = maxBuildDepth+8;
73
static const size_t maxDepth = 2*maxBuildDepthLeaf; // 2x because of two level builder
74
75
/*! Maximum number of primitive blocks in a leaf. */
76
static const size_t maxLeafBlocks = NodeRef::maxLeafBlocks;
77
78
public:
79
80
/*! Builder interface to create allocator */
81
struct CreateAlloc : public FastAllocator::Create {
82
__forceinline CreateAlloc (BVHN* bvh) : FastAllocator::Create(&bvh->alloc) {}
83
};
84
85
typedef BVHNodeRecord<NodeRef> NodeRecord;
86
typedef BVHNodeRecordMB<NodeRef> NodeRecordMB;
87
typedef BVHNodeRecordMB4D<NodeRef> NodeRecordMB4D;
88
89
public:
90
91
/*! BVHN default constructor. */
92
BVHN (const PrimitiveType& primTy, Scene* scene);
93
94
/*! BVHN destruction */
95
~BVHN ();
96
97
/*! clears the acceleration structure */
98
void clear();
99
100
/*! sets BVH members after build */
101
void set (NodeRef root, const LBBox3fa& bounds, size_t numPrimitives);
102
103
/*! Clears the barrier bits of a subtree. */
104
void clearBarrier(NodeRef& node);
105
106
/*! lays out num large nodes of the BVH */
107
void layoutLargeNodes(size_t num);
108
NodeRef layoutLargeNodesRecursion(NodeRef& node, const FastAllocator::CachedAllocator& allocator);
109
110
/*! called by all builders before build starts */
111
double preBuild(const std::string& builderName);
112
113
/*! called by all builders after build ended */
114
void postBuild(double t0);
115
116
/*! allocator class */
117
struct Allocator {
118
BVHN* bvh;
119
Allocator (BVHN* bvh) : bvh(bvh) {}
120
__forceinline void* operator() (size_t bytes) const {
121
return bvh->alloc._threadLocal()->malloc(&bvh->alloc,bytes);
122
}
123
};
124
125
/*! post build cleanup */
126
void cleanup() {
127
alloc.cleanup();
128
}
129
130
public:
131
132
/*! Encodes a node */
133
static __forceinline NodeRef encodeNode(AABBNode* node) { return NodeRef::encodeNode(node); }
134
static __forceinline NodeRef encodeNode(AABBNodeMB* node) { return NodeRef::encodeNode(node); }
135
static __forceinline NodeRef encodeNode(AABBNodeMB4D* node) { return NodeRef::encodeNode(node); }
136
static __forceinline NodeRef encodeNode(OBBNode* node) { return NodeRef::encodeNode(node); }
137
static __forceinline NodeRef encodeNode(OBBNodeMB* node) { return NodeRef::encodeNode(node); }
138
static __forceinline NodeRef encodeLeaf(void* tri, size_t num) { return NodeRef::encodeLeaf(tri,num); }
139
static __forceinline NodeRef encodeTypedLeaf(void* ptr, size_t ty) { return NodeRef::encodeTypedLeaf(ptr,ty); }
140
141
public:
142
143
/*! Prefetches the node this reference points to */
144
__forceinline static void prefetch(const NodeRef ref, int types=0)
145
{
146
#if defined(__AVX512PF__) // MIC
147
if (types != BVH_FLAG_QUANTIZED_NODE) {
148
prefetchL2(((char*)ref.ptr)+0*64);
149
prefetchL2(((char*)ref.ptr)+1*64);
150
if ((N >= 8) || (types > BVH_FLAG_ALIGNED_NODE)) {
151
prefetchL2(((char*)ref.ptr)+2*64);
152
prefetchL2(((char*)ref.ptr)+3*64);
153
}
154
if ((N >= 8) && (types > BVH_FLAG_ALIGNED_NODE)) {
155
/* KNL still needs L2 prefetches for large nodes */
156
prefetchL2(((char*)ref.ptr)+4*64);
157
prefetchL2(((char*)ref.ptr)+5*64);
158
prefetchL2(((char*)ref.ptr)+6*64);
159
prefetchL2(((char*)ref.ptr)+7*64);
160
}
161
}
162
else
163
{
164
/* todo: reduce if 32bit offsets are enabled */
165
prefetchL2(((char*)ref.ptr)+0*64);
166
prefetchL2(((char*)ref.ptr)+1*64);
167
prefetchL2(((char*)ref.ptr)+2*64);
168
}
169
#else
170
if (types != BVH_FLAG_QUANTIZED_NODE) {
171
prefetchL1(((char*)ref.ptr)+0*64);
172
prefetchL1(((char*)ref.ptr)+1*64);
173
if ((N >= 8) || (types > BVH_FLAG_ALIGNED_NODE)) {
174
prefetchL1(((char*)ref.ptr)+2*64);
175
prefetchL1(((char*)ref.ptr)+3*64);
176
}
177
if ((N >= 8) && (types > BVH_FLAG_ALIGNED_NODE)) {
178
/* deactivate for large nodes on Xeon, as it introduces regressions */
179
//prefetchL1(((char*)ref.ptr)+4*64);
180
//prefetchL1(((char*)ref.ptr)+5*64);
181
//prefetchL1(((char*)ref.ptr)+6*64);
182
//prefetchL1(((char*)ref.ptr)+7*64);
183
}
184
}
185
else
186
{
187
/* todo: reduce if 32bit offsets are enabled */
188
prefetchL1(((char*)ref.ptr)+0*64);
189
prefetchL1(((char*)ref.ptr)+1*64);
190
prefetchL1(((char*)ref.ptr)+2*64);
191
}
192
#endif
193
}
194
195
__forceinline static void prefetchW(const NodeRef ref, int types=0)
196
{
197
embree::prefetchEX(((char*)ref.ptr)+0*64);
198
embree::prefetchEX(((char*)ref.ptr)+1*64);
199
if ((N >= 8) || (types > BVH_FLAG_ALIGNED_NODE)) {
200
embree::prefetchEX(((char*)ref.ptr)+2*64);
201
embree::prefetchEX(((char*)ref.ptr)+3*64);
202
}
203
if ((N >= 8) && (types > BVH_FLAG_ALIGNED_NODE)) {
204
embree::prefetchEX(((char*)ref.ptr)+4*64);
205
embree::prefetchEX(((char*)ref.ptr)+5*64);
206
embree::prefetchEX(((char*)ref.ptr)+6*64);
207
embree::prefetchEX(((char*)ref.ptr)+7*64);
208
}
209
}
210
211
/*! bvh type information */
212
public:
213
const PrimitiveType* primTy; //!< primitive type stored in the BVH
214
215
/*! bvh data */
216
public:
217
Device* device; //!< device pointer
218
Scene* scene; //!< scene pointer
219
NodeRef root; //!< root node
220
FastAllocator alloc; //!< allocator used to allocate nodes
221
222
/*! statistics data */
223
public:
224
size_t numPrimitives; //!< number of primitives the BVH is build over
225
size_t numVertices; //!< number of vertices the BVH references
226
227
/*! data arrays for special builders */
228
public:
229
std::vector<BVHN*> objects;
230
vector_t<char,aligned_allocator<char,32>> subdiv_patches;
231
};
232
233
typedef BVHN<4> BVH4;
234
typedef BVHN<8> BVH8;
235
}
236
237