vk/vulkan.h: Update clear color handling to 130
[mesa.git] / src / vulkan / meta.c
1 /*
2 * Copyright © 2015 Intel Corporation
3 *
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 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8 * and/or sell copies of the Software, and to permit persons to whom the
9 * Software is furnished to do so, subject to the following conditions:
10 *
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
13 * Software.
14 *
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 NONINFRINGEMENT. IN NO EVENT SHALL
18 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
20 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
21 * IN THE SOFTWARE.
22 */
23
24 #include <assert.h>
25 #include <stdbool.h>
26 #include <string.h>
27 #include <unistd.h>
28 #include <fcntl.h>
29
30 #include "private.h"
31 #include "meta-spirv.h"
32
33 static void
34 anv_device_init_meta_clear_state(struct anv_device *device)
35 {
36 VkPipelineIaStateCreateInfo ia_create_info = {
37 .sType = VK_STRUCTURE_TYPE_PIPELINE_IA_STATE_CREATE_INFO,
38 .topology = VK_PRIMITIVE_TOPOLOGY_TRIANGLE_STRIP,
39 .primitiveRestartEnable = false,
40 };
41
42 /* We don't use a vertex shader for clearing, but instead build and pass
43 * the VUEs directly to the rasterization backend.
44 */
45 VkShader fs = GLSL_VK_SHADER(device, FRAGMENT,
46 out vec4 f_color;
47 flat in vec4 v_color;
48 void main()
49 {
50 f_color = v_color;
51 }
52 );
53
54 VkPipelineShaderStageCreateInfo fs_create_info = {
55 .sType = VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO,
56 .pNext = &ia_create_info,
57 .shader = {
58 .stage = VK_SHADER_STAGE_FRAGMENT,
59 .shader = fs,
60 .linkConstBufferCount = 0,
61 .pLinkConstBufferInfo = NULL,
62 .pSpecializationInfo = NULL
63 }
64 };
65
66 /* We use instanced rendering to clear multiple render targets. We have two
67 * vertex buffers: the first vertex buffer holds per-vertex data and
68 * provides the vertices for the clear rectangle. The second one holds
69 * per-instance data, which consists of the VUE header (which selects the
70 * layer) and the color (Vulkan supports per-RT clear colors).
71 */
72 VkPipelineVertexInputStateCreateInfo vi_create_info = {
73 .sType = VK_STRUCTURE_TYPE_PIPELINE_VERTEX_INPUT_STATE_CREATE_INFO,
74 .pNext = &fs_create_info,
75 .bindingCount = 2,
76 .pVertexBindingDescriptions = (VkVertexInputBindingDescription[]) {
77 {
78 .binding = 0,
79 .strideInBytes = 8,
80 .stepRate = VK_VERTEX_INPUT_STEP_RATE_VERTEX
81 },
82 {
83 .binding = 1,
84 .strideInBytes = 32,
85 .stepRate = VK_VERTEX_INPUT_STEP_RATE_INSTANCE
86 },
87 },
88 .attributeCount = 3,
89 .pVertexAttributeDescriptions = (VkVertexInputAttributeDescription[]) {
90 {
91 /* VUE Header */
92 .location = 0,
93 .binding = 1,
94 .format = VK_FORMAT_R32G32B32A32_UINT,
95 .offsetInBytes = 0
96 },
97 {
98 /* Position */
99 .location = 1,
100 .binding = 0,
101 .format = VK_FORMAT_R32G32_SFLOAT,
102 .offsetInBytes = 0
103 },
104 {
105 /* Color */
106 .location = 2,
107 .binding = 1,
108 .format = VK_FORMAT_R32G32B32A32_SFLOAT,
109 .offsetInBytes = 16
110 }
111 }
112 };
113
114 VkPipelineRsStateCreateInfo rs_create_info = {
115 .sType = VK_STRUCTURE_TYPE_PIPELINE_RS_STATE_CREATE_INFO,
116 .pNext = &vi_create_info,
117 .depthClipEnable = true,
118 .rasterizerDiscardEnable = false,
119 .fillMode = VK_FILL_MODE_SOLID,
120 .cullMode = VK_CULL_MODE_NONE,
121 .frontFace = VK_FRONT_FACE_CCW
122 };
123
124 VkPipelineCbStateCreateInfo cb_create_info = {
125 .sType = VK_STRUCTURE_TYPE_PIPELINE_CB_STATE_CREATE_INFO,
126 .pNext = &rs_create_info,
127 .attachmentCount = 1,
128 .pAttachments = (VkPipelineCbAttachmentState []) {
129 { .channelWriteMask = VK_CHANNEL_A_BIT |
130 VK_CHANNEL_R_BIT | VK_CHANNEL_G_BIT | VK_CHANNEL_B_BIT },
131 }
132 };
133
134 anv_pipeline_create((VkDevice) device,
135 &(VkGraphicsPipelineCreateInfo) {
136 .sType = VK_STRUCTURE_TYPE_GRAPHICS_PIPELINE_CREATE_INFO,
137 .pNext = &cb_create_info,
138 .flags = 0,
139 .layout = 0
140 },
141 &(struct anv_pipeline_create_info) {
142 .use_repclear = true,
143 .disable_viewport = true,
144 .use_rectlist = true
145 },
146 &device->meta_state.clear.pipeline);
147
148 anv_DestroyObject((VkDevice) device, VK_OBJECT_TYPE_SHADER, fs);
149 }
150
151 #define NUM_VB_USED 2
152 struct anv_saved_state {
153 struct anv_vertex_binding old_vertex_bindings[NUM_VB_USED];
154 struct anv_descriptor_set *old_descriptor_set0;
155 struct anv_pipeline *old_pipeline;
156 VkDynamicCbState cb_state;
157 };
158
159 static void
160 anv_cmd_buffer_save(struct anv_cmd_buffer *cmd_buffer,
161 struct anv_saved_state *state)
162 {
163 state->old_pipeline = cmd_buffer->pipeline;
164 state->old_descriptor_set0 = cmd_buffer->descriptors[0].set;
165 memcpy(state->old_vertex_bindings, cmd_buffer->vertex_bindings,
166 sizeof(state->old_vertex_bindings));
167 }
168
169 static void
170 anv_cmd_buffer_restore(struct anv_cmd_buffer *cmd_buffer,
171 const struct anv_saved_state *state)
172 {
173 cmd_buffer->pipeline = state->old_pipeline;
174 cmd_buffer->descriptors[0].set = state->old_descriptor_set0;
175 memcpy(cmd_buffer->vertex_bindings, state->old_vertex_bindings,
176 sizeof(state->old_vertex_bindings));
177
178 cmd_buffer->vb_dirty |= (1 << NUM_VB_USED) - 1;
179 cmd_buffer->dirty |= ANV_CMD_BUFFER_PIPELINE_DIRTY;
180 cmd_buffer->descriptors_dirty |= VK_SHADER_STAGE_VERTEX_BIT;
181 }
182
183 struct vue_header {
184 uint32_t Reserved;
185 uint32_t RTAIndex;
186 uint32_t ViewportIndex;
187 float PointWidth;
188 };
189
190 struct clear_instance_data {
191 struct vue_header vue_header;
192 VkClearColorValue color;
193 };
194
195 static void
196 meta_emit_clear(struct anv_cmd_buffer *cmd_buffer,
197 int num_instances,
198 struct clear_instance_data *instance_data)
199 {
200 struct anv_device *device = cmd_buffer->device;
201 struct anv_framebuffer *fb = cmd_buffer->framebuffer;
202 struct anv_state state;
203 uint32_t size;
204
205 const float vertex_data[] = {
206 /* Rect-list coordinates */
207 0.0, 0.0,
208 fb->width, 0.0,
209 fb->width, fb->height,
210
211 /* Align to 16 bytes */
212 0.0, 0.0,
213 };
214
215 size = sizeof(vertex_data) + num_instances * sizeof(*instance_data);
216 state = anv_state_stream_alloc(&cmd_buffer->surface_state_stream, size, 16);
217
218 /* Copy in the vertex and instance data */
219 memcpy(state.map, vertex_data, sizeof(vertex_data));
220 memcpy(state.map + sizeof(vertex_data), instance_data,
221 num_instances * sizeof(*instance_data));
222
223 struct anv_buffer vertex_buffer = {
224 .device = cmd_buffer->device,
225 .size = size,
226 .bo = &device->surface_state_block_pool.bo,
227 .offset = state.offset
228 };
229
230 anv_CmdBindVertexBuffers((VkCmdBuffer) cmd_buffer, 0, 2,
231 (VkBuffer[]) {
232 (VkBuffer) &vertex_buffer,
233 (VkBuffer) &vertex_buffer
234 },
235 (VkDeviceSize[]) {
236 0,
237 sizeof(vertex_data)
238 });
239
240 if ((VkPipeline) cmd_buffer->pipeline != device->meta_state.clear.pipeline)
241 anv_CmdBindPipeline((VkCmdBuffer) cmd_buffer,
242 VK_PIPELINE_BIND_POINT_GRAPHICS,
243 device->meta_state.clear.pipeline);
244
245 /* We don't need anything here, only set if not already set. */
246 if (cmd_buffer->rs_state == NULL)
247 anv_CmdBindDynamicStateObject((VkCmdBuffer) cmd_buffer,
248 VK_STATE_BIND_POINT_RASTER,
249 device->meta_state.shared.rs_state);
250
251 if (cmd_buffer->vp_state == NULL)
252 anv_CmdBindDynamicStateObject((VkCmdBuffer) cmd_buffer,
253 VK_STATE_BIND_POINT_VIEWPORT,
254 cmd_buffer->framebuffer->vp_state);
255
256 if (cmd_buffer->ds_state == NULL)
257 anv_CmdBindDynamicStateObject((VkCmdBuffer) cmd_buffer,
258 VK_STATE_BIND_POINT_DEPTH_STENCIL,
259 device->meta_state.shared.ds_state);
260
261 if (cmd_buffer->cb_state == NULL)
262 anv_CmdBindDynamicStateObject((VkCmdBuffer) cmd_buffer,
263 VK_STATE_BIND_POINT_COLOR_BLEND,
264 device->meta_state.shared.cb_state);
265
266 anv_CmdDraw((VkCmdBuffer) cmd_buffer, 0, 3, 0, num_instances);
267 }
268
269 void
270 anv_cmd_buffer_clear(struct anv_cmd_buffer *cmd_buffer,
271 struct anv_render_pass *pass)
272 {
273 struct anv_saved_state saved_state;
274
275 int num_clear_layers = 0;
276 struct clear_instance_data instance_data[MAX_RTS];
277
278 for (uint32_t i = 0; i < pass->num_layers; i++) {
279 if (pass->layers[i].color_load_op == VK_ATTACHMENT_LOAD_OP_CLEAR) {
280 instance_data[num_clear_layers++] = (struct clear_instance_data) {
281 .vue_header = {
282 .RTAIndex = i,
283 .ViewportIndex = 0,
284 .PointWidth = 0.0
285 },
286 .color = pass->layers[i].clear_color,
287 };
288 }
289 }
290
291 if (num_clear_layers == 0)
292 return;
293
294 anv_cmd_buffer_save(cmd_buffer, &saved_state);
295
296 meta_emit_clear(cmd_buffer, num_clear_layers, instance_data);
297
298 /* Restore API state */
299 anv_cmd_buffer_restore(cmd_buffer, &saved_state);
300 }
301
302 static void
303 anv_device_init_meta_blit_state(struct anv_device *device)
304 {
305 VkPipelineIaStateCreateInfo ia_create_info = {
306 .sType = VK_STRUCTURE_TYPE_PIPELINE_IA_STATE_CREATE_INFO,
307 .topology = VK_PRIMITIVE_TOPOLOGY_TRIANGLE_STRIP,
308 .primitiveRestartEnable = false,
309 };
310
311 /* We don't use a vertex shader for clearing, but instead build and pass
312 * the VUEs directly to the rasterization backend. However, we do need
313 * to provide GLSL source for the vertex shader so that the compiler
314 * does not dead-code our inputs.
315 */
316 VkShader vs = GLSL_VK_SHADER(device, VERTEX,
317 in vec2 a_pos;
318 in vec2 a_tex_coord;
319 out vec4 v_tex_coord;
320 void main()
321 {
322 v_tex_coord = vec4(a_tex_coord, 0, 1);
323 gl_Position = vec4(a_pos, 0, 1);
324 }
325 );
326
327 VkShader fs = GLSL_VK_SHADER(device, FRAGMENT,
328 out vec4 f_color;
329 in vec4 v_tex_coord;
330 layout(set = 0, binding = 0) uniform sampler2D u_tex;
331 void main()
332 {
333 f_color = texture(u_tex, v_tex_coord.xy);
334 }
335 );
336
337 VkPipelineShaderStageCreateInfo vs_create_info = {
338 .sType = VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO,
339 .pNext = &ia_create_info,
340 .shader = {
341 .stage = VK_SHADER_STAGE_VERTEX,
342 .shader = vs,
343 .linkConstBufferCount = 0,
344 .pLinkConstBufferInfo = NULL,
345 .pSpecializationInfo = NULL
346 }
347 };
348
349 VkPipelineShaderStageCreateInfo fs_create_info = {
350 .sType = VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO,
351 .pNext = &vs_create_info,
352 .shader = {
353 .stage = VK_SHADER_STAGE_FRAGMENT,
354 .shader = fs,
355 .linkConstBufferCount = 0,
356 .pLinkConstBufferInfo = NULL,
357 .pSpecializationInfo = NULL
358 }
359 };
360
361 VkPipelineVertexInputStateCreateInfo vi_create_info = {
362 .sType = VK_STRUCTURE_TYPE_PIPELINE_VERTEX_INPUT_STATE_CREATE_INFO,
363 .pNext = &fs_create_info,
364 .bindingCount = 2,
365 .pVertexBindingDescriptions = (VkVertexInputBindingDescription[]) {
366 {
367 .binding = 0,
368 .strideInBytes = 0,
369 .stepRate = VK_VERTEX_INPUT_STEP_RATE_VERTEX
370 },
371 {
372 .binding = 1,
373 .strideInBytes = 16,
374 .stepRate = VK_VERTEX_INPUT_STEP_RATE_VERTEX
375 },
376 },
377 .attributeCount = 3,
378 .pVertexAttributeDescriptions = (VkVertexInputAttributeDescription[]) {
379 {
380 /* VUE Header */
381 .location = 0,
382 .binding = 0,
383 .format = VK_FORMAT_R32G32B32A32_UINT,
384 .offsetInBytes = 0
385 },
386 {
387 /* Position */
388 .location = 1,
389 .binding = 1,
390 .format = VK_FORMAT_R32G32_SFLOAT,
391 .offsetInBytes = 0
392 },
393 {
394 /* Texture Coordinate */
395 .location = 2,
396 .binding = 1,
397 .format = VK_FORMAT_R32G32_SFLOAT,
398 .offsetInBytes = 8
399 }
400 }
401 };
402
403 VkDescriptorSetLayoutCreateInfo ds_layout_info = {
404 .sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_CREATE_INFO,
405 .count = 1,
406 .pBinding = (VkDescriptorSetLayoutBinding[]) {
407 {
408 .descriptorType = VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE,
409 .arraySize = 1,
410 .stageFlags = VK_SHADER_STAGE_FRAGMENT_BIT,
411 .pImmutableSamplers = NULL
412 },
413 }
414 };
415 anv_CreateDescriptorSetLayout((VkDevice) device, &ds_layout_info,
416 &device->meta_state.blit.ds_layout);
417
418 anv_CreatePipelineLayout((VkDevice) device,
419 &(VkPipelineLayoutCreateInfo) {
420 .sType = VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO,
421 .descriptorSetCount = 1,
422 .pSetLayouts = &device->meta_state.blit.ds_layout,
423 },
424 &device->meta_state.blit.pipeline_layout);
425
426 VkPipelineRsStateCreateInfo rs_create_info = {
427 .sType = VK_STRUCTURE_TYPE_PIPELINE_RS_STATE_CREATE_INFO,
428 .pNext = &vi_create_info,
429 .depthClipEnable = true,
430 .rasterizerDiscardEnable = false,
431 .fillMode = VK_FILL_MODE_SOLID,
432 .cullMode = VK_CULL_MODE_NONE,
433 .frontFace = VK_FRONT_FACE_CCW
434 };
435
436 VkPipelineCbStateCreateInfo cb_create_info = {
437 .sType = VK_STRUCTURE_TYPE_PIPELINE_CB_STATE_CREATE_INFO,
438 .pNext = &rs_create_info,
439 .attachmentCount = 1,
440 .pAttachments = (VkPipelineCbAttachmentState []) {
441 { .channelWriteMask = VK_CHANNEL_A_BIT |
442 VK_CHANNEL_R_BIT | VK_CHANNEL_G_BIT | VK_CHANNEL_B_BIT },
443 }
444 };
445
446 VkGraphicsPipelineCreateInfo pipeline_info = {
447 .sType = VK_STRUCTURE_TYPE_GRAPHICS_PIPELINE_CREATE_INFO,
448 .pNext = &cb_create_info,
449 .flags = 0,
450 .layout = device->meta_state.blit.pipeline_layout,
451 };
452
453 anv_pipeline_create((VkDevice) device, &pipeline_info,
454 &(struct anv_pipeline_create_info) {
455 .use_repclear = false,
456 .disable_viewport = true,
457 .disable_scissor = true,
458 .disable_vs = true,
459 .use_rectlist = true
460 },
461 &device->meta_state.blit.pipeline);
462
463 anv_DestroyObject((VkDevice) device, VK_OBJECT_TYPE_SHADER, vs);
464 anv_DestroyObject((VkDevice) device, VK_OBJECT_TYPE_SHADER, fs);
465 }
466
467 static void
468 meta_prepare_blit(struct anv_cmd_buffer *cmd_buffer,
469 struct anv_saved_state *saved_state)
470 {
471 struct anv_device *device = cmd_buffer->device;
472
473 anv_cmd_buffer_save(cmd_buffer, saved_state);
474
475 if ((VkPipeline) cmd_buffer->pipeline != device->meta_state.blit.pipeline)
476 anv_CmdBindPipeline((VkCmdBuffer) cmd_buffer,
477 VK_PIPELINE_BIND_POINT_GRAPHICS,
478 device->meta_state.blit.pipeline);
479
480 /* We don't need anything here, only set if not already set. */
481 if (cmd_buffer->rs_state == NULL)
482 anv_CmdBindDynamicStateObject((VkCmdBuffer) cmd_buffer,
483 VK_STATE_BIND_POINT_RASTER,
484 device->meta_state.shared.rs_state);
485 if (cmd_buffer->ds_state == NULL)
486 anv_CmdBindDynamicStateObject((VkCmdBuffer) cmd_buffer,
487 VK_STATE_BIND_POINT_DEPTH_STENCIL,
488 device->meta_state.shared.ds_state);
489
490 saved_state->cb_state = (VkDynamicCbState) cmd_buffer->cb_state;
491 anv_CmdBindDynamicStateObject((VkCmdBuffer) cmd_buffer,
492 VK_STATE_BIND_POINT_COLOR_BLEND,
493 device->meta_state.shared.cb_state);
494 }
495
496 struct blit_region {
497 VkOffset3D src_offset;
498 VkExtent3D src_extent;
499 VkOffset3D dest_offset;
500 VkExtent3D dest_extent;
501 };
502
503 static void
504 meta_emit_blit(struct anv_cmd_buffer *cmd_buffer,
505 struct anv_surface_view *src,
506 VkOffset3D src_offset,
507 VkExtent3D src_extent,
508 struct anv_surface_view *dest,
509 VkOffset3D dest_offset,
510 VkExtent3D dest_extent)
511 {
512 struct anv_device *device = cmd_buffer->device;
513
514 struct blit_vb_data {
515 float pos[2];
516 float tex_coord[2];
517 } *vb_data;
518
519 unsigned vb_size = sizeof(struct vue_header) + 3 * sizeof(*vb_data);
520
521 struct anv_state vb_state =
522 anv_state_stream_alloc(&cmd_buffer->surface_state_stream, vb_size, 16);
523 memset(vb_state.map, 0, sizeof(struct vue_header));
524 vb_data = vb_state.map + sizeof(struct vue_header);
525
526 vb_data[0] = (struct blit_vb_data) {
527 .pos = {
528 dest_offset.x + dest_extent.width,
529 dest_offset.y + dest_extent.height,
530 },
531 .tex_coord = {
532 (float)(src_offset.x + src_extent.width) / (float)src->extent.width,
533 (float)(src_offset.y + src_extent.height) / (float)src->extent.height,
534 },
535 };
536
537 vb_data[1] = (struct blit_vb_data) {
538 .pos = {
539 dest_offset.x,
540 dest_offset.y + dest_extent.height,
541 },
542 .tex_coord = {
543 (float)src_offset.x / (float)src->extent.width,
544 (float)(src_offset.y + src_extent.height) / (float)src->extent.height,
545 },
546 };
547
548 vb_data[2] = (struct blit_vb_data) {
549 .pos = {
550 dest_offset.x,
551 dest_offset.y,
552 },
553 .tex_coord = {
554 (float)src_offset.x / (float)src->extent.width,
555 (float)src_offset.y / (float)src->extent.height,
556 },
557 };
558
559 struct anv_buffer vertex_buffer = {
560 .device = device,
561 .size = vb_size,
562 .bo = &device->surface_state_block_pool.bo,
563 .offset = vb_state.offset,
564 };
565
566 anv_CmdBindVertexBuffers((VkCmdBuffer) cmd_buffer, 0, 2,
567 (VkBuffer[]) {
568 (VkBuffer) &vertex_buffer,
569 (VkBuffer) &vertex_buffer
570 },
571 (VkDeviceSize[]) {
572 0,
573 sizeof(struct vue_header),
574 });
575
576 uint32_t count;
577 VkDescriptorSet set;
578 anv_AllocDescriptorSets((VkDevice) device, 0 /* pool */,
579 VK_DESCRIPTOR_SET_USAGE_ONE_SHOT,
580 1, &device->meta_state.blit.ds_layout, &set, &count);
581 anv_UpdateDescriptors((VkDevice) device, set, 1,
582 (const void * []) {
583 &(VkUpdateImages) {
584 .sType = VK_STRUCTURE_TYPE_UPDATE_IMAGES,
585 .descriptorType = VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE,
586 .binding = 0,
587 .count = 1,
588 .pImageViews = (VkImageViewAttachInfo[]) {
589 {
590 .sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_ATTACH_INFO,
591 .view = (VkImageView) src,
592 .layout = VK_IMAGE_LAYOUT_GENERAL,
593 }
594 }
595 }
596 });
597
598 struct anv_framebuffer *fb;
599 anv_CreateFramebuffer((VkDevice) device,
600 &(VkFramebufferCreateInfo) {
601 .sType = VK_STRUCTURE_TYPE_FRAMEBUFFER_CREATE_INFO,
602 .colorAttachmentCount = 1,
603 .pColorAttachments = (VkColorAttachmentBindInfo[]) {
604 {
605 .view = (VkColorAttachmentView) dest,
606 .layout = VK_IMAGE_LAYOUT_GENERAL
607 }
608 },
609 .pDepthStencilAttachment = NULL,
610 .sampleCount = 1,
611 .width = dest->extent.width,
612 .height = dest->extent.height,
613 .layers = 1
614 }, (VkFramebuffer *)&fb);
615
616
617 VkRenderPass pass;
618 anv_CreateRenderPass((VkDevice )device,
619 &(VkRenderPassCreateInfo) {
620 .sType = VK_STRUCTURE_TYPE_RENDER_PASS_CREATE_INFO,
621 .renderArea = { { 0, 0 }, { dest->extent.width, dest->extent.height } },
622 .colorAttachmentCount = 1,
623 .extent = { 0, },
624 .sampleCount = 1,
625 .layers = 1,
626 .pColorFormats = (VkFormat[]) { dest->format },
627 .pColorLayouts = (VkImageLayout[]) { VK_IMAGE_LAYOUT_GENERAL },
628 .pColorLoadOps = (VkAttachmentLoadOp[]) { VK_ATTACHMENT_LOAD_OP_LOAD },
629 .pColorStoreOps = (VkAttachmentStoreOp[]) { VK_ATTACHMENT_STORE_OP_STORE },
630 .pColorLoadClearValues = (VkClearColorValue[]) {
631 { .f32 = { 1.0, 0.0, 0.0, 1.0 } }
632 },
633 .depthStencilFormat = VK_FORMAT_UNDEFINED,
634 }, &pass);
635
636 anv_CmdBeginRenderPass((VkCmdBuffer) cmd_buffer,
637 &(VkRenderPassBegin) {
638 .renderPass = pass,
639 .framebuffer = (VkFramebuffer) fb,
640 });
641
642 anv_CmdBindDynamicStateObject((VkCmdBuffer) cmd_buffer,
643 VK_STATE_BIND_POINT_VIEWPORT, fb->vp_state);
644
645 anv_CmdBindDescriptorSets((VkCmdBuffer) cmd_buffer,
646 VK_PIPELINE_BIND_POINT_GRAPHICS, 0, 1,
647 &set, 0, NULL);
648
649 anv_CmdDraw((VkCmdBuffer) cmd_buffer, 0, 3, 0, 1);
650
651 anv_CmdEndRenderPass((VkCmdBuffer) cmd_buffer);
652
653 /* At the point where we emit the draw call, all data from the
654 * descriptor sets, etc. has been used. We are free to delete it.
655 */
656 anv_DestroyObject((VkDevice) device, VK_OBJECT_TYPE_DESCRIPTOR_SET, set);
657 anv_DestroyObject((VkDevice) device, VK_OBJECT_TYPE_FRAMEBUFFER,
658 (VkFramebuffer) fb);
659 anv_DestroyObject((VkDevice) device, VK_OBJECT_TYPE_RENDER_PASS, pass);
660 }
661
662 static void
663 meta_finish_blit(struct anv_cmd_buffer *cmd_buffer,
664 const struct anv_saved_state *saved_state)
665 {
666 anv_cmd_buffer_restore(cmd_buffer, saved_state);
667 anv_CmdBindDynamicStateObject((VkCmdBuffer) cmd_buffer,
668 VK_STATE_BIND_POINT_COLOR_BLEND,
669 saved_state->cb_state);
670 }
671
672 static VkFormat
673 vk_format_for_cpp(int cpp)
674 {
675 switch (cpp) {
676 case 1: return VK_FORMAT_R8_UINT;
677 case 2: return VK_FORMAT_R8G8_UINT;
678 case 3: return VK_FORMAT_R8G8B8_UINT;
679 case 4: return VK_FORMAT_R8G8B8A8_UINT;
680 case 6: return VK_FORMAT_R16G16B16_UINT;
681 case 8: return VK_FORMAT_R16G16B16A16_UINT;
682 case 12: return VK_FORMAT_R32G32B32_UINT;
683 case 16: return VK_FORMAT_R32G32B32A32_UINT;
684 default:
685 unreachable("Invalid format cpp");
686 }
687 }
688
689 static void
690 do_buffer_copy(struct anv_cmd_buffer *cmd_buffer,
691 struct anv_bo *src, uint64_t src_offset,
692 struct anv_bo *dest, uint64_t dest_offset,
693 int width, int height, VkFormat copy_format)
694 {
695 VkDevice vk_device = (VkDevice)cmd_buffer->device;
696
697 VkImageCreateInfo image_info = {
698 .sType = VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO,
699 .imageType = VK_IMAGE_TYPE_2D,
700 .format = copy_format,
701 .extent = {
702 .width = width,
703 .height = height,
704 .depth = 1,
705 },
706 .mipLevels = 1,
707 .arraySize = 1,
708 .samples = 1,
709 .tiling = VK_IMAGE_TILING_LINEAR,
710 .usage = VK_IMAGE_USAGE_SAMPLED_BIT,
711 .flags = 0,
712 };
713
714 struct anv_image *src_image, *dest_image;
715 anv_CreateImage(vk_device, &image_info, (VkImage *)&src_image);
716 anv_CreateImage(vk_device, &image_info, (VkImage *)&dest_image);
717
718 /* We could use a vk call to bind memory, but that would require
719 * creating a dummy memory object etc. so there's really no point.
720 */
721 src_image->bo = src;
722 src_image->offset = src_offset;
723 dest_image->bo = dest;
724 dest_image->offset = dest_offset;
725
726 struct anv_surface_view src_view;
727 anv_image_view_init(&src_view, cmd_buffer->device,
728 &(VkImageViewCreateInfo) {
729 .sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO,
730 .image = (VkImage)src_image,
731 .viewType = VK_IMAGE_VIEW_TYPE_2D,
732 .format = copy_format,
733 .channels = {
734 VK_CHANNEL_SWIZZLE_R,
735 VK_CHANNEL_SWIZZLE_G,
736 VK_CHANNEL_SWIZZLE_B,
737 VK_CHANNEL_SWIZZLE_A
738 },
739 .subresourceRange = {
740 .aspect = VK_IMAGE_ASPECT_COLOR,
741 .baseMipLevel = 0,
742 .mipLevels = 1,
743 .baseArraySlice = 0,
744 .arraySize = 1
745 },
746 .minLod = 0
747 },
748 cmd_buffer);
749
750 struct anv_surface_view dest_view;
751 anv_color_attachment_view_init(&dest_view, cmd_buffer->device,
752 &(VkColorAttachmentViewCreateInfo) {
753 .sType = VK_STRUCTURE_TYPE_COLOR_ATTACHMENT_VIEW_CREATE_INFO,
754 .image = (VkImage)dest_image,
755 .format = copy_format,
756 .mipLevel = 0,
757 .baseArraySlice = 0,
758 .arraySize = 1,
759 },
760 cmd_buffer);
761
762 meta_emit_blit(cmd_buffer,
763 &src_view,
764 (VkOffset3D) { 0, 0, 0 },
765 (VkExtent3D) { width, height, 1 },
766 &dest_view,
767 (VkOffset3D) { 0, 0, 0 },
768 (VkExtent3D) { width, height, 1 });
769
770 anv_DestroyObject(vk_device, VK_OBJECT_TYPE_IMAGE, (VkImage) src_image);
771 anv_DestroyObject(vk_device, VK_OBJECT_TYPE_IMAGE, (VkImage) dest_image);
772 }
773
774 void anv_CmdCopyBuffer(
775 VkCmdBuffer cmdBuffer,
776 VkBuffer srcBuffer,
777 VkBuffer destBuffer,
778 uint32_t regionCount,
779 const VkBufferCopy* pRegions)
780 {
781 struct anv_cmd_buffer *cmd_buffer = (struct anv_cmd_buffer *)cmdBuffer;
782 struct anv_buffer *src_buffer = (struct anv_buffer *)srcBuffer;
783 struct anv_buffer *dest_buffer = (struct anv_buffer *)destBuffer;
784 struct anv_saved_state saved_state;
785
786 meta_prepare_blit(cmd_buffer, &saved_state);
787
788 for (unsigned r = 0; r < regionCount; r++) {
789 uint64_t src_offset = src_buffer->offset + pRegions[r].srcOffset;
790 uint64_t dest_offset = dest_buffer->offset + pRegions[r].destOffset;
791 uint64_t copy_size = pRegions[r].copySize;
792
793 /* First, we compute the biggest format that can be used with the
794 * given offsets and size.
795 */
796 int cpp = 16;
797
798 int fs = ffs(src_offset) - 1;
799 if (fs != -1)
800 cpp = MIN2(cpp, 1 << fs);
801 assert(src_offset % cpp == 0);
802
803 fs = ffs(dest_offset) - 1;
804 if (fs != -1)
805 cpp = MIN2(cpp, 1 << fs);
806 assert(dest_offset % cpp == 0);
807
808 fs = ffs(pRegions[r].copySize) - 1;
809 if (fs != -1)
810 cpp = MIN2(cpp, 1 << fs);
811 assert(pRegions[r].copySize % cpp == 0);
812
813 VkFormat copy_format = vk_format_for_cpp(cpp);
814
815 /* This is maximum possible width/height our HW can handle */
816 uint64_t max_surface_dim = 1 << 14;
817
818 /* First, we make a bunch of max-sized copies */
819 uint64_t max_copy_size = max_surface_dim * max_surface_dim * cpp;
820 while (copy_size > max_copy_size) {
821 do_buffer_copy(cmd_buffer, src_buffer->bo, src_offset,
822 dest_buffer->bo, dest_offset,
823 max_surface_dim, max_surface_dim, copy_format);
824 copy_size -= max_copy_size;
825 src_offset += max_copy_size;
826 dest_offset += max_copy_size;
827 }
828
829 uint64_t height = copy_size / (max_surface_dim * cpp);
830 assert(height < max_surface_dim);
831 if (height != 0) {
832 uint64_t rect_copy_size = height * max_surface_dim * cpp;
833 do_buffer_copy(cmd_buffer, src_buffer->bo, src_offset,
834 dest_buffer->bo, dest_offset,
835 max_surface_dim, height, copy_format);
836 copy_size -= rect_copy_size;
837 src_offset += rect_copy_size;
838 dest_offset += rect_copy_size;
839 }
840
841 if (copy_size != 0) {
842 do_buffer_copy(cmd_buffer, src_buffer->bo, src_offset,
843 dest_buffer->bo, dest_offset,
844 copy_size / cpp, 1, copy_format);
845 }
846 }
847
848 meta_finish_blit(cmd_buffer, &saved_state);
849 }
850
851 void anv_CmdCopyImage(
852 VkCmdBuffer cmdBuffer,
853 VkImage srcImage,
854 VkImageLayout srcImageLayout,
855 VkImage destImage,
856 VkImageLayout destImageLayout,
857 uint32_t regionCount,
858 const VkImageCopy* pRegions)
859 {
860 struct anv_cmd_buffer *cmd_buffer = (struct anv_cmd_buffer *)cmdBuffer;
861 struct anv_image *src_image = (struct anv_image *)srcImage;
862 struct anv_saved_state saved_state;
863
864 meta_prepare_blit(cmd_buffer, &saved_state);
865
866 for (unsigned r = 0; r < regionCount; r++) {
867 struct anv_surface_view src_view;
868 anv_image_view_init(&src_view, cmd_buffer->device,
869 &(VkImageViewCreateInfo) {
870 .sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO,
871 .image = srcImage,
872 .viewType = VK_IMAGE_VIEW_TYPE_2D,
873 .format = src_image->format,
874 .channels = {
875 VK_CHANNEL_SWIZZLE_R,
876 VK_CHANNEL_SWIZZLE_G,
877 VK_CHANNEL_SWIZZLE_B,
878 VK_CHANNEL_SWIZZLE_A
879 },
880 .subresourceRange = {
881 .aspect = pRegions[r].srcSubresource.aspect,
882 .baseMipLevel = pRegions[r].srcSubresource.mipLevel,
883 .mipLevels = 1,
884 .baseArraySlice = pRegions[r].srcSubresource.arraySlice,
885 .arraySize = 1
886 },
887 .minLod = 0
888 },
889 cmd_buffer);
890
891 struct anv_surface_view dest_view;
892 anv_color_attachment_view_init(&dest_view, cmd_buffer->device,
893 &(VkColorAttachmentViewCreateInfo) {
894 .sType = VK_STRUCTURE_TYPE_COLOR_ATTACHMENT_VIEW_CREATE_INFO,
895 .image = destImage,
896 .format = src_image->format,
897 .mipLevel = pRegions[r].destSubresource.mipLevel,
898 .baseArraySlice = pRegions[r].destSubresource.arraySlice,
899 .arraySize = 1,
900 },
901 cmd_buffer);
902
903 meta_emit_blit(cmd_buffer,
904 &src_view,
905 pRegions[r].srcOffset,
906 pRegions[r].extent,
907 &dest_view,
908 pRegions[r].destOffset,
909 pRegions[r].extent);
910 }
911
912 meta_finish_blit(cmd_buffer, &saved_state);
913 }
914
915 void anv_CmdBlitImage(
916 VkCmdBuffer cmdBuffer,
917 VkImage srcImage,
918 VkImageLayout srcImageLayout,
919 VkImage destImage,
920 VkImageLayout destImageLayout,
921 uint32_t regionCount,
922 const VkImageBlit* pRegions)
923 {
924 struct anv_cmd_buffer *cmd_buffer = (struct anv_cmd_buffer *)cmdBuffer;
925 struct anv_image *src_image = (struct anv_image *)srcImage;
926 struct anv_image *dest_image = (struct anv_image *)destImage;
927 struct anv_saved_state saved_state;
928
929 meta_prepare_blit(cmd_buffer, &saved_state);
930
931 for (unsigned r = 0; r < regionCount; r++) {
932 struct anv_surface_view src_view;
933 anv_image_view_init(&src_view, cmd_buffer->device,
934 &(VkImageViewCreateInfo) {
935 .sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO,
936 .image = srcImage,
937 .viewType = VK_IMAGE_VIEW_TYPE_2D,
938 .format = src_image->format,
939 .channels = {
940 VK_CHANNEL_SWIZZLE_R,
941 VK_CHANNEL_SWIZZLE_G,
942 VK_CHANNEL_SWIZZLE_B,
943 VK_CHANNEL_SWIZZLE_A
944 },
945 .subresourceRange = {
946 .aspect = pRegions[r].srcSubresource.aspect,
947 .baseMipLevel = pRegions[r].srcSubresource.mipLevel,
948 .mipLevels = 1,
949 .baseArraySlice = pRegions[r].srcSubresource.arraySlice,
950 .arraySize = 1
951 },
952 .minLod = 0
953 },
954 cmd_buffer);
955
956 struct anv_surface_view dest_view;
957 anv_color_attachment_view_init(&dest_view, cmd_buffer->device,
958 &(VkColorAttachmentViewCreateInfo) {
959 .sType = VK_STRUCTURE_TYPE_COLOR_ATTACHMENT_VIEW_CREATE_INFO,
960 .image = destImage,
961 .format = dest_image->format,
962 .mipLevel = pRegions[r].destSubresource.mipLevel,
963 .baseArraySlice = pRegions[r].destSubresource.arraySlice,
964 .arraySize = 1,
965 },
966 cmd_buffer);
967
968 meta_emit_blit(cmd_buffer,
969 &src_view,
970 pRegions[r].srcOffset,
971 pRegions[r].srcExtent,
972 &dest_view,
973 pRegions[r].destOffset,
974 pRegions[r].destExtent);
975 }
976
977 meta_finish_blit(cmd_buffer, &saved_state);
978 }
979
980 void anv_CmdCopyBufferToImage(
981 VkCmdBuffer cmdBuffer,
982 VkBuffer srcBuffer,
983 VkImage destImage,
984 VkImageLayout destImageLayout,
985 uint32_t regionCount,
986 const VkBufferImageCopy* pRegions)
987 {
988 struct anv_cmd_buffer *cmd_buffer = (struct anv_cmd_buffer *)cmdBuffer;
989 VkDevice vk_device = (VkDevice) cmd_buffer->device;
990 struct anv_buffer *src_buffer = (struct anv_buffer *)srcBuffer;
991 struct anv_image *dest_image = (struct anv_image *)destImage;
992 struct anv_saved_state saved_state;
993
994 meta_prepare_blit(cmd_buffer, &saved_state);
995
996 for (unsigned r = 0; r < regionCount; r++) {
997 struct anv_image *src_image;
998 anv_CreateImage(vk_device,
999 &(VkImageCreateInfo) {
1000 .sType = VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO,
1001 .imageType = VK_IMAGE_TYPE_2D,
1002 .format = dest_image->format,
1003 .extent = {
1004 .width = pRegions[r].imageExtent.width,
1005 .height = pRegions[r].imageExtent.height,
1006 .depth = 1,
1007 },
1008 .mipLevels = 1,
1009 .arraySize = 1,
1010 .samples = 1,
1011 .tiling = VK_IMAGE_TILING_LINEAR,
1012 .usage = VK_IMAGE_USAGE_SAMPLED_BIT,
1013 .flags = 0,
1014 }, (VkImage *)&src_image);
1015
1016 /* We could use a vk call to bind memory, but that would require
1017 * creating a dummy memory object etc. so there's really no point.
1018 */
1019 src_image->bo = src_buffer->bo;
1020 src_image->offset = src_buffer->offset + pRegions[r].bufferOffset;
1021
1022 struct anv_surface_view src_view;
1023 anv_image_view_init(&src_view, cmd_buffer->device,
1024 &(VkImageViewCreateInfo) {
1025 .sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO,
1026 .image = (VkImage)src_image,
1027 .viewType = VK_IMAGE_VIEW_TYPE_2D,
1028 .format = dest_image->format,
1029 .channels = {
1030 VK_CHANNEL_SWIZZLE_R,
1031 VK_CHANNEL_SWIZZLE_G,
1032 VK_CHANNEL_SWIZZLE_B,
1033 VK_CHANNEL_SWIZZLE_A
1034 },
1035 .subresourceRange = {
1036 .aspect = pRegions[r].imageSubresource.aspect,
1037 .baseMipLevel = 0,
1038 .mipLevels = 1,
1039 .baseArraySlice = 0,
1040 .arraySize = 1
1041 },
1042 .minLod = 0
1043 },
1044 cmd_buffer);
1045
1046 struct anv_surface_view dest_view;
1047 anv_color_attachment_view_init(&dest_view, cmd_buffer->device,
1048 &(VkColorAttachmentViewCreateInfo) {
1049 .sType = VK_STRUCTURE_TYPE_COLOR_ATTACHMENT_VIEW_CREATE_INFO,
1050 .image = (VkImage)dest_image,
1051 .format = dest_image->format,
1052 .mipLevel = pRegions[r].imageSubresource.mipLevel,
1053 .baseArraySlice = pRegions[r].imageSubresource.arraySlice,
1054 .arraySize = 1,
1055 },
1056 cmd_buffer);
1057
1058 meta_emit_blit(cmd_buffer,
1059 &src_view,
1060 (VkOffset3D) { 0, 0, 0 },
1061 pRegions[r].imageExtent,
1062 &dest_view,
1063 pRegions[r].imageOffset,
1064 pRegions[r].imageExtent);
1065
1066 anv_DestroyObject(vk_device, VK_OBJECT_TYPE_IMAGE, (VkImage) src_image);
1067 }
1068
1069 meta_finish_blit(cmd_buffer, &saved_state);
1070 }
1071
1072 void anv_CmdCopyImageToBuffer(
1073 VkCmdBuffer cmdBuffer,
1074 VkImage srcImage,
1075 VkImageLayout srcImageLayout,
1076 VkBuffer destBuffer,
1077 uint32_t regionCount,
1078 const VkBufferImageCopy* pRegions)
1079 {
1080 struct anv_cmd_buffer *cmd_buffer = (struct anv_cmd_buffer *)cmdBuffer;
1081 VkDevice vk_device = (VkDevice) cmd_buffer->device;
1082 struct anv_image *src_image = (struct anv_image *)srcImage;
1083 struct anv_buffer *dest_buffer = (struct anv_buffer *)destBuffer;
1084 struct anv_saved_state saved_state;
1085
1086 meta_prepare_blit(cmd_buffer, &saved_state);
1087
1088 for (unsigned r = 0; r < regionCount; r++) {
1089 struct anv_surface_view src_view;
1090 anv_image_view_init(&src_view, cmd_buffer->device,
1091 &(VkImageViewCreateInfo) {
1092 .sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO,
1093 .image = srcImage,
1094 .viewType = VK_IMAGE_VIEW_TYPE_2D,
1095 .format = src_image->format,
1096 .channels = {
1097 VK_CHANNEL_SWIZZLE_R,
1098 VK_CHANNEL_SWIZZLE_G,
1099 VK_CHANNEL_SWIZZLE_B,
1100 VK_CHANNEL_SWIZZLE_A
1101 },
1102 .subresourceRange = {
1103 .aspect = pRegions[r].imageSubresource.aspect,
1104 .baseMipLevel = pRegions[r].imageSubresource.mipLevel,
1105 .mipLevels = 1,
1106 .baseArraySlice = pRegions[r].imageSubresource.arraySlice,
1107 .arraySize = 1
1108 },
1109 .minLod = 0
1110 },
1111 cmd_buffer);
1112
1113 struct anv_image *dest_image;
1114 anv_CreateImage(vk_device,
1115 &(VkImageCreateInfo) {
1116 .sType = VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO,
1117 .imageType = VK_IMAGE_TYPE_2D,
1118 .format = src_image->format,
1119 .extent = {
1120 .width = pRegions[r].imageExtent.width,
1121 .height = pRegions[r].imageExtent.height,
1122 .depth = 1,
1123 },
1124 .mipLevels = 1,
1125 .arraySize = 1,
1126 .samples = 1,
1127 .tiling = VK_IMAGE_TILING_LINEAR,
1128 .usage = VK_IMAGE_USAGE_SAMPLED_BIT,
1129 .flags = 0,
1130 }, (VkImage *)&dest_image);
1131
1132 /* We could use a vk call to bind memory, but that would require
1133 * creating a dummy memory object etc. so there's really no point.
1134 */
1135 dest_image->bo = dest_buffer->bo;
1136 dest_image->offset = dest_buffer->offset + pRegions[r].bufferOffset;
1137
1138 struct anv_surface_view dest_view;
1139 anv_color_attachment_view_init(&dest_view, cmd_buffer->device,
1140 &(VkColorAttachmentViewCreateInfo) {
1141 .sType = VK_STRUCTURE_TYPE_COLOR_ATTACHMENT_VIEW_CREATE_INFO,
1142 .image = (VkImage)dest_image,
1143 .format = src_image->format,
1144 .mipLevel = 0,
1145 .baseArraySlice = 0,
1146 .arraySize = 1,
1147 },
1148 cmd_buffer);
1149
1150 meta_emit_blit(cmd_buffer,
1151 &src_view,
1152 pRegions[r].imageOffset,
1153 pRegions[r].imageExtent,
1154 &dest_view,
1155 (VkOffset3D) { 0, 0, 0 },
1156 pRegions[r].imageExtent);
1157
1158 anv_DestroyObject(vk_device, VK_OBJECT_TYPE_IMAGE, (VkImage) dest_image);
1159 }
1160
1161 meta_finish_blit(cmd_buffer, &saved_state);
1162 }
1163
1164 void anv_CmdUpdateBuffer(
1165 VkCmdBuffer cmdBuffer,
1166 VkBuffer destBuffer,
1167 VkDeviceSize destOffset,
1168 VkDeviceSize dataSize,
1169 const uint32_t* pData)
1170 {
1171 stub();
1172 }
1173
1174 void anv_CmdFillBuffer(
1175 VkCmdBuffer cmdBuffer,
1176 VkBuffer destBuffer,
1177 VkDeviceSize destOffset,
1178 VkDeviceSize fillSize,
1179 uint32_t data)
1180 {
1181 stub();
1182 }
1183
1184 void anv_CmdClearColorImage(
1185 VkCmdBuffer cmdBuffer,
1186 VkImage _image,
1187 VkImageLayout imageLayout,
1188 const VkClearColorValue* pColor,
1189 uint32_t rangeCount,
1190 const VkImageSubresourceRange* pRanges)
1191 {
1192 struct anv_cmd_buffer *cmd_buffer = (struct anv_cmd_buffer *)cmdBuffer;
1193 struct anv_image *image = (struct anv_image *)_image;
1194 struct anv_saved_state saved_state;
1195
1196 anv_cmd_buffer_save(cmd_buffer, &saved_state);
1197
1198 for (uint32_t r = 0; r < rangeCount; r++) {
1199 for (uint32_t l = 0; l < pRanges[r].mipLevels; l++) {
1200 for (uint32_t s = 0; s < pRanges[r].arraySize; s++) {
1201 struct anv_surface_view view;
1202 anv_color_attachment_view_init(&view, cmd_buffer->device,
1203 &(VkColorAttachmentViewCreateInfo) {
1204 .sType = VK_STRUCTURE_TYPE_COLOR_ATTACHMENT_VIEW_CREATE_INFO,
1205 .image = _image,
1206 .format = image->format,
1207 .mipLevel = pRanges[r].baseMipLevel + l,
1208 .baseArraySlice = pRanges[r].baseArraySlice + s,
1209 .arraySize = 1,
1210 },
1211 cmd_buffer);
1212
1213 VkFramebuffer fb;
1214 anv_CreateFramebuffer((VkDevice) cmd_buffer->device,
1215 &(VkFramebufferCreateInfo) {
1216 .sType = VK_STRUCTURE_TYPE_FRAMEBUFFER_CREATE_INFO,
1217 .colorAttachmentCount = 1,
1218 .pColorAttachments = (VkColorAttachmentBindInfo[]) {
1219 {
1220 .view = (VkColorAttachmentView) &view,
1221 .layout = VK_IMAGE_LAYOUT_GENERAL
1222 }
1223 },
1224 .pDepthStencilAttachment = NULL,
1225 .sampleCount = 1,
1226 .width = view.extent.width,
1227 .height = view.extent.height,
1228 .layers = 1
1229 }, &fb);
1230
1231 VkRenderPass pass;
1232 anv_CreateRenderPass((VkDevice) cmd_buffer->device,
1233 &(VkRenderPassCreateInfo) {
1234 .sType = VK_STRUCTURE_TYPE_RENDER_PASS_CREATE_INFO,
1235 .renderArea = { { 0, 0 }, { view.extent.width, view.extent.height } },
1236 .colorAttachmentCount = 1,
1237 .extent = { 0, },
1238 .sampleCount = 1,
1239 .layers = 1,
1240 .pColorFormats = (VkFormat[]) { image->format },
1241 .pColorLayouts = (VkImageLayout[]) { imageLayout },
1242 .pColorLoadOps = (VkAttachmentLoadOp[]) { VK_ATTACHMENT_LOAD_OP_DONT_CARE },
1243 .pColorStoreOps = (VkAttachmentStoreOp[]) { VK_ATTACHMENT_STORE_OP_STORE },
1244 .pColorLoadClearValues = pColor,
1245 .depthStencilFormat = VK_FORMAT_UNDEFINED,
1246 }, &pass);
1247
1248 anv_CmdBeginRenderPass((VkCmdBuffer) cmd_buffer,
1249 &(VkRenderPassBegin) {
1250 .renderPass = pass,
1251 .framebuffer = (VkFramebuffer) fb,
1252 });
1253
1254 struct clear_instance_data instance_data = {
1255 .vue_header = {
1256 .RTAIndex = 0,
1257 .ViewportIndex = 0,
1258 .PointWidth = 0.0
1259 },
1260 .color = *pColor,
1261 };
1262
1263 meta_emit_clear(cmd_buffer, 1, &instance_data);
1264
1265 anv_CmdEndRenderPass((VkCmdBuffer) cmd_buffer);
1266 }
1267 }
1268 }
1269
1270 /* Restore API state */
1271 anv_cmd_buffer_restore(cmd_buffer, &saved_state);
1272 }
1273
1274 void anv_CmdClearDepthStencilImage(
1275 VkCmdBuffer cmdBuffer,
1276 VkImage image,
1277 VkImageLayout imageLayout,
1278 float depth,
1279 uint32_t stencil,
1280 uint32_t rangeCount,
1281 const VkImageSubresourceRange* pRanges)
1282 {
1283 stub();
1284 }
1285
1286 void anv_CmdClearColorAttachment(
1287 VkCmdBuffer cmdBuffer,
1288 uint32_t colorAttachment,
1289 VkImageLayout imageLayout,
1290 const VkClearColorValue* pColor,
1291 uint32_t rectCount,
1292 const VkRect3D* pRects)
1293 {
1294 stub();
1295 }
1296
1297 void anv_CmdClearDepthStencilAttachment(
1298 VkCmdBuffer cmdBuffer,
1299 VkImageAspectFlags imageAspectMask,
1300 VkImageLayout imageLayout,
1301 float depth,
1302 uint32_t stencil,
1303 uint32_t rectCount,
1304 const VkRect3D* pRects)
1305 {
1306 stub();
1307 }
1308
1309 void anv_CmdResolveImage(
1310 VkCmdBuffer cmdBuffer,
1311 VkImage srcImage,
1312 VkImageLayout srcImageLayout,
1313 VkImage destImage,
1314 VkImageLayout destImageLayout,
1315 uint32_t regionCount,
1316 const VkImageResolve* pRegions)
1317 {
1318 stub();
1319 }
1320
1321 void
1322 anv_device_init_meta(struct anv_device *device)
1323 {
1324 anv_device_init_meta_clear_state(device);
1325 anv_device_init_meta_blit_state(device);
1326
1327 anv_CreateDynamicRasterState((VkDevice) device,
1328 &(VkDynamicRsStateCreateInfo) {
1329 .sType = VK_STRUCTURE_TYPE_DYNAMIC_RS_STATE_CREATE_INFO,
1330 },
1331 &device->meta_state.shared.rs_state);
1332
1333 anv_CreateDynamicColorBlendState((VkDevice) device,
1334 &(VkDynamicCbStateCreateInfo) {
1335 .sType = VK_STRUCTURE_TYPE_DYNAMIC_CB_STATE_CREATE_INFO
1336 },
1337 &device->meta_state.shared.cb_state);
1338
1339 anv_CreateDynamicDepthStencilState((VkDevice) device,
1340 &(VkDynamicDsStateCreateInfo) {
1341 .sType = VK_STRUCTURE_TYPE_DYNAMIC_DS_STATE_CREATE_INFO
1342 },
1343 &device->meta_state.shared.ds_state);
1344 }
1345
1346 void
1347 anv_device_finish_meta(struct anv_device *device)
1348 {
1349 /* Clear */
1350 anv_DestroyObject((VkDevice) device, VK_OBJECT_TYPE_PIPELINE,
1351 device->meta_state.clear.pipeline);
1352
1353 /* Blit */
1354 anv_DestroyObject((VkDevice) device, VK_OBJECT_TYPE_PIPELINE,
1355 device->meta_state.blit.pipeline);
1356 anv_DestroyObject((VkDevice) device, VK_OBJECT_TYPE_PIPELINE_LAYOUT,
1357 device->meta_state.blit.pipeline_layout);
1358 anv_DestroyObject((VkDevice) device, VK_OBJECT_TYPE_DESCRIPTOR_SET_LAYOUT,
1359 device->meta_state.blit.ds_layout);
1360
1361 /* Shared */
1362 anv_DestroyObject((VkDevice) device, VK_OBJECT_TYPE_DYNAMIC_RS_STATE,
1363 device->meta_state.shared.rs_state);
1364 anv_DestroyObject((VkDevice) device, VK_OBJECT_TYPE_DYNAMIC_CB_STATE,
1365 device->meta_state.shared.cb_state);
1366 anv_DestroyObject((VkDevice) device, VK_OBJECT_TYPE_DYNAMIC_DS_STATE,
1367 device->meta_state.shared.ds_state);
1368 }