From 040efa2820e45675fc4ebc54648e288eefed9827 Mon Sep 17 00:00:00 2001 From: Dzmitry Malyshau Date: Tue, 31 Dec 2019 18:57:09 -0500 Subject: [PATCH] Fix refcount use of the texture view source --- wgpu-core/src/command/mod.rs | 33 ++++++++++++++++++--------------- wgpu-core/src/device/mod.rs | 11 +++++++---- wgpu-core/src/swap_chain.rs | 4 ++-- 3 files changed, 27 insertions(+), 21 deletions(-) diff --git a/wgpu-core/src/command/mod.rs b/wgpu-core/src/command/mod.rs index 9b5fa00e41..c88319c56d 100644 --- a/wgpu-core/src/command/mod.rs +++ b/wgpu-core/src/command/mod.rs @@ -252,7 +252,11 @@ impl> Global { ); const MAX_TOTAL_ATTACHMENTS: usize = 10; - type OutputAttachment<'a> = (TextureId, &'a hal::image::SubresourceRange, Option); + type OutputAttachment<'a> = ( + &'a Stored, + &'a hal::image::SubresourceRange, + Option, + ); let mut output_attachments = ArrayVec::<[OutputAttachment; MAX_TOTAL_ATTACHMENTS]>::new(); log::trace!( @@ -271,8 +275,8 @@ impl> Global { } else { extent = Some(view.extent); } - let texture_id = match view.inner { - TextureViewInner::Native { ref source_id, .. } => source_id.value, + let source_id = match view.inner { + TextureViewInner::Native { ref source_id, .. } => source_id, TextureViewInner::SwapChain { .. } => { panic!("Unexpected depth/stencil use of swapchain image!") } @@ -280,10 +284,10 @@ impl> Global { // Using render pass for transition. let consistent_usage = cmb.trackers.textures.query( - texture_id, + source_id.value, view.range.clone(), ); - output_attachments.push((texture_id, &view.range, consistent_usage)); + output_attachments.push((source_id, &view.range, consistent_usage)); let old_layout = match consistent_usage { Some(usage) => conv::map_texture_state( @@ -333,7 +337,7 @@ impl> Global { source_id.value, view.range.clone(), ); - output_attachments.push((source_id.value, &view.range, consistent_usage)); + output_attachments.push((source_id, &view.range, consistent_usage)); let old_layout = match consistent_usage { Some(usage) => conv::map_texture_state(usage, hal::format::Aspects::COLOR).1, @@ -393,7 +397,7 @@ impl> Global { source_id.value, view.range.clone(), ); - output_attachments.push((source_id.value, &view.range, consistent_usage)); + output_attachments.push((source_id, &view.range, consistent_usage)); let old_layout = match consistent_usage { Some(usage) => conv::map_texture_state(usage, hal::format::Aspects::COLOR).1, @@ -442,27 +446,26 @@ impl> Global { }; let mut trackers = TrackerSet::new(B::VARIANT); - for (texture_id, view_range, consistent_usage) in output_attachments { - let texture = &texture_guard[texture_id]; + for (source_id, view_range, consistent_usage) in output_attachments { + let texture = &texture_guard[source_id.value]; assert!(texture.usage.contains(TextureUsage::OUTPUT_ATTACHMENT)); let usage = consistent_usage.unwrap_or(TextureUsage::OUTPUT_ATTACHMENT); - let ref_count = texture.life_guard.ref_count.as_ref().unwrap(); match trackers.textures.init( - texture_id, - ref_count.clone(), + source_id.value, + source_id.ref_count.clone(), &texture.full_range, ) { Some(mut init) => init.set(view_range.clone(), usage), - None => panic!("Your texture {:?} is in the another attachment!", texture_id), + None => panic!("Your texture {:?} is in the another attachment!", source_id.value), }; if consistent_usage.is_some() { // If we expect the texture to be transited to a new state by the // render pass configuration, make the tracker aware of that. let _ = trackers.textures.change_replace( - texture_id, - ref_count, + source_id.value, + &source_id.ref_count, view_range.clone(), TextureUsage::OUTPUT_ATTACHMENT, &texture.full_range, diff --git a/wgpu-core/src/device/mod.rs b/wgpu-core/src/device/mod.rs index cbf2e639dd..05ddb28b66 100644 --- a/wgpu-core/src/device/mod.rs +++ b/wgpu-core/src/device/mod.rs @@ -1069,13 +1069,16 @@ impl> Global { ref raw, ref source_id, } => { - let texture = used - .textures - .use_extend( - &*texture_guard, + // Careful here: the texture may no longer have its own ref count, + // if it was deleted by the user. + let texture = &texture_guard[source_id.value]; + used.textures + .change_extend( source_id.value, + &source_id.ref_count, view.range.clone(), usage, + &texture.full_range, ) .unwrap(); assert!(texture.usage.contains(usage)); diff --git a/wgpu-core/src/swap_chain.rs b/wgpu-core/src/swap_chain.rs index 757a82a471..b760de378a 100644 --- a/wgpu-core/src/swap_chain.rs +++ b/wgpu-core/src/swap_chain.rs @@ -167,7 +167,7 @@ impl> Global { image, source_id: Stored { value: swap_chain_id, - ref_count: sc.life_guard.ref_count.clone().unwrap(), + ref_count: sc.life_guard.add_ref(), }, framebuffers: SmallVec::new(), }, @@ -185,7 +185,7 @@ impl> Global { }, life_guard: LifeGuard::new(), }; - let ref_count = view.life_guard.ref_count.clone().unwrap(); + let ref_count = view.life_guard.add_ref(); let view_id = hub .texture_views .register_identity(view_id_in, view, &mut token);