2 * Copyright 2014, 2015 Red Hat.
4 * Permission is hereby granted, free of charge, to any person obtaining a
5 * copy of this software and associated documentation files (the "Software"),
6 * to deal in the Software without restriction, including without limitation
7 * on the rights to use, copy, modify, merge, publish, distribute, sub
8 * license, and/or sell copies of the Software, and to permit persons to whom
9 * the Software is furnished to do so, subject to the following conditions:
11 * The above copyright notice and this permission notice (including the next
12 * paragraph) shall be included in all copies or substantial portions of the
15 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
18 * THE AUTHOR(S) AND/OR THEIR SUPPLIERS BE LIABLE FOR ANY CLAIM,
19 * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
20 * OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
21 * USE OR OTHER DEALINGS IN THE SOFTWARE.
25 #include "util/u_memory.h"
26 #include "util/u_math.h"
27 #include "pipe/p_state.h"
28 #include "virgl_encode.h"
29 #include "virgl_resource.h"
30 #include "tgsi/tgsi_dump.h"
31 #include "tgsi/tgsi_parse.h"
33 static int virgl_encoder_write_cmd_dword(struct virgl_context
*ctx
,
36 int len
= (dword
>> 16);
38 if ((ctx
->cbuf
->cdw
+ len
+ 1) > VIRGL_MAX_CMDBUF_DWORDS
)
39 ctx
->base
.flush(&ctx
->base
, NULL
, 0);
41 virgl_encoder_write_dword(ctx
->cbuf
, dword
);
45 static void virgl_encoder_write_res(struct virgl_context
*ctx
,
46 struct virgl_resource
*res
)
48 struct virgl_winsys
*vws
= virgl_screen(ctx
->base
.screen
)->vws
;
50 if (res
&& res
->hw_res
)
51 vws
->emit_res(vws
, ctx
->cbuf
, res
->hw_res
, TRUE
);
53 virgl_encoder_write_dword(ctx
->cbuf
, 0);
57 int virgl_encode_bind_object(struct virgl_context
*ctx
,
58 uint32_t handle
, uint32_t object
)
60 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_BIND_OBJECT
, object
, 1));
61 virgl_encoder_write_dword(ctx
->cbuf
, handle
);
65 int virgl_encode_delete_object(struct virgl_context
*ctx
,
66 uint32_t handle
, uint32_t object
)
68 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_DESTROY_OBJECT
, object
, 1));
69 virgl_encoder_write_dword(ctx
->cbuf
, handle
);
73 int virgl_encode_blend_state(struct virgl_context
*ctx
,
75 const struct pipe_blend_state
*blend_state
)
80 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_CREATE_OBJECT
, VIRGL_OBJECT_BLEND
, VIRGL_OBJ_BLEND_SIZE
));
81 virgl_encoder_write_dword(ctx
->cbuf
, handle
);
84 VIRGL_OBJ_BLEND_S0_INDEPENDENT_BLEND_ENABLE(blend_state
->independent_blend_enable
) |
85 VIRGL_OBJ_BLEND_S0_LOGICOP_ENABLE(blend_state
->logicop_enable
) |
86 VIRGL_OBJ_BLEND_S0_DITHER(blend_state
->dither
) |
87 VIRGL_OBJ_BLEND_S0_ALPHA_TO_COVERAGE(blend_state
->alpha_to_coverage
) |
88 VIRGL_OBJ_BLEND_S0_ALPHA_TO_ONE(blend_state
->alpha_to_one
);
90 virgl_encoder_write_dword(ctx
->cbuf
, tmp
);
92 tmp
= VIRGL_OBJ_BLEND_S1_LOGICOP_FUNC(blend_state
->logicop_func
);
93 virgl_encoder_write_dword(ctx
->cbuf
, tmp
);
95 for (i
= 0; i
< VIRGL_MAX_COLOR_BUFS
; i
++) {
97 VIRGL_OBJ_BLEND_S2_RT_BLEND_ENABLE(blend_state
->rt
[i
].blend_enable
) |
98 VIRGL_OBJ_BLEND_S2_RT_RGB_FUNC(blend_state
->rt
[i
].rgb_func
) |
99 VIRGL_OBJ_BLEND_S2_RT_RGB_SRC_FACTOR(blend_state
->rt
[i
].rgb_src_factor
) |
100 VIRGL_OBJ_BLEND_S2_RT_RGB_DST_FACTOR(blend_state
->rt
[i
].rgb_dst_factor
)|
101 VIRGL_OBJ_BLEND_S2_RT_ALPHA_FUNC(blend_state
->rt
[i
].alpha_func
) |
102 VIRGL_OBJ_BLEND_S2_RT_ALPHA_SRC_FACTOR(blend_state
->rt
[i
].alpha_src_factor
) |
103 VIRGL_OBJ_BLEND_S2_RT_ALPHA_DST_FACTOR(blend_state
->rt
[i
].alpha_dst_factor
) |
104 VIRGL_OBJ_BLEND_S2_RT_COLORMASK(blend_state
->rt
[i
].colormask
);
105 virgl_encoder_write_dword(ctx
->cbuf
, tmp
);
110 int virgl_encode_dsa_state(struct virgl_context
*ctx
,
112 const struct pipe_depth_stencil_alpha_state
*dsa_state
)
116 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_CREATE_OBJECT
, VIRGL_OBJECT_DSA
, VIRGL_OBJ_DSA_SIZE
));
117 virgl_encoder_write_dword(ctx
->cbuf
, handle
);
119 tmp
= VIRGL_OBJ_DSA_S0_DEPTH_ENABLE(dsa_state
->depth
.enabled
) |
120 VIRGL_OBJ_DSA_S0_DEPTH_WRITEMASK(dsa_state
->depth
.writemask
) |
121 VIRGL_OBJ_DSA_S0_DEPTH_FUNC(dsa_state
->depth
.func
) |
122 VIRGL_OBJ_DSA_S0_ALPHA_ENABLED(dsa_state
->alpha
.enabled
) |
123 VIRGL_OBJ_DSA_S0_ALPHA_FUNC(dsa_state
->alpha
.func
);
124 virgl_encoder_write_dword(ctx
->cbuf
, tmp
);
126 for (i
= 0; i
< 2; i
++) {
127 tmp
= VIRGL_OBJ_DSA_S1_STENCIL_ENABLED(dsa_state
->stencil
[i
].enabled
) |
128 VIRGL_OBJ_DSA_S1_STENCIL_FUNC(dsa_state
->stencil
[i
].func
) |
129 VIRGL_OBJ_DSA_S1_STENCIL_FAIL_OP(dsa_state
->stencil
[i
].fail_op
) |
130 VIRGL_OBJ_DSA_S1_STENCIL_ZPASS_OP(dsa_state
->stencil
[i
].zpass_op
) |
131 VIRGL_OBJ_DSA_S1_STENCIL_ZFAIL_OP(dsa_state
->stencil
[i
].zfail_op
) |
132 VIRGL_OBJ_DSA_S1_STENCIL_VALUEMASK(dsa_state
->stencil
[i
].valuemask
) |
133 VIRGL_OBJ_DSA_S1_STENCIL_WRITEMASK(dsa_state
->stencil
[i
].writemask
);
134 virgl_encoder_write_dword(ctx
->cbuf
, tmp
);
137 virgl_encoder_write_dword(ctx
->cbuf
, fui(dsa_state
->alpha
.ref_value
));
140 int virgl_encode_rasterizer_state(struct virgl_context
*ctx
,
142 const struct pipe_rasterizer_state
*state
)
146 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_CREATE_OBJECT
, VIRGL_OBJECT_RASTERIZER
, VIRGL_OBJ_RS_SIZE
));
147 virgl_encoder_write_dword(ctx
->cbuf
, handle
);
149 tmp
= VIRGL_OBJ_RS_S0_FLATSHADE(state
->flatshade
) |
150 VIRGL_OBJ_RS_S0_DEPTH_CLIP(state
->depth_clip
) |
151 VIRGL_OBJ_RS_S0_CLIP_HALFZ(state
->clip_halfz
) |
152 VIRGL_OBJ_RS_S0_RASTERIZER_DISCARD(state
->rasterizer_discard
) |
153 VIRGL_OBJ_RS_S0_FLATSHADE_FIRST(state
->flatshade_first
) |
154 VIRGL_OBJ_RS_S0_LIGHT_TWOSIZE(state
->light_twoside
) |
155 VIRGL_OBJ_RS_S0_SPRITE_COORD_MODE(state
->sprite_coord_mode
) |
156 VIRGL_OBJ_RS_S0_POINT_QUAD_RASTERIZATION(state
->point_quad_rasterization
) |
157 VIRGL_OBJ_RS_S0_CULL_FACE(state
->cull_face
) |
158 VIRGL_OBJ_RS_S0_FILL_FRONT(state
->fill_front
) |
159 VIRGL_OBJ_RS_S0_FILL_BACK(state
->fill_back
) |
160 VIRGL_OBJ_RS_S0_SCISSOR(state
->scissor
) |
161 VIRGL_OBJ_RS_S0_FRONT_CCW(state
->front_ccw
) |
162 VIRGL_OBJ_RS_S0_CLAMP_VERTEX_COLOR(state
->clamp_vertex_color
) |
163 VIRGL_OBJ_RS_S0_CLAMP_FRAGMENT_COLOR(state
->clamp_fragment_color
) |
164 VIRGL_OBJ_RS_S0_OFFSET_LINE(state
->offset_line
) |
165 VIRGL_OBJ_RS_S0_OFFSET_POINT(state
->offset_point
) |
166 VIRGL_OBJ_RS_S0_OFFSET_TRI(state
->offset_tri
) |
167 VIRGL_OBJ_RS_S0_POLY_SMOOTH(state
->poly_smooth
) |
168 VIRGL_OBJ_RS_S0_POLY_STIPPLE_ENABLE(state
->poly_stipple_enable
) |
169 VIRGL_OBJ_RS_S0_POINT_SMOOTH(state
->point_smooth
) |
170 VIRGL_OBJ_RS_S0_POINT_SIZE_PER_VERTEX(state
->point_size_per_vertex
) |
171 VIRGL_OBJ_RS_S0_MULTISAMPLE(state
->multisample
) |
172 VIRGL_OBJ_RS_S0_LINE_SMOOTH(state
->line_smooth
) |
173 VIRGL_OBJ_RS_S0_LINE_STIPPLE_ENABLE(state
->line_stipple_enable
) |
174 VIRGL_OBJ_RS_S0_LINE_LAST_PIXEL(state
->line_last_pixel
) |
175 VIRGL_OBJ_RS_S0_HALF_PIXEL_CENTER(state
->half_pixel_center
) |
176 VIRGL_OBJ_RS_S0_BOTTOM_EDGE_RULE(state
->bottom_edge_rule
);
178 virgl_encoder_write_dword(ctx
->cbuf
, tmp
); /* S0 */
179 virgl_encoder_write_dword(ctx
->cbuf
, fui(state
->point_size
)); /* S1 */
180 virgl_encoder_write_dword(ctx
->cbuf
, state
->sprite_coord_enable
); /* S2 */
181 tmp
= VIRGL_OBJ_RS_S3_LINE_STIPPLE_PATTERN(state
->line_stipple_pattern
) |
182 VIRGL_OBJ_RS_S3_LINE_STIPPLE_FACTOR(state
->line_stipple_factor
) |
183 VIRGL_OBJ_RS_S3_CLIP_PLANE_ENABLE(state
->clip_plane_enable
);
184 virgl_encoder_write_dword(ctx
->cbuf
, tmp
); /* S3 */
185 virgl_encoder_write_dword(ctx
->cbuf
, fui(state
->line_width
)); /* S4 */
186 virgl_encoder_write_dword(ctx
->cbuf
, fui(state
->offset_units
)); /* S5 */
187 virgl_encoder_write_dword(ctx
->cbuf
, fui(state
->offset_scale
)); /* S6 */
188 virgl_encoder_write_dword(ctx
->cbuf
, fui(state
->offset_clamp
)); /* S7 */
192 static void virgl_emit_shader_header(struct virgl_context
*ctx
,
193 uint32_t handle
, uint32_t len
,
194 uint32_t type
, uint32_t offlen
,
197 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_CREATE_OBJECT
, VIRGL_OBJECT_SHADER
, len
));
198 virgl_encoder_write_dword(ctx
->cbuf
, handle
);
199 virgl_encoder_write_dword(ctx
->cbuf
, type
);
200 virgl_encoder_write_dword(ctx
->cbuf
, offlen
);
201 virgl_encoder_write_dword(ctx
->cbuf
, num_tokens
);
204 static void virgl_emit_shader_streamout(struct virgl_context
*ctx
,
205 const struct pipe_stream_output_info
*so_info
)
212 num_outputs
= so_info
->num_outputs
;
214 virgl_encoder_write_dword(ctx
->cbuf
, num_outputs
);
216 for (i
= 0; i
< 4; i
++)
217 virgl_encoder_write_dword(ctx
->cbuf
, so_info
->stride
[i
]);
219 for (i
= 0; i
< so_info
->num_outputs
; i
++) {
221 VIRGL_OBJ_SHADER_SO_OUTPUT_REGISTER_INDEX(so_info
->output
[i
].register_index
) |
222 VIRGL_OBJ_SHADER_SO_OUTPUT_START_COMPONENT(so_info
->output
[i
].start_component
) |
223 VIRGL_OBJ_SHADER_SO_OUTPUT_NUM_COMPONENTS(so_info
->output
[i
].num_components
) |
224 VIRGL_OBJ_SHADER_SO_OUTPUT_BUFFER(so_info
->output
[i
].output_buffer
) |
225 VIRGL_OBJ_SHADER_SO_OUTPUT_DST_OFFSET(so_info
->output
[i
].dst_offset
);
226 virgl_encoder_write_dword(ctx
->cbuf
, tmp
);
227 virgl_encoder_write_dword(ctx
->cbuf
, 0);
232 int virgl_encode_shader_state(struct virgl_context
*ctx
,
235 const struct pipe_stream_output_info
*so_info
,
236 const struct tgsi_token
*tokens
)
239 uint32_t shader_len
, len
;
241 int num_tokens
= tgsi_num_tokens(tokens
);
242 int str_total_size
= 65536;
244 uint32_t left_bytes
, base_hdr_size
, strm_hdr_size
, thispass
;
246 str
= CALLOC(1, str_total_size
);
253 bret
= tgsi_dump_str(tokens
, TGSI_DUMP_FLOAT_AS_HEX
, str
, str_total_size
);
255 fprintf(stderr
, "Failed to translate shader in available space - trying again\n");
256 old_size
= str_total_size
;
257 str_total_size
= 65536 * ++retry_size
;
258 str
= REALLOC(str
, old_size
, str_total_size
);
262 } while (bret
== false && retry_size
< 10);
267 shader_len
= strlen(str
) + 1;
269 left_bytes
= shader_len
;
272 strm_hdr_size
= so_info
->num_outputs
? so_info
->num_outputs
* 2 + 4 : 0;
276 uint32_t length
, offlen
;
277 int hdr_len
= base_hdr_size
+ (first_pass
? strm_hdr_size
: 0);
278 if (ctx
->cbuf
->cdw
+ hdr_len
+ 1 > VIRGL_MAX_CMDBUF_DWORDS
)
279 ctx
->base
.flush(&ctx
->base
, NULL
, 0);
281 thispass
= (VIRGL_MAX_CMDBUF_DWORDS
- ctx
->cbuf
->cdw
- hdr_len
- 1) * 4;
283 length
= MIN2(thispass
, left_bytes
);
284 len
= ((length
+ 3) / 4) + hdr_len
;
287 offlen
= VIRGL_OBJ_SHADER_OFFSET_VAL(shader_len
);
289 offlen
= VIRGL_OBJ_SHADER_OFFSET_VAL((uintptr_t)sptr
- (uintptr_t)str
) | VIRGL_OBJ_SHADER_OFFSET_CONT
;
291 virgl_emit_shader_header(ctx
, handle
, len
, type
, offlen
, num_tokens
);
293 virgl_emit_shader_streamout(ctx
, first_pass
? so_info
: NULL
);
295 virgl_encoder_write_block(ctx
->cbuf
, (uint8_t *)sptr
, length
);
299 left_bytes
-= length
;
307 int virgl_encode_clear(struct virgl_context
*ctx
,
309 const union pipe_color_union
*color
,
310 double depth
, unsigned stencil
)
314 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_CLEAR
, 0, VIRGL_OBJ_CLEAR_SIZE
));
315 virgl_encoder_write_dword(ctx
->cbuf
, buffers
);
316 for (i
= 0; i
< 4; i
++)
317 virgl_encoder_write_dword(ctx
->cbuf
, color
->ui
[i
]);
318 virgl_encoder_write_qword(ctx
->cbuf
, *(uint64_t *)&depth
);
319 virgl_encoder_write_dword(ctx
->cbuf
, stencil
);
323 int virgl_encoder_set_framebuffer_state(struct virgl_context
*ctx
,
324 const struct pipe_framebuffer_state
*state
)
326 struct virgl_surface
*zsurf
= virgl_surface(state
->zsbuf
);
329 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_SET_FRAMEBUFFER_STATE
, 0, VIRGL_SET_FRAMEBUFFER_STATE_SIZE(state
->nr_cbufs
)));
330 virgl_encoder_write_dword(ctx
->cbuf
, state
->nr_cbufs
);
331 virgl_encoder_write_dword(ctx
->cbuf
, zsurf
? zsurf
->handle
: 0);
332 for (i
= 0; i
< state
->nr_cbufs
; i
++) {
333 struct virgl_surface
*surf
= virgl_surface(state
->cbufs
[i
]);
334 virgl_encoder_write_dword(ctx
->cbuf
, surf
? surf
->handle
: 0);
340 int virgl_encoder_set_viewport_states(struct virgl_context
*ctx
,
343 const struct pipe_viewport_state
*states
)
346 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_SET_VIEWPORT_STATE
, 0, VIRGL_SET_VIEWPORT_STATE_SIZE(num_viewports
)));
347 virgl_encoder_write_dword(ctx
->cbuf
, start_slot
);
348 for (v
= 0; v
< num_viewports
; v
++) {
349 for (i
= 0; i
< 3; i
++)
350 virgl_encoder_write_dword(ctx
->cbuf
, fui(states
[v
].scale
[i
]));
351 for (i
= 0; i
< 3; i
++)
352 virgl_encoder_write_dword(ctx
->cbuf
, fui(states
[v
].translate
[i
]));
357 int virgl_encoder_create_vertex_elements(struct virgl_context
*ctx
,
359 unsigned num_elements
,
360 const struct pipe_vertex_element
*element
)
363 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_CREATE_OBJECT
, VIRGL_OBJECT_VERTEX_ELEMENTS
, VIRGL_OBJ_VERTEX_ELEMENTS_SIZE(num_elements
)));
364 virgl_encoder_write_dword(ctx
->cbuf
, handle
);
365 for (i
= 0; i
< num_elements
; i
++) {
366 virgl_encoder_write_dword(ctx
->cbuf
, element
[i
].src_offset
);
367 virgl_encoder_write_dword(ctx
->cbuf
, element
[i
].instance_divisor
);
368 virgl_encoder_write_dword(ctx
->cbuf
, element
[i
].vertex_buffer_index
);
369 virgl_encoder_write_dword(ctx
->cbuf
, element
[i
].src_format
);
374 int virgl_encoder_set_vertex_buffers(struct virgl_context
*ctx
,
375 unsigned num_buffers
,
376 const struct pipe_vertex_buffer
*buffers
)
379 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_SET_VERTEX_BUFFERS
, 0, VIRGL_SET_VERTEX_BUFFERS_SIZE(num_buffers
)));
380 for (i
= 0; i
< num_buffers
; i
++) {
381 struct virgl_resource
*res
= virgl_resource(buffers
[i
].buffer
);
382 virgl_encoder_write_dword(ctx
->cbuf
, buffers
[i
].stride
);
383 virgl_encoder_write_dword(ctx
->cbuf
, buffers
[i
].buffer_offset
);
384 virgl_encoder_write_res(ctx
, res
);
389 int virgl_encoder_set_index_buffer(struct virgl_context
*ctx
,
390 const struct pipe_index_buffer
*ib
)
392 int length
= VIRGL_SET_INDEX_BUFFER_SIZE(ib
);
393 struct virgl_resource
*res
= NULL
;
395 res
= virgl_resource(ib
->buffer
);
397 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_SET_INDEX_BUFFER
, 0, length
));
398 virgl_encoder_write_res(ctx
, res
);
400 virgl_encoder_write_dword(ctx
->cbuf
, ib
->index_size
);
401 virgl_encoder_write_dword(ctx
->cbuf
, ib
->offset
);
406 int virgl_encoder_draw_vbo(struct virgl_context
*ctx
,
407 const struct pipe_draw_info
*info
)
409 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_DRAW_VBO
, 0, VIRGL_DRAW_VBO_SIZE
));
410 virgl_encoder_write_dword(ctx
->cbuf
, info
->start
);
411 virgl_encoder_write_dword(ctx
->cbuf
, info
->count
);
412 virgl_encoder_write_dword(ctx
->cbuf
, info
->mode
);
413 virgl_encoder_write_dword(ctx
->cbuf
, info
->indexed
);
414 virgl_encoder_write_dword(ctx
->cbuf
, info
->instance_count
);
415 virgl_encoder_write_dword(ctx
->cbuf
, info
->index_bias
);
416 virgl_encoder_write_dword(ctx
->cbuf
, info
->start_instance
);
417 virgl_encoder_write_dword(ctx
->cbuf
, info
->primitive_restart
);
418 virgl_encoder_write_dword(ctx
->cbuf
, info
->restart_index
);
419 virgl_encoder_write_dword(ctx
->cbuf
, info
->min_index
);
420 virgl_encoder_write_dword(ctx
->cbuf
, info
->max_index
);
421 if (info
->count_from_stream_output
)
422 virgl_encoder_write_dword(ctx
->cbuf
, info
->count_from_stream_output
->buffer_size
);
424 virgl_encoder_write_dword(ctx
->cbuf
, 0);
428 int virgl_encoder_create_surface(struct virgl_context
*ctx
,
430 struct virgl_resource
*res
,
431 const struct pipe_surface
*templat
)
433 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_CREATE_OBJECT
, VIRGL_OBJECT_SURFACE
, VIRGL_OBJ_SURFACE_SIZE
));
434 virgl_encoder_write_dword(ctx
->cbuf
, handle
);
435 virgl_encoder_write_res(ctx
, res
);
436 virgl_encoder_write_dword(ctx
->cbuf
, templat
->format
);
437 if (templat
->texture
->target
== PIPE_BUFFER
) {
438 virgl_encoder_write_dword(ctx
->cbuf
, templat
->u
.buf
.first_element
);
439 virgl_encoder_write_dword(ctx
->cbuf
, templat
->u
.buf
.last_element
);
442 virgl_encoder_write_dword(ctx
->cbuf
, templat
->u
.tex
.level
);
443 virgl_encoder_write_dword(ctx
->cbuf
, templat
->u
.tex
.first_layer
| (templat
->u
.tex
.last_layer
<< 16));
448 int virgl_encoder_create_so_target(struct virgl_context
*ctx
,
450 struct virgl_resource
*res
,
451 unsigned buffer_offset
,
452 unsigned buffer_size
)
454 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_CREATE_OBJECT
, VIRGL_OBJECT_STREAMOUT_TARGET
, VIRGL_OBJ_STREAMOUT_SIZE
));
455 virgl_encoder_write_dword(ctx
->cbuf
, handle
);
456 virgl_encoder_write_res(ctx
, res
);
457 virgl_encoder_write_dword(ctx
->cbuf
, buffer_offset
);
458 virgl_encoder_write_dword(ctx
->cbuf
, buffer_size
);
462 static void virgl_encoder_iw_emit_header_1d(struct virgl_context
*ctx
,
463 struct virgl_resource
*res
,
464 unsigned level
, unsigned usage
,
465 const struct pipe_box
*box
,
466 unsigned stride
, unsigned layer_stride
)
468 virgl_encoder_write_res(ctx
, res
);
469 virgl_encoder_write_dword(ctx
->cbuf
, level
);
470 virgl_encoder_write_dword(ctx
->cbuf
, usage
);
471 virgl_encoder_write_dword(ctx
->cbuf
, stride
);
472 virgl_encoder_write_dword(ctx
->cbuf
, layer_stride
);
473 virgl_encoder_write_dword(ctx
->cbuf
, box
->x
);
474 virgl_encoder_write_dword(ctx
->cbuf
, box
->y
);
475 virgl_encoder_write_dword(ctx
->cbuf
, box
->z
);
476 virgl_encoder_write_dword(ctx
->cbuf
, box
->width
);
477 virgl_encoder_write_dword(ctx
->cbuf
, box
->height
);
478 virgl_encoder_write_dword(ctx
->cbuf
, box
->depth
);
481 int virgl_encoder_inline_write(struct virgl_context
*ctx
,
482 struct virgl_resource
*res
,
483 unsigned level
, unsigned usage
,
484 const struct pipe_box
*box
,
485 const void *data
, unsigned stride
,
486 unsigned layer_stride
)
488 uint32_t size
= (stride
? stride
: box
->width
) * box
->height
;
489 uint32_t length
, thispass
, left_bytes
;
490 struct pipe_box mybox
= *box
;
492 length
= 11 + (size
+ 3) / 4;
493 if ((ctx
->cbuf
->cdw
+ length
+ 1) > VIRGL_MAX_CMDBUF_DWORDS
) {
494 if (box
->height
> 1 || box
->depth
> 1) {
495 debug_printf("inline transfer failed due to multi dimensions and too large\n");
502 if (ctx
->cbuf
->cdw
+ 12 > VIRGL_MAX_CMDBUF_DWORDS
)
503 ctx
->base
.flush(&ctx
->base
, NULL
, 0);
505 thispass
= (VIRGL_MAX_CMDBUF_DWORDS
- ctx
->cbuf
->cdw
- 12) * 4;
507 length
= MIN2(thispass
, left_bytes
);
509 mybox
.width
= length
;
510 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_RESOURCE_INLINE_WRITE
, 0, ((length
+ 3) / 4) + 11));
511 virgl_encoder_iw_emit_header_1d(ctx
, res
, level
, usage
, &mybox
, stride
, layer_stride
);
512 virgl_encoder_write_block(ctx
->cbuf
, data
, length
);
513 left_bytes
-= length
;
520 int virgl_encoder_flush_frontbuffer(struct virgl_context
*ctx
,
521 struct virgl_resource
*res
)
523 // virgl_encoder_write_dword(ctx->cbuf, VIRGL_CMD0(VIRGL_CCMD_FLUSH_FRONTUBFFER, 0, 1));
524 // virgl_encoder_write_dword(ctx->cbuf, res_handle);
528 int virgl_encode_sampler_state(struct virgl_context
*ctx
,
530 const struct pipe_sampler_state
*state
)
534 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_CREATE_OBJECT
, VIRGL_OBJECT_SAMPLER_STATE
, VIRGL_OBJ_SAMPLER_STATE_SIZE
));
535 virgl_encoder_write_dword(ctx
->cbuf
, handle
);
537 tmp
= VIRGL_OBJ_SAMPLE_STATE_S0_WRAP_S(state
->wrap_s
) |
538 VIRGL_OBJ_SAMPLE_STATE_S0_WRAP_T(state
->wrap_t
) |
539 VIRGL_OBJ_SAMPLE_STATE_S0_WRAP_R(state
->wrap_r
) |
540 VIRGL_OBJ_SAMPLE_STATE_S0_MIN_IMG_FILTER(state
->min_img_filter
) |
541 VIRGL_OBJ_SAMPLE_STATE_S0_MIN_MIP_FILTER(state
->min_mip_filter
) |
542 VIRGL_OBJ_SAMPLE_STATE_S0_MAG_IMG_FILTER(state
->mag_img_filter
) |
543 VIRGL_OBJ_SAMPLE_STATE_S0_COMPARE_MODE(state
->compare_mode
) |
544 VIRGL_OBJ_SAMPLE_STATE_S0_COMPARE_FUNC(state
->compare_func
);
546 virgl_encoder_write_dword(ctx
->cbuf
, tmp
);
547 virgl_encoder_write_dword(ctx
->cbuf
, fui(state
->lod_bias
));
548 virgl_encoder_write_dword(ctx
->cbuf
, fui(state
->min_lod
));
549 virgl_encoder_write_dword(ctx
->cbuf
, fui(state
->max_lod
));
550 for (i
= 0; i
< 4; i
++)
551 virgl_encoder_write_dword(ctx
->cbuf
, state
->border_color
.ui
[i
]);
556 int virgl_encode_sampler_view(struct virgl_context
*ctx
,
558 struct virgl_resource
*res
,
559 const struct pipe_sampler_view
*state
)
562 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_CREATE_OBJECT
, VIRGL_OBJECT_SAMPLER_VIEW
, VIRGL_OBJ_SAMPLER_VIEW_SIZE
));
563 virgl_encoder_write_dword(ctx
->cbuf
, handle
);
564 virgl_encoder_write_res(ctx
, res
);
565 virgl_encoder_write_dword(ctx
->cbuf
, state
->format
);
566 if (res
->u
.b
.target
== PIPE_BUFFER
) {
567 virgl_encoder_write_dword(ctx
->cbuf
, state
->u
.buf
.first_element
);
568 virgl_encoder_write_dword(ctx
->cbuf
, state
->u
.buf
.last_element
);
570 virgl_encoder_write_dword(ctx
->cbuf
, state
->u
.tex
.first_layer
| state
->u
.tex
.last_layer
<< 16);
571 virgl_encoder_write_dword(ctx
->cbuf
, state
->u
.tex
.first_level
| state
->u
.tex
.last_level
<< 8);
573 tmp
= VIRGL_OBJ_SAMPLER_VIEW_SWIZZLE_R(state
->swizzle_r
) |
574 VIRGL_OBJ_SAMPLER_VIEW_SWIZZLE_G(state
->swizzle_g
) |
575 VIRGL_OBJ_SAMPLER_VIEW_SWIZZLE_B(state
->swizzle_b
) |
576 VIRGL_OBJ_SAMPLER_VIEW_SWIZZLE_A(state
->swizzle_a
);
577 virgl_encoder_write_dword(ctx
->cbuf
, tmp
);
581 int virgl_encode_set_sampler_views(struct virgl_context
*ctx
,
582 uint32_t shader_type
,
585 struct virgl_sampler_view
**views
)
588 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_SET_SAMPLER_VIEWS
, 0, VIRGL_SET_SAMPLER_VIEWS_SIZE(num_views
)));
589 virgl_encoder_write_dword(ctx
->cbuf
, shader_type
);
590 virgl_encoder_write_dword(ctx
->cbuf
, start_slot
);
591 for (i
= 0; i
< num_views
; i
++) {
592 uint32_t handle
= views
[i
] ? views
[i
]->handle
: 0;
593 virgl_encoder_write_dword(ctx
->cbuf
, handle
);
598 int virgl_encode_bind_sampler_states(struct virgl_context
*ctx
,
599 uint32_t shader_type
,
601 uint32_t num_handles
,
605 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_BIND_SAMPLER_STATES
, 0, VIRGL_BIND_SAMPLER_STATES(num_handles
)));
606 virgl_encoder_write_dword(ctx
->cbuf
, shader_type
);
607 virgl_encoder_write_dword(ctx
->cbuf
, start_slot
);
608 for (i
= 0; i
< num_handles
; i
++)
609 virgl_encoder_write_dword(ctx
->cbuf
, handles
[i
]);
613 int virgl_encoder_write_constant_buffer(struct virgl_context
*ctx
,
619 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_SET_CONSTANT_BUFFER
, 0, size
+ 2));
620 virgl_encoder_write_dword(ctx
->cbuf
, shader
);
621 virgl_encoder_write_dword(ctx
->cbuf
, index
);
623 virgl_encoder_write_block(ctx
->cbuf
, data
, size
* 4);
627 int virgl_encoder_set_uniform_buffer(struct virgl_context
*ctx
,
632 struct virgl_resource
*res
)
634 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_SET_UNIFORM_BUFFER
, 0, VIRGL_SET_UNIFORM_BUFFER_SIZE
));
635 virgl_encoder_write_dword(ctx
->cbuf
, shader
);
636 virgl_encoder_write_dword(ctx
->cbuf
, index
);
637 virgl_encoder_write_dword(ctx
->cbuf
, offset
);
638 virgl_encoder_write_dword(ctx
->cbuf
, length
);
639 virgl_encoder_write_res(ctx
, res
);
644 int virgl_encoder_set_stencil_ref(struct virgl_context
*ctx
,
645 const struct pipe_stencil_ref
*ref
)
647 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_SET_STENCIL_REF
, 0, VIRGL_SET_STENCIL_REF_SIZE
));
648 virgl_encoder_write_dword(ctx
->cbuf
, VIRGL_STENCIL_REF_VAL(ref
->ref_value
[0] , (ref
->ref_value
[1])));
652 int virgl_encoder_set_blend_color(struct virgl_context
*ctx
,
653 const struct pipe_blend_color
*color
)
656 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_SET_BLEND_COLOR
, 0, VIRGL_SET_BLEND_COLOR_SIZE
));
657 for (i
= 0; i
< 4; i
++)
658 virgl_encoder_write_dword(ctx
->cbuf
, fui(color
->color
[i
]));
662 int virgl_encoder_set_scissor_state(struct virgl_context
*ctx
,
665 const struct pipe_scissor_state
*ss
)
668 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_SET_SCISSOR_STATE
, 0, VIRGL_SET_SCISSOR_STATE_SIZE(num_scissors
)));
669 virgl_encoder_write_dword(ctx
->cbuf
, start_slot
);
670 for (i
= 0; i
< num_scissors
; i
++) {
671 virgl_encoder_write_dword(ctx
->cbuf
, (ss
[i
].minx
| ss
[i
].miny
<< 16));
672 virgl_encoder_write_dword(ctx
->cbuf
, (ss
[i
].maxx
| ss
[i
].maxy
<< 16));
677 void virgl_encoder_set_polygon_stipple(struct virgl_context
*ctx
,
678 const struct pipe_poly_stipple
*ps
)
681 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_SET_POLYGON_STIPPLE
, 0, VIRGL_POLYGON_STIPPLE_SIZE
));
682 for (i
= 0; i
< VIRGL_POLYGON_STIPPLE_SIZE
; i
++) {
683 virgl_encoder_write_dword(ctx
->cbuf
, ps
->stipple
[i
]);
687 void virgl_encoder_set_sample_mask(struct virgl_context
*ctx
,
688 unsigned sample_mask
)
690 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_SET_SAMPLE_MASK
, 0, VIRGL_SET_SAMPLE_MASK_SIZE
));
691 virgl_encoder_write_dword(ctx
->cbuf
, sample_mask
);
694 void virgl_encoder_set_clip_state(struct virgl_context
*ctx
,
695 const struct pipe_clip_state
*clip
)
698 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_SET_CLIP_STATE
, 0, VIRGL_SET_CLIP_STATE_SIZE
));
699 for (i
= 0; i
< VIRGL_MAX_CLIP_PLANES
; i
++) {
700 for (j
= 0; j
< 4; j
++) {
701 virgl_encoder_write_dword(ctx
->cbuf
, fui(clip
->ucp
[i
][j
]));
706 int virgl_encode_resource_copy_region(struct virgl_context
*ctx
,
707 struct virgl_resource
*dst_res
,
709 unsigned dstx
, unsigned dsty
, unsigned dstz
,
710 struct virgl_resource
*src_res
,
712 const struct pipe_box
*src_box
)
714 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_RESOURCE_COPY_REGION
, 0, VIRGL_CMD_RESOURCE_COPY_REGION_SIZE
));
715 virgl_encoder_write_res(ctx
, dst_res
);
716 virgl_encoder_write_dword(ctx
->cbuf
, dst_level
);
717 virgl_encoder_write_dword(ctx
->cbuf
, dstx
);
718 virgl_encoder_write_dword(ctx
->cbuf
, dsty
);
719 virgl_encoder_write_dword(ctx
->cbuf
, dstz
);
720 virgl_encoder_write_res(ctx
, src_res
);
721 virgl_encoder_write_dword(ctx
->cbuf
, src_level
);
722 virgl_encoder_write_dword(ctx
->cbuf
, src_box
->x
);
723 virgl_encoder_write_dword(ctx
->cbuf
, src_box
->y
);
724 virgl_encoder_write_dword(ctx
->cbuf
, src_box
->z
);
725 virgl_encoder_write_dword(ctx
->cbuf
, src_box
->width
);
726 virgl_encoder_write_dword(ctx
->cbuf
, src_box
->height
);
727 virgl_encoder_write_dword(ctx
->cbuf
, src_box
->depth
);
731 int virgl_encode_blit(struct virgl_context
*ctx
,
732 struct virgl_resource
*dst_res
,
733 struct virgl_resource
*src_res
,
734 const struct pipe_blit_info
*blit
)
737 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_BLIT
, 0, VIRGL_CMD_BLIT_SIZE
));
738 tmp
= VIRGL_CMD_BLIT_S0_MASK(blit
->mask
) |
739 VIRGL_CMD_BLIT_S0_FILTER(blit
->filter
) |
740 VIRGL_CMD_BLIT_S0_SCISSOR_ENABLE(blit
->scissor_enable
);
741 virgl_encoder_write_dword(ctx
->cbuf
, tmp
);
742 virgl_encoder_write_dword(ctx
->cbuf
, (blit
->scissor
.minx
| blit
->scissor
.miny
<< 16));
743 virgl_encoder_write_dword(ctx
->cbuf
, (blit
->scissor
.maxx
| blit
->scissor
.maxy
<< 16));
745 virgl_encoder_write_res(ctx
, dst_res
);
746 virgl_encoder_write_dword(ctx
->cbuf
, blit
->dst
.level
);
747 virgl_encoder_write_dword(ctx
->cbuf
, blit
->dst
.format
);
748 virgl_encoder_write_dword(ctx
->cbuf
, blit
->dst
.box
.x
);
749 virgl_encoder_write_dword(ctx
->cbuf
, blit
->dst
.box
.y
);
750 virgl_encoder_write_dword(ctx
->cbuf
, blit
->dst
.box
.z
);
751 virgl_encoder_write_dword(ctx
->cbuf
, blit
->dst
.box
.width
);
752 virgl_encoder_write_dword(ctx
->cbuf
, blit
->dst
.box
.height
);
753 virgl_encoder_write_dword(ctx
->cbuf
, blit
->dst
.box
.depth
);
755 virgl_encoder_write_res(ctx
, src_res
);
756 virgl_encoder_write_dword(ctx
->cbuf
, blit
->src
.level
);
757 virgl_encoder_write_dword(ctx
->cbuf
, blit
->src
.format
);
758 virgl_encoder_write_dword(ctx
->cbuf
, blit
->src
.box
.x
);
759 virgl_encoder_write_dword(ctx
->cbuf
, blit
->src
.box
.y
);
760 virgl_encoder_write_dword(ctx
->cbuf
, blit
->src
.box
.z
);
761 virgl_encoder_write_dword(ctx
->cbuf
, blit
->src
.box
.width
);
762 virgl_encoder_write_dword(ctx
->cbuf
, blit
->src
.box
.height
);
763 virgl_encoder_write_dword(ctx
->cbuf
, blit
->src
.box
.depth
);
767 int virgl_encoder_create_query(struct virgl_context
*ctx
,
771 struct virgl_resource
*res
,
774 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_CREATE_OBJECT
, VIRGL_OBJECT_QUERY
, VIRGL_OBJ_QUERY_SIZE
));
775 virgl_encoder_write_dword(ctx
->cbuf
, handle
);
776 virgl_encoder_write_dword(ctx
->cbuf
, ((query_type
& 0xffff) | (query_index
<< 16)));
777 virgl_encoder_write_dword(ctx
->cbuf
, offset
);
778 virgl_encoder_write_res(ctx
, res
);
782 int virgl_encoder_begin_query(struct virgl_context
*ctx
,
785 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_BEGIN_QUERY
, 0, 1));
786 virgl_encoder_write_dword(ctx
->cbuf
, handle
);
790 int virgl_encoder_end_query(struct virgl_context
*ctx
,
793 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_END_QUERY
, 0, 1));
794 virgl_encoder_write_dword(ctx
->cbuf
, handle
);
798 int virgl_encoder_get_query_result(struct virgl_context
*ctx
,
799 uint32_t handle
, boolean wait
)
801 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_GET_QUERY_RESULT
, 0, 2));
802 virgl_encoder_write_dword(ctx
->cbuf
, handle
);
803 virgl_encoder_write_dword(ctx
->cbuf
, wait
? 1 : 0);
807 int virgl_encoder_render_condition(struct virgl_context
*ctx
,
808 uint32_t handle
, boolean condition
,
811 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_SET_RENDER_CONDITION
, 0, VIRGL_RENDER_CONDITION_SIZE
));
812 virgl_encoder_write_dword(ctx
->cbuf
, handle
);
813 virgl_encoder_write_dword(ctx
->cbuf
, condition
);
814 virgl_encoder_write_dword(ctx
->cbuf
, mode
);
818 int virgl_encoder_set_so_targets(struct virgl_context
*ctx
,
819 unsigned num_targets
,
820 struct pipe_stream_output_target
**targets
,
821 unsigned append_bitmask
)
825 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_SET_STREAMOUT_TARGETS
, 0, num_targets
+ 1));
826 virgl_encoder_write_dword(ctx
->cbuf
, append_bitmask
);
827 for (i
= 0; i
< num_targets
; i
++) {
828 struct virgl_so_target
*tg
= virgl_so_target(targets
[i
]);
829 virgl_encoder_write_dword(ctx
->cbuf
, tg
->handle
);
835 int virgl_encoder_set_sub_ctx(struct virgl_context
*ctx
, uint32_t sub_ctx_id
)
837 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_SET_SUB_CTX
, 0, 1));
838 virgl_encoder_write_dword(ctx
->cbuf
, sub_ctx_id
);
842 int virgl_encoder_create_sub_ctx(struct virgl_context
*ctx
, uint32_t sub_ctx_id
)
844 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_CREATE_SUB_CTX
, 0, 1));
845 virgl_encoder_write_dword(ctx
->cbuf
, sub_ctx_id
);
849 int virgl_encoder_destroy_sub_ctx(struct virgl_context
*ctx
, uint32_t sub_ctx_id
)
851 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_DESTROY_SUB_CTX
, 0, 1));
852 virgl_encoder_write_dword(ctx
->cbuf
, sub_ctx_id
);
856 int virgl_encode_bind_shader(struct virgl_context
*ctx
,
857 uint32_t handle
, uint32_t type
)
859 virgl_encoder_write_cmd_dword(ctx
, VIRGL_CMD0(VIRGL_CCMD_BIND_SHADER
, 0, 2));
860 virgl_encoder_write_dword(ctx
->cbuf
, handle
);
861 virgl_encoder_write_dword(ctx
->cbuf
, type
);