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_mb_utils.c 23 * 24 * \brief 25 * Contains utitlity functions needed for Macroblock decoding 26 * 27 * \date 28 * 18/12/2002 29 * 30 * \author AI 31 ************************************************************************** 32 */ 33 #include <string.h> 34 #include <stdlib.h> 35 #include "ih264d_bitstrm.h" 36 #include "ih264d_defs.h" 37 #include "ih264d_debug.h" 38 #include "ih264d_structs.h" 39 #include "ih264d_defs.h" 40 #include "ih264d_mb_utils.h" 41 #include "ih264d_parse_slice.h" 42 #include "ih264d_error_handler.h" 43 #include "ih264d_parse_mb_header.h" 44 #include "ih264d_cabac.h" 45 #include "ih264d_defs.h" 46 #include "ih264d_tables.h" 47 48 /*****************************************************************************/ 49 /* */ 50 /* Function Name : get_mb_info_cavlc */ 51 /* */ 52 /* Description : This function sets the following information of cur MB */ 53 /* (a) mb_x and mb_y */ 54 /* (b) Neighbour availablity */ 55 /* (c) Macroblock location in the frame buffer */ 56 /* (e) For mbaff predicts field/frame u4_flag for topMb */ 57 /* and sets the field/frame for botMb. This is */ 58 /* written in ps_dec->u1_cur_mb_fld_dec_flag */ 59 /* */ 60 /* Inputs : pointer to decstruct */ 61 /* pointer to current mb info */ 62 /* currentMbaddress */ 63 /* */ 64 /* Processing : leftMb and TopMb params are used by DecMbskip and */ 65 /* DecCtxMbfield modules so that these modules do not */ 66 /* check for neigbour availability and then find the */ 67 /* neigbours for context increments */ 68 /* */ 69 /* Returns : OK */ 70 /* */ 71 /* Issues : <List any issues or problems with this function> */ 72 /* */ 73 /* Revision History: */ 74 /* */ 75 /* DD MM YYYY Author(s) Changes (Describe the changes made) */ 76 /* 13 07 2002 Jay Draft */ 77 /* */ 78 /*****************************************************************************/ 79 80 UWORD32 ih264d_get_mb_info_cavlc_nonmbaff(dec_struct_t *ps_dec, 81 const UWORD16 u2_cur_mb_address, 82 dec_mb_info_t * ps_cur_mb_info, 83 UWORD32 u4_mbskip_run) 84 { 85 WORD32 mb_x; 86 WORD32 mb_y; 87 UWORD8 u1_mb_ngbr_avail = 0; 88 UWORD16 u2_frm_width_in_mb = ps_dec->u2_frm_wd_in_mbs; 89 WORD16 i2_prev_slice_mbx = ps_dec->i2_prev_slice_mbx; 90 UWORD16 u2_top_right_mask = TOP_RIGHT_DEFAULT_AVAILABLE; 91 UWORD16 u2_top_left_mask = TOP_LEFT_DEFAULT_AVAILABLE; 92 UNUSED(u4_mbskip_run); 93 /*--------------------------------------------------------------------*/ 94 /* Calculate values of mb_x and mb_y */ 95 /*--------------------------------------------------------------------*/ 96 mb_x = (WORD16)ps_dec->u2_mbx; 97 mb_y = (WORD16)ps_dec->u2_mby; 98 99 ps_dec->u2_cur_mb_addr = u2_cur_mb_address; 100 101 mb_x++; 102 103 if(mb_x == u2_frm_width_in_mb) 104 { 105 mb_x = 0; 106 mb_y++; 107 } 108 if(mb_y > ps_dec->i2_prev_slice_mby) 109 { 110 /* if not in the immemdiate row of prev slice end then top 111 will be available */ 112 if(mb_y > (ps_dec->i2_prev_slice_mby + 1)) 113 i2_prev_slice_mbx = -1; 114 115 if(mb_x > i2_prev_slice_mbx) 116 { 117 u1_mb_ngbr_avail |= TOP_MB_AVAILABLE_MASK; 118 u2_top_right_mask |= TOP_RIGHT_TOP_AVAILABLE; 119 u2_top_left_mask |= TOP_LEFT_TOP_AVAILABLE; 120 } 121 122 if((mb_x > (i2_prev_slice_mbx - 1)) 123 && (mb_x != (u2_frm_width_in_mb - 1))) 124 { 125 u1_mb_ngbr_avail |= TOP_RIGHT_MB_AVAILABLE_MASK; 126 u2_top_right_mask |= TOP_RIGHT_TOPR_AVAILABLE; 127 } 128 129 if(mb_x > (i2_prev_slice_mbx + 1)) 130 { 131 u1_mb_ngbr_avail |= TOP_LEFT_MB_AVAILABLE_MASK; 132 u2_top_left_mask |= TOP_LEFT_TOPL_AVAILABLE; 133 } 134 135 /* Next row Left will be available*/ 136 i2_prev_slice_mbx = -1; 137 } 138 139 /* Same row */ 140 if(mb_x > (i2_prev_slice_mbx + 1)) 141 { 142 u1_mb_ngbr_avail |= LEFT_MB_AVAILABLE_MASK; 143 u2_top_left_mask |= TOP_LEFT_LEFT_AVAILABLE; 144 } 145 146 { 147 mb_neigbour_params_t *ps_cur_mb_row = ps_dec->ps_cur_mb_row; 148 mb_neigbour_params_t *ps_top_mb_row = ps_dec->ps_top_mb_row; 149 150 /* copy the parameters of topleft Mb */ 151 ps_cur_mb_info->u1_topleft_mbtype = ps_dec->u1_topleft_mbtype; 152 /* Neighbour pointer assignments*/ 153 ps_cur_mb_info->ps_curmb = ps_cur_mb_row + mb_x; 154 ps_cur_mb_info->ps_left_mb = ps_cur_mb_row + mb_x - 1; 155 ps_cur_mb_info->ps_top_mb = ps_top_mb_row + mb_x; 156 ps_cur_mb_info->ps_top_right_mb = ps_top_mb_row + mb_x + 1; 157 158 /* Update the parameters of topleftmb*/ 159 ps_dec->u1_topleft_mbtype = ps_cur_mb_info->ps_top_mb->u1_mb_type; 160 } 161 162 ps_dec->u2_mby = mb_y; 163 ps_dec->u2_mbx = mb_x; 164 ps_cur_mb_info->u2_mbx = mb_x; 165 ps_cur_mb_info->u2_mby = mb_y; 166 ps_cur_mb_info->u1_topmb = 1; 167 ps_dec->i4_submb_ofst += SUB_BLK_SIZE; 168 ps_dec->u1_mb_ngbr_availablity = u1_mb_ngbr_avail; 169 ps_cur_mb_info->u1_mb_ngbr_availablity = u1_mb_ngbr_avail; 170 ps_cur_mb_info->ps_curmb->u1_mb_fld = ps_dec->u1_cur_mb_fld_dec_flag; 171 ps_cur_mb_info->u1_mb_field_decodingflag = ps_dec->u1_cur_mb_fld_dec_flag; 172 ps_cur_mb_info->u2_top_left_avail_mask = u2_top_left_mask; 173 ps_cur_mb_info->u2_top_right_avail_mask = u2_top_right_mask; 174 return (OK); 175 176 } 177 178 /*****************************************************************************/ 179 /* */ 180 /* Function Name : get_mb_info_cavlc */ 181 /* */ 182 /* Description : This function sets the following information of cur MB */ 183 /* (a) mb_x and mb_y */ 184 /* (b) Neighbour availablity */ 185 /* (c) Macroblock location in the frame buffer */ 186 /* (e) For mbaff predicts field/frame u4_flag for topMb */ 187 /* and sets the field/frame for botMb. This is */ 188 /* written in ps_dec->u1_cur_mb_fld_dec_flag */ 189 /* */ 190 /* Inputs : pointer to decstruct */ 191 /* pointer to current mb info */ 192 /* currentMbaddress */ 193 /* */ 194 /* Processing : leftMb and TopMb params are used by DecMbskip and */ 195 /* DecCtxMbfield modules so that these modules do not */ 196 /* check for neigbour availability and then find the */ 197 /* neigbours for context increments */ 198 /* */ 199 /* Returns : OK */ 200 /* */ 201 /* Issues : <List any issues or problems with this function> */ 202 /* */ 203 /* Revision History: */ 204 /* */ 205 /* DD MM YYYY Author(s) Changes (Describe the changes made) */ 206 /* 13 07 2002 Jay Draft */ 207 /* */ 208 /*****************************************************************************/ 209 210 UWORD32 ih264d_get_mb_info_cavlc_mbaff(dec_struct_t *ps_dec, 211 const UWORD16 u2_cur_mb_address, 212 dec_mb_info_t * ps_cur_mb_info, 213 UWORD32 u4_mbskip_run) 214 { 215 UWORD16 u2_mb_x; 216 UWORD16 u2_mb_y; 217 UWORD8 u1_mb_ngbr_avail = 0; 218 UWORD16 u2_frm_width_in_mb = ps_dec->u2_frm_wd_in_mbs; 219 220 UWORD8 u1_top_mb = 1 - (u2_cur_mb_address & 0x01); 221 WORD16 i2_prev_slice_mbx = ps_dec->i2_prev_slice_mbx; 222 UWORD8 u1_cur_mb_field = 0; 223 UWORD16 u2_top_right_mask = TOP_RIGHT_DEFAULT_AVAILABLE; 224 UWORD16 u2_top_left_mask = TOP_LEFT_DEFAULT_AVAILABLE; 225 226 /*--------------------------------------------------------------------*/ 227 /* Calculate values of mb_x and mb_y */ 228 /*--------------------------------------------------------------------*/ 229 u2_mb_x = ps_dec->u2_mbx; 230 u2_mb_y = ps_dec->u2_mby; 231 232 ps_dec->u2_cur_mb_addr = u2_cur_mb_address; 233 234 235 if(u1_top_mb) 236 { 237 u2_mb_x++; 238 if(u2_mb_x == u2_frm_width_in_mb) 239 { 240 u2_mb_x = 0; 241 u2_mb_y += 2; 242 } 243 if(u2_mb_y > ps_dec->i2_prev_slice_mby) 244 { 245 /* if not in the immemdiate row of prev slice end then top 246 will be available */ 247 if(u2_mb_y > (ps_dec->i2_prev_slice_mby + 2)) 248 i2_prev_slice_mbx = -1; 249 if(u2_mb_x > i2_prev_slice_mbx) 250 { 251 u1_mb_ngbr_avail |= TOP_MB_AVAILABLE_MASK; 252 u1_cur_mb_field = ps_dec->ps_top_mb_row[u2_mb_x << 1].u1_mb_fld; 253 u2_top_right_mask |= TOP_RIGHT_TOP_AVAILABLE; 254 u2_top_left_mask |= TOP_LEFT_TOP_AVAILABLE; 255 } 256 if((u2_mb_x > (i2_prev_slice_mbx - 1)) 257 && (u2_mb_x != (u2_frm_width_in_mb - 1))) 258 { 259 u1_mb_ngbr_avail |= TOP_RIGHT_MB_AVAILABLE_MASK; 260 u2_top_right_mask |= TOP_RIGHT_TOPR_AVAILABLE; 261 } 262 263 if(u2_mb_x > (i2_prev_slice_mbx + 1)) 264 { 265 u1_mb_ngbr_avail |= TOP_LEFT_MB_AVAILABLE_MASK; 266 u2_top_left_mask |= TOP_LEFT_TOPL_AVAILABLE; 267 } 268 269 i2_prev_slice_mbx = -1; 270 } 271 /* Same row */ 272 if(u2_mb_x > (i2_prev_slice_mbx + 1)) 273 { 274 u1_mb_ngbr_avail |= LEFT_MB_AVAILABLE_MASK; 275 u1_cur_mb_field = 276 ps_dec->ps_cur_mb_row[(u2_mb_x << 1) - 1].u1_mb_fld; 277 u2_top_left_mask |= TOP_LEFT_LEFT_AVAILABLE; 278 } 279 /* Read u1_cur_mb_field from the bitstream if u4_mbskip_run <= 1*/ 280 if(u4_mbskip_run <= 1) 281 u1_cur_mb_field = (UWORD8)ih264d_get_bit_h264(ps_dec->ps_bitstrm); 282 283 ps_dec->u1_cur_mb_fld_dec_flag = u1_cur_mb_field; 284 ps_dec->u2_top_left_mask = u2_top_left_mask; 285 ps_dec->u2_top_right_mask = u2_top_right_mask; 286 } 287 else 288 { 289 u1_mb_ngbr_avail = ps_dec->u1_mb_ngbr_availablity; 290 u1_cur_mb_field = ps_dec->u1_cur_mb_fld_dec_flag; 291 u2_top_left_mask = ps_dec->u2_top_left_mask; 292 u2_top_right_mask = ps_dec->u2_top_right_mask; 293 294 if(!u1_cur_mb_field) 295 { 296 /* Top is available */ 297 u1_mb_ngbr_avail |= TOP_MB_AVAILABLE_MASK; 298 u2_top_right_mask |= TOP_RIGHT_TOP_AVAILABLE; 299 u2_top_left_mask |= TOP_LEFT_TOP_AVAILABLE; 300 /* Top Right not available */ 301 u1_mb_ngbr_avail &= TOP_RT_SUBBLOCK_MASK_MOD; 302 u2_top_right_mask &= (~TOP_RIGHT_TOPR_AVAILABLE); 303 304 if(u1_mb_ngbr_avail & LEFT_MB_AVAILABLE_MASK) 305 { 306 u1_mb_ngbr_avail |= TOP_LEFT_MB_AVAILABLE_MASK; 307 u2_top_left_mask |= TOP_LEFT_LEFT_AVAILABLE; 308 u2_top_left_mask |= TOP_LEFT_TOPL_AVAILABLE; 309 } 310 } 311 } 312 313 ps_dec->u2_mby = u2_mb_y; 314 ps_dec->u2_mbx = u2_mb_x; 315 ps_cur_mb_info->u2_mbx = u2_mb_x; 316 ps_cur_mb_info->u2_mby = u2_mb_y; 317 ps_cur_mb_info->u1_topmb = u1_top_mb; 318 ps_dec->i4_submb_ofst += SUB_BLK_SIZE; 319 ps_dec->u1_mb_ngbr_availablity = u1_mb_ngbr_avail; 320 ps_cur_mb_info->u1_mb_ngbr_availablity = u1_mb_ngbr_avail; 321 ps_cur_mb_info->u1_mb_field_decodingflag = u1_cur_mb_field; 322 ps_cur_mb_info->u2_top_left_avail_mask = u2_top_left_mask; 323 ps_cur_mb_info->u2_top_right_avail_mask = u2_top_right_mask; 324 ih264d_get_mbaff_neighbours(ps_dec, ps_cur_mb_info, u1_cur_mb_field); 325 return (OK); 326 } 327 328 /*****************************************************************************/ 329 /* */ 330 /* Function Name : get_mb_info_cabac */ 331 /* */ 332 /* Description : This function sets the following information of cur MB */ 333 /* (a) mb_x and mb_y */ 334 /* (b) Neighbour availablity */ 335 /* (c) Macroblock location in the frame buffer */ 336 /* (e) leftMb parama and TopMb params of curMB */ 337 /* (f) For Mbaff case leftMb params and TopMb params of */ 338 /* bottomMb are also set if curMB is top */ 339 /* (g) For mbaff predicts field/frame u4_flag for topMb */ 340 /* and sets the field/frame for botMb. This is */ 341 /* written in ps_dec->u1_cur_mb_fld_dec_flag */ 342 /* */ 343 /* Inputs : pointer to decstruct */ 344 /* pointer to current mb info */ 345 /* currentMbaddress */ 346 /* */ 347 /* Processing : leftMb and TopMb params are used by DecMbskip and */ 348 /* DecCtxMbfield modules so that these modules do not */ 349 /* check for neigbour availability and then find the */ 350 /* neigbours for context increments */ 351 /* */ 352 /* Returns : OK */ 353 /* */ 354 /* Issues : <List any issues or problems with this function> */ 355 /* */ 356 /* Revision History: */ 357 /* */ 358 /* DD MM YYYY Author(s) Changes (Describe the changes made) */ 359 /* 13 07 2002 Jay Draft */ 360 /* */ 361 /*****************************************************************************/ 362 UWORD32 ih264d_get_mb_info_cabac_nonmbaff(dec_struct_t *ps_dec, 363 const UWORD16 u2_cur_mb_address, 364 dec_mb_info_t * ps_cur_mb_info, 365 UWORD32 u4_mbskip) 366 { 367 WORD32 mb_x; 368 WORD32 mb_y; 369 UWORD32 u1_mb_ngbr_avail = 0; 370 UWORD32 u2_frm_width_in_mb = ps_dec->u2_frm_wd_in_mbs; 371 UWORD32 u1_top_mb = 1; 372 WORD32 i2_prev_slice_mbx = ps_dec->i2_prev_slice_mbx; 373 UWORD32 u2_top_right_mask = TOP_RIGHT_DEFAULT_AVAILABLE; 374 UWORD32 u2_top_left_mask = TOP_LEFT_DEFAULT_AVAILABLE; 375 ctxt_inc_mb_info_t * const p_ctx_inc_mb_map = ps_dec->p_ctxt_inc_mb_map; 376 377 /*--------------------------------------------------------------------*/ 378 /* Calculate values of mb_x and mb_y */ 379 /*--------------------------------------------------------------------*/ 380 mb_x = (WORD16)ps_dec->u2_mbx; 381 mb_y = (WORD16)ps_dec->u2_mby; 382 383 ps_dec->u2_cur_mb_addr = u2_cur_mb_address; 384 385 mb_x++; 386 if((UWORD32)mb_x == u2_frm_width_in_mb) 387 { 388 mb_x = 0; 389 mb_y++; 390 } 391 /*********************************************************************/ 392 /* Cabac Context Initialisations */ 393 /*********************************************************************/ 394 ps_dec->ps_curr_ctxt_mb_info = p_ctx_inc_mb_map + mb_x; 395 ps_dec->p_left_ctxt_mb_info = p_ctx_inc_mb_map - 1; 396 ps_dec->p_top_ctxt_mb_info = p_ctx_inc_mb_map - 1; 397 398 /********************************************************************/ 399 /* neighbour availablility */ 400 /********************************************************************/ 401 if(mb_y > ps_dec->i2_prev_slice_mby) 402 { 403 /* if not in the immemdiate row of prev slice end then top 404 will be available */ 405 if(mb_y > (ps_dec->i2_prev_slice_mby + 1)) 406 i2_prev_slice_mbx = -1; 407 408 if(mb_x > i2_prev_slice_mbx) 409 { 410 u1_mb_ngbr_avail |= TOP_MB_AVAILABLE_MASK; 411 u2_top_right_mask |= TOP_RIGHT_TOP_AVAILABLE; 412 u2_top_left_mask |= TOP_LEFT_TOP_AVAILABLE; 413 ps_dec->p_top_ctxt_mb_info = ps_dec->ps_curr_ctxt_mb_info; 414 } 415 if((mb_x > (i2_prev_slice_mbx - 1)) 416 && ((UWORD32)mb_x != (u2_frm_width_in_mb - 1))) 417 { 418 u1_mb_ngbr_avail |= TOP_RIGHT_MB_AVAILABLE_MASK; 419 u2_top_right_mask |= TOP_RIGHT_TOPR_AVAILABLE; 420 } 421 422 if(mb_x > (i2_prev_slice_mbx + 1)) 423 { 424 u1_mb_ngbr_avail |= TOP_LEFT_MB_AVAILABLE_MASK; 425 u2_top_left_mask |= TOP_LEFT_TOPL_AVAILABLE; 426 } 427 /* Next row */ 428 i2_prev_slice_mbx = -1; 429 } 430 /* Same row */ 431 if(mb_x > (i2_prev_slice_mbx + 1)) 432 { 433 u1_mb_ngbr_avail |= LEFT_MB_AVAILABLE_MASK; 434 u2_top_left_mask |= TOP_LEFT_LEFT_AVAILABLE; 435 ps_dec->p_left_ctxt_mb_info = ps_dec->ps_curr_ctxt_mb_info - 1; 436 } 437 { 438 mb_neigbour_params_t *ps_cur_mb_row = ps_dec->ps_cur_mb_row; 439 mb_neigbour_params_t *ps_top_mb_row = ps_dec->ps_top_mb_row; 440 /* copy the parameters of topleft Mb */ 441 ps_cur_mb_info->u1_topleft_mbtype = ps_dec->u1_topleft_mbtype; 442 /* Neighbour pointer assignments*/ 443 ps_cur_mb_info->ps_curmb = ps_cur_mb_row + mb_x; 444 ps_cur_mb_info->ps_left_mb = ps_cur_mb_row + mb_x - 1; 445 ps_cur_mb_info->ps_top_mb = ps_top_mb_row + mb_x; 446 ps_cur_mb_info->ps_top_right_mb = ps_top_mb_row + mb_x + 1; 447 448 /* Update the parameters of topleftmb*/ 449 ps_dec->u1_topleft_mbtype = ps_cur_mb_info->ps_top_mb->u1_mb_type; 450 } 451 452 ps_dec->u2_mby = mb_y; 453 ps_dec->u2_mbx = mb_x; 454 ps_cur_mb_info->u2_mbx = mb_x; 455 ps_cur_mb_info->u2_mby = mb_y; 456 ps_cur_mb_info->u1_topmb = u1_top_mb; 457 ps_dec->i4_submb_ofst += SUB_BLK_SIZE; 458 ps_dec->u1_mb_ngbr_availablity = u1_mb_ngbr_avail; 459 ps_cur_mb_info->u1_mb_ngbr_availablity = u1_mb_ngbr_avail; 460 ps_cur_mb_info->ps_curmb->u1_mb_fld = ps_dec->u1_cur_mb_fld_dec_flag; 461 ps_cur_mb_info->u1_mb_field_decodingflag = ps_dec->u1_cur_mb_fld_dec_flag; 462 ps_cur_mb_info->u2_top_left_avail_mask = u2_top_left_mask; 463 ps_cur_mb_info->u2_top_right_avail_mask = u2_top_right_mask; 464 465 /*********************************************************************/ 466 /* Assign the neigbours */ 467 /*********************************************************************/ 468 if(u4_mbskip) 469 { 470 UWORD32 u4_ctx_inc = 471 2 472 - ((!!(ps_dec->p_top_ctxt_mb_info->u1_mb_type 473 & CAB_SKIP_MASK)) 474 + (!!(ps_dec->p_left_ctxt_mb_info->u1_mb_type 475 & CAB_SKIP_MASK))); 476 477 u4_mbskip = ih264d_decode_bin(u4_ctx_inc, ps_dec->p_mb_skip_flag_t, 478 ps_dec->ps_bitstrm, &ps_dec->s_cab_dec_env); 479 480 if(!u4_mbskip) 481 { 482 if(!(u1_mb_ngbr_avail & LEFT_MB_AVAILABLE_MASK)) 483 { 484 UWORD32 *pu4_buf; 485 UWORD8 *pu1_buf; 486 487 pu1_buf = ps_dec->pu1_left_nnz_y; 488 pu4_buf = (UWORD32 *)pu1_buf; 489 *pu4_buf = 0; 490 pu1_buf = ps_dec->pu1_left_nnz_uv; 491 pu4_buf = (UWORD32 *)pu1_buf; 492 *pu4_buf = 0; 493 494 495 *(ps_dec->pu1_left_yuv_dc_csbp) = 0; 496 MEMSET_16BYTES(&ps_dec->pu1_left_mv_ctxt_inc[0][0], 0); 497 *(UWORD32 *)ps_dec->pi1_left_ref_idx_ctxt_inc = 0; 498 } 499 if(!(u1_mb_ngbr_avail & TOP_MB_AVAILABLE_MASK)) 500 { 501 MEMSET_16BYTES(ps_dec->ps_curr_ctxt_mb_info->u1_mv, 0); 502 memset(ps_dec->ps_curr_ctxt_mb_info->i1_ref_idx, 0, 4); 503 } 504 } 505 } 506 return (u4_mbskip); 507 } 508 509 /*****************************************************************************/ 510 /* */ 511 /* Function Name : get_mb_info_cabac */ 512 /* */ 513 /* Description : This function sets the following information of cur MB */ 514 /* (a) mb_x and mb_y */ 515 /* (b) Neighbour availablity */ 516 /* (c) Macroblock location in the frame buffer */ 517 /* (e) leftMb parama and TopMb params of curMB */ 518 /* (f) For Mbaff case leftMb params and TopMb params of */ 519 /* bottomMb are also set if curMB is top */ 520 /* (g) For mbaff predicts field/frame u4_flag for topMb */ 521 /* and sets the field/frame for botMb. This is */ 522 /* written in ps_dec->u1_cur_mb_fld_dec_flag */ 523 /* */ 524 /* Inputs : pointer to decstruct */ 525 /* pointer to current mb info */ 526 /* currentMbaddress */ 527 /* */ 528 /* Processing : leftMb and TopMb params are used by DecMbskip and */ 529 /* DecCtxMbfield modules so that these modules do not */ 530 /* check for neigbour availability and then find the */ 531 /* neigbours for context increments */ 532 /* */ 533 /* Returns : OK */ 534 /* */ 535 /* Issues : <List any issues or problems with this function> */ 536 /* */ 537 /* Revision History: */ 538 /* */ 539 /* DD MM YYYY Author(s) Changes (Describe the changes made) */ 540 /* 13 07 2002 Jay Draft */ 541 /* */ 542 /*****************************************************************************/ 543 544 UWORD32 ih264d_get_mb_info_cabac_mbaff(dec_struct_t *ps_dec, 545 const UWORD16 u2_cur_mb_address, 546 dec_mb_info_t * ps_cur_mb_info, 547 UWORD32 u4_mbskip) 548 { 549 WORD32 mb_x; 550 WORD32 mb_y; 551 UWORD8 u1_mb_ngbr_avail = 0; 552 UWORD16 u2_frm_width_in_mb = ps_dec->u2_frm_wd_in_mbs; 553 ctxt_inc_mb_info_t * const p_ctx_inc_mb_map = ps_dec->p_ctxt_inc_mb_map; 554 ctxt_inc_mb_info_t *ps_curr_ctxt, *ps_top_ctxt, *ps_left_ctxt; 555 mb_neigbour_params_t *ps_cur_mb_row = ps_dec->ps_cur_mb_row; 556 mb_neigbour_params_t *ps_top_mb_row = ps_dec->ps_top_mb_row; 557 UWORD32 u4_left_mb_pair_fld = 0; 558 UWORD32 u4_top_mb_pair_fld = 0; 559 UWORD8 u1_cur_mb_field = 0; 560 UWORD8 u1_top_mb = 1 - (u2_cur_mb_address & 0x01); 561 WORD16 i2_prev_slice_mbx = ps_dec->i2_prev_slice_mbx; 562 UWORD16 u2_top_right_mask = TOP_RIGHT_DEFAULT_AVAILABLE; 563 UWORD16 u2_top_left_mask = TOP_LEFT_DEFAULT_AVAILABLE; 564 565 /*--------------------------------------------------------------------*/ 566 /* Calculate values of mb_x and mb_y */ 567 /*--------------------------------------------------------------------*/ 568 mb_x = (WORD16)ps_dec->u2_mbx; 569 mb_y = (WORD16)ps_dec->u2_mby; 570 571 ps_dec->u2_cur_mb_addr = u2_cur_mb_address; 572 573 ps_top_ctxt = ps_left_ctxt = p_ctx_inc_mb_map - 1; 574 575 if(u1_top_mb) 576 { 577 ctxt_inc_mb_info_t *ps_left_mb_of_bot = ps_left_ctxt; 578 ctxt_inc_mb_info_t *ps_top_mb_of_bot = ps_top_ctxt; 579 580 mb_x++; 581 582 if(mb_x == u2_frm_width_in_mb) 583 { 584 mb_x = 0; 585 mb_y += 2; 586 } 587 588 ps_curr_ctxt = p_ctx_inc_mb_map + (mb_x << 1); 589 if(mb_y > ps_dec->i2_prev_slice_mby) 590 { 591 UWORD8 u1_cur_mb_fld_flag_known = 0; 592 /* Next row */ 593 if(mb_x > 0) 594 { 595 /***********************************************************************/ 596 /* Left Mb is avialable */ 597 /***********************************************************************/ 598 u1_mb_ngbr_avail |= LEFT_MB_AVAILABLE_MASK; 599 ps_left_ctxt = ps_curr_ctxt - 2; 600 ps_left_mb_of_bot = ps_curr_ctxt - 1; 601 u1_cur_mb_field = u4_left_mb_pair_fld = ps_cur_mb_row[(mb_x 602 << 1) - 1].u1_mb_fld; 603 u1_cur_mb_fld_flag_known = 1; 604 u2_top_left_mask |= TOP_LEFT_LEFT_AVAILABLE; 605 } 606 /* if not in the immemdiate row of prev slice end then top 607 will be available */ 608 if(mb_y > (ps_dec->i2_prev_slice_mby + 2)) 609 i2_prev_slice_mbx = -1; 610 if(mb_x > i2_prev_slice_mbx) 611 { 612 /*********************************************************************/ 613 /* Top Mb is avialable */ 614 /*********************************************************************/ 615 u1_mb_ngbr_avail |= TOP_MB_AVAILABLE_MASK; 616 u2_top_right_mask |= TOP_RIGHT_TOP_AVAILABLE; 617 u2_top_left_mask |= TOP_LEFT_TOP_AVAILABLE; 618 619 /* point to MbAddrB + 1 */ 620 ps_top_ctxt = ps_curr_ctxt + 1; 621 u4_top_mb_pair_fld = ps_top_mb_row[(mb_x << 1)].u1_mb_fld; 622 623 u1_cur_mb_field = 624 u1_cur_mb_fld_flag_known ? 625 u1_cur_mb_field : 626 u4_top_mb_pair_fld; 627 ps_top_mb_of_bot = u1_cur_mb_field ? ps_top_ctxt : ps_curr_ctxt; 628 629 /* MbAddrB */ 630 ps_top_ctxt -= (u1_cur_mb_field && u4_top_mb_pair_fld); 631 } 632 633 if((mb_x > (i2_prev_slice_mbx - 1)) 634 && (mb_x != (u2_frm_width_in_mb - 1))) 635 { 636 u1_mb_ngbr_avail |= TOP_RIGHT_MB_AVAILABLE_MASK; 637 u2_top_right_mask |= TOP_RIGHT_TOPR_AVAILABLE; 638 } 639 640 if(mb_x > (i2_prev_slice_mbx + 1)) 641 { 642 u1_mb_ngbr_avail |= TOP_LEFT_MB_AVAILABLE_MASK; 643 u2_top_left_mask |= TOP_LEFT_TOPL_AVAILABLE; 644 } 645 } 646 else 647 { 648 /* Same row */ 649 if(mb_x > (i2_prev_slice_mbx + 1)) 650 { 651 /***************************************************************/ 652 /* Left Mb is avialable */ 653 /***************************************************************/ 654 u1_mb_ngbr_avail |= LEFT_MB_AVAILABLE_MASK; 655 656 u1_cur_mb_field = u4_left_mb_pair_fld = ps_cur_mb_row[(mb_x 657 << 1) - 1].u1_mb_fld; 658 ps_left_ctxt = ps_curr_ctxt - 2; 659 ps_left_mb_of_bot = ps_curr_ctxt - 1; 660 u2_top_left_mask |= TOP_LEFT_LEFT_AVAILABLE; 661 } 662 } 663 /*********************************************************/ 664 /* Check whether the call is from I slice or Inter slice */ 665 /*********************************************************/ 666 if(u4_mbskip) 667 { 668 UWORD32 u4_ctx_inc = 2 669 - ((!!(ps_top_ctxt->u1_mb_type & CAB_SKIP_MASK)) 670 + (!!(ps_left_ctxt->u1_mb_type 671 & CAB_SKIP_MASK))); 672 dec_bit_stream_t * const ps_bitstrm = ps_dec->ps_bitstrm; 673 decoding_envirnoment_t *ps_cab_dec_env = &ps_dec->s_cab_dec_env; 674 bin_ctxt_model_t *p_mb_skip_flag_t = ps_dec->p_mb_skip_flag_t; 675 676 ps_dec->u4_next_mb_skip = 0; 677 u4_mbskip = ih264d_decode_bin(u4_ctx_inc, p_mb_skip_flag_t, 678 ps_bitstrm, ps_cab_dec_env); 679 680 if(u4_mbskip) 681 { 682 UWORD32 u4_next_mbskip; 683 ps_curr_ctxt->u1_mb_type = CAB_SKIP; 684 685 u4_ctx_inc = 686 2 687 - ((!!(ps_top_mb_of_bot->u1_mb_type 688 & CAB_SKIP_MASK)) 689 + (!!(ps_left_mb_of_bot->u1_mb_type 690 & CAB_SKIP_MASK))); 691 692 /* Decode the skip u4_flag of bottom Mb */ 693 u4_next_mbskip = ih264d_decode_bin(u4_ctx_inc, p_mb_skip_flag_t, 694 ps_bitstrm, 695 ps_cab_dec_env); 696 697 ps_dec->u4_next_mb_skip = u4_next_mbskip; 698 699 if(!u4_next_mbskip) 700 { 701 u4_ctx_inc = u4_top_mb_pair_fld + u4_left_mb_pair_fld; 702 703 u1_cur_mb_field = ih264d_decode_bin( 704 u4_ctx_inc, ps_dec->p_mb_field_dec_flag_t, 705 ps_bitstrm, ps_cab_dec_env); 706 } 707 } 708 } 709 710 if(!u4_mbskip) 711 { 712 UWORD32 u4_ctx_inc = u4_top_mb_pair_fld + u4_left_mb_pair_fld; 713 u1_cur_mb_field = ih264d_decode_bin(u4_ctx_inc, 714 ps_dec->p_mb_field_dec_flag_t, 715 ps_dec->ps_bitstrm, 716 &ps_dec->s_cab_dec_env); 717 } 718 719 ps_dec->u1_cur_mb_fld_dec_flag = u1_cur_mb_field; 720 ps_dec->u2_top_left_mask = u2_top_left_mask; 721 ps_dec->u2_top_right_mask = u2_top_right_mask; 722 ps_dec->u2_mby = mb_y; 723 ps_dec->u2_mbx = mb_x; 724 } 725 else 726 { 727 u1_cur_mb_field = ps_dec->u1_cur_mb_fld_dec_flag; 728 u1_mb_ngbr_avail = ps_dec->u1_mb_ngbr_availablity; 729 u2_top_left_mask = ps_dec->u2_top_left_mask; 730 u2_top_right_mask = ps_dec->u2_top_right_mask; 731 ps_curr_ctxt = p_ctx_inc_mb_map + (mb_x << 1) + 1; 732 733 if(u1_mb_ngbr_avail & LEFT_MB_AVAILABLE_MASK) 734 { 735 u4_left_mb_pair_fld = ps_cur_mb_row[(mb_x << 1) - 1].u1_mb_fld; 736 737 /* point to A if top else A+1 */ 738 ps_left_ctxt = ps_curr_ctxt - 2 739 - (u4_left_mb_pair_fld != u1_cur_mb_field); 740 } 741 742 if(u1_cur_mb_field) 743 { 744 if(u1_mb_ngbr_avail & TOP_MB_AVAILABLE_MASK) 745 { 746 /* point to MbAddrB + 1 */ 747 ps_top_ctxt = ps_curr_ctxt; 748 } 749 } 750 else 751 { 752 /* Top is available */ 753 u1_mb_ngbr_avail |= TOP_MB_AVAILABLE_MASK; 754 u2_top_right_mask |= TOP_RIGHT_TOP_AVAILABLE; 755 u2_top_left_mask |= TOP_LEFT_TOP_AVAILABLE; 756 /* Top Right not available */ 757 u1_mb_ngbr_avail &= TOP_RT_SUBBLOCK_MASK_MOD; 758 u2_top_right_mask &= (~TOP_RIGHT_TOPR_AVAILABLE); 759 760 if(u1_mb_ngbr_avail & LEFT_MB_AVAILABLE_MASK) 761 { 762 u1_mb_ngbr_avail |= TOP_LEFT_MB_AVAILABLE_MASK; 763 u2_top_left_mask |= TOP_LEFT_LEFT_AVAILABLE; 764 u2_top_left_mask |= TOP_LEFT_TOPL_AVAILABLE; 765 } 766 767 /* CurMbAddr - 1 */ 768 ps_top_ctxt = ps_curr_ctxt - 1; 769 } 770 771 if(u4_mbskip) 772 { 773 if(ps_curr_ctxt[-1].u1_mb_type & CAB_SKIP_MASK) 774 { 775 /* If previous mb is skipped, return value of next mb skip */ 776 u4_mbskip = ps_dec->u4_next_mb_skip; 777 778 } 779 else 780 { 781 /* If previous mb is not skipped then call DecMbSkip */ 782 UWORD32 u4_ctx_inc = 783 2 784 - ((!!(ps_top_ctxt->u1_mb_type 785 & CAB_SKIP_MASK)) 786 + (!!(ps_left_ctxt->u1_mb_type 787 & CAB_SKIP_MASK))); 788 789 u4_mbskip = ih264d_decode_bin(u4_ctx_inc, 790 ps_dec->p_mb_skip_flag_t, 791 ps_dec->ps_bitstrm, 792 &ps_dec->s_cab_dec_env); 793 } 794 } 795 } 796 797 ps_cur_mb_info->u2_mbx = mb_x; 798 ps_cur_mb_info->u2_mby = mb_y; 799 ps_cur_mb_info->u1_topmb = u1_top_mb; 800 ps_dec->i4_submb_ofst += SUB_BLK_SIZE; 801 ps_dec->u1_mb_ngbr_availablity = u1_mb_ngbr_avail; 802 ps_cur_mb_info->u1_mb_ngbr_availablity = u1_mb_ngbr_avail; 803 ps_cur_mb_info->u1_mb_field_decodingflag = u1_cur_mb_field; 804 ps_cur_mb_info->u2_top_left_avail_mask = u2_top_left_mask; 805 ps_cur_mb_info->u2_top_right_avail_mask = u2_top_right_mask; 806 807 ih264d_get_mbaff_neighbours(ps_dec, ps_cur_mb_info, u1_cur_mb_field); 808 { 809 ih264d_get_cabac_context_mbaff(ps_dec, ps_cur_mb_info, u4_mbskip); 810 } 811 812 { 813 bin_ctxt_model_t *p_cabac_ctxt_table_t = ps_dec->p_cabac_ctxt_table_t; 814 815 if(u1_cur_mb_field) 816 { 817 p_cabac_ctxt_table_t += SIGNIFICANT_COEFF_FLAG_FLD; 818 } 819 else 820 { 821 p_cabac_ctxt_table_t += SIGNIFICANT_COEFF_FLAG_FRAME; 822 } 823 { 824 bin_ctxt_model_t * * p_significant_coeff_flag_t = 825 ps_dec->p_significant_coeff_flag_t; 826 p_significant_coeff_flag_t[0] = p_cabac_ctxt_table_t 827 + SIG_COEFF_CTXT_CAT_0_OFFSET; 828 p_significant_coeff_flag_t[1] = p_cabac_ctxt_table_t 829 + SIG_COEFF_CTXT_CAT_1_OFFSET; 830 p_significant_coeff_flag_t[2] = p_cabac_ctxt_table_t 831 + SIG_COEFF_CTXT_CAT_2_OFFSET; 832 p_significant_coeff_flag_t[3] = p_cabac_ctxt_table_t 833 + SIG_COEFF_CTXT_CAT_3_OFFSET; 834 p_significant_coeff_flag_t[4] = p_cabac_ctxt_table_t 835 + SIG_COEFF_CTXT_CAT_4_OFFSET; 836 p_significant_coeff_flag_t[5] = p_cabac_ctxt_table_t 837 + SIG_COEFF_CTXT_CAT_5_OFFSET; 838 839 } 840 } 841 return (u4_mbskip); 842 } 843 844 /*****************************************************************************/ 845 /* */ 846 /* Function Name : ih264d_get_cabac_context_mbaff */ 847 /* */ 848 /* Description : Gets the current macroblock Cabac Context and sets the */ 849 /* top and left cabac context ptrs in CtxIncMbMap */ 850 /* 1. For Coss field left neigbours it alters coded block */ 851 /* u4_flag , motion vectors, reference indices, cbp of */ 852 /* the left neigbours which increases the code i4_size */ 853 /* 2. For Coss field top neigbours it alters motion */ 854 /* vectors reference indices of the top neigbours */ 855 /* which further increases the code i4_size */ 856 /* */ 857 /* Inputs : 1. dec_struct_t */ 858 /* 2. CurMbAddr used for Mbaff (only to see if curMB */ 859 /* is top or bottom) */ 860 /* 3. uc_curMbFldDecFlag only for Mbaff */ 861 /* */ 862 /* Returns : 0 */ 863 /* */ 864 /* Issues : code i4_size can be reduced if ui_CodedBlockFlag storage */ 865 /* structure in context is changed. This change however */ 866 /* would break the parseResidual4x4Cabac asm routine. */ 867 /* */ 868 /* Revision History: */ 869 /* */ 870 /* DD MM YYYY Author(s) Changes (Describe the changes made) */ 871 /* 18 06 2005 Jay */ 872 /* */ 873 /*****************************************************************************/ 874 UWORD32 ih264d_get_cabac_context_mbaff(dec_struct_t * ps_dec, 875 dec_mb_info_t *ps_cur_mb_info, 876 UWORD32 u4_mbskip) 877 { 878 const UWORD8 u1_mb_ngbr_availablity = ps_dec->u1_mb_ngbr_availablity; 879 ctxt_inc_mb_info_t * const p_ctx_inc_mb_map = ps_dec->p_ctxt_inc_mb_map; 880 881 UWORD8 (*pu1_left_mv_ctxt_inc_2d)[4] = &ps_dec->pu1_left_mv_ctxt_inc[0]; 882 WORD8 (*pi1_left_ref_idx_ctxt_inc) = ps_dec->pi1_left_ref_idx_ctxt_inc; 883 const UWORD8 u1_cur_mb_fld_flag = ps_cur_mb_info->u1_mb_field_decodingflag; 884 const UWORD8 u1_topmb = ps_cur_mb_info->u1_topmb; 885 const UWORD8 uc_botMb = 1 - ps_cur_mb_info->u1_topmb; 886 887 ctxt_inc_mb_info_t * ps_leftMB; 888 889 ps_dec->ps_curr_ctxt_mb_info = p_ctx_inc_mb_map + (ps_dec->u2_mbx << 1); 890 ps_dec->p_top_ctxt_mb_info = ps_dec->ps_curr_ctxt_mb_info; 891 892 if(u1_topmb) 893 { 894 pu1_left_mv_ctxt_inc_2d = ps_dec->u1_left_mv_ctxt_inc_arr[0]; 895 pi1_left_ref_idx_ctxt_inc = &ps_dec->i1_left_ref_idx_ctx_inc_arr[0][0]; 896 ps_dec->pu1_left_yuv_dc_csbp = &ps_dec->u1_yuv_dc_csbp_topmb; 897 } 898 else 899 { 900 /* uc_botMb */ 901 pu1_left_mv_ctxt_inc_2d = ps_dec->u1_left_mv_ctxt_inc_arr[1]; 902 pi1_left_ref_idx_ctxt_inc = &ps_dec->i1_left_ref_idx_ctx_inc_arr[1][0]; 903 ps_dec->pu1_left_yuv_dc_csbp = &ps_dec->u1_yuv_dc_csbp_bot_mb; 904 ps_dec->ps_curr_ctxt_mb_info += 1; 905 } 906 907 ps_dec->pu1_left_mv_ctxt_inc = pu1_left_mv_ctxt_inc_2d; 908 ps_dec->pi1_left_ref_idx_ctxt_inc = pi1_left_ref_idx_ctxt_inc; 909 910 if(u1_mb_ngbr_availablity & LEFT_MB_AVAILABLE_MASK) 911 { 912 const UWORD8 u1_left_mb_fld_flag = ps_cur_mb_info->ps_left_mb->u1_mb_fld; 913 914 ps_leftMB = ps_dec->ps_curr_ctxt_mb_info - 2; 915 if(u1_left_mb_fld_flag != u1_cur_mb_fld_flag) 916 { 917 ctxt_inc_mb_info_t *ps_tempLeft; 918 UWORD8 u1_cbp_t, u1_cbp_b; 919 UWORD8 u1_cr_cpb; 920 921 ps_leftMB -= uc_botMb; 922 ps_tempLeft = ps_dec->ps_left_mb_ctxt_info; 923 ps_tempLeft->u1_mb_type = ps_leftMB->u1_mb_type; 924 ps_tempLeft->u1_intra_chroma_pred_mode = 925 ps_leftMB->u1_intra_chroma_pred_mode; 926 927 ps_tempLeft->u1_transform8x8_ctxt = ps_leftMB->u1_transform8x8_ctxt; 928 929 u1_cr_cpb = ps_leftMB->u1_cbp; 930 /*****************************************************************/ 931 /* reform RefIdx, CBP, MV and CBF ctxInc taking care of A and A+1*/ 932 /*****************************************************************/ 933 if(u1_cur_mb_fld_flag) 934 { 935 /* current MB is a FLD and left a FRM */ 936 UWORD8 (* const pu1_left_mv_ctxt_inc_2d_arr_top)[4] = 937 ps_dec->u1_left_mv_ctxt_inc_arr[0]; 938 UWORD8 (* const pu1_left_mv_ctxt_inc_2d_arr_bot)[4] = 939 ps_dec->u1_left_mv_ctxt_inc_arr[1]; 940 WORD8 (* const i1_left_ref_idx_ctxt_inc_arr_top) = 941 &ps_dec->i1_left_ref_idx_ctx_inc_arr[0][0]; 942 WORD8 (* const i1_left_ref_idx_ctxt_inc_arr_bot) = 943 &ps_dec->i1_left_ref_idx_ctx_inc_arr[1][0]; 944 945 u1_cbp_t = ps_leftMB->u1_cbp; 946 u1_cbp_b = (ps_leftMB + 1)->u1_cbp; 947 ps_tempLeft->u1_cbp = (u1_cbp_t & 0x02) 948 | ((u1_cbp_b & 0x02) << 2); 949 950 // set motionvectors as 951 // 0T = 0T 0B = 0T 952 // 1T = 2T 1B = 2T 953 // 2T = 0B 2B = 0B 954 // 3T = 2B 3B = 2B 955 if(u1_topmb) 956 { 957 /********************************************/ 958 /* Bottoms DC CBF = Top DC CBF */ 959 /********************************************/ 960 ps_dec->u1_yuv_dc_csbp_bot_mb = 961 ps_dec->u1_yuv_dc_csbp_topmb; 962 963 *(UWORD32 *)pu1_left_mv_ctxt_inc_2d[3] = 964 *(UWORD32 *)pu1_left_mv_ctxt_inc_2d_arr_bot[2]; 965 *(UWORD32 *)pu1_left_mv_ctxt_inc_2d[1] = 966 *(UWORD32 *)pu1_left_mv_ctxt_inc_2d_arr_top[2]; 967 *(UWORD32 *)pu1_left_mv_ctxt_inc_2d[2] = 968 *(UWORD32 *)pu1_left_mv_ctxt_inc_2d_arr_bot[0]; 969 *(UWORD32 *)pu1_left_mv_ctxt_inc_2d[0] = 970 *(UWORD32 *)pu1_left_mv_ctxt_inc_2d_arr_top[0]; 971 972 i1_left_ref_idx_ctxt_inc_arr_top[1] = 973 i1_left_ref_idx_ctxt_inc_arr_bot[0]; 974 i1_left_ref_idx_ctxt_inc_arr_top[3] = 975 i1_left_ref_idx_ctxt_inc_arr_bot[2]; 976 977 *(UWORD32 *)(i1_left_ref_idx_ctxt_inc_arr_bot) = 978 *(UWORD32 *)(i1_left_ref_idx_ctxt_inc_arr_top); 979 980 memcpy(pu1_left_mv_ctxt_inc_2d_arr_bot, 981 pu1_left_mv_ctxt_inc_2d_arr_top, 16); 982 } 983 984 { 985 UWORD8 i; 986 for(i = 0; i < 4; i++) 987 { 988 pu1_left_mv_ctxt_inc_2d[i][1] >>= 1; 989 pu1_left_mv_ctxt_inc_2d[i][3] >>= 1; 990 } 991 } 992 } 993 else 994 { 995 /* current MB is a FRM and left FLD */ 996 if(u1_topmb) 997 { 998 u1_cbp_t = ps_leftMB->u1_cbp; 999 u1_cbp_t = (u1_cbp_t & 0x02); 1000 ps_tempLeft->u1_cbp = (u1_cbp_t | (u1_cbp_t << 2)); 1001 1002 /********************************************/ 1003 /* Bottoms DC CBF = Top DC CBF */ 1004 /********************************************/ 1005 ps_dec->u1_yuv_dc_csbp_bot_mb = 1006 ps_dec->u1_yuv_dc_csbp_topmb; 1007 1008 // set motionvectors as 1009 // 3B = 2B = 3T 1010 // 1B = 0B = 2T 1011 // 3T = 2T = 1T 1012 // 1T = 0T = 0T 1013 1014 *(UWORD32 *)pu1_left_mv_ctxt_inc_2d[7] = 1015 *(UWORD32 *)pu1_left_mv_ctxt_inc_2d[3]; 1016 *(UWORD32 *)pu1_left_mv_ctxt_inc_2d[6] = 1017 *(UWORD32 *)pu1_left_mv_ctxt_inc_2d[3]; 1018 1019 *(UWORD32 *)pu1_left_mv_ctxt_inc_2d[5] = 1020 *(UWORD32 *)pu1_left_mv_ctxt_inc_2d[2]; 1021 *(UWORD32 *)pu1_left_mv_ctxt_inc_2d[4] = 1022 *(UWORD32 *)pu1_left_mv_ctxt_inc_2d[2]; 1023 1024 *(UWORD32 *)pu1_left_mv_ctxt_inc_2d[3] = 1025 *(UWORD32 *)pu1_left_mv_ctxt_inc_2d[1]; 1026 *(UWORD32 *)pu1_left_mv_ctxt_inc_2d[2] = 1027 *(UWORD32 *)pu1_left_mv_ctxt_inc_2d[1]; 1028 1029 *(UWORD32 *)pu1_left_mv_ctxt_inc_2d[1] = 1030 *(UWORD32 *)pu1_left_mv_ctxt_inc_2d[0]; 1031 1032 pi1_left_ref_idx_ctxt_inc[7] = (pi1_left_ref_idx_ctxt_inc[3] 1033 - 1); 1034 pi1_left_ref_idx_ctxt_inc[6] = (pi1_left_ref_idx_ctxt_inc[3] 1035 - 1); 1036 1037 pi1_left_ref_idx_ctxt_inc[5] = (pi1_left_ref_idx_ctxt_inc[1] 1038 - 1); 1039 pi1_left_ref_idx_ctxt_inc[4] = (pi1_left_ref_idx_ctxt_inc[1] 1040 - 1); 1041 1042 pi1_left_ref_idx_ctxt_inc[3] = (pi1_left_ref_idx_ctxt_inc[2] 1043 - 1); 1044 pi1_left_ref_idx_ctxt_inc[2] = (pi1_left_ref_idx_ctxt_inc[2] 1045 - 1); 1046 1047 pi1_left_ref_idx_ctxt_inc[1] = (pi1_left_ref_idx_ctxt_inc[0] 1048 - 1); 1049 pi1_left_ref_idx_ctxt_inc[0] = (pi1_left_ref_idx_ctxt_inc[0] 1050 - 1); 1051 } 1052 else 1053 { 1054 u1_cbp_t = ps_leftMB->u1_cbp; 1055 u1_cbp_t = (u1_cbp_t & 0x08); 1056 ps_tempLeft->u1_cbp = (u1_cbp_t | (u1_cbp_t >> 2)); 1057 } 1058 1059 { 1060 UWORD8 i; 1061 for(i = 0; i < 4; i++) 1062 { 1063 pu1_left_mv_ctxt_inc_2d[i][1] <<= 1; 1064 pu1_left_mv_ctxt_inc_2d[i][3] <<= 1; 1065 } 1066 } 1067 1068 } 1069 1070 ps_tempLeft->u1_cbp = ps_tempLeft->u1_cbp + ((u1_cr_cpb >> 4) << 4); 1071 ps_leftMB = ps_tempLeft; 1072 } 1073 1074 ps_dec->p_left_ctxt_mb_info = ps_leftMB; 1075 } 1076 else 1077 { 1078 ps_dec->p_left_ctxt_mb_info = p_ctx_inc_mb_map - 1; 1079 if(!u4_mbskip) 1080 { 1081 *(ps_dec->pu1_left_yuv_dc_csbp) = 0; 1082 1083 MEMSET_16BYTES(&pu1_left_mv_ctxt_inc_2d[0][0], 0); 1084 *(UWORD32 *)pi1_left_ref_idx_ctxt_inc = 0; 1085 } 1086 } 1087 1088 /*************************************************************************/ 1089 /* Now get the top context mb info */ 1090 /*************************************************************************/ 1091 { 1092 UWORD8 (*u1_top_mv_ctxt_inc_arr_2d)[4] = 1093 ps_dec->ps_curr_ctxt_mb_info->u1_mv; 1094 WORD8 (*pi1_top_ref_idx_ctxt_inc) = 1095 ps_dec->ps_curr_ctxt_mb_info->i1_ref_idx; 1096 UWORD8 uc_topMbFldDecFlag = ps_cur_mb_info->ps_top_mb->u1_mb_fld; 1097 1098 if(u1_mb_ngbr_availablity & TOP_MB_AVAILABLE_MASK) 1099 { 1100 if(ps_cur_mb_info->i1_offset) 1101 ps_dec->p_top_ctxt_mb_info += 1; 1102 1103 if(!u4_mbskip) 1104 { 1105 memcpy(u1_top_mv_ctxt_inc_arr_2d, 1106 &ps_dec->p_top_ctxt_mb_info->u1_mv, 16); 1107 memcpy(pi1_top_ref_idx_ctxt_inc, 1108 &ps_dec->p_top_ctxt_mb_info->i1_ref_idx, 4); 1109 if(uc_topMbFldDecFlag ^ u1_cur_mb_fld_flag) 1110 { 1111 UWORD8 i; 1112 if(u1_cur_mb_fld_flag) 1113 { 1114 for(i = 0; i < 4; i++) 1115 { 1116 u1_top_mv_ctxt_inc_arr_2d[i][1] >>= 1; 1117 u1_top_mv_ctxt_inc_arr_2d[i][3] >>= 1; 1118 } 1119 } 1120 else 1121 { 1122 for(i = 0; i < 4; i++) 1123 { 1124 u1_top_mv_ctxt_inc_arr_2d[i][1] <<= 1; 1125 u1_top_mv_ctxt_inc_arr_2d[i][3] <<= 1; 1126 pi1_top_ref_idx_ctxt_inc[i] -= 1; 1127 } 1128 } 1129 } 1130 } 1131 } 1132 else 1133 { 1134 ps_dec->p_top_ctxt_mb_info = p_ctx_inc_mb_map - 1; 1135 if(!u4_mbskip) 1136 { 1137 1138 MEMSET_16BYTES(&u1_top_mv_ctxt_inc_arr_2d[0][0], 0); 1139 memset(pi1_top_ref_idx_ctxt_inc, 0, 4); 1140 } 1141 } 1142 } 1143 1144 return OK; 1145 } 1146 1147 /*****************************************************************************/ 1148 /* */ 1149 /* Function Name : ih264d_update_mbaff_left_nnz */ 1150 /* */ 1151 /* Description : This function updates the left luma and chroma nnz for */ 1152 /* mbaff cases. */ 1153 /* */ 1154 /* Inputs : <What inputs does the function take?> */ 1155 /* Globals : <Does it use any global variables?> */ 1156 /* Processing : <Describe how the function operates - include algorithm */ 1157 /* description> */ 1158 /* Outputs : <What does the function produce?> */ 1159 /* Returns : <What does the function return?> */ 1160 /* */ 1161 /* Issues : <List any issues or problems with this function> */ 1162 /* */ 1163 /* Revision History: */ 1164 /* */ 1165 /* DD MM YYYY Author(s) Changes (Describe the changes made) */ 1166 /* 13 07 2002 Ittiam Draft */ 1167 /* */ 1168 /*****************************************************************************/ 1169 void ih264d_update_mbaff_left_nnz(dec_struct_t * ps_dec, 1170 dec_mb_info_t * ps_cur_mb_info) 1171 { 1172 UWORD32 *pu4_buf; 1173 UWORD8 *pu1_buf; 1174 if(ps_cur_mb_info->u1_topmb) 1175 { 1176 pu1_buf = ps_dec->pu1_left_nnz_y; 1177 pu4_buf = (UWORD32 *)pu1_buf; 1178 ps_dec->u4_n_left_temp_y = *pu4_buf; 1179 1180 pu1_buf = ps_dec->pu1_left_nnz_uv; 1181 pu4_buf = (UWORD32 *)pu1_buf; 1182 ps_dec->u4_n_left_temp_uv = *pu4_buf; 1183 } 1184 else 1185 { 1186 1187 ps_dec->u4_n_leftY[0] = ps_dec->u4_n_left_temp_y; 1188 pu1_buf = ps_dec->pu1_left_nnz_y; 1189 pu4_buf = (UWORD32 *)pu1_buf; 1190 ps_dec->u4_n_leftY[1] = *pu4_buf; 1191 ps_dec->u4_n_left_cr[0] = ps_dec->u4_n_left_temp_uv; 1192 pu1_buf = ps_dec->pu1_left_nnz_uv; 1193 pu4_buf = (UWORD32 *)pu1_buf; 1194 ps_dec->u4_n_left_cr[1] = *pu4_buf; 1195 1196 } 1197 } 1198 1199 /*! 1200 ************************************************************************** 1201 * \if Function name : ih264d_get_mbaff_neighbours \endif 1202 * 1203 * \brief 1204 * Gets the neighbors for the current MB if it is of type MB-AFF 1205 * frame. 1206 * 1207 * \return 1208 * None 1209 * 1210 ************************************************************************** 1211 */ 1212 void ih264d_get_mbaff_neighbours(dec_struct_t * ps_dec, 1213 dec_mb_info_t * ps_cur_mb_info, 1214 UWORD8 uc_curMbFldDecFlag) 1215 { 1216 1217 mb_neigbour_params_t *ps_left_mb; 1218 mb_neigbour_params_t *ps_top_mb; 1219 mb_neigbour_params_t *ps_top_right_mb = NULL; 1220 mb_neigbour_params_t *ps_curmb; 1221 const UWORD8 u1_topmb = ps_cur_mb_info->u1_topmb; 1222 const UWORD8 uc_botMb = 1 - u1_topmb; 1223 const UWORD32 u4_mb_x = ps_cur_mb_info->u2_mbx; 1224 1225 /* Current MbParams location in top row buffer */ 1226 ps_curmb = ps_dec->ps_cur_mb_row + (u4_mb_x << 1) + uc_botMb; 1227 ps_left_mb = ps_curmb - 2; 1228 /* point to A if top else A+1 */ 1229 if(uc_botMb && (ps_left_mb->u1_mb_fld != uc_curMbFldDecFlag)) 1230 { 1231 /* move from A + 1 to A */ 1232 ps_left_mb--; 1233 } 1234 ps_cur_mb_info->i1_offset = 0; 1235 if((uc_curMbFldDecFlag == 0) && uc_botMb) 1236 { 1237 mb_neigbour_params_t *ps_topleft_mb; 1238 /* CurMbAddr - 1 */ 1239 ps_top_mb = ps_curmb - 1; 1240 1241 /* Mark Top right Not available */ 1242 /* point to A */ 1243 ps_topleft_mb = ps_curmb - 3; 1244 1245 if(ps_topleft_mb->u1_mb_fld) 1246 { 1247 /* point to A + 1 */ 1248 ps_topleft_mb++; 1249 } 1250 ps_cur_mb_info->u1_topleft_mb_fld = ps_topleft_mb->u1_mb_fld; 1251 ps_cur_mb_info->u1_topleft_mbtype = ps_topleft_mb->u1_mb_type; 1252 } 1253 else 1254 { 1255 /* Top = B + 1 */ 1256 ps_top_mb = ps_dec->ps_top_mb_row + (u4_mb_x << 1) + 1; 1257 ps_top_right_mb = ps_top_mb + 2; 1258 ps_cur_mb_info->i1_offset = 4; 1259 /* TopRight = C + 1 */ 1260 1261 /* TopLeft = D+1 */ 1262 ps_cur_mb_info->u1_topleft_mb_fld = ps_dec->u1_topleft_mb_fld_bot; 1263 ps_cur_mb_info->u1_topleft_mbtype = ps_dec->u1_topleft_mbtype_bot; 1264 1265 if(uc_curMbFldDecFlag && u1_topmb) 1266 { 1267 if(ps_top_mb->u1_mb_fld) 1268 { 1269 /* MbAddrB */ 1270 ps_top_mb--; 1271 ps_cur_mb_info->i1_offset = 0; 1272 } 1273 /* If topright is field then point to C */ 1274 ps_top_right_mb -= ps_top_right_mb->u1_mb_fld ? 1 : 0; 1275 if(ps_cur_mb_info->u1_topleft_mb_fld) 1276 { 1277 /* TopLeft = D */ 1278 ps_cur_mb_info->u1_topleft_mb_fld = ps_dec->u1_topleft_mb_fld; 1279 ps_cur_mb_info->u1_topleft_mbtype = ps_dec->u1_topleft_mbtype; 1280 } 1281 } 1282 } 1283 if(u1_topmb) 1284 { 1285 /* Update the parameters of topleftmb*/ 1286 ps_dec->u1_topleft_mb_fld = ps_top_mb->u1_mb_fld; 1287 ps_dec->u1_topleft_mbtype = ps_top_mb->u1_mb_type; 1288 /* Set invscan and dequantMatrixScan*/ 1289 if(uc_curMbFldDecFlag) 1290 { 1291 ps_dec->pu1_inv_scan = (UWORD8 *)gau1_ih264d_inv_scan_fld; 1292 } 1293 else 1294 { 1295 ps_dec->pu1_inv_scan = (UWORD8 *)gau1_ih264d_inv_scan; 1296 } 1297 ps_dec->pu2_quant_scale_y = 1298 gau2_ih264_iquant_scale_4x4[ps_dec->u1_qp_y_rem6]; 1299 ps_dec->pu2_quant_scale_u = 1300 gau2_ih264_iquant_scale_4x4[ps_dec->u1_qp_u_rem6]; 1301 ps_dec->pu2_quant_scale_v = 1302 gau2_ih264_iquant_scale_4x4[ps_dec->u1_qp_v_rem6]; 1303 1304 } 1305 else 1306 { 1307 /* Update the parameters of topleftmb*/ 1308 mb_neigbour_params_t *ps_top_mb_temp = ps_dec->ps_top_mb_row 1309 + (u4_mb_x << 1) + 1; 1310 ps_dec->u1_topleft_mb_fld_bot = ps_top_mb_temp->u1_mb_fld; 1311 ps_dec->u1_topleft_mbtype_bot = ps_top_mb_temp->u1_mb_type; 1312 } 1313 1314 ps_cur_mb_info->ps_left_mb = ps_left_mb; 1315 ps_cur_mb_info->ps_top_mb = ps_top_mb; 1316 ps_cur_mb_info->ps_top_right_mb = ps_top_right_mb; 1317 ps_cur_mb_info->ps_curmb = ps_curmb; 1318 ps_curmb->u1_mb_fld = uc_curMbFldDecFlag; 1319 1320 { 1321 /* Form Left NNZ */ 1322 UWORD8 u1_is_left_mb_fld = ps_left_mb->u1_mb_fld; 1323 UWORD8 *pu1_left_mb_pair_nnz_y = (UWORD8 *)&ps_dec->u4_n_leftY[0]; 1324 UWORD8 *pu1_left_mb_pair_nnz_uv = (UWORD8 *)&ps_dec->u4_n_left_cr[0]; 1325 UWORD8 *pu1_left_nnz_y = ps_dec->pu1_left_nnz_y; 1326 UWORD8 *pu1_left_nnz_uv = ps_dec->pu1_left_nnz_uv; 1327 1328 if(uc_curMbFldDecFlag == u1_is_left_mb_fld) 1329 { 1330 *(UWORD32 *)pu1_left_nnz_y = *(UWORD32 *)(pu1_left_mb_pair_nnz_y 1331 + (uc_botMb << 2)); 1332 *(UWORD32 *)pu1_left_nnz_uv = *(UWORD32 *)(pu1_left_mb_pair_nnz_uv 1333 + (uc_botMb << 2)); 1334 } 1335 else if((uc_curMbFldDecFlag == 0) && u1_topmb && u1_is_left_mb_fld) 1336 { 1337 /* 0 0 1 1 of u4_n_leftY[0], 0 0 2 2 of u4_n_left_cr[0] */ 1338 pu1_left_nnz_y[0] = pu1_left_nnz_y[1] = pu1_left_mb_pair_nnz_y[0]; 1339 pu1_left_nnz_y[2] = pu1_left_nnz_y[3] = pu1_left_mb_pair_nnz_y[1]; 1340 pu1_left_nnz_uv[0] = pu1_left_nnz_uv[1] = 1341 pu1_left_mb_pair_nnz_uv[0]; 1342 pu1_left_nnz_uv[2] = pu1_left_nnz_uv[3] = 1343 pu1_left_mb_pair_nnz_uv[2]; 1344 } 1345 else if((uc_curMbFldDecFlag == 0) && uc_botMb && u1_is_left_mb_fld) 1346 { 1347 /* 2 2 3 3 of u4_n_leftY[0] , 1 1 3 3 of u4_n_left_cr[0] */ 1348 pu1_left_nnz_y[0] = pu1_left_nnz_y[1] = pu1_left_mb_pair_nnz_y[2]; 1349 pu1_left_nnz_y[2] = pu1_left_nnz_y[3] = pu1_left_mb_pair_nnz_y[3]; 1350 pu1_left_nnz_uv[0] = pu1_left_nnz_uv[1] = 1351 pu1_left_mb_pair_nnz_uv[1]; 1352 pu1_left_nnz_uv[2] = pu1_left_nnz_uv[3] = 1353 pu1_left_mb_pair_nnz_uv[3]; 1354 } 1355 else 1356 { 1357 /* 0 2 0 2 of u4_n_leftY[0], u4_n_leftY[1] */ 1358 pu1_left_nnz_y[0] = pu1_left_mb_pair_nnz_y[0]; 1359 pu1_left_nnz_y[1] = pu1_left_mb_pair_nnz_y[2]; 1360 pu1_left_nnz_y[2] = pu1_left_mb_pair_nnz_y[4 + 0]; 1361 pu1_left_nnz_y[3] = pu1_left_mb_pair_nnz_y[4 + 2]; 1362 1363 /* 0 of u4_n_left_cr[0] and 0 u4_n_left_cr[1] 1364 2 of u4_n_left_cr[0] and 2 u4_n_left_cr[1] */ 1365 pu1_left_nnz_uv[0] = pu1_left_mb_pair_nnz_uv[0]; 1366 pu1_left_nnz_uv[1] = pu1_left_mb_pair_nnz_uv[4 + 0]; 1367 pu1_left_nnz_uv[2] = pu1_left_mb_pair_nnz_uv[2]; 1368 pu1_left_nnz_uv[3] = pu1_left_mb_pair_nnz_uv[4 + 2]; 1369 } 1370 } 1371 } 1372 1373 /* 1374 ************************************************************************** 1375 * \if Function name : ih264d_transfer_mb_group_data \endif 1376 * 1377 * \brief 1378 * Transfer the Following things 1379 * N-Mb DeblkParams Data ( To Ext DeblkParams Buffer ) 1380 * N-Mb Recon Data ( To Ext Frame Buffer ) 1381 * N-Mb Intrapredline Data ( Updated Internally) 1382 * N-Mb MV Data ( To Ext MV Buffer ) 1383 * N-Mb MVTop/TopRight Data ( To Int MV Top Scratch Buffers) 1384 * 1385 * \return 1386 * None 1387 * 1388 ************************************************************************** 1389 */ 1390 void ih264d_transfer_mb_group_data(dec_struct_t * ps_dec, 1391 const UWORD8 u1_num_mbs, 1392 const UWORD8 u1_end_of_row, /* Cur n-Mb End of Row Flag */ 1393 const UWORD8 u1_end_of_row_next /* Next n-Mb End of Row Flag */ 1394 ) 1395 { 1396 dec_mb_info_t *ps_cur_mb_info = ps_dec->ps_nmb_info; 1397 tfr_ctxt_t *ps_trns_addr = &ps_dec->s_tran_addrecon; 1398 UWORD16 u2_mb_y; 1399 UWORD32 y_offset; 1400 UWORD32 u4_frame_stride; 1401 mb_neigbour_params_t *ps_temp; 1402 const UWORD8 u1_mbaff = ps_dec->ps_cur_slice->u1_mbaff_frame_flag; 1403 UNUSED(u1_end_of_row_next); 1404 1405 ps_trns_addr->pu1_dest_y += ps_trns_addr->u4_inc_y[u1_end_of_row]; 1406 ps_trns_addr->pu1_dest_u += ps_trns_addr->u4_inc_uv[u1_end_of_row]; 1407 ps_trns_addr->pu1_dest_v += ps_trns_addr->u4_inc_uv[u1_end_of_row]; 1408 1409 /* Swap top and current pointers */ 1410 if(u1_end_of_row) 1411 { 1412 1413 if(ps_dec->u1_separate_parse) 1414 { 1415 u2_mb_y = ps_dec->i2_dec_thread_mb_y; 1416 } 1417 else 1418 { 1419 ps_temp = ps_dec->ps_cur_mb_row; 1420 ps_dec->ps_cur_mb_row = ps_dec->ps_top_mb_row; 1421 ps_dec->ps_top_mb_row = ps_temp; 1422 1423 u2_mb_y = ps_dec->u2_mby + (1 + u1_mbaff); 1424 } 1425 1426 u4_frame_stride = ps_dec->u2_frm_wd_y 1427 << ps_dec->ps_cur_slice->u1_field_pic_flag; 1428 y_offset = (u2_mb_y * u4_frame_stride) << 4; 1429 ps_trns_addr->pu1_dest_y = ps_dec->s_cur_pic.pu1_buf1 + y_offset; 1430 1431 u4_frame_stride = ps_dec->u2_frm_wd_uv 1432 << ps_dec->ps_cur_slice->u1_field_pic_flag; 1433 y_offset = (u2_mb_y * u4_frame_stride) << 3; 1434 ps_trns_addr->pu1_dest_u = ps_dec->s_cur_pic.pu1_buf2 + y_offset; 1435 ps_trns_addr->pu1_dest_v = ps_dec->s_cur_pic.pu1_buf3 + y_offset; 1436 1437 ps_trns_addr->pu1_mb_y = ps_trns_addr->pu1_dest_y; 1438 ps_trns_addr->pu1_mb_u = ps_trns_addr->pu1_dest_u; 1439 ps_trns_addr->pu1_mb_v = ps_trns_addr->pu1_dest_v; 1440 } 1441 1442 /* 1443 * The Slice boundary is also a valid condition to transfer. So recalculate 1444 * the Left increment, in case the number of MBs is lesser than the 1445 * N MB value. u1_num_mbs will be equal to N of N MB if the entire N Mb is 1446 * decoded. 1447 */ 1448 ps_dec->s_tran_addrecon.u2_mv_left_inc = ((u1_num_mbs >> u1_mbaff) - 1) 1449 << (4 + u1_mbaff); 1450 ps_dec->s_tran_addrecon.u2_mv_top_left_inc = (u1_num_mbs << 2) - 1 1451 - (u1_mbaff << 2); 1452 1453 if(ps_dec->u1_separate_parse == 0) 1454 { 1455 /* reassign left MV and cur MV pointers */ 1456 ps_dec->ps_mv_left = ps_dec->ps_mv_cur 1457 + ps_dec->s_tran_addrecon.u2_mv_left_inc; 1458 1459 ps_dec->ps_mv_cur += (u1_num_mbs << 4); 1460 } 1461 1462 /* Increment deblock parameters pointer in external memory */ 1463 1464 if(ps_dec->u1_separate_parse == 0) 1465 { 1466 ps_dec->ps_deblk_mbn += u1_num_mbs; 1467 } 1468 1469 } 1470 1471