summaryrefslogtreecommitdiffstats
path: root/src/gallium/drivers/freedreno/freedreno_util.h
diff options
context:
space:
mode:
authorRob Clark <[email protected]>2014-01-07 10:55:07 -0500
committerRob Clark <[email protected]>2014-01-08 16:30:18 -0500
commitc0766528baaef48902c87bbdaa4f5926c472269b (patch)
treef825706059f50c37a9fda7961ec596b0fb6a65da /src/gallium/drivers/freedreno/freedreno_util.h
parentbfb44c24bc1eff850d47984b2cb60c957ffc143d (diff)
freedreno/a3xx: support for hw binning pass
The binning pass sorts vertices into which bins/tiles they apply to. The visibility information generated during the binning pass can be used to speed up the rendering pass by filtering out vertices which do not apply to the current tile. See: https://github.com/freedreno/freedreno/wiki/Adreno-tiling#optimized-approach This brings a significant fps boost. A rough assortment of tests (supertuxkart, etracer, tremulous, glmark2 'build' test, etc) seems to yield a ~35-45% fps improvement. For now, to be conservative, the binning pass is not enabled yet by default. To enable it use: FD_MESA_DEBUG=binning So far I haven't found anything that breaks with binning enabled, but I'd like a bit more testing before I enable it as default. Signed-off-by: Rob Clark <[email protected]>
Diffstat (limited to 'src/gallium/drivers/freedreno/freedreno_util.h')
-rw-r--r--src/gallium/drivers/freedreno/freedreno_util.h44
1 files changed, 35 insertions, 9 deletions
diff --git a/src/gallium/drivers/freedreno/freedreno_util.h b/src/gallium/drivers/freedreno/freedreno_util.h
index 48d346eb35b..fae5ba06b1d 100644
--- a/src/gallium/drivers/freedreno/freedreno_util.h
+++ b/src/gallium/drivers/freedreno/freedreno_util.h
@@ -37,6 +37,7 @@
#include "util/u_debug.h"
#include "util/u_math.h"
#include "util/u_half.h"
+#include "util/u_dynarray.h"
#include "adreno_common.xml.h"
#include "adreno_pm4.xml.h"
@@ -52,16 +53,19 @@ enum adreno_stencil_op fd_stencil_op(unsigned op);
/* TBD if it is same on a2xx, but for now: */
#define MAX_MIP_LEVELS A3XX_MAX_MIP_LEVELS
-#define FD_DBG_MSGS 0x01
-#define FD_DBG_DISASM 0x02
-#define FD_DBG_DCLEAR 0x04
-#define FD_DBG_DGMEM 0x08
-#define FD_DBG_DSCIS 0x10
-#define FD_DBG_DIRECT 0x20
-#define FD_DBG_DBYPASS 0x40
-#define FD_DBG_FRAGHALF 0x80
+#define FD_DBG_MSGS 0x0001
+#define FD_DBG_DISASM 0x0002
+#define FD_DBG_DCLEAR 0x0004
+#define FD_DBG_DGMEM 0x0008
+#define FD_DBG_DSCIS 0x0010
+#define FD_DBG_DIRECT 0x0020
+#define FD_DBG_DBYPASS 0x0040
+#define FD_DBG_FRAGHALF 0x0080
+#define FD_DBG_BINNING 0x0100
+#define FD_DBG_DBINNING 0x0200
extern int fd_mesa_debug;
+extern bool fd_binning_enabled;
#define DBG(fmt, ...) \
do { if (fd_mesa_debug & FD_DBG_MSGS) \
@@ -87,6 +91,13 @@ static inline uint32_t DRAW(enum pc_di_primtype prim_type,
(1 << 14);
}
+/* for tracking cmdstream positions that need to be patched: */
+struct fd_cs_patch {
+ uint32_t *cs;
+ uint32_t val;
+};
+#define fd_patch_num_elements(buf) ((buf)->size / sizeof(struct fd_cs_patch))
+#define fd_patch_element(buf, i) util_dynarray_element(buf, struct fd_cs_patch, i)
static inline enum pipe_format
pipe_surface_format(struct pipe_surface *psurf)
@@ -110,6 +121,21 @@ OUT_RING(struct fd_ringbuffer *ring, uint32_t data)
*(ring->cur++) = data;
}
+/* like OUT_RING() but appends a cmdstream patch point to 'buf' */
+static inline void
+OUT_RINGP(struct fd_ringbuffer *ring, uint32_t data,
+ struct util_dynarray *buf)
+{
+ if (LOG_DWORDS) {
+ DBG("ring[%p]: OUT_RINGP %04x: %08x", ring,
+ (uint32_t)(ring->cur - ring->last_start), data);
+ }
+ util_dynarray_append(buf, struct fd_cs_patch, ((struct fd_cs_patch){
+ .cs = ring->cur++,
+ .val = data,
+ }));
+}
+
static inline void
OUT_RELOC(struct fd_ringbuffer *ring, struct fd_bo *bo,
uint32_t offset, uint32_t or, int32_t shift)
@@ -132,7 +158,7 @@ OUT_RELOCW(struct fd_ringbuffer *ring, struct fd_bo *bo,
uint32_t offset, uint32_t or, int32_t shift)
{
if (LOG_DWORDS) {
- DBG("ring[%p]: OUT_RELOC %04x: %p+%u << %d", ring,
+ DBG("ring[%p]: OUT_RELOCW %04x: %p+%u << %d", ring,
(uint32_t)(ring->cur - ring->last_start), bo, offset, shift);
}
fd_ringbuffer_reloc(ring, &(struct fd_reloc){