blob: 132d074d3025456f9d2297e7988e85ac51610b85 [file] [log] [blame]
tlegrand@chromium.orge3ea0492013-10-23 09:13:50 +00001/* Copyright (c) 2011-2013 Xiph.Org Foundation
sergeyu@chromium.org885f2ff2012-10-17 22:31:52 +00002 Written by Gregory Maxwell */
3/*
4 Redistribution and use in source and binary forms, with or without
5 modification, are permitted provided that the following conditions
6 are met:
7
8 - Redistributions of source code must retain the above copyright
9 notice, this list of conditions and the following disclaimer.
10
11 - Redistributions in binary form must reproduce the above copyright
12 notice, this list of conditions and the following disclaimer in the
13 documentation and/or other materials provided with the distribution.
14
15 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
16 ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
17 LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
18 A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER
19 OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
20 EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
21 PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
22 PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
23 LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
24 NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26*/
27
28#ifdef HAVE_CONFIG_H
29#include "config.h"
30#endif
31
32#include <stdio.h>
33#include <stdlib.h>
34#include <limits.h>
35#include <stdint.h>
36#include <math.h>
37#include <string.h>
38#include <time.h>
39#if (!defined WIN32 && !defined _WIN32) || defined(__MINGW32__)
40#include <unistd.h>
sergeyu@chromium.org6b6bee22013-02-28 21:17:26 +000041#else
42#include <process.h>
43#define getpid _getpid
sergeyu@chromium.org885f2ff2012-10-17 22:31:52 +000044#endif
45#include "opus_multistream.h"
46#include "opus.h"
47#include "../src/opus_private.h"
48#include "test_opus_common.h"
49
50#define MAX_PACKET (1500)
51#define SAMPLES (48000*30)
52#define SSAMPLES (SAMPLES/3)
53#define MAX_FRAME_SAMP (5760)
54
55#define PI (3.141592653589793238462643f)
56
57void generate_music(short *buf, opus_int32 len)
58{
59 opus_int32 a1,b1,a2,b2;
60 opus_int32 c1,c2,d1,d2;
61 opus_int32 i,j;
62 a1=b1=a2=b2=0;
63 c1=c2=d1=d2=0;
64 j=0;
65 /*60ms silence*/
66 for(i=0;i<2880;i++)buf[i*2]=buf[i*2+1]=0;
67 for(i=2880;i<len;i++)
68 {
69 opus_uint32 r;
70 opus_int32 v1,v2;
71 v1=v2=(((j*((j>>12)^((j>>10|j>>12)&26&j>>7)))&128)+128)<<15;
72 r=fast_rand();v1+=r&65535;v1-=r>>16;
73 r=fast_rand();v2+=r&65535;v2-=r>>16;
74 b1=v1-a1+((b1*61+32)>>6);a1=v1;
75 b2=v2-a2+((b2*61+32)>>6);a2=v2;
76 c1=(30*(c1+b1+d1)+32)>>6;d1=b1;
77 c2=(30*(c2+b2+d2)+32)>>6;d2=b2;
78 v1=(c1+128)>>8;
79 v2=(c2+128)>>8;
80 buf[i*2]=v1>32767?32767:(v1<-32768?-32768:v1);
81 buf[i*2+1]=v2>32767?32767:(v2<-32768?-32768:v2);
82 if(i%6==0)j++;
83 }
84}
85
86#if 0
87static int save_ctr = 0;
88static void int_to_char(opus_uint32 i, unsigned char ch[4])
89{
90 ch[0] = i>>24;
91 ch[1] = (i>>16)&0xFF;
92 ch[2] = (i>>8)&0xFF;
93 ch[3] = i&0xFF;
94}
95
tlegrand@google.com3c3902f2013-12-09 08:35:25 +000096static OPUS_INLINE void save_packet(unsigned char* p, int len, opus_uint32 rng)
sergeyu@chromium.org885f2ff2012-10-17 22:31:52 +000097{
98 FILE *fout;
99 unsigned char int_field[4];
100 char name[256];
101 snprintf(name,255,"test_opus_encode.%llu.%d.bit",(unsigned long long)iseed,save_ctr);
102 fprintf(stdout,"writing %d byte packet to %s\n",len,name);
103 fout=fopen(name, "wb+");
104 if(fout==NULL)test_failed();
105 int_to_char(len, int_field);
106 fwrite(int_field, 1, 4, fout);
107 int_to_char(rng, int_field);
108 fwrite(int_field, 1, 4, fout);
109 fwrite(p, 1, len, fout);
110 fclose(fout);
111 save_ctr++;
112}
113#endif
114
115int run_test1(int no_fuzz)
116{
117 static const int fsizes[6]={960*3,960*2,120,240,480,960};
118 static const char *mstrings[3] = {" LP","Hybrid"," MDCT"};
119 unsigned char mapping[256] = {0,1,255};
120 unsigned char db62[36];
121 opus_int32 i;
122 int rc,j,err;
123 OpusEncoder *enc;
124 OpusMSEncoder *MSenc;
125 OpusDecoder *dec;
126 OpusMSDecoder *MSdec;
127 OpusMSDecoder *MSdec_err;
128 OpusDecoder *dec_err[10];
129 short *inbuf;
130 short *outbuf;
131 short *out2buf;
132 opus_int32 bitrate_bps;
tlegrand@google.com3c3902f2013-12-09 08:35:25 +0000133 unsigned char packet[MAX_PACKET+257];
sergeyu@chromium.org885f2ff2012-10-17 22:31:52 +0000134 opus_uint32 enc_final_range;
135 opus_uint32 dec_final_range;
136 int fswitch;
137 int fsize;
138 int count;
139
140 /*FIXME: encoder api tests, fs!=48k, mono, VBR*/
141
142 fprintf(stdout," Encode+Decode tests.\n");
143
144 enc = opus_encoder_create(48000, 2, OPUS_APPLICATION_VOIP, &err);
145 if(err != OPUS_OK || enc==NULL)test_failed();
146
sergeyu@chromium.org6b6bee22013-02-28 21:17:26 +0000147 for(i=0;i<2;i++)
148 {
149 int *ret_err;
150 ret_err = i?0:&err;
151 MSenc = opus_multistream_encoder_create(8000, 2, 2, 0, mapping, OPUS_UNIMPLEMENTED, ret_err);
152 if((ret_err && *ret_err != OPUS_BAD_ARG) || MSenc!=NULL)test_failed();
153
154 MSenc = opus_multistream_encoder_create(8000, 0, 1, 0, mapping, OPUS_APPLICATION_VOIP, ret_err);
155 if((ret_err && *ret_err != OPUS_BAD_ARG) || MSenc!=NULL)test_failed();
156
157 MSenc = opus_multistream_encoder_create(44100, 2, 2, 0, mapping, OPUS_APPLICATION_VOIP, ret_err);
158 if((ret_err && *ret_err != OPUS_BAD_ARG) || MSenc!=NULL)test_failed();
159
160 MSenc = opus_multistream_encoder_create(8000, 2, 2, 3, mapping, OPUS_APPLICATION_VOIP, ret_err);
161 if((ret_err && *ret_err != OPUS_BAD_ARG) || MSenc!=NULL)test_failed();
162
163 MSenc = opus_multistream_encoder_create(8000, 2, -1, 0, mapping, OPUS_APPLICATION_VOIP, ret_err);
164 if((ret_err && *ret_err != OPUS_BAD_ARG) || MSenc!=NULL)test_failed();
165
166 MSenc = opus_multistream_encoder_create(8000, 256, 2, 0, mapping, OPUS_APPLICATION_VOIP, ret_err);
167 if((ret_err && *ret_err != OPUS_BAD_ARG) || MSenc!=NULL)test_failed();
168 }
169
sergeyu@chromium.org885f2ff2012-10-17 22:31:52 +0000170 MSenc = opus_multistream_encoder_create(8000, 2, 2, 0, mapping, OPUS_APPLICATION_AUDIO, &err);
171 if(err != OPUS_OK || MSenc==NULL)test_failed();
172
sergeyu@chromium.org6b6bee22013-02-28 21:17:26 +0000173 /*Some multistream encoder API tests*/
sergeyu@chromium.org885f2ff2012-10-17 22:31:52 +0000174 if(opus_multistream_encoder_ctl(MSenc, OPUS_GET_BITRATE(&i))!=OPUS_OK)test_failed();
175 if(opus_multistream_encoder_ctl(MSenc, OPUS_GET_LSB_DEPTH(&i))!=OPUS_OK)test_failed();
sergeyu@chromium.org6b6bee22013-02-28 21:17:26 +0000176 if(i<16)test_failed();
177
178 {
179 OpusEncoder *tmp_enc;
180 if(opus_multistream_encoder_ctl(MSenc, OPUS_MULTISTREAM_GET_ENCODER_STATE(1,&tmp_enc))!=OPUS_OK)test_failed();
181 if(opus_encoder_ctl(tmp_enc, OPUS_GET_LSB_DEPTH(&j))!=OPUS_OK)test_failed();
182 if(i!=j)test_failed();
183 if(opus_multistream_encoder_ctl(MSenc, OPUS_MULTISTREAM_GET_ENCODER_STATE(2,&tmp_enc))!=OPUS_BAD_ARG)test_failed();
184 }
sergeyu@chromium.org885f2ff2012-10-17 22:31:52 +0000185
186 dec = opus_decoder_create(48000, 2, &err);
187 if(err != OPUS_OK || dec==NULL)test_failed();
188
189 MSdec = opus_multistream_decoder_create(48000, 2, 2, 0, mapping, &err);
190 if(err != OPUS_OK || MSdec==NULL)test_failed();
191
192 MSdec_err = opus_multistream_decoder_create(48000, 3, 2, 0, mapping, &err);
193 if(err != OPUS_OK || MSdec_err==NULL)test_failed();
194
195 dec_err[0]=(OpusDecoder *)malloc(opus_decoder_get_size(2));
196 memcpy(dec_err[0],dec,opus_decoder_get_size(2));
197 dec_err[1] = opus_decoder_create(48000, 1, &err);
198 dec_err[2] = opus_decoder_create(24000, 2, &err);
199 dec_err[3] = opus_decoder_create(24000, 1, &err);
200 dec_err[4] = opus_decoder_create(16000, 2, &err);
201 dec_err[5] = opus_decoder_create(16000, 1, &err);
202 dec_err[6] = opus_decoder_create(12000, 2, &err);
203 dec_err[7] = opus_decoder_create(12000, 1, &err);
204 dec_err[8] = opus_decoder_create(8000, 2, &err);
205 dec_err[9] = opus_decoder_create(8000, 1, &err);
206 for(i=0;i<10;i++)if(dec_err[i]==NULL)test_failed();
207
208 {
209 OpusEncoder *enccpy;
210 /*The opus state structures contain no pointers and can be freely copied*/
211 enccpy=(OpusEncoder *)malloc(opus_encoder_get_size(2));
212 memcpy(enccpy,enc,opus_encoder_get_size(2));
213 memset(enc,255,opus_encoder_get_size(2));
214 opus_encoder_destroy(enc);
215 enc=enccpy;
216 }
217
218 inbuf=(short *)malloc(sizeof(short)*SAMPLES*2);
219 outbuf=(short *)malloc(sizeof(short)*SAMPLES*2);
220 out2buf=(short *)malloc(sizeof(short)*MAX_FRAME_SAMP*3);
221 if(inbuf==NULL || outbuf==NULL || out2buf==NULL)test_failed();
222
223 generate_music(inbuf,SAMPLES);
224
225/* FILE *foo;
226 foo = fopen("foo.sw", "wb+");
227 fwrite(inbuf, 1, SAMPLES*2*2, foo);
228 fclose(foo);*/
229
230 if(opus_encoder_ctl(enc, OPUS_SET_BANDWIDTH(OPUS_AUTO))!=OPUS_OK)test_failed();
231 if(opus_encoder_ctl(enc, OPUS_SET_FORCE_MODE(-2))!=OPUS_BAD_ARG)test_failed();
232
233 for(rc=0;rc<3;rc++)
234 {
235 if(opus_encoder_ctl(enc, OPUS_SET_VBR(rc<2))!=OPUS_OK)test_failed();
236 if(opus_encoder_ctl(enc, OPUS_SET_VBR_CONSTRAINT(rc==1))!=OPUS_OK)test_failed();
237 if(opus_encoder_ctl(enc, OPUS_SET_VBR_CONSTRAINT(rc==1))!=OPUS_OK)test_failed();
238 if(opus_encoder_ctl(enc, OPUS_SET_INBAND_FEC(rc==0))!=OPUS_OK)test_failed();
239 for(j=0;j<13;j++)
240 {
241 int rate;
242 int modes[13]={0,0,0,1,1,1,1,2,2,2,2,2,2};
243 int rates[13]={6000,12000,48000,16000,32000,48000,64000,512000,13000,24000,48000,64000,96000};
244 int frame[13]={960*2,960,480,960,960,960,480,960*3,960*3,960,480,240,120};
245 rate=rates[j]+fast_rand()%rates[j];
246 count=i=0;
247 do {
248 int bw,len,out_samples,frame_size;
249 frame_size=frame[j];
tlegrand@google.com3c3902f2013-12-09 08:35:25 +0000250 if((fast_rand()&255)==0)
251 {
252 if(opus_encoder_ctl(enc, OPUS_RESET_STATE)!=OPUS_OK)test_failed();
253 if(opus_decoder_ctl(dec, OPUS_RESET_STATE)!=OPUS_OK)test_failed();
254 if((fast_rand()&1)!=0)
255 {
256 if(opus_decoder_ctl(dec_err[fast_rand()&1], OPUS_RESET_STATE)!=OPUS_OK)test_failed();
257 }
258 }
259 if((fast_rand()&127)==0)
260 {
261 if(opus_decoder_ctl(dec_err[fast_rand()&1], OPUS_RESET_STATE)!=OPUS_OK)test_failed();
262 }
tlegrand@chromium.orge3ea0492013-10-23 09:13:50 +0000263 if(fast_rand()%10==0){
264 int complex=fast_rand()%11;
265 if(opus_encoder_ctl(enc, OPUS_SET_COMPLEXITY(complex))!=OPUS_OK)test_failed();
266 }
sergeyu@chromium.org885f2ff2012-10-17 22:31:52 +0000267 if(fast_rand()%50==0)opus_decoder_ctl(dec, OPUS_RESET_STATE);
268 if(opus_encoder_ctl(enc, OPUS_SET_INBAND_FEC(rc==0))!=OPUS_OK)test_failed();
269 if(opus_encoder_ctl(enc, OPUS_SET_FORCE_MODE(MODE_SILK_ONLY+modes[j]))!=OPUS_OK)test_failed();
270 if(opus_encoder_ctl(enc, OPUS_SET_DTX(fast_rand()&1))!=OPUS_OK)test_failed();
271 if(opus_encoder_ctl(enc, OPUS_SET_BITRATE(rate))!=OPUS_OK)test_failed();
272 if(opus_encoder_ctl(enc, OPUS_SET_FORCE_CHANNELS((rates[j]>=64000?2:1)))!=OPUS_OK)test_failed();
273 if(opus_encoder_ctl(enc, OPUS_SET_COMPLEXITY((count>>2)%11))!=OPUS_OK)test_failed();
274 if(opus_encoder_ctl(enc, OPUS_SET_PACKET_LOSS_PERC((fast_rand()&15)&(fast_rand()%15)))!=OPUS_OK)test_failed();
275 bw=modes[j]==0?OPUS_BANDWIDTH_NARROWBAND+(fast_rand()%3):
276 modes[j]==1?OPUS_BANDWIDTH_SUPERWIDEBAND+(fast_rand()&1):
277 OPUS_BANDWIDTH_NARROWBAND+(fast_rand()%5);
278 if(modes[j]==2&&bw==OPUS_BANDWIDTH_MEDIUMBAND)bw+=3;
279 if(opus_encoder_ctl(enc, OPUS_SET_BANDWIDTH(bw))!=OPUS_OK)test_failed();
280 len = opus_encode(enc, &inbuf[i<<1], frame_size, packet, MAX_PACKET);
281 if(len<0 || len>MAX_PACKET)test_failed();
282 if(opus_encoder_ctl(enc, OPUS_GET_FINAL_RANGE(&enc_final_range))!=OPUS_OK)test_failed();
tlegrand@google.com3c3902f2013-12-09 08:35:25 +0000283 if((fast_rand()&3)==0)
284 {
285 if(opus_packet_pad(packet,len,len+1)!=OPUS_OK)test_failed();
286 len++;
287 }
288 if((fast_rand()&7)==0)
289 {
290 if(opus_packet_pad(packet,len,len+256)!=OPUS_OK)test_failed();
291 len+=256;
292 }
293 if((fast_rand()&3)==0)
294 {
295 len=opus_packet_unpad(packet,len);
296 if(len<1)test_failed();
297 }
sergeyu@chromium.org885f2ff2012-10-17 22:31:52 +0000298 out_samples = opus_decode(dec, packet, len, &outbuf[i<<1], MAX_FRAME_SAMP, 0);
299 if(out_samples!=frame_size)test_failed();
300 if(opus_decoder_ctl(dec, OPUS_GET_FINAL_RANGE(&dec_final_range))!=OPUS_OK)test_failed();
301 if(enc_final_range!=dec_final_range)test_failed();
302 /*LBRR decode*/
sergeyu@chromium.org6b6bee22013-02-28 21:17:26 +0000303 out_samples = opus_decode(dec_err[0], packet, len, out2buf, frame_size, (fast_rand()&3)!=0);
sergeyu@chromium.org885f2ff2012-10-17 22:31:52 +0000304 if(out_samples!=frame_size)test_failed();
305 out_samples = opus_decode(dec_err[1], packet, (fast_rand()&3)==0?0:len, out2buf, MAX_FRAME_SAMP, (fast_rand()&7)!=0);
306 if(out_samples<120)test_failed();
307 i+=frame_size;
308 count++;
309 }while(i<(SSAMPLES-MAX_FRAME_SAMP));
310 fprintf(stdout," Mode %s FB encode %s, %6d bps OK.\n",mstrings[modes[j]],rc==0?" VBR":rc==1?"CVBR":" CBR",rate);
311 }
312 }
313
314 if(opus_encoder_ctl(enc, OPUS_SET_FORCE_MODE(OPUS_AUTO))!=OPUS_OK)test_failed();
315 if(opus_encoder_ctl(enc, OPUS_SET_FORCE_CHANNELS(OPUS_AUTO))!=OPUS_OK)test_failed();
316 if(opus_encoder_ctl(enc, OPUS_SET_INBAND_FEC(0))!=OPUS_OK)test_failed();
317 if(opus_encoder_ctl(enc, OPUS_SET_DTX(0))!=OPUS_OK)test_failed();
318
319 for(rc=0;rc<3;rc++)
320 {
321 if(opus_multistream_encoder_ctl(MSenc, OPUS_SET_VBR(rc<2))!=OPUS_OK)test_failed();
322 if(opus_multistream_encoder_ctl(MSenc, OPUS_SET_VBR_CONSTRAINT(rc==1))!=OPUS_OK)test_failed();
323 if(opus_multistream_encoder_ctl(MSenc, OPUS_SET_VBR_CONSTRAINT(rc==1))!=OPUS_OK)test_failed();
324 if(opus_multistream_encoder_ctl(MSenc, OPUS_SET_INBAND_FEC(rc==0))!=OPUS_OK)test_failed();
325 for(j=0;j<16;j++)
326 {
327 int rate;
328 int modes[16]={0,0,0,0,0,0,0,0,2,2,2,2,2,2,2,2};
329 int rates[16]={4000,12000,32000,8000,16000,32000,48000,88000,4000,12000,32000,8000,16000,32000,48000,88000};
330 int frame[16]={160*1,160,80,160,160,80,40,20,160*1,160,80,160,160,80,40,20};
331 if(opus_multistream_encoder_ctl(MSenc, OPUS_SET_INBAND_FEC(rc==0&&j==1))!=OPUS_OK)test_failed();
332 if(opus_multistream_encoder_ctl(MSenc, OPUS_SET_FORCE_MODE(MODE_SILK_ONLY+modes[j]))!=OPUS_OK)test_failed();
333 rate=rates[j]+fast_rand()%rates[j];
334 if(opus_multistream_encoder_ctl(MSenc, OPUS_SET_DTX(fast_rand()&1))!=OPUS_OK)test_failed();
335 if(opus_multistream_encoder_ctl(MSenc, OPUS_SET_BITRATE(rate))!=OPUS_OK)test_failed();
336 count=i=0;
337 do {
tlegrand@google.com3c3902f2013-12-09 08:35:25 +0000338 int pred,len,out_samples,frame_size,loss;
339 if(opus_multistream_encoder_ctl(MSenc, OPUS_GET_PREDICTION_DISABLED(&pred))!=OPUS_OK)test_failed();
340 if(opus_multistream_encoder_ctl(MSenc, OPUS_SET_PREDICTION_DISABLED((int)(fast_rand()&15)<(pred?11:4)))!=OPUS_OK)test_failed();
sergeyu@chromium.org885f2ff2012-10-17 22:31:52 +0000341 frame_size=frame[j];
342 if(opus_multistream_encoder_ctl(MSenc, OPUS_SET_COMPLEXITY((count>>2)%11))!=OPUS_OK)test_failed();
343 if(opus_multistream_encoder_ctl(MSenc, OPUS_SET_PACKET_LOSS_PERC((fast_rand()&15)&(fast_rand()%15)))!=OPUS_OK)test_failed();
tlegrand@google.com3c3902f2013-12-09 08:35:25 +0000344 if((fast_rand()&255)==0)
345 {
346 if(opus_multistream_encoder_ctl(MSenc, OPUS_RESET_STATE)!=OPUS_OK)test_failed();
347 if(opus_multistream_decoder_ctl(MSdec, OPUS_RESET_STATE)!=OPUS_OK)test_failed();
348 if((fast_rand()&3)!=0)
349 {
350 if(opus_multistream_decoder_ctl(MSdec_err, OPUS_RESET_STATE)!=OPUS_OK)test_failed();
351 }
352 }
353 if((fast_rand()&255)==0)
354 {
355 if(opus_multistream_decoder_ctl(MSdec_err, OPUS_RESET_STATE)!=OPUS_OK)test_failed();
356 }
sergeyu@chromium.org885f2ff2012-10-17 22:31:52 +0000357 len = opus_multistream_encode(MSenc, &inbuf[i<<1], frame_size, packet, MAX_PACKET);
358 if(len<0 || len>MAX_PACKET)test_failed();
359 if(opus_multistream_encoder_ctl(MSenc, OPUS_GET_FINAL_RANGE(&enc_final_range))!=OPUS_OK)test_failed();
tlegrand@google.com3c3902f2013-12-09 08:35:25 +0000360 if((fast_rand()&3)==0)
361 {
362 if(opus_multistream_packet_pad(packet,len,len+1,2)!=OPUS_OK)test_failed();
363 len++;
364 }
365 if((fast_rand()&7)==0)
366 {
367 if(opus_multistream_packet_pad(packet,len,len+256,2)!=OPUS_OK)test_failed();
368 len+=256;
369 }
370 if((fast_rand()&3)==0)
371 {
372 len=opus_multistream_packet_unpad(packet,len,2);
373 if(len<1)test_failed();
374 }
sergeyu@chromium.org885f2ff2012-10-17 22:31:52 +0000375 out_samples = opus_multistream_decode(MSdec, packet, len, out2buf, MAX_FRAME_SAMP, 0);
376 if(out_samples!=frame_size*6)test_failed();
377 if(opus_multistream_decoder_ctl(MSdec, OPUS_GET_FINAL_RANGE(&dec_final_range))!=OPUS_OK)test_failed();
378 if(enc_final_range!=dec_final_range)test_failed();
379 /*LBRR decode*/
380 loss=(fast_rand()&63)==0;
sergeyu@chromium.org6b6bee22013-02-28 21:17:26 +0000381 out_samples = opus_multistream_decode(MSdec_err, packet, loss?0:len, out2buf, frame_size*6, (fast_rand()&3)!=0);
382 if(out_samples!=(frame_size*6))test_failed();
sergeyu@chromium.org885f2ff2012-10-17 22:31:52 +0000383 i+=frame_size;
384 count++;
385 }while(i<(SSAMPLES/12-MAX_FRAME_SAMP));
386 fprintf(stdout," Mode %s NB dual-mono MS encode %s, %6d bps OK.\n",mstrings[modes[j]],rc==0?" VBR":rc==1?"CVBR":" CBR",rate);
387 }
388 }
389
390 bitrate_bps=512000;
391 fsize=fast_rand()%31;
392 fswitch=100;
393
394 debruijn2(6,db62);
395 count=i=0;
396 do {
397 unsigned char toc;
398 const unsigned char *frames[48];
399 short size[48];
400 int payload_offset;
401 opus_uint32 dec_final_range2;
402 int jj,dec2;
403 int len,out_samples;
404 int frame_size=fsizes[db62[fsize]];
405 opus_int32 offset=i%(SAMPLES-MAX_FRAME_SAMP);
406
407 opus_encoder_ctl(enc, OPUS_SET_BITRATE(bitrate_bps));
408
409 len = opus_encode(enc, &inbuf[offset<<1], frame_size, packet, MAX_PACKET);
410 if(len<0 || len>MAX_PACKET)test_failed();
411 count++;
412
413 opus_encoder_ctl(enc, OPUS_GET_FINAL_RANGE(&enc_final_range));
414
415 out_samples = opus_decode(dec, packet, len, &outbuf[offset<<1], MAX_FRAME_SAMP, 0);
416 if(out_samples!=frame_size)test_failed();
417
418 opus_decoder_ctl(dec, OPUS_GET_FINAL_RANGE(&dec_final_range));
419
420 /* compare final range encoder rng values of encoder and decoder */
421 if(dec_final_range!=enc_final_range)test_failed();
422
423 /* We fuzz the packet, but take care not to only corrupt the payload
424 Corrupted headers are tested elsewhere and we need to actually run
425 the decoders in order to compare them. */
426 if(opus_packet_parse(packet,len,&toc,frames,size,&payload_offset)<=0)test_failed();
427 if((fast_rand()&1023)==0)len=0;
428 for(j=(frames[0]-packet);j<len;j++)for(jj=0;jj<8;jj++)packet[j]^=((!no_fuzz)&&((fast_rand()&1023)==0))<<jj;
429 out_samples = opus_decode(dec_err[0], len>0?packet:NULL, len, out2buf, MAX_FRAME_SAMP, 0);
430 if(out_samples<0||out_samples>MAX_FRAME_SAMP)test_failed();
431 if((len>0&&out_samples!=frame_size))test_failed(); /*FIXME use lastframe*/
432
433 opus_decoder_ctl(dec_err[0], OPUS_GET_FINAL_RANGE(&dec_final_range));
434
435 /*randomly select one of the decoders to compare with*/
436 dec2=fast_rand()%9+1;
437 out_samples = opus_decode(dec_err[dec2], len>0?packet:NULL, len, out2buf, MAX_FRAME_SAMP, 0);
438 if(out_samples<0||out_samples>MAX_FRAME_SAMP)test_failed(); /*FIXME, use factor, lastframe for loss*/
439
440 opus_decoder_ctl(dec_err[dec2], OPUS_GET_FINAL_RANGE(&dec_final_range2));
441 if(len>0&&dec_final_range!=dec_final_range2)test_failed();
442
443 fswitch--;
444 if(fswitch<1)
445 {
446 int new_size;
447 fsize=(fsize+1)%36;
448 new_size=fsizes[db62[fsize]];
449 if(new_size==960||new_size==480)fswitch=2880/new_size*(fast_rand()%19+1);
450 else fswitch=(fast_rand()%(2880/new_size))+1;
451 }
452 bitrate_bps=((fast_rand()%508000+4000)+bitrate_bps)>>1;
453 i+=frame_size;
454 }while(i<SAMPLES*4);
455 fprintf(stdout," All framesize pairs switching encode, %d frames OK.\n",count);
456
tlegrand@google.com3c3902f2013-12-09 08:35:25 +0000457 if(opus_encoder_ctl(enc, OPUS_RESET_STATE)!=OPUS_OK)test_failed();
sergeyu@chromium.org885f2ff2012-10-17 22:31:52 +0000458 opus_encoder_destroy(enc);
tlegrand@google.com3c3902f2013-12-09 08:35:25 +0000459 if(opus_multistream_encoder_ctl(MSenc, OPUS_RESET_STATE)!=OPUS_OK)test_failed();
sergeyu@chromium.org885f2ff2012-10-17 22:31:52 +0000460 opus_multistream_encoder_destroy(MSenc);
tlegrand@google.com3c3902f2013-12-09 08:35:25 +0000461 if(opus_decoder_ctl(dec, OPUS_RESET_STATE)!=OPUS_OK)test_failed();
sergeyu@chromium.org885f2ff2012-10-17 22:31:52 +0000462 opus_decoder_destroy(dec);
tlegrand@google.com3c3902f2013-12-09 08:35:25 +0000463 if(opus_multistream_decoder_ctl(MSdec, OPUS_RESET_STATE)!=OPUS_OK)test_failed();
sergeyu@chromium.org885f2ff2012-10-17 22:31:52 +0000464 opus_multistream_decoder_destroy(MSdec);
465 opus_multistream_decoder_destroy(MSdec_err);
466 for(i=0;i<10;i++)opus_decoder_destroy(dec_err[i]);
467 free(inbuf);
468 free(outbuf);
469 free(out2buf);
470 return 0;
471}
472
473int main(int _argc, char **_argv)
474{
475 const char * oversion;
476 const char * env_seed;
477 int env_used;
478
479 if(_argc>2)
480 {
481 fprintf(stderr,"Usage: %s [<seed>]\n",_argv[0]);
482 return 1;
483 }
484
485 env_used=0;
486 env_seed=getenv("SEED");
487 if(_argc>1)iseed=atoi(_argv[1]);
488 else if(env_seed)
489 {
490 iseed=atoi(env_seed);
491 env_used=1;
492 }
493 else iseed=(opus_uint32)time(NULL)^((getpid()&65535)<<16);
494 Rw=Rz=iseed;
495
496 oversion=opus_get_version_string();
497 if(!oversion)test_failed();
498 fprintf(stderr,"Testing %s encoder. Random seed: %u (%.4X)\n", oversion, iseed, fast_rand() % 65535);
499 if(env_used)fprintf(stderr," Random seed set from the environment (SEED=%s).\n", env_seed);
500
501 /*Setting TEST_OPUS_NOFUZZ tells the tool not to send garbage data
502 into the decoders. This is helpful because garbage data
503 may cause the decoders to clip, which angers CLANG IOC.*/
504 run_test1(getenv("TEST_OPUS_NOFUZZ")!=NULL);
505
506 fprintf(stderr,"Tests completed successfully.\n");
507
508 return 0;
509}