diff --git a/gnu/local.mk b/gnu/local.mk index c87af5a17b..636919550c 100644 --- a/gnu/local.mk +++ b/gnu/local.mk @@ -609,6 +609,7 @@ dist_patch_DATA = \ %D%/packages/patches/dtc-format-modifier.patch \ %D%/packages/patches/dtc-32-bits-check.patch \ %D%/packages/patches/dvd+rw-tools-add-include.patch \ + %D%/packages/patches/eigen-arm-neon-fixes.patch \ %D%/packages/patches/elfutils-tests-ptrace.patch \ %D%/packages/patches/elixir-disable-failing-tests.patch \ %D%/packages/patches/einstein-build.patch \ diff --git a/gnu/packages/algebra.scm b/gnu/packages/algebra.scm index a7336066ef..7e26e76f4a 100644 --- a/gnu/packages/algebra.scm +++ b/gnu/packages/algebra.scm @@ -7,6 +7,7 @@ ;;; Copyright © 2017 Efraim Flashner ;;; Copyright © 2017 Tobias Geerinckx-Rice ;;; Copyright © 2017 Marius Bakke +;;; Copyright © 2017 Eric Bavier ;;; ;;; This file is part of GNU Guix. ;;; @@ -577,27 +578,34 @@ cosine/ sine transforms or DCT/DST).") (define-public eigen (package (name "eigen") - (version "3.2.9") + (version "3.3.4") (source (origin (method url-fetch) (uri (string-append "https://bitbucket.org/eigen/eigen/get/" version ".tar.bz2")) (sha256 (base32 - "1zs5b210mq7nyanky07li6456rrd0xv2nxf6sl2lhkzdq5p067jd")) + "19m4406jvqnwh7kpcvx1lfx2vdc5zwia5q9ayv89bimg1gmln9fx")) (file-name (string-append name "-" version ".tar.bz2")) + (patches (search-patches "eigen-arm-neon-fixes.patch")) (modules '((guix build utils))) (snippet ;; There are 3 test failures in the "unsupported" directory, ;; but maintainers say it's a known issue and it's unsupported ;; anyway, so just skip them. - '(substitute* "CMakeLists.txt" - (("add_subdirectory\\(unsupported\\)") - "# Do not build the tests for unsupported features.\n") - ;; Work around - ;; . - (("\"include/eigen3\"") - "\"${CMAKE_INSTALL_PREFIX}/include/eigen3\""))))) + '(begin + (substitute* "CMakeLists.txt" + (("add_subdirectory\\(unsupported\\)") + "# Do not build the tests for unsupported features.\n") + ;; Work around + ;; . + (("\"include/eigen3\"") + "\"${CMAKE_INSTALL_PREFIX}/include/eigen3\"")) + (substitute* "test/bdcsvd.cpp" + ;; See + ;; https://bitbucket.org/eigen/eigen/commits/ea8c22ce6920e982d15245ee41d0531a46a28e5d + ((".*svd_preallocate[^\n]*" &) + (string-append "//" & " // Not supported by BDCSVD"))))))) (build-system cmake-build-system) (arguments '(;; Turn off debugging symbols to save space. @@ -608,6 +616,7 @@ cosine/ sine transforms or DCT/DST).") (lambda _ (let* ((cores (parallel-job-count)) (dash-j (format #f "-j~a" cores))) + (setenv "EIGEN_SEED" "1") ;for reproducibility ;; First build the tests, in parallel. See ;; . (and (zero? (system* "make" "buildtests" dash-j)) diff --git a/gnu/packages/patches/eigen-arm-neon-fixes.patch b/gnu/packages/patches/eigen-arm-neon-fixes.patch new file mode 100644 index 0000000000..0838f30463 --- /dev/null +++ b/gnu/packages/patches/eigen-arm-neon-fixes.patch @@ -0,0 +1,245 @@ +# HG changeset patch +# User Gael Guennebaud +# Date 1497514590 -7200 +# Node ID d781c1de98342c5ca29c2fe719d8d3c96a35dcd4 +# Parent 48cd83b2b459aa9f3f5dca135d38760fe0b02a2f +Bug 1436: fix compilation of Jacobi rotations with ARM NEON, some specializations of internal::conj_helper were missing. + +diff --git a/Eigen/Core b/Eigen/Core +--- a/Eigen/Core ++++ b/Eigen/Core +@@ -371,6 +371,7 @@ + #include "src/Core/MathFunctions.h" + #include "src/Core/GenericPacketMath.h" + #include "src/Core/MathFunctionsImpl.h" ++#include "src/Core/arch/Default/ConjHelper.h" + + #if defined EIGEN_VECTORIZE_AVX512 + #include "src/Core/arch/SSE/PacketMath.h" +diff --git a/Eigen/src/Core/arch/AVX/Complex.h b/Eigen/src/Core/arch/AVX/Complex.h +--- a/Eigen/src/Core/arch/AVX/Complex.h ++++ b/Eigen/src/Core/arch/AVX/Complex.h +@@ -204,23 +204,7 @@ + } + }; + +-template<> struct conj_helper +-{ +- EIGEN_STRONG_INLINE Packet4cf pmadd(const Packet8f& x, const Packet4cf& y, const Packet4cf& c) const +- { return padd(c, pmul(x,y)); } +- +- EIGEN_STRONG_INLINE Packet4cf pmul(const Packet8f& x, const Packet4cf& y) const +- { return Packet4cf(Eigen::internal::pmul(x, y.v)); } +-}; +- +-template<> struct conj_helper +-{ +- EIGEN_STRONG_INLINE Packet4cf pmadd(const Packet4cf& x, const Packet8f& y, const Packet4cf& c) const +- { return padd(c, pmul(x,y)); } +- +- EIGEN_STRONG_INLINE Packet4cf pmul(const Packet4cf& x, const Packet8f& y) const +- { return Packet4cf(Eigen::internal::pmul(x.v, y)); } +-}; ++EIGEN_MAKE_CONJ_HELPER_CPLX_REAL(Packet4cf,Packet8f) + + template<> EIGEN_STRONG_INLINE Packet4cf pdiv(const Packet4cf& a, const Packet4cf& b) + { +@@ -400,23 +384,7 @@ + } + }; + +-template<> struct conj_helper +-{ +- EIGEN_STRONG_INLINE Packet2cd pmadd(const Packet4d& x, const Packet2cd& y, const Packet2cd& c) const +- { return padd(c, pmul(x,y)); } +- +- EIGEN_STRONG_INLINE Packet2cd pmul(const Packet4d& x, const Packet2cd& y) const +- { return Packet2cd(Eigen::internal::pmul(x, y.v)); } +-}; +- +-template<> struct conj_helper +-{ +- EIGEN_STRONG_INLINE Packet2cd pmadd(const Packet2cd& x, const Packet4d& y, const Packet2cd& c) const +- { return padd(c, pmul(x,y)); } +- +- EIGEN_STRONG_INLINE Packet2cd pmul(const Packet2cd& x, const Packet4d& y) const +- { return Packet2cd(Eigen::internal::pmul(x.v, y)); } +-}; ++EIGEN_MAKE_CONJ_HELPER_CPLX_REAL(Packet2cd,Packet4d) + + template<> EIGEN_STRONG_INLINE Packet2cd pdiv(const Packet2cd& a, const Packet2cd& b) + { +diff --git a/Eigen/src/Core/arch/AltiVec/Complex.h b/Eigen/src/Core/arch/AltiVec/Complex.h +--- a/Eigen/src/Core/arch/AltiVec/Complex.h ++++ b/Eigen/src/Core/arch/AltiVec/Complex.h +@@ -224,23 +224,7 @@ + } + }; + +-template<> struct conj_helper +-{ +- EIGEN_STRONG_INLINE Packet2cf pmadd(const Packet4f& x, const Packet2cf& y, const Packet2cf& c) const +- { return padd(c, pmul(x,y)); } +- +- EIGEN_STRONG_INLINE Packet2cf pmul(const Packet4f& x, const Packet2cf& y) const +- { return Packet2cf(internal::pmul(x, y.v)); } +-}; +- +-template<> struct conj_helper +-{ +- EIGEN_STRONG_INLINE Packet2cf pmadd(const Packet2cf& x, const Packet4f& y, const Packet2cf& c) const +- { return padd(c, pmul(x,y)); } +- +- EIGEN_STRONG_INLINE Packet2cf pmul(const Packet2cf& x, const Packet4f& y) const +- { return Packet2cf(internal::pmul(x.v, y)); } +-}; ++EIGEN_MAKE_CONJ_HELPER_CPLX_REAL(Packet2cf,Packet4f) + + template<> EIGEN_STRONG_INLINE Packet2cf pdiv(const Packet2cf& a, const Packet2cf& b) + { +@@ -416,23 +400,8 @@ + return pconj(internal::pmul(a, b)); + } + }; +-template<> struct conj_helper +-{ +- EIGEN_STRONG_INLINE Packet1cd pmadd(const Packet2d& x, const Packet1cd& y, const Packet1cd& c) const +- { return padd(c, pmul(x,y)); } + +- EIGEN_STRONG_INLINE Packet1cd pmul(const Packet2d& x, const Packet1cd& y) const +- { return Packet1cd(internal::pmul(x, y.v)); } +-}; +- +-template<> struct conj_helper +-{ +- EIGEN_STRONG_INLINE Packet1cd pmadd(const Packet1cd& x, const Packet2d& y, const Packet1cd& c) const +- { return padd(c, pmul(x,y)); } +- +- EIGEN_STRONG_INLINE Packet1cd pmul(const Packet1cd& x, const Packet2d& y) const +- { return Packet1cd(internal::pmul(x.v, y)); } +-}; ++EIGEN_MAKE_CONJ_HELPER_CPLX_REAL(Packet1cd,Packet2d) + + template<> EIGEN_STRONG_INLINE Packet1cd pdiv(const Packet1cd& a, const Packet1cd& b) + { +diff --git a/Eigen/src/Core/arch/Default/ConjHelper.h b/Eigen/src/Core/arch/Default/ConjHelper.h +new file mode 100644 +--- /dev/null ++++ b/Eigen/src/Core/arch/Default/ConjHelper.h +@@ -0,0 +1,29 @@ ++ ++// This file is part of Eigen, a lightweight C++ template library ++// for linear algebra. ++// ++// Copyright (C) 2017 Gael Guennebaud ++// ++// This Source Code Form is subject to the terms of the Mozilla ++// Public License v. 2.0. If a copy of the MPL was not distributed ++// with this file, You can obtain one at http://mozilla.org/MPL/2.0/. ++ ++#ifndef EIGEN_ARCH_CONJ_HELPER_H ++#define EIGEN_ARCH_CONJ_HELPER_H ++ ++#define EIGEN_MAKE_CONJ_HELPER_CPLX_REAL(PACKET_CPLX, PACKET_REAL) \ ++ template<> struct conj_helper { \ ++ EIGEN_STRONG_INLINE PACKET_CPLX pmadd(const PACKET_REAL& x, const PACKET_CPLX& y, const PACKET_CPLX& c) const \ ++ { return padd(c, pmul(x,y)); } \ ++ EIGEN_STRONG_INLINE PACKET_CPLX pmul(const PACKET_REAL& x, const PACKET_CPLX& y) const \ ++ { return PACKET_CPLX(Eigen::internal::pmul(x, y.v)); } \ ++ }; \ ++ \ ++ template<> struct conj_helper { \ ++ EIGEN_STRONG_INLINE PACKET_CPLX pmadd(const PACKET_CPLX& x, const PACKET_REAL& y, const PACKET_CPLX& c) const \ ++ { return padd(c, pmul(x,y)); } \ ++ EIGEN_STRONG_INLINE PACKET_CPLX pmul(const PACKET_CPLX& x, const PACKET_REAL& y) const \ ++ { return PACKET_CPLX(Eigen::internal::pmul(x.v, y)); } \ ++ }; ++ ++#endif // EIGEN_ARCH_CONJ_HELPER_H +diff --git a/Eigen/src/Core/arch/NEON/Complex.h b/Eigen/src/Core/arch/NEON/Complex.h +--- a/Eigen/src/Core/arch/NEON/Complex.h ++++ b/Eigen/src/Core/arch/NEON/Complex.h +@@ -265,6 +265,8 @@ + } + }; + ++EIGEN_MAKE_CONJ_HELPER_CPLX_REAL(Packet2cf,Packet4f) ++ + template<> EIGEN_STRONG_INLINE Packet2cf pdiv(const Packet2cf& a, const Packet2cf& b) + { + // TODO optimize it for NEON +@@ -456,6 +458,8 @@ + } + }; + ++EIGEN_MAKE_CONJ_HELPER_CPLX_REAL(Packet1cd,Packet2d) ++ + template<> EIGEN_STRONG_INLINE Packet1cd pdiv(const Packet1cd& a, const Packet1cd& b) + { + // TODO optimize it for NEON +diff --git a/Eigen/src/Core/arch/SSE/Complex.h b/Eigen/src/Core/arch/SSE/Complex.h +--- a/Eigen/src/Core/arch/SSE/Complex.h ++++ b/Eigen/src/Core/arch/SSE/Complex.h +@@ -229,23 +229,7 @@ + } + }; + +-template<> struct conj_helper +-{ +- EIGEN_STRONG_INLINE Packet2cf pmadd(const Packet4f& x, const Packet2cf& y, const Packet2cf& c) const +- { return padd(c, pmul(x,y)); } +- +- EIGEN_STRONG_INLINE Packet2cf pmul(const Packet4f& x, const Packet2cf& y) const +- { return Packet2cf(Eigen::internal::pmul(x, y.v)); } +-}; +- +-template<> struct conj_helper +-{ +- EIGEN_STRONG_INLINE Packet2cf pmadd(const Packet2cf& x, const Packet4f& y, const Packet2cf& c) const +- { return padd(c, pmul(x,y)); } +- +- EIGEN_STRONG_INLINE Packet2cf pmul(const Packet2cf& x, const Packet4f& y) const +- { return Packet2cf(Eigen::internal::pmul(x.v, y)); } +-}; ++EIGEN_MAKE_CONJ_HELPER_CPLX_REAL(Packet2cf,Packet4f) + + template<> EIGEN_STRONG_INLINE Packet2cf pdiv(const Packet2cf& a, const Packet2cf& b) + { +@@ -430,23 +414,7 @@ + } + }; + +-template<> struct conj_helper +-{ +- EIGEN_STRONG_INLINE Packet1cd pmadd(const Packet2d& x, const Packet1cd& y, const Packet1cd& c) const +- { return padd(c, pmul(x,y)); } +- +- EIGEN_STRONG_INLINE Packet1cd pmul(const Packet2d& x, const Packet1cd& y) const +- { return Packet1cd(Eigen::internal::pmul(x, y.v)); } +-}; +- +-template<> struct conj_helper +-{ +- EIGEN_STRONG_INLINE Packet1cd pmadd(const Packet1cd& x, const Packet2d& y, const Packet1cd& c) const +- { return padd(c, pmul(x,y)); } +- +- EIGEN_STRONG_INLINE Packet1cd pmul(const Packet1cd& x, const Packet2d& y) const +- { return Packet1cd(Eigen::internal::pmul(x.v, y)); } +-}; ++EIGEN_MAKE_CONJ_HELPER_CPLX_REAL(Packet1cd,Packet2d) + + template<> EIGEN_STRONG_INLINE Packet1cd pdiv(const Packet1cd& a, const Packet1cd& b) + { +diff --git a/Eigen/src/Core/arch/ZVector/Complex.h b/Eigen/src/Core/arch/ZVector/Complex.h +--- a/Eigen/src/Core/arch/ZVector/Complex.h ++++ b/Eigen/src/Core/arch/ZVector/Complex.h +@@ -336,6 +336,9 @@ + } + }; + ++EIGEN_MAKE_CONJ_HELPER_CPLX_REAL(Packet2cf,Packet4f) ++EIGEN_MAKE_CONJ_HELPER_CPLX_REAL(Packet1cd,Packet2d) ++ + template<> EIGEN_STRONG_INLINE Packet1cd pdiv(const Packet1cd& a, const Packet1cd& b) + { + // TODO optimize it for AltiVec