https://gcc.gnu.org/bugzilla/show_bug.cgi?id=79207
Bug ID: 79207
Summary: Special trigonometric simplification for solving
cubics with -ffast-math
Product: gcc
Version: 7.0
Status: UNCONFIRMED
Severity: enhancement
Priority: P3
Component: tree-optimization
Assignee: unassigned at gcc dot gnu.org
Reporter: tkoenig at gcc dot gnu.org
Target Milestone: ---
There is a special trigonometric identity that comes up
when solving cubic equations with three real roots
(see https://en.wikipedia.org/wiki/Cubic_function#Three_real_roots ).
The function
#include <math.h>
#define ONETHIRD (1./3.)
void c3(double alpha, double ret[3])
{
ret[0]=cos(alpha*ONETHIRD);
ret[1]=cos((alpha+2*M_PI)*ONETHIRD);
ret[2]=cos((alpha-2*M_PI)*ONETHIRD);
}
could be transformed to
#include <math.h>
#define ONETHIRD (1./3.)
void c3(double alpha, double ret[3])
{
double t_a, t_cos, t_sin, t_ss3;
t_a = alpha * ONETHIRD;
__builtin_sincos(t_a, &t_sin, &t_cos);
ret[0] = t_cos;
t_ss3 = t_sin * sqrt(3.);
ret[1] = -0.5 * (t_ss3 + t_cos);
ret[2] = 0.5 * (t_ss3 - t_cos);
}
replacing three calls to cos with one call to __builtin_sincos.
Of course, it could also be argued that this is an extremely
specialized case. Still, I suspect that people who calculate
solutions to cubic equations a lot (which, for example, happens
in real gas equations of state), or who calculate eigenvalues
and eigenvectors of 3*3 tensors, might be pleasantly surprised if
their codes suddenly start running much faster.