mirror of
https://bitbucket.org/librepilot/librepilot.git
synced 2024-12-02 10:24:11 +01:00
OP-191: Merge from full-calibration branch. Import Eigen 2.0.15 to the GCS. Add the bits that eclipse missed the first time around.
git-svn-id: svn://svn.openpilot.org/OpenPilot/trunk@3052 ebee16cc-31ac-478f-84a7-5cbb03baadba
This commit is contained in:
parent
bf191fed27
commit
e40f6752bd
@ -0,0 +1,9 @@
|
|||||||
|
ADD_SUBDIRECTORY(Core)
|
||||||
|
ADD_SUBDIRECTORY(LU)
|
||||||
|
ADD_SUBDIRECTORY(QR)
|
||||||
|
ADD_SUBDIRECTORY(SVD)
|
||||||
|
ADD_SUBDIRECTORY(Cholesky)
|
||||||
|
ADD_SUBDIRECTORY(Array)
|
||||||
|
ADD_SUBDIRECTORY(Geometry)
|
||||||
|
ADD_SUBDIRECTORY(LeastSquares)
|
||||||
|
ADD_SUBDIRECTORY(Sparse)
|
@ -0,0 +1,2 @@
|
|||||||
|
ADD_SUBDIRECTORY(SSE)
|
||||||
|
ADD_SUBDIRECTORY(AltiVec)
|
@ -0,0 +1,6 @@
|
|||||||
|
FILE(GLOB Eigen_Core_util_SRCS "*.h")
|
||||||
|
|
||||||
|
INSTALL(FILES
|
||||||
|
${Eigen_Core_util_SRCS}
|
||||||
|
DESTINATION ${INCLUDE_INSTALL_DIR}/Eigen/src/Core/util
|
||||||
|
)
|
@ -0,0 +1,254 @@
|
|||||||
|
// This file is part of Eigen, a lightweight C++ template library
|
||||||
|
// for linear algebra. Eigen itself is part of the KDE project.
|
||||||
|
//
|
||||||
|
// Copyright (C) 2008 Gael Guennebaud <g.gael@free.fr>
|
||||||
|
// Copyright (C) 2006-2008 Benoit Jacob <jacob.benoit.1@gmail.com>
|
||||||
|
//
|
||||||
|
// Eigen is free software; you can redistribute it and/or
|
||||||
|
// modify it under the terms of the GNU Lesser General Public
|
||||||
|
// License as published by the Free Software Foundation; either
|
||||||
|
// version 3 of the License, or (at your option) any later version.
|
||||||
|
//
|
||||||
|
// Alternatively, you can redistribute it and/or
|
||||||
|
// modify it under the terms of the GNU General Public License as
|
||||||
|
// published by the Free Software Foundation; either version 2 of
|
||||||
|
// the License, or (at your option) any later version.
|
||||||
|
//
|
||||||
|
// Eigen is distributed in the hope that it will be useful, but WITHOUT ANY
|
||||||
|
// WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
|
||||||
|
// FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License or the
|
||||||
|
// GNU General Public License for more details.
|
||||||
|
//
|
||||||
|
// You should have received a copy of the GNU Lesser General Public
|
||||||
|
// License and a copy of the GNU General Public License along with
|
||||||
|
// Eigen. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
|
#ifndef EIGEN_CONSTANTS_H
|
||||||
|
#define EIGEN_CONSTANTS_H
|
||||||
|
|
||||||
|
/** This value means that a quantity is not known at compile-time, and that instead the value is
|
||||||
|
* stored in some runtime variable.
|
||||||
|
*
|
||||||
|
* Explanation for the choice of this value:
|
||||||
|
* - It should be positive and larger than any reasonable compile-time-fixed number of rows or columns.
|
||||||
|
* This allows to simplify many compile-time conditions throughout Eigen.
|
||||||
|
* - It should be smaller than the sqrt of INT_MAX. Indeed, we often multiply a number of rows with a number
|
||||||
|
* of columns in order to compute a number of coefficients. Even if we guard that with an "if" checking whether
|
||||||
|
* the values are Dynamic, we still get a compiler warning "integer overflow". So the only way to get around
|
||||||
|
* it would be a meta-selector. Doing this everywhere would reduce code readability and lenghten compilation times.
|
||||||
|
* Also, disabling compiler warnings for integer overflow, sounds like a bad idea.
|
||||||
|
*
|
||||||
|
* If you wish to port Eigen to a platform where sizeof(int)==2, it is perfectly possible to set Dynamic to, say, 100.
|
||||||
|
*/
|
||||||
|
const int Dynamic = 10000;
|
||||||
|
|
||||||
|
/** This value means +Infinity; it is currently used only as the p parameter to MatrixBase::lpNorm<int>().
|
||||||
|
* The value Infinity there means the L-infinity norm.
|
||||||
|
*/
|
||||||
|
const int Infinity = -1;
|
||||||
|
|
||||||
|
/** \defgroup flags flags
|
||||||
|
* \ingroup Core_Module
|
||||||
|
*
|
||||||
|
* These are the possible bits which can be OR'ed to constitute the flags of a matrix or
|
||||||
|
* expression.
|
||||||
|
*
|
||||||
|
* It is important to note that these flags are a purely compile-time notion. They are a compile-time property of
|
||||||
|
* an expression type, implemented as enum's. They are not stored in memory at runtime, and they do not incur any
|
||||||
|
* runtime overhead.
|
||||||
|
*
|
||||||
|
* \sa MatrixBase::Flags
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** \ingroup flags
|
||||||
|
*
|
||||||
|
* for a matrix, this means that the storage order is row-major.
|
||||||
|
* If this bit is not set, the storage order is column-major.
|
||||||
|
* For an expression, this determines the storage order of
|
||||||
|
* the matrix created by evaluation of that expression. */
|
||||||
|
const unsigned int RowMajorBit = 0x1;
|
||||||
|
|
||||||
|
/** \ingroup flags
|
||||||
|
*
|
||||||
|
* means the expression should be evaluated by the calling expression */
|
||||||
|
const unsigned int EvalBeforeNestingBit = 0x2;
|
||||||
|
|
||||||
|
/** \ingroup flags
|
||||||
|
*
|
||||||
|
* means the expression should be evaluated before any assignement */
|
||||||
|
const unsigned int EvalBeforeAssigningBit = 0x4;
|
||||||
|
|
||||||
|
/** \ingroup flags
|
||||||
|
*
|
||||||
|
* Short version: means the expression might be vectorized
|
||||||
|
*
|
||||||
|
* Long version: means that the coefficients can be handled by packets
|
||||||
|
* and start at a memory location whose alignment meets the requirements
|
||||||
|
* of the present CPU architecture for optimized packet access. In the fixed-size
|
||||||
|
* case, there is the additional condition that the total size of the coefficients
|
||||||
|
* array is a multiple of the packet size, so that it is possible to access all the
|
||||||
|
* coefficients by packets. In the dynamic-size case, there is no such condition
|
||||||
|
* on the total size, so it might not be possible to access the few last coeffs
|
||||||
|
* by packets.
|
||||||
|
*
|
||||||
|
* \note This bit can be set regardless of whether vectorization is actually enabled.
|
||||||
|
* To check for actual vectorizability, see \a ActualPacketAccessBit.
|
||||||
|
*/
|
||||||
|
const unsigned int PacketAccessBit = 0x8;
|
||||||
|
|
||||||
|
#ifdef EIGEN_VECTORIZE
|
||||||
|
/** \ingroup flags
|
||||||
|
*
|
||||||
|
* If vectorization is enabled (EIGEN_VECTORIZE is defined) this constant
|
||||||
|
* is set to the value \a PacketAccessBit.
|
||||||
|
*
|
||||||
|
* If vectorization is not enabled (EIGEN_VECTORIZE is not defined) this constant
|
||||||
|
* is set to the value 0.
|
||||||
|
*/
|
||||||
|
const unsigned int ActualPacketAccessBit = PacketAccessBit;
|
||||||
|
#else
|
||||||
|
const unsigned int ActualPacketAccessBit = 0x0;
|
||||||
|
#endif
|
||||||
|
|
||||||
|
/** \ingroup flags
|
||||||
|
*
|
||||||
|
* Short version: means the expression can be seen as 1D vector.
|
||||||
|
*
|
||||||
|
* Long version: means that one can access the coefficients
|
||||||
|
* of this expression by coeff(int), and coeffRef(int) in the case of a lvalue expression. These
|
||||||
|
* index-based access methods are guaranteed
|
||||||
|
* to not have to do any runtime computation of a (row, col)-pair from the index, so that it
|
||||||
|
* is guaranteed that whenever it is available, index-based access is at least as fast as
|
||||||
|
* (row,col)-based access. Expressions for which that isn't possible don't have the LinearAccessBit.
|
||||||
|
*
|
||||||
|
* If both PacketAccessBit and LinearAccessBit are set, then the
|
||||||
|
* packets of this expression can be accessed by packet(int), and writePacket(int) in the case of a
|
||||||
|
* lvalue expression.
|
||||||
|
*
|
||||||
|
* Typically, all vector expressions have the LinearAccessBit, but there is one exception:
|
||||||
|
* Product expressions don't have it, because it would be troublesome for vectorization, even when the
|
||||||
|
* Product is a vector expression. Thus, vector Product expressions allow index-based coefficient access but
|
||||||
|
* not index-based packet access, so they don't have the LinearAccessBit.
|
||||||
|
*/
|
||||||
|
const unsigned int LinearAccessBit = 0x10;
|
||||||
|
|
||||||
|
/** \ingroup flags
|
||||||
|
*
|
||||||
|
* Means that the underlying array of coefficients can be directly accessed. This means two things.
|
||||||
|
* First, references to the coefficients must be available through coeffRef(int, int). This rules out read-only
|
||||||
|
* expressions whose coefficients are computed on demand by coeff(int, int). Second, the memory layout of the
|
||||||
|
* array of coefficients must be exactly the natural one suggested by rows(), cols(), stride(), and the RowMajorBit.
|
||||||
|
* This rules out expressions such as DiagonalCoeffs, whose coefficients, though referencable, do not have
|
||||||
|
* such a regular memory layout.
|
||||||
|
*/
|
||||||
|
const unsigned int DirectAccessBit = 0x20;
|
||||||
|
|
||||||
|
/** \ingroup flags
|
||||||
|
*
|
||||||
|
* means the first coefficient packet is guaranteed to be aligned */
|
||||||
|
const unsigned int AlignedBit = 0x40;
|
||||||
|
|
||||||
|
/** \ingroup flags
|
||||||
|
*
|
||||||
|
* means all diagonal coefficients are equal to 0 */
|
||||||
|
const unsigned int ZeroDiagBit = 0x80;
|
||||||
|
|
||||||
|
/** \ingroup flags
|
||||||
|
*
|
||||||
|
* means all diagonal coefficients are equal to 1 */
|
||||||
|
const unsigned int UnitDiagBit = 0x100;
|
||||||
|
|
||||||
|
/** \ingroup flags
|
||||||
|
*
|
||||||
|
* means the matrix is selfadjoint (M=M*). */
|
||||||
|
const unsigned int SelfAdjointBit = 0x200;
|
||||||
|
|
||||||
|
/** \ingroup flags
|
||||||
|
*
|
||||||
|
* means the strictly lower triangular part is 0 */
|
||||||
|
const unsigned int UpperTriangularBit = 0x400;
|
||||||
|
|
||||||
|
/** \ingroup flags
|
||||||
|
*
|
||||||
|
* means the strictly upper triangular part is 0 */
|
||||||
|
const unsigned int LowerTriangularBit = 0x800;
|
||||||
|
|
||||||
|
/** \ingroup flags
|
||||||
|
*
|
||||||
|
* means the expression includes sparse matrices and the sparse path has to be taken. */
|
||||||
|
const unsigned int SparseBit = 0x1000;
|
||||||
|
|
||||||
|
// list of flags that are inherited by default
|
||||||
|
const unsigned int HereditaryBits = RowMajorBit
|
||||||
|
| EvalBeforeNestingBit
|
||||||
|
| EvalBeforeAssigningBit
|
||||||
|
| SparseBit;
|
||||||
|
|
||||||
|
// Possible values for the Mode parameter of part() and of extract()
|
||||||
|
const unsigned int UpperTriangular = UpperTriangularBit;
|
||||||
|
const unsigned int StrictlyUpperTriangular = UpperTriangularBit | ZeroDiagBit;
|
||||||
|
const unsigned int LowerTriangular = LowerTriangularBit;
|
||||||
|
const unsigned int StrictlyLowerTriangular = LowerTriangularBit | ZeroDiagBit;
|
||||||
|
const unsigned int SelfAdjoint = SelfAdjointBit;
|
||||||
|
|
||||||
|
// additional possible values for the Mode parameter of extract()
|
||||||
|
const unsigned int UnitUpperTriangular = UpperTriangularBit | UnitDiagBit;
|
||||||
|
const unsigned int UnitLowerTriangular = LowerTriangularBit | UnitDiagBit;
|
||||||
|
const unsigned int Diagonal = UpperTriangular | LowerTriangular;
|
||||||
|
|
||||||
|
enum { Aligned, Unaligned };
|
||||||
|
enum { ForceAligned, AsRequested };
|
||||||
|
enum { ConditionalJumpCost = 5 };
|
||||||
|
enum CornerType { TopLeft, TopRight, BottomLeft, BottomRight };
|
||||||
|
enum DirectionType { Vertical, Horizontal };
|
||||||
|
enum ProductEvaluationMode { NormalProduct, CacheFriendlyProduct, DiagonalProduct, SparseTimeSparseProduct, SparseTimeDenseProduct, DenseTimeSparseProduct };
|
||||||
|
|
||||||
|
enum {
|
||||||
|
/** \internal Equivalent to a slice vectorization for fixed-size matrices having good alignment
|
||||||
|
* and good size */
|
||||||
|
InnerVectorization,
|
||||||
|
/** \internal Vectorization path using a single loop plus scalar loops for the
|
||||||
|
* unaligned boundaries */
|
||||||
|
LinearVectorization,
|
||||||
|
/** \internal Generic vectorization path using one vectorized loop per row/column with some
|
||||||
|
* scalar loops to handle the unaligned boundaries */
|
||||||
|
SliceVectorization,
|
||||||
|
NoVectorization
|
||||||
|
};
|
||||||
|
|
||||||
|
enum {
|
||||||
|
NoUnrolling,
|
||||||
|
InnerUnrolling,
|
||||||
|
CompleteUnrolling
|
||||||
|
};
|
||||||
|
|
||||||
|
enum {
|
||||||
|
ColMajor = 0,
|
||||||
|
RowMajor = 0x1, // it is only a coincidence that this is equal to RowMajorBit -- don't rely on that
|
||||||
|
/** \internal Don't require alignment for the matrix itself (the array of coefficients, if dynamically allocated, may still be
|
||||||
|
requested to be aligned) */
|
||||||
|
DontAlign = 0,
|
||||||
|
/** \internal Align the matrix itself if it is vectorizable fixed-size */
|
||||||
|
AutoAlign = 0x2
|
||||||
|
};
|
||||||
|
|
||||||
|
enum {
|
||||||
|
IsDense = 0,
|
||||||
|
IsSparse = SparseBit,
|
||||||
|
NoDirectAccess = 0,
|
||||||
|
HasDirectAccess = DirectAccessBit
|
||||||
|
};
|
||||||
|
|
||||||
|
const int EiArch_Generic = 0x0;
|
||||||
|
const int EiArch_SSE = 0x1;
|
||||||
|
const int EiArch_AltiVec = 0x2;
|
||||||
|
|
||||||
|
#if defined EIGEN_VECTORIZE_SSE
|
||||||
|
const int EiArch = EiArch_SSE;
|
||||||
|
#elif defined EIGEN_VECTORIZE_ALTIVEC
|
||||||
|
const int EiArch = EiArch_AltiVec;
|
||||||
|
#else
|
||||||
|
const int EiArch = EiArch_Generic;
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#endif // EIGEN_CONSTANTS_H
|
@ -0,0 +1,5 @@
|
|||||||
|
|
||||||
|
#ifdef _MSC_VER
|
||||||
|
#pragma warning( push )
|
||||||
|
#pragma warning( disable : 4181 4244 4127 4211 4717 )
|
||||||
|
#endif
|
@ -0,0 +1,4 @@
|
|||||||
|
|
||||||
|
#ifdef _MSC_VER
|
||||||
|
#pragma warning( pop )
|
||||||
|
#endif
|
@ -0,0 +1,125 @@
|
|||||||
|
// This file is part of Eigen, a lightweight C++ template library
|
||||||
|
// for linear algebra. Eigen itself is part of the KDE project.
|
||||||
|
//
|
||||||
|
// Copyright (C) 2006-2008 Benoit Jacob <jacob.benoit.1@gmail.com>
|
||||||
|
//
|
||||||
|
// Eigen is free software; you can redistribute it and/or
|
||||||
|
// modify it under the terms of the GNU Lesser General Public
|
||||||
|
// License as published by the Free Software Foundation; either
|
||||||
|
// version 3 of the License, or (at your option) any later version.
|
||||||
|
//
|
||||||
|
// Alternatively, you can redistribute it and/or
|
||||||
|
// modify it under the terms of the GNU General Public License as
|
||||||
|
// published by the Free Software Foundation; either version 2 of
|
||||||
|
// the License, or (at your option) any later version.
|
||||||
|
//
|
||||||
|
// Eigen is distributed in the hope that it will be useful, but WITHOUT ANY
|
||||||
|
// WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
|
||||||
|
// FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License or the
|
||||||
|
// GNU General Public License for more details.
|
||||||
|
//
|
||||||
|
// You should have received a copy of the GNU Lesser General Public
|
||||||
|
// License and a copy of the GNU General Public License along with
|
||||||
|
// Eigen. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
|
#ifndef EIGEN_FORWARDDECLARATIONS_H
|
||||||
|
#define EIGEN_FORWARDDECLARATIONS_H
|
||||||
|
|
||||||
|
template<typename T> struct ei_traits;
|
||||||
|
template<typename T> struct NumTraits;
|
||||||
|
|
||||||
|
template<typename _Scalar, int _Rows, int _Cols,
|
||||||
|
int _Options = EIGEN_DEFAULT_MATRIX_STORAGE_ORDER_OPTION | AutoAlign,
|
||||||
|
int _MaxRows = _Rows, int _MaxCols = _Cols> class Matrix;
|
||||||
|
|
||||||
|
template<typename ExpressionType, unsigned int Added, unsigned int Removed> class Flagged;
|
||||||
|
template<typename ExpressionType> class NestByValue;
|
||||||
|
template<typename ExpressionType> class SwapWrapper;
|
||||||
|
template<typename MatrixType> class Minor;
|
||||||
|
template<typename MatrixType, int BlockRows=Dynamic, int BlockCols=Dynamic, int PacketAccess=AsRequested,
|
||||||
|
int _DirectAccessStatus = ei_traits<MatrixType>::Flags&DirectAccessBit ? DirectAccessBit
|
||||||
|
: ei_traits<MatrixType>::Flags&SparseBit> class Block;
|
||||||
|
template<typename MatrixType> class Transpose;
|
||||||
|
template<typename MatrixType> class Conjugate;
|
||||||
|
template<typename NullaryOp, typename MatrixType> class CwiseNullaryOp;
|
||||||
|
template<typename UnaryOp, typename MatrixType> class CwiseUnaryOp;
|
||||||
|
template<typename BinaryOp, typename Lhs, typename Rhs> class CwiseBinaryOp;
|
||||||
|
template<typename Lhs, typename Rhs, int ProductMode> class Product;
|
||||||
|
template<typename CoeffsVectorType> class DiagonalMatrix;
|
||||||
|
template<typename MatrixType> class DiagonalCoeffs;
|
||||||
|
template<typename MatrixType, int PacketAccess = AsRequested> class Map;
|
||||||
|
template<typename MatrixType, unsigned int Mode> class Part;
|
||||||
|
template<typename MatrixType, unsigned int Mode> class Extract;
|
||||||
|
template<typename ExpressionType> class Cwise;
|
||||||
|
template<typename ExpressionType> class WithFormat;
|
||||||
|
template<typename MatrixType> struct CommaInitializer;
|
||||||
|
|
||||||
|
|
||||||
|
template<typename Lhs, typename Rhs> struct ei_product_mode;
|
||||||
|
template<typename Lhs, typename Rhs, int ProductMode = ei_product_mode<Lhs,Rhs>::value> struct ProductReturnType;
|
||||||
|
|
||||||
|
template<typename Scalar> struct ei_scalar_sum_op;
|
||||||
|
template<typename Scalar> struct ei_scalar_difference_op;
|
||||||
|
template<typename Scalar> struct ei_scalar_product_op;
|
||||||
|
template<typename Scalar> struct ei_scalar_quotient_op;
|
||||||
|
template<typename Scalar> struct ei_scalar_opposite_op;
|
||||||
|
template<typename Scalar> struct ei_scalar_conjugate_op;
|
||||||
|
template<typename Scalar> struct ei_scalar_real_op;
|
||||||
|
template<typename Scalar> struct ei_scalar_imag_op;
|
||||||
|
template<typename Scalar> struct ei_scalar_abs_op;
|
||||||
|
template<typename Scalar> struct ei_scalar_abs2_op;
|
||||||
|
template<typename Scalar> struct ei_scalar_sqrt_op;
|
||||||
|
template<typename Scalar> struct ei_scalar_exp_op;
|
||||||
|
template<typename Scalar> struct ei_scalar_log_op;
|
||||||
|
template<typename Scalar> struct ei_scalar_cos_op;
|
||||||
|
template<typename Scalar> struct ei_scalar_sin_op;
|
||||||
|
template<typename Scalar> struct ei_scalar_pow_op;
|
||||||
|
template<typename Scalar> struct ei_scalar_inverse_op;
|
||||||
|
template<typename Scalar> struct ei_scalar_square_op;
|
||||||
|
template<typename Scalar> struct ei_scalar_cube_op;
|
||||||
|
template<typename Scalar, typename NewType> struct ei_scalar_cast_op;
|
||||||
|
template<typename Scalar> struct ei_scalar_multiple_op;
|
||||||
|
template<typename Scalar> struct ei_scalar_quotient1_op;
|
||||||
|
template<typename Scalar> struct ei_scalar_min_op;
|
||||||
|
template<typename Scalar> struct ei_scalar_max_op;
|
||||||
|
template<typename Scalar> struct ei_scalar_random_op;
|
||||||
|
template<typename Scalar> struct ei_scalar_add_op;
|
||||||
|
template<typename Scalar> struct ei_scalar_constant_op;
|
||||||
|
template<typename Scalar> struct ei_scalar_identity_op;
|
||||||
|
|
||||||
|
struct IOFormat;
|
||||||
|
|
||||||
|
template<typename Scalar>
|
||||||
|
void ei_cache_friendly_product(
|
||||||
|
int _rows, int _cols, int depth,
|
||||||
|
bool _lhsRowMajor, const Scalar* _lhs, int _lhsStride,
|
||||||
|
bool _rhsRowMajor, const Scalar* _rhs, int _rhsStride,
|
||||||
|
bool resRowMajor, Scalar* res, int resStride);
|
||||||
|
|
||||||
|
// Array module
|
||||||
|
template<typename ConditionMatrixType, typename ThenMatrixType, typename ElseMatrixType> class Select;
|
||||||
|
template<typename MatrixType, typename BinaryOp, int Direction> class PartialReduxExpr;
|
||||||
|
template<typename ExpressionType, int Direction> class PartialRedux;
|
||||||
|
|
||||||
|
template<typename MatrixType> class LU;
|
||||||
|
template<typename MatrixType> class QR;
|
||||||
|
template<typename MatrixType> class SVD;
|
||||||
|
template<typename MatrixType> class LLT;
|
||||||
|
template<typename MatrixType> class LDLT;
|
||||||
|
|
||||||
|
// Geometry module:
|
||||||
|
template<typename Derived, int _Dim> class RotationBase;
|
||||||
|
template<typename Lhs, typename Rhs> class Cross;
|
||||||
|
template<typename Scalar> class Quaternion;
|
||||||
|
template<typename Scalar> class Rotation2D;
|
||||||
|
template<typename Scalar> class AngleAxis;
|
||||||
|
template<typename Scalar,int Dim> class Transform;
|
||||||
|
template <typename _Scalar, int _AmbientDim> class ParametrizedLine;
|
||||||
|
template <typename _Scalar, int _AmbientDim> class Hyperplane;
|
||||||
|
template<typename Scalar,int Dim> class Translation;
|
||||||
|
template<typename Scalar,int Dim> class Scaling;
|
||||||
|
|
||||||
|
// Sparse module:
|
||||||
|
template<typename Lhs, typename Rhs, int ProductMode> class SparseProduct;
|
||||||
|
|
||||||
|
#endif // EIGEN_FORWARDDECLARATIONS_H
|
276
ground/openpilotgcs/src/libs/eigen/Eigen/src/Core/util/Macros.h
Normal file
276
ground/openpilotgcs/src/libs/eigen/Eigen/src/Core/util/Macros.h
Normal file
@ -0,0 +1,276 @@
|
|||||||
|
// This file is part of Eigen, a lightweight C++ template library
|
||||||
|
// for linear algebra. Eigen itself is part of the KDE project.
|
||||||
|
//
|
||||||
|
// Copyright (C) 2008 Gael Guennebaud <g.gael@free.fr>
|
||||||
|
// Copyright (C) 2006-2008 Benoit Jacob <jacob.benoit.1@gmail.com>
|
||||||
|
//
|
||||||
|
// Eigen is free software; you can redistribute it and/or
|
||||||
|
// modify it under the terms of the GNU Lesser General Public
|
||||||
|
// License as published by the Free Software Foundation; either
|
||||||
|
// version 3 of the License, or (at your option) any later version.
|
||||||
|
//
|
||||||
|
// Alternatively, you can redistribute it and/or
|
||||||
|
// modify it under the terms of the GNU General Public License as
|
||||||
|
// published by the Free Software Foundation; either version 2 of
|
||||||
|
// the License, or (at your option) any later version.
|
||||||
|
//
|
||||||
|
// Eigen is distributed in the hope that it will be useful, but WITHOUT ANY
|
||||||
|
// WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
|
||||||
|
// FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License or the
|
||||||
|
// GNU General Public License for more details.
|
||||||
|
//
|
||||||
|
// You should have received a copy of the GNU Lesser General Public
|
||||||
|
// License and a copy of the GNU General Public License along with
|
||||||
|
// Eigen. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
|
#ifndef EIGEN_MACROS_H
|
||||||
|
#define EIGEN_MACROS_H
|
||||||
|
|
||||||
|
#undef minor
|
||||||
|
|
||||||
|
#define EIGEN_WORLD_VERSION 2
|
||||||
|
#define EIGEN_MAJOR_VERSION 0
|
||||||
|
#define EIGEN_MINOR_VERSION 15
|
||||||
|
|
||||||
|
#define EIGEN_VERSION_AT_LEAST(x,y,z) (EIGEN_WORLD_VERSION>x || (EIGEN_WORLD_VERSION>=x && \
|
||||||
|
(EIGEN_MAJOR_VERSION>y || (EIGEN_MAJOR_VERSION>=y && \
|
||||||
|
EIGEN_MINOR_VERSION>=z))))
|
||||||
|
|
||||||
|
// 16 byte alignment is only useful for vectorization. Since it affects the ABI, we need to enable 16 byte alignment on all
|
||||||
|
// platforms where vectorization might be enabled. In theory we could always enable alignment, but it can be a cause of problems
|
||||||
|
// on some platforms, so we just disable it in certain common platform (compiler+architecture combinations) to avoid these problems.
|
||||||
|
#if defined(__GNUC__) && !(defined(__i386__) || defined(__x86_64__) || defined(__powerpc__) || defined(__ppc__) || defined(__ia64__))
|
||||||
|
#define EIGEN_GCC_AND_ARCH_DOESNT_WANT_ALIGNMENT 1
|
||||||
|
#else
|
||||||
|
#define EIGEN_GCC_AND_ARCH_DOESNT_WANT_ALIGNMENT 0
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if defined(__GNUC__) && (__GNUC__ <= 3)
|
||||||
|
#define EIGEN_GCC3_OR_OLDER 1
|
||||||
|
#else
|
||||||
|
#define EIGEN_GCC3_OR_OLDER 0
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// FIXME vectorization + alignment is completely disabled with sun studio
|
||||||
|
#if !EIGEN_GCC_AND_ARCH_DOESNT_WANT_ALIGNMENT && !EIGEN_GCC3_OR_OLDER && !defined(__SUNPRO_CC) && !defined(__QNXNTO__)
|
||||||
|
#define EIGEN_ARCH_WANTS_ALIGNMENT 1
|
||||||
|
#else
|
||||||
|
#define EIGEN_ARCH_WANTS_ALIGNMENT 0
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// EIGEN_ALIGN is the true test whether we want to align or not. It takes into account both the user choice to explicitly disable
|
||||||
|
// alignment (EIGEN_DONT_ALIGN) and the architecture config (EIGEN_ARCH_WANTS_ALIGNMENT). Henceforth, only EIGEN_ALIGN should be used.
|
||||||
|
#if EIGEN_ARCH_WANTS_ALIGNMENT && !defined(EIGEN_DONT_ALIGN)
|
||||||
|
#define EIGEN_ALIGN 1
|
||||||
|
#else
|
||||||
|
#define EIGEN_ALIGN 0
|
||||||
|
#ifdef EIGEN_VECTORIZE
|
||||||
|
#error "Vectorization enabled, but our platform checks say that we don't do 16 byte alignment on this platform. If you added vectorization for another architecture, you also need to edit this platform check."
|
||||||
|
#endif
|
||||||
|
#ifndef EIGEN_DISABLE_UNALIGNED_ARRAY_ASSERT
|
||||||
|
#define EIGEN_DISABLE_UNALIGNED_ARRAY_ASSERT
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifdef EIGEN_DEFAULT_TO_ROW_MAJOR
|
||||||
|
#define EIGEN_DEFAULT_MATRIX_STORAGE_ORDER_OPTION RowMajor
|
||||||
|
#else
|
||||||
|
#define EIGEN_DEFAULT_MATRIX_STORAGE_ORDER_OPTION ColMajor
|
||||||
|
#endif
|
||||||
|
|
||||||
|
/** \internal Defines the maximal loop size to enable meta unrolling of loops.
|
||||||
|
* Note that the value here is expressed in Eigen's own notion of "number of FLOPS",
|
||||||
|
* it does not correspond to the number of iterations or the number of instructions
|
||||||
|
*/
|
||||||
|
#ifndef EIGEN_UNROLLING_LIMIT
|
||||||
|
#define EIGEN_UNROLLING_LIMIT 100
|
||||||
|
#endif
|
||||||
|
|
||||||
|
/** \internal Define the maximal size in Bytes of blocks fitting in CPU cache.
|
||||||
|
* The current value is set to generate blocks of 256x256 for float
|
||||||
|
*
|
||||||
|
* Typically for a single-threaded application you would set that to 25% of the size of your CPU caches in bytes
|
||||||
|
*/
|
||||||
|
#ifndef EIGEN_TUNE_FOR_CPU_CACHE_SIZE
|
||||||
|
#define EIGEN_TUNE_FOR_CPU_CACHE_SIZE (sizeof(float)*256*256)
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// FIXME this should go away quickly
|
||||||
|
#ifdef EIGEN_TUNE_FOR_L2_CACHE_SIZE
|
||||||
|
#error EIGEN_TUNE_FOR_L2_CACHE_SIZE is now called EIGEN_TUNE_FOR_CPU_CACHE_SIZE.
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#define USING_PART_OF_NAMESPACE_EIGEN \
|
||||||
|
EIGEN_USING_MATRIX_TYPEDEFS \
|
||||||
|
using Eigen::Matrix; \
|
||||||
|
using Eigen::MatrixBase; \
|
||||||
|
using Eigen::ei_random; \
|
||||||
|
using Eigen::ei_real; \
|
||||||
|
using Eigen::ei_imag; \
|
||||||
|
using Eigen::ei_conj; \
|
||||||
|
using Eigen::ei_abs; \
|
||||||
|
using Eigen::ei_abs2; \
|
||||||
|
using Eigen::ei_sqrt; \
|
||||||
|
using Eigen::ei_exp; \
|
||||||
|
using Eigen::ei_log; \
|
||||||
|
using Eigen::ei_sin; \
|
||||||
|
using Eigen::ei_cos;
|
||||||
|
|
||||||
|
#ifdef NDEBUG
|
||||||
|
# ifndef EIGEN_NO_DEBUG
|
||||||
|
# define EIGEN_NO_DEBUG
|
||||||
|
# endif
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef ei_assert
|
||||||
|
#ifdef EIGEN_NO_DEBUG
|
||||||
|
#define ei_assert(x)
|
||||||
|
#else
|
||||||
|
#define ei_assert(x) assert(x)
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifdef EIGEN_INTERNAL_DEBUGGING
|
||||||
|
#define ei_internal_assert(x) ei_assert(x)
|
||||||
|
#else
|
||||||
|
#define ei_internal_assert(x)
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifdef EIGEN_NO_DEBUG
|
||||||
|
#define EIGEN_ONLY_USED_FOR_DEBUG(x) (void)x
|
||||||
|
#else
|
||||||
|
#define EIGEN_ONLY_USED_FOR_DEBUG(x)
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// EIGEN_ALWAYS_INLINE_ATTRIB should be use in the declaration of function
|
||||||
|
// which should be inlined even in debug mode.
|
||||||
|
// FIXME with the always_inline attribute,
|
||||||
|
// gcc 3.4.x reports the following compilation error:
|
||||||
|
// Eval.h:91: sorry, unimplemented: inlining failed in call to 'const Eigen::Eval<Derived> Eigen::MatrixBase<Scalar, Derived>::eval() const'
|
||||||
|
// : function body not available
|
||||||
|
#if EIGEN_GNUC_AT_LEAST(4,0)
|
||||||
|
#define EIGEN_ALWAYS_INLINE_ATTRIB __attribute__((always_inline))
|
||||||
|
#else
|
||||||
|
#define EIGEN_ALWAYS_INLINE_ATTRIB
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// EIGEN_FORCE_INLINE means "inline as much as possible"
|
||||||
|
#if (defined _MSC_VER)
|
||||||
|
#define EIGEN_STRONG_INLINE __forceinline
|
||||||
|
#else
|
||||||
|
#define EIGEN_STRONG_INLINE inline
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if (defined __GNUC__)
|
||||||
|
#define EIGEN_DONT_INLINE __attribute__((noinline))
|
||||||
|
#elif (defined _MSC_VER)
|
||||||
|
#define EIGEN_DONT_INLINE __declspec(noinline)
|
||||||
|
#else
|
||||||
|
#define EIGEN_DONT_INLINE
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if (defined __GNUC__)
|
||||||
|
#define EIGEN_DEPRECATED __attribute__((deprecated))
|
||||||
|
#elif (defined _MSC_VER)
|
||||||
|
#define EIGEN_DEPRECATED __declspec(deprecated)
|
||||||
|
#else
|
||||||
|
#define EIGEN_DEPRECATED
|
||||||
|
#endif
|
||||||
|
|
||||||
|
/* EIGEN_ALIGN_128 forces data to be 16-byte aligned, EVEN if vectorization (EIGEN_VECTORIZE) is disabled,
|
||||||
|
* so that vectorization doesn't affect binary compatibility.
|
||||||
|
*
|
||||||
|
* If we made alignment depend on whether or not EIGEN_VECTORIZE is defined, it would be impossible to link
|
||||||
|
* vectorized and non-vectorized code.
|
||||||
|
*/
|
||||||
|
#if !EIGEN_ALIGN
|
||||||
|
#define EIGEN_ALIGN_128
|
||||||
|
#elif (defined __GNUC__)
|
||||||
|
#define EIGEN_ALIGN_128 __attribute__((aligned(16)))
|
||||||
|
#elif (defined _MSC_VER)
|
||||||
|
#define EIGEN_ALIGN_128 __declspec(align(16))
|
||||||
|
#else
|
||||||
|
#error Please tell me what is the equivalent of __attribute__((aligned(16))) for your compiler
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifdef EIGEN_DONT_USE_RESTRICT_KEYWORD
|
||||||
|
#define EIGEN_RESTRICT
|
||||||
|
#endif
|
||||||
|
#ifndef EIGEN_RESTRICT
|
||||||
|
#define EIGEN_RESTRICT __restrict
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef EIGEN_STACK_ALLOCATION_LIMIT
|
||||||
|
#define EIGEN_STACK_ALLOCATION_LIMIT 1000000
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef EIGEN_DEFAULT_IO_FORMAT
|
||||||
|
#define EIGEN_DEFAULT_IO_FORMAT Eigen::IOFormat()
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// format used in Eigen's documentation
|
||||||
|
// needed to define it here as escaping characters in CMake add_definition's argument seems very problematic.
|
||||||
|
#define EIGEN_DOCS_IO_FORMAT IOFormat(3, AlignCols, " ", "\n", "", "")
|
||||||
|
|
||||||
|
#define EIGEN_INHERIT_ASSIGNMENT_OPERATOR(Derived, Op) \
|
||||||
|
template<typename OtherDerived> \
|
||||||
|
EIGEN_STRONG_INLINE Derived& operator Op(const Eigen::MatrixBase<OtherDerived>& other) \
|
||||||
|
{ \
|
||||||
|
return Base::operator Op(other.derived()); \
|
||||||
|
} \
|
||||||
|
EIGEN_STRONG_INLINE Derived& operator Op(const Derived& other) \
|
||||||
|
{ \
|
||||||
|
return Base::operator Op(other); \
|
||||||
|
}
|
||||||
|
|
||||||
|
#define EIGEN_INHERIT_SCALAR_ASSIGNMENT_OPERATOR(Derived, Op) \
|
||||||
|
template<typename Other> \
|
||||||
|
EIGEN_STRONG_INLINE Derived& operator Op(const Other& scalar) \
|
||||||
|
{ \
|
||||||
|
return Base::operator Op(scalar); \
|
||||||
|
}
|
||||||
|
|
||||||
|
#define EIGEN_INHERIT_ASSIGNMENT_OPERATORS(Derived) \
|
||||||
|
EIGEN_INHERIT_ASSIGNMENT_OPERATOR(Derived, =) \
|
||||||
|
EIGEN_INHERIT_ASSIGNMENT_OPERATOR(Derived, +=) \
|
||||||
|
EIGEN_INHERIT_ASSIGNMENT_OPERATOR(Derived, -=) \
|
||||||
|
EIGEN_INHERIT_SCALAR_ASSIGNMENT_OPERATOR(Derived, *=) \
|
||||||
|
EIGEN_INHERIT_SCALAR_ASSIGNMENT_OPERATOR(Derived, /=)
|
||||||
|
|
||||||
|
#define _EIGEN_GENERIC_PUBLIC_INTERFACE(Derived, BaseClass) \
|
||||||
|
typedef BaseClass Base; \
|
||||||
|
typedef typename Eigen::ei_traits<Derived>::Scalar Scalar; \
|
||||||
|
typedef typename Eigen::NumTraits<Scalar>::Real RealScalar; \
|
||||||
|
typedef typename Base::PacketScalar PacketScalar; \
|
||||||
|
typedef typename Eigen::ei_nested<Derived>::type Nested; \
|
||||||
|
enum { RowsAtCompileTime = Eigen::ei_traits<Derived>::RowsAtCompileTime, \
|
||||||
|
ColsAtCompileTime = Eigen::ei_traits<Derived>::ColsAtCompileTime, \
|
||||||
|
MaxRowsAtCompileTime = Eigen::ei_traits<Derived>::MaxRowsAtCompileTime, \
|
||||||
|
MaxColsAtCompileTime = Eigen::ei_traits<Derived>::MaxColsAtCompileTime, \
|
||||||
|
Flags = Eigen::ei_traits<Derived>::Flags, \
|
||||||
|
CoeffReadCost = Eigen::ei_traits<Derived>::CoeffReadCost, \
|
||||||
|
SizeAtCompileTime = Base::SizeAtCompileTime, \
|
||||||
|
MaxSizeAtCompileTime = Base::MaxSizeAtCompileTime, \
|
||||||
|
IsVectorAtCompileTime = Base::IsVectorAtCompileTime };
|
||||||
|
|
||||||
|
#define EIGEN_GENERIC_PUBLIC_INTERFACE(Derived) \
|
||||||
|
_EIGEN_GENERIC_PUBLIC_INTERFACE(Derived, Eigen::MatrixBase<Derived>)
|
||||||
|
|
||||||
|
#define EIGEN_ENUM_MIN(a,b) (((int)a <= (int)b) ? (int)a : (int)b)
|
||||||
|
#define EIGEN_SIZE_MIN(a,b) (((int)a == 1 || (int)b == 1) ? 1 \
|
||||||
|
: ((int)a == Dynamic || (int)b == Dynamic) ? Dynamic \
|
||||||
|
: ((int)a <= (int)b) ? (int)a : (int)b)
|
||||||
|
#define EIGEN_ENUM_MAX(a,b) (((int)a >= (int)b) ? (int)a : (int)b)
|
||||||
|
|
||||||
|
// just an empty macro !
|
||||||
|
#define EIGEN_EMPTY
|
||||||
|
|
||||||
|
// concatenate two tokens
|
||||||
|
#define EIGEN_CAT2(a,b) a ## b
|
||||||
|
#define EIGEN_CAT(a,b) EIGEN_CAT2(a,b)
|
||||||
|
|
||||||
|
// convert a token to a string
|
||||||
|
#define EIGEN_MAKESTRING2(a) #a
|
||||||
|
#define EIGEN_MAKESTRING(a) EIGEN_MAKESTRING2(a)
|
||||||
|
|
||||||
|
#endif // EIGEN_MACROS_H
|
417
ground/openpilotgcs/src/libs/eigen/Eigen/src/Core/util/Memory.h
Normal file
417
ground/openpilotgcs/src/libs/eigen/Eigen/src/Core/util/Memory.h
Normal file
@ -0,0 +1,417 @@
|
|||||||
|
// This file is part of Eigen, a lightweight C++ template library
|
||||||
|
// for linear algebra.
|
||||||
|
//
|
||||||
|
// Copyright (C) 2008 Gael Guennebaud <g.gael@free.fr>
|
||||||
|
// Copyright (C) 2008-2009 Benoit Jacob <jacob.benoit.1@gmail.com>
|
||||||
|
// Copyright (C) 2009 Kenneth Riddile <kfriddile@yahoo.com>
|
||||||
|
//
|
||||||
|
// Eigen is free software; you can redistribute it and/or
|
||||||
|
// modify it under the terms of the GNU Lesser General Public
|
||||||
|
// License as published by the Free Software Foundation; either
|
||||||
|
// version 3 of the License, or (at your option) any later version.
|
||||||
|
//
|
||||||
|
// Alternatively, you can redistribute it and/or
|
||||||
|
// modify it under the terms of the GNU General Public License as
|
||||||
|
// published by the Free Software Foundation; either version 2 of
|
||||||
|
// the License, or (at your option) any later version.
|
||||||
|
//
|
||||||
|
// Eigen is distributed in the hope that it will be useful, but WITHOUT ANY
|
||||||
|
// WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
|
||||||
|
// FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License or the
|
||||||
|
// GNU General Public License for more details.
|
||||||
|
//
|
||||||
|
// You should have received a copy of the GNU Lesser General Public
|
||||||
|
// License and a copy of the GNU General Public License along with
|
||||||
|
// Eigen. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
|
#ifndef EIGEN_MEMORY_H
|
||||||
|
#define EIGEN_MEMORY_H
|
||||||
|
|
||||||
|
// FreeBSD 6 seems to have 16-byte aligned malloc
|
||||||
|
// See http://svn.freebsd.org/viewvc/base/stable/6/lib/libc/stdlib/malloc.c?view=markup
|
||||||
|
// FreeBSD 7 seems to have 16-byte aligned malloc except on ARM and MIPS architectures
|
||||||
|
// See http://svn.freebsd.org/viewvc/base/stable/7/lib/libc/stdlib/malloc.c?view=markup
|
||||||
|
#if defined(__FreeBSD__) && !defined(__arm__) && !defined(__mips__)
|
||||||
|
#define EIGEN_FREEBSD_MALLOC_ALREADY_ALIGNED 1
|
||||||
|
#else
|
||||||
|
#define EIGEN_FREEBSD_MALLOC_ALREADY_ALIGNED 0
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if defined(__APPLE__) || defined(_WIN64) || EIGEN_FREEBSD_MALLOC_ALREADY_ALIGNED
|
||||||
|
#define EIGEN_MALLOC_ALREADY_ALIGNED 1
|
||||||
|
#else
|
||||||
|
#define EIGEN_MALLOC_ALREADY_ALIGNED 0
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if (defined __QNXNTO__) || (((defined _GNU_SOURCE) || ((defined _XOPEN_SOURCE) && (_XOPEN_SOURCE >= 600))) && (defined _POSIX_ADVISORY_INFO) && (_POSIX_ADVISORY_INFO > 0))
|
||||||
|
#define EIGEN_HAS_POSIX_MEMALIGN 1
|
||||||
|
#else
|
||||||
|
#define EIGEN_HAS_POSIX_MEMALIGN 0
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifdef EIGEN_VECTORIZE_SSE
|
||||||
|
#define EIGEN_HAS_MM_MALLOC 1
|
||||||
|
#else
|
||||||
|
#define EIGEN_HAS_MM_MALLOC 0
|
||||||
|
#endif
|
||||||
|
|
||||||
|
/** \internal like malloc, but the returned pointer is guaranteed to be 16-byte aligned.
|
||||||
|
* Fast, but wastes 16 additional bytes of memory.
|
||||||
|
* Does not throw any exception.
|
||||||
|
*/
|
||||||
|
inline void* ei_handmade_aligned_malloc(std::size_t size)
|
||||||
|
{
|
||||||
|
void *original = std::malloc(size+16);
|
||||||
|
void *aligned = reinterpret_cast<void*>((reinterpret_cast<std::size_t>(original) & ~(std::size_t(15))) + 16);
|
||||||
|
*(reinterpret_cast<void**>(aligned) - 1) = original;
|
||||||
|
return aligned;
|
||||||
|
}
|
||||||
|
|
||||||
|
/** \internal frees memory allocated with ei_handmade_aligned_malloc */
|
||||||
|
inline void ei_handmade_aligned_free(void *ptr)
|
||||||
|
{
|
||||||
|
if(ptr)
|
||||||
|
std::free(*(reinterpret_cast<void**>(ptr) - 1));
|
||||||
|
}
|
||||||
|
|
||||||
|
/** \internal allocates \a size bytes. The returned pointer is guaranteed to have 16 bytes alignment.
|
||||||
|
* On allocation error, the returned pointer is null, and if exceptions are enabled then a std::bad_alloc is thrown.
|
||||||
|
*/
|
||||||
|
inline void* ei_aligned_malloc(std::size_t size)
|
||||||
|
{
|
||||||
|
#ifdef EIGEN_NO_MALLOC
|
||||||
|
ei_assert(false && "heap allocation is forbidden (EIGEN_NO_MALLOC is defined)");
|
||||||
|
#endif
|
||||||
|
|
||||||
|
void *result;
|
||||||
|
#if !EIGEN_ALIGN
|
||||||
|
result = std::malloc(size);
|
||||||
|
#elif EIGEN_MALLOC_ALREADY_ALIGNED
|
||||||
|
result = std::malloc(size);
|
||||||
|
#elif EIGEN_HAS_POSIX_MEMALIGN
|
||||||
|
if(posix_memalign(&result, 16, size)) result = 0;
|
||||||
|
#elif EIGEN_HAS_MM_MALLOC
|
||||||
|
result = _mm_malloc(size, 16);
|
||||||
|
#elif (defined _MSC_VER)
|
||||||
|
result = _aligned_malloc(size, 16);
|
||||||
|
#else
|
||||||
|
result = ei_handmade_aligned_malloc(size);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifdef EIGEN_EXCEPTIONS
|
||||||
|
if(result == 0)
|
||||||
|
throw std::bad_alloc();
|
||||||
|
#endif
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
/** allocates \a size bytes. If Align is true, then the returned ptr is 16-byte-aligned.
|
||||||
|
* On allocation error, the returned pointer is null, and if exceptions are enabled then a std::bad_alloc is thrown.
|
||||||
|
*/
|
||||||
|
template<bool Align> inline void* ei_conditional_aligned_malloc(std::size_t size)
|
||||||
|
{
|
||||||
|
return ei_aligned_malloc(size);
|
||||||
|
}
|
||||||
|
|
||||||
|
template<> inline void* ei_conditional_aligned_malloc<false>(std::size_t size)
|
||||||
|
{
|
||||||
|
#ifdef EIGEN_NO_MALLOC
|
||||||
|
ei_assert(false && "heap allocation is forbidden (EIGEN_NO_MALLOC is defined)");
|
||||||
|
#endif
|
||||||
|
|
||||||
|
void *result = std::malloc(size);
|
||||||
|
#ifdef EIGEN_EXCEPTIONS
|
||||||
|
if(!result) throw std::bad_alloc();
|
||||||
|
#endif
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
/** \internal construct the elements of an array.
|
||||||
|
* The \a size parameter tells on how many objects to call the constructor of T.
|
||||||
|
*/
|
||||||
|
template<typename T> inline T* ei_construct_elements_of_array(T *ptr, std::size_t size)
|
||||||
|
{
|
||||||
|
for (std::size_t i=0; i < size; ++i) ::new (ptr + i) T;
|
||||||
|
return ptr;
|
||||||
|
}
|
||||||
|
|
||||||
|
/** allocates \a size objects of type T. The returned pointer is guaranteed to have 16 bytes alignment.
|
||||||
|
* On allocation error, the returned pointer is undefined, but if exceptions are enabled then a std::bad_alloc is thrown.
|
||||||
|
* The default constructor of T is called.
|
||||||
|
*/
|
||||||
|
template<typename T> inline T* ei_aligned_new(std::size_t size)
|
||||||
|
{
|
||||||
|
T *result = reinterpret_cast<T*>(ei_aligned_malloc(sizeof(T)*size));
|
||||||
|
return ei_construct_elements_of_array(result, size);
|
||||||
|
}
|
||||||
|
|
||||||
|
template<typename T, bool Align> inline T* ei_conditional_aligned_new(std::size_t size)
|
||||||
|
{
|
||||||
|
T *result = reinterpret_cast<T*>(ei_conditional_aligned_malloc<Align>(sizeof(T)*size));
|
||||||
|
return ei_construct_elements_of_array(result, size);
|
||||||
|
}
|
||||||
|
|
||||||
|
/** \internal free memory allocated with ei_aligned_malloc
|
||||||
|
*/
|
||||||
|
inline void ei_aligned_free(void *ptr)
|
||||||
|
{
|
||||||
|
#if !EIGEN_ALIGN
|
||||||
|
std::free(ptr);
|
||||||
|
#elif EIGEN_MALLOC_ALREADY_ALIGNED
|
||||||
|
std::free(ptr);
|
||||||
|
#elif EIGEN_HAS_POSIX_MEMALIGN
|
||||||
|
std::free(ptr);
|
||||||
|
#elif EIGEN_HAS_MM_MALLOC
|
||||||
|
_mm_free(ptr);
|
||||||
|
#elif defined(_MSC_VER)
|
||||||
|
_aligned_free(ptr);
|
||||||
|
#else
|
||||||
|
ei_handmade_aligned_free(ptr);
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
/** \internal free memory allocated with ei_conditional_aligned_malloc
|
||||||
|
*/
|
||||||
|
template<bool Align> inline void ei_conditional_aligned_free(void *ptr)
|
||||||
|
{
|
||||||
|
ei_aligned_free(ptr);
|
||||||
|
}
|
||||||
|
|
||||||
|
template<> inline void ei_conditional_aligned_free<false>(void *ptr)
|
||||||
|
{
|
||||||
|
std::free(ptr);
|
||||||
|
}
|
||||||
|
|
||||||
|
/** \internal destruct the elements of an array.
|
||||||
|
* The \a size parameters tells on how many objects to call the destructor of T.
|
||||||
|
*/
|
||||||
|
template<typename T> inline void ei_destruct_elements_of_array(T *ptr, std::size_t size)
|
||||||
|
{
|
||||||
|
// always destruct an array starting from the end.
|
||||||
|
if(ptr)
|
||||||
|
while(size) ptr[--size].~T();
|
||||||
|
}
|
||||||
|
|
||||||
|
/** \internal delete objects constructed with ei_aligned_new
|
||||||
|
* The \a size parameters tells on how many objects to call the destructor of T.
|
||||||
|
*/
|
||||||
|
template<typename T> inline void ei_aligned_delete(T *ptr, std::size_t size)
|
||||||
|
{
|
||||||
|
ei_destruct_elements_of_array<T>(ptr, size);
|
||||||
|
ei_aligned_free(ptr);
|
||||||
|
}
|
||||||
|
|
||||||
|
/** \internal delete objects constructed with ei_conditional_aligned_new
|
||||||
|
* The \a size parameters tells on how many objects to call the destructor of T.
|
||||||
|
*/
|
||||||
|
template<typename T, bool Align> inline void ei_conditional_aligned_delete(T *ptr, std::size_t size)
|
||||||
|
{
|
||||||
|
ei_destruct_elements_of_array<T>(ptr, size);
|
||||||
|
ei_conditional_aligned_free<Align>(ptr);
|
||||||
|
}
|
||||||
|
|
||||||
|
/** \internal \returns the index of the first element of the array that is well aligned for vectorization.
|
||||||
|
*
|
||||||
|
* \param array the address of the start of the array
|
||||||
|
* \param size the size of the array
|
||||||
|
*
|
||||||
|
* \note If no element of the array is well aligned, the size of the array is returned. Typically,
|
||||||
|
* for example with SSE, "well aligned" means 16-byte-aligned. If vectorization is disabled or if the
|
||||||
|
* packet size for the given scalar type is 1, then everything is considered well-aligned.
|
||||||
|
*
|
||||||
|
* \note If the scalar type is vectorizable, we rely on the following assumptions: sizeof(Scalar) is a
|
||||||
|
* power of 2, the packet size in bytes is also a power of 2, and is a multiple of sizeof(Scalar). On the
|
||||||
|
* other hand, we do not assume that the array address is a multiple of sizeof(Scalar), as that fails for
|
||||||
|
* example with Scalar=double on certain 32-bit platforms, see bug #79.
|
||||||
|
*
|
||||||
|
* There is also the variant ei_first_aligned(const MatrixBase&, Integer) defined in Coeffs.h.
|
||||||
|
*/
|
||||||
|
template<typename Scalar, typename Integer>
|
||||||
|
inline static Integer ei_alignmentOffset(const Scalar* array, Integer size)
|
||||||
|
{
|
||||||
|
typedef typename ei_packet_traits<Scalar>::type Packet;
|
||||||
|
enum { PacketSize = ei_packet_traits<Scalar>::size,
|
||||||
|
PacketAlignedMask = PacketSize-1
|
||||||
|
};
|
||||||
|
|
||||||
|
if(PacketSize==1)
|
||||||
|
{
|
||||||
|
// Either there is no vectorization, or a packet consists of exactly 1 scalar so that all elements
|
||||||
|
// of the array have the same aligment.
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
else if(std::size_t(array) & (sizeof(Scalar)-1))
|
||||||
|
{
|
||||||
|
// There is vectorization for this scalar type, but the array is not aligned to the size of a single scalar.
|
||||||
|
// Consequently, no element of the array is well aligned.
|
||||||
|
return size;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return std::min<Integer>( (PacketSize - (Integer((std::size_t(array)/sizeof(Scalar))) & PacketAlignedMask))
|
||||||
|
& PacketAlignedMask, size);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/** \internal
|
||||||
|
* ei_aligned_stack_alloc(SIZE) allocates an aligned buffer of SIZE bytes
|
||||||
|
* on the stack if SIZE is smaller than EIGEN_STACK_ALLOCATION_LIMIT.
|
||||||
|
* Otherwise the memory is allocated on the heap.
|
||||||
|
* Data allocated with ei_aligned_stack_alloc \b must be freed by calling ei_aligned_stack_free(PTR,SIZE).
|
||||||
|
* \code
|
||||||
|
* float * data = ei_aligned_stack_alloc(float,array.size());
|
||||||
|
* // ...
|
||||||
|
* ei_aligned_stack_free(data,float,array.size());
|
||||||
|
* \endcode
|
||||||
|
*/
|
||||||
|
#ifdef __linux__
|
||||||
|
#define ei_aligned_stack_alloc(SIZE) (SIZE<=EIGEN_STACK_ALLOCATION_LIMIT) \
|
||||||
|
? alloca(SIZE) \
|
||||||
|
: ei_aligned_malloc(SIZE)
|
||||||
|
#define ei_aligned_stack_free(PTR,SIZE) if(SIZE>EIGEN_STACK_ALLOCATION_LIMIT) ei_aligned_free(PTR)
|
||||||
|
#else
|
||||||
|
#define ei_aligned_stack_alloc(SIZE) ei_aligned_malloc(SIZE)
|
||||||
|
#define ei_aligned_stack_free(PTR,SIZE) ei_aligned_free(PTR)
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#define ei_aligned_stack_new(TYPE,SIZE) ei_construct_elements_of_array(reinterpret_cast<TYPE*>(ei_aligned_stack_alloc(sizeof(TYPE)*SIZE)), SIZE)
|
||||||
|
#define ei_aligned_stack_delete(TYPE,PTR,SIZE) do {ei_destruct_elements_of_array<TYPE>(PTR, SIZE); \
|
||||||
|
ei_aligned_stack_free(PTR,sizeof(TYPE)*SIZE);} while(0)
|
||||||
|
|
||||||
|
|
||||||
|
#if EIGEN_ALIGN
|
||||||
|
#ifdef EIGEN_EXCEPTIONS
|
||||||
|
#define EIGEN_MAKE_ALIGNED_OPERATOR_NEW_NOTHROW(NeedsToAlign) \
|
||||||
|
void* operator new(std::size_t size, const std::nothrow_t&) throw() { \
|
||||||
|
try { return Eigen::ei_conditional_aligned_malloc<NeedsToAlign>(size); } \
|
||||||
|
catch (...) { return 0; } \
|
||||||
|
return 0; \
|
||||||
|
}
|
||||||
|
#else
|
||||||
|
#define EIGEN_MAKE_ALIGNED_OPERATOR_NEW_NOTHROW(NeedsToAlign) \
|
||||||
|
void* operator new(std::size_t size, const std::nothrow_t&) throw() { \
|
||||||
|
return Eigen::ei_conditional_aligned_malloc<NeedsToAlign>(size); \
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#define EIGEN_MAKE_ALIGNED_OPERATOR_NEW_IF(NeedsToAlign) \
|
||||||
|
void *operator new(std::size_t size) { \
|
||||||
|
return Eigen::ei_conditional_aligned_malloc<NeedsToAlign>(size); \
|
||||||
|
} \
|
||||||
|
void *operator new[](std::size_t size) { \
|
||||||
|
return Eigen::ei_conditional_aligned_malloc<NeedsToAlign>(size); \
|
||||||
|
} \
|
||||||
|
void operator delete(void * ptr) throw() { Eigen::ei_conditional_aligned_free<NeedsToAlign>(ptr); } \
|
||||||
|
void operator delete[](void * ptr) throw() { Eigen::ei_conditional_aligned_free<NeedsToAlign>(ptr); } \
|
||||||
|
/* in-place new and delete. since (at least afaik) there is no actual */ \
|
||||||
|
/* memory allocated we can safely let the default implementation handle */ \
|
||||||
|
/* this particular case. */ \
|
||||||
|
static void *operator new(std::size_t size, void *ptr) { return ::operator new(size,ptr); } \
|
||||||
|
void operator delete(void * memory, void *ptr) throw() { return ::operator delete(memory,ptr); } \
|
||||||
|
/* nothrow-new (returns zero instead of std::bad_alloc) */ \
|
||||||
|
EIGEN_MAKE_ALIGNED_OPERATOR_NEW_NOTHROW(NeedsToAlign) \
|
||||||
|
void operator delete(void *ptr, const std::nothrow_t&) throw() { \
|
||||||
|
Eigen::ei_conditional_aligned_free<NeedsToAlign>(ptr); \
|
||||||
|
} \
|
||||||
|
typedef void ei_operator_new_marker_type;
|
||||||
|
#else
|
||||||
|
#define EIGEN_MAKE_ALIGNED_OPERATOR_NEW_IF(NeedsToAlign)
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#define EIGEN_MAKE_ALIGNED_OPERATOR_NEW EIGEN_MAKE_ALIGNED_OPERATOR_NEW_IF(true)
|
||||||
|
#define EIGEN_MAKE_ALIGNED_OPERATOR_NEW_IF_VECTORIZABLE_FIXED_SIZE(Scalar,Size) \
|
||||||
|
EIGEN_MAKE_ALIGNED_OPERATOR_NEW_IF(((Size)!=Eigen::Dynamic) && ((sizeof(Scalar)*(Size))%16==0))
|
||||||
|
|
||||||
|
|
||||||
|
/** \class aligned_allocator
|
||||||
|
*
|
||||||
|
* \brief stl compatible allocator to use with with 16 byte aligned types
|
||||||
|
*
|
||||||
|
* Example:
|
||||||
|
* \code
|
||||||
|
* // Matrix4f requires 16 bytes alignment:
|
||||||
|
* std::map< int, Matrix4f, std::less<int>, aligned_allocator<Matrix4f> > my_map_mat4;
|
||||||
|
* // Vector3f does not require 16 bytes alignment, no need to use Eigen's allocator:
|
||||||
|
* std::map< int, Vector3f > my_map_vec3;
|
||||||
|
* \endcode
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
template<class T>
|
||||||
|
class aligned_allocator
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
typedef std::size_t size_type;
|
||||||
|
typedef std::ptrdiff_t difference_type;
|
||||||
|
typedef T* pointer;
|
||||||
|
typedef const T* const_pointer;
|
||||||
|
typedef T& reference;
|
||||||
|
typedef const T& const_reference;
|
||||||
|
typedef T value_type;
|
||||||
|
|
||||||
|
template<class U>
|
||||||
|
struct rebind
|
||||||
|
{
|
||||||
|
typedef aligned_allocator<U> other;
|
||||||
|
};
|
||||||
|
|
||||||
|
pointer address( reference value ) const
|
||||||
|
{
|
||||||
|
return &value;
|
||||||
|
}
|
||||||
|
|
||||||
|
const_pointer address( const_reference value ) const
|
||||||
|
{
|
||||||
|
return &value;
|
||||||
|
}
|
||||||
|
|
||||||
|
aligned_allocator() throw()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
aligned_allocator( const aligned_allocator& ) throw()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
template<class U>
|
||||||
|
aligned_allocator( const aligned_allocator<U>& ) throw()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
~aligned_allocator() throw()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
size_type max_size() const throw()
|
||||||
|
{
|
||||||
|
return std::numeric_limits<size_type>::max();
|
||||||
|
}
|
||||||
|
|
||||||
|
pointer allocate( size_type num, const_pointer* hint = 0 )
|
||||||
|
{
|
||||||
|
static_cast<void>( hint ); // suppress unused variable warning
|
||||||
|
return static_cast<pointer>( ei_aligned_malloc( num * sizeof(T) ) );
|
||||||
|
}
|
||||||
|
|
||||||
|
void construct( pointer p, const T& value )
|
||||||
|
{
|
||||||
|
::new( p ) T( value );
|
||||||
|
}
|
||||||
|
|
||||||
|
void destroy( pointer p )
|
||||||
|
{
|
||||||
|
p->~T();
|
||||||
|
}
|
||||||
|
|
||||||
|
void deallocate( pointer p, size_type /*num*/ )
|
||||||
|
{
|
||||||
|
ei_aligned_free( p );
|
||||||
|
}
|
||||||
|
|
||||||
|
bool operator!=(const aligned_allocator<T>& other) const
|
||||||
|
{ return false; }
|
||||||
|
|
||||||
|
bool operator==(const aligned_allocator<T>& other) const
|
||||||
|
{ return true; }
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif // EIGEN_MEMORY_H
|
183
ground/openpilotgcs/src/libs/eigen/Eigen/src/Core/util/Meta.h
Normal file
183
ground/openpilotgcs/src/libs/eigen/Eigen/src/Core/util/Meta.h
Normal file
@ -0,0 +1,183 @@
|
|||||||
|
// This file is part of Eigen, a lightweight C++ template library
|
||||||
|
// for linear algebra. Eigen itself is part of the KDE project.
|
||||||
|
//
|
||||||
|
// Copyright (C) 2008 Gael Guennebaud <g.gael@free.fr>
|
||||||
|
// Copyright (C) 2006-2008 Benoit Jacob <jacob.benoit.1@gmail.com>
|
||||||
|
//
|
||||||
|
// Eigen is free software; you can redistribute it and/or
|
||||||
|
// modify it under the terms of the GNU Lesser General Public
|
||||||
|
// License as published by the Free Software Foundation; either
|
||||||
|
// version 3 of the License, or (at your option) any later version.
|
||||||
|
//
|
||||||
|
// Alternatively, you can redistribute it and/or
|
||||||
|
// modify it under the terms of the GNU General Public License as
|
||||||
|
// published by the Free Software Foundation; either version 2 of
|
||||||
|
// the License, or (at your option) any later version.
|
||||||
|
//
|
||||||
|
// Eigen is distributed in the hope that it will be useful, but WITHOUT ANY
|
||||||
|
// WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
|
||||||
|
// FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License or the
|
||||||
|
// GNU General Public License for more details.
|
||||||
|
//
|
||||||
|
// You should have received a copy of the GNU Lesser General Public
|
||||||
|
// License and a copy of the GNU General Public License along with
|
||||||
|
// Eigen. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
|
#ifndef EIGEN_META_H
|
||||||
|
#define EIGEN_META_H
|
||||||
|
|
||||||
|
/** \internal
|
||||||
|
* \file Meta.h
|
||||||
|
* This file contains generic metaprogramming classes which are not specifically related to Eigen.
|
||||||
|
* \note In case you wonder, yes we're aware that Boost already provides all these features,
|
||||||
|
* we however don't want to add a dependency to Boost.
|
||||||
|
*/
|
||||||
|
|
||||||
|
struct ei_meta_true { enum { ret = 1 }; };
|
||||||
|
struct ei_meta_false { enum { ret = 0 }; };
|
||||||
|
|
||||||
|
template<bool Condition, typename Then, typename Else>
|
||||||
|
struct ei_meta_if { typedef Then ret; };
|
||||||
|
|
||||||
|
template<typename Then, typename Else>
|
||||||
|
struct ei_meta_if <false, Then, Else> { typedef Else ret; };
|
||||||
|
|
||||||
|
template<typename T, typename U> struct ei_is_same_type { enum { ret = 0 }; };
|
||||||
|
template<typename T> struct ei_is_same_type<T,T> { enum { ret = 1 }; };
|
||||||
|
|
||||||
|
template<typename T> struct ei_unref { typedef T type; };
|
||||||
|
template<typename T> struct ei_unref<T&> { typedef T type; };
|
||||||
|
|
||||||
|
template<typename T> struct ei_unpointer { typedef T type; };
|
||||||
|
template<typename T> struct ei_unpointer<T*> { typedef T type; };
|
||||||
|
template<typename T> struct ei_unpointer<T*const> { typedef T type; };
|
||||||
|
|
||||||
|
template<typename T> struct ei_unconst { typedef T type; };
|
||||||
|
template<typename T> struct ei_unconst<const T> { typedef T type; };
|
||||||
|
template<typename T> struct ei_unconst<T const &> { typedef T & type; };
|
||||||
|
template<typename T> struct ei_unconst<T const *> { typedef T * type; };
|
||||||
|
|
||||||
|
template<typename T> struct ei_cleantype { typedef T type; };
|
||||||
|
template<typename T> struct ei_cleantype<const T> { typedef typename ei_cleantype<T>::type type; };
|
||||||
|
template<typename T> struct ei_cleantype<const T&> { typedef typename ei_cleantype<T>::type type; };
|
||||||
|
template<typename T> struct ei_cleantype<T&> { typedef typename ei_cleantype<T>::type type; };
|
||||||
|
template<typename T> struct ei_cleantype<const T*> { typedef typename ei_cleantype<T>::type type; };
|
||||||
|
template<typename T> struct ei_cleantype<T*> { typedef typename ei_cleantype<T>::type type; };
|
||||||
|
|
||||||
|
/** \internal
|
||||||
|
* Convenient struct to get the result type of a unary or binary functor.
|
||||||
|
*
|
||||||
|
* It supports both the current STL mechanism (using the result_type member) as well as
|
||||||
|
* upcoming next STL generation (using a templated result member).
|
||||||
|
* If none of these members is provided, then the type of the first argument is returned. FIXME, that behavior is a pretty bad hack.
|
||||||
|
*/
|
||||||
|
template<typename T> struct ei_result_of {};
|
||||||
|
|
||||||
|
struct ei_has_none {int a[1];};
|
||||||
|
struct ei_has_std_result_type {int a[2];};
|
||||||
|
struct ei_has_tr1_result {int a[3];};
|
||||||
|
|
||||||
|
template<typename Func, typename ArgType, int SizeOf=sizeof(ei_has_none)>
|
||||||
|
struct ei_unary_result_of_select {typedef ArgType type;};
|
||||||
|
|
||||||
|
template<typename Func, typename ArgType>
|
||||||
|
struct ei_unary_result_of_select<Func, ArgType, sizeof(ei_has_std_result_type)> {typedef typename Func::result_type type;};
|
||||||
|
|
||||||
|
template<typename Func, typename ArgType>
|
||||||
|
struct ei_unary_result_of_select<Func, ArgType, sizeof(ei_has_tr1_result)> {typedef typename Func::template result<Func(ArgType)>::type type;};
|
||||||
|
|
||||||
|
template<typename Func, typename ArgType>
|
||||||
|
struct ei_result_of<Func(ArgType)> {
|
||||||
|
template<typename T>
|
||||||
|
static ei_has_std_result_type testFunctor(T const *, typename T::result_type const * = 0);
|
||||||
|
template<typename T>
|
||||||
|
static ei_has_tr1_result testFunctor(T const *, typename T::template result<T(ArgType)>::type const * = 0);
|
||||||
|
static ei_has_none testFunctor(...);
|
||||||
|
|
||||||
|
// note that the following indirection is needed for gcc-3.3
|
||||||
|
enum {FunctorType = sizeof(testFunctor(static_cast<Func*>(0)))};
|
||||||
|
typedef typename ei_unary_result_of_select<Func, ArgType, FunctorType>::type type;
|
||||||
|
};
|
||||||
|
|
||||||
|
template<typename Func, typename ArgType0, typename ArgType1, int SizeOf=sizeof(ei_has_none)>
|
||||||
|
struct ei_binary_result_of_select {typedef ArgType0 type;};
|
||||||
|
|
||||||
|
template<typename Func, typename ArgType0, typename ArgType1>
|
||||||
|
struct ei_binary_result_of_select<Func, ArgType0, ArgType1, sizeof(ei_has_std_result_type)>
|
||||||
|
{typedef typename Func::result_type type;};
|
||||||
|
|
||||||
|
template<typename Func, typename ArgType0, typename ArgType1>
|
||||||
|
struct ei_binary_result_of_select<Func, ArgType0, ArgType1, sizeof(ei_has_tr1_result)>
|
||||||
|
{typedef typename Func::template result<Func(ArgType0,ArgType1)>::type type;};
|
||||||
|
|
||||||
|
template<typename Func, typename ArgType0, typename ArgType1>
|
||||||
|
struct ei_result_of<Func(ArgType0,ArgType1)> {
|
||||||
|
template<typename T>
|
||||||
|
static ei_has_std_result_type testFunctor(T const *, typename T::result_type const * = 0);
|
||||||
|
template<typename T>
|
||||||
|
static ei_has_tr1_result testFunctor(T const *, typename T::template result<T(ArgType0,ArgType1)>::type const * = 0);
|
||||||
|
static ei_has_none testFunctor(...);
|
||||||
|
|
||||||
|
// note that the following indirection is needed for gcc-3.3
|
||||||
|
enum {FunctorType = sizeof(testFunctor(static_cast<Func*>(0)))};
|
||||||
|
typedef typename ei_binary_result_of_select<Func, ArgType0, ArgType1, FunctorType>::type type;
|
||||||
|
};
|
||||||
|
|
||||||
|
/** \internal In short, it computes int(sqrt(\a Y)) with \a Y an integer.
|
||||||
|
* Usage example: \code ei_meta_sqrt<1023>::ret \endcode
|
||||||
|
*/
|
||||||
|
template<int Y,
|
||||||
|
int InfX = 0,
|
||||||
|
int SupX = ((Y==1) ? 1 : Y/2),
|
||||||
|
bool Done = ((SupX-InfX)<=1 ? true : ((SupX*SupX <= Y) && ((SupX+1)*(SupX+1) > Y))) >
|
||||||
|
// use ?: instead of || just to shut up a stupid gcc 4.3 warning
|
||||||
|
class ei_meta_sqrt
|
||||||
|
{
|
||||||
|
enum {
|
||||||
|
MidX = (InfX+SupX)/2,
|
||||||
|
TakeInf = MidX*MidX > Y ? 1 : 0,
|
||||||
|
NewInf = int(TakeInf) ? InfX : int(MidX),
|
||||||
|
NewSup = int(TakeInf) ? int(MidX) : SupX
|
||||||
|
};
|
||||||
|
public:
|
||||||
|
enum { ret = ei_meta_sqrt<Y,NewInf,NewSup>::ret };
|
||||||
|
};
|
||||||
|
|
||||||
|
template<int Y, int InfX, int SupX>
|
||||||
|
class ei_meta_sqrt<Y, InfX, SupX, true> { public: enum { ret = (SupX*SupX <= Y) ? SupX : InfX }; };
|
||||||
|
|
||||||
|
/** \internal determines whether the product of two numeric types is allowed and what the return type is */
|
||||||
|
template<typename T, typename U> struct ei_scalar_product_traits
|
||||||
|
{
|
||||||
|
// dummy general case where T and U aren't compatible -- not allowed anyway but we catch it elsewhere
|
||||||
|
//enum { Cost = NumTraits<T>::MulCost };
|
||||||
|
typedef T ReturnType;
|
||||||
|
};
|
||||||
|
|
||||||
|
template<typename T> struct ei_scalar_product_traits<T,T>
|
||||||
|
{
|
||||||
|
//enum { Cost = NumTraits<T>::MulCost };
|
||||||
|
typedef T ReturnType;
|
||||||
|
};
|
||||||
|
|
||||||
|
template<typename T> struct ei_scalar_product_traits<T,std::complex<T> >
|
||||||
|
{
|
||||||
|
//enum { Cost = 2*NumTraits<T>::MulCost };
|
||||||
|
typedef std::complex<T> ReturnType;
|
||||||
|
};
|
||||||
|
|
||||||
|
template<typename T> struct ei_scalar_product_traits<std::complex<T>, T>
|
||||||
|
{
|
||||||
|
//enum { Cost = 2*NumTraits<T>::MulCost };
|
||||||
|
typedef std::complex<T> ReturnType;
|
||||||
|
};
|
||||||
|
|
||||||
|
// FIXME quick workaround around current limitation of ei_result_of
|
||||||
|
template<typename Scalar, typename ArgType0, typename ArgType1>
|
||||||
|
struct ei_result_of<ei_scalar_product_op<Scalar>(ArgType0,ArgType1)> {
|
||||||
|
typedef typename ei_scalar_product_traits<typename ei_cleantype<ArgType0>::type, typename ei_cleantype<ArgType1>::type>::ReturnType type;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
#endif // EIGEN_META_H
|
@ -0,0 +1,149 @@
|
|||||||
|
// This file is part of Eigen, a lightweight C++ template library
|
||||||
|
// for linear algebra. Eigen itself is part of the KDE project.
|
||||||
|
//
|
||||||
|
// Copyright (C) 2008 Gael Guennebaud <g.gael@free.fr>
|
||||||
|
// Copyright (C) 2006-2008 Benoit Jacob <jacob.benoit.1@gmail.com>
|
||||||
|
//
|
||||||
|
// Eigen is free software; you can redistribute it and/or
|
||||||
|
// modify it under the terms of the GNU Lesser General Public
|
||||||
|
// License as published by the Free Software Foundation; either
|
||||||
|
// version 3 of the License, or (at your option) any later version.
|
||||||
|
//
|
||||||
|
// Alternatively, you can redistribute it and/or
|
||||||
|
// modify it under the terms of the GNU General Public License as
|
||||||
|
// published by the Free Software Foundation; either version 2 of
|
||||||
|
// the License, or (at your option) any later version.
|
||||||
|
//
|
||||||
|
// Eigen is distributed in the hope that it will be useful, but WITHOUT ANY
|
||||||
|
// WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
|
||||||
|
// FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License or the
|
||||||
|
// GNU General Public License for more details.
|
||||||
|
//
|
||||||
|
// You should have received a copy of the GNU Lesser General Public
|
||||||
|
// License and a copy of the GNU General Public License along with
|
||||||
|
// Eigen. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
|
#ifndef EIGEN_STATIC_ASSERT_H
|
||||||
|
#define EIGEN_STATIC_ASSERT_H
|
||||||
|
|
||||||
|
/* Some notes on Eigen's static assertion mechanism:
|
||||||
|
*
|
||||||
|
* - in EIGEN_STATIC_ASSERT(CONDITION,MSG) the parameter CONDITION must be a compile time boolean
|
||||||
|
* expression, and MSG an enum listed in struct ei_static_assert<true>
|
||||||
|
*
|
||||||
|
* - define EIGEN_NO_STATIC_ASSERT to disable them (and save compilation time)
|
||||||
|
* in that case, the static assertion is converted to the following runtime assert:
|
||||||
|
* ei_assert(CONDITION && "MSG")
|
||||||
|
*
|
||||||
|
* - currently EIGEN_STATIC_ASSERT can only be used in function scope
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef EIGEN_NO_STATIC_ASSERT
|
||||||
|
|
||||||
|
#ifdef __GXX_EXPERIMENTAL_CXX0X__
|
||||||
|
|
||||||
|
// if native static_assert is enabled, let's use it
|
||||||
|
#define EIGEN_STATIC_ASSERT(X,MSG) static_assert(X,#MSG);
|
||||||
|
|
||||||
|
#else // CXX0X
|
||||||
|
|
||||||
|
template<bool condition>
|
||||||
|
struct ei_static_assert {};
|
||||||
|
|
||||||
|
template<>
|
||||||
|
struct ei_static_assert<true>
|
||||||
|
{
|
||||||
|
enum {
|
||||||
|
YOU_TRIED_CALLING_A_VECTOR_METHOD_ON_A_MATRIX,
|
||||||
|
YOU_MIXED_VECTORS_OF_DIFFERENT_SIZES,
|
||||||
|
YOU_MIXED_MATRICES_OF_DIFFERENT_SIZES,
|
||||||
|
THIS_METHOD_IS_ONLY_FOR_VECTORS_OF_A_SPECIFIC_SIZE,
|
||||||
|
THIS_METHOD_IS_ONLY_FOR_MATRICES_OF_A_SPECIFIC_SIZE,
|
||||||
|
YOU_MADE_A_PROGRAMMING_MISTAKE,
|
||||||
|
YOU_CALLED_A_FIXED_SIZE_METHOD_ON_A_DYNAMIC_SIZE_MATRIX_OR_VECTOR,
|
||||||
|
UNALIGNED_LOAD_AND_STORE_OPERATIONS_UNIMPLEMENTED_ON_ALTIVEC,
|
||||||
|
NUMERIC_TYPE_MUST_BE_FLOATING_POINT,
|
||||||
|
COEFFICIENT_WRITE_ACCESS_TO_SELFADJOINT_NOT_SUPPORTED,
|
||||||
|
WRITING_TO_TRIANGULAR_PART_WITH_UNIT_DIAGONAL_IS_NOT_SUPPORTED,
|
||||||
|
THIS_METHOD_IS_ONLY_FOR_FIXED_SIZE,
|
||||||
|
INVALID_MATRIX_PRODUCT,
|
||||||
|
INVALID_VECTOR_VECTOR_PRODUCT__IF_YOU_WANTED_A_DOT_OR_COEFF_WISE_PRODUCT_YOU_MUST_USE_THE_EXPLICIT_FUNCTIONS,
|
||||||
|
INVALID_MATRIX_PRODUCT__IF_YOU_WANTED_A_COEFF_WISE_PRODUCT_YOU_MUST_USE_THE_EXPLICIT_FUNCTION,
|
||||||
|
YOU_MIXED_DIFFERENT_NUMERIC_TYPES__YOU_NEED_TO_USE_THE_CAST_METHOD_OF_MATRIXBASE_TO_CAST_NUMERIC_TYPES_EXPLICITLY,
|
||||||
|
THIS_METHOD_IS_ONLY_FOR_COLUMN_MAJOR_MATRICES,
|
||||||
|
THIS_METHOD_IS_ONLY_FOR_ROW_MAJOR_MATRICES,
|
||||||
|
INVALID_MATRIX_TEMPLATE_PARAMETERS,
|
||||||
|
INVALID_MATRIXBASE_TEMPLATE_PARAMETERS,
|
||||||
|
BOTH_MATRICES_MUST_HAVE_THE_SAME_STORAGE_ORDER,
|
||||||
|
THIS_METHOD_IS_ONLY_FOR_DIAGONAL_MATRIX
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
// Specialized implementation for MSVC to avoid "conditional
|
||||||
|
// expression is constant" warnings. This implementation doesn't
|
||||||
|
// appear to work under GCC, hence the multiple implementations.
|
||||||
|
#ifdef _MSC_VER
|
||||||
|
|
||||||
|
#define EIGEN_STATIC_ASSERT(CONDITION,MSG) \
|
||||||
|
{Eigen::ei_static_assert<CONDITION ? true : false>::MSG;}
|
||||||
|
|
||||||
|
#else
|
||||||
|
|
||||||
|
#define EIGEN_STATIC_ASSERT(CONDITION,MSG) \
|
||||||
|
if (Eigen::ei_static_assert<CONDITION ? true : false>::MSG) {}
|
||||||
|
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#endif // not CXX0X
|
||||||
|
|
||||||
|
#else // EIGEN_NO_STATIC_ASSERT
|
||||||
|
|
||||||
|
#define EIGEN_STATIC_ASSERT(CONDITION,MSG) ei_assert((CONDITION) && #MSG);
|
||||||
|
|
||||||
|
#endif // EIGEN_NO_STATIC_ASSERT
|
||||||
|
|
||||||
|
|
||||||
|
// static assertion failing if the type \a TYPE is not a vector type
|
||||||
|
#define EIGEN_STATIC_ASSERT_VECTOR_ONLY(TYPE) \
|
||||||
|
EIGEN_STATIC_ASSERT(TYPE::IsVectorAtCompileTime, \
|
||||||
|
YOU_TRIED_CALLING_A_VECTOR_METHOD_ON_A_MATRIX)
|
||||||
|
|
||||||
|
// static assertion failing if the type \a TYPE is not fixed-size
|
||||||
|
#define EIGEN_STATIC_ASSERT_FIXED_SIZE(TYPE) \
|
||||||
|
EIGEN_STATIC_ASSERT(TYPE::SizeAtCompileTime!=Eigen::Dynamic, \
|
||||||
|
YOU_CALLED_A_FIXED_SIZE_METHOD_ON_A_DYNAMIC_SIZE_MATRIX_OR_VECTOR)
|
||||||
|
|
||||||
|
// static assertion failing if the type \a TYPE is not a vector type of the given size
|
||||||
|
#define EIGEN_STATIC_ASSERT_VECTOR_SPECIFIC_SIZE(TYPE, SIZE) \
|
||||||
|
EIGEN_STATIC_ASSERT(TYPE::IsVectorAtCompileTime && TYPE::SizeAtCompileTime==SIZE, \
|
||||||
|
THIS_METHOD_IS_ONLY_FOR_VECTORS_OF_A_SPECIFIC_SIZE)
|
||||||
|
|
||||||
|
// static assertion failing if the type \a TYPE is not a vector type of the given size
|
||||||
|
#define EIGEN_STATIC_ASSERT_MATRIX_SPECIFIC_SIZE(TYPE, ROWS, COLS) \
|
||||||
|
EIGEN_STATIC_ASSERT(TYPE::RowsAtCompileTime==ROWS && TYPE::ColsAtCompileTime==COLS, \
|
||||||
|
THIS_METHOD_IS_ONLY_FOR_MATRICES_OF_A_SPECIFIC_SIZE)
|
||||||
|
|
||||||
|
// static assertion failing if the two vector expression types are not compatible (same fixed-size or dynamic size)
|
||||||
|
#define EIGEN_STATIC_ASSERT_SAME_VECTOR_SIZE(TYPE0,TYPE1) \
|
||||||
|
EIGEN_STATIC_ASSERT( \
|
||||||
|
(int(TYPE0::SizeAtCompileTime)==Eigen::Dynamic \
|
||||||
|
|| int(TYPE1::SizeAtCompileTime)==Eigen::Dynamic \
|
||||||
|
|| int(TYPE0::SizeAtCompileTime)==int(TYPE1::SizeAtCompileTime)),\
|
||||||
|
YOU_MIXED_VECTORS_OF_DIFFERENT_SIZES)
|
||||||
|
|
||||||
|
#define EIGEN_PREDICATE_SAME_MATRIX_SIZE(TYPE0,TYPE1) \
|
||||||
|
((int(TYPE0::RowsAtCompileTime)==Eigen::Dynamic \
|
||||||
|
|| int(TYPE1::RowsAtCompileTime)==Eigen::Dynamic \
|
||||||
|
|| int(TYPE0::RowsAtCompileTime)==int(TYPE1::RowsAtCompileTime)) \
|
||||||
|
&& (int(TYPE0::ColsAtCompileTime)==Eigen::Dynamic \
|
||||||
|
|| int(TYPE1::ColsAtCompileTime)==Eigen::Dynamic \
|
||||||
|
|| int(TYPE0::ColsAtCompileTime)==int(TYPE1::ColsAtCompileTime)))
|
||||||
|
|
||||||
|
// static assertion failing if it is guaranteed at compile-time that the two matrix expression types have different sizes
|
||||||
|
#define EIGEN_STATIC_ASSERT_SAME_MATRIX_SIZE(TYPE0,TYPE1) \
|
||||||
|
EIGEN_STATIC_ASSERT( \
|
||||||
|
EIGEN_PREDICATE_SAME_MATRIX_SIZE(TYPE0,TYPE1),\
|
||||||
|
YOU_MIXED_MATRICES_OF_DIFFERENT_SIZES)
|
||||||
|
|
||||||
|
#endif // EIGEN_STATIC_ASSERT_H
|
@ -0,0 +1,242 @@
|
|||||||
|
// This file is part of Eigen, a lightweight C++ template library
|
||||||
|
// for linear algebra. Eigen itself is part of the KDE project.
|
||||||
|
//
|
||||||
|
// Copyright (C) 2008 Gael Guennebaud <g.gael@free.fr>
|
||||||
|
// Copyright (C) 2006-2008 Benoit Jacob <jacob.benoit.1@gmail.com>
|
||||||
|
//
|
||||||
|
// Eigen is free software; you can redistribute it and/or
|
||||||
|
// modify it under the terms of the GNU Lesser General Public
|
||||||
|
// License as published by the Free Software Foundation; either
|
||||||
|
// version 3 of the License, or (at your option) any later version.
|
||||||
|
//
|
||||||
|
// Alternatively, you can redistribute it and/or
|
||||||
|
// modify it under the terms of the GNU General Public License as
|
||||||
|
// published by the Free Software Foundation; either version 2 of
|
||||||
|
// the License, or (at your option) any later version.
|
||||||
|
//
|
||||||
|
// Eigen is distributed in the hope that it will be useful, but WITHOUT ANY
|
||||||
|
// WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
|
||||||
|
// FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License or the
|
||||||
|
// GNU General Public License for more details.
|
||||||
|
//
|
||||||
|
// You should have received a copy of the GNU Lesser General Public
|
||||||
|
// License and a copy of the GNU General Public License along with
|
||||||
|
// Eigen. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
|
#ifndef EIGEN_XPRHELPER_H
|
||||||
|
#define EIGEN_XPRHELPER_H
|
||||||
|
|
||||||
|
// just a workaround because GCC seems to not really like empty structs
|
||||||
|
#ifdef __GNUG__
|
||||||
|
struct ei_empty_struct{char _ei_dummy_;};
|
||||||
|
#define EIGEN_EMPTY_STRUCT : Eigen::ei_empty_struct
|
||||||
|
#else
|
||||||
|
#define EIGEN_EMPTY_STRUCT
|
||||||
|
#endif
|
||||||
|
|
||||||
|
//classes inheriting ei_no_assignment_operator don't generate a default operator=.
|
||||||
|
class ei_no_assignment_operator
|
||||||
|
{
|
||||||
|
#if EIGEN_GCC3_OR_OLDER
|
||||||
|
protected:
|
||||||
|
void nevermind_this_is_just_to_work_around_a_stupid_gcc3_warning();
|
||||||
|
#endif
|
||||||
|
private:
|
||||||
|
ei_no_assignment_operator& operator=(const ei_no_assignment_operator&);
|
||||||
|
};
|
||||||
|
|
||||||
|
/** \internal If the template parameter Value is Dynamic, this class is just a wrapper around an int variable that
|
||||||
|
* can be accessed using value() and setValue().
|
||||||
|
* Otherwise, this class is an empty structure and value() just returns the template parameter Value.
|
||||||
|
*/
|
||||||
|
template<int Value> class ei_int_if_dynamic EIGEN_EMPTY_STRUCT
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
ei_int_if_dynamic() {}
|
||||||
|
explicit ei_int_if_dynamic(int) {}
|
||||||
|
static int value() { return Value; }
|
||||||
|
void setValue(int) {}
|
||||||
|
};
|
||||||
|
|
||||||
|
template<> class ei_int_if_dynamic<Dynamic>
|
||||||
|
{
|
||||||
|
int m_value;
|
||||||
|
ei_int_if_dynamic() {}
|
||||||
|
public:
|
||||||
|
explicit ei_int_if_dynamic(int value) : m_value(value) {}
|
||||||
|
int value() const { return m_value; }
|
||||||
|
void setValue(int value) { m_value = value; }
|
||||||
|
};
|
||||||
|
|
||||||
|
template<typename T> struct ei_functor_traits
|
||||||
|
{
|
||||||
|
enum
|
||||||
|
{
|
||||||
|
Cost = 10,
|
||||||
|
PacketAccess = false
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
template<typename T> struct ei_packet_traits
|
||||||
|
{
|
||||||
|
typedef T type;
|
||||||
|
enum {size=1};
|
||||||
|
};
|
||||||
|
|
||||||
|
template<typename T> struct ei_unpacket_traits
|
||||||
|
{
|
||||||
|
typedef T type;
|
||||||
|
enum {size=1};
|
||||||
|
};
|
||||||
|
|
||||||
|
template<typename Scalar, int Rows, int Cols, int Options, int MaxRows, int MaxCols>
|
||||||
|
class ei_compute_matrix_flags
|
||||||
|
{
|
||||||
|
enum {
|
||||||
|
row_major_bit = Options&RowMajor ? RowMajorBit : 0,
|
||||||
|
inner_max_size = int(MaxRows==1) ? int(MaxCols)
|
||||||
|
: int(MaxCols==1) ? int(MaxRows)
|
||||||
|
: int(row_major_bit) ? int(MaxCols) : int(MaxRows),
|
||||||
|
is_big = inner_max_size == Dynamic,
|
||||||
|
storage_has_fixed_size = MaxRows != Dynamic && MaxCols != Dynamic,
|
||||||
|
storage_has_aligned_fixed_size = storage_has_fixed_size
|
||||||
|
&& ( (MaxCols*MaxRows) % ei_packet_traits<Scalar>::size == 0 ),
|
||||||
|
aligned_bit = ( (Options&AutoAlign)
|
||||||
|
&& (is_big || storage_has_aligned_fixed_size)
|
||||||
|
) ? AlignedBit : 0,
|
||||||
|
packet_access_bit = ei_packet_traits<Scalar>::size > 1 && aligned_bit ? PacketAccessBit : 0
|
||||||
|
};
|
||||||
|
|
||||||
|
public:
|
||||||
|
enum { ret = LinearAccessBit | DirectAccessBit | packet_access_bit | row_major_bit | aligned_bit };
|
||||||
|
};
|
||||||
|
|
||||||
|
template<int _Rows, int _Cols> struct ei_size_at_compile_time
|
||||||
|
{
|
||||||
|
enum { ret = (_Rows==Dynamic || _Cols==Dynamic) ? Dynamic : _Rows * _Cols };
|
||||||
|
};
|
||||||
|
|
||||||
|
/* ei_eval : the return type of eval(). For matrices, this is just a const reference
|
||||||
|
* in order to avoid a useless copy
|
||||||
|
*/
|
||||||
|
|
||||||
|
template<typename T, int Sparseness = ei_traits<T>::Flags&SparseBit> class ei_eval;
|
||||||
|
|
||||||
|
template<typename T> struct ei_eval<T,IsDense>
|
||||||
|
{
|
||||||
|
typedef Matrix<typename ei_traits<T>::Scalar,
|
||||||
|
ei_traits<T>::RowsAtCompileTime,
|
||||||
|
ei_traits<T>::ColsAtCompileTime,
|
||||||
|
AutoAlign | (ei_traits<T>::Flags&RowMajorBit ? RowMajor : ColMajor),
|
||||||
|
ei_traits<T>::MaxRowsAtCompileTime,
|
||||||
|
ei_traits<T>::MaxColsAtCompileTime
|
||||||
|
> type;
|
||||||
|
};
|
||||||
|
|
||||||
|
// for matrices, no need to evaluate, just use a const reference to avoid a useless copy
|
||||||
|
template<typename _Scalar, int _Rows, int _Cols, int _StorageOrder, int _MaxRows, int _MaxCols>
|
||||||
|
struct ei_eval<Matrix<_Scalar, _Rows, _Cols, _StorageOrder, _MaxRows, _MaxCols>, IsDense>
|
||||||
|
{
|
||||||
|
typedef const Matrix<_Scalar, _Rows, _Cols, _StorageOrder, _MaxRows, _MaxCols>& type;
|
||||||
|
};
|
||||||
|
|
||||||
|
/* ei_plain_matrix_type : the difference from ei_eval is that ei_plain_matrix_type is always a plain matrix type,
|
||||||
|
* whereas ei_eval is a const reference in the case of a matrix
|
||||||
|
*/
|
||||||
|
template<typename T> struct ei_plain_matrix_type
|
||||||
|
{
|
||||||
|
typedef Matrix<typename ei_traits<T>::Scalar,
|
||||||
|
ei_traits<T>::RowsAtCompileTime,
|
||||||
|
ei_traits<T>::ColsAtCompileTime,
|
||||||
|
AutoAlign | (ei_traits<T>::Flags&RowMajorBit ? RowMajor : ColMajor),
|
||||||
|
ei_traits<T>::MaxRowsAtCompileTime,
|
||||||
|
ei_traits<T>::MaxColsAtCompileTime
|
||||||
|
> type;
|
||||||
|
};
|
||||||
|
|
||||||
|
/* ei_plain_matrix_type_column_major : same as ei_plain_matrix_type but guaranteed to be column-major
|
||||||
|
*/
|
||||||
|
template<typename T> struct ei_plain_matrix_type_column_major
|
||||||
|
{
|
||||||
|
typedef Matrix<typename ei_traits<T>::Scalar,
|
||||||
|
ei_traits<T>::RowsAtCompileTime,
|
||||||
|
ei_traits<T>::ColsAtCompileTime,
|
||||||
|
AutoAlign | ColMajor,
|
||||||
|
ei_traits<T>::MaxRowsAtCompileTime,
|
||||||
|
ei_traits<T>::MaxColsAtCompileTime
|
||||||
|
> type;
|
||||||
|
};
|
||||||
|
|
||||||
|
/* ei_plain_matrix_type_row_major : same as ei_plain_matrix_type but guaranteed to be row-major
|
||||||
|
*/
|
||||||
|
template<typename T> struct ei_plain_matrix_type_row_major
|
||||||
|
{
|
||||||
|
typedef Matrix<typename ei_traits<T>::Scalar,
|
||||||
|
ei_traits<T>::RowsAtCompileTime,
|
||||||
|
ei_traits<T>::ColsAtCompileTime,
|
||||||
|
AutoAlign | RowMajor,
|
||||||
|
ei_traits<T>::MaxRowsAtCompileTime,
|
||||||
|
ei_traits<T>::MaxColsAtCompileTime
|
||||||
|
> type;
|
||||||
|
};
|
||||||
|
|
||||||
|
template<typename T> struct ei_must_nest_by_value { enum { ret = false }; };
|
||||||
|
template<typename T> struct ei_must_nest_by_value<NestByValue<T> > { enum { ret = true }; };
|
||||||
|
|
||||||
|
/** \internal Determines how a given expression should be nested into another one.
|
||||||
|
* For example, when you do a * (b+c), Eigen will determine how the expression b+c should be
|
||||||
|
* nested into the bigger product expression. The choice is between nesting the expression b+c as-is, or
|
||||||
|
* evaluating that expression b+c into a temporary variable d, and nest d so that the resulting expression is
|
||||||
|
* a*d. Evaluating can be beneficial for example if every coefficient access in the resulting expression causes
|
||||||
|
* many coefficient accesses in the nested expressions -- as is the case with matrix product for example.
|
||||||
|
*
|
||||||
|
* \param T the type of the expression being nested
|
||||||
|
* \param n the number of coefficient accesses in the nested expression for each coefficient access in the bigger expression.
|
||||||
|
*
|
||||||
|
* Example. Suppose that a, b, and c are of type Matrix3d. The user forms the expression a*(b+c).
|
||||||
|
* b+c is an expression "sum of matrices", which we will denote by S. In order to determine how to nest it,
|
||||||
|
* the Product expression uses: ei_nested<S, 3>::ret, which turns out to be Matrix3d because the internal logic of
|
||||||
|
* ei_nested determined that in this case it was better to evaluate the expression b+c into a temporary. On the other hand,
|
||||||
|
* since a is of type Matrix3d, the Product expression nests it as ei_nested<Matrix3d, 3>::ret, which turns out to be
|
||||||
|
* const Matrix3d&, because the internal logic of ei_nested determined that since a was already a matrix, there was no point
|
||||||
|
* in copying it into another matrix.
|
||||||
|
*/
|
||||||
|
template<typename T, int n=1, typename PlainMatrixType = typename ei_eval<T>::type> struct ei_nested
|
||||||
|
{
|
||||||
|
enum {
|
||||||
|
CostEval = (n+1) * int(NumTraits<typename ei_traits<T>::Scalar>::ReadCost),
|
||||||
|
CostNoEval = (n-1) * int(ei_traits<T>::CoeffReadCost)
|
||||||
|
};
|
||||||
|
typedef typename ei_meta_if<
|
||||||
|
ei_must_nest_by_value<T>::ret,
|
||||||
|
T,
|
||||||
|
typename ei_meta_if<
|
||||||
|
(int(ei_traits<T>::Flags) & EvalBeforeNestingBit)
|
||||||
|
|| ( int(CostEval) <= int(CostNoEval) ),
|
||||||
|
PlainMatrixType,
|
||||||
|
const T&
|
||||||
|
>::ret
|
||||||
|
>::ret type;
|
||||||
|
};
|
||||||
|
|
||||||
|
template<unsigned int Flags> struct ei_are_flags_consistent
|
||||||
|
{
|
||||||
|
enum { ret = !( (Flags&UnitDiagBit && Flags&ZeroDiagBit) )
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
/** \internal Gives the type of a sub-matrix or sub-vector of a matrix of type \a ExpressionType and size \a Size
|
||||||
|
* TODO: could be a good idea to define a big ReturnType struct ??
|
||||||
|
*/
|
||||||
|
template<typename ExpressionType, int RowsOrSize=Dynamic, int Cols=Dynamic> struct BlockReturnType {
|
||||||
|
typedef Block<ExpressionType, (ei_traits<ExpressionType>::RowsAtCompileTime == 1 ? 1 : RowsOrSize),
|
||||||
|
(ei_traits<ExpressionType>::ColsAtCompileTime == 1 ? 1 : RowsOrSize)> SubVectorType;
|
||||||
|
typedef Block<ExpressionType, RowsOrSize, Cols> Type;
|
||||||
|
};
|
||||||
|
|
||||||
|
template<typename CurrentType, typename NewType> struct ei_cast_return_type
|
||||||
|
{
|
||||||
|
typedef typename ei_meta_if<ei_is_same_type<CurrentType,NewType>::ret,const CurrentType&,NewType>::ret type;
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif // EIGEN_XPRHELPER_H
|
Loading…
Reference in New Issue
Block a user