]> git.sesse.net Git - vlc/blob - src/video_decoder/vdec_motion.c
Le retour du demoronifier qui n'est pas content.
[vlc] / src / video_decoder / vdec_motion.c
1 /*****************************************************************************
2  * vdec_motion.c : motion compensation routines
3  * (c)1999 VideoLAN
4  *****************************************************************************/
5
6 /*****************************************************************************
7  * Preamble
8  *****************************************************************************/
9 #include <errno.h>
10 #include <stdlib.h>
11 #include <stdio.h>
12 #include <unistd.h>
13 #include <string.h>
14 #include <sys/uio.h>
15
16 #include "config.h"
17 #include "common.h"
18 #include "mtime.h"
19 #include "vlc_thread.h"
20
21 #include "intf_msg.h"
22 #include "debug.h"                 /* XXX?? temporaire, requis par netlist.h */
23
24 #include "input.h"
25 #include "input_netlist.h"
26 #include "decoder_fifo.h"
27 #include "video.h"
28 #include "video_output.h"
29
30 #include "vdec_idct.h"
31 #include "video_decoder.h"
32 #include "vdec_motion.h"
33
34 #include "vpar_blocks.h"
35 #include "vpar_headers.h"
36 #include "vpar_synchro.h"
37 #include "video_parser.h"
38 #include "video_fifo.h"
39
40 /*****************************************************************************
41  * vdec_MotionComponent : last stage of motion compensation
42  *****************************************************************************/
43 static __inline__ void MotionComponent(
44                     yuv_data_t * p_src,     /* source block */
45                     yuv_data_t * p_dest,    /* dest block */
46                     int i_width,            /* (explicit) width of block */
47                     int i_height,           /* (explicit) height of block */
48                     int i_stride,           /* number of coeffs to jump
49                                              * between each predicted line */
50                     int i_step,             /* number of coeffs to jump to
51                                              * go to the next line of the
52                                              * field */
53                     int i_select,           /* half-pel vectors */
54                     boolean_t b_average     /* (explicit) averaging of several
55                                              * predictions */ )
56 {
57     int i_x, i_y, i_x1;
58     unsigned int i_dummy;
59
60     if( !b_average )
61     {
62         /* Please note that b_average will be expanded at compile time */
63
64         switch( i_select )
65         {
66         case 0:
67             /* !xh, !yh, !average */
68             for( i_y = 0; i_y < i_height; i_y ++ )
69             {
70                     for( i_x = 0; i_x < i_width; i_x += 8 )
71                     {
72                          for( i_x1 = 0; i_x1 < 8; i_x1++ )
73                          {
74                              p_dest[i_x+i_x1] = p_src[i_x+i_x1];
75                          }
76                     }
77                     p_dest += i_stride;
78                     p_src += i_stride;
79             }
80             break;
81
82         case 1:
83             /* xh, !yh, !average */
84             for( i_y = 0; i_y < i_height; i_y ++ )
85             {
86                     for( i_x = 0; i_x < i_width; i_x += 8 )
87                     {
88                          for( i_x1 = 0; i_x1 < 8; i_x1++ )
89                          {
90                              p_dest[i_x+i_x1] = (unsigned int)(p_src[i_x+i_x1]
91                                                       + p_src[i_x+i_x1 + 1] + 1)
92                                                     >> 1;
93                          }
94                     }
95                     p_dest += i_stride;
96                     p_src += i_stride;
97             }
98             break;
99
100         case 2:
101             /* !xh, yh, !average */
102             for( i_y = 0; i_y < i_height; i_y ++ )
103             {
104                     for( i_x = 0; i_x < i_width; i_x += 8 )
105                     {
106                          for( i_x1 = 0; i_x1 < 8; i_x1++ )
107                          {
108                              p_dest[i_x+i_x1] = (unsigned int)(p_src[i_x+i_x1] + 1
109                                                 + p_src[i_x+i_x1 + i_step])
110                                               >> 1;
111                          }
112                     }
113                     p_dest += i_stride;
114                     p_src += i_stride;
115             }
116             break;
117
118         case 3:
119             /* xh, yh, !average (3) */
120             for( i_y = 0; i_y < i_height; i_y ++ )
121             {
122                     for( i_x = 0; i_x < i_width; i_x += 8 )
123                     {
124                          for( i_x1 = 0; i_x1 < 8; i_x1++ )
125                          {
126                              p_dest[i_x+i_x1]
127                                 = ((unsigned int)(
128                                       p_src[i_x+i_x1]
129                                     + p_src[i_x+i_x1 + 1]
130                                     + p_src[i_x+i_x1 + i_step]
131                                     + p_src[i_x+i_x1 + i_step + 1]
132                                     + 2) >> 2);
133                          }
134                     }
135                     p_dest += i_stride;
136                     p_src += i_stride;
137             }
138             break;
139         }
140
141     }
142     else
143     {
144         /* b_average */
145         switch( i_select )
146         {
147         case 0:
148             /* !xh, !yh, average */
149             for( i_y = 0; i_y < i_height; i_y ++ )
150             {
151                     for( i_x = 0; i_x < i_width; i_x += 8 )
152                     {
153                          for( i_x1 = 0; i_x1 < 8; i_x1++ )
154                          {
155                              i_dummy = p_dest[i_x + i_x1] + p_src[i_x + i_x1];
156                              p_dest[i_x + i_x1] = (i_dummy + 1) >> 1;
157                          }
158                     }
159                     p_dest += i_stride;
160                     p_src += i_stride;
161             }
162             break;
163
164         case 1:
165             /* xh, !yh, average */
166             for( i_y = 0; i_y < i_height; i_y ++ )
167             {
168                     for( i_x = 0; i_x < i_width; i_x += 8 )
169                     {
170                          for( i_x1 = 0; i_x1 < 8; i_x1++ )
171                          {
172                              i_dummy = p_dest[i_x+i_x1]
173                                 + ((unsigned int)(p_src[i_x+i_x1]
174                                                   + p_src[i_x+i_x1 + 1] + 1) >> 1);
175                              p_dest[i_x + i_x1] = (i_dummy + 1) >> 1;
176                          }
177                     }
178                     p_dest += i_stride;
179                     p_src += i_stride;
180             }
181             break;
182
183         case 2:
184             /* !xh, yh, average */
185             for( i_y = 0; i_y < i_height; i_y ++ )
186             {
187                     for( i_x = 0; i_x < i_width; i_x += 8 )
188                     {
189                          for( i_x1 = 0; i_x1 < 8; i_x1++ )
190                          {
191                              i_dummy = p_dest[i_x+i_x1]
192                                 + ((unsigned int)(p_src[i_x+i_x1] + 1
193                                          + p_src[i_x+i_x1 + i_step]) >> 1);
194                              p_dest[i_x + i_x1] = (i_dummy + 1) >> 1;
195                          }
196                     }
197                     p_dest += i_stride;
198                     p_src += i_stride;
199             }
200             break;
201
202         case 3:
203             /* xh, yh, average */
204             for( i_y = 0; i_y < i_height; i_y ++ )
205             {
206                     for( i_x = 0; i_x < i_width; i_x += 8 )
207                     {
208                          for( i_x1 = 0; i_x1 < 8; i_x1++ )
209                          {
210                              i_dummy = p_dest[i_x+i_x1]
211                                 + ((unsigned int)(
212                                       p_src[i_x+i_x1]
213                                     + p_src[i_x+i_x1 + 1]
214                                     + p_src[i_x+i_x1 + i_step]
215                                     + p_src[i_x+i_x1 + i_step + 1]
216                                     + 2) >> 2);
217                              p_dest[i_x + i_x1] = (i_dummy + 1) >> 1;
218                          }
219                     }
220                     p_dest += i_stride;
221                     p_src += i_stride;
222             }
223             break;
224         }
225     }
226 }
227
228 /*****************************************************************************
229  * Motion420 : motion compensation for a 4:2:0 macroblock
230  *****************************************************************************/
231 static __inline__ void Motion420(
232                     macroblock_t * p_mb,        /* destination macroblock */
233                     picture_t * p_source,       /* source picture */
234                     boolean_t b_source_field,   /* source field */
235                     boolean_t b_dest_field,     /* destination field */
236                     int i_mv_x, int i_mv_y,     /* motion vector coordinates,
237                                                  * in half pels */
238                     int i_l_stride,             /* number of coeffs to jump to
239                                                  * go to the next predicted
240                                                  * line */
241                     int i_c_stride,
242                     int i_height,               /* height of the block to
243                                                  * predict, in luminance
244                                                  * (explicit) */
245                     int i_offset,               /* position of the first
246                                                  * predicted line (explicit) */
247                     boolean_t b_average         /* (explicit) averaging of
248                                                  * several predictions */ )
249 {
250     /* Temporary variables to avoid recalculating things twice */
251     int     i_source_offset, i_dest_offset, i_c_height, i_c_select;
252
253     i_source_offset = (p_mb->i_l_x + (i_mv_x >> 1))
254                        + (p_mb->i_motion_l_y + i_offset
255                          + (i_mv_y >> 1)
256                          + b_source_field)
257                          * p_mb->p_picture->i_width;
258     if( i_source_offset >= p_source->i_width * p_source->i_height )
259     {
260         fprintf( stderr, "vdec error: bad motion vector\n" );
261         return;
262     }
263
264     /* Luminance */
265     MotionComponent( /* source */
266                      p_source->p_y + i_source_offset,
267                      /* destination */
268                      p_mb->p_picture->p_y
269                        + (p_mb->i_l_x)
270                        + (p_mb->i_motion_l_y + b_dest_field)
271                          * p_mb->p_picture->i_width,
272                      /* prediction width and height */
273                      16, i_height,
274                      /* stride */
275                      i_l_stride, p_mb->i_l_stride,
276                      /* select */
277                      ((i_mv_y & 1) << 1) | (i_mv_x & 1),
278                      b_average );
279
280     i_source_offset = (p_mb->i_c_x + ((i_mv_x/2) >> 1))
281                         + ((p_mb->i_motion_c_y + (i_offset >> 1)
282                            + ((i_mv_y/2) >> 1))
283                            + b_source_field)
284                           * p_mb->p_picture->i_chroma_width;
285     if( i_source_offset >= (p_source->i_width * p_source->i_height) / 4 )
286     {
287         fprintf( stderr, "vdec error: bad motion vector\n" );
288         return;
289     }
290
291     i_dest_offset = (p_mb->i_c_x)
292                       + (p_mb->i_motion_c_y + b_dest_field)
293                         * p_mb->p_picture->i_chroma_width;
294     i_c_height = i_height >> 1;
295     i_c_select = (((i_mv_y/2) & 1) << 1) | ((i_mv_x/2) & 1);
296
297     /* Chrominance Cr */
298     MotionComponent( p_source->p_u
299                        + i_source_offset,
300                      p_mb->p_picture->p_u
301                        + i_dest_offset,
302                      8, i_c_height, i_c_stride, p_mb->i_c_stride,
303                      i_c_select, b_average );
304
305     /* Chrominance Cb */
306     MotionComponent( p_source->p_v
307                        + i_source_offset,
308                      p_mb->p_picture->p_v
309                        + i_dest_offset,
310                      8, i_c_height, i_c_stride, p_mb->i_c_stride,
311                      i_c_select, b_average );
312 }
313
314 /*****************************************************************************
315  * Motion422 : motion compensation for a 4:2:2 macroblock
316  *****************************************************************************/
317 static __inline__ void Motion422(
318                     macroblock_t * p_mb,        /* destination macroblock */
319                     picture_t * p_source,       /* source picture */
320                     boolean_t b_source_field,   /* source field */
321                     boolean_t b_dest_field,     /* destination field */
322                     int i_mv_x, int i_mv_y,     /* motion vector coordinates,
323                                                  * in half pels */
324                     int i_l_stride,             /* number of coeffs to jump to
325                                                  * go to the next predicted
326                                                  * line */
327                     int i_c_stride,
328                     int i_height,               /* height of the block to
329                                                  * predict, in luminance
330                                                  * (explicit) */
331                     int i_offset,               /* position of the first
332                                                  * predicted line (explicit) */
333                     boolean_t b_average         /* (explicit) averaging of
334                                                  * several predictions */ )
335 {
336 #if 0
337     int     i_source_offset, i_dest_offset, i_c_select;
338
339     /* Luminance */
340     MotionComponent( /* source */
341                      p_source->p_y
342                        + (p_mb->i_l_x + (i_mv_x >> 1))
343                        + (p_mb->i_motion_l_y + i_offset
344                           + (i_mv_y >> 1)
345                           + b_source_field)
346                          * p_mb->p_picture->i_width,
347                      /* destination */
348                      p_mb->p_picture->p_y
349                        + (p_mb->i_l_x)
350                        + (p_mb->i_motion_l_y + b_dest_field)
351                          * p_mb->p_picture->i_width,
352                      /* prediction width and height */
353                      16, i_height,
354                      /* stride */
355                      i_l_stride, p_mb->i_l_stride,
356                      /* select */
357                      ((i_mv_y & 1) << 1) | (i_mv_x & 1),
358                      b_average );
359
360     i_source_offset = (p_mb->i_c_x + ((i_mv_x/2) >> 1))
361                         + ((p_mb->i_motion_c_y + (i_offset)
362                            + ((i_mv_y) >> 1))
363                            + b_source_field)
364                           * p_mb->p_picture->i_chroma_width;
365     i_dest_offset = (p_mb->i_c_x)
366                       + (p_mb->i_motion_c_y + b_dest_field)
367                         * p_mb->p_picture->i_chroma_width;
368     i_c_select = ((i_mv_y & 1) << 1) | ((i_mv_x/2) & 1);
369
370     /* Chrominance Cr */
371     MotionComponent( p_source->p_u
372                        + i_source_offset,
373                      p_mb->p_picture->p_u
374                        + i_dest_offset,
375                      8, i_height, i_c_stride, p_mb->i_c_stride,
376                      i_c_select, b_average );
377
378     /* Chrominance Cb */
379     MotionComponent( p_source->p_v
380                        + i_source_offset,
381                      p_mb->p_picture->p_u
382                        + i_dest_offset,
383                      8, i_height, i_c_stride, p_mb->i_c_stride,
384                      i_c_select, b_average );
385 #endif
386 }
387
388 /*****************************************************************************
389  * Motion444 : motion compensation for a 4:4:4 macroblock
390  *****************************************************************************/
391 static __inline__ void Motion444(
392                     macroblock_t * p_mb,        /* destination macroblock */
393                     picture_t * p_source,       /* source picture */
394                     boolean_t b_source_field,   /* source field */
395                     boolean_t b_dest_field,     /* destination field */
396                     int i_mv_x, int i_mv_y,     /* motion vector coordinates,
397                                                  * in half pels */
398                     int i_l_stride,             /* number of coeffs to jump to
399                                                  * go to the next predicted
400                                                  * line */
401                     int i_c_stride,
402                     int i_height,               /* height of the block to
403                                                  * predict, in luminance
404                                                  * (explicit) */
405                     int i_offset,               /* position of the first
406                                                  * predicted line (explicit) */
407                     boolean_t b_average         /* (explicit) averaging of
408                                                  * several predictions */ )
409 {
410 #if 0
411     int     i_source_offset, i_dest_offset, i_select;
412
413     i_source_offset = (p_mb->i_l_x + (i_mv_x >> 1))
414                         + (p_mb->i_motion_l_y + i_offset
415                            + (i_mv_y >> 1)
416                            + b_source_field)
417                           * p_mb->p_picture->i_width;
418     i_dest_offset = (p_mb->i_l_x)
419                       + (p_mb->i_motion_l_y + b_dest_field)
420                         * p_mb->p_picture->i_width;
421     i_select = ((i_mv_y & 1) << 1) | (i_mv_x & 1);
422
423
424     /* Luminance */
425     MotionComponent( p_source->p_y
426                        + i_source_offset,
427                      p_mb->p_picture->p_y
428                        + i_dest_offset,
429                      16, i_height, i_l_stride, p_mb->i_l_stride,
430                      i_select, b_average );
431
432     /* Chrominance Cr */
433     MotionComponent( p_source->p_u
434                        + i_source_offset,
435                      p_mb->p_picture->p_u
436                        + i_dest_offset,
437                      16, i_height, i_l_stride, p_mb->i_l_stride,
438                      i_select, b_average );
439
440     /* Chrominance Cb */
441     MotionComponent( p_source->p_v
442                        + i_source_offset,
443                      p_mb->p_picture->p_v
444                        + i_dest_offset,
445                      16, i_height, i_l_stride, p_mb->i_l_stride,
446                      i_select, b_average );
447 #endif
448 }
449
450 /*****************************************************************************
451  * vdec_MotionFieldField : motion compensation for field motion type (field)
452  *****************************************************************************/
453 #define FIELDFIELD( MOTION )                                            \
454     picture_t *     p_pred;                                             \
455                                                                         \
456     if( p_mb->i_mb_type & MB_MOTION_FORWARD )                           \
457     {                                                                   \
458         if( p_mb->b_P_second                                            \
459              && (p_mb->b_motion_field != p_mb->ppi_field_select[0][0]) )\
460             p_pred = p_mb->p_picture;                                   \
461         else                                                            \
462             p_pred = p_mb->p_forward;                                   \
463                                                                         \
464         MOTION( p_mb, p_pred, p_mb->ppi_field_select[0][0],             \
465                 p_mb->b_motion_field,                                   \
466                 p_mb->pppi_motion_vectors[0][0][0],                     \
467                 p_mb->pppi_motion_vectors[0][0][1],                     \
468                 p_mb->i_l_stride, p_mb->i_c_stride, 16, 0, 0 );         \
469                                                                         \
470         if( p_mb->i_mb_type & MB_MOTION_BACKWARD )                      \
471         {                                                               \
472             MOTION( p_mb, p_mb->p_backward,                             \
473                     p_mb->ppi_field_select[0][1],                       \
474                     p_mb->b_motion_field,                               \
475                     p_mb->pppi_motion_vectors[0][1][0],                 \
476                     p_mb->pppi_motion_vectors[0][1][1],                 \
477                     p_mb->i_l_stride, p_mb->i_c_stride, 16, 0, 1 );     \
478     }                                                                   \
479                                                                         \
480     else /* MB_MOTION_BACKWARD */                                       \
481     {                                                                   \
482         MOTION( p_mb, p_mb->p_backward, p_mb->ppi_field_select[0][1],   \
483                 p_mb->b_motion_field,                                   \
484                 p_mb->pppi_motion_vectors[0][1][0],                     \
485                 p_mb->pppi_motion_vectors[0][1][1],                     \
486                 p_mb->i_l_stride, p_mb->i_c_stride, 16, 0, 0 );         \
487     }                                                                   \
488 }
489
490 void vdec_MotionFieldField420( macroblock_t * p_mb )
491 {
492     FIELDFIELD( Motion420 )
493 }
494
495 void vdec_MotionFieldField422( macroblock_t * p_mb )
496 {
497     //FIELDFIELD( Motion422 )
498 }
499
500 void vdec_MotionFieldField444( macroblock_t * p_mb )
501 {
502     //FIELDFIELD( Motion444 )
503 }
504
505 /*****************************************************************************
506  * vdec_MotionField16x8XXX?? : motion compensation for 16x8 motion type (field)
507  *****************************************************************************/
508 #define FIELD16X8( MOTION )                                             \
509 {                                                                       \
510     picture_t *     p_pred;                                             \
511                                                                         \
512     if( p_mb->i_mb_type & MB_MOTION_FORWARD )                           \
513     {                                                                   \
514         if( p_mb->b_P_second                                            \
515              && (p_mb->b_motion_field != p_mb->ppi_field_select[0][0]) )\
516             p_pred = p_mb->p_picture;                                   \
517         else                                                            \
518             p_pred = p_mb->p_forward;                                   \
519                                                                         \
520         MOTION( p_mb, p_pred, p_mb->ppi_field_select[0][0],             \
521                 p_mb->b_motion_field,                                   \
522                 p_mb->pppi_motion_vectors[0][0][0],                     \
523                 p_mb->pppi_motion_vectors[0][0][1],                     \
524                 p_mb->i_l_stride, p_mb->i_c_stride, 8, 0, 0 );          \
525                                                                         \
526         if( p_mb->b_P_second                                            \
527              && (p_mb->b_motion_field != p_mb->ppi_field_select[1][0]) )\
528             p_pred = p_mb->p_picture;                                   \
529         else                                                            \
530             p_pred = p_mb->p_forward;                                   \
531                                                                         \
532         MOTION( p_mb, p_pred, p_mb->ppi_field_select[1][0],             \
533                 p_mb->b_motion_field,                                   \
534                 p_mb->pppi_motion_vectors[1][0][0],                     \
535                 p_mb->pppi_motion_vectors[1][0][1],                     \
536                 p_mb->i_l_stride, p_mb->i_c_stride, 8, 8, 0 );          \
537                                                                         \
538         if( p_mb->i_mb_type & MB_MOTION_BACKWARD )                      \
539         {                                                               \
540             MOTION( p_mb, p_mb->p_backward,                             \
541                     p_mb->ppi_field_select[0][1],                       \
542                     p_mb->b_motion_field,                               \
543                     p_mb->pppi_motion_vectors[0][1][0],                 \
544                     p_mb->pppi_motion_vectors[0][1][1],                 \
545                     p_mb->i_l_stride, p_mb->i_c_stride, 8, 0, 1 );      \
546                                                                         \
547             MOTION( p_mb, p_mb->p_backward,                             \
548                     p_mb->ppi_field_select[1][1],                       \
549                     p_mb->b_motion_field,                               \
550                     p_mb->pppi_motion_vectors[1][1][0],                 \
551                     p_mb->pppi_motion_vectors[1][1][1],                 \
552                     p_mb->i_l_stride, p_mb->i_c_stride, 8, 8, 1 );      \
553         }                                                               \
554     }                                                                   \
555                                                                         \
556     else /* MB_MOTION_BACKWARD */                                       \
557     {                                                                   \
558         MOTION( p_mb, p_mb->p_backward, p_mb->ppi_field_select[0][1],   \
559                 p_mb->b_motion_field,                                   \
560                 p_mb->pppi_motion_vectors[0][1][0],                     \
561                 p_mb->pppi_motion_vectors[0][1][1],                     \
562                 p_mb->i_l_stride, p_mb->i_c_stride, 8, 0, 0 );          \
563                                                                         \
564         MOTION( p_mb, p_mb->p_backward, p_mb->ppi_field_select[1][1],   \
565                 p_mb->b_motion_field,                                   \
566                 p_mb->pppi_motion_vectors[1][1][0],                     \
567                 p_mb->pppi_motion_vectors[1][1][1],                     \
568                 p_mb->i_l_stride, p_mb->i_c_stride, 8, 8, 0 );          \
569     }                                                                   \
570 }
571
572 void vdec_MotionField16x8420( macroblock_t * p_mb )
573 {
574     FIELD16X8( Motion420 )
575 }
576
577 void vdec_MotionField16x8422( macroblock_t * p_mb )
578 {
579     //FIELD16X8( Motion422 )
580 }
581
582 void vdec_MotionField16x8444( macroblock_t * p_mb )
583 {
584     //FIELD16X8( Motion444 )
585 }
586
587 /*****************************************************************************
588  * vdec_MotionFieldDMVXXX?? : motion compensation for dmv motion type (field)
589  *****************************************************************************/
590 #define FIELDDMV( MOTION )                                              \
591 {                                                                       \
592     /* This is necessarily a MOTION_FORWARD only macroblock, in a P     \
593      * picture. */                                                      \
594     picture_t *     p_pred;                                             \
595                                                                         \
596     /* predict from field of same parity */                             \
597     MOTION( p_mb, p_mb->p_forward,                                      \
598             p_mb->b_motion_field, p_mb->b_motion_field,                 \
599             p_mb->pppi_motion_vectors[0][0][0],                         \
600             p_mb->pppi_motion_vectors[0][0][1],                         \
601             p_mb->i_l_stride, p_mb->i_c_stride, 16, 0, 0 );             \
602                                                                         \
603     if( p_mb->b_P_second )                                              \
604         p_pred = p_mb->p_picture;                                       \
605     else                                                                \
606         p_pred = p_mb->p_forward;                                       \
607                                                                         \
608     /* predict from field of opposite parity */                         \
609     MOTION( p_mb, p_pred, !p_mb->b_motion_field, p_mb->b_motion_field,  \
610             p_mb->ppi_dmv[0][0], p_mb->ppi_dmv[0][1],                   \
611             p_mb->i_l_stride, p_mb->i_c_stride, 16, 0, 1 );             \
612 } /* FIELDDMV */
613
614 void vdec_MotionFieldDMV420( macroblock_t * p_mb )
615 {
616     FIELDDMV( Motion420 )
617 }
618
619 void vdec_MotionFieldDMV422( macroblock_t * p_mb )
620 {
621     //FIELDDMV( Motion422 )
622 }
623
624 void vdec_MotionFieldDMV444( macroblock_t * p_mb )
625 {
626     //FIELDDMV( Motion444 )
627 }
628
629 /*****************************************************************************
630  * vdec_MotionFrameFrameXXX?? : motion compensation for frame motion type (frame)
631  *****************************************************************************/
632 #define FRAMEFRAME( MOTION )                                            \
633 {                                                                       \
634     if( p_mb->i_mb_type & MB_MOTION_FORWARD )                           \
635     {                                                                   \
636         MOTION( p_mb, p_mb->p_forward, 0, 0,                            \
637                 p_mb->pppi_motion_vectors[0][0][0],                     \
638                 p_mb->pppi_motion_vectors[0][0][1],                     \
639                 p_mb->i_l_stride, p_mb->i_c_stride, 16, 0, 0 );         \
640                                                                         \
641         if( p_mb->i_mb_type & MB_MOTION_BACKWARD )                      \
642         {                                                               \
643             MOTION( p_mb, p_mb->p_backward, 0, 0,                       \
644                     p_mb->pppi_motion_vectors[0][1][0],                 \
645                     p_mb->pppi_motion_vectors[0][1][1],                 \
646                     p_mb->i_l_stride, p_mb->i_c_stride, 16, 0, 1 );     \
647         }                                                               \
648     }                                                                   \
649                                                                         \
650     else /* MB_MOTION_BACKWARD */                                       \
651     {                                                                   \
652         MOTION( p_mb, p_mb->p_backward, 0, 0,                           \
653                 p_mb->pppi_motion_vectors[0][1][0],                     \
654                 p_mb->pppi_motion_vectors[0][1][1],                     \
655                 p_mb->i_l_stride, p_mb->i_c_stride, 16, 0, 0 );         \
656     }                                                                   \
657 } /* FRAMEFRAME */
658
659 void vdec_MotionFrameFrame420( macroblock_t * p_mb )
660 {
661     FRAMEFRAME( Motion420 )
662 }
663
664 void vdec_MotionFrameFrame422( macroblock_t * p_mb )
665 {
666     //FRAMEFRAME( Motion422 )
667 }
668
669 void vdec_MotionFrameFrame444( macroblock_t * p_mb )
670 {
671     //FRAMEFRAME( Motion444 )
672 }
673
674 /*****************************************************************************
675  * vdec_MotionFrameFieldXXX?? : motion compensation for field motion type (frame)
676  *****************************************************************************/
677 #define FRAMEFIELD( MOTION )                                            \
678 {                                                                       \
679     int i_l_stride = p_mb->i_l_stride << 1;                             \
680     int i_c_stride = p_mb->i_c_stride << 1;                             \
681                                                                         \
682     if( p_mb->i_mb_type & MB_MOTION_FORWARD )                           \
683     {                                                                   \
684         MOTION( p_mb, p_mb->p_forward, p_mb->ppi_field_select[0][0], 0, \
685                 p_mb->pppi_motion_vectors[0][0][0],                     \
686                 p_mb->pppi_motion_vectors[0][0][1],                     \
687                 i_l_stride, i_c_stride, 8, 0, 0 );                      \
688                                                                         \
689         MOTION( p_mb, p_mb->p_forward, p_mb->ppi_field_select[1][0], 1, \
690                 p_mb->pppi_motion_vectors[1][0][0],                     \
691                 p_mb->pppi_motion_vectors[1][0][1],                     \
692                 i_l_stride, i_c_stride, 8, 0, 0 );                      \
693                                                                         \
694         if( p_mb->i_mb_type & MB_MOTION_BACKWARD )                      \
695         {                                                               \
696             MOTION( p_mb, p_mb->p_backward,                             \
697                     p_mb->ppi_field_select[0][1], 0,                    \
698                     p_mb->pppi_motion_vectors[0][1][0],                 \
699                     p_mb->pppi_motion_vectors[0][1][1],                 \
700                     i_l_stride, i_c_stride, 8, 0, 1 );                  \
701                                                                         \
702             MOTION( p_mb, p_mb->p_backward,                             \
703                     p_mb->ppi_field_select[1][1], 1,                    \
704                     p_mb->pppi_motion_vectors[1][1][0],                 \
705                     p_mb->pppi_motion_vectors[1][1][1],                 \
706                     i_l_stride, i_c_stride, 8, 0, 1 );                  \
707         }                                                               \
708     }                                                                   \
709                                                                         \
710     else /* MB_MOTION_BACKWARD only */                                  \
711     {                                                                   \
712         MOTION( p_mb, p_mb->p_backward, p_mb->ppi_field_select[0][1], 0,\
713                 p_mb->pppi_motion_vectors[0][1][0],                     \
714                 p_mb->pppi_motion_vectors[0][1][1],                     \
715                 i_l_stride, i_c_stride, 8, 0, 0 );                      \
716                                                                         \
717         MOTION( p_mb, p_mb->p_backward, p_mb->ppi_field_select[1][1], 1,\
718                 p_mb->pppi_motion_vectors[1][1][0],                     \
719                 p_mb->pppi_motion_vectors[1][1][1],                     \
720                 i_l_stride, i_c_stride, 8, 0, 0 );                      \
721     }                                                                   \
722 } /* FRAMEFIELD */
723
724 void vdec_MotionFrameField420( macroblock_t * p_mb )
725 {
726     FRAMEFIELD( Motion420 )
727 }
728
729 void vdec_MotionFrameField422( macroblock_t * p_mb )
730 {
731     //FRAMEFIELD( Motion422 )
732 }
733
734 void vdec_MotionFrameField444( macroblock_t * p_mb )
735 {
736     //FRAMEFIELD( Motion444 )
737 }
738
739 /*****************************************************************************
740  * vdec_MotionFrameDMVXXX?? : motion compensation for dmv motion type (frame)
741  *****************************************************************************/
742 #define FRAMEDMV( MOTION )                                              \
743 {                                                                       \
744     /* This is necessarily a MOTION_FORWARD only macroblock, in a P     \
745      * picture. */                                                      \
746                                                                         \
747     /* predict top field from top field */                              \
748     MOTION( p_mb, p_mb->p_forward, 0, 0,                                \
749             p_mb->pppi_motion_vectors[0][0][0],                         \
750             p_mb->pppi_motion_vectors[0][0][1],                         \
751             /* XXX?? XXX?? >> 1 ? */                                        \
752             p_mb->i_l_stride << 1, p_mb->i_c_stride << 1, 8, 0, 0 );    \
753                                                                         \
754     /* predict and add to top field from bottom field */                \
755     MOTION( p_mb, p_mb->p_forward, 1, 0,                                \
756             p_mb->ppi_dmv[0][0], p_mb->ppi_dmv[0][1],                   \
757             p_mb->i_l_stride << 1, p_mb->i_c_stride << 1, 8, 0, 1 );    \
758                                                                         \
759     /* predict bottom field from bottom field */                        \
760     MOTION( p_mb, p_mb->p_forward, 1, 1,                                \
761             p_mb->pppi_motion_vectors[0][0][0],                         \
762             p_mb->pppi_motion_vectors[0][0][1],                         \
763             /* XXX?? XXX?? >> 1 ? */                                        \
764             p_mb->i_l_stride << 1, p_mb->i_c_stride << 1, 8, 0, 0 );    \
765                                                                         \
766     /* predict and add to bottom field from top field */                \
767     MOTION( p_mb, p_mb->p_forward, 1, 0,                                \
768             p_mb->ppi_dmv[1][0], p_mb->ppi_dmv[1][1],                   \
769             p_mb->i_l_stride << 1, p_mb->i_c_stride << 1, 8, 0, 1 );    \
770 } /* FRAMEDMV */
771
772 void vdec_MotionFrameDMV420( macroblock_t * p_mb )
773 {
774     FRAMEDMV( Motion420 )
775 }
776
777 void vdec_MotionFrameDMV422( macroblock_t * p_mb )
778 {
779     //FRAMEDMV( Motion422 )
780 }
781
782 void vdec_MotionFrameDMV444( macroblock_t * p_mb )
783 {
784     //FRAMEDMV( Motion444 )
785 }