New user self-registration is currently disabled. Please email eigen-core-team @ lists.tuxfamily.org if you need an account.
Bug 1328 - 3.3-rc1 doesn't compile on gcc 4.2.1 (apple)
3.3-rc1 doesn't compile on gcc 4.2.1 (apple)
Status: RESOLVED FIXED
Product: Eigen
Classification: Unclassified
Component: Core - general
3.3 (current stable)
x86 - 64-bit Mac OS
: Normal Compilation Problem
Assigned To: Nobody
:
Depends on:
Blocks: 3.3
  Show dependency treegraph
 
Reported: 2016-10-17 09:14 UTC by eugvas
Modified: 2016-11-03 08:07 UTC (History)
2 users (show)



Attachments

Description eugvas 2016-10-17 09:14:00 UTC
my program that used Eigen 3.2.x happily with gcc 4.2.1 doesn't compile with the newer version; here are the error messages that I get (also appear when building unit tests):
Eigen/src/Core/util/XprHelper.h:194: error: expected primary-expression before ‘bool’
Eigen/src/Core/util/XprHelper.h:194: error: expected ‘>’ before ‘bool’
Eigen/src/Core/util/XprHelper.h:210: error: template argument 4 is invalid
Eigen/src/Core/util/XprHelper.h:223: error: template argument 4 is invalid

Eigen/src/Core/util/Meta.h:392: error: no matching function for call to ‘Eigen::internal::scalar_identity_op<double>::operator()() const’
Eigen/src/Core/util/Meta.h: In instantiation of ‘Eigen::internal::has_unary_operator<Eigen::internal::scalar_identity_op<double>, long int>’

If C++11 is a requirement now, this needs to be stated explicitly in the docs?
Comment 1 Christoph Hertzberg 2016-10-17 09:35:33 UTC
We still support C++98/C++03, but older compilers usually have some deficits in supporting the standard.
We only claim to support gcc 4.4 and newer now:
http://eigen.tuxfamily.org/index.php?title=Main_Page&oldid=2003#Compiler_support

Note that gcc 4.2.1 was released more than 9 years ago and the 4.2 series is not maintained since 2008:
https://gcc.gnu.org/gcc-4.2/
Comment 2 eugvas 2016-10-17 09:44:09 UTC
ok, sorry, I must have overlooked this.
yeah, it's old but is the default compiler for my macos, c'est la vie!
Comment 3 Gael Guennebaud 2016-10-17 15:55:25 UTC
For the record, the offending code is:

template<int ArrayBytes, int AlignmentBytes,
         bool Match     =  bool((ArrayBytes%AlignmentBytes)==0),
         bool TryHalf   =  bool(AlignmentBytes>EIGEN_MIN_ALIGN_BYTES) >
struct compute_default_alignment_helper;

It seems that the comparison operator is miss-interpreted as the termination of the template declaration. If changing it to:

bool(EIGEN_MIN_ALIGN_BYTES<AlignmentBytes)

is all you need to make 4.2 happy, then let's do it!
Comment 4 eugvas 2016-10-19 13:30:14 UTC
thanks, that helped to get rid of that problem, but there is another one remaining.
in Eigen/src/Core/util/Meta.h, lines 392, 401 and 410, a handful of errors like this:
error: no matching function for call to 'Eigen::internal::linspaced_op<int, long long int __vector__, false>::operator()() const'
Eigen/src/Core/util/Meta.h: In instantiation of 'Eigen::internal::has_binary_operator<Eigen::internal::scalar_constant_op<int>, long int>':Eigen/src/Core/functors/NullaryFunctors.h:163:   instantiated from 'Eigen::internal::functor_has_linear_access<Eigen::internal::scalar_constant_op<int> >'
Eigen/src/Core/CoreEvaluators.h:461:   instantiated from ...

I don't see what exactly it complains about, but if it is similarly easy to fix, that would be great.
Comment 5 Gael Guennebaud 2016-10-20 17:15:47 UTC
ah, here we go. I expected such trouble some issues. All old compilers complain about this part, including MSVC 2010 and ICC 11. Making this piece of code compatible with all version of MSVC >= 2012, gcc >= 4.4 and clang has been extremely tedious.  Making those old compilers truly happy might just be impossible. Since this is affecting several old compilers, a workaround, would be to specialize those structures for our internal nullary functors (there are only 3). Of course, users of such compilers would not be able to benefits from the automatic detection of operator() (), (i), and (i,j) for custom nullary functors, but that's acceptable I guess.
Comment 6 Gael Guennebaud 2016-10-25 14:56:57 UTC
I've pushed a workaround for old compilers: https://bitbucket.org/eigen/eigen/commits/153266fe2b36

Let us known if that works for you as well.
Comment 7 eugvas 2016-10-25 17:26:49 UTC
Wow, now it does take **ages** to compile! (10 minutes for a single source file on my machine!)
The compilation itself proceeds without errors, but then the linker complains:
ld: duplicate symbol double __vector Eigen::internal::pinsertlast<double __vector>(double __vector const&, Eigen::internal::unpacket_traits<double __vector>::type)in obj/math_linalg.o and obj/math_fit.o

and this is fairly strange because this is a template function for which the instantiations in different object files are supposed to be coalesced together by the linker...
Comment 8 Gael Guennebaud 2016-10-25 18:23:19 UTC
I fixed the missing inline keywords.

Regarding the 10mn of compilation, I guess you are running out of memory and that your system is swapping.
Comment 9 eugvas 2016-10-25 20:01:41 UTC
That almost worked; I had to make similar changes in Core/arch/SSE/PacketMath.h and then all went fine. Thanks! You're right, 2Gb of memory is clearly not enough for the compiler to chew these intricate constructs...
On a different machine icc 13.0 wasn't complaining about duplicate symbols, although it ranted about "warning #2536: type qualifiers are meaningless here" in src/Core/ProductEvaluators.h lines 570,571,1305. And also the BDCSVD suffers from a larger floating-point errors (~1e-10 for a 500x500 matrix) when compiled with intel; I think we already discussed its too aggressive optimization strategy a few month ago (it wasn't even finishing the computation at all back then!)
Comment 10 Gael Guennebaud 2016-10-25 20:22:10 UTC
What's missing in Core/arch/SSE/PacketMath.h? All pinsertlast functions are now declared inline.

Regarding the warnings, I fixed the first two, but there is no line 1305 in ProductEvaluators.h.

For ICC and lack of accuracy, yes, you need to disable some unsafe math optimizations. Perhaps it could be possible to temporarily disable them in Eigen using pragamas??? If you manage to do so, then please send us a patch!

At least, this needs to be documented.

I see you are using BDCSVD! That piece of code is indeed highly demanding on the compiler as it instantiates a very large part of Eigen.
Comment 11 eugvas 2016-10-25 22:02:59 UTC
> What's missing in Core/arch/SSE/PacketMath.h? All pinsertlast functions are now declared inline.

ah! sorry, it was already there in the patch, I just did not scroll down the entire screen!:)

line 1305 was in src/Core/CoreEvaluators.h, sorry for confusion.

Yes, compiling with -fp-model precise restores the accuracy, but may negatively impact the performance elsewhere.
I tried to add #pragma float_control(precise,on)  before the BDCSVD class is instantiated, or at the beginning of BDCSVD::compute, but that had no effect.
Comment 12 Gael Guennebaud 2016-11-02 10:52:06 UTC
I've also played with #pragma float_control but it has to be put in your .cpp file. So there is no solution on Eigen's side.

Note You need to log in before you can comment on or make changes to this bug.