Workaround for 720p/1080p encoding
authorXiang, Haihao <haihao.xiang@intel.com>
Sat, 2 Apr 2011 05:54:53 +0000 (13:54 +0800)
committerXiang, Haihao <haihao.xiang@intel.com>
Thu, 7 Apr 2011 06:45:03 +0000 (14:45 +0800)
Signed-off-by: Xiang, Haihao <haihao.xiang@intel.com>
i965_drv_video/gen6_mfc.c
i965_drv_video/gen6_vme.c
i965_drv_video/intel_batchbuffer.c
i965_drv_video/intel_batchbuffer.h

index 602d0d2..52b8bc3 100644 (file)
@@ -409,13 +409,14 @@ gen6_mfc_avc_insert_object(VADriverContextP ctx, int flush_data)
     ADVANCE_BCS_BATCH(ctx);
 }
 
-static void
+static int
 gen6_mfc_avc_pak_object(VADriverContextP ctx, int x, int y, int end_mb, int qp,unsigned int *msg)
 {
-    BEGIN_BCS_BATCH(ctx, 11);
+    int len_in_dowrds = 11;
 
-    OUT_BCS_BATCH(ctx, MFC_AVC_PAK_OBJECT | (11 -2 ) );
+    BEGIN_BCS_BATCH(ctx, len_in_dowrds);
 
+    OUT_BCS_BATCH(ctx, MFC_AVC_PAK_OBJECT | (len_in_dowrds - 2));
     OUT_BCS_BATCH(ctx, 0);
     OUT_BCS_BATCH(ctx, 0);
     OUT_BCS_BATCH(ctx, 
@@ -439,6 +440,7 @@ gen6_mfc_avc_pak_object(VADriverContextP ctx, int x, int y, int end_mb, int qp,u
 
     ADVANCE_BCS_BATCH(ctx);
 
+    return len_in_dowrds * 4;
 }
 
 static void gen6_mfc_init(VADriverContextP ctx)
@@ -506,30 +508,44 @@ void gen6_mfc_avc_pipeline_programing(VADriverContextP ctx, void *obj)
     struct gen6_media_state *media_state = &i965->gen6_media_state;
     VAEncSequenceParameterBufferH264 *pSequenceParameter = (VAEncSequenceParameterBufferH264 *)encode_state->seq_param->buffer;
     unsigned int *msg;
+    int emit_new_state = 1, object_len_in_bytes;
 
     intel_batchbuffer_start_atomic_bcs(ctx, 0x1000); 
-    intel_batchbuffer_emit_mi_flush_bcs(ctx);
-    gen6_mfc_pipe_mode_select(ctx);
-    gen6_mfc_surface_state(ctx);
-    gen6_mfc_pipe_buf_addr_state(ctx);
-    gen6_mfc_ind_obj_base_addr_state(ctx);
-    gen6_mfc_bsp_buf_base_addr_state(ctx);
-    gen6_mfc_avc_img_state(ctx);
-    gen6_mfc_avc_qm_state(ctx);
-    gen6_mfc_avc_directmode_state(ctx);
-    gen6_mfc_avc_slice_state(ctx);
-    gen6_mfc_avc_fqm_state(ctx);
-    /*gen6_mfc_avc_ref_idx_state(ctx);*/
-    /*gen6_mfc_avc_insert_object(ctx, 0);*/
 
     dri_bo_map(media_state->vme_output.bo , 1);
     msg = (unsigned int *)media_state->vme_output.bo->virtual;
-    for( y = 0; y < height_in_mbs; y++) {
-        for( x = 0; x < width_in_mbs; x++) { 
+
+    for (y = 0; y < height_in_mbs; y++) {
+        for (x = 0; x < width_in_mbs; x++) { 
             int last_mb = (y == (height_in_mbs-1)) && ( x == (width_in_mbs-1) );
             int qp = pSequenceParameter->initial_qp;
-            gen6_mfc_avc_pak_object(ctx, x, y, last_mb, qp, msg);
+
+            if (emit_new_state) {
+                intel_batchbuffer_emit_mi_flush_bcs(ctx);
+                gen6_mfc_pipe_mode_select(ctx);
+                gen6_mfc_surface_state(ctx);
+                gen6_mfc_pipe_buf_addr_state(ctx);
+                gen6_mfc_ind_obj_base_addr_state(ctx);
+                gen6_mfc_bsp_buf_base_addr_state(ctx);
+                gen6_mfc_avc_img_state(ctx);
+                gen6_mfc_avc_qm_state(ctx);
+                gen6_mfc_avc_directmode_state(ctx);
+                gen6_mfc_avc_slice_state(ctx);
+                gen6_mfc_avc_fqm_state(ctx);
+                /*gen6_mfc_avc_ref_idx_state(ctx);*/
+                /*gen6_mfc_avc_insert_object(ctx, 0);*/
+                emit_new_state = 0;
+            }
+
+            object_len_in_bytes = gen6_mfc_avc_pak_object(ctx, x, y, last_mb, qp, msg);
             msg += 4;
+
+            if (intel_batchbuffer_check_free_space_bcs(ctx, object_len_in_bytes) == 0) {
+                intel_batchbuffer_end_atomic_bcs(ctx);
+                intel_batchbuffer_flush_bcs(ctx);
+                emit_new_state = 1;
+                intel_batchbuffer_start_atomic_bcs(ctx, 0x1000);
+            }
         }
     }
 
index b62e1f8..a12bbea 100644 (file)
@@ -424,7 +424,7 @@ static void gen6_vme_idrt(VADriverContextP ctx)
     ADVANCE_BATCH(ctx);
 }
 
-static void gen6_vme_media_object(VADriverContextP ctx, 
+static int gen6_vme_media_object(VADriverContextP ctx, 
                                   VAContextID context, 
                                   struct mfc_encode_state *encode_state,
                                   int mb_x, int mb_y)
@@ -435,10 +435,11 @@ static void gen6_vme_media_object(VADriverContextP ctx,
     unsigned char *pPixel[17]; 
     int pitch = obj_surface->width;
     int mb_width = ALIGN(obj_surface->orig_width, 16) / 16;
+    int len_in_dowrds = 6 + 32 + 8;
 
-    BEGIN_BATCH(ctx, 6 + 32 + 8);
+    BEGIN_BATCH(ctx, len_in_dowrds);
     
-    OUT_BATCH(ctx, CMD_MEDIA_OBJECT | 44);
+    OUT_BATCH(ctx, CMD_MEDIA_OBJECT | (len_in_dowrds - 2));
     OUT_BATCH(ctx, VME_INTRA_SHADER);          /*Interface Descriptor Offset*/ 
     OUT_BATCH(ctx, 0);
     OUT_BATCH(ctx, 0);
@@ -552,6 +553,8 @@ static void gen6_vme_media_object(VADriverContextP ctx,
     drm_intel_gem_bo_unmap_gtt( obj_surface->bo );
 
     ADVANCE_BATCH(ctx);
+
+    return len_in_dowrds * 4;
 }
 
 static void gen6_vme_media_init(VADriverContextP ctx)
@@ -616,34 +619,46 @@ static void gen6_vme_pipeline_programing(VADriverContextP ctx,
 {
     struct i965_driver_data *i965 = i965_driver_data(ctx); 
     struct object_context *obj_context = CONTEXT(context);
-
     int width_in_mbs = (obj_context->picture_width + 15) / 16;
     int height_in_mbs = (obj_context->picture_height + 15) / 16;
-    int x,y;
+    int x, y;
+    int emit_new_state = 1, object_len_in_bytes;
 
     intel_batchbuffer_start_atomic(ctx, 0x1000);
-       
-    /*Step1: MI_FLUSH/PIPE_CONTROL*/
-    BEGIN_BATCH(ctx, 4);
-    OUT_BATCH(ctx, CMD_PIPE_CONTROL | 0x02);
-    OUT_BATCH(ctx, 0);
-    OUT_BATCH(ctx, 0);
-    OUT_BATCH(ctx, 0);
-    ADVANCE_BATCH(ctx);
-
-    /*Step2: State command PIPELINE_SELECT*/
-    gen6_vme_pipeline_select(ctx);                           
-
-    /*Step3: State commands configuring pipeline states*/
-    gen6_vme_state_base_address(ctx);
-    gen6_vme_vfe_state(ctx);
-    gen6_vme_curbe_load(ctx);
-    gen6_vme_idrt(ctx);
 
     for(y = 0; y < height_in_mbs; y++){
         for(x = 0; x < width_in_mbs; x++){     
+
+            if (emit_new_state) {
+                /*Step1: MI_FLUSH/PIPE_CONTROL*/
+                BEGIN_BATCH(ctx, 4);
+                OUT_BATCH(ctx, CMD_PIPE_CONTROL | 0x02);
+                OUT_BATCH(ctx, 0);
+                OUT_BATCH(ctx, 0);
+                OUT_BATCH(ctx, 0);
+                ADVANCE_BATCH(ctx);
+
+                /*Step2: State command PIPELINE_SELECT*/
+                gen6_vme_pipeline_select(ctx);                           
+
+                /*Step3: State commands configuring pipeline states*/
+                gen6_vme_state_base_address(ctx);
+                gen6_vme_vfe_state(ctx);
+                gen6_vme_curbe_load(ctx);
+                gen6_vme_idrt(ctx);
+
+                emit_new_state = 0;
+            }
+
             /*Step4: Primitive commands*/
-            gen6_vme_media_object(ctx, context, encode_state, x, y);
+            object_len_in_bytes = gen6_vme_media_object(ctx, context, encode_state, x, y);
+
+            if (intel_batchbuffer_check_free_space(ctx, object_len_in_bytes) == 0) {
+                intel_batchbuffer_end_atomic(ctx);     
+                intel_batchbuffer_flush(ctx);
+                emit_new_state = 1;
+                intel_batchbuffer_start_atomic(ctx, 0x1000);
+            }
         }
     }
 
index 9d623f1..f4e629a 100644 (file)
@@ -431,3 +431,19 @@ intel_batchbuffer_check_batchbuffer_flag(VADriverContextP ctx, int flag)
     intel_batchbuffer_flush_helper(ctx, intel->batch);
     intel->batch->flag = flag;
 }
+
+int
+intel_batchbuffer_check_free_space(VADriverContextP ctx, int size)
+{
+    struct intel_driver_data *intel = intel_driver_data(ctx);
+
+    return intel_batchbuffer_space_helper(intel->batch) >= size;
+}
+
+int
+intel_batchbuffer_check_free_space_bcs(VADriverContextP ctx, int size)
+{
+    struct intel_driver_data *intel = intel_driver_data(ctx);
+
+    return intel_batchbuffer_space_helper(intel->batch_bcs) >= size;
+}
index 25652e1..77174fe 100644 (file)
@@ -59,6 +59,9 @@ void intel_batchbuffer_advance_batch_bcs(VADriverContextP ctx);
 
 void intel_batchbuffer_check_batchbuffer_flag(VADriverContextP ctx, int flag);
 
+int intel_batchbuffer_check_free_space(VADriverContextP ctx, int size);
+int intel_batchbuffer_check_free_space_bcs(VADriverContextP ctx, int size);
+
 #define __BEGIN_BATCH(ctx, n, flag) do {                        \
         intel_batchbuffer_check_batchbuffer_flag(ctx, flag);    \
         intel_batchbuffer_require_space(ctx, (n) * 4);          \