[cvs] / xvidcore / src / image / qpel.h Repository:
ViewVC logotype

Diff of /xvidcore/src/image/qpel.h

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 1.1, Sat May 3 23:26:35 2003 UTC revision 1.2, Mon Mar 22 22:36:23 2004 UTC
# Line 0  Line 1 
1    /*****************************************************************************
2     *
3     *  XVID MPEG-4 VIDEO CODEC
4     *  - QPel interpolation -
5     *
6     *  Copyright(C) 2003 Pascal Massimino <skal@planet-d.net>
7     *
8     *  This program is free software ; you can redistribute it and/or modify
9     *  it under the terms of the GNU General Public License as published by
10     *  the Free Software Foundation ; either version 2 of the License, or
11     *  (at your option) any later version.
12     *
13     *  This program is distributed in the hope that it will be useful,
14     *  but WITHOUT ANY WARRANTY ; without even the implied warranty of
15     *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16     *  GNU General Public License for more details.
17     *
18     *  You should have received a copy of the GNU General Public License
19     *  along with this program ; if not, write to the Free Software
20     *  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
21     *
22     * $Id$
23     *
24     ****************************************************************************/
25    
26    #ifndef _XVID_QPEL_H_
27    #define _XVID_QPEL_H_
28    
29    #include "../utils/mem_transfer.h"
30    
31    /*****************************************************************************
32     * Signatures
33     ****************************************************************************/
34    
35    #define XVID_QP_PASS_SIGNATURE(NAME)  \
36      void (NAME)(uint8_t *dst, const uint8_t *src, int32_t length, int32_t BpS, int32_t rounding)
37    
38    typedef  XVID_QP_PASS_SIGNATURE(XVID_QP_PASS);
39    
40    /* We put everything in a single struct so it can easily be passed
41     * to prediction functions as a whole... */
42    
43    typedef struct _XVID_QP_FUNCS {
44    
45            /* filter for QPel 16x? prediction */
46    
47            XVID_QP_PASS *H_Pass;
48            XVID_QP_PASS *H_Pass_Avrg;
49            XVID_QP_PASS *H_Pass_Avrg_Up;
50            XVID_QP_PASS *V_Pass;
51            XVID_QP_PASS *V_Pass_Avrg;
52            XVID_QP_PASS *V_Pass_Avrg_Up;
53    
54        /* filter for QPel 8x? prediction */
55    
56            XVID_QP_PASS *H_Pass_8;
57            XVID_QP_PASS *H_Pass_Avrg_8;
58            XVID_QP_PASS *H_Pass_Avrg_Up_8;
59            XVID_QP_PASS *V_Pass_8;
60            XVID_QP_PASS *V_Pass_Avrg_8;
61            XVID_QP_PASS *V_Pass_Avrg_Up_8;
62    } XVID_QP_FUNCS;
63    
64    /*****************************************************************************
65     * fwd dcl
66     ****************************************************************************/
67    extern void xvid_Init_QP();
68    
69    extern XVID_QP_FUNCS xvid_QP_Funcs_C;       /* for P-frames */
70    extern XVID_QP_FUNCS xvid_QP_Add_Funcs_C;   /* for B-frames */
71    
72    #ifdef ARCH_IS_IA32
73    extern XVID_QP_FUNCS xvid_QP_Funcs_mmx;
74    extern XVID_QP_FUNCS xvid_QP_Add_Funcs_mmx;
75    #endif
76    
77    extern XVID_QP_FUNCS *xvid_QP_Funcs;      /* <- main pointer for enc/dec structure */
78    extern XVID_QP_FUNCS *xvid_QP_Add_Funcs;  /* <- main pointer for enc/dec structure */
79    
80    /*****************************************************************************
81     * macros
82     ****************************************************************************/
83    
84    /*****************************************************************************
85    
86        Passes to be performed
87    
88     case 0:         copy
89     case 2:         h-pass
90     case 1/3:       h-pass + h-avrg
91     case 8:                           v-pass
92     case 10:        h-pass          + v-pass
93     case 9/11:      h-pass + h-avrg + v-pass
94     case 4/12:                        v-pass + v-avrg
95     case 6/14:      h-pass          + v-pass + v-avrg
96     case 5/13/7/15: h-pass + h-avrg + v-pass + v-avrg
97    
98     ****************************************************************************/
99    
100    static void __inline
101    new_interpolate16x16_quarterpel(uint8_t * const cur,
102                                                                    uint8_t * const refn,
103                                                                    uint8_t * const refh,
104                                                                    uint8_t * const refv,
105                                                                    uint8_t * const refhv,
106                                                                    const uint32_t x, const uint32_t y,
107                                                                    const int32_t dx,  const int dy,
108                                                                    const uint32_t stride,
109                                                                    const uint32_t rounding)
110    {
111            const uint8_t *src;
112            uint8_t *dst;
113            uint8_t *tmp;
114            int32_t quads;
115            const XVID_QP_FUNCS *Ops;
116    
117            int32_t x_int, y_int;
118    
119            const int32_t xRef = x*4 + dx;
120            const int32_t yRef = y*4 + dy;
121    
122            Ops = xvid_QP_Funcs; /* TODO: pass as argument */
123            quads = (dx&3) | ((dy&3)<<2);
124    
125            x_int = xRef/4;
126            if (xRef < 0 && xRef % 4)
127                    x_int--;
128    
129            y_int    = yRef/4;
130            if (yRef < 0 && yRef % 4)
131                    y_int--;
132    
133            dst = cur + y * stride + x;
134            src = refn + y_int * stride + x_int;
135    
136            tmp = refh; /* we need at least a 16 x stride scratch block */
137    
138            switch(quads) {
139            case 0:
140                    transfer8x8_copy( dst, src, stride);
141                    transfer8x8_copy( dst+8, src+8, stride);
142                    transfer8x8_copy( dst+8*stride, src+8*stride, stride);
143                    transfer8x8_copy( dst+8*stride+8, src+8*stride+8, stride);
144                    break;
145            case 1:
146                    Ops->H_Pass_Avrg(dst, src, 16, stride, rounding);
147                    break;
148            case 2:
149                    Ops->H_Pass(dst, src, 16, stride, rounding);
150                    break;
151            case 3:
152                    Ops->H_Pass_Avrg_Up(dst, src, 16, stride, rounding);
153                    break;
154            case 4:
155                    Ops->V_Pass_Avrg(dst, src, 16, stride, rounding);
156                    break;
157            case 5:
158                    Ops->H_Pass_Avrg(tmp, src, 17, stride, rounding);
159                    Ops->V_Pass_Avrg(dst, tmp, 16, stride, rounding);
160                    break;
161            case 6:
162                    Ops->H_Pass(tmp, src,     17, stride, rounding);
163                    Ops->V_Pass_Avrg(dst, tmp, 16, stride, rounding);
164                    break;
165            case 7:
166                    Ops->H_Pass_Avrg_Up(tmp, src, 17, stride, rounding);
167                    Ops->V_Pass_Avrg(dst, tmp, 16, stride, rounding);
168                    break;
169            case 8:
170                    Ops->V_Pass(dst, src, 16, stride, rounding);
171                    break;
172            case 9:
173                    Ops->H_Pass_Avrg(tmp, src, 17, stride, rounding);
174                    Ops->V_Pass(dst, tmp, 16, stride, rounding);
175                    break;
176            case 10:
177                    Ops->H_Pass(tmp, src, 17, stride, rounding);
178                    Ops->V_Pass(dst, tmp, 16, stride, rounding);
179                    break;
180            case 11:
181                    Ops->H_Pass_Avrg_Up(tmp, src, 17, stride, rounding);
182                    Ops->V_Pass(dst, tmp, 16, stride, rounding);
183                    break;
184            case 12:
185                    Ops->V_Pass_Avrg_Up(dst, src, 16, stride, rounding);
186                    break;
187            case 13:
188                    Ops->H_Pass_Avrg(tmp, src, 17, stride, rounding);
189                    Ops->V_Pass_Avrg_Up(dst, tmp, 16, stride, rounding);
190                    break;
191            case 14:
192                    Ops->H_Pass(tmp, src, 17, stride, rounding);
193                    Ops->V_Pass_Avrg_Up( dst, tmp, 16, stride, rounding);
194                    break;
195            case 15:
196                    Ops->H_Pass_Avrg_Up(tmp, src, 17, stride, rounding);
197                    Ops->V_Pass_Avrg_Up(dst, tmp, 16, stride, rounding);
198                    break;
199            }
200    }
201    
202    static void __inline
203    new_interpolate16x8_quarterpel(uint8_t * const cur,
204                                                               uint8_t * const refn,
205                                                               uint8_t * const refh,
206                                                               uint8_t * const refv,
207                                                               uint8_t * const refhv,
208                                                               const uint32_t x, const uint32_t y,
209                                                               const int32_t dx,  const int dy,
210                                                               const uint32_t stride,
211                                                               const uint32_t rounding)
212    {
213            const uint8_t *src;
214            uint8_t *dst;
215            uint8_t *tmp;
216            int32_t quads;
217            const XVID_QP_FUNCS *Ops;
218    
219            int32_t x_int, y_int;
220    
221            const int32_t xRef = x*4 + dx;
222            const int32_t yRef = y*4 + dy;
223    
224            Ops = xvid_QP_Funcs; /* TODO: pass as argument */
225            quads = (dx&3) | ((dy&3)<<2);
226    
227            x_int = xRef/4;
228            if (xRef < 0 && xRef % 4)
229                    x_int--;
230    
231            y_int    = yRef/4;
232            if (yRef < 0 && yRef % 4)
233                    y_int--;
234    
235            dst = cur + y * stride + x;
236            src = refn + y_int * stride + x_int;
237    
238            tmp = refh; /* we need at least a 16 x stride scratch block */
239    
240            switch(quads) {
241            case 0:
242                    transfer8x8_copy( dst, src, stride);
243                    transfer8x8_copy( dst+8, src+8, stride);
244                    break;
245            case 1:
246                    Ops->H_Pass_Avrg(dst, src, 8, stride, rounding);
247                    break;
248            case 2:
249                    Ops->H_Pass(dst, src, 8, stride, rounding);
250                    break;
251            case 3:
252                    Ops->H_Pass_Avrg_Up(dst, src, 8, stride, rounding);
253                    break;
254            case 4:
255                    Ops->V_Pass_Avrg_8(dst, src, 16, stride, rounding);
256                    break;
257            case 5:
258                    Ops->H_Pass_Avrg(tmp, src, 9, stride, rounding);
259                    Ops->V_Pass_Avrg_8(dst, tmp, 16, stride, rounding);
260                    break;
261            case 6:
262                    Ops->H_Pass(tmp, src,     9, stride, rounding);
263                    Ops->V_Pass_Avrg_8(dst, tmp, 16, stride, rounding);
264                    break;
265            case 7:
266                    Ops->H_Pass_Avrg_Up(tmp, src, 9, stride, rounding);
267                    Ops->V_Pass_Avrg_8(dst, tmp, 16, stride, rounding);
268                    break;
269            case 8:
270                    Ops->V_Pass_8(dst, src, 16, stride, rounding);
271                    break;
272            case 9:
273                    Ops->H_Pass_Avrg(tmp, src, 9, stride, rounding);
274                    Ops->V_Pass_8(dst, tmp, 16, stride, rounding);
275                    break;
276            case 10:
277                    Ops->H_Pass(tmp, src, 9, stride, rounding);
278                    Ops->V_Pass_8(dst, tmp, 16, stride, rounding);
279                    break;
280            case 11:
281                    Ops->H_Pass_Avrg_Up(tmp, src, 9, stride, rounding);
282                    Ops->V_Pass_8(dst, tmp, 16, stride, rounding);
283                    break;
284            case 12:
285                    Ops->V_Pass_Avrg_Up_8(dst, src, 16, stride, rounding);
286                    break;
287            case 13:
288                    Ops->H_Pass_Avrg(tmp, src, 9, stride, rounding);
289                    Ops->V_Pass_Avrg_Up_8(dst, tmp, 16, stride, rounding);
290                    break;
291            case 14:
292                    Ops->H_Pass(tmp, src, 9, stride, rounding);
293                    Ops->V_Pass_Avrg_Up_8( dst, tmp, 16, stride, rounding);
294                    break;
295            case 15:
296                    Ops->H_Pass_Avrg_Up(tmp, src, 9, stride, rounding);
297                    Ops->V_Pass_Avrg_Up_8(dst, tmp, 16, stride, rounding);
298                    break;
299            }
300    }
301    
302    static void __inline
303    new_interpolate8x8_quarterpel(uint8_t * const cur,
304                                                              uint8_t * const refn,
305                                                              uint8_t * const refh,
306                                                              uint8_t * const refv,
307                                                              uint8_t * const refhv,
308                                                              const uint32_t x, const uint32_t y,
309                                                              const int32_t dx,  const int dy,
310                                                              const uint32_t stride,
311                                                              const uint32_t rounding)
312    {
313            const uint8_t *src;
314            uint8_t *dst;
315            uint8_t *tmp;
316            int32_t quads;
317            const XVID_QP_FUNCS *Ops;
318    
319            int32_t x_int, y_int;
320    
321            const int32_t xRef = x*4 + dx;
322            const int32_t yRef = y*4 + dy;
323    
324            Ops = xvid_QP_Funcs; /* TODO: pass as argument */
325            quads = (dx&3) | ((dy&3)<<2);
326    
327            x_int = xRef/4;
328            if (xRef < 0 && xRef % 4)
329                    x_int--;
330    
331            y_int    = yRef/4;
332            if (yRef < 0 && yRef % 4)
333                    y_int--;
334    
335            dst = cur + y * stride + x;
336            src = refn + y_int * stride + x_int;
337    
338            tmp = refh; /* we need at least a 16 x stride scratch block */
339    
340            switch(quads) {
341            case 0:
342                    transfer8x8_copy( dst, src, stride);
343                    break;
344            case 1:
345                    Ops->H_Pass_Avrg_8(dst, src, 8, stride, rounding);
346                    break;
347            case 2:
348                    Ops->H_Pass_8(dst, src, 8, stride, rounding);
349                    break;
350            case 3:
351                    Ops->H_Pass_Avrg_Up_8(dst, src, 8, stride, rounding);
352                    break;
353            case 4:
354                    Ops->V_Pass_Avrg_8(dst, src, 8, stride, rounding);
355                    break;
356            case 5:
357                    Ops->H_Pass_Avrg_8(tmp, src, 9, stride, rounding);
358                    Ops->V_Pass_Avrg_8(dst, tmp, 8, stride, rounding);
359                    break;
360            case 6:
361                    Ops->H_Pass_8(tmp, src, 9, stride, rounding);
362                    Ops->V_Pass_Avrg_8(dst, tmp, 8, stride, rounding);
363                    break;
364            case 7:
365                    Ops->H_Pass_Avrg_Up_8(tmp, src, 9, stride, rounding);
366                    Ops->V_Pass_Avrg_8(dst, tmp, 8, stride, rounding);
367                    break;
368            case 8:
369                    Ops->V_Pass_8(dst, src, 8, stride, rounding);
370                    break;
371            case 9:
372                    Ops->H_Pass_Avrg_8(tmp, src, 9, stride, rounding);
373                    Ops->V_Pass_8(dst, tmp, 8, stride, rounding);
374                    break;
375            case 10:
376                    Ops->H_Pass_8(tmp, src, 9, stride, rounding);
377                    Ops->V_Pass_8(dst, tmp, 8, stride, rounding);
378                    break;
379            case 11:
380                    Ops->H_Pass_Avrg_Up_8(tmp, src, 9, stride, rounding);
381                    Ops->V_Pass_8(dst, tmp, 8, stride, rounding);
382                    break;
383            case 12:
384                    Ops->V_Pass_Avrg_Up_8(dst, src, 8, stride, rounding);
385                    break;
386            case 13:
387                    Ops->H_Pass_Avrg_8(tmp, src, 9, stride, rounding);
388                    Ops->V_Pass_Avrg_Up_8(dst, tmp, 8, stride, rounding);
389                    break;
390            case 14:
391                    Ops->H_Pass_8(tmp, src, 9, stride, rounding);
392                    Ops->V_Pass_Avrg_Up_8( dst, tmp, 8, stride, rounding);
393                    break;
394            case 15:
395                    Ops->H_Pass_Avrg_Up_8(tmp, src, 9, stride, rounding);
396                    Ops->V_Pass_Avrg_Up_8(dst, tmp, 8, stride, rounding);
397                    break;
398            }
399    }
400    
401    #endif  /* _XVID_QPEL_H_ */

Legend:
Removed from v.1.1  
changed lines
  Added in v.1.2

No admin address has been configured
ViewVC Help
Powered by ViewVC 1.0.4