summaryrefslogtreecommitdiff
path: root/src/gen75_mfc.c
diff options
context:
space:
mode:
authorXiang, Haihao <haihao.xiang@intel.com>2012-12-13 13:39:10 +0800
committerXiang, Haihao <haihao.xiang@intel.com>2012-12-14 16:03:26 +0800
commit30b1a1198c54d175c2eff877e9e30a423d59bae7 (patch)
tree675d38f60a0d54f12838b96940f14bbe7c113b8e /src/gen75_mfc.c
parent593eaafc319d3d71c5c4b28915558e9e366c240d (diff)
downloadlibva-intel-driver-30b1a1198c54d175c2eff877e9e30a423d59bae7.tar.gz
libva-intel-driver-30b1a1198c54d175c2eff877e9e30a423d59bae7.tar.bz2
libva-intel-driver-30b1a1198c54d175c2eff877e9e30a423d59bae7.zip
Fix Motion Vector
Signed-off-by: Xiang, Haihao <haihao.xiang@intel.com>
Diffstat (limited to 'src/gen75_mfc.c')
-rw-r--r--src/gen75_mfc.c65
1 files changed, 42 insertions, 23 deletions
diff --git a/src/gen75_mfc.c b/src/gen75_mfc.c
index b2130db..f876953 100644
--- a/src/gen75_mfc.c
+++ b/src/gen75_mfc.c
@@ -2000,8 +2000,44 @@ gen75_mfc_mpeg2_pak_object_intra(VADriverContextP ctx,
#define MV_OFFSET_IN_WORD 112
+static struct _mv_ranges
+{
+ int low; /* in the unit of 1/2 pixel */
+ int high; /* in the unit of 1/2 pixel */
+} mv_ranges[] = {
+ {0, 0},
+ {-16, 15},
+ {-32, 31},
+ {-64, 63},
+ {-128, 127},
+ {-256, 255},
+ {-512, 511},
+ {-1024, 1023},
+ {-2048, 2047},
+ {-4096, 4095}
+};
+
+static int
+mpeg2_motion_vector(int mv, int pos, int display_max, int f_code)
+{
+ if (mv + pos * 16 * 2 < 0 ||
+ mv + (pos + 1) * 16 * 2 > display_max * 2)
+ mv = 0;
+
+ if (f_code > 0 && f_code < 10) {
+ if (mv < mv_ranges[f_code].low)
+ mv = mv_ranges[f_code].low;
+
+ if (mv > mv_ranges[f_code].high)
+ mv = mv_ranges[f_code].high;
+ }
+
+ return mv;
+}
+
static int
gen75_mfc_mpeg2_pak_object_inter(VADriverContextP ctx,
+ struct encode_state *encode_state,
struct intel_encoder_context *encoder_context,
unsigned int *msg,
int width_in_mbs, int height_in_mbs,
@@ -2015,6 +2051,7 @@ gen75_mfc_mpeg2_pak_object_inter(VADriverContextP ctx,
unsigned char max_size_in_word,
struct intel_batchbuffer *batch)
{
+ VAEncPictureParameterBufferMPEG2 *pic_param = (VAEncPictureParameterBufferMPEG2 *)encode_state->pic_param_ext->buffer;
int len_in_dwords = 9;
short *mvptr, mvx0, mvy0, mvx1, mvy1;
@@ -2022,29 +2059,10 @@ gen75_mfc_mpeg2_pak_object_inter(VADriverContextP ctx,
batch = encoder_context->base.batch;
mvptr = (short *)msg;
- mvx0 = mvptr[MV_OFFSET_IN_WORD] / 2; /* the output from VME is in the unit of 1/4 pixel */
-
- if (mvx0 + x * 16 * 2 < 0 ||
- mvx0 + (x + 1) * 16 * 2 > width_in_mbs * 16 * 2)
- mvx0 = 0;
-
- mvy0 = mvptr[MV_OFFSET_IN_WORD + 1] / 2;
-
- if (mvy0 + y * 16 * 2 < 0 ||
- mvy0 + (y + 1) * 16 * 2 > height_in_mbs * 16 * 2)
- mvy0 = 0;
-
- mvx1 = mvptr[MV_OFFSET_IN_WORD + 2] / 2;
-
- if (mvx1 + x * 16 * 2 < 0 ||
- mvx1 + (x + 1) * 16 * 2 > width_in_mbs * 16 * 2)
- mvx1 = 0;
-
- mvy1 = mvptr[MV_OFFSET_IN_WORD + 3] / 2;
-
- if (mvy1 + y * 16 * 2 < 0 ||
- mvy1 + (y + 1) * 16 * 2 > height_in_mbs * 16 * 2)
- mvy1 = 0;
+ mvx0 = mpeg2_motion_vector(mvptr[MV_OFFSET_IN_WORD + 0] / 2, x, width_in_mbs * 16, pic_param->f_code[0][0]);
+ mvy0 = mpeg2_motion_vector(mvptr[MV_OFFSET_IN_WORD + 1] / 2, y, height_in_mbs * 16, pic_param->f_code[0][0]);
+ mvx1 = mpeg2_motion_vector(mvptr[MV_OFFSET_IN_WORD + 2] / 2, x, width_in_mbs * 16, pic_param->f_code[1][0]);
+ mvy1 = mpeg2_motion_vector(mvptr[MV_OFFSET_IN_WORD + 3] / 2, y, height_in_mbs * 16, pic_param->f_code[1][0]);
BEGIN_BCS_BATCH(batch, len_in_dwords);
@@ -2240,6 +2258,7 @@ gen75_mfc_mpeg2_pipeline_slice_group(VADriverContextP ctx,
slice_batch);
} else {
gen75_mfc_mpeg2_pak_object_inter(ctx,
+ encode_state,
encoder_context,
msg,
width_in_mbs, height_in_mbs,