Skip to content

Commit 002e3c8

Browse files
author
Vakho Tsulaia
committed
single_store: added support for handling multiple contexts on the host
1 parent 59b52c3 commit 002e3c8

File tree

6 files changed

+90
-22
lines changed

6 files changed

+90
-22
lines changed

core/include/detray/core/detail/single_store.hpp

+83-15
Original file line numberDiff line numberDiff line change
@@ -65,7 +65,9 @@ class single_store {
6565
template <typename allocator_t = vecmem::memory_resource>
6666
requires(std::derived_from<allocator_t, std::pmr::memory_resource>)
6767
DETRAY_HOST explicit single_store(allocator_t &resource)
68-
: m_container(&resource) {}
68+
: m_container(&resource) {
69+
m_context_size=m_container.size();
70+
}
6971

7072
/// Copy Construct with a specific memory resource @param resource
7173
/// (host-side only)
@@ -74,7 +76,9 @@ class single_store {
7476
requires(std::is_same_v<C, std::vector<T>>
7577
&&std::derived_from<allocator_t, std::pmr::memory_resource>)
7678
DETRAY_HOST single_store(allocator_t &resource, const T &arg)
77-
: m_container(&resource, arg) {}
79+
: m_container(&resource, arg) {
80+
m_context_size=m_container.size();
81+
}
7882

7983
/// Construct from the container @param view . Mainly used device-side.
8084
template <concepts::device_view container_view_t>
@@ -95,36 +99,58 @@ class single_store {
9599
DETRAY_HOST_DEVICE
96100
constexpr auto size(const context_type & /*ctx*/ = {}) const noexcept
97101
-> dindex {
98-
return static_cast<dindex>(m_container.size());
102+
if(m_n_contexts==0) {
103+
return static_cast<dindex>(m_container.size());
104+
}
105+
else {
106+
return static_cast<dindex>(m_context_size);
107+
}
99108
}
100109

101110
/// @returns true if the underlying container is empty
102111
DETRAY_HOST_DEVICE
103-
constexpr auto empty(const context_type & /*ctx*/ = {}) const noexcept
112+
constexpr auto empty(const context_type & ctx = {}) const noexcept
104113
-> bool {
105-
return m_container.empty();
114+
if(m_n_contexts==0) {
115+
return m_container.empty();
116+
}
117+
else {
118+
return ctx.get()>m_n_contexts;
119+
}
106120
}
107121

108122
/// @returns the collections iterator at the start position
109123
DETRAY_HOST_DEVICE
110-
constexpr auto begin(const context_type & /*ctx*/ = {}) const {
111-
return m_container.begin();
124+
constexpr auto begin(const context_type & ctx = {}) const {
125+
if(m_n_contexts==0) {
126+
return m_container.begin();
127+
}
128+
else {
129+
return m_container.begin()+ctx.get()*m_context_size;
130+
}
112131
}
113132

114133
/// @returns the collections iterator sentinel
115134
DETRAY_HOST_DEVICE
116-
constexpr auto end(const context_type & /*ctx*/ = {}) const {
117-
return m_container.end();
135+
constexpr auto end(const context_type & ctx = {}) const {
136+
if(m_n_contexts==0) {
137+
return m_container.end();
138+
}
139+
else {
140+
return m_container.begin()+(ctx.get()+1)*m_context_size;
141+
}
118142
}
119143

120144
/// @returns access to the underlying container - const
145+
/// ? Remove the ctx argument ?
121146
DETRAY_HOST_DEVICE
122147
constexpr auto get(const context_type & /*ctx*/) const noexcept
123148
-> const base_type & {
124149
return m_container;
125150
}
126151

127152
/// @returns access to the underlying container - non-const
153+
/// ? Remove the ctx argument ?
128154
DETRAY_HOST_DEVICE
129155
constexpr auto get(const context_type & /*ctx*/) noexcept -> base_type & {
130156
return m_container;
@@ -135,33 +161,44 @@ class single_store {
135161
constexpr auto at(const dindex i,
136162
const context_type &ctx = {}) const noexcept
137163
-> const T & {
138-
[[maybe_unused]] context_type tmp_ctx{
139-
ctx}; // Temporary measure to avoid warnings
140-
return m_container.at(i);
164+
if(m_n_contexts==0) {
165+
return m_container.at(i);
166+
}
167+
else {
168+
return m_container.at(ctx.get()*m_context_size+i);
169+
}
141170
}
142171

143172
/// @returns context based access to an element (also range checked)
144173
DETRAY_HOST_DEVICE
145174
constexpr auto at(const dindex i, const context_type &ctx = {}) noexcept
146175
-> T & {
147-
[[maybe_unused]] context_type tmp_ctx{
148-
ctx}; // Temporary measure to avoid warnings
149-
return m_container.at(i);
176+
if(m_n_contexts==0) {
177+
return m_container.at(i);
178+
}
179+
else {
180+
return m_container.at(ctx.get()*m_context_size+i);
181+
}
150182
}
151183

152184
/// Removes and destructs all elements in the container.
185+
/// ? Remove the ctx argument ?
153186
DETRAY_HOST void clear(const context_type & /*ctx*/) {
154187
m_container.clear();
188+
m_context_size=0;
155189
}
156190

157191
/// Reserve memory of size @param n for a given geometry context
192+
/// ? Remove the ctx argument ?
158193
DETRAY_HOST void reserve(std::size_t n, const context_type & /*ctx*/) {
159194
m_container.reserve(n);
160195
}
161196

162197
/// Resize the underlying container to @param n for a given geometry context
198+
/// ? Remove the ctx argument ?
163199
DETRAY_HOST void resize(std::size_t n, const context_type & /*ctx*/) {
164200
m_container.resize(n);
201+
m_context_size=m_container.size();
165202
}
166203

167204
/// Add a new element to the collection - copy
@@ -171,11 +208,13 @@ class single_store {
171208
/// @param arg the constructor argument
172209
///
173210
/// @note in general can throw an exception
211+
/// ? Remove the ctx argument ?
174212
template <typename U>
175213
DETRAY_HOST constexpr auto push_back(
176214
const U &arg, const context_type & /*ctx*/ = {}) noexcept(false)
177215
-> void {
178216
m_container.push_back(arg);
217+
m_context_size=m_container.size();
179218
}
180219

181220
/// Add a new element to the collection - move
@@ -185,10 +224,12 @@ class single_store {
185224
/// @param arg the constructor argument
186225
///
187226
/// @note in general can throw an exception
227+
/// ? Remove the ctx argument ?
188228
template <typename U>
189229
DETRAY_HOST constexpr auto push_back(
190230
U &&arg, const context_type & /*ctx*/ = {}) noexcept(false) -> void {
191231
m_container.push_back(std::forward<U>(arg));
232+
m_context_size=m_container.size();
192233
}
193234

194235
/// Add a new element to the collection in place
@@ -198,9 +239,11 @@ class single_store {
198239
/// @param args is the list of constructor arguments
199240
///
200241
/// @note in general can throw an exception
242+
/// ? Remove the ctx argument ?
201243
template <typename... Args>
202244
DETRAY_HOST constexpr decltype(auto) emplace_back(
203245
const context_type & /*ctx*/ = {}, Args &&... args) noexcept(false) {
246+
m_context_size++;
204247
return m_container.emplace_back(std::forward<Args>(args)...);
205248
}
206249

@@ -211,12 +254,14 @@ class single_store {
211254
/// @param new_data is the new collection to be added
212255
///
213256
/// @note in general can throw an exception
257+
/// ? Remove the ctx argument ?
214258
template <typename U>
215259
DETRAY_HOST auto insert(container_t<U> &new_data,
216260
const context_type & /*ctx*/ = {}) noexcept(false)
217261
-> void {
218262
m_container.reserve(m_container.size() + new_data.size());
219263
m_container.insert(m_container.end(), new_data.begin(), new_data.end());
264+
m_context_size=m_container.size();
220265
}
221266

222267
/// Insert another collection - move
@@ -226,6 +271,7 @@ class single_store {
226271
/// @param new_data is the new collection to be added
227272
///
228273
/// @note in general can throw an exception
274+
/// ? Remove the ctx argument ?
229275
template <typename U>
230276
DETRAY_HOST auto insert(container_t<U> &&new_data,
231277
const context_type & /*ctx*/ = {}) noexcept(false)
@@ -234,26 +280,46 @@ class single_store {
234280
m_container.insert(m_container.end(),
235281
std::make_move_iterator(new_data.begin()),
236282
std::make_move_iterator(new_data.end()));
283+
m_context_size=m_container.size();
284+
}
285+
286+
template <typename U>
287+
DETRAY_HOST auto add_context(container_t<U> &context_data) noexcept(false)
288+
-> void {
289+
// Cannot add context data to an empty store
290+
if(m_context_size==0) return;
291+
// Wrong size of the context_data vector
292+
if(context_data.size()%m_context_size!=0) return;
293+
// Drop previous contexts if any
294+
if(m_container.size()>m_context_size) m_container.resize(m_context_size);
295+
// Add new contexts
296+
m_n_contexts = context_data.size()/m_context_size;
297+
m_container.reserve(m_container.size() + context_data.size());
298+
m_container.insert(m_container.end(), context_data.begin(), context_data.end());
237299
}
238300

239301
/// Append another store to the current one
240302
///
241303
/// @param other The other container
242304
///
243305
/// @note in general can throw an exception
306+
/// ? Remove the ctx argument ?
244307
DETRAY_HOST void append(single_store &other,
245308
const context_type &ctx = {}) noexcept(false) {
246309
insert(other.m_container, ctx);
310+
m_context_size=m_container.size();
247311
}
248312

249313
/// Append another store to the current one - move
250314
///
251315
/// @param other The other container
252316
///
253317
/// @note in general can throw an exception
318+
/// ? Remove the ctx argument ?
254319
DETRAY_HOST void append(single_store &&other,
255320
const context_type &ctx = {}) noexcept(false) {
256321
insert(std::move(other.m_container), ctx);
322+
m_context_size=m_container.size();
257323
}
258324

259325
/// @return the view on the underlying container - non-const
@@ -269,6 +335,8 @@ class single_store {
269335
private:
270336
/// The underlying container implementation
271337
base_type m_container;
338+
size_type m_context_size{0};
339+
size_type m_n_contexts{0};
272340
};
273341

274342
} // namespace detray

tests/unit_tests/cpu/core/transform_store.cpp

+1-1
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,7 @@ GTEST_TEST(detray_core, static_transform_store) {
2020
using transform3 = test::transform3;
2121
using point3 = test::point3;
2222

23-
using transform_store_t = single_store<transform3>;
23+
using transform_store_t = single_store<transform3,dvector,geometry_context>;
2424
transform_store_t static_store;
2525
typename transform_store_t::context_type ctx0{};
2626
typename transform_store_t::context_type ctx1{};

tests/unit_tests/cpu/navigation/intersection/intersection_kernel.cpp

+1-1
Original file line numberDiff line numberDiff line change
@@ -73,7 +73,7 @@ using mask_container_t =
7373
using mask_link_t = typename mask_container_t::single_link;
7474
using material_link_t = dtyped_index<material_ids, dindex>;
7575

76-
using transform_container_t = single_store<test::transform3>;
76+
using transform_container_t = single_store<test::transform3,dvector,geometry_context>;
7777

7878
/// The Surface definition:
7979
using surface_t =

tests/unit_tests/device/cuda/container_cuda.cpp

+1-1
Original file line numberDiff line numberDiff line change
@@ -46,7 +46,7 @@ TEST(container_cuda, single_store) {
4646
EXPECT_EQ(mng_store.size(), 0u);
4747

4848
// Test the managed memory allocation
49-
empty_context ctx{};
49+
geometry_context ctx{};
5050
mng_store.reserve(4, ctx);
5151
mng_store.emplace_back(ctx, 1.);
5252
mng_store.push_back(2., ctx);

tests/unit_tests/device/cuda/container_cuda_kernel.hpp

+2-2
Original file line numberDiff line numberDiff line change
@@ -19,8 +19,8 @@ namespace detray {
1919

2020
// Single store test
2121
/// @{
22-
using single_store_t = single_store<double, vecmem::vector>;
23-
using single_store_dev_t = single_store<double, vecmem::device_vector>;
22+
using single_store_t = single_store<double, vecmem::vector, geometry_context>;
23+
using single_store_dev_t = single_store<double, vecmem::device_vector, geometry_context>;
2424
/// @}
2525

2626
// Tuple container test

tests/unit_tests/device/cuda/transform_store_cuda_kernel.hpp

+2-2
Original file line numberDiff line numberDiff line change
@@ -24,10 +24,10 @@ using scalar = dscalar<test_algebra>;
2424
using point3 = dpoint3D<test_algebra>;
2525
using transform3 = dtransform3D<test_algebra>;
2626

27-
using host_transform_store_t = single_store<transform3, vecmem::vector>;
27+
using host_transform_store_t = single_store<transform3, vecmem::vector, geometry_context>;
2828

2929
using device_transform_store_t =
30-
single_store<transform3, vecmem::device_vector>;
30+
single_store<transform3, vecmem::device_vector, geometry_context>;
3131

3232
void transform_test(vecmem::data::vector_view<point3> input_data,
3333
typename host_transform_store_t::view_type store_data,

0 commit comments

Comments
 (0)