• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2017 Etnaviv Project
3  * Copyright (C) 2017 Zodiac Inflight Innovations
4  *
5  * Permission is hereby granted, free of charge, to any person obtaining a
6  * copy of this software and associated documentation files (the "Software"),
7  * to deal in the Software without restriction, including without limitation
8  * the rights to use, copy, modify, merge, publish, distribute, sub license,
9  * and/or sell copies of the Software, and to permit persons to whom the
10  * Software is furnished to do so, subject to the following conditions:
11  *
12  * The above copyright notice and this permission notice (including the
13  * next paragraph) shall be included in all copies or substantial portions
14  * of the Software.
15  *
16  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18  * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
19  * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20  * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
21  * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
22  * DEALINGS IN THE SOFTWARE.
23  *
24  * Authors:
25  *    Rob Clark <robclark@freedesktop.org>
26  *    Christian Gmeiner <christian.gmeiner@gmail.com>
27  */
28 
29 #include "util/compiler.h"
30 #include "util/u_inlines.h"
31 #include "util/u_memory.h"
32 
33 #include "etnaviv_context.h"
34 #include "etnaviv_debug.h"
35 #include "etnaviv_emit.h"
36 #include "etnaviv_query_acc.h"
37 #include "etnaviv_screen.h"
38 
39 /*
40  * Occlusion Query:
41  *
42  * OCCLUSION_COUNTER and OCCLUSION_PREDICATE differ only in how they
43  * interpret results
44  */
45 
46 static bool
occlusion_supports(unsigned query_type)47 occlusion_supports(unsigned query_type)
48 {
49    switch (query_type) {
50    case PIPE_QUERY_OCCLUSION_COUNTER:
51       FALLTHROUGH;
52    case PIPE_QUERY_OCCLUSION_PREDICATE:
53       FALLTHROUGH;
54    case PIPE_QUERY_OCCLUSION_PREDICATE_CONSERVATIVE:
55       return true;
56    default:
57       return false;
58    }
59 }
60 
61 static struct etna_acc_query *
occlusion_allocate(struct etna_context * ctx,ASSERTED unsigned query_type)62 occlusion_allocate(struct etna_context *ctx, ASSERTED unsigned query_type)
63 {
64    return CALLOC_STRUCT(etna_acc_query);
65 }
66 
67 static void
occlusion_resume(struct etna_acc_query * aq,struct etna_context * ctx)68 occlusion_resume(struct etna_acc_query *aq, struct etna_context *ctx)
69 {
70    struct etna_resource *rsc = etna_resource(aq->prsc);
71    struct etna_reloc r = {
72       .bo = rsc->bo,
73       .flags = ETNA_RELOC_WRITE
74    };
75 
76    if (aq->samples > 63) {
77       aq->samples = 63;
78       BUG("samples overflow");
79    }
80 
81    r.offset = aq->samples * 8; /* 64bit value */
82 
83    etna_set_state_reloc(ctx->stream, VIVS_GL_OCCLUSION_QUERY_ADDR, &r);
84    resource_written(ctx, aq->prsc);
85 }
86 
87 static void
occlusion_suspend(struct etna_acc_query * aq,struct etna_context * ctx)88 occlusion_suspend(struct etna_acc_query *aq, struct etna_context *ctx)
89 {
90    /* 0x1DF5E76 is the value used by blob - but any random value will work */
91    etna_set_state(ctx->stream, VIVS_GL_OCCLUSION_QUERY_CONTROL, 0x1DF5E76);
92    resource_written(ctx, aq->prsc);
93 }
94 
95 static bool
occlusion_result(struct etna_acc_query * aq,void * buf,union pipe_query_result * result)96 occlusion_result(struct etna_acc_query *aq, void *buf,
97                  union pipe_query_result *result)
98 {
99    uint64_t sum = 0;
100    uint64_t *ptr = (uint64_t *)buf;
101 
102    for (unsigned i = 0; i < aq->samples; i++)
103       sum += *(ptr + i);
104 
105    if (aq->base.type == PIPE_QUERY_OCCLUSION_COUNTER)
106       result->u64 = sum;
107    else
108       result->b = !!sum;
109 
110    return true;
111 }
112 
113 const struct etna_acc_sample_provider occlusion_provider = {
114    .supports = occlusion_supports,
115    .allocate = occlusion_allocate,
116    .suspend = occlusion_suspend,
117    .resume = occlusion_resume,
118    .result = occlusion_result,
119 };
120