ReleaseTest-API.cc revision b7e5054414ff524f9db81dab7917729b8c4c8bcb
1/* 2 * Copyright (c) 2012 The WebRTC project authors. All Rights Reserved. 3 * 4 * Use of this source code is governed by a BSD-style license 5 * that can be found in the LICENSE file in the root of the source 6 * tree. An additional intellectual property rights grant can be found 7 * in the file PATENTS. All contributing project authors may 8 * be found in the AUTHORS file in the root of the source tree. 9 */ 10 11// ReleaseTest-API.cpp : Defines the entry point for the console application. 12// 13 14#include <stdio.h> 15#include <stdlib.h> 16#include <string.h> 17#include <time.h> 18#include <ctype.h> 19#include <iostream> 20 21/* include API */ 22#include "isac.h" 23#include "utility.h" 24 25/* Defines */ 26#define SEED_FILE "randseed.txt" /* Used when running decoder on garbage data */ 27#define MAX_FRAMESAMPLES 960 /* max number of samples per frame 28 (= 60 ms frame & 16 kHz) or 29 (= 30 ms frame & 32 kHz) */ 30#define FRAMESAMPLES_10ms 160 /* number of samples per 10ms frame */ 31#define SWBFRAMESAMPLES_10ms 320 32//#define FS 16000 /* sampling frequency (Hz) */ 33 34#ifdef WIN32 35#define CLOCKS_PER_SEC 1000 /* Runtime statistics */ 36#endif 37 38using namespace std; 39 40int main(int argc, char* argv[]) { 41 char inname[100], outname[100], bottleneck_file[100], vadfile[100]; 42 FILE* inp, *outp, * f_bn = NULL, * vadp = NULL, *bandwidthp; 43 int framecnt, endfile; 44 45 int i, errtype, VADusage = 0, packetLossPercent = 0; 46 int16_t CodingMode; 47 int32_t bottleneck = 0; 48 int16_t framesize = 30; /* ms */ 49 int cur_framesmpls, err; 50 51 /* Runtime statistics */ 52 double starttime, runtime, length_file; 53 54 int16_t stream_len = 0; 55 int16_t declen = 0, declenTC = 0; 56 bool lostFrame = false; 57 58 int16_t shortdata[SWBFRAMESAMPLES_10ms]; 59 int16_t vaddata[SWBFRAMESAMPLES_10ms * 3]; 60 int16_t decoded[MAX_FRAMESAMPLES << 1]; 61 int16_t decodedTC[MAX_FRAMESAMPLES << 1]; 62 uint16_t streamdata[500]; 63 int16_t speechType[1]; 64 int16_t rateBPS = 0; 65 int16_t fixedFL = 0; 66 int16_t payloadSize = 0; 67 int32_t payloadRate = 0; 68 int setControlBWE = 0; 69 short FL, testNum; 70 char version_number[20]; 71 FILE* plFile; 72 int32_t sendBN; 73 74#ifdef _DEBUG 75 FILE* fy; 76 double kbps; 77#endif /* _DEBUG */ 78 int totalbits = 0; 79 int totalsmpls = 0; 80 81 /* If use GNS file */ 82 FILE* fp_gns = NULL; 83 char gns_file[100]; 84 short maxStreamLen30 = 0; 85 short maxStreamLen60 = 0; 86 short sampFreqKHz = 32; 87 short samplesIn10Ms; 88 short useAssign = 0; 89 // FILE logFile; 90 bool doTransCoding = false; 91 int32_t rateTransCoding = 0; 92 uint8_t streamDataTransCoding[1200]; 93 int16_t streamLenTransCoding = 0; 94 FILE* transCodingFile = NULL; 95 FILE* transcodingBitstream = NULL; 96 uint32_t numTransCodingBytes = 0; 97 98 /* only one structure used for ISAC encoder */ 99 ISACStruct* ISAC_main_inst = NULL; 100 ISACStruct* decoderTransCoding = NULL; 101 102 BottleNeckModel BN_data; 103 104#ifdef _DEBUG 105 fy = fopen("bit_rate.dat", "w"); 106 fclose(fy); 107 fy = fopen("bytes_frames.dat", "w"); 108 fclose(fy); 109#endif /* _DEBUG */ 110 111 /* Handling wrong input arguments in the command line */ 112 if ((argc < 3) || (argc > 17)) { 113 printf("\n\nWrong number of arguments or flag values.\n\n"); 114 115 printf("\n"); 116 WebRtcIsac_version(version_number); 117 printf("iSAC-swb version %s \n\n", version_number); 118 119 printf("Usage:\n\n"); 120 printf("./kenny.exe [-I] bottleneck_value infile outfile \n\n"); 121 printf("with:\n"); 122 printf("[-FS num] : sampling frequency in kHz, valid values are\n"); 123 printf(" 16 & 32, with 16 as default.\n"); 124 printf("[-I] : if -I option is specified, the coder will use\n"); 125 printf(" an instantaneous Bottleneck value. If not, it\n"); 126 printf(" will be an adaptive Bottleneck value.\n"); 127 printf("[-assign] : Use Assign API.\n"); 128 printf("[-B num] : the value of the bottleneck provided either\n"); 129 printf(" as a fixed value in bits/sec (e.g. 25000) or\n"); 130 printf(" read from a file (e.g. bottleneck.txt)\n"); 131 printf("[-INITRATE num] : Set a new value for initial rate. Note! Only\n"); 132 printf(" used in adaptive mode.\n"); 133 printf("[-FL num] : Set (initial) frame length in msec. Valid\n"); 134 printf(" lengths are 30 and 60 msec.\n"); 135 printf("[-FIXED_FL] : Frame length will be fixed to initial value.\n"); 136 printf("[-MAX num] : Set the limit for the payload size of iSAC\n"); 137 printf(" in bytes. Minimum 100 maximum 400.\n"); 138 printf("[-MAXRATE num] : Set the maxrate for iSAC in bits per second.\n"); 139 printf(" Minimum 32000, maximum 53400.\n"); 140 printf("[-F num] : if -F option is specified, the test function\n"); 141 printf(" will run the iSAC API fault scenario\n"); 142 printf(" specified by the supplied number.\n"); 143 printf(" F 1 - Call encoder prior to init encoder call\n"); 144 printf(" F 2 - Call decoder prior to init decoder call\n"); 145 printf(" F 3 - Call decoder prior to encoder call\n"); 146 printf(" F 4 - Call decoder with a too short coded\n"); 147 printf(" sequence\n"); 148 printf(" F 5 - Call decoder with a too long coded\n"); 149 printf(" sequence\n"); 150 printf(" F 6 - Call decoder with random bit stream\n"); 151 printf(" F 7 - Call init encoder/decoder at random\n"); 152 printf(" during a call\n"); 153 printf(" F 8 - Call encoder/decoder without having\n"); 154 printf(" allocated memory for encoder/decoder\n"); 155 printf(" instance\n"); 156 printf(" F 9 - Call decodeB without calling decodeA\n"); 157 printf(" F 10 - Call decodeB with garbage data\n"); 158 printf("[-PL num] : if -PL option is specified \n"); 159 printf("[-T rate file] : test trans-coding with target bottleneck\n"); 160 printf(" 'rate' bits/sec\n"); 161 printf(" the output file is written to 'file'\n"); 162 printf("[-LOOP num] : number of times to repeat coding the input\n"); 163 printf(" file for stress testing\n"); 164 // printf("[-CE num] : Test of APIs used by Conference Engine.\n"); 165 // printf(" CE 1 - getNewBitstream, getBWE \n"); 166 // printf(" (CE 2 - RESERVED for transcoding)\n"); 167 // printf(" CE 3 - getSendBWE, setSendBWE. \n"); 168 // printf("-L filename : write the logging info into file 169 // (appending)\n"); 170 printf("infile : Normal speech input file\n"); 171 printf("outfile : Speech output file\n"); 172 exit(0); 173 } 174 175 /* Print version number */ 176 printf("-------------------------------------------------\n"); 177 WebRtcIsac_version(version_number); 178 printf("iSAC version %s \n\n", version_number); 179 180 /* Loop over all command line arguments */ 181 CodingMode = 0; 182 testNum = 0; 183 useAssign = 0; 184 // logFile = NULL; 185 char transCodingFileName[500]; 186 int16_t totFileLoop = 0; 187 int16_t numFileLoop = 0; 188 for (i = 1; i + 2 < argc; i++) { 189 if (!strcmp("-LOOP", argv[i])) { 190 i++; 191 totFileLoop = (int16_t)atol(argv[i]); 192 if (totFileLoop <= 0) { 193 fprintf(stderr, "Invalid number of runs for the given input file, %d.", 194 totFileLoop); 195 exit(0); 196 } 197 } 198 199 if (!strcmp("-T", argv[i])) { 200 doTransCoding = true; 201 i++; 202 rateTransCoding = atoi(argv[i]); 203 i++; 204 strcpy(transCodingFileName, argv[i]); 205 } 206 207 /*Should we use assign API*/ 208 if (!strcmp("-assign", argv[i])) { 209 useAssign = 1; 210 } 211 212 /* Set Sampling Rate */ 213 if (!strcmp("-FS", argv[i])) { 214 i++; 215 sampFreqKHz = atoi(argv[i]); 216 } 217 218 /* Instantaneous mode */ 219 if (!strcmp("-I", argv[i])) { 220 printf("Instantaneous BottleNeck\n"); 221 CodingMode = 1; 222 } 223 224 /* Set (initial) bottleneck value */ 225 if (!strcmp("-INITRATE", argv[i])) { 226 rateBPS = atoi(argv[i + 1]); 227 setControlBWE = 1; 228 if ((rateBPS < 10000) || (rateBPS > 32000)) { 229 printf("\n%d is not a initial rate. Valid values are in the range " 230 "10000 to 32000.\n", rateBPS); 231 exit(0); 232 } 233 printf("New initial rate: %d\n", rateBPS); 234 i++; 235 } 236 237 /* Set (initial) framelength */ 238 if (!strcmp("-FL", argv[i])) { 239 framesize = atoi(argv[i + 1]); 240 if ((framesize != 30) && (framesize != 60)) { 241 printf("\n%d is not a valid frame length. Valid length are 30 and 60 " 242 "msec.\n", framesize); 243 exit(0); 244 } 245 setControlBWE = 1; 246 printf("Frame Length: %d\n", framesize); 247 i++; 248 } 249 250 /* Fixed frame length */ 251 if (!strcmp("-FIXED_FL", argv[i])) { 252 fixedFL = 1; 253 setControlBWE = 1; 254 printf("Fixed Frame Length\n"); 255 } 256 257 /* Set maximum allowed payload size in bytes */ 258 if (!strcmp("-MAX", argv[i])) { 259 payloadSize = atoi(argv[i + 1]); 260 printf("Maximum Payload Size: %d\n", payloadSize); 261 i++; 262 } 263 264 /* Set maximum rate in bytes */ 265 if (!strcmp("-MAXRATE", argv[i])) { 266 payloadRate = atoi(argv[i + 1]); 267 printf("Maximum Rate in kbps: %d\n", payloadRate); 268 i++; 269 } 270 271 /* Test of fault scenarious */ 272 if (!strcmp("-F", argv[i])) { 273 testNum = atoi(argv[i + 1]); 274 printf("Fault test: %d\n", testNum); 275 if (testNum < 1 || testNum > 10) { 276 printf("\n%d is not a valid Fault Scenario number. Valid Fault " 277 "Scenarios are numbered 1-10.\n", testNum); 278 exit(0); 279 } 280 i++; 281 } 282 283 /* Packet loss test */ 284 if (!strcmp("-PL", argv[i])) { 285 if (isdigit(*argv[i + 1])) { 286 packetLossPercent = atoi(argv[i + 1]); 287 if ((packetLossPercent < 0) | (packetLossPercent > 100)) { 288 printf("\nInvalid packet loss perentage \n"); 289 exit(0); 290 } 291 if (packetLossPercent > 0) { 292 printf("Simulating %d %% of independent packet loss\n", 293 packetLossPercent); 294 } else { 295 printf("\nNo Packet Loss Is Simulated \n"); 296 } 297 } else { 298 plFile = fopen(argv[i + 1], "rb"); 299 if (plFile == NULL) { 300 printf("\n couldn't open the frameloss file: %s\n", argv[i + 1]); 301 exit(0); 302 } 303 printf("Simulating packet loss through the given channel file: %s\n", 304 argv[i + 1]); 305 } 306 i++; 307 } 308 309 /* Random packetlosses */ 310 if (!strcmp("-rnd", argv[i])) { 311 srand((unsigned int)time(NULL)); 312 printf("Random pattern in lossed packets \n"); 313 } 314 315 /* Use gns file */ 316 if (!strcmp("-G", argv[i])) { 317 sscanf(argv[i + 1], "%s", gns_file); 318 fp_gns = fopen(gns_file, "rb"); 319 if (fp_gns == NULL) { 320 printf("Cannot read file %s.\n", gns_file); 321 exit(0); 322 } 323 i++; 324 } 325 326 // make it with '-B' 327 /* Get Bottleneck value */ 328 if (!strcmp("-B", argv[i])) { 329 i++; 330 bottleneck = atoi(argv[i]); 331 if (bottleneck == 0) { 332 sscanf(argv[i], "%s", bottleneck_file); 333 f_bn = fopen(bottleneck_file, "rb"); 334 if (f_bn == NULL) { 335 printf("Error No value provided for BottleNeck and cannot read file " 336 "%s.\n", bottleneck_file); 337 exit(0); 338 } else { 339 printf("reading bottleneck rates from file %s\n\n", bottleneck_file); 340 if (fscanf(f_bn, "%d", &bottleneck) == EOF) { 341 /* Set pointer to beginning of file */ 342 fseek(f_bn, 0L, SEEK_SET); 343 if (fscanf(f_bn, "%d", &bottleneck) == EOF) { 344 exit(0); 345 } 346 } 347 348 /* Bottleneck is a cosine function 349 * Matlab code for writing the bottleneck file: 350 * BottleNeck_10ms = 20e3 + 10e3 * cos((0:5999)/5999*2*pi); 351 * fid = fopen('bottleneck.txt', 'wb'); 352 * fprintf(fid, '%d\n', BottleNeck_10ms); fclose(fid); 353 */ 354 } 355 } else { 356 printf("\nfixed bottleneck rate of %d bits/s\n\n", bottleneck); 357 } 358 } 359 /* Run Conference Engine APIs */ 360 // Do not test it in the first release 361 // 362 // if(!strcmp ("-CE", argv[i])) 363 // { 364 // testCE = atoi(argv[i + 1]); 365 // if(testCE==1) 366 // { 367 // i++; 368 // scale = (float)atof( argv[i+1] ); 369 // } 370 // else if(testCE == 2) 371 // { 372 // printf("\nCE-test 2 (transcoding) not implemented.\n"); 373 // exit(0); 374 // } 375 // else if(testCE < 1 || testCE > 3) 376 // { 377 // printf("\n%d is not a valid CE-test number. Valid CE tests 378 // are 1-3.\n", testCE); 379 // exit(0); 380 // } 381 // printf("CE-test number: %d\n", testCE); 382 // i++; 383 // } 384 } 385 386 if (CodingMode == 0) { 387 printf("\nAdaptive BottleNeck\n"); 388 } 389 390 switch (sampFreqKHz) { 391 case 16: { 392 printf("iSAC Wideband.\n"); 393 samplesIn10Ms = FRAMESAMPLES_10ms; 394 break; 395 } 396 case 32: { 397 printf("iSAC Supper-Wideband.\n"); 398 samplesIn10Ms = SWBFRAMESAMPLES_10ms; 399 break; 400 } 401 default: 402 printf("Unsupported sampling frequency %d kHz", sampFreqKHz); 403 exit(0); 404 } 405 406 /* Get Input and Output files */ 407 sscanf(argv[argc - 2], "%s", inname); 408 sscanf(argv[argc - 1], "%s", outname); 409 printf("\nInput file: %s\n", inname); 410 printf("Output file: %s\n\n", outname); 411 if ((inp = fopen(inname, "rb")) == NULL) { 412 printf(" Error iSAC Cannot read file %s.\n", inname); 413 cout << flush; 414 exit(1); 415 } 416 417 if ((outp = fopen(outname, "wb")) == NULL) { 418 printf(" Error iSAC Cannot write file %s.\n", outname); 419 cout << flush; 420 getc(stdin); 421 exit(1); 422 } 423 if (VADusage) { 424 if ((vadp = fopen(vadfile, "rb")) == NULL) { 425 printf(" Error iSAC Cannot read file %s.\n", vadfile); 426 cout << flush; 427 exit(1); 428 } 429 } 430 431 if ((bandwidthp = fopen("bwe.pcm", "wb")) == NULL) { 432 printf(" Error iSAC Cannot read file %s.\n", "bwe.pcm"); 433 cout << flush; 434 exit(1); 435 } 436 437 starttime = clock() / (double)CLOCKS_PER_SEC; /* Runtime statistics */ 438 439 /* Initialize the ISAC and BN structs */ 440 if (testNum != 8) { 441 if (!useAssign) { 442 err = WebRtcIsac_Create(&ISAC_main_inst); 443 WebRtcIsac_SetEncSampRate(ISAC_main_inst, sampFreqKHz * 1000); 444 WebRtcIsac_SetDecSampRate(ISAC_main_inst, 445 sampFreqKHz >= 32 ? 32000 : 16000); 446 } else { 447 /* Test the Assign functions */ 448 int sss; 449 void* ppp; 450 err = WebRtcIsac_AssignSize(&sss); 451 ppp = malloc(sss); 452 err = WebRtcIsac_Assign(&ISAC_main_inst, ppp); 453 WebRtcIsac_SetEncSampRate(ISAC_main_inst, sampFreqKHz * 1000); 454 WebRtcIsac_SetDecSampRate(ISAC_main_inst, 455 sampFreqKHz >= 32 ? 32000 : 16000); 456 } 457 /* Error check */ 458 if (err < 0) { 459 printf("\n\n Error in create.\n\n"); 460 cout << flush; 461 exit(EXIT_FAILURE); 462 } 463 } 464 BN_data.arrival_time = 0; 465 BN_data.sample_count = 0; 466 BN_data.rtp_number = 0; 467 468 /* Initialize encoder and decoder */ 469 framecnt = 0; 470 endfile = 0; 471 472 if (doTransCoding) { 473 WebRtcIsac_Create(&decoderTransCoding); 474 WebRtcIsac_SetEncSampRate(decoderTransCoding, sampFreqKHz * 1000); 475 WebRtcIsac_SetDecSampRate(decoderTransCoding, 476 sampFreqKHz >= 32 ? 32000 : 16000); 477 WebRtcIsac_DecoderInit(decoderTransCoding); 478 transCodingFile = fopen(transCodingFileName, "wb"); 479 if (transCodingFile == NULL) { 480 printf("Could not open %s to output trans-coding.\n", 481 transCodingFileName); 482 exit(0); 483 } 484 strcat(transCodingFileName, ".bit"); 485 transcodingBitstream = fopen(transCodingFileName, "wb"); 486 if (transcodingBitstream == NULL) { 487 printf("Could not open %s to write the bit-stream of transcoder.\n", 488 transCodingFileName); 489 exit(0); 490 } 491 } 492 493 if (testNum != 1) { 494 if (WebRtcIsac_EncoderInit(ISAC_main_inst, CodingMode) < 0) { 495 printf("Error could not initialize the encoder \n"); 496 cout << flush; 497 return 0; 498 } 499 } 500 if (testNum != 2) { 501 if (WebRtcIsac_DecoderInit(ISAC_main_inst) < 0) { 502 printf("Error could not initialize the decoder \n"); 503 cout << flush; 504 return 0; 505 } 506 } 507 if (CodingMode == 1) { 508 err = WebRtcIsac_Control(ISAC_main_inst, bottleneck, framesize); 509 if (err < 0) { 510 /* exit if returned with error */ 511 errtype = WebRtcIsac_GetErrorCode(ISAC_main_inst); 512 printf("\n\n Error in initialization (control): %d.\n\n", errtype); 513 cout << flush; 514 if (testNum == 0) { 515 exit(EXIT_FAILURE); 516 } 517 } 518 } 519 520 if ((setControlBWE) && (CodingMode == 0)) { 521 err = WebRtcIsac_ControlBwe(ISAC_main_inst, rateBPS, framesize, fixedFL); 522 if (err < 0) { 523 /* exit if returned with error */ 524 errtype = WebRtcIsac_GetErrorCode(ISAC_main_inst); 525 526 printf("\n\n Error in Control BWE: %d.\n\n", errtype); 527 cout << flush; 528 exit(EXIT_FAILURE); 529 } 530 } 531 532 if (payloadSize != 0) { 533 err = WebRtcIsac_SetMaxPayloadSize(ISAC_main_inst, payloadSize); 534 if (err < 0) { 535 /* exit if returned with error */ 536 errtype = WebRtcIsac_GetErrorCode(ISAC_main_inst); 537 printf("\n\n Error in SetMaxPayloadSize: %d.\n\n", errtype); 538 cout << flush; 539 exit(EXIT_FAILURE); 540 } 541 } 542 if (payloadRate != 0) { 543 err = WebRtcIsac_SetMaxRate(ISAC_main_inst, payloadRate); 544 if (err < 0) { 545 /* exit if returned with error */ 546 errtype = WebRtcIsac_GetErrorCode(ISAC_main_inst); 547 printf("\n\n Error in SetMaxRateInBytes: %d.\n\n", errtype); 548 cout << flush; 549 exit(EXIT_FAILURE); 550 } 551 } 552 553 *speechType = 1; 554 555 cout << "\n" << flush; 556 557 length_file = 0; 558 int16_t bnIdxTC = 0; 559 int16_t jitterInfoTC = 0; 560 while (endfile == 0) { 561 /* Call init functions at random, fault test number 7 */ 562 if (testNum == 7 && (rand() % 2 == 0)) { 563 err = WebRtcIsac_EncoderInit(ISAC_main_inst, CodingMode); 564 /* Error check */ 565 if (err < 0) { 566 errtype = WebRtcIsac_GetErrorCode(ISAC_main_inst); 567 printf("\n\n Error in encoderinit: %d.\n\n", errtype); 568 cout << flush; 569 } 570 571 err = WebRtcIsac_DecoderInit(ISAC_main_inst); 572 /* Error check */ 573 if (err < 0) { 574 errtype = WebRtcIsac_GetErrorCode(ISAC_main_inst); 575 printf("\n\n Error in decoderinit: %d.\n\n", errtype); 576 cout << flush; 577 } 578 } 579 580 cur_framesmpls = 0; 581 while (1) { 582 /* Read 10 ms speech block */ 583 endfile = readframe(shortdata, inp, samplesIn10Ms); 584 585 if (endfile) { 586 numFileLoop++; 587 if (numFileLoop < totFileLoop) { 588 rewind(inp); 589 framecnt = 0; 590 fprintf(stderr, "\n"); 591 endfile = readframe(shortdata, inp, samplesIn10Ms); 592 } 593 } 594 595 if (testNum == 7) { 596 srand((unsigned int)time(NULL)); 597 } 598 599 /* iSAC encoding */ 600 if (!(testNum == 3 && framecnt == 0)) { 601 stream_len = 602 WebRtcIsac_Encode(ISAC_main_inst, shortdata, (uint8_t*)streamdata); 603 if ((payloadSize != 0) && (stream_len > payloadSize)) { 604 if (testNum == 0) { 605 printf("\n\n"); 606 } 607 608 printf("\nError: Streamsize out of range %d\n", 609 stream_len - payloadSize); 610 cout << flush; 611 } 612 613 WebRtcIsac_GetUplinkBw(ISAC_main_inst, &sendBN); 614 615 if (stream_len > 0) { 616 if (doTransCoding) { 617 int16_t indexStream; 618 uint8_t auxUW8; 619 620 /******************** Main Transcoding stream ********************/ 621 WebRtcIsac_GetDownLinkBwIndex(ISAC_main_inst, &bnIdxTC, 622 &jitterInfoTC); 623 streamLenTransCoding = WebRtcIsac_GetNewBitStream( 624 ISAC_main_inst, bnIdxTC, jitterInfoTC, rateTransCoding, 625 streamDataTransCoding, false); 626 if (streamLenTransCoding < 0) { 627 fprintf(stderr, "Error in trans-coding\n"); 628 exit(0); 629 } 630 auxUW8 = (uint8_t)(((streamLenTransCoding & 0xFF00) >> 8) & 0x00FF); 631 if (fwrite(&auxUW8, sizeof(uint8_t), 1, transcodingBitstream) != 632 1) { 633 return -1; 634 } 635 636 auxUW8 = (uint8_t)(streamLenTransCoding & 0x00FF); 637 if (fwrite(&auxUW8, sizeof(uint8_t), 1, transcodingBitstream) != 638 1) { 639 return -1; 640 } 641 642 if (fwrite(streamDataTransCoding, sizeof(uint8_t), 643 streamLenTransCoding, transcodingBitstream) != 644 static_cast<size_t>(streamLenTransCoding)) { 645 return -1; 646 } 647 648 WebRtcIsac_ReadBwIndex(streamDataTransCoding, &indexStream); 649 if (indexStream != bnIdxTC) { 650 fprintf(stderr, 651 "Error in inserting Bandwidth index into transcoding " 652 "stream.\n"); 653 exit(0); 654 } 655 numTransCodingBytes += streamLenTransCoding; 656 } 657 } 658 } else { 659 break; 660 } 661 662 if (stream_len < 0) { 663 /* exit if returned with error */ 664 errtype = WebRtcIsac_GetErrorCode(ISAC_main_inst); 665 printf("\n\nError in encoder: %d.\n\n", errtype); 666 cout << flush; 667 } 668 cur_framesmpls += samplesIn10Ms; 669 /* exit encoder loop if the encoder returned a bitstream */ 670 if (stream_len != 0) 671 break; 672 } 673 674 /* read next bottleneck rate */ 675 if (f_bn != NULL) { 676 if (fscanf(f_bn, "%d", &bottleneck) == EOF) { 677 /* Set pointer to beginning of file */ 678 fseek(f_bn, 0L, SEEK_SET); 679 if (fscanf(f_bn, "%d", &bottleneck) == EOF) { 680 exit(0); 681 } 682 } 683 if (CodingMode == 1) { 684 WebRtcIsac_Control(ISAC_main_inst, bottleneck, framesize); 685 } 686 } 687 688 length_file += cur_framesmpls; 689 if (cur_framesmpls == (3 * samplesIn10Ms)) { 690 maxStreamLen30 = 691 (stream_len > maxStreamLen30) ? stream_len : maxStreamLen30; 692 } else { 693 maxStreamLen60 = 694 (stream_len > maxStreamLen60) ? stream_len : maxStreamLen60; 695 } 696 697 if (!lostFrame) { 698 lostFrame = ((rand() % 100) < packetLossPercent); 699 } else { 700 lostFrame = false; 701 } 702 703 // RED. 704 if (lostFrame) { 705 stream_len = WebRtcIsac_GetRedPayload( 706 ISAC_main_inst, reinterpret_cast<uint8_t*>(streamdata)); 707 708 if (doTransCoding) { 709 streamLenTransCoding = WebRtcIsac_GetNewBitStream( 710 ISAC_main_inst, bnIdxTC, jitterInfoTC, rateTransCoding, 711 streamDataTransCoding, true); 712 if (streamLenTransCoding < 0) { 713 fprintf(stderr, "Error in RED trans-coding\n"); 714 exit(0); 715 } 716 } 717 } 718 719 /* make coded sequence to short be inreasing */ 720 /* the length the decoder expects */ 721 if (testNum == 4) { 722 stream_len += 10; 723 } 724 725 /* make coded sequence to long be decreasing */ 726 /* the length the decoder expects */ 727 if (testNum == 5) { 728 stream_len -= 10; 729 } 730 731 if (testNum == 6) { 732 srand((unsigned int)time(NULL)); 733 for (i = 0; i < stream_len; i++) { 734 streamdata[i] = rand(); 735 } 736 } 737 738 if (VADusage) { 739 readframe(vaddata, vadp, samplesIn10Ms * 3); 740 } 741 742 /* simulate packet handling through NetEq and the modem */ 743 if (!(testNum == 3 && framecnt == 0)) { 744 get_arrival_time(cur_framesmpls, stream_len, bottleneck, &BN_data, 745 sampFreqKHz * 1000, sampFreqKHz * 1000); 746 } 747 748 if (VADusage && (framecnt > 10 && vaddata[0] == 0)) { 749 BN_data.rtp_number--; 750 } else { 751 /* Error test number 10, garbage data */ 752 if (testNum == 10) { 753 /* Test to run decoder with garbage data */ 754 for (i = 0; i < stream_len; i++) { 755 streamdata[i] = (short)(streamdata[i]) + (short)rand(); 756 } 757 } 758 759 if (testNum != 9) { 760 err = WebRtcIsac_UpdateBwEstimate( 761 ISAC_main_inst, reinterpret_cast<const uint8_t*>(streamdata), 762 stream_len, BN_data.rtp_number, BN_data.sample_count, 763 BN_data.arrival_time); 764 765 if (err < 0) { 766 /* exit if returned with error */ 767 errtype = WebRtcIsac_GetErrorCode(ISAC_main_inst); 768 if (testNum == 0) { 769 printf("\n\n"); 770 } 771 772 printf("Error: in decoder: %d.", errtype); 773 cout << flush; 774 if (testNum == 0) { 775 printf("\n\n"); 776 } 777 } 778 } 779 780 /* Call getFramelen, only used here for function test */ 781 err = WebRtcIsac_ReadFrameLen( 782 ISAC_main_inst, reinterpret_cast<const uint8_t*>(streamdata), &FL); 783 if (err < 0) { 784 /* exit if returned with error */ 785 errtype = WebRtcIsac_GetErrorCode(ISAC_main_inst); 786 if (testNum == 0) { 787 printf("\n\n"); 788 } 789 printf(" Error: in getFrameLen %d.", errtype); 790 cout << flush; 791 if (testNum == 0) { 792 printf("\n\n"); 793 } 794 } 795 796 // iSAC decoding 797 798 if (lostFrame) { 799 declen = WebRtcIsac_DecodeRcu( 800 ISAC_main_inst, reinterpret_cast<const uint8_t*>(streamdata), 801 stream_len, decoded, speechType); 802 803 if (doTransCoding) { 804 declenTC = 805 WebRtcIsac_DecodeRcu(decoderTransCoding, streamDataTransCoding, 806 streamLenTransCoding, decodedTC, speechType); 807 } 808 } else { 809 declen = WebRtcIsac_Decode(ISAC_main_inst, 810 reinterpret_cast<const uint8_t*>(streamdata), 811 stream_len, decoded, speechType); 812 if (doTransCoding) { 813 declenTC = 814 WebRtcIsac_Decode(decoderTransCoding, streamDataTransCoding, 815 streamLenTransCoding, decodedTC, speechType); 816 } 817 } 818 819 if (declen < 0) { 820 /* exit if returned with error */ 821 errtype = WebRtcIsac_GetErrorCode(ISAC_main_inst); 822 if (testNum == 0) { 823 printf("\n\n"); 824 } 825 printf(" Error: in decoder %d.", errtype); 826 cout << flush; 827 if (testNum == 0) { 828 printf("\n\n"); 829 } 830 } 831 832 if (declenTC < 0) { 833 if (testNum == 0) { 834 printf("\n\n"); 835 } 836 printf(" Error: in decoding the transcoded stream"); 837 cout << flush; 838 if (testNum == 0) { 839 printf("\n\n"); 840 } 841 } 842 } 843 /* Write decoded speech frame to file */ 844 if ((declen > 0) && (numFileLoop == 0)) { 845 if (fwrite(decoded, sizeof(int16_t), declen, outp) != 846 static_cast<size_t>(declen)) { 847 return -1; 848 } 849 } 850 851 if ((declenTC > 0) && (numFileLoop == 0)) { 852 if (fwrite(decodedTC, sizeof(int16_t), declen, transCodingFile) != 853 static_cast<size_t>(declen)) { 854 return -1; 855 } 856 } 857 858 fprintf(stderr, "\rframe = %5d ", framecnt); 859 fflush(stderr); 860 framecnt++; 861 862 /* Error test number 10, garbage data */ 863 // if (testNum == 10) 864 // { 865 // /* Test to run decoder with garbage data */ 866 // if ((seedfile = fopen(SEED_FILE, "a+t")) == NULL) { 867 // fprintf(stderr, "Error: Could not open file %s\n", SEED_FILE); 868 // } else { 869 // fprintf(seedfile, "ok\n\n"); 870 // fclose(seedfile); 871 // } 872 // } 873 /* Error test number 10, garbage data */ 874 // if (testNum == 10) { 875 // /* Test to run decoder with garbage data */ 876 // for (i = 0; i < stream_len; i++) { 877 // streamdata[i] = (short) (streamdata[i] + (short) rand()); 878 // } 879 // } 880 881 totalsmpls += declen; 882 totalbits += 8 * stream_len; 883#ifdef _DEBUG 884 kbps = ((double)sampFreqKHz * 1000.) / ((double)cur_framesmpls) * 8.0 * 885 stream_len / 1000.0; // kbits/s 886 fy = fopen("bit_rate.dat", "a"); 887 fprintf(fy, "Frame %i = %0.14f\n", framecnt, kbps); 888 fclose(fy); 889 890#endif /* _DEBUG */ 891 } 892 printf("\n"); 893 printf("total bits = %d bits\n", totalbits); 894 printf("measured average bitrate = %0.3f kbits/s\n", 895 (double)totalbits * (sampFreqKHz) / totalsmpls); 896 if (doTransCoding) { 897 printf("Transcoding average bit-rate = %0.3f kbps\n", 898 (double)numTransCodingBytes * 8.0 * (sampFreqKHz) / totalsmpls); 899 fclose(transCodingFile); 900 } 901 printf("\n"); 902 903 /* Runtime statistics */ 904 runtime = (double)(clock() / (double)CLOCKS_PER_SEC - starttime); 905 length_file = length_file / (sampFreqKHz * 1000.); 906 907 printf("\n\nLength of speech file: %.1f s\n", length_file); 908 printf("Time to run iSAC: %.2f s (%.2f %% of realtime)\n\n", runtime, 909 (100 * runtime / length_file)); 910 911 if (maxStreamLen30 != 0) { 912 printf("Maximum payload size 30ms Frames %d bytes (%0.3f kbps)\n", 913 maxStreamLen30, maxStreamLen30 * 8 / 30.); 914 } 915 if (maxStreamLen60 != 0) { 916 printf("Maximum payload size 60ms Frames %d bytes (%0.3f kbps)\n", 917 maxStreamLen60, maxStreamLen60 * 8 / 60.); 918 } 919 // fprintf(stderr, "\n"); 920 921 fprintf(stderr, " %.1f s", length_file); 922 fprintf(stderr, " %0.1f kbps", 923 (double)totalbits * (sampFreqKHz) / totalsmpls); 924 if (maxStreamLen30 != 0) { 925 fprintf(stderr, " plmax-30ms %d bytes (%0.0f kbps)", maxStreamLen30, 926 maxStreamLen30 * 8 / 30.); 927 } 928 if (maxStreamLen60 != 0) { 929 fprintf(stderr, " plmax-60ms %d bytes (%0.0f kbps)", maxStreamLen60, 930 maxStreamLen60 * 8 / 60.); 931 } 932 if (doTransCoding) { 933 fprintf(stderr, " transcoding rate %.0f kbps", 934 (double)numTransCodingBytes * 8.0 * (sampFreqKHz) / totalsmpls); 935 } 936 937 fclose(inp); 938 fclose(outp); 939 WebRtcIsac_Free(ISAC_main_inst); 940 941 exit(0); 942} 943