This forum has been archived. All content is frozen. Please use KDE Discuss instead.

[Help]The following code failed

Tags: None
(comma "," separated)
lastsnow
Registered Member
Posts
4
Karma
0

[Help]The following code failed

Wed Oct 14, 2009 3:42 pm
I'm using Eigen 2.0.6 with sse2 . The compiler is icc 10.1 for windows.
There is an exception throwed:
Access violation reading location 0xcdcdcdd1
when D* dd = new D;
So what's wrong with the code below?
Code: Select all
typedef Eigen::Transform<float,3> transform_t;
using namespace Eigen;
struct C{
   EIGEN_MAKE_ALIGNED_OPERATOR_NEW

   char a;
   transform_t b;
};
struct D{
   EIGEN_MAKE_ALIGNED_OPERATOR_NEW
   C x;
   char c;
};
void test(){
   C* cc = new C;
   cc->b.setIdentity();
   
   D* dd = new D;
   dd->x.b.setIdentity();
   cc->b = dd->x.b;
   delete dd;
   delete cc;
}



Last edited by lastsnow on Wed Oct 14, 2009 3:56 pm, edited 1 time in total.
User avatar
bjacob
Registered Member
Posts
658
Karma
3

Re: [Help]The following code failed

Wed Oct 14, 2009 3:51 pm
I can't reproduce your issue, i even checked that all objects are created at aligned locations. Please provide a readily compilable program and specify your compiler version. Please also paste a full back-trace.


Join us on Eigen's IRC channel: #eigen on irc.freenode.net
Have a serious interest in Eigen? Then join the mailing list!
User avatar
ggael
Moderator
Posts
3447
Karma
19
OS

Re: [Help]The following code failed

Wed Oct 14, 2009 3:57 pm
your code looks ok, and since here I cannot reproduce your issue we'll need more information: Can you run your test under a debugger and post a complete backtrace ? and/or if you are running linux try to run it with valgrind. What happens if you disable SSE, or if you try with a different compiler ?
lastsnow
Registered Member
Posts
4
Karma
0

Re: [Help]The following code failed

Wed Oct 14, 2009 5:00 pm
Thanks for your reply.
I just tried gcc 4.4 under linux.It seems ok.
The code will have problem when using intel compiler(10.1.013 ) under windows.It's weired that I cannot always reproduce the problem(memory not aligned ?).
I will try it under different circumtance to find out what's going on.
I will capture more data if I encounter this problem again.
lastsnow
Registered Member
Posts
4
Karma
0

Re: [Help]The following code failed

Wed Oct 14, 2009 5:18 pm
BTW, this is really inconvenient for struct D to use the macro EIGEN_MAKE_ALIGNED_OPERATOR_NEW, if other class or struct wrap a D member,the macro must write there.This intrusive way makes me uncomfortable.

What about do something like this in matrixstorage.h, I have tried it.
But the cost is obvious: extra 16 bytes storage.
Code: Select all
template <typename T, int Size, int MatrixOptions,
bool Align = (MatrixOptions&AutoAlign) && (((Size*sizeof(T))&0xf)==0)
> struct ei_matrix_array
{
   EIGEN_ALIGN_128 T data[Size]; //make extra room for it
   char x[16];
template<typename U> inline U* align_up(U* p, size_t a) {return (U*)(((size_t)p + (a-1)) & -(int)a);}
   ei_matrix_array()
   {
      x[15] = (char)align_up(data,0x10)- (char)data;
#ifndef EIGEN_DISABLE_UNALIGNED_ARRAY_ASSERT
      ei_assert((reinterpret_cast<size_t>(array()) & 0xf) == 0
         && "this assertion is explained here: http://eigen.tuxfamily.org/dox/UnalignedArrayAssert.html  **** READ THIS WEB PAGE !!! ****");
#endif
   }

   ei_matrix_array(ei_constructor_without_unaligned_array_assert) {
      x[15] = (char)align_up(data,0x10)- (char)data;
   }
   T* array(){return (T*)((size_t)data+(size_t)x[15]);}
   const T* array()const{return (T*)((size_t)data+(size_t)x[15]);}
};


User avatar
bjacob
Registered Member
Posts
658
Karma
3

Re: [Help]The following code failed

Wed Oct 14, 2009 5:37 pm
But the cost is obvious: extra 16 bytes storage.

And also a runtime computation. Two good reasons why we can't do that.

If you don't like that you can:
- disable vectorization/alignment (define EIGEN_DONT_ALIGN)
or
- wait for the next C++ standard which finally provides good alignment support.


Join us on Eigen's IRC channel: #eigen on irc.freenode.net
Have a serious interest in Eigen? Then join the mailing list!
lastsnow
Registered Member
Posts
4
Karma
0

Re: [Help]The following code failed

Fri Oct 16, 2009 12:05 pm
Is the alignment enabled by default ?

vs2005 compile the following code without define EIGEN_DONT_ALIGN

std::vector<transform_t> v;

will generate this error:

error C2719: '_Val': formal parameter with __declspec(align('16')) won't be aligned

I think no alignment should be the default option.
User avatar
bjacob
Registered Member
Posts
658
Karma
3

Re: [Help]The following code failed

Fri Oct 16, 2009 12:09 pm
On VS 2005, we don't vectorize. So alignment is useless indeed. But, if we want to preserve ABI compatibility, we still need to align. If you are sure that VS 2005 doesn't have the same C++ ABI as VS 2008 anyway, then I'm OK to disable alignment on VS 2005.


Join us on Eigen's IRC channel: #eigen on irc.freenode.net
Have a serious interest in Eigen? Then join the mailing list!
vernal
Registered Member
Posts
37
Karma
0

