File indexing completed on 2026-07-28 08:21:00
0001
0002
0003
0004
0005
0006
0007
0008
0009 #pragma once
0010
0011 #include "Acts/Definitions/Algebra.hpp"
0012 #include "Acts/EventData/CompositeSpacePoint.hpp"
0013 #include "Acts/Geometry/GeometryIdentifier.hpp"
0014 #include "Acts/Utilities/detail/ContainerIterator.hpp"
0015 #include "ActsExamples/EventData/MuonSpacePoint.hpp"
0016
0017 #include <array>
0018 #include <cstddef>
0019 #include <cstdint>
0020 #include <vector>
0021
0022 #include <cuda_runtime.h>
0023
0024 namespace ActsExamples {
0025
0026
0027
0028
0029
0030
0031
0032
0033
0034
0035
0036
0037
0038
0039
0040
0041
0042
0043
0044
0045
0046
0047 __host__ __device__ inline unsigned detLayer(std::uint32_t rawId) noexcept {
0048 static constexpr std::uint32_t fourBit = 0xFu;
0049 static constexpr std::uint32_t layerShift = 17u;
0050
0051 return static_cast<unsigned>((rawId >> layerShift) & fourBit);
0052 }
0053
0054
0055
0056
0057
0058 struct CudaMuonSpacePointArrays {
0059 Acts::GeometryIdentifier::Value* geometryId = nullptr;
0060 std::uint32_t* muonId = nullptr;
0061
0062 double* localPositionX = nullptr;
0063 double* localPositionY = nullptr;
0064 double* localPositionZ = nullptr;
0065
0066 double* sensorDirectionX = nullptr;
0067 double* sensorDirectionY = nullptr;
0068 double* sensorDirectionZ = nullptr;
0069
0070 double* toNextSensorX = nullptr;
0071 double* toNextSensorY = nullptr;
0072 double* toNextSensorZ = nullptr;
0073
0074 double* planeNormalX = nullptr;
0075 double* planeNormalY = nullptr;
0076 double* planeNormalZ = nullptr;
0077
0078 double* covariance0 = nullptr;
0079 double* covariance1 = nullptr;
0080 double* covariance2 = nullptr;
0081
0082 double* driftRadius = nullptr;
0083 double* time = nullptr;
0084
0085 std::uint32_t* bucketStart = nullptr;
0086 std::uint32_t* bucketEnd = nullptr;
0087 };
0088
0089
0090
0091 struct CudaMuonSpacePointHostData {
0092 std::vector<Acts::GeometryIdentifier::Value> geometryId;
0093 std::vector<std::uint32_t> muonId;
0094
0095 std::vector<double> localPositionX;
0096 std::vector<double> localPositionY;
0097 std::vector<double> localPositionZ;
0098
0099 std::vector<double> sensorDirectionX;
0100 std::vector<double> sensorDirectionY;
0101 std::vector<double> sensorDirectionZ;
0102
0103 std::vector<double> toNextSensorX;
0104 std::vector<double> toNextSensorY;
0105 std::vector<double> toNextSensorZ;
0106
0107 std::vector<double> planeNormalX;
0108 std::vector<double> planeNormalY;
0109 std::vector<double> planeNormalZ;
0110
0111 std::vector<double> covariance0;
0112 std::vector<double> covariance1;
0113 std::vector<double> covariance2;
0114
0115 std::vector<double> driftRadius;
0116 std::vector<double> time;
0117
0118 std::vector<std::uint32_t> bucketStart;
0119 std::vector<std::uint32_t> bucketEnd;
0120 };
0121
0122 class CudaMuonSpacePointContainer;
0123
0124
0125
0126
0127
0128
0129 class CudaMuonSpacePointProxy {
0130 public:
0131
0132 CudaMuonSpacePointProxy() = default;
0133
0134
0135
0136
0137 CudaMuonSpacePointProxy(const CudaMuonSpacePointContainer& container,
0138 std::size_t index) noexcept;
0139
0140
0141 const MuonSpacePoint::MuonId& id() const;
0142
0143
0144 const Acts::GeometryIdentifier& geometryId() const;
0145
0146
0147 const Acts::Vector3& localPosition() const;
0148
0149
0150 const Acts::Vector3& sensorDirection() const;
0151
0152
0153 const Acts::Vector3& planeNormal() const;
0154
0155
0156 const Acts::Vector3& toNextSensor() const;
0157
0158
0159 const std::array<double, 3>& covariance() const;
0160
0161
0162 double driftRadius() const;
0163
0164
0165 double time() const;
0166
0167
0168 bool isStraw() const;
0169
0170
0171 bool hasTime() const;
0172
0173
0174 bool measuresLoc0() const;
0175
0176
0177 bool measuresLoc1() const;
0178
0179 private:
0180 const CudaMuonSpacePointContainer* m_container = nullptr;
0181 std::size_t m_index = 0;
0182
0183
0184 mutable MuonSpacePoint::MuonId m_idCache{};
0185 mutable Acts::GeometryIdentifier m_geometryIdCache{};
0186 mutable Acts::Vector3 m_localPositionCache{Acts::Vector3::Zero()};
0187 mutable Acts::Vector3 m_sensorDirectionCache{Acts::Vector3::Zero()};
0188 mutable Acts::Vector3 m_toNextSensorCache{Acts::Vector3::Zero()};
0189 mutable Acts::Vector3 m_planeNormalCache{Acts::Vector3::Zero()};
0190 mutable std::array<double, 3> m_covarianceCache{0.0, 0.0, 0.0};
0191 };
0192
0193
0194
0195
0196
0197 class CudaMuonSpacePointPtr {
0198 public:
0199
0200 using element_type = CudaMuonSpacePointProxy;
0201
0202
0203 CudaMuonSpacePointPtr() = default;
0204
0205
0206
0207
0208 CudaMuonSpacePointPtr(const CudaMuonSpacePointContainer& container,
0209 std::size_t index) noexcept;
0210
0211
0212 element_type* operator->() noexcept { return &m_proxy; }
0213
0214
0215 element_type& operator*() noexcept { return m_proxy; }
0216
0217
0218 explicit operator bool() noexcept { return m_valid; }
0219
0220 private:
0221 element_type m_proxy{};
0222 bool m_valid = false;
0223 };
0224
0225
0226
0227
0228
0229 class CudaMuonSpacePointContainer {
0230 public:
0231
0232 using value_type = CudaMuonSpacePointPtr;
0233
0234 using size_type = std::size_t;
0235
0236
0237 template <bool read_only>
0238 using Iterator = Acts::detail::ContainerIterator<
0239 CudaMuonSpacePointContainer, CudaMuonSpacePointPtr, size_type, read_only>;
0240
0241
0242 using iterator = Iterator<false>;
0243
0244 using const_iterator = Iterator<true>;
0245
0246
0247 CudaMuonSpacePointContainer() = default;
0248
0249
0250 explicit CudaMuonSpacePointContainer(
0251 const MuonSpacePointContainer& spacePoints);
0252
0253
0254
0255 explicit CudaMuonSpacePointContainer(size_type size);
0256
0257
0258 CudaMuonSpacePointContainer(const CudaMuonSpacePointContainer&) = delete;
0259 CudaMuonSpacePointContainer& operator=(const CudaMuonSpacePointContainer&) =
0260 delete;
0261
0262
0263 CudaMuonSpacePointContainer(CudaMuonSpacePointContainer&& other) noexcept;
0264 CudaMuonSpacePointContainer& operator=(
0265 CudaMuonSpacePointContainer&& other) noexcept;
0266
0267
0268 ~CudaMuonSpacePointContainer() noexcept;
0269
0270
0271 size_type size() const noexcept { return m_size; }
0272
0273
0274 bool empty() const noexcept { return size() == 0; }
0275
0276
0277 size_type bucketCount() const noexcept { return m_host.bucketStart.size(); }
0278
0279
0280
0281 size_type bucketStart(size_type bucket) const;
0282
0283
0284
0285 size_type bucketEnd(size_type bucket) const;
0286
0287
0288
0289
0290 void addBucket(size_type start, size_type end);
0291
0292
0293
0294
0295 void setGeometryId(size_type index,
0296 Acts::GeometryIdentifier::Value geometryId);
0297
0298
0299
0300
0301 void setId(size_type index, std::uint32_t muonId);
0302
0303
0304
0305
0306
0307
0308 void defineCoordinates(size_type index, const Acts::Vector3& position,
0309 const Acts::Vector3& sensorDirection,
0310 const Acts::Vector3& toNextSensor);
0311
0312
0313
0314
0315 void setRadius(size_type index, double radius);
0316
0317
0318
0319
0320 void setTime(size_type index, double time);
0321
0322
0323
0324
0325
0326
0327 void setCovariance(size_type index, double cov0, double cov1, double cov2);
0328
0329
0330 void moveToDevice();
0331
0332
0333 void moveToHost();
0334
0335
0336 void clearDevice() noexcept;
0337
0338
0339 bool isOnDevice() const noexcept { return m_onDevice; }
0340
0341
0342 CudaMuonSpacePointArrays deviceArrays() const noexcept { return m_device; }
0343
0344
0345
0346 value_type operator[](size_type index) noexcept {
0347 return value_type{*this, index};
0348 }
0349
0350
0351
0352 value_type operator[](size_type index) const noexcept {
0353 return value_type{*this, index};
0354 }
0355
0356 value_type at(size_type index) const;
0357
0358 iterator begin() noexcept { return {*this, 0}; }
0359
0360 iterator end() noexcept { return {*this, size()}; }
0361
0362 const_iterator begin() const noexcept { return {*this, 0}; }
0363
0364 const_iterator end() const noexcept { return {*this, size()}; }
0365
0366
0367 std::uint32_t muonId(std::uint32_t idx) const noexcept {
0368 return m_host.muonId[idx];
0369 }
0370
0371
0372 void setLogicalLayer(size_type index, std::uint32_t layer);
0373
0374 private:
0375
0376 friend class CudaMuonSpacePointProxy;
0377
0378 size_type m_size = 0;
0379 CudaMuonSpacePointHostData m_host{};
0380 CudaMuonSpacePointArrays m_device{};
0381 bool m_onDevice = false;
0382
0383 void checkIndex(size_type index) const;
0384 void checkBucket(size_type bucket) const;
0385 };
0386
0387
0388 static_assert(Acts::Experimental::CompositeSpacePoint<CudaMuonSpacePointProxy>);
0389 static_assert(
0390 Acts::Experimental::CompositeSpacePointPtr<CudaMuonSpacePointPtr>);
0391 static_assert(Acts::Experimental::CompositeSpacePointContainer<
0392 CudaMuonSpacePointContainer>);
0393
0394 }