diff --git a/vulkano/src/command_buffer/auto.rs b/vulkano/src/command_buffer/auto.rs index 468157ae8..677be2381 100644 --- a/vulkano/src/command_buffer/auto.rs +++ b/vulkano/src/command_buffer/auto.rs @@ -65,12 +65,18 @@ use sync::PipelineStages; pub struct AutoCommandBufferBuilder
{ inner: SyncCommandBufferBuilder
,
state_cacher: StateCacher,
+
// Contains the number of subpasses remaining in the current render pass, or `None` if we're
// outside a render pass. If this is `Some(0)`, the user must call `end_render_pass`. If this
// is `Some(1)` or more, the user must call `next_subpass`.
subpasses_remaining: Option AutoCommandBufferBuilder {
}
#[inline]
- fn ensure_inside_render_pass(&self) -> Result<(), AutoCommandBufferBuilderContextError> {
+ fn ensure_inside_render_pass(&self, secondary: bool)
+ -> Result<(), AutoCommandBufferBuilderContextError>
+ {
if self.subpasses_remaining.is_some() {
- Ok(())
+ if self.subpass_secondary == secondary {
+ Ok(())
+ } else {
+ Err(AutoCommandBufferBuilderContextError::WrongSubpassType)
+ }
} else {
Err(AutoCommandBufferBuilderContextError::ForbiddenOutsideRenderPass)
}
@@ -151,6 +164,7 @@ impl AutoCommandBufferBuilder {
self.inner
.begin_render_pass(framebuffer, contents, clear_values)?;
self.subpasses_remaining = Some(num_subpasses - 1);
+ self.subpass_secondary = secondary;
Ok(self)
}
}
@@ -260,7 +274,7 @@ impl AutoCommandBufferBuilder {
unsafe {
// TODO: must check that pipeline is compatible with render pass
- self.ensure_inside_render_pass()?;
+ self.ensure_inside_render_pass(false)?;
check_dynamic_state_validity(&pipeline, &dynamic)?;
check_push_constants_validity(&pipeline, &constants)?;
check_descriptor_sets_validity(&pipeline, &sets)?;
@@ -296,7 +310,7 @@ impl AutoCommandBufferBuilder {
unsafe {
// TODO: must check that pipeline is compatible with render pass
- self.ensure_inside_render_pass()?;
+ self.ensure_inside_render_pass(false)?;
let ib_infos = check_index_buffer(self.device(), &index_buffer)?;
check_dynamic_state_validity(&pipeline, &dynamic)?;
check_push_constants_validity(&pipeline, &constants)?;
@@ -341,7 +355,7 @@ impl AutoCommandBufferBuilder {
unsafe {
// TODO: must check that pipeline is compatible with render pass
- self.ensure_inside_render_pass()?;
+ self.ensure_inside_render_pass(false)?;
check_dynamic_state_validity(&pipeline, &dynamic)?;
check_push_constants_validity(&pipeline, &constants)?;
check_descriptor_sets_validity(&pipeline, &sets)?;
@@ -435,7 +449,9 @@ impl AutoCommandBufferBuilder {
Some(ref mut num) => {
*num -= 1;
}
- }
+ };
+
+ self.subpass_secondary = secondary;
let contents = if secondary { SubpassContents::SecondaryCommandBuffers }
else { SubpassContents::Inline };
@@ -716,6 +732,9 @@ pub enum AutoCommandBufferBuilderContextError {
/// Tried to end a render pass with subpasses remaining, or tried to go to next subpass with no
/// subpass remaining.
NumSubpassesMismatch,
+ /// Tried to execute a secondary command buffer inside a subpass that only allows inline
+ /// commands, or a draw command in a subpass that only allows secondary command buffers.
+ WrongSubpassType,
}
impl error::Error for AutoCommandBufferBuilderContextError {
@@ -735,6 +754,11 @@ impl error::Error for AutoCommandBufferBuilderContextError {
"tried to end a render pass with subpasses remaining, or tried to go to next \
subpass with no subpass remaining"
},
+ AutoCommandBufferBuilderContextError::WrongSubpassType => {
+ "tried to execute a secondary command buffer inside a subpass that only allows \
+ inline commands, or a draw command in a subpass that only allows secondary \
+ command buffers"
+ },
}
}
}