1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198
// Copyright (c) 2016 The vulkano developers // Licensed under the Apache License, Version 2.0 // <LICENSE-APACHE or // http://www.apache.org/licenses/LICENSE-2.0> or the MIT // license <LICENSE-MIT or http://opensource.org/licenses/MIT>, // at your option. All files in the project carrying such // notice may not be copied, modified, or distributed except // according to those terms. use std::ops::Range; use std::sync::Arc; use command_buffer::Submission; use format::ClearValue; use format::Format; use image::sys::Dimensions; use image::sys::Layout; use image::sys::UnsafeImage; use image::sys::UnsafeImageView; use sampler::Sampler; use sync::Semaphore; pub unsafe trait Image: 'static + Send + Sync { /// Returns the inner unsafe image object used by this image. // TODO: should be named "inner()" after https://github.com/rust-lang/rust/issues/12808 is fixed fn inner_image(&self) -> &UnsafeImage; //fn align(&self, subresource_range: ) -> ; /// Returns the format of this image. #[inline] fn format(&self) -> Format { self.inner_image().format() } #[inline] fn samples(&self) -> u32 { self.inner_image().samples() } /// Returns the dimensions of the image. #[inline] fn dimensions(&self) -> Dimensions { self.inner_image().dimensions() } /// Given a range, returns the list of blocks which each range is contained in. /// /// Each block must have a unique number. Hint: it can simply be the offset of the start of the /// mipmap and array layer. /// Calling this function multiple times with the same parameter must always return the same /// value. /// The return value must not be empty. fn blocks(&self, mipmap_levels: Range<u32>, array_layers: Range<u32>) -> Vec<(u32, u32)>; fn block_mipmap_levels_range(&self, block: (u32, u32)) -> Range<u32>; fn block_array_layers_range(&self, block: (u32, u32)) -> Range<u32>; /// Called when a command buffer that uses this image is being built. Given a block, this /// function should return the layout that the block will have when the command buffer is /// submitted. /// /// The `first_required_layout` is provided as a hint and corresponds to the first layout /// that the image will be used for. If this function returns a value different from /// `first_required_layout`, then a layout transition will be performed by the command buffer. /// /// The two additional elements are: /// /// - Whether a pipeline barrier should be added in order to address a read or write from /// the host (VK_ACCESS_HOST_READ_BIT | VK_ACCESS_HOST_WRITE_BIT). /// - Whether a pipeline barrier should be added in order to address a read or write from /// memory (VK_ACCESS_MEMORY_READ_BIT | VK_ACCESS_MEMORY_WRITE_BIT). /// fn initial_layout(&self, block: (u32, u32), first_required_layout: Layout) -> (Layout, bool, bool); /// Called when a command buffer that uses this image is being built. Given a block, this /// function should return the layout that the block must have when the command buffer is /// end. /// /// The `last_required_layout` is provided as a hint and corresponds to the last layout /// that the image will be in at the end of the command buffer. If this function returns a /// value different from `last_required_layout`, then a layout transition will be performed /// by the command buffer. /// /// The two additional elements are: /// /// - Whether a pipeline barrier should be added in order to address a read or write from /// the host (VK_ACCESS_HOST_READ_BIT | VK_ACCESS_HOST_WRITE_BIT). /// - Whether a pipeline barrier should be added in order to address a read or write from /// memory (VK_ACCESS_MEMORY_READ_BIT | VK_ACCESS_MEMORY_WRITE_BIT). /// fn final_layout(&self, block: (u32, u32), last_required_layout: Layout) -> (Layout, bool, bool); /// Returns whether accessing a subresource of that image should signal a fence. fn needs_fence(&self, access: &mut Iterator<Item = AccessRange>) -> Option<bool>; /// /// **Important**: The `Submission` object likely holds an `Arc` to `self`. Therefore you /// should store the `Submission` in the form of a `Weak<Submission>` and not /// of an `Arc<Submission>` to avoid cyclic references. unsafe fn gpu_access(&self, access: &mut Iterator<Item = AccessRange>, submission: &Arc<Submission>) -> GpuAccessResult; /// Returns true if the image can be used as a source for blits. #[inline] fn supports_blit_source(&self) -> bool { self.inner_image().supports_blit_source() } /// Returns true if the image can be used as a destination for blits. #[inline] fn supports_blit_destination(&self) -> bool { self.inner_image().supports_blit_destination() } } pub unsafe trait ImageClearValue<T>: Image { fn decode(&self, T) -> Option<ClearValue>; } pub unsafe trait ImageContent<P>: Image { /// Checks whether pixels of type `P` match the format of the image. fn matches_format(&self) -> bool; } pub unsafe trait ImageView: 'static + Send + Sync { fn parent(&self) -> &Image; fn parent_arc(&Arc<Self>) -> Arc<Image> where Self: Sized; /// Returns the inner unsafe image view object used by this image view. // TODO: should be named "inner()" after https://github.com/rust-lang/rust/issues/12808 is fixed fn inner_view(&self) -> &UnsafeImageView; /// Returns the blocks of the parent image this image view overlaps. fn blocks(&self) -> Vec<(u32, u32)>; /// Returns the format of this view. This can be different from the parent's format. #[inline] fn format(&self) -> Format { self.inner_view().format() } #[inline] fn samples(&self) -> u32 { self.parent().samples() } /// Returns the image layout to use in a descriptor with the given subresource. fn descriptor_set_storage_image_layout(&self) -> Layout; /// Returns the image layout to use in a descriptor with the given subresource. fn descriptor_set_combined_image_sampler_layout(&self) -> Layout; /// Returns the image layout to use in a descriptor with the given subresource. fn descriptor_set_sampled_image_layout(&self) -> Layout; /// Returns the image layout to use in a descriptor with the given subresource. fn descriptor_set_input_attachment_layout(&self) -> Layout; /// Returns true if the view doesn't use components swizzling. /// /// Must be true when the view is used as a framebuffer attachment or TODO: I don't remember /// the other thing. fn identity_swizzle(&self) -> bool; /// Returns true if the given sampler can be used with this image view. /// /// This method should check whether the sampler's configuration can be used with the format /// of the view. // TODO: return a Result fn can_be_sampled(&self, sampler: &Sampler) -> bool { true /* FIXME */ } //fn usable_as_render_pass_attachment(&self, ???) -> Result<(), ???>; } pub unsafe trait AttachmentImageView: ImageView { fn accept(&self, initial_layout: Layout, final_layout: Layout) -> bool; } #[derive(Debug, Clone)] pub struct AccessRange { pub block: (u32, u32), pub write: bool, pub initial_layout: Layout, pub final_layout: Layout, } pub struct GpuAccessResult { pub dependencies: Vec<Arc<Submission>>, pub additional_wait_semaphore: Option<Arc<Semaphore>>, pub additional_signal_semaphore: Option<Arc<Semaphore>>, pub before_transitions: Vec<Transition>, pub after_transitions: Vec<Transition>, } pub struct Transition { pub block: (u32, u32), pub from: Layout, pub to: Layout, }