omxVCM4P2_DecodeBlockCoef_Intra.c revision 21e525fdcc234c22d843a8bf1a4ec35c4b376314
1/**
2 *
3 * File Name:  omxVCM4P2_DecodeBlockCoef_Intra.c
4 * OpenMAX DL: v1.0.2
5 * Revision:   12290
6 * Date:       Wednesday, April 9, 2008
7 *
8 * (c) Copyright 2007-2008 ARM Limited. All Rights Reserved.
9 *
10 *
11 *
12 * Description:
13 * Contains modules for intra reconstruction
14 *
15 */
16
17#include "omxtypes.h"
18#include "armOMX.h"
19#include "omxVC.h"
20
21#include "armCOMM.h"
22#include "armVC.h"
23
24/* Function for saturating 16 bit values to the [0,255] range and  */
25/* writing out as 8 bit values.  Does 64 entries                   */
26void armVCM4P2_Clip8(OMX_S16 *pSrc, OMX_U8 *pDst, OMX_INT dstStep );
27
28
29
30/**
31 * Function: omxVCM4P2_DecodeBlockCoef_Intra
32 *
33 * Description:
34 * Decodes the INTRA block coefficients. Inverse quantization, inversely zigzag
35 * positioning, and IDCT, with appropriate clipping on each step, are performed
36 * on the coefficients. The results are then placed in the output frame/plane on
37 * a pixel basis. For INTRA block, the output values are clipped to [0, 255] and
38 * written to corresponding block buffer within the destination plane.
39 *
40 * Remarks:
41 *
42 * Parameters:
43 * [in]	ppBitStream		pointer to the pointer to the current byte in
44 *								the bit stream buffer. There is no boundary
45 *								check for the bit stream buffer.
46 * [in]	pBitOffset		pointer to the bit position in the byte pointed
47 *								to by *ppBitStream. *pBitOffset is valid within
48 *								[0-7].
49 * [in]	step			width of the destination plane
50 * [in/out]	pCoefBufRow		[in]  pointer to the coefficient row buffer
51 *                        [out] updated coefficient rwo buffer
52 * [in/out]	pCoefBufCol		[in]  pointer to the coefficient column buffer
53 *                        [out] updated coefficient column buffer
54 * [in]	curQP			quantization parameter of the macroblock which
55 *								the current block belongs to
56 * [in]	pQpBuf		 Pointer to a 2-element QP array. pQpBuf[0] holds the QP of the 8x8 block left to
57 *                   the current block(QPa). pQpBuf[1] holds the QP of the 8x8 block just above the
58 *                   current block(QPc).
59 *                   Note, in case the corresponding block is out of VOP bound, the QP value will have
60 *                   no effect to the intra-prediction process. Refer to subclause  "7.4.3.3 Adaptive
61 *                   ac coefficient prediction" of ISO/IEC 14496-2(MPEG4 Part2) for accurate description.
62 * [in]	blockIndex		block index indicating the component type and
63 *								position as defined in subclause 6.1.3.8,
64 *								Figure 6-5 of ISO/IEC 14496-2.
65 * [in]	intraDCVLC		a code determined by intra_dc_vlc_thr and QP.
66 *								This allows a mechanism to switch between two VLC
67 *								for coding of Intra DC coefficients as per Table
68 *								6-21 of ISO/IEC 14496-2.
69 * [in]	ACPredFlag		a flag equal to ac_pred_flag (of luminance) indicating
70 *								if the ac coefficients of the first row or first
71 *								column are differentially coded for intra coded
72 *								macroblock.
73 * [in] shortVideoHeader    a flag indicating presence of short_video_header;
74 *                           shortVideoHeader==1 selects linear intra DC mode,
75 *							and shortVideoHeader==0 selects nonlinear intra DC mode.
76 * [out]	ppBitStream		*ppBitStream is updated after the block is
77 *								decoded, so that it points to the current byte
78 *								in the bit stream buffer
79 * [out]	pBitOffset		*pBitOffset is updated so that it points to the
80 *								current bit position in the byte pointed by
81 *								*ppBitStream
82 * [out]	pDst			pointer to the block in the destination plane.
83 *								pDst should be 16-byte aligned.
84 * [out]	pCoefBufRow		pointer to the updated coefficient row buffer.
85 *
86 * Return Value:
87 * OMX_Sts_NoErr - no error
88 * OMX_Sts_BadArgErr - bad arguments
89 *   -	At least one of the following pointers is NULL: ppBitStream, *ppBitStream, pBitOffset,
90 *                                                      pCoefBufRow, pCoefBufCol, pQPBuf, pDst.
91 *      or
92 *   -  At least one of the below case: *pBitOffset exceeds [0,7], curQP exceeds (1, 31),
93 *      blockIndex exceeds [0,9], step is not the multiple of 8, intraDCVLC is zero while
94 *      blockIndex greater than 5.
95 *      or
96 *   -	pDst is not 16-byte aligned
97 * OMX_Sts_Err - status error
98 *
99 */
100
101OMXResult omxVCM4P2_DecodeBlockCoef_Intra(
102     const OMX_U8 ** ppBitStream,
103     OMX_INT *pBitOffset,
104     OMX_U8 *pDst,
105     OMX_INT step,
106     OMX_S16 *pCoefBufRow,
107     OMX_S16 *pCoefBufCol,
108     OMX_U8 curQP,
109     const OMX_U8 *pQPBuf,
110     OMX_INT blockIndex,
111     OMX_INT intraDCVLC,
112     OMX_INT ACPredFlag,
113	 OMX_INT shortVideoHeader
114 )
115{
116    OMX_S16 tempBuf1[79], tempBuf2[79];
117    OMX_S16 *pTempBuf1, *pTempBuf2;
118    OMX_INT predDir, predACDir;
119    OMX_INT  predQP;
120    OMXVCM4P2VideoComponent videoComp;
121    OMXResult errorCode;
122
123
124    /* Aligning the local buffers */
125    pTempBuf1 = armAlignTo16Bytes(tempBuf1);
126    pTempBuf2 = armAlignTo16Bytes(tempBuf2);
127
128    /* Setting the AC prediction direction and prediction direction */
129    armVCM4P2_SetPredDir(
130        blockIndex,
131        pCoefBufRow,
132        pCoefBufCol,
133        &predDir,
134        &predQP,
135        pQPBuf);
136
137    predACDir = predDir;
138
139
140    if (ACPredFlag == 0)
141    {
142        predACDir = OMX_VC_NONE;
143    }
144
145    /* Setting the videoComp */
146    if (blockIndex <= 3)
147    {
148        videoComp = OMX_VC_LUMINANCE;
149    }
150    else
151    {
152        videoComp = OMX_VC_CHROMINANCE;
153    }
154
155
156    /* VLD and zigzag */
157    if (intraDCVLC == 1)
158    {
159        errorCode = omxVCM4P2_DecodeVLCZigzag_IntraDCVLC(
160            ppBitStream,
161            pBitOffset,
162            pTempBuf1,
163            predACDir,
164            shortVideoHeader,
165            videoComp);
166        armRetDataErrIf((errorCode != OMX_Sts_NoErr), errorCode);
167    }
168    else
169    {
170        errorCode = omxVCM4P2_DecodeVLCZigzag_IntraACVLC(
171            ppBitStream,
172            pBitOffset,
173            pTempBuf1,
174            predACDir,
175            shortVideoHeader);
176        armRetDataErrIf((errorCode != OMX_Sts_NoErr), errorCode);
177    }
178
179    /* AC DC prediction */
180    errorCode = omxVCM4P2_PredictReconCoefIntra(
181        pTempBuf1,
182        pCoefBufRow,
183        pCoefBufCol,
184        curQP,
185        predQP,
186        predDir,
187        ACPredFlag,
188        videoComp);
189    armRetDataErrIf((errorCode != OMX_Sts_NoErr), errorCode);
190
191    /* Dequantization */
192    errorCode = omxVCM4P2_QuantInvIntra_I(
193     pTempBuf1,
194     curQP,
195     videoComp,
196     shortVideoHeader);
197    armRetDataErrIf((errorCode != OMX_Sts_NoErr), errorCode);
198
199    /* Inverse transform */
200    errorCode = omxVCM4P2_IDCT8x8blk (pTempBuf1, pTempBuf2);
201    armRetDataErrIf((errorCode != OMX_Sts_NoErr), errorCode);
202
203    /* Placing the linear array into the destination plane and clipping
204       it to 0 to 255 */
205
206	armVCM4P2_Clip8(pTempBuf2,pDst,step);
207
208
209    return OMX_Sts_NoErr;
210}
211
212/* End of file */
213
214
215