i965_drv_video: multiple slices in a picture for H.264 40/540/1
authorXiang, Haihao <haihao.xiang@intel.com>
Tue, 6 Apr 2010 07:06:45 +0000 (15:06 +0800)
committerXiang, Haihao <haihao.xiang@intel.com>
Tue, 6 Apr 2010 07:07:52 +0000 (15:07 +0800)
i965_drv_video/i965_avc_bsd.c
i965_drv_video/i965_drv_video.c
i965_drv_video/i965_drv_video.h
i965_drv_video/i965_media_h264.c
i965_drv_video/i965_media_mpeg2.c

index d9a45b7..80d26d4 100644 (file)
@@ -85,9 +85,9 @@ i965_avc_bsd_initialize_private_surface_data(VADriverContextP ctx, struct object
 }
 
 static void
-i965_bsd_ind_obj_base_address(VADriverContextP ctx, struct decode_state *decode_state)
+i965_bsd_ind_obj_base_address(VADriverContextP ctx, struct decode_state *decode_state, int slice)
 {
-    dri_bo *ind_bo = decode_state->slice_data->bo;
+    dri_bo *ind_bo = decode_state->slice_datas[slice]->bo;
 
     BEGIN_BCS_BATCH(ctx, 3);
     OUT_BCS_BATCH(ctx, CMD_BSD_IND_OBJ_BASE_ADDR | (3 - 2));
@@ -401,21 +401,19 @@ i965_avc_bsd_slice_state(VADriverContextP ctx,
 }
 
 static void
-i965_avc_bsd_buf_base_state(VADriverContextP ctx, struct decode_state *decode_state)
+i965_avc_bsd_buf_base_state(VADriverContextP ctx,
+                            VAPictureParameterBufferH264 *pic_param, 
+                            VASliceParameterBufferH264 *slice_param)
 {
     struct i965_driver_data *i965 = i965_driver_data(ctx);
     struct i965_media_state *media_state = &i965->media_state;
     struct i965_h264_context *i965_h264_context;
     struct i965_avc_bsd_context *i965_avc_bsd_context;
     int i;
-    VAPictureParameterBufferH264 *pic_param;
     VAPictureH264 *va_pic;
     struct object_surface *obj_surface;
     struct i965_avc_bsd_surface *avc_bsd_surface;
 
-    assert(decode_state->pic_param && decode_state->pic_param->buffer);
-    pic_param = (VAPictureParameterBufferH264 *)decode_state->pic_param->buffer;
-
     assert(media_state->private_context);
     i965_h264_context = (struct i965_h264_context *)media_state->private_context;
     i965_avc_bsd_context = &i965_h264_context->i965_avc_bsd_context;
@@ -770,34 +768,36 @@ i965_avc_bsd_phantom_slice(VADriverContextP ctx,
 void 
 i965_avc_bsd_pipeline(VADriverContextP ctx, struct decode_state *decode_state)
 {
-    int i;
+    int i, j;
     VAPictureParameterBufferH264 *pic_param;
     VASliceParameterBufferH264 *slice_param;
 
     assert(decode_state->pic_param && decode_state->pic_param->buffer);
     pic_param = (VAPictureParameterBufferH264 *)decode_state->pic_param->buffer;
-    assert(decode_state->slice_param && decode_state->slice_param->buffer);
-    slice_param = (VASliceParameterBufferH264 *)decode_state->slice_param->buffer;
-
     intel_batchbuffer_start_atomic_bcs(ctx, 0x1000);
-    i965_bsd_ind_obj_base_address(ctx, decode_state);
-
-    assert(decode_state->num_slices == 1); /* FIXME: */
-    for (i = 0; i < decode_state->num_slices; i++) {
-        assert(slice_param->slice_data_flag == VA_SLICE_DATA_FLAG_ALL);
-        assert((slice_param->slice_type == SLICE_TYPE_I) ||
-               (slice_param->slice_type == SLICE_TYPE_P) ||
-               (slice_param->slice_type == SLICE_TYPE_B)); /* hardware requirement */
-
-        if (i == 0) {
-            i965_avc_bsd_img_state(ctx, decode_state);
-            i965_avc_bsd_qm_state(ctx, decode_state);
+
+    i965_avc_bsd_img_state(ctx, decode_state);
+    i965_avc_bsd_qm_state(ctx, decode_state);
+
+    for (j = 0; j < decode_state->num_slice_params; j++) {
+        assert(decode_state->slice_params && decode_state->slice_params[j]->buffer);
+        slice_param = (VASliceParameterBufferH264 *)decode_state->slice_params[j]->buffer;
+
+        i965_bsd_ind_obj_base_address(ctx, decode_state, j);
+
+        assert(decode_state->slice_params[j]->num_elements == 1);  /* FIXME */
+        for (i = 0; i < decode_state->slice_params[j]->num_elements; i++) {
+            assert(slice_param->slice_data_flag == VA_SLICE_DATA_FLAG_ALL);
+            assert((slice_param->slice_type == SLICE_TYPE_I) ||
+                   (slice_param->slice_type == SLICE_TYPE_P) ||
+                   (slice_param->slice_type == SLICE_TYPE_B)); /* hardware requirement */
+
+            i965_avc_bsd_slice_state(ctx, pic_param, slice_param);
+            i965_avc_bsd_buf_base_state(ctx, pic_param, slice_param);
+            i965_avc_bsd_object(ctx, decode_state, pic_param, slice_param);
+            slice_param++;
         }
 
-        i965_avc_bsd_slice_state(ctx, pic_param, slice_param);
-        i965_avc_bsd_buf_base_state(ctx, decode_state);
-        i965_avc_bsd_object(ctx, decode_state, pic_param, slice_param);
-        slice_param++;
     }
 
     i965_avc_bsd_phantom_slice(ctx, decode_state, pic_param);
index e0b5ee4..c902834 100644 (file)
@@ -632,12 +632,23 @@ static void
 i965_destroy_context(struct object_heap *heap, struct object_base *obj)
 {
     struct object_context *obj_context = (struct object_context *)obj;
+    int i;
+
+    assert(obj_context->decode_state.num_slice_params <= obj_context->decode_state.max_slice_params);
+    assert(obj_context->decode_state.num_slice_datas <= obj_context->decode_state.max_slice_datas);
 
     i965_release_buffer_store(&obj_context->decode_state.pic_param);
-    i965_release_buffer_store(&obj_context->decode_state.slice_param);
     i965_release_buffer_store(&obj_context->decode_state.iq_matrix);
     i965_release_buffer_store(&obj_context->decode_state.bit_plane);
-    i965_release_buffer_store(&obj_context->decode_state.slice_data);
+
+    for (i = 0; i < obj_context->decode_state.num_slice_params; i++)
+        i965_release_buffer_store(&obj_context->decode_state.slice_params[i]);
+
+    for (i = 0; i < obj_context->decode_state.num_slice_datas; i++)
+        i965_release_buffer_store(&obj_context->decode_state.slice_datas[i]);
+
+    free(obj_context->decode_state.slice_params);
+    free(obj_context->decode_state.slice_datas);
     free(obj_context->render_targets);
     object_heap_free(heap, obj);
 }
@@ -678,6 +689,12 @@ i965_CreateContext(VADriverContextP ctx,
     *context = contextID;
     memset(&obj_context->decode_state, 0, sizeof(obj_context->decode_state));
     obj_context->decode_state.current_render_target = -1;
+    obj_context->decode_state.max_slice_params = NUM_SLICES;
+    obj_context->decode_state.max_slice_datas = NUM_SLICES;
+    obj_context->decode_state.slice_params = calloc(obj_context->decode_state.max_slice_params,
+                                                    sizeof(*obj_context->decode_state.slice_params));
+    obj_context->decode_state.slice_datas = calloc(obj_context->decode_state.max_slice_datas,
+                                                   sizeof(*obj_context->decode_state.slice_datas));
     obj_context->config_id = config_id;
     obj_context->picture_width = picture_width;
     obj_context->picture_height = picture_height;
@@ -791,6 +808,7 @@ i965_CreateBuffer(VADriverContextP ctx,
             memcpy(buffer_store->buffer, data, size * num_elements);
     }
 
+    buffer_store->num_elements = obj_buffer->num_elements;
     i965_reference_buffer_store(&obj_buffer->buffer_store, buffer_store);
     i965_release_buffer_store(&buffer_store);
     *buf_id = bufferID;
@@ -971,10 +989,18 @@ i965_render_slice_parameter_buffer(VADriverContextP ctx,
 {
     assert(obj_buffer->buffer_store->bo == NULL);
     assert(obj_buffer->buffer_store->buffer);
-    i965_release_buffer_store(&obj_context->decode_state.slice_param);
-    i965_reference_buffer_store(&obj_context->decode_state.slice_param,
+    
+    if (obj_context->decode_state.num_slice_params == obj_context->decode_state.max_slice_params) {
+        obj_context->decode_state.slice_params = realloc(obj_context->decode_state.slice_params,
+                                                        (obj_context->decode_state.max_slice_params + NUM_SLICES) * sizeof(*obj_context->decode_state.slice_params));
+        memset(obj_context->decode_state.slice_params + obj_context->decode_state.max_slice_params, 0, NUM_SLICES * sizeof(*obj_context->decode_state.slice_params));
+        obj_context->decode_state.max_slice_params += NUM_SLICES;
+    }
+        
+    i965_release_buffer_store(&obj_context->decode_state.slice_params[obj_context->decode_state.num_slice_params]);
+    i965_reference_buffer_store(&obj_context->decode_state.slice_params[obj_context->decode_state.num_slice_params],
                                 obj_buffer->buffer_store);
-    obj_context->decode_state.num_slices = obj_buffer->num_elements;    
+    obj_context->decode_state.num_slice_params++;
     
     return VA_STATUS_SUCCESS;
 }
@@ -986,9 +1012,18 @@ i965_render_slice_data_buffer(VADriverContextP ctx,
 {
     assert(obj_buffer->buffer_store->buffer == NULL);
     assert(obj_buffer->buffer_store->bo);
-    i965_release_buffer_store(&obj_context->decode_state.slice_data);
-    i965_reference_buffer_store(&obj_context->decode_state.slice_data,
+
+    if (obj_context->decode_state.num_slice_datas == obj_context->decode_state.max_slice_datas) {
+        obj_context->decode_state.slice_datas = realloc(obj_context->decode_state.slice_datas,
+                                                        (obj_context->decode_state.max_slice_datas + NUM_SLICES) * sizeof(*obj_context->decode_state.slice_datas));
+        memset(obj_context->decode_state.slice_datas + obj_context->decode_state.max_slice_datas, 0, NUM_SLICES * sizeof(*obj_context->decode_state.slice_datas));
+        obj_context->decode_state.max_slice_datas += NUM_SLICES;
+    }
+        
+    i965_release_buffer_store(&obj_context->decode_state.slice_datas[obj_context->decode_state.num_slice_datas]);
+    i965_reference_buffer_store(&obj_context->decode_state.slice_datas[obj_context->decode_state.num_slice_datas],
                                 obj_buffer->buffer_store);
+    obj_context->decode_state.num_slice_datas++;
     
     return VA_STATUS_SUCCESS;
 }
@@ -1048,11 +1083,13 @@ i965_EndPicture(VADriverContextP ctx, VAContextID context)
     struct object_context *obj_context = CONTEXT(context);
     struct object_config *obj_config;
     VAContextID config;
+    int i;
 
     assert(obj_context);
     assert(obj_context->decode_state.pic_param);
-    assert(obj_context->decode_state.slice_param);
-    assert(obj_context->decode_state.slice_data);
+    assert(obj_context->decode_state.num_slice_params >= 1);
+    assert(obj_context->decode_state.num_slice_datas >= 1);
+    assert(obj_context->decode_state.num_slice_params == obj_context->decode_state.num_slice_datas);
 
     config = obj_context->config_id;
     obj_config = CONFIG(config);
@@ -1071,12 +1108,16 @@ i965_EndPicture(VADriverContextP ctx, VAContextID context)
 
     i965_media_decode_picture(ctx, obj_config->profile, &obj_context->decode_state);
     obj_context->decode_state.current_render_target = -1;
-    obj_context->decode_state.num_slices = 0;
+    obj_context->decode_state.num_slice_params = 0;
+    obj_context->decode_state.num_slice_datas = 0;
     i965_release_buffer_store(&obj_context->decode_state.pic_param);
-    i965_release_buffer_store(&obj_context->decode_state.slice_param);
     i965_release_buffer_store(&obj_context->decode_state.iq_matrix);
     i965_release_buffer_store(&obj_context->decode_state.bit_plane);
-    i965_release_buffer_store(&obj_context->decode_state.slice_data);
+
+    for (i = 0; i < obj_context->decode_state.num_slice_params; i++) {
+        i965_release_buffer_store(&obj_context->decode_state.slice_params[i]);
+        i965_release_buffer_store(&obj_context->decode_state.slice_datas[i]);
+    }
 
     return VA_STATUS_SUCCESS;
 }
index b7e02a5..33b46f3 100644 (file)
@@ -53,6 +53,7 @@ struct buffer_store
     unsigned char *buffer;
     dri_bo *bo;
     int ref_count;
+    int num_elements;
 };
     
 struct object_config 
@@ -64,15 +65,20 @@ struct object_config
     int num_attribs;
 };
 
+#define NUM_SLICES     10
+
 struct decode_state
 {
     struct buffer_store *pic_param;
-    struct buffer_store *slice_param;
+    struct buffer_store **slice_params;
     struct buffer_store *iq_matrix;
     struct buffer_store *bit_plane;
-    struct buffer_store *slice_data;
+    struct buffer_store **slice_datas;
     VASurfaceID current_render_target;
-    int num_slices;
+    int max_slice_params;
+    int max_slice_datas;
+    int num_slice_params;
+    int num_slice_datas;
 };
 
 struct object_context 
index c1b5626..841b777 100644 (file)
@@ -517,8 +517,8 @@ i965_media_h264_vfe_state_extension(VADriverContextP ctx,
     assert(decode_state->pic_param && decode_state->pic_param->buffer);
     pic_param = (VAPictureParameterBufferH264 *)decode_state->pic_param->buffer;
 
-    assert(decode_state->slice_param && decode_state->slice_param->buffer);
-    slice_param = (VASliceParameterBufferH264 *)decode_state->slice_param->buffer;
+    assert(decode_state->slice_params[0] && decode_state->slice_params[0]->buffer);
+    slice_param = (VASliceParameterBufferH264 *)decode_state->slice_params[0]->buffer;
 
     mbaff_frame_flag = (pic_param->seq_fields.bits.mb_adaptive_frame_field_flag &&
                         !pic_param->pic_fields.bits.field_pic_flag);
@@ -651,8 +651,8 @@ i965_media_h264_upload_constants(VADriverContextP ctx, struct decode_state *deco
     assert(media_state->private_context);
     i965_h264_context = (struct i965_h264_context *)media_state->private_context;
 
-    assert(decode_state->slice_param && decode_state->slice_param->buffer);
-    slice_param = (VASliceParameterBufferH264 *)decode_state->slice_param->buffer;
+    assert(decode_state->slice_params[0] && decode_state->slice_params[0]->buffer);
+    slice_param = (VASliceParameterBufferH264 *)decode_state->slice_params[0]->buffer;
 
     dri_bo_map(media_state->curbe.bo, 1);
     assert(media_state->curbe.bo->virtual);
index eaed1e9..c966904 100644 (file)
@@ -851,30 +851,33 @@ i965_media_mpeg2_states_setup(VADriverContextP ctx, struct decode_state *decode_
 static void
 i965_media_mpeg2_objects(VADriverContextP ctx, struct decode_state *decode_state)
 {
-    int i;
+    int i, j;
     VASliceParameterBufferMPEG2 *slice_param;
 
-    assert(decode_state->slice_param && decode_state->slice_param->buffer);
-    slice_param = (VASliceParameterBufferMPEG2 *)decode_state->slice_param->buffer;
-
-    for (i = 0; i < decode_state->num_slices; i++) {
-        assert(slice_param->slice_data_flag == VA_SLICE_DATA_FLAG_ALL);
-
-        BEGIN_BATCH(ctx, 6);
-        OUT_BATCH(ctx, CMD_MEDIA_OBJECT | 4);
-        OUT_BATCH(ctx, 0);
-        OUT_BATCH(ctx, slice_param->slice_data_size - (slice_param->macroblock_offset >> 3));
-        OUT_RELOC(ctx, decode_state->slice_data->bo, 
-                  I915_GEM_DOMAIN_SAMPLER, 0, 
-                  slice_param->slice_data_offset + (slice_param->macroblock_offset >> 3));
-        OUT_BATCH(ctx, 
-                  ((slice_param->slice_horizontal_position << 24) |     
-                   (slice_param->slice_vertical_position << 16) |
-                   (127 << 8) | 
-                   (slice_param->macroblock_offset & 0x7)));
-        OUT_BATCH(ctx, slice_param->quantiser_scale_code << 24);
-        ADVANCE_BATCH(ctx);          
-        slice_param++;
+    for (j = 0; j < decode_state->num_slice_params; j++) {
+        assert(decode_state->slice_params[j] && decode_state->slice_params[j]->buffer);
+        assert(decode_state->slice_datas[j] && decode_state->slice_datas[j]->bo);
+        slice_param = (VASliceParameterBufferMPEG2 *)decode_state->slice_params[j]->buffer;
+
+        for (i = 0; i < decode_state->slice_params[j]->num_elements; i++) {
+            assert(slice_param->slice_data_flag == VA_SLICE_DATA_FLAG_ALL);
+
+            BEGIN_BATCH(ctx, 6);
+            OUT_BATCH(ctx, CMD_MEDIA_OBJECT | 4);
+            OUT_BATCH(ctx, 0);
+            OUT_BATCH(ctx, slice_param->slice_data_size - (slice_param->macroblock_offset >> 3));
+            OUT_RELOC(ctx, decode_state->slice_datas[j]->bo, 
+                      I915_GEM_DOMAIN_SAMPLER, 0, 
+                      slice_param->slice_data_offset + (slice_param->macroblock_offset >> 3));
+            OUT_BATCH(ctx, 
+                      ((slice_param->slice_horizontal_position << 24) |     
+                       (slice_param->slice_vertical_position << 16) |
+                       (127 << 8) | 
+                       (slice_param->macroblock_offset & 0x7)));
+            OUT_BATCH(ctx, slice_param->quantiser_scale_code << 24);
+            ADVANCE_BATCH(ctx);          
+            slice_param++;
+        }
     }
 }