intel: add support for vkCmdExecuteCommands()
Only supported on Gen7.5+. Add some error checks to catch common user errors.
diff --git a/icd/intel/cmd_pipeline.c b/icd/intel/cmd_pipeline.c
index 5e7cf67..79d0d2d 100644
--- a/icd/intel/cmd_pipeline.c
+++ b/icd/intel/cmd_pipeline.c
@@ -3396,6 +3396,26 @@
cmd_batch_flush_all(cmd);
}
+static void cmd_exec(struct intel_cmd *cmd, struct intel_bo *bo)
+{
+ const uint8_t cmd_len = 2;
+ uint32_t *dw;
+ uint32_t pos;
+
+ if (cmd_gen(cmd) < INTEL_GEN(7.5)) {
+ cmd->result = VK_ERROR_UNKNOWN;
+ return;
+ }
+
+ pos = cmd_batch_pointer(cmd, cmd_len, &dw);
+ dw[0] = GEN6_MI_CMD(MI_BATCH_BUFFER_START) | (cmd_len - 2) |
+ GEN75_MI_BATCH_BUFFER_START_DW0_SECOND_LEVEL |
+ GEN75_MI_BATCH_BUFFER_START_DW0_NON_PRIVILEGED |
+ GEN6_MI_BATCH_BUFFER_START_DW0_USE_PPGTT;
+
+ cmd_batch_reloc(cmd, pos + 1, bo, 0, 0);
+}
+
ICD_EXPORT void VKAPI vkCmdBindPipeline(
VkCmdBuffer cmdBuffer,
VkPipelineBindPoint pipelineBindPoint,
@@ -3598,7 +3618,12 @@
struct intel_fb *fb = (struct intel_fb *) pRenderPassBegin->framebuffer;
unsigned i;
- cmd_begin_render_pass(cmd, rp, fb);
+ if (!cmd->primary) {
+ cmd_fail(cmd, VK_ERROR_UNKNOWN);
+ return;
+ }
+
+ cmd_begin_render_pass(cmd, rp, fb, pRenderPassBegin->contents);
/* issue load ops */
for (i = 0; i < rp->colorAttachmentCount; i++) {
@@ -3637,6 +3662,25 @@
const VkCmdBuffer* pCmdBuffers)
{
struct intel_cmd *cmd = intel_cmd(cmdBuffer);
+ uint32_t i;
- cmd->result = VK_ERROR_UNKNOWN;
+ if (!cmd->bind.render_pass || cmd->bind.render_pass_contents !=
+ VK_RENDER_PASS_CONTENTS_SECONDARY_CMD_BUFFERS) {
+ cmd_fail(cmd, VK_ERROR_UNKNOWN);
+ return;
+ }
+
+ for (i = 0; i < cmdBuffersCount; i++) {
+ const struct intel_cmd *secondary = intel_cmd(pCmdBuffers[i]);
+
+ if (secondary->primary) {
+ cmd->result = VK_ERROR_INVALID_VALUE;
+ break;
+ }
+
+ cmd_exec(cmd, intel_cmd_get_batch(secondary, NULL));
+ }
+
+ if (i)
+ cmd_batch_state_base_address(cmd);
}