The attached example either crashes or gives me the "unaligned assert" when I use /arch:AVX. I'm using 3.3.1. See https://bitbucket.org/bjornpiltz/eigen_msvc_avx_test/.
Created attachment 771 [details] Compile with /arch:AVX
I cannot reproduce, but here is my guess: MSVC is not good at aligning the stack, so fix your Ray ctor from: Ray(const Mat34 P_, const Vec2& p_) to Ray(const Mat34& P_, const Vec2& p_)
Oh, I missed that. It doesn't help though. I'm using MSVC Community 2015 Update 3 Here's the call stack: > AVX_TEST.exe!Eigen::internal::pstore<double,__m256d>(double * to, const __m256d & from) Line 251 C++ AVX_TEST.exe!Eigen::internal::pstoret<double,__m256d,32>(double * to, const __m256d & from) Line 475 C++ AVX_TEST.exe!Eigen::internal::assign_op<double,double>::assignPacket<32,__m256d>(double * a, const __m256d & b) Line 28 C++ AVX_TEST.exe!Eigen::internal::generic_dense_assignment_kernel<Eigen::internal::evaluator<Eigen::Matrix<double,3,4,0,3,4> >,Eigen::internal::evaluator<Eigen::Matrix<double,3,4,0,3,4> >,Eigen::internal::assign_op<double,double>,0>::assignPacket<32,32,__m256d>(__int64 row, __int64 col) Line 653 C++ AVX_TEST.exe!Eigen::internal::generic_dense_assignment_kernel<Eigen::internal::evaluator<Eigen::Matrix<double,3,4,0,3,4> >,Eigen::internal::evaluator<Eigen::Matrix<double,3,4,0,3,4> >,Eigen::internal::assign_op<double,double>,0>::assignPacketByOuterInner<32,32,__m256d>(__int64 outer, __int64 inner) Line 667 C++ AVX_TEST.exe!Eigen::internal::copy_using_evaluator_innervec_CompleteUnrolling<Eigen::internal::generic_dense_assignment_kernel<Eigen::internal::evaluator<Eigen::Matrix<double,3,4,0,3,4> >,Eigen::internal::evaluator<Eigen::Matrix<double,3,4,0,3,4> >,Eigen::internal::assign_op<double,double>,0>,0,12>::run(Eigen::internal::generic_dense_assignment_kernel<Eigen::internal::evaluator<Eigen::Matrix<double,3,4,0,3,4> >,Eigen::internal::evaluator<Eigen::Matrix<double,3,4,0,3,4> >,Eigen::internal::assign_op<double,double>,0> & kernel) Line 276 C++ AVX_TEST.exe!Eigen::internal::dense_assignment_loop<Eigen::internal::generic_dense_assignment_kernel<Eigen::internal::evaluator<Eigen::Matrix<double,3,4,0,3,4> >,Eigen::internal::evaluator<Eigen::Matrix<double,3,4,0,3,4> >,Eigen::internal::assign_op<double,double>,0>,3,2>::run(Eigen::internal::generic_dense_assignment_kernel<Eigen::internal::evaluator<Eigen::Matrix<double,3,4,0,3,4> >,Eigen::internal::evaluator<Eigen::Matrix<double,3,4,0,3,4> >,Eigen::internal::assign_op<double,double>,0> & kernel) Line 435 C++ AVX_TEST.exe!Eigen::internal::call_dense_assignment_loop<Eigen::Matrix<double,3,4,0,3,4>,Eigen::Matrix<double,3,4,0,3,4>,Eigen::internal::assign_op<double,double> >(Eigen::Matrix<double,3,4,0,3,4> & dst, const Eigen::Matrix<double,3,4,0,3,4> & src, const Eigen::internal::assign_op<double,double> & func) Line 724 C++ AVX_TEST.exe!Eigen::internal::Assignment<Eigen::Matrix<double,3,4,0,3,4>,Eigen::Matrix<double,3,4,0,3,4>,Eigen::internal::assign_op<double,double>,Eigen::internal::Dense2Dense,void>::run(Eigen::Matrix<double,3,4,0,3,4> & dst, const Eigen::Matrix<double,3,4,0,3,4> & src, const Eigen::internal::assign_op<double,double> & func) Line 863 C++ AVX_TEST.exe!Eigen::internal::call_assignment_no_alias<Eigen::Matrix<double,3,4,0,3,4>,Eigen::Matrix<double,3,4,0,3,4>,Eigen::internal::assign_op<double,double> >(Eigen::Matrix<double,3,4,0,3,4> & dst, const Eigen::Matrix<double,3,4,0,3,4> & src, const Eigen::internal::assign_op<double,double> & func) Line 820 C++ AVX_TEST.exe!Eigen::PlainObjectBase<Eigen::Matrix<double,3,4,0,3,4> >::_set_noalias<Eigen::Matrix<double,3,4,0,3,4> >(const Eigen::DenseBase<Eigen::Matrix<double,3,4,0,3,4> > & other) Line 722 C++ AVX_TEST.exe!Eigen::Matrix<double,3,4,0,3,4>::Matrix<double,3,4,0,3,4>(Eigen::Matrix<double,3,4,0,3,4> && other) Line 278 C++ [External Code] AVX_TEST.exe!main(int argc, char * * argv) Line 47 C++
You must also use: std::vector<Ray, Eigen::aligned_allocator<Ray> > (you should actually also use Eigen::aligned_allocator when compiling for SSE, even though it is not necessary on most 64bit systems).
Thanks, that does it! Then the documentation for "An alternative - specializing std::vector for Eigen types" is wrong: #include<Eigen/StdVector> /* ... */ EIGEN_DEFINE_STL_VECTOR_SPECIALIZATION(Matrix2d) std::vector<Eigen::Vector2d>
Or actually it seems <StdVector> needs to be fixed: #if EIGEN_COMP_MSVC && EIGEN_OS_WIN64 /* MSVC auto aligns in 64 bit builds */ #define EIGEN_DEFINE_STL_VECTOR_SPECIALIZATION(...)
I see, so we should remove EIGEN_OS_WIN64 if EIGEN_MAX_STATIC_ALIGN_BYTES>16
I think the only safe case to not apply the EIGEN_DEFINE_STL_VECTOR_SPECIALIZATION fix is: #if EIGEN_COMP_MSVC && EIGEN_OS_WIN64 && EIGEN_MAX_STATIC_ALIGN_BYTES==16 but don't take my word for it!
Let me know if the following truly work. If so I'll backport it. https://bitbucket.org/eigen/eigen/commits/5430cad55312/ Summary: Bug 1389: MSVC's std containers do not properly align in 64 bits mode if the requested alignment is larger than 16 bytes (e.g., with AVX)
Yeah, that works.
btw, in C++11 the prototype of std::vector::resize as been fixed, and it must now be: void resize( size_type count, const value_type& value ); instead of void resize( size_type count, const value_type value ); in c++98/03. But according to msdn: https://msdn.microsoft.com/en-us/library/9xd04bzs.aspx#vector__resize even with MSVC 2015, std::vector::resize still follows the broken C++98/03 standard. Could someone confirm this from the MSVC's header of vector?
backport: https://bitbucket.org/eigen/eigen/commits/29f0625a5c72/
The MSDN documentation seems to be wrong. "C:\Program Files (x86)\Microsoft Visual Studio 14.0\VC\include\vector" has the right signature.
ok, thank you.
-- GitLab Migration Automatic Message -- This bug has been migrated to gitlab.com's GitLab instance and has been closed from further activity. You can subscribe and participate further through the new bug through this link to our GitLab instance: https://gitlab.com/libeigen/eigen/issues/1389.