Math: optimizations for 4x4x matrix inverse, multiplications.

In some heavy rigs matrix inverse can be 10% of computation time. This
reduces it to 2% by using Eigen's optimized 4x4 matrix inverse and SSE
matrix multiplication.
This commit is contained in:
Brecht Van Lommel
2018-05-31 16:36:20 +02:00
parent 719e782f2c
commit 01c75c3765
7 changed files with 128 additions and 66 deletions

View File

@@ -36,10 +36,12 @@ set(SRC
intern/eigenvalues.cc
intern/linear_solver.cc
intern/matrix.cc
intern/svd.cc
intern/eigenvalues.h
intern/linear_solver.h
intern/matrix.h
intern/svd.h
)

View File

@@ -29,6 +29,7 @@
#include "intern/eigenvalues.h"
#include "intern/linear_solver.h"
#include "intern/matrix.h"
#include "intern/svd.h"
#endif /* __EIGEN_C_API_H__ */

View File

@@ -0,0 +1,56 @@
/*
* ***** BEGIN GPL LICENSE BLOCK *****
*
* This program is free software; 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.
*
* This program 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 General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software Foundation,
* Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*
* The Original Code is Copyright (C) 2015 Blender Foundation.
* All rights reserved.
*
* Contributor(s): Blender Foundation,
* Bastien Montagne
*
* ***** END GPL LICENSE BLOCK *****
*/
#ifndef __EIGEN3_MATRIX_C_API_CC__
#define __EIGEN3_MATRIX_C_API_CC__
/* Eigen gives annoying huge amount of warnings here, silence them! */
#if defined(__GNUC__) && !defined(__clang__)
# pragma GCC diagnostic ignored "-Wlogical-op"
#endif
#ifdef __EIGEN3_MATRIX_C_API_CC__ /* quiet warning */
#endif
#include <Eigen/Core>
#include <Eigen/Dense>
#include "matrix.h"
using Eigen::Map;
using Eigen::Matrix4f;
bool EIG_invert_m4_m4(float inverse[4][4], const float matrix[4][4])
{
Map<Matrix4f> M = Map<Matrix4f>((float*)matrix);
Matrix4f R;
bool invertible = true;
M.computeInverseWithCheck(R, invertible, 0.0f);
memcpy(inverse, R.data(), sizeof(float)*4*4);
return invertible;
}
#endif /* __EIGEN3_MATRIX_C_API_CC__ */

View File

@@ -0,0 +1,40 @@
/*
* ***** BEGIN GPL LICENSE BLOCK *****
*
* This program is free software; 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.
*
* This program 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 General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software Foundation,
* Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*
* The Original Code is Copyright (C) 2015 Blender Foundation.
* All rights reserved.
*
* Contributor(s): Blender Foundation,
* Bastien Montagne
*
* ***** END GPL LICENSE BLOCK *****
*/
#ifndef __EIGEN3_MATRIX_C_API_H__
#define __EIGEN3_MATRIX_C_API_H__
#ifdef __cplusplus
extern "C" {
#endif
bool EIG_invert_m4_m4(float inverse[4][4], const float matrix[4][4]);
#ifdef __cplusplus
}
#endif
#endif /* __EIGEN3_MATRIX_C_API_H__ */

View File

@@ -37,6 +37,7 @@
#include <Eigen/Core>
#include <Eigen/SVD>
#include <Eigen/Dense>
#include "svd.h"
@@ -51,6 +52,8 @@ using Eigen::MatrixXf;
using Eigen::VectorXf;
using Eigen::Map;
using Eigen::Matrix4f;
void EIG_svd_square_matrix(const int size, const float *matrix, float *r_U, float *r_S, float *r_V)
{
/* Since our matrix is squared, we can use thinU/V. */