diff options
author | Brian Paul <brianp@vmware.com> | 2013-04-01 17:51:43 -0600 |
---|---|---|
committer | Brian Paul <brianp@vmware.com> | 2013-04-03 09:56:08 -0600 |
commit | 3838edaf5d3f75ca5c2276db22ea0b96fce2bad7 (patch) | |
tree | bfbf4127c4d08f694bbe74100d827deb45f84c7f | |
parent | 49ed1f3cb335fada1f9ee26d5420889292da3c92 (diff) |
svga: add HUD queries for number of draw calls, number of fallbacks
The fallbacks count is the number of drawing calls that use a "draw"
module fallback, such as polygon stipple.
Reviewed-by: Jose Fonseca <jfonseca@vmware.com>
-rw-r--r-- | src/gallium/drivers/svga/svga_context.h | 9 | ||||
-rw-r--r-- | src/gallium/drivers/svga/svga_pipe_draw.c | 3 | ||||
-rw-r--r-- | src/gallium/drivers/svga/svga_pipe_query.c | 27 | ||||
-rw-r--r-- | src/gallium/drivers/svga/svga_screen.c | 22 |
4 files changed, 61 insertions, 0 deletions
diff --git a/src/gallium/drivers/svga/svga_context.h b/src/gallium/drivers/svga/svga_context.h index 32671ecafa7..e27778eafad 100644 --- a/src/gallium/drivers/svga/svga_context.h +++ b/src/gallium/drivers/svga/svga_context.h @@ -39,12 +39,17 @@ #include "svga_state.h" #include "svga_tgsi.h" #include "svga_hw_reg.h" #include "svga3d_shaderdefs.h" +/** Non-GPU queries for gallium HUD */ +#define SVGA_QUERY_DRAW_CALLS (PIPE_QUERY_DRIVER_SPECIFIC + 0) +#define SVGA_QUERY_FALLBACKS (PIPE_QUERY_DRIVER_SPECIFIC + 1) + + struct draw_vertex_shader; struct draw_fragment_shader; struct svga_shader_result; struct SVGACmdMemory; struct util_bitmask; struct u_upload_mgr; @@ -367,12 +372,16 @@ struct svga_context /** The occlusion query currently in progress */ struct svga_query *sq; /** List of buffers with queued transfers */ struct list_head dirty_buffers; + + /** performance / info queries */ + uint64_t num_draw_calls; /**< SVGA_QUERY_DRAW_CALLS */ + uint64_t num_fallbacks; /**< SVGA_QUERY_FALLBACKS */ }; /* A flag for each state_tracker state object: */ #define SVGA_NEW_BLEND 0x1 #define SVGA_NEW_DEPTH_STENCIL 0x2 diff --git a/src/gallium/drivers/svga/svga_pipe_draw.c b/src/gallium/drivers/svga/svga_pipe_draw.c index e72032e685d..f0da1704538 100644 --- a/src/gallium/drivers/svga/svga_pipe_draw.c +++ b/src/gallium/drivers/svga/svga_pipe_draw.c @@ -327,12 +327,14 @@ svga_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info) struct svga_context *svga = svga_context( pipe ); unsigned reduced_prim = u_reduced_prim( info->mode ); unsigned count = info->count; enum pipe_error ret = 0; boolean needed_swtnl; + svga->num_draw_calls++; /* for SVGA_QUERY_DRAW_CALLS */ + if (!u_trim_pipe_prim( info->mode, &count )) return; /* * Mark currently bound target surfaces as dirty * doesn't really matter if it is done before drawing. @@ -355,12 +357,13 @@ svga_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info) if (svga->curr.vs->base.id == svga->debug.disable_shader || svga->curr.fs->base.id == svga->debug.disable_shader) return; #endif if (svga->state.sw.need_swtnl) { + svga->num_fallbacks++; /* for SVGA_QUERY_FALLBACKS */ if (!needed_swtnl) { /* * We're switching from HW to SW TNL. SW TNL will require mapping all * currently bound vertex buffers, some of which may already be * referenced in the current command buffer as result of previous HW * TNL. So flush now, to prevent the context to flush while a referred diff --git a/src/gallium/drivers/svga/svga_pipe_query.c b/src/gallium/drivers/svga/svga_pipe_query.c index 5cfebaf6f79..11f6a052730 100644 --- a/src/gallium/drivers/svga/svga_pipe_query.c +++ b/src/gallium/drivers/svga/svga_pipe_query.c @@ -48,12 +48,15 @@ struct svga_query { SVGA3dQueryType svga_type; /**< SVGA3D_QUERYTYPE_x or unused */ /** For PIPE_QUERY_OCCLUSION_COUNTER / SVGA3D_QUERYTYPE_OCCLUSION */ struct svga_winsys_buffer *hwbuf; volatile SVGA3dQueryResult *queryResult; struct pipe_fence_handle *fence; + + /** For non-GPU SVGA_QUERY_x queries */ + uint64_t begin_count, end_count; }; /*********************************************************************** * Inline conversion functions. These are better-typed than the * macros used previously: */ @@ -103,12 +106,15 @@ static struct pipe_query *svga_create_query( struct pipe_context *pipe, /* We request the buffer to be pinned and assume it is always mapped. * The reason is that we don't want to wait for fences when checking the * query status. */ sws->buffer_unmap(sws, sq->hwbuf); break; + case SVGA_QUERY_DRAW_CALLS: + case SVGA_QUERY_FALLBACKS: + break; default: assert(!"unexpected query type in svga_create_query()"); } sq->type = query_type; @@ -133,12 +139,16 @@ static void svga_destroy_query(struct pipe_context *pipe, switch (sq->type) { case PIPE_QUERY_OCCLUSION_COUNTER: sws->buffer_destroy(sws, sq->hwbuf); sws->fence_reference(sws, &sq->fence, NULL); break; + case SVGA_QUERY_DRAW_CALLS: + case SVGA_QUERY_FALLBACKS: + /* nothing */ + break; default: assert(!"svga: unexpected query type in svga_destroy_query()"); } FREE(sq); } @@ -184,12 +194,18 @@ static void svga_begin_query(struct pipe_context *pipe, ret = SVGA3D_BeginQuery(svga->swc, sq->svga_type); assert(ret == PIPE_OK); } svga->sq = sq; break; + case SVGA_QUERY_DRAW_CALLS: + sq->begin_count = svga->num_draw_calls; + break; + case SVGA_QUERY_FALLBACKS: + sq->begin_count = svga->num_fallbacks; + break; default: assert(!"unexpected query type in svga_begin_query()"); } } static void svga_end_query(struct pipe_context *pipe, @@ -221,12 +237,18 @@ static void svga_end_query(struct pipe_context *pipe, * that there is one flush before svga_get_query_result attempts to get the * result */ svga_context_flush(svga, NULL); svga->sq = NULL; break; + case SVGA_QUERY_DRAW_CALLS: + sq->end_count = svga->num_draw_calls; + break; + case SVGA_QUERY_FALLBACKS: + sq->end_count = svga->num_fallbacks; + break; default: assert(!"unexpected query type in svga_end_query()"); } } static boolean svga_get_query_result(struct pipe_context *pipe, @@ -274,12 +296,17 @@ static boolean svga_get_query_result(struct pipe_context *pipe, assert(state == SVGA3D_QUERYSTATE_SUCCEEDED || state == SVGA3D_QUERYSTATE_FAILED); *result = (uint64_t)sq->queryResult->result32; break; + case SVGA_QUERY_DRAW_CALLS: + /* fall-through */ + case SVGA_QUERY_FALLBACKS: + vresult->u64 = sq->end_count - sq->begin_count; + break; default: assert(!"unexpected query type in svga_get_query_result"); } SVGA_DBG(DEBUG_QUERY, "%s result %d\n", __FUNCTION__, (unsigned)*result); diff --git a/src/gallium/drivers/svga/svga_screen.c b/src/gallium/drivers/svga/svga_screen.c index 49059a5d294..bd1b03fc66c 100644 --- a/src/gallium/drivers/svga/svga_screen.c +++ b/src/gallium/drivers/svga/svga_screen.c @@ -489,12 +489,33 @@ svga_fence_finish(struct pipe_screen *screen, __FUNCTION__, fence); return sws->fence_finish(sws, fence, 0) == 0; } +static int +svga_get_driver_query_info(struct pipe_screen *screen, + unsigned index, + struct pipe_driver_query_info *info) +{ + static const struct pipe_driver_query_info queries[] = { + {"draw-calls", SVGA_QUERY_DRAW_CALLS, 0, FALSE}, + {"fallbacks", SVGA_QUERY_FALLBACKS, 0, FALSE} + }; + + if (!info) + return Elements(queries); + + if (index >= Elements(queries)) + return 0; + + *info = queries[index]; + return 1; +} + + static void svga_destroy_screen( struct pipe_screen *screen ) { struct svga_screen *svgascreen = svga_screen(screen); svga_screen_cache_cleanup(svgascreen); @@ -548,12 +569,13 @@ svga_screen_create(struct svga_winsys_screen *sws) screen->get_paramf = svga_get_paramf; screen->is_format_supported = svga_is_format_supported; screen->context_create = svga_context_create; screen->fence_reference = svga_fence_reference; screen->fence_signalled = svga_fence_signalled; screen->fence_finish = svga_fence_finish; + screen->get_driver_query_info = svga_get_driver_query_info; svgascreen->sws = sws; svga_init_screen_resource_functions(svgascreen); if (sws->get_hw_version) { svgascreen->hw_version = sws->get_hw_version(sws); |