Re: [Help]The following code failed

Wed Oct 13, 2010 1:33 pm
I assume patching the vector file of the STL is considered to have side-effects and should be avoided?
It solved the Compile error error "C2719: '_Val': formal parameter with __declspec(align('16')) won't be aligned" for me but I don't feel good with that solution.

Orignial vector (VS2010)
Code: Select all
void resize(size_type _Newsize, _Ty _Val)

Modification
Code: Select all
void resize(size_type _Newsize, const _Ty & _Val)


Do I break lots of things with that? xD

I use latest Eigen 2.x with the Eigen STL allocators.
Inspiration came from that thread:
http://ompf.org/forum/viewtopic.php?f=11&t=686
There is also source code for an aligned vector, but somehow I'd rather use the STL. Or should I switch to Qvector of Qt?
Hauke
Registered Member
Posts
109
Karma
3
OS

Re: [Help]The following code failed

Sat Oct 16, 2010 8:20 am
We have corrected these STL issues and provide classes

Eigen/StdDeque
Eigen/StdList
Eigen/StdVector

- Hauke
vernal
Registered Member
Posts
37
Karma
0

Re: [Help]The following code failed

Mon Oct 18, 2010 2:31 pm
Thank you very much. I removed all the hand-written calls of the Eigen allocator and included the Eigen::StdVector.
The only remaining problem is now an error when I try to push_back() an Eigen::MatrixXd into a std::vector:

Code: Select all
error C2664: 'void std::std_vector<_Ty,_Ax>::push_back(_Ty &&)' : cannot convert parameter 1 from 'Eigen::MatrixXd' to 'Eigen::ei_workaround_msvc_std_vector<T> &&'


Is the error on my side here? Am I using it wrongly or is it a side-effect?
Using MSVC10 on WinXP.
Hauke
Registered Member
Posts
109
Karma
3
OS

Re: [Help]The following code failed

Mon Oct 18, 2010 3:06 pm
Could you please provide a self-contained example?

I am unable to reproduce the error. Besides that, std::vector should not be specialized for MatrixXd. It does not required special handling since it is not stack but heap aligned.

You seem to trigger the rvalue reference push_back method, i.e. you must call something like this
Code: Select all
v.push_back( MatrixXd() );

but even here, I fail to reproduce the problem.

Regards,
Hauke
vernal
Registered Member
Posts
37
Karma
0

Re: [Help]The following code failed

Tue Oct 19, 2010 9:52 am
Thank you for your answer. Here is a short example that triggers the error.

Code: Select all
#include <Eigen/StdVector>
#include <Eigen/Core>

#define COMPILETIMESIZE 4

int main()
{
   std::vector<Eigen::Matrix<double, COMPILETIMESIZE, 1> > collection; //create collection
   collection.reserve(200);   //avoid repeated resizing of vector
   Eigen::MatrixXd collElement = Eigen::Matrix<double, COMPILETIMESIZE, 1>::Zero();  //init with zeroes
   for (size_t m = 0;m < 200;++m)
   {
      //assign some values to the element
      collElement(0) = 1.0;
      collElement(1) = 2.0;
      collElement(2) = 3.0;
      collElement(3) = 4.0;
      //push it
      collection.push_back(collElement);
   }

   return 0;
};


Besides that, std::vector should not be specialized for MatrixXd.

If I understand correctly that means that I should not use Eigen::StdVector at all for MatrixXd? But why did I get compile errors about something not being aligned then? The error pointed me to the Eigen documentation site and that was why I started to use the aligned allocator in the first place.
Hauke
Registered Member
Posts
109
Karma
3
OS

Re: [Help]The following code failed

Tue Oct 19, 2010 10:06 am
Let me start by answering your last question. You got the error, because the std::vector is storing stack matrices (vectors) and these are stack aligned. They are allocated on the stack since they are declared as fixed size types.
Code: Select all
typedef Eigen::Matrix<double, COMPILETIMESIZE, 1> VectorType;

In the loop on the other hand side, you are pushing MatrixXd and not VectorType. This causes the MatrixXd to be converted into VectorType and in turn it causes a call to the rvalue push_back method. Not a problem at all, if your std::vector were correctly declared or specialized.

When you want to use our special implementation of std::vector, you either need to specialize by putting the following convenience macro in your code (assuming you have the typedef as above)
Code: Select all
EIGEN_DEFINE_STL_VECTOR_SPECIALIZATION( VectorType );

or, you need to specify the std::vector as
Code: Select all
std::vector<VectorType, Eigen::aligned_allocator<VectorType> > collection;

In any case, we need to make sure to use our special aligned_allocator.

Besides the falsely declared std::vector you have a useless conversion in your code which you can improve by this code
Code: Select all
VectorType collElement = VectorType::Zero();

Regards,
Hauke
vernal
Registered Member
Posts
37
Karma
0

Re: [Help]The following code failed

Tue Oct 19, 2010 10:42 am
Thank you very much!
I was assuming that a MatrixXd is the same as a hand-declared Matrix<...>. But I think I was confused because in another part of the code I have MatrixXd with sizes known only at runtime. That's also why I have that useless conversion in my code. But I'm seeing clearer now 8)

I can't find EIGEN_DEFINE_STL_VECTOR_SPECIALIZATION anywhere in the Eigen2 source. I think I have to use Eigen3 for that? And is Eigen3 stable enough to do the change now? (I don't use very advanced features of Eigen so far).

Regards,
vernal


Bookmarks



Who is online

Registered users: Bing [Bot], Evergrowing, Google [Bot], rockscient