Hamsalekha S | 8d3d303 | 2015-03-13 21:24:58 +0530 | [diff] [blame] | 1 | /****************************************************************************** |
| 2 | * |
| 3 | * Copyright (C) 2015 The Android Open Source Project |
| 4 | * |
| 5 | * Licensed under the Apache License, Version 2.0 (the "License"); |
| 6 | * you may not use this file except in compliance with the License. |
| 7 | * You may obtain a copy of the License at: |
| 8 | * |
| 9 | * http://www.apache.org/licenses/LICENSE-2.0 |
| 10 | * |
| 11 | * Unless required by applicable law or agreed to in writing, software |
| 12 | * distributed under the License is distributed on an "AS IS" BASIS, |
| 13 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
| 14 | * See the License for the specific language governing permissions and |
| 15 | * limitations under the License. |
| 16 | * |
| 17 | ***************************************************************************** |
| 18 | * Originally developed and contributed by Ittiam Systems Pvt. Ltd, Bangalore |
| 19 | */ |
| 20 | /*! |
| 21 | ************************************************************************** |
| 22 | * \file ih264d_nal.c |
| 23 | * |
| 24 | * \brief NAL parsing routines |
| 25 | * |
| 26 | * Detailed_description |
| 27 | * |
| 28 | * \author |
| 29 | * - AI 19 11 2002 Creation |
| 30 | ************************************************************************** |
| 31 | */ |
| 32 | #include "ih264d_bitstrm.h" |
| 33 | #include "ih264d_defs.h" |
| 34 | #include "ih264_typedefs.h" |
| 35 | #include "ih264_macros.h" |
| 36 | #include "ih264_platform_macros.h" |
| 37 | #include "ih264d_defs.h" |
| 38 | #define NUM_OF_ZERO_BYTES_BEFORE_START_CODE 2 |
| 39 | #define EMULATION_PREVENTION_BYTE 0x03 |
| 40 | |
| 41 | #define NAL_FIRST_BYTE_SIZE 1 |
| 42 | |
| 43 | /*! |
| 44 | ************************************************************************** |
| 45 | * \if Function name : ih264d_find_start_code \endif |
| 46 | * |
| 47 | * \brief |
| 48 | * This function searches for the Start Code Prefix. |
| 49 | * |
| 50 | * \param pu1_buf : Pointer to char buffer which contains bitstream. |
| 51 | * \param u4_cur_pos : Current position in the buffer. |
| 52 | * \param u4_max_ofst : Number of bytes in Buffer. |
| 53 | * \param pu4_length_of_start_code : Poiter to length of Start Code. |
| 54 | * |
| 55 | * \return |
| 56 | * Returns 0 on success and -1 on error. |
| 57 | * |
| 58 | ************************************************************************** |
| 59 | */ |
| 60 | #define START_CODE_NOT_FOUND -1 |
| 61 | #define END_OF_STREAM_BUFFER -2 |
| 62 | #define END_OF_STREAM -1 |
| 63 | |
| 64 | void ih264d_check_if_aud(UWORD8 *pu1_buf, |
| 65 | UWORD32 u4_cur_pos, |
| 66 | UWORD32 u4_max_ofst, |
| 67 | UWORD32 *pu4_next_is_aud) |
| 68 | { |
| 69 | UWORD8 u1_first_byte, u1_nal_unit_type; |
| 70 | if(u4_cur_pos + 1 < u4_max_ofst) |
| 71 | { |
| 72 | u1_first_byte = pu1_buf[u4_cur_pos + 1]; |
| 73 | u1_nal_unit_type = NAL_UNIT_TYPE(u1_first_byte); |
| 74 | |
| 75 | if(u1_nal_unit_type == ACCESS_UNIT_DELIMITER_RBSP) |
| 76 | { |
| 77 | *pu4_next_is_aud = 1; |
| 78 | } |
| 79 | } |
| 80 | |
| 81 | } |
| 82 | WORD32 ih264d_find_start_code(UWORD8 *pu1_buf, |
| 83 | UWORD32 u4_cur_pos, |
| 84 | UWORD32 u4_max_ofst, |
| 85 | UWORD32 *pu4_length_of_start_code, |
| 86 | UWORD32 *pu4_next_is_aud) |
| 87 | { |
| 88 | WORD32 zero_byte_cnt = 0; |
| 89 | UWORD32 ui_curPosTemp; |
| 90 | |
| 91 | *pu4_length_of_start_code = 0; |
| 92 | /*Find first start code */ |
| 93 | while(u4_cur_pos < u4_max_ofst) |
| 94 | { |
| 95 | if(pu1_buf[u4_cur_pos] == 0) |
| 96 | zero_byte_cnt++; |
| 97 | else if(pu1_buf[u4_cur_pos] |
| 98 | == 0x01 && zero_byte_cnt >= NUM_OF_ZERO_BYTES_BEFORE_START_CODE) |
| 99 | { |
| 100 | /* Found the start code */ |
| 101 | u4_cur_pos++; |
| 102 | break; |
| 103 | } |
| 104 | else |
| 105 | { |
| 106 | zero_byte_cnt = 0; |
| 107 | } |
| 108 | u4_cur_pos++; |
| 109 | } |
| 110 | /*Find Next Start Code */ |
| 111 | *pu4_length_of_start_code = u4_cur_pos; |
| 112 | zero_byte_cnt = 0; |
| 113 | ui_curPosTemp = u4_cur_pos; |
| 114 | while(u4_cur_pos < u4_max_ofst) |
| 115 | { |
| 116 | |
| 117 | if(pu1_buf[u4_cur_pos] == 0) |
| 118 | zero_byte_cnt++; |
| 119 | else if(pu1_buf[u4_cur_pos] |
| 120 | == 0x01 && zero_byte_cnt >= NUM_OF_ZERO_BYTES_BEFORE_START_CODE) |
| 121 | { |
| 122 | /* Found the start code */ |
| 123 | ih264d_check_if_aud(pu1_buf, u4_cur_pos, u4_max_ofst, |
| 124 | pu4_next_is_aud); |
| 125 | return (u4_cur_pos - zero_byte_cnt - ui_curPosTemp); |
| 126 | } |
| 127 | else |
| 128 | { |
| 129 | zero_byte_cnt = 0; |
| 130 | } |
| 131 | u4_cur_pos++; |
| 132 | } |
| 133 | |
| 134 | return (u4_cur_pos - zero_byte_cnt - ui_curPosTemp); //(START_CODE_NOT_FOUND); |
| 135 | } |
| 136 | |
| 137 | /*! |
| 138 | ************************************************************************** |
| 139 | * \if Function name : ih264d_get_next_nal_unit \endif |
| 140 | * |
| 141 | * \brief |
| 142 | * This function reads one NAl unit. |
| 143 | * |
| 144 | * \param ps_nalStream : Poiter to NalUnitStream structure. |
| 145 | * \param ps_nalUnit : Pointer to NalUnit. |
| 146 | * |
| 147 | * \return |
| 148 | * Returns 0 on success and -1 on error. |
| 149 | * |
| 150 | ************************************************************************** |
| 151 | */ |
| 152 | WORD32 ih264d_get_next_nal_unit(UWORD8 *pu1_buf, |
| 153 | UWORD32 u4_cur_pos, |
| 154 | UWORD32 u4_max_ofst, |
| 155 | UWORD32 *pu4_length_of_start_code) |
| 156 | { |
| 157 | |
| 158 | WORD32 i_length_of_nal_unit = 0; |
| 159 | UWORD32 u4_next_is_aud; |
| 160 | |
| 161 | /* NAL Thread starts */ |
| 162 | |
| 163 | ih264d_find_start_code(pu1_buf, u4_cur_pos, u4_max_ofst, |
| 164 | pu4_length_of_start_code, &u4_next_is_aud); |
| 165 | |
| 166 | return (i_length_of_nal_unit); |
| 167 | } |
| 168 | |
| 169 | /*! |
| 170 | ************************************************************************** |
| 171 | * \if Function name : ih264d_process_nal_unit \endif |
| 172 | * |
| 173 | * \brief |
| 174 | * This function removes emulation byte "0x03" from bitstream (EBSP to RBSP). |
| 175 | * It also converts bytestream format into 32 bit little-endian format. |
| 176 | * |
| 177 | * \param ps_bitstrm : Poiter to dec_bit_stream_t structure. |
| 178 | * \param pu1_nal_unit : Pointer to char buffer of NalUnit. |
| 179 | * \param u4_numbytes_in_nal_unit : Number bytes in NalUnit buffer. |
| 180 | * |
| 181 | * \return |
| 182 | * Returns number of bytes in RBSP ps_bitstrm. |
| 183 | * |
| 184 | * \note |
| 185 | * This function is same as nal_unit() of 7.3.1. Apart from nal_unit() |
| 186 | * implementation it converts char buffer into 32 bit Buffer. This |
| 187 | * facilitates efficient access of bitstream. This has been done taking |
| 188 | * into account present processor architectures. |
| 189 | * |
| 190 | ************************************************************************** |
| 191 | */ |
| 192 | WORD32 ih264d_process_nal_unit(dec_bit_stream_t *ps_bitstrm, |
| 193 | UWORD8 *pu1_nal_unit, |
| 194 | UWORD32 u4_numbytes_in_nal_unit) |
| 195 | { |
| 196 | UWORD32 u4_num_bytes_in_rbsp; |
| 197 | UWORD8 u1_cur_byte; |
| 198 | WORD32 i = 0; |
| 199 | WORD8 c_count; |
| 200 | UWORD32 ui_word; |
| 201 | UWORD32 *puc_bitstream_buffer = (UWORD32*)pu1_nal_unit; |
| 202 | ps_bitstrm->pu4_buffer = puc_bitstream_buffer; |
| 203 | |
| 204 | /*--------------------------------------------------------------------*/ |
| 205 | /* First Byte of the NAL Unit */ |
| 206 | /*--------------------------------------------------------------------*/ |
| 207 | |
| 208 | ui_word = *pu1_nal_unit++; |
| 209 | |
| 210 | /*--------------------------------------------------------------------*/ |
| 211 | /* Convertion of the EBSP to RBSP */ |
| 212 | /* ie Remove the emulation_prevention_byte [equal to 0x03] */ |
| 213 | /*--------------------------------------------------------------------*/ |
| 214 | u4_num_bytes_in_rbsp = 0; |
| 215 | c_count = 0; |
| 216 | |
| 217 | //first iteration |
| 218 | |
| 219 | u1_cur_byte = *pu1_nal_unit++; |
| 220 | |
| 221 | ui_word = ((ui_word << 8) | u1_cur_byte); |
| 222 | |
| 223 | c_count++; |
| 224 | if(u1_cur_byte != 0x00) |
| 225 | c_count = 0; |
| 226 | |
| 227 | //second iteration |
| 228 | |
| 229 | u1_cur_byte = *pu1_nal_unit++; |
| 230 | |
| 231 | ui_word = ((ui_word << 8) | u1_cur_byte); |
| 232 | u4_num_bytes_in_rbsp = 2; |
| 233 | |
| 234 | c_count++; |
| 235 | if(u1_cur_byte != 0x00) |
| 236 | c_count = 0; |
| 237 | |
| 238 | if(u4_numbytes_in_nal_unit > 2) |
| 239 | { |
| 240 | i = ((u4_numbytes_in_nal_unit - 3)); |
| 241 | } |
| 242 | |
| 243 | for(; i > 8; i -= 4) |
| 244 | { |
| 245 | |
| 246 | // loop 0 |
| 247 | u1_cur_byte = *pu1_nal_unit++; |
| 248 | |
| 249 | if(c_count == NUM_OF_ZERO_BYTES_BEFORE_START_CODE |
| 250 | && u1_cur_byte == EMULATION_PREVENTION_BYTE) |
| 251 | { |
| 252 | c_count = 0; |
| 253 | u1_cur_byte = *pu1_nal_unit++; |
| 254 | i--; |
| 255 | } |
| 256 | |
| 257 | ui_word = ((ui_word << 8) | u1_cur_byte); |
| 258 | *puc_bitstream_buffer = ui_word; |
| 259 | puc_bitstream_buffer++; |
| 260 | c_count++; |
| 261 | if(u1_cur_byte != 0x00) |
| 262 | c_count = 0; |
| 263 | |
| 264 | // loop 1 |
| 265 | u1_cur_byte = *pu1_nal_unit++; |
| 266 | |
| 267 | if(c_count == NUM_OF_ZERO_BYTES_BEFORE_START_CODE |
| 268 | && u1_cur_byte == EMULATION_PREVENTION_BYTE) |
| 269 | { |
| 270 | c_count = 0; |
| 271 | u1_cur_byte = *pu1_nal_unit++; |
| 272 | i--; |
| 273 | } |
| 274 | ui_word = ((ui_word << 8) | u1_cur_byte); |
| 275 | |
| 276 | c_count++; |
| 277 | if(u1_cur_byte != 0x00) |
| 278 | c_count = 0; |
| 279 | |
| 280 | // loop 2 |
| 281 | u1_cur_byte = *pu1_nal_unit++; |
| 282 | |
| 283 | if(c_count == NUM_OF_ZERO_BYTES_BEFORE_START_CODE |
| 284 | && u1_cur_byte == EMULATION_PREVENTION_BYTE) |
| 285 | { |
| 286 | c_count = 0; |
| 287 | u1_cur_byte = *pu1_nal_unit++; |
| 288 | i--; |
| 289 | } |
| 290 | |
| 291 | ui_word = ((ui_word << 8) | u1_cur_byte); |
| 292 | |
| 293 | c_count++; |
| 294 | if(u1_cur_byte != 0x00) |
| 295 | c_count = 0; |
| 296 | |
| 297 | // loop 3 |
| 298 | u1_cur_byte = *pu1_nal_unit++; |
| 299 | |
| 300 | if(c_count == NUM_OF_ZERO_BYTES_BEFORE_START_CODE |
| 301 | && u1_cur_byte == EMULATION_PREVENTION_BYTE) |
| 302 | { |
| 303 | c_count = 0; |
| 304 | u1_cur_byte = *pu1_nal_unit++; |
| 305 | i--; |
| 306 | } |
| 307 | |
| 308 | ui_word = ((ui_word << 8) | u1_cur_byte); |
| 309 | |
| 310 | c_count++; |
| 311 | if(u1_cur_byte != 0x00) |
| 312 | c_count = 0; |
| 313 | |
| 314 | u4_num_bytes_in_rbsp += 4; |
| 315 | |
| 316 | } |
| 317 | |
| 318 | for(; i > 0; i--) |
| 319 | { |
| 320 | u1_cur_byte = *pu1_nal_unit++; |
| 321 | |
| 322 | if(c_count == NUM_OF_ZERO_BYTES_BEFORE_START_CODE |
| 323 | && u1_cur_byte == EMULATION_PREVENTION_BYTE) |
| 324 | { |
| 325 | c_count = 0; |
| 326 | i--; |
| 327 | u1_cur_byte = *pu1_nal_unit++; |
| 328 | } |
| 329 | |
| 330 | ui_word = ((ui_word << 8) | u1_cur_byte); |
| 331 | u4_num_bytes_in_rbsp++; |
| 332 | |
| 333 | if((u4_num_bytes_in_rbsp & 0x03) == 0x03) |
| 334 | { |
| 335 | *puc_bitstream_buffer = ui_word; |
| 336 | puc_bitstream_buffer++; |
| 337 | } |
| 338 | c_count++; |
| 339 | if(u1_cur_byte != 0x00) |
| 340 | c_count = 0; |
| 341 | |
| 342 | } |
| 343 | |
| 344 | *puc_bitstream_buffer = (ui_word |
| 345 | << ((3 - (((u4_num_bytes_in_rbsp << 30) >> 30))) << 3)); |
| 346 | ps_bitstrm->u4_ofst = 0; |
| 347 | ps_bitstrm->u4_max_ofst = ((u4_num_bytes_in_rbsp + NAL_FIRST_BYTE_SIZE) << 3); |
| 348 | |
| 349 | return (u4_num_bytes_in_rbsp); |
| 350 | } |
| 351 | |
| 352 | |
| 353 | /*! |
| 354 | ************************************************************************** |
| 355 | * \if Function name : ih264d_rbsp_to_sodb \endif |
| 356 | * |
| 357 | * \brief |
| 358 | * This function converts RBSP to SODB. |
| 359 | * |
| 360 | * \param ps_bitstrm : Poiter to dec_bit_stream_t structure. |
| 361 | * |
| 362 | * \return |
| 363 | * None. |
| 364 | * |
| 365 | ************************************************************************** |
| 366 | */ |
| 367 | void ih264d_rbsp_to_sodb(dec_bit_stream_t *ps_bitstrm) |
| 368 | { |
| 369 | UWORD32 ui_lastWord; |
| 370 | UWORD32 ui_word; |
| 371 | UWORD8 uc_lastByte; |
| 372 | WORD8 i; |
| 373 | |
| 374 | ui_lastWord = (ps_bitstrm->u4_max_ofst >> 5); |
| 375 | i = (ps_bitstrm->u4_max_ofst >> 3) & 0x03; |
| 376 | |
| 377 | if(i) |
| 378 | { |
| 379 | ui_word = ps_bitstrm->pu4_buffer[ui_lastWord]; |
| 380 | uc_lastByte = ((ui_word << ((i - 1) << 3)) >> 24); |
| 381 | } |
| 382 | else |
| 383 | { |
| 384 | ui_word = ps_bitstrm->pu4_buffer[ui_lastWord - 1]; |
| 385 | uc_lastByte = ((ui_word << 24) >> 24); |
| 386 | } |
| 387 | /*--------------------------------------------------------------------*/ |
| 388 | /* Find out the rbsp_stop_bit position in the last byte of rbsp */ |
| 389 | /*--------------------------------------------------------------------*/ |
| 390 | for(i = 0; (i < 8) && !CHECKBIT(uc_lastByte, i); ++i) |
| 391 | ; |
| 392 | ps_bitstrm->u4_max_ofst = ps_bitstrm->u4_max_ofst - (i + 1); |
| 393 | } |