Just out of curiosity, if someone did this:
#if __INTEL__ //<-- I forget the actual macro
#define vpowf(a,b) vpowf(b,a)
#endif
Would their app break when Apple revved the OS?
Yeah, it'll break. We view this operand swapping as a bug, not legacy
that we intend to support until the end of time.
It is probably not unrealistic to require Intel users to update to
MacOS X.4.whatever for correct operation of your code on Intel, but
if you want to be soft on your users (or don't like the uncertainty
of hinging product release on Apple's bug fix schedule) then you'll
probably need to test for brokenness and then branch to either vpowf
or a wrapper that fixes up vpowf. A function pointer is probably the
way to go. I'm imagining something like the code below. You could
also do version testing on vecLib, except that it isn't known
precisely what the version number will be that fixes the problem.
vpowf is one of those functions that are expensive enough that the
cost of storing and loading vectors is trivial by comparison or even
free. If it is possible to fairly trivially reorganize your code to
use vvpowf instead, that might be the right choice since it should be
doing the right thing in all cases, and in many cases will be faster.
vpowf doesn't have enough data to operate as efficiently as one would
like. It is generally true of all of vMathLib that the vForce (that
is, "array") version should be faster, provided that you have enough
data (perhaps >16 floats) and tile intelligently to avoid cache
problems.
Ian
#include <Accelerate/Accelerate.h>
typedef vFloat (*vPowfPtr)(vFloat, vFloat );
//To be used on systems where the pow arguments are backwards
vFloat vPowfr( vFloat x, vFloat y) { return vpowf( y, x ); }
//Call to get the correct function pointer for a sane vpow
vPowfPtr GetvPowf( void )
{
#if defined( __ppc__ ) || defined( __ppc64__ )
return vpowf;
#else
static vPowfPtr vpowfptr = NULL;
int main( void )
{
vFloat a = (vFloat) { 2.0f, 2.0f, 2.0f, 2.0f };
vFloat b = (vFloat) { 0.5f, 0.5f, 0.5f, 0.5f };
vFloat c = vpowf( a, b );
vPowfPtr _pow = GetvPowf();
vFloat d = _pow( a, b );
int i;
//Should print the same number twice on PPC systems and fixed Intel
systems, but get it right only on the second line on broken Intel
systems
//Apologies for not completely Kosher code below:
printf( "pow(2,0.5) = %f, %f, %f, %f\n", ((float*)&c)[0], ((float*)
&c)[1], ((float*)&c)[2], ((float*)&c)[3] );
printf( "pow(2,0.5) = %f, %f, %f, %f\n", ((float*)&d)[0],
((float*)&d)[1], ((float*)&d)[2], ((float*)&d)[3] );