annotate src/fftw-3.3.3/tests/bench.c @ 169:223a55898ab9 tip default

Add null config files
author Chris Cannam <cannam@all-day-breakfast.com>
date Mon, 02 Mar 2020 14:03:47 +0000
parents 89f5e221ed7b
children
rev   line source
cannam@95 1 /**************************************************************************/
cannam@95 2 /* NOTE to users: this is the FFTW self-test and benchmark program.
cannam@95 3 It is probably NOT a good place to learn FFTW usage, since it has a
cannam@95 4 lot of added complexity in order to exercise and test the full API,
cannam@95 5 etcetera. We suggest reading the manual.
cannam@95 6
cannam@95 7 (Some of the self-test code is split off into fftw-bench.c and
cannam@95 8 hook.c.) */
cannam@95 9 /**************************************************************************/
cannam@95 10
cannam@95 11 #include <math.h>
cannam@95 12 #include <stdio.h>
cannam@95 13 #include <string.h>
cannam@95 14 #include "fftw-bench.h"
cannam@95 15
cannam@95 16 static const char *mkversion(void) { return FFTW(version); }
cannam@95 17 static const char *mkcc(void) { return FFTW(cc); }
cannam@95 18 static const char *mkcodelet_optim(void) { return FFTW(codelet_optim); }
cannam@95 19
cannam@95 20 BEGIN_BENCH_DOC
cannam@95 21 BENCH_DOC("name", "fftw3")
cannam@95 22 BENCH_DOCF("version", mkversion)
cannam@95 23 BENCH_DOCF("cc", mkcc)
cannam@95 24 BENCH_DOCF("codelet-optim", mkcodelet_optim)
cannam@95 25 END_BENCH_DOC
cannam@95 26
cannam@95 27 static FFTW(iodim) *bench_tensor_to_fftw_iodim(bench_tensor *t)
cannam@95 28 {
cannam@95 29 FFTW(iodim) *d;
cannam@95 30 int i;
cannam@95 31
cannam@95 32 BENCH_ASSERT(t->rnk >= 0);
cannam@95 33 if (t->rnk == 0) return 0;
cannam@95 34
cannam@95 35 d = (FFTW(iodim) *)bench_malloc(sizeof(FFTW(iodim)) * t->rnk);
cannam@95 36 for (i = 0; i < t->rnk; ++i) {
cannam@95 37 d[i].n = t->dims[i].n;
cannam@95 38 d[i].is = t->dims[i].is;
cannam@95 39 d[i].os = t->dims[i].os;
cannam@95 40 }
cannam@95 41
cannam@95 42 return d;
cannam@95 43 }
cannam@95 44
cannam@95 45 static void extract_reim_split(int sign, int size, bench_real *p,
cannam@95 46 bench_real **r, bench_real **i)
cannam@95 47 {
cannam@95 48 if (sign == FFTW_FORWARD) {
cannam@95 49 *r = p + 0;
cannam@95 50 *i = p + size;
cannam@95 51 } else {
cannam@95 52 *r = p + size;
cannam@95 53 *i = p + 0;
cannam@95 54 }
cannam@95 55 }
cannam@95 56
cannam@95 57 static int sizeof_problem(bench_problem *p)
cannam@95 58 {
cannam@95 59 return tensor_sz(p->sz) * tensor_sz(p->vecsz);
cannam@95 60 }
cannam@95 61
cannam@95 62 /* ouch */
cannam@95 63 static int expressible_as_api_many(bench_tensor *t)
cannam@95 64 {
cannam@95 65 int i;
cannam@95 66
cannam@95 67 BENCH_ASSERT(FINITE_RNK(t->rnk));
cannam@95 68
cannam@95 69 i = t->rnk - 1;
cannam@95 70 while (--i >= 0) {
cannam@95 71 bench_iodim *d = t->dims + i;
cannam@95 72 if (d[0].is % d[1].is) return 0;
cannam@95 73 if (d[0].os % d[1].os) return 0;
cannam@95 74 }
cannam@95 75 return 1;
cannam@95 76 }
cannam@95 77
cannam@95 78 static int *mkn(bench_tensor *t)
cannam@95 79 {
cannam@95 80 int *n = (int *) bench_malloc(sizeof(int *) * t->rnk);
cannam@95 81 int i;
cannam@95 82 for (i = 0; i < t->rnk; ++i)
cannam@95 83 n[i] = t->dims[i].n;
cannam@95 84 return n;
cannam@95 85 }
cannam@95 86
cannam@95 87 static void mknembed_many(bench_tensor *t, int **inembedp, int **onembedp)
cannam@95 88 {
cannam@95 89 int i;
cannam@95 90 bench_iodim *d;
cannam@95 91 int *inembed = (int *) bench_malloc(sizeof(int *) * t->rnk);
cannam@95 92 int *onembed = (int *) bench_malloc(sizeof(int *) * t->rnk);
cannam@95 93
cannam@95 94 BENCH_ASSERT(FINITE_RNK(t->rnk));
cannam@95 95 *inembedp = inembed; *onembedp = onembed;
cannam@95 96
cannam@95 97 i = t->rnk - 1;
cannam@95 98 while (--i >= 0) {
cannam@95 99 d = t->dims + i;
cannam@95 100 inembed[i+1] = d[0].is / d[1].is;
cannam@95 101 onembed[i+1] = d[0].os / d[1].os;
cannam@95 102 }
cannam@95 103 }
cannam@95 104
cannam@95 105 /* try to use the most appropriate API function. Big mess. */
cannam@95 106
cannam@95 107 static int imax(int a, int b) { return (a > b ? a : b); }
cannam@95 108
cannam@95 109 static int halfish_sizeof_problem(bench_problem *p)
cannam@95 110 {
cannam@95 111 int n2 = sizeof_problem(p);
cannam@95 112 if (FINITE_RNK(p->sz->rnk) && p->sz->rnk > 0)
cannam@95 113 n2 = (n2 / imax(p->sz->dims[p->sz->rnk - 1].n, 1)) *
cannam@95 114 (p->sz->dims[p->sz->rnk - 1].n / 2 + 1);
cannam@95 115 return n2;
cannam@95 116 }
cannam@95 117
cannam@95 118 static FFTW(plan) mkplan_real_split(bench_problem *p, unsigned flags)
cannam@95 119 {
cannam@95 120 FFTW(plan) pln;
cannam@95 121 bench_tensor *sz = p->sz, *vecsz = p->vecsz;
cannam@95 122 FFTW(iodim) *dims, *howmany_dims;
cannam@95 123 bench_real *ri, *ii, *ro, *io;
cannam@95 124 int n2 = halfish_sizeof_problem(p);
cannam@95 125
cannam@95 126 extract_reim_split(FFTW_FORWARD, n2, (bench_real *) p->in, &ri, &ii);
cannam@95 127 extract_reim_split(FFTW_FORWARD, n2, (bench_real *) p->out, &ro, &io);
cannam@95 128
cannam@95 129 dims = bench_tensor_to_fftw_iodim(sz);
cannam@95 130 howmany_dims = bench_tensor_to_fftw_iodim(vecsz);
cannam@95 131 if (p->sign < 0) {
cannam@95 132 if (verbose > 2) printf("using plan_guru_split_dft_r2c\n");
cannam@95 133 pln = FFTW(plan_guru_split_dft_r2c)(sz->rnk, dims,
cannam@95 134 vecsz->rnk, howmany_dims,
cannam@95 135 ri, ro, io, flags);
cannam@95 136 }
cannam@95 137 else {
cannam@95 138 if (verbose > 2) printf("using plan_guru_split_dft_c2r\n");
cannam@95 139 pln = FFTW(plan_guru_split_dft_c2r)(sz->rnk, dims,
cannam@95 140 vecsz->rnk, howmany_dims,
cannam@95 141 ri, ii, ro, flags);
cannam@95 142 }
cannam@95 143 bench_free(dims);
cannam@95 144 bench_free(howmany_dims);
cannam@95 145 return pln;
cannam@95 146 }
cannam@95 147
cannam@95 148 static FFTW(plan) mkplan_real_interleaved(bench_problem *p, unsigned flags)
cannam@95 149 {
cannam@95 150 FFTW(plan) pln;
cannam@95 151 bench_tensor *sz = p->sz, *vecsz = p->vecsz;
cannam@95 152
cannam@95 153 if (vecsz->rnk == 0 && tensor_unitstridep(sz)
cannam@95 154 && tensor_real_rowmajorp(sz, p->sign, p->in_place))
cannam@95 155 goto api_simple;
cannam@95 156
cannam@95 157 if (vecsz->rnk == 1 && expressible_as_api_many(sz))
cannam@95 158 goto api_many;
cannam@95 159
cannam@95 160 goto api_guru;
cannam@95 161
cannam@95 162 api_simple:
cannam@95 163 switch (sz->rnk) {
cannam@95 164 case 1:
cannam@95 165 if (p->sign < 0) {
cannam@95 166 if (verbose > 2) printf("using plan_dft_r2c_1d\n");
cannam@95 167 return FFTW(plan_dft_r2c_1d)(sz->dims[0].n,
cannam@95 168 (bench_real *) p->in,
cannam@95 169 (bench_complex *) p->out,
cannam@95 170 flags);
cannam@95 171 }
cannam@95 172 else {
cannam@95 173 if (verbose > 2) printf("using plan_dft_c2r_1d\n");
cannam@95 174 return FFTW(plan_dft_c2r_1d)(sz->dims[0].n,
cannam@95 175 (bench_complex *) p->in,
cannam@95 176 (bench_real *) p->out,
cannam@95 177 flags);
cannam@95 178 }
cannam@95 179 break;
cannam@95 180 case 2:
cannam@95 181 if (p->sign < 0) {
cannam@95 182 if (verbose > 2) printf("using plan_dft_r2c_2d\n");
cannam@95 183 return FFTW(plan_dft_r2c_2d)(sz->dims[0].n, sz->dims[1].n,
cannam@95 184 (bench_real *) p->in,
cannam@95 185 (bench_complex *) p->out,
cannam@95 186 flags);
cannam@95 187 }
cannam@95 188 else {
cannam@95 189 if (verbose > 2) printf("using plan_dft_c2r_2d\n");
cannam@95 190 return FFTW(plan_dft_c2r_2d)(sz->dims[0].n, sz->dims[1].n,
cannam@95 191 (bench_complex *) p->in,
cannam@95 192 (bench_real *) p->out,
cannam@95 193 flags);
cannam@95 194 }
cannam@95 195 break;
cannam@95 196 case 3:
cannam@95 197 if (p->sign < 0) {
cannam@95 198 if (verbose > 2) printf("using plan_dft_r2c_3d\n");
cannam@95 199 return FFTW(plan_dft_r2c_3d)(
cannam@95 200 sz->dims[0].n, sz->dims[1].n, sz->dims[2].n,
cannam@95 201 (bench_real *) p->in, (bench_complex *) p->out,
cannam@95 202 flags);
cannam@95 203 }
cannam@95 204 else {
cannam@95 205 if (verbose > 2) printf("using plan_dft_c2r_3d\n");
cannam@95 206 return FFTW(plan_dft_c2r_3d)(
cannam@95 207 sz->dims[0].n, sz->dims[1].n, sz->dims[2].n,
cannam@95 208 (bench_complex *) p->in, (bench_real *) p->out,
cannam@95 209 flags);
cannam@95 210 }
cannam@95 211 break;
cannam@95 212 default: {
cannam@95 213 int *n = mkn(sz);
cannam@95 214 if (p->sign < 0) {
cannam@95 215 if (verbose > 2) printf("using plan_dft_r2c\n");
cannam@95 216 pln = FFTW(plan_dft_r2c)(sz->rnk, n,
cannam@95 217 (bench_real *) p->in,
cannam@95 218 (bench_complex *) p->out,
cannam@95 219 flags);
cannam@95 220 }
cannam@95 221 else {
cannam@95 222 if (verbose > 2) printf("using plan_dft_c2r\n");
cannam@95 223 pln = FFTW(plan_dft_c2r)(sz->rnk, n,
cannam@95 224 (bench_complex *) p->in,
cannam@95 225 (bench_real *) p->out,
cannam@95 226 flags);
cannam@95 227 }
cannam@95 228 bench_free(n);
cannam@95 229 return pln;
cannam@95 230 }
cannam@95 231 }
cannam@95 232
cannam@95 233 api_many:
cannam@95 234 {
cannam@95 235 int *n, *inembed, *onembed;
cannam@95 236 BENCH_ASSERT(vecsz->rnk == 1);
cannam@95 237 n = mkn(sz);
cannam@95 238 mknembed_many(sz, &inembed, &onembed);
cannam@95 239 if (p->sign < 0) {
cannam@95 240 if (verbose > 2) printf("using plan_many_dft_r2c\n");
cannam@95 241 pln = FFTW(plan_many_dft_r2c)(
cannam@95 242 sz->rnk, n, vecsz->dims[0].n,
cannam@95 243 (bench_real *) p->in, inembed,
cannam@95 244 sz->dims[sz->rnk - 1].is, vecsz->dims[0].is,
cannam@95 245 (bench_complex *) p->out, onembed,
cannam@95 246 sz->dims[sz->rnk - 1].os, vecsz->dims[0].os,
cannam@95 247 flags);
cannam@95 248 }
cannam@95 249 else {
cannam@95 250 if (verbose > 2) printf("using plan_many_dft_c2r\n");
cannam@95 251 pln = FFTW(plan_many_dft_c2r)(
cannam@95 252 sz->rnk, n, vecsz->dims[0].n,
cannam@95 253 (bench_complex *) p->in, inembed,
cannam@95 254 sz->dims[sz->rnk - 1].is, vecsz->dims[0].is,
cannam@95 255 (bench_real *) p->out, onembed,
cannam@95 256 sz->dims[sz->rnk - 1].os, vecsz->dims[0].os,
cannam@95 257 flags);
cannam@95 258 }
cannam@95 259 bench_free(n); bench_free(inembed); bench_free(onembed);
cannam@95 260 return pln;
cannam@95 261 }
cannam@95 262
cannam@95 263 api_guru:
cannam@95 264 {
cannam@95 265 FFTW(iodim) *dims, *howmany_dims;
cannam@95 266
cannam@95 267 if (p->sign < 0) {
cannam@95 268 dims = bench_tensor_to_fftw_iodim(sz);
cannam@95 269 howmany_dims = bench_tensor_to_fftw_iodim(vecsz);
cannam@95 270 if (verbose > 2) printf("using plan_guru_dft_r2c\n");
cannam@95 271 pln = FFTW(plan_guru_dft_r2c)(sz->rnk, dims,
cannam@95 272 vecsz->rnk, howmany_dims,
cannam@95 273 (bench_real *) p->in,
cannam@95 274 (bench_complex *) p->out,
cannam@95 275 flags);
cannam@95 276 }
cannam@95 277 else {
cannam@95 278 dims = bench_tensor_to_fftw_iodim(sz);
cannam@95 279 howmany_dims = bench_tensor_to_fftw_iodim(vecsz);
cannam@95 280 if (verbose > 2) printf("using plan_guru_dft_c2r\n");
cannam@95 281 pln = FFTW(plan_guru_dft_c2r)(sz->rnk, dims,
cannam@95 282 vecsz->rnk, howmany_dims,
cannam@95 283 (bench_complex *) p->in,
cannam@95 284 (bench_real *) p->out,
cannam@95 285 flags);
cannam@95 286 }
cannam@95 287 bench_free(dims);
cannam@95 288 bench_free(howmany_dims);
cannam@95 289 return pln;
cannam@95 290 }
cannam@95 291 }
cannam@95 292
cannam@95 293 static FFTW(plan) mkplan_real(bench_problem *p, unsigned flags)
cannam@95 294 {
cannam@95 295 if (p->split)
cannam@95 296 return mkplan_real_split(p, flags);
cannam@95 297 else
cannam@95 298 return mkplan_real_interleaved(p, flags);
cannam@95 299 }
cannam@95 300
cannam@95 301 static FFTW(plan) mkplan_complex_split(bench_problem *p, unsigned flags)
cannam@95 302 {
cannam@95 303 FFTW(plan) pln;
cannam@95 304 bench_tensor *sz = p->sz, *vecsz = p->vecsz;
cannam@95 305 FFTW(iodim) *dims, *howmany_dims;
cannam@95 306 bench_real *ri, *ii, *ro, *io;
cannam@95 307
cannam@95 308 extract_reim_split(p->sign, p->iphyssz, (bench_real *) p->in, &ri, &ii);
cannam@95 309 extract_reim_split(p->sign, p->ophyssz, (bench_real *) p->out, &ro, &io);
cannam@95 310
cannam@95 311 dims = bench_tensor_to_fftw_iodim(sz);
cannam@95 312 howmany_dims = bench_tensor_to_fftw_iodim(vecsz);
cannam@95 313 if (verbose > 2) printf("using plan_guru_split_dft\n");
cannam@95 314 pln = FFTW(plan_guru_split_dft)(sz->rnk, dims,
cannam@95 315 vecsz->rnk, howmany_dims,
cannam@95 316 ri, ii, ro, io, flags);
cannam@95 317 bench_free(dims);
cannam@95 318 bench_free(howmany_dims);
cannam@95 319 return pln;
cannam@95 320 }
cannam@95 321
cannam@95 322 static FFTW(plan) mkplan_complex_interleaved(bench_problem *p, unsigned flags)
cannam@95 323 {
cannam@95 324 FFTW(plan) pln;
cannam@95 325 bench_tensor *sz = p->sz, *vecsz = p->vecsz;
cannam@95 326
cannam@95 327 if (vecsz->rnk == 0 && tensor_unitstridep(sz) && tensor_rowmajorp(sz))
cannam@95 328 goto api_simple;
cannam@95 329
cannam@95 330 if (vecsz->rnk == 1 && expressible_as_api_many(sz))
cannam@95 331 goto api_many;
cannam@95 332
cannam@95 333 goto api_guru;
cannam@95 334
cannam@95 335 api_simple:
cannam@95 336 switch (sz->rnk) {
cannam@95 337 case 1:
cannam@95 338 if (verbose > 2) printf("using plan_dft_1d\n");
cannam@95 339 return FFTW(plan_dft_1d)(sz->dims[0].n,
cannam@95 340 (bench_complex *) p->in,
cannam@95 341 (bench_complex *) p->out,
cannam@95 342 p->sign, flags);
cannam@95 343 break;
cannam@95 344 case 2:
cannam@95 345 if (verbose > 2) printf("using plan_dft_2d\n");
cannam@95 346 return FFTW(plan_dft_2d)(sz->dims[0].n, sz->dims[1].n,
cannam@95 347 (bench_complex *) p->in,
cannam@95 348 (bench_complex *) p->out,
cannam@95 349 p->sign, flags);
cannam@95 350 break;
cannam@95 351 case 3:
cannam@95 352 if (verbose > 2) printf("using plan_dft_3d\n");
cannam@95 353 return FFTW(plan_dft_3d)(
cannam@95 354 sz->dims[0].n, sz->dims[1].n, sz->dims[2].n,
cannam@95 355 (bench_complex *) p->in, (bench_complex *) p->out,
cannam@95 356 p->sign, flags);
cannam@95 357 break;
cannam@95 358 default: {
cannam@95 359 int *n = mkn(sz);
cannam@95 360 if (verbose > 2) printf("using plan_dft\n");
cannam@95 361 pln = FFTW(plan_dft)(sz->rnk, n,
cannam@95 362 (bench_complex *) p->in,
cannam@95 363 (bench_complex *) p->out, p->sign, flags);
cannam@95 364 bench_free(n);
cannam@95 365 return pln;
cannam@95 366 }
cannam@95 367 }
cannam@95 368
cannam@95 369 api_many:
cannam@95 370 {
cannam@95 371 int *n, *inembed, *onembed;
cannam@95 372 BENCH_ASSERT(vecsz->rnk == 1);
cannam@95 373 n = mkn(sz);
cannam@95 374 mknembed_many(sz, &inembed, &onembed);
cannam@95 375 if (verbose > 2) printf("using plan_many_dft\n");
cannam@95 376 pln = FFTW(plan_many_dft)(
cannam@95 377 sz->rnk, n, vecsz->dims[0].n,
cannam@95 378 (bench_complex *) p->in,
cannam@95 379 inembed, sz->dims[sz->rnk - 1].is, vecsz->dims[0].is,
cannam@95 380 (bench_complex *) p->out,
cannam@95 381 onembed, sz->dims[sz->rnk - 1].os, vecsz->dims[0].os,
cannam@95 382 p->sign, flags);
cannam@95 383 bench_free(n); bench_free(inembed); bench_free(onembed);
cannam@95 384 return pln;
cannam@95 385 }
cannam@95 386
cannam@95 387 api_guru:
cannam@95 388 {
cannam@95 389 FFTW(iodim) *dims, *howmany_dims;
cannam@95 390
cannam@95 391 dims = bench_tensor_to_fftw_iodim(sz);
cannam@95 392 howmany_dims = bench_tensor_to_fftw_iodim(vecsz);
cannam@95 393 if (verbose > 2) printf("using plan_guru_dft\n");
cannam@95 394 pln = FFTW(plan_guru_dft)(sz->rnk, dims,
cannam@95 395 vecsz->rnk, howmany_dims,
cannam@95 396 (bench_complex *) p->in,
cannam@95 397 (bench_complex *) p->out,
cannam@95 398 p->sign, flags);
cannam@95 399 bench_free(dims);
cannam@95 400 bench_free(howmany_dims);
cannam@95 401 return pln;
cannam@95 402 }
cannam@95 403 }
cannam@95 404
cannam@95 405 static FFTW(plan) mkplan_complex(bench_problem *p, unsigned flags)
cannam@95 406 {
cannam@95 407 if (p->split)
cannam@95 408 return mkplan_complex_split(p, flags);
cannam@95 409 else
cannam@95 410 return mkplan_complex_interleaved(p, flags);
cannam@95 411 }
cannam@95 412
cannam@95 413 static FFTW(plan) mkplan_r2r(bench_problem *p, unsigned flags)
cannam@95 414 {
cannam@95 415 FFTW(plan) pln;
cannam@95 416 bench_tensor *sz = p->sz, *vecsz = p->vecsz;
cannam@95 417 FFTW(r2r_kind) *k;
cannam@95 418
cannam@95 419 k = (FFTW(r2r_kind) *) bench_malloc(sizeof(FFTW(r2r_kind)) * sz->rnk);
cannam@95 420 {
cannam@95 421 int i;
cannam@95 422 for (i = 0; i < sz->rnk; ++i)
cannam@95 423 switch (p->k[i]) {
cannam@95 424 case R2R_R2HC: k[i] = FFTW_R2HC; break;
cannam@95 425 case R2R_HC2R: k[i] = FFTW_HC2R; break;
cannam@95 426 case R2R_DHT: k[i] = FFTW_DHT; break;
cannam@95 427 case R2R_REDFT00: k[i] = FFTW_REDFT00; break;
cannam@95 428 case R2R_REDFT01: k[i] = FFTW_REDFT01; break;
cannam@95 429 case R2R_REDFT10: k[i] = FFTW_REDFT10; break;
cannam@95 430 case R2R_REDFT11: k[i] = FFTW_REDFT11; break;
cannam@95 431 case R2R_RODFT00: k[i] = FFTW_RODFT00; break;
cannam@95 432 case R2R_RODFT01: k[i] = FFTW_RODFT01; break;
cannam@95 433 case R2R_RODFT10: k[i] = FFTW_RODFT10; break;
cannam@95 434 case R2R_RODFT11: k[i] = FFTW_RODFT11; break;
cannam@95 435 default: BENCH_ASSERT(0);
cannam@95 436 }
cannam@95 437 }
cannam@95 438
cannam@95 439 if (vecsz->rnk == 0 && tensor_unitstridep(sz) && tensor_rowmajorp(sz))
cannam@95 440 goto api_simple;
cannam@95 441
cannam@95 442 if (vecsz->rnk == 1 && expressible_as_api_many(sz))
cannam@95 443 goto api_many;
cannam@95 444
cannam@95 445 goto api_guru;
cannam@95 446
cannam@95 447 api_simple:
cannam@95 448 switch (sz->rnk) {
cannam@95 449 case 1:
cannam@95 450 if (verbose > 2) printf("using plan_r2r_1d\n");
cannam@95 451 pln = FFTW(plan_r2r_1d)(sz->dims[0].n,
cannam@95 452 (bench_real *) p->in,
cannam@95 453 (bench_real *) p->out,
cannam@95 454 k[0], flags);
cannam@95 455 goto done;
cannam@95 456 case 2:
cannam@95 457 if (verbose > 2) printf("using plan_r2r_2d\n");
cannam@95 458 pln = FFTW(plan_r2r_2d)(sz->dims[0].n, sz->dims[1].n,
cannam@95 459 (bench_real *) p->in,
cannam@95 460 (bench_real *) p->out,
cannam@95 461 k[0], k[1], flags);
cannam@95 462 goto done;
cannam@95 463 case 3:
cannam@95 464 if (verbose > 2) printf("using plan_r2r_3d\n");
cannam@95 465 pln = FFTW(plan_r2r_3d)(
cannam@95 466 sz->dims[0].n, sz->dims[1].n, sz->dims[2].n,
cannam@95 467 (bench_real *) p->in, (bench_real *) p->out,
cannam@95 468 k[0], k[1], k[2], flags);
cannam@95 469 goto done;
cannam@95 470 default: {
cannam@95 471 int *n = mkn(sz);
cannam@95 472 if (verbose > 2) printf("using plan_r2r\n");
cannam@95 473 pln = FFTW(plan_r2r)(sz->rnk, n,
cannam@95 474 (bench_real *) p->in, (bench_real *) p->out,
cannam@95 475 k, flags);
cannam@95 476 bench_free(n);
cannam@95 477 goto done;
cannam@95 478 }
cannam@95 479 }
cannam@95 480
cannam@95 481 api_many:
cannam@95 482 {
cannam@95 483 int *n, *inembed, *onembed;
cannam@95 484 BENCH_ASSERT(vecsz->rnk == 1);
cannam@95 485 n = mkn(sz);
cannam@95 486 mknembed_many(sz, &inembed, &onembed);
cannam@95 487 if (verbose > 2) printf("using plan_many_r2r\n");
cannam@95 488 pln = FFTW(plan_many_r2r)(
cannam@95 489 sz->rnk, n, vecsz->dims[0].n,
cannam@95 490 (bench_real *) p->in,
cannam@95 491 inembed, sz->dims[sz->rnk - 1].is, vecsz->dims[0].is,
cannam@95 492 (bench_real *) p->out,
cannam@95 493 onembed, sz->dims[sz->rnk - 1].os, vecsz->dims[0].os,
cannam@95 494 k, flags);
cannam@95 495 bench_free(n); bench_free(inembed); bench_free(onembed);
cannam@95 496 goto done;
cannam@95 497 }
cannam@95 498
cannam@95 499 api_guru:
cannam@95 500 {
cannam@95 501 FFTW(iodim) *dims, *howmany_dims;
cannam@95 502
cannam@95 503 dims = bench_tensor_to_fftw_iodim(sz);
cannam@95 504 howmany_dims = bench_tensor_to_fftw_iodim(vecsz);
cannam@95 505 if (verbose > 2) printf("using plan_guru_r2r\n");
cannam@95 506 pln = FFTW(plan_guru_r2r)(sz->rnk, dims,
cannam@95 507 vecsz->rnk, howmany_dims,
cannam@95 508 (bench_real *) p->in,
cannam@95 509 (bench_real *) p->out, k, flags);
cannam@95 510 bench_free(dims);
cannam@95 511 bench_free(howmany_dims);
cannam@95 512 goto done;
cannam@95 513 }
cannam@95 514
cannam@95 515 done:
cannam@95 516 bench_free(k);
cannam@95 517 return pln;
cannam@95 518 }
cannam@95 519
cannam@95 520 FFTW(plan) mkplan(bench_problem *p, unsigned flags)
cannam@95 521 {
cannam@95 522 switch (p->kind) {
cannam@95 523 case PROBLEM_COMPLEX: return mkplan_complex(p, flags);
cannam@95 524 case PROBLEM_REAL: return mkplan_real(p, flags);
cannam@95 525 case PROBLEM_R2R: return mkplan_r2r(p, flags);
cannam@95 526 default: BENCH_ASSERT(0); return 0;
cannam@95 527 }
cannam@95 528 }
cannam@95 529
cannam@95 530 void main_init(int *argc, char ***argv)
cannam@95 531 {
cannam@95 532 UNUSED(argc);
cannam@95 533 UNUSED(argv);
cannam@95 534 }
cannam@95 535
cannam@95 536 void initial_cleanup(void)
cannam@95 537 {
cannam@95 538 }
cannam@95 539
cannam@95 540 void final_cleanup(void)
cannam@95 541 {
cannam@95 542 }
cannam@95 543
cannam@95 544 int import_wisdom(FILE *f)
cannam@95 545 {
cannam@95 546 return FFTW(import_wisdom_from_file)(f);
cannam@95 547 }
cannam@95 548
cannam@95 549 void export_wisdom(FILE *f)
cannam@95 550 {
cannam@95 551 FFTW(export_wisdom_to_file)(f);
cannam@95 552 }