fft4g.h 36 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214121512161217121812191220122112221223122412251226122712281229123012311232123312341235123612371238123912401241124212431244124512461247124812491250125112521253125412551256125712581259126012611262126312641265126612671268126912701271127212731274127512761277127812791280128112821283128412851286128712881289129012911292129312941295129612971298129913001301130213031304130513061307130813091310131113121313131413151316
  1. //$ nobt
  2. //$ nocpp
  3. /**
  4. * @file fft4g.h
  5. *
  6. * @brief Wrapper class for Takuya OOURA's FFT functions.
  7. *
  8. * Functions from the FFT package by: Copyright(C) 1996-2001 Takuya OOURA
  9. * http://www.kurims.kyoto-u.ac.jp/~ooura/fft.html
  10. *
  11. * Modified and used with permission granted by the license.
  12. *
  13. * Here, the original "fft4g.c" file was wrapped into the "ooura_fft" class.
  14. */
  15. #ifndef R8B_FFT4G_INCLUDED
  16. #define R8B_FFT4G_INCLUDED
  17. /*
  18. Fast Fourier/Cosine/Sine Transform
  19. dimension :one
  20. data length :power of 2
  21. decimation :frequency
  22. radix :4, 2
  23. data :inplace
  24. table :use
  25. functions
  26. cdft: Complex Discrete Fourier Transform
  27. rdft: Real Discrete Fourier Transform
  28. ddct: Discrete Cosine Transform
  29. ddst: Discrete Sine Transform
  30. dfct: Cosine Transform of RDFT (Real Symmetric DFT)
  31. dfst: Sine Transform of RDFT (Real Anti-symmetric DFT)
  32. function prototypes
  33. void cdft(int, int, FPType *, int *, FPType *);
  34. void rdft(int, int, FPType *, int *, FPType *);
  35. void ddct(int, int, FPType *, int *, FPType *);
  36. void ddst(int, int, FPType *, int *, FPType *);
  37. void dfct(int, FPType *, FPType *, int *, FPType *);
  38. void dfst(int, FPType *, FPType *, int *, FPType *);
  39. -------- Complex DFT (Discrete Fourier Transform) --------
  40. [definition]
  41. <case1>
  42. X[k] = sum_j=0^n-1 x[j]*exp(2*pi*i*j*k/n), 0<=k<n
  43. <case2>
  44. X[k] = sum_j=0^n-1 x[j]*exp(-2*pi*i*j*k/n), 0<=k<n
  45. (notes: sum_j=0^n-1 is a summation from j=0 to n-1)
  46. [usage]
  47. <case1>
  48. ip[0] = 0; // first time only
  49. cdft(2*n, 1, a, ip, w);
  50. <case2>
  51. ip[0] = 0; // first time only
  52. cdft(2*n, -1, a, ip, w);
  53. [parameters]
  54. 2*n :data length (int)
  55. n >= 1, n = power of 2
  56. a[0...2*n-1] :input/output data (FPType *)
  57. input data
  58. a[2*j] = Re(x[j]),
  59. a[2*j+1] = Im(x[j]), 0<=j<n
  60. output data
  61. a[2*k] = Re(X[k]),
  62. a[2*k+1] = Im(X[k]), 0<=k<n
  63. ip[0...*] :work area for bit reversal (int *)
  64. length of ip >= 2+sqrt(n)
  65. strictly,
  66. length of ip >=
  67. 2+(1<<(int)(log(n+0.5)/log(2))/2).
  68. ip[0],ip[1] are pointers of the cos/sin table.
  69. w[0...n/2-1] :cos/sin table (FPType *)
  70. w[],ip[] are initialized if ip[0] == 0.
  71. [remark]
  72. Inverse of
  73. cdft(2*n, -1, a, ip, w);
  74. is
  75. cdft(2*n, 1, a, ip, w);
  76. for (j = 0; j <= 2 * n - 1; j++) {
  77. a[j] *= 1.0 / n;
  78. }
  79. .
  80. -------- Real DFT / Inverse of Real DFT --------
  81. [definition]
  82. <case1> RDFT
  83. R[k] = sum_j=0^n-1 a[j]*cos(2*pi*j*k/n), 0<=k<=n/2
  84. I[k] = sum_j=0^n-1 a[j]*sin(2*pi*j*k/n), 0<k<n/2
  85. <case2> IRDFT (excluding scale)
  86. a[k] = (R[0] + R[n/2]*cos(pi*k))/2 +
  87. sum_j=1^n/2-1 R[j]*cos(2*pi*j*k/n) +
  88. sum_j=1^n/2-1 I[j]*sin(2*pi*j*k/n), 0<=k<n
  89. [usage]
  90. <case1>
  91. ip[0] = 0; // first time only
  92. rdft(n, 1, a, ip, w);
  93. <case2>
  94. ip[0] = 0; // first time only
  95. rdft(n, -1, a, ip, w);
  96. [parameters]
  97. n :data length (int)
  98. n >= 2, n = power of 2
  99. a[0...n-1] :input/output data (FPType *)
  100. <case1>
  101. output data
  102. a[2*k] = R[k], 0<=k<n/2
  103. a[2*k+1] = I[k], 0<k<n/2
  104. a[1] = R[n/2]
  105. <case2>
  106. input data
  107. a[2*j] = R[j], 0<=j<n/2
  108. a[2*j+1] = I[j], 0<j<n/2
  109. a[1] = R[n/2]
  110. ip[0...*] :work area for bit reversal (int *)
  111. length of ip >= 2+sqrt(n/2)
  112. strictly,
  113. length of ip >=
  114. 2+(1<<(int)(log(n/2+0.5)/log(2))/2).
  115. ip[0],ip[1] are pointers of the cos/sin table.
  116. w[0...n/2-1] :cos/sin table (FPType *)
  117. w[],ip[] are initialized if ip[0] == 0.
  118. [remark]
  119. Inverse of
  120. rdft(n, 1, a, ip, w);
  121. is
  122. rdft(n, -1, a, ip, w);
  123. for (j = 0; j <= n - 1; j++) {
  124. a[j] *= 2.0 / n;
  125. }
  126. .
  127. -------- DCT (Discrete Cosine Transform) / Inverse of DCT --------
  128. [definition]
  129. <case1> IDCT (excluding scale)
  130. C[k] = sum_j=0^n-1 a[j]*cos(pi*j*(k+1/2)/n), 0<=k<n
  131. <case2> DCT
  132. C[k] = sum_j=0^n-1 a[j]*cos(pi*(j+1/2)*k/n), 0<=k<n
  133. [usage]
  134. <case1>
  135. ip[0] = 0; // first time only
  136. ddct(n, 1, a, ip, w);
  137. <case2>
  138. ip[0] = 0; // first time only
  139. ddct(n, -1, a, ip, w);
  140. [parameters]
  141. n :data length (int)
  142. n >= 2, n = power of 2
  143. a[0...n-1] :input/output data (FPType *)
  144. output data
  145. a[k] = C[k], 0<=k<n
  146. ip[0...*] :work area for bit reversal (int *)
  147. length of ip >= 2+sqrt(n/2)
  148. strictly,
  149. length of ip >=
  150. 2+(1<<(int)(log(n/2+0.5)/log(2))/2).
  151. ip[0],ip[1] are pointers of the cos/sin table.
  152. w[0...n*5/4-1] :cos/sin table (FPType *)
  153. w[],ip[] are initialized if ip[0] == 0.
  154. [remark]
  155. Inverse of
  156. ddct(n, -1, a, ip, w);
  157. is
  158. a[0] *= 0.5;
  159. ddct(n, 1, a, ip, w);
  160. for (j = 0; j <= n - 1; j++) {
  161. a[j] *= 2.0 / n;
  162. }
  163. .
  164. -------- DST (Discrete Sine Transform) / Inverse of DST --------
  165. [definition]
  166. <case1> IDST (excluding scale)
  167. S[k] = sum_j=1^n A[j]*sin(pi*j*(k+1/2)/n), 0<=k<n
  168. <case2> DST
  169. S[k] = sum_j=0^n-1 a[j]*sin(pi*(j+1/2)*k/n), 0<k<=n
  170. [usage]
  171. <case1>
  172. ip[0] = 0; // first time only
  173. ddst(n, 1, a, ip, w);
  174. <case2>
  175. ip[0] = 0; // first time only
  176. ddst(n, -1, a, ip, w);
  177. [parameters]
  178. n :data length (int)
  179. n >= 2, n = power of 2
  180. a[0...n-1] :input/output data (FPType *)
  181. <case1>
  182. input data
  183. a[j] = A[j], 0<j<n
  184. a[0] = A[n]
  185. output data
  186. a[k] = S[k], 0<=k<n
  187. <case2>
  188. output data
  189. a[k] = S[k], 0<k<n
  190. a[0] = S[n]
  191. ip[0...*] :work area for bit reversal (int *)
  192. length of ip >= 2+sqrt(n/2)
  193. strictly,
  194. length of ip >=
  195. 2+(1<<(int)(log(n/2+0.5)/log(2))/2).
  196. ip[0],ip[1] are pointers of the cos/sin table.
  197. w[0...n*5/4-1] :cos/sin table (FPType *)
  198. w[],ip[] are initialized if ip[0] == 0.
  199. [remark]
  200. Inverse of
  201. ddst(n, -1, a, ip, w);
  202. is
  203. a[0] *= 0.5;
  204. ddst(n, 1, a, ip, w);
  205. for (j = 0; j <= n - 1; j++) {
  206. a[j] *= 2.0 / n;
  207. }
  208. .
  209. -------- Cosine Transform of RDFT (Real Symmetric DFT) --------
  210. [definition]
  211. C[k] = sum_j=0^n a[j]*cos(pi*j*k/n), 0<=k<=n
  212. [usage]
  213. ip[0] = 0; // first time only
  214. dfct(n, a, t, ip, w);
  215. [parameters]
  216. n :data length - 1 (int)
  217. n >= 2, n = power of 2
  218. a[0...n] :input/output data (FPType *)
  219. output data
  220. a[k] = C[k], 0<=k<=n
  221. t[0...n/2] :work area (FPType *)
  222. ip[0...*] :work area for bit reversal (int *)
  223. length of ip >= 2+sqrt(n/4)
  224. strictly,
  225. length of ip >=
  226. 2+(1<<(int)(log(n/4+0.5)/log(2))/2).
  227. ip[0],ip[1] are pointers of the cos/sin table.
  228. w[0...n*5/8-1] :cos/sin table (FPType *)
  229. w[],ip[] are initialized if ip[0] == 0.
  230. [remark]
  231. Inverse of
  232. a[0] *= 0.5;
  233. a[n] *= 0.5;
  234. dfct(n, a, t, ip, w);
  235. is
  236. a[0] *= 0.5;
  237. a[n] *= 0.5;
  238. dfct(n, a, t, ip, w);
  239. for (j = 0; j <= n; j++) {
  240. a[j] *= 2.0 / n;
  241. }
  242. .
  243. -------- Sine Transform of RDFT (Real Anti-symmetric DFT) --------
  244. [definition]
  245. S[k] = sum_j=1^n-1 a[j]*sin(pi*j*k/n), 0<k<n
  246. [usage]
  247. ip[0] = 0; // first time only
  248. dfst(n, a, t, ip, w);
  249. [parameters]
  250. n :data length + 1 (int)
  251. n >= 2, n = power of 2
  252. a[0...n-1] :input/output data (FPType *)
  253. output data
  254. a[k] = S[k], 0<k<n
  255. (a[0] is used for work area)
  256. t[0...n/2-1] :work area (FPType *)
  257. ip[0...*] :work area for bit reversal (int *)
  258. length of ip >= 2+sqrt(n/4)
  259. strictly,
  260. length of ip >=
  261. 2+(1<<(int)(log(n/4+0.5)/log(2))/2).
  262. ip[0],ip[1] are pointers of the cos/sin table.
  263. w[0...n*5/8-1] :cos/sin table (FPType *)
  264. w[],ip[] are initialized if ip[0] == 0.
  265. [remark]
  266. Inverse of
  267. dfst(n, a, t, ip, w);
  268. is
  269. dfst(n, a, t, ip, w);
  270. for (j = 1; j <= n - 1; j++) {
  271. a[j] *= 2.0 / n;
  272. }
  273. .
  274. Appendix :
  275. The cos/sin table is recalculated when the larger table required.
  276. w[] and ip[] are compatible with all routines.
  277. */
  278. namespace r8b {
  279. /**
  280. * @brief A wrapper class around Takuya OOURA's FFT functions.
  281. *
  282. * A wrapper class around fft4g.c file's FFT functions by Takuya OOURA.
  283. * Provides static private functions for use by the CDSPRealFFT class.
  284. */
  285. class ooura_fft
  286. {
  287. friend class CDSPRealFFT;
  288. private:
  289. typedef double FPType;
  290. static void cdft(int n, int isgn, FPType *a, int *ip, FPType *w)
  291. {
  292. if (n > (ip[0] << 2)) {
  293. makewt(n >> 2, ip, w);
  294. }
  295. if (n > 4) {
  296. if (isgn >= 0) {
  297. bitrv2(n, ip + 2, a);
  298. cftfsub(n, a, w);
  299. } else {
  300. bitrv2conj(n, ip + 2, a);
  301. cftbsub(n, a, w);
  302. }
  303. } else if (n == 4) {
  304. cftfsub(n, a, w);
  305. }
  306. }
  307. static void rdft(int n, int isgn, FPType *a, int *ip, FPType *w)
  308. {
  309. int nw, nc;
  310. double xi;
  311. nw = ip[0];
  312. if (n > (nw << 2)) {
  313. nw = n >> 2;
  314. makewt(nw, ip, w);
  315. }
  316. nc = ip[1];
  317. if (n > (nc << 2)) {
  318. nc = n >> 2;
  319. makect(nc, ip, w + nw);
  320. }
  321. if (isgn >= 0) {
  322. if (n > 4) {
  323. bitrv2(n, ip + 2, a);
  324. cftfsub(n, a, w);
  325. rftfsub(n, a, nc, w + nw);
  326. } else if (n == 4) {
  327. cftfsub(n, a, w);
  328. }
  329. xi = a[0] - a[1];
  330. a[0] += a[1];
  331. a[1] = xi;
  332. } else {
  333. a[1] = 0.5 * (a[0] - a[1]);
  334. a[0] -= a[1];
  335. if (n > 4) {
  336. rftbsub(n, a, nc, w + nw);
  337. bitrv2(n, ip + 2, a);
  338. cftbsub(n, a, w);
  339. } else if (n == 4) {
  340. cftfsub(n, a, w);
  341. }
  342. }
  343. }
  344. static void ddct(int n, int isgn, FPType *a, int *ip, FPType *w)
  345. {
  346. int j, nw, nc;
  347. double xr;
  348. nw = ip[0];
  349. if (n > (nw << 2)) {
  350. nw = n >> 2;
  351. makewt(nw, ip, w);
  352. }
  353. nc = ip[1];
  354. if (n > nc) {
  355. nc = n;
  356. makect(nc, ip, w + nw);
  357. }
  358. if (isgn < 0) {
  359. xr = a[n - 1];
  360. for (j = n - 2; j >= 2; j -= 2) {
  361. a[j + 1] = a[j] - a[j - 1];
  362. a[j] += a[j - 1];
  363. }
  364. a[1] = a[0] - xr;
  365. a[0] += xr;
  366. if (n > 4) {
  367. rftbsub(n, a, nc, w + nw);
  368. bitrv2(n, ip + 2, a);
  369. cftbsub(n, a, w);
  370. } else if (n == 4) {
  371. cftfsub(n, a, w);
  372. }
  373. }
  374. dctsub(n, a, nc, w + nw);
  375. if (isgn >= 0) {
  376. if (n > 4) {
  377. bitrv2(n, ip + 2, a);
  378. cftfsub(n, a, w);
  379. rftfsub(n, a, nc, w + nw);
  380. } else if (n == 4) {
  381. cftfsub(n, a, w);
  382. }
  383. xr = a[0] - a[1];
  384. a[0] += a[1];
  385. for (j = 2; j < n; j += 2) {
  386. a[j - 1] = a[j] - a[j + 1];
  387. a[j] += a[j + 1];
  388. }
  389. a[n - 1] = xr;
  390. }
  391. }
  392. static void ddst(int n, int isgn, FPType *a, int *ip, FPType *w)
  393. {
  394. int j, nw, nc;
  395. double xr;
  396. nw = ip[0];
  397. if (n > (nw << 2)) {
  398. nw = n >> 2;
  399. makewt(nw, ip, w);
  400. }
  401. nc = ip[1];
  402. if (n > nc) {
  403. nc = n;
  404. makect(nc, ip, w + nw);
  405. }
  406. if (isgn < 0) {
  407. xr = a[n - 1];
  408. for (j = n - 2; j >= 2; j -= 2) {
  409. a[j + 1] = -a[j] - a[j - 1];
  410. a[j] -= a[j - 1];
  411. }
  412. a[1] = a[0] + xr;
  413. a[0] -= xr;
  414. if (n > 4) {
  415. rftbsub(n, a, nc, w + nw);
  416. bitrv2(n, ip + 2, a);
  417. cftbsub(n, a, w);
  418. } else if (n == 4) {
  419. cftfsub(n, a, w);
  420. }
  421. }
  422. dstsub(n, a, nc, w + nw);
  423. if (isgn >= 0) {
  424. if (n > 4) {
  425. bitrv2(n, ip + 2, a);
  426. cftfsub(n, a, w);
  427. rftfsub(n, a, nc, w + nw);
  428. } else if (n == 4) {
  429. cftfsub(n, a, w);
  430. }
  431. xr = a[0] - a[1];
  432. a[0] += a[1];
  433. for (j = 2; j < n; j += 2) {
  434. a[j - 1] = -a[j] - a[j + 1];
  435. a[j] -= a[j + 1];
  436. }
  437. a[n - 1] = -xr;
  438. }
  439. }
  440. static void dfct(int n, FPType *a, FPType *t, int *ip, FPType *w)
  441. {
  442. int j, k, l, m, mh, nw, nc;
  443. double xr, xi, yr, yi;
  444. nw = ip[0];
  445. if (n > (nw << 3)) {
  446. nw = n >> 3;
  447. makewt(nw, ip, w);
  448. }
  449. nc = ip[1];
  450. if (n > (nc << 1)) {
  451. nc = n >> 1;
  452. makect(nc, ip, w + nw);
  453. }
  454. m = n >> 1;
  455. yi = a[m];
  456. xi = a[0] + a[n];
  457. a[0] -= a[n];
  458. t[0] = xi - yi;
  459. t[m] = xi + yi;
  460. if (n > 2) {
  461. mh = m >> 1;
  462. for (j = 1; j < mh; j++) {
  463. k = m - j;
  464. xr = a[j] - a[n - j];
  465. xi = a[j] + a[n - j];
  466. yr = a[k] - a[n - k];
  467. yi = a[k] + a[n - k];
  468. a[j] = xr;
  469. a[k] = yr;
  470. t[j] = xi - yi;
  471. t[k] = xi + yi;
  472. }
  473. t[mh] = a[mh] + a[n - mh];
  474. a[mh] -= a[n - mh];
  475. dctsub(m, a, nc, w + nw);
  476. if (m > 4) {
  477. bitrv2(m, ip + 2, a);
  478. cftfsub(m, a, w);
  479. rftfsub(m, a, nc, w + nw);
  480. } else if (m == 4) {
  481. cftfsub(m, a, w);
  482. }
  483. a[n - 1] = a[0] - a[1];
  484. a[1] = a[0] + a[1];
  485. for (j = m - 2; j >= 2; j -= 2) {
  486. a[2 * j + 1] = a[j] + a[j + 1];
  487. a[2 * j - 1] = a[j] - a[j + 1];
  488. }
  489. l = 2;
  490. m = mh;
  491. while (m >= 2) {
  492. dctsub(m, t, nc, w + nw);
  493. if (m > 4) {
  494. bitrv2(m, ip + 2, t);
  495. cftfsub(m, t, w);
  496. rftfsub(m, t, nc, w + nw);
  497. } else if (m == 4) {
  498. cftfsub(m, t, w);
  499. }
  500. a[n - l] = t[0] - t[1];
  501. a[l] = t[0] + t[1];
  502. k = 0;
  503. for (j = 2; j < m; j += 2) {
  504. k += l << 2;
  505. a[k - l] = t[j] - t[j + 1];
  506. a[k + l] = t[j] + t[j + 1];
  507. }
  508. l <<= 1;
  509. mh = m >> 1;
  510. for (j = 0; j < mh; j++) {
  511. k = m - j;
  512. t[j] = t[m + k] - t[m + j];
  513. t[k] = t[m + k] + t[m + j];
  514. }
  515. t[mh] = t[m + mh];
  516. m = mh;
  517. }
  518. a[l] = t[0];
  519. a[n] = t[2] - t[1];
  520. a[0] = t[2] + t[1];
  521. } else {
  522. a[1] = a[0];
  523. a[2] = t[0];
  524. a[0] = t[1];
  525. }
  526. }
  527. static void dfst(int n, FPType *a, FPType *t, int *ip, FPType *w)
  528. {
  529. int j, k, l, m, mh, nw, nc;
  530. double xr, xi, yr, yi;
  531. nw = ip[0];
  532. if (n > (nw << 3)) {
  533. nw = n >> 3;
  534. makewt(nw, ip, w);
  535. }
  536. nc = ip[1];
  537. if (n > (nc << 1)) {
  538. nc = n >> 1;
  539. makect(nc, ip, w + nw);
  540. }
  541. if (n > 2) {
  542. m = n >> 1;
  543. mh = m >> 1;
  544. for (j = 1; j < mh; j++) {
  545. k = m - j;
  546. xr = a[j] + a[n - j];
  547. xi = a[j] - a[n - j];
  548. yr = a[k] + a[n - k];
  549. yi = a[k] - a[n - k];
  550. a[j] = xr;
  551. a[k] = yr;
  552. t[j] = xi + yi;
  553. t[k] = xi - yi;
  554. }
  555. t[0] = a[mh] - a[n - mh];
  556. a[mh] += a[n - mh];
  557. a[0] = a[m];
  558. dstsub(m, a, nc, w + nw);
  559. if (m > 4) {
  560. bitrv2(m, ip + 2, a);
  561. cftfsub(m, a, w);
  562. rftfsub(m, a, nc, w + nw);
  563. } else if (m == 4) {
  564. cftfsub(m, a, w);
  565. }
  566. a[n - 1] = a[1] - a[0];
  567. a[1] = a[0] + a[1];
  568. for (j = m - 2; j >= 2; j -= 2) {
  569. a[2 * j + 1] = a[j] - a[j + 1];
  570. a[2 * j - 1] = -a[j] - a[j + 1];
  571. }
  572. l = 2;
  573. m = mh;
  574. while (m >= 2) {
  575. dstsub(m, t, nc, w + nw);
  576. if (m > 4) {
  577. bitrv2(m, ip + 2, t);
  578. cftfsub(m, t, w);
  579. rftfsub(m, t, nc, w + nw);
  580. } else if (m == 4) {
  581. cftfsub(m, t, w);
  582. }
  583. a[n - l] = t[1] - t[0];
  584. a[l] = t[0] + t[1];
  585. k = 0;
  586. for (j = 2; j < m; j += 2) {
  587. k += l << 2;
  588. a[k - l] = -t[j] - t[j + 1];
  589. a[k + l] = t[j] - t[j + 1];
  590. }
  591. l <<= 1;
  592. mh = m >> 1;
  593. for (j = 1; j < mh; j++) {
  594. k = m - j;
  595. t[j] = t[m + k] + t[m + j];
  596. t[k] = t[m + k] - t[m + j];
  597. }
  598. t[0] = t[m + mh];
  599. m = mh;
  600. }
  601. a[l] = t[0];
  602. }
  603. a[0] = 0;
  604. }
  605. /* -------- initializing routines -------- */
  606. static void makewt(int nw, int *ip, FPType *w)
  607. {
  608. int j, nwh;
  609. double delta, x, y;
  610. ip[0] = nw;
  611. ip[1] = 1;
  612. if (nw > 2) {
  613. nwh = nw >> 1;
  614. delta = atan(1.0) / nwh;
  615. w[0] = 1;
  616. w[1] = 0;
  617. w[nwh] = cos(delta * nwh);
  618. w[nwh + 1] = w[nwh];
  619. if (nwh > 2) {
  620. for (j = 2; j < nwh; j += 2) {
  621. x = cos(delta * j);
  622. y = sin(delta * j);
  623. w[j] = x;
  624. w[j + 1] = y;
  625. w[nw - j] = y;
  626. w[nw - j + 1] = x;
  627. }
  628. bitrv2(nw, ip + 2, w);
  629. }
  630. }
  631. }
  632. static void makect(int nc, int *ip, FPType *c)
  633. {
  634. int j, nch;
  635. double delta;
  636. ip[1] = nc;
  637. if (nc > 1) {
  638. nch = nc >> 1;
  639. delta = atan(1.0) / nch;
  640. c[0] = cos(delta * nch);
  641. c[nch] = 0.5 * c[0];
  642. for (j = 1; j < nch; j++) {
  643. c[j] = 0.5 * cos(delta * j);
  644. c[nc - j] = 0.5 * sin(delta * j);
  645. }
  646. }
  647. }
  648. /* -------- child routines -------- */
  649. static void bitrv2(int n, int *ip, FPType *a)
  650. {
  651. int j, j1, k, k1, l, m, m2;
  652. double xr, xi, yr, yi;
  653. ip[0] = 0;
  654. l = n;
  655. m = 1;
  656. while ((m << 3) < l) {
  657. l >>= 1;
  658. for (j = 0; j < m; j++) {
  659. ip[m + j] = ip[j] + l;
  660. }
  661. m <<= 1;
  662. }
  663. m2 = 2 * m;
  664. if ((m << 3) == l) {
  665. for (k = 0; k < m; k++) {
  666. for (j = 0; j < k; j++) {
  667. j1 = 2 * j + ip[k];
  668. k1 = 2 * k + ip[j];
  669. xr = a[j1];
  670. xi = a[j1 + 1];
  671. yr = a[k1];
  672. yi = a[k1 + 1];
  673. a[j1] = yr;
  674. a[j1 + 1] = yi;
  675. a[k1] = xr;
  676. a[k1 + 1] = xi;
  677. j1 += m2;
  678. k1 += 2 * m2;
  679. xr = a[j1];
  680. xi = a[j1 + 1];
  681. yr = a[k1];
  682. yi = a[k1 + 1];
  683. a[j1] = yr;
  684. a[j1 + 1] = yi;
  685. a[k1] = xr;
  686. a[k1 + 1] = xi;
  687. j1 += m2;
  688. k1 -= m2;
  689. xr = a[j1];
  690. xi = a[j1 + 1];
  691. yr = a[k1];
  692. yi = a[k1 + 1];
  693. a[j1] = yr;
  694. a[j1 + 1] = yi;
  695. a[k1] = xr;
  696. a[k1 + 1] = xi;
  697. j1 += m2;
  698. k1 += 2 * m2;
  699. xr = a[j1];
  700. xi = a[j1 + 1];
  701. yr = a[k1];
  702. yi = a[k1 + 1];
  703. a[j1] = yr;
  704. a[j1 + 1] = yi;
  705. a[k1] = xr;
  706. a[k1 + 1] = xi;
  707. }
  708. j1 = 2 * k + m2 + ip[k];
  709. k1 = j1 + m2;
  710. xr = a[j1];
  711. xi = a[j1 + 1];
  712. yr = a[k1];
  713. yi = a[k1 + 1];
  714. a[j1] = yr;
  715. a[j1 + 1] = yi;
  716. a[k1] = xr;
  717. a[k1 + 1] = xi;
  718. }
  719. } else {
  720. for (k = 1; k < m; k++) {
  721. for (j = 0; j < k; j++) {
  722. j1 = 2 * j + ip[k];
  723. k1 = 2 * k + ip[j];
  724. xr = a[j1];
  725. xi = a[j1 + 1];
  726. yr = a[k1];
  727. yi = a[k1 + 1];
  728. a[j1] = yr;
  729. a[j1 + 1] = yi;
  730. a[k1] = xr;
  731. a[k1 + 1] = xi;
  732. j1 += m2;
  733. k1 += m2;
  734. xr = a[j1];
  735. xi = a[j1 + 1];
  736. yr = a[k1];
  737. yi = a[k1 + 1];
  738. a[j1] = yr;
  739. a[j1 + 1] = yi;
  740. a[k1] = xr;
  741. a[k1 + 1] = xi;
  742. }
  743. }
  744. }
  745. }
  746. static void bitrv2conj(int n, int *ip, FPType *a)
  747. {
  748. int j, j1, k, k1, l, m, m2;
  749. double xr, xi, yr, yi;
  750. ip[0] = 0;
  751. l = n;
  752. m = 1;
  753. while ((m << 3) < l) {
  754. l >>= 1;
  755. for (j = 0; j < m; j++) {
  756. ip[m + j] = ip[j] + l;
  757. }
  758. m <<= 1;
  759. }
  760. m2 = 2 * m;
  761. if ((m << 3) == l) {
  762. for (k = 0; k < m; k++) {
  763. for (j = 0; j < k; j++) {
  764. j1 = 2 * j + ip[k];
  765. k1 = 2 * k + ip[j];
  766. xr = a[j1];
  767. xi = -a[j1 + 1];
  768. yr = a[k1];
  769. yi = -a[k1 + 1];
  770. a[j1] = yr;
  771. a[j1 + 1] = yi;
  772. a[k1] = xr;
  773. a[k1 + 1] = xi;
  774. j1 += m2;
  775. k1 += 2 * m2;
  776. xr = a[j1];
  777. xi = -a[j1 + 1];
  778. yr = a[k1];
  779. yi = -a[k1 + 1];
  780. a[j1] = yr;
  781. a[j1 + 1] = yi;
  782. a[k1] = xr;
  783. a[k1 + 1] = xi;
  784. j1 += m2;
  785. k1 -= m2;
  786. xr = a[j1];
  787. xi = -a[j1 + 1];
  788. yr = a[k1];
  789. yi = -a[k1 + 1];
  790. a[j1] = yr;
  791. a[j1 + 1] = yi;
  792. a[k1] = xr;
  793. a[k1 + 1] = xi;
  794. j1 += m2;
  795. k1 += 2 * m2;
  796. xr = a[j1];
  797. xi = -a[j1 + 1];
  798. yr = a[k1];
  799. yi = -a[k1 + 1];
  800. a[j1] = yr;
  801. a[j1 + 1] = yi;
  802. a[k1] = xr;
  803. a[k1 + 1] = xi;
  804. }
  805. k1 = 2 * k + ip[k];
  806. a[k1 + 1] = -a[k1 + 1];
  807. j1 = k1 + m2;
  808. k1 = j1 + m2;
  809. xr = a[j1];
  810. xi = -a[j1 + 1];
  811. yr = a[k1];
  812. yi = -a[k1 + 1];
  813. a[j1] = yr;
  814. a[j1 + 1] = yi;
  815. a[k1] = xr;
  816. a[k1 + 1] = xi;
  817. k1 += m2;
  818. a[k1 + 1] = -a[k1 + 1];
  819. }
  820. } else {
  821. a[1] = -a[1];
  822. a[m2 + 1] = -a[m2 + 1];
  823. for (k = 1; k < m; k++) {
  824. for (j = 0; j < k; j++) {
  825. j1 = 2 * j + ip[k];
  826. k1 = 2 * k + ip[j];
  827. xr = a[j1];
  828. xi = -a[j1 + 1];
  829. yr = a[k1];
  830. yi = -a[k1 + 1];
  831. a[j1] = yr;
  832. a[j1 + 1] = yi;
  833. a[k1] = xr;
  834. a[k1 + 1] = xi;
  835. j1 += m2;
  836. k1 += m2;
  837. xr = a[j1];
  838. xi = -a[j1 + 1];
  839. yr = a[k1];
  840. yi = -a[k1 + 1];
  841. a[j1] = yr;
  842. a[j1 + 1] = yi;
  843. a[k1] = xr;
  844. a[k1 + 1] = xi;
  845. }
  846. k1 = 2 * k + ip[k];
  847. a[k1 + 1] = -a[k1 + 1];
  848. a[k1 + m2 + 1] = -a[k1 + m2 + 1];
  849. }
  850. }
  851. }
  852. static void cftfsub(int n, FPType *a, const FPType *w)
  853. {
  854. int j, j1, j2, j3, l;
  855. double x0r, x0i, x1r, x1i, x2r, x2i, x3r, x3i;
  856. l = 2;
  857. if (n > 8) {
  858. cft1st(n, a, w);
  859. l = 8;
  860. while ((l << 2) < n) {
  861. cftmdl(n, l, a, w);
  862. l <<= 2;
  863. }
  864. }
  865. if ((l << 2) == n) {
  866. for (j = 0; j < l; j += 2) {
  867. j1 = j + l;
  868. j2 = j1 + l;
  869. j3 = j2 + l;
  870. x0r = a[j] + a[j1];
  871. x0i = a[j + 1] + a[j1 + 1];
  872. x1r = a[j] - a[j1];
  873. x1i = a[j + 1] - a[j1 + 1];
  874. x2r = a[j2] + a[j3];
  875. x2i = a[j2 + 1] + a[j3 + 1];
  876. x3r = a[j2] - a[j3];
  877. x3i = a[j2 + 1] - a[j3 + 1];
  878. a[j] = x0r + x2r;
  879. a[j + 1] = x0i + x2i;
  880. a[j2] = x0r - x2r;
  881. a[j2 + 1] = x0i - x2i;
  882. a[j1] = x1r - x3i;
  883. a[j1 + 1] = x1i + x3r;
  884. a[j3] = x1r + x3i;
  885. a[j3 + 1] = x1i - x3r;
  886. }
  887. } else {
  888. for (j = 0; j < l; j += 2) {
  889. j1 = j + l;
  890. x0r = a[j] - a[j1];
  891. x0i = a[j + 1] - a[j1 + 1];
  892. a[j] += a[j1];
  893. a[j + 1] += a[j1 + 1];
  894. a[j1] = x0r;
  895. a[j1 + 1] = x0i;
  896. }
  897. }
  898. }
  899. static void cftbsub(int n, FPType *a, const FPType *w)
  900. {
  901. int j, j1, j2, j3, l;
  902. double x0r, x0i, x1r, x1i, x2r, x2i, x3r, x3i;
  903. l = 2;
  904. if (n > 8) {
  905. cft1st(n, a, w);
  906. l = 8;
  907. while ((l << 2) < n) {
  908. cftmdl(n, l, a, w);
  909. l <<= 2;
  910. }
  911. }
  912. if ((l << 2) == n) {
  913. for (j = 0; j < l; j += 2) {
  914. j1 = j + l;
  915. j2 = j1 + l;
  916. j3 = j2 + l;
  917. x0r = a[j] + a[j1];
  918. x0i = -a[j + 1] - a[j1 + 1];
  919. x1r = a[j] - a[j1];
  920. x1i = -a[j + 1] + a[j1 + 1];
  921. x2r = a[j2] + a[j3];
  922. x2i = a[j2 + 1] + a[j3 + 1];
  923. x3r = a[j2] - a[j3];
  924. x3i = a[j2 + 1] - a[j3 + 1];
  925. a[j] = x0r + x2r;
  926. a[j + 1] = x0i - x2i;
  927. a[j2] = x0r - x2r;
  928. a[j2 + 1] = x0i + x2i;
  929. a[j1] = x1r - x3i;
  930. a[j1 + 1] = x1i - x3r;
  931. a[j3] = x1r + x3i;
  932. a[j3 + 1] = x1i + x3r;
  933. }
  934. } else {
  935. for (j = 0; j < l; j += 2) {
  936. j1 = j + l;
  937. x0r = a[j] - a[j1];
  938. x0i = -a[j + 1] + a[j1 + 1];
  939. a[j] += a[j1];
  940. a[j + 1] = -a[j + 1] - a[j1 + 1];
  941. a[j1] = x0r;
  942. a[j1 + 1] = x0i;
  943. }
  944. }
  945. }
  946. static void cft1st(int n, FPType *a, const FPType *w)
  947. {
  948. int j, k1, k2;
  949. double wk1r, wk1i, wk2r, wk2i, wk3r, wk3i;
  950. double x0r, x0i, x1r, x1i, x2r, x2i, x3r, x3i;
  951. x0r = a[0] + a[2];
  952. x0i = a[1] + a[3];
  953. x1r = a[0] - a[2];
  954. x1i = a[1] - a[3];
  955. x2r = a[4] + a[6];
  956. x2i = a[5] + a[7];
  957. x3r = a[4] - a[6];
  958. x3i = a[5] - a[7];
  959. a[0] = x0r + x2r;
  960. a[1] = x0i + x2i;
  961. a[4] = x0r - x2r;
  962. a[5] = x0i - x2i;
  963. a[2] = x1r - x3i;
  964. a[3] = x1i + x3r;
  965. a[6] = x1r + x3i;
  966. a[7] = x1i - x3r;
  967. wk1r = w[2];
  968. x0r = a[8] + a[10];
  969. x0i = a[9] + a[11];
  970. x1r = a[8] - a[10];
  971. x1i = a[9] - a[11];
  972. x2r = a[12] + a[14];
  973. x2i = a[13] + a[15];
  974. x3r = a[12] - a[14];
  975. x3i = a[13] - a[15];
  976. a[8] = x0r + x2r;
  977. a[9] = x0i + x2i;
  978. a[12] = x2i - x0i;
  979. a[13] = x0r - x2r;
  980. x0r = x1r - x3i;
  981. x0i = x1i + x3r;
  982. a[10] = wk1r * (x0r - x0i);
  983. a[11] = wk1r * (x0r + x0i);
  984. x0r = x3i + x1r;
  985. x0i = x3r - x1i;
  986. a[14] = wk1r * (x0i - x0r);
  987. a[15] = wk1r * (x0i + x0r);
  988. k1 = 0;
  989. for (j = 16; j < n; j += 16) {
  990. k1 += 2;
  991. k2 = 2 * k1;
  992. wk2r = w[k1];
  993. wk2i = w[k1 + 1];
  994. wk1r = w[k2];
  995. wk1i = w[k2 + 1];
  996. wk3r = wk1r - 2 * wk2i * wk1i;
  997. wk3i = 2 * wk2i * wk1r - wk1i;
  998. x0r = a[j] + a[j + 2];
  999. x0i = a[j + 1] + a[j + 3];
  1000. x1r = a[j] - a[j + 2];
  1001. x1i = a[j + 1] - a[j + 3];
  1002. x2r = a[j + 4] + a[j + 6];
  1003. x2i = a[j + 5] + a[j + 7];
  1004. x3r = a[j + 4] - a[j + 6];
  1005. x3i = a[j + 5] - a[j + 7];
  1006. a[j] = x0r + x2r;
  1007. a[j + 1] = x0i + x2i;
  1008. x0r -= x2r;
  1009. x0i -= x2i;
  1010. a[j + 4] = wk2r * x0r - wk2i * x0i;
  1011. a[j + 5] = wk2r * x0i + wk2i * x0r;
  1012. x0r = x1r - x3i;
  1013. x0i = x1i + x3r;
  1014. a[j + 2] = wk1r * x0r - wk1i * x0i;
  1015. a[j + 3] = wk1r * x0i + wk1i * x0r;
  1016. x0r = x1r + x3i;
  1017. x0i = x1i - x3r;
  1018. a[j + 6] = wk3r * x0r - wk3i * x0i;
  1019. a[j + 7] = wk3r * x0i + wk3i * x0r;
  1020. wk1r = w[k2 + 2];
  1021. wk1i = w[k2 + 3];
  1022. wk3r = wk1r - 2 * wk2r * wk1i;
  1023. wk3i = 2 * wk2r * wk1r - wk1i;
  1024. x0r = a[j + 8] + a[j + 10];
  1025. x0i = a[j + 9] + a[j + 11];
  1026. x1r = a[j + 8] - a[j + 10];
  1027. x1i = a[j + 9] - a[j + 11];
  1028. x2r = a[j + 12] + a[j + 14];
  1029. x2i = a[j + 13] + a[j + 15];
  1030. x3r = a[j + 12] - a[j + 14];
  1031. x3i = a[j + 13] - a[j + 15];
  1032. a[j + 8] = x0r + x2r;
  1033. a[j + 9] = x0i + x2i;
  1034. x0r -= x2r;
  1035. x0i -= x2i;
  1036. a[j + 12] = -wk2i * x0r - wk2r * x0i;
  1037. a[j + 13] = -wk2i * x0i + wk2r * x0r;
  1038. x0r = x1r - x3i;
  1039. x0i = x1i + x3r;
  1040. a[j + 10] = wk1r * x0r - wk1i * x0i;
  1041. a[j + 11] = wk1r * x0i + wk1i * x0r;
  1042. x0r = x1r + x3i;
  1043. x0i = x1i - x3r;
  1044. a[j + 14] = wk3r * x0r - wk3i * x0i;
  1045. a[j + 15] = wk3r * x0i + wk3i * x0r;
  1046. }
  1047. }
  1048. static void cftmdl(int n, int l, FPType *a, const FPType *w)
  1049. {
  1050. int j, j1, j2, j3, k, k1, k2, m, m2;
  1051. double wk1r, wk1i, wk2r, wk2i, wk3r, wk3i;
  1052. double x0r, x0i, x1r, x1i, x2r, x2i, x3r, x3i;
  1053. m = l << 2;
  1054. for (j = 0; j < l; j += 2) {
  1055. j1 = j + l;
  1056. j2 = j1 + l;
  1057. j3 = j2 + l;
  1058. x0r = a[j] + a[j1];
  1059. x0i = a[j + 1] + a[j1 + 1];
  1060. x1r = a[j] - a[j1];
  1061. x1i = a[j + 1] - a[j1 + 1];
  1062. x2r = a[j2] + a[j3];
  1063. x2i = a[j2 + 1] + a[j3 + 1];
  1064. x3r = a[j2] - a[j3];
  1065. x3i = a[j2 + 1] - a[j3 + 1];
  1066. a[j] = x0r + x2r;
  1067. a[j + 1] = x0i + x2i;
  1068. a[j2] = x0r - x2r;
  1069. a[j2 + 1] = x0i - x2i;
  1070. a[j1] = x1r - x3i;
  1071. a[j1 + 1] = x1i + x3r;
  1072. a[j3] = x1r + x3i;
  1073. a[j3 + 1] = x1i - x3r;
  1074. }
  1075. wk1r = w[2];
  1076. for (j = m; j < l + m; j += 2) {
  1077. j1 = j + l;
  1078. j2 = j1 + l;
  1079. j3 = j2 + l;
  1080. x0r = a[j] + a[j1];
  1081. x0i = a[j + 1] + a[j1 + 1];
  1082. x1r = a[j] - a[j1];
  1083. x1i = a[j + 1] - a[j1 + 1];
  1084. x2r = a[j2] + a[j3];
  1085. x2i = a[j2 + 1] + a[j3 + 1];
  1086. x3r = a[j2] - a[j3];
  1087. x3i = a[j2 + 1] - a[j3 + 1];
  1088. a[j] = x0r + x2r;
  1089. a[j + 1] = x0i + x2i;
  1090. a[j2] = x2i - x0i;
  1091. a[j2 + 1] = x0r - x2r;
  1092. x0r = x1r - x3i;
  1093. x0i = x1i + x3r;
  1094. a[j1] = wk1r * (x0r - x0i);
  1095. a[j1 + 1] = wk1r * (x0r + x0i);
  1096. x0r = x3i + x1r;
  1097. x0i = x3r - x1i;
  1098. a[j3] = wk1r * (x0i - x0r);
  1099. a[j3 + 1] = wk1r * (x0i + x0r);
  1100. }
  1101. k1 = 0;
  1102. m2 = 2 * m;
  1103. for (k = m2; k < n; k += m2) {
  1104. k1 += 2;
  1105. k2 = 2 * k1;
  1106. wk2r = w[k1];
  1107. wk2i = w[k1 + 1];
  1108. wk1r = w[k2];
  1109. wk1i = w[k2 + 1];
  1110. wk3r = wk1r - 2 * wk2i * wk1i;
  1111. wk3i = 2 * wk2i * wk1r - wk1i;
  1112. for (j = k; j < l + k; j += 2) {
  1113. j1 = j + l;
  1114. j2 = j1 + l;
  1115. j3 = j2 + l;
  1116. x0r = a[j] + a[j1];
  1117. x0i = a[j + 1] + a[j1 + 1];
  1118. x1r = a[j] - a[j1];
  1119. x1i = a[j + 1] - a[j1 + 1];
  1120. x2r = a[j2] + a[j3];
  1121. x2i = a[j2 + 1] + a[j3 + 1];
  1122. x3r = a[j2] - a[j3];
  1123. x3i = a[j2 + 1] - a[j3 + 1];
  1124. a[j] = x0r + x2r;
  1125. a[j + 1] = x0i + x2i;
  1126. x0r -= x2r;
  1127. x0i -= x2i;
  1128. a[j2] = wk2r * x0r - wk2i * x0i;
  1129. a[j2 + 1] = wk2r * x0i + wk2i * x0r;
  1130. x0r = x1r - x3i;
  1131. x0i = x1i + x3r;
  1132. a[j1] = wk1r * x0r - wk1i * x0i;
  1133. a[j1 + 1] = wk1r * x0i + wk1i * x0r;
  1134. x0r = x1r + x3i;
  1135. x0i = x1i - x3r;
  1136. a[j3] = wk3r * x0r - wk3i * x0i;
  1137. a[j3 + 1] = wk3r * x0i + wk3i * x0r;
  1138. }
  1139. wk1r = w[k2 + 2];
  1140. wk1i = w[k2 + 3];
  1141. wk3r = wk1r - 2 * wk2r * wk1i;
  1142. wk3i = 2 * wk2r * wk1r - wk1i;
  1143. for (j = k + m; j < l + (k + m); j += 2) {
  1144. j1 = j + l;
  1145. j2 = j1 + l;
  1146. j3 = j2 + l;
  1147. x0r = a[j] + a[j1];
  1148. x0i = a[j + 1] + a[j1 + 1];
  1149. x1r = a[j] - a[j1];
  1150. x1i = a[j + 1] - a[j1 + 1];
  1151. x2r = a[j2] + a[j3];
  1152. x2i = a[j2 + 1] + a[j3 + 1];
  1153. x3r = a[j2] - a[j3];
  1154. x3i = a[j2 + 1] - a[j3 + 1];
  1155. a[j] = x0r + x2r;
  1156. a[j + 1] = x0i + x2i;
  1157. x0r -= x2r;
  1158. x0i -= x2i;
  1159. a[j2] = -wk2i * x0r - wk2r * x0i;
  1160. a[j2 + 1] = -wk2i * x0i + wk2r * x0r;
  1161. x0r = x1r - x3i;
  1162. x0i = x1i + x3r;
  1163. a[j1] = wk1r * x0r - wk1i * x0i;
  1164. a[j1 + 1] = wk1r * x0i + wk1i * x0r;
  1165. x0r = x1r + x3i;
  1166. x0i = x1i - x3r;
  1167. a[j3] = wk3r * x0r - wk3i * x0i;
  1168. a[j3 + 1] = wk3r * x0i + wk3i * x0r;
  1169. }
  1170. }
  1171. }
  1172. static void rftfsub(int n, FPType *a, int nc, const FPType *c)
  1173. {
  1174. int j, k, kk, ks, m;
  1175. double wkr, wki, xr, xi, yr, yi;
  1176. m = n >> 1;
  1177. ks = 2 * nc / m;
  1178. kk = 0;
  1179. for (j = 2; j < m; j += 2) {
  1180. k = n - j;
  1181. kk += ks;
  1182. wkr = 0.5 - c[nc - kk];
  1183. wki = c[kk];
  1184. xr = a[j] - a[k];
  1185. xi = a[j + 1] + a[k + 1];
  1186. yr = wkr * xr - wki * xi;
  1187. yi = wkr * xi + wki * xr;
  1188. a[j] -= yr;
  1189. a[j + 1] -= yi;
  1190. a[k] += yr;
  1191. a[k + 1] -= yi;
  1192. }
  1193. }
  1194. static void rftbsub(int n, FPType *a, int nc, const FPType *c)
  1195. {
  1196. int j, k, kk, ks, m;
  1197. double wkr, wki, xr, xi, yr, yi;
  1198. a[1] = -a[1];
  1199. m = n >> 1;
  1200. ks = 2 * nc / m;
  1201. kk = 0;
  1202. for (j = 2; j < m; j += 2) {
  1203. k = n - j;
  1204. kk += ks;
  1205. wkr = 0.5 - c[nc - kk];
  1206. wki = c[kk];
  1207. xr = a[j] - a[k];
  1208. xi = a[j + 1] + a[k + 1];
  1209. yr = wkr * xr + wki * xi;
  1210. yi = wkr * xi - wki * xr;
  1211. a[j] -= yr;
  1212. a[j + 1] = yi - a[j + 1];
  1213. a[k] += yr;
  1214. a[k + 1] = yi - a[k + 1];
  1215. }
  1216. a[m + 1] = -a[m + 1];
  1217. }
  1218. static void dctsub(int n, FPType *a, int nc, const FPType *c)
  1219. {
  1220. int j, k, kk, ks, m;
  1221. double wkr, wki, xr;
  1222. m = n >> 1;
  1223. ks = nc / n;
  1224. kk = 0;
  1225. for (j = 1; j < m; j++) {
  1226. k = n - j;
  1227. kk += ks;
  1228. wkr = c[kk] - c[nc - kk];
  1229. wki = c[kk] + c[nc - kk];
  1230. xr = wki * a[j] - wkr * a[k];
  1231. a[j] = wkr * a[j] + wki * a[k];
  1232. a[k] = xr;
  1233. }
  1234. a[m] *= c[0];
  1235. }
  1236. static void dstsub(int n, FPType *a, int nc, const FPType *c)
  1237. {
  1238. int j, k, kk, ks, m;
  1239. double wkr, wki, xr;
  1240. m = n >> 1;
  1241. ks = nc / n;
  1242. kk = 0;
  1243. for (j = 1; j < m; j++) {
  1244. k = n - j;
  1245. kk += ks;
  1246. wkr = c[kk] - c[nc - kk];
  1247. wki = c[kk] + c[nc - kk];
  1248. xr = wki * a[k] - wkr * a[j];
  1249. a[k] = wkr * a[k] + wki * a[j];
  1250. a[j] = xr;
  1251. }
  1252. a[m] *= c[0];
  1253. }
  1254. };
  1255. } // namespace r8b
  1256. #endif // R8B_FFT4G_INCLUDED