diff options
author | Zhao Yakui <yakui.zhao@intel.com> | 2013-08-12 15:13:23 +0800 |
---|---|---|
committer | Xiang, Haihao <haihao.xiang@intel.com> | 2013-09-06 15:32:29 +0800 |
commit | 19c32cefd707c0b547be5da5123160eaf22411bb (patch) | |
tree | 619b15b2b581af3fe9dea6c8a4fa344779fe7ba9 | |
parent | fe782daf315bf491780dc61a6b866f13ec190762 (diff) |
Use the scoreboard/walker to assure MB dependency for MPEG2 encoding
If MVP is added for MPEG2 encoding, it must be assured that the left macroblock
should be already finished before processing the current macroblock.
And this needs the scoreboard/walker mechanism to assure MB dependency.
Signed-off-by: Zhao Yakui <yakui.zhao@intel.com>
(cherry picked from commit 5d2163d02d395fc0a794d834979a06c287bf9ba5)
-rw-r--r-- | src/gen6_mfc_common.c | 124 | ||||
-rw-r--r-- | src/gen6_vme.h | 7 | ||||
-rw-r--r-- | src/gen75_vme.c | 37 |
3 files changed, 166 insertions, 2 deletions
diff --git a/src/gen6_mfc_common.c b/src/gen6_mfc_common.c index ac28d23..469bf64 100644 --- a/src/gen6_mfc_common.c +++ b/src/gen6_mfc_common.c @@ -1186,3 +1186,127 @@ void intel_vme_mpeg2_state_setup(VADriverContextP ctx, vme_state_message[MPEG2_PIC_WIDTH_HEIGHT] = (height_in_mbs << 16) | width_in_mbs; } + +void +gen7_vme_mpeg2_walker_fill_vme_batchbuffer(VADriverContextP ctx, + struct encode_state *encode_state, + int mb_width, int mb_height, + int kernel, + struct intel_encoder_context *encoder_context) +{ + struct gen6_vme_context *vme_context = encoder_context->vme_context; + unsigned int *command_ptr; + +#define MPEG2_SCOREBOARD (1 << 21) + + dri_bo_map(vme_context->vme_batchbuffer.bo, 1); + command_ptr = vme_context->vme_batchbuffer.bo->virtual; + + { + unsigned int mb_intra_ub, score_dep; + int x_outer, y_outer, x_inner, y_inner; + int xtemp_outer = 0; + int first_mb = 0; + int num_mb = mb_width * mb_height; + + x_outer = 0; + y_outer = 0; + + + for (; x_outer < (mb_width -2 ) && !loop_in_bounds(x_outer, y_outer, first_mb, num_mb, mb_width, mb_height); ) { + x_inner = x_outer; + y_inner = y_outer; + for (; !loop_in_bounds(x_inner, y_inner, first_mb, num_mb, mb_width, mb_height);) { + mb_intra_ub = 0; + score_dep = 0; + if (x_inner != 0) { + mb_intra_ub |= INTRA_PRED_AVAIL_FLAG_AE; + score_dep |= MB_SCOREBOARD_A; + } + if (y_inner != 0) { + mb_intra_ub |= INTRA_PRED_AVAIL_FLAG_B; + score_dep |= MB_SCOREBOARD_B; + + if (x_inner != 0) + mb_intra_ub |= INTRA_PRED_AVAIL_FLAG_D; + + if (x_inner != (mb_width -1)) { + mb_intra_ub |= INTRA_PRED_AVAIL_FLAG_C; + score_dep |= MB_SCOREBOARD_C; + } + } + + *command_ptr++ = (CMD_MEDIA_OBJECT | (8 - 2)); + *command_ptr++ = kernel; + *command_ptr++ = MPEG2_SCOREBOARD; + /* Indirect data */ + *command_ptr++ = 0; + /* the (X, Y) term of scoreboard */ + *command_ptr++ = ((y_inner << 16) | x_inner); + *command_ptr++ = score_dep; + /*inline data */ + *command_ptr++ = (mb_width << 16 | y_inner << 8 | x_inner); + *command_ptr++ = ((1 << 18) | (1 << 16) | (mb_intra_ub << 8)); + x_inner -= 2; + y_inner += 1; + } + x_outer += 1; + } + + xtemp_outer = mb_width - 2; + if (xtemp_outer < 0) + xtemp_outer = 0; + x_outer = xtemp_outer; + y_outer = 0; + for (;!loop_in_bounds(x_outer, y_outer, first_mb, num_mb, mb_width, mb_height); ) { + y_inner = y_outer; + x_inner = x_outer; + for (; !loop_in_bounds(x_inner, y_inner, first_mb, num_mb, mb_width, mb_height);) { + mb_intra_ub = 0; + score_dep = 0; + if (x_inner != 0) { + mb_intra_ub |= INTRA_PRED_AVAIL_FLAG_AE; + score_dep |= MB_SCOREBOARD_A; + } + if (y_inner != 0) { + mb_intra_ub |= INTRA_PRED_AVAIL_FLAG_B; + score_dep |= MB_SCOREBOARD_B; + + if (x_inner != 0) + mb_intra_ub |= INTRA_PRED_AVAIL_FLAG_D; + + if (x_inner != (mb_width -1)) { + mb_intra_ub |= INTRA_PRED_AVAIL_FLAG_C; + score_dep |= MB_SCOREBOARD_C; + } + } + + *command_ptr++ = (CMD_MEDIA_OBJECT | (8 - 2)); + *command_ptr++ = kernel; + *command_ptr++ = MPEG2_SCOREBOARD; + /* Indirect data */ + *command_ptr++ = 0; + /* the (X, Y) term of scoreboard */ + *command_ptr++ = ((y_inner << 16) | x_inner); + *command_ptr++ = score_dep; + /*inline data */ + *command_ptr++ = (mb_width << 16 | y_inner << 8 | x_inner); + *command_ptr++ = ((1 << 18) | (1 << 16) | (mb_intra_ub << 8)); + + x_inner -= 2; + y_inner += 1; + } + x_outer++; + if (x_outer >= mb_width) { + y_outer += 1; + x_outer = xtemp_outer; + } + } + } + + *command_ptr++ = 0; + *command_ptr++ = MI_BATCH_BUFFER_END; + + dri_bo_unmap(vme_context->vme_batchbuffer.bo); + return; +} diff --git a/src/gen6_vme.h b/src/gen6_vme.h index ab0ff3b..b130b58 100644 --- a/src/gen6_vme.h +++ b/src/gen6_vme.h @@ -151,4 +151,11 @@ intel_vme_mpeg2_state_setup(VADriverContextP ctx, struct encode_state *encode_state, struct intel_encoder_context *encoder_context); +extern void +gen7_vme_mpeg2_walker_fill_vme_batchbuffer(VADriverContextP ctx, + struct encode_state *encode_state, + int mb_width, int mb_height, + int kernel, + struct intel_encoder_context *encoder_context); + #endif /* _GEN6_VME_H_ */ diff --git a/src/gen75_vme.c b/src/gen75_vme.c index 3935528..3e769ed 100644 --- a/src/gen75_vme.c +++ b/src/gen75_vme.c @@ -916,14 +916,47 @@ gen75_vme_mpeg2_pipeline_programing(VADriverContextP ctx, { struct gen6_vme_context *vme_context = encoder_context->vme_context; struct intel_batchbuffer *batch = encoder_context->base.batch; + VAEncPictureParameterBufferMPEG2 *pic_param = NULL; VAEncSequenceParameterBufferMPEG2 *seq_param = (VAEncSequenceParameterBufferMPEG2 *)encode_state->seq_param_ext->buffer; int width_in_mbs = ALIGN(seq_param->picture_width, 16) / 16; int height_in_mbs = ALIGN(seq_param->picture_height, 16) / 16; + bool allow_hwscore = true; + int s; + int kernel_shader; - gen75_vme_mpeg2_fill_vme_batchbuffer(ctx, + pic_param = (VAEncPictureParameterBufferMPEG2 *)encode_state->pic_param_ext->buffer; + + for (s = 0; s < encode_state->num_slice_params_ext; s++) { + int j; + VAEncSliceParameterBufferMPEG2 *slice_param = (VAEncSliceParameterBufferMPEG2 *)encode_state->slice_params_ext[s]->buffer; + + for (j = 0; j < encode_state->slice_params_ext[s]->num_elements; j++) { + if (slice_param->macroblock_address % width_in_mbs) { + allow_hwscore = false; + break; + } + } + } + + pic_param = (VAEncPictureParameterBufferMPEG2 *)encode_state->pic_param_ext->buffer; + if (pic_param->picture_type == VAEncPictureTypeIntra) { + allow_hwscore = false; + kernel_shader = VME_INTRA_SHADER; + } else { + kernel_shader = VME_INTER_SHADER; + } + + if (allow_hwscore) + gen7_vme_mpeg2_walker_fill_vme_batchbuffer(ctx, + encode_state, + width_in_mbs, height_in_mbs, + kernel_shader, + encoder_context); + else + gen75_vme_mpeg2_fill_vme_batchbuffer(ctx, encode_state, width_in_mbs, height_in_mbs, - is_intra ? VME_INTRA_SHADER : VME_INTER_SHADER, + kernel_shader, 0, encoder_context); |