aboutsummaryrefslogtreecommitdiffhomepage
path: root/Eigen/src/Core/Transpose.h
diff options
context:
space:
mode:
authorGravatar Benoit Jacob <jacob.benoit.1@gmail.com>2010-06-16 09:23:32 -0400
committerGravatar Benoit Jacob <jacob.benoit.1@gmail.com>2010-06-16 09:23:32 -0400
commit42c62c8876283b24aee574584844526480bd8fa4 (patch)
tree1f8d548957aec69b8e318492408faff8f275c00b /Eigen/src/Core/Transpose.h
parent2d1ae6fa0868f79c588ce6c64b30e3b268ddf641 (diff)
fix #126, part 2/2: the checkTransposeAliasing() assertion was always compiled, for all expressions,
even for expressions that are known at compile time to not need it because they don't involve any transposing. This gave 'controlling condition is constant' warnings on ICC, and potentially worse, this could generate a lot of useless code per-expression if the compiler failed to realize that the condition was constant.
Diffstat (limited to 'Eigen/src/Core/Transpose.h')
-rw-r--r--Eigen/src/Core/Transpose.h55
1 files changed, 51 insertions, 4 deletions
diff --git a/Eigen/src/Core/Transpose.h b/Eigen/src/Core/Transpose.h
index 6928ae31a..b1a509a3e 100644
--- a/Eigen/src/Core/Transpose.h
+++ b/Eigen/src/Core/Transpose.h
@@ -310,8 +310,23 @@ struct ei_blas_traits<SelfCwiseBinaryOp<BinOp,NestedXpr> >
static inline const XprType extract(const XprType& x) { return x; }
};
+template<bool DestIsTranposed, typename OtherDerived>
+struct ei_check_transpose_aliasing_compile_time_selector
+{
+ enum { ret = ei_blas_traits<OtherDerived>::IsTransposed != DestIsTranposed
+ };
+};
+
+template<bool DestIsTranposed, typename BinOp, typename DerivedA, typename DerivedB>
+struct ei_check_transpose_aliasing_compile_time_selector<DestIsTranposed,CwiseBinaryOp<BinOp,DerivedA,DerivedB> >
+{
+ enum { ret = ei_blas_traits<DerivedA>::IsTransposed != DestIsTranposed
+ || ei_blas_traits<DerivedB>::IsTransposed != DestIsTranposed
+ };
+};
+
template<typename Scalar, bool DestIsTranposed, typename OtherDerived>
-struct ei_check_transpose_aliasing_selector
+struct ei_check_transpose_aliasing_run_time_selector
{
static bool run(const Scalar* dest, const OtherDerived& src)
{
@@ -320,7 +335,7 @@ struct ei_check_transpose_aliasing_selector
};
template<typename Scalar, bool DestIsTranposed, typename BinOp, typename DerivedA, typename DerivedB>
-struct ei_check_transpose_aliasing_selector<Scalar,DestIsTranposed,CwiseBinaryOp<BinOp,DerivedA,DerivedB> >
+struct ei_check_transpose_aliasing_run_time_selector<Scalar,DestIsTranposed,CwiseBinaryOp<BinOp,DerivedA,DerivedB> >
{
static bool run(const Scalar* dest, const CwiseBinaryOp<BinOp,DerivedA,DerivedB>& src)
{
@@ -329,12 +344,44 @@ struct ei_check_transpose_aliasing_selector<Scalar,DestIsTranposed,CwiseBinaryOp
}
};
+// the following selector, checkTransposeAliasing_impl, based on MightHaveTransposeAliasing,
+// is because when the condition controlling the assert is known at compile time, ICC emits a warning.
+// This is actually a good warning: in expressions that don't have any transposing, the condition is
+// known at compile time to be false, and using that, we can avoid generating the code of the assert again
+// and again for all these expressions that don't need it.
+
+template<typename Derived, typename OtherDerived,
+ bool MightHaveTransposeAliasing
+ = ei_check_transpose_aliasing_compile_time_selector
+ <ei_blas_traits<Derived>::IsTransposed,OtherDerived>::ret
+ >
+struct checkTransposeAliasing_impl
+{
+ static void run(const Derived& dst, const OtherDerived& other)
+ {
+ ei_assert((!ei_check_transpose_aliasing_run_time_selector
+ <typename Derived::Scalar,ei_blas_traits<Derived>::IsTransposed,OtherDerived>
+ ::run(ei_extract_data(dst), other))
+ && "aliasing detected during tranposition, use transposeInPlace() "
+ "or evaluate the rhs into a temporary using .eval()");
+
+ }
+};
+
+template<typename Derived, typename OtherDerived>
+struct checkTransposeAliasing_impl<Derived, OtherDerived, false>
+{
+ static void run(const Derived&, const OtherDerived&)
+ {
+ }
+};
+
+
template<typename Derived>
template<typename OtherDerived>
void DenseBase<Derived>::checkTransposeAliasing(const OtherDerived& other) const
{
- ei_assert((!ei_check_transpose_aliasing_selector<Scalar,ei_blas_traits<Derived>::IsTransposed,OtherDerived>::run(ei_extract_data(derived()), other))
- && "aliasing detected during tranposition, use transposeInPlace() or evaluate the rhs into a temporary using .eval()");
+ checkTransposeAliasing_impl<Derived, OtherDerived>::run(derived(), other);
}
#endif