update copyright for 2001
[flac.git] / src / test_streams / main.c
1 /* test_streams - Simple test pattern generator
2  * Copyright (C) 2000,2001  Josh Coalson
3  *
4  * This program is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU General Public License
6  * as published by the Free Software Foundation; either version 2
7  * of the License, or (at your option) any later version.
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12  * GNU General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with this program; if not, write to the Free Software
16  * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
17  */
18
19 #include <math.h>
20 #include <stdio.h>
21 #include <stdlib.h>
22 #include <assert.h>
23 #include "FLAC/ordinals.h"
24
25 #ifdef _WIN32
26         static const char *mode = "wb";
27 #else
28         static const char *mode = "w";
29 #endif
30
31 static bool is_big_endian_host;
32
33 static void swap16(int16 *i)
34 {
35         unsigned char *x = (unsigned char *)i, b;
36         if(!is_big_endian_host) {
37                 b = x[0];
38                 x[0] = x[1];
39                 x[1] = b;
40         }
41 }
42
43 /* a mono one-sample 16bps stream */
44 static bool generate_01()
45 {
46         FILE *f;
47         int16 x = -32768;
48
49         if(0 == (f = fopen("test01.raw", mode)))
50                 return false;
51
52         swap16(&x);
53         if(fwrite(&x, sizeof(x), 1, f) < 1)
54                 goto foo;
55
56         fclose(f);
57         return true;
58 foo:
59         fclose(f);
60         return false;
61 }
62
63 /* a stereo one-sample 16bps stream */
64 static bool generate_02()
65 {
66         FILE *f;
67         int16 xl = -32768, xr = 32767;
68
69         if(0 == (f = fopen("test02.raw", mode)))
70                 return false;
71
72         swap16(&xl);
73         swap16(&xr);
74
75         if(fwrite(&xl, sizeof(xl), 1, f) < 1)
76                 goto foo;
77         if(fwrite(&xr, sizeof(xr), 1, f) < 1)
78                 goto foo;
79
80         fclose(f);
81         return true;
82 foo:
83         fclose(f);
84         return false;
85 }
86
87 /* a mono five-sample 16bps stream */
88 static bool generate_03()
89 {
90         FILE *f;
91         int16 x[] = { -25, 0, 25, 50, 100 };
92         unsigned i;
93
94         if(0 == (f = fopen("test03.raw", mode)))
95                 return false;
96
97         for(i = 0; i < 5; i++)
98                 swap16(x+i);
99
100         if(fwrite(&x, sizeof(int16), 5, f) < 5)
101                 goto foo;
102
103         fclose(f);
104         return true;
105 foo:
106         fclose(f);
107         return false;
108 }
109
110 /* a stereo five-sample 16bps stream */
111 static bool generate_04()
112 {
113         FILE *f;
114         int16 x[] = { -25, 500, 0, 400, 25, 300, 50, 200, 100, 100 };
115         unsigned i;
116
117         if(0 == (f = fopen("test04.raw", mode)))
118                 return false;
119
120         for(i = 0; i < 10; i++)
121                 swap16(x+i);
122
123         if(fwrite(&x, sizeof(int16), 10, f) < 10)
124                 goto foo;
125
126         fclose(f);
127         return true;
128 foo:
129         fclose(f);
130         return false;
131 }
132
133 /* a mono full-scale deflection 8bps stream */
134 static bool generate_fsd8(const char *fn, const int pattern[], unsigned reps)
135 {
136         FILE *f;
137         unsigned rep, p;
138
139         assert(pattern != 0);
140
141         if(0 == (f = fopen(fn, mode)))
142                 return false;
143
144         for(rep = 0; rep < reps; rep++) {
145                 for(p = 0; pattern[p]; p++) {
146                         signed char x = pattern[p] > 0? 127 : -128;
147                         if(fwrite(&x, sizeof(x), 1, f) < 1)
148                                 goto foo;
149                 }
150         }
151
152         fclose(f);
153         return true;
154 foo:
155         fclose(f);
156         return false;
157 }
158
159 /* a mono full-scale deflection 16bps stream */
160 static bool generate_fsd16(const char *fn, const int pattern[], unsigned reps)
161 {
162         FILE *f;
163         unsigned rep, p;
164
165         assert(pattern != 0);
166
167         if(0 == (f = fopen(fn, mode)))
168                 return false;
169
170         for(rep = 0; rep < reps; rep++) {
171                 for(p = 0; pattern[p]; p++) {
172                         int16 x = pattern[p] > 0? 32767 : -32768;
173                         swap16(&x);
174                         if(fwrite(&x, sizeof(x), 1, f) < 1)
175                                 goto foo;
176                 }
177         }
178
179         fclose(f);
180         return true;
181 foo:
182         fclose(f);
183         return false;
184 }
185
186 /* a mono sine-wave 16bps stream */
187 static bool generate_sine16(const char *fn, const double sample_rate, const unsigned samples, const double f1, const double a1, const double f2, const double a2)
188 {
189         const signed short full_scale = 32767;
190         const double delta1 = 2.0 * M_PI / ( sample_rate / f1);
191         const double delta2 = 2.0 * M_PI / ( sample_rate / f2);
192         FILE *f;
193         double theta1, theta2;
194         unsigned i;
195
196         if(0 == (f = fopen(fn, mode)))
197                 return false;
198
199         for(i = 0, theta1 = theta2 = 0.0; i < samples; i++, theta1 += delta1, theta2 += delta2) {
200                 double val = (a1*sin(theta1) + a2*sin(theta2))*(double)full_scale;
201                 int16 v = (int16)(val + 0.5);
202                 swap16(&v);
203                 if(fwrite(&v, sizeof(v), 1, f) < 1)
204                         goto foo;
205         }
206
207         fclose(f);
208         return true;
209 foo:
210         fclose(f);
211         return false;
212 }
213
214 int main(int argc, char *argv[])
215 {
216         uint32 test = 1;
217
218         int pattern01[] = { 1, -1, 0 };
219         int pattern02[] = { 1, 1, -1, 0 };
220         int pattern03[] = { 1, -1, -1, 0 };
221         int pattern04[] = { 1, -1, 1, -1, 0 };
222         int pattern05[] = { 1, -1, -1, 1, 0 };
223         int pattern06[] = { 1, -1, 1, 1, -1, 0 };
224         int pattern07[] = { 1, -1, -1, 1, -1, 0 };
225
226         (void)argc;
227         (void)argv;
228         is_big_endian_host = (*((byte*)(&test)))? false : true;
229
230         if(!generate_01()) return 1;
231         if(!generate_02()) return 1;
232         if(!generate_03()) return 1;
233         if(!generate_04()) return 1;
234
235         if(!generate_fsd8("fsd8-01.raw", pattern01, 100)) return 1;
236         if(!generate_fsd8("fsd8-02.raw", pattern02, 100)) return 1;
237         if(!generate_fsd8("fsd8-03.raw", pattern03, 100)) return 1;
238         if(!generate_fsd8("fsd8-04.raw", pattern04, 100)) return 1;
239         if(!generate_fsd8("fsd8-05.raw", pattern05, 100)) return 1;
240         if(!generate_fsd8("fsd8-06.raw", pattern06, 100)) return 1;
241         if(!generate_fsd8("fsd8-07.raw", pattern07, 100)) return 1;
242
243         if(!generate_fsd16("fsd16-01.raw", pattern01, 100)) return 1;
244         if(!generate_fsd16("fsd16-02.raw", pattern02, 100)) return 1;
245         if(!generate_fsd16("fsd16-03.raw", pattern03, 100)) return 1;
246         if(!generate_fsd16("fsd16-04.raw", pattern04, 100)) return 1;
247         if(!generate_fsd16("fsd16-05.raw", pattern05, 100)) return 1;
248         if(!generate_fsd16("fsd16-06.raw", pattern06, 100)) return 1;
249         if(!generate_fsd16("fsd16-07.raw", pattern07, 100)) return 1;
250
251         if(!generate_sine16("sine-01.raw", 44100.0, 80000, 441.0, 0.50, 441.0, 0.49)) return 1;
252         if(!generate_sine16("sine-02.raw", 44100.0, 80000, 441.0, 0.61, 661.5, 0.37)) return 1;
253         if(!generate_sine16("sine-03.raw", 44100.0, 80000, 441.0, 0.50, 882.0, 0.49)) return 1;
254         if(!generate_sine16("sine-04.raw", 44100.0, 80000, 441.0, 0.50, 4410.0, 0.49)) return 1;
255         if(!generate_sine16("sine-05.raw", 44100.0, 50000, 8820.0, 0.70, 4410.0, 0.29)) return 1;
256
257         return 0;
258 }