From f8d3b4c0606683bb19ae2cf037e6fd637002954a Mon Sep 17 00:00:00 2001 From: Gael Guennebaud Date: Wed, 7 Jul 2010 09:43:29 +0200 Subject: fix mixing types in DiagonalProduct --- Eigen/src/Core/DiagonalProduct.h | 48 ++++++++++++++++++++++++++-------------- 1 file changed, 32 insertions(+), 16 deletions(-) (limited to 'Eigen/src/Core/DiagonalProduct.h') diff --git a/Eigen/src/Core/DiagonalProduct.h b/Eigen/src/Core/DiagonalProduct.h index 7caf3858f..248b2db9a 100644 --- a/Eigen/src/Core/DiagonalProduct.h +++ b/Eigen/src/Core/DiagonalProduct.h @@ -36,8 +36,16 @@ struct ei_traits > ColsAtCompileTime = MatrixType::ColsAtCompileTime, MaxRowsAtCompileTime = MatrixType::MaxRowsAtCompileTime, MaxColsAtCompileTime = MatrixType::MaxColsAtCompileTime, - Flags = (HereditaryBits & (unsigned int)(MatrixType::Flags)) - | (PacketAccessBit & (unsigned int)(MatrixType::Flags) & (unsigned int)(DiagonalType::DiagonalVectorType::Flags)), + + _StorageOrder = MatrixType::Flags & RowMajorBit ? RowMajor : ColMajor, + _PacketOnDiag = !((int(_StorageOrder) == RowMajor && int(ProductOrder) == OnTheLeft) + ||(int(_StorageOrder) == ColMajor && int(ProductOrder) == OnTheRight)), + _SameTypes = ei_is_same_type::ret, + // FIXME currently we need same types, but in the future the next rule should be the one + //_Vectorizable = bool(int(MatrixType::Flags)&PacketAccessBit) && ((!_PacketOnDiag) || _SameTypes), + _Vectorizable = bool(int(MatrixType::Flags)&PacketAccessBit) && _SameTypes, + + Flags = (HereditaryBits & (unsigned int)(MatrixType::Flags)) | (_Vectorizable ? PacketAccessBit : 0), CoeffReadCost = NumTraits::MulCost + MatrixType::CoeffReadCost + DiagonalType::DiagonalVectorType::CoeffReadCost }; }; @@ -69,26 +77,34 @@ class DiagonalProduct : ei_no_assignment_operator, EIGEN_STRONG_INLINE PacketScalar packet(Index row, Index col) const { enum { - StorageOrder = Flags & RowMajorBit ? RowMajor : ColMajor, - InnerSize = (MatrixType::Flags & RowMajorBit) ? MatrixType::ColsAtCompileTime : MatrixType::RowsAtCompileTime, - DiagonalVectorPacketLoadMode = (LoadMode == Aligned && ((InnerSize%16) == 0)) ? Aligned : Unaligned + StorageOrder = Flags & RowMajorBit ? RowMajor : ColMajor }; const Index indexInDiagonalVector = ProductOrder == OnTheLeft ? row : col; - if((int(StorageOrder) == RowMajor && int(ProductOrder) == OnTheLeft) - ||(int(StorageOrder) == ColMajor && int(ProductOrder) == OnTheRight)) - { - return ei_pmul(m_matrix.template packet(row, col), - ei_pset1(m_diagonal.diagonal().coeff(indexInDiagonalVector))); - } - else - { - return ei_pmul(m_matrix.template packet(row, col), - m_diagonal.diagonal().template packet(indexInDiagonalVector)); - } + return packet_impl(row,col,indexInDiagonalVector,typename ei_meta_if< + ((int(StorageOrder) == RowMajor && int(ProductOrder) == OnTheLeft) + ||(int(StorageOrder) == ColMajor && int(ProductOrder) == OnTheRight)), ei_meta_true, ei_meta_false>::ret()); } protected: + template + EIGEN_STRONG_INLINE PacketScalar packet_impl(Index row, Index col, Index id, ei_meta_true) const + { + return ei_pmul(m_matrix.template packet(row, col), + ei_pset1(m_diagonal.diagonal().coeff(id))); + } + + template + EIGEN_STRONG_INLINE PacketScalar packet_impl(Index row, Index col, Index id, ei_meta_false) const + { + enum { + InnerSize = (MatrixType::Flags & RowMajorBit) ? MatrixType::ColsAtCompileTime : MatrixType::RowsAtCompileTime, + DiagonalVectorPacketLoadMode = (LoadMode == Aligned && ((InnerSize%16) == 0)) ? Aligned : Unaligned + }; + return ei_pmul(m_matrix.template packet(row, col), + m_diagonal.diagonal().template packet(id)); + } + const typename MatrixType::Nested m_matrix; const typename DiagonalType::Nested m_diagonal; }; -- cgit v1.2.3