• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /* ------------------------------------------------------------------
2  * Copyright (C) 1998-2009 PacketVideo
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either
13  * express or implied.
14  * See the License for the specific language governing permissions
15  * and limitations under the License.
16  * -------------------------------------------------------------------
17  */
18 /* Note for optimization: syntax decoding or operations related to B_SLICE should be
19 commented out by macro definition or function pointers. */
20 
21 #include "oscl_mem.h"
22 #include "avcdec_lib.h"
23 #include "avcdec_bitstream.h"
24 
25 const static int mbPart2raster[3][4] = {{0, 0, 0, 0}, {1, 1, 0, 0}, {1, 0, 1, 0}};
26 /* decode_frame_slice() */
27 /* decode_one_slice() */
DecodeSlice(AVCDecObject * decvid)28 AVCDec_Status DecodeSlice(AVCDecObject *decvid)
29 {
30     AVCDec_Status status;
31     AVCCommonObj *video = decvid->common;
32     AVCSliceHeader *sliceHdr = video->sliceHdr;
33     AVCMacroblock *currMB ;
34     AVCDecBitstream *stream = decvid->bitstream;
35     uint slice_group_id;
36     uint CurrMbAddr, moreDataFlag;
37 
38     /* set the first mb in slice */
39     CurrMbAddr = sliceHdr->first_mb_in_slice;
40     slice_group_id = video->MbToSliceGroupMap[CurrMbAddr];
41 
42     if ((CurrMbAddr && (CurrMbAddr != (uint)(video->mbNum + 1))) && video->currSeqParams->constrained_set1_flag == 1)
43     {
44         ConcealSlice(decvid, video->mbNum, CurrMbAddr);
45     }
46 
47     moreDataFlag = 1;
48     video->mb_skip_run = -1;
49 
50 
51     /* while loop , see subclause 7.3.4 */
52     do
53     {
54         if (CurrMbAddr >= video->PicSizeInMbs)
55         {
56             return AVCDEC_FAIL;
57         }
58 
59         currMB = video->currMB = &(video->mblock[CurrMbAddr]);
60         video->mbNum = CurrMbAddr;
61         currMB->slice_id = video->slice_id;  //  slice
62 
63         /* we can remove this check if we don't support Mbaff. */
64         /* we can wrap below into an initMB() function which will also
65         do necessary reset of macroblock related parameters. */
66 
67         video->mb_x = CurrMbAddr % video->PicWidthInMbs;
68         video->mb_y = CurrMbAddr / video->PicWidthInMbs;
69 
70         /* check the availability of neighboring macroblocks */
71         InitNeighborAvailability(video, CurrMbAddr);
72 
73         /* read_macroblock and decode_one_macroblock() */
74         status = DecodeMB(decvid);
75         if (status != AVCDEC_SUCCESS)
76         {
77             return status;
78         }
79 #ifdef MB_BASED_DEBLOCK
80         if (video->currPicParams->num_slice_groups_minus1 == 0)
81         {
82             MBInLoopDeblock(video); /* MB-based deblocking */
83         }
84         else    /* this mode cannot be used if the number of slice group is not one. */
85         {
86             return AVCDEC_FAIL;
87         }
88 #endif
89         video->numMBs--;
90 
91         moreDataFlag = more_rbsp_data(stream);
92 
93 
94         /* go to next MB */
95         while (++CurrMbAddr < video->PicSizeInMbs && video->MbToSliceGroupMap[CurrMbAddr] != (int)slice_group_id)
96         {
97         }
98 
99     }
100     while ((moreDataFlag && video->numMBs > 0) || video->mb_skip_run > 0); /* even if no more data, but last few MBs are skipped */
101 
102     if (video->numMBs == 0)
103     {
104         video->newPic = TRUE;
105         video->mbNum = 0;  // _Conceal
106         return AVCDEC_PICTURE_READY;
107     }
108 
109     return AVCDEC_SUCCESS;
110 }
111 
112 /* read MB mode and motion vectors */
113 /* perform Intra/Inter prediction and residue */
114 /* update video->mb_skip_run */
DecodeMB(AVCDecObject * decvid)115 AVCDec_Status DecodeMB(AVCDecObject *decvid)
116 {
117     AVCDec_Status status;
118     AVCCommonObj *video = decvid->common;
119     AVCDecBitstream *stream = decvid->bitstream;
120     AVCMacroblock *currMB = video->currMB;
121     uint mb_type;
122     int slice_type = video->slice_type;
123     int temp;
124 
125     currMB->QPy = video->QPy;
126     currMB->QPc = video->QPc;
127 
128     if (slice_type == AVC_P_SLICE)
129     {
130         if (video->mb_skip_run < 0)
131         {
132             ue_v(stream, (uint *)&(video->mb_skip_run));
133         }
134 
135         if (video->mb_skip_run == 0)
136         {
137             /* this will not handle the case where the slice ends with a mb_skip_run == 0 and no following MB data  */
138             ue_v(stream, &mb_type);
139             if (mb_type > 30)
140             {
141                 return AVCDEC_FAIL;
142             }
143             InterpretMBModeP(currMB, mb_type);
144             video->mb_skip_run = -1;
145         }
146         else
147         {
148             /* see subclause 7.4.4 for more details on how
149             mb_field_decoding_flag is derived in case of skipped MB */
150 
151             currMB->mb_intra = FALSE;
152 
153             currMB->mbMode = AVC_SKIP;
154             currMB->MbPartWidth = currMB->MbPartHeight = 16;
155             currMB->NumMbPart = 1;
156             currMB->NumSubMbPart[0] = currMB->NumSubMbPart[1] =
157                                           currMB->NumSubMbPart[2] = currMB->NumSubMbPart[3] = 1; //
158             currMB->SubMbPartWidth[0] = currMB->SubMbPartWidth[1] =
159                                             currMB->SubMbPartWidth[2] = currMB->SubMbPartWidth[3] = currMB->MbPartWidth;
160             currMB->SubMbPartHeight[0] = currMB->SubMbPartHeight[1] =
161                                              currMB->SubMbPartHeight[2] = currMB->SubMbPartHeight[3] = currMB->MbPartHeight;
162 
163             oscl_memset(currMB->nz_coeff, 0, sizeof(uint8)*NUM_BLKS_IN_MB);
164 
165             currMB->CBP = 0;
166             video->cbp4x4 = 0;
167             /* for skipped MB, always look at the first entry in RefPicList */
168             currMB->RefIdx[0] = currMB->RefIdx[1] =
169                                     currMB->RefIdx[2] = currMB->RefIdx[3] = video->RefPicList0[0]->RefIdx;
170             InterMBPrediction(video);
171             video->mb_skip_run--;
172             return AVCDEC_SUCCESS;
173         }
174 
175     }
176     else
177     {
178         /* Then decode mode and MV */
179         ue_v(stream, &mb_type);
180         if (mb_type > 25)
181         {
182             return AVCDEC_FAIL;
183         }
184         InterpretMBModeI(currMB, mb_type);
185     }
186 
187 
188     if (currMB->mbMode != AVC_I_PCM)
189     {
190 
191         if (currMB->mbMode == AVC_P8 || currMB->mbMode == AVC_P8ref0)
192         {
193             status = sub_mb_pred(video, currMB, stream);
194         }
195         else
196         {
197             status = mb_pred(video, currMB, stream) ;
198         }
199 
200         if (status != AVCDEC_SUCCESS)
201         {
202             return status;
203         }
204 
205         if (currMB->mbMode != AVC_I16)
206         {
207             /* decode coded_block_pattern */
208             status = DecodeCBP(currMB, stream);
209             if (status != AVCDEC_SUCCESS)
210             {
211                 return status;
212             }
213         }
214 
215         if (currMB->CBP > 0 || currMB->mbMode == AVC_I16)
216         {
217             se_v(stream, &temp);
218             if (temp)
219             {
220                 temp += (video->QPy + 52);
221                 currMB->QPy = video->QPy = temp - 52 * (temp * 79 >> 12);
222                 if (currMB->QPy > 51 || currMB->QPy < 0)
223                 {
224                     video->QPy = AVC_CLIP3(0, 51, video->QPy);
225 //                  return AVCDEC_FAIL;
226                 }
227                 video->QPy_div_6 = (video->QPy * 43) >> 8;
228                 video->QPy_mod_6 = video->QPy - 6 * video->QPy_div_6;
229                 currMB->QPc = video->QPc = mapQPi2QPc[AVC_CLIP3(0, 51, video->QPy + video->currPicParams->chroma_qp_index_offset)];
230                 video->QPc_div_6 = (video->QPc * 43) >> 8;
231                 video->QPc_mod_6 = video->QPc - 6 * video->QPc_div_6;
232             }
233         }
234         /* decode residue and inverse transform */
235         status = residual(decvid, currMB);
236         if (status != AVCDEC_SUCCESS)
237         {
238             return status;
239         }
240     }
241     else
242     {
243         if (stream->bitcnt & 7)
244         {
245             BitstreamByteAlign(stream);
246         }
247         /* decode pcm_byte[i] */
248         DecodeIntraPCM(video, stream);
249 
250         currMB->QPy = 0;  /* necessary for deblocking */ // _OPTIMIZE
251         currMB->QPc = mapQPi2QPc[AVC_CLIP3(0, 51, video->currPicParams->chroma_qp_index_offset)];
252 
253         /* default values, don't know if really needed */
254         currMB->CBP = 0x3F;
255         video->cbp4x4 = 0xFFFF;
256         currMB->mb_intra = TRUE;
257         oscl_memset(currMB->nz_coeff, 16, sizeof(uint8)*NUM_BLKS_IN_MB);
258         return AVCDEC_SUCCESS;
259     }
260 
261 
262     /* do Intra/Inter prediction, together with the residue compensation */
263     /* This part should be common between the skip and no-skip */
264     if (currMB->mbMode == AVC_I4 || currMB->mbMode == AVC_I16)
265     {
266         IntraMBPrediction(video);
267     }
268     else
269     {
270         InterMBPrediction(video);
271     }
272 
273 
274 
275     return AVCDEC_SUCCESS;
276 }
277 
278 /* see subclause 7.3.5.1 */
mb_pred(AVCCommonObj * video,AVCMacroblock * currMB,AVCDecBitstream * stream)279 AVCDec_Status mb_pred(AVCCommonObj *video, AVCMacroblock *currMB, AVCDecBitstream *stream)
280 {
281     int mbPartIdx;
282     AVCSliceHeader *sliceHdr = video->sliceHdr;
283     uint max_ref_idx;
284     const int *temp_0;
285     int16 *temp_1;
286     uint code;
287 
288     if (currMB->mbMode == AVC_I4 || currMB->mbMode == AVC_I16)
289     {
290 
291         video->intraAvailA = video->intraAvailB = video->intraAvailC = video->intraAvailD = 0;
292 
293         if (!video->currPicParams->constrained_intra_pred_flag)
294         {
295             video->intraAvailA = video->mbAvailA;
296             video->intraAvailB = video->mbAvailB;
297             video->intraAvailC = video->mbAvailC;
298             video->intraAvailD = video->mbAvailD;
299         }
300         else
301         {
302             if (video->mbAvailA)
303             {
304                 video->intraAvailA = video->mblock[video->mbAddrA].mb_intra;
305             }
306             if (video->mbAvailB)
307             {
308                 video->intraAvailB = video->mblock[video->mbAddrB].mb_intra ;
309             }
310             if (video->mbAvailC)
311             {
312                 video->intraAvailC = video->mblock[video->mbAddrC].mb_intra;
313             }
314             if (video->mbAvailD)
315             {
316                 video->intraAvailD = video->mblock[video->mbAddrD].mb_intra;
317             }
318         }
319 
320 
321         if (currMB->mbMode == AVC_I4)
322         {
323             /* perform prediction to get the actual intra 4x4 pred mode */
324             DecodeIntra4x4Mode(video, currMB, stream);
325             /* output will be in currMB->i4Mode[4][4] */
326         }
327 
328         ue_v(stream, &code);
329 
330         if (code > 3)
331         {
332             return AVCDEC_FAIL; /* out of range */
333         }
334         currMB->intra_chroma_pred_mode = (AVCIntraChromaPredMode)code;
335     }
336     else
337     {
338 
339         oscl_memset(currMB->ref_idx_L0, 0, sizeof(int16)*4);
340 
341         /* see subclause 7.4.5.1 for the range of ref_idx_lX */
342 //      max_ref_idx = sliceHdr->num_ref_idx_l0_active_minus1;
343         max_ref_idx = video->refList0Size - 1;
344 
345         /* decode ref index for L0 */
346         if (sliceHdr->num_ref_idx_l0_active_minus1 > 0)
347         {
348             for (mbPartIdx = 0; mbPartIdx < currMB->NumMbPart; mbPartIdx++)
349             {
350                 te_v(stream, &code, max_ref_idx);
351                 if (code > (uint)max_ref_idx)
352                 {
353                     return AVCDEC_FAIL;
354                 }
355                 currMB->ref_idx_L0[mbPartIdx] = code;
356             }
357         }
358 
359         /* populate ref_idx_L0 */
360         temp_0 = &mbPart2raster[currMB->mbMode-AVC_P16][0];
361         temp_1 = &currMB->ref_idx_L0[3];
362 
363         *temp_1-- = currMB->ref_idx_L0[*temp_0++];
364         *temp_1-- = currMB->ref_idx_L0[*temp_0++];
365         *temp_1-- = currMB->ref_idx_L0[*temp_0++];
366         *temp_1-- = currMB->ref_idx_L0[*temp_0++];
367 
368         /* Global reference index, these values are used in deblock */
369         currMB->RefIdx[0] = video->RefPicList0[currMB->ref_idx_L0[0]]->RefIdx;
370         currMB->RefIdx[1] = video->RefPicList0[currMB->ref_idx_L0[1]]->RefIdx;
371         currMB->RefIdx[2] = video->RefPicList0[currMB->ref_idx_L0[2]]->RefIdx;
372         currMB->RefIdx[3] = video->RefPicList0[currMB->ref_idx_L0[3]]->RefIdx;
373 
374         /* see subclause 7.4.5.1 for the range of ref_idx_lX */
375         max_ref_idx = sliceHdr->num_ref_idx_l1_active_minus1;
376         /* decode mvd_l0 */
377         for (mbPartIdx = 0; mbPartIdx < currMB->NumMbPart; mbPartIdx++)
378         {
379             se_v(stream, &(video->mvd_l0[mbPartIdx][0][0]));
380             se_v(stream, &(video->mvd_l0[mbPartIdx][0][1]));
381         }
382     }
383 
384     return AVCDEC_SUCCESS;
385 }
386 
387 /* see subclause 7.3.5.2 */
sub_mb_pred(AVCCommonObj * video,AVCMacroblock * currMB,AVCDecBitstream * stream)388 AVCDec_Status sub_mb_pred(AVCCommonObj *video, AVCMacroblock *currMB, AVCDecBitstream *stream)
389 {
390     int mbPartIdx, subMbPartIdx;
391     AVCSliceHeader *sliceHdr = video->sliceHdr;
392     uint max_ref_idx;
393     uint sub_mb_type[4];
394     uint code;
395 
396     oscl_memset(currMB->ref_idx_L0, 0, sizeof(int16)*4);
397 
398     for (mbPartIdx = 0; mbPartIdx < 4; mbPartIdx++)
399     {
400         ue_v(stream, &(sub_mb_type[mbPartIdx]));
401         if (sub_mb_type[mbPartIdx] > 3)
402         {
403             return AVCDEC_FAIL;
404         }
405 
406     }
407     /* we have to check the values to make sure they are valid  */
408     /* assign values to currMB->sub_mb_type[], currMB->MBPartPredMode[][x] */
409 
410     InterpretSubMBModeP(currMB, sub_mb_type);
411 
412 
413     /* see subclause 7.4.5.1 for the range of ref_idx_lX */
414 //      max_ref_idx = sliceHdr->num_ref_idx_l0_active_minus1;
415     max_ref_idx = video->refList0Size - 1;
416 
417     if (sliceHdr->num_ref_idx_l0_active_minus1 > 0 && currMB->mbMode != AVC_P8ref0)
418     {
419         for (mbPartIdx = 0; mbPartIdx < 4; mbPartIdx++)
420         {
421             te_v(stream, (uint*)&code, max_ref_idx);
422             if (code > max_ref_idx)
423             {
424                 return AVCDEC_FAIL;
425             }
426             currMB->ref_idx_L0[mbPartIdx] = code;
427         }
428     }
429     /* see subclause 7.4.5.1 for the range of ref_idx_lX */
430 
431     max_ref_idx = sliceHdr->num_ref_idx_l1_active_minus1;
432     /*  if(video->MbaffFrameFlag && currMB->mb_field_decoding_flag)
433             max_ref_idx = 2*sliceHdr->num_ref_idx_l1_active_minus1 + 1;*/
434     for (mbPartIdx = 0; mbPartIdx < 4; mbPartIdx++)
435     {
436         for (subMbPartIdx = 0; subMbPartIdx < currMB->NumSubMbPart[mbPartIdx]; subMbPartIdx++)
437         {
438             se_v(stream, &(video->mvd_l0[mbPartIdx][subMbPartIdx][0]));
439             se_v(stream, &(video->mvd_l0[mbPartIdx][subMbPartIdx][1]));
440         }
441         /* used in deblocking */
442         currMB->RefIdx[mbPartIdx] = video->RefPicList0[currMB->ref_idx_L0[mbPartIdx]]->RefIdx;
443     }
444     return AVCDEC_SUCCESS;
445 }
446 
InterpretMBModeI(AVCMacroblock * mblock,uint mb_type)447 void InterpretMBModeI(AVCMacroblock *mblock, uint mb_type)
448 {
449     mblock->NumMbPart = 1;
450 
451     mblock->mb_intra = TRUE;
452 
453     if (mb_type == 0) /* I_4x4 */
454     {
455         mblock->mbMode = AVC_I4;
456     }
457     else if (mb_type < 25) /* I_PCM */
458     {
459         mblock->mbMode = AVC_I16;
460         mblock->i16Mode = (AVCIntra16x16PredMode)((mb_type - 1) & 0x3);
461         if (mb_type > 12)
462         {
463             mblock->CBP = (((mb_type - 13) >> 2) << 4) + 0x0F;
464         }
465         else
466         {
467             mblock->CBP = ((mb_type - 1) >> 2) << 4;
468         }
469     }
470     else
471     {
472         mblock->mbMode = AVC_I_PCM;
473     }
474 
475     return ;
476 }
477 
InterpretMBModeP(AVCMacroblock * mblock,uint mb_type)478 void InterpretMBModeP(AVCMacroblock *mblock, uint mb_type)
479 {
480     const static int map2PartWidth[5] = {16, 16, 8, 8, 8};
481     const static int map2PartHeight[5] = {16, 8, 16, 8, 8};
482     const static int map2NumPart[5] = {1, 2, 2, 4, 4};
483     const static AVCMBMode map2mbMode[5] = {AVC_P16, AVC_P16x8, AVC_P8x16, AVC_P8, AVC_P8ref0};
484 
485     mblock->mb_intra = FALSE;
486     if (mb_type < 5)
487     {
488         mblock->mbMode = map2mbMode[mb_type];
489         mblock->MbPartWidth = map2PartWidth[mb_type];
490         mblock->MbPartHeight = map2PartHeight[mb_type];
491         mblock->NumMbPart = map2NumPart[mb_type];
492         mblock->NumSubMbPart[0] = mblock->NumSubMbPart[1] =
493                                       mblock->NumSubMbPart[2] = mblock->NumSubMbPart[3] = 1;
494         mblock->SubMbPartWidth[0] = mblock->SubMbPartWidth[1] =
495                                         mblock->SubMbPartWidth[2] = mblock->SubMbPartWidth[3] = mblock->MbPartWidth;
496         mblock->SubMbPartHeight[0] = mblock->SubMbPartHeight[1] =
497                                          mblock->SubMbPartHeight[2] = mblock->SubMbPartHeight[3] = mblock->MbPartHeight;
498     }
499     else
500     {
501         InterpretMBModeI(mblock, mb_type - 5);
502         /* set MV and Ref_Idx codes of Intra blocks in P-slices  */
503         oscl_memset(mblock->mvL0, 0, sizeof(int32)*16);
504         mblock->ref_idx_L0[0] = mblock->ref_idx_L0[1] = mblock->ref_idx_L0[2] = mblock->ref_idx_L0[3] = -1;
505     }
506     return ;
507 }
508 
InterpretMBModeB(AVCMacroblock * mblock,uint mb_type)509 void InterpretMBModeB(AVCMacroblock *mblock, uint mb_type)
510 {
511     const static int map2PartWidth[23] = {8, 16, 16, 16, 16, 8, 16, 8, 16, 8,
512                                           16, 8, 16, 8, 16, 8, 16, 8, 16, 8, 16, 8, 8
513                                          };
514     const static int map2PartHeight[23] = {8, 16, 16, 16, 8, 16, 8, 16, 8,
515                                            16, 8, 16, 8, 16, 8, 16, 8, 16, 8, 16, 8, 16, 8
516                                           };
517     /* see enum AVCMBType declaration */
518     const static AVCMBMode map2mbMode[23] = {AVC_BDirect16, AVC_P16, AVC_P16, AVC_P16,
519                                             AVC_P16x8, AVC_P8x16, AVC_P16x8, AVC_P8x16, AVC_P16x8, AVC_P8x16,
520                                             AVC_P16x8, AVC_P8x16, AVC_P16x8, AVC_P8x16, AVC_P16x8, AVC_P8x16,
521                                             AVC_P16x8, AVC_P8x16, AVC_P16x8, AVC_P8x16, AVC_P16x8, AVC_P8x16, AVC_P8
522                                             };
523     const static int map2PredMode1[23] = {3, 0, 1, 2, 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 1, 1, 2, 2, 2, 2, 2, 2, -1};
524     const static int map2PredMode2[23] = { -1, -1, -1, -1, 0, 0, 1, 1, 1, 1, 0, 0, 2, 2, 2, 2, 0, 0, 1, 1, 2, 2, -1};
525     const static int map2NumPart[23] = { -1, 1, 1, 1, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 4};
526 
527     mblock->mb_intra = FALSE;
528 
529     if (mb_type < 23)
530     {
531         mblock->mbMode = map2mbMode[mb_type];
532         mblock->NumMbPart = map2NumPart[mb_type];
533         mblock->MBPartPredMode[0][0] = (AVCPredMode)map2PredMode1[mb_type];
534         if (mblock->NumMbPart > 1)
535         {
536             mblock->MBPartPredMode[1][0] = (AVCPredMode)map2PredMode2[mb_type];
537         }
538         mblock->MbPartWidth = map2PartWidth[mb_type];
539         mblock->MbPartHeight = map2PartHeight[mb_type];
540     }
541     else
542     {
543         InterpretMBModeI(mblock, mb_type - 23);
544     }
545 
546     return ;
547 }
548 
InterpretMBModeSI(AVCMacroblock * mblock,uint mb_type)549 void InterpretMBModeSI(AVCMacroblock *mblock, uint mb_type)
550 {
551     mblock->mb_intra = TRUE;
552 
553     if (mb_type == 0)
554     {
555         mblock->mbMode = AVC_SI4;
556         /* other values are N/A */
557     }
558     else
559     {
560         InterpretMBModeI(mblock, mb_type - 1);
561     }
562     return ;
563 }
564 
565 /* input is mblock->sub_mb_type[] */
InterpretSubMBModeP(AVCMacroblock * mblock,uint * sub_mb_type)566 void InterpretSubMBModeP(AVCMacroblock *mblock, uint *sub_mb_type)
567 {
568     int i,  sub_type;
569     /* see enum AVCMBType declaration */
570 //  const static AVCSubMBMode map2subMbMode[4] = {AVC_8x8,AVC_8x4,AVC_4x8,AVC_4x4};
571     const static int map2subPartWidth[4] = {8, 8, 4, 4};
572     const static int map2subPartHeight[4] = {8, 4, 8, 4};
573     const static int map2numSubPart[4] = {1, 2, 2, 4};
574 
575     for (i = 0; i < 4 ; i++)
576     {
577         sub_type = (int) sub_mb_type[i];
578         //  mblock->subMbMode[i] = map2subMbMode[sub_type];
579         mblock->NumSubMbPart[i] = map2numSubPart[sub_type];
580         mblock->SubMbPartWidth[i] = map2subPartWidth[sub_type];
581         mblock->SubMbPartHeight[i] = map2subPartHeight[sub_type];
582     }
583 
584     return ;
585 }
586 
InterpretSubMBModeB(AVCMacroblock * mblock,uint * sub_mb_type)587 void InterpretSubMBModeB(AVCMacroblock *mblock, uint *sub_mb_type)
588 {
589     int i, j, sub_type;
590     /* see enum AVCMBType declaration */
591     const static AVCSubMBMode map2subMbMode[13] = {AVC_BDirect8, AVC_8x8, AVC_8x8,
592             AVC_8x8, AVC_8x4, AVC_4x8, AVC_8x4, AVC_4x8, AVC_8x4, AVC_4x8, AVC_4x4, AVC_4x4, AVC_4x4
593                                                   };
594     const static int map2subPartWidth[13] = {4, 8, 8, 8, 8, 4, 8, 4, 8, 4, 4, 4, 4};
595     const static int map2subPartHeight[13] = {4, 8, 8, 8, 4, 8, 4, 8, 4, 8, 4, 4, 4};
596     const static int map2numSubPart[13] = {1, 1, 1, 2, 2, 2, 2, 2, 2, 4, 4, 4};
597     const static int map2predMode[13] = {3, 0, 1, 2, 0, 0, 1, 1, 2, 2, 0, 1, 2};
598 
599     for (i = 0; i < 4 ; i++)
600     {
601         sub_type = (int) sub_mb_type[i];
602         mblock->subMbMode[i] = map2subMbMode[sub_type];
603         mblock->NumSubMbPart[i] = map2numSubPart[sub_type];
604         mblock->SubMbPartWidth[i] = map2subPartWidth[sub_type];
605         mblock->SubMbPartHeight[i] = map2subPartHeight[sub_type];
606         for (j = 0; j < 4; j++)
607         {
608             mblock->MBPartPredMode[i][j] = (AVCPredMode)map2predMode[sub_type];
609         }
610     }
611 
612     return ;
613 }
614 
615 /* see subclause 8.3.1 */
DecodeIntra4x4Mode(AVCCommonObj * video,AVCMacroblock * currMB,AVCDecBitstream * stream)616 AVCDec_Status DecodeIntra4x4Mode(AVCCommonObj *video, AVCMacroblock *currMB, AVCDecBitstream *stream)
617 {
618     int intra4x4PredModeA = 0, intra4x4PredModeB = 0, predIntra4x4PredMode = 0;
619     int component, SubBlock_indx, block_x, block_y;
620     int dcOnlyPredictionFlag;
621     uint    prev_intra4x4_pred_mode_flag[16];
622     int     rem_intra4x4_pred_mode[16];
623     int bindx = 0;
624 
625     for (component = 0; component < 4; component++) /* partition index */
626     {
627         block_x = ((component & 1) << 1);
628         block_y = ((component >> 1) << 1);
629 
630         for (SubBlock_indx = 0; SubBlock_indx < 4; SubBlock_indx++) /* sub-partition index */
631         {
632             BitstreamRead1Bit(stream, &(prev_intra4x4_pred_mode_flag[bindx]));
633 
634             if (!prev_intra4x4_pred_mode_flag[bindx])
635             {
636                 BitstreamReadBits(stream, 3, (uint*)&(rem_intra4x4_pred_mode[bindx]));
637             }
638 
639             dcOnlyPredictionFlag = 0;
640             if (block_x > 0)
641             {
642                 intra4x4PredModeA = currMB->i4Mode[(block_y << 2) + block_x - 1 ];
643             }
644             else
645             {
646                 if (video->intraAvailA)
647                 {
648                     if (video->mblock[video->mbAddrA].mbMode == AVC_I4)
649                     {
650                         intra4x4PredModeA = video->mblock[video->mbAddrA].i4Mode[(block_y << 2) + 3];
651                     }
652                     else
653                     {
654                         intra4x4PredModeA = AVC_I4_DC;
655                     }
656                 }
657                 else
658                 {
659                     dcOnlyPredictionFlag = 1;
660                 }
661             }
662 
663             if (block_y > 0)
664             {
665                 intra4x4PredModeB = currMB->i4Mode[((block_y-1) << 2) + block_x];
666             }
667             else
668             {
669                 if (video->intraAvailB)
670                 {
671                     if (video->mblock[video->mbAddrB].mbMode == AVC_I4)
672                     {
673                         intra4x4PredModeB = video->mblock[video->mbAddrB].i4Mode[(3 << 2) + block_x];
674                     }
675                     else
676                     {
677                         intra4x4PredModeB = AVC_I4_DC;
678                     }
679                 }
680                 else
681                 {
682                     dcOnlyPredictionFlag = 1;
683                 }
684             }
685 
686             if (dcOnlyPredictionFlag)
687             {
688                 intra4x4PredModeA = intra4x4PredModeB = AVC_I4_DC;
689             }
690 
691             predIntra4x4PredMode = AVC_MIN(intra4x4PredModeA, intra4x4PredModeB);
692             if (prev_intra4x4_pred_mode_flag[bindx])
693             {
694                 currMB->i4Mode[(block_y<<2)+block_x] = (AVCIntra4x4PredMode)predIntra4x4PredMode;
695             }
696             else
697             {
698                 if (rem_intra4x4_pred_mode[bindx] < predIntra4x4PredMode)
699                 {
700                     currMB->i4Mode[(block_y<<2)+block_x] = (AVCIntra4x4PredMode)rem_intra4x4_pred_mode[bindx];
701                 }
702                 else
703                 {
704                     currMB->i4Mode[(block_y<<2)+block_x] = (AVCIntra4x4PredMode)(rem_intra4x4_pred_mode[bindx] + 1);
705                 }
706             }
707             bindx++;
708             block_y += (SubBlock_indx & 1) ;
709             block_x += (1 - 2 * (SubBlock_indx & 1)) ;
710         }
711     }
712     return AVCDEC_SUCCESS;
713 }
ConcealSlice(AVCDecObject * decvid,int mbnum_start,int mbnum_end)714 AVCDec_Status ConcealSlice(AVCDecObject *decvid, int mbnum_start, int mbnum_end)
715 {
716     AVCCommonObj *video = decvid->common;
717     AVCMacroblock *currMB ;
718 
719     int CurrMbAddr;
720 
721     if (video->RefPicList0[0] == NULL)
722     {
723         return AVCDEC_FAIL;
724     }
725 
726     for (CurrMbAddr = mbnum_start; CurrMbAddr < mbnum_end; CurrMbAddr++)
727     {
728         currMB = video->currMB = &(video->mblock[CurrMbAddr]);
729         video->mbNum = CurrMbAddr;
730         currMB->slice_id = video->slice_id++;  //  slice
731 
732         /* we can remove this check if we don't support Mbaff. */
733         /* we can wrap below into an initMB() function which will also
734         do necessary reset of macroblock related parameters. */
735 
736         video->mb_x = CurrMbAddr % video->PicWidthInMbs;
737         video->mb_y = CurrMbAddr / video->PicWidthInMbs;
738 
739         /* check the availability of neighboring macroblocks */
740         InitNeighborAvailability(video, CurrMbAddr);
741 
742         currMB->mb_intra = FALSE;
743 
744         currMB->mbMode = AVC_SKIP;
745         currMB->MbPartWidth = currMB->MbPartHeight = 16;
746 
747         currMB->NumMbPart = 1;
748         currMB->NumSubMbPart[0] = currMB->NumSubMbPart[1] =
749                                       currMB->NumSubMbPart[2] = currMB->NumSubMbPart[3] = 1;
750         currMB->SubMbPartWidth[0] = currMB->SubMbPartWidth[1] =
751                                         currMB->SubMbPartWidth[2] = currMB->SubMbPartWidth[3] = currMB->MbPartWidth;
752         currMB->SubMbPartHeight[0] = currMB->SubMbPartHeight[1] =
753                                          currMB->SubMbPartHeight[2] = currMB->SubMbPartHeight[3] = currMB->MbPartHeight;
754         currMB->QPy = 26;
755         currMB->QPc = 26;
756         oscl_memset(currMB->nz_coeff, 0, sizeof(uint8)*NUM_BLKS_IN_MB);
757 
758         currMB->CBP = 0;
759         video->cbp4x4 = 0;
760         /* for skipped MB, always look at the first entry in RefPicList */
761         currMB->RefIdx[0] = currMB->RefIdx[1] =
762                                 currMB->RefIdx[2] = currMB->RefIdx[3] = video->RefPicList0[0]->RefIdx;
763         InterMBPrediction(video);
764 
765         video->numMBs--;
766 
767     }
768 
769     return AVCDEC_SUCCESS;
770 }
771 
772