From 4953ba6a717ad1d3aa4426d147b52d05932c47ab Mon Sep 17 00:00:00 2001 From: Marek Olšák Date: Tue, 7 Dec 2010 07:54:31 +0100 Subject: r300g: validate buffers only if any of bound buffers is changed This prevents needless buffer validation (CS space checking). --- src/gallium/drivers/r300/r300_context.h | 4 ++++ src/gallium/drivers/r300/r300_emit.c | 8 ++------ src/gallium/drivers/r300/r300_flush.c | 2 ++ src/gallium/drivers/r300/r300_render.c | 26 +++++++++++++++++++----- src/gallium/drivers/r300/r300_render_translate.c | 4 ++++ src/gallium/drivers/r300/r300_screen_buffer.c | 1 + src/gallium/drivers/r300/r300_state.c | 7 +++++-- 7 files changed, 39 insertions(+), 13 deletions(-) (limited to 'src/gallium') diff --git a/src/gallium/drivers/r300/r300_context.h b/src/gallium/drivers/r300/r300_context.h index 8d50ea3a30..39dcde0610 100644 --- a/src/gallium/drivers/r300/r300_context.h +++ b/src/gallium/drivers/r300/r300_context.h @@ -614,6 +614,10 @@ struct r300_context { /* AOS (PACKET3_3D_LOAD_VBPNTR) command buffer for the case offset=0. */ uint32_t aos_cb[(16 * 3 + 1) / 2]; boolean aos_dirty; + + /* Whether any buffer (FB, textures, VBOs) has been set, but buffers + * haven't been validated yet. */ + boolean validate_buffers; }; #define foreach_atom(r300, atom) \ diff --git a/src/gallium/drivers/r300/r300_emit.c b/src/gallium/drivers/r300/r300_emit.c index 82391e11a9..04a5bd92d1 100644 --- a/src/gallium/drivers/r300/r300_emit.c +++ b/src/gallium/drivers/r300/r300_emit.c @@ -1219,12 +1219,6 @@ boolean r300_emit_buffer_validate(struct r300_context *r300, struct pipe_resource *pbuf; unsigned i; - /* upload buffers first */ - if (r300->screen->caps.has_tcl && r300->any_user_vbs) { - r300_upload_user_buffers(r300); - r300->any_user_vbs = false; - } - /* Clean out BOs. */ r300->rws->cs_reset_buffers(r300->cs); @@ -1263,6 +1257,8 @@ boolean r300_emit_buffer_validate(struct r300_context *r300, if (do_validate_vertex_buffers) { for (i = 0; i < r300->velems->count; i++) { pbuf = vbuf[velem[i].vertex_buffer_index].buffer; + if (!pbuf) + continue; r300->rws->cs_add_buffer(r300->cs, r300_buffer(pbuf)->cs_buf, r300_buffer(pbuf)->domain, 0); diff --git a/src/gallium/drivers/r300/r300_flush.c b/src/gallium/drivers/r300/r300_flush.c index 074c5c8543..451fe525b4 100644 --- a/src/gallium/drivers/r300/r300_flush.c +++ b/src/gallium/drivers/r300/r300_flush.c @@ -68,6 +68,8 @@ static void r300_flush(struct pipe_context* pipe, r300->vs_state.dirty = FALSE; r300->vs_constants.dirty = FALSE; } + + r300->validate_buffers = TRUE; } /* reset flushed query */ diff --git a/src/gallium/drivers/r300/r300_render.c b/src/gallium/drivers/r300/r300_render.c index fa55e4f8cd..7bb5eaa4a9 100644 --- a/src/gallium/drivers/r300/r300_render.c +++ b/src/gallium/drivers/r300/r300_render.c @@ -232,14 +232,28 @@ static boolean r300_emit_states(struct r300_context *r300, boolean emit_aos = flags & PREP_EMIT_AOS; boolean emit_aos_swtcl = flags & PREP_EMIT_AOS_SWTCL; boolean indexed = flags & PREP_INDEXED; + boolean validate_vbos = flags & PREP_VALIDATE_VBOS; /* Validate buffers and emit dirty state if needed. */ if (first_draw) { - if (!r300_emit_buffer_validate(r300, flags & PREP_VALIDATE_VBOS, - index_buffer)) { - fprintf(stderr, "r300: CS space validation failed. " - "(not enough memory?) Skipping rendering.\n"); - return FALSE; + /* upload buffers first */ + if (r300->screen->caps.has_tcl && r300->any_user_vbs) { + r300_upload_user_buffers(r300); + r300->any_user_vbs = false; + } + + if (r300->validate_buffers) { + if (!r300_emit_buffer_validate(r300, validate_vbos, + index_buffer)) { + fprintf(stderr, "r300: CS space validation failed. " + "(not enough memory?) Skipping rendering.\n"); + return FALSE; + } + + /* Consider the validation done only if everything was validated. */ + if (validate_vbos) { + r300->validate_buffers = FALSE; + } } r300_emit_dirty_state(r300); @@ -1080,6 +1094,8 @@ static void r300_blitter_draw_rectangle(struct blitter_context *blitter, const float zeros[4] = {0, 0, 0, 0}; CS_LOCALS(r300); + r300->context.set_vertex_buffers(&r300->context, 0, NULL); + if (type == UTIL_BLITTER_ATTRIB_TEXCOORD) r300->sprite_coord_enable = 1; diff --git a/src/gallium/drivers/r300/r300_render_translate.c b/src/gallium/drivers/r300/r300_render_translate.c index 9247064508..41a43b04de 100644 --- a/src/gallium/drivers/r300/r300_render_translate.c +++ b/src/gallium/drivers/r300/r300_render_translate.c @@ -145,6 +145,7 @@ void r300_begin_vertex_translate(struct r300_context *r300) vb->max_index = num_verts - 1; vb->stride = key.output_stride; r300->tran.vb_slot = i; + r300->validate_buffers = TRUE; break; } } @@ -199,12 +200,14 @@ void r300_translate_index_buffer(struct r300_context *r300, util_shorten_ubyte_elts(&r300->context, index_buffer, index_offset, *start, count); *index_size = 2; *start = 0; + r300->validate_buffers = TRUE; break; case 2: if (*start % 2 != 0 || index_offset) { util_rebuild_ushort_elts(&r300->context, index_buffer, index_offset, *start, count); *start = 0; + r300->validate_buffers = TRUE; } break; @@ -212,6 +215,7 @@ void r300_translate_index_buffer(struct r300_context *r300, if (index_offset) { util_rebuild_uint_elts(&r300->context, index_buffer, index_offset, *start, count); *start = 0; + r300->validate_buffers = TRUE; } break; } diff --git a/src/gallium/drivers/r300/r300_screen_buffer.c b/src/gallium/drivers/r300/r300_screen_buffer.c index bbb91d1cd5..4436443522 100644 --- a/src/gallium/drivers/r300/r300_screen_buffer.c +++ b/src/gallium/drivers/r300/r300_screen_buffer.c @@ -118,6 +118,7 @@ int r300_upload_user_buffers(struct r300_context *r300) pipe_resource_reference(&vb->buffer, NULL); vb->buffer = upload_buffer; vb->buffer_offset = upload_offset; + r300->validate_buffers = TRUE; } } return ret; diff --git a/src/gallium/drivers/r300/r300_state.c b/src/gallium/drivers/r300/r300_state.c index c4945fb2fd..7529253240 100644 --- a/src/gallium/drivers/r300/r300_state.c +++ b/src/gallium/drivers/r300/r300_state.c @@ -751,6 +751,7 @@ static void util_copy_framebuffer_state(r300->fb_state.state, state); r300_mark_fb_state_dirty(r300, R300_CHANGED_FB_STATE); + r300->validate_buffers = TRUE; r300->z_compression = false; @@ -1333,6 +1334,7 @@ static void r300_set_fragment_sampler_views(struct pipe_context* pipe, state->sampler_view_count = count; r300_mark_atom_dirty(r300, &r300->textures_state); + r300->validate_buffers = TRUE; if (dirty_tex) { r300_mark_atom_dirty(r300, &r300->texture_cache_inval); @@ -1510,6 +1512,7 @@ static void r300_set_vertex_buffers(struct pipe_context* pipe, r300->any_user_vbs = any_user_buffer; r300->vertex_buffer_max_index = max_index; r300->aos_dirty = TRUE; + r300->validate_buffers = TRUE; } else { /* SW TCL. */ draw_set_vertex_buffers(r300->draw, count, buffers); @@ -1545,10 +1548,10 @@ static void r300_set_index_buffer(struct pipe_context* pipe, } if (r300->screen->caps.has_tcl) { - /* TODO make this more like a state */ + r300->validate_buffers = TRUE; } else { - draw_set_index_buffer(r300->draw, ib); + draw_set_index_buffer(r300->draw, ib); } } -- cgit v1.2.3