gallium: add PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE

To be able to properly distinguish between GL_ANY_SAMPLES_PASSED
and GL_ANY_SAMPLES_PASSED_CONSERVATIVE.

This patch goes through all drivers, having them treat the two
query types identically, except:

1. radeon incorrectly enabled conservative mode on
   PIPE_QUERY_OCCLUSION_PREDICATE. We now do it correctly, only
   on PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE.
2. st/mesa uses the new query type.

Fixes dEQP-GLES31.functional.fbo.no_attachments.*

Reviewed-by: Marek Olšák <marek.olsak@amd.com>
This commit is contained in:
Nicolai Hähnle 2017-09-12 18:46:46 +02:00
parent 94736d31c3
commit 3f6b3d9db7
24 changed files with 97 additions and 12 deletions

View File

@ -365,6 +365,7 @@ static const char *
util_query_type_names[] = {
"PIPE_QUERY_OCCLUSION_COUNTER",
"PIPE_QUERY_OCCLUSION_PREDICATE",
"PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE",
"PIPE_QUERY_TIMESTAMP",
"PIPE_QUERY_TIMESTAMP_DISJOINT",
"PIPE_QUERY_TIME_ELAPSED",

View File

@ -536,6 +536,7 @@ util_query_clear_result(union pipe_query_result *result, unsigned type)
{
switch (type) {
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
case PIPE_QUERY_SO_OVERFLOW_PREDICATE:
case PIPE_QUERY_SO_OVERFLOW_ANY_PREDICATE:
case PIPE_QUERY_GPU_FINISHED:

View File

@ -394,6 +394,12 @@ value of FALSE for cases where COUNTER would result in 0 and TRUE
for all other cases.
This query can be used with ``render_condition``.
In cases where a conservative approximation of an occlusion query is enough,
``PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE`` should be used. It behaves
like ``PIPE_QUERY_OCCLUSION_PREDICATE``, except that it may return TRUE in
additional, implementation-dependent cases.
This query can be used with ``render_condition``.
``PIPE_QUERY_TIME_ELAPSED`` returns the amount of time, in nanoseconds,
the context takes to perform operations.
The result is an unsigned 64-bit integer.

View File

@ -131,6 +131,13 @@ static const struct fd_hw_sample_provider occlusion_predicate = {
.accumulate_result = occlusion_predicate_accumulate_result,
};
static const struct fd_hw_sample_provider occlusion_predicate_conservative = {
.query_type = PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE,
.active = FD_STAGE_DRAW,
.get_sample = occlusion_get_sample,
.accumulate_result = occlusion_predicate_accumulate_result,
};
void fd3_query_context_init(struct pipe_context *pctx)
{
struct fd_context *ctx = fd_context(pctx);
@ -142,4 +149,5 @@ void fd3_query_context_init(struct pipe_context *pctx)
fd_hw_query_register_provider(pctx, &occlusion_counter);
fd_hw_query_register_provider(pctx, &occlusion_predicate);
fd_hw_query_register_provider(pctx, &occlusion_predicate_conservative);
}

View File

@ -251,6 +251,13 @@ static const struct fd_hw_sample_provider occlusion_predicate = {
.accumulate_result = occlusion_predicate_accumulate_result,
};
static const struct fd_hw_sample_provider occlusion_predicate = {
.query_type = PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE,
.active = FD_STAGE_DRAW,
.get_sample = occlusion_get_sample,
.accumulate_result = occlusion_predicate_accumulate_result,
};
static const struct fd_hw_sample_provider time_elapsed = {
.query_type = PIPE_QUERY_TIME_ELAPSED,
.active = FD_STAGE_DRAW | FD_STAGE_CLEAR,
@ -284,6 +291,7 @@ void fd4_query_context_init(struct pipe_context *pctx)
fd_hw_query_register_provider(pctx, &occlusion_counter);
fd_hw_query_register_provider(pctx, &occlusion_predicate);
fd_hw_query_register_provider(pctx, &occlusion_predicate_conservative);
fd_hw_query_register_provider(pctx, &time_elapsed);
fd_hw_query_register_provider(pctx, &timestamp);
}

View File

@ -144,6 +144,15 @@ static const struct fd_acc_sample_provider occlusion_predicate = {
.result = occlusion_predicate_result,
};
static const struct fd_acc_sample_provider occlusion_predicate_conservative = {
.query_type = PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE,
.active = FD_STAGE_DRAW,
.size = sizeof(struct fd5_query_sample),
.resume = occlusion_resume,
.pause = occlusion_pause,
.result = occlusion_predicate_result,
};
/*
* Timestamp Queries:
*/
@ -247,6 +256,7 @@ fd5_query_context_init(struct pipe_context *pctx)
fd_acc_query_register_provider(pctx, &occlusion_counter);
fd_acc_query_register_provider(pctx, &occlusion_predicate);
fd_acc_query_register_provider(pctx, &occlusion_predicate_conservative);
fd_acc_query_register_provider(pctx, &time_elapsed);
fd_acc_query_register_provider(pctx, &timestamp);

View File

@ -85,6 +85,7 @@ int pidx(unsigned query_type)
case PIPE_QUERY_OCCLUSION_COUNTER:
return 0;
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
return 1;
/* TODO currently queries only emitted in main pass (not in binning pass)..
* which is fine for occlusion query, but pretty much not anything else.

View File

@ -125,6 +125,7 @@ llvmpipe_get_query_result(struct pipe_context *pipe,
}
break;
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
for (i = 0; i < num_threads; i++) {
/* safer (still not guaranteed) when there's an overflow */
vresult->b = vresult->b || pq->end[i];
@ -231,6 +232,7 @@ llvmpipe_begin_query(struct pipe_context *pipe, struct pipe_query *q)
break;
case PIPE_QUERY_OCCLUSION_COUNTER:
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
llvmpipe->active_occlusion_queries++;
llvmpipe->dirty |= LP_NEW_OCCLUSION_QUERY;
break;
@ -294,6 +296,7 @@ llvmpipe_end_query(struct pipe_context *pipe, struct pipe_query *q)
break;
case PIPE_QUERY_OCCLUSION_COUNTER:
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
assert(llvmpipe->active_occlusion_queries);
llvmpipe->active_occlusion_queries--;
llvmpipe->dirty |= LP_NEW_OCCLUSION_QUERY;

View File

@ -486,6 +486,7 @@ lp_rast_begin_query(struct lp_rasterizer_task *task,
switch (pq->type) {
case PIPE_QUERY_OCCLUSION_COUNTER:
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
pq->start[task->thread_index] = task->thread_data.vis_counter;
break;
case PIPE_QUERY_PIPELINE_STATISTICS:
@ -512,6 +513,7 @@ lp_rast_end_query(struct lp_rasterizer_task *task,
switch (pq->type) {
case PIPE_QUERY_OCCLUSION_COUNTER:
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
pq->end[task->thread_index] +=
task->thread_data.vis_counter - pq->start[task->thread_index];
pq->start[task->thread_index] = 0;

View File

@ -1380,6 +1380,7 @@ lp_setup_begin_query(struct lp_setup_context *setup,
if (!(pq->type == PIPE_QUERY_OCCLUSION_COUNTER ||
pq->type == PIPE_QUERY_OCCLUSION_PREDICATE ||
pq->type == PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE ||
pq->type == PIPE_QUERY_PIPELINE_STATISTICS))
return;
@ -1430,6 +1431,7 @@ lp_setup_end_query(struct lp_setup_context *setup, struct llvmpipe_query *pq)
if (pq->type == PIPE_QUERY_OCCLUSION_COUNTER ||
pq->type == PIPE_QUERY_OCCLUSION_PREDICATE ||
pq->type == PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE ||
pq->type == PIPE_QUERY_PIPELINE_STATISTICS ||
pq->type == PIPE_QUERY_TIMESTAMP) {
if (pq->type == PIPE_QUERY_TIMESTAMP &&
@ -1466,6 +1468,7 @@ fail:
*/
if (pq->type == PIPE_QUERY_OCCLUSION_COUNTER ||
pq->type == PIPE_QUERY_OCCLUSION_PREDICATE ||
pq->type == PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE ||
pq->type == PIPE_QUERY_PIPELINE_STATISTICS) {
unsigned i;

View File

@ -121,6 +121,7 @@ nv30_query_create(struct pipe_context *pipe, unsigned type, unsigned index)
break;
case PIPE_QUERY_OCCLUSION_COUNTER:
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
q->enable = NV30_3D_QUERY_ENABLE;
q->report = 1;
break;
@ -228,7 +229,8 @@ nv30_query_result(struct pipe_context *pipe, struct pipe_query *pq,
nv30_query_object_del(screen, &q->qo[1]);
}
if (q->type == PIPE_QUERY_OCCLUSION_PREDICATE)
if (q->type == PIPE_QUERY_OCCLUSION_PREDICATE ||
q->type == PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE)
result->b = !!q->result;
else
result->u64 = q->result;

View File

@ -97,6 +97,7 @@ nv50_render_condition(struct pipe_context *pipe,
break;
case PIPE_QUERY_OCCLUSION_COUNTER:
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
if (likely(!condition)) {
if (unlikely(hq->nesting))
cond = wait ? NV50_3D_COND_MODE_NOT_EQUAL :

View File

@ -157,6 +157,7 @@ nv50_hw_begin_query(struct nv50_context *nv50, struct nv50_query *q)
switch (q->type) {
case PIPE_QUERY_OCCLUSION_COUNTER:
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
hq->nesting = nv50->screen->num_occlusion_queries_active++;
if (hq->nesting) {
nv50_hw_query_get(push, q, 0x10, 0x0100f002);
@ -215,6 +216,7 @@ nv50_hw_end_query(struct nv50_context *nv50, struct nv50_query *q)
switch (q->type) {
case PIPE_QUERY_OCCLUSION_COUNTER:
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
nv50_hw_query_get(push, q, 0, 0x0100f002);
if (--nv50->screen->num_occlusion_queries_active == 0) {
PUSH_SPACE(push, 2);
@ -307,6 +309,7 @@ nv50_hw_get_query_result(struct nv50_context *nv50, struct nv50_query *q,
res64[0] = hq->data[1] - hq->data[5];
break;
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
res8[0] = hq->data[1] != hq->data[5];
break;
case PIPE_QUERY_PRIMITIVES_GENERATED: /* u64 count, u64 time */
@ -378,6 +381,7 @@ nv50_hw_create_query(struct nv50_context *nv50, unsigned type, unsigned index)
switch (q->type) {
case PIPE_QUERY_OCCLUSION_COUNTER:
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
hq->rotate = 32;
break;
case PIPE_QUERY_PRIMITIVES_GENERATED:

View File

@ -119,6 +119,7 @@ nvc0_render_condition(struct pipe_context *pipe,
break;
case PIPE_QUERY_OCCLUSION_COUNTER:
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
if (likely(!condition)) {
if (unlikely(hq->nesting))
cond = wait ? NVC0_3D_COND_MODE_NOT_EQUAL :

View File

@ -157,6 +157,7 @@ nvc0_hw_begin_query(struct nvc0_context *nvc0, struct nvc0_query *q)
switch (q->type) {
case PIPE_QUERY_OCCLUSION_COUNTER:
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
hq->nesting = nvc0->screen->num_occlusion_queries_active++;
if (hq->nesting) {
nvc0_hw_query_get(push, q, 0x10, 0x0100f002);
@ -224,6 +225,7 @@ nvc0_hw_end_query(struct nvc0_context *nvc0, struct nvc0_query *q)
switch (q->type) {
case PIPE_QUERY_OCCLUSION_COUNTER:
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
nvc0_hw_query_get(push, q, 0, 0x0100f002);
if (--nvc0->screen->num_occlusion_queries_active == 0) {
PUSH_SPACE(push, 1);
@ -320,6 +322,7 @@ nvc0_hw_get_query_result(struct nvc0_context *nvc0, struct nvc0_query *q,
res64[0] = hq->data[1] - hq->data[5];
break;
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
res8[0] = hq->data[1] != hq->data[5];
break;
case PIPE_QUERY_PRIMITIVES_GENERATED: /* u64 count, u64 time */
@ -408,7 +411,8 @@ nvc0_hw_get_query_result_resource(struct nvc0_context *nvc0,
PUSH_REFN (push, hq->bo, NOUVEAU_BO_GART | NOUVEAU_BO_RD);
PUSH_REFN (push, buf->bo, buf->domain | NOUVEAU_BO_WR);
BEGIN_1IC0(push, NVC0_3D(MACRO_QUERY_BUFFER_WRITE), 9);
if (q->type == PIPE_QUERY_OCCLUSION_PREDICATE) /* XXX what if 64-bit? */
if (q->type == PIPE_QUERY_OCCLUSION_PREDICATE ||
q->type ++ PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE) /* XXX what if 64-bit? */
PUSH_DATA(push, 0x00000001);
else if (result_type == PIPE_QUERY_TYPE_I32)
PUSH_DATA(push, 0x7fffffff);
@ -513,6 +517,7 @@ nvc0_hw_create_query(struct nvc0_context *nvc0, unsigned type, unsigned index)
switch (q->type) {
case PIPE_QUERY_OCCLUSION_COUNTER:
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
hq->rotate = 32;
space = NVC0_HW_QUERY_ALLOC_SPACE;
break;

View File

@ -39,6 +39,7 @@ static struct pipe_query *r300_create_query(struct pipe_context *pipe,
if (query_type != PIPE_QUERY_OCCLUSION_COUNTER &&
query_type != PIPE_QUERY_OCCLUSION_PREDICATE &&
query_type != PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE &&
query_type != PIPE_QUERY_GPU_FINISHED) {
return NULL;
}
@ -171,7 +172,8 @@ static boolean r300_get_query_result(struct pipe_context* pipe,
map++;
}
if (q->type == PIPE_QUERY_OCCLUSION_PREDICATE) {
if (q->type == PIPE_QUERY_OCCLUSION_PREDICATE ||
q->type == PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE) {
vresult->b = temp != 0;
} else {
vresult->u64 = temp;
@ -195,7 +197,8 @@ static void r300_render_condition(struct pipe_context *pipe,
mode == PIPE_RENDER_COND_BY_REGION_WAIT;
if (r300_get_query_result(pipe, query, wait, &result)) {
if (r300_query(query)->type == PIPE_QUERY_OCCLUSION_PREDICATE) {
if (r300_query(query)->type == PIPE_QUERY_OCCLUSION_PREDICATE ||
r300_query(query)->type == PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE) {
r300->skip_rendering = condition == result.b;
} else {
r300->skip_rendering = condition == !!result.u64;

View File

@ -126,7 +126,8 @@ void r600_gfx_write_event_eop(struct r600_common_context *ctx,
*/
if (ctx->chip_class == GFX9 &&
query_type != PIPE_QUERY_OCCLUSION_COUNTER &&
query_type != PIPE_QUERY_OCCLUSION_PREDICATE) {
query_type != PIPE_QUERY_OCCLUSION_PREDICATE &&
query_type != PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE) {
struct r600_resource *scratch = ctx->eop_bug_scratch;
assert(16 * ctx->screen->info.num_render_backends <=

View File

@ -551,7 +551,8 @@ static bool r600_query_hw_prepare_buffer(struct r600_common_screen *rscreen,
memset(results, 0, buffer->b.b.width0);
if (query->b.type == PIPE_QUERY_OCCLUSION_COUNTER ||
query->b.type == PIPE_QUERY_OCCLUSION_PREDICATE) {
query->b.type == PIPE_QUERY_OCCLUSION_PREDICATE ||
query->b.type == PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE) {
unsigned max_rbs = rscreen->info.num_render_backends;
unsigned enabled_rb_mask = rscreen->info.enabled_rb_mask;
unsigned num_results;
@ -636,6 +637,7 @@ static struct pipe_query *r600_query_hw_create(struct r600_common_screen *rscree
switch (query_type) {
case PIPE_QUERY_OCCLUSION_COUNTER:
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
query->result_size = 16 * rscreen->info.num_render_backends;
query->result_size += 16; /* for the fence + alignment */
query->num_cs_dw_begin = 6;
@ -692,7 +694,8 @@ static void r600_update_occlusion_query_state(struct r600_common_context *rctx,
unsigned type, int diff)
{
if (type == PIPE_QUERY_OCCLUSION_COUNTER ||
type == PIPE_QUERY_OCCLUSION_PREDICATE) {
type == PIPE_QUERY_OCCLUSION_PREDICATE ||
type == PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE) {
bool old_enable = rctx->num_occlusion_queries != 0;
bool old_perfect_enable =
rctx->num_perfect_occlusion_queries != 0;
@ -701,7 +704,7 @@ static void r600_update_occlusion_query_state(struct r600_common_context *rctx,
rctx->num_occlusion_queries += diff;
assert(rctx->num_occlusion_queries >= 0);
if (type == PIPE_QUERY_OCCLUSION_COUNTER) {
if (type != PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE) {
rctx->num_perfect_occlusion_queries += diff;
assert(rctx->num_perfect_occlusion_queries >= 0);
}
@ -745,6 +748,7 @@ static void r600_query_hw_do_emit_start(struct r600_common_context *ctx,
switch (query->b.type) {
case PIPE_QUERY_OCCLUSION_COUNTER:
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
radeon_emit(cs, PKT3(PKT3_EVENT_WRITE, 2, 0));
radeon_emit(cs, EVENT_TYPE(EVENT_TYPE_ZPASS_DONE) | EVENT_INDEX(1));
radeon_emit(cs, va);
@ -839,6 +843,7 @@ static void r600_query_hw_do_emit_stop(struct r600_common_context *ctx,
switch (query->b.type) {
case PIPE_QUERY_OCCLUSION_COUNTER:
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
va += 8;
radeon_emit(cs, PKT3(PKT3_EVENT_WRITE, 2, 0));
radeon_emit(cs, EVENT_TYPE(EVENT_TYPE_ZPASS_DONE) | EVENT_INDEX(1));
@ -961,6 +966,7 @@ static void r600_emit_query_predication(struct r600_common_context *ctx,
switch (query->b.type) {
case PIPE_QUERY_OCCLUSION_COUNTER:
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
op = PRED_OP(PREDICATION_OP_ZPASS);
break;
case PIPE_QUERY_SO_OVERFLOW_PREDICATE:
@ -1139,6 +1145,7 @@ static void r600_get_hw_query_params(struct r600_common_context *rctx,
switch (rquery->b.type) {
case PIPE_QUERY_OCCLUSION_COUNTER:
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
params->start_offset = 0;
params->end_offset = 8;
params->fence_offset = max_rbs * 16;
@ -1231,7 +1238,8 @@ static void r600_query_hw_add_result(struct r600_common_screen *rscreen,
}
break;
}
case PIPE_QUERY_OCCLUSION_PREDICATE: {
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE: {
for (unsigned i = 0; i < max_rbs; ++i) {
unsigned results_base = i * 16;
result->b = result->b ||
@ -1711,7 +1719,8 @@ static void r600_query_hw_get_result_resource(struct r600_common_context *rctx,
consts.config = 0;
if (index < 0)
consts.config |= 4;
if (query->b.type == PIPE_QUERY_OCCLUSION_PREDICATE)
if (query->b.type == PIPE_QUERY_OCCLUSION_PREDICATE ||
query->b.type == PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE)
consts.config |= 8;
else if (query->b.type == PIPE_QUERY_SO_OVERFLOW_PREDICATE ||
query->b.type == PIPE_QUERY_SO_OVERFLOW_ANY_PREDICATE)

View File

@ -60,6 +60,7 @@ softpipe_create_query(struct pipe_context *pipe,
assert(type == PIPE_QUERY_OCCLUSION_COUNTER ||
type == PIPE_QUERY_OCCLUSION_PREDICATE ||
type == PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE ||
type == PIPE_QUERY_TIME_ELAPSED ||
type == PIPE_QUERY_SO_STATISTICS ||
type == PIPE_QUERY_SO_OVERFLOW_PREDICATE ||
@ -93,6 +94,7 @@ softpipe_begin_query(struct pipe_context *pipe, struct pipe_query *q)
switch (sq->type) {
case PIPE_QUERY_OCCLUSION_COUNTER:
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
sq->start = softpipe->occlusion_count;
break;
case PIPE_QUERY_TIME_ELAPSED:
@ -147,6 +149,7 @@ softpipe_end_query(struct pipe_context *pipe, struct pipe_query *q)
switch (sq->type) {
case PIPE_QUERY_OCCLUSION_COUNTER:
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
sq->end = softpipe->occlusion_count;
break;
case PIPE_QUERY_TIMESTAMP:
@ -252,6 +255,7 @@ softpipe_get_query_result(struct pipe_context *pipe,
*result = sq->so.primitives_storage_needed;
break;
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
vresult->b = sq->end - sq->start != 0;
break;
default:

View File

@ -707,6 +707,7 @@ svga_create_query(struct pipe_context *pipe,
}
break;
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
if (svga_have_vgpu10(svga)) {
sq->svga_type = SVGA3D_QUERYTYPE_OCCLUSIONPREDICATE;
define_query_vgpu10(svga, sq, sizeof(SVGADXOcclusionPredicateQueryResult));
@ -789,6 +790,7 @@ svga_destroy_query(struct pipe_context *pipe, struct pipe_query *q)
switch (sq->type) {
case PIPE_QUERY_OCCLUSION_COUNTER:
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
if (svga_have_vgpu10(svga)) {
/* make sure to also destroy any associated predicate query */
if (sq->predicate)
@ -864,6 +866,7 @@ svga_begin_query(struct pipe_context *pipe, struct pipe_query *q)
switch (sq->type) {
case PIPE_QUERY_OCCLUSION_COUNTER:
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
if (svga_have_vgpu10(svga)) {
ret = begin_query_vgpu10(svga, sq);
/* also need to start the associated occlusion predicate query */
@ -977,6 +980,7 @@ svga_end_query(struct pipe_context *pipe, struct pipe_query *q)
switch (sq->type) {
case PIPE_QUERY_OCCLUSION_COUNTER:
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
if (svga_have_vgpu10(svga)) {
ret = end_query_vgpu10(svga, sq);
/* also need to end the associated occlusion predicate query */
@ -1093,7 +1097,8 @@ svga_get_query_result(struct pipe_context *pipe,
ret = get_query_result_vgpu9(svga, sq, wait, result);
}
break;
case PIPE_QUERY_OCCLUSION_PREDICATE: {
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE: {
if (svga_have_vgpu10(svga)) {
SVGADXOcclusionPredicateQueryResult occResult;
ret = get_query_result_vgpu10(svga, sq, wait,

View File

@ -94,6 +94,7 @@ swr_get_query_result(struct pipe_context *pipe,
switch (pq->type) {
/* Booleans */
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
result->b = pq->result.core.DepthPassCount != 0;
break;
case PIPE_QUERY_GPU_FINISHED:

View File

@ -878,6 +878,7 @@ trace_dump_query_result(unsigned query_type,
switch (query_type) {
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
case PIPE_QUERY_SO_OVERFLOW_PREDICATE:
case PIPE_QUERY_SO_OVERFLOW_ANY_PREDICATE:
case PIPE_QUERY_GPU_FINISHED:

View File

@ -530,6 +530,7 @@ enum pipe_tess_spacing {
enum pipe_query_type {
PIPE_QUERY_OCCLUSION_COUNTER,
PIPE_QUERY_OCCLUSION_PREDICATE,
PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE,
PIPE_QUERY_TIMESTAMP,
PIPE_QUERY_TIMESTAMP_DISJOINT,
PIPE_QUERY_TIME_ELAPSED,
@ -946,6 +947,7 @@ union pipe_numeric_type_union
union pipe_query_result
{
/* PIPE_QUERY_OCCLUSION_PREDICATE */
/* PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE */
/* PIPE_QUERY_SO_OVERFLOW_PREDICATE */
/* PIPE_QUERY_SO_OVERFLOW_ANY_PREDICATE */
/* PIPE_QUERY_GPU_FINISHED */

View File

@ -102,9 +102,11 @@ st_BeginQuery(struct gl_context *ctx, struct gl_query_object *q)
/* convert GL query type to Gallium query type */
switch (q->Target) {
case GL_ANY_SAMPLES_PASSED:
case GL_ANY_SAMPLES_PASSED_CONSERVATIVE:
type = PIPE_QUERY_OCCLUSION_PREDICATE;
break;
case GL_ANY_SAMPLES_PASSED_CONSERVATIVE:
type = PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE;
break;
case GL_SAMPLES_PASSED_ARB:
type = PIPE_QUERY_OCCLUSION_COUNTER;
break;
@ -260,6 +262,7 @@ get_query_result(struct pipe_context *pipe,
default:
switch (stq->type) {
case PIPE_QUERY_OCCLUSION_PREDICATE:
case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
case PIPE_QUERY_SO_OVERFLOW_PREDICATE:
case PIPE_QUERY_SO_OVERFLOW_ANY_PREDICATE:
stq->base.Result = !!data.b;