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

Several Questions and feature requests

Tags: None
(comma "," separated)
renorm
Registered Member
Posts
31
Karma
0
I did some reading of Eigen's source code recently. It is nice to see quality linear algebra code being written in C++ and not in FORTRAN :)

And here are my questions.

Does Eignen use platform/cache specific tuning like Atlas?

Is there a way to use different allocators with dynamic size matrices? I want to use cache aligned allocation, but couldn't figure out how to do it.

What is the easiest way to switch from 16 byte alignment to 128 byte alignment? From what I see, dynamic size matrices delegate allocation to free functions. Could it be better to templatize memory allocation and delegate it to allocators instead of free functions? Just my thoughts,

Regards,
renorm.
User avatar
ggael
Moderator
Posts
3447
Karma
19
OS
renorm wrote:I did some reading of Eigen's source code recently. It is nice to see quality linear algebra code being written in C++ and not in FORTRAN :)

And here are my questions.

Does Eignen use platform/cache specific tuning like Atlas?


yes, block sizes are computed automatically in function of various parameters:
- size of the scalar type
- sizes of the register level blocks (depends on the number of available registers, on the size of the packets, etc.)
- sizes of the L1 and L2/L3 caches which are queried at runtime using the cpuid instruction on compatible CPU

But you can also control yourself the cache size values using:

setCpuCacheSizes(l1,l2)

Is there a way to use different allocators with dynamic size matrices? I want to use cache aligned allocation, but couldn't figure out how to do it.


there is no easy way, yet.

What is the easiest way to switch from 16 byte alignment to 128 byte alignment? From what I see, dynamic size matrices delegate allocation to free functions. Could it be better to templatize memory allocation and delegate it to allocators instead of free functions? Just my thoughts,


This has been suggested a couple of times, and I think that would be a nice feature to have. Feel free to add an entry in our tracker: http://eigen.tuxfamily.org/bz/.
renorm
Registered Member
Posts
31
Karma
0
Thanks ggael.

Another nice feature (or tiny redesign) to have would be non-reallocating resize/assignment when the capacity doesn't increase, similar to std::vector. According to the manual, shrinking resize causes memory reallocation. Reallocation is expensive and causes free store fragmentation.

With non-reallocating resize reallocation cost would be amortized or avoided all together when the upper bound on capacity is known. If needed, users could prune the excess capacity using swap trick.

My current project requires many very large matrices to be created and destroyed in sequential order. I can't use Eigen, because of free store fragmentation and reallocation cost. Maybe there a way to avoid reallocation using views? I couldn't find the answer in the manual. In my case, the upper on capacity is known. With non-reallocating resize I could simply resize and recycle the same matrix many times over.
User avatar
ggael
Moderator
Posts
3447
Karma
19
OS
Hi,

this one is more intrusive but it seems to me that allowing custom allocators would solve the problem, since this mechanism could be easily implemented at the level of the allocator, right?

Now if many users are interested by such a feature we could add a "capacity" member variable and a lazyResize(rows,cols) function without changing the current behavior.

Also not that if your matrices are small, you can already do static allocation with dynamic sizes using the MaxRows, MaxCols template parameters...
renorm
Registered Member
Posts
31
Karma
0
Resizing should be handled by the matrix class itself. Allocators can't know when to relocate or to recycle the storage. But templatzing memory management with allocator is a good idea on its own. It would solve alignment problem very nicely and let the users to use custom allocators. Some STL implementation would still be broken (copying into stack breaks alignment), but hopefully it is going to be fixed in the next standard.

Templatzing allocators could be harder to implement, but changing resize behavior should be easy. I can do it on my own platform, but I don't have much knowledge about other platforms and my code won't be portable.

Amortizing with excess capacity is not really needed, but recycling the storage when the capacity doesn't increase is good. I am for making it the default behavior. This can improve resize/assignment performance tremendously (under certain circumstances) without breaking legacy code.

Also not that if your matrices are small, you can already do static allocation with dynamic sizes using the MaxRows, MaxCols template parameters...
This is very interesting. It can be what I needed, at least until non-reallocating resize is implemented :) How it works? If I set both MaxRows and MaxCols at compile time, static size array is used instead of dynamically allocated storage? What happens if I specify either MaxRows or MaxCols, but not both?

My matrices are big, but I could still allocate matrices with MaxRows, MaxCols on free store. All I need is to avoid reallocation.
renorm
Registered Member
Posts
31
Karma
0
P.S. Now I have to set _Options template parameter (is it used as a bit flags?), because it precedes _MaxRows and _MaxCols. I know that the the default is 0 (=RowMajor|AutoAlign ?), but how to do it properly? What is the value for (ColMajor|AutoAlign)?
I tried to read the source code, but the typedefs are defined with macros. It will take some time before I can figure out all of them.
User avatar
ggael
Moderator
Posts
3447
Karma
19
OS
Amortizing with excess capacity is not really needed, but recycling the storage when the capacity doesn't increase is good. I am for making it the default behavior. This can improve resize/assignment performance tremendously (under certain circumstances) without breaking legacy code.


Some care about avoiding reallocation while other care about small memory usage... so there is no good default behavior. I think adding a "lazyResize" function would be a good and explicit compromise.


P.S. Now I have to set _Options template parameter (is it used as a bit flags?), because it precedes _MaxRows and _MaxCols. I know that the the default is 0 (=RowMajor|AutoAlign ?), but how to do it properly? What is the value for (ColMajor|AutoAlign)?
I tried to read the source code, but the typedefs are defined with macros. It will take some time before I can figure out all of them.


The default is 0 = ColMajor|AutoAlign, not RowMajor. So just use 0 or ColMajor|AutoAlign !
renorm
Registered Member
Posts
31
Karma
0
After reading the source code for some time I decided to contribute to the project non-trivial amount of my time. I want to tackle lazy resizing, templatizing memory allocation and cache alignment first. All these issues are related and it makes sense to deal with them simultaneously. Later, once I make myself familiar with implementation details, I want to contribute QR and SVD implementations optimized for multithreading.

But before anything else, I need to learn Eigen's inner workings. I hope it is OK if I post many itty bitty questions on this forum and save the mailing list for serious questions only. I will post my questions in a single thread titled something like "Novice developer workshop: Implementing Eignen".
User avatar
ggael
Moderator
Posts
3447
Karma
19
OS
ok, great!

Before starting any work, please open a new bug on our issue tracker (http://eigen.tuxfamily.org/bz/) for each feature, and let's have the specific discussions there.

For short questions you can also join us on our IRC channel (#eigen on irc.freenode.net).

thank you!
renorm
Registered Member
Posts
31
Karma
0
That sounds good. Thanks.


Bookmarks



Who is online

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