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