armVCM4P10_Interpolate_Luma.c revision 0c1bc742181ded4930842b46e9507372f0b1b963
1/**
2 *
3 * File Name:  armVCM4P10_Interpolate_Luma.c
4 * OpenMAX DL: v1.0.2
5 * Revision:   9641
6 * Date:       Thursday, February 7, 2008
7 *
8 * (c) Copyright 2007-2008 ARM Limited. All Rights Reserved.
9 *
10 *
11 * Description:
12 * This function will calculate interpolation for luma components
13 *
14 */
15
16#include "omxtypes.h"
17#include "armOMX.h"
18#include "omxVC.h"
19
20#include "armCOMM.h"
21#include "armVC.h"
22
23/**
24 * Function: armM4P10_Copy
25 *
26 * Description:
27 * This function performs copy a block of data from source to destination
28 *
29 * Remarks:
30 *
31 *  [in]    pSrc            Pointer to top-left corner of block
32 *  [in]    iSrcStep    Step of the source buffer.
33 *  [in]    iDstStep    Step of the destination  buffer.
34 *  [in]    iWidth      Width of the current block
35 *  [in]    iHeight     Height of the current block
36 *  [out]   pDst            Pointer to the interpolation buffer
37 *
38 * Return Value:
39 * Standard OMXResult value.
40 *
41 */
42static OMXResult armM4P10_Copy(
43    const OMX_U8*     pSrc,
44    OMX_U32     iSrcStep,
45    OMX_U8*     pDst,
46    OMX_U32     iDstStep,
47    OMX_U32     iWidth,
48    OMX_U32     iHeight
49)
50{
51    OMX_U32     x, y;
52
53    for (y = 0; y < iHeight; y++)
54    {
55        for (x = 0; x < iWidth; x++)
56        {
57            pDst [y * iDstStep + x] = pSrc [y * iSrcStep + x];
58        }
59    }
60
61    return OMX_Sts_NoErr;
62}
63
64/**
65 * Function: armVCM4P10_Interpolate_Luma
66 *
67 * Description:
68 * This function performs interpolation for luma components.
69 *
70 * Remarks:
71 *
72 *  [in]    pSrc            Pointer to top-left corner of block used to
73 *                                              interpolate in the reconstructed frame plane
74 *  [in]    iSrcStep    Step of the source buffer.
75 *  [in]    iDstStep    Step of the destination(interpolation) buffer.
76 *  [in]    iWidth      Width of the current block
77 *  [in]    iHeight     Height of the current block
78 *  [in]    dx              Fractional part of horizontal motion vector
79 *                                              component in 1/4 pixel unit (0~3)
80 *  [in]    dy              Fractional part of vertical motion vector
81 *                                              component in 1/4 pixel unit (0~3)
82 *  [out]   pDst            Pointer to the interpolation buffer
83 *
84 * Return Value:
85 * Standard OMXResult value.
86 *
87 */
88
89 OMXResult armVCM4P10_Interpolate_Luma(
90     const OMX_U8     *pSrc,
91     OMX_U32    iSrcStep,
92     OMX_U8     *pDst,
93     OMX_U32    iDstStep,
94     OMX_U32    iWidth,
95     OMX_U32    iHeight,
96     OMX_U32    dx,
97     OMX_U32    dy
98)
99{
100    OMX_U8      pBuf1 [16*16];
101    const OMX_U8      *pSrcHalfHor = pSrc;
102    const OMX_U8      *pSrcHalfVer = pSrc;
103
104    /* check for argument error */
105    armRetArgErrIf(pSrc == NULL, OMX_Sts_BadArgErr)
106    armRetArgErrIf(pDst == NULL, OMX_Sts_BadArgErr)
107    armRetArgErrIf(dx > 3, OMX_Sts_BadArgErr)
108    armRetArgErrIf(dy > 3, OMX_Sts_BadArgErr)
109
110    /* Work out positions for half pixel interpolation */
111    if (dx == 3)
112    {
113        pSrcHalfVer += 1;
114    }
115    if (dy == 3)
116    {
117        pSrcHalfHor += iSrcStep;
118    }
119
120    /* Switch on type of pixel
121     * Pixels are named 'a' to 's' as in the H.264 standard
122     */
123    if (dx == 0 && dy == 0)
124    {
125        /* G */
126        armM4P10_Copy(pSrc, iSrcStep, pDst, iDstStep, iWidth, iHeight);
127    }
128    else if (dy == 0)
129    {
130        /* a, b, c */
131        armVCM4P10_InterpolateHalfHor_Luma
132            (pSrcHalfHor, iSrcStep, pDst, iDstStep, iWidth, iHeight);
133
134        if (dx == 1 || dx == 3)
135        {
136            armVCCOMM_Average
137                (pDst, pSrcHalfVer, iDstStep, iSrcStep, pDst, iDstStep, iWidth, iHeight);
138        }
139    }
140    else if (dx == 0)
141    {
142        /* d, h, n */
143        armVCM4P10_InterpolateHalfVer_Luma
144            (pSrcHalfVer, iSrcStep, pDst, iDstStep, iWidth, iHeight);
145
146        if (dy == 1 || dy == 3)
147        {
148            armVCCOMM_Average
149                (pDst, pSrcHalfHor, iDstStep, iSrcStep, pDst, iDstStep, iWidth, iHeight);
150        }
151    }
152    else if (dx == 2 || dy == 2)
153    {
154        /* j */
155        armVCM4P10_InterpolateHalfDiag_Luma
156            (pSrc, iSrcStep, pDst, iDstStep, iWidth, iHeight);
157
158        if (dx == 1 || dx == 3)
159        {
160            /* i, k */
161            armVCM4P10_InterpolateHalfVer_Luma
162                (pSrcHalfVer, iSrcStep, pBuf1, iWidth, iWidth, iHeight);
163
164            armVCCOMM_Average
165                (pDst, pBuf1, iDstStep, iWidth, pDst, iDstStep, iWidth, iHeight);
166        }
167        if (dy == 1 || dy == 3)
168        {
169            /* f,q */
170            armVCM4P10_InterpolateHalfHor_Luma
171                (pSrcHalfHor, iSrcStep, pBuf1, iWidth, iWidth, iHeight);
172
173            armVCCOMM_Average
174                (pDst, pBuf1, iDstStep, iWidth, pDst, iDstStep, iWidth, iHeight);
175        }
176    }
177    else /* dx=1,3 and dy=1,3 */
178    {
179        /* e, g, p, r */
180        armVCM4P10_InterpolateHalfHor_Luma
181            (pSrcHalfHor, iSrcStep, pBuf1, iWidth, iWidth, iHeight);
182
183        armVCM4P10_InterpolateHalfVer_Luma
184            (pSrcHalfVer, iSrcStep, pDst, iDstStep, iWidth, iHeight);
185
186        armVCCOMM_Average
187            (pBuf1, pDst, iWidth, iDstStep, pDst, iDstStep, iWidth, iHeight);
188    }
189
190    return OMX_Sts_NoErr;
191}
192
193/*****************************************************************************
194 *                              END OF FILE
195 *****************************************************************************/
196