1bf215546Sopenharmony_ci/*
2bf215546Sopenharmony_ci * Copyright © 2016 Red Hat.
3bf215546Sopenharmony_ci * Copyright © 2016 Bas Nieuwenhuizen
4bf215546Sopenharmony_ci * SPDX-License-Identifier: MIT
5bf215546Sopenharmony_ci *
6bf215546Sopenharmony_ci * based in part on anv driver which is:
7bf215546Sopenharmony_ci * Copyright © 2015 Intel Corporation
8bf215546Sopenharmony_ci */
9bf215546Sopenharmony_ci
10bf215546Sopenharmony_ci#ifndef TU_CMD_BUFFER_H
11bf215546Sopenharmony_ci#define TU_CMD_BUFFER_H
12bf215546Sopenharmony_ci
13bf215546Sopenharmony_ci#include "tu_common.h"
14bf215546Sopenharmony_ci
15bf215546Sopenharmony_ci#include "tu_cs.h"
16bf215546Sopenharmony_ci#include "tu_descriptor_set.h"
17bf215546Sopenharmony_ci#include "tu_device.h"
18bf215546Sopenharmony_ci#include "tu_lrz.h"
19bf215546Sopenharmony_ci#include "tu_pass.h"
20bf215546Sopenharmony_ci#include "tu_pipeline.h"
21bf215546Sopenharmony_ci
22bf215546Sopenharmony_cienum tu_draw_state_group_id
23bf215546Sopenharmony_ci{
24bf215546Sopenharmony_ci   TU_DRAW_STATE_PROGRAM_CONFIG,
25bf215546Sopenharmony_ci   TU_DRAW_STATE_PROGRAM,
26bf215546Sopenharmony_ci   TU_DRAW_STATE_PROGRAM_BINNING,
27bf215546Sopenharmony_ci   TU_DRAW_STATE_VB,
28bf215546Sopenharmony_ci   TU_DRAW_STATE_VI,
29bf215546Sopenharmony_ci   TU_DRAW_STATE_VI_BINNING,
30bf215546Sopenharmony_ci   TU_DRAW_STATE_RAST,
31bf215546Sopenharmony_ci   TU_DRAW_STATE_CONST,
32bf215546Sopenharmony_ci   TU_DRAW_STATE_DESC_SETS,
33bf215546Sopenharmony_ci   TU_DRAW_STATE_DESC_SETS_LOAD,
34bf215546Sopenharmony_ci   TU_DRAW_STATE_VS_PARAMS,
35bf215546Sopenharmony_ci   TU_DRAW_STATE_INPUT_ATTACHMENTS_GMEM,
36bf215546Sopenharmony_ci   TU_DRAW_STATE_INPUT_ATTACHMENTS_SYSMEM,
37bf215546Sopenharmony_ci   TU_DRAW_STATE_LRZ_AND_DEPTH_PLANE,
38bf215546Sopenharmony_ci   TU_DRAW_STATE_PRIM_MODE_GMEM,
39bf215546Sopenharmony_ci   TU_DRAW_STATE_PRIM_MODE_SYSMEM,
40bf215546Sopenharmony_ci
41bf215546Sopenharmony_ci   /* dynamic state related draw states */
42bf215546Sopenharmony_ci   TU_DRAW_STATE_DYNAMIC,
43bf215546Sopenharmony_ci   TU_DRAW_STATE_COUNT = TU_DRAW_STATE_DYNAMIC + TU_DYNAMIC_STATE_COUNT,
44bf215546Sopenharmony_ci};
45bf215546Sopenharmony_ci
46bf215546Sopenharmony_cistruct tu_descriptor_state
47bf215546Sopenharmony_ci{
48bf215546Sopenharmony_ci   struct tu_descriptor_set *sets[MAX_SETS];
49bf215546Sopenharmony_ci   struct tu_descriptor_set push_set;
50bf215546Sopenharmony_ci   uint32_t dynamic_descriptors[MAX_DYNAMIC_BUFFERS_SIZE];
51bf215546Sopenharmony_ci};
52bf215546Sopenharmony_ci
53bf215546Sopenharmony_cienum tu_cmd_dirty_bits
54bf215546Sopenharmony_ci{
55bf215546Sopenharmony_ci   TU_CMD_DIRTY_VERTEX_BUFFERS = BIT(0),
56bf215546Sopenharmony_ci   TU_CMD_DIRTY_VB_STRIDE = BIT(1),
57bf215546Sopenharmony_ci   TU_CMD_DIRTY_GRAS_SU_CNTL = BIT(2),
58bf215546Sopenharmony_ci   TU_CMD_DIRTY_RB_DEPTH_CNTL = BIT(3),
59bf215546Sopenharmony_ci   TU_CMD_DIRTY_RB_STENCIL_CNTL = BIT(4),
60bf215546Sopenharmony_ci   TU_CMD_DIRTY_DESC_SETS_LOAD = BIT(5),
61bf215546Sopenharmony_ci   TU_CMD_DIRTY_COMPUTE_DESC_SETS_LOAD = BIT(6),
62bf215546Sopenharmony_ci   TU_CMD_DIRTY_SHADER_CONSTS = BIT(7),
63bf215546Sopenharmony_ci   TU_CMD_DIRTY_LRZ = BIT(8),
64bf215546Sopenharmony_ci   TU_CMD_DIRTY_VS_PARAMS = BIT(9),
65bf215546Sopenharmony_ci   TU_CMD_DIRTY_RASTERIZER_DISCARD = BIT(10),
66bf215546Sopenharmony_ci   TU_CMD_DIRTY_VIEWPORTS = BIT(11),
67bf215546Sopenharmony_ci   TU_CMD_DIRTY_BLEND = BIT(12),
68bf215546Sopenharmony_ci   /* all draw states were disabled and need to be re-enabled: */
69bf215546Sopenharmony_ci   TU_CMD_DIRTY_DRAW_STATE = BIT(13)
70bf215546Sopenharmony_ci};
71bf215546Sopenharmony_ci
72bf215546Sopenharmony_ci/* There are only three cache domains we have to care about: the CCU, or
73bf215546Sopenharmony_ci * color cache unit, which is used for color and depth/stencil attachments
74bf215546Sopenharmony_ci * and copy/blit destinations, and is split conceptually into color and depth,
75bf215546Sopenharmony_ci * and the universal cache or UCHE which is used for pretty much everything
76bf215546Sopenharmony_ci * else, except for the CP (uncached) and host. We need to flush whenever data
77bf215546Sopenharmony_ci * crosses these boundaries.
78bf215546Sopenharmony_ci */
79bf215546Sopenharmony_ci
80bf215546Sopenharmony_cienum tu_cmd_access_mask {
81bf215546Sopenharmony_ci   TU_ACCESS_UCHE_READ = 1 << 0,
82bf215546Sopenharmony_ci   TU_ACCESS_UCHE_WRITE = 1 << 1,
83bf215546Sopenharmony_ci   TU_ACCESS_CCU_COLOR_READ = 1 << 2,
84bf215546Sopenharmony_ci   TU_ACCESS_CCU_COLOR_WRITE = 1 << 3,
85bf215546Sopenharmony_ci   TU_ACCESS_CCU_DEPTH_READ = 1 << 4,
86bf215546Sopenharmony_ci   TU_ACCESS_CCU_DEPTH_WRITE = 1 << 5,
87bf215546Sopenharmony_ci
88bf215546Sopenharmony_ci   /* Experiments have shown that while it's safe to avoid flushing the CCU
89bf215546Sopenharmony_ci    * after each blit/renderpass, it's not safe to assume that subsequent
90bf215546Sopenharmony_ci    * lookups with a different attachment state will hit unflushed cache
91bf215546Sopenharmony_ci    * entries. That is, the CCU needs to be flushed and possibly invalidated
92bf215546Sopenharmony_ci    * when accessing memory with a different attachment state. Writing to an
93bf215546Sopenharmony_ci    * attachment under the following conditions after clearing using the
94bf215546Sopenharmony_ci    * normal 2d engine path is known to have issues:
95bf215546Sopenharmony_ci    *
96bf215546Sopenharmony_ci    * - It isn't the 0'th layer.
97bf215546Sopenharmony_ci    * - There are more than one attachment, and this isn't the 0'th attachment
98bf215546Sopenharmony_ci    *   (this seems to also depend on the cpp of the attachments).
99bf215546Sopenharmony_ci    *
100bf215546Sopenharmony_ci    * Our best guess is that the layer/MRT state is used when computing
101bf215546Sopenharmony_ci    * the location of a cache entry in CCU, to avoid conflicts. We assume that
102bf215546Sopenharmony_ci    * any access in a renderpass after or before an access by a transfer needs
103bf215546Sopenharmony_ci    * a flush/invalidate, and use the _INCOHERENT variants to represent access
104bf215546Sopenharmony_ci    * by a renderpass.
105bf215546Sopenharmony_ci    */
106bf215546Sopenharmony_ci   TU_ACCESS_CCU_COLOR_INCOHERENT_READ = 1 << 6,
107bf215546Sopenharmony_ci   TU_ACCESS_CCU_COLOR_INCOHERENT_WRITE = 1 << 7,
108bf215546Sopenharmony_ci   TU_ACCESS_CCU_DEPTH_INCOHERENT_READ = 1 << 8,
109bf215546Sopenharmony_ci   TU_ACCESS_CCU_DEPTH_INCOHERENT_WRITE = 1 << 9,
110bf215546Sopenharmony_ci
111bf215546Sopenharmony_ci   /* Accesses which bypasses any cache. e.g. writes via the host,
112bf215546Sopenharmony_ci    * CP_EVENT_WRITE::BLIT, and the CP are SYSMEM_WRITE.
113bf215546Sopenharmony_ci    */
114bf215546Sopenharmony_ci   TU_ACCESS_SYSMEM_READ = 1 << 10,
115bf215546Sopenharmony_ci   TU_ACCESS_SYSMEM_WRITE = 1 << 11,
116bf215546Sopenharmony_ci
117bf215546Sopenharmony_ci   /* Memory writes from the CP start in-order with draws and event writes,
118bf215546Sopenharmony_ci    * but execute asynchronously and hence need a CP_WAIT_MEM_WRITES if read.
119bf215546Sopenharmony_ci    */
120bf215546Sopenharmony_ci   TU_ACCESS_CP_WRITE = 1 << 12,
121bf215546Sopenharmony_ci
122bf215546Sopenharmony_ci   TU_ACCESS_READ =
123bf215546Sopenharmony_ci      TU_ACCESS_UCHE_READ |
124bf215546Sopenharmony_ci      TU_ACCESS_CCU_COLOR_READ |
125bf215546Sopenharmony_ci      TU_ACCESS_CCU_DEPTH_READ |
126bf215546Sopenharmony_ci      TU_ACCESS_CCU_COLOR_INCOHERENT_READ |
127bf215546Sopenharmony_ci      TU_ACCESS_CCU_DEPTH_INCOHERENT_READ |
128bf215546Sopenharmony_ci      TU_ACCESS_SYSMEM_READ,
129bf215546Sopenharmony_ci
130bf215546Sopenharmony_ci   TU_ACCESS_WRITE =
131bf215546Sopenharmony_ci      TU_ACCESS_UCHE_WRITE |
132bf215546Sopenharmony_ci      TU_ACCESS_CCU_COLOR_WRITE |
133bf215546Sopenharmony_ci      TU_ACCESS_CCU_COLOR_INCOHERENT_WRITE |
134bf215546Sopenharmony_ci      TU_ACCESS_CCU_DEPTH_WRITE |
135bf215546Sopenharmony_ci      TU_ACCESS_CCU_DEPTH_INCOHERENT_WRITE |
136bf215546Sopenharmony_ci      TU_ACCESS_SYSMEM_WRITE |
137bf215546Sopenharmony_ci      TU_ACCESS_CP_WRITE,
138bf215546Sopenharmony_ci
139bf215546Sopenharmony_ci   TU_ACCESS_ALL =
140bf215546Sopenharmony_ci      TU_ACCESS_READ |
141bf215546Sopenharmony_ci      TU_ACCESS_WRITE,
142bf215546Sopenharmony_ci};
143bf215546Sopenharmony_ci
144bf215546Sopenharmony_ci/* Starting with a6xx, the pipeline is split into several "clusters" (really
145bf215546Sopenharmony_ci * pipeline stages). Each stage has its own pair of register banks and can
146bf215546Sopenharmony_ci * switch them independently, so that earlier stages can run ahead of later
147bf215546Sopenharmony_ci * ones. e.g. the FS of draw N and the VS of draw N + 1 can be executing at
148bf215546Sopenharmony_ci * the same time.
149bf215546Sopenharmony_ci *
150bf215546Sopenharmony_ci * As a result of this, we need to insert a WFI when an earlier stage depends
151bf215546Sopenharmony_ci * on the result of a later stage. CP_DRAW_* and CP_BLIT will wait for any
152bf215546Sopenharmony_ci * pending WFI's to complete before starting, and usually before reading
153bf215546Sopenharmony_ci * indirect params even, so a WFI also acts as a full "pipeline stall".
154bf215546Sopenharmony_ci *
155bf215546Sopenharmony_ci * Note, the names of the stages come from CLUSTER_* in devcoredump. We
156bf215546Sopenharmony_ci * include all the stages for completeness, even ones which do not read/write
157bf215546Sopenharmony_ci * anything.
158bf215546Sopenharmony_ci */
159bf215546Sopenharmony_ci
160bf215546Sopenharmony_cienum tu_stage {
161bf215546Sopenharmony_ci   /* This doesn't correspond to a cluster, but we need it for tracking
162bf215546Sopenharmony_ci    * indirect draw parameter reads etc.
163bf215546Sopenharmony_ci    */
164bf215546Sopenharmony_ci   TU_STAGE_CP,
165bf215546Sopenharmony_ci
166bf215546Sopenharmony_ci   /* - Fetch index buffer
167bf215546Sopenharmony_ci    * - Fetch vertex attributes, dispatch VS
168bf215546Sopenharmony_ci    */
169bf215546Sopenharmony_ci   TU_STAGE_FE,
170bf215546Sopenharmony_ci
171bf215546Sopenharmony_ci   /* Execute all geometry stages (VS thru GS) */
172bf215546Sopenharmony_ci   TU_STAGE_SP_VS,
173bf215546Sopenharmony_ci
174bf215546Sopenharmony_ci   /* Write to VPC, do primitive assembly. */
175bf215546Sopenharmony_ci   TU_STAGE_PC_VS,
176bf215546Sopenharmony_ci
177bf215546Sopenharmony_ci   /* Rasterization. RB_DEPTH_BUFFER_BASE only exists in CLUSTER_PS according
178bf215546Sopenharmony_ci    * to devcoredump so presumably this stage stalls for TU_STAGE_PS when
179bf215546Sopenharmony_ci    * early depth testing is enabled before dispatching fragments? However
180bf215546Sopenharmony_ci    * GRAS reads and writes LRZ directly.
181bf215546Sopenharmony_ci    */
182bf215546Sopenharmony_ci   TU_STAGE_GRAS,
183bf215546Sopenharmony_ci
184bf215546Sopenharmony_ci   /* Execute FS */
185bf215546Sopenharmony_ci   TU_STAGE_SP_PS,
186bf215546Sopenharmony_ci
187bf215546Sopenharmony_ci   /* - Fragment tests
188bf215546Sopenharmony_ci    * - Write color/depth
189bf215546Sopenharmony_ci    * - Streamout writes (???)
190bf215546Sopenharmony_ci    * - Varying interpolation (???)
191bf215546Sopenharmony_ci    */
192bf215546Sopenharmony_ci   TU_STAGE_PS,
193bf215546Sopenharmony_ci};
194bf215546Sopenharmony_ci
195bf215546Sopenharmony_cienum tu_cmd_flush_bits {
196bf215546Sopenharmony_ci   TU_CMD_FLAG_CCU_FLUSH_DEPTH = 1 << 0,
197bf215546Sopenharmony_ci   TU_CMD_FLAG_CCU_FLUSH_COLOR = 1 << 1,
198bf215546Sopenharmony_ci   TU_CMD_FLAG_CCU_INVALIDATE_DEPTH = 1 << 2,
199bf215546Sopenharmony_ci   TU_CMD_FLAG_CCU_INVALIDATE_COLOR = 1 << 3,
200bf215546Sopenharmony_ci   TU_CMD_FLAG_CACHE_FLUSH = 1 << 4,
201bf215546Sopenharmony_ci   TU_CMD_FLAG_CACHE_INVALIDATE = 1 << 5,
202bf215546Sopenharmony_ci   TU_CMD_FLAG_WAIT_MEM_WRITES = 1 << 6,
203bf215546Sopenharmony_ci   TU_CMD_FLAG_WAIT_FOR_IDLE = 1 << 7,
204bf215546Sopenharmony_ci   TU_CMD_FLAG_WAIT_FOR_ME = 1 << 8,
205bf215546Sopenharmony_ci
206bf215546Sopenharmony_ci   TU_CMD_FLAG_ALL_FLUSH =
207bf215546Sopenharmony_ci      TU_CMD_FLAG_CCU_FLUSH_DEPTH |
208bf215546Sopenharmony_ci      TU_CMD_FLAG_CCU_FLUSH_COLOR |
209bf215546Sopenharmony_ci      TU_CMD_FLAG_CACHE_FLUSH |
210bf215546Sopenharmony_ci      /* Treat the CP as a sort of "cache" which may need to be "flushed" via
211bf215546Sopenharmony_ci       * waiting for writes to land with WAIT_FOR_MEM_WRITES.
212bf215546Sopenharmony_ci       */
213bf215546Sopenharmony_ci      TU_CMD_FLAG_WAIT_MEM_WRITES,
214bf215546Sopenharmony_ci
215bf215546Sopenharmony_ci   TU_CMD_FLAG_ALL_INVALIDATE =
216bf215546Sopenharmony_ci      TU_CMD_FLAG_CCU_INVALIDATE_DEPTH |
217bf215546Sopenharmony_ci      TU_CMD_FLAG_CCU_INVALIDATE_COLOR |
218bf215546Sopenharmony_ci      TU_CMD_FLAG_CACHE_INVALIDATE |
219bf215546Sopenharmony_ci      /* Treat CP_WAIT_FOR_ME as a "cache" that needs to be invalidated when a
220bf215546Sopenharmony_ci       * a command that needs CP_WAIT_FOR_ME is executed. This means we may
221bf215546Sopenharmony_ci       * insert an extra WAIT_FOR_ME before an indirect command requiring it
222bf215546Sopenharmony_ci       * in case there was another command before the current command buffer
223bf215546Sopenharmony_ci       * that it needs to wait for.
224bf215546Sopenharmony_ci       */
225bf215546Sopenharmony_ci      TU_CMD_FLAG_WAIT_FOR_ME,
226bf215546Sopenharmony_ci};
227bf215546Sopenharmony_ci
228bf215546Sopenharmony_ci/* Changing the CCU from sysmem mode to gmem mode or vice-versa is pretty
229bf215546Sopenharmony_ci * heavy, involving a CCU cache flush/invalidate and a WFI in order to change
230bf215546Sopenharmony_ci * which part of the gmem is used by the CCU. Here we keep track of what the
231bf215546Sopenharmony_ci * state of the CCU.
232bf215546Sopenharmony_ci */
233bf215546Sopenharmony_cienum tu_cmd_ccu_state {
234bf215546Sopenharmony_ci   TU_CMD_CCU_SYSMEM,
235bf215546Sopenharmony_ci   TU_CMD_CCU_GMEM,
236bf215546Sopenharmony_ci   TU_CMD_CCU_UNKNOWN,
237bf215546Sopenharmony_ci};
238bf215546Sopenharmony_ci
239bf215546Sopenharmony_cistruct tu_cache_state {
240bf215546Sopenharmony_ci   /* Caches which must be made available (flushed) eventually if there are
241bf215546Sopenharmony_ci    * any users outside that cache domain, and caches which must be
242bf215546Sopenharmony_ci    * invalidated eventually if there are any reads.
243bf215546Sopenharmony_ci    */
244bf215546Sopenharmony_ci   enum tu_cmd_flush_bits pending_flush_bits;
245bf215546Sopenharmony_ci   /* Pending flushes */
246bf215546Sopenharmony_ci   enum tu_cmd_flush_bits flush_bits;
247bf215546Sopenharmony_ci};
248bf215546Sopenharmony_ci
249bf215546Sopenharmony_cistruct tu_vs_params {
250bf215546Sopenharmony_ci   uint32_t vertex_offset;
251bf215546Sopenharmony_ci   uint32_t first_instance;
252bf215546Sopenharmony_ci};
253bf215546Sopenharmony_ci
254bf215546Sopenharmony_ci/* This should be for state that is set inside a renderpass and used at
255bf215546Sopenharmony_ci * renderpass end time, e.g. to decide whether to use sysmem. This needs
256bf215546Sopenharmony_ci * special handling for secondary cmdbufs and suspending/resuming render
257bf215546Sopenharmony_ci * passes where the state may need to be combined afterwards.
258bf215546Sopenharmony_ci */
259bf215546Sopenharmony_cistruct tu_render_pass_state
260bf215546Sopenharmony_ci{
261bf215546Sopenharmony_ci   bool xfb_used;
262bf215546Sopenharmony_ci   bool has_tess;
263bf215546Sopenharmony_ci   bool has_prim_generated_query_in_rp;
264bf215546Sopenharmony_ci   bool disable_gmem;
265bf215546Sopenharmony_ci
266bf215546Sopenharmony_ci   /* Track whether conditional predicate for COND_REG_EXEC is changed in draw_cs */
267bf215546Sopenharmony_ci   bool draw_cs_writes_to_cond_pred;
268bf215546Sopenharmony_ci
269bf215546Sopenharmony_ci   uint32_t drawcall_count;
270bf215546Sopenharmony_ci
271bf215546Sopenharmony_ci   /* A calculated "draw cost" value for renderpass, which tries to
272bf215546Sopenharmony_ci    * estimate the bandwidth-per-sample of all the draws according
273bf215546Sopenharmony_ci    * to:
274bf215546Sopenharmony_ci    *
275bf215546Sopenharmony_ci    *    foreach_draw (...) {
276bf215546Sopenharmony_ci    *      sum += pipeline->color_bandwidth_per_sample;
277bf215546Sopenharmony_ci    *      if (depth_test_enabled)
278bf215546Sopenharmony_ci    *        sum += pipeline->depth_cpp_per_sample;
279bf215546Sopenharmony_ci    *      if (depth_write_enabled)
280bf215546Sopenharmony_ci    *        sum += pipeline->depth_cpp_per_sample;
281bf215546Sopenharmony_ci    *      if (stencil_write_enabled)
282bf215546Sopenharmony_ci    *        sum += pipeline->stencil_cpp_per_sample * 2;
283bf215546Sopenharmony_ci    *    }
284bf215546Sopenharmony_ci    *    drawcall_bandwidth_per_sample = sum / drawcall_count;
285bf215546Sopenharmony_ci    *
286bf215546Sopenharmony_ci    * It allows us to estimate the total bandwidth of drawcalls later, by
287bf215546Sopenharmony_ci    * calculating (drawcall_bandwidth_per_sample * zpass_sample_count).
288bf215546Sopenharmony_ci    *
289bf215546Sopenharmony_ci    * This does ignore depth buffer traffic for samples which do not
290bf215546Sopenharmony_ci    * pass due to depth-test fail, and some other details.  But it is
291bf215546Sopenharmony_ci    * just intended to be a rough estimate that is easy to calculate.
292bf215546Sopenharmony_ci    */
293bf215546Sopenharmony_ci   uint32_t drawcall_bandwidth_per_sample_sum;
294bf215546Sopenharmony_ci};
295bf215546Sopenharmony_ci
296bf215546Sopenharmony_cistruct tu_cmd_state
297bf215546Sopenharmony_ci{
298bf215546Sopenharmony_ci   uint32_t dirty;
299bf215546Sopenharmony_ci
300bf215546Sopenharmony_ci   struct tu_pipeline *pipeline;
301bf215546Sopenharmony_ci   struct tu_pipeline *compute_pipeline;
302bf215546Sopenharmony_ci
303bf215546Sopenharmony_ci   struct tu_render_pass_state rp;
304bf215546Sopenharmony_ci
305bf215546Sopenharmony_ci   /* Vertex buffers, viewports, and scissors
306bf215546Sopenharmony_ci    * the states for these can be updated partially, so we need to save these
307bf215546Sopenharmony_ci    * to be able to emit a complete draw state
308bf215546Sopenharmony_ci    */
309bf215546Sopenharmony_ci   struct {
310bf215546Sopenharmony_ci      uint64_t base;
311bf215546Sopenharmony_ci      uint32_t size;
312bf215546Sopenharmony_ci      uint32_t stride;
313bf215546Sopenharmony_ci   } vb[MAX_VBS];
314bf215546Sopenharmony_ci   VkViewport viewport[MAX_VIEWPORTS];
315bf215546Sopenharmony_ci   VkRect2D scissor[MAX_SCISSORS];
316bf215546Sopenharmony_ci   uint32_t max_viewport, max_scissor;
317bf215546Sopenharmony_ci
318bf215546Sopenharmony_ci   /* for dynamic states that can't be emitted directly */
319bf215546Sopenharmony_ci   uint32_t dynamic_stencil_mask;
320bf215546Sopenharmony_ci   uint32_t dynamic_stencil_wrmask;
321bf215546Sopenharmony_ci   uint32_t dynamic_stencil_ref;
322bf215546Sopenharmony_ci
323bf215546Sopenharmony_ci   uint32_t gras_su_cntl, rb_depth_cntl, rb_stencil_cntl;
324bf215546Sopenharmony_ci   uint32_t pc_raster_cntl, vpc_unknown_9107;
325bf215546Sopenharmony_ci   uint32_t rb_mrt_control[MAX_RTS], rb_mrt_blend_control[MAX_RTS];
326bf215546Sopenharmony_ci   uint32_t rb_mrt_control_rop;
327bf215546Sopenharmony_ci   uint32_t rb_blend_cntl, sp_blend_cntl;
328bf215546Sopenharmony_ci   uint32_t pipeline_color_write_enable, pipeline_blend_enable;
329bf215546Sopenharmony_ci   uint32_t color_write_enable;
330bf215546Sopenharmony_ci   bool logic_op_enabled;
331bf215546Sopenharmony_ci   bool rop_reads_dst;
332bf215546Sopenharmony_ci   enum pc_di_primtype primtype;
333bf215546Sopenharmony_ci   bool primitive_restart_enable;
334bf215546Sopenharmony_ci
335bf215546Sopenharmony_ci   /* saved states to re-emit in TU_CMD_DIRTY_DRAW_STATE case */
336bf215546Sopenharmony_ci   struct tu_draw_state dynamic_state[TU_DYNAMIC_STATE_COUNT];
337bf215546Sopenharmony_ci   struct tu_draw_state vertex_buffers;
338bf215546Sopenharmony_ci   struct tu_draw_state shader_const;
339bf215546Sopenharmony_ci   struct tu_draw_state desc_sets;
340bf215546Sopenharmony_ci
341bf215546Sopenharmony_ci   struct tu_draw_state vs_params;
342bf215546Sopenharmony_ci
343bf215546Sopenharmony_ci   /* Index buffer */
344bf215546Sopenharmony_ci   uint64_t index_va;
345bf215546Sopenharmony_ci   uint32_t max_index_count;
346bf215546Sopenharmony_ci   uint8_t index_size;
347bf215546Sopenharmony_ci
348bf215546Sopenharmony_ci   /* because streamout base has to be 32-byte aligned
349bf215546Sopenharmony_ci    * there is an extra offset to deal with when it is
350bf215546Sopenharmony_ci    * unaligned
351bf215546Sopenharmony_ci    */
352bf215546Sopenharmony_ci   uint8_t streamout_offset[IR3_MAX_SO_BUFFERS];
353bf215546Sopenharmony_ci
354bf215546Sopenharmony_ci   /* Renderpasses are tricky, because we may need to flush differently if
355bf215546Sopenharmony_ci    * using sysmem vs. gmem and therefore we have to delay any flushing that
356bf215546Sopenharmony_ci    * happens before a renderpass. So we have to have two copies of the flush
357bf215546Sopenharmony_ci    * state, one for intra-renderpass flushes (i.e. renderpass dependencies)
358bf215546Sopenharmony_ci    * and one for outside a renderpass.
359bf215546Sopenharmony_ci    */
360bf215546Sopenharmony_ci   struct tu_cache_state cache;
361bf215546Sopenharmony_ci   struct tu_cache_state renderpass_cache;
362bf215546Sopenharmony_ci
363bf215546Sopenharmony_ci   enum tu_cmd_ccu_state ccu_state;
364bf215546Sopenharmony_ci
365bf215546Sopenharmony_ci   /* Decides which GMEM layout to use from the tu_pass, based on whether the CCU
366bf215546Sopenharmony_ci    * might get used by tu_store_gmem_attachment().
367bf215546Sopenharmony_ci    */
368bf215546Sopenharmony_ci   enum tu_gmem_layout gmem_layout;
369bf215546Sopenharmony_ci
370bf215546Sopenharmony_ci   const struct tu_render_pass *pass;
371bf215546Sopenharmony_ci   const struct tu_subpass *subpass;
372bf215546Sopenharmony_ci   const struct tu_framebuffer *framebuffer;
373bf215546Sopenharmony_ci   const struct tu_tiling_config *tiling;
374bf215546Sopenharmony_ci   VkRect2D render_area;
375bf215546Sopenharmony_ci
376bf215546Sopenharmony_ci   const struct tu_image_view **attachments;
377bf215546Sopenharmony_ci
378bf215546Sopenharmony_ci   /* State that in the dynamic case comes from VkRenderingInfo and needs to
379bf215546Sopenharmony_ci    * be saved/restored when suspending. This holds the state for the last
380bf215546Sopenharmony_ci    * suspended renderpass, which may point to this command buffer's dynamic_*
381bf215546Sopenharmony_ci    * or another command buffer if executed on a secondary.
382bf215546Sopenharmony_ci    */
383bf215546Sopenharmony_ci   struct {
384bf215546Sopenharmony_ci      const struct tu_render_pass *pass;
385bf215546Sopenharmony_ci      const struct tu_subpass *subpass;
386bf215546Sopenharmony_ci      const struct tu_framebuffer *framebuffer;
387bf215546Sopenharmony_ci      VkRect2D render_area;
388bf215546Sopenharmony_ci      enum tu_gmem_layout gmem_layout;
389bf215546Sopenharmony_ci
390bf215546Sopenharmony_ci      const struct tu_image_view **attachments;
391bf215546Sopenharmony_ci
392bf215546Sopenharmony_ci      struct tu_lrz_state lrz;
393bf215546Sopenharmony_ci   } suspended_pass;
394bf215546Sopenharmony_ci
395bf215546Sopenharmony_ci   bool tessfactor_addr_set;
396bf215546Sopenharmony_ci   bool predication_active;
397bf215546Sopenharmony_ci   enum a5xx_line_mode line_mode;
398bf215546Sopenharmony_ci   bool z_negative_one_to_one;
399bf215546Sopenharmony_ci
400bf215546Sopenharmony_ci   /* VK_QUERY_PIPELINE_STATISTIC_CLIPPING_INVOCATIONS_BIT and
401bf215546Sopenharmony_ci    * VK_QUERY_TYPE_PRIMITIVES_GENERATED_EXT are allowed to run simultaniously,
402bf215546Sopenharmony_ci    * but they use the same {START,STOP}_PRIMITIVE_CTRS control.
403bf215546Sopenharmony_ci    */
404bf215546Sopenharmony_ci   uint32_t prim_counters_running;
405bf215546Sopenharmony_ci
406bf215546Sopenharmony_ci   bool prim_generated_query_running_before_rp;
407bf215546Sopenharmony_ci
408bf215546Sopenharmony_ci   /* These are the states of the suspend/resume state machine. In addition to
409bf215546Sopenharmony_ci    * tracking whether we're in the middle of a chain of suspending and
410bf215546Sopenharmony_ci    * resuming passes that will be merged, we need to track whether the
411bf215546Sopenharmony_ci    * command buffer begins in the middle of such a chain, for when it gets
412bf215546Sopenharmony_ci    * merged with other command buffers. We call such a chain that begins
413bf215546Sopenharmony_ci    * before the command buffer starts a "pre-chain".
414bf215546Sopenharmony_ci    *
415bf215546Sopenharmony_ci    * Note that when this command buffer is finished, this state is untouched
416bf215546Sopenharmony_ci    * but it gains a different meaning. For example, if we finish in state
417bf215546Sopenharmony_ci    * SR_IN_CHAIN, we finished in the middle of a suspend/resume chain, so
418bf215546Sopenharmony_ci    * there's a suspend/resume chain that extends past the end of the command
419bf215546Sopenharmony_ci    * buffer. In this sense it's the "opposite" of SR_AFTER_PRE_CHAIN, which
420bf215546Sopenharmony_ci    * means that there's a suspend/resume chain that extends before the
421bf215546Sopenharmony_ci    * beginning.
422bf215546Sopenharmony_ci    */
423bf215546Sopenharmony_ci   enum {
424bf215546Sopenharmony_ci      /* Either there are no suspend/resume chains, or they are entirely
425bf215546Sopenharmony_ci       * contained in the current command buffer.
426bf215546Sopenharmony_ci       *
427bf215546Sopenharmony_ci       *   BeginCommandBuffer() <- start of current command buffer
428bf215546Sopenharmony_ci       *       ...
429bf215546Sopenharmony_ci       *       // we are here
430bf215546Sopenharmony_ci       */
431bf215546Sopenharmony_ci      SR_NONE = 0,
432bf215546Sopenharmony_ci
433bf215546Sopenharmony_ci      /* We are in the middle of a suspend/resume chain that starts before the
434bf215546Sopenharmony_ci       * current command buffer. This happens when the command buffer begins
435bf215546Sopenharmony_ci       * with a resuming render pass and all of the passes up to the current
436bf215546Sopenharmony_ci       * one are suspending. In this state, our part of the chain is not saved
437bf215546Sopenharmony_ci       * and is in the current draw_cs/state.
438bf215546Sopenharmony_ci       *
439bf215546Sopenharmony_ci       *   BeginRendering() ... EndRendering(suspending)
440bf215546Sopenharmony_ci       *   BeginCommandBuffer() <- start of current command buffer
441bf215546Sopenharmony_ci       *       BeginRendering(resuming) ... EndRendering(suspending)
442bf215546Sopenharmony_ci       *       BeginRendering(resuming) ... EndRendering(suspending)
443bf215546Sopenharmony_ci       *       ...
444bf215546Sopenharmony_ci       *       // we are here
445bf215546Sopenharmony_ci       */
446bf215546Sopenharmony_ci      SR_IN_PRE_CHAIN,
447bf215546Sopenharmony_ci
448bf215546Sopenharmony_ci      /* We are currently outside of any suspend/resume chains, but there is a
449bf215546Sopenharmony_ci       * chain starting before the current command buffer. It is saved in
450bf215546Sopenharmony_ci       * pre_chain.
451bf215546Sopenharmony_ci       *
452bf215546Sopenharmony_ci       *   BeginRendering() ... EndRendering(suspending)
453bf215546Sopenharmony_ci       *   BeginCommandBuffer() <- start of current command buffer
454bf215546Sopenharmony_ci       *       // This part is stashed in pre_chain
455bf215546Sopenharmony_ci       *       BeginRendering(resuming) ... EndRendering(suspending)
456bf215546Sopenharmony_ci       *       BeginRendering(resuming) ... EndRendering(suspending)
457bf215546Sopenharmony_ci       *       ...
458bf215546Sopenharmony_ci       *       BeginRendering(resuming) ... EndRendering() // end of chain
459bf215546Sopenharmony_ci       *       ...
460bf215546Sopenharmony_ci       *       // we are here
461bf215546Sopenharmony_ci       */
462bf215546Sopenharmony_ci      SR_AFTER_PRE_CHAIN,
463bf215546Sopenharmony_ci
464bf215546Sopenharmony_ci      /* We are in the middle of a suspend/resume chain and there is no chain
465bf215546Sopenharmony_ci       * starting before the current command buffer.
466bf215546Sopenharmony_ci       *
467bf215546Sopenharmony_ci       *   BeginCommandBuffer() <- start of current command buffer
468bf215546Sopenharmony_ci       *       ...
469bf215546Sopenharmony_ci       *       BeginRendering() ... EndRendering(suspending)
470bf215546Sopenharmony_ci       *       BeginRendering(resuming) ... EndRendering(suspending)
471bf215546Sopenharmony_ci       *       BeginRendering(resuming) ... EndRendering(suspending)
472bf215546Sopenharmony_ci       *       ...
473bf215546Sopenharmony_ci       *       // we are here
474bf215546Sopenharmony_ci       */
475bf215546Sopenharmony_ci      SR_IN_CHAIN,
476bf215546Sopenharmony_ci
477bf215546Sopenharmony_ci      /* We are in the middle of a suspend/resume chain and there is another,
478bf215546Sopenharmony_ci       * separate, chain starting before the current command buffer.
479bf215546Sopenharmony_ci       *
480bf215546Sopenharmony_ci       *   BeginRendering() ... EndRendering(suspending)
481bf215546Sopenharmony_ci       *   CommandBufferBegin() <- start of current command buffer
482bf215546Sopenharmony_ci       *       // This part is stashed in pre_chain
483bf215546Sopenharmony_ci       *       BeginRendering(resuming) ... EndRendering(suspending)
484bf215546Sopenharmony_ci       *       BeginRendering(resuming) ... EndRendering(suspending)
485bf215546Sopenharmony_ci       *       ...
486bf215546Sopenharmony_ci       *       BeginRendering(resuming) ... EndRendering() // end of chain
487bf215546Sopenharmony_ci       *       ...
488bf215546Sopenharmony_ci       *       BeginRendering() ... EndRendering(suspending)
489bf215546Sopenharmony_ci       *       BeginRendering(resuming) ... EndRendering(suspending)
490bf215546Sopenharmony_ci       *       BeginRendering(resuming) ... EndRendering(suspending)
491bf215546Sopenharmony_ci       *       ...
492bf215546Sopenharmony_ci       *       // we are here
493bf215546Sopenharmony_ci       */
494bf215546Sopenharmony_ci      SR_IN_CHAIN_AFTER_PRE_CHAIN,
495bf215546Sopenharmony_ci   } suspend_resume;
496bf215546Sopenharmony_ci
497bf215546Sopenharmony_ci   bool suspending, resuming;
498bf215546Sopenharmony_ci
499bf215546Sopenharmony_ci   struct tu_lrz_state lrz;
500bf215546Sopenharmony_ci
501bf215546Sopenharmony_ci   struct tu_draw_state lrz_and_depth_plane_state;
502bf215546Sopenharmony_ci
503bf215546Sopenharmony_ci   struct tu_vs_params last_vs_params;
504bf215546Sopenharmony_ci};
505bf215546Sopenharmony_ci
506bf215546Sopenharmony_cistruct tu_cmd_pool
507bf215546Sopenharmony_ci{
508bf215546Sopenharmony_ci   struct vk_command_pool vk;
509bf215546Sopenharmony_ci
510bf215546Sopenharmony_ci   struct list_head cmd_buffers;
511bf215546Sopenharmony_ci   struct list_head free_cmd_buffers;
512bf215546Sopenharmony_ci};
513bf215546Sopenharmony_ciVK_DEFINE_NONDISP_HANDLE_CASTS(tu_cmd_pool, vk.base, VkCommandPool,
514bf215546Sopenharmony_ci                               VK_OBJECT_TYPE_COMMAND_POOL)
515bf215546Sopenharmony_ci
516bf215546Sopenharmony_cienum tu_cmd_buffer_status
517bf215546Sopenharmony_ci{
518bf215546Sopenharmony_ci   TU_CMD_BUFFER_STATUS_INVALID,
519bf215546Sopenharmony_ci   TU_CMD_BUFFER_STATUS_INITIAL,
520bf215546Sopenharmony_ci   TU_CMD_BUFFER_STATUS_RECORDING,
521bf215546Sopenharmony_ci   TU_CMD_BUFFER_STATUS_EXECUTABLE,
522bf215546Sopenharmony_ci   TU_CMD_BUFFER_STATUS_PENDING,
523bf215546Sopenharmony_ci};
524bf215546Sopenharmony_ci
525bf215546Sopenharmony_cistruct tu_cmd_buffer
526bf215546Sopenharmony_ci{
527bf215546Sopenharmony_ci   struct vk_command_buffer vk;
528bf215546Sopenharmony_ci
529bf215546Sopenharmony_ci   struct tu_device *device;
530bf215546Sopenharmony_ci
531bf215546Sopenharmony_ci   struct tu_cmd_pool *pool;
532bf215546Sopenharmony_ci   struct list_head pool_link;
533bf215546Sopenharmony_ci
534bf215546Sopenharmony_ci   struct u_trace trace;
535bf215546Sopenharmony_ci   struct u_trace_iterator trace_renderpass_start;
536bf215546Sopenharmony_ci   struct u_trace_iterator trace_renderpass_end;
537bf215546Sopenharmony_ci
538bf215546Sopenharmony_ci   struct list_head renderpass_autotune_results;
539bf215546Sopenharmony_ci   struct tu_autotune_results_buffer* autotune_buffer;
540bf215546Sopenharmony_ci
541bf215546Sopenharmony_ci   VkCommandBufferUsageFlags usage_flags;
542bf215546Sopenharmony_ci   enum tu_cmd_buffer_status status;
543bf215546Sopenharmony_ci
544bf215546Sopenharmony_ci   VkQueryPipelineStatisticFlags inherited_pipeline_statistics;
545bf215546Sopenharmony_ci
546bf215546Sopenharmony_ci   struct tu_cmd_state state;
547bf215546Sopenharmony_ci   uint32_t queue_family_index;
548bf215546Sopenharmony_ci
549bf215546Sopenharmony_ci   uint32_t push_constants[MAX_PUSH_CONSTANTS_SIZE / 4];
550bf215546Sopenharmony_ci   VkShaderStageFlags push_constant_stages;
551bf215546Sopenharmony_ci   struct tu_descriptor_set meta_push_descriptors;
552bf215546Sopenharmony_ci
553bf215546Sopenharmony_ci   struct tu_descriptor_state descriptors[MAX_BIND_POINTS];
554bf215546Sopenharmony_ci
555bf215546Sopenharmony_ci   struct tu_render_pass_attachment dynamic_rp_attachments[2 * (MAX_RTS + 1)];
556bf215546Sopenharmony_ci   struct tu_subpass_attachment dynamic_color_attachments[MAX_RTS];
557bf215546Sopenharmony_ci   struct tu_subpass_attachment dynamic_resolve_attachments[MAX_RTS + 1];
558bf215546Sopenharmony_ci   const struct tu_image_view *dynamic_attachments[2 * (MAX_RTS + 1)];
559bf215546Sopenharmony_ci
560bf215546Sopenharmony_ci   struct tu_render_pass dynamic_pass;
561bf215546Sopenharmony_ci   struct tu_subpass dynamic_subpass;
562bf215546Sopenharmony_ci   struct tu_framebuffer dynamic_framebuffer;
563bf215546Sopenharmony_ci
564bf215546Sopenharmony_ci   VkResult record_result;
565bf215546Sopenharmony_ci
566bf215546Sopenharmony_ci   struct tu_cs cs;
567bf215546Sopenharmony_ci   struct tu_cs draw_cs;
568bf215546Sopenharmony_ci   struct tu_cs tile_store_cs;
569bf215546Sopenharmony_ci   struct tu_cs draw_epilogue_cs;
570bf215546Sopenharmony_ci   struct tu_cs sub_cs;
571bf215546Sopenharmony_ci
572bf215546Sopenharmony_ci   /* If the first render pass in the command buffer is resuming, then it is
573bf215546Sopenharmony_ci    * part of a suspend/resume chain that starts before the current command
574bf215546Sopenharmony_ci    * buffer and needs to be merged later. In this case, its incomplete state
575bf215546Sopenharmony_ci    * is stored in pre_chain. In the symmetric case where the last render pass
576bf215546Sopenharmony_ci    * is suspending, we just skip ending the render pass and its state is
577bf215546Sopenharmony_ci    * stored in draw_cs/the current state. The first and last render pass
578bf215546Sopenharmony_ci    * might be part of different chains, which is why all the state may need
579bf215546Sopenharmony_ci    * to be saved separately here.
580bf215546Sopenharmony_ci    */
581bf215546Sopenharmony_ci   struct {
582bf215546Sopenharmony_ci      struct tu_cs draw_cs;
583bf215546Sopenharmony_ci      struct tu_cs draw_epilogue_cs;
584bf215546Sopenharmony_ci
585bf215546Sopenharmony_ci      struct u_trace_iterator trace_renderpass_start, trace_renderpass_end;
586bf215546Sopenharmony_ci
587bf215546Sopenharmony_ci      struct tu_render_pass_state state;
588bf215546Sopenharmony_ci   } pre_chain;
589bf215546Sopenharmony_ci
590bf215546Sopenharmony_ci   uint32_t vsc_draw_strm_pitch;
591bf215546Sopenharmony_ci   uint32_t vsc_prim_strm_pitch;
592bf215546Sopenharmony_ci};
593bf215546Sopenharmony_ciVK_DEFINE_HANDLE_CASTS(tu_cmd_buffer, vk.base, VkCommandBuffer,
594bf215546Sopenharmony_ci                       VK_OBJECT_TYPE_COMMAND_BUFFER)
595bf215546Sopenharmony_ci
596bf215546Sopenharmony_cistatic inline uint32_t
597bf215546Sopenharmony_citu_attachment_gmem_offset(struct tu_cmd_buffer *cmd,
598bf215546Sopenharmony_ci                          const struct tu_render_pass_attachment *att)
599bf215546Sopenharmony_ci{
600bf215546Sopenharmony_ci   assert(cmd->state.gmem_layout < TU_GMEM_LAYOUT_COUNT);
601bf215546Sopenharmony_ci   return att->gmem_offset[cmd->state.gmem_layout];
602bf215546Sopenharmony_ci}
603bf215546Sopenharmony_ci
604bf215546Sopenharmony_cistatic inline uint32_t
605bf215546Sopenharmony_citu_attachment_gmem_offset_stencil(struct tu_cmd_buffer *cmd,
606bf215546Sopenharmony_ci                                  const struct tu_render_pass_attachment *att)
607bf215546Sopenharmony_ci{
608bf215546Sopenharmony_ci   assert(cmd->state.gmem_layout < TU_GMEM_LAYOUT_COUNT);
609bf215546Sopenharmony_ci   return att->gmem_offset_stencil[cmd->state.gmem_layout];
610bf215546Sopenharmony_ci}
611bf215546Sopenharmony_ci
612bf215546Sopenharmony_civoid tu_render_pass_state_merge(struct tu_render_pass_state *dst,
613bf215546Sopenharmony_ci                                const struct tu_render_pass_state *src);
614bf215546Sopenharmony_ci
615bf215546Sopenharmony_ciVkResult tu_cmd_buffer_begin(struct tu_cmd_buffer *cmd_buffer,
616bf215546Sopenharmony_ci                             VkCommandBufferUsageFlags usage_flags);
617bf215546Sopenharmony_ci
618bf215546Sopenharmony_civoid tu_emit_cache_flush_renderpass(struct tu_cmd_buffer *cmd_buffer,
619bf215546Sopenharmony_ci                                    struct tu_cs *cs);
620bf215546Sopenharmony_ci
621bf215546Sopenharmony_civoid tu_emit_cache_flush_ccu(struct tu_cmd_buffer *cmd_buffer,
622bf215546Sopenharmony_ci                             struct tu_cs *cs,
623bf215546Sopenharmony_ci                             enum tu_cmd_ccu_state ccu_state);
624bf215546Sopenharmony_ci
625bf215546Sopenharmony_civoid
626bf215546Sopenharmony_citu_append_pre_chain(struct tu_cmd_buffer *cmd,
627bf215546Sopenharmony_ci                    struct tu_cmd_buffer *secondary);
628bf215546Sopenharmony_ci
629bf215546Sopenharmony_civoid
630bf215546Sopenharmony_citu_append_pre_post_chain(struct tu_cmd_buffer *cmd,
631bf215546Sopenharmony_ci                         struct tu_cmd_buffer *secondary);
632bf215546Sopenharmony_ci
633bf215546Sopenharmony_civoid
634bf215546Sopenharmony_citu_append_post_chain(struct tu_cmd_buffer *cmd,
635bf215546Sopenharmony_ci                     struct tu_cmd_buffer *secondary);
636bf215546Sopenharmony_ci
637bf215546Sopenharmony_civoid
638bf215546Sopenharmony_citu_restore_suspended_pass(struct tu_cmd_buffer *cmd,
639bf215546Sopenharmony_ci                          struct tu_cmd_buffer *suspended);
640bf215546Sopenharmony_ci
641bf215546Sopenharmony_civoid tu_cmd_render(struct tu_cmd_buffer *cmd);
642bf215546Sopenharmony_ci
643bf215546Sopenharmony_civoid
644bf215546Sopenharmony_citu6_emit_event_write(struct tu_cmd_buffer *cmd,
645bf215546Sopenharmony_ci                     struct tu_cs *cs,
646bf215546Sopenharmony_ci                     enum vgt_event_type event);
647bf215546Sopenharmony_ci
648bf215546Sopenharmony_cistatic inline struct tu_descriptor_state *
649bf215546Sopenharmony_citu_get_descriptors_state(struct tu_cmd_buffer *cmd_buffer,
650bf215546Sopenharmony_ci                         VkPipelineBindPoint bind_point)
651bf215546Sopenharmony_ci{
652bf215546Sopenharmony_ci   return &cmd_buffer->descriptors[bind_point];
653bf215546Sopenharmony_ci}
654bf215546Sopenharmony_ci
655bf215546Sopenharmony_civoid tu6_emit_msaa(struct tu_cs *cs, VkSampleCountFlagBits samples,
656bf215546Sopenharmony_ci                   enum a5xx_line_mode line_mode);
657bf215546Sopenharmony_ci
658bf215546Sopenharmony_civoid tu6_emit_window_scissor(struct tu_cs *cs, uint32_t x1, uint32_t y1, uint32_t x2, uint32_t y2);
659bf215546Sopenharmony_ci
660bf215546Sopenharmony_civoid tu6_emit_window_offset(struct tu_cs *cs, uint32_t x1, uint32_t y1);
661bf215546Sopenharmony_ci
662bf215546Sopenharmony_civoid tu_disable_draw_states(struct tu_cmd_buffer *cmd, struct tu_cs *cs);
663bf215546Sopenharmony_ci
664bf215546Sopenharmony_civoid tu6_apply_depth_bounds_workaround(struct tu_device *device,
665bf215546Sopenharmony_ci                                       uint32_t *rb_depth_cntl);
666bf215546Sopenharmony_ci
667bf215546Sopenharmony_civoid
668bf215546Sopenharmony_ciupdate_stencil_mask(uint32_t *value, VkStencilFaceFlags face, uint32_t mask);
669bf215546Sopenharmony_ci
670bf215546Sopenharmony_ci#endif /* TU_CMD_BUFFER_H */
671