00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023 #include "libavcodec/dsputil.h"
00024
00025 #include "gcc_fixes.h"
00026
00027 #include "dsputil_ppc.h"
00028 #include "util_altivec.h"
00040 void ff_fft_calc_altivec(FFTContext *s, FFTComplex *z)
00041 {
00042 POWERPC_PERF_DECLARE(altivec_fft_num, s->nbits >= 6);
00043 register const vector float vczero = (const vector float)vec_splat_u32(0.);
00044
00045 int ln = s->nbits;
00046 int j, np, np2;
00047 int nblocks, nloops;
00048 register FFTComplex *p, *q;
00049 FFTComplex *cptr, *cptr1;
00050 int k;
00051
00052 POWERPC_PERF_START_COUNT(altivec_fft_num, s->nbits >= 6);
00053
00054 np = 1 << ln;
00055
00056 {
00057 vector float *r, a, b, a1, c1, c2;
00058
00059 r = (vector float *)&z[0];
00060
00061 c1 = vcii(p,p,n,n);
00062
00063 if (s->inverse) {
00064 c2 = vcii(p,p,n,p);
00065 } else {
00066 c2 = vcii(p,p,p,n);
00067 }
00068
00069 j = (np >> 2);
00070 do {
00071 a = vec_ld(0, r);
00072 a1 = vec_ld(sizeof(vector float), r);
00073
00074 b = vec_perm(a,a,vcprmle(1,0,3,2));
00075 a = vec_madd(a,c1,b);
00076
00077
00078 b = vec_perm(a1,a1,vcprmle(1,0,3,2));
00079 b = vec_madd(a1,c1,b);
00080
00081
00082
00083 b = vec_perm(b,b,vcprmle(2,3,1,0));
00084
00085
00086 vec_st(vec_madd(b,c2,a), 0, r);
00087 vec_st(vec_nmsub(b,c2,a), sizeof(vector float), r);
00088
00089 r += 2;
00090 } while (--j != 0);
00091 }
00092
00093
00094 nblocks = np >> 3;
00095 nloops = 1 << 2;
00096 np2 = np >> 1;
00097
00098 cptr1 = s->exptab1;
00099 do {
00100 p = z;
00101 q = z + nloops;
00102 j = nblocks;
00103 do {
00104 cptr = cptr1;
00105 k = nloops >> 1;
00106 do {
00107 vector float a,b,c,t1;
00108
00109 a = vec_ld(0, (float*)p);
00110 b = vec_ld(0, (float*)q);
00111
00112
00113 c = vec_ld(0, (float*)cptr);
00114
00115 t1 = vec_madd(c, vec_perm(b,b,vcprmle(2,2,0,0)),vczero);
00116 c = vec_ld(sizeof(vector float), (float*)cptr);
00117
00118 b = vec_madd(c, vec_perm(b,b,vcprmle(3,3,1,1)),t1);
00119
00120
00121 vec_st(vec_add(a,b), 0, (float*)p);
00122 vec_st(vec_sub(a,b), 0, (float*)q);
00123
00124 p += 2;
00125 q += 2;
00126 cptr += 4;
00127 } while (--k);
00128
00129 p += nloops;
00130 q += nloops;
00131 } while (--j);
00132 cptr1 += nloops * 2;
00133 nblocks = nblocks >> 1;
00134 nloops = nloops << 1;
00135 } while (nblocks != 0);
00136
00137 POWERPC_PERF_STOP_COUNT(altivec_fft_num, s->nbits >= 6);
00138 }