From 5cb779e5e15ff0e10976f59672bd9067ea0e972e Mon Sep 17 00:00:00 2001 From: Benoit Jacob Date: Wed, 16 Dec 2009 08:53:14 -0500 Subject: [PATCH] * introduce ei_alignmentOffset(MatrixBase&,Integer) couldnt put it in Memory.h as it needs the definition of MatrixBase * make Redux use it --- Eigen/src/Core/Coeffs.h | 32 ++++++++++++++++++++++++++++++++ Eigen/src/Core/Redux.h | 5 +---- Eigen/src/Core/util/Memory.h | 6 +++++- 3 files changed, 38 insertions(+), 5 deletions(-) diff --git a/Eigen/src/Core/Coeffs.h b/Eigen/src/Core/Coeffs.h index 2618f0dce..eda36b7bb 100644 --- a/Eigen/src/Core/Coeffs.h +++ b/Eigen/src/Core/Coeffs.h @@ -379,6 +379,38 @@ EIGEN_STRONG_INLINE void MatrixBase::copyPacket(int index, const Matrix other.derived().template packet(index)); } + +template +struct ei_alignmentOffset_impl +{ + inline static Integer run(const MatrixBase&, Integer) + { return 0; } +}; + +template +struct ei_alignmentOffset_impl +{ + inline static Integer run(const MatrixBase& m, Integer maxOffset) + { + return ei_alignmentOffset(&m.const_cast_derived().coeffRef(0,0), maxOffset); + } +}; + +/** \internal \returns the number of elements which have to be skipped, starting + * from the address of coeffRef(0,0), to find the first 16-byte aligned element. + * + * \note If the expression doesn't have the DirectAccessBit, this function returns 0. + * + * There is also the variant ei_alignmentOffset(const Scalar*, Integer) defined in Memory.h. + */ +template +inline static Integer ei_alignmentOffset(const MatrixBase& m, Integer maxOffset) +{ + return ei_alignmentOffset_impl + ::run(m, maxOffset); +} + #endif #endif // EIGEN_COEFFS_H diff --git a/Eigen/src/Core/Redux.h b/Eigen/src/Core/Redux.h index 171f6dcf5..ae6b01f57 100644 --- a/Eigen/src/Core/Redux.h +++ b/Eigen/src/Core/Redux.h @@ -209,10 +209,7 @@ struct ei_redux_impl { const int size = mat.size(); const int packetSize = ei_packet_traits::size; - const int alignedStart = (Derived::Flags & AlignedBit) - || !(Derived::Flags & DirectAccessBit) - ? 0 - : ei_alignmentOffset(&mat.const_cast_derived().coeffRef(0), size); + const int alignedStart = ei_alignmentOffset(mat,size); enum { alignment = (Derived::Flags & DirectAccessBit) || (Derived::Flags & AlignedBit) ? Aligned : Unaligned diff --git a/Eigen/src/Core/util/Memory.h b/Eigen/src/Core/util/Memory.h index ebeb55ddd..524bec2fc 100644 --- a/Eigen/src/Core/util/Memory.h +++ b/Eigen/src/Core/util/Memory.h @@ -209,7 +209,11 @@ template inline void ei_conditional_aligned_delete(T *pt ei_conditional_aligned_free(ptr); } -/** \internal \returns the number of elements which have to be skipped such that data are 16 bytes aligned */ +/** \internal \returns the number of elements which have to be skipped to + * find the first 16-byte aligned element + * + * There is also the variant ei_alignmentOffset(const MatrixBase&, Integer) defined in Coeffs.h. + */ template inline static Integer ei_alignmentOffset(const Scalar* ptr, Integer maxOffset) {