1111// Workaround for building on clang+libstdc++
1212#include " Acts/Utilities/detail/ReferenceWrapperAnyCompat.hpp"
1313
14- #include " Acts/Propagator/detail/SimdHelpers.hpp"
14+ #include " Acts/Propagator/detail/SimdStd.hpp"
15+ // #include "Acts/Propagator/detail/SimdArray.hpp"
16+
1517#include " Acts/Definitions/Algebra.hpp"
1618#include " Acts/Definitions/Units.hpp"
1719#include " Acts/EventData/MultiComponentTrackParameters.hpp"
2426#include " Acts/Propagator/MultiStepperError.hpp"
2527#include " Acts/Propagator/StepperExtensionList.hpp"
2628#include " Acts/Propagator/detail/Auctioneer.hpp"
27- #include " Acts/Propagator/detail/SimdHelpers .hpp"
29+ #include " Acts/Propagator/detail/MultiStepperUtils .hpp"
2830#include " Acts/Propagator/detail/SimdStepperUtils.hpp"
2931#include " Acts/Propagator/detail/SteppingHelper.hpp"
30- #include " Acts/Propagator/detail/MultiStepperUtils.hpp"
3132#include " Acts/Utilities/Intersection.hpp"
3233#include " Acts/Utilities/Result.hpp"
3334
3839#include < numeric>
3940#include < vector>
4041
42+ #include < boost/container/static_vector.hpp>
43+
4144namespace Acts {
4245
4346// / @brief Reducer struct for the SIMD MultiEigenStepper which reduces the
@@ -60,11 +63,11 @@ struct WeightedComponentReducerSIMD {
6063
6164 static_assert (std::is_same_v<typename T::Scalar, SimdType<N>>);
6265
63- Eigen::Matrix<typename SimdType<N>::Scalar , R, C> ret;
66+ Eigen::Matrix<double , R, C> ret;
6467
6568 for (int c = 0 ; c < C; ++c)
6669 for (int r = 0 ; r < R; ++r)
67- ret (r, c) = SimdHelpers:: sum (m (r, c) * w);
70+ ret (r, c) = sum (m (r, c) * w);
6871
6972 return ret;
7073 }
@@ -82,12 +85,13 @@ struct WeightedComponentReducerSIMD {
8285
8386 template <typename stepper_state_t >
8487 static ActsScalar absoluteMomentum (const stepper_state_t & s) {
85- return SimdHelpers::sum ((1 / (s.pars [eFreeQOverP] / s.q )) * s.weights );
88+ return sum ((s.particleHypothesis .absoluteCharge () / (s.pars [eFreeQOverP])) *
89+ s.weights );
8690 }
8791
8892 template <typename stepper_state_t >
8993 static ActsScalar time (const stepper_state_t & s) {
90- return SimdHelpers:: sum (s.pars [eFreeTime] * s.weights );
94+ return sum (s.pars [eFreeTime] * s.weights );
9195 }
9296
9397 template <typename stepper_state_t >
@@ -133,7 +137,7 @@ class MultiEigenStepperSIMD
133137
134138 // / @brief How many components can this stepper manage?
135139 static constexpr int maxComponents = NComponents;
136-
140+
137141 using BoundState = detail::MultiStepperBoundState;
138142 using CurvilinearState = detail::MultiStepperCurvilinearState;
139143
@@ -142,32 +146,31 @@ class MultiEigenStepperSIMD
142146 using SimdVector3 = Eigen::Matrix<SimdScalar, 3 , 1 >;
143147 using SimdFreeVector = Eigen::Matrix<SimdScalar, eFreeSize, 1 >;
144148 using SimdFreeMatrix = Eigen::Matrix<SimdScalar, eFreeSize, eFreeSize>;
145-
149+
146150 std::unique_ptr<const Acts::Logger> m_logger;
147-
148- const Acts::Logger & logger () const { return *m_logger; }
151+
152+ const Acts::Logger& logger () const { return *m_logger; }
149153
150154 struct State {
151155 // / Number of current active components
152- std::size_t numComponents;
156+ std::size_t numComponents = 0 ;
153157
154158 // / SIMD objects parameters
155- SimdScalar weights = 0 ;
159+ SimdScalar weights = SimdScalar{ 0 } ;
156160 SimdFreeVector pars = SimdFreeVector::Zero();
157161 SimdFreeVector derivative = SimdFreeVector::Zero();
158162 SimdFreeMatrix jacTransport = SimdFreeMatrix::Identity();
159163
160- // / Scalar objects in arrays TODO should they also be SIMD?
164+ // / Scalar objects in arrays
165+ // / TODO should they also be SIMD?
161166 std::array<Intersection3D::Status, NComponents> status;
162167 std::array<Covariance, NComponents> covs;
163168 std::array<Jacobian, NComponents> jacobians;
164169 std::array<BoundToFreeMatrix, NComponents> jacToGlobals;
170+ boost::container::static_vector<ConstrainedStep, NComponents> stepSizes;
165171
166- // no std::array, because ConstrainedStep is not default constructable.
167- // TODO boost::static_vector for rescue
168- std::vector<ConstrainedStep> stepSizes;
169-
170- // TODO this is quite a ugly hack to interface with updateSingleSurfaceStatus
172+ // TODO this is quite a ugly hack to interface with
173+ // updateSingleSurfaceStatus
171174 ConstrainedStep stepSize;
172175
173176 // / Particle hypothesis
@@ -190,8 +193,10 @@ class MultiEigenStepperSIMD
190193
191194 // TODO Why is this here and not function-scope-local?
192195 struct {
193- SimdVector3 B_first = SimdVector3::Zero(), B_middle = SimdVector3::Zero(), B_last = SimdVector3::Zero();
194- SimdVector3 k1 = SimdVector3::Zero(), k2 = SimdVector3::Zero(), k3 = SimdVector3::Zero(), k4 = SimdVector3::Zero();
196+ SimdVector3 B_first = SimdVector3::Zero(), B_middle = SimdVector3::Zero(),
197+ B_last = SimdVector3::Zero();
198+ SimdVector3 k1 = SimdVector3::Zero(), k2 = SimdVector3::Zero(),
199+ k3 = SimdVector3::Zero(), k4 = SimdVector3::Zero();
195200 std::array<SimdScalar, 4 > kQoP ;
196201 } stepData;
197202
@@ -217,9 +222,12 @@ class MultiEigenStepperSIMD
217222 : particleHypothesis(multipars.particleHypothesis()),
218223 fieldCache(bfield->makeCache (mctx)),
219224 geoContext(gctx) {
220- assert (!multipars.components ().empty () && " empty cmps" );
221- assert (multipars.components ().size () <= NComponents &&
222- " mismatching cmp number" );
225+ if (multipars.components ().empty ()) {
226+ throw std::invalid_argument (
227+ " Cannot construct MultiEigenStepperLoop::State with empty "
228+ " multi-component parameters" );
229+ }
230+ assert (multipars.components ().size () <= NComponents);
223231
224232 numComponents = multipars.components ().size ();
225233
@@ -243,10 +251,13 @@ class MultiEigenStepperSIMD
243251 covs[i] = BoundSquareMatrix (*cov);
244252 jacToGlobals[i] =
245253 multipars.referenceSurface ().boundToFreeJacobian (gctx, bound);
254+ } else {
255+ covTransport = false ;
256+ covs[i] = BoundSquareMatrix::Zero ();
257+ jacToGlobals[i] = BoundToFreeMatrix::Zero ();
246258 }
247259 }
248260
249- // TODO Smater initialization when moving to std::array...
250261 for (auto i = 0ul ; i < NComponents; ++i) {
251262 stepSizes.push_back (ConstrainedStep (ssize));
252263 status[i] = Intersection3D::Status::reachable;
@@ -350,11 +361,8 @@ class MultiEigenStepperSIMD
350361 State makeState (std::reference_wrapper<const GeometryContext> gctx,
351362 std::reference_wrapper<const MagneticFieldContext> mctx,
352363 const MultiComponentBoundTrackParameters& par,
353- Direction ndir = Direction::Forward,
354- double ssize = std::numeric_limits<double >::max(),
355- double stolerance = s_onSurfaceTolerance) const {
356- return State (gctx, SingleStepper::m_bField->makeCache (mctx), par, ndir,
357- ssize, stolerance);
364+ double ssize = std::numeric_limits<double >::max()) const {
365+ return State (gctx, mctx, SingleStepper::m_bField, par, ssize);
358366 }
359367
360368 // / Updates the components in the multistepper
@@ -385,7 +393,8 @@ class MultiEigenStepperSIMD
385393 }
386394
387395 // / Constructor
388- MultiEigenStepperSIMD (std::shared_ptr<const MagneticFieldProvider> bField, std::unique_ptr<const Logger> logger =
396+ MultiEigenStepperSIMD (std::shared_ptr<const MagneticFieldProvider> bField,
397+ std::unique_ptr<const Logger> logger =
389398 getDefaultLogger (" SIMDStepper" , Logging::VERBOSE))
390399 : SingleStepper(bField), m_logger(std::move(logger)) {}
391400
@@ -503,8 +512,8 @@ class MultiEigenStepperSIMD
503512 // / @param surface [in] The surface provided
504513 // / @param bcheck [in] The boundary check for this status update
505514 Intersection3D::Status updateSurfaceStatus (
506- State& state, const Surface& surface, std::uint8_t index, Direction navDir,
507- const BoundaryCheck& bcheck,
515+ State& state, const Surface& surface, std::uint8_t index,
516+ Direction navDir, const BoundaryCheck& bcheck,
508517 const Logger& logger = getDummyLogger()) const ;
509518
510519 // / Update step size
@@ -520,8 +529,6 @@ class MultiEigenStepperSIMD
520529 template <typename object_intersection_t >
521530 void updateStepSize (State& state, const object_intersection_t & oIntersection,
522531 bool release = true ) const {
523- ACTS_DEBUG (" MultiEigenStepperSIMD::updateStepSize" );
524-
525532 for (auto i = 0ul ; i < state.numComponents ; ++i) {
526533 const auto intersection = oIntersection.representation ->intersect (
527534 state.geoContext , position (i, state),
@@ -539,13 +546,11 @@ class MultiEigenStepperSIMD
539546 void setStepSize (State& state, double stepSize,
540547 ConstrainedStep::Type stype = ConstrainedStep::actor,
541548 bool /* release*/ = true ) const {
542- ACTS_DEBUG (" MultiEigenStepperSIMD::setStepSize" );
543549 for (auto & ss : state.stepSizes )
544550 ss.update (stepSize, stype, true );
545551 }
546552
547553 double getStepSize (const State& state, ConstrainedStep::Type stype) const {
548- ACTS_DEBUG (" MultiEigenStepperSIMD::getStepSize" );
549554 return std::min_element (begin (state.stepSizes ), end (state.stepSizes ),
550555 [stype](const auto & a, const auto & b) {
551556 return a.value (stype) < b.value (stype);
@@ -557,7 +562,6 @@ class MultiEigenStepperSIMD
557562 // /
558563 // / @param state [in,out] The stepping state (thread-local cache)
559564 void releaseStepSize (State& state) const {
560- ACTS_DEBUG (" MultiEigenStepperSIMD::releaseStepSize" );
561565 for (auto & ss : state.stepSizes )
562566 ss.release (ConstrainedStep::actor);
563567 }
@@ -612,8 +616,7 @@ class MultiEigenStepperSIMD
612616 // / - the stepwise jacobian towards it (from last bound)
613617 // / - and the path length (from start - for ordering)
614618 Result<BoundState> boundState (
615- State& state, const Surface& surface,
616- bool transportCov = true ,
619+ State& state, const Surface& surface, bool transportCov = true ,
617620 const FreeToBoundCorrection& freeToBoundCorrection =
618621 FreeToBoundCorrection (false )) const ;
619622
0 commit comments