Making the MDCT produce interleaved data
[opus.git] / libcelt / dump_modes.c
1 /* Copyright (c) 2008 CSIRO
2    Copyright (c) 2008-2009 Xiph.Org Foundation
3    Written by Jean-Marc Valin */
4 /*
5    Redistribution and use in source and binary forms, with or without
6    modification, are permitted provided that the following conditions
7    are met:
8
9    - Redistributions of source code must retain the above copyright
10    notice, this list of conditions and the following disclaimer.
11
12    - Redistributions in binary form must reproduce the above copyright
13    notice, this list of conditions and the following disclaimer in the
14    documentation and/or other materials provided with the distribution.
15
16    THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
17    ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
18    LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
19    A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR
20    CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
21    EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
22    PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
23    PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
24    LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
25    NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
26    SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 */
28
29 #ifdef HAVE_CONFIG_H
30 #include "config.h"
31 #endif
32
33 #include <stdlib.h>
34 #include <stdio.h>
35 #include "modes.h"
36 #include "celt.h"
37 #include "rate.h"
38
39 #define INT16 "%d"
40 #define INT32 "%d"
41 #define FLOAT "%#0.8gf"
42
43 #ifdef FIXED_POINT
44 #define WORD16 INT16
45 #define WORD32 INT32
46 #else
47 #define WORD16 FLOAT
48 #define WORD32 FLOAT
49 #endif
50
51 void dump_modes(FILE *file, CELTMode **modes, int nb_modes)
52 {
53    int i, j, k;
54    fprintf(file, "/* The contents of this file is automatically generated and contains static\n");
55    fprintf(file, "   definitions for some pre-defined modes */\n");
56    fprintf(file, "#include \"modes.h\"\n");
57    fprintf(file, "#include \"rate.h\"\n");
58
59    fprintf(file, "\n");
60
61    for (i=0;i<nb_modes;i++)
62    {
63       CELTMode *mode = modes[i];
64       int mdctSize;
65       int standard, framerate;
66
67       mdctSize = mode->shortMdctSize*mode->nbShortMdcts;
68       standard = (mode->Fs == 400*(opus_int32)mode->shortMdctSize);
69       framerate = mode->Fs/mode->shortMdctSize;
70
71       if (!standard)
72       {
73          fprintf(file, "#ifndef DEF_EBANDS%d_%d\n", mode->Fs, mdctSize);
74          fprintf(file, "#define DEF_EBANDS%d_%d\n", mode->Fs, mdctSize);
75          fprintf (file, "static const opus_int16 eBands%d_%d[%d] = {\n", mode->Fs, mdctSize, mode->nbEBands+2);
76          for (j=0;j<mode->nbEBands+2;j++)
77             fprintf (file, "%d, ", mode->eBands[j]);
78          fprintf (file, "};\n");
79          fprintf(file, "#endif\n");
80          fprintf(file, "\n");
81       }
82
83       fprintf(file, "#ifndef DEF_WINDOW%d\n", mode->overlap);
84       fprintf(file, "#define DEF_WINDOW%d\n", mode->overlap);
85       fprintf (file, "static const opus_val16 window%d[%d] = {\n", mode->overlap, mode->overlap);
86       for (j=0;j<mode->overlap;j++)
87          fprintf (file, WORD16 ", ", mode->window[j]);
88       fprintf (file, "};\n");
89       fprintf(file, "#endif\n");
90       fprintf(file, "\n");
91
92       if (!standard)
93       {
94          fprintf(file, "#ifndef DEF_ALLOC_VECTORS%d_%d\n", mode->Fs, mdctSize);
95          fprintf(file, "#define DEF_ALLOC_VECTORS%d_%d\n", mode->Fs, mdctSize);
96          fprintf (file, "static const unsigned char allocVectors%d_%d[%d] = {\n", mode->Fs, mdctSize, mode->nbEBands*mode->nbAllocVectors);
97          for (j=0;j<mode->nbAllocVectors;j++)
98          {
99             for (k=0;k<mode->nbEBands;k++)
100                fprintf (file, "%2d, ", mode->allocVectors[j*mode->nbEBands+k]);
101             fprintf (file, "\n");
102          }
103          fprintf (file, "};\n");
104          fprintf(file, "#endif\n");
105          fprintf(file, "\n");
106       }
107
108       fprintf(file, "#ifndef DEF_LOGN%d\n", framerate);
109       fprintf(file, "#define DEF_LOGN%d\n", framerate);
110       fprintf (file, "static const opus_int16 logN%d[%d] = {\n", framerate, mode->nbEBands);
111       for (j=0;j<mode->nbEBands;j++)
112          fprintf (file, "%d, ", mode->logN[j]);
113       fprintf (file, "};\n");
114       fprintf(file, "#endif\n");
115       fprintf(file, "\n");
116
117       /* Pulse cache */
118       fprintf(file, "#ifndef DEF_PULSE_CACHE%d\n", mode->Fs/mdctSize);
119       fprintf(file, "#define DEF_PULSE_CACHE%d\n", mode->Fs/mdctSize);
120       fprintf (file, "static const opus_int16 cache_index%d[%d] = {\n", mode->Fs/mdctSize, (mode->maxLM+2)*mode->nbEBands);
121       for (j=0;j<mode->nbEBands*(mode->maxLM+2);j++)
122          fprintf (file, "%d, ", mode->cache.index[j]);
123       fprintf (file, "};\n");
124       fprintf (file, "static const unsigned char cache_bits%d[%d] = {\n", mode->Fs/mdctSize, mode->cache.size);
125       for (j=0;j<mode->cache.size;j++)
126          fprintf (file, "%d, ", mode->cache.bits[j]);
127       fprintf (file, "};\n");
128       fprintf (file, "static const unsigned char cache_caps%d[%d] = {\n", mode->Fs/mdctSize, (mode->maxLM+1)*2*mode->nbEBands);
129       for (j=0;j<(mode->maxLM+1)*2*mode->nbEBands;j++)
130          fprintf (file, "%d, ", mode->cache.caps[j]);
131       fprintf (file, "};\n");
132
133       fprintf(file, "#endif\n");
134       fprintf(file, "\n");
135
136       /* FFT twiddles */
137       fprintf(file, "#ifndef FFT_TWIDDLES%d_%d\n", mode->Fs, mdctSize);
138       fprintf(file, "#define FFT_TWIDDLES%d_%d\n", mode->Fs, mdctSize);
139       fprintf (file, "static const kiss_twiddle_cpx fft_twiddles%d_%d[%d] = {\n",
140             mode->Fs, mdctSize, mode->mdct.kfft[0]->nfft);
141       for (j=0;j<mode->mdct.kfft[0]->nfft;j++)
142          fprintf (file, "{" WORD16 ", " WORD16 "}, ", mode->mdct.kfft[0]->twiddles[j].r, mode->mdct.kfft[0]->twiddles[j].i);
143       fprintf (file, "};\n");
144
145       /* FFT Bitrev tables */
146       for (k=0;k<=mode->mdct.maxshift;k++)
147       {
148          fprintf(file, "#ifndef FFT_BITREV%d\n", mode->mdct.kfft[k]->nfft);
149          fprintf(file, "#define FFT_BITREV%d\n", mode->mdct.kfft[k]->nfft);
150          fprintf (file, "static const opus_int16 fft_bitrev%d[%d] = {\n",
151                mode->mdct.kfft[k]->nfft, mode->mdct.kfft[k]->nfft);
152          for (j=0;j<mode->mdct.kfft[k]->nfft;j++)
153             fprintf (file, "%d, ", mode->mdct.kfft[k]->bitrev[j]);
154          fprintf (file, "};\n");
155
156          fprintf(file, "#endif\n");
157          fprintf(file, "\n");
158       }
159
160       /* FFT States */
161       for (k=0;k<=mode->mdct.maxshift;k++)
162       {
163          fprintf(file, "#ifndef FFT_STATE%d_%d_%d\n", mode->Fs, mdctSize, k);
164          fprintf(file, "#define FFT_STATE%d_%d_%d\n", mode->Fs, mdctSize, k);
165          fprintf (file, "static const kiss_fft_state fft_state%d_%d_%d = {\n",
166                mode->Fs, mdctSize, k);
167          fprintf (file, "%d,\t/* nfft */\n", mode->mdct.kfft[k]->nfft);
168 #ifndef FIXED_POINT
169          fprintf (file, "%0.9ff,\t/* scale */\n", mode->mdct.kfft[k]->scale);
170 #endif
171          fprintf (file, "%d,\t/* shift */\n", mode->mdct.kfft[k]->shift);
172          fprintf (file, "{");
173          for (j=0;j<2*MAXFACTORS;j++)
174             fprintf (file, "%d, ", mode->mdct.kfft[k]->factors[j]);
175          fprintf (file, "},\t/* factors */\n");
176          fprintf (file, "fft_bitrev%d,\t/* bitrev */\n", mode->mdct.kfft[k]->nfft);
177          fprintf (file, "fft_twiddles%d_%d,\t/* bitrev */\n", mode->Fs, mdctSize);
178          fprintf (file, "};\n");
179
180          fprintf(file, "#endif\n");
181          fprintf(file, "\n");
182       }
183
184       fprintf(file, "#endif\n");
185       fprintf(file, "\n");
186
187       /* MDCT twiddles */
188       fprintf(file, "#ifndef MDCT_TWIDDLES%d\n", mdctSize);
189       fprintf(file, "#define MDCT_TWIDDLES%d\n", mdctSize);
190       fprintf (file, "static const opus_val16 mdct_twiddles%d[%d] = {\n",
191             mdctSize, mode->mdct.n/4+1);
192       for (j=0;j<=mode->mdct.n/4;j++)
193          fprintf (file, WORD16 ", ", mode->mdct.trig[j]);
194       fprintf (file, "};\n");
195
196       fprintf(file, "#endif\n");
197       fprintf(file, "\n");
198
199
200       /* Print the actual mode data */
201       fprintf(file, "static const CELTMode mode%d_%d_%d = {\n", mode->Fs, mdctSize, mode->overlap);
202       fprintf(file, INT32 ",\t/* Fs */\n", mode->Fs);
203       fprintf(file, "%d,\t/* overlap */\n", mode->overlap);
204       fprintf(file, "%d,\t/* nbEBands */\n", mode->nbEBands);
205       fprintf(file, "%d,\t/* effEBands */\n", mode->effEBands);
206       fprintf(file, "{");
207       for (j=0;j<4;j++)
208          fprintf(file, WORD16 ", ", mode->preemph[j]);
209       fprintf(file, "},\t/* preemph */\n");
210       if (standard)
211          fprintf(file, "eband5ms,\t/* eBands */\n");
212       else
213          fprintf(file, "eBands%d_%d,\t/* eBands */\n", mode->Fs, mdctSize);
214
215       fprintf(file, "%d,\t/* maxLM */\n", mode->maxLM);
216       fprintf(file, "%d,\t/* nbShortMdcts */\n", mode->nbShortMdcts);
217       fprintf(file, "%d,\t/* shortMdctSize */\n", mode->shortMdctSize);
218
219       fprintf(file, "%d,\t/* nbAllocVectors */\n", mode->nbAllocVectors);
220       if (standard)
221          fprintf(file, "band_allocation,\t/* allocVectors */\n");
222       else
223          fprintf(file, "allocVectors%d_%d,\t/* allocVectors */\n", mode->Fs, mdctSize);
224
225       fprintf(file, "logN%d,\t/* logN */\n", framerate);
226       fprintf(file, "window%d,\t/* window */\n", mode->overlap);
227       fprintf(file, "{%d, %d, {", mode->mdct.n, mode->mdct.maxshift);
228       for (k=0;k<=mode->mdct.maxshift;k++)
229          fprintf(file, "&fft_state%d_%d_%d, ", mode->Fs, mdctSize, k);
230       fprintf (file, "}, mdct_twiddles%d},\t/* mdct */\n", mdctSize);
231
232       fprintf(file, "{%d, cache_index%d, cache_bits%d, cache_caps%d},\t/* cache */\n",
233             mode->cache.size, mode->Fs/mdctSize, mode->Fs/mdctSize, mode->Fs/mdctSize);
234       fprintf(file, "};\n");
235    }
236    fprintf(file, "\n");
237    fprintf(file, "/* List of all the available modes */\n");
238    fprintf(file, "#define TOTAL_MODES %d\n", nb_modes);
239    fprintf(file, "static const CELTMode * const static_mode_list[TOTAL_MODES] = {\n");
240    for (i=0;i<nb_modes;i++)
241    {
242       CELTMode *mode = modes[i];
243       int mdctSize;
244       mdctSize = mode->shortMdctSize*mode->nbShortMdcts;
245       fprintf(file, "&mode%d_%d_%d,\n", mode->Fs, mdctSize, mode->overlap);
246    }
247    fprintf(file, "};\n");
248 }
249
250 void dump_header(FILE *file, CELTMode **modes, int nb_modes)
251 {
252    int i;
253    int channels = 0;
254    int frame_size = 0;
255    int overlap = 0;
256    fprintf (file, "/* This header file is generated automatically*/\n");
257    for (i=0;i<nb_modes;i++)
258    {
259       CELTMode *mode = modes[i];
260       if (frame_size==0)
261          frame_size = mode->shortMdctSize*mode->nbShortMdcts;
262       else if (frame_size != mode->shortMdctSize*mode->nbShortMdcts)
263          frame_size = -1;
264       if (overlap==0)
265          overlap = mode->overlap;
266       else if (overlap != mode->overlap)
267          overlap = -1;
268    }
269    if (channels>0)
270    {
271       fprintf (file, "#define CHANNELS(mode) %d\n", channels);
272       if (channels==1)
273          fprintf (file, "#define DISABLE_STEREO\n");
274    }
275    if (frame_size>0)
276    {
277       fprintf (file, "#define FRAMESIZE(mode) %d\n", frame_size);
278    }
279    if (overlap>0)
280    {
281       fprintf (file, "#define OVERLAP(mode) %d\n", overlap);
282    }
283 }
284
285 #ifdef FIXED_POINT
286 #define BASENAME "static_modes_fixed"
287 #else
288 #define BASENAME "static_modes_float"
289 #endif
290
291 int main(int argc, char **argv)
292 {
293    int i, nb;
294    FILE *file;
295    CELTMode **m;
296    if (argc%2 != 1)
297    {
298       fprintf (stderr, "must have a multiple of 2 arguments\n");
299       return 1;
300    }
301    nb = (argc-1)/2;
302    m = malloc(nb*sizeof(CELTMode*));
303    for (i=0;i<nb;i++)
304    {
305       int Fs, frame;
306       Fs      = atoi(argv[2*i+1]);
307       frame   = atoi(argv[2*i+2]);
308       m[i] = celt_mode_create(Fs, frame, NULL);
309       if (m[i]==NULL)
310       {
311          fprintf(stderr,"Error creating mode with Fs=%s, frame_size=%s\n",
312                argv[2*i+1],argv[2*i+2]);
313          return EXIT_FAILURE;
314       }
315    }
316    file = fopen(BASENAME ".h", "w");
317    dump_modes(file, m, nb);
318    fclose(file);
319    for (i=0;i<nb;i++)
320       celt_mode_destroy(m[i]);
321    free(m);
322    return 0;
323 }