1 2/*-------------------------------------------------------------------------- 3Copyright (c) 2010-2014, The Linux Foundation. All rights reserved. 4 5Redistribution and use in source and binary forms, with or without 6modification, are permitted provided that the following conditions are met: 7 * Redistributions of source code must retain the above copyright 8 notice, this list of conditions and the following disclaimer. 9 * Redistributions in binary form must reproduce the above copyright 10 notice, this list of conditions and the following disclaimer in the 11 documentation and/or other materials provided with the distribution. 12 * Neither the name of The Linux Foundation nor 13 the names of its contributors may be used to endorse or promote 14 products derived from this software without specific prior written 15 permission. 16 17THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 18AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 19IMPLIED WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 20NON-INFRINGEMENT ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR 21CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, 22EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 23PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; 24OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, 25WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR 26OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF 27ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 28--------------------------------------------------------------------------*/ 29 30 31/* 32 An Open max test application .... 33*/ 34 35#include <stdio.h> 36#include <string.h> 37#include <stdlib.h> 38#include <unistd.h> 39#include <fcntl.h> 40#include <sys/types.h> 41#include <sys/mman.h> 42#include <time.h> 43#include <sys/ioctl.h> 44#include "OMX_Core.h" 45#include "OMX_Component.h" 46#include "pthread.h" 47#include <signal.h> 48 49#include <stdio.h> 50#include <stdlib.h> 51#include <fcntl.h> 52#include <stdint.h> 53#include <sys/mman.h> 54#include <sys/ioctl.h> 55#include<unistd.h> 56#include<string.h> 57#include <pthread.h> 58#include "QOMX_AudioExtensions.h" 59#include "QOMX_AudioIndexExtensions.h" 60#ifdef AUDIOV2 61#include "control.h" 62#endif 63 64 65#include <linux/ioctl.h> 66 67typedef unsigned char uint8; 68typedef unsigned char byte; 69typedef unsigned int uint32; 70typedef unsigned int uint16; 71QOMX_AUDIO_STREAM_INFO_DATA streaminfoparam; 72/* maximum ADTS frame header length */ 73void Release_Encoder(); 74 75#ifdef AUDIOV2 76unsigned short session_id; 77int device_id; 78int control = 0; 79const char *device="handset_tx"; 80#define DIR_TX 2 81#endif 82 83uint32_t samplerate = 8000; 84uint32_t channels = 1; 85uint32_t bandmode = 7; 86uint32_t dtxenable = 0; 87uint32_t rectime = 0; 88uint32_t recpath = 0; 89uint32_t pcmplayback = 0; 90uint32_t tunnel = 0; 91uint32_t format = 1; 92#define DEBUG_PRINT printf 93unsigned to_idle_transition = 0; 94unsigned long total_pcm_bytes; 95 96/************************************************************************/ 97/* GLOBAL INIT */ 98/************************************************************************/ 99 100/************************************************************************/ 101/* #DEFINES */ 102/************************************************************************/ 103#define false 0 104#define true 1 105 106#define CONFIG_VERSION_SIZE(param) \ 107 param.nVersion.nVersion = CURRENT_OMX_SPEC_VERSION;\ 108 param.nSize = sizeof(param); 109 110#define MIN_BITRATE 4 /* Bit rate 1 - 13.6 , 2 - 6.2 , 3 - 2.7 , 4 - 1.0 kbps*/ 111#define MAX_BITRATE 4 112#define AMR_HEADER_SIZE 6 113#define FAILED(result) (result != OMX_ErrorNone) 114 115#define SUCCEEDED(result) (result == OMX_ErrorNone) 116 117/************************************************************************/ 118/* GLOBAL DECLARATIONS */ 119/************************************************************************/ 120 121pthread_mutex_t lock; 122pthread_cond_t cond; 123pthread_mutex_t elock; 124pthread_cond_t econd; 125pthread_cond_t fcond; 126pthread_mutex_t etb_lock; 127pthread_mutex_t etb_lock1; 128pthread_cond_t etb_cond; 129FILE * inputBufferFile; 130FILE * outputBufferFile; 131OMX_PARAM_PORTDEFINITIONTYPE inputportFmt; 132OMX_PARAM_PORTDEFINITIONTYPE outputportFmt; 133OMX_AUDIO_PARAM_AMRTYPE amrparam; 134OMX_AUDIO_PARAM_PCMMODETYPE pcmparam; 135OMX_PORT_PARAM_TYPE portParam; 136OMX_PORT_PARAM_TYPE portFmt; 137OMX_ERRORTYPE error; 138 139 140 141 142#define ID_RIFF 0x46464952 143#define ID_WAVE 0x45564157 144#define ID_FMT 0x20746d66 145#define ID_DATA 0x61746164 146 147#define FORMAT_PCM 1 148 149struct wav_header { 150 uint32_t riff_id; 151 uint32_t riff_sz; 152 uint32_t riff_fmt; 153 uint32_t fmt_id; 154 uint32_t fmt_sz; 155 uint16_t audio_format; 156 uint16_t num_channels; 157 uint32_t sample_rate; 158 uint32_t byte_rate; /* sample_rate * num_channels * bps / 8 */ 159 uint16_t block_align; /* num_channels * bps / 8 */ 160 uint16_t bits_per_sample; 161 uint32_t data_id; 162 uint32_t data_sz; 163}; 164struct enc_meta_out{ 165 unsigned int offset_to_frame; 166 unsigned int frame_size; 167 unsigned int encoded_pcm_samples; 168 unsigned int msw_ts; 169 unsigned int lsw_ts; 170 unsigned int nflags; 171} __attribute__ ((packed)); 172 173struct qcp_header { 174 /* RIFF Section */ 175 char riff[4]; 176 unsigned int s_riff; 177 char qlcm[4]; 178 179 /* Format chunk */ 180 char fmt[4]; 181 unsigned int s_fmt; 182 char mjr; 183 char mnr; 184 unsigned int data1; /* UNIQUE ID of the codec */ 185 unsigned short data2; 186 unsigned short data3; 187 char data4[8]; 188 unsigned short ver; /* Codec Info */ 189 char name[80]; 190 unsigned short abps; /* average bits per sec of the codec */ 191 unsigned short bytes_per_pkt; 192 unsigned short samp_per_block; 193 unsigned short samp_per_sec; 194 unsigned short bits_per_samp; 195 unsigned char vr_num_of_rates; /* Rate Header fmt info */ 196 unsigned char rvd1[3]; 197 unsigned short vr_bytes_per_pkt[8]; 198 unsigned int rvd2[5]; 199 200 /* Vrat chunk */ 201 unsigned char vrat[4]; 202 unsigned int s_vrat; 203 unsigned int v_rate; 204 unsigned int size_in_pkts; 205 206 /* Data chunk */ 207 unsigned char data[4]; 208 unsigned int s_data; 209} __attribute__ ((packed)); 210 211static int totaldatalen = 0; 212static int framecnt = 0; 213/************************************************************************/ 214/* GLOBAL INIT */ 215/************************************************************************/ 216 217unsigned int input_buf_cnt = 0; 218unsigned int output_buf_cnt = 0; 219int used_ip_buf_cnt = 0; 220volatile int event_is_done = 0; 221volatile int ebd_event_is_done = 0; 222volatile int fbd_event_is_done = 0; 223volatile int etb_event_is_done = 0; 224int ebd_cnt; 225int bInputEosReached = 0; 226int bOutputEosReached = 0; 227int bInputEosReached_tunnel = 0; 228static int etb_done = 0; 229int bFlushing = false; 230int bPause = false; 231const char *in_filename; 232const char *out_filename; 233 234int timeStampLfile = 0; 235int timestampInterval = 100; 236 237//* OMX Spec Version supported by the wrappers. Version = 1.1 */ 238const OMX_U32 CURRENT_OMX_SPEC_VERSION = 0x00000101; 239OMX_COMPONENTTYPE* amr_enc_handle = 0; 240 241OMX_BUFFERHEADERTYPE **pInputBufHdrs = NULL; 242OMX_BUFFERHEADERTYPE **pOutputBufHdrs = NULL; 243 244/************************************************************************/ 245/* GLOBAL FUNC DECL */ 246/************************************************************************/ 247int Init_Encoder(char*); 248int Play_Encoder(); 249OMX_STRING aud_comp; 250/**************************************************************************/ 251/* STATIC DECLARATIONS */ 252/**************************************************************************/ 253 254static int open_audio_file (); 255static int Read_Buffer(OMX_BUFFERHEADERTYPE *pBufHdr ); 256static OMX_ERRORTYPE Allocate_Buffer ( OMX_COMPONENTTYPE *amr_enc_handle, 257 OMX_BUFFERHEADERTYPE ***pBufHdrs, 258 OMX_U32 nPortIndex, 259 unsigned int bufCntMin, unsigned int bufSize); 260 261 262static OMX_ERRORTYPE EventHandler(OMX_IN OMX_HANDLETYPE hComponent, 263 OMX_IN OMX_PTR pAppData, 264 OMX_IN OMX_EVENTTYPE eEvent, 265 OMX_IN OMX_U32 nData1, OMX_IN OMX_U32 nData2, 266 OMX_IN OMX_PTR pEventData); 267static OMX_ERRORTYPE EmptyBufferDone(OMX_IN OMX_HANDLETYPE hComponent, 268 OMX_IN OMX_PTR pAppData, 269 OMX_IN OMX_BUFFERHEADERTYPE* pBuffer); 270 271static OMX_ERRORTYPE FillBufferDone(OMX_IN OMX_HANDLETYPE hComponent, 272 OMX_IN OMX_PTR pAppData, 273 OMX_IN OMX_BUFFERHEADERTYPE* pBuffer); 274static OMX_ERRORTYPE parse_pcm_header(); 275void wait_for_event(void) 276{ 277 pthread_mutex_lock(&lock); 278 DEBUG_PRINT("%s: event_is_done=%d", __FUNCTION__, event_is_done); 279 while (event_is_done == 0) { 280 pthread_cond_wait(&cond, &lock); 281 } 282 event_is_done = 0; 283 pthread_mutex_unlock(&lock); 284} 285 286void event_complete(void ) 287{ 288 pthread_mutex_lock(&lock); 289 if (event_is_done == 0) { 290 event_is_done = 1; 291 pthread_cond_broadcast(&cond); 292 } 293 pthread_mutex_unlock(&lock); 294} 295 296void etb_wait_for_event(void) 297{ 298 pthread_mutex_lock(&etb_lock1); 299 DEBUG_PRINT("%s: etb_event_is_done=%d", __FUNCTION__, etb_event_is_done); 300 while (etb_event_is_done == 0) { 301 pthread_cond_wait(&etb_cond, &etb_lock1); 302 } 303 etb_event_is_done = 0; 304 pthread_mutex_unlock(&etb_lock1); 305} 306 307void etb_event_complete(void ) 308{ 309 pthread_mutex_lock(&etb_lock1); 310 if (etb_event_is_done == 0) { 311 etb_event_is_done = 1; 312 pthread_cond_broadcast(&etb_cond); 313 } 314 pthread_mutex_unlock(&etb_lock1); 315} 316 317 318OMX_ERRORTYPE EventHandler(OMX_IN OMX_HANDLETYPE hComponent, 319 OMX_IN OMX_PTR pAppData, 320 OMX_IN OMX_EVENTTYPE eEvent, 321 OMX_IN OMX_U32 nData1, OMX_IN OMX_U32 nData2, 322 OMX_IN OMX_PTR pEventData) 323{ 324 DEBUG_PRINT("Function %s \n", __FUNCTION__); 325 326 /* To remove warning for unused variable to keep prototype same */ 327 (void)hComponent; 328 (void)pAppData; 329 (void)pEventData; 330 switch(eEvent) { 331 case OMX_EventCmdComplete: 332 DEBUG_PRINT("\n OMX_EventCmdComplete event=%d data1=%u data2=%u\n",(OMX_EVENTTYPE)eEvent, 333 nData1,nData2); 334 event_complete(); 335 break; 336 case OMX_EventError: 337 DEBUG_PRINT("\n OMX_EventError \n"); 338 break; 339 case OMX_EventBufferFlag: 340 DEBUG_PRINT("\n OMX_EventBufferFlag \n"); 341 bOutputEosReached = true; 342 event_complete(); 343 break; 344 case OMX_EventPortSettingsChanged: 345 DEBUG_PRINT("\n OMX_EventPortSettingsChanged \n"); 346 break; 347 default: 348 DEBUG_PRINT("\n Unknown Event \n"); 349 break; 350 } 351 return OMX_ErrorNone; 352} 353 354OMX_ERRORTYPE FillBufferDone(OMX_IN OMX_HANDLETYPE hComponent, 355 OMX_IN OMX_PTR pAppData, 356 OMX_IN OMX_BUFFERHEADERTYPE* pBuffer) 357{ 358 size_t bytes_writen = 0; 359 size_t total_bytes_writen = 0; 360 size_t len = 0; 361 struct enc_meta_out *meta = NULL; 362 OMX_U8 *src = pBuffer->pBuffer; 363 unsigned int num_of_frames = 1; 364 365 /* To remove warning for unused variable to keep prototype same */ 366 (void)pAppData; 367 368 if(((pBuffer->nFlags & OMX_BUFFERFLAG_EOS) == OMX_BUFFERFLAG_EOS)) { 369 DEBUG_PRINT("FBD::EOS on output port\n "); 370 bOutputEosReached = true; 371 return OMX_ErrorNone; 372 } 373 if(bInputEosReached_tunnel || bOutputEosReached) 374 { 375 DEBUG_PRINT("EOS REACHED NO MORE PROCESSING OF BUFFERS\n"); 376 return OMX_ErrorNone; 377 } 378 if(num_of_frames != src[0]){ 379 380 printf("Data corrupt\n"); 381 return OMX_ErrorNone; 382 } 383 /* Skip the first bytes */ 384 385 386 387 src += sizeof(unsigned char); 388 meta = (struct enc_meta_out *)src; 389 while (num_of_frames > 0) { 390 meta = (struct enc_meta_out *)src; 391 /*printf("offset=%d framesize=%d encoded_pcm[%d] msw_ts[%d]lsw_ts[%d] nflags[%d]\n", 392 meta->offset_to_frame, 393 meta->frame_size, 394 meta->encoded_pcm_samples, meta->msw_ts, meta->lsw_ts, meta->nflags);*/ 395 len = meta->frame_size; 396 397 bytes_writen = fwrite(pBuffer->pBuffer + sizeof(unsigned char) + meta->offset_to_frame,1,len,outputBufferFile); 398 if(bytes_writen < len) 399 { 400 DEBUG_PRINT("error: invalid AMR encoded data \n"); 401 return OMX_ErrorNone; 402 } 403 src += sizeof(struct enc_meta_out); 404 num_of_frames--; 405 total_bytes_writen += len; 406 } 407 DEBUG_PRINT(" FillBufferDone size writen to file %zu count %d\n",total_bytes_writen, framecnt); 408 totaldatalen = totaldatalen + (int)total_bytes_writen; 409 framecnt++; 410 411 DEBUG_PRINT(" FBD calling FTB\n"); 412 OMX_FillThisBuffer(hComponent,pBuffer); 413 414 return OMX_ErrorNone; 415} 416 417OMX_ERRORTYPE EmptyBufferDone(OMX_IN OMX_HANDLETYPE hComponent, 418 OMX_IN OMX_PTR pAppData, 419 OMX_IN OMX_BUFFERHEADERTYPE* pBuffer) 420{ 421 int readBytes =0; 422 /* To remove warning for unused variable to keep prototype same */ 423 (void)pAppData; 424 425 ebd_cnt++; 426 used_ip_buf_cnt--; 427 pthread_mutex_lock(&etb_lock); 428 if(!etb_done) 429 { 430 DEBUG_PRINT("\n*********************************************\n"); 431 DEBUG_PRINT("Wait till first set of buffers are given to component\n"); 432 DEBUG_PRINT("\n*********************************************\n"); 433 etb_done++; 434 pthread_mutex_unlock(&etb_lock); 435 etb_wait_for_event(); 436 } 437 else 438 { 439 pthread_mutex_unlock(&etb_lock); 440 } 441 442 443 if(bInputEosReached) 444 { 445 DEBUG_PRINT("\n*********************************************\n"); 446 DEBUG_PRINT(" EBD::EOS on input port\n "); 447 DEBUG_PRINT("*********************************************\n"); 448 return OMX_ErrorNone; 449 }else if (bFlushing == true) { 450 DEBUG_PRINT("omx_amr_adec_test: bFlushing is set to TRUE used_ip_buf_cnt=%d\n",used_ip_buf_cnt); 451 if (used_ip_buf_cnt == 0) { 452 bFlushing = false; 453 } else { 454 DEBUG_PRINT("omx_amr_adec_test: more buffer to come back used_ip_buf_cnt=%d\n",used_ip_buf_cnt); 455 return OMX_ErrorNone; 456 } 457 } 458 459 if((readBytes = Read_Buffer(pBuffer)) > 0) { 460 pBuffer->nFilledLen = (OMX_U32)readBytes; 461 used_ip_buf_cnt++; 462 OMX_EmptyThisBuffer(hComponent,pBuffer); 463 } 464 else{ 465 pBuffer->nFlags |= OMX_BUFFERFLAG_EOS; 466 used_ip_buf_cnt++; 467 bInputEosReached = true; 468 pBuffer->nFilledLen = 0; 469 OMX_EmptyThisBuffer(hComponent,pBuffer); 470 DEBUG_PRINT("EBD..Either EOS or Some Error while reading file\n"); 471 } 472 return OMX_ErrorNone; 473} 474 475void signal_handler(int sig_id) { 476 477 /* Flush */ 478 if (sig_id == SIGUSR1) { 479 DEBUG_PRINT("%s Initiate flushing\n", __FUNCTION__); 480 bFlushing = true; 481 OMX_SendCommand(amr_enc_handle, OMX_CommandFlush, OMX_ALL, NULL); 482 } else if (sig_id == SIGUSR2) { 483 if (bPause == true) { 484 DEBUG_PRINT("%s resume record\n", __FUNCTION__); 485 bPause = false; 486 OMX_SendCommand(amr_enc_handle, OMX_CommandStateSet, OMX_StateExecuting, NULL); 487 } else { 488 DEBUG_PRINT("%s pause record\n", __FUNCTION__); 489 bPause = true; 490 OMX_SendCommand(amr_enc_handle, OMX_CommandStateSet, OMX_StatePause, NULL); 491 } 492 } 493} 494 495int main(int argc, char **argv) 496{ 497 unsigned int bufCnt=0; 498 OMX_ERRORTYPE result; 499 500 struct sigaction sa; 501 char amr_header[6] = {0x23, 0x21, 0x41, 0x4D, 0x52, 0x0A}; 502 memset(&sa, 0, sizeof(sa)); 503 sa.sa_handler = &signal_handler; 504 sigaction(SIGABRT, &sa, NULL); 505 sigaction(SIGUSR1, &sa, NULL); 506 sigaction(SIGUSR2, &sa, NULL); 507 508 (void) signal(SIGINT, Release_Encoder); 509 510 pthread_cond_init(&cond, 0); 511 pthread_mutex_init(&lock, 0); 512 pthread_cond_init(&etb_cond, 0); 513 pthread_mutex_init(&etb_lock, 0); 514 pthread_mutex_init(&etb_lock1, 0); 515 516 if (argc >= 8) { 517 in_filename = argv[1]; 518 out_filename = argv[2]; 519 tunnel = (uint32_t)atoi(argv[3]); 520 bandmode = (uint32_t)atoi(argv[4]); 521 dtxenable = (uint32_t)atoi(argv[5]); 522 recpath = (uint32_t)atoi(argv[6]); // No configuration support yet.. 523 rectime = (uint32_t)atoi(argv[7]); 524 525 } else { 526 DEBUG_PRINT(" invalid format: \n"); 527 DEBUG_PRINT("ex: ./mm-aenc-omxamr-test INPUTFILE OUTPUTFILE Tunnel BANDMODE DTXENABLE RECORDPATH RECORDTIME\n"); 528 DEBUG_PRINT("Bandmode 1-7, dtxenable 0-1\n"); 529 DEBUG_PRINT("RECORDPATH 0(TX),1(RX),2(BOTH),3(MIC)\n"); 530 DEBUG_PRINT("RECORDTIME in seconds for AST Automation\n"); 531 return 0; 532 } 533 if(recpath != 3) { 534 DEBUG_PRINT("For RECORDPATH Only MIC supported\n"); 535 return 0; 536 } 537 if(tunnel == 0) 538 aud_comp = "OMX.qcom.audio.encoder.amrnb"; 539 else 540 aud_comp = "OMX.qcom.audio.encoder.tunneled.amrnb"; 541 if(Init_Encoder(aud_comp)!= 0x00) 542 { 543 DEBUG_PRINT("Decoder Init failed\n"); 544 return -1; 545 } 546 547 fcntl(0, F_SETFL, O_NONBLOCK); 548 549 if(Play_Encoder() != 0x00) 550 { 551 DEBUG_PRINT("Play_Decoder failed\n"); 552 return -1; 553 } 554 555 // Wait till EOS is reached... 556 if(rectime && tunnel) 557 { 558 sleep(rectime); 559 rectime = 0; 560 bInputEosReached_tunnel = 1; 561 DEBUG_PRINT("\EOS ON INPUT PORT\n"); 562 } 563 else 564 { 565 wait_for_event(); 566 } 567 568 if((bInputEosReached_tunnel) || ((bOutputEosReached) && !tunnel)) 569 { 570 571 DEBUG_PRINT("\nMoving the decoder to idle state \n"); 572 OMX_SendCommand(amr_enc_handle, OMX_CommandStateSet, OMX_StateIdle,0); 573 wait_for_event(); 574 575 DEBUG_PRINT("\nMoving the encoder to loaded state \n"); 576 OMX_SendCommand(amr_enc_handle, OMX_CommandStateSet, OMX_StateLoaded,0); 577 sleep(1); 578 if (!tunnel) 579 { 580 DEBUG_PRINT("\nFillBufferDone: Deallocating i/p buffers \n"); 581 for(bufCnt=0; bufCnt < input_buf_cnt; ++bufCnt) { 582 OMX_FreeBuffer(amr_enc_handle, 0, pInputBufHdrs[bufCnt]); 583 } 584 } 585 586 DEBUG_PRINT ("\nFillBufferDone: Deallocating o/p buffers \n"); 587 for(bufCnt=0; bufCnt < output_buf_cnt; ++bufCnt) { 588 OMX_FreeBuffer(amr_enc_handle, 1, pOutputBufHdrs[bufCnt]); 589 } 590 wait_for_event(); 591 fseek(outputBufferFile, 0,SEEK_SET); 592 fwrite(amr_header,1,AMR_HEADER_SIZE,outputBufferFile); 593 594 result = OMX_FreeHandle(amr_enc_handle); 595 if (result != OMX_ErrorNone) { 596 DEBUG_PRINT ("\nOMX_FreeHandle error. Error code: %d\n", result); 597 } 598 599 /* Deinit OpenMAX */ 600 if(tunnel) 601 { 602 #ifdef AUDIOV2 603 if (msm_route_stream(DIR_TX,session_id,device_id, 0)) 604 { 605 DEBUG_PRINT("\ncould not set stream routing\n"); 606 return -1; 607 } 608 if (msm_en_device(device_id, 0)) 609 { 610 DEBUG_PRINT("\ncould not enable device\n"); 611 return -1; 612 } 613 msm_mixer_close(); 614 #endif 615 } 616 OMX_Deinit(); 617 ebd_cnt=0; 618 bOutputEosReached = false; 619 bInputEosReached_tunnel = false; 620 bInputEosReached = 0; 621 amr_enc_handle = NULL; 622 pthread_cond_destroy(&cond); 623 pthread_mutex_destroy(&lock); 624 fclose(outputBufferFile); 625 DEBUG_PRINT("*****************************************\n"); 626 DEBUG_PRINT("******...AMR ENC TEST COMPLETED...***************\n"); 627 DEBUG_PRINT("*****************************************\n"); 628 } 629 return 0; 630} 631 632void Release_Encoder() 633{ 634 static int cnt=0; 635 OMX_ERRORTYPE result; 636 637 DEBUG_PRINT("END OF AMR ENCODING: EXITING PLEASE WAIT\n"); 638 bInputEosReached_tunnel = 1; 639 event_complete(); 640 cnt++; 641 if(cnt > 1) 642 { 643 /* FORCE RESET */ 644 amr_enc_handle = NULL; 645 ebd_cnt=0; 646 bInputEosReached_tunnel = false; 647 648 result = OMX_FreeHandle(amr_enc_handle); 649 if (result != OMX_ErrorNone) { 650 DEBUG_PRINT ("\nOMX_FreeHandle error. Error code: %d\n", result); 651 } 652 653 /* Deinit OpenMAX */ 654 655 OMX_Deinit(); 656 657 pthread_cond_destroy(&cond); 658 pthread_mutex_destroy(&lock); 659 DEBUG_PRINT("*****************************************\n"); 660 DEBUG_PRINT("******...AMR ENC TEST COMPLETED...***************\n"); 661 DEBUG_PRINT("*****************************************\n"); 662 exit(0); 663 } 664} 665 666int Init_Encoder(OMX_STRING audio_component) 667{ 668 DEBUG_PRINT("Inside %s \n", __FUNCTION__); 669 OMX_ERRORTYPE omxresult; 670 OMX_U32 total = 0; 671 typedef OMX_U8* OMX_U8_PTR; 672 char *role ="audio_encoder"; 673 674 static OMX_CALLBACKTYPE call_back = { 675 &EventHandler,&EmptyBufferDone,&FillBufferDone 676 }; 677 678 /* Init. the OpenMAX Core */ 679 DEBUG_PRINT("\nInitializing OpenMAX Core....\n"); 680 omxresult = OMX_Init(); 681 682 if(OMX_ErrorNone != omxresult) { 683 DEBUG_PRINT("\n Failed to Init OpenMAX core"); 684 return -1; 685 } 686 else { 687 DEBUG_PRINT("\nOpenMAX Core Init Done\n"); 688 } 689 690 /* Query for audio decoders*/ 691 DEBUG_PRINT("Amr_test: Before entering OMX_GetComponentOfRole"); 692 OMX_GetComponentsOfRole(role, &total, 0); 693 DEBUG_PRINT ("\nTotal components of role=%s :%u", role, total); 694 695 696 omxresult = OMX_GetHandle((OMX_HANDLETYPE*)(&amr_enc_handle), 697 (OMX_STRING)audio_component, NULL, &call_back); 698 if (FAILED(omxresult)) { 699 DEBUG_PRINT("\nFailed to Load the component:%s\n", audio_component); 700 return -1; 701 } 702 else 703 { 704 DEBUG_PRINT("\nComponent %s is in LOADED state\n", audio_component); 705 } 706 707 /* Get the port information */ 708 CONFIG_VERSION_SIZE(portParam); 709 omxresult = OMX_GetParameter(amr_enc_handle, OMX_IndexParamAudioInit, 710 (OMX_PTR)&portParam); 711 712 if(FAILED(omxresult)) { 713 DEBUG_PRINT("\nFailed to get Port Param\n"); 714 return -1; 715 } 716 else 717 { 718 DEBUG_PRINT("\nportParam.nPorts:%u\n", portParam.nPorts); 719 DEBUG_PRINT("\nportParam.nStartPortNumber:%u\n", 720 portParam.nStartPortNumber); 721 } 722 723 if(OMX_ErrorNone != omxresult) 724 { 725 DEBUG_PRINT("Set parameter failed"); 726 } 727 728 return 0; 729} 730 731int Play_Encoder() 732{ 733 unsigned int i; 734 int Size=0; 735 DEBUG_PRINT("Inside %s \n", __FUNCTION__); 736 OMX_ERRORTYPE ret; 737 OMX_INDEXTYPE index; 738#ifdef __LP64__ 739 DEBUG_PRINT("sizeof[%ld]\n", sizeof(OMX_BUFFERHEADERTYPE)); 740#else 741 DEBUG_PRINT("sizeof[%d]\n", sizeof(OMX_BUFFERHEADERTYPE)); 742#endif 743 744 /* open the i/p and o/p files based on the video file format passed */ 745 if(open_audio_file()) { 746 DEBUG_PRINT("\n Returning -1"); 747 return -1; 748 } 749 750 /* Query the encoder input min buf requirements */ 751 CONFIG_VERSION_SIZE(inputportFmt); 752 753 /* Port for which the Client needs to obtain info */ 754 inputportFmt.nPortIndex = portParam.nStartPortNumber; 755 756 OMX_GetParameter(amr_enc_handle,OMX_IndexParamPortDefinition,&inputportFmt); 757 DEBUG_PRINT ("\nEnc Input Buffer Count %u\n", inputportFmt.nBufferCountMin); 758 DEBUG_PRINT ("\nEnc: Input Buffer Size %u\n", inputportFmt.nBufferSize); 759 760 if(OMX_DirInput != inputportFmt.eDir) { 761 DEBUG_PRINT ("\nEnc: Expect Input Port\n"); 762 return -1; 763 } 764 765 pcmparam.nPortIndex = 0; 766 pcmparam.nChannels = channels; 767 pcmparam.nSamplingRate = samplerate; 768 OMX_SetParameter(amr_enc_handle,OMX_IndexParamAudioPcm,&pcmparam); 769 770 771 /* Query the encoder outport's min buf requirements */ 772 CONFIG_VERSION_SIZE(outputportFmt); 773 /* Port for which the Client needs to obtain info */ 774 outputportFmt.nPortIndex = portParam.nStartPortNumber + 1; 775 776 OMX_GetParameter(amr_enc_handle,OMX_IndexParamPortDefinition,&outputportFmt); 777 DEBUG_PRINT ("\nEnc: Output Buffer Count %u\n", outputportFmt.nBufferCountMin); 778 DEBUG_PRINT ("\nEnc: Output Buffer Size %u\n", outputportFmt.nBufferSize); 779 780 if(OMX_DirOutput != outputportFmt.eDir) { 781 DEBUG_PRINT ("\nEnc: Expect Output Port\n"); 782 return -1; 783 } 784 785 786 CONFIG_VERSION_SIZE(amrparam); 787 788 amrparam.nPortIndex = 1; 789 amrparam.nChannels = channels; //2 ; /* 1-> mono 2-> stereo*/ 790 amrparam.eAMRBandMode = bandmode; 791 amrparam.eAMRDTXMode = dtxenable; 792 OMX_SetParameter(amr_enc_handle,OMX_IndexParamAudioAmr,&amrparam); 793 OMX_GetExtensionIndex(amr_enc_handle,"OMX.Qualcomm.index.audio.sessionId",&index); 794 OMX_GetParameter(amr_enc_handle,index,&streaminfoparam); 795 if(tunnel) { 796 #ifdef AUDIOV2 797 session_id = streaminfoparam.sessionId; 798 control = msm_mixer_open("/dev/snd/controlC0", 0); 799 if(control < 0) 800 printf("ERROR opening the device\n"); 801 device_id = msm_get_device(device); 802 DEBUG_PRINT ("\ndevice_id = %d\n",device_id); 803 DEBUG_PRINT("\nsession_id = %d\n",session_id); 804 if (msm_en_device(device_id, 1)) 805 { 806 perror("could not enable device\n"); 807 return -1; 808 } 809 if (msm_route_stream(DIR_TX,session_id,device_id, 1)) 810 { 811 perror("could not set stream routing\n"); 812 return -1; 813 } 814 #endif 815 } 816 817 DEBUG_PRINT ("\nOMX_SendCommand Encoder -> IDLE\n"); 818 OMX_SendCommand(amr_enc_handle, OMX_CommandStateSet, OMX_StateIdle,0); 819 /* wait_for_event(); should not wait here event complete status will 820 not come until enough buffer are allocated */ 821 if (tunnel == 0) 822 { 823 input_buf_cnt = inputportFmt.nBufferCountActual; // inputportFmt.nBufferCountMin + 5; 824 DEBUG_PRINT("Transition to Idle State succesful...\n"); 825 /* Allocate buffer on decoder's i/p port */ 826 error = Allocate_Buffer(amr_enc_handle, &pInputBufHdrs, inputportFmt.nPortIndex, 827 input_buf_cnt, inputportFmt.nBufferSize); 828 if (error != OMX_ErrorNone || pInputBufHdrs == NULL ) { 829 DEBUG_PRINT ("\nOMX_AllocateBuffer Input buffer error\n"); 830 return -1; 831 } 832 else { 833 DEBUG_PRINT ("\nOMX_AllocateBuffer Input buffer success\n"); 834 } 835 } 836 output_buf_cnt = outputportFmt.nBufferCountMin ; 837 838 /* Allocate buffer on encoder's O/Pp port */ 839 error = Allocate_Buffer(amr_enc_handle, &pOutputBufHdrs, outputportFmt.nPortIndex, 840 output_buf_cnt, outputportFmt.nBufferSize); 841 if (error != OMX_ErrorNone || pOutputBufHdrs == NULL ) { 842 DEBUG_PRINT ("\nOMX_AllocateBuffer Output buffer error\n"); 843 return -1; 844 } 845 else { 846 DEBUG_PRINT ("\nOMX_AllocateBuffer Output buffer success\n"); 847 } 848 849 wait_for_event(); 850 851 852 if (tunnel == 1) 853 { 854 DEBUG_PRINT ("\nOMX_SendCommand to enable TUNNEL MODE during IDLE\n"); 855 OMX_SendCommand(amr_enc_handle, OMX_CommandPortDisable,0,0); // disable input port 856 wait_for_event(); 857 } 858 859 DEBUG_PRINT ("\nOMX_SendCommand encoder -> Executing\n"); 860 OMX_SendCommand(amr_enc_handle, OMX_CommandStateSet, OMX_StateExecuting,0); 861 wait_for_event(); 862 863 DEBUG_PRINT(" Start sending OMX_FILLthisbuffer\n"); 864 865 for(i=0; i < output_buf_cnt; i++) { 866 DEBUG_PRINT ("\nOMX_FillThisBuffer on output buf no.%d\n",i); 867 pOutputBufHdrs[i]->nOutputPortIndex = 1; 868 pOutputBufHdrs[i]->nFlags = pOutputBufHdrs[i]->nFlags & (unsigned)~OMX_BUFFERFLAG_EOS; 869 ret = OMX_FillThisBuffer(amr_enc_handle, pOutputBufHdrs[i]); 870 if (OMX_ErrorNone != ret) { 871 DEBUG_PRINT("OMX_FillThisBuffer failed with result %d\n", ret); 872 } 873 else { 874 DEBUG_PRINT("OMX_FillThisBuffer success!\n"); 875 } 876 } 877 878if(tunnel == 0) 879{ 880 DEBUG_PRINT(" Start sending OMX_emptythisbuffer\n"); 881 for (i = 0;i < input_buf_cnt;i++) { 882 DEBUG_PRINT ("\nOMX_EmptyThisBuffer on Input buf no.%d\n",i); 883 pInputBufHdrs[i]->nInputPortIndex = 0; 884 Size = Read_Buffer(pInputBufHdrs[i]); 885 if(Size <=0 ){ 886 DEBUG_PRINT("NO DATA READ\n"); 887 bInputEosReached = true; 888 pInputBufHdrs[i]->nFlags= OMX_BUFFERFLAG_EOS; 889 } 890 pInputBufHdrs[i]->nFilledLen = (OMX_U32)Size; 891 pInputBufHdrs[i]->nInputPortIndex = 0; 892 used_ip_buf_cnt++; 893 ret = OMX_EmptyThisBuffer(amr_enc_handle, pInputBufHdrs[i]); 894 if (OMX_ErrorNone != ret) { 895 DEBUG_PRINT("OMX_EmptyThisBuffer failed with result %d\n", ret); 896 } 897 else { 898 DEBUG_PRINT("OMX_EmptyThisBuffer success!\n"); 899 } 900 if(Size <=0 ){ 901 break;//eos reached 902 } 903 } 904 pthread_mutex_lock(&etb_lock); 905 if(etb_done) 906{ 907 DEBUG_PRINT("Component is waiting for EBD to be released.\n"); 908 etb_event_complete(); 909 } 910 else 911 { 912 DEBUG_PRINT("\n****************************\n"); 913 DEBUG_PRINT("EBD not yet happened ...\n"); 914 DEBUG_PRINT("\n****************************\n"); 915 etb_done++; 916 } 917 pthread_mutex_unlock(&etb_lock); 918} 919 920 return 0; 921} 922 923 924 925static OMX_ERRORTYPE Allocate_Buffer ( OMX_COMPONENTTYPE *avc_enc_handle, 926 OMX_BUFFERHEADERTYPE ***pBufHdrs, 927 OMX_U32 nPortIndex, 928 unsigned int bufCntMin, unsigned int bufSize) 929{ 930 DEBUG_PRINT("Inside %s \n", __FUNCTION__); 931 OMX_ERRORTYPE error=OMX_ErrorNone; 932 unsigned int bufCnt=0; 933 934 /* To remove warning for unused variable to keep prototype same */ 935 (void)avc_enc_handle; 936 *pBufHdrs= (OMX_BUFFERHEADERTYPE **) 937 malloc(sizeof(OMX_BUFFERHEADERTYPE*)*bufCntMin); 938 939 for(bufCnt=0; bufCnt < bufCntMin; ++bufCnt) { 940 DEBUG_PRINT("\n OMX_AllocateBuffer No %d \n", bufCnt); 941 error = OMX_AllocateBuffer(amr_enc_handle, &((*pBufHdrs)[bufCnt]), 942 nPortIndex, NULL, bufSize); 943 } 944 945 return error; 946} 947 948 949 950 951static int Read_Buffer (OMX_BUFFERHEADERTYPE *pBufHdr ) 952{ 953 954 size_t bytes_read=0; 955 956 957 pBufHdr->nFilledLen = 0; 958 pBufHdr->nFlags |= OMX_BUFFERFLAG_EOS; 959 960 bytes_read = fread(pBufHdr->pBuffer, 1, pBufHdr->nAllocLen , inputBufferFile); 961 962 pBufHdr->nFilledLen = (OMX_U32)bytes_read; 963 // Time stamp logic 964 ((OMX_BUFFERHEADERTYPE *)pBufHdr)->nTimeStamp = \ 965 966 (OMX_TICKS) ((total_pcm_bytes * 1000)/(samplerate * channels *2)); 967 968 DEBUG_PRINT ("\n--time stamp -- %ld\n", (unsigned long)((OMX_BUFFERHEADERTYPE *)pBufHdr)->nTimeStamp); 969 if(bytes_read == 0) 970 { 971 pBufHdr->nFlags |= OMX_BUFFERFLAG_EOS; 972 DEBUG_PRINT ("\nBytes read zero\n"); 973 } 974 else 975 { 976 pBufHdr->nFlags = pBufHdr->nFlags & (unsigned)~OMX_BUFFERFLAG_EOS; 977 978 total_pcm_bytes = (unsigned)(total_pcm_bytes + bytes_read); 979 } 980 981 return (int)bytes_read;; 982} 983 984 985 986//In Encoder this Should Open a PCM or WAV file for input. 987 988static int open_audio_file () 989{ 990 int error_code = 0; 991 992 if (!tunnel) 993 { 994 DEBUG_PRINT("Inside %s filename=%s\n", __FUNCTION__, in_filename); 995 inputBufferFile = fopen (in_filename, "rb"); 996 if (inputBufferFile == NULL) { 997 DEBUG_PRINT("\ni/p file %s could NOT be opened\n", 998 in_filename); 999 error_code = -1; 1000 } 1001 if(parse_pcm_header() != 0x00) 1002 { 1003 DEBUG_PRINT("PCM parser failed \n"); 1004 return -1; 1005 } 1006 } 1007 1008 DEBUG_PRINT("Inside %s filename=%s\n", __FUNCTION__, out_filename); 1009 outputBufferFile = fopen (out_filename, "wb"); 1010 if (outputBufferFile == NULL) { 1011 DEBUG_PRINT("\ni/p file %s could NOT be opened\n", 1012 out_filename); 1013 error_code = -1; 1014 return error_code; 1015 } 1016 fseek(outputBufferFile, AMR_HEADER_SIZE, SEEK_SET); 1017 return error_code; 1018} 1019 1020static OMX_ERRORTYPE parse_pcm_header() 1021{ 1022 struct wav_header hdr; 1023 1024 DEBUG_PRINT("\n***************************************************************\n"); 1025 if(fread(&hdr, 1, sizeof(hdr),inputBufferFile)!=sizeof(hdr)) 1026 { 1027 DEBUG_PRINT("Wav file cannot read header\n"); 1028 return -1; 1029 } 1030 1031 if ((hdr.riff_id != ID_RIFF) || 1032 (hdr.riff_fmt != ID_WAVE)|| 1033 (hdr.fmt_id != ID_FMT)) 1034 { 1035 DEBUG_PRINT("Wav file is not a riff/wave file\n"); 1036 return -1; 1037 } 1038 1039 if (hdr.audio_format != FORMAT_PCM) 1040 { 1041 DEBUG_PRINT("Wav file is not adpcm format %d and fmt size is %d\n", 1042 hdr.audio_format, hdr.fmt_sz); 1043 return -1; 1044 } 1045 1046 DEBUG_PRINT("Samplerate is %d\n", hdr.sample_rate); 1047 DEBUG_PRINT("Channel Count is %d\n", hdr.num_channels); 1048 DEBUG_PRINT("\n***************************************************************\n"); 1049 1050 samplerate = hdr.sample_rate; 1051 channels = hdr.num_channels; 1052 total_pcm_bytes = 0; 1053 1054 return OMX_ErrorNone; 1055} 1056