1/*-------------------------------------------------------------------------- 2Copyright (c) 2010-2012, Code Aurora Forum. All rights reserved. 3 4Redistribution and use in source and binary forms, with or without 5modification, are permitted provided that the following conditions are met: 6 * Redistributions of source code must retain the above copyright 7 notice, this list of conditions and the following disclaimer. 8 * Redistributions in binary form must reproduce the above copyright 9 notice, this list of conditions and the following disclaimer in the 10 documentation and/or other materials provided with the distribution. 11 * Neither the name of Code Aurora nor 12 the names of its contributors may be used to endorse or promote 13 products derived from this software without specific prior written 14 permission. 15 16THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 17AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 18IMPLIED WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 19NON-INFRINGEMENT ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR 20CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, 21EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 22PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; 23OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, 24WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR 25OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF 26ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27--------------------------------------------------------------------------*/ 28/*======================================================================== 29 30 O p e n M M 31 V i d e o U t i l i t i e s 32 33*//** @file VideoUtils.cpp 34 This module contains utilities and helper routines. 35 36@par EXTERNALIZED FUNCTIONS 37 38@par INITIALIZATION AND SEQUENCING REQUIREMENTS 39 (none) 40 41*//*====================================================================== */ 42 43/* ======================================================================= 44 45 INCLUDE FILES FOR MODULE 46 47========================================================================== */ 48#include "h264_utils.h" 49#include "extra_data_handler.h" 50#include <string.h> 51#include <stdlib.h> 52#include <limits.h> 53#include <sys/time.h> 54#ifdef _ANDROID_ 55#include <cutils/properties.h> 56 extern "C"{ 57 #include<utils/Log.h> 58 } 59 60#endif 61 62/* ======================================================================= 63 64 DEFINITIONS AND DECLARATIONS FOR MODULE 65 66This section contains definitions for constants, macros, types, variables 67and other items needed by this module. 68 69========================================================================== */ 70 71#define SIZE_NAL_FIELD_MAX 4 72#define BASELINE_PROFILE 66 73#define MAIN_PROFILE 77 74#define HIGH_PROFILE 100 75 76#define MAX_SUPPORTED_LEVEL 32 77 78RbspParser::RbspParser (const uint8 *_begin, const uint8 *_end) 79: begin (_begin), end(_end), pos (- 1), bit (0), 80cursor (0xFFFFFF), advanceNeeded (true) 81{ 82} 83 84// Destructor 85/*lint -e{1540} Pointer member neither freed nor zeroed by destructor 86 * No problem 87 */ 88RbspParser::~RbspParser () {} 89 90// Return next RBSP byte as a word 91uint32 RbspParser::next () 92{ 93 if (advanceNeeded) advance (); 94 //return static_cast<uint32> (*pos); 95 return static_cast<uint32> (begin[pos]); 96} 97 98// Advance RBSP decoder to next byte 99void RbspParser::advance () 100{ 101 ++pos; 102 //if (pos >= stop) 103 if (begin + pos == end) 104 { 105 /*lint -e{730} Boolean argument to function 106 * I don't see a problem here 107 */ 108 //throw false; 109 ALOGV("H264Parser-->NEED TO THROW THE EXCEPTION...\n"); 110 } 111 cursor <<= 8; 112 //cursor |= static_cast<uint32> (*pos); 113 cursor |= static_cast<uint32> (begin[pos]); 114 if ((cursor & 0xFFFFFF) == 0x000003) 115 { 116 advance (); 117 } 118 advanceNeeded = false; 119} 120 121// Decode unsigned integer 122uint32 RbspParser::u (uint32 n) 123{ 124 uint32 i, s, x = 0; 125 for (i = 0; i < n; i += s) 126 { 127 s = static_cast<uint32>STD_MIN(static_cast<int>(8 - bit), 128 static_cast<int>(n - i)); 129 x <<= s; 130 131 x |= ((next () >> ((8 - static_cast<uint32>(bit)) - s)) & 132 ((1 << s) - 1)); 133 134 bit = (bit + s) % 8; 135 if (!bit) 136 { 137 advanceNeeded = true; 138 } 139 } 140 return x; 141} 142 143// Decode unsigned integer Exp-Golomb-coded syntax element 144uint32 RbspParser::ue () 145{ 146 int leadingZeroBits = -1; 147 for (uint32 b = 0; !b; ++leadingZeroBits) 148 { 149 b = u (1); 150 } 151 return ((1 << leadingZeroBits) - 1) + 152 u (static_cast<uint32>(leadingZeroBits)); 153} 154 155// Decode signed integer Exp-Golomb-coded syntax element 156int32 RbspParser::se () 157{ 158 const uint32 x = ue (); 159 if (!x) return 0; 160 else if (x & 1) return static_cast<int32> ((x >> 1) + 1); 161 else return - static_cast<int32> (x >> 1); 162} 163 164void H264_Utils::allocate_rbsp_buffer(uint32 inputBufferSize) 165{ 166 m_rbspBytes = (byte *) calloc(1,inputBufferSize); 167 m_prv_nalu.nal_ref_idc = 0; 168 m_prv_nalu.nalu_type = NALU_TYPE_UNSPECIFIED; 169} 170 171H264_Utils::H264_Utils(): m_height(0), 172 m_width(0), 173 m_rbspBytes(NULL), 174 m_au_data (false) 175{ 176 initialize_frame_checking_environment(); 177} 178 179H264_Utils::~H264_Utils() 180{ 181/* if(m_pbits) 182 { 183 delete(m_pbits); 184 m_pbits = NULL; 185 } 186*/ 187 if (m_rbspBytes) 188 { 189 free(m_rbspBytes); 190 m_rbspBytes = NULL; 191 } 192} 193 194/***********************************************************************/ 195/* 196FUNCTION: 197 H264_Utils::initialize_frame_checking_environment 198 199DESCRIPTION: 200 Extract RBSP data from a NAL 201 202INPUT/OUTPUT PARAMETERS: 203 None 204 205RETURN VALUE: 206 boolean 207 208SIDE EFFECTS: 209 None. 210*/ 211/***********************************************************************/ 212void H264_Utils::initialize_frame_checking_environment() 213{ 214 m_forceToStichNextNAL = false; 215 m_au_data = false; 216 m_prv_nalu.nal_ref_idc = 0; 217 m_prv_nalu.nalu_type = NALU_TYPE_UNSPECIFIED; 218} 219 220/***********************************************************************/ 221/* 222FUNCTION: 223 H264_Utils::extract_rbsp 224 225DESCRIPTION: 226 Extract RBSP data from a NAL 227 228INPUT/OUTPUT PARAMETERS: 229 <In> 230 buffer : buffer containing start code or nal length + NAL units 231 buffer_length : the length of the NAL buffer 232 start_code : If true, start code is detected, 233 otherwise size nal length is detected 234 size_of_nal_length_field: size of nal length field 235 236 <Out> 237 rbsp_bistream : extracted RBSP bistream 238 rbsp_length : the length of the RBSP bitstream 239 nal_unit : decoded NAL header information 240 241RETURN VALUE: 242 boolean 243 244SIDE EFFECTS: 245 None. 246*/ 247/***********************************************************************/ 248 249boolean H264_Utils::extract_rbsp(OMX_IN OMX_U8 *buffer, 250 OMX_IN OMX_U32 buffer_length, 251 OMX_IN OMX_U32 size_of_nal_length_field, 252 OMX_OUT OMX_U8 *rbsp_bistream, 253 OMX_OUT OMX_U32 *rbsp_length, 254 OMX_OUT NALU *nal_unit) 255{ 256 byte coef1, coef2, coef3; 257 uint32 pos = 0; 258 uint32 nal_len = buffer_length; 259 uint32 sizeofNalLengthField = 0; 260 uint32 zero_count; 261 boolean eRet = true; 262 boolean start_code = (size_of_nal_length_field==0)?true:false; 263 264 if(start_code) { 265 // Search start_code_prefix_one_3bytes (0x000001) 266 coef2 = buffer[pos++]; 267 coef3 = buffer[pos++]; 268 do { 269 if(pos >= buffer_length) 270 { 271 ALOGE("ERROR: In %s() - line %d", __func__, __LINE__); 272 return false; 273 } 274 275 coef1 = coef2; 276 coef2 = coef3; 277 coef3 = buffer[pos++]; 278 } while(coef1 || coef2 || coef3 != 1); 279 } 280 else if (size_of_nal_length_field) 281 { 282 /* This is the case to play multiple NAL units inside each access unit*/ 283 /* Extract the NAL length depending on sizeOfNALength field */ 284 sizeofNalLengthField = size_of_nal_length_field; 285 nal_len = 0; 286 while(size_of_nal_length_field--) 287 { 288 nal_len |= buffer[pos++]<<(size_of_nal_length_field<<3); 289 } 290 if (nal_len >= buffer_length) 291 { 292 ALOGE("ERROR: In %s() - line %d", __func__, __LINE__); 293 return false; 294 } 295 } 296 297 if (nal_len > buffer_length) 298 { 299 ALOGE("ERROR: In %s() - line %d", __func__, __LINE__); 300 return false; 301 } 302 if(pos + 1 > (nal_len + sizeofNalLengthField)) 303 { 304 ALOGE("ERROR: In %s() - line %d", __func__, __LINE__); 305 return false; 306 } 307 if (nal_unit->forbidden_zero_bit = (buffer[pos] & 0x80)) 308 { 309 ALOGE("ERROR: In %s() - line %d", __func__, __LINE__); 310 } 311 nal_unit->nal_ref_idc = (buffer[pos] & 0x60) >> 5; 312 nal_unit->nalu_type = buffer[pos++] & 0x1f; 313 ALOGV("\n@#@# Pos = %x NalType = %x buflen = %d", 314 pos-1, nal_unit->nalu_type, buffer_length); 315 *rbsp_length = 0; 316 317 318 if( nal_unit->nalu_type == NALU_TYPE_EOSEQ || 319 nal_unit->nalu_type == NALU_TYPE_EOSTREAM) 320 return (nal_len + sizeofNalLengthField); 321 322 zero_count = 0; 323 while (pos < (nal_len+sizeofNalLengthField)) //similar to for in p-42 324 { 325 if( zero_count == 2 ) { 326 if( buffer[pos] == 0x03 ) { 327 pos ++; 328 zero_count = 0; 329 continue; 330 } 331 if( buffer[pos] <= 0x01 ) { 332 if( start_code ) { 333 *rbsp_length -= 2; 334 pos -= 2; 335 return pos; 336 } 337 } 338 zero_count = 0; 339 } 340 zero_count ++; 341 if( buffer[pos] != 0 ) 342 zero_count = 0; 343 344 rbsp_bistream[(*rbsp_length)++] = buffer[pos++]; 345 } 346 347 return eRet; 348} 349 350/*=========================================================================== 351FUNCTION: 352 H264_Utils::iSNewFrame 353 354DESCRIPTION: 355 Returns true if NAL parsing successfull otherwise false. 356 357INPUT/OUTPUT PARAMETERS: 358 <In> 359 buffer : buffer containing start code or nal length + NAL units 360 buffer_length : the length of the NAL buffer 361 start_code : If true, start code is detected, 362 otherwise size nal length is detected 363 size_of_nal_length_field: size of nal length field 364 <out> 365 isNewFrame: true if the NAL belongs to a differenet frame 366 false if the NAL belongs to a current frame 367 368RETURN VALUE: 369 boolean true, if nal parsing is successful 370 false, if the nal parsing has errors 371 372SIDE EFFECTS: 373 None. 374===========================================================================*/ 375bool H264_Utils::isNewFrame(OMX_BUFFERHEADERTYPE *p_buf_hdr, 376 OMX_IN OMX_U32 size_of_nal_length_field, 377 OMX_OUT OMX_BOOL &isNewFrame) 378{ 379 NALU nal_unit; 380 uint16 first_mb_in_slice = 0; 381 OMX_IN OMX_U32 numBytesInRBSP = 0; 382 OMX_IN OMX_U8 *buffer = p_buf_hdr->pBuffer; 383 OMX_IN OMX_U32 buffer_length = p_buf_hdr->nFilledLen; 384 bool eRet = true; 385 386 ALOGV("isNewFrame: buffer %p buffer_length %d " 387 "size_of_nal_length_field %d\n", buffer, buffer_length, 388 size_of_nal_length_field); 389 390 if ( false == extract_rbsp(buffer, buffer_length, size_of_nal_length_field, 391 m_rbspBytes, &numBytesInRBSP, &nal_unit) ) 392 { 393 ALOGE("ERROR: In %s() - extract_rbsp() failed", __func__); 394 isNewFrame = OMX_FALSE; 395 eRet = false; 396 } 397 else 398 { 399 nalu_type = nal_unit.nalu_type; 400 switch (nal_unit.nalu_type) 401 { 402 case NALU_TYPE_IDR: 403 case NALU_TYPE_NON_IDR: 404 { 405 ALOGV("\n AU Boundary with NAL type %d ",nal_unit.nalu_type); 406 if (m_forceToStichNextNAL) 407 { 408 isNewFrame = OMX_FALSE; 409 } 410 else 411 { 412 RbspParser rbsp_parser(m_rbspBytes, (m_rbspBytes+numBytesInRBSP)); 413 first_mb_in_slice = rbsp_parser.ue(); 414 415 if((!first_mb_in_slice) || /*(slice.prv_frame_num != slice.frame_num ) ||*/ 416 ( (m_prv_nalu.nal_ref_idc != nal_unit.nal_ref_idc) && ( nal_unit.nal_ref_idc * m_prv_nalu.nal_ref_idc == 0 ) ) || 417 /*( ((m_prv_nalu.nalu_type == NALU_TYPE_IDR) && (nal_unit.nalu_type == NALU_TYPE_IDR)) && (slice.idr_pic_id != slice.prv_idr_pic_id) ) || */ 418 ( (m_prv_nalu.nalu_type != nal_unit.nalu_type ) && ((m_prv_nalu.nalu_type == NALU_TYPE_IDR) || (nal_unit.nalu_type == NALU_TYPE_IDR)) ) ) 419 { 420 //ALOGV("Found a New Frame due to NALU_TYPE_IDR/NALU_TYPE_NON_IDR"); 421 isNewFrame = OMX_TRUE; 422 } 423 else 424 { 425 isNewFrame = OMX_FALSE; 426 } 427 } 428 m_au_data = true; 429 m_forceToStichNextNAL = false; 430 break; 431 } 432 case NALU_TYPE_SPS: 433 case NALU_TYPE_PPS: 434 case NALU_TYPE_SEI: 435 { 436 ALOGV("\n Non-AU boundary with NAL type %d", nal_unit.nalu_type); 437 if(m_au_data) 438 { 439 isNewFrame = OMX_TRUE; 440 m_au_data = false; 441 } 442 else 443 { 444 isNewFrame = OMX_FALSE; 445 } 446 447 m_forceToStichNextNAL = true; 448 break; 449 } 450 case NALU_TYPE_ACCESS_DELIM: 451 case NALU_TYPE_UNSPECIFIED: 452 case NALU_TYPE_EOSEQ: 453 case NALU_TYPE_EOSTREAM: 454 default: 455 { 456 isNewFrame = OMX_FALSE; 457 // Do not update m_forceToStichNextNAL 458 break; 459 } 460 } // end of switch 461 } // end of if 462 m_prv_nalu = nal_unit; 463 ALOGV("get_h264_nal_type - newFrame value %d\n",isNewFrame); 464 return eRet; 465} 466 467void perf_metrics::start() 468{ 469 if (!active) 470 { 471 start_time = get_act_time(); 472 active = true; 473 } 474} 475 476void perf_metrics::stop() 477{ 478 OMX_U64 stop_time = get_act_time(); 479 if (active) 480 { 481 proc_time += (stop_time - start_time); 482 active = false; 483 } 484} 485 486void perf_metrics::end(OMX_U32 units_cntr) 487{ 488 stop(); 489 ALOGV("--> Processing time : [%.2f] Sec", (float)proc_time / 1e6); 490 if (units_cntr) 491 { 492 ALOGV("--> Avrg proc time : [%.2f] mSec", proc_time / (float)(units_cntr * 1e3)); 493 } 494} 495 496void perf_metrics::reset() 497{ 498 start_time = 0; 499 proc_time = 0; 500 active = false; 501} 502 503OMX_U64 perf_metrics::get_act_time() 504{ 505 struct timeval act_time = {0, 0}; 506 gettimeofday(&act_time, NULL); 507 return (act_time.tv_usec + act_time.tv_sec * 1e6); 508} 509 510OMX_U64 perf_metrics::processing_time_us() 511{ 512 return proc_time; 513} 514 515h264_stream_parser::h264_stream_parser() 516{ 517 reset(); 518#ifdef PANSCAN_HDLR 519 panscan_hdl = new panscan_handler(); 520 if (!panscan_hdl) 521 { 522 ALOGE("ERROR: Panscan hdl was not allocated!"); 523 } 524 else if (!panscan_hdl->initialize(10)) 525 { 526 ALOGE("ERROR: Allocating memory for panscan!"); 527 delete panscan_hdl; 528 panscan_hdl = NULL; 529 } 530#else 531 memset(&panscan_param, 0, sizeof(panscan_param)); 532 panscan_param.rect_id = NO_PAN_SCAN_BIT; 533#endif 534} 535 536h264_stream_parser::~h264_stream_parser() 537{ 538#ifdef PANSCAN_HDLR 539 if (panscan_hdl) 540 { 541 delete panscan_hdl; 542 panscan_hdl = NULL; 543 } 544#endif 545} 546 547void h264_stream_parser::reset() 548{ 549 curr_32_bit = 0; 550 bits_read = 0; 551 zero_cntr = 0; 552 emulation_code_skip_cntr = 0; 553 emulation_sc_enabled = true; 554 bitstream = NULL; 555 bitstream_bytes = 0; 556 memset(&vui_param, 0, sizeof(vui_param)); 557 vui_param.fixed_fps_prev_ts = LLONG_MAX; 558 memset(&sei_buf_period, 0, sizeof(sei_buf_period)); 559 memset(&sei_pic_timing, 0, sizeof(sei_pic_timing)); 560 memset(&frame_packing_arrangement,0,sizeof(frame_packing_arrangement)); 561 frame_packing_arrangement.cancel_flag = 1; 562 mbaff_flag = 0; 563} 564 565void h264_stream_parser::init_bitstream(OMX_U8* data, OMX_U32 size) 566{ 567 bitstream = data; 568 bitstream_bytes = size; 569 curr_32_bit = 0; 570 bits_read = 0; 571 zero_cntr = 0; 572 emulation_code_skip_cntr = 0; 573} 574 575void h264_stream_parser::parse_vui(bool vui_in_extradata) 576{ 577 OMX_U32 value = 0; 578 ALOGV("parse_vui: IN"); 579 if (vui_in_extradata) 580 while (!extract_bits(1) && more_bits()); // Discard VUI enable flag 581 if (!more_bits()) 582 return; 583 584 vui_param.aspect_ratio_info_present_flag = extract_bits(1); //aspect_ratio_info_present_flag 585 if (vui_param.aspect_ratio_info_present_flag) 586 { 587 ALOGV("Aspect Ratio Info present!"); 588 aspect_ratio_info(); 589 } 590 591 if (extract_bits(1)) //overscan_info_present_flag 592 extract_bits(1); //overscan_appropriate_flag 593 if (extract_bits(1)) //video_signal_type_present_flag 594 { 595 extract_bits(3); //video_format 596 extract_bits(1); //video_full_range_flag 597 if (extract_bits(1)) //colour_description_present_flag 598 { 599 extract_bits(8); //colour_primaries 600 extract_bits(8); //transfer_characteristics 601 extract_bits(8); //matrix_coefficients 602 } 603 } 604 if (extract_bits(1)) //chroma_location_info_present_flag 605 { 606 uev(); //chroma_sample_loc_type_top_field 607 uev(); //chroma_sample_loc_type_bottom_field 608 } 609 vui_param.timing_info_present_flag = extract_bits(1); 610 if (vui_param.timing_info_present_flag) 611 { 612 vui_param.num_units_in_tick = extract_bits(32); 613 vui_param.time_scale = extract_bits(32); 614 vui_param.fixed_frame_rate_flag = extract_bits(1); 615 ALOGV("Timing info present in VUI!"); 616 ALOGV(" num units in tick : %u", vui_param.num_units_in_tick); 617 ALOGV(" time scale : %u", vui_param.time_scale); 618 ALOGV(" fixed frame rate : %u", vui_param.fixed_frame_rate_flag); 619 } 620 vui_param.nal_hrd_parameters_present_flag = extract_bits(1); 621 if (vui_param.nal_hrd_parameters_present_flag) 622 { 623 ALOGV("nal hrd params present!"); 624 hrd_parameters(&vui_param.nal_hrd_parameters); 625 } 626 vui_param.vcl_hrd_parameters_present_flag = extract_bits(1); 627 if (vui_param.vcl_hrd_parameters_present_flag) 628 { 629 ALOGV("vcl hrd params present!"); 630 hrd_parameters(&vui_param.vcl_hrd_parameters); 631 } 632 if (vui_param.nal_hrd_parameters_present_flag || 633 vui_param.vcl_hrd_parameters_present_flag) 634 vui_param.low_delay_hrd_flag = extract_bits(1); 635 vui_param.pic_struct_present_flag = extract_bits(1); 636 ALOGV("pic_struct_present_flag : %u", vui_param.pic_struct_present_flag); 637 if (extract_bits(1)) //bitstream_restriction_flag 638 { 639 extract_bits(1); //motion_vectors_over_pic_boundaries_flag 640 uev(); //max_bytes_per_pic_denom 641 uev(); //max_bits_per_mb_denom 642 uev(); //log2_max_mv_length_vertical 643 uev(); //log2_max_mv_length_horizontal 644 uev(); //num_reorder_frames 645 uev(); //max_dec_frame_buffering 646 } 647 ALOGV("parse_vui: OUT"); 648} 649 650void h264_stream_parser::aspect_ratio_info() 651{ 652 ALOGV("aspect_ratio_info: IN"); 653 OMX_U32 aspect_ratio_idc = 0; 654 OMX_U32 aspect_ratio_x = 0; 655 OMX_U32 aspect_ratio_y = 0; 656 aspect_ratio_idc = extract_bits(8); //aspect_ratio_idc 657 switch (aspect_ratio_idc) 658 { 659 case 1: 660 aspect_ratio_x = 1; 661 aspect_ratio_y = 1; 662 break; 663 case 2: 664 aspect_ratio_x = 12; 665 aspect_ratio_y = 11; 666 break; 667 case 3: 668 aspect_ratio_x = 10; 669 aspect_ratio_y = 11; 670 break; 671 case 4: 672 aspect_ratio_x = 16; 673 aspect_ratio_y = 11; 674 break; 675 case 5: 676 aspect_ratio_x = 40; 677 aspect_ratio_y = 33; 678 break; 679 case 6: 680 aspect_ratio_x = 24; 681 aspect_ratio_y = 11; 682 break; 683 case 7: 684 aspect_ratio_x = 20; 685 aspect_ratio_y = 11; 686 break; 687 case 8: 688 aspect_ratio_x = 32; 689 aspect_ratio_y = 11; 690 break; 691 case 9: 692 aspect_ratio_x = 80; 693 aspect_ratio_y = 33; 694 break; 695 case 10: 696 aspect_ratio_x = 18; 697 aspect_ratio_y = 11; 698 break; 699 case 11: 700 aspect_ratio_x = 15; 701 aspect_ratio_y = 11; 702 break; 703 case 12: 704 aspect_ratio_x = 64; 705 aspect_ratio_y = 33; 706 break; 707 case 13: 708 aspect_ratio_x = 160; 709 aspect_ratio_y = 99; 710 break; 711 case 14: 712 aspect_ratio_x = 4; 713 aspect_ratio_y = 3; 714 break; 715 case 15: 716 aspect_ratio_x = 3; 717 aspect_ratio_y = 2; 718 break; 719 case 16: 720 aspect_ratio_x = 2; 721 aspect_ratio_y = 1; 722 break; 723 case 255: 724 aspect_ratio_x = extract_bits(16); //sar_width 725 aspect_ratio_y = extract_bits(16); //sar_height 726 break; 727 default: 728 ALOGV("-->aspect_ratio_idc: Reserved Value "); 729 break; 730 } 731 ALOGV("-->aspect_ratio_idc : %u", aspect_ratio_idc); 732 ALOGV("-->aspect_ratio_x : %u", aspect_ratio_x); 733 ALOGV("-->aspect_ratio_y : %u", aspect_ratio_y); 734 vui_param.aspect_ratio_info.aspect_ratio_idc = aspect_ratio_idc; 735 vui_param.aspect_ratio_info.aspect_ratio_x = aspect_ratio_x; 736 vui_param.aspect_ratio_info.aspect_ratio_y = aspect_ratio_y; 737 ALOGV("aspect_ratio_info: OUT"); 738} 739 740void h264_stream_parser::hrd_parameters(h264_hrd_param *hrd_param) 741{ 742 int idx; 743 ALOGV("hrd_parameters: IN"); 744 hrd_param->cpb_cnt = uev() + 1; 745 hrd_param->bit_rate_scale = extract_bits(4); 746 hrd_param->cpb_size_scale = extract_bits(4); 747 ALOGV("-->cpb_cnt : %u", hrd_param->cpb_cnt); 748 ALOGV("-->bit_rate_scale : %u", hrd_param->bit_rate_scale); 749 ALOGV("-->cpb_size_scale : %u", hrd_param->cpb_size_scale); 750 if (hrd_param->cpb_cnt > MAX_CPB_COUNT) 751 { 752 ALOGV("ERROR: Invalid hrd_param->cpb_cnt [%u]!", hrd_param->cpb_cnt); 753 return; 754 } 755 for (idx = 0; idx < hrd_param->cpb_cnt && more_bits(); idx++) 756 { 757 hrd_param->bit_rate_value[idx] = uev() + 1; 758 hrd_param->cpb_size_value[idx] = uev() + 1; 759 hrd_param->cbr_flag[idx] = extract_bits(1); 760 ALOGV("-->bit_rate_value [%d] : %u", idx, hrd_param->bit_rate_value[idx]); 761 ALOGV("-->cpb_size_value [%d] : %u", idx, hrd_param->cpb_size_value[idx]); 762 ALOGV("-->cbr_flag [%d] : %u", idx, hrd_param->cbr_flag[idx]); 763 } 764 hrd_param->initial_cpb_removal_delay_length = extract_bits(5) + 1; 765 hrd_param->cpb_removal_delay_length = extract_bits(5) + 1; 766 hrd_param->dpb_output_delay_length = extract_bits(5) + 1; 767 hrd_param->time_offset_length = extract_bits(5); 768 ALOGV("-->initial_cpb_removal_delay_length : %u", hrd_param->initial_cpb_removal_delay_length); 769 ALOGV("-->cpb_removal_delay_length : %u", hrd_param->cpb_removal_delay_length); 770 ALOGV("-->dpb_output_delay_length : %u", hrd_param->dpb_output_delay_length); 771 ALOGV("-->time_offset_length : %u", hrd_param->time_offset_length); 772 ALOGV("hrd_parameters: OUT"); 773} 774 775void h264_stream_parser::parse_sei() 776{ 777 OMX_U32 value = 0, processed_bytes = 0; 778 OMX_U8 *sei_msg_start = bitstream; 779 OMX_U32 sei_unit_size = bitstream_bytes; 780 ALOGV("@@parse_sei: IN sei_unit_size(%u)", sei_unit_size); 781 while ((processed_bytes + 2) < sei_unit_size && more_bits()) 782 { 783 init_bitstream(sei_msg_start + processed_bytes, sei_unit_size - processed_bytes); 784 ALOGV("-->NALU_TYPE_SEI"); 785 OMX_U32 payload_type = 0, payload_size = 0, aux = 0; 786 do { 787 value = extract_bits(8); 788 payload_type += value; 789 processed_bytes++; 790 } while (value == 0xFF); 791 ALOGV("-->payload_type : %u", payload_type); 792 do { 793 value = extract_bits(8); 794 payload_size += value; 795 processed_bytes++; 796 } while (value == 0xFF); 797 ALOGV("-->payload_size : %u", payload_size); 798 if (payload_size > 0) 799 { 800 switch (payload_type) 801 { 802 case BUFFERING_PERIOD: 803 sei_buffering_period(); 804 break; 805 case PIC_TIMING: 806 sei_picture_timing(); 807 break; 808 case PAN_SCAN_RECT: 809 sei_pan_scan(); 810 break; 811 case SEI_PAYLOAD_FRAME_PACKING_ARRANGEMENT: 812 parse_frame_pack(); 813 break; 814 default: 815 ALOGV("-->SEI payload type [%u] not implemented! size[%u]", payload_type, payload_size); 816 } 817 } 818 processed_bytes += (payload_size + emulation_code_skip_cntr); 819 ALOGV("-->SEI processed_bytes[%u]", processed_bytes); 820 } 821 ALOGV("@@parse_sei: OUT"); 822} 823 824void h264_stream_parser::sei_buffering_period() 825{ 826 int idx; 827 OMX_U32 value = 0; 828 h264_hrd_param *hrd_param = NULL; 829 ALOGV("@@sei_buffering_period: IN"); 830 value = uev(); // seq_parameter_set_id 831 ALOGV("-->seq_parameter_set_id : %u", value); 832 if (value > 31) 833 { 834 ALOGV("ERROR: Invalid seq_parameter_set_id [%u]!", value); 835 return; 836 } 837 sei_buf_period.is_valid = false; 838 if (vui_param.nal_hrd_parameters_present_flag) 839 { 840 hrd_param = &vui_param.nal_hrd_parameters; 841 if (hrd_param->cpb_cnt > MAX_CPB_COUNT) 842 { 843 ALOGV("ERROR: Invalid hrd_param->cpb_cnt [%u]!", hrd_param->cpb_cnt); 844 return; 845 } 846 for (idx = 0; idx < hrd_param->cpb_cnt ; idx++) 847 { 848 sei_buf_period.is_valid = true; 849 sei_buf_period.initial_cpb_removal_delay[idx] = extract_bits(hrd_param->initial_cpb_removal_delay_length); 850 sei_buf_period.initial_cpb_removal_delay_offset[idx] = extract_bits(hrd_param->initial_cpb_removal_delay_length); 851 ALOGV("-->initial_cpb_removal_delay : %u", sei_buf_period.initial_cpb_removal_delay[idx]); 852 ALOGV("-->initial_cpb_removal_delay_offset : %u", sei_buf_period.initial_cpb_removal_delay_offset[idx]); 853 } 854 } 855 if (vui_param.vcl_hrd_parameters_present_flag) 856 { 857 hrd_param = &vui_param.vcl_hrd_parameters; 858 if (hrd_param->cpb_cnt > MAX_CPB_COUNT) 859 { 860 ALOGV("ERROR: Invalid hrd_param->cpb_cnt [%u]!", hrd_param->cpb_cnt); 861 return; 862 } 863 for (idx = 0; idx < hrd_param->cpb_cnt ; idx++) 864 { 865 sei_buf_period.is_valid = true; 866 sei_buf_period.initial_cpb_removal_delay[idx] = extract_bits(hrd_param->initial_cpb_removal_delay_length); 867 sei_buf_period.initial_cpb_removal_delay_offset[idx] = extract_bits(hrd_param->initial_cpb_removal_delay_length); 868 ALOGV("-->initial_cpb_removal_delay : %u", sei_buf_period.initial_cpb_removal_delay[idx]); 869 ALOGV("-->initial_cpb_removal_delay_offset : %u", sei_buf_period.initial_cpb_removal_delay_offset[idx]); 870 } 871 } 872 sei_buf_period.au_cntr = 0; 873 ALOGV("@@sei_buffering_period: OUT"); 874} 875 876void h264_stream_parser::sei_picture_timing() 877{ 878 ALOGV("@@sei_picture_timing: IN"); 879 OMX_U32 time_offset_len = 0, cpb_removal_len = 24, dpb_output_len = 24; 880 OMX_U8 cbr_flag = 0; 881 sei_pic_timing.is_valid = true; 882 if (vui_param.nal_hrd_parameters_present_flag) 883 { 884 cpb_removal_len = vui_param.nal_hrd_parameters.cpb_removal_delay_length; 885 dpb_output_len = vui_param.nal_hrd_parameters.dpb_output_delay_length; 886 time_offset_len = vui_param.nal_hrd_parameters.time_offset_length; 887 cbr_flag = vui_param.nal_hrd_parameters.cbr_flag[0]; 888 } 889 else if (vui_param.vcl_hrd_parameters_present_flag) 890 { 891 cpb_removal_len = vui_param.vcl_hrd_parameters.cpb_removal_delay_length; 892 dpb_output_len = vui_param.vcl_hrd_parameters.dpb_output_delay_length; 893 time_offset_len = vui_param.vcl_hrd_parameters.time_offset_length; 894 cbr_flag = vui_param.vcl_hrd_parameters.cbr_flag[0]; 895 } 896 sei_pic_timing.cpb_removal_delay = extract_bits(cpb_removal_len); 897 sei_pic_timing.dpb_output_delay = extract_bits(dpb_output_len); 898 ALOGV("-->cpb_removal_len : %u", cpb_removal_len); 899 ALOGV("-->dpb_output_len : %u", dpb_output_len); 900 ALOGV("-->cpb_removal_delay : %u", sei_pic_timing.cpb_removal_delay); 901 ALOGV("-->dpb_output_delay : %u", sei_pic_timing.dpb_output_delay); 902 if (vui_param.pic_struct_present_flag) 903 { 904 sei_pic_timing.pic_struct = extract_bits(4); 905 sei_pic_timing.num_clock_ts = 0; 906 switch (sei_pic_timing.pic_struct) 907 { 908 case 0: case 1: case 2: sei_pic_timing.num_clock_ts = 1; break; 909 case 3: case 4: case 7: sei_pic_timing.num_clock_ts = 2; break; 910 case 5: case 6: case 8: sei_pic_timing.num_clock_ts = 3; break; 911 default: 912 ALOGE("sei_picture_timing: pic_struct invalid!"); 913 } 914 ALOGV("-->num_clock_ts : %u", sei_pic_timing.num_clock_ts); 915 for (int i = 0; i < sei_pic_timing.num_clock_ts && more_bits(); i++) 916 { 917 sei_pic_timing.clock_ts_flag = extract_bits(1); 918 if(sei_pic_timing.clock_ts_flag) 919 { 920 ALOGV("-->clock_timestamp present!"); 921 sei_pic_timing.ct_type = extract_bits(2); 922 sei_pic_timing.nuit_field_based_flag = extract_bits(1); 923 sei_pic_timing.counting_type = extract_bits(5); 924 sei_pic_timing.full_timestamp_flag = extract_bits(1); 925 sei_pic_timing.discontinuity_flag = extract_bits(1); 926 sei_pic_timing.cnt_dropped_flag = extract_bits(1); 927 sei_pic_timing.n_frames = extract_bits(8); 928 ALOGV("-->f_timestamp_flg : %u", sei_pic_timing.full_timestamp_flag); 929 ALOGV("-->n_frames : %u", sei_pic_timing.n_frames); 930 sei_pic_timing.seconds_value = 0; 931 sei_pic_timing.minutes_value = 0; 932 sei_pic_timing.hours_value = 0; 933 if (sei_pic_timing.full_timestamp_flag) 934 { 935 sei_pic_timing.seconds_value = extract_bits(6); 936 sei_pic_timing.minutes_value = extract_bits(6); 937 sei_pic_timing.hours_value = extract_bits(5); 938 } 939 else if (extract_bits(1)) 940 { 941 ALOGV("-->seconds_flag enabled!"); 942 sei_pic_timing.seconds_value = extract_bits(6); 943 if (extract_bits(1)) 944 { 945 ALOGV("-->minutes_flag enabled!"); 946 sei_pic_timing.minutes_value = extract_bits(6); 947 if (extract_bits(1)) 948 { 949 ALOGV("-->hours_flag enabled!"); 950 sei_pic_timing.hours_value = extract_bits(5); 951 } 952 } 953 } 954 sei_pic_timing.time_offset = 0; 955 if (time_offset_len > 0) 956 sei_pic_timing.time_offset = iv(time_offset_len); 957 ALOGV("-->seconds_value : %u", sei_pic_timing.seconds_value); 958 ALOGV("-->minutes_value : %u", sei_pic_timing.minutes_value); 959 ALOGV("-->hours_value : %u", sei_pic_timing.hours_value); 960 ALOGV("-->time_offset : %d", sei_pic_timing.time_offset); 961 } 962 } 963 } 964 ALOGV("@@sei_picture_timing: OUT"); 965} 966 967void h264_stream_parser::sei_pan_scan() 968{ 969#ifdef _ANDROID_ 970 char property_value[PROPERTY_VALUE_MAX] = {0}; 971 OMX_S32 enable_panscan_log = 0; 972 property_get("vidc.dec.debug.panframedata", property_value, "0"); 973 enable_panscan_log = atoi(property_value); 974#endif 975#ifdef PANSCAN_HDLR 976 h264_pan_scan *pan_scan_param = panscan_hdl->get_free(); 977#else 978 h264_pan_scan *pan_scan_param = &panscan_param; 979#endif 980 981 if (!pan_scan_param) 982 { 983 ALOGE("sei_pan_scan: ERROR: Invalid pointer!"); 984 return; 985 } 986 987 pan_scan_param->rect_id = uev(); 988 if (pan_scan_param->rect_id > 0xFF) 989 { 990 ALOGE("sei_pan_scan: ERROR: Invalid rect_id[%u]!", pan_scan_param->rect_id); 991 pan_scan_param->rect_id = NO_PAN_SCAN_BIT; 992 return; 993 } 994 995 pan_scan_param->rect_cancel_flag = extract_bits(1); 996 997 if (pan_scan_param->rect_cancel_flag) 998 pan_scan_param->rect_id = NO_PAN_SCAN_BIT; 999 else 1000 { 1001 pan_scan_param->cnt = uev() + 1; 1002 if (pan_scan_param->cnt > MAX_PAN_SCAN_RECT) 1003 { 1004 ALOGE("sei_pan_scan: ERROR: Invalid num of rect [%u]!", pan_scan_param->cnt); 1005 pan_scan_param->rect_id = NO_PAN_SCAN_BIT; 1006 return; 1007 } 1008 1009 for (int i = 0; i < pan_scan_param->cnt; i++) 1010 { 1011 pan_scan_param->rect_left_offset[i] = sev(); 1012 pan_scan_param->rect_right_offset[i] = sev(); 1013 pan_scan_param->rect_top_offset[i] = sev(); 1014 pan_scan_param->rect_bottom_offset[i] = sev(); 1015 1016 } 1017 pan_scan_param->rect_repetition_period = uev(); 1018#ifdef PANSCAN_HDLR 1019 if (pan_scan_param->rect_repetition_period > 1) 1020 // Repetition period is decreased by 2 each time panscan data is used 1021 pan_scan_param->rect_repetition_period *= 2; 1022#endif 1023#ifdef _ANDROID_ 1024 if (enable_panscan_log) 1025 { 1026 print_pan_data(pan_scan_param); 1027 } 1028#endif 1029 } 1030} 1031 1032void h264_stream_parser::print_pan_data(h264_pan_scan *pan_scan_param) 1033{ 1034 ALOGV("@@print_pan_data: IN"); 1035 1036 ALOGV("-->rect_id : %u", pan_scan_param->rect_id); 1037 ALOGV("-->rect_cancel_flag : %u", pan_scan_param->rect_cancel_flag); 1038 1039 ALOGV("-->cnt : %u", pan_scan_param->cnt); 1040 1041 for (int i = 0; i < pan_scan_param->cnt; i++) 1042 { 1043 ALOGV("-->rect_left_offset : %d", pan_scan_param->rect_left_offset[i]); 1044 ALOGV("-->rect_right_offset : %d", pan_scan_param->rect_right_offset[i]); 1045 ALOGV("-->rect_top_offset : %d", pan_scan_param->rect_top_offset[i]); 1046 ALOGV("-->rect_bottom_offset : %d", pan_scan_param->rect_bottom_offset[i]); 1047 } 1048 ALOGV("-->repetition_period : %u", pan_scan_param->rect_repetition_period); 1049 1050 ALOGV("@@print_pan_data: OUT"); 1051} 1052 1053void h264_stream_parser::parse_sps() 1054{ 1055 OMX_U32 value = 0, scaling_matrix_limit; 1056 ALOGV("@@parse_sps: IN"); 1057 value = extract_bits(8); //profile_idc 1058 extract_bits(8); //constraint flags and reserved bits 1059 extract_bits(8); //level_idc 1060 uev(); //sps id 1061 if (value == 100 || value == 110 || value == 122 || value == 244 || 1062 value == 44 || value == 83 || value == 86 || value == 118) 1063 { 1064 if (uev() == 3) //chroma_format_idc 1065 { 1066 extract_bits(1); //separate_colour_plane_flag 1067 scaling_matrix_limit = 12; 1068 } 1069 else 1070 scaling_matrix_limit = 12; 1071 uev(); //bit_depth_luma_minus8 1072 uev(); //bit_depth_chroma_minus8 1073 extract_bits(1); //qpprime_y_zero_transform_bypass_flag 1074 if (extract_bits(1)) //seq_scaling_matrix_present_flag 1075 for (int i = 0; i < scaling_matrix_limit && more_bits(); i++) 1076 { 1077 if (extract_bits(1)) ////seq_scaling_list_present_flag[ i ] 1078 if (i < 6) 1079 scaling_list(16); 1080 else 1081 scaling_list(64); 1082 } 1083 } 1084 uev(); //log2_max_frame_num_minus4 1085 value = uev(); //pic_order_cnt_type 1086 if (value == 0) 1087 uev(); //log2_max_pic_order_cnt_lsb_minus4 1088 else if (value == 1) 1089 { 1090 extract_bits(1); //delta_pic_order_always_zero_flag 1091 sev(); //offset_for_non_ref_pic 1092 sev(); //offset_for_top_to_bottom_field 1093 value = uev(); // num_ref_frames_in_pic_order_cnt_cycle 1094 for (int i = 0; i < value; i++) 1095 sev(); //offset_for_ref_frame[ i ] 1096 } 1097 uev(); //max_num_ref_frames 1098 extract_bits(1); //gaps_in_frame_num_value_allowed_flag 1099 value = uev(); //pic_width_in_mbs_minus1 1100 value = uev(); //pic_height_in_map_units_minus1 1101 if (!extract_bits(1)) //frame_mbs_only_flag 1102 mbaff_flag = extract_bits(1); //mb_adaptive_frame_field_flag 1103 extract_bits(1); //direct_8x8_inference_flag 1104 if (extract_bits(1)) //frame_cropping_flag 1105 { 1106 uev(); //frame_crop_left_offset 1107 uev(); //frame_crop_right_offset 1108 uev(); //frame_crop_top_offset 1109 uev(); //frame_crop_bottom_offset 1110 } 1111 if (extract_bits(1)) //vui_parameters_present_flag 1112 parse_vui(false); 1113 ALOGV("@@parse_sps: OUT"); 1114} 1115 1116void h264_stream_parser::scaling_list(OMX_U32 size_of_scaling_list) 1117{ 1118 OMX_S32 last_scale = 8, next_scale = 8, delta_scale; 1119 for (int j = 0; j < size_of_scaling_list; j++) 1120 { 1121 if (next_scale != 0) 1122 { 1123 delta_scale = sev(); 1124 next_scale = (last_scale + delta_scale + 256) % 256; 1125 } 1126 last_scale = (next_scale == 0)? last_scale : next_scale; 1127 } 1128} 1129 1130OMX_U32 h264_stream_parser::extract_bits(OMX_U32 n) 1131{ 1132 OMX_U32 value = 0; 1133 if (n > 32) 1134 { 1135 ALOGE("ERROR: extract_bits limit to 32 bits!"); 1136 return value; 1137 } 1138 value = curr_32_bit >> (32 - n); 1139 if (bits_read < n) 1140 { 1141 n -= bits_read; 1142 read_word(); 1143 value |= (curr_32_bit >> (32 - n)); 1144 if (bits_read < n) 1145 { 1146 ALOGV("ERROR: extract_bits underflow!"); 1147 value >>= (n - bits_read); 1148 n = bits_read; 1149 } 1150 } 1151 bits_read -= n; 1152 curr_32_bit <<= n; 1153 return value; 1154} 1155 1156void h264_stream_parser::read_word() 1157{ 1158 curr_32_bit = 0; 1159 bits_read = 0; 1160 while (bitstream_bytes && bits_read < 32) 1161 { 1162 if (*bitstream == EMULATION_PREVENTION_THREE_BYTE && 1163 zero_cntr >= 2 && emulation_sc_enabled) 1164 { 1165 ALOGV("EMULATION_PREVENTION_THREE_BYTE: Skip 0x03 byte aligned!"); 1166 emulation_code_skip_cntr++; 1167 } 1168 else 1169 { 1170 curr_32_bit <<= 8; 1171 curr_32_bit |= *bitstream; 1172 bits_read += 8; 1173 } 1174 if (*bitstream == 0) 1175 zero_cntr++; 1176 else 1177 zero_cntr = 0; 1178 bitstream++; 1179 bitstream_bytes--; 1180 } 1181 curr_32_bit <<= (32 - bits_read); 1182} 1183 1184OMX_U32 h264_stream_parser::uev() 1185{ 1186 OMX_U32 lead_zero_bits = 0, code_num = 0; 1187 while(!extract_bits(1) && more_bits()) 1188 lead_zero_bits++; 1189 code_num = lead_zero_bits == 0 ? 0 : 1190 (1 << lead_zero_bits) - 1 + extract_bits(lead_zero_bits); 1191 return code_num; 1192} 1193 1194bool h264_stream_parser::more_bits() 1195{ 1196 return (bitstream_bytes > 0 || bits_read > 0); 1197} 1198 1199OMX_S32 h264_stream_parser::sev() 1200{ 1201 OMX_U32 code_num = uev(); 1202 OMX_S32 ret; 1203 ret = (code_num + 1) >> 1; 1204 return ((code_num & 1) ? ret : -ret); 1205} 1206 1207OMX_S32 h264_stream_parser::iv(OMX_U32 n_bits) 1208{ 1209 OMX_U32 code_num = extract_bits(n_bits); 1210 OMX_S32 ret = (code_num >> (n_bits - 1))? (-1)*(~(code_num & ~(0x1 << (n_bits - 1))) + 1) : code_num; 1211 return ret; 1212} 1213 1214OMX_U32 h264_stream_parser::get_nal_unit_type(OMX_U32 *nal_unit_type) 1215{ 1216 OMX_U32 value = 0, consumed_bytes = 3; 1217 *nal_unit_type = NALU_TYPE_UNSPECIFIED; 1218 ALOGV("-->get_nal_unit_type: IN"); 1219 value = extract_bits(24); 1220 while (value != 0x00000001 && more_bits()) 1221 { 1222 value <<= 8; 1223 value |= extract_bits(8); 1224 consumed_bytes++; 1225 } 1226 if (value != 0x00000001) 1227 { 1228 ALOGE("ERROR in get_nal_unit_type: Start code not found!"); 1229 } 1230 else 1231 { 1232 if (extract_bits(1)) // forbidden_zero_bit 1233 { 1234 ALOGE("WARNING: forbidden_zero_bit should be zero!"); 1235 } 1236 value = extract_bits(2); 1237 ALOGV("-->nal_ref_idc : %x", value); 1238 *nal_unit_type = extract_bits(5); 1239 ALOGV("-->nal_unit_type : %x", *nal_unit_type); 1240 consumed_bytes++; 1241 if (consumed_bytes > 5) 1242 { 1243 ALOGE("-->WARNING: Startcode was found after the first 4 bytes!"); 1244 } 1245 } 1246 ALOGV("-->get_nal_unit_type: OUT"); 1247 return consumed_bytes; 1248} 1249 1250OMX_S64 h264_stream_parser::calculate_buf_period_ts(OMX_S64 timestamp) 1251{ 1252 OMX_S64 clock_ts = timestamp; 1253 ALOGV("calculate_ts(): IN"); 1254 if (sei_buf_period.au_cntr == 0) 1255 clock_ts = sei_buf_period.reference_ts = timestamp; 1256 else if (sei_pic_timing.is_valid && VALID_TS(sei_buf_period.reference_ts)) 1257 { 1258 clock_ts = sei_buf_period.reference_ts + sei_pic_timing.cpb_removal_delay * 1259 1e6 * vui_param.num_units_in_tick / vui_param.time_scale; 1260 } 1261 sei_buf_period.au_cntr++; 1262 ALOGV("calculate_ts(): OUT"); 1263 return clock_ts; 1264} 1265 1266OMX_S64 h264_stream_parser::calculate_fixed_fps_ts(OMX_S64 timestamp, OMX_U32 DeltaTfiDivisor) 1267{ 1268 if (VALID_TS(timestamp)) 1269 vui_param.fixed_fps_prev_ts = timestamp; 1270 else if (VALID_TS(vui_param.fixed_fps_prev_ts)) 1271 vui_param.fixed_fps_prev_ts += DeltaTfiDivisor * 1e6 * 1272 vui_param.num_units_in_tick / vui_param.time_scale; 1273 return vui_param.fixed_fps_prev_ts; 1274} 1275 1276void h264_stream_parser::parse_frame_pack() 1277{ 1278#ifdef _ANDROID_ 1279 char property_value[PROPERTY_VALUE_MAX] = {0}; 1280 OMX_S32 enable_framepack_log = 0; 1281 1282 property_get("vidc.dec.debug.panframedata", property_value, "0"); 1283 enable_framepack_log = atoi(property_value); 1284#endif 1285 ALOGV("\n%s:%d parse_frame_pack", __func__, __LINE__); 1286 1287 frame_packing_arrangement.id = uev(); 1288 1289 frame_packing_arrangement.cancel_flag = extract_bits(1); 1290 if(!frame_packing_arrangement.cancel_flag) { 1291 frame_packing_arrangement.type = extract_bits(7); 1292 frame_packing_arrangement.quincunx_sampling_flag = extract_bits(1); 1293 frame_packing_arrangement.content_interpretation_type = extract_bits(6); 1294 frame_packing_arrangement.spatial_flipping_flag = extract_bits(1); 1295 frame_packing_arrangement.frame0_flipped_flag = extract_bits(1); 1296 frame_packing_arrangement.field_views_flag = extract_bits(1); 1297 frame_packing_arrangement.current_frame_is_frame0_flag = extract_bits(1); 1298 frame_packing_arrangement.frame0_self_contained_flag = extract_bits(1); 1299 frame_packing_arrangement.frame1_self_contained_flag = extract_bits(1); 1300 1301 if(!frame_packing_arrangement.quincunx_sampling_flag && 1302 frame_packing_arrangement.type != 5) { 1303 frame_packing_arrangement.frame0_grid_position_x = extract_bits(4); 1304 frame_packing_arrangement.frame0_grid_position_y = extract_bits(4); 1305 frame_packing_arrangement.frame1_grid_position_x = extract_bits(4); 1306 frame_packing_arrangement.frame1_grid_position_y = extract_bits(4); 1307 } 1308 frame_packing_arrangement.reserved_byte = extract_bits(8); 1309 frame_packing_arrangement.repetition_period = uev(); 1310 } 1311 frame_packing_arrangement.extension_flag = extract_bits(1); 1312 1313#ifdef _ANDROID_ 1314 if (enable_framepack_log) 1315 { 1316 print_frame_pack(); 1317 } 1318#endif 1319} 1320 1321void h264_stream_parser::print_frame_pack() 1322{ 1323 ALOGV("\n ## frame_packing_arrangement.id = %u", frame_packing_arrangement.id); 1324 ALOGV("\n ## frame_packing_arrangement.cancel_flag = %u", 1325 frame_packing_arrangement.cancel_flag); 1326 if(!frame_packing_arrangement.cancel_flag) 1327 { 1328 ALOGV("\n ## frame_packing_arrangement.type = %u", 1329 frame_packing_arrangement.type); 1330 ALOGV("\n ## frame_packing_arrangement.quincunx_sampling_flag = %u", 1331 frame_packing_arrangement.quincunx_sampling_flag); 1332 ALOGV("\n ## frame_packing_arrangement.content_interpretation_type = %u", 1333 frame_packing_arrangement.content_interpretation_type); 1334 ALOGV("\n ## frame_packing_arrangement.spatial_flipping_flag = %u", 1335 frame_packing_arrangement.spatial_flipping_flag); 1336 ALOGV("\n ## frame_packing_arrangement.frame0_flipped_flag = %u", 1337 frame_packing_arrangement.frame0_flipped_flag); 1338 ALOGV("\n ## frame_packing_arrangement.field_views_flag = %u", 1339 frame_packing_arrangement.field_views_flag); 1340 ALOGV("\n ## frame_packing_arrangement.current_frame_is_frame0_flag = %u", 1341 frame_packing_arrangement.current_frame_is_frame0_flag); 1342 ALOGV("\n ## frame_packing_arrangement.frame0_self_contained_flag = %u", 1343 frame_packing_arrangement.frame0_self_contained_flag); 1344 ALOGV("\n ## frame_packing_arrangement.frame1_self_contained_flag = %u", 1345 frame_packing_arrangement.frame1_self_contained_flag); 1346 ALOGV("\n ## frame_packing_arrangement.reserved_byte = %u", 1347 frame_packing_arrangement.reserved_byte); 1348 ALOGV("\n ## frame_packing_arrangement.repetition_period = %u", 1349 frame_packing_arrangement.repetition_period); 1350 ALOGV("\n ## frame_packing_arrangement.extension_flag = %u", 1351 frame_packing_arrangement.extension_flag); 1352 } 1353} 1354/* API'S EXPOSED TO OMX COMPONENT */ 1355 1356void h264_stream_parser::get_frame_pack_data( 1357 OMX_QCOM_FRAME_PACK_ARRANGEMENT *frame_pack) 1358{ 1359 ALOGV("\n%s:%d get frame data", __func__, __LINE__); 1360 memcpy(&frame_pack->id,&frame_packing_arrangement.id, 1361 FRAME_PACK_SIZE*sizeof(OMX_U32)); 1362 return; 1363} 1364 1365 1366bool h264_stream_parser::is_mbaff() 1367{ 1368 ALOGV("\n%s:%d MBAFF flag=%d", __func__, __LINE__,mbaff_flag); 1369 return mbaff_flag; 1370} 1371 1372void h264_stream_parser::get_frame_rate(OMX_U32 *frame_rate) 1373{ 1374 if (vui_param.num_units_in_tick != 0) 1375 *frame_rate = vui_param.time_scale / (2 * vui_param.num_units_in_tick); 1376} 1377 1378void h264_stream_parser::parse_nal(OMX_U8* data_ptr, OMX_U32 data_len, OMX_U32 nal_type, bool enable_emu_sc) 1379{ 1380 OMX_U32 nal_unit_type = NALU_TYPE_UNSPECIFIED, cons_bytes = 0; 1381 ALOGV("parse_nal(): IN nal_type(%lu)", nal_type); 1382 if (!data_len) 1383 return; 1384 init_bitstream(data_ptr, data_len); 1385 emulation_sc_enabled = enable_emu_sc; 1386 if (nal_type != NALU_TYPE_VUI) 1387 { 1388 cons_bytes = get_nal_unit_type(&nal_unit_type); 1389 if (nal_type != nal_unit_type && nal_type != NALU_TYPE_UNSPECIFIED) 1390 { 1391 ALOGV("Unexpected nal_type(%x) expected(%x)", nal_unit_type, nal_type); 1392 return; 1393 } 1394 } 1395 switch (nal_type) 1396 { 1397 case NALU_TYPE_SPS: 1398 if (more_bits()) 1399 parse_sps(); 1400#ifdef PANSCAN_HDLR 1401 panscan_hdl->get_free(); 1402#endif 1403 break; 1404 case NALU_TYPE_SEI: 1405 init_bitstream(data_ptr + cons_bytes, data_len - cons_bytes); 1406 parse_sei(); 1407 break; 1408 case NALU_TYPE_VUI: 1409 parse_vui(true); 1410 break; 1411 default: 1412 ALOGV("nal_unit_type received : %lu", nal_type); 1413 } 1414 ALOGV("parse_nal(): OUT"); 1415} 1416 1417#ifdef PANSCAN_HDLR 1418void h264_stream_parser::update_panscan_data(OMX_S64 timestamp) 1419{ 1420 panscan_hdl->update_last(timestamp); 1421} 1422#endif 1423 1424void h264_stream_parser::fill_aspect_ratio_info(OMX_QCOM_ASPECT_RATIO *dest_aspect_ratio) 1425{ 1426 if(dest_aspect_ratio && vui_param.aspect_ratio_info_present_flag) 1427 { 1428 dest_aspect_ratio->aspectRatioX = vui_param.aspect_ratio_info.aspect_ratio_x; 1429 dest_aspect_ratio->aspectRatioY = vui_param.aspect_ratio_info.aspect_ratio_y; 1430 } 1431} 1432 1433void h264_stream_parser::fill_pan_scan_data(OMX_QCOM_PANSCAN *dest_pan_scan, OMX_S64 timestamp) 1434{ 1435#ifdef PANSCAN_HDLR 1436 h264_pan_scan *pan_scan_param = panscan_hdl->get_populated(timestamp); 1437#else 1438 h264_pan_scan *pan_scan_param = &panscan_param; 1439#endif 1440 if (pan_scan_param) 1441 if (!(pan_scan_param->rect_id & NO_PAN_SCAN_BIT)) 1442 { 1443 PRINT_PANSCAN_PARAM(*pan_scan_param); 1444 dest_pan_scan->numWindows = pan_scan_param->cnt; 1445 for (int i = 0; i < dest_pan_scan->numWindows; i++) 1446 { 1447 dest_pan_scan->window[i].x = pan_scan_param->rect_left_offset[i]; 1448 dest_pan_scan->window[i].y = pan_scan_param->rect_top_offset[i]; 1449 dest_pan_scan->window[i].dx = pan_scan_param->rect_right_offset[i]; 1450 dest_pan_scan->window[i].dy = pan_scan_param->rect_bottom_offset[i]; 1451 } 1452#ifndef PANSCAN_HDLR 1453 if (pan_scan_param->rect_repetition_period == 0) 1454 pan_scan_param->rect_id = NO_PAN_SCAN_BIT; 1455 else if (pan_scan_param->rect_repetition_period > 1) 1456 pan_scan_param->rect_repetition_period = 1457 (pan_scan_param->rect_repetition_period == 2)? 0 : 1458 (pan_scan_param->rect_repetition_period - 1); 1459#endif 1460 } 1461 else 1462 pan_scan_param->rect_repetition_period = 0; 1463} 1464 1465OMX_S64 h264_stream_parser::process_ts_with_sei_vui(OMX_S64 timestamp) 1466{ 1467 bool clock_ts_flag = false; 1468 OMX_S64 clock_ts = timestamp; 1469 OMX_U32 deltaTfiDivisor = 2; 1470 if (vui_param.timing_info_present_flag) 1471 { 1472 if (vui_param.pic_struct_present_flag) 1473 { 1474 if(sei_pic_timing.clock_ts_flag) 1475 { 1476 clock_ts = ((sei_pic_timing.hours_value * 60 + sei_pic_timing.minutes_value) * 60 + sei_pic_timing.seconds_value) * 1e6 + 1477 (sei_pic_timing.n_frames * (vui_param.num_units_in_tick * (1 + sei_pic_timing.nuit_field_based_flag)) + sei_pic_timing.time_offset) * 1478 1e6 / vui_param.time_scale; 1479 ALOGV("-->CLOCK TIMESTAMP : %lld", clock_ts); 1480 clock_ts_flag = true; 1481 } 1482 if (vui_param.fixed_frame_rate_flag) 1483 { 1484 switch (sei_pic_timing.pic_struct) 1485 { 1486 case 1: case 2: deltaTfiDivisor = 1; break; 1487 case 0: case 3: case 4: deltaTfiDivisor = 2; break; 1488 case 5: case 6: deltaTfiDivisor = 3; break; 1489 case 7: deltaTfiDivisor = 4; break; 1490 case 8: deltaTfiDivisor = 6; break; 1491 default: 1492 ALOGE("process_ts_with_sei_vui: pic_struct invalid!"); 1493 } 1494 } 1495 } 1496 if (!clock_ts_flag) 1497 { 1498 if (vui_param.fixed_frame_rate_flag) 1499 clock_ts = calculate_fixed_fps_ts(timestamp, deltaTfiDivisor); 1500 else if (sei_buf_period.is_valid) 1501 clock_ts = calculate_buf_period_ts(timestamp); 1502 } 1503 } 1504 else 1505 { 1506 ALOGV("NO TIMING information present in VUI!"); 1507 } 1508 sei_pic_timing.is_valid = false; // SEI data is valid only for current frame 1509 return clock_ts; 1510} 1511 1512#ifdef PANSCAN_HDLR 1513 1514panscan_handler::panscan_handler() : panscan_data(NULL) {} 1515 1516panscan_handler::~panscan_handler() 1517{ 1518 if (panscan_data) 1519 { 1520 free(panscan_data); 1521 panscan_data = NULL; 1522 } 1523} 1524 1525bool panscan_handler::initialize(int num_data) 1526{ 1527 bool ret = false; 1528 if (!panscan_data) 1529 { 1530 panscan_data = (PANSCAN_NODE *) malloc (sizeof(PANSCAN_NODE) * num_data); 1531 if (panscan_data) 1532 { 1533 panscan_free.add_multiple(panscan_data, num_data); 1534 ret = true; 1535 } 1536 } 1537 else 1538 { 1539 ALOGE("ERROR: Old panscan memory must be freed to allocate new"); 1540 } 1541 return ret; 1542} 1543 1544h264_pan_scan *panscan_handler::get_free() 1545{ 1546 h264_pan_scan *data = NULL; 1547 PANSCAN_NODE *panscan_node = panscan_used.watch_last(); 1548 panscan_node = (!panscan_node || VALID_TS(panscan_node->start_ts))? 1549 panscan_free.remove_first() : 1550 panscan_used.remove_last(); 1551 if (panscan_node) 1552 { 1553 panscan_node->start_ts = LLONG_MAX; 1554 panscan_node->end_ts = LLONG_MAX; 1555 panscan_node->pan_scan_param.rect_id = NO_PAN_SCAN_BIT; 1556 panscan_node->active = false; 1557 panscan_used.add_last(panscan_node); 1558 data = &panscan_node->pan_scan_param; 1559 } 1560 return data; 1561} 1562 1563h264_pan_scan *panscan_handler::get_populated(OMX_S64 frame_ts) 1564{ 1565 h264_pan_scan *data = NULL; 1566 PANSCAN_NODE *panscan_node = panscan_used.watch_first(); 1567 while (panscan_node && !data) 1568 { 1569 if (VALID_TS(panscan_node->start_ts)) 1570 { 1571 if (panscan_node->active && frame_ts < panscan_node->start_ts) 1572 panscan_node->start_ts = frame_ts; 1573 if (frame_ts >= panscan_node->start_ts) 1574 if (frame_ts < panscan_node->end_ts) 1575 { 1576 data = &panscan_node->pan_scan_param; 1577 panscan_node->active = true; 1578 } 1579 else 1580 { 1581 panscan_free.add_last(panscan_used.remove_first()); 1582 panscan_node = panscan_used.watch_first(); 1583 } 1584 else 1585 // Finish search if current timestamp has not reached 1586 // start timestamp of first panscan data. 1587 panscan_node = NULL; 1588 } 1589 else 1590 { 1591 // Only one panscan data is stored for clips 1592 // with invalid timestamps in every frame 1593 data = &panscan_node->pan_scan_param; 1594 panscan_node->active = true; 1595 } 1596 } 1597 if (data) 1598 if (data->rect_repetition_period == 0) 1599 panscan_free.add_last(panscan_used.remove_first()); 1600 else if (data->rect_repetition_period > 1) 1601 data->rect_repetition_period -= 2; 1602 PRINT_PANSCAN_DATA(panscan_node); 1603 return data; 1604} 1605 1606void panscan_handler::update_last(OMX_S64 frame_ts) 1607{ 1608 PANSCAN_NODE *panscan_node = panscan_used.watch_last(); 1609 if (panscan_node && !VALID_TS(panscan_node->start_ts)) 1610 { 1611 panscan_node->start_ts = frame_ts; 1612 PRINT_PANSCAN_DATA(panscan_node); 1613 if (panscan_node->prev) 1614 { 1615 if (frame_ts < panscan_node->prev->end_ts) 1616 panscan_node->prev->end_ts = frame_ts; 1617 else if (!VALID_TS(frame_ts)) 1618 panscan_node->prev->pan_scan_param.rect_repetition_period = 0; 1619 PRINT_PANSCAN_DATA(panscan_node->prev); 1620 } 1621 } 1622} 1623 1624template <class NODE_STRUCT> 1625void omx_dl_list<NODE_STRUCT>::add_multiple(NODE_STRUCT *data_arr, int data_num) 1626{ 1627 for (int idx = 0; idx < data_num; idx++) 1628 add_last(&data_arr[idx]); 1629} 1630 1631template <class NODE_STRUCT> 1632NODE_STRUCT *omx_dl_list<NODE_STRUCT>::remove_first() 1633{ 1634 NODE_STRUCT *data = head; 1635 if (head) 1636 { 1637 if (head->next) 1638 { 1639 head = head->next; 1640 head->prev = NULL; 1641 } 1642 else 1643 head = tail = NULL; 1644 data->next = data->prev = NULL; 1645 } 1646 return data; 1647} 1648 1649template <class NODE_STRUCT> 1650NODE_STRUCT *omx_dl_list<NODE_STRUCT>::remove_last() 1651{ 1652 NODE_STRUCT *data = tail; 1653 if (tail) 1654 { 1655 if (tail->prev) 1656 { 1657 tail = tail->prev; 1658 tail->next = NULL; 1659 } 1660 else 1661 head = tail = NULL; 1662 data->next = data->prev = NULL; 1663 } 1664 return data; 1665} 1666 1667template <class NODE_STRUCT> 1668void omx_dl_list<NODE_STRUCT>::add_last(NODE_STRUCT* data_ptr) 1669{ 1670 if (data_ptr) 1671 { 1672 data_ptr->next = NULL; 1673 data_ptr->prev = tail; 1674 if (tail) 1675 { 1676 tail->next = data_ptr; 1677 tail = data_ptr; 1678 } 1679 else 1680 head = tail = data_ptr; 1681 } 1682} 1683 1684template <class NODE_STRUCT> 1685NODE_STRUCT* omx_dl_list<NODE_STRUCT>::watch_first() 1686{ 1687 return head; 1688} 1689 1690template <class NODE_STRUCT> 1691NODE_STRUCT* omx_dl_list<NODE_STRUCT>::watch_last() 1692{ 1693 return tail; 1694} 1695 1696#endif 1